UnsatisfiedLinkError:指定されたプロシージャが見つかりませんでした

StackOverflow https://stackoverflow.com/questions/159846

  •  03-07-2019
  •  | 
  •  

質問

Windows XPのアプレットから呼び出されるJNIコードをC ++で書いています。アプレットを正常に実行し、JNIライブラリをロードして呼び出すことができました。他のDLLの関数を呼び出すことさえできます。 PATHシステム環境変数を設定して、すべてのDLLが入っているディレクトリを含めることで、これが機能するようになりました。

したがって、問題は、新しい外部DLLを使用する別の呼び出しを追加することです。突然ライブラリをロードすると、UnsatisfiedLinkErrorがスローされます。メッセージ:「指定されたプロシージャが見つかりませんでした」。依存DLLを削除して、依存DLLが見つからないという別のメッセージを取得できるため、これは依存DLLが見つからない場合の問題ではないようです。私がオンラインで見つけたものから、このメッセージはネイティブJava関数の実装がDLLにないことを意味しているように見えますが、この余分なコードがなくても正常に動作するのは奇妙です。

誰がこれを引き起こしているのか知っていますか? UnsatisifedLinkErrorに対して「指定されたプロシージャが見つかりませんでした」というメッセージが表示されるのはどのようなものですか?

役に立ちましたか?

解決

問題を見つけました。これはすごかった。メッセージ「指定されたプロシージャが見つかりませんでした」 UnsatisfiedLinkErrorは、ルートdllまたは依存dll の関数が見つからなかったことを示します。 JNIの状況で最も可能性の高い原因は、ネイティブJNI関数が正しくエクスポートされないことです。ただし、依存DLLがロードされ、そのDLLがその親に必要な機能を欠いている場合、これは明らかに発生する可能性があります。

例として、input.dllという名前のライブラリがあります。 DLLの検索順序は、常に最初にアプリケーションディレクトリを探し、最後にPATHディレクトリを探します。以前は、input.dllと同じディレクトリから常に実行可能ファイルを実行していました。ただし、Windowsシステムディレクトリに別のinput.dllがあります(DLL検索順序の途中にあります)。したがって、これをjavaアプレットから実行するときに、上記のコードをアプレットに含めると、input.dllがロードされ、input.dllがシステムディレクトリからロードされます。コードはinput.dllに存在しない特定の関数を予期しているため(異なるDLLであるため)、ロードが失敗し、プロシージャがないことを示すエラーメッセージが表示されます。 JNI関数が誤ってエクスポートされたためではなく、誤った依存DLLがロードされ、予期される関数が含まれていなかったためです。

他のヒント

DLLがC ++を使用して構築された可能性があります(Cとは対照的に)。手順で外部を行うように注意を払わない限り、これが考えられる理由の1つです。

DLLからすべての関数をエクスポートしてみてください。リストに関数が含まれている場合は、問題ありません。

通常、他のライブラリにリンクする場合、関連する.libファイルにリンクする必要があります。必要なすべてのlibファイルを参照しているわけではないようです。リンクしていないものを確認し、そのライブラリがリンカーのリストに追加されていることを確認してください。

標準のJNI手順を使用して新しい外部DLLを作成しましたか?つまり、javahなどを使用していますか?もしそうなら、何が間違っているのか分かりません。

そうでない場合は、呼び出そうとしているプロシージャはエクスポートされていません(anjanbが述べているように)。関数をエクスポートする方法は2つあります。個別のエクスポートリストと、__ declspec(dllexport)を使用して特定の関数をマークする方法です。

C ++ DLLの変数にアクセスできませんCアプリには、DLLのトピックに関するもう少しの情報があります。

デバッグモードでc ++コードをコンパイルします。次に、DebugBreak()を挿入します。デバッグを開始するステートメント。 Javaコードを実行します。 DebugBreak()ステートメントが検出されると、デバッグボタンが付いたポップアップが表示されます。クリックして。 Dev Studioが開き、プログラムがマシンコードで実行されます。デバッガーで2回ステップオーバーすると、ソースコードをステップオーバーできるはずです。

JNIのマニュアルと例ですべてのプログラミングの問題を解決したが、それでも同じ欠落プロシージャエラーが表示される場合は、おそらくパス変数に問題がある可能性があります。以下の手順を実行して、もう一度実行します。

  1. JAVA_HOME変数をJDKフォルダーに設定してください(JREにはjniヘッダーが含まれていないため、JREではありません) 例: 環境変数設定パネルでvar:JAVA_HOME val:C:\ Program Files \ Java \ jdk1.7.0_11を定義します
  2. パス変数に%JAVA_HOME%\ bin を追加します

これらの手順を実行すると、アプリケーションはjniプロシージャ名とJNI.dllへのリンクを正しい方法で見つけることができます。そのため、この欠落したプロシージャエラーが再び発生しないことを願っています。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top