[Letux-kernel] [PATCH] fbpng: make it work with 32 bpp fb

H. Nikolaus Schaller hns at goldelico.com
Thu Jan 18 15:43:11 CET 2018


Hi Andreas,
queued for inclusion.

BTW: I have tried cat /dev/urandom >/dev/fb0 and had not seen hangs or
bus errors. Well, I also haven't seen anything since an X server was running.
And I haven't done heavy load testing or randomized page allocation effects.

BR and thanks,
Nikolaus

> Am 18.01.2018 um 08:07 schrieb Andreas Kemnade <andreas at kemnade.info>:
> 
> fbpng did require 24 bpp fb which is not possible
> on moderm omapfb. So be a bit flexible here to still
> have it as a test program.
> It does not work on stretch yet.
> 
> Signed-off-by: Andreas Kemnade <andreas at kemnade.info>
> ---
> Letux/root/fbpng.c | 55 +++++++++++++++++++++++++++++++++++++-----------------
> 1 file changed, 38 insertions(+), 17 deletions(-)
> 
> diff --git a/Letux/root/fbpng.c b/Letux/root/fbpng.c
> index 048185fb8920..bc636707e863 100644
> --- a/Letux/root/fbpng.c
> +++ b/Letux/root/fbpng.c
> @@ -53,7 +53,14 @@ int main(int argc, char *argv[])
> 
> 	// Start reading
> 	png_init_io(png_ptr, fp);
> -	png_read_png(png_ptr, info_ptr, PNG_TRANSFORM_STRIP_16 | PNG_TRANSFORM_STRIP_ALPHA | PNG_TRANSFORM_PACKING, NULL);
> +	png_read_png(png_ptr, info_ptr,
> +		PNG_TRANSFORM_STRIP_16 |
> +		PNG_TRANSFORM_STRIP_ALPHA |
> +		PNG_TRANSFORM_PACKING |
> +		PNG_TRANSFORM_GRAY_TO_RGB |
> +		PNG_TRANSFORM_EXPAND,
> +		NULL);
> +
> 	row_ptr = png_get_rows(png_ptr, info_ptr);
> 	if (row_ptr == NULL)
> 	{
> @@ -75,21 +82,22 @@ int main(int argc, char *argv[])
> 	if (ret == -1)
> 		perror("ioctl(FBIOGET_VSCREENINFO)");
> 
> +	if ((fbvar.bits_per_pixel != 32) && (fbvar.bits_per_pixel != 24)) {
> +		fbvar.bits_per_pixel = info_ptr->pixel_depth;
> +
> +		ret = ioctl(fd, FBIOPUT_VSCREENINFO, &fbvar);
> +		if (ret == -1)
> +			perror("ioctl(FBIOPUT_VSCREENINFO)");
> +	}
> +
> 	destsize = fbvar.xres_virtual * fbvar.yres_virtual
> -		 * info_ptr->pixel_depth / 8;
> +		 * fbvar.bits_per_pixel / 8;
> 	dest = mmap(0, destsize, PROT_WRITE|PROT_READ, MAP_SHARED, fd, 0);
> 	if (dest == MAP_FAILED)
> 	{
> 		perror("mmap(fbptr) failed");
> 		return 1;
> 	}
> -
> -	fbvar.bits_per_pixel = info_ptr->pixel_depth;
> -
> -	ret = ioctl(fd, FBIOPUT_VSCREENINFO, &fbvar);
> -	if (ret == -1)
> -		perror("ioctl(FBIOPUT_VSCREENINFO)");
> -
> 	memset(dest, 0, destsize);
> 
> 	switch (info_ptr->pixel_depth)
> @@ -105,20 +113,32 @@ int main(int argc, char *argv[])
> 			width = info_ptr->width;
> 			if (width  > fbvar.xres_virtual)
> 				width = fbvar.xres_virtual;
> -			dst += (fbvar.xres_virtual-width) / 2 * 3;
> +			dst += (fbvar.xres_virtual-width) / 2 * fbvar.bits_per_pixel / 8;
> 
> 			for (h = 0; h < height; h++)
> 			{
> 				unsigned char *src = row_ptr[h];
> 				int len = width;
> -				while (len--)
> -				{
> -					*dst++ = src[2];
> -					*dst++ = src[1];
> -					*dst++ = src[0];
> -					src += 3;
> +				if (fbvar.bits_per_pixel == 32) {
> +					while (len--)
> +					{
> +						*dst++ = src[2];
> +						*dst++ = src[1];
> +						*dst++ = src[0];
> +						src += 3;
> +						dst++;

Well, we could think about one loop and make this additional increment conditional.
Or even use src += (fbvar.bits_per_pixel == 32) ? 1:0.

If the compiler (and speculative execution) is clever enough
it would not even be slower.

But it is good enough for its purpose.

> +					}
> +				} else {
> +					while (len--)
> +					{
> +						*dst++ = src[2];
> +						*dst++ = src[1];
> +						*dst++ = src[0];
> +						src += 3;
> +					}
> 				}
> -				dst += fbvar.xres_virtual - width;
> +				dst += (fbvar.xres_virtual - width) 
> +				*  fbvar.bits_per_pixel / 8;
> 			}
> 			break;
> 		}
> @@ -135,3 +155,4 @@ int main(int argc, char *argv[])
> 
> 	return 0;
> }
> +
> -- 
> 2.11.0
> 
> _______________________________________________
> http://projects.goldelico.com/p/gta04-kernel/
> Letux-kernel mailing list
> Letux-kernel at openphoenux.org
> http://lists.goldelico.com/mailman/listinfo.cgi/letux-kernel



More information about the Letux-kernel mailing list