2014-11-18 12 views
5

Sono nuovo di lldb e cercando di diagnosticare un errore utilizzando po [$eax class]esecuzione è stata interrotta, la ragione: EXC_BAD_ACCESS (codice = 1, indirizzo = 0xb06b9940)

L'errore mostrato nella UI è:

Thread 1: EXC_BREAKPOINT (code=EXC_i386_BPT, subcode=0x0) 

Ecco la console lldb compreso quello che ho inserito e ciò che è stato restituito:

(lldb) po [$eax class] 
error: Execution was interrupted, reason: EXC_BAD_ACCESS (code=1, address=0xb06b9940). 
The process has been returned to the state before expression evaluation. 

il toggle stato breakpoint globale è fuori.

risposta

3

L'app viene arrestata perché il codice in esecuzione genera un'eccezione Mach non rilevata. Le eccezioni Mach sono l'equivalente di BSD Signals per il kernel Mach - che costituisce i livelli più bassi del sistema operativo macOS.

In questo caso, la specifica eccezione Mach è EXC_BREAKPOINT. EXC_BREAKPOINT è una fonte comune di confusione ... Perché ha la parola "breakpoint" nel nome la gente pensa che sia un breakpoint del debugger. Non è del tutto sbagliato, ma l'eccezione è usata in generale.

EXC_BREAKPOINT è infatti l'eccezione che gli strati inferiori di Mach segnalano quando esegue una determinata istruzione (un'istruzione trap). Quella istruzione trap viene utilizzata da lldb per implementare i punti di interruzione, ma viene anche utilizzata come alternativa a assert in vari bit del software di sistema. Ad esempio, swift usa questo errore se si accede oltre la fine di un array. È un modo per fermare il tuo programma proprio al punto dell'errore. Se si sta eseguendo fuori dal debugger, si verificherà un arresto anomalo. Ma se si sta eseguendo il debugger, il controllo verrà restituito al debugger con questo motivo di interruzione EXC_BREAKPOINT.

Per evitare confusione, lldb non mostrerà mai EXC_BREAKPOINT come il motivo di arresto se il trap era uno che lldb inserito nel programma si sta eseguendo il debug per implementare un punto di interruzione del debugger. Invece dirà sempre breakpoint n.n.

Quindi, se si vede un thread interrotto con EXC_BREAKPOINT come motivo di arresto, significa che si è verificato un errore fatale, in genere in alcune librerie di sistema utilizzate dal programma. Un backtrace a questo punto ti mostrerà quale componente sta generando quell'errore.

Ad ogni modo, dopo aver riscontrato questo errore, si è tentato di calcolare la classe del valore nel registro eax chiamando il metodo di classe su di esso eseguendo po [$eax class]. Chiamare quel metodo (che causerà l'esecuzione del codice nel programma che si sta eseguendo il debug) porterà a un arresto anomalo. Questo è ciò che il messaggio di "errore" che hai citato ti stava dicendo.

Questo è quasi sicuramente perché $eax non punta a un oggetto ObjC valido, quindi stai solo chiamando un metodo su un valore casuale, e questo è in crash.

Nota: se si esegue il debug di un programma a 64 bit, $ eax è in realtà i 32 bit inferiori del registro di passaggio dell'argomento reale - $ rax. È improbabile che i 32 bit inferiori di un puntatore a 64 bit siano un valore di puntatore valido, quindi non sorprende affatto che chiamare class abbia provocato un arresto anomalo.

Se si stava tentando di chiamare classe il primo argomento passato (auto nei metodi objc) a 64 bit di Intel, si voleva davvero fare:

(lldb) po [$rax class] 

nota, che era anche improbabile che funzioni, dal momento che contiene solo self all'inizio della funzione. Quindi viene utilizzato come registro scratch. Quindi, se sei in qualche modo nella funzione (il fatto che il tuo codice abbia fatalmente fallito qualche test sembra probabile) sarebbe improbabile che $ rax contenga ancora self.

Nota anche, se questo è un programma a 32 bit, quindi $eax non viene in effetti utilizzato per il passaggio di argomenti - il codice Intel a 32 bit passa gli argomenti nello stack, non nei registri.

In ogni caso, la prima cosa da fare per capire cosa è andato storto è stato stampare il backtrace quando si ottiene questa eccezione e vedere quale codice si stava eseguendo nel momento in cui si è verificato questo errore.

+0

@Jim Ingham Potresti modificare la tua risposta per renderla facile da leggere? Penso che molte persone siano difficili da capire. – aircraft

+0

Sto affrontando lo stesso problema ma potresti fornire qualche frammento o immagine per spiegare le tue risposte per favore –

+0

Se puoi dirmi dove ti ho perso nella risposta sopra, posso provare ad espandermi su quell'area per renderla più chiara. –

Problemi correlati