diff --git a/src/main/java/org/bytedeco/javacpp/Pointer.java b/src/main/java/org/bytedeco/javacpp/Pointer.java index c15a9e184..94d3fa94b 100644 --- a/src/main/java/org/bytedeco/javacpp/Pointer.java +++ b/src/main/java/org/bytedeco/javacpp/Pointer.java @@ -33,6 +33,7 @@ import java.util.Iterator; import java.util.concurrent.atomic.AtomicInteger; import org.bytedeco.javacpp.annotation.Name; +import org.bytedeco.javacpp.annotation.Raw; import org.bytedeco.javacpp.tools.Generator; import org.bytedeco.javacpp.tools.Logger; @@ -589,6 +590,10 @@ public static long maxPhysicalBytes() { /** Returns the amount of physical memory that is free according to the operating system, or 0 if unknown. */ @Name("JavaCPP_availablePhysicalBytes") public static native long availablePhysicalBytes(); + /** Returns the starting address of the memory region referenced by the given direct {@link java.nio.Buffer}. + * An alternative to allocating a new Pointer object if all you need is the memory address. */ + @Name("JavaCPP_getDirectBufferAddress") protected static native long getDirectBufferAddress(@Raw(withEnv = true) Buffer b); + /** The native address of this Pointer, which can be an array. */ protected long address = 0; /** The index of the element of a native array that should be accessed. */ diff --git a/src/main/java/org/bytedeco/javacpp/tools/Generator.java b/src/main/java/org/bytedeco/javacpp/tools/Generator.java index a20c471f0..2725dfeeb 100644 --- a/src/main/java/org/bytedeco/javacpp/tools/Generator.java +++ b/src/main/java/org/bytedeco/javacpp/tools/Generator.java @@ -664,6 +664,10 @@ boolean classes(boolean handleExceptions, boolean defineAdapters, boolean conver out.println(" return size;"); out.println("}"); out.println(); + out.println("static inline jlong JavaCPP_getDirectBufferAddress(JNIEnv *env, jclass cls, jobject obj) {"); + out.println(" return (jlong)env->GetDirectBufferAddress(obj);"); + out.println("}"); + out.println(); out.println("static inline jint JavaCPP_totalProcessors() {"); out.println(" jint total = 0;"); out.println("#ifdef __linux__"); diff --git a/src/test/java/org/bytedeco/javacpp/BufferTest.java b/src/test/java/org/bytedeco/javacpp/BufferTest.java index d993b9d2e..7f1bd270d 100644 --- a/src/test/java/org/bytedeco/javacpp/BufferTest.java +++ b/src/test/java/org/bytedeco/javacpp/BufferTest.java @@ -101,6 +101,7 @@ public ByteBuffer call(ByteBuffer buffer) { BytePointer pointer = new BytePointer(arrayBuffer); ByteBuffer directBuffer = pointer.asBuffer(); assertEquals(pointer.address(), new BytePointer(directBuffer).address()); + assertEquals(pointer.address(), Pointer.getDirectBufferAddress(directBuffer)); assertTrue(directBuffer.compareTo(arrayBuffer) == 0); assertEquals(arrayBuffer.position(), directBuffer.position()); @@ -123,6 +124,7 @@ public ByteBuffer call(ByteBuffer buffer) { ShortPointer pointer = new ShortPointer(arrayBuffer); ShortBuffer directBuffer = pointer.asBuffer(); assertEquals(pointer.address() + pointer.position() * pointer.sizeof(), new ShortPointer(directBuffer).address()); + assertEquals(pointer.address() + pointer.position() * pointer.sizeof(), Pointer.getDirectBufferAddress(directBuffer)); assertTrue(directBuffer.compareTo(arrayBuffer) == 0); assertEquals(arrayBuffer.limit() - arrayBuffer.position(), directBuffer.limit()); @@ -144,6 +146,7 @@ public ByteBuffer call(ByteBuffer buffer) { IntPointer pointer = new IntPointer(arrayBuffer); IntBuffer directBuffer = pointer.asBuffer(); assertEquals(pointer.address() + pointer.position() * pointer.sizeof(), new IntPointer(directBuffer).address()); + assertEquals(pointer.address() + pointer.position() * pointer.sizeof(), Pointer.getDirectBufferAddress(directBuffer)); assertTrue(directBuffer.compareTo(arrayBuffer) == 0); assertEquals(arrayBuffer.limit() - arrayBuffer.position(), directBuffer.limit()); @@ -165,6 +168,7 @@ public ByteBuffer call(ByteBuffer buffer) { LongPointer pointer = new LongPointer(arrayBuffer); LongBuffer directBuffer = pointer.asBuffer(); assertEquals(pointer.address() + pointer.position() * pointer.sizeof(), new LongPointer(directBuffer).address()); + assertEquals(pointer.address() + pointer.position() * pointer.sizeof(), Pointer.getDirectBufferAddress(directBuffer)); assertTrue(directBuffer.compareTo(arrayBuffer) == 0); assertEquals(arrayBuffer.limit() - arrayBuffer.position(), directBuffer.limit()); @@ -186,6 +190,7 @@ public ByteBuffer call(ByteBuffer buffer) { FloatPointer pointer = new FloatPointer(arrayBuffer); FloatBuffer directBuffer = pointer.asBuffer(); assertEquals(pointer.address() + pointer.position() * pointer.sizeof(), new FloatPointer(directBuffer).address()); + assertEquals(pointer.address() + pointer.position() * pointer.sizeof(), Pointer.getDirectBufferAddress(directBuffer)); assertTrue(directBuffer.compareTo(arrayBuffer) == 0); assertEquals(arrayBuffer.limit() - arrayBuffer.position(), directBuffer.limit()); @@ -207,6 +212,7 @@ public ByteBuffer call(ByteBuffer buffer) { DoublePointer pointer = new DoublePointer(arrayBuffer); DoubleBuffer directBuffer = pointer.asBuffer(); assertEquals(pointer.address() + pointer.position() * pointer.sizeof(), new DoublePointer(directBuffer).address()); + assertEquals(pointer.address() + pointer.position() * pointer.sizeof(), Pointer.getDirectBufferAddress(directBuffer)); assertTrue(directBuffer.compareTo(arrayBuffer) == 0); assertEquals(arrayBuffer.limit() - arrayBuffer.position(), directBuffer.limit());