第 20 章 调试正在运行的应用程序


本章介绍了用于调试应用(可根据需要多次)在开发人员直接访问的机器上执行的技术。

20.1. 使用调试信息启用调试

要调试应用和库,需要调试信息。以下小节描述了如何获取此信息。

20.1.1. 调试信息

在调试任何可执行代码时,两种信息可以允许工具,并扩展程序员以理解二进制代码:

  • 源代码文本
  • 有关源代码文本与二进制代码的关系的描述

这称为调试信息。

Red Hat Enterprise Linux 对可执行二进制文件、共享库或调试信息文件使用 ELF 格式。在这些 ELF 文件中,DWARF 格式用于保存调试信息。

DWARF 符号由 readelf -w file 命令读取。

小心

UNIX 偶尔会使用 STABS。STABS 是一种较旧、更少的格式。红帽不鼓励其使用。GCC 和 GDB 只支持 STABS 生产与消费。Valgrind 和 elfutils 等其他工具根本不支持 STABS。

其它资源

20.1.2. 使用 GCC 启用 C 和 C++ 应用程序

由于调试信息较大,因此默认情况下,不会包含在可执行文件中。要为您的 C 和 C++ 应用程序进行调试,您必须明确指示编译器创建调试信息。

使用 GCC 启用调试信息

要在编译和链接代码时使用 GCC 创建调试信息,请使用 -g 选项:

$ gcc ... -g ...
  • 由编译器和链接器执行的优化可能会导致可执行代码难以与原始源代码相关:变量可以被优化,取消滚动,将操作合并到周围的代码中。这会影响调试。要改进调试体验,请考虑使用 -Og 选项设置优化。但是,更改优化级别会更改可执行代码,并可能会更改实际行为,以便删除一些程序错误。
  • f compare-debug GCC 选项测试 GCC 使用调试信息编译的代码,无需调试信息。如果生成的两个二进制文件相同,则测试将通过。此测试可确保可执行代码不受任何调试选项的影响,进一步确保调试代码中没有隐藏的错误。请注意,使用 -fcompare-debug 选项可显著增加编译时间。有关这个选项的详情,请查看 GCC 手册页。
其它资源

20.1.3. debuginfo Packages

debuginfo 软件包包含程序和库的调试信息和调试源代码。

先决条件
debuginfo Packages

对于从 Red Hat Enterprise Linux 软件仓库安装的软件包中安装的应用程序和库,您可以获得调试信息和调试源代码作为单独的通过另一个频道提供的调试信息软件包。debuginfo 软件包包含 .debug 文件,其中包含 DWARF debuginfo 和用于编译二进制软件包的源文件。debuginfo 软件包内容安装到 /usr/lib/debug 目录中。

debuginfo 软件包仅对具有相同名称、版本、发行版本和架构的二进制软件包提供调试信息有效:

  • 二进制 软件包:packagename-version-release.architecture.rpm
  • debuginfo package: packagename-debuginfo-version-release.architecture.rpm

20.1.4. 使用 GDB 获取应用程序或库的调试信息软件包

GNU Debugger(GDB)会自动识别缺少的调试信息并解决软件包名称。

先决条件
步骤
  1. 启动连接到要调试的应用程序或库的 GDB。GDB 自动识别缺少的调试信息,并建议要运行的命令。

    $ gdb -q /bin/ls
    Reading symbols from /usr/bin/ls...Reading symbols from /usr/bin/ls...(no debugging symbols found)...done.
    (no debugging symbols found)...done.
    Missing separate debuginfos, use: debuginfo-install coreutils-8.22-21.el7.x86_64
    (gdb)
  2. 退出 GDB,但不继续操作:键入 qEnter

    (gdb) q
  3. 运行 GDB 建议的命令来安装所需的 debuginfo 软件包:

    # debuginfo-install coreutils-8.22-21.el7.x86_64

    为应用程序或库安装 debuginfo 软件包会为所有依赖项安装 debuginfo 软件包。

  4. 如果 GDB 无法推荐 debuginfo 软件包,请按照 第 20.1.5 节 “手动 获取 应用程序或库的调试信息软件包” 中的步骤操作。
其它资源

20.1.5. 手动 获取 应用程序或库的调试信息软件包

要手动选择(安装) debuginfo 软件包(用于安装),请找到可执行文件 并查找该软件包来安装该软件包。

注意

使用 GDB 确定安装的软件包更好。只有在 GDB 无法建议安装软件包时,才使用此手动步骤。

先决条件
步骤
  1. 查找应用程序或库的可执行文件。

    1. 使用 哪个命令 查找应用文件。

      $ which nautilus
      /usr/bin/nautilus
    2. 使用 locate 命令查找库文件。

      $ locate libz | grep so
      /usr/lib64/libz.so
      /usr/lib64/libz.so.1
      /usr/lib64/libz.so.1.2.7

      如果调试包含的错误消息的原始原因,请在其文件名中选择库具有相同额外数字的结果。若有疑问,请尝试遵循库文件名不包含其他数字的结果。

      注意

      locate 命令由 mlocate 软件包提供。安装它并启用其使用:

      # yum install mlocate
      # updatedb
  2. 使用文件路径,搜索提供该文件的软件包。

    # yum provides /usr/lib64/libz.so.1.2.7
    Loaded plugins: product-id, search-disabled-repos, subscription-manager
    zlib-1.2.7-17.el7.x86_64 : The compression and decompression library
    Repo        : @anaconda/7.4
    Matched from:
    Filename    : /usr/lib64/libz.so.1.2.7

    输出以格式 名称提供软件包列表 -版本分发架构。在这一步中,只有 软件包名称 很重要,因为 yum 输出中显示的版本可能不是实际安装的版本。

    重要

    如果此步骤没有生成任何结果,则无法决定哪个软件包提供二进制文件,这个过程会失败。

  3. 使用 rpm 低级别软件包管理工具查找系统上安装哪个软件包版本。使用软件包名称作为参数:

    $ rpm -q zlib
    zlib-1.2.7-17.el7.x86_64

    输出提供以格式 名称版本 )的已安装软件包的详细信息。分发.架构

  4. 使用 debuginfo -install 实用程序安装 debuginfo 软件包。在命令中,使用软件包名称以及您在上一步中确定的其他详情:

    # debuginfo-install zlib-1.2.7-17.el7.x86_64

    为应用程序或库安装 debuginfo 软件包会为所有依赖项安装 debuginfo 软件包。

其它资源
Red Hat logoGithubRedditYoutubeTwitter

学习

尝试、购买和销售

社区

关于红帽文档

通过我们的产品和服务,以及可以信赖的内容,帮助红帽用户创新并实现他们的目标。

让开源更具包容性

红帽致力于替换我们的代码、文档和 Web 属性中存在问题的语言。欲了解更多详情,请参阅红帽博客.

關於紅帽

我们提供强化的解决方案,使企业能够更轻松地跨平台和环境(从核心数据中心到网络边缘)工作。

© 2024 Red Hat, Inc.