Files
scc/libs/ir/lir/include/scc_lir.h
zzy e5cb70732e feat(lir): 添加函数参数操作数类型支持
添加 SCC_LIR_INSTR_KIND_ARG 枚举值用于表示函数参数操作数,
修改 scc_lir_instr 结构体以支持参数类型的值存储,
新增 SCC_LIR_ARG 宏定义用于创建参数操作数,
更新 HIR 到 LIR 的转换逻辑以正确处理函数参数引用。

BREAKING CHANGE: 修改了 LIR 指令格式以支持参数操作数类型。

refactor(mir): 重命名并重构 x86_64 指令选择模块

将 mir_x86.c 重命名为 arch/x86_64_isel.c,
创建新的头文件 arch/x86_64_isel.h,
重构结构体名称为 scc_x86_64_isel_t,
统一函数命名前缀为 scc_x86_,
移除重复的包含头文件。

feat(abi): 添加 ABI 降低框架接口定义

定义 scc_abi_lowering_t 结构体用于 ABI 降低功能,
提供函数指针类型定义用于调用、返回、参数等处理,
为后续实现不同平台 ABI 支持奠定基础。

fix(x86): 支持参数操作数的 MIR 转换

更新 lir_val_to_mir_op 函数以处理 SCC_LIR_INSTR_KIND_ARG 类型,
通过 ABI 降低框架获取参数的实际物理位置,
修复移位运算和除法运算中的函数调用命名。

test: 更新测试用例期望值

调整多个测试用例的期望返回值,
修改字符串字面量和循环条件以匹配新的预期行为,
确保测试用例与编译器功能变化保持一致。
2026-05-07 20:07:27 +08:00

