文章目录
前言
在Framework中开发中,不可避免的都会遇到客户在问,为啥开机这么慢要等待那么久,必须要优化到xx秒中才行。遇到那种选的芯片比较低端,要求又特别高的客户,心理一顿mmp,但是没办法,活还得干,日子还得过。今天这边文章就是总结一些优化开机启动的方案给各位为同仁一个参考。
可优化阶段划分
Android 系统启动优化通常可以分为七个部分,每个部分都有对应优化方法。接下来,对每个阶段的方法进行简单的总结与介绍。(硬件不在研究范围内)
- Bootloader
- Kernel
- Init.rc
- Zygote
- SystemServer
- Launcher
- Application
一、Bootloader 阶段优化
Bootloader是系统启动最初的阶段,主要负责初始化硬件加载内核。
- 延迟初始发非必要的外设(传感器、摄像头),缩短Bootloader的执行链。
- 关闭调试接口,停用UART日志输出(修改Kernel Config的CONFIG_DEBUG_*)。
- 压缩算法升级Gzip升级为LZ4.。
- 简化AVB校验流程,或者采用硬件加速签名验证。
- 采用fastboot、快速启动。
二、Kernel 阶段优化
Kernel启动主要初始化软硬环境,加载驱动程序,挂载根文件系统等操作。主要优化手段有以下方案。
- 精简内核配置(只编译必要模块)。
- 移除不要的日志如(printk)。
- 异步初始化驱动(initcall 异步)。
- 移除 CONFIG_CC_OPTIMIZE_FOR_SIZE。
三、Init.rc阶段
init.rc是内核到安卓框架建立之前的衔接过程,初始化系统守护进程和服务。
- 精简脚本中的启动服务(按需裁剪)。
- 使用class_start_late_start分阶段启动服务。
- 合理配置import和on boot触发条件,避免不要的early启动。
- 延迟或按需启动关键服务(logd、usb等)。
四、Zygote阶段
创建应用进程模板(fork进程)
- 精简zygote preload的类和资源加载(preloadClasses、preloadResources)
(frameworks/base/preload-classe、frameworks/base/core/res/res/values/arrays.xml) - 使用lazyPreload技术延迟非关键资源加载。
- 推迟非关键初始化(ZRAM)。
- zygote-start早期阶段启动zygote。
五、SystemServer阶段
启动Android核心服务(AMS、WMS、PMS等)
- 延迟不必要的系统服务(搜索、PrintManager)。
- 使用线程池并发启动服务。
- 拆分AMS、WMS初始化过程,使用异步完成部分逻辑。
- 精简不必要的服务。
六、Launcher
- 减少冷启动逻辑、布局优化
- SplashScreen提前展示UI
- 提前预加载常用应用
- 利用binder idle handel 、idle handler 延后非必要任务。
七、Application
不同应用结合实际场景来进行各自优化。
优化措施
裁剪预制APK、Features、Sensors等
- 裁剪APK
注意device/rockchip/common/apps.mk根据不同厂商有不同的名称。
# build/target/product/generic_no_telephony.mk
PRODUCT_PACKAGES := \
BasicDreams \
Bluetooth \
# Telephony # 注释或删除电话相关模块[1]()
# device/rockchip/common/apps.mk
ROCKCHIP_APPS := \
VideoPlayer \
# Gallery2 # 移除默认图库[3]()
- 裁剪Features
diff --git /frameworks/native/data/etc/android.software.print.xml /frameworks/native/data/etc/android.software.print.xml
index 713a7f7..e76bb88 100644
--- /frameworks/native/data/etc/android.software.print.xml
+++ /frameworks/native/data/etc/android.software.print.xml
@@ -15,5 +15,5 @@
-->
<permissions>
- <feature name="android.software.print" />
+<!-- <feature name="android.software.print" />-->
</permissions>
- 裁剪Sensors
根据实际需求,按需裁剪。
#查看设备中的sensor
adb shell dumpsys sensorservice
配置优化
- 关闭锁屏显示通知
<!-- Default for Settings.Secure.LOCK_SCREEN_SHOW_NOTIFICATIONS, 1==on -->
- <integer name="def_lock_screen_show_notifications">1</integer>
+ <integer name="def_lock_screen_show_notifications">0</integer>
- 关闭手势唤醒
<!-- Default for Settings.Secure.WAKE_GESTURE_ENABLED -->
- <bool name="def_wake_gesture_enabled">true</bool>
+ <bool name="def_wake_gesture_enabled">false</bool>
- 关闭双击唤醒
<!-- Default state of tap to wake -->
- <bool name="def_double_tap_to_wake">true</bool>
+ <bool name="def_double_tap_to_wake">false</bool>
- 关闭自动旋转
<bool name="def_accelerometer_rotation">false</bool>
- 关闭Wifi Debugging
<!-- Disable WiFi Debugging -->
<bool translatable="false" name="config_wifi_enable_wifi_firmware_debugging">false</bool>
- 关闭壁纸服务
frameworks/base/core/res/res/values/config.xml
<!-- True if WallpaperService is enabled -->
<bool name="config_enableWallpaperService">true</bool>
- 调整窗口动画渲染
frameworks/base/packages/SettingsProvider/res/values/defaults.xml
- <fraction name="def_window_animation_scale">100%</fraction>
- <fraction name="def_window_transition_scale">100%</fraction>
+ <fraction name="def_window_animation_scale">25%</fraction>
+ <fraction name="def_window_transition_scale">25%</fraction>
删除开机动画
frameworks/base/cmds/bootanimation/BootAnimationUtil.cpp
bool bootAnimationDisabled() {
char value[PROPERTY_VALUE_MAX];
//将获取结果改为1,则无法进入到开机动画流程中
//property_get("debug.sf.nobootanimation", value, "0");
property_get("debug.sf.nobootanimation", value, "1");
if (atoi(value) > 0) {
return true;
}
property_get("ro.boot.quiescent", value, "0");
if (atoi(value) > 0) {
// Only show the bootanimation for quiescent boots if this system property is set to enabled
if (!property_get_bool("ro.bootanim.quiescent.enabled", false)) {
return true;
}
}
return false;
}
CPU调度策略
为关键服务(如zygote、servicemanager)绑定独立CPU核心
write /dev/cpuset/system-background/cpus 0-3 # 指定核心范围
修改内核电源管理模块(如cpufreq),在启动阶段锁定最高频
echo performance > /sys/devices/system/cpu/cpu*/cpufreq/scaling_governor
启用CPU缓存预取
echo 1 > /sys/module/rcupdate/parameters/rcu_cpu_stall_suppress
关闭非必要外设
echo disable > /sys/bus/usb/devices/usb1/power/wakeup
禁用FallbackHome机制
取消设置FallbackHomeComponent
frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
// 原始代码:
if (r == null) {
r = startHomeActivityLocked(currentUserId, "noHomeTask", false, false);
if (r == null) {
r = mStackSupervisor.startFallbackActivity(currentUserId);
}
}
// 改为只尝试启动默认 Launcher,不启动 FallbackActivity:
if (r == null) {
r = startHomeActivityLocked(currentUserId, "noHomeTask", false, false);
// 不再 fallback 到 FallbackActivity
}
屏蔽packageManager中的FallbackActivity
frameworks/base/core/res/AndroidManifest.xml
<activity android:name="com.android.internal.app.FallbackActivity"
android:theme="@android:style/Theme.Holo"
android:excludeFromRecents="true"
android:enabled="true"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.HOME" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
裁剪SystemService
部分服务参考
1.VibratorService 震动器服务
2.ClipboardService 粘贴板服务
3.FingerprintService 指纹
4.BatteryService 电池服务,当电量不足时发广播
5.AlarmManagerService 闹钟服务
6.WallpaperManagerService 壁纸管理服务
7.StatusBarManagerService 状态栏管理服务
裁剪位置
frameworks/base/services/java/com/android/server/SystemServer.java
// Start services.
try {
t.traceBegin("StartServices");
startBootstrapServices(t);
startCoreServices(t);
startOtherServices(t);
startApexServices(t);
} catch (Throwable ex) {
Slog.e("System", "******************************************");
Slog.e("System", "************ Failure starting system services", ex);
throw ex;
} finally {
t.traceEnd(); // StartServices
}
PMS优化
APK扫描安装时耗一般最为耗时,这里修改通常采用多线程方案。
frameworks/base/services/core/java/com/android/server/pm/ParallelPackageParser.java
class ParallelPackageParser {
private static final int QUEUE_CAPACITY = 30;
// private static final int MAX_THREADS = 4;
private static final int MAX_THREADS = 8;
//省略部分代码
}
针对性优化
在项目中,增加了自定义开机启动项,可以通过抓取trace借助perfetto分析耗时选项。