7029979: (fs) Path.toRealPath(boolean) should be toRealPath(LinkOption...)
authoralanb
Mon, 04 Apr 2011 18:09:53 +0100
changeset 9025 a72fc1fc4b71
parent 9021 5cf29386a520
child 9026 cdf11e673c21
7029979: (fs) Path.toRealPath(boolean) should be toRealPath(LinkOption...) Reviewed-by: sherman
jdk/src/share/classes/java/nio/file/Path.java
jdk/src/share/classes/sun/nio/fs/Util.java
jdk/src/share/classes/sun/util/calendar/ZoneInfoFile.java
jdk/src/share/demo/nio/zipfs/src/com/sun/nio/zipfs/ZipFileSystemProvider.java
jdk/src/share/demo/nio/zipfs/src/com/sun/nio/zipfs/ZipPath.java
jdk/src/solaris/classes/sun/nio/fs/LinuxFileSystemProvider.java
jdk/src/solaris/classes/sun/nio/fs/SolarisFileSystemProvider.java
jdk/src/solaris/classes/sun/nio/fs/UnixFileSystemProvider.java
jdk/src/solaris/classes/sun/nio/fs/UnixPath.java
jdk/src/solaris/classes/sun/nio/fs/UnixSecureDirectoryStream.java
jdk/src/windows/classes/sun/nio/fs/WindowsFileSystemProvider.java
jdk/src/windows/classes/sun/nio/fs/WindowsPath.java
jdk/test/java/nio/file/Files/CheckPermissions.java
jdk/test/java/nio/file/Files/PassThroughFileSystem.java
jdk/test/java/nio/file/Path/Misc.java
--- a/jdk/src/share/classes/java/nio/file/Path.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/share/classes/java/nio/file/Path.java	Mon Apr 04 18:09:53 2011 +0100
@@ -550,18 +550,21 @@
      * <p> If this path is relative then its absolute path is first obtained,
      * as if by invoking the {@link #toAbsolutePath toAbsolutePath} method.
      *
-     * <p> The {@code resolveLinks} parameter specifies if symbolic links
-     * should be resolved. This parameter is ignored when symbolic links are
-     * not supported. Where supported, and the parameter has the value {@code
-     * true} then symbolic links are resolved to their final target. Where the
-     * parameter has the value {@code false} then this method does not resolve
-     * symbolic links. Some implementations allow special names such as
-     * "{@code ..}" to refer to the parent directory. When deriving the <em>real
-     * path</em>, and a "{@code ..}" (or equivalent) is preceded by a
-     * non-"{@code ..}" name then an implementation will typically causes both
-     * names to be removed. When not resolving symbolic links and the preceding
-     * name is a symbolic link then the names are only removed if it guaranteed
-     * that the resulting path will locate the same file as this path.
+     * <p> The {@code options} array may be used to indicate how symbolic links
+     * are handled. By default, symbolic links are resolved to their final
+     * target. If the option {@link LinkOption#NOFOLLOW_LINKS NOFOLLOW_LINKS} is
+     * present then this method does not resolve symbolic links.
+     *
+     * Some implementations allow special names such as "{@code ..}" to refer to
+     * the parent directory. When deriving the <em>real path</em>, and a
+     * "{@code ..}" (or equivalent) is preceded by a non-"{@code ..}" name then
+     * an implementation will typically cause both names to be removed. When
+     * not resolving symbolic links and the preceding name is a symbolic link
+     * then the names are only removed if it guaranteed that the resulting path
+     * will locate the same file as this path.
+     *
+     * @param   options
+     *          options indicating how symbolic links are handled
      *
      * @return  an absolute path represent the <em>real</em> path of the file
      *          located by this object
@@ -576,7 +579,7 @@
      *          checkPropertyAccess} method is invoked to check access to the
      *          system property {@code user.dir}
      */
-    Path toRealPath(boolean resolveLinks) throws IOException;
+    Path toRealPath(LinkOption... options) throws IOException;
 
     /**
      * Returns a {@link File} object representing this path. Where this {@code
--- a/jdk/src/share/classes/sun/nio/fs/Util.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/share/classes/sun/nio/fs/Util.java	Mon Apr 04 18:09:53 2011 +0100
@@ -26,6 +26,7 @@
 package sun.nio.fs;
 
 import java.util.*;
+import java.nio.file.*;
 
 /**
  * Utility methods
@@ -80,4 +81,21 @@
         }
         return set;
     }
+
+    /**
+     * Returns {@code true} if symbolic links should be followed
+     */
+    static boolean followLinks(LinkOption... options) {
+        boolean followLinks = true;
+        for (LinkOption option: options) {
+            if (option == LinkOption.NOFOLLOW_LINKS) {
+                followLinks = false;
+            } else if (option == null) {
+                throw new NullPointerException();
+            } else {
+                throw new AssertionError("Should not get here");
+            }
+        }
+        return followLinks;
+    }
 }
