Commit 57d4e267 authored by AngeloGioacchino Del Regno's avatar AngeloGioacchino Del Regno Committed by Steven Price

drm/panfrost: Perform hard reset to recover GPU if soft reset fails

Even though soft reset should ideally never fail, during development of
some power management features I managed to get some bits wrong: this
resulted in GPU soft reset failures, where the GPU was never able to
recover, not even after suspend/resume cycles, meaning that the only
way to get functionality back was to reboot the machine.

Perform a hard reset after a soft reset failure to be able to recover
the GPU during runtime (so, without any machine reboot).
Signed-off-by: default avatarAngeloGioacchino Del Regno <angelogioacchino.delregno@collabora.com>
Reviewed-by: default avatarSteven Price <steven.price@arm.com>
Signed-off-by: default avatarSteven Price <steven.price@arm.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20231109102543.42971-2-angelogioacchino.delregno@collabora.com
parent 22aa1a20
...@@ -60,14 +60,21 @@ int panfrost_gpu_soft_reset(struct panfrost_device *pfdev) ...@@ -60,14 +60,21 @@ int panfrost_gpu_soft_reset(struct panfrost_device *pfdev)
gpu_write(pfdev, GPU_INT_MASK, 0); gpu_write(pfdev, GPU_INT_MASK, 0);
gpu_write(pfdev, GPU_INT_CLEAR, GPU_IRQ_RESET_COMPLETED); gpu_write(pfdev, GPU_INT_CLEAR, GPU_IRQ_RESET_COMPLETED);
gpu_write(pfdev, GPU_CMD, GPU_CMD_SOFT_RESET);
gpu_write(pfdev, GPU_CMD, GPU_CMD_SOFT_RESET);
ret = readl_relaxed_poll_timeout(pfdev->iomem + GPU_INT_RAWSTAT, ret = readl_relaxed_poll_timeout(pfdev->iomem + GPU_INT_RAWSTAT,
val, val & GPU_IRQ_RESET_COMPLETED, 100, 10000); val, val & GPU_IRQ_RESET_COMPLETED, 100, 10000);
if (ret) { if (ret) {
dev_err(pfdev->dev, "gpu soft reset timed out\n"); dev_err(pfdev->dev, "gpu soft reset timed out, attempting hard reset\n");
return ret;
gpu_write(pfdev, GPU_CMD, GPU_CMD_HARD_RESET);
ret = readl_relaxed_poll_timeout(pfdev->iomem + GPU_INT_RAWSTAT, val,
val & GPU_IRQ_RESET_COMPLETED, 100, 10000);
if (ret) {
dev_err(pfdev->dev, "gpu hard reset timed out\n");
return ret;
}
} }
gpu_write(pfdev, GPU_INT_CLEAR, GPU_IRQ_MASK_ALL); gpu_write(pfdev, GPU_INT_CLEAR, GPU_IRQ_MASK_ALL);
......
...@@ -44,6 +44,7 @@ ...@@ -44,6 +44,7 @@
GPU_IRQ_MULTIPLE_FAULT) GPU_IRQ_MULTIPLE_FAULT)
#define GPU_CMD 0x30 #define GPU_CMD 0x30
#define GPU_CMD_SOFT_RESET 0x01 #define GPU_CMD_SOFT_RESET 0x01
#define GPU_CMD_HARD_RESET 0x02
#define GPU_CMD_PERFCNT_CLEAR 0x03 #define GPU_CMD_PERFCNT_CLEAR 0x03
#define GPU_CMD_PERFCNT_SAMPLE 0x04 #define GPU_CMD_PERFCNT_SAMPLE 0x04
#define GPU_CMD_CYCLE_COUNT_START 0x05 #define GPU_CMD_CYCLE_COUNT_START 0x05
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment