
A linux system call fuzzer using TriforceAFL
नया: जो लोग TriforceAFL और TLSF के साथ प्रयोग करना चाहते हैं, Richard Johnson ने एक Dockerfile बनाई है जो दोनों को इंस्टॉल करती है (और आपके लिए Linux कर्नेल भी बनाती है)। यह यहाँ उपलब्ध है https://hub.docker.com/r/moflow/afl-triforce/tags/।
यह Linux x86_64 कर्नेलों का सिस्टम कॉल
फ़ज़िंग करने के लिए AFL और QEMU का उपयोग करने वाली फाइलों का एक संग्रह है। उपयोग करने के लिए
आपको https://github.com/nccgroup/TriforceAFL से TriforceAFL
और फ़ज़ करने के लिए एक कर्नेल इमेज की आवश्यकता होगी। स्क्रिप्ट्स मानती हैं कि TriforceAFL
$TAFL या ../TriforceAFL/ में मिलता है (नोट: testAfl बनाने के लिए
../TriforceAFL/config.h का मौजूद होना आवश्यक है)।
निर्माण करने के लिए:
make
चलाने के लिए, पहले ./kern/bzImage में एक कर्नेल इंस्टॉल करें और
/proc/kallsyms निकालें
./kern/kallsyms में। K=kern पर्यावरण चर को अपने कर्नेल की ओर संकेत करने के लिए सेट करें।
अब चलाएँ:
make inputs
./runFuzz -M M0
ध्यान दें कि runFuzz स्क्रिप्ट एक master या slave नाम की अपेक्षा करती है,
क्योंकि यह हमेशा master/slave मोड में चलती है।
अधिक उपयोग जानकारी के लिए runFuzz स्क्रिप्ट देखें।
यह भी ध्यान दें कि यह केवल उदाहरण इनपुट का एक छोटा समूह बनाता है।
बड़ी संख्या में महत्वपूर्ण सिस्टम कॉल्स का परीक्षण करने के लिए, आप शायद
प्रत्येक सिस्टम कॉल का एक उदाहरण, या कम से कम एक उदाहरण
सिस्टम कॉल के प्रत्येक "आकार" के लिए बनाना चाहेंगे। इन्हें inputs/ में रखा जाना चाहिए।
उदाहरण के लिए gen2.py देखें।
परीक्षण मामलों (जैसे क्रैश) को पुनरुत्पादित करने के लिए चलाएँ:
./runTest inputs/ex1
./runTest outputs/crashes/id*
आप ड्राइवर को अनुकरणित वातावरण से बाहर भी चला सकते हैं
-t विकल्प के साथ, -vv के साथ विस्तृत लॉगिंग के साथ
और -x के साथ वास्तव में सिस्टम कॉल किए बिना:
./driver -tvvx < inputs/ex1
strace ./driver -t < inputs/ex1
कभी-कभी कर्नेल को बूट करने और इंटरैक्टिव रूप से परीक्षण चलाने में सक्षम होना उपयोगी होता है। ऐसा करने के लिए, rootTemplate फाइलों को अपनी आवश्यकता अनुसार संपादित करें (उदाहरण के लिए, रूट फाइलसिस्टम में अधिक परीक्षण उपकरण जोड़ने के लिए), फिर चलाएँ:
./runCmd
शेल के अलावा अन्य कमांड्स को आमंत्रित किया जा सकता है,
उन्हें runCmd के कमांड लाइन तर्कों के रूप में निर्दिष्ट करके।
नोट: शेल के साथ काम पूरा होने पर, QEMU प्रॉम्प्ट पाने के लिए ^A-c उपयोग करें
और quit टाइप करें।
डीबगिंग उस कर्नेल के साथ सबसे आसान होती है जो डीबगिंग प्रतीकों को सक्षम करके बनाया गया हो।
runTest का उपयोग कर्नेल शुरू करने और ड्राइवर के माध्यम से एक परीक्षण चलाने के लिए करें,
या शेल से मैन्युअल रूप से एक परीक्षण मामला चलाने के लिए runCmd का उपयोग करें।
afl-qemu-system-trace शुरू करते समय अपनी रन स्क्रिप्ट में -s विकल्प शामिल करें।
यह TCP पोर्ट 1234 पर gdb समर्थन सक्षम करेगा। getvmlinux का उपयोग करके
अपने bzImage कर्नेल से vmlinux कर्नेल इमेज निकालें और gdb चलाएँ
सिस्टम बूट होने के बाद:
cp kern/bzImage .
./getvmlinux
gdb ./vmlinux
target remote :1234
break somefunction
continue
आप runTest के क्रैश होने के बाद डीबगर को संलग्न कर सकते हैं
या runCmd में मैन्युअल रूप से बग ट्रिगर करने से पहले।
ध्यान दें कि Linux स्रोत ऑप्टिमाइज़ेशन के साथ संकलित किए जाते हैं
डिफ़ॉल्ट रूप से चालू। यह डीबगिंग को भ्रमित करने वाला और कठिन बना सकता है।
आप फ़ाइल-दर-फ़ाइल आधार पर ऑप्टिमाइज़ेशन अक्षम कर सकते हैं
उस सबडायरेक्टरी के Linux make फ़ाइल को संपादित करके जिसमें फ़ाइल स्थित है
और Makefile में CFLAGS_name.o = -O0 जोड़कर। उदाहरण के लिए
kernel/Makefile को संपादित करके और CFLAGS_sys_ni.o = -O0 जोड़ने से
kernel/sys_ni.o बनाते समय ऑप्टिमाइज़ेशन अक्षम हो जाएगा।
getSyms शेल स्क्रिप्ट runCmd का उपयोग करके cat /proc/kallsyms चलाती है
और इसे kallsyms नामक स्थानीय फ़ाइल में निकालती है। यह आमतौर पर
आपके कर्नेल को फ़ज़िंग के लिए तैयार करने हेतु उपयोग किया जाता है:
kallsyms प्राप्त करने के लिए K=yourKernDir ./getSyms चलाएँmv kallsyms yourKernDir चलाएँनोट: Linux 2.* कर्नेल को फ़ज़ करते समय आपको सक्षम करने की आवश्यकता होगी
CPU टाइमर। जब टाइमर सक्षम नहीं होता है, तो पैनिक और लॉगिंग
डिटेक्शन ठीक से काम नहीं करते प्रतीत होते हैं और पैनिक
हैंग में परिणत होते हैं। टाइमर सक्षम करने के लिए, startForkserver(1) कॉल करें
driver.c में startForkserver(0) के बजाय। यह समस्या
Linux3.* और Linux4.* कर्नेलों में नहीं होती प्रतीत होती है।