java 动态获取类名_反射01 Class类的使用、动态加载类、类类型说明、获取类的信息...

/** Copyright (c) 1994, 2014, Oracle and/or its affiliates. All rights reserved.

* ORACLE PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.

*

*

*

*

*

*

*

*

*

*

*

*

*

*

*

*

*

*

*

**/

packagejava.lang;importjava.lang.reflect.AnnotatedElement;importjava.lang.reflect.Array;importjava.lang.reflect.GenericArrayType;importjava.lang.reflect.GenericDeclaration;importjava.lang.reflect.Member;importjava.lang.reflect.Field;importjava.lang.reflect.Executable;importjava.lang.reflect.Method;importjava.lang.reflect.Constructor;importjava.lang.reflect.Modifier;importjava.lang.reflect.Type;importjava.lang.reflect.TypeVariable;importjava.lang.reflect.InvocationTargetException;importjava.lang.reflect.AnnotatedType;importjava.lang.ref.SoftReference;importjava.io.InputStream;importjava.io.ObjectStreamField;importjava.security.AccessController;importjava.security.PrivilegedAction;importjava.util.ArrayList;importjava.util.Arrays;importjava.util.Collection;importjava.util.HashSet;importjava.util.LinkedHashMap;importjava.util.List;importjava.util.Set;importjava.util.Map;importjava.util.HashMap;importjava.util.Objects;importsun.misc.Unsafe;importsun.reflect.CallerSensitive;importsun.reflect.ConstantPool;importsun.reflect.Reflection;importsun.reflect.ReflectionFactory;importsun.reflect.generics.factory.CoreReflectionFactory;importsun.reflect.generics.factory.GenericsFactory;importsun.reflect.generics.repository.ClassRepository;importsun.reflect.generics.repository.MethodRepository;importsun.reflect.generics.repository.ConstructorRepository;importsun.reflect.generics.scope.ClassScope;importsun.security.util.SecurityConstants;importjava.lang.annotation.Annotation;importjava.lang.reflect.Proxy;import sun.reflect.annotation.*;importsun.reflect.misc.ReflectUtil;/*** Instances of the class {@codeClass} represent classes and

* interfaces in a running Java application. An enum is a kind of

* class and an annotation is a kind of interface. Every array also

* belongs to a class that is reflected as a {@codeClass} object

* that is shared by all arrays with the same element type and number

* of dimensions. The primitive Java types ({@codeboolean},

* {@codebyte}, {@codechar}, {@codeshort},

* {@codeint}, {@codelong}, {@codefloat}, and

* {@codedouble}), and the keyword {@codevoid} are also

* represented as {@codeClass} objects.

*

*

{@codeClass} has no public constructor. Instead {@codeClass}

* objects are constructed automatically by the Java Virtual Machine as classes

* are loaded and by calls to the {@codedefineClass} method in the class

* loader.

*

*

The following example uses a {@codeClass} object to print the

* class name of an object:

*

*

 
  

* void printClassName(Object obj) {

* System.out.println("The class of " + obj +

* " is " + obj.getClass().getName());

* }

*

*

*

It is also possible to get the {@codeClass} object for a named

* type (or for void) using a class literal. See Section 15.8.2 of

* The Java™ Language Specification.

* For example:

*

*

* {@codeSystem.out.println("The name of class Foo is: "+Foo.class.getName());}

*

*

*@param the type of the class modeled by this {@codeClass}

* object. For example, the type of {@codeString.class} is {@code* Class}. Use {@codeClass>} if the class being modeled is

* unknown.

*

*@authorunascribed

*@seejava.lang.ClassLoader#defineClass(byte[], int, int)

*@sinceJDK1.0*/

public final class Class implementsjava.io.Serializable,

GenericDeclaration,

Type,

