From be4f235c43f06ae749b8f99b04f899d1e9bd561e Mon Sep 17 00:00:00 2001 From: Tomi Valkeinen Date: Fri, 8 Jan 2016 15:51:02 +0200 Subject: drm/omap: verify that fb plane pitches are the same The DSS hardware uses the same ROW_INC value for both Y and UV planes for NV12 format. This means that the pitches of the Y and UV planes have to match. omapdrm doesn't check this at the moment, and this can lead into a broken NV12 fb on the screen. This patch adds the check. Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart --- drivers/gpu/drm/omapdrm/omap_fb.c | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'drivers/gpu/drm/omapdrm/omap_fb.c') diff --git a/drivers/gpu/drm/omapdrm/omap_fb.c b/drivers/gpu/drm/omapdrm/omap_fb.c index ad202dfc1a49..481512db2656 100644 --- a/drivers/gpu/drm/omapdrm/omap_fb.c +++ b/drivers/gpu/drm/omapdrm/omap_fb.c @@ -449,6 +449,14 @@ struct drm_framebuffer *omap_framebuffer_init(struct drm_device *dev, goto fail; } + if (i > 0 && pitch != mode_cmd->pitches[i - 1]) { + dev_err(dev->dev, + "pitches are not the same between framebuffer planes %d != %d\n", + pitch, mode_cmd->pitches[i - 1]); + ret = -EINVAL; + goto fail; + } + plane->bo = bos[i]; plane->offset = mode_cmd->offsets[i]; plane->pitch = pitch; -- cgit From bfeece553335f9b9bf0d4dc9ea8a602a2248dfd6 Mon Sep 17 00:00:00 2001 From: Tomi Valkeinen Date: Thu, 27 Aug 2015 13:09:22 +0300 Subject: drm/omap: check if rotation is supported before commit omapdrm is missing a check on the validity of the rotation property. This leads to omapdrm possibly trying to use rotation on non-rotateable framebuffer, which causes the overlay setup to fail. This patch adds the necessary check to omap_plane_atomic_check(). Signed-off-by: Tomi Valkeinen Reviewed-by: Laurent Pinchart --- drivers/gpu/drm/omapdrm/omap_drv.h | 1 + drivers/gpu/drm/omapdrm/omap_fb.c | 8 ++++++++ drivers/gpu/drm/omapdrm/omap_plane.c | 6 ++++++ 3 files changed, 15 insertions(+) (limited to 'drivers/gpu/drm/omapdrm/omap_fb.c') diff --git a/drivers/gpu/drm/omapdrm/omap_drv.h b/drivers/gpu/drm/omapdrm/omap_drv.h index c077367dcb1a..16c3eeeae668 100644 --- a/drivers/gpu/drm/omapdrm/omap_drv.h +++ b/drivers/gpu/drm/omapdrm/omap_drv.h @@ -189,6 +189,7 @@ void omap_framebuffer_update_scanout(struct drm_framebuffer *fb, struct omap_drm_window *win, struct omap_overlay_info *info); struct drm_connector *omap_framebuffer_get_next_connector( struct drm_framebuffer *fb, struct drm_connector *from); +bool omap_framebuffer_supports_rotation(struct drm_framebuffer *fb); void omap_gem_init(struct drm_device *dev); void omap_gem_deinit(struct drm_device *dev); diff --git a/drivers/gpu/drm/omapdrm/omap_fb.c b/drivers/gpu/drm/omapdrm/omap_fb.c index 481512db2656..610962396eb0 100644 --- a/drivers/gpu/drm/omapdrm/omap_fb.c +++ b/drivers/gpu/drm/omapdrm/omap_fb.c @@ -145,6 +145,14 @@ static uint32_t get_linear_addr(struct plane *plane, return plane->paddr + offset; } +bool omap_framebuffer_supports_rotation(struct drm_framebuffer *fb) +{ + struct omap_framebuffer *omap_fb = to_omap_framebuffer(fb); + struct plane *plane = &omap_fb->planes[0]; + + return omap_gem_flags(plane->bo) & OMAP_BO_TILED; +} + /* update ovl info for scanout, handles cases of multi-planar fb's, etc. */ void omap_framebuffer_update_scanout(struct drm_framebuffer *fb, diff --git a/drivers/gpu/drm/omapdrm/omap_plane.c b/drivers/gpu/drm/omapdrm/omap_plane.c index d75b197eff46..93ee538a99f5 100644 --- a/drivers/gpu/drm/omapdrm/omap_plane.c +++ b/drivers/gpu/drm/omapdrm/omap_plane.c @@ -177,6 +177,12 @@ static int omap_plane_atomic_check(struct drm_plane *plane, if (state->crtc_y + state->crtc_h > crtc_state->adjusted_mode.vdisplay) return -EINVAL; + if (state->fb) { + if (state->rotation != BIT(DRM_ROTATE_0) && + !omap_framebuffer_supports_rotation(state->fb)) + return -EINVAL; + } + return 0; } -- cgit