This patch allows framebuffers for cirrus to be created with 32bpp pixel formats provided that they do not violate certain restrictions of the cirrus hardware. Signed-off-by: Zach Reizner <zachr@xxxxxxxxxx> --- drivers/gpu/drm/cirrus/cirrus_drv.h | 2 ++ drivers/gpu/drm/cirrus/cirrus_fbdev.c | 4 +++- drivers/gpu/drm/cirrus/cirrus_main.c | 22 ++++++++++++++++++++-- 3 files changed, 25 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/cirrus/cirrus_drv.h b/drivers/gpu/drm/cirrus/cirrus_drv.h index 401c890..fac475c 100644 --- a/drivers/gpu/drm/cirrus/cirrus_drv.h +++ b/drivers/gpu/drm/cirrus/cirrus_drv.h @@ -208,6 +208,8 @@ int cirrus_framebuffer_init(struct drm_device *dev, struct drm_mode_fb_cmd2 *mode_cmd, struct drm_gem_object *obj); +bool cirrus_check_framebuffer(int width, int height, int bpp, int pitch); + /* cirrus_display.c */ int cirrus_modeset_init(struct cirrus_device *cdev); void cirrus_modeset_fini(struct cirrus_device *cdev); diff --git a/drivers/gpu/drm/cirrus/cirrus_fbdev.c b/drivers/gpu/drm/cirrus/cirrus_fbdev.c index 2a135f2..4a0756c 100644 --- a/drivers/gpu/drm/cirrus/cirrus_fbdev.c +++ b/drivers/gpu/drm/cirrus/cirrus_fbdev.c @@ -146,8 +146,10 @@ static int cirrusfb_create_object(struct cirrus_fbdev *afbdev, int ret = 0; drm_fb_get_bpp_depth(mode_cmd->pixel_format, &depth, &bpp); - if (bpp > 24) + if (!cirrus_check_framebuffer(mode_cmd->width, mode_cmd->height, bpp, + mode_cmd->pitches[0])) return -EINVAL; + size = mode_cmd->pitches[0] * mode_cmd->height; ret = cirrus_gem_create(dev, size, true, &gobj); if (ret) diff --git a/drivers/gpu/drm/cirrus/cirrus_main.c b/drivers/gpu/drm/cirrus/cirrus_main.c index 99c1983..029f9e9 100644 --- a/drivers/gpu/drm/cirrus/cirrus_main.c +++ b/drivers/gpu/drm/cirrus/cirrus_main.c @@ -55,8 +55,9 @@ cirrus_user_framebuffer_create(struct drm_device *dev, u32 bpp, depth; drm_fb_get_bpp_depth(mode_cmd->pixel_format, &depth, &bpp); - /* cirrus can't handle > 24bpp framebuffers at all */ - if (bpp > 24) + + if (!cirrus_check_framebuffer(mode_cmd->width, mode_cmd->height, + bpp, mode_cmd->pitches[0])) return ERR_PTR(-EINVAL); obj = drm_gem_object_lookup(dev, filp, mode_cmd->handles[0]); @@ -307,3 +308,20 @@ out_unlock: return ret; } + +bool cirrus_check_framebuffer(int width, int height, int bpp, int pitch) +{ + const int max_pitch = 0x1FF << 3; /* (4096 - 1) & ~111b bytes */ + const int max_size = 0x400000; /* 4MB */ + + if (bpp > 32) + return false; + + if (pitch > max_pitch) + return false; + + if (pitch * height > max_size) + return false; + + return true; +} -- 2.1.0.rc2.206.gedb03e5 _______________________________________________ dri-devel mailing list dri-devel@xxxxxxxxxxxxxxxxxxxxx http://lists.freedesktop.org/mailman/listinfo/dri-devel