Решил на выходных обстоятельно потыкать палочкой на своем наборе виртуальных серверов в Snort и Suricata (gentoo, qemu-kvm, сетевые virtio, все через статически прописанные tap-ы с бриджами), уж больно заинтересовало в каком они сейчас состоянии. Поставил на DNS сервер Snort, программа отлично работает — оповещает и блокирует, но обнаружилась какая-то аномальная работа в режиме NIPS (NFQ) — «пропадает» второй пакет приходящий на DNS сервер при последовательных запросах (A+AAAA) от клиента. Если запросы идут с достаточным интервалом для ответа DNS сервера, второй пакет с запросом проходит (не «теряется»). Выключил Snort, поставил на сервер Suricata, запустил как NIPS (тоже NFQ) и все повторилось 1 в 1 (все работает, фильтрует, пишет в логи алерты и блокирует... но второй пакет с DNS запросом опять заходит и «теряется» на уровне ядро-юзер спейс не доходя до DNS сервера). Думал, что их фильтрует как DNS флуд, только вот у той же Suricata стоит «request-flood: 500» по умолчанию, что «немного» больше чем 2, да и логи подозрительно молчат у обеих программ (хотя правила отрабатываются отлично, пишет в лог алерты).
Запустил wireshark и начал смотреть на сетевой интерфейс виртуального сервера:
- При включенном на сервере NIPS (стоит и на входящие и на исходящие пакеты):
15 0.091477407 192.168.64.4 192.168.64.1 DNS 73 Standard query 0x83c2 A ldap.corp.net 16 0.091492929 192.168.64.4 192.168.64.1 DNS 73 Standard query 0x63f1 AAAA ldap.corp.net 17 0.092691561 192.168.64.1 192.168.64.4 DNS 89 Standard query response 0x83c2 A ldap.corp.net A 192.168.64.3 ... 20 5.096090016 192.168.64.4 192.168.64.1 DNS 73 Standard query 0x83c2 A ldap.corp.net 21 5.096631256 192.168.64.1 192.168.64.4 DNS 89 Standard query response 0x83c2 A ldap.corp.net A 192.168.64.3 22 5.096737005 192.168.64.4 192.168.64.1 DNS 73 Standard query 0x63f1 AAAA ldap.corp.net 23 5.098640900 192.168.64.1 192.168.64.4 DNS 73 Standard query response 0x63f1 AAAA ldap.corp.net
Как видно, в первом блоке на DNS сервер из сети приходит два запроса, а уходит только один ответ, клиент ждет 5 секунд и отсылает повторный запрос, но с уже большим интервалом по времени между пакетами. DNS сервер в логах клятвенно заверяет, что второй пакет из первого блока (с AAAA запросом) к нему вообще не поступал. При повторном запросе от клиента через 5 секунд - временной интервал между запросами выше, и сервер успевает ответить на первый запрос (А) до поступления второго (AAAA). В логах DNS все это отображается аналогично информации полученной снифером. Если задать через iptables запись в лог (-j LOG до -j NFQUEUE) — пишет тоже самое, что ловлю на снифере, т. е. пакеты 100% заходят и идут до передачи в юзер спейс.
- Если NIPS выключен:
7 0.058400579 192.168.64.4 192.168.64.1 DNS 73 Standard query 0xb226 A ldap.corp.net 8 0.058433208 192.168.64.4 192.168.64.1 DNS 73 Standard query 0xfa0b AAAA ldap.corp.net 9 0.058548122 192.168.64.1 192.168.64.4 DNS 89 Standard query response 0xb226 A ldap.corp.net A 192.168.64.3 10 0.058611081 192.168.64.1 192.168.64.4 DNS 73 Standard query response 0xfa0b AAAA ldap.corp.net
Оба запроса проходят и DNS отвечает на них. В логах DNS все так и отображается.
- Если сам сервер выступает в роли DNS клиента (например, при резолве yandex.ru) с включенным NIPS (стоит и на входящие и на исходящие пакеты):
1 0.000000000 192.168.64.1 192.168.64.10 DNS 69 Standard query 0xabf7 A yandex.ru 2 0.000018120 192.168.64.1 192.168.64.10 DNS 69 Standard query 0x70df AAAA yandex.ru ... 5 0.003540832 192.168.64.10 192.168.64.1 DNS 133 Standard query response 0xabf7 A yandex.ru A 77.88.55.66 A 77.88.55.55 A 5.255.255.5 A 5.255.255.55 6 0.003941852 192.168.64.10 192.168.64.1 DNS 97 Standard query response 0x70df AAAA yandex.ru AAAA 2a02:6b8:a::a
Т. е. предположение, что NIPS не хватает временного интервала не подтвердилось, клиентские (исходящие) DNS запросы с такими же интервалами отлично обрабатывает.
Полностью убирал правила, собирал Suricata вообще с конфигурацией "--disable-detection", вносил udp 53 в исключения на Snort и выключал работу по dns вообще в Suricata, выключал все что можно, но даже «голые» Suricata и Snort ведут себя так же. Пока на входящем 53 udp сидит Suricata или Snort и обрабатывают nfq очередь, я ловлю этот нюанс со 100% вероятностью. Очередь nfqueue всегда около нулевая (судя по «cat /proc/net/netfilter/nfnetlink_queue»), нагрузки никакой нет 100%, плюс, fail open на обеих программах задействован. Логи на вопрос «где пакет?» молчат как партизаны на допросе.
Самое смешное, в статистике нет ни слова что пакет вообще был потерян или заблокирован:
- как-то так для Snort:
Packet I/O Totals: Received: 223 Analyzed: 223 (100.000%) Dropped: 0 ( 0.000%) Filtered: 0 ( 0.000%) Outstanding: 0 ( 0.000%) Injected: 0
- вот так для Suricata:
<Notice> - (Recv-Q1) Treated: Pkts 182, Bytes 43384, Errors 0 <Notice> - (Recv-Q1) Verdict: Accepted 182, Dropped 0, Replaced 0
Идеи закончились... ощущение, что я не учитываю какую-то мелочь, но какую — понять не могу. Может, кто-то сталкивался с подобным?