1 16 17 package org.springframework.aop.aspectj; 18 19 import java.lang.reflect.Field ; 20 21 import org.aspectj.weaver.ast.And; 22 import org.aspectj.weaver.ast.Call; 23 import org.aspectj.weaver.ast.FieldGetCall; 24 import org.aspectj.weaver.ast.HasAnnotation; 25 import org.aspectj.weaver.ast.ITestVisitor; 26 import org.aspectj.weaver.ast.Instanceof; 27 import org.aspectj.weaver.ast.Literal; 28 import org.aspectj.weaver.ast.Not; 29 import org.aspectj.weaver.ast.Or; 30 import org.aspectj.weaver.ast.Test; 31 import org.aspectj.weaver.internal.tools.MatchingContextBasedTest; 32 import org.aspectj.weaver.reflect.ReflectionVar; 33 import org.aspectj.weaver.reflect.ShadowMatchImpl; 34 import org.aspectj.weaver.tools.ShadowMatch; 35 36 51 public class RuntimeTestWalker { 52 53 private Test runtimeTest; 54 55 public RuntimeTestWalker(ShadowMatch shadowMatch) { 56 ShadowMatchImpl shadowMatchImplementation = (ShadowMatchImpl) shadowMatch; 57 try { 58 Field testField = shadowMatchImplementation.getClass().getDeclaredField("residualTest"); 59 testField.setAccessible(true); 60 this.runtimeTest = (Test) testField.get(shadowMatch); 61 } 62 catch(NoSuchFieldException noSuchFieldEx) { 63 throw new IllegalStateException ("the version of aspectjtools.jar / aspectjweaver.jar " + 64 "on the classpath is incompatible with this version of Spring:- expected field " + 65 "'runtimeTest' is not present on ShadowMatchImpl class"); 66 } 67 catch (IllegalAccessException illegalAccessEx) { 68 throw new IllegalStateException ("Unable to access ShadowMatchImpl.runtimeTest field."); 71 } 72 } 73 74 78 public boolean testsSubtypeSensitiveVars() { 79 return new SubtypeSensitiveVarTypeTestVisitor().testsSubtypeSensitiveVars(this.runtimeTest); 80 } 81 82 83 private static class SubtypeSensitiveVarTypeTestVisitor implements ITestVisitor { 84 85 private static final int AT_THIS_VAR = 3; 86 private static final int AT_TARGET_VAR = 4; 87 private static final int AT_ANNOTATION_VAR = 8; 88 89 private final Object thisObj = new Object (); 90 private final Object targetObj = new Object (); 91 private final Object [] argsObjs = new Object [0]; 92 93 private boolean testsSubtypeSensitiveVars = false; 94 95 public boolean testsSubtypeSensitiveVars(Test aTest) { 96 aTest.accept(this); 97 return this.testsSubtypeSensitiveVars; 98 } 99 100 public void visit(And e) { 101 e.getLeft().accept(this); 102 e.getRight().accept(this); 103 } 104 105 public void visit(Or e) { 106 e.getLeft().accept(this); 107 e.getRight().accept(this); 108 } 109 110 public void visit(Not e) { 111 e.getBody().accept(this); 112 } 113 114 public void visit(Instanceof i) { 115 ReflectionVar v = (ReflectionVar) i.getVar(); 116 Object varUnderTest = v.getBindingAtJoinPoint(thisObj,targetObj,argsObjs); 117 if ((varUnderTest == thisObj) || (varUnderTest == targetObj)) { 118 this.testsSubtypeSensitiveVars = true; 119 } 120 } 121 122 public void visit(HasAnnotation hasAnn) { 123 ReflectionVar v = (ReflectionVar) hasAnn.getVar(); 126 try { 127 Field varTypeField = ReflectionVar.class.getDeclaredField("varType"); 128 varTypeField.setAccessible(true); 129 Integer varTypeValue = (Integer ) varTypeField.get(v); 130 int varType = varTypeValue.intValue(); 131 if ((varType == AT_THIS_VAR) || 132 (varType == AT_TARGET_VAR) || 133 (varType == AT_ANNOTATION_VAR)) { 134 this.testsSubtypeSensitiveVars = true; 135 } 136 } 137 catch(NoSuchFieldException noSuchFieldEx) { 138 throw new IllegalStateException ("the version of aspectjtools.jar / aspectjweaver.jar " + 139 "on the classpath is incompatible with this version of Spring:- expected field " + 140 "'varType' is not present on ReflectionVar class"); 141 } 142 catch(IllegalAccessException illegalAccessEx) { 143 throw new IllegalStateException ("Unable to access ReflectionVar.varType field."); 146 } 147 } 148 149 public void visit(Literal e) { 150 } 152 153 public void visit(Call e) { 154 } 156 157 public void visit(FieldGetCall e) { 158 } 160 161 public void visit(MatchingContextBasedTest arg0) { 162 } 164 165 } 166 } 167 | Popular Tags |