Main Page   Packages   Class Hierarchy   Alphabetical List   Compound List   File List   Compound Members  

PredicateImpl.java

00001 package edu.ksu.cis.bandera.abstraction.predicate.parser;
00002 
00003 /**
00004  * Predicate data structure.
00005  * Creation date: (4/15/01 1:20:34 AM)
00006  * @author: Roby Joehanes
00007  */
00008 import java.util.*;
00009 import ca.mcgill.sable.soot.*;
00010 import ca.mcgill.sable.soot.jimple.*;
00011 import ca.mcgill.sable.soot.grimp.*;
00012 
00013 public class PredicateImpl implements Predicate {
00014     private String name;
00015     private Value v = null;
00016     private SootClass cls = null;
00017     private SootMethod method = null;
00018     private boolean global = false;
00019     private SimpleNode ast = null;
00020     private String methodName = null;
00021     private String className = null;
00022     private List args = null;
00023     public PredicateImpl() {}
00024 /**
00025  * Predicate constructor comment.
00026  */
00027 public PredicateImpl(String n) {
00028     name = n;
00029 }
00030 public SootClass getClassContext()
00031 {
00032     if (cls == null) cls = PredicateProcessor.getSootClass(className);
00033     return cls;
00034 }
00035 public String getClassName() { return className; }
00036 /**
00037  * 
00038  * @return ca.mcgill.sable.soot.jimple.Value
00039  */
00040 public Value getExpr() {
00041     return v;
00042 }
00043     public SimpleNode getExprAST() { return ast; }
00044 public SootMethod getMethodContext()
00045 {
00046     if (method == null)
00047     {
00048         method = PredicateProcessor.getSootMethod(className, methodName, args);
00049     }
00050     return method;
00051 }
00052 /**
00053  * 
00054  * @return java.lang.String
00055  */
00056 public String getName() {
00057     return name;
00058 }
00059 public boolean isGlobal() { return global; }
00060 public void resolveArgs(PredicateProcessor v)
00061 {
00062     LinkedList ll = new LinkedList();
00063     for (Iterator i = args.iterator(); i.hasNext();)
00064     {
00065         ll.addLast(((ASTType) i.next()).jjtAccept(v, this));
00066     }
00067     args = ll;
00068 }
00069 public void setClassContext(String s)
00070 {
00071     className = s;
00072 }
00073 public void setContext(SootClass sc, SootMethod sm)
00074 {
00075     if (sc == null) throw new RuntimeException("Cannot set null context on predicates!");
00076     if (isGlobal())
00077     {
00078         if (sm == null)
00079         {
00080             // Another field access, so we ignore it
00081             return;
00082         }
00083         if (method != null)
00084             throw new RuntimeException("Local access can't be brought into global scope! It's a bug!!");
00085 
00086         // At this point, we're certain that the global scope can only happen
00087         // on access fields between two classes. Now, the newly introduced
00088         // scope has a local limit on it. Therefore, the whole context is no
00089         // longer global.
00090         global = false;
00091 
00092         // The next step is to introduce our newly limiting scope
00093         cls = sc;
00094         method = sm;
00095     } else if (cls == null)
00096     {
00097         cls = sc;    // Initialization
00098         method = sm;
00099     } else
00100     {
00101         if (cls.getName().equals(sc.getName()))
00102         {
00103             // Here, we are in the same class
00104             if (method == null)
00105             {
00106                 method = sm;  // Previously, it's a field access, now convert it to local (if any)
00107             } else
00108             {
00109                 // We make sure if we have local access, it must occur at the same method
00110                 // and the same class
00111                 if (sm != null && !sm.getName().equals(method))
00112                     throw new RuntimeException("Cannot compare locals in different methods!");
00113             }
00114         } else
00115         {
00116             // Here we have two different classes
00117             // if we have sm == null && method == null  ==> field to field access
00118             // if we have sm != null && method == null  ==> field to local access
00119             // if we have sm == null && method != null  ==> local to field access
00120             // Otherwise: local to local, if the methods are not equal, then it's illegal
00121             if (sm != null && method != null)
00122             {
00123                 if (!sm.getName().equals(method))
00124                 {
00125                     throw new RuntimeException("Cannot compare locals in different methods (and even worse: in different class)!");
00126                 }
00127             } else if (method == null && sm != null)
00128             {
00129                 // It was previously a field access, now we have a method enclosure,
00130                 // So, the context must be this method and this class.
00131                 method = sm;
00132                 cls = sc;
00133             } else if (method != null && sm == null)
00134             {
00135                 // It was previously a local access, now we're accessing fields
00136                 // So, nothing is changed
00137             } else
00138             {
00139                 // Here, we are accessing fields between classes
00140                 global = true;
00141             }
00142         }
00143     }
00144 }
00145 /**
00146  * 
00147  * @param newV ca.mcgill.sable.soot.jimple.Value
00148  */
00149 public void setExpr(Value newV) {
00150     v = newV;
00151 }
00152     public void setExprAST(SimpleNode n) { ast = n; }
00153 public void setMethodContext(String s, List a)
00154 {
00155     methodName = s; args = a;
00156 }
00157 /**
00158  * 
00159  * @param newName java.lang.String
00160  */
00161 public void setName(String newName) {
00162     name = newName;
00163 }
00164 public String toString() { return name; }
00165 }

Generated at Thu Feb 7 06:52:27 2002 for Bandera by doxygen1.2.10 written by Dimitri van Heesch, © 1997-2001