我想添加ASAN(谷歌的/ Clang的地址消毒)到我们的项目,并坚持在这个问题。铿锵和铿锵与ASAN ++产生不同的输出
例如,我们有这个简单的C++代码
#include <iostream>
int main() {
std::cout << "Started Program\n";
int* i = new int();
*i = 42;
std::cout << "Expected i: " << *i << std::endl;
}
然后,我铿锵++
clang++-3.8 -o memory-leak++ memory_leak.cpp -fsanitize=address -fno-omit-frame-pointer -g
该计划使这个输出
Started Program
Expected i: 42
=================================================================
==14891==ERROR: LeakSanitizer: detected memory leaks
Direct leak of 4 byte(s) in 1 object(s) allocated from:
#0 0x4f2040 in operator new(unsigned long) (memory-leak+++0x4f2040)
#1 0x4f4f00 in main memory_leak.cpp:4:11
#2 0x7fae13ce6f44 in __libc_start_main /build/eglibc-SvCtMH/eglibc-2.19/csu/libc-start.c:287
SUMMARY: AddressSanitizer: 4 byte(s) leaked in 1 allocation(s).
酷构建它,它的工作原理象征符也给出了有意义的信息。
现在,我建立这个铿锵
clang-3.8 -o memory-leak memory_leak.cpp -std=c++11 -fsanitize=address -fno-omit-frame-pointer -g -lstdc++
而且程序提供了这种输出
Started Program
Expected i: 42
=================================================================
==14922==ERROR: LeakSanitizer: detected memory leaks
Direct leak of 4 byte(s) in 1 object(s) allocated from:
#0 0x4c3bc8 in malloc (memory-leak+0x4c3bc8)
#1 0x7f024a8e4dac in operator new(unsigned long) (/usr/lib/x86_64-linux-gnu/libstdc++.so.6+0x5edac)
#2 0x7f0249998f44 in __libc_start_main /build/eglibc-SvCtMH/eglibc-2.19/csu/libc-start.c:287
SUMMARY: AddressSanitizer: 4 byte(s) leaked in 1 allocation(s).
好吧,它检测内存泄漏,但堆栈跟踪看起来很奇怪,它并没有真正包括memory_leak.cpp:4:11行。
我花了很长时间试图缩小我们的代码库中的这个问题,最终唯一的区别是clang vs clang ++。
为什么事件是一个问题,我们不能使用clang ++吗? 我们使用bazel,它使用CC编译器代替CXX来达到一些糟糕的理由。我们不能盲目强制使用CXX,因为我们拥有无法由CXX构建的CC依赖关系。所以...
任何想法如何获得相同的ASAN输出时使用铿锵和铿锵++?或者,如何让Bazel为C++目标使用clang ++和Cng目标?
这可能没有帮助,但是在使用clang 5.0.0时,我看到的输出与clang ++相同。 – Rakete1111
我可以用clang3.8重现你的问题。在我的系统上,关键的区别在于不同的链接器命令 - 如果使用clang调用,某些asan-stuff会丢失。对我来说看起来像一个bug。 – ead
我从来没有使用bazel,但你可能可以定义连接器命令行与正确的库 – ead