#ifndef __SCC_MIR_H__ #define __SCC_MIR_H__ #include // 伪指令 opcode(负数),所有后端通用约定 typedef enum { SCC_MIR_PSEUDO_NONE = 0, SCC_MIR_PSEUDO_ALLOCA = -1, SCC_MIR_PSEUDO_VA_START = -2, } scc_mir_pseudo_t; typedef struct scc_mir_instr { int opcode; union { struct { int size; int align; int vreg; } alloc; } data; } scc_mir_instr_t; #define SCC_MIR_BBLOCK_VALUES_PTR(bb) ((void *)(&(bb)->values)) // 栈槽信息(由 FrameLayout Pass 填充) typedef struct scc_mir_stack_slot { int slot_id; int size; // 通常是 8 字节 (指针大小) int alignment; // 对齐要求 int offset; // 相对于 RSP 的偏移 (最终确定) int arg_idx; // == 0 means local slot, > 0 means argument slot } scc_mir_stack_slot_t; typedef SCC_VEC(scc_mir_stack_slot_t) scc_mir_stack_slot_vec_t; typedef scc_cfg_bblock_t scc_mir_bblock_t; // 函数元数据 —— 不包含任何指令结构,由各后端自行定义指令布局 typedef scc_cfg_func_t scc_mir_func_t; typedef struct scc_mir_func_meta { int need_va_args; int frame_size; int stack_alignment; int vregs_count; void *target_data; // 目标后端私有数据,例如 x86_64_func_info_t* scc_mir_stack_slot_vec_t stack_slots; // vreg -> phys reg / stack slot // 0 = not mapped (still a vreg) // >0 = stack slot index // <0 = physical register (negated) scc_hashtable_t vreg2physic; } scc_mir_func_meta_t; #define SCC_MIR_FUNC_META(func) ((scc_mir_func_meta_t *)(func)->meta) void scc_mir_func_meta_init(scc_mir_func_meta_t *func_meta); int scc_mir_alloc_vreg(scc_mir_func_t *func); void scc_mir_vreg_map2preg(scc_mir_func_t *func, int vreg, int preg); int scc_mir_vreg_map2slot(scc_mir_func_t *func, int vreg, int size, int align); // 从 vreg2physic 表中查询映射结果: // 返回 0 → 该 vreg 仍为 vreg,未映射 // 返回 1 → 已映射到物理寄存器,*out_preg 有效 // 返回 -1 → 已溢出到栈槽,*out_slot 有效 static inline int scc_mir_vreg_lookup(const scc_mir_func_t *func, int vreg, int *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) return 0; if (idx < 0) { *out = (int)-idx; return 1; } *out = (int)idx; return -1; } static inline scc_mir_stack_slot_t * scc_mir_unsafe_slot(const scc_mir_func_t *func, int slot) { Assert(slot > 0); return &scc_vec_at(SCC_MIR_FUNC_META(func)->stack_slots, slot); } #endif /* __SCC_MIR_H__ */