import java.util.HashMap; | import java.util.HashMap; | ||||
import java.util.HashSet; | import java.util.HashSet; | ||||
import java.util.Iterator; | import java.util.Iterator; | ||||
import java.util.LinkedHashSet; | |||||
import java.util.List; | import java.util.List; | ||||
import java.util.Map; | import java.util.Map; | ||||
import java.util.Properties; | import java.util.Properties; | ||||
* will iterate over the fields repeatedly until everything has been applied. | * will iterate over the fields repeatedly until everything has been applied. | ||||
* | * | ||||
*/ | */ | ||||
private boolean weaveAtFieldRepeatedly(List<DeclareAnnotation> decaFs, List itdFields, List<Integer> reportedErrors) { | |||||
private boolean weaveAtFieldRepeatedly(List<DeclareAnnotation> decaFs, List<ConcreteTypeMunger> itdFields, | |||||
List<Integer> reportedErrors) { | |||||
boolean isChanged = false; | boolean isChanged = false; | ||||
for (Iterator iter = itdFields.iterator(); iter.hasNext();) { | |||||
for (Iterator<ConcreteTypeMunger> iter = itdFields.iterator(); iter.hasNext();) { | |||||
BcelTypeMunger fieldMunger = (BcelTypeMunger) iter.next(); | BcelTypeMunger fieldMunger = (BcelTypeMunger) iter.next(); | ||||
ResolvedMember itdIsActually = fieldMunger.getSignature(); | ResolvedMember itdIsActually = fieldMunger.getSignature(); | ||||
List<DeclareAnnotation> worthRetrying = new ArrayList<DeclareAnnotation>(); | |||||
Set<DeclareAnnotation> worthRetrying = new LinkedHashSet<DeclareAnnotation>(); | |||||
boolean modificationOccured = false; | boolean modificationOccured = false; | ||||
for (Iterator<DeclareAnnotation> iter2 = decaFs.iterator(); iter2.hasNext();) { | for (Iterator<DeclareAnnotation> iter2 = decaFs.iterator(); iter2.hasNext();) { | ||||
DeclareAnnotation decaF = iter2.next(); | DeclareAnnotation decaF = iter2.next(); | ||||
if (decaF.matches(itdIsActually, world)) { | if (decaF.matches(itdIsActually, world)) { | ||||
LazyMethodGen annotationHolder = locateAnnotationHolderForFieldMunger(clazz, fieldMunger); | |||||
if (doesAlreadyHaveAnnotation(annotationHolder, itdIsActually, decaF, reportedErrors)) { | |||||
continue; // skip this one... | |||||
} | |||||
annotationHolder.addAnnotation(decaF.getAnnotation()); | |||||
AsmRelationshipProvider.addDeclareAnnotationRelationship(world.getModelAsAsmManager(), | |||||
decaF.getSourceLocation(), itdIsActually.getSourceLocation()); | |||||
isChanged = true; | |||||
modificationOccured = true; | |||||
if (decaF.isRemover()) { | |||||
LazyMethodGen annotationHolder = locateAnnotationHolderForFieldMunger(clazz, fieldMunger); | |||||
if (annotationHolder.hasAnnotation(decaF.getAnnotationType())) { | |||||
isChanged = true; | |||||
// something to remove | |||||
annotationHolder.removeAnnotation(decaF.getAnnotationType()); | |||||
AsmRelationshipProvider.addDeclareAnnotationRelationship(world.getModelAsAsmManager(), | |||||
decaF.getSourceLocation(), itdIsActually.getSourceLocation(), true); | |||||
} else { | |||||
worthRetrying.add(decaF); | |||||
} | |||||
} else { | |||||
LazyMethodGen annotationHolder = locateAnnotationHolderForFieldMunger(clazz, fieldMunger); | |||||
if (doesAlreadyHaveAnnotation(annotationHolder, itdIsActually, decaF, reportedErrors)) { | |||||
continue; // skip this one... | |||||
} | |||||
annotationHolder.addAnnotation(decaF.getAnnotation()); | |||||
AsmRelationshipProvider.addDeclareAnnotationRelationship(world.getModelAsAsmManager(), | |||||
decaF.getSourceLocation(), itdIsActually.getSourceLocation(), false); | |||||
isChanged = true; | |||||
modificationOccured = true; | |||||
} | |||||
} else { | } else { | ||||
if (!decaF.isStarredAnnotationPattern()) { | if (!decaF.isStarredAnnotationPattern()) { | ||||
worthRetrying.add(decaF); // an annotation is specified | worthRetrying.add(decaF); // an annotation is specified | ||||
for (Iterator<DeclareAnnotation> iter2 = worthRetrying.iterator(); iter2.hasNext();) { | for (Iterator<DeclareAnnotation> iter2 = worthRetrying.iterator(); iter2.hasNext();) { | ||||
DeclareAnnotation decaF = iter2.next(); | DeclareAnnotation decaF = iter2.next(); | ||||
if (decaF.matches(itdIsActually, world)) { | if (decaF.matches(itdIsActually, world)) { | ||||
LazyMethodGen annotationHolder = locateAnnotationHolderForFieldMunger(clazz, fieldMunger); | |||||
if (doesAlreadyHaveAnnotation(annotationHolder, itdIsActually, decaF, reportedErrors)) { | |||||
continue; // skip this one... | |||||
if (decaF.isRemover()) { | |||||
LazyMethodGen annotationHolder = locateAnnotationHolderForFieldMunger(clazz, fieldMunger); | |||||
if (annotationHolder.hasAnnotation(decaF.getAnnotationType())) { | |||||
isChanged = true; | |||||
// something to remove | |||||
annotationHolder.removeAnnotation(decaF.getAnnotationType()); | |||||
AsmRelationshipProvider.addDeclareAnnotationRelationship(world.getModelAsAsmManager(), | |||||
decaF.getSourceLocation(), itdIsActually.getSourceLocation(), true); | |||||
forRemoval.add(decaF); | |||||
} | |||||
} else { | |||||
LazyMethodGen annotationHolder = locateAnnotationHolderForFieldMunger(clazz, fieldMunger); | |||||
if (doesAlreadyHaveAnnotation(annotationHolder, itdIsActually, decaF, reportedErrors)) { | |||||
continue; // skip this one... | |||||
} | |||||
annotationHolder.addAnnotation(decaF.getAnnotation()); | |||||
AsmRelationshipProvider.addDeclareAnnotationRelationship(world.getModelAsAsmManager(), | |||||
decaF.getSourceLocation(), itdIsActually.getSourceLocation(), false); | |||||
isChanged = true; | |||||
modificationOccured = true; | |||||
forRemoval.add(decaF); | |||||
} | } | ||||
annotationHolder.addAnnotation(decaF.getAnnotation()); | |||||
AsmRelationshipProvider.addDeclareAnnotationRelationship(world.getModelAsAsmManager(), | |||||
decaF.getSourceLocation(), itdIsActually.getSourceLocation()); | |||||
isChanged = true; | |||||
modificationOccured = true; | |||||
forRemoval.add(decaF); | |||||
} | } | ||||
} | } | ||||
worthRetrying.removeAll(forRemoval); | worthRetrying.removeAll(forRemoval); | ||||
annotationHolder.addAnnotation(decaMC.getAnnotation()); | annotationHolder.addAnnotation(decaMC.getAnnotation()); | ||||
isChanged = true; | isChanged = true; | ||||
AsmRelationshipProvider.addDeclareAnnotationRelationship(asmManager, decaMC.getSourceLocation(), | AsmRelationshipProvider.addDeclareAnnotationRelationship(asmManager, decaMC.getSourceLocation(), | ||||
unMangledInterMethod.getSourceLocation()); | |||||
unMangledInterMethod.getSourceLocation(), false); | |||||
reportMethodCtorWeavingMessage(clazz, unMangledInterMethod, decaMC, -1); | reportMethodCtorWeavingMessage(clazz, unMangledInterMethod, decaMC, -1); | ||||
modificationOccured = true; | modificationOccured = true; | ||||
} else { | } else { | ||||
annotationHolder.addAnnotation(decaMC.getAnnotation()); | annotationHolder.addAnnotation(decaMC.getAnnotation()); | ||||
unMangledInterMethod.addAnnotation(decaMC.getAnnotation()); | unMangledInterMethod.addAnnotation(decaMC.getAnnotation()); | ||||
AsmRelationshipProvider.addDeclareAnnotationRelationship(asmManager, decaMC.getSourceLocation(), | AsmRelationshipProvider.addDeclareAnnotationRelationship(asmManager, decaMC.getSourceLocation(), | ||||
unMangledInterMethod.getSourceLocation()); | |||||
unMangledInterMethod.getSourceLocation(), false); | |||||
isChanged = true; | isChanged = true; | ||||
modificationOccured = true; | modificationOccured = true; | ||||
forRemoval.add(decaMC); | forRemoval.add(decaMC); | ||||
} | } | ||||
private boolean dontAddTwice(DeclareAnnotation decaF, AnnotationAJ[] dontAddMeTwice) { | private boolean dontAddTwice(DeclareAnnotation decaF, AnnotationAJ[] dontAddMeTwice) { | ||||
for (int i = 0; i < dontAddMeTwice.length; i++) { | |||||
AnnotationAJ ann = dontAddMeTwice[i]; | |||||
for (AnnotationAJ ann : dontAddMeTwice) { | |||||
if (ann != null && decaF.getAnnotation().getTypeName().equals(ann.getTypeName())) { | if (ann != null && decaF.getAnnotation().getTypeName().equals(ann.getTypeName())) { | ||||
// dontAddMeTwice[i] = null; // incase it really has been added | |||||
// twice! | |||||
return true; | return true; | ||||
} | } | ||||
} | } | ||||
return false; | return false; | ||||
} | } | ||||
// BUGWARNING not getting enough warnings out on declare @field ? There is a potential problem here with warnings not | |||||
// coming out - this will occur if they are created on the second iteration round this loop. | |||||
// We currently deactivate error reporting for the second time round. A possible solution is to record what annotations | |||||
// were added by what decafs and check that to see if an error needs to be reported - this would be expensive so lets | |||||
// skip it for now | |||||
/** | /** | ||||
* Weave any declare @field statements into the fields of the supplied class | |||||
* Weave any declare @field statements into the fields of the supplied class. This will attempt to apply them to the ITDs too. | |||||
* | * | ||||
* Interesting case relating to public ITDd fields. The annotations are really stored against the interfieldinit method in the | * Interesting case relating to public ITDd fields. The annotations are really stored against the interfieldinit method in the | ||||
* aspect, but the public field is placed in the target type and then is processed in the 2nd pass over fields that occurs. I | * aspect, but the public field is placed in the target type and then is processed in the 2nd pass over fields that occurs. I | ||||
* as well as on the interfieldinit method. | * as well as on the interfieldinit method. | ||||
*/ | */ | ||||
private boolean weaveDeclareAtField(LazyClassGen clazz) { | private boolean weaveDeclareAtField(LazyClassGen clazz) { | ||||
// BUGWARNING not getting enough warnings out on declare @field ? | |||||
// There is a potential problem here with warnings not coming out - this | |||||
// will occur if they are created on the second iteration round this | |||||
// loop. | |||||
// We currently deactivate error reporting for the second time round. | |||||
// A possible solution is to record what annotations were added by what | |||||
// decafs and check that to see if an error needs to be reported - this | |||||
// would be expensive so lets skip it for now | |||||
List<Integer> reportedProblems = new ArrayList<Integer>(); | List<Integer> reportedProblems = new ArrayList<Integer>(); | ||||
List<DeclareAnnotation> allDecafs = world.getDeclareAnnotationOnFields(); | List<DeclareAnnotation> allDecafs = world.getDeclareAnnotationOnFields(); | ||||
if (allDecafs.isEmpty()) { | if (allDecafs.isEmpty()) { | ||||
return false; | return false; | ||||
} | } | ||||
boolean isChanged = false; | |||||
List<ConcreteTypeMunger> itdFields = getITDSubset(clazz, ResolvedTypeMunger.Field); | |||||
if (itdFields != null) { | |||||
isChanged = weaveAtFieldRepeatedly(allDecafs, itdFields, reportedProblems); | |||||
boolean typeIsChanged = false; | |||||
List<ConcreteTypeMunger> relevantItdFields = getITDSubset(clazz, ResolvedTypeMunger.Field); | |||||
if (relevantItdFields != null) { | |||||
typeIsChanged = weaveAtFieldRepeatedly(allDecafs, relevantItdFields, reportedProblems); | |||||
} | } | ||||
List<DeclareAnnotation> decaFs = getMatchingSubset(allDecafs, clazz.getType()); | |||||
if (decaFs.isEmpty()) { | |||||
return false; // nothing more to do | |||||
List<DeclareAnnotation> decafs = getMatchingSubset(allDecafs, clazz.getType()); | |||||
if (decafs.isEmpty()) { | |||||
return typeIsChanged; | |||||
} | } | ||||
List<BcelField> fields = clazz.getFieldGens(); | List<BcelField> fields = clazz.getFieldGens(); | ||||
if (fields != null) { | if (fields != null) { | ||||
Set<DeclareAnnotation> unusedDecafs = new HashSet<DeclareAnnotation>(); | Set<DeclareAnnotation> unusedDecafs = new HashSet<DeclareAnnotation>(); | ||||
unusedDecafs.addAll(decaFs); | |||||
for (int fieldCounter = 0; fieldCounter < fields.size(); fieldCounter++) { | |||||
BcelField aBcelField = fields.get(fieldCounter);// new | |||||
// BcelField(clazz.getBcelObjectType(),fields[fieldCounter | |||||
// ]); | |||||
if (!aBcelField.getName().startsWith(NameMangler.PREFIX)) { | |||||
unusedDecafs.addAll(decafs); | |||||
for (BcelField field : fields) { | |||||
if (!field.getName().startsWith(NameMangler.PREFIX)) { | |||||
// Single first pass | // Single first pass | ||||
List<DeclareAnnotation> worthRetrying = new ArrayList<DeclareAnnotation>(); | |||||
Set<DeclareAnnotation> worthRetrying = new LinkedHashSet<DeclareAnnotation>(); | |||||
boolean modificationOccured = false; | boolean modificationOccured = false; | ||||
AnnotationAJ[] dontAddMeTwice = aBcelField.getAnnotations(); | |||||
AnnotationAJ[] dontAddMeTwice = field.getAnnotations(); | |||||
// go through all the declare @field statements | // go through all the declare @field statements | ||||
for (DeclareAnnotation decaF : decaFs) { | |||||
if (decaF.getAnnotation() == null) { | |||||
for (DeclareAnnotation decaf : decafs) { | |||||
if (decaf.getAnnotation() == null) { | |||||
return false; | return false; | ||||
} | } | ||||
if (decaF.matches(aBcelField, world)) { | |||||
if (!dontAddTwice(decaF, dontAddMeTwice)) { | |||||
if (doesAlreadyHaveAnnotation(aBcelField, decaF, reportedProblems)) { | |||||
// remove the declare @field since don't | |||||
// want an error when | |||||
// the annotation is already there | |||||
unusedDecafs.remove(decaF); | |||||
continue; | |||||
} | |||||
if (decaF.getAnnotation().isRuntimeVisible()) { // isAnnotationWithRuntimeRetention | |||||
// ( | |||||
// clazz | |||||
// . | |||||
// getJavaClass(world))){ | |||||
// if(decaF.getAnnotationTypeX(). | |||||
// isAnnotationWithRuntimeRetention(world)){ | |||||
// it should be runtime visible, so put it | |||||
// on the Field | |||||
// Annotation a = | |||||
// decaF.getAnnotationX().getBcelAnnotation | |||||
// (); | |||||
// AnnotationGen ag = new | |||||
// AnnotationGen(a,clazz | |||||
// .getConstantPoolGen(),true); | |||||
// FieldGen myGen = new | |||||
// FieldGen(fields[fieldCounter | |||||
// ],clazz.getConstantPoolGen()); | |||||
// myGen.addAnnotation(ag); | |||||
// Field newField = myGen.getField(); | |||||
aBcelField.addAnnotation(decaF.getAnnotation()); | |||||
// clazz.replaceField(fields[fieldCounter], | |||||
// newField); | |||||
// fields[fieldCounter]=newField; | |||||
if (decaf.matches(field, world)) { | |||||
if (decaf.isRemover()) { | |||||
AnnotationAJ annotation = decaf.getAnnotation(); | |||||
if (field.hasAnnotation(annotation.getType())) { | |||||
// something to remove | |||||
typeIsChanged = true; | |||||
field.removeAnnotation(annotation); | |||||
AsmRelationshipProvider.addDeclareAnnotationFieldRelationship(world.getModelAsAsmManager(), | |||||
decaf.getSourceLocation(), clazz.getName(), field, true); | |||||
reportFieldAnnotationWeavingMessage(clazz, field, decaf, true); | |||||
} else { | } else { | ||||
aBcelField.addAnnotation(decaF.getAnnotation()); | |||||
worthRetrying.add(decaf); | |||||
} | } | ||||
unusedDecafs.remove(decaf); | |||||
} else { | |||||
if (!dontAddTwice(decaf, dontAddMeTwice)) { | |||||
if (doesAlreadyHaveAnnotation(field, decaf, reportedProblems)) { | |||||
// remove the declare @field since don't want an error when the annotation is already there | |||||
unusedDecafs.remove(decaf); | |||||
continue; | |||||
} | |||||
field.addAnnotation(decaf.getAnnotation()); | |||||
} | |||||
AsmRelationshipProvider.addDeclareAnnotationFieldRelationship(world.getModelAsAsmManager(), | |||||
decaf.getSourceLocation(), clazz.getName(), field, false); | |||||
reportFieldAnnotationWeavingMessage(clazz, field, decaf, false); | |||||
typeIsChanged = true; | |||||
modificationOccured = true; | |||||
unusedDecafs.remove(decaf); | |||||
} | } | ||||
AsmRelationshipProvider.addDeclareAnnotationFieldRelationship(world.getModelAsAsmManager(), | |||||
decaF.getSourceLocation(), clazz.getName(), aBcelField); | |||||
reportFieldAnnotationWeavingMessage(clazz, fields, fieldCounter, decaF); | |||||
isChanged = true; | |||||
modificationOccured = true; | |||||
// remove the declare @field since have matched | |||||
// against it | |||||
unusedDecafs.remove(decaF); | |||||
} else { | |||||
if (!decaF.isStarredAnnotationPattern()) { | |||||
worthRetrying.add(decaF); // an annotation is | |||||
// specified that | |||||
// might be put on | |||||
// by a subsequent | |||||
// decaf | |||||
} | |||||
} else if (!decaf.isStarredAnnotationPattern() || decaf.isRemover()) { | |||||
worthRetrying.add(decaf); // an annotation is specified that might be put on by a subsequent decaf | |||||
} | } | ||||
} | } | ||||
// Multiple secondary passes | // Multiple secondary passes | ||||
while (!worthRetrying.isEmpty() && modificationOccured) { | while (!worthRetrying.isEmpty() && modificationOccured) { | ||||
modificationOccured = false; | modificationOccured = false; | ||||
// lets have another go | |||||
// lets have another go with any remaining ones | |||||
List<DeclareAnnotation> forRemoval = new ArrayList<DeclareAnnotation>(); | List<DeclareAnnotation> forRemoval = new ArrayList<DeclareAnnotation>(); | ||||
for (Iterator<DeclareAnnotation> iter = worthRetrying.iterator(); iter.hasNext();) { | for (Iterator<DeclareAnnotation> iter = worthRetrying.iterator(); iter.hasNext();) { | ||||
DeclareAnnotation decaF = iter.next(); | DeclareAnnotation decaF = iter.next(); | ||||
if (decaF.matches(aBcelField, world)) { | |||||
// below code is for recursive things | |||||
if (doesAlreadyHaveAnnotation(aBcelField, decaF, reportedProblems)) { | |||||
// remove the declare @field since don't | |||||
// want an error when | |||||
// the annotation is already there | |||||
if (decaF.matches(field, world)) { | |||||
if (decaF.isRemover()) { | |||||
AnnotationAJ annotation = decaF.getAnnotation(); | |||||
if (field.hasAnnotation(annotation.getType())) { | |||||
// something to remove | |||||
typeIsChanged = modificationOccured = true; | |||||
forRemoval.add(decaF); | |||||
field.removeAnnotation(annotation); | |||||
AsmRelationshipProvider.addDeclareAnnotationFieldRelationship(world.getModelAsAsmManager(), | |||||
decaF.getSourceLocation(), clazz.getName(), field, true); | |||||
reportFieldAnnotationWeavingMessage(clazz, field, decaF, true); | |||||
} | |||||
} else { | |||||
// below code is for recursive things | |||||
unusedDecafs.remove(decaF); | unusedDecafs.remove(decaF); | ||||
continue; // skip this one... | |||||
if (doesAlreadyHaveAnnotation(field, decaF, reportedProblems)) { | |||||
continue; | |||||
} | |||||
field.addAnnotation(decaF.getAnnotation()); | |||||
AsmRelationshipProvider.addDeclareAnnotationFieldRelationship(world.getModelAsAsmManager(), | |||||
decaF.getSourceLocation(), clazz.getName(), field, false); | |||||
typeIsChanged = modificationOccured = true; | |||||
forRemoval.add(decaF); | |||||
} | } | ||||
aBcelField.addAnnotation(decaF.getAnnotation()); | |||||
AsmRelationshipProvider.addDeclareAnnotationFieldRelationship(world.getModelAsAsmManager(), | |||||
decaF.getSourceLocation(), clazz.getName(), aBcelField); | |||||
isChanged = true; | |||||
modificationOccured = true; | |||||
forRemoval.add(decaF); | |||||
// remove the declare @field since have matched | |||||
// against it | |||||
unusedDecafs.remove(decaF); | |||||
} | } | ||||
} | } | ||||
worthRetrying.removeAll(forRemoval); | worthRetrying.removeAll(forRemoval); | ||||
} | } | ||||
checkUnusedDeclareAts(unusedDecafs, true); | checkUnusedDeclareAts(unusedDecafs, true); | ||||
} | } | ||||
return isChanged; | |||||
return typeIsChanged; | |||||
} | } | ||||
// bug 99191 - put out an error message if the type doesn't exist | // bug 99191 - put out an error message if the type doesn't exist | ||||
for (DeclareAnnotation declA : unusedDecaTs) { | for (DeclareAnnotation declA : unusedDecaTs) { | ||||
// Error if an exact type pattern was specified | // Error if an exact type pattern was specified | ||||
boolean shouldCheck = declA.isExactPattern() || declA.getSignaturePattern().getExactDeclaringTypes().size() != 0;// != | |||||
// null;// | |||||
// instanceof | |||||
// ExactTypePattern; | |||||
boolean shouldCheck = declA.isExactPattern() || declA.getSignaturePattern().getExactDeclaringTypes().size() != 0; | |||||
if (shouldCheck && declA.getKind() != DeclareAnnotation.AT_CONSTRUCTOR) { | if (shouldCheck && declA.getKind() != DeclareAnnotation.AT_CONSTRUCTOR) { | ||||
if (declA.getSignaturePattern().isMatchOnAnyName()/* getName().isAny() */) { | |||||
if (declA.getSignaturePattern().isMatchOnAnyName()) { | |||||
shouldCheck = false; | shouldCheck = false; | ||||
} else { | } else { | ||||
List<ExactTypePattern> declaringTypePatterns = declA.getSignaturePattern().getExactDeclaringTypes(); | List<ExactTypePattern> declaringTypePatterns = declA.getSignaturePattern().getExactDeclaringTypes(); | ||||
} | } | ||||
// TAG: WeavingMessage | // TAG: WeavingMessage | ||||
private void reportFieldAnnotationWeavingMessage(LazyClassGen clazz, List fields, int fieldCounter, DeclareAnnotation decaF) { | |||||
private void reportFieldAnnotationWeavingMessage(LazyClassGen clazz, BcelField theField, DeclareAnnotation decaf, | |||||
boolean isRemove) { | |||||
if (!getWorld().getMessageHandler().isIgnoring(IMessage.WEAVEINFO)) { | if (!getWorld().getMessageHandler().isIgnoring(IMessage.WEAVEINFO)) { | ||||
BcelField theField = (BcelField) fields.get(fieldCounter); | |||||
world.getMessageHandler().handleMessage( | world.getMessageHandler().handleMessage( | ||||
WeaveMessage.constructWeavingMessage( | WeaveMessage.constructWeavingMessage( | ||||
WeaveMessage.WEAVEMESSAGE_ANNOTATES, | |||||
isRemove ? WeaveMessage.WEAVEMESSAGE_REMOVES_ANNOTATION : WeaveMessage.WEAVEMESSAGE_ANNOTATES, | |||||
new String[] { theField.getFieldAsIs().toString() + "' of type '" + clazz.getName(), | new String[] { theField.getFieldAsIs().toString() + "' of type '" + clazz.getName(), | ||||
clazz.getFileName(), decaF.getAnnotationString(), "field", decaF.getAspect().toString(), | |||||
Utility.beautifyLocation(decaF.getSourceLocation()) })); | |||||
clazz.getFileName(), decaf.getAnnotationString(), "field", decaf.getAspect().toString(), | |||||
Utility.beautifyLocation(decaf.getSourceLocation()) })); | |||||
} | } | ||||
} | } | ||||
import org.aspectj.util.GenericSignature; | import org.aspectj.util.GenericSignature; | ||||
import org.aspectj.util.GenericSignatureParser; | import org.aspectj.util.GenericSignatureParser; | ||||
import org.aspectj.weaver.AjAttribute; | import org.aspectj.weaver.AjAttribute; | ||||
import org.aspectj.weaver.AjAttribute.WeaverVersionInfo; | |||||
import org.aspectj.weaver.AnnotationAJ; | import org.aspectj.weaver.AnnotationAJ; | ||||
import org.aspectj.weaver.BCException; | |||||
import org.aspectj.weaver.ISourceContext; | import org.aspectj.weaver.ISourceContext; | ||||
import org.aspectj.weaver.ResolvedMemberImpl; | import org.aspectj.weaver.ResolvedMemberImpl; | ||||
import org.aspectj.weaver.ResolvedType; | import org.aspectj.weaver.ResolvedType; | ||||
import org.aspectj.weaver.UnresolvedType; | import org.aspectj.weaver.UnresolvedType; | ||||
import org.aspectj.weaver.World; | import org.aspectj.weaver.World; | ||||
import org.aspectj.weaver.AjAttribute.WeaverVersionInfo; | |||||
import org.aspectj.weaver.bcel.BcelGenericSignatureToTypeXConverter.GenericSignatureFormatException; | import org.aspectj.weaver.bcel.BcelGenericSignatureToTypeXConverter.GenericSignatureFormatException; | ||||
/** | |||||
* An AspectJ Field object that is backed by a Bcel Field object. | |||||
* | |||||
* @author PARC | |||||
* @author Andy Clement | |||||
*/ | |||||
final class BcelField extends ResolvedMemberImpl { | final class BcelField extends ResolvedMemberImpl { | ||||
public static int AccSynthetic = 0x1000; | public static int AccSynthetic = 0x1000; | ||||
private final BcelObjectType bcelObjectType; | private final BcelObjectType bcelObjectType; | ||||
private UnresolvedType genericFieldType = null; | private UnresolvedType genericFieldType = null; | ||||
private boolean unpackedGenericSignature = false; | private boolean unpackedGenericSignature = false; | ||||
private boolean annotationsAdded = false; | |||||
private boolean annotationsOnFieldObjectAreOutOfDate = false; | |||||
BcelField(BcelObjectType declaringType, Field field) { | BcelField(BcelObjectType declaringType, Field field) { | ||||
super(FIELD, declaringType.getResolvedTypeX(), field.getModifiers(), field.getName(), field.getSignature()); | super(FIELD, declaringType.getResolvedTypeX(), field.getModifiers(), field.getName(), field.getSignature()); | ||||
checkedExceptions = UnresolvedType.NONE; | checkedExceptions = UnresolvedType.NONE; | ||||
} | } | ||||
// ---- | |||||
private void unpackAttributes(World world) { | private void unpackAttributes(World world) { | ||||
Attribute[] attrs = field.getAttributes(); | Attribute[] attrs = field.getAttributes(); | ||||
if (attrs != null && attrs.length > 0) { | if (attrs != null && attrs.length > 0) { | ||||
List<AjAttribute> as = Utility.readAjAttributes(getDeclaringType().getClassName(), attrs, sourceContext, world, | List<AjAttribute> as = Utility.readAjAttributes(getDeclaringType().getClassName(), attrs, sourceContext, world, | ||||
(bcelObjectType != null ? bcelObjectType.getWeaverVersionAttribute() : WeaverVersionInfo.CURRENT), | (bcelObjectType != null ? bcelObjectType.getWeaverVersionAttribute() : WeaverVersionInfo.CURRENT), | ||||
new BcelConstantPoolReader(field.getConstantPool())); | new BcelConstantPoolReader(field.getConstantPool())); | ||||
as.addAll(AtAjAttributes.readAj5FieldAttributes(field, this, world.resolve(getDeclaringType()), sourceContext, world | |||||
.getMessageHandler())); | |||||
for (AjAttribute a : as) { | |||||
if (a instanceof AjAttribute.AjSynthetic) { | |||||
isAjSynthetic = true; | |||||
} else { | |||||
throw new BCException("weird field attribute " + a); | |||||
} | |||||
} | |||||
as.addAll(AtAjAttributes.readAj5FieldAttributes(field, this, world.resolve(getDeclaringType()), sourceContext, | |||||
world.getMessageHandler())); | |||||
// FIXME this code has no effect!!!??? it is set to false immediately after the block | |||||
// for (AjAttribute a : as) { | |||||
// if (a instanceof AjAttribute.AjSynthetic) { | |||||
// isAjSynthetic = true; | |||||
// } else { | |||||
// throw new BCException("weird field attribute " + a); | |||||
// } | |||||
// } | |||||
} | } | ||||
isAjSynthetic = false; | isAjSynthetic = false; | ||||
isSynthetic = true; | isSynthetic = true; | ||||
} | } | ||||
} | } | ||||
// in 1.5, synthetic is a modifier, not an attribute | // in 1.5, synthetic is a modifier, not an attribute | ||||
if ((field.getModifiers() & AccSynthetic) != 0) { | if ((field.getModifiers() & AccSynthetic) != 0) { | ||||
isSynthetic = true; | isSynthetic = true; | ||||
@Override | @Override | ||||
public boolean isAjSynthetic() { | public boolean isAjSynthetic() { | ||||
return isAjSynthetic; // || getName().startsWith(NameMangler.PREFIX); | |||||
return isAjSynthetic; | |||||
} | } | ||||
@Override | @Override | ||||
@Override | @Override | ||||
public AnnotationAJ getAnnotationOfType(UnresolvedType ofType) { | public AnnotationAJ getAnnotationOfType(UnresolvedType ofType) { | ||||
ensureAnnotationTypesRetrieved(); | ensureAnnotationTypesRetrieved(); | ||||
for (int i = 0; i < annotations.length; i++) { | |||||
if (annotations[i].getTypeName().equals(ofType.getName())) { | |||||
return annotations[i]; | |||||
for (AnnotationAJ annotation : annotations) { | |||||
if (annotation.getTypeName().equals(ofType.getName())) { | |||||
return annotation; | |||||
} | } | ||||
} | } | ||||
return null; | return null; | ||||
@Override | @Override | ||||
public void addAnnotation(AnnotationAJ annotation) { | public void addAnnotation(AnnotationAJ annotation) { | ||||
ensureAnnotationTypesRetrieved(); | ensureAnnotationTypesRetrieved(); | ||||
int len = annotations.length; | int len = annotations.length; | ||||
AnnotationAJ[] ret = new AnnotationAJ[len + 1]; | AnnotationAJ[] ret = new AnnotationAJ[len + 1]; | ||||
System.arraycopy(annotations, 0, ret, 0, len); | System.arraycopy(annotations, 0, ret, 0, len); | ||||
newAnnotationTypes[len] = annotation.getType(); | newAnnotationTypes[len] = annotation.getType(); | ||||
annotationTypes = newAnnotationTypes; | annotationTypes = newAnnotationTypes; | ||||
annotationsAdded = true; | |||||
annotationsOnFieldObjectAreOutOfDate = true; | |||||
} | |||||
public void removeAnnotation(AnnotationAJ annotation) { | |||||
ensureAnnotationTypesRetrieved(); | |||||
int len = annotations.length; | |||||
AnnotationAJ[] ret = new AnnotationAJ[len - 1]; | |||||
int p = 0; | |||||
for (AnnotationAJ anno : annotations) { | |||||
if (!anno.getType().equals(annotation.getType())) { | |||||
ret[p++] = anno; | |||||
} | |||||
} | |||||
annotations = ret; | |||||
ResolvedType[] newAnnotationTypes = new ResolvedType[len - 1]; | |||||
p = 0; | |||||
for (ResolvedType anno : annotationTypes) { | |||||
if (!anno.equals(annotation.getType())) { | |||||
newAnnotationTypes[p++] = anno; | |||||
} | |||||
} | |||||
annotationTypes = newAnnotationTypes; | |||||
annotationsOnFieldObjectAreOutOfDate = true; | |||||
} | } | ||||
/** | /** | ||||
return field; | return field; | ||||
} | } | ||||
// FIXME asc badly performing code ftw ! | |||||
public Field getField(ConstantPool cpg) { | |||||
if (!annotationsAdded) { | |||||
public Field getField(ConstantPool cpool) { | |||||
if (!annotationsOnFieldObjectAreOutOfDate) { | |||||
return field; | return field; | ||||
} | } | ||||
FieldGen fg = new FieldGen(field, cpg); | |||||
List<AnnotationGen> alreadyHas = fg.getAnnotations(); | |||||
if (annotations != null) { | |||||
for (int i = 0; i < annotations.length; i++) { | |||||
AnnotationAJ array_element = annotations[i]; | |||||
boolean alreadyHasIt = false; | |||||
for (AnnotationGen gen : alreadyHas) { | |||||
if (gen.getTypeName().equals(array_element.getTypeName())) { | |||||
alreadyHasIt = true; | |||||
break; | |||||
} | |||||
} | |||||
if (!alreadyHasIt) { | |||||
fg.addAnnotation(new AnnotationGen(((BcelAnnotation) array_element).getBcelAnnotation(), cpg, true)); | |||||
} | |||||
} | |||||
FieldGen newFieldGen = new FieldGen(field, cpool); | |||||
newFieldGen.removeAnnotations(); | |||||
// List<AnnotationGen> alreadyHas = fg.getAnnotations(); | |||||
// if (annotations != null) { | |||||
// fg.removeAnnotations(); | |||||
for (AnnotationAJ annotation : annotations) { | |||||
newFieldGen.addAnnotation(new AnnotationGen(((BcelAnnotation) annotation).getBcelAnnotation(), cpool, true)); | |||||
} | } | ||||
field = fg.getField(); | |||||
annotationsAdded = false; // we are now correct again | |||||
// for (int i = 0; i < annotations.length; i++) { | |||||
// AnnotationAJ array_element = annotations[i]; | |||||
// boolean alreadyHasIt = false; | |||||
// for (AnnotationGen gen : alreadyHas) { | |||||
// if (gen.getTypeName().equals(array_element.getTypeName())) { | |||||
// alreadyHasIt = true; | |||||
// break; | |||||
// } | |||||
// } | |||||
// if (!alreadyHasIt) { | |||||
// fg.addAnnotation(new AnnotationGen(((BcelAnnotation) array_element).getBcelAnnotation(), cpg, true)); | |||||
// // } | |||||
// // } | |||||
// } | |||||
field = newFieldGen.getField(); | |||||
annotationsOnFieldObjectAreOutOfDate = false; // we are now correct again | |||||
return field; | return field; | ||||
} | } | ||||
bitflags |= HAS_ANNOTATIONS; | bitflags |= HAS_ANNOTATIONS; | ||||
} | } | ||||
public void removeAnnotation(ResolvedType annotationType) { | |||||
ensureAnnotationsRetrieved(); | |||||
if ((bitflags & HAS_ANNOTATIONS) == 0) { | |||||
// nothing to do, why did we get called? | |||||
} else { | |||||
int len = annotations.length; | |||||
if (len == 1) { | |||||
bitflags &= ~HAS_ANNOTATIONS; | |||||
annotations = null; | |||||
annotationTypes = null; | |||||
return; | |||||
} | |||||
AnnotationAJ[] ret = new AnnotationAJ[len - 1]; | |||||
int p = 0; | |||||
for (AnnotationAJ annotation : annotations) { | |||||
if (!annotation.getType().equals(annotationType)) { | |||||
ret[p++] = annotation; | |||||
} | |||||
} | |||||
annotations = ret; | |||||
ResolvedType[] newAnnotationTypes = new ResolvedType[len - 1]; | |||||
p = 0; | |||||
for (AnnotationAJ annotation : annotations) { | |||||
if (!annotation.getType().equals(annotationType)) { | |||||
newAnnotationTypes[p++] = annotationType; | |||||
} | |||||
} | |||||
annotationTypes = newAnnotationTypes; | |||||
} | |||||
bitflags |= HAS_ANNOTATIONS; | |||||
} | |||||
public static final AnnotationAJ[] NO_PARAMETER_ANNOTATIONS = new AnnotationAJ[] {}; | public static final AnnotationAJ[] NO_PARAMETER_ANNOTATIONS = new AnnotationAJ[] {}; | ||||
public void addParameterAnnotation(int param, AnnotationAJ anno) { | public void addParameterAnnotation(int param, AnnotationAJ anno) { |
if (!problemReported) { | if (!problemReported) { | ||||
AsmRelationshipProvider.addDeclareAnnotationRelationship(world.getModelAsAsmManager(), decA.getSourceLocation(), | AsmRelationshipProvider.addDeclareAnnotationRelationship(world.getModelAsAsmManager(), decA.getSourceLocation(), | ||||
onType.getSourceLocation()); | |||||
onType.getSourceLocation(), false); | |||||
// TAG: WeavingMessage | // TAG: WeavingMessage | ||||
if (!getWorld().getMessageHandler().isIgnoring(IMessage.WEAVEINFO)) { | if (!getWorld().getMessageHandler().isIgnoring(IMessage.WEAVEINFO)) { | ||||
getWorld().getMessageHandler().handleMessage( | getWorld().getMessageHandler().handleMessage( |
import org.aspectj.bridge.IMessage; | import org.aspectj.bridge.IMessage; | ||||
import org.aspectj.bridge.ISourceLocation; | import org.aspectj.bridge.ISourceLocation; | ||||
import org.aspectj.weaver.AjAttribute; | import org.aspectj.weaver.AjAttribute; | ||||
import org.aspectj.weaver.AjAttribute.WeaverVersionInfo; | |||||
import org.aspectj.weaver.AnnotationAJ; | import org.aspectj.weaver.AnnotationAJ; | ||||
import org.aspectj.weaver.BCException; | import org.aspectj.weaver.BCException; | ||||
import org.aspectj.weaver.ISourceContext; | import org.aspectj.weaver.ISourceContext; | ||||
import org.aspectj.weaver.Shadow; | import org.aspectj.weaver.Shadow; | ||||
import org.aspectj.weaver.UnresolvedType; | import org.aspectj.weaver.UnresolvedType; | ||||
import org.aspectj.weaver.WeaverMessages; | import org.aspectj.weaver.WeaverMessages; | ||||
import org.aspectj.weaver.AjAttribute.WeaverVersionInfo; | |||||
import org.aspectj.weaver.tools.Traceable; | import org.aspectj.weaver.tools.Traceable; | ||||
/** | /** | ||||
private InstructionList body; | private InstructionList body; | ||||
private List<Attribute> attributes; | private List<Attribute> attributes; | ||||
private List<AnnotationAJ> newAnnotations; | private List<AnnotationAJ> newAnnotations; | ||||
private List<ResolvedType> annotationsForRemoval; | |||||
private AnnotationAJ[][] newParameterAnnotations; | private AnnotationAJ[][] newParameterAnnotations; | ||||
private final LazyClassGen enclosingClass; | private final LazyClassGen enclosingClass; | ||||
private BcelMethod memberView; | private BcelMethod memberView; | ||||
} | } | ||||
} | } | ||||
public void removeAnnotation(ResolvedType annotationType) { | |||||
initialize(); | |||||
if (memberView == null) { | |||||
// If member view is null, we manage them in newAnnotations | |||||
if (annotationsForRemoval == null) { | |||||
annotationsForRemoval = new ArrayList<ResolvedType>(); | |||||
} | |||||
annotationsForRemoval.add(annotationType); | |||||
} else { | |||||
memberView.removeAnnotation(annotationType); | |||||
} | |||||
} | |||||
public void addParameterAnnotation(int parameterNumber, AnnotationAJ anno) { | public void addParameterAnnotation(int parameterNumber, AnnotationAJ anno) { | ||||
initialize(); | initialize(); | ||||
if (memberView == null) { | if (memberView == null) { | ||||
public boolean hasAnnotation(UnresolvedType annotationType) { | public boolean hasAnnotation(UnresolvedType annotationType) { | ||||
initialize(); | initialize(); | ||||
if (memberView == null) { | if (memberView == null) { | ||||
if (annotationsForRemoval != null) { | |||||
for (ResolvedType at : annotationsForRemoval) { | |||||
if (at.equals(annotationType)) { | |||||
return false; | |||||
} | |||||
} | |||||
} | |||||
// Check local annotations first | // Check local annotations first | ||||
if (newAnnotations != null) { | if (newAnnotations != null) { | ||||
for (AnnotationAJ annotation : newAnnotations) { | for (AnnotationAJ annotation : newAnnotations) { | ||||
savedMethod = gen.getMethod(); | savedMethod = gen.getMethod(); | ||||
return savedMethod; | return savedMethod; | ||||
} catch (ClassGenException e) { | } catch (ClassGenException e) { | ||||
enclosingClass.getBcelObjectType().getResolvedTypeX().getWorld().showMessage( | |||||
IMessage.ERROR, | |||||
WeaverMessages.format(WeaverMessages.PROBLEM_GENERATING_METHOD, this.getClassName(), this.getName(), e | |||||
.getMessage()), this.getMemberView() == null ? null : this.getMemberView().getSourceLocation(), null); | |||||
enclosingClass | |||||
.getBcelObjectType() | |||||
.getResolvedTypeX() | |||||
.getWorld() | |||||
.showMessage( | |||||
IMessage.ERROR, | |||||
WeaverMessages.format(WeaverMessages.PROBLEM_GENERATING_METHOD, this.getClassName(), this.getName(), | |||||
e.getMessage()), | |||||
this.getMemberView() == null ? null : this.getMemberView().getSourceLocation(), null); | |||||
// throw e; PR 70201.... let the normal problem reporting | // throw e; PR 70201.... let the normal problem reporting | ||||
// infrastructure deal with this rather than crashing. | // infrastructure deal with this rather than crashing. | ||||
body = null; | body = null; | ||||
for (int i = 0; i < newParameterAnnotations.length; i++) { | for (int i = 0; i < newParameterAnnotations.length; i++) { | ||||
AnnotationAJ[] annos = newParameterAnnotations[i]; | AnnotationAJ[] annos = newParameterAnnotations[i]; | ||||
for (int j = 0; j < annos.length; j++) { | for (int j = 0; j < annos.length; j++) { | ||||
gen.addParameterAnnotation(i, new AnnotationGen(((BcelAnnotation) annos[j]).getBcelAnnotation(), gen | |||||
.getConstantPool(), true)); | |||||
gen.addParameterAnnotation(i, | |||||
new AnnotationGen(((BcelAnnotation) annos[j]).getBcelAnnotation(), gen.getConstantPool(), true)); | |||||
} | } | ||||
} | } | ||||
} | } | ||||
continue; | continue; | ||||
} | } | ||||
gen.addExceptionHandler(jumpForward(r.getRealStart(), forDeletion), jumpForward(r.getRealEnd(), forDeletion), | gen.addExceptionHandler(jumpForward(r.getRealStart(), forDeletion), jumpForward(r.getRealEnd(), forDeletion), | ||||
jumpForward(r.getHandler(), forDeletion), (r.getCatchType() == null) ? null : (ObjectType) BcelWorld | |||||
.makeBcelType(r.getCatchType())); | |||||
jumpForward(r.getHandler(), forDeletion), | |||||
(r.getCatchType() == null) ? null : (ObjectType) BcelWorld.makeBcelType(r.getCatchType())); | |||||
} | } | ||||
for (InstructionHandle handle : forDeletion) { | for (InstructionHandle handle : forDeletion) { |
import org.aspectj.weaver.ResolvedPointcutDefinition; | import org.aspectj.weaver.ResolvedPointcutDefinition; | ||||
import org.aspectj.weaver.ResolvedType; | import org.aspectj.weaver.ResolvedType; | ||||
import org.aspectj.weaver.ResolvedTypeMunger; | import org.aspectj.weaver.ResolvedTypeMunger; | ||||
import org.aspectj.weaver.ResolvedTypeMunger.Kind; | |||||
import org.aspectj.weaver.Shadow; | import org.aspectj.weaver.Shadow; | ||||
import org.aspectj.weaver.ShadowMunger; | import org.aspectj.weaver.ShadowMunger; | ||||
import org.aspectj.weaver.UnresolvedType; | import org.aspectj.weaver.UnresolvedType; | ||||
import org.aspectj.weaver.World; | import org.aspectj.weaver.World; | ||||
import org.aspectj.weaver.ResolvedTypeMunger.Kind; | |||||
import org.aspectj.weaver.bcel.BcelShadow; | import org.aspectj.weaver.bcel.BcelShadow; | ||||
import org.aspectj.weaver.bcel.BcelTypeMunger; | import org.aspectj.weaver.bcel.BcelTypeMunger; | ||||
import org.aspectj.weaver.patterns.DeclareErrorOrWarning; | import org.aspectj.weaver.patterns.DeclareErrorOrWarning; | ||||
public static final String ANNOTATES = "annotates"; | public static final String ANNOTATES = "annotates"; | ||||
public static final String ANNOTATED_BY = "annotated by"; | public static final String ANNOTATED_BY = "annotated by"; | ||||
// public static final String REMOVES_ANNOTATION = "removes annotation"; | |||||
// public static final String ANNOTATION_REMOVED_BY = "annotated removed by"; | |||||
/** | /** | ||||
* Add a relationship for a declare error or declare warning | * Add a relationship for a declare error or declare warning | ||||
*/ | */ | ||||
((sl.getColumn() == 0) ? ISourceLocation.NO_COLUMN : sl.getColumn()), sl.getContext(), sourceFileName); | ((sl.getColumn() == 0) ? ISourceLocation.NO_COLUMN : sl.getColumn()), sl.getContext(), sourceFileName); | ||||
return sLoc; | return sLoc; | ||||
} | } | ||||
private static ISourceLocation createSourceLocation(String sourcefilename, ResolvedType aspect, ISourceLocation sl) { | private static ISourceLocation createSourceLocation(String sourcefilename, ResolvedType aspect, ISourceLocation sl) { | ||||
ISourceLocation sLoc = new SourceLocation(getBinaryFile(aspect), sl.getLine(), sl.getEndLine(), | ISourceLocation sLoc = new SourceLocation(getBinaryFile(aspect), sl.getLine(), sl.getEndLine(), | ||||
((sl.getColumn() == 0) ? ISourceLocation.NO_COLUMN : sl.getColumn()), sl.getContext(), sourcefilename); | ((sl.getColumn() == 0) ? ISourceLocation.NO_COLUMN : sl.getColumn()), sl.getContext(), sourcefilename); | ||||
* this method if that is the case as they will look the entities up in the structure model. | * this method if that is the case as they will look the entities up in the structure model. | ||||
*/ | */ | ||||
public static void addDeclareAnnotationRelationship(AsmManager model, ISourceLocation declareAnnotationLocation, | public static void addDeclareAnnotationRelationship(AsmManager model, ISourceLocation declareAnnotationLocation, | ||||
ISourceLocation annotatedLocation) { | |||||
ISourceLocation annotatedLocation, boolean isRemove) { | |||||
if (model == null) { | if (model == null) { | ||||
return; | return; | ||||
} | } | ||||
} | } | ||||
IRelationshipMap mapper = model.getRelationshipMap(); | IRelationshipMap mapper = model.getRelationshipMap(); | ||||
// if (isRemove) { | |||||
// IRelationship foreward = mapper.get(sourceHandle, IRelationship.Kind.DECLARE_INTER_TYPE, REMOVES_ANNOTATION, false, | |||||
// true); | |||||
// foreward.addTarget(targetHandle); | |||||
// | |||||
// IRelationship back = mapper | |||||
// .get(targetHandle, IRelationship.Kind.DECLARE_INTER_TYPE, ANNOTATION_REMOVED_BY, false, true); | |||||
// back.addTarget(sourceHandle); | |||||
// if (sourceNode.getSourceLocation() != null) { | |||||
// model.addAspectInEffectThisBuild(sourceNode.getSourceLocation().getSourceFile()); | |||||
// } | |||||
// } else { | |||||
IRelationship foreward = mapper.get(sourceHandle, IRelationship.Kind.DECLARE_INTER_TYPE, ANNOTATES, false, true); | IRelationship foreward = mapper.get(sourceHandle, IRelationship.Kind.DECLARE_INTER_TYPE, ANNOTATES, false, true); | ||||
foreward.addTarget(targetHandle); | foreward.addTarget(targetHandle); | ||||
if (sourceNode.getSourceLocation() != null) { | if (sourceNode.getSourceLocation() != null) { | ||||
model.addAspectInEffectThisBuild(sourceNode.getSourceLocation().getSourceFile()); | model.addAspectInEffectThisBuild(sourceNode.getSourceLocation().getSourceFile()); | ||||
} | } | ||||
// } | |||||
} | } | ||||
/** | /** | ||||
ResolvedType aspect = munger.getDeclaringType(); | ResolvedType aspect = munger.getDeclaringType(); | ||||
// create the class file node | // create the class file node | ||||
IProgramElement classFileNode = new ProgramElement(asm, sourceFileNode.getName(), IProgramElement.Kind.FILE, munger | |||||
.getBinarySourceLocation(aspect.getSourceLocation()), 0, null, null); | |||||
IProgramElement classFileNode = new ProgramElement(asm, sourceFileNode.getName(), IProgramElement.Kind.FILE, | |||||
munger.getBinarySourceLocation(aspect.getSourceLocation()), 0, null, null); | |||||
// create package ipe if one exists.... | // create package ipe if one exists.... | ||||
IProgramElement root = asm.getHierarchy().getRoot(); | IProgramElement root = asm.getHierarchy().getRoot(); | ||||
// null)); | // null)); | ||||
// add and create aspect ipe | // add and create aspect ipe | ||||
IProgramElement aspectNode = new ProgramElement(asm, aspect.getSimpleName(), IProgramElement.Kind.ASPECT, munger | |||||
.getBinarySourceLocation(aspect.getSourceLocation()), aspect.getModifiers(), null, null); | |||||
IProgramElement aspectNode = new ProgramElement(asm, aspect.getSimpleName(), IProgramElement.Kind.ASPECT, | |||||
munger.getBinarySourceLocation(aspect.getSourceLocation()), aspect.getModifiers(), null, null); | |||||
classFileNode.addChild(aspectNode); | classFileNode.addChild(aspectNode); | ||||
String sourcefilename = getSourceFileName(aspect); | String sourcefilename = getSourceFileName(aspect); | ||||
} | } | ||||
private static IProgramElement createAdviceChild(AsmManager model, Advice advice) { | private static IProgramElement createAdviceChild(AsmManager model, Advice advice) { | ||||
IProgramElement adviceNode = new ProgramElement(model, advice.getKind().getName(), IProgramElement.Kind.ADVICE, advice | |||||
.getBinarySourceLocation(advice.getSourceLocation()), advice.getSignature().getModifiers(), null, | |||||
IProgramElement adviceNode = new ProgramElement(model, advice.getKind().getName(), IProgramElement.Kind.ADVICE, | |||||
advice.getBinarySourceLocation(advice.getSourceLocation()), advice.getSignature().getModifiers(), null, | |||||
Collections.EMPTY_LIST); | Collections.EMPTY_LIST); | ||||
adviceNode.setDetails(AsmRelationshipUtils.genPointcutDetails(advice.getPointcut())); | adviceNode.setDetails(AsmRelationshipUtils.genPointcutDetails(advice.getPointcut())); | ||||
adviceNode.setBytecodeName(advice.getSignature().getName()); | adviceNode.setBytecodeName(advice.getSignature().getName()); | ||||
* number info for it, we have to dig through the structure model under the fields' type in order to locate it. | * number info for it, we have to dig through the structure model under the fields' type in order to locate it. | ||||
*/ | */ | ||||
public static void addDeclareAnnotationFieldRelationship(AsmManager model, ISourceLocation declareLocation, | public static void addDeclareAnnotationFieldRelationship(AsmManager model, ISourceLocation declareLocation, | ||||
String affectedTypeName, ResolvedMember affectedFieldName) { | |||||
String affectedTypeName, ResolvedMember affectedFieldName, boolean isRemove) { | |||||
if (model == null) { | if (model == null) { | ||||
return; | return; | ||||
} | } | ||||
return; | return; | ||||
} | } | ||||
IProgramElement fieldElem = hierarchy.findElementForSignature(typeElem, IProgramElement.Kind.FIELD, affectedFieldName | |||||
.getName()); | |||||
IProgramElement fieldElem = hierarchy.findElementForSignature(typeElem, IProgramElement.Kind.FIELD, | |||||
affectedFieldName.getName()); | |||||
if (fieldElem == null) { | if (fieldElem == null) { | ||||
return; | return; | ||||
} | } | ||||
} | } | ||||
IRelationshipMap relmap = model.getRelationshipMap(); | IRelationshipMap relmap = model.getRelationshipMap(); | ||||
// if (isRemove) { | |||||
// IRelationship foreward = relmap.get(sourceHandle, IRelationship.Kind.DECLARE_INTER_TYPE, REMOVES_ANNOTATION, false, | |||||
// true); | |||||
// foreward.addTarget(targetHandle); | |||||
// IRelationship back = relmap | |||||
// .get(targetHandle, IRelationship.Kind.DECLARE_INTER_TYPE, ANNOTATION_REMOVED_BY, false, true); | |||||
// back.addTarget(sourceHandle); | |||||
// } else { | |||||
IRelationship foreward = relmap.get(sourceHandle, IRelationship.Kind.DECLARE_INTER_TYPE, ANNOTATES, false, true); | IRelationship foreward = relmap.get(sourceHandle, IRelationship.Kind.DECLARE_INTER_TYPE, ANNOTATES, false, true); | ||||
foreward.addTarget(targetHandle); | foreward.addTarget(targetHandle); | ||||
IRelationship back = relmap.get(targetHandle, IRelationship.Kind.DECLARE_INTER_TYPE, ANNOTATED_BY, false, true); | IRelationship back = relmap.get(targetHandle, IRelationship.Kind.DECLARE_INTER_TYPE, ANNOTATED_BY, false, true); | ||||
back.addTarget(sourceHandle); | back.addTarget(sourceHandle); | ||||
// } | |||||
} | } | ||||
} | } |