1
2
3
4
5
6
7
8
9
10
11 package org.eclipse.jgit.internal.storage.file;
12
13 import java.io.BufferedOutputStream;
14 import java.io.DataOutput;
15 import java.io.IOException;
16 import java.io.OutputStream;
17 import java.security.DigestOutputStream;
18 import java.text.MessageFormat;
19
20 import org.eclipse.jgit.internal.JGitText;
21 import org.eclipse.jgit.internal.storage.file.PackBitmapIndexBuilder.StoredEntry;
22 import org.eclipse.jgit.lib.Constants;
23
24 import com.googlecode.javaewah.EWAHCompressedBitmap;
25
26
27
28
29
30
31 public class PackBitmapIndexWriterV1 {
32 private final DigestOutputStream out;
33 private final DataOutput dataOutput;
34
35
36
37
38
39
40
41 public PackBitmapIndexWriterV1(final OutputStream dst) {
42 out = new DigestOutputStream(dst instanceof BufferedOutputStream ? dst
43 : new BufferedOutputStream(dst),
44 Constants.newMessageDigest());
45 dataOutput = new SimpleDataOutput(out);
46 }
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63 public void write(PackBitmapIndexBuilder bitmaps, byte[] packDataChecksum)
64 throws IOException {
65 if (bitmaps == null || packDataChecksum.length != 20)
66 throw new IllegalStateException();
67
68 writeHeader(bitmaps.getOptions(), bitmaps.getBitmapCount(),
69 packDataChecksum);
70 writeBody(bitmaps);
71 writeFooter();
72
73 out.flush();
74 }
75
76 private void writeHeader(
77 int options, int bitmapCount, byte[] packDataChecksum)
78 throws IOException {
79 out.write(PackBitmapIndexV1.MAGIC);
80 dataOutput.writeShort(1);
81 dataOutput.writeShort(options);
82 dataOutput.writeInt(bitmapCount);
83 out.write(packDataChecksum);
84 }
85
86 private void writeBody(PackBitmapIndexBuilder bitmaps) throws IOException {
87 writeBitmap(bitmaps.getCommits());
88 writeBitmap(bitmaps.getTrees());
89 writeBitmap(bitmaps.getBlobs());
90 writeBitmap(bitmaps.getTags());
91 writeBitmaps(bitmaps);
92 }
93
94 private void writeBitmap(EWAHCompressedBitmap bitmap) throws IOException {
95 bitmap.serialize(dataOutput);
96 }
97
98 private void writeBitmaps(PackBitmapIndexBuilder bitmaps)
99 throws IOException {
100 int bitmapCount = 0;
101 for (StoredEntry entry : bitmaps.getCompressedBitmaps()) {
102 writeBitmapEntry(entry);
103 bitmapCount++;
104 }
105
106 int expectedBitmapCount = bitmaps.getBitmapCount();
107 if (expectedBitmapCount != bitmapCount)
108 throw new IOException(MessageFormat.format(
109 JGitText.get().expectedGot,
110 String.valueOf(expectedBitmapCount),
111 String.valueOf(bitmapCount)));
112 }
113
114 private void writeBitmapEntry(StoredEntry entry) throws IOException {
115
116 dataOutput.writeInt((int) entry.getObjectId());
117 out.write(entry.getXorOffset());
118 out.write(entry.getFlags());
119 writeBitmap(entry.getBitmap());
120 }
121
122 private void writeFooter() throws IOException {
123 out.on(false);
124 out.write(out.getMessageDigest().digest());
125 }
126 }