for(Iterator it=cn.getInnerClasses(); it.hasNext(); ) {
ClassDescriptor icd=(ClassDescriptor)it.next();
+ if(icd.isStatic()) {
+ continue;
+ }
//iterate over all ctors of I.Cs and add a new param
for(Iterator method_it=icd.getMethods(); method_it.hasNext(); ) {
FieldAccessNode fan=new FieldAccessNode(en,fieldname);
fan.setNumLine(pn.getLine());
return fan;
+ } else if (isNode(pn,"superfieldaccess")) {
+ ExpressionNode en=new NameNode(new NameDescriptor("super"));
+ String fieldname=pn.getChild("field").getTerminal();
+
+ FieldAccessNode fan=new FieldAccessNode(en,fieldname);
+ fan.setNumLine(pn.getLine());
+ return fan;
+ } else if (isNode(pn,"supernamefieldaccess")) {
+ ExpressionNode en=parseExpression(pn.getChild("base").getFirstChild());
+ ExpressionNode exp = new FieldAccessNode(en, "super");
+ exp.setNumLine(pn.getLine());
+ String fieldname=pn.getChild("field").getTerminal();
+
+ FieldAccessNode fan=new FieldAccessNode(exp,fieldname);
+ fan.setNumLine(pn.getLine());
+ return fan;
} else if (isNode(pn,"arrayaccess")) {
ExpressionNode en=parseExpression(pn.getChild("base").getFirstChild());
ExpressionNode index=parseExpression(pn.getChild("index").getFirstChild());
ExpressionNode left;
String fieldname;
FieldDescriptor field;
+ boolean issuper;
public FieldAccessNode(ExpressionNode l, String field) {
fieldname=field;
left=l;
+ this.issuper = false;
}
public void setField(FieldDescriptor fd) {
public TypeDescriptor getType() {
return getField().getType();
}
+
+ public void setIsSuper() {
+ this.issuper = true;
+ }
+
+ public boolean isSuper() {
+ return issuper;
+ }
public Long evaluate() {
// if the field is a constant value then OK
FieldDescriptor fd;
ExpressionNode en;
ClassDescriptor cd;
+ boolean issuper;
public NameNode(NameDescriptor nd) {
this.name=nd;
this.vd=null;
this.fd=null;
this.cd = null;
+ this.issuper= false;
+ }
+
+ public boolean isSuper() {
+ return this.issuper;
+ }
+
+ public void setIsSuper() {
+ this.issuper = true;
}
public ExpressionNode getExpression() {
FieldDescriptor fd=null;
if (ltd.isArray()&&fieldname.equals("length"))
fd=FieldDescriptor.arrayLength;
- else {
+ else if(((left instanceof NameNode) && ((NameNode)left).isSuper())
+ ||((left instanceof FieldAccessNode) && ((FieldAccessNode)left).isSuper())){
+ fd = (FieldDescriptor) ltd.getClassDesc().getSuperDesc().getFieldTable().get(fieldname);
+ } else {
fd=(FieldDescriptor) ltd.getClassDesc().getFieldTable().get(fieldname);
}
if(ltd.isClassNameRef()) {
// the field access is using a class name directly
if (fd==null) {
// check if it is to access a surrounding class in an inner class
- if(fieldname.equals("this")) {
+ if(fieldname.equals("this") || fieldname.equals("super")) {
ClassDescriptor icd = ((VarDescriptor)nametable.get("this")).getType().getClassDesc();
if(icd.isInnerClass()) {
NameNode nn = new NameNode(new NameDescriptor("this"));
// this is an inner class this operation
fd = new FieldDescriptor(new Modifiers(),new TypeDescriptor(icd),"this",null,false);
}
+ if(fieldname.equals("super")) {
+ fan.setIsSuper();
+ }
fan.setField(fd);
return;
}
- }
+ }
ClassDescriptor surroundingCls=ltd.getClassDesc().getSurroundingDesc();
while(surroundingCls!=null) {
checkExpressionNode(md,nametable,en,td);
} else {
String varname=nd.toString();
- if(varname.equals("this")) {
+ if(varname.equals("this") || varname.equals("super")) {
// "this"
nn.setVar((VarDescriptor)nametable.get("this"));
+ if(varname.equals("super")) {
+ nn.setIsSuper();
+ }
return;
}
Descriptor d=(Descriptor)nametable.get(varname);
pn.addChild("field").addChild(id);
RESULT=pn;
:}
-// | SUPER DOT IDENTIFIER
-// | name DOT SUPER DOT IDENTIFIER
+ | SUPER DOT IDENTIFIER:id {:
+ ParseNode pn=new ParseNode("superfieldaccess",parser.lexer.line_num);
+ pn.addChild("field").addChild(id);
+ RESULT=pn;
+ :}
+ | name:name DOT SUPER DOT IDENTIFIER:id {:
+ ParseNode pn=new ParseNode("supernamefieldaccess",parser.lexer.line_num);
+ pn.addChild("base").addChild(name);
+ pn.addChild("field").addChild(id);
+ RESULT=pn;
+ :}
;
method_invocation ::=
name:name LPAREN argument_list_opt:args RPAREN {:
dotest StaticTest StaticTest.java
dotest SwitchCaseTest SwitchCaseTest.java
dotest TryCatchTest TryCatchTest.java
+dotest inner inner.java innerp.java innerpt.java
System.out.println("\t Inner class print: ");
System.out.println(outer);
System.out.println(super.outer);
+ t.super.outer = 1;
+ System.out.println(outer);
+ System.out.println(t.super.outer);
System.out.println(inner.this.outer);
System.out.println(inner.super.outer);
System.out.println(f1);
--- /dev/null
+Outer class print: 35; 0
+ Inner class print:
+4
+0
+4
+1
+35
+31
+2
+3
+4
+Outer class print: 35; 3