[PATCH v9 04/10] drm: renesas: rz-du: Reference the DRM device by pointer

From: Tommaso Merciai

Date: Fri Oct 23 2026 - 12:52:30 EST


struct rzg2l_du_device embeds the DRM device, which makes a DU instance
and the DRM device one and the same. RZ/G3E has two instances that have
to share a single DRM device.

In preparation of supporting it, reference the DRM device by pointer and
give it a container of its own. The instance is allocated with the DRM
device rather than with the platform device, as the CRTC and VSP cleanup
handlers point into it and run once the DRM device is released.

No functional change intended.

Signed-off-by: Tommaso Merciai <tommaso.merciai.xr@xxxxxxxxxxxxxx>
---
v8->v9:
- New patch.

drivers/gpu/drm/renesas/rz-du/rzg2l_du_crtc.c | 2 +-
drivers/gpu/drm/renesas/rz-du/rzg2l_du_drv.c | 39 ++++++++++++-------
drivers/gpu/drm/renesas/rz-du/rzg2l_du_drv.h | 7 +---
.../gpu/drm/renesas/rz-du/rzg2l_du_encoder.c | 8 ++--
.../gpu/drm/renesas/rz-du/rzg2l_du_encoder.h | 1 +
drivers/gpu/drm/renesas/rz-du/rzg2l_du_kms.c | 2 +-
drivers/gpu/drm/renesas/rz-du/rzg2l_du_vsp.c | 4 +-
7 files changed, 35 insertions(+), 28 deletions(-)

diff --git a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_crtc.c b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_crtc.c
index c57884ab5b9b..398532933013 100644
--- a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_crtc.c
+++ b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_crtc.c
@@ -411,7 +411,7 @@ int rzg2l_du_crtc_create(struct rzg2l_du_device *rcdu)

primary = &rcrtc->vsp->planes[rcrtc->vsp_pipe]->plane;