--- a/jdk/src/share/classes/sun/util/calendar/ZoneInfoFile.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/share/classes/sun/util/calendar/ZoneInfoFile.java	Mon Apr 04 18:09:53 2011 +0100
@@ -479,7 +479,7 @@
                 String zi = System.getProperty("java.home") +
                     File.separator + "lib" + File.separator + "zi";
                 try {
-                    zi = FileSystems.getDefault().getPath(zi).toRealPath(true).toString();
+                    zi = FileSystems.getDefault().getPath(zi).toRealPath().toString();
                 } catch(Exception e) {
                 }
                 return zi;
--- a/jdk/src/share/demo/nio/zipfs/src/com/sun/nio/zipfs/ZipFileSystemProvider.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/share/demo/nio/zipfs/src/com/sun/nio/zipfs/ZipFileSystemProvider.java	Mon Apr 04 18:09:53 2011 +0100
@@ -99,7 +99,7 @@
         synchronized(filesystems) {
             Path realPath = null;
             if (ensureFile(path)) {
-                realPath = path.toRealPath(true);
+                realPath = path.toRealPath();
                 if (filesystems.containsKey(realPath))
                     throw new FileSystemAlreadyExistsException();
             }
@@ -154,7 +154,7 @@
         synchronized (filesystems) {
             ZipFileSystem zipfs = null;
             try {
-                zipfs = filesystems.get(uriToPath(uri).toRealPath(true));
+                zipfs = filesystems.get(uriToPath(uri).toRealPath());
             } catch (IOException x) {
                 // ignore the ioe from toRealPath(), return FSNFE
             }
@@ -310,7 +310,7 @@
     //////////////////////////////////////////////////////////////
     void removeFileSystem(Path zfpath, ZipFileSystem zfs) throws IOException {
         synchronized (filesystems) {
-            zfpath = zfpath.toRealPath(true);
+            zfpath = zfpath.toRealPath();
             if (filesystems.get(zfpath) == zfs)
                 filesystems.remove(zfpath);
         }
--- a/jdk/src/share/demo/nio/zipfs/src/com/sun/nio/zipfs/ZipPath.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/share/demo/nio/zipfs/src/com/sun/nio/zipfs/ZipPath.java	Mon Apr 04 18:09:53 2011 +0100
@@ -150,7 +150,7 @@
     }
 
     @Override
-    public ZipPath toRealPath(boolean resolveLinks) throws IOException {
+    public ZipPath toRealPath(LinkOption... options) throws IOException {
         ZipPath realPath = new ZipPath(zfs, getResolvedPath()).toAbsolutePath();
         realPath.checkAccess();
         return realPath;
--- a/jdk/src/solaris/classes/sun/nio/fs/LinuxFileSystemProvider.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/solaris/classes/sun/nio/fs/LinuxFileSystemProvider.java	Mon Apr 04 18:09:53 2011 +0100
@@ -56,11 +56,11 @@
     {
         if (type == DosFileAttributeView.class) {
             return (V) new LinuxDosFileAttributeView(UnixPath.toUnixPath(obj),
-                                                     followLinks(options));
+                                                     Util.followLinks(options));
         }
         if (type == UserDefinedFileAttributeView.class) {
             return (V) new LinuxUserDefinedFileAttributeView(UnixPath.toUnixPath(obj),
-                                                             followLinks(options));
+                                                             Util.followLinks(options));
         }
         return super.getFileAttributeView(obj, type, options);
     }
@@ -72,11 +72,11 @@
     {
         if (name.equals("dos")) {
             return new LinuxDosFileAttributeView(UnixPath.toUnixPath(obj),
-                                                 followLinks(options));
+                                                 Util.followLinks(options));
         }
         if (name.equals("user")) {
             return new LinuxUserDefinedFileAttributeView(UnixPath.toUnixPath(obj),
-                                                         followLinks(options));
+                                                         Util.followLinks(options));
         }
         return super.getFileAttributeView(obj, name, options);
     }
