Android通话过程分析

2018-12-03 19:33

Android通话过程分析

本文档主要对android平台下的call的实现做详细分析。

Call处理的五大核心分别是:Call,Phone, CallTracker,DriverCall,Connection

1. Call

Call是Call应用中的最基本的单位,其主要是用来管理Connection的。Call中非常重要的是其状态,Call中共有九种状态:

IDLE, ACTIVE, HOLDING, DIALING, ALERTING, INCOMING, WAITING, DISCONNECTED, DISCONNECTING;

对call的处理实际上是对状态转换上的处理。对这九中状态所对应的含义和call此时的现状要很熟。

Call的继承关系图:

Call+hangup()+hangupAllCalls()+getConnections()GsmCall#connections+attach()+attachFake()+detach()+isFull() : bool+clearDisconnected()CdmaCall#connections+attach()+attachFake()+detach()+isFull() : bool+clearDisconnected()

Call是一个抽象类,从图中可知,实际操作是在其子类GsmCall和CdmaCall。在GsmCall中,有个成员变量:connections,这个变量是用来管理Call中的connection的,一个Call最大允许有5个connections:

static final int MAX_CONNECTIONS_PER_CALL = 5; // only 5 connections allowed per call

2. Phone

Phone不仅是call的处理核心,而且是整个Telephony处理的核心。Phone是一个最基本的概念,用来控制Phone系统相关(即无线相关的)模块的处理:simcard,call,message,datacall等。

Phone的继承关系如下:

<<接口>>PhoneHander+handleMessage()PhoneBase#mPhoneId : intPhoneProxy-mActivePhone : PhoneGsmPhone#GsmCallTracker mCT+dial()+rejectCall()+acceptCall()+switchHoldingAndActive()CdmaPhone#CdmaCallTracker mCT+dial()+rejectCall()+acceptCall()+switchHoldingAndActive()

在Phone的继承关系中可知,Phone只是一个接口,它被PhoneBase和PhoneProxy实现,而PhoneBase是抽象类,它被GsmPhone和CdmaPhone继承。所以有此可知Phone分为两类:GsmPhone和CdmaPhone。

PhoneBase还有另外一个继承关系:继承自Handler。这就说明GsmPhone和CdmaPhone其实都是一个Handler。所以PhoneBase的子类是可以进行事件处理的。

3. Connection

Connection用来处理一个真正的通话通路,包含通话过程中call的数据,包括号码、通话时间、MT还是MO、是第几路通话、挂断原因等信息。

Connection类关系图:

ConnectionGsmConnectionCdmaConnectionCallTracker

GsmConnection中有个成员变量:GsmCall parent,这个成员变量是用来表示该connection是属于哪个Call的。由变量名(parent)可以看出Call与Connection的关系:父与子的关系,一个Call可以有多个Connection(3gpp中规定最多5个),但一个Connection只能属于一个Call。

所以一个Connection必定要依附于一个Call。Connection是怎样依附于一个Call的呢?从Connection的构造方法中就可以知道:

a. GsmConnection (Context context, DriverCall dc, GsmCallTracker ct, int index)

这个构造方法是在MT的时候使用的,因为它有一个DriverCall的参数。它通过

parentFromDCState进行管理。

方法来获得对应的

parent(Call)且通过

parent.attach(this, dc);把connection加入到Call的Connections变量

b. GsmConnection (Context context, String dialString, GsmCallTracker ct, GsmCall parent)

这个构造方法是在MO的时候使用的,它会传入一个指定的parent(Call)且通过parent.attachFake(this, GsmCall.State.DIALING);调用把Connection加入到Call的Connections变量进行管理。

从上面知道Connection调用了Call的2个重要的方法:Attach和attachFake。这两个方法都是把一个connection加入到Call的Connections成员变量中进行管理的。Call中还有一个方法detach(GsmConnection conn),这个方法是用来把connection从Call中移除的。

其中还有一个方法:/*package*/ boolean update (DriverCall dc)。这个是用来更新connection的。

