Commit Graph

1482328 Commits

Author SHA1 Message Date
Ian Rogers
eeb70645a8 perf python: Port event_analyzing_sample to perf module
Port event_analyzing_sample.py to a standalone script in
tools/perf/python/ using the perf module and standard library sqlite3
module.

Improvements compared to the legacy script:
- Encapsulate database state in a _DB container instead of mutating
  module-level globals, and ensure temporary SQLite database files are
  cleaned up on exit.
- Add argparse CLI options (-i/--input and -d/--db) while preserving
  PerfEvent, PebsEvent, and PebsNHM binary raw_buf unpacking and
  symbol/DSO histogram reporting.
- Remove Python 2 compatibility code and add type annotations.

Add a shell test (test_event_analyzing_sample_python.sh) to verify the
standalone script.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:29 +02:00
Ian Rogers
e1e4bd6f8b perf python: Port gecko to perf module
Port gecko.py to a standalone script in tools/perf/python/ that uses
the perf module directly to convert perf.data profiles into Firefox
Gecko profile format.

Improvements compared to the legacy script:
- Encapsulate profiler state in GeckoCLI and CategoryData classes with
  full type annotations, removing global variables.
- Harden the local HTTP server in _write_and_launch(): write the
  temporary profile to an isolated tempfile.TemporaryDirectory() with a
  randomized UUID filename instead of the current working directory,
  bind HTTPServer exclusively to 127.0.0.1 on an OS-assigned ephemeral
  port (0), restrict CORS Access-Control-Allow-Origin to
  'https://profiler.firefox.com' instead of '*', and restrict HTTP GET
  requests exclusively to the randomized profile filename (returning
  HTTP 403 for directory listings and any other path).
- Add -i/--input and -e/--event CLI options via argparse.

Add a shell test (test_gecko_python.sh) to verify the standalone script.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:28 +02:00
Ian Rogers
eb08738a7f perf python: Port flamegraph to perf module
Port flamegraph.py to a standalone script in tools/perf/python/ that
uses the perf module directly, avoiding intermediate dictionary
allocations for event fields.

Improvements compared to the legacy script:
- Add Subresource Integrity (integrity="sha256-...") and
  crossorigin="anonymous" attributes to external CDN stylesheet and
  script tags in MINIMAL_HTML.
- Upgrade CDN HTML template hash verification from weak MD5
  (hashlib.md5) to cryptographic SHA-256 (hashlib.sha256).
- Escape '<', '>', and '&' ('\u003c', '\u003e', '\u0026') in embedded
  JSON payloads (stacks_json and options_json) to prevent HTML script
  injection / XSS when rendering untrusted symbol or command names.
- Skip invoking 'perf report --header-only' when the input is stdin
  ('-'), a FIFO pipe, or a character device (S_ISFIFO / S_ISCHR) so
  non-seekable streams do not hang or fail.

Add a shell test (test_flamegraph_python.sh) to verify the standalone
script.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:28 +02:00
Ian Rogers
c3034e70c6 perf python: Port stackcollapse to perf module
Port stackcollapse.py from tools/perf/scripts/python/ to a standalone
script in tools/perf/python/ refactored into a StackCollapseAnalyzer
class.

Improvements compared to the legacy script:
- Traverse sample.callchain directly from perf.session without
  allocating per-event dictionaries, and fall back to sample.symbol when
  a sample has no callchain.
- Replace deprecated optparse with argparse, adding -i/--input alongside
  --include-tid, --include-pid, --no-comm, --tidy-java, and --kernel.
- Handle BrokenPipeError cleanly when output is piped into downstream
  tools (such as head or flamegraph.pl).

Add a shell test (test_stackcollapse_python.sh) using a CPU workload
(perf test -w noploop) to verify the standalone script.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:28 +02:00
Ian Rogers
6ceccefad0 perf python: Port mem-phys-addr to perf module
Port mem-phys-addr.py to a standalone script in tools/perf/python/
using the perf.session API to read perf.data files and profile physical
memory access types against /proc/iomem.

Improvements compared to the legacy script:
- Parse the full indentation hierarchy of /proc/iomem into a parent-child
  tree of frozen IomemEntry dataclasses (instead of only top-level
  indent-0 ranges), resolving physical addresses to the most specific
  sub-range (such as Kernel code/data/bss inside System RAM) and rolling
  child counts up into parent totals.
- Support profiling multiple memory events in a single perf.data session
  (keyed by evsel name) instead of assuming a single global event.
- Add argparse CLI options (-i/--input and --iomem to allow supplying an
  offline /proc/iomem snapshot from a target system).

Add a shell test (test_mem_phys_addr_python.sh) to verify the standalone
script.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:28 +02:00
Ian Rogers
4425182d42 perf python: Port stat-cpi to perf module
Port stat-cpi.py from the legacy embedded scripting framework to a
standalone Python script in tools/perf/python/ to calculate Cycles Per
Instruction (CPI) per interval per CPU or thread.

Improvements compared to the legacy script:
- Support both perf.data file mode (via perf.session stat callbacks)
  and live counter collection mode (using perf.parse_events,
  evlist.open, and evsel.read across intervals), with automatic fallback
  to user-space (:u) and self-process monitoring when perf_event_paranoid
  restricts system-wide events (EACCES).
- Compute per-interval counter deltas (val, ena, run) keyed by raw event
  name so cumulative PERF_RECORD_STAT snapshots and hybrid PMU events
  (e.g. cpu_core/cycles/, cpu_atom/cycles/) are accumulated accurately,
  and scale counts by time_enabled / time_running when multiplexed.
- Replace hard-coded CPU ([0, 1]) and thread ([0]) arrays with dynamic
  CPU and thread discovery so arbitrary system topologies work
  automatically.
- Add CLI option handling (-i, -I, -p) via argparse and type annotations
  passing mypy and pylint.

