00001 package edu.ksu.cis.bandera.annotation;
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035 import edu.ksu.cis.bandera.jjjc.node.*;
00036 import edu.ksu.cis.bandera.jjjc.util.*;
00037 import ca.mcgill.sable.soot.jimple.*;
00038 import ca.mcgill.sable.util.*;
00039 import java.util.*;
00040 public class SwitchStmtAnnotation extends ConditionalAnnotation {
00041 private Hashtable switchCases = new Hashtable();
00042 private Annotation defaultAnnotation = null;
00043 private Vector values = new Vector();
00044
00045
00046
00047
00048 public SwitchStmtAnnotation(Node node) {
00049 super(node);
00050 }
00051
00052
00053
00054
00055
00056 public void addSwitchCase(Integer value, Annotation annotation) {
00057 annotation.setParent(this);
00058 switchCases.put(value, annotation);
00059 values.addElement(value);
00060 }
00061 public void apply(Switch sw)
00062 {
00063 ((AnnotationSwitch) sw).caseSwitchStmtAnnotation(this);
00064 }
00065
00066
00067
00068
00069 public Object clone() {
00070 SwitchStmtAnnotation result = new SwitchStmtAnnotation((Node) node.clone());
00071
00072
00073
00074
00075
00076
00077
00078 for (Enumeration e = values.elements(); e.hasMoreElements();) {
00079 Integer value = (Integer) e.nextElement();
00080 Annotation a = (Annotation) ((Annotation) switchCases.get(value)).clone();
00081 result.addSwitchCase(new Integer(value.intValue()), a);
00082 }
00083
00084 return result;
00085 }
00086
00087
00088
00089
00090
00091 public Vector getAllAnnotations(boolean includeSequential) {
00092 Vector result = new Vector();
00093 result.addElement(this);
00094 for (Enumeration e = values.elements(); e.hasMoreElements();) {
00095 for (Enumeration e2 = ((Annotation) switchCases.get(e.nextElement())).getAllAnnotations(includeSequential).elements();
00096 e2.hasMoreElements();) {
00097 result.addElement(e2.nextElement());
00098 }
00099 }
00100 return result;
00101 }
00102
00103
00104
00105
00106
00107 public Annotation getContainingAnnotation(Stmt stmt) throws AnnotationException {
00108 Vector result = new Vector();
00109
00110 if (contains(stmt)) result.addElement(this);
00111
00112 if (defaultAnnotation != null) {
00113 Annotation a = defaultAnnotation.getContainingAnnotation(stmt);
00114 if ((a != null) && !result.contains(a)) result.addElement(a);
00115 }
00116
00117 for (Enumeration e = switchCases.elements(); e.hasMoreElements();) {
00118 Annotation a = ((Annotation) e.nextElement()).getContainingAnnotation(stmt);
00119 if ((a != null) && !result.contains(a)) result.addElement(a);
00120 }
00121
00122 int size = result.size();
00123 if (size == 0) return null;
00124 else if (size == 1) return (Annotation) result.elementAt(0);
00125 throw new AnnotationException("Statement " + stmt + " is contained in two or more annotations");
00126 }
00127
00128
00129
00130
00131 public Annotation getDefaultAnnotation() {
00132 return defaultAnnotation;
00133 }
00134
00135
00136
00137
00138 public Stmt[] getStatements() {
00139 Vector result = new Vector();
00140
00141 Stmt[] switchStmts = toArray();
00142
00143 for (int i = 0; i < switchStmts.length; i++) {
00144 result.addElement(switchStmts[i]);
00145 }
00146
00147 Vector generated = new Vector();
00148
00149 for (Enumeration e = values.elements(); e.hasMoreElements();) {
00150 Annotation a = ((Annotation) switchCases.get(e.nextElement()));
00151 if (!generated.contains(a)) {
00152 generated.addElement(a);
00153 Stmt[] stmts = a.getStatements();
00154 for (int i = 0; i < stmts.length; i++) {
00155 result.addElement(stmts[i]);
00156 }
00157 }
00158 }
00159
00160 if (defaultAnnotation != null) {
00161 Stmt[] stmts = defaultAnnotation.getStatements();
00162 for (int i = 0; i < stmts.length; i++) {
00163 result.addElement(stmts[i]);
00164 }
00165 }
00166
00167 Stmt[] stmts = new Stmt[result.size()];
00168
00169 for (int i = 0; i < stmts.length; i++) {
00170 stmts[i] = (Stmt) result.elementAt(i);
00171 }
00172
00173 return stmts;
00174 }
00175
00176
00177
00178
00179 public Hashtable getSwitchCases() {
00180 return switchCases;
00181 }
00182
00183
00184
00185
00186 public Vector getValues() {
00187 return values;
00188 }
00189
00190
00191
00192
00193
00194 public boolean removeStmt(Stmt stmt) throws AnnotationException {
00195 Annotation a = getContainingAnnotation(stmt);
00196 if (a == null) return false;
00197 else if (a == this) return remove(stmt);
00198 else return a.removeStmt(stmt);
00199 }
00200
00201
00202
00203
00204
00205 public boolean removeStmtByMark(Stmt stmt) throws AnnotationException {
00206 Annotation a = getContainingAnnotation(stmt);
00207 if (a == null) return false;
00208 else if (a == this) return removeByMark(stmt);
00209 else return a.removeStmtByMark(stmt);
00210 }
00211
00212
00213
00214
00215
00216 public boolean removeSwitchCase(Integer value) {
00217 return (switchCases.remove(value) != null);
00218 }
00219
00220
00221
00222
00223
00224
00225 public boolean replaceStmt(Stmt oldStmt, Stmt newStmt) throws AnnotationException {
00226 Annotation a = getContainingAnnotation(oldStmt);
00227 if (a == null) return false;
00228 else if (a == this) return replace(oldStmt, newStmt);
00229 else return a.replaceStmt(oldStmt, newStmt);
00230 }
00231
00232
00233
00234
00235
00236
00237 public boolean replaceStmtByMark(Stmt oldStmt, Stmt newStmt) throws AnnotationException {
00238 Annotation a = getContainingAnnotation(oldStmt);
00239 if (a == null) return false;
00240 else if (a == this) return replaceByMark(oldStmt, newStmt);
00241 else return a.replaceStmtByMark(oldStmt, newStmt);
00242 }
00243
00244
00245
00246
00247 public void setDefaultAnnotation(Annotation annotation) {
00248 defaultAnnotation = annotation;
00249 defaultAnnotation.setParent(this);
00250 }
00251
00252
00253
00254
00255 public void setSwitchCases(Hashtable table) {
00256 switchCases = table;
00257 }
00258
00259
00260
00261
00262 public void setValues(Vector values) {
00263 this.values = values;
00264 }
00265
00266
00267
00268
00269 public String toString() {
00270 return "switch (" + ((ASwitchStmt) node).getExp().toString().trim() + ")";
00271 }
00272
00273
00274
00275
00276 public void validate(JimpleBody body) {
00277 super.validate(body);
00278
00279 for (Enumeration e = switchCases.elements(); e.hasMoreElements();) {
00280 ((Statements) e.nextElement()).validate(body);
00281 }
00282
00283 if (defaultAnnotation != null) defaultAnnotation.validate(body);
00284 }
00285 }