1、相关代码

\frameworks\base\core\java\android\app\ContextImpl.java

\frameworks\base\core\java\android\app\LoadedApk.java

\frameworks\base\services\core\java\com\android\server\am\ActivityManagerService.java

\frameworks\base\services\core\java\com\android\server\am\BroadcastQueue.java

\frameworks\base\core\java\android\app\BroadcastOptions.java

\frameworks\base\services\core\java\com\android\server\am\ReceiverList.java

\frameworks\base\services\core\java\com\android\server\IntentResolver.java

\frameworks\base\services\core\java\com\android\server\am\BroadcastFilter.java

2.1广播动态注册流程

简要流程如上图,注册过程主要通过AMS调用,将注册的intentFilter添加到BroadcastFilter中的队列mFilters中,同时将IIntentReceiver对象添加到mRegisteredReceivers中。

public Intent registerReceiver(IApplicationThread caller, String callerPackage,        IIntentReceiver receiver, IntentFilter filter, String permission, int userId,        int flags) {    ArrayList stickyIntents = null;    //...... 对调用者,instantApp、flag等做检查    //......处理粘性广播,将粘性广播加到粘性广播队列中    synchronized (this) {       //从现有队列中查找本地的IIntentReceiver        ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder());        if (rl == null) {            //如果当前没有,则新建,并且每个应用只能创建1000个receiver超过会报异常            rl = new ReceiverList(this, callerApp, callingPid, callingUid,                    userId, receiver);            //......            mRegisteredReceivers.put(receiver.asBinder(), rl);        } else if (rl.uid != callingUid) {            //跟已有uid不同报异常        } else if (rl.pid != callingPid) {           //跟已有pid不同报异常        } else if (rl.userId != userId) {            //跟已有userId不同报异常        }        BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage,                permission, callingUid, userId, instantApp, visibleToInstantApps);        if (rl.containsFilter(filter)) {            //intentfilter已存在,不再重复添加        } else {            rl.add(bf);            //添加intentFilter到mReceiverResolver表中            mReceiverResolver.addFilter(bf);        }        if (allSticky != null) {            //发送粘性广播            for (int i = 0; i < stickyCount; i++) {                Intent intent = allSticky.get(i);                BroadcastQueue queue = broadcastQueueForIntent(intent);                BroadcastRecord r = new BroadcastRecord(queue, intent, null,                        null, -1, -1, false, null, null, OP_NONE, null, receivers,                        null, 0, null, null, false, true, true, -1);                queue.enqueueParallelBroadcastLocked(r);                queue.scheduleBroadcastsLocked();            }        }     //......    }}

注册过程主要涉及两个重要标量:

final HashMap mRegisteredReceivers = new HashMap<>();final IntentResolver mReceiverResolver        = new IntentResolver() {    //......};
final class ReceiverList extends ArrayList        implements IBinder.DeathRecipient {    final ActivityManagerService owner;    public final IIntentReceiver receiver;    public final ProcessRecord app;    public final int pid;    public final int uid;    public final int userId;    BroadcastRecord curBroadcast = null;    boolean linkedToDeath = false;
final class BroadcastFilter extends IntentFilter {    // Back-pointer to the list this filter is in.    final ReceiverList receiverList;    final String packageName;    final String requiredPermission;    final int owningUid;    final int owningUserId;    final boolean instantApp;    final boolean visibleToInstantApp;

 

ReceiverList类相当于我们代码中的具体receiver,BroadcastFilter则相当于我们在注册广播时候施使用的intentFilter,一个进程不能注册超过1000个receiver,每个receiver中可以有多个BroadcastFilte,每次注册时候,先查找该receiver是否已经存在于当前的mRegisteredReceivers列表中了,如果已经存在,则检查这次注册者的pid、uid、userId是否跟已经存在的receiver中的这三个值相同,不同则抛出异常。

然后根据现有的或者新生成的ReceiverList名称rl,生成BroadcastFilter,如果该rl中已经包含给intentFilter,表示该已经存在了相同的receiver,包含了相同的intentfilter,不用再重复注册了,如果不包含,则将新生成的BroadcastFilter加入到rl中,将新建的BroadcastFilter加入到mReceiverResolver中。

 

解除注册,最重要的就是从这两个表中移出对象:

void removeReceiverLocked(ReceiverList rl) {    mRegisteredReceivers.remove(rl.receiver.asBinder());    for (int i = rl.size() - 1; i >= 0; i--) {        mReceiverResolver.removeFilter(rl.get(i));    }}

2.2 广播发送流程

 

广播发送简略流程如上图所示,在进行了一些列的检查,包括参数,调用者,广播flag,特殊action,系统广播,等之后,从mReceiverResolver中检索出广播接收者,然后按照优先无序广播,之后发送有序广播的顺序,依次调用所有接收者的IIntentReceiver中的onReceive中。

两个广播发送序列,前台序列、后台序列

BroadcastQueue mFgBroadcastQueue;BroadcastQueue mBgBroadcastQueue;

 

public final int broadcastIntent(IApplicationThread caller,        Intent intent, String resolvedType, IIntentReceiver resultTo,        int resultCode, String resultData, Bundle resultExtras,        String[] requiredPermissions, int appOp, Bundle bOptions,        boolean serialized, boolean sticky, int userId) {    enforceNotIsolatedCaller("broadcastIntent");    synchronized(this) {        intent = verifyBroadcastLocked(intent);        final ProcessRecord callerApp = getRecordForAppLocked(caller);        final int callingPid = Binder.getCallingPid();        final int callingUid = Binder.getCallingUid();        final long origId = Binder.clearCallingIdentity();        int res = broadcastIntentLocked(callerApp,                callerApp != null ? callerApp.info.packageName : null,                intent, resolvedType, resultTo, resultCode, resultData, resultExtras,                requiredPermissions, appOp, bOptions, serialized, sticky,                callingPid, callingUid, userId);        Binder.restoreCallingIdentity(origId);        return res;    }}

 

final int broadcastIntentLocked(ProcessRecord callerApp,        String callerPackage, Intent intent, String resolvedType,        IIntentReceiver resultTo, int resultCode, String resultData,        Bundle resultExtras, String[] requiredPermissions, int appOp, Bundle bOptions,        boolean ordered, boolean sticky, int callingPid, int callingUid, int userId) {                    //......flag 相关处理        if (callerInstantApp) {            intent.setFlags(intent.getFlags() & ~Intent.FLAG_RECEIVER_VISIBLE_TO_INSTANT_APPS);        }         intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES);        if (!mProcessesReady && (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) {            intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);        }         //......保护广播检测,非系统应用发送保护广播会报错        isProtectedBroadcast = AppGlobals.getPackageManager().isProtectedBroadcast(action);         if (!isCallerSystem) {                if (isProtectedBroadcast) {                    String msg = "Permission Denial: not allowed to send broadcast "                    + action + " from pid="                    + callingPid + ", uid=" + callingUid;                Slog.w(TAG, msg);                throw new SecurityException(msg);            //......        }             //......处理特殊action,如:ACTION_UID_REMOVED,ACTION_PACKAGES_UNSUSPENDED,ACTION_PACKAGE_REPLACED等         //如果发送的是粘性广播if (sticky) {    //检查android.Manifest.permission.BROADCAST_STICKY权限,没有则抛出异常    if (checkPermission(android.Manifest.permission.BROADCAST_STICKY,        callingPid, callingUid)        != PackageManager.PERMISSION_GRANTED) {        String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid="            + callingPid + ", uid=" + callingUid            + " requires " + android.Manifest.permission.BROADCAST_STICKY;        Slog.w(TAG, msg);        throw new SecurityException(msg);    }    //强制粘性广播必须带权限发送,否则直接返回    if (requiredPermissions != null && requiredPermissions.length > 0) {        Slog.w(TAG, "Can't broadcast sticky intent " + intent                + " and enforce permissions " + Arrays.toString(requiredPermissions));        return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION;    }    //强制粘性广播不允许指定接收组件,否则抛出异常    if (intent.getComponent() != null) {        throw new SecurityException(                "Sticky broadcasts can't target a specific component");    }    //检查发送用户组   //......    for (i = 0; i < stickiesCount; i++) {        if (intent.filterEquals(list.get(i))) {            // 该粘性广播已经存在,直接替换            list.set(i, new Intent(intent));            break;        }    }    if (i >= stickiesCount) {        //不存在,则添加到队列中        list.add(new Intent(intent));    }    }        //一下两个列表用于装载广播接收者    List receivers = null;    List registeredReceivers = null;    //......    //检索广播接收对象    registeredReceivers = mReceiverResolver.queryIntent(intent,        resolvedType, false /*defaultOnly*/, userId);    //优先发送无序广播 ,ordered为false表示无序       int NR = registeredReceivers != null ? registeredReceivers.size() : 0;    if (!ordered && NR > 0) {        final BroadcastQueue queue = broadcastQueueForIntent(intent);        BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp,            callerPackage, callingPid, callingUid, callerInstantApp, resolvedType,            requiredPermissions, appOp, brOptions, registeredReceivers, resultTo,            resultCode, resultData, resultExtras, ordered, sticky, false, userId);    // ......    if (!replaced) {        //发送广播        queue.enqueueParallelBroadcastLocked(r);        queue.scheduleBroadcastsLocked();    }    registeredReceivers = null;    NR = 0;    }      //......发送有序广播    BroadcastQueue queue = broadcastQueueForIntent(intent);    BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp,        callerPackage, callingPid, callingUid, callerInstantApp, resolvedType,        requiredPermissions, appOp, brOptions, receivers, resultTo, resultCode,        resultData, resultExtras, ordered, sticky, false, userId);    queue.enqueueOrderedBroadcastLocked(r);    queue.scheduleBroadcastsLocked();         } 

BroadcastQueue中两个列表,无序广播队列、有序广播队列。

final ArrayList mParallelBroadcasts = new ArrayList<>();final ArrayList mOrderedBroadcasts = new ArrayList<>();

如以上分析,分别将有序广播和无序广播加入到不同的两个队列中。

public void enqueueParallelBroadcastLocked(BroadcastRecord r) {    mParallelBroadcasts.add(r);    enqueueBroadcastHelper(r);}public void enqueueOrderedBroadcastLocked(BroadcastRecord r) {    mOrderedBroadcasts.add(r);    enqueueBroadcastHelper(r);}

发送消息进入广播发送流程

public void scheduleBroadcastsLocked() {    if (mBroadcastsScheduled) {        return;    }    mHandler.sendMessage(mHandler.obtainMessage(BROADCAST_INTENT_MSG, this));    mBroadcastsScheduled = true;}

广播在同步方法块中进行

final void processNextBroadcast(boolean fromMsg) {    synchronized (mService) {        processNextBroadcastLocked(fromMsg, false);    }}

processNextBroadcastLocked方法详细流程如下:

final void processNextBroadcastLocked(boolean fromMsg, boolean skipOomAdj) {    BroadcastRecord r;    if (DEBUG_BROADCAST) Slog.v(TAG_BROADCAST, "processNextBroadcast ["            + mQueueName + "]: "            + mParallelBroadcasts.size() + " parallel broadcasts, "            + mOrderedBroadcasts.size() + " ordered broadcasts");    mService.updateCpuStats();    if (fromMsg) {        mBroadcastsScheduled = false;    }    // 先将无序广播发送掉    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 0) {            synchronized (mService.mPidsSelfLocked) {                ProcessRecord proc = mService.mPidsSelfLocked.get(                        mPendingBroadcast.curApp.pid);                isDead = proc == null || proc.crashing;            }        } else {            final ProcessRecord proc = mService.mProcessNames.get(                    mPendingBroadcast.curApp.processName, mPendingBroadcast.curApp.uid);            isDead = proc == null || !proc.pendingStart;        }        if (!isDead) {            //此处无法理为什么进程存在的时候要返回            return;        } else {        ......            mPendingBroadcast.state = BroadcastRecord.IDLE;            mPendingBroadcast.nextReceiver = mPendingBroadcastRecvIndex;            mPendingBroadcast = null;        }    }    boolean looped = false;    do {        ......        //从有序广播队列中获取接收队列        r = mOrderedBroadcasts.get(0);        int numReceivers = (r.receivers != null) ? r.receivers.size() : 0;        if (mService.mProcessesReady && r.dispatchTime > 0) {            long now = SystemClock.uptimeMillis();            //如果现在距离dispatch时候的时间超过了mTimeoutPeriod的两倍,则进入超时ANR异常            //mTimeoutPeriod定义:前天广播10秒,后台广播60秒            if ((numReceivers > 0) &&                    (now > r.dispatchTime + (2*mTimeoutPeriod*numReceivers))) {                broadcastTimeoutLocked(false);                 forceReceive = true;                r.state = BroadcastRecord.IDLE;            }        }        ......            return;        }        if (r.receivers == null || r.nextReceiver >= numReceivers                || r.resultAbort || forceReceive) {                        if (r.resultTo != null) {                try {                   //通知到接收者的onrecevier中                    performReceiveLocked(r.callerApp, r.resultTo,                        new Intent(r.intent), r.resultCode,                        r.resultData, r.resultExtras, false, false, r.userId);                                       r.resultTo = null;                } catch (RemoteException e) {                }            }           ......            mOrderedBroadcasts.remove(0);            r = null;            looped = true;            continue;        }    } while (r == null);    // 得到下一个 receiver...    int recIdx = r.nextReceiver++;    // 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) {        r.dispatchTime = r.receiverTime;        r.dispatchClockTime = System.currentTimeMillis();        ......    }    if (! mPendingBroadcastTimeoutMessage) {        long timeoutTime = r.receiverTime + mTimeoutPeriod;       //设置发送超时        setBroadcastTimeoutLocked(timeoutTime);    }    final BroadcastOptions brOptions = r.options;    final Object nextReceiver = r.receivers.get(recIdx);    if (nextReceiver instanceof BroadcastFilter) {        BroadcastFilter filter = (BroadcastFilter)nextReceiver;       //发送广播        deliverToRegisteredReceiverLocked(r, filter, r.ordered, recIdx);        if (r.receiver == null || !r.ordered) {            //进入递归调用启动发送广播            scheduleBroadcastsLocked();        } else {            if (brOptions != null && brOptions.getTemporaryAppWhitelistDuration() > 0) {                scheduleTempWhitelistLocked(filter.owningUid,                        brOptions.getTemporaryAppWhitelistDuration(), r);            }        }        return;    }    //难点:需要实例化接收者,可能需要启动他们的应用用来支持这个receiver    ResolveInfo info =        (ResolveInfo)nextReceiver;    ComponentName component = new ComponentName(            info.activityInfo.applicationInfo.packageName,            info.activityInfo.name);    boolean skip = false;    //brOptions非空,并且当前targetSdkVersion小于option设置的最小值或者大于最大值,skip就为true,直接跳过    if (brOptions != null &&            (info.activityInfo.applicationInfo.targetSdkVersion                    < brOptions.getMinManifestReceiverApiLevel() ||            info.activityInfo.applicationInfo.targetSdkVersion                    > brOptions.getMaxManifestReceiverApiLevel())) {        skip = true;    }    //得到授权信息,系统或者root进程直接返回granted    int perm = mService.checkComponentPermission(info.activityInfo.permission,            r.callingPid, r.callingUid, info.activityInfo.applicationInfo.uid,            info.activityInfo.exported);    if (!skip && perm != PackageManager.PERMISSION_GRANTED) {        //不跳过,但是权限不允许,则skip置为true        skip = true;    } else if (!skip && info.activityInfo.permission != null) {        final int opCode = AppOpsManager.permissionToOpCode(info.activityInfo.permission);        if (opCode != AppOpsManager.OP_NONE                && mService.mAppOpsService.noteOperation(opCode, r.callingUid,                        r.callerPackage) != AppOpsManager.MODE_ALLOWED) {           //......permission不为空,并且appops授权检查未通过            skip = true;        }    }    if (!skip && info.activityInfo.applicationInfo.uid != Process.SYSTEM_UID &&        r.requiredPermissions != null && r.requiredPermissions.length > 0) {        for (int i = 0; i < r.requiredPermissions.length; i++) {            String requiredPermission = r.requiredPermissions[i];            try {                perm = AppGlobals.getPackageManager().                        checkPermission(requiredPermission,                                info.activityInfo.applicationInfo.packageName,                                UserHandle                                        .getUserId(info.activityInfo.applicationInfo.uid));            } catch (RemoteException e) {                perm = PackageManager.PERMISSION_DENIED;            }            if (perm != PackageManager.PERMISSION_GRANTED) {                //uid不等于SYSTEM_UID,requiredPermissions不为空,并且PMS未授权                skip = true;                break;            }            int appOp = AppOpsManager.permissionToOpCode(requiredPermission);            if (appOp != AppOpsManager.OP_NONE && appOp != r.appOp                    && mService.mAppOpsService.noteOperation(appOp,                    info.activityInfo.applicationInfo.uid, info.activityInfo.packageName)                    != AppOpsManager.MODE_ALLOWED) {                //uid不等于SYSTEM_UID,requiredPermissions不为空,并且APPOPS未授权                skip = true;                break;            }        }    }    if (!skip && r.appOp != AppOpsManager.OP_NONE            && mService.mAppOpsService.noteOperation(r.appOp,            info.activityInfo.applicationInfo.uid, info.activityInfo.packageName)            != AppOpsManager.MODE_ALLOWED) {        //appOp非空,并且appops权限检查未授予        skip = true;    }    if (!skip) {        //检测该intent是否阻塞        skip = !mService.mIntentFirewall.checkBroadcast(r.intent, r.callingUid,                r.callingPid, r.resolvedType, info.activityInfo.applicationInfo.uid);    }    boolean isSingleton = false;    try {        isSingleton = mService.isSingleton(info.activityInfo.processName,                info.activityInfo.applicationInfo,                info.activityInfo.name, info.activityInfo.flags);    } catch (SecurityException e) {        Slog.w(TAG, e.getMessage());        skip = true;    }    if ((info.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) {        if (ActivityManager.checkUidPermission(                android.Manifest.permission.INTERACT_ACROSS_USERS,                info.activityInfo.applicationInfo.uid)                        != PackageManager.PERMISSION_GRANTED) {           //设置了activityInfo.flags,FLAG_SINGLE_USER,但没有INTERACT_ACROSS_USERS权限            skip = true;        }    }    if (!skip && info.activityInfo.applicationInfo.isInstantApp()            && r.callingUid != info.activityInfo.applicationInfo.uid) {       //isInstantApp跳过        skip = true;    }    if (!skip && r.callerInstantApp            && (info.activityInfo.flags & ActivityInfo.FLAG_VISIBLE_TO_INSTANT_APP) == 0            && r.callingUid != info.activityInfo.applicationInfo.uid) {       //callerInstantApp,并且设置了FLAG_VISIBLE_TO_INSTANT_APP        skip = true;    }    if (r.curApp != null && r.curApp.crashing) {        // 进程正在报错,跳过        skip = true;    }    if (!skip) {        boolean isAvailable = false;        try {            isAvailable = AppGlobals.getPackageManager().isPackageAvailable(                    info.activityInfo.packageName,                    UserHandle.getUserId(info.activityInfo.applicationInfo.uid));        } catch (Exception e) {        }        if (!isAvailable) {           //应用当前不可用 ,依然跳过            skip = true;        }    }    //如果组件权限需要review才能运行,跳过该广播,如果应用在前台,则启动review界面传递该intent    if (mService.mPermissionReviewRequired && !skip) {        if (!requestStartTargetPermissionsReviewIfNeededLocked(r,                info.activityInfo.packageName, UserHandle.getUserId(                        info.activityInfo.applicationInfo.uid))) {            skip = true;        }    }    ......    String targetProcess = info.activityInfo.processName;    ProcessRecord app = mService.getProcessRecordLocked(targetProcess,            info.activityInfo.applicationInfo.uid, false);    if (!skip) {        final int allowed = mService.getAppStartModeLocked(                info.activityInfo.applicationInfo.uid, info.activityInfo.packageName,                info.activityInfo.applicationInfo.targetSdkVersion, -1, true, false, false);        if (allowed != ActivityManager.APP_START_MODE_NORMAL) {            if (allowed == ActivityManager.APP_START_MODE_DISABLED) {                //startMode是APP_START_MODE_DISABLED的时候跳过                skip = true;            } else if (((r.intent.getFlags()&Intent.FLAG_RECEIVER_EXCLUDE_BACKGROUND) != 0)                    || (r.intent.getComponent() == null                        && r.intent.getPackage() == null                        && ((r.intent.getFlags()                                & Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND) == 0)                        && !isSignaturePerm(r.requiredPermissions))) {                mService.addBackgroundCheckViolationLocked(r.intent.getAction(),                        component.getPackageName());                //设置了FLAG_RECEIVER_EXCLUDE_BACKGROUND 或者 (component为空,并且package为空,并且                //设置了FLAG_RECEIVER_INCLUDE_BACKGROUND 并且requiredPermissions都是签名权限) 则跳过,不允许                skip = true;            }        }    }    if (!skip && !Intent.ACTION_SHUTDOWN.equals(r.intent.getAction())            && !mService.mUserController            .isUserRunning(UserHandle.getUserId(info.activityInfo.applicationInfo.uid),                    0 /* flags */)) {        skip = true;        //用户已经停止运行,跳过    }    if (skip) {        if (DEBUG_BROADCAST)  Slog.v(TAG_BROADCAST,                "Skipping delivery of ordered [" + mQueueName + "] "                + r + " for whatever reason");        r.delivery[recIdx] = BroadcastRecord.DELIVERY_SKIPPED;        r.receiver = null;        r.curFilter = null;        r.state = BroadcastRecord.IDLE;        r.manifestSkipCount++;        //递归调用发送广播流程        scheduleBroadcastsLocked();        return;    }    r.manifestCount++;    r.delivery[recIdx] = BroadcastRecord.DELIVERY_DELIVERED;    r.state = BroadcastRecord.APP_RECEIVE;    r.curComponent = component;    r.curReceiver = info.activityInfo;    if (brOptions != null && brOptions.getTemporaryAppWhitelistDuration() > 0) {        scheduleTempWhitelistLocked(receiverUid,                brOptions.getTemporaryAppWhitelistDuration(), r);    }    // 广播正在执行,包无法停止.    try {        AppGlobals.getPackageManager().setPackageStoppedState(                r.curComponent.getPackageName(), false, UserHandle.getUserId(r.callingUid));    } catch (RemoteException e) {    } catch (IllegalArgumentException e) {    }    // 接收进程正在运行    if (app != null && app.thread != null && !app.killed) {        try {            app.addPackage(info.activityInfo.packageName,                    info.activityInfo.applicationInfo.versionCode, mService.mProcessStats);            //调用app.thread.scheduleReceiver后返回                    processCurBroadcastLocked(r, app, skipOomAdj);            return;        } catch (RemoteException e) {                   } catch (RuntimeException e) {            //如果发生了预料之外的异常,则跳过这次广播,重新开发下次广播发送,            //这里现在是在系统进程中            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;        }    }    //未在运行,则调用startProcessLocked启动该进程,用来接收广播    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) {        //进程启动过程发生异常,结束本次广播,继续下个广播        logBroadcastReceiverDiscardLocked(r);        finishReceiverLocked(r, r.resultCode, r.resultData,                r.resultExtras, r.resultAbort, false);        scheduleBroadcastsLocked();        r.state = BroadcastRecord.IDLE;        return;    }    mPendingBroadcast = r;    mPendingBroadcastRecvIndex = recIdx;}

deliverToRegisteredReceiverLocked方法流程分析:

private void deliverToRegisteredReceiverLocked(BroadcastRecord r,        BroadcastFilter filter, boolean ordered, int index) {    boolean skip = false;    if (filter.requiredPermission != null) {        int perm = mService.checkComponentPermission(filter.requiredPermission,                r.callingPid, r.callingUid, -1, true);        if (perm != PackageManager.PERMISSION_GRANTED) {            // BroadcastFilter所带权限不允许,跳过            skip = true;        } else {            final int opCode = AppOpsManager.permissionToOpCode(filter.requiredPermission);            if (opCode != AppOpsManager.OP_NONE                    && mService.mAppOpsService.noteOperation(opCode, r.callingUid,                            r.callerPackage) != AppOpsManager.MODE_ALLOWED) {                // BroadcastFilter所带权限appops检测不允许,跳过                skip = true;            }        }    }    //检查BroadcastRecord的requiredPermission是否通过PMS和APPOPS授权,若未授权,则跳过    if (!skip && (filter.receiverList.app == null || filter.receiverList.app.killed            || filter.receiverList.app.crashing)) {        //crash 进程跳过        skip = true;    }    ......    if (!skip && !visibleToInstantApps && filter.instantApp            && filter.receiverList.uid != r.callingUid) {        //instantApp 跳过        skip = true;    }    if (!skip && !filter.visibleToInstantApp && r.callerInstantApp            && filter.receiverList.uid != r.callingUid) {                skip = true;    }    //跳过该广播发送    if (skip) {        r.delivery[index] = BroadcastRecord.DELIVERY_SKIPPED;        return;    }    ......    try {       // ......发送广播            performReceiveLocked(filter.receiverList.app, filter.receiverList.receiver,                    new Intent(r.intent), r.resultCode, r.resultData,                    r.resultExtras, r.ordered, r.initialSticky, r.userId);        ......    } catch (RemoteException e) {        ......    }}

 

void performReceiveLocked(ProcessRecord app, IIntentReceiver receiver,        Intent intent, int resultCode, String data, Bundle extras,        boolean ordered, boolean sticky, int sendingUser) throws RemoteException {    // Send the intent to the receiver asynchronously using one-way binder calls.    if (app != null) {        if (app.thread != null) {            //app 与 thread 不为空,则直接调用scheduleRegisteredReceiver,回调进广播线程            try {                app.thread.scheduleRegisteredReceiver(receiver, intent, resultCode,                        data, extras, ordered, sticky, sendingUser, app.repProcState);            } catch (RemoteException ex) {                // Failed to call into the process. It's either dying or wedged. Kill it gently.                synchronized (mService) {                    Slog.w(TAG, "Can't deliver broadcast to " + app.processName                            + " (pid " + app.pid + "). Crashing it.");                    app.scheduleCrash("can't deliver broadcast");                }                throw ex;            }        } else {            // Application has died. Receiver doesn't exist.            throw new RemoteException("app.thread must not be null");        }    } else {        receiver.performReceive(intent, resultCode, data, extras, ordered,                sticky, sendingUser);    }}

通过binder远程调用,回到ApplicationThread中,

private class ApplicationThread extends IApplicationThread.Stub {public void scheduleRegisteredReceiver(IIntentReceiver receiver, Intent intent,        int resultCode, String dataStr, Bundle extras, boolean ordered,        boolean sticky, int sendingUser, int processState) throws RemoteException {    updateProcessState(processState, false);    receiver.performReceive(intent, resultCode, dataStr, extras, ordered,            sticky, sendingUser);}}

LoadedApk中流程如下:

static final class ReceiverDispatcher {    final static class InnerReceiver extends IIntentReceiver.Stub {        final WeakReference mDispatcher;        final LoadedApk.ReceiverDispatcher mStrongRef;        InnerReceiver(LoadedApk.ReceiverDispatcher rd, boolean strong) {            mDispatcher = new WeakReference(rd);            mStrongRef = strong ? rd : null;        }        @Override        public void performReceive(Intent intent, int resultCode, String data,                Bundle extras, boolean ordered, boolean sticky, int sendingUser) {           ......            if (rd != null) {                rd.performReceive(intent, resultCode, data, extras,                        ordered, sticky, sendingUser);            ......            }        }    }
public void performReceive(Intent intent, int resultCode, String data,        Bundle extras, boolean ordered, boolean sticky, int sendingUser) {    final Args args = new Args(intent, resultCode, data, extras, ordered,            sticky, sendingUser);    if (intent == null) {        Log.wtf(TAG, "Null intent received");    } else {        if (ActivityThread.DEBUG_BROADCAST) {            int seq = intent.getIntExtra("seq", -1);            Slog.i(ActivityThread.TAG, "Enqueueing broadcast " + intent.getAction()                    + " seq=" + seq + " to " + mReceiver);        }    }    //将该runnable发送到activitythread线程中执行,所以广播的执行是在主线程中,超时会产生ANR    if (intent == null || !mActivityThread.post(args.getRunnable())) {        if (mRegistered && ordered) {            IActivityManager mgr = ActivityManager.getService();            if (ActivityThread.DEBUG_BROADCAST) Slog.i(ActivityThread.TAG,                    "Finishing sync broadcast to " + mReceiver);            args.sendFinished(mgr);        }    }}

 Args类中流程如下:

public final Runnable getRunnable() {    return () -> {        final BroadcastReceiver receiver = mReceiver;        final boolean ordered = mOrdered;        ......        try {            ClassLoader cl = mReceiver.getClass().getClassLoader();            intent.setExtrasClassLoader(cl);            intent.prepareToEnterProcess();            setExtrasClassLoader(cl);            receiver.setPendingResult(this);            //回调到onReceiver接口            receiver.onReceive(mContext, intent);        } catch (Exception e) {           ......        }        ......    };

至此,广播的动态注册,和动态发送流程简要分析结束。

 

更多相关文章

  1. android 3G pppd 调试记录
  2. Android面试系列文章2018之Android部分Broadcast篇
  3. Android面试系列文章2018之Android部分Broadcast篇
  4. 【Android(安卓)开发】: Android(安卓)消息处理机制之一: Handle
  5. 【Android(安卓)开发】: Android(安卓)消息处理机制之一: Handle
  6. Android(安卓)短信发送
  7. Android(安卓)应用程序请求Vsync
  8. android 中发送短信
  9. 【Android】Android(安卓)开机广播的使用

随机推荐

  1. Android(安卓)解析 json
  2. Android学习-使用ViewFlipper实现屏幕切
  3. Android(安卓)适配器Adapter的学习
  4. 解开Android应用程序组件Activity的"sing
  5. 分享给大家一些高质量的资源
  6. 实战Android应用开发
  7. 如何在Android(安卓)studio中以compile直
  8. Android(安卓)VideoVIew 视频全屏拉伸
  9. ActiveAndroid--Android轻量级ORM框架
  10. Android(安卓)录屏adb命令组合