diff options
author | tomsmeding <tom.smeding@gmail.com> | 2018-01-24 23:00:31 +0100 |
---|---|---|
committer | tomsmeding <tom.smeding@gmail.com> | 2018-01-24 23:00:31 +0100 |
commit | 1fc88ae00940e04ee76cbdf13a5df429faf72451 (patch) | |
tree | 59692bd2354819ee8b7fea2253fcefacdf1ecce9 | |
parent | bd7ef7a572f3faa58a550baca46a1b4f95e9b95d (diff) |
Also do the BP dance if no spills occur
This is because arguments are annoyingly generated relative to
BP, which fails completely if the stack frame is not set up nicely.
TODO do stuff relative to SP so BP is just a general purpose register.
-rw-r--r-- | test/t2.c | 1 | ||||
-rw-r--r-- | to_assembly.c | 13 |
2 files changed, 10 insertions, 4 deletions
@@ -14,6 +14,7 @@ void main() { mov b, @dir hwi 1 // legs } + holo_dec(dir); dir = dir + 1; if (dir == 4) dir = 0; } diff --git a/to_assembly.c b/to_assembly.c index bd680b3..6f40e2d 100644 --- a/to_assembly.c +++ b/to_assembly.c @@ -81,13 +81,18 @@ static void fix_function(struct ir *ir, int startidx, struct allocation *ral) { } free(offsets); - - if (spillspace == 0) return; + + // TODO: Really, nothing should be relative to BP, instead everything should use SP. That + // would completely eliminate this BP dance anyway. + + // if (spillspace == 0) return; ir_insert_before(ir, startidx + 0, irins_make_1(INS_PUSH, ref_reg(REG_BP))); ir_insert_before(ir, startidx + 1, irins_make_01(INS_MOV, ref_reg(REG_BP), ref_reg(REG_SP))); - ir_insert_before(ir, startidx + 2, - irins_make_012(INS_SUB, ref_reg(REG_SP), ref_reg(REG_SP), ref_imm(spillspace))); + if (spillspace != 0) { + ir_insert_before(ir, startidx + 2, + irins_make_012(INS_SUB, ref_reg(REG_SP), ref_reg(REG_SP), ref_imm(spillspace))); + } for (int idx = startidx + 1; idx < ir->len; idx++) { struct irins *ins = ir->inss[idx]; |