1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44 package org.eclipse.jgit.pgm.debug;
45
46 import java.io.ByteArrayInputStream;
47 import java.io.ByteArrayOutputStream;
48 import java.io.IOException;
49 import java.util.Collections;
50 import java.util.zip.InflaterInputStream;
51
52 import org.eclipse.jgit.errors.MissingObjectException;
53 import org.eclipse.jgit.errors.StoredObjectRepresentationNotAvailableException;
54 import org.eclipse.jgit.internal.storage.pack.BinaryDelta;
55 import org.eclipse.jgit.internal.storage.pack.ObjectReuseAsIs;
56 import org.eclipse.jgit.internal.storage.pack.ObjectToPack;
57 import org.eclipse.jgit.internal.storage.pack.PackOutputStream;
58 import org.eclipse.jgit.internal.storage.pack.PackWriter;
59 import org.eclipse.jgit.internal.storage.pack.StoredObjectRepresentation;
60 import org.eclipse.jgit.lib.NullProgressMonitor;
61 import org.eclipse.jgit.lib.ObjectId;
62 import org.eclipse.jgit.lib.ObjectReader;
63 import org.eclipse.jgit.pgm.Command;
64 import org.eclipse.jgit.pgm.TextBuiltin;
65 import org.eclipse.jgit.revwalk.RevObject;
66 import org.eclipse.jgit.revwalk.RevWalk;
67 import org.eclipse.jgit.util.TemporaryBuffer;
68 import org.kohsuke.args4j.Argument;
69
70 @Command(usage = "usage_ShowPackDelta")
71 class ShowPackDelta extends TextBuiltin {
72 @Argument(index = 0)
73 private ObjectId objectId;
74
75 @Override
76 protected void run() throws Exception {
77 ObjectReader reader = db.newObjectReader();
78 RevObject obj;
79 try (RevWalk rw = new RevWalk(reader)) {
80 obj = rw.parseAny(objectId);
81 }
82 byte[] delta = getDelta(reader, obj);
83
84
85
86
87 long size = reader.getObjectSize(obj, obj.getType());
88 try {
89 if (BinaryDelta.getResultSize(delta) != size)
90 throw die("Object " + obj.name() + " is not a delta");
91 } catch (ArrayIndexOutOfBoundsException bad) {
92 throw die("Object " + obj.name() + " is not a delta");
93 }
94
95 outw.println(BinaryDelta.format(delta));
96 }
97
98 private static byte[] getDelta(ObjectReader reader, RevObject obj)
99 throws IOException, MissingObjectException,
100 StoredObjectRepresentationNotAvailableException {
101 ObjectReuseAsIs asis = (ObjectReuseAsIs) reader;
102 ObjectToPack target = asis.newObjectToPack(obj, obj.getType());
103
104 PackWriter pw = new PackWriter(reader) {
105 @Override
106 public void select(ObjectToPack otp, StoredObjectRepresentation next) {
107 otp.select(next);
108 }
109 };
110
111 ByteArrayOutputStream buf = new ByteArrayOutputStream();
112 asis.selectObjectRepresentation(pw, NullProgressMonitor.INSTANCE,
113 Collections.singleton(target));
114 asis.copyObjectAsIs(new PackOutputStream(NullProgressMonitor.INSTANCE,
115 buf, pw), target, true);
116
117
118
119
120
121 byte[] bufArray = buf.toByteArray();
122 int ptr = 0;
123 while ((bufArray[ptr] & 0x80) != 0)
124 ptr++;
125 ptr++;
126
127 @SuppressWarnings("resource" )
128 TemporaryBuffer.Heap raw = new TemporaryBuffer.Heap(bufArray.length);
129 InflaterInputStream inf = new InflaterInputStream(
130 new ByteArrayInputStream(bufArray, ptr, bufArray.length));
131 raw.copy(inf);
132 inf.close();
133 return raw.toByteArray();
134 }
135 }