diff options
author | aclement <aclement> | 2006-02-21 10:49:15 +0000 |
---|---|---|
committer | aclement <aclement> | 2006-02-21 10:49:15 +0000 |
commit | 3b4d09438dd366cf4bb90c9d19cc8134853a347d (patch) | |
tree | 7c3dc1ed2130409eeb4b1ffb966a0d9f524126f0 | |
parent | bf5612533611857b24a90ba8ef19fe4023329b6e (diff) | |
download | aspectj-3b4d09438dd366cf4bb90c9d19cc8134853a347d.tar.gz aspectj-3b4d09438dd366cf4bb90c9d19cc8134853a347d.zip |
optimization: use tags not gens. improves memory (create less garbage), faster (dont need to transform the garbage): see pr128650, optimization #6.
-rw-r--r-- | bcel-builder/src/org/aspectj/apache/bcel/generic/LineNumberTag.java (renamed from weaver/src/org/aspectj/weaver/bcel/LineNumberTag.java) | 7 | ||||
-rw-r--r-- | bcel-builder/src/org/aspectj/apache/bcel/generic/LocalVariableTag.java (renamed from weaver/src/org/aspectj/weaver/bcel/LocalVariableTag.java) | 46 | ||||
-rw-r--r-- | bcel-builder/src/org/aspectj/apache/bcel/generic/MethodGen.java | 85 | ||||
-rw-r--r-- | bcel-builder/src/org/aspectj/apache/bcel/generic/Tag.java (renamed from weaver/src/org/aspectj/weaver/bcel/Tag.java) | 9 | ||||
-rw-r--r-- | lib/bcel/bcel-src.zip | bin | 872478 -> 875449 bytes | |||
-rw-r--r-- | lib/bcel/bcel.jar | bin | 595683 -> 598986 bytes | |||
-rw-r--r-- | weaver/src/org/aspectj/weaver/bcel/BcelClassWeaver.java | 3 | ||||
-rw-r--r-- | weaver/src/org/aspectj/weaver/bcel/BcelShadow.java | 16 | ||||
-rw-r--r-- | weaver/src/org/aspectj/weaver/bcel/LazyMethodGen.java | 90 | ||||
-rw-r--r-- | weaver/src/org/aspectj/weaver/bcel/Range.java | 6 | ||||
-rw-r--r-- | weaver/src/org/aspectj/weaver/bcel/ShadowRange.java | 1 | ||||
-rw-r--r-- | weaver/src/org/aspectj/weaver/bcel/Utility.java | 11 |
12 files changed, 204 insertions, 70 deletions
diff --git a/weaver/src/org/aspectj/weaver/bcel/LineNumberTag.java b/bcel-builder/src/org/aspectj/apache/bcel/generic/LineNumberTag.java index 9dc5b8a15..b8136de35 100644 --- a/weaver/src/org/aspectj/weaver/bcel/LineNumberTag.java +++ b/bcel-builder/src/org/aspectj/apache/bcel/generic/LineNumberTag.java @@ -1,5 +1,5 @@ /* ******************************************************************* - * Copyright (c) 2002 Palo Alto Research Center, Incorporated (PARC). + * Copyright (c) 2002 Contributors * All rights reserved. * This program and the accompanying materials are made available * under the terms of the Common Public License v1.0 @@ -7,11 +7,12 @@ * http://www.eclipse.org/legal/cpl-v10.html * * Contributors: - * PARC initial implementation + * PARC initial implementation + * Andy Clement pushed down into bcel module * ******************************************************************/ -package org.aspectj.weaver.bcel; +package org.aspectj.apache.bcel.generic; /** we don't actually target instructions, but instructions target us. */ public class LineNumberTag extends Tag { diff --git a/weaver/src/org/aspectj/weaver/bcel/LocalVariableTag.java b/bcel-builder/src/org/aspectj/apache/bcel/generic/LocalVariableTag.java index 14bb30acf..53d43c462 100644 --- a/weaver/src/org/aspectj/weaver/bcel/LocalVariableTag.java +++ b/bcel-builder/src/org/aspectj/apache/bcel/generic/LocalVariableTag.java @@ -1,5 +1,5 @@ /* ******************************************************************* - * Copyright (c) 2002 Palo Alto Research Center, Incorporated (PARC). + * Copyright (c) 2002 Contributors * All rights reserved. * This program and the accompanying materials are made available * under the terms of the Common Public License v1.0 @@ -8,15 +8,15 @@ * * Contributors: * PARC initial implementation + * Andy Clement pushed down into bcel module * ******************************************************************/ -package org.aspectj.weaver.bcel; - -import org.aspectj.weaver.UnresolvedType; +package org.aspectj.apache.bcel.generic; public final class LocalVariableTag extends Tag { - private final UnresolvedType type; + private Type type; // not always known, in which case signature has to be used + private final String signature; private final String name; private int slot; private final int startPos; @@ -24,22 +24,26 @@ public final class LocalVariableTag extends Tag { // AMC - pr101047, two local vars with the same name can share the same slot, but must in that case // have different start positions. - public LocalVariableTag(UnresolvedType type, String name, int slot, int startPosition) { - this.type = type; + public LocalVariableTag(String sig, String name, int slot, int startPosition) { + this.signature = sig; this.name = name; this.slot = slot; this.startPos = startPosition; } - - public String getName() { - return name; - } - public int getSlot() { - return slot; - } - public UnresolvedType getType() { - return type; + + public LocalVariableTag(Type t,String sig, String name, int slot, int startPosition) { + this.type = t; + this.signature = sig; + this.name = name; + this.slot = slot; + this.startPos = startPosition; } + + + public String getName() {return name;} + public int getSlot() {return slot;} + public String getType() {return signature;} + public Type getRealType() {return type;} public void updateSlot(int newSlot) { this.slot = newSlot; @@ -51,18 +55,20 @@ public final class LocalVariableTag extends Tag { // ---- from Object public String toString() { - return "local " + slot + ": " + type + " " + name; + return "local " + slot + ": " + signature + " " + name; } + public boolean equals(Object other) { if (!(other instanceof LocalVariableTag)) return false; LocalVariableTag o = (LocalVariableTag)other; - return o.type.equals(type) && o.name.equals(name) && o.slot == slot && o.startPos == startPos; + return o.slot == slot && o.startPos == startPos && o.signature.equals(signature) && o.name.equals(name); } - private volatile int hashCode = 0; + + private int hashCode = 0; public int hashCode() { if (hashCode == 0) { int ret = 17; - ret = 37*ret + type.hashCode(); + ret = 37*ret + signature.hashCode(); ret = 37*ret + name.hashCode(); ret = 37*ret + slot; ret = 37*ret + startPos; diff --git a/bcel-builder/src/org/aspectj/apache/bcel/generic/MethodGen.java b/bcel-builder/src/org/aspectj/apache/bcel/generic/MethodGen.java index 96b2b0f90..e414b94e7 100644 --- a/bcel-builder/src/org/aspectj/apache/bcel/generic/MethodGen.java +++ b/bcel-builder/src/org/aspectj/apache/bcel/generic/MethodGen.java @@ -86,7 +86,7 @@ import org.aspectj.apache.bcel.generic.annotation.AnnotationGen; * use the `removeNOPs' method to get rid off them. * The resulting method object can be obtained via the `getMethod()' method. * - * @version $Id: MethodGen.java,v 1.6 2006/02/14 13:32:07 aclement Exp $ + * @version $Id: MethodGen.java,v 1.7 2006/02/21 10:49:15 aclement Exp $ * @author <A HREF="mailto:markus.dahm@berlin.de">M. Dahm</A> * @author <A HREF="http://www.vmeng.com/beard">Patrick C. Beard</A> [setMaxStack()] * @see InstructionList @@ -100,6 +100,7 @@ public class MethodGen extends FieldGenOrMethodGen { private int max_stack; private InstructionList il; private boolean strip_attributes; + private int highestLineNumber = 0; private ArrayList variable_vec = new ArrayList(); private ArrayList line_number_vec = new ArrayList(); @@ -188,6 +189,8 @@ public class MethodGen extends FieldGenOrMethodGen { } } } + + public int getHighestlinenumber() { return highestLineNumber; } /** * Instantiate from existing method. @@ -198,6 +201,10 @@ public class MethodGen extends FieldGenOrMethodGen { */ public MethodGen(Method m, String class_name, ConstantPoolGen cp) { + this(m,class_name,cp,false); + } + + public MethodGen(Method m, String class_name, ConstantPoolGen cp,boolean useTags) { this( m.getAccessFlags(), @@ -261,29 +268,63 @@ public class MethodGen extends FieldGenOrMethodGen { if (a instanceof LineNumberTable) { LineNumber[] ln = ((LineNumberTable) a).getLineNumberTable(); - - for (int k = 0; k < ln.length; k++) { - LineNumber l = ln[k]; - addLineNumber(il.findHandle(l.getStartPC(),arrayOfInstructions), - l.getLineNumber()); + if (useTags) { + // abracadabra, lets create tags rather than linenumbergens. + for (int k = 0; k < ln.length; k++) { + LineNumber l = ln[k]; + int lnum = l.getLineNumber(); + if (lnum>highestLineNumber) highestLineNumber=lnum; + LineNumberTag lt = new LineNumberTag(lnum); + il.findHandle(l.getStartPC(),arrayOfInstructions).addTargeter(lt); + } + } else { + for (int k = 0; k < ln.length; k++) { + LineNumber l = ln[k]; + addLineNumber(il.findHandle(l.getStartPC(),arrayOfInstructions), + l.getLineNumber()); + } } } else if (a instanceof LocalVariableTable) { - LocalVariable[] lv = ((LocalVariableTable) a).getLocalVariableTable(); - - removeLocalVariables(); - - for (int k = 0; k < lv.length; k++) { - LocalVariable l = lv[k]; - InstructionHandle start = il.findHandle(l.getStartPC(), arrayOfInstructions); - InstructionHandle end = il.findHandle(l.getStartPC() + l.getLength(), arrayOfInstructions); - // AMC, this actually gives us the first instruction AFTER the range, - // so move back one... (findHandle can't cope with mid-instruction indices) - if (end != null) end = end.getPrev(); - // Repair malformed handles - if (null == start) start = il.getStart(); - if (null == end) end = il.getEnd(); - - addLocalVariable(l.getName(), Type.getType(l.getSignature()), l.getIndex(), start, end); + + // Lets have a go at creating Tags directly + if (useTags) { + LocalVariable[] lv = ((LocalVariableTable) a).getLocalVariableTable(); + + for (int k = 0; k < lv.length; k++) { + LocalVariable l = lv[k]; + Type t = Type.getType(l.getSignature()); + LocalVariableTag lvt = new LocalVariableTag(t,l.getSignature(),l.getName(),l.getIndex(),l.getStartPC()); + InstructionHandle start = il.findHandle(l.getStartPC(), arrayOfInstructions); + byte b = t.getType(); + if (b!= Constants.T_ADDRESS) { + int increment = t.getSize(); + if (l.getIndex()+increment>max_locals) max_locals = l.getIndex()+increment; + } + int end = l.getStartPC()+l.getLength(); + do { + start.addTargeter(lvt); + start = start.getNext(); + } while (start!=null && start.getPosition()<end); + } + } else { + + LocalVariable[] lv = ((LocalVariableTable) a).getLocalVariableTable(); + + removeLocalVariables(); + + for (int k = 0; k < lv.length; k++) { + LocalVariable l = lv[k]; + InstructionHandle start = il.findHandle(l.getStartPC(), arrayOfInstructions); + InstructionHandle end = il.findHandle(l.getStartPC() + l.getLength(), arrayOfInstructions); + // AMC, this actually gives us the first instruction AFTER the range, + // so move back one... (findHandle can't cope with mid-instruction indices) + if (end != null) end = end.getPrev(); + // Repair malformed handles + if (null == start) start = il.getStart(); + if (null == end) end = il.getEnd(); + + addLocalVariable(l.getName(), Type.getType(l.getSignature()), l.getIndex(), start, end); + } } } else addCodeAttribute(a); } diff --git a/weaver/src/org/aspectj/weaver/bcel/Tag.java b/bcel-builder/src/org/aspectj/apache/bcel/generic/Tag.java index 427fc3f94..2cb5f9ddc 100644 --- a/weaver/src/org/aspectj/weaver/bcel/Tag.java +++ b/bcel-builder/src/org/aspectj/apache/bcel/generic/Tag.java @@ -1,5 +1,5 @@ /* ******************************************************************* - * Copyright (c) 2002 Palo Alto Research Center, Incorporated (PARC). + * Copyright (c) 2002 Contributors * All rights reserved. * This program and the accompanying materials are made available * under the terms of the Common Public License v1.0 @@ -8,16 +8,15 @@ * * Contributors: * PARC initial implementation + * Andy Clement pushed down into bcel module * ******************************************************************/ -package org.aspectj.weaver.bcel; +package org.aspectj.apache.bcel.generic; -import org.aspectj.apache.bcel.generic.InstructionHandle; -import org.aspectj.apache.bcel.generic.InstructionTargeter; /** A tag is an instruction-targeter that doesn't bother remembering its target(s) */ -abstract class Tag implements InstructionTargeter, Cloneable { +public abstract class Tag implements InstructionTargeter, Cloneable { public Tag() { } diff --git a/lib/bcel/bcel-src.zip b/lib/bcel/bcel-src.zip Binary files differindex 162657a4e..1376af6d7 100644 --- a/lib/bcel/bcel-src.zip +++ b/lib/bcel/bcel-src.zip diff --git a/lib/bcel/bcel.jar b/lib/bcel/bcel.jar Binary files differindex 709d6194d..87bf5b75b 100644 --- a/lib/bcel/bcel.jar +++ b/lib/bcel/bcel.jar diff --git a/weaver/src/org/aspectj/weaver/bcel/BcelClassWeaver.java b/weaver/src/org/aspectj/weaver/bcel/BcelClassWeaver.java index d080ec18f..527e7369b 100644 --- a/weaver/src/org/aspectj/weaver/bcel/BcelClassWeaver.java +++ b/weaver/src/org/aspectj/weaver/bcel/BcelClassWeaver.java @@ -55,6 +55,7 @@ import org.aspectj.apache.bcel.generic.PUTSTATIC; import org.aspectj.apache.bcel.generic.RET; import org.aspectj.apache.bcel.generic.ReturnInstruction; import org.aspectj.apache.bcel.generic.Select; +import org.aspectj.apache.bcel.generic.Tag; import org.aspectj.apache.bcel.generic.Type; import org.aspectj.apache.bcel.generic.annotation.AnnotationGen; import org.aspectj.bridge.IMessage; @@ -769,7 +770,7 @@ class BcelClassWeaver implements IClassWeaver { Annotation a = decaM.getAnnotationX().getBcelAnnotation(); AnnotationGen ag = new AnnotationGen(a,clazz.getConstantPoolGen(),true); Method oldMethod = mg.getMethod(); - MethodGen myGen = new MethodGen(oldMethod,clazz.getClassName(),clazz.getConstantPoolGen()); + MethodGen myGen = new MethodGen(oldMethod,clazz.getClassName(),clazz.getConstantPoolGen(),false);// dont use tags, they won't get repaired like for woven methods. myGen.addAnnotation(ag); Method newMethod = myGen.getMethod(); mg.addAnnotation(decaM.getAnnotationX()); diff --git a/weaver/src/org/aspectj/weaver/bcel/BcelShadow.java b/weaver/src/org/aspectj/weaver/bcel/BcelShadow.java index a5dd60910..b6b661154 100644 --- a/weaver/src/org/aspectj/weaver/bcel/BcelShadow.java +++ b/weaver/src/org/aspectj/weaver/bcel/BcelShadow.java @@ -43,6 +43,7 @@ import org.aspectj.apache.bcel.generic.InstructionList; import org.aspectj.apache.bcel.generic.InstructionTargeter; import org.aspectj.apache.bcel.generic.InvokeInstruction; import org.aspectj.apache.bcel.generic.LoadInstruction; +import org.aspectj.apache.bcel.generic.LocalVariableTag; import org.aspectj.apache.bcel.generic.MULTIANEWARRAY; import org.aspectj.apache.bcel.generic.NEW; import org.aspectj.apache.bcel.generic.ObjectType; @@ -1344,12 +1345,13 @@ public class BcelShadow extends Shadow { */ public UnresolvedType ensureTargetTypeIsCorrect(UnresolvedType tx) { - - if (tx.equals(ResolvedType.OBJECT) && getKind() == MethodCall && - getSignature().getReturnType().equals(ResolvedType.OBJECT) && - getSignature().getArity()==0 && - getSignature().getName().charAt(0) == 'c' && - getSignature().getName().equals("clone")) { + Member msig = getSignature(); + if (msig.getArity()==0 && + getKind() == MethodCall && + msig.getName().charAt(0) == 'c' && + tx.equals(ResolvedType.OBJECT) && + msig.getReturnType().equals(ResolvedType.OBJECT) && + msig.getName().equals("clone")) { // Lets go back through the code from the start of the shadow InstructionHandle searchPtr = range.getStart().getPrev(); @@ -1363,7 +1365,7 @@ public class BcelShadow extends Shadow { LoadInstruction li = (LoadInstruction)searchPtr.getInstruction(); li.getIndex(); LocalVariableTag lvt = LazyMethodGen.getLocalVariableTag(searchPtr,li.getIndex()); - if (lvt!=null) return lvt.getType(); + if (lvt!=null) return UnresolvedType.forSignature(lvt.getType()); } // A field access instruction may tell us the real type of what the clone() call is on if (searchPtr.getInstruction() instanceof FieldInstruction) { diff --git a/weaver/src/org/aspectj/weaver/bcel/LazyMethodGen.java b/weaver/src/org/aspectj/weaver/bcel/LazyMethodGen.java index 809d41225..043537de1 100644 --- a/weaver/src/org/aspectj/weaver/bcel/LazyMethodGen.java +++ b/weaver/src/org/aspectj/weaver/bcel/LazyMethodGen.java @@ -24,6 +24,7 @@ import java.util.LinkedList; import java.util.List; import java.util.ListIterator; import java.util.Map; +import java.util.Properties; import java.util.Set; import java.util.Stack; @@ -44,15 +45,19 @@ import org.aspectj.apache.bcel.generic.InstructionHandle; import org.aspectj.apache.bcel.generic.InstructionList; import org.aspectj.apache.bcel.generic.InstructionTargeter; import org.aspectj.apache.bcel.generic.LineNumberGen; +import org.aspectj.apache.bcel.generic.LineNumberTag; import org.aspectj.apache.bcel.generic.LocalVariableGen; import org.aspectj.apache.bcel.generic.LocalVariableInstruction; +import org.aspectj.apache.bcel.generic.LocalVariableTag; import org.aspectj.apache.bcel.generic.MethodGen; import org.aspectj.apache.bcel.generic.ObjectType; import org.aspectj.apache.bcel.generic.Select; +import org.aspectj.apache.bcel.generic.Tag; import org.aspectj.apache.bcel.generic.Type; import org.aspectj.apache.bcel.generic.annotation.AnnotationGen; import org.aspectj.bridge.IMessage; import org.aspectj.bridge.ISourceLocation; +import org.aspectj.bridge.MessageUtil; import org.aspectj.weaver.AjAttribute; import org.aspectj.weaver.AnnotationX; import org.aspectj.weaver.BCException; @@ -94,6 +99,27 @@ public final class LazyMethodGen { private BcelMethod memberView; private AjAttribute.EffectiveSignatureAttribute effectiveSignature; int highestLineNumber = 0; + + + /* + * This option specifies whether we let the BCEL classes create LineNumberGens and LocalVariableGens + * or if we make it create LineNumberTags and LocalVariableTags. Up until 1.5.1 we always created + * Gens - then on return from the MethodGen ctor we took them apart, reprocessed them all and + * created Tags. (see unpackLocals/unpackLineNumbers). As we have our own copy of Bcel, why not create + * the right thing straightaway? So setting this to true will call the MethodGen ctor() in such + * a way that it creates Tags - removing the need for unpackLocals/unpackLineNumbers - HOWEVER see + * the ensureAllLineNumberSetup() method for some other relevant info. + * + * Whats the difference between a Tag and a Gen? A Tag is more lightweight, it doesn't know which + * instructions it targets, it relies on the instructions targetting *it* - this reduces the amount + * of targeter manipulation we have to do. + * + * Because this *could* go wrong - it passes all our tests, but you never know, the option: + * -Xset:optimizeWithTags=false + * will turn it *OFF* + */ + public static boolean avoidUseOfBcelGenObjects = true; + public static boolean checkedXsetOption = false; /** This is nonnull if this method is the result of an "inlining". We currently * copy methods into other classes for around advice. We add this field so @@ -248,9 +274,20 @@ public final class LazyMethodGen { private void initialize() { if (returnType != null) return; + // Check whether we need to configure the optimization + if (!checkedXsetOption) { + Properties p = enclosingClass.getWorld().getExtraConfiguration(); + if (p!=null) { + avoidUseOfBcelGenObjects = Boolean.parseBoolean(p.getProperty("optimizeWithTags","true")); + if (!avoidUseOfBcelGenObjects) + enclosingClass.getWorld().getMessageHandler().handleMessage(MessageUtil.info("[optimizeWithTags=false] Disabling optimization to use Tags rather than Gens")); + } + checkedXsetOption=true; + } + //System.err.println("initializing: " + getName() + ", " + enclosingClass.getName() + ", " + returnType + ", " + savedMethod); - MethodGen gen = new MethodGen(savedMethod, enclosingClass.getName(), enclosingClass.getConstantPoolGen()); + MethodGen gen = new MethodGen(savedMethod, enclosingClass.getName(), enclosingClass.getConstantPoolGen(),avoidUseOfBcelGenObjects); this.returnType = gen.getReturnType(); this.argumentTypes = gen.getArgumentTypes(); @@ -273,10 +310,16 @@ public final class LazyMethodGen { } else { //body = new InstructionList(savedMethod.getCode().getCode()); body = gen.getInstructionList(); - + unpackHandlers(gen); - unpackLineNumbers(gen); - unpackLocals(gen); + + if (avoidUseOfBcelGenObjects) { + ensureAllLineNumberSetup(gen); + highestLineNumber = gen.getHighestlinenumber(); + } else { + unpackLineNumbers(gen); + unpackLocals(gen); + } } assertGoodBody(); @@ -363,6 +406,33 @@ public final class LazyMethodGen { gen.removeLineNumbers(); } + /** + * On entry to this method we have a method whose instruction stream contains a few instructions + * that have line numbers assigned to them (LineNumberTags). The aim is to ensure every instruction + * has the right line number. This is necessary because some of them may be extracted out into other + * methods - and it'd be useful for them to maintain the source line number for debugging. + */ + private void ensureAllLineNumberSetup(MethodGen gen) { + LineNumberTag lr = null; + boolean skip = false; + for (InstructionHandle ih = body.getStart(); ih != null; ih = ih.getNext()) { + InstructionTargeter[] targeters = ih.getTargeters(); + skip = false; + if (targeters != null) { + for (int i = targeters.length - 1; i >= 0; i--) { + InstructionTargeter targeter = targeters[i]; + if (targeter instanceof LineNumberTag) { + lr = (LineNumberTag) targeter; + skip=true; + } + } + } + if (lr != null && !skip) { + ih.addTargeter(lr); + } + } + } + private void unpackLocals(MethodGen gen) { Set locals = new HashSet(); for (InstructionHandle ih = body.getStart(); ih != null; ih = ih.getNext()) { @@ -373,7 +443,7 @@ public final class LazyMethodGen { InstructionTargeter targeter = targeters[i]; if (targeter instanceof LocalVariableGen) { LocalVariableGen lng = (LocalVariableGen) targeter; - LocalVariableTag lr = new LocalVariableTag(BcelWorld.fromBcel(lng.getType()), lng.getName(), lng.getIndex(), lng.getStart().getPosition()); + LocalVariableTag lr = new LocalVariableTag(lng.getType().getSignature()/*BcelWorld.fromBcel(lng.getType())*/, lng.getName(), lng.getIndex(), lng.getStart().getPosition()); if (lng.getStart() == ih) { locals.add(lr); } else { @@ -1006,9 +1076,13 @@ public final class LazyMethodGen { continue; } slots.add(new Integer(tag.getSlot())); - - gen.addLocalVariable(tag.getName(), - BcelWorld.makeBcelType(tag.getType()), + Type t = tag.getRealType(); + if (t==null) { + t = BcelWorld.makeBcelType(UnresolvedType.forSignature(tag.getType())); + } + gen.addLocalVariable( + tag.getName(), + t, tag.getSlot(),(InstructionHandle) start,(InstructionHandle) lvpos.end); } } diff --git a/weaver/src/org/aspectj/weaver/bcel/Range.java b/weaver/src/org/aspectj/weaver/bcel/Range.java index 60702912b..f32335dd4 100644 --- a/weaver/src/org/aspectj/weaver/bcel/Range.java +++ b/weaver/src/org/aspectj/weaver/bcel/Range.java @@ -197,6 +197,7 @@ abstract class Range implements InstructionTargeter { // assert isRangeHandle(ih) Range ret = null; InstructionTargeter[] targeters = ih.getTargeters(); + if (targeters!=null) { for (int i = targeters.length - 1; i >= 0; i--) { if (targeters[i] instanceof Range) { Range r = (Range) targeters[i]; @@ -205,7 +206,10 @@ abstract class Range implements InstructionTargeter { ret = (Range) targeters[i]; } } - if (ret == null) throw new BCException("shouldn't happen"); + } + if (ret == null) { + throw new BCException("shouldn't happen"); + } return ret; } diff --git a/weaver/src/org/aspectj/weaver/bcel/ShadowRange.java b/weaver/src/org/aspectj/weaver/bcel/ShadowRange.java index 7632c3e16..cf46cbf68 100644 --- a/weaver/src/org/aspectj/weaver/bcel/ShadowRange.java +++ b/weaver/src/org/aspectj/weaver/bcel/ShadowRange.java @@ -21,6 +21,7 @@ import org.aspectj.apache.bcel.generic.InstructionHandle; import org.aspectj.apache.bcel.generic.InstructionList; import org.aspectj.apache.bcel.generic.InstructionTargeter; import org.aspectj.apache.bcel.generic.LocalVariableInstruction; +import org.aspectj.apache.bcel.generic.LocalVariableTag; import org.aspectj.apache.bcel.generic.RET; import org.aspectj.apache.bcel.generic.Select; import org.aspectj.apache.bcel.generic.TargetLostException; diff --git a/weaver/src/org/aspectj/weaver/bcel/Utility.java b/weaver/src/org/aspectj/weaver/bcel/Utility.java index 7eec5ef41..79571fcf7 100644 --- a/weaver/src/org/aspectj/weaver/bcel/Utility.java +++ b/weaver/src/org/aspectj/weaver/bcel/Utility.java @@ -44,6 +44,7 @@ import org.aspectj.apache.bcel.generic.InstructionHandle; import org.aspectj.apache.bcel.generic.InstructionList; import org.aspectj.apache.bcel.generic.InstructionTargeter; import org.aspectj.apache.bcel.generic.LDC; +import org.aspectj.apache.bcel.generic.LineNumberTag; import org.aspectj.apache.bcel.generic.ObjectType; import org.aspectj.apache.bcel.generic.ReferenceType; import org.aspectj.apache.bcel.generic.SIPUSH; @@ -655,9 +656,8 @@ public class Utility { // } // return getSourceLine(ih.getNext()); // } - - public static int getSourceLine(InstructionHandle ih) { + public static int getSourceLine(InstructionHandle ih) {//,boolean goforwards) { int lookahead=0; // arbitrary rule that we will never lookahead more than 100 instructions for a line # while (lookahead++ < 100) { @@ -672,11 +672,16 @@ public class Utility { } } } - ih = ih.getNext(); +// if (goforwards) ih=ih.getNext(); else + ih=ih.getPrev(); } //System.err.println("no line information available for: " + ih); return -1; } + +// public static int getSourceLine(InstructionHandle ih) { +// return getSourceLine(ih,false); +// } // assumes that there is no already extant source line tag. Otherwise we'll have to be better. public static void setSourceLine(InstructionHandle ih, int lineNumber) { |