You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tomcat.apache.org by ma...@apache.org on 2019/10/04 11:25:59 UTC

[tomcat] branch master updated: Ensure correct exception with ImportHandler and Java 9+

This is an automated email from the ASF dual-hosted git repository.

markt pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/tomcat.git


The following commit(s) were added to refs/heads/master by this push:
     new 0379a3a  Ensure correct exception with ImportHandler and Java 9+
0379a3a is described below

commit 0379a3a590c3082491062d8d5aeb0bb337299393
Author: Mark Thomas <ma...@apache.org>
AuthorDate: Thu Oct 3 23:24:47 2019 +0100

    Ensure correct exception with ImportHandler and Java 9+
---
 java/javax/el/ImportHandler.java      |  6 ++++--
 java/javax/el/Jre9Compat.java         | 29 +++++++++++++++++++++++++++--
 java/javax/el/JreCompat.java          | 13 +++++++++++++
 java/javax/el/LocalStrings.properties |  2 +-
 4 files changed, 45 insertions(+), 5 deletions(-)

diff --git a/java/javax/el/ImportHandler.java b/java/javax/el/ImportHandler.java
index b222ea5..eb9e270 100644
--- a/java/javax/el/ImportHandler.java
+++ b/java/javax/el/ImportHandler.java
@@ -464,10 +464,12 @@ public class ImportHandler {
             return null;
         }
 
-        // Class must be public, non-abstract and not an interface
+        // Class must be public, non-abstract, not an interface and (for
+        // Java 9+) in an exported package
+        JreCompat jreCompat = JreCompat.getInstance();
         int modifiers = clazz.getModifiers();
         if (!Modifier.isPublic(modifiers) || Modifier.isAbstract(modifiers) ||
-                Modifier.isInterface(modifiers)) {
+                Modifier.isInterface(modifiers) || !jreCompat.isExported(clazz)) {
             if (throwException) {
                 throw new ELException(Util.message(
                         null, "importHandler.invalidClass", name));
diff --git a/java/javax/el/Jre9Compat.java b/java/javax/el/Jre9Compat.java
index 2718713..b95f93a 100644
--- a/java/javax/el/Jre9Compat.java
+++ b/java/javax/el/Jre9Compat.java
@@ -29,16 +29,29 @@ import java.lang.reflect.Method;
 class Jre9Compat extends JreCompat {
 
     private static final Method canAccessMethod;
-
+    private static final Method getModuleMethod;
+    private static final Method isExportedMethod;
 
     static {
         Method m1 = null;
+        Method m2 = null;
+        Method m3 = null;
+
         try {
-            m1 = AccessibleObject.class.getMethod("canAccess", new Class<?>[] { Object.class });
+            m1 = AccessibleObject.class.getMethod("canAccess", Object.class);
+            m2 = Class.class.getMethod("getModule");
+            Class<?> moduleClass = Class.forName("java.lang.Module");
+            m3 = moduleClass.getMethod("isExported", String.class);
         } catch (NoSuchMethodException e) {
             // Expected for Java 8
+        } catch (ClassNotFoundException e) {
+            // Can't log this so...
+            throw new RuntimeException(e);
         }
+
         canAccessMethod = m1;
+        getModuleMethod = m2;
+        isExportedMethod = m3;
     }
 
 
@@ -55,4 +68,16 @@ class Jre9Compat extends JreCompat {
             return false;
         }
     }
+
+
+    @Override
+    public boolean isExported(Class<?> type) {
+        try {
+            String packageName = type.getPackage().getName();
+            Object module = getModuleMethod.invoke(type);
+            return ((Boolean) isExportedMethod.invoke(module, packageName)).booleanValue();
+        } catch (ReflectiveOperationException e) {
+            return false;
+        }
+    }
 }
diff --git a/java/javax/el/JreCompat.java b/java/javax/el/JreCompat.java
index 6d68ed0..1b21af9 100644
--- a/java/javax/el/JreCompat.java
+++ b/java/javax/el/JreCompat.java
@@ -57,4 +57,17 @@ class JreCompat {
         // Java 8 doesn't support modules so default to true
         return true;
     }
+
+
+    /**
+     * Is the given class in an exported package?
+     *
+     * @param type  The class to test
+     *
+     * @return Always {@code true} for Java 8. {@code true} if the enclosing
+     *         package is exported for Java 9+
+     */
+    public boolean isExported(Class<?> type) {
+        return true;
+    }
 }
diff --git a/java/javax/el/LocalStrings.properties b/java/javax/el/LocalStrings.properties
index b875ab4..4bca364 100644
--- a/java/javax/el/LocalStrings.properties
+++ b/java/javax/el/LocalStrings.properties
@@ -29,7 +29,7 @@ expressionFactory.readFailed=Failed to read [{0}]
 importHandler.ambiguousImport=The class [{0}] could not be imported as it conflicts with [{1}] which has already been imported
 importHandler.ambiguousStaticImport=The static import [{0}] could not be processed as it conflicts with [{1}] which has already been imported
 importHandler.classNotFound=The class [{0}] could not be imported as it could not be found
-importHandler.invalidClass=The class [{0}] must be public, non-abstract and not an interface
+importHandler.invalidClass=The class [{0}] must be public, non-abstract, not an interface and (for Java 9+) in an exported package
 importHandler.invalidClassName=Name of class to import [{0}] must include a package
 importHandler.invalidClassNameForStatic=The class [{0}] specified for static import [{1}] is not valid
 importHandler.invalidStaticName=Name of static method or field to import [{0}] must include a class


---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@tomcat.apache.org
For additional commands, e-mail: dev-help@tomcat.apache.org