
एक आधिकारिक eml-parser उदाहरण स्क्रिप्ट में पाथ ट्रैवर्सल भेद्यता प्रदर्शित करता है, जो तैयार किए गए अटैचमेंट फ़ाइलनामों के माध्यम से मनमानी फ़ाइल लेखन की अनुमति देता है, साथ में PoC और फिक्स भी।
आधिकारिक उदाहरण स्क्रिप्ट examples/recursively_extract_attachments.py में एक पाथ ट्रैवर्सल भेद्यता है जो इच्छित आउटपुट निर्देशिका के बाहर मनमाना फ़ाइल लेखन की अनुमति देती है। पार्स किए गए ईमेल से निकाले गए अटैचमेंट फ़ाइलनाम सीधे बिना किसी सैनिटाइज़ेशन के आउटपुट फ़ाइल पथ बनाने के लिए उपयोग किए जाते हैं, जिससे हमलावर-नियंत्रित फ़ाइलनाम लक्ष्य निर्देशिका से बाहर निकल सकता है।
फ़ाइल: examples/recursively_extract_attachments.py
पंक्तियाँ: 61–64
for a in m['attachment']:
out_filepath = out_path / a['filename'] # कोई सैनिटाइज़ेशन नहीं
print(f'\tWriting attachment: {out_filepath}')
with out_filepath.open('wb') as a_out:
a_out.write(base64.b64decode(a['raw']))
मान a['filename'] क्राफ्टेड ईमेल अटैचमेंट हेडर के माध्यम से हमलावर-नियंत्रित होता है:
Content-Disposition: attachment; filename="../outside/pwned.txt"
लिखने से पहले कोई पाथ नॉर्मलाइज़ेशन या सीमा सत्यापन नहीं किया जाता है।
.eml फ़ाइल बनाएं:Content-Disposition: attachment; filename="../outside/pwned.txt"
python recursively_extract_attachments.py -p ./emails -o ./safe
./safe/pwned.txt./outside/pwned.txt ← इच्छित निर्देशिका के बाहर लिखा गयावर्चुअल एनवायरनमेंट में pip के माध्यम से स्थापित eml-parser के साथ Kali Linux पर सत्यापित किया गया।
यह भेद्यता केवल उदाहरण स्क्रिप्ट तक सीमित है और कोर eml-parser लाइब्रेरी को प्रभावित नहीं करती है। हालाँकि, चूंकि यह स्क्रिप्ट आधिकारिक रिपॉजिटरी का हिस्सा है और उत्पादन उपयोग के लिए अनुकूलित किए जाने की संभावना है, एक हमलावर क्राफ्टेड ईमेल प्रदान करके निष्पादन संदर्भ के भीतर मनमाना फ़ाइल लेखन प्राप्त कर सकता है।
संभावित हमले के परिदृश्यों में शामिल हैं:
filename="../../etc/cron.d/backdoor"filename="../../var/www/html/shell.php"filename="../../home/user/.ssh/authorized_keys"import os.path
for a in m['attachment']:
filename = os.path.basename(a['filename'])
out_filepath = out_path / filename
if not out_filepath.resolve().is_relative_to(out_path.resolve()):
print(f'[!] Skipping suspicious filename: {a["filename"]}')
continue
print(f'\tWriting attachment: {out_filepath}')
with out_filepath.open('wb') as a_out:
a_out.write(base64.b64decode(a['raw']))