It's described in this document as a **mapping** format because its goal is
to store the data that is required for a code coverage tool to map between
the specific source ranges in a file and the execution counts obtained
after running the instrumented version of the program.
The mapping data is used in two places in the code coverage process:
1. When clang compiles a source file with ``-fcoverage-mapping``, it
generates the mapping information that describes the mapping between the
source ranges and the profiling instrumentation counters.
This information gets embedded into the LLVM IR and conveniently
ends up in the final executable file when the program is linked.
2. It is also used by *llvm-cov* - the mapping information is extracted from an
object file and is used to associate the execution counts (the values of the
profile instrumentation counters), and the source ranges in a file.
After that, the tool is able to generate various code coverage reports
for the program.
The coverage mapping format aims to be a "universal format" that would be
suitable for usage by any frontend, and not just by Clang. It also aims to
provide the frontend the possibility of generating the minimal coverage mapping
data in order to reduce the size of the IR and object files - for example,
instead of emitting mapping information for each statement in a function, the
frontend is allowed to group the statements with the same execution count into
regions of code, and emit the mapping information only for those regions.
Advanced Concepts
=================
The remainder of this guide is meant to give you insight into the way the
coverage mapping format works.
The coverage mapping format operates on a per-function level as the
profile instrumentation counters are associated with a specific function.
For each function that requires code coverage, the frontend has to create
coverage mapping data that can map between the source code ranges and
the profile instrumentation counters for that function.
Mapping Region
--------------
The function's coverage mapping data contains an array of mapping regions.
A mapping region stores the `source code range`_ that is covered by this region,
the `file id <coverage file id_>`_, the `coverage mapping counter`_ and
the region's kind.
There are several kinds of mapping regions:
* Code regions associate portions of source code and `coverage mapping
counters`_. They make up the majority of the mapping regions. They are used
by the code coverage tool to compute the execution counts for lines,
highlight the regions of code that were never executed, and to obtain
the various code coverage statistics for a function.
For example:
:raw-html:`<pre class='highlight' style='line-height:initial;'><span>int main(int argc, const char *argv[]) </span><span style='background-color:#4A789C'>{ </span> <span class='c1'>// Code Region from 1:40 to 9:2</span>
<span style='background-color:#4A789C'> </span>
<span style='background-color:#4A789C'> if (argc > 1) </span><span style='background-color:#85C1F5'>{ </span> <span class='c1'>// Code Region from 3:17 to 5:4</span>
* Skipped regions are used to represent source ranges that were skipped
by Clang's preprocessor. They don't associate with
`coverage mapping counters`_, as the frontend knows that they are never
executed. They are used by the code coverage tool to mark the skipped lines
inside a function as non-code lines that don't have execution counts.
For example:
:raw-html:`<pre class='highlight' style='line-height:initial;'><span>int main() </span><span style='background-color:#4A789C'>{ </span> <span class='c1'>// Code Region from 1:12 to 6:2</span>
<span style='background-color:#85C1F5'>#ifdef DEBUG </span> <span class='c1'>// Skipped Region from 2:1 to 4:2</span>
* Branch regions associate instrumentable branch conditions in the source code
with a `coverage mapping counter`_ to track how many times an individual
condition evaluated to 'true' and another `coverage mapping counter`_ to
track how many times that condition evaluated to false. Instrumentable
branch conditions may comprise larger boolean expressions using boolean
logical operators. The 'true' and 'false' cases reflect unique branch paths
that can be traced back to the source code.
For example:
:raw-html:`<pre class='highlight' style='line-height:initial;'><span>int func(int x, int y) {
<span> if (<span style='background-color:#4A789C'>(x > 1)</span> || <span style='background-color:#4A789C'>(y > 3)</span>) {</span> <span class='c1'>// Branch Region from 3:6 to 3:12</span>
<span> </span><span class='c1'>// Branch Region from 3:17 to 3:23</span>
The source range record contains the starting and ending location of a certain
mapping region. Both locations include the line and the column numbers.
.._coverage file id:
File ID:
^^^^^^^^
The file id an integer value that tells us
in which source file or macro expansion is this region located.
It enables Clang to produce mapping information for the code
defined inside macros, like this example demonstrates:
:raw-html:`<pre class='highlight' style='line-height:initial;'><span>void func(const char *str) </span><span style='background-color:#4A789C'>{ </span> <span class='c1'>// Code Region from 1:28 to 6:2 with file id 0</span>
<span style='background-color:#4A789C'> #define PUT </span><span style='background-color:#85C1F5'>printf("%s\n", str)</span><span style='background-color:#4A789C'> </span> <span class='c1'>// 2 Code Regions from 2:15 to 2:34 with file ids 1 and 2</span>
<span style='background-color:#4A789C'> </span><span style='background-color:#F6D55D'>PUT</span><span style='background-color:#4A789C'>; </span> <span class='c1'>// Expansion Region from 4:5 to 4:8 with file id 0 that expands a macro with file id 1</span>
<span style='background-color:#4A789C'> </span><span style='background-color:#F6D55D'>PUT</span><span style='background-color:#4A789C'>; </span> <span class='c1'>// Expansion Region from 5:3 to 5:6 with file id 0 that expands a macro with file id 2</span>
<span style='background-color:#4A789C'>}</span>
</pre>`
.._coverage mapping counter:
.._coverage mapping counters:
Counter:
^^^^^^^^
A coverage mapping counter can represents a reference to the profile
instrumentation counter. The execution count for a region with such counter
is determined by looking up the value of the corresponding profile
instrumentation counter.
It can also represent a binary arithmetical expression that operates on
coverage mapping counters or other expressions.
The execution count for a region with an expression counter is determined by
evaluating the expression's arguments and then adding them together or
subtracting them from one another.
In the example below, a subtraction expression is used to compute the execution
count for the compound statement that follows the *else* keyword:
:raw-html:`<pre class='highlight' style='line-height:initial;'><span>int main(int argc, const char *argv[]) </span><span style='background-color:#4A789C'>{ </span> <span class='c1'>// Region's counter is a reference to the profile counter #0</span>
<span style='background-color:#4A789C'> </span>
<span style='background-color:#4A789C'> if (argc > 1) </span><span style='background-color:#85C1F5'>{ </span> <span class='c1'>// Region's counter is a reference to the profile counter #1</span>
<span style='background-color:#85C1F5'> }</span><span style='background-color:#4A789C'> else </span><span style='background-color:#F6D55D'>{ </span> <span class='c1'>// Region's counter is an expression (reference to the profile counter #0 - reference to the profile counter #1)</span>
* The length of the string in the third field of *__llvm_coverage_mapping* that contains any encoded coverage mapping data affixed to the coverage header. Always 0, but present for backwards compatibility.