
Support most of possible pixel formats so we can test them in sandbox.
Signed-off-by: Jiaxun Yang jiaxun.yang@flygoat.com --- arch/sandbox/cpu/sdl.c | 58 +++++++++++++++++++++++++++++++++++++----- arch/sandbox/include/asm/sdl.h | 17 ++++++++----- drivers/video/sandbox_sdl.c | 16 +++++++----- include/dm/test.h | 2 ++ test/dm/video.c | 14 +++++----- 5 files changed, 81 insertions(+), 26 deletions(-)
diff --git a/arch/sandbox/cpu/sdl.c b/arch/sandbox/cpu/sdl.c index ed84646bdab7..436c0448de1f 100644 --- a/arch/sandbox/cpu/sdl.c +++ b/arch/sandbox/cpu/sdl.c @@ -5,8 +5,10 @@
#include <errno.h> #include <unistd.h> +#include <stdint.h> #include <stdbool.h> #include <sysreset.h> +#include <video_format.h> #include <linux/input.h> #include <SDL2/SDL.h> #include <asm/state.h> @@ -69,6 +71,47 @@ static struct sdl_info { int src_depth; } sdl;
+static inline SDL_PixelFormatEnum sandbox_video_format(int l2bbp, int format) +{ + switch (l2bbp) { + case VIDEO_BPP8: + switch (format) { + case VIDEO_DEFAULT: + case VIDEO_RGB332: + return SDL_PIXELFORMAT_RGB332; + } + case VIDEO_BPP16: + switch (format) { + case VIDEO_DEFAULT: + case VIDEO_RGB565: + return SDL_PIXELFORMAT_RGB565; + default: + break; + } + break; + case VIDEO_BPP32: + switch (format) { + case VIDEO_DEFAULT: + case VIDEO_XRGB8888: + return SDL_PIXELFORMAT_RGB888; + case VIDEO_BGRX8888: + return SDL_PIXELFORMAT_BGRX8888; + case VIDEO_XBGR8888: + return SDL_PIXELFORMAT_BGR888; + case VIDEO_RGBA8888: + return SDL_PIXELFORMAT_RGBA8888; + case VIDEO_XRGB2101010: + return SDL_PIXELFORMAT_ARGB2101010; + default: + break; + } + default: + break; + } + + return SDL_PIXELFORMAT_UNKNOWN; +} + static void sandbox_sdl_poll_events(void) { /* @@ -122,9 +165,10 @@ int sandbox_sdl_remove_display(void) }
int sandbox_sdl_init_display(int width, int height, int log2_bpp, - bool double_size) + int format, bool double_size) { struct sandbox_state *state = state_get_current(); + SDL_PixelFormatEnum sdl_format; int err;
if (!width || !state->show_lcd) @@ -135,6 +179,12 @@ int sandbox_sdl_init_display(int width, int height, int log2_bpp, if (sdl.renderer) sandbox_sdl_remove_display();
+ sdl_format = sandbox_video_format(log2_bpp, format); + if (sdl_format == SDL_PIXELFORMAT_UNKNOWN) { + printf("Unsupported video format\n"); + return -EINVAL; + } + if (SDL_InitSubSystem(SDL_INIT_VIDEO) < 0) { printf("Unable to initialise SDL LCD: %s\n", SDL_GetError()); return -EPERM; @@ -153,8 +203,6 @@ int sandbox_sdl_init_display(int width, int height, int log2_bpp, printf("Unable to init hinting: %s", SDL_GetError());
sdl.src_depth = 1 << log2_bpp; - if (log2_bpp != 4 && log2_bpp != 5) - log2_bpp = 5; sdl.depth = 1 << log2_bpp; sdl.pitch = sdl.width * sdl.depth / 8; sdl.screen = SDL_CreateWindow("U-Boot", SDL_WINDOWPOS_UNDEFINED, @@ -174,9 +222,7 @@ int sandbox_sdl_init_display(int width, int height, int log2_bpp, return -EIO; }
- sdl.texture = SDL_CreateTexture(sdl.renderer, log2_bpp == 4 ? - SDL_PIXELFORMAT_RGB565 : - SDL_PIXELFORMAT_RGB888, + sdl.texture = SDL_CreateTexture(sdl.renderer, sdl_format, SDL_TEXTUREACCESS_STREAMING, width, height); if (!sdl.texture) { diff --git a/arch/sandbox/include/asm/sdl.h b/arch/sandbox/include/asm/sdl.h index ee4991f7c24a..7b4f26f994da 100644 --- a/arch/sandbox/include/asm/sdl.h +++ b/arch/sandbox/include/asm/sdl.h @@ -24,7 +24,7 @@ * and -EPERM if the video failed to come up. */ int sandbox_sdl_init_display(int width, int height, int log2_bpp, - bool double_size); + int format, bool double_size);
/** * sandbox_sdl_remove_display() - Remove the SDL screen @@ -89,12 +89,13 @@ int sandbox_sdl_sound_stop(void); int sandbox_sdl_sound_init(int rate, int channels);
/** - * sandbox_sdl_set_bpp() - Set the depth of the sandbox display + * sandbox_sdl_set_pixel() - Set depth and format of the sandbox display * * The device must not be active when this function is called. It activiates it * before returning. * - * This updates the depth value and adjusts a few other settings accordingly. + * This updates the depth value and pixel format for the sandbox display, then + * it adjusts a few other settings accordingly. * It must be called before the display is probed. * * @dev: Device to adjust @@ -102,11 +103,12 @@ int sandbox_sdl_sound_init(int rate, int channels); * Return: 0 if the device was already active, other error if it fails to probe * after the change */ -int sandbox_sdl_set_bpp(struct udevice *dev, enum video_log2_bpp l2bpp); +int sandbox_sdl_set_pixel(struct udevice *dev, enum video_log2_bpp l2bpp, + enum video_format format);
#else static inline int sandbox_sdl_init_display(int width, int height, int log2_bpp, - bool double_size) + int format, bool double_size) { return -ENODEV; } @@ -151,8 +153,9 @@ static inline int sandbox_sdl_sound_init(int rate, int channels) return -ENODEV; }
-static inline int sandbox_sdl_set_bpp(struct udevice *dev, - enum video_log2_bpp l2bpp) +static inline int sandbox_sdl_set_pixel(struct udevice *dev, + enum video_log2_bpp l2bpp, + enum video_format format) { return -ENOSYS; } diff --git a/drivers/video/sandbox_sdl.c b/drivers/video/sandbox_sdl.c index 69dfa9302735..ddd72a14de83 100644 --- a/drivers/video/sandbox_sdl.c +++ b/drivers/video/sandbox_sdl.c @@ -31,7 +31,7 @@ static int sandbox_sdl_probe(struct udevice *dev) int ret;
ret = sandbox_sdl_init_display(plat->xres, plat->yres, plat->bpix, - state->double_lcd); + plat->format, state->double_lcd); if (ret) { puts("LCD init failed\n"); return ret; @@ -39,6 +39,7 @@ static int sandbox_sdl_probe(struct udevice *dev) uc_priv->xsize = plat->xres; uc_priv->ysize = plat->yres; uc_priv->bpix = plat->bpix; + uc_priv->format = plat->format; uc_priv->rot = plat->rot; uc_priv->vidconsole_drv_name = plat->vidconsole_drv_name; uc_priv->font_size = plat->font_size; @@ -48,12 +49,14 @@ static int sandbox_sdl_probe(struct udevice *dev) return 0; }
-static void set_bpp(struct udevice *dev, enum video_log2_bpp l2bpp) +static void set_pixel(struct udevice *dev, enum video_log2_bpp l2bpp, + enum video_format format) { struct video_uc_plat *uc_plat = dev_get_uclass_plat(dev); struct sandbox_sdl_plat *plat = dev_get_plat(dev);
plat->bpix = l2bpp; + plat->format = format;
uc_plat->size = plat->xres * plat->yres * VNBYTES(plat->bpix);
@@ -61,7 +64,7 @@ static void set_bpp(struct udevice *dev, enum video_log2_bpp l2bpp) * Set up to the maximum size we'll ever need. This is a strange case. * The video memory is allocated by video_post_bind() called from * board_init_r(). If a test changes the reoslution so it needs more - * memory later (with sandbox_sdl_set_bpp()), it is too late to make + * memory later (with sandbox_sdl_set_pixel()), it is too late to make * the frame buffer larger. * * So use a maximum size here. @@ -79,7 +82,8 @@ static void set_bpp(struct udevice *dev, enum video_log2_bpp l2bpp) uc_plat->size *= 2; }
-int sandbox_sdl_set_bpp(struct udevice *dev, enum video_log2_bpp l2bpp) +int sandbox_sdl_set_pixel(struct udevice *dev, enum video_log2_bpp l2bpp, + enum video_format format) { struct video_uc_plat *uc_plat = dev_get_uclass_plat(dev); int ret; @@ -89,7 +93,7 @@ int sandbox_sdl_set_bpp(struct udevice *dev, enum video_log2_bpp l2bpp) sandbox_sdl_remove_display();
uc_plat->hide_logo = true; - set_bpp(dev, l2bpp); + set_pixel(dev, l2bpp, format);
ret = device_probe(dev); if (ret) @@ -122,7 +126,7 @@ static int sandbox_sdl_bind(struct udevice *dev) l2bpp = dev_read_u32_default(dev, "log2-depth", VIDEO_BPP16); plat->rot = dev_read_u32_default(dev, "rotate", 0);
- set_bpp(dev, l2bpp); + set_pixel(dev, l2bpp, VIDEO_DEFAULT);
return ret; } diff --git a/include/dm/test.h b/include/dm/test.h index 02737411a164..87568d741d49 100644 --- a/include/dm/test.h +++ b/include/dm/test.h @@ -153,6 +153,7 @@ extern struct unit_test_state global_dm_test_state; * @xres: Width of display in pixels * @yres: Height of display in pixels * @bpix: Log2 of bits per pixel (enum video_log2_bpp) + * @format: Pixel format (enum video_format) * @rot: Console rotation (0=normal orientation, 1=90 degrees clockwise, * 2=upside down, 3=90 degree counterclockwise) * @vidconsole_drv_name: Name of video console driver (set by tests) @@ -162,6 +163,7 @@ struct sandbox_sdl_plat { int xres; int yres; int bpix; + int format; int rot; const char *vidconsole_drv_name; int font_size; diff --git a/test/dm/video.c b/test/dm/video.c index 0da96aec5efd..47a8df511e8b 100644 --- a/test/dm/video.c +++ b/test/dm/video.c @@ -395,7 +395,7 @@ static int dm_test_video_bmp8(struct unit_test_state *uts)
ut_assertok(uclass_find_first_device(UCLASS_VIDEO, &dev)); ut_assertnonnull(dev); - ut_assertok(sandbox_sdl_set_bpp(dev, VIDEO_BPP8)); + ut_assertok(sandbox_sdl_set_pixel(dev, VIDEO_BPP8, VIDEO_DEFAULT));
ut_assertok(read_file(uts, "tools/logos/denx.bmp", &addr));
@@ -416,7 +416,7 @@ static int dm_test_video_bmp16(struct unit_test_state *uts)
ut_assertok(uclass_find_first_device(UCLASS_VIDEO, &dev)); ut_assertnonnull(dev); - ut_assertok(sandbox_sdl_set_bpp(dev, VIDEO_BPP16)); + ut_assertok(sandbox_sdl_set_pixel(dev, VIDEO_BPP16, VIDEO_DEFAULT));
ut_assertok(read_file(uts, "tools/logos/denx-16bpp.bmp.gz", &src)); ut_assertok(gunzip(map_sysmem(dst, 0), dst_len, map_sysmem(src, 0), @@ -439,7 +439,7 @@ static int dm_test_video_bmp24(struct unit_test_state *uts)
ut_assertok(uclass_find_first_device(UCLASS_VIDEO, &dev)); ut_assertnonnull(dev); - ut_assertok(sandbox_sdl_set_bpp(dev, VIDEO_BPP16)); + ut_assertok(sandbox_sdl_set_pixel(dev, VIDEO_BPP16, VIDEO_DEFAULT));
ut_assertok(read_file(uts, "tools/logos/denx-24bpp.bmp.gz", &src)); ut_assertok(gunzip(map_sysmem(dst, 0), dst_len, map_sysmem(src, 0), @@ -462,7 +462,7 @@ static int dm_test_video_bmp24_32(struct unit_test_state *uts)
ut_assertok(uclass_find_first_device(UCLASS_VIDEO, &dev)); ut_assertnonnull(dev); - ut_assertok(sandbox_sdl_set_bpp(dev, VIDEO_BPP32)); + ut_assertok(sandbox_sdl_set_pixel(dev, VIDEO_BPP32, VIDEO_DEFAULT));
ut_assertok(read_file(uts, "tools/logos/denx-24bpp.bmp.gz", &src)); ut_assertok(gunzip(map_sysmem(dst, 0), dst_len, map_sysmem(src, 0), @@ -483,7 +483,7 @@ static int dm_test_video_bmp32(struct unit_test_state *uts)
ut_assertok(uclass_find_first_device(UCLASS_VIDEO, &dev)); ut_assertnonnull(dev); - ut_assertok(sandbox_sdl_set_bpp(dev, VIDEO_BPP32)); + ut_assertok(sandbox_sdl_set_pixel(dev, VIDEO_BPP32, VIDEO_DEFAULT)); ut_assertok(read_file(uts, "tools/logos/denx.bmp", &addr));
ut_assertok(video_bmp_display(dev, addr, 0, 0, false)); @@ -517,7 +517,7 @@ static int dm_test_video_comp_bmp32(struct unit_test_state *uts)
ut_assertok(uclass_find_first_device(UCLASS_VIDEO, &dev)); ut_assertnonnull(dev); - ut_assertok(sandbox_sdl_set_bpp(dev, VIDEO_BPP32)); + ut_assertok(sandbox_sdl_set_pixel(dev, VIDEO_BPP32, VIDEO_DEFAULT));
ut_assertok(read_file(uts, "tools/logos/denx.bmp", &addr));
@@ -536,7 +536,7 @@ static int dm_test_video_comp_bmp8(struct unit_test_state *uts)
ut_assertok(uclass_find_first_device(UCLASS_VIDEO, &dev)); ut_assertnonnull(dev); - ut_assertok(sandbox_sdl_set_bpp(dev, VIDEO_BPP8)); + ut_assertok(sandbox_sdl_set_pixel(dev, VIDEO_BPP8, VIDEO_DEFAULT));
ut_assertok(read_file(uts, "tools/logos/denx.bmp", &addr));