Pārlūkot izejas kodu

Help: Add documentation for debugging with GDB

Taylor Sasser 2 mēneši atpakaļ
vecāks
revīzija
9d93853405
3 mainītis faili ar 204 papildinājumiem un 0 dzēšanām
  1. 2 0
      Help/dev/README.rst
  2. 197 0
      Help/dev/debug.rst
  3. 5 0
      Utilities/gdb/gdbinit-template

+ 2 - 0
Help/dev/README.rst

@@ -40,11 +40,13 @@ CMake developer documentation is provided by the following documents:
 * The `CMake Documentation Guide`_.
 * The `CMake Testing Guide`_.
 * The `CMake Experimental Features Guide`_.
+* The `CMake Debugging Guide`_.
 
 .. _`CMake Source Code Guide`: source.rst
 .. _`CMake Documentation Guide`: documentation.rst
 .. _`CMake Testing Guide`: testing.rst
 .. _`CMake Experimental Features Guide`: experimental.rst
+.. _`CMake Debugging Guide`: debug.rst
 
 Maintainer Documentation
 ========================

+ 197 - 0
Help/dev/debug.rst

@@ -0,0 +1,197 @@
+CMake Debugging Guide
+*********************
+
+This guide explains how to attach a debugger to CMake's unit testing framework.
+We'll focus on using **GDB** on Linux for both command-line and IDE debugging.
+See documentation on `CMake Development`_ for more information.
+
+.. _`CMake Development`: README.rst
+
+Linux: Using GDB
+================
+
+On Linux, the GNU Debugger (**GDB**) is the standard tool for debugging the
+CMake test suite. The core process involves launching the ``cmake`` executable
+from within GDB with a specific set of arguments that configure and run the
+desired test.
+
+GDB Configuration
+-----------------
+
+For effective debugging, GDB must be configured to handle child processes
+correctly, which CMake tests often create. A good practice is to use a local
+``.gdbinit`` file in your build directory. This keeps CMake-specific settings
+separate from your global configuration.
+
+**1. Enable Local .gdbinit Files (One-Time Setup)**
+
+To allow GDB to automatically load configuration from your build directory,
+add the following line to your global GDB initialization file at
+``$HOME/.gdbinit``. This is a one-time setup that makes future projects easier
+to manage.
+
+.. code-block:: text
+
+  set auto-load local-gdbinit on
+
+**2. Create a Project-Specific .gdbinit**
+
+Next, create a ``.gdbinit`` file inside your CMake **build directory**.
+This file will contain settings specific to debugging CMake.
+To make this easier, you can symlink the template file provided in the CMake
+source tree:
+
+.. code-block:: bash
+
+  # Navigate to your build directory
+  cd /path/to/your/cmake/build
+
+  # Create a symlink to the template
+  ln -s $cmake_srcdir/Utilities/gdb/gdbinit-template .gdbinit
+
+The template contains the essential settings for debugging CMake tests:
+
+.. code-block:: gdb
+
+  # Allows GDB to follow child processes
+  set follow-fork-mode child
+
+  # Allows the parent process continue in parallel
+  set non-stop on
+
+Debugging from the Command Line
+-------------------------------
+
+To start debugging, first cd to the build directory. Then, launch the
+``cmake`` executable using ``gdb --args``, which passes the necessary test
+configuration arguments directly to CMake.
+
+.. note::
+
+  To get the launch command, run ``ctest -R "RunCMake.$TESTNAME" -VV -N``
+
+
+The following example runs the ``InstallPackageInfo`` test.
+
+.. code-block:: bash
+
+  # Define paths to your CMake source and build directories
+  CMAKE_SOURCE_DIR="$HOME/cmake"
+  CMAKE_BUILD_DIR="$CMAKE_SOURCE_DIR/build"
+
+  # Define the specific test to run
+  TEST_NAME="InstallPackageInfo"
+
+  # Navigate to the build directory
+  cd "$CMAKE_BUILD_DIR"
+
+  # Launch GDB with the appropriate arguments for the test
+  gdb --args ./bin/cmake \
+    "-DCMAKE_MODULE_PATH=$CMAKE_SOURCE_DIR/Tests/RunCMake" \
+    "-DRunCMake_GENERATOR=Ninja" \
+    "-DRunCMake_SOURCE_DIR=$CMAKE_SOURCE_DIR/Tests/RunCMake/$TEST_NAME" \
+    "-DRunCMake_BINARY_DIR=$CMAKE_BUILD_DIR/Tests/RunCMake/$TEST_NAME" \
+    "-P" "$CMAKE_SOURCE_DIR/Tests/RunCMake/RunCMakeTest.cmake"
+
+Once GDB loads, you may set breakpoints (e.g., ``b cmInstallCommand``) and
+then start the test by typing ``run``.
+
+Filtering Tests
+---------------
+
+Some test suites contain multiple sub-tests. To run only a specific one,
+you can use the ``RunCMake_TEST_FILTER`` environment variable.
+
+For example, to run only the "Metadata" test within the ``InstallPackageInfo``
+suite, you can set the variable before launching GDB:
+
+.. code-block:: bash
+
+  RunCMake_TEST_FILTER="Metadata" gdb --args ...
+
+Alternatively, you can set the environment variable from within the
+GDB session before running the test:
+
+.. code-block:: gdb-prompt
+
+  (gdb) set environment RunCMake_TEST_FILTER Metadata
+  (gdb) run
+
+
+IDE Integration
+---------------
+
+You can also debug CMake tests directly from your IDE.
+
+CLion
+=====
+
+If you have configured GDB to auto-load local ``.gdbinit`` files as described
+above, CLion will automatically pick up the necessary settings.
+
+A simple way to debug a test is to modify its ``CTest`` run configuration:
+
+#. **Select the Test**: In the "Run/Debug Configurations" dialog, find the
+   ``CTest`` entry for your test (e.g., ``RunCMake.InstallPackageInfo``).
+#. **Add CTest Arguments**: In the "CTest arguments" field, add
+   ``--extra-verbose``. This is helpful for debugging because it prints the
+   exact command ``CTest`` uses to run the test.
+#. **Set Working Directory**: Ensure the "Working Directory" field is set to
+   ``$CMakeCurrentLocalGenerationDir$``.
+
+You can now set breakpoints in your code and debug this configuration.
+
+Visual Studio Code
+==================
+
+Create a ``launch.json`` file in the ``.vscode`` directory of your
+CMake **source folder** with the following configuration. This configuration
+hardcodes the necessary GDB settings, so it does not depend on an external
+``.gdbinit`` file.
+
+.. code-block:: json
+
+  {
+   "version": "0.2.0",
+   "configurations": [
+     {
+       "name": "Debug CMake Test",
+       "type": "cppdbg",
+       "request": "launch",
+       "program": "${workspaceFolder}/build/bin/cmake",
+       "args": [
+         "-DCMAKE_MODULE_PATH=${workspaceFolder}/Tests/RunCMake",
+         "-DRunCMake_GENERATOR=Ninja",
+         "-DRunCMake_SOURCE_DIR=${workspaceFolder}/Tests/RunCMake/InstallPackageInfo",
+         "-DRunCMake_BINARY_DIR=${workspaceFolder}/build/Tests/RunCMake/InstallPackageInfo",
+         "-P",
+         "${workspaceFolder}/Tests/RunCMake/RunCMakeTest.cmake"
+       ],
+       "stopAtEntry": false,
+       "cwd": "${workspaceFolder}/build",
+       "environment": [],
+       "MIMode": "gdb",
+       "setupCommands": [
+         {
+           "description": "Enable pretty-printing for gdb",
+           "text": "-enable-pretty-printing",
+           "ignoreFailures": true
+         },
+         {
+           "description": "Follow child processes",
+           "text": "set follow-fork-mode child",
+           "ignoreFailures": true
+         },
+         {
+           "description": "Don't stop the parent process",
+           "text": "set non-stop on",
+           "ignoreFailures": true
+         }
+       ]
+     }
+   ]
+  }
+
+.. note::
+
+  Remember to change the test name (``InstallPackageInfo``) in the ``"args"`` section to the specific test you want to debug.

+ 5 - 0
Utilities/gdb/gdbinit-template

@@ -0,0 +1,5 @@
+# Allows GDB to follow child processes
+set follow-fork-mode child
+
+# Allows the parent process continue in parallel
+set non-stop on