Фильтр пакетов Android (APF) позволяет фреймворку управлять логикой аппаратной фильтрации пакетов во время выполнения. Это позволяет системе экономить электроэнергию, отбрасывая пакеты на аппаратном уровне, одновременно позволяя фреймворку Android изменять правила фильтрации во время выполнения в зависимости от состояния сети.
Обзор АПФ
АПФ состоит из двух основных компонентов:
- Интерпретатор APF работает на сетевом оборудовании (обычно на чипсете Wi-Fi). Интерпретатор APF обрабатывает байт-код APF пакетами, полученными оборудованием, и решает, принимать ли их, отбрасывать или отвечать на них.
- Код генерации программ APF выполняется на основном процессоре. Он создаёт и обновляет программы APF в соответствии с состоянием сети и устройства.
Методы Wi-Fi HAL позволяют фреймворку Android устанавливать байт-код программы APF и считывать текущие счётчики. Модуль Network Stack Mainline может обновлять байт-код программы APF в любой момент во время работы APF.
Реализовано несколько фильтров APF. Например, APF включает фильтры для отбрасывания запрещённых типов эфира, фильтрации пакетов объявлений маршрутизатора IPv6 (RA), фильтрации многоадресного и широковещательного трафика при отсутствии блокировки многоадресной рассылки, отбрасывания пакетов DHCP для других хостов и отбрасывания пакетов протокола разрешения незапрошенных адресов (ARP) и обнаружения соседей (ND). Если прошивка поддерживает APFv6, ApfFilter
также генерирует правила для ответа на распространённые типы пакетов, для ответа на которые в противном случае потребовалось бы пробуждение процессора, например, запросы ARP и запросы NS. Полный список фильтров определён в ApfFilter
.
Поскольку код генерации программы APF является частью модуля сетевого стека, вы можете использовать ежемесячные обновления [Mainline] для добавления новых фильтров и обновления логики фильтрации.
Пересмотр АПФ
В следующем списке описывается история изменений APF:
- APFv6: эта версия, представленная в Android 15, поддерживает фильтрацию пакетов, включает счетчики для отладки и метрик, а также поддерживает передачу пакетов.
- APFv4: эта версия, представленная в Android 10, поддерживает фильтрацию пакетов и включает счетчики для отладки и метрик.
- APFv2: эта версия, представленная в Android 7, поддерживает фильтрацию пакетов.
Интеграция АПФ
API APF между интерпретатором APF и оборудованием определены в apf_interpreter.h
( APFv4 , APFv6 ). Код прошивки Wi-Fi вызывает accept_packet()
в APFv4 или apf_run()
в APFv6, чтобы определить, следует ли отбросить пакет (нулевое возвращаемое значение) или передать его процессору приложения (ненулевое возвращаемое значение). Если пакет необходимо передать, apf_run()
также возвращает ноль, поскольку его пакет не нужно передавать процессору приложения. Если прошивка поддерживает APFv6, она должна реализовать API apf_allocate_buffer()
и apf_transmit_buffer()
. Интерпретатор APF вызывает эти два API во время логики передачи пакетов. Инструкции APF имеют переменную длину. Каждая инструкция имеет длину не менее 1 байта. Коды инструкций APF определены в apf.h
для APFv4 и встроены непосредственно в apf_interpreter.c
для APFv6.
APF использует выделенную память. Память используется как для самой программы APF, так и для хранения данных. Память не должна очищаться или записываться чипсетом, за исключением методов HAL APF. Байт-код APF использует хранилище данных для хранения счетчиков принятых и отброшенных пакетов. Область данных может быть прочитана из фреймворка Android. Инструкции APF эффективно используют память, но для максимизации их энергосберегающего и функционального потенциала требуются сложные динамические правила фильтрации. Эта сложность требует выделенной области памяти на чипсете. Минимальный объем памяти, требуемый для APFv4, составляет 1024 байта, в то время как для APFv6 требуется 2048 байт. Однако мы настоятельно рекомендуем выделить 4096 байт для APFv6 для обеспечения оптимальной производительности. Интерпретатор APF должен быть скомпилирован в прошивку. Интерпретаторы APFv4 и APFv6 оптимизированы по размеру кода. В архитектуре arm32 скомпилированный интерпретатор APFv4 весит около 1,8 КБ, тогда как более сложный интерпретатор APFv6 с дополнительными функциями (например, собственной поддержкой контрольных сумм и собственным кодом распаковки DNS) весит около 4 КБ.
Фильтры APF могут работать вместе с другими фильтрами, специфичными для конкретного производителя чипсета, в рамках прошивки. Производители чипсетов могут выбрать, запускать ли свою логику фильтрации до или после процесса фильтрации APF. Если пакет отбрасывается до достижения фильтра APF, фильтр APF его не обрабатывает.
Чтобы обеспечить корректную работу фильтра APF, при включении APF прошивка должна предоставлять фильтру APF доступ ко всему пакету, а не только к заголовку, когда APF включен.
Примеры программ APF
ApfTest
и ApfFilterTest
содержат примеры тестовых программ, иллюстрирующих работу каждого фильтра APF. Чтобы изучить фактическую сгенерированную программу, измените тестовый пример так, чтобы программа выводилась в виде шестнадцатеричной строки.
Папка testdata
содержит примеры программ APFv4 для фильтров APF RA. Папка samples
содержит утилиты Python, генерирующие программы разгрузки APFv6. Подробнее см. документацию в файлах утилит Python.
Отладка APF
Чтобы проверить, включён ли APF на устройстве, отобразите текущую программу, текущие счётчики и выполните команду adb shell dumpsys network_stack
. Ниже приведён пример этой команды:
adb shell dumpsys network_stack
......
IpClient.wlan0 APF dump:
Capabilities: ApfCapabilities{version: 4, maxSize: 4096, format: 1}
......
Last program:
6bfcb03a01b8120c6b9494026506006b907c025e88a27c025988a47c025488b87c024f88cd7c024a88e17c024588e384004408066a0e6bdca4022b000600010800060412147a1e016bd884021f00021a1c6b8c7c021c0000686bd4a402080006ffffffffffff6a266bbca402010004c0a801eb6bf87401f6120c84005f08000a17821f1112149c00181fffab0d2a108211446a3239a20506c2fc393057dd6bf47401cb0a1e52f06bac7c01c600e06bb41a1e7e000001b9ffffffff6bb07e000001aec0a801ff6be868a4019a0006ffffffffffff6bb874019b6bf07401907c001386dd686bd0a4017d0006ffffffffffff6bc874017e0a147a0e3a6b980a267c017000ff6be07401650a366ba87c016200858219886a26a2050fff02000000000000000000000000006ba4740146aa0e84013700e6aa0f8c0130006068a4011b000f33330000000184c9b26aed4c86dd606a12a2f02600b03afffe8000000000000086c9b2fffe6aed4cff02000000000000000000000000000186006a3aa2e9024000123c92e4606a3ea2d70800000000000000006a56a2ce04030440c01a5a92c9601a5e92c4606a62a2bb04000000006a66a2a6102401fa00049c048400000000000000006a76a29d04030440c01a7a9298601a7e9293606c0082a28904000000006c0086a27310fdfd9ed67950000400000000000000006c0096a2690418033c001a9a9264606c009ea24e102401fa00049c048000000000000000006c00aea24404180330001ab2923f606c00b6a22910fdfd9ed67950000000000000000000006c00c6a21f04190300001aca921a606c00cea20410fdfd9ed67950000400000000000000016bc472086be4b03a01b87206b03a01b87201
APF packet counters:
TOTAL_PACKETS: 469
PASSED_DHCP: 4
PASSED_IPV4: 65
PASSED_IPV6_NON_ICMP: 64
PASSED_IPV4_UNICAST: 64
PASSED_IPV6_ICMP: 223
PASSED_IPV6_UNICAST_NON_ICMP: 6
PASSED_ARP_UNICAST_REPLY: 4
PASSED_NON_IP_UNICAST: 1
DROPPED_RA: 4
DROPPED_IPV4_BROADCAST_ADDR: 7
DROPPED_IPV4_BROADCAST_NET: 27
Вывод этого примера команды adb shell dumpsys network_stack
включает следующее:
-
ApfCapabilities{version: 4, maxSize: 4096, format: 1}
: это означает, что чипы Wi-Fi поддерживают APF (версию 4). -
Last program
: В этом разделе находится последний установленный двоичный файл программы APF в формате шестнадцатеричной строки. -
APF packet counters
: в этом разделе показано, сколько пакетов было передано или отброшено APF, а также конкретные причины.
Для декодирования и дизассемблирования кода в понятный человеку язык ассемблера используйте инструмент apf_disassembler
. Для компиляции исполняемого файла выполните команду m apf_disassembler
. Ниже приведён пример использования инструмента apf_disassembler
:
echo "6bfcb03a01b8120c6b949401e906006b907c01e288a27c01dd88a47c01d888b87c01d388cd7c01ce88e17c01c988e384004008066a0e6bdca401af000600010800060412147a1e016bd88401a300021a1c6b8c7c01a00000686bd4a4018c0006ffffffffffff1a266bc07c018900006bf874017e120c84005408000a17821f1112149c00181fffab0d2a108211446a3239a205065a56483ac3146bf47401530a1e52f06bac7c014e00e06bb41a1e7e00000141ffffffff6be868a4012d0006ffffffffffff6bb874012e6bf07401237c001386dd686bd0a401100006ffffffffffff6bc87401110a147a0d3a6b980a267c010300ff6be072f90a366ba87af8858218886a26a2040fff02000000000000000000000000006ba472ddaa0e82d0aeaa0f8c00c9025868a2b60f5a56483ac3140c8126f3895186dd606a12a28b2600783afffe8000000000000002005efffe00026fff02000000000000000000000000000186006a3aa284024000123c94007d02586a3ea2700800000000000000006a56a26704190500001a5a94006002586a5ea23b2020014860486000000000000000006464200148604860000000000000000000646a7ea23204030440c01a8294002b02581a8694002402586c008aa21a04000000006c008ea204102a0079e10abcf60500000000000000006bc472086be4b03a01b87206b03a01b87201" | out/host/linux-x86/bin/apf_disassembler
0: li r1, -4
2: lddw r0, [r1+0]
3: add r0, 1
5: stdw r0, [r1+0]
6: ldh r0, [12]
8: li r1, -108
10: jlt r0, 0x600, 504
15: li r1, -112
17: jeq r0, 0x88a2, 504
22: jeq r0, 0x88a4, 504
27: jeq r0, 0x88b8, 504
32: jeq r0, 0x88cd, 504
37: jeq r0, 0x88e1, 504
42: jeq r0, 0x88e3, 504
47: jne r0, 0x806, 116
......
Для проверки результатов APF в автономном режиме используйте инструмент apf_run
. Для компиляции исполняемого файла выполните команду m apf_run
. Инструмент apf_run
поддерживает интерпретаторы APFv4 и APFv6.
Ниже приведено руководство по команде apf_run
. По умолчанию команда apf_run
выполняется в интерпретаторе APFv4. Передача аргумента --v6
команде apf_run
позволяет ей работать с интерпретатором APFv6. Все остальные аргументы можно использовать как для APFv4, так и для APFv6.
apf_run --help
Usage: apf_run --program <program> --pcap <file>|--packet <packet> [--data <content>] [--age <number>] [--trace]
--program APF program, in hex.
--pcap Pcap file to run through program.
--packet Packet to run through program.
--data Data memory contents, in hex.
--age Age of program in seconds (default: 0).
--trace Enable APF interpreter debug tracing
--v6 Use APF v6
-c, --cnt Print the APF counters
-h, --help Show this message.
Вот пример передачи одного пакета в APF для проверки возможности его отбрасывания или передачи.
Чтобы представить необработанный пакет в виде шестнадцатеричной двоичной строки, используйте параметр --packet
. Чтобы представить область данных, используемую для хранения счётчика APF , в виде шестнадцатеричной двоичной строки, используйте --data option
. Поскольку каждый счётчик имеет длину 4 байта, области данных должны быть достаточно длинными, чтобы исключить переполнение буфера.
out/host/linux-x86/bin/apf_run --program 6bfcb03a01b8120c6b9494010c06006b907c010588a27c010088a47c00fb88b87c00f688cd7c00f188e17c00ec88e384003908066a0e6bdca2d40600010800060412147a18016bd882ca021a1c6b8c7ac900686bd4a2b706ffffffffffff6a266bbca2b204c0a814656bf872a8120c84005808000a17821e1112149c00171fffab0d2a108210446a3239a204064651dbcc88ff6bf4727e0a1e52f06bac7a7be06bb41a1e7e0000006effffffff6bb07e00000063c0a814ff6be868a25106ffffffffffff6bb872536bf072497c001086dd686bd0a23806ffffffffffff6bc8723a0a147a0b3a6b980a267a2eff6be072240a366ba87a23858218886a26a2040fff02000000000000000000000000006ba472086be4b03a01b87206b03a01b87201 --packet 5ebcd79a8f0dc244efaab81408060001080006040002c244efaab814c0a8ca1e5ebcd79a8f0d --data 00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
Packet passed
Data: 00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000000000000000000001
Чтобы проверить результаты APF по файлу pcap, полученному с помощью tcpdump, используйте команду apf_run
следующим образом:
out/host/linux-x86/bin/apf_run --program 6bfcb03a01b8120c6b989401df06006b947c01d888a27c01d388a47c01ce88b87c01c988cd7c01c488e17c01bf88e384004408066a0e6bdca401a5000600010800060412147a1e016bd884019900021a1c6b907c01960000686bd4a401820006ffffffffffff6a266bc0a4017b0004c0a82b056bf874017084005f08000a17821f1112149c00181fffab0d2a108211446a3239a20506fabe589435936bf47401470a1e52f06bb07c014200e06bb81a1e7e00000135ffffffff6bb47e0000012ac0a82bff6be868a401160006ffffffffffff6bbc7401176bf074010c7c001086dd686bd0a2fb06ffffffffffff6bcc72fd0a147a0b3a6b9c0a267af1ff6be072e70a366bac7ae6858218886a26a2040fff02000000000000000000000000006ba872cbaa0e82be8eaa0f8c00b7025868a2a40ffabe5894359352a9874d08aa86dd606a12a2792600583afffe80000000000000f7d4e8ccd81ddb43fe80000000000000f8be58fffe94359386006a3aa272024108123c94006b02586a3ea25e0800000000000000006a56a25504030440c01a5a94004e02581a5e94004702586a62a23e04000000006a66a229102409891f9a26ae6d00000000000000006a76a22004190300001a7a94001902586a7ea204102409891f9a26ae6dba98e781ca9ef9ba6bc872086be4b03a01b87206b03a01b87201 --pcap apf.pcap --data 00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
37 packets dropped
1733 packets passed
Data: 00000000000000000000000000000000000000000200000005000000000000000000000002000000000000001b000000000000000000000001000000000000000000000000000000000000000000000000000000000000000000000689000000000000003c00000000000000000000000000000000000006ea
Чтобы проверить возможности передачи APFv6, используйте команду apf_run
следующим образом:
$ apf_run --program 75001001020304050608060001080006040002AA300E3CAA0FBA06AA09BA07AA08BA086A01BA09120C84006F08066A0EA30206000108000604032B12147A27017A020203301A1C820200032D68A30206FFFFFFFFFFFF020E1A267E000000020A000001032C020B1A267E000000020A000001032CAB24003CCA0606CB0306CB090ACB0306C60A000001CA0606CA1C04AA 0A3A12AA1AAA25FFFF032F020D120C84001708000A1782100612149C00091FFFAB0D2A10820207032A02117C000E86DD68A30206FFFFFFFFFFFF021603190A1482020002187A023A02120A36820285031F8216886A26A2020FFF020000000000000000000000000003200214 --packet FFFFFFFFFFFF112233445566080600010800060400011122334455660A0000020000000000000A0000 01 --data 0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000 000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000 --age 0 --v6 --trace R0 R1 PC Instruction
------------------------------------------------- 0 0 0: data 16, 01020304050608060001080006040002 0 0 19: debugbuf size=3644 0 0 23: ldm r0, m[15] 0 0 25: stdw counter=6, r0 0 0 27: ldm r0, m[9] 0 0 29: stdw counter=7, r0 0 0 31: ldm r0, m[8] 134d811 0 33: stdw counter=8, r0 134d811 0 35: li r0, 1 1 0 37: stdw counter=9, r0 1 0 39: ldh r0, [12] 806 0 41: jne r0, 0x806, 157 806 0 46: li r0, 14 e 0 48: jbseq r0, 0x6, 59, 000108000604 e 0 59: ldh r0, [20] 1 0 61: jeq r0, 0x1, 103 1 0 103: ldw r0, [38] a000001 0 105: jeq r0, 0xa000001, 116 a000001 0 116: allocate 60 a000001 0 120: pktcopy src=6, len=6 a000001 0 123: datacopy src=3, len=6 a000001 0 126: datacopy src=9, len=10 a000001 0 129: datacopy src=3, len=6 a000001 0 132: write 0x0a000001 a000001 0 137: pktcopy src=6, len=6 a000001 0 140: pktcopy src=28, len=4 a000001 0 143: ldm r0, m[10] 2a 0 145: add r0, 18 3c 0 147: stm r0, m[10] 3c 0 149: transmit ip_ofs=255 3c 0 153: drop counter=47 Packet dropped Data: 00000000000000000000000001000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000 000000000000000000000000000100000011d8340100000000000000000000000000000000000000000100000078563412 transmitted packet: 112233445566010203040506080600010800060400020102030405060a0000011122334455660a000002000000000000000000000000000000000000
При использовании параметра --trace
инструмент apf_run
выводит подробную информацию о каждом этапе выполнения интерпретатора, что полезно для отладки. В этом примере мы передаем пакет ARP-запроса в программу APF. Вывод показывает, что ARP-запрос отбрасывается, но генерируется ответный пакет. Подробная информация об этом сгенерированном пакете представлена в разделе transmitted packet
.
Распространенные проблемы интеграции
В этом разделе рассматриваются несколько распространенных проблем, возникающих при интеграции APF:
- Неожиданная очистка области данных: Память APF должна быть полностью выделена для APF; изменять область памяти APF разрешено только коду интерпретатора или коду фреймворка (через API HAL).
- Проблемы установки программ APF длиной X байт (X <=
maxLen
): прошивка должна поддерживать чтение и запись любой программы длиной доmaxLen
без сбоев, сбоев и усечения. Запись не должна изменять ни один байт междуX
иmaxLen
. - Реализация APF в коде драйвера: APF следует реализовывать только в прошивке, а не в коде драйвера. В противном случае экономия энергии невозможна, поскольку для обработки пакета процессору необходимо выйти из спящего режима.
- Неверные значения
filter_age
илиfilter_age_16384th
: Значенияfilter_age
(APFv4) иfilter_age_16384th
(APFv6) должны быть корректно переданы функциямaccept_packet()
иapf_run()
. Подробную информацию о вычисленииfilter_age_16384th
см. в документации в файлеapf_interpreter.h
. - APF не включен, когда это необходимо: APF необходимо включить, когда экран выключен и соединение Wi-Fi неактивно или скорость трафика ниже 10 Мбит/с.
- Усеченные пакеты, передаваемые в
accept_packet()
илиapf_run()
: Все одноадресные, широковещательные и многоадресные пакеты, передаваемые вaccept_packet()
илиapf_run()
должны быть полными. Передача усеченных пакетов в APF недопустима.
тесты АПФ
Начиная с Android 15, Android предоставляет тестовые случаи CTS как для одного, так и для нескольких устройств для интеграции фильтра APF и интерпретатора APF, чтобы гарантировать корректную работу APF. Ниже приведено описание назначения каждого тестового случая:
- Интеграционный тест
ApfFilter
иapf_interpreter
: проверяет, чтоApfFilter
генерирует правильный байт-код, аapf_interpreter
правильно выполняет код для получения ожидаемых результатов. - APF single-device CTS : использует одно устройство для проверки функциональности APF на чипсете Wi-Fi. Подтверждает, что:
- APF включается, когда экран выключен, а скорость Wi-Fi-трафика ниже 10 Мбит/с.
- Возможности APF заявлены корректно.
- Операции чтения и записи в области памяти APF выполняются успешно, и область памяти не подвергается неожиданным изменениям.
- Аргументы правильно передаются в
accept_packet()
илиapf_run()
. - Прошивка, интегрированная с APFv4/APFv6, может отбрасывать пакеты.
- Интегрированная с APFv6 прошивка может отвечать на пакеты.
- Многоустройствовый CTS APF : использует два устройства (одно отправитель, одно получатель) для проверки фильтрующего поведения APF. На стороне отправителя генерируются различные типы пакетов, и тест проверяет, корректно ли они отбрасываются, передаются или на них отправляется ответ в соответствии с правилами, настроенными в
ApfFilter
.
Дополнительные инструкции по интеграционному тестированию
Кроме того, мы настоятельно рекомендуем поставщикам чипсетов включать тестирование APF в свои собственные наборы тестов интеграции Wi-Fi-прошивок.
Интеграция тестирования APF в наборы тестов интеграции Wi-Fi-прошивок критически важна для проверки корректной работы APF в сложных сценариях Wi-Fi-подключения, таких как «с фиксацией до разрыва соединения» или «роуминг». Подробные инструкции по проведению интеграционных тестов см. в следующем разделе.
Предпосылки
При проведении интеграционных тестов выполните следующие действия:
- APF должен быть включен во всех тестовых случаях интеграции (например, роуминг, включение-выключение).
- В начале каждого теста очищайте память APF.
- Устанавливайте или переустанавливайте программы APF каждые 5 минут во время теста.
Тестовые сценарии
APF должен быть активен во время интеграционных тестов. В этом документе представлены две программы APF, которые можно установить во время тестирования. Программы представлены в формате шестнадцатеричной строки, и тестировщик должен преобразовать шестнадцатеричную строку в двоичный код и установить их в прошивку, чтобы программы могли выполняться с помощью apf_interpreter
. Во время интеграционного теста тестировщик должен отправлять пакеты, которые, как ожидается, вызовут срабатывание логики фильтрации в программе 1 и программе 2.
Программа АПФ 1
При включённом экране устройства установите программу APF 1. Эта программа может отбрасывать безвредные пакеты, не влияющие на функциональность устройства. Эти пакеты используются для проверки корректности фильтрации сетевого трафика APF.
Логика программы АПФ 1 следующая:
- Удалить и увеличить счетчик:
- Значения EtherType:
0x88A2
,0x88A4
,0x88B8
,0x88CD
,0x88E1
,0x88E3
- Пакеты обнаружения или запроса DHCP IPv4
- RS-пакеты
- Значения EtherType:
- Пройти и увеличить счетчик: Все остальные пакеты.
1-байтовые коды программы APF следующие:
6BF0B03A01B86BF8AA0FB86BF4AA09B8120C6BEC7C005D88A27C005888A47C005388B87C004E88CD7C004988E17C004488E3120C84002008001A1A821B001A1E8600000010FFFFFFFF0A17820B11AB0D2A108204436BE8721D120C84000E86DD0A1482093A0A368204856BE072086BDCB03A01B87206B03A01B87201
Программа АПФ 2
При выключенном экране устройства установите программу APF 2. Эта программа отфильтрует все пакеты, которые фильтрует программа APF 1 , а также пакеты ping-запросов. Чтобы убедиться в корректной установке программы APF 2 , отправьте ping-пакеты на тестируемое устройство.
Логика программы АПФ 2 следующая:
- Удалить и увеличить счетчик:
- Значения EtherType:
0x88A2
,0x88A4
,0x88B8
,0x88CD
,0x88E1
,0x88E3
- Пакеты обнаружения или запроса DHCP IPv4
- RS-пакеты
- Значения EtherType:
- Счетчик отбрасывания и увеличения: пакеты запросов ICMP ping
- Пройти и увеличить счетчик: Все остальные пакеты
Коды 2-байтовой программы APF следующие:
6BF0B03A01B86BF8AA0FB86BF4AA09B8120C6BEC7C007488A27C006F88A47C006A88B87C006588CD7C006088E17C005B88E3120C84002008001A1A821B001A1E8600000010FFFFFFFF0A17820B11AB0D2A108204436BE87234120C84000E86DD0A1482093A0A368204856BE0721F120C84001008000A17820B01AB0D220E8204086BE472086BDCB03A01B87206B03A01B87201
Проверка данных
Чтобы проверить, что программа APF выполняется и пакеты передаются или отбрасываются правильно, выполните следующие действия:
- Извлекайте и проверяйте область данных APF каждые 5 минут.
- Не очищайте счетчик.
- Сгенерируйте тестовые пакеты для активации каждого правила фильтра.
Проверьте приращение счетчика, используя следующие области памяти:
Имя счетчика Расположение памяти DROPPED_ETHERTYPE_DENYLISTED
[Размер_памяти_Apf - 20, Размер_памяти_Apf - 16] DROPPED_DHCP_REQUEST_DISCOVERY
[Размер_памяти_в_памяти - 24, Размер_памяти_в_памяти - 20] DROPPED_ICMP4_ECHO_REQUEST
[Размер_памяти_в_памяти - 28, Размер_памяти_в_памяти - 24] DROPPED_RS
[Размер_памяти_Apf - 32, Размер_памяти_Apf - 28] PASSED_PACKET
[Размер_памяти_Apf - 36, Размер_памяти_Apf - 32]
Псевдокод для программы APF 1 и программы APF 2
Следующий псевдокод подробно объясняет логику программы APF 1 и программы APF 2:
// ethertype filter
If the ethertype in [0x88A2, 0x88A4, 0x88B8, 0x88CD, 0x88E1, 0x88E3]:
drop packet and increase counter: DROPPED_ETHERTYPE_DENYLISTED
// dhcp discover/request filter
if ethertype != ETH_P_IP:
skip the filter
if ipv4_src_addr != 0.0.0.0:
skip the filter
if ipv4_dst_addr != 255.255.255.255
skip the filter
if not UDP packet:
skip the filter
if UDP src port is not dhcp request port:
skip the filter
else:
drop the packet and increase the counter: DROPPED_DHCP_REQUEST_DISCOVERY
// Router Solicitation filter:
if ethertype != ETH_P_IPV6:
skip the filter
if not ICMP6 packet:
skip the filter
if ICMP6 type is not a Router Solicitation:
skip the filter
else:
drop the packet and increase the counter: DROPPED_RS
// IPv4 ping filter (only included in Program 2)
if ethertype != ETH_P_IP:
skip the filter
if it ipv4 protocol is not ICMP:
skip the filter
if port is not a ping request port
skip the filter
else:
drop the packet and increase the counter: DROPPED_ICMP4_ECHO_REQUEST
pass the packet and increase: PASSED_PACKET