From cc40beb2fa718b77152ba81a8ce663c58e314ab8 Mon Sep 17 00:00:00 2001 From: Mick Jordan <mick.jordan@oracle.com> Date: Tue, 26 May 2015 15:35:41 -0700 Subject: [PATCH] file functions bug fixes --- .../r/nodes/builtin/base/FileFunctions.java | 32 ++++++++++++------- .../com/oracle/truffle/r/runtime/Utils.java | 2 +- 2 files changed, 22 insertions(+), 12 deletions(-) diff --git a/com.oracle.truffle.r.nodes.builtin/src/com/oracle/truffle/r/nodes/builtin/base/FileFunctions.java b/com.oracle.truffle.r.nodes.builtin/src/com/oracle/truffle/r/nodes/builtin/base/FileFunctions.java index 2c2135d960..91e7aafb10 100644 --- a/com.oracle.truffle.r.nodes.builtin/src/com/oracle/truffle/r/nodes/builtin/base/FileFunctions.java +++ b/com.oracle.truffle.r.nodes.builtin/src/com/oracle/truffle/r/nodes/builtin/base/FileFunctions.java @@ -525,6 +525,9 @@ public class FileFunctions { // TODO Implement all the options @RBuiltin(name = "list.files", kind = INTERNAL, parameterNames = {"path", "pattern", "all.files", "full.names", "recursive", "ignore.case", "include.dirs", "no.."}) public abstract static class ListFiles extends RBuiltinNode { + private static final String DOT = "."; + private static final String DOTDOT = ".."; + @SuppressWarnings("unused") @Specialization @TruffleBoundary @@ -548,7 +551,7 @@ public class FileFunctions { return doListFilesBody(vec, pattern, allFiles, fullNames, recursive, ignoreCase, includeDirs, noDotDot); } - protected RStringVector doListFilesBody(RAbstractStringVector vec, String pattern, byte allFilesL, byte fullNamesL, byte recursiveL, byte ignoreCaseL, byte includeDirsL, byte noDotDotL) { + protected RStringVector doListFilesBody(RAbstractStringVector vec, String patternString, byte allFilesL, byte fullNamesL, byte recursiveL, byte ignoreCaseL, byte includeDirsL, byte noDotDotL) { controlVisibility(); boolean allFiles = RRuntime.fromLogical(allFilesL); boolean fullNames = RRuntime.fromLogical(fullNamesL); @@ -557,6 +560,7 @@ public class FileFunctions { boolean ignoreCase = check(ignoreCaseL, "ignoreCase"); boolean includeDirs = !recursive || RRuntime.fromLogical(includeDirsL); boolean noDotDot = RRuntime.fromLogical(noDotDotL); + Pattern pattern = patternString == null ? null : Pattern.compile(patternString); // Curiously the result is not a vector of same length as the input, // as typical for R, but a single vector, which means duplicates may occur ArrayList<String> files = new ArrayList<>(); @@ -568,12 +572,11 @@ public class FileFunctions { continue; } Path rootPath = root.toPath(); - try (Stream<Path> stream = Files.find(rootPath, recursive ? Integer.MAX_VALUE : 1, new FileMatcher(pattern, allFiles, includeDirs, noDotDot))) { + try (Stream<Path> stream = Files.find(rootPath, recursive ? Integer.MAX_VALUE : 1, new FileMatcher(pattern, allFiles, includeDirs))) { Iterator<Path> iter = stream.iterator(); Path vecPath = null; if (!fullNames) { - FileSystem fileSystem = FileSystems.getDefault(); - vecPath = fileSystem.getPath(vecPathString); + vecPath = FileSystems.getDefault().getPath(vecPathString); } while (iter.hasNext()) { Path file = iter.next(); @@ -585,6 +588,18 @@ public class FileFunctions { } files.add(file.toString()); } + /* + * Annoyingly "." and ".." are never visited by Files.find, so we have to + * process them manually. + */ + if (!noDotDot) { + if (pattern == null || pattern.matcher(DOT).find()) { + files.add(fullNames ? FileSystems.getDefault().getPath(vecPathString, DOT).toString() : DOT); + } + if (pattern == null || pattern.matcher(DOTDOT).find()) { + files.add(fullNames ? FileSystems.getDefault().getPath(vecPathString, DOTDOT).toString() : DOTDOT); + } + } } catch (IOException ex) { // ignored } @@ -611,14 +626,12 @@ public class FileFunctions { private static class FileMatcher implements BiPredicate<Path, BasicFileAttributes> { final Pattern pattern; final boolean includeDirs; - final boolean noDotDot; final boolean allFiles; - FileMatcher(String pattern, boolean allFiles, boolean includeDirs, boolean noDotDot) { + FileMatcher(Pattern pattern, boolean allFiles, boolean includeDirs) { this.allFiles = allFiles; this.includeDirs = includeDirs; - this.noDotDot = noDotDot; - this.pattern = pattern == null ? null : Pattern.compile(pattern); + this.pattern = pattern; } public boolean test(Path path, BasicFileAttributes u) { @@ -628,9 +641,6 @@ public class FileFunctions { if (!allFiles && path.getFileName().toString().charAt(0) == '.') { return false; } - if (noDotDot && path.getFileName().toString().equals("..")) { - return false; - } if (pattern == null) { return true; } diff --git a/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/Utils.java b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/Utils.java index 39101765e3..fc7360db1d 100644 --- a/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/Utils.java +++ b/com.oracle.truffle.r.runtime/src/com/oracle/truffle/r/runtime/Utils.java @@ -276,7 +276,7 @@ public final class Utils { * support in Java as much of it works relative to the initial setting. */ if (path.length() == 0) { - return wdState().getCurrentPath().toString(); + return keepRelative ? path : wdState().getCurrentPath().toString(); } else { Path p = wdState().getFileSystem().getPath(path); if (p.isAbsolute()) { -- GitLab