首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 移动开发 > Android >

Android系统的开机镜头显示过程分析

2012-08-17 
Android系统的开机画面显示过程分析好几个月都没有更新过博客了,从今天开始,老罗将尝试对Android系统的UI

Android系统的开机画面显示过程分析

        好几个月都没有更新过博客了,从今天开始,老罗将尝试对Android系统的UI实现作一个系统的分析,也算是落实之前所作出的承诺。提到Android系统的UI,我们最先接触到的便是系统在启动过程中所出现的画面了。Android系统在启动的过程中,最多可以出现三个画面,每一个画面都用来描述一个不同的启动阶段。本文将详细分析这三个开机画面的显示过程,以便可以开启我们对Android系统UI实现的分析之路。

        第一个开机画面是在内核启动的过程中出现的,它是一个静态的画面。第二个开机画面是在init进程启动的过程中出现的,它也是一个静态的画面。第三个开机画面是在系统服务启动的过程中出现的,它是一个动态的画面。无论是哪一个画面,它们都是在一个称为帧缓冲区(frame buffer,简称fb)的硬件设备上进行渲染的。接下来,我们就分别分析这三个画面是如何在fb上显示的。

        1. 第一个开机画面的显示过程

        Android系统的第一个开机画面其实是Linux内核的启动画面。在默认情况下,这个画面是不会出现的,除非我们在编译内核的时候,启用以下两个编译选项:

        CONFIG_FRAMEBUFFER_CONSOLE

        CONFIG_LOGO

        第一个编译选项表示内核支持帧缓冲区控制台,它对应的配置菜单项为:Device Drivers ---> Graphics support ---> Console display driver support ---> Framebuffer Console support。第二个编译选项表示内核在启动的过程中,需要显示LOGO,它对应的配置菜单项为:Device Drivers ---> Graphics support ---> Bootup logo。配置Android内核编译选项可以参考在Ubuntu上下载、编译和安装Android最新内核源代码(Linux Kernel)一文。

        帧缓冲区硬件设备在内核中有一个对应的驱动程序模块fbmem,它实现在文件kernel/goldfish/drivers/video/fbmem.c中,它的初始化函数如下所示:

static void msg_stop(const char *name){    struct service *svc = service_find_by_name(name);    if (svc) {        service_stop(svc);    } else {        ERROR("no such service '%s'\n", name);    }}
       这个函数首先调用函数service_find_by_name来找到名称等于name,即“bootanim”的服务,然后再调用函数service_stop来停止这个服务。

       前面提到,名称为“bootanim”的服务对应的应用程序即为/system/bin/bootanimation。因此,停止名称为“bootanim”的服务即为停止执行应用程序/system/bin/bootanimation,而当应用程序/system/bin/bootanimation停止执行的时候,开机动画就会停止显示了。

       至此,Android系统的三个开机画面的显示过程就分析完成了。通过这个三个开机画面的显示过程分析,我们学习到:

       1. 在内核层,系统屏幕是使用一个称为帧缓冲区的硬件设备来描述的,而用户空间的应用程序可以通过设备文件/dev/fb0或者/dev/graphics/fb0来操作这个硬件设备。实际上,帧缓冲区本身并不是一个真正的硬件,它只不过是对显卡的一个抽象表示,不过,我们通过访帧缓冲区就可以间接地操作显卡内存以及显卡中的其它寄存器。

       2. OpenGL是通过EGL接口来渲染屏幕,而EGL接口是通过ANativeWindow类来间接地渲染屏幕的。我们可以将ANativeWindow类理解成一个Android系统的本地窗口类,即相当于是Windows系统中的窗口句柄概念,它最终是通过文件/dev/fb0或者/dev/graphics/fb0来渲染屏幕的。

       3. init进程在启动的过程中,会将另外一个ueventd进程也启动起来。ueventd进程对应的可执行文件与init进程对应的可执行文件均为/init,不过ueventd进程主要负责处理内核发出的uevent事件,即负责管理系统中的设备文件。

       4. 每当我们设置一个系统属性的时候,init进程都会接收到一个系统属性变化事件。当发生变化的系统属性的名称等于“ctl.start”或者“ctl.stop”,那么实际上是向init进程发出一个启动或者停止服务的命令。

       前面第1点和第2点的知识是与Android系统的UI实现相关的,而后面第3点和第4点是两个额外获得的知识点。

       本文的目的并不是单纯为了介绍Android系统的开机画面,而是希望能够以Android系统的开机画面来作为切入点来分析Android系统的UI实现。在后面的文章中,我们就会根据本文所涉及到的知识点,来展开分析Android系统的UI实现,敬请关注。

