Skip to content

Commit

Permalink
[RemoveDIs] Add documentation for IR debug records (#81156)
Browse files Browse the repository at this point in the history
This patch adds minimal documentation for the IR representation of the
RemoveDIs model of debug info. This patch assumes
that the default for all cases is still debug intrinsic functions, and
so does not update all existing text to refer to debug records, but only
adds a section in the LangRef and SourceLevelDebugging documents to
explain the new format.
  • Loading branch information
SLTozer committed Mar 8, 2024
1 parent ba2236d commit 01e5d46
Show file tree
Hide file tree
Showing 2 changed files with 95 additions and 2 deletions.
31 changes: 29 additions & 2 deletions llvm/docs/LangRef.rst
Expand Up @@ -908,7 +908,8 @@ Syntax::

A function definition contains a list of basic blocks, forming the CFG (Control
Flow Graph) for the function. Each basic block may optionally start with a label
(giving the basic block a symbol table entry), contains a list of instructions,
(giving the basic block a symbol table entry), contains a list of instructions
and :ref:`debug records <debugrecords>`,
and ends with a :ref:`terminator <terminators>` instruction (such as a branch or
function return). If an explicit label name is not provided, a block is assigned
an implicit numbered label, using the next value from the same counter as used
Expand Down Expand Up @@ -8541,7 +8542,10 @@ The LLVM instruction set consists of several different classifications
of instructions: :ref:`terminator instructions <terminators>`, :ref:`binary
instructions <binaryops>`, :ref:`bitwise binary
instructions <bitwiseops>`, :ref:`memory instructions <memoryops>`, and
:ref:`other instructions <otherops>`.
:ref:`other instructions <otherops>`. There are also :ref:`debug records
<debugrecords>`, which are not instructions themselves but are printed
interleaved with instructions to describe changes in the state of the program's
debug information at each position in the program's execution.

.. _terminators:

Expand Down Expand Up @@ -12695,6 +12699,29 @@ Example:

%tok = cleanuppad within %cs []

.. _debugrecords:

Debug Records
-----------------------

Debug records appear interleaved with instructions, but are not instructions;
they are used only to define debug information, and have no effect on generated
code. They are distinguished from instructions by the use of a leading `#` and
an extra level of indentation. As an example:

.. code-block:: llvm

%inst1 = op1 %a, %b
#dbg_value(%inst1, !10, !DIExpression(), !11)
%inst2 = op2 %inst1, %c

These debug records are an optional replacement for
:ref:`debug intrinsics<dbg_intrinsics>`. Debug records will be output if the
``--write-experimental-debuginfo`` flag is passed to LLVM; it is an error for both
records and intrinsics to appear in the same module. More information about
debug records can be found in the `LLVM Source Level Debugging
<SourceLevelDebugging.html#format-common-intrinsics>`_ document.

.. _intrinsics:

Intrinsic Functions
Expand Down
66 changes: 66 additions & 0 deletions llvm/docs/SourceLevelDebugging.rst
Expand Up @@ -167,6 +167,17 @@ conventions used by the C and C++ front-ends.
Debug information descriptors are `specialized metadata nodes
<LangRef.html#specialized-metadata>`_, first-class subclasses of ``Metadata``.

There are two models for defining the values of source variables at different
states of the program and tracking these values through optimization and code
generation: :ref:`intrinsic function calls <format_common_intrinsics>`, the
current default, and :ref:`debug records <debug_records>`, which are a new
non-instruction-based model
(for an explanation of how this works and why it is desirable, see the
`RemoveDIs <RemoveDIsDebugInfo.html>`_ document). Each module must use one or
the other; they may never be mixed within an IR module. To enable writing debug
records instead of intrinsic calls, use the flag
``--write-experimental-debuginfo``.

.. _format_common_intrinsics:

Debugger intrinsic functions
Expand Down Expand Up @@ -268,6 +279,61 @@ The formal LLVM-IR signature is:
See :doc:`AssignmentTracking` for more info.

.. _debug_records:

Debug Records
----------------------------

LLVM also has an alternative to intrinsic functions, debug records, which
function similarly but are not instructions. The basic syntax for debug records
is:

.. code-block:: llvm
#dbg_<kind>([<arg>, ]* <DILocation>)
; Using the intrinsic model, the above is equivalent to:
call void llvm.dbg.<kind>([metadata <arg>, ]*), !dbg <DILocation>
A debug intrinsic function can be converted to a debug record with the
following steps:

1. Add an extra level of indentation.
2. Replace everything prior to the intrinsic kind (declare/value/assign) with
``#dbg_``.
3. Remove the leading ``metadata`` from the intrinsic's arguments.
4. Transfer the ``!dbg`` attachment to be an argument, dropping the leading
``!dbg``.

For each kind of intrinsic function, there is an equivalent debug record.

``#dbg_declare``
^^^^^^^^^^^^^^^^

.. code-block:: llvm
#dbg_declare([Value|MDNode], DILocalVariable, DIExpression, DILocation)
Equivalent to the ``llvm.dbg.declare`` intrinsic.

``#dbg_value``
^^^^^^^^^^^^^^

.. code-block:: llvm
#dbg_value([Value|DIArgList|MDNode], DILocalVariable, DIExpression, DILocation)
Equivalent to the ``llvm.dbg.value`` intrinsic.

``#dbg_assign``
^^^^^^^^^^^^^^^

.. code-block:: llvm
#dbg_assign([Value|DIArgList|MDNode], DILocalVariable, DIExpression,
DIAssignID, [Value|MDNode], DIExpression, DILocation)
Equivalent to the ``llvm.dbg.assign`` intrinsic.

Object lifetimes and scoping
============================

Expand Down

0 comments on commit 01e5d46

Please sign in to comment.