从Android MM 开始,手机开机时,会加载手机call模块中的TelecomService,把Telecom服务添加到系统服务中,并对默认短信通过模块等默认app进行相应的授权。
模块名 LOCAL_PACKAGE_NAME = Telecom
SystemServer启动TelecomLoaderService
mSystemServiceManager.startService(TelecomLoaderService.class);
在SystemServer的startOtherService启动TelecomLoaderService,然而这个TelecomLoaderService现在起来并没有做什么。需要等到回调onBootPhase(),才会去启动TelecomService。顾名思义,这个类就是为了去加载TelecomService而存在的。system_process启动完毕后,会回调所有SystemService的onBootPhase函数。
```
@Override
public void onBootPhase(int phase) {
if (phase == PHASE_ACTIVITY_MANAGER_READY) {
registerDefaultAppNotifier();
registerCarrierConfigChangedReceiver();
connectToTelecom();
}
}
```
TelecomLoaderService启动TelecomService
在TelecomLoaderService的connectToTelecom(),绑定TelecomService。
实例化一个intent,也就是启动我们要绑定的服务。其中,intent的相关信息如下:
Action: "com.android.ITelecomServcie"
ComponentName: new ComponentName("com.android.server.telecom", "com.androdi.server.telecom.components.TelecomService");
从这里的参数可以找到对应要启动的服务是哪个包下的哪个服务。
```
private void connectToTelecom() {
synchronized (mLock) {
if (mServiceConnection != null) {
// TODO: Is unbinding worth doing or wait for system to rebind?
mContext.unbindService(mServiceConnection);
mServiceConnection = null;
}
TelecomServiceConnection serviceConnection = new TelecomServiceConnection();
Intent intent = new Intent(SERVICE_ACTION);
intent.setComponent(SERVICE_COMPONENT);
int flags = Context.BIND_IMPORTANT | Context.BIND_FOREGROUND_SERVICE
| Context.BIND_AUTO_CREATE;
// Bind to Telecom and register the service
if (mContext.bindServiceAsUser(intent, serviceConnection, flags, UserHandle.SYSTEM)) {
mServiceConnection = serviceConnection;
}
}
}
```
当绑定TelecomService服务后,会回调TelecomServiceConnection的onServiceConnected方法。这个函数主要处理的就是对默认的call,sms app授予运行时权限,具体调用参考流程图。同时,最主要的就是把Context.TELECOM_SERVICE添加到系统服务中,这里添加的就是TelecomServiceImpl中的mBinderImpl。
ServiceManager.addService(Context.TELECOM_SERVICE, service);
packageManagerInternal.grantDefaultPermissionsToDefaultSmsApp(
packageName, userId);
packageManagerInternal.grantDefaultPermissionsToDefaultDialerApp(
packageName, userId);
packageManagerInternal.grantDefaultPermissionsToDefaultSimCallManager(
packageName, userId);
TelecomService加载TelecomSystem
TelecomService的onBind方法,返回的IBinder对象就是上面说的TelecoomServiceImpl的mBinderImpl。
public IBinder onBind(Intent intent) {
Log.d(this, "onBind");
initializeTelecomSystem(this);
/*White Pages Code begins*/
if (CscFeature.getInstance().getEnableStatus(NameIDHelper.mEnableWhitePagesConfig)
&& NameIDHelper.isNameIDInstalledAndEnabled(this)) {
NameIDHelper.init(this);
}
/*White Pages Code ends*/
synchronized (getTelecomSystem().getLock()) {
return getTelecomSystem().getTelecomServiceImpl().getBinder();
}
}
InitializeTelecomSystem主要初始化TelecomSystem对象,里面包含Call将会用到的各个对象。比如:
- CallsManager
- CallIntentProcessor
- TelecomServiceImpl
- TelecomSystemDB
在创建TelecomServiceImpl对象的时候,就会生成ITelecomService.Stub mBinderImpl对象。
private final ITelecomService.Stub mBinderImpl = new ITelecomService.Stub(){}
这个就是我们最终添加到系统服务的对象。至此,TelecomLoaderService的加载TelecomService的工作基本完成。
总结
TelecomLoaderService加载TelecomService的过程和他的名字非常符合,完成的工作比较简单,启动TelecomService,搜权默认应用。最后附上一张时序图: