
un framework per l'hooking di funzioni del kernel iOS per dispositivi compatibili con checkra1n

Output del log del kernel dopo la compilazione e l'esecuzione di example/open1_hook.c
xnuspy è un modulo di pongoOS che installa una nuova syscall, xnuspy_ctl,
che consente di hookare funzioni del kernel dallo spazio utente. Supporta iOS 13.x,
iOS 14.x e iOS 15.x su checkra1n 0.12.2 e superiori. I dispositivi 4K non sono supportati.
Questo modulo neutralizza completamente KTRR/KPP e rende possibile creare memoria RWX all'interno di EL1. Non usarlo sul tuo dispositivo principale.
Richiede libusb: brew install libusb
Esegui make nella directory principale. Costruirà il loader e il modulo.
Aggiungi queste opzioni prima di make.
XNUSPY_DEBUG=1
kprintf).XNUSPY_SERIAL=1
IOLog.XNUSPY_LEAKED_PAGE_LIMIT=n
64. Maggiori informazioni
possono essere trovate in Debugging Kernel Panics.XNUSPY_TRAMP_PAGES=n
XNUSPY_DEBUG e XNUSPY_SERIAL non dipendono l'uno dall'altro.
Dopo aver costruito tutto, fai avviare il dispositivo con checkra1n in una shell
pongo: /Applications/checkra1n.app/Contents/MacOS/checkra1n -p
Nella stessa directory in cui hai costruito il loader e il modulo, esegui
loader/loader module/xnuspy. Dopo aver fatto ciò, xnuspy farà il suo lavoro e
in pochi secondi il dispositivo si avvierà. loader attenderà ancora un paio di
secondi dopo aver emesso xnuspy-getkernelv nel caso in cui SEPROM debba essere sfruttato.
A volte un paio dei miei telefoni si bloccano su "Booting" dopo che checkra1n's KPF
viene eseguito. Non ho ancora capito cosa lo causa, ma se succede, riprova.
Inoltre, se il dispositivo si blocca dopo bootx, riprova. Infine, marcare il
codice compilato di xnuspy_ctl come eseguibile sul mio iPhone X con iOS 13.3.1 è
un po' incostante, ma riesce al 100% delle volte sugli altri miei telefoni. Se ottieni
un panic con un kernel instruction fetch abort quando esegui il tuo programma di hook,
riprova.
xnuspy modificherà una syscall enosys per puntare a xnuspy_ctl_tramp.
Questo è un piccolo trampolino che marca il codice compilato di xnuspy_ctl come
eseguibile e salta ad esso. Puoi trovare l'implementazione di xnuspy_ctl in
module/el1/xnuspy_ctl/xnuspy_ctl.c e degli esempi nella directory example.
All'interno di include/xnuspy/ si trova xnuspy_ctl.h, un header che definisce le costanti
per xnuspy_ctl. È pensato per essere incluso in tutti i programmi che hookano
funzioni del kernel.
Puoi usare sysctlbyname per scoprire quale syscall è stata modificata:```
size_t oldlen = sizeof(long);
long SYS_xnuspy_ctl = 0;
sysctlbyname("kern.xnuspy_ctl_callnum", &SYS_xnuspy_ctl, &oldlen, NULL, 0);
Questa chiamata di sistema accetta quattro argomenti: `flavor`, `arg1`, `arg2` e `arg3`.
Il flavor può essere `XNUSPY_CHECK_IF_PATCHED`, `XNUSPY_INSTALL_HOOK`,
`XNUSPY_REGISTER_DEATH_CALLBACK`, `XNUSPY_CALL_HOOKME`, `XNUSPY_CACHE_READ`,
`XNUSPY_KREAD`, `XNUSPY_KWRITE` o `XNUSPY_GET_CURRENT_THREAD`.
Il significato dei successivi tre argomenti dipende dal flavor.
## `XNUSPY_CHECK_IF_PATCHED`
Questo esiste per permetterti di verificare se `xnuspy_ctl` è presente. Invocarlo con questo
flavor farà sì che restituisca `999`. I valori degli altri argomenti vengono
ignorati.
## `XNUSPY_INSTALL_HOOK`
Ho progettato questo flavor per corrispondere all'API di [`MSHookFunction`](http://www.cydiasubstrate.com/api/c/MSHookFunction/).
`arg1` è l'indirizzo *NON SLIDATO* della funzione del kernel che desideri agganciare. Se
fornisci un indirizzo slidato, molto probabilmente causerai un panic. `arg2` è un puntatore alla tua
funzione sostitutiva compatibile con l'ABI. `arg3` è un puntatore affinché `xnuspy_ctl`
`copyout` l'indirizzo di un trampolino che rappresenta la funzione originale del
kernel. Può essere `NULL` se non intendi chiamare l'originale.
## `XNUSPY_REGISTER_DEATH_CALLBACK`
Questo flavor ti permette di registrare un "callback di terminazione" opzionale, una funzione che xnuspy
chiamerà quando il tuo programma di hook termina. Ti dà la possibilità di pulire tutto ciò
che hai creato dai tuoi hook del kernel. Se hai creato thread del kernel, dovresti
dire loro di terminare in questa funzione.
Il tuo callback non viene invocato in modo asincrono, quindi se ti blocchi, impedisci
al thread di garbage collection di xnuspy di eseguire.
`arg1` è un puntatore alla tua funzione di callback. I valori degli altri argomenti
vengono ignorati.
## `XNUSPY_CALL_HOOKME`
`hookme` è un piccolo stub in assembly che xnuspy esporta attraverso la cache di xnuspy
per permetterti di agganciarlo. Invocare `xnuspy_ctl` con questo flavor farà sì che
`hookme` venga chiamato, fornendoti un modo per ottenere facilmente l'esecuzione di codice nel kernel
senza dover agganciare una funzione reale del kernel.
`arg1` è un argomento che verrà passato a `hookme` quando viene invocato.
Può essere `NULL`.
## `XNUSPY_CACHE_READ`
Questo flavor ti offre un modo per leggere dalla cache di xnuspy. Contiene molte cose
utili come `kprintf`, `current_proc`, `kernel_thread_start`, alcune funzioni libc,
e lo slide del kernel, in modo che tu non debba trovarli da solo. Per un elenco completo
degli ID della cache, consulta `example/xnuspy_ctl.h`.
`arg1` è uno degli ID della cache definiti in `xnuspy_ctl.h` e `arg2` è un
puntatore affinché `xnuspy_ctl` `copyout` l'indirizzo o il valore di ciò che hai richiesto.
I valori degli altri argomenti vengono ignorati.
## `XNUSPY_KREAD`
Questo flavor ti offre un modo semplice per leggere la memoria del kernel dallo spazio utente senza
tfp0.
`arg1` è un indirizzo virtuale del kernel, `arg2` è l'indirizzo di un buffer nello spazio utente,
e `arg3` è la dimensione di quel buffer nello spazio utente. `arg3` byte verranno scritti
da `arg1` a `arg2`.
## `XNUSPY_KWRITE`
Questo flavor ti offre un modo semplice per scrivere nella memoria del kernel dallo spazio utente senza
tfp0.
`arg1` è un indirizzo virtuale del kernel, `arg2` è l'indirizzo di un buffer nello spazio utente,
e `arg3` è la dimensione di quel buffer nello spazio utente. `arg3` byte verranno scritti
da `arg2` a `arg1`.
## `XNUSPY_GET_CURRENT_THREAD`
Questo flavor fornisce allo spazio utente l'indirizzo nel kernel del thread chiamante.
`arg1` è un puntatore affinché `xnuspy_ctl` `copyout` il valore di ritorno di
`current_thread`. I valori degli altri argomenti vengono ignorati.
### Errori
Per tutti i flavor tranne `XNUSPY_CHECK_IF_PATCHED`, viene restituito `0` in caso di successo.
In caso di errore, viene restituito `-1` e `errno` viene impostato. `XNUSPY_CHECK_IF_PATCHED`
non restituisce alcun errore. Viene utilizzato `mach_to_bsd_errno` di XNU per convertire un
`kern_return_t` nell'`errno` appropriato.