Может ли сокет-клиент и сервер на одном компьютере связываться с одним и тем же портом? - PullRequest
0 голосов
/ 28 декабря 2018

В моем случае мне нужно запустить сокет-клиент и сервер на одном компьютере.

Клиент сокета udp должен связать локальный порт с 1234 и будет взаимодействовать с сервером socker на удаленной стороне.Хотя серверу сокетов udp на том же компьютере необходимо также привязать локальный порт к 1234, и он также будет взаимодействовать с клиентом сокетов на удаленной стороне.

Возможно ли это?Любая потенциальная проблема или уведомление?Спасибо!

Ответы [ 5 ]

0 голосов
/ 28 декабря 2018

Нет, это ограничение API сокетов, и оно ограничивает написание одноранговых приложений на основе TCP.

В одноранговом приложении естественным являетсясделать это использовать один порт для исходящих и входящих соединений.Хотя эта модель поддерживается протоколом TCP, она не поддерживается API-интерфейсом сокетов - если сокет прослушивает порт p , привязка активного сокета к порту p не будет выполнена..

Очевидный обходной путь - использовать эфемерный порт для исходящих соединений (не используйте bind на активных сокетах).В некоторых случаях это вызывает другие проблемы, которые необходимо обойти - см., Например, параметр p в расширенном рукопожатии BitTorrent в BEP-10 .

0 голосов
/ 28 декабря 2018

Если вы используете многоадресную или широковещательную связь UDP, то часто имеет смысл привязать несколько программ к одному и тому же порту UDP, и это можно сделать, если вы вызовете setsockopt() с соответствующими аргументами перед вызовом bind()на нем:

  const int trueValue = 1;
  setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &trueValue, sizeof(trueValue));
#ifdef __APPLE__
  setsockopt(fd, SOL_SOCKET, SO_REUSEPORT, &trueValue, sizeof(trueValue));
#endif

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

OTOH, если вы отправляете только одноадресные UDP-пакеты (то есть пакеты, предназначенные для передачи одному получателю), то обычно этобесполезно связывать несколько программ с одним и тем же портом, поскольку каждый отправленный вами UDP-пакет будет приниматься ровно одной принимающей программой, а с несколькими программами, прослушивающими один и тот же порт, неизвестно / непредсказуемо, какая это будет программа.Например, в вашем случае ваша клиентская программа может отправить пакет, а сервер не получит его, потому что пакет был помещен в очередь в буфере сокета клиента.Так что в этом случае лучше связать клиент и сервер с разными портами.(Имейте в виду, что любая программа, которая получает пакет UDP, может легко узнать, к какому порту подключен отправитель пакета, вызвав recvfrom() для получения пакета и посмотрев содержимое аргумента address впоследствии; поэтому она должнасервер будет просто отвечать на пакеты, отправленные ему клиентом, даже если клиент использует абсолютно произвольный / произвольный порт UDP при каждом запуске. Если вы сообщаете своему клиенту bind() для порта 0, сетевой стек будетвыберите доступный в настоящее время UDP-порт для привязки к нему)

0 голосов
/ 28 декабря 2018

из man nc:

CLIENT/SERVER MODEL
 It is quite simple to build a very basic client/server model using nc.  On
 one console, start nc listening on a specific port for a connection.  For
 example:

       $ nc -l 1234

 nc is now listening on port 1234 for a connection.  On a second console (or a
 second machine), connect to the machine and port being listened on:

       $ nc 127.0.0.1 1234
0 голосов
/ 28 декабря 2018

Определенно, клиент и сервер не могут связываться с одним и тем же адресом.Функция bind () вернет -1, а функция perror () выведет сообщение об ошибке «адрес уже используется».Но зачем вам клиент и сервер для привязки к одному и тому же порту?Обычно клиент выбирает случайный порт для связи с сервером, или вы можете привязать другой порт к серверу.

0 голосов
/ 28 декабря 2018

Что вы используете?Language, Framework, Libraries ...

В общем, сервер прослушивает локальный порт.Клиент обычно подключается к ним и не блокирует их.Так что, с моей точки зрения, здесь не должно быть проблем.

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