Java SEバージョン1.4で導入された
JNIの拡張機能

JNIバージョン1.4では、JNI呼出しインタフェースの新しいエントリ・ポイントのほか、java.nioパッケージのサポートが追加されました。また、JNIバージョン番号が上がったことに伴ってJNI_OnLoadの解説が更新されました。

新しい呼出しインタフェース・ルーチンによって、ネイティブ・コードがJava仮想マシン(JVM)にデーモン・スレッドを接続できます。これは、このスレッドがシャットダウン時に終了するのをJVMが待つべきではない場合に便利です。

NIO関連のエントリ・ポイントにより、ネイティブ・コードがjava.nio 直接バッファにアクセスできます。直接バッファのコンテンツは、通常のガベージ・コレクトされたヒープの外側の、ネイティブ・メモリー内に格納できます。直接バッファについては、New I/O APIおよびjava.nio.ByteBufferクラスの仕様を参照してください。

3つの新しい関数によって、直接バッファをJNIコードで作成、検査、および操作できます。

Java仮想マシンの各実装ではこれらの関数をサポートする必要がありますが、すべての実装が直接バッファへのJNIのアクセスをサポートする必要はありません。JVMがこのようなアクセスをサポートしない場合は、NewDirectByteBufferおよびGetDirectBufferAddress関数は常にNULLを返し、GetDirectBufferCapacity関数は常に-1を返します。JVMがこのようなアクセスをサポートする場合、これら3つの関数は適切な値を返すように実装される必要があります。


バージョン番号の増加

JNIのバージョン番号が上がりました。インクルード・ファイルjni.hでは、新しい定数を定義しています。

    #define JNI_VERSION_1_4 0x00010004

GetVersionプロシージャは現在この値を返し、JNI_OnLoadプロシージャの仕様が改訂されています。

    jint JNI_OnLoad(JavaVM *vm, void *reserved);

      The VM calls JNI_OnLoad when the native library is loaded (for example,
      through System.loadLibrary).  JNI_OnLoad must return the JNI version
      needed by the native library.

      In order to use the JNI functions introduced in Java SE release 1.2 in
      addition to those that were available in JDK 1.1, a native library must
      export a JNI_OnLoad function that returns JNI_VERSION_1_2.

      In order to use the JNI functions introduced in Java SE release 1.4 in
      addition to those that were available in release 1.2, a native library
      must export a JNI_OnLoad function that returns JNI_VERSION_1_4.

      If the native library does not export a JNI_OnLoad function, the VM
      assumes that the library only requires JNI version JNI_VERSION_1_1.  If
      the VM does not recognize the version number returned by JNI_OnLoad, the
      native library cannot be loaded.

JNI呼出しインタフェースへの追加

AttachCurrentThreadAsDaemon

jint AttachCurrentThreadAsDaemon(JavaVM* vm, void** penv, void* args);

AttachCurrentThreadとセマンティックスは同じですが、新しく作成されたjava.lang.Threadインスタンスはデーモンです。

スレッドがすでにAttachCurrentThreadまたはAttachCurrentThreadAsDaemonを介して接続されている場合、このルーチンは、penvが指している値を現在のスレッドのJNIEnvに設定します。この場合、AttachCurrentThreadもこのルーチンも、スレッドのデーモン・ステータスに影響しません。

リンケージ

JavaVMインタフェース関数表のインデックス7。

パラメータ

vm: 現在のスレッドが接続される仮想マシン・インスタンス。

penv: 現在のスレッドのJNIEnvインタフェース・ポインタが配置される位置へのポインタ。

args: JavaVMAttachArgs構造体へのポインタ。

戻り値

成功した場合は0、失敗した場合は負の数を返します。

例外

なし。


JNIインタフェースへの追加

NewDirectByteBuffer

jobject NewDirectByteBuffer(JNIEnv* env, void* address, jlong capacity);

メモリー・アドレスaddressから始まるcapacityバイトまでのメモリー・ブロックを参照する直接バッファjava.nio.ByteBufferを割り当てて返します。

この関数を呼び出して、Javaレベルのコードに最終的なバイト・バッファのオブジェクトを返すネイティブ・コードは、そのバッファが、読み込みと、適切な場合には書出しのアクセスが可能な、有効なメモリー領域を参照する必要があります。Javaコードから無効なメモリー位置にアクセスしようとすると、視覚効果のない任意の値を返すか、指定されていない例外が発生します。

リンケージ

JNIEnvインタフェース関数表のインデックス229。

パラメータ

env: JNIEnvインタフェース・ポインタ

address: メモリー領域の開始アドレス(NULLは不可)

capacity: メモリー領域のバイト数で示したサイズ(正の数であること)

戻り値

新規にインスタンス化されたjava.nio.ByteBufferオブジェクトのローカル参照を返します。例外が発生したり、この仮想マシンが、直接バッファへのJNIのアクセスをサポートしていない場合は、NULLを返します。

例外

OutOfMemoryError: ByteBufferオブジェクトの割当てに失敗した場合


GetDirectBufferAddress

void* GetDirectBufferAddress(JNIEnv* env, jobject buf);

指定された直接バッファjava.nio.Bufferによって参照されるメモリー領域の開始アドレスをフェッチし、返します。

この関数によって、ネイティブ・コードは、Javaコードがバッファ・オブジェクトを介してアクセスできるメモリー領域と同じメモリー領域にアクセスできるようになります。

リンケージ

JNIEnvインタフェース関数表のインデックス230。

パラメータ

env: JNIEnvインタフェース・ポインタ

buf: 直接バッファjava.nio.Bufferオブジェクト(NULLは不可)

戻り値

バッファに参照されるメモリー領域の開始アドレスを返します。メモリー領域が未定義の場合、指定されたオブジェクトが直接バッファjava.nio.Bufferでない場合、または、直接バッファへのJNIのアクセスがこの仮想マシンでサポートされていない場合は、NULLを返します。


GetDirectBufferCapacity

jlong GetDirectBufferCapacity(JNIEnv* env, jobject buf);

指定された直接バッファjava.nio.Bufferによって参照されるメモリー領域のバイト数で示したサイズをフェッチし、返します。

リンケージ

JNIEnvインタフェース関数表のインデックス231。

パラメータ

env: JNIEnvインタフェース・ポインタ

buf: 直接バッファjava.nio.Bufferオブジェクト(NULLは不可)

戻り値

バッファに関連付けられたメモリー領域のサイズをバイト数で返します。指定されたオブジェクトが直接バッファjava.nio.Bufferでない場合、または、直接バッファへのJNIのアクセスがこの仮想マシンでサポートされていない場合は、-1を返します。


Copyright © 1993, 2020, Oracle and/or its affiliates. All rights reserved.