qbe

Internal scc patchset buffer for QBE
Log | Files | Refs | README | LICENSE

commit 5b54910adcd012c98da49bcbffb89cdd5acaef47
parent 62ff1f2f50c70573e2613cf616d53dd89c5461f2
Author: Quentin Carbonneaux <quentin.carbonneaux@yale.edu>
Date:   Fri, 30 Oct 2015 13:15:25 -0400

add simple dce into isel

This looks simple, but it's unclear that the use counts
are correct or at least sound after all the instruction
massaging that happens for calls/jumps.

Diffstat:
Mlisc/isel.c | 24+++++++++++++++++++++++-
1 file changed, 23 insertions(+), 1 deletion(-)

diff --git a/lisc/isel.c b/lisc/isel.c @@ -12,6 +12,11 @@ * - implement fast locals (the streak of * constant allocX in the first basic block) * - recognize complex addressing modes + * + * Invariant: the use counts that are used + * in sel() must be sound. This + * is not so trivial, maybe the + * dce should be moved out... */ typedef struct ANum ANum; @@ -86,6 +91,13 @@ fixargs(Ins *i, Fn *fn) } static void +chuse(Ref r, int du, Fn *fn) +{ + if (rtype(r) == RTmp) + fn->tmp[r.val].nuse += du; +} + +static void seladdr(Ref *r, ANum *an, Fn *fn) { Addr a; @@ -93,14 +105,17 @@ seladdr(Ref *r, ANum *an, Fn *fn) r0 = *r; if (rtype(r0) == RTmp) { + chuse(r0, -1, fn); r1 = an[r0.val].mem; if (req(r1, R)) { amatch(&a, r0, an, fn, 1); vgrow(&fn->mem, ++fn->nmem); fn->mem[fn->nmem-1] = a; r1 = MEM(fn->nmem-1); + chuse(a.base, +1, fn); + chuse(a.index, +1, fn); if (rtype(a.base) != RTmp) - if (req(a.index, R)) + if (rtype(a.index) != RTmp) an[r0.val].mem = r1; } *r = r1; @@ -130,6 +145,13 @@ sel(Ins i, ANum *an, Fn *fn) int64_t val; Ins *i0; + if (rtype(i.to) == RTmp) + if (!isreg(i.to) && !isreg(i.arg[0]) && !isreg(i.arg[1])) + if (fn->tmp[i.to.val].nuse == 0) { + chuse(i.arg[0], -1, fn); + chuse(i.arg[1], -1, fn); + return; + } i0 = curi; w = i.wide; switch (i.op) {