diff options
| author | Michal Wilczynski <m.wilczynski@samsung.com> | 2025-04-18 13:22:49 +0200 |
|---|---|---|
| committer | Matt Coster <matt.coster@imgtec.com> | 2025-04-24 11:08:48 +0100 |
| commit | 3a2b7389feea9a7afd18d58cda59b7a989445f38 (patch) | |
| tree | 219ddca0920c1ceb273b7bc071e0e55466f6b88d /drivers/gpu/drm/imagination/pvr_power.c | |
| parent | 1300a7f8a7d4c5f88de30312cf34448b96539c23 (diff) | |
drm/imagination: Add reset controller support for GPU initialization
All IMG Rogue GPUs include a reset line that participates in the
power-up sequence. On some SoCs (e.g., T-Head TH1520 and Banana Pi
BPI-F3), this reset line is exposed and must be driven explicitly to
ensure proper initialization. On others, such as the currently
supported TI SoC, the reset logic is handled in hardware or firmware
without exposing the line directly. In platforms where the reset line is
externally accessible, if it is not driven correctly, the GPU may remain
in an undefined state, leading to instability or performance issues.
This commit adds a dedicated reset controller to the drm/imagination
driver. By managing the reset line (where applicable) as part of normal
GPU bring-up, the driver ensures reliable initialization across
platforms regardless of whether the reset is controlled externally or
handled internally.
Signed-off-by: Michal Wilczynski <m.wilczynski@samsung.com>
Reviewed-by: Matt Coster <matt.coster@imgtec.com>
Link: https://lore.kernel.org/r/20250418-apr_18_reset_img-v6-2-85a06757b698@samsung.com
Signed-off-by: Matt Coster <matt.coster@imgtec.com>
Diffstat (limited to 'drivers/gpu/drm/imagination/pvr_power.c')
| -rw-r--r-- | drivers/gpu/drm/imagination/pvr_power.c | 22 |
1 files changed, 21 insertions, 1 deletions
diff --git a/drivers/gpu/drm/imagination/pvr_power.c b/drivers/gpu/drm/imagination/pvr_power.c index 19b079b357df..41f5d89e78b8 100644 --- a/drivers/gpu/drm/imagination/pvr_power.c +++ b/drivers/gpu/drm/imagination/pvr_power.c @@ -18,6 +18,7 @@ #include <linux/platform_device.h> #include <linux/pm_domain.h> #include <linux/pm_runtime.h> +#include <linux/reset.h> #include <linux/timer.h> #include <linux/types.h> #include <linux/workqueue.h> @@ -255,6 +256,8 @@ pvr_power_device_suspend(struct device *dev) clk_disable_unprepare(pvr_dev->sys_clk); clk_disable_unprepare(pvr_dev->core_clk); + err = reset_control_assert(pvr_dev->reset); + err_drm_dev_exit: drm_dev_exit(idx); @@ -285,16 +288,33 @@ pvr_power_device_resume(struct device *dev) if (err) goto err_sys_clk_disable; + /* + * According to the hardware manual, a delay of at least 32 clock + * cycles is required between de-asserting the clkgen reset and + * de-asserting the GPU reset. Assuming a worst-case scenario with + * a very high GPU clock frequency, a delay of 1 microsecond is + * sufficient to ensure this requirement is met across all + * feasible GPU clock speeds. + */ + udelay(1); + + err = reset_control_deassert(pvr_dev->reset); + if (err) + goto err_mem_clk_disable; + if (pvr_dev->fw_dev.booted) { err = pvr_power_fw_enable(pvr_dev); if (err) - goto err_mem_clk_disable; + goto err_reset_assert; } drm_dev_exit(idx); return 0; +err_reset_assert: + reset_control_assert(pvr_dev->reset); + err_mem_clk_disable: clk_disable_unprepare(pvr_dev->mem_clk); |