[jboss-cvs] JBossAS SVN: r60289 - in projects/aop/trunk/aop/src/main/org/jboss/aop: instrument and 1 other directories.
jboss-cvs-commits at lists.jboss.org
jboss-cvs-commits at lists.jboss.org
Mon Feb 5 08:55:08 EST 2007
Author: flavia.rainone at jboss.com
Date: 2007-02-05 08:55:07 -0500 (Mon, 05 Feb 2007)
New Revision: 60289
Modified:
projects/aop/trunk/aop/src/main/org/jboss/aop/advice/PerVmAdvice.java
projects/aop/trunk/aop/src/main/org/jboss/aop/instrument/NonOptimizedConstructorExecutionTransformer.java
projects/aop/trunk/aop/src/main/org/jboss/aop/instrument/NonOptimizedMethodExecutionTransformer.java
projects/aop/trunk/aop/src/main/org/jboss/aop/util/ReflectToJavassist.java
Log:
[JBAOP-354] Bug solved on trunk
Modified: projects/aop/trunk/aop/src/main/org/jboss/aop/advice/PerVmAdvice.java
===================================================================
--- projects/aop/trunk/aop/src/main/org/jboss/aop/advice/PerVmAdvice.java 2007-02-05 13:37:52 UTC (rev 60288)
+++ projects/aop/trunk/aop/src/main/org/jboss/aop/advice/PerVmAdvice.java 2007-02-05 13:55:07 UTC (rev 60289)
@@ -21,22 +21,26 @@
*/
package org.jboss.aop.advice;
+import java.lang.reflect.Field;
+import java.lang.reflect.Method;
+import java.util.ArrayList;
+
+import javassist.CannotCompileException;
import javassist.ClassPool;
import javassist.CtClass;
import javassist.CtField;
import javassist.CtMethod;
import javassist.CtNewMethod;
+
import org.jboss.aop.AspectManager;
import org.jboss.aop.instrument.OptimizedMethodInvocations;
import org.jboss.aop.instrument.TransformerCommon;
import org.jboss.aop.joinpoint.Invocation;
import org.jboss.aop.joinpoint.Joinpoint;
+import org.jboss.aop.joinpoint.MethodInvocation;
import org.jboss.aop.joinpoint.MethodJoinpoint;
+import org.jboss.aop.util.ReflectToJavassist;
-import java.lang.reflect.Field;
-import java.lang.reflect.Method;
-import java.util.ArrayList;
-
/**
* Comment
*
@@ -109,7 +113,7 @@
if (methods[i].getName().equals(adviceName)) matches.add(methods[i]);
}
- // todo: Need to have checks on whether the advice is overloaded and it is an argument type interception
+ // TODO Need to have checks on whether the advice is overloaded and it is an argument type interception
if (matches.size() == 1)
{
Method method = (Method) matches.get(0);
@@ -192,10 +196,8 @@
public static Interceptor generateArgsInterceptor(Object aspect, Method advice, Joinpoint joinpoint) throws Exception
{
- Method method = ((MethodJoinpoint) joinpoint).getMethod();
- String optimized = OptimizedMethodInvocations.getOptimizedInvocationClassName(method);
+
-
ClassPool pool = AspectManager.instance().findClassPool(aspect.getClass().getClassLoader());
CtClass clazz = TransformerCommon.makeClass(pool, "org.jboss.aop.advice." + aspect.getClass().getName() + counter++);
@@ -219,17 +221,44 @@
clazz.addMethod(getName);
// invoke
- String invokeBody = null;
+ Method method = ((MethodJoinpoint) joinpoint).getMethod();
+ String invocationType = null;
+ if (AspectManager.optimize)
+ {
+ invocationType = OptimizedMethodInvocations.getOptimizedInvocationClassName(method);
+ }
+ else
+ {
+ invocationType = MethodInvocation.class.getName();
+ }
+
+ StringBuffer invokeBody = new StringBuffer("public Object invoke(org.jboss.aop.joinpoint.Invocation invocation) throws java.lang.Throwable ");
+ invokeBody.append("{ ").append(invocationType).append(" typedInvocation = (");
+ invokeBody.append(invocationType).append(")invocation; ");
+ if (!AspectManager.optimize)
+ {
+ invokeBody.append(" Object[] arguments = typedInvocation.getArguments();");
+ }
if (advice.getParameterTypes().length > 0 &&
Invocation.class.isAssignableFrom(advice.getParameterTypes()[0]))
{
- invokeBody = getInvocationBody(optimized, advice, method);
+ fillInvocationBody(invokeBody, advice, method);
}
else
{
- invokeBody = getThreadStackBody(optimized, advice, method);
+ fillThreadStackBody(invokeBody, advice, method);
}
- CtMethod invoke = CtNewMethod.make(invokeBody, clazz);
+ invokeBody.append('}');
+ CtMethod invoke = null;
+ try
+ {
+ invoke = CtNewMethod.make(invokeBody.toString(), clazz);
+ }
+ catch(CannotCompileException e)
+ {
+ System.out.println(invokeBody);
+ throw e;
+ }
invoke.setModifiers(javassist.Modifier.PUBLIC);
clazz.addMethod(invoke);
Class iclass = TransformerCommon.toClass(clazz);
@@ -240,101 +269,89 @@
return rtn;
}
- private static String getThreadStackBody(String optimized, Method advice, Method method)
+ private static void fillThreadStackBody(StringBuffer invokeBody, Method advice, Method method) throws Exception
{
- String invokeBody =
- "public Object invoke(org.jboss.aop.joinpoint.Invocation invocation) throws java.lang.Throwable " +
- "{ " +
- " " + optimized + " optimized = (" + optimized + ")invocation; " +
- " org.jboss.aop.joinpoint.CurrentInvocation.push(invocation); " +
- " try {";
- invokeBody += "return ($w)aspectField." + advice.getName() + "(";
- Class[] adviceParams = advice.getParameterTypes();
- Class[] params = method.getParameterTypes();
- boolean first = true;
+ invokeBody.append(" org.jboss.aop.joinpoint.CurrentInvocation.push(invocation); ");
+ invokeBody.append(" try {");
+ invokeBody.append("return ($w)aspectField.").append(advice.getName());
+ invokeBody.append("(");
+ appendParamList(invokeBody, 0, advice.getParameterTypes(), method.getParameterTypes());
+ invokeBody.append(");");
+ invokeBody.append(" } finally { org.jboss.aop.joinpoint.CurrentInvocation.pop(); }");
+ }
+
+ private static void fillInvocationBody(StringBuffer invokeBody, Method advice, Method method)
+ {
+ invokeBody.append(" return ($w)aspectField.").append(advice.getName());
+ invokeBody.append("(typedInvocation, ");
+ appendParamList(invokeBody, 1, advice.getParameterTypes(), method.getParameterTypes());
+ invokeBody.append(");");
+ }
+
+ /**
+ * Appends the joinpoint parameter list to <code>code</code>.
+ *
+ * @param code buffer to where generated code is appended
+ * @param offset indicates from which advice parameter index are the
+ * joinpoint parameters. All advice parameters that
+ * come before the <code>offset</code> stand for other
+ * values, that are not joinpoint parameters.
+ * @param adviceParams list of advice parameter types
+ * @param joinPointParams list of joinpoint parameter types
+ */
+ private static void appendParamList(StringBuffer code, int offset, Class adviceParams[], Class[] joinPointParams)
+ {
if (adviceParams.length > 0)
{
- // TODO review this with Kabir
- /*int adviceParam = 0;
- for (int i = 0; i < params.length && adviceParam < adviceParams.length; i++)
+ int [] paramIndexes = new int[adviceParams.length];
+ boolean[] assignedParams = new boolean[joinPointParams.length];
+ for (int i = offset; i < adviceParams.length; i++)
{
- if (adviceParams[adviceParam].equals(params[i]))
- {
- adviceParam++;
- if (first)
- {
- first = false;
- }
- else
- {
- invokeBody += ", ";
- }
- invokeBody += "optimized.arg" + i;
- }
- }*/
- boolean[] assignedParams = new boolean[params.length];
- for (int i = 0; i < adviceParams.length; i++)
- {
int j;
- for (j = 0; j < params.length; j++)
+ for (j = 0; j < joinPointParams.length; j++)
{
- if (adviceParams[i].equals(params[j]) && !assignedParams[j])
+ if (adviceParams[i].equals(joinPointParams[j]) && !assignedParams[j])
{
break;
}
}
- if (j == params.length)
+ // if didn't find the same type, look for supertypes
+ if (j == joinPointParams.length)
{
- for (j = 0; j < params.length; j++)
+ for (j = 0; j < joinPointParams.length; j++)
{
- if (adviceParams[i].isAssignableFrom(params[j]) && !assignedParams[j])
+ if (adviceParams[i].isAssignableFrom(joinPointParams[j]) && !assignedParams[j])
break;
}
- if (j == params.length)
+ // didn't find super types either
+ if (j == joinPointParams.length)
throw new RuntimeException();
}
assignedParams[j] = true;
- if (i != 0)
+ paramIndexes[i] = j;
+ }
+ if (AspectManager.optimize)
+ {
+ code.append("typedInvocation.arg").append(paramIndexes[offset]);
+ for (int i = offset + 1; i < paramIndexes.length; i++)
{
- invokeBody += ", ";
+ code.append(", typedInvocation.arg");
+ code.append(paramIndexes[i]);
}
- invokeBody += "optimized.arg" + j;
-
}
- }
- invokeBody += "); ";
- invokeBody +=
- " } finally { org.jboss.aop.joinpoint.CurrentInvocation.pop(); }";
- invokeBody +=
- "}";
- return invokeBody;
- }
-
- private static String getInvocationBody(String optimized, Method advice, Method method)
- {
- String invokeBody =
- "public Object invoke(org.jboss.aop.joinpoint.Invocation invocation) throws java.lang.Throwable " +
- "{ " +
- " " + optimized + " optimized = (" + optimized + ")invocation; " +
- " return ($w)aspectField." + advice.getName() + "(optimized";
- Class[] adviceParams = advice.getParameterTypes();
- Class[] params = method.getParameterTypes();
- if (adviceParams.length > 0)
- {
- int adviceParam = 1;
- for (int i = 0; i < params.length && adviceParam < adviceParams.length; i++)
+ else
{
- if (adviceParams[adviceParam].equals(params[i]))
+ code.append(ReflectToJavassist.castInvocationValueToTypeString(
+ adviceParams[offset],
+ "arguments[" + paramIndexes[offset] + "]"));
+ for (int i = offset + 1; i < paramIndexes.length; i++)
{
- adviceParam++;
- invokeBody += ", ";
- invokeBody += "optimized.arg" + i;
+ code.append(", ");
+ code.append(ReflectToJavassist.castInvocationValueToTypeString(
+ adviceParams[i],
+ "arguments[" + paramIndexes[i] + "]"));
}
}
}
- invokeBody += "); ";
- invokeBody +=
- "}";
- return invokeBody;
- }
-}
+ }
+}
\ No newline at end of file
Modified: projects/aop/trunk/aop/src/main/org/jboss/aop/instrument/NonOptimizedConstructorExecutionTransformer.java
===================================================================
--- projects/aop/trunk/aop/src/main/org/jboss/aop/instrument/NonOptimizedConstructorExecutionTransformer.java 2007-02-05 13:37:52 UTC (rev 60288)
+++ projects/aop/trunk/aop/src/main/org/jboss/aop/instrument/NonOptimizedConstructorExecutionTransformer.java 2007-02-05 13:55:07 UTC (rev 60289)
@@ -47,12 +47,6 @@
protected void createWrapper(ConstructorTransformation trans) throws CannotCompileException, NotFoundException
{
String code = null;
- String args = "(Object[])null";
- if (trans.getConstructor().getParameterTypes().length > 0)
- {
- args = "$args";
- }
-
String infoName = getConstructorInfoFieldName(trans.getSimpleName(), trans.getIndex());
code =
@@ -61,7 +55,7 @@
" org.jboss.aop.advice.Interceptor[] interceptors = info.getInterceptors(); " +
" if (interceptors != (org.jboss.aop.advice.Interceptor[])null) " +
" { " +
- " return ($r)" + Instrumentor.HELPER_FIELD_NAME + ".invokeNew(" + args + ", (int)" + (trans.getIndex()) + "); " +
+ " return ($r)" + Instrumentor.HELPER_FIELD_NAME + ".invokeNew($args, (int)" + (trans.getIndex()) + "); " +
" } " +
" return new " + trans.getClazz().getName() + "($$); " +
"}";
Modified: projects/aop/trunk/aop/src/main/org/jboss/aop/instrument/NonOptimizedMethodExecutionTransformer.java
===================================================================
--- projects/aop/trunk/aop/src/main/org/jboss/aop/instrument/NonOptimizedMethodExecutionTransformer.java 2007-02-05 13:37:52 UTC (rev 60288)
+++ projects/aop/trunk/aop/src/main/org/jboss/aop/instrument/NonOptimizedMethodExecutionTransformer.java 2007-02-05 13:55:07 UTC (rev 60289)
@@ -86,8 +86,6 @@
//wmethod = method;
boolean isStatic = Modifier.isStatic(trans.getMethod().getModifiers());
String code = null;
- String args = "null";
- if (trans.getMethod().getParameterTypes().length > 0) args = "$args";
if (!isStatic)
{
code =
@@ -96,7 +94,7 @@
" org.jboss.aop.ClassInstanceAdvisor instAdv = (org.jboss.aop.ClassInstanceAdvisor)_getInstanceAdvisor();" +
" if (info.getInterceptors() != (Object[])null || (instAdv != null && instAdv.hasInstanceAspects)) " +
" { " +
- " Object[] ags = " + args + "; " +
+ " Object[] ags = $args; " +
" " + getAopReturnStr(trans.getMethod()) + Instrumentor.HELPER_FIELD_NAME + ".invokeMethod(instAdv, this, " + trans.getHash() + "L, ags, info); " +
" } " +
" else " +
@@ -113,7 +111,7 @@
" if (info.getInterceptors() != (Object[])null) " +
" { " +
" org.jboss.aop.ClassInstanceAdvisor ia = null; " +
- " Object[] ags = " + args + "; " +
+ " Object[] ags = $args; " +
" Object target = null; " +
" " + getAopReturnStr(trans.getMethod()) + Instrumentor.HELPER_FIELD_NAME + ".invokeMethod(ia, target, " + trans.getHash() + "L, ags, info); " +
" } " +
Modified: projects/aop/trunk/aop/src/main/org/jboss/aop/util/ReflectToJavassist.java
===================================================================
--- projects/aop/trunk/aop/src/main/org/jboss/aop/util/ReflectToJavassist.java 2007-02-05 13:37:52 UTC (rev 60288)
+++ projects/aop/trunk/aop/src/main/org/jboss/aop/util/ReflectToJavassist.java 2007-02-05 13:55:07 UTC (rev 60289)
@@ -52,7 +52,6 @@
public static CtField fieldToJavassist(Field field) throws NotFoundException
{
- Class clazz = field.getDeclaringClass();
return classToJavassist(field.getDeclaringClass()).getField(field.getName());
}
public static CtConstructor constructorToJavassist(Constructor con) throws NotFoundException
@@ -146,5 +145,66 @@
//throw new Exception("failed to find method: " + method.toString() + " state: " + state);
return null;
}
+
+ /**
+ * Casts a value to the type required.
+ *
+ * @param type type to use on casting
+ * @param valueName name of the value as recognized on the generated code.
+ * Compiler considers this expression as being of type <code>
+ * java.lang.Object</code>
+ * @return a string that casts <code>valueName</code> to <code>type
+ * </code> (if <code>type</code> is primitive, the value will
+ * be unwrapped).
+ */
+ public static String castInvocationValueToTypeString(Class type, String valueName)
+ {
+ // TODO replace this method by T Class.cast(valueName) once javassist enables support to generics
+ String cast = null;
+ if (type.isPrimitive())
+ {
+ if (type.equals(boolean.class))
+ {
+ cast = "((Boolean)" + valueName +").booleanValue()";
+ }
+ else if (type.equals(byte.class))
+ {
+ cast = "((Byte)" + valueName +").byteValue()";
+ }
+ else if (type.equals(char.class))
+ {
+ cast = "((Character)" + valueName +").charValue()";
+ }
+ else if (type.equals(double.class))
+ {
+ cast = "((Double)" + valueName +").doubleValue()";
+ }
+ else if (type.equals(float.class))
+ {
+ cast = "((Float)" + valueName +").floatValue()";
+ }
+ else if (type.equals(int.class))
+ {
+ cast = "((Integer)" + valueName +").intValue()";
+ }
+ else if (type.equals(long.class))
+ {
+ cast = "((Long)" + valueName +").longValue()";
+ }
+ else if (type.equals(short.class))
+ {
+ cast = "((Short)" + valueName +").shortValue()";
+ }
+ }
+ else if (type.isArray())
+ {
+ cast = "(" + type.getName() + ")" + valueName;
+ }
+ else
+ {
+ cast = "(" + type.getName() + ")" + valueName;
+ }
-}
+ return cast;
+ }
+}
\ No newline at end of file
More information about the jboss-cvs-commits
mailing list