diff --git a/src/main/java/com/google/devtools/build/lib/remote/RemoteActionFileSystem.java b/src/main/java/com/google/devtools/build/lib/remote/RemoteActionFileSystem.java index daedfdb1c9b538..d777e1df0ac671 100644 --- a/src/main/java/com/google/devtools/build/lib/remote/RemoteActionFileSystem.java +++ b/src/main/java/com/google/devtools/build/lib/remote/RemoteActionFileSystem.java @@ -16,9 +16,13 @@ package com.google.devtools.build.lib.remote; import com.google.common.base.Preconditions; +import com.google.devtools.build.lib.actions.ActionInput; import com.google.devtools.build.lib.actions.ActionInputMap; +import com.google.devtools.build.lib.actions.Artifact; +import com.google.devtools.build.lib.actions.Artifact.TreeFileArtifact; import com.google.devtools.build.lib.actions.FileArtifactValue; import com.google.devtools.build.lib.actions.FileArtifactValue.RemoteFileArtifactValue; +import com.google.devtools.build.lib.actions.cache.MetadataInjector; import com.google.devtools.build.lib.vfs.DelegateFileSystem; import com.google.devtools.build.lib.vfs.Dirent; import com.google.devtools.build.lib.vfs.FileStatus; @@ -30,6 +34,9 @@ import java.io.InputStream; import java.nio.channels.ReadableByteChannel; import java.util.Collection; +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; import javax.annotation.Nullable; /** @@ -42,12 +49,13 @@ * *

This implementation only supports creating local action outputs. */ -class RemoteActionFileSystem extends DelegateFileSystem { +class RemoteActionFileSystem extends DelegateFileSystem implements MetadataInjector { private final Path execRoot; private final Path outputBase; private final ActionInputMap inputArtifactData; private final RemoteActionInputFetcher inputFetcher; + private final ConcurrentMap injectedMetadata = new ConcurrentHashMap<>(); RemoteActionFileSystem( FileSystem localDelegate, @@ -339,6 +347,10 @@ private RemoteFileArtifactValue getRemoteInputMetadata(String execPathString) { if (m != null && m.isRemote()) { return (RemoteFileArtifactValue) m; } + RemoteFileArtifactValue rm = injectedMetadata.get(execPathString); + if (rm != null) { + return rm; + } return null; } @@ -383,4 +395,33 @@ protected Collection readdir(Path path, boolean followSymlinks) throws I protected void createHardLink(Path linkPath, Path originalPath) throws IOException { super.createHardLink(linkPath, originalPath); } + + // MetadataInjector interface + @Override + public void addExpandedTreeOutput(TreeFileArtifact output) { + throw new UnsupportedOperationException(); + } + + @Override + public void injectDigest(ActionInput output, FileStatus statNoFollow, byte[] digest) { + throw new UnsupportedOperationException(); + } + + @Override + public void injectRemoteFile(Artifact output, byte[] digest, long size, int locationIndex) { + RemoteFileArtifactValue m = new FileArtifactValue.RemoteFileArtifactValue(digest, size, locationIndex); + Path transformedPath = getPath(output.getPath().getPathString()); + injectedMetadata.put(execPathString(transformedPath), m); + } + + @Override + public void injectRemoteDirectory( + Artifact.SpecialArtifact treeArtifact, Map children) { + throw new UnsupportedOperationException(); + } + + @Override + public void markOmitted(ActionInput output) { + throw new UnsupportedOperationException(); + } } diff --git a/src/main/java/com/google/devtools/build/lib/skyframe/ActionMetadataHandler.java b/src/main/java/com/google/devtools/build/lib/skyframe/ActionMetadataHandler.java index bbf13fede32cd6..35696128b40049 100644 --- a/src/main/java/com/google/devtools/build/lib/skyframe/ActionMetadataHandler.java +++ b/src/main/java/com/google/devtools/build/lib/skyframe/ActionMetadataHandler.java @@ -37,12 +37,14 @@ import com.google.devtools.build.lib.actions.FilesetOutputSymlink; import com.google.devtools.build.lib.actions.cache.DigestUtils; import com.google.devtools.build.lib.actions.cache.MetadataHandler; +import com.google.devtools.build.lib.actions.cache.MetadataInjector; import com.google.devtools.build.lib.util.io.TimestampGranularityMonitor; import com.google.devtools.build.lib.vfs.Dirent; import com.google.devtools.build.lib.vfs.Dirent.Type; import com.google.devtools.build.lib.vfs.FileStatus; import com.google.devtools.build.lib.vfs.FileStatusWithDigest; import com.google.devtools.build.lib.vfs.FileStatusWithDigestAdapter; +import com.google.devtools.build.lib.vfs.FileSystem; import com.google.devtools.build.lib.vfs.Path; import com.google.devtools.build.lib.vfs.PathFragment; import com.google.devtools.build.lib.vfs.RootedPath; @@ -551,6 +553,13 @@ public void injectRemoteFile(Artifact output, byte[] digest, long size, int loca Preconditions.checkState( executionMode.get(), "Tried to inject %s outside of execution", output); store.injectRemoteFile(output, digest, size, locationIndex); + + // Ensure that this artifact is also known to the remote filesystem that + // artifactPathResolver resolves to. + FileSystem fs = artifactPathResolver.toPath(output).getFileSystem(); + if (fs instanceof MetadataInjector) { + ((MetadataInjector) fs).injectRemoteFile(output, digest, size, locationIndex); + } } @Override