277 lines
7.4 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/**
* @file scc_lir.h
* @brief 低层中间表示 (Low-Level IR) - 实用精简版
*
* 设计原则:
* - 依赖 scc_core.h 和 scc_utils.h (仅使用哈希表)
* - 保留所有核心功能复杂地址、并行复制、VA 支持、符号引用
* - 基本块使用稳定 ID通过哈希表快速查找
* - 预留属性位掩码 (attr),未来可扩展 align、packed、weak 等
* - 无字符串池、无类型缓存,保持简单
*/
#ifndef __SCC_LIR_H__
#define __SCC_LIR_H__
#include <scc_ap.h>
#include <scc_cfg.h>
#include <scc_core.h>
#include <scc_hashtable.h>
#include <scc_pos.h>
typedef enum scc_lir_attr {
SCC_LIR_ATTR_NONE = 0,
SCC_LIR_ATTR_STATIC = 1 << 0, // 内部链接
SCC_LIR_ATTR_WEAK = 1 << 1, // 弱符号
SCC_LIR_ATTR_VIS_HIDDEN = 1 << 2, // 符号可见性 hidden
SCC_LIR_ATTR_NOINLINE = 1 << 3,
SCC_LIR_ATTR_ALWAYSINLINE = 1 << 4,
// 对齐值可编码在 attr 的高位,例如:
// #define SCC_LIR_ATTR_ALIGN(n) (((n) << 8) | SCC_LIR_ATTR_ALIGN_FLAG)
} scc_lir_attr_t;
typedef enum {
SCC_LIR_INSTR_KIND_NONE, // 无操作数
SCC_LIR_INSTR_KIND_ARG, // 参数
SCC_LIR_INSTR_KIND_VREG, // 虚拟寄存器
// SCC_LIR_INSTR_KIND_PREG, // 物理寄存器 (后端定义编号)
SCC_LIR_INSTR_KIND_IMM, // 整数立即数
SCC_LIR_INSTR_KIND_FIMM, // 浮点立即数
SCC_LIR_INSTR_KIND_SYMBOL, // 全局符号 (函数名、全局变量、字符串常量)
SCC_LIR_INSTR_KIND_MEM, // 复杂地址表达式 (base + index*scale + offset)
} scc_lir_instr_kind_t;
/**
* @brief 复杂地址表达式
* base + index * scale + offset
*/
typedef struct scc_lir_addr {
int base; // 基址寄存器,-1 表示无
int index; // 索引寄存器,-1 表示无
int scale; // 比例因子 (1, 2, 4, 8)
i64 offset; // 常量偏移
} scc_lir_addr_t;
typedef struct scc_lir_instr {
scc_lir_instr_kind_t kind;
union {
int arg;
int reg; // VREG 或 PREG 索引
scc_ap_t imm; // 整型立即数
f64 fimm; // 浮点立即数
const char *symbol; // 符号名 (生命周期由前端管理)
scc_lir_addr_t addr; // 复杂地址
} data;
} scc_lir_val_t;
/* 构造宏 */
#define SCC_LIR_NONE() ((scc_lir_val_t){.kind = SCC_LIR_INSTR_KIND_NONE})
#define SCC_LIR_VREG(n) \
((scc_lir_val_t){.kind = SCC_LIR_INSTR_KIND_VREG, .data.reg = (n)})
#define SCC_LIR_IMM(v) \
((scc_lir_val_t){.kind = SCC_LIR_INSTR_KIND_IMM, .data.imm = (v)})
#define SCC_LIR_FIMM(v) \
((scc_lir_val_t){.kind = SCC_LIR_INSTR_KIND_FIMM, .data.fimm = (v)})
#define SCC_LIR_SYMBOL(s) \
((scc_lir_val_t){.kind = SCC_LIR_INSTR_KIND_SYMBOL, .data.symbol = (s)})
#define SCC_LIR_ADDR(b, i, s, o) \
((scc_lir_val_t){.kind = SCC_LIR_INSTR_KIND_MEM, .data.addr = {b, i, s, o}})
#define SCC_LIR_ARG(n) \
((scc_lir_val_t){.kind = SCC_LIR_INSTR_KIND_ARG, .data.arg = (n)})
#define SCC_LIR_SIZE_8 1
#define SCC_LIR_SIZE_16 2
#define SCC_LIR_SIZE_32 4
#define SCC_LIR_SIZE_64 8
typedef enum {
SCC_LIR_EXT_NONE,
SCC_LIR_EXT_SEXT,
SCC_LIR_EXT_ZEXT,
SCC_LIR_EXT_FLOAT
} scc_lir_ext_t;
typedef enum {
/* 数据移动 */
SCC_LIR_MOV,
SCC_LIR_LOAD,
SCC_LIR_LOAD_ADDR,
SCC_LIR_STORE,
SCC_LIR_STORE_ADDR,
SCC_LIR_LEA,
/* 整数算术 */
SCC_LIR_ADD,
SCC_LIR_SUB,
SCC_LIR_MUL,
SCC_LIR_DIV_S,
SCC_LIR_DIV_U,
SCC_LIR_REM_S,
SCC_LIR_REM_U,
SCC_LIR_AND,
SCC_LIR_OR,
SCC_LIR_XOR,
SCC_LIR_SHL,
SCC_LIR_SHR,
SCC_LIR_SAR,
SCC_LIR_NEG,
SCC_LIR_NOT,
/* 浮点算术 */
SCC_LIR_FADD,
SCC_LIR_FSUB,
SCC_LIR_FMUL,
SCC_LIR_FDIV,
SCC_LIR_FNEG,
SCC_LIR_FCVT,
/* 比较 */
SCC_LIR_CMP,
/* 控制流 */
SCC_LIR_BR,
SCC_LIR_JMP,
SCC_LIR_JMP_INDIRECT,
SCC_LIR_CALL,
SCC_LIR_CALL_INDIRECT,
SCC_LIR_RET,
/* 并行复制 */
SCC_LIR_PARALLEL_COPY,
/* 可变参数 */
SCC_LIR_VA_START,
SCC_LIR_VA_ARG,
SCC_LIR_VA_END,
SCC_LIR_VA_COPY,
/* 栈管理 */
SCC_LIR_ALLOCA,
SCC_LIR_NOP
} scc_lir_op_t;
typedef enum {
SCC_LIR_COND_EQ,
SCC_LIR_COND_NE,
SCC_LIR_COND_SLT,
SCC_LIR_COND_SLE,
SCC_LIR_COND_SGT,
SCC_LIR_COND_SGE,
SCC_LIR_COND_ULT,
SCC_LIR_COND_ULE,
SCC_LIR_COND_UGT,
SCC_LIR_COND_UGE,
SCC_LIR_COND_FEQ,
SCC_LIR_COND_FNE,
SCC_LIR_COND_FLT,
SCC_LIR_COND_FLE,
SCC_LIR_COND_FGT,
SCC_LIR_COND_FGE
} scc_lir_cond_t;
typedef scc_cfg_bblock_id_t scc_lir_bblock_id_t;
typedef struct scc_lir_ins {
scc_lir_op_t op;
u8 size;
scc_lir_ext_t ext;
scc_lir_val_t to;
scc_lir_val_t arg0;
scc_lir_val_t arg1;
/// @brief debug 信息
scc_pos_t src_loc;
union {
scc_lir_cond_t cond;
struct scc_lir_br {
scc_lir_bblock_id_t true_target;
scc_lir_bblock_id_t false_target;
} br;
scc_lir_bblock_id_t jmp_target;
struct scc_lir_call {
const char *callee;
scc_lir_val_t *args;
int arg_count;
scc_lir_val_t ret_vreg;
u64 clobber_mask;
} call;
struct scc_lir_call_indirect {
scc_lir_val_t target;
scc_lir_val_t *args;
int arg_count;
scc_lir_val_t ret_vreg;
u64 clobber_mask;
} call_indirect;
scc_lir_val_t ret_val;
struct scc_lir_parallel_copy {
scc_lir_val_t *dests;
scc_lir_val_t *srcs;
int num_copies;
} parallel_copy;
struct scc_lir_alloca {
int size_bytes;
int align_bytes;
} alloca;
struct {
scc_lir_val_t ap;
scc_lir_val_t last;
} va_start;
struct {
scc_lir_val_t ap;
int type_size;
int type_align;
char is_float;
scc_lir_val_t to;
} va_arg;
struct {
scc_lir_val_t ap;
} va_end;
struct {
scc_lir_val_t dest;
scc_lir_val_t src;
} va_copy;
} metadata;
} scc_lir_instr_t;
typedef SCC_VEC(scc_lir_instr_t) scc_lir_instr_vec_t;
typedef scc_cfg_bblock_t scc_lir_bblock_t;
#define SCC_LIR_BBLOCK_VALUES(bblock) \
((scc_lir_instr_vec_t *)&((bblock)->values))
typedef scc_cfg_func_t scc_lir_func_t;
typedef struct scc_lir_func_meta {
int vregs_count;
int frame_size;
scc_lir_attr_t attr;
} scc_lir_func_meta_t;
#define SCC_LIR_FUNC_META(func) ((scc_lir_func_meta_t *)(func)->meta)
typedef scc_cfg_symbol_id_t scc_lir_symbol_id_t;
typedef scc_cfg_symbol_t scc_lir_symbol_t;
typedef struct scc_lir_symbol_meta {
union {
struct {
scc_lir_func_t *func; // 指向函数体(若为定义)
} func;
struct {
u8 *init_data; // 初始化数据(若为 NULL 则零初始化)
usize size; // 数据大小(字节)
int align; // 对齐要求
} data;
};
} scc_lir_symbol_meta_t;
#define SCC_LIR_SYMBOL_META(symbol) ((scc_lir_symbol_meta_t *)(symbol)->meta)
#endif /* __SCC_LIR_H__ */