All of lore.kernel.org
 help / color / mirror / Atom feed
From: Dapeng Mi <dapeng1.mi@linux.intel.com>
To: Peter Zijlstra <peterz@infradead.org>,
	Ingo Molnar <mingo@redhat.com>,
	Arnaldo Carvalho de Melo <acme@kernel.org>,
	Namhyung Kim <namhyung@kernel.org>,
	Ian Rogers <irogers@google.com>,
	Adrian Hunter <adrian.hunter@intel.com>,
	Alexander Shishkin <alexander.shishkin@linux.intel.com>
Cc: linux-perf-users@vger.kernel.org, linux-kernel@vger.kernel.org,
	Zide Chen <zide.chen@intel.com>,
	Falcon Thomas <thomas.falcon@intel.com>,
	Dapeng Mi <dapeng1.mi@intel.com>,
	Xudong Hao <xudong.hao@intel.com>,
	Dapeng Mi <dapeng1.mi@linux.intel.com>
Subject: [Patch v9 08/10] perf dwarf-regs: Add SIMD/eGPRs support for x86 DWARF registers
Date: Mon,  6 Jul 2026 10:34:42 +0800	[thread overview]
Message-ID: <20260706023444.3067660-9-dapeng1.mi@linux.intel.com> (raw)
In-Reply-To: <20260706023444.3067660-1-dapeng1.mi@linux.intel.com>

Enhance the x86-specific DWARF register handling by adding support for
SIMD and eGPRs registers.

This update is based on the "DWARF Register Number Mapping" table from
the "System V Application Binary Interface AMD64 Architecture Processor
Supplement" (version 1.0).

Modifications include:
- Updating the x86_64_regidx_table[] array to incorporate SIMD and eGPRs
  registers.
- Enhancing the __get_dwarf_regnum_for_perf_regnum_x86_64() function to
  retrieve the DWARF register index for eGPRs.

Since currently libdw doesn't support SIMD and APX eGPRs registers yet,
still keep the original return value for get_libdw_frame_nregs() helper.

Signed-off-by: Dapeng Mi <dapeng1.mi@linux.intel.com>
---
 .../util/dwarf-regs-arch/dwarf-regs-x86.c     | 138 +++++++++++++++---
 tools/perf/util/dwarf-regs.c                  |   9 +-
 tools/perf/util/include/dwarf-regs.h          |   7 +-
 tools/perf/util/unwind-libdw.c                |   6 +-
 4 files changed, 132 insertions(+), 28 deletions(-)

