Android Packet Filter (APF) की मदद से, फ़्रेमवर्क को रनटाइम के दौरान हार्डवेयर पैकेट फ़िल्टर करने के लॉजिक को कंट्रोल करने की अनुमति मिलती है. इससे सिस्टम को बिजली बचाने में मदद मिलती है. ऐसा इसलिए होता है, क्योंकि हार्डवेयर में पैकेट ड्रॉप हो जाते हैं. साथ ही, Android फ़्रेमवर्क को नेटवर्क की स्थितियों के आधार पर, फ़िल्टर करने के नियमों को रनटाइम पर बदलने की अनुमति मिलती है.
एपीएफ़ के बारे में खास जानकारी
APF में दो मुख्य कॉम्पोनेंट होते हैं:
- एपीएफ़ इंटरप्रेटर, नेटवर्किंग हार्डवेयर पर काम करता है. आम तौर पर, यह वाई-फ़ाई चिपसेट होता है. APF इंटरप्रेटर, हार्डवेयर को मिले पैकेट पर APF बाइटकोड चलाता है. साथ ही, यह तय करता है कि उन्हें स्वीकार करना है, छोड़ना है या उनका जवाब देना है.
- APF प्रोग्राम जनरेशन कोड, मुख्य सीपीयू पर चलता है. यह कोड, नेटवर्क और डिवाइस की स्थिति के हिसाब से APF प्रोग्राम बनाता है और उन्हें अपडेट करता है.
वाई-फ़ाई एचएएल के तरीके, Android फ़्रेमवर्क को APF प्रोग्राम बाइटकोड इंस्टॉल करने और मौजूदा काउंटर पढ़ने की अनुमति देते हैं. नेटवर्क स्टैक मेनलाइन मॉड्यूल, APF के चालू रहने के दौरान किसी भी समय APF प्रोग्राम बाइटकोड को अपडेट कर सकता है.
कई एपीएफ़ फ़िल्टर लागू किए गए हैं. उदाहरण के लिए, APF में ये फ़िल्टर शामिल होते हैं: अनुमति न दी गई इथरटाइप को हटाना, IPv6 राउटर विज्ञापन (आरए) पैकेट को फ़िल्टर करना, मल्टीकास्ट लॉक न होने पर मल्टीकास्ट और ब्रॉडकास्ट ट्रैफ़िक को फ़िल्टर करना, अन्य होस्ट के लिए डीएचसीपी पैकेट हटाना, और बिना मांगे गए पते के रिज़ॉल्यूशन प्रोटोकॉल (एआरपी) और आस-पास के डिवाइसों का पता लगाने (एनडी) वाले पैकेट हटाना. अगर फ़र्मवेयर APFv6 के साथ काम करता है, तो
ApfFilter
यह सामान्य पैकेट टाइप के जवाब देने के लिए भी नियम जनरेट करता है. ऐसा न होने पर, जवाब देने के लिए सीपीयू को चालू करना पड़ता है. जैसे, एआरपी क्वेरी और एनएस क्वेरी. फ़िल्टर की पूरी सूची, ApfFilter
में दी गई है.
एपीएफ़ प्रोग्राम जनरेशन कोड, नेटवर्क स्टैक मॉड्यूल का हिस्सा होता है. इसलिए, नए फ़िल्टर जोड़ने और फ़िल्टर करने के लॉजिक को अपडेट करने के लिए, हर महीने होने वाले मेनलाइन अपडेट का इस्तेमाल किया जा सकता है.
एपीएफ़ में बदलाव
यहां दी गई सूची में, एपीएफ़ के बदलाव के इतिहास के बारे में बताया गया है:
- APFv6: इसे Android 15 में पेश किया गया था. यह वर्शन, पैकेट फ़िल्टर करने की सुविधा के साथ काम करता है. इसमें डीबग करने और मेट्रिक के लिए काउंटर शामिल होते हैं. साथ ही, यह पैकेट ट्रांसमिशन के साथ काम करता है.
- APFv4: इसे Android 10 में पेश किया गया था. यह वर्शन, पैकेट फ़िल्टर करने की सुविधा के साथ काम करता है. इसमें डीबग करने और मेट्रिक के लिए काउंटर शामिल होते हैं.
- APFv2: इसे Android 7 में पेश किया गया था. यह वर्शन, पैकेट फ़िल्टर करने की सुविधा के साथ काम करता है.
APF इंटिग्रेशन
APF इंटरप्रेटर और हार्डवेयर के बीच APF एपीआई, apf_interpreter.h
(APFv4,
APFv6) में तय किए गए हैं.
Wi-Fi फ़र्मवेयर कोड, APFv4 में accept_packet()
या APFv6 में apf_run()
को कॉल करता है. इससे यह तय किया जाता है कि पैकेट को ड्रॉप किया जाना चाहिए (शून्य रिटर्न वैल्यू) या ऐप्लिकेशन प्रोसेसर को पास किया जाना चाहिए (शून्य से अलग रिटर्न वैल्यू). अगर किसी पैकेट को ट्रांसमिट करने की ज़रूरत होती है, तो apf_run()
भी शून्य दिखाता है, क्योंकि इसके पैकेट को ऐप्लिकेशन प्रोसेसर को पास करने की ज़रूरत नहीं होती. अगर फ़र्मवेयर APFv6 के साथ काम करता है, तो उसे apf_allocate_buffer()
और apf_transmit_buffer()
एपीआई लागू करने होंगे. APF इंटरप्रेटर, पैकेट ट्रांसमिशन लॉजिक के दौरान इन दोनों एपीआई को कॉल करता है.
APF के निर्देश अलग-अलग लंबाई के होते हैं. हर निर्देश की लंबाई कम से कम 1 बाइट होती है. एपीएफ़ के निर्देश कोड, एपीएफ़v4 के लिए apf.h
में तय किए गए हैं. वहीं, एपीएफ़v6 के लिए, इन्हें सीधे तौर पर apf_interpreter.c
में शामिल किया गया है.
APF, खास तौर पर डिज़ाइन की गई मेमोरी पर काम करता है. इस मेमोरी का इस्तेमाल, APF प्रोग्राम और डेटा स्टोरेज, दोनों के लिए किया जाता है. इस मेमोरी को चिपसेट से मिटाया या लिखा नहीं जाना चाहिए. हालांकि, APF HAL के तरीकों से ऐसा किया जा सकता है. APF बाइटकोड, डेटा स्टोरेज का इस्तेमाल करके, स्वीकार किए गए और छोड़े गए पैकेट के काउंटर को सेव करता है. डेटा क्षेत्र को Android फ़्रेमवर्क से पढ़ा जा सकता है. एपीएफ़ के निर्देश, मेमोरी का कम इस्तेमाल करते हैं. हालांकि, बैटरी बचाने और फ़ंक्शन के इस्तेमाल की क्षमता को ज़्यादा से ज़्यादा करने के लिए, फ़िल्टर करने के जटिल और डाइनैमिक नियमों की ज़रूरत होती है. इस जटिलता की वजह से, चिपसेट में मौजूद मेमोरी का एक हिस्सा इसके लिए रिज़र्व करना पड़ता है. APFv4 के लिए कम से कम 1024 बाइट मेमोरी की ज़रूरत होती है, जबकि APFv6 के लिए 2048 बाइट मेमोरी की ज़रूरत होती है. हालांकि, हम बेहतर परफ़ॉर्मेंस के लिए, APFv6 के लिए 4096 बाइट आवंटित करने का सुझाव देते हैं. एपीएफ़ इंटरप्रेटर को फ़र्मवेयर में कंपाइल किया जाना चाहिए. APFv4 और APFv6, दोनों इंटरप्रेटर को कोड के साइज़ के लिए ऑप्टिमाइज़ किया गया है. arm32 आर्किटेक्चर के तहत, कंपाइल किया गया APFv4 इंटरप्रेटर करीब 1.8 केबी का होता है. वहीं, ज़्यादा जटिल APFv6 इंटरप्रेटर, जोड़ी गई सुविधाओं (उदाहरण के लिए, नेटिव चेकसम सपोर्ट और नेटिव डीएनएस डीकंप्रेशन कोड) के साथ करीब 4 केबी का होता है.
APF फ़िल्टर, फ़र्मवेयर में चिपसेट वेंडर के हिसाब से बनाए गए अन्य फ़िल्टर के साथ काम कर सकते हैं. चिपसेट बनाने वाली कंपनियां, एपीएफ़ फ़िल्टर करने की प्रोसेस से पहले या बाद में, फ़िल्टर करने का लॉजिक लागू कर सकती हैं. अगर कोई पैकेट, APF फ़िल्टर तक पहुंचने से पहले ही ड्रॉप हो जाता है, तो APF फ़िल्टर उस पैकेट को प्रोसेस नहीं करता है.
APF फ़िल्टर की सुविधा ठीक से काम करे, इसके लिए ज़रूरी है कि APF चालू होने पर फ़र्मवेयर, APF फ़िल्टर को पूरे पैकेट का ऐक्सेस दे. सिर्फ़ हेडर का ऐक्सेस न दे.
APF प्रोग्राम के सैंपल
ApfTest
और
ApfFilterTest
में सैंपल टेस्ट प्रोग्राम शामिल हैं. इनसे पता चलता है कि हर APF फ़िल्टर कैसे काम करता है. जनरेट किए गए प्रोग्राम की जांच करने के लिए, टेस्ट केस में बदलाव करें, ताकि प्रोग्राम को हेक्स स्ट्रिंग के तौर पर प्रिंट किया जा सके.
testdata
फ़ोल्डर में, APF RA फ़िल्टर के लिए APFv4 प्रोग्राम के सैंपल होते हैं. samples
फ़ोल्डर में Python की ऐसी यूटिलिटी होती हैं जो APFv6 ऑफलोड प्रोग्राम जनरेट करती हैं. ज़्यादा जानकारी के लिए, Python यूटिलिटी फ़ाइलों में मौजूद दस्तावेज़ देखें.
एपीएफ़ को डीबग करें
यह देखने के लिए कि डिवाइस पर 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}
: इसका मतलब है कि वाई-फ़ाई चिप, 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_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
विकल्प का इस्तेमाल करें. डेटा क्षेत्र की हेक्स बाइनरी स्ट्रिंग देने के लिए --data option
का इस्तेमाल करें. इसका इस्तेमाल APF काउंटर को सेव करने के लिए किया जाता है. हर काउंटर की लंबाई 4 बाइट होती है. इसलिए, डेटा रीजन की लंबाई इतनी होनी चाहिए कि बफ़र ओवरफ़्लो न हो.
out/host/linux-x86/bin/apf_run --program 6bfcb03a01b8120c6b9494010c06006b907c010588a27c010088a47c00fb88b87c00f688cd7c00f188e17c00ec88e384003908066a0e6bdca2d40600010800060412147a18016bd882ca021a1c6b8c7ac900686bd4a2b706ffffffffffff6a266bbca2b204c0a814656bf872a8120c84005808000a17821e1112149c00171fffab0d2a108210446a3239a204064651dbcc88ff6bf4727e0a1e52f06bac7a7be06bb41a1e7e0000006effffffff6bb07e00000063c0a814ff6be868a25106ffffffffffff6bb872536bf072497c001086dd686bd0a23806ffffffffffff6bc8723a0a147a0b3a6b980a267a2eff6be072240a366ba87a23858218886a26a2040fff02000000000000000000000000006ba472086be4b03a01b87206b03a01b87201 --packet 5ebcd79a8f0dc244efaab81408060001080006040002c244efaab814c0a8ca1e5ebcd79a8f0d --data 00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
Packet passed
Data: 00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000000000000000000001
tcpdump से ली गई पीकैप फ़ाइल के मुकाबले, APF के नतीजों की जांच करने के लिए, apf_run
कमांड का इस्तेमाल इस तरह करें:
out/host/linux-x86/bin/apf_run --program 6bfcb03a01b8120c6b989401df06006b947c01d888a27c01d388a47c01ce88b87c01c988cd7c01c488e17c01bf88e384004408066a0e6bdca401a5000600010800060412147a1e016bd884019900021a1c6b907c01960000686bd4a401820006ffffffffffff6a266bc0a4017b0004c0a82b056bf874017084005f08000a17821f1112149c00181fffab0d2a108211446a3239a20506fabe589435936bf47401470a1e52f06bb07c014200e06bb81a1e7e00000135ffffffff6bb47e0000012ac0a82bff6be868a401160006ffffffffffff6bbc7401176bf074010c7c001086dd686bd0a2fb06ffffffffffff6bcc72fd0a147a0b3a6b9c0a267af1ff6be072e70a366bac7ae6858218886a26a2040fff02000000000000000000000000006ba872cbaa0e82be8eaa0f8c00b7025868a2a40ffabe5894359352a9874d08aa86dd606a12a2792600583afffe80000000000000f7d4e8ccd81ddb43fe80000000000000f8be58fffe94359386006a3aa272024108123c94006b02586a3ea25e0800000000000000006a56a25504030440c01a5a94004e02581a5e94004702586a62a23e04000000006a66a229102409891f9a26ae6d00000000000000006a76a22004190300001a7a94001902586a7ea204102409891f9a26ae6dba98e781ca9ef9ba6bc872086be4b03a01b87206b03a01b87201 --pcap apf.pcap --data 00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000
37 packets dropped
1733 packets passed
Data: 00000000000000000000000000000000000000000200000005000000000000000000000002000000000000001b000000000000000000000001000000000000000000000000000000000000000000000000000000000000000000000689000000000000003c00000000000000000000000000000000000006ea
एपीएफ़वी6 की ट्रांसमिट करने की सुविधाओं की जांच करने के लिए, 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
टूल, इंटरप्रेटर के हर चरण का पूरा आउटपुट देता है. यह डीबग करने में मददगार होता है. इस उदाहरण में, हम एपीएफ़ प्रोग्राम में एआरपी क्वेरी पैकेट डालते हैं.
आउटपुट से पता चलता है कि एआरपी क्वेरी को हटा दिया गया है, लेकिन जवाब वाला पैकेट जनरेट किया गया है.
जनरेट किए गए इस पैकेट की जानकारी, transmitted packet
सेक्शन में दिखती है.
इंटिग्रेशन से जुड़ी आम समस्याएं
इस सेक्शन में, एपीआई इंटिग्रेशन के दौरान आने वाली कुछ सामान्य समस्याओं के बारे में बताया गया है:
- डेटा क्षेत्र को अनचाहे तरीके से साफ़ करना: APF मेमोरी पूरी तरह से APF के लिए होनी चाहिए. सिर्फ़ इंटरप्रेटर कोड या फ़्रेमवर्क कोड (HAL API के ज़रिए) को APF मेमोरी क्षेत्र में बदलाव करने की अनुमति है.
- X बाइट (X <=
maxLen
) के APF प्रोग्राम इंस्टॉल करने से जुड़ी समस्याएं: फ़र्मवेयर को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 चालू होना चाहिए. ऐसा तब भी होना चाहिए, जब वाई-फ़ाई लिंक का इस्तेमाल न हो रहा हो या ट्रैफ़िक 10 एमबीपीएस से कम हो.
accept_packet()
याapf_run()
को भेजे गए छोटे किए गए पैकेट:accept_packet()
याapf_run()
को भेजे गए सभी यूनिकास्ट, ब्रॉडकास्ट, और मल्टीकास्ट पैकेट पूरे होने चाहिए. APF में काटे गए पैकेट पास करना मान्य नहीं है.
एपीएफ़ टेस्ट
Android 15 से, Android, APF फ़िल्टर और APF इंटरप्रेटर इंटिग्रेशन के लिए, सिंगल-डिवाइस और मल्टी-डिवाइस, दोनों तरह के सीटीएस टेस्ट केस उपलब्ध कराता है. इससे यह पक्का किया जा सकता है कि APF सही तरीके से काम कर रहा है. यहां हर टेस्ट केस के मकसद के बारे में जानकारी दी गई है:
ApfFilter
औरapf_interpreter
इंटिग्रेशन टेस्ट: इससे यह पुष्टि की जाती है किApfFilter
सही बाइटकोड जनरेट करता है औरapf_interpreter
कोड को सही तरीके से एक्ज़ीक्यूट करता है, ताकि उम्मीद के मुताबिक नतीजे मिल सकें.- APF सिंगल-डिवाइस सीटीएस:
इसमें एक ही डिवाइस का इस्तेमाल किया जाता है, ताकि वाई-फ़ाई चिपसेट पर APF की सुविधा की जांच की जा सके.
इस कुकी से यह पुष्टि होती है कि:
- स्क्रीन बंद होने पर और वाई-फ़ाई ट्रैफ़िक 10 एमबीपीएस से कम होने पर, एपीएफ़ चालू हो जाता है.
- एपीएफ़ की सुविधाओं के बारे में सही जानकारी दी गई हो.
- APF मेमोरी क्षेत्र पर पढ़ने और लिखने की कार्रवाइयां पूरी होती हैं. साथ ही, मेमोरी क्षेत्र में अचानक बदलाव नहीं होता.
accept_packet()
याapf_run()
में सही तरीके से आर्ग्युमेंट पास किए गए हों.- APFv4/APFv6 के साथ इंटिग्रेट किया गया फ़र्मवेयर, पैकेट छोड़ सकता है.
- APFv6 के साथ इंटिग्रेट किया गया फ़र्मवेयर, पैकेट का जवाब दे सकता है.
- APF मल्टी-डिवाइस सीटीएस:
APF के फ़िल्टर करने के तरीके की जांच करने के लिए, दो डिवाइसों (एक भेजने वाला, एक पाने वाला) का इस्तेमाल करता है. भेजने वाले के सिस्टम पर अलग-अलग तरह के पैकेट जनरेट होते हैं. टेस्ट से यह पुष्टि होती है कि
ApfFilter
में कॉन्फ़िगर किए गए नियमों के आधार पर, उन्हें सही तरीके से ड्रॉप, पास या जवाब दिया गया है या नहीं.
इंटिग्रेशन की जांच करने के लिए अतिरिक्त निर्देश
इसके अलावा, हमारा सुझाव है कि चिपसेट बनाने वाली कंपनियां, APF की जांच को अपने फ़र्मवेयर में वाई-फ़ाई इंटिग्रेशन की जांच करने वाले टेस्ट सुइट में शामिल करें.
फ़र्मवेयर के वाई-फ़ाई इंटिग्रेशन टेस्ट सुइट में एपीएफ़ टेस्टिंग को इंटिग्रेट करना ज़रूरी है. इससे, वाई-फ़ाई कनेक्शन के मुश्किल मामलों में एपीएफ़ के सही तरीके से काम करने की पुष्टि की जा सकती है. जैसे, मेक-बिफ़ोर-ब्रेक या रोमिंग वाई-फ़ाई कनेक्शन के मामले. इंटिग्रेशन टेस्ट करने के बारे में ज़्यादा जानकारी, यहां दी गई है.
ज़रूरी शर्तें
इंटिग्रेशन की जांच करते समय, यह तरीका अपनाएं:
- इंटिग्रेशन के सभी टेस्ट केस में APF चालू होना चाहिए. उदाहरण के लिए, रोमिंग, मेक-बिफ़ोर-ब्रेक.
- हर टेस्ट की शुरुआत में, APF मेमोरी को मिटा दें.
- जांच के दौरान, हर पांच मिनट में APF प्रोग्राम इंस्टॉल या फिर से इंस्टॉल करें.
टेस्ट के उदाहरण
इंटिग्रेशन की जांच के दौरान, एपीएफ़ चालू होना चाहिए. इस दस्तावेज़ में, दो APF प्रोग्राम दिए गए हैं. इन्हें टेस्टिंग के दौरान इंस्टॉल किया जा सकता है. प्रोग्राम, हेक्स स्ट्रिंग फ़ॉर्मैट में होते हैं. टेस्टर को हेक्स स्ट्रिंग को बाइनरी में बदलना होगा और उन्हें फ़र्मवेयर में इंस्टॉल करना होगा, ताकि प्रोग्राम को apf_interpreter
से चलाया जा सके. इंटिग्रेशन टेस्ट के दौरान, टेस्टर को ऐसे पैकेट भेजने चाहिए
जिनसे प्रोग्राम 1 और प्रोग्राम 2 में फ़िल्टर करने की सुविधा ट्रिगर हो.
APF program 1
डिवाइस की स्क्रीन चालू होने पर, APF program 1 इंस्टॉल करें. यह प्रोग्राम, ऐसे पैकेट छोड़ सकता है जिनसे डिवाइस की सुविधाओं पर कोई असर नहीं पड़ता. इन पैकेट का इस्तेमाल यह जांचने के लिए किया जाता है कि APF, नेटवर्क ट्रैफ़िक को सही तरीके से फ़िल्टर कर रहा है या नहीं.
APF प्रोग्राम 1 का लॉजिक यहां दिया गया है:
- ड्रॉप और इंक्रीमेंट काउंटर:
- EtherType वैल्यू:
0x88A2
,0x88A4
,0x88B8
,0x88CD
,0x88E1
,0x88E3
- IPv4 DHCP डिस्कवर या अनुरोध पैकेट
- RS पैकेट
- EtherType वैल्यू:
- पास और इंक्रीमेंट काउंटर: अन्य सभी पैकेट.
APF प्रोग्राम के 1 बाइट कोड यहां दिए गए हैं:
6BF0B03A01B86BF8AA0FB86BF4AA09B8120C6BEC7C005D88A27C005888A47C005388B87C004E88CD7C004988E17C004488E3120C84002008001A1A821B001A1E8600000010FFFFFFFF0A17820B11AB0D2A108204436BE8721D120C84000E86DD0A1482093A0A368204856BE072086BDCB03A01B87206B03A01B87201
APF program 2
डिवाइस की स्क्रीन बंद होने पर, APF program 2 इंस्टॉल करें. यह प्रोग्राम, APF प्रोग्राम 1 के फ़िल्टर किए गए सभी पैकेट और पिंग अनुरोध वाले पैकेट को फ़िल्टर करता है. यह पुष्टि करने के लिए कि APF program 2 सही तरीके से इंस्टॉल किया गया है, टेस्ट किए जा रहे डिवाइस पर पिंग पैकेट भेजें.
APF प्रोग्राम 2 का लॉजिक इस तरह है:
- ड्रॉप और इंक्रीमेंट काउंटर:
- EtherType वैल्यू:
0x88A2
,0x88A4
,0x88B8
,0x88CD
,0x88E1
,0x88E3
- IPv4 DHCP डिस्कवर या अनुरोध पैकेट
- RS पैकेट
- EtherType वैल्यू:
- ड्रॉप और इंक्रीमेंट काउंटर: ICMP पिंग अनुरोध पैकेट
- पास और इंक्रीमेंट काउंटर: अन्य सभी पैकेट
APF प्रोग्राम के 2 बाइट वाले कोड यहां दिए गए हैं:
6BF0B03A01B86BF8AA0FB86BF4AA09B8120C6BEC7C007488A27C006F88A47C006A88B87C006588CD7C006088E17C005B88E3120C84002008001A1A821B001A1E8600000010FFFFFFFF0A17820B11AB0D2A108204436BE87234120C84000E86DD0A1482093A0A368204856BE0721F120C84001008000A17820B01AB0D220E8204086BE472086BDCB03A01B87206B03A01B87201
डेटा की पुष्टि करना
यह पुष्टि करने के लिए कि APF प्रोग्राम को लागू किया गया है और पैकेट सही तरीके से पास किए गए हैं या छोड़े गए हैं, यह तरीका अपनाएं:
- हर पांच मिनट में, एपीएफ़ डेटा क्षेत्र को फ़ेच और पुष्टि करें.
- काउंटर को न हटाएं.
- हर फ़िल्टर नियम को ट्रिगर करने के लिए, टेस्ट पैकेट जनरेट करें.
मेमोरी की इन जगहों का इस्तेमाल करके, काउंटर के बढ़ने की पुष्टि करें:
काउंटर का नाम मेमोरी की जगह DROPPED_ETHERTYPE_DENYLISTED
[ApfRamSize - 20, ApfRamSize - 16] DROPPED_DHCP_REQUEST_DISCOVERY
[ApfRamSize - 24, ApfRamSize - 20] DROPPED_ICMP4_ECHO_REQUEST
[ApfRamSize - 28, ApfRamSize - 24] DROPPED_RS
[ApfRamSize - 32, ApfRamSize - 28] PASSED_PACKET
[ApfRamSize - 36, ApfRamSize - 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