Я пытаюсь определить время, необходимое машине для получения пакета, обработать его и дать ответ.
Эта машина, которую я назову "сервер", запускает очень простую программу, которая получает пакет (recv(2)
) в буфере, копирует полученный контент (memcpy(3)
) в другой буфер и отправляет пакет назад (send(2)
). Сервер запускает NetBSD 5.1.2.
Мой клиент измеряет время разворота несколько раз (pkt_count
):
struct timespec start, end;
for(i = 0; i < pkt_count; ++i)
{
printf("%d ", i+1);
clock_gettime(CLOCK_MONOTONIC, &start);
send(sock, send_buf, pkt_size, 0);
recv(sock, recv_buf, pkt_size, 0);
clock_gettime(CLOCK_MONOTONIC, &end);
//struct timespec nsleep = {.tv_sec = 0, .tv_nsec = 100000};
//nanosleep(&nsleep, NULL);
printf("%.3f ", timespec_diff_usec(&end, &start));
}
Я удалил проверки ошибок и другие незначительные вещи для ясности. Клиент работает на 64-битной версии Ubuntu 12.04. Обе программы работают в режиме реального времени, хотя только ядро Ubuntu - в реальном времени (-rt). Соединение между программами - TCP. Это отлично работает и дает мне в среднем 750 микросекунд.
Однако, если я включу прокомментированный вызов наномного режима (со сном 100 мкс), мои измерения снижают 100 мкс, давая в среднем 650 мкс. Если я сплю в течение 200 мкс, меры упадут до 550 мкс и т.д. Это поднимается до сна 600 мкс, давая в среднем 150 мкс. Затем, если я подниму сон до 700 мкс, мои измерения пройдут до 800 мкс в среднем. Я подтвердил свои программные меры с помощью Wireshark.
Я не могу понять, что происходит. Я уже установил опцию сокета TCP_NODELAY как на клиенте, так и на сервере, без разницы. Я использовал UDP, никакой разницы (то же поведение). Поэтому я предполагаю, что это поведение не связано с алгоритмом Нагле. Что это может быть?
[ОБНОВЛЕНИЕ]
Вот скриншот выхода клиента вместе с Wireshark. Теперь я запустил свой сервер на другой машине. Я использовал одну и ту же ОС с той же конфигурацией (поскольку это Live System в ручном накопителе), но аппаратное обеспечение отличается. Такое поведение не появилось, все работало, как ожидалось. Но остается вопрос: почему это происходит в предыдущем аппаратном обеспечении?
[ОБНОВЛЕНИЕ 2: Дополнительная информация]
Как я уже говорил, я тестировал пару своих программ (клиент/сервер) на двух разных серверах. Я построил два полученных результата.
Первый сервер (странный) - это одноплатный компьютер RTD с интерфейсом Ethernet 1 Гбит/с. Второй сервер (обычный) - это Diamond Single Board Computer с интерфейсом Ethernet 100 Мбит/с. Оба они запускают ОСИЮ ОСУШУЮ (NetBSD 5.1.2) из SAME Pendrive.
Из этих результатов я верю, что это поведение связано либо с драйвером, либо с самим NIC, хотя я до сих пор не могу представить, почему это происходит...