[PATCH linux dev-6.12 v2 4/6] soc: aspeed: xdma: Add trace events

Ninad Palsule ninad at linux.ibm.com
Thu Sep 4 01:58:06 AEST 2025


From: Eddie James <eajames at linux.ibm.com>

Trace the flow of the driver to aid debugging after an error.

OpenBMC-Staging-Count: 6
Signed-off-by: Eddie James <eajames at linux.ibm.com>
Acked-by: Andrew Jeffery <andrew at aj.id.au>
Link: https://lore.kernel.org/r/20220412215331.42491-1-eajames@linux.ibm.com
Signed-off-by: Joel Stanley <joel at jms.id.au>
Signed-off-by: Ninad Palsule <ninad at linux.ibm.com>
---
 drivers/soc/aspeed/aspeed-xdma.c |  18 ++++-
 include/trace/events/xdma.h      | 126 +++++++++++++++++++++++++++++++
 2 files changed, 142 insertions(+), 2 deletions(-)
 create mode 100644 include/trace/events/xdma.h

diff --git a/drivers/soc/aspeed/aspeed-xdma.c b/drivers/soc/aspeed/aspeed-xdma.c
index 40104602f5a2c..cb9bcfc44bc28 100644
--- a/drivers/soc/aspeed/aspeed-xdma.c
+++ b/drivers/soc/aspeed/aspeed-xdma.c
@@ -253,6 +253,9 @@ struct aspeed_xdma_client {
 	u32 size;
 };
 