16楼szbhzc昨天 10:21
老罗,你平时在阅读源代码的时候用什么工具软件?source insight?还是其它?
Re: Luoshengyang9小时前
回复szbhzcn在windows平台用vs + va,在linux平台就用最原始的工具vim。
15楼zhangjie201412前天 12:58
首先,多谢您的无私奉献精神。n我一直对android 的bind机制看的糊里糊涂,看你的博客里面介绍android进程间通信部分,一直没坚持看下去。。。
Re: Luoshengyang前天 13:10
回复zhangjie201412n如果想要理解Android系统的代码,Binder机制是一定要熟悉的,因为用到Binder机制的地方实在是太多了。
Re: zhangjie201412前天 13:16
其实很多地方看不下去是因为对应用层编程以及Linux kernel中对内存映射技术的不了解,要静下心来慢慢看,您有推荐的资料吗?回复Luoshengyang
Re: Luoshengyang前天 14:53
回复zhangjie201412n有两本书推荐一下: n1. Understanding the Linux Kernel.n2. Linux内核源代码情景分析.n不过这两本书也是有点难啃的,要花点力气和精力才行。理解Linux内核的基础知识对学习Android系统源代码很重要。至于应用层编译,就需要自己多动手了。
14楼szbhzc4天前 16:57
老罗在哪个城市呀?
Re: Luoshengyang前天 11:56
回复szbhzcnGZ
Re: szbhzc前天 11:59
回复Luoshengyangn哦,很近呀。SZ
13楼duli_03274天前 16:53
默默关注你的博客已经很久了,以为最近没更新在忙着出书呢!呵呵 不过终于有新的东西更新了,并且应该是我一直搞不懂的关于surface的相关的内容。继续期待罗老师杰作!
Re: Luoshengyang4天前 16:55
回复duli_0327n对,后续会重点分析以下两个与UI相关的点:n1. Surface的实现,主要就是SurfaceFlinger的实现了n2. 一个界面控件,例如,一个Button,是如何渲染出来的n本文介绍的主要是一些基础知识,例如,帧缓冲区(FrameBuffer),是比较底层的东西,不过了解了这些知识之后,就可以对Android系统的UI有一个感性的认识了。
12楼wangkuifeng01184天前 16:52
太深奥了,完全看不懂!
11楼houyizi3378257704天前 13:19
不好意思;看了大家的评论和你的回复我知道我该看什么书籍了!1. Understanding the Linux Kernel.n2. Linux内核源代码情景分析.
Re: Luoshengyang4天前 13:32
回复houyizi337825770n《Linux Device Drivers》这本书也不错,讲Linux驱动的,对理解Android系统的日志驱动、Binder驱动以及匿名共享内存驱动有帮助。其它的书籍可以参考这篇文章http://blog.csdn.net/luoshengyang/article/details/6557518。
10楼LRS0307403044天前 09:36
终于知道开机动画是怎么停止的了! 好文章,可惜对前面的看不透,继续学习.......
Re: Luoshengyang4天前 10:09
回复LRS030740304n停止开机动画的代码的确是比较隐密,WindowManagerService通过向SurfaceFlinger发送一个IBinder.FIRST_CALL_TRANSACTION请求来实现,不像一般的代码调用那么直观。
9楼huangfurenhe5天前 14:34
罗兄最先是做驱动开发还是应用开发的?
Re: Luoshengyang5天前 14:39
回复huangfurenhen都不是~~不过无论是做驱动开发还是应用开发,最好都是对系统有一个整体的了解会好一些~~
Re: huangfurenhe5天前 14:41
“对系统有一个整体的了解”要从哪里开始,内核吗?回复Luoshengyang
Re: Luoshengyang4天前 09:20
回复huangfurenhen内核是一方面,像Android系统的应用程序框架层的实现,也是很值得去了解一下的,这样有助于开发APP。
8楼zhongyuanceshi5天前 09:31
老罗,讲下shell命令下的一些文件及作用,感觉/dev,/sys,/proc,不知道是啥回事?
Re: Luoshengyang5天前 11:02
回复zhongyuanceshin这几个目录的文件太多了,其实没有必要都知道它们是干什么用的,要用的时候再去查一下资料就可以了。ndev目录下面的文件都是设备文件,即内核中硬件驱动程序一般都会在里面创建一个设备文件,以便用户空间的应用程序可以通过这些设备文件来和它们交互。ndev目录下的设备文件是以扁平方式来组织的,比较混乱,不方便管理,Linux内核后来设计了一套新的设备文件管理系统sysfs,它一般就挂载在sys目录中。sys目录下面的文件也是设备文件,不过它们是分门别类地组织的,并且提供了属性文件的概念,用来细化用户空间的应用程序与内核中的硬件驱动程序的交互方式。nproc目录下面的文件主要是用来访问内核参数的,它挂载的即为proc文件系统。
7楼zhongyuanceshi6天前 17:51
欢迎欢迎,你终于回来了。n顺便问个问题:android所有界面的状态栏如果要去掉,该如何修改?
Re: Luoshengyang5天前 08:45
回复zhongyuanceshin不好意思,没研究过这个。
6楼hellowolrd6天前 17:46
哇,老罗又更新了n我是看你这博客开始学android的,写的真的太好了n每一个系列都自成一体,无需其他参考.从顶到下都能串到一起,这样看起来最痛快了.
Re: Luoshengyang6天前 17:51
回复hellowolrdn你说的正是我想做的,多谢关注!
5楼houyizi3378257706天前 17:01
谢谢罗哥的回复:我看了一半《linux device drivers》;公司又让搞Android的系统;我年前自己掏钱参加才职业培训嵌入式ARM+Linux;刚踏入这个行业;所以还是……很容易学着学着就乱了头绪……!现在是感觉是对:ARM、MIPS、UBOOT、YAMON、LINUX、ANDROID、QT(感觉已经过时了)、都了解点一点点!但是没有一个精通的!现在让我做Android的系统移植!也没人管我!自己自学!天天上班就是看看书、看看网页!无意间发现了你的博客、昨天看了一天、今天差不多又看了一天……计划按你走过的路认真学习学习;比我买的哪几本书写的强多了!他们那知识点、层层都联系不起来!看了都想骂作者……误人子弟!强烈推荐罗哥:整理一下出一本书出来……一定捧场……
4楼houyizi3378257706天前 16:47
罗哥:推荐几本循序渐进Linux系统、Android系统的书呗?就是要像你这样把他们内部的原理理解的透透彻彻、大彻大悟的书籍……非常感谢……houyizi313@gmail.com
3楼houyizi3378257706天前 16:41
罗哥:你为什么不出一本Android书腻?看你这分析的比那些出Android的书的分析的透彻、明白多了!看了几本Android的书看的人稀里糊涂的!不清不楚!你这水平太高了!
2楼uoykcuftnawi6天前 14:52
終於更新了。。等得好苦啊。
Re: Luoshengyang6天前 15:04
回复uoykcuftnawin多谢关注,后续会重点分析Android系统的UI实现。
1楼mutemob6天前 12:37
老罗,你的新书什么时候出版?
Re: Luoshengyang6天前 13:01
回复mutemobn10月底的样子

热点排行
Bad Request.