Newsgroup: it.comp.programmare
Titolo: Disassemblatore

Salve a tutto il NG.
Vengo subito al punto.
Ho scritto un prg (con delphi, ma questo non ha importanza) che prende 
in ingresso un file .HEX, derivato dalla compilazione di un programma 
assembler di un microcontrollore ST62XX, e lo riconverte in sorgente 
ASM. Purtroppo tale progetto è nato quasi per scherzo per cui 
ottimizzazione zero!
In questo progetto decodifico le istruzioni passando i valori 
esadecimali del file .HEX ad una serie di CASE annidati che rilevano le 
varie istruzioni e le stampano in un memo ricostruendo il sorgente 
originale, salvo ovviamente il nome delle variabili (che chiamo "var1", 
"var2" ecc) e le label di salto.
Stranamente tale "accrocchio" funziona ed è anche abbastanza veloce, ma 
questo dipende dal fatto che il set di istruzioni dei microcontrollori 
ST62xx è abbastanza ridotto. Ora mi chiedevo se il metodo da me adottato 
fosse il migliore (sicuramente no) oppure l'unico. Daltronde se dovessi 
decodificare il set di istruzioni di un X86, con le centinaia di 
istruzioni diverse di cui è costituito (compresi i vari modi di 
indirizzamento), il mio metodo mostrerebbe tutti i suoi limiti.
Quello che chiedo è quindi in quale modo i disassemblatori professionali 
lavorano? Esiste della documentazione sui migliori algoritmi da 
utilizzare per questo tipo di programmi?
Tenete conto che sono a digiuno su algoritmi e tecniche di 
programmazione, non possedendo un "background" scolastico in materia 
(sono un hobbista),ma non mi spaventa studiare, per cui se qualcuno sa 
darmi qualche dritta, se non altro sulle parole da impostare su Google, 
gliene sarò eternamente grato.
Grazie a tutti e ciao.
Marco.

 tutti i suoi limiti.
Sě, sarebbe molto lento.
Il metodo piů veloce consiste nell'utilizzare tavole di ptr, cioč array di
puntatori a stringhe, istruzioni, tipi di operandi, ecc...
In pratica si utilizza il primo byte dell'opcode come indice in un array di
puntatori a funzioni o label (specialmente se programmato in assembly).
A questo punto l'opcode viene analizzato e viene utilizzato il secondo byte
dell'opcode in una nuova tavola (solitamente dipendente dalla prima, quindi
esistono varie versioni della tavola secondaria).
Per es:
tab1    dd    type1, type2, type3, invalid
type1    dd    type1_sub1, type1_sub2, type1_sub3, invalid
ecc...
    mov    eax, opcode
    mov    edx, eax
    and    eax, 0ffh
    shr    edx, 8        ; elimina il primo byte
    jmp    [tab1+eax*4]
type1:
    mov    eax, edx
    and    eax, 0ffh
    shr    edx, 8        ; elimina il secondo byte
    jmp    [type1+eax*4]
type1_sub1:
type1_sub2:
type1_sub3:
type2:
    .......
type2_sub1:
    ...
type2_sub2:
    ...
type3:
    .....
invalid:
    ; opcode invalido...
ecc...
La struttura di questo "albero di chiamate" ti viene suggerito dalla tavole
per decifrare gli opcode che si trovano solitamente in fondo ai manuali
(vedi il secondo manuale Intel (Pentium 4 Manuals)).
Vedrai che nel manuale Intel c'č una sezione per "codificare" opcode e
"decodificare" opcode (sono due cose - se vuoi che siano entrambe
efficienti - completamente diverse).
Ovviamente incontrerai punti nei quali dovrai trattare qualche caso
speciale...hai presente i prefissi? E' un inferno...e inoltre non č raro
trovare errori sparsi per tutto il manuale (e ritrovarsi a sorridere nel
vedere che la Numega non se n'č accorta, cosě come molti altri programmatori
di disassemblatori e debugger).
Kiuhnm


Sicuramente dev'essere un inferno lavorare con il set di un P4!!
Comunque, per il momento, mi accontento di ottimizzare la mia umile 
applicazioncina :)), chissà che in futuro non tenti anche con un P4.
Per il momento ti ringrazio della tua risposta.
Ciao.
Marco.