fix(sem)解决数组变量绑定缺失问题

feature/sem
mxr 2 weeks ago
parent 0826c86772
commit c945a61f90

@ -121,15 +121,6 @@ std::any IRGenImpl::visitLVal(SysYParser::LValContext* ctx) {
// 首先尝试从语义分析获取变量定义
auto* var_decl = sema_.ResolveVarUse(ctx);
// 从语义分析获取变量定义
auto* decl = sema_.ResolveVarUse(ctx);
if (!decl) {
auto* const_def = sema_.ResolveConstUse(ctx);
if (!const_def) {
FormatError("irgen",
"使用缺少语义绑定: " + varName);
}
}
if (var_decl) {
// 找到变量定义

@ -180,6 +180,9 @@ public:
if (is_array) {
// 处理数组维度
for (auto* dim_exp : ctx->constExp()) {
// ========== 绑定维度表达式 ==========
dim_exp->addExp()->accept(this); // 触发常量绑定(如 N
int dim = table_.EvaluateConstExp(dim_exp);
if (dim <= 0) {
throw std::runtime_error(FormatError("sema", "数组维度必须为正整数"));
@ -212,6 +215,10 @@ public:
if (is_global && has_init) {
CheckGlobalInitIsConst(ctx->initVal()); // 全局变量初始化必须是常量表达式
}
// ========== 绑定初始化表达式 ==========
if (ctx->initVal()) {
BindInitVal(ctx->initVal());
}
// 创建符号
Symbol sym;
sym.name = name;
@ -275,9 +282,18 @@ public:
type = ir::Type::GetArrayType(base_type, dims);
std::cout << "[DEBUG] 创建数组类型完成IsArray: " << type->IsArray() << std::endl;
}
// ========== 绑定维度表达式 ==========
for (auto* dim_exp : ctx->constExp()) {
dim_exp->addExp()->accept(this);
}
// 求值初始化器
std::vector<SymbolTable::ConstValue> init_values;
if (ctx->constInitVal()) {
// ========== 绑定初始化表达式 ==========
BindConstInitVal(ctx->constInitVal());
init_values = table_.EvaluateConstInitVal(ctx->constInitVal(), dims, base_type);
std::cout << "[DEBUG] 初始化值数量: " << init_values.size() << std::endl;
}
@ -294,6 +310,7 @@ public:
Symbol sym;
sym.name = name;
sym.kind = SymbolKind::Constant;
std::cout << "CheckConstDef: before addSymbol, sym.kind = " << (int)sym.kind << std::endl;
sym.type = type;
sym.scope_level = table_.currentScopeLevel();
sym.is_initialized = true;
@ -314,6 +331,10 @@ public:
std::cout << "[DEBUG] 数组常量,不存储单个常量值" << std::endl;
}
table_.addSymbol(sym);
std::cout << "CheckConstDef: after addSymbol, sym.kind = " << (int)sym.kind << std::endl;
auto* stored = table_.lookup(name);
std::cout << "CheckConstDef: after addSymbol, stored const_def_ctx = " << stored->const_def_ctx << std::endl;
std::cout << "[DEBUG] 常量符号添加完成" << std::endl;
}
@ -1056,6 +1077,8 @@ private:
if (!sym) {
throw std::runtime_error(FormatError("sema", "未定义的变量: " + name));
}
std::cout << "CheckLValue: found sym->name = " << sym->name
<< ", sym->kind = " << (int)sym->kind << std::endl;
if (sym->kind == SymbolKind::Variable && sym->var_def_ctx) {
sema_.BindVarUse(ctx, sym->var_def_ctx);
@ -1448,6 +1471,29 @@ private:
throw std::runtime_error(FormatError("sema", "main 函数不能有参数"));
}
}
void BindConstInitVal(SysYParser::ConstInitValContext* ctx) {
if (!ctx) return;
if (ctx->constExp()) {
// 遍历表达式树,触发 visitLVal 中的绑定
ctx->constExp()->addExp()->accept(this);
} else {
for (auto* sub : ctx->constInitVal()) {
BindConstInitVal(sub);
}
}
}
void BindInitVal(SysYParser::InitValContext* ctx) {
if (!ctx) return;
if (ctx->exp()) {
CheckExp(ctx->exp()); // 触发绑定
} else {
for (auto* sub : ctx->initVal()) {
BindInitVal(sub);
}
}
}
};
} // namespace

@ -39,6 +39,14 @@ bool SymbolTable::addSymbol(const Symbol& sym) {
return false; // 重复定义
}
current_scope[sym.name] = sym;
// 立即验证存储的符号
const auto& stored = current_scope[sym.name];
std::cout << "SymbolTable::addSymbol: stored " << sym.name
<< " with kind=" << (int)stored.kind
<< ", const_def_ctx=" << stored.const_def_ctx
<< std::endl;
return true;
}
@ -55,6 +63,12 @@ const Symbol* SymbolTable::lookup(const std::string& name) const {
const auto& scope = *it;
auto found = scope.find(name);
if (found != scope.end()) {
std::cout << "SymbolTable::lookup: found " << name
<< " in scope level " << (scopes_.rend() - it - 1)
<< ", kind=" << (int)found->second.kind
<< ", const_def_ctx=" << found->second.const_def_ctx
<< std::endl;
return &found->second;
}
}

Loading…
Cancel
Save