Re: [PATCH 3/3] drm/tegra: sor: Initialize runtime PM before use

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On 31/01/2020 16:59, Thierry Reding wrote:
> From: Thierry Reding <treding@xxxxxxxxxx>
> 
> Commit fd67e9c6ed5a ("drm/tegra: Do not implement runtime PM") replaced
> the generic runtime PM usage by a host1x bus-specific implementation in
> order to work around some assumptions baked into runtime PM that are in
> conflict with the requirements in the Tegra DRM driver.
> 
> Unfortunately the new runtime PM callbacks are not setup yet at the time
> when the SOR driver first needs to resume the device to register the SOR
> pad clock, and accesses to register will cause the system to hang.
> 
> Note that this only happens on Tegra124 and Tegra210 because those are
> the only SoCs where the SOR pad clock is registered from the SOR driver.
> Later generations use a SOR pad clock provided by the BPMP.
> 
> Fix this by moving the registration of the SOR pad clock after the
> host1x client has been registered. That's somewhat suboptimal because
> this could potentially, though it's very unlikely, cause the Tegra DRM
> to be probed if the SOR happens to be the last subdevice to register,
> only to be immediately removed again if the SOR pad output clock fails
> to register. That's just a minor annoyance, though, and doesn't justify
> implementing a workaround.
> 
> Fixes: fd67e9c6ed5a ("drm/tegra: Do not implement runtime PM")
> Signed-off-by: Thierry Reding <treding@xxxxxxxxxx>
> ---
>  drivers/gpu/drm/tegra/sor.c | 32 +++++++++++++++++---------------
>  1 file changed, 17 insertions(+), 15 deletions(-)
> 
> diff --git a/drivers/gpu/drm/tegra/sor.c b/drivers/gpu/drm/tegra/sor.c
> index aa4e1695b537..81226a4953c1 100644
> --- a/drivers/gpu/drm/tegra/sor.c
> +++ b/drivers/gpu/drm/tegra/sor.c
> @@ -3915,6 +3915,17 @@ static int tegra_sor_probe(struct platform_device *pdev)
>  	platform_set_drvdata(pdev, sor);
>  	pm_runtime_enable(&pdev->dev);
>  
> +	INIT_LIST_HEAD(&sor->client.list);
> +	sor->client.ops = &sor_client_ops;
> +	sor->client.dev = &pdev->dev;
> +
> +	err = host1x_client_register(&sor->client);
> +	if (err < 0) {
> +		dev_err(&pdev->dev, "failed to register host1x client: %d\n",
> +			err);
> +		goto rpm_disable;
> +	}
> +
>  	/*
>  	 * On Tegra210 and earlier, provide our own implementation for the
>  	 * pad output clock.
> @@ -3926,13 +3937,13 @@ static int tegra_sor_probe(struct platform_device *pdev)
>  				      sor->index);
>  		if (!name) {
>  			err = -ENOMEM;
> -			goto rpm_disable;
> +			goto unregister;
>  		}
>  
>  		err = host1x_client_resume(&sor->client);
>  		if (err < 0) {
>  			dev_err(sor->dev, "failed to resume: %d\n", err);
> -			goto rpm_disable;
> +			goto unregister;
>  		}
>  
>  		sor->clk_pad = tegra_clk_sor_pad_register(sor, name);
> @@ -3941,24 +3952,15 @@ static int tegra_sor_probe(struct platform_device *pdev)
>  
>  	if (IS_ERR(sor->clk_pad)) {
>  		err = PTR_ERR(sor->clk_pad);
> -		dev_err(&pdev->dev, "failed to register SOR pad clock: %d\n",
> +		dev_err(sor->dev, "failed to register SOR pad clock: %d\n",
>  			err);
> -		goto rpm_disable;
> -	}
> -
> -	INIT_LIST_HEAD(&sor->client.list);
> -	sor->client.ops = &sor_client_ops;
> -	sor->client.dev = &pdev->dev;
> -
> -	err = host1x_client_register(&sor->client);
> -	if (err < 0) {
> -		dev_err(&pdev->dev, "failed to register host1x client: %d\n",
> -			err);
> -		goto rpm_disable;
> +		goto unregister;
>  	}
>  
>  	return 0;
>  
> +unregister:
> +	host1x_client_unregister(&sor->client);
>  rpm_disable:
>  	pm_runtime_disable(&pdev->dev);
>  remove:
> 

Reviewed-by: Jon Hunter <jonathanh@xxxxxxxxxx>
Tested-by: Jon Hunter <jonathanh@xxxxxxxxxx>

Cheers
Jon

-- 
nvpublic



[Index of Archives]     [ARM Kernel]     [Linux ARM]     [Linux ARM MSM]     [Linux USB Devel]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]

  Powered by Linux