深入Framework层剖析Android系统启动流程
本文从Framework层对 Init进程启动,Zygote进程,SystemServer进程,Launcher进程四部分对安卓系统系统启动流程的完整源码分析。篇幅较长,请耐心阅读!
后续文章逐渐深入Framework层,剖析源码,关注小编,学习不迷路!
简介
当Android手机从按下开机键时,屏幕点亮,到Launcher系统桌面的显示,整个过程系统是怎么启动的?下面我们一起深入源码来看一下。整体流程如下图所示。
源码分析
init进程启动
1.BootROM
当按下电源开关键时,引导芯片程序会从预定义的地方开始执行,加载系统引导程序BootLoader到RAM,启动执行。
2.BootLoader
初始化系统硬件资源,引导操作系统启动。
3.idel进程
初始化进程管理,内存管理,加载Binder驱动,Display,Camera 驱动等相关工作。
4. init进程启动
Main.main()
Android系统启动时 通过Android.bp启动Main.cpp的main函数。
int main(int argc, char** argv) {
#if __has_feature(address_sanitizer)
__asan_set_error_report_callback(AsanReportCallback);
#endif
// 设置进程优先级
setpriority(PRIO_PROCESS, 0, -20);
if (!strcmp(basename(argv[0]), "ueventd")) {
return ueventd_main(argc, argv);
}
if (argc > 1) {
//根据不同的参数 执行不同的函数。
if (!strcmp(argv[1], "subcontext")) {
android::base::InitLogging(argv, &android::base::KernelLogger);
const BuiltinFunctionMap& function_map = GetBuiltinFunctionMap();
return SubcontextMain(argc, argv, &function_map);
}
//第二次执行
if (!strcmp(argv[1], "selinux_setup")) {
return SetupSelinux(argv);
}
//最后执行到 SecondStageMain
if (!strcmp(argv[1], "second_stage")) {
return SecondStageMain(argc, argv);
}
}
//firstStageMain中再次调用main.cpp,参数传为selinux_setup,后续执行SetupSelinux
return FirstStageMain(argc, argv);
Init.SecondStageMain
Main.cpp的main方法被反复执行,最后执行到init.cp的SecondStageMain方法。
int SecondStageMain(int argc, char** argv) {
.............
//初始化属性服务
PropertyInit();
// Umount the debug ramdisk after property service has read the .prop files when it means to.
if (load_debug_prop) {
UmountDebugRamdisk();
}
// Mount extra filesystems required during second stage init
MountExtraFilesystems();
// 设置系统安全策略
SelinuxSetupKernelLogging();
SelabelInitialize();
SelinuxRestoreContext();
//定义epoll机制
Epoll epoll;
if (auto result = epoll.Open(); !result.ok()) {
PLOG(FATAL) << result.error();
}
//解析init.rc文件
LoadBootScripts(am, sm);
.......................
while (true) {
// 循环等待处理
auto epoll_timeout = std::optional<std::chrono::milliseconds>{};
auto shutdown_command = shutdown_state.CheckShutdown();
.........................
}
return 0;
}
} // namespace init
SecondStageMain方法中,init进程主要处理:
1)挂载文件,设置系统安全策略。
2)开启属性服务,注册到epoll中。
3)解析init.rc ,启动Zygote进程。
Zygote进程启动
当安卓系统启动后,会创建一个init进程,所以的进程都是这个init进程fork出来的,包括Zygote进程,当系统要求启动一个Android应用程序时,都会通过AMS通知Zygote进程创建一个子进程用来启动该应用程序。
1.App_main.cpp
Zygote进程启动时会执行app_main.cpp的main函数。
int main(int argc, char* const argv[])
{
.............
//初始化AppRuntime
AppRuntime runtime(argv[0], computeArgBlockSize(argc, argv));
argc--;
argv++;
...........................
//是否是zygote进程
bool zygote = false;
//是否启动systemServer进程
bool startSystemServer = false;
bool application = false;
//进程名称
String8 niceName;
String8 className;
++i;
while (i < argc) {
const char* arg = argv[i++];
//设置zygote启动
if (strcmp(arg, "--zygote") == 0) {
zygote = true;
niceName = ZYGOTE_NICE_NAME;
} else if (strcmp(arg, "--start-system-server") == 0) {
startSystemServer = true;
} else if (strcmp(arg, "--application") == 0) {
application = true;
} else if (strncmp(arg, "--nice-name=", 12) == 0) {
niceName.setTo(arg + 12);
} else if (strncmp(arg, "--", 2) != 0) {
className.setTo(arg);
break;
} else {
--i;
break;
}
}
.........................
if (!niceName.isEmpty()) {
runtime.setArgv0(niceName.string(), true /* setProcName */);
}
if (zygote) {
//如果是zygote进程 执行AppRuntime.start
runtime.start("com.android.internal.os.ZygoteInit", args, zygote);
} else if (className) {
runtime.start("com.android.internal.os.RuntimeInit", args, zygote);
} else {
fprintf(stderr, "Error: no class name or --zygote supplied.\n");
app_usage();
LOG_ALWAYS_FATAL("app_process: no class name or --zygote supplied.");
}
}
2.AndroidRuntime.cpp
AppRuntime继承于AndroidRuntime,执行AppRuntime的start方法就是执行AndroidRuntime中的start方法。className传入的是 "com.android.internal.os.ZygoteInit"。
void AndroidRuntime::start(const char* className, const Vector<String8>& options, bool zygote)
{
static const String8 startSystemServer("start-system-server");
//记录当前zygote是否是fork出SystemServer进程
bool primary_zygote = false;
JniInvocation jni_invocation;
jni_invocation.Init(NULL);
JNIEnv* env;
//启动虚拟机
if (startVm(&mJavaVM, &env, zygote, primary_zygote) != 0) {
return;
}
//如果没有虚拟机则创建新的虚拟机
onVmCreated(env);
/*
* 注册系统jni方法
*/
if (startReg(env) < 0) {
ALOGE("Unable to register all android natives\n");
return;
}
..................
/*
* 启动虚拟机线程,执行ZygoteInit的main方法
* className :com.android.internal.os.ZygoteInit
*/
char* slashClassName = toSlashClassName(className != NULL ? className : "");
jclass startClass = env->FindClass(slashClassName);
if (startClass == NULL) {
ALOGE("JavaVM unable to locate class '%s'\n", slashClassName);
/* keep going */
} else {
jmethodID startMeth = env->GetStaticMethodID(startClass, "main",
"([Ljava/lang/String;)V");
if (startMeth == NULL) {
ALOGE("JavaVM unable to find main() in '%s'\n", className);
/* keep going */
} else {
//执行jni方法 进入:com.android.internal.os.ZygoteInit的main方法
env->CallStaticVoidMethod(startClass, startMeth, strArray);
}
....................
}
3.ZygoteInit.java
AndroidRuntime.start方法中 通过jni调用java代码,执行com.android.internal.os.ZygoteInit的main方法。
public static void main(String argv[]) {
ZygoteServer zygoteServer = null;
//标记zygote进程启动
ZygoteHooks.startZygoteNoThreadCreation();
...............
Runnable caller;
try {
...................
boolean startSystemServer = false;
String zygoteSocketName = "zygote";
String abiList = null;
boolean enableLazyPreload = false;
for (int i = 1; i < argv.length; i++) {
if ("start-system-server".equals(argv[i])) {
startSystemServer = true;
} else if ("--enable-lazy-preload".equals(argv[i])) {
enableLazyPreload = true;
} else if (argv[i].startsWith(ABI_LIST_ARG)) {
abiList = argv[i].substring(ABI_LIST_ARG.length());
} else if (argv[i].startsWith(SOCKET_NAME_ARG)) {
zygoteSocketName = argv[i].substring(SOCKET_NAME_ARG.length());
} else {
throw new RuntimeException("Unknown command line argument: " + argv[i]);
}
}
if (!enableLazyPreload) {
bootTimingsTraceLog.traceBegin("ZygotePreload");
//预加载资源
preload(bootTimingsTraceLog);
}
//创建zygote服务
zygoteServer = new ZygoteServer(isPrimaryZygote);
//通过zygote进程fork出SystemServer进程
if (startSystemServer) {
Runnable r = forkSystemServer(abiList, zygoteSocketName, zygoteServer);
if (r != null) {
//执行SystemServer的main方法
r.run();
return;
}
}
//开启循环
caller = zygoteServer.runSelectLoop(abiList);
} catch (Throwable ex) {
} finally {
if (zygoteServer != null) {
zygoteServer.closeServerSocket();
}
}
}
ZygoteInit的main方法主要的作用是:
1).预加载系统资源。
2).创建zygote的socket服务。
3).通过Zygote进程fork出SystemServer进程。
4).执行SystemServer的main方法,启动进程。
5).zygote进入循环等待状态,接收AMS传递的消息。
Zygote作为进程孵化器,当需要启动一个程序时,首先会通过AMS使用Socket发送消息到Zygote进程,Zygote通过fork函数创建需要启动的程序进程。
SystemServer进程启动
ZygoteInit通过forkSystemServer创建出SystemServer进程,然后调用SystemServer的run方法进行执行。SystemServer的main方法。
//通过zygote进程fork出SystemServer进程
if (startSystemServer) {
Runnable r = forkSystemServer(abiList, zygoteSocketName, zygoteServer);
if (r != null) {
//执行SystemServer的main方法
r.run();
return;
}
}
1.SystemServer.java
/**
* 从Zygote进程进入SystemServer进程.
*/
public static void main(String[] args) {
new SystemServer().run();
}
private void run() {
TimingsTraceAndSlog t = new TimingsTraceAndSlog();
try {
............省略部分代码..............
//创建当前线程的Looper
Looper.prepareMainLooper();
Looper.getMainLooper().setSlowLogThresholdMs(
SLOW_DISPATCH_THRESHOLD_MS, SLOW_DELIVERY_THRESHOLD_MS);
SystemServiceRegistry.sEnableServiceNotFoundWtf = true;
//初始化android_servers静态库
System.loadLibrary("android_servers");
..................
// 创建系统context.
createSystemContext();
// 初始化主线程模块
ActivityThread.initializeMainlineModules();
// 创建系统服务管理对象-SystemServiceManager
mSystemServiceManager = new SystemServiceManager(mSystemContext);
mSystemServiceManager.setStartInfo(mRuntimeRestart,
mRuntimeStartElapsedTime, mRuntimeStartUptime);
LocalServices.addService(SystemServiceManager.class, mSystemServiceManager);
// 启动线程池
SystemServerInitThreadPool.start();
...........................
try {
t.traceBegin("StartServices");
startBootstrapServices(t); //启动程序引导服务
startCoreServices(t); //启动核心服务
startOtherServices(t);//启动其他服务
} catch (Throwable ex) {
} finally {
t.traceEnd(); // StartServices
}
................
// 主线程循环等待消息处理.
Looper.loop();
throw new RuntimeException("Main thread loop unexpectedly exited");
进入SystemServer进程,SystemServer中主要处理以下工作:
1)创建当前线程的Looper。
2) 初始化android_servers静态库。
3)创建系统context。
4)初始化主线程模块。
5)创建系统服务管理对象-SystemServiceManager。
6) 启动线程池。
7) 启动程序引导服务。
8) 启动核心服务。
9) 启动其他服务。
10) 主线程循环等待消息处理。
Launcher启动流程
Launcher作为android系统启动流程的最后一步。它是android系统的桌面程序,在android系统中具有重要作用。用来显示系统已经安装的应用程序。
作用如下:
- Launcher作为android系统的启动程序,用于系统程序的启动。
- Launcher作为android系统的桌面程序,用于管理和显示已安装的应用程序图标及桌面其他组件。
启动流程分析
1.SystemServer.startOtherServices
SystemServer的main方法中startOtherServices()启动了其他服务,startOtherServices()中就包括了应用程序Launcher的启动。
private void startOtherServices(@NonNull TimingsTraceAndSlog t) {
..............................
//通过AMS开始启动初始应用程序Launcher
mActivityManagerService.systemReady(() -> {
Slog.i(TAG, "Making services ready");
t.traceBegin("StartActivityManagerReadyPhase");
mSystemServiceManager.startBootPhase(t, SystemService.PHASE_ACTIVITY_MANAGER_READY);
t.traceEnd();
t.traceBegin("StartObservingNativeCrashes");
try {
mActivityManagerService.startObservingNativeCrashes();
} catch (Throwable e) {
reportWtf("observing native crashes", e);
}
t.traceEnd();
..................
}
2.ActivityManagerService.systemReady
在ActivityManagerService中调用systemReady进行系统准备启动工作。
public void systemReady(final Runnable goingCallback, @NonNull TimingsTraceAndSlog t) {
t.traceBegin("PhaseActivityManagerReady");
mSystemServiceManager.preSystemReady();
.....................
t.traceBegin("resumeTopActivities");
mAtmInternal.resumeTopActivities(false /* scheduleIdle */);
t.traceEnd();
.....................
}
systemReady中调用了ActivityTaskManagerService的resumeTopActivities方法,接着看这个resumeTopActivities方法做了哪些工作。
3.ActivityTaskManagerService.resumeTopActivities
@Override
public void resumeTopActivities(boolean scheduleIdle) {
synchronized (mGlobalLock) {
//进入RootWindowContainer
mRootWindowContainer.resumeFocusedStacksTopActivities();
if (scheduleIdle) {
mStackSupervisor.scheduleIdle();
}
}
}
在ActivityTaskManagerService中调用RootWindowContainer的resumeFocusedStacksTopActivities方法。
4.RootWindowContainer.resumeFocusedStacksTopActivities
//第一次进入
boolean resumeFocusedStacksTopActivities() {
return resumeFocusedStacksTopActivities(null, null, null);
}
//入参都为null
boolean resumeFocusedStacksTopActivities(
ActivityStack targetStack, ActivityRecord target, ActivityOptions targetOptions) {
if (!mStackSupervisor.readyToResume()) {
return false;
}
.........................
if (!resumedOnDisplay) {
final ActivityStack focusedStack = display.getFocusedStack();
if (focusedStack != null) {
result |= focusedStack.resumeTopActivityUncheckedLocked(target, targetOptions);
}
//首次启动Launcher,入参为null
else if (targetStack == null) {
//启动homeActivity
result |= resumeHomeActivity(null /* prev */, "no-focusable-task",
display.getDefaultTaskDisplayArea());
}
}
return result;
}
系统首次启动时,调用resumeFocusedStacksTopActivities传入的参数都为nul,然后通过if判断targetStack==null为true,调用resumeHomeActivity方法进行homeActivity启动。
5.RootWindowContainer.resumeHomeActivity
boolean resumeHomeActivity(ActivityRecord prev, String reason,
TaskDisplayArea taskDisplayArea) {
//服务是否已经启动
if (!mService.isBooting() && !mService.isBooted()) {
return false;
}
.....
//从任务栈中获取HomeActivity
final ActivityRecord r = taskDisplayArea.getHomeActivity();
final String myReason = reason + " resumeHomeActivity";
// 已经启动过了
if (r != null && !r.finishing) {
r.moveFocusableActivityToTop(myReason);
return resumeFocusedStacksTopActivities(r.getRootTask(), prev, null);
}
//首次启动
return startHomeOnTaskDisplayArea(mCurrentUser, myReason, taskDisplayArea,
false /* allowInstrumenting */, false /* fromHomeKey */);
}
在resumeHomeActivity方法中,判断服务是已经初始化完成,通过ActivityRecord任务栈获取HomeActivty,如果已经启动过则直接从任务栈中恢复,否则启动新的HomeActivity,这里系统是首次启动,进入startHomeOnTaskDisplayArea执行。
6.RootWindowContainer.startHomeOnTaskDisplayArea
boolean startHomeOnTaskDisplayArea(int userId, String reason, TaskDisplayArea taskDisplayArea,
boolean allowInstrumenting, boolean fromHomeKey) {
// 创建显示区域
if (taskDisplayArea == null) {
final ActivityStack stack = getTopDisplayFocusedStack();
taskDisplayArea = stack != null ? stack.getDisplayArea()
: getDefaultTaskDisplayArea();
}
Intent homeIntent = null;
ActivityInfo aInfo = null;
if (taskDisplayArea == getDefaultTaskDisplayArea()) {
//创建Intent
homeIntent = mService.getHomeIntent();
aInfo = resolveHomeActivity(userId, homeIntent);
} else if (shouldPlaceSecondaryHomeOnDisplayArea(taskDisplayArea)) {
Pair<ActivityInfo, Intent> info = resolveSecondaryHomeActivity(userId, taskDisplayArea);
aInfo = info.first;
homeIntent = info.second;
}
//更新Intent启动信息
homeIntent.setComponent(new ComponentName(aInfo.applicationInfo.packageName, aInfo.name));
homeIntent.setFlags(homeIntent.getFlags() | FLAG_ACTIVITY_NEW_TASK);
//启动HomeActivity
mService.getActivityStartController().startHomeActivity(homeIntent, aInfo, myReason,
taskDisplayArea);
return true;
}
//创建Intent
Intent getHomeIntent() {
Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null);
intent.setComponent(mTopComponent);
intent.addFlags(Intent.FLAG_DEBUG_TRIAGED_MISSING);
if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) {
intent.addCategory(Intent.CATEGORY_HOME);
}
return intent;
}
homeIntent.setComponent()设置需要启动的包名和HomeActivity信息homeIntent.setFlags(homeIntent.getFlags() | FLAG_ACTIVITY_NEW_TASK),分配新的任务栈。在getHomeIntent()中创建Intent,并将mTopAction和mTopdata作为参数传入Intent中,其中 mTopAction 默认为 Intent.ACTION_MAIN,同时设置Gategory为Intent.CATEGORY_HOME。系统通过Intent的参数匹配Launcher的AndroidManifest中的内容,启动Launcher进程。
系统启动流程
从Android系统按下电源键到Launcher进程的启动总结如下:
当Launcher进程启动完成,系统桌面展示出已经安装的应用程序图标。至此整个Android系统启动流程就结束了。
还不会的同学赶紧学起来吧,感谢您的阅读,创造不易,如果您觉得本篇文章对您有帮助,请点击关注小编,您的支持就是小编创作的最大动力!
后续文章逐渐深入WMS,PMS等Framework层,剖析源码,关注小编,学习不迷路!