# NetPDL (Network Protocol Description Language)
###### tags: `summary`, `netpdl`
[TOC]
---
Язык описания данных и сетевых протоколов, основанный на XML. Инфраструктура языка ориентирована только на описание **сетевых протоколов** — все вспомогательные программы инфраструктуры работают с pcap-файлами. Тем не менее сам по себе язык не накладывает такого ограничения и позволяет описывать произвольные структуры бинарных данных.
*Фрагмент описания протокола Ethernet*
```xml
<proto name="Ethernet">
<fields>
<fixed name="dst" size="6"/>
<fixed name="src" size="6"/>
<fixed name="type-length" size="2"/>
</fields>
<nextproto>
<switch>
<expr type="int">
<fieldref name="type-length">
</expr>
<case value="2048"><protoref name="IP"/></case>
<case value="2054"><protoref name="ARP"/></case>
</switch>
</nextproto>
</proto>
```
Разработчики: [Netgroup at Politecnico di Torino](http://netgroup.polito.it/)
[Проект на GitHub](https://github.com/netgroup-polito/netbee), [форк проекта](https://github.com/aleasims/netbee) *(компилируется под Ubuntu 18.04)*
Статья [NetPDL: An extensible XML-based language for packet header description](https://getbox.ispras.ru/index.php/s/hdRVCq5wzBdMADB/download?path=%2F&files=2006_NetPDL_An%20Extensible%20XML-Based%20Language%20for%20Packet%20Header%20Description.pdf)
[Архив](https://getbox.ispras.ru/index.php/s/hdRVCq5wzBdMADB) статей по смежной тематике от авторов
## Язык NetPDL
* нет описания временного состояние протокола (автомата состояний). Как следствие, проблемы при разборе stateful-протоколов;
* расширяемость описаний протоколов (новая версия не требует нового описания с нуля);
* большое количество описанных протоколов ([тут](https://github.com/netgroup-polito/netbee/tree/master/languages/netpdl-dissectors));
* явная инкапсуляция протоколов (`<nextproto>`);
* битовые поля (`<bit>`, `<masked>`);
* выравнивания до 16, 32 бит (`<padding>`);
* поля переменной длины (`<variable>`). Длина определяется:
* другим полем или
* появлением определенного символа;
* условные конструкции (`<switch>-<case>`, `<if>`);
* циклы (`<loop>`);
* внешние плагины для обработки заголовков (`<plugin>`);
* выбор типа поля уже после чтения (`<lookahead>`);
* выбор протокола после чтения первых байт (`<presentif>`);
## Инфраструктура
Инфраструктура языка состоит из библиотеки `nbee`, предоставляющей возможность работать с NetPDL/PDML/PSML и т.д. и вспомогательных инструментов. Имеющаяся инфраструктура ориентирована на описание сетевых протоколов в pcap-файлах и только.
При описании сразу нескольких протоколов, используется всего один NetPDL-файл. Таким образом, собирается некоторая *база* известных протоколов.
## Комментарии по установке
Сборку рекомендуется проводить не из основного репозитория, поскольку там содержатся ошибки, не позволяющие скомпилировать код на Ubuntu 18.04. Вместо этого имеется [исправленный форк](https://github.com/aleasims/netbee) репозитория. Проверен на:
* `Ubuntu 18.04`
* `cmake version 3.10.2`
* `g++ (Ubuntu 7.4.0-1ubuntu1~18.04.1) 7.4.0`
Процесс сборки основной библиотеки:
```
cd netbee/src
cmake .
make
```
Помимо этого можно также собрать дополнительные инструменты:
```
cd netbee/tools
cmake .
make
```
```
cd netbee/samples
cmake .
make
```
Все скомпилированные файлы складываются в папку `netbee/bin`.
## База протоколов
Для составления своей базы (NetPDL-файла) рекомендуется воспользоваться скриптом `languages/misc/netpdl_creator.sh`. Руководство по его использованию находится там же (`languages/misc/netpdl_creator_readme.txt`). Используя его, можно добавлять свои протоколы к имеющимся в папке `languages` и вообще составлять любую базу, какую только хочется. Результат работы скрипта — файл `netbee/bin/netpdl.xml` c базой протоколов. В папке `netbee/bin` также уже имеется несколько готовых баз.
`netbee/bin/netpdl-download` — программа для загрузки последней версии базы, предоставляемой разработчиками (собирается в `netbee/samples`). На данный момент сервер не отвечает.
## Описание имеющихся инструментов
При компиляции только из папки `netbee/src`, собираются только библиотеки `.so`:
* `libnbee.so` — основная библиотека, дающая доступ ко всем возможностям Netbee
* `libnbpflcompiler.so` — компилятор фильтров пакетов
* `libnbsockutils.so` — библиотека кросс-платформенных сокетов от Netbee
* `libnbnetvm.so` — виртуальная машина для фильтров
* `libnbprotodb.so` — обработчик NetPDL базы протоколов
Но в папке `tools` есть набор консольных инструментов, которые могут быть полезны.
* ***nbeedump*** — разбирает входные пакеты в соответствии с базой и сохраняет краткое резюме в определенном формате, указанном в базе (под тегом `<visualization>`)
```
./nbeedump -netpdl netpdl-min.xml -r /path/to/pcap
```
* ***nbextractor*** — разбирает вход и отображает только указанные поля
* `libnbsvchelper.so`
Также имеется набор примеров из папки `netbee/samples`, которые тоже можно скомпилировать в полезные консольные программы:
* ***protodbdump*** — выводит краткое описание всех протоколов в имеющейся базе
* ***packetdecoder*** — непосредственно разбирает поданную на вход трассу и сохраняет результат в PDML/PSML
* ***fieldextractor*** — разбирает пакеты в соответствии с базой и выводит значения указанного поля
* ***filtercompiler*** — визуализирует работу компилятора фильтров `NetPFLCompiler`, строя на выходе диаграмму конечного автомата
* ***sockutilstest*** — демонстрирует работу кросс-платформенных сокетов `SockUtils`
* ***netvmexec***
* ***netvmcompiler***
* ***netpdl-download***
* ***psmlreader***
* ***pdmlreader***
* ***pdmlfieldextractor***
* ***netpdlutils***
## Принцип работы
Библиотека `nbee` при своей инициализации читает файл базы NetPDL или, при отсутствии такового, пытается использовать свою "встроенную" базу. Затем она транслируется SAX-парсером в некоторое внутреннее представление и в таком виде используется для дальнейшей работы. С точки зрения API библиотеки это выливается в необходимость вызывать методы `nbInitialize()` в начале работы и `nbCleanup()` в конце.
Класс `CNetPDLDecoder` реализует парсер на основе прочитанного XML. В процессе обработки пакета, на основе данного NetPDL генерируется соотвествующий PDML.
Экспорта полученного парсера в исполняемую библиотеку или в код нет. Библиотека просто разбирает полученный буфер в соответствии с данным NetPDL и создает соответствующий PDML.