2012-02-22 13 views
5

Ho scritto alcune funzioni per creare un file exe usando ILGenerator. Quello che voglio è mostrare all'utente il linguaggio IL generato senza l'utilizzo di strumenti esterni come ILDasm o Reflector.Recupera codice da ILGenerator

durante l'esecuzione del mio programma Ho aggiunto ogni OpCode a ILGenerator, così posso salvare ognuno di questo OpCode in una lista usando una stringa con la rappresentazione OpCode ma desidero preferire ottenere il codice IL direttamente. Può essere fatto?

Importante: Sto usando Mono 2.6.

+3

Mono.Cecil è la risposta standard per questo tipo di domande. –

risposta

3

Come Hans Passant aveva detto e svick, la risposta è Mono.Cecil. Vediamo:

using Mono.Cecil; 
using Mono.Cecil.Cil; 

[...] 


public void Print() { 
    AssemblyDefinition assembly = AssemblyDefinition.ReadAssembly(this.module_name); 

    int i = 0, j = 0; 
    foreach (TypeDefinition t in assembly.MainModule.Types) { 
     if (t.Name == "FooClass") { 
      j = i; 
     } 
     i++; 
    } 

    TypeDefinition type = assembly.MainModule.Types[ j ]; 

    i = j = 0; 
    foreach (MethodDefinition md in type.Methods) { 
     if (md.Name == "BarMethod") { 
      j = i; 
     } 
     i++; 
    } 

    MethodDefinition foundMethod = type.Methods[ j ]; 

    foreach(Instruction instr in foundMethod.Body.Instructions) { 
     System.Console.WriteLine("{0} {1} {2}", instr.Offset, instr.OpCode, instr.Operand); 
    } 
} 

Sicuro che può essere fatto più efficiente ma risolve il mio problema.

+0

Penso che il tuo codice possa essere facilmente riscritto per essere molto più leggibile usando LINQ e 'Single()'. – svick

5

Se si dispone di un MethodBuilder, si dovrebbe essere in grado di utilizzare builder.GetMethodBody().GetILAsByteArray() per ottenere l'IL come byte[]. Ma per dare un senso a tutto questo, avresti bisogno di analizzarlo in qualche modo.

Quindi, una scelta migliore probabilmente sta usando Mono Cecil, che può dare il codice IL di un assieme in un formato leggibile.