6 public class ClassDescriptor extends Descriptor {
7 private static int UIDCount=1; // start from 1 instead of 0 for multicore gc
8 private final int classid;
10 ClassDescriptor superdesc;
11 boolean hasFlags=false;
21 Hashtable singleImports;
24 int numstaticblocks = 0;
25 int numstaticfields = 0;
28 Vector<String> superinterfaces;
29 SymbolTable superIFdesc;
30 private int interfaceid;
33 boolean isInnerClass=false;
35 // inner classes/enum can have these
36 String surroundingclass=null;
37 ClassDescriptor surroudingdesc=null;
38 SymbolTable innerdescs;
41 boolean isEnum = false;
42 SymbolTable enumdescs;
43 HashMap<String, Integer> enumConstantTbl;
44 int enumconstantid = 0;
46 boolean isClassLibrary=false;
48 String sourceFileName;
50 public ClassDescriptor(String classname, boolean isInterface) {
51 this("", classname, isInterface);
54 public ClassDescriptor(String packagename, String classname, boolean isInterface) {
55 //make the name canonical by class file path (i.e. package)
58 flags=new SymbolTable();
59 fields=new SymbolTable();
60 fieldvec=new Vector();
61 methods=new SymbolTable();
64 this.interfaceid = -1;
68 this.packagename=packagename;
69 superinterfaces = new Vector<String>();
70 superIFdesc = new SymbolTable();
71 this.innerdescs = new SymbolTable();
72 this.enumdescs = new SymbolTable();
76 if(this.isInterface()) {
77 return this.interfaceid;
82 public Iterator getMethods() {
83 return methods.getDescriptorsIterator();
86 public Iterator getFields() {
87 return fields.getDescriptorsIterator();
90 public Iterator getFlags() {
91 return flags.getDescriptorsIterator();
94 public Iterator getSuperInterfaces() {
95 return this.superIFdesc.getDescriptorsIterator();
98 public SymbolTable getFieldTable() {
102 public Vector getFieldVec() {
106 public String getPackage() {
110 public SymbolTable getFlagTable() {
114 public SymbolTable getMethodTable() {
118 public SymbolTable getSuperInterfaceTable() {
119 return this.superIFdesc;
122 public String getSafeDescriptor() {
123 return "L"+safename.replace('.','/');
126 public String printTree(State state) {
128 String st=modifiers.toString()+"class "+getSymbol();
129 if (superclass!=null)
130 st+="extends "+superclass.toString();
131 if(this.superinterfaces != null) {
133 boolean needcomma = false;
134 for(int i = 0; i < this.superinterfaces.size(); i++) {
138 st += this.superinterfaces.elementAt(i);
143 indent=TreeNode.INDENT;
144 boolean printcr=false;
146 for(Iterator it=getFlags(); it.hasNext();) {
147 FlagDescriptor fd=(FlagDescriptor)it.next();
148 st+=TreeNode.printSpace(indent)+fd.toString()+"\n";
156 for(Iterator it=getFields(); it.hasNext();) {
157 FieldDescriptor fd=(FieldDescriptor)it.next();
158 st+=TreeNode.printSpace(indent)+fd.toString()+"\n";
164 for(Iterator it=this.getInnerClasses(); it.hasNext();) {
165 ClassDescriptor icd=(ClassDescriptor)it.next();
166 st+=icd.printTree(state)+"\n";
172 for(Iterator it=this.getEnum(); it.hasNext();) {
173 ClassDescriptor icd = (ClassDescriptor)it.next();
174 st += icd.getModifier().toString() + " enum " + icd.getSymbol() + " {\n ";
175 Set keys = icd.getEnumConstantTbl().keySet();
176 String[] econstants = new String[keys.size()];
177 Iterator it_keys = keys.iterator();
178 while(it_keys.hasNext()) {
179 String key = (String)it_keys.next();
180 econstants[icd.getEnumConstant(key)] = key;
182 for(int i = 0; i < econstants.length; i++) {
184 if(i < econstants.length-1) {
194 for(Iterator it=getMethods(); it.hasNext();) {
195 MethodDescriptor md=(MethodDescriptor)it.next();
196 st+=TreeNode.printSpace(indent)+md.toString()+" ";
197 BlockNode bn=state.getMethodBody(md);
198 st+=bn.printNode(indent)+"\n\n";
204 public MethodDescriptor getCalledMethod(MethodDescriptor md) {
205 ClassDescriptor cn=this;
208 // TODO: the original code returned "null" if no super class
209 // ever defines the method. Is there a situation where this is
210 // fine and the client should take other actions? If not, we should
211 // change this warning to an error.
212 System.out.println( "ClassDescriptor.java: WARNING "+md+
213 " did not resolve to an actual method." );
216 Set possiblematches=cn.getMethodTable().getSetFromSameScope(md.getSymbol());
217 for(Iterator matchit=possiblematches.iterator(); matchit.hasNext();) {
218 MethodDescriptor matchmd=(MethodDescriptor)matchit.next();
220 if (md.matches(matchmd)) {
225 //Not found...walk one level up
226 cn=cn.getSuperDesc();
230 public void addFlag(FlagDescriptor fd) {
231 if (flags.contains(fd.getSymbol()))
232 throw new Error(fd.getSymbol()+" already defined");
237 public boolean hasFlags() {
238 return hasFlags||getSuperDesc()!=null&&getSuperDesc().hasFlags();
241 public void addField(FieldDescriptor fd) {
242 if (fields.contains(fd.getSymbol()))
243 throw new Error(fd.getSymbol()+" already defined");
247 this.incStaticFields();
249 fd.setClassDescriptor(this);
252 public void addMethod(MethodDescriptor md) {
256 public void setModifiers(Modifiers modifiers) {
257 this.modifiers=modifiers;
260 public void setSuper(String superclass) {
261 this.superclass=superclass;
264 public ClassDescriptor getSuperDesc() {
268 public void setSuper(ClassDescriptor scd) {
272 public String getSuper() {
276 public void addSuperInterface(String superif) {
277 this.superinterfaces.addElement(superif);
280 public Vector<String> getSuperInterface() {
281 return this.superinterfaces;
284 public void addSuperInterfaces(ClassDescriptor sif) {
285 this.superIFdesc.add(sif);
288 public void incStaticBlocks() {
289 this.numstaticblocks++;
292 public int getNumStaticBlocks() {
293 return this.numstaticblocks;
296 public void incStaticFields() {
297 this.numstaticfields++;
300 public int getNumStaticFields() {
301 return this.numstaticfields;
304 public boolean isAbstract() {
305 return this.modifiers.isAbstract();
308 public boolean isInterface() {
309 return (this.classid == -2);
312 public void setInterfaceId(int id) {
313 this.interfaceid = id;
316 public boolean isStatic() {
317 return this.modifiers.isStatic();
320 public void setAsInnerClass() {
321 this.isInnerClass = true;
324 public boolean isInnerClass() {
325 return this.isInnerClass;
328 public void setSurroundingClass(String sclass) {
329 this.surroundingclass=sclass;
332 public String getSurrounding() {
333 return this.surroundingclass;
336 public ClassDescriptor getSurroundingDesc() {
337 return this.surroudingdesc;
340 public void setSurrounding(ClassDescriptor scd) {
341 this.surroudingdesc=scd;
344 public void addInnerClass(ClassDescriptor icd) {
345 this.innerdescs.add(icd);
348 public Iterator getInnerClasses() {
349 return this.innerdescs.getDescriptorsIterator();
352 public SymbolTable getInnerClassTable() {
353 return this.innerdescs;
356 public void setAsEnum() {
360 public boolean isEnum() {
364 public void addEnum(ClassDescriptor icd) {
365 this.enumdescs.add(icd);
368 public Iterator getEnum() {
369 return this.enumdescs.getDescriptorsIterator();
372 public SymbolTable getEnumTable() {
373 return this.enumdescs;
376 public void addEnumConstant(String econstant) {
377 if(this.enumConstantTbl == null) {
378 this.enumConstantTbl = new HashMap<String, Integer>();
380 if(this.enumConstantTbl.containsKey(econstant)) {
383 this.enumConstantTbl.put(econstant, this.enumconstantid++);
388 public int getEnumConstant(String econstant) {
389 if(this.enumConstantTbl.containsKey(econstant)) {
390 return this.enumConstantTbl.get(econstant).intValue();
396 public HashMap<String, Integer> getEnumConstantTbl() {
397 return this.enumConstantTbl;
400 public Modifiers getModifier() {
401 return this.modifiers;
404 public void setClassLibrary(){
405 this.isClassLibrary=true;
408 public boolean isClassLibrary(){
409 return isClassLibrary;
412 public void setSourceFileName(String sourceFileName){
413 this.sourceFileName=sourceFileName;
416 public void setImports(Hashtable singleImports, Vector multiImports) {
417 this.singleImports = singleImports;
418 this.multiImports = multiImports;
421 public String getSourceFileName(){
422 return this.sourceFileName;
425 public Hashtable getSingleImportMappings() {
426 return this.singleImports;