gpt4 book ai didi

c# - 从另一个 AppDomain 的程序集中复制方法并从 CurrentDomain 执行它

转载 作者:行者123 更新时间:2023-11-30 12:27:49 29 4
gpt4 key购买 nike

总的来说,我试图从主域中的 dll 执行方法,但之后,卸载该 dll。到目前为止,我已经创建了新的 AppDomain 并在那里加载了 Assembly\dll,使用 MarshalByRefObject 我获取了主体和 MaxStackSize 到主域的方法,在那里创建了 DynamicMethod,在其中重新创建了主体并调用了它。但是当我调用它时出现异常:System.BadImageFormatException:签名不是 IMAGE_CEE_CS_CALLCONV_LOCAL_SIG

获取和调用它的代码:

DynamicMethod method = new DynamicMethod( "func", typeof( void ), new Type[ 0 ] );
var info = method.GetDynamicILInfo( );
info.SetCode( marshal.GetILCode( ), marshal.GetMaxStackSize());
info.SetLocalSignature(
SignatureHelper.GetMethodSigHelper( CallingConventions.Standard, typeof( void ) ).GetSignature( ) );
method.Invoke( null, new object[ 0 ] ); //<-- exception here

marshalProxy 类型的对象.可能需要的一些注意事项:

  1. 我正在获取\调用的方法是public static void Run();
  2. 尝试调用该方法的 AppDomain 和加载 dll\assembly 的 AppDomain 具有相同的引用。

编辑

我通过将 GetSignature 方法的第一个字节更改为 0x07 来修复签名。但是出现了新问题 System.InvalidProgramException: Common Language Runtime detected an invalid program.

最佳答案

你的实现有一个很大的错误,字节数组来自MethodBase.GetMethodBody 不可移植

使用 OpCodes.Call 的方法调用或 OpCodes.Callvirt产生几个字节,一个指示调用类型 (call/callvirt),后跟四个字节表示元数据标记。在这种情况下,此标记可以解析为 Int32 并使用 Module.ResolveMethod 解析为 MethodBase。 .

请注意,这些元数据标记是在编译时生成的;它们可能因编译而异。 (虽然这是编译器的实现细节,但我相信它们只是根据编译期间看到的方法顺序自动递增的数字。)

这意味着您尝试使用的实际字节包含在您的动态模块中无效的元数据标记。它们可能指向与您预期的签名不同的现有方法,或者可能根本不存在于您的模块中。

您需要解析您的 il 代码并再次发出所有内容,从而生成新的有效元数据 token 。

关于c# - 从另一个 AppDomain 的程序集中复制方法并从 CurrentDomain 执行它,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24350769/

29 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com