您现在的位置是:首页 >技术交流 >【安卓源码】安卓app应用进程启动原理网站首页技术交流
【安卓源码】安卓app应用进程启动原理
目录
2. zygote socket 通信,通知 zygote 创建应用进程
1-1) 去fork 一个子进程 Zygote.forkAndSpecialize
1-3)执行父进程方法 handleParentProc,通知子进程的pid 号
- App发起进程:当从桌面启动应用,则发起进程便是Launcher所在进程;当从某App内启动远程进程,则发送进程便是该App所在进程。发起进程先通过binder发送消息给system_server进程;
- system_server进程:调用Process.start()方法,通过socket向zygote进程发送创建新进程的请求;
- zygote进程:在执行
ZygoteInit.main()
后便进入runSelectLoop()
循环体内,当有客户端连接时便会执行ZygoteConnection.runOnce()方法,再经过层层调用后fork出新的应用进程;- 新进程:执行handleChildProc方法,最后调用ActivityThread.main()方法。
0. 应用app 调用 startActivity
/frameworks/base/core/java/android/app/ContextImpl.java
public void startActivity(Intent intent) {
warnIfCallingFromSystemProcess();
startActivity(intent, null);
}
=========
@Override
public void startActivity(Intent intent, Bundle options) {
warnIfCallingFromSystemProcess();
。。。。
// mMainThread.getApplicationThread() 为:ApplicationThread 用于进程间通信
// final ApplicationThread mAppThread = new ApplicationThread()
// 可以系统进程与 应用进程交互
mMainThread.getInstrumentation().execStartActivity(
getOuterContext(), mMainThread.getApplicationThread(), null,
(Activity) null, intent, -1, options);
}
Instrumentation().execStartActivity(
/frameworks/base/core/java/android/app/Instrumentation.java
@UnsupportedAppUsage
public ActivityResult execStartActivity(
Context who, IBinder contextThread, IBinder token, Activity target,
Intent intent, int requestCode, Bundle options) {
// 将 app 进程设置为:whoThread
IApplicationThread whoThread = (IApplicationThread) contextThread;
。。。
// 关于 activity 的监控类
if (mActivityMonitors != null) {
。。。
try {
intent.migrateExtraStreamToClipData(who);
intent.prepareToLeaveProcess(who);
// 调用系统进程的 ActivityTaskManagerService 的 startActivity
int result = ActivityTaskManager.getService().startActivity(whoThread,
who.getOpPackageName(), who.getAttributionTag(), intent,
intent.resolveTypeIfNeeded(who.getContentResolver()), token,
target != null ? target.mEmbeddedID : null, requestCode, 0, null, options);
// 检查返回来的值
checkStartActivityResult(result, intent);
} catch (RemoteException e) {
throw new RuntimeException("Failure from system", e);
}
return null;
}
1. AMS 调用 startActivity 方法
调用系统进程的 ActivityTaskManagerService 的 startActivity
/frameworks/base/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
@Override
public final int startActivity(IApplicationThread caller, String callingPackage,
String callingFeatureId, Intent intent, String resolvedType, IBinder resultTo,
String resultWho, int requestCode, int startFlags, ProfilerInfo profilerInfo,
Bundle bOptions) {
return startActivityAsUser(caller, callingPackage, callingFeatureId, intent, resolvedType,
resultTo, resultWho, requestCode, startFlags, profilerInfo, bOptions,
UserHandle.getCallingUserId());
}
=======
private int startActivityAsUser(IApplicationThread caller, String callingPackage,
@Nullable String callingFeatureId, Intent intent, String resolvedType,
IBinder resultTo, String resultWho, int requestCode, int startFlags,
ProfilerInfo profilerInfo, Bundle bOptions, int userId, boolean validateIncomingUser) {
assertPackageMatchesCallingUid(callingPackage);
enforceNotIsolatedCaller("startActivityAsUser");
userId = getActivityStartController().checkTargetUser(userId, validateIncomingUser,
Binder.getCallingPid(), Binder.getCallingUid(), "startActivityAsUser");
// TODO: Switch to user app stacks here.
return getActivityStartController().obtainStarter(intent, "startActivityAsUser")
// caller 为:ApplicationThread
.setCaller(caller)
.setCallingPackage(callingPackage)
.setCallingFeatureId(callingFeatureId)
.setResolvedType(resolvedType)
// resultTo 为null, resultWho为 null
.setResultTo(resultTo)
.setResultWho(resultWho)
// requestCode 为 -1
.setRequestCode(requestCode)
.setStartFlags(startFlags)
.setProfilerInfo(profilerInfo)
.setActivityOptions(bOptions)
.setUserId(userId)
.execute();
}
执行如下,省略:
/frameworks/base/services/core/java/com/android/server/wm/ActivityStartController.java
ActivityStartController(ActivityTaskManagerService service) {
this(service, service.mTaskSupervisor,
new DefaultFactory(service, service.mTaskSupervisor,
new ActivityStartInterceptor(service, service.mTaskSupervisor)));
}
-----
ActivityStarter obtainStarter(Intent intent, String reason) {
// DefaultFactory
return mFactory.obtain().setIntent(intent).setReason(reason);
}
==============
/frameworks/base/services/core/java/com/android/server/wm/ActivityStarter.java
execute() ==> executeRequest ==> startActivityUnchecked ==> startActivityInner
==> .....
==============
/frameworks/base/services/core/java/com/android/server/wm/ActivityTaskSupervisor.java
startSpecificActivity(
/frameworks/base/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
void startProcessAsync(ActivityRecord activity, boolean knownToBeDead, boolean isTop,
String hostingType) {
try {
if (Trace.isTagEnabled(TRACE_TAG_WINDOW_MANAGER)) {
Trace.traceBegin(TRACE_TAG_WINDOW_MANAGER, "dispatchingStartProcess:"
+ activity.processName);
}
// Post message to start process to avoid possible deadlock of calling into AMS with the
// ATMS lock held.
// 相当于设置了一个 runnable
final Message m = PooledLambda.obtainMessage(ActivityManagerInternal::startProcess,
mAmInternal, activity.processName, activity.info.applicationInfo, knownToBeDead,
isTop, hostingType, activity.intent.getComponent());
mH.sendMessage(m);
} finally {
Trace.traceEnd(TRACE_TAG_WINDOW_MANAGER);
}
}
mH.sendMessage(m) 看下是跑在什么线程
/frameworks/base/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
public void initialize(IntentFirewall intentFirewall, PendingIntentController intentController,
Looper looper) {
// 这里传入了 looper 对象
mH = new H(looper);
looper 执行在那个线程,消息处理就是在那个线程
/frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
2226 public ActivityManagerService(Context systemContext, ActivityTaskManagerService atm) {
2227 LockGuard.installLock(this, LockGuard.INDEX_ACTIVITY);
2228 mInjector = new Injector(systemContext);
。。。。。。。
2322 mActivityTaskManager.initialize(mIntentFirewall, mPendingIntentController,
2323 DisplayThread.get().getLooper());
looper 是 DisplayThread.get().getLooper()
/frameworks/base/services/core/java/com/android/server/DisplayThread.java
DisplayThread 是个handlerThread
public final class DisplayThread extends ServiceThread {
private static DisplayThread sInstance;
private static Handler sHandler;
。。。
private static void ensureThreadLocked() {
if (sInstance == null) {
sInstance = new DisplayThread();
sInstance.start();
sInstance.getLooper().setTraceTag(Trace.TRACE_TAG_SYSTEM_SERVER);
sHandler = new Handler(sInstance.getLooper());
}
}
public static DisplayThread get() {
synchronized (DisplayThread.class) {
ensureThreadLocked();
return sInstance;
}
}
==========
// ServiceThread 继承了 HandlerThread
26 public class ServiceThread extends HandlerThread {
所以是跑在 DisplayThread 线程中
/frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
16020 @Override
16021 public void startProcess(String processName, ApplicationInfo info, boolean knownToBeDead,
16022 boolean isTop, String hostingType, ComponentName hostingName) {
16023 try {
16024 if (Trace.isTagEnabled(Trace.TRACE_TAG_ACTIVITY_MANAGER)) {
16025 Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "startProcess:"
16026 + processName);
16027 }
16028 synchronized (ActivityManagerService.this) {
16029 // If the process is known as top app, set a hint so when the process is
16030 // started, the top priority can be applied immediately to avoid cpu being
16031 // preempted by other processes before attaching the process of top app.
16032 startProcessLocked(processName, info, knownToBeDead, 0 /* intentFlags */,
16033 new HostingRecord(hostingType, hostingName, isTop),
16034 ZYGOTE_POLICY_FLAG_LATENCY_SENSITIVE, false /* allowWhileBooting */,
16035 false /* isolated */);
16036 }
16037 } finally {
16038 Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
16039 }
16040 }
===============
2682 final ProcessRecord startProcessLocked(String processName,
2683 ApplicationInfo info, boolean knownToBeDead, int intentFlags,
2684 HostingRecord hostingRecord, int zygotePolicyFlags, boolean allowWhileBooting,
2685 boolean isolated) {
2686 return mProcessList.startProcessLocked(processName, info, knownToBeDead, intentFlags,
2687 hostingRecord, zygotePolicyFlags, allowWhileBooting, isolated, 0 /* isolatedUid */,
2688 null /* ABI override */, null /* entryPoint */,
2689 null /* entryPointArgs */, null /* crashHandler */);
2690 }
/frameworks/base/services/core/java/com/android/server/am/ProcessList.java
// 要启动的对象
2023 final String entryPoint = "android.app.ActivityThread";
2043 @GuardedBy("mService")
2044 boolean startProcessLocked(HostingRecord hostingRecord, String entryPoint, ProcessRecord app,
2045 int uid, int[] gids, int runtimeFlags, int zygotePolicyFlags, int mountExternal,
2046 String seInfo, String requiredAbi, String instructionSet, String invokeWith,
2047 long startTime) {
2048 app.setPendingStart(true);
2049 app.setRemoved(false);
2050 synchronized (mProcLock) {
2051 app.setKilledByAm(false);
2052 app.setKilled(false);
2053 }
。。。。
2080 } else {
2081 try {
2082 final Process.ProcessStartResult startResult = startProcess(hostingRecord,
2083 entryPoint, app,
2084 uid, gids, runtimeFlags, zygotePolicyFlags, mountExternal, seInfo,
2085 requiredAbi, instructionSet, invokeWith, startTime);
2086 handleProcessStartedLocked(app, startResult.pid, startResult.usingWrapper,
2087 startSeq, false);
// ProcessList.java
// ===== startProcessLocked 在fork 一个应用进程之后,保存这个 pid 值:handleProcessStartedLocked =====
2086 handleProcessStartedLocked(app, startResult.pid, startResult.usingWrapper,
2087 startSeq, false);
========
2297 private Process.ProcessStartResult startProcess(HostingRecord hostingRecord, String entryPoint,
2298 ProcessRecord app, int uid, int[] gids, int runtimeFlags, int zygotePolicyFlags,
2299 int mountExternal, String seInfo, String requiredAbi, String instructionSet,
2300 String invokeWith, long startTime) {
2301 try {
。。。。
2382 } else if (hostingRecord.usesAppZygote()) {
。。。。。。。。
2394 } else {
2395 regularZygote = true;
2396 startResult = Process.start(entryPoint,
2397 app.processName, uid, uid, gids, runtimeFlags, mountExternal,
2398 app.info.targetSdkVersion, seInfo, requiredAbi, instructionSet,
2399 app.info.dataDir, invokeWith, app.info.packageName, zygotePolicyFlags,
2400 isTopApp, app.getDisabledCompatChanges(), pkgDataInfoMap,
2401 allowlistedAppDataInfoMap, bindMountAppsData, bindMountAppStorageDirs,
2402 new String[]{PROC_START_SEQ_IDENT + app.getStartSeq()});
2403 }
handleProcessStartedLocked
2. zygote socket 通信,通知 zygote 创建应用进程
Process.start 方法
/frameworks/base/core/java/android/os/Process.java
public static ProcessStartResult start(@NonNull final String processClass,
@Nullable final String niceName,
int uid, int gid, @Nullable int[] gids,
int runtimeFlags,
int mountExternal,
int targetSdkVersion,
@Nullable String seInfo,
@NonNull String abi,
@Nullable String instructionSet,
@Nullable String appDataDir,
@Nullable String invokeWith,
@Nullable String packageName,
int zygotePolicyFlags,
boolean isTopApp,
@Nullable long[] disabledCompatChanges,
@Nullable Map<String, Pair<String, Long>>
pkgDataInfoMap,
@Nullable Map<String, Pair<String, Long>>
whitelistedDataInfoMap,
boolean bindMountAppsData,
boolean bindMountAppStorageDirs,
@Nullable String[] zygoteArgs) {
return ZYGOTE_PROCESS.start(processClass, niceName, uid, gid, gids,
runtimeFlags, mountExternal, targetSdkVersion, seInfo,
abi, instructionSet, appDataDir, invokeWith, packageName,
zygotePolicyFlags, isTopApp, disabledCompatChanges,
pkgDataInfoMap, whitelistedDataInfoMap, bindMountAppsData,
bindMountAppStorageDirs, zygoteArgs);
}
===============
606 public static final ZygoteProcess ZYGOTE_PROCESS = new ZygoteProcess();
// 创建了 ZygoteProcess 对象
public ZygoteProcess() {
// String PRIMARY_SOCKET_NAME = "zygote";
// 设置 SOCKET_NAME 为 "zygote"
mZygoteSocketAddress =
new LocalSocketAddress(Zygote.PRIMARY_SOCKET_NAME,
LocalSocketAddress.Namespace.RESERVED);
====================start==========================
java 层的Socket 通信的使用:
客户端:
import android.net.LocalSocket;
import android.net.LocalSocketAddress;
// 连接服务器端
LocalSocket Client = new LocalSocket();
string name = "socket_name";
Client.connect(new LocalSocketAddress(name));
// 写入数据:
os = new PrintWriter(Client.getOutputStream());
os.println(data);
os.flush();
// 读取服务端数据
BufferedReader is = new BufferedReader(new InputStreamReader(Client.getInputStream()));
String result = is.readLine();
服务器端:
import android.net.LocalServerSocket;
import android.net.LocalSocket;
import android.net.LocalSocketAddress;
// 创建 LocalServerSocket 对象,执行accept 方法
// LocalServerSocket 的名字需要和客户端创建的name 是一样的
string name = "socket_name";
LocalServerSocket server = new LocalServerSocket(name);
while (!exit) {
LocalSocket connect = server.accept();
// 获取客户端的数据
InputStream input = socket.getInputStream();
byte[] buffer = new byte[1024];
int len = input.read(buffer);
PrintWriter os = new PrintWriter(socket.getOutputStream());
os.println("this is server ");
os.flush();
====================end==========================
zygote 进程 执行
/frameworks/base/core/java/com/android/internal/os/ZygoteInit.java
@UnsupportedAppUsage
public static void main(String[] argv) {
ZygoteServer zygoteServer = null;
。。。。。。
final boolean isPrimaryZygote = zygoteSocketName.equals(Zygote.PRIMARY_SOCKET_NAME);
// 创建了 ZygoteServer 对象
zygoteServer = new ZygoteServer(isPrimaryZygote);
// The select loop returns early in the child process after a fork and
// loops forever in the zygote.
// 执行 runSelectLoop 循环监听客户端的创建进程的消息
caller = zygoteServer.runSelectLoop(abiList);
// 创建了 ZygoteServer 对象
/frameworks/base/core/java/com/android/internal/os/ZygoteServer.java
/**
* Listening socket that accepts new server connections.
*/
private LocalServerSocket mZygoteSocket;
。。。。。
ZygoteServer(boolean isPrimaryZygote) {
mUsapPoolEventFD = Zygote.getUsapPoolEventFD();
if (isPrimaryZygote) {
// 调用createManagedSocketFromInitSocket 创建LocalServerSocket 对象,socket名字为: PRIMARY_SOCKET_NAME = "zygote";
mZygoteSocket = Zygote.createManagedSocketFromInitSocket(Zygote.PRIMARY_SOCKET_NAME);
mUsapPoolSocket =
Zygote.createManagedSocketFromInitSocket(
Zygote.USAP_POOL_PRIMARY_SOCKET_NAME);
构造函数中调用createManagedSocketFromInitSocket 创建LocalServerSocket 对象,socket名字为: PRIMARY_SOCKET_NAME = "zygote";
static LocalServerSocket createManagedSocketFromInitSocket(String socketName) {
int fileDesc;
final String fullSocketName = ANDROID_SOCKET_PREFIX + socketName;
try {
String env = System.getenv(fullSocketName);
fileDesc = Integer.parseInt(env);
} catch (RuntimeException ex) {
throw new RuntimeException("Socket unset or invalid: " + fullSocketName, ex);
}
try {
FileDescriptor fd = new FileDescriptor();
fd.setInt$(fileDesc);
// 获取 LocalServerSocket 对象
return new LocalServerSocket(fd);
} catch (IOException ex) {
throw new RuntimeException(
"Error building socket from file descriptor: " + fileDesc, ex);
}
}
// 执行 runSelectLoop 循环监听客户端的创建进程的消息
/frameworks/base/core/java/com/android/internal/os/ZygoteServer.java
Runnable runSelectLoop(String abiList) {
ArrayList<FileDescriptor> socketFDs = new ArrayList<>();
ArrayList<ZygoteConnection> peers = new ArrayList<>();
// 将 ZygoteSocket 的文件描述符放到 socketFDs 数组中
socketFDs.add(mZygoteSocket.getFileDescriptor());
peers.add(null);
while (true) {
StructPollfd[] pollFDs;
} else {
pollFDs = new StructPollfd[socketFDs.size()];
}
int pollIndex = 0;
// 创建 StructPollfd ,并赋值初值
for (FileDescriptor socketFD : socketFDs) {
pollFDs[pollIndex] = new StructPollfd();
pollFDs[pollIndex].fd = socketFD;
pollFDs[pollIndex].events = (short) POLLIN;
++pollIndex;
}
final int usapPoolEventFDIndex = pollIndex;
if (mUsapPoolEnabled) {
。。。。
}
int pollTimeoutMs;
if (mUsapPoolRefillTriggerTimestamp == INVALID_TIMESTAMP) {
pollTimeoutMs = -1;
} else {
long elapsedTimeMs = System.currentTimeMillis() - mUsapPoolRefillTriggerTimestamp;
if (elapsedTimeMs >= mUsapPoolRefillDelayMs) {
pollTimeoutMs = 0;
mUsapPoolRefillTriggerTimestamp = INVALID_TIMESTAMP;
mUsapPoolRefillAction = UsapPoolRefillAction.DELAYED;
} else if (elapsedTimeMs <= 0) {
pollTimeoutMs = mUsapPoolRefillDelayMs;
} else {
pollTimeoutMs = (int) (mUsapPoolRefillDelayMs - elapsedTimeMs);
}
}
int pollReturnValue;
try {
// poll 监听 fd 变化
pollReturnValue = Os.poll(pollFDs, pollTimeoutMs);
} catch (ErrnoException ex) {
throw new RuntimeException("poll failed", ex);
}
if (pollReturnValue == 0) {
mUsapPoolRefillTriggerTimestamp = INVALID_TIMESTAMP;
mUsapPoolRefillAction = UsapPoolRefillAction.DELAYED;
} else {
boolean usapPoolFDRead = false;
while (--pollIndex >= 0) {
if ((pollFDs[pollIndex].revents & POLLIN) == 0) {
continue;
}
if (pollIndex == 0) {
// Zygote server socket
// acceptCommandPeer 创建 ZygoteConnection 对象
ZygoteConnection newPeer = acceptCommandPeer(abiList);
peers.add(newPeer);
// 将其增加到监听的数组中
socketFDs.add(newPeer.getFileDescriptor());
} else if (pollIndex < usapPoolEventFDIndex) {
// Session socket accepted from the Zygote server socket
try {
// 再次循环后,监听到客户端消息,则执行下列方法
ZygoteConnection connection = peers.get(pollIndex);
boolean multipleForksOK = !isUsapPoolEnabled()
&& ZygoteHooks.isIndefiniteThreadSuspensionSafe();
// 执行 ZygoteConnection 对象 的 processCommand 方法
final Runnable command =
connection.processCommand(this, multipleForksOK);
if (mIsForkChild) {
if (command == null) {
throw new IllegalStateException("command == null");
}
return command;
} else {
// We're in the server - we should never have any commands to run.
if (command != null) {
throw new IllegalStateException("command != null");
}
if (connection.isClosedByPeer()) {
connection.closeSocket();
peers.remove(pollIndex);
socketFDs.remove(pollIndex);
}
}
} catch (Exception e) {
if (!mIsForkChild) {
。。。。。。。。。。
} else {
。。。。。。。。
throw e;
} else {
long messagePayload;
try {
byte[] buffer = new byte[Zygote.USAP_MANAGEMENT_MESSAGE_BYTES];
int readBytes =
Os.read(pollFDs[pollIndex].fd, buffer, 0, buffer.length);
if (readBytes == Zygote.USAP_MANAGEMENT_MESSAGE_BYTES) {
DataInputStream inputStream =
new DataInputStream(new ByteArrayInputStream(buffer));
messagePayload = inputStream.readLong();
} else {
。。。
。。。。。。。。
}
}
}
}
// acceptCommandPeer 创建 ZygoteConnection 对象
private ZygoteConnection acceptCommandPeer(String abiList) {
try {
return createNewConnection(mZygoteSocket.accept(), abiList);
} catch (IOException ex) {
throw new RuntimeException(
"IOException during accept()", ex);
}
}
=========
protected ZygoteConnection createNewConnection(LocalSocket socket, String abiList)
throws IOException {
return new ZygoteConnection(socket, abiList);
}
startViaZygote 创建应用进程 :system 进程与 zygote 进程 socket 通信
/frameworks/base/core/java/android/os/ZygoteProcess.java
public final Process.ProcessStartResult start(@NonNull final String processClass,
final String niceName,
。。。
try {
return startViaZygote(processClass, niceName, uid, gid, gids,
runtimeFlags, mountExternal, targetSdkVersion, seInfo,
abi, instructionSet, appDataDir, invokeWith, /*startChildZygote=*/ false,
packageName, zygotePolicyFlags, isTopApp, disabledCompatChanges,
pkgDataInfoMap, allowlistedDataInfoList, bindMountAppsData,
bindMountAppStorageDirs, zygoteArgs);
=================
private Process.ProcessStartResult startViaZygote(@NonNull final String processClass,
@Nullable final String niceName,
final int uid, final int gid,
@Nullable final int[] gids,
int runtimeFlags, int mountExternal,
int targetSdkVersion,
@Nullable String seInfo,
@NonNull String abi,
@Nullable String instructionSet,
@Nullable String appDataDir,
@Nullable String invokeWith,
boolean startChildZygote,
@Nullable String packageName,
int zygotePolicyFlags,
boolean isTopApp,
@Nullable long[] disabledCompatChanges,
@Nullable Map<String, Pair<String, Long>>
pkgDataInfoMap,
@Nullable Map<String, Pair<String, Long>>
allowlistedDataInfoList,
boolean bindMountAppsData,
boolean bindMountAppStorageDirs,
@Nullable String[] extraArgs)
throws ZygoteStartFailedEx {
ArrayList<String> argsForZygote = new ArrayList<>();
。。。。
argsForZygote.add("--target-sdk-version=" + targetSdkVersion);
// --setgroups is a comma-separated list
if (gids != null && gids.length > 0) {
final StringBuilder sb = new StringBuilder();
sb.append("--setgroups=");
final int sz = gids.length;
for (int i = 0; i < sz; i++) {
if (i != 0) {
sb.append(',');
}
sb.append(gids[i]);
}
argsForZygote.add(sb.toString());
}
。。。。。
。。。。。
argsForZygote.add(processClass);
// 将消息封装 再 argsForZygote 中
if (extraArgs != null) {
Collections.addAll(argsForZygote, extraArgs);
}
synchronized(mLock) {
return zygoteSendArgsAndGetResult(openZygoteSocketIfNeeded(abi),
zygotePolicyFlags,
argsForZygote);
}
}
zygoteSendArgsAndGetResult(openZygoteSocketIfNeeded(abi)
openZygoteSocketIfNeeded 方法:返回值是 zygoteState
@GuardedBy("mLock")
private ZygoteState openZygoteSocketIfNeeded(String abi) throws ZygoteStartFailedEx {
try {
attemptConnectionToPrimaryZygote();
。。。。。。。。
@GuardedBy("mLock")
private void attemptConnectionToPrimaryZygote() throws IOException {
if (primaryZygoteState == null || primaryZygoteState.isClosed()) {
primaryZygoteState =
ZygoteState.connect(mZygoteSocketAddress, mUsapPoolSocketAddress);
// 连接的 socket name 为:PRIMARY_SOCKET_NAME = "zygote";
public ZygoteProcess() {
mZygoteSocketAddress =
new LocalSocketAddress(Zygote.PRIMARY_SOCKET_NAME,
LocalSocketAddress.Namespace.RESERVED);
zygoteSendArgsAndGetResult 方法
private Process.ProcessStartResult zygoteSendArgsAndGetResult(
ZygoteState zygoteState, int zygotePolicyFlags, @NonNull ArrayList<String> args)
throws ZygoteStartFailedEx {
。。。。
*/
String msgStr = args.size() + "
" + String.join("
", args) + "
";
return attemptZygoteSendArgsAndGetResult(zygoteState, msgStr);
}
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();
// Always read the entire result from the input stream to avoid leaving
// bytes in the stream for future process starts to accidentally stumble
// upon.
// 读取服务器端返回的进程号 pid
Process.ProcessStartResult result = new Process.ProcessStartResult();
result.pid = zygoteInputStream.readInt();
result.usingWrapper = zygoteInputStream.readBoolean();
if (result.pid < 0) {
throw new ZygoteStartFailedEx("fork() failed");
}
// 返回这个 result
return result;
zygote 进程执行
/frameworks/base/core/java/com/android/internal/os/ZygoteConnection.java
Runnable processCommand(ZygoteServer zygoteServer, boolean multipleOK) {
ZygoteArguments parsedArgs;
try (ZygoteCommandBuffer argBuffer = new ZygoteCommandBuffer(mSocket)) {
while (true) {
try {
// 将传过来的参数包装为:ZygoteArguments
// 调用 parseArgs 函数解析这些参数
parsedArgs = ZygoteArguments.getInstance(argBuffer);
// Keep argBuffer around, since we need it to fork.
} catch (IOException ex) {
throw new IllegalStateException("IOException on command socket", ex);
}
if (parsedArgs == null) {
isEof = true;
return null;
}
int pid;
。。。。。。。
if (parsedArgs.mInvokeWith != null || parsedArgs.mStartChildZygote
|| !multipleOK || peer.getUid() != Process.SYSTEM_UID) {
// Continue using old code for now. TODO: Handle these cases in the other path.
//1-1) 去fork 一个子进程 Zygote.forkAndSpecialize
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.mAllowlistedDataInfoList, parsedArgs.mBindMountAppDataDirs,
parsedArgs.mBindMountAppStorageDirs);
try {
if (pid == 0) {
// 设置是子进程,退出 runSelectLoop
// in child
zygoteServer.setForkChild();
// 关闭socket 通信
zygoteServer.closeServerSocket();
IoUtils.closeQuietly(serverPipeFd);
serverPipeFd = null;
// 1-2)执行子进程方法 handleChildProc
return handleChildProc(parsedArgs, childPipeFd,
parsedArgs.mStartChildZygote);
} else {
// In the parent. A pid < 0 indicates a failure and will be handled in
// handleParentProc.
IoUtils.closeQuietly(childPipeFd);
childPipeFd = null;
// 1-3)执行父进程方法 handleParentProc,通知子进程的pid 号
handleParentProc(pid, serverPipeFd);
return null;
}
} finally {
IoUtils.closeQuietly(childPipeFd);
IoUtils.closeQuietly(serverPipeFd);
}
} else {
。。。。。
throw new AssertionError("Shouldn't get here");
}
1-1) 去fork 一个子进程 Zygote.forkAndSpecialize
/frameworks/base/core/java/com/android/internal/os/Zygote.java
static int forkAndSpecialize(int uid, int gid, int[] gids, int runtimeFlags,
int[][] rlimits, int mountExternal, String seInfo, String niceName, int[] fdsToClose,
int[] fdsToIgnore, boolean startChildZygote, String instructionSet, String appDataDir,
boolean isTopApp, String[] pkgDataInfoList, String[] allowlistedDataInfoList,
boolean bindMountAppDataDirs, boolean bindMountAppStorageDirs) {
ZygoteHooks.preFork();
// 调用native 层代码 nativeForkAndSpecialize
int pid = nativeForkAndSpecialize(
uid, gid, gids, runtimeFlags, rlimits, mountExternal, seInfo, niceName, fdsToClose,
fdsToIgnore, startChildZygote, instructionSet, appDataDir, isTopApp,
pkgDataInfoList, allowlistedDataInfoList, bindMountAppDataDirs,
bindMountAppStorageDirs);
// 调用native 层代码 nativeForkAndSpecialize
/frameworks/base/core/jni/com_android_internal_os_Zygote.cpp
static jint com_android_internal_os_Zygote_nativeForkAndSpecialize(
JNIEnv* env, jclass, jint uid, jint gid, jintArray gids, jint runtime_flags,
jobjectArray rlimits, jint mount_external, jstring se_info, jstring nice_name,
jintArray managed_fds_to_close, jintArray managed_fds_to_ignore, jboolean is_child_zygote,
jstring instruction_set, jstring app_data_dir, jboolean is_top_app,
jobjectArray pkg_data_info_list, jobjectArray allowlisted_data_info_list,
jboolean mount_data_dirs, jboolean mount_storage_dirs) {
。。。。
// fork 一个进程
pid_t pid = zygote::ForkCommon(env, /* is_system_server= */ false, fds_to_close, fds_to_ignore,
true);
// 如果是子进程的话,则执行 SpecializeCommon
if (pid == 0) {
SpecializeCommon(env, uid, gid, gids, runtime_flags, rlimits, capabilities, capabilities,
mount_external, se_info, nice_name, false, is_child_zygote == JNI_TRUE,
instruction_set, app_data_dir, is_top_app == JNI_TRUE, pkg_data_info_list,
allowlisted_data_info_list, mount_data_dirs == JNI_TRUE,
mount_storage_dirs == JNI_TRUE);
}
return pid;
}
// Utility routine to fork a process from the zygote.
pid_t zygote::ForkCommon(JNIEnv* env, bool is_system_server,
const std::vector<int>& fds_to_close,
const std::vector<int>& fds_to_ignore,
bool is_priority_fork,
bool purge) {
SetSignalHandlers();
。。。。
// fork 一个子进程
pid_t pid = fork();
if (pid == 0) {
if (is_priority_fork) {
setpriority(PRIO_PROCESS, 0, PROCESS_PRIORITY_MAX);
} else {
setpriority(PRIO_PROCESS, 0, PROCESS_PRIORITY_MIN);
}
fork采用copy-on-write技术,这是linux创建进程的标准方法,调用一次,返回两次,返回值有3种类型:
- 在父进程中,fork返回新创建的子进程pid。
- 在子进程中,fork返回0;
- 当出现错误时,fork返回负数。
fork的主要工作是寻找空闲的进程号pid,然后从父进程拷贝进程信息,例如数据段和代码段,fork()后子进程要执行的代码等。Zygote进程是所有Android进程的母体,包括system_server和各个App进程。
Zygote利用fork方法生成新进程,对于新进程A复用Zygote进程本身的资源,再加上新进程A相关的资源,构成新的应用进程A。
1-2)执行子进程方法 handleChildProc
private Runnable handleChildProc(ZygoteArguments parsedArgs,
FileDescriptor pipeFd, boolean isZygote) {
/*
* By the time we get here, the native code has closed the two actual Zygote
* socket connections, and substituted /dev/null in their place. The LocalSocket
* objects still need to be closed properly.
*/
closeSocket();
Zygote.setAppProcessName(parsedArgs, TAG);
...
} else {
if (!isZygote) {
return ZygoteInit.zygoteInit(parsedArgs.mTargetSdkVersion,
parsedArgs.mDisabledCompatChanges,
parsedArgs.mRemainingArgs, null /* classLoader */);
} else {
/frameworks/base/core/java/com/android/internal/os/ZygoteInit.java
public static Runnable zygoteInit(int targetSdkVersion, long[] disabledCompatChanges,
String[] argv, ClassLoader classLoader) {
if (RuntimeInit.DEBUG) {
Slog.d(RuntimeInit.TAG, "RuntimeInit: Starting application from zygote");
}
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "ZygoteInit");
RuntimeInit.redirectLogStreams();
RuntimeInit.commonInit();
// 连接biander 驱动 nativeZygoteInit
ZygoteInit.nativeZygoteInit();
// 反射获取 ActivityThread 的main 方法,调用run 方法时执行
return RuntimeInit.applicationInit(targetSdkVersion, disabledCompatChanges, argv,
classLoader);
}
连接biander 驱动 nativeZygoteInit
/frameworks/base/core/jni/AndroidRuntime.cpp
int register_com_android_internal_os_ZygoteInit_nativeZygoteInit(JNIEnv* env)
{
const JNINativeMethod methods[] = {
{ "nativeZygoteInit", "()V",
(void*) com_android_internal_os_ZygoteInit_nativeZygoteInit },
};
=====
static AndroidRuntime* gCurRuntime = NULL;
static void com_android_internal_os_ZygoteInit_nativeZygoteInit(JNIEnv* env, jobject clazz)
{
gCurRuntime->onZygoteInit();
}
AndroidRuntime 的 onZygoteInit 方法
/frameworks/base/cmds/app_process/app_main.cpp
class AppRuntime : public AndroidRuntime
{
public:
AppRuntime(char* argBlockStart, const size_t argBlockLength)
: AndroidRuntime(argBlockStart, argBlockLength)
, mClass(NULL)
{
}
virtual void onZygoteInit()
{
sp<ProcessState> proc = ProcessState::self();
ALOGV("App process: starting thread pool.
");
proc->startThreadPool();
}
/frameworks/native/libs/binder/ProcessState.cpp
创建binder 主线程
void ProcessState::startThreadPool()
{
AutoMutex _l(mLock);
if (!mThreadPoolStarted) {
mThreadPoolStarted = true;
spawnPooledThread(true);
}
}
=====
void ProcessState::spawnPooledThread(bool isMain)
{
if (mThreadPoolStarted) {
String8 name = makeBinderThreadName();
ALOGV("Spawning new pooled thread, name=%s
", name.string());
sp<Thread> t = sp<PoolThread>::make(isMain);
t->run(name.string());
}
}
1-3)执行父进程方法 handleParentProc,通知子进程的pid 号
private void handleParentProc(int pid, FileDescriptor pipeFd) {
if (pid > 0) {
setChildPgid(pid);
}
boolean usingWrapper = false;
if (pipeFd != null && pid > 0) {
int innerPid = -1;
try {
。。。。。。
try {
mSocketOutStream.writeInt(pid);
mSocketOutStream.writeBoolean(usingWrapper);
} catch (IOException ex) {
throw new IllegalStateException("Error writing to command socket", ex);
}
}
3. 应用进程初始化流程
/frameworks/base/core/java/android/app/ActivityThread.java
public static void main(String[] args) {
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "ActivityThreadMain");
// 开启应用的主线程
Looper.prepareMainLooper();
// 创建 ActivityThread 对象,然后执行 attach 方法
ActivityThread thread = new ActivityThread();
thread.attach(false, startSeq);
if (sMainThreadHandler == null) {
sMainThreadHandler = thread.getHandler();
}
// 循环
Looper.loop();
throw new RuntimeException("Main thread loop unexpectedly exited");
}
创建 ActivityThread 对象,然后执行 attach 方法
@UnsupportedAppUsage
ActivityThread() {
mResourcesManager = ResourcesManager.getInstance();
}
=======
private void attach(boolean system, long startSeq) {
sCurrentActivityThread = this;
mConfigurationController = new ConfigurationController(this);
mSystemThread = system;
// 不是 system 进程
if (!system) {
android.ddm.DdmHandleAppName.setAppName("<pre-initialized>",
UserHandle.myUserId());
RuntimeInit.setApplicationObject(mAppThread.asBinder());
final IActivityManager mgr = ActivityManager.getService();
try {
mgr.attachApplication(mAppThread, startSeq);
} catch (RemoteException ex) {
throw ex.rethrowFromSystemServer();
}
/// mAppThread 为:
final ApplicationThread mAppThread = new ApplicationThread();
// ApplicationThread 继承了 Stub 表明可以进程间通信
private class ApplicationThread extends IApplicationThread.Stub {
ActivityThread 管理着主线程,与 system 进程 的ams 交互。实现方式是:attachApplication(mAppThread,应用进程使用AMS需要拿到AMS的句柄IActivityManager,而系统需要通知应用和管理应用的生命周期,所以也需要持有应用进程的binder句柄IApplicationThread。
/frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
4638 public final void attachApplication(IApplicationThread thread, long startSeq) {
4639 if (thread == null) {
4640 throw new SecurityException("Invalid application interface");
4641 }
4642 synchronized (this) {
4643 int callingPid = Binder.getCallingPid();
4644 final int callingUid = Binder.getCallingUid();
4645 final long origId = Binder.clearCallingIdentity();
4646 attachApplicationLocked(thread, callingPid, callingUid, startSeq);
4647 Binder.restoreCallingIdentity(origId);
4648 }
==========
ProcessList.java
===== startProcessLocked 在fork 一个应用进程之后,保存这个 pid 值:handleProcessStartedLocked =====
/frameworks/base/services/core/java/com/android/server/am/ProcessList.java
@GuardedBy("mService")
boolean handleProcessStartedLocked(ProcessRecord app, int pid, boolean usingWrapper,
long expectedStartSeq, boolean procAttached) {
mPendingStarts.remove(expectedStartSeq);
final String reason = isProcStartValidLocked(app, expectedStartSeq);
if (reason != null) {
Slog.w(TAG_PROCESSES, app + " start not valid, killing pid=" +
pid
+ ", " + reason);
app.setPendingStart(false);
// 如果判断该进程是无效的,则调用native 层方法kill 这个进程
killProcessQuiet(pid);
Process.killProcessGroup(app.uid, app.getPid());
noteAppKill(app, ApplicationExitInfo.REASON_OTHER,
ApplicationExitInfo.SUBREASON_INVALID_START, reason);
return false;
}
mService.mBatteryStatsService.noteProcessStart(app.processName, app.info.uid);
checkSlow(app.getStartTime(), "startProcess: done updating battery stats");
// 打印对应的log
EventLog.writeEvent(EventLogTags.AM_PROC_START,
UserHandle.getUserId(app.getStartUid()), pid, app.getStartUid(),
app.processName, app.getHostingRecord().getType(),
app.getHostingRecord().getName() != null ? app.getHostingRecord().getName() : "");
try {
AppGlobals.getPackageManager().logAppProcessStartIfNeeded(app.info.packageName,
app.processName, app.uid, app.getSeInfo(), app.info.sourceDir, pid);
} catch (RemoteException ex) {
// Ignore
}
Watchdog.getInstance().processStarted(app.processName, pid);
checkSlow(app.getStartTime(), "startProcess: building log message");
StringBuilder buf = mStringBuilder;
buf.setLength(0);
buf.append("Start proc ");
buf.append(pid);
buf.append(':');
buf.append(app.processName);
buf.append('/');
UserHandle.formatUid(buf, app.getStartUid());
if (app.getIsolatedEntryPoint() != null) {
buf.append(" [");
buf.append(app.getIsolatedEntryPoint());
buf.append("]");
}
buf.append(" for ");
buf.append(app.getHostingRecord().getType());
if (app.getHostingRecord().getName() != null) {
buf.append(" ");
buf.append(app.getHostingRecord().getName());
}
mService.reportUidInfoMessageLocked(TAG, buf.toString(), app.getStartUid());
synchronized (mProcLock) {
app.setPid(pid);
app.setUsingWrapper(usingWrapper);
app.setPendingStart(false);
}
checkSlow(app.getStartTime(), "startProcess: starting to update pids map");
ProcessRecord oldApp;
synchronized (mService.mPidsSelfLocked) {
oldApp = mService.mPidsSelfLocked.get(pid);
}
// If there is already an app occupying that pid that hasn't been cleaned up
if (oldApp != null && !app.isolated) {
// Clean up anything relating to this pid first
Slog.wtf(TAG, "handleProcessStartedLocked process:" + app.processName
+ " startSeq:" + app.getStartSeq()
+ " pid:" + pid
+ " belongs to another existing app:" + oldApp.processName
+ " startSeq:" + oldApp.getStartSeq());
mService.cleanUpApplicationRecordLocked(oldApp, pid, false, false, -1,
true /*replacingPid*/, false /* fromBinderDied */);
}
// 给 ActivityManagerService 管理
mService.addPidLocked(app);
synchronized (mService.mPidsSelfLocked) {
if (!procAttached) {
Message msg = mService.mHandler.obtainMessage(PROC_START_TIMEOUT_MSG);
msg.obj = app;
mService.mHandler.sendMessageDelayed(msg, usingWrapper
? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT);
}
}
checkSlow(app.getStartTime(), "startProcess: done updating pids map");
return true;
}
打印对应的log:
EventLog.writeEvent(EventLogTags.AM_PROC_START,
UserHandle.getUserId(app.getStartUid()), pid, app.getStartUid(),
app.processName, app.getHostingRecord().getType(),
app.getHostingRecord().getName() != null ? app.getHostingRecord().getName() : "");
// 0:看log 全是0
// 1238 是pid进程号
// app.getStartUid 传给zygote 的uid为 :1001
// 应用名字processName:com.android.phone
am_proc_start: [0,1238,1001,com.android.phone,added application,com.android.phone]
// 给 ActivityManagerService 管理
mService.addPidLocked(app);
/frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
885 @GuardedBy("this")
886 void addPidLocked(ProcessRecord app) {
887 final int pid = app.getPid();
888 synchronized (mPidsSelfLocked) {
889 mPidsSelfLocked.doAddInternal(pid, app);
890 }
891 synchronized (sActiveProcessInfoSelfLocked) {
892 if (app.processInfo != null) {
893 sActiveProcessInfoSelfLocked.put(pid, app.processInfo);
894 } else {
895 sActiveProcessInfoSelfLocked.remove(pid);
896 }
897 }
898 mAtmInternal.onProcessMapped(pid, app.getWindowProcessController());
899 }
深入理解Android之应用程序进程启动流程(Android 10) - 掘金
Android Framework(三)——应用程序进程启动流程 - Sukai's Blog - Android Developer