shithub: mc

Download patch

ref: f76858ddb7d53feb5b52f5828fdd0eaec4a968f4
parent: a88491ed41617826250a922307112dc662a93a4c
parent: 3982a9ac9debac6f6c0670f59d3577610b69d4f9
author: Ori Bernstein <[email protected]>
date: Thu Jun 21 05:56:24 EDT 2012

Merge branch 'master' of git+ssh://mimir.eigenstate.org/git/ori/mc2

--- a/8/asm.h
+++ b/8/asm.h
@@ -74,6 +74,7 @@
     char *name;
     int   isglobl;
     size_t stksz;
+    Type *type;
     Htab *locs;
     Node *ret;
     Cfg  *cfg;
--- a/8/reduce.c
+++ b/8/reduce.c
@@ -30,7 +30,8 @@
 
     /* return handling */
     Node *endlbl;
-    Node *retval;
+    Node *ret;
+    int   isbigret;
 
     /* pre/postinc handling */
     Node **incqueue;
@@ -43,7 +44,6 @@
     size_t argsz;
     Htab *globls;
     Htab *locs;
-    Node *ret;
 };
 
 static Node *simp(Simp *s, Node *n);
@@ -197,6 +197,7 @@
     sz = 0;
     switch (t->type) {
         case Tyvoid:
+            die("void has no size");
             return 1;
         case Tybool: case Tychar: case Tyint8:
         case Tybyte: case Tyuint8:
@@ -252,23 +253,33 @@
     return tysize(t);
 }
 
-static Node *temp(Simp *simp, Node *e)
+static Node *gentemp(Simp *simp, Node *e, Type *ty, Node **dcl)
 {
     char buf[128];
     static int nexttmp;
     Node *t, *r, *n;
 
-    assert(e->type == Nexpr);
     snprintf(buf, 128, ".t%d", nexttmp++);
     n = mkname(e->line, buf);
-    t = mkdecl(e->line, n, e->expr.type);
-    declarelocal(simp, t);
-    r = mkexpr(e->line, Ovar, t, NULL);
+    t = mkdecl(e->line, n, ty);
+    r = mkexpr(e->line, Ovar, n, NULL);
     r->expr.type = t->decl.type;
     r->expr.did = t->decl.did;
+    if (dcl)
+        *dcl = t;
     return r;
 }
 
+static Node *temp(Simp *simp, Node *e)
+{
+    Node *t, *dcl;
+
+    assert(e->type == Nexpr);
+    t = gentemp(simp, e, e->expr.type, &dcl);
+    declarelocal(simp, dcl);
+    return t;
+}
+
 static void jmp(Simp *s, Node *lbl)
 {
     append(s, mkexpr(lbl->line, Ojmp, lbl, NULL));
@@ -539,8 +550,13 @@
     if (ispure(n)) {
         r = n;
     } else {
-        r = temp(s, n);
-        append(s, store(r, n));
+        if (exprtype(n)->type == Tyvoid) {
+            r = NULL;
+            append(s, n);
+        } else {
+            r = temp(s, n);
+            append(s, store(r, n));
+        }
     }
     return r;
 }
@@ -551,6 +567,7 @@
     Node *t, *u, *v; /* temporary nodes */
     Type *ty;
     Node **args;
