Beispiel #1
0
static void checkreach(Cfg *cfg)
{
    Bitset *reach, *kill;
    size_t i, j, k;
    Reaching *r;
    Node *n, *m;
    Bb *bb;

    r = reaching(cfg);
//    dumpcfg(cfg, stdout);
    for (i = 0; i < cfg->nbb; i++) {
        bb = cfg->bb[i];
        if (!bb)
            continue;
        reach = bsdup(r->in[i]);
        kill = mkbs();
        for (j = 0; j < bb->nnl; j++) {
            n = bb->nl[j];
            if (exprop(n) == Oundef) {
                bsput(reach, n->nid);
            } else {
                m = assignee(n);
                if (m)
                    for (k = 0; k < r->ndefs[m->expr.did]; k++)
                        bsput(kill, r->defs[m->expr.did][k]);
                checkundef(n, r, reach, kill);
            }
        }
        bsfree(reach);
        bsfree(kill);
    }
}
Beispiel #2
0
Reaching *reaching(Cfg *cfg)
{
	Bitset **in, **out;
	Bitset **gen, **kill;
	Bitset *bbin, *bbout;
	Reaching *reaching;
	size_t **defs;        /* mapping from did => [def,list] */
	size_t *ndefs;      
	size_t i, j;
	int changed;

	in = zalloc(cfg->nbb * sizeof(Bb*));
	out = zalloc(cfg->nbb * sizeof(Bb*));
	gen = zalloc(cfg->nbb * sizeof(Bb*));
	kill = zalloc(cfg->nbb * sizeof(Bb*));
	defs = zalloc(ndecls * sizeof(size_t*));
	ndefs = zalloc(ndecls * sizeof(size_t));

	collectdefs(cfg, defs, ndefs);
	for (i = 0; i < cfg->nbb; i++) {
		in[i] = mkbs();
		out[i] = mkbs();
		gen[i] = mkbs();
		kill[i] = mkbs();
		if (cfg->bb[i])
			genkill(cfg->bb[i], defs, ndefs, gen[i], kill[i]);
	}

	do {
		changed = 0;
		for (i = 0; i < cfg->nbb; i++) {
			if (!cfg->bb[i])
				continue;
			bbin = mkbs();
			for (j = 0; bsiter(cfg->bb[i]->pred, &j); j++)
				bsunion(bbin, out[j]);
			bbout = bsdup(bbin);
			bsdiff(bbout, kill[i]);
			bsunion(bbout, gen[i]);

			if (!bseq(out[i], bbout) || !bseq(in[i], bbin)) {
				changed = 1;
				bsfree(in[i]);
				bsfree(out[i]);
				in[i] = bbin;
				out[i] = bbout;
			}
		}
	} while (changed);


	reaching = xalloc(sizeof(Reaching));
	reaching->in = in;
	reaching->out = out;
	reaching->defs = defs;
	reaching->ndefs = ndefs;
	return reaching;
}
Beispiel #3
0
Datei: pipe.c Projekt: aiju/hdl
static void
doif(ASTNode *n, int ctxt)
{
	BitSet *g, *k, *kp;
	BitSet *g1, *k1, *k1p;
	BitSet *g2, *k2, *k2p, *t;
	PipeStage *p;

	p = stcur;
	t = bsnew(p->nvars);
	findstages(n->n1, ctxt);
	g = p->gen;
	k = p->kill;
	kp = p->killp;
	p->gen = g1 = bsdup(g);
	p->kill = k1 = bsdup(k);
	p->killp = k1p = bsdup(kp);
	findstages(n->n2, ctxt);
	p->gen = g2 = bsdup(g);
	p->kill = k2 = bsdup(k);
	p->killp = k2p = bsdup(kp);
	findstages(n->n3, ctxt);
	bsunion(g, g1, g);
	bsunion(g, g2, g);
	bsunion(k, k1, k);
	bsunion(k, k2, k);
	bsunion(kp, k1p, kp);
	bsunion(kp, k2p, kp);
	bsminus(t, k1, k2);
	addeq(t, &n->n3, 0);
	bsunion(g, t, g);
	bsminus(t, k2, k1);
	addeq(t, &n->n2, 0);
	bsunion(g, t, g);
	bsminus(t, k1p, k2p);
	addeq(t, &n->n3, 1);
	bsunion(g, t, g);
	bsminus(t, k2p, k1p);
	addeq(t, &n->n2, 1);
	bsunion(g, t, g);
	p->gen = g;
	p->kill = k;
	p->killp = kp;
	bsfree(g1);
	bsfree(g2);
	bsfree(k1);
	bsfree(k2);
	bsfree(k1p);
	bsfree(k2p);
	bsfree(t);
}
Beispiel #4
0
Datei: pipe.c Projekt: aiju/hdl
static Nodes *
process(ASTNode *n)
{
	Nodes *r, *s, *t;
	int ours;
	BitSet *ks;

	if(n == nil) return nil;
	switch(n->t){
	case ASTPIPEL:
		t = nil;
		s = nil;
		for(r = n->nl; r != nil; r = r->next)
			if(r->n->t == ASTSTATE){
				if(stcur == nil) stcur = stlist.next;
				else stcur = stcur->next;
				assert(stcur != nil && stcur->sym == r->n->sym);
				bsreset(killed);
				if(s != nil) t = nlcat(t, nl(node(ASTBLOCK, s)));
				s = nil;
			}else
				s = nlcat(s, process(r->n));
		if(s != nil) t = nlcat(t, nl(node(ASTBLOCK, s)));
		return t;

	case ASTSYMB:
		if(stcur != nil && n->sym->pipeidx >= 0)
			if(bstest(killed, n->sym->pipeidx))
				n->sym = stcur->outvars[n->sym->pipeidx];
			else
				n->sym = stcur->invars[n->sym->pipeidx];
		return nl(n);
	case ASTPRIME:
		ours = 0;
		return nl(lvalfix(n, 0, &ours));
	case ASTASS:
		n = nodedup(n);
		n->n2 = onlyone(process(n->n2));
		ours = 0;
		n->n1 = lvalfix(n->n1, LVAL, &ours);
		return nl(n);
	case ASTDECL:
		return nil;
	case ASTBLOCK:
		n = nodedup(n);
		s = nil;
		for(r = n->nl; r != nil; r = r->next)
			s = nlcat(s, process(r->n));
		n->nl = s;
		return nl(n);
	case ASTCINT:
	case ASTCONST:
		return nl(n);
	case ASTOP:
	case ASTTERN:
		n = nodedup(n);
		n->n1 = onlyone(process(n->n1));
		n->n2 = onlyone(process(n->n2));
		n->n3 = onlyone(process(n->n3));
		n->n4 = onlyone(process(n->n4));
		return nl(n);
	case ASTIF:
		n = nodedup(n);
		n->n1 = onlyone(process(n->n1));
		ks = killed;
		killed = bsdup(ks);
		n->n2 = onlyone(process(n->n2));
		bsfree(killed);
		killed = ks;
		n->n3 = onlyone(process(n->n3));
		return nl(n);
	default:
		warn(n, "process: unknown %A", n->t);
	}
	return nl(n);
}