A workshop on Java's Project Panama for Newbies to learn about native access to C libraries. Labs are located: https://github.com/carldea/java-panama-workshop
2. About Me
• A Sr. Developer Advocate at Azul Systems
• Developing software for 20+ years
• Authored & Tech Reviewed Java books
• A JavaFX (fanboy) enthusiast
• Loves sharing and advocating Java based technologies
Other interests:
Graphics, UI, Game programming, GEO spatial data & map
visualizations, Custom UI controls, IoT, Smart phones, AI, and
Robotics and Boating.
Twitter: @carldea
LinkedIn: https://github.com/carldea
Email: cdea@azul.com
Carl Dea
2
8. The JACOB Project: A JAva-COM Bridge
Now you can call COM Automation from any Win32 Java VM using JNI
Copyright 1999-2004 Dan Adler
Latest Version: October 17, 2004 (V1.8)
https://danadler.com/tech-articles/jacob-2/
8
17. JEP 389: 1st Incubator
JEP 370: 1st Incubator
Foreign-Memory Access API
Vector API
JEP 338: 1st Incubator JEP 383: 2nd Incubator
JEP 393: 3rd Incubator
Foreign Linker API
Foreign Function
&
Memory Access API
JEP 412: 1st Incubator
Project Panama
JEP 419: 2nd Incubator
JEP 424: Preview
JEP 414: 2nd Incubator
17
21. Bene
fi
ts
Ease of use — Alternative to Java Native Interface (JNI) with a superior,
pure-Java
Performance — Provide performance that is comparable to, if not better than,
existing APIs such as JNI and sun.misc.Unsafe.
General Purpose — Provide ways to operate on different kinds of foreign memory
(e.g., native memory, persistent memory, and managed heap memory) and, over time, to
accommodate other platforms (e.g., 32-bit x86) and foreign functions written in languages
other than C (e.g., C++, Fortran).
Safety — Disable unsafe operations by default, allowing them only after
explicit opt-in from application developers or end users.
21
22. Ease of use — Alternative to Java Native Interface (JNI) with a superior, pure-Java
development model.
Performance — Provide performance that is comparable to, if not better than,
existing APIs such as JNI and sun.misc.Unsafe.
General Purpose — Provide ways to operate on different kinds of foreign memory
(e.g., native memory, persistent memory, and managed heap memory) and, over time, to
accommodate other platforms (e.g., 32-bit x86) and foreign functions written in languages
other than C (e.g., C++, Fortran).
Safety — Disable unsafe operations by default, allowing them only after
explicit opt-in from application developers or end users.
Bene
fi
ts
22
23. Performance — Provide performance that is comparable to, if not better than,
existing APIs such as JNI and sun.misc.Unsafe.
General Purpose — Provide ways to operate on different kinds of foreign memory
(e.g., native memory, persistent memory, and managed heap memory) and, over time, to
accommodate other platforms (e.g., 32-bit x86) and foreign functions written in languages
other than C (e.g., C++, Fortran).
Safety — Disable unsafe operations by default, allowing them only after
explicit opt-in from application developers or end users.
Bene
fi
ts
Ease of use — Alternative to Java Native Interface (JNI) with a superior, pure-Java
development model.
23
24. Performance — Provide performance that is comparable to, if not better than,
existing APIs such as JNI and sun.misc.Unsafe.
General Purpose — Provide ways to operate on different kinds of foreign memory
(e.g., native memory, persistent memory, and managed heap memory) and, over time, to
accommodate other platforms (e.g., 32-bit x86) and foreign functions written in languages
other than C (e.g., C++, Fortran).
Safety — Disable unsafe operations by default, allowing them only after
explicit opt-in from application developers or end users.
Bene
fi
ts
Ease of use — Alternative to Java Native Interface (JNI) with a superior, pure-Java
development model.
24
34. What’s a MethodHandle?
A method handle is a Java object that references a
native C function or C variable in memory and
the ability to accessed or invoked from Java code.
In the C/C++ world symbols are a unique lookup of C
functions and variables from the C linker
(java.library.path).
In layman’s (newbie) terms:
34
35. What’s a MethodHandle?
A method handle is a typed, directly executable
reference to an underlying method, constructor,
fi
eld, or
similar low-level operation, with optional
transformations of arguments or return values.These
transformations are quite general, and include such
patterns as conversion, insertion, deletion, and
substitution.
According to the Javadoc Documentation since JDK 7
35
37. Creating a MethodHandle - JDK 18+
MethodHandle class
FunctionDescriptor
describes return type from C
NativeSymbol
C symbols from library path
Note: For better performance make method handles public
fi
nal static
37
38. Is there a better way?
FILE *freopen(const char *filename, const char *mode, FILE *stream)
38
45. jextract -h
Quick Check
Option Description
------ -----------
-?, -h, --help print help
-C <String> pass through argument for clang
-I <String> specify include files path
-d <String> specify where to place generated files
--dump-includes <String> dump included symbols into specified file
--header-class-name <String> name of the header class
--include-function <String> name of function to include
--include-macro <String> name of constant macro to include
--include-struct <String> name of struct definition to include
--include-typedef <String> name of type definition to include
--include-union <String> name of union definition to include
--include-var <String> name of global variable to include
-l <String> specify a library
--source generate java sources
-t, --target-package <String> target package for specified header files
Panama’s JExtract
45
46. jextract -h
Quick Check
Option Description
------ -----------
-?, -h, --help print help
-C <String> pass through argument for clang
-I <String> specify include files path
-d <String> specify where to place generated files
--dump-includes <String> dump included symbols into specified file
--header-class-name <String> name of the header class
--include-function <String> name of function to include
--include-macro <String> name of constant macro to include
--include-struct <String> name of struct definition to include
--include-typedef <String> name of type definition to include
--include-union <String> name of union definition to include
--include-var <String> name of global variable to include
-l <String> specify a library
--source generate java sources
-t, --target-package <String> target package for specified header files
Panama’s JExtract
C headers path
ie: /usr/local/include
46
47. jextract -h
Quick Check
Option Description
------ -----------
-?, -h, --help print help
-C <String> pass through argument for clang
-I <String> specify include files path
-d <String> specify where to place generated files
--dump-includes <String> dump included symbols into specified file
--header-class-name <String> name of the header class
--include-function <String> name of function to include
--include-macro <String> name of constant macro to include
--include-struct <String> name of struct definition to include
--include-typedef <String> name of type definition to include
--include-union <String> name of union definition to include
--include-var <String> name of global variable to include
-l <String> specify a library
--source generate java sources
-t, --target-package <String> target package for specified header files
Panama’s JExtract
Generated Code
ie: ./classes
./generated/src
47
48. jextract -h
Quick Check
Option Description
------ -----------
-?, -h, --help print help
-C <String> pass through argument for clang
-I <String> specify include files path
-d <String> specify where to place generated files
--dump-includes <String> dump included symbols into specified file
--header-class-name <String> name of the header class
--include-function <String> name of function to include
--include-macro <String> name of constant macro to include
--include-struct <String> name of struct definition to include
--include-typedef <String> name of type definition to include
--include-union <String> name of union definition to include
--include-var <String> name of global variable to include
-l <String> specify a library
--source generate java sources
-t, --target-package <String> target package for specified header files
Panama’s JExtract
Library
ie: tensorflow
48
49. jextract -h
Quick Check
Option Description
------ -----------
-?, -h, --help print help
-C <String> pass through argument for clang
-I <String> specify include files path
-d <String> specify where to place generated files
--dump-includes <String> dump included symbols into specified file
--header-class-name <String> name of the header class
--include-function <String> name of function to include
--include-macro <String> name of constant macro to include
--include-struct <String> name of struct definition to include
--include-typedef <String> name of type definition to include
--include-union <String> name of union definition to include
--include-var <String> name of global variable to include
-l <String> specify a library
--source generate java sources
-t, --target-package <String> target package for specified header files
Panama’s JExtract
Generated Java Source
ie: org/unix/foo_h.java
49
50. jextract -h
Quick Check
Option Description
------ -----------
-?, -h, --help print help
-C <String> pass through argument for clang
-I <String> specify include files path
-d <String> specify where to place generated files
--dump-includes <String> dump included symbols into specified file
--header-class-name <String> name of the header class
--include-function <String> name of function to include
--include-macro <String> name of constant macro to include
--include-struct <String> name of struct definition to include
--include-typedef <String> name of type definition to include
--include-union <String> name of union definition to include
--include-var <String> name of global variable to include
-l <String> specify a library
--source generate java sources
-t, --target-package <String> target package for specified header files
Panama’s JExtract
Package namespace prefix
ie: org.unix
50
51. $ export C_INCLUDE_PATH=/usr/local/include
# or depending where the defaults are installed
$ export C_INCLUDE_PATH=/usr/include
MacOS
$ export C_INCLUDE_PATH=Applications/Xcode.app/Contents/
Developer/Platforms/MacOSX.platform/Developer/SDKs/
MacOSX.sdk/usr/include
Let’s jextract stdio.h
Windows
Linux
Create a convenient
environment variable
C_INCLUDE
51
C:MinGWinclude (If MinGW is used)
C:mysys2include (If mysys2 is used)
72. ValueLayout
To create a C primitive use CLinker’s C ValueLayouts such as
C_INT
C_DOUBLE
C_POINTER, etc.
MemorySegment
72
73. ValueLayout
To create a C primitive use CLinker’s C ValueLayouts such as
C_INT
C_DOUBLE
C_POINTER, etc. Native Allocator
73
74. ValueLayout
To create a C primitive use CLinker’s C ValueLayouts such as
C_INT
C_DOUBLE
C_POINTER, etc.
74
75. ValueLayout
To create a C primitive use CLinker’s C ValueLayouts such as
C_INT
C_DOUBLE
C_POINTER, etc.
JDK 18+ uses the
MemorySegment class’
get()/set() methods
75
87. What’s a C Pointer?
C supports the use of pointers, a type of reference that records the
address or location of an object or function in memory. Pointers can
be dereferenced to access data stored at the address pointed to, or
to invoke a pointed-to function. Pointers can be manipulated using
assignment or pointer arithmetic.
The C Programming Language book
by
Brian W. Kernighan & Dennis M. Ritchie
87
88. What’s a C Pointer?
ptr = &x x = 5
0x0DDBA11 0xCAFEBABE 0xCAFEBABE 5
Address or Location
88
89. What’s a C Pointer?
ptr = &x x = 5
0x0DDBA11 0xCAFEBABE 0xCAFEBABE 5
Storage
89
90. Obtaining a C Pointer in Panama
The reference or address of a C int variable:
90
91. How to Dereference A Pointer?
Obtain value at the address referenced by the pointer.
91
92. Dereferencing a C Pointer in Panama - JDK 18+
MemoryAddress class
92
93. What’s a C Struct?
To put it simply, this is the ancestor to C++ & Java's
concept of classes or records.
Declaring pt of type Point struct
93
94. How to Create a Struct in
Panama?
Use GroupLayout and MemoryLayout to describe a C struct.
94
95. Creating C Structs in Panama
Using MemoryLayout’s structLayout() method.
95
96. Accessing C Structs in Panama - JDK 18+
To access a MemoryLayout (C Struct) use VarHandles.
96