【Android 系统开发】 Android 系统启动流程简介

Android 系统启动总结 : Android 系统启动分底层 Linux 内核启动 和 应用系统启动;

-- 底层系统启动 : 系统上电, bootloader 启动, linux kernel 启动, init 进程启动;

-- 应用系统启动 : init 进程启动关键的进程如 Zygote 进程System Server 等系统服务, 之后进入 Home 界面;

一. Android 底层系统启动流程(Bootloader Kernel init)

1. 系统上电 执行 ROM 引导代码

(1) Android 系统执行的操作

Android 底层上电流程 : CPU 上电 --> PC 指向 ROM 启动代码零地址 --> 直接执行启动代码 / 将启动代码载入 RAM 后执行

-- CPU 上电 : 首先 Android 系统的 CPU 上电复位;

-- 程序指针指向 : 复位时 PC 指针指向 ROM 的零地址, 即 Android 系统的启动代码的地址;

-- 直接执行代码 : 从 零地址 读取可执行代码直接运行;

-- 转载代码到RAM再执行 : 将执行代码载入到 CPU 的 RAM 中执行;

启动代码介绍 : 启动代码 固化在 ROM 中, CPU 复位上电后, PC 指向 ROM 中代码的初始地址 即 零地址, 并执行该代码;

(2) PC 启动与 Android 启动比较

PC 启动系统机制 : ROM 分类BIOS 作用 (初始化硬件设备, 载入硬盘运行);

-- 启动 ROM 分类 : 包括 PROM, EPROM, EEPROM三种;

-- ROM 中的启动程序 BIOS : BIOS 是 PC 的启动代码, 其作用是初始化硬件设备, BIOS 被载入到硬盘的扇区 MBR 之后运行并开始引导操作系统;

Android 系统机制 : ROM 分类 和 Bootloader 启动程序;

-- 启动 ROM 分类 : Android 中的 启动 ROM 分为 NOR FlashNAND Flash 两种;

-- ROM 中的启动程序 Bootloader : Bootloader 地址是 CPU 复位后指向的地址, 即零地址;

(3) Bootloader 启动方式简介

Bootloader 启动位置 : Bootloader 在 ROM 中直接启动 还是 装载到 RAM 中启动取决与 ROM 是否可以按字节寻址;

-- 按字节寻址的 ROM : NOR Flash 可以按字节寻址, Bootloader 可以直接在 ROM 中执行;

-- 不可字节寻址 ROM : NAND Flash 不支持按字节寻址, Bootloader 需要先载入到 CPU 的 RAM 中, 然后在执行;

(4) NOR Flash 启动过程

启动方式总结 : 直接执行 Bootloader -> 写寄存器 -> 配置模块 -> 复制代码到内存中 -> PC 指向零地址 -> 地址映射 -> 执行映射的启动代码;

注意 : 这种情况是将 Bootloader 烧写入 NOR Flash 中的情况, 与现在最新的 CPU 内置 ROM 方式不同;

NOR Flash 启动过程 : 这种 ROM 支持字节寻址, 固化在其中的启动代码(Bootloader)可以按照顺序执行;

-- 开始启动 : Bootloader 存放在 NOR Flash 零地址, CPU 复位后 PC 指向零地址, 开始执行 Bootloader;

-- 写寄存器 : 配置 EMI 寄存器, 该寄存器存储设置好的各存储器地址 和 存取规则;

-- 模块配置 : 配置电源管理模块, 使各个模块上电;

-- 复制代码 : 为了提高执行效率, 将 NOR Flash 中的代码复制到内存中;

-- PC指针 : PC 指针指向 NOR Flash 零地址, 开始执行启动代码;

-- 地址映射 : 启动代码执行后, 会将启动代码所在的 零地址 映射到 内存 RAM 空间;

-- RAM执行 : PC 指针指向 RAM 中映射的地址, 开始执行启动代码;

(5) NAND Flash 启动过程

注意 : 这种情况是将 Bootloader 烧写入 NAND Flash 中启动代码执行流程;

NAND Flash 启动过程 :

-- 搬运代码到内部 RAM : CPU 上电复位之后, DMA 将 NAND Flash 中的 Bootloader 启动代码搬运到 CPU 内部的 RAM 中, 设置 PC 到 RAM 代码地址, 开始执行 Bootloader;

-- 设置配置 向量 : Bootloader 会执行 设置中断向量, 设置硬件配置 操作;

-- 搬运代码到外部 RAM : 计算出 Bootloader 所占大小, 预留出 Bootloader 空间大小, 将执行代码搬运到 SDRAM 或 DD-RAM 外部 RAM 中;

-- 搬运 Bootloader : 将 Bootloader 代码搬运到 SDRAM 或 DDR-RAM 中的首地址;

-- 地址映射 : 设置 Remap, 映射 0 地址到 SDRAM 或者 DDR-RAM 首地址;

-- 执行Bootloader : 设置 PC 指针到 零地址, 执行 Bootloader;

(6) Bootloader 烧录工艺

MASK 烧录 : 早期的 ROM PROM 通过 MASK 植入启动代码;

烧录器 : EPROM EEPROM 通过烧录器烧入启动代码, 之后贴片焊接;

JTAG 调试器 : NOR FlashNAND Flash 通过 JTAG 调试器连接 CPU 的 JTAG 调试接口PC 机, 将编译好的 Bootloader 烧入 NOR Flash 和 NAND Flash 指定地址;

CPU 内置 ROM :

-- 固化代码 : CPU 再内置的 ROM 中固化一段代码, 这段代码不是 Bootloader;

-- 代码作用 : 这段代码启动后可以与 PC 连接, 直接使用网络接口 或 USB 接口便可以连接 PC, 不再依赖 JTAG 调试器烧录, 速度和效率也提高了;

2. Bootloader 引导程序简介

(1) Bootloader 作用

Bootloader 作用 : 初始化硬件设备, 建立内存空间映射图, 为内核启动准备好软件, 硬件环境;

-- 类似 BIOS : Bootloader 本质与 PC 上的 BIOS 相同, 都是为 操作系统 初始化 软件, 硬件环境;

(2) Bootloader 加密

加密简介 :

-- 加锁原因 : 手机厂商为了实现 系统价值, 稳定运行, 用户信息安全 等功能, 会对 Bootloader 进行加锁;

-- 加锁局限 : Bootloader 加锁后只能引导指定手机厂商的 硬件, 内核, 和操作系统, 不能识别其他厂商硬件;

-- 解锁隐患 : Bootloader 一旦解锁, 对用户来说 : 存在潜在的稳定性 与 系统安全问题; 对厂商来说 : 手机可以随意刷写 沦为硬件平台;

3. Linux 内核

(1) Linux 内核镜像

Linux 内核镜像 : Linux 内核有两种镜像 Image 和 zImage;

-- Image (非压缩内核) : 没有经过压缩的内核镜像, 占用空间大, 执行速度快;

-- zImage (压缩内核) : Image 经过压缩后的内核镜像, 占用空间小, 但是执行的时候需要解压缩, 执行效率慢;

-- 嵌入式选择 : 嵌入式系统中空间比较小, 通常采用 zImage 压缩镜像, 牺牲一点执行效率换取较少的存储空间;

(2) 内核启动流程

Kernel 启动流程 : 内核初始化 -> 设备驱动初始化 -> 内核启动 -> 挂载文件系统 -> 启动用户空间进程;

(3) 内核初始化

内核初始化 : 主要对硬件进行配置;

-- 向量表 : 创建异常向量表 和 初始化中断处理函数;

-- 进程调度器 : 初始化系统核心进程调度器时钟中断处理机制;

-- 串口 : 初始化串口控制台;

-- 缓存 : 创建和初始化系统, 为内存调用提供缓存;

-- 内存管理 : 初始化内存管理, 检测内存大小及碑内核占用的内存情况;

-- 进程通信 : 初始化系统进程通信机制;

(4) 设备初始化

设备初始化 : 加载设备驱动, 主要有 静态加载 和 动态加载两种方式;

-- 静态加载 : 将驱动模块加载到内核中, 设备驱动会在内核启动的时候自动加载, 这种驱动是无法卸载的;

-- 动态加载 : 在系统中使用 modprobe 或者 insmod 进行设备驱动模块的加载, 使用 rmmod 进行设备驱动模块卸载;

(5) 挂载文件系统

挂载文件系统 :

-- 创建并挂载根设备 : kernel 初始化 和 设备初始化之后会创建 根设备, 根设备文件系统以只读方式挂载;

-- 释放内存到根设备 : 根设备创建成功之后, 根设备是只读的, 这时释放未使用的内存到 根设备上;

(6) 启动 init 程序

启动应用程序 : 根文件挂载成功后, 启动 /sbin/init 程序, 这是 linux 系统第一个应用程序, 启动成功后 init 进程会获得 linux 系统的控制权;

-- 硬件初始化 : 初始化 Android 设备硬件;

