mbox series

[v2,00/22] Deprecate struct drm_device.irq_enabled

Message ID 20210622141002.11590-1-tzimmermann@suse.de
Headers show
Series Deprecate struct drm_device.irq_enabled | expand

Message

Thomas Zimmermann June 22, 2021, 2:09 p.m. UTC
Remove references to struct drm_device.irq_enabled from modern
DRM drivers and core.

KMS drivers enable IRQs for their devices internally. They don't
have to keep track of the IRQ state via irq_enabled. For vblanking,
it's cleaner to test for vblanking support directly than to test
for enabled IRQs.

This used to be a single patch, [1] but it's now a full series.

The first 3 patches replace instances of irq_enabled that are not
required.

Patch 4 fixes vblank ioctls to actually test for vblank support
instead of IRQs.

THe rest of the patchset removes irq_enabled from all non-legacy
drivers. The only exception is omapdrm, which has an internal
dpendency on the field's value. For this drivers, the state gets
duplicated internally.

With the patchset applied, drivers can later switch over to plain
Linux IRQ interfaces and DRM's IRQ midlayer can be declared legacy.

v2:
	* keep the original test for legacy drivers in
	  drm_wait_vblank_ioctl() (Daniel)

[1] https://lore.kernel.org/dri-devel/20210608090301.4752-1-tzimmermann@suse.de/

Thomas Zimmermann (22):
  drm/amdgpu: Track IRQ state in local device state
  drm/hibmc: Call drm_irq_uninstall() unconditionally
  drm/radeon: Track IRQ state in local device state
  drm: Don't test for IRQ support in VBLANK ioctls
  drm/komeda: Don't set struct drm_device.irq_enabled
  drm/malidp: Don't set struct drm_device.irq_enabled
  drm/exynos: Don't set struct drm_device.irq_enabled
  drm/kirin: Don't set struct drm_device.irq_enabled
  drm/imx: Don't set struct drm_device.irq_enabled
  drm/mediatek: Don't set struct drm_device.irq_enabled
  drm/nouveau: Don't set struct drm_device.irq_enabled
  drm/omapdrm: Track IRQ state in local device state
  drm/rockchip: Don't set struct drm_device.irq_enabled
  drm/sti: Don't set struct drm_device.irq_enabled
  drm/stm: Don't set struct drm_device.irq_enabled
  drm/sun4i: Don't set struct drm_device.irq_enabled
  drm/tegra: Don't set struct drm_device.irq_enabled
  drm/tidss: Don't use struct drm_device.irq_enabled
  drm/vc4: Don't set struct drm_device.irq_enabled
  drm/vmwgfx: Don't set struct drm_device.irq_enabled
  drm/xlnx: Don't set struct drm_device.irq_enabled
  drm/zte: Don't set struct drm_device.irq_enabled

 drivers/gpu/drm/amd/amdgpu/amdgpu_irq.c         |  6 +++---
 drivers/gpu/drm/arm/display/komeda/komeda_kms.c |  4 ----
 drivers/gpu/drm/arm/malidp_drv.c                |  4 ----
 drivers/gpu/drm/drm_irq.c                       | 10 +++-------
 drivers/gpu/drm/drm_vblank.c                    | 13 +++++++++----
 drivers/gpu/drm/exynos/exynos_drm_drv.c         | 10 ----------
 drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.c |  3 +--
 drivers/gpu/drm/hisilicon/kirin/kirin_drm_drv.c |  2 --
 drivers/gpu/drm/imx/dcss/dcss-kms.c             |  3 ---
 drivers/gpu/drm/imx/imx-drm-core.c              | 11 -----------
 drivers/gpu/drm/mediatek/mtk_drm_drv.c          |  6 ------
 drivers/gpu/drm/nouveau/nouveau_drm.c           |  3 ---
 drivers/gpu/drm/omapdrm/omap_drv.h              |  2 ++
 drivers/gpu/drm/omapdrm/omap_irq.c              |  6 +++---
 drivers/gpu/drm/radeon/radeon_fence.c           |  2 +-
 drivers/gpu/drm/radeon/radeon_irq_kms.c         | 16 ++++++++--------
 drivers/gpu/drm/rockchip/rockchip_drm_drv.c     |  6 ------
 drivers/gpu/drm/sti/sti_compositor.c            |  2 --
 drivers/gpu/drm/stm/ltdc.c                      |  3 ---
 drivers/gpu/drm/sun4i/sun4i_drv.c               |  2 --
 drivers/gpu/drm/tegra/drm.c                     |  7 -------
 drivers/gpu/drm/tidss/tidss_irq.c               |  3 ---
 drivers/gpu/drm/vc4/vc4_kms.c                   |  1 -
 drivers/gpu/drm/vmwgfx/vmwgfx_irq.c             |  8 --------
 drivers/gpu/drm/xlnx/zynqmp_dpsub.c             |  2 --
 drivers/gpu/drm/zte/zx_drm_drv.c                |  6 ------
 26 files changed, 30 insertions(+), 111 deletions(-)


