diff --git 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 index c4972c6..057dbc0 100644 --- 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 @@ -739,14 +739,12 @@ public class FileStore implements SegmentStore, Closeable { @Nonnull String gcInfo) throws IOException { Stopwatch watch = Stopwatch.createStarted(); - long initialSize = size(); Set bulkRefs = newHashSet(); Map cleaned = newLinkedHashMap(); fileStoreLock.writeLock().lock(); try { - gcListener.info("TarMK GC #{}: cleanup started. Current repository size is {} ({} bytes)", - GC_COUNT, humanReadableByteCount(initialSize), initialSize); + gcListener.info("TarMK GC #{}: cleanup started.", GC_COUNT); newWriter(); segmentCache.clear(); @@ -766,7 +764,11 @@ public class FileStore implements SegmentStore, Closeable { } finally { fileStoreLock.writeLock().unlock(); } - + + // compute initial size here to better reflect repository size after the previous tar writer was closed + long initialSize = size(); + gcListener.info("Current repository size is {} ({} bytes)", humanReadableByteCount(initialSize), initialSize); + Set reclaim = newHashSet(); for (TarReader reader : cleaned.keySet()) { reader.mark(bulkRefs, reclaim, reclaimGeneration); @@ -786,6 +788,9 @@ public class FileStore implements SegmentStore, Closeable { } } + // it doesn't account for concurrent commits that might have happened + long afterCleanupSize = 0; + List oldReaders = newArrayList(); fileStoreLock.writeLock().lock(); try { @@ -798,8 +803,12 @@ public class FileStore implements SegmentStore, Closeable { if (newReader != null) { newReaders.add(newReader); } + // if these two differ, the former represents the swept version of the latter if (newReader != reader) { + afterCleanupSize += newReader != null ? newReader.size() : 0; oldReaders.add(reader); + } else { + afterCleanupSize += reader.size(); } } else { newReaders.add(reader); @@ -822,15 +831,16 @@ public class FileStore implements SegmentStore, Closeable { } long finalSize = size(); - stats.reclaimed(initialSize - finalSize); + long reclaimedSize = initialSize - afterCleanupSize; + stats.reclaimed(reclaimedSize); + gcJournal.persist(finalSize); - // FIXME OAK-4106: Reclaimed size reported by FileStore.cleanup is off - gcListener.cleaned(initialSize - finalSize, finalSize); + gcListener.cleaned(reclaimedSize, finalSize); gcListener.info("TarMK GC #{}: cleanup completed in {} ({} ms). Post cleanup size is {} ({} bytes)" + " and space reclaimed {} ({} bytes).", GC_COUNT, watch, watch.elapsed(MILLISECONDS), humanReadableByteCount(finalSize), finalSize, - humanReadableByteCount(initialSize - finalSize), initialSize - finalSize); + humanReadableByteCount(reclaimedSize), reclaimedSize); return toRemove; }