--- a/jdk/src/solaris/classes/sun/nio/fs/SolarisFileSystemProvider.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/solaris/classes/sun/nio/fs/SolarisFileSystemProvider.java	Mon Apr 04 18:09:53 2011 +0100
@@ -57,11 +57,11 @@
     {
         if (type == AclFileAttributeView.class) {
             return (V) new SolarisAclFileAttributeView(UnixPath.toUnixPath(obj),
-                                                       followLinks(options));
+                                                       Util.followLinks(options));
         }
         if (type == UserDefinedFileAttributeView.class) {
             return(V) new SolarisUserDefinedFileAttributeView(UnixPath.toUnixPath(obj),
-                                                              followLinks(options));
+                                                              Util.followLinks(options));
         }
         return super.getFileAttributeView(obj, type, options);
     }
@@ -73,10 +73,10 @@
     {
         if (name.equals("acl"))
             return new SolarisAclFileAttributeView(UnixPath.toUnixPath(obj),
-                                                   followLinks(options));
+                                                   Util.followLinks(options));
         if (name.equals("user"))
             return new SolarisUserDefinedFileAttributeView(UnixPath.toUnixPath(obj),
-                                                           followLinks(options));
+                                                           Util.followLinks(options));
         return super.getFileAttributeView(obj, name, options);
     }
 }
--- a/jdk/src/solaris/classes/sun/nio/fs/UnixFileSystemProvider.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/solaris/classes/sun/nio/fs/UnixFileSystemProvider.java	Mon Apr 04 18:09:53 2011 +0100
@@ -105,20 +105,6 @@
         return (UnixPath)obj;
     }
 
-    boolean followLinks(LinkOption... options) {
-        boolean followLinks = true;
-        for (LinkOption option: options) {
-            if (option == LinkOption.NOFOLLOW_LINKS) {
-                followLinks = false;
-                continue;
-            }
-            if (option == null)
-                throw new NullPointerException();
-            throw new AssertionError("Should not get here");
-        }
-        return followLinks;
-    }
-
     @Override
     @SuppressWarnings("unchecked")
     public <V extends FileAttributeView> V getFileAttributeView(Path obj,
@@ -126,7 +112,7 @@
                                                                 LinkOption... options)
     {
         UnixPath file = UnixPath.toUnixPath(obj);
-        boolean followLinks =  followLinks(options);
+        boolean followLinks = Util.followLinks(options);
         if (type == BasicFileAttributeView.class)
             return (V) UnixFileAttributeViews.createBasicView(file, followLinks);
         if (type == PosixFileAttributeView.class)
@@ -163,7 +149,7 @@
                                                             LinkOption... options)
     {
         UnixPath file = UnixPath.toUnixPath(obj);
-        boolean followLinks = followLinks(options);
+        boolean followLinks = Util.followLinks(options);
         if (name.equals("basic"))
             return UnixFileAttributeViews.createBasicView(file, followLinks);
         if (name.equals("posix"))
--- a/jdk/src/solaris/classes/sun/nio/fs/UnixPath.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/solaris/classes/sun/nio/fs/UnixPath.java	Mon Apr 04 18:09:53 2011 +0100
@@ -819,13 +819,13 @@
     }
 
     @Override
