LINUX.ORG.RU

network sniffing и wireshark


0

1

Всем привет.

У меня наверное достаточно простой вопрос по сетевым пакетам, но найти решение не получилось.

Поставлена задача: модифицировать имеющийся сниффер для выгрузки данных в формат, поддерживаемый wireshark'ом (я склоняюсь в сторону формата tcpdump).

Сниффер использует библиотеку libpcap для сбора данных. Реализация примитивна:

ph = pcap_open_live('eth0', 65535, 1, 0, errbuf);
while (1) {
    data = pcap_next(ph, info);
    // process packet (info, data)
}

Но здесь есть проблема. data указывает на начало Ethernet пакета. Структура Ethernet пакета достаточно проста: маки источника и получателя, протокол, данные, никаких меток начала нового заголовка пакета. Поэтому если просто выгружать в файл данные из data, то непонятно как отделять окончание одного пакета и начало другого (в моем примере snaplen = 65535, но на самом деле используются меньшие значения, что приводит к обрезанию пакетов, т.е. использовать длины пакетов в заголовках - не вариант). Само собой, Wireshark некорректно обрабатывает dump файл, сформированный таким образом.

Можно заставить libpcap сформировать нормальный dump файл его же средствами.

pcap_loop(ph, 100, pcap_dump_open(ph, "wireshark.dump"));
Просмотрев полученный файл, обнаружил, что между Ethernet пакетами в файле находятся некие неизвестные мне байты. В то же время этот файл Wireshark отлично открывает и обрабатывает.

Собственно, вопрос. Что необходимо вставлять между Ethernet пакетами? Или как иначе можно вручную сгенерировать dump файл для Wireshark, используя libpcap?


Ответ на: комментарий от true_admin

Навряд ли. Посмотрел внимательнее на эти байты - заметил следующую закономерность.

Перед первым Ethernet заголовком идет сначала стандартная шапка из 4х байт (A1B2C3D4 или D4C3B2A1). Затем 20 байт, из которых первые 4 (00 02 00 04) похоже одинаковы для всех случаев, еще 8 нулевых байтов и еще 8 пока что неизвестных байтов.

Затем перед каждым пакетом идет «шапка» из 16 байт. Первые 4 для всех пакетов одинаковы, но при этом различны в разных файлах. Следующие 4 - скорее всего какое-то число, не понял что оно означает. Следующие 4 - похоже - размер пакета, повторяется два раза.

В общем, в первом случае шапка была такая.

A1 B2 C3 D4 00 02 00 04  00 00 00 00 00 00 00 00
00 00 05 DC 00 00 00 01
«Шапки» перед пакетами:
4C F8 95 41 00 02 A3 29  00 00 00 5C 00 00 00 5C
4C F8 95 41 00 03 39 6C  00 00 00 5C 00 00 00 5C

Во втором случае.

d4 c3 b2 a1 02 00 04 00  00 00 00 00 00 00 00 00
e8 03 00 00 01 00 00 00
3e 48 b1 4d ce 02 05 00  6a 00 00 00 6a 00 00 00
3e 48 b1 4d c0 08 06 00  3c 00 00 00 3c 00 00 00

Вот теперь интересно, есть ли какие-то правила генерирования неизвестных байтов, или можно их брать произвольными?

В общем, если кому-то интересно: http://pastebin.com/LENwKr3V - вывод hexdump -C для корректного дампа.

ksv ()
Ответ на: комментарий от ksv

хм... почитал changelog от libpcap.

0.9.5
...
OP_PACKET now matches the beginning of the packet, instead of beginning+link-layer
...

Для libpcap 0.8 сгенерированный dump файл нормально принимался ethereal'ом, текущий (0.9.8) выдает только Ethernet пакеты. Вывод: или ставить старый libpcap, или вручную генерировать link-layer frame headers. Склоняюсь ко второму варианту, надо почитать как эти frame headers генерируются.

ksv ()
Ответ на: комментарий от true_admin

А нельзя посмотреть в tcpdump как он это делает?

Склонялся именно к этому варианту. Посмотрел. tcpdump делает очень просто - в pcap_loop передает функцию pcap_dump, предварительно открыв dump файл.

Просмотрел pcap_dump из libpcap и понял значения всех полей. Помимо самого пакета, в файл записывается структура

struct pcap_sf_pkthdr {
    struct pcap_timeval ts;	/* time stamp */
    bpf_u_int32 caplen;		/* length of portion present */
    bpf_u_int32 len;		/* length this packet (off wire) */
};
(pcap_timeval - два 4-байтных целых числа). В принципе, сразу становится понятно как генерировать нужные заголовки.

ksv ()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.