mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
From: Ian Rogers <irogers@google.com>
To: irogers@google.com, acme@kernel.org, adrian.hunter@intel.com,
	 mingo@redhat.com, namhyung@kernel.org, peterz@infradead.org
Cc: ak@linux.intel.com, alexander.shishkin@linux.intel.com,
	 atrajeev@linux.ibm.com, dvyukov@google.com, fzczx123@gmail.com,
	 james.clark@linaro.org, jolsa@kernel.org, kjain@linux.ibm.com,
	 krzysztof.m.lopatowski@gmail.com, leo.yan@arm.com,
	lihuafei1@huawei.com,  linux-kernel@vger.kernel.org,
	linux-perf-users@vger.kernel.org,  linux@treblig.org,
	m.liska@foxlink.cz, mark.rutland@arm.com,  martin.liska@hey.com,
	mpetlan@redhat.com, quic_zhonhan@quicinc.com,
	 scclevenger@os.amperecomputing.com, sesse@google.com,
	 stephen.s.brennan@oracle.com, thomas.falcon@intel.com,
	 yangyicong@hisilicon.com
Subject: [PATCH v2 2/8] perf/core: Add BUILD_ID_OFFSET to UAPI
Date: Fri,  2 Oct 2026 10:38:35 -0700	[thread overview]
Message-ID: <20261002173848.3228217-3-irogers@google.com> (raw)
In-Reply-To: <20261002173848.3228217-1-irogers@google.com>

Introduce PERF_SAMPLE_BUILD_ID_OFFSET and
PERF_SAMPLE_CALLCHAIN_BUILD_ID_OFFSET

Signed-off-by: Ian Rogers <irogers@google.com>
---
 include/uapi/linux/perf_event.h       | 34 +++++++++++++++++++++++----
 tools/include/uapi/linux/perf_event.h | 34 +++++++++++++++++++++++----
 tools/lib/perf/include/perf/event.h   | 33 +++++++++++++++++++++++++-
 tools/perf/util/session.c             | 34 ++++++++++++++++++++++++++-
 4 files changed, 125 insertions(+), 10 deletions(-)

diff --git a/include/uapi/linux/perf_event.h b/include/uapi/linux/perf_event.h
index 035b4b416ce3..4157aa8a243a 100644
--- a/include/uapi/linux/perf_event.h
+++ b/include/uapi/linux/perf_event.h
@@ -165,8 +165,10 @@ enum perf_event_sample_format {
 	PERF_SAMPLE_DATA_PAGE_SIZE		= 1U << 22,
 	PERF_SAMPLE_CODE_PAGE_SIZE		= 1U << 23,
 	PERF_SAMPLE_WEIGHT_STRUCT		= 1U << 24,
+	PERF_SAMPLE_BUILD_ID_OFFSET		= 1U << 25,
+	PERF_SAMPLE_CALLCHAIN_BUILD_ID_OFFSET	= 1U << 26,
 
-	PERF_SAMPLE_MAX = 1U << 25,		/* non-ABI */
+	PERF_SAMPLE_MAX = 1U << 27,		/* non-ABI */
 };
 
 #define PERF_SAMPLE_WEIGHT_TYPE	(PERF_SAMPLE_WEIGHT | PERF_SAMPLE_WEIGHT_STRUCT)
