[PATCH v2 18/28] drm/panthor: Route arbitration events
From: Karunika Choo
Date: Tue Nov 10 2026 - 10:51:05 EST
Connect resource-group message handling, the arbitration scheduler and
partition control.
Forward GPU request and idle messages to the scheduler. When a partition
reset completes after firmware yields GPU access or a CLOSE_WINDOW
command, report the active access window as stopped.
Add callbacks that let the scheduler grant GPU access, request a yield
and close access windows.
Signed-off-by: Karunika Choo <karunika.choo@xxxxxxx>
---
v2:
- Align with sched to AW interface changes.
v1:
- Notify arbitration scheduler when RESET_DONE completes due to
close_window, as well as due to yield by Panthor FW.
.../panthor/arbitration/panthor_arbitration.h | 6 ++++
.../arbitration/panthor_arbitration_drv.c | 28 +++++++++++++++++--
.../arbitration/panthor_partition_control.c | 9 ++++++
.../arbitration/panthor_resource_group.c | 4 +--
4 files changed, 42 insertions(+), 5 deletions(-)
diff --git a/drivers/gpu/drm/panthor/arbitration/panthor_arbitration.h b/drivers/gpu/drm/panthor/arbitration/panthor_arbitration.h
index 8d4c0aab12666..1350a5982a93b 100644
--- a/drivers/gpu/drm/panthor/arbitration/panthor_arbitration.h
+++ b/drivers/gpu/drm/panthor/arbitration/panthor_arbitration.h
@@ -34,6 +34,12 @@ struct panthor_arbitration {
struct panthor_arbitration_sched *sched[AM_ARB_MAX_PC_COUNT];
};
+/* AW to Arbiter events */
+int panthor_arbitration_on_request(struct panthor_arbitration *adev, u8 aw_id);
+int panthor_arbitration_on_idle(struct panthor_arbitration *adev, u8 aw_id);
+int panthor_arbitration_on_stopped(struct panthor_arbitration *adev, u8 aw_id);
+
+/* Arbiter to AW events */
int panthor_arbitration_on_grant(struct panthor_arbitration *adev, u8 sched_id, u8 aw_id);
int panthor_arbitration_on_stop(struct panthor_arbitration *adev, u8 sched_id);
int panthor_arbitration_on_close(struct panthor_arbitration *adev, u8 sched_id);
diff --git a/drivers/gpu/drm/panthor/arbitration/panthor_arbitration_drv.c b/drivers/gpu/drm/panthor/arbitration/panthor_arbitration_drv.c
index f26dcdcbc9198..48016d0d88557 100644
--- a/drivers/gpu/drm/panthor/arbitration/panthor_arbitration_drv.c
+++ b/drivers/gpu/drm/panthor/arbitration/panthor_arbitration_drv.c
@@ -57,20 +57,42 @@ static int panthor_arbitration_runtime_resume(struct device *dev)
return 0;
}
+/* AW to Arbiter events */
+int panthor_arbitration_on_request(struct panthor_arbitration *adev, u8 aw_id)
+{
+ /* TODO: AW to PC assignment */
+ return panthor_arbitration_sched_on_request(adev->sched[0], aw_id);
+}
+
+int panthor_arbitration_on_idle(struct panthor_arbitration *adev, u8 aw_id)
+{
+ /* TODO: AW to PC assignment */
+ return panthor_arbitration_sched_on_idle(adev->sched[0], aw_id);
+}
+
+int panthor_arbitration_on_stopped(struct panthor_arbitration *adev, u8 aw_id)
+{
+ /* TODO: AW to PC assignment */
+ return panthor_arbitration_sched_on_stopped(adev->sched[0], aw_id);
+}
+
/* Arbiter to AW events */
int panthor_arbitration_on_grant(struct panthor_arbitration *adev, u8 sched_id, u8 aw_id)
{
- return 0;
+ /* TODO: AW to PC assignment */
+ return panthor_partition_control_open_window(adev->pc[0], aw_id);
}
int panthor_arbitration_on_stop(struct panthor_arbitration *adev, u8 sched_id)
{
- return 0;
+ /* TODO: AW to PC assignment */
+ return panthor_partition_control_yield_now(adev->pc[0]);
}
int panthor_arbitration_on_close(struct panthor_arbitration *adev, u8 sched_id)
{
- return 0;
+ /* TODO: AW to PC assignment */
+ return panthor_partition_control_close_window(adev->pc[0]);
}
static int panthor_arbitration_probe(struct platform_device *pdev)
diff --git a/drivers/gpu/drm/panthor/arbitration/panthor_partition_control.c b/drivers/gpu/drm/panthor/arbitration/panthor_partition_control.c
index 330d0bf5fd375..d8fdafbf31864 100644
--- a/drivers/gpu/drm/panthor/arbitration/panthor_partition_control.c
+++ b/drivers/gpu/drm/panthor/arbitration/panthor_partition_control.c
@@ -198,13 +198,22 @@ static int window_open(struct panthor_partition_control *pc, u8 aw_id)
static void partition_handle_reset_done(struct panthor_partition_control *pc)
{
+ bool notify_stopped = false;
+ int aw_id;
+
scoped_guard(spinlock_irqsave, &pc->lock) {
+ aw_id = pc->current_aw;
pc->current_aw = AW_UNASSIGNED;
/* RESET_DONE from CLOSE_WINDOW */
if (pc->closing)
pc->closing = false;
+ if (aw_id >= 0)
+ notify_stopped = true;
}
+
+ if (notify_stopped)
+ panthor_arbitration_on_stopped(dev_get_drvdata(pc->dev), aw_id);
}
static irqreturn_t partition_irq_raw_handler(int irq, void *data)
diff --git a/drivers/gpu/drm/panthor/arbitration/panthor_resource_group.c b/drivers/gpu/drm/panthor/arbitration/panthor_resource_group.c
index e413cfd9e6d25..26b22461f6d39 100644
--- a/drivers/gpu/drm/panthor/arbitration/panthor_resource_group.c
+++ b/drivers/gpu/drm/panthor/arbitration/panthor_resource_group.c
@@ -163,10 +163,10 @@ static void rg_handle_message(struct panthor_resource_group *rg, u8 aw_id,
switch (msg_id) {
case VM_ARB_GPU_REQUEST:
- /* TODO: on_request */
+ panthor_arbitration_on_request(dev_get_drvdata(rg->dev), aw_id);
break;
case VM_ARB_GPU_STOPPED:
- /* TODO: on_idle */
+ panthor_arbitration_on_idle(dev_get_drvdata(rg->dev), aw_id);
break;
default:
dev_warn(rg->dev, "Invalid message (0x%llx)", message);
--
2.43.0