RK3568 kernel阶段播放开机动画方案实现


方案介绍

基于 RK3568 在 kernel 阶段显示开机 logo 动画,本质原理是将 logo 图片采用刷新的方式演示成为开机动画的效果。kernel 版本采用 4.19 版本(5.10 同样适用)。

本文将首先描述如何将一张自定义的图片修改添加到 kernel 中称为 kernel 的开机动画(该方式将不仅仅是在 kernel 路径下替换 logo.bmp 这么简单)。本文主要内容如下:

  • kernel 层开机 logo 显示
  • 修改代码,实现开机动画效果
  • 基于 RK3568 SDK 下配置增加 logo 图片资源分区,实现后期简单可替换的 logo 开机动画方式

kernel 层开机 logo 显示

这里采用 Linux kernel 自身设定的开机 logo 方式,所以 logo 的文件名为 logo_linux_clut224.ppm,该文件一般会存放在 kernel/drivers/video/logo/ 路径下。采用 netpbm 工具生成想要替换的 logo(注意图片的尺寸大小,参考显示屏幕的尺寸)。

  1. logo 格式转换(Linux 只支持 ppm 格式的图片,需要将 png / bmp 格式转换成 ppm)
# png 格式
pngtopnm logo.png > logo.pnm
# bmp 格式
bmptopnm logo.bmp > logo.pnm
# 下面步骤一致
pnmquant 224 logo.pnm > logo224.pnm
pnmtoplainpnm logo224.pnm > logo_linux_clut224.ppm

以上转换完成后,将生成的 logo_linux_clut224.ppm 放入 kernel/drivers/video/logo/ 路径下(会替换原有的 logo_linux_clut224.ppm),在编译时会生成对应的 .c 文件和 .o 文件,可能会出现如下错误:

kernel/drivers/video/logo/logo_linux_clut224.ppm: Binary PNM is not supported
Use pnmnoraw(1) to convert it to ASCII PNM

以上错误是因为 ppm 图片是 bin 格式,需要转换成 ASCII 格式,方法如下:

pnmnoraw logo_linux_no_ascii_clut224.ppm > logo_linux_clut224.ppm

替换目录中的文件重新编译即可。

  1. 调整显示位置
    默认是左上角对齐,调整为中心对齐的方法如下:
    修改 drivers/video/fbmem.c 文件的 fb_show_logo_line() 函数:
    在这里插入图片描述
    修改其中画住位置的代码如下:
image.dx = (info->var.xres / 2) - (image.width / 2); //中心
image.dy =  (info->var.yres / 2) - (image.height/ 2); //中心
image.width = logo->width;
image.height = logo->height;

注意:info->var.xresinfo->var.yres 是分辨率大小,image.widthimage.height 是 logo 图片的大小。

图片显示起点位置修改,修改 drivers/video/console/fbcon.c 文件的 fbcon_prepare_logo() 函数:
在这里插入图片描述根据图片大小修改起点位置如下:

logo_height = fb_prepare_logo(info, ops->rotate);
logo_height += (info->var.yres / 2) - (logo_height / 2);
  1. 配置 kernel config ,启用 kernel logo:
Device Drivers--->
	Graphics support--->
		[*]Boot logo--->
			[*]Standard 224-color Linux logo

在这里插入图片描述需要添加支持 kernel console,不选会看不到 logo:

Device Drivers--->
	Graphics support--->
		Console display driver support--->
			<*>Framebuffer Console support

在这里插入图片描述全屏显示时,屏幕左上角会有光标闪烁的问题,解决方法如下:
修改 drivers/video/fbdev/core/bitblit.c 中的 bit_cursor() 函数:
在这里插入图片描述
将这个判断注释掉,或者将 err 改为 0, 如下:
在这里插入图片描述


修改代码,实现开机动画效果

通过分析代码,可以发现显示 logo 的位置在 drivers/video/fbdev/core/fbcon.c 文件中的 fbcon_switch() 函数中,具体位置如下:

在这里插入图片描述可以看到其中的 fb_show_logo() 函数,进入这个函数,位置在 drivers/video/fbdev/core/fbmem.c ,代码如下:
在这里插入图片描述通过以上函数可以发现,显示 logo 资源数据来自 fb_logo.logo,在这里,我们只需要修改 fb_logo.logo 资源就可以实现动态的 logo 显示。

通过查找代码,发现加载 logo 资源的代码来自于 drivers/video/fbdev/core/fbcon.c 文件的 fbcon_prepare_logo() 函数中,参考流程如下:

fbcon_prepare_logo()
	--->fb_prepare_logo()
		--->fb_find_logo() [这个函数位于 drivers/video/logo/logo.c 中]

通过上面的代码执行流程可以得到 fb_logo.logo 资源。所以,如果想要实现动态 logo 显示,只需要使用多个 logo 资源来循环显示就可以实现动画效果。因此,我们可以循环调用 fb_find_logo() 来实现。问题来了,现在我们 fb_find_logo(int depth) 的参数是 depth 这个值,本身 kernel 查找 logo 资源是通过这个值来找到不同颜色深度的图片资源,通常系统中使用 depth 这个值只会用到低 16 位,我们可以使用这个 depth 参数的高 16 位用于传递动态显示图片的图片序号值。

drivers/video/logo/logo.c 文件中的 fb_find_logo() 函数修改如下:
在这里插入图片描述可以看出,通过提取 depth 的高 16 位作为 num 来标识图片序号。至于后面的 logo 数据,参考这里的 logo_linux_clut224(上一章内容中添加 logo 资源的方式进行添加)。

注意:编译配置为:Standard 224-color Linux logo 时,logo 资源数据文件一定要以 _clut224.ppm 结尾,否则 Makefile 识别不到,具体内容可以参考 drivers/video/logo/ 路径下的 Makefile 文件中关于 ppm 文件的编译规则:
在这里插入图片描述
到这里,我们就可以编写函数来实现循环获取 logo 资源用于动画显示了。这里我们不修改 fbcon_prepare_logo() 函数,重新实现一个获取 logo 资源的 fb_get_logo() 函数,这是因为在 fbcon_prepare_logo() 中有很多操作是不需要我们去修改的,所以仅仅在 fb_show_logo 之前更新 fb_logo.logo 资源即可。

drivers/video/fbdev/core/fbmem.c 文件中添加如下的新函数:
在这里插入图片描述需要注意我们使用该函数的位置是在 drivers/video/fbdev/core/fbcon.c 中,所以在这里还需要使用 EXPORT_SYMBOL(fb_get_logo); 将这个函数导出,否则编译的时候会提示未定义的引用。

现在一切就绪,我们就可以做动态显示了。回到 logo 显示的 drivers/video/fbdev/core/fbcon.c 文件中的 fbcon_switch()函数中,做如下修改:

static int fbcon_switch(struct vc_data *vc)
{
	... ...
	if(logo_shown == FBCON_LOGO_DRAW) {
		logo_shown = fg_console;
		/* This is protected above by initmem_freed*/
		for(i = 0; i <
  • 2
    点赞
  • 20
    收藏
    觉得还不错? 一键收藏
  • 4
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值