base-commit: 8c1323b422f8473421682ba783b5949ddd89a3f4
prerequisite-patch-id: c2b2f08f0eccc9f5df0c0da49fa1d36267deb11d
prerequisite-patch-id: c67e5d886a47b7d0266d81100837557fda34cb24
--
2.32.0

Comments

Liviu Dudau June 22, 2021, 3:25 p.m. UTC | #1
Hello,

On Tue, Jun 22, 2021 at 04:09:44PM +0200, Thomas Zimmermann wrote:
> For KMS drivers, replace the IRQ check in VBLANK ioctls with a check for
> vblank support. IRQs might be enabled wthout vblanking being supported.
> 
> This change also removes the DRM framework's only dependency on IRQ state
> for non-legacy drivers. For legacy drivers with userspace modesetting,
> the original test remains in drm_wait_vblank_ioctl().
> 
> v2:
> 	* keep the old test for legacy drivers in
> 	  drm_wait_vblank_ioctl() (Daniel)
> 
> Signed-off-by: Thomas Zimmermann <tzimmermann@suse.de>
> ---
>  drivers/gpu/drm/drm_irq.c    | 10 +++-------
>  drivers/gpu/drm/drm_vblank.c | 13 +++++++++----
>  2 files changed, 12 insertions(+), 11 deletions(-)
> 
> diff --git a/drivers/gpu/drm/drm_irq.c b/drivers/gpu/drm/drm_irq.c
> index c3bd664ea733..1d7785721323 100644
> --- a/drivers/gpu/drm/drm_irq.c
> +++ b/drivers/gpu/drm/drm_irq.c
> @@ -74,10 +74,8 @@
>   * only supports devices with a single interrupt on the main device stored in
>   * &drm_device.dev and set as the device paramter in drm_dev_alloc().
>   *
> - * These IRQ helpers are strictly optional. Drivers which roll their own only
> - * need to set &drm_device.irq_enabled to signal the DRM core that vblank
> - * interrupts are working. Since these helpers don't automatically clean up the
> - * requested interrupt like e.g. devm_request_irq() they're not really
> + * These IRQ helpers are strictly optional. Since these helpers don't automatically
> + * clean up the requested interrupt like e.g. devm_request_irq() they're not really
>   * recommended.
>   */
>  
> @@ -91,9 +89,7 @@
>   * and after the installation.
>   *
>   * This is the simplified helper interface provided for drivers with no special
> - * needs. Drivers which need to install interrupt handlers for multiple
> - * interrupts must instead set &drm_device.irq_enabled to signal the DRM core
> - * that vblank interrupts are available.
> + * needs.
>   *
>   * @irq must match the interrupt number that would be passed to request_irq(),
>   * if called directly instead of using this helper function.
> diff --git a/drivers/gpu/drm/drm_vblank.c b/drivers/gpu/drm/drm_vblank.c
> index 3417e1ac7918..a98a4aad5037 100644
> --- a/drivers/gpu/drm/drm_vblank.c
> +++ b/drivers/gpu/drm/drm_vblank.c
> @@ -1748,8 +1748,13 @@ int drm_wait_vblank_ioctl(struct drm_device *dev, void *data,
>  	unsigned int pipe_index;
>  	unsigned int flags, pipe, high_pipe;
>  
> -	if (!dev->irq_enabled)
> -		return -EOPNOTSUPP;
> +	if  (drm_core_check_feature(dev, DRIVER_MODESET)) {
> +		if (!drm_dev_has_vblank(dev))
> +			return -EOPNOTSUPP;
> +	} else {
> +		if (!dev->irq_enabled)
> +			return -EOPNOTSUPP;
> +	}

For a system call that is used quite a lot by userspace we have increased the code size
in a noticeable way. Can we not cache it privately?

Best regards,
Liviu

>  
>  	if (vblwait->request.type & _DRM_VBLANK_SIGNAL)
>  		return -EINVAL;
> @@ -2023,7 +2028,7 @@ int drm_crtc_get_sequence_ioctl(struct drm_device *dev, void *data,
>  	if (!drm_core_check_feature(dev, DRIVER_MODESET))
>  		return -EOPNOTSUPP;
>  
> -	if (!dev->irq_enabled)
> +	if (!drm_dev_has_vblank(dev))
>  		return -EOPNOTSUPP;
>  
>  	crtc = drm_crtc_find(dev, file_priv, get_seq->crtc_id);
> @@ -2082,7 +2087,7 @@ int drm_crtc_queue_sequence_ioctl(struct drm_device *dev, void *data,
>  	if (!drm_core_check_feature(dev, DRIVER_MODESET))
>  		return -EOPNOTSUPP;
>  
> -	if (!dev->irq_enabled)
> +	if (!drm_dev_has_vblank(dev))
>  		return -EOPNOTSUPP;
>  
>  	crtc = drm_crtc_find(dev, file_priv, queue_seq->crtc_id);
> -- 
> 2.32.0
>
Liviu Dudau June 22, 2021, 3:26 p.m. UTC | #2
On Tue, Jun 22, 2021 at 04:09:46PM +0200, Thomas Zimmermann wrote:
> The field drm_device.irq_enabled is only used by legacy drivers
> with userspace modesetting. Don't set it in malidp.
> 
> Signed-off-by: Thomas Zimmermann <tzimmermann@suse.de>

Acked-by: Liviu Dudau <liviu.dudau@arm.com>

Best regards,
Liviu

> ---
>  drivers/gpu/drm/arm/malidp_drv.c | 4 ----
>  1 file changed, 4 deletions(-)
> 
> diff --git a/drivers/gpu/drm/arm/malidp_drv.c b/drivers/gpu/drm/arm/malidp_drv.c
> index de59f3302516..78d15b04b105 100644
> --- a/drivers/gpu/drm/arm/malidp_drv.c
> +++ b/drivers/gpu/drm/arm/malidp_drv.c
> @@ -847,8 +847,6 @@ static int malidp_bind(struct device *dev)
>  	if (ret < 0)
>  		goto irq_init_fail;
>  
> -	drm->irq_enabled = true;
> -
>  	ret = drm_vblank_init(drm, drm->mode_config.num_crtc);
>  	if (ret < 0) {
>  		DRM_ERROR("failed to initialise vblank\n");
> @@ -874,7 +872,6 @@ static int malidp_bind(struct device *dev)
>  vblank_fail:
>  	malidp_se_irq_fini(hwdev);
>  	malidp_de_irq_fini(hwdev);
> -	drm->irq_enabled = false;
>  irq_init_fail:
>  	drm_atomic_helper_shutdown(drm);
>  	component_unbind_all(dev, drm);
> @@ -909,7 +906,6 @@ static void malidp_unbind(struct device *dev)
>  	drm_atomic_helper_shutdown(drm);
>  	malidp_se_irq_fini(hwdev);
>  	malidp_de_irq_fini(hwdev);
> -	drm->irq_enabled = false;
>  	component_unbind_all(dev, drm);
>  	of_node_put(malidp->crtc.port);
>  	malidp->crtc.port = NULL;
> -- 
> 2.32.0
>
Laurent Pinchart June 22, 2021, 4:17 p.m. UTC | #3
On Tue, Jun 22, 2021 at 07:11:33PM +0300, Laurent Pinchart wrote:
> Hi Thomas,
> 
> Thank you for the patches.
> 
> On Tue, Jun 22, 2021 at 04:09:40PM +0200, Thomas Zimmermann wrote:
> > Remove references to struct drm_device.irq_enabled from modern
> > DRM drivers and core.
> > 
> > KMS drivers enable IRQs for their devices internally. They don't
> > have to keep track of the IRQ state via irq_enabled. For vblanking,
> > it's cleaner to test for vblanking support directly than to test
> > for enabled IRQs.
> > 
> > This used to be a single patch, [1] but it's now a full series.
> > 
> > The first 3 patches replace instances of irq_enabled that are not
> > required.
> > 
> > Patch 4 fixes vblank ioctls to actually test for vblank support
> > instead of IRQs.
> > 
> > THe rest of the patchset removes irq_enabled from all non-legacy
> > drivers. The only exception is omapdrm, which has an internal
> > dpendency on the field's value. For this drivers, the state gets
> > duplicated internally.
> > 
> > With the patchset applied, drivers can later switch over to plain
> > Linux IRQ interfaces and DRM's IRQ midlayer can be declared legacy.
> > 
> > v2:
> > 	* keep the original test for legacy drivers in
> > 	  drm_wait_vblank_ioctl() (Daniel)
> > 
> > [1] https://lore.kernel.org/dri-devel/20210608090301.4752-1-tzimmermann@suse.de/
> > 
> > Thomas Zimmermann (22):
> >   drm/amdgpu: Track IRQ state in local device state
> >   drm/hibmc: Call drm_irq_uninstall() unconditionally
> >   drm/radeon: Track IRQ state in local device state
> >   drm: Don't test for IRQ support in VBLANK ioctls
> >   drm/komeda: Don't set struct drm_device.irq_enabled
> >   drm/malidp: Don't set struct drm_device.irq_enabled
> >   drm/exynos: Don't set struct drm_device.irq_enabled
> >   drm/kirin: Don't set struct drm_device.irq_enabled
> >   drm/imx: Don't set struct drm_device.irq_enabled
> >   drm/mediatek: Don't set struct drm_device.irq_enabled
> >   drm/nouveau: Don't set struct drm_device.irq_enabled
> >   drm/omapdrm: Track IRQ state in local device state
> >   drm/rockchip: Don't set struct drm_device.irq_enabled
> >   drm/sti: Don't set struct drm_device.irq_enabled
> >   drm/stm: Don't set struct drm_device.irq_enabled
> >   drm/sun4i: Don't set struct drm_device.irq_enabled
> >   drm/tegra: Don't set struct drm_device.irq_enabled
> >   drm/tidss: Don't use struct drm_device.irq_enabled
> >   drm/vc4: Don't set struct drm_device.irq_enabled
> >   drm/vmwgfx: Don't set struct drm_device.irq_enabled
> >   drm/xlnx: Don't set struct drm_device.irq_enabled
> >   drm/zte: Don't set struct drm_device.irq_enabled
> 
> The list seems to be missing armada, rcar-du and vkms. It would also be
> nice to address i915 if possible.

In addition to this, for all the existing patches,

Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>

> >  drivers/gpu/drm/amd/amdgpu/amdgpu_irq.c         |  6 +++---
> >  drivers/gpu/drm/arm/display/komeda/komeda_kms.c |  4 ----
> >  drivers/gpu/drm/arm/malidp_drv.c                |  4 ----
> >  drivers/gpu/drm/drm_irq.c                       | 10 +++-------
> >  drivers/gpu/drm/drm_vblank.c                    | 13 +++++++++----
> >  drivers/gpu/drm/exynos/exynos_drm_drv.c         | 10 ----------
> >  drivers/gpu/drm/hisilicon/hibmc/hibmc_drm_drv.c |  3 +--
> >  drivers/gpu/drm/hisilicon/kirin/kirin_drm_drv.c |  2 --
> >  drivers/gpu/drm/imx/dcss/dcss-kms.c             |  3 ---
> >  drivers/gpu/drm/imx/imx-drm-core.c              | 11 -----------
> >  drivers/gpu/drm/mediatek/mtk_drm_drv.c          |  6 ------
> >  drivers/gpu/drm/nouveau/nouveau_drm.c           |  3 ---
> >  drivers/gpu/drm/omapdrm/omap_drv.h              |  2 ++
> >  drivers/gpu/drm/omapdrm/omap_irq.c              |  6 +++---
> >  drivers/gpu/drm/radeon/radeon_fence.c           |  2 +-
> >  drivers/gpu/drm/radeon/radeon_irq_kms.c         | 16 ++++++++--------
> >  drivers/gpu/drm/rockchip/rockchip_drm_drv.c     |  6 ------
> >  drivers/gpu/drm/sti/sti_compositor.c            |  2 --
> >  drivers/gpu/drm/stm/ltdc.c                      |  3 ---
> >  drivers/gpu/drm/sun4i/sun4i_drv.c               |  2 --
> >  drivers/gpu/drm/tegra/drm.c                     |  7 -------
> >  drivers/gpu/drm/tidss/tidss_irq.c               |  3 ---
> >  drivers/gpu/drm/vc4/vc4_kms.c                   |  1 -
> >  drivers/gpu/drm/vmwgfx/vmwgfx_irq.c             |  8 --------
> >  drivers/gpu/drm/xlnx/zynqmp_dpsub.c             |  2 --
> >  drivers/gpu/drm/zte/zx_drm_drv.c                |  6 ------
> >  26 files changed, 30 insertions(+), 111 deletions(-)
> > 
> > 
> > base-commit: 8c1323b422f8473421682ba783b5949ddd89a3f4
> > prerequisite-patch-id: c2b2f08f0eccc9f5df0c0da49fa1d36267deb11d
> > prerequisite-patch-id: c67e5d886a47b7d0266d81100837557fda34cb24
Thomas Zimmermann June 23, 2021, 6:43 a.m. UTC | #4
Hi Liviu

Am 22.06.21 um 17:25 schrieb Liviu Dudau:
> Hello,

> 

> On Tue, Jun 22, 2021 at 04:09:44PM +0200, Thomas Zimmermann wrote:

>> For KMS drivers, replace the IRQ check in VBLANK ioctls with a check for

>> vblank support. IRQs might be enabled wthout vblanking being supported.

>>

>> This change also removes the DRM framework's only dependency on IRQ state

>> for non-legacy drivers. For legacy drivers with userspace modesetting,

>> the original test remains in drm_wait_vblank_ioctl().

>>

>> v2:

>> 	* keep the old test for legacy drivers in

>> 	  drm_wait_vblank_ioctl() (Daniel)

>>

>> Signed-off-by: Thomas Zimmermann <tzimmermann@suse.de>

>> ---

>>   drivers/gpu/drm/drm_irq.c    | 10 +++-------

>>   drivers/gpu/drm/drm_vblank.c | 13 +++++++++----

>>   2 files changed, 12 insertions(+), 11 deletions(-)

>>

>> diff --git a/drivers/gpu/drm/drm_irq.c b/drivers/gpu/drm/drm_irq.c

>> index c3bd664ea733..1d7785721323 100644

>> --- a/drivers/gpu/drm/drm_irq.c

>> +++ b/drivers/gpu/drm/drm_irq.c

>> @@ -74,10 +74,8 @@

>>    * only supports devices with a single interrupt on the main device stored in

>>    * &drm_device.dev and set as the device paramter in drm_dev_alloc().

>>    *

>> - * These IRQ helpers are strictly optional. Drivers which roll their own only

>> - * need to set &drm_device.irq_enabled to signal the DRM core that vblank

>> - * interrupts are working. Since these helpers don't automatically clean up the

>> - * requested interrupt like e.g. devm_request_irq() they're not really

>> + * These IRQ helpers are strictly optional. Since these helpers don't automatically

>> + * clean up the requested interrupt like e.g. devm_request_irq() they're not really

>>    * recommended.

>>    */

>>   

>> @@ -91,9 +89,7 @@

>>    * and after the installation.

>>    *

>>    * This is the simplified helper interface provided for drivers with no special

>> - * needs. Drivers which need to install interrupt handlers for multiple

>> - * interrupts must instead set &drm_device.irq_enabled to signal the DRM core

>> - * that vblank interrupts are available.

>> + * needs.

>>    *

>>    * @irq must match the interrupt number that would be passed to request_irq(),

>>    * if called directly instead of using this helper function.

>> diff --git a/drivers/gpu/drm/drm_vblank.c b/drivers/gpu/drm/drm_vblank.c

>> index 3417e1ac7918..a98a4aad5037 100644

>> --- a/drivers/gpu/drm/drm_vblank.c

>> +++ b/drivers/gpu/drm/drm_vblank.c

>> @@ -1748,8 +1748,13 @@ int drm_wait_vblank_ioctl(struct drm_device *dev, void *data,

>>   	unsigned int pipe_index;

>>   	unsigned int flags, pipe, high_pipe;

>>   

>> -	if (!dev->irq_enabled)

>> -		return -EOPNOTSUPP;

>> +	if  (drm_core_check_feature(dev, DRIVER_MODESET)) {

>> +		if (!drm_dev_has_vblank(dev))

>> +			return -EOPNOTSUPP;

>> +	} else {

>> +		if (!dev->irq_enabled)

>> +			return -EOPNOTSUPP;

>> +	}

> 

> For a system call that is used quite a lot by userspace we have increased the code size

> in a noticeable way. Can we not cache it privately?


I'm not quite sure that I understand your concern. The additionally 
called functions are trivial one-liners; probably inlined anyway.

However, irq_enabled is only relevant for legacy drivers and will 
eventually disappear behind CONFIG_DRM_LEGACY. We can rewrite the test 
like this:

ifdef CONFIG_DRM_LEGACY
   if (unlikely(check_feature(dev, DRIVER_LEGACY))) {
     if (!irq_enabled)
       return;
   } else
#endif
   {
     if (!has_vblank_support(dev))
       return;
   }

As CONFIG_DRM_LEGACY is most likely disabled on concurrent systems, we'd 
get a single test for the modern drivers. If DRM_LEGACYis on, the 
compiler at least knows that the else branch is preferred.

Best regards
Thomas

-- 
Thomas Zimmermann
Graphics Driver Developer
SUSE Software Solutions Germany GmbH
Maxfeldstr. 5, 90409 Nürnberg, Germany
(HRB 36809, AG Nürnberg)
Geschäftsführer: Felix Imendörffer
Thomas Zimmermann June 23, 2021, 6:46 a.m. UTC | #5
Am 22.06.21 um 18:11 schrieb Laurent Pinchart:
> Hi Thomas,
> 
> Thank you for the patches.
> 
> On Tue, Jun 22, 2021 at 04:09:40PM +0200, Thomas Zimmermann wrote:
>> Remove references to struct drm_device.irq_enabled from modern
>> DRM drivers and core.
>>
>> KMS drivers enable IRQs for their devices internally. They don't
>> have to keep track of the IRQ state via irq_enabled. For vblanking,
>> it's cleaner to test for vblanking support directly than to test
>> for enabled IRQs.
>>
>> This used to be a single patch, [1] but it's now a full series.
>>
>> The first 3 patches replace instances of irq_enabled that are not
>> required.
>>
>> Patch 4 fixes vblank ioctls to actually test for vblank support
>> instead of IRQs.
>>
>> THe rest of the patchset removes irq_enabled from all non-legacy
>> drivers. The only exception is omapdrm, which has an internal
>> dpendency on the field's value. For this drivers, the state gets
>> duplicated internally.
>>
>> With the patchset applied, drivers can later switch over to plain
>> Linux IRQ interfaces and DRM's IRQ midlayer can be declared legacy.
>>
>> v2:
>> 	* keep the original test for legacy drivers in
>> 	  drm_wait_vblank_ioctl() (Daniel)
>>
>> [1] https://lore.kernel.org/dri-devel/20210608090301.4752-1-tzimmermann@suse.de/
>>
>> Thomas Zimmermann (22):
>>    drm/amdgpu: Track IRQ state in local device state
>>    drm/hibmc: Call drm_irq_uninstall() unconditionally
>>    drm/radeon: Track IRQ state in local device state
>>    drm: Don't test for IRQ support in VBLANK ioctls
>>    drm/komeda: Don't set struct drm_device.irq_enabled
>>    drm/malidp: Don't set struct drm_device.irq_enabled
>>    drm/exynos: Don't set struct drm_device.irq_enabled
>>    drm/kirin: Don't set struct drm_device.irq_enabled
>>    drm/imx: Don't set struct drm_device.irq_enabled
>>    drm/mediatek: Don't set struct drm_device.irq_enabled
>>    drm/nouveau: Don't set struct drm_device.irq_enabled
>>    drm/omapdrm: Track IRQ state in local device state
>>    drm/rockchip: Don't set struct drm_device.irq_enabled
>>    drm/sti: Don't set struct drm_device.irq_enabled
>>    drm/stm: Don't set struct drm_device.irq_enabled
>>    drm/sun4i: Don't set struct drm_device.irq_enabled
>>    drm/tegra: Don't set struct drm_device.irq_enabled
>>    drm/tidss: Don't use struct drm_device.irq_enabled
>>    drm/vc4: Don't set struct drm_device.irq_enabled
>>    drm/vmwgfx: Don't set struct drm_device.irq_enabled
>>    drm/xlnx: Don't set struct drm_device.irq_enabled
>>    drm/zte: Don't set struct drm_device.irq_enabled
> 
> The list seems to be missing armada, rcar-du and vkms. It would also be
> nice to address i915 if possible.

Indeed. I grepped for \>irq_enabled. But some few drivers use 
.irq_enabled. I'll fix this in the patchset's next iteration. Thanks for 
double checking.

Best regards
Thomas
Liviu Dudau June 23, 2021, 12:15 p.m. UTC | #6
Hi Thomas,

On Wed, Jun 23, 2021 at 08:43:07AM +0200, Thomas Zimmermann wrote:
> Hi Liviu
> 
> Am 22.06.21 um 17:25 schrieb Liviu Dudau:
> > Hello,
> > 
> > On Tue, Jun 22, 2021 at 04:09:44PM +0200, Thomas Zimmermann wrote:
> > > For KMS drivers, replace the IRQ check in VBLANK ioctls with a check for
> > > vblank support. IRQs might be enabled wthout vblanking being supported.
> > > 
> > > This change also removes the DRM framework's only dependency on IRQ state
> > > for non-legacy drivers. For legacy drivers with userspace modesetting,
> > > the original test remains in drm_wait_vblank_ioctl().
> > > 
> > > v2:
> > > 	* keep the old test for legacy drivers in
> > > 	  drm_wait_vblank_ioctl() (Daniel)
> > > 
> > > Signed-off-by: Thomas Zimmermann <tzimmermann@suse.de>
> > > ---
> > >   drivers/gpu/drm/drm_irq.c    | 10 +++-------
> > >   drivers/gpu/drm/drm_vblank.c | 13 +++++++++----
> > >   2 files changed, 12 insertions(+), 11 deletions(-)
> > > 
> > > diff --git a/drivers/gpu/drm/drm_irq.c b/drivers/gpu/drm/drm_irq.c
> > > index c3bd664ea733..1d7785721323 100644
> > > --- a/drivers/gpu/drm/drm_irq.c
> > > +++ b/drivers/gpu/drm/drm_irq.c
> > > @@ -74,10 +74,8 @@
> > >    * only supports devices with a single interrupt on the main device stored in
> > >    * &drm_device.dev and set as the device paramter in drm_dev_alloc().
> > >    *
> > > - * These IRQ helpers are strictly optional. Drivers which roll their own only
> > > - * need to set &drm_device.irq_enabled to signal the DRM core that vblank
> > > - * interrupts are working. Since these helpers don't automatically clean up the
> > > - * requested interrupt like e.g. devm_request_irq() they're not really
> > > + * These IRQ helpers are strictly optional. Since these helpers don't automatically
> > > + * clean up the requested interrupt like e.g. devm_request_irq() they're not really
> > >    * recommended.
> > >    */
> > > @@ -91,9 +89,7 @@
> > >    * and after the installation.
> > >    *
> > >    * This is the simplified helper interface provided for drivers with no special
> > > - * needs. Drivers which need to install interrupt handlers for multiple
> > > - * interrupts must instead set &drm_device.irq_enabled to signal the DRM core
> > > - * that vblank interrupts are available.
> > > + * needs.
> > >    *
> > >    * @irq must match the interrupt number that would be passed to request_irq(),
> > >    * if called directly instead of using this helper function.
> > > diff --git a/drivers/gpu/drm/drm_vblank.c b/drivers/gpu/drm/drm_vblank.c
> > > index 3417e1ac7918..a98a4aad5037 100644
> > > --- a/drivers/gpu/drm/drm_vblank.c
> > > +++ b/drivers/gpu/drm/drm_vblank.c
> > > @@ -1748,8 +1748,13 @@ int drm_wait_vblank_ioctl(struct drm_device *dev, void *data,
> > >   	unsigned int pipe_index;
> > >   	unsigned int flags, pipe, high_pipe;
> > > -	if (!dev->irq_enabled)
> > > -		return -EOPNOTSUPP;
> > > +	if  (drm_core_check_feature(dev, DRIVER_MODESET)) {
> > > +		if (!drm_dev_has_vblank(dev))
> > > +			return -EOPNOTSUPP;
> > > +	} else {
> > > +		if (!dev->irq_enabled)
> > > +			return -EOPNOTSUPP;
> > > +	}
> > 
> > For a system call that is used quite a lot by userspace we have increased the code size
> > in a noticeable way. Can we not cache it privately?
> 
> I'm not quite sure that I understand your concern. The additionally called
> functions are trivial one-liners; probably inlined anyway.

They are inlined. However we replace the pointer dereference (which can be calculated
at compile time as offset from a base pointer) with the code in
drm_core_check_all_features() that does 3 pointer dereferences, masking and logical
AND before checking for matching value.

> 
> However, irq_enabled is only relevant for legacy drivers and will eventually
> disappear behind CONFIG_DRM_LEGACY. We can rewrite the test like this:

I get the point that irq_enabled is legacy. However the IOCTL call is not and usually
is used in time critical code to wait for vblank before starting the old buffers for
a new frame. At 60Hz that's probably less of a concern, but at 120Hz refresh rate and
reduced vblank time your time slice allocation for new work matters.

Best regards,
Liviu

> 
> ifdef CONFIG_DRM_LEGACY
>   if (unlikely(check_feature(dev, DRIVER_LEGACY))) {
>     if (!irq_enabled)
>       return;
>   } else
> #endif
>   {
>     if (!has_vblank_support(dev))
>       return;
>   }
> 
> As CONFIG_DRM_LEGACY is most likely disabled on concurrent systems, we'd get
> a single test for the modern drivers. If DRM_LEGACYis on, the compiler at
> least knows that the else branch is preferred.
> 
> Best regards
> Thomas
> 
> -- 
> Thomas Zimmermann
> Graphics Driver Developer
> SUSE Software Solutions Germany GmbH
> Maxfeldstr. 5, 90409 Nürnberg, Germany
> (HRB 36809, AG Nürnberg)
> Geschäftsführer: Felix Imendörffer
>