Unverified Commit 509433d8 authored by Maíra Canal's avatar Maíra Canal
Browse files

drm/v3d: Expose the total GPU usage stats on sysfs



The previous patch exposed the accumulated amount of active time per
client for each V3D queue. But this doesn't provide a global notion of
the GPU usage.

Therefore, provide the accumulated amount of active time for each V3D
queue (BIN, RENDER, CSD, TFU and CACHE_CLEAN), considering all the jobs
submitted to the queue, independent of the client.

This data is exposed through the sysfs interface, so that if the
interface is queried at two different points of time the usage percentage
of each of the queues can be calculated.

Co-developed-by: default avatarJose Maria Casanova Crespo <jmcasanova@igalia.com>
Signed-off-by: default avatarJose Maria Casanova Crespo <jmcasanova@igalia.com>
Signed-off-by: default avatarMaíra Canal <mcanal@igalia.com>
Acked-by: default avatarJose Maria Casanova Crespo <jmcasanova@igalia.com>
Reviewed-by: default avatarMelissa Wen <mwen@igalia.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20230905213416.1290219-3-mcanal@igalia.com
parent 09a93cc4
Loading
Loading
Loading
Loading
+2 −1
Original line number Diff line number Diff line
@@ -11,7 +11,8 @@ v3d-y := \
	v3d_mmu.o \
	v3d_perfmon.o \
	v3d_trace_points.o \
	v3d_sched.o
	v3d_sched.o \
	v3d_sysfs.o

v3d-$(CONFIG_DEBUG_FS) += v3d_debugfs.o

+9 −0
Original line number Diff line number Diff line
@@ -316,8 +316,14 @@ static int v3d_platform_drm_probe(struct platform_device *pdev)
	if (ret)
		goto irq_disable;

	ret = v3d_sysfs_init(dev);
	if (ret)
		goto drm_unregister;

	return 0;

drm_unregister:
	drm_dev_unregister(drm);
irq_disable:
	v3d_irq_disable(v3d);
gem_destroy:
@@ -331,6 +337,9 @@ static void v3d_platform_drm_remove(struct platform_device *pdev)
{
	struct drm_device *drm = platform_get_drvdata(pdev);
	struct v3d_dev *v3d = to_v3d_dev(drm);
	struct device *dev = &pdev->dev;

	v3d_sysfs_destroy(dev);

	drm_dev_unregister(drm);

+8 −0
Original line number Diff line number Diff line
@@ -38,6 +38,10 @@ struct v3d_queue_state {

	u64 fence_context;
	u64 emit_seqno;

	u64 start_ns;
	u64 enabled_ns;
	u64 jobs_sent;
};

/* Performance monitor object. The perform lifetime is controlled by userspace
@@ -441,3 +445,7 @@ int v3d_perfmon_destroy_ioctl(struct drm_device *dev, void *data,
			      struct drm_file *file_priv);
int v3d_perfmon_get_values_ioctl(struct drm_device *dev, void *data,
				 struct drm_file *file_priv);

/* v3d_sysfs.c */
int v3d_sysfs_init(struct device *dev);
void v3d_sysfs_destroy(struct device *dev);
+5 −1
Original line number Diff line number Diff line
@@ -1014,8 +1014,12 @@ v3d_gem_init(struct drm_device *dev)
	u32 pt_size = 4096 * 1024;
	int ret, i;

	for (i = 0; i < V3D_MAX_QUEUES; i++)
	for (i = 0; i < V3D_MAX_QUEUES; i++) {
		v3d->queue[i].fence_context = dma_fence_context_alloc(1);
		v3d->queue[i].start_ns = 0;
		v3d->queue[i].enabled_ns = 0;
		v3d->queue[i].jobs_sent = 0;
	}

	spin_lock_init(&v3d->mm_lock);
	spin_lock_init(&v3d->job_lock);
+28 −0
Original line number Diff line number Diff line
@@ -103,10 +103,17 @@ v3d_irq(int irq, void *arg)
		struct v3d_fence *fence =
			to_v3d_fence(v3d->bin_job->base.irq_fence);
		struct v3d_file_priv *file = v3d->bin_job->base.file->driver_priv;
		u64 runtime = local_clock() - file->start_ns[V3D_BIN];

		file->enabled_ns[V3D_BIN] += local_clock() - file->start_ns[V3D_BIN];
		file->jobs_sent[V3D_BIN]++;
		v3d->queue[V3D_BIN].jobs_sent++;

		file->start_ns[V3D_BIN] = 0;
		v3d->queue[V3D_BIN].start_ns = 0;

		file->enabled_ns[V3D_BIN] += runtime;
		v3d->queue[V3D_BIN].enabled_ns += runtime;

		trace_v3d_bcl_irq(&v3d->drm, fence->seqno);
		dma_fence_signal(&fence->base);
@@ -117,10 +124,17 @@ v3d_irq(int irq, void *arg)
		struct v3d_fence *fence =
			to_v3d_fence(v3d->render_job->base.irq_fence);
		struct v3d_file_priv *file = v3d->render_job->base.file->driver_priv;
		u64 runtime = local_clock() - file->start_ns[V3D_RENDER];

		file->enabled_ns[V3D_RENDER] += local_clock() - file->start_ns[V3D_RENDER];
		file->jobs_sent[V3D_RENDER]++;
		v3d->queue[V3D_RENDER].jobs_sent++;

		file->start_ns[V3D_RENDER] = 0;
		v3d->queue[V3D_RENDER].start_ns = 0;

		file->enabled_ns[V3D_RENDER] += runtime;
		v3d->queue[V3D_RENDER].enabled_ns += runtime;

		trace_v3d_rcl_irq(&v3d->drm, fence->seqno);
		dma_fence_signal(&fence->base);
@@ -131,10 +145,17 @@ v3d_irq(int irq, void *arg)
		struct v3d_fence *fence =
			to_v3d_fence(v3d->csd_job->base.irq_fence);
		struct v3d_file_priv *file = v3d->csd_job->base.file->driver_priv;
		u64 runtime = local_clock() - file->start_ns[V3D_CSD];

		file->enabled_ns[V3D_CSD] += local_clock() - file->start_ns[V3D_CSD];
		file->jobs_sent[V3D_CSD]++;
		v3d->queue[V3D_CSD].jobs_sent++;

		file->start_ns[V3D_CSD] = 0;
		v3d->queue[V3D_CSD].start_ns = 0;

		file->enabled_ns[V3D_CSD] += runtime;
		v3d->queue[V3D_CSD].enabled_ns += runtime;

		trace_v3d_csd_irq(&v3d->drm, fence->seqno);
		dma_fence_signal(&fence->base);
@@ -172,10 +193,17 @@ v3d_hub_irq(int irq, void *arg)
		struct v3d_fence *fence =
			to_v3d_fence(v3d->tfu_job->base.irq_fence);
		struct v3d_file_priv *file = v3d->tfu_job->base.file->driver_priv;
		u64 runtime = local_clock() - file->start_ns[V3D_TFU];

		file->enabled_ns[V3D_TFU] += local_clock() - file->start_ns[V3D_TFU];
		file->jobs_sent[V3D_TFU]++;
		v3d->queue[V3D_TFU].jobs_sent++;

		file->start_ns[V3D_TFU] = 0;
		v3d->queue[V3D_TFU].start_ns = 0;

		file->enabled_ns[V3D_TFU] += runtime;
		v3d->queue[V3D_TFU].enabled_ns += runtime;

		trace_v3d_tfu_irq(&v3d->drm, fence->seqno);
		dma_fence_signal(&fence->base);
Loading