マルチスレッド アパートメントとして初期化されたスレッドからシェル関数またはシェル インターフェイスを呼び出したり、シェル インターフェイスにアクセスしたりすると、関数またはインターフェイスの機能が損なわれたり、完全に失敗したりする可能性があります。
元のバージョン: Windows シェルとインターフェイス
元の KB 番号: 287087
原因
CoInitializeEx (COINIT_MULTITHREADED)
を呼び出すと、呼び出し元スレッドで作成されたオブジェクトの呼び出しを任意のスレッドで実行できます。 マルチスレッド アパートメントからアパートメント スレッド モデルを使用するオブジェクトにアクセスすると、COM はオブジェクトへのアクセスを同期します。 この同期を行うには、COM がオブジェクトの呼び出しをマーシャリングする必要があります。 シェルは現在、タイプ ライブラリまたはプロキシ/スタブ コードを介してオブジェクトをマーシャリングするために必要な情報を提供していないため、マルチスレッド アパートメントからシェル オブジェクトにアクセスしようとすると失敗します。
シェル関数に影響する可能性がある呼び出し
CoInitializeEx (COINIT_MULTITHREADED)
の呼び出しがシェル オブジェクトに依存する関数に与える影響の例を次に示します。
GetOpenFileName/GetSaveFileName
ユーザーは、[開く] ダイアログ ボックスと [名前を付けて保存] ダイアログ ボックスを使用して、マイ ドキュメントなどの名前空間拡張フォルダーに移動できます。 ただし、ブラウザーで必要なインターフェイス (
IShellFolder
など) を作成できないため、これらのフォルダーを参照できません。ShellExecute/ShellExecuteEx
ShellExecute
フックは、ShellExecute
インターフェイスを実装することによって、ShellExecuteEx
またはIShellExecuteHook
の機能を拡張するために記述できます。ShellExecute
またはShellExecuteEx
が呼び出されると、登録済みのShellExecute
フックを読み込めません。
どちらの例でも、 CoCreateInstance
、 IUnknown::QueryInterface
などを使用してシェル オブジェクトへのインターフェイス ポインターを取得しようとしているコンポーネントは、通常、マルチスレッド アパートメントから呼び出されたときにエラー E_NOINTERFACE
で失敗します。 上記のように、要求されるオブジェクトの型情報やプロキシ/スタブ コードがないためです。