- ret = drmm_crtc_init_with_planes(&rcdu->ddev, crtc, primary, NULL,
+ ret = drmm_crtc_init_with_planes(rcdu->ddev, crtc, primary, NULL,
&crtc_funcs_rz, NULL);
if (ret < 0)
return ret;
diff --git a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_drv.c b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_drv.c
index 6c2dc86abc7d..84da5a2df8f6 100644
--- a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_drv.c
+++ b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_drv.c
@@ -17,6 +17,7 @@
#include <drm/drm_drv.h>
#include <drm/drm_fbdev_dma.h>
#include <drm/drm_gem_dma_helper.h>
+#include <drm/drm_managed.h>
#include <drm/drm_print.h>
#include <drm/drm_probe_helper.h>

@@ -144,10 +145,14 @@ static const struct drm_driver rzg2l_du_driver = {
* Platform driver
*/

+struct rzg2l_du_drm {
+ struct drm_device ddev;
+};
+
static void rzg2l_du_remove(struct platform_device *pdev)
{
- struct rzg2l_du_device *rcdu = platform_get_drvdata(pdev);
- struct drm_device *ddev = &rcdu->ddev;
+ struct rzg2l_du_drm *rzgdrm = platform_get_drvdata(pdev);
+ struct drm_device *ddev = &rzgdrm->ddev;

drm_dev_unregister(ddev);
drm_atomic_helper_shutdown(ddev);
@@ -157,29 +162,35 @@ static void rzg2l_du_remove(struct platform_device *pdev)

static void rzg2l_du_shutdown(struct platform_device *pdev)
{
- struct rzg2l_du_device *rcdu = platform_get_drvdata(pdev);
+ struct rzg2l_du_drm *rzgdrm = platform_get_drvdata(pdev);

- drm_atomic_helper_shutdown(&rcdu->ddev);
+ drm_atomic_helper_shutdown(&rzgdrm->ddev);
}

static int rzg2l_du_probe(struct platform_device *pdev)
{
struct rzg2l_du_device *rcdu;
+ struct rzg2l_du_drm *rzgdrm;
int ret;

if (drm_firmware_drivers_only())
return -ENODEV;

/* Allocate and initialize the RZ/G2L device structure. */
- rcdu = devm_drm_dev_alloc(&pdev->dev, &rzg2l_du_driver,
- struct rzg2l_du_device, ddev);
- if (IS_ERR(rcdu))
- return PTR_ERR(rcdu);
+ rzgdrm = devm_drm_dev_alloc(&pdev->dev, &rzg2l_du_driver,
+ struct rzg2l_du_drm, ddev);
+ if (IS_ERR(rzgdrm))
+ return PTR_ERR(rzgdrm);
+
+ platform_set_drvdata(pdev, rzgdrm);
+
+ rcdu = drmm_kzalloc(&rzgdrm->ddev, sizeof(*rcdu), GFP_KERNEL);
+ if (!rcdu)
+ return -ENOMEM;

rcdu->dev = &pdev->dev;
rcdu->info = of_device_get_match_data(rcdu->dev);
-
- platform_set_drvdata(pdev, rcdu);
+ rcdu->ddev = &rzgdrm->ddev;

/* I/O resources */
rcdu->mmio = devm_platform_ioremap_resource(pdev, 0);
@@ -207,18 +218,18 @@ static int rzg2l_du_probe(struct platform_device *pdev)
* Register the DRM device with the core and the connectors with
* sysfs.
*/
- ret = drm_dev_register(&rcdu->ddev, 0);
+ ret = drm_dev_register(&rzgdrm->ddev, 0);
if (ret)
goto error;

- drm_info(&rcdu->ddev, "Device %s probed\n", dev_name(&pdev->dev));
+ drm_info(&rzgdrm->ddev, "Device %s probed\n", dev_name(&pdev->dev));

- drm_client_setup(&rcdu->ddev, NULL);
+ drm_client_setup(&rzgdrm->ddev, NULL);

return 0;

error:
- drm_kms_helper_poll_fini(&rcdu->ddev);
+ drm_kms_helper_poll_fini(&rzgdrm->ddev);
return ret;
}

diff --git a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_drv.h b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_drv.h
index e9626ef37cde..47ceaf892339 100644
--- a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_drv.h
+++ b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_drv.h
@@ -69,7 +69,7 @@ struct rzg2l_du_device {

void __iomem *mmio;

- struct drm_device ddev;
+ struct drm_device *ddev;

struct rzg2l_du_crtc crtcs[RZG2L_DU_MAX_CRTCS];
unsigned int num_crtcs;
@@ -77,11 +77,6 @@ struct rzg2l_du_device {
struct rzg2l_du_vsp vsps[RZG2L_DU_MAX_VSPS];
};

-static inline struct rzg2l_du_device *to_rzg2l_du_device(struct drm_device *dev)
-{
- return container_of(dev, struct rzg2l_du_device, ddev);
-}
-
static inline bool rzg2l_du_has(struct rzg2l_du_device *rcdu,
unsigned int feature)
{
diff --git a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_encoder.c b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_encoder.c
index a1b48973aa8e..5c21c5f9fbaf 100644
--- a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_encoder.c
+++ b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_encoder.c
@@ -52,8 +52,7 @@ rzg2l_du_encoder_mode_valid(struct drm_encoder *encoder,
const struct drm_display_mode *mode)
{
struct rzg2l_du_encoder *renc = to_rzg2l_encoder(encoder);
- struct rzg2l_du_device *rcdu = to_rzg2l_du_device(renc->base.dev);
- const struct rzg2l_du_device_info *info = rcdu->info;
+ const struct rzg2l_du_device_info *info = renc->dev->info;

if (renc->output != RZG2L_DU_OUTPUT_DPAD0)
return MODE_OK;
@@ -133,12 +132,13 @@ int rzg2l_du_encoder_init(struct rzg2l_du_device *rcdu,
dev_dbg(rcdu->dev, "initializing encoder %pOF for output %s\n",
enc_node, rzg2l_du_output_name(output));

- renc = drmm_encoder_alloc(&rcdu->ddev, struct rzg2l_du_encoder, base,
+ renc = drmm_encoder_alloc(rcdu->ddev, struct rzg2l_du_encoder, base,
&rzg2l_du_encoder_funcs, DRM_MODE_ENCODER_NONE,
NULL);
if (IS_ERR(renc))
return PTR_ERR(renc);

+ renc->dev = rcdu;
renc->output = output;
drm_encoder_helper_add(&renc->base, &rzg2l_du_encoder_helper_funcs);

@@ -153,7 +153,7 @@ int rzg2l_du_encoder_init(struct rzg2l_du_device *rcdu,
}

/* Create the connector for the chain of bridges. */
- connector = drm_bridge_connector_init(&rcdu->ddev, &renc->base);
+ connector = drm_bridge_connector_init(rcdu->ddev, &renc->base);
if (IS_ERR(connector)) {
dev_err(rcdu->dev,
"failed to created connector for output %s (%ld)\n",
diff --git a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_encoder.h b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_encoder.h
index 3e430c1f6132..dfffcc14e0a3 100644
--- a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_encoder.h
+++ b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_encoder.h
@@ -17,6 +17,7 @@ struct rzg2l_du_device;

struct rzg2l_du_encoder {
struct drm_encoder base;
+ struct rzg2l_du_device *dev;
enum rzg2l_du_output output;
};

diff --git a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_kms.c b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_kms.c
index 87f171145a23..13d14ecacba9 100644
--- a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_kms.c
+++ b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_kms.c
@@ -402,7 +402,7 @@ static int rzg2l_du_vsps_init(struct rzg2l_du_device *rcdu)

int rzg2l_du_modeset_init(struct rzg2l_du_device *rcdu)
{
- struct drm_device *dev = &rcdu->ddev;
+ struct drm_device *dev = rcdu->ddev;
struct drm_encoder *encoder;
unsigned int num_encoders;
int ret;
diff --git a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_vsp.c b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_vsp.c
index 12fe35740c62..4df4f0ff0ed5 100644
--- a/drivers/gpu/drm/renesas/rz-du/rzg2l_du_vsp.c
+++ b/drivers/gpu/drm/renesas/rz-du/rzg2l_du_vsp.c
@@ -298,7 +298,7 @@ int rzg2l_du_vsp_init(struct rzg2l_du_vsp *vsp, struct device_node *np,

vsp->vsp = &pdev->dev;

- ret = drmm_add_action_or_reset(&rcdu->ddev, rzg2l_du_vsp_cleanup, vsp);
+ ret = drmm_add_action_or_reset(rcdu->ddev, rzg2l_du_vsp_cleanup, vsp);
if (ret < 0)
return ret;

@@ -324,7 +324,7 @@ int rzg2l_du_vsp_init(struct rzg2l_du_vsp *vsp, struct device_node *np,
: DRM_PLANE_TYPE_OVERLAY;
struct rzg2l_du_vsp_plane *plane;

- plane = drmm_universal_plane_alloc(&rcdu->ddev, struct rzg2l_du_vsp_plane,
+ plane = drmm_universal_plane_alloc(rcdu->ddev, struct rzg2l_du_vsp_plane,
plane, crtcs, &rzg2l_du_vsp_plane_funcs,
rzg2l_du_vsp_formats,
ARRAY_SIZE(rzg2l_du_vsp_formats),
--
2.54.0