use of com.google.devtools.build.lib.vfs.Dirent in project bazel by bazelbuild.
the class AndroidSdkRepositoryFunction method getNewestBuildToolsDirectory.
/**
* Gets the newest build tools directory according to {@link Revision}.
*
* @throws RepositoryFunctionException if none of the buildToolsDirectories are directories and
* have names that are parsable as build tools version.
*/
private static String getNewestBuildToolsDirectory(Rule rule, Dirents buildToolsDirectories) throws RepositoryFunctionException {
String newestBuildToolsDirectory = null;
Revision newestBuildToolsRevision = null;
for (Dirent buildToolsDirectory : buildToolsDirectories) {
if (buildToolsDirectory.getType() != Dirent.Type.DIRECTORY) {
continue;
}
try {
Revision buildToolsRevision = Revision.parseRevision(buildToolsDirectory.getName());
if (newestBuildToolsRevision == null || buildToolsRevision.compareTo(newestBuildToolsRevision) > 0) {
newestBuildToolsDirectory = buildToolsDirectory.getName();
newestBuildToolsRevision = buildToolsRevision;
}
} catch (NumberFormatException e) {
// Ignore unparsable build tools directories.
}
}
if (newestBuildToolsDirectory == null) {
throw new RepositoryFunctionException(new EvalException(rule.getLocation(), String.format("Bazel requires Android build tools version %s or newer but none are installed. " + "Please install a recent version through the Android SDK manager.", MIN_BUILD_TOOLS_REVISION)), Transience.PERSISTENT);
}
return newestBuildToolsDirectory;
}
use of com.google.devtools.build.lib.vfs.Dirent in project bazel by bazelbuild.
the class SkyframeExecutor method getDiff.
protected Differencer.Diff getDiff(TimestampGranularityMonitor tsgm, Iterable<PathFragment> modifiedSourceFiles, final Path pathEntry) throws InterruptedException {
if (Iterables.isEmpty(modifiedSourceFiles)) {
return new ImmutableDiff(ImmutableList.<SkyKey>of(), ImmutableMap.<SkyKey, SkyValue>of());
}
// TODO(bazel-team): change ModifiedFileSet to work with RootedPaths instead of PathFragments.
Iterable<SkyKey> dirtyFileStateSkyKeys = Iterables.transform(modifiedSourceFiles, new Function<PathFragment, SkyKey>() {
@Override
public SkyKey apply(PathFragment pathFragment) {
Preconditions.checkState(!pathFragment.isAbsolute(), "found absolute PathFragment: %s", pathFragment);
return FileStateValue.key(RootedPath.toRootedPath(pathEntry, pathFragment));
}
});
// We only need to invalidate directory values when a file has been created or deleted or
// changes type, not when it has merely been modified. Unfortunately we do not have that
// information here, so we compute it ourselves.
// TODO(bazel-team): Fancy filesystems could provide it with a hypothetically modified
// DiffAwareness interface.
LOG.info("About to recompute filesystem nodes corresponding to files that are known to have " + "changed");
FilesystemValueChecker fsvc = new FilesystemValueChecker(tsgm, null);
Map<SkyKey, SkyValue> valuesMap = memoizingEvaluator.getValues();
Differencer.DiffWithDelta diff = fsvc.getNewAndOldValues(valuesMap, dirtyFileStateSkyKeys, new FileDirtinessChecker());
Set<SkyKey> valuesToInvalidate = new HashSet<>();
Map<SkyKey, SkyValue> valuesToInject = new HashMap<>();
for (Map.Entry<SkyKey, Delta> entry : diff.changedKeysWithNewAndOldValues().entrySet()) {
SkyKey key = entry.getKey();
Preconditions.checkState(key.functionName().equals(SkyFunctions.FILE_STATE), key);
RootedPath rootedPath = (RootedPath) key.argument();
Delta delta = entry.getValue();
FileStateValue oldValue = (FileStateValue) delta.getOldValue();
FileStateValue newValue = (FileStateValue) delta.getNewValue();
if (newValue != null) {
valuesToInject.put(key, newValue);
} else {
valuesToInvalidate.add(key);
}
SkyKey dirListingStateKey = parentDirectoryListingStateKey(rootedPath);
// Invalidate the directory listing for the path's parent directory if the change was
// relevant (e.g. path turned from a symlink into a directory) OR if we don't have enough
// information to determine it was irrelevant.
boolean changedType = false;
if (newValue == null) {
changedType = true;
} else if (oldValue != null) {
changedType = !oldValue.getType().equals(newValue.getType());
} else {
DirectoryListingStateValue oldDirListingStateValue = (DirectoryListingStateValue) valuesMap.get(dirListingStateKey);
if (oldDirListingStateValue != null) {
String baseName = rootedPath.getRelativePath().getBaseName();
Dirent oldDirent = oldDirListingStateValue.getDirents().maybeGetDirent(baseName);
changedType = (oldDirent == null) || !compatibleFileTypes(oldDirent.getType(), newValue.getType());
} else {
changedType = true;
}
}
if (changedType) {
valuesToInvalidate.add(dirListingStateKey);
}
}
for (SkyKey key : diff.changedKeysWithoutNewValues()) {
Preconditions.checkState(key.functionName().equals(SkyFunctions.FILE_STATE), key);
RootedPath rootedPath = (RootedPath) key.argument();
valuesToInvalidate.add(parentDirectoryListingStateKey(rootedPath));
}
return new ImmutableDiff(valuesToInvalidate, valuesToInject);
}
use of com.google.devtools.build.lib.vfs.Dirent in project bazel by bazelbuild.
the class ProcessPackageDirectory method getSubdirDeps.
private Iterable<SkyKey> getSubdirDeps(DirectoryListingValue dirListingValue, RootedPath rootedPath, RepositoryName repositoryName, Set<PathFragment> excludedPaths) {
Path root = rootedPath.getRoot();
PathFragment rootRelativePath = rootedPath.getRelativePath();
boolean followSymlinks = shouldFollowSymlinksWhenTraversing(dirListingValue.getDirents());
List<SkyKey> childDeps = new ArrayList<>();
for (Dirent dirent : dirListingValue.getDirents()) {
Type type = dirent.getType();
if (type != Type.DIRECTORY && (type != Type.SYMLINK || !followSymlinks)) {
// rise to infinite directory trees are diagnosed by FileValue.
continue;
}
String basename = dirent.getName();
if (rootRelativePath.equals(PathFragment.EMPTY_FRAGMENT) && PathPackageLocator.DEFAULT_TOP_LEVEL_EXCLUDES.contains(basename)) {
continue;
}
PathFragment subdirectory = rootRelativePath.getRelative(basename);
// If this subdirectory is one of the excluded paths, don't recurse into it.
if (excludedPaths.contains(subdirectory)) {
continue;
}
// If we have an excluded path that isn't below this subdirectory, we shouldn't pass that
// excluded path to our evaluation of the subdirectory, because the exclusion can't
// possibly match anything beneath the subdirectory.
//
// For example, if we're currently evaluating directory "a", are looking at its subdirectory
// "a/b", and we have an excluded path "a/c/d", there's no need to pass the excluded path
// "a/c/d" to our evaluation of "a/b".
//
// This strategy should help to get more skyframe sharing. Consider the example above. A
// subsequent request of "a/b/...", without any excluded paths, will be a cache hit.
//
// TODO(bazel-team): Replace the excludedPaths set with a trie or a SortedSet for better
// efficiency.
ImmutableSet<PathFragment> excludedSubdirectoriesBeneathThisSubdirectory = PathFragment.filterPathsStartingWith(excludedPaths, subdirectory);
RootedPath subdirectoryRootedPath = RootedPath.toRootedPath(root, subdirectory);
childDeps.add(skyKeyTransformer.makeSkyKey(repositoryName, subdirectoryRootedPath, excludedSubdirectoriesBeneathThisSubdirectory));
}
return childDeps;
}
use of com.google.devtools.build.lib.vfs.Dirent in project bazel by bazelbuild.
the class RecursiveFilesystemTraversalFunction method createRecursiveTraversalKeys.
/**
* List the directory and create {@code SkyKey}s to request contents of its children recursively.
*
* <p>The returned keys are of type {@link SkyFunctions#RECURSIVE_FILESYSTEM_TRAVERSAL}.
*/
private static Collection<SkyKey> createRecursiveTraversalKeys(Environment env, TraversalRequest traversal) throws MissingDepException, InterruptedException {
// Use the traversal's path, even if it's a symlink. The contents of the directory, as listed
// in the result, must be relative to it.
DirectoryListingValue dirListing = (DirectoryListingValue) getDependentSkyValue(env, DirectoryListingValue.key(traversal.path));
List<SkyKey> result = new ArrayList<>();
for (Dirent dirent : dirListing.getDirents()) {
RootedPath childPath = RootedPath.toRootedPath(traversal.path.getRoot(), traversal.path.getRelativePath().getRelative(dirent.getName()));
TraversalRequest childTraversal = traversal.forChildEntry(childPath);
result.add(RecursiveFilesystemTraversalValue.key(childTraversal));
}
return result;
}
use of com.google.devtools.build.lib.vfs.Dirent in project bazel by bazelbuild.
the class IncrementalLoadingTest method createTester.
@Before
public final void createTester() throws Exception {
ManualClock clock = new ManualClock();
FileSystem fs = new InMemoryFileSystem(clock) {
@Override
public Collection<Dirent> readdir(Path path, boolean followSymlinks) throws IOException {
if (path.equals(throwOnReaddir)) {
throw new FileNotFoundException(path.getPathString());
}
return super.readdir(path, followSymlinks);
}
@Nullable
@Override
public FileStatus stat(Path path, boolean followSymlinks) throws IOException {
if (path.equals(throwOnStat)) {
throw new IOException("bork " + path.getPathString());
}
return super.stat(path, followSymlinks);
}
};
tester = createTester(fs, clock);
}
Aggregations