diff --git a/hadoop-hdfs-project/hadoop-hdfs-client/src/main/java/org/apache/hadoop/hdfs/DFSInputStream.java b/hadoop-hdfs-project/hadoop-hdfs-client/src/main/java/org/apache/hadoop/hdfs/DFSInputStream.java index 8c4c3de1aa9e8..da7978d48fa1c 100644 --- a/hadoop-hdfs-project/hadoop-hdfs-client/src/main/java/org/apache/hadoop/hdfs/DFSInputStream.java +++ b/hadoop-hdfs-project/hadoop-hdfs-client/src/main/java/org/apache/hadoop/hdfs/DFSInputStream.java @@ -520,15 +520,20 @@ private LocatedBlock fetchBlockAt(long offset, long length, boolean useCache) // Update the LastLocatedBlock, if offset is for last block. if (offset >= locatedBlocks.getFileLength()) { setLocatedBlocksFields(newBlocks, getLastBlockLength(newBlocks)); + // Here locatedBlocks has been updated, need to check offset again. + // If offset to the portion of the last block, will return the last block, + // otherwise the block containing the specified offset needs to be searched again. + if (offset >= locatedBlocks.getFileLength()) { + return locatedBlocks.getLastLocatedBlock(); + } else { + targetBlockIdx = locatedBlocks.findBlock(offset); + assert targetBlockIdx >= 0 && targetBlockIdx < locatedBlocks.locatedBlockCount(); + } } else { locatedBlocks.insertRange(targetBlockIdx, newBlocks.getLocatedBlocks()); } } - if (targetBlockIdx >= locatedBlocks.locatedBlockCount()) { - DFSClient.LOG.debug("Could not find target position " + offset); - throw new EOFException("Could not find target position " + offset); - } return locatedBlocks.get(targetBlockIdx); } } diff --git a/hadoop-hdfs-project/hadoop-hdfs/src/test/java/org/apache/hadoop/hdfs/TestDFSInputStream.java b/hadoop-hdfs-project/hadoop-hdfs/src/test/java/org/apache/hadoop/hdfs/TestDFSInputStream.java index c3aa0bcdb2cd9..d3932198a940a 100644 --- a/hadoop-hdfs-project/hadoop-hdfs/src/test/java/org/apache/hadoop/hdfs/TestDFSInputStream.java +++ b/hadoop-hdfs-project/hadoop-hdfs/src/test/java/org/apache/hadoop/hdfs/TestDFSInputStream.java @@ -305,8 +305,6 @@ public void testReadWithoutPreferredCachingReplica() throws IOException { public void testCreateBlockReaderWhenInvalidBlockTokenException() throws IOException, InterruptedException, TimeoutException { GenericTestUtils.setLogLevel(DFSClient.LOG, Level.DEBUG); - GenericTestUtils.LogCapturer logs = - GenericTestUtils.LogCapturer.captureLogs(DFSClient.LOG); Configuration conf = new Configuration(); DFSClientFaultInjector oldFaultInjector = DFSClientFaultInjector.get(); try (MiniDFSCluster cluster = new MiniDFSCluster.Builder(conf).numDataNodes(3).build()) { @@ -363,9 +361,6 @@ public Void answer(InvocationOnMock invocation) throws Throwable { int read = in.read(buf, 0, bufLen); assertEquals(1024, read); } - - assertTrue(logs.getOutput().contains("Could not find target position 1")); - logs.clearOutput(); } finally { DFSClientFaultInjector.set(oldFaultInjector); }