aboutsummaryrefslogtreecommitdiffstats
path: root/org.eclipse.jgit/src/org/eclipse/jgit
diff options
context:
space:
mode:
authorShawn Pearce <spearce@spearce.org>2013-09-04 12:56:38 -0700
committerShawn Pearce <spearce@spearce.org>2013-09-04 14:54:50 -0700
commitaa8d5ac26c29663ef2792cd2eb1a749746c9307f (patch)
treee154f2052bbbd4dce3b7ed426716bc88b3094909 /org.eclipse.jgit/src/org/eclipse/jgit
parentf68ffb48eb16171da3d42b91f20c842201ea7431 (diff)
downloadjgit-aa8d5ac26c29663ef2792cd2eb1a749746c9307f.tar.gz
jgit-aa8d5ac26c29663ef2792cd2eb1a749746c9307f.zip
Remove unnecessary inflate stride in DfsBlock
OpenJDK 7 does not benefit from using an inflate stride on the input array. The implementation of java.util.zip.Inflater supplies the entire input byte[] to libz, with no regards for the bounds supplied. Slicing at 512 byte increments in DfsBlock no longer has any benefit. In OpenJDK 6 the native portion of Inflater used GetByteArrayRegion to obtain a copy of the input buffer for libz. In this use case supplying a small stride made sense, it avoided allocating space for and copying data past the end of the object's compressed stream. In OpenJDK 7 the native code uses GetPrimitiveArrayCritical, which tries to avoid copying by freezing Java garbage collection and accessing the byte[] contents in place. On OpenJDK 7 derived JVMs it is likely more efficient to supply the entire DfsBlock. Since OpenJDK 5 and 6 are deprecated and replaced by OpenJDK 7 it is reasonable to suggest any consumers running JGit with DFS support use an OpenJDK 7 derived JVM. However, JGit still targets local filesystem support on Java 5, so it is still not reasonble to apply this same simplification to the internal.storage.file package. See: JDK-6751338 (http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6751338) Change-Id: Ib248b6d383da5c8aa887d9c355a0df6f3e2247a5
Diffstat (limited to 'org.eclipse.jgit/src/org/eclipse/jgit')
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/dfs/DfsBlock.java35
-rw-r--r--org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/dfs/DfsReader.java25
2 files changed, 17 insertions, 43 deletions
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/dfs/DfsBlock.java b/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/dfs/DfsBlock.java
index 1e447b3178..7289b9ee9c 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/dfs/DfsBlock.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/dfs/DfsBlock.java
@@ -55,17 +55,6 @@ import org.eclipse.jgit.internal.storage.pack.PackOutputStream;
/** A cached slice of a {@link DfsPackFile}. */
final class DfsBlock {
- /**
- * Size in bytes to pass to {@link Inflater} at a time.
- * <p>
- * Blocks can be large (for example 1 MiB), while compressed objects inside
- * of them are very small (for example less than 100 bytes for a delta). JNI
- * forces the data supplied to the Inflater to be copied during setInput(),
- * so use a smaller stride to reduce the risk that too much unnecessary was
- * moved into the native layer.
- */
- private static final int INFLATE_STRIDE = 512;
-
final DfsPackKey pack;
final long start;
@@ -105,29 +94,9 @@ final class DfsBlock {
return n;
}
- int inflate(Inflater inf, long pos, byte[] dstbuf, int dstoff)
- throws DataFormatException {
+ void setInput(Inflater inf, long pos) {
int ptr = (int) (pos - start);
- int in = Math.min(INFLATE_STRIDE, block.length - ptr);
- if (dstoff < dstbuf.length)
- in = Math.min(in, dstbuf.length - dstoff);
- inf.setInput(block, ptr, in);
-
- for (;;) {
- int out = inf.inflate(dstbuf, dstoff, dstbuf.length - dstoff);
- if (out == 0) {
- if (inf.needsInput()) {
- ptr += in;
- in = Math.min(INFLATE_STRIDE, block.length - ptr);
- if (in == 0)
- return dstoff;
- inf.setInput(block, ptr, in);
- continue;
- }
- return dstoff;
- }
- dstoff += out;
- }
+ inf.setInput(block, ptr, block.length - ptr);
}
void crc32(CRC32 out, long pos, int cnt) {
diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/dfs/DfsReader.java b/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/dfs/DfsReader.java
index 26fc035834..d7b222866d 100644
--- a/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/dfs/DfsReader.java
+++ b/org.eclipse.jgit/src/org/eclipse/jgit/internal/storage/dfs/DfsReader.java
@@ -616,19 +616,24 @@ public final class DfsReader extends ObjectReader implements ObjectReuseAsIs {
boolean headerOnly) throws IOException, DataFormatException {
prepareInflater();
pin(pack, position);
+ block.setInput(inf, position);
int dstoff = 0;
for (;;) {
- dstoff = block.inflate(inf, position, dstbuf, dstoff);
-
- if (headerOnly && dstoff == dstbuf.length)
- return dstoff;
- if (inf.needsInput()) {
- position += block.remaining(position);
- pin(pack, position);
- } else if (inf.finished())
- return dstoff;
- else
+ int n = inf.inflate(dstbuf, dstoff, dstbuf.length - dstoff);
+ if (n == 0) {
+ if (headerOnly && dstoff == dstbuf.length)
+ return dstoff;
+ if (inf.needsInput()) {
+ position += block.remaining(position);
+ pin(pack, position);
+ block.setInput(inf, position);
+ continue;
+ }
+ if (inf.finished())
+ return dstoff;
throw new DataFormatException();
+ }
+ dstoff += n;
}
}