1. ホーム
  2. java

JNIによるCとJavaの間のポインタの受け渡し

2023-08-27 22:16:47

質問

現在、私は CUDA 機能を使用する Java アプリケーションを作成しようとしています。CUDA と Java の間の接続はうまくいきますが、別の問題があり、それについて私の考えが正しいかどうか、尋ねたいと思いました。

Java からネイティブ関数を呼び出すとき、いくつかのデータを渡し、関数は何かを計算し、結果を返します。最初の関数がこの結果への参照 (ポインター) を返すようにして、それを JNI に渡して、その結果でさらに計算する別の関数を呼び出すことは可能でしょうか。

私のアイデアは、データをGPUメモリに残し、他の関数がそれを使用できるようにそれへの参照を渡すことによって、GPUとの間でデータをコピーすることから生じるオーバーヘッドを減らすことでした。

しばらく試した後、私は自分自身で考えました。ポインターはアプリケーションが終了した後(この場合、C関数が終了したとき)削除されるため、これは可能ではないはずです。これは正しいのでしょうか?それとも、解決策を見るには、私が C 言語に不得手なだけでしょうか?

編集します。 さて、質問を少し拡大するために(またはより明確にするために)。JNI ネイティブ関数によって割り当てられたメモリは、関数が終了したときに解放されるのでしょうか? それとも、JNI アプリケーションが終了するか、または手動で解放するまで、まだアクセスできるのでしょうか?

あなたの意見に感謝します :)

どのように解決するのですか?

次のような方法をとりました。

JNIコードで、必要なオブジェクトへの参照を保持する構造体を作成します。この構造体を最初に作成するとき、そのポインタをJavaに long . そして、javaから任意のメソッドを呼び出すには、この long をパラメータとして任意のメソッドを呼び出し、C言語ではこれを構造体へのポインタにキャストします。

構造体はヒープにあるので、異なるJNI呼び出しの間でクリアされることはないでしょう。

EDIT: long ptr = を使うことはできないと思います。 (long)&address; アドレスはスタティック変数なので Gunslinger47が提案した方法、つまりクラスや構造体の新しいインスタンスを(newやmallocを使って)作り、そのポインタを渡すという方法で使ってください。