PDA

View Full Version : [PYTHON] Disassemblare


!k-0t1c!
15-05-2009, 10:24
Per varie ragioni sono interessato ad effettuare analisi statica su alcuni moduli in python. Avendo già esperienza con il CIL penso che il bytecode di python non possa crearmi troppi problemi, ma al momento non so come ottenere un dump del bytecode di un modulo (.pyo)
Dunque la domanda è se è possibile farlo, quanto agevolmente e se eventualmente insieme al listato è possibile avere anche informazioni riguardo al file offset a cui si trova l'istruzione. Infine gradirei sapere se (a fini di instrumentation) esiste la possibilità di modificare il bytecode e salvare un nuovo modulo contenente le modifiche apportate e in caso come fare :)

Grazie anticipatamente

cdimauro
16-05-2009, 10:01
Per varie ragioni sono interessato ad effettuare analisi statica su alcuni moduli in python. Avendo già esperienza con il CIL penso che il bytecode di python non possa crearmi troppi problemi,
No, perché è molto più leggibile.
ma al momento non so come ottenere un dump del bytecode di un modulo (.pyo)
Se hai il sorgente, puoi usare il modulo dis della libreria standard per vedere qual è il codice generato.

In alternativa potresti usare il programma che ho scritto per wpython e che è in grado di generare anche qualche statistica. Lo trovi qui (http://code.google.com/p/wpython/source/browse/trunk/Tools/codestats/ByteCodeStats.py).

Senza parametri esegue la compilazione di tutti i file .py che trova nella libreria standard (nelle cartelle Lib e Tools, per la precisione). Se ci sono dei parametri, invece, è in grado di compilare sia i singoli file che le intere cartelle specificate.
Se, oltre alle statistiche, ti serve visualizzare anche il bytecode di tutti gli oggetti che ne hanno, basta mettere come primo parametro -print. A differenza del modulo dis, è in grado di visualizzare ricorsivamente tutti gli oggetti dotati di codice che riesce a trovare all'interno di altri oggetti.
Quindi l'output può essere anche molto lungo.
Dunque la domanda è se è possibile farlo, quanto agevolmente e se eventualmente insieme al listato è possibile avere anche informazioni riguardo al file offset a cui si trova l'istruzione.
Se vuoi / puoi operare soltanto sul compilato (file .pyc o .pyo) l'unica strada è affidarsi a programmi che esaminano questo tipo di file.

Tipo questo (http://nedbatchelder.com/blog/200804/the_structure_of_pyc_files.html) che carica un file .pyc (ma penso vada bene anche per i .pyo), eseguendo l'unmarshalling dei dati (tramite un'apposita libreria).
Infine gradirei sapere se (a fini di instrumentation) esiste la possibilità di modificare il bytecode e salvare un nuovo modulo contenente le modifiche apportate e in caso come fare :)

Grazie anticipatamente
Puoi utilizzare byteplay (http://pypi.python.org/pypi/byteplay/0.1) per "giocare" ad assemblare bytecode.

Comunque modificare direttamente i file .pyc è abbastanza complicato, e non ho trovato in giro programmi in grado di farlo. Quindi dovresti fartelo tu.

Se invece hai il file .py, puoi, ad esempio, rimpiazzare il bytecode prodotto normalmente dal compilatore con uno che hai assemblato tu con byteplay.

Personalmente seguirei questa strada, che è la più semplice.