ref: 019c09f1c3d0d04dc60ba01b0a51e59d5b4fdcaa
parent: 9873b208d15f5486f9b417f4de0f70be4b57ae24
parent: bc6c47037bff22b29abc5418fc04c4af4fbc28d9
author: Ori Bernstein <[email protected]>
date: Tue Sep 4 17:28:19 EDT 2012
Merge branch 'master' of git+ssh://mimir.eigenstate.org/git/ori/mc2
--- a/6/simp.c
+++ b/6/simp.c
@@ -422,18 +422,18 @@
return NULL;
}
-static Node *uconid(Node *n, size_t off)
+static Node *uconid(Node *n)
{
Ucon *uc;
if (exprop(n) != Oucon)
- return load(addk(addr(n, mktype(n->line, Tyuint)), off));
+ return load(addr(n, mktype(n->line, Tyuint)));
uc = finducon(n);
return word(uc->line, uc->id);
}
-static Node *uval(Node *n, size_t off, Type *t)
+static Node *patval(Node *n, Type *t)
{
if (exprop(n) == Oucon)
return n->expr.args[1];
@@ -440,13 +440,13 @@
else if (exprop(n) == Olit)
return n;
else
- return load(addk(addr(n, t), off));
+ return load(addk(addr(n, t), Wordsz));
}
-static void umatch(Simp *s, Node *pat, Node *val, Type *t, size_t off, Node *iftrue, Node *iffalse)
+static void umatch(Simp *s, Node *pat, Node *val, Type *t, Node *iftrue, Node *iffalse)
{
Node *v, *x, *y;
- Node *next;
+ Node *deeper;
Ucon *uc;
assert(pat->type == Nexpr);
@@ -473,26 +473,25 @@
case Tyint8: case Tyint16: case Tyint32: case Tyint:
case Tyuint8: case Tyuint16: case Tyuint32: case Tyuint:
case Typtr: case Tyfunc:
- x = uval(pat, off, t);
- y = uval(val, off, t);
- v = mkexpr(pat->line, Oeq, x, y, NULL);
+ v = mkexpr(pat->line, Oeq, pat, val, NULL);
cjmp(s, v, iftrue, iffalse);
break;
case Tyunion:
- x = uconid(pat, off);
- y = uconid(val, off);
uc = finducon(pat);
if (!uc)
uc = finducon(val);
+ deeper = genlbl();
- next = genlbl();
+ x = uconid(pat);
+ y = uconid(val);
v = mkexpr(pat->line, Oeq, x, y, NULL);
v->expr.type = tyintptr;
- cjmp(s, v, next, iffalse);
- append(s, next);
+ cjmp(s, v, deeper, iffalse);
+ append(s, deeper);
if (uc->etype) {
- off += Wordsz;
- umatch(s, pat, val, uc->etype, off, iftrue, iffalse);
+ pat = patval(pat, uc->etype);
+ val = patval(val, uc->etype);
+ umatch(s, pat, val, uc->etype, iftrue, iffalse);
}
break;
}
@@ -518,7 +517,7 @@
/* check pattern */
cur = genlbl();
next = genlbl();
- umatch(s, m->match.pat, val, val->expr.type, 0, cur, next);
+ umatch(s, m->match.pat, val, val->expr.type, cur, next);
/* do the action if it matches */
append(s, cur);
--- a/parse/gram.y
+++ b/parse/gram.y
@@ -122,12 +122,12 @@
%type <ty> type structdef uniondef tupledef compoundtype functype funcsig
%type <ty> generictype
-%type <tylist> tuptybody
+%type <tylist> typelist
%type <nodelist> typaramlist
%type <tok> asnop cmpop addop mulop shiftop
-%type <tydef> tydef
+%type <tydef> tydef typeid
%type <node> exprln retexpr expr atomicexpr littok literal asnexpr lorexpr landexpr borexpr
%type <node> bandexpr cmpexpr unionexpr addexpr mulexpr shiftexpr prefixexpr postfixexpr
@@ -137,11 +137,11 @@
%type <node> pat unionpat match
%type <node> castexpr
%type <ucon> unionelt
-%type <node> body
+%type <node> body
%type <nodelist> arglist argdefs params matches
%type <nodelist> structbody seqbody tupbody tuprest
-%type <uconlist> unionbody
+%type <uconlist> unionbody
%union {
struct {
@@ -163,6 +163,8 @@
int line;
char *name;
Type *type;
+ Type **params;
+ size_t nparams;
} tydef;
Node *node;
Tok *tok;
@@ -256,16 +258,30 @@
{$$ = $3; setns($3, $1->str);}
;
-tydef : Ttype Tident Tasn type
+tydef : Ttype typeid Tasn type
+ {$$ = $2;
+ $$.type = mktyalias($2.line, mkname($2.line, $2.name), $4);}
+ | Ttype typeid
+ {$$ = $2;}
+ ;
+
+typeid : Tident
{$$.line = $1->line;
- $$.name = $2->str;
- $$.type = mktyalias($2->line, mkname($2->line, $2->str), $4);}
- | Ttype Tident
- {$$.line = $1->line;
- $$.name = $2->str;
+ $$.name = $1->str;
+ $$.params = NULL;
$$.type = NULL;}
+ | Tident Toparen typarams Tcparen
+ {$$.line = $1->line;
+ $$.name = $1->str;
+ $$.params = NULL;
+ $$.type = NULL;
+ die("Unimplemented generic types");}
;
+typarams: generictype
+ | typarams Tcomma generictype
+ ;
+
type : structdef
| tupledef
| uniondef
@@ -300,8 +316,9 @@
| type Tosqbrac Tcolon Tcsqbrac {$$ = mktyslice($2->line, $1);}
| type Tosqbrac expr Tcsqbrac {$$ = mktyarray($2->line, $1, $3);}
| type Tstar {$$ = mktyptr($2->line, $1);}
- | name {$$ = mktynamed($1->line, $1);}
| Tat Tident {$$ = mktyparam($1->line, $2->str);}
+ | name {$$ = mktynamed($1->line, $1);}
+ | name Toparen typelist Tcparen {die("Generic types not supported");}
;
functype: Toparen funcsig Tcparen {$$ = $2;}
@@ -325,15 +342,14 @@
$$.nn = 0;}
;
-tupledef: Tosqbrac tuptybody Tcsqbrac
+tupledef: Tosqbrac typelist Tcsqbrac
{$$ = mktytuple($1->line, $2.types, $2.ntypes);}
;
-tuptybody
- : type
+typelist: type
{$$.types = NULL; $$.ntypes = 0;
lappend(&$$.types, &$$.ntypes, $1);}
- | tuptybody Tcomma type
+ | typelist Tcomma type
{lappend(&$$.types, &$$.ntypes, $3);}
;
@@ -714,6 +730,8 @@
Type *b;
size_t i;
+ if (!t)
+ return;
b = tybase(t);
if (b->type != Tyunion)
return;
--- a/test/tests
+++ b/test/tests
@@ -57,6 +57,7 @@
B generic E 42
B cstr-builtin E 42
B genericcall E 42
+B generictype E 0
B sizeof E 4
B gsizeof E 5
B mkunion E 0