[PATCH] kernel/drm: vblank wait on crtc > 1
Alex Deucher
alexdeucher at gmail.com
Sat Mar 19 12:35:43 PDT 2011
On Fri, Mar 18, 2011 at 5:58 PM, Ilija Hadzic
<ihadzic at research.bell-labs.com> wrote:
>
> Hi Dave,
>
> Below is a patch against drm-next branch of 2.6.38-rc8+ kernel that adds the
> capability to wait on vblank events for CRTCs that are greater than 1 and
> thus cannot be represented with primary/secondary flags in the legacy
> interface. It was discussed on the dri-devel list in these two threads:
>
> http://lists.freedesktop.org/archives/dri-devel/2011-March/009009.html
> http://lists.freedesktop.org/archives/dri-devel/2011-March/009025.html
>
> This patch extends the interface to drm_wait_vblank ioctl so that crtc>1 can
> be represented. It also adds a new capability to drm_getcap ioctl so that
> the user space can check whether the new interface to drm_wait_vblank is
> supported (and fall back to the legacy interface if not)
>
> Regards,
>
> Ilija
>
>
> Reviewed-by: Mario Kleiner <mario.kleiner at tuebingen.mpg.de>
> Acked-by: Mario Kleiner <mario.kleiner at tuebingen.mpg.de>
Looks good to me.
Reviewed-by: Alex Deucher <alexdeucher at gmail.com>
Tested-by: Alex Deucher <alexdeucher at gmail.com>
>
> diff --git a/drivers/gpu/drm/drm_ioctl.c b/drivers/gpu/drm/drm_ioctl.c
> index 7f6912a..3617b4c 100644
> --- a/drivers/gpu/drm/drm_ioctl.c
> +++ b/drivers/gpu/drm/drm_ioctl.c
> @@ -280,6 +280,9 @@ int drm_getcap(struct drm_device *dev, void *data,
> struct drm_file *file_priv)
> if (dev->driver->dumb_create)
> req->value = 1;
> break;
> + case DRM_CAP_HIGH_CRTC:
> + req->value = 1;
> + break;
> default:
> return -EINVAL;
> }
> diff --git a/drivers/gpu/drm/drm_irq.c b/drivers/gpu/drm/drm_irq.c
> index a34ef97..c725088 100644
> --- a/drivers/gpu/drm/drm_irq.c
> +++ b/drivers/gpu/drm/drm_irq.c
> @@ -1125,7 +1125,7 @@ int drm_wait_vblank(struct drm_device *dev, void
> *data,
> {
> union drm_wait_vblank *vblwait = data;
> int ret = 0;
> - unsigned int flags, seq, crtc;
> + unsigned int flags, seq, crtc, high_crtc;
>
> if ((!drm_dev_to_irq(dev)) || (!dev->irq_enabled))
> return -EINVAL;
> @@ -1134,16 +1134,21 @@ int drm_wait_vblank(struct drm_device *dev, void
> *data,
> return -EINVAL;
>
> if (vblwait->request.type &
> - ~(_DRM_VBLANK_TYPES_MASK | _DRM_VBLANK_FLAGS_MASK)) {
> + ~(_DRM_VBLANK_TYPES_MASK | _DRM_VBLANK_FLAGS_MASK | +
> _DRM_VBLANK_HIGH_CRTC_MASK)) {
> DRM_ERROR("Unsupported type value 0x%x, supported mask
> 0x%x\n",
> vblwait->request.type,
> - (_DRM_VBLANK_TYPES_MASK |
> _DRM_VBLANK_FLAGS_MASK));
> + (_DRM_VBLANK_TYPES_MASK | _DRM_VBLANK_FLAGS_MASK |
> + _DRM_VBLANK_HIGH_CRTC_MASK));
> return -EINVAL;
> }
>
> flags = vblwait->request.type & _DRM_VBLANK_FLAGS_MASK;
> - crtc = flags & _DRM_VBLANK_SECONDARY ? 1 : 0;
> -
> + high_crtc = (vblwait->request.type & _DRM_VBLANK_HIGH_CRTC_MASK);
> + if (high_crtc)
> + crtc = high_crtc >> _DRM_VBLANK_HIGH_CRTC_SHIFT;
> + else
> + crtc = flags & _DRM_VBLANK_SECONDARY ? 1 : 0;
> if (crtc >= dev->num_crtcs)
> return -EINVAL;
>
> diff --git a/include/drm/drm.h b/include/drm/drm.h
> index 9ac4313..99cd074 100644
> --- a/include/drm/drm.h
> +++ b/include/drm/drm.h
> @@ -469,6 +469,8 @@ enum drm_vblank_seq_type {
> _DRM_VBLANK_SECONDARY = 0x20000000, /**< Secondary display
> controller */
> _DRM_VBLANK_SIGNAL = 0x40000000 /**< Send signal instead of blocking,
> unsupported */
> };
> +#define _DRM_VBLANK_HIGH_CRTC_SHIFT 16
> +#define _DRM_VBLANK_HIGH_CRTC_MASK 0x001F0000
>
> #define _DRM_VBLANK_TYPES_MASK (_DRM_VBLANK_ABSOLUTE |
> _DRM_VBLANK_RELATIVE)
> #define _DRM_VBLANK_FLAGS_MASK (_DRM_VBLANK_EVENT | _DRM_VBLANK_SIGNAL | \
> @@ -753,6 +755,7 @@ struct drm_event_vblank {
> };
>
> #define DRM_CAP_DUMB_BUFFER 0x1
> +#define DRM_CAP_HIGH_CRTC 0x2
>
> /* typedef area */
> #ifndef __KERNEL__
>
More information about the dri-devel
mailing list