Deserialization
Last updated
Last updated
Learn & practice AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE) Learn & practice GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)
Serileştirme, bir nesneyi saklanabilir bir formata dönüştürme yöntemi olarak anlaşılır; bu, nesneyi depolama veya bir iletişim sürecinin parçası olarak iletme amacı taşır. Bu teknik, nesnenin daha sonra yeniden oluşturulabilmesini sağlamak için yaygın olarak kullanılır ve yapısını ve durumunu korur.
Deserialization ise, serileştirmenin tersine olan süreçtir. Belirli bir formatta yapılandırılmış verileri alıp, tekrar bir nesne haline getirmeyi içerir.
Deserialization tehlikeli olabilir çünkü bu, saldırganların serileştirilmiş verileri manipüle ederek zararlı kod çalıştırmalarına veya nesne yeniden yapılandırma sürecinde uygulamada beklenmedik davranışlar yaratmalarına olanak tanır.
PHP'de, serileştirme ve deserialization süreçlerinde belirli sihirli yöntemler kullanılır:
__sleep
: Bir nesne serileştirildiğinde çağrılır. Bu yöntem, serileştirilmesi gereken nesnenin tüm özelliklerinin adlarını içeren bir dizi döndürmelidir. Genellikle bekleyen verileri taahhüt etmek veya benzer temizlik görevlerini yerine getirmek için kullanılır.
__wakeup
: Bir nesne deserialized edildiğinde çağrılır. Serileştirme sırasında kaybolmuş olabilecek veritabanı bağlantılarını yeniden kurmak ve diğer yeniden başlatma görevlerini yerine getirmek için kullanılır.
__unserialize
: Bu yöntem, bir nesne deserialized edilirken __wakeup
yerine çağrılır (varsa). Deserialization süreci üzerinde __wakeup
'a göre daha fazla kontrol sağlar.
__destruct
: Bu yöntem, bir nesne yok edilmek üzereyken veya script sona erdiğinde çağrılır. Genellikle dosya tanıtıcılarını veya veritabanı bağlantılarını kapatmak gibi temizlik görevleri için kullanılır.
__toString
: Bu yöntem, bir nesnenin bir dize olarak muamele görmesini sağlar. Bir dosyayı okumak veya içindeki işlev çağrılarına dayalı diğer görevler için kullanılabilir ve nesnenin metinsel temsilini etkili bir şekilde sağlar.
Eğer sonuçlara bakarsanız, nesne serileştirildiğinde __wakeup
ve __destruct
fonksiyonlarının çağrıldığını görebilirsiniz. Birçok eğitimde __toString
fonksiyonunun bazı özellikleri yazdırmaya çalışırken çağrıldığını göreceksiniz, ancak görünüşe göre bu artık olmuyor.
Eğer sınıfta uygulanmışsa, __unserialize(array $data)
metodu __wakeup()
yerine çağrılır. Bu, serileştirilmiş veriyi bir dizi olarak sağlayarak nesneyi serileştirmeye olanak tanır. Bu metodu, özellikleri serileştirmek ve serileştirme sırasında gerekli görevleri yerine getirmek için kullanabilirsiniz.
Açıklamalı bir PHP örneğini burada okuyabilirsiniz: https://www.notsosecure.com/remote-code-execution-via-php-unserialize/, burada https://www.exploit-db.com/docs/english/44756-deserialization-vulnerability.pdf veya burada https://securitycafe.ro/2015/01/05/understanding-php-object-injection/
Arbitrary php dosyalarını yüklemek ve daha fazlası için PHP autoload işlevselliğini kötüye kullanabilirsiniz:
PHP - Deserialization + Autoload ClassesHerhangi bir nedenle bir değeri başka bir seri hale getirilmiş değere referans olarak seri hale getirmek istiyorsanız:
PHPGGC, PHP deserialization'larını kötüye kullanmak için payload'lar oluşturmanıza yardımcı olabilir.
Uygulamanın kaynak kodunda bir deserialization'ı kötüye kullanmanın bir yolunu bulamayabileceğinizi unutmayın, ancak harici PHP uzantılarının kodunu kötüye kullanabilirsiniz.
Bu nedenle, mümkünse, sunucunun phpinfo()
'sunu kontrol edin ve internette (hatta PHPGGC'nin gadgets'lerinde) kötüye kullanabileceğiniz bazı olası gadget'ları arayın.
Eğer sadece dosyayı okuyan ve içindeki php kodunu çalıştırmayan bir LFI bulduysanız, örneğin file_get_contents(), fopen(), file() veya file_exists(), md5_file(), filemtime() veya filesize()** gibi fonksiyonlar kullanarak.** phar protokolünü kullanarak bir dosya okurken meydana gelen bir deserialization'ı kötüye kullanmayı deneyebilirsiniz. Daha fazla bilgi için aşağıdaki gönderiyi okuyun:
phar:// deserializationNesne unpickle edildiğinde, __reduce__ fonksiyonu çalıştırılacaktır. Kötüye kullanıldığında, sunucu bir hata dönebilir.
Before checking the bypass technique, try using print(base64.b64encode(pickle.dumps(P(),2)))
to generate an object that is compatible with python2 if you're running python3.
For more information about escaping from pickle jails check:
Bypass Python sandboxesAşağıdaki sayfa, yaml'lerde güvensiz deserialization'ı kötüye kullanma tekniğini sunmakta ve Pickle, PyYAML, jsonpickle ve ruamel.yaml için RCE deserialization yükü oluşturmak için kullanılabilecek bir araçla bitmektedir:
Python Yaml DeserializationJS PHP veya Python gibi "sihirli" fonksiyonlara sahip değildir; bu fonksiyonlar sadece bir nesne oluşturmak için çalıştırılacaktır. Ancak, doğrudan çağrılmadan bile sıklıkla kullanılan bazı fonksiyonlar vardır, örneğin toString
, valueOf
, toJSON
.
Eğer bir deserialization'ı kötüye kullanıyorsanız, bu fonksiyonları diğer kodları çalıştırmak için tehlikeye atabilirsiniz (potansiyel olarak prototype pollution'ı kötüye kullanarak) ve çağrıldıklarında rastgele kod çalıştırabilirsiniz.
Bir fonksiyonu doğrudan çağırmadan çağırmanın başka bir "sihirli" yolu, bir async fonksiyondan dönen bir nesneyi tehlikeye atmaktır (promise). Çünkü, eğer o dönüş nesnesini **"then" adında bir fonksiyon türünde bir özellik ile başka bir promise'e dönüştürürseniz, bu, başka bir promise tarafından döndürüldüğü için çalıştırılacaktır. Daha fazla bilgi için bu bağlantıyı takip edin.
__proto__
ve prototype
kirlenmesiBu tekniği öğrenmek istiyorsanız aşağıdaki eğitime göz atın:
NodeJS - __proto__ & prototype PollutionBu kütüphane fonksiyonları serileştirmeye olanak tanır. Örnek:
Serileştirilmiş nesne şöyle görünecektir:
Örnekte, bir fonksiyon serileştirildiğinde _$$ND_FUNC$$_
bayrağının serileştirilmiş nesneye eklendiğini görebilirsiniz.
node-serialize/lib/serialize.js
dosyasında aynı bayrağı ve kodun bunu nasıl kullandığını bulabilirsiniz.
Son kod parçasında görebileceğiniz gibi, eğer bayrak bulunursa eval
fonksiyonu kullanılarak fonksiyon serileştirilir, bu nedenle temelde kullanıcı girişi eval
fonksiyonu içinde kullanılmaktadır.
Ancak, sadece bir fonksiyonu serileştirmek onu çalıştırmaz, çünkü kodun bir kısmının örneğimizde y.rce
çağırması gerekir ve bu oldukça olasılık dışıdır.
Yine de, serileştirilmiş nesneyi değiştirerek bazı parantezler ekleyerek nesne serileştirildiğinde serileştirilmiş fonksiyonun otomatik olarak çalışmasını sağlayabilirsiniz.
Son kod parçasında son parantezi ve unserialize
fonksiyonunun kodu otomatik olarak nasıl çalıştıracağını gözlemleyin:
Daha önce belirtildiği gibi, bu kütüphane _$$ND_FUNC$$_
sonrasındaki kodu alacak ve eval
kullanarak çalıştıracaktır. Bu nedenle, otomatik olarak kod çalıştırmak için fonksiyon oluşturma kısmını ve son parantezi silip sadece bir JS tek satırı çalıştırabilirsiniz; aşağıdaki örnekte olduğu gibi:
Burada daha fazla bilgi bulabilirsiniz bu güvenlik açığını nasıl istismar edeceğiniz hakkında.
funcster'ın dikkate değer bir yönü, standart yerleşik nesnelerin erişilemezliğidir; bunlar erişilebilir kapsamın dışındadır. Bu kısıtlama, yerleşik nesneler üzerinde yöntem çağırmaya çalışan kodun çalıştırılmasını engeller ve console.log()
veya require(something)
gibi komutlar kullanıldığında "ReferenceError: console is not defined"
gibi istisnalara yol açar.
Bu sınırlamaya rağmen, tüm standart yerleşik nesneler dahil olmak üzere küresel bağlama tam erişimin geri kazanılması belirli bir yaklaşım aracılığıyla mümkündür. Küresel bağlamı doğrudan kullanarak, bu kısıtlamayı aşmak mümkündür. Örneğin, aşağıdaki kod parçası kullanılarak erişim yeniden sağlanabilir:
Daha fazla bilgi için bu kaynağı okuyun source.
serialize-javascript paketi yalnızca serileştirme amaçları için tasarlanmıştır ve herhangi bir yerleşik deserialization yeteneğine sahip değildir. Kullanıcılar, deserialization için kendi yöntemlerini uygulamaktan sorumludur. Resmi örnek, serileştirilmiş verileri deserialization için eval
kullanımını önermektedir:
Eğer bu fonksiyon nesneleri deseralize etmek için kullanılıyorsa, bunu kolayca istismar edebilirsiniz:
Daha fazla bilgi için bu kaynağı okuyun source.
Aşağıdaki sayfalarda bu kütüphaneyi kötüye kullanarak rastgele komutlar çalıştırma hakkında bilgi bulabilirsiniz:
Java'da, deserialization geri çağırmaları deserialization süreci sırasında çalıştırılır. Bu yürütme, bu geri çağırmaları tetikleyen kötü niyetli yükler oluşturan saldırganlar tarafından istismar edilebilir ve zararlı eylemlerin potansiyel olarak yürütülmesine yol açabilir.
Kod tabanında potansiyel serileştirme zafiyetlerini belirlemek için arayın:
Serializable
arayüzünü uygulayan sınıflar.
java.io.ObjectInputStream
, readObject
, readUnshare
fonksiyonlarının kullanımı.
Aşağıdakilere ekstra dikkat edin:
Dış kullanıcılar tarafından tanımlanan parametrelerle kullanılan XMLDecoder
.
XStream
'in fromXML
metodu, özellikle XStream sürümü 1.46 veya daha düşükse, çünkü serileştirme sorunlarına duyarlıdır.
readObject
metodu ile birlikte kullanılan ObjectInputStream
.
readObject
, readObjectNodData
, readResolve
veya readExternal
gibi yöntemlerin uygulanması.
ObjectInputStream.readUnshared
.
Serializable
genel kullanımı.
Siyah kutu testleri için, java serileştirilmiş nesnelerini belirten belirli imzalar veya "Sihirli Baytlar" arayın ( ObjectInputStream
'den kaynaklanan):
Onaltılık desen: AC ED 00 05
.
Base64 deseni: rO0
.
Content-type
değeri application/x-java-serialized-object
olarak ayarlanmış HTTP yanıt başlıkları.
Önceki sıkıştırmayı belirten onaltılık desen: 1F 8B 08 00
.
Önceki sıkıştırmayı belirten Base64 deseni: H4sIA
.
.faces
uzantısına sahip web dosyaları ve faces.ViewState
parametresi. Bu desenlerin bir web uygulamasında keşfedilmesi, Java JSF ViewState Deserialization hakkında detaylı bir inceleme yapılmasını gerektirmelidir.
Eğer Java Deserialized istismarının nasıl çalıştığını öğrenmek istiyorsanız Basic Java Deserialization, Java DNS Deserialization ve CommonsCollection1 Payload belgelerine göz atmalısınız.
Bilinen güvenlik açıklarına sahip herhangi bir uygulamanın kurulu olup olmadığını kontrol edebilirsiniz.
You could try to check all the libraries known to be vulnerable and that Ysoserial can provide an exploit for. Or you could check the libraries indicated on Java-Deserialization-Cheat-Sheet. You could also use gadgetinspector to search for possible gadget chains that can be exploited. When running gadgetinspector (after building it) don't care about the tons of warnings/errors that it's going through and let it finish. It will write all the findings under gadgetinspector/gadget-results/gadget-chains-year-month-day-hore-min.txt. Please, notice that gadgetinspector won't create an exploit and it may indicate false positives.
Using the Burp extension gadgetprobe you can identify which libraries are available (and even the versions). With this information it could be easier to choose a payload to exploit the vulnerability.
Read this to learn more about GadgetProbe.
GadgetProbe is focused on ObjectInputStream
deserializations.
Using Burp extension Java Deserialization Scanner you can identify vulnerable libraries exploitable with ysoserial and exploit them.
Read this to learn more about Java Deserialization Scanner.
Java Deserialization Scanner is focused on ObjectInputStream
deserializations.
You can also use Freddy to detect deserializations vulnerabilities in Burp. This plugin will detect not only ObjectInputStream
related vulnerabilities but also vulns from Json an Yml deserialization libraries. In active mode, it will try to confirm them using sleep or DNS payloads.
You can find more information about Freddy here.
Serialization Test
Not all is about checking if any vulnerable library is used by the server. Sometimes you could be able to change the data inside the serialized object and bypass some checks (maybe grant you admin privileges inside a webapp). If you find a java serialized object being sent to a web application, you can use SerializationDumper to print in a more human readable format the serialization object that is sent. Knowing which data are you sending would be easier to modify it and bypass some checks.
The main tool to exploit Java deserializations is ysoserial (download here). You can also consider using ysoseral-modified which will allow you to use complex commands (with pipes for example).
Note that this tool is focused on exploiting ObjectInputStream
.
I would start using the "URLDNS" payload before a RCE payload to test if the injection is possible. Anyway, note that maybe the "URLDNS" payload is not working but other RCE payload is.
java.lang.Runtime.exec() için bir payload oluştururken, bir yürütmenin çıktısını yönlendirmek için ">" veya "|" gibi özel karakterler kullanamazsınız, komutları yürütmek için "$()" kullanamazsınız veya bir komuta boşluklarla ayrılmış argümanlar bile geçiremezsiniz ( echo -n "hello world"
yapabilirsiniz ama python2 -c 'print "Hello world"'
yapamazsınız). Payload'u doğru bir şekilde kodlamak için bu web sayfasını kullanabilirsiniz.
Windows ve Linux için tüm olası kod yürütme payload'larını oluşturmak ve ardından bunları savunmasız web sayfasında test etmek için aşağıdaki scripti kullanmaktan çekinmeyin:
You can use https://github.com/pwntester/SerialKillerBypassGadgetCollection birlikte ysoserial ile daha fazla exploit oluşturmak için. Bu aracın daha fazla bilgisi, aracın sunulduğu konuşmanın slaytlarında bulunmaktadır: https://es.slideshare.net/codewhitesec/java-deserialization-vulnerabilities-the-forgotten-bug-class?next_slideshow=1
marshalsec Java'daki farklı Json ve Yml serileştirme kütüphanelerini istismar etmek için payload'lar oluşturmak için kullanılabilir.
Projeyi derlemek için pom.xml
dosyasına bu bağımlılıkları eklemem gerekti:
Maven'ı kurun ve projeyi derleyin:
Bu Java JSON kütüphanesi hakkında daha fazla bilgi edinin: https://www.alphabot.com/security/blog/2020/java/Fastjson-exceptional-deserialization-vulnerabilities.html
Bazı ysoserial payload'larını test etmek istiyorsanız bu web uygulamasını çalıştırabilirsiniz: https://github.com/hvqzao/java-deserialize-webapp
Java, çeşitli amaçlar için çok fazla serileştirme kullanır:
HTTP istekleri: Serileştirme, parametrelerin, ViewState'in, çerezlerin vb. yönetiminde yaygın olarak kullanılmaktadır.
RMI (Uzak Yöntem Çağrısı): Tamamen serileştirmeye dayanan Java RMI protokolü, Java uygulamalarında uzak iletişim için bir köşe taşıdır.
HTTP üzerinden RMI: Bu yöntem, tüm nesne iletişimleri için serileştirmeyi kullanan Java tabanlı kalın istemci web uygulamaları tarafından yaygın olarak kullanılmaktadır.
JMX (Java Yönetim Uzantıları): JMX, nesneleri ağ üzerinden iletmek için serileştirmeyi kullanır.
Özel Protokoller: Java'da, standart uygulama, ham Java nesnelerinin iletimini içerir; bu, gelecek istismar örneklerinde gösterilecektir.
Serializable
arayüzünü uygulayan bir sınıf, serileştirilemeyecek herhangi bir nesneyi sınıf içinde transient
olarak işaretleyebilir. Örneğin:
Belirli nesnelerin sınıf hiyerarşisi nedeniyle Serializable
arayüzünü uygulaması gereken senaryolarda, istemeden deserialization riski vardır. Bunu önlemek için, aşağıda gösterildiği gibi, sürekli bir istisna fırlatan final
bir readObject()
metodu tanımlayarak bu nesnelerin deserializable olmadığından emin olun:
java.io.ObjectInputStream
'i Özelleştirmek, deserialization süreçlerini güvence altına almak için pratik bir yaklaşımdır. Bu yöntem, aşağıdaki durumlarda uygundur:
Deserialization kodu kontrolünüz altındadır.
Deserialization için beklenen sınıflar biliniyor.
Deserialization'ı yalnızca izin verilen sınıflarla sınırlamak için resolveClass()
yöntemini geçersiz kılın. Bu, yalnızca açıkça izin verilen sınıfların, örneğin deserialization'ı yalnızca Bicycle
sınıfıyla sınırlayan aşağıdaki örnekte olduğu gibi, deserialization'ını önler:
Güvenlik Artırımı için Java Ajansı Kullanımı kod değişikliğinin mümkün olmadığı durumlarda bir geri dönüş çözümü sunar. Bu yöntem esasen zararlı sınıfları kara listeye alma için bir JVM parametresi kullanır:
Dinamik olarak deserialization'ı güvence altına almanın bir yolunu sağlar, anlık kod değişikliklerinin pratik olmadığı ortamlarda idealdir.
rO0 by Contrast Security örneğine bakın
Serileştirme Filtrelerinin Uygulanması: Java 9, serileştirilmiş nesnelerin deserialization'dan önce karşılaması gereken kriterleri belirlemek için güçlü bir mekanizma sağlayan ObjectInputFilter
arayüzü aracılığıyla serileştirme filtrelerini tanıttı. Bu filtreler, deserialization süreci üzerinde ayrıntılı kontrol sunarak küresel veya akış başına uygulanabilir.
Serileştirme filtrelerini kullanmak için, tüm deserialization işlemlerine uygulanan küresel bir filtre ayarlayabilir veya belirli akışlar için dinamik olarak yapılandırabilirsiniz. Örneğin:
Dış Kütüphaneleri Kullanarak Güvenliği Artırma: NotSoSerial, jdeserialize ve Kryo gibi kütüphaneler, Java deserialization'ını kontrol etme ve izleme için gelişmiş özellikler sunar. Bu kütüphaneler, deserialization'dan önce serileştirilmiş nesneleri analiz etme ve özel serileştirme stratejileri uygulama gibi ek güvenlik katmanları sağlayabilir.
NotSoSerial, güvensiz kodun çalıştırılmasını önlemek için deserialization süreçlerini engeller.
jdeserialize, serileştirilmiş Java nesnelerinin deserialization'ını yapmadan analiz edilmesine olanak tanır ve potansiyel olarak zararlı içeriği tanımlamaya yardımcı olur.
Kryo, hız ve verimliliğe vurgu yapan alternatif bir serileştirme çerçevesidir ve güvenliği artırabilecek yapılandırılabilir serileştirme stratejileri sunar.
Deserialization ve ysoserial konuşması: http://frohoff.github.io/appseccali-marshalling-pickles/
Gadgetinspector hakkında konuşma: https://www.youtube.com/watch?v=wPbW6zQ52w8 ve slaytlar: https://i.blackhat.com/us-18/Thu-August-9/us-18-Haken-Automated-Discovery-of-Deserialization-Gadget-Chains.pdf
Marshalsec makalesi: https://www.github.com/mbechler/marshalsec/blob/master/marshalsec.pdf?raw=true
Java ve .Net JSON deserialization makalesi: https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-JSON-Attacks-wp.pdf, konuşma: https://www.youtube.com/watch?v=oUAeWhW5b8c ve slaytlar: https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-Json-Attacks.pdf
Deserialization CVE'leri: https://paper.seebug.org/123/
JNDI Enjeksiyonu nedir, RMI, CORBA & LDAP aracılığıyla nasıl kötüye kullanılır ve log4shell'i nasıl istismar edilir (ve bu zafiyetin bir örneği) hakkında bilgi için aşağıdaki sayfayı ziyaret edin:
JNDI - Java Naming and Directory Interface & Log4ShellJava Mesaj Servisi (JMS) API'si, iki veya daha fazla istemci arasında mesaj göndermek için kullanılan bir Java mesaj odaklı ara yazılım API'sidir. Üretici-tüketici sorununu çözmek için bir uygulamadır. JMS, Java Platformu, Kurumsal Sürüm (Java EE) bir parçasıdır ve Sun Microsystems tarafından geliştirilen bir spesifikasyonla tanımlanmıştır, ancak o zamandan beri Java Topluluk Süreci tarafından yönlendirilmiştir. Uygulama bileşenlerinin Java EE tabanlı olarak mesaj oluşturmasına, göndermesine, almasına ve okumasına olanak tanıyan bir mesajlaşma standardıdır. Farklı bileşenler arasında iletişimi gevşek bir şekilde bağlanmış, güvenilir ve asenkron hale getirir. (Kaynak: Wikipedia).
Bu ara yazılımı kullanarak mesaj gönderen birkaç ürün bulunmaktadır:
Temelde, tehlikeli bir şekilde JMS kullanan birçok hizmet bulunmaktadır. Bu nedenle, bu hizmetlere mesaj göndermek için yeterli ayrıcalıklara sahipseniz (genellikle geçerli kimlik bilgilerine ihtiyacınız olacaktır), tüketici/abone tarafından deserialization yapılacak zararlı nesneler serileştirebilirsiniz. Bu, bu istismar sırasında o mesajı kullanacak tüm istemcilerin enfekte olacağı anlamına gelir.
Bir hizmetin zayıf olduğunu hatırlamalısınız (çünkü kullanıcı girdisini güvensiz bir şekilde deserialization yapıyorsa), yine de zafiyeti istismar etmek için geçerli gadget'lar bulmanız gerekir.
JMET aracı, bilinen gadget'lar kullanarak birkaç zararlı nesne serileştirerek bu hizmetlere bağlanmak ve saldırmak için oluşturulmuştur. Bu istismarlar, hizmet hala zayıfsa ve kullanılan gadget'lardan herhangi biri zayıf uygulama içinde bulunuyorsa çalışacaktır.
JMET konuşması: https://www.youtube.com/watch?v=0h8DWiOWGGA
.Net bağlamında, deserialization istismarları, bir nesnenin deserialization'ı sırasında belirli kodları çalıştırmak için gadget'ların istismar edilmesi şeklinde çalışır.
Kaynak kodu, aşağıdaki durumların varlığı için incelenmelidir:
TypeNameHandling
JavaScriptTypeResolver
Odak, türün kullanıcı kontrolündeki bir değişken tarafından belirlenmesine izin veren serileştiriciler üzerinde olmalıdır.
Arama, sunucu tarafında deserialization yapılabilecek Base64 kodlu dize AAEAAAD///// veya benzeri bir deseni hedeflemelidir ve bu, deserialization yapılacak tür üzerinde kontrol sağlamaktadır. Bu, TypeObject
veya $type
içeren JSON veya XML yapıları dahil, ancak bunlarla sınırlı değildir.
Bu durumda, deserialization istismarlarını oluşturmak için ysoserial.net aracını kullanabilirsiniz. Git deposunu indirdikten sonra, örneğin Visual Studio kullanarak aracı derlemelisiniz.
ysoserial.net'in istismarını nasıl oluşturduğunu öğrenmek istiyorsanız, ObjectDataProvider gadget + ExpandedWrapper + Json.Net formatlayıcı'sının açıklandığı bu sayfayı kontrol edebilirsiniz.
ysoserial.net'in ana seçenekleri: --gadget
, --formatter
, --output
ve --plugin
.
--gadget
, istismar edilecek gadget'ı belirtmek için kullanılır (deserialization sırasında komutları çalıştırmak için istismar edilecek sınıf/fonksiyonu belirtir).
--formatter
, istismarı serileştirmek için kullanılacak yöntemi belirtir (payload'ı deserialization yapmak için arka uçta hangi kütüphanenin kullanıldığını bilmeniz ve aynı kütüphaneyi kullanarak serileştirmeniz gerekir).
--output
, istismarı ham veya base64 kodlu olarak almak isteyip istemediğinizi belirtmek için kullanılır. Not: ysoserial.net, payload'ı UTF-16LE kullanarak kodlayacaktır (Windows'ta varsayılan olarak kullanılan kodlama) bu nedenle ham veriyi alıp sadece bir linux konsolundan kodlarsanız bazı kodlama uyumluluk sorunları yaşayabilirsiniz ve bu da istismarın düzgün çalışmasını engelleyebilir (HTB JSON kutusunda payload hem UTF-16LE hem de ASCII'de çalıştı ama bu her zaman çalışacağı anlamına gelmez).
--plugin
, ysoserial.net, belirli çerçeveler için istismarlar oluşturmak üzere eklentileri destekler; örneğin ViewState.
--minify
, daha küçük bir payload sağlayacaktır (mümkünse)
--raf -f Json.Net -c "anything"
Bu, sağlanan bir formatlayıcı ile kullanılabilecek tüm gadget'ları gösterecektir (Json.Net
bu durumda).
--sf xml
, bir gadget'ı (-g
) belirtebilir ve ysoserial.net "xml" içeren formatlayıcıları arayacaktır (büyük/küçük harf duyarsız).
ysoserial örnekleri ile istismar oluşturma:
ysoserial.net ayrıca her bir exploitin nasıl çalıştığını daha iyi anlamaya yardımcı olan çok ilginç bir parametreye sahiptir: --test
Bu parametreyi belirtirseniz ysoserial.net yerel olarak exploit denemesi yapacaktır, böylece yüklemenizin doğru çalışıp çalışmadığını test edebilirsiniz.
Bu parametre faydalıdır çünkü kodu gözden geçirirseniz aşağıdaki gibi kod parçaları bulacaksınız ( ObjectDataProviderGenerator.cs):
Bu, istismarı test etmek için kodun serializersHelper.JsonNet_deserialize çağıracağı anlamına gelir.
In the önceki kod, oluşturulan istismara karşı savunmasızdır. Yani, bir .Net uygulamasında benzer bir şey bulursanız, muhtemelen o uygulama da savunmasızdır.
Bu nedenle, --test
parametresi, hangi kod parçalarının ysoserial.net tarafından oluşturulabilen deserialization istismarına karşı savunmasız olduğunu anlamamıza olanak tanır.
Nasıl __ViewState parametresini istismar etmeye çalışılır konulu bu POST'a göz atın rastgele kod çalıştırmak için. Eğer kurban makinesinde kullanılan sırları zaten biliyorsanız, kod çalıştırmayı öğrenmek için bu yazıyı okuyun.
.Net'te deserialization ile ilişkili riskleri azaltmak için:
Veri akışlarının nesne türlerini tanımlamasına izin vermekten kaçının. Mümkünse DataContractSerializer
veya XmlSerializer
kullanın.
JSON.Net
için TypeNameHandling
'i None
olarak ayarlayın: %%%TypeNameHandling = TypeNameHandling.None%%%
JavaScriptSerializer
'ı JavaScriptTypeResolver
ile kullanmaktan kaçının.
Deserialized edilebilecek türleri sınırlayın, System.IO.FileInfo
gibi .Net türleri ile ilişkili riskleri anlayarak, bu türler sunucu dosyalarının özelliklerini değiştirebilir ve hizmet reddi saldırılarına yol açabilir.
Riskli özelliklere sahip türlerle dikkatli olun, Value
özelliği ile System.ComponentModel.DataAnnotations.ValidationException
gibi, istismar edilebilir.
Tür örneklemesini güvenli bir şekilde kontrol edin; bu, saldırganların deserialization sürecini etkilemesini önler ve bu nedenle DataContractSerializer
veya XmlSerializer
bile savunmasız hale gelebilir.
BinaryFormatter
ve JSON.Net
için özel bir SerializationBinder
kullanarak beyaz liste kontrolleri uygulayın.
.Net içindeki bilinen güvensiz deserialization aletleri hakkında bilgi sahibi olun ve deserializer'ların bu türleri örneklemediğinden emin olun.
Potansiyel olarak riskli kodu internet erişimi olan koddan izole edin, böylece System.Windows.Data.ObjectDataProvider
gibi bilinen aletleri güvensiz veri kaynaklarına maruz bırakmaktan kaçının.
Java ve .Net JSON deserialization belgesi: https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-JSON-Attacks-wp.pdf, konuşma: https://www.youtube.com/watch?v=oUAeWhW5b8c ve slaytlar: https://www.blackhat.com/docs/us-17/thursday/us-17-Munoz-Friday-The-13th-Json-Attacks.pdf
Ruby'de, serialization marshal kütüphanesindeki iki yöntemle sağlanır. İlk yöntem, dump olarak bilinir ve bir nesneyi bir bayt akışına dönüştürmek için kullanılır. Bu süreç serialization olarak adlandırılır. Tersine, ikinci yöntem load olarak adlandırılır ve bir bayt akışını tekrar bir nesneye döndürmek için kullanılır; bu süreç ise deserialization olarak bilinir.
Serileştirilmiş nesneleri güvence altına almak için, Ruby HMAC (Hash-Based Message Authentication Code) kullanır ve verilerin bütünlüğünü ve doğruluğunu sağlar. Bu amaçla kullanılan anahtar, birkaç olası konumdan birinde saklanır:
config/environment.rb
config/initializers/secret_token.rb
config/secrets.yml
/proc/self/environ
Ruby 2.X genel deserialization'dan RCE alet zincirine (daha fazla bilgi için https://www.elttam.com/blog/ruby-deserialization/):
Diğer RCE zinciri Ruby On Rails'i istismar etmek için: https://codeclimate.com/blog/rails-remote-code-execution-vulnerability-explained/
bu güvenlik açığı raporunda açıklandığı gibi, bazı kullanıcıların temizlenmemiş girişi bir ruby nesnesinin .send()
metoduna ulaşırsa, bu metod nesnenin herhangi bir diğer metodunu herhangi bir parametre ile çağırmaya izin verir.
Örneğin, eval çağırmak ve ardından ruby kodunu ikinci parametre olarak vermek, rastgele kodu çalıştırmaya olanak tanır:
Ayrıca, .send()
yönteminin yalnızca bir parametresi bir saldırgan tarafından kontrol ediliyorsa, önceki yazıda belirtildiği gibi, argüman gerektirmeyen veya argümanlarının varsayılan değerleri olan herhangi bir nesne yöntemini çağırmak mümkündür.
Bunun için, bu gereksinimleri karşılayan ilginç yöntemleri bulmak üzere nesnenin tüm yöntemlerini listelemek mümkündür.
Bu teknik bu blog yazısından alınmıştır.
RCE elde etmek için güvenli olmayan bir deserialization sırasında kötüye kullanılabilecek nesneleri serileştirmek için kullanılabilecek başka Ruby kütüphaneleri vardır. Aşağıdaki tablo, bu kütüphanelerden bazılarını ve yüklenen kütüphanenin deserialized edildiğinde çağırdığı yöntemi göstermektedir (temelde RCE elde etmek için kötüye kullanılacak fonksiyon):
Kütüphane
Girdi verisi
Sınıf içindeki başlatma yöntemi
Marshal (Ruby)
Binary
_load
Oj
JSON
hash
(sınıfın hash(map) içinde anahtar olarak yer alması gerekir)
Ox
XML
hash
(sınıfın hash(map) içinde anahtar olarak yer alması gerekir)
Psych (Ruby)
YAML
hash
(sınıfın hash(map) içinde anahtar olarak yer alması gerekir)
init_with
JSON (Ruby)
JSON
json_create
([json_create ile ilgili notlara bakın](#table-vulnerable-sinks) )
Temel örnek:
Oj'yi kötüye kullanmaya çalışırken, hash
fonksiyonu içinde to_s
çağıran bir gadget sınıfı bulmak mümkün oldu. Bu, spec'i çağıracak ve fetch_path'ı çağıracak şekildeydi; bu da rastgele bir URL almasını sağladı ve bu tür sanitasyonsuz deserialization zafiyetlerinin harika bir dedektörünü sağladı.
Ayrıca, önceki teknikle sistemde bir klasörün de oluşturulduğu, bunun başka bir gadget'ı istismar etmek için bir gereklilik olduğu ve bunun bir RCE'ye dönüştürülmesi gerektiği bulundu:
Daha fazla detay için orijinal gönderiye bakın.
AWS Hacking öğrenin ve pratik yapın:HackTricks Training AWS Red Team Expert (ARTE) GCP Hacking öğrenin ve pratik yapın: HackTricks Training GCP Red Team Expert (GRTE)