diff options
| author | Thomas Zimmermann <tzimmermann@suse.de> | 2025-08-21 10:17:17 +0200 |
|---|---|---|
| committer | Thomas Zimmermann <tzimmermann@suse.de> | 2025-09-29 14:00:57 +0200 |
| commit | b1d0e470f881f25d38d5b51accd6dd30baf069aa (patch) | |
| tree | 10d287a29d3f19f9ec99453fd77576fb7a326b0b /drivers/gpu/drm/imx/ipuv3/imx-drm-core.c | |
| parent | ecf29357b6268f70d13949f86df9d62e077d4b89 (diff) | |
drm/imx/ipuv3: Compute dumb-buffer sizes with drm_mode_size_dumb()
Call drm_mode_size_dumb() to compute dumb-buffer scanline pitch and
buffer size. The hardware requires the framebuffer width to be a
multiple of 8. The scanline pitch has to be large enough to support
this. Therefore compute the byte size of 8 pixels in the given color
mode and align the pitch accordingly.
v5:
- fix typo in commit description
Signed-off-by: Thomas Zimmermann <tzimmermann@suse.de>
Reviewed-by: Philipp Zabel <p.zabel@pengutronix.de>
Cc: Philipp Zabel <p.zabel@pengutronix.de>
Cc: Shawn Guo <shawnguo@kernel.org>
Cc: Sascha Hauer <s.hauer@pengutronix.de>
Cc: Pengutronix Kernel Team <kernel@pengutronix.de>
Cc: Fabio Estevam <festevam@gmail.com>
Link: https://lore.kernel.org/r/20250821081918.79786-11-tzimmermann@suse.de
Diffstat (limited to 'drivers/gpu/drm/imx/ipuv3/imx-drm-core.c')
| -rw-r--r-- | drivers/gpu/drm/imx/ipuv3/imx-drm-core.c | 31 |
1 files changed, 23 insertions, 8 deletions
diff --git a/drivers/gpu/drm/imx/ipuv3/imx-drm-core.c b/drivers/gpu/drm/imx/ipuv3/imx-drm-core.c index af4a30311e18..465b5a6ad5bb 100644 --- a/drivers/gpu/drm/imx/ipuv3/imx-drm-core.c +++ b/drivers/gpu/drm/imx/ipuv3/imx-drm-core.c @@ -17,7 +17,9 @@ #include <drm/drm_atomic.h> #include <drm/drm_atomic_helper.h> #include <drm/drm_drv.h> +#include <drm/drm_dumb_buffers.h> #include <drm/drm_fbdev_dma.h> +#include <drm/drm_fourcc.h> #include <drm/drm_gem_dma_helper.h> #include <drm/drm_gem_framebuffer_helper.h> #include <drm/drm_managed.h> @@ -141,19 +143,32 @@ static int imx_drm_dumb_create(struct drm_file *file_priv, struct drm_device *drm, struct drm_mode_create_dumb *args) { - u32 width = args->width; + u32 fourcc; + const struct drm_format_info *info; + u64 pitch_align; int ret; - args->width = ALIGN(width, 8); - args->pitch = DIV_ROUND_UP(args->width * args->bpp, 8); - args->size = args->pitch * args->height; - - ret = drm_gem_dma_dumb_create_internal(file_priv, drm, args); + /* + * Hardware requires the framebuffer width to be aligned to + * multiples of 8. The mode-setting code handles this, but + * the buffer pitch has to be aligned as well. Set the pitch + * alignment accordingly, so that the each scanline fits into + * the allocated buffer. + */ + fourcc = drm_driver_color_mode_format(drm, args->bpp); + if (fourcc == DRM_FORMAT_INVALID) + return -EINVAL; + info = drm_format_info(fourcc); + if (!info) + return -EINVAL; + pitch_align = drm_format_info_min_pitch(info, 0, SZ_8); + if (!pitch_align || pitch_align > U32_MAX) + return -EINVAL; + ret = drm_mode_size_dumb(drm, args, pitch_align, 0); if (ret) return ret; - args->width = width; - return ret; + return drm_gem_dma_dumb_create(file_priv, drm, args); } static const struct drm_driver imx_drm_driver = { |