Do not reconstitute absolute path until after FilesetManifest.
This way callers aren't required to pass in the exec root.
RELNOTES: None.
PiperOrigin-RevId: 217500815
diff --git a/src/main/java/com/google/devtools/build/lib/analysis/skylark/SkylarkCustomCommandLine.java b/src/main/java/com/google/devtools/build/lib/analysis/skylark/SkylarkCustomCommandLine.java
index 53bfb09..133aaf3 100644
--- a/src/main/java/com/google/devtools/build/lib/analysis/skylark/SkylarkCustomCommandLine.java
+++ b/src/main/java/com/google/devtools/build/lib/analysis/skylark/SkylarkCustomCommandLine.java
@@ -22,7 +22,6 @@
import com.google.devtools.build.lib.actions.ActionKeyContext;
import com.google.devtools.build.lib.actions.Artifact;
import com.google.devtools.build.lib.actions.Artifact.ArtifactExpander;
-import com.google.devtools.build.lib.actions.ArtifactRoot;
import com.google.devtools.build.lib.actions.CommandLine;
import com.google.devtools.build.lib.actions.CommandLineExpansionException;
import com.google.devtools.build.lib.actions.CommandLineItem;
@@ -359,8 +358,7 @@
FilesetManifest.constructFilesetManifest(
artifactExpander.getFileset(fileset),
fileset.getExecPath(),
- RelativeSymlinkBehavior.IGNORE,
- extractExecRoot(fileset));
+ RelativeSymlinkBehavior.IGNORE);
for (PathFragment relativePath : filesetManifest.getEntries().keySet()) {
expandedValues.add(new FilesetSymlinkFile(fileset, relativePath));
}
@@ -369,14 +367,6 @@
}
}
- // TODO(b/117267351): Pass in the exec root more cleanly, or put relative paths in the manifest.
- private static PathFragment extractExecRoot(Artifact fileset) {
- Preconditions.checkArgument(!fileset.isSourceArtifact(), fileset);
- ArtifactRoot root = fileset.getRoot();
- PathFragment rootFrag = root.getRoot().asPath().asFragment();
- return rootFrag.subFragment(0, rootFrag.segmentCount() - root.getExecPath().segmentCount());
- }
-
private int addToFingerprint(
List<Object> arguments,
int argi,
diff --git a/src/main/java/com/google/devtools/build/lib/exec/FilesetManifest.java b/src/main/java/com/google/devtools/build/lib/exec/FilesetManifest.java
index fa4e993..7dd1a98 100644
--- a/src/main/java/com/google/devtools/build/lib/exec/FilesetManifest.java
+++ b/src/main/java/com/google/devtools/build/lib/exec/FilesetManifest.java
@@ -51,17 +51,15 @@
public static FilesetManifest constructFilesetManifest(
List<FilesetOutputSymlink> outputSymlinks,
PathFragment targetPrefix,
- RelativeSymlinkBehavior relSymlinkBehavior,
- PathFragment execRoot)
+ RelativeSymlinkBehavior relSymlinkBehavior)
throws IOException {
LinkedHashMap<PathFragment, String> entries = new LinkedHashMap<>();
Map<PathFragment, String> relativeLinks = new HashMap<>();
Map<String, FileArtifactValue> artifactValues = new HashMap<>();
for (FilesetOutputSymlink outputSymlink : outputSymlinks) {
PathFragment fullLocation = targetPrefix.getRelative(outputSymlink.getName());
- PathFragment linkTarget = outputSymlink.reconstituteTargetPath(execRoot);
- String artifact = Strings.emptyToNull(linkTarget.getPathString());
- if (!linkTarget.isAbsolute() && !linkTarget.isEmpty()) {
+ String artifact = Strings.emptyToNull(outputSymlink.getTargetPath().getPathString());
+ if (isRelativeSymlink(outputSymlink)) {
addRelativeSymlinkEntry(artifact, fullLocation, relSymlinkBehavior, relativeLinks);
} else if (!entries.containsKey(fullLocation)) { // Keep consistent behavior: no overwriting.
entries.put(fullLocation, artifact);
@@ -70,7 +68,14 @@
artifactValues.put(artifact, (FileArtifactValue) outputSymlink.getMetadata());
}
}
- return constructFilesetManifest(entries, relativeLinks, artifactValues);
+ resolveRelativeSymlinks(entries, relativeLinks);
+ return new FilesetManifest(entries, artifactValues);
+ }
+
+ private static boolean isRelativeSymlink(FilesetOutputSymlink symlink) {
+ return !symlink.getTargetPath().isEmpty()
+ && !symlink.getTargetPath().isAbsolute()
+ && !symlink.isRelativeToExecRoot();
}
/** Potentially adds the relative symlink to the map, depending on {@code relSymlinkBehavior}. */
@@ -95,12 +100,14 @@
private static final int MAX_SYMLINK_TRAVERSALS = 256;
- private static FilesetManifest constructFilesetManifest(
- Map<PathFragment, String> entries,
- Map<PathFragment, String> relativeLinks,
- Map<String, FileArtifactValue> artifactValues) {
- // Resolve relative symlinks. Note that relativeLinks only contains entries in RESOLVE mode.
- // We must find targets for these symlinks that are not inside the Fileset itself.
+ /**
+ * Resolves relative symlinks and puts them in the {@code entries} map.
+ *
+ * <p>Note that {@code relativeLinks} should only contain entries in {@link
+ * RelativeSymlinkBehavior#RESOLVE} mode.
+ */
+ private static void resolveRelativeSymlinks(
+ Map<PathFragment, String> entries, Map<PathFragment, String> relativeLinks) {
for (Map.Entry<PathFragment, String> e : relativeLinks.entrySet()) {
PathFragment location = e.getKey();
String value = e.getValue();
@@ -142,22 +149,37 @@
entries.put(location, entries.get(actualLocation));
}
}
- return new FilesetManifest(entries, artifactValues);
}
private final Map<PathFragment, String> entries;
private final Map<String, FileArtifactValue> artifactValues;
- private FilesetManifest(Map<PathFragment, String> entries,
- Map<String, FileArtifactValue> artifactValues) {
+ private FilesetManifest(
+ Map<PathFragment, String> entries, Map<String, FileArtifactValue> artifactValues) {
this.entries = Collections.unmodifiableMap(entries);
this.artifactValues = artifactValues;
}
+ /**
+ * Returns a mapping of symlink name to its target path.
+ *
+ * <p>Values in this map can be:
+ *
+ * <ul>
+ * <li>An absolute path.
+ * <li>A relative path, which should be considered relative to the exec root.
+ * <li>{@code null}, which represents an empty file.
+ * </ul>
+ */
public Map<PathFragment, String> getEntries() {
return entries;
}
+ /**
+ * Returns a mapping of target path to {@link FileArtifactValue}.
+ *
+ * <p>The keyset of this map is a subset of the values in the map returned by {@link #getEntries}.
+ */
public Map<String, FileArtifactValue> getArtifactValues() {
return artifactValues;
}
diff --git a/src/main/java/com/google/devtools/build/lib/exec/SpawnInputExpander.java b/src/main/java/com/google/devtools/build/lib/exec/SpawnInputExpander.java
index cf53a85..81a8170 100644
--- a/src/main/java/com/google/devtools/build/lib/exec/SpawnInputExpander.java
+++ b/src/main/java/com/google/devtools/build/lib/exec/SpawnInputExpander.java
@@ -163,11 +163,14 @@
ImmutableList<FilesetOutputSymlink> outputSymlinks = filesetMappings.get(fileset);
FilesetManifest filesetManifest =
FilesetManifest.constructFilesetManifest(
- outputSymlinks, fileset.getExecPath(), relSymlinkBehavior, execRoot.asFragment());
+ outputSymlinks, fileset.getExecPath(), relSymlinkBehavior);
for (Map.Entry<PathFragment, String> mapping : filesetManifest.getEntries().entrySet()) {
String value = mapping.getValue();
- ActionInput artifact = value == null ? EMPTY_FILE : ActionInputHelper.fromPath(value);
+ ActionInput artifact =
+ value == null
+ ? EMPTY_FILE
+ : ActionInputHelper.fromPath(execRoot.getRelative(value).getPathString());
addMapping(inputMappings, mapping.getKey(), artifact);
}
}