判断当前是否正在处理广播,true ,则返回等待;发送空消息processNextBroadcast
public void scheduleBroadcastsLocked() {
if (mBroadcastsScheduled) {
return;
}
mHandler.sendMessage(mHandler.obtainMessage(BROADCAST_INTENT_MSG, this));
mBroadcastsScheduled = true;
}
private final class BroadcastHandler extends Handler {
@Override
public void handleMessage(Message msg) {
switch(msg.what) {
case BROADCAST_INTENT_MSG: {
if (DEBUG_BROADCAST) Slog.v(
TAG_BROADCAST, "Received BROADCAST_INTENT_MSG");
processNextBroadcast(true);
} break;
...
}
}
}
我们在前文已经说过,==所有的静态receiver都是串行处理的==,而动态receiver则会按照发广播时指定的方式,==进行“并行”或“串行”处理
能够并行处理的广播,其对应的若干receiver一定都已经存在了,不会牵扯到启动新进程的操作,所以可以在一个while循环中,一次性全部deliver,分给对应的进程即可。
处理Queue中的并行部分,仅需要遍例mParallelBroadcasts中的每一个BroadcastRecord以及其中的receivers列表.对于平行广播而言receivers每个节点都是BroadcastFilter,只需要将广播分发下去即可:
// First, deliver any non-serialized broadcasts right away.
while (mParallelBroadcasts.size() > 0) {
r = mParallelBroadcasts.remove(0);
r.dispatchTime = SystemClock.uptimeMillis();
r.dispatchClockTime = System.currentTimeMillis();
final int N = r.receivers.size();
for (int i=0; i
Object target = r.receivers.get(i);
// BroadcastFiler
deliverToRegisteredReceiverLocked(r, (BroadcastFilter)target, false, i);
}
addBroadcastToHistoryLocked(r);
}
private final void deliverToRegisteredReceiverLocked(BroadcastRecord r,
BroadcastFilter filter,
boolean ordered)
{
// 权限检查
. . . . . .
. . . . . .
if (!skip)
{
if (ordered)
{
r.receiver = filter.receiverList.receiver.asBinder();
r.curFilter = filter;
filter.receiverList.curBroadcast = r;
r.state = BroadcastRecord.CALL_IN_RECEIVE;
if (filter.receiverList.app != null)
{
r.curApp = filter.receiverList.app;
filter.receiverList.app.curReceiver = r;
mService.updateOomAdjLocked();
}
}
. . . . . .
performReceiveLocked(filter.receiverList.app,
filter.receiverList.receiver,
new Intent(r.intent), r.resultCode,
r.resultData, r.resultExtras,
r.ordered, r.initialSticky);
if (ordered)
{
r.state = BroadcastRecord.CALL_DONE_RECEIVE;
}
. . . . . .
}
检查对应的BroadcastFilter是否有权限处理该intent,否则就将deliver[i] = BroadcastRecord.DELIVERY_SKIPPED
private static void performReceiveLocked(ProcessRecord app, IIntentReceiver receiver,
Intent intent, int resultCode, String data, Bundle extras,
boolean ordered, boolean sticky) throws RemoteException
{
// Send the intent to the receiver asynchronously using one-way binder calls.
if (app != null && app.thread != null)
{
// If we have an app thread, do the call through that so it is
// correctly ordered with other one-way calls.
// app.thread 调用Reciever APP所在主线程的schedule方法
app.thread.scheduleRegisteredReceiver(receiver, intent, resultCode,
data, extras, ordered, sticky);
}
else
{
receiver.performReceive(intent, resultCode, data, extras, ordered, sticky);
}
}
终于通过app.thread向用户进程传递语义了。注意scheduleRegisteredReceiver()的receiver参数,它对应的就是前文所说的ReceiverDispatcher的Binder实体——InnerReceiver了;调用到这里则是进入到每个APP的进程中了
frameworks/base/core/java/android/app/ActivityThread.java
// This function exists to make sure all receiver dispatching is
// correctly ordered, since these are one-way calls and the binder driver
// applies transaction ordering per object for such calls.
public void scheduleRegisteredReceiver(IIntentReceiver receiver, Intent intent,
int resultCode, String dataStr, Bundle extras, boolean ordered,
boolean sticky) throws RemoteException
{
//receiver 的实现类即是ReceiverDispatcher.InnerReceiver
receiver.performReceive(intent, resultCode, dataStr, extras, ordered, sticky);
}
==终于走到ReceiverDispatcher的InnerReceiver了:==
static final class ReceiverDispatcher
{
final static class InnerReceiver extends IIntentReceiver.Stub
{
. . . . . .
. . . . . .
public void performReceive(Intent intent, int resultCode,
String data, Bundle extras,
boolean ordered, boolean sticky)
{
LoadedApk.ReceiverDispatcher rd = mDispatcher.get();
. . . . . .
if (rd != null) {
rd.performReceive(intent, resultCode, data, extras,
ordered, sticky);
}
. . . . . .
}
}
. . . . . .
public void performReceive(Intent intent, int resultCode,
String data, Bundle extras,
boolean ordered, boolean sticky)
{
. . . . . .
Args args = new Args(intent, resultCode, data, extras, ordered, sticky);
// 此处的ActivityThread则是每个APP的main thread.
// 将此Runnable对象放入主线程队列等待处理
if (!mActivityThread.post(args)) // 请注意这一句!
{
if (mRegistered && ordered)
{
IActivityManager mgr = ActivityManagerNative.getDefault();
if (ActivityThread.DEBUG_BROADCAST) Slog.i(ActivityThread.TAG,
"Finishing sync broadcast to " + mReceiver);
args.sendFinished(mgr);
}
}
}
}
轮到Args执行
final class Args extends BroadcastReceiver.PendingResult implements Runnable
{
. . . . . .
. . . . . .
public void run()
{
final BroadcastReceiver receiver = mReceiver;
. . . . . .
try {
ClassLoader cl = mReceiver.getClass().getClassLoader();
intent.setExtrasClassLoader(cl);
intent.prepareToEnterProcess();
setExtrasClassLoader(cl);
receiver.setPendingResult(this);
// 通过反射调用onReceiver
receiver.onReceive(mContext, intent);
} catch (Exception e) {
if (mRegistered && ordered) {
if (ActivityThread.DEBUG_BROADCAST) Slog.i(ActivityThread.TAG,
"Finishing failed broadcast to " + mReceiver);
sendFinished(mgr);
}
if (mInstrumentation == null ||
!mInstrumentation.onException(mReceiver, e)) {
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
throw new RuntimeException(
"Error receiving broadcast " + intent
+ " in " + mReceiver, e);
}
}
if (receiver.getPendingResult() != null) {
finish();
}
. . . . . .
}
}
有序广播和静态广播都是以串行的方式分发出去
// Now take care of the next serialized one...
// If we are waiting for a process to come up to handle the next
// broadcast, then do nothing at this point. Just in case, we
// check that the process we're waiting for still exists.
//
if (mPendingBroadcast != null) {
boolean isDead;
synchronized (mService.mPidsSelfLocked) {
ProcessRecord proc = mService.mPidsSelfLocked.get(mPendingBroadcast.curApp.pid);
isDead = proc == null || proc.crashing;
}
if (!isDead) {
// It's still alive, so keep waiting
return;
} else {
mPendingBroadcast.state = BroadcastRecord.IDLE;
mPendingBroadcast.nextReceiver = mPendingBroadcastRecvIndex;
mPendingBroadcast = null;
}
}
do {
// 总是从集合第一个获取
r = mOrderedBroadcasts.get(0);
//超时处理
//最后一个receiver处理完后,重新get(0)
{
cancelBroadcastTimeoutLocked();
// ... and on to the next...
addBroadcastToHistoryLocked(r);
if (r.intent.getComponent() == null && r.intent.getPackage() == null
&& (r.intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) {
// This was an implicit broadcast... let's record it for posterity.
mService.addBroadcastStatLocked(r.intent.getAction(), r.callerPackage,
r.manifestCount, r.manifestSkipCount, r.finishTime-r.dispatchTime);
}
// 当前Intent已经完全发送结束,移除,进入下一个节点
mOrderedBroadcasts.remove(0);
continue;
}
} while (r != null)
// Get the next receiver...
// 每个intent对应一个Receiver集合,每有一个receiver接收,都会同步其索引
int recIdx = r.nextReceiver++; // after nextReceiver = 1, recIdx = 0
// Keep track of when this receiver started, and make sure there
// is a timeout message pending to kill it if need be.
// 开始接收,此时记录接收时间
r.receiverTime = SystemClock.uptimeMillis();
if (recIdx == 0) {
// 如果recIdx = 0,表示开始分发intent
// 此时记录分发的时间
r.dispatchTime = r.receiverTime;
r.dispatchClockTime = System.currentTimeMillis();
}
// 处理超时的代码
if (! mPendingBroadcastTimeoutMessage) {
long timeoutTime = r.receiverTime + mTimeoutPeriod;
setBroadcastTimeoutLocked(timeoutTime);
}
final Object nextReceiver = r.receivers.get(recIdx);
// 有序广播中的动态接收者,分发流程与普通动态广播的分发流程基本一致
if (nextReceiver instanceof BroadcastFilter) {
// Simple case: this is a registered receiver who gets
// a direct call.
BroadcastFilter filter = (BroadcastFilter)nextReceiver;
deliverToRegisteredReceiverLocked(r, filter, r.ordered, recIdx);
if (r.receiver == null || !r.ordered) {
// The receiver has already finished, so schedule to
// process the next one.
r.state = BroadcastRecord.IDLE;
scheduleBroadcastsLocked();
} else {
if (brOptions != null && brOptions.getTemporaryAppWhitelistDuration() > 0) {
scheduleTempWhitelistLocked(filter.owningUid,
brOptions.getTemporaryAppWhitelistDuration(), r);
}
}
return;
}
// 此时才是真正处理静态注册的receiver
// Hard case: need to instantiate the receiver, possibly
// starting its application process to host it.
ResolveInfo info = (ResolveInfo)nextReceiver;
ComponentName component = new ComponentName(
info.activityInfo.applicationInfo.packageName,
info.activityInfo.name);
...
// 这里将有一系统的权限检查,若是不合法则会skip
...
String targetProcess = info.activityInfo.processName;
ProcessRecord app = mService.getProcessRecordLocked(targetProcess,info.activityInfo.applicationInfo.uid, false);
// 需要skip的receiver,修改状态且重发下一个
if (skip) {
r.delivery[recIdx] = BroadcastRecord.DELIVERY_SKIPPED;
r.receiver = null;
r.curFilter = null;
r.state = BroadcastRecord.IDLE;
scheduleBroadcastsLocked();
return;
}
// 修改状态,并在BroadcastRecord节点中保存当前的receiver
r.delivery[recIdx] = BroadcastRecord.DELIVERY_DELIVERED;
r.state = BroadcastRecord.APP_RECEIVE;
r.curComponent = component;
r.curReceiver = info.activityInfo;
// 如果广播正在发送的话,这个receiver所在APK是不可被禁用的!!!
// Broadcast is being executed, its package can't be stopped.
try {
AppGlobals.getPackageManager().setPackageStoppedState(
r.curComponent.getPackageName(), false, UserHandle.getUserId(r.callingUid));
} catch (RemoteException e) {
} catch (IllegalArgumentException e) {
Slog.w(TAG, "Failed trying to unstop package "
+ r.curComponent.getPackageName() + ": " + e);
}
// 若是receiver所在进程已启动
if (app != null && app.thread != null) {
try {
app.addPackage(info.activityInfo.packageName,
info.activityInfo.applicationInfo.versionCode, mService.mProcessStats);
// 直接分发给指定进程
processCurBroadcastLocked(r, app);
return;
} catch (RemoteException e) {
Slog.w(TAG, "Exception when sending broadcast to "
+ r.curComponent, e);
} catch (RuntimeException e) {
Slog.wtf(TAG, "Failed sending broadcast to "
+ r.curComponent + " with " + r.intent, e);
// If some unexpected exception happened, just skip
// this broadcast. At this point we are not in the call
// from a client, so throwing an exception out from here
// will crash the entire system instead of just whoever
// sent the broadcast.
logBroadcastReceiverDiscardLocked(r);
finishReceiverLocked(r, r.resultCode, r.resultData,
r.resultExtras, r.resultAbort, false);
scheduleBroadcastsLocked();
// We need to reset the state if we failed to start the receiver.
r.state = BroadcastRecord.IDLE;
return;
}
// If a dead object exception was thrown -- fall through to
// restart the application.
}
// receiver所在进程不可用,启动该进程
if ((r.curApp=mService.startProcessLocked(targetProcess,
info.activityInfo.applicationInfo, true,
r.intent.getFlags() | Intent.FLAG_FROM_BACKGROUND,
"broadcast", r.curComponent,
(r.intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0, false, false))
== null) {
// Ah, this recipient is unavailable. Finish it if necessary,
// and mark the broadcast record as ready for the next.
logBroadcastReceiverDiscardLocked(r);
finishReceiverLocked(r, r.resultCode, r.resultData,
r.resultExtras, r.resultAbort, false);
scheduleBroadcastsLocked();
r.state = BroadcastRecord.IDLE;
return;
}
// 将此节点保存在pendingBroadcast 以便进程启动后即时发送,
// 进入到这里,表示该receiver的进程未启动,需要等其启动后再发送
mPendingBroadcast = r;
mPendingBroadcastRecvIndex = recIdx;
如果进程已经存在,只需要直接发送到该进程即可
private final void processCurBroadcastLocked(BroadcastRecord r,
ProcessRecord app) throws RemoteException
{
. . . . . .
r.receiver = app.thread.asBinder();
r.curApp = app;
app.curReceiver = r;
. . . . . .
. . . . . .
app.thread.scheduleReceiver(new Intent(r.intent), r.curReceiver,
mService.compatibilityInfoForPackageLocked(r.curReceiver.applicationInfo),
r.resultCode, r.resultData, r.resultExtras, r.ordered);
. . . . . .
started = true;
. . . . . .
}
ActivityThread.java
==当handleReceiver后,通过反射创建出BroadcastReceiver,调用它的onreceiver方法,到此处,BroadcastReceiver就可以收到此广播了==
void scheduleReceiver(Intent intent, ActivityInfo info,
CompatibilityInfo compatInfo,
int resultCode, String data,
Bundle extras, boolean sync)
throws RemoteException;
case RECEIVER:
...
handleReceiver((ReceiverData)msg.obj);
...
break;
private void handleReceiver(ReceiverData data)
{
. . . . . .
IActivityManager mgr = ActivityManagerNative.getDefault();
BroadcastReceiver receiver;
try {
java.lang.ClassLoader cl = packageInfo.getClassLoader();
data.intent.setExtrasClassLoader(cl);
data.setExtrasClassLoader(cl);
receiver = (BroadcastReceiver)cl.loadClass(component).newInstance();
} catch (Exception e) {
. . . . . .
}
try {
. . . . . .
receiver.setPendingResult(data);
// 反射回调
receiver.onReceive(context.getReceiverRestrictedContext(), data.intent);
} catch (Exception e) {
. . . . . .
} finally {
sCurrentBroadcastIntent.set(null);
}
//
if (receiver.getPendingResult() != null) {
data.finish();
}
}
如果进程不存在,需要等待receiver所在进程启动后再次触发;启动的过程是异步的,可能很耗时,所以要把BroadcastRecord节点记入mPendingBroadcast。
现在我们回过头来看,在目标进程尚未启动的情况下,是如何完成递送的。刚刚我们已经看到调用startProcessLocked()的句子了,只要不出问题,目标进程成功启动后就会调用AMS的attachApplication()。
有关attachApplication()的详情,请参考其他关于AMS的文档,此处我们只需知道它里面又会调用attachApplicationLocked()函数。
private final boolean attachApplicationLocked(IApplicationThread thread, int pid)
...
// Check if a next-broadcast receiver is in this process...
if (!badApp && isPendingBroadcastProcessLocked(pid)) {
try {
didSomething = sendPendingBroadcastsLocked(app);
} catch (Exception e) {
// If the app died trying to launch the receiver we declare it 'bad'
badApp = true;
}
}
...
public boolean sendPendingBroadcastsLocked(ProcessRecord app) {
boolean didSomething = false;
final BroadcastRecord br = mPendingBroadcast;
if (br != null && br.curApp.pid == app.pid) {
try {
mPendingBroadcast = null;
processCurBroadcastLocked(br, app);
didSomething = true;
} catch (Exception e) {
. . . . . .
}
}
return didSomething;
}
可以看到,既然目标进程已经成功启动了,那么mPendingBroadcast = null了。接着,sendPendingBroadcastsLocked()会调用前文刚刚阐述的processCurBroadcastLocked(),其内再通过app.thread.scheduleReceiver(),将语义发送到用户进程,完成真正的广播递送。这部分在上一小节已有阐述,这里就不多说了。
它们的意思是,如果新启动的进程就是刚刚mPendingBroadcast所记录的进程的话,此时AMS就会执行sendPendingBroadcastsLocked(app)一句。