6931128: (spec) File attribute tests fail when run as root.
authorrobm
Wed, 15 Aug 2012 22:46:35 +0100
changeset 13568 ce5ab758aeb5
parent 13567 b124faa29aef
child 13569 a6a02227e47f
6931128: (spec) File attribute tests fail when run as root. Reviewed-by: alanb
jdk/src/share/classes/java/io/File.java
jdk/test/java/io/File/Basic.java
jdk/test/java/io/File/SetAccess.java
jdk/test/java/io/File/SetReadOnly.java
jdk/test/java/io/File/SymLinks.java
jdk/test/java/io/File/Util.java
--- a/jdk/src/share/classes/java/io/File.java	Wed Aug 15 14:35:36 2012 +0100
+++ b/jdk/src/share/classes/java/io/File.java	Wed Aug 15 22:46:35 2012 +0100
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1994, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1994, 2012, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -711,7 +711,10 @@
 
     /**
      * Tests whether the application can read the file denoted by this
-     * abstract pathname.
+     * abstract pathname. On some platforms it may be possible to start the
+     * Java virtual machine with special privileges that allow it to read
+     * files that are marked as unreadable. Consequently this method may return
+     * {@code true} even though the file does not have read permissions.
      *
      * @return  <code>true</code> if and only if the file specified by this
      *          abstract pathname exists <em>and</em> can be read by the
@@ -732,7 +735,10 @@
 
     /**
      * Tests whether the application can modify the file denoted by this
-     * abstract pathname.
+     * abstract pathname. On some platforms it may be possible to start the
+     * Java virtual machine with special privileges that allow it to modify
+     * files that are marked read-only. Consequently this method may return
+     * {@code true} even though the file is marked read-only.
      *
      * @return  <code>true</code> if and only if the file system actually
      *          contains a file denoted by this abstract pathname <em>and</em>
@@ -1351,9 +1357,11 @@
 
     /**
      * Marks the file or directory named by this abstract pathname so that
-     * only read operations are allowed.  After invoking this method the file
-     * or directory is guaranteed not to change until it is either deleted or
-     * marked to allow write access.  Whether or not a read-only file or
+     * only read operations are allowed. After invoking this method the file
+     * or directory will not change until it is either deleted or marked
+     * to allow write access. On some platforms it may be possible to start the
+     * Java virtual machine with special privileges that allow it to modify
+     * files that are marked read-only. Whether or not a read-only file or
      * directory may be deleted depends upon the underlying system.
      *
      * @return <code>true</code> if and only if the operation succeeded;
@@ -1376,7 +1384,9 @@
 
     /**
      * Sets the owner's or everybody's write permission for this abstract
-     * pathname.
+     * pathname. On some platforms it may be possible to start the Java virtual
+     * machine with special privileges that allow it to modify files that
+     * disallow write operations.
      *
      * <p> The {@link java.nio.file.Files} class defines methods that operate on
      * file attributes including file permissions. This may be used when finer
@@ -1414,7 +1424,9 @@
 
     /**
      * A convenience method to set the owner's write permission for this abstract
-     * pathname.
+     * pathname. On some platforms it may be possible to start the Java virtual
+     * machine with special privileges that allow it to modify files that
+     * disallow write operations.
      *
      * <p> An invocation of this method of the form <tt>file.setWritable(arg)</tt>
      * behaves in exactly the same way as the invocation
@@ -1443,7 +1455,9 @@
 
     /**
      * Sets the owner's or everybody's read permission for this abstract
-     * pathname.
+     * pathname. On some platforms it may be possible to start the Java virtual
+     * machine with special privileges that allow it to read files that are
+     * marked as unreadable.
      *
      * <p> The {@link java.nio.file.Files} class defines methods that operate on
      * file attributes including file permissions. This may be used when finer
@@ -1484,7 +1498,9 @@
 
     /**
      * A convenience method to set the owner's read permission for this abstract
-     * pathname.
+     * pathname. On some platforms it may be possible to start the Java virtual
+     * machine with special privileges that allow it to read files that that are
+     * marked as unreadable.
      *
      * <p>An invocation of this method of the form <tt>file.setReadable(arg)</tt>
      * behaves in exactly the same way as the invocation
@@ -1516,7 +1532,9 @@
 
     /**
      * Sets the owner's or everybody's execute permission for this abstract
-     * pathname.
+     * pathname. On some platforms it may be possible to start the Java virtual
+     * machine with special privileges that allow it to execute files that are
+     * not marked executable.
      *
      * <p> The {@link java.nio.file.Files} class defines methods that operate on
      * file attributes including file permissions. This may be used when finer
@@ -1556,8 +1574,10 @@
     }
 
     /**
-     * A convenience method to set the owner's execute permission for this abstract
-     * pathname.
+     * A convenience method to set the owner's execute permission for this
+     * abstract pathname. On some platforms it may be possible to start the Java
+     * virtual machine with special privileges that allow it to execute files
+     * that are not marked executable.
      *
      * <p>An invocation of this method of the form <tt>file.setExcutable(arg)</tt>
      * behaves in exactly the same way as the invocation
@@ -1589,7 +1609,10 @@
 
     /**
      * Tests whether the application can execute the file denoted by this
-     * abstract pathname.
+     * abstract pathname. On some platforms it may be possible to start the
+     * Java virtual machine with special privileges that allow it to execute
+     * files that are not marked executable. Consequently this method may return
+     * {@code true} even though the file does not have execute permissions.
      *
      * @return  <code>true</code> if and only if the abstract pathname exists
      *          <em>and</em> the application is allowed to execute the file
--- a/jdk/test/java/io/File/Basic.java	Wed Aug 15 14:35:36 2012 +0100
+++ b/jdk/test/java/io/File/Basic.java	Wed Aug 15 22:46:35 2012 +0100
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 2012, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -25,7 +25,7 @@
    @bug 4165666 4203706 4288670 4290024
    @summary Basic heartbeat test for File methods that access the filesystem
 
-   @build Basic
+   @build Basic Util
    @run shell basic.sh
  */
 
@@ -73,7 +73,7 @@
         if (!f.isFile()) fail(f, "is not a file");
         if (f.isDirectory()) fail(f, "is a directory");
         if (!f.canRead()) fail(f, "is not readable");
-        if (f.canWrite() != writeable)
+        if (!Util.isPrivileged() && f.canWrite() != writeable)
             fail(f, writeable ? "is not writeable" : "is writeable");
         int rwLen = 6;
         if (f.length() != length) fail(f, "has wrong length");
--- a/jdk/test/java/io/File/SetAccess.java	Wed Aug 15 14:35:36 2012 +0100
+++ b/jdk/test/java/io/File/SetAccess.java	Wed Aug 15 22:46:35 2012 +0100
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 2012, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -24,6 +24,8 @@
 /* @test
    @bug 4167472 5097703 6216563 6284003 6728842 6464744
    @summary Basic test for setWritable/Readable/Executable methods
+   @build SetAccess Util
+   @run main SetAccess
  */
 
 import java.io.*;
@@ -32,6 +34,11 @@
 
 public class SetAccess {
     public static void main(String[] args) throws Exception {
+        if (Util.isPrivileged()) {
+            System.out.println("Unable to test file permissions when running with privileges");
+            return;
+        }
+
         File d = new File(System.getProperty("test.dir", "."));
 
         File f = new File(d, "x.SetAccessPermission");
--- a/jdk/test/java/io/File/SetReadOnly.java	Wed Aug 15 14:35:36 2012 +0100
+++ b/jdk/test/java/io/File/SetReadOnly.java	Wed Aug 15 22:46:35 2012 +0100
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 2012, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -24,6 +24,8 @@
 /* @test
    @bug 4091757 4939819 6728842
    @summary Basic test for setReadOnly method
+   @build SetReadOnly Util
+   @run main SetReadOnly
  */
 
 import java.io.*;
@@ -32,6 +34,11 @@
 public class SetReadOnly {
 
     public static void main(String[] args) throws Exception {
+        if (Util.isPrivileged()) {
+            System.out.println("Unable to test file permissions when running with privileges");
+            return;
+        }
+
         File d = new File(System.getProperty("test.dir", "."));
         File f = new File(d, "x.SetReadOnly");
 
--- a/jdk/test/java/io/File/SymLinks.java	Wed Aug 15 14:35:36 2012 +0100
+++ b/jdk/test/java/io/File/SymLinks.java	Wed Aug 15 22:46:35 2012 +0100
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 2012, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -24,6 +24,8 @@
 /* @test
  * @bug 6595866
  * @summary Test java.io.File operations with sym links
+ * @build SymLinks Util
+ * @run main SymLinks
  */
 
 import java.io.*;
@@ -338,7 +340,7 @@
         assertTrue(link2link2file.canRead());
         assertTrue(link2link2file.canWrite());
 
-        if (file.setReadOnly()) {
+        if (!Util.isPrivileged() && file.setReadOnly()) {
             assertFalse(file.canWrite());
             assertFalse(link2file.canWrite());
             assertFalse(link2link2file.canWrite());
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/java/io/File/Util.java	Wed Aug 15 22:46:35 2012 +0100
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+import java.io.File;
+
+/**
+ * Utility class used by tests for java.io.File.
+ */
+
+class Util {
+    private Util() { }
+
+    /**
+     * Returns {@code true} if the Java virtual machine is running with
+     * privileges (loosely defined here as have write access to /etc/passwd).
+     */
+    static boolean isPrivileged() {
+        String osname = System.getProperty("os.name");
+        if (osname.startsWith("Windows"))
+            return false;
+
+        return (new File("/etc/passwd")).canWrite();
+    }
+}
+