# HG changeset patch # User jfranck # Date 1381483341 -7200 # Node ID 4e22c127db00c0d0d601d7a1153c69f9394f3e3a # Parent d0208369f7cb5f9c80f8427b907d0e368e005d28 8023301: Enhance generic classes Reviewed-by: mchung, hawtin diff -r d0208369f7cb -r 4e22c127db00 src/share/classes/sun/reflect/generics/reflectiveObjects/TypeVariableImpl.java --- a/src/share/classes/sun/reflect/generics/reflectiveObjects/TypeVariableImpl.java Thu Oct 24 19:21:52 2013 +0100 +++ b/src/share/classes/sun/reflect/generics/reflectiveObjects/TypeVariableImpl.java Fri Oct 11 11:22:21 2013 +0200 @@ -25,13 +25,17 @@ package sun.reflect.generics.reflectiveObjects; +import java.lang.reflect.Constructor; import java.lang.reflect.GenericDeclaration; +import java.lang.reflect.Member; +import java.lang.reflect.Method; import java.lang.reflect.Type; import java.lang.reflect.TypeVariable; import sun.reflect.generics.factory.GenericsFactory; import sun.reflect.generics.tree.FieldTypeSignature; import sun.reflect.generics.visitor.Reifier; +import sun.reflect.misc.ReflectUtil; /** * Implementation of java.lang.reflect.TypeVariable interface @@ -87,6 +91,13 @@ TypeVariableImpl make(T decl, String name, FieldTypeSignature[] bs, GenericsFactory f) { + + if (!((decl instanceof Class) || + (decl instanceof Method) || + (decl instanceof Constructor))) { + throw new AssertionError("Unexpected kind of GenericDeclaration" + + decl.getClass().toString()); + } return new TypeVariableImpl(decl, name, bs, f); } @@ -141,6 +152,13 @@ * @since 1.5 */ public D getGenericDeclaration(){ + if (genericDeclaration instanceof Class) + ReflectUtil.checkPackageAccess((Class)genericDeclaration); + else if ((genericDeclaration instanceof Method) || + (genericDeclaration instanceof Constructor)) + ReflectUtil.conservativeCheckMemberAccess((Member)genericDeclaration); + else + throw new AssertionError("Unexpected kind of GenericDeclaration"); return genericDeclaration; } @@ -156,7 +174,8 @@ @Override public boolean equals(Object o) { - if (o instanceof TypeVariable) { + if (o instanceof TypeVariable && + o.getClass() == TypeVariableImpl.class) { TypeVariable that = (TypeVariable) o; GenericDeclaration thatDecl = that.getGenericDeclaration(); diff -r d0208369f7cb -r 4e22c127db00 src/share/classes/sun/reflect/misc/ReflectUtil.java --- a/src/share/classes/sun/reflect/misc/ReflectUtil.java Thu Oct 24 19:21:52 2013 +0100 +++ b/src/share/classes/sun/reflect/misc/ReflectUtil.java Fri Oct 11 11:22:21 2013 +0200 @@ -26,11 +26,13 @@ package sun.reflect.misc; +import java.lang.reflect.Member; import java.lang.reflect.Method; import java.lang.reflect.Modifier; import java.lang.reflect.Proxy; import java.util.Arrays; import sun.reflect.Reflection; +import sun.security.util.SecurityConstants; public final class ReflectUtil { @@ -117,6 +119,39 @@ return false; } + /** + * Does a conservative approximation of member access check. Use this if + * you don't have an actual 'userland' caller Class/ClassLoader available. + * This might be more restrictive than a precise member access check where + * you have a caller, but should never allow a member access that is + * forbidden. + * + * @param m the {@code Member} about to be accessed + */ + public static void conservativeCheckMemberAccess(Member m) throws SecurityException{ + final SecurityManager sm = System.getSecurityManager(); + if (sm == null) + return; + + // Check for package access on the declaring class. + // + // In addition, unless the member and the declaring class are both + // public check for access declared member permissions. + // + // This is done regardless of ClassLoader relations between the {@code + // Member m} and any potential caller. + + final Class declaringClass = m.getDeclaringClass(); + + checkPackageAccess(declaringClass); + + if (Modifier.isPublic(m.getModifiers()) && + Modifier.isPublic(declaringClass.getModifiers())) + return; + + // Check for declared member access. + sm.checkPermission(SecurityConstants.CHECK_MEMBER_ACCESS_PERMISSION); + } /** * Checks package access on the given class.