私はのDLLの何百もの巨大な(主に)C++/MFCアプリケーションで作業(アンマネージド)C++
[これは...申し訳ありません... TLDRを取得しています] ; COMを介して動的にロードされる「アドイン」メカニズムをサポートするため、COM相互運用機能を使用して.NETでアドインを開発することができます。この「アドイン」メカニズム(ただし、動的にロードされていますが)を使用しないで、一部の新機能が.NETで開発されました。ただし、エンドユーザーはこの機能を使用しないことを決定できます。したがって、起動時に.NETがロードされないことがあります。
しかし、.NET はは、私はいくつかの.NET固有initialzationを行う必要があり、ロードされたときに(特にネイティブ/非管理UIに一致するようにCurrentUICultureのを設定)。
解決策の1つは、コードが新しい.NET機能またはCOMアドインのいずれかを読み込むようになったときに、この.NET初期化を単純に行い、実行することです。このアプリケーションの性質を考えると、おそらく95 +%のソリューションです(ほとんどのユーザーは新しい機能を使用します)。
しかし、それは絶対確実ではありません。 /clrフラグ(これは巨大なアプリケーションであることを覚えておいてください)を持つモジュールを構築することで、いつでも新しい.NET機能を簡単に追加できます。
もうひとつの堅牢な(明らかな)解決策は、C++/CLIを使って起動時に.NETをロードすることです。しかし、すべてのバイトとクロックのサイクルが関係しているダイハードのC++開発者の中には、これをしたくないものもあります。 CurrentUICultureを設定する必要がないため、.NETがロードされていない限り、若干理解できます。
私が考えた別の可能性は、LoadLibrary
をフックしてmscorlibを探すことです。今私は.NETが何らかの理由でロードされようとしていることを知り、通常の方法でロードし、他のコードが何もしないうちに初期化を行います。しかし、フックLoadLibrary
(またはそれに関しては他のもの)は本当に私がやりたいことではありません。
.NETの読み込みを容易にする方法はありますか?
編集:LockClrVersionのリードの答えはかなりくそ近くにあります。唯一の問題は、混在モードのDLL /アセンブリでリンクするとうまくいかないことです。
// ClrAboutToLoad.cpp : Defines the entry point for the console application.
//
#include "stdafx.h"
#include <MSCorEE.h>
// http://community.bartdesmet.net/blogs/bart/archive/2005/07/22/2882.aspx
FLockClrVersionCallback begin_init, end_init;
STDAPI hostCallback()
{
printf("hostCallback()\n");
// we're in control; notify the shim to grant us the exclusive initialization right
begin_init();
ICLRRuntimeHost *pHost = NULL;
HRESULT hr = CorBindToRuntimeEx(NULL, L"wks", STARTUP_SERVER_GC, CLSID_CLRRuntimeHost, IID_ICLRRuntimeHost, (PVOID*) &pHost);
hr = pHost->Start();
// mission completed; tell the shim we're ready
end_init();
return S_OK;
}
int _tmain(int argc, _TCHAR* argv[])
{
LockClrVersion(&hostCallback, &begin_init, &end_init);
//fnTheDLL();
HMODULE hModule = LoadLibrary(L"TheDLL");
FARPROC fp = GetProcAddress(hModule, "fnTheDLL");
typedef void (*fnTheDLL_t)();
fnTheDLL_t fnTheDLL = reinterpret_cast<fnTheDLL_t>(fp);
fnTheDLL();
FreeLibrary(hModule);
return 0;
}
これは有望そうです! –
これはあなたが何をしているのか正確にする必要があります。私は今まで実装していませんでしたが、CLRホスティングAPI全体を追跡して追跡しました。 –
これはほぼ完璧です。唯一のヒッチは、* LockClrVersion *を呼び出す前に何もCLRがロードされないことを確認する必要があることです。 "問題"は、混合モードアセンブリでリンクするとCLRが読み込まれるため、アセンブリを動的にロードする必要があります。 –