IGNITE-5816 - Fixed race in WAL segment close leading to ClosedChannelException


Project: http://git-wip-us.apache.org/repos/asf/ignite/repo
Commit: http://git-wip-us.apache.org/repos/asf/ignite/commit/770efe23
Tree: http://git-wip-us.apache.org/repos/asf/ignite/tree/770efe23
Diff: http://git-wip-us.apache.org/repos/asf/ignite/diff/770efe23

Branch: refs/heads/ignite-5578
Commit: 770efe23ce58a62461c698b42b4d58c5791bceb2
Parents: c685e39
Author: Alexey Goncharuk <[email protected]>
Authored: Fri Jul 28 17:26:19 2017 +0300
Committer: Alexey Goncharuk <[email protected]>
Committed: Fri Jul 28 17:26:52 2017 +0300

----------------------------------------------------------------------
 .../wal/FileWriteAheadLogManager.java           | 32 +++++++++++++++-----
 1 file changed, 24 insertions(+), 8 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/ignite/blob/770efe23/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/wal/FileWriteAheadLogManager.java
----------------------------------------------------------------------
diff --git 
a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/wal/FileWriteAheadLogManager.java
 
b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/wal/FileWriteAheadLogManager.java
index b655ddf..85eb480 100644
--- 
a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/wal/FileWriteAheadLogManager.java
+++ 
b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/wal/FileWriteAheadLogManager.java
@@ -1800,6 +1800,13 @@ public class FileWriteAheadLogManager extends 
GridCacheSharedManagerAdapter impl
 
             if (flush(ptr, stop))
                 return;
+            else if (stop) {
+                FakeRecord fr = (FakeRecord)head.get();
+
+                assert fr.stop : "Invalid fake record on top of the queue: " + 
fr;
+
+                expWritten = recordOffset(fr);
+            }
 
             // Spin-wait for a while before acquiring the lock.
             for (int i = 0; i < 64; i++) {
@@ -2049,14 +2056,11 @@ public class FileWriteAheadLogManager extends 
GridCacheSharedManagerAdapter impl
          * @throws StorageException If failed.
          */
         private boolean close(boolean rollOver) throws IgniteCheckedException, 
StorageException {
-            if (mode == WALMode.DEFAULT)
-                fsync(null, true);
-            else
+            if (stop.compareAndSet(false, true)) {
                 flushOrWait(null, true);
 
-            assert stopped() : "Segment is not closed after close flush: " + 
head.get();
+                assert stopped() : "Segment is not closed after close flush: " 
+ head.get();
 
-            if (stop.compareAndSet(false, true)) {
                 try {
                     int switchSegmentRecSize = 
RecordV1Serializer.REC_TYPE_SIZE + RecordV1Serializer.FILE_WAL_POINTER_SIZE;
 
@@ -2070,10 +2074,22 @@ public class FileWriteAheadLogManager extends 
GridCacheSharedManagerAdapter impl
 
                         buf.rewind();
 
-                        fileIO.write(buf, written);
+                        int rem = buf.remaining();
+
+                        while (rem > 0) {
+                            int written0 = fileIO.write(buf, written);
+
+                            written += written0;
+
+                            rem -= written0;
+                        }
+                    }
+
+                    // Do the final fsync.
+                    if (mode == WALMode.DEFAULT) {
+                        fileIO.force();
 
-                        if (mode == WALMode.DEFAULT)
-                            fileIO.force();
+                        lastFsyncPos = written;
                     }
 
                     fileIO.close();

Reply via email to