-- 挂载根文件 : 根据命令行参数挂载根文件系统;

-- 跑启动脚本 : 执行用户自定义的 init 启动脚本;

4. init 初始化系统服务

(1) init 初始化系统服务

Linux 中 init 进程简介 :

-- 系统父进程 : init 进程是 Linux 系统所有进程的 父进程, id 为 1;

-- init 进程作用 : 初始化 和 启动 系统, 创建其它进程 如 shell login 等进程;

Android 中 init 进程简介 :

-- 系统父进程 : init 在 Android 中也是第一个进程, id 为 1;

-- 创建其它进程 : 创建 zygote 进程, 该进程可以提供 属性服务 用于管理系统属性;

(2) init 完成操作

init 操作 : 系统初始化操作, 解析 init.rc 配置文件等操作;

-- 初始化 : 初始化 log 系统;

-- 解析配置 : 解析 init.rc 配置文件 和 /init.硬件平台名称.rc 配置文件, 执行 early-init, 解析 init 动作, eartly-boot 动作, boot 动作, Execute property 动作;

-- 初始化2 : 设备初始化, 属性服务初始化, 开启属性服务;

-- 无限循环 : 进入无限循环状态, 等待属性设置 或 子进程退出事件;

(3) init.rc 配置文件解析

init.rc 组成 : 该配置文件由 命令类, 动作类, 服务类, 选项类 声明组成;

-- 对应语法 : 命令, 动作, 触发条件, 服务, 选项属性;

命令示例 : init.rc 中的命令在 init 程序中解析, 之后调用相关函数实现;

[plain] view plaincopy

  1. # Create cgroup mount point for memory
  2. mount tmpfs none /sys/fs/cgroup mode=0750,uid=0,gid=1000
  3. mkdir /sys/fs/cgroup/memory 0750 root system
  4. mount cgroup none /sys/fs/cgroup/memory memory
  5. write /sys/fs/cgroup/memory/memory.move_charge_at_immigrate 1
  6. chown root system /sys/fs/cgroup/memory/tasks
  7. chmod 0660 /sys/fs/cgroup/memory/tasks
  8. mkdir /sys/fs/cgroup/memory/sw 0750 root system
  9. write /sys/fs/cgroup/memory/sw/memory.swappiness 100
  10. write /sys/fs/cgroup/memory/sw/memory.move_charge_at_immigrate 1
  11. chown root system /sys/fs/cgroup/memory/sw/tasks
  12. chmod 0660 /sys/fs/cgroup/memory/sw/tasks

动作 触发条件 示例 :

[plain] view plaincopy

  1. on nonencrypted
  2. class_start late_start
  3. on charger
  4. class_start charger
  5. on property:vold.decrypt=trigger_reset_main
  6. class_reset main

服务 选项 示例 : 服务表示启动一个可执行程序, 服务一般都附加 选项, 用于配合服务使用

[plain] view plaincopy

  1. service zygote /system/bin/app_process -Xzygote /system/bin --zygote --start-system-server
  2. class main
  3. socket zygote stream 660 root system
  4. onrestart write /sys/android_power/request_state wake
  5. onrestart write /sys/power/state on
  6. onrestart restart media
  7. onrestart restart netd

-- 示例解析
: 启动 zygote 服务, 通过 /system/bin/app_process 启动, "--start-system-server"
表示启动的同时启动该服务, "socket zygote stream 660 root system" 表示启动后建立 zygote 通信
socket, "onrestart " 表示 zygote 服务重启时需要执行的命令;

属性 示例 : 系统中设置的属性值, 可设置 或者 读写;

[plain] view plaincopy

  1. # Define TCP buffer sizes for various networks
  2. #   ReadMin, ReadInitial, ReadMax, WriteMin, WriteInitial, WriteMax,
  3. setprop net.tcp.buffersize.default 4096,87380,110208,4096,16384,110208
  4. setprop net.tcp.buffersize.wifi    524288,1048576,2097152,262144,524288,1048576
  5. setprop net.tcp.buffersize.lte     524288,1048576,2097152,262144,524288,1048576
  6. setprop net.tcp.buffersize.umts    4094,87380,110208,4096,16384,110208
  7. setprop net.tcp.buffersize.hspa    4094,87380,262144,4096,16384,262144

-- 示例解析 : "setprop" 用于设置属性;

二. Android 上层系统启动流程

1. Android 上层系统启动简介