AnnotatedElement {private static final int ANNOTATION= 0x00002000;private static final int ENUM = 0x00004000;private static final int SYNTHETIC = 0x00001000;private static native voidregisterNatives();static{

registerNatives();

}/** Private constructor. Only the Java Virtual Machine creates Class objects.

* This constructor is not used and prevents the default constructor being

* generated.*/

privateClass(ClassLoader loader) {//Initialize final field for classLoader. The initialization value of non-null//prevents future JIT optimizations from assuming this final field is null.

classLoader =loader;

}/*** Converts the object to a string. The string representation is the

* string "class" or "interface", followed by a space, and then by the

* fully qualified name of the class in the format returned by

* {@codegetName}. If this {@codeClass} object represents a

* primitive type, this method returns the name of the primitive type. If

* this {@codeClass} object represents void this method returns

* "void".

*

*@returna string representation of this class object.*/

publicString toString() {return (isInterface() ? "interface " : (isPrimitive() ? "" : "class "))+getName();

}/*** Returns a string describing this {@codeClass}, including

* information about modifiers and type parameters.

*

* The string is formatted as a list of type modifiers, if any,

* followed by the kind of type (empty string for primitive types

* and {@codeclass}, {@codeenum}, {@codeinterface}, or

* @{@codeinterface}, as appropriate), followed

* by the type's name, followed by an angle-bracketed

* comma-separated list of the type's type parameters, if any.

*

* A space is used to separate modifiers from one another and to

* separate any modifiers from the kind of type. The modifiers

* occur in canonical order. If there are no type parameters, the

* type parameter list is elided.

*

*

Note that since information about the runtime representation

* of a type is being generated, modifiers not present on the

* originating source code or illegal on the originating source

* code may be present.

*

*@returna string describing this {@codeClass}, including

* information about modifiers and type parameters

*

*@since1.8*/

publicString toGenericString() {if(isPrimitive()) {returntoString();

}else{

StringBuilder sb= newStringBuilder();//Class modifiers are a superset of interface modifiers

int modifiers = getModifiers() &Modifier.classModifiers();if (modifiers != 0) {

sb.append(Modifier.toString(modifiers));

sb.append(' ');

}if(isAnnotation()) {

sb.append('@');

}if (isInterface()) { //Note: all annotation types are interfaces

sb.append("interface");

}else{if(isEnum())

sb.append("enum");elsesb.append("class");

}

sb.append(' ');

sb.append(getName());

TypeVariable>[] typeparms =getTypeParameters();if (typeparms.length > 0) {boolean first = true;

sb.append('typeparm: typeparms) {if (!first)

sb.append(',');

sb.append(typeparm.getTypeName());

first= false;

}

sb.append('>');

}returnsb.toString();

}

}/*** Returns the {@codeClass} object associated with the class or

* interface with the given string name. Invoking this method is

* equivalent to:

*

*

* {@codeClass.forName(className, true, currentLoader)}

*

*

* where {@codecurrentLoader} denotes the defining class loader of

* the current class.

*

*

For example, the following code fragment returns the

* runtime {@codeClass} descriptor for the class named

* {@codejava.lang.Thread}:

*

*

* {@codeClass t = Class.forName("java.lang.Thread")}

*

*

* A call to {@codeforName("X")} causes the class named

* {@codeX} to be initialized.

*

*@paramclassName the fully qualified name of the desired class.

*@returnthe {@codeClass} object for the class with the

* specified name.

*@exceptionLinkageError if the linkage fails

*@exceptionExceptionInInitializerError if the initialization provoked

* by this method fails

*@exceptionClassNotFoundException if the class cannot be located*/@CallerSensitivepublic static Class>forName(String className)throwsClassNotFoundException {

Class> caller =Reflection.getCallerClass();return forName0(className, true, ClassLoader.getClassLoader(caller), caller);

}/*** Returns the {@codeClass} object associated with the class or

* interface with the given string name, using the given class loader.

* Given the fully qualified name for a class or interface (in the same

* format returned by {@codegetName}) this method attempts to

* locate, load, and link the class or interface. The specified class

* loader is used to load the class or interface. If the parameter

* {@codeloader} is null, the class is loaded through the bootstrap

* class loader. The class is initialized only if the

* {@codeinitialize} parameter is {@codetrue} and if it has

* not been initialized earlier.

*

*

If {@codename} denotes a primitive type or void, an attempt

* will be made to locate a user-defined class in the unnamed package whose

* name is {@codename}. Therefore, this method cannot be used to

* obtain any of the {@codeClass} objects representing primitive

* types or void.

*

*

If {@codename} denotes an array class, the component type of

* the array class is loaded but not initialized.

*

*

For example, in an instance method the expression:

*

*

* {@codeClass.forName("Foo")}

*

*

* is equivalent to:

*

*

* {@codeClass.forName("Foo", true, this.getClass().getClassLoader())}

*

*

* Note that this method throws errors related to loading, linking or

* initializing as specified in Sections 12.2, 12.3 and 12.4 of The

* Java Language Specification.

* Note that this method does not check whether the requested class

* is accessible to its caller.

*

*

If the {@codeloader} is {@codenull}, and a security

* manager is present, and the caller's class loader is not null, then this

* method calls the security manager's {@codecheckPermission} method

* with a {@codeRuntimePermission("getClassLoader")} permission to

* ensure it's ok to access the bootstrap class loader.

*

*@paramname fully qualified name of the desired class

*@paraminitialize if {@codetrue} the class will be initialized.

* See Section 12.4 of The Java Language Specification.

*@paramloader class loader from which the class must be loaded

*@returnclass object representing the desired class

*

*@exceptionLinkageError if the linkage fails

*@exceptionExceptionInInitializerError if the initialization provoked

* by this method fails

*@exceptionClassNotFoundException if the class cannot be located by

* the specified class loader

*

*@seejava.lang.Class#forName(String)

*@seejava.lang.ClassLoader

*@since1.2*/@CallerSensitivepublic static Class> forName(String name, booleaninitialize,

ClassLoader loader)throwsClassNotFoundException

{

Class> caller = null;

SecurityManager sm=System.getSecurityManager();if (sm != null) {//Reflective call to get caller class is only needed if a security manager//is present. Avoid the overhead of making this call otherwise.

caller =Reflection.getCallerClass();if(sun.misc.VM.isSystemDomainLoader(loader)) {

ClassLoader ccl=ClassLoader.getClassLoader(caller);if (!sun.misc.VM.isSystemDomainLoader(ccl)) {

sm.checkPermission(

SecurityConstants.GET_CLASSLOADER_PERMISSION);

}

}

}returnforName0(name, initialize, loader, caller);

}/**Called after security check for system loader access checks have been made.*/

private static native Class> forName0(String name, booleaninitialize,

ClassLoader loader,

Class>caller)throwsClassNotFoundException;/*** Creates a new instance of the class represented by this {@codeClass}

* object. The class is instantiated as if by a {@codenew}

* expression with an empty argument list. The class is initialized if it

* has not already been initialized.

*

*

Note that this method propagates any exception thrown by the

* nullary constructor, including a checked exception. Use of

* this method effectively bypasses the compile-time exception

* checking that would otherwise be performed by the compiler.

* The {@link* java.lang.reflect.Constructor#newInstance(java.lang.Object...)

* Constructor.newInstance} method avoids this problem by wrapping

* any exception thrown by the constructor in a (checked) {@link* java.lang.reflect.InvocationTargetException}.

*

*@returna newly allocated instance of the class represented by this

* object.

*@throwsIllegalAccessException if the class or its nullary

* constructor is not accessible.

*@throwsInstantiationException

* if this {@codeClass} represents an abstract class,

* an interface, an array class, a primitive type, or void;

* or if the class has no nullary constructor;

* or if the instantiation fails for some other reason.

*@throwsExceptionInInitializerError if the initialization

* provoked by this method fails.

*@throwsSecurityException

* If a security manager, s, is present and

* the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class.*/@CallerSensitivepublicT newInstance()throwsInstantiationException, IllegalAccessException

{if (System.getSecurityManager() != null) {

checkMemberAccess(Member.PUBLIC, Reflection.getCallerClass(),false);

}//NOTE: the following code may not be strictly correct under//the current Java memory model.//Constructor lookup

if (cachedConstructor == null) {if (this == Class.class) {throw newIllegalAccessException("Can not call newInstance() on the Class for java.lang.Class");

}try{

Class>[] empty ={};final Constructor c =getConstructor0(empty, Member.DECLARED);//Disable accessibility checks on the constructor//since we have to do the security check here anyway//(the stack depth is wrong for the Constructor's//security check to work)

java.security.AccessController.doPrivileged(new java.security.PrivilegedAction() {publicVoid run() {

c.setAccessible(true);return null;

}

});

cachedConstructor=c;

}catch(NoSuchMethodException e) {throw(InstantiationException)newInstantiationException(getName()).initCause(e);

}

}

Constructor tmpConstructor =cachedConstructor;//Security check (same as in java.lang.reflect.Constructor)

int modifiers =tmpConstructor.getModifiers();if (!Reflection.quickCheckMemberAccess(this, modifiers)) {

Class> caller =Reflection.getCallerClass();if (newInstanceCallerCache !=caller) {

Reflection.ensureMemberAccess(caller,this, null, modifiers);

newInstanceCallerCache=caller;

}

}//Run constructor

try{return tmpConstructor.newInstance((Object[])null);

}catch(InvocationTargetException e) {

Unsafe.getUnsafe().throwException(e.getTargetException());//Not reached

return null;

}

}private volatile transient ConstructorcachedConstructor;private volatile transient Class>newInstanceCallerCache;/*** Determines if the specified {@codeObject} is assignment-compatible

* with the object represented by this {@codeClass}. This method is

* the dynamic equivalent of the Java language {@codeinstanceof}

* operator. The method returns {@codetrue} if the specified

* {@codeObject} argument is non-null and can be cast to the

* reference type represented by this {@codeClass} object without

* raising a {@codeClassCastException.} It returns {@codefalse}

* otherwise.

*

*

Specifically, if this {@codeClass} object represents a

* declared class, this method returns {@codetrue} if the specified

* {@codeObject} argument is an instance of the represented class (or

* of any of its subclasses); it returns {@codefalse} otherwise. If

* this {@codeClass} object represents an array class, this method

* returns {@codetrue} if the specified {@codeObject} argument

* can be converted to an object of the array class by an identity

* conversion or by a widening reference conversion; it returns

* {@codefalse} otherwise. If this {@codeClass} object

* represents an interface, this method returns {@codetrue} if the

* class or any superclass of the specified {@codeObject} argument

* implements this interface; it returns {@codefalse} otherwise. If

* this {@codeClass} object represents a primitive type, this method

* returns {@codefalse}.

*

*@paramobj the object to check

*@returntrue if {@codeobj} is an instance of this class

*

*@sinceJDK1.1*/

public native booleanisInstance(Object obj);/*** Determines if the class or interface represented by this

* {@codeClass} object is either the same as, or is a superclass or

* superinterface of, the class or interface represented by the specified

* {@codeClass} parameter. It returns {@codetrue} if so;

* otherwise it returns {@codefalse}. If this {@codeClass}

* object represents a primitive type, this method returns

* {@codetrue} if the specified {@codeClass} parameter is

* exactly this {@codeClass} object; otherwise it returns

* {@codefalse}.

*

*

Specifically, this method tests whether the type represented by the

* specified {@codeClass} parameter can be converted to the type

* represented by this {@codeClass} object via an identity conversion

* or via a widening reference conversion. See The Java Language

* Specification, sections 5.1.1 and 5.1.4 , for details.

*

*@paramcls the {@codeClass} object to be checked

*@returnthe {@codeboolean} value indicating whether objects of the

* type {@codecls} can be assigned to objects of this class

*@exceptionNullPointerException if the specified Class parameter is

* null.

*@sinceJDK1.1*/

public native boolean isAssignableFrom(Class>cls);/*** Determines if the specified {@codeClass} object represents an

* interface type.

*

*@return{@codetrue} if this object represents an interface;

* {@codefalse} otherwise.*/

public native booleanisInterface();/*** Determines if this {@codeClass} object represents an array class.

*

*@return{@codetrue} if this object represents an array class;

* {@codefalse} otherwise.

*@sinceJDK1.1*/

public native booleanisArray();/*** Determines if the specified {@codeClass} object represents a

* primitive type.

*

*

There are nine predefined {@codeClass} objects to represent

* the eight primitive types and void. These are created by the Java

* Virtual Machine, and have the same names as the primitive types that

* they represent, namely {@codeboolean}, {@codebyte},

* {@codechar}, {@codeshort}, {@codeint},

* {@codelong}, {@codefloat}, and {@codedouble}.

*

*

These objects may only be accessed via the following public static

* final variables, and are the only {@codeClass} objects for which

* this method returns {@codetrue}.

*

*@returntrue if and only if this class represents a primitive type

*

*@seejava.lang.Boolean#TYPE

*@seejava.lang.Character#TYPE

*@seejava.lang.Byte#TYPE

*@seejava.lang.Short#TYPE

*@seejava.lang.Integer#TYPE

*@seejava.lang.Long#TYPE

*@seejava.lang.Float#TYPE

*@seejava.lang.Double#TYPE

*@seejava.lang.Void#TYPE

*@sinceJDK1.1*/

public native booleanisPrimitive();/*** Returns true if this {@codeClass} object represents an annotation

* type. Note that if this method returns true, {@link#isInterface()}

* would also return true, as all annotation types are also interfaces.

*

*@return{@codetrue} if this class object represents an annotation

* type; {@codefalse} otherwise

*@since1.5*/

public booleanisAnnotation() {return (getModifiers() & ANNOTATION) != 0;

}/*** Returns {@codetrue} if this class is a synthetic class;

* returns {@codefalse} otherwise.

*@return{@codetrue} if and only if this class is a synthetic class as

* defined by the Java Language Specification.

* @jls 13.1 The Form of a Binary

*@since1.5*/

public booleanisSynthetic() {return (getModifiers() & SYNTHETIC) != 0;

}/*** Returns the name of the entity (class, interface, array class,

* primitive type, or void) represented by this {@codeClass} object,

* as a {@codeString}.

*

*

If this class object represents a reference type that is not an

* array type then the binary name of the class is returned, as specified

* by

* The Java™ Language Specification.

*

*

If this class object represents a primitive type or void, then the

* name returned is a {@codeString} equal to the Java language

* keyword corresponding to the primitive type or void.

*

*

If this class object represents a class of arrays, then the internal

* form of the name consists of the name of the element type preceded by

* one or more '{@code[}' characters representing the depth of the array

* nesting. The encoding of element type names is as follows:

*

*

*

Element Type     Encoding

*

boolean     Z

*

byte     B

*

char     C

*

class or interface

*

    L classname;

*

double     D

*

float     F

*

int     I

*

long     J

*

short     S

*

*

*

The class or interface name classname is the binary name of

* the class specified above.

*

*

Examples:

*

 
  

* String.class.getName()

* returns "java.lang.String"

* byte.class.getName()

* returns "byte"

* (new Object[3]).getClass().getName()

* returns "[Ljava.lang.Object;"

* (new int[3][4][5][6][7][8][9]).getClass().getName()

* returns "[[[[[[[I"

*

*

*@returnthe name of the class or interface

* represented by this object.*/

publicString getName() {

String name= this.name;if (name == null)this.name = name =getName0();returnname;

}//cache the name to reduce the number of calls into the VM

private transientString name;private nativeString getName0();/*** Returns the class loader for the class. Some implementations may use

* null to represent the bootstrap class loader. This method will return

* null in such implementations if this class was loaded by the bootstrap

* class loader.

*

*

If a security manager is present, and the caller's class loader is

* not null and the caller's class loader is not the same as or an ancestor of

* the class loader for the class whose class loader is requested, then

* this method calls the security manager's {@codecheckPermission}

* method with a {@codeRuntimePermission("getClassLoader")}

* permission to ensure it's ok to access the class loader for the class.

*

*

If this object

* represents a primitive type or void, null is returned.

*

*@returnthe class loader that loaded the class or interface

* represented by this object.

*@throwsSecurityException

* if a security manager exists and its

* {@codecheckPermission} method denies

* access to the class loader for the class.

*@seejava.lang.ClassLoader

*@seeSecurityManager#checkPermission

*@seejava.lang.RuntimePermission*/@CallerSensitivepublicClassLoader getClassLoader() {

ClassLoader cl=getClassLoader0();if (cl == null)return null;

SecurityManager sm=System.getSecurityManager();if (sm != null) {

ClassLoader.checkClassLoaderPermission(cl, Reflection.getCallerClass());

}returncl;

}//Package-private to allow ClassLoader access

ClassLoader getClassLoader0() { returnclassLoader; }//Initialized in JVM not by private constructor//This field is filtered from reflection access, i.e. getDeclaredField//will throw NoSuchFieldException

private finalClassLoader classLoader;/*** Returns an array of {@codeTypeVariable} objects that represent the

* type variables declared by the generic declaration represented by this

* {@codeGenericDeclaration} object, in declaration order. Returns an

* array of length 0 if the underlying generic declaration declares no type

* variables.

*

*@returnan array of {@codeTypeVariable} objects that represent

* the type variables declared by this generic declaration

*@throwsjava.lang.reflect.GenericSignatureFormatError if the generic

* signature of this generic declaration does not conform to

* the format specified in

* The Java™ Virtual Machine Specification

*@since1.5*/@SuppressWarnings("unchecked")public TypeVariable>[] getTypeParameters() {

ClassRepository info=getGenericInfo();if (info != null)return (TypeVariable>[])info.getTypeParameters();else

return (TypeVariable>[])new TypeVariable>[0];

}/*** Returns the {@codeClass} representing the superclass of the entity

* (class, interface, primitive type or void) represented by this

* {@codeClass}. If this {@codeClass} represents either the

* {@codeObject} class, an interface, a primitive type, or void, then

* null is returned. If this object represents an array class then the

* {@codeClass} object representing the {@codeObject} class is

* returned.

*

*@returnthe superclass of the class represented by this object.*/

public native Class super T>getSuperclass();/*** Returns the {@codeType} representing the direct superclass of

* the entity (class, interface, primitive type or void) represented by

* this {@codeClass}.

*

*

If the superclass is a parameterized type, the {@codeType}

* object returned must accurately reflect the actual type

* parameters used in the source code. The parameterized type

* representing the superclass is created if it had not been

* created before. See the declaration of {@link* java.lang.reflect.ParameterizedType ParameterizedType} for the

* semantics of the creation process for parameterized types. If

* this {@codeClass} represents either the {@codeObject}

* class, an interface, a primitive type, or void, then null is

* returned. If this object represents an array class then the

* {@codeClass} object representing the {@codeObject} class is

* returned.

*

*@throwsjava.lang.reflect.GenericSignatureFormatError if the generic

* class signature does not conform to the format specified in

* The Java™ Virtual Machine Specification

*@throwsTypeNotPresentException if the generic superclass

* refers to a non-existent type declaration

*@throwsjava.lang.reflect.MalformedParameterizedTypeException if the

* generic superclass refers to a parameterized type that cannot be

* instantiated for any reason

*@returnthe superclass of the class represented by this object

*@since1.5*/

publicType getGenericSuperclass() {

ClassRepository info=getGenericInfo();if (info == null) {returngetSuperclass();

}//Historical irregularity://Generic signature marks interfaces with superclass = Object//but this API returns null for interfaces

if(isInterface()) {return null;

}returninfo.getSuperclass();

}/*** Gets the package for this class. The class loader of this class is used

* to find the package. If the class was loaded by the bootstrap class

* loader the set of packages loaded from CLASSPATH is searched to find the

* package of the class. Null is returned if no package object was created

* by the class loader of this class.

*

*

Packages have attributes for versions and specifications only if the

* information was defined in the manifests that accompany the classes, and

* if the class loader created the package instance with the attributes

* from the manifest.

*

*@returnthe package of the class, or null if no package

* information is available from the archive or codebase.*/

publicPackage getPackage() {return Package.getPackage(this);

}/*** Determines the interfaces implemented by the class or interface

* represented by this object.

*

*

If this object represents a class, the return value is an array

* containing objects representing all interfaces implemented by the

* class. The order of the interface objects in the array corresponds to

* the order of the interface names in the {@codeimplements} clause

* of the declaration of the class represented by this object. For

* example, given the declaration:

*

* {@codeclass Shimmer implements FloorWax, DessertTopping { ... }}

*

* suppose the value of {@codes} is an instance of

* {@codeShimmer}; the value of the expression:

*

* {@codes.getClass().getInterfaces()[0]}

*

* is the {@codeClass} object that represents interface

* {@codeFloorWax}; and the value of:

*

* {@codes.getClass().getInterfaces()[1]}

*

* is the {@codeClass} object that represents interface

* {@codeDessertTopping}.

*

*

If this object represents an interface, the array contains objects

* representing all interfaces extended by the interface. The order of the

* interface objects in the array corresponds to the order of the interface

* names in the {@codeextends} clause of the declaration of the

* interface represented by this object.

*

*

If this object represents a class or interface that implements no

* interfaces, the method returns an array of length 0.

*

*

If this object represents a primitive type or void, the method

* returns an array of length 0.

*

*

If this {@codeClass} object represents an array type, the

* interfaces {@codeCloneable} and {@codejava.io.Serializable} are

* returned in that order.

*

*@returnan array of interfaces implemented by this class.*/

public Class>[] getInterfaces() {

ReflectionData rd =reflectionData();if (rd == null) {//no cloning required

returngetInterfaces0();

}else{

Class>[] interfaces =rd.interfaces;if (interfaces == null) {

interfaces=getInterfaces0();

rd.interfaces=interfaces;

}//defensively copy before handing over to user code

returninterfaces.clone();

}

}private native Class>[] getInterfaces0();/*** Returns the {@codeType}s representing the interfaces

* directly implemented by the class or interface represented by

* this object.

*

*

If a superinterface is a parameterized type, the

* {@codeType} object returned for it must accurately reflect

* the actual type parameters used in the source code. The

* parameterized type representing each superinterface is created

* if it had not been created before. See the declaration of

* {@linkjava.lang.reflect.ParameterizedType ParameterizedType}

* for the semantics of the creation process for parameterized

* types.

*

*

If this object represents a class, the return value is an

* array containing objects representing all interfaces

* implemented by the class. The order of the interface objects in

* the array corresponds to the order of the interface names in

* the {@codeimplements} clause of the declaration of the class

* represented by this object. In the case of an array class, the

* interfaces {@codeCloneable} and {@codeSerializable} are

* returned in that order.

*

*

If this object represents an interface, the array contains

* objects representing all interfaces directly extended by the

* interface. The order of the interface objects in the array

* corresponds to the order of the interface names in the

* {@codeextends} clause of the declaration of the interface

* represented by this object.

*

*

If this object represents a class or interface that

* implements no interfaces, the method returns an array of length

* 0.

*

*

If this object represents a primitive type or void, the

* method returns an array of length 0.

*

*@throwsjava.lang.reflect.GenericSignatureFormatError

* if the generic class signature does not conform to the format

* specified in

* The Java™ Virtual Machine Specification

*@throwsTypeNotPresentException if any of the generic

* superinterfaces refers to a non-existent type declaration

*@throwsjava.lang.reflect.MalformedParameterizedTypeException

* if any of the generic superinterfaces refer to a parameterized

* type that cannot be instantiated for any reason

*@returnan array of interfaces implemented by this class

*@since1.5*/

publicType[] getGenericInterfaces() {

ClassRepository info=getGenericInfo();return (info == null) ?getInterfaces() : info.getSuperInterfaces();

}/*** Returns the {@codeClass} representing the component type of an

* array. If this class does not represent an array class this method

* returns null.

*

*@returnthe {@codeClass} representing the component type of this

* class if this class is an array

*@seejava.lang.reflect.Array

*@sinceJDK1.1*/

public native Class>getComponentType();/*** Returns the Java language modifiers for this class or interface, encoded

* in an integer. The modifiers consist of the Java Virtual Machine's

* constants for {@codepublic}, {@codeprotected},

* {@codeprivate}, {@codefinal}, {@codestatic},

* {@codeabstract} and {@codeinterface}; they should be decoded

* using the methods of class {@codeModifier}.

*

*

If the underlying class is an array class, then its

* {@codepublic}, {@codeprivate} and {@codeprotected}

* modifiers are the same as those of its component type. If this

* {@codeClass} represents a primitive type or void, its

* {@codepublic} modifier is always {@codetrue}, and its

* {@codeprotected} and {@codeprivate} modifiers are always

* {@codefalse}. If this object represents an array class, a

* primitive type or void, then its {@codefinal} modifier is always

* {@codetrue} and its interface modifier is always

* {@codefalse}. The values of its other modifiers are not determined

* by this specification.

*

*

The modifier encodings are defined in The Java Virtual Machine

* Specification, table 4.1.

*

*@returnthe {@codeint} representing the modifiers for this class

*@seejava.lang.reflect.Modifier

*@sinceJDK1.1*/

public native intgetModifiers();/*** Gets the signers of this class.

*

*@returnthe signers of this class, or null if there are no signers. In

* particular, this method returns null if this object represents

* a primitive type or void.

*@sinceJDK1.1*/

public nativeObject[] getSigners();/*** Set the signers of this class.*/

native voidsetSigners(Object[] signers);/*** If this {@codeClass} object represents a local or anonymous

* class within a method, returns a {@link* java.lang.reflect.Method Method} object representing the

* immediately enclosing method of the underlying class. Returns

* {@codenull} otherwise.

*

* In particular, this method returns {@codenull} if the underlying

* class is a local or anonymous class immediately enclosed by a type

* declaration, instance initializer or static initializer.

*

*@returnthe immediately enclosing method of the underlying class, if

* that class is a local or anonymous class; otherwise {@codenull}.

*

*@throwsSecurityException

* If a security manager, s, is present and any of the

* following conditions is met:

*

*

*

*

the caller's class loader is not the same as the

* class loader of the enclosing class and invocation of

* {@linkSecurityManager#checkPermission

* s.checkPermission} method with

* {@codeRuntimePermission("accessDeclaredMembers")}

* denies access to the methods within the enclosing class

*

*

the caller's class loader is not the same as or an

* ancestor of the class loader for the enclosing class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of the enclosing class

*

*

*@since1.5*/@CallerSensitivepublic Method getEnclosingMethod() throwsSecurityException {

EnclosingMethodInfo enclosingInfo=getEnclosingMethodInfo();if (enclosingInfo == null)return null;else{if (!enclosingInfo.isMethod())return null;

MethodRepository typeInfo=MethodRepository.make(enclosingInfo.getDescriptor(),

getFactory());

Class> returnType =toClass(typeInfo.getReturnType());

Type [] parameterTypes=typeInfo.getParameterTypes();

Class>[] parameterClasses = new Class>[parameterTypes.length];//Convert Types to Classes; returned types *should*//be class objects since the methodDescriptor's used//don't have generics information

for(int i = 0; i < parameterClasses.length; i++)

parameterClasses[i]=toClass(parameterTypes[i]);//Perform access check

Class> enclosingCandidate =enclosingInfo.getEnclosingClass();

enclosingCandidate.checkMemberAccess(Member.DECLARED,

Reflection.getCallerClass(),true);/** Loop over all declared methods; match method name,

* number of and type of parameters, *and* return

* type. Matching return type is also necessary

* because of covariant returns, etc.*/

for(Method m: enclosingCandidate.getDeclaredMethods()) {if(m.getName().equals(enclosingInfo.getName()) ) {

Class>[] candidateParamClasses =m.getParameterTypes();if (candidateParamClasses.length ==parameterClasses.length) {boolean matches = true;for(int i = 0; i < candidateParamClasses.length; i++) {if (!candidateParamClasses[i].equals(parameterClasses[i])) {

matches= false;break;

}

}if (matches) { //finally, check return type

if(m.getReturnType().equals(returnType) )returnm;

}

}

}

}throw new InternalError("Enclosing method not found");

}

}private nativeObject[] getEnclosingMethod0();privateEnclosingMethodInfo getEnclosingMethodInfo() {

Object[] enclosingInfo=getEnclosingMethod0();if (enclosingInfo == null)return null;else{return newEnclosingMethodInfo(enclosingInfo);

}

}private final static classEnclosingMethodInfo {private Class>enclosingClass;privateString name;privateString descriptor;privateEnclosingMethodInfo(Object[] enclosingInfo) {if (enclosingInfo.length != 3)throw new InternalError("Malformed enclosing method information");try{//The array is expected to have three elements://the immediately enclosing class

enclosingClass = (Class>) enclosingInfo[0];assert(enclosingClass != null);//the immediately enclosing method or constructor's//name (can be null).

name = (String) enclosingInfo[1];//the immediately enclosing method or constructor's//descriptor (null iff name is).

descriptor = (String) enclosingInfo[2];assert((name != null && descriptor != null) || name ==descriptor);

}catch(ClassCastException cce) {throw new InternalError("Invalid type in enclosing method information", cce);

}

}booleanisPartial() {return enclosingClass == null || name == null || descriptor == null;

}boolean isConstructor() { return !isPartial() && "".equals(name); }boolean isMethod() { return !isPartial() && !isConstructor() && !"".equals(name); }

Class> getEnclosingClass() { returnenclosingClass; }

String getName() {returnname; }

String getDescriptor() {returndescriptor; }

}private static Class>toClass(Type o) {if (o instanceofGenericArrayType)returnArray.newInstance(toClass(((GenericArrayType)o).getGenericComponentType()),0)

.getClass();return (Class>)o;

}/*** If this {@codeClass} object represents a local or anonymous

* class within a constructor, returns a {@link* java.lang.reflect.Constructor Constructor} object representing

* the immediately enclosing constructor of the underlying

* class. Returns {@codenull} otherwise. In particular, this

* method returns {@codenull} if the underlying class is a local

* or anonymous class immediately enclosed by a type declaration,

* instance initializer or static initializer.

*

*@returnthe immediately enclosing constructor of the underlying class, if

* that class is a local or anonymous class; otherwise {@codenull}.

*@throwsSecurityException

* If a security manager, s, is present and any of the

* following conditions is met:

*

*

*

*

the caller's class loader is not the same as the

* class loader of the enclosing class and invocation of

* {@linkSecurityManager#checkPermission

* s.checkPermission} method with

* {@codeRuntimePermission("accessDeclaredMembers")}

* denies access to the constructors within the enclosing class

*

*

the caller's class loader is not the same as or an

* ancestor of the class loader for the enclosing class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of the enclosing class

*

*

*@since1.5*/@CallerSensitivepublic Constructor> getEnclosingConstructor() throwsSecurityException {

EnclosingMethodInfo enclosingInfo=getEnclosingMethodInfo();if (enclosingInfo == null)return null;else{if (!enclosingInfo.isConstructor())return null;

ConstructorRepository typeInfo=ConstructorRepository.make(enclosingInfo.getDescriptor(),

getFactory());

Type [] parameterTypes=typeInfo.getParameterTypes();

Class>[] parameterClasses = new Class>[parameterTypes.length];//Convert Types to Classes; returned types *should*//be class objects since the methodDescriptor's used//don't have generics information

for(int i = 0; i < parameterClasses.length; i++)

parameterClasses[i]=toClass(parameterTypes[i]);//Perform access check

Class> enclosingCandidate =enclosingInfo.getEnclosingClass();

enclosingCandidate.checkMemberAccess(Member.DECLARED,

Reflection.getCallerClass(),true);/** Loop over all declared constructors; match number

* of and type of parameters.*/

for(Constructor>c: enclosingCandidate.getDeclaredConstructors()) {

Class>[] candidateParamClasses =c.getParameterTypes();if (candidateParamClasses.length ==parameterClasses.length) {boolean matches = true;for(int i = 0; i < candidateParamClasses.length; i++) {if (!candidateParamClasses[i].equals(parameterClasses[i])) {

matches= false;break;

}

}if(matches)returnc;

}

}throw new InternalError("Enclosing constructor not found");

}

}/*** If the class or interface represented by this {@codeClass} object

* is a member of another class, returns the {@codeClass} object

* representing the class in which it was declared. This method returns

* null if this class or interface is not a member of any other class. If

* this {@codeClass} object represents an array class, a primitive

* type, or void,then this method returns null.

*

*@returnthe declaring class for this class

*@throwsSecurityException

* If a security manager, s, is present and the caller's

* class loader is not the same as or an ancestor of the class

* loader for the declaring class and invocation of {@link* SecurityManager#checkPackageAccess s.checkPackageAccess()}

* denies access to the package of the declaring class

*@sinceJDK1.1*/@CallerSensitivepublic Class> getDeclaringClass() throwsSecurityException {final Class> candidate =getDeclaringClass0();if (candidate != null)

candidate.checkPackageAccess(

ClassLoader.getClassLoader(Reflection.getCallerClass()),true);returncandidate;

}private native Class>getDeclaringClass0();/*** Returns the immediately enclosing class of the underlying

* class. If the underlying class is a top level class this

* method returns {@codenull}.

*@returnthe immediately enclosing class of the underlying class

*@exceptionSecurityException

* If a security manager, s, is present and the caller's

* class loader is not the same as or an ancestor of the class

* loader for the enclosing class and invocation of {@link* SecurityManager#checkPackageAccess s.checkPackageAccess()}

* denies access to the package of the enclosing class

*@since1.5*/@CallerSensitivepublic Class> getEnclosingClass() throwsSecurityException {//There are five kinds of classes (or interfaces)://a) Top level classes//b) Nested classes (static member classes)//c) Inner classes (non-static member classes)//d) Local classes (named classes declared within a method)//e) Anonymous classes//JVM Spec 4.8.6: A class must have an EnclosingMethod//attribute if and only if it is a local class or an//anonymous class.

EnclosingMethodInfo enclosingInfo =getEnclosingMethodInfo();

Class>enclosingCandidate;if (enclosingInfo == null) {//This is a top level or a nested class or an inner class (a, b, or c)

enclosingCandidate =getDeclaringClass();

}else{

Class> enclosingClass =enclosingInfo.getEnclosingClass();//This is a local class or an anonymous class (d or e)

if (enclosingClass == this || enclosingClass == null)throw new InternalError("Malformed enclosing method information");elseenclosingCandidate=enclosingClass;

}if (enclosingCandidate != null)

enclosingCandidate.checkPackageAccess(

ClassLoader.getClassLoader(Reflection.getCallerClass()),true);returnenclosingCandidate;

}/*** Returns the simple name of the underlying class as given in the

* source code. Returns an empty string if the underlying class is

* anonymous.

*

*

The simple name of an array is the simple name of the

* component type with "[]" appended. In particular the simple

* name of an array whose component type is anonymous is "[]".

*

*@returnthe simple name of the underlying class

*@since1.5*/

publicString getSimpleName() {if(isArray())return getComponentType().getSimpleName()+"[]";

String simpleName=getSimpleBinaryName();if (simpleName == null) { //top level class

simpleName =getName();return simpleName.substring(simpleName.lastIndexOf(".")+1); //strip the package name

}//According to JLS3 "Binary Compatibility" (13.1) the binary//name of non-package classes (not top level) is the binary//name of the immediately enclosing class followed by a '$' followed by://(for nested and inner classes): the simple name.//(for local classes): 1 or more digits followed by the simple name.//(for anonymous classes): 1 or more digits.//Since getSimpleBinaryName() will strip the binary name of//the immediatly enclosing class, we are now looking at a//string that matches the regular expression "\$[0-9]*"//followed by a simple name (considering the simple of an//anonymous class to be the empty string).//Remove leading "\$[0-9]*" from the name

int length =simpleName.length();if (length < 1 || simpleName.charAt(0) != '$')throw new InternalError("Malformed class name");int index = 1;while (index < length &&isAsciiDigit(simpleName.charAt(index)))

index++;//Eventually, this is the empty string iff this is an anonymous class

returnsimpleName.substring(index);

}/*** Return an informative string for the name of this type.

*

*@returnan informative string for the name of this type

*@since1.8*/

publicString getTypeName() {if(isArray()) {try{

Class> cl = this;int dimensions = 0;while(cl.isArray()) {

dimensions++;

cl=cl.getComponentType();

}

StringBuilder sb= newStringBuilder();

sb.append(cl.getName());for (int i = 0; i < dimensions; i++) {

sb.append("[]");

}returnsb.toString();

}catch (Throwable e) { /*FALLTHRU*/}

}returngetName();

}/*** Character.isDigit answers {@codetrue} to some non-ascii

* digits. This one does not.*/

private static boolean isAsciiDigit(charc) {return '0' <= c && c <= '9';

}/*** Returns the canonical name of the underlying class as

* defined by the Java Language Specification. Returns null if

* the underlying class does not have a canonical name (i.e., if

* it is a local or anonymous class or an array whose component

* type does not have a canonical name).

*@returnthe canonical name of the underlying class if it exists, and

* {@codenull} otherwise.

*@since1.5*/

publicString getCanonicalName() {if(isArray()) {

String canonicalName=getComponentType().getCanonicalName();if (canonicalName != null)return canonicalName + "[]";else

return null;

}if(isLocalOrAnonymousClass())return null;

Class> enclosingClass =getEnclosingClass();if (enclosingClass == null) { //top level class

returngetName();

}else{

String enclosingName=enclosingClass.getCanonicalName();if (enclosingName == null)return null;return enclosingName + "." +getSimpleName();

}

}/*** Returns {@codetrue} if and only if the underlying class

* is an anonymous class.

*

*@return{@codetrue} if and only if this class is an anonymous class.

*@since1.5*/

public booleanisAnonymousClass() {return "".equals(getSimpleName());

}/*** Returns {@codetrue} if and only if the underlying class

* is a local class.

*

*@return{@codetrue} if and only if this class is a local class.

*@since1.5*/

public booleanisLocalClass() {return isLocalOrAnonymousClass() && !isAnonymousClass();

}/*** Returns {@codetrue} if and only if the underlying class

* is a member class.

*

*@return{@codetrue} if and only if this class is a member class.

*@since1.5*/

public booleanisMemberClass() {return getSimpleBinaryName() != null && !isLocalOrAnonymousClass();

}/*** Returns the "simple binary name" of the underlying class, i.e.,

* the binary name without the leading enclosing class name.

* Returns {@codenull} if the underlying class is a top level

* class.*/

privateString getSimpleBinaryName() {

Class> enclosingClass =getEnclosingClass();if (enclosingClass == null) //top level class

return null;//Otherwise, strip the enclosing class' name

try{returngetName().substring(enclosingClass.getName().length());

}catch(IndexOutOfBoundsException ex) {throw new InternalError("Malformed class name", ex);

}

}/*** Returns {@codetrue} if this is a local class or an anonymous

* class. Returns {@codefalse} otherwise.*/

private booleanisLocalOrAnonymousClass() {//JVM Spec 4.8.6: A class must have an EnclosingMethod//attribute if and only if it is a local class or an//anonymous class.

return getEnclosingMethodInfo() != null;

}/*** Returns an array containing {@codeClass} objects representing all

* the public classes and interfaces that are members of the class

* represented by this {@codeClass} object. This includes public

* class and interface members inherited from superclasses and public class

* and interface members declared by the class. This method returns an

* array of length 0 if this {@codeClass} object has no public member

* classes or interfaces. This method also returns an array of length 0 if

* this {@codeClass} object represents a primitive type, an array

* class, or void.

*

*@returnthe array of {@codeClass} objects representing the public

* members of this class

*@throwsSecurityException

* If a security manager, s, is present and

* the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class.

*

*@sinceJDK1.1*/@CallerSensitivepublic Class>[] getClasses() {

checkMemberAccess(Member.PUBLIC, Reflection.getCallerClass(),false);//Privileged so this implementation can look at DECLARED classes,//something the caller might not have privilege to do. The code here//is allowed to look at DECLARED classes because (1) it does not hand//out anything other than public members and (2) public member access//has already been ok'd by the SecurityManager.

returnjava.security.AccessController.doPrivileged(new java.security.PrivilegedAction[]>() {public Class>[] run() {

List> list = new ArrayList<>();

Class> currentClass = Class.this;while (currentClass != null) {

Class>[] members =currentClass.getDeclaredClasses();for (int i = 0; i < members.length; i++) {if(Modifier.isPublic(members[i].getModifiers())) {

list.add(members[i]);

}

}

currentClass=currentClass.getSuperclass();

}return list.toArray(new Class>[0]);

}

});

}/*** Returns an array containing {@codeField} objects reflecting all

* the accessible public fields of the class or interface represented by

* this {@codeClass} object.

*

*

If this {@codeClass} object represents a class or interface with no

* no accessible public fields, then this method returns an array of length

* 0.

*

*

If this {@codeClass} object represents a class, then this method

* returns the public fields of the class and of all its superclasses.

*

*

If this {@codeClass} object represents an interface, then this

* method returns the fields of the interface and of all its

* superinterfaces.

*

*

If this {@codeClass} object represents an array type, a primitive

* type, or void, then this method returns an array of length 0.

*

*

The elements in the returned array are not sorted and are not in any

* particular order.

*

*@returnthe array of {@codeField} objects representing the

* public fields

*@throwsSecurityException

* If a security manager, s, is present and

* the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class.

*

*@sinceJDK1.1

* @jls 8.2 Class Members

* @jls 8.3 Field Declarations*/@CallerSensitivepublic Field[] getFields() throwsSecurityException {

checkMemberAccess(Member.PUBLIC, Reflection.getCallerClass(),true);return copyFields(privateGetPublicFields(null));

}/*** Returns an array containing {@codeMethod} objects reflecting all the

* public methods of the class or interface represented by this {@code* Class} object, including those declared by the class or interface and

* those inherited from superclasses and superinterfaces.

*

*

If this {@codeClass} object represents a type that has multiple

* public methods with the same name and parameter types, but different

* return types, then the returned array has a {@codeMethod} object for

* each such method.

*

*

If this {@codeClass} object represents a type with a class

* initialization method {@code}, then the returned array does

* not have a corresponding {@codeMethod} object.

*

*

If this {@codeClass} object represents an array type, then the

* returned array has a {@codeMethod} object for each of the public

* methods inherited by the array type from {@codeObject}. It does not

* contain a {@codeMethod} object for {@codeclone()}.

*

*

If this {@codeClass} object represents an interface then the

* returned array does not contain any implicitly declared methods from

* {@codeObject}. Therefore, if no methods are explicitly declared in

* this interface or any of its superinterfaces then the returned array

* has length 0. (Note that a {@codeClass} object which represents a class

* always has public methods, inherited from {@codeObject}.)

*

*

If this {@codeClass} object represents a primitive type or void,

* then the returned array has length 0.

*

*

Static methods declared in superinterfaces of the class or interface

* represented by this {@codeClass} object are not considered members of

* the class or interface.

*

*

The elements in the returned array are not sorted and are not in any

* particular order.

*

*@returnthe array of {@codeMethod} objects representing the

* public methods of this class

*@throwsSecurityException

* If a security manager, s, is present and

* the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class.

*

* @jls 8.2 Class Members

* @jls 8.4 Method Declarations

*@sinceJDK1.1*/@CallerSensitivepublic Method[] getMethods() throwsSecurityException {

checkMemberAccess(Member.PUBLIC, Reflection.getCallerClass(),true);returncopyMethods(privateGetPublicMethods());

}/*** Returns an array containing {@codeConstructor} objects reflecting

* all the public constructors of the class represented by this

* {@codeClass} object. An array of length 0 is returned if the

* class has no public constructors, or if the class is an array class, or

* if the class reflects a primitive type or void.

*

* Note that while this method returns an array of {@code* Constructor} objects (that is an array of constructors from

* this class), the return type of this method is {@code* Constructor>[]} and not {@codeConstructor[]} as

* might be expected. This less informative return type is

* necessary since after being returned from this method, the

* array could be modified to hold {@codeConstructor} objects for

* different classes, which would violate the type guarantees of

* {@codeConstructor[]}.

*

*@returnthe array of {@codeConstructor} objects representing the

* public constructors of this class

*@throwsSecurityException

* If a security manager, s, is present and

* the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class.

*

*@sinceJDK1.1*/@CallerSensitivepublic Constructor>[] getConstructors() throwsSecurityException {

checkMemberAccess(Member.PUBLIC, Reflection.getCallerClass(),true);return copyConstructors(privateGetDeclaredConstructors(true));

}/*** Returns a {@codeField} object that reflects the specified public member

* field of the class or interface represented by this {@codeClass}

* object. The {@codename} parameter is a {@codeString} specifying the

* simple name of the desired field.

*

*

The field to be reflected is determined by the algorithm that

* follows. Let C be the class or interface represented by this object:

*

*

*

If C declares a public field with the name specified, that is the

* field to be reflected.

*

If no field was found in step 1 above, this algorithm is applied

* recursively to each direct superinterface of C. The direct

* superinterfaces are searched in the order they were declared.

*

If no field was found in steps 1 and 2 above, and C has a

* superclass S, then this algorithm is invoked recursively upon S.

* If C has no superclass, then a {@codeNoSuchFieldException}

* is thrown.

*

*

*

If this {@codeClass} object represents an array type, then this

* method does not find the {@codelength} field of the array type.

*

*@paramname the field name

*@returnthe {@codeField} object of this class specified by

* {@codename}

*@throwsNoSuchFieldException if a field with the specified name is

* not found.

*@throwsNullPointerException if {@codename} is {@codenull}

*@throwsSecurityException

* If a security manager, s, is present and

* the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class.

*

*@sinceJDK1.1

* @jls 8.2 Class Members

* @jls 8.3 Field Declarations*/@CallerSensitivepublicField getField(String name)throwsNoSuchFieldException, SecurityException {

checkMemberAccess(Member.PUBLIC, Reflection.getCallerClass(),true);

Field field=getField0(name);if (field == null) {throw newNoSuchFieldException(name);

}returnfield;

}/*** Returns a {@codeMethod} object that reflects the specified public

* member method of the class or interface represented by this

* {@codeClass} object. The {@codename} parameter is a

* {@codeString} specifying the simple name of the desired method. The

* {@codeparameterTypes} parameter is an array of {@codeClass}

* objects that identify the method's formal parameter types, in declared

* order. If {@codeparameterTypes} is {@codenull}, it is

* treated as if it were an empty array.

*

*

If the {@codename} is "{@code}" or "{@code}" a

* {@codeNoSuchMethodException} is raised. Otherwise, the method to

* be reflected is determined by the algorithm that follows. Let C be the

* class or interface represented by this object:

*

*

C is searched for a matching method, as defined below. If a

* matching method is found, it is reflected.

*

If no matching method is found by step 1 then:

*

*

If C is a class other than {@codeObject}, then this algorithm is

* invoked recursively on the superclass of C.

*

If C is the class {@codeObject}, or if C is an interface, then

* the superinterfaces of C (if any) are searched for a matching

* method. If any such method is found, it is reflected.

*

*

*

*

To find a matching method in a class or interface C:  If C

* declares exactly one public method with the specified name and exactly

* the same formal parameter types, that is the method reflected. If more

* than one such method is found in C, and one of these methods has a

* return type that is more specific than any of the others, that method is

* reflected; otherwise one of the methods is chosen arbitrarily.

*

*

Note that there may be more than one matching method in a

* class because while the Java language forbids a class to

* declare multiple methods with the same signature but different

* return types, the Java virtual machine does not. This

* increased flexibility in the virtual machine can be used to

* implement various language features. For example, covariant

* returns can be implemented with {@linkplain* java.lang.reflect.Method#isBridge bridge methods}; the bridge

* method and the method being overridden would have the same

* signature but different return types.

*

*

If this {@codeClass} object represents an array type, then this

* method does not find the {@codeclone()} method.

*

*

Static methods declared in superinterfaces of the class or interface

* represented by this {@codeClass} object are not considered members of

* the class or interface.

*

*@paramname the name of the method

*@paramparameterTypes the list of parameters

*@returnthe {@codeMethod} object that matches the specified

* {@codename} and {@codeparameterTypes}

*@throwsNoSuchMethodException if a matching method is not found

* or if the name is "<init>"or "<clinit>".

*@throwsNullPointerException if {@codename} is {@codenull}

*@throwsSecurityException

* If a security manager, s, is present and

* the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class.

*

* @jls 8.2 Class Members

* @jls 8.4 Method Declarations

*@sinceJDK1.1*/@CallerSensitivepublic Method getMethod(String name, Class>... parameterTypes)throwsNoSuchMethodException, SecurityException {

checkMemberAccess(Member.PUBLIC, Reflection.getCallerClass(),true);

Method method= getMethod0(name, parameterTypes, true);if (method == null) {throw new NoSuchMethodException(getName() + "." + name +argumentTypesToString(parameterTypes));

}returnmethod;

}/*** Returns a {@codeConstructor} object that reflects the specified

* public constructor of the class represented by this {@codeClass}

* object. The {@codeparameterTypes} parameter is an array of

* {@codeClass} objects that identify the constructor's formal

* parameter types, in declared order.

*

* If this {@codeClass} object represents an inner class

* declared in a non-static context, the formal parameter types

* include the explicit enclosing instance as the first parameter.

*

*

The constructor to reflect is the public constructor of the class

* represented by this {@codeClass} object whose formal parameter

* types match those specified by {@codeparameterTypes}.

*

*@paramparameterTypes the parameter array

*@returnthe {@codeConstructor} object of the public constructor that

* matches the specified {@codeparameterTypes}

*@throwsNoSuchMethodException if a matching method is not found.

*@throwsSecurityException

* If a security manager, s, is present and

* the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class.

*

*@sinceJDK1.1*/@CallerSensitivepublic Constructor getConstructor(Class>... parameterTypes)throwsNoSuchMethodException, SecurityException {

checkMemberAccess(Member.PUBLIC, Reflection.getCallerClass(),true);returngetConstructor0(parameterTypes, Member.PUBLIC);

}/*** Returns an array of {@codeClass} objects reflecting all the

* classes and interfaces declared as members of the class represented by

* this {@codeClass} object. This includes public, protected, default

* (package) access, and private classes and interfaces declared by the

* class, but excludes inherited classes and interfaces. This method

* returns an array of length 0 if the class declares no classes or

* interfaces as members, or if this {@codeClass} object represents a

* primitive type, an array class, or void.

*

*@returnthe array of {@codeClass} objects representing all the

* declared members of this class

*@throwsSecurityException

* If a security manager, s, is present and any of the

* following conditions is met:

*

*

*

*

the caller's class loader is not the same as the

* class loader of this class and invocation of

* {@linkSecurityManager#checkPermission

* s.checkPermission} method with

* {@codeRuntimePermission("accessDeclaredMembers")}

* denies access to the declared classes within this class

*

*

the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class

*

*

*

*@sinceJDK1.1*/@CallerSensitivepublic Class>[] getDeclaredClasses() throwsSecurityException {

checkMemberAccess(Member.DECLARED, Reflection.getCallerClass(),false);returngetDeclaredClasses0();

}/*** Returns an array of {@codeField} objects reflecting all the fields

* declared by the class or interface represented by this

* {@codeClass} object. This includes public, protected, default

* (package) access, and private fields, but excludes inherited fields.

*

*

If this {@codeClass} object represents a class or interface with no

* declared fields, then this method returns an array of length 0.

*

*

If this {@codeClass} object represents an array type, a primitive

* type, or void, then this method returns an array of length 0.

*

*

The elements in the returned array are not sorted and are not in any

* particular order.

*

*@returnthe array of {@codeField} objects representing all the

* declared fields of this class

*@throwsSecurityException

* If a security manager, s, is present and any of the

* following conditions is met:

*

*

*

*

the caller's class loader is not the same as the

* class loader of this class and invocation of

* {@linkSecurityManager#checkPermission

* s.checkPermission} method with

* {@codeRuntimePermission("accessDeclaredMembers")}

* denies access to the declared fields within this class

*

*

the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class

*

*

*

*@sinceJDK1.1

* @jls 8.2 Class Members

* @jls 8.3 Field Declarations*/@CallerSensitivepublic Field[] getDeclaredFields() throwsSecurityException {

checkMemberAccess(Member.DECLARED, Reflection.getCallerClass(),true);return copyFields(privateGetDeclaredFields(false));

}/***

* Returns an array containing {@codeMethod} objects reflecting all the

* declared methods of the class or interface represented by this {@code* Class} object, including public, protected, default (package)

* access, and private methods, but excluding inherited methods.

*

*

If this {@codeClass} object represents a type that has multiple

* declared methods with the same name and parameter types, but different

* return types, then the returned array has a {@codeMethod} object for

* each such method.

*

*

If this {@codeClass} object represents a type that has a class

* initialization method {@code}, then the returned array does

* not have a corresponding {@codeMethod} object.

*

*

If this {@codeClass} object represents a class or interface with no

* declared methods, then the returned array has length 0.

*

*

If this {@codeClass} object represents an array type, a primitive

* type, or void, then the returned array has length 0.

*

*

The elements in the returned array are not sorted and are not in any

* particular order.

*

*@returnthe array of {@codeMethod} objects representing all the

* declared methods of this class

*@throwsSecurityException

* If a security manager, s, is present and any of the

* following conditions is met:

*

*

*

*

the caller's class loader is not the same as the

* class loader of this class and invocation of

* {@linkSecurityManager#checkPermission

* s.checkPermission} method with

* {@codeRuntimePermission("accessDeclaredMembers")}

* denies access to the declared methods within this class

*

*

the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class

*

*

*

* @jls 8.2 Class Members

* @jls 8.4 Method Declarations

*@sinceJDK1.1*/@CallerSensitivepublic Method[] getDeclaredMethods() throwsSecurityException {

checkMemberAccess(Member.DECLARED, Reflection.getCallerClass(),true);return copyMethods(privateGetDeclaredMethods(false));

}/*** Returns an array of {@codeConstructor} objects reflecting all the

* constructors declared by the class represented by this

* {@codeClass} object. These are public, protected, default

* (package) access, and private constructors. The elements in the array

* returned are not sorted and are not in any particular order. If the

* class has a default constructor, it is included in the returned array.

* This method returns an array of length 0 if this {@codeClass}

* object represents an interface, a primitive type, an array class, or

* void.

*

*

See The Java Language Specification, section 8.2.

*

*@returnthe array of {@codeConstructor} objects representing all the

* declared constructors of this class

*@throwsSecurityException

* If a security manager, s, is present and any of the

* following conditions is met:

*

*

*

*

the caller's class loader is not the same as the

* class loader of this class and invocation of

* {@linkSecurityManager#checkPermission

* s.checkPermission} method with

* {@codeRuntimePermission("accessDeclaredMembers")}

* denies access to the declared constructors within this class

*

*

the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class

*

*

*

*@sinceJDK1.1*/@CallerSensitivepublic Constructor>[] getDeclaredConstructors() throwsSecurityException {

checkMemberAccess(Member.DECLARED, Reflection.getCallerClass(),true);return copyConstructors(privateGetDeclaredConstructors(false));

}/*** Returns a {@codeField} object that reflects the specified declared

* field of the class or interface represented by this {@codeClass}

* object. The {@codename} parameter is a {@codeString} that specifies

* the simple name of the desired field.

*

*

If this {@codeClass} object represents an array type, then this

* method does not find the {@codelength} field of the array type.

*

*@paramname the name of the field

*@returnthe {@codeField} object for the specified field in this

* class

*@throwsNoSuchFieldException if a field with the specified name is

* not found.

*@throwsNullPointerException if {@codename} is {@codenull}

*@throwsSecurityException

* If a security manager, s, is present and any of the

* following conditions is met:

*

*

*

*

the caller's class loader is not the same as the

* class loader of this class and invocation of

* {@linkSecurityManager#checkPermission

* s.checkPermission} method with

* {@codeRuntimePermission("accessDeclaredMembers")}

* denies access to the declared field

*

*

the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class

*

*

*

*@sinceJDK1.1

* @jls 8.2 Class Members

* @jls 8.3 Field Declarations*/@CallerSensitivepublicField getDeclaredField(String name)throwsNoSuchFieldException, SecurityException {

checkMemberAccess(Member.DECLARED, Reflection.getCallerClass(),true);

Field field= searchFields(privateGetDeclaredFields(false), name);if (field == null) {throw newNoSuchFieldException(name);

}returnfield;

}/*** Returns a {@codeMethod} object that reflects the specified

* declared method of the class or interface represented by this

* {@codeClass} object. The {@codename} parameter is a

* {@codeString} that specifies the simple name of the desired

* method, and the {@codeparameterTypes} parameter is an array of

* {@codeClass} objects that identify the method's formal parameter

* types, in declared order. If more than one method with the same

* parameter types is declared in a class, and one of these methods has a

* return type that is more specific than any of the others, that method is

* returned; otherwise one of the methods is chosen arbitrarily. If the

* name is "<init>"or "<clinit>" a {@codeNoSuchMethodException}

* is raised.

*

*

If this {@codeClass} object represents an array type, then this

* method does not find the {@codeclone()} method.

*

*@paramname the name of the method

*@paramparameterTypes the parameter array

*@returnthe {@codeMethod} object for the method of this class

* matching the specified name and parameters

*@throwsNoSuchMethodException if a matching method is not found.

*@throwsNullPointerException if {@codename} is {@codenull}

*@throwsSecurityException

* If a security manager, s, is present and any of the

* following conditions is met:

*

*

*

*

the caller's class loader is not the same as the

* class loader of this class and invocation of

* {@linkSecurityManager#checkPermission

* s.checkPermission} method with

* {@codeRuntimePermission("accessDeclaredMembers")}

* denies access to the declared method

*

*

the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class

*

*

*

* @jls 8.2 Class Members

* @jls 8.4 Method Declarations

*@sinceJDK1.1*/@CallerSensitivepublic Method getDeclaredMethod(String name, Class>... parameterTypes)throwsNoSuchMethodException, SecurityException {

checkMemberAccess(Member.DECLARED, Reflection.getCallerClass(),true);

Method method= searchMethods(privateGetDeclaredMethods(false), name, parameterTypes);if (method == null) {throw new NoSuchMethodException(getName() + "." + name +argumentTypesToString(parameterTypes));

}returnmethod;

}/*** Returns a {@codeConstructor} object that reflects the specified

* constructor of the class or interface represented by this

* {@codeClass} object. The {@codeparameterTypes} parameter is

* an array of {@codeClass} objects that identify the constructor's

* formal parameter types, in declared order.

*

* If this {@codeClass} object represents an inner class

* declared in a non-static context, the formal parameter types

* include the explicit enclosing instance as the first parameter.

*

*@paramparameterTypes the parameter array

*@returnThe {@codeConstructor} object for the constructor with the

* specified parameter list

*@throwsNoSuchMethodException if a matching method is not found.

*@throwsSecurityException

* If a security manager, s, is present and any of the

* following conditions is met:

*

*

*

*

the caller's class loader is not the same as the

* class loader of this class and invocation of

* {@linkSecurityManager#checkPermission

* s.checkPermission} method with

* {@codeRuntimePermission("accessDeclaredMembers")}

* denies access to the declared constructor

*

*

the caller's class loader is not the same as or an

* ancestor of the class loader for the current class and

* invocation of {@linkSecurityManager#checkPackageAccess

* s.checkPackageAccess()} denies access to the package

* of this class

*

*

*

*@sinceJDK1.1*/@CallerSensitivepublic Constructor getDeclaredConstructor(Class>... parameterTypes)throwsNoSuchMethodException, SecurityException {

checkMemberAccess(Member.DECLARED, Reflection.getCallerClass(),true);returngetConstructor0(parameterTypes, Member.DECLARED);

}/*** Finds a resource with a given name. The rules for searching resources

* associated with a given class are implemented by the defining

* {@linkplainClassLoader class loader} of the class. This method

* delegates to this object's class loader. If this object was loaded by

* the bootstrap class loader, the method delegates to {@link* ClassLoader#getSystemResourceAsStream}.

*

*

Before delegation, an absolute resource name is constructed from the

* given resource name using this algorithm:

*

*

*

*

If the {@codename} begins with a {@code'/'}

* ('\u002f'), then the absolute name of the resource is the

* portion of the {@codename} following the {@code'/'}.

*

*

Otherwise, the absolute name is of the following form:

*

*

* {@codemodified_package_name/name}

*

*

*

Where the {@codemodified_package_name} is the package name of this

* object with {@code'/'} substituted for {@code'.'}

* ('\u002e').

*

*

*

*@paramname name of the desired resource

*@returnA {@linkjava.io.InputStream} object or {@codenull} if

* no resource with this name is found

*@throwsNullPointerException If {@codename} is {@codenull}

*@sinceJDK1.1*/

publicInputStream getResourceAsStream(String name) {

name=resolveName(name);

ClassLoader cl=getClassLoader0();if (cl==null) {//A system class.

returnClassLoader.getSystemResourceAsStream(name);

}returncl.getResourceAsStream(name);

}/*** Finds a resource with a given name. The rules for searching resources

* associated with a given class are implemented by the defining

* {@linkplainClassLoader class loader} of the class. This method

* delegates to this object's class loader. If this object was loaded by

* the bootstrap class loader, the method delegates to {@link* ClassLoader#getSystemResource}.

*

*

Before delegation, an absolute resource name is constructed from the

* given resource name using this algorithm:

*

*

*

*

If the {@codename} begins with a {@code'/'}

* ('\u002f'), then the absolute name of the resource is the

* portion of the {@codename} following the {@code'/'}.

*

*

Otherwise, the absolute name is of the following form:

*

*

* {@codemodified_package_name/name}

*

*

*

Where the {@codemodified_package_name} is the package name of this

* object with {@code'/'} substituted for {@code'.'}

* ('\u002e').

*

*

*

*@paramname name of the desired resource

*@returnA {@linkjava.net.URL} object or {@codenull} if no

* resource with this name is found

*@sinceJDK1.1*/

publicjava.net.URL getResource(String name) {

name=resolveName(name);

ClassLoader cl=getClassLoader0();if (cl==null) {//A system class.

returnClassLoader.getSystemResource(name);

}returncl.getResource(name);

}/**protection domain returned when the internal domain is null*/

private staticjava.security.ProtectionDomain allPermDomain;/*** Returns the {@codeProtectionDomain} of this class. If there is a

* security manager installed, this method first calls the security

* manager's {@codecheckPermission} method with a

* {@codeRuntimePermission("getProtectionDomain")} permission to

* ensure it's ok to get the

* {@codeProtectionDomain}.

*

*@returnthe ProtectionDomain of this class

*

*@throwsSecurityException

* if a security manager exists and its

* {@codecheckPermission} method doesn't allow

* getting the ProtectionDomain.

*

*@seejava.security.ProtectionDomain

*@seeSecurityManager#checkPermission

*@seejava.lang.RuntimePermission

*@since1.2*/

publicjava.security.ProtectionDomain getProtectionDomain() {

SecurityManager sm=System.getSecurityManager();if (sm != null) {

sm.checkPermission(SecurityConstants.GET_PD_PERMISSION);

}

java.security.ProtectionDomain pd=getProtectionDomain0();if (pd == null) {if (allPermDomain == null) {

java.security.Permissions perms=

newjava.security.Permissions();

perms.add(SecurityConstants.ALL_PERMISSION);

allPermDomain=

new java.security.ProtectionDomain(null, perms);

}

pd=allPermDomain;

}returnpd;

}/*** Returns the ProtectionDomain of this class.*/

private nativejava.security.ProtectionDomain getProtectionDomain0();/** Return the Virtual Machine's Class object for the named

* primitive type.*/

static native Class>getPrimitiveClass(String name);/** Check if client is allowed to access members. If access is denied,

* throw a SecurityException.

*

* This method also enforces package access.

*

*

Default policy: allow all clients access with normal Java access

* control.*/

private void checkMemberAccess(int which, Class> caller, booleancheckProxyInterfaces) {final SecurityManager s =System.getSecurityManager();if (s != null) {/*Default policy allows access to all {@link Member#PUBLIC} members,

* as well as access to classes that have the same class loader as the caller.

* In all other cases, it requires RuntimePermission("accessDeclaredMembers")

* permission.*/

final ClassLoader ccl =ClassLoader.getClassLoader(caller);final ClassLoader cl =getClassLoader0();if (which !=Member.PUBLIC) {if (ccl !=cl) {

s.checkPermission(SecurityConstants.CHECK_MEMBER_ACCESS_PERMISSION);

}

}this.checkPackageAccess(ccl, checkProxyInterfaces);

}

}/** Checks if a client loaded in ClassLoader ccl is allowed to access this

* class under the current package access policy. If access is denied,

* throw a SecurityException.*/

private void checkPackageAccess(final ClassLoader ccl, booleancheckProxyInterfaces) {final SecurityManager s =System.getSecurityManager();if (s != null) {final ClassLoader cl =getClassLoader0();if(ReflectUtil.needsPackageAccessCheck(ccl, cl)) {

String name= this.getName();int i = name.lastIndexOf('.');if (i != -1) {//skip the package access check on a proxy class in default proxy package

String pkg = name.substring(0, i);if (!Proxy.isProxyClass(this) || ReflectUtil.isNonPublicProxyClass(this)) {

s.checkPackageAccess(pkg);

}

}

}//check package access on the proxy interfaces

if (checkProxyInterfaces && Proxy.isProxyClass(this)) {

ReflectUtil.checkProxyPackageAccess(ccl,this.getInterfaces());

}

}

}/*** Add a package name prefix if the name is not absolute Remove leading "/"

* if name is absolute*/

privateString resolveName(String name) {if (name == null) {returnname;

}if (!name.startsWith("/")) {

Class> c = this;while(c.isArray()) {

c=c.getComponentType();

}

String baseName=c.getName();int index = baseName.lastIndexOf('.');if (index != -1) {

name= baseName.substring(0, index).replace('.', '/')+"/"+name;

}

}else{

name= name.substring(1);

}returnname;

}/*** Atomic operations support.*/

private static classAtomic {//initialize Unsafe machinery here, since we need to call Class.class instance method//and have to avoid calling it in the static initializer of the Class class...

private static final Unsafe unsafe =Unsafe.getUnsafe();//offset of Class.reflectionData instance field

private static final longreflectionDataOffset;//offset of Class.annotationType instance field

private static final longannotationTypeOffset;//offset of Class.annotationData instance field

private static final longannotationDataOffset;static{

Field[] fields= Class.class.getDeclaredFields0(false); //bypass caches

reflectionDataOffset = objectFieldOffset(fields, "reflectionData");

annotationTypeOffset= objectFieldOffset(fields, "annotationType");

annotationDataOffset= objectFieldOffset(fields, "annotationData");

}private static longobjectFieldOffset(Field[] fields, String fieldName) {

Field field=searchFields(fields, fieldName);if (field == null) {throw new Error("No " + fieldName + " field found in java.lang.Class");

}returnunsafe.objectFieldOffset(field);

}static boolean casReflectionData(Class>clazz,

SoftReference>oldData,

SoftReference>newData) {returnunsafe.compareAndSwapObject(clazz, reflectionDataOffset, oldData, newData);

}static boolean casAnnotationType(Class>clazz,

AnnotationType oldType,

AnnotationType newType) {returnunsafe.compareAndSwapObject(clazz, annotationTypeOffset, oldType, newType);

}static boolean casAnnotationData(Class>clazz,

AnnotationData oldData,

AnnotationData newData) {returnunsafe.compareAndSwapObject(clazz, annotationDataOffset, oldData, newData);

}

}/*** Reflection support.*/

//Caches for certain reflective results

private static boolean useCaches = true;//reflection data that might get invalidated when JVM TI RedefineClasses() is called

private static class ReflectionData{volatileField[] declaredFields;volatileField[] publicFields;volatileMethod[] declaredMethods;volatileMethod[] publicMethods;volatile Constructor[] declaredConstructors;volatile Constructor[] publicConstructors;//Intermediate results for getFields and getMethods

volatileField[] declaredPublicFields;volatileMethod[] declaredPublicMethods;volatile Class>[] interfaces;//Value of classRedefinedCount when we created this ReflectionData instance

final intredefinedCount;

ReflectionData(intredefinedCount) {this.redefinedCount =redefinedCount;

}

}private volatile transient SoftReference>reflectionData;//Incremented by the VM on each call to JVM TI RedefineClasses()//that redefines this class or a superclass.

private volatile transient int classRedefinedCount = 0;//Lazily create and cache ReflectionData

private ReflectionDatareflectionData() {

SoftReference> reflectionData = this.reflectionData;int classRedefinedCount = this.classRedefinedCount;

ReflectionDatard;if (useCaches &&reflectionData!= null &&(rd= reflectionData.get()) != null &&rd.redefinedCount==classRedefinedCount) {returnrd;

}//else no SoftReference or cleared SoftReference or stale ReflectionData//-> create and replace new instance

returnnewReflectionData(reflectionData, classRedefinedCount);

}private ReflectionData newReflectionData(SoftReference>oldReflectionData,intclassRedefinedCount) {if (!useCaches) return null;while (true) {

ReflectionData rd = new ReflectionData<>(classRedefinedCount);//try to CAS it...

if (Atomic.casReflectionData(this, oldReflectionData, new SoftReference<>(rd))) {returnrd;

}//else retry

oldReflectionData = this.reflectionData;

classRedefinedCount= this.classRedefinedCount;if (oldReflectionData != null &&(rd= oldReflectionData.get()) != null &&rd.redefinedCount==classRedefinedCount) {returnrd;

}

}

}//Generic signature handling

private nativeString getGenericSignature0();//Generic info repository; lazily initialized

private volatile transientClassRepository genericInfo;//accessor for factory

privateGenericsFactory getFactory() {//create scope and factory

return CoreReflectionFactory.make(this, ClassScope.make(this));

}//accessor for generic info repository;//generic info is lazily initialized

privateClassRepository getGenericInfo() {

ClassRepository genericInfo= this.genericInfo;if (genericInfo == null) {

String signature=getGenericSignature0();if (signature == null) {

genericInfo=ClassRepository.NONE;

}else{

genericInfo=ClassRepository.make(signature, getFactory());

}this.genericInfo =genericInfo;

}return (genericInfo != ClassRepository.NONE) ? genericInfo : null;

}//Annotations handling

native byte[] getRawAnnotations();//Since 1.8

native byte[] getRawTypeAnnotations();static byte[] getExecutableTypeAnnotationBytes(Executable ex) {returngetReflectionFactory().getExecutableTypeAnnotationBytes(ex);

}nativeConstantPool getConstantPool();//

//

//java.lang.reflect.Field handling//

//

//Returns an array of "root" fields. These Field objects must NOT//be propagated to the outside world, but must instead be copied//via ReflectionFactory.copyField.

private Field[] privateGetDeclaredFields(booleanpublicOnly) {

checkInitted();

Field[] res;

ReflectionData rd =reflectionData();if (rd != null) {

res= publicOnly ?rd.declaredPublicFields : rd.declaredFields;if (res != null) returnres;

}//No cached value available; request value from VM

res = Reflection.filterFields(this, getDeclaredFields0(publicOnly));if (rd != null) {if(publicOnly) {

rd.declaredPublicFields=res;

}else{

rd.declaredFields=res;

}

}returnres;

}//Returns an array of "root" fields. These Field objects must NOT//be propagated to the outside world, but must instead be copied//via ReflectionFactory.copyField.

private Field[] privateGetPublicFields(Set>traversedInterfaces) {

checkInitted();

Field[] res;

ReflectionData rd =reflectionData();if (rd != null) {

res=rd.publicFields;if (res != null) returnres;

}//No cached value available; compute value recursively.//Traverse in correct order for getField().

List fields = new ArrayList<>();if (traversedInterfaces == null) {

traversedInterfaces= new HashSet<>();

}//Local fields

Field[] tmp = privateGetDeclaredFields(true);

addAll(fields, tmp);//Direct superinterfaces, recursively

for (Class>c : getInterfaces()) {if (!traversedInterfaces.contains(c)) {

traversedInterfaces.add(c);

addAll(fields, c.privateGetPublicFields(traversedInterfaces));

}

}//Direct superclass, recursively

if (!isInterface()) {

Class> c =getSuperclass();if (c != null) {

addAll(fields, c.privateGetPublicFields(traversedInterfaces));

}

}

res= newField[fields.size()];

fields.toArray(res);if (rd != null) {

rd.publicFields=res;

}returnres;

}private static void addAll(Collectionc, Field[] o) {for (int i = 0; i < o.length; i++) {

c.add(o[i]);

}

}//

//

//java.lang.reflect.Constructor handling//

//

//Returns an array of "root" constructors. These Constructor//objects must NOT be propagated to the outside world, but must//instead be copied via ReflectionFactory.copyConstructor.

private Constructor[] privateGetDeclaredConstructors(booleanpublicOnly) {

checkInitted();

Constructor[] res;

ReflectionData rd =reflectionData();if (rd != null) {

res= publicOnly ?rd.publicConstructors : rd.declaredConstructors;if (res != null) returnres;

}//No cached value available; request value from VM

if(isInterface()) {

@SuppressWarnings("unchecked")

Constructor[] temporaryRes = (Constructor[]) new Constructor>[0];

res=temporaryRes;

}else{

res=getDeclaredConstructors0(publicOnly);

}if (rd != null) {if(publicOnly) {

rd.publicConstructors=res;

}else{

rd.declaredConstructors=res;

}

}returnres;

}//

//

//java.lang.reflect.Method handling//

//

//Returns an array of "root" methods. These Method objects must NOT//be propagated to the outside world, but must instead be copied//via ReflectionFactory.copyMethod.

private Method[] privateGetDeclaredMethods(booleanpublicOnly) {

checkInitted();

Method[] res;

ReflectionData rd =reflectionData();if (rd != null) {

res= publicOnly ?rd.declaredPublicMethods : rd.declaredMethods;if (res != null) returnres;

}//No cached value available; request value from VM

res = Reflection.filterMethods(this, getDeclaredMethods0(publicOnly));if (rd != null) {if(publicOnly) {

rd.declaredPublicMethods=res;

}else{

rd.declaredMethods=res;

}

}returnres;

}static classMethodArray {//Don't add or remove methods except by add() or remove() calls.

privateMethod[] methods;private intlength;private intdefaults;

MethodArray() {this(20);

}

MethodArray(intinitialSize) {if (initialSize < 2)throw new IllegalArgumentException("Size should be 2 or more");

methods= newMethod[initialSize];

length= 0;

defaults= 0;

}booleanhasDefaults() {return defaults != 0;

}voidadd(Method m) {if (length ==methods.length) {

methods= Arrays.copyOf(methods, 2 *methods.length);

}

methods[length++] =m;if (m != null &&m.isDefault())

defaults++;

}voidaddAll(Method[] ma) {for (int i = 0; i < ma.length; i++) {

add(ma[i]);

}

}voidaddAll(MethodArray ma) {for (int i = 0; i < ma.length(); i++) {

add(ma.get(i));

}

}voidaddIfNotPresent(Method newMethod) {for (int i = 0; i < length; i++) {

Method m=methods[i];if (m == newMethod || (m != null &&m.equals(newMethod))) {return;

}

}

add(newMethod);

}voidaddAllIfNotPresent(MethodArray newMethods) {for (int i = 0; i < newMethods.length(); i++) {

Method m=newMethods.get(i);if (m != null) {

addIfNotPresent(m);

}

}

}/*Add Methods declared in an interface to this MethodArray.

* Static methods declared in interfaces are not inherited.*/

voidaddInterfaceMethods(Method[] methods) {for(Method candidate : methods) {if (!Modifier.isStatic(candidate.getModifiers())) {

add(candidate);

}

}

}intlength() {returnlength;

}

Method get(inti) {returnmethods[i];

}

Method getFirst() {for(Method m : methods)if (m != null)returnm;return null;

}voidremoveByNameAndDescriptor(Method toRemove) {for (int i = 0; i < length; i++) {

Method m=methods[i];if (m != null &&matchesNameAndDescriptor(m, toRemove)) {

remove(i);

}

}

}private void remove(inti) {if (methods[i] != null &&methods[i].isDefault())

defaults--;

methods[i]= null;

}private booleanmatchesNameAndDescriptor(Method m1, Method m2) {return m1.getReturnType() == m2.getReturnType() &&m1.getName()== m2.getName() && //name is guaranteed to be interned

arrayContentsEq(m1.getParameterTypes(),

m2.getParameterTypes());

}voidcompactAndTrim() {int newPos = 0;//Get rid of null slots

for (int pos = 0; pos < length; pos++) {

Method m=methods[pos];if (m != null) {if (pos !=newPos) {

methods[newPos]=m;

}

newPos++;

}

}if (newPos !=methods.length) {

methods=Arrays.copyOf(methods, newPos);

}

}/*Removes all Methods from this MethodArray that have a more specific

* default Method in this MethodArray.

*

* Users of MethodArray are responsible for pruning Methods that have

* a more specific concrete Method.*/

voidremoveLessSpecifics() {if (!hasDefaults())return;for (int i = 0; i < length; i++) {

Method m=get(i);if (m == null || !m.isDefault())continue;for (int j = 0; j < length; j++) {if (i ==j)continue;

Method candidate=get(j);if (candidate == null)continue;if (!matchesNameAndDescriptor(m, candidate))continue;if(hasMoreSpecificClass(m, candidate))

remove(j);

}

}

}

Method[] getArray() {returnmethods;

}//Returns true if m1 is more specific than m2

static booleanhasMoreSpecificClass(Method m1, Method m2) {

Class> m1Class =m1.getDeclaringClass();

Class> m2Class =m2.getDeclaringClass();return m1Class != m2Class &&m2Class.isAssignableFrom(m1Class);

}

}//Returns an array of "root" methods. These Method objects must NOT//be propagated to the outside world, but must instead be copied//via ReflectionFactory.copyMethod.

privateMethod[] privateGetPublicMethods() {

checkInitted();

Method[] res;

ReflectionData rd =reflectionData();if (rd != null) {

res=rd.publicMethods;if (res != null) returnres;

}//No cached value available; compute value recursively.//Start by fetching public declared methods

MethodArray methods = newMethodArray();

{

Method[] tmp= privateGetDeclaredMethods(true);

methods.addAll(tmp);

}//Now recur over superclass and direct superinterfaces.//Go over superinterfaces first so we can more easily filter//out concrete implementations inherited from superclasses at//the end.

MethodArray inheritedMethods = newMethodArray();for (Class>i : getInterfaces()) {

inheritedMethods.addInterfaceMethods(i.privateGetPublicMethods());

}if (!isInterface()) {

Class> c =getSuperclass();if (c != null) {

MethodArray supers= newMethodArray();

supers.addAll(c.privateGetPublicMethods());//Filter out concrete implementations of any//interface methods

for (int i = 0; i < supers.length(); i++) {

Method m=supers.get(i);if (m != null &&

!Modifier.isAbstract(m.getModifiers()) &&

!m.isDefault()) {

inheritedMethods.removeByNameAndDescriptor(m);

}

}//Insert superclass's inherited methods before//superinterfaces' to satisfy getMethod's search//order

supers.addAll(inheritedMethods);

inheritedMethods=supers;

}

}//Filter out all local methods from inherited ones

for (int i = 0; i < methods.length(); i++) {

Method m=methods.get(i);

inheritedMethods.removeByNameAndDescriptor(m);

}

methods.addAllIfNotPresent(inheritedMethods);

methods.removeLessSpecifics();

methods.compactAndTrim();

res=methods.getArray();if (rd != null) {

rd.publicMethods=res;

}returnres;

}//

//Helpers for fetchers of one field, method, or constructor//

private staticField searchFields(Field[] fields, String name) {

String internedName=name.intern();for (int i = 0; i < fields.length; i++) {if (fields[i].getName() ==internedName) {returngetReflectionFactory().copyField(fields[i]);

}

}return null;

}private Field getField0(String name) throwsNoSuchFieldException {//Note: the intent is that the search algorithm this routine//uses be equivalent to the ordering imposed by//privateGetPublicFields(). It fetches only the declared//public fields for each class, however, to reduce the number//of Field objects which have to be created for the common//case where the field being requested is declared in the//class which is being queried.

Field res;//Search declared public fields

if ((res = searchFields(privateGetDeclaredFields(true), name)) != null) {returnres;

}//Direct superinterfaces, recursively

Class>[] interfaces =getInterfaces();for (int i = 0; i < interfaces.length; i++) {

Class> c =interfaces[i];if ((res = c.getField0(name)) != null) {returnres;

}

}//Direct superclass, recursively

if (!isInterface()) {

Class> c =getSuperclass();if (c != null) {if ((res = c.getField0(name)) != null) {returnres;

}

}

}return null;

}private staticMethod searchMethods(Method[] methods,

String name,

Class>[] parameterTypes)

{

Method res= null;

String internedName=name.intern();for (int i = 0; i < methods.length; i++) {

Method m=methods[i];if (m.getName() ==internedName&&arrayContentsEq(parameterTypes, m.getParameterTypes())&& (res == null

||res.getReturnType().isAssignableFrom(m.getReturnType())))

res=m;

}return (res == null ?res : getReflectionFactory().copyMethod(res));

}private Method getMethod0(String name, Class>[] parameterTypes, booleanincludeStaticMethods) {

MethodArray interfaceCandidates= new MethodArray(2);

Method res=privateGetMethodRecursive(name, parameterTypes, includeStaticMethods, interfaceCandidates);if (res != null)returnres;//Not found on class or superclass directly

interfaceCandidates.removeLessSpecifics();return interfaceCandidates.getFirst(); //may be null

}privateMethod privateGetMethodRecursive(String name,

Class>[] parameterTypes,booleanincludeStaticMethods,

MethodArray allInterfaceCandidates) {//Note: the intent is that the search algorithm this routine//uses be equivalent to the ordering imposed by//privateGetPublicMethods(). It fetches only the declared//public methods for each class, however, to reduce the//number of Method objects which have to be created for the//common case where the method being requested is declared in//the class which is being queried.//

//Due to default methods, unless a method is found on a superclass,//methods declared in any superinterface needs to be considered.//Collect all candidates declared in superinterfaces in {@code//allInterfaceCandidates} and select the most specific if no match on//a superclass is found.//Must _not_ return root methods

Method res;//Search declared public methods

if ((res = searchMethods(privateGetDeclaredMethods(true),

name,

parameterTypes))!= null) {if (includeStaticMethods || !Modifier.isStatic(res.getModifiers()))returnres;

}//Search superclass's methods

if (!isInterface()) {

Class super T> c =getSuperclass();if (c != null) {if ((res = c.getMethod0(name, parameterTypes, true)) != null) {returnres;

}

}

}//Search superinterfaces' methods

Class>[] interfaces =getInterfaces();for (Class>c : interfaces)if ((res = c.getMethod0(name, parameterTypes, false)) != null)

allInterfaceCandidates.add(res);//Not found

return null;

}private Constructor getConstructor0(Class>[] parameterTypes,int which) throwsNoSuchMethodException

{

Constructor[] constructors = privateGetDeclaredConstructors((which ==Member.PUBLIC));for (Constructorconstructor : constructors) {if(arrayContentsEq(parameterTypes,

constructor.getParameterTypes())) {returngetReflectionFactory().copyConstructor(constructor);

}

}throw new NoSuchMethodException(getName() + "." +argumentTypesToString(parameterTypes));

}//

//Other helpers and base implementation//

private static booleanarrayContentsEq(Object[] a1, Object[] a2) {if (a1 == null) {return a2 == null || a2.length == 0;

}if (a2 == null) {return a1.length == 0;

}if (a1.length !=a2.length) {return false;

}for (int i = 0; i < a1.length; i++) {if (a1[i] !=a2[i]) {return false;

}

}return true;

}private staticField[] copyFields(Field[] arg) {

Field[] out= newField[arg.length];

ReflectionFactory fact=getReflectionFactory();for (int i = 0; i < arg.length; i++) {

out[i]=fact.copyField(arg[i]);

}returnout;

}private staticMethod[] copyMethods(Method[] arg) {

Method[] out= newMethod[arg.length];

ReflectionFactory fact=getReflectionFactory();for (int i = 0; i < arg.length; i++) {

out[i]=fact.copyMethod(arg[i]);

}returnout;

}private static Constructor[] copyConstructors(Constructor[] arg) {

Constructor[] out =arg.clone();

ReflectionFactory fact=getReflectionFactory();for (int i = 0; i < out.length; i++) {

out[i]=fact.copyConstructor(out[i]);

}returnout;

}private native Field[] getDeclaredFields0(booleanpublicOnly);private native Method[] getDeclaredMethods0(booleanpublicOnly);private native Constructor[] getDeclaredConstructors0(booleanpublicOnly);private native Class>[] getDeclaredClasses0();private static String argumentTypesToString(Class>[] argTypes) {

StringBuilder buf= newStringBuilder();

buf.append("(");if (argTypes != null) {for (int i = 0; i < argTypes.length; i++) {if (i > 0) {

buf.append(", ");

}

Class> c =argTypes[i];

buf.append((c== null) ? "null": c.getName());

}

}

buf.append(")");returnbuf.toString();

}/**use serialVersionUID from JDK 1.1 for interoperability*/

private static final long serialVersionUID = 3206093459760846163L;/*** Class Class is special cased within the Serialization Stream Protocol.

*

* A Class instance is written initially into an ObjectOutputStream in the

* following format:

*

 
 

* {@codeTC_CLASS} ClassDescriptor

* A ClassDescriptor is a special cased serialization of

* a {@codejava.io.ObjectStreamClass} instance.

*

* A new handle is generated for the initial time the class descriptor

* is written into the stream. Future references to the class descriptor

* are written as references to the initial class descriptor instance.

*

*@seejava.io.ObjectStreamClass*/

private static final ObjectStreamField[] serialPersistentFields =

new ObjectStreamField[0];/*** Returns the assertion status that would be assigned to this

* class if it were to be initialized at the time this method is invoked.

* If this class has had its assertion status set, the most recent

* setting will be returned; otherwise, if any package default assertion

* status pertains to this class, the most recent setting for the most

* specific pertinent package default assertion status is returned;

* otherwise, if this class is not a system class (i.e., it has a

* class loader) its class loader's default assertion status is returned;

* otherwise, the system class default assertion status is returned.

*

* Few programmers will have any need for this method; it is provided

* for the benefit of the JRE itself. (It allows a class to determine at

* the time that it is initialized whether assertions should be enabled.)

* Note that this method is not guaranteed to return the actual

* assertion status that was (or will be) associated with the specified

* class when it was (or will be) initialized.

*

*@returnthe desired assertion status of the specified class.

*@seejava.lang.ClassLoader#setClassAssertionStatus

*@seejava.lang.ClassLoader#setPackageAssertionStatus

*@seejava.lang.ClassLoader#setDefaultAssertionStatus

*@since1.4*/

public booleandesiredAssertionStatus() {

ClassLoader loader=getClassLoader();//If the loader is null this is a system class, so ask the VM

if (loader == null)return desiredAssertionStatus0(this);//If the classloader has been initialized with the assertion//directives, ask it. Otherwise, ask the VM.

synchronized(loader.assertionLock) {if (loader.classAssertionStatus != null) {returnloader.desiredAssertionStatus(getName());

}

}return desiredAssertionStatus0(this);

}//Retrieves the desired assertion status of this class from the VM

private static native boolean desiredAssertionStatus0(Class>clazz);/*** Returns true if and only if this class was declared as an enum in the

* source code.

*

*@returntrue if and only if this class was declared as an enum in the

* source code

*@since1.5*/

public booleanisEnum() {//An enum must both directly extend java.lang.Enum and have//the ENUM bit set; classes for specialized enum constants//don't do the former.

return (this.getModifiers() & ENUM) != 0 &&

this.getSuperclass() == java.lang.Enum.class;

}//Fetches the factory for reflective objects

private staticReflectionFactory getReflectionFactory() {if (reflectionFactory == null) {

reflectionFactory=java.security.AccessController.doPrivileged

(newsun.reflect.ReflectionFactory.GetReflectionFactoryAction());

}returnreflectionFactory;

}private staticReflectionFactory reflectionFactory;//To be able to query system properties as soon as they're available

private static boolean initted = false;private static voidcheckInitted() {if (initted) return;

AccessController.doPrivileged(new PrivilegedAction() {publicVoid run() {//Tests to ensure the system properties table is fully//initialized. This is needed because reflection code is//called very early in the initialization process (before//command-line arguments have been parsed and therefore//these user-settable properties installed.) We assume that//if System.out is non-null then the System class has been//fully initialized and that the bulk of the startup code//has been run.

if (System.out == null) {//java.lang.System not yet fully initialized

return null;

}//Doesn't use Boolean.getBoolean to avoid class init.

String val =System.getProperty("sun.reflect.noCaches");if (val != null && val.equals("true")) {

useCaches= false;

}

initted= true;return null;

}

});

}/*** Returns the elements of this enum class or null if this

* Class object does not represent an enum type.

*

*@returnan array containing the values comprising the enum class

* represented by this Class object in the order they're

* declared, or null if this Class object does not

* represent an enum type

*@since1.5*/

publicT[] getEnumConstants() {

T[] values=getEnumConstantsShared();return (values != null) ? values.clone() : null;

}/*** Returns the elements of this enum class or null if this

* Class object does not represent an enum type;

* identical to getEnumConstants except that the result is

* uncloned, cached, and shared by all callers.*/T[] getEnumConstantsShared() {if (enumConstants == null) {if (!isEnum()) return null;try{final Method values = getMethod("values");

java.security.AccessController.doPrivileged(new java.security.PrivilegedAction() {publicVoid run() {

values.setAccessible(true);return null;

}

});

@SuppressWarnings("unchecked")

T[] temporaryConstants= (T[])values.invoke(null);

enumConstants=temporaryConstants;

}//These can happen when users concoct enum-like classes//that don't comply with the enum spec.

catch (InvocationTargetException | NoSuchMethodException |IllegalAccessException ex) {return null; }

}returnenumConstants;

}private volatile transient T[] enumConstants = null;/*** Returns a map from simple name to enum constant. This package-private

* method is used internally by Enum to implement

* {@codepublic static > T valueOf(Class, String)}

* efficiently. Note that the map is returned by this method is

* created lazily on first use. Typically it won't ever get created.*/MapenumConstantDirectory() {if (enumConstantDirectory == null) {

T[] universe=getEnumConstantsShared();if (universe == null)throw newIllegalArgumentException(

getName()+ " is not an enum type");

Map m = new HashMap<>(2 *universe.length);for(T constant : universe)

m.put(((Enum>)constant).name(), constant);

enumConstantDirectory=m;

}returnenumConstantDirectory;

}private volatile transient Map enumConstantDirectory = null;/*** Casts an object to the class or interface represented

* by this {@codeClass} object.

*

*@paramobj the object to be cast

*@returnthe object after casting, or null if obj is null

*

*@throwsClassCastException if the object is not

* null and is not assignable to the type T.

*

*@since1.5*/@SuppressWarnings("unchecked")publicT cast(Object obj) {if (obj != null && !isInstance(obj))throw newClassCastException(cannotCastMsg(obj));return(T) obj;

}privateString cannotCastMsg(Object obj) {return "Cannot cast " + obj.getClass().getName() + " to " +getName();

}/*** Casts this {@codeClass} object to represent a subclass of the class

* represented by the specified class object. Checks that the cast

* is valid, and throws a {@codeClassCastException} if it is not. If

* this method succeeds, it always returns a reference to this class object.

*

*

This method is useful when a client needs to "narrow" the type of

* a {@codeClass} object to pass it to an API that restricts the

* {@codeClass} objects that it is willing to accept. A cast would

* generate a compile-time warning, as the correctness of the cast

* could not be checked at runtime (because generic types are implemented

* by erasure).

*

*@param the type to cast this class object to

*@paramclazz the class of the type to cast this class object to

*@returnthis {@codeClass} object, cast to represent a subclass of

* the specified class object.

*@throwsClassCastException if this {@codeClass} object does not

* represent a subclass of the specified class (here "subclass" includes

* the class itself).

*@since1.5*/@SuppressWarnings("unchecked")public Class extends U> asSubclass(Classclazz) {if (clazz.isAssignableFrom(this))return (Class extends U>) this;else

throw new ClassCastException(this.toString());

}/***@throwsNullPointerException {@inheritDoc}

*@since1.5*/@SuppressWarnings("unchecked")public A getAnnotation(ClassannotationClass) {

Objects.requireNonNull(annotationClass);return(A) annotationData().annotations.get(annotationClass);

}/*** {@inheritDoc}

*@throwsNullPointerException {@inheritDoc}

*@since1.5*/@Overridepublic boolean isAnnotationPresent(Class extends Annotation>annotationClass) {return GenericDeclaration.super.isAnnotationPresent(annotationClass);

}/***@throwsNullPointerException {@inheritDoc}

*@since1.8*/@Overridepublic A[] getAnnotationsByType(ClassannotationClass) {

Objects.requireNonNull(annotationClass);

AnnotationData annotationData=annotationData();returnAnnotationSupport.getAssociatedAnnotations(annotationData.declaredAnnotations,this,

annotationClass);

}/***@since1.5*/

publicAnnotation[] getAnnotations() {returnAnnotationParser.toArray(annotationData().annotations);

}/***@throwsNullPointerException {@inheritDoc}

*@since1.8*/@Override

@SuppressWarnings("unchecked")public A getDeclaredAnnotation(ClassannotationClass) {

Objects.requireNonNull(annotationClass);return(A) annotationData().declaredAnnotations.get(annotationClass);

}/***@throwsNullPointerException {@inheritDoc}

*@since1.8*/@Overridepublic A[] getDeclaredAnnotationsByType(ClassannotationClass) {

Objects.requireNonNull(annotationClass);returnAnnotationSupport.getDirectlyAndIndirectlyPresent(annotationData().declaredAnnotations,

annotationClass);

}/***@since1.5*/

publicAnnotation[] getDeclaredAnnotations() {returnAnnotationParser.toArray(annotationData().declaredAnnotations);

}//annotation data that might get invalidated when JVM TI RedefineClasses() is called

private static classAnnotationData {final Map, Annotation>annotations;final Map, Annotation>declaredAnnotations;//Value of classRedefinedCount when we created this AnnotationData instance

final intredefinedCount;

AnnotationData(Map, Annotation>annotations,

Map, Annotation>declaredAnnotations,intredefinedCount) {this.annotations =annotations;this.declaredAnnotations =declaredAnnotations;this.redefinedCount =redefinedCount;

}

}//Annotations cache

@SuppressWarnings("UnusedDeclaration")private volatile transientAnnotationData annotationData;privateAnnotationData annotationData() {while (true) { //retry loop

AnnotationData annotationData = this.annotationData;int classRedefinedCount = this.classRedefinedCount;if (annotationData != null &&annotationData.redefinedCount==classRedefinedCount) {returnannotationData;

}//null or stale annotationData -> optimistically create new instance

AnnotationData newAnnotationData =createAnnotationData(classRedefinedCount);//try to install it

if (Atomic.casAnnotationData(this, annotationData, newAnnotationData)) {//successfully installed new AnnotationData

returnnewAnnotationData;

}

}

}private AnnotationData createAnnotationData(intclassRedefinedCount) {

Map, Annotation> declaredAnnotations =AnnotationParser.parseAnnotations(getRawAnnotations(), getConstantPool(),this);

Class> superClass =getSuperclass();

Map, Annotation> annotations = null;if (superClass != null) {

Map, Annotation> superAnnotations =superClass.annotationData().annotations;for (Map.Entry, Annotation>e : superAnnotations.entrySet()) {

Class extends Annotation> annotationClass =e.getKey();if(AnnotationType.getInstance(annotationClass).isInherited()) {if (annotations == null) { //lazy construction

annotations = new LinkedHashMap<>((Math.max(

declaredAnnotations.size(),

Math.min(12, declaredAnnotations.size() +superAnnotations.size())

)* 4 + 2) / 3);

}

annotations.put(annotationClass, e.getValue());

}

}

}if (annotations == null) {//no inherited annotations -> share the Map with declaredAnnotations

annotations =declaredAnnotations;

}else{//at least one inherited annotation -> declared may override inherited

annotations.putAll(declaredAnnotations);

}return newAnnotationData(annotations, declaredAnnotations, classRedefinedCount);

}//Annotation types cache their internal (AnnotationType) form

@SuppressWarnings("UnusedDeclaration")private volatile transientAnnotationType annotationType;booleancasAnnotationType(AnnotationType oldType, AnnotationType newType) {return Atomic.casAnnotationType(this, oldType, newType);

}

AnnotationType getAnnotationType() {returnannotationType;

}

Map, Annotation>getDeclaredAnnotationMap() {returnannotationData().declaredAnnotations;

}/*Backing store of user-defined values pertaining to this class.

* Maintained by the ClassValue class.*/

transientClassValue.ClassValueMap classValueMap;/*** Returns an {@codeAnnotatedType} object that represents the use of a

* type to specify the superclass of the entity represented by this {@code* Class} object. (The use of type Foo to specify the superclass

* in '... extends Foo' is distinct from the declaration of type

* Foo.)

*

*

If this {@codeClass} object represents a type whose declaration

* does not explicitly indicate an annotated superclass, then the return

* value is an {@codeAnnotatedType} object representing an element with no

* annotations.

*

*

If this {@codeClass} represents either the {@codeObject} class, an

* interface type, an array type, a primitive type, or void, the return

* value is {@codenull}.

*

*@returnan object representing the superclass

*@since1.8*/

publicAnnotatedType getAnnotatedSuperclass() {if (this == Object.class ||isInterface()||isArray()||isPrimitive()||

this ==Void.TYPE) {return null;

}return TypeAnnotationParser.buildAnnotatedSuperclass(getRawTypeAnnotations(), getConstantPool(), this);

}/*** Returns an array of {@codeAnnotatedType} objects that represent the use

* of types to specify superinterfaces of the entity represented by this

* {@codeClass} object. (The use of type Foo to specify a

* superinterface in '... implements Foo' is distinct from the

* declaration of type Foo.)

*

*

If this {@codeClass} object represents a class, the return value is

* an array containing objects representing the uses of interface types to

* specify interfaces implemented by the class. The order of the objects in

* the array corresponds to the order of the interface types used in the

* 'implements' clause of the declaration of this {@codeClass} object.

*

*

If this {@codeClass} object represents an interface, the return

* value is an array containing objects representing the uses of interface

* types to specify interfaces directly extended by the interface. The

* order of the objects in the array corresponds to the order of the

* interface types used in the 'extends' clause of the declaration of this

* {@codeClass} object.

*

*

If this {@codeClass} object represents a class or interface whose

* declaration does not explicitly indicate any annotated superinterfaces,

* the return value is an array of length 0.

*

*

If this {@codeClass} object represents either the {@codeObject}

* class, an array type, a primitive type, or void, the return value is an

* array of length 0.

*

*@returnan array representing the superinterfaces

*@since1.8*/

publicAnnotatedType[] getAnnotatedInterfaces() {return TypeAnnotationParser.buildAnnotatedInterfaces(getRawTypeAnnotations(), getConstantPool(), this);

}

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值