【发布时间】:2019-09-10 05:52:05
【问题描述】:
我正在按照此处的说明在 Android NDK 中使用地址清理程序:https://developer.android.com/ndk/guides/asan
即使处理了异常,当抛出异常时我也会收到 SIGABRT。例如,以下代码在使用 ASAN 运行时引发异常时会导致 SIGABRT,但在没有 ASAN 的情况下运行时不会中止。根据我在网上阅读的内容,ASAN 可以处理带有异常的代码。我做错了什么?
#include <jni.h>
#include <exception>
void testThrowException()
{
try {
throw std::exception(); // Stops here with SIGABRT
}
catch (std::exception& )
{
}
}
extern "C"
{
JNIEXPORT void JNICALL
Java_com_example_hellojnicallback_MainActivity_doNativeStuff(JNIEnv *env, jobject thiz) {
testThrowException();
}
}
这是我的 CMakeLists.txt:
cmake_minimum_required(VERSION 3.4.1)
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fsanitize=address -fno-omit-frame-pointer -DANDROID_ARM_MODE=arm -DANDROID_STL=c++_shared")
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fsanitize=address -fno-omit-frame-pointer -DANDROID_ARM_MODE=arm -DANDROID_STL=c++_shared")
set(CMAKE_SHARED_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS} -fsanitize=address")
set(CMAKE_STATIC_LINKER_FLAGS "${CMAKE_STATIC_LINKER_FLAGS} -fsanitize=address")
add_library(hello-jnicallback SHARED
hello-jnicallback.cpp)
# Include libraries needed for hello-jnicallback lib
target_link_libraries(hello-jnicallback
android
log)
这是我的 wrap.sh:
#!/system/bin/sh
HERE="$(cd "$(dirname "$0")" && pwd)"
export ASAN_OPTIONS=log_to_syslog=false,allow_user_segv_handler=1,detect_leaks=0
export LD_PRELOAD=$HERE/libclang_rt.asan-i686-android.so
cmd=$1
shift
os_version=$(getprop ro.build.version.sdk)
if [ "$os_version" -eq "27" ]; then
cmd="$cmd -Xrunjdwp:transport=dt_android_adb,suspend=n,server=y -Xcompiler-option --debuggable $@"
elif [ "$os_version" -ge "28" ]; then
cmd="$cmd -XjdwpProvider:adbconnection -XjdwpOptions:suspend=n,server=y -Xcompiler-option --debuggable $@"
else
cmd="$cmd -XjdwpProvider:adbconnection $@"
fi
exec $cmd
我正在使用运行在 Windows 上的 Android Studio 的 NDK 版本 20.0.5594570。
我已经在运行 Android 10 的 Android 模拟器 (x86) 和运行 Android 9 的 Pixel (arm 64) 上进行了测试,结果相同。
编辑:根据 Dan Alberts 的回复,这里是更新的 CMakeLists.txt 和 wrap.sh。通过这些更改以及将 -DANDROID_ARM_MODE=arm", "-DANDROID_STL=c++_shared" 移动到 build.gradle,它可以正常工作。
add_library(hello-jnicallback SHARED
hello-jnicallback.cpp)
target_compile_options(hello-jnicallback PUBLIC -fsanitize=address -fno-omit-frame-pointer)
set_target_properties(hello-jnicallback PROPERTIES LINK_FLAGS -fsanitize=address)
# Include libraries needed for hello-jnicallback lib
target_link_libraries(hello-jnicallback
android
log)
#!/system/bin/sh
HERE="$(cd "$(dirname "$0")" && pwd)"
export ASAN_OPTIONS=log_to_syslog=false,allow_user_segv_handler=1
ASAN_LIB=$(ls $HERE/libclang_rt.asan-*-android.so)
if [ -f "$HERE/libc++_shared.so" ]; then
# Workaround for https://github.com/android-ndk/ndk/issues/988.
export LD_PRELOAD="$ASAN_LIB $HERE/libc++_shared.so"
else
export LD_PRELOAD="$ASAN_LIB"
fi
cmd=$1
shift
os_version=$(getprop ro.build.version.sdk)
if [ "$os_version" -eq "27" ]; then
cmd="$cmd -Xrunjdwp:transport=dt_android_adb,suspend=n,server=y -Xcompiler-option --debuggable $@"
elif [ "$os_version" -ge "28" ]; then
cmd="$cmd -XjdwpProvider:adbconnection -XjdwpOptions:suspend=n,server=y -Xcompiler-option --debuggable $@"
else
cmd="$cmd -XjdwpProvider:adbconnection $@"
fi
exec $cmd
【问题讨论】:
标签: android android-ndk address-sanitizer