On 13/05/2026 13:00, Alexandru Dadu wrote: > Add support for workload submission trace points. > > Co-developed-by: Donald Robson <[email protected]> > Signed-off-by: Donald Robson <[email protected]> > Signed-off-by: Alexandru Dadu <[email protected]>
Reviewed-by: Matt Coster <[email protected]> > --- > drivers/gpu/drm/imagination/Makefile | 3 + > drivers/gpu/drm/imagination/pvr_drv.c | 3 + > drivers/gpu/drm/imagination/pvr_job.c | 3 + > drivers/gpu/drm/imagination/pvr_queue.c | 5 ++ > drivers/gpu/drm/imagination/pvr_trace.h | 113 > +++++++++++++++++++++++++ > drivers/gpu/drm/imagination/pvr_trace_points.c | 7 ++ > 6 files changed, 134 insertions(+) > > diff --git a/drivers/gpu/drm/imagination/Makefile > b/drivers/gpu/drm/imagination/Makefile > index 1222a14262e4..a5c5e386f16a 100644 > --- a/drivers/gpu/drm/imagination/Makefile > +++ b/drivers/gpu/drm/imagination/Makefile > @@ -32,6 +32,9 @@ powervr-y := \ > powervr-$(CONFIG_DEBUG_FS) += \ > pvr_debugfs.o > > +powervr-$(CONFIG_TRACEPOINTS) += \ > + pvr_trace_points.o > + > obj-$(CONFIG_DRM_POWERVR) += powervr.o > > obj-$(CONFIG_DRM_POWERVR_KUNIT_TEST) += pvr_test.o > diff --git a/drivers/gpu/drm/imagination/pvr_drv.c > b/drivers/gpu/drm/imagination/pvr_drv.c > index 268900464ab6..b20c462bcba0 100644 > --- a/drivers/gpu/drm/imagination/pvr_drv.c > +++ b/drivers/gpu/drm/imagination/pvr_drv.c > @@ -14,6 +14,7 @@ > #include "pvr_rogue_defs.h" > #include "pvr_rogue_fwif_client.h" > #include "pvr_rogue_fwif_shared.h" > +#include "pvr_trace.h" > #include "pvr_vm.h" > > #include <uapi/drm/pvr_drm.h> > @@ -1150,6 +1151,8 @@ pvr_ioctl_submit_jobs(struct drm_device *drm_dev, void > *raw_args, > int idx; > int err; > > + trace_pvr_job_submit_ioctl(pvr_dev, args->jobs.count); > + > if (!drm_dev_enter(drm_dev, &idx)) > return -EIO; > > diff --git a/drivers/gpu/drm/imagination/pvr_job.c > b/drivers/gpu/drm/imagination/pvr_job.c > index dd9f5df01e08..b8a58d817009 100644 > --- a/drivers/gpu/drm/imagination/pvr_job.c > +++ b/drivers/gpu/drm/imagination/pvr_job.c > @@ -14,6 +14,7 @@ > #include "pvr_stream.h" > #include "pvr_stream_defs.h" > #include "pvr_sync.h" > +#include "pvr_trace.h" > > #include <drm/drm_exec.h> > #include <drm/drm_gem.h> > @@ -510,6 +511,8 @@ static int pvr_job_data_init(struct pvr_device *pvr_dev, > } > > job_data_out[i].sync_op_count = job_args[i].sync_ops.count; > + > + trace_pvr_job_create(pvr_dev, job_data_out[i].job, > job_data_out[i].sync_op_count); > } > > return 0; > diff --git a/drivers/gpu/drm/imagination/pvr_queue.c > b/drivers/gpu/drm/imagination/pvr_queue.c > index d10a13173f0f..3c2331e834fb 100644 > --- a/drivers/gpu/drm/imagination/pvr_queue.c > +++ b/drivers/gpu/drm/imagination/pvr_queue.c > @@ -10,6 +10,7 @@ > #include "pvr_drv.h" > #include "pvr_job.h" > #include "pvr_queue.h" > +#include "pvr_trace.h" > #include "pvr_vm.h" > > #include "pvr_rogue_fwif_client.h" > @@ -725,6 +726,8 @@ static void pvr_queue_submit_job_to_cccb(struct pvr_job > *job) > cmd->partial_render_geom_frag_fence.value = > job->done_fence->seqno - 1; > } > > + trace_pvr_job_submit_fw(job); > + > /* Submit job to FW */ > pvr_cccb_write_command_with_header(cccb, job->fw_ccb_cmd_type, > job->cmd_len, job->cmd, > job->id, job->id); > @@ -1193,6 +1196,8 @@ void pvr_queue_job_cleanup(struct pvr_job *job) > > if (job->base.s_fence) > drm_sched_job_cleanup(&job->base); > + > + trace_pvr_job_done(job); > } > > /** > diff --git a/drivers/gpu/drm/imagination/pvr_trace.h > b/drivers/gpu/drm/imagination/pvr_trace.h > new file mode 100644 > index 000000000000..ffbbde3b2bcc > --- /dev/null > +++ b/drivers/gpu/drm/imagination/pvr_trace.h > @@ -0,0 +1,113 @@ > +/* SPDX-License-Identifier: GPL-2.0 OR MIT */ > +/* Copyright (c) 2026 Imagination Technologies Ltd. */ > + > +#undef TRACE_SYSTEM > +#define TRACE_SYSTEM pvr > + > +#if !defined(PVR_TRACE_H) || defined(TRACE_HEADER_MULTI_READ) > +#define PVR_TRACE_H > + > +#include "pvr_context.h" > +#include "pvr_device.h" > +#include "pvr_fw.h" > +#include "pvr_hwrt.h" > +#include "pvr_job.h" > +#include "pvr_sync.h" > + > +#include <linux/stringify.h> > +#include <linux/types.h> > +#include <linux/tracepoint.h> > + > +/* > + * NOTE: > + * When adding trace points, or extra data to existing ones - you must > capture > + * all the data in the TP_fast_assign section that you wish to use in the > + * TP_printk section. This is because the printk is performed on demand from > the > + * captured data when you `cat /sys/kernel/tracing/trace` and by the time > this > + * happens any pointers you captured will likely no longer point to valid > data. > + */ > + > +/* Job submit */ > + > +TRACE_EVENT(pvr_job_submit_ioctl, > + TP_PROTO(struct pvr_device *pvr_dev, u32 count), > + TP_ARGS(pvr_dev, count), > + TP_STRUCT__entry(__field(struct pvr_device *, pvr_dev) > + __field(u32, count)), > + TP_fast_assign(__entry->pvr_dev = pvr_dev; > + __entry->count = count;), > + TP_printk("pvr_dev=%p count=%u", > + __entry->pvr_dev, > + __entry->count) > +); > + > +#define PVR_JOB_TYPE_TO_STR(val) \ > + __print_symbolic(val, \ > + { DRM_PVR_JOB_TYPE_GEOMETRY, "geometry" }, \ > + { DRM_PVR_JOB_TYPE_FRAGMENT, "fragment" }, \ > + { DRM_PVR_JOB_TYPE_COMPUTE, "compute" }, \ > + { DRM_PVR_JOB_TYPE_TRANSFER_FRAG, "transfer" }) > + > +TRACE_EVENT(pvr_job_create, > + TP_PROTO(struct pvr_device *pvr_dev, struct pvr_job *job, > + u32 sync_op_count), > + TP_ARGS(pvr_dev, job, sync_op_count), > + TP_STRUCT__entry(__field(struct pvr_device *, pvr_dev) > + __field(struct pvr_context *, ctx) > + __field(struct pvr_fw_object *, fw_obj) > + __field(u32, fw_addr) > + __field(u32, hwrt_addr) > + __field(struct pvr_job *, job) > + __field(enum drm_pvr_job_type, job_type) > + __field(u32, sync_op_count)), > + TP_fast_assign(__entry->pvr_dev = pvr_dev; > + __entry->ctx = job->ctx; > + __entry->fw_obj = job->ctx->fw_obj; > + pvr_fw_object_get_fw_addr(job->ctx->fw_obj, > &__entry->fw_addr); > + __entry->hwrt_addr = job->hwrt ? > + > job->hwrt->fw_obj->fw_addr_offset : > + 0; > + __entry->job = job; > + __entry->job_type = job->type; > + __entry->sync_op_count = sync_op_count;), > + TP_printk("pvr_dev=%p ctx=%p fw_obj=%p fw_addr=0x%x > hwrt_addr=0x%x job=%p job_type=%s sync_op_count=%u", > + __entry->pvr_dev, > + __entry->ctx, > + __entry->fw_obj, > + __entry->fw_addr, > + __entry->hwrt_addr, > + __entry->job, > + PVR_JOB_TYPE_TO_STR(__entry->job_type), > + __entry->sync_op_count) > +); > + > +#undef PVR_JOB_TYPE_TO_STR > + > +TRACE_EVENT(pvr_job_submit_fw, > + TP_PROTO(struct pvr_job *job), > + TP_ARGS(job), > + TP_STRUCT__entry(__field(struct pvr_job *, job) > + __field(u32, done_seqno)), > + TP_fast_assign(__entry->job = job; > + __entry->done_seqno = job->done_fence->seqno;), > + TP_printk("job=%p done_seqno=%u", > + __entry->job, > + __entry->done_seqno) > +); > + > +TRACE_EVENT(pvr_job_done, > + TP_PROTO(struct pvr_job *job), > + TP_ARGS(job), > + TP_STRUCT__entry(__field(struct pvr_job *, job)), > + TP_fast_assign(__entry->job = job;), > + TP_printk("job=%p", __entry->job) > +); > + > +#endif /* PVR_TRACE_H */ > + > +/* This part must be outside protection */ > +#undef TRACE_INCLUDE_PATH > +#undef TRACE_INCLUDE_FILE > +#define TRACE_INCLUDE_PATH ../../drivers/gpu/drm/imagination > +#define TRACE_INCLUDE_FILE pvr_trace > +#include <trace/define_trace.h> > diff --git a/drivers/gpu/drm/imagination/pvr_trace_points.c > b/drivers/gpu/drm/imagination/pvr_trace_points.c > new file mode 100644 > index 000000000000..71b53f267af0 > --- /dev/null > +++ b/drivers/gpu/drm/imagination/pvr_trace_points.c > @@ -0,0 +1,7 @@ > +// SPDX-License-Identifier: GPL-2.0 OR MIT > +/* Copyright (c) 2026 Imagination Technologies Ltd. */ > + > +#ifndef __CHECKER__ > +#define CREATE_TRACE_POINTS > +#include "pvr_trace.h" > +#endif > > --- > base-commit: 921578cf373981eba92774a27f7644a11282cf89 > change-id: 20260512-b4-pvr-trace-points-4d3b66116e15 > > Best regards, > -- > Alexandru Dadu <[email protected]> > -- Matt Coster E: [email protected]
OpenPGP_signature.asc
Description: OpenPGP digital signature
