目录
- 应用进程的启动流程
- 1、ActivityStackSupervisor.startSpecificActivity
- 2、ATMS.startProcessAsync
- 3、LocalService.startProcess
- 4、startProcessLocked函数
- 5、ProcessList.startProcessLocked
- 6、ProcessList.startProcessLocked重载
- 7、ProcessList.startProcess
- 8、ZygoteState.startViaZygote
- 9、ZygoteState.openZygoteSocketIfNeeded
- 10、attemptZygoteSendArgsAndGetResult
- 11、attemptZygoteSendArgsAndGetResult
- 12、Zygote.main
- 13、ZygoteServer.runSelectLoo
- 14、ZygoteConnection.processOneCommand
- 15、handleChildProc
- 16、 ZygoteInit.zygoteInit
- 17、RuntimeInit.applicationInit
- 18、RuntimeInit.findStaticMain
- 19、进程ActivityThread.main。
- 知识点
- 疑问点
应用进程的启动流程
本文基于Android 11,主要分析应用程序的启动流程,会直接定位到ActivityStackSupervisor.startSpecificActivity函数开始,因为该函数前面的内容主要在Activity的启动流程中,可以通过这部分的文章来阅读。
看源码流程,需要戒骄戒躁,心态好。配合源码使用,建议先收藏,夜深人静,心血来潮再看。
通过分析应用进程的启动流程,可以得到:
- 在Framework层,现在不止有AMS负责请求Zygote进程创建新进程,还有ATMS、ActivityStarter、ActivityTaskManger、ActivityTaskS在协助分担一些参数和逻辑的检查。
- 每个进程都是通过fork Zygote进程而来,且获得Java虚拟机。也就是说每一个应用进程都有自己的虚拟机。
- 应用进程是通过Soket去请求Zygote进程fork自己的。
- 每个进程都有自己的Binder线程池用于IPC。
- 每个应用进程的主线程在ActivityThread,其main函数会创建消息循环机制。
1、ActivityStackSupervisor.startSpecificActivity
ATMS有一个ProcessMap<WindowProcessController>类型的mProcessNames ,用于存储封装了已启动进程信息ProcessRecord和窗口信息Windows的WindowProcessController实例。WindowProcessController用于协调ActivityManger管理ProcessReocrd和WindwManger管理WIndow和Activity的关系。
void startSpecificActivity(ActivityRecord r, boolean andResume, boolean checkConfig) { | |
// Is this activity's application already running? | |
final WindowProcessController wpc = | |
mService.getProcessController(r.processName, r.info.applicationInfo.uid); | |
boolean knownToBeDead = false; | |
if (wpc != null && wpc.hasThread()) { | |
realStartActivityLocked(r, wpc, andResume, checkConfig); | |
return; | |
... | |
knownToBeDead = true; | |
} | |
r.notifyUnknownVisibilityLaunchedForKeyguardTransition(); | |
final boolean isTop = andResume && r.isTopRunningActivity(); | |
mService.startProcessAsync(r, knownToBeDead, isTop, isTop ? "top-activity" : "activity"); | |
} |
这里的mService是ActivityTaskManagerService的实例,通过getProcessController函数获得当前wpc对象,判断当前启动应用进程是否启动wpc != null && wpc.hasThread(),如果条件成立,则开始真正启动一个未启动过的Activity,通过realStartActivityLocked;条件不成立,则调用mService的startProcessAsync启动当前Activity的所在的进程。即startSpecificActivity函数是启动进程和启动Activity的一个分界点。
2、ATMS.startProcessAsync
PooledLambda.obtainMessage函数是Lambda的调用方式,表示调用ActivityManagerInternal的startProcess函数,后续则是其参数。并返回一个Message对象,发给Handler类型的mH。
void startProcessAsync(ActivityRecord activity, boolean knownToBeDead, boolean isTop, | |
String hostingType) { | |
final Message m = PooledLambda.obtainMessage(ActivityManagerInternal::startProcess, | |
mAmInternal, activity.processName, activity.info.applicationInfo, knownToBeDead, | |
isTop, hostingType, activity.intent.getComponent()); | |
mH.sendMessage(m); | |
} |
抽象类ActivityManagerInternal的继承类定义在ActivityManagerService的内部类LocalService。
public final class LocalService extends ActivityManagerInternal
3、LocalService.startProcess
public void startProcess(String processName, ApplicationInfo info, boolean knownToBeDead, | |
boolean isTop, String hostingType, ComponentName hostingName) { | |
startProcessLocked(processName, info, knownToBeDead, /* intentFlags */, | |
new HostingRecord(hostingType, hostingName, isTop), | |
ZYGOTE_POLICY_FLAG_LATENCY_SENSITIVE, false /* allowWhileBooting */, | |
false /* isolated */, true /* keepIfLarge */); | |
} |
4、startProcessLocked函数
final ProcessRecord startProcessLocked(String processName, | |
ApplicationInfo info, boolean knownToBeDead, int intentFlags, | |
HostingRecord hostingRecord, int zygotePolicyFlags, boolean allowWhileBooting, | |
boolean isolated, boolean keepIfLarge) { | |
return mProcessList.startProcessLocked(processName, info, knownToBeDead, intentFlags, | |
hostingRecord, zygotePolicyFlags, allowWhileBooting, isolated, /* isolatedUid */, | |
keepIfLarge, null /* ABI override */, null /* entryPoint */, | |
null /* entryPointArgs */, null /* crashHandler */); | |
} |
5、ProcessList.startProcessLocked
ProcessList类的startProcessLocked函数,有几个重载函数,第一个调用。
在 !isolated,判断了启动IntentFlag是否后台运行,是的话,直接拒绝。否则清理AMS中发生过Crash的进程(当前应用)。
分析一:创立当前应用进程的描述ProcessRecord。
判断当前系统是否启动完毕,未启动完毕,将进程信息缓存到AMS的mProcessesOnHold中。
分析二:调用了另外一个重载函数。
final ProcessRecord startProcessLocked(String processName, ApplicationInfo info, | |
boolean knownToBeDead, int intentFlags, HostingRecord hostingRecord, | |
int zygotePolicyFlags, boolean allowWhileBooting, boolean isolated, int isolatedUid, | |
boolean keepIfLarge, String abiOverride, String entryPoint, String[] entryPointArgs, | |
Runnable crashHandler) { | |
long startTime = SystemClock.uptimeMillis(); | |
ProcessRecord app; | |
//isolated传递进来是false, if (!isolated) { | |
//从mProcessNames缓存获取,由于是首次创建,null app = getProcessRecordLocked(processName, info.uid, keepIfLarge); | |
checkSlow(startTime, "startProcess: after getProcessRecord"); | |
//判断要启动进程是否后台运行,直接return null if ((intentFlags & Intent.FLAG_FROM_BACKGROUND) !=) { | |
if (mService.mAppErrors.isBadProcessLocked(info)) { | |
return null; | |
} | |
} else { | |
//重置进程的crash状态,使其处于正常状态 | |
mService.mAppErrors.resetProcessCrashTimeLocked(info); | |
if (mService.mAppErrors.isBadProcessLocked(info)) { | |
mService.mAppErrors.clearBadProcessLocked(info); | |
if (app != null) { | |
app.bad = false; | |
} | |
} | |
} | |
} else { | |
app = null; | |
} | |
ProcessRecord precedence = null; | |
if (app != null && app.pid >) { | |
if ((!knownToBeDead && !app.killed) || app.thread == null) { | |
app.addPackage(info.packageName, info.longVersionCode, mService.mProcessStats); | |
return app; | |
} | |
ProcessList.killProcessGroup(app.uid, app.pid); | |
precedence = app; | |
app = null; | |
} | |
if (app == null) { | |
// 分析一、创建新的应用进程描述ProcessRocrd //内部会将自己添加到mProcessNames中 | |
app = newProcessRecordLocked(info, processName, isolated, isolatedUid, hostingRecord); if (app == null) { | |
return null; | |
} | |
//此时三者都是null app.crashHandler = crashHandler; | |
app.isolatedEntryPoint = entryPoint; | |
app.isolatedEntryPointArgs = entryPointArgs; | |
if (precedence != null) { | |
app.mPrecedence = precedence; | |
precedence.mSuccessor = app; | |
} | |
} else { | |
app.addPackage(info.packageName, info.longVersionCode, mService.mProcessStats); | |
} | |
// If the system is not ready yet, then hold off on starting this | |
// process until it is. | |
if (!mService.mProcessesReady | |
&& !mService.isAllowedWhileBooting(info) | |
&& !allowWhileBooting) { | |
if (!mService.mProcessesOnHold.contains(app)) { | |
mService.mProcessesOnHold.add(app); | |
} | |
if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES, | |
"System not ready, putting on hold: " + app); | |
checkSlow(startTime, "startProcess: returning with proc on hold"); | |
return app; | |
} | |
分析二: final boolean success = | |
startProcessLocked(app, hostingRecord, zygotePolicyFlags, abiOverride); | |
checkSlow(startTime, "startProcess: done starting proc!"); | |
return success ? app : null; | |
} |
6、ProcessList.startProcessLocked重载
再次调用另外一个重载函数。
final boolean startProcessLocked(ProcessRecord app, HostingRecord hostingRecord, | |
int zygotePolicyFlags, String abiOverride) { | |
return startProcessLocked(app, hostingRecord, zygotePolicyFlags, | |
false /* disableHiddenApiChecks */, false /* disableTestApiChecks */, | |
false /* mountExtStorageFull */, abiOverride); | |
} |
重载函数,这个重载函数处理逻辑很长,主要给前面创建的ProcessRecord类型的app设置各种属性。例如外部存储挂载模式,应用进程运行模式,abi架构等等,其中包括最重要一点就是分析一,确定要启动进程的的类名:android.app.ActivityThread。分析二,继续调用重载函数。
boolean startProcessLocked(ProcessRecord app, HostingRecord hostingRecord, | |
int zygotePolicyFlags, boolean disableHiddenApiChecks, boolean disableTestApiChecks, | |
boolean mountExtStorageFull, String abiOverride) { | |
... app.gids = gids; | |
app.setRequiredAbi(requiredAbi); | |
app.instructionSet = instructionSet; | |
final String seInfo = app.info.seInfo | |
+ (TextUtils.isEmpty(app.info.seInfoUser) ? "" : app.info.seInfoUser); | |
//分析一:确定要启动应用程序的类名 | |
final String entryPoint = "android.app.ActivityThread"; | |
//分析二:调用另外一个重载函数 return startProcessLocked(hostingRecord, entryPoint, app, uid, gids, | |
runtimeFlags, zygotePolicyFlags, mountExternal, seInfo, requiredAbi, | |
instructionSet, invokeWith, startTime); | |
} catch (RuntimeException e) { | |
... | |
} | |
} |
重载函数:也是设置一些属性,然后调用startProcess函数。
boolean startProcessLocked(HostingRecord hostingRecord, String entryPoint, ProcessRecord app, | |
int uid, int[] gids, int runtimeFlags, int zygotePolicyFlags, int mountExternal, | |
String seInfo, String requiredAbi, String instructionSet, String invokeWith, | |
long startTime) { | |
... | |
final Process.ProcessStartResult startResult = startProcess(hostingRecord, | |
entryPoint, app, | |
uid, gids, runtimeFlags, zygotePolicyFlags, mountExternal, seInfo, | |
requiredAbi, instructionSet, invokeWith, startTime); | |
handleProcessStartedLocked(app, startResult.pid, startResult.usingWrapper, | |
startSeq, false); | |
... | |
} | |
} |
7、ProcessList.startProcess
ProcessList类的startProcess函数会根据hostingRecord属性mHostingZygote判断走不同的创建分支,前面创建使用默认值,所以走了else分支。通过 Process.start函数创建新的应用进程。
Process.start的一路调用:
Process.start=>ZygoteProcess.start=>ZygoteState.start=>ZygoteState.startViaZygote
8、ZygoteState.startViaZygote
startViaZygote函数,主要是将传递进来的参数拼接成成字符串和收集起来。其中processClass是
private Process.ProcessStartResult startViaZygote(...) | |
throws ZygoteStartFailedEx { | |
//根据传递进来的参数,拼接成字符串并收集到ArrayList<String>类型argsForZygote | |
//将作为新应用程序的主函数的参数 | |
return zygoteSendArgsAndGetResult(openZygoteSocketIfNeeded(abi), | |
zygotePolicyFlags, | |
argsForZygote); | |
} |
9、ZygoteState.openZygoteSocketIfNeeded
zygoteSendArgsAndGetResult的第一个参数,调用了openZygoteSocketIfNeeded函数。尝试建立与Socket的连接(如果之前未建立的话)。我们知道Zygote进程在创建的过程,会调用runSelectLoop函数,创建Server端的Socket,一直等待来自AMS的Client端的Socket创建进程请求。
private ZygoteState openZygoteSocketIfNeeded(String abi) throws ZygoteStartFailedEx { | |
try { | |
//建立和Zygote的Socket连接 | |
attemptConnectionToPrimaryZygote(); | |
//匹配abi的架构。在Zygote的创建对应四种模式:,32_64和64,64_32 | |
//,64 | |
if (primaryZygoteState.matches(abi)) { | |
return primaryZygoteState; | |
} | |
//主要架构模式不配,匹配第二种_64,64_32 | |
if (mZygoteSecondarySocketAddress != null) { | |
// The primary zygote didn't match. Try the secondary. | |
attemptConnectionToSecondaryZygote(); | |
if (secondaryZygoteState.matches(abi)) { | |
return secondaryZygoteState; | |
} | |
} | |
} catch (IOException ioe) { | |
throw new ZygoteStartFailedEx("Error connecting to zygote", ioe); | |
} | |
throw new ZygoteStartFailedEx("Unsupported zygote ABI: " + abi); | |
} |
attemptConnectionToPrimaryZygote函数主要通过底层的LocalSocket创建与Zygote进程的Socket连接,并获得输入流zygoteInputStream和输出流zygoteOutputWriter。
private void attemptConnectionToPrimaryZygote() throws IOException { | |
if (primaryZygoteState == null || primaryZygoteState.isClosed()) { | |
primaryZygoteState = | |
ZygoteState.connect(mZygoteSocketAddress, mUsapPoolSocketAddress); | |
maybeSetApiBlacklistExemptions(primaryZygoteState, false); | |
maybeSetHiddenApiAccessLogSampleRate(primaryZygoteState); | |
} | |
} |
和Zygote进程的Server端Socket建立连接后,就是开始往Socket写数据了。
10、attemptZygoteSendArgsAndGetResult
回到第8步调用了zygoteSendArgsAndGetResult函数,又调用了attemptZygoteSendArgsAndGetResult函数。
zygoteSendArgsAndGetResult=>attemptZygoteSendArgsAndGetResult
11、attemptZygoteSendArgsAndGetResult
到这里,通过Socket的方式向Zygote进程写进前面拼接好的参数,Zygote在Server端的Socket接收到数据之后,会执行创建动作。在返回的result.pid>=0表示创建成功,并运行在新的进程。
private Process.ProcessStartResult attemptZygoteSendArgsAndGetResult( | |
ZygoteState zygoteState, String msgStr) throws ZygoteStartFailedEx { | |
try { | |
final BufferedWriter zygoteWriter = zygoteState.mZygoteOutputWriter; | |
final DataInputStream zygoteInputStream = zygoteState.mZygoteInputStream; | |
zygoteWriter.write(msgStr); | |
zygoteWriter.flush(); | |
Process.ProcessStartResult result = new Process.ProcessStartResult(); | |
result.pid = zygoteInputStream.readInt(); | |
result.usingWrapper = zygoteInputStream.readBoolean(); | |
if (result.pid <) { | |
throw new ZygoteStartFailedEx("fork() failed"); | |
} | |
return result; | |
} catch (IOException ex) { | |
zygoteState.close(); | |
Log.e(LOG_TAG, "IO Exception while communicating with Zygote - " | |
+ ex.toString()); | |
throw new ZygoteStartFailedEx(ex); | |
} | |
} |
12、Zygote.main
在Zygote的启动流程过程,调用了ZygoteInit的main函数,因为Zygote是通过fork自身来创建其他进程,所以需要根据传递进来的参数,进行判断是启动什么类型的进程,例如自身isPrimaryZygote=true,或者SystemServer进程。然后通过ZygoteServer.runSelectLoop函数,等待其他进程请求创建新的进程。
public static void main(String argv[]) { | |
ZygoteServer zygoteServer = null; | |
Runnable caller; | |
try { | |
... | |
boolean startSystemServer = false; | |
String zygoteSocketName = "zygote"; | |
String abiList = null; | |
boolean enableLazyPreload = false; | |
for (int i =; i < argv.length; i++) { | |
if ("start-system-server".equals(argv[i])) { | |
startSystemServer = true; //判断是否SystemServer进程 | |
} 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)) { | |
//SCOKET_NAME_ARG="--socket-name=",根据参数得到SocketName | |
zygoteSocketName = argv[i].substring(SOCKET_NAME_ARG.length()); | |
} else { | |
throw new RuntimeException("Unknown command line argument: " + argv[i]); | |
} | |
} | |
//PRIMARY_SOCKET_NAME=zygote | |
final boolean isPrimaryZygote = zygoteSocketName.equals(Zygote.PRIMARY_SOCKET_NAME); | |
gcAndFinalize(); | |
Zygote.initNativeState(isPrimaryZygote); | |
ZygoteHooks.stopZygoteNoThreadCreation(); | |
zygoteServer = new ZygoteServer(isPrimaryZygote); | |
if (startSystemServer) { | |
//启动SystemServer进程 | |
Runnable r = forkSystemServer(abiList, zygoteSocketName, zygoteServer); | |
if (r != null) { | |
r.run(); | |
return; | |
} | |
} | |
//循环等待AMS来请求创建新的进程 | |
caller = zygoteServer.runSelectLoop(abiList); | |
} catch (Throwable ex) { | |
Log.e(TAG, "System zygote died with exception", ex); | |
throw ex; | |
} finally { | |
if (zygoteServer != null) { | |
zygoteServer.closeServerSocket(); | |
} | |
} | |
//调用新的进程主函数 if (caller != null) { | |
caller.run(); | |
} | |
} |
13、ZygoteServer.runSelectLoo
这里只关注ZygoteServer.runSelectLoop函数,接受Socket客户端数据。
/** | |
* Runs the zygote process's select loop. Accepts new connections as | |
* they happen, and reads commands from connections one spawn-request's | |
* worth at a time. | |
*/ | |
Runnable runSelectLoop(String abiList) { | |
while (true) { | |
... | |
ZygoteConnection connection = peers.get(pollIndex); | |
final Runnable command = connection.processOneCommand(this); | |
... | |
if (mIsForkChild) { | |
return command; | |
} | |
.... | |
} | |
} |
14、ZygoteConnection.processOneCommand
runSelctLoop主要是从循环中检测是否有连接建立,建立之后执行ZygoteConnection的processOneCommand函数,并返回一个Runable类型的command对象。
Runnable processOneCommand(ZygoteServer zygoteServer) { | |
... | |
args = Zygote.readArgumentList(mSocketReader); | |
//根据参数内容,作其他类型的处理 | |
... | |
//创建进程,调用底层nativeForkAndSpecialize方法,通过fork当前进程来创建一个子线程。 | |
pid = Zygote.forkAndSpecialize(parsedArgs.mUid, parsedArgs.mGid, parsedArgs.mGids, | |
parsedArgs.mRuntimeFlags, rlimits, parsedArgs.mMountExternal, parsedArgs.mSeInfo, | |
parsedArgs.mNiceName, fdsToClose, fdsToIgnore, parsedArgs.mStartChildZygote, | |
parsedArgs.mInstructionSet, parsedArgs.mAppDataDir, parsedArgs.mIsTopApp, | |
parsedArgs.mPkgDataInfoList, parsedArgs.mWhitelistedDataInfoList, | |
parsedArgs.mBindMountAppDataDirs, parsedArgs.mBindMountAppStorageDirs); | |
... | |
if (pid ==) { | |
//设置mIsForkChild=true | |
zygoteServer.setForkChild(); | |
//关闭Socket连接 | |
zygoteServer.closeServerSocket(); | |
IoUtils.closeQuietly(serverPipeFd); | |
serverPipeFd = null; | |
//执行子进程内容 | |
return handleChildProc(parsedArgs, childPipeFd, parsedArgs.mStartChildZygote); | |
} | |
... | |
} |
15、handleChildProc
handleChildProc函数。
private Runnable handleChildProc(ZygoteArguments parsedArgs, | |
FileDescriptor pipeFd, boolean isZygote) { | |
... | |
if (!isZygote) { | |
return ZygoteInit.zygoteInit(parsedArgs.mTargetSdkVersion, | |
parsedArgs.mDisabledCompatChanges, | |
parsedArgs.mRemainingArgs, null /* classLoader */); | |
} else { | |
return ZygoteInit.childZygoteInit(parsedArgs.mTargetSdkVersion, | |
parsedArgs.mRemainingArgs, null /* classLoader */); | |
} | |
} |
16、 ZygoteInit.zygoteInit
public static final Runnable zygoteInit(int targetSdkVersion, long[] disabledCompatChanges, | |
String[] argv, ClassLoader classLoader) { | |
RuntimeInit.commonInit(); | |
ZygoteInit.nativeZygoteInit();//为新进程创建Binder线程池 | |
return RuntimeInit.applicationInit(targetSdkVersion, disabledCompatChanges, argv, | |
classLoader); | |
} |
以前还以为每个进程共用一个Binder线程池,现在知道每个进程都有自己的Binder线程池进行IPC。
17、RuntimeInit.applicationInit
protected static Runnable applicationInit(int targetSdkVersion, long[] disabledCompatChanges, | |
String[] argv, ClassLoader classLoader) { | |
final Arguments args = new Arguments(argv); | |
return findStaticMain(args.startClass, args.startArgs, classLoader); | |
} |
这里的args.startClass就是Socket客户端传递下来的android.app.ActivityThread。
18、RuntimeInit.findStaticMain
RuntimeInit.findStaticMain函数主要通过反射创建ActivityThread类的实例,并反射主函数main,然后封装到MethodAndArgsCaller实例中返回。
protected static Runnable findStaticMain(String className, String[] argv, | |
ClassLoader classLoader) { | |
... | |
Class<?> cl = Class.forName(className, true, classLoader); | |
Method m = cl.getMethod("main", new Class[] { String[].class }); | |
... | |
return new MethodAndArgsCaller(m, argv); | |
} |
MethodAndArgsCaller类继承自Runable,并在其run函数,调用主函数方法。
static class MethodAndArgsCaller implements Runnable { | |
/** method to call */ | |
private final Method mMethod; | |
/** argument array */ | |
private final String[] mArgs; | |
public MethodAndArgsCaller(Method method, String[] args) { | |
mMethod = method; | |
mArgs = args; | |
} | |
public void run() { | |
... | |
mMethod.invoke(null, new Object[] { mArgs }); | |
... | |
} | |
} |
随着findStaticMain函数方法栈一路返回到runSelectLoop函数,因为mIsForkChild是true,所以MethodAndArgsCaller对象返回到ZygoteInit的main函数,并赋值给caller变量。main函数最后调用caller的run函数。即执行了ActivityThread的主函数main。
本来自己还有个疑惑,fork子进程之后,并caller的run函数,已经退出了Zygote进程的runSelectLoop循环等待。怎么继续去接收AMS新的请求。原来如此,fork子进程后,后续的代码都运行在了子进程,这里return其实是子进程了。
一个进程调用fork()函数后,系统先给新的进程分配资源,例如存储数据和代码的空间。然后把原来的进程的所有值都复制到新的新进程中,只有少数值与原来的进程的值不同。相当于克隆了一个自己。
19、进程ActivityThread.main。
public static void main(String[] args) { | |
Looper.prepareMainLooper(); | |
ActivityThread thread = new ActivityThread(); | |
thread.attach(false, startSeq); | |
if (sMainThreadHandler == null) { | |
sMainThreadHandler = thread.getHandler(); | |
} | |
Looper.loop(); | |
} |
ActivityThread的主函数,创建了ActivityThread进程,并启动了消息循环队列,代表着当前进程的主线程已启动。
知识点
- fork函数。
- 通过Socket创建新的进程。
- Binder机制和应用程序创建的时机。
- ActivityThread的进程的主线程。
疑问点
- 通过Zygote进程fork而来的子进程都会获得Zygote创建的Java虚拟机,也就是每个应用进程都有自己的Java虚拟机。
- 每个应用进程都有属于自己的Binder线程池和消息循环机制。
- 之所以fork Zygote进程而不是init进程,是避免重复初始化环境资源的加载和虚拟机的创建。
- 进程的创建之所选择Socket机制进行,因为Binder机制会导致死锁,怕父进程binder线程有锁,然后子进程的主线程一直在等其子线程(从父进程拷贝过来的子进程)的资源,但是其实父进程的子进程并没有被拷贝过来,造成死锁,所以fork不允许存在多线程。