8161454: Fails to Load external Java method from inside of a XSL stylesheet if SecurityManager is present
authorjoehw
Thu, 01 Sep 2016 17:03:41 -0700
changeset 40755 26f6264ee481
parent 40754 ec9bb4e51ec7
child 40756 ac2a115938ab
8161454: Fails to Load external Java method from inside of a XSL stylesheet if SecurityManager is present Reviewed-by: aefimov, lancea, dfuchs
jaxp/src/java.xml/share/classes/jdk/xml/internal/JdkXmlFeatures.java
jaxp/test/javax/xml/jaxp/unittest/transform/XSLTFunctionsTest.java
--- a/jaxp/src/java.xml/share/classes/jdk/xml/internal/JdkXmlFeatures.java	Thu Sep 01 17:12:12 2016 +0300
+++ b/jaxp/src/java.xml/share/classes/jdk/xml/internal/JdkXmlFeatures.java	Thu Sep 01 17:03:41 2016 -0700
@@ -42,6 +42,9 @@
             ORACLE_JAXP_PROPERTY_PREFIX + "enableExtensionFunctions";
     public static final String SP_ENABLE_EXTENSION_FUNCTION =
             "javax.xml.enableExtensionFunctions";
+    // This is the correct name by the spec
+    public static final String SP_ENABLE_EXTENSION_FUNCTION_SPEC =
+            "jdk.xml.enableExtensionFunctions";
     public static final String CATALOG_FEATURES = "javax.xml.catalog.catalogFeatures";
 
     public final static String PROPERTY_USE_CATALOG = XMLConstants.USE_CATALOG;
@@ -49,11 +52,11 @@
     public static enum XmlFeature {
         /**
          * Feature enableExtensionFunctions
-         * FSP: extension function is enforced by FSP. When FSP is on, entension
+         * FSP: extension function is enforced by FSP. When FSP is on, extension
          * function is disabled.
          */
         ENABLE_EXTENSION_FUNCTION(ORACLE_ENABLE_EXTENSION_FUNCTION,
-                SP_ENABLE_EXTENSION_FUNCTION, true, false, true, true),
+                SP_ENABLE_EXTENSION_FUNCTION_SPEC, true, false, true, true),
         /**
          * The {@link javax.xml.XMLConstants.USE_CATALOG} feature.
          * FSP: USE_CATALOG is not enforced by FSP.
@@ -149,6 +152,30 @@
     }
 
     /**
+     * Maps old property names with the new ones. This map is used to keep track of
+     * name changes so that old or incorrect names continue to be supported for compatibility.
+     */
+    public static enum NameMap {
+
+        ENABLE_EXTENSION_FUNCTION(SP_ENABLE_EXTENSION_FUNCTION_SPEC, SP_ENABLE_EXTENSION_FUNCTION);
+
+        final String newName;
+        final String oldName;
+
+        NameMap(String newName, String oldName) {
+            this.newName = newName;
+            this.oldName = oldName;
+        }
+
+        String getOldName(String newName) {
+            if (newName.equals(this.newName)) {
+                return oldName;
+            }
+            return null;
+        }
+    }
+
+    /**
      * States of the settings of a property, in the order: default value, value
      * set by FEATURE_SECURE_PROCESSING, jaxp.properties file, jaxp system
      * properties, and jaxp api properties
@@ -316,6 +343,15 @@
     private void readSystemProperties() {
         for (XmlFeature feature : XmlFeature.values()) {
             getSystemProperty(feature, feature.systemProperty());
+            if (!getSystemProperty(feature, feature.systemProperty())) {
+                //if system property is not found, try the older form if any
+                for (NameMap nameMap : NameMap.values()) {
+                    String oldName = nameMap.getOldName(feature.systemProperty());
+                    if (oldName != null) {
+                        getSystemProperty(feature, oldName);
+                    }
+                }
+            }
         }
     }
 
--- a/jaxp/test/javax/xml/jaxp/unittest/transform/XSLTFunctionsTest.java	Thu Sep 01 17:12:12 2016 +0300
+++ b/jaxp/test/javax/xml/jaxp/unittest/transform/XSLTFunctionsTest.java	Thu Sep 01 17:03:41 2016 -0700
@@ -34,11 +34,16 @@
 import javax.xml.transform.stream.StreamResult;
 import javax.xml.transform.stream.StreamSource;
 
+import org.testng.Assert;
 import org.testng.annotations.DataProvider;
 import org.testng.annotations.Listeners;
 import org.testng.annotations.Test;
 
 import static org.testng.Assert.assertEquals;
+import static jaxp.library.JAXPTestUtilities.runWithAllPerm;
+import static jaxp.library.JAXPTestUtilities.clearSystemProperty;
+import static jaxp.library.JAXPTestUtilities.setSystemProperty;
+import static jaxp.library.JAXPTestUtilities.getSystemProperty;
 
 /*
  * @test
@@ -49,10 +54,66 @@
  * @summary This class contains tests for XSLT functions.
  */
 
