У меня есть прокси Kamailio 4.0.4 (K) с регистратором и tm. Для некоторых AOR существует несколько клиентов, и все они автоматически принимают определенные INVITE, которые вызывают состояние гонки и имеют 200 OK из нескольких ветвей, отправляемых вызываемому.
Сценарий: - A отправляет приглашение B
- K находит 2 контакта в uloc для B, назовем их B1 и B2.
INVITE разветвляется и отправляется на B1 и B2. Примечание. B1 имеет задержку канала 100 мс, а задержка B2 — 150 мс.
И B1, и B2 автоматически принимают с 200 OK сразу же, как они его получают.
Через 200 мс после ветвления INVITE K получает 200 OK от B1 и передает его A
- K также ОТМЕНЯЕТ ПРИГЛАШЕНИЕ на B2
A на самом деле является локальной AS, которая мгновенно отправляет ACK 200 OK обратно B1.
Теперь проблема в том, что B2 уже отправил 200 OK 50 мс назад и не получит CANCEL еще 150 мс.
Таким образом, 200 OK от B2 приходит к K, но вызов уже установлен между A и B1.
- Что происходит, так это то, что 200 OK передается на A, который в этот момент совершенно запутался, потому что, если честно, это не очень хорошая AS.
Теперь к самому вопросу: как сделать так, чтобы лишние 200 OK не попали в A?
Я вижу несколько вариантов того, как это должно работать:
- Бросьте 200 ОК, просто выбросьте его. B2 не должен повторно отправлять его, потому что вскоре появится сообщение CANCEL.
- ACK + BYE 200 OK изнутри Kamailio, но это приведет к тому, что медиа-сессия будет запущена и немедленно прервана B2.
Я даже не могу найти RFC, охватывающий это состояние гонки.