Linux Perf Users
 help / color / mirror / Atom feed
From: sashiko-bot@kernel.org
To: "Ian Rogers" <irogers@google.com>
Cc: bpf@vger.kernel.org, linux-perf-users@vger.kernel.org
Subject: Re: [RFC PATCH v1 8/8] perf tests: Add build_id_offset test coverage
Date: Fri, 07 Aug 2026 09:58:35 +0000	[thread overview]
Message-ID: <20260807095836.572991F000E9@smtp.kernel.org> (raw)
In-Reply-To: <20260807071818.718751-9-irogers@google.com>

Thank you for your contribution! Sashiko AI review found 5 potential issue(s) to consider:
- [Medium] Heap Use-After-Free of `thread` reference handle in `mmap_events`.
- [Medium] Raw pointer comparison of reference-counted `struct map` handles causes spurious test failures.
- [Medium] Silent test bypass due to missing validation of `PERF_SAMPLE_BUILD_ID_OFFSET` fields.
- [Medium] Stack Out-Of-Bounds Read when synthesizing `PERF_SAMPLE_CALLCHAIN_BUILD_ID_OFFSET`.
- [Low] Missing explicit `<string.h>` inclusion causes compilation failures on musl libc.
--

--- Patch [8]: [RFC PATCH v1 8/8] perf tests: Add build_id_offset test coverage ---
commit 2b1a4526386e7ebd56cc41f452ac5f172c32e199
Author: Ian Rogers <irogers@google.com>

perf tests: Add build_id_offset test coverage

Test the kernel interface using sys_perf_event_open, test perf inject
--sample-buildids with pipe mode and callchains, and test perf record
--buildid-offset across multiple sampling modes.

> diff --git a/tools/perf/tests/mmap-thread-lookup.c b/tools/perf/tests/mmap-thread-lookup.c
> index dca8bbfe780a7..65c72ed896ac2 100644
> --- a/tools/perf/tests/mmap-thread-lookup.c
> +++ b/tools/perf/tests/mmap-thread-lookup.c
[ ... ]
> @@ -211,6 +213,40 @@ static int mmap_events(synth_cb synth)
>  
>  		pr_debug("map %p, addr %" PRIx64 "\n", al.map, map__start(al.map));
>  
> +		/* Verify lookup by build ID and offset */
> +		{
> +			struct dso *dso = dso__get(map__dso(al.map));
> +
> +			if (dso) {
> +				const struct build_id *bid = dso__bid(dso);
> +
> +				if (bid && bid->size > 0) {
> +					struct addr_location al2;
> +					struct perf_build_id pbid = { .size = bid->size };
> +					u64 offset = map__dso_map_ip(al.map,
> +								     (unsigned long)(td->map + 1));
> +
> +					memcpy(pbid.data, bid->data, bid->size);

[Severity: Low]
Does this code need to explicitly include <string.h>?

Without the explicit include, calling memcpy() causes compilation failures on
systems using musl libc.

> +					addr_location__init(&al2);
> +					thread__find_map(thread, &(struct perf_sample){

[Severity: Medium]
Can this use-after-free the thread reference handle?

Looking at mmap_events(), thread__put(thread) is called right after the first
thread__find_map() call.

This means the newly added test code dereferences the freed thread pointer
here. Under REFCNT_CHECKING (ASAN), this invalidates the handle and poisons
the memory.

> +								.cpumode = PERF_RECORD_MISC_USER,
> +								.ip = 0,
> +								.bid = {
> +									.bid = &pbid,
> +									.offset = offset,
> +								},
> +							 }, &al2);
> +
> +					if (al2.map != al.map) {

[Severity: Medium]
Will this raw pointer comparison of reference-counted struct map handles cause
spurious test failures?

When perf is compiled with REFCNT_CHECKING, map__get() creates a newly
allocated wrapper struct for each reference, meaning two handles to the same
underlying map will have different pointer addresses.

Should this use RC_CHK_EQUAL(al2.map, al.map)?

> +						pr_debug("failed, couldn't find map by build id and offset\n");
> +						err = -1;
> +					}
> +					addr_location__exit(&al2);
> +				}
> +				dso__put(dso);
> +			}
> +		}
> +
>  		addr_location__exit(&al);
>  		if (err)
>  			break;

