2013-02-16 42 views
5

Tôi muốn xem phiên bản x86 được tạo bởi trình biên dịch just-in-time của .Net. Tôi biết how to do this for "normal" code, được biên soạn trước, nhưng không biết làm thế nào để làm điều đó cho mã được tạo động trong thời gian chạy (mà tôi đang làm với cây biểu thức).Làm cách nào để xem việc tháo gỡ đại biểu được tạo bằng cách biên dịch một cây biểu thức?

Tôi thậm chí không thực sự chắc chắn nên thử những gì. Ví dụ, đại biểu được tạo ra bằng cách biên dịch các điểm biểu thức cây tại một địa chỉ, nhưng tôi không biết phải sử dụng cái gì để xem những gì ở địa chỉ đó.

Trả lời

2

Tôi đã kết thúc bằng cách sử dụng đề xuất cơ bản của leppie, xuất biểu thức cho một hội đồng bên ngoài. Sau đó, tôi sử dụng phản xạ để trích xuất phương pháp và dán nó vào mã của riêng tôi. Sau đó, tôi chạy phương pháp dán, và kiểm tra những gì đã được jitted. Điều này có thể không chính xác 100%, nhưng ít nhất nó cũng đưa ra một dấu hiệu.

Dưới đây là một số mã để viết ra phương pháp (lắp ráp dẫn đến kết thúc trong cùng một thư mục như thực thi):

/// <summary> 
/// Writes an assembly, containing the given method, to the working directory. 
/// The assembly, type, and method are named based on the given hash name. 
/// </summary> 
public static void WriteMethodToAssembly<T>(Expression<T> method, string hashName) { 
    var assemblyName = new AssemblyName(hashName); 
    var assemblyBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.RunAndSave); 
    var moduleBuilder = assemblyBuilder.DefineDynamicModule(assemblyName.Name, assemblyName.Name + ".dll"); 
    var typeBuilder = moduleBuilder.DefineType(hashName, TypeAttributes.Public); 
    var methodBuilder = typeBuilder.DefineMethod("Run" + hashName, MethodAttributes.Public | MethodAttributes.Static); 
    method.CompileToMethod(methodBuilder); 

    typeBuilder.CreateType(); 
    assemblyBuilder.Save(hashName + ".dll"); 
} 

Một khi bạn đã lắp ráp, bạn có thể sử dụng một công cụ như phản xạ để trích xuất phương pháp .

+0

Cảm ơn bạn đã chia sẻ :) – leppie

2

Sử dụng LambdaExpression.CompileToMethod(MethodBuilder).

Sau đó, bạn có thể lưu AssemblyBuilder vào một tệp mà bạn có thể kiểm tra trong trình tháo rời NET yêu thích của mình.

+0

Người lập tức có xử lý CIL được tạo ra khi chạy theo đúng cách giống như CIL được nạp từ một assembly không? Điều gì xảy ra nếu có, ví dụ, chẩn đoán làm tối ưu hóa nhiều hơn trong một trong các trường hợp? –

+0

Bạn có muốn xem hội đồng JIT hoặc IL không? Câu trả lời của tôi không áp dụng cho câu trả lời trước đây. IL nạp từ bất cứ nơi nào nên được điều trị như nhau. – leppie

+0

Tôi muốn xem mã lắp ráp x86. –