2012-10-27 11 views
6

Sto lavorando a un progetto di compiti a casa che coinvolge una "bomba" scritta in compilato c che devo eseguire il reverse engineering per ottenere 5 stringhe che disarmeranno ciascuna delle cinque "fasi" della bomba. Sono bloccato alla fase 3 in questo momento, cercando di tradurre l'assembly (x86, AT & sintassi T credo) prodotto da gdb per quella funzione. Quello che sono riuscito a capire finora è che sta cercando di prendere una stringa di sei numeri come input dell'utente e giudicarli su alcuni criteri, ma è lì che lo sto perdendo. La funzione è la seguente (con il mio tentativo di traduzione pseudocodice accanto ad essa).Traduzione dell'assemblaggio su pseudocodice

0x08048816 <phase_3+0>: push %ebp 
0x08048817 <phase_3+1>: mov %esp,%ebp 
0x08048819 <phase_3+3>: push %edi 
0x0804881a <phase_3+4>: push %ebx 
0x0804881b <phase_3+5>: sub $0x30,%esp 
0x0804881e <phase_3+8>: lea -0x24(%ebp),%eax        
0x08048821 <phase_3+11>: mov %eax,0x4(%esp)       
0x08048825 <phase_3+15>: mov 0x8(%ebp),%eax       
0x08048828 <phase_3+18>: mov %eax,(%esp)        
0x0804882b <phase_3+21>: call 0x8048d2c <read_six_numbers> 
0x08048830 <phase_3+26>: mov -0x24(%ebp),%eax      eax = p1 
0x08048833 <phase_3+29>: cmp $0x1,%eax        if eax != 1 
0x08048836 <phase_3+32>: je  0x804883d <phase_3+39>     explode bomb 
0x08048838 <phase_3+34>: call 0x8048fec <explode_bomb>    else 
0x0804883d <phase_3+39>: movl $0x1,-0xc(%ebp)      ebp[-12] = 1 
0x08048844 <phase_3+46>: jmp 0x804888a <phase_3+116>    while ebp[-12] < 5 { 
0x08048846 <phase_3+48>: mov -0xc(%ebp),%eax       eax = ebp[-12] 
0x08048849 <phase_3+51>: mov -0x24(%ebp,%eax,4),%eax     {magic} 
0x0804884d <phase_3+55>: mov %eax,%ebx        ebx = eax 
0x0804884f <phase_3+57>: mov -0xc(%ebp),%eax       eax = ebp[-12] 
0x08048852 <phase_3+60>: sub $0x1,%eax         eax -= 1 
0x08048855 <phase_3+63>: mov -0x24(%ebp,%eax,4),%eax     {magic} 
0x08048859 <phase_3+67>: mov %eax,%edx        edx = eax 
0x0804885b <phase_3+69>: mov 0x804a6d8,%eax       eax = 0x804a6d8 
0x08048860 <phase_3+74>: mov $0xffffffff,%ecx      ecx = 255 
0x08048865 <phase_3+79>: mov %eax,-0x2c(%ebp)       ebp[-12] = eax 
0x08048868 <phase_3+82>: mov $0x0,%eax         eax = 0 
0x0804886d <phase_3+87>: cld       
0x0804886e <phase_3+88>: mov -0x2c(%ebp),%edi       edi = ebp[-12] 
0x08048871 <phase_3+91>: repnz scas %es:(%edi),%al      {deep magic} 
0x08048873 <phase_3+93>: mov %ecx,%eax        eax = ecx 
0x08048875 <phase_3+95>: not %eax          eax = -eax 
0x08048877 <phase_3+97>: sub $0x1,%eax         eax -= 1 
0x0804887a <phase_3+100>: imul %edx,%eax        eax *= edx 
0x0804887d <phase_3+103>: cmp %eax,%ebx        if (eax != ebx) 
0x0804887f <phase_3+105>: je  0x8048886 <phase_3+112>      explode_bomb 
0x08048881 <phase_3+107>: call 0x8048fec <explode_bomb>     else 
0x08048886 <phase_3+112>: addl $0x1,-0xc(%ebp)       ebp[-12] += 1 
0x0804888a <phase_3+116>: cmpl $0x5,-0xc(%ebp) 
0x0804888e <phase_3+120>: jle 0x8048846 <phase_3+48>    } 
0x08048890 <phase_3+122>: add $0x30,%esp 
0x08048893 <phase_3+125>: pop %ebx 
0x08048894 <phase_3+126>: pop %edi 
0x08048895 <phase_3+127>: pop %ebp 
0x08048896 <phase_3+128>: ret 

Sono almeno un po '(anche se non molto) fiducioso nella maggior parte di questo; le linee che sono assolutamente sicure sono le tre linee attualmente contrassegnate come "magic" - phase_3 + 51, phase_3 + 63 e phase_3 + 91 (le due linee mov con strane sintassi e repnz). Non ho visto molto la sintassi e non riesco a capire quali termini di ricerca utilizzare per cercarli.

Eventuali critiche generali (e/o graffianti) del mio tentativo in questo? Luoghi ovvi dove sto andando fuori dai binari? Ovviamente, dato che questo è compito a casa, non ho bisogno che qualcuno mi dia la risposta; Voglio solo sapere se la mia interpretazione è generalmente valida (e quelle tre righe significano che sono sconcertato).

