--- old/src/java.base/share/native/libjava/io_util.c 2016-08-25 17:51:53.692564695 -0700 +++ new/src/java.base/share/native/libjava/io_util.c 2016-08-25 17:51:53.587564694 -0700 @@ -122,6 +122,103 @@ return nread; } +jint +readBytesD(JNIEnv *env, jobject this, jbyteArray bytes, + jint off, jint len, jfieldID fid, jfieldID pgsz_id) +{ +#ifdef _WIN32 + JNU_ThrowIOException(env, "DirectIO is not supported on Windows platform!"); +#else + jint nread; + void *buf = NULL; + int delta = 0; + int gap = 0; + int newLen = 0; + long currentLocation; + long newStartLocation; + FD fd; + int pageSize; + if (IS_NULL(bytes)) { + JNU_ThrowNullPointerException(env, NULL); + return -1; + } + + if (outOfBounds(env, off, len, bytes)) { + JNU_ThrowByName(env, "java/lang/IndexOutOfBoundsException", NULL); + return -1; + } + + if (len == 0) { + return 0; + } + + fd = GET_FD(this, fid); + pageSize = GET_PG_SIZE(this, pgsz_id); + + if (fd == -1) { + JNU_ThrowIOException(env, "Stream Closed"); + return -1; + } else if (pageSize == -1) { + JNU_ThrowIOException(env, "Error getting kernel pageSize for DirectIO alligment"); + return -1; + } else { + currentLocation = IO_Lseek(fd, 0, SEEK_CUR); + + if ((currentLocation % pageSize) != 0) { + newStartLocation = currentLocation / pageSize * pageSize; + gap = currentLocation - newStartLocation; + } else { + newStartLocation = currentLocation; + gap = 0; + } + IO_Lseek(fd, newStartLocation, SEEK_SET); + if ((len % pageSize) != 0) { + newLen = (len / pageSize + 1) * pageSize; + } else { + newLen = len; + } + if ((newLen - gap) < len) { + newLen = newLen + pageSize; + } + + delta = newLen - len; + if (newLen == 0) { + return 0; + } else { + posix_memalign(&buf, pageSize, newLen); + if (buf == NULL) { + JNU_ThrowOutOfMemoryError(env, NULL); + return 0; + } + } + nread = IO_Read(fd, buf, newLen); + if (nread > 0) { + if (nread >= len) { + (*env)->SetByteArrayRegion(env, bytes, off, len, ((jbyte *)(buf) + gap)); //read in the middle of a file + } else { + (*env)->SetByteArrayRegion(env, bytes, off, (nread-gap), ((jbyte *)(buf) + gap)); //reached the end of the file + } + } else if (nread == -1) { + JNU_ThrowIOExceptionWithLastError(env, "Read error"); + } else { /*EOF*/ + nread = -1; + } + IO_Lseek(fd, (currentLocation + len), SEEK_SET); + + free(buf); + if (nread != -1) { + if (nread >= len) { + return len; + } else { + return (nread - gap); + } + } else { + return -1; + } + } +#endif +} + void writeSingle(JNIEnv *env, jobject this, jint byte, jboolean append, jfieldID fid) { // Discard the 24 high-order bits of byte. See OutputStream#write(int) @@ -202,6 +299,78 @@ } void +writeBytesD(JNIEnv *env, jobject this, jbyteArray bytes, + jint off, jint len, jboolean append, jfieldID fid, jfieldID pgsz_id) +{ +#ifdef _WIN32 + JNU_ThrowIOException(env, "DirectIO is not supported on Windows platform!"); +#else + jint n; + void *buf = NULL; + FD fd; + int pageSize; + long currentLocation; + + fd = GET_FD(this, fid); + if (fd == -1) { + JNU_ThrowIOException(env, "Stream Closed"); + } + + pageSize = GET_PG_SIZE(this, pgsz_id); + if (pageSize == -1) { + JNU_ThrowIOException(env, "Error getting kernel pageSize for DirectIO alligment"); + } + + currentLocation = IO_Lseek(fd, 0, SEEK_CUR); + + if ((len % pageSize != 0) || (currentLocation % pageSize != 0)) { + JNU_ThrowIOException(env, + "In DirectIO mode, the IO size and currentLocation must be aligned with kernel page size!"); + } + + if (IS_NULL(bytes)) { + JNU_ThrowNullPointerException(env, NULL); + return; + } + + if (outOfBounds(env, off, len, bytes)) { + JNU_ThrowByName(env, "java/lang/IndexOutOfBoundsException", NULL); + return; + } + + if (len == 0) { + return; + } else { + posix_memalign(&buf, pageSize, len); + if (buf == NULL) { + JNU_ThrowOutOfMemoryError(env, NULL); + return; + } + } + + (*env)->GetByteArrayRegion(env, bytes, off, len, (jbyte *)buf); + + if (!(*env)->ExceptionOccurred(env)) { + off = 0; + while (len > 0) { + if (append == JNI_TRUE) { + n = IO_Append(fd, buf+off, len); + } else { + n = IO_Write(fd, buf+off, len); + } + if (n == -1) { + JNU_ThrowIOExceptionWithLastError(env, "Write error"); + break; + } + off += n; + len -= n; + } + } + free(buf); +#endif +} + +void throwFileNotFoundException(JNIEnv *env, jstring path) { char buf[256];