Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 00/12] drm/format-helper: Move to struct iosys_map
Change format-conversion helpers to use struct iosys_map for source
and destination buffers. Update all users. Also prepare interface for
multi-plane color formats.
The format-conversion helpers mostly used to convert to I/O memory
or system memory. To actual memory type depended on the usecase. We
now have drivers upcomming that do the conversion entirely in system
memory. It's a good opportunity to stream-line the interface of the
conversion helpers to use struct iosys_map. Source and destination
buffers can now be either in system or in I/O memory. Note that the
implementation still only supports source buffers in system memory.
This patchset also changes the interface to support multi-plane
color formats, where the values for each component are stored in
distinct memory locations. Converting from RGBRGBRGB to RRRGGGBBB
would require a single source buffer with RGB values and 3 destination
buffers for the R, G and B values. Conversion-helper interfaces now
support this.
Thomas Zimmermann (12):
drm/format-helper: Provide drm_fb_blit()
drm/format-helper: Merge drm_fb_memcpy() and drm_fb_memcpy_toio()
drm/format-helper: Convert drm_fb_swab() to struct iosys_map
drm/format-helper: Rework XRGB8888-to-RGBG332 conversion
drm/format-helper: Rework XRGB8888-to-RGBG565 conversion
drm/format-helper: Rework XRGB8888-to-RGB888 conversion
drm/format-helper: Rework RGB565-to-XRGB8888 conversion
drm/format-helper: Rework RGB888-to-XRGB8888 conversion
drm/format-helper: Rework XRGB8888-to-XRGB2101010 conversion
drm/format-helper: Rework XRGB8888-to-GRAY8 conversion
drm/format-helper: Rework XRGB8888-to-MONO conversion
drm/format-helper: Move destination-buffer handling into internal
helper
drivers/gpu/drm/drm_format_helper.c | 379 +++++++++---------
drivers/gpu/drm/drm_mipi_dbi.c | 9 +-
drivers/gpu/drm/gud/gud_pipe.c | 20 +-
drivers/gpu/drm/hyperv/hyperv_drm_modeset.c | 11 +-
drivers/gpu/drm/mgag200/mgag200_mode.c | 11 +-
drivers/gpu/drm/solomon/ssd130x.c | 7 +-
.../gpu/drm/tests/drm_format_helper_test.c | 14 +-
drivers/gpu/drm/tiny/cirrus.c | 19 +-
drivers/gpu/drm/tiny/repaper.c | 6 +-
drivers/gpu/drm/tiny/simpledrm.c | 18 +-
drivers/gpu/drm/tiny/st7586.c | 5 +-
include/drm/drm_format_helper.h | 56 ++-
12 files changed, 294 insertions(+), 261 deletions(-)
base-commit: 15fbed4f822211fbb7653c2b8591594d92de9551
prerequisite-patch-id: c2b2f08f0eccc9f5df0c0da49fa1d36267deb11d
prerequisite-patch-id: c67e5d886a47b7d0266d81100837557fda34cb24
prerequisite-patch-id: 3f204510fcbf9530d6540bd8e6128cce598988b6
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 01/12] drm/format-helper: Provide drm_fb_blit()
Provide drm_fb_blit() that works with struct iosys_map. Update all
users of drm_fb_blit_toio(), which required a destination buffer in
I/O memory. The new function's interface works with multi-plane
color formats, although the implementation only supports a single
plane for now.
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 39 ++++++++++++++++++-----------
drivers/gpu/drm/tiny/simpledrm.c | 18 +++++++------
include/drm/drm_format_helper.h | 7 +++---
3 files changed, 38 insertions(+), 26 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index c6182b5de78b..4d74d46ab155 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -8,9 +8,10 @@
* (at your option) any later version.
*/
+#include <linux/io.h>
+#include <linux/iosys-map.h>
#include <linux/module.h>
#include <linux/slab.h>
-#include <linux/io.h>
#include <drm/drm_device.h>
#include <drm/drm_format_helper.h>
@@ -545,9 +546,9 @@ void drm_fb_xrgb8888_to_gray8(void *dst, unsigned int
dst_pitch, const void *vad
EXPORT_SYMBOL(drm_fb_xrgb8888_to_gray8);
/**
- * drm_fb_blit_toio - Copy parts of a framebuffer to display memory
- * @dst: The display memory to copy to
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
+ * drm_fb_blit - Copy parts of a framebuffer to display memory
+ * @dst: Array of display-memory addresses to copy to
+ * @dst_pitch: Array of numbers of bytes between two consecutive scanlines
within dst
* @dst_format: FOURCC code of the display's color format
* @vmap: The framebuffer memory to copy from
* @fb: The framebuffer to copy from
@@ -557,14 +558,18 @@ EXPORT_SYMBOL(drm_fb_xrgb8888_to_gray8);
* formats of the display and the framebuffer mismatch, the blit function
* will attempt to convert between them.
*
+ * The parameters @dst, @dst_pitch and @vmap refer to arrays. Each array must
+ * have at least as many entries as there are planes in @dst_format's
format. Each
+ * entry stores the value for the format's respective color plane at the
same index.
+ *
* Returns:
* 0 on success, or
* -EINVAL if the color-format conversion failed, or
* a negative error code otherwise.
*/
-int drm_fb_blit_toio(void __iomem *dst, unsigned int dst_pitch, uint32_t
dst_format,
- const void *vmap, const struct drm_framebuffer *fb,
- const struct drm_rect *clip)
+int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t
dst_format,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip)
{
uint32_t fb_format = fb->format->format;
@@ -579,30 +584,35 @@ int drm_fb_blit_toio(void __iomem *dst, unsigned int
dst_pitch, uint32_t dst_for
dst_format = DRM_FORMAT_XRGB2101010;
if (dst_format == fb_format) {
- drm_fb_memcpy_toio(dst, dst_pitch, vmap, fb, clip);
+ drm_fb_memcpy_toio(dst[0].vaddr_iomem, dst_pitch[0], vmap[0].vaddr, fb,
clip);
return 0;
} else if (dst_format == DRM_FORMAT_RGB565) {
if (fb_format == DRM_FORMAT_XRGB8888) {
- drm_fb_xrgb8888_to_rgb565_toio(dst, dst_pitch, vmap, fb, clip, false);
+ drm_fb_xrgb8888_to_rgb565_toio(dst[0].vaddr_iomem, dst_pitch[0],
+ vmap[0].vaddr, fb, clip, false);
return 0;
}
} else if (dst_format == DRM_FORMAT_RGB888) {
if (fb_format == DRM_FORMAT_XRGB8888) {
- drm_fb_xrgb8888_to_rgb888_toio(dst, dst_pitch, vmap, fb, clip);
+ drm_fb_xrgb8888_to_rgb888_toio(dst[0].vaddr_iomem, dst_pitch[0],
+ vmap[0].vaddr, fb, clip);
return 0;
}
} else if (dst_format == DRM_FORMAT_XRGB8888) {
if (fb_format == DRM_FORMAT_RGB888) {
- drm_fb_rgb888_to_xrgb8888_toio(dst, dst_pitch, vmap, fb, clip);
+ drm_fb_rgb888_to_xrgb8888_toio(dst[0].vaddr_iomem, dst_pitch[0],
+ vmap[0].vaddr, fb, clip);
return 0;
} else if (fb_format == DRM_FORMAT_RGB565) {
- drm_fb_rgb565_to_xrgb8888_toio(dst, dst_pitch, vmap, fb, clip);
+ drm_fb_rgb565_to_xrgb8888_toio(dst[0].vaddr_iomem, dst_pitch[0],
+ vmap[0].vaddr, fb, clip);
return 0;
}
} else if (dst_format == DRM_FORMAT_XRGB2101010) {
if (fb_format == DRM_FORMAT_XRGB8888) {
- drm_fb_xrgb8888_to_xrgb2101010_toio(dst, dst_pitch, vmap, fb, clip);
+ drm_fb_xrgb8888_to_xrgb2101010_toio(dst[0].vaddr_iomem, dst_pitch[0],
+ vmap[0].vaddr, fb, clip);
return 0;
}
}
@@ -612,8 +622,7 @@ int drm_fb_blit_toio(void __iomem *dst, unsigned int
dst_pitch, uint32_t dst_for
return -EINVAL;
}
-EXPORT_SYMBOL(drm_fb_blit_toio);
-
+EXPORT_SYMBOL(drm_fb_blit);
static void drm_fb_gray8_to_mono_line(void *dbuf, const void *sbuf, unsigned
int pixels)
{
diff --git a/drivers/gpu/drm/tiny/simpledrm.c b/drivers/gpu/drm/tiny/simpledrm.c
index 5422363690e7..1ec73bec0513 100644
--- a/drivers/gpu/drm/tiny/simpledrm.c
+++ b/drivers/gpu/drm/tiny/simpledrm.c
@@ -652,9 +652,8 @@ simpledrm_simple_display_pipe_enable(struct
drm_simple_display_pipe *pipe,
struct simpledrm_device *sdev = simpledrm_device_of_dev(pipe->crtc.dev);
struct drm_shadow_plane_state *shadow_plane_state =
to_drm_shadow_plane_state(plane_state);
struct drm_framebuffer *fb = plane_state->fb;
- void *vmap = shadow_plane_state->data[0].vaddr; /* TODO: Use mapping
abstraction */
struct drm_device *dev = &sdev->dev;
- void __iomem *dst = sdev->screen_base;
+ struct iosys_map dst;
struct drm_rect src_clip, dst_clip;
int idx;
@@ -670,8 +669,10 @@ simpledrm_simple_display_pipe_enable(struct
drm_simple_display_pipe *pipe,
if (!drm_dev_enter(dev, &idx))
return;
- dst += drm_fb_clip_offset(sdev->pitch, sdev->format, &dst_clip);
- drm_fb_blit_toio(dst, sdev->pitch, sdev->format->format, vmap, fb,
&src_clip);
+ iosys_map_set_vaddr_iomem(&dst, sdev->screen_base);
+ iosys_map_incr(&dst, drm_fb_clip_offset(sdev->pitch, sdev->format,
&dst_clip));
+ drm_fb_blit(&dst, &sdev->pitch, sdev->format->format,
+ shadow_plane_state->data, fb, &src_clip);
drm_dev_exit(idx);
}
@@ -699,10 +700,9 @@ simpledrm_simple_display_pipe_update(struct
drm_simple_display_pipe *pipe,
struct simpledrm_device *sdev = simpledrm_device_of_dev(pipe->crtc.dev);
struct drm_plane_state *plane_state = pipe->plane.state;
struct drm_shadow_plane_state *shadow_plane_state =
to_drm_shadow_plane_state(plane_state);
- void *vmap = shadow_plane_state->data[0].vaddr; /* TODO: Use mapping
abstraction */
struct drm_framebuffer *fb = plane_state->fb;
struct drm_device *dev = &sdev->dev;
- void __iomem *dst = sdev->screen_base;
+ struct iosys_map dst;
struct drm_rect src_clip, dst_clip;
int idx;
@@ -719,8 +719,10 @@ simpledrm_simple_display_pipe_update(struct
drm_simple_display_pipe *pipe,
if (!drm_dev_enter(dev, &idx))
return;
- dst += drm_fb_clip_offset(sdev->pitch, sdev->format, &dst_clip);
- drm_fb_blit_toio(dst, sdev->pitch, sdev->format->format, vmap, fb,
&src_clip);
+ iosys_map_set_vaddr_iomem(&dst, sdev->screen_base);
+ iosys_map_incr(&dst, drm_fb_clip_offset(sdev->pitch, sdev->format,
&dst_clip));
+ drm_fb_blit(&dst, &sdev->pitch, sdev->format->format,
+ shadow_plane_state->data, fb, &src_clip);
drm_dev_exit(idx);
}
diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h
index 55145eca0782..21daea7fda99 100644
--- a/include/drm/drm_format_helper.h
+++ b/include/drm/drm_format_helper.h
@@ -6,6 +6,7 @@
#ifndef __LINUX_DRM_FORMAT_HELPER_H
#define __LINUX_DRM_FORMAT_HELPER_H
+struct iosys_map;
struct drm_format_info;
struct drm_framebuffer;
struct drm_rect;
@@ -39,9 +40,9 @@ void drm_fb_xrgb8888_to_xrgb2101010_toio(void __iomem *dst,
unsigned int dst_pit
void drm_fb_xrgb8888_to_gray8(void *dst, unsigned int dst_pitch, const void
*vaddr,
const struct drm_framebuffer *fb, const struct drm_rect *clip);
-int drm_fb_blit_toio(void __iomem *dst, unsigned int dst_pitch, uint32_t
dst_format,
- const void *vmap, const struct drm_framebuffer *fb,
- const struct drm_rect *rect);
+int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t
dst_format,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *rect);
void drm_fb_xrgb8888_to_mono(void *dst, unsigned int dst_pitch, const void
*src,
const struct drm_framebuffer *fb, const struct drm_rect *clip);
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 02/12] drm/format-helper: Merge drm_fb_memcpy() and drm_fb_memcpy_toio()
Merge drm_fb_memcpy() and drm_fb_memcpy() into drm_fb_memcpy() that
uses struct iosys_map for buffers. The new function also supports
multi-plane color formats. Convert all users of the original helpers.
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 77 +++++++++------------
drivers/gpu/drm/drm_mipi_dbi.c | 3 +-
drivers/gpu/drm/gud/gud_pipe.c | 4 +-
drivers/gpu/drm/hyperv/hyperv_drm_modeset.c | 11 +--
drivers/gpu/drm/mgag200/mgag200_mode.c | 11 +--
drivers/gpu/drm/tiny/cirrus.c | 21 +++---
include/drm/drm_format_helper.h | 7 +-
7 files changed, 63 insertions(+), 71 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index 4d74d46ab155..49589b442f18 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -131,63 +131,48 @@ static int drm_fb_xfrm_toio(void __iomem *dst, unsigned
long dst_pitch, unsigned
/**
* drm_fb_memcpy - Copy clip buffer
- * @dst: Destination buffer
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
- * @vaddr: Source buffer
+ * @dst: Array of destination buffers
+ * @dst_pitch: Array of numbers of bytes between two consecutive scanlines
within dst
+ * @vmap: Array of source buffers
* @fb: DRM framebuffer
* @clip: Clip rectangle area to copy
*
* This function does not apply clipping on dst, i.e. the destination
* is at the top-left corner.
*/
-void drm_fb_memcpy(void *dst, unsigned int dst_pitch, const void *vaddr,
- const struct drm_framebuffer *fb, const struct drm_rect *clip)
+void drm_fb_memcpy(struct iosys_map *dst, const unsigned int *dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip)
{
- unsigned int cpp = fb->format->cpp[0];
- size_t len = (clip->x2 - clip->x1) * cpp;
- unsigned int y, lines = clip->y2 - clip->y1;
-
- if (!dst_pitch)
- dst_pitch = len;
+ static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
+ 0, 0, 0, 0
+ };
- vaddr += clip_offset(clip, fb->pitches[0], cpp);
- for (y = 0; y < lines; y++) {
- memcpy(dst, vaddr, len);
- vaddr += fb->pitches[0];
- dst += dst_pitch;
- }
-}
-EXPORT_SYMBOL(drm_fb_memcpy);
-
-/**
- * drm_fb_memcpy_toio - Copy clip buffer
- * @dst: Destination buffer (iomem)
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
- * @vaddr: Source buffer
- * @fb: DRM framebuffer
- * @clip: Clip rectangle area to copy
- *
- * This function does not apply clipping on dst, i.e. the destination
- * is at the top-left corner.
- */
-void drm_fb_memcpy_toio(void __iomem *dst, unsigned int dst_pitch, const void
*vaddr,
- const struct drm_framebuffer *fb, const struct drm_rect *clip)
-{
- unsigned int cpp = fb->format->cpp[0];
- size_t len = (clip->x2 - clip->x1) * cpp;
- unsigned int y, lines = clip->y2 - clip->y1;
+ const struct drm_format_info *format = fb->format;
+ unsigned int i, y, lines = drm_rect_height(clip);
if (!dst_pitch)
- dst_pitch = len;
-
- vaddr += clip_offset(clip, fb->pitches[0], cpp);
- for (y = 0; y < lines; y++) {
- memcpy_toio(dst, vaddr, len);
- vaddr += fb->pitches[0];
- dst += dst_pitch;
+ dst_pitch = default_dst_pitch;
+
+ for (i = 0; i < format->num_planes; ++i) {
+ unsigned int cpp_i = format->cpp[i];
+ size_t len_i = drm_rect_width(clip) * cpp_i;
+ unsigned int dst_pitch_i = dst_pitch[i];
+ struct iosys_map dst_i = dst[i];
+ struct iosys_map vmap_i = vmap[i];
+
+ if (!dst_pitch_i)
+ dst_pitch_i = len_i;
+
+ iosys_map_incr(&vmap_i, clip_offset(clip, fb->pitches[i], cpp_i));
+ for (y = 0; y < lines; y++) {
+ iosys_map_memcpy_to(&dst_i, 0, vmap_i.vaddr, len_i);
+ iosys_map_incr(&vmap_i, fb->pitches[i]);
+ iosys_map_incr(&dst_i, dst_pitch_i);
+ }
}
}
-EXPORT_SYMBOL(drm_fb_memcpy_toio);
+EXPORT_SYMBOL(drm_fb_memcpy);
static void drm_fb_swab16_line(void *dbuf, const void *sbuf, unsigned int
pixels)
{
@@ -584,7 +569,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int
*dst_pitch, uint32_t d
dst_format = DRM_FORMAT_XRGB2101010;
if (dst_format == fb_format) {
- drm_fb_memcpy_toio(dst[0].vaddr_iomem, dst_pitch[0], vmap[0].vaddr, fb,
clip);
+ drm_fb_memcpy(dst, dst_pitch, vmap, fb, clip);
return 0;
} else if (dst_format == DRM_FORMAT_RGB565) {
diff --git a/drivers/gpu/drm/drm_mipi_dbi.c b/drivers/gpu/drm/drm_mipi_dbi.c
index 2f61f53d472f..22451806fb5c 100644
--- a/drivers/gpu/drm/drm_mipi_dbi.c
+++ b/drivers/gpu/drm/drm_mipi_dbi.c
@@ -205,6 +205,7 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb,
struct drm_gem_object *gem = drm_gem_fb_get_obj(fb, 0);
struct iosys_map map[DRM_FORMAT_MAX_PLANES];
struct iosys_map data[DRM_FORMAT_MAX_PLANES];
+ struct iosys_map dst_map = IOSYS_MAP_INIT_VADDR(dst);
void *src;
int ret;
@@ -222,7 +223,7 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb,
if (swap)
drm_fb_swab(dst, 0, src, fb, clip, !gem->import_attach);
else
- drm_fb_memcpy(dst, 0, src, fb, clip);
+ drm_fb_memcpy(&dst_map, NULL, data, fb, clip);
break;
case DRM_FORMAT_XRGB8888:
drm_fb_xrgb8888_to_rgb565(dst, 0, src, fb, clip, swap);
diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c
index d42592f6daab..449c95a4aee0 100644
--- a/drivers/gpu/drm/gud/gud_pipe.c
+++ b/drivers/gpu/drm/gud/gud_pipe.c
@@ -156,6 +156,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct
drm_framebuffer *fb,
u8 compression = gdrm->compression;
struct iosys_map map[DRM_FORMAT_MAX_PLANES];
struct iosys_map map_data[DRM_FORMAT_MAX_PLANES];
+ struct iosys_map dst;
void *vaddr, *buf;
size_t pitch, len;
int ret = 0;
@@ -179,6 +180,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct
drm_framebuffer *fb,
buf = gdrm->compress_buf;
else
buf = gdrm->bulk_buf;
+ iosys_map_set_vaddr(&dst, buf);
/*
* Imported buffers are assumed to be write-combined and thus uncached
@@ -208,7 +210,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct
drm_framebuffer *fb,
/* can compress directly from the framebuffer */
buf = vaddr + rect->y1 * pitch;
} else {
- drm_fb_memcpy(buf, 0, vaddr, fb, rect);
+ drm_fb_memcpy(&dst, NULL, map_data, fb, rect);
}
memset(req, 0, sizeof(*req));
diff --git a/drivers/gpu/drm/hyperv/hyperv_drm_modeset.c
b/drivers/gpu/drm/hyperv/hyperv_drm_modeset.c
index b8e64dd8d3a6..26e63148e226 100644
--- a/drivers/gpu/drm/hyperv/hyperv_drm_modeset.c
+++ b/drivers/gpu/drm/hyperv/hyperv_drm_modeset.c
@@ -21,19 +21,20 @@
#include "hyperv_drm.h"
static int hyperv_blit_to_vram_rect(struct drm_framebuffer *fb,
- const struct iosys_map *map,
+ const struct iosys_map *vmap,
struct drm_rect *rect)
{
struct hyperv_drm_device *hv = to_hv(fb->dev);
- void __iomem *dst = hv->vram;
- void *vmap = map->vaddr; /* TODO: Use mapping abstraction properly */
+ struct iosys_map dst;
int idx;
if (!drm_dev_enter(&hv->dev, &idx))
return -ENODEV;
- dst += drm_fb_clip_offset(fb->pitches[0], fb->format, rect);
- drm_fb_memcpy_toio(dst, fb->pitches[0], vmap, fb, rect);
+ iosys_map_set_vaddr_iomem(&dst, hv->vram);
+ iosys_map_incr(&dst, drm_fb_clip_offset(fb->pitches[0], fb->format,
rect));
+
+ drm_fb_memcpy(&dst, fb->pitches, vmap, fb, rect);
drm_dev_exit(idx);
diff --git a/drivers/gpu/drm/mgag200/mgag200_mode.c
b/drivers/gpu/drm/mgag200/mgag200_mode.c
index a02f599cb9cf..a79a0ee3a50d 100644
--- a/drivers/gpu/drm/mgag200/mgag200_mode.c
+++ b/drivers/gpu/drm/mgag200/mgag200_mode.c
@@ -755,13 +755,14 @@ mgag200_simple_display_pipe_mode_valid(struct
drm_simple_display_pipe *pipe,
static void
mgag200_handle_damage(struct mga_device *mdev, struct drm_framebuffer *fb,
- struct drm_rect *clip, const struct iosys_map *map)
+ struct drm_rect *clip, const struct iosys_map *vmap)
{
- void __iomem *dst = mdev->vram;
- void *vmap = map->vaddr; /* TODO: Use mapping abstraction properly */
+ struct iosys_map dst;
- dst += drm_fb_clip_offset(fb->pitches[0], fb->format, clip);
- drm_fb_memcpy_toio(dst, fb->pitches[0], vmap, fb, clip);
+ iosys_map_set_vaddr_iomem(&dst, mdev->vram);
+ iosys_map_incr(&dst, drm_fb_clip_offset(fb->pitches[0], fb->format,
clip));
+
+ drm_fb_memcpy(&dst, fb->pitches, vmap, fb, clip);
}
static void
diff --git a/drivers/gpu/drm/tiny/cirrus.c b/drivers/gpu/drm/tiny/cirrus.c
index c4f5beea1f90..73fb9f63d227 100644
--- a/drivers/gpu/drm/tiny/cirrus.c
+++ b/drivers/gpu/drm/tiny/cirrus.c
@@ -316,28 +316,31 @@ static int cirrus_mode_set(struct cirrus_device *cirrus,
}
static int cirrus_fb_blit_rect(struct drm_framebuffer *fb,
- const struct iosys_map *map,
+ const struct iosys_map *vmap,
struct drm_rect *rect)
{
struct cirrus_device *cirrus = to_cirrus(fb->dev);
- void __iomem *dst = cirrus->vram;
- void *vmap = map->vaddr; /* TODO: Use mapping abstraction properly */
+ struct iosys_map dst;
+ void *vaddr = vmap->vaddr; /* TODO: Use mapping abstraction properly */
int idx;
if (!drm_dev_enter(&cirrus->dev, &idx))
return -ENODEV;
+ iosys_map_set_vaddr_iomem(&dst, cirrus->vram);
+
if (cirrus->cpp == fb->format->cpp[0]) {
- dst += drm_fb_clip_offset(fb->pitches[0], fb->format, rect);
- drm_fb_memcpy_toio(dst, fb->pitches[0], vmap, fb, rect);
+ iosys_map_incr(&dst, drm_fb_clip_offset(fb->pitches[0], fb->format,
rect));
+ drm_fb_memcpy(&dst, fb->pitches, vmap, fb, rect);
} else if (fb->format->cpp[0] == 4 && cirrus->cpp == 2) {
- dst += drm_fb_clip_offset(cirrus->pitch, fb->format, rect);
- drm_fb_xrgb8888_to_rgb565_toio(dst, cirrus->pitch, vmap, fb, rect, false);
+ iosys_map_incr(&dst, drm_fb_clip_offset(cirrus->pitch, fb->format,
rect));
+ drm_fb_xrgb8888_to_rgb565_toio(dst.vaddr_iomem, cirrus->pitch, vaddr, fb,
rect,
+ false);
} else if (fb->format->cpp[0] == 4 && cirrus->cpp == 3) {
- dst += drm_fb_clip_offset(cirrus->pitch, fb->format, rect);
- drm_fb_xrgb8888_to_rgb888_toio(dst, cirrus->pitch, vmap, fb, rect);
+ iosys_map_incr(&dst, drm_fb_clip_offset(cirrus->pitch, fb->format,
rect));
+ drm_fb_xrgb8888_to_rgb888_toio(dst.vaddr_iomem, cirrus->pitch, vaddr, fb,
rect);
} else {
WARN_ON_ONCE("cpp mismatch");
diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h
index 21daea7fda99..8af6a2717bc9 100644
--- a/include/drm/drm_format_helper.h
+++ b/include/drm/drm_format_helper.h
@@ -14,10 +14,9 @@ struct drm_rect;
unsigned int drm_fb_clip_offset(unsigned int pitch, const struct
drm_format_info *format,
const struct drm_rect *clip);
-void drm_fb_memcpy(void *dst, unsigned int dst_pitch, const void *vaddr,
- const struct drm_framebuffer *fb, const struct drm_rect *clip);
-void drm_fb_memcpy_toio(void __iomem *dst, unsigned int dst_pitch, const void
*vaddr,
- const struct drm_framebuffer *fb, const struct drm_rect *clip);
+void drm_fb_memcpy(struct iosys_map *dst, const unsigned int *dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip);
void drm_fb_swab(void *dst, unsigned int dst_pitch, const void *src,
const struct drm_framebuffer *fb, const struct drm_rect *clip,
bool cached);
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 03/12] drm/format-helper: Convert drm_fb_swab() to struct iosys_map
Convert drm_fb_swab() to use struct iosys_map() and convert users. The
new interface supports multi-plane color formats.
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 38 +++++++++++++++++++++--------
drivers/gpu/drm/drm_mipi_dbi.c | 2 +-
drivers/gpu/drm/gud/gud_pipe.c | 2 +-
include/drm/drm_format_helper.h | 6 ++---
4 files changed, 33 insertions(+), 15 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index 49589b442f18..fa22d3cb11e8 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -196,9 +196,9 @@ static void drm_fb_swab32_line(void *dbuf, const void *sbuf,
unsigned int pixels
/**
* drm_fb_swab - Swap bytes into clip buffer
- * @dst: Destination buffer
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
- * @src: Source buffer
+ * @dst: Array of destination buffers
+ * @dst_pitch: Array of numbers of bytes between two consecutive scanlines
within dst
+ * @vmap: Array of source buffers
* @fb: DRM framebuffer
* @clip: Clip rectangle area to copy
* @cached: Source buffer is mapped cached (eg. not write-combined)
@@ -209,24 +209,42 @@ static void drm_fb_swab32_line(void *dbuf, const void
*sbuf, unsigned int pixels
* This function does not apply clipping on dst, i.e. the destination
* is at the top-left corner.
*/
-void drm_fb_swab(void *dst, unsigned int dst_pitch, const void *src,
- const struct drm_framebuffer *fb, const struct drm_rect *clip,
- bool cached)
+void drm_fb_swab(struct iosys_map *dst, const unsigned int *dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip, bool cached)
{
- u8 cpp = fb->format->cpp[0];
+ static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
+ 0, 0, 0, 0
+ };
+ const struct drm_format_info *format = fb->format;
+ u8 cpp = format->cpp[0];
+ void (*swab_line)(void *dbuf, const void *sbuf, unsigned int npixels);
switch (cpp) {
case 4:
- drm_fb_xfrm(dst, dst_pitch, cpp, src, fb, clip, cached, drm_fb_swab32_line);
+ swab_line = drm_fb_swab32_line;
break;
case 2:
- drm_fb_xfrm(dst, dst_pitch, cpp, src, fb, clip, cached, drm_fb_swab16_line);
+ swab_line = drm_fb_swab16_line;
break;
default:
drm_warn_once(fb->dev, "Format %p4cc has unsupported pixel
size.\n",
- &fb->format->format);
+ &format->format);
+ swab_line = NULL;
break;
}
+ if (!swab_line)
+ return;
+
+ if (!dst_pitch)
+ dst_pitch = default_dst_pitch;
+
+ if (dst->is_iomem)
+ drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], cpp,
+ vmap[0].vaddr, fb, clip, cached, swab_line);
+ else
+ drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], cpp, vmap[0].vaddr, fb,
+ clip, cached, swab_line);
}
EXPORT_SYMBOL(drm_fb_swab);
diff --git a/drivers/gpu/drm/drm_mipi_dbi.c b/drivers/gpu/drm/drm_mipi_dbi.c
index 22451806fb5c..973a75585cad 100644
--- a/drivers/gpu/drm/drm_mipi_dbi.c
+++ b/drivers/gpu/drm/drm_mipi_dbi.c
@@ -221,7 +221,7 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb,
switch (fb->format->format) {
case DRM_FORMAT_RGB565:
if (swap)
- drm_fb_swab(dst, 0, src, fb, clip, !gem->import_attach);
+ drm_fb_swab(&dst_map, NULL, data, fb, clip, !gem->import_attach);
else
drm_fb_memcpy(&dst_map, NULL, data, fb, clip);
break;
diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c
index 449c95a4aee0..a15cda9ba058 100644
--- a/drivers/gpu/drm/gud/gud_pipe.c
+++ b/drivers/gpu/drm/gud/gud_pipe.c
@@ -205,7 +205,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct
drm_framebuffer *fb,
len = gud_xrgb8888_to_color(buf, format, vaddr, fb, rect);
}
} else if (gud_is_big_endian() && format->cpp[0] > 1) {
- drm_fb_swab(buf, 0, vaddr, fb, rect, !import_attach);
+ drm_fb_swab(&dst, NULL, map_data, fb, rect, !import_attach);
} else if (compression && !import_attach && pitch ==
fb->pitches[0]) {
/* can compress directly from the framebuffer */
buf = vaddr + rect->y1 * pitch;
diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h
index 8af6a2717bc9..60944feaa936 100644
--- a/include/drm/drm_format_helper.h
+++ b/include/drm/drm_format_helper.h
@@ -17,9 +17,9 @@ unsigned int drm_fb_clip_offset(unsigned int pitch, const
struct drm_format_info
void drm_fb_memcpy(struct iosys_map *dst, const unsigned int *dst_pitch,
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip);
-void drm_fb_swab(void *dst, unsigned int dst_pitch, const void *src,
- const struct drm_framebuffer *fb, const struct drm_rect *clip,
- bool cached);
+void drm_fb_swab(struct iosys_map *dst, const unsigned int *dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip, bool cached);
void drm_fb_xrgb8888_to_rgb332(void *dst, unsigned int dst_pitch, const void
*vaddr,
const struct drm_framebuffer *fb, const struct drm_rect *clip);
void drm_fb_xrgb8888_to_rgb565(void *dst, unsigned int dst_pitch, const void
*vaddr,
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 04/12] drm/format-helper: Rework XRGB8888-to-RGBG332 conversion
Update XRGB8888-to-RGB332 conversion to support struct iosys_map
and convert all users. Although these are single-plane color formats,
the new interface supports multi-plane formats for consistency with
drm_fb_blit().
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 25 ++++++++++++++-----
drivers/gpu/drm/gud/gud_pipe.c | 2 +-
.../gpu/drm/tests/drm_format_helper_test.c | 14 ++++++-----
include/drm/drm_format_helper.h | 5 ++--
4 files changed, 31 insertions(+), 15 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index fa22d3cb11e8..2b5c3746ff4a 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -265,18 +265,31 @@ static void drm_fb_xrgb8888_to_rgb332_line(void *dbuf,
const void *sbuf, unsigne
/**
* drm_fb_xrgb8888_to_rgb332 - Convert XRGB8888 to RGB332 clip buffer
- * @dst: RGB332 destination buffer
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
- * @src: XRGB8888 source buffer
+ * @dst: Array of RGB332 destination buffers
+ * @dst_pitch: Array of numbers of bytes between two consecutive scanlines
within dst
+ * @vmap: Array of XRGB8888 source buffers
* @fb: DRM framebuffer
* @clip: Clip rectangle area to copy
*
* Drivers can use this function for RGB332 devices that don't natively
support XRGB8888.
*/
-void drm_fb_xrgb8888_to_rgb332(void *dst, unsigned int dst_pitch, const void
*src,
- const struct drm_framebuffer *fb, const struct drm_rect *clip)
+void drm_fb_xrgb8888_to_rgb332(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip)
{
- drm_fb_xfrm(dst, dst_pitch, 1, src, fb, clip, false,
drm_fb_xrgb8888_to_rgb332_line);
+ static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
+ 0, 0, 0, 0
+ };
+
+ if (!dst_pitch)
+ dst_pitch = default_dst_pitch;
+
+ if (dst[0].is_iomem)
+ drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 1, vmap[0].vaddr, fb,
clip,
+ false, drm_fb_xrgb8888_to_rgb332_line);
+ else
+ drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 1, vmap[0].vaddr, fb, clip,
+ false, drm_fb_xrgb8888_to_rgb332_line);
}
EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb332);
diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c
index a15cda9ba058..426a3ae6cc50 100644
--- a/drivers/gpu/drm/gud/gud_pipe.c
+++ b/drivers/gpu/drm/gud/gud_pipe.c
@@ -196,7 +196,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct
drm_framebuffer *fb,
} else if (format->format == DRM_FORMAT_R8) {
drm_fb_xrgb8888_to_gray8(buf, 0, vaddr, fb, rect);
} else if (format->format == DRM_FORMAT_RGB332) {
- drm_fb_xrgb8888_to_rgb332(buf, 0, vaddr, fb, rect);
+ drm_fb_xrgb8888_to_rgb332(&dst, NULL, map_data, fb, rect);
} else if (format->format == DRM_FORMAT_RGB565) {
drm_fb_xrgb8888_to_rgb565(buf, 0, vaddr, fb, rect, gud_is_big_endian());
} else if (format->format == DRM_FORMAT_RGB888) {
diff --git a/drivers/gpu/drm/tests/drm_format_helper_test.c
b/drivers/gpu/drm/tests/drm_format_helper_test.c
index 98583bf56044..b74dba06f704 100644
--- a/drivers/gpu/drm/tests/drm_format_helper_test.c
+++ b/drivers/gpu/drm/tests/drm_format_helper_test.c
@@ -124,7 +124,8 @@ static void xrgb8888_to_rgb332_test(struct kunit *test)
{
const struct xrgb8888_to_rgb332_case *params = test->param_value;
size_t dst_size;
- __u8 *dst = NULL;
+ struct iosys_map dst, xrgb8888;
+ __u8 *buf = NULL;
struct drm_framebuffer fb = {
.format = drm_format_info(DRM_FORMAT_XRGB8888),
@@ -135,12 +136,13 @@ static void xrgb8888_to_rgb332_test(struct kunit *test)
¶ms->clip);
KUNIT_ASSERT_GT(test, dst_size, 0);
- dst = kunit_kzalloc(test, dst_size, GFP_KERNEL);
- KUNIT_ASSERT_NOT_ERR_OR_NULL(test, dst);
+ buf = kunit_kzalloc(test, dst_size, GFP_KERNEL);
+ KUNIT_ASSERT_NOT_ERR_OR_NULL(test, buf);
- drm_fb_xrgb8888_to_rgb332(dst, params->dst_pitch, params->xrgb8888,
- &fb, ¶ms->clip);
- KUNIT_EXPECT_EQ(test, memcmp(dst, params->expected, dst_size), 0);
+ iosys_map_set_vaddr(&dst, buf);
+ iosys_map_set_vaddr(&xrgb8888, (void __force *)params->xrgb8888);
+ drm_fb_xrgb8888_to_rgb332(&dst, ¶ms->dst_pitch, &xrgb8888,
&fb, ¶ms->clip);
+ KUNIT_EXPECT_EQ(test, memcmp(buf, params->expected, dst_size), 0);
}
static struct kunit_case drm_format_helper_test_cases[] = {
diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h
index 60944feaa936..3c28f099e3ed 100644
--- a/include/drm/drm_format_helper.h
+++ b/include/drm/drm_format_helper.h
@@ -20,8 +20,9 @@ void drm_fb_memcpy(struct iosys_map *dst, const unsigned int
*dst_pitch,
void drm_fb_swab(struct iosys_map *dst, const unsigned int *dst_pitch,
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip, bool cached);
-void drm_fb_xrgb8888_to_rgb332(void *dst, unsigned int dst_pitch, const void
*vaddr,
- const struct drm_framebuffer *fb, const struct drm_rect *clip);
+void drm_fb_xrgb8888_to_rgb332(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip);
void drm_fb_xrgb8888_to_rgb565(void *dst, unsigned int dst_pitch, const void
*vaddr,
const struct drm_framebuffer *fb, const struct drm_rect *clip,
bool swab);
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 05/12] drm/format-helper: Rework XRGB8888-to-RGBG565 conversion
Update XRGB8888-to-RGB565 conversion to support struct iosys_map
and convert all users. Although these are single-plane color formats,
the new interface supports multi-plane formats for consistency with
drm_fb_blit().
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 59 +++++++++++------------------
drivers/gpu/drm/drm_mipi_dbi.c | 4 +-
drivers/gpu/drm/gud/gud_pipe.c | 3 +-
drivers/gpu/drm/tiny/cirrus.c | 3 +-
include/drm/drm_format_helper.h | 9 ++---
5 files changed, 30 insertions(+), 48 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index 2b5c3746ff4a..8bf5655f5ce0 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -330,9 +330,9 @@ static void drm_fb_xrgb8888_to_rgb565_swab_line(void *dbuf,
const void *sbuf,
/**
* drm_fb_xrgb8888_to_rgb565 - Convert XRGB8888 to RGB565 clip buffer
- * @dst: RGB565 destination buffer
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
- * @vaddr: XRGB8888 source buffer
+ * @dst: Array of RGB565 destination buffers
+ * @dst_pitch: Array of numbers of bytes between two consecutive scanlines
within dst
+ * @vmap: Array of XRGB8888 source buffer
* @fb: DRM framebuffer
* @clip: Clip rectangle area to copy
* @swab: Swap bytes
@@ -340,43 +340,31 @@ static void drm_fb_xrgb8888_to_rgb565_swab_line(void
*dbuf, const void *sbuf,
* Drivers can use this function for RGB565 devices that don't natively
* support XRGB8888.
*/
-void drm_fb_xrgb8888_to_rgb565(void *dst, unsigned int dst_pitch, const void
*vaddr,
- const struct drm_framebuffer *fb, const struct drm_rect *clip,
- bool swab)
+void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip, bool swab)
{
+ static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
+ 0, 0, 0, 0
+ };
+ void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels);
+
if (swab)
- drm_fb_xfrm(dst, dst_pitch, 2, vaddr, fb, clip, false,
- drm_fb_xrgb8888_to_rgb565_swab_line);
+ xfrm_line = drm_fb_xrgb8888_to_rgb565_swab_line;
else
- drm_fb_xfrm(dst, dst_pitch, 2, vaddr, fb, clip, false,
- drm_fb_xrgb8888_to_rgb565_line);
-}
-EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb565);
+ xfrm_line = drm_fb_xrgb8888_to_rgb565_line;
-/**
- * drm_fb_xrgb8888_to_rgb565_toio - Convert XRGB8888 to RGB565 clip buffer
- * @dst: RGB565 destination buffer (iomem)
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
- * @vaddr: XRGB8888 source buffer
- * @fb: DRM framebuffer
- * @clip: Clip rectangle area to copy
- * @swab: Swap bytes
- *
- * Drivers can use this function for RGB565 devices that don't natively
- * support XRGB8888.
- */
-void drm_fb_xrgb8888_to_rgb565_toio(void __iomem *dst, unsigned int dst_pitch,
- const void *vaddr, const struct drm_framebuffer *fb,
- const struct drm_rect *clip, bool swab)
-{
- if (swab)
- drm_fb_xfrm_toio(dst, dst_pitch, 2, vaddr, fb, clip, false,
- drm_fb_xrgb8888_to_rgb565_swab_line);
+ if (!dst_pitch)
+ dst_pitch = default_dst_pitch;
+
+ if (dst[0].is_iomem)
+ drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 2, vmap[0].vaddr, fb,
clip,
+ false, xfrm_line);
else
- drm_fb_xfrm_toio(dst, dst_pitch, 2, vaddr, fb, clip, false,
- drm_fb_xrgb8888_to_rgb565_line);
+ drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 2, vmap[0].vaddr, fb, clip,
+ false, xfrm_line);
}
-EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb565_toio);
+EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb565);
static void drm_fb_xrgb8888_to_rgb888_line(void *dbuf, const void *sbuf,
unsigned int pixels)
{
@@ -605,8 +593,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int
*dst_pitch, uint32_t d
} else if (dst_format == DRM_FORMAT_RGB565) {
if (fb_format == DRM_FORMAT_XRGB8888) {
- drm_fb_xrgb8888_to_rgb565_toio(dst[0].vaddr_iomem, dst_pitch[0],
- vmap[0].vaddr, fb, clip, false);
+ drm_fb_xrgb8888_to_rgb565(dst, dst_pitch, vmap, fb, clip, false);
return 0;
}
} else if (dst_format == DRM_FORMAT_RGB888) {
diff --git a/drivers/gpu/drm/drm_mipi_dbi.c b/drivers/gpu/drm/drm_mipi_dbi.c
index 973a75585cad..d0bdbcb96705 100644
--- a/drivers/gpu/drm/drm_mipi_dbi.c
+++ b/drivers/gpu/drm/drm_mipi_dbi.c
@@ -206,7 +206,6 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb,
struct iosys_map map[DRM_FORMAT_MAX_PLANES];
struct iosys_map data[DRM_FORMAT_MAX_PLANES];
struct iosys_map dst_map = IOSYS_MAP_INIT_VADDR(dst);
- void *src;
int ret;
ret = drm_gem_fb_begin_cpu_access(fb, DMA_FROM_DEVICE);
@@ -216,7 +215,6 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb,
ret = drm_gem_fb_vmap(fb, map, data);
if (ret)
goto out_drm_gem_fb_end_cpu_access;
- src = data[0].vaddr; /* TODO: Use mapping abstraction properly */
switch (fb->format->format) {
case DRM_FORMAT_RGB565:
@@ -226,7 +224,7 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb,
drm_fb_memcpy(&dst_map, NULL, data, fb, clip);
break;
case DRM_FORMAT_XRGB8888:
- drm_fb_xrgb8888_to_rgb565(dst, 0, src, fb, clip, swap);
+ drm_fb_xrgb8888_to_rgb565(&dst_map, NULL, data, fb, clip, swap);
break;
default:
drm_err_once(fb->dev, "Format is not supported: %p4cc\n",
diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c
index 426a3ae6cc50..a43eb6645352 100644
--- a/drivers/gpu/drm/gud/gud_pipe.c
+++ b/drivers/gpu/drm/gud/gud_pipe.c
@@ -198,7 +198,8 @@ static int gud_prep_flush(struct gud_device *gdrm, struct
drm_framebuffer *fb,
} else if (format->format == DRM_FORMAT_RGB332) {
drm_fb_xrgb8888_to_rgb332(&dst, NULL, map_data, fb, rect);
} else if (format->format == DRM_FORMAT_RGB565) {
- drm_fb_xrgb8888_to_rgb565(buf, 0, vaddr, fb, rect, gud_is_big_endian());
+ drm_fb_xrgb8888_to_rgb565(&dst, NULL, map_data, fb, rect,
+ gud_is_big_endian());
} else if (format->format == DRM_FORMAT_RGB888) {
drm_fb_xrgb8888_to_rgb888(buf, 0, vaddr, fb, rect);
} else {
diff --git a/drivers/gpu/drm/tiny/cirrus.c b/drivers/gpu/drm/tiny/cirrus.c
index 73fb9f63d227..9cd398e4700b 100644
--- a/drivers/gpu/drm/tiny/cirrus.c
+++ b/drivers/gpu/drm/tiny/cirrus.c
@@ -335,8 +335,7 @@ static int cirrus_fb_blit_rect(struct drm_framebuffer *fb,
} else if (fb->format->cpp[0] == 4 && cirrus->cpp == 2) {
iosys_map_incr(&dst, drm_fb_clip_offset(cirrus->pitch, fb->format,
rect));
- drm_fb_xrgb8888_to_rgb565_toio(dst.vaddr_iomem, cirrus->pitch, vaddr, fb,
rect,
- false);
+ drm_fb_xrgb8888_to_rgb565(&dst, &cirrus->pitch, vmap, fb, rect,
false);
} else if (fb->format->cpp[0] == 4 && cirrus->cpp == 3) {
iosys_map_incr(&dst, drm_fb_clip_offset(cirrus->pitch, fb->format,
rect));
diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h
index 3c28f099e3ed..9f1d45d7ce84 100644
--- a/include/drm/drm_format_helper.h
+++ b/include/drm/drm_format_helper.h
@@ -23,12 +23,9 @@ void drm_fb_swab(struct iosys_map *dst, const unsigned int
*dst_pitch,
void drm_fb_xrgb8888_to_rgb332(struct iosys_map *dst, const unsigned int
*dst_pitch,
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip);
-void drm_fb_xrgb8888_to_rgb565(void *dst, unsigned int dst_pitch, const void
*vaddr,
- const struct drm_framebuffer *fb, const struct drm_rect *clip,
- bool swab);
-void drm_fb_xrgb8888_to_rgb565_toio(void __iomem *dst, unsigned int dst_pitch,
- const void *vaddr, const struct drm_framebuffer *fb,
- const struct drm_rect *clip, bool swab);
+void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip, bool swab);
void drm_fb_xrgb8888_to_rgb888(void *dst, unsigned int dst_pitch, const void
*src,
const struct drm_framebuffer *fb, const struct drm_rect *clip);
void drm_fb_xrgb8888_to_rgb888_toio(void __iomem *dst, unsigned int dst_pitch,
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 06/12] drm/format-helper: Rework XRGB8888-to-RGB888 conversion
Update XRGB8888-to-RGB888 conversion to support struct iosys_map
and convert all users. Although these are single-plane color formats,
the new interface supports multi-plane formats for consistency with
drm_fb_blit().
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 48 ++++++++++++-----------------
drivers/gpu/drm/gud/gud_pipe.c | 2 +-
drivers/gpu/drm/tiny/cirrus.c | 3 +-
include/drm/drm_format_helper.h | 8 ++---
4 files changed, 25 insertions(+), 36 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index 8bf5655f5ce0..4edab44336d8 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -383,41 +383,34 @@ static void drm_fb_xrgb8888_to_rgb888_line(void *dbuf,
const void *sbuf, unsigne
/**
* drm_fb_xrgb8888_to_rgb888 - Convert XRGB8888 to RGB888 clip buffer
- * @dst: RGB888 destination buffer
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
- * @src: XRGB8888 source buffer
+ * @dst: Array of RGB888 destination buffers
+ * @dst_pitch: Array of numbers of bytes between two consecutive scanlines
within dst
+ * @vmap: Array of XRGB8888 source buffers
* @fb: DRM framebuffer
* @clip: Clip rectangle area to copy
*
* Drivers can use this function for RGB888 devices that don't natively
* support XRGB8888.
*/
-void drm_fb_xrgb8888_to_rgb888(void *dst, unsigned int dst_pitch, const void
*src,
- const struct drm_framebuffer *fb, const struct drm_rect *clip)
+void drm_fb_xrgb8888_to_rgb888(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip)
{
- drm_fb_xfrm(dst, dst_pitch, 3, src, fb, clip, false,
drm_fb_xrgb8888_to_rgb888_line);
-}
-EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb888);
+ static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
+ 0, 0, 0, 0
+ };
-/**
- * drm_fb_xrgb8888_to_rgb888_toio - Convert XRGB8888 to RGB888 clip buffer
- * @dst: RGB565 destination buffer (iomem)
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
- * @vaddr: XRGB8888 source buffer
- * @fb: DRM framebuffer
- * @clip: Clip rectangle area to copy
- *
- * Drivers can use this function for RGB888 devices that don't natively
- * support XRGB8888.
- */
-void drm_fb_xrgb8888_to_rgb888_toio(void __iomem *dst, unsigned int dst_pitch,
- const void *vaddr, const struct drm_framebuffer *fb,
- const struct drm_rect *clip)
-{
- drm_fb_xfrm_toio(dst, dst_pitch, 3, vaddr, fb, clip, false,
- drm_fb_xrgb8888_to_rgb888_line);
+ if (!dst_pitch)
+ dst_pitch = default_dst_pitch;
+
+ if (dst[0].is_iomem)
+ drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 3, vmap[0].vaddr, fb,
+ clip, false, drm_fb_xrgb8888_to_rgb888_line);
+ else
+ drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 3, vmap[0].vaddr, fb,
+ clip, false, drm_fb_xrgb8888_to_rgb888_line);
}
-EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb888_toio);
+EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb888);
static void drm_fb_rgb565_to_xrgb8888_line(void *dbuf, const void *sbuf,
unsigned int pixels)
{
@@ -598,8 +591,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int
*dst_pitch, uint32_t d
}
} else if (dst_format == DRM_FORMAT_RGB888) {
if (fb_format == DRM_FORMAT_XRGB8888) {
- drm_fb_xrgb8888_to_rgb888_toio(dst[0].vaddr_iomem, dst_pitch[0],
- vmap[0].vaddr, fb, clip);
+ drm_fb_xrgb8888_to_rgb888(dst, dst_pitch, vmap, fb, clip);
return 0;
}
} else if (dst_format == DRM_FORMAT_XRGB8888) {
diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c
index a43eb6645352..0caa228f736d 100644
--- a/drivers/gpu/drm/gud/gud_pipe.c
+++ b/drivers/gpu/drm/gud/gud_pipe.c
@@ -201,7 +201,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct
drm_framebuffer *fb,
drm_fb_xrgb8888_to_rgb565(&dst, NULL, map_data, fb, rect,
gud_is_big_endian());
} else if (format->format == DRM_FORMAT_RGB888) {
- drm_fb_xrgb8888_to_rgb888(buf, 0, vaddr, fb, rect);
+ drm_fb_xrgb8888_to_rgb888(&dst, NULL, map_data, fb, rect);
} else {
len = gud_xrgb8888_to_color(buf, format, vaddr, fb, rect);
}
diff --git a/drivers/gpu/drm/tiny/cirrus.c b/drivers/gpu/drm/tiny/cirrus.c
index 9cd398e4700b..354d5e854a6f 100644
--- a/drivers/gpu/drm/tiny/cirrus.c
+++ b/drivers/gpu/drm/tiny/cirrus.c
@@ -321,7 +321,6 @@ static int cirrus_fb_blit_rect(struct drm_framebuffer *fb,
{
struct cirrus_device *cirrus = to_cirrus(fb->dev);
struct iosys_map dst;
- void *vaddr = vmap->vaddr; /* TODO: Use mapping abstraction properly */
int idx;
if (!drm_dev_enter(&cirrus->dev, &idx))
@@ -339,7 +338,7 @@ static int cirrus_fb_blit_rect(struct drm_framebuffer *fb,
} else if (fb->format->cpp[0] == 4 && cirrus->cpp == 3) {
iosys_map_incr(&dst, drm_fb_clip_offset(cirrus->pitch, fb->format,
rect));
- drm_fb_xrgb8888_to_rgb888_toio(dst.vaddr_iomem, cirrus->pitch, vaddr, fb,
rect);
+ drm_fb_xrgb8888_to_rgb888(&dst, &cirrus->pitch, vmap, fb, rect);
} else {
WARN_ON_ONCE("cpp mismatch");
diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h
index 9f1d45d7ce84..8c633dbab5d6 100644
--- a/include/drm/drm_format_helper.h
+++ b/include/drm/drm_format_helper.h
@@ -26,11 +26,9 @@ void drm_fb_xrgb8888_to_rgb332(struct iosys_map *dst, const
unsigned int *dst_pi
void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const unsigned int
*dst_pitch,
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip, bool swab);
-void drm_fb_xrgb8888_to_rgb888(void *dst, unsigned int dst_pitch, const void
*src,
- const struct drm_framebuffer *fb, const struct drm_rect *clip);
-void drm_fb_xrgb8888_to_rgb888_toio(void __iomem *dst, unsigned int dst_pitch,
- const void *vaddr, const struct drm_framebuffer *fb,
- const struct drm_rect *clip);
+void drm_fb_xrgb8888_to_rgb888(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip);
void drm_fb_xrgb8888_to_xrgb2101010_toio(void __iomem *dst, unsigned int
dst_pitch,
const void *vaddr, const struct drm_framebuffer *fb,
const struct drm_rect *clip);
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 07/12] drm/format-helper: Rework RGB565-to-XRGB8888 conversion
Update RGB565-to-XRGB8888 conversion to support struct iosys_map
and convert all users. Although these are single-plane color formats,
the new interface supports multi-plane formats for consistency with
drm_fb_blit().
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 25 ++++++++++++++++++-------
1 file changed, 18 insertions(+), 7 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index 4edab44336d8..5ef06f696657 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -430,12 +430,24 @@ static void drm_fb_rgb565_to_xrgb8888_line(void *dbuf,
const void *sbuf, unsigne
}
}
-static void drm_fb_rgb565_to_xrgb8888_toio(void __iomem *dst, unsigned int
dst_pitch,
- const void *vaddr, const struct drm_framebuffer *fb,
- const struct drm_rect *clip)
+static void drm_fb_rgb565_to_xrgb8888(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap,
+ const struct drm_framebuffer *fb,
+ const struct drm_rect *clip)
{
- drm_fb_xfrm_toio(dst, dst_pitch, 4, vaddr, fb, clip, false,
- drm_fb_rgb565_to_xrgb8888_line);
+ static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
+ 0, 0, 0, 0
+ };
+
+ if (!dst_pitch)
+ dst_pitch = default_dst_pitch;
+
+ if (dst[0].is_iomem)
+ drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb,
+ clip, false, drm_fb_rgb565_to_xrgb8888_line);
+ else
+ drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb,
+ clip, false, drm_fb_rgb565_to_xrgb8888_line);
}
static void drm_fb_rgb888_to_xrgb8888_line(void *dbuf, const void *sbuf,
unsigned int pixels)
@@ -600,8 +612,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int
*dst_pitch, uint32_t d
vmap[0].vaddr, fb, clip);
return 0;
} else if (fb_format == DRM_FORMAT_RGB565) {
- drm_fb_rgb565_to_xrgb8888_toio(dst[0].vaddr_iomem, dst_pitch[0],
- vmap[0].vaddr, fb, clip);
+ drm_fb_rgb565_to_xrgb8888(dst, dst_pitch, vmap, fb, clip);
return 0;
}
} else if (dst_format == DRM_FORMAT_XRGB2101010) {
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 08/12] drm/format-helper: Rework RGB888-to-XRGB8888 conversion
Update RGB888-to-XRGB8888 conversion to support struct iosys_map
and convert all users. Although these are single-plane color formats,
the new interface supports multi-plane formats for consistency with
drm_fb_blit().
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 25 ++++++++++++++++++-------
1 file changed, 18 insertions(+), 7 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index 5ef06f696657..155827eebe99 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -465,12 +465,24 @@ static void drm_fb_rgb888_to_xrgb8888_line(void *dbuf,
const void *sbuf, unsigne
}
}
-static void drm_fb_rgb888_to_xrgb8888_toio(void __iomem *dst, unsigned int
dst_pitch,
- const void *vaddr, const struct drm_framebuffer *fb,
- const struct drm_rect *clip)
+static void drm_fb_rgb888_to_xrgb8888(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap,
+ const struct drm_framebuffer *fb,
+ const struct drm_rect *clip)
{
- drm_fb_xfrm_toio(dst, dst_pitch, 4, vaddr, fb, clip, false,
- drm_fb_rgb888_to_xrgb8888_line);
+ static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
+ 0, 0, 0, 0
+ };
+
+ if (!dst_pitch)
+ dst_pitch = default_dst_pitch;
+
+ if (dst[0].is_iomem)
+ drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb,
+ clip, false, drm_fb_rgb888_to_xrgb8888_line);
+ else
+ drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb,
+ clip, false, drm_fb_rgb888_to_xrgb8888_line);
}
static void drm_fb_xrgb8888_to_xrgb2101010_line(void *dbuf, const void *sbuf,
unsigned int pixels)
@@ -608,8 +620,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int
*dst_pitch, uint32_t d
}
} else if (dst_format == DRM_FORMAT_XRGB8888) {
if (fb_format == DRM_FORMAT_RGB888) {
- drm_fb_rgb888_to_xrgb8888_toio(dst[0].vaddr_iomem, dst_pitch[0],
- vmap[0].vaddr, fb, clip);
+ drm_fb_rgb888_to_xrgb8888(dst, dst_pitch, vmap, fb, clip);
return 0;
} else if (fb_format == DRM_FORMAT_RGB565) {
drm_fb_rgb565_to_xrgb8888(dst, dst_pitch, vmap, fb, clip);
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 09/12] drm/format-helper: Rework XRGB8888-to-XRGB2101010 conversion
Update XRGB8888-to-XRGB2101010 conversion to support struct iosys_map
and convert all users. Although these are single-plane color formats,
the new interface supports multi-plane formats for consistency with
drm_fb_blit().
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 35 +++++++++++++++++------------
include/drm/drm_format_helper.h | 6 ++---
2 files changed, 24 insertions(+), 17 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index 155827eebe99..209f63b66c5f 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -504,26 +504,34 @@ static void drm_fb_xrgb8888_to_xrgb2101010_line(void
*dbuf, const void *sbuf, un
}
/**
- * drm_fb_xrgb8888_to_xrgb2101010_toio - Convert XRGB8888 to XRGB2101010 clip
- * buffer
- * @dst: XRGB2101010 destination buffer (iomem)
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
- * @vaddr: XRGB8888 source buffer
+ * drm_fb_xrgb8888_to_xrgb2101010 - Convert XRGB8888 to XRGB2101010 clip buffer
+ * @dst: Array of XRGB2101010 destination buffers
+ * @dst_pitch: Array of numbers of bytes between two consecutive scanlines
within dst
+ * @vmap: Array of XRGB8888 source buffers
* @fb: DRM framebuffer
* @clip: Clip rectangle area to copy
*
* Drivers can use this function for XRGB2101010 devices that don't
natively
* support XRGB8888.
*/
-void drm_fb_xrgb8888_to_xrgb2101010_toio(void __iomem *dst,
- unsigned int dst_pitch, const void *vaddr,
- const struct drm_framebuffer *fb,
- const struct drm_rect *clip)
+void drm_fb_xrgb8888_to_xrgb2101010(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip)
{
- drm_fb_xfrm_toio(dst, dst_pitch, 4, vaddr, fb, clip, false,
- drm_fb_xrgb8888_to_xrgb2101010_line);
+ static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
+ 0, 0, 0, 0
+ };
+
+ if (!dst_pitch)
+ dst_pitch = default_dst_pitch;
+
+ if (dst[0].is_iomem)
+ drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb,
+ clip, false, drm_fb_xrgb8888_to_xrgb2101010_line);
+ else
+ drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb,
+ clip, false, drm_fb_xrgb8888_to_xrgb2101010_line);
}
-EXPORT_SYMBOL(drm_fb_xrgb8888_to_xrgb2101010_toio);
static void drm_fb_xrgb8888_to_gray8_line(void *dbuf, const void *sbuf,
unsigned int pixels)
{
@@ -628,8 +636,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int
*dst_pitch, uint32_t d
}
} else if (dst_format == DRM_FORMAT_XRGB2101010) {
if (fb_format == DRM_FORMAT_XRGB8888) {
- drm_fb_xrgb8888_to_xrgb2101010_toio(dst[0].vaddr_iomem, dst_pitch[0],
- vmap[0].vaddr, fb, clip);
+ drm_fb_xrgb8888_to_xrgb2101010(dst, dst_pitch, vmap, fb, clip);
return 0;
}
}
diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h
index 8c633dbab5d6..6807440ce29c 100644
--- a/include/drm/drm_format_helper.h
+++ b/include/drm/drm_format_helper.h
@@ -29,9 +29,9 @@ void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const
unsigned int *dst_pi
void drm_fb_xrgb8888_to_rgb888(struct iosys_map *dst, const unsigned int
*dst_pitch,
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip);
-void drm_fb_xrgb8888_to_xrgb2101010_toio(void __iomem *dst, unsigned int
dst_pitch,
- const void *vaddr, const struct drm_framebuffer *fb,
- const struct drm_rect *clip);
+void drm_fb_xrgb8888_to_xrgb2101010(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip);
void drm_fb_xrgb8888_to_gray8(void *dst, unsigned int dst_pitch, const void
*vaddr,
const struct drm_framebuffer *fb, const struct drm_rect *clip);
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 10/12] drm/format-helper: Rework XRGB8888-to-GRAY8 conversion
Update XRGB8888-to-GRAY8 conversion to support struct iosys_map
and convert all users. Although these are single-plane color formats,
the new interface supports multi-plane formats for consistency with
drm_fb_blit().
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 25 +++++++++++++++++++------
drivers/gpu/drm/gud/gud_pipe.c | 7 +++++--
drivers/gpu/drm/tiny/st7586.c | 5 ++++-
include/drm/drm_format_helper.h | 5 +++--
4 files changed, 31 insertions(+), 11 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index 209f63b66c5f..521932fac491 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -552,9 +552,9 @@ static void drm_fb_xrgb8888_to_gray8_line(void *dbuf, const
void *sbuf, unsigned
/**
* drm_fb_xrgb8888_to_gray8 - Convert XRGB8888 to grayscale
- * @dst: 8-bit grayscale destination buffer
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
- * @vaddr: XRGB8888 source buffer
+ * @dst: Array of 8-bit grayscale destination buffers
+ * @dst_pitch: Array of number of bytes between two consecutive scanlines
within dst
+ * @vmap: Array of XRGB8888 source buffers
* @fb: DRM framebuffer
* @clip: Clip rectangle area to copy
*
@@ -567,10 +567,23 @@ static void drm_fb_xrgb8888_to_gray8_line(void *dbuf,
const void *sbuf, unsigned
*
* ITU BT.601 is used for the RGB -> luma (brightness) conversion.
*/
-void drm_fb_xrgb8888_to_gray8(void *dst, unsigned int dst_pitch, const void
*vaddr,
- const struct drm_framebuffer *fb, const struct drm_rect *clip)
+void drm_fb_xrgb8888_to_gray8(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip)
{
- drm_fb_xfrm(dst, dst_pitch, 1, vaddr, fb, clip, false,
drm_fb_xrgb8888_to_gray8_line);
+ static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
+ 0, 0, 0, 0
+ };
+
+ if (!dst_pitch)
+ dst_pitch = default_dst_pitch;
+
+ if (dst[0].is_iomem)
+ drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 1, vmap[0].vaddr, fb,
+ clip, false, drm_fb_xrgb8888_to_gray8_line);
+ else
+ drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 1, vmap[0].vaddr, fb,
+ clip, false, drm_fb_xrgb8888_to_gray8_line);
}
EXPORT_SYMBOL(drm_fb_xrgb8888_to_gray8);
diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c
index 0caa228f736d..7c6dc2bcd14a 100644
--- a/drivers/gpu/drm/gud/gud_pipe.c
+++ b/drivers/gpu/drm/gud/gud_pipe.c
@@ -59,6 +59,7 @@ static size_t gud_xrgb8888_to_r124(u8 *dst, const struct
drm_format_info *format
unsigned int bits_per_pixel = 8 / block_width;
unsigned int x, y, width, height;
u8 pix, *pix8, *block = dst; /* Assign to silence compiler warning */
+ struct iosys_map dst_map, vmap;
size_t len;
void *buf;
@@ -74,7 +75,9 @@ static size_t gud_xrgb8888_to_r124(u8 *dst, const struct
drm_format_info *format
if (!buf)
return 0;
- drm_fb_xrgb8888_to_gray8(buf, 0, src, fb, rect);
+ iosys_map_set_vaddr(&dst_map, buf);
+ iosys_map_set_vaddr(&vmap, src);
+ drm_fb_xrgb8888_to_gray8(&dst_map, NULL, &vmap, fb, rect);
pix8 = buf;
for (y = 0; y < height; y++) {
@@ -194,7 +197,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct
drm_framebuffer *fb,
goto end_cpu_access;
}
} else if (format->format == DRM_FORMAT_R8) {
- drm_fb_xrgb8888_to_gray8(buf, 0, vaddr, fb, rect);
+ drm_fb_xrgb8888_to_gray8(&dst, NULL, map_data, fb, rect);
} else if (format->format == DRM_FORMAT_RGB332) {
drm_fb_xrgb8888_to_rgb332(&dst, NULL, map_data, fb, rect);
} else if (format->format == DRM_FORMAT_RGB565) {
diff --git a/drivers/gpu/drm/tiny/st7586.c b/drivers/gpu/drm/tiny/st7586.c
index 8eddb020c43e..702350d0f8bc 100644
--- a/drivers/gpu/drm/tiny/st7586.c
+++ b/drivers/gpu/drm/tiny/st7586.c
@@ -69,12 +69,15 @@ static void st7586_xrgb8888_to_gray332(u8 *dst, void *vaddr,
size_t len = (clip->x2 - clip->x1) * (clip->y2 - clip->y1);
unsigned int x, y;
u8 *src, *buf, val;
+ struct iosys_map dst_map, vmap;
buf = kmalloc(len, GFP_KERNEL);
if (!buf)
return;
- drm_fb_xrgb8888_to_gray8(buf, 0, vaddr, fb, clip);
+ iosys_map_set_vaddr(&dst_map, buf);
+ iosys_map_set_vaddr(&vmap, vaddr);
+ drm_fb_xrgb8888_to_gray8(&dst_map, NULL, &vmap, fb, clip);
src = buf;
for (y = clip->y1; y < clip->y2; y++) {
diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h
index 6807440ce29c..68087c982497 100644
--- a/include/drm/drm_format_helper.h
+++ b/include/drm/drm_format_helper.h
@@ -32,8 +32,9 @@ void drm_fb_xrgb8888_to_rgb888(struct iosys_map *dst, const
unsigned int *dst_pi
void drm_fb_xrgb8888_to_xrgb2101010(struct iosys_map *dst, const unsigned int
*dst_pitch,
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip);
-void drm_fb_xrgb8888_to_gray8(void *dst, unsigned int dst_pitch, const void
*vaddr,
- const struct drm_framebuffer *fb, const struct drm_rect *clip);
+void drm_fb_xrgb8888_to_gray8(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip);
int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t
dst_format,
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 11/12] drm/format-helper: Rework XRGB8888-to-MONO conversion
Update XRGB8888-to-MONO conversion to support struct iosys_map
and convert all users. Although these are single-plane color formats,
the new interface supports multi-plane formats for consistency with
drm_fb_blit().
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 28 +++++++++++++++++++---------
drivers/gpu/drm/solomon/ssd130x.c | 7 ++++---
drivers/gpu/drm/tiny/repaper.c | 6 +++++-
include/drm/drm_format_helper.h | 5 +++--
4 files changed, 31 insertions(+), 15 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index 521932fac491..d296d181659d 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -680,9 +680,9 @@ static void drm_fb_gray8_to_mono_line(void *dbuf, const void
*sbuf, unsigned int
/**
* drm_fb_xrgb8888_to_mono - Convert XRGB8888 to monochrome
- * @dst: monochrome destination buffer (0=black, 1=white)
- * @dst_pitch: Number of bytes between two consecutive scanlines within dst
- * @vaddr: XRGB8888 source buffer
+ * @dst: Array of monochrome destination buffers (0=black, 1=white)
+ * @dst_pitch: Array of numbers of bytes between two consecutive scanlines
within dst
+ * @vmap: Array of XRGB8888 source buffers
* @fb: DRM framebuffer
* @clip: Clip rectangle area to copy
*
@@ -700,26 +700,36 @@ static void drm_fb_gray8_to_mono_line(void *dbuf, const
void *sbuf, unsigned int
* x-coordinate that is a multiple of 8, then the caller must take care itself
* of supplying a suitable clip rectangle.
*/
-void drm_fb_xrgb8888_to_mono(void *dst, unsigned int dst_pitch, const void
*vaddr,
- const struct drm_framebuffer *fb, const struct drm_rect *clip)
+void drm_fb_xrgb8888_to_mono(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip)
{
+ static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
+ 0, 0, 0, 0
+ };
unsigned int linepixels = drm_rect_width(clip);
unsigned int lines = drm_rect_height(clip);
unsigned int cpp = fb->format->cpp[0];
unsigned int len_src32 = linepixels * cpp;
struct drm_device *dev = fb->dev;
+ void *vaddr = vmap[0].vaddr;
+ unsigned int dst_pitch_0;
unsigned int y;
- u8 *mono = dst, *gray8;
+ u8 *mono = dst[0].vaddr, *gray8;
u32 *src32;
if (drm_WARN_ON(dev, fb->format->format != DRM_FORMAT_XRGB8888))
return;
+ if (!dst_pitch)
+ dst_pitch = default_dst_pitch;
+ dst_pitch_0 = dst_pitch[0];
+
/*
* The mono destination buffer contains 1 bit per pixel
*/
- if (!dst_pitch)
- dst_pitch = DIV_ROUND_UP(linepixels, 8);
+ if (!dst_pitch_0)
+ dst_pitch_0 = DIV_ROUND_UP(linepixels, 8);
/*
* The cma memory is write-combined so reads are uncached.
@@ -744,7 +754,7 @@ void drm_fb_xrgb8888_to_mono(void *dst, unsigned int
dst_pitch, const void *vadd
drm_fb_xrgb8888_to_gray8_line(gray8, src32, linepixels);
drm_fb_gray8_to_mono_line(mono, gray8, linepixels);
vaddr += fb->pitches[0];
- mono += dst_pitch;
+ mono += dst_pitch_0;
}
kfree(src32);
diff --git a/drivers/gpu/drm/solomon/ssd130x.c
b/drivers/gpu/drm/solomon/ssd130x.c
index 5a3e3b78cd9e..aa7329a65c98 100644
--- a/drivers/gpu/drm/solomon/ssd130x.c
+++ b/drivers/gpu/drm/solomon/ssd130x.c
@@ -537,11 +537,11 @@ static void ssd130x_clear_screen(struct ssd130x_device
*ssd130x)
kfree(buf);
}
-static int ssd130x_fb_blit_rect(struct drm_framebuffer *fb, const struct
iosys_map *map,
+static int ssd130x_fb_blit_rect(struct drm_framebuffer *fb, const struct
iosys_map *vmap,
struct drm_rect *rect)
{
struct ssd130x_device *ssd130x = drm_to_ssd130x(fb->dev);
- void *vmap = map->vaddr; /* TODO: Use mapping abstraction properly */
+ struct iosys_map dst;
unsigned int dst_pitch;
int ret = 0;
u8 *buf = NULL;
@@ -555,7 +555,8 @@ static int ssd130x_fb_blit_rect(struct drm_framebuffer *fb,
const struct iosys_m
if (!buf)
return -ENOMEM;
- drm_fb_xrgb8888_to_mono(buf, dst_pitch, vmap, fb, rect);
+ iosys_map_set_vaddr(&dst, buf);
+ drm_fb_xrgb8888_to_mono(&dst, &dst_pitch, vmap, fb, rect);
ssd130x_update_rect(ssd130x, buf, rect);
diff --git a/drivers/gpu/drm/tiny/repaper.c b/drivers/gpu/drm/tiny/repaper.c
index 013790c45d0a..0cdf6ab8fcc5 100644
--- a/drivers/gpu/drm/tiny/repaper.c
+++ b/drivers/gpu/drm/tiny/repaper.c
@@ -513,6 +513,8 @@ static int repaper_fb_dirty(struct drm_framebuffer *fb)
{
struct drm_gem_cma_object *cma_obj = drm_fb_cma_get_gem_obj(fb, 0);
struct repaper_epd *epd = drm_to_epd(fb->dev);
+ unsigned int dst_pitch = 0;
+ struct iosys_map dst, vmap;
struct drm_rect clip;
int idx, ret = 0;
u8 *buf = NULL;
@@ -541,7 +543,9 @@ static int repaper_fb_dirty(struct drm_framebuffer *fb)
if (ret)
goto out_free;
- drm_fb_xrgb8888_to_mono(buf, 0, cma_obj->vaddr, fb, &clip);
+ iosys_map_set_vaddr(&dst, buf);
+ iosys_map_set_vaddr(&vmap, cma_obj->vaddr);
+ drm_fb_xrgb8888_to_mono(&dst, &dst_pitch, &vmap, fb, &clip);
drm_gem_fb_end_cpu_access(fb, DMA_FROM_DEVICE);
diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h
index 68087c982497..1e1d8f356cc1 100644
--- a/include/drm/drm_format_helper.h
+++ b/include/drm/drm_format_helper.h
@@ -40,7 +40,8 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int
*dst_pitch, uint32_t d
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *rect);
-void drm_fb_xrgb8888_to_mono(void *dst, unsigned int dst_pitch, const void
*src,
- const struct drm_framebuffer *fb, const struct drm_rect *clip);
+void drm_fb_xrgb8888_to_mono(struct iosys_map *dst, const unsigned int
*dst_pitch,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip);
#endif /* __LINUX_DRM_FORMAT_HELPER_H */
--
2.37.1
Thomas Zimmermann
2022-Jul-27 11:33 UTC
[PATCH 12/12] drm/format-helper: Move destination-buffer handling into internal helper
The format-convertion helpers handle several cases for different
values of destination buffer and pitch. Move that code into the
internal helper drm_fb_xfrm() and avoid quite a bit of duplucation.
Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>
---
drivers/gpu/drm/drm_format_helper.c | 169 +++++++++++-----------------
1 file changed, 64 insertions(+), 105 deletions(-)
diff --git a/drivers/gpu/drm/drm_format_helper.c
b/drivers/gpu/drm/drm_format_helper.c
index d296d181659d..35aebdb90165 100644
--- a/drivers/gpu/drm/drm_format_helper.c
+++ b/drivers/gpu/drm/drm_format_helper.c
@@ -41,11 +41,11 @@ unsigned int drm_fb_clip_offset(unsigned int pitch, const
struct drm_format_info
}
EXPORT_SYMBOL(drm_fb_clip_offset);
-/* TODO: Make this functon work with multi-plane formats. */
-static int drm_fb_xfrm(void *dst, unsigned long dst_pitch, unsigned long
dst_pixsize,
- const void *vaddr, const struct drm_framebuffer *fb,
- const struct drm_rect *clip, bool vaddr_cached_hint,
- void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels))
+/* TODO: Make this function work with multi-plane formats. */
+static int __drm_fb_xfrm(void *dst, unsigned long dst_pitch, unsigned long
dst_pixsize,
+ const void *vaddr, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip, bool vaddr_cached_hint,
+ void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels))
{
unsigned long linepixels = drm_rect_width(clip);
unsigned long lines = drm_rect_height(clip);
@@ -84,11 +84,11 @@ static int drm_fb_xfrm(void *dst, unsigned long dst_pitch,
unsigned long dst_pix
return 0;
}
-/* TODO: Make this functon work with multi-plane formats. */
-static int drm_fb_xfrm_toio(void __iomem *dst, unsigned long dst_pitch,
unsigned long dst_pixsize,
- const void *vaddr, const struct drm_framebuffer *fb,
- const struct drm_rect *clip, bool vaddr_cached_hint,
- void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels))
+/* TODO: Make this function work with multi-plane formats. */
+static int __drm_fb_xfrm_toio(void __iomem *dst, unsigned long dst_pitch,
unsigned long dst_pixsize,
+ const void *vaddr, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip, bool vaddr_cached_hint,
+ void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels))
{
unsigned long linepixels = drm_rect_width(clip);
unsigned long lines = drm_rect_height(clip);
@@ -129,6 +129,29 @@ static int drm_fb_xfrm_toio(void __iomem *dst, unsigned
long dst_pitch, unsigned
return 0;
}
+/* TODO: Make this function work with multi-plane formats. */
+static int drm_fb_xfrm(struct iosys_map *dst,
+ const unsigned int *dst_pitch, const u8 *dst_pixsize,
+ const struct iosys_map *vmap, const struct drm_framebuffer *fb,
+ const struct drm_rect *clip, bool vaddr_cached_hint,
+ void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels))
+{
+ static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
+ 0, 0, 0, 0
+ };
+
+ if (!dst_pitch)
+ dst_pitch = default_dst_pitch;
+
+ if (dst[0].is_iomem)
+ return __drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], dst_pixsize[0],
+ vmap[0].vaddr, fb, clip, false, xfrm_line);
+ else
+ return __drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], dst_pixsize[0],
+ vmap[0].vaddr, fb, clip, false, xfrm_line);
+}
+
+
/**
* drm_fb_memcpy - Copy clip buffer
* @dst: Array of destination buffers
@@ -213,14 +236,10 @@ void drm_fb_swab(struct iosys_map *dst, const unsigned int
*dst_pitch,
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip, bool cached)
{
- static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
- 0, 0, 0, 0
- };
const struct drm_format_info *format = fb->format;
- u8 cpp = format->cpp[0];
void (*swab_line)(void *dbuf, const void *sbuf, unsigned int npixels);
- switch (cpp) {
+ switch (format->cpp[0]) {
case 4:
swab_line = drm_fb_swab32_line;
break;
@@ -230,21 +249,10 @@ void drm_fb_swab(struct iosys_map *dst, const unsigned int
*dst_pitch,
default:
drm_warn_once(fb->dev, "Format %p4cc has unsupported pixel
size.\n",
&format->format);
- swab_line = NULL;
- break;
- }
- if (!swab_line)
return;
+ }
- if (!dst_pitch)
- dst_pitch = default_dst_pitch;
-
- if (dst->is_iomem)
- drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], cpp,
- vmap[0].vaddr, fb, clip, cached, swab_line);
- else
- drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], cpp, vmap[0].vaddr, fb,
- clip, cached, swab_line);
+ drm_fb_xfrm(dst, dst_pitch, format->cpp, vmap, fb, clip, cached,
swab_line);
}
EXPORT_SYMBOL(drm_fb_swab);
@@ -277,19 +285,12 @@ void drm_fb_xrgb8888_to_rgb332(struct iosys_map *dst,
const unsigned int *dst_pi
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip)
{
- static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
- 0, 0, 0, 0
+ static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = {
+ 1,
};
- if (!dst_pitch)
- dst_pitch = default_dst_pitch;
-
- if (dst[0].is_iomem)
- drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 1, vmap[0].vaddr, fb,
clip,
- false, drm_fb_xrgb8888_to_rgb332_line);
- else
- drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 1, vmap[0].vaddr, fb, clip,
- false, drm_fb_xrgb8888_to_rgb332_line);
+ drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false,
+ drm_fb_xrgb8888_to_rgb332_line);
}
EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb332);
@@ -344,9 +345,10 @@ void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const
unsigned int *dst_pi
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip, bool swab)
{
- static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
- 0, 0, 0, 0
+ static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = {
+ 2,
};
+
void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels);
if (swab)
@@ -354,15 +356,7 @@ void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const
unsigned int *dst_pi
else
xfrm_line = drm_fb_xrgb8888_to_rgb565_line;
- if (!dst_pitch)
- dst_pitch = default_dst_pitch;
-
- if (dst[0].is_iomem)
- drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 2, vmap[0].vaddr, fb,
clip,
- false, xfrm_line);
- else
- drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 2, vmap[0].vaddr, fb, clip,
- false, xfrm_line);
+ drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false, xfrm_line);
}
EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb565);
@@ -396,19 +390,12 @@ void drm_fb_xrgb8888_to_rgb888(struct iosys_map *dst,
const unsigned int *dst_pi
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip)
{
- static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
- 0, 0, 0, 0
+ static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = {
+ 3,
};
- if (!dst_pitch)
- dst_pitch = default_dst_pitch;
-
- if (dst[0].is_iomem)
- drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 3, vmap[0].vaddr, fb,
- clip, false, drm_fb_xrgb8888_to_rgb888_line);
- else
- drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 3, vmap[0].vaddr, fb,
- clip, false, drm_fb_xrgb8888_to_rgb888_line);
+ drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false,
+ drm_fb_xrgb8888_to_rgb888_line);
}
EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb888);
@@ -435,19 +422,12 @@ static void drm_fb_rgb565_to_xrgb8888(struct iosys_map
*dst, const unsigned int
const struct drm_framebuffer *fb,
const struct drm_rect *clip)
{
- static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
- 0, 0, 0, 0
+ static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = {
+ 4,
};
- if (!dst_pitch)
- dst_pitch = default_dst_pitch;
-
- if (dst[0].is_iomem)
- drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb,
- clip, false, drm_fb_rgb565_to_xrgb8888_line);
- else
- drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb,
- clip, false, drm_fb_rgb565_to_xrgb8888_line);
+ drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false,
+ drm_fb_rgb565_to_xrgb8888_line);
}
static void drm_fb_rgb888_to_xrgb8888_line(void *dbuf, const void *sbuf,
unsigned int pixels)
@@ -470,19 +450,12 @@ static void drm_fb_rgb888_to_xrgb8888(struct iosys_map
*dst, const unsigned int
const struct drm_framebuffer *fb,
const struct drm_rect *clip)
{
- static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
- 0, 0, 0, 0
+ static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = {
+ 4,
};
- if (!dst_pitch)
- dst_pitch = default_dst_pitch;
-
- if (dst[0].is_iomem)
- drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb,
- clip, false, drm_fb_rgb888_to_xrgb8888_line);
- else
- drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb,
- clip, false, drm_fb_rgb888_to_xrgb8888_line);
+ drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false,
+ drm_fb_rgb888_to_xrgb8888_line);
}
static void drm_fb_xrgb8888_to_xrgb2101010_line(void *dbuf, const void *sbuf,
unsigned int pixels)
@@ -518,19 +491,12 @@ void drm_fb_xrgb8888_to_xrgb2101010(struct iosys_map *dst,
const unsigned int *d
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip)
{
- static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
- 0, 0, 0, 0
+ static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = {
+ 4,
};
- if (!dst_pitch)
- dst_pitch = default_dst_pitch;
-
- if (dst[0].is_iomem)
- drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb,
- clip, false, drm_fb_xrgb8888_to_xrgb2101010_line);
- else
- drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb,
- clip, false, drm_fb_xrgb8888_to_xrgb2101010_line);
+ drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false,
+ drm_fb_xrgb8888_to_xrgb2101010_line);
}
static void drm_fb_xrgb8888_to_gray8_line(void *dbuf, const void *sbuf,
unsigned int pixels)
@@ -571,19 +537,12 @@ void drm_fb_xrgb8888_to_gray8(struct iosys_map *dst, const
unsigned int *dst_pit
const struct iosys_map *vmap, const struct drm_framebuffer *fb,
const struct drm_rect *clip)
{
- static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = {
- 0, 0, 0, 0
+ static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = {
+ 1,
};
- if (!dst_pitch)
- dst_pitch = default_dst_pitch;
-
- if (dst[0].is_iomem)
- drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 1, vmap[0].vaddr, fb,
- clip, false, drm_fb_xrgb8888_to_gray8_line);
- else
- drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 1, vmap[0].vaddr, fb,
- clip, false, drm_fb_xrgb8888_to_gray8_line);
+ drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false,
+ drm_fb_xrgb8888_to_gray8_line);
}
EXPORT_SYMBOL(drm_fb_xrgb8888_to_gray8);
--
2.37.1
Hi Thomas, On Wed, Jul 27, 2022 at 01:33:01PM +0200, Thomas Zimmermann wrote:> Provide drm_fb_blit() that works with struct iosys_map. Update all > users of drm_fb_blit_toio(), which required a destination buffer in > I/O memory. The new function's interface works with multi-plane > color formats, although the implementation only supports a single > plane for now. > > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de> > --- > drivers/gpu/drm/drm_format_helper.c | 39 ++++++++++++++++++----------- > drivers/gpu/drm/tiny/simpledrm.c | 18 +++++++------ > include/drm/drm_format_helper.h | 7 +++--- > 3 files changed, 38 insertions(+), 26 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index c6182b5de78b..4d74d46ab155 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -8,9 +8,10 @@ > * (at your option) any later version. > */ > > +#include <linux/io.h> > +#include <linux/iosys-map.h> > #include <linux/module.h> > #include <linux/slab.h> > -#include <linux/io.h> > > #include <drm/drm_device.h> > #include <drm/drm_format_helper.h> > @@ -545,9 +546,9 @@ void drm_fb_xrgb8888_to_gray8(void *dst, unsigned int dst_pitch, const void *vad > EXPORT_SYMBOL(drm_fb_xrgb8888_to_gray8); > > /** > - * drm_fb_blit_toio - Copy parts of a framebuffer to display memory > - * @dst: The display memory to copy to > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > + * drm_fb_blit - Copy parts of a framebuffer to display memory > + * @dst: Array of display-memory addresses to copy to > + * @dst_pitch: Array of numbers of bytes between two consecutive scanlines within dstThe rename confused me since this function continue to operate only on io memory, but I see that this is all fixed up in later patches. It would be nice to have this mentioned in the changelog, just in case someone else takes a deeper look at it. With the changelog updated: Reviewed-by: Sam Ravnborg <sam at ravnborg.org> See also comments below.> * @dst_format: FOURCC code of the display's color format > * @vmap: The framebuffer memory to copy from > * @fb: The framebuffer to copy from > @@ -557,14 +558,18 @@ EXPORT_SYMBOL(drm_fb_xrgb8888_to_gray8); > * formats of the display and the framebuffer mismatch, the blit function > * will attempt to convert between them. > * > + * The parameters @dst, @dst_pitch and @vmap refer to arrays. Each array must > + * have at least as many entries as there are planes in @dst_format's format. Each > + * entry stores the value for the format's respective color plane at the same index. > + * > * Returns: > * 0 on success, or > * -EINVAL if the color-format conversion failed, or > * a negative error code otherwise. > */ > -int drm_fb_blit_toio(void __iomem *dst, unsigned int dst_pitch, uint32_t dst_format, > - const void *vmap, const struct drm_framebuffer *fb, > - const struct drm_rect *clip) > +int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t dst_format, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip) > { > uint32_t fb_format = fb->format->format; > > @@ -579,30 +584,35 @@ int drm_fb_blit_toio(void __iomem *dst, unsigned int dst_pitch, uint32_t dst_for > dst_format = DRM_FORMAT_XRGB2101010; > > if (dst_format == fb_format) { > - drm_fb_memcpy_toio(dst, dst_pitch, vmap, fb, clip); > + drm_fb_memcpy_toio(dst[0].vaddr_iomem, dst_pitch[0], vmap[0].vaddr, fb, clip); > return 0; > > } else if (dst_format == DRM_FORMAT_RGB565) { > if (fb_format == DRM_FORMAT_XRGB8888) { > - drm_fb_xrgb8888_to_rgb565_toio(dst, dst_pitch, vmap, fb, clip, false); > + drm_fb_xrgb8888_to_rgb565_toio(dst[0].vaddr_iomem, dst_pitch[0], > + vmap[0].vaddr, fb, clip, false); > return 0; > } > } else if (dst_format == DRM_FORMAT_RGB888) { > if (fb_format == DRM_FORMAT_XRGB8888) { > - drm_fb_xrgb8888_to_rgb888_toio(dst, dst_pitch, vmap, fb, clip); > + drm_fb_xrgb8888_to_rgb888_toio(dst[0].vaddr_iomem, dst_pitch[0], > + vmap[0].vaddr, fb, clip); > return 0; > } > } else if (dst_format == DRM_FORMAT_XRGB8888) { > if (fb_format == DRM_FORMAT_RGB888) { > - drm_fb_rgb888_to_xrgb8888_toio(dst, dst_pitch, vmap, fb, clip); > + drm_fb_rgb888_to_xrgb8888_toio(dst[0].vaddr_iomem, dst_pitch[0], > + vmap[0].vaddr, fb, clip); > return 0; > } else if (fb_format == DRM_FORMAT_RGB565) { > - drm_fb_rgb565_to_xrgb8888_toio(dst, dst_pitch, vmap, fb, clip); > + drm_fb_rgb565_to_xrgb8888_toio(dst[0].vaddr_iomem, dst_pitch[0], > + vmap[0].vaddr, fb, clip); > return 0; > } > } else if (dst_format == DRM_FORMAT_XRGB2101010) { > if (fb_format == DRM_FORMAT_XRGB8888) { > - drm_fb_xrgb8888_to_xrgb2101010_toio(dst, dst_pitch, vmap, fb, clip); > + drm_fb_xrgb8888_to_xrgb2101010_toio(dst[0].vaddr_iomem, dst_pitch[0], > + vmap[0].vaddr, fb, clip); > return 0; > } > } > @@ -612,8 +622,7 @@ int drm_fb_blit_toio(void __iomem *dst, unsigned int dst_pitch, uint32_t dst_for > > return -EINVAL; > } > -EXPORT_SYMBOL(drm_fb_blit_toio); > - > +EXPORT_SYMBOL(drm_fb_blit); > > static void drm_fb_gray8_to_mono_line(void *dbuf, const void *sbuf, unsigned int pixels) > { > diff --git a/drivers/gpu/drm/tiny/simpledrm.c b/drivers/gpu/drm/tiny/simpledrm.c > index 5422363690e7..1ec73bec0513 100644 > --- a/drivers/gpu/drm/tiny/simpledrm.c > +++ b/drivers/gpu/drm/tiny/simpledrm.c > @@ -652,9 +652,8 @@ simpledrm_simple_display_pipe_enable(struct drm_simple_display_pipe *pipe, > struct simpledrm_device *sdev = simpledrm_device_of_dev(pipe->crtc.dev); > struct drm_shadow_plane_state *shadow_plane_state = to_drm_shadow_plane_state(plane_state); > struct drm_framebuffer *fb = plane_state->fb; > - void *vmap = shadow_plane_state->data[0].vaddr; /* TODO: Use mapping abstraction */ > struct drm_device *dev = &sdev->dev; > - void __iomem *dst = sdev->screen_base; > + struct iosys_map dst;Maybe struct iosys_map dst = IOSYS_MAP_INIT_VADDR(sdev->screen_base);> struct drm_rect src_clip, dst_clip; > int idx; > > @@ -670,8 +669,10 @@ simpledrm_simple_display_pipe_enable(struct drm_simple_display_pipe *pipe, > if (!drm_dev_enter(dev, &idx)) > return; > > - dst += drm_fb_clip_offset(sdev->pitch, sdev->format, &dst_clip); > - drm_fb_blit_toio(dst, sdev->pitch, sdev->format->format, vmap, fb, &src_clip); > + iosys_map_set_vaddr_iomem(&dst, sdev->screen_base); > + iosys_map_incr(&dst, drm_fb_clip_offset(sdev->pitch, sdev->format, &dst_clip)); > + drm_fb_blit(&dst, &sdev->pitch, sdev->format->format, > + shadow_plane_state->data, fb, &src_clip); > > drm_dev_exit(idx); > } > @@ -699,10 +700,9 @@ simpledrm_simple_display_pipe_update(struct drm_simple_display_pipe *pipe, > struct simpledrm_device *sdev = simpledrm_device_of_dev(pipe->crtc.dev); > struct drm_plane_state *plane_state = pipe->plane.state; > struct drm_shadow_plane_state *shadow_plane_state = to_drm_shadow_plane_state(plane_state); > - void *vmap = shadow_plane_state->data[0].vaddr; /* TODO: Use mapping abstraction */ > struct drm_framebuffer *fb = plane_state->fb; > struct drm_device *dev = &sdev->dev; > - void __iomem *dst = sdev->screen_base; > + struct iosys_map dst;Likewise: struct iosys_map dst = IOSYS_MAP_INIT_VADDR(sdev->screen_base);> struct drm_rect src_clip, dst_clip; > int idx; > > @@ -719,8 +719,10 @@ simpledrm_simple_display_pipe_update(struct drm_simple_display_pipe *pipe, > if (!drm_dev_enter(dev, &idx)) > return; > > - dst += drm_fb_clip_offset(sdev->pitch, sdev->format, &dst_clip); > - drm_fb_blit_toio(dst, sdev->pitch, sdev->format->format, vmap, fb, &src_clip); > + iosys_map_set_vaddr_iomem(&dst, sdev->screen_base); > + iosys_map_incr(&dst, drm_fb_clip_offset(sdev->pitch, sdev->format, &dst_clip)); > + drm_fb_blit(&dst, &sdev->pitch, sdev->format->format, > + shadow_plane_state->data, fb, &src_clip); > > drm_dev_exit(idx); > } > diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h > index 55145eca0782..21daea7fda99 100644 > --- a/include/drm/drm_format_helper.h > +++ b/include/drm/drm_format_helper.h > @@ -6,6 +6,7 @@ > #ifndef __LINUX_DRM_FORMAT_HELPER_H > #define __LINUX_DRM_FORMAT_HELPER_H > > +struct iosys_map; > struct drm_format_info; > struct drm_framebuffer; > struct drm_rect; > @@ -39,9 +40,9 @@ void drm_fb_xrgb8888_to_xrgb2101010_toio(void __iomem *dst, unsigned int dst_pit > void drm_fb_xrgb8888_to_gray8(void *dst, unsigned int dst_pitch, const void *vaddr, > const struct drm_framebuffer *fb, const struct drm_rect *clip); > > -int drm_fb_blit_toio(void __iomem *dst, unsigned int dst_pitch, uint32_t dst_format, > - const void *vmap, const struct drm_framebuffer *fb, > - const struct drm_rect *rect); > +int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t dst_format, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *rect); > > void drm_fb_xrgb8888_to_mono(void *dst, unsigned int dst_pitch, const void *src, > const struct drm_framebuffer *fb, const struct drm_rect *clip); > -- > 2.37.1
Sam Ravnborg
2022-Aug-04 19:52 UTC
[PATCH 02/12] drm/format-helper: Merge drm_fb_memcpy() and drm_fb_memcpy_toio()
Hi Thomas, On Wed, Jul 27, 2022 at 01:33:02PM +0200, Thomas Zimmermann wrote:> Merge drm_fb_memcpy() and drm_fb_memcpy() into drm_fb_memcpy() thatOne of these is drm_fb_memcpy_toio()> uses struct iosys_map for buffers. The new function also supports > multi-plane color formats. Convert all users of the original helpers.A few comments in the patch below. Sam> > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de> > --- > drivers/gpu/drm/drm_format_helper.c | 77 +++++++++------------ > drivers/gpu/drm/drm_mipi_dbi.c | 3 +- > drivers/gpu/drm/gud/gud_pipe.c | 4 +- > drivers/gpu/drm/hyperv/hyperv_drm_modeset.c | 11 +-- > drivers/gpu/drm/mgag200/mgag200_mode.c | 11 +-- > drivers/gpu/drm/tiny/cirrus.c | 21 +++--- > include/drm/drm_format_helper.h | 7 +- > 7 files changed, 63 insertions(+), 71 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index 4d74d46ab155..49589b442f18 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -131,63 +131,48 @@ static int drm_fb_xfrm_toio(void __iomem *dst, unsigned long dst_pitch, unsigned > > /** > * drm_fb_memcpy - Copy clip buffer > - * @dst: Destination buffer > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > - * @vaddr: Source buffer > + * @dst: Array of destination buffers > + * @dst_pitch: Array of numbers of bytes between two consecutive scanlines within dstDocument that this may be NULL, in which case the distance is considered 0.> + * @vmap: Array of source buffersIt would have helped my understanding if this argument was named src, so it is a little more obvious that we copy from src to dst. Maybe document that data is copied from src based on the pitch info in the framebuffer, and likewise the format_info in the framebuffer.> * @fb: DRM framebuffer > * @clip: Clip rectangle area to copy > * > * This function does not apply clipping on dst, i.e. the destination > * is at the top-left corner. > */ > -void drm_fb_memcpy(void *dst, unsigned int dst_pitch, const void *vaddr, > - const struct drm_framebuffer *fb, const struct drm_rect *clip) > +void drm_fb_memcpy(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip) > { > - unsigned int cpp = fb->format->cpp[0]; > - size_t len = (clip->x2 - clip->x1) * cpp; > - unsigned int y, lines = clip->y2 - clip->y1; > - > - if (!dst_pitch) > - dst_pitch = len; > + static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > + 0, 0, 0, 0 > + };This is used in several places in this series. What I read is that a static variable is declared where the first element in the array is set to all zeroes. But the other elements in the array are ignored - but since it is static they are also set to 0 so we are good here. In some cases I see it removed again, I did not check the end result if we end up dropping them all again.> > - vaddr += clip_offset(clip, fb->pitches[0], cpp); > - for (y = 0; y < lines; y++) { > - memcpy(dst, vaddr, len); > - vaddr += fb->pitches[0]; > - dst += dst_pitch; > - } > -} > -EXPORT_SYMBOL(drm_fb_memcpy); > - > -/** > - * drm_fb_memcpy_toio - Copy clip buffer > - * @dst: Destination buffer (iomem) > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > - * @vaddr: Source buffer > - * @fb: DRM framebuffer > - * @clip: Clip rectangle area to copy > - * > - * This function does not apply clipping on dst, i.e. the destination > - * is at the top-left corner. > - */ > -void drm_fb_memcpy_toio(void __iomem *dst, unsigned int dst_pitch, const void *vaddr, > - const struct drm_framebuffer *fb, const struct drm_rect *clip) > -{ > - unsigned int cpp = fb->format->cpp[0]; > - size_t len = (clip->x2 - clip->x1) * cpp; > - unsigned int y, lines = clip->y2 - clip->y1; > + const struct drm_format_info *format = fb->format; > + unsigned int i, y, lines = drm_rect_height(clip); > > if (!dst_pitch) > - dst_pitch = len; > - > - vaddr += clip_offset(clip, fb->pitches[0], cpp); > - for (y = 0; y < lines; y++) { > - memcpy_toio(dst, vaddr, len); > - vaddr += fb->pitches[0]; > - dst += dst_pitch; > + dst_pitch = default_dst_pitch; > + > + for (i = 0; i < format->num_planes; ++i) { > + unsigned int cpp_i = format->cpp[i];unsigned int cpp_i = drm_format_info_bpp(format, i) / 8; This avoid adding more uses of the deprecated cpp[] array.> + size_t len_i = drm_rect_width(clip) * cpp_i; > + unsigned int dst_pitch_i = dst_pitch[i]; > + struct iosys_map dst_i = dst[i]; > + struct iosys_map vmap_i = vmap[i];WARN_ON_ONCE(dst_i == NULL)? WARN_ON_ONCE(vmap_i == NULL)? Or something else so we error out somehow if we do not have enough planes in dst or src (vmap).> + > + if (!dst_pitch_i) > + dst_pitch_i = len_i;If there can be NULL in the dst_pitch array, this should be documented above I think. I do not like the current dst pitch workaround, but I failed to come up with something better.> + > + iosys_map_incr(&vmap_i, clip_offset(clip, fb->pitches[i], cpp_i)); > + for (y = 0; y < lines; y++) { > + iosys_map_memcpy_to(&dst_i, 0, vmap_i.vaddr, len_i);This hardcodes (vmap_i.vaddr) that vmap (src) is system memory. From a quick look this is not fixed in a later patch. At minimum add a TODO entry here.> + iosys_map_incr(&vmap_i, fb->pitches[i]); > + iosys_map_incr(&dst_i, dst_pitch_i); > + } > } > } > -EXPORT_SYMBOL(drm_fb_memcpy_toio); > +EXPORT_SYMBOL(drm_fb_memcpy); > > static void drm_fb_swab16_line(void *dbuf, const void *sbuf, unsigned int pixels) > { > @@ -584,7 +569,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t d > dst_format = DRM_FORMAT_XRGB2101010; > > if (dst_format == fb_format) { > - drm_fb_memcpy_toio(dst[0].vaddr_iomem, dst_pitch[0], vmap[0].vaddr, fb, clip); > + drm_fb_memcpy(dst, dst_pitch, vmap, fb, clip); > return 0; > > } else if (dst_format == DRM_FORMAT_RGB565) { > diff --git a/drivers/gpu/drm/drm_mipi_dbi.c b/drivers/gpu/drm/drm_mipi_dbi.c > index 2f61f53d472f..22451806fb5c 100644 > --- a/drivers/gpu/drm/drm_mipi_dbi.c > +++ b/drivers/gpu/drm/drm_mipi_dbi.c > @@ -205,6 +205,7 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb, > struct drm_gem_object *gem = drm_gem_fb_get_obj(fb, 0); > struct iosys_map map[DRM_FORMAT_MAX_PLANES]; > struct iosys_map data[DRM_FORMAT_MAX_PLANES]; > + struct iosys_map dst_map = IOSYS_MAP_INIT_VADDR(dst); > void *src; > int ret; > > @@ -222,7 +223,7 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb, > if (swap) > drm_fb_swab(dst, 0, src, fb, clip, !gem->import_attach); > else > - drm_fb_memcpy(dst, 0, src, fb, clip); > + drm_fb_memcpy(&dst_map, NULL, data, fb, clip); > break; > case DRM_FORMAT_XRGB8888: > drm_fb_xrgb8888_to_rgb565(dst, 0, src, fb, clip, swap); > diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c > index d42592f6daab..449c95a4aee0 100644 > --- a/drivers/gpu/drm/gud/gud_pipe.c > +++ b/drivers/gpu/drm/gud/gud_pipe.c > @@ -156,6 +156,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct drm_framebuffer *fb, > u8 compression = gdrm->compression; > struct iosys_map map[DRM_FORMAT_MAX_PLANES]; > struct iosys_map map_data[DRM_FORMAT_MAX_PLANES]; > + struct iosys_map dst; > void *vaddr, *buf; > size_t pitch, len; > int ret = 0; > @@ -179,6 +180,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct drm_framebuffer *fb, > buf = gdrm->compress_buf; > else > buf = gdrm->bulk_buf; > + iosys_map_set_vaddr(&dst, buf); > > /* > * Imported buffers are assumed to be write-combined and thus uncached > @@ -208,7 +210,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct drm_framebuffer *fb, > /* can compress directly from the framebuffer */ > buf = vaddr + rect->y1 * pitch; > } else { > - drm_fb_memcpy(buf, 0, vaddr, fb, rect); > + drm_fb_memcpy(&dst, NULL, map_data, fb, rect); > > memset(req, 0, sizeof(*req)); > diff --git a/drivers/gpu/drm/hyperv/hyperv_drm_modeset.c b/drivers/gpu/drm/hyperv/hyperv_drm_modeset.c > index b8e64dd8d3a6..26e63148e226 100644 > --- a/drivers/gpu/drm/hyperv/hyperv_drm_modeset.c > +++ b/drivers/gpu/drm/hyperv/hyperv_drm_modeset.c > @@ -21,19 +21,20 @@ > #include "hyperv_drm.h" > > static int hyperv_blit_to_vram_rect(struct drm_framebuffer *fb, > - const struct iosys_map *map, > + const struct iosys_map *vmap, > struct drm_rect *rect) > { > struct hyperv_drm_device *hv = to_hv(fb->dev); > - void __iomem *dst = hv->vram; > - void *vmap = map->vaddr; /* TODO: Use mapping abstraction properly */ > + struct iosys_map dst; > int idx; > > if (!drm_dev_enter(&hv->dev, &idx)) > return -ENODEV; > > - dst += drm_fb_clip_offset(fb->pitches[0], fb->format, rect); > - drm_fb_memcpy_toio(dst, fb->pitches[0], vmap, fb, rect); > + iosys_map_set_vaddr_iomem(&dst, hv->vram); > + iosys_map_incr(&dst, drm_fb_clip_offset(fb->pitches[0], fb->format, rect)); > + > + drm_fb_memcpy(&dst, fb->pitches, vmap, fb, rect); > > drm_dev_exit(idx); > > diff --git a/drivers/gpu/drm/mgag200/mgag200_mode.c b/drivers/gpu/drm/mgag200/mgag200_mode.c > index a02f599cb9cf..a79a0ee3a50d 100644 > --- a/drivers/gpu/drm/mgag200/mgag200_mode.c > +++ b/drivers/gpu/drm/mgag200/mgag200_mode.c > @@ -755,13 +755,14 @@ mgag200_simple_display_pipe_mode_valid(struct drm_simple_display_pipe *pipe, > > static void > mgag200_handle_damage(struct mga_device *mdev, struct drm_framebuffer *fb, > - struct drm_rect *clip, const struct iosys_map *map) > + struct drm_rect *clip, const struct iosys_map *vmap) > { > - void __iomem *dst = mdev->vram; > - void *vmap = map->vaddr; /* TODO: Use mapping abstraction properly */ > + struct iosys_map dst;Or use struct iosys_map dst = IOSYS_MAP_INIT_VADDR(mdev->vram); There is no drm_dev_enter() here we need to pass first, like in hyperv_drm_modeset.c above.> > - dst += drm_fb_clip_offset(fb->pitches[0], fb->format, clip); > - drm_fb_memcpy_toio(dst, fb->pitches[0], vmap, fb, clip); > + iosys_map_set_vaddr_iomem(&dst, mdev->vram); > + iosys_map_incr(&dst, drm_fb_clip_offset(fb->pitches[0], fb->format, clip)); > + > + drm_fb_memcpy(&dst, fb->pitches, vmap, fb, clip); > } > > static void > diff --git a/drivers/gpu/drm/tiny/cirrus.c b/drivers/gpu/drm/tiny/cirrus.c > index c4f5beea1f90..73fb9f63d227 100644 > --- a/drivers/gpu/drm/tiny/cirrus.c > +++ b/drivers/gpu/drm/tiny/cirrus.c > @@ -316,28 +316,31 @@ static int cirrus_mode_set(struct cirrus_device *cirrus, > } > > static int cirrus_fb_blit_rect(struct drm_framebuffer *fb, > - const struct iosys_map *map, > + const struct iosys_map *vmap, > struct drm_rect *rect) > { > struct cirrus_device *cirrus = to_cirrus(fb->dev); > - void __iomem *dst = cirrus->vram; > - void *vmap = map->vaddr; /* TODO: Use mapping abstraction properly */ > + struct iosys_map dst; > + void *vaddr = vmap->vaddr; /* TODO: Use mapping abstraction properly */ > int idx; > > if (!drm_dev_enter(&cirrus->dev, &idx)) > return -ENODEV; > > + iosys_map_set_vaddr_iomem(&dst, cirrus->vram); > + > if (cirrus->cpp == fb->format->cpp[0]) { > - dst += drm_fb_clip_offset(fb->pitches[0], fb->format, rect); > - drm_fb_memcpy_toio(dst, fb->pitches[0], vmap, fb, rect); > + iosys_map_incr(&dst, drm_fb_clip_offset(fb->pitches[0], fb->format, rect)); > + drm_fb_memcpy(&dst, fb->pitches, vmap, fb, rect); > > } else if (fb->format->cpp[0] == 4 && cirrus->cpp == 2) { > - dst += drm_fb_clip_offset(cirrus->pitch, fb->format, rect); > - drm_fb_xrgb8888_to_rgb565_toio(dst, cirrus->pitch, vmap, fb, rect, false); > + iosys_map_incr(&dst, drm_fb_clip_offset(cirrus->pitch, fb->format, rect)); > + drm_fb_xrgb8888_to_rgb565_toio(dst.vaddr_iomem, cirrus->pitch, vaddr, fb, rect, > + false); > > } else if (fb->format->cpp[0] == 4 && cirrus->cpp == 3) { > - dst += drm_fb_clip_offset(cirrus->pitch, fb->format, rect); > - drm_fb_xrgb8888_to_rgb888_toio(dst, cirrus->pitch, vmap, fb, rect); > + iosys_map_incr(&dst, drm_fb_clip_offset(cirrus->pitch, fb->format, rect)); > + drm_fb_xrgb8888_to_rgb888_toio(dst.vaddr_iomem, cirrus->pitch, vaddr, fb, rect); > > } else { > WARN_ON_ONCE("cpp mismatch"); > diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h > index 21daea7fda99..8af6a2717bc9 100644 > --- a/include/drm/drm_format_helper.h > +++ b/include/drm/drm_format_helper.h > @@ -14,10 +14,9 @@ struct drm_rect; > unsigned int drm_fb_clip_offset(unsigned int pitch, const struct drm_format_info *format, > const struct drm_rect *clip); > > -void drm_fb_memcpy(void *dst, unsigned int dst_pitch, const void *vaddr, > - const struct drm_framebuffer *fb, const struct drm_rect *clip); > -void drm_fb_memcpy_toio(void __iomem *dst, unsigned int dst_pitch, const void *vaddr, > - const struct drm_framebuffer *fb, const struct drm_rect *clip); > +void drm_fb_memcpy(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip); > void drm_fb_swab(void *dst, unsigned int dst_pitch, const void *src, > const struct drm_framebuffer *fb, const struct drm_rect *clip, > bool cached); > -- > 2.37.1
Sam Ravnborg
2022-Aug-04 20:08 UTC
[PATCH 03/12] drm/format-helper: Convert drm_fb_swab() to struct iosys_map
Hi Thomas, On Wed, Jul 27, 2022 at 01:33:03PM +0200, Thomas Zimmermann wrote:> Convert drm_fb_swab() to use struct iosys_map() and convert users. The > new interface supports multi-plane color formats.It swabs only plane[0], sbut this is maybe enough to say so. A few comments in the following. Sam> > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de> > --- > drivers/gpu/drm/drm_format_helper.c | 38 +++++++++++++++++++++-------- > drivers/gpu/drm/drm_mipi_dbi.c | 2 +- > drivers/gpu/drm/gud/gud_pipe.c | 2 +- > include/drm/drm_format_helper.h | 6 ++--- > 4 files changed, 33 insertions(+), 15 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index 49589b442f18..fa22d3cb11e8 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -196,9 +196,9 @@ static void drm_fb_swab32_line(void *dbuf, const void *sbuf, unsigned int pixels > > /** > * drm_fb_swab - Swap bytes into clip buffer > - * @dst: Destination buffer > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > - * @src: Source buffer > + * @dst: Array of destination buffers > + * @dst_pitch: Array of numbers of bytes between two consecutive scanlines within dstDocument that it may be NULL?> + * @vmap: Array of source buffersPrefer that the source is named src, and vmap smells like system (virtual) memory to me. Also vmap must be system memory - but this is maybe fixed later.> * @fb: DRM framebuffer > * @clip: Clip rectangle area to copy > * @cached: Source buffer is mapped cached (eg. not write-combined) > @@ -209,24 +209,42 @@ static void drm_fb_swab32_line(void *dbuf, const void *sbuf, unsigned int pixels > * This function does not apply clipping on dst, i.e. the destination > * is at the top-left corner. > */ > -void drm_fb_swab(void *dst, unsigned int dst_pitch, const void *src, > - const struct drm_framebuffer *fb, const struct drm_rect *clip, > - bool cached) > +void drm_fb_swab(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip, bool cached) > { > - u8 cpp = fb->format->cpp[0]; > + static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > + 0, 0, 0, 0 > + }; > + const struct drm_format_info *format = fb->format; > + u8 cpp = format->cpp[0];u8 cpp = drm_format_info_bpp(format, 0) / 8;> + void (*swab_line)(void *dbuf, const void *sbuf, unsigned int npixels); > > switch (cpp) { > case 4: > - drm_fb_xfrm(dst, dst_pitch, cpp, src, fb, clip, cached, drm_fb_swab32_line); > + swab_line = drm_fb_swab32_line; > break; > case 2: > - drm_fb_xfrm(dst, dst_pitch, cpp, src, fb, clip, cached, drm_fb_swab16_line); > + swab_line = drm_fb_swab16_line; > break; > default: > drm_warn_once(fb->dev, "Format %p4cc has unsupported pixel size.\n", > - &fb->format->format); > + &format->format); > + swab_line = NULL; > break; > } > + if (!swab_line) > + return; > + > + if (!dst_pitch) > + dst_pitch = default_dst_pitch; > + > + if (dst->is_iomem) > + drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], cpp, > + vmap[0].vaddr, fb, clip, cached, swab_line); > + else > + drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], cpp, vmap[0].vaddr, fb, > + clip, cached, swab_line);Here vmap is assumes system memory, not IO. I assume this is fixed later.> } > EXPORT_SYMBOL(drm_fb_swab); > > diff --git a/drivers/gpu/drm/drm_mipi_dbi.c b/drivers/gpu/drm/drm_mipi_dbi.c > index 22451806fb5c..973a75585cad 100644 > --- a/drivers/gpu/drm/drm_mipi_dbi.c > +++ b/drivers/gpu/drm/drm_mipi_dbi.c > @@ -221,7 +221,7 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb, > switch (fb->format->format) { > case DRM_FORMAT_RGB565: > if (swap) > - drm_fb_swab(dst, 0, src, fb, clip, !gem->import_attach); > + drm_fb_swab(&dst_map, NULL, data, fb, clip, !gem->import_attach); > else > drm_fb_memcpy(&dst_map, NULL, data, fb, clip); > break; > diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c > index 449c95a4aee0..a15cda9ba058 100644 > --- a/drivers/gpu/drm/gud/gud_pipe.c > +++ b/drivers/gpu/drm/gud/gud_pipe.c > @@ -205,7 +205,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct drm_framebuffer *fb, > len = gud_xrgb8888_to_color(buf, format, vaddr, fb, rect); > } > } else if (gud_is_big_endian() && format->cpp[0] > 1) { > - drm_fb_swab(buf, 0, vaddr, fb, rect, !import_attach); > + drm_fb_swab(&dst, NULL, map_data, fb, rect, !import_attach); > } else if (compression && !import_attach && pitch == fb->pitches[0]) { > /* can compress directly from the framebuffer */ > buf = vaddr + rect->y1 * pitch; > diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h > index 8af6a2717bc9..60944feaa936 100644 > --- a/include/drm/drm_format_helper.h > +++ b/include/drm/drm_format_helper.h > @@ -17,9 +17,9 @@ unsigned int drm_fb_clip_offset(unsigned int pitch, const struct drm_format_info > void drm_fb_memcpy(struct iosys_map *dst, const unsigned int *dst_pitch, > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip); > -void drm_fb_swab(void *dst, unsigned int dst_pitch, const void *src, > - const struct drm_framebuffer *fb, const struct drm_rect *clip, > - bool cached); > +void drm_fb_swab(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip, bool cached); > void drm_fb_xrgb8888_to_rgb332(void *dst, unsigned int dst_pitch, const void *vaddr, > const struct drm_framebuffer *fb, const struct drm_rect *clip); > void drm_fb_xrgb8888_to_rgb565(void *dst, unsigned int dst_pitch, const void *vaddr, > -- > 2.37.1
Sam Ravnborg
2022-Aug-04 20:10 UTC
[PATCH 04/12] drm/format-helper: Rework XRGB8888-to-RGBG332 conversion
Hi Thomas, On Wed, Jul 27, 2022 at 01:33:04PM +0200, Thomas Zimmermann wrote:> Update XRGB8888-to-RGB332 conversion to support struct iosys_map > and convert all users. Although these are single-plane color formats, > the new interface supports multi-plane formats for consistency with > drm_fb_blit(). > > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>I am not going to repeat my naming rant here, so Reviewed-by: Sam Ravnborg <sam at ravnborg.org>> --- > drivers/gpu/drm/drm_format_helper.c | 25 ++++++++++++++----- > drivers/gpu/drm/gud/gud_pipe.c | 2 +- > .../gpu/drm/tests/drm_format_helper_test.c | 14 ++++++----- > include/drm/drm_format_helper.h | 5 ++-- > 4 files changed, 31 insertions(+), 15 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index fa22d3cb11e8..2b5c3746ff4a 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -265,18 +265,31 @@ static void drm_fb_xrgb8888_to_rgb332_line(void *dbuf, const void *sbuf, unsigne > > /** > * drm_fb_xrgb8888_to_rgb332 - Convert XRGB8888 to RGB332 clip buffer > - * @dst: RGB332 destination buffer > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > - * @src: XRGB8888 source buffer > + * @dst: Array of RGB332 destination buffers > + * @dst_pitch: Array of numbers of bytes between two consecutive scanlines within dst > + * @vmap: Array of XRGB8888 source buffers > * @fb: DRM framebuffer > * @clip: Clip rectangle area to copy > * > * Drivers can use this function for RGB332 devices that don't natively support XRGB8888. > */ > -void drm_fb_xrgb8888_to_rgb332(void *dst, unsigned int dst_pitch, const void *src, > - const struct drm_framebuffer *fb, const struct drm_rect *clip) > +void drm_fb_xrgb8888_to_rgb332(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip) > { > - drm_fb_xfrm(dst, dst_pitch, 1, src, fb, clip, false, drm_fb_xrgb8888_to_rgb332_line); > + static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > + 0, 0, 0, 0 > + }; > + > + if (!dst_pitch) > + dst_pitch = default_dst_pitch; > + > + if (dst[0].is_iomem) > + drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 1, vmap[0].vaddr, fb, clip, > + false, drm_fb_xrgb8888_to_rgb332_line); > + else > + drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 1, vmap[0].vaddr, fb, clip, > + false, drm_fb_xrgb8888_to_rgb332_line); > } > EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb332); > > diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c > index a15cda9ba058..426a3ae6cc50 100644 > --- a/drivers/gpu/drm/gud/gud_pipe.c > +++ b/drivers/gpu/drm/gud/gud_pipe.c > @@ -196,7 +196,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct drm_framebuffer *fb, > } else if (format->format == DRM_FORMAT_R8) { > drm_fb_xrgb8888_to_gray8(buf, 0, vaddr, fb, rect); > } else if (format->format == DRM_FORMAT_RGB332) { > - drm_fb_xrgb8888_to_rgb332(buf, 0, vaddr, fb, rect); > + drm_fb_xrgb8888_to_rgb332(&dst, NULL, map_data, fb, rect); > } else if (format->format == DRM_FORMAT_RGB565) { > drm_fb_xrgb8888_to_rgb565(buf, 0, vaddr, fb, rect, gud_is_big_endian()); > } else if (format->format == DRM_FORMAT_RGB888) { > diff --git a/drivers/gpu/drm/tests/drm_format_helper_test.c b/drivers/gpu/drm/tests/drm_format_helper_test.c > index 98583bf56044..b74dba06f704 100644 > --- a/drivers/gpu/drm/tests/drm_format_helper_test.c > +++ b/drivers/gpu/drm/tests/drm_format_helper_test.c > @@ -124,7 +124,8 @@ static void xrgb8888_to_rgb332_test(struct kunit *test) > { > const struct xrgb8888_to_rgb332_case *params = test->param_value; > size_t dst_size; > - __u8 *dst = NULL; > + struct iosys_map dst, xrgb8888; > + __u8 *buf = NULL; > > struct drm_framebuffer fb = { > .format = drm_format_info(DRM_FORMAT_XRGB8888), > @@ -135,12 +136,13 @@ static void xrgb8888_to_rgb332_test(struct kunit *test) > ¶ms->clip); > KUNIT_ASSERT_GT(test, dst_size, 0); > > - dst = kunit_kzalloc(test, dst_size, GFP_KERNEL); > - KUNIT_ASSERT_NOT_ERR_OR_NULL(test, dst); > + buf = kunit_kzalloc(test, dst_size, GFP_KERNEL); > + KUNIT_ASSERT_NOT_ERR_OR_NULL(test, buf); > > - drm_fb_xrgb8888_to_rgb332(dst, params->dst_pitch, params->xrgb8888, > - &fb, ¶ms->clip); > - KUNIT_EXPECT_EQ(test, memcmp(dst, params->expected, dst_size), 0); > + iosys_map_set_vaddr(&dst, buf); > + iosys_map_set_vaddr(&xrgb8888, (void __force *)params->xrgb8888); > + drm_fb_xrgb8888_to_rgb332(&dst, ¶ms->dst_pitch, &xrgb8888, &fb, ¶ms->clip); > + KUNIT_EXPECT_EQ(test, memcmp(buf, params->expected, dst_size), 0); > } > > static struct kunit_case drm_format_helper_test_cases[] = { > diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h > index 60944feaa936..3c28f099e3ed 100644 > --- a/include/drm/drm_format_helper.h > +++ b/include/drm/drm_format_helper.h > @@ -20,8 +20,9 @@ void drm_fb_memcpy(struct iosys_map *dst, const unsigned int *dst_pitch, > void drm_fb_swab(struct iosys_map *dst, const unsigned int *dst_pitch, > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip, bool cached); > -void drm_fb_xrgb8888_to_rgb332(void *dst, unsigned int dst_pitch, const void *vaddr, > - const struct drm_framebuffer *fb, const struct drm_rect *clip); > +void drm_fb_xrgb8888_to_rgb332(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip); > void drm_fb_xrgb8888_to_rgb565(void *dst, unsigned int dst_pitch, const void *vaddr, > const struct drm_framebuffer *fb, const struct drm_rect *clip, > bool swab); > -- > 2.37.1
Sam Ravnborg
2022-Aug-04 20:12 UTC
[PATCH 05/12] drm/format-helper: Rework XRGB8888-to-RGBG565 conversion
On Wed, Jul 27, 2022 at 01:33:05PM +0200, Thomas Zimmermann wrote:> Update XRGB8888-to-RGB565 conversion to support struct iosys_map > and convert all users. Although these are single-plane color formats, > the new interface supports multi-plane formats for consistency with > drm_fb_blit(). > > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>Reviewed-by: Sam Ravnborg <sam at ravnborg.org>> --- > drivers/gpu/drm/drm_format_helper.c | 59 +++++++++++------------------ > drivers/gpu/drm/drm_mipi_dbi.c | 4 +- > drivers/gpu/drm/gud/gud_pipe.c | 3 +- > drivers/gpu/drm/tiny/cirrus.c | 3 +- > include/drm/drm_format_helper.h | 9 ++--- > 5 files changed, 30 insertions(+), 48 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index 2b5c3746ff4a..8bf5655f5ce0 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -330,9 +330,9 @@ static void drm_fb_xrgb8888_to_rgb565_swab_line(void *dbuf, const void *sbuf, > > /** > * drm_fb_xrgb8888_to_rgb565 - Convert XRGB8888 to RGB565 clip buffer > - * @dst: RGB565 destination buffer > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > - * @vaddr: XRGB8888 source buffer > + * @dst: Array of RGB565 destination buffers > + * @dst_pitch: Array of numbers of bytes between two consecutive scanlines within dst > + * @vmap: Array of XRGB8888 source buffer > * @fb: DRM framebuffer > * @clip: Clip rectangle area to copy > * @swab: Swap bytes > @@ -340,43 +340,31 @@ static void drm_fb_xrgb8888_to_rgb565_swab_line(void *dbuf, const void *sbuf, > * Drivers can use this function for RGB565 devices that don't natively > * support XRGB8888. > */ > -void drm_fb_xrgb8888_to_rgb565(void *dst, unsigned int dst_pitch, const void *vaddr, > - const struct drm_framebuffer *fb, const struct drm_rect *clip, > - bool swab) > +void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip, bool swab) > { > + static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > + 0, 0, 0, 0 > + }; > + void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels); > + > if (swab) > - drm_fb_xfrm(dst, dst_pitch, 2, vaddr, fb, clip, false, > - drm_fb_xrgb8888_to_rgb565_swab_line); > + xfrm_line = drm_fb_xrgb8888_to_rgb565_swab_line; > else > - drm_fb_xfrm(dst, dst_pitch, 2, vaddr, fb, clip, false, > - drm_fb_xrgb8888_to_rgb565_line); > -} > -EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb565); > + xfrm_line = drm_fb_xrgb8888_to_rgb565_line; > > -/** > - * drm_fb_xrgb8888_to_rgb565_toio - Convert XRGB8888 to RGB565 clip buffer > - * @dst: RGB565 destination buffer (iomem) > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > - * @vaddr: XRGB8888 source buffer > - * @fb: DRM framebuffer > - * @clip: Clip rectangle area to copy > - * @swab: Swap bytes > - * > - * Drivers can use this function for RGB565 devices that don't natively > - * support XRGB8888. > - */ > -void drm_fb_xrgb8888_to_rgb565_toio(void __iomem *dst, unsigned int dst_pitch, > - const void *vaddr, const struct drm_framebuffer *fb, > - const struct drm_rect *clip, bool swab) > -{ > - if (swab) > - drm_fb_xfrm_toio(dst, dst_pitch, 2, vaddr, fb, clip, false, > - drm_fb_xrgb8888_to_rgb565_swab_line); > + if (!dst_pitch) > + dst_pitch = default_dst_pitch; > + > + if (dst[0].is_iomem) > + drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 2, vmap[0].vaddr, fb, clip, > + false, xfrm_line); > else > - drm_fb_xfrm_toio(dst, dst_pitch, 2, vaddr, fb, clip, false, > - drm_fb_xrgb8888_to_rgb565_line); > + drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 2, vmap[0].vaddr, fb, clip, > + false, xfrm_line); > } > -EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb565_toio); > +EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb565); > > static void drm_fb_xrgb8888_to_rgb888_line(void *dbuf, const void *sbuf, unsigned int pixels) > { > @@ -605,8 +593,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t d > > } else if (dst_format == DRM_FORMAT_RGB565) { > if (fb_format == DRM_FORMAT_XRGB8888) { > - drm_fb_xrgb8888_to_rgb565_toio(dst[0].vaddr_iomem, dst_pitch[0], > - vmap[0].vaddr, fb, clip, false); > + drm_fb_xrgb8888_to_rgb565(dst, dst_pitch, vmap, fb, clip, false); > return 0; > } > } else if (dst_format == DRM_FORMAT_RGB888) { > diff --git a/drivers/gpu/drm/drm_mipi_dbi.c b/drivers/gpu/drm/drm_mipi_dbi.c > index 973a75585cad..d0bdbcb96705 100644 > --- a/drivers/gpu/drm/drm_mipi_dbi.c > +++ b/drivers/gpu/drm/drm_mipi_dbi.c > @@ -206,7 +206,6 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb, > struct iosys_map map[DRM_FORMAT_MAX_PLANES]; > struct iosys_map data[DRM_FORMAT_MAX_PLANES]; > struct iosys_map dst_map = IOSYS_MAP_INIT_VADDR(dst); > - void *src; > int ret; > > ret = drm_gem_fb_begin_cpu_access(fb, DMA_FROM_DEVICE); > @@ -216,7 +215,6 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb, > ret = drm_gem_fb_vmap(fb, map, data); > if (ret) > goto out_drm_gem_fb_end_cpu_access; > - src = data[0].vaddr; /* TODO: Use mapping abstraction properly */ > > switch (fb->format->format) { > case DRM_FORMAT_RGB565: > @@ -226,7 +224,7 @@ int mipi_dbi_buf_copy(void *dst, struct drm_framebuffer *fb, > drm_fb_memcpy(&dst_map, NULL, data, fb, clip); > break; > case DRM_FORMAT_XRGB8888: > - drm_fb_xrgb8888_to_rgb565(dst, 0, src, fb, clip, swap); > + drm_fb_xrgb8888_to_rgb565(&dst_map, NULL, data, fb, clip, swap); > break; > default: > drm_err_once(fb->dev, "Format is not supported: %p4cc\n", > diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c > index 426a3ae6cc50..a43eb6645352 100644 > --- a/drivers/gpu/drm/gud/gud_pipe.c > +++ b/drivers/gpu/drm/gud/gud_pipe.c > @@ -198,7 +198,8 @@ static int gud_prep_flush(struct gud_device *gdrm, struct drm_framebuffer *fb, > } else if (format->format == DRM_FORMAT_RGB332) { > drm_fb_xrgb8888_to_rgb332(&dst, NULL, map_data, fb, rect); > } else if (format->format == DRM_FORMAT_RGB565) { > - drm_fb_xrgb8888_to_rgb565(buf, 0, vaddr, fb, rect, gud_is_big_endian()); > + drm_fb_xrgb8888_to_rgb565(&dst, NULL, map_data, fb, rect, > + gud_is_big_endian()); > } else if (format->format == DRM_FORMAT_RGB888) { > drm_fb_xrgb8888_to_rgb888(buf, 0, vaddr, fb, rect); > } else { > diff --git a/drivers/gpu/drm/tiny/cirrus.c b/drivers/gpu/drm/tiny/cirrus.c > index 73fb9f63d227..9cd398e4700b 100644 > --- a/drivers/gpu/drm/tiny/cirrus.c > +++ b/drivers/gpu/drm/tiny/cirrus.c > @@ -335,8 +335,7 @@ static int cirrus_fb_blit_rect(struct drm_framebuffer *fb, > > } else if (fb->format->cpp[0] == 4 && cirrus->cpp == 2) { > iosys_map_incr(&dst, drm_fb_clip_offset(cirrus->pitch, fb->format, rect)); > - drm_fb_xrgb8888_to_rgb565_toio(dst.vaddr_iomem, cirrus->pitch, vaddr, fb, rect, > - false); > + drm_fb_xrgb8888_to_rgb565(&dst, &cirrus->pitch, vmap, fb, rect, false); > > } else if (fb->format->cpp[0] == 4 && cirrus->cpp == 3) { > iosys_map_incr(&dst, drm_fb_clip_offset(cirrus->pitch, fb->format, rect)); > diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h > index 3c28f099e3ed..9f1d45d7ce84 100644 > --- a/include/drm/drm_format_helper.h > +++ b/include/drm/drm_format_helper.h > @@ -23,12 +23,9 @@ void drm_fb_swab(struct iosys_map *dst, const unsigned int *dst_pitch, > void drm_fb_xrgb8888_to_rgb332(struct iosys_map *dst, const unsigned int *dst_pitch, > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip); > -void drm_fb_xrgb8888_to_rgb565(void *dst, unsigned int dst_pitch, const void *vaddr, > - const struct drm_framebuffer *fb, const struct drm_rect *clip, > - bool swab); > -void drm_fb_xrgb8888_to_rgb565_toio(void __iomem *dst, unsigned int dst_pitch, > - const void *vaddr, const struct drm_framebuffer *fb, > - const struct drm_rect *clip, bool swab); > +void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip, bool swab); > void drm_fb_xrgb8888_to_rgb888(void *dst, unsigned int dst_pitch, const void *src, > const struct drm_framebuffer *fb, const struct drm_rect *clip); > void drm_fb_xrgb8888_to_rgb888_toio(void __iomem *dst, unsigned int dst_pitch, > -- > 2.37.1
Sam Ravnborg
2022-Aug-04 20:14 UTC
[PATCH 06/12] drm/format-helper: Rework XRGB8888-to-RGB888 conversion
On Wed, Jul 27, 2022 at 01:33:06PM +0200, Thomas Zimmermann wrote:> Update XRGB8888-to-RGB888 conversion to support struct iosys_map > and convert all users. Although these are single-plane color formats, > the new interface supports multi-plane formats for consistency with > drm_fb_blit(). > > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>Reviewed-by: Sam Ravnborg <sam at ravnborg.org>> --- > drivers/gpu/drm/drm_format_helper.c | 48 ++++++++++++----------------- > drivers/gpu/drm/gud/gud_pipe.c | 2 +- > drivers/gpu/drm/tiny/cirrus.c | 3 +- > include/drm/drm_format_helper.h | 8 ++--- > 4 files changed, 25 insertions(+), 36 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index 8bf5655f5ce0..4edab44336d8 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -383,41 +383,34 @@ static void drm_fb_xrgb8888_to_rgb888_line(void *dbuf, const void *sbuf, unsigne > > /** > * drm_fb_xrgb8888_to_rgb888 - Convert XRGB8888 to RGB888 clip buffer > - * @dst: RGB888 destination buffer > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > - * @src: XRGB8888 source buffer > + * @dst: Array of RGB888 destination buffers > + * @dst_pitch: Array of numbers of bytes between two consecutive scanlines within dst > + * @vmap: Array of XRGB8888 source buffers > * @fb: DRM framebuffer > * @clip: Clip rectangle area to copy > * > * Drivers can use this function for RGB888 devices that don't natively > * support XRGB8888. > */ > -void drm_fb_xrgb8888_to_rgb888(void *dst, unsigned int dst_pitch, const void *src, > - const struct drm_framebuffer *fb, const struct drm_rect *clip) > +void drm_fb_xrgb8888_to_rgb888(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip) > { > - drm_fb_xfrm(dst, dst_pitch, 3, src, fb, clip, false, drm_fb_xrgb8888_to_rgb888_line); > -} > -EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb888); > + static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > + 0, 0, 0, 0 > + }; > > -/** > - * drm_fb_xrgb8888_to_rgb888_toio - Convert XRGB8888 to RGB888 clip buffer > - * @dst: RGB565 destination buffer (iomem) > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > - * @vaddr: XRGB8888 source buffer > - * @fb: DRM framebuffer > - * @clip: Clip rectangle area to copy > - * > - * Drivers can use this function for RGB888 devices that don't natively > - * support XRGB8888. > - */ > -void drm_fb_xrgb8888_to_rgb888_toio(void __iomem *dst, unsigned int dst_pitch, > - const void *vaddr, const struct drm_framebuffer *fb, > - const struct drm_rect *clip) > -{ > - drm_fb_xfrm_toio(dst, dst_pitch, 3, vaddr, fb, clip, false, > - drm_fb_xrgb8888_to_rgb888_line); > + if (!dst_pitch) > + dst_pitch = default_dst_pitch; > + > + if (dst[0].is_iomem) > + drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 3, vmap[0].vaddr, fb, > + clip, false, drm_fb_xrgb8888_to_rgb888_line); > + else > + drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 3, vmap[0].vaddr, fb, > + clip, false, drm_fb_xrgb8888_to_rgb888_line); > } > -EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb888_toio); > +EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb888); > > static void drm_fb_rgb565_to_xrgb8888_line(void *dbuf, const void *sbuf, unsigned int pixels) > { > @@ -598,8 +591,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t d > } > } else if (dst_format == DRM_FORMAT_RGB888) { > if (fb_format == DRM_FORMAT_XRGB8888) { > - drm_fb_xrgb8888_to_rgb888_toio(dst[0].vaddr_iomem, dst_pitch[0], > - vmap[0].vaddr, fb, clip); > + drm_fb_xrgb8888_to_rgb888(dst, dst_pitch, vmap, fb, clip); > return 0; > } > } else if (dst_format == DRM_FORMAT_XRGB8888) { > diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c > index a43eb6645352..0caa228f736d 100644 > --- a/drivers/gpu/drm/gud/gud_pipe.c > +++ b/drivers/gpu/drm/gud/gud_pipe.c > @@ -201,7 +201,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct drm_framebuffer *fb, > drm_fb_xrgb8888_to_rgb565(&dst, NULL, map_data, fb, rect, > gud_is_big_endian()); > } else if (format->format == DRM_FORMAT_RGB888) { > - drm_fb_xrgb8888_to_rgb888(buf, 0, vaddr, fb, rect); > + drm_fb_xrgb8888_to_rgb888(&dst, NULL, map_data, fb, rect); > } else { > len = gud_xrgb8888_to_color(buf, format, vaddr, fb, rect); > } > diff --git a/drivers/gpu/drm/tiny/cirrus.c b/drivers/gpu/drm/tiny/cirrus.c > index 9cd398e4700b..354d5e854a6f 100644 > --- a/drivers/gpu/drm/tiny/cirrus.c > +++ b/drivers/gpu/drm/tiny/cirrus.c > @@ -321,7 +321,6 @@ static int cirrus_fb_blit_rect(struct drm_framebuffer *fb, > { > struct cirrus_device *cirrus = to_cirrus(fb->dev); > struct iosys_map dst; > - void *vaddr = vmap->vaddr; /* TODO: Use mapping abstraction properly */ > int idx; > > if (!drm_dev_enter(&cirrus->dev, &idx)) > @@ -339,7 +338,7 @@ static int cirrus_fb_blit_rect(struct drm_framebuffer *fb, > > } else if (fb->format->cpp[0] == 4 && cirrus->cpp == 3) { > iosys_map_incr(&dst, drm_fb_clip_offset(cirrus->pitch, fb->format, rect)); > - drm_fb_xrgb8888_to_rgb888_toio(dst.vaddr_iomem, cirrus->pitch, vaddr, fb, rect); > + drm_fb_xrgb8888_to_rgb888(&dst, &cirrus->pitch, vmap, fb, rect); > > } else { > WARN_ON_ONCE("cpp mismatch"); > diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h > index 9f1d45d7ce84..8c633dbab5d6 100644 > --- a/include/drm/drm_format_helper.h > +++ b/include/drm/drm_format_helper.h > @@ -26,11 +26,9 @@ void drm_fb_xrgb8888_to_rgb332(struct iosys_map *dst, const unsigned int *dst_pi > void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const unsigned int *dst_pitch, > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip, bool swab); > -void drm_fb_xrgb8888_to_rgb888(void *dst, unsigned int dst_pitch, const void *src, > - const struct drm_framebuffer *fb, const struct drm_rect *clip); > -void drm_fb_xrgb8888_to_rgb888_toio(void __iomem *dst, unsigned int dst_pitch, > - const void *vaddr, const struct drm_framebuffer *fb, > - const struct drm_rect *clip); > +void drm_fb_xrgb8888_to_rgb888(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip); > void drm_fb_xrgb8888_to_xrgb2101010_toio(void __iomem *dst, unsigned int dst_pitch, > const void *vaddr, const struct drm_framebuffer *fb, > const struct drm_rect *clip); > -- > 2.37.1
Sam Ravnborg
2022-Aug-04 20:15 UTC
[PATCH 07/12] drm/format-helper: Rework RGB565-to-XRGB8888 conversion
On Wed, Jul 27, 2022 at 01:33:07PM +0200, Thomas Zimmermann wrote:> Update RGB565-to-XRGB8888 conversion to support struct iosys_map > and convert all users. Although these are single-plane color formats, > the new interface supports multi-plane formats for consistency with > drm_fb_blit(). > > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>Reviewed-by: Sam Ravnborg <sam at ravnborg.org>> --- > drivers/gpu/drm/drm_format_helper.c | 25 ++++++++++++++++++------- > 1 file changed, 18 insertions(+), 7 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index 4edab44336d8..5ef06f696657 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -430,12 +430,24 @@ static void drm_fb_rgb565_to_xrgb8888_line(void *dbuf, const void *sbuf, unsigne > } > } > > -static void drm_fb_rgb565_to_xrgb8888_toio(void __iomem *dst, unsigned int dst_pitch, > - const void *vaddr, const struct drm_framebuffer *fb, > - const struct drm_rect *clip) > +static void drm_fb_rgb565_to_xrgb8888(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, > + const struct drm_framebuffer *fb, > + const struct drm_rect *clip) > { > - drm_fb_xfrm_toio(dst, dst_pitch, 4, vaddr, fb, clip, false, > - drm_fb_rgb565_to_xrgb8888_line); > + static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > + 0, 0, 0, 0 > + }; > + > + if (!dst_pitch) > + dst_pitch = default_dst_pitch; > + > + if (dst[0].is_iomem) > + drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb, > + clip, false, drm_fb_rgb565_to_xrgb8888_line); > + else > + drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb, > + clip, false, drm_fb_rgb565_to_xrgb8888_line); > } > > static void drm_fb_rgb888_to_xrgb8888_line(void *dbuf, const void *sbuf, unsigned int pixels) > @@ -600,8 +612,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t d > vmap[0].vaddr, fb, clip); > return 0; > } else if (fb_format == DRM_FORMAT_RGB565) { > - drm_fb_rgb565_to_xrgb8888_toio(dst[0].vaddr_iomem, dst_pitch[0], > - vmap[0].vaddr, fb, clip); > + drm_fb_rgb565_to_xrgb8888(dst, dst_pitch, vmap, fb, clip); > return 0; > } > } else if (dst_format == DRM_FORMAT_XRGB2101010) { > -- > 2.37.1
Sam Ravnborg
2022-Aug-04 20:16 UTC
[PATCH 08/12] drm/format-helper: Rework RGB888-to-XRGB8888 conversion
On Wed, Jul 27, 2022 at 01:33:08PM +0200, Thomas Zimmermann wrote:> Update RGB888-to-XRGB8888 conversion to support struct iosys_map > and convert all users. Although these are single-plane color formats, > the new interface supports multi-plane formats for consistency with > drm_fb_blit(). > > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>Reviewed-by: Sam Ravnborg <sam at ravnborg.org>> --- > drivers/gpu/drm/drm_format_helper.c | 25 ++++++++++++++++++------- > 1 file changed, 18 insertions(+), 7 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index 5ef06f696657..155827eebe99 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -465,12 +465,24 @@ static void drm_fb_rgb888_to_xrgb8888_line(void *dbuf, const void *sbuf, unsigne > } > } > > -static void drm_fb_rgb888_to_xrgb8888_toio(void __iomem *dst, unsigned int dst_pitch, > - const void *vaddr, const struct drm_framebuffer *fb, > - const struct drm_rect *clip) > +static void drm_fb_rgb888_to_xrgb8888(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, > + const struct drm_framebuffer *fb, > + const struct drm_rect *clip) > { > - drm_fb_xfrm_toio(dst, dst_pitch, 4, vaddr, fb, clip, false, > - drm_fb_rgb888_to_xrgb8888_line); > + static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > + 0, 0, 0, 0 > + }; > + > + if (!dst_pitch) > + dst_pitch = default_dst_pitch; > + > + if (dst[0].is_iomem) > + drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb, > + clip, false, drm_fb_rgb888_to_xrgb8888_line); > + else > + drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb, > + clip, false, drm_fb_rgb888_to_xrgb8888_line); > } > > static void drm_fb_xrgb8888_to_xrgb2101010_line(void *dbuf, const void *sbuf, unsigned int pixels) > @@ -608,8 +620,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t d > } > } else if (dst_format == DRM_FORMAT_XRGB8888) { > if (fb_format == DRM_FORMAT_RGB888) { > - drm_fb_rgb888_to_xrgb8888_toio(dst[0].vaddr_iomem, dst_pitch[0], > - vmap[0].vaddr, fb, clip); > + drm_fb_rgb888_to_xrgb8888(dst, dst_pitch, vmap, fb, clip); > return 0; > } else if (fb_format == DRM_FORMAT_RGB565) { > drm_fb_rgb565_to_xrgb8888(dst, dst_pitch, vmap, fb, clip); > -- > 2.37.1
Sam Ravnborg
2022-Aug-04 20:17 UTC
[PATCH 09/12] drm/format-helper: Rework XRGB8888-to-XRGB2101010 conversion
On Wed, Jul 27, 2022 at 01:33:09PM +0200, Thomas Zimmermann wrote:> Update XRGB8888-to-XRGB2101010 conversion to support struct iosys_map > and convert all users. Although these are single-plane color formats, > the new interface supports multi-plane formats for consistency with > drm_fb_blit(). > > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de> > ---Reviewed-by: Sam Ravnborg <sam at ravnborg.org>> drivers/gpu/drm/drm_format_helper.c | 35 +++++++++++++++++------------ > include/drm/drm_format_helper.h | 6 ++--- > 2 files changed, 24 insertions(+), 17 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index 155827eebe99..209f63b66c5f 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -504,26 +504,34 @@ static void drm_fb_xrgb8888_to_xrgb2101010_line(void *dbuf, const void *sbuf, un > } > > /** > - * drm_fb_xrgb8888_to_xrgb2101010_toio - Convert XRGB8888 to XRGB2101010 clip > - * buffer > - * @dst: XRGB2101010 destination buffer (iomem) > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > - * @vaddr: XRGB8888 source buffer > + * drm_fb_xrgb8888_to_xrgb2101010 - Convert XRGB8888 to XRGB2101010 clip buffer > + * @dst: Array of XRGB2101010 destination buffers > + * @dst_pitch: Array of numbers of bytes between two consecutive scanlines within dst > + * @vmap: Array of XRGB8888 source buffers > * @fb: DRM framebuffer > * @clip: Clip rectangle area to copy > * > * Drivers can use this function for XRGB2101010 devices that don't natively > * support XRGB8888. > */ > -void drm_fb_xrgb8888_to_xrgb2101010_toio(void __iomem *dst, > - unsigned int dst_pitch, const void *vaddr, > - const struct drm_framebuffer *fb, > - const struct drm_rect *clip) > +void drm_fb_xrgb8888_to_xrgb2101010(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip) > { > - drm_fb_xfrm_toio(dst, dst_pitch, 4, vaddr, fb, clip, false, > - drm_fb_xrgb8888_to_xrgb2101010_line); > + static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > + 0, 0, 0, 0 > + }; > + > + if (!dst_pitch) > + dst_pitch = default_dst_pitch; > + > + if (dst[0].is_iomem) > + drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb, > + clip, false, drm_fb_xrgb8888_to_xrgb2101010_line); > + else > + drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb, > + clip, false, drm_fb_xrgb8888_to_xrgb2101010_line); > } > -EXPORT_SYMBOL(drm_fb_xrgb8888_to_xrgb2101010_toio); > > static void drm_fb_xrgb8888_to_gray8_line(void *dbuf, const void *sbuf, unsigned int pixels) > { > @@ -628,8 +636,7 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t d > } > } else if (dst_format == DRM_FORMAT_XRGB2101010) { > if (fb_format == DRM_FORMAT_XRGB8888) { > - drm_fb_xrgb8888_to_xrgb2101010_toio(dst[0].vaddr_iomem, dst_pitch[0], > - vmap[0].vaddr, fb, clip); > + drm_fb_xrgb8888_to_xrgb2101010(dst, dst_pitch, vmap, fb, clip); > return 0; > } > } > diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h > index 8c633dbab5d6..6807440ce29c 100644 > --- a/include/drm/drm_format_helper.h > +++ b/include/drm/drm_format_helper.h > @@ -29,9 +29,9 @@ void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const unsigned int *dst_pi > void drm_fb_xrgb8888_to_rgb888(struct iosys_map *dst, const unsigned int *dst_pitch, > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip); > -void drm_fb_xrgb8888_to_xrgb2101010_toio(void __iomem *dst, unsigned int dst_pitch, > - const void *vaddr, const struct drm_framebuffer *fb, > - const struct drm_rect *clip); > +void drm_fb_xrgb8888_to_xrgb2101010(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip); > void drm_fb_xrgb8888_to_gray8(void *dst, unsigned int dst_pitch, const void *vaddr, > const struct drm_framebuffer *fb, const struct drm_rect *clip); > > -- > 2.37.1
Sam Ravnborg
2022-Aug-04 20:19 UTC
[PATCH 10/12] drm/format-helper: Rework XRGB8888-to-GRAY8 conversion
On Wed, Jul 27, 2022 at 01:33:10PM +0200, Thomas Zimmermann wrote:> Update XRGB8888-to-GRAY8 conversion to support struct iosys_map > and convert all users. Although these are single-plane color formats, > the new interface supports multi-plane formats for consistency with > drm_fb_blit(). > > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>Reviewed-by: Sam Ravnborg <sam at ravnborg.org>> --- > drivers/gpu/drm/drm_format_helper.c | 25 +++++++++++++++++++------ > drivers/gpu/drm/gud/gud_pipe.c | 7 +++++-- > drivers/gpu/drm/tiny/st7586.c | 5 ++++- > include/drm/drm_format_helper.h | 5 +++-- > 4 files changed, 31 insertions(+), 11 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index 209f63b66c5f..521932fac491 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -552,9 +552,9 @@ static void drm_fb_xrgb8888_to_gray8_line(void *dbuf, const void *sbuf, unsigned > > /** > * drm_fb_xrgb8888_to_gray8 - Convert XRGB8888 to grayscale > - * @dst: 8-bit grayscale destination buffer > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > - * @vaddr: XRGB8888 source buffer > + * @dst: Array of 8-bit grayscale destination buffers > + * @dst_pitch: Array of number of bytes between two consecutive scanlines within dst > + * @vmap: Array of XRGB8888 source buffers > * @fb: DRM framebuffer > * @clip: Clip rectangle area to copy > * > @@ -567,10 +567,23 @@ static void drm_fb_xrgb8888_to_gray8_line(void *dbuf, const void *sbuf, unsigned > * > * ITU BT.601 is used for the RGB -> luma (brightness) conversion. > */ > -void drm_fb_xrgb8888_to_gray8(void *dst, unsigned int dst_pitch, const void *vaddr, > - const struct drm_framebuffer *fb, const struct drm_rect *clip) > +void drm_fb_xrgb8888_to_gray8(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip) > { > - drm_fb_xfrm(dst, dst_pitch, 1, vaddr, fb, clip, false, drm_fb_xrgb8888_to_gray8_line); > + static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > + 0, 0, 0, 0 > + }; > + > + if (!dst_pitch) > + dst_pitch = default_dst_pitch; > + > + if (dst[0].is_iomem) > + drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 1, vmap[0].vaddr, fb, > + clip, false, drm_fb_xrgb8888_to_gray8_line); > + else > + drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 1, vmap[0].vaddr, fb, > + clip, false, drm_fb_xrgb8888_to_gray8_line); > } > EXPORT_SYMBOL(drm_fb_xrgb8888_to_gray8); > > diff --git a/drivers/gpu/drm/gud/gud_pipe.c b/drivers/gpu/drm/gud/gud_pipe.c > index 0caa228f736d..7c6dc2bcd14a 100644 > --- a/drivers/gpu/drm/gud/gud_pipe.c > +++ b/drivers/gpu/drm/gud/gud_pipe.c > @@ -59,6 +59,7 @@ static size_t gud_xrgb8888_to_r124(u8 *dst, const struct drm_format_info *format > unsigned int bits_per_pixel = 8 / block_width; > unsigned int x, y, width, height; > u8 pix, *pix8, *block = dst; /* Assign to silence compiler warning */ > + struct iosys_map dst_map, vmap; > size_t len; > void *buf; > > @@ -74,7 +75,9 @@ static size_t gud_xrgb8888_to_r124(u8 *dst, const struct drm_format_info *format > if (!buf) > return 0; > > - drm_fb_xrgb8888_to_gray8(buf, 0, src, fb, rect); > + iosys_map_set_vaddr(&dst_map, buf); > + iosys_map_set_vaddr(&vmap, src); > + drm_fb_xrgb8888_to_gray8(&dst_map, NULL, &vmap, fb, rect); > pix8 = buf; > > for (y = 0; y < height; y++) { > @@ -194,7 +197,7 @@ static int gud_prep_flush(struct gud_device *gdrm, struct drm_framebuffer *fb, > goto end_cpu_access; > } > } else if (format->format == DRM_FORMAT_R8) { > - drm_fb_xrgb8888_to_gray8(buf, 0, vaddr, fb, rect); > + drm_fb_xrgb8888_to_gray8(&dst, NULL, map_data, fb, rect); > } else if (format->format == DRM_FORMAT_RGB332) { > drm_fb_xrgb8888_to_rgb332(&dst, NULL, map_data, fb, rect); > } else if (format->format == DRM_FORMAT_RGB565) { > diff --git a/drivers/gpu/drm/tiny/st7586.c b/drivers/gpu/drm/tiny/st7586.c > index 8eddb020c43e..702350d0f8bc 100644 > --- a/drivers/gpu/drm/tiny/st7586.c > +++ b/drivers/gpu/drm/tiny/st7586.c > @@ -69,12 +69,15 @@ static void st7586_xrgb8888_to_gray332(u8 *dst, void *vaddr, > size_t len = (clip->x2 - clip->x1) * (clip->y2 - clip->y1); > unsigned int x, y; > u8 *src, *buf, val; > + struct iosys_map dst_map, vmap; > > buf = kmalloc(len, GFP_KERNEL); > if (!buf) > return; > > - drm_fb_xrgb8888_to_gray8(buf, 0, vaddr, fb, clip); > + iosys_map_set_vaddr(&dst_map, buf); > + iosys_map_set_vaddr(&vmap, vaddr); > + drm_fb_xrgb8888_to_gray8(&dst_map, NULL, &vmap, fb, clip); > src = buf; > > for (y = clip->y1; y < clip->y2; y++) { > diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h > index 6807440ce29c..68087c982497 100644 > --- a/include/drm/drm_format_helper.h > +++ b/include/drm/drm_format_helper.h > @@ -32,8 +32,9 @@ void drm_fb_xrgb8888_to_rgb888(struct iosys_map *dst, const unsigned int *dst_pi > void drm_fb_xrgb8888_to_xrgb2101010(struct iosys_map *dst, const unsigned int *dst_pitch, > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip); > -void drm_fb_xrgb8888_to_gray8(void *dst, unsigned int dst_pitch, const void *vaddr, > - const struct drm_framebuffer *fb, const struct drm_rect *clip); > +void drm_fb_xrgb8888_to_gray8(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip); > > int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t dst_format, > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > -- > 2.37.1
Sam Ravnborg
2022-Aug-04 20:21 UTC
[PATCH 11/12] drm/format-helper: Rework XRGB8888-to-MONO conversion
On Wed, Jul 27, 2022 at 01:33:11PM +0200, Thomas Zimmermann wrote:> Update XRGB8888-to-MONO conversion to support struct iosys_map > and convert all users. Although these are single-plane color formats, > the new interface supports multi-plane formats for consistency with > drm_fb_blit(). > > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de>Reviewed-by: Sam Ravnborg <sam at ravnborg.org>> --- > drivers/gpu/drm/drm_format_helper.c | 28 +++++++++++++++++++--------- > drivers/gpu/drm/solomon/ssd130x.c | 7 ++++--- > drivers/gpu/drm/tiny/repaper.c | 6 +++++- > include/drm/drm_format_helper.h | 5 +++-- > 4 files changed, 31 insertions(+), 15 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index 521932fac491..d296d181659d 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -680,9 +680,9 @@ static void drm_fb_gray8_to_mono_line(void *dbuf, const void *sbuf, unsigned int > > /** > * drm_fb_xrgb8888_to_mono - Convert XRGB8888 to monochromeIt should be documented that this only supports system memory (no io memory support). Sam> - * @dst: monochrome destination buffer (0=black, 1=white) > - * @dst_pitch: Number of bytes between two consecutive scanlines within dst > - * @vaddr: XRGB8888 source buffer > + * @dst: Array of monochrome destination buffers (0=black, 1=white) > + * @dst_pitch: Array of numbers of bytes between two consecutive scanlines within dst > + * @vmap: Array of XRGB8888 source buffers > * @fb: DRM framebuffer > * @clip: Clip rectangle area to copy > * > @@ -700,26 +700,36 @@ static void drm_fb_gray8_to_mono_line(void *dbuf, const void *sbuf, unsigned int > * x-coordinate that is a multiple of 8, then the caller must take care itself > * of supplying a suitable clip rectangle. > */ > -void drm_fb_xrgb8888_to_mono(void *dst, unsigned int dst_pitch, const void *vaddr, > - const struct drm_framebuffer *fb, const struct drm_rect *clip) > +void drm_fb_xrgb8888_to_mono(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip) > { > + static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > + 0, 0, 0, 0 > + }; > unsigned int linepixels = drm_rect_width(clip); > unsigned int lines = drm_rect_height(clip); > unsigned int cpp = fb->format->cpp[0]; > unsigned int len_src32 = linepixels * cpp; > struct drm_device *dev = fb->dev; > + void *vaddr = vmap[0].vaddr; > + unsigned int dst_pitch_0; > unsigned int y; > - u8 *mono = dst, *gray8; > + u8 *mono = dst[0].vaddr, *gray8; > u32 *src32; > > if (drm_WARN_ON(dev, fb->format->format != DRM_FORMAT_XRGB8888)) > return; > > + if (!dst_pitch) > + dst_pitch = default_dst_pitch; > + dst_pitch_0 = dst_pitch[0]; > + > /* > * The mono destination buffer contains 1 bit per pixel > */ > - if (!dst_pitch) > - dst_pitch = DIV_ROUND_UP(linepixels, 8); > + if (!dst_pitch_0) > + dst_pitch_0 = DIV_ROUND_UP(linepixels, 8); > > /* > * The cma memory is write-combined so reads are uncached. > @@ -744,7 +754,7 @@ void drm_fb_xrgb8888_to_mono(void *dst, unsigned int dst_pitch, const void *vadd > drm_fb_xrgb8888_to_gray8_line(gray8, src32, linepixels); > drm_fb_gray8_to_mono_line(mono, gray8, linepixels); > vaddr += fb->pitches[0]; > - mono += dst_pitch; > + mono += dst_pitch_0; > } > > kfree(src32); > diff --git a/drivers/gpu/drm/solomon/ssd130x.c b/drivers/gpu/drm/solomon/ssd130x.c > index 5a3e3b78cd9e..aa7329a65c98 100644 > --- a/drivers/gpu/drm/solomon/ssd130x.c > +++ b/drivers/gpu/drm/solomon/ssd130x.c > @@ -537,11 +537,11 @@ static void ssd130x_clear_screen(struct ssd130x_device *ssd130x) > kfree(buf); > } > > -static int ssd130x_fb_blit_rect(struct drm_framebuffer *fb, const struct iosys_map *map, > +static int ssd130x_fb_blit_rect(struct drm_framebuffer *fb, const struct iosys_map *vmap, > struct drm_rect *rect) > { > struct ssd130x_device *ssd130x = drm_to_ssd130x(fb->dev); > - void *vmap = map->vaddr; /* TODO: Use mapping abstraction properly */ > + struct iosys_map dst; > unsigned int dst_pitch; > int ret = 0; > u8 *buf = NULL; > @@ -555,7 +555,8 @@ static int ssd130x_fb_blit_rect(struct drm_framebuffer *fb, const struct iosys_m > if (!buf) > return -ENOMEM; > > - drm_fb_xrgb8888_to_mono(buf, dst_pitch, vmap, fb, rect); > + iosys_map_set_vaddr(&dst, buf); > + drm_fb_xrgb8888_to_mono(&dst, &dst_pitch, vmap, fb, rect); > > ssd130x_update_rect(ssd130x, buf, rect); > > diff --git a/drivers/gpu/drm/tiny/repaper.c b/drivers/gpu/drm/tiny/repaper.c > index 013790c45d0a..0cdf6ab8fcc5 100644 > --- a/drivers/gpu/drm/tiny/repaper.c > +++ b/drivers/gpu/drm/tiny/repaper.c > @@ -513,6 +513,8 @@ static int repaper_fb_dirty(struct drm_framebuffer *fb) > { > struct drm_gem_cma_object *cma_obj = drm_fb_cma_get_gem_obj(fb, 0); > struct repaper_epd *epd = drm_to_epd(fb->dev); > + unsigned int dst_pitch = 0; > + struct iosys_map dst, vmap; > struct drm_rect clip; > int idx, ret = 0; > u8 *buf = NULL; > @@ -541,7 +543,9 @@ static int repaper_fb_dirty(struct drm_framebuffer *fb) > if (ret) > goto out_free; > > - drm_fb_xrgb8888_to_mono(buf, 0, cma_obj->vaddr, fb, &clip); > + iosys_map_set_vaddr(&dst, buf); > + iosys_map_set_vaddr(&vmap, cma_obj->vaddr); > + drm_fb_xrgb8888_to_mono(&dst, &dst_pitch, &vmap, fb, &clip); > > drm_gem_fb_end_cpu_access(fb, DMA_FROM_DEVICE); > > diff --git a/include/drm/drm_format_helper.h b/include/drm/drm_format_helper.h > index 68087c982497..1e1d8f356cc1 100644 > --- a/include/drm/drm_format_helper.h > +++ b/include/drm/drm_format_helper.h > @@ -40,7 +40,8 @@ int drm_fb_blit(struct iosys_map *dst, const unsigned int *dst_pitch, uint32_t d > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *rect); > > -void drm_fb_xrgb8888_to_mono(void *dst, unsigned int dst_pitch, const void *src, > - const struct drm_framebuffer *fb, const struct drm_rect *clip); > +void drm_fb_xrgb8888_to_mono(struct iosys_map *dst, const unsigned int *dst_pitch, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip); > > #endif /* __LINUX_DRM_FORMAT_HELPER_H */ > -- > 2.37.1
Sam Ravnborg
2022-Aug-05 17:52 UTC
[PATCH 12/12] drm/format-helper: Move destination-buffer handling into internal helper
Hi Thomas, On Wed, Jul 27, 2022 at 01:33:12PM +0200, Thomas Zimmermann wrote:> The format-convertion helpers handle several cases for different > values of destination buffer and pitch. Move that code into the > internal helper drm_fb_xfrm() and avoid quite a bit of duplucation.This is very nice patch that should come before all the conversion patches - but then you have had to come up with another name. So I think this is fine. A few comments below, mostly in the same area as the comments from Jos?. Sam> > Signed-off-by: Thomas Zimmermann <tzimmermann at suse.de> > --- > drivers/gpu/drm/drm_format_helper.c | 169 +++++++++++----------------- > 1 file changed, 64 insertions(+), 105 deletions(-) > > diff --git a/drivers/gpu/drm/drm_format_helper.c b/drivers/gpu/drm/drm_format_helper.c > index d296d181659d..35aebdb90165 100644 > --- a/drivers/gpu/drm/drm_format_helper.c > +++ b/drivers/gpu/drm/drm_format_helper.c > @@ -41,11 +41,11 @@ unsigned int drm_fb_clip_offset(unsigned int pitch, const struct drm_format_info > } > EXPORT_SYMBOL(drm_fb_clip_offset); > > -/* TODO: Make this functon work with multi-plane formats. */ > -static int drm_fb_xfrm(void *dst, unsigned long dst_pitch, unsigned long dst_pixsize, > - const void *vaddr, const struct drm_framebuffer *fb, > - const struct drm_rect *clip, bool vaddr_cached_hint, > - void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels)) > +/* TODO: Make this function work with multi-plane formats. */ > +static int __drm_fb_xfrm(void *dst, unsigned long dst_pitch, unsigned long dst_pixsize, > + const void *vaddr, const struct drm_framebuffer *fb, > + const struct drm_rect *clip, bool vaddr_cached_hint, > + void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels)) > { > unsigned long linepixels = drm_rect_width(clip); > unsigned long lines = drm_rect_height(clip); > @@ -84,11 +84,11 @@ static int drm_fb_xfrm(void *dst, unsigned long dst_pitch, unsigned long dst_pix > return 0; > } > > -/* TODO: Make this functon work with multi-plane formats. */ > -static int drm_fb_xfrm_toio(void __iomem *dst, unsigned long dst_pitch, unsigned long dst_pixsize, > - const void *vaddr, const struct drm_framebuffer *fb, > - const struct drm_rect *clip, bool vaddr_cached_hint, > - void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels)) > +/* TODO: Make this function work with multi-plane formats. */ > +static int __drm_fb_xfrm_toio(void __iomem *dst, unsigned long dst_pitch, unsigned long dst_pixsize, > + const void *vaddr, const struct drm_framebuffer *fb, > + const struct drm_rect *clip, bool vaddr_cached_hint, > + void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels)) > { > unsigned long linepixels = drm_rect_width(clip); > unsigned long lines = drm_rect_height(clip); > @@ -129,6 +129,29 @@ static int drm_fb_xfrm_toio(void __iomem *dst, unsigned long dst_pitch, unsigned > return 0; > } > > +/* TODO: Make this function work with multi-plane formats. */ > +static int drm_fb_xfrm(struct iosys_map *dst, > + const unsigned int *dst_pitch, const u8 *dst_pixsize, > + const struct iosys_map *vmap, const struct drm_framebuffer *fb, > + const struct drm_rect *clip, bool vaddr_cached_hint, > + void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels)) > +{Just to repeat myself a little, this assumes src (vmap) is always system memory (not io).> + static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > + 0, 0, 0, 0 > + }; > + > + if (!dst_pitch) > + dst_pitch = default_dst_pitch; > + > + if (dst[0].is_iomem) > + return __drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], dst_pixsize[0], > + vmap[0].vaddr, fb, clip, false, xfrm_line); > + else > + return __drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], dst_pixsize[0], > + vmap[0].vaddr, fb, clip, false, xfrm_line);It looks like vaddr_cached_hint is always false, so can we remove it?> +} > + > + > /** > * drm_fb_memcpy - Copy clip buffer > * @dst: Array of destination buffers > @@ -213,14 +236,10 @@ void drm_fb_swab(struct iosys_map *dst, const unsigned int *dst_pitch, > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip, bool cached) > { > - static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > - 0, 0, 0, 0 > - }; > const struct drm_format_info *format = fb->format; > - u8 cpp = format->cpp[0]; > void (*swab_line)(void *dbuf, const void *sbuf, unsigned int npixels); > > - switch (cpp) { > + switch (format->cpp[0]) { > case 4: > swab_line = drm_fb_swab32_line; > break; > @@ -230,21 +249,10 @@ void drm_fb_swab(struct iosys_map *dst, const unsigned int *dst_pitch, > default: > drm_warn_once(fb->dev, "Format %p4cc has unsupported pixel size.\n", > &format->format); > - swab_line = NULL; > - break; > - } > - if (!swab_line) > return; > + } > > - if (!dst_pitch) > - dst_pitch = default_dst_pitch; > - > - if (dst->is_iomem) > - drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], cpp, > - vmap[0].vaddr, fb, clip, cached, swab_line); > - else > - drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], cpp, vmap[0].vaddr, fb, > - clip, cached, swab_line); > + drm_fb_xfrm(dst, dst_pitch, format->cpp, vmap, fb, clip, cached, swab_line);In this case we pass fb->format-cpp as dst_pitch - so we could retreive is via the fb pointer.> } > EXPORT_SYMBOL(drm_fb_swab); > > @@ -277,19 +285,12 @@ void drm_fb_xrgb8888_to_rgb332(struct iosys_map *dst, const unsigned int *dst_pi > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip) > { > - static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > - 0, 0, 0, 0 > + static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = { > + 1, > }; > > - if (!dst_pitch) > - dst_pitch = default_dst_pitch; > - > - if (dst[0].is_iomem) > - drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 1, vmap[0].vaddr, fb, clip, > - false, drm_fb_xrgb8888_to_rgb332_line); > - else > - drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 1, vmap[0].vaddr, fb, clip, > - false, drm_fb_xrgb8888_to_rgb332_line); > + drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false, > + drm_fb_xrgb8888_to_rgb332_line);Here we construct the dst_pixsize. What is needed to make us trust fb->format->cpp so we can just fetch the info from format_info and drop dst_pixsize? I do not see any lookup being necessary here or in the functions below. If we use cpp (or even better using a helper function that avoid the deprecated cpp), then adding support for planes is simpler. For now dst_pixsize only pass the size for the first plane and there are a lot of updates required to support additional planes. Maybe I miss something obvious?!?> } > EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb332); > > @@ -344,9 +345,10 @@ void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const unsigned int *dst_pi > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip, bool swab) > { > - static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > - 0, 0, 0, 0 > + static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = { > + 2, > }; > + > void (*xfrm_line)(void *dbuf, const void *sbuf, unsigned int npixels); > > if (swab) > @@ -354,15 +356,7 @@ void drm_fb_xrgb8888_to_rgb565(struct iosys_map *dst, const unsigned int *dst_pi > else > xfrm_line = drm_fb_xrgb8888_to_rgb565_line; > > - if (!dst_pitch) > - dst_pitch = default_dst_pitch; > - > - if (dst[0].is_iomem) > - drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 2, vmap[0].vaddr, fb, clip, > - false, xfrm_line); > - else > - drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 2, vmap[0].vaddr, fb, clip, > - false, xfrm_line); > + drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false, xfrm_line); > } > EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb565); > > @@ -396,19 +390,12 @@ void drm_fb_xrgb8888_to_rgb888(struct iosys_map *dst, const unsigned int *dst_pi > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip) > { > - static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > - 0, 0, 0, 0 > + static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = { > + 3, > }; > > - if (!dst_pitch) > - dst_pitch = default_dst_pitch; > - > - if (dst[0].is_iomem) > - drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 3, vmap[0].vaddr, fb, > - clip, false, drm_fb_xrgb8888_to_rgb888_line); > - else > - drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 3, vmap[0].vaddr, fb, > - clip, false, drm_fb_xrgb8888_to_rgb888_line); > + drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false, > + drm_fb_xrgb8888_to_rgb888_line); > } > EXPORT_SYMBOL(drm_fb_xrgb8888_to_rgb888); > > @@ -435,19 +422,12 @@ static void drm_fb_rgb565_to_xrgb8888(struct iosys_map *dst, const unsigned int > const struct drm_framebuffer *fb, > const struct drm_rect *clip) > { > - static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > - 0, 0, 0, 0 > + static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = { > + 4, > }; > > - if (!dst_pitch) > - dst_pitch = default_dst_pitch; > - > - if (dst[0].is_iomem) > - drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb, > - clip, false, drm_fb_rgb565_to_xrgb8888_line); > - else > - drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb, > - clip, false, drm_fb_rgb565_to_xrgb8888_line); > + drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false, > + drm_fb_rgb565_to_xrgb8888_line); > } > > static void drm_fb_rgb888_to_xrgb8888_line(void *dbuf, const void *sbuf, unsigned int pixels) > @@ -470,19 +450,12 @@ static void drm_fb_rgb888_to_xrgb8888(struct iosys_map *dst, const unsigned int > const struct drm_framebuffer *fb, > const struct drm_rect *clip) > { > - static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > - 0, 0, 0, 0 > + static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = { > + 4, > }; > > - if (!dst_pitch) > - dst_pitch = default_dst_pitch; > - > - if (dst[0].is_iomem) > - drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb, > - clip, false, drm_fb_rgb888_to_xrgb8888_line); > - else > - drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb, > - clip, false, drm_fb_rgb888_to_xrgb8888_line); > + drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false, > + drm_fb_rgb888_to_xrgb8888_line); > } > > static void drm_fb_xrgb8888_to_xrgb2101010_line(void *dbuf, const void *sbuf, unsigned int pixels) > @@ -518,19 +491,12 @@ void drm_fb_xrgb8888_to_xrgb2101010(struct iosys_map *dst, const unsigned int *d > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip) > { > - static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > - 0, 0, 0, 0 > + static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = { > + 4, > }; > > - if (!dst_pitch) > - dst_pitch = default_dst_pitch; > - > - if (dst[0].is_iomem) > - drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 4, vmap[0].vaddr, fb, > - clip, false, drm_fb_xrgb8888_to_xrgb2101010_line); > - else > - drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 4, vmap[0].vaddr, fb, > - clip, false, drm_fb_xrgb8888_to_xrgb2101010_line); > + drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false, > + drm_fb_xrgb8888_to_xrgb2101010_line); > } > > static void drm_fb_xrgb8888_to_gray8_line(void *dbuf, const void *sbuf, unsigned int pixels) > @@ -571,19 +537,12 @@ void drm_fb_xrgb8888_to_gray8(struct iosys_map *dst, const unsigned int *dst_pit > const struct iosys_map *vmap, const struct drm_framebuffer *fb, > const struct drm_rect *clip) > { > - static const unsigned int default_dst_pitch[DRM_FORMAT_MAX_PLANES] = { > - 0, 0, 0, 0 > + static const u8 dst_pixsize[DRM_FORMAT_MAX_PLANES] = { > + 1, > }; > > - if (!dst_pitch) > - dst_pitch = default_dst_pitch; > - > - if (dst[0].is_iomem) > - drm_fb_xfrm_toio(dst[0].vaddr_iomem, dst_pitch[0], 1, vmap[0].vaddr, fb, > - clip, false, drm_fb_xrgb8888_to_gray8_line); > - else > - drm_fb_xfrm(dst[0].vaddr, dst_pitch[0], 1, vmap[0].vaddr, fb, > - clip, false, drm_fb_xrgb8888_to_gray8_line); > + drm_fb_xfrm(dst, dst_pitch, dst_pixsize, vmap, fb, clip, false, > + drm_fb_xrgb8888_to_gray8_line); > } > EXPORT_SYMBOL(drm_fb_xrgb8888_to_gray8); > > -- > 2.37.1
Sam Ravnborg
2022-Aug-05 17:59 UTC
[PATCH 00/12] drm/format-helper: Move to struct iosys_map
Hi Thomas, On Wed, Jul 27, 2022 at 01:33:00PM +0200, Thomas Zimmermann wrote:> Change format-conversion helpers to use struct iosys_map for source > and destination buffers. Update all users. Also prepare interface for > multi-plane color formats. > > The format-conversion helpers mostly used to convert to I/O memory > or system memory. To actual memory type depended on the usecase. We > now have drivers upcomming that do the conversion entirely in system > memory. It's a good opportunity to stream-line the interface of the > conversion helpers to use struct iosys_map. Source and destination > buffers can now be either in system or in I/O memory.Thanks for looking into this - I like how we hide the memory details in the helpers (system vs io). And unifying the system and io variants makes the API simpler - also good.> Note that the > implementation still only supports source buffers in system memory.Yeah, I noted this in my feedback but realized only now that it is written here. I left a few comments (details only) in some of the patches, most are reviewed without comments. There is a few general things - mostly bikeshedding about naming and such. As usual ignore what you think is irrelevant. Sam