Grazie mille per qualsiasi aiuto!

* EDIT ***

La funzione read_six_numbers scompone come segue:

0x08048d2c <read_six_numbers+0>: push %ebp 
0x08048d2d <read_six_numbers+1>: mov %esp,%ebp 
0x08048d2f <read_six_numbers+3>: push %esi 
0x08048d30 <read_six_numbers+4>: push %ebx 
0x08048d31 <read_six_numbers+5>: sub $0x30,%esp 
0x08048d34 <read_six_numbers+8>: mov 0xc(%ebp),%eax 
0x08048d37 <read_six_numbers+11>: add $0x14,%eax 
0x08048d3a <read_six_numbers+14>: mov 0xc(%ebp),%edx 
0x08048d3d <read_six_numbers+17>: add $0x10,%edx 
0x08048d40 <read_six_numbers+20>: mov 0xc(%ebp),%ecx 
0x08048d43 <read_six_numbers+23>: add $0xc,%ecx 
0x08048d46 <read_six_numbers+26>: mov 0xc(%ebp),%ebx 
0x08048d49 <read_six_numbers+29>: add $0x8,%ebx 
0x08048d4c <read_six_numbers+32>: mov 0xc(%ebp),%esi 
0x08048d4f <read_six_numbers+35>: add $0x4,%esi 
0x08048d52 <read_six_numbers+38>: mov %eax,0x1c(%esp) 
0x08048d56 <read_six_numbers+42>: mov %edx,0x18(%esp) 
0x08048d5a <read_six_numbers+46>: mov %ecx,0x14(%esp) 
0x08048d5e <read_six_numbers+50>: mov %ebx,0x10(%esp) 
0x08048d62 <read_six_numbers+54>: mov %esi,0xc(%esp) 
0x08048d66 <read_six_numbers+58>: mov 0xc(%ebp),%eax 
0x08048d69 <read_six_numbers+61>: mov %eax,0x8(%esp) 
0x08048d6d <read_six_numbers+65>: movl $0x804965d,0x4(%esp) 
0x08048d75 <read_six_numbers+73>: mov 0x8(%ebp),%eax 
0x08048d78 <read_six_numbers+76>: mov %eax,(%esp) 
0x08048d7b <read_six_numbers+79>: call 0x80485a4 <[email protected]> 
0x08048d80 <read_six_numbers+84>: mov %eax,-0xc(%ebp) 
0x08048d83 <read_six_numbers+87>: cmpl $0x5,-0xc(%ebp) 
0x08048d87 <read_six_numbers+91>: jg  0x8048d8e <read_six_numbers+98> 
0x08048d89 <read_six_numbers+93>: call 0x8048fec <explode_bomb> 
0x08048d8e <read_six_numbers+98>: add $0x30,%esp 
0x08048d91 <read_six_numbers+101>: pop %ebx 
0x08048d92 <read_six_numbers+102>: pop %esi 
0x08048d93 <read_six_numbers+103>: pop %ebp 
0x08048d94 <read_six_numbers+104>: ret  
+1

Se è assemblatore ... le persone non dovrebbero conoscere l'architettura? Ti piace x86? – FoolishSeth

+0

@FoolishSeth sicuramente x86 –

+0

Aggiunta una nota nella domanda: è la sintassi x86, AT & T. – rosalindwills

risposta

7
mov -0x24(%ebp,%eax,4),%eax 

L'istruzione sopra accede a un elemento di una matrice. Questo è chiamato indirizzo SIB in x86, per Scala, Indice, Base. C'è anche un componente Offset. L'array si basa su un indirizzo determinato dal registro Base (EBP qui) più uno spostamento (quando si utilizza un puntatore del frame, le variabili locali, inclusi gli array, vengono indirizzate come offset dal puntatore del frame). Il numero dell'elemento si trova nel registro dell'indice (EAX qui). La dimensione di ogni elemento è determinata dalla scala (4 qui).

mov 0x804a6d8,%eax 
mov $0xffffffff,%ecx 
mov %eax,-0x2c(%ebp) 
mov $0x0,%eax 
cld       
mov -0x2c(%ebp),%edi 
repnz scas %es:(%edi),%al 
mov %ecx,%eax 
not %eax 
sub $0x1,%eax 

Questo è solo strlen(0x805a6d8). ES:EDI punta a una stringa da scansionare (confronta di nuovo un byte di riferimento) a 0x804a6d8. AL contiene il carattere da cercare: 0 - ASCII NUL. cld imposta la direzione per la scansione: crescente (std renderebbe la scansione discendente). ECX: tutti i bit 1. repnz ripetono le istruzioni scas (SCAN STRING) decrementando ECX mentre ECX non è zero (cosa che non accadrà poiché ECX è abbastanza grande da impedirlo) e la scansione non ha esito positivo (NZ, mentre la scansione (confronta tra la stringa e il riferimento AL) non ha impostato il flag di zero). Dopodiché, ECX contiene -1-(steps in the scan). NOT lo rende (steps in the scan). SUB lo rende (steps in the scan) - 1 = (length of string not including the terminating NUL). Anche spiegato a http://www.int80h.org/strlen/.

+0

Wow, grazie. Questo è molto utile. Grazie mille! – rosalindwills