启动流程 : init 进程启动 -> 启动 Android 系统本地服务(Native Service) -> Zygote进程 -> Android 系统服务(System Service) -> HomeActivity 启动;

2. 启动 Native Service (本地服务)

Native Service 简介 :

-- 启动进程 : 由 init 启动, 是 C/C++ 实现的;

-- 主要作用 : 本地服务 是 Android 内核Android 应用 通信 的通道, 两层之间通过 socket 进行通信;

Native Service 提供的服务 : 其启动项定义在 init.rc 中;

-- Console : shell console 服务;

-- Service Manager : Binder 服务管理器, 管理所有的 Android 系统服务;

-- Vold : 支持外设热插拔服务;

-- Mountd : 设备安装 状态通知服务;

-- Debuggerd : 处理调试进程请求服务;

-- Rild : 无线接口层服务;

-- Zygote : 启动 Dalvik 并创建其它进程服务;

-- MediaServer : 多媒体相关服务;

3. Zygote 进程启动

Zygote 进程简介 : Zygote 由 init 进程创建, init.rc 中配置了 Zygote 的创建参数;

-- init.rc 中配置 : Zygote 原始名称是 "app_process", 启动中改名为 Zygote;

[plain] view plaincopy

  1. service zygote /system/bin/app_process -Xzygote /system/bin --zygote --start-system-server

Zygote 作用 :

-- 本质 : Zygote 进程是一个虚拟的进程, 是虚拟实例(Dalvik虚拟机)的孵化器;

-- 操作 : Zygote 负责 Dalvik 虚拟机初始化, 预置类库加载等操作;

-- 应用启动处理 : 每个 Android 应用启动时, Zygote 会创建一个子进程(Dalvik虚拟机)执行它;

-- 节省内存策略 : Android 中有些系统库是只读的, 所有的 Dalvik 虚拟机都可以共享这些只读系统库;

4. Android System Service 启动

Android 系统服务 :

-- 启动 : Android System Service 是 Zygote 进程第一个子进程, 由 Zygote 进程孵化而来;

-- 作用 : System Service 是 Android 框架核心, 负责 Android 系统初始化 启动其它服务;

-- 其它服务 : System Service 孵化的其它服务运行在对应 Dalvik 虚拟机进程的空间里;

-- init.rc 配置 : 在 Zygote 配置中 "--start-system-server" 参数用来实现 System Service 的启动;

5. 启动 HomeActivity 主界面

Launcher 应用程序 : 该应用程序就是 HomeActivity 所在的程序;

-- 启动 : Launcher 由 Activity Manager Service 启动, 启动流程 System Service -> Activity Manager Service -> Launcher;

-- 展示图标 : Launcher 启动后就会将已经安装的 app 程序的快捷图标展示到桌面;

时间: 2024-12-24 10:20:08

【Android 系统开发】 Android 系统启动流程简介的相关文章

【Android 系统开发】CyanogenMod 13.0 源码下载 编译 ROM 制作 ( 手机平台 : 小米4 | 编译平台 : Ubuntu 14.04 LTS 虚拟机)

作者 : 韩曙亮 转载请注明出处 : http://blog.csdn.net/shulianghan/article/details/51592930 手机的两种模式 : 在下面有详细的图片示例; -- Recovery 模式 : 音量键增加 + 电源键, 长按上述组合键, 看到 "MI" 的 LOGO 后即进入 Recovery 模式; -- Fastboot 模式 : 音量键减小 + 电源键, 长按上述组合键, 看到 "FASTBOOT" 后, 即 进入 FA

上门洗车APP --- Android客户端开发 前言及业务简介

