]> source.dussan.org Git - aspectj.git/blob
8da8151cf3529e497ea213f65887c9ce509f3080
[aspectj.git] /
1 /* *******************************************************************
2  * Copyright (c) 2005 Contributors.
3  * All rights reserved.
4  * This program and the accompanying materials are made available
5  * under the terms of the Eclipse Public License v 2.0
6  * which accompanies this distribution and is available at
7  * https://www.eclipse.org/org/documents/epl-2.0/EPL-2.0.txt
8  *
9  * Contributors:
10  *   Adrian Colyer                      Initial implementation
11  * ******************************************************************/
12 package org.aspectj.weaver.reflect;
13
14 import java.lang.reflect.Constructor;
15 import java.lang.reflect.Field;
16 import java.lang.reflect.InvocationTargetException;
17 import java.lang.reflect.Member;
18 import java.lang.reflect.Method;
19 import java.lang.reflect.Modifier;
20
21 import org.aspectj.weaver.ReferenceType;
22 import org.aspectj.weaver.ResolvedMember;
23 import org.aspectj.weaver.ResolvedMemberImpl;
24 import org.aspectj.weaver.ResolvedType;
25 import org.aspectj.weaver.UnresolvedType;
26 import org.aspectj.weaver.World;
27
28 /**
29  * @author colyer Creates the appropriate ReflectionBasedReferenceTypeDelegate according to the VM level we are running at. Uses
30  *         reflection to avoid 1.5 dependencies in 1.4 and 1.3 code base.
31  */
32 public class ReflectionBasedReferenceTypeDelegateFactory {
33
34         public static ReflectionBasedReferenceTypeDelegate createDelegate(ReferenceType forReferenceType, World inWorld,
35                         ClassLoader usingClassLoader) {
36                 try {
37                         Class c = Class.forName(forReferenceType.getName(), false, usingClassLoader);
38                         ReflectionBasedReferenceTypeDelegate rbrtd = create15Delegate(forReferenceType, c, usingClassLoader, inWorld);
39                         if (rbrtd != null) {
40                                 return rbrtd; // can be null if we didn't find the class the delegate logic loads
41                         }
42                         return new ReflectionBasedReferenceTypeDelegate(c, usingClassLoader, inWorld, forReferenceType);
43                 } catch (ClassNotFoundException cnfEx) {
44                         return null;
45                 }
46         }
47
48         public static ReflectionBasedReferenceTypeDelegate createDelegate(ReferenceType forReferenceType, World inWorld,
49                         Class<?> clazz) {
50                 ReflectionBasedReferenceTypeDelegate rbrtd = create15Delegate(forReferenceType, clazz, clazz.getClassLoader(), inWorld);
51                 if (rbrtd != null) {
52                         return rbrtd; // can be null if we didn't find the class the delegate logic loads
53                 }
54                 return new ReflectionBasedReferenceTypeDelegate(clazz, clazz.getClassLoader(), inWorld, forReferenceType);
55         }
56
57         public static ReflectionBasedReferenceTypeDelegate create14Delegate(ReferenceType forReferenceType, World inWorld,
58                         ClassLoader usingClassLoader) {
59                 try {
60                         Class c = Class.forName(forReferenceType.getName(), false, usingClassLoader);
61                         return new ReflectionBasedReferenceTypeDelegate(c, usingClassLoader, inWorld, forReferenceType);
62                 } catch (ClassNotFoundException cnfEx) {
63                         return null;
64                 }
65         }
66
67         // can return 'null' if we can't find the class
68         private static ReflectionBasedReferenceTypeDelegate create15Delegate(ReferenceType forReferenceType, Class forClass,
69                         ClassLoader usingClassLoader, World inWorld) {
70                 try {
71                         Class delegateClass = Class.forName("org.aspectj.weaver.reflect.Java15ReflectionBasedReferenceTypeDelegate");
72                         ReflectionBasedReferenceTypeDelegate ret = (ReflectionBasedReferenceTypeDelegate) delegateClass.getDeclaredConstructor().newInstance();
73                         ret.initialize(forReferenceType, forClass, usingClassLoader, inWorld);
74                         return ret;
75                 } catch (ClassNotFoundException cnfEx) {
76                         throw new IllegalStateException(
77                                         "Attempted to create Java 1.5 reflection based delegate but org.aspectj.weaver.reflect.Java15ReflectionBasedReferenceTypeDelegate was not found on classpath");
78                 } catch (InstantiationException insEx) {
79                         throw new IllegalStateException("Attempted to create Java 1.5 reflection based delegate but InstantiationException: "
80                                         + insEx + " occured");
81                 } catch (IllegalAccessException illAccEx) {
82                         throw new IllegalStateException("Attempted to create Java 1.5 reflection based delegate but IllegalAccessException: "
83                                         + illAccEx + " occured");
84                 } catch (NoSuchMethodException nsMethEx) {
85                         throw new IllegalStateException("Attempted to create Java 1.5 reflection based delegate but NoSuchMethodException: "
86                                         + nsMethEx + " occured");
87                 } catch (InvocationTargetException invTargEx) {
88                         throw new IllegalStateException("Attempted to create Java 1.5 reflection based delegate but InvocationTargetException: "
89                                         + invTargEx + " occured");
90                 }
91         }
92
93         private static GenericSignatureInformationProvider createGenericSignatureProvider(World inWorld) {
94                 try {
95                         Class providerClass = Class.forName("org.aspectj.weaver.reflect.Java15GenericSignatureInformationProvider");
96                         Constructor cons = providerClass.getConstructor(new Class[] { World.class });
97                         GenericSignatureInformationProvider ret = (GenericSignatureInformationProvider) cons
98                                         .newInstance(new Object[] { inWorld });
99                         return ret;
100                 } catch (ClassNotFoundException cnfEx) {
101                         // drop through and create a 14 provider...
102                         // throw new
103                         // IllegalStateException("Attempted to create Java 1.5 generic signature provider but org.aspectj.weaver.reflect.Java15GenericSignatureInformationProvider was not found on classpath");
104                 } catch (NoSuchMethodException nsmEx) {
105                         throw new IllegalStateException("Attempted to create Java 1.5 generic signature provider but: " + nsmEx
106                                         + " occured");
107                 } catch (InstantiationException insEx) {
108                         throw new IllegalStateException("Attempted to create Java 1.5 generic signature provider but: " + insEx
109                                         + " occured");
110                 } catch (InvocationTargetException invEx) {
111                         throw new IllegalStateException("Attempted to create Java 1.5 generic signature provider but: " + invEx
112                                         + " occured");
113                 } catch (IllegalAccessException illAcc) {
114                         throw new IllegalStateException("Attempted to create Java 1.5 generic signature provider but: " + illAcc
115                                         + " occured");
116                 }
117                 return new Java14GenericSignatureInformationProvider();
118         }
119
120         /**
121          * convert a java.lang.reflect.Member into a resolved member in the world
122          *
123          * @param reflectMember
124          * @param inWorld
125          * @return
126          */
127         public static ResolvedMember createResolvedMember(Member reflectMember, World inWorld) {
128                 if (reflectMember instanceof Method) {
129                         return createResolvedMethod((Method) reflectMember, inWorld);
130                 } else if (reflectMember instanceof Constructor) {
131                         return createResolvedConstructor((Constructor) reflectMember, inWorld);
132                 } else {
133                         return createResolvedField((Field) reflectMember, inWorld);
134                 }
135         }
136
137         public static ResolvedMember createResolvedMethod(Method aMethod, World inWorld) {
138                 ReflectionBasedResolvedMemberImpl ret = new ReflectionBasedResolvedMemberImpl(org.aspectj.weaver.Member.METHOD,
139                                 toResolvedType(aMethod.getDeclaringClass(), (IReflectionWorld) inWorld), aMethod.getModifiers(), toResolvedType(
140                                                 aMethod.getReturnType(), (IReflectionWorld) inWorld), aMethod.getName(), toResolvedTypeArray(
141                                                 aMethod.getParameterTypes(), inWorld), toResolvedTypeArray(aMethod.getExceptionTypes(), inWorld), aMethod);
142                 if (inWorld instanceof IReflectionWorld) {
143                         ret.setAnnotationFinder(((IReflectionWorld) inWorld).getAnnotationFinder());
144                 }
145                 ret.setGenericSignatureInformationProvider(createGenericSignatureProvider(inWorld));
146                 return ret;
147         }
148
149         public static ResolvedMember createResolvedAdviceMember(Method aMethod, World inWorld) {
150                 ReflectionBasedResolvedMemberImpl ret = new ReflectionBasedResolvedMemberImpl(org.aspectj.weaver.Member.ADVICE,
151                                 toResolvedType(aMethod.getDeclaringClass(), (IReflectionWorld) inWorld), aMethod.getModifiers(), toResolvedType(
152                                                 aMethod.getReturnType(), (IReflectionWorld) inWorld), aMethod.getName(), toResolvedTypeArray(
153                                                 aMethod.getParameterTypes(), inWorld), toResolvedTypeArray(aMethod.getExceptionTypes(), inWorld), aMethod);
154                 if (inWorld instanceof IReflectionWorld) {
155                         ret.setAnnotationFinder(((IReflectionWorld) inWorld).getAnnotationFinder());
156                 }
157                 ret.setGenericSignatureInformationProvider(createGenericSignatureProvider(inWorld));
158                 return ret;
159         }
160
161         public static ResolvedMember createStaticInitMember(Class forType, World inWorld) {
162                 return new ResolvedMemberImpl(org.aspectj.weaver.Member.STATIC_INITIALIZATION, toResolvedType(forType,
163                                 (IReflectionWorld) inWorld), Modifier.STATIC, UnresolvedType.VOID, "<clinit>", new UnresolvedType[0],
164                                 new UnresolvedType[0]);
165         }
166
167         public static ResolvedMember createResolvedConstructor(Constructor aConstructor, World inWorld) {
168                 ReflectionBasedResolvedMemberImpl ret = new ReflectionBasedResolvedMemberImpl(org.aspectj.weaver.Member.CONSTRUCTOR,
169                                 toResolvedType(aConstructor.getDeclaringClass(), (IReflectionWorld) inWorld), aConstructor.getModifiers(),
170                                 // to return what BCEL returns, the return type for ctor is void
171                                 UnresolvedType.VOID,// toResolvedType(aConstructor.getDeclaringClass(),(IReflectionWorld)inWorld),
172                                 "<init>", toResolvedTypeArray(aConstructor.getParameterTypes(), inWorld), toResolvedTypeArray(
173                                                 aConstructor.getExceptionTypes(), inWorld), aConstructor);
174                 if (inWorld instanceof IReflectionWorld) {
175                         ret.setAnnotationFinder(((IReflectionWorld) inWorld).getAnnotationFinder());
176                 }
177                 ret.setGenericSignatureInformationProvider(createGenericSignatureProvider(inWorld));
178                 return ret;
179         }
180
181         public static ResolvedMember createResolvedField(Field aField, World inWorld) {
182                 ReflectionBasedResolvedMemberImpl ret = new ReflectionBasedResolvedMemberImpl(org.aspectj.weaver.Member.FIELD,
183                                 toResolvedType(aField.getDeclaringClass(), (IReflectionWorld) inWorld), aField.getModifiers(), toResolvedType(
184                                                 aField.getType(), (IReflectionWorld) inWorld), aField.getName(), new UnresolvedType[0], aField);
185                 if (inWorld instanceof IReflectionWorld) {
186                         ret.setAnnotationFinder(((IReflectionWorld) inWorld).getAnnotationFinder());
187                 }
188                 ret.setGenericSignatureInformationProvider(createGenericSignatureProvider(inWorld));
189                 return ret;
190         }
191
192         public static ResolvedMember createHandlerMember(Class exceptionType, Class inType, World inWorld) {
193                 return new ResolvedMemberImpl(org.aspectj.weaver.Member.HANDLER, toResolvedType(inType, (IReflectionWorld) inWorld),
194                                 Modifier.STATIC, "<catch>", "(" + inWorld.resolve(exceptionType.getName()).getSignature() + ")V");
195         }
196
197         public static ResolvedType resolveTypeInWorld(Class aClass, World aWorld) {
198                 // classes that represent arrays return a class name that is the signature of the array type, ho-hum...
199                 String className = aClass.getName();
200                 if (aClass.isArray()) {
201                         return aWorld.resolve(UnresolvedType.forSignature(className.replace('.', '/')));
202                 } else {
203                         return aWorld.resolve(className);
204                 }
205         }
206
207         private static ResolvedType toResolvedType(Class aClass, IReflectionWorld aWorld) {
208                 return aWorld.resolve(aClass);
209         }
210
211         private static ResolvedType[] toResolvedTypeArray(Class[] classes, World inWorld) {
212                 ResolvedType[] ret = new ResolvedType[classes.length];
213                 for (int i = 0; i < ret.length; i++) {
214                         ret[i] = ((IReflectionWorld) inWorld).resolve(classes[i]);
215                 }
216                 return ret;
217         }
218 }