java - AddressSanitizer:运行包含调用 JNI_CreateJavaVM 的 C++ 代码时的 SEGV
问题描述
我们的产品是用 C++ 编写的,根据程序流程,调用 Java 本地接口 (JNI) 以加载和运行 Java 类,主要是为了进行 JBDC 调用以访问数据库表。当这个进程在 Linux 上运行时,具有特定的客户配置,大约 20% 的时间它会因分段错误而失败,从而生成核心转储。核心转储中的回溯表明程序在 JVM (libjvm.so) 中的某个地方出现故障。我尝试使用 -Xcheck:jni 运行,但它提供的信息似乎无法帮助隔离此问题。我已经尝试了 Java 7 和 8 的几个版本/构建。
为了尝试获取有关该崩溃的更多信息,我使用附加选项 -fsanitize=address -fstack-protector -fno-omit-frame-pointer 使用 gcc 4.8.5 重新编译了代码。当我编译并使用 -fsanitize=address 选项,然后运行程序时,它很快崩溃并出现以下错误:
ASAN:SIGSEGV
=================================================================
==15864== ERROR: AddressSanitizer: SEGV on unknown address 0x00000000 (pc 0xe2a00202 sp 0xfff4a8cc bp 0xf35e2b40 T0)
AddressSanitizer can not provide additional info.
#0 0xe2a00201 (+0x201)
==15864== ABORTING
当从 C++ 代码调用 JNI_CreateJavaVM() 函数以设置调用 Java 时,似乎正在发生这种崩溃。我从图片中取出我们的代码,并尝试重新编译并运行此处提供的示例调用 API 代码。当我编译此代码并使用 -fsanitize=address 选项然后运行它时,它会因与上述相同的错误而崩溃。我使用的编译命令和选项粘贴在下面:
/usr/bin/g++ -m32 -fsanitize=address -I/scratch/jwcarter/jdk1.8.0_291_x86/include -I/scratch/jwcarter/jdk1.8.0_291_x86/include/linux -L/scratch/jwcarter/jdk1.8.0_291_x86/jre/lib/i386/client /scratch/jwcarter/rel125as/rps100/jnitest/c/jnitest.cpp -o jnitest -ljvm
为了使用 -fsanitize=address 编译选项来构建包含对 JNI_CreateJavaVM() 的调用的代码,是否需要指定其他编译或链接标志?谢谢。
解决方案
推荐阅读
- haskell - Haskell 类型推理编译速度
- java - 如果列表的总大小小于限制,stream().limit() 会优化执行吗?
- c++ - 为什么或何时我们将使用 linux 命令调用系统函数而不是编写 C/C++ 代码?
- xcode - react-native-fbsdk LoginManger 未定义
- javascript - Cordova/Phonegap 构建 Google play 目标 api26 不适用于旧的 android 手机
- react-native - React Native Modal +半透明不适用于android
- c# - 如何将 MySQL 中的所有数据导出到 Crystal Report
- python-3.x - 将数据插入到页面中的特定列Python,pandas
- javascript - 使用adaptiveHeight时无法正确显示第一张图片
- ruby-on-rails - 如何从rails中的索引更新记录