sinsin
|
|
« : 22-03-2013 11:43 » |
|
Доброго времени суток. Есть один вопрос по функцинированию стека TCP/IP в Windows: я посылаю широковешательный UDP пакет на некоторый порт, например так: sockaddr_in RecvAddr; RecvAddr.sin_family = AF_INET; RecvAddr.sin_port = htons(RBC_UDP_RECEIVER_PORT); RecvAddr.sin_addr.s_addr = INADDR_BROADCAST;
int iResult = sendto(SendSock,&CicleBuf[ReadIndex*RBC_ONE_PACCKET_LEN], RBC_ONE_PACCKET_LEN, 0, (SOCKADDR *) & RecvAddr, sizeof (RecvAddr)); if (iResult == SOCKET_ERROR) { wprintf(L"sendto failed with error: %d\n", WSAGetLastError()); }
На той же машине, с которой он отправлен я его принимаю: sockaddr_in ServAddr; ServAddr.sin_family = AF_INET; ServAddr.sin_port = htons(RBC_UDP_RECEIVER_PORT); ServAddr.sin_addr.s_addr = INADDR_ANY;
sockaddr RcvAddr; ZeroMemory(&RcvAddr, sizeof(sockaddr_in));
bind( UDPReceiverSock, (sockaddr*)&ServAddr, sizeof(ServAddr));
int BytesReceived = recvfrom(UDPReceiverSock,TmpBuf, RBC_ONE_PACCKET_LEN, 0, &RcvAddr, &ir);
А какой был маршрут у этого пакета с момента его отправления: через сетевую карту или через Loopback?
|
|
|
Записан
|
|
|
|
Finch
Спокойный
Администратор
Offline
Пол:
Пролетал мимо
|
|
« Ответ #1 : 22-03-2013 15:07 » |
|
По идее говоря через Loopback, Посылаеш широковешательный, следовательно и через адрес 127.0.0.1 Насколько я знаю, раутеры должны резать этот адрес.
|
|
|
Записан
|
Не будите спашяго дракона. Джаффар (Коша)
|
|
|
sinsin
|
|
« Ответ #2 : 22-03-2013 16:32 » |
|
Ясно. А можно ли как-нибудь запретить Loopback?
|
|
|
Записан
|
|
|
|
Dimka
Деятель
Команда клуба
Offline
Пол:
|
|
« Ответ #3 : 22-03-2013 16:40 » |
|
sinsin, ты бы лучше сказал, что ты хочешь получить в конечном результате. Заслать "в провод" пакет так, чтобы он "из провода" вернулся у тебя никогда не получится.
|
|
|
Записан
|
Программировать - значит понимать (К. Нюгард) Невывернутое лучше, чем вправленное (М. Аврелий) Многие готовы скорее умереть, чем подумать (Б. Рассел)
|
|
|
Finch
Спокойный
Администратор
Offline
Пол:
Пролетал мимо
|
|
« Ответ #4 : 22-03-2013 16:43 » |
|
Можеш в принципе на Файраоле написать правило, чтобы, он глушил UDP пакеты идушие по 127.0.0.1 адресу и твоему порту. Совсем закрывать интрефейс чревато. Слишком многое на нем работает.
|
|
|
Записан
|
Не будите спашяго дракона. Джаффар (Коша)
|
|
|
RXL
|
|
« Ответ #5 : 22-03-2013 17:17 » |
|
sinsin, ты бы лучше сказал, что ты хочешь получить в конечном результате. Заслать "в провод" пакет так, чтобы он "из провода" вернулся у тебя никогда не получится.
Не знаю как в вашей винде, классические BSD-сокеты не запрещают получать собственное широковещательное отправление. Более того, можно регулировать его получение.
|
|
|
Записан
|
... мы преодолеваем эту трудность без синтеза распределенных прототипов. (с) Жуков М.С.
|
|
|
Dimka
Деятель
Команда клуба
Offline
Пол:
|
|
« Ответ #6 : 22-03-2013 19:17 » |
|
RXL, а кто его вернёт на 2-м уровне OSI?
|
|
|
Записан
|
Программировать - значит понимать (К. Нюгард) Невывернутое лучше, чем вправленное (М. Аврелий) Многие готовы скорее умереть, чем подумать (Б. Рассел)
|
|
|
RXL
|
|
« Ответ #7 : 22-03-2013 19:33 » |
|
Дим, при чем тут 2-й уровень? Вопрос в логике выбора интерфейса для отправки. Если бы это был multicast, то в подобной ситуации ушел бы через все интерфейсы, но broadcast может уйти только с одного интерфейса. Без выполнения bind или connect для сокета, выбор интерфейса остается за системой. Быстрее всего выбран будет первый попавшийся интерфейс в списке (т.к. адрес не спицифичен к конкретному интерфейсу). Отсюда: делать bind. Но это я описываю классические сокеты — винда, ведь, уникум...
|
|
|
Записан
|
... мы преодолеваем эту трудность без синтеза распределенных прототипов. (с) Жуков М.С.
|
|
|
Dimka
Деятель
Команда клуба
Offline
Пол:
|
|
« Ответ #8 : 22-03-2013 19:53 » |
|
RXL, при том, что "в провод" не уйдёт. Перетасуется на 3-м уровне. Он потому и хочет lo запретить, чтобы пакет внутри машины не ходил, только не добьётся желаемого. Поэтому вопрос о маршруте, которым ходил пойманный собственный бродкаст, смысла не имеет - маршрута как такового для этого пакета вообще нет.
|
|
|
Записан
|
Программировать - значит понимать (К. Нюгард) Невывернутое лучше, чем вправленное (М. Аврелий) Многие готовы скорее умереть, чем подумать (Б. Рассел)
|
|
|
RXL
|
|
« Ответ #9 : 22-03-2013 20:04 » |
|
Цитирую классика: Адрес 255.255.255.255 предназначен с использованием в качестве адреса получателя во время процесса начальной загрузки такими приложениями, как TFTP и BOOTP, которым еще не известен IP-адрес узла. Возникает вопрос: что делает узел, когда приложение посылает дейтаграмму UDP на адрес 255.255.255.255? Большинство узлов допускают это (если процесс установил параметр сокета SO_BROADCAST) и преобразуют адрес получателя в широковещательный адрес исходящего интерфейса, направленный в подсеть. ... Может появиться другой вопрос: что делает узел с несколькими сетевыми интерфейсами, когда приложение посылает дейтаграмму UDP на адрес 255.255.255.255? Некоторые системы посылают одно широковещательное сообщение с основного интерфейса (с интерфейса, который был сконфигурирован первым) с IP-адресом получателя, равным широковещательному адресу подсети этого интерфейса. Другие системы посылают по одной копии дейтаграммы с каждого интерфейса, поддерживающего широковещательную передачу. ... Короче, систем специфик — курим MSDN. Совет: 1. Привязывать (bind) сокет к определенному широковещательному адресу, характерному непосредственно доступной сети. 2. Если надо послать широковещательный пакет в несколько непосредственно доступных сетей, создавать по сокету для каждой и посылать через каждый копию пакета.
|
|
« Последнее редактирование: 22-03-2013 20:08 от RXL »
|
Записан
|
... мы преодолеваем эту трудность без синтеза распределенных прототипов. (с) Жуков М.С.
|
|
|
Dale
|
|
« Ответ #10 : 22-03-2013 20:31 » |
|
Не знаю как в вашей винде, классические BSD-сокеты не запрещают получать собственное широковещательное отправление. В нашей винде, разумеется, все точно так же. Некоторое время назад пригласили в одну фирму в качестве консультанта (люблю охотиться на чужие ошибки). Там разрабатывается самописный медийный сервер. Разработчики не смогли найти утечку памяти, которая понемногу вычерпывала память, пока не закончится адресное пространство. Обнаружил, что сервер получал собственные широковещательные пакеты, но не читал их (программисты сочли это излишеством, поскольку сервер и так знает, что отправляет). В результате буфер с непрочитанными пакетами постепенно занимал всю память, после чего приложение рушилось. Так что факт, проверенный на практике: отправитель заведомо принимает данные наравне с остальными получателями.
|
|
|
Записан
|
Всего лишь неделя кодирования с последующей неделей отладки могут сэкономить целый час, потраченный на планирование программы. - Дж. Коплин.
Ходить по воде и разрабатывать программное обеспечение по спецификациям очень просто, когда и то, и другое заморожено. - Edward V. Berard
Любые проблемы в информатике решаются добавлением еще одного уровня косвенности – кроме, разумеется, проблемы переизбытка уровней косвенности. — Дэвид Уилер.
|
|
|
RXL
|
|
« Ответ #11 : 22-03-2013 20:36 » |
|
Dale, значит ли это, что буфер UDP в винде резиновый? Добавлено через 2 минуты и 4 секунды:В нашей винде, разумеется, все точно так же.
Я верю в MS. Winsock изначально было с извратом.
|
|
« Последнее редактирование: 22-03-2013 20:38 от RXL »
|
Записан
|
... мы преодолеваем эту трудность без синтеза распределенных прототипов. (с) Жуков М.С.
|
|
|
Dale
|
|
« Ответ #12 : 22-03-2013 20:41 » |
|
Может, есть возможность как-то регулировать его аппетит, я не искал такое средство. В "моем" случае забивались все 3 гигабайта виртуальной памяти процесса (приложение 32-разрядное), после чего следовал крах.
Решил проблему простейшим способом - заставил программу делать пустое чтение собственного сокета, после чего дальше уже копать не было интереса.
|
|
« Последнее редактирование: 22-03-2013 20:43 от Dale »
|
Записан
|
Всего лишь неделя кодирования с последующей неделей отладки могут сэкономить целый час, потраченный на планирование программы. - Дж. Коплин.
Ходить по воде и разрабатывать программное обеспечение по спецификациям очень просто, когда и то, и другое заморожено. - Edward V. Berard
Любые проблемы в информатике решаются добавлением еще одного уровня косвенности – кроме, разумеется, проблемы переизбытка уровней косвенности. — Дэвид Уилер.
|
|
|
RXL
|
|
« Ответ #13 : 22-03-2013 20:48 » |
|
Совет: 1. Привязывать (bind) сокет к определенному широковещательному адресу, характерному непосредственно доступной сети. 2. Если надо послать широковещательный пакет в несколько непосредственно доступных сетей, создавать по сокету для каждой и посылать через каждый копию пакета.
Поправлюсь: bind не обязателен, но в sendto надо явно указывать адрес назначения и, для посылки в несколько сетей, выполнять соотв. число sendto с соотв. этим сетям адресом назнанчения. Добавлено через 2 минуты и 37 секунд:Dale, был ли в приложении открыт UDP сокет, связанный с данным портом? В противном случае пакет должен игнорироваться системой.
|
|
« Последнее редактирование: 22-03-2013 20:52 от RXL »
|
Записан
|
... мы преодолеваем эту трудность без синтеза распределенных прототипов. (с) Жуков М.С.
|
|
|
Dale
|
|
« Ответ #14 : 22-03-2013 21:21 » |
|
Dale, был ли в приложении открыт UDP сокет, связанный с данным портом? В противном случае пакет должен игнорироваться системой. Конечно, был. Иначе и самой проблемы не было бы. Там приложение в принципе дуплексное (учебный класс): сервер не только транслирует контент, но и принимает обратную связь от ученических мест. Только разработчики не учли, что собственная трансляция туда тоже попадет.
|
|
|
Записан
|
Всего лишь неделя кодирования с последующей неделей отладки могут сэкономить целый час, потраченный на планирование программы. - Дж. Коплин.
Ходить по воде и разрабатывать программное обеспечение по спецификациям очень просто, когда и то, и другое заморожено. - Edward V. Berard
Любые проблемы в информатике решаются добавлением еще одного уровня косвенности – кроме, разумеется, проблемы переизбытка уровней косвенности. — Дэвид Уилер.
|
|
|
|