use new vector functions instead of reallocs
This commit is contained in:
parent
1f61873799
commit
99ad19546d
5 changed files with 106 additions and 60 deletions
76
lisc/util.c
76
lisc/util.c
|
@ -1,5 +1,23 @@
|
|||
#include "lisc.h"
|
||||
|
||||
typedef struct Vec Vec;
|
||||
|
||||
struct Vec {
|
||||
ulong mag;
|
||||
size_t esz;
|
||||
ulong cap;
|
||||
union {
|
||||
long long ll;
|
||||
long double ld;
|
||||
void *ptr;
|
||||
} align[];
|
||||
};
|
||||
|
||||
enum {
|
||||
VMin = 2,
|
||||
VMag = 0xcabba9e,
|
||||
};
|
||||
|
||||
Typ typ[NTyp];
|
||||
Ins insb[NIns], *curi;
|
||||
|
||||
|
@ -80,3 +98,61 @@ icpy(Ins *d, Ins *s, ulong n)
|
|||
memcpy(d, s, n * sizeof(Ins));
|
||||
return d + n;
|
||||
}
|
||||
|
||||
void *
|
||||
valloc(ulong len, size_t esz)
|
||||
{
|
||||
ulong cap;
|
||||
Vec *v;
|
||||
|
||||
v = alloc(len * esz + sizeof(Vec));
|
||||
v->mag = VMag;
|
||||
for (cap=VMin; cap<len; cap*=2)
|
||||
;
|
||||
v->cap = cap;
|
||||
v->esz = esz;
|
||||
return v + 1;
|
||||
}
|
||||
|
||||
void
|
||||
vgrow(void *vp, ulong len)
|
||||
{
|
||||
Vec *v;
|
||||
void *v1;
|
||||
|
||||
v = *(Vec **)vp - 1;
|
||||
assert(v+1 && v->mag == VMag);
|
||||
if (v->cap >= len)
|
||||
return;
|
||||
v1 = valloc(len, v->esz);
|
||||
memcpy(v1, v+1, v->cap * v->esz);
|
||||
free(v);
|
||||
*(Vec **)vp = v1;
|
||||
}
|
||||
|
||||
Ref
|
||||
newtmp(char *prfx, Fn *fn)
|
||||
{
|
||||
static int n;
|
||||
int t;
|
||||
|
||||
t = fn->ntmp++;
|
||||
vgrow(&fn->tmp, fn->ntmp);
|
||||
sprintf(fn->tmp[t].name, "%s%d", prfx, ++n);
|
||||
fn->tmp[t].spill = -1;
|
||||
return TMP(t);
|
||||
}
|
||||
|
||||
Ref
|
||||
getcon(int64_t val, Fn *fn)
|
||||
{
|
||||
int c;
|
||||
|
||||
for (c=0; c<fn->ncon; c++)
|
||||
if (fn->con[c].type == CNum && fn->con[c].val == val)
|
||||
return CON(c);
|
||||
fn->ncon++;
|
||||
vgrow(&fn->con, fn->ncon);
|
||||
fn->con[c] = (Con){.type = CNum, .val = val};
|
||||
return CON(c);
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue