Fix possible NegativeArraySizeException in PackIndexV1

Due to an integer overflow bug, the current "Index file is too large
for jgit" check did not work properly and subsequently a
NegativeArraySizeException was raised.

Change-Id: I2736efb28987c29e56bc946563b7fa781898a94a
Signed-off-by: Marc Strapetz <marc.strapetz@syntevo.com>
diff --git a/org.eclipse.jgit.test/tst-rsrc/org/eclipse/jgit/test/resources/pack-bad-fanout-table.idx b/org.eclipse.jgit.test/tst-rsrc/org/eclipse/jgit/test/resources/pack-bad-fanout-table.idx
new file mode 100644
index 0000000..2029915
--- /dev/null
+++ b/org.eclipse.jgit.test/tst-rsrc/org/eclipse/jgit/test/resources/pack-bad-fanout-table.idx
Binary files differ
diff --git a/org.eclipse.jgit.test/tst-rsrc/org/eclipse/jgit/test/resources/pack-bad-fanout-table.idxV2 b/org.eclipse.jgit.test/tst-rsrc/org/eclipse/jgit/test/resources/pack-bad-fanout-table.idxV2
new file mode 100644
index 0000000..28bd4a7
--- /dev/null
+++ b/org.eclipse.jgit.test/tst-rsrc/org/eclipse/jgit/test/resources/pack-bad-fanout-table.idxV2
Binary files differ
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexTestCase.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexTestCase.java
index fe05fba..910b928 100644
--- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexTestCase.java
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexTestCase.java
@@ -12,13 +12,17 @@
 
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertThrows;
 import static org.junit.Assert.fail;
 
 import java.io.File;
+import java.io.FileInputStream;
+import java.io.IOException;
 import java.util.Iterator;
 import java.util.NoSuchElementException;
 
 import org.eclipse.jgit.errors.MissingObjectException;
+import org.eclipse.jgit.internal.JGitText;
 import org.eclipse.jgit.internal.storage.file.PackIndex.MutableEntry;
 import org.eclipse.jgit.junit.RepositoryTestCase;
 import org.junit.Test;
@@ -51,6 +55,13 @@
 	public abstract File getFileForPackdf2982f28();
 
 	/**
+	 * Return file with appropriate index version for bad fanout table test.
+	 *
+	 * @return file with index
+	 */
+	public abstract File getFileForBadFanoutTable();
+
+	/**
 	 * Verify CRC32 support.
 	 *
 	 * @throws MissingObjectException
@@ -158,4 +169,15 @@
 				.name());
 	}
 
+	@Test
+	public void testBadFanoutTable() {
+		IOException ex = assertThrows(IOException.class, () -> {
+			try (FileInputStream fis = new FileInputStream(
+					getFileForBadFanoutTable())) {
+				PackIndex.read(fis);
+			}
+		});
+		assertEquals(JGitText.get().indexFileIsTooLargeForJgit,
+				ex.getMessage());
+	}
 }
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexV1Test.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexV1Test.java
index e41ded7..c4f6372 100644
--- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexV1Test.java
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexV1Test.java
@@ -35,6 +35,11 @@
                     "pack-df2982f284bbabb6bdb59ee3fcc6eb0983e20371.idx");
 	}
 
+	@Override
+	public File getFileForBadFanoutTable() {
+		return JGitTestUtil.getTestResourceFile("pack-bad-fanout-table.idx");
+	}
+
 	/**
 	 * Verify CRC32 - V1 should not index anything.
 	 *
diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexV2Test.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexV2Test.java
index c1da547..1d179ab 100644
--- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexV2Test.java
+++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/internal/storage/file/PackIndexV2Test.java
@@ -35,6 +35,11 @@
 				"pack-df2982f284bbabb6bdb59ee3fcc6eb0983e20371.idxV2");
 	}
 
+	@Override
+	public File getFileForBadFanoutTable() {
+		return JGitTestUtil.getTestResourceFile("pack-bad-fanout-table.idxV2");
+	}
+
 	/**
 	 * Verify CRC32 indexing.
 	 *
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/file/PackIndexV1.java b/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/file/PackIndexV1.java
index 9cf95d0..eb0ac6a 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/file/PackIndexV1.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/file/PackIndexV1.java
@@ -49,11 +49,11 @@
 			idxHeader[k] = NB.decodeUInt32(fanoutTable, k * 4);
 		idxdata = new byte[idxHeader.length][];
 		for (int k = 0; k < idxHeader.length; k++) {
-			int n;
+			long n;
 			if (k == 0) {
-				n = (int) (idxHeader[k]);
+				n = idxHeader[k];
 			} else {
-				n = (int) (idxHeader[k] - idxHeader[k - 1]);
+				n = idxHeader[k] - idxHeader[k - 1];
 			}
 			if (n > 0) {
 				final long len = n * (Constants.OBJECT_ID_LENGTH + 4);