-    public Path toRealPath(boolean resolveLinks) throws IOException {
+    public Path toRealPath(LinkOption... options) throws IOException {
         checkRead();
 
         UnixPath absolute = toAbsolutePath();
 
-        // if resolveLinks is true then use realpath
-        if (resolveLinks) {
+        // if resolving links then use realpath
+        if (Util.followLinks(options)) {
             try {
                 byte[] rp = realpath(absolute);
                 return new UnixPath(getFileSystem(), rp);
@@ -834,7 +834,7 @@
             }
         }
 
-        // if resolveLinks is false then eliminate "." and also ".."
+        // if not resolving links then eliminate "." and also ".."
         // where the previous element is not a link.
         UnixPath result = fs.rootDirectory();
         for (int i=0; i<absolute.getNameCount(); i++) {
--- a/jdk/src/solaris/classes/sun/nio/fs/UnixSecureDirectoryStream.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/solaris/classes/sun/nio/fs/UnixSecureDirectoryStream.java	Mon Apr 04 18:09:53 2011 +0100
@@ -81,20 +81,6 @@
         return (UnixPath)obj;
     }
 
-    private boolean followLinks(LinkOption... options) {
-        boolean followLinks = true;
-        for (LinkOption option: options) {
-            if (option == LinkOption.NOFOLLOW_LINKS) {
-                followLinks = false;
-                continue;
-            }
-            if (option == null)
-                throw new NullPointerException();
-            throw new AssertionError("Should not get here");
-        }
-        return followLinks;
-    }
-
     /**
      * Opens sub-directory in this directory
      */
@@ -105,7 +91,7 @@
     {
         UnixPath file = getName(obj);
         UnixPath child = ds.directory().resolve(file);
-        boolean followLinks = followLinks(options);
+        boolean followLinks = Util.followLinks(options);
 
         // permission check using name resolved against original path of directory
         SecurityManager sm = System.getSecurityManager();
@@ -316,7 +302,7 @@
                                                                 LinkOption... options)
     {
         UnixPath file = getName(obj);
-        boolean followLinks = followLinks(options);
+        boolean followLinks = Util.followLinks(options);
         return getFileAttributeViewImpl(file, type, followLinks);
     }
 
--- a/jdk/src/windows/classes/sun/nio/fs/WindowsFileSystemProvider.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/windows/classes/sun/nio/fs/WindowsFileSystemProvider.java	Mon Apr 04 18:09:53 2011 +0100
@@ -150,20 +150,6 @@
         }
     }
 
-    private boolean followLinks(LinkOption... options) {
-        boolean followLinks = true;
-        for (LinkOption option: options) {
-            if (option == LinkOption.NOFOLLOW_LINKS) {
-                followLinks = false;
-                continue;
-            }
-            if (option == null)
-                throw new NullPointerException();
-            throw new AssertionError("Should not get here");
-        }
-        return followLinks;
-    }
-
     @Override
     @SuppressWarnings("unchecked")
     public <V extends FileAttributeView> V
@@ -172,7 +158,7 @@
         WindowsPath file = WindowsPath.toWindowsPath(obj);
         if (view == null)
             throw new NullPointerException();
-        boolean followLinks = followLinks(options);
+        boolean followLinks = Util.followLinks(options);
         if (view == BasicFileAttributeView.class)
             return (V) WindowsFileAttributeViews.createBasicView(file, followLinks);
         if (view == DosFileAttributeView.class)
@@ -209,7 +195,7 @@
     @Override
     public DynamicFileAttributeView getFileAttributeView(Path obj, String name, LinkOption... options) {
         WindowsPath file = WindowsPath.toWindowsPath(obj);
-        boolean followLinks = followLinks(options);
+        boolean followLinks = Util.followLinks(options);
         if (name.equals("basic"))
             return WindowsFileAttributeViews.createBasicView(file, followLinks);
         if (name.equals("dos"))
--- a/jdk/src/windows/classes/sun/nio/fs/WindowsPath.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/src/windows/classes/sun/nio/fs/WindowsPath.java	Mon Apr 04 18:09:53 2011 +0100
@@ -831,9 +831,9 @@
     }
 
     @Override
-    public WindowsPath toRealPath(boolean resolveLinks) throws IOException {
+    public WindowsPath toRealPath(LinkOption... options) throws IOException {
         checkRead();
-        String rp = WindowsLinkSupport.getRealPath(this, resolveLinks);
+        String rp = WindowsLinkSupport.getRealPath(this, Util.followLinks(options));
         return createFromNormalizedPath(getFileSystem(), rp);
     }
 
--- a/jdk/test/java/nio/file/Files/CheckPermissions.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/test/java/nio/file/Files/CheckPermissions.java	Mon Apr 04 18:09:53 2011 +0100
@@ -521,19 +521,19 @@
             // -- toRealPath --
 
             prepare();
-            file.toRealPath(true);
+            file.toRealPath();
             assertCheckRead(file);
 
             prepare();
-            file.toRealPath(false);
+            file.toRealPath(LinkOption.NOFOLLOW_LINKS);
             assertCheckRead(file);
 
             prepare();
-            Paths.get(".").toRealPath(true);
+            Paths.get(".").toRealPath();
             assertCheckPropertyAccess("user.dir");
 
             prepare();
-            Paths.get(".").toRealPath(false);
+            Paths.get(".").toRealPath(LinkOption.NOFOLLOW_LINKS);
             assertCheckPropertyAccess("user.dir");
 
             // -- register --
--- a/jdk/test/java/nio/file/Files/PassThroughFileSystem.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/test/java/nio/file/Files/PassThroughFileSystem.java	Mon Apr 04 18:09:53 2011 +0100
@@ -486,8 +486,8 @@
         }
 
         @Override
-        public Path toRealPath(boolean resolveLinks) throws IOException {
-            return wrap(delegate.toRealPath(resolveLinks));
+        public Path toRealPath(LinkOption... options) throws IOException {
+            return wrap(delegate.toRealPath(options));
         }
 
         @Override
--- a/jdk/test/java/nio/file/Path/Misc.java	Thu Mar 31 22:07:32 2011 -0700
+++ b/jdk/test/java/nio/file/Path/Misc.java	Mon Apr 04 18:09:53 2011 +0100
@@ -22,12 +22,13 @@
  */
 
 /* @test
- * @bug 4313887 6838333
+ * @bug 4313887 6838333 7029979
  * @summary Unit test for miscellenous java.nio.file.Path methods
  * @library ..
  */
 
 import java.nio.file.*;
+import static java.nio.file.LinkOption.*;
 import java.io.*;
 
 public class Misc {
@@ -96,65 +97,65 @@
         final Path link = dir.resolve("link");
 
         /**
-         * Test: totRealPath(true) will access same file as toRealPath(false)
+         * Test: totRealPath() will access same file as toRealPath(NOFOLLOW_LINKS)
          */
-        assertTrue(Files.isSameFile(file.toRealPath(true), file.toRealPath(false)));
+        assertTrue(Files.isSameFile(file.toRealPath(), file.toRealPath(NOFOLLOW_LINKS)));
 
         /**
          * Test: toRealPath should fail if file does not exist
          */
         Path doesNotExist = dir.resolve("DoesNotExist");
         try {
-            doesNotExist.toRealPath(true);
+            doesNotExist.toRealPath();
             throw new RuntimeException("IOException expected");
         } catch (IOException expected) {
         }
         try {
-            doesNotExist.toRealPath(false);
+            doesNotExist.toRealPath(NOFOLLOW_LINKS);
             throw new RuntimeException("IOException expected");
         } catch (IOException expected) {
         }
 
         /**
-         * Test: toRealPath(true) should resolve links
+         * Test: toRealPath() should resolve links
          */
         if (supportsLinks) {
             Files.createSymbolicLink(link, file.toAbsolutePath());
-            assertTrue(link.toRealPath(true).equals(file.toRealPath(true)));
+            assertTrue(link.toRealPath().equals(file.toRealPath()));
             Files.delete(link);
         }
 
         /**
-         * Test: toRealPath(false) should not resolve links
+         * Test: toRealPath(NOFOLLOW_LINKS) should not resolve links
          */
         if (supportsLinks) {
             Files.createSymbolicLink(link, file.toAbsolutePath());
-            assertTrue(link.toRealPath(false).getFileName().equals(link.getFileName()));
+            assertTrue(link.toRealPath(NOFOLLOW_LINKS).getFileName().equals(link.getFileName()));
             Files.delete(link);
         }
 
         /**
-         * Test: toRealPath(false) with broken link
+         * Test: toRealPath(NOFOLLOW_LINKS) with broken link
          */
         if (supportsLinks) {
             Path broken = Files.createSymbolicLink(link, doesNotExist);
-            assertTrue(link.toRealPath(false).getFileName().equals(link.getFileName()));
+            assertTrue(link.toRealPath(NOFOLLOW_LINKS).getFileName().equals(link.getFileName()));
             Files.delete(link);
         }
 
         /**
          * Test: toRealPath should eliminate "."
          */
-        assertTrue(dir.resolve(".").toRealPath(true).equals(dir.toRealPath(true)));
-        assertTrue(dir.resolve(".").toRealPath(false).equals(dir.toRealPath(false)));
+        assertTrue(dir.resolve(".").toRealPath().equals(dir.toRealPath()));
+        assertTrue(dir.resolve(".").toRealPath(NOFOLLOW_LINKS).equals(dir.toRealPath(NOFOLLOW_LINKS)));
 
         /**
          * Test: toRealPath should eliminate ".." when it doesn't follow a
          *       symbolic link
          */
         Path subdir = Files.createDirectory(dir.resolve("subdir"));
-        assertTrue(subdir.resolve("..").toRealPath(true).equals(dir.toRealPath(true)));
-        assertTrue(subdir.resolve("..").toRealPath(false).equals(dir.toRealPath(false)));
+        assertTrue(subdir.resolve("..").toRealPath().equals(dir.toRealPath()));
+        assertTrue(subdir.resolve("..").toRealPath(NOFOLLOW_LINKS).equals(dir.toRealPath(NOFOLLOW_LINKS)));
         Files.delete(subdir);
 
         // clean-up