diff --git a/tools/perf/util/dwarf-regs-arch/dwarf-regs-x86.c b/tools/perf/util/dwarf-regs-arch/dwarf-regs-x86.c
index c2a70e03b1a9..bb17d779036a 100644
--- a/tools/perf/util/dwarf-regs-arch/dwarf-regs-x86.c
+++ b/tools/perf/util/dwarf-regs-arch/dwarf-regs-x86.c
@@ -90,22 +90,22 @@ static const struct dwarf_regs_idx x86_64_regidx_table[] = {
 	{ "r14", 14 }, { "r14d", 14 }, { "r14w", 14 }, { "r14b", 14 },
 	{ "r15", 15 }, { "r15d", 15 }, { "r15w", 15 }, { "r15b", 15 },
 	// 16 - Return Address RA
-	{ "xmm0", 17},
-	{ "xmm1", 18},
-	{ "xmm2", 19},
-	{ "xmm3", 20},
-	{ "xmm4", 21},
-	{ "xmm5", 22},
-	{ "xmm6", 23},
-	{ "xmm7", 24},
-	{ "xmm8", 25},
-	{ "xmm9", 26},
-	{ "xmm10", 27},
-	{ "xmm11", 28},
-	{ "xmm12", 29},
-	{ "xmm13", 30},
-	{ "xmm14", 31},
-	{ "xmm15", 32},
+	{ "zmm0", 17 }, { "ymm0", 17 }, { "xmm0", 17 },
+	{ "zmm1", 18 }, { "ymm1", 18 }, { "xmm1", 18 },
+	{ "zmm2", 19 }, { "ymm2", 19 }, { "xmm2", 19 },
+	{ "zmm3", 20 }, { "ymm3", 20 }, { "xmm3", 20 },
+	{ "zmm4", 21 }, { "ymm4", 21 }, { "xmm4", 21 },
+	{ "zmm5", 22 }, { "ymm5", 22 }, { "xmm5", 22 },
+	{ "zmm6", 23 }, { "ymm6", 23 }, { "xmm6", 23 },
+	{ "zmm7", 24 }, { "ymm7", 24 }, { "xmm7", 24 },
+	{ "zmm8", 25 }, { "ymm8", 25 }, { "xmm8", 25 },
+	{ "zmm9", 26 }, { "ymm9", 26 }, { "xmm9", 26 },
+	{ "zmm10", 27 }, { "ymm10", 27 }, { "xmm10", 27 },
+	{ "zmm11", 28 }, { "ymm11", 28 }, { "xmm11", 28 },
+	{ "zmm12", 29 }, { "ymm12", 29 }, { "xmm12", 29 },
+	{ "zmm13", 30 }, { "ymm13", 30 }, { "xmm13", 30 },
+	{ "zmm14", 31 }, { "ymm14", 31 }, { "xmm14", 31 },
+	{ "zmm15", 32 }, { "ymm15", 32 }, { "xmm15", 32 },
 	{ "st0", 33},
 	{ "st1", 34},
 	{ "st2", 35},
@@ -129,7 +129,7 @@ static const struct dwarf_regs_idx x86_64_regidx_table[] = {
 	{ "ds", 53},
 	{ "fs", 54},
 	{ "gs", 55},
-	// 56-47 - reserved
+	// 56-57 - reserved
 	{ "fs.base", 58},
 	{ "gs.base", 59},
 	// 60-61 - reserved
@@ -138,6 +138,49 @@ static const struct dwarf_regs_idx x86_64_regidx_table[] = {
 	{ "mxcsr", 64}, // 128-bit Media Control and Status
 	{ "fcw", 65}, // x87 Control Word
 	{ "fsw", 66}, // x87 Status Word
+	// 67-82 - Upper Vector Registers 16–31
+	{ "zmm16", 67 }, { "ymm16", 67 }, { "xmm16", 67 },
+	{ "zmm17", 68 }, { "ymm17", 68 }, { "xmm17", 68 },
+	{ "zmm18", 69 }, { "ymm18", 69 }, { "xmm18", 69 },
+	{ "zmm19", 70 }, { "ymm19", 70 }, { "xmm19", 70 },
+	{ "zmm20", 71 }, { "ymm20", 71 }, { "xmm20", 71 },
+	{ "zmm21", 72 }, { "ymm21", 72 }, { "xmm21", 72 },
+	{ "zmm22", 73 }, { "ymm22", 73 }, { "xmm22", 73 },
+	{ "zmm23", 74 }, { "ymm23", 74 }, { "xmm23", 74 },
+	{ "zmm24", 75 }, { "ymm24", 75 }, { "xmm24", 75 },
+	{ "zmm25", 76 }, { "ymm25", 76 }, { "xmm25", 76 },
+	{ "zmm26", 77 }, { "ymm26", 77 }, { "xmm26", 77 },
+	{ "zmm27", 78 }, { "ymm27", 78 }, { "xmm27", 78 },
+	{ "zmm28", 79 }, { "ymm28", 79 }, { "xmm28", 79 },
+	{ "zmm29", 80 }, { "ymm29", 80 }, { "xmm29", 80 },
+	{ "zmm30", 81 }, { "ymm30", 81 }, { "xmm30", 81 },
+	{ "zmm31", 82 }, { "ymm31", 82 }, { "xmm31", 82 },
+	// 118-125 - Vector Mask Registers 0–7
+	{ "k0", 118 },
+	{ "k1", 119 },
+	{ "k2", 120 },
+	{ "k3", 121 },
+	{ "k4", 122 },
+	{ "k5", 123 },
+	{ "k6", 124 },
+	{ "k7", 125 },
+	// 130-145 - APX Integer Registers 16-31
+	{ "r16", 130 }, { "r16d", 130 }, { "r16w", 130 }, { "r16b", 130 },
+	{ "r17", 131 }, { "r17d", 131 }, { "r17w", 131 }, { "r17b", 131 },
+	{ "r18", 132 }, { "r18d", 132 }, { "r18w", 132 }, { "r18b", 132 },
+	{ "r19", 133 }, { "r19d", 133 }, { "r19w", 133 }, { "r19b", 133 },
+	{ "r20", 134 }, { "r20d", 134 }, { "r20w", 134 }, { "r20b", 134 },
+	{ "r21", 135 }, { "r21d", 135 }, { "r21w", 135 }, { "r21b", 135 },
+	{ "r22", 136 }, { "r22d", 136 }, { "r22w", 136 }, { "r22b", 136 },
+	{ "r23", 137 }, { "r23d", 137 }, { "r23w", 137 }, { "r23b", 137 },
+	{ "r24", 138 }, { "r24d", 138 }, { "r24w", 138 }, { "r24b", 138 },
+	{ "r25", 139 }, { "r25d", 139 }, { "r25w", 139 }, { "r25b", 139 },
+	{ "r26", 140 }, { "r26d", 140 }, { "r26w", 140 }, { "r26b", 140 },
+	{ "r27", 141 }, { "r27d", 141 }, { "r27w", 141 }, { "r27b", 141 },
+	{ "r28", 142 }, { "r28d", 142 }, { "r28w", 142 }, { "r28b", 142 },
+	{ "r29", 143 }, { "r29d", 143 }, { "r29w", 143 }, { "r29b", 143 },
+	{ "r30", 144 }, { "r30d", 144 }, { "r30w", 144 }, { "r30b", 144 },
+	{ "r31", 145 }, { "r31d", 145 }, { "r31w", 145 }, { "r31b", 145 },
 	// End of regular dwarf registers.
 	{ "rip", DWARF_REG_PC }, { "eip", DWARF_REG_PC }, { "ip", DWARF_REG_PC },
 };
@@ -204,7 +247,7 @@ int __get_dwarf_regnum_for_perf_regnum_i386(int perf_regnum)
 	return dwarf_i386_regnums[perf_regnum];
 }
 
-int __get_dwarf_regnum_for_perf_regnum_x86_64(int perf_regnum)
+int __get_dwarf_regnum_for_perf_regnum_x86_64(int perf_regnum, int abi)
 {
 	static const int dwarf_x86_64_regnums[] = {
 		[PERF_REG_X86_AX] = 0,
@@ -248,13 +291,66 @@ int __get_dwarf_regnum_for_perf_regnum_x86_64(int perf_regnum)
 		[PERF_REG_X86_XMM14] = 31,
 		[PERF_REG_X86_XMM15] = 32,
 	};
+	static const int dwarf_x86_64_regnums_apx[] = {
+		[PERF_REG_X86_AX] = 0,
+		[PERF_REG_X86_BX] = 3,
+		[PERF_REG_X86_CX] = 2,
+		[PERF_REG_X86_DX] = 1,
+		[PERF_REG_X86_SI] = 4,
+		[PERF_REG_X86_DI] = 5,
+		[PERF_REG_X86_BP] = 6,
+		[PERF_REG_X86_SP] = 7,
+		[PERF_REG_X86_IP] = 16,
+		[PERF_REG_X86_FLAGS] = 49,
+		[PERF_REG_X86_CS] = 51,
+		[PERF_REG_X86_SS] = 52,
+		[PERF_REG_X86_DS] = 53,
+		[PERF_REG_X86_ES] = 50,
+		[PERF_REG_X86_FS] = 54,
+		[PERF_REG_X86_GS] = 55,
+		[PERF_REG_X86_R8] = 8,
+		[PERF_REG_X86_R9] = 9,
+		[PERF_REG_X86_R10] = 10,
+		[PERF_REG_X86_R11] = 11,
+		[PERF_REG_X86_R12] = 12,
+		[PERF_REG_X86_R13] = 13,
+		[PERF_REG_X86_R14] = 14,
+		[PERF_REG_X86_R15] = 15,
+		[PERF_REG_X86_R16] = 130,
+		[PERF_REG_X86_R17] = 131,
+		[PERF_REG_X86_R18] = 132,
+		[PERF_REG_X86_R19] = 133,
+		[PERF_REG_X86_R20] = 134,
+		[PERF_REG_X86_R21] = 135,
+		[PERF_REG_X86_R22] = 136,
+		[PERF_REG_X86_R23] = 137,
+		[PERF_REG_X86_R24] = 138,
+		[PERF_REG_X86_R25] = 139,
+		[PERF_REG_X86_R26] = 140,
+		[PERF_REG_X86_R27] = 141,
+		[PERF_REG_X86_R28] = 142,
+		[PERF_REG_X86_R29] = 143,
+		[PERF_REG_X86_R30] = 144,
+		[PERF_REG_X86_R31] = 145,
+	};
 
 	if (perf_regnum == 0)
 		return 0;
 
-	if (perf_regnum < 0 || perf_regnum >= (int)ARRAY_SIZE(dwarf_x86_64_regnums) ||
-	    dwarf_x86_64_regnums[perf_regnum] == 0)
+	if (perf_regnum < 0)
+		return -ENOENT;
+
+	if (!(abi & PERF_SAMPLE_REGS_ABI_SIMD) &&
+	    (perf_regnum >= (int)ARRAY_SIZE(dwarf_x86_64_regnums) ||
+	     dwarf_x86_64_regnums[perf_regnum] == 0))
+		return -ENOENT;
+
+	if ((abi & PERF_SAMPLE_REGS_ABI_SIMD) &&
+	    (perf_regnum >= (int)ARRAY_SIZE(dwarf_x86_64_regnums_apx) ||
+	     dwarf_x86_64_regnums_apx[perf_regnum] == 0))
 		return -ENOENT;
 
-	return dwarf_x86_64_regnums[perf_regnum];
+	return abi & PERF_SAMPLE_REGS_ABI_SIMD ?
+			dwarf_x86_64_regnums_apx[perf_regnum] :
+			dwarf_x86_64_regnums[perf_regnum];
 }
diff --git a/tools/perf/util/dwarf-regs.c b/tools/perf/util/dwarf-regs.c
index 797f455eba0d..67f38342247e 100644
--- a/tools/perf/util/dwarf-regs.c
+++ b/tools/perf/util/dwarf-regs.c
@@ -158,6 +158,10 @@ static int get_libdw_frame_nregs(unsigned int machine, unsigned int flags __mayb
 {
 	switch (machine) {
 	case EM_X86_64:
+		/*
+		 * Since libdw doesn't support SIMD and APX eGPR register yet,
+		 * still keep nregs to 17.
+		 */
 		return 17;
 	case EM_386:
 		return 9;
@@ -187,13 +191,14 @@ static int get_libdw_frame_nregs(unsigned int machine, unsigned int flags __mayb
 }
 
 int get_dwarf_regnum_for_perf_regnum(int perf_regnum, unsigned int machine,
-				     unsigned int flags, bool only_libdw_supported)
+				     unsigned int flags,
+				     bool only_libdw_supported, int abi)
 {
 	int reg;
 
 	switch (machine) {
 	case EM_X86_64:
-		reg = __get_dwarf_regnum_for_perf_regnum_x86_64(perf_regnum);
+		reg = __get_dwarf_regnum_for_perf_regnum_x86_64(perf_regnum, abi);
 		break;
 	case EM_386:
 		reg = __get_dwarf_regnum_for_perf_regnum_i386(perf_regnum);
diff --git a/tools/perf/util/include/dwarf-regs.h b/tools/perf/util/include/dwarf-regs.h
index 46a764cf322f..92cf0af93e9e 100644
--- a/tools/perf/util/include/dwarf-regs.h
+++ b/tools/perf/util/include/dwarf-regs.h
@@ -103,7 +103,7 @@ int __get_csky_regnum(const char *name, unsigned int flags);
 int __get_dwarf_regnum_i386(const char *name);
 int __get_dwarf_regnum_x86_64(const char *name);
 int __get_dwarf_regnum_for_perf_regnum_i386(int perf_regnum);
-int __get_dwarf_regnum_for_perf_regnum_x86_64(int perf_regnum);
+int __get_dwarf_regnum_for_perf_regnum_x86_64(int perf_regnum, int abi);
 
 int __get_dwarf_regnum_for_perf_regnum_arm(int perf_regnum);
 int __get_dwarf_regnum_for_perf_regnum_arm64(int perf_regnum);
@@ -125,8 +125,9 @@ int get_dwarf_regnum(const char *name, unsigned int machine, unsigned int flags)
 /*
  * get_dwarf_regnum - Returns DWARF regnum from perf register number.
  */
-int get_dwarf_regnum_for_perf_regnum(int perf_regnum, unsigned int machine, unsigned int flags,
-				     bool only_libdw_supported);
+int get_dwarf_regnum_for_perf_regnum(int perf_regnum, unsigned int machine,
+				     unsigned int flags,
+				     bool only_libdw_supported, int abi);
 
 void get_powerpc_regs(u32 raw_insn, int is_source, struct annotated_op_loc *op_loc);
 
diff --git a/tools/perf/util/unwind-libdw.c b/tools/perf/util/unwind-libdw.c
index 7f35042be567..13fd81af5b54 100644
--- a/tools/perf/util/unwind-libdw.c
+++ b/tools/perf/util/unwind-libdw.c
@@ -273,7 +273,8 @@ static bool libdw_set_initial_registers(Dwfl_Thread *thread, void *arg)
 			int dwarf_reg =
 				get_dwarf_regnum_for_perf_regnum(perf_reg, e_machine,
 								 e_flags,
-								 /*only_libdw_supported=*/true);
+								 /*only_libdw_supported=*/true,
+								 user_regs->abi);
 			if (dwarf_reg > max_dwarf_reg)
 				max_dwarf_reg = dwarf_reg;
 		}
@@ -288,7 +289,8 @@ static bool libdw_set_initial_registers(Dwfl_Thread *thread, void *arg)
 			int dwarf_reg =
 				get_dwarf_regnum_for_perf_regnum(perf_reg, e_machine,
 								 e_flags,
-								 /*only_libdw_supported=*/true);
+								 /*only_libdw_supported=*/true,
+								 user_regs->abi);
 			if (dwarf_reg >= 0) {
 				val = 0;
 				if (perf_reg_value(&val, user_regs, perf_reg) == 0)
-- 
2.34.1


  parent reply	other threads:[~2026-07-06  2:41 UTC|newest]

Thread overview: 19+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-07-06  2:34 [Patch v9 00/10] Perf tools: Support eGPRs/SSP/SIMD registers sampling Dapeng Mi
2026-07-06  2:34 ` [Patch v9 01/10] perf dwarf-regs: Fix DWARF register index bounds check Dapeng Mi
2026-07-06  2:34 ` [Patch v9 02/10] perf util: Add missed fields in _attr__fprintf() and __attr_swap() Dapeng Mi
2026-07-06  2:34 ` [Patch v9 03/10] tools headers: Sync x86 headers with kernel sources Dapeng Mi
2026-07-06  2:54   ` sashiko-bot
2026-07-08  2:05     ` Mi, Dapeng
2026-07-06  2:34 ` [Patch v9 04/10] perf headers: Sync perf_event.h/perf_regs.h with the kernel headers Dapeng Mi
2026-07-06  2:34 ` [Patch v9 05/10] perf regs: Support x86 eGPRs/SSP sampling Dapeng Mi
2026-07-06  2:59   ` sashiko-bot
2026-07-08  2:15     ` Mi, Dapeng
2026-07-06  2:34 ` [Patch v9 06/10] perf regs: Support x86 SIMD registers sampling Dapeng Mi
2026-07-06  2:34 ` [Patch v9 07/10] perf regs: Enable dumping of SIMD registers Dapeng Mi
2026-07-06  2:55   ` sashiko-bot
2026-07-08  2:21     ` Mi, Dapeng
2026-07-06  2:34 ` Dapeng Mi [this message]
2026-07-06  2:34 ` [Patch v9 09/10] perf tests: Add x86 eGPRs/SSP registers sampling test Dapeng Mi
2026-07-06  3:00   ` sashiko-bot
2026-07-08  2:30     ` Mi, Dapeng
2026-07-06  2:34 ` [Patch v9 10/10] perf tests: Add SIMD " Dapeng Mi

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=20260706023444.3067660-9-dapeng1.mi@linux.intel.com \
    --to=dapeng1.mi@linux.intel.com \
    --cc=acme@kernel.org \
    --cc=adrian.hunter@intel.com \
    --cc=alexander.shishkin@linux.intel.com \
    --cc=dapeng1.mi@intel.com \
    --cc=irogers@google.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-perf-users@vger.kernel.org \
    --cc=mingo@redhat.com \
    --cc=namhyung@kernel.org \
    --cc=peterz@infradead.org \
    --cc=thomas.falcon@intel.com \
    --cc=xudong.hao@intel.com \
    --cc=zide.chen@intel.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 an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.