001    package edu.rice.cs.cunit.subAnnot;
002    
003    import edu.rice.cs.cunit.classFile.ClassFileTools;
004    import edu.rice.cs.cunit.classFile.attributes.RuntimeVisibleAnnotationsAttributeInfo;
005    
006    import java.lang.reflect.*;
007    import java.util.ArrayList;
008    import java.util.List;
009    import java.io.InputStream;
010    import java.io.IOException;
011    import java.net.URL;
012    import java.security.ProtectionDomain;
013    
014    /**
015     * Extended Class class to support annotations with subclassing.
016     *
017     * @author Mathias Ricken
018     */
019    public class ClassEx<T> extends AAnnotatedElementEx {
020        /**
021         * The java.lang.Class object that represents the class.
022         */
023        public final Class<T> java;
024    
025        /**
026         * Return an extended Class instance for the class with the specified class name.
027         * @param s class name
028         * @return class
029         * @throws ClassNotFoundException if class is not found
030         */
031        @SuppressWarnings("unchecked")
032        public static ClassEx<?> forName(String s) throws ClassNotFoundException {
033            return new ClassEx(Class.forName(s));
034        }
035    
036        /**
037         * Return an extended Class instance for the class with the specified class name.
038         * @param s class name
039         * @param initialize whether the class must be initialized
040         * @param loader class loader from which the class must be loaded
041         * @return class
042         * @throws ClassNotFoundException if class is not found
043         */
044        @SuppressWarnings("unchecked")
045        public static ClassEx<?> forName(String s, boolean initialize, ClassLoader loader) throws ClassNotFoundException {
046            return new ClassEx(Class.forName(s,initialize,loader), loader);
047        }
048    
049        /**
050         * Create an extended Class instance for the specified class.
051         * @param c class
052         */
053        public ClassEx(Class<T> c) {
054            this(c, null);
055        }
056    
057        /**
058         * Create an extended Class instance for the specified class.
059         * @param c class
060         * @param loader class loader
061         */
062        public ClassEx(Class<T> c, ClassLoader loader) {
063            java = c;
064            _classLoader = loader;
065            if (java.isPrimitive()) {
066                _ai = null;
067                return;
068            }
069            List<RuntimeVisibleAnnotationsAttributeInfo> ais =
070                    new ArrayList<RuntimeVisibleAnnotationsAttributeInfo>();
071            Class<?> current = java;
072            while (current != null) {
073                ClassFileTools.ClassLocation cl = ClassFileTools.findClassFile(current.getName(), _classPath);
074                if (cl == null) {
075                    setClassFileNotFound(true);
076                    return;
077                }
078                final RuntimeVisibleAnnotationsAttributeInfo a = (RuntimeVisibleAnnotationsAttributeInfo)
079                        cl.getClassFile().getAttribute(RuntimeVisibleAnnotationsAttributeInfo.getAttributeName());
080                ais.add(a);
081                try {
082                    cl.close();
083                }
084                catch (IOException e) { /* ignore */ }
085                current = current.getSuperclass();
086            }
087            _ai = ais.toArray(new RuntimeVisibleAnnotationsAttributeInfo[0]);
088        }
089    
090        /**
091         * Return the annotated element.
092         *
093         * @return annotated element
094         */
095        protected AnnotatedElement getAnnotatedElement() {
096            return java;
097        }
098    
099        /**
100         * Returns a array containing extended Class objects representing all the public classes and interfaces that
101         * are members of the class represented by this extended Class object.
102         * @return array of classes
103         */
104        @SuppressWarnings("unchecked")
105        public ClassEx[] getClasses() {
106            List<ClassEx> list = new ArrayList<ClassEx>();
107            for(Class c: java.getClasses()) {
108                list.add(new ClassEx(c, c.getClassLoader()));
109            }
110            return list.toArray(new ClassEx[list.size()]);
111        }
112    
113        /**
114         * Returns the extended Class representing the component type of an array.
115         * If this class does not represent an array class this method returns null.
116         * @return component type
117         */
118        @SuppressWarnings("unchecked")
119        public ClassEx<?> getComponentType() {
120            Class<?> c = java.getComponentType();
121            if (c==null) { return null; }
122            return new ClassEx(c, c.getClassLoader());
123        }
124    
125        /**
126         * Returns an extended Constructor object that reflects the specified public constructor of the class represented
127         * by this extended Class object. The parameterTypes parameter is an array of Class objects that identify the
128         * constructor's formal parameter types, in declared order.
129         * @param parameterTypes parameter types
130         * @return extended Constructor object
131         * @throws NoSuchMethodException if the constructor is not found
132         * @throws SecurityException if access is denied
133         */
134        public ConstructorEx<T> getConstructor(Class... parameterTypes) throws NoSuchMethodException, SecurityException {
135            Constructor<T> c = java.getConstructor(parameterTypes);
136            return new ConstructorEx<T>(c, _classLoader);
137        }
138    
139        /**
140         * Returns an extended Constructor object that reflects the specified public constructor of the class represented
141         * by this extended Class object. The parameterTypes parameter is an array of extended Class objects that identify
142         * the constructor's formal parameter types, in declared order.
143         * @param parameterTypes parameter types
144         * @return extended Constructor object
145         * @throws NoSuchMethodException if the constructor is not found
146         * @throws SecurityException if access is denied
147         */
148        public ConstructorEx<T> getConstructor(ClassEx... parameterTypes) throws NoSuchMethodException, SecurityException {
149            Class[] pt = new Class[parameterTypes.length];
150            for(int i=0; i<pt.length; ++i) {
151                pt[i] = parameterTypes[i].java;
152            }
153            Constructor<T> c = java.getConstructor(pt);
154            return new ConstructorEx<T>(c, _classLoader);
155        }
156    
157        /**
158         * Returns an array containing extended Constructor objects reflecting all the public constructors of the
159         * class represented by this extended Class object.
160         * @return array of constructors
161         * @throws SecurityException if access is denied
162         */
163        @SuppressWarnings("unchecked")
164        public ConstructorEx[] getConstructors() throws SecurityException {
165            List<ConstructorEx> list = new ArrayList<ConstructorEx>();
166            for(Constructor c: java.getConstructors()) {
167                list.add(new ConstructorEx(c, _classLoader));
168            }
169            return list.toArray(new ConstructorEx[list.size()]);
170        }
171    
172        /**
173         * Returns an array of extended Class objects reflecting all the classes and interfaces declared as members of
174         * the class represented by this extended Class object.
175         * @return array of classes
176         */
177        @SuppressWarnings("unchecked")
178        public ClassEx[] getDeclaredClasses() {
179            List<ClassEx> list = new ArrayList<ClassEx>();
180            for(Class c: java.getDeclaredClasses()) {
181                list.add(new ClassEx(c, c.getClassLoader()));
182            }
183            return list.toArray(new ClassEx[list.size()]);
184        }
185    
186        /**
187         * Returns an extended Constructor object that reflects the specified constructor of the class or interface
188         * represented by this extended Class object.
189         * @param parameterTypes parameter types
190         * @return extended Constructor object
191         * @throws NoSuchMethodException if the constructor is not found
192         * @throws SecurityException if access is denied
193         */
194        public ConstructorEx<T> getDeclaredConstructor(Class... parameterTypes)
195            throws NoSuchMethodException, SecurityException {
196            Constructor<T> c = java.getDeclaredConstructor(parameterTypes);
197            return new ConstructorEx<T>(c, _classLoader);
198        }
199    
200        /**
201         * Returns an extended Constructor object that reflects the specified constructor of the class or interface
202         * represented by this extended Class object.
203         * @param parameterTypes parameter types
204         * @return extended Constructor object
205         * @throws NoSuchMethodException if the constructor is not found
206         * @throws SecurityException if access is denied
207         */
208        public ConstructorEx<T> getDeclaredConstructor(ClassEx... parameterTypes) throws NoSuchMethodException, SecurityException {
209            Class[] pt = new Class[parameterTypes.length];
210            for(int i=0; i<pt.length; ++i) {
211                pt[i] = parameterTypes[i].java;
212            }
213            Constructor<T> c = java.getDeclaredConstructor(pt);
214            return new ConstructorEx<T>(c, _classLoader);
215        }
216    
217        /**
218         * Returns an array of extended Constructor objects reflecting all the constructors declared by the class
219         * represented by this extended Class object.
220         * @return array of constructors
221         * @throws SecurityException if access is denied
222         */
223        @SuppressWarnings("unchecked")
224        public ConstructorEx[] getDeclaredConstructors() throws SecurityException {
225            List<ConstructorEx> list = new ArrayList<ConstructorEx>();
226            for(Constructor c: java.getDeclaredConstructors()) {
227                list.add(new ConstructorEx(c, _classLoader));
228            }
229            return list.toArray(new ConstructorEx[list.size()]);
230        }
231    
232        /**
233         * Returns an extended Field object that reflects the specified declared field of the class or interface
234         * represented by this extended Class object.
235         * @param name field name
236         * @return extended Field object
237         * @throws NoSuchFieldException if field not found
238         * @throws SecurityException if access is denied
239         */
240        public FieldEx getDeclaredField(String name) throws NoSuchFieldException, SecurityException {
241            Field f = java.getDeclaredField(name);
242            return new FieldEx(f, f.getClass().getClassLoader());
243        }
244    
245        /**
246         * Returns an array of extended Field objects reflecting all the fields declared by the class
247         * represented by this extended Class object.
248         * @return array of fields
249         * @throws SecurityException if access is denied
250         */
251        public FieldEx[] getDeclaredFields() throws SecurityException {
252            List<FieldEx> list = new ArrayList<FieldEx>();
253            for(Field f: java.getDeclaredFields()) {
254                list.add(new FieldEx(f, f.getClass().getClassLoader()));
255            }
256            return list.toArray(new FieldEx[list.size()]);
257        }
258    
259        /**
260         * Returns an extended Method object that reflects the specified declared method of the class or interface
261         * represented by this extended Class object.
262         * @param name method name
263         * @param parameterTypes parameter types
264         * @return extended Method object
265         * @throws NoSuchMethodException if method not found
266         * @throws SecurityException if access is denied
267         */
268        public MethodEx getDeclaredMethod(String name, Class... parameterTypes)
269            throws NoSuchMethodException, SecurityException {
270            return new MethodEx(java.getDeclaredMethod(name, parameterTypes), _classLoader);
271        }
272    
273        /**
274         * Returns an extended Method object that reflects the specified declared method of the class or interface
275         * represented by this extended Class object.
276         * @param name method name
277         * @param parameterTypes parameter types
278         * @return extended Method object
279         * @throws NoSuchMethodException if method not found
280         * @throws SecurityException if access is denied
281         */
282        public MethodEx getDeclaredMethod(String name, ClassEx... parameterTypes)
283            throws NoSuchMethodException, SecurityException {
284            Class[] pt = new Class[parameterTypes.length];
285            for(int i=0; i<pt.length; ++i) {
286                pt[i] = parameterTypes[i].java;
287            }
288            return new MethodEx(java.getDeclaredMethod(name, pt), _classLoader);
289        }
290    
291        /**
292         * Returns an array of extended Method objects reflecting all the methods declared by the class
293         * represented by this extended Class object.
294         * @return array of methods
295         * @throws SecurityException if access is denied
296         */
297        public MethodEx[] getDeclaredMethods() throws SecurityException {
298            List<MethodEx> list = new ArrayList<MethodEx>();
299            for(Method m: java.getDeclaredMethods()) {
300                list.add(new MethodEx(m, _classLoader));
301            }
302            return list.toArray(new MethodEx[list.size()]);
303        }
304    
305        /**
306         * If the class or interface represented by this extended Class object is a member of another class, returns the
307         * extended Class object representing the class in which it was declared. This method returns null if this class
308         * or interface is not a member of any other class. If this Class object represents an array class, a primitive
309         * type, or void, then this method returns null.
310         * @return the declaring class for this class
311         */
312        @SuppressWarnings("unchecked")
313        public ClassEx<?> getDeclaringClass() {
314            Class<?> c = java.getDeclaringClass();
315            if (c==null) { return null; }
316            return new ClassEx(c, c.getClassLoader());
317        }
318    
319        /**
320         * Returns the immediately enclosing class of the underlying class. If the underlying class is a top level class
321         * this method returns null.
322         * @return the enclosing class for this class
323         */
324        @SuppressWarnings("unchecked")
325        public ClassEx<?> getEnclosingClass() {
326            Class<?> c = java.getEnclosingClass();
327            if (c==null) { return null; }
328            return new ClassEx(c, c.getClassLoader());
329        }
330    
331        /**
332         * If this extended Class object represents a local or anonymous class within a constructor, returns an
333         * extended Constructor object representing the immediately enclosing constructor of the underlying class.
334         * Returns null otherwise. In particular, this method returns null if the underlying class is a local or
335         * anonymous class immediately enclosed by a type declaration, instance initializer or static initializer.
336         * @return the enclosing constructor for this class
337         */
338        @SuppressWarnings("unchecked")
339        public ConstructorEx<?> getEnclosingConstructor() {
340            Constructor<?> c = java.getEnclosingConstructor();
341            if (c==null) { return null; }
342            return new ConstructorEx(c, _classLoader);
343        }
344    
345        /**
346         * If this extended Class object represents a local or anonymous class within a method, returns an extended Method
347         * object representing the immediately enclosing method of the underlying class. Returns null otherwise.
348         * In particular, this method returns null if the underlying class is a local or anonymous class immediately
349         * enclosed by a type declaration, instance initializer or static initializer.
350         * @return the enclosing method for this class
351         */
352        public MethodEx getEnclosingMethod() {
353            Method m = java.getEnclosingMethod();
354            if (m==null) { return null; }
355            return new MethodEx(m, _classLoader);
356        }
357    
358        /**
359         * Returns an extended Field object that reflects the specified field of the class or interface
360         * represented by this extended Class object.
361         * @param name field name
362         * @return extended Field object
363         * @throws NoSuchFieldException if field not found
364         * @throws SecurityException if access is denied
365         */
366        public FieldEx getField(String name) throws NoSuchFieldException, SecurityException {
367            Field f = java.getField(name);
368            return new FieldEx(f, f.getClass().getClassLoader());
369        }
370    
371        /**
372         * Returns an array containing extended Field objects reflecting all the accessible public fields of the
373         * class or interface represented by this extended Class object.
374         * @return array of fields
375         * @throws SecurityException if access is denied
376         */
377        public FieldEx[] getFields() throws SecurityException {
378            List<FieldEx> list = new ArrayList<FieldEx>();
379            for(Field f: java.getFields()) {
380                list.add(new FieldEx(f, f.getClass().getClassLoader()));
381            }
382            return list.toArray(new FieldEx[list.size()]);
383        }
384    
385        /**
386         * Returns an extended Method object that reflects the specified method of the class or interface
387         * represented by this extended Class object.
388         * @param name method name
389         * @param parameterTypes parameter types
390         * @return extended Method object
391         * @throws NoSuchMethodException if method not found
392         * @throws SecurityException if access is denied
393         */
394        public MethodEx getMethod(String name, Class... parameterTypes)
395            throws NoSuchMethodException, SecurityException {
396            return new MethodEx(java.getMethod(name, parameterTypes), _classLoader);
397        }
398    
399        /**
400         * Returns an array containing extended Method objects reflecting all the public member methods of the class
401         * or interface represented by this extended Class object, including those declared by the class or interface
402         * and those inherited from superclasses and superinterfaces.
403         * @param name method name
404         * @param parameterTypes parameter types
405         * @return extended Method object
406         * @throws NoSuchMethodException if method not found
407         * @throws SecurityException if access is denied
408         */
409        public MethodEx getMethod(String name, ClassEx... parameterTypes)
410            throws NoSuchMethodException, SecurityException {
411            Class[] pt = new Class[parameterTypes.length];
412            for(int i=0; i<pt.length; ++i) {
413                pt[i] = parameterTypes[i].java;
414            }
415            return new MethodEx(java.getMethod(name, pt), _classLoader);
416        }
417    
418        /**
419         * Returns an array containing extended Method objects reflecting all the public member methods of the class
420         * or interface represented by this extended Class object, including those declared by the class or interface
421         * and those inherited from superclasses and superinterfaces.
422         * @return array of methods
423         * @throws SecurityException if access is denied
424         */
425        public MethodEx[] getMethods() throws SecurityException {
426            List<MethodEx> list = new ArrayList<MethodEx>();
427            for(Method m: java.getMethods()) {
428                list.add(new MethodEx(m, _classLoader));
429            }
430            return list.toArray(new MethodEx[list.size()]);
431        }
432    
433        /**
434         * Determines the interfaces implemented by the class or interface represented by this object.
435         * @return array of interfaces
436         */
437        @SuppressWarnings("unchecked")
438        public ClassEx[] getInterfaces() {
439            List<ClassEx> list = new ArrayList<ClassEx>();
440            for(Class c: java.getInterfaces()) {
441                list.add(new ClassEx(c, c.getClassLoader()));
442            }
443            return list.toArray(new ClassEx[list.size()]);
444        }
445    
446        /**
447         * Gets the package for this class.
448         * @return package
449         */
450        public PackageEx getPackage() {
451            Package p = java.getPackage();
452            if (p==null) { return null; }
453            return new PackageEx(p, _classLoader);
454        }
455    
456        /**
457         * Returns the extended Class representing the superclass of the entity (class, interface, primitive type or void)
458         * represented by this extended Class.
459         * @return superclass
460         */
461        @SuppressWarnings("unchecked")
462        public ClassEx<? super T> getSuperclass() {
463            Class<? super T> c = java.getSuperclass();
464            if (c==null) { return null; }
465            return new ClassEx(c, c.getClassLoader());
466        }
467    
468        /**
469         * Converts the object to a string. The string representation is the string "class" or "interface", followed by a
470         * space, and then by the fully qualified name of the class in the format returned by <code>getName</code>.  If this
471         * <code>Class</code> object represents a primitive type, this method returns the name of the primitive type.  If
472         * this <code>Class</code> object represents void this method returns "void".
473         *
474         * @return a string representation of this class object.
475         */
476        public String toString() {
477            return java.toString();
478        }
479    
480        /**
481         * Creates a new instance of the class represented by this <tt>Class</tt> object.  The class is instantiated as if
482         * by a <code>new</code> expression with an empty argument list.  The class is initialized if it has not already
483         * been initialized.
484         * <p/>
485         * <p>Note that this method propagates any exception thrown by the nullary constructor, including a checked
486         * exception. Use of this method effectively bypasses the compile-time exception checking that would otherwise be
487         * performed by the compiler. The {@link java.lang.reflect.Constructor#newInstance(Object...)
488         * Constructor.newInstance} method avoids this problem by wrapping any exception thrown by the constructor in a
489         * (checked) {@link java.lang.reflect.InvocationTargetException}.
490         *
491         * @return a newly allocated instance of the class represented by this object.
492         *
493         * @throws IllegalAccessException      if the class or its nullary constructor is not accessible.
494         * @throws InstantiationException      if this <code>Class</code> represents an abstract class, an interface, an
495         *                                     array class, a primitive type, or void; or if the class has no nullary
496         *                                     constructor; or if the instantiation fails for some other reason.
497         * @throws ExceptionInInitializerError if the initialization provoked by this method fails.
498         * @throws SecurityException           If a security manager, <i>s</i>, is present and any of the following
499         *                                     conditions is met:
500         *                                     <p/>
501         *                                     <ul>
502         *                                     <p/>
503         *                                     <li> invocation of <tt>{@link SecurityManager#checkMemberAccess
504         *                                     s.checkMemberAccess(this, Member.PUBLIC)}</tt> denies creation of new
505         *                                     instances of this class
506         *                                     <p/>
507         *                                     <li> the caller's class loader is not the same as or an ancestor of the class
508         *                                     loader for the current class and invocation of <tt>{@link
509         *                                     SecurityManager#checkPackageAccess s.checkPackageAccess()}</tt> denies access
510         *                                     to the package of this class
511         *                                     <p/>
512         *                                     </ul>
513         */
514        public T newInstance() throws InstantiationException, IllegalAccessException {
515            return java.newInstance();
516        }
517    
518        /**
519         * Determines if the specified <code>Object</code> is assignment-compatible with the object represented by this
520         * <code>Class</code>.  This method is the dynamic equivalent of the Java language <code>instanceof</code> operator.
521         * The method returns <code>true</code> if the specified <code>Object</code> argument is non-null and can be cast to
522         * the reference type represented by this <code>Class</code> object without raising a <code>ClassCastException.</code>
523         * It returns <code>false</code> otherwise.
524         * <p/>
525         * <p> Specifically, if this <code>Class</code> object represents a declared class, this method returns
526         * <code>true</code> if the specified <code>Object</code> argument is an instance of the represented class (or of any
527         * of its subclasses); it returns <code>false</code> otherwise. If this <code>Class</code> object represents an array
528         * class, this method returns <code>true</code> if the specified <code>Object</code> argument can be converted to an
529         * object of the array class by an identity conversion or by a widening reference conversion; it returns
530         * <code>false</code> otherwise. If this <code>Class</code> object represents an interface, this method returns
531         * <code>true</code> if the class or any superclass of the specified <code>Object</code> argument implements this
532         * interface; it returns <code>false</code> otherwise. If this <code>Class</code> object represents a primitive type,
533         * this method returns <code>false</code>.
534         *
535         * @param obj the object to check
536         *
537         * @return true if <code>obj</code> is an instance of this class
538         *
539         * @since JDK1.1
540         */
541        public boolean isInstance(Object obj) {
542            return java.isInstance(obj);
543        }
544    
545        /**
546         * Determines if the class or interface represented by this <code>Class</code> object is either the same as, or is a
547         * superclass or superinterface of, the class or interface represented by the specified <code>Class</code> parameter.
548         * It returns <code>true</code> if so; otherwise it returns <code>false</code>. If this <code>Class</code> object
549         * represents a primitive type, this method returns <code>true</code> if the specified <code>Class</code> parameter is
550         * exactly this <code>Class</code> object; otherwise it returns <code>false</code>.
551         * <p/>
552         * <p> Specifically, this method tests whether the type represented by the specified <code>Class</code> parameter can
553         * be converted to the type represented by this <code>Class</code> object via an identity conversion or via a widening
554         * reference conversion. See <em>The Java Language Specification</em>, sections 5.1.1 and 5.1.4 , for details.
555         *
556         * @param cls the <code>Class</code> object to be checked
557         *
558         * @return the <code>boolean</code> value indicating whether objects of the type <code>cls</code> can be assigned to
559         *         objects of this class
560         *
561         * @throws NullPointerException if the specified Class parameter is null.
562         * @since JDK1.1
563         */
564        public boolean isAssignableFrom(java.lang.Class cls) {
565            return java.isAssignableFrom(cls);
566        }
567    
568        /**
569         * Determines if the specified <code>Class</code> object represents an interface type.
570         *
571         * @return <code>true</code> if this object represents an interface; <code>false</code> otherwise.
572         */
573        public boolean isInterface() {
574            return java.isInterface();
575        }
576    
577        /**
578         * Determines if this <code>Class</code> object represents an array class.
579         *
580         * @return <code>true</code> if this object represents an array class; <code>false</code> otherwise.
581         *
582         * @since JDK1.1
583         */
584        public boolean isArray() {
585            return java.isArray();
586        }
587    
588        /**
589         * Determines if the specified <code>Class</code> object represents a primitive type.
590         * <p/>
591         * <p> There are nine predefined <code>Class</code> objects to represent the eight primitive types and void.  These
592         * are created by the Java Virtual Machine, and have the same names as the primitive types that they represent,
593         * namely <code>boolean</code>, <code>byte</code>, <code>char</code>, <code>short</code>, <code>int</code>,
594         * <code>long</code>, <code>float</code>, and <code>double</code>.
595         * <p/>
596         * <p> These objects may only be accessed via the following public static final variables, and are the only
597         * <code>Class</code> objects for which this method returns <code>true</code>.
598         *
599         * @return true if and only if this class represents a primitive type
600         *
601         * @see Boolean#TYPE
602         * @see Character#TYPE
603         * @see Byte#TYPE
604         * @see Short#TYPE
605         * @see Integer#TYPE
606         * @see Long#TYPE
607         * @see Float#TYPE
608         * @see Double#TYPE
609         * @see Void#TYPE
610         * @since JDK1.1
611         */
612        public boolean isPrimitive() {
613            return java.isPrimitive();
614        }
615    
616        /**
617         * Returns true if this <tt>Class</tt> object represents an annotation type.  Note that if this method returns true,
618         * {@link #isInterface()} would also return true, as all annotation types are also interfaces.
619         *
620         * @return <tt>true</tt> if this class object represents an annotation type; <tt>false</tt> otherwise
621         *
622         * @since 1.5
623         */
624        public boolean isAnnotation() {
625            return java.isAnnotation();
626        }
627    
628        /**
629         * Returns <tt>true</tt> if this class is a synthetic class; returns <tt>false</tt> otherwise.
630         *
631         * @return <tt>true</tt> if and only if this class is a synthetic class as defined by the Java Language
632         *         Specification.
633         *
634         * @since 1.5
635         */
636        public boolean isSynthetic() {
637            return java.isSynthetic();
638        }
639    
640        /**
641         * Returns the  name of the entity (class, interface, array class, primitive type, or void) represented by this
642         * <tt>Class</tt> object, as a <tt>String</tt>.
643         * <p/>
644         * <p> If this class object represents a reference type that is not an array type then the binary name of the class
645         * is returned, as specified by the Java Language Specification, Second Edition.
646         * <p/>
647         * <p> If this class object represents a primitive type or void, then the name returned is a <tt>String</tt> equal
648         * to the Java language keyword corresponding to the primitive type or void.
649         * <p/>
650         * <p> If this class object represents a class of arrays, then the internal form of the name consists of the name of
651         * the element type preceded by one or more '<tt>[</tt>' characters representing the depth of the array nesting.
652         * The encoding of element type names is as follows:
653         * <p/>
654         * <blockquote><table summary="Element types and encodings"> <tr><th> Element Type <th> Encoding <tr><td> boolean
655         * <td align=center> Z <tr><td> byte         <td align=center> B <tr><td> char         <td align=center> C <tr><td>
656         * class or interface  <td align=center> L<i>classname;</i> <tr><td> double       <td align=center> D <tr><td> float
657         * <td align=center> F <tr><td> int          <td align=center> I <tr><td> long         <td align=center> J <tr><td>
658         * short        <td align=center> S </table></blockquote>
659         * <p/>
660         * <p> The class or interface name <i>classname</i> is the binary name of the class specified above.
661         * <p/>
662         * <p> Examples:
663         * <blockquote><pre>
664         * String.class.getName()
665         *     returns "java.lang.String"
666         * byte.class.getName()
667         *     returns "byte"
668         * (new Object[3]).getClass().getName()
669         *     returns "[Ljava.lang.Object;"
670         * (new int[3][4][5][6][7][8][9]).getClass().getName()
671         *     returns "[[[[[[[I"
672         * </pre></blockquote>
673         *
674         * @return the name of the class or interface represented by this object.
675         */
676        public String getName() {
677            return java.getName();
678        }
679    
680        /**
681         * Returns the class loader for the class.  Some implementations may use null to represent the bootstrap class
682         * loader. This method will return null in such implementations if this class was loaded by the bootstrap class
683         * loader.
684         * <p/>
685         * <p> If a security manager is present, and the caller's class loader is not null and the caller's class loader is
686         * not the same as or an ancestor of the class loader for the class whose class loader is requested, then this
687         * method calls the security manager's <code>checkPermission</code> method with a
688         * <code>RuntimePermission("getClassLoader")</code> permission to ensure it's ok to access the class loader for the
689         * class.
690         * <p/>
691         * <p>If this object represents a primitive type or void, null is returned.
692         *
693         * @return the class loader that loaded the class or interface represented by this object.
694         *
695         * @throws SecurityException if a security manager exists and its <code>checkPermission</code> method denies access
696         *                           to the class loader for the class.
697         * @see ClassLoader
698         * @see SecurityManager#checkPermission
699         * @see RuntimePermission
700         */
701        public ClassLoader getClassLoader() {
702            return java.getClassLoader();
703        }
704    
705        /**
706         * Returns an array of <tt>TypeVariable</tt> objects that represent the type variables declared by the generic
707         * declaration represented by this <tt>GenericDeclaration</tt> object, in declaration order.  Returns an array of
708         * length 0 if the underlying generic declaration declares no type variables.
709         *
710         * @return an array of <tt>TypeVariable</tt> objects that represent the type variables declared by this generic
711         *         declaration
712         *
713         * @throws GenericSignatureFormatError if the generic signature of this generic declaration does not conform to the
714         *                                     format specified in the Java Virtual Machine Specification, 3rd edition
715         * @since 1.5
716         */
717        public TypeVariable[] getTypeParameters() {
718            return java.getTypeParameters();
719        }
720    
721        /**
722         * Returns the <tt>Type</tt> representing the direct superclass of the entity (class, interface, primitive type or
723         * void) represented by this <tt>Class</tt>.
724         * <p/>
725         * <p>If the superclass is a parameterized type, the <tt>Type</tt> object returned must accurately reflect the actual
726         * type parameters used in the source code. The parameterized type representing the superclass is created if it had not
727         * been created before. See the declaration of {@link java.lang.reflect.ParameterizedType ParameterizedType} for the
728         * semantics of the creation process for parameterized types.  If this <tt>Class</tt> represents either the
729         * <tt>Object</tt> class, an interface, a primitive type, or void, then null is returned.  If this object represents an
730         * array class then the <tt>Class</tt> object representing the <tt>Object</tt> class is returned.
731         *
732         * @return the superclass of the class represented by this object
733         *
734         * @throws GenericSignatureFormatError if the generic class signature does not conform to the format specified in the
735         *                                     Java Virtual Machine Specification, 3rd edition
736         * @throws TypeNotPresentException     if the generic superclass refers to a non-existent type declaration
737         * @throws MalformedParameterizedTypeException
738         *                                     if the generic superclass refers to a parameterized type that cannot be
739         *                                     instantiated  for any reason
740         * @since 1.5
741         */
742        public Type getGenericSuperclass() {
743            return java.getGenericSuperclass();
744        }
745    
746        /**
747         * Returns the <tt>Type</tt>s representing the interfaces directly implemented by the class or interface represented by
748         * this object.
749         * <p/>
750         * <p>If a superinterface is a parameterized type, the <tt>Type</tt> object returned for it must accurately reflect the
751         * actual type parameters used in the source code. The parameterized type representing each superinterface is created
752         * if it had not been created before. See the declaration of {@link java.lang.reflect.ParameterizedType
753         * ParameterizedType} for the semantics of the creation process for parameterized types.
754         * <p/>
755         * <p> If this object represents a class, the return value is an array containing objects representing all interfaces
756         * implemented by the class. The order of the interface objects in the array corresponds to the order of the interface
757         * names in the <tt>implements</tt> clause of the declaration of the class represented by this object.  In the case of
758         * an array class, the interfaces <tt>Cloneable</tt> and <tt>Serializable</tt> are returned in that order.
759         * <p/>
760         * <p>If this object represents an interface, the array contains objects representing all interfaces directly extended
761         * by the interface.  The order of the interface objects in the array corresponds to the order of the interface names
762         * in the <tt>extends</tt> clause of the declaration of the interface represented by this object.
763         * <p/>
764         * <p>If this object represents a class or interface that implements no interfaces, the method returns an array of
765         * length 0.
766         * <p/>
767         * <p>If this object represents a primitive type or void, the method returns an array of length 0.
768         *
769         * @return an array of interfaces implemented by this class
770         *
771         * @throws GenericSignatureFormatError if the generic class signature does not conform to the format specified in the
772         *                                     Java Virtual Machine Specification, 3rd edition
773         * @throws TypeNotPresentException     if any of the generic superinterfaces refers to a non-existent type declaration
774         * @throws MalformedParameterizedTypeException
775         *                                     if any of the generic superinterfaces refer to a parameterized type that cannot
776         *                                     be instantiated  for any reason
777         * @since 1.5
778         */
779        public Type[] getGenericInterfaces() {
780            return java.getGenericInterfaces();
781        }
782    
783        /**
784         * Returns the Java language modifiers for this class or interface, encoded in an integer. The modifiers consist of
785         * the Java Virtual Machine's constants for <code>public</code>, <code>protected</code>, <code>private</code>,
786         * <code>final</code>, <code>static</code>, <code>abstract</code> and <code>interface</code>; they should be decoded
787         * using the methods of class <code>Modifier</code>.
788         * <p/>
789         * <p> If the underlying class is an array class, then its <code>public</code>, <code>private</code> and
790         * <code>protected</code> modifiers are the same as those of its component type.  If this <code>Class</code>
791         * represents a primitive type or void, its <code>public</code> modifier is always <code>true</code>, and its
792         * <code>protected</code> and <code>private</code> modifiers are always <code>false</code>. If this object
793         * represents an array class, a primitive type or void, then its <code>final</code> modifier is always
794         * <code>true</code> and its interface modifier is always <code>false</code>. The values of its other modifiers are
795         * not determined by this specification.
796         * <p/>
797         * <p> The modifier encodings are defined in <em>The Java Virtual Machine Specification</em>, table 4.1.
798         *
799         * @return the <code>int</code> representing the modifiers for this class
800         *
801         * @see java.lang.reflect.Modifier
802         * @since JDK1.1
803         */
804        public int getModifiers() {
805            return java.getModifiers();
806        }
807    
808        /**
809         * Gets the signers of this class.
810         *
811         * @return the signers of this class, or null if there are no signers.  In particular, this method returns null if
812         *         this object represents a primitive type or void.
813         *
814         * @since JDK1.1
815         */
816        public Object[] getSigners() {
817            return java.getSigners();
818        }
819    
820        /**
821         * Returns the simple name of the underlying class as given in the source code. Returns an empty string if the
822         * underlying class is anonymous.
823         * <p/>
824         * <p>The simple name of an array is the simple name of the component type with "[]" appended.  In particular the
825         * simple name of an array whose component type is anonymous is "[]".
826         *
827         * @return the simple name of the underlying class
828         *
829         * @since 1.5
830         */
831        public String getSimpleName() {
832            return java.getSimpleName();
833        }
834    
835        /**
836         * Returns the canonical name of the the underlying class as defined by the Java Language Specification.  Returns
837         * null if the underlying class does not have a canonical name (i.e., if it is a local or anonymous class or an
838         * array whose component type does not have a canonical name).
839         *
840         * @return the canonical name of the underlying class if it exists, and <tt>null</tt> otherwise.
841         *
842         * @since 1.5
843         */
844        public String getCanonicalName() {
845            return java.getCanonicalName();
846        }
847    
848        /**
849         * Returns <tt>true</tt> if and only if the underlying class is an anonymous class.
850         *
851         * @return <tt>true</tt> if and only if this class is an anonymous class.
852         *
853         * @since 1.5
854         */
855        public boolean isAnonymousClass() {
856            return java.isAnonymousClass();
857        }
858    
859        /**
860         * Returns <tt>true</tt> if and only if the underlying class is a local class.
861         *
862         * @return <tt>true</tt> if and only if this class is a local class.
863         *
864         * @since 1.5
865         */
866        public boolean isLocalClass() {
867            return java.isLocalClass();
868        }
869    
870        /**
871         * Returns <tt>true</tt> if and only if the underlying class is a member class.
872         *
873         * @return <tt>true</tt> if and only if this class is a member class.
874         *
875         * @since 1.5
876         */
877        public boolean isMemberClass() {
878            return java.isMemberClass();
879        }
880    
881        /**
882         * Finds a resource with a given name.  The rules for searching resources associated with a given class are implemented
883         * by the defining {@linkplain ClassLoader class loader} of the class.  This method delegates to this object's class
884         * loader.  If this object was loaded by the bootstrap class loader, the method delegates to {@link
885         * ClassLoader#getSystemResourceAsStream}.
886         * <p/>
887         * <p> Before delegation, an absolute resource name is constructed from the given resource name using this algorithm:
888         * <p/>
889         * <ul>
890         * <p/>
891         * <li> If the <tt>name</tt> begins with a <tt>'/'</tt> (<tt>'&#92;u002f'</tt>), then the absolute name of the resource
892         * is the portion of the <tt>name</tt> following the <tt>'/'</tt>.
893         * <p/>
894         * <li> Otherwise, the absolute name is of the following form:
895         * <p/>
896         * <blockquote><pre>
897         *   <tt>modified_package_name</tt>/<tt>name</tt>
898         * </pre></blockquote>
899         * <p/>
900         * <p> Where the <tt>modified_package_name</tt> is the package name of this object with <tt>'/'</tt> substituted for
901         * <tt>'.'</tt> (<tt>'&#92;u002e'</tt>).
902         * <p/>
903         * </ul>
904         *
905         * @param name name of the desired resource
906         *
907         * @return A {@link java.io.InputStream} object or <tt>null</tt> if no resource with this name is found
908         *
909         * @throws NullPointerException If <tt>name</tt> is <tt>null</tt>
910         * @since JDK1.1
911         */
912        public InputStream getResourceAsStream(String name) {
913            return java.getResourceAsStream(name);
914        }
915    
916        /**
917         * Finds a resource with a given name.  The rules for searching resources associated with a given class are implemented
918         * by the defining {@linkplain ClassLoader class loader} of the class.  This method delegates to this object's class
919         * loader.  If this object was loaded by the bootstrap class loader, the method delegates to {@link
920         * ClassLoader#getSystemResource}.
921         * <p/>
922         * <p> Before delegation, an absolute resource name is constructed from the given resource name using this algorithm:
923         * <p/>
924         * <ul>
925         * <p/>
926         * <li> If the <tt>name</tt> begins with a <tt>'/'</tt> (<tt>'&#92;u002f'</tt>), then the absolute name of the resource
927         * is the portion of the <tt>name</tt> following the <tt>'/'</tt>.
928         * <p/>
929         * <li> Otherwise, the absolute name is of the following form:
930         * <p/>
931         * <blockquote><pre>
932         *   <tt>modified_package_name</tt>/<tt>name</tt>
933         * </pre></blockquote>
934         * <p/>
935         * <p> Where the <tt>modified_package_name</tt> is the package name of this object with <tt>'/'</tt> substituted for
936         * <tt>'.'</tt> (<tt>'&#92;u002e'</tt>).
937         * <p/>
938         * </ul>
939         *
940         * @param name name of the desired resource
941         *
942         * @return A  {@link java.net.URL} object or <tt>null</tt> if no resource with this name is found
943         *
944         * @since JDK1.1
945         */
946        public URL getResource(String name) {
947            return java.getResource(name);
948        }
949    
950        /**
951         * Returns the <code>ProtectionDomain</code> of this class.  If there is a security manager installed, this method
952         * first calls the security manager's <code>checkPermission</code> method with a <code>RuntimePermission("getProtectionDomain")</code>
953         * permission to ensure it's ok to get the <code>ProtectionDomain</code>.
954         *
955         * @return the ProtectionDomain of this class
956         *
957         * @throws SecurityException if a security manager exists and its <code>checkPermission</code> method doesn't allow
958         *                           getting the ProtectionDomain.
959         * @see java.security.ProtectionDomain
960         * @see SecurityManager#checkPermission
961         * @see RuntimePermission
962         * @since 1.2
963         */
964        public ProtectionDomain getProtectionDomain() {
965            return java.getProtectionDomain();
966        }
967    
968        /**
969         * Returns the assertion status that would be assigned to this class if it were to be initialized at the time this
970         * method is invoked. If this class has had its assertion status set, the most recent setting will be returned;
971         * otherwise, if any package default assertion status pertains to this class, the most recent setting for the most
972         * specific pertinent package default assertion status is returned; otherwise, if this class is not a system class
973         * (i.e., it has a class loader) its class loader's default assertion status is returned; otherwise, the system
974         * class default assertion status is returned.
975         * <p/>
976         * Few programmers will have any need for this method; it is provided for the benefit of the JRE itself.  (It allows
977         * a class to determine at the time that it is initialized whether assertions should be enabled.) Note that this
978         * method is not guaranteed to return the actual assertion status that was (or will be) associated with the
979         * specified class when it was (or will be) initialized.
980         *
981         * @return the desired assertion status of the specified class.
982         *
983         * @see ClassLoader#setClassAssertionStatus
984         * @see ClassLoader#setPackageAssertionStatus
985         * @see ClassLoader#setDefaultAssertionStatus
986         * @since 1.4
987         */
988        public boolean desiredAssertionStatus() {
989            return java.desiredAssertionStatus();
990        }
991    
992        /**
993         * Returns true if and only if this class was declared as an enum in the source code.
994         *
995         * @return true if and only if this class was declared as an enum in the source code
996         *
997         * @since 1.5
998         */
999        public boolean isEnum() {
1000            return java.isEnum();
1001        }
1002    
1003        /**
1004         * Returns the elements of this enum class or null if this Class object does not represent an enum type.
1005         *
1006         * @return an array containing the values comprising the enum class represented by this Class object in the order
1007         *         they're declared, or null if this Class object does not represent an enum type
1008         *
1009         * @since 1.5
1010         */
1011        public Object[] getEnumConstants() {
1012            return java.getEnumConstants();
1013        }
1014    
1015        /**
1016         * Casts an object to the class or interface represented by this <tt>Class</tt> object.
1017         *
1018         * @param obj the object to be cast
1019         *
1020         * @return the object after casting, or null if obj is null
1021         *
1022         * @throws ClassCastException if the object is not null and is not assignable to the type T.
1023         * @since 1.5
1024         */
1025        public Object cast(Object obj) {
1026            return java.cast(obj);
1027        }
1028    
1029        /**
1030         * Casts this <tt>Class</tt> object to represent a subclass of the class represented by the specified class object.
1031         * Checks that that the cast is valid, and throws a <tt>ClassCastException</tt> if it is not.  If this method succeeds,
1032         * it always returns a reference to this class object.
1033         * <p/>
1034         * <p>This method is useful when a client needs to "narrow" the type of a <tt>Class</tt> object to pass it to an API
1035         * that restricts the <tt>Class</tt> objects that it is willing to accept.  A cast would generate a compile-time
1036         * warning, as the correctness of the cast could not be checked at runtime (because generic types are implemented by
1037         * erasure).
1038         * @param clazz superclass
1039         * @return this <tt>Class</tt> object, cast to represent a subclass of the specified class object.
1040         *
1041         * @throws ClassCastException if this <tt>Class</tt> object does not represent a subclass of the specified class (here
1042         *                            "subclass" includes the class itself).
1043         * @since 1.5
1044         */
1045        @SuppressWarnings("unchecked")
1046        public <U> ClassEx<? extends U> asSubclass(ClassEx<U> clazz) {
1047            Class<? extends U> c = java.asSubclass(clazz.java);
1048            return new ClassEx(c, c.getClassLoader());
1049        }
1050    
1051        /**
1052         * Compares this <code>Constructor</code> against the specified object. Returns true if the objects are the same.  Two
1053         * <code>Constructor</code> objects are the same if they were declared by the same class and have the same formal
1054         * parameter types.
1055         */
1056        public boolean equals(Object obj) {
1057            return (obj!=null)&&(obj.getClass().equals(this.getClass()) && (java.equals(obj)));
1058        }
1059    
1060        /**
1061         * Returns a hashcode for this <code>Constructor</code>. The hashcode is the same as the hashcode for the underlying
1062         * constructor's declaring class name.
1063         */
1064        public int hashCode() {
1065            return java.hashCode();
1066        }
1067    }