+    size_t i;
     const Op fusedmap[] = {
         [Oaddeq]        = Oadd,
         [Osubeq]        = Osub,
@@ -659,11 +676,14 @@
             r = n;
             break;
         case Oret:
-            if (n->expr.args[0]) {
-                if (s->ret)
-                    t = s->ret;
-                else
-                    t = s->ret = temp(s, args[0]);
+            if (s->isbigret) {
+                t = rval(s, args[0]);
+                t = addr(t, exprtype(args[0]));
+                u = word(n->line, size(args[0]));
+                v = mkexpr(n->line, Oblit, s->ret, t, u, NULL);
+                append(s, v);
+            } else if (n->expr.args[0]) {
+                t = s->ret;
                 t = store(t, rval(s, args[0]));
                 append(s, t);
             }
@@ -682,15 +702,16 @@
             }
             break;
         case Ocall:
-            if (size(n) > 4) {
+            if (exprtype(n)->type != Tyvoid && size(n) > 4) {
                 r = temp(s, n);
                 ty = mktyptr(n->line, exprtype(r));
                 linsert(&n->expr.args, &n->expr.nargs, 1, addr(r, exprtype(n)));
-                linsert(&args[0]->expr.type->sub, &n->expr.type->nsub, 1, ty);
-                args[0]->expr.type->sub[0] = tyvoid;
-                n->expr.type = tyvoid;
+                for (i = 0; i < n->expr.nargs; i++)
+                    n->expr.args[i] = rval(s, n->expr.args[i]);
+                append(s, n);
+            } else {
+                r = visit(s, n);
             }
-            r = visit(s, n);
             break;
         default:
             r = visit(s, n);
@@ -769,6 +790,8 @@
 
 static void reduce(Simp *s, Node *f)
 {
+    Node *dcl;
+    Type *ty;
     size_t i;
 
     assert(f->type == Nfunc);
@@ -775,16 +798,25 @@
     s->nstmts = 0;
     s->stmts = NULL;
     s->endlbl = genlbl();
-    s->retval = NULL;
+    s->ret = NULL;
 
-    if (f->type == Nfunc) {
-        for (i = 0; i < f->func.nargs; i++) {
-            declarearg(s, f->func.args[i]);
-        }
-        simp(s, f->func.body);
-    } else {
-        die("Got a non-func (%s) to reduce", nodestr(f->type));
+    assert(f->type == Nfunc);
+
+    ty = f->func.type->sub[0];
+    if (ty->type != Tyvoid && tysize(ty) > 4) {
+        s->isbigret = 1;
+        s->ret = gentemp(s, f, mktyptr(f->line, ty), &dcl);
+        declarearg(s, dcl);
+    } else if (ty->type != Tyvoid) {
+        s->isbigret = 0;
+        s->ret = gentemp(s, f, ty, &dcl);
+        declarelocal(s, dcl);
     }
+
+    for (i = 0; i < f->func.nargs; i++) {
+      declarearg(s, f->func.args[i]);
+    }
+    simp(s, f->func.body);
 
     append(s, s->endlbl);
 }
--- a/test/hello/sys.myr
+++ b/test/hello/sys.myr
@@ -1,4 +1,3 @@
-
 pkg sys =
 	type scno = int
 	type fdopt = int
@@ -42,6 +41,8 @@
 	const Sysfstat	: scno = 108
 	const Syskill	: scno = 37
 	const Sysgetpid	: scno = 20
+	const Sysmmap2	: scno = 192
+	const Sysmunmap	: scno = 91
 
 	extern const syscall : (sc:scno, count:int, args:... -> int)
 
@@ -55,6 +56,8 @@
 	const write	: (fd:int, buf:char[,] -> int)
 	const lseek	: (fd:int, off:uint, whence:int -> int)
 	const fstat	: (fd:int, sb:statbuf* -> int)
+	const munmap	: (addr:byte*, len:uint -> int)
+	const mmap	: (add:byte*, len:uint, prot:uint, flags:uint, fd:int, off:uint)
 ;;
 
 const exit	= {status;		-> syscall(Sysexit, 1);}
@@ -67,3 +70,5 @@
 const write	= {fd, buf;		-> syscall(Syswrite, 3, fd, buf castto(char*), buf.len);}
 const lseek	= {fd, off, whence;	-> syscall(Syslseek, 2, fd, off, whence);}
 const fstat	= {fd, sb;		-> syscall(Sysfstat, 2, fd, sb);}
+const munmap	= {addr, len;		-> syscall(Sysmunmap,   2, addr, len);}
+const mmap	= {addr, len, prot, flags, fd, off;	-> syscall(Sysmmap2, 6, addr, len, prot, flags, fd, off);}
--- a/test/hello/syscall.s
+++ b/test/hello/syscall.s
@@ -11,13 +11,22 @@
 	.long .a2
 	.long .a3
 	.long .a4
-.a5:	movl 32(%ebp),%edi
-.a4:	movl 28(%ebp),%esi
-.a3:	movl 24(%ebp),%edx
-.a2:	movl 20(%ebp),%ecx
-.a1:	movl 16(%ebp),%ebx
-	/* 12(%ebp) holds nargs */
-.a0:	movl 8(%ebp),%eax
+	.long .a5
+	.long .a5 
+	/*
+	   hack: 6 args uses %ebp, so we index
+	   relative to %esp. This means that if
+	   we actually start using stack space,
+	   this code will need adjustment
+	 */
+.a6:	movl 36(%esp),%ebp
+.a5:	movl 32(%esp),%edi
+.a4:	movl 28(%esp),%esi
+.a3:	movl 24(%esp),%edx
+.a2:	movl 20(%esp),%ecx
+.a1:	movl 16(%esp),%ebx
+	/* 12(%esp) holds nargs */
+.a0:	movl 8(%esp),%eax
         int $0x80
 	movl %ebp,%esp
 	popl %ebp