diff options
author | aclement <aclement> | 2005-09-20 16:35:56 +0000 |
---|---|---|
committer | aclement <aclement> | 2005-09-20 16:35:56 +0000 |
commit | fc2d08e2ae9d03fb377bd0ed0bd56983af4687a5 (patch) | |
tree | 04d71add3ea39deb384f3dbaef87e5447462a650 | |
parent | 2a9b5d8d87d841a40b690f3a6c77e02828768f7a (diff) | |
download | aspectj-fc2d08e2ae9d03fb377bd0ed0bd56983af4687a5.tar.gz aspectj-fc2d08e2ae9d03fb377bd0ed0bd56983af4687a5.zip |
Fix for pr109728: generates correct aroundBody methods for field-get JPs that are affected when compiling at 1.4/1.5 level.
-rw-r--r-- | weaver/src/org/aspectj/weaver/bcel/BcelClassWeaver.java | 9 | ||||
-rw-r--r-- | weaver/src/org/aspectj/weaver/bcel/BcelShadow.java | 23 |
2 files changed, 30 insertions, 2 deletions
diff --git a/weaver/src/org/aspectj/weaver/bcel/BcelClassWeaver.java b/weaver/src/org/aspectj/weaver/bcel/BcelClassWeaver.java index f50cc7260..6c17184b7 100644 --- a/weaver/src/org/aspectj/weaver/bcel/BcelClassWeaver.java +++ b/weaver/src/org/aspectj/weaver/bcel/BcelClassWeaver.java @@ -1603,7 +1603,7 @@ class BcelClassWeaver implements IClassWeaver { private void matchGetInstruction(LazyMethodGen mg, InstructionHandle ih, BcelShadow enclosingShadow, List shadowAccumulator) { FieldInstruction fi = (FieldInstruction) ih.getInstruction(); Member field = BcelWorld.makeFieldJoinPointSignature(clazz, fi); - + // synthetic fields are never join points if (field.getName().startsWith(NameMangler.PREFIX)) return; @@ -1615,7 +1615,12 @@ class BcelClassWeaver implements IClassWeaver { // sets of synthetics aren't join points in 1.1 return; } else { - match(BcelShadow.makeFieldGet(world, resolvedField, mg, ih, enclosingShadow), shadowAccumulator); + BcelShadow bs = BcelShadow.makeFieldGet(world,resolvedField,mg,ih,enclosingShadow); + String cname = fi.getClassName(cpg); + if (!resolvedField.getDeclaringType().getName().equals(cname)) { + bs.setActualTargetType(cname); + } + match(bs, shadowAccumulator); } } diff --git a/weaver/src/org/aspectj/weaver/bcel/BcelShadow.java b/weaver/src/org/aspectj/weaver/bcel/BcelShadow.java index 1dc4c52e8..60f47f0aa 100644 --- a/weaver/src/org/aspectj/weaver/bcel/BcelShadow.java +++ b/weaver/src/org/aspectj/weaver/bcel/BcelShadow.java @@ -133,6 +133,10 @@ public class BcelShadow extends Shadow { private final BcelWorld world; private final LazyMethodGen enclosingMethod; private boolean fallsThrough; //XXX not used anymore + + // Some instructions have a target type that will vary + // from the signature (pr109728) (1.4 declaring type issue) + private String actualInstructionTargetType; // ---- initialization @@ -1221,6 +1225,8 @@ public class BcelShadow extends Shadow { * are true, it has a sneak peek at the code before the call to see what is on the stack. */ public UnresolvedType ensureTargetTypeIsCorrect(UnresolvedType tx) { + + if (tx.equals(ResolvedType.OBJECT) && getKind() == MethodCall && getSignature().getReturnType().equals(ResolvedType.OBJECT) && getSignature().getArity()==0 && @@ -2938,6 +2944,15 @@ public class BcelShadow extends Shadow { if (targetVar != null && targetVar != thisVar) { UnresolvedType targetType = getTargetType(); targetType = ensureTargetTypeIsCorrect(targetType); + // see pr109728 - this fixes the case when the declaring class is sometype 'X' but the getfield + // in the bytecode refers to a subtype of 'X'. This makes sure we use the type originally + // mentioned in the fieldget instruction as the method parameter and *not* the type upon which the + // field is declared because when the instructions are extracted into the new around body, + // they will still refer to the subtype. + if (getKind()==FieldGet && getActualTargetType()!=null && + !getActualTargetType().equals(targetType.getName())) { + targetType = UnresolvedType.forName(getActualTargetType()).resolve(world); + } ResolvedMember resolvedMember = getSignature().resolve(world); if (resolvedMember != null && Modifier.isProtected(resolvedMember.getModifiers()) && @@ -3072,4 +3087,12 @@ public class BcelShadow extends Shadow { public boolean isFallsThrough() { return !terminatesWithReturn(); //fallsThrough; } + + public void setActualTargetType(String className) { + this.actualInstructionTargetType = className; + } + + public String getActualTargetType() { + return actualInstructionTargetType; + } } |