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

ANTLR4生成的C++词法分析器无法接收输入流问题求助

问题描述

在Ubuntu系统中,通过ANTLR4的-Dlanguage=Cpp参数生成ExprLexer和ExprParser,未修改生成文件,使用官方示例代码:

#include <iostream>

#include "antlr4-runtime.h"
#include "ExprLexer.h"
#include "ExprParser.h"

using namespace antlr4;

int main(int , const char **) {
  // make input stream with string, put input stream into ANTLRInputStream
  ANTLRInputStream input("h");
  ExprLexer lexer(&input);
  return 0;
}

编译命令:

g++ -std=c++17 *.cpp -o index -I/usr/local/include/antlr4-runtime -L. -lantlr4-runtime

编译正常,但运行时抛出错误:

terminate called after throwing an instance of 'std::system_error'
  what():  Unknown error -1
Aborted (core dumped)

尝试用try-catch捕获仅得知是系统调用错误,无法定位具体原因。

解决方法

1. 匹配ANTLR4 Runtime与生成代码的版本

ANTLR4生成代码和runtime库版本必须严格一致,版本不兼容会触发底层调用错误:

  • 查看runtime版本:查看/usr/local/include/antlr4-runtime/antlr4-runtime.h中的版本宏定义,或执行pkg-config --modversion antlr4-runtime
  • 查看生成代码用的antlr4.jar版本:java -jar antlr4.jar -version
  • 版本不一致时,重新安装对应版本的runtime,或用相同版本的antlr4.jar重新生成词法/解析器代码。

2. 确保动态链接库可被加载

编译时指定的-L.仅在编译阶段生效,运行时需确保antlr4-runtime的so文件能被找到:

  • 临时指定库路径运行:LD_LIBRARY_PATH=/usr/local/lib ./index(默认antlr4-runtime安装在/usr/local/lib)
  • 编译时嵌入库路径:
    g++ -std=c++17 *.cpp -o index -I/usr/local/include/antlr4-runtime -L/usr/local/lib -Wl,-rpath=/usr/local/lib -lantlr4-runtime
    
  • 永久添加库路径:将/usr/local/lib写入/etc/ld.so.conf,执行sudo ldconfig更新配置。

3. 修复Locale设置问题

ANTLR4 C++ runtime初始化依赖正确的locale,缺失会导致系统调用错误:

  • 运行前设置locale:export LC_ALL=C.UTF-8 && ./index
  • 或在代码开头添加locale初始化:
    #include <locale>
    
    int main(int , const char **) {
      std::locale::global(std::locale("C.UTF-8"));
      ANTLRInputStream input("h");
      ExprLexer lexer(&input);
      return 0;
    }
    

4. 捕获更详细的错误信息

修改代码打印完整错误细节,帮助定位问题:

#include <iostream>
#include <system_error>

#include "antlr4-runtime.h"
#include "ExprLexer.h"
#include "ExprParser.h"

using namespace antlr4;

int main(int , const char **) {
  try {
    ANTLRInputStream input("h");
    ExprLexer lexer(&input);
  } catch (const std::system_error& e) {
    std::cerr << "System error: " << e.what() << ", error code: " << e.code() << std::endl;
    std::cerr << "Error category: " << e.code().category().name() << std::endl;
  } catch (const std::exception& e) {
    std::cerr << "Exception: " << e.what() << std::endl;
  }
  return 0;
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.07 18:46:17