--- old/src/java.base/unix/native/libnio/ch/FileChannelImpl.c 2018-07-19 11:59:03.935320578 +0100 +++ new/src/java.base/unix/native/libnio/ch/FileChannelImpl.c 2018-07-19 11:59:03.463319157 +0100 @@ -47,6 +47,7 @@ #include "nio_util.h" #include "sun_nio_ch_FileChannelImpl.h" #include "java_lang_Integer.h" +#include static jfieldID chan_fd; /* jobject 'fd' in sun.nio.ch.FileChannelImpl */ @@ -72,7 +73,7 @@ JNIEXPORT jlong JNICALL Java_sun_nio_ch_FileChannelImpl_map0(JNIEnv *env, jobject this, - jint prot, jlong off, jlong len) + jint prot, jlong off, jlong len, jboolean map_sync) { void *mapAddress = 0; jobject fdo = (*env)->GetObjectField(env, this, chan_fd); @@ -80,6 +81,9 @@ int protections = 0; int flags = 0; + // should never be called with map_sync and prot == PRIVATE + assert((prot != sun_nio_ch_FileChannelImpl_MAP_PV) ||! map_sync); + if (prot == sun_nio_ch_FileChannelImpl_MAP_RO) { protections = PROT_READ; flags = MAP_SHARED; @@ -91,6 +95,36 @@ flags = MAP_PRIVATE; } + // TODO - remove the following defines + // for testing we need to define the extra MAP_XXX flags used for + // persistent memory. they will eventually get defined by the + // system and included via sys/mman.h + +#ifndef MAP_SYNC +#define MAP_SYNC 0x80000 +#define MAP_SHARED_VALIDATE 0x03; +#define __NEEDS_MAP_SYNC_UNDEF__ +#endif + + if (map_sync) { + // ensure + // 1) this is Linux on AArch64 or x86_64 + // 2) the mmap APIs are available/ at compile time +#if !defined(LINUX) || ! (defined(aarch64) || (defined(amd64) && defined(_LP64))) || ! defined(MAP_SYNC) || ! defined(MAP_SHARED_VALIDATE) + // TODO - implement for solaris/AIX/BSD/WINDOWS and for 32 bit + JNU_ThrowIOException(env, "map_persistent is not implemented"); + return IOS_THROWN; +#else + flags |= MAP_SYNC | MAP_SHARED_VALIDATE; +#endif + } + +#ifdef __NEEDS_MAP_SYNC_UNDEF__ +#undef MAP_SYNC +#undef MAP_SHARED_VALIDATE +#undef __NEEDS_MAP_SYNC_UNDEF__ +#endif + mapAddress = mmap64( 0, /* Let OS decide location */ len, /* Number of bytes to map */ @@ -100,6 +134,11 @@ off); /* Offset into file */ if (mapAddress == MAP_FAILED) { + if (map_sync && errno == ENOTSUP) { + JNU_ThrowIOExceptionWithLastError(env, "map_persistent is not supported"); + return IOS_THROWN; + } + if (errno == ENOMEM) { JNU_ThrowOutOfMemoryError(env, "Map failed"); return IOS_THROWN;