Index: modules/luni/src/main/java/java/io/RandomAccessFile.java =================================================================== --- modules/luni/src/main/java/java/io/RandomAccessFile.java (revision 386064) +++ modules/luni/src/main/java/java/io/RandomAccessFile.java (working copy) @@ -35,6 +35,8 @@ */ FileDescriptor fd; + private boolean syncMetadata = false; + // The unique file channel associated with this FileInputStream (lazily // initialized). private FileChannel channel; @@ -66,10 +68,24 @@ public RandomAccessFile(File file, String mode) throws FileNotFoundException { super(); + + int options = 0; + if (mode.equals("r")) { //$NON-NLS-1$ isReadOnly = true; + options = IFileSystem.O_RDONLY; } else if (mode.equals("rw") || mode.equals("rws") || mode.equals("rwd")) { //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ isReadOnly = false; + options = IFileSystem.O_RDWR; + + if (mode.equals("rws")) { + // Sync file and metadata with every write + syncMetadata = true; + } else if (mode.equals("rwd")) { + // Sync file, but not necessarily metadata + options = IFileSystem.O_RDWRSYNC; + } + } else { throw new IllegalArgumentException(com.ibm.oti.util.Msg .getString("K0081")); //$NON-NLS-1$ @@ -83,13 +99,18 @@ } fd = new FileDescriptor(); - // FIXME: add support to "rwd", "rws" - fd.descriptor = fileSystem.open(file.properPath(true), - isReadOnly ? IFileSystem.O_RDONLY : IFileSystem.O_RDWR); - channel = FileChannelFactory.getFileChannel(this, fd.descriptor, - isReadOnly ? IFileSystem.O_RDONLY : IFileSystem.O_RDWR); + fd.descriptor = fileSystem.open(file.properPath(true), options); + channel = FileChannelFactory.getFileChannel(this, fd.descriptor, options); + + // if we are in "rws" mode, attempt to sync file+metadata + if (syncMetadata) { + try { + fd.sync(); + } catch (IOException e) {} + } } + /** * Constructs a new RandomAccessFile on the file named fileName * and opens it according to the access String in mode. The @@ -616,6 +637,11 @@ fileSystem.truncate(fd.descriptor, newLength); seek(position > newLength ? newLength : position); } + + // if we are in "rws" mode, attempt to sync file+metadata + if (syncMetadata) { + fd.sync(); + } } /** @@ -688,6 +714,11 @@ synchronized (repositionLock) { fileSystem.write(fd.descriptor, buffer, offset, count); } + + // if we are in "rws" mode, attempt to sync file+metadata + if (syncMetadata) { + fd.sync(); + } } /** @@ -713,6 +744,11 @@ synchronized (repositionLock) { fileSystem.write(fd.descriptor, bytes, 0, 1); } + + // if we are in "rws" mode, attempt to sync file+metadata + if (syncMetadata) { + fd.sync(); + } } /** Index: modules/luni/src/main/java/java/io/FileChannelFactory.java =================================================================== --- modules/luni/src/main/java/java/io/FileChannelFactory.java (revision 386064) +++ modules/luni/src/main/java/java/io/FileChannelFactory.java (working copy) @@ -36,6 +36,8 @@ return new WriteOnlyFileChannel(stream, fd); case IFileSystem.O_RDWR: return new ReadWriteFileChannel(stream, fd); + case IFileSystem.O_RDWRSYNC: + return new ReadWriteFileChannel(stream, fd); case IFileSystem.O_APPEND: return new WriteOnlyFileChannel(stream, fd, true); default: Index: modules/luni/src/main/java/org/apache/harmony/luni/platform/IFileSystem.java =================================================================== --- modules/luni/src/main/java/org/apache/harmony/luni/platform/IFileSystem.java (revision 386064) +++ modules/luni/src/main/java/org/apache/harmony/luni/platform/IFileSystem.java (working copy) @@ -41,6 +41,8 @@ public final int O_RDWR = 0x00000010; + public final int O_RDWRSYNC = 0x00000020; + public final int O_APPEND = 0x00000100; public final int O_CREAT = 0x00001000; @@ -52,7 +54,7 @@ public final int O_NONBLOCK = 0x01000000; public final int O_TRUNC = 0x10000000; - + public long read(long fileDescriptor, byte[] bytes, int offset, int length) throws IOException; Index: native-src/shared/luni/OSFileSystem.c =================================================================== --- native-src/shared/luni/OSFileSystem.c (revision 386064) +++ native-src/shared/luni/OSFileSystem.c (working copy) @@ -220,6 +220,10 @@ flags = HyOpenWrite | HyOpenCreate | HyOpenAppend; mode = 0666; break; + case org_apache_harmony_luni_platform_IFileSystem_O_RDWRSYNC: + flags = HyOpenRead | HyOpenWrite | HyOpenCreate | HyOpenSync; + mode = 0666; + break; } length = (*env)->GetArrayLength (env, path); Index: native-src/win.IA32/include/hyport.h =================================================================== --- native-src/win.IA32/include/hyport.h (revision 386064) +++ native-src/win.IA32/include/hyport.h (working copy) @@ -94,6 +94,7 @@ #define HyOpenAppend 16 #define HyOpenText 32 #define HyOpenCreateNew 64 /* Use this flag with HyOpenCreate, if this flag is specified then trying to create an existing file will fail */ +#define HyOpenSync 128 #define HyIsDir 0 /* Return values for HyFileAttr */ #define HyIsFile 1 Index: native-src/win.IA32/port/hyfile.c =================================================================== --- native-src/win.IA32/port/hyfile.c (revision 386064) +++ native-src/win.IA32/port/hyfile.c (working copy) @@ -399,7 +399,7 @@ hyfile_open (struct HyPortLibrary * portLibrary, const char *path, I_32 flags, I_32 mode) { - DWORD accessMode, shareMode, createMode; + DWORD accessMode, shareMode, createMode, flagsAndAttributes; HANDLE aHandle; I_32 error; @@ -430,9 +430,14 @@ createMode = OPEN_EXISTING; } + flagsAndAttributes = FILE_ATTRIBUTE_NORMAL; + if (flags & HyOpenSync) { + flagsAndAttributes |= FILE_FLAG_WRITE_THROUGH; + } + aHandle = CreateFile (path, accessMode, shareMode, NULL, createMode, - FILE_ATTRIBUTE_NORMAL, NULL); + flagsAndAttributes, NULL); if (aHandle == INVALID_HANDLE_VALUE) { error = GetLastError (); @@ -452,7 +457,7 @@ aHandle = CreateFile (path, accessMode, shareMode, NULL, TRUNCATE_EXISTING, - FILE_ATTRIBUTE_NORMAL, NULL); + flagsAndAttributes, NULL); if (aHandle == INVALID_HANDLE_VALUE) { error = GetLastError (); Index: native-src/win.IA32/luni/IFileSystem.h =================================================================== --- native-src/win.IA32/luni/IFileSystem.h (revision 386064) +++ native-src/win.IA32/luni/IFileSystem.h (working copy) @@ -38,6 +38,8 @@ #define org_apache_harmony_luni_platform_IFileSystem_O_WRONLY 1L #undef org_apache_harmony_luni_platform_IFileSystem_O_RDWR #define org_apache_harmony_luni_platform_IFileSystem_O_RDWR 16L +#undef org_apache_harmony_luni_platform_IFileSystem_O_RDWRSYNC +#define org_apache_harmony_luni_platform_IFileSystem_O_RDWRSYNC 32L #undef org_apache_harmony_luni_platform_IFileSystem_O_APPEND #define org_apache_harmony_luni_platform_IFileSystem_O_APPEND 256L #undef org_apache_harmony_luni_platform_IFileSystem_O_CREAT Index: native-src/linux.IA32/include/hyport.h =================================================================== --- native-src/linux.IA32/include/hyport.h (revision 386064) +++ native-src/linux.IA32/include/hyport.h (working copy) @@ -91,6 +91,7 @@ #define HyOpenAppend 16 #define HyOpenText 32 #define HyOpenCreateNew 64 /* Use this flag with HyOpenCreate, if this flag is specified then trying to create an existing file will fail */ +#define HyOpenSync 128 #define HyIsDir 0 /* Return values for HyFileAttr */ #define HyIsFile 1 /** HyMaxPath was chosen from unix MAXPATHLEN. Override in platform Index: native-src/linux.IA32/port/hyfile.c =================================================================== --- native-src/linux.IA32/port/hyfile.c (revision 386064) +++ native-src/linux.IA32/port/hyfile.c (working copy) @@ -64,6 +64,11 @@ { realFlags |= O_EXCL | O_CREAT; } +#ifdef O_SYNC + if (flags & HyOpenSync) { + realFlags |= O_SYNC; + } +#endif if (flags & HyOpenRead) { if (flags & HyOpenWrite) @@ -169,8 +174,6 @@ return -1; } - /* Neutrino does not handle NULL for stat */ - if (!stat (path, &buffer)) { if (S_ISDIR (buffer.st_mode)) Index: native-src/linux.IA32/luni/IFileSystem.h =================================================================== --- native-src/linux.IA32/luni/IFileSystem.h (revision 386064) +++ native-src/linux.IA32/luni/IFileSystem.h (working copy) @@ -38,6 +38,8 @@ #define org_apache_harmony_luni_platform_IFileSystem_O_WRONLY 1L #undef org_apache_harmony_luni_platform_IFileSystem_O_RDWR #define org_apache_harmony_luni_platform_IFileSystem_O_RDWR 16L +#undef org_apache_harmony_luni_platform_IFileSystem_O_RDWRSYNC +#define org_apache_harmony_luni_platform_IFileSystem_O_RDWRSYNC 32L #undef org_apache_harmony_luni_platform_IFileSystem_O_APPEND #define org_apache_harmony_luni_platform_IFileSystem_O_APPEND 256L #undef org_apache_harmony_luni_platform_IFileSystem_O_CREAT