Browse Source

HDDS-639. ChunkGroupInputStream gets into infinite loop after reading a block. Contributed by Mukul Kumar Singh.

Arpit Agarwal 6 years ago
parent
commit
56b18b9df1

+ 5 - 1
hadoop-ozone/client/src/main/java/org/apache/hadoop/ozone/client/io/ChunkGroupInputStream.java

@@ -111,7 +111,11 @@ public class ChunkGroupInputStream extends InputStream implements Seekable {
     }
     int totalReadLen = 0;
     while (len > 0) {
-      if (streamEntries.size() <= currentStreamIndex) {
+      // if we are at the last block and have read the entire block, return
+      if (streamEntries.size() == 0 ||
+              (streamEntries.size() - 1 <= currentStreamIndex &&
+                      streamEntries.get(currentStreamIndex)
+                              .getRemaining() == 0)) {
         return totalReadLen == 0 ? EOF : totalReadLen;
       }
       ChunkInputStreamEntry current = streamEntries.get(currentStreamIndex);

+ 10 - 1
hadoop-ozone/ozonefs/src/test/java/org/apache/hadoop/fs/ozone/TestOzoneFileInterfaces.java

@@ -174,9 +174,18 @@ public class TestOzoneFileInterfaces {
 
     try (FSDataInputStream inputStream = fs.open(path)) {
       byte[] buffer = new byte[stringLen];
-      inputStream.readFully(0, buffer);
+      // This read will not change the offset inside the file
+      int readBytes = inputStream.read(0, buffer, 0, buffer.length);
       String out = new String(buffer, 0, buffer.length);
       assertEquals(data, out);
+      assertEquals(readBytes, buffer.length);
+      assertEquals(0, inputStream.getPos());
+
+      // The following read will change the internal offset
+      readBytes = inputStream.read(buffer, 0, buffer.length);
+      assertEquals(data, out);
+      assertEquals(readBytes, buffer.length);
+      assertEquals(buffer.length, inputStream.getPos());
     }
   }