From: stephey Date: Fri, 20 May 2011 09:42:02 +0000 (+0000) Subject: Fixed import bug but some other issues now pop up: X-Git-Url: http://demsky.eecs.uci.edu/git/?a=commitdiff_plain;h=b5b0cd4ffcb94c1f82aff3c265e719543c48f71d;p=IRC.git Fixed import bug but some other issues now pop up: 1) make rcrpointer now crashes at processNode in Pointer.java starting at line 439. The switch statement encounters a FlatLiteralNode and doesn't know what to do with it. 2) We fail to parse Hashtable.java in the gnu labrary when using the -jni option. The line of code it fails at is "Hashtable.this.clear();". I can't seem to find any resources telling me what having a "this" midline means, so I can't fix it myself. --- diff --git a/Robust/src/Analysis/Pointer/Pointer.java b/Robust/src/Analysis/Pointer/Pointer.java index 4947b959..57f6181c 100644 --- a/Robust/src/Analysis/Pointer/Pointer.java +++ b/Robust/src/Analysis/Pointer/Pointer.java @@ -470,7 +470,7 @@ nextdelta: return processFlatCall(bblock, index, (FlatCall) node, delta, newgraph); default: - throw new Error("Unrecognized node:"+node); + throw new Error("Unrecognized node:"+node + " of kind " + node.kind()); } } diff --git a/Robust/src/IR/ClassDescriptor.java b/Robust/src/IR/ClassDescriptor.java index 5d4af197..221c878c 100644 --- a/Robust/src/IR/ClassDescriptor.java +++ b/Robust/src/IR/ClassDescriptor.java @@ -18,7 +18,8 @@ public class ClassDescriptor extends Descriptor { SymbolTable flags; SymbolTable methods; - Hashtable singleImports; + Hashtable mandatoryImports; + Hashtable multiImports; int numstaticblocks = 0; int numstaticfields = 0; @@ -402,8 +403,9 @@ public class ClassDescriptor extends Descriptor { this.sourceFileName=sourceFileName; } - public void setImports(Hashtable singleImports) { - this.singleImports = singleImports; + public void setImports(Hashtable singleImports, Hashtable multiImports) { + this.mandatoryImports = singleImports; + this.multiImports = multiImports; } public String getSourceFileName() { @@ -411,7 +413,30 @@ public class ClassDescriptor extends Descriptor { } public Hashtable getSingleImportMappings() { - return this.singleImports; + return this.mandatoryImports; + } + + public Hashtable getMultiImportMappings() { + return this.multiImports; + } + + //Returns the full name/path of another class referenced from this class via imports. + public String getCannonicalImportMapName(String otherClassname) { + if(mandatoryImports.containsKey(otherClassname)) { + return (String) mandatoryImports.get(otherClassname); + } else if(multiImports.containsKey(otherClassname)) { + //Test for error + Object o = multiImports.get(otherClassname); + if(o instanceof Error) { + throw new Error("Class " + otherClassname + " is ambiguous. Cause: more than 1 package import contain the same class."); + } else { + //At this point, if we found a unique class + //we can treat it as a single, mandatory import. + mandatoryImports.put(otherClassname, o); + return (String) o; + } + } else { + return otherClassname; + } } - } diff --git a/Robust/src/IR/Tree/BuildIR.java b/Robust/src/IR/Tree/BuildIR.java index 21587c03..f42d7d82 100644 --- a/Robust/src/IR/Tree/BuildIR.java +++ b/Robust/src/IR/Tree/BuildIR.java @@ -240,7 +240,7 @@ public class BuildIR { private ClassDescriptor parseEnumDecl(ClassDescriptor cn, ParseNode pn) { ClassDescriptor ecd=new ClassDescriptor(pn.getChild("name").getTerminal(), false); - ecd.setImports(mandatoryImports); + ecd.setImports(mandatoryImports, multiimports); ecd.setAsEnum(); if(cn != null) { ecd.setSurroundingClass(cn.getSymbol()); @@ -275,7 +275,7 @@ public class BuildIR { private ClassDescriptor parseAnnotationTypeDecl(ParseNode pn) { ClassDescriptor cn=new ClassDescriptor(pn.getChild("name").getTerminal(), true); - cn.setImports(mandatoryImports); + cn.setImports(mandatoryImports, multiimports); ParseNode modifiers=pn.getChild("modifiers"); if(modifiers!=null) { cn.setModifiers(parseModifiersList(modifiers)); @@ -320,7 +320,7 @@ public class BuildIR { cn= new ClassDescriptor(packageName, newClassname, true); } - cn.setImports(mandatoryImports); + cn.setImports(mandatoryImports, multiimports); //cn.setAsInterface(); if (!isEmpty(pn.getChild("superIF").getTerminal())) { /* parse inherited interface name */ @@ -564,7 +564,7 @@ public class BuildIR { String newClassname = packageName + "." + pn.getChild("name").getTerminal(); cn= new ClassDescriptor(packageName, newClassname, false); } - cn.setImports(mandatoryImports); + cn.setImports(mandatoryImports, multiimports); if (!isEmpty(pn.getChild("super").getTerminal())) { /* parse superclass name */ ParseNode snn=pn.getChild("super").getChild("type").getChild("class").getChild("name"); @@ -662,7 +662,7 @@ public class BuildIR { private ClassDescriptor parseInnerClassDecl(ClassDescriptor cn, ParseNode pn) { ClassDescriptor icn=new ClassDescriptor(pn.getChild("name").getTerminal(), false); - icn.setImports(mandatoryImports); + icn.setImports(mandatoryImports, multiimports); icn.setAsInnerClass(); icn.setSurroundingClass(cn.getSymbol()); icn.setSurrounding(cn); @@ -760,6 +760,7 @@ public class BuildIR { //This will get the mapping of a terminal class name //to a canonical classname (with imports/package locations in them) private String resolveName(String terminal) { + if(mandatoryImports.containsKey(terminal)) { return (String) mandatoryImports.get(terminal); } else { @@ -972,7 +973,7 @@ public class BuildIR { TypeDescriptor td=parseTypeDescriptor(pn); innerCount++; ClassDescriptor cnnew=new ClassDescriptor(td.getSymbol()+"$"+innerCount, false); - cnnew.setImports(mandatoryImports); + cnnew.setImports(mandatoryImports, multiimports); cnnew.setSuper(td.getSymbol()); parseClassBody(cnnew, pn.getChild("decl").getChild("classbody")); Vector args=parseArgumentList(pn); diff --git a/Robust/src/IR/Tree/SemanticCheck.java b/Robust/src/IR/Tree/SemanticCheck.java index 1f14bf6e..b5a92a93 100644 --- a/Robust/src/IR/Tree/SemanticCheck.java +++ b/Robust/src/IR/Tree/SemanticCheck.java @@ -11,9 +11,6 @@ public class SemanticCheck { HashSet toanalyze; HashMap completed; - //This is the class mappings for a particular file based - //on the import names. Maps class to canonical class name. - static Hashtable singleImportMap; public static final int NOCHECK=0; public static final int REFERENCE=1; public static final int INIT=2; @@ -40,11 +37,11 @@ public class SemanticCheck { public ClassDescriptor getClass(ClassDescriptor context, String classname) { return getClass(context, classname, INIT); } - public ClassDescriptor getClass(ClassDescriptor context, String classname, int fullcheck) { + public ClassDescriptor getClass(ClassDescriptor context, String classnameIn, int fullcheck) { + String classname = classnameIn; if (context!=null) { // System.out.println(context.getSymbol() + " is looking for " + classname); - Hashtable remaptable=context.getSingleImportMappings(); - classname=remaptable.containsKey(classname)?((String)remaptable.get(classname)):classname; + classname = context.getCannonicalImportMapName(classnameIn); } ClassDescriptor cd=typeutil.getClass(classname, toanalyze); checkClass(cd, fullcheck); @@ -125,8 +122,6 @@ public class SemanticCheck { } else { ClassDescriptor cd = (ClassDescriptor) obj; toanalyze.remove(cd); - //set the class mappings based on imports. - singleImportMap = cd.getSingleImportMappings(); // need to initialize typeutil object here...only place we can // get class descriptors without first calling getclass diff --git a/Robust/src/IR/TypeUtil.java b/Robust/src/IR/TypeUtil.java index cdb2a171..69fb890d 100644 --- a/Robust/src/IR/TypeUtil.java +++ b/Robust/src/IR/TypeUtil.java @@ -54,6 +54,7 @@ public class TypeUtil { for (int i = 0; i < state.classpath.size(); i++) { String path = (String) state.classpath.get(i); File f = new File(path, cl.replace('.', '/') + ".java"); +// System.out.println("Looking in " + f.getAbsolutePath()); if (f.exists()) { try { ParseNode pn = Main.readSourceFile(state, f.getCanonicalPath());