-//@Listeners({jaxp.library.BasePolicy.class}) //uncomment this line after 8161454 is resolved
+@Listeners({jaxp.library.BasePolicy.class})
 public class XSLTFunctionsTest {
 
     /**
+     * @bug 8161454
+     * Verifies that the new / correct name is supported, as is the old / incorrect
+     * one for compatibility
+     */
+    @Test
+    public void testNameChange() {
+
+        boolean feature;
+        TransformerFactory tf = TransformerFactory.newInstance();
+        feature = tf.getFeature(ORACLE_ENABLE_EXTENSION_FUNCTION);
+        System.out.println("Default setting: " + feature);
+        // The default: true if no SecurityManager, false otherwise
+        Assert.assertTrue(feature == getDefault());
+
+        setSystemProperty(SP_ENABLE_EXTENSION_FUNCTION, getDefaultOpposite());
+        tf = TransformerFactory.newInstance();
+        feature = tf.getFeature(ORACLE_ENABLE_EXTENSION_FUNCTION);
+        System.out.println("After setting " + SP_ENABLE_EXTENSION_FUNCTION + ": " + feature);
+        clearSystemProperty(SP_ENABLE_EXTENSION_FUNCTION);
+        // old/incorrect name is still supported
+        Assert.assertTrue(feature != getDefault());
+
+        setSystemProperty(SP_ENABLE_EXTENSION_FUNCTION_SPEC, getDefaultOpposite());
+        tf = TransformerFactory.newInstance();
+        feature = tf.getFeature(ORACLE_ENABLE_EXTENSION_FUNCTION);
+        System.out.println("After setting " + SP_ENABLE_EXTENSION_FUNCTION_SPEC + ": " + feature);
+        clearSystemProperty(SP_ENABLE_EXTENSION_FUNCTION_SPEC);
+        // new/correct name is effective
+        Assert.assertTrue(feature != getDefault());
+    }
+
+    final boolean isSecure;
+    {
+        String runSecMngr = getSystemProperty("runSecMngr");
+        isSecure = runSecMngr != null && runSecMngr.equals("true");
+    }
+
+    // The default: true if no SecurityManager, false otherwise
+    private boolean getDefault() {
+        if (isSecure) {
+            return false;
+        } else {
+            return true;
+        }
+    }
+
+    // Gets a String value that is opposite to the default value
+    private String getDefaultOpposite() {
+        if (isSecure) {
+            return "true";
+        } else {
+            return "false";
+        }
+    }
+
+    /**
      * @bug 8062518 8153082
      * Verifies that a reference to the DTM created by XSLT document function is
      * actually read from the DTM by an extension function.
@@ -72,7 +133,9 @@
 
         // Create factory and transformer
         TransformerFactory tf = TransformerFactory.newInstance();
-        tf.setFeature("http://www.oracle.com/xml/jaxp/properties/enableExtensionFunctions", true);
+        tf.setFeature(ORACLE_ENABLE_EXTENSION_FUNCTION, true);
+        tf.setAttribute(EXTENSION_CLASS_LOADER,
+                runWithAllPerm(() -> Thread.currentThread().getContextClassLoader()));
         Transformer t = tf.newTransformer( xslsrc );
         t.setErrorListener(tf.getErrorListener());
 
@@ -133,5 +196,16 @@
 
     static final String documentTesteExpectedResult = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>"
                                                     + "<root>[Test:Doc][Test:External Doc]</root>";
+
+    public static final String ORACLE_JAXP_PROPERTY_PREFIX =
+        "http://www.oracle.com/xml/jaxp/properties/";
+    /**
+     * Feature enableExtensionFunctions
+     */
+    public static final String ORACLE_ENABLE_EXTENSION_FUNCTION =
+            ORACLE_JAXP_PROPERTY_PREFIX + "enableExtensionFunctions";
+    static final String SP_ENABLE_EXTENSION_FUNCTION = "javax.xml.enableExtensionFunctions";
+    // This is the correct name by the spec
+    static final String SP_ENABLE_EXTENSION_FUNCTION_SPEC = "jdk.xml.enableExtensionFunctions";
+    private static final String EXTENSION_CLASS_LOADER = "jdk.xml.transform.extensionClassLoader";
 }
-