2015-06-21 58 views
2

我正在使用RemotingLite庫(see at github),並且存在Proxy類工廠的問題。 簡而言之,問題在於生成用於返回像用戶定義結構這樣的對象的代碼。MSIL存儲結構的值返回

這裏的原代碼的一部分:

... 
mIL.Emit(OpCodes.Ldloc, resultLB.LocalIndex); //load the result array 
mIL.Emit(OpCodes.Ldc_I4, 0); //load the index of the return value. Alway 0 
mIL.Emit(OpCodes.Ldelem_Ref); //load the value in the index of the array 

if (returnType.IsValueType) 
{ 
    mIL.Emit(OpCodes.Unbox, returnType); //unbox it 
    mIL.Emit(ldindOpCodeTypeMap[returnType]); 
} 
else 
    mIL.Emit(OpCodes.Castclass, returnType); 
} 
     mIL.Emit(OpCodes.Ret); 

ldindOpCodeTypeMap是一個像OpCodes.Ldind_U2等操作碼字典所以它僅適用於標準MSIL類型,如Int16, Int32等,但我需要什麼,如果我需要做的推入棧然後返回一個自定義值ValueType(例如 - Guid - 大小爲16字節)?

例如:

... 
mIL.Emit(OpCodes.Unbox, returnType); //unbox it 
OpCode opcode; 
if (ldindOpCodeTypeMap.TryGetValue(returnType, out opcode)) 
{ 
    mIL.Emit(ldindOpCodeTypeMap[returnType]); 
} 
else 
{ 
    // here I getting the size of custom type 
    var size = System.Runtime.InteropServices.Marshal.SizeOf(returnType); 
    // what next? 
} 
... 

這裏我得到一個尺寸定製ValueType價值。那麼如何將自定義ValueType的值加載到評估堆棧上,如Ldind_ x opcodes那樣間接地執行該操作? 謝謝!

回答

3

Ldobj會做你想做的。但是你也可以用Unbox_Any替換整個條件:它將完成你需要的值類型或引用類型。

的全部更換爲您發佈的代碼如下:

... 
mIL.Emit(OpCodes.Ldloc, resultLB.LocalIndex); //load the result array 
mIL.Emit(OpCodes.Ldc_I4, 0); //load the index of the return value. Alway 0 
mIL.Emit(OpCodes.Ldelem_Ref); //load the value in the index of the array 

mIL.Emit(OpCodes.Unbox_Any, returnType); 
mIL.Emit(OpCodes.Ret); 
+0

感謝,我會努力再後的結果 – user2598575