00001 package edu.ksu.cis.bandera.pdgslicer;
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
00036 import ca.mcgill.sable.util.*;
00037 import ca.mcgill.sable.soot.*;
00038 import ca.mcgill.sable.soot.jimple.*;
00039 import edu.ksu.cis.bandera.pdgslicer.exceptions.*;
00040 import edu.ksu.cis.bandera.annotation.*;
00041 import java.util.BitSet;
00042 import java.util.Vector;
00043 import java.util.Enumeration;
00044
00045
00046
00047
00048 public class IndexMaps {
00049
00050
00051
00052 private Map locAssIndex;
00053 private JimpleBody jimpleBody;
00054 private StmtGraph stmtGraph;
00055 private StmtList stmtList;
00056
00057
00058
00059 private StmtList originalStmtList;
00060
00061
00062
00063
00064
00065
00066
00067
00068 private Local paraLocalSet[];
00069
00070
00071
00072
00073
00074
00075
00076 private Stmt paraIdentityStmt[];
00077
00078
00079
00080
00081
00082
00083 private Local thisRefLocal = null;
00084
00085
00086
00087 private Integer thisRefStmtIndex;
00088 private Stmt thisRefStmt;
00089
00090
00091
00092
00093 private Map callSiteMap;
00094 private Fields MOD = new Fields();
00095 private Fields REF = new Fields();
00096
00097
00098
00099 private List specialInvokeList = new ArrayList();
00100
00101
00102
00103
00104
00105 private Map jumpTargetMap = new HashMap();
00106 protected final static int ENTRY = -1;
00107 protected final static int SPECIALEXIT = -2;
00108 protected final static Integer specialExitNode = new Integer(SPECIALEXIT);
00109 public ca.mcgill.sable.soot.SootMethod sootMethod;
00110 protected final static java.lang.Integer EntryNode = new Integer(ENTRY);
00111 private Set returnAnnotations = new ArraySet();
00112
00113
00114
00115
00116
00117
00118
00119
00120 public IndexMaps(SootMethod sm) {
00121 sootMethod = sm;
00122 jimpleBody = (JimpleBody) sootMethod.getBody(Jimple.v());
00123 stmtList = jimpleBody.getStmtList();
00124 originalStmtList = new StmtList(jimpleBody);
00125 originalStmtList.addAll(stmtList);
00126 stmtGraph = new CompleteStmtGraph(stmtList);
00127 buildJumpTargetMap();
00128 buildLocalAssIndexMap();
00129 collectFieldReferences();
00130
00131
00132
00133
00134
00135
00136 collectSpecialInvokes();
00137 buildCallSiteMap();
00138
00139 collectReturnAnnotations();
00140 }
00141
00142
00143
00144
00145
00146
00147 private boolean annotationContainsReturn(Annotation ann) {
00148 Stmt[] statements = ann.getStatements();
00149 for (int i = 0; i < statements.length; i++) {
00150 if ((statements[i] instanceof ReturnStmt) || (statements[i] instanceof ReturnVoidStmt))
00151 return true;
00152 }
00153 return false;
00154 }
00155
00156
00157
00158 private void buildCallSiteMap() {
00159 callSiteMap = new HashMap();
00160 InvokeExpr invokeExpr = null;
00161 for (Iterator stmtIt = stmtList.iterator(); stmtIt.hasNext();) {
00162 Stmt stmt = (Stmt) stmtIt.next();
00163 if (SlicingMethod.isBanderaInvoke(stmt))
00164 continue;
00165 if ((stmt instanceof InvokeStmt))
00166 invokeExpr = (InvokeExpr) ((InvokeStmt) stmt).getInvokeExpr();
00167 else
00168
00169
00170
00171 invokeExpr = getInvokeExprFrom(stmt);
00172 if (invokeExpr != null) {
00173 SootMethod calledMethod;
00174 if (invokeExpr instanceof InterfaceInvokeExpr)
00175 calledMethod = getImplementedMd(invokeExpr);
00176 else
00177 calledMethod = invokeExpr.getMethod();
00178 if (calledMethod == null)
00179 continue;
00180 int modifier = calledMethod.getModifiers();
00181 if (Modifier.isAbstract(modifier)) {
00182 calledMethod = getImplementedMd(calledMethod);
00183 }
00184 if (calledMethod == null)
00185 continue;
00186 String calledMethodSignature = calledMethod.getSignature();
00187 if (InfoAnalysis.nativeMdSig.contains(calledMethod))
00188 continue;
00189 if (calledMethodSignature.startsWith("java.lang.Thread.start()"))
00190 calledMethod = getInvokeMethodForStart(invokeExpr, stmt);
00191 else
00192 if (calledMethodSignature.startsWith("java.") || calledMethodSignature.startsWith("javax."))
00193 continue;
00194 if (calledMethod == null)
00195 continue;
00196 CallSite callSite = new CallSite();
00197 callSite.invokeExpr = invokeExpr;
00198 callSite.callerSootMethod = jimpleBody.getMethod();
00199 callSite.callStmt = stmt;
00200 callSiteMap.put(callSite, calledMethod);
00201 }
00202 }
00203 }
00204
00205
00206
00207 private void buildJumpTargetMap() {
00208 for (Iterator stmtIt = stmtList.iterator(); stmtIt.hasNext();) {
00209 Stmt stmt = (Stmt) stmtIt.next();
00210 if (stmt instanceof GotoStmt) {
00211 Stmt gotoTarget = (Stmt) ((GotoStmt) stmt).getTarget();
00212 putTargetIntoMap(gotoTarget, stmt);
00213 } else
00214 if (stmt instanceof IfStmt) {
00215 Stmt ifTarget = ((IfStmt) stmt).getTarget();
00216 putTargetIntoMap(ifTarget, stmt);
00217 }
00218 }
00219 }
00220
00221
00222
00223
00224
00225 private void buildLocalAssIndexMap() {
00226 int paraCount = sootMethod.getParameterCount();
00227 paraLocalSet = new Local[paraCount];
00228 paraIdentityStmt = new Stmt[paraCount];
00229 locAssIndex = new HashMap();
00230 for (Iterator stmtIt = stmtList.iterator(); stmtIt.hasNext();) {
00231 Stmt stmt = (Stmt) stmtIt.next();
00232 List defBoxes = stmt.getDefBoxes();
00233 for (Iterator boxIt = defBoxes.iterator(); boxIt.hasNext();) {
00234 Value defValue = ((ValueBox) boxIt.next()).getValue();
00235 BitSet defSet = new BitSet(stmtList.size());
00236 defSet.set(stmtList.indexOf(stmt));
00237 if (locAssIndex.containsKey(defValue))
00238 defSet.or((BitSet) locAssIndex.get(defValue));
00239 locAssIndex.put(defValue, defSet);
00240 }
00241 if (stmt instanceof IdentityStmt) {
00242 IdentityStmt defStmt = (IdentityStmt) stmt;
00243 Value rightOp = defStmt.getRightOp();
00244 if (rightOp instanceof ParameterRef) {
00245 Value left = defStmt.getLeftOp();
00246 ParameterRef pr = (ParameterRef) rightOp;
00247 if (left instanceof Local) {
00248 paraLocalSet[pr.getIndex()] = (Local) left;
00249 paraIdentityStmt[pr.getIndex()] = stmt;
00250 } else
00251 throw new BaseValueNonLocalException("parameter ref should be a local variable in method: IndexMaps.buildLocalAssIndexMap()");
00252 } else
00253 if (rightOp instanceof ThisRef) {
00254 Value left = defStmt.getLeftOp();
00255 if (left instanceof Local) {
00256 thisRefLocal = (Local) left;
00257 thisRefStmtIndex = new Integer(stmtList.indexOf(stmt));
00258 thisRefStmt = defStmt;
00259 } else
00260 throw new BaseValueNonLocalException("this ref should be a local variable in method: IndexMaps.buildLocalAssIndexMap()");
00261 }
00262 }
00263 }
00264 }
00265
00266
00267
00268
00269
00270 private void collectFieldReferences() {
00271 Set modStaticFields = new ArraySet();
00272 Set modInstanceFields = new ArraySet();
00273 Set modParaFields = new ArraySet();
00274 Set modOtherInsFds = new ArraySet();
00275 Set refStaticFields = new ArraySet();
00276 Set refInstanceFields = new ArraySet();
00277 Set refParaFields = new ArraySet();
00278 Set refOtherInsFds = new ArraySet();
00279 for (Iterator stmtIt = stmtList.iterator(); stmtIt.hasNext();) {
00280 Stmt originalStmt = (Stmt) stmtIt.next();
00281 Stmt newStmt = originalStmt;
00282 List useBoxes = originalStmt.getUseBoxes();
00283 List defBoxes = originalStmt.getDefBoxes();
00284 Set instanceFdsNotInCurrentClass = new ArraySet();
00285 Set staticFields = new ArraySet();
00286 Set instanceFields = new ArraySet();
00287 Set paraFields = new ArraySet();
00288 for (Iterator varBoxIt = useBoxes.iterator(); varBoxIt.hasNext();) {
00289 Value v = ((ValueBox) varBoxIt.next()).getValue();
00290
00291
00292
00293
00294
00295
00296
00297
00298 if (v instanceof StaticFieldRef)
00299 staticFields.add((StaticFieldRef) v);
00300 else
00301 if (v instanceof InstanceFieldRef) {
00302
00303
00304
00305 InstanceFieldRef insFieldRef = ((InstanceFieldRef) v);
00306 if (Fields.isThisRef(sootMethod, insFieldRef.getBase(), thisRefStmt))
00307 instanceFields.add(insFieldRef);
00308
00309
00310
00311 else
00312 if (isParaField(insFieldRef, newStmt))
00313 paraFields.add(insFieldRef);
00314 else
00315 instanceFdsNotInCurrentClass.add(insFieldRef);
00316 }
00317 }
00318 if (staticFields.size() != 0) {
00319 DataBox newdbx = new DataBox(originalStmt, staticFields);
00320 refStaticFields.add(newdbx);
00321 }
00322 if (instanceFields.size() != 0) {
00323 DataBox newdbx = new DataBox(originalStmt, instanceFields);
00324 refInstanceFields.add(newdbx);
00325 }
00326 if (paraFields.size() != 0) {
00327 DataBox newdbx = new DataBox(originalStmt, paraFields);
00328 refParaFields.add(newdbx);
00329 }
00330 if (!instanceFdsNotInCurrentClass.isEmpty()) {
00331 DataBox newdbx = new DataBox(originalStmt, instanceFdsNotInCurrentClass);
00332 refOtherInsFds.add(newdbx);
00333 }
00334 staticFields = new ArraySet();
00335 instanceFields = new ArraySet();
00336 paraFields = new ArraySet();
00337 instanceFdsNotInCurrentClass = new ArraySet();
00338 newStmt = originalStmt;
00339 for (Iterator varBoxIt = defBoxes.iterator(); varBoxIt.hasNext();) {
00340 Value v = ((ValueBox) varBoxIt.next()).getValue();
00341
00342
00343
00344
00345
00346
00347
00348
00349 if (v instanceof StaticFieldRef)
00350 staticFields.add((StaticFieldRef) v);
00351 else
00352 if (v instanceof InstanceFieldRef) {
00353 InstanceFieldRef insFieldRef = ((InstanceFieldRef) v);
00354 if (Fields.isThisRef(sootMethod, insFieldRef.getBase(), thisRefStmt))
00355 instanceFields.add(insFieldRef);
00356 else
00357 if (isParaField(insFieldRef, newStmt))
00358 paraFields.add(insFieldRef);
00359 else
00360 instanceFdsNotInCurrentClass.add(insFieldRef);
00361 }
00362 }
00363 if (staticFields.size() != 0) {
00364 DataBox newdbx = new DataBox(originalStmt, staticFields);
00365 modStaticFields.add(newdbx);
00366 }
00367 if (instanceFields.size() != 0) {
00368 DataBox newdbx = new DataBox(originalStmt, instanceFields);
00369 modInstanceFields.add(newdbx);
00370 }
00371 if (paraFields.size() != 0) {
00372 DataBox newdbx = new DataBox(originalStmt, paraFields);
00373 modParaFields.add(newdbx);
00374 }
00375 if (!instanceFdsNotInCurrentClass.isEmpty()) {
00376 DataBox newdbx = new DataBox(originalStmt, instanceFdsNotInCurrentClass);
00377 modOtherInsFds.add(newdbx);
00378 }
00379 }
00380 MOD.staticFields = modStaticFields;
00381 MOD.instanceFields = modInstanceFields;
00382 MOD.paraFields = modParaFields;
00383 MOD.otherInsFds = modOtherInsFds;
00384 REF.staticFields = refStaticFields;
00385 REF.instanceFields = refInstanceFields;
00386 REF.paraFields = refParaFields;
00387 REF.otherInsFds = refOtherInsFds;
00388 }
00389
00390
00391
00392
00393 private void collectReturnAnnotations() {
00394 SootClass sc= sootMethod.getDeclaringClass();
00395
00396
00397
00398
00399
00400 Annotation annForSm = Slicer.annManagerForSlicer.getAnnotation(sootMethod.getDeclaringClass(), sootMethod);
00401 Vector currentCFANNs = annForSm.getAllAnnotations(true);
00402 for (Enumeration e = currentCFANNs.elements(); e.hasMoreElements();) {
00403 Annotation cfann = (Annotation) e.nextElement();
00404 if (annotationContainsReturn(cfann))
00405 returnAnnotations.add(cfann);
00406 }
00407 }
00408
00409
00410
00411 private void collectSpecialInvokes() {
00412 for (Iterator stmtIt = stmtList.iterator(); stmtIt.hasNext();) {
00413 InvokeExpr invokeExpr = null;
00414 Stmt stmt = (Stmt) stmtIt.next();
00415 if (stmt instanceof InvokeStmt) {
00416 Value invokeValue = ((InvokeStmt) stmt).getInvokeExpr();
00417 invokeExpr = (InvokeExpr) invokeValue;
00418 }
00419
00420
00421
00422
00423
00424
00425
00426
00427
00428 if (invokeExpr != null)
00429 if (invokeExpr instanceof SpecialInvokeExpr)
00430 specialInvokeList.add(stmt);
00431 }
00432 }
00433
00434
00435
00436
00437 public BitSet exitNodes() {
00438 BitSet exitNodeSet = new BitSet(stmtList.size());
00439 List tails = stmtGraph.getTails();
00440 for (Iterator tailIt = tails.iterator(); tailIt.hasNext();) {
00441 Stmt tail = (Stmt) tailIt.next();
00442 exitNodeSet.set(stmtList.indexOf(tail));
00443 }
00444
00445
00446
00447
00448
00449
00450
00451
00452
00453 for (Iterator stmtIt = stmtList.iterator(); stmtIt.hasNext();) {
00454 Stmt retStmt = (Stmt) stmtIt.next();
00455 if ((retStmt instanceof ReturnStmt) || (retStmt instanceof ReturnVoidStmt) || (retStmt instanceof ThrowStmt)) {
00456 List succs = stmtGraph.getSuccsOf(retStmt);
00457 if (succs.size() != 0)
00458
00459
00460
00461 exitNodeSet.set(stmtList.indexOf(retStmt));
00462 }
00463 }
00464 return exitNodeSet;
00465 }
00466
00467
00468
00469
00470
00471
00472 public BitSet exitNodesWithoutThrow(BitSet exitNodeSet) {
00473
00474 BitSet nodeSet = (BitSet) exitNodeSet.clone();
00475 for (int i = 0; i < exitNodeSet.size(); i++) {
00476 if (! exitNodeSet.get(i))
00477 continue;
00478 Stmt exitStmt = (Stmt) stmtList.get(i);
00479 if (exitStmt instanceof ThrowStmt)
00480 nodeSet.clear(i);
00481 }
00482 return nodeSet;
00483 }
00484
00485
00486
00487
00488
00489 public Map getCallSiteMap()
00490 {
00491 return callSiteMap;
00492 }
00493
00494
00495
00496
00497
00498
00499 private BitSet getDefSetFrom(Value basev)
00500 {
00501 String baseStr = basev.toString();
00502 for (Iterator keyIt = locAssIndex.keySet().iterator(); keyIt.hasNext();)
00503 {
00504 Value keyValue = (Value) keyIt.next();
00505 if (keyValue.toString().equals(baseStr)) return ((BitSet) locAssIndex.get(keyValue));
00506 }
00507 return null;
00508 }
00509
00510
00511
00512
00513
00514
00515
00516
00517 private SootMethod getImplementedMd(InvokeExpr invokeExp) {
00518 SootMethod sm = invokeExp.getMethod();
00519 SootClass interfaceClass = sm.getDeclaringClass();
00520 Set implementingClassSet = (Set) Slicer.interfaceImplementedByMap.get(interfaceClass);
00521 if (implementingClassSet == null || implementingClassSet.isEmpty())
00522 return null;
00523 SootClass implementingClass = getImplementingClassByBOFA(implementingClassSet);
00524 SootMethod impMd = implementingClass.getMethod(sm.getName(), sm.getParameterTypes());
00525 return impMd;
00526 }
00527
00528
00529
00530
00531
00532
00533 private SootMethod getImplementedMd(SootMethod abstractMd) {
00534 SootClass interfaceClass = abstractMd.getDeclaringClass();
00535 Set implementingClassSet = (Set) Slicer.interfaceImplementedByMap.get(interfaceClass);
00536 if (implementingClassSet == null || implementingClassSet.isEmpty())
00537 return null;
00538 SootClass implementingClass = getImplementingClassByBOFA(implementingClassSet);
00539 SootMethod impMd = implementingClass.getMethod(abstractMd.getName(), abstractMd.getParameterTypes());
00540 return impMd;
00541 }
00542
00543
00544
00545
00546
00547
00548 private SootClass getImplementingClassByBOFA(Set impClasses) {
00549 SootClass returnClass = null;
00550 for (Iterator impIt = impClasses.iterator(); impIt.hasNext();) {
00551 returnClass = (SootClass) impIt.next();
00552 break;
00553 }
00554 return returnClass;
00555 }
00556
00557
00558
00559
00560
00561
00562
00563 private InvokeExpr getInvokeExprFrom(Stmt stmt) {
00564
00565 InvokeExpr invokeExpr = null;
00566 for (Iterator useBoxIt = stmt.getUseBoxes().iterator(); useBoxIt.hasNext();) {
00567 Value useValue = ((ValueBox) useBoxIt.next()).getValue();
00568 if (useValue instanceof InvokeExpr)
00569 return ((InvokeExpr) useValue);
00570 }
00571 return invokeExpr;
00572 }
00573
00574
00575
00576
00577
00578
00579
00580
00581
00582
00583
00584
00585
00586
00587
00588
00589
00590
00591
00592
00593
00594
00595
00596
00597
00598
00599
00600 private SootMethod getInvokeMethodForStart(InvokeExpr invokeExpr, Stmt invokeStmt) {
00601 SootMethod returnMd = null;
00602 List paraList = new ArrayList();
00603 if (invokeExpr instanceof StaticInvokeExpr)
00604 throw new SlicerException("the invokeExpr of start should be nonStaticInvokeExpr");
00605 NonStaticInvokeExpr startInvoke = (NonStaticInvokeExpr) invokeExpr;
00606 Type baseType = startInvoke.getBase().getType();
00607
00608 if (baseType instanceof RefType) {
00609 if (baseType.toString().equals("java.lang.Thread")) {
00610
00611 SootClass sootClass = lookupSootClassByThread(startInvoke, invokeStmt);
00612 while (returnMd == null) {
00613 if (sootClass != null) {
00614 try {
00615 returnMd = sootClass.getMethod("run", paraList);
00616 } catch (ca.mcgill.sable.soot.NoSuchMethodException nsme) {
00617 sootClass = sootClass.getSuperClass();
00618 }
00619 } else
00620 return returnMd;
00621 }
00622
00623
00624 } else {
00625 SootClass sootClass = lookupSootClassByName(((RefType) baseType).className);
00626 while (returnMd == null) {
00627 if (sootClass != null) {
00628 try {
00629 returnMd = sootClass.getMethod("run", paraList);
00630 } catch (ca.mcgill.sable.soot.NoSuchMethodException nsme) {
00631 sootClass = sootClass.getSuperClass();
00632 }
00633 } else
00634 return returnMd;
00635 }
00636 }
00637 } else
00638 throw new SlicerException("the base type of invokeExpr should be RefType");
00639 return returnMd;
00640 }
00641
00642
00643
00644
00645
00646 public Map getJumpTargetMap()
00647 {
00648 return jumpTargetMap;
00649 }
00650
00651
00652
00653
00654
00655 Fields getMOD()
00656 {
00657 return MOD;
00658 }
00659
00660
00661
00662
00663
00664 StmtList getOriginalStmtList() {
00665 return originalStmtList;
00666 }
00667
00668
00669
00670
00671
00672 Stmt [] getParaIdentityStmts()
00673 {
00674 return paraIdentityStmt;
00675 }
00676
00677
00678
00679
00680
00681 Local[] getParaLocalSet()
00682 {
00683 return paraLocalSet;
00684 }
00685
00686
00687
00688
00689
00690 Fields getREF()
00691 {
00692 return REF;
00693 }
00694
00695
00696
00697
00698
00699 Set getReturnAnnotations() {
00700 return returnAnnotations;
00701 }
00702
00703
00704
00705
00706
00707
00708
00709
00710 private InvokeStmt getSpecialInvokeFor(Value base) {
00711 for (Iterator specIt = specialInvokeList.iterator(); specIt.hasNext();) {
00712 InvokeStmt specInvoke = (InvokeStmt) specIt.next();
00713 SpecialInvokeExpr specExpr = (SpecialInvokeExpr) specInvoke.getInvokeExpr();
00714 if (base == specExpr.getBase()) {
00715 String signature = specExpr.getMethod().getSignature();
00716 if (signature.startsWith("java.lang.Thread.<init>"))
00717 return ((InvokeStmt) (specInvoke));
00718 }
00719 }
00720 return null;
00721 }
00722
00723
00724
00725
00726
00727
00728
00729
00730
00731
00732
00733
00734
00735
00736
00737
00738
00739
00740
00741 private InvokeStmt getSpecialInvokeForThread(Value base, Stmt invokeStmt) {
00742 boolean found = false;
00743 List baseList = new ArrayList();
00744 baseList.add(base);
00745 Set visitedBase = new ArraySet();
00746 InvokeStmt specInvoke = null;
00747 while (!found) {
00748 if (baseList.isEmpty())
00749 found = true;
00750 else {
00751 Value baseV = (Value) baseList.remove(0);
00752 specInvoke = getSpecialInvokeFor(baseV);
00753 if (specInvoke != null)
00754 found = true;
00755 else {
00756 visitedBase.add(baseV);
00757 BitSet defSet = null;
00758 if (baseV instanceof Local)
00759 defSet = (BitSet) locAssIndex.get(baseV);
00760 else
00761 defSet = getDefSetFrom(baseV);
00762 if (defSet == null)
00763 continue;
00764 Set defStmtSet = SetUtil.bitSetToStmtSet(defSet, stmtList);
00765 for (Iterator defIt = defStmtSet.iterator(); defIt.hasNext();) {
00766 Stmt defStmt = (Stmt) defIt.next();
00767 List reachableStmts = SlicingMethod.reachableStmtFrom(defStmt, stmtGraph);
00768 if (!reachableStmts.contains(invokeStmt))
00769 continue;
00770 if (!(defStmt instanceof AssignStmt))
00771 continue;
00772 AssignStmt assDefStmt = (AssignStmt) defStmt;
00773 Value rightOp = assDefStmt.getRightOp();
00774 if (visitedBase.contains(rightOp))
00775 continue;
00776 if (baseList.contains(rightOp))
00777 continue;
00778 baseList.add(rightOp);
00779 }
00780 }
00781 }
00782 }
00783 return specInvoke;
00784 }
00785
00786
00787
00788
00789
00790
00791
00792
00793 List getSpecialInvokeList()
00794 {
00795 return specialInvokeList;
00796 }
00797
00798
00799
00800
00801
00802 public StmtGraph getStmtGraph()
00803 {
00804 return stmtGraph;
00805 }
00806
00807
00808
00809
00810
00811 StmtList getStmtList() {
00812 return stmtList;
00813 }
00814
00815
00816
00817
00818
00819 Local getThisRefLocal()
00820 {
00821 return thisRefLocal;
00822 }
00823
00824
00825
00826
00827
00828 Stmt getThisRefStmt() {
00829 return thisRefStmt;
00830 }
00831
00832
00833
00834
00835
00836 Integer getThisRefStmtIndex() {
00837 return thisRefStmtIndex;
00838 }
00839
00840
00841
00842
00843
00844
00845
00846
00847 BitSet indexSetWithoutExceptionHandling()
00848 {
00849 LinkedList workList = new LinkedList();
00850 BitSet indexSet = new BitSet(stmtList.size());
00851
00852 workList.addFirst(new Integer(0));
00853
00854 while (workList.size() != 0)
00855 {
00856 int nodeIndex = ((Integer) workList.removeFirst()).intValue();
00857 indexSet.set(nodeIndex);
00858 Stmt nodeStmt = (Stmt) stmtList.get(nodeIndex);
00859 List nodeStmtSuccs = stmtGraph.getSuccsOf(nodeStmt);
00860 List newSuccs = removeExceptionCaught(nodeStmtSuccs);
00861 for (Iterator succIt = newSuccs.iterator();succIt.hasNext();)
00862 {
00863 Stmt succStmt = (Stmt) succIt.next();
00864 int succIndex = stmtList.indexOf(succStmt);
00865 if (workList.contains(new Integer(succIndex)) || indexSet.get(succIndex))
00866 {
00867 }
00868 else workList.addLast(new Integer(succIndex));
00869 }
00870 }
00871 return indexSet;
00872 }
00873
00874
00875
00876
00877
00878
00879
00880
00881
00882
00883
00884
00885
00886
00887
00888
00889
00890
00891 boolean isParaField(InstanceFieldRef fieldRef, Stmt stmt) {
00892
00893 Value base = fieldRef.getBase();
00894 Local baseLocal = null;
00895 if (base instanceof Local) {
00896 baseLocal = (Local) base;
00897 } else
00898 throw new BaseValueNonLocalException("the base of field reference should be local in the method isParaField() in IndexMaps.java");
00899 return isParaField(baseLocal, stmt);
00900 }
00901
00902
00903
00904 boolean isParaField(Local baseLocal, Stmt stmt) {
00905 Set paraLocalObjects = new ArraySet();
00906 for (int i = 0; i < paraLocalSet.length; i++) {
00907 Local paraLocal = paraLocalSet[i];
00908 Type paraType = paraLocal.getType();
00909 if (paraType instanceof BaseType)
00910 if (paraType instanceof RefType)
00911 paraLocalObjects.add(paraLocal);
00912 }
00913 SimpleLocalCopies simpleLocalCopies = new SimpleLocalCopies((CompleteStmtGraph) stmtGraph);
00914 for (Iterator j = paraLocalObjects.iterator(); j.hasNext();) {
00915 Local paraObj = (Local) j.next();
00916 if (simpleLocalCopies.isLocalCopyOfBefore(baseLocal, paraObj, stmt)) {
00917 return true;
00918 } else
00919 if (baseLocal.equals(paraObj))
00920 return true;
00921 }
00922 return false;
00923 }
00924
00925
00926
00927
00928
00929 public Map localAssMap()
00930 {
00931 return locAssIndex;
00932 }
00933
00934
00935
00936
00937
00938
00939
00940
00941
00942 public static SootClass lookupSootClassByName(String className) {
00943 SootClass classArray[] = Slicer.relevantClassArray;
00944 for (int i = 0; i < classArray.length; i++)
00945 if (classArray[i].getName().equals(className))
00946 return classArray[i];
00947 return null;
00948
00949 }
00950
00951
00952
00953
00954
00955
00956
00957
00958
00959
00960
00961
00962
00963
00964
00965
00966
00967
00968
00969
00970
00971
00972
00973
00974
00975
00976
00977
00978 private SootClass lookupSootClassByThread(NonStaticInvokeExpr startInvoke, Stmt invokeStmt) {
00979 Value base = startInvoke.getBase();
00980
00981 InvokeStmt sInvokeStmt = getSpecialInvokeForThread(base, invokeStmt);
00982 if (sInvokeStmt == null)
00983 return null;
00984 SpecialInvokeExpr sInvoke = (SpecialInvokeExpr) sInvokeStmt.getInvokeExpr();
00985
00986
00987
00988
00989
00990 for (int i = 0; i < sInvoke.getArgCount(); i++) {
00991 Value arg = sInvoke.getArg(i);
00992 Type argType = arg.getType();
00993 if (argType instanceof RefType) {
00994 if (argType.toString().equals("java.lang.Runnable")) {
00995
00996 SimpleLocalDefs simpleLocalDefs = new SimpleLocalDefs((CompleteStmtGraph) stmtGraph);
00997 Local argLocal = (Local) arg;
00998 List defList = simpleLocalDefs.getDefsOfAt(argLocal, sInvokeStmt);
00999 for (Iterator defIt = defList.iterator(); defIt.hasNext();) {
01000 DefinitionStmt oneDef = (DefinitionStmt) defIt.next();
01001 Value rightOp = oneDef.getRightOp();
01002 if (!(rightOp instanceof NewExpr))
01003 continue;
01004 NewExpr newExpr = (NewExpr) rightOp;
01005 Type opType = newExpr.getType();
01006 SootClass sootClass = lookupSootClassByName(opType.toString());
01007 if (sootClass != null) {
01008 if (sootClass.implementsInterface("java.lang.Runnable"))
01009 return sootClass;
01010 else
01011 if (sootClass.getSuperClass().getName().equals("java.lang.Thread"))
01012 return sootClass;
01013 }
01014 }
01015 throw new SlicerException("can not find the SootClass by allocator");
01016 } else {
01017 SootClass sootClass = lookupSootClassByName(((RefType) argType).className);
01018 if (sootClass != null) {
01019 if (sootClass.implementsInterface("java.lang.Runnable"))
01020 return sootClass;
01021 else
01022 if (sootClass.getSuperClass().getName().equals("java.lang.Thread"))
01023 return sootClass;
01024 }
01025 }
01026 }
01027 }
01028 return null;
01029 }
01030
01031
01032
01033
01034
01035
01036
01037 private void putTargetIntoMap(Stmt target, Stmt source) {
01038 BitSet sourceSet;
01039 if (jumpTargetMap.containsKey(target))
01040 sourceSet = (BitSet) jumpTargetMap.get(target);
01041 else
01042 sourceSet = new BitSet(stmtList.size());
01043 sourceSet.set(stmtList.indexOf(source));
01044 jumpTargetMap.put(target, sourceSet);
01045 }
01046
01047
01048
01049
01050
01051
01052
01053 private List removeExceptionCaught(List actualSuccs)
01054 {
01055 List newSuccs = new ArrayList();
01056 Iterator asuccsIt = actualSuccs.iterator();
01057 while (asuccsIt.hasNext())
01058 {
01059 Stmt succStmt = (Stmt) asuccsIt.next();
01060 if (!jimpleBody.getTraps().contains(succStmt))
01061 newSuccs.add(succStmt);
01062 }
01063
01064 return newSuccs;
01065 }
01066 }