【问题标题】:Can Address Sanitizer abort immediately after an error is detected?Address Sanitizer 可以在检测到错误后立即中止吗?
【发布时间】:2021-09-17 05:19:08
【问题描述】:

我将系统调用检查器与-fsanitize=address 结合使用,当ASAN 发现错误时,它会在打印报告时调用一些系统调用(ioctl(ISATTY) 等)。系统调用检查器中断 ASAN 的 ioctl,错误报告没有被正确收集。

我希望 ASAN 在不打印报告或失败的情况下简单地中止,这是一种确定(可能使用 libasan4 API 调用)ASAN 发现错误的方法,因此我可以阻止系统调用检查器拦截系统调用.

不幸的是,来自 libasan4 的 __asan_error_report__sanitizer_set_death_callback__asan_set_error_report_callback 都在 ASAN 收集报告后加入:

0 __asan_error_report()
1 syscall_checker()
2 ioctl(ISATTY)
3 asan::PrintReport()
4 app_code_that_crashes()

并且系统调用检查器无法正确处理 ASAN 的 ioctl() 调用,因此它正常退出(),而我希望保持 ASAN 的 abort()ing 行为。

【问题讨论】:

    标签: gcc llvm sanitizer address-sanitizer


    【解决方案1】:

    您应该能够在报告打印之前通过覆盖__asan_on_error 进行拦截(在asan_interface.h 中声明,默认为空):

    // User may provide function that would be called right when ASan detects
    // an error. This can be used to notice cases when ASan detects an error, but
    // the program crashes before ASan report is printed.
    void __asan_on_error();
    

    请注意,由于奇怪的 Asan 回调接口,您最好在主二进制文件中实现此回调(共享库中的定义可能无法拦截来自 libasan.a 的默认定义)。

    【讨论】:

    • 正确,谢谢。我之前的错误是试图在系统调用检查器(一个 .so 库)中定义 __asan_on_error。如果我在主应用程序二进制文件中覆盖它,它就可以工作。
    • 是的,因为由于插入语义.so 无法覆盖链接到主二进制文件的libasan.a 中的定义。 TBH 由于这个原因,我发现一些回调的接口非常笨拙(__asan_default_options 有同样的问题)。我已经更新了答案。
    猜你喜欢
    • 1970-01-01
    • 2021-09-22
    • 1970-01-01
    • 1970-01-01
    • 2017-10-09
    • 2022-01-23
    • 1970-01-01
    • 2013-02-16
    相关资源
    最近更新 更多