[08 - AST] First implementations of Abstract Syntax Tree parsing

This commit is contained in:
2020-05-18 12:21:35 +02:00
parent 8cf57691dc
commit dba220ceb8
2 changed files with 285 additions and 0 deletions

View File

@@ -1,5 +1,8 @@
package de.dhbw.compiler.xparser; package de.dhbw.compiler.xparser;
import java.util.LinkedList;
import java.util.List;
import de.dhbw.compiler.xparser.api.Parser; import de.dhbw.compiler.xparser.api.Parser;
/** /**
@@ -13,6 +16,286 @@ public class ASTParser extends Parser {
@Override @Override
public Tree parseProgram() { public Tree parseProgram() {
int oldPosition = in.getPosition();
Tree program, id, decList, statList;
if ((program = parseToken(Token.PROGRAM)) != null
&& (id = parseToken(Token.ID)) != null
&& parseToken(Token.SEMICOLON) != null
&& (decList = parseDecList()) != null
&& (statList = parseStatList()) != null
&& parseToken(Token.DOT) != null
&& parseToken(Token.EOF) != null) {
Tree tree = new Tree(program.getToken());
tree.addLastChild(id);
tree.addLastChild(decList);
tree.addLastChild(statList);
return tree;
}
System.out.println("parseProgram> Skipping Tree");
in.setPosition(oldPosition);
return null; return null;
} }
private Tree parseStatList() {
Tree tree = new Tree(new Token(Token.STATLIST));
Tree stat;
while ((stat = parseStatWithSemicolon()) != null) {
tree.addLastChild(stat);
}
return tree;
}
private Tree parseStatWithSemicolon() {
int oldPosition = in.getPosition();
Tree tree = new Tree(new Token(Token.STATWITHSEMI));
Tree state, semicolon;
if (((state = parseStat()) != null)
&& ((semicolon = parseToken(Token.SEMICOLON)) != null)) {
tree.addLastChild(state);
tree.addLastChild(semicolon);
return tree;
}
in.setPosition(oldPosition);
return null;
}
private Tree parseStat() {
int oldPosition = in.getPosition();
Tree tree = new Tree(new Token(Token.STAT));
Tree numAssign, condStat, block;
if ((numAssign = parseNumAssign()) != null) {
tree.addLastChild(numAssign);
return tree;
}
in.setPosition(oldPosition);
if ((condStat = parseCondStat()) != null) {
tree.addLastChild(condStat);
return tree;
}
in.setPosition(oldPosition);
if ((block = parseBlock()) != null) {
tree.addLastChild(block);
return tree;
}
in.setPosition(oldPosition);
return null;
}
private Tree parseCondStat() {
int oldPosition = in.getPosition();
Tree tree = new Tree(new Token(Token.CONDSTAT));
Tree ifKey, cond, then, stat1, elseKey, stat2;
if ((ifKey = parseToken(Token.IF)) != null
&& (cond = parseCond()) != null
&& (then = parseToken(Token.THEN)) != null
&& (stat1 = parseStat()) != null
&& (elseKey = parseToken(Token.ELSE)) != null
&& (stat2 = parseStat()) != null) {
tree.addLastChild(ifKey);
tree.addLastChild(cond);
tree.addLastChild(then);
tree.addLastChild(stat1);
tree.addLastChild(elseKey);
tree.addLastChild(stat2);
return tree;
}
in.setPosition(oldPosition);
if (((ifKey = parseToken(Token.IF)) != null)
&& (cond = parseCond()) != null
&& (then = parseToken(Token.THEN)) != null
&& (stat1 = parseStat()) != null) {
tree.addLastChild(ifKey);
tree.addLastChild(cond);
tree.addLastChild(then);
tree.addLastChild(stat1);
return tree;
}
in.setPosition(oldPosition);
return null;
}
private Tree parseCond() {
int oldPosition = in.getPosition();
Tree tree = new Tree(new Token(Token.COND));
Tree a, operator, b;
if ((a = parseNumExpr()) != null
&& ((operator = parseToken(Token.EQUALS)) != null
|| (operator = parseToken(Token.LESS)) != null
|| (operator = parseToken(Token.MORE)) != null)
&& (b = parseNumExpr()) != null) {
tree.addLastChild(a);
tree.addLastChild(operator);
tree.addLastChild(b);
return tree;
}
in.setPosition(oldPosition);
return null;
}
private Tree parseNumAssign() {
int oldPosition = in.getPosition();
Tree tree = new Tree(new Token(Token.ASSIGNSTAT));
Tree id, assign, numExpr;
if ((id = parseToken(Token.ID)) != null
&& (assign = parseToken(Token.ASSIGN)) != null
&& (numExpr = parseNumExpr()) != null) {
tree.addLastChild(id);
tree.addLastChild(assign);
tree.addLastChild(numExpr);
return tree;
}
in.setPosition(oldPosition);
return null;
}
private Tree parseNumExpr() {
int oldPosition = in.getPosition();
Tree tree = new Tree(new Token(Token.EXPR));
Tree a, b, operator;
if (((a = parseNumExpr2()) != null)
&& (((operator = parseToken(Token.PLUS)) != null
|| (operator = parseToken(Token.MINUS)) != null))
&& (b = parseNumExpr()) != null) {
tree.addLastChild(a);
tree.addLastChild(operator);
tree.addLastChild(b);
return tree;
}
in.setPosition(oldPosition);
if ((a = parseNumExpr2()) != null) {
tree.addLastChild(a);
return tree;
}
in.setPosition(oldPosition);
return null;
}
private Tree parseNumExpr2() {
int oldPosition = in.getPosition();
Tree tree = new Tree(new Token(Token.EXPR2));
Tree a, b, operator;
if (((a = parseNumExpr3()) != null)
&& (((operator = parseToken(Token.MULT)) != null
|| (operator = parseToken(Token.DIV)) != null))
&& (b = parseNumExpr2()) != null) {
tree.addLastChild(a);
tree.addLastChild(operator);
tree.addLastChild(b);
return tree;
}
in.setPosition(oldPosition);
if ((a = parseNumExpr3()) != null) {
tree.addLastChild(a);
return tree;
}
in.setPosition(oldPosition);
return null;
}
private Tree parseNumExpr3() {
int oldPosition = in.getPosition();
Tree tree = new Tree(new Token(Token.EXPR3));
Tree sign, intConst, id, num, lbr, rbr;
if ((intConst = parseToken(Token.INTCONST)) != null) {
tree.addLastChild(intConst);
return tree;
}
in.setPosition(oldPosition);
if (((sign = parseToken(Token.MINUS)) != null
&& ((intConst = parseToken(Token.INTCONST))) != null)) {
tree.addLastChild(sign);
tree.addLastChild(intConst);
return tree;
}
in.setPosition(oldPosition);
if ((id = parseToken(Token.ID)) != null) {
tree.addLastChild(id);
return tree;
}
if (((lbr = parseToken(Token.LBR)) != null) && ((num = parseNumExpr()) != null)
&& ((rbr = parseToken(Token.RBR)) != null)) {
tree.addLastChild(lbr);
tree.addLastChild(num);
tree.addLastChild(rbr);
return tree;
}
in.setPosition(oldPosition);
return null;
}
private Tree parseDecList() {
Tree decList = new Tree(new Token(Token.DECLLIST));
Tree dec;
while ((dec = parseDec()) != null) {
decList.addLastChild(dec);
}
return decList;
}
private Tree parseDec() {
int oldPosition = in.getPosition();
Tree id, type;
List<Tree> modifiers = parseModifier();
if ((id = parseToken(Token.ID)) != null
&& (parseToken(Token.COLON)) != null
&& (type = parseToken(Token.TYPE)) != null) {
Tree tree = new Tree(new Token(Token.DECL));
tree.addLastChildren(modifiers);
tree.addLastChild(id);
tree.addLastChild(type);
return tree;
}
in.setPosition(oldPosition);
return null;
}
private List<Tree> parseModifier() {
int oldPosition = in.getPosition();
List<Tree> treeList = new LinkedList<>();
Tree read, print;
if ((read = parseToken(Token.READ)) != null) {
treeList.add(read);
}
if ((print = parseToken(Token.PRINT)) != null) {
treeList.add(print);
}
return treeList;
}
} }

View File

@@ -31,6 +31,8 @@ public class Tree {
public void addLastChild(Tree child) { public void addLastChild(Tree child) {
this.children.addLast(child); this.children.addLast(child);
} }
public void addLastChildren(List<Tree> children) { this.children.addAll(children); }
public void addFirstChild(Tree child) { public void addFirstChild(Tree child) {
this.children.addFirst(child); this.children.addFirst(child);