4. DriverCall

是与ril层通信时的一个中间处理类,主要用来接收到ril的call数据后转到到java层上来。

DriverCall中包含了协议中规定的有关call的相关参数,具体如下: public int index; //Connection Index for use with, eg, AT+CHLD public boolean isMT; //是incoming还是outgoing public State state; //connection state。

public boolean isMpty;// nonzero if is mpty call。 public String number;// Remote party number public int TOA; //type of address, eg 145 = intl

public boolean isVoice;// nonzero if this is is a voice call

public boolean isVoicePrivacy;// nonzero if CDMA voice privacy mode is active public int als;// ALS line indicator if available (0 = line 1)

public int numberPresentation;// 0=Allowed, 1=Restricted, 2=Not Specified/Unknown 3=Payphone

public String name;// Remote party name

public int namePresentation;// 0=Allowed, 1=Restricted, 2=Not Specified/Unknown 3=Payphone 5. CallTracker

CallTracker的类关系图:

HandlerCallTrackerGsmConnection#pendingOperations : int#needsPoll : bool-Message lastRelevantPoll<<接口>>CommandsInterfaceGsmPhoneGsmCallTrackerGsmCall#ringingCall : GsmCall#foregroundCall : GsmCall#backgroundCall : GsmCall#connections[] : GsmConnectionCdmaCallTracker#ringingCall : CdmaCall#foregroundCall : CdmaCall#backgroundCall : CdmaCall#connections[] : CdmaConnectionCdmaPhoneCdmaCallCdmaConnection

从上图中可以看到,CallTracker 在本质上是一个Handler。

CallTracker是一个抽象类,所以其实际的操作对象是其子类:GSMCallTracker和CdmaCallTracker。

下面以GSMCallTracker为例介绍CallTracker的相关处理,CdmaCallTracker处理基本与之相同。

GSMCallTracker是Android 的通话管理层。GSMCallTracker建立了ConnectionList 来管理现行的通话连接,并向上层提供电话调用接口。

1) Connections

Connections是GSMCallTracker 用来维护所有的通话的列表,最大可维护7路通话。 static final int MAX_CONNECTIONS = 7; // only 7 connections allowed in GSM

2) ringingCall、foregroundCall、backgroundCall

一个手机系统只允许3个Call同时存在,即ring call、active call和held call,所以GSMCallTracker用ringingCall、foregroundCall、backgroundCall来管理。 ringingCall:用来管理INCOMING和WAITING的通话

foregroundCall:用来管理DAILING、ALERTING、ACTIVE的通话 backgroundCall:用来管理HOLD的通话

那么,ringingCall、foregroundCall、backgroundCall是如何来管理对应的call和connection的呢?前面已经讲过了Call和Connection及它们之间的关系,其实系统中的Call是已经存在的,就是上面的3个,其实主要的是对于一个connection,它需要依附于那个call,由connection的构造方法知:

1) 在 从RIL获取的Calls列表的时候,通过parentFromDCState来获取相应的

Call:

private GsmCall

parentFromDCState (DriverCall.State state) { switch (state) {

case ACTIVE: case DIALING: case ALERTING:

return owner.foregroundCall; //break;

case HOLDING:

return owner.backgroundCall; //break;

case INCOMING: case WAITING:

return owner.ringingCall; //break;

default:

throw new RuntimeException(\call state: \ + state); }

}

2) 在其他情况下,一般根据上面的状态直接传入对应的call。

3) GsmCallTracker中的事件处理机制

Call的事件处理基本上是请求应答模式,具体如下(以dail为例,其他类同):


Android通话过程分析.doc 将本文的Word文档下载到电脑 下载失败或者文档不完整,请联系客服人员解决!

下一篇:徽商启示

相关阅读
本类排行
× 注册会员免费下载(下载后可以自由复制和排版)

马上注册会员

注:下载文档有可能“只有目录或者内容不全”等情况,请下载之前注意辨别,如果您已付费且无法下载或内容有问题,请联系我们协助你处理。
微信: QQ: