shithub: mc

Download patch

ref: 9424339d8d453f5c559edd5d23549d662d1c9d8d
parent: e6967548eec255e4518b1cdff5955d4b333f103b
author: Ori Bernstein <[email protected]>
date: Tue Jan 2 17:14:43 EST 2018

Fix how we bind types.

	Now we accept most valid programs, and reject most invalid ones.

--- a/parse/infer.c
+++ b/parse/infer.c
@@ -37,6 +37,7 @@
 
 static Type *tyfreshen(Tysubst *subst, Type *orig);
 static Type *tf(Type *t);
+static Type *basetype(Type *a);
 
 static Type *unify(Node *ctx, Type *a, Type *b);
 static Type *tyfix(Node *ctx, Type *orig, int noerr);
@@ -463,7 +464,7 @@
 static Type *
 tyfreshen(Tysubst *subst, Type *orig)
 {
-	Type *ty;
+	Type *ty, *base;
 
 	if (!needfreshen(orig))
 		return orig;
@@ -477,6 +478,9 @@
 	}
 	ty->spec = orig->spec;
 	ty->nspec = orig->nspec;
+	base = basetype(ty);
+	if (base)
+		htput(seqbase, ty, base);
 	popenv(orig->env);
 	return ty;
 }
@@ -2594,7 +2598,8 @@
 		typesub(n->iterstmt.elt, noerr);
 		typesub(n->iterstmt.seq, noerr);
 		typesub(n->iterstmt.body, noerr);
-		additerspecialization(n, curstab());
+		if (!ingeneric)
+			additerspecialization(n, curstab());
 		break;
 	case Nmatchstmt:
 		typesub(n->matchstmt.val, noerr);
@@ -2693,6 +2698,8 @@
 			tr = traittab[Tciter];
 			assert(tr->nproto == 2);
 			ty = exprtype(n->iterstmt.seq);
+			if (ty->type == Typaram)
+				continue;
 
 			it = itertype(n->iterstmt.seq, mktype(n->loc, Tybool));
 			d = specializedcl(tr->proto[0], ty, it, &name);
@@ -2855,6 +2862,7 @@
 	Type *ty;
 
 	pushstab(file->file.globls);
+	seqbase = mkht(tyhash, tyeq);
 	traitmap = zalloc(sizeof(Traitmap));
 	builtintraits();
 	for (i = 0; i < nimpltab; i++) {
--- a/parse/parse.h
+++ b/parse/parse.h
@@ -360,7 +360,6 @@
 };
 
 /* globals */
-extern Htab *seqbase;
 extern Srcloc curloc;
 extern char *filename;
 extern Tok *curtok;	/* the last token we tokenized */
@@ -378,6 +377,7 @@
 extern size_t ndecls;
 extern Node **exportimpls;
 extern size_t nexportimpls;
+extern Htab *seqbase;
 
 /* property tables */
 extern int opispure[];
--- a/parse/specialize.c
+++ b/parse/specialize.c
@@ -98,6 +98,9 @@
 		ret = mktyvar(t->loc);
 		ret->trneed = bsdup(t->trneed);
 		substput(tsmap, t, ret);
+		tmp = htget(seqbase, t);
+		if (tmp)
+			htput(seqbase, ret, tmp);
 		break;
 	case Tygeneric:
 		var = mktyvar(t->loc);
--- a/parse/stab.c
+++ b/parse/stab.c
@@ -671,6 +671,9 @@
 			tytab[t->tid] = tt;
 		else if (!boundtype(t))
 			htput(e->tab, t, t);
+		for (i = 0; i < t->nspec; i++)
+			if (t->spec[i]->aux)
+				bindtype_rec(e, t->spec[i]->aux, visited);
 		break;
 	case Tygeneric:
 		for (i = 0; i < t->ngparam; i++)
--- a/parse/type.c
+++ b/parse/type.c
@@ -1084,7 +1084,6 @@
 	Type *ty;
 	Trait *tr;
 
-	seqbase = mkht(tyhash, tyeq);
 	eqcache = mkht(typairhash, typaireq);
 	tydeduptab = mkht(tyhash, tystricteq);
 	/* this must be done after all the types are created, otherwise we will