Page MenuHomeFreeBSD

libdtrace: implement inline function tracing for kinst
Needs ReviewPublic

Authored by christos on Feb 28 2023, 5:10 PM.
Referenced Files
Unknown Object (File)
Sat, Jul 13, 1:16 AM
Unknown Object (File)
Fri, Jul 12, 10:58 AM
Unknown Object (File)
Wed, Jul 10, 11:39 PM
Unknown Object (File)
Thu, Jul 4, 11:02 AM
Unknown Object (File)
Thu, Jul 4, 10:21 AM
Unknown Object (File)
Tue, Jul 2, 6:56 AM
Unknown Object (File)
Tue, Jul 2, 2:47 AM
Unknown Object (File)
Mon, Jul 1, 7:49 AM



The following code implements inline tracing for the kinst DTrace provider.

Briefly explained, what the code does is, for each probe of the form:


libdtrace checks to see if <inline_func> is indeed an inline function, where
in this case it finds all inline copies of it and creates new probes for each
one of them. Otherwise, it converts the probe to an FBT one so that we don't
duplicate FBT's functionality in kinst.


Unlike FBT, leaving the probe name empty won't trace both entry and return.
kinst goes into "inline-tracing mode" only when it sees entry/return in the
probe name, otherwise it thinks it's a regular kinst probe, in which case the
dtrace(1) invocation will fail if we try to trace an inline function with an
empty probe name.

Diff Detail

rG FreeBSD src repository
Lint Skipped
Tests Skipped

Event Timeline

There are a very large number of changes, so older changes are hidden. Show Older Changes

No real use other than to make it obvious that I'm handling both entry
and return probes.


This doesn't affect kinst::<func>:<offset> probes at all. The
flag is tested in dt_sugar_do_kinst_inline() and will exit right away
if the probe is neither entry nor return.


Didn't notice it.

christos marked 4 inline comments as done.
christos edited the summary of this revision. (Show Details)

Address Mark's comments.

diff against main, not last patch

  • use dt_free() instead of free()
  • add error checks after calls to dt_alloc() and dt_node_xalloc()

use dtp->bootfile in dt_sugar_do_kinst_inline() instead of hardcoding the path

fix dtrace_disx86() fail in dt_sugar_kinst_find_caller_func()

update dtrace_kinst.4 man page to mention inline tracing

remove call to dwarf_next_types_section()

Handle leaf functions with their push %rbp ommitted.

christos edited the summary of this revision. (Show Details)

Got rid of deep copying, appending to the main clause is simpler.

Handle multiple dn_pdescs properly, move handling away from

christos edited the summary of this revision. (Show Details)

Do not always go back one instruction.

Improve example in man page.

Get rid of push %rbp check (depends on D39166).

christos edited the summary of this revision. (Show Details)

Parse all loaded modules and their debug files instead of just kernel.
Mention new bug in summary.

christos edited the summary of this revision. (Show Details)

Fix bugs, surround amd64-specific code in an #ifdef, merge flags into
dtsp_flags, handle dt_sugar_elf_init() and dwarf_elf_init() errors, use
longjmp() for dt_alloc() failures.

Fix per-module parsing. Create an additional FBT probe if a non-inline definition is
found along an inline definition in the same module.

More bug fixes. I always keep finding them after I submit the patch.

Do not exclude inline copies that have DW_AT_subprogram instead of

Add tests. kinst_test_inline() needs modification so that it can be splitted
into DW_AT_ranges.

Implement dt_sugar_elf_verify_debuglink() to make sure the debug files we're
reading are up to date, and if they're not, skip them. Also stop leaking
elf_info structs in dt_sugar_do_kinst_inline().

Fix accidental dangling brace.

Surround amd64-specific code in an ifdef.

Use dtrace_instr_size() and get rid of machine-dependent code (depends on

Fix Makefile conflict, check if dtracetest is already loaded before attempting to load it.

Add libdwarf in Makefile.inc1 (Thanks Mark).

Bail out if kinst doesn't exist (i.e the architecture doesn't support it).

Fix return offset handling.

Fix off->val type causing a build failure.

90 ↗(On Diff #127670)

@markj do you have a good idea for this?