View Javadoc

1   /***************************************************************************************
2    * Copyright (c) Jonas BonŽr, Alexandre Vasseur. All rights reserved.                 *
3    * http://aspectwerkz.codehaus.org                                                    *
4    * ---------------------------------------------------------------------------------- *
5    * The software in this package is published under the terms of the LGPL license      *
6    * a copy of which has been included with this distribution in the license.txt file.  *
7    **************************************************************************************/
8   package org.codehaus.aspectwerkz.expression;
9   
10  import org.codehaus.aspectwerkz.reflect.ClassInfo;
11  import org.codehaus.aspectwerkz.reflect.ConstructorInfo;
12  import org.codehaus.aspectwerkz.reflect.FieldInfo;
13  import org.codehaus.aspectwerkz.reflect.MethodInfo;
14  import org.codehaus.aspectwerkz.reflect.ReflectionInfo;
15  import org.codehaus.aspectwerkz.reflect.StaticInitializationInfo;
16  
17  import gnu.trove.TIntIntHashMap;
18  import gnu.trove.TObjectIntHashMap;
19  
20  /***
21   * The expression context for AST evaluation.
22   *
23   * @author <a href="mailto:jboner@codehaus.org">Jonas BonŽr </a>
24   * @author <a href="mailto:alex AT gnilux DOT com">Alexandre Vasseur</a>
25   */
26  public class ExpressionContext {
27      public static final int INFO_NOT_AVAILABLE = -1;
28  
29      public static final int METHOD_INFO = 0;
30  
31      public static final int CONSTRUCTOR_INFO = 1;
32  
33      public static final int FIELD_INFO = 2;
34  
35      public static final int CLASS_INFO = 3;
36      
37      private static final int STATIC_INFO = 4;
38  
39      private final int m_reflectionInfoType;
40  
41      private final PointcutType m_pointcutType;
42  
43      private final ReflectionInfo m_matchingReflectionInfo;
44  
45      private final ReflectionInfo m_withinReflectionInfo;
46  
47      private boolean m_inCflowSubAST = false;
48  
49      private boolean m_cflowEvaluation = false;
50  
51      private boolean m_hasBeenVisitingCflow = false;
52  
53      private int m_currentTargetArgsIndex = 0;
54  
55      /***
56       * Expression to advised target (method / ctor) argument index map.
57       * It depends on the matching context and the pointcut signature, as well as args(..)
58       */
59      public gnu.trove.TObjectIntHashMap m_exprIndexToTargetIndex = new TObjectIntHashMap();
60  
61      /***
62       * The variable name corresponding to the this(..) designator,
63       * or null if nothing is bound (this(<type>) or no this(..))
64       */
65      public String m_thisBoundedName = null;
66  
67      /***
68       * The variable name corresponding to the target(..) designator,
69       * or null if nothing is bound (target(<type>) or no target(..))
70       */
71      public String m_targetBoundedName = null;
72  
73      /***
74       * Set to true when we encounter a poincut using target(..) and when match cannot be done without a
75       * runtime check with instance of.
76       */
77      public boolean m_targetWithRuntimeCheck = false;
78  
79      /***
80       * Creates a new expression context.
81       *
82       * @param pointcutType
83       * @param reflectionInfo       - can be null f.e. with early evaluation of CALL pointcut
84       * @param withinReflectionInfo
85       */
86      public ExpressionContext(final PointcutType pointcutType,
87                               final ReflectionInfo reflectionInfo,
88                               final ReflectionInfo withinReflectionInfo) {
89          if (pointcutType == null) {
90              throw new IllegalArgumentException("pointcut type can not be null");
91          }
92          m_pointcutType = pointcutType;
93          m_matchingReflectionInfo = reflectionInfo;
94          if (withinReflectionInfo != null) {
95              m_withinReflectionInfo = withinReflectionInfo;
96          } else {
97              if (PointcutType.EXECUTION.equals(pointcutType)
98                  || PointcutType.STATIC_INITIALIZATION.equals(pointcutType)
99                  || PointcutType.WITHIN.equals(pointcutType)) {
100                 m_withinReflectionInfo = m_matchingReflectionInfo;
101             } else {
102                 m_withinReflectionInfo = null;
103             }
104         }
105         if (reflectionInfo instanceof MethodInfo) {
106             m_reflectionInfoType = METHOD_INFO;
107         } else if (reflectionInfo instanceof ConstructorInfo) {
108             m_reflectionInfoType = CONSTRUCTOR_INFO;
109         } else if (reflectionInfo instanceof FieldInfo) {
110             m_reflectionInfoType = FIELD_INFO;
111         } else if (reflectionInfo instanceof ClassInfo) {
112             m_reflectionInfoType = CLASS_INFO;
113         } else if (reflectionInfo instanceof StaticInitializationInfo) {
114         	m_reflectionInfoType = STATIC_INFO;
115         } else {
116             m_reflectionInfoType = INFO_NOT_AVAILABLE;// used for early eval on CALL
117         }
118     }
119 
120     public ReflectionInfo getReflectionInfo() {
121         return m_matchingReflectionInfo;
122     }
123 
124     public ReflectionInfo getWithinReflectionInfo() {
125         return m_withinReflectionInfo;
126     }
127 
128     public boolean hasExecutionPointcut() {
129         return m_pointcutType.equals(PointcutType.EXECUTION);
130     }
131 
132     public boolean hasCallPointcut() {
133         return m_pointcutType.equals(PointcutType.CALL);
134     }
135 
136     public boolean hasSetPointcut() {
137         return m_pointcutType.equals(PointcutType.SET);
138     }
139 
140     public boolean hasGetPointcut() {
141         return m_pointcutType.equals(PointcutType.GET);
142     }
143 
144     public boolean hasHandlerPointcut() {
145         return m_pointcutType.equals(PointcutType.HANDLER);
146     }
147 
148     public boolean hasStaticInitializationPointcut() {
149         return m_pointcutType.equals(PointcutType.STATIC_INITIALIZATION);
150     }
151 
152     public boolean hasWithinPointcut() {
153         return m_pointcutType.equals(PointcutType.WITHIN);
154     }
155 //
156 //    public boolean hasHasMethodPointcut() {
157 //        return m_pointcutType.equals(PointcutType.HAS_METHOD);
158 //    }
159 //
160 //    public boolean hasHasFieldPointcut() {
161 //        return m_pointcutType.equals(PointcutType.HAS_FIELD);
162 //    }
163 
164     public boolean hasWithinReflectionInfo() {
165         return m_withinReflectionInfo != null;
166     }
167 
168     public boolean hasMethodInfo() {
169         return m_reflectionInfoType == METHOD_INFO;
170     }
171 
172     public boolean hasConstructorInfo() {
173         return m_reflectionInfoType == CONSTRUCTOR_INFO;
174     }
175 
176     public boolean hasFieldInfo() {
177         return m_reflectionInfoType == FIELD_INFO;
178     }
179 
180     public boolean hasClassInfo() {
181         return m_reflectionInfoType == CLASS_INFO;
182     }
183 
184     public boolean hasReflectionInfo() {
185         return m_reflectionInfoType != INFO_NOT_AVAILABLE;
186     }
187 
188     public void setInCflowSubAST(final boolean inCflowAST) {
189         m_inCflowSubAST = inCflowAST;
190     }
191 
192     public boolean inCflowSubAST() {
193         return m_inCflowSubAST;
194     }
195 
196     public void setHasBeenVisitingCflow(final boolean hasBeenVisitingCflow) {
197         m_hasBeenVisitingCflow = hasBeenVisitingCflow;
198     }
199 
200     public boolean hasBeenVisitingCflow() {
201         return m_hasBeenVisitingCflow;
202     }
203 
204     public boolean getCflowEvaluation() {
205         return m_cflowEvaluation;
206     }
207 
208     public void setCflowEvaluation(boolean cflowEvaluation) {
209         m_cflowEvaluation = cflowEvaluation;
210     }
211 
212     public int getCurrentTargetArgsIndex() {
213         return m_currentTargetArgsIndex;
214     }
215 
216     public void setCurrentTargetArgsIndex(int argsIndex) {
217         this.m_currentTargetArgsIndex = argsIndex;
218     }
219 
220     public boolean equals(Object o) {
221         if (this == o) {
222             return true;
223         }
224         if (!(o instanceof ExpressionContext)) {
225             return false;
226         }
227         final ExpressionContext expressionContext = (ExpressionContext) o;
228         if (m_reflectionInfoType != expressionContext.m_reflectionInfoType) {
229             return false;
230         }
231         if (!m_matchingReflectionInfo.equals(expressionContext.m_matchingReflectionInfo)) {
232             return false;
233         }
234         if (!m_pointcutType.equals(expressionContext.m_pointcutType)) {
235             return false;
236         }
237         if ((m_withinReflectionInfo != null) ?
238             (!m_withinReflectionInfo
239                 .equals(expressionContext.m_withinReflectionInfo)) :
240             (expressionContext.m_withinReflectionInfo != null)) {
241             return false;
242         }
243         return true;
244     }
245 
246     public int hashCode() {
247         int result;
248         result = m_pointcutType.hashCode();
249         result = (29 * result) + m_matchingReflectionInfo.hashCode();
250         result = (29 * result) + ((m_withinReflectionInfo != null) ? m_withinReflectionInfo.hashCode() : 0);
251         result = (29 * result) + m_reflectionInfoType;
252         return result;
253     }
254 
255     public PointcutType getPointcutType() {
256         return m_pointcutType;
257     }
258 
259     public void resetRuntimeState() {
260         m_targetBoundedName = null;
261         m_thisBoundedName = null;
262         m_exprIndexToTargetIndex = new TObjectIntHashMap();
263         m_targetWithRuntimeCheck = false;
264     }
265 }