From patchwork Fri Mar 14 16:21:31 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Li Huafei X-Patchwork-Id: 14016428 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from bombadil.infradead.org (bombadil.infradead.org [198.137.202.133]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id DFCF2C282EC for ; Fri, 14 Mar 2025 08:32:05 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20210309; h=Sender:List-Subscribe:List-Help :List-Post:List-Archive:List-Unsubscribe:List-Id:Content-Type: Content-Transfer-Encoding:MIME-Version:References:In-Reply-To:Message-ID:Date :Subject:CC:To:From:Reply-To:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Owner; bh=8fgl61DdgclIley/12cHvL6cz/HYGNHwE80JQr+byLU=; b=pnhNhqhwLtJjFZ2tO3yhD/FLrg 2GnLfiqXKgiiudRKJyDIwRAc0FAXTe7nC7Wpi3Eviu65eazhFAhgEmAUGXEiOmOuqug+q5HvyXzBp IXifzuFb65uguMaD0NeUSqea84LsekS6NAALmMHK7JUBiY2YZ1DvkAQsx4NQ8JQJIgaDs5HrIuGiu nz9SEMR234T8tRMYDYBAL6Ve7DllaoHBekz1V8oia7ziyGTJvi/OoHN9GdFMmypBKhBN9z8FcHYj+ dqsO4IBJLehe28LSMreITjLS1GB0g1EvXQyxT+PVpX/vC16sS1Ge9Q6TBFprCZSmlcHGyqkYzm5uT VCGZSSYA==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.98 #2 (Red Hat Linux)) id 1tt0SR-0000000DU6r-2tIL; Fri, 14 Mar 2025 08:31:55 +0000 Received: from szxga05-in.huawei.com ([45.249.212.191]) by bombadil.infradead.org with esmtps (Exim 4.98 #2 (Red Hat Linux)) id 1tt0Hd-0000000DQv3-1xKf for linux-arm-kernel@lists.infradead.org; Fri, 14 Mar 2025 08:20:47 +0000 Received: from mail.maildlp.com (unknown [172.19.88.234]) by szxga05-in.huawei.com (SkyGuard) with ESMTP id 4ZDchc4gCbz1R6Wc; Fri, 14 Mar 2025 16:18:56 +0800 (CST) Received: from kwepemf500004.china.huawei.com (unknown [7.202.181.242]) by mail.maildlp.com (Postfix) with ESMTPS id 995EC14022D; Fri, 14 Mar 2025 16:20:38 +0800 (CST) Received: from lihuafei.huawei.com (10.90.53.74) by kwepemf500004.china.huawei.com (7.202.181.242) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.11; Fri, 14 Mar 2025 16:20:37 +0800 From: Li Huafei To: , , , , , , , CC: , , , , , , , , , , , , , , Subject: [PATCH 1/7] perf annotate: Handle arm64 load and store instructions Date: Sat, 15 Mar 2025 00:21:31 +0800 Message-ID: <20250314162137.528204-2-lihuafei1@huawei.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20250314162137.528204-1-lihuafei1@huawei.com> References: <20250314162137.528204-1-lihuafei1@huawei.com> MIME-Version: 1.0 X-Originating-IP: [10.90.53.74] X-ClientProxiedBy: dggems706-chm.china.huawei.com (10.3.19.183) To kwepemf500004.china.huawei.com (7.202.181.242) X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20250314_012045_893545_94C74BD7 X-CRM114-Status: GOOD ( 15.35 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.34 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Add ldst_ops to handle load and store instructions in order to parse the data types and offsets associated with PMU events for memory access instructions. There are many variants of load and store instructions in ARM64, making it difficult to match all of these instruction names completely. Therefore, only the instruction prefixes are matched. The prefix 'ld|st' covers most of the memory access instructions, 'cas|swp' matches atomic instructions, and 'prf' matches memory prefetch instructions. Signed-off-by: Li Huafei --- tools/perf/arch/arm64/annotate/instructions.c | 67 ++++++++++++++++++- 1 file changed, 66 insertions(+), 1 deletion(-) diff --git a/tools/perf/arch/arm64/annotate/instructions.c b/tools/perf/arch/arm64/annotate/instructions.c index d465d093e7eb..c212eb7341bd 100644 --- a/tools/perf/arch/arm64/annotate/instructions.c +++ b/tools/perf/arch/arm64/annotate/instructions.c @@ -6,7 +6,8 @@ struct arm64_annotate { regex_t call_insn, - jump_insn; + jump_insn, + ldst_insn; /* load and store instruction */ }; static int arm64_mov__parse(struct arch *arch __maybe_unused, @@ -67,6 +68,57 @@ static struct ins_ops arm64_mov_ops = { .scnprintf = mov__scnprintf, }; +static int arm64_ldst__parse(struct arch *arch __maybe_unused, + struct ins_operands *ops, + struct map_symbol *ms __maybe_unused, + struct disasm_line *dl __maybe_unused) +{ + char *s, *target; + + /* + * The part starting from the memory access annotation '[' is parsed + * as 'target', while the part before it is parsed as 'source'. + */ + target = s = strchr(ops->raw, '['); + if (!s) + return -1; + + while (s > ops->raw && *s != ',') + --s; + + if (s == ops->raw) + return -1; + + *s = '\0'; + ops->source.raw = strdup(ops->raw); + + *s = ','; + if (!ops->source.raw) + return -1; + + ops->target.raw = strdup(target); + if (!ops->target.raw) { + zfree(ops->source.raw); + return -1; + } + ops->target.mem_ref = true; + + return 0; +} + +static int ldst__scnprintf(struct ins *ins, char *bf, size_t size, + struct ins_operands *ops, int max_ins_name) +{ + return scnprintf(bf, size, "%-*s %s,%s", max_ins_name, ins->name, + ops->source.name ?: ops->source.raw, + ops->target.name ?: ops->target.raw); +} + +static struct ins_ops arm64_ldst_ops = { + .parse = arm64_ldst__parse, + .scnprintf = ldst__scnprintf, +}; + static struct ins_ops *arm64__associate_instruction_ops(struct arch *arch, const char *name) { struct arm64_annotate *arm = arch->priv; @@ -77,6 +129,8 @@ static struct ins_ops *arm64__associate_instruction_ops(struct arch *arch, const ops = &jump_ops; else if (!regexec(&arm->call_insn, name, 2, match, 0)) ops = &call_ops; + else if (!regexec(&arm->ldst_insn, name, 2, match, 0)) + ops = &arm64_ldst_ops; else if (!strcmp(name, "ret")) ops = &ret_ops; else @@ -107,6 +161,15 @@ static int arm64__annotate_init(struct arch *arch, char *cpuid __maybe_unused) REG_EXTENDED); if (err) goto out_free_call; + /* + * The ARM64 architecture has many variants of load/store instructions. + * It is quite challenging to match all of them completely. Here, we + * only match the prefixes of these instructions. + */ + err = regcomp(&arm->ldst_insn, "^(ld|st|cas|prf|swp)", + REG_EXTENDED); + if (err) + goto out_free_jump; arch->initialized = true; arch->priv = arm; @@ -117,6 +180,8 @@ static int arm64__annotate_init(struct arch *arch, char *cpuid __maybe_unused) arch->e_flags = 0; return 0; +out_free_jump: + regfree(&arm->jump_insn); out_free_call: regfree(&arm->call_insn); out_free_arm: From patchwork Fri Mar 14 16:21:32 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Li Huafei X-Patchwork-Id: 14016425 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from bombadil.infradead.org (bombadil.infradead.org [198.137.202.133]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id CF44BC28B2F for ; Fri, 14 Mar 2025 08:28:42 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20210309; h=Sender:List-Subscribe:List-Help :List-Post:List-Archive:List-Unsubscribe:List-Id:Content-Type: Content-Transfer-Encoding:MIME-Version:References:In-Reply-To:Message-ID:Date :Subject:CC:To:From:Reply-To:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Owner; bh=g1/fd4D2fxZy8Mgd9AyxZx0+qOiqfX47sDLO5E40g8c=; b=3yEryaYsPTnFk5IMg5BVOlM1q8 42BOGUJ+pGuCrwmCQSo0vzm3SRUsa8Jj2xJnKjUWSKTx7xICkSJcmy8XZnC42a6aHHDck//cixn+3 ojJlW2RYxQjUPq0VZyZXJFz/q88tvxIxVAq9Z4RcdSPBInEs5xogwTLz9zu2GS57xEHG7WPEjrR+c nvog/T0kvgEBRnjKFk7/fDtMGDC9XI9jwCQtECe24CVJhghyR5HrlLcGoWTrzll6ZuisYN1FuxJ2a 5hRwNarDFKeUiBqHtkToDvA8SymvSW5ykGbMKWzunFlpy4JlY6GJJUQW0t5jIzKWkZ9fCrPHd9sI0 /WW8wh6Q==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.98 #2 (Red Hat Linux)) id 1tt0P9-0000000DStY-10Mh; Fri, 14 Mar 2025 08:28:31 +0000 Received: from desiato.infradead.org ([2001:8b0:10b:1:d65d:64ff:fe57:4e05]) by bombadil.infradead.org with esmtps (Exim 4.98 #2 (Red Hat Linux)) id 1tt0Hu-0000000DR8M-0y4V for linux-arm-kernel@bombadil.infradead.org; Fri, 14 Mar 2025 08:21:02 +0000 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=infradead.org; s=desiato.20200630; h=Content-Type:Content-Transfer-Encoding :MIME-Version:References:In-Reply-To:Message-ID:Date:Subject:CC:To:From: Sender:Reply-To:Content-ID:Content-Description; bh=g1/fd4D2fxZy8Mgd9AyxZx0+qOiqfX47sDLO5E40g8c=; b=Gq84Pt+da5krT+f0ObQl4tPDpw vhOhaIqktl0AexqRPDNNw5wm9qpTM5spLfQNzKwFRpkPKmgpFUCV9mFN3F7t/4QcZgA9FaJGWNV6K Fn1Bi7zO8Ax6qpkMOUzwFhlLHgFHEiQqWYZPPAQwzRz2j2/X72j8IXz0pwYrzcNliF5+sWP549Kok V634tjOdSv+EXuKU9Ofn4a1ECwA5IEOGVn1pQv+aduCzmoOg6M+lzMnOChAeNsN9eAErRyJ9j2MWH LvaxQ7AqfMy1E1GThxU2CVLLnA9hCcgo8qcdBSYE21Gi+kUAv7mKKwBBlLXUcNgPS+b3Jv+6kKvGX rEr0AAnQ==; Received: from szxga02-in.huawei.com ([45.249.212.188]) by desiato.infradead.org with esmtps (Exim 4.98 #2 (Red Hat Linux)) id 1tt0Hq-00000002rOA-2cCo for linux-arm-kernel@lists.infradead.org; Fri, 14 Mar 2025 08:21:01 +0000 Received: from mail.maildlp.com (unknown [172.19.163.48]) by szxga02-in.huawei.com (SkyGuard) with ESMTP id 4ZDcht3WbMztQfY; Fri, 14 Mar 2025 16:19:10 +0800 (CST) Received: from kwepemf500004.china.huawei.com (unknown [7.202.181.242]) by mail.maildlp.com (Postfix) with ESMTPS id 5ED0818006C; Fri, 14 Mar 2025 16:20:39 +0800 (CST) Received: from lihuafei.huawei.com (10.90.53.74) by kwepemf500004.china.huawei.com (7.202.181.242) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.11; Fri, 14 Mar 2025 16:20:38 +0800 From: Li Huafei To: , , , , , , , CC: , , , , , , , , , , , , , , Subject: [PATCH 2/7] perf annotate: Advance the mem_ref check to mov__parse() Date: Sat, 15 Mar 2025 00:21:32 +0800 Message-ID: <20250314162137.528204-3-lihuafei1@huawei.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20250314162137.528204-1-lihuafei1@huawei.com> References: <20250314162137.528204-1-lihuafei1@huawei.com> MIME-Version: 1.0 X-Originating-IP: [10.90.53.74] X-ClientProxiedBy: dggems706-chm.china.huawei.com (10.3.19.183) To kwepemf500004.china.huawei.com (7.202.181.242) X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20250314_082059_547347_25E4C840 X-CRM114-Status: GOOD ( 11.43 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.34 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Advance the mem_ref check on x86 to mov__parse(), along with the multi_reg check, to make annotate_get_insn_location() more concise. Signed-off-by: Li Huafei --- tools/perf/util/annotate.c | 9 ++++----- tools/perf/util/disasm.c | 8 ++++++++ 2 files changed, 12 insertions(+), 5 deletions(-) diff --git a/tools/perf/util/annotate.c b/tools/perf/util/annotate.c index 31bb326b07a6..860ea6c72411 100644 --- a/tools/perf/util/annotate.c +++ b/tools/perf/util/annotate.c @@ -2442,18 +2442,17 @@ int annotate_get_insn_location(struct arch *arch, struct disasm_line *dl, continue; } + op_loc->mem_ref = mem_ref; + op_loc->multi_regs = multi_regs; + /* * For powerpc, call get_powerpc_regs function which extracts the * required fields for op_loc, ie reg1, reg2, offset from the * raw instruction. */ if (arch__is(arch, "powerpc")) { - op_loc->mem_ref = mem_ref; - op_loc->multi_regs = multi_regs; get_powerpc_regs(dl->raw.raw_insn, !i, op_loc); - } else if (strchr(insn_str, arch->objdump.memory_ref_char)) { - op_loc->mem_ref = true; - op_loc->multi_regs = multi_regs; + } else if (mem_ref) { extract_reg_offset(arch, insn_str, op_loc); } else { char *s, *p = NULL; diff --git a/tools/perf/util/disasm.c b/tools/perf/util/disasm.c index 50c5c206b70e..d91526cff9df 100644 --- a/tools/perf/util/disasm.c +++ b/tools/perf/util/disasm.c @@ -607,6 +607,12 @@ static bool check_multi_regs(struct arch *arch, const char *op) return count > 1; } +/* Check whether the operand accesses memory. */ +static bool check_memory_ref(struct arch *arch, const char *op) +{ + return strchr(op, arch->objdump.memory_ref_char) != NULL; +} + static int mov__parse(struct arch *arch, struct ins_operands *ops, struct map_symbol *ms __maybe_unused, struct disasm_line *dl __maybe_unused) { @@ -635,6 +641,7 @@ static int mov__parse(struct arch *arch, struct ins_operands *ops, struct map_sy if (ops->source.raw == NULL) return -1; + ops->source.mem_ref = check_memory_ref(arch, ops->source.raw); ops->source.multi_regs = check_multi_regs(arch, ops->source.raw); target = skip_spaces(++s); @@ -657,6 +664,7 @@ static int mov__parse(struct arch *arch, struct ins_operands *ops, struct map_sy if (ops->target.raw == NULL) goto out_free_source; + ops->target.mem_ref = check_memory_ref(arch, ops->target.raw); ops->target.multi_regs = check_multi_regs(arch, ops->target.raw); if (comment == NULL) From patchwork Fri Mar 14 16:21:33 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Li Huafei X-Patchwork-Id: 14016426 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from bombadil.infradead.org (bombadil.infradead.org [198.137.202.133]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id EB9DAC282EC for ; Fri, 14 Mar 2025 08:30:27 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20210309; h=Sender:List-Subscribe:List-Help :List-Post:List-Archive:List-Unsubscribe:List-Id:Content-Type: Content-Transfer-Encoding:MIME-Version:References:In-Reply-To:Message-ID:Date :Subject:CC:To:From:Reply-To:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Owner; bh=ONe7scuOHzoCKcERzbzvp1reFKg9ltYcr2r9k7N1Vqo=; b=kWXFptsRfgoiBbguaAQnPaYNIQ BJ4rdxjWwM3V1at4EUfFpul3XKx+IpBLG7yW+D/HfhUZ1V5YxUcIAZUkZWKtMdcg2km+Ml+8Yf03q qiAc46b6dWecsD2/rvjJffcrRLglGzFNIWb40cKfzYV8ok4mtJdlxAYkXvQ+wu7/oZpLnzssg8yz2 4OGr/PSsB+wGiSx01RhBfprYvjCdIk57YUo13WyOWZgAUoU5lMh3WQPJO278P0Io9gmSZhfOL0YFd zUzKkaZxRWd5cgfqpzm/m3wAcyqMQ4HNbDJRsYM4I+nYwklwHMGlK+WdOvtWVKdxh+rbftQguK9+k /NJmch0w==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.98 #2 (Red Hat Linux)) id 1tt0Qn-0000000DTa7-3mao; Fri, 14 Mar 2025 08:30:13 +0000 Received: from szxga04-in.huawei.com ([45.249.212.190]) by bombadil.infradead.org with esmtps (Exim 4.98 #2 (Red Hat Linux)) id 1tt0Hd-0000000DQuz-0uFc for linux-arm-kernel@lists.infradead.org; Fri, 14 Mar 2025 08:20:47 +0000 Received: from mail.maildlp.com (unknown [172.19.88.234]) by szxga04-in.huawei.com (SkyGuard) with ESMTP id 4ZDcdX1Jxdz2RTXM; Fri, 14 Mar 2025 16:16:16 +0800 (CST) Received: from kwepemf500004.china.huawei.com (unknown [7.202.181.242]) by mail.maildlp.com (Postfix) with ESMTPS id 264DF14022D; Fri, 14 Mar 2025 16:20:40 +0800 (CST) Received: from lihuafei.huawei.com (10.90.53.74) by kwepemf500004.china.huawei.com (7.202.181.242) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.11; Fri, 14 Mar 2025 16:20:39 +0800 From: Li Huafei To: , , , , , , , CC: , , , , , , , , , , , , , , Subject: [PATCH 3/7] perf annotate: Add 'extract_reg_offset' callback function to extract register number and access offset Date: Sat, 15 Mar 2025 00:21:33 +0800 Message-ID: <20250314162137.528204-4-lihuafei1@huawei.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20250314162137.528204-1-lihuafei1@huawei.com> References: <20250314162137.528204-1-lihuafei1@huawei.com> MIME-Version: 1.0 X-Originating-IP: [10.90.53.74] X-ClientProxiedBy: dggems706-chm.china.huawei.com (10.3.19.183) To kwepemf500004.china.huawei.com (7.202.181.242) X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20250314_012045_558890_EDD193D7 X-CRM114-Status: GOOD ( 24.85 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.34 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org The assembly syntax for memory access instructions varies significantly across different architectures, which makes it difficult to reuse the code for extracting register numbers and access offsets in the function annotate_get_insn_location(). To simplify the code, the extraction of register numbers and access offsets from operands is written as a callback function for the architecture, facilitating the implementation of architecture-specific extraction logic. Signed-off-by: Li Huafei --- .../perf/arch/powerpc/annotate/instructions.c | 10 ++ tools/perf/arch/x86/annotate/instructions.c | 99 ++++++++++++++++ tools/perf/util/annotate.c | 107 +----------------- tools/perf/util/disasm.c | 2 + tools/perf/util/disasm.h | 4 + 5 files changed, 117 insertions(+), 105 deletions(-) diff --git a/tools/perf/arch/powerpc/annotate/instructions.c b/tools/perf/arch/powerpc/annotate/instructions.c index ca567cfdcbdb..fd6516890f3b 100644 --- a/tools/perf/arch/powerpc/annotate/instructions.c +++ b/tools/perf/arch/powerpc/annotate/instructions.c @@ -1,5 +1,6 @@ // SPDX-License-Identifier: GPL-2.0 #include +#include static struct ins_ops *powerpc__associate_instruction_ops(struct arch *arch, const char *name) { @@ -315,3 +316,12 @@ static int powerpc__annotate_init(struct arch *arch, char *cpuid __maybe_unused) return 0; } + +static int extract_reg_offset_powerpc(struct arch *arch __maybe_unused, + struct disasm_line *dl, + const char *insn_str __maybe_unused, int insn_ops, + struct annotated_op_loc *op_loc) +{ + get_powerpc_regs(dl->raw.raw_insn, insn_ops == INSN_OP_SOURCE, op_loc); + return 0; +} diff --git a/tools/perf/arch/x86/annotate/instructions.c b/tools/perf/arch/x86/annotate/instructions.c index ae94b1f0b9cc..83e0fc4b9788 100644 --- a/tools/perf/arch/x86/annotate/instructions.c +++ b/tools/perf/arch/x86/annotate/instructions.c @@ -596,3 +596,102 @@ static void update_insn_state_x86(struct type_state *state, /* Case 4. memory to memory transfers (not handled for now) */ } #endif + +/* + * Get register number and access offset from the given instruction. + * It assumes AT&T x86 asm format like OFFSET(REG). Maybe it needs + * to revisit the format when it handles different architecture. + * Fills @reg and @offset when return 0. + */ +static int extract_reg_offset(struct arch *arch, const char *str, + struct annotated_op_loc *op_loc) +{ + char *p; + char *regname; + + if (arch->objdump.register_char == 0) + return -1; + + /* + * It should start from offset, but it's possible to skip 0 + * in the asm. So 0(%rax) should be same as (%rax). + * + * However, it also start with a segment select register like + * %gs:0x18(%rbx). In that case it should skip the part. + */ + if (*str == arch->objdump.register_char) { + /* FIXME: Handle other segment registers */ + if (!strncmp(str, "%gs:", 4)) + op_loc->segment = INSN_SEG_X86_GS; + + while (*str && !isdigit(*str) && + *str != arch->objdump.memory_ref_char) + str++; + } + + op_loc->offset = strtol(str, &p, 0); + + p = strchr(p, arch->objdump.register_char); + if (p == NULL) + return -1; + + regname = strdup(p); + if (regname == NULL) + return -1; + + op_loc->reg1 = get_dwarf_regnum(regname, arch->e_machine, arch->e_flags); + free(regname); + + /* Get the second register */ + if (op_loc->multi_regs) { + p = strchr(p + 1, arch->objdump.register_char); + if (p == NULL) + return -1; + + regname = strdup(p); + if (regname == NULL) + return -1; + + op_loc->reg2 = get_dwarf_regnum(regname, arch->e_machine, arch->e_flags); + free(regname); + } + return 0; +} + +static int extract_reg_offset_x86(struct arch *arch, struct disasm_line *dl __maybe_unused, + const char *insn_str, int insn_ops __maybe_unused, + struct annotated_op_loc *op_loc) +{ + if (insn_str == NULL) + return 0; + + if (op_loc->mem_ref) { + extract_reg_offset(arch, insn_str, op_loc); + } else { + char *s, *p = NULL; + + /* FIXME: Handle other segment registers */ + if (!strncmp(insn_str, "%gs:", 4)) { + op_loc->segment = INSN_SEG_X86_GS; + op_loc->offset = strtol(insn_str + 4, &p, 0); + if (p && p != insn_str + 4) + op_loc->imm = true; + return 0; + } + + s = strdup(insn_str); + if (s == NULL) + return -1; + + if (*s == arch->objdump.register_char) + op_loc->reg1 = get_dwarf_regnum(s, arch->e_machine, arch->e_flags); + else if (*s == arch->objdump.imm_char) { + op_loc->offset = strtol(s + 1, &p, 0); + if (p && p != s + 1) + op_loc->imm = true; + } + free(s); + } + + return 0; +} diff --git a/tools/perf/util/annotate.c b/tools/perf/util/annotate.c index 860ea6c72411..288200e4b2b5 100644 --- a/tools/perf/util/annotate.c +++ b/tools/perf/util/annotate.c @@ -2318,69 +2318,6 @@ int annotate_check_args(void) return 0; } -/* - * Get register number and access offset from the given instruction. - * It assumes AT&T x86 asm format like OFFSET(REG). Maybe it needs - * to revisit the format when it handles different architecture. - * Fills @reg and @offset when return 0. - */ -static int extract_reg_offset(struct arch *arch, const char *str, - struct annotated_op_loc *op_loc) -{ - char *p; - char *regname; - - if (arch->objdump.register_char == 0) - return -1; - - /* - * It should start from offset, but it's possible to skip 0 - * in the asm. So 0(%rax) should be same as (%rax). - * - * However, it also start with a segment select register like - * %gs:0x18(%rbx). In that case it should skip the part. - */ - if (*str == arch->objdump.register_char) { - if (arch__is(arch, "x86")) { - /* FIXME: Handle other segment registers */ - if (!strncmp(str, "%gs:", 4)) - op_loc->segment = INSN_SEG_X86_GS; - } - - while (*str && !isdigit(*str) && - *str != arch->objdump.memory_ref_char) - str++; - } - - op_loc->offset = strtol(str, &p, 0); - - p = strchr(p, arch->objdump.register_char); - if (p == NULL) - return -1; - - regname = strdup(p); - if (regname == NULL) - return -1; - - op_loc->reg1 = get_dwarf_regnum(regname, arch->e_machine, arch->e_flags); - free(regname); - - /* Get the second register */ - if (op_loc->multi_regs) { - p = strchr(p + 1, arch->objdump.register_char); - if (p == NULL) - return -1; - - regname = strdup(p); - if (regname == NULL) - return -1; - - op_loc->reg2 = get_dwarf_regnum(regname, arch->e_machine, arch->e_flags); - free(regname); - } - return 0; -} - /** * annotate_get_insn_location - Get location of instruction * @arch: the architecture info @@ -2437,51 +2374,11 @@ int annotate_get_insn_location(struct arch *arch, struct disasm_line *dl, op_loc->reg1 = -1; op_loc->reg2 = -1; - if (insn_str == NULL) { - if (!arch__is(arch, "powerpc")) - continue; - } - op_loc->mem_ref = mem_ref; op_loc->multi_regs = multi_regs; - /* - * For powerpc, call get_powerpc_regs function which extracts the - * required fields for op_loc, ie reg1, reg2, offset from the - * raw instruction. - */ - if (arch__is(arch, "powerpc")) { - get_powerpc_regs(dl->raw.raw_insn, !i, op_loc); - } else if (mem_ref) { - extract_reg_offset(arch, insn_str, op_loc); - } else { - char *s, *p = NULL; - - if (arch__is(arch, "x86")) { - /* FIXME: Handle other segment registers */ - if (!strncmp(insn_str, "%gs:", 4)) { - op_loc->segment = INSN_SEG_X86_GS; - op_loc->offset = strtol(insn_str + 4, - &p, 0); - if (p && p != insn_str + 4) - op_loc->imm = true; - continue; - } - } - - s = strdup(insn_str); - if (s == NULL) - return -1; - - if (*s == arch->objdump.register_char) - op_loc->reg1 = get_dwarf_regnum(s, arch->e_machine, arch->e_flags); - else if (*s == arch->objdump.imm_char) { - op_loc->offset = strtol(s + 1, &p, 0); - if (p && p != s + 1) - op_loc->imm = true; - } - free(s); - } + if (arch->extract_reg_offset(arch, dl, insn_str, i, op_loc)) + return -1; } return 0; diff --git a/tools/perf/util/disasm.c b/tools/perf/util/disasm.c index d91526cff9df..905eceb824a4 100644 --- a/tools/perf/util/disasm.c +++ b/tools/perf/util/disasm.c @@ -155,6 +155,7 @@ static struct arch architectures[] = { #ifdef HAVE_LIBDW_SUPPORT .update_insn_state = update_insn_state_x86, #endif + .extract_reg_offset = extract_reg_offset_x86, }, { .name = "powerpc", @@ -162,6 +163,7 @@ static struct arch architectures[] = { #ifdef HAVE_LIBDW_SUPPORT .update_insn_state = update_insn_state_powerpc, #endif + .extract_reg_offset = extract_reg_offset_powerpc, }, { .name = "riscv64", diff --git a/tools/perf/util/disasm.h b/tools/perf/util/disasm.h index c135db2416b5..44ac5aa892f7 100644 --- a/tools/perf/util/disasm.h +++ b/tools/perf/util/disasm.h @@ -16,6 +16,7 @@ struct symbol; struct data_loc_info; struct type_state; struct disasm_line; +struct annotated_op_loc; struct arch { const char *name; @@ -44,6 +45,9 @@ struct arch { struct data_loc_info *dloc, Dwarf_Die *cu_die, struct disasm_line *dl); #endif + int (*extract_reg_offset)(struct arch *arch, struct disasm_line *dl, + const char *insn_str, int insn_ops, + struct annotated_op_loc *op_loc); /** @e_machine: ELF machine associated with arch. */ unsigned int e_machine; /** @e_flags: Optional ELF flags associated with arch. */ From patchwork Fri Mar 14 16:21:34 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Li Huafei X-Patchwork-Id: 14016430 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from bombadil.infradead.org (bombadil.infradead.org [198.137.202.133]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 8EFE4C282EC for ; Fri, 14 Mar 2025 08:35:29 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20210309; h=Sender:List-Subscribe:List-Help :List-Post:List-Archive:List-Unsubscribe:List-Id:Content-Type: Content-Transfer-Encoding:MIME-Version:References:In-Reply-To:Message-ID:Date :Subject:CC:To:From:Reply-To:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Owner; bh=IDQpZnKOwg8xvl3hBP1CVJrE/5b1YbVGtnJdK4DcRVY=; b=3ZiMFWDNHBTk6d7iAptVSzZstu 5Ib8WMFAGsWUErO0VH/LwV7JSuNlZki2Cy4Qz7n1CDmcxbWwAIGrKMyT4zl3G8cT/WWz5o6L/TqkV j+kFs56EsyXki0/7AeQ1ImsptWvQlONpbjvkL+ZNHZkMSNwxnf5Wj2rmWwztNVOwuYhld/n4BCGi1 g8Lw9FBF0rZEno4QJb6c2aCB62Z17oTJd/oRugeL+DlaWe+b6+76Ps7wPIVpab9mbMnHMqqJXmGlu XGZ/tJmMCSeX7JCuHXCj3YZ79cJkXj6mkUqbgxXqzWvOBnAUWxtee0NUvPwre3Xb2oyi8zIzNOjFU zSgPX1Yw==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.98 #2 (Red Hat Linux)) id 1tt0Vj-0000000DV7N-0rca; Fri, 14 Mar 2025 08:35:19 +0000 Received: from szxga03-in.huawei.com ([45.249.212.189]) by bombadil.infradead.org with esmtps (Exim 4.98 #2 (Red Hat Linux)) id 1tt0Hd-0000000DQvL-2drM for linux-arm-kernel@lists.infradead.org; Fri, 14 Mar 2025 08:20:48 +0000 Received: from mail.maildlp.com (unknown [172.19.163.174]) by szxga03-in.huawei.com (SkyGuard) with ESMTP id 4ZDcfx0mk3zCtSP; Fri, 14 Mar 2025 16:17:29 +0800 (CST) Received: from kwepemf500004.china.huawei.com (unknown [7.202.181.242]) by mail.maildlp.com (Postfix) with ESMTPS id EC7F2140156; Fri, 14 Mar 2025 16:20:40 +0800 (CST) Received: from lihuafei.huawei.com (10.90.53.74) by kwepemf500004.china.huawei.com (7.202.181.242) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.11; Fri, 14 Mar 2025 16:20:39 +0800 From: Li Huafei To: , , , , , , , CC: , , , , , , , , , , , , , , Subject: [PATCH 4/7] perf annotate: Support for the 'extract_reg_offset' callback function in arm64 Date: Sat, 15 Mar 2025 00:21:34 +0800 Message-ID: <20250314162137.528204-5-lihuafei1@huawei.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20250314162137.528204-1-lihuafei1@huawei.com> References: <20250314162137.528204-1-lihuafei1@huawei.com> MIME-Version: 1.0 X-Originating-IP: [10.90.53.74] X-ClientProxiedBy: dggems706-chm.china.huawei.com (10.3.19.183) To kwepemf500004.china.huawei.com (7.202.181.242) X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20250314_012046_042565_3966DF62 X-CRM114-Status: GOOD ( 20.06 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.34 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org At present, only the following two addressing modes are supported: 1. Base register only (no offset): [base{, #0}] 2. Base plus offset (immediate): [base{, #imm}] For addressing modes where the offset needs to be calculated from the register value, it is difficult to know the specific value of the offset register, making it impossible to calculate the offset. Signed-off-by: Li Huafei --- tools/perf/arch/arm64/annotate/instructions.c | 62 +++++++++++++++++++ tools/perf/util/Build | 1 + tools/perf/util/disasm.c | 1 + tools/perf/util/dwarf-regs-arm64.c | 25 ++++++++ tools/perf/util/include/dwarf-regs.h | 7 +++ 5 files changed, 96 insertions(+) create mode 100644 tools/perf/util/dwarf-regs-arm64.c diff --git a/tools/perf/arch/arm64/annotate/instructions.c b/tools/perf/arch/arm64/annotate/instructions.c index c212eb7341bd..54497b72a5c5 100644 --- a/tools/perf/arch/arm64/annotate/instructions.c +++ b/tools/perf/arch/arm64/annotate/instructions.c @@ -188,3 +188,65 @@ static int arm64__annotate_init(struct arch *arch, char *cpuid __maybe_unused) free(arm); return SYMBOL_ANNOTATE_ERRNO__ARCH_INIT_REGEXP; } + + +/* + * Get the base register number and access offset in load/store instructions. + * At present, only the following two addressing modes are supported: + * + * 1. Base register only (no offset): [base{, #0}] + * 2. Base plus offset (immediate): [base{, #imm}] + * + * For addressing modes where the offset needs to be calculated from the + * register value, it is difficult to know the specific value of the offset + * register, making it impossible to calculate the offset. + * + * Fills @reg and @offset when return 0. + */ +static int +extract_reg_offset_arm64(struct arch *arch __maybe_unused, + struct disasm_line *dl __maybe_unused, + const char *insn_str, int insn_ops __maybe_unused, + struct annotated_op_loc *op_loc) +{ + char *str; + regmatch_t match[4]; + static regex_t reg_off_regex; + static bool regex_compiled; + + if (!regex_compiled) { + regcomp(®_off_regex, "^\\[(sp|[xw][0-9]{1,2})(, #(-?[0-9]+))?\\].*", + REG_EXTENDED); + regex_compiled = true; + } + + if (!op_loc->mem_ref) + return 0; + + if (regexec(®_off_regex, insn_str, 4, match, 0)) + return -1; + + str = strdup(insn_str); + if (!str) + return -1; + + /* Get the base register number. */ + str[match[1].rm_eo] = '\0'; + op_loc->reg1 = get_arm64_regnum(str + match[1].rm_so); + + /* + * If there is an immediate offset, match[2] records the start and end + * positions of "#imm". + */ + if (match[2].rm_so == -1) { + free(str); + return 0; + } + + /* Get the immediate offset. */ + str[match[3].rm_eo] = '\0'; + op_loc->offset = strtol(str + match[3].rm_so, NULL, 0); + + free(str); + return 0; +} diff --git a/tools/perf/util/Build b/tools/perf/util/Build index 5ec97e8d6b6d..d408cbe94fdd 100644 --- a/tools/perf/util/Build +++ b/tools/perf/util/Build @@ -210,6 +210,7 @@ perf-util-$(CONFIG_LIBDW) += dwarf-regs.o perf-util-$(CONFIG_LIBDW) += dwarf-regs-csky.o perf-util-$(CONFIG_LIBDW) += dwarf-regs-powerpc.o perf-util-$(CONFIG_LIBDW) += dwarf-regs-x86.o +perf-util-$(CONFIG_LIBDW) += dwarf-regs-arm64.o perf-util-$(CONFIG_LIBDW) += debuginfo.o perf-util-$(CONFIG_LIBDW) += annotate-data.o diff --git a/tools/perf/util/disasm.c b/tools/perf/util/disasm.c index 905eceb824a4..1035c60a8545 100644 --- a/tools/perf/util/disasm.c +++ b/tools/perf/util/disasm.c @@ -128,6 +128,7 @@ static struct arch architectures[] = { { .name = "arm64", .init = arm64__annotate_init, + .extract_reg_offset = extract_reg_offset_arm64, }, { .name = "csky", diff --git a/tools/perf/util/dwarf-regs-arm64.c b/tools/perf/util/dwarf-regs-arm64.c new file mode 100644 index 000000000000..edf41c059967 --- /dev/null +++ b/tools/perf/util/dwarf-regs-arm64.c @@ -0,0 +1,25 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Mapping of DWARF debug register numbers into register names. + * + * Copyright (c) 2025 Huawei Inc, Li Huafei + */ +#include +#include +#include + +int get_arm64_regnum(const char *name) +{ + int reg; + + if (!strcmp(name, "sp")) + return 31; + + if (*name != 'x' && *name != 'w') + return -EINVAL; + + name++; + reg = strtol(name, NULL, 0); + + return reg >= 0 && reg <= 30 ? reg : -EINVAL; +} diff --git a/tools/perf/util/include/dwarf-regs.h b/tools/perf/util/include/dwarf-regs.h index 6f1b9f6b2466..81cc5f69a391 100644 --- a/tools/perf/util/include/dwarf-regs.h +++ b/tools/perf/util/include/dwarf-regs.h @@ -101,6 +101,8 @@ const char *get_dwarf_regstr(unsigned int n, unsigned int machine, unsigned int int get_x86_regnum(const char *name); +int get_arm64_regnum(const char *name); + #if !defined(__x86_64__) && !defined(__i386__) int get_arch_regnum(const char *name); #endif @@ -128,6 +130,11 @@ static inline void get_powerpc_regs(u32 raw_insn __maybe_unused, int is_source _ { return; } + +static inline int get_arm64_regnum(const char *name __maybe_unused) +{ + return -1; +} #endif #endif From patchwork Fri Mar 14 16:21:35 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Li Huafei X-Patchwork-Id: 14016429 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from bombadil.infradead.org (bombadil.infradead.org [198.137.202.133]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id EECCEC28B2F for ; Fri, 14 Mar 2025 08:33:48 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20210309; h=Sender:List-Subscribe:List-Help :List-Post:List-Archive:List-Unsubscribe:List-Id:Content-Type: Content-Transfer-Encoding:MIME-Version:References:In-Reply-To:Message-ID:Date :Subject:CC:To:From:Reply-To:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Owner; bh=OgsX2c9I1bcCq6x9YAJPK9pb11UWR20P/k47Q4srlQI=; b=xQwu/nSyZoD/oW9UAOzTzTBRFg kmObQJYTCIK5Od17amBRfYpT1uKngJebj0cU82uAbDo5NLp/xyat2aB7+KXs+p5iUuWdalJpeV3dj 4wmJnnX2LQMjvzAVApQXU/mtiVme0L4ZJQpjBe9Y6qG934T/S2d0vLutXFTX77IE/ejiq9xdaDGyx vPeGxxjxeYHM4MnfuZKapS0zwnP4zalAn3Z6/9v+EMcDkd1zjb4Fk9KcIcVd03eK4ykt9J6r4tZ7j GriFz7rxFVP7+7MhsjenU6IEIlRP6CmtLvZx9N4KO2OqYpeYDmKu04GkbbhzFWbURvRDRpxoiHp2i ++iDOL7Q==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.98 #2 (Red Hat Linux)) id 1tt0U5-0000000DUZe-1vI1; Fri, 14 Mar 2025 08:33:37 +0000 Received: from szxga03-in.huawei.com ([45.249.212.189]) by bombadil.infradead.org with esmtps (Exim 4.98 #2 (Red Hat Linux)) id 1tt0Hd-0000000DQva-28Pk for linux-arm-kernel@lists.infradead.org; Fri, 14 Mar 2025 08:20:48 +0000 Received: from mail.maildlp.com (unknown [172.19.163.252]) by szxga03-in.huawei.com (SkyGuard) with ESMTP id 4ZDcfx5lN6zCtSS; Fri, 14 Mar 2025 16:17:29 +0800 (CST) Received: from kwepemf500004.china.huawei.com (unknown [7.202.181.242]) by mail.maildlp.com (Postfix) with ESMTPS id AF96F1800E4; Fri, 14 Mar 2025 16:20:41 +0800 (CST) Received: from lihuafei.huawei.com (10.90.53.74) by kwepemf500004.china.huawei.com (7.202.181.242) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.11; Fri, 14 Mar 2025 16:20:40 +0800 From: Li Huafei To: , , , , , , , CC: , , , , , , , , , , , , , , Subject: [PATCH 5/7] perf annotate-data: Support instruction tracking for arm64 Date: Sat, 15 Mar 2025 00:21:35 +0800 Message-ID: <20250314162137.528204-6-lihuafei1@huawei.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20250314162137.528204-1-lihuafei1@huawei.com> References: <20250314162137.528204-1-lihuafei1@huawei.com> MIME-Version: 1.0 X-Originating-IP: [10.90.53.74] X-ClientProxiedBy: dggems706-chm.china.huawei.com (10.3.19.183) To kwepemf500004.china.huawei.com (7.202.181.242) X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20250314_012045_852964_5AE9EF9A X-CRM114-Status: GOOD ( 17.95 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.34 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Support for arm64 instruction tracing. This patch addresses the scenario where type information cannot be found during multi-level pointer references. For example, consider the vfs_ioctl() function: long vfs_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) { int error = -ENOTTY; if (!filp->f_op->unlocked_ioctl) goto out; error = filp->f_op->unlocked_ioctl(filp, cmd, arg); if (error == -ENOIOCTLCMD) error = -ENOTTY; out: return error; } The 'SYSCALL_DEFINE3(ioctl)' inlines vfs_ioctl, and the assembly instructions for 'if (!filp->f_op->unlocked_ioctl)' are as follows: ldr x0, [x21, #16] ldr x3, [x0, #80] cbz x3, ffff80008048e9a4 The first instruction loads the 'filp->f_op' pointer, and the second instruction loads the 'filp->f_op->unlocked_ioctl' pointer. DWARF generates type information for x21, but not for x0. Therefore, if PMU sampling occurs on the second instruction, the corresponding data type cannot be obtained. However, by using the type information and offset from x21 in the first ldr instruction, we can infer the type of x0 and, combined with the offset, resolve the accessed data member. Signed-off-by: Li Huafei --- tools/perf/arch/arm64/annotate/instructions.c | 44 ++++++++++++++++++- tools/perf/util/annotate-data.c | 3 +- tools/perf/util/annotate-data.h | 2 +- tools/perf/util/disasm.c | 3 ++ 4 files changed, 49 insertions(+), 3 deletions(-) diff --git a/tools/perf/arch/arm64/annotate/instructions.c b/tools/perf/arch/arm64/annotate/instructions.c index 54497b72a5c5..f70d93001fe7 100644 --- a/tools/perf/arch/arm64/annotate/instructions.c +++ b/tools/perf/arch/arm64/annotate/instructions.c @@ -215,7 +215,8 @@ extract_reg_offset_arm64(struct arch *arch __maybe_unused, static bool regex_compiled; if (!regex_compiled) { - regcomp(®_off_regex, "^\\[(sp|[xw][0-9]{1,2})(, #(-?[0-9]+))?\\].*", + regcomp(®_off_regex, + "^\\[(sp|[xw][0-9]{1,2})(, #(-?[0-9]+))?\\].*", REG_EXTENDED); regex_compiled = true; } @@ -250,3 +251,44 @@ extract_reg_offset_arm64(struct arch *arch __maybe_unused, free(str); return 0; } + +#ifdef HAVE_LIBDW_SUPPORT +static void +update_insn_state_arm64(struct type_state *state, struct data_loc_info *dloc, + Dwarf_Die * cu_die __maybe_unused, struct disasm_line *dl) +{ + struct annotated_insn_loc loc; + struct annotated_op_loc *dst = &loc.ops[INSN_OP_TARGET]; + struct type_state_reg *tsr; + Dwarf_Die type_die; + int sreg, dreg; + + if (strncmp(dl->ins.name, "ld", 2)) + return; + + if (annotate_get_insn_location(dloc->arch, dl, &loc) < 0) + return; + + sreg = get_arm64_regnum(dl->ops.source.raw); + if (sreg < 0) + return; + if (!has_reg_type(state, sreg)) + return; + + dreg = dst->reg1; + if (has_reg_type(state, dreg) && state->regs[dreg].ok && + state->regs[dreg].kind == TSR_KIND_TYPE && + dwarf_tag(&state->regs[dreg].type) == DW_TAG_pointer_type && + die_deref_ptr_type(&state->regs[dreg].type, + dst->offset, &type_die)) { + tsr = &state->regs[sreg]; + tsr->type = type_die; + tsr->kind = TSR_KIND_TYPE; + tsr->ok = true; + + pr_debug_dtp("load [%x] %#x(reg%d) -> reg%d", + (u32)dl->al.offset, dst->offset, dreg, sreg); + pr_debug_type_name(&tsr->type, tsr->kind); + } +} +#endif diff --git a/tools/perf/util/annotate-data.c b/tools/perf/util/annotate-data.c index 976abedca09e..2bc8d646eedc 100644 --- a/tools/perf/util/annotate-data.c +++ b/tools/perf/util/annotate-data.c @@ -1293,7 +1293,8 @@ static enum type_match_result find_data_type_insn(struct data_loc_info *dloc, static int arch_supports_insn_tracking(struct data_loc_info *dloc) { - if ((arch__is(dloc->arch, "x86")) || (arch__is(dloc->arch, "powerpc"))) + if ((arch__is(dloc->arch, "x86")) || (arch__is(dloc->arch, "powerpc")) || + (arch__is(dloc->arch, "arm64"))) return 1; return 0; } diff --git a/tools/perf/util/annotate-data.h b/tools/perf/util/annotate-data.h index 98c80b2268dd..717f394eb8f1 100644 --- a/tools/perf/util/annotate-data.h +++ b/tools/perf/util/annotate-data.h @@ -190,7 +190,7 @@ struct type_state_stack { }; /* FIXME: This should be arch-dependent */ -#ifdef __powerpc__ +#if defined(__powerpc__) || defined(__aarch64__) #define TYPE_STATE_MAX_REGS 32 #else #define TYPE_STATE_MAX_REGS 16 diff --git a/tools/perf/util/disasm.c b/tools/perf/util/disasm.c index 1035c60a8545..540981c155f9 100644 --- a/tools/perf/util/disasm.c +++ b/tools/perf/util/disasm.c @@ -129,6 +129,9 @@ static struct arch architectures[] = { .name = "arm64", .init = arm64__annotate_init, .extract_reg_offset = extract_reg_offset_arm64, +#ifdef HAVE_LIBDW_SUPPORT + .update_insn_state = update_insn_state_arm64, +#endif }, { .name = "csky", From patchwork Fri Mar 14 16:21:36 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Li Huafei X-Patchwork-Id: 14016420 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from bombadil.infradead.org (bombadil.infradead.org [198.137.202.133]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id B9C3CC28B2F for ; Fri, 14 Mar 2025 08:25:09 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20210309; h=Sender:List-Subscribe:List-Help :List-Post:List-Archive:List-Unsubscribe:List-Id:Content-Type: Content-Transfer-Encoding:MIME-Version:References:In-Reply-To:Message-ID:Date :Subject:CC:To:From:Reply-To:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Owner; bh=6c4rNPX9KYZkw6UGJ7wf01mW0kMliSBgjDLx+b3r4GU=; b=EqtewSDIp88WJ70EI/1m2H52Kc L7SW3piJ7nVzGz1MXQT3Mc/s7Caoz1Mdn/r9cG2Zkz+ZTTcs1EkZ9vTFKSVJYThAgqALKtx1TVqrp a7W2fFcxGgdIlMzoL5Sp3y0jodm37owkDebzlzWCZZPsLslffahbev+Kktjy0EeZVPToHmAYaCVJQ QjnwnnEetICL8BfTVrPC0EsegLje5s8I3B13ELUbr7BsRYQ1sOmTnGjBMb1+GcGk4wn7/hXuHxmKR BUVUPhJRopATuhDZW8iaRf9SDKgblO3J3P6phfMHHxQuhZMnUOwsxbbZ6PlP895wcU/vuDxJsNL+K QsbWkUiA==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.98 #2 (Red Hat Linux)) id 1tt0Ll-0000000DS2O-1GPq; Fri, 14 Mar 2025 08:25:01 +0000 Received: from szxga03-in.huawei.com ([45.249.212.189]) by bombadil.infradead.org with esmtps (Exim 4.98 #2 (Red Hat Linux)) id 1tt0Hd-0000000DQw7-2r2v for linux-arm-kernel@lists.infradead.org; Fri, 14 Mar 2025 08:20:50 +0000 Received: from mail.maildlp.com (unknown [172.19.163.48]) by szxga03-in.huawei.com (SkyGuard) with ESMTP id 4ZDcfy4Js8zCtSW; Fri, 14 Mar 2025 16:17:30 +0800 (CST) Received: from kwepemf500004.china.huawei.com (unknown [7.202.181.242]) by mail.maildlp.com (Postfix) with ESMTPS id 79E4018006C; Fri, 14 Mar 2025 16:20:42 +0800 (CST) Received: from lihuafei.huawei.com (10.90.53.74) by kwepemf500004.china.huawei.com (7.202.181.242) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.11; Fri, 14 Mar 2025 16:20:41 +0800 From: Li Huafei To: , , , , , , , CC: , , , , , , , , , , , , , , Subject: [PATCH 6/7] perf annotate-data: Handle arm64 global variable access Date: Sat, 15 Mar 2025 00:21:36 +0800 Message-ID: <20250314162137.528204-7-lihuafei1@huawei.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20250314162137.528204-1-lihuafei1@huawei.com> References: <20250314162137.528204-1-lihuafei1@huawei.com> MIME-Version: 1.0 X-Originating-IP: [10.90.53.74] X-ClientProxiedBy: dggems706-chm.china.huawei.com (10.3.19.183) To kwepemf500004.china.huawei.com (7.202.181.242) X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20250314_012046_091349_726BE663 X-CRM114-Status: GOOD ( 17.25 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.34 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org Arm64 uses the 'adrp' and 'add' instructions to load the address of a global variable. For example: adrp x19, ffff8000819c3000 add x19, x19, #0x3e8 <> ldr x22, [x19, #8] Here, 'adrp' retrieves the base address of the page where the global variable is located, and 'add' adds the offset within the page. If PMU sampling occurs at the instruction 'ldr x22, [x19, #8]', we need to trace the preceding 'adrp' and 'add' instructions to obtain the status information of x19. A new register status type 'TSR_KIND_GLOBAL_ADDR' is introduced, indicating that the register holds the address of a global variable, and this address is also stored in the 'type_state_reg' structure. After obtaining the status information of x19, we use get_global_var_type() to search for a matching global variable and verify whether the returned offset is equal to 8. If it is, then we have identified the data type and offset of the accessed global variable. Signed-off-by: Li Huafei --- tools/perf/arch/arm64/annotate/instructions.c | 90 ++++++++++++++++++- tools/perf/util/annotate-data.c | 20 +++++ tools/perf/util/annotate-data.h | 2 + 3 files changed, 111 insertions(+), 1 deletion(-) diff --git a/tools/perf/arch/arm64/annotate/instructions.c b/tools/perf/arch/arm64/annotate/instructions.c index f70d93001fe7..f2053e7f60a8 100644 --- a/tools/perf/arch/arm64/annotate/instructions.c +++ b/tools/perf/arch/arm64/annotate/instructions.c @@ -262,6 +262,94 @@ update_insn_state_arm64(struct type_state *state, struct data_loc_info *dloc, struct type_state_reg *tsr; Dwarf_Die type_die; int sreg, dreg; + u32 insn_offset = dl->al.offset; + + /* Access global variables via PC relative addressing, for example: + * + * adrp x19, ffff800082074000 + * add x19, x19, #0x380 + * + * The adrp instruction locates the page base address, and the add + * instruction adds the offset within the page. + */ + if (!strncmp(dl->ins.name, "adrp", 4)) { + sreg = get_arm64_regnum(dl->ops.source.raw); + if (sreg < 0 || !has_reg_type(state, sreg)) + return; + + tsr = &state->regs[sreg]; + tsr->ok = true; + tsr->kind = TSR_KIND_GLOBAL_ADDR; + /* + * The default arm64_mov_ops has already parsed the adrp + * instruction and saved the target address. + */ + tsr->addr = dl->ops.target.addr; + + pr_debug_dtp("adrp [%x] global addr=%#"PRIx64" -> reg%d\n", + insn_offset, tsr->addr, sreg); + return; + } + + /* Add the offset within the page. */ + if (!strncmp(dl->ins.name, "add", 3)) { + regmatch_t match[4]; + char *ops = strdup(dl->ops.raw); + u64 offset; + static regex_t add_regex; + static bool regex_compiled; + + /* + * Matching the operand assembly syntax of the add instruction: + * + * , , # + */ + if (!regex_compiled) { + regcomp(&add_regex, + "^([xw][0-9]{1,2}|sp), ([xw][0-9]{1,2}|sp), #(0x[0-9a-f]+)", + REG_EXTENDED); + regex_compiled = true; + } + + if (!ops) + return; + + if (regexec(&add_regex, dl->ops.raw, 4, match, 0)) + return; + + /* + * Parse the source register first. If it is not of the type + * TSR_KIND_GLOBAL_ADDR, further parsing is not required. + */ + ops[match[2].rm_eo] = '\0'; + sreg = get_arm64_regnum(ops + match[2].rm_so); + if (sreg < 0 || !has_reg_type(state, sreg) || + state->regs[sreg].kind != TSR_KIND_GLOBAL_ADDR) { + free(ops); + return; + } + + ops[match[1].rm_eo] = '\0'; + dreg = get_arm64_regnum(ops + match[1].rm_so); + if (dreg < 0 || !has_reg_type(state, dreg)) { + free(ops); + return; + } + + ops[match[3].rm_eo] = '\0'; + offset = strtoul(ops + match[3].rm_so, NULL, 16); + + tsr = &state->regs[dreg]; + tsr->ok = true; + tsr->kind = TSR_KIND_GLOBAL_ADDR; + tsr->addr = state->regs[sreg].addr + offset; + + pr_debug_dtp("add [%x] global addr=%#"PRIx64"(reg%d) -> reg%d\n", + insn_offset, tsr->addr, sreg, dreg); + + free(ops); + return; + } if (strncmp(dl->ins.name, "ld", 2)) return; @@ -287,7 +375,7 @@ update_insn_state_arm64(struct type_state *state, struct data_loc_info *dloc, tsr->ok = true; pr_debug_dtp("load [%x] %#x(reg%d) -> reg%d", - (u32)dl->al.offset, dst->offset, dreg, sreg); + insn_offset, dst->offset, dreg, sreg); pr_debug_type_name(&tsr->type, tsr->kind); } } diff --git a/tools/perf/util/annotate-data.c b/tools/perf/util/annotate-data.c index 2bc8d646eedc..aaca08bb9097 100644 --- a/tools/perf/util/annotate-data.c +++ b/tools/perf/util/annotate-data.c @@ -65,6 +65,9 @@ void pr_debug_type_name(Dwarf_Die *die, enum type_state_kind kind) case TSR_KIND_CANARY: pr_info(" stack canary\n"); return; + case TSR_KIND_GLOBAL_ADDR: + pr_info(" global address\n"); + return; case TSR_KIND_TYPE: default: break; @@ -1087,6 +1090,23 @@ static enum type_match_result check_matching_type(struct type_state *state, return PERF_TMR_OK; } + if (state->regs[reg].kind == TSR_KIND_GLOBAL_ADDR) { + int var_offset; + u64 var_addr; + + pr_debug_dtp("global var by address"); + + var_addr = state->regs[reg].addr + dloc->op->offset; + + if (get_global_var_type(cu_die, dloc, dloc->ip, var_addr, + &var_offset, type_die)) { + dloc->type_offset = var_offset; + return PERF_TMR_OK; + } + + return PERF_TMR_BAIL_OUT; + } + if (state->regs[reg].kind == TSR_KIND_CANARY) { pr_debug_dtp("stack canary"); diff --git a/tools/perf/util/annotate-data.h b/tools/perf/util/annotate-data.h index 717f394eb8f1..e3e877313207 100644 --- a/tools/perf/util/annotate-data.h +++ b/tools/perf/util/annotate-data.h @@ -36,6 +36,7 @@ enum type_state_kind { TSR_KIND_CONST, TSR_KIND_POINTER, TSR_KIND_CANARY, + TSR_KIND_GLOBAL_ADDR, }; /** @@ -177,6 +178,7 @@ struct type_state_reg { bool caller_saved; u8 kind; u8 copied_from; + u64 addr; }; /* Type information in a stack location, dynamically allocated */ From patchwork Fri Mar 14 16:21:37 2025 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Li Huafei X-Patchwork-Id: 14016424 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from bombadil.infradead.org (bombadil.infradead.org [198.137.202.133]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 0F59EC282EC for ; Fri, 14 Mar 2025 08:26:53 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20210309; h=Sender:List-Subscribe:List-Help :List-Post:List-Archive:List-Unsubscribe:List-Id:Content-Type: Content-Transfer-Encoding:MIME-Version:References:In-Reply-To:Message-ID:Date :Subject:CC:To:From:Reply-To:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Owner; bh=G1WeB4x6CHyrgzt8D5W31tN8y9H8QgucSRoa9BiEA7g=; b=vbaZ74d7qabCm0YJN2egJUsQOD keq/kCruNsJn7EAdCKUS0foZt8XY/xfqsZCFUAdJBhIvGMylzzVYiAgXzsxI6lSHzz94gsnKV5MS5 KqnPyU+3h/IBRb7AxRduFG+3xwkhs9ahnvRmEF3949aZu885u5RxTjnTHSzx7eT65XVpxLPhkuOAJ bAlLtp6qfLqyGtFGMMVWLNKc/dR+7yGihkAYoEyIcKwA4HiEbft+I2ZnvekPdYEGLwnC5CvsxW9m9 x3TLVwpIKR24b8WeGER4S9msM6aLewjPtl0K9zRCJ3f3TO2oseW9TMrkyrsZZ7ohBjlaYHrt1ZklN vAIFtkNg==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.98 #2 (Red Hat Linux)) id 1tt0NO-0000000DSO6-40dK; Fri, 14 Mar 2025 08:26:42 +0000 Received: from szxga01-in.huawei.com ([45.249.212.187]) by bombadil.infradead.org with esmtps (Exim 4.98 #2 (Red Hat Linux)) id 1tt0He-0000000DQwc-2x8v for linux-arm-kernel@lists.infradead.org; Fri, 14 Mar 2025 08:20:50 +0000 Received: from mail.maildlp.com (unknown [172.19.88.105]) by szxga01-in.huawei.com (SkyGuard) with ESMTP id 4ZDcfC6PFrzvWsF; Fri, 14 Mar 2025 16:16:51 +0800 (CST) Received: from kwepemf500004.china.huawei.com (unknown [7.202.181.242]) by mail.maildlp.com (Postfix) with ESMTPS id 42B101401F3; Fri, 14 Mar 2025 16:20:43 +0800 (CST) Received: from lihuafei.huawei.com (10.90.53.74) by kwepemf500004.china.huawei.com (7.202.181.242) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.11; Fri, 14 Mar 2025 16:20:42 +0800 From: Li Huafei To: , , , , , , , CC: , , , , , , , , , , , , , , Subject: [PATCH 7/7] perf annotate-data: Handle the access to the 'current' pointer on arm64 Date: Sat, 15 Mar 2025 00:21:37 +0800 Message-ID: <20250314162137.528204-8-lihuafei1@huawei.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20250314162137.528204-1-lihuafei1@huawei.com> References: <20250314162137.528204-1-lihuafei1@huawei.com> MIME-Version: 1.0 X-Originating-IP: [10.90.53.74] X-ClientProxiedBy: dggems706-chm.china.huawei.com (10.3.19.183) To kwepemf500004.china.huawei.com (7.202.181.242) X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20250314_012047_138114_0CD4EDEF X-CRM114-Status: GOOD ( 14.18 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.34 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org According to the implementation of the 'current' macro on ARM64, the sp_el0 register stores the pointer to the current task's task_struct. For example: mrs x1, sp_el0 ldr x2, [x1, #1896] We can infer that the ldr instruction is accessing a member of the task_struct structure at an offset of 1896. The key is to construct the data type for x1. The instruction 'mrs x1, sp_el0' belongs to the inline function get_current(). By finding the DIE of the inline function through its instruction address, and then obtaining the DIE for its return type, which should be 'struct task_struct *'. Then, we update the register state of x1 with this type information. Signed-off-by: Li Huafei --- tools/perf/arch/arm64/annotate/instructions.c | 71 +++++++++++++++---- 1 file changed, 57 insertions(+), 14 deletions(-) diff --git a/tools/perf/arch/arm64/annotate/instructions.c b/tools/perf/arch/arm64/annotate/instructions.c index f2053e7f60a8..c5a0a6381547 100644 --- a/tools/perf/arch/arm64/annotate/instructions.c +++ b/tools/perf/arch/arm64/annotate/instructions.c @@ -263,6 +263,20 @@ update_insn_state_arm64(struct type_state *state, struct data_loc_info *dloc, Dwarf_Die type_die; int sreg, dreg; u32 insn_offset = dl->al.offset; + static regex_t add_regex, mrs_regex; + static bool regex_compiled; + + if (!regex_compiled) { + /* + * Matching the operand assembly syntax of the add instruction: + * + * , , # + */ + regcomp(&add_regex, "^([xw][0-9]{1,2}|sp), ([xw][0-9]{1,2}|sp), #(0x[0-9a-f]+)", + REG_EXTENDED); + regcomp(&mrs_regex, "^(x[0-9]{1,2}), sp_el0", REG_EXTENDED); + regex_compiled = true; + } /* Access global variables via PC relative addressing, for example: * @@ -296,20 +310,6 @@ update_insn_state_arm64(struct type_state *state, struct data_loc_info *dloc, regmatch_t match[4]; char *ops = strdup(dl->ops.raw); u64 offset; - static regex_t add_regex; - static bool regex_compiled; - - /* - * Matching the operand assembly syntax of the add instruction: - * - * , , # - */ - if (!regex_compiled) { - regcomp(&add_regex, - "^([xw][0-9]{1,2}|sp), ([xw][0-9]{1,2}|sp), #(0x[0-9a-f]+)", - REG_EXTENDED); - regex_compiled = true; - } if (!ops) return; @@ -351,6 +351,49 @@ update_insn_state_arm64(struct type_state *state, struct data_loc_info *dloc, return; } + if (!strncmp(dl->ins.name, "mrs", 3)) { + regmatch_t match[2]; + char *ops = strdup(dl->ops.raw); + Dwarf_Die func_die; + Dwarf_Attribute attr; + u64 ip = dloc->ms->sym->start + dl->al.offset; + u64 pc = map__rip_2objdump(dloc->ms->map, ip); + + if (!ops) + return; + + if (regexec(&mrs_regex, dl->ops.raw, 2, match, 0)) + return; + + ops[match[1].rm_eo] = '\0'; + sreg = get_arm64_regnum(ops + match[1].rm_so); + if (sreg < 0 || !has_reg_type(state, sreg)) { + free(ops); + return; + } + + /* + * Find the inline function 'get_current()' Dwarf_Die and + * obtain its return value data type, which should be + * 'struct task_struct *'. + */ + if (!die_find_inlinefunc(cu_die, pc, &func_die) || + !dwarf_attr_integrate(&func_die, DW_AT_type, &attr) || + !dwarf_formref_die(&attr, &type_die)) { + free(ops); + return; + } + + tsr = &state->regs[sreg]; + tsr->type = type_die; + tsr->kind = TSR_KIND_TYPE; + tsr->ok = true; + + pr_debug_dtp("mrs sp_el0 [%x] -> reg%d", insn_offset, sreg); + free(ops); + return; + } + if (strncmp(dl->ins.name, "ld", 2)) return;