モジュール java.base
パッケージ java.lang.foreign

インタフェースSymbolLookup

関数型インタフェース:
これは関数型インタフェースなので、ラムダ式またはメソッド参照の代入先として使用できます。

@FunctionalInterface public interface SymbolLookup
「シンボル・ルックアップ」は、1つ以上のライブラリ内のシンボルのアドレスを取得します。 シンボルは、関数やグローバル変数などの名前付きエンティティです。

シンボル・ルックアップは、特定のライブラリ (またはライブラリ)に対して作成されます。 その後、find(String)メソッドはシンボルの名前を取得し、そのライブラリ内のシンボルのアドレスを返します。

シンボルのアドレスは、長さゼロの「メモリー・セグメント」としてモデル化されます。 セグメントは次の様々な方法で使用できます:

  • Linkerに渡してダウンコール・メソッド・ハンドルを作成でき、これを使用してセグメントのアドレスで外部ファンクションをコールできます。
  • これは、基礎となる外部関数の引数として、既存のdowncall method handleRESTRICTEDに渡すことができます。
  • 別のメモリー・セグメント内で「保管済み」にできます。
  • グローバル変数(この場合は、最初にセグメントresizingRESTRICTEDが必要です)をバッキングするメモリー・リージョンにアクセスするために使用できます。

シンボル・ルックアップの取得

ファクトリ・メソッドlibraryLookup(String, Arena)RESTRICTEDおよびlibraryLookup(Path, Arena)RESTRICTEDは、オペレーティング・システムで認識されるライブラリのシンボル・ルックアップを作成します。 ライブラリは、その名前またはパスで指定されます。 ライブラリがまだロードされていない場合はロードされます。 シンボル・ルックアップ(「ライブラリ・ルックアップ」と呼ばれ、その存続期間は「アリーナ」によって制御されます)。 たとえば、指定されたアリーナが限定されたアリーナである場合、限定されたアリーナがclosedのときに、シンボル・ルックアップに関連付けられたライブラリがアンロードされます。
 try (Arena arena = Arena.ofConfined()) {
     SymbolLookup libGL = SymbolLookup.libraryLookup("libGL.so", arena); // libGL.so loaded here
     MemorySegment glGetString = libGL.find("glGetString").orElseThrow();
     ...
 } //  libGL.so unloaded here

以前にSystem.load(String)またはSystem.loadLibrary(String)によってJNI、i.eを介してライブラリがロードされていた場合、ライブラリは特定のクラス・ローダーにも関連付けられていました。 ファクトリ・メソッドloaderLookup()は、コール元クラス・ローダーに関連付けられたすべてのライブラリのシンボル・ルックアップを作成します:

System.loadLibrary("GL"); // libGL.so loaded here
...
SymbolLookup libGL = SymbolLookup.loaderLookup();
MemorySegment glGetString = libGL.find("glGetString").orElseThrow();
このシンボル・ルックアップは「ローダー・ルックアップ」と呼ばれ、クラス・ローダーに関連付けられたライブラリに関して動的です。 その後、他のライブラリがJNIを介してロードされ、クラス・ローダーに関連付けられている場合、ローダー・ルック・アッ・ルックアッププではそのシンボルが自動的に公開されます。

ローダー・ルックアップでは、System.load(String)またはSystem.loadLibrary(String)によって以前にJNI、i.eを介してロードされたライブラリ内の記号のみが公開されることに注意してください。 ローダー・ルックアップでは、ライブラリ・ルックアップの作成中にロードされたライブラリ内のシンボルは公開されません:

 libraryLookup("libGL.so", arena).find("glGetString").isPresent(); // true
 loaderLookup().find("glGetString").isPresent(); // false
ライブラリLのライブラリ・ルックアップでは、Lが以前にJNI (クラス・ローダーとの関連付けはライブラリ・ルックアップにとって重要ではありません)を介してロードされている場合でも、Lのシンボルが公開されることにも注意してください:
 System.loadLibrary("GL"); // libGL.so loaded here
 libraryLookup("libGL.so", arena).find("glGetString").isPresent(); // true

最後に、各Linkerは、そのLinkerでサポートされているOSとプロセッサの組合せで一般的に使用されるライブラリのシンボル・ルックアップを提供します。 このシンボル・ルックアップは「デフォルト・ルックアップ」と呼ばれ、クライアントが既知のシンボルのアドレスをすばやく検索するのに役立ちます。 たとえば、Linux/x64のLinkerは、デフォルトのルックアップを介してlibcのシンボルを公開することを選択できます。

 Linker nativeLinker = Linker.nativeLinker();
 SymbolLookup stdlib = nativeLinker.defaultLookup();
 MemorySegment malloc = stdlib.find("malloc").orElseThrow();

導入されたバージョン:
22