В сети
находится большое количество устройств
с серверной частью на базе UOS.
Перед
подключением к устройствам, клиент
(ПЭВМ) массово рассылает пачки ARP-запросов
(10-15 за раз, каждую секунду) для получения
адресов.
При отсуствии устройства клиент пытается переподключится.
При приеме
пачки ARP-запросов, состоящей из 10-20 пакетов,
устройство начинает увеличивать время
ответа на запросы по TCP/ICMP.
Время ответа увеличивается до 3 секунд.
Тестировалось на различных платформах(AVR + ENC28J60, STM32F407 + ENC28J60, 1986ВЕ1Т, 1986ВЕ91Т + 5600ВГ1) и ветках дистрибутивов.
Грубо говоря
сетевая подсистема устройств подвисает
при ARP-флуде.
Есть ощущение, что накапливается огромное количество неотработанных пакетов в памяти.
Вылечилось временным костылем.
Файл netif.c:
buf_t *
netif_input (netif_t *netif) {
struct _buf_t *p;
for (;;) { // крутимся пока не отработаем ВСЕ арпы
p = netif->interface->input (netif);
if (p && netif->arp) p = arp_input (netif, p); // если есть пакет передаем в arp_input. если нет пакетов выходим из netif_input
else return 0;
if (p) return p; // arp_input вернул указатель отдаем его остальным уровням
}
}
У кого какие мысли по этому поводу?
--
Вы получили это сообщение, поскольку подписаны на группу "uOS embedded".
Чтобы отменить подписку на эту группу и больше не получать от нее сообщения, отправьте письмо на электронный адрес uos-embedded+unsubscribe@googlegroups.com.
Чтобы отправлять сообщения в эту группу, отправьте письмо на электронный адрес uos-em...@googlegroups.com.
Чтобы зайти в группу, перейдите по ссылке https://groups.google.com/group/uos-embedded.
Чтобы настроить другие параметры, перейдите по ссылке https://groups.google.com/d/optout.
p = netif->interface->input (netif); //возвращает p если есть пакеты, 0 если нет
if (p && netif->arp) p = arp_input (netif, p); // если netif->interface->input вернул р отдаем arp_input, если не веренул р, то вообще выходим (else return 0;) из netif_input.
// то есть никаких пакетов для работы нет.
else return 0; // вышли из netif_input
if (p) return p; // из условия if (p...) p = arp_input (..); если пакеты были, и это были арпы, то arp_input их отработает и вернет 0,
// сответственно условие для возврата не выполнится if (p) return p; и мы снова перейдем в начало for (;;).
for (;;) {
if (!(p = netif->interface->input (netif))) return 0; //пакетов нет! возвращаемся!
...
...
}
...