+#define CREATE_TRACE_POINTS
+#include <trace/events/xdma.h>
+
 static u32 aspeed_xdma_readl(struct aspeed_xdma *ctx, u8 reg)
 {
 	u32 v = readl(ctx->base + reg);
@@ -449,6 +452,7 @@ static int aspeed_xdma_start(struct aspeed_xdma *ctx, unsigned int num_cmds,
 
 	ctx->upstream = upstream;
 	for (i = 0; i < num_cmds; ++i) {
+		trace_xdma_start(ctx, &cmds[i]);
 		/*
 		 * Use memcpy_toio here to get some barriers before starting
 		 * the operation. The command(s) need to be in physical memory
@@ -491,6 +495,8 @@ static irqreturn_t aspeed_xdma_irq(int irq, void *arg)
 	spin_lock(&ctx->engine_lock);
 	status = aspeed_xdma_readl(ctx, ctx->chip->regs.status);
 
+	trace_xdma_irq(status);
+
 	if (status & ctx->chip->status_bits.ds_dirty) {
 		aspeed_xdma_done(ctx, true);
 	} else {
@@ -515,6 +521,8 @@ static void aspeed_xdma_reset(struct aspeed_xdma *ctx)
 {
 	unsigned long flags;
 
+	trace_xdma_reset(ctx);
+
 	reset_control_assert(ctx->reset);
 	usleep_range(XDMA_ENGINE_SETUP_TIME_MIN_US,
 		     XDMA_ENGINE_SETUP_TIME_MAX_US);
@@ -545,7 +553,7 @@ static irqreturn_t aspeed_xdma_pcie_irq(int irq, void *arg)
 {
 	struct aspeed_xdma *ctx = arg;
 
-	dev_dbg(ctx->dev, "PCI-E reset requested.\n");
+	trace_xdma_perst(ctx);
 
 	spin_lock(&ctx->engine_lock);
 	if (ctx->in_reset) {
@@ -683,6 +691,7 @@ static void aspeed_xdma_vma_close(struct vm_area_struct *vma)
 
 	gen_pool_free(client->ctx->pool, (unsigned long)client->virt,
 		      client->size);
+	trace_xdma_unmap(client);
 
 	client->virt = NULL;
 	client->phys = 0;
@@ -707,6 +716,7 @@ static int aspeed_xdma_mmap(struct file *file, struct vm_area_struct *vma)
 	client->virt = gen_pool_dma_alloc(ctx->pool, client->size,
 					  &client->phys);
 	if (!client->virt) {
+		trace_xdma_mmap_error(client, 0UL);
 		client->phys = 0;
 		client->size = 0;
 		return -ENOMEM;
@@ -726,12 +736,14 @@ static int aspeed_xdma_mmap(struct file *file, struct vm_area_struct *vma)
 		gen_pool_free(ctx->pool, (unsigned long)client->virt,
 			      client->size);
 
+		trace_xdma_mmap_error(client, vma->vm_start);
 		client->virt = NULL;
 		client->phys = 0;
 		client->size = 0;
 		return rc;
 	}
 
+	trace_xdma_mmap(client);
 	dev_dbg(ctx->dev, "mmap: v[%08lx] to p[%08x], s[%08x]\n",
 		vma->vm_start, (u32)client->phys, client->size);
 
@@ -777,9 +789,11 @@ static int aspeed_xdma_release(struct inode *inode, struct file *file)
 	if (reset)
 		aspeed_xdma_reset(ctx);
 
-	if (client->virt)
+	if (client->virt) {
 		gen_pool_free(ctx->pool, (unsigned long)client->virt,
 			      client->size);
+		trace_xdma_unmap(client);
+	}
 
 	kfree(client);
 	kobject_put(&ctx->kobj);
diff --git a/include/trace/events/xdma.h b/include/trace/events/xdma.h
new file mode 100644
index 0000000000000..ac3cdd3ee898e
--- /dev/null
+++ b/include/trace/events/xdma.h
@@ -0,0 +1,126 @@
+/* SPDX-License-Identifier: GPL-2.0 */
+
+#undef TRACE_SYSTEM
+#define TRACE_SYSTEM xdma
+
+#if !defined(_TRACE_XDMA_H) || defined(TRACE_HEADER_MULTI_READ)
+#define _TRACE_XDMA_H
+
+#include <linux/tracepoint.h>
+
+TRACE_EVENT(xdma_start,
+	    TP_PROTO(const struct aspeed_xdma *ctx, const struct aspeed_xdma_cmd *cmd),
+	    TP_ARGS(ctx, cmd),
+	    TP_STRUCT__entry(__field(bool,	dir_upstream)
+			     __field(unsigned int,	index)
+			     __field(__u64,	host)
+			     __field(__u64,	pitch)
+			     __field(__u64,	cmd)
+	    ),
+	    TP_fast_assign(__entry->dir_upstream = ctx->upstream;
+			   __entry->index = ctx->cmd_idx;
+			   __entry->host = cmd->host_addr;
+			   __entry->pitch = cmd->pitch;
+			   __entry->cmd = cmd->cmd;
+	    ),
+	    TP_printk("%s cmd:%u [%08llx %016llx %016llx]",
+		      __entry->dir_upstream ? "upstream" : "downstream",
+		      __entry->index,
+		      __entry->host,
+		      __entry->pitch,
+		      __entry->cmd
+	    )
+);
+
+TRACE_EVENT(xdma_irq,
+	    TP_PROTO(u32 sts),
+	    TP_ARGS(sts),
+	    TP_STRUCT__entry(__field(__u32,	status)
+	    ),
+	    TP_fast_assign(__entry->status = sts;
+	    ),
+	    TP_printk("sts:%08x",
+		      __entry->status
+	    )
+);
+
+TRACE_EVENT(xdma_reset,
+	    TP_PROTO(const struct aspeed_xdma *ctx),
+	    TP_ARGS(ctx),
+	    TP_STRUCT__entry(__field(bool,	dir_upstream)
+			     __field(bool,	in_progress)
+	    ),
+	    TP_fast_assign(__entry->dir_upstream = ctx->upstream;
+			   __entry->in_progress =
+			ctx->current_client ? ctx->current_client->in_progress : false;
+	    ),
+	    TP_printk("%sin progress%s",
+		      __entry->in_progress ? "" : "not ",
+		      __entry->in_progress ? (__entry->dir_upstream ?
+			" upstream" : " downstream") : ""
+	    )
+);
+
+TRACE_EVENT(xdma_perst,
+	    TP_PROTO(const struct aspeed_xdma *ctx),
+	    TP_ARGS(ctx),
+	    TP_STRUCT__entry(__field(bool,	in_reset)
+	    ),
+	    TP_fast_assign(__entry->in_reset = ctx->in_reset;
+	    ),
+	    TP_printk("%s",
+		      __entry->in_reset ? "in reset" : ""
+	    )
+);
+
+TRACE_EVENT(xdma_unmap,
+	    TP_PROTO(const struct aspeed_xdma_client *client),
+	    TP_ARGS(client),
+	    TP_STRUCT__entry(__field(__u32,	phys)
+			     __field(__u32,	size)
+	    ),
+	    TP_fast_assign(__entry->phys = client->phys;
+			   __entry->size = client->size;
+	    ),
+	    TP_printk("p:%08x s:%08x",
+		      __entry->phys,
+		      __entry->size
+	    )
+);
+
+TRACE_EVENT(xdma_mmap_error,
+	    TP_PROTO(const struct aspeed_xdma_client *client, unsigned long vm_start),
+	    TP_ARGS(client, vm_start),
+	    TP_STRUCT__entry(__field(__u32,	phys)
+			     __field(__u32,	size)
+			     __field(unsigned long,	vm_start)
+	    ),
+	    TP_fast_assign(__entry->phys = client->phys;
+			   __entry->size = client->size;
+			   __entry->vm_start = vm_start;
+	    ),
+	    TP_printk("p:%08x s:%08x v:%08lx",
+		      __entry->phys,
+		      __entry->size,
+		      __entry->vm_start
+	    )
+);
+
+TRACE_EVENT(xdma_mmap,
+	    TP_PROTO(const struct aspeed_xdma_client *client),
+	    TP_ARGS(client),
+	    TP_STRUCT__entry(__field(__u32,	phys)
+			     __field(__u32,	size)
+	    ),
+	    TP_fast_assign(__entry->phys = client->phys;
+			   __entry->size = client->size;
+	    ),
+	    TP_printk("p:%08x s:%08x",
+		      __entry->phys,
+		      __entry->size
+	    )
+);
+
+#endif /* _TRACE_XDMA_H */
+
+#include <trace/define_trace.h>
-- 
2.48.1



More information about the openbmc mailing list