protected internal override void VisitAST(ForStmtAST node) { this.Visit(node.PreRun); // init var(postLabel, endLabel) = OpenLoop(); var beginLabel = Ins.CreateLabel(); GenCode.Add(Ins.Label(beginLabel)); this.Visit(node.InfLoop.Cond); // repeat's logic is opposite to for if (node.NodeType == ASTType.Repeat) { GenCode.Add(Ins.Not()); } GenCode.Add(Ins.Fjp(endLabel)); // body this.Visit(node.InfLoop.Body); // post run GenCode.Add(Ins.Label(postLabel)); this.Visit(node.PostRun); // jump to cond GenCode.Add(Ins.Ujp(beginLabel)); GenCode.Add(Ins.Label(endLabel)); CloseLoop(); }
protected internal override void VisitAST(BinaryExprAST node) { // for convenience, convert both of the LHS and RHS type explicitly var ty = (TypeKind) Math.Max((int) node.Lhs.RetType, (int) node.Rhs.RetType); this.Visit(node.Lhs); GenCode.Add(Ins.Conv(node.Lhs.RetType,ty)); this.Visit(node.Rhs); GenCode.Add(Ins.Conv(node.Rhs.RetType, ty)); var code = node.NodeType switch { ASTType.Add => Ins.Add(ty), ASTType.Subtract => Ins.Sub(ty), ASTType.Multiply => Ins.Mul(ty), ASTType.Divide => Ins.Div(ty), ASTType.Modulo => Ins.Mod(), ASTType.Equal => Ins.Equ(ty), ASTType.NotEqual => Ins.Neq(ty), ASTType.LessThan => Ins.Les(ty), ASTType.LessEqual => Ins.Leq(ty), ASTType.GreaterThan => Ins.Grt(ty), ASTType.GreaterEqual => Ins.Geq(ty), ASTType.And => Ins.And(), ASTType.Or => Ins.Or(), _ => throw new NotImplementedException() }; GenCode.Add(code); }
public override void Clear() { Ins.CleanLabel(); GenCode.Clear(); _symTbl.Clear(); _loops.Clear(); _allocated = 0; }
protected internal override void VisitAST(AssignStmtAST node) { if (!HasId(node.Name)) { RegisterId(node.Name, node.Value.RetType); } var(ty, addr) = GetId(node.Name); this.Visit(node.Value); GenCode.Add(Ins.Dpl(ty)); // duplicate the stack top first GenCode.Add(Ins.Str(ty, 0, addr)); // then move to the specified addr, sp-- }
protected internal override void VisitAST(UnaryExprAST node) { this.Visit(node.Hs); var code = node.NodeType switch { ASTType.Not => Ins.Not(), ASTType.Neg => Ins.Neg(node.RetType), _ => throw new NotImplementedException() }; GenCode.Add(code); }
protected internal override void VisitAST(IfStmtAST node) { var elseLabel = Ins.CreateLabel(); var endLabel = Ins.CreateLabel(); Branch ifBranch = node.Branches.First(); this.Visit(ifBranch.Cond); GenCode.Add(Ins.Fjp(elseLabel)); this.Visit(ifBranch.Body); GenCode.Add(Ins.Ujp(endLabel)); GenCode.Add(Ins.Label(elseLabel)); this.Visit(node.ElseBranch?.Body); GenCode.Add(Ins.Label(endLabel)); }
protected internal override void VisitAST(RepeatStmtAST node) { var(beginLabel, endLabel) = OpenLoop(); GenCode.Add(Ins.Label(beginLabel)); this.Visit(node.InfLoop.Body); // repeat's logic is opposite to for this.Visit(node.InfLoop.Cond); GenCode.Add(Ins.Not()); GenCode.Add(Ins.Fjp(endLabel)); GenCode.Add(Ins.Ujp(beginLabel)); GenCode.Add(Ins.Label(endLabel)); CloseLoop(); }
protected internal override void VisitAST(WriteStmtAST node) { this.Visit(node.Value); GenCode.Add(Ins.Out(node.Value.RetType)); }
protected internal override void VisitAST(ReadStmtAST node) { RegisterId(node.Name, node.VarType); GenCode.Add(Ins.In(node.VarType)); }
protected internal override void VisitAST(ContinueStmtAST node) { GenCode.Add(Ins.Ujp(LoopStart)); }
protected internal override void VisitAST(BreakStmtAST node) { GenCode.Add(Ins.Ujp(LoopEnd)); }
protected internal override void VisitAST(IntExprAST node) { GenCode.Add(Ins.Ldc(node.RetType, node.Value)); }
protected internal override void VisitAST(BoolExprAST node) { GenCode.Add(Ins.Ldc(TypeKind.Bool, node.Value ? "t" : "f")); }
protected internal override void VisitAST(VariableExprAST node) { var (_, addr) = GetId(node.Name); GenCode.Add(Ins.Lod(node.RetType, 0, addr)); }
protected internal override void VisitAST(FloatExprAST node) { GenCode.Add(Ins.Ldc(TypeKind.Float, node.Value)); }