diff --git a/JavassistTest/data/constructor.txt b/JavassistTest/data/constructor.txt new file mode 100644 index 0000000..87e3cf9 --- /dev/null +++ b/JavassistTest/data/constructor.txt @@ -0,0 +1,16 @@ +Method constructor.Main,public static void constructor.Main.main(java.lang.String[]):1083498136:Line 1:2176964354155346:ThreadNo 1 +Class constructor.Main:1083498136:Line 2:ThreadNo 1 +Args:[Ljava.lang.String;:1839328839:Line 3:ThreadNo 1 +New constructor.B:0:Line 4:ThreadNo 1 +Method constructor.B,public constructor.B():0:Line 5:2176964354548369:ThreadNo 1 +Class constructor.B:0:Line 6:ThreadNo 1 +New constructor.A:0:Line 7:ThreadNo 1 +Method constructor.A,public constructor.A():0:Line 8:2176964354609042:ThreadNo 1 +Class constructor.A:0:Line 9:ThreadNo 1 +Return initialization(A()):constructor.B:572698508:572698508:Line 10:ThreadNo 1 +Return initialization(B()):constructor.B:572698508:572698508:Line 11:ThreadNo 1 +Method constructor.B,public constructor.A constructor.B.m(constructor.A):572698508:Line 12:2176964354770538:ThreadNo 1 +Class constructor.B:572698508:Line 13:ThreadNo 1 +Args:constructor.B:572698508:Line 14:ThreadNo 1 +Return execution(B.m(..)):constructor.B:572698508:572698508:Line 15:ThreadNo 1 +Return execution(Main.main(..)):void:0:0:Line 16:ThreadNo 1 \ No newline at end of file diff --git a/JavassistTest/src/constructor/A.java b/JavassistTest/src/constructor/A.java new file mode 100644 index 0000000..a162ed2 --- /dev/null +++ b/JavassistTest/src/constructor/A.java @@ -0,0 +1,5 @@ +package constructor; + +public abstract class A { + public abstract A m(A a); +} diff --git a/JavassistTest/src/constructor/B.java b/JavassistTest/src/constructor/B.java new file mode 100644 index 0000000..e1f6496 --- /dev/null +++ b/JavassistTest/src/constructor/B.java @@ -0,0 +1,10 @@ +package constructor; + +public class B extends A { + + @Override + public A m(A a) { + return a; + } + +} diff --git a/JavassistTest/src/constructor/Main.java b/JavassistTest/src/constructor/Main.java new file mode 100644 index 0000000..7b27b8d --- /dev/null +++ b/JavassistTest/src/constructor/Main.java @@ -0,0 +1,13 @@ +package constructor; + +public class Main { + + /** + * @param args + */ + public static void main(String[] args) { + B b = new B(); + A a = b.m(b); + } + +} diff --git a/JavassistTest/src/tracer/Tracer.java b/JavassistTest/src/tracer/Tracer.java index 04b2185..cf6d263 100644 --- a/JavassistTest/src/tracer/Tracer.java +++ b/JavassistTest/src/tracer/Tracer.java @@ -25,6 +25,7 @@ import javassist.expr.ExprEditor; import javassist.expr.FieldAccess; import javassist.expr.MethodCall; +import javassist.expr.NewExpr; public class Tracer { public static int lineNo = 1; @@ -34,7 +35,7 @@ private static final String CONCRETE_STANDARD_CLASSES = "java.util.Vector|java.util.ArrayList|java.util.Stack |java.util.HashMap|java.util.HashSet|java.util.Hashtable|java.util.LinkedList|java.lang.Thread"; public static void main(String[] args) { - String packageName = "worstCase"; // �w�肵���p�b�P�[�W�����̑S�N���X�ɃC���X�g�D�������e�[�V�������s�� + String packageName = "constructor"; // �w�肵���p�b�P�[�W�����̑S�N���X�ɃC���X�g�D�������e�[�V�������s�� ClassLoader loader = Thread.currentThread().getContextClassLoader(); URL resource = loader.getResource(packageName); File dir; @@ -62,7 +63,7 @@ CtClass cc; try { cc = cp.get(className); - for (final CtConstructor c : cc.getConstructors()) { + for (final CtConstructor c : cc.getDeclaredConstructors()) { methodInstrumentation(cc, c); } for (final CtMethod m : cc.getDeclaredMethods()) { @@ -125,8 +126,8 @@ } public void edit(MethodCall c) throws CannotCompileException { try { - if (c.getMethod().getDeclaringClass().getName().matches(STANDARD_CLASSES)) { - CtMethod m = c.getMethod(); + CtMethod m = c.getMethod(); + if (m.getDeclaringClass().getName().matches(STANDARD_CLASSES)) { Outputs out = generateOutputs(m.getDeclaringClass(), m, true); c.replace("{" + out.newOutput + out.methodOutput + out.classOutput + out.argsOutput + " $_ = $proceed($$); " + out.returnOutput + "}"); } @@ -134,10 +135,22 @@ e.printStackTrace(); } } + public void edit(NewExpr n) throws CannotCompileException { + try { + CtConstructor m = n.getConstructor(); + if (m.isEmpty() || m.getDeclaringClass().getName().matches(CONCRETE_STANDARD_CLASSES)) { + Outputs out = generateOutputs(m.getDeclaringClass(), m, true); + n.replace("{" + out.newOutput + out.methodOutput + out.classOutput + out.argsOutput + " $_ = $proceed($$); " + out.returnOutput + "}"); + } + } catch (NotFoundException e) { + e.printStackTrace(); + } + } public void edit(ConstructorCall c) throws CannotCompileException { try { - if (c.getConstructor().getDeclaringClass().getName().matches(CONCRETE_STANDARD_CLASSES)) { - CtConstructor m = c.getConstructor(); + CtConstructor m = c.getConstructor(); + if ((m.isEmpty() && !m.getDeclaringClass().getName().equals("java.lang.Object")) + || m.getDeclaringClass().getName().matches(CONCRETE_STANDARD_CLASSES)) { Outputs out = generateOutputs(m.getDeclaringClass(), m, true); c.replace("{" + out.newOutput + out.methodOutput + out.classOutput + out.argsOutput + " $_ = $proceed($$); " + out.returnOutput + "}"); } @@ -148,11 +161,13 @@ }); // ���\�b�h�p�̏o�͕��𐶐����� - Outputs outputs = generateOutputs(cc, m, false); - - // ���\�b�h�̎��s�O��ɏo�͕���}������ - m.insertBefore("{" + outputs.newOutput + outputs.methodOutput + outputs.classOutput + outputs.argsOutput + "}"); - m.insertAfter("{" + outputs.returnOutput + "}"); + if (!m.isEmpty()) { + Outputs outputs = generateOutputs(cc, m, false); + + // ���\�b�h�̎��s�O��ɏo�͕���}������ + m.insertBefore("{" + outputs.newOutput + outputs.methodOutput + outputs.classOutput + outputs.argsOutput + "}"); + m.insertAfter("{" + outputs.returnOutput + "}"); + } // CodeConverter conv = new CodeConverter(); // conv.replaceArrayAccess(cc, new @@ -268,6 +283,14 @@ // }); } + /** + * �g���[�X�o�͗p�̖��ߗ�𐶐����� + * @param cls �ΏۃN���X + * @param m �Ώۃ��\�b�h(�R���X�g���N�^) + * @param isCallerSideInstrumentation ���ߗ���Ăяo�����ɑ}�����邩�Ăяo����鑤�ɑ}�����邩? + * @return + * @throws NotFoundException + */ private static Outputs generateOutputs(CtClass cls, CtBehavior m, boolean isCallerSideInstrumentation) throws NotFoundException { Outputs outputs = new Outputs(); String declaredClassName = cls.getName(); @@ -353,12 +376,18 @@ shortName = m.getName().replace('$', '.') + "()"; // AspectJ�ł̓��\�b�h�V�O�j�`�����ł͖����N���X�̓h�b�g�ŋ�؂��� if (!isCallerSideInstrumentation) { // �Ăяo����ɖ��ߍ��ޏꍇ(�ʏ�) - outputs.returnOutput = "tracer.MyPrintStream.print(\"Return initialization(" + shortName + "):" + declaredClassName + ":\" + System.identityHashCode($0) + \":\");" + + outputs.returnOutput = "tracer.MyPrintStream.print(\"Return initialization(" + shortName + "):\" + $0.getClass().getName() + \":\" + System.identityHashCode($0) + \":\");" + "tracer.MyPrintStream.println(\"\" + System.identityHashCode($0) + " + LINE_AND_THREAD + ");"; } else { - // �ďo�����ɖ��ߍ��ޏꍇ(�W���N���X�̌ďo��) - outputs.returnOutput = "tracer.MyPrintStream.print(\"Return call(" + shortName + "):" + declaredClassName + ":\" + System.identityHashCode($_) + \":\");" + - "tracer.MyPrintStream.println(\"\" + System.identityHashCode($_) + " + LINE_AND_THREAD + ");"; + // �ďo�����ɖ��ߍ��ޏꍇ(�W���N���X�������̓f�t�H���g�R���X�g���N�^�̌ďo��) + outputs.returnOutput = "if ($_ != null) {" + + "tracer.MyPrintStream.print(\"Return initialization(" + shortName + "):\" + $_.getClass().getName() + \":\" + System.identityHashCode($_) + \":\");" + + "tracer.MyPrintStream.println(\"\" + System.identityHashCode($_) + " + LINE_AND_THREAD + ");" + + "} else {" + + // �e�R���X�g���N�^�ďo���̏ꍇ(�߂�l�͂Ȃ�) + "tracer.MyPrintStream.print(\"Return initialization(" + shortName + "):\" + $0.getClass().getName() + \":\" + System.identityHashCode($0) + \":\");" + + "tracer.MyPrintStream.println(\"\" + System.identityHashCode($0) + " + LINE_AND_THREAD + ");" + + "}"; } } else { // �ʏ�̃��\�b�h�̏ꍇ