在非托管程序中托管CLR时从内存加载程序集

时间:2015-07-07 01:54:13

标签: c++ .net reflection clr .net-assembly

由于丰富的文档,我设法在非托管程序中托管CLR。 但是,当托管CLR时,似乎只能从硬盘驱动器加载程序集 - 运行托管应用程序时,可以通过调用Assembly.Load()来从内存加载程序集。

有没有办法从内存中执行托管CLR中的程序集?像:

  1. 将托管程序集写入内存
  2. 发起CLR
  3. 启动CLR
  4. 从内存执行托管程序集
  5. 等待托管程序集返回
  6. 停止CLR
  7. 我已经在网络和MSDN上搜索了几个小时,但无法找到解决此问题的方法!我想出的一个解决方法是涉及另一个调用Assembly.Load()的程序集 - 但是我担心这可能有点矫枉过正。

    提前感谢任何提示或提示!

1 个答案:

答案 0 :(得分:2)

我建议你从这个样本开始:C++ app hosts CLR 4 and invokes .NET assembly (CppHostCLR)似乎几乎可以满足您的需求。唯一缺少的部分是它没有从内存加载程序集,而是使用文件。

所以你需要做的就是替换以下行(在RuntimeHostV4.cpp中):

// Load the .NET assembly. 
wprintf(L"Load the assembly %s\n", pszAssemblyName); 
hr = spDefaultAppDomain->Load_2(bstrAssemblyName, &spAssembly); 
if (FAILED(hr)) 
{ 
    wprintf(L"Failed to load the assembly w/hr 0x%08lx\n", hr); 
    goto Cleanup; 
} 

通过以下使用此方法的行代替:_AppDomain.Load Method (Byte[])

// let's suppose I have a LPBYTE (pointer to byte array) and an ULONG (int32) value
// that describe the buffer that contains an assembly bytes.
LPBYTE buffer = <my buffer>;
ULONG size = <my buffer size>;

// let's create an OLEAUT's SAFEARRAY of BYTEs and copy the buffer into it
// TODO: add some error checking here (mostly for out of memory errors)
SAFEARRAYBOUND bounds = { size, 0 };
SAFEARRAY *psa = SafeArrayCreate(VT_UI1, 1, &bounds);
void* data;
SafeArrayAccessData(psa, &data);
CopyMemory(data, buffer, size);
SafeArrayUnaccessData(psa);

hr = spDefaultAppDomain->Load_3(psa, &spAssembly);
if (FAILED(hr))
{
    wprintf(L"Failed to load the assembly w/hr 0x%08lx\n", hr);
    goto Cleanup;
}
SafeArrayDestroy(psa); // don't forget to destroy