diff options
Diffstat (limited to 'src/ast/nodes/AtomNode.java')
-rw-r--r-- | src/ast/nodes/AtomNode.java | 71 |
1 files changed, 57 insertions, 14 deletions
diff --git a/src/ast/nodes/AtomNode.java b/src/ast/nodes/AtomNode.java index 37d4d79..ea99808 100644 --- a/src/ast/nodes/AtomNode.java +++ b/src/ast/nodes/AtomNode.java @@ -2,6 +2,7 @@ package ast.nodes; import ast.types.*; import java.util.ArrayList; +import java.util.Arrays; import java.util.regex.Matcher; import java.util.regex.Pattern; import semanticanalysis.SemanticError; @@ -15,6 +16,10 @@ public class AtomNode implements Node { protected String val; protected TestlistCompNode exprlist; + // very scatchy + protected int ns; + protected int offset; + public AtomNode(String val, Node exprlist) { this.val = val; this.exprlist = (TestlistCompNode) exprlist; @@ -25,23 +30,29 @@ public class AtomNode implements Node { * returns `null`. */ public String getId() { - return this.val; + return val; } @Override - public ArrayList<SemanticError> checkSemantics(SymbolTable ST, int _nesting) { + public ArrayList<SemanticError> checkSemantics(SymbolTable ST, int _nesting, FunctionType ft) { ArrayList<SemanticError> errors = new ArrayList<>(); if (val != null) { - if ((this.typeCheck() instanceof AtomType) && ST.nslookup(this.getId()) < 0) { - errors.add(new SemanticError("name '" + this.getId() + "' is not defined.")); - } else { - // System.out.println("exist " + this.typeCheck()); + if (!Arrays.asList(bif).contains(getId())) { + if ((typeCheck() instanceof AtomType) && ST.nslookup(getId()) < 0) { + errors.add(new SemanticError("name '" + getId() + "' is not defined.")); + } else { + if ((typeCheck() instanceof AtomType)) { + int varNs = ST.lookup(getId()).getNesting(); + this.ns = _nesting - varNs; + offset = ST.lookup(getId()).getOffset(); + } + } } } if (exprlist != null) { - errors.addAll(exprlist.checkSemantics(ST, _nesting)); + errors.addAll(exprlist.checkSemantics(ST, _nesting, ft)); } return errors; @@ -50,29 +61,34 @@ public class AtomNode implements Node { // ENHANCE: return more specific types @Override public Type typeCheck() { - if (this.val == null) { + if (val == null) { return new VoidType(); } Pattern noneVariable = Pattern.compile("^(None)$"); Pattern booleanVariable = Pattern.compile("^(True|False)$"); + Pattern integerVariable = Pattern.compile("^[0-9]+$"); Pattern reservedWords = Pattern.compile("^(continue|break|int|float)$"); // this regex should match every possible atom name written in this format: CHAR // (CHAR | DIGIT)* Pattern simpleVariable = Pattern.compile("^[a-zA-Z][a-zA-Z0-9]*$", Pattern.CASE_INSENSITIVE); - Matcher noneVariableMatcher = noneVariable.matcher(this.val); - Matcher booleanVariableMatcher = booleanVariable.matcher(this.val); - Matcher reservedWordsMatcher = reservedWords.matcher(this.val); - Matcher simpleVariableMatcher = simpleVariable.matcher(this.val); + Matcher noneVariableMatcher = noneVariable.matcher(val); + Matcher booleanVariableMatcher = booleanVariable.matcher(val); + Matcher integerVariableMatcher = integerVariable.matcher(val); + Matcher reservedWordsMatcher = reservedWords.matcher(val); + Matcher simpleVariableMatcher = simpleVariable.matcher(val); boolean matchFoundNone = noneVariableMatcher.find(); boolean matchFoundBoolean = booleanVariableMatcher.find(); + boolean matchFoundInteger = integerVariableMatcher.find(); boolean matchFoundContinueBreak = reservedWordsMatcher.find(); boolean matchFoundSimpleVariable = simpleVariableMatcher.find(); if (matchFoundBoolean) { return new BoolType(); + } else if (matchFoundInteger) { + return new IntType(); } else if (matchFoundContinueBreak) { return new ReservedWordsType(); } else if (matchFoundNone) { @@ -84,10 +100,37 @@ public class AtomNode implements Node { } } - // TODO: add code generation for atom node @Override public String codeGeneration() { - return ""; + if (exprlist != null) { + return exprlist.codeGeneration(); + } + + if (typeCheck() instanceof IntType) { + return "storei A0 " + getId() + "\n"; + } + + if (typeCheck() instanceof BoolType) { + return "storei A0 " + boolValue(getId()) + "\n"; + } + + if (typeCheck() instanceof AtomType) { + // We need to ascend the access-link chain to the top (or bottom, + // who knows). + String str = "move AL T1\n"; + for (int i = 0; i < this.ns; i++) { + str += "store T1 0(T1)\n"; + } + + str += "subi T1 " + offset + "\nstore A0 0(T1)\n"; + return str; + } + + return "Error: could not parse an atom\n"; + } + + public static String boolValue(String id) { + return id.equals("True") ? "1" : "0"; } @Override |