#c #sockets
#c #сокеты
Вопрос:
Я следую примеру, приведенному во вводном руководстве по межпроцессному взаимодействию 4.4BSD, где показан процесс обмена данными с использованием дейтаграмм в интернет-домене. В примерах 6a и 6b, 6a задает порт и имя хоста
name.sin_addr.s_addr = INADDR_ANY;
name.sin_port = 0;
Насколько я понимаю, INADDR_ANY
это подстановочное значение, позволяющее сокету получать данные из любого места. Но я не могу отправлять из любого места и явно указать имя хоста в 6b
hp = gethostbyname(argv[1]);
Итак, какое имя хоста будет допустимым здесь? Когда я попытался
program6b localhost 0
Но это говорит о том, что он не может назначить запрошенный адрес (я использовал другие адреса и то же сообщение). 6a говорит, что «Сокет имеет порт # 0», хотя это означает, что он прослушивает все порты, верно? В любом случае я попытался установить post вручную, чтобы «Сокет имел порт # 53790». Netstat показывает, что он прослушивает
udp4 0 0 * .53790 .
И с помощью команды
program6b localhost 53790
Я получаю ответ, что данные были получены из сокета, который считывает. Итак, я частично понимаю, что происходит, но я хотел бы знать, как пример должен работать для порта # 0.
Ответ №1:
Порт 0, как UDP, так и TCP, обычно не могут использоваться. Они указаны в API сокетов bind
, чтобы запросить, чтобы операционная система назначила произвольный свободный порт приложению. Обычно это делается с помощью клиентского кода, который не заботится о конкретном используемом порту. С другой стороны, код сервера обычно указывает известный порт.
О том INADDR_ANY
, что при выполнении локального bind
, это означает:
- Прослушивание на всех сетевых интерфейсах, если сокет прослушивает.
- Пусть ОС выберет соответствующий сетевой интерфейс для отправки данных.
Если вместо этого вы указываете адрес, это должен быть адрес вашего компьютера и относится к сетевому интерфейсу, которому принадлежит этот адрес. Затем:
- Если сокет прослушивает: он будет прослушивать только в этом сетевом интерфейсе.
- Если сокет отправляет данные, он будет учитывать только этот сетевой интерфейс.
В качестве примечания: вы не можете прослушивать каждый порт одновременно, если вы не используете какой-то необработанный сокет. Но не с помощью UDP или TCP.