diff options
| author | 2025-10-19 08:09:09 +0200 | |
|---|---|---|
| committer | 2025-10-19 08:09:09 +0200 | |
| commit | dea8fd171acb54b6d9685422d5e391fb55074008 (patch) | |
| tree | 2c149892f35c5183c9b2a1da4ab437228dc432ef /ir/ssa.c | |
| parent | 3437945692f2b87883a4f066473c9deed50f25f5 (diff) | |
Organize source files into directories
Diffstat (limited to 'ir/ssa.c')
| -rw-r--r-- | ir/ssa.c | 58 |
1 files changed, 58 insertions, 0 deletions
diff --git a/ir/ssa.c b/ir/ssa.c new file mode 100644 index 0000000..9b89878 --- /dev/null +++ b/ir/ssa.c @@ -0,0 +1,58 @@ +#include "ir.h" + +/* require use, keeps use */ +void +copyopt(struct function *fn) +{ + struct block *blk = fn->entry; + + do { + for (int i = 0; i < blk->ins.n; ++i) { + union ref var = mkref(RTMP, blk->ins.p[i]); + struct instr *ins = &instrtab[var.i]; + enum irclass k; + + if (ins->op == Ocopy) { + union ref arg = ins->l; + if (arg.t == RTMP) k = insrescls(instrtab[arg.i]); + else if (arg.t == RICON) k = cls2siz[ins->cls] == 4 ? KI4 : KI8; + else if (arg.t == RXCON) k = isnumcon(arg) ? conht[arg.i].cls : KPTR; + else continue; + if (ins->cls != k) continue; + + replcuses(var, arg); + *ins = mkinstr(Onop,0,); + deluses(var.i); + } + } + delnops(blk); + } while ((blk = blk->lnext) != fn->entry); +} + +void +filluses(struct function *fn) +{ + extern int ninstr; + struct block *blk = fn->entry; + + for (int i = 0; i < ninstr; ++i) + deluses(i); + + do { + for (int i = 0; i < blk->phi.n; ++i) { + int ins = blk->phi.p[i]; + union ref *phi = phitab.p[instrtab[ins].l.i]; + for (int i = 0; i < blk->npred; ++i) + adduse(blk, ins, phi[i]); + } + for (int i = 0; i < blk->ins.n; ++i) { + int ins = blk->ins.p[i]; + adduse(blk, ins, instrtab[ins].l); + adduse(blk, ins, instrtab[ins].r); + } + adduse(blk, USERJUMP, blk->jmp.arg[0]); + adduse(blk, USERJUMP, blk->jmp.arg[1]); + } while ((blk = blk->lnext) != fn->entry); +} + +/* vim:set ts=3 sw=3 expandtab: */ |