#include void scc_mir_func_meta_init(scc_mir_func_meta_t *func_meta) { func_meta->frame_size = 0; func_meta->stack_alignment = 0; func_meta->vregs_count = 0; scc_vec_init(func_meta->stack_slots); // For null stack slot scc_vec_push(func_meta->stack_slots, (scc_mir_stack_slot_t){0}); scc_hashtable_usize_init(&func_meta->vreg2physic); } int scc_mir_alloc_vreg(scc_mir_func_t *func) { scc_mir_func_meta_t *meta = SCC_MIR_FUNC_META(func); return meta->vregs_count++; } void scc_mir_vreg_op(const scc_mir_func_t *func, int vreg, scc_mir_operand_t *out) { scc_mir_func_meta_t *meta = SCC_MIR_FUNC_META(func); isize idx = (isize)scc_hashtable_get(&meta->vreg2physic, (void *)(usize)vreg); if (idx == 0) { out->kind = SCC_MIR_OP_VREG; out->vreg = vreg; } else if (idx < 0) { out->kind = SCC_MIR_OP_PREG; out->preg = (int)-idx; } else { out->kind = SCC_MIR_OP_STACK_SLOT; Assert(idx < scc_vec_size(meta->stack_slots)); out->stack_slot = (int)(usize)idx; } } void scc_mir_vreg_map2preg(scc_mir_func_t *func, int vreg, int preg) { scc_mir_func_meta_t *meta = SCC_MIR_FUNC_META(func); isize val = (isize)scc_hashtable_get(&meta->vreg2physic, (void *)(usize)vreg); if (val != 0) { Panic("vreg %d already mapped", vreg); return; } scc_hashtable_set(&meta->vreg2physic, (void *)(usize)vreg, (void *)(usize)(isize)-preg); } int scc_mir_vreg_map2slot(scc_mir_func_t *func, int vreg, int size, int align) { scc_mir_func_meta_t *meta = SCC_MIR_FUNC_META(func); isize val = (isize)scc_hashtable_get(&meta->vreg2physic, (void *)(usize)vreg); if (val != 0) { Panic("vreg %d already mapped", vreg); return 0; } int new_slot = scc_vec_size(meta->stack_slots); scc_mir_stack_slot_t s = { .slot_id = new_slot, .size = size, .alignment = align, .offset = 0}; scc_vec_push(meta->stack_slots, s); scc_hashtable_set(&meta->vreg2physic, (void *)(usize)vreg, (void *)(usize)new_slot); return new_slot; }