ref: 3d71446ecb6569add0d9eaf2e7e4a05d99bd2625
parent: 35b4358b60d0afdff7e4599a9e625c0fc1580288
author: Ori Bernstein <ori@eigenstate.org>
date: Tue Apr 17 18:28:18 EDT 2018
Don't mutate the traits on builtin types. mktylike() should return a generic type based on the builtin, and that means that if we mutate the builtin, we will be adding traits to our literals. This is wrong on multiple levels. First off, it means that '@t :: numeric,integral @t' will now require whatever other types are implemented over literals. And second, it means that if, for example, a trait is implemented for flt64, flt32 literals will also need it.
--- a/parse/infer.c
+++ b/parse/infer.c
@@ -70,6 +70,7 @@
static Stab **specializationscope;
static size_t nspecializationscope;
static Traitmap *traitmap;
+static Bitset *tytraits[Ntypes];
static void
@@ -687,7 +688,7 @@
t = mktyvar(l);
/* not perfect in general, but good enough for all places mktylike is used. */
- t->trneed = bsdup(traitmap->sub[other]->traits);
+ t->trneed = bsdup(tytraits[other]);
return t;
}
@@ -2785,41 +2786,47 @@
/* char::(numeric,integral) */
for (i = 0; i < Ntypes; i++)
- traitmap->sub[i] = mktraitmap();
+ tytraits[i] = mkbs();
- bsput(traitmap->sub[Tychar]->traits, Tcnum);
- bsput(traitmap->sub[Tychar]->traits, Tcint);
+ bsput(tytraits[Tychar], Tcnum);
+ bsput(tytraits[Tychar], Tcint);
- bsput(traitmap->sub[Tybyte]->traits, Tcnum);
- bsput(traitmap->sub[Tybyte]->traits, Tcint);
+ bsput(tytraits[Tybyte], Tcnum);
+ bsput(tytraits[Tybyte], Tcint);
/* <integer types>::(numeric,integral) */
for (i = Tyint8; i < Tyflt32; i++) {
- bsput(traitmap->sub[i]->traits, Tcnum);
- bsput(traitmap->sub[i]->traits, Tcint);
+ bsput(tytraits[i], Tcnum);
+ bsput(tytraits[i], Tcint);
}
/* <floats>::(numeric,floating) */
- bsput(traitmap->sub[Tyflt32]->traits, Tcnum);
- bsput(traitmap->sub[Tyflt32]->traits, Tcflt);
- bsput(traitmap->sub[Tyflt64]->traits, Tcnum);
- bsput(traitmap->sub[Tyflt64]->traits, Tcflt);
+ bsput(tytraits[Tyflt32], Tcnum);
+ bsput(tytraits[Tyflt32], Tcflt);
+ bsput(tytraits[Tyflt64], Tcnum);
+ bsput(tytraits[Tyflt64], Tcflt);
/* @a*::(sliceable) */
- bsput(traitmap->sub[Typtr]->traits, Tcslice);
+ bsput(tytraits[Typtr], Tcslice);
/* @a[:]::(indexable,sliceable) */
- bsput(traitmap->sub[Tyslice]->traits, Tcidx);
- bsput(traitmap->sub[Tyslice]->traits, Tcslice);
- bsput(traitmap->sub[Tyslice]->traits, Tciter);
+ bsput(tytraits[Tyslice], Tcidx);
+ bsput(tytraits[Tyslice], Tcslice);
+ bsput(tytraits[Tyslice], Tciter);
/* @a[SZ]::(indexable,sliceable) */
- bsput(traitmap->sub[Tyarray]->traits, Tcidx);
- bsput(traitmap->sub[Tyarray]->traits, Tcslice);
- bsput(traitmap->sub[Tyarray]->traits, Tciter);
+ bsput(tytraits[Tyarray], Tcidx);
+ bsput(tytraits[Tyarray], Tcslice);
+ bsput(tytraits[Tyarray], Tciter);
/* @a::function */
- bsput(traitmap->sub[Tyfunc]->traits, Tcfunc);
+ bsput(tytraits[Tyfunc], Tcfunc);
+
+ for (i = 0; i < Ntypes; i++) {
+ traitmap->sub[i] = mktraitmap();
+ bsunion(traitmap->sub[i]->traits, tytraits[i]);
+ }
+
}
static Trait*