上门洗车APP --- Android客户端开发 前言及业务简介 最近有些小累,私自接了一个项目,利用空余时间在开发,也比较乏力,时间和精力上有时候分配不过来,毕竟公司的事情要忙,只能自己抽时间来完成了,男人嘛,累点好,舒服是留给死人的(套用了一句逼格的话,o_O"~). 项目目前还在开发中,接口的调试以及业务的分析,框架的搭建,客户端这边已进行的差不多了,明天端午节,先祝大家节日快乐,汗~,看了下时间,貌似博客写完发表已经是端午节了,好吧,咕嘟咕嘟...... 大晚上的也是睡不着,写写博客,总

Android系统开发实务实训

实训项目 :               Android系统开发实务实训                                            项目源码获取:   <绝地坦克>是一款坦克大战类型的javascript网络游戏,本游戏项目运行说明可分为三个方向:说明运行的项目是什么.如何运行,以及运行该项目的结果和意义是什么?其中运行的是什么包括:项目说明与功能分析:如何运行主要是指,该项目程序的实现原理和运行方式.具体说明如下: 一.项目说明与功能分析 首先从逻辑上而言,本项目

Android系统开发(2)——GDB调试工具

调试的过程 我们在eclipse中来看一下一般调试的过程: 1.debug模式编译 2.打上断点 3.运行调试 4.单步调试 step into:跳到函数体内部 step over:不跳到函数体内 step return:运行完当前函数 5.继续运行 continue 6.打印和监控值 GDB调试 先写一段C++的代码,代码内容如下: 使用debug模式编译: 进入Debug调试模式: 1.打断点,打断点的方式如下(GDB中的命令可以使用首字母来替代,比如break和b的作用相同) break 

(2) 搭建 Android 系统开发环境

说干就干,先按 Google 官方的指导,搭建 Android 系统开发环境.页面(需FQ):http://source.android.com/source/initializing.html 安装 ubuntu-14.04 64bit 安装系统有两种方式可选,直接装在物理机上或装在虚拟机中,区别主要就是性能了,本次是安装在虚拟机中的.之前都是装在物理机上的,但是只有一台电脑,而做开发的时候往往还要做些笔记或者其它的事情.总之,在 ubuntu 中完成这些工作并不容易,以前折腾过,也怕了.另外

Android系统开发(1)——GCC编译器的编译和安装过程

GCC编译器介绍 GCC编译器(GNG C Compiler)是GNU项目中符合ANSI C标准的编译系统,能够编译C  C++  Object C等语言编写的程序,同时GCC也是一个交叉编译器,特别使用于不同平台的嵌入式开发. GNU: GNU是"GNU is Not Unix"的递归缩写,1984年,史托曼开始GNU项目,这个项目的目的是创建一个自由,开放的Unix操作系统(Free UNIX),刚开始史托曼参考UNIX上面的软件,开发出功能类似的软件,在开发期间并没有看其他软件的

mac 系统开发android,真机调试解决方式(无数的坑之后吐血总结)

近期学习android开发,安装了ADT开发环境之后,启动模拟器,慢的要死啊,全然不如苹果的好用,没法,自己买个android手机,准备联机调试程序.没想到在这个过程中,遇到了好多的坑,作为一个新人,每一步都过不去,花了将近2个小时,在万能的百度里查了n多次,最终攻克了.在此,做个记录,希望大家不要走我走过的弯路. 1.确保你的android设备真正链接到电脑上了,我在这里遇到过坑,弄了好久,才发现能充电的线,确无法传递数据过去.所以不要以为随便拿一根线,能充电,就能够传递数据了,我就是这么傻傻

《Android系统开发》笔记

<Android系统开发>笔记1:Android系统概述 Android四层架构: 1. Linux Kernel&driver层 a.依赖于Linux 2.6内核,包含安全性.内存管理.进程管理,网络协议栈.驱动模型等b.Android自己加入的驱动,Binder IPC驱动,显示驱动,输入设备驱动.音频系统驱动,摄像头驱动,Wifi驱动.蓝牙驱动,电源管理等 2. Android本地库 & Java执行环境层 Android本地库(C/C++)Bionic:为嵌入式设备定制

Android菜鸟如何学习Android系统开发?

如何做好Android学习前的准备? 如果你已经确定了学习Android的目标,那么,应该提前做好哪些工作.先打下哪些基础呢? 首先,你最好先熟悉一门编程语言,现在大学里面和计算机相关的专业甚至理工类专业一般都会开设C语言课程,只是很多同学在大学期间并没有好好学习,如果对它掌握的不太好或者很久没用了,建议先从将其好好复习一下,将其基本的语法再好好回顾一下,最好能搭建一个环境来运行.调试它.如果没有学过,不妨也提前学习一下,可以参考清华大学出版社出版的谭浩强老师的<C语言程序设计>,推荐这本书的

Android系统开发的学习教程在哪里可以看?

Android蛰伏很多年,终于赶上移动互联时代,迅猛崛起,以80%以上的占比成为行业占有率首位,Android程序员也成为移动互联发展必不可少的推动者,移动互联网行业的发展人才是非常重要的,很多开发者都纷纷转型到Android,这些传统的开发者想要从事移动互联网行业的开发,需要参加培训,参加Android培训来提升自身的技术实力,传智播客Android培训行业的领导者,为各大企业很多企业输送了大量的Android人才,来提升人才的战略. 目前Android系统占据了移动互联网行业的主体,很多用户