summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/back/generator.py8
-rw-r--r--src/back/tac.py2
-rw-r--r--src/emu/syscall.c8
-rw-r--r--src/emu/syscall.h7
-rw-r--r--src/front/ast.py12
-rw-r--r--src/front/lexer.py1
-rw-r--r--src/front/parser.py9
-rw-r--r--src/front/token.py1
-rw-r--r--test/test1.t3
9 files changed, 39 insertions, 12 deletions
diff --git a/src/back/generator.py b/src/back/generator.py
index 414cf7b..7ca2658 100644
--- a/src/back/generator.py
+++ b/src/back/generator.py
@@ -90,6 +90,14 @@ class Generator(object):
elif tac.op == Op.RETURN:
self.emit("ADD rv, r0, r%d" % tac.arg1)
self.emit(tac)
+ elif tac.op == Op.PRINT:
+ r = Register().new()
+ self.emit("PUSH r%d" % tac.arg1)
+ self.emit("MOV r%d, %d" % (r, 1))
+ self.emit("PUSH r%d" % r)
+ self.emit("SYS")
+ self.emit("POP r0")
+ self.emit("POP r0")
elif isinstance(tac, FunctionPrologue):
self.generate_prologue(tac.name)
elif isinstance(tac, FunctionEpilogue):
diff --git a/src/back/tac.py b/src/back/tac.py
index 03303cf..86ccd90 100644
--- a/src/back/tac.py
+++ b/src/back/tac.py
@@ -40,6 +40,8 @@ Op.JMP = Op("JMP") # goto x
Op.CALL = Op("CALL") # call x return in y
Op.RETURN = Op("RETURN") # return x
+Op.PRINT = Op("PRINT") # print x
+
class TAC(object):
def __init__(self,op,arg1=None,arg2=None):
self.op = op
diff --git a/src/emu/syscall.c b/src/emu/syscall.c
index 625bbf4..aba3448 100644
--- a/src/emu/syscall.c
+++ b/src/emu/syscall.c
@@ -1,5 +1,6 @@
#include <unistd.h>
#include <stdlib.h>
+#include <inttypes.h>
#include "cpu.h"
#include "mem.h"
@@ -13,11 +14,8 @@ void do_syscall(void)
case SYS_exit:
exit(arg(1));
break;
- case SYS_read:
- push(read(arg(1), &MEM[arg(2)], arg(3)));
- break;
- case SYS_write:
- push(write(arg(1), &MEM[arg(2)], arg(3)));
+ case SYS_print:
+ printf("%"PRIu32"\n", arg(1));
break;
default:
push(-1);
diff --git a/src/emu/syscall.h b/src/emu/syscall.h
index 7c7265c..afd3e9d 100644
--- a/src/emu/syscall.h
+++ b/src/emu/syscall.h
@@ -2,14 +2,11 @@
#define _SYSCALL_H
/* calling convention:
- * - pass syscall number in GPR[1]
- * - pass arguments in GPR[2]-GPR[9]
- * - return code is passed in GPR[2]
+ * - syscall number and params are passed on stack
*/
#define SYS_exit 0x00
-#define SYS_read 0x01
-#define SYS_write 0x02
+#define SYS_print 0x01
void do_syscall(void);
diff --git a/src/front/ast.py b/src/front/ast.py
index 77aab95..f272ca2 100644
--- a/src/front/ast.py
+++ b/src/front/ast.py
@@ -149,6 +149,18 @@ class ReturnStatement(Statement):
def __repr__(self):
return "<ReturnStatement at line %d>" % self.lineno
+class PrintStatement(Statement):
+ def __init__(self, expression, lineno = -1):
+ self.expression = expression
+ self.lineno = lineno
+
+ def generate(self, before, after, last):
+ self.debug("PrintStatement.generate(before = %d, after = %d): %s" % (before, after, repr(self)))
+ self.emit(Op.PRINT, self.expression.reduce(), last)
+
+ def __repr__(self):
+ return "<PrintStatement at line %d>" % self.lineno
+
class AssignStatement(Statement):
def __init__(self, ident, expression, lineno = -1):
self.ident = ident
diff --git a/src/front/lexer.py b/src/front/lexer.py
index e6eb172..dcaa672 100644
--- a/src/front/lexer.py
+++ b/src/front/lexer.py
@@ -22,6 +22,7 @@ class Lexer:
'if': Token(Tag.IF),
'else': Token(Tag.ELSE),
'call': Token(Tag.CALL),
+ 'print': Token(Tag.PRINT),
'fun': Token(Tag.FUN),
'end': Token(Tag.END)}
return
diff --git a/src/front/parser.py b/src/front/parser.py
index 72e0051..5029158 100644
--- a/src/front/parser.py
+++ b/src/front/parser.py
@@ -149,12 +149,13 @@ class Parser:
self.match(Tag.END, Tag.NEWLINE)
return Function(name, args, block, line)
- # statement = ( if_statement | while_statement | assign_statement | return_statement | function_call ) nl.
+ # statement = ( if_statement | while_statement | assign_statement | return_statement | function_call | print_statement ) nl.
def statement(self):
res = {Tag.IF: self.if_statement,
Tag.WHILE: self.while_statement,
Tag.IDENT: self.assignment,
Tag.RETURN: self.return_statement,
+ Tag.PRINT: self.print_statement,
Tag.CALL: self.function_call,
}[self.token.tag]()
self.match(Tag.NEWLINE)
@@ -201,6 +202,12 @@ class Parser:
self.scope.add_locals(name)
return AssignStatement(name, exp, line)
+ def print_statement(self):
+ line = self.lexer.line
+ self.match(Tag.PRINT)
+ exp = self.boolean()
+ return PrintStatement(exp, line)
+
# program = function_list.
def program(self):
return Program(self.function_list())
diff --git a/src/front/token.py b/src/front/token.py
index 78e9dab..d0970f3 100644
--- a/src/front/token.py
+++ b/src/front/token.py
@@ -26,6 +26,7 @@ Tag.LPAREN = Tag("LPAREN")
Tag.RPAREN = Tag("RPAREN")
Tag.NEWLINE = Tag("NEWLINE")
Tag.COMMA = Tag("COMMA")
+Tag.PRINT = Tag("PRINT")
Tag.FUN = Tag("FUN")
Tag.CALL = Tag("CALL")
Tag.ASSIGNMENT = Tag("ASSIGNMENT")
diff --git a/test/test1.t b/test/test1.t
index af9d688..12580bd 100644
--- a/test/test1.t
+++ b/test/test1.t
@@ -13,5 +13,6 @@ fun main[]
sum = sum + call fib[i]
i = i + 1
end
- @sum
+ print sum
+ @0
end