//Find fields containing the @Type annotation and add to map
Collection<SootField> fields = sootClass.getFields();
for (SootField field : fields) {
if (field.hasTag("VisibilityAnnotationTag")) {
VisibilityAnnotationTag vat = (VisibilityAnnotationTag)field.getTag("VisibilityAnnotationTag");
Automaton automaton = getAutomatonFromTag(vat);
if (automaton != null) {
fieldAutomatonMap.put(field, automaton);
}
}
//Remove all tags from field. JSA tags will be added later
field.removeAllTags();
}
//Find methods containing @Type or @LoadType annotation and add to map
Collection<SootMethod> methods = sootClass.getMethods();
for (SootMethod m : methods) {
//Find return annotation
if (isStringType(m.getReturnType())) {
VisibilityAnnotationTag vat = (VisibilityAnnotationTag)m.getTag("VisibilityAnnotationTag");
if (vat != null) {
Automaton automaton = getAutomatonFromTag(vat);
if (automaton != null) {
returnAutomatonMap.put(m, automaton);
}
}
}
//Find parameter annotations
int count = m.getParameterCount();
for (int i = 0; i<count; i++) {
if (isStringType(m.getParameterType(i))) {
VisibilityParameterAnnotationTag vpat = (VisibilityParameterAnnotationTag)m.getTag("VisibilityParameterAnnotationTag");
if (vpat != null) {
VisibilityAnnotationTag vat = vpat.getVisibilityAnnotations().get(i);
Automaton automaton = getAutomatonFromTag(vat);
if (automaton != null) {
Map<Integer,Automaton> pMap;
if (parameterAutomatonMap.containsKey(m)) {
pMap = parameterAutomatonMap.get(m);
}
else {
pMap = new HashMap<Integer,Automaton>();
parameterAutomatonMap.put(m, pMap);
}
pMap.put(i, automaton);
}
}
}
}
//Remove all tags from method. JSA tags will be added later
m.removeAllTags();
}
}
// apply inheritance relations to construct the 'full' maps
for (SootClass sootClass : classes) {
for (SootMethod m1 : sootClass.getMethods()) {
Automaton m1Returns = returnAutomatonMap.get(m1);
Map<Integer, Automaton> m1Parameters = parameterAutomatonMap.get(m1);
//if (m1Returns == null && m1Parameters == null)
// continue;
if (m1Parameters == null)
m1Parameters = Collections.emptyMap();
for (SootMethod m2 : (List<SootMethod>)h.resolveAbstractDispatch(sootClass, m1)) {
// HANDLE RETURN TYPES
if (m1Returns != null) {
inheritReturnType(m1, m1Returns, m2);
}
// HANDLE PARAMETER TYPES
//if (m1Parameters != null) {
if (!parameterAutomatonMapFull.containsKey(m2)) {
parameterAutomatonMapFull.put(m2, new HashMap<Integer,Automaton>());
}
for (int i=0; i<m1.getParameterCount(); i++) {
Automaton m1Parameter = m1Parameters.get(i);
if (m1Parameter == null) {
// ensure that the child's parameter has no annotation
Map<Integer,Automaton> m2Parameters = parameterAutomatonMap.get(m2);
if (m2Parameters != null && m2Parameters.containsKey(i)) {
errorSuperParameterNotAnnotated(m2, m1, i);