You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

__static_initialization_and_destruction_0段错误问题排查求助

静态初始化阶段触发__static_initialization_and_destruction_0(int, int)段错误问题

程序运行时触发该段错误,且错误发生在main函数执行之前。即使移除构造函数中的this->push(false, T_VOID);代码行,错误依然存在。补充说明:所有源文件中未定义静态变量。


SymbolStack类定义(Symbols.h)

#ifndef HW3_SYMBOLS_H
#define HW3_SYMBOLS_H

#include <string>
#include <vector>
#include <iostream>
#include "shared_def.h"

using std::vector; using std::string;
extern int yylineno;

...

class SymbolStack {
public:
    vector<int> pos_stack = vector<int>();
    vector<SymbolTable*> scope_stack = vector<SymbolTable*>();
public:
    SymbolStack();
    ErrorType is_func_valid(const string& func_name, const string& retype, vector<string>* params_types, bool is_override);
    void push(bool is_while, Types retType = T_NONE);
    void pop();
    SymbolTable* get_curr_scope();
    void symbol_document(const string& symbol_name,const string& symbol_type, bool is_func = false,
                         bool is_over = false, vector<string>* func_params_types = nullptr); // add new symbol to the stack
    void func_param_document(const string& symbol_name, const string& symbol_type, int pos); // add new function to the stack
    bool symbol_exists(const string& symbol_name); // does a symbol exists?
    SymbolEntry* get_symbol(const string& symbol_name);
    SymbolEntry* get_func_symbol(const string& func_name, const string& retype, vector<string>* params_types, int* count); // if retype == "" error if count >= 2
   // bool function_exists(const string& name, vector<string>* params_types = nullptr);
    bool check_program();
    ~SymbolStack();
};

...

#endif //HW3_SYMBOLS_H

注:Types是shared_def.h中定义的枚举类型


SymbolStack实现代码(Symbols.cpp)

SymbolStack::SymbolStack(){
    pos_stack.push_back(0); // init to offset = zero
    this->push(false, T_VOID);
    vector<string> print_param = vector<string>();
    vector<string> printi_param = vector<string>();
    print_param.push_back("string");
    printi_param.push_back("int");
    this->symbol_document("print", "void", FUNC, &print_param);
    this->symbol_document("printi", "void", FUNC, &printi_param);
}
void SymbolStack::push(bool is_while, Types retType){
    retType = retType == T_NONE? scope_stack.back()->ret_type : retType;
    SymbolTable* first_scope = new SymbolTable(pos_stack.back(), is_while, retType);
    pos_stack.push_back(pos_stack.back());
    scope_stack.push_back(first_scope);
}

parser.ypp中SymbolStack的调用代码

%{
    #include <stdio.h>
    #include <iostream>
    #include "types.h"
    #include "hw3_output.hpp"
    extern int yylineno;
    extern int yylex();
    int yyerror(const char* message);
    extern SymbolStack tables;
%}

definitions...
%%
Rule...
%%

tables = SymbolStack();
int main(){
        int res = yyparse();
        bool is_valid_program = tables.check_program();
        if(!is_valid_program){
            output::errorMainMissing();
            exit(0);
        }
        tables.pop();
        return res;
}
int yyerror(const char * message){
    output::errorSyn(yylineno);
    exit(0);
}

问题定位与修复思路

核心问题

  1. 全局对象初始化顺序冲突:全局对象tables的初始化发生在main之前,若其构造依赖的其他全局/静态资源(如SymbolTable相关逻辑、shared_def.h中的枚举关联资源)未完成初始化,会触发未定义行为导致段错误。
  2. 空指针访问风险:push方法中直接调用scope_stack.back()->ret_type,但构造初期scope_stack为空,会直接访问空指针。即使移除构造函数中的push调用,全局对象默认构造后的无效状态也可能引发错误。
  3. 全局赋值的隐含风险:全局作用域执行tables = SymbolStack();时,会先默认构造tables(全局对象的默认初始化),再执行赋值操作,无效的默认构造状态可能触发错误。

修复建议

  • 改用局部对象替代全局对象:将tables移至main函数内作为局部对象,确保初始化发生在所有依赖资源就绪之后:
    int main(){
            SymbolStack tables; // 局部构造,规避全局初始化顺序问题
            int res = yyparse();
            bool is_valid_program = tables.check_program();
            if(!is_valid_program){
                output::errorMainMissing();
                exit(0);
            }
            tables.pop();
            return res;
    }
    
    同时移除parser.ypp中的extern SymbolStack tables;和全局作用域的tables = SymbolStack();语句,调整其他模块对tables的访问逻辑(如通过参数传递)。
  • 加固push方法的安全性:在调用scope_stack.back()前先判断栈是否为空,比如在构造函数中先手动添加初始SymbolTable,再执行push操作。
  • 排查隐式全局资源:检查shared_def.h、SymbolTable等头文件中是否存在隐含的全局/静态变量,确认它们的初始化顺序是否会影响SymbolStack的构造。

内容的提问来源于stack exchange,提问作者user3917631

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.20 09:34:52