@@ -815,7 +817,8 @@ struct perf_event_mmap_page {
  *
  *   PERF_RECORD_MISC_EXACT_IP           - PERF_RECORD_SAMPLE of precise events
  *   PERF_RECORD_MISC_SWITCH_OUT_PREEMPT - PERF_RECORD_SWITCH* events
- *   PERF_RECORD_MISC_MMAP_BUILD_ID      - PERF_RECORD_MMAP2 event
+ *   PERF_RECORD_MISC_MMAP_BUILD_ID      - PERF_RECORD_MMAP2 and
+ *                                         PERF_RECORD_CALLCHAIN_DEFERRED events
  *
  *
  * PERF_RECORD_MISC_EXACT_IP:
@@ -827,7 +830,7 @@ struct perf_event_mmap_page {
  *   Indicates that thread was preempted in TASK_RUNNING state.
  *
  * PERF_RECORD_MISC_MMAP_BUILD_ID:
- *   Indicates that mmap2 event carries build ID data.
+ *   Indicates that mmap2 or deferred callchain event carries build ID data.
  */
 #define PERF_RECORD_MISC_EXACT_IP		(1 << 14)
 #define PERF_RECORD_MISC_SWITCH_OUT_PREEMPT	(1 << 14)
@@ -1054,6 +1057,23 @@ enum perf_event_type {
 	 *	{ u64			code_page_size;} && PERF_SAMPLE_CODE_PAGE_SIZE
 	 *	{ u64			size;
 	 *	  char			data[size]; } && PERF_SAMPLE_AUX
+	 *	{ union {
+	 *		struct {
+	 *			struct perf_build_id	bid;
+	 *			u64			offset;
+	 *		};
+	 *		struct {
+	 *			u64			zero;
+	 *			u64			context;
+	 *			u64			cookie;
+	 *			u64			ip;
+	 *		}; && attr.defer_callchain
+	 *	  }; } && PERF_SAMPLE_BUILD_ID_OFFSET
+	 *	{ u64			nr;
+	 *	  struct {
+	 *		struct perf_build_id	bid;
+	 *		u64			offset;
+	 *	  }[nr]; } && PERF_SAMPLE_CALLCHAIN_BUILD_ID_OFFSET
 	 * };
 	 */
 	PERF_RECORD_SAMPLE			= 9,
@@ -1260,7 +1280,13 @@ enum perf_event_type {
 	 *	struct perf_event_header	header;
 	 *	u64				cookie;
 	 *	u64				nr;
-	 *	u64				ips[nr];
+	 *	union {
+	 *		u64			ips[nr];
+	 *		struct {
+	 *			struct perf_build_id bid;
+	 *			u64		offset;
+	 *		}[nr]; && (header.misc & PERF_RECORD_MISC_MMAP_BUILD_ID)
+	 *	};
 	 *	struct sample_id		sample_id;
 	 * };
 	 */
diff --git a/tools/include/uapi/linux/perf_event.h b/tools/include/uapi/linux/perf_event.h
index 63f8866479a3..56b0cd504a3d 100644
--- a/tools/include/uapi/linux/perf_event.h
+++ b/tools/include/uapi/linux/perf_event.h
@@ -165,8 +165,10 @@ enum perf_event_sample_format {
 	PERF_SAMPLE_DATA_PAGE_SIZE		= 1U << 22,
 	PERF_SAMPLE_CODE_PAGE_SIZE		= 1U << 23,
 	PERF_SAMPLE_WEIGHT_STRUCT		= 1U << 24,
+	PERF_SAMPLE_BUILD_ID_OFFSET		= 1U << 25,
+	PERF_SAMPLE_CALLCHAIN_BUILD_ID_OFFSET	= 1U << 26,
 
-	PERF_SAMPLE_MAX = 1U << 25,		/* non-ABI */
+	PERF_SAMPLE_MAX = 1U << 27,		/* non-ABI */
 };
 
 #define PERF_SAMPLE_WEIGHT_TYPE	(PERF_SAMPLE_WEIGHT | PERF_SAMPLE_WEIGHT_STRUCT)
@@ -840,7 +842,8 @@ struct perf_event_mmap_page {
  *
  *   PERF_RECORD_MISC_EXACT_IP           - PERF_RECORD_SAMPLE of precise events
  *   PERF_RECORD_MISC_SWITCH_OUT_PREEMPT - PERF_RECORD_SWITCH* events
- *   PERF_RECORD_MISC_MMAP_BUILD_ID      - PERF_RECORD_MMAP2 event
+ *   PERF_RECORD_MISC_MMAP_BUILD_ID      - PERF_RECORD_MMAP2 and
+ *                                         PERF_RECORD_CALLCHAIN_DEFERRED events
  *
  *
  * PERF_RECORD_MISC_EXACT_IP:
@@ -852,7 +855,7 @@ struct perf_event_mmap_page {
  *   Indicates that thread was preempted in TASK_RUNNING state.
  *
  * PERF_RECORD_MISC_MMAP_BUILD_ID:
- *   Indicates that mmap2 event carries build ID data.
+ *   Indicates that mmap2 or deferred callchain event carries build ID data.
  */
 #define PERF_RECORD_MISC_EXACT_IP		(1 << 14)
 #define PERF_RECORD_MISC_SWITCH_OUT_PREEMPT	(1 << 14)
@@ -1095,6 +1098,23 @@ enum perf_event_type {
 	 *	{ u64			code_page_size;} && PERF_SAMPLE_CODE_PAGE_SIZE
 	 *	{ u64			size;
 	 *	  char			data[size]; } && PERF_SAMPLE_AUX
+	 *	{ union {
+	 *		struct {
+	 *			struct perf_build_id	bid;
+	 *			u64			offset;
+	 *		};
+	 *		struct {
+	 *			u64			zero;
+	 *			u64			context;
+	 *			u64			cookie;
+	 *			u64			ip;
+	 *		}; && attr.defer_callchain
+	 *	  }; } && PERF_SAMPLE_BUILD_ID_OFFSET
+	 *	{ u64			nr;
+	 *	  struct {
+	 *		struct perf_build_id	bid;
+	 *		u64			offset;
+	 *	  }[nr]; } && PERF_SAMPLE_CALLCHAIN_BUILD_ID_OFFSET
 	 * };
 	 */
 	PERF_RECORD_SAMPLE			= 9,
@@ -1301,7 +1321,13 @@ enum perf_event_type {
 	 *	struct perf_event_header	header;
 	 *	u64				cookie;
 	 *	u64				nr;
-	 *	u64				ips[nr];
+	 *	union {
+	 *		u64			ips[nr];
+	 *		struct {
+	 *			struct perf_build_id bid;
+	 *			u64		offset;
+	 *		}[nr]; && (header.misc & PERF_RECORD_MISC_MMAP_BUILD_ID)
+	 *	};
 	 *	struct sample_id		sample_id;
 	 * };
 	 */
diff --git a/tools/lib/perf/include/perf/event.h b/tools/lib/perf/include/perf/event.h
index 173eab43c148..3d35a82cccb0 100644
--- a/tools/lib/perf/include/perf/event.h
+++ b/tools/lib/perf/include/perf/event.h
@@ -3,11 +3,24 @@
 #define __LIBPERF_EVENT_H
 
 #include <linux/perf_event.h>
+#include <linux/stddef.h>
 #include <linux/types.h>
 #include <linux/limits.h>
 #include <linux/bpf.h>
 #include <sys/types.h> /* pid_t */
 
+#ifndef __DECLARE_FLEX_ARRAY
+#ifdef __cplusplus
+#define __DECLARE_FLEX_ARRAY(T, member)	T member[0]
+#else
+#define __DECLARE_FLEX_ARRAY(TYPE, NAME)	\
+	struct { \
+		struct { } __empty_ ## NAME; \
+		TYPE NAME[]; \
+	}
+#endif
+#endif
+
 /*
  * Verify the full field fits within the event, not just its start offset.
  * Only valid for fixed-size scalar fields — for trailing arrays like
@@ -162,6 +175,21 @@ struct perf_record_switch {
 	__u32			 next_prev_tid;
 };
 
+struct perf_sample_build_id_offset {
+	union {
+		struct perf_build_id	bid;
+		struct {
+			__u64		zero;
+			__u64		context;
+			__u64		cookie;
+		};
+	};
+	union {
+		__u64			offset;
+		__u64			ip;
+	};
+};
+
 struct perf_record_callchain_deferred {
 	struct perf_event_header header;
 	/*
@@ -171,7 +199,10 @@ struct perf_record_callchain_deferred {
 	 */
 	__u64			 cookie;
 	__u64			 nr;
-	__u64			 ips[];
+	union {
+		__DECLARE_FLEX_ARRAY(__u64, ips);
+		__DECLARE_FLEX_ARRAY(struct perf_sample_build_id_offset, bids);
+	};
 };
 
 struct perf_record_header_attr {
diff --git a/tools/perf/util/session.c b/tools/perf/util/session.c
index 7fea9e72726c..5e113070b3c6 100644
--- a/tools/perf/util/session.c
+++ b/tools/perf/util/session.c
@@ -1186,6 +1186,38 @@ static int perf_event__header_feature_swap(union perf_event *event,
 	return 0;
 }
 
+static int perf_event__callchain_deferred_swap(union perf_event *event,
+					       bool sample_id_all)
+{
+	u64 nr, max_nr;
+
+	if (!(event->header.misc & PERF_RECORD_MISC_MMAP_BUILD_ID))
+		return perf_event__all64_swap(event, sample_id_all);
+
+	if (event->header.size < sizeof(event->callchain_deferred))
+		return -1;
+
+	event->callchain_deferred.cookie = bswap_64(event->callchain_deferred.cookie);
+	event->callchain_deferred.nr = bswap_64(event->callchain_deferred.nr);
+
+	nr = event->callchain_deferred.nr;
+	max_nr = (event->header.size - sizeof(event->callchain_deferred)) /
+		 sizeof(event->callchain_deferred.bids[0]);
+	if (nr > max_nr)
+		return -1;
+
+	for (u64 i = 0; i < nr; i++) {
+		struct perf_sample_build_id_offset *bid =
+			&event->callchain_deferred.bids[i];
+
+		bid->offset = bswap_64(bid->offset);
+	}
+
+	if (sample_id_all)
+		swap_sample_id_all(event, &event->callchain_deferred.bids[nr]);
+	return 0;
+}
+
 typedef int (*perf_event__swap_op)(union perf_event *event,
 				   bool sample_id_all);
 
@@ -1211,7 +1243,7 @@ static perf_event__swap_op perf_event__swap_ops[] = {
 	[PERF_RECORD_BPF_EVENT]		  = perf_event__bpf_event_swap,
 	[PERF_RECORD_TEXT_POKE]		  = perf_event__text_poke_swap,
 	[PERF_RECORD_AUX_OUTPUT_HW_ID]	  = perf_event__all64_swap,
-	[PERF_RECORD_CALLCHAIN_DEFERRED]  = perf_event__all64_swap,
+	[PERF_RECORD_CALLCHAIN_DEFERRED]  = perf_event__callchain_deferred_swap,
 	[PERF_RECORD_HEADER_ATTR]	  = perf_event__hdr_attr_swap,
 	[PERF_RECORD_HEADER_EVENT_TYPE]	  = perf_event__event_type_swap,
 	[PERF_RECORD_HEADER_TRACING_DATA] = perf_event__tracing_data_swap,
-- 
2.56.0.rc1.315.gc6ed9934b7-goog


  parent reply	other threads:[~2026-10-02 17:39 UTC|newest]

Thread overview: 19+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2025-04-24  6:19 [PATCH v1 0/5] perf: Default use of build IDs and improvements Ian Rogers
2025-04-24  6:19 ` [PATCH v1 1/5] perf build-id: Reduce size of "size" variable Ian Rogers
2025-04-24  6:19 ` [PATCH v1 2/5] perf build-id: Truncate to avoid overflowing the build_id data Ian Rogers
2025-04-24  6:19 ` [PATCH v1 3/5] perf build-id: Change sprintf functions to snprintf Ian Rogers
2025-04-24  6:19 ` [PATCH v1 4/5] perf dso: Move build_id to dso_id Ian Rogers
2025-04-24  6:19 ` [PATCH v1 5/5] perf record: Make --buildid-mmap the default Ian Rogers
2025-04-24  7:20   ` Ian Rogers
2025-04-25 14:45     ` Arnaldo Carvalho de Melo
2025-04-25 14:59       ` Arnaldo Carvalho de Melo
2025-04-25 16:03       ` Ian Rogers
2026-10-02 17:38 ` [PATCH v2 0/8] perf/core, perf/tools: Add PERF_SAMPLE_BUILD_ID_OFFSET support Ian Rogers
2026-10-02 17:38   ` [PATCH v2 1/8] perf event: Factor build_id out into its own top-level struct Ian Rogers
2026-10-02 17:38   ` Ian Rogers [this message]
2026-10-02 17:38   ` [PATCH v2 3/8] perf/core: Implement BUILD_ID_OFFSET sample type Ian Rogers
2026-10-02 17:38   ` [PATCH v2 4/8] perf: Refactor thread map and symbol APIs to take perf_sample Ian Rogers
2026-10-02 17:38   ` [PATCH v2 5/8] perf tools: Internal support for BUILD_ID_OFFSET Ian Rogers
2026-10-02 17:38   ` [PATCH v2 6/8] perf inject: Extend perf inject to support bid_offset conversion Ian Rogers
2026-10-02 17:38   ` [PATCH v2 7/8] perf record: Add --buildid-offset option Ian Rogers
2026-10-02 17:38   ` [PATCH v2 8/8] perf tests: Add build_id_offset test coverage Ian Rogers

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=20261002173848.3228217-3-irogers@google.com \
    --to=irogers@google.com \
    --cc=acme@kernel.org \
    --cc=adrian.hunter@intel.com \
    --cc=ak@linux.intel.com \
    --cc=alexander.shishkin@linux.intel.com \
    --cc=atrajeev@linux.ibm.com \
    --cc=dvyukov@google.com \
    --cc=fzczx123@gmail.com \
    --cc=james.clark@linaro.org \
    --cc=jolsa@kernel.org \
    --cc=kjain@linux.ibm.com \
    --cc=krzysztof.m.lopatowski@gmail.com \
    --cc=leo.yan@arm.com \
    --cc=lihuafei1@huawei.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-perf-users@vger.kernel.org \
    --cc=linux@treblig.org \
    --cc=m.liska@foxlink.cz \
    --cc=mark.rutland@arm.com \
    --cc=martin.liska@hey.com \
    --cc=mingo@redhat.com \
    --cc=mpetlan@redhat.com \
    --cc=namhyung@kernel.org \
    --cc=peterz@infradead.org \
    --cc=quic_zhonhan@quicinc.com \
    --cc=scclevenger@os.amperecomputing.com \
    --cc=sesse@google.com \
    --cc=stephen.s.brennan@oracle.com \
    --cc=thomas.falcon@intel.com \
    --cc=yangyicong@hisilicon.com \
    /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

all inboxes | Powered by JetHome®