Повторное использование номера порта в UDP - PullRequest
1 голос
/ 21 сентября 2010

В ASIO возможно ли создать еще один сокет, имеющий тот же порт источника, что и другой сокет?

Мое приложение сервера UDP вызывает receive_from, используя порт 3000. Он передает пакет рабочему потоку, которыйотправит ответ (в настоящее время использует динамический исходный порт).

Сокет в другом потоке создается следующим образом:

udp::socket sock2(io_service, udp::endpoint(udp::v4(), 0));

И отвечает на исходный запрос, используя sender_endpoint, сохраненный сисходный пакет.

То, что я хотел бы сделать, это ответить клиенту, используя тот же порт источника, который прослушивает сервер.Но я не понимаю, как это можно сделать.Я получаю исключение, если я пытаюсь использовать этот говорящий адрес.Можно ли сделать то, что я спрашиваю?Причина, по которой я хочу, заключается в том, что если я использую динамические порты, это означает, что клиенты должны добавить специальные правила брандмауэра в окнах, чтобы разрешить чтение ответных пакетов.Я обнаружил, что если в ответе порт источника совпадает, брандмауэр Windows разрешит ему вернуться обратно.

Ответы [ 3 ]

3 голосов
/ 21 сентября 2010

Исключение говорит вам как есть: вы не можете создать два живых сокета с одним и тем же портом источника.Я не знаю ASIO, но вы должны быть в состоянии создать сокет перед тем, как раскрутить поток, сохраняя ссылку на сокет и поток для последующего использования, и как только поток отправки данных простаивает, присоединяется к нему и отправляет любыедругие вещи.

РЕДАКТИРОВАТЬ: с небольшим усилием, вы также можете сделать сокет, для которого вам не нужно ждать, пока все данные из одного потока будут отправлены: иметь рабочий поток, владеющийсокет прослушивает очередь для фрагментов данных (в идеале именно тот размер полезной нагрузки, который вы намереваетесь отправить) и отправляет произвольные фрагменты полезной нагрузки в эту очередь из нескольких потоков.

1 голос
/ 21 сентября 2010

Вы должны иметь возможность использовать опцию сокета SO_REUSEADDR, чтобы привязать несколько сокетов к одному и тому же адресу. Но, сказав это, вы не хотите этого делать, потому что не указано, какой сокет будет получать входящие данные на этот порт (вам придется проверить все сокеты на наличие входящих данных)

Лучшим вариантом будет просто использовать один и тот же сокет для отправки ответов - это можно безопасно сделать из нескольких потоков без какой-либо дополнительной синхронизации (как вы используете UDP).

1 голос
/ 21 сентября 2010

отправьте ответ на тот же сокет (на который вы получили запрос клиента) вместо создания нового, но убедитесь, что вы не отправляете на один сокет из обоих потоков одновременно

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...