//Call to constructor
FlatCall fc=new FlatCall(md, null, out_temp, temps);
last.addNext(fc);
- return new NodePair(fn,fc);
+ last=fc;
+ if (con.getFlagEffects()!=null) {
+ FlatFlagActionNode ffan=new FlatFlagActionNode(false);
+ FlagEffects fes=con.getFlagEffects();
+ TempDescriptor flagtemp=outtemp;
+ for(int j=0;j<fes.numEffects();j++) {
+ FlagEffect fe=fes.getEffect(j);
+ ffan.addFlagAction(flagtemp, fe.getFlag(), fe.getStatus());
+ }
+ last.addNext(ffan);
+ last=ffan;
+ }
+ return new NodePair(fn,last);
} else {
FlatNode first=null;
FlatNode last=null;
for(int i=0;i<args.size();i++) {
con.addArgument((ExpressionNode)args.get(i));
}
+ /* Could have flag set here */
+ if (pn.getChild("flag_list")!=null) {
+ FlagEffects fe=new FlagEffects(null);
+ parseFlagEffect(fe, pn.getChild("flag_list"));
+ con.addFlagEffects(fe);
+ }
return con;
} else if (isNode(pn,"createarray")) {
System.out.println(pn.PPrint(3,true));
TypeDescriptor td;
Vector argumentlist;
MethodDescriptor md;
+ FlagEffects fe;
public CreateObjectNode(TypeDescriptor type) {
td=type;
argumentlist=new Vector();
}
+ public void addFlagEffects(FlagEffects fe) {
+ this.fe=fe;
+ }
+
+ public FlagEffects getFlagEffects() {
+ return fe;
+ }
+
public void addArgument(ExpressionNode en) {
argumentlist.add(en);
}
TypeDescriptor typetolookin=con.getType();
checkTypeDescriptor(typetolookin);
+
+ /* Check flag effects */
+ if (con.getFlagEffects()!=null) {
+ FlagEffects fe=con.getFlagEffects();
+ ClassDescriptor cd=typetolookin.getClassDesc();
+
+ for(int j=0;j<fe.numEffects();j++) {
+ FlagEffect flag=fe.getEffect(j);
+ String name=flag.getName();
+ FlagDescriptor flag_d=(FlagDescriptor)cd.getFlagTable().get(name);
+ //Make sure the flag is declared
+ if (flag_d==null)
+ throw new Error("Flag descriptor "+name+" undefined in class: "+cd.getSymbol());
+ flag.setFlag(flag_d);
+ }
+ }
+
+
if ((!typetolookin.isClass())&&(!typetolookin.isArray()))
throw new Error("Can't allocate primitive type:"+con.printNode(0));
default:
throw new Error();
}
-
-
-
+
if (td!=null)
if (!typeutil.isSuperorType(td, on.getType())) {
System.out.println(td);
non terminal ParseNode flag_effects;
non terminal ParseNode flag_effect;
non terminal ParseNode flag_list;
+non terminal ParseNode flag_list_opt;
non terminal ParseNode flag_change;
start with goal;
RESULT=pn;
:};
+flag_list_opt ::= LPAREN flag_list:fl RPAREN {:RESULT=fl;:}
+ | {: RESULT = new ParseNode("empty"); :}
+ ;
+
flag_list ::= flag_change:fc {:
ParseNode pn=new ParseNode("flag_list");
pn.addChild(fc);
// | name DOT THIS
;
class_instance_creation_expression ::=
- NEW class_or_interface_type:type LPAREN argument_list_opt:args RPAREN {:
+ NEW class_or_interface_type:type LPAREN argument_list_opt:args RPAREN flag_effects_opt:feo {:
ParseNode pn=new ParseNode("createobject");
pn.addChild(type);
pn.addChild(args);
+ pn.addChild(feo);
RESULT=pn;
:}
// | NEW class_or_interface_type LPAREN argument_list_opt RPAREN class_body
Task parameters can't be modified
How do we handle new object allocation?
-Idea #1: Simply lose precision -- don't even attempt analysis
- Improvement - let set flags at allocation
+Idea #1: Set flags at allocation
+ Only allow flag setting at exit for parameters
Non parameter variables:
1) Type must contain flags