Index: oak-segment-tar/src/main/java/org/apache/jackrabbit/oak/segment/file/AbstractFileStore.java =================================================================== --- oak-segment-tar/src/main/java/org/apache/jackrabbit/oak/segment/file/AbstractFileStore.java (revision 1841203) +++ oak-segment-tar/src/main/java/org/apache/jackrabbit/oak/segment/file/AbstractFileStore.java (working copy) @@ -28,7 +28,9 @@ import java.io.File; import java.io.IOException; import java.nio.ByteBuffer; +import java.util.ArrayList; import java.util.Arrays; +import java.util.List; import java.util.Map; import java.util.UUID; import java.util.regex.Matcher; @@ -37,6 +39,7 @@ import javax.annotation.CheckForNull; import javax.annotation.Nonnull; +import com.google.common.base.Supplier; import org.apache.jackrabbit.oak.api.jmx.CacheStatsMBean; import org.apache.jackrabbit.oak.segment.CachingSegmentReader; import org.apache.jackrabbit.oak.segment.RecordType; @@ -56,8 +59,6 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import com.google.common.base.Supplier; - /** * The storage implementation for tar files. */ @@ -331,31 +332,47 @@ w.writeEntry(msb, lsb, data, 0, data.length, generation); if (SegmentId.isDataSegmentId(lsb)) { Segment segment = new Segment(this, segmentReader, newSegmentId(msb, lsb), buffer); - populateTarGraph(segment, w); - populateTarBinaryReferences(segment, w); + populateTarGraph(segment, w, readGraphReferences(segment)); + populateTarBinaryReferences(segment, w, readBinaryReferences(segment)); } } - static void populateTarGraph(Segment segment, TarWriter w) { + static void populateTarGraph(Segment segment, TarWriter w, Iterable references) { UUID from = segment.getSegmentId().asUUID(); + for (UUID reference : references) { + w.addGraphEdge(from, reference); + } + } + + static Iterable readGraphReferences(Segment segment) { + List reference = new ArrayList<>(); for (int i = 0; i < segment.getReferencedSegmentIdCount(); i++) { - w.addGraphEdge(from, segment.getReferencedSegmentId(i)); + reference.add(segment.getReferencedSegmentId(i)); + } + return reference; + } + + static void populateTarBinaryReferences(Segment segment, TarWriter w, Iterable references) { + int generation = segment.getGcGeneration(); + UUID id = segment.getSegmentId().asUUID(); + for (String reference : references) { + w.addBinaryReference(generation, id, reference); } } - static void populateTarBinaryReferences(final Segment segment, final TarWriter w) { - final int generation = segment.getGcGeneration(); - final UUID id = segment.getSegmentId().asUUID(); + static Iterable readBinaryReferences(final Segment segment) { + final List references = new ArrayList<>(); segment.forEachRecord(new RecordConsumer() { @Override public void consume(int number, RecordType type, int offset) { if (type == RecordType.BLOB_ID) { - w.addBinaryReference(generation, id, SegmentBlob.readBlobId(segment, number)); + references.add(SegmentBlob.readBlobId(segment, number)); } } }); + return references; } static void closeAndLogOnFail(Closeable closeable) { Index: oak-segment-tar/src/main/java/org/apache/jackrabbit/oak/segment/file/FileStore.java =================================================================== --- oak-segment-tar/src/main/java/org/apache/jackrabbit/oak/segment/file/FileStore.java (revision 1841203) +++ oak-segment-tar/src/main/java/org/apache/jackrabbit/oak/segment/file/FileStore.java (working copy) @@ -615,6 +615,8 @@ @Override public void writeSegment(SegmentId id, byte[] buffer, int offset, int length) throws IOException { Segment segment = null; + Iterable graphReferences = null; + Iterable binaryReferences = null; // If the segment is a data segment, create a new instance of Segment to // access some internal information stored in the segment and to store @@ -634,6 +636,8 @@ segment = new Segment(this, segmentReader, id, data); generation = segment.getGcGeneration(); + graphReferences = readGraphReferences(segment); + binaryReferences = readBinaryReferences(segment); } fileStoreLock.writeLock().lock(); @@ -653,8 +657,8 @@ // (potentially) flushing the TAR file. if (segment != null) { - populateTarGraph(segment, tarWriter); - populateTarBinaryReferences(segment, tarWriter); + populateTarGraph(segment, tarWriter, graphReferences); + populateTarBinaryReferences(segment, tarWriter, binaryReferences); } // Close the TAR file if the size exceeds the maximum.