【问题标题】:How to link against debug versions of libc and libstdc++ in GCC?如何在 GCC 中链接 libc 和 libstdc++ 的调试版本?
【发布时间】:2012-01-09 22:11:49
【问题描述】:

我知道this question,但它似乎对我不起作用。

对于设置,使用一个简单的 C++ 程序,hw.cpp,由:int main() { } 给出

在 Linux 上使用 g++ -o hw hw.cpp -O0 -g 编译时,运行 ldd ./hw 会给出:

    linux-gate.so.1 =>  (0x003e5000)
    libstdc++.so.6 => /usr/local/lib/libstdc++.so.6 (0x007c5000)
    libm.so.6 => /lib/tls/i686/cmov/libm.so.6 (0x006a4000)
    libgcc_s.so.1 => /usr/local/lib/libgcc_s.so.1 (0x00a40000)
    libc.so.6 => /lib/tls/i686/cmov/libc.so.6 (0x00a93000)
    /lib/ld-linux.so.2 (0x00a0f000)

现在我在/usr/lib/debug/lib/tls/i686/cmov/ 中似乎也有调试库,我想这是系统库的相应调试版本。

问题:如何编译我的程序,以便它与标准 C 和/或 C++ 库的调试版本链接,libc/libm/libstdc++,共享还是静态的?对于共享构建,我希望ldd ./hw 的输出指向调试目录。

(背景:我的项目使用的共享库之一被 Valgrind 报告为泄漏(“仍然可以访问”),但起源不在共享库本身,而是在 dlopen 类型代码中( see here)。所以我想如果我可以在 CRT 中逐步执行 _Start() 调用,我可能能够追踪到罪魁祸首。)

更新/更正:我认为我非常非常愚蠢 - 调试库可能一直都是按需要链接的。我对调试器在单步执行时没有显示任何内容感到困惑,这是因为我没有库的源代码

更新 II: 好的,保护上一次更新。我现在有库源,但标准库确实带有调试 symbols,但我似乎没有单独的调试 build。这样的构建是否可用,我将如何链接它?

【问题讨论】:

  • 您可能知道一些标准库实现使用池进行快速分配? valgrind.org/docs/manual/faq.html#faq.undeferrors
  • @honk:我很高兴接受这不是真正的担忧。让我感到困扰的是第三方代码可能会在 my 代码中引起警告(请注意,我实际上没有引用一些虚假的 .c 文件,not 到共享库),我似乎无法抑制......至少通过调试 CRT,我希望能够更好地了解。

标签: c++ c debugging gcc


【解决方案1】:

在许多 Linux 安装中,调试库不包含实际代码;它们只包含调试信息。两者是分开的,如果你不需要它们并且磁盘空间不足,你可以选择不安装它们,但调试库本身并不好。

GDB 通常预配置为在您需要时查找调试库。

当然,您的系统可能不同。你不说它是什么。

【讨论】:

  • 你是对的——我确实一直链接到调试库。我被最愚蠢的事情甩了,即我没有标准库 source 代码 - 所以调试器正在逐步执行,但无法显示任何内容!
  • 实际上这毕竟没有帮助 - 我不仅想要调试符号,还想要库的实际调试 build。这在 Debian/Ubuntu 上可用吗?
  • 通常不会。如果您想单步执行库代码,那么您绝对正确,正常的优化库是一个问题。当然,如果它只是你想要的一个特定的库,那么你总是可以自己重新构建它。 sudo apt-get build-dep package-name 将安装您构建所需的任何内容,并且可以使用 apt-get source package-name 下载源包本身。
  • 我可以得到源代码,如eglibc-source,但是我将如何链接它以便我不会意外使用标准库? -nostdlib 的东西?
  • 假设您使用的是动态库,您可能根本不需要重新链接。只需执行export LD_PRELOAD=/path/to/debug/libc.so.6,然后从该 shell 运行的任何程序都将使用调试库。
【解决方案2】:

您的程序已链接到调试库。

只有 'ldd ./hw' 在标准位置找到 libstdc++。 为此,您需要更改 LD_LIBRARY_PATH 以加载调试共享库,并更改 ldd 以正确找到它们。

【讨论】:

  • 这对我也不起作用。我尝试了几种设置该变量的变体,但ldd 没有改变。我知道设置LD_LIBRARY_PATH 确实可以这样工作,因为它与其他(非系统)库配合得很好......或者你是说ldd从不报告调试库?
  • @KerrekSB:你试过了吗(假设是 bash):LD_LIBRARY_PATH=/usr/lib/debug/lib/tls/i686/cmov/ ldd ./hw
猜你喜欢
  • 1970-01-01
  • 2012-04-17
  • 2011-01-06
  • 2015-10-08
  • 2016-12-19
  • 2013-03-14
  • 1970-01-01
  • 2014-02-19
  • 2018-08-20
相关资源
最近更新 更多