Add a shell test (test_stat_cpi_python.sh) to verify the standalone
script.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:28 +02:00
Ian Rogers
af2f226e8c perf Makefile: Install standalone Python scripts during transition
Install the newly ported standalone Python scripts (python/*.py), type
stubs (python/perf.pyi), and compiled perf Python extension module
(python/perf*.so, when built) into $(perfexec_instdir_SQ)/python
alongside the legacy scripts during the transition phase so that newly
ported scripts can import perf directly from the installation directory
before legacy support is removed.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:28 +02:00
Ian Rogers
5fe83fb352 perf build: Make pylint build test opt-out (NO_PYLINT=1)
Commit 8a54784e70 ("perf build: Add pylint build tests") added a
compile-time pylint check for Python files in tools/perf, but left it
opt-in via PYLINT=1.

Now that pylint issues across tools/perf/python, tools/perf/pmu-events,
and tools/perf/tests/shell/lib have been cleaned up, enable the pylint
check by default when pylint is installed on the system, with an opt-out
via NO_PYLINT=1 (matching NO_SHELLCHECK=1, NO_MYPY=1, and other perf
build feature flags).

Configure PYTHONPATH in Makefile.perf so pylint resolves perf.pyi type
stubs and pmu-events modules, enable error and warning categories
(--disable=all --enable=E,W --disable=W0123,W0311,W0511,W0603,W0622,W0718
--ignored-modules=textual,setproctitle) appropriate for perf's standalone
CLI and test scripts, and require pylint >= 2.16.0 (skipping with a
warning if an older version is installed).

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:28 +02:00
Ian Rogers
b3e9c396d0 perf build: Make mypy build test opt-out (NO_MYPY=1)
Commit 168910d0f9 ("perf build: Add mypy build tests") added a
compile-time mypy type check for Python files in tools/perf, but left it
opt-in via MYPY=1.

Now that mypy issues across tools/perf/python, tools/perf/pmu-events,
and tools/perf/tests/shell/lib have been cleaned up, enable the mypy
check by default when mypy is installed on the system, with an opt-out
via NO_MYPY=1 (matching NO_SHELLCHECK=1 and other perf build feature
flags). Also configure MYPYPATH in Makefile.perf so scripts can resolve
perf.pyi type stubs and local modules, pass --ignore-missing-imports so
optional third-party packages do not fail default builds, and remove
*.mypy_log files during `make clean`.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:28 +02:00
Ian Rogers
1331150d7d perf test: Clean up mypy and pylint issues in shell test libraries
Clean up mypy type errors and pylint errors/warnings in
tools/perf/tests/shell/lib/ (attr.py, perf_json_output_lint.py, and
perf_metric_validation.py):
- Fix E0606 (possibly-used-before-assignment) in perf_metric_validation.py
  by importing sys at module level.
- Add type annotations for stack, second_results, collectlist,
  get_bounds(), and main() in perf_metric_validation.py.
- Avoid assigning -1 to list[int] expected_items in
  perf_json_output_lint.py, rename shadowing variables, and remove
  redundant lambdas.
- Remove unnecessary semicolons, use lazy logging arguments, specify
  exception types and file encodings, and initialize module-level logger
  in attr.py.

Also update tools/perf/tests/shell/lib/setup_python.sh to:
- Avoid x-prefix string comparisons.
- Export PYTHON and resolve PYTHONPATH and PERF_EXEC_PATH from
  BASH_SOURCE[0], ../../../python (for nested test directories such as
  coresight/), and the directory containing the perf binary so out-of-tree
  builds and standalone perf python scripts work seamlessly.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:28 +02:00
Ian Rogers
db5a607501 perf pmu-events: Clean up mypy and pylint issues
Clean up mypy type errors and pylint warnings across the pmu-events Python
scripts (amd_metrics.py, intel_metrics.py, jevents.py,
make_legacy_cache.py,
and metric.py) in preparation for making MYPY and PYLINT build tests
opt-out.

In addition to type annotations and unused import/variable cleanups, fix
three bugs in intel_metrics.py exposed by static analysis:
- Fix references to undefined 'args.model' (instead of '_args.model')
  inside
  try/except blocks in IntelL2() and UncoreMemBw(), which previously threw
  NameError and silently disabled Skylake/CascadeLake L2 silent eviction
  adjustments and uncore memory bandwidth JSON loading.
- Define DC_WB_U and DC_WB_D before their first use in IntelL2(), fixing
  an UnboundLocalError that silently dropped the l2_out_rate, wbn, and isd
  metrics.
- Fix Event-to-string comparison and addition in IntelFp() by comparing
  and modifying 'f_assist.name' instead of the Event object 'f_assist'.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:28 +02:00
Ian Rogers
ca23ecf8ee perf python: Allow KeyboardInterrupt to propagate in LiveSession
LiveSession.run() synchronously blocks while polling evlist for events.
When running interactive tools or scripts from the terminal,
KeyboardInterrupt exceptions raised via Ctrl-C must propagate so the
caller can break out of the polling loop.

Previously, LiveSession caught KeyboardInterrupt with an empty pass
statement, swallowing the exception and preventing calling scripts from
detecting the interrupt cleanly. Remove the empty handler so calling
scripts receive KeyboardInterrupt and can perform clean teardown.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:27 +02:00
Ian Rogers
f66944587d perf python: Add Intel PT call_return and itrace capability
Add support for Intel PT call_return events and itrace options to the
perf Python extension so standalone Python scripts can decode and
inspect low-level instruction traces.

Specifically:
- Add a call_return callback parameter and itrace option string to
  perf.session, treating explicit None (Py_None) callbacks as omitted.
- Expose the perf.call_return object with db_id, parent_id, insn_count,
  cyc_count, comm, pid, tid, call_time, return_time, branch_count,
  call_ref, return_ref, flags, and call_path (resolved as a
  perf.callchain ordered from outermost caller to callee, populating
  frame->map and frame->sym so call_path entries expose resolved symbol
  and DSO names).
- Export perf.CALL_RETURN_NO_CALL, perf.CALL_RETURN_NO_RETURN, and
  perf.CALL_RETURN_NON_CALL flag constants.
- Expose session.e_machine and session.is_64_bit properties, preferring
  recorded thread ELF machines (perf_session__e_machine) over perf_env
  so pipe-mode traces do not prematurely cache host bitness.
- Support optional vmlinux, kallsyms, and symfs symbol configuration
  parameters (and PERF_SYMBOL_VMLINUX, PERF_SYMBOL_KALLSYMS,
  PERF_SYMBOL_SYMFS environment fallbacks) in perf.session, resetting
  symbol_conf pointers and freeing vm_tm_corr_args, cpu_bitmap, and
  ptime_range in pyrf_session__delete().

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:27 +02:00
Ian Rogers
7a481f6c71 perf python: Expose addr location, transaction, and context_switch
Expose destination address location components (addr_dso, addr_symbol,
addr_sym_offset), branch/transaction metrics (branch_type, in_tx,
flags, transaction), machine_pid, vcpu, sym_offset, and context_switch
callbacks directly to the Python extension.

Also include supporting fixes and infrastructure updates in
util/python.c and perf.pyi:
- Support fetching sym_offset on resolved sample symbols.
- Populate sample machine_pid and vcpu from evlist__id2sid() when
  perf_guest is enabled, and resolve samples against the matching guest
  or host machine.
- Expose next_prev_pid and next_prev_tid on switch_event only for
  PERF_RECORD_SWITCH_CPU_WIDE records (returning None otherwise).
- Wire up tracing_data in pyrf_session__new() and update perf.pyi type
  stubs (including srccode() and insn() return types).

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:27 +02:00
Ian Rogers
4b15226c14 perf python: Improve perf script -l descriptions
Add module docstrings to counting.py, tracepoint.py, and twatch.py. This
satisfies pylint's missing-module-docstring check and prepares these
existing standalone scripts in tools/perf/python/ for the later commit
in this series ("perf script: Support standalone scripts and remove
embedded scripting"), which updates 'perf script -l' to scan
tools/perf/python/ and display each script's module docstring:

```
$ perf script -l
List of available scripts:
...
  counting
    Example for counting perf events.
...
  tracepoint
    Example showing how to enable a tracepoint and access its fields.
  twatch
    Example to show how to enable a software event and track
    context switches.
...
```

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:27 +02:00
Ian Rogers
abbcb48f33 perf python: Clean up pylint warnings in twatch.py
Clean up pylint warnings in twatch.py so that it passes pylint without
warning suppression comments:
- Convert tab indentation to 4 spaces (W0311: bad-indentation).
- Remove unnecessary trailing semicolon (W0301: unnecessary-semicolon)
  after evsel.open().
- Convert floating multi-line string comments to '#' comments (W0105:
  pointless-string-statement).

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:27 +02:00
Ian Rogers
62dfb55494 perf python: Clean up pylint warnings in tracepoint.py
Clean up pylint warnings in tracepoint.py so that it passes pylint
without warning suppression comments:
- Catch ImportError instead of bare 'except:' (W0702: bare-except) when
  importing setproctitle.
- Remove unnecessary trailing semicolon (W0301: unnecessary-semicolon)
  after evlist.enable().

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:27 +02:00
Ian Rogers
2997739214 perf python: Clean up pylint warnings in treport.py
Clean up pylint warnings in treport.py so that it passes pylint without
warning suppression comments:
- Replace broad 'except Exception:' clauses (W0718:
  broad-exception-caught) with specific exception tuples.
- Pass both pid and sample_tid to session.find_thread() so guest and
  process threads are resolved accurately.
- Rename parameter 'args' to 'pos_args' in FlameGraph.__init__() to
  avoid shadowing the outer scope variable 'args' (W0621:
  redefined-outer-name).
- Clear session = None in a finally block after session.process_events()
  to break the C perf_session reference cycle before launching the TUI.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:27 +02:00
Ian Rogers
2dfe9eaec5 perf python: Clean up pylint warnings in ilist.py
Replace bare 'except:' clauses (pylint W0702: bare-except) in ilist.py
with specific exception tuples (OSError, ValueError, RuntimeError,
TypeError, KeyError) and use a safe '.get("name", "")' sort key in
IListApp.compose() so that ilist.py passes pylint without warning
suppression comments and handles unnamed PMU events gracefully.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:27 +02:00
Ian Rogers
514ecdfd00 perf python: Update callchain stubs and session thread lookup
Update pyrf_session__find_thread() in util/python.c to accept an
optional tid parameter (defaulting to pid) and return None instead of
raising TypeError when a thread is not found in the session machines.

Update perf.pyi to match:
- Set session.find_thread() signature to (pid: int, tid: int = -1) ->
  Optional[thread].
- Update callchain_node.symbol and callchain_node.dso to str (the C
  getters return "[unknown]" fallback strings rather than None) and add
  __iter__() to callchain.

Also update treport.py to handle Optional[thread] returned by
session.find_thread().

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:27 +02:00
Ian Rogers
c4925cc8b8 perf python: Update syscall helpers and expose arch_strerrno
Update the PyArg_ParseTupleAndKeywords format string for
pyrf__syscall_name() and pyrf__syscall_id() from "i|$i" to "i|i" (and
"s|$i" to "s|i"), allowing elf_machine to be passed as an optional
positional argument as well as a keyword argument. Update syscall_id()
and syscall_name() in perf.pyi to match, and set the return type of
syscall_name() to Optional[str] as unknown syscall numbers return None.

Also expose perf_env__arch_strerrno() as perf.arch_strerrno(err,
elf_machine=None) so standalone Python scripts can resolve
architecture-specific errno names directly from the auto-generated
trace beauty tables instead of maintaining duplicate errno dictionaries
in Python. Tighten the macro pattern in arch_errno_names.sh to
E[A-Z0-9]+ so compiler -D flags containing underscores (such as LLVM's
-DEXPERIMENTAL_KEY_INSTRUCTIONS=1) do not shadow EPERM (1), and add
EM_SPARC32PLUS alongside EM_SPARC and EM_SPARCV9.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:49:27 +02:00
Hui Su
bac027175a perf synthetic-events: Check schedstat domain allocation failure
__synthesize_schedstat_domain() uses event after zalloc() without
checking for allocation failure, unlike __synthesize_schedstat_cpu().

If zalloc() fails and returns NULL, dereferencing ds->header.type
immediately crashes with a segmentation fault:

  Program received signal SIGSEGV, Segmentation fault.
  0x00005555558aed8a in __synthesize_schedstat_domain ()
  #0  0x00005555558aed8a in __synthesize_schedstat_domain ()
  #1  0x00005555558b889a in perf_event__synthesize_schedstat ()
  #2  0x000055555563c397 in cmd_sched ()
  #3  0x00005555556583a1 in handle_internal_command ()
  #4  0x00005555555bf739 in main ()

perf_event__synthesize_schedstat() already treats a NULL event as an
error and cleans up, so return NULL when the allocation fails.

After this fix, an allocation failure returns NULL safely, allowing the
caller to exit gracefully without crashing:

  [ perf sched stats: Failed !! ]

Fixes: c3030995f2 ("perf sched stats: Add record and rawdump support")
Signed-off-by: Hui Su <sh_def@163.com>
Cc: Swapnil Sapkal <swapnil.sapkal@amd.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 20:29:40 +02:00
Arnaldo Carvalho de Melo
b1d0b4093f perf tools: Bump the minimum Python version to 3.9
perf's build only refused interpreters older than 3.6, the check added
when jevents.py started using f-strings, and jevents.py carried a
removesuffix() shim to stay usable on them.

The kernel itself requires Python 3.9.x since 5e25b972a2 ("docs:
changes: update Python minimal version"), so tools in the tree are
expected to work with it, and staying compatible with older
interpreters stopped paying off:

 - the PEP 585 generics, list[...], used by the type annotations in
   jevents.py and util/setup.py are only subscriptable from Python 3.9
   and, being evaluated at import or definition time, they break the
   build on RHEL 8's python3.6.8 with:

   TypeError: 'type' object is not subscriptable

 - ProcessPoolExecutor(initializer=, initargs=) requires Python 3.7, so
   generating pmu-events.c fails there as well.

Rather than spreading version guards and typing.List() workarounds for
interpreters that cannot be supported anyway, make 3.9 the floor: ask
for it once in Makefile.config and use the result in both places that
run python while building, jevents generation and the python binding,
as the binding is still built when NO_JEVENTS=1 skips the generation
check, and drop the removesuffix() shim, since str.removesuffix() was
added in 3.9.

RHEL 8 is in feature freeze, so those wanting a new perf and its python
features have to vendor a newer interpreter, just as
Documentation/process/changes.rst already asks for the kernel itself.

Tested with Python 3.9.22: perf builds, generating pmu-events.c and the
python binding, with byte for byte identical output to the build made
with the shim, while Python 3.8.20 and 3.6.15 are rejected with the
"older than 3.9" error, by the jevents check in a regular build and by
the binding check when NO_JEVENTS=1 makes them sail past it, where they
used to die on the TypeError from util/setup.py. With NO_JEVENTS=1 and
NO_LIBPYTHON=1 no interpreter runs while building, so neither check
applies. vermin reports no perf build file as requiring more than 3.9,
the only offender being the runtime script
scripts/python/mem-phys-addr.py, which the build doesn't run.

Suggested-by: Ian Rogers <irogers@google.com>
Reviewed-by: Ian Rogers <irogers@google.com>
Reviewed-by: Mauro Carvalho Chehab <mchehab+huawei@kernel.org>
Cc: Mauro Carvalho Chehab <mchehab+huawei@kernel.org>
Assisted-by: LLM
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-26 05:21:58 -03:00
Arnaldo Carvalho de Melo
528b1475f9 perf mem record: Use the IBS swfilt filter when available
IBS events with exclude_{user,kernel} bits, as used for per-thread
recording when kernel samples are not allowed, are rejected on hardware
without the privilege filter, so per-thread 'perf mem record' fails on
AMD:

  $ perf mem record -o /dev/null -- true
  Failure to open event 'ibs_op/ldlat=0/u' on PMU 'ibs_op' which will be removed.

Kernel v6.14 added swfilt, a software privilege filter exposed as the
'swfilt' format term, making those events usable per-thread.  Give the
ibs_op memory events extra tables with the term, selected in
perf_pmu__arch_init() when the PMU exposes it, keeping the names that
need system wide mode otherwise; the knowledge that IBS needs this
stays in the arch code.

Suggested-by: Namhyung Kim <namhyung@kernel.org>
Suggested-by: Ravi Bangoria <ravi.bangoria@amd.com>
Reviewed-by: Namhyung Kim <namhyung@kernel.org>
Reviewed-by: Ravi Bangoria <ravi.bangoria@amd.com>
Assisted-by: LLM
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 18:14:26 +02:00
Arnaldo Carvalho de Melo
010147f87a perf mem record: Request PERF_SAMPLE_CPU by default
The data type profiling per-sample stream keys cross-CPU contention on
sample->cpu, which without PERF_SAMPLE_CPU is the "no CPU info"
sentinel, making same-instance accesses from different cores
indistinguishable from same-CPU traffic.  'perf mem record' already
passes -d and -W to the record parser, add --sample-cpu and document it
in perf-mem(1).

Also grow rec_argv: the new entry overflows it on PMUs with separate
load and store events, as the space for the fixed arguments was not
reserved.

Reviewed-by: Ian Rogers <irogers@google.com>
Reviewed-by: Namhyung Kim <namhyung@kernel.org>
Assisted-by: LLM
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 18:14:22 +02:00
Arnaldo Carvalho de Melo
02ee4666a0 perf annotate-data: Bound the member nesting recursion
Members are added recursively, and a broken DIE can make a member's
type point back at one of its own ancestors, recursing until the stack
is gone; nothing usable comes out of nesting members 32 deep anyway, so
stop there, marking the member as truncated and giving up on member
types that don't resolve.

The check is where the children of an aggregate would be expanded, so
only struct/union members are marked as truncated.

Reviewed-by: Ian Rogers <irogers@google.com>
Reviewed-by: Namhyung Kim <namhyung@kernel.org>
Assisted-by: LLM
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 18:13:51 +02:00
Arnaldo Carvalho de Melo
14ca0a28de perf annotate-data: Resolve type DIEs in the debug file they came from
'perf report -s type' hangs burning CPU on the dwz compressed debug
info of libz.so.1 (zlib-ng): die_collect_vars() saves the
dwarf_dieoffset() of the type DIE, which is relative to the file it
lives in - the dwz alt file for the types shared by more than one CU -
and update_var_state() resolves that offset in the main debug file,
parsing whatever is at it, here a typedef whose DW_AT_type refers to
itself.

Record whether the type DIE came from the alt file and resolve the
offset with die_get_type_die() in that file, with no fallback.

Fixes: 06b2ce7538 ("perf annotate-data: Maintain variable type info")
Fixes: 55ee3d005d ("perf annotate-data: Add a cache for global variable types")
Reviewed-by: Ian Rogers <irogers@google.com>
Reviewed-by: Namhyung Kim <namhyung@kernel.org>
Assisted-by: LLM
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 18:13:45 +02:00
Arnaldo Carvalho de Melo
3dfdd195c7 perf dwarf-aux: Add die_same_file() and die_get_type_die()
dwarf_dieoffset() is relative to the file the DIE is in, so an offset
saved by die_collect_vars()/die_collect_global_vars() is only
meaningful in that file: add die_same_file(), comparing the Dwarf each
DIE's CU belongs to, and die_get_type_die(), resolving the offset in it
with the saved tag as a sanity check.  Resolving the offset in the main
file instead parses whatever is at it when it came from the dwz common
file.

dwarf_cu_getdwarf() is new in elfutils 0.160, so the libdw feature test
probes for it and Makefile.config says 0.160.

Reviewed-by: Ian Rogers <irogers@google.com>
Reviewed-by: Namhyung Kim <namhyung@kernel.org>
Cc: Masami Hiramatsu <mhiramat@kernel.org>
Assisted-by: LLM
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 18:13:25 +02:00
Arnaldo Carvalho de Melo
a6ac1e9ca9 perf dwarf-aux: Bound the type chases for broken debug info
A DIE parsed at an offset that is not the start of a DIE can have a
DW_AT_type that refers back to itself, making the typedef/qualifier
chases in die_get_real_type(), die_get_pointer_type() and
die_get_typename_from_type() spin forever; 'perf report -s type' did
that on the dwz compressed debug info of zlib-ng (libz.so.1).

No sane typedef/qualifier chain is 32 DIEs long, so give up on the type
with a pr_debug instead of hanging.

Reviewed-by: Ian Rogers <irogers@google.com>
Reviewed-by: Namhyung Kim <namhyung@kernel.org>
Cc: Masami Hiramatsu <mhiramat@kernel.org>
Assisted-by: LLM
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 18:12:23 +02:00
Ian Rogers
906af9e1c9 perf test stat metrics cgroup: Strip possible slash from cgroup name
The grep to match cgroup name in metric output assumes no leading / on
the cgroup name, however, cgroups in /proc/self/cgroup may have a
leading /. Strip the / if it exists to avoid failures to match the
cgroup name in the perf stat output.

Signed-off-by: Ian Rogers <irogers@google.com>
Acked-by: Namhyung Kim <namhyung@kernel.org>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 17:42:21 +02:00
Arnaldo Carvalho de Melo
66fcf1357a perf test workload: Use unsigned int in code_with_type instead of uint
The declaration of the Rust helper test_rs() uses "uint", a BSD-ism
that lives in <sys/types.h>, so on glibc it is only visible by
accident: glibc's <stdlib.h> includes <sys/types.h>, where uint is
exposed under __USE_MISC, which is on by default.

musl does none of that: its <stdlib.h> doesn't include <sys/types.h>
and it typedefs uint there only when _GNU_SOURCE/_BSD_SOURCE is
defined, while nothing else in this translation unit includes
<sys/types.h>. Building it on Alpine therefore fails with:

  tests/workloads/code_with_type.c:9:21: error: unknown type name 'uint'; did you mean 'int'?
  tests/workloads/code_with_type.c:39:17: error: implicit declaration of function 'test_rs' [-Wimplicit-function-declaration]

The second error is a consequence of the first one: with the
declaration at line 9 rejected, the call at line 39 has no prototype,
which is an error since gcc 14.

The breakage is only visible when rustc is present, because
tests/workloads/Build adds code_with_type.o when CONFIG_RUST_SUPPORT
is detected, and tools/build/feature only checks for "rustc
--version". That is why alpine:3.23 and alpine:3.24 fail while
alpine:3.22 and alpine:edge, lacking rustc, build fine and hide it.

Use unsigned int, which needs no header at all.

Fixes: 2e05bb52a1 ("perf test workload: Add code_with_type test workload")
Reviewed-by: Ian Rogers <irogers@google.com>
Acked-by: Namhyung Kim <namhyung@kernel.org>
Cc: Dmitrii Dolgov <9erthalion6@gmail.com>
Assisted-by: LLM
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 17:42:16 +02:00
longlong yan
2d3135cded perf bench numa: Add NULL check after calloc()
Two calloc() calls in the numa benchmark lack NULL return checks,
leading to potential NULL pointer dereferences on allocation failure:

1. worker_process(): the allocated `pthreads` array is used in the
   following for-loop via pthreads[t] without checking for NULL.

2. __bench_numa(): the allocated `pids` array is used in the following
   for-loop via pids[i] without checking for NULL.

Add BUG_ON() checks after each calloc(), consistent with the existing
NULL check style used elsewhere in the same file (e.g., node_present
and nodes allocations).

Signed-off-by: longlong yan <yanlonglong@kylinos.cn>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 17:02:31 +02:00
Nia Su
aa9265d507 perf evlist: Don't restrict uncore events to PMU CPUs
The PMU CPU map has different semantics for core and uncore PMUs.

For core PMUs, pmu_cpus contains the CPUs on which the event can be
opened. Intersect the user-requested CPU map with the PMU CPU map to
reject CPUs unsupported by the PMU.

For uncore PMUs, pmu_cpus is read from the PMU's cpumask sysfs attribute,
which lists the default CPU to open the event on per socket/die, not the
set of CPUs it can only be opened on. The user-requested CPU may override
these defaults, and the driver can redirect the event to the appropriate
control CPU.

Currently, __perf_evlist__propagate_maps() intersects the user-requested
CPU map with pmu_cpus for all PMUs. If the user-requested CPU is not in
pmu_cpus, the intersection becomes empty and the evsel is removed before
perf_event_open() is called.

Add evsel->is_pmu_uncore, set once from pmu->is_uncore at parse time,
to skip the intersection for uncore PMUs. Core PMUs, and other
non-core PMUs such as software events, breakpoints, or tracepoints,
continue to be restricted to their PMU CPU map.

Fixes: 811082e4b6 ("perf parse-events: Support user CPUs mixed with threads/processes")
Reviewed-by: Ian Rogers <irogers@google.com>
Assisted-by: Claude:claude-sonnet-5
Signed-off-by: Nia Su <nia.su@sifive.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 15:29:56 +02:00
Jiebin Sun
0d91c10f88 perf tests c2c: Add function view stdio coverage
Exercise the function view without driving a terminal now that it has
a stdio path. Keep the existing datasym record/report coverage and make a
separate recording of the contended locks used by the futex hash benchmark.

Always check the function table headers, table replacement, missing-iaddr
diagnostic, and conflicting options. A machine can support c2c recording
without capturing a contended sample, so report a skip when the hierarchy
is empty rather than treating hardware sampling variance as a failure.

When samples are available, check generic row shapes for all three
hierarchy levels, their expanded fold signs, cacheline addresses, and the
absence of trailing whitespace in the table body.

Reviewed-by: Tianyou Li <tianyou.li@intel.com>
Reviewed-by: Wangyang Guo <wangyang.guo@intel.com>
Signed-off-by: Jiebin Sun <jiebin.sun@intel.com>
Acked-by: Namhyung Kim <namhyung@kernel.org>
Tested-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Dapeng Mi <dapeng1.mi@linux.intel.com>
Cc: Ian Rogers <irogers@google.com>
Cc: James Clark <james.clark@linaro.org>
Cc: Thomas Falcon <thomas.falcon@intel.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 15:27:17 +02:00
Jiebin Sun
89cfd46b7e perf c2c: Add stdio support for the function view
The function view is currently TUI-only, so it cannot be used by builds
without SLANG support, when output is piped, or from a script. Add a
--function option that prints the fully expanded three-level hierarchy to
stdout.

Keep the stdio renderer in builtin-c2c.c and reuse the common function-view
model introduced by the merged series. Export only the coalescing-field
capability check from the model, preserving the util/UI boundary and
leaving the TUI object in libperf-ui.a.

Stop padding the final identity column in symbol_view_entry(). The generic
formatter pads non-final columns but deliberately leaves the final column
unpadded, avoiding trailing whitespace in function-view table rows. The TUI
remains unchanged because its browser clears the rest of each rendered row.

--function implies --stdio and is rejected together with --stats. Validate
the iaddr requirement before processing events. Return function-view build
failures from the report command, and preserve TUI browser errors when
converting the display helpers to return a status.

Committer notes:

  root@x2:~# uname -r
  7.2.5-200.fc44.x86_64
  root@x2:~# rpm -q kernel-debuginfo
  kernel-debuginfo-7.2.5-200.fc44.x86_64
  root@x2:~# perf c2c record perf bench futex hash -t 4 -r 1 -s > /dev/null 2>&1
  root@x2:~# perf c2c report --stdio --function | grep "Functions Table" -A25
             Shared Data Functions Table
  =================================================
  #
  #    Cycles    Store
  #         %    count  Function / Contending function / Cacheline
  # .........  .......  ..............................
  #
    -  47.89%      703  - [k] _raw_spin_lock
                   322    - [k] _raw_spin_lock
                    24        0xffff8b6dcbadf040
                    23        0xffff8b6dcbadf2c0
                    23        0xffff8b6dcbadf080
                    23        0xffff8b6dcbadf380
                    22        0xffff8b6dcbadf280
                    22        0xffff8b6dcbadf140
                    22        0xffff8b6dcbadf340
                    21        0xffff8b6dcbadf300
                    21        0xffff8b6dcbadf400
                    20        0xffff8b6dcbadf1c0
                    19        0xffff8b6dcbadf3c0
                    19        0xffff8b6dcbadf180
                    19        0xffff8b6dcbadf0c0
                    17        0xffff8b6dcbadf100
                    16        0xffff8b6dcbadf240
                    11        0xffff8b6dcbadf200
                   205    - [k] futex_q_unlock
  root@x2:~#

Reviewed-by: Tianyou Li <tianyou.li@intel.com>
Reviewed-by: Wangyang Guo <wangyang.guo@intel.com>
Signed-off-by: Jiebin Sun <jiebin.sun@intel.com>
Acked-by: Namhyung Kim <namhyung@kernel.org>
Tested-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Dapeng Mi <dapeng1.mi@linux.intel.com>
Cc: Ian Rogers <irogers@google.com>
Cc: James Clark <james.clark@linaro.org>
Cc: Thomas Falcon <thomas.falcon@intel.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 15:25:07 +02:00
Jiebin Sun
f4a58c7164 perf tests c2c: Report skip when the workload fails
The workload path leaves err at 0 and returns, so the test exits 0 and is
reported as a pass even though nothing was recorded and neither report
invocation ran. The check_c2c_support() path above it already sets err=2.

Set err=2 there as well so a failing workload is reported as a skip.

Fixes: ac881007c4 ("perf tests c2c: Add a basic c2c")
Reviewed-by: Tianyou Li <tianyou.li@intel.com>
Reviewed-by: Wangyang Guo <wangyang.guo@intel.com>
Signed-off-by: Jiebin Sun <jiebin.sun@intel.com>
Acked-by: Namhyung Kim <namhyung@kernel.org>
Cc: Dapeng Mi <dapeng1.mi@linux.intel.com>
Cc: Ian Rogers <irogers@google.com>
Cc: James Clark <james.clark@linaro.org>
Cc: Thomas Falcon <thomas.falcon@intel.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 15:18:38 +02:00
Jiebin Sun
b36a6f180b perf c2c: Fix documented default coalesce fields
The default coalesce fields dropped pid in favor of iaddr, but the man
page still documents the old pid,iaddr default. Update it to match the
command.

Fixes: 423701a0c8 ("perf c2c: Change the default coalesce setup")
Reviewed-by: Tianyou Li <tianyou.li@intel.com>
Reviewed-by: Wangyang Guo <wangyang.guo@intel.com>
Signed-off-by: Jiebin Sun <jiebin.sun@intel.com>
Acked-by: Namhyung Kim <namhyung@kernel.org>
Cc: Dapeng Mi <dapeng1.mi@linux.intel.com>
Cc: Ian Rogers <irogers@google.com>
Cc: James Clark <james.clark@linaro.org>
Cc: Jiri Olsa <jolsa@kernel.org>
Cc: Thomas Falcon <thomas.falcon@intel.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 15:18:01 +02:00
nanshuaibo
4c32b6d6bd perf sched: Make output_name variable static
The output_name variable is only used within builtin-sched.c for the
stats subcommand, so declare it static. This fixes a sparse warning:

  builtin-sched.c:4140:12: warning: symbol 'output_name' was not
  declared. Should it be static?

Reviewed-by: Ian Rogers <irogers@google.com>
Signed-off-by: nanshuaibo <nanshuaibo811@163.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 15:12:43 +02:00
Hemanth Selam
d552148607 perf tools: Fix typos in comments
Fix typos in comments, reported by scripts/checkpatch.pl using the
misspelling list in scripts/spelling.txt.  Only touches comments, no
code changes.

Assisted-by: Cursor:claude-opus-5
Signed-off-by: Hemanth Selam <hemanth.selam@gmail.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 15:11:36 +02:00
Hemanth Selam
c9dd729e80 perf synthetic-events: Fix repeated word in log message
Drop the word written twice, reported by checkpatch.pl as a possible
repeated word.

Only the message text changes, no code changes.

Assisted-by: Cursor:claude-opus-5
Signed-off-by: Hemanth Selam <hemanth.selam@gmail.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 15:10:02 +02:00
Ian Rogers
8c74fcecb4 tools include: Add missing stdarg.h include
Header file makes use of varargs but doesn't directly include stdarg.h.

Closes: https://lore.kernel.org/linux-perf-users/20260916062233.192271F000FF@smtp.kernel.org/
Reported-by: sashiko-bot@kernel.org
Signed-off-by: Ian Rogers <irogers@google.com>
Acked-by: Namhyung Kim <namhyung@kernel.org>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 15:04:50 +02:00
Ian Rogers
5d0e31779b perf thread: Free the comm read from procfs
procfs__read_str() allocates the buffer it hands back and
thread__set_comm() only stores an interned copy of the string, so the
caller owns the buffer. thread__set_comm_from_proc() freed it when the
read came back empty but not once it had been used, leaking it on
every successful call.

Free it on both paths. The empty read still returns -1, err being
untouched in that case.

Found with leak sanitizer while running 'perf trace':

  Direct leak of 7 byte(s) in 1 object(s) allocated from:
      #1 io__getdelim fs/../io.h:179
      #2 filename__read_str fs/fs.c:365
      #3 procfs__read_str fs/fs.c:402
      #4 thread__set_comm_from_proc util/thread.c:297
      #5 syscall_arg__scnprintf_pid trace/beauty/pid.c:15

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 15:00:03 +02:00
Ian Rogers
0cf5416f48 perf trace: Free the host machine allocation
trace__symbols_init() creates the host machine with machine__new_host(),
which allocates a struct machine, but trace__symbols__exit() released it
with machine__exit(). That tears down the contents of the machine and
leaves the allocation itself behind, so use machine__delete(), which
does both. The replay path points trace->host at the machine embedded in
the session and never reaches here, so nothing else is affected.

The leak was hidden from leak sanitizer because trace__symbols_init()
passes the machine to trace_event__register_resolver(), which stores it
as the private pointer of the global tep handle. The handle kept the
machine reachable for as long as the process lived, so it was only once
the handle started being freed that this was reported:

  Direct leak of 1256 byte(s) in 1 object(s) allocated from:
      #1 __machine__new_host util/machine.c:135
      #2 machine__new_host util/machine.c:155
      #3 trace__symbols_init builtin-trace.c:2105
      #4 trace__run builtin-trace.c:4759
      #5 cmd_trace builtin-trace.c:6091

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 14:59:28 +02:00
Ian Rogers
5a3d7afdfb perf trace-event: Free the global trace_event when a command ends
The tep handle behind trace_event__tp_format() is a process wide cache
of the running kernel's tracepoint formats and nothing ever released
it, as the comment above it had noted since the code was added.

Add trace_event__exit() and call it from run_builtin() next to the
existing perf_config__exit(). By then the builtin has returned, so the
tep_event pointers it handed out, such as the ones cached in
evsel->tp_format, are no longer reachable.

Note that this does not silence every libtraceevent report under
leak sanitizer. Parsing a print fmt drops a token inside the library
itself, and as those allocations are not linked into the handle,
freeing the handle cannot reclaim them.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 14:58:03 +02:00
Ian Rogers
d9eba1d5b5 perf trace-event: Reuse an already parsed tracepoint format
tp_format() read and parsed the format file on every call. Each parse
registers another tep_event with the global tep handle, and
libtraceevent has no way to free an individual event, only the whole
handle, so a repeated lookup of the same tracepoint both redoes the
work of reading and parsing the file and leaves a duplicate behind for
the rest of the session.

Ask the handle for the event first with tep_find_event_by_name() and
only fall back to reading the format file when it has not been parsed
yet. The handle holds formats for the running kernel alone, so a name
that is found is the same format that would have been read.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 14:57:52 +02:00
Ian Rogers
e223a41c42 perf trace-event: Report tracepoint format errors with NULL and errno
trace_event__tp_format() encoded failure with ERR_PTR() while
trace_event__tp_format_id() returned a plain NULL when tep_find_event()
found nothing, and tp_format() itself returned NULL when
tep_parse_format() failed, as its return value was discarded. Callers
test with IS_ERR(), which NULL does not satisfy, so those two failures
were taken for success. In syscall__read_info() that leads straight to:

	if (IS_ERR(sc->tp_format)) {
		...
		return err;
	}
	if (syscall__alloc_arg_fmts(sc, sc->tp_format->format.nr_fields - 1))

which dereferences NULL when a format file fails to parse.

Mixing encoded error pointers with pointers that are compared against
NULL is what allows that to happen, so drop ERR_PTR() here and report
failures the way the rest of these paths already expect, by returning
NULL with errno set. evsel__tp_format() no longer has to translate the
error back into errno before printing it with %m, and the remaining
callers become NULL tests.

syscall__scnprintf_args() gains back its fallback of printing raw
arguments: it asked for IS_ERR(sc->tp_format), but syscall__read_info()
had already replaced the error pointer with NULL, so the branch could
never be taken.

Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 14:57:39 +02:00
Ian Rogers
d227b45fc1 perf machine: Add session back pointer to fix out of bounds read
thread__e_machine_endian() decides whether a thread is live, and so
whether to read /proc/pid/exe rather than fall back to the perf.data
environment, by recovering the session from the machine:

	session = container_of(machine->machines, struct perf_session,
			       machines);
	is_live = !session->data;

That only holds when the struct machines is the one embedded in a struct
perf_session. It is not the only one. aslr_tool keeps its own in struct
aslr_tool, and hists_cumulate, hists_filter, hists_link, hists_output
and thread-maps-share each put one on the stack. For those the
container_of subtracts offsetof(struct perf_session, machines) from an
address that was never inside a session, and the following load of
session->data reads outside the object, which is what ASan reports.

Replace the derivation with an explicit link. machines__init() takes the
owning session, or NULL when the machines is standalone, and
thread__e_machine_endian() reads it back through machines__session().

A NULL session is treated as live. The tests use synthetic pids that
have no /proc entry, so the read fails there and the e_machine falls
back to EM_HOST as before, rather than being decided by whatever the
out of bounds read happened to return. perf inject registers its
session with the aslr tool once the session exists, before any event is
processed, so that tool keeps reporting file based threads as not live.

Fixes: 70351029b5 ("perf thread: Add support for reading the e_machine type for a thread")
Assisted-by: Antigravity:gemini-3.1-pro
Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 14:08:40 +02:00
Zhan Xusheng
7e27239d22 perf symbols: Apply the symfs flat layout to the composed filename
--symfs=<dir>,flat documents itself as matching only the base name, so a
debuginfo lookup for /usr/lib/x86_64-linux-gnu/libc.so.6 should land on
<dir>/libc.so.6.debug.  It lands on
<dir>/debug/usr/lib/x86_64-linux-gnu/libc.so.6.debug instead, because the
layout is applied to a fixed prefix and the file name arrives afterwards:

	len = __symbol__join_symfs(filename, size, "/usr/lib/debug");
	snprintf(filename + len, size - len, "%s.debug", dso__long_name(dso));

perf_basename() only ever sees "/usr/lib/debug", so neither layout comes
out of it.

Compose the path as it would appear on the profiled system and join it
once, which puts the layout on the whole name.  That covers
FEDORA_DEBUGINFO, UBUNTU_DEBUGINFO, MIXEDUP_UBUNTU_DEBUGINFO,
OPENEMBEDDED_DEBUGINFO and BUILDID_DEBUGINFO, plus the same composition in
build_id_cache__find_debug().

BUILDID_DEBUGINFO needs one more step: the build id cache splits the first
two characters of the build id off into a directory name, so the basename
of the hierarchy path is only part of the build id.  Name the flat file
after the whole build id.

dso__disassemble_filename() passes a path from perf's own build id cache
rather than one on the profiled system, and every entry there is named
"elf" or "debug".  Use path__join() so the layout does not apply.

With --symfs /s,flat the lookups are now /s/libc.so.6, /s/libc.so.6.debug,
/s/sleep and /s/<build id>.debug.  hierarchy is unchanged.

Reviewed-by: Namhyung Kim <namhyung@kernel.org>
Signed-off-by: Zhan Xusheng <zhanxusheng@xiaomi.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 14:07:01 +02:00
Ethan Nelson-Moore
60d454456f perf tools: Remove unused empty help-unknown-cmd.h header
tools/perf/util/help-unknown-cmd.h has been empty and unused ever since
it was added to the kernel in commit 5feaac248a ("perf tools: Move
help_unknown_cmd() to its own file") to its own file"). Remove it.

Signed-off-by: Ethan Nelson-Moore <enelsonmoore@gmail.com>
Reviewed-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 13:05:48 +02:00
Ian Rogers
97e94e5c5a perf test: Fix PMU metric parsing tests for unknown literals
On ARM the #slots literal may or may not be present, it won't be present
on x86. As it is missing it causes the ampereone and ampereonex PMU
metric tests to fail when run say on x86.

Extend the fake_pmu logic so that in these test cases we fake the
unknown literals like #slots as 1.0.

When building with JEVENTS_ARCH=all the ampere metric tests no longer
fail.

Signed-off-by: Ian Rogers <irogers@google.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
2026-09-25 12:51:49 +02:00