Перевод статьи: Monitoring Systems, SNMPv3 and the engineID
Автор: Михаэль Шварцкопф (Michael Schwartzkopff)
Иногда шифрованные запросы SNMPv3 от системы сетевого мониторинга (NMS - Network Monitoring Systems) к устройствам совершенно неожиданно перестают работать. Нет никаких видимых причин, объясняющих это поведение. В этой статье я опишу проблему, с которой я столкнулся в Zabbix, поразмышляю о причинах и покажу обходной путь (или решение, если вам так угодно). Решение помогло мне, но я не уверен, что нашёл настоящую причину проблемы. По крайней мере, решение устраняет проблему, демонстрирующую странное поведение сервера Zabbix и наблюдаемого устройства. Но проблема встречается не только в системе сетевого мониторинга Zabbix - я также замечал её и в системе CA Spectrum.
Более 10 лет SNMPv3 - единственный актуальный стандарт SNMP. Старые версии - SNMPv1 и v2c - считаются устаревшими, однако эти версии по-прежнему используются для управления большинством сетевых устройств.
SNMPv3 предоставляет полный комплект средств для обеспечения безопасности на основе пользователей (USM - User-based Security Model) и для управления доступом на основе представлений (VACM - View Access Control Model). Эти средства позволяют ограничить доступ аутентифицированных пользователей к информации, которую они авторизованы видеть. И конечно, все запросы от станции управления к агенту могут быть аутентифицированы и, если нужно, зашифрованы. В большинстве случаев достаточно аутентифицировать трафик мониторинга во внутренней сети, но если трафик проходит через внешнюю сеть (то есть интернет), его стоит также зашифровать. SNMPv3 предоставляет все эти возможности.
Каждая сущность SNMPv3 имеет собственный идентификатор - так называемый engineID. Это уникальный номер каждого контекста, с которым работают агенты. Но в большинстве устройств запущен только один SNMP-агент, поэтому каждое устройство имеет единственный engineID. В RFC 3411 имеется раздел snmpModules.10 (страница 40), в котором описывается способ формирования engineID. Если трафик шифруется, то engineID используется алгоритмом шифрования, поэтому зашифрованные данные разных устройств отличаются друг от друга.
Поскольку изначально станция управления не знает значения engineID агента на управляемом устройстве, в RFC 5343 описан способ первоначального обнаружения engineID.
Стандарт SNMPv3 также защищает обмен информацией от атак повторного воспроизведения, когда злоумышленник записывает пакеты и позже отправляет их повторно в сторону станции-получателя, чтобы спровоцировать какую-то реакцию. Для защиты станция управления сначала спрашивает у агента, сколько раз он уже перезагружался (snmpEngineBoots) и как много времени прошло с момента последней перезагрузки (snmpEngineTime). Станция управления шифрует данные вместе с количеством загрузок и временем, прошедшим с момента последней загрузки агента. Агент может правильно расшифровать пакет только если его время сочетается со временем поступления запроса. Отметим, что в SNMPv3 используется не абсолютное время, а относительное время кадра. Станция управления может принять информацию от контролируемого устройства, даже если время на обеих системах не совпадает.
Обмен информацией при включенном шифровании SNMPv3 выглядит следующим образом:
Станция управления -> агенту: Какой у тебя engineID? Агент -> станции управления: Мой engineID равен ... Мой SNMP-агент перезагружался x раз и с момента последней загрузки прошло y секунд. Станция управления -> агенту: Какая у тебя загрузка процессора, зашифрованная вместе с engineID, snmpEngineBoots и snmpEngineTime? Агент -> станции управления: Загрузка процессора равна x, зашифровано вместе с engineID, snmpEngineBoots и snmpEngineTime.
Как можно видеть, любая проблема с интерпретацией engineID, snmpEngineBoots или snmpEngineTime приводит к ошибке обмена зашифрованными данными.
Zabbix - это система мониторинга, поддерживающая протокол SNMP. И разумеется, она поддерживает протокол версии 3. В Zabbix нужно просто настроить пользователя SNMP, пароль для аутентификации и пароль для шифрования. Имя пользователя и пароли можно настроить через макросы в определении сетевого узла. Использование макросов облегчает повторное использование шаблонов узлов, параметры которых могут различаться.
Проблемы начинаются с того, что внезапно обнаруживается устройство, не отвечающее на зашифрованные запросы SNMPv3 от системы Zabbix. При проверке настроек SNMP при помощи snmpget или snmpwalk из командной строки сервера мониторинга проблем не обнаруживается. Все запросы из командной строки завершаются успешно.
Теперь запустим tcpdump, чтобы проверить обмен данными построчно. В первом пакете станция управления запрашивает у агента его engineID:
07.406643 IP (tos 0x0, ttl 53, id 0, offset 0, flags [DF], proto UDP (17), length 92) manager.37780 > agent.161: [udp sum ok] { SNMPv3 { F=r } { USM B=0 T=0 U= } { ScopedPDU E= C= { GetRequest(14) R=537447614 } } }
Как можно увидеть, в запрос не включается имя пользователя (U=), количество загрузок равно нулю (B=0), как и время с момента последней загрузки (T=0). В следующем пакете агент предоставляет станции управления необходимую информацию:
07.408916 IP (tos 0x0, ttl 64, id 0, offset 0, flags [DF], proto UDP (17), length 143) agent.161 > manager.37780: [udp sum ok] { SNMPv3 { F= } { USM B=28 T=27 U= } { ScopedPDU E= 0x800x000x1F0x880x800x8E0xE50xD80x7B0x120x0C0x330x520x000x000x000x00 C= { Report(31) R=537447614 .1.3.6.1.6.3.15.1.1.4.0=1 } } }
Агент сообщает станции управления свой engineID, что он загружался уже 28 раз, а с момента последней загрузки прошло 27 секунд. И теперь станция управления ведёт себя совершенно странно. В следующей строке можно увидеть такой пакет:
07.427289 IP (tos 0x0, ttl 53, id 0, offset 0, flags [DF], proto UDP (17), length 177) manager.37780 > agent.161: [udp sum ok] { SNMPv3 { F=apr } { USM B=27 T=178 U=user } { ScopedPDU [!scoped PDU] (encrypted data) } }
Можно увидеть, что станция управления отправляет в запросе 27 загрузок и 178 секунд с момента последней загрузки, что не соответствует их текущим значениям. Агент сообщил о 28 загрузках и 27 секундах, что в два раз меньше прошлого значения. И конечно, агент отвечает следующим образом:
07.429382 IP (tos 0x0, ttl 64, id 0, offset 0, flags [DF], proto UDP (17), length 163) agent.161 > manager.37780: [udp sum ok] { SNMPv3 { F=a } { USM B=28 T=27 U=user } { ScopedPDU E= 0x800x000x1F0x880x800x8E0xE50xD80x7B0x120x0C0x330x520x000x000x000x00 C= { Report(28) R=0 .1.3.6.1.6.3.15.1.1.2.0=1 } } }
Этим OID'ом агент сообщает станции управления, что запрошенный PDU не может быть расшифрован, потому что окно приемлемого времени уже прошло.
Как я написал выше, тот же SNMP-запрос из командной строки работает отлично. SNMP-запрос с аутентификацией, но без шифрования тоже работает. Я встречал эту проблему в Zabbix, установленном на сервере Linux и на Spectrum-сервере в Windows-окружении. Со стороны агента были Cisco IOS, Cisco Nexus или Linux-компьютер с установленным net-snmp.
Похоже, Zabbix-сервер неправильно интерпретирует snmpEngineBoots и snmpEngineTime. Но разработчики Zabbix клятвенно заверяют, что они используют библиотеку snmp из net-snmp. Те же библиотеки используются в командной строке. Так что расследование, видимо, зашло в тупик.
С другой стороны, имеется несколько отчётов об ошибках на сайте Zabbix, которые указывают на не уникальные значения engineID у агентов. За подробностями можно обратиться к отчёту об ошибке ZBX-2152.
Поскольку понять причину проблемы не удалось, я поменял engineID у агента:
engineIDType 3
Эта строка в файле конфигурации snmpd.conf агента изменяет идентификатор со случайного значения, предоставленного net-snmp, на MAC-адрес интерфейса eth0, который каким-то образом должен оказаться и правда уникальным. Конечно, только после перезагрузки. И правда, Zabbix восстановил обмен данными с агентом и начал собирать данные. Проблема решена.
Если у вас есть какие-то дополнительные вопросы, свяжитесь со мной по электронной почте ms@sys4.de (примечание переводчика: автор скорее всего не понимает по-русски, поэтому пишите на английском или немецком).