Home Homebrew Rilasciato RING0GDB per eseguire il debug del kernel della PlayStation 4

[Scena PS4] Rilasciato RING0GDB per eseguire il debug del kernel della PlayStation 4

525
0

Lo sviluppo di PS4GDB ha spinto il developer m0rph3us1987 alla pubblicazione di un nuovo payload che una volta iniettato nella console PlayStation 4 ci permetterà di eseguire il debugger del kernel utilizzando GDB.

Come PS4GDB, il payload è integrato in Mira e si avvia in background non appena si carica Mira.

Il payload RING0GDB (triggerRING0.bin) potrebbe risultare inutile per la maggior parte delle persone, ma non per gli sviluppatori che possono eseguire il debugger del kernel e studiarne il funzionamento.

Come attivare RING0GDB

RING0GDB viene avviato automaticamente durante il processo di caricamento di Mira. Da un punto di vista tecnico non si avvia proprio, ma l’installazione avviene sovrascrivendo due ISR (Interrupt Service Routine). Sovrascriviamo le routine per INT1 (debug) e INT3 (breakpoint).

Ciò significa che non appena uno di questi due interrupt viene attivato, RING0GDB prende il controllo e ci consente di connetterci ad esso con gdb proprio come possiamo fare per PS4GDB.

Esempio di debug exec_self_imgact

exec_self_imgact è responsabile del caricamento/avvio dei file eseguibili su PS4. Quindi il nostro obiettivo è impostare un punto di interruzione in questa funzione ed eseguirne il debug non appena viene chiamato dal kernel.

Come accennato in precedenza, dobbiamo attivare uno dei due interrupt. Questo può essere facilmente ottenuto eseguendo un payload del kernel simile a questo:

int main(int argc, char *argv[]){
  asm("int $3");
  return 0;
}

All’interno di questa repository è possibile trovare il binario triggerRING0.bin precompilato contenuto in questo codice.

A questo punto il ModuleLoader introdotto in Mira potrebbe risultare molto utile, questo difatti permette di inviare il binario alla porta 9025 eseguendo RING0GDB.

Non appena viene iniettato il payload alla porta 9025, klog dovrebbe mostrare qualcosa del genere:

[handle_exceptionRing0] remcomOutBuffer allocated at 0xffffa6eb440dc000
received interrupt 03 - errorCode: 0x0
RAX: 0x0000000000000202 RBX: 0xffffa6eb12eac590
RCX: 0x000000000000040d RDX: 0xffffffff841101ef
RSI: 0xffffff8065b8bab0 RDI: 0x0000000000000000
RBP: 0xffffff8065b8baa0 RSP: 0xffffff8065b8ba58
R8: 0xffffff8065b8bb80 R9: 0xffffffff85c40a78
R10: 0x0000000000000001 R11: 0xffffffff85ba0f98
R12: 0x0000000000000000 R13: 0xffffa6eb13540b68
R14: 0xffffff8065b8bab0 R15: 0xffffff8065dd4000
RIP: 0xffffff8065dd401a FLAGS:0x0000000000000286
CS: 0x0000000000000020 SS: 0x0000000000000028
DS: 0xe8afafafafaf003b ES: 0x000000000000003b
FS: 0x0080000000000013 GS: 0x0000000880b8001b
kernelbase: 0xffffffff8394c000
[handle_exceptionRing0] gdb_stub: Entering main loop...
[getpacketRing0] remcomInBufferRing0 allocated at 0xffffa6eb273b0000

<-[gdb_start_serverRing0] gdb_start_server
[gdb_start_serverRing0] sys_socket: 0x3
[gdb_start_serverRing0] sys_bind: 0x0

A questo punto RING0GDB è in attesa che gdb si connetta sulla porta 9946.

Come già fatto per PS4GDB, creare un file (kernel.source) con i comandi necessari che gdb dovrebbe eseguire all’avvio, il file si presenta così:

set architecture i386:x86-64
set disassembly-flavor intel
target remote 192.168.0.2:9946

Ricordarsi di sostituire l’indirizzo IP con l’indirizzo IP della console PS4. Eseguire quindi gdb e caricare il file sorgente, ecco come appare il risultato:

Quindi gdb è connesso e possiamo iniziare il debug. Il nostro obiettivo era impostare un punto di interruzione su exec_self_imgact, quindi dobbiamo trovarne l’indirizzo.

Nel precedente klog, vedi l’indirizzo di base del kernel che nel nostro caso è 0xffffffff8394c000 e so che la diapositiva di exec_self_imgact è 0x3CE730 (fw 6.72). Quindi abbiamo tutto ciò di cui abbiamo bisogno per calcolare l’indirizzo a cui dobbiamo impostare il nostro punto di interruzione.

0xFFFFFFFF8394C000 + 0x3CE730 = 0xFFFFFFFF83D1A730

Quindi impostiamo il nostro punto di interruzione:

A questo punto possiamo dire a gdb di continuare (continua comando), il controllo viene passato di nuovo a gdb non appena il nostro punto di interruzione viene attivato.

Per attivare il breakpoint dovrebbe essere sufficiente avviare un’applicazione, in questo caso Playroom. Come possiamo vedere, non appena Playroom viene caricato, i nostri trigger di breakpoint e possiamo continuare con la nostra sessione di debug.

Conclusione

Il debug del kernel può essere un problema a causa di kaslr e di molti problemi di temporizzazione e blocco che possono verificarsi quando si mantengono le risorse bloccate per troppo tempo.

Download: triggerRING0.bin

Fonte: twitter.com

LASCIA UN COMMENTO

Per favore inserisci il tuo commento!
Per favore inserisci il tuo nome qui

Questo sito usa Akismet per ridurre lo spam. Scopri come i tuoi dati vengono elaborati.