Permalink
Browse files

Use optimized write and read calls if memoryAddress is present. Part …

…of [#2239]
  • Loading branch information...
1 parent b49490e commit 55d0f36a61b3cf469bb62a77550e7bbb658482a6 @normanmaurer normanmaurer committed Feb 17, 2014
@@ -461,14 +461,8 @@ JNIEXPORT void JNICALL Java_io_netty_channel_epoll_Native_epollCtlDel(JNIEnv * e
}
}
-JNIEXPORT jint JNICALL Java_io_netty_channel_epoll_Native_write(JNIEnv * env, jclass clazz, jint fd, jobject jbuffer, jint pos, jint limit) {
- // TODO: We could also maybe pass the address in directly and so eliminate this call
- // not sure if this would buy us much. So some testing is needed.
- void *buffer = (*env)->GetDirectBufferAddress(env, jbuffer);
- if (buffer == NULL) {
- throwRuntimeException(env, "Unable to access address of buffer");
- return -1;
- }
+
+jint write0(JNIEnv * env, jclass clazz, jint fd, void *buffer, jint pos, jint limit) {
ssize_t res;
int err;
do {
@@ -488,14 +482,22 @@ JNIEXPORT jint JNICALL Java_io_netty_channel_epoll_Native_write(JNIEnv * env, jc
throwIOException(env, exceptionMessage("Error while write(...): ", err));
return -1;
}
- if (posFieldId == NULL) {
- (*env)->CallObjectMethod(env, jbuffer, updatePosId, pos + res);
- } else {
- (*env)->SetIntField(env, jbuffer, posFieldId, pos + res);
- }
return (jint) res;
}
+JNIEXPORT jint JNICALL Java_io_netty_channel_epoll_Native_write(JNIEnv * env, jclass clazz, jint fd, jobject jbuffer, jint pos, jint limit) {
+ void *buffer = (*env)->GetDirectBufferAddress(env, jbuffer);
+ if (buffer == NULL) {
+ throwRuntimeException(env, "Unable to access address of buffer");
+ return -1;
+ }
+ return write0(env, clazz, fd, buffer, pos, limit);
+}
+
+JNIEXPORT jint JNICALL Java_io_netty_channel_epoll_Native_writeAddress(JNIEnv * env, jclass clazz, jint fd, jlong address, jint pos, jint limit) {
+ return write0(env, clazz, fd, (void *) address, pos, limit);
+}
+
void incrementPosition(JNIEnv * env, jobject bufObj, int written) {
// Get the current position using the (*env)->GetIntField if possible and fallback
// to slower (*env)->CallIntMethod(...) if needed
@@ -578,14 +580,7 @@ JNIEXPORT jlong JNICALL Java_io_netty_channel_epoll_Native_writev(JNIEnv * env,
return res;
}
-JNIEXPORT jint JNICALL Java_io_netty_channel_epoll_Native_read(JNIEnv * env, jclass clazz, jint fd, jobject jbuffer, jint pos, jint limit) {
- // TODO: We could also maybe pass the address in directly and so eliminate this call
- // not sure if this would buy us much. So some testing is needed.
- void *buffer = (*env)->GetDirectBufferAddress(env, jbuffer);
- if (buffer == NULL) {
- throwRuntimeException(env, "Unable to access address of buffer");
- return -1;
- }
+jint read0(JNIEnv * env, jclass clazz, jint fd, void *buffer, jint pos, jint limit) {
ssize_t res;
int err;
do {
@@ -613,6 +608,19 @@ JNIEXPORT jint JNICALL Java_io_netty_channel_epoll_Native_read(JNIEnv * env, jcl
return (jint) res;
}
+JNIEXPORT jint JNICALL Java_io_netty_channel_epoll_Native_read(JNIEnv * env, jclass clazz, jint fd, jobject jbuffer, jint pos, jint limit) {
+ void *buffer = (*env)->GetDirectBufferAddress(env, jbuffer);
+ if (buffer == NULL) {
+ throwRuntimeException(env, "Unable to access address of buffer");
+ return -1;
+ }
+ return read0(env, clazz, fd, buffer, pos, limit);
+}
+
+JNIEXPORT jint JNICALL Java_io_netty_channel_epoll_Native_readAddress(JNIEnv * env, jclass clazz, jint fd, jlong address, jint pos, jint limit) {
+ return read0(env, clazz, fd, (void*) address, pos, limit);
+}
+
JNIEXPORT void JNICALL Java_io_netty_channel_epoll_Native_close(JNIEnv * env, jclass clazz, jint fd) {
if (close(fd) < 0) {
throwIOException(env, "Error closing file descriptor");
@@ -30,8 +30,10 @@ void Java_io_netty_channel_epoll_Native_epollCtlAdd(JNIEnv * env, jclass clazz,
void Java_io_netty_channel_epoll_Native_epollCtlMod(JNIEnv * env, jclass clazz, jint efd, jint fd, jint flags, jint id);
void Java_io_netty_channel_epoll_Native_epollCtlDel(JNIEnv * env, jclass clazz, jint efd, jint fd);
jint Java_io_netty_channel_epoll_Native_write(JNIEnv * env, jclass clazz, jint fd, jobject jbuffer, jint pos, jint limit);
+jint Java_io_netty_channel_epoll_Native_writeAddress(JNIEnv * env, jclass clazz, jint fd, jlong address, jint pos, jint limit);
jlong Java_io_netty_channel_epoll_Native_writev(JNIEnv * env, jclass clazz, jint fd, jobjectArray buffers, jint offset, jint length);
jint Java_io_netty_channel_epoll_Native_read(JNIEnv * env, jclass clazz, jint fd, jobject jbuffer, jint pos, jint limit);
+jint Java_io_netty_channel_epoll_Native_readAddress(JNIEnv * env, jclass clazz, jint fd, jlong address, jint pos, jint limit);
void JNICALL Java_io_netty_channel_epoll_Native_close(JNIEnv * env, jclass clazz, jint fd);
void Java_io_netty_channel_epoll_Native_shutdown(JNIEnv * env, jclass clazz, jint fd, jboolean read, jboolean write);
jint Java_io_netty_channel_epoll_Native_socket(JNIEnv * env, jclass clazz);
@@ -115,8 +115,12 @@ private int doWriteBytes(ByteBuf buf, int readable) throws Exception {
int readerIndex = buf.readerIndex();
int localFlushedAmount;
if (buf.nioBufferCount() == 1) {
- ByteBuffer nioBuf = buf.internalNioBuffer(readerIndex, readable);
- localFlushedAmount = Native.write(fd, nioBuf, nioBuf.position(), nioBuf.limit());
+ if (buf.hasMemoryAddress()) {
+ localFlushedAmount = Native.writeAddress(fd, buf.memoryAddress(), readerIndex, buf.writerIndex());
+ } else {
+ ByteBuffer nioBuf = buf.internalNioBuffer(readerIndex, readable);
+ localFlushedAmount = Native.write(fd, nioBuf, nioBuf.position(), nioBuf.limit());
+ }
} else {
// backed by more then one buffer, do a gathering write...
ByteBuffer[] nioBufs = buf.nioBuffers();
@@ -509,8 +513,13 @@ private void doFinishConnect() throws Exception {
*/
private int doReadBytes(ByteBuf byteBuf) throws Exception {
int writerIndex = byteBuf.writerIndex();
- ByteBuffer buf = byteBuf.internalNioBuffer(writerIndex, byteBuf.writableBytes());
- int localReadAmount = Native.read(fd, buf, buf.position(), buf.limit());
+ int localReadAmount;
+ if (byteBuf.hasMemoryAddress()) {
+ localReadAmount = Native.readAddress(fd, byteBuf.memoryAddress(), writerIndex, byteBuf.capacity());
+ } else {
+ ByteBuffer buf = byteBuf.internalNioBuffer(writerIndex, byteBuf.writableBytes());
+ localReadAmount = Native.read(fd, buf, buf.position(), buf.limit());
+ }
if (localReadAmount > 0) {
byteBuf.writerIndex(writerIndex + localReadAmount);
}
@@ -60,9 +60,14 @@
// File-descriptor operations
public static native void close(int fd) throws IOException;
+
public static native int write(int fd, ByteBuffer buf, int pos, int limit) throws IOException;
+ public static native int writeAddress(int fd, long address, int pos, int limit) throws IOException;
+
public static native long writev(int fd, ByteBuffer[] buffers, int offset, int length) throws IOException;
public static native int read(int fd, ByteBuffer buf, int pos, int limit) throws IOException;
+ public static native int readAddress(int fd, long address, int pos, int limit) throws IOException;
+
public static native long sendfile(int dest, DefaultFileRegion src, long offset, long length) throws IOException;
// socket operations

0 comments on commit 55d0f36

Please sign in to comment.