> diff --git a/tools/perf/tests/sample-parsing.c b/tools/perf/tests/sample-parsing.c
> index 20cab91ceaeb2..b49b6dcf10cdd 100644
> --- a/tools/perf/tests/sample-parsing.c
> +++ b/tools/perf/tests/sample-parsing.c
[ ... ]
> @@ -229,6 +229,36 @@ static int do_test(u64 sample_type, u64 sample_regs, u64 read_format)
>  	const u32 raw_data[] = {0x12345678, 0x0a0b0c0d, 0x11020304, 0x05060708, 0 };
>  	const u64 data[] = {0x2211443366558877ULL, 0, 0xaabbccddeeff4321ULL};
>  	const u64 aux_data[] = {0xa55a, 0, 0xeeddee, 0x0282028202820282};
> +	const struct perf_build_id bid = {
> +		.size = 20,
> +		.data = {
> +			'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
> +			'0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
> +		}
> +	};
> +	const struct perf_build_id callchain_bids[] = {

[Severity: Medium]
Will this result in a stack out-of-bounds read when synthesizing
PERF_SAMPLE_CALLCHAIN_BUILD_ID_OFFSET?

callchain_bids is declared as an array of 3 struct perf_build_id elements
(3 * 24 = 72 bytes).

However, perf_event__synthesize_sample() expects this array to contain
elements of size sizeof(struct perf_build_id) + sizeof(u64) (32 bytes).
It calculates the size as 96 bytes and calls memcpy(), reading past the end
of the stack array.

> +		{
> +			.size = 20,
> +			.data = {
> +				'9', '8', '7', '6', '5', '4', '3', '2', '1', '0',
> +				'9', '8', '7', '6', '5', '4', '3', '2', '1', '0',
> +			}
> +		},
[ ... ]
> @@ -277,6 +307,11 @@ static int do_test(u64 sample_type, u64 sample_regs, u64 read_format)
>  			.size	= sizeof(aux_data),
>  			.data	= (void *)aux_data,
>  		},
> +		.bid		= {
> +			.bid = (struct perf_build_id *)&bid,
> +			.offset = 0,
> +		},
> +		.callchain_bids = (struct perf_build_id *)callchain_bids,

[Severity: Medium]
Are the new PERF_SAMPLE_BUILD_ID_OFFSET fields actually being validated?

do_test() synthesizes events with bid and callchain_bids data here, but
the samples_same() validation function completely omits the COMP() checks
for these new flags.

Does this mean the parsing is never actually verified?

>  	};
>  	struct sample_read_value values[] = {{1, 5, 0}, {9, 3, 0}, {2, 7, 0}, {6, 4, 1},};
>  	struct perf_sample sample_out, sample_out_endian;

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260807071818.718751-1-irogers@google.com?part=8

  reply	other threads:[~2026-08-07  9:58 UTC|newest]

Thread overview: 18+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-08-07  7:18 [RFC PATCH v1 0/8] perf/core, perf/tools: Add PERF_SAMPLE_BUILD_ID_OFFSET support Ian Rogers
2026-08-07  7:18 ` [RFC PATCH v1 1/8] perf event: Factor build_id out into its own top-level struct Ian Rogers
2026-08-07  7:33   ` sashiko-bot
2026-08-07  7:18 ` [RFC PATCH v1 2/8] perf/core: Add BUILD_ID_OFFSET to UAPI Ian Rogers
2026-08-07  7:42   ` sashiko-bot
2026-08-07  7:18 ` [RFC PATCH v1 3/8] perf/core: Implement BUILD_ID_OFFSET sample type Ian Rogers
2026-08-07  7:54   ` sashiko-bot
2026-08-07  7:18 ` [RFC PATCH v1 4/8] perf: Refactor thread map and symbol APIs to take perf_sample Ian Rogers
2026-08-07  8:20   ` sashiko-bot
2026-08-07  7:18 ` [RFC PATCH v1 5/8] perf tools: Internal support for BUILD_ID_OFFSET Ian Rogers
2026-08-07  8:41   ` sashiko-bot
2026-08-07  7:18 ` [RFC PATCH v1 6/8] perf inject: Extend perf inject to support bid_offset conversion Ian Rogers
2026-08-07  9:18   ` sashiko-bot
2026-08-07  7:18 ` [RFC PATCH v1 7/8] perf record: Add --buildid-offset option Ian Rogers
2026-08-07  9:47   ` sashiko-bot
2026-08-07  7:18 ` [RFC PATCH v1 8/8] perf tests: Add build_id_offset test coverage Ian Rogers
2026-08-07  9:58   ` sashiko-bot [this message]
2026-08-07 11:18 ` [RFC PATCH v1 0/8] perf/core, perf/tools: Add PERF_SAMPLE_BUILD_ID_OFFSET support Peter Zijlstra

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20260807095836.572991F000E9@smtp.kernel.org \
    --to=sashiko-bot@kernel.org \
    --cc=bpf@vger.kernel.org \
    --cc=irogers@google.com \
    --cc=linux-perf-users@vger.kernel.org \
    --cc=sashiko-reviews@lists.linux.dev \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox