問題タブ [safearray]
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.
winapi - IDispatchを介してSAFEARRAYをCOMオブジェクトに渡す方法は?
文書化されたパラメータの1つが「バイトの配列」であるCOMオブジェクトのメソッドを呼び出そうとしています。実際の宣言は、表示している言語ごとのドキュメントによって異なります。
C #言語:
/li>C++言語で;
/li>VB言語:
/li>F #言語:
/li>
私が使用しているオブジェクトには、COMを使用してアクセスすることもできます。ICryptoTransformオブジェクトは、メソッドを使用していると宣言する初期バインディングインターフェイスを提供しますSAFEARRAY。
タイプライブラリから:
IDL構文を使用する
/li>Object Pascal構文の使用:
/li>
つまり、アーリーバインディングを使用する場合は、メソッドaを渡す必要がありますSAFEARRAY。私が使用している言語はSafeArrayAPIをサポートしていますが、呼び出しを簡単に実行できますか?
これがJavaのような言語の同じコードです:
そして、すべてが正常に機能します; しかし、それは私の質問ではありません。
注: COMは言語に依存しないテクノロジーであるため、これは言語に依存しない質問であるという点を理解しようとしています。しかし、ある時点で、コードをデモンストレーションする言語を実際に使用する必要があります。言語とテクノロジーを混同する人もいます。Knuthが発明した言語を知っていれば、それを使用したでしょう。
しかし、遅延バインディングはIDispatchどうですか?
COMオブジェクトにaを渡すことができることがわかったので(アーリーバインディングを使用する場合)、レイトバインディングを使用して配列を渡す問題を解決する必要があります。SAFEARRAY
注:IDispatchを介してSAFEARRAYをCOMオブジェクトに渡す方法の質問は、以外の状況で役立ちます
ICryptoTransform。
IDispatch一部の言語は、実行時にインターフェースを介してメソッドを呼び出す自動メカニズムを提供します(つまり、遅延バインディング)。実際IDispatch、遅延バインディングはVBScript用に発明されました。
また、遅延バインディングコンパイラの自動マジックが.NET4.0に追加されました。
遅延バインディングコンパイラの魔法もDelphiに存在していました。
私はたまたまDephiを使用していますが、この呼び出しは失敗します。
しかし、それは実際にはコンパイラの魔法ではありません
VBScript、C#ダイナミック、およびDelphiが行っていることは実際には魔法ではありません。彼らはただ呼んでいますIDispatch.Invoke:
混乱はこれらのパラメータを設定しています:
本当のトリックはdispParams、引数を含む構造です。
引数はバリアントになります
DISPPARAMSを介して渡される引数は、すべてバリアントです。
したがって、何が起こっても、私の「バイト配列」はバリアントになります。
Win32のAVARIANTは、以下を含む単なる結合です。
VARTYPE vt:ユニオン内のデータのタイプ。適切な組合員、例:
/li>
今まで私はタイプの変種を渡してきました:
MSDNには、 parrayユニオンをVT_ARRAY | *次のコマンドで使用する場合に実行する必要があることが記載されています。
値:
VT_ARRAY | <anything>説明:データ型の配列が渡されました。VT_EMPTYおよびVT_NULLは、VT_ARRAYと組み合わせるには無効な型です。pbyrefValのポインタは、配列記述子を指します。配列記述子は、配列の次元、サイズ、およびメモリ内の場所を記述します。
これが意味するのは、parrayメンバーを使用することです。
メンバーを構造体parrayへのポインターに設定する必要があります。SAFEARRAY
私の場合、バイトの配列は実際にはSAFEARRAYであり、バリアントに格納されています。
注:もちろん、私はこのセーフアレイを自分で作成するほど頭がおかしいわけではありません。私は
SafeArrayCreateAPI関数を使用しています。私はそれがすべて知っていることを示しているだけであり、魔法ではありません。
言い換えれば、私はバイトの配列バリアントを渡します
言い換えれば、私はすべての呼び出しとして、バリアントにラップされたバイトの配列を渡します:
でなければなりません。遅延バインディング呼び出しがエラーをスローすることを除いて:
だから私はおそらく間違っているのですか?
バイトの配列をレイトバウンド IDispatch呼び出しに渡すにはどうすればよいですか?
私の質問
IDispatchを介してSAFEARRAYをCOMオブジェクトに渡す方法は?
delphi - Delphi7 で PSafeArray を使用して COM を呼び出すとエラーが発生する
COM を使用して呼び出す必要があるプロシージャがあり、C# では次のように宣言されています。
インポートされた TypeLibrary の Delphi 宣言は次のとおりです。
整数配列を PSafeArray に変換する次のコードがあります。
そして、このコードは私のCOM関数を呼び出します
しかし、エラーが発生します:
「「ランク 0 の SafeArray がランク 1 の配列を期待するメソッドに渡されました」というメッセージを含む EOLeExeption ...」
私は何をすべきですか?
c# - IUnknownsのSAFEARRAYをインターフェイスポインターの反復可能な配列に変換/キャストします
私はC#で次のインターフェイスを使用しており、同じ名前のクラス(Iなし)を実装しています。
パブリッククラスOrder:IOrderの実装は、3つのプライベートフィールドと、必要な3つのパラメーターを持つコンストラクターです。
他の場所で、次のメソッドを使用して、COMファイルと.tlb/.tlhファイルを介してC++アンマネージコード内で作業したい結果を取得しました。
私はすでに、C#マネージコードを使用してC++アンマネージコード間で基本的な作業を行うことができました。
しかし、クラス配列は別の課題であることが証明されました...
私にとって、COMは新しく、残酷に混乱し、C ++は長い間忘れられていたことを認めます...しかし、私は両方のライブラリを開発しているので、あきらめません。C ++ DLLをプログラムとC#コード間のプロキシとして機能させたい。
明確化:私はMFCもATLも使用していません。C ++コードで#importを使用して、C#で生成されたインターフェイスとクラスポインター、およびまだ完全には理解していないその他のCOMのものを取得します。
1時間の調査の後、私はここに行って助けを求めています>。<
以下は、私が達成しようとしていることのC++コードです。
この時点で、SAFEARRAY*をIOrderPtr*などに変換するために、まだ理解していないCOMマジックが必要です。これにより、返された配列全体を反復処理して、「Order」タイプのメソッドを呼び出すことができます。
- GetQuantity()
- GetOrderType()
- GetPositionType()
したがって、最初のサイクルでは値1、2、3を取得し、2番目のサイクルでは値4、5、6を取得します。
私はC++とC#の両方のライブラリの作成者なので、このCOMのクレイジーなものをすべてスキップして、コレクション数を取得するメソッドや、特定のインデックスのプロパティの値を取得する他のメソッドを作成できます。
しかし、それは良くないようです。私が欲しいものの仕組みは簡単だと思いますが、グーグルで見つけたすべての答えは常に何かが欠けています。
c# - クラス メソッド ポインタを取得しようとしたときの E_NOINTERFACE
C++ アンマネージ コードから C# メソッドを呼び出しています。配列で返されたクラス インスタンスから値を取得する際に問題があります。
コードを少し簡略化しました
これが問題の方法です。
これは IScOrder インターフェイスです
これが ScOrder の実装です
これは、前回のリクエストで Zdeslav Vojkovic の助けを借りて作成した C++ コードです。問題はコメントに記載されています
- 私はATLもMFCも使用していません。
- C++ tlb ファイルは regasm によって生成されます。
COM の初期化と GetOrders メソッドの呼び出しはうまく機能します
Zdeslav のおかげで、注文 (パンク) 内でデバッグできることがわかりました。
それで、そこで何が起こっているのかを見るために、オーダー(パンク)に足を踏み入れました。「comip.h」に入りました
...次に、_QueryInterface(p) 実装の内部に足を踏み入れました。comip.h にもあります
ここでの問題は、返される "hr" の値が E_NOINTERFACE であることです ... これは正しくありません。
私は C++ や COM の専門家ではありません...助けてください :)
.net - SAFEARRAY で ref パラメータをマーシャリングすることは可能ですか?
これが私のC#サーバーメソッドです:
私の C++ クライアントは、このメソッドをセットアップして呼び出しています。これは正常に機能しますが、ステータス変数と出力変数が連鎖しているようには見えません。参照ではなく値で渡されているかのようです。
これが私のクライアントコードです:
「ref」パラメーターがコピーバックされるように、SAFEARRAY 引数の設定について誰かが支援できますか?
c++ - SAFEARRAY を反復処理する方法 **
C++ safearray ポインターからポインターへの反復処理を行い、その要素にアクセスする方法。
Lim Bio Liong http://social.msdn.microsoft.com/Forums/en-US/vcgeneral/thread/022dba14-9abf-4872-9f43-f4fc05bd2602によって投稿されたソリューションを複製しようとしまし たが、最も奇妙なことは、IDLメソッドシグネチャは次のようになります
それ以外の
何か案は?
前もって感謝します
c# - COM Interop によるマネージド構造の SAFEARRAY のマーシャリング
私は、ac# ライブラリからエクスポートされた構造体の配列を C++ コードに渡そうとしています。目的は、構造体の SAFEARRAY を C++ から C# に渡すことです。
私はからの指示に従いました
しかし、 GetRecordInfoFromTypeInfo の呼び出しでこのエラーが発生します
0x80028019 古い形式または無効なタイプ ライブラリです。
c++ - fstream を LPSAFEARRAY に読み込むにはどうすればよいですか?
C++ でマネージド DLL のメソッドを呼び出そうとしています。パラメータの 1 つはバイト配列で、ライブラリのインポートによって LPSAFEARRAY に変換されます。バイト配列/LPSAFEARRAY は、ファイルの内容であることを意図しています。ファイルを LPSAFEARRAY に読み込んでメソッドに渡すにはどうすればよいですか?
生成されたライブラリ ヘッダー ファイルの関数シグネチャは次のとおりです。
2 番目のパラメーターは、メソッドから戻るときに使用する必要がある別のバイト配列です。
c# - 多次元 PSafeArray からデータを取得するには?
PSafeArrayDelphiからデータを読み取る必要があります。
これPSafeArrayは、C# で開発された DLL に実装されたメソッドによって返されます。このメソッドは、2 次元の文字列配列を返しますstring[,]。PSafeArrayそのような結果を Delphi で読み取る方法は?
vb.net - SafeArrayTypeMismatchExceptionを引き起こすSAFEARRAY(Long)を返すCOMオブジェクト
私は、プラグインが提供するAPIタイプライブラリを使用して、職場で使用するプログラムのプラグインを作成します。これは、SCAPIという名前のCOMオブジェクトです。COMオブジェクトはVB6用に作成されているため、.NET用に参照を追加すると、その相互運用バージョンが作成されます。
次のコードを使用すると、ドキュメントに従ってSAFEARRAY(Long)が返されるはずですが、SafeArrayTypeMismatchExceptionがあるというエラーが表示されます。
エラーは、私が書いたものではなく、COMオブジェクトの一部であるSCAPI.PropertyBagClass.get_Value(Object Property)関数からスローされています。私が行ったすべての調査の後、これを機能させるために何をする必要があるのか理解できないようです。tlbimp.exeを使用してメソッド情報を取得しましたが、文字列を返す同じ関数oBag.Value( "Name")を使用したにもかかわらず、[out]タグが含まれていないようです。値であり、エラーをスローしません: