Android O 拨打电话流程之呼出

时间:2022-11-10 09:51:20

DialtactsActivity.java模块是负责电话拨打界面
DialpadFragment.java:负责拨号盘的类文件
Android O 拨打电话流程之呼出

拨打电话界面,在onClick方法中点击dialpad_floating_action_button按钮进行拨打电话,进入handleDialButtonPressed()中处理拨打电话 DialerUtils.startActivityWithErrorToast
在CallIntentBuilder类的build方法中,
Intent intent = new Intent(Intent.ACTION_CALL, uri);
Intent.ACTION_CALL =”android.intent.action.CALL”

Android O 拨打电话流程之呼出

AndroidManifest.xml文件中有定义,对应文件为UserCallActivity
Android O 拨打电话流程之呼出
Android O 拨打电话流程之呼出

startActivityWithErrorToast中调用 placeCallOrMakeToast,最终调用
Android O 拨打电话流程之呼出

TelecomManager.java中的placeCall
Android O 拨打电话流程之呼出
最终进入TelecomManager.placeCall中,该方法继续调用ITelecomService,具体实现在类TelecomServiceImpl中
Android O 拨打电话流程之呼出
/packages/services/Telecomm/src/com/android/server/telecom/components/UserCallIntentProcessor.java
UserCallIntentProcessor.java中处理processIntent去发送到Activity
Android O 拨打电话流程之呼出

在processOutgoingCallIntent中处理,拨号权限,看是否直接拒绝,都是通过 sendBroadcastToReceiver(intent)发送出去
Android O 拨打电话流程之呼出

Android O 拨打电话流程之呼出

/packages/services/Telecomm/src/com/android/server/telecom/components/PrimaryCallReceiver.java

进入广播接收器PrimaryCallReceiver中通过调用getTelecomSystem中的getCallIntentProcessor来获取CallIntentProcessor对象,该对象的创建在TelecomSystem的构造方法中
Android O 拨打电话流程之呼出

Android O 拨打电话流程之呼出

/packages/services/Telecomm/src/com/android/server/telecom/CallIntentProcessor.java

该processIntent中处理,该类中的CallsManager是从哪儿来的呢?
这是CallIntentProcessor构造方法中传入进来的,这就要追寻到CallIntentProcessor创建来的,最终发现CallManager也是在TelecomSystem中创造的!
Android O 拨打电话流程之呼出

processOutgoingCallIntent中的处理部分,通过CallManager创建Call
Android O 拨打电话流程之呼出
Android O 拨打电话流程之呼出

/packages/services/Telecomm/src/com/android/server/telecom/CallsManager.java

Android O 拨打电话流程之呼出

主要完成的功能是:
创建Call对象
获取当前激活的卡的列表
获取当前使用哪一张卡呼出
设置当前通话账户: call.setTargetPhoneAccount(phoneAccountHandle);
设置当前call正在连接,将call加入列表 addCall(call);
Android O 拨打电话流程之呼出

Android O 拨打电话流程之呼出

当调用CallsManager的startOutgoingCall结束,返回call对象,之后调用
/packages/services/Telecomm/src/com/android/server/telecom/NewOutgoingCallIntentBroadcaster.java

processIntent()方法中最终调用 mCallsManager.placeOutgoingCall,该mCallsManager对象还是在之前创建的,placeOutgoingCall继续调用 call.startCreateConnection(mPhoneAccountRegistrar);建立连接

packages/services/Telecomm/src/com/android/server/telecom/Call.java
Android O 拨打电话流程之呼出

/packages/services/Telecomm/src/com/android/server/telecom/CreateConnectionProcessor.java
处理连接请求
Android O 拨打电话流程之呼出

/packages/services/Telecomm/src/com/android/server/telecom/ConnectionServiceWrapper.java

在方法createConnection 内部有 mBinder.bind(callback, call);这是一个回调函数,调用完成之后,将会调用callback中的onSuccess方法

Android O 拨打电话流程之呼出

Android O 拨打电话流程之呼出

会继续调用createConnection,mServiceInterface是IConnectionService的具体实现在ConnectionService.java的匿名内部类中

frameworks/base/telecomm/java/android/telecom/ConnectionService.java

Android O 拨打电话流程之呼出

发送创建连接消息MSG_CREATE_CONNECTION,之后调用ConnectionService.java中的方法createConnection
Android O 拨打电话流程之呼出
Android O 拨打电话流程之呼出

调用onCreateOutgoingConnection去创建连接,该方法为空,所以实现应该再起子类之中

/packages/services/Telephony/src/com/android/services/telephony/TelephonyConnectionService.java
public Connection onCreateOutgoingConnection( PhoneAccountHandle connectionManagerPhoneAccount, final ConnectionRequest request)方法来呼出连接

Android O 拨打电话流程之呼出

创建TelephonyConnection对象,获取该对象后,调用placeOutgoingConnection
Android O 拨打电话流程之呼出
Android O 拨打电话流程之呼出

frameworks/opt/telephony/src/java/com/android/internal/telephony/GsmCdmaPhone.java

发现是调用phone.dial拨打电话,该phone其实是GsCdmaPhone.java对象
public Connection dial(String dialString, UUSInfo uusInfo, int videoState, Bundle intentExtras)

Android O 拨打电话流程之呼出

dial方法之中还有一个ImsPhone对象,该对象主要处理Volte通话的

protected Connection dialInternal(String dialString, UUSInfo uusInfo, int videoState, Bundle intentExtras, ResultReceiver wrappedCallback)
Android O 拨打电话流程之呼出
在这里将会调用mCT.dial方法,也就是GsmCdmaCallTracker对象

/frameworks/opt/telephony/src/java/com/android/internal/telephony/GsmCdmaCallTracker.java
Android O 拨打电话流程之呼出

调用mCi.dial拨打,mCi是RIL对象,在GsmCdmaCallTracker的父类CallTracker中定义,updatePhoneState状态,发起状态改变通知.
那么这些对象是什么时候创建的呢?GsmCdmaCallTracker,RIL对象

/packages/services/Telephony/src/com/android/phone/PhoneApp.java
/packages/services/Telephony/src/com/android/phone/PhoneGlobals.java
/frameworks/opt/telephony/src/java/com/android/internal/telephony/PhoneFactory.java

/packages/services/Telephony/src/com/android/phone/PhoneApp.java
application标签中的android:persistent=”true”表示该应用始终常驻内存,一开始系统服务启动完毕之后,自动加载到内存中
Android O 拨打电话流程之呼出

Android O 拨打电话流程之呼出

/packages/services/Telephony/src/com/android/phone/PhoneGlobals.java

Android O 拨打电话流程之呼出

/frameworks/opt/telephony/src/java/com/android/internal/telephony/PhoneFactory.java


public static void makeDefaultPhone(Context context){
TelephonyComponentFactory telephonyComponentFactory = TelephonyComponentFactory.getInstance();
sCommandsInterfaces[i] = telephonyComponentFactory.makeRIL(context,networkModes[i], cdmaSubscription, i);
Android O 拨打电话流程之呼出

在makePhone里面创建GsmCdmaPhone,在GsmCdmaPhone的构造方法中创建来GsmCdmaCallTracker
Android O 拨打电话流程之呼出

综上所述,也就是说在系统开机之后,这些对象已经随着PhoneApp被创建出来了

frameworks/opt/telephony/src/java/com/android/internal/telephony/RIL.java
Android O 拨打电话流程之呼出

发送请求:RIL_REQUEST_DIAL

/frameworks/opt/telephony/src/java/com/android/internal/telephony/RadioResponse.java主要处理上层发出请求,底层回馈信息并调用RIL对象的processResponseDone方法,完成一次主动请求,相当之前的processsolicated
/frameworks/opt/telephony/src/java/com/android/internal/telephony/RadioIndication.java主要处理底层上报消息,相当之前的processUnsolicated
/hardware/ril/libril/ril_service.cpp
RIL.java中新采用的radioProxy代理类来调用相关操作,该类调用的相关操作最终都是调用ril_service.cpp 中的方法

在RIL里面由对应的请求,dial,那么在RadioResponse.java中由 *+Response,dialResponse
Android O 拨打电话流程之呼出

Android O 拨打电话流程之呼出

Android O 拨打电话流程之呼出

在responseVoid中调用sendMessageResponse向上层发送消息
先去调用mRil.processResponse处理上报,然后发送消息,最终在调用processResponseDone来完成一次对应的请求
发送的消息为EVENT_OPERATION_COMPLETE,该消息是GsmCdmaCallTracker调用dial时利用obtainCompleteMessage去处理的.

Android O 拨打电话流程之呼出

Android O 拨打电话流程之呼出

Android O 拨打电话流程之呼出

在operationComplete中继续调用mCi.getCurrentCalls来获取call状态,消息为EVENT_POLL_CALLS_RESULT

   protected synchronized void handlePollCalls(AsyncResult ar) {
>>>>>>>>>>>>>>>>>>
updatePhoneState(); //更新手机状态
mPhone.notifyPreciseCallStateChanged();//发起状态改变通知
>>>>>>>>>>>>>>>>>>>
}

之后底层会自动上报消息:RIL_UNSOL_RESPONSE_CALL_STATE_CHANGED
先调用RIL对象中的processIndication
Android O 拨打电话流程之呼出

最后mCallStateRegistrants发起通知,GsmCdmaCallTracker注册来该事件, mCi.registerForCallStateChanged(this, EVENT_CALL_STATE_CHANGE, null);
Android O 拨打电话流程之呼出

GsmCdmaCallTracker处理消息 EVENT_CALL_STATE_CHANGE,最后调用其父类中pollCallsWhenSafe()方法来处理,调用 handlePollCalls来查询call的状态等操作。

拨打电话呼出流程图:

Android O 拨打电话流程之呼出