1 27 package ch.ethz.prose.crosscut; 28 29 import java.lang.reflect.Method ; 31 import java.lang.Class ; 32 33 34 53 public abstract 54 class SignaturePattern { 55 56 57 protected final static int WILDCARD_1 = 0x02; 59 protected final static int WILDCARD_2 = 0x04; 60 protected final static int CONCRETE_1= 0x08; 61 protected final static int CONCRETE_2= 0x01; 62 63 protected static final int SIGNATURE__WILDCARD__WILDCARD = WILDCARD_1 | WILDCARD_2; 65 protected static final int SIGNATURE__WILDCARD__CONCRETE = WILDCARD_1 | CONCRETE_2; 66 protected static final int SIGNATURE__CONCRETE__WILDCARD = CONCRETE_1 | WILDCARD_2; 67 protected static final int SIGNATURE__CONCRETE__CONCRETE = CONCRETE_1 | CONCRETE_2; 68 protected static final int SIGNATURE__ARBITRARY = 0; 69 protected static final int SIGNATURE__EMPTY = 0x1000; 70 71 73 protected int signatureCathegory = SIGNATURE__ARBITRARY; 74 75 79 protected transient Method methodObj = null; 80 81 85 protected transient Class [] signature = null; 86 87 protected transient Class wildcardClass = null; 88 89 90 91 94 protected int getLength() 95 { 96 return signature.length; 97 } 98 99 protected Class getReceiverType() 100 { 101 if (signature.length == 0) 102 return null; 103 else 104 return signature[0]; 105 } 106 112 protected boolean matchesTarget(Class actualClass) 113 { 114 if (signatureCathegory == SIGNATURE__EMPTY) 115 return true; 116 else 117 return isAssignable(actualClass, signature[0]); 118 } 119 120 121 protected boolean isAssignable(Class actualParameterType, Class formalParameterType) throws Error 122 { 123 if (Wildcard.class.isAssignableFrom(formalParameterType)) 124 { 125 try 126 { 127 if (((Wildcard)formalParameterType.newInstance()).isAssignableFrom(actualParameterType)) 128 return true; 129 130 } 134 catch (IllegalAccessException noConstructor) 135 { 136 throw new Error (noConstructor.toString()); 137 } 138 catch (InstantiationException wrongConstructor) 139 { 140 throw new Error (wrongConstructor.toString()); 141 } 142 return false; 143 } 144 else if ( formalParameterType.isAssignableFrom(actualParameterType)) 145 return true; 146 else 147 return false; 148 } 149 150 151 protected void initFromMethod(Class methodClass, String adviceName, Class wildcardClass,Class htop) 152 { 153 154 this.wildcardClass = wildcardClass; 155 initAdviceMethod(methodClass,adviceName,htop); 156 signature = methodObj.getParameterTypes(); 157 initSignatureCathegory(); 158 } 159 160 private void initAdviceMethod(Class methodClass,String adviceName,Class hierarchyTop) 161 { 162 int ambigousCnt = 0; 163 Method mObj = null; 164 Class crtClass = methodClass; 165 166 167 while (crtClass != null && 169 !crtClass.equals(hierarchyTop) && hierarchyTop.isAssignableFrom(crtClass) && mObj == null) 172 { 173 Method [] methods = crtClass.getDeclaredMethods(); 174 ambigousCnt = 0; 175 176 179 for (int i=0; i < methods.length; i++) 180 if ( methods[i].getName().equals(adviceName)) 181 { 182 mObj = methods[i]; 183 ambigousCnt++; 184 } 185 186 crtClass=crtClass.getSuperclass(); 187 } 188 189 if (mObj == null) 190 throw new MissingInformationException("No advice action specified"); 191 if (ambigousCnt > 1) 192 throw new MissingInformationException("Two advice methods detected. Ambigous advice specification"); 193 194 try 195 { 196 mObj.setAccessible(true); 197 } 198 catch (SecurityException opaqueCrosscut) 199 { 200 } 202 203 methodObj = mObj; 204 } 205 206 private void initSignatureCathegory() 207 { 208 Method m = methodObj; 209 int optimization = SIGNATURE__ARBITRARY; 210 Class [] adviceParamTypes = m.getParameterTypes(); 211 212 if (adviceParamTypes.length == 0) 213 { 214 signatureCathegory = SIGNATURE__EMPTY; 215 return; 216 } 217 218 if (ANY.class.isAssignableFrom(adviceParamTypes[0])) 220 optimization |= WILDCARD_1; 221 else 222 optimization |= CONCRETE_1; 223 224 225 boolean restIsWildcard = true; 227 boolean restIsConcrete = true; 228 for (int i = 1; i < adviceParamTypes.length; i++) 229 { 230 if (Wildcard.class.isAssignableFrom(adviceParamTypes[i])) 231 restIsConcrete = false; 232 else 233 restIsWildcard = false; 234 } 235 236 if (restIsWildcard && adviceParamTypes.length == 2 && adviceParamTypes[1].equals(wildcardClass)) 238 optimization |= WILDCARD_2; 239 if (restIsConcrete) 240 optimization |= CONCRETE_2; 241 242 signatureCathegory = optimization; 243 } 244 245 246 protected boolean isAssignable(Class [] actualParameterType, Class formalParameterType) 247 { 248 if (Wildcard.class.isAssignableFrom(formalParameterType)) 249 { 250 try 251 { 252 if (((Wildcard)formalParameterType.newInstance()).isAssignableFrom(actualParameterType)) 253 return true; 254 } 255 catch (IllegalAccessException noConstructor) 256 { 257 throw new Error (noConstructor.toString()); 258 } 259 catch (InstantiationException wrongConstructor) 260 { 261 throw new Error (wrongConstructor.toString()); 262 } 263 return false; 264 } 265 else 266 return false; 267 } 268 269 } 270 271 272
| Popular Tags
|