問題タブ [regfreecom]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
vb.net - リリース フォルダーにマニフェスト ファイルを強制的に作成するにはどうすればよいですか?
これは私を夢中にさせています。アプリケーションの一部のレガシー関数を更新および置換するために、VB6 DLL ラッパーで使用される .NET COM DLL を開発しました。
私は現在、クライアント マシンで regasm を使用する要件を取り除こうとしているので、すべて正常に動作するテスト DLL でそれを行う方法を考え出しました。
念のため DLL を分岐し、app.manifest ファイルを追加しました。他のすべてはうまくいき、すべてうまくいきました。マニフェストが埋め込まれ、Visual Studio 2012 がリリース フォルダーに mydll.dll.manifest ファイルを生成します。
次に、元のトランクに戻り、app.manifest ファイルを追加しました (コードの変更がないため、マージしても意味がありません)。ブランチの内容を app.manifest ファイルにコピーし、リリース バージョンをビルドしました。マニフェストは DLL に埋め込まれていますが、mydll.dll.manifest ファイルは生成されません。
mydll.dll.manifest ファイルが必ずしも必要ではないことはわかっていますが、一貫性を持たせたい (そして、何らかの理由でテスト プロセスがトランク バージョンと同じ結果を生成しない) ため、どうすれば強制できますか?それは作成されますか?
これは VB.NET DLL プロジェクトであるため、最初の回答 hereに記載されている「マニフェストの生成」プロパティのドロップダウンがありません (または見つかりません) 。どうすればこれを設定できますか? または、プロジェクトファイルを直接編集して設定する方法はありますか?
参考文献:
- 元のチュートリアル記事といくつかの修正。
- Junfeng Zhang による2 つの記事と便利なツールによる概要
visual-studio-2010 - アンマネージ C++ regfree COM アプリケーション: パスに親ディレクトリがある IDE から起動するときの問題 (VS2010)
アプリケーション A と DLL B があり、どちらも VS2010 に組み込まれたアンマネージ C++ です。DLL B は COM サーバーです。A は、いくつかのメソッドとクラスに対して B への暗黙的な C++ リンケージを使用しますが、B に実装されているコクラスにも COM 経由でアクセスしています。登録済みの COM を使用している場合、これはすべて正常に機能しますが、A が登録なしの COM を介して B を使用している場合、奇妙な問題が発生します。
IDE 内から A を起動すると (F5 または Ctrl+F5)、B で実装されたコクラスを共同作成しようとすると、アプリケーションがクラッシュします。また、これをデバッグしようとすると、Visual Studio Debugger が単にコマンドを無視する場合があることにも気付きました。メソッドにステップインします。ソース コードと実際に実行しているものは、何らかの形で同期していないようです。
その後、最終的に問題の原因を突き止めました。アプリケーション A のデバッグ設定で、コマンドが $(TargetPath) に設定されています。$(TargetPath) は、"$(ProjectDir)..\bin\" に設定されたプロジェクトの出力ディレクトリを使用します。出力ディレクトリを「..」親ディレクトリ構文を含まない絶対パスに変更すると、指しているディレクトリがまったく同じであったとしても、問題は解決しました。
そこで何が起こっているのか説明できる人はいますか?私のアプリケーションが起動時に暗黙的な C++ リンケージを介して B.dll をロードし、登録不要の COM のマニフェストに依存アセンブリとしてリストするという事実と関係があるという漠然とした考えがあります。これにより、B dll が何らかの形で 2 回読み込まれる可能性がありますか? また、IDE 内から A を起動したときにのみこれが発生するのはなぜですか? コマンド ラインから A を起動する場合、パスに「..」を使用すると問題なく動作します。
windows-7 - VB6 IDE から Comwrapped Net コードを呼び出すと、Win7 では「ActiveX コンポーネントがオブジェクトを作成できません」で失敗するが、WinXP では失敗する
RegFree Com を 1 年以上使用して、ハイブリッド VB6/VB.Net プログラムの作成に成功しています。Net 4.5 でいくつかのコンポーネントを開発したいので、最初に WinXP から開発した Win7 から VB6 IDE の使用を開始する必要があります。
問題は、WinXP の VB6 IDE とまったく同じ RegFree Com 構成が Win7 では機能しないことです (コンパイルされた実行可能ファイルのインストールは問題なく機能します)。一般的な「ActiveX コンポーネントはオブジェクトを作成できません」というエラーが発生します。Fuslogvw.exe と SxSTrace.exe を使用し、Windows ログを調べましたが、オブジェクトのインスタンス化が失敗した理由を説明するエラー メッセージは表示されません。
では、この問題の原因を見つけるために、さらに何ができるでしょうか?
com - Windows でプロセスを開始するときに使用するマニフェストを選択することはできますか?
私が制御できない実行可能ファイルのオブジェクトの代わりとして使用できる COM オブジェクトを提供しようとしています。すべて同じインターフェイスを使用して、この COM オブジェクトの実装を作成しました。この置換をたまにしか使用できないようにしたいので、その登録で元のオブジェクトを置換したくありません。
実行可能ファイルのマニフェストを変更して、レジストリを介してオリジナルを見つけるのではなく、dll を調べて com オブジェクトを見つけることにより、reg-free COM を使用してオリジナルの代わりに COM オブジェクトをロードするように実行可能ファイルを取得できます。
ここまでは順調ですね。ただし、これを行うには、実行可能ファイルのマニフェスト ファイルを変更する必要があります。この変更を永続的なものにしたくありません。通常、実行可能ファイルは「プログラム ファイル」にインストールされるため、このファイルを変更するには管理者権限も必要です。
理想的には、元の実行可能ファイルを変更せずにそのままにしておくことです。次に、必要に応じて、作成した別のランチャー プログラムが、実行可能ファイルの元のマニフェスト ファイルではなく、com オブジェクトにリダイレクトするマニフェストを使用して、要求された実行可能ファイルをロードします。
このようなことは可能ですか?それとも、私がやろうとしていることを行うためのより良い方法ですか?
注: この実行可能ファイルのすべての依存関係がどのようなものになるか事前にわからないため、書き込みアクセス権のある場所で変更されたマニフェストを使用して、実行可能ファイルの複製コピーを作成することはおそらくできません (この実行可能ファイルの dll が必要になる場合があります)。同じディレクトリ、またはサブディレクトリのデータ ファイル)。変更された実行可能ファイルの作業ディレクトリを元の実行可能ファイルのディレクトリに設定することはできますが、実行可能ファイルがそのファイルの場所に基づいて何かを行うと、壊れてしまいます。
manifest - 埋め込みマニフェストが使用されないようにするにはどうすればよいですか?
私は RegFree COM Activation を使用する多くのアプリに取り組んでいますが、アプリケーションの 1 つが JIT タイプのコンパイラを使用する古いテクノロジを使用して実行されていることを除いて、すべて正常に動作します。
RegFree COM を機能させるには、起動中の実行可能ファイルにマニフェストを提供し、依存関係を一覧表示する必要があります (間違っている場合は訂正してください)。私の他のすべてのアプリケーションは社内で構築されており、マニフェストを完全に制御できます (オーサリングと、埋め込む場合、サイド バイ サイドのままにしておく場合など)。しかし、この JIT コンパイラ (ala Java JRE) は私のものではなく、すでにマニフェストが含まれています (埋め込まれています)。
マニフェストを抽出し (MT を -inputresource および -outfile と共に使用)、変更して再埋め込みしました。期待どおりに動作します。しかし、この実行ファイルに対する所有権がないため、このような操作 (サード パーティの実行ファイルを変更して再配布する!) の合法性が心配であり、そのようなことは避けたいと考えています。また、ある時点でこの実行可能ファイルがサードパーティによって署名されている可能性があるため、埋め込まれたマニフェストを変更すると署名が壊れる可能性があるのではないかと心配しています.
最初に sxs-loader に別のマニフェストを探す方法はありますか? 埋め込まれているものが見つかった場合、デフォルトでそれを取得するようです (ほとんどの場合はこれで問題ありません)。埋め込みマニフェストをスキップして、サイド バイ サイドで提供されたもの (myExe.exe 内の RT_MANIFEST リソースの代わりに myExe.exe.manifest) を使用する構成ファイルまたは何かを提供できますか?
manifest - メインの実行可能ファイル以外のアイテムへの依存関係のマニフェスト?
最初に何をしようとしているのか (およびその理由) を説明し、次に詳細を説明します。
JIT でコンパイルされた言語のコンテキストで、Registration Free COM アクティベーションを機能させようとしています。Reg-Fre COM を使用しているのは、COM コンポーネントを登録する必要がないようにし、このアプリケーションを管理者権限なしでインストールできるようにしたいからです。
JIT コンパイラはメインの実行可能ファイルであり、署名されており、マニフェストが埋め込まれています。Windows の最新バージョンでは、既定で外部マニフェストよりも埋め込みマニフェストが優先されます (Windows XP では逆でした)。JIT は署名されているため、署名を壊さずにマニフェストを抽出/変更/更新することはできません。また、これにより、アプリケーションのメンテナンスが複雑になります (常に新しいマニフェストを埋め込む必要があります)。また、私が権利を所有していないプログラムを変更することの法的影響もあります。
したがって、私の考えは、依存関係をリストするマニフェストを提供する Win32 ラッパー ライブラリを介して WinSxS アクティベーションを実行しようとすることでした。概念実証として、単純な VB6 アプリ、C++ ラッパー ライブラリ、および 2 つの COM ライブラリ (.NET に 1 つ、VB6 に 1 つ) を作成することにしました。ラッパーには、VB6 COM を呼び出すメソッド、.NET COM を呼び出すメソッド、単純な文字列を返すメソッドの 3 つのメソッドが含まれています。もちろん、COM などのすべてが登録されている限り、動作します。それらを登録解除し、COM のマニフェストを提供し、メインの実行可能ファイルのマニフェストに依存関係として追加すると、機能します。それらを登録解除し、COM と C++ ラッパーのマニフェストを提供し、C++ ラッパーの依存関係として com を追加してから、メインの実行可能ファイルのマニフェストに唯一の依存関係として C++ ラッパーを追加すると、機能します。
すべてのテストで、すべてのファイルの変更日を変更する Powershell スクリプトを実行し、アクティベーション コンテキスト キャッシュ (マニフェスト) を確実にトリップすることに注意してください。
そこから、SXSTrace.exe を使用してデバッグを開始し、COMPlus_LoadLogDir 変数を設定しました。私のマニフェストが外部にある場合、それは決して考慮されないことがわかりました。また、それを .DLL に埋め込むと、sxstrace はそれが検出され、解析され、依存関係が検出され、それらのマニフェストが検出され、ログに通常の成功したコンテキスト アクティベーション行が表示されることもわかりました。
ただし、ログに記載されていても、COM 呼び出しはまだ成功していません。呼び出しが .NET COM 呼び出しを通過すると、COMPlus_CLRLoadLogDir 構成パスで出力が得られます。
この場合、出力は得られません。
メインの実行可能ファイルへの依存関係として C++ ラッパーのみをリストするマニフェストを追加するとすぐに、すべてが再び機能し始めます。SXSTrace から同様の出力が得られますが、COM 呼び出しが機能するようになりました。前述のように、すべての場合において、C++ ラッパーの単純な文字列メソッドが機能します。つまり、メインの実行可能ファイルからマニフェストがなくても、.dll を見つけて呼び出すことができます。完全なマニフェスト チェーンがない場合、COM が機能しないようです: Application.Manifest > Wrapper.Manifest > COM マニフェスト
だから、ここで2つのこと... 1.私がやろうとしていることは可能ですか? (メインの実行可能ファイルのマニフェストには触れずに、自分に属する DLL のマニフェストにのみ依存関係をリストする) :)
誰かが em で何かを試すことに興味がある場合は、すべてのコード/実行可能ファイルを例として提供できます。
c++ - 登録不要の COM のマニフェストで必要なタグはどれですか?
TL;DRによって生成されたすべてのレジストリ エントリregsvr32
は、SxS reg-free-COM マニフェストに存在する必要がありますか? またその逆も同様ですか?
サードパーティ コンポーネント用に登録不要の COM を取得しようとしています。
この件について読んでみると、マニフェストに入れることができるいくつかの要素が言及されていることがわかりました。
docs から、次のタグをマニフェストに追加して、COM コンポーネントを記述することができます。
assemblyIdentity
-私が知る限り、これは本当に「抽象的なアセンブリ」を説明しているだけですcomClass
- COM クラス (IID インターフェイス) について説明します。どうやら、これは常に必要です。typelib
- いつ?comInterfaceExternalProxyStub
- いつ?comInterfaceProxyStub
- いつ?
他のドキュメントからHKEY_LOCAL_MACHINE\SOFTWARE\Classes
、COM レジストリ エントリにはいくつかのカテゴリがあることがわかります。
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\CLSID\{CLSID}
おおよそ対応すると思いますcomClass
HKEY_LOCAL_MACHINE\SOFTWARE\Classes\Interface\{IID}
どちら にも対応しますcomInterface[External]ProxyStub
が、どちら(または両方)をいつ使用するかはまったくわかりません- マニフェストエントリに対応するレジストリ エントリはどれ
typelib
ですか??
regsvr42を使用して、regfree しようとしている dll のものを抽出すると、エントリのみを含みcomClass
、typelib または ProxyStub エントリを含まないマニフェストが生成されます。(そして、書き込まれたキー、問題の DLL をクロス チェックしましたpdm.dll
。MS の Process Debug Manager はそれらのキーのみを書き込みます。つまり、レジストリにタイプ ライブラリまたはプロキシ スタブ情報はありません。)
レジストリに関連する情報のみが含まれている場合、comClass
この情報は SxS マニフェストで十分であることを意味しますか、それともマニフェストで追加情報が必要になる可能性がありますか?
余談ですが、レジストリには、末尾にバージョン番号が追加されたaVersionIndependentProgId
と aが含まれていることに気付きました。ProgId
マニフェストにはProgId
エントリのみがあり、ドキュメントには次のように記載されています。
progid : COM コンポーネントに関連付けられた、バージョンに依存するプログラム識別子。ProgID の形式は
<vendor>.<component>.<version>
.
しかし、ドキュメントにも記載されています
comClass要素は、バージョンに依存する progid をリストする要素を子として持つことができます。
<progid>...</progid>
彼らは、progid 属性はバージョンに依存しないものであるべきだと言っています。
では、ここに何を入れますか?また、クライアントが特定のバージョンを要求していない場合でも問題になるでしょうか?
winapi - Activation Context をどこで切り替える必要がありますか?
私が直面している問題は、基本的にここで説明されています。つまり、次のとおりです。
- サードパーティのインプロセス COM コンポーネント dll を使用している DLL があります。
- そのインプロセス コンポーネントで登録不要の COM を使用したい。
- この DLL (メインの EXE ではなく) にマンフェストを埋め込んで使用したいので、サードパーティのコンポーネントを reg フリーの方法で使用できます。
- コンポーネントから使用するインターフェイスは、 への呼び出しによってアクティブ化され
CoCreateInstance
ます。 - サード パーティの COM コンポーネントには、それ以上の (COM) 依存関係がなく、分離に依存したり、分離を必要としたりしません。
リンクされた質問で説明されているように、マニフェストを DLL に埋め込むだけでは機能しないことがわかります。アクティベーション コンテキストを手動で切り替える必要があります。
私が理解していないのは、いつどこでアクティベーション コンテキストを切り替える必要があるかということです: への呼び出しを(*) のCoCreateInstance
ようなものでラップするだけでよいですか、それともすべての呼び出しをサード パーティ コンポーネントにラップする必要がありますか? (私が理解している限り、それは助けになるはずです。)CActCtxActivator ScopedContext
ISOLATION_AWARE_ENABLED
では、登録不要の COM を使用する場合、どこでActivation Contextを切り替える必要があるのでしょうか?
(*) :または(**) または何でも。AFX_MANAGE_STATE(AfxGetStaticModuleState());
(**): 実際には、AFX_MANAGE_STATE
以前は機能していましたが、「新しい」MFC バージョンでは機能しなくなりました。たとえば、VS2012: MFC でのアクティブ コンテキスト スイッチングのサポートを削除しましたか?を参照してください。:
MFC からアクティベーション コンテキストのサポートをすべて削除しました。これは、MFC 自体の内部で Windows 分離対応 API を使用しているためです。
// 投稿者: Pat Brenner、Visual C++ ライブラリ開発: 2013 年 6 月 5 日水曜日 11:10 PM