diff mbox series

[2/2] drm/mediatek: dpi/dsi: fix possible_crtcs calculation

Message ID 20230829131941.3353439-2-mwalle@kernel.org (mailing list archive)
State New, archived
Headers show
Series [1/2] drm/mediathek: fix kernel oops if no crtc is found | expand

Commit Message

Michael Walle Aug. 29, 2023, 1:19 p.m. UTC
mtk_drm_find_possible_crtc_by_comp() assumed that the main path will
always have the CRTC with id 0, the ext id 1 and the third id 2. This
is only true if the paths are all available. But paths are optional (see
also comment in mtk_drm_kms_init()), e.g. the main path might not be
enabled or available at all. Then the CRTC IDs will shift one up, e.g.
ext will be 1 and the third path will be 2.

To fix that, dynamically calculate the IDs by the precence of the paths.

Fixes: 5aa8e7647676 ("drm/mediatek: dpi/dsi: Change the getting possible_crtc way")
Suggested-by: Nícolas F. R. A. Prado <nfraprado@collabora.com>
Signed-off-by: Michael Walle <mwalle@kernel.org>
---
 drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c | 41 ++++++++++++++-------
 1 file changed, 27 insertions(+), 14 deletions(-)

Comments

Nícolas F. R. A. Prado Aug. 29, 2023, 5:50 p.m. UTC | #1
On Tue, Aug 29, 2023 at 03:19:41PM +0200, Michael Walle wrote:
> mtk_drm_find_possible_crtc_by_comp() assumed that the main path will
> always have the CRTC with id 0, the ext id 1 and the third id 2. This
> is only true if the paths are all available. But paths are optional (see
> also comment in mtk_drm_kms_init()), e.g. the main path might not be
> enabled or available at all. Then the CRTC IDs will shift one up, e.g.
> ext will be 1 and the third path will be 2.
> 
> To fix that, dynamically calculate the IDs by the precence of the paths.
> 
> Fixes: 5aa8e7647676 ("drm/mediatek: dpi/dsi: Change the getting possible_crtc way")
> Suggested-by: Nícolas F. R. A. Prado <nfraprado@collabora.com>
> Signed-off-by: Michael Walle <mwalle@kernel.org>
> ---
>  drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c | 41 ++++++++++++++-------
>  1 file changed, 27 insertions(+), 14 deletions(-)
> 
> diff --git a/drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c b/drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c
> index 771f4e173353..f3064bff64e8 100644
> --- a/drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c
> +++ b/drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c
> @@ -526,21 +526,34 @@ unsigned int mtk_drm_find_possible_crtc_by_comp(struct drm_device *drm,
>  						struct device *dev)
>  {
>  	struct mtk_drm_private *private = drm->dev_private;
> -	unsigned int ret = 0;
> -
> -	if (mtk_drm_find_comp_in_ddp(dev, private->data->main_path, private->data->main_len,
> -				     private->ddp_comp))
> -		ret = BIT(0);
> -	else if (mtk_drm_find_comp_in_ddp(dev, private->data->ext_path,
> -					  private->data->ext_len, private->ddp_comp))
> -		ret = BIT(1);
> -	else if (mtk_drm_find_comp_in_ddp(dev, private->data->third_path,
> -					  private->data->third_len, private->ddp_comp))
> -		ret = BIT(2);
> -	else
> -		DRM_INFO("Failed to find comp in ddp table\n");
> +	int i = 0;
> +
> +	if (private->data->main_path) {
> +		if (mtk_drm_find_comp_in_ddp(dev, private->data->main_path,
> +					     private->data->main_len,
> +					     private->ddp_comp))
> +			return BIT(i);
> +		i++;
> +	}
> +
> +	if (private->data->ext_path) {
> +		if (mtk_drm_find_comp_in_ddp(dev, private->data->ext_path,
> +					     private->data->ext_len,
> +					     private->ddp_comp))
> +			return BIT(i);
> +		i++;

This won't work. On MT8195 there are two display IPs, vdosys0 and vdosys1,
vdosys0 only has the main path while vdosys1 only has the external path. So you
need to loop over each one in all_drm_private[j] to get the right crtc ID for
MT8195.

Thanks,
Nícolas
Michael Walle Aug. 30, 2023, 10:55 a.m. UTC | #2
> This won't work. On MT8195 there are two display IPs, vdosys0 and 
> vdosys1,
> vdosys0 only has the main path while vdosys1 only has the external 
> path. So you
> need to loop over each one in all_drm_private[j] to get the right crtc 
> ID for
> MT8195.

Ahh thanks, got it.

-michael
diff mbox series

Patch

diff --git a/drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c b/drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c
index 771f4e173353..f3064bff64e8 100644
--- a/drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c
+++ b/drivers/gpu/drm/mediatek/mtk_drm_ddp_comp.c
@@ -526,21 +526,34 @@  unsigned int mtk_drm_find_possible_crtc_by_comp(struct drm_device *drm,
 						struct device *dev)
 {
 	struct mtk_drm_private *private = drm->dev_private;
-	unsigned int ret = 0;
-
-	if (mtk_drm_find_comp_in_ddp(dev, private->data->main_path, private->data->main_len,
-				     private->ddp_comp))
-		ret = BIT(0);
-	else if (mtk_drm_find_comp_in_ddp(dev, private->data->ext_path,
-					  private->data->ext_len, private->ddp_comp))
-		ret = BIT(1);
-	else if (mtk_drm_find_comp_in_ddp(dev, private->data->third_path,
-					  private->data->third_len, private->ddp_comp))
-		ret = BIT(2);
-	else
-		DRM_INFO("Failed to find comp in ddp table\n");
+	int i = 0;
+
+	if (private->data->main_path) {
+		if (mtk_drm_find_comp_in_ddp(dev, private->data->main_path,
+					     private->data->main_len,
+					     private->ddp_comp))
+			return BIT(i);
+		i++;
+	}
+
+	if (private->data->ext_path) {
+		if (mtk_drm_find_comp_in_ddp(dev, private->data->ext_path,
+					     private->data->ext_len,
+					     private->ddp_comp))
+			return BIT(i);
+		i++;
+	}
 
-	return ret;
+	if (private->data->third_path) {
+		if (mtk_drm_find_comp_in_ddp(dev, private->data->third_path,
+					     private->data->third_len,
+					     private->ddp_comp))
+			return BIT(i);
+		i++;
+	}
+
+	DRM_INFO("Failed to find comp in ddp table\n");
+	return 0;
 }
 
 int mtk_ddp_comp_init(struct device_node *node, struct mtk_ddp_comp *comp,