diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/util/io/UnionInputStreamTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/util/io/UnionInputStreamTest.java index 9fb323c4d..daebffbc1 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/util/io/UnionInputStreamTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/util/io/UnionInputStreamTest.java @@ -50,6 +50,7 @@ import java.io.ByteArrayInputStream; import java.io.IOException; +import java.io.InputStream; import java.util.Arrays; import org.junit.Test; @@ -238,4 +239,26 @@ public void close() throws IOException { assertEquals("I AM A TEST", e.getMessage()); } } + + @Test + public void testNonBlockingPartialRead() throws Exception { + InputStream errorReadStream = new InputStream() { + @Override + public int read() throws IOException { + throw new IOException("Expected"); + } + }; + final UnionInputStream u = new UnionInputStream( + new ByteArrayInputStream(new byte[]{1,2,3}), + errorReadStream); + byte buf[] = new byte[10]; + assertEquals(3, u.read(buf, 0, 10)); + assertTrue(Arrays.equals(new byte[] {1,2,3}, slice(buf, 3))); + try { + u.read(buf, 0, 1); + fail("Expected exception from errorReadStream"); + } catch (IOException e) { + assertEquals("Expected", e.getMessage()); + } + } } diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/util/io/UnionInputStream.java b/org.eclipse.jgit/src/org/eclipse/jgit/util/io/UnionInputStream.java index 0df3775f1..20dcd4659 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/util/io/UnionInputStream.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/util/io/UnionInputStream.java @@ -138,23 +138,18 @@ else if (in == EOF) @Override public int read(byte[] b, int off, int len) throws IOException { - int cnt = 0; - while (0 < len) { + if (len == 0) + return 0; + for (;;) { final InputStream in = head(); final int n = in.read(b, off, len); - if (0 < n) { - cnt += n; - off += n; - len -= n; - } else if (in == EOF) - return 0 < cnt ? cnt : -1; - else { + if (0 < n) + return n; + else if (in == EOF) + return -1; + else pop(); - if (0 < cnt) - break; - } } - return cnt; } @Override