Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
import com.google.common.base.Preconditions;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.ImmutableSet;
import com.google.common.collect.Maps;
import com.google.common.flogger.GoogleLogger;
import com.google.devtools.build.lib.actions.FileArtifactValue.RemoteFileArtifactValue;
Expand Down Expand Up @@ -253,9 +254,37 @@ private static CompactPersistentActionCache create(
}
misses.put(reason, new AtomicInteger(0));
}
deleteUnrecognizedFiles(cacheRoot);
return new CompactPersistentActionCache(indexer, map, Maps.immutableEnumMap(misses));
}

/**
* Deletes unrecognized files from the action cache on-disk directory.
*
* <p>This works around an incrementality bug when building a runfiles tree while alternating
* between Bazel versions. Specifically, because the runfiles output manifest is a symlink to the
* input manifest (and therefore always appears to have the contents of the latter), one can get a
* spurious cache hit for a stale runfiles tree if the tree was updated in an intervening build
* without the action cache being updated accordingly.
*
* <p>Backported from https://github.com/bazelbuild/bazel/pull/27525 (Bazel 9.0.0).
*/
private static void deleteUnrecognizedFiles(Path cacheRoot) throws IOException {
Path indexFile = cacheRoot.getChild("filename_index_v" + VERSION + ".blaze");
Path indexJournalFile = cacheRoot.getChild("filename_index_v" + VERSION + ".journal");
ImmutableSet<Path> knownFiles =
ImmutableSet.of(
cacheFile(cacheRoot),
journalFile(cacheRoot),
indexFile,
indexJournalFile);
for (Path child : cacheRoot.getDirectoryEntries()) {
if (!knownFiles.contains(child)) {
child.delete();
}
}
}

private static CompactPersistentActionCache logAndThrowOrRecurse(
Path cacheRoot,
Clock clock,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -451,6 +451,15 @@ public void putAndGet_treeMetadata_savesMaterializationExecPath() {
Optional.of(materializationExecPath)));
}

@Test
public void testDeleteUnrecognizedFiles() throws Exception {
Path unrecognizedFile = dataRoot.getChild("unrecognized_file");
FileSystemUtils.writeContentAsLatin1(unrecognizedFile, "content");
assertThat(unrecognizedFile.exists()).isTrue();
CompactPersistentActionCache.create(dataRoot, clock, NullEventHandler.INSTANCE);
assertThat(unrecognizedFile.exists()).isFalse();
}

private static void assertKeyEquals(ActionCache cache1, ActionCache cache2, String key) {
Object entry = cache1.get(key);
assertThat(entry).isNotNull();
Expand Down
Loading