zoukankan      html  css  js  c++  java
  • Framework层Ril控制流程分析

         Framework层Ril控制流程分析

    RIL Native层分析:http://www.cnblogs.com/bastard/archive/2012/11/05/2754891.html

    一 RIL整体框架

    看一下整个RIL部分框架图:

        

      实际上Framework部分比较复杂的,包含了很多类;但其核心的两个类是GSMPhone/,RIL.Java.

    还包括围绕这两个类构成的状态管理,命令交互的类。

    二 PhoneApp 启动过程

    在AndroidManifest.xml文件中:

      <application android:name="PhoneApp"

         android:persistent="true"

         …… 

             在开机启动时到ActivityManagerService的systemReady时,会将带有这个属性的App启动。

    调用应用的Application——PhoneApp

    public class PhoneApp extends Application
    {
        @Override
        public void onCreate() {
             //初始化framework层telephony相关
             PhoneFactory.makeDefaultPhones(this);
         Phone phone = PhoneFactory.getDefaultPhone();
             
             CallManager mCM = CallManager.getInstance();
             mCM.registerPhone(phone);
        }
    }

    PhoneFactory初始化Framework层相关对象:  

    public static void makeDefaultPhone(Context context) 
    {
        sPhoneNotifier = new DefaultPhoneNotifier();
        
        //创建CommandsInterface实例RIL
        sCommandsInterface = new RIL(context, networkMode, cdmaSubscription);
        
        // Instantiate UiccController so that all other classes can just call getInstance()
        UiccController.make(context, sCommandsInterface);
        
        //根据类型创建Phone实例
        int phoneType = getPhoneType(networkMode);
        //创建Phone实例GSMPhone 以及代理对象ProxyPhone
        sProxyPhone = new PhoneProxy(new GSMPhone(context,
                            sCommandsInterface, sPhoneNotifier));
    }

      这个sCommandsInterface很关键 是连接GSMPhone与RIL。

      整个Framewrok Telephony中很关键的就是Phone和CommandInterface两个接口:

    核心就是围绕这两个接口派生的类;还有各种对Phone进行了包装的类。

      Phone:Internal interface used to control the phone;

      CommandInterface:提供跟native层Ril交互的接口发送命令和接受命令,注册状态传递回调接口,向上层传递状态变化。

    下面是这几个核心类的结构图:

        

    三 命令控制流程

             命令从Phone开始,在传递到RIL,在通过Socket传递给Rild。下面看一下framework中RIL类工作流程。

    与Native端交互过程:

        

      RIL提供了call和connection过程命令接口,状态变化回调,unsolicited事件通知。

    类结构图:

        

     

      其中关键的两个线程:sender和receiver ,运行单独的线程中处理向下和向上的请求。

    RIL构造函数:

    public RIL(Context context, ……) {    
        //创建sender运行线程 
        mSenderThread = new HandlerThread("RILSender");
        mSenderThread.start();
        //send消息处理循环
        Looper looper = mSenderThread.getLooper();
        mSender = new RILSender(looper);
        
        //建立receiver运行的线程
        mReceiver = new RILReceiver();
        mReceiverThread = new Thread(mReceiver, "RILReceiver");
        mReceiverThread.start();
    }

    1 send事件流程

    dial拨号流程:

    public void dial(String address, int clirMode, 
                    UUSInfo uusInfo, Message result) {
                                        
        //获取一个RILRequest对象 请求对象类型
        RILRequest rr = RILRequest.obtain(RIL_REQUEST_DIAL, result);
        //将数据打包成parcel
        rr.mp.writeString(address);
        rr.mp.writeInt(clirMode);
        rr.mp.writeInt(0); // UUS information is absent
        ……
        //将数据发送到send线程中处理 内部公共接口send
        send(rr);
    }
        
    private void send(RILRequest rr) {
        //Handler异步处理消息
        msg = mSender.obtainMessage(EVENT_SEND, rr);
        msg.sendToTarget();
    } 

    Send消息处理过程:

    class RILSender extends Handler implements Runnable {
      public RILSender(Looper looper) {
          super(looper);
     }
    
      // Only allocated once
      byte[] dataLength = new byte[4];
    
      public void run() {
          //setup if needed
      }
    
      handleMessage(Message msg) {
          RILRequest rr = (RILRequest)(msg.obj);
          RILRequest req = null;
    
          switch (msg.what) {
            case EVENT_SEND:
              //与rild通信socket
              LocalSocket s;
              s = mSocket;    
          //加入请求队列
              synchronized (mRequestsList) {
                  mRequestsList.add(rr);
                  mRequestMessagesWaiting++;
              }
              byte[] data;
              data = rr.mp.marshall();
              //将将数据通过socket传入到rild进程中
              s.getOutputStream().write(dataLength);
              s.getOutputStream().write(data);
                break;
        }
      }
    }

             在send线程中将数据通过socket传递给rild进程处理。

    2 receive事件流程

    Receiver接收rild发送来的事件以及send事件的response事件:

    class RILReceiver implements Runnable {
      byte[] buffer;
      RILReceiver() {
          buffer = new byte[RIL_MAX_COMMAND_BYTES];
      }
        public void run() {
            String rilSocket = "rild";
            //循环处理rild传递来的事件
            for (;;) {
                //创建于rild通信的socket 建立连接
                s = new LocalSocket();
                l = new LocalSocketAddress(rilSocket,
                                LocalSocketAddress.Namespace.RESERVED);
                s.connect(l);
                  mSocket = s;
                  //读取socket数据
                InputStream is = mSocket.getInputStream();
            
              for (;;) {
                  //解析数据
                  Parcel p;
                  length = readRilMessage(is, buffer);
                  p = Parcel.obtain();
                  p.unmarshall(buffer, 0, length);
                  p.setDataPosition(0);
                  
                  //处理rild传递来的消息
                  processResponse(p);
              }
            
              setRadioState (RadioState.RADIO_UNAVAILABLE);
              mSocket.close();
              // Clear request list on close
              clearRequestsList(RADIO_NOT_AVAILABLE, false);
          }
        }
    }
        private void processResponse (Parcel p) {
      type = p.readInt();
        //新事件Or send事件response
      if (type == RESPONSE_UNSOLICITED) {
          processUnsolicited (p);
      } else if (type == RESPONSE_SOLICITED) {
          processSolicited (p);
      }
    }

    网络端事件处理流程:

    private void processUnsolicited (Parcel p) {
        Object ret;
        int response = p.readInt();
        switch(response) {
            //来电
            case RIL_UNSOL_CALL_RING: 
                ret =  responseCallRing(p); break;
            ……
        }
        
        switch(response) {
            case RIL_UNSOL_CALL_RING:
                //通知注册来电事件的register
                if (mRingRegistrant != null) {
                    mRingRegistrant.notifyRegistrant(
                        new AsyncResult (null, ret, null));
                }
                break;
            ……
        }
    } 

    3 receiver事件通知register机制

    对事件状态的注册是在RIL的父类BaseCommands完成的。

    BaseCommands类注册事件的实现:

    public abstract class BaseCommands implements CommandsInterface {
        //注册到列表中
        protected RegistrantList mRadioStateChangedRegistrants = new RegistrantList();
        protected RegistrantList mCallStateRegistrants = new RegistrantList();
        protected RegistrantList mDataNetworkStateRegistrants = new RegistrantList();
        ……
        
        //注册某一事件发生
        protected Registrant mRingRegistrant;
        protected Registrant mSmsStatusRegistrant;
        protected Registrant mRestrictedStateRegistrant;
        ……
        
        //注册接口
        public void registerForRadioStateChanged(Handler h, int what, Object obj) {
            Registrant r = new Registrant (h, what, obj);
            
            synchronized (mStateMonitor) {
                mRadioStateChangedRegistrants.add(r);
                r.notifyRegistrant();
            }
        }
    
        //注册回调
        public void setOnCallRing(Handler h, int what, Object obj) {
            mRingRegistrant = new Registrant (h, what, obj);
        }
    } 

    这里有RegistrantList与Registrant类,注册事件以Registrant对象存储;

    下面是Registrant类得主要成员:

    public class Registrant{
        WeakReference   refH;
        int             what;
        Object          userObj;
        public Registrant(Handler h, int what, Object obj){
            refH = new WeakReference(h);
            this.what = what;
            userObj = obj;
        }
        
        public void notifyRegistrant(){
            internalNotifyRegistrant (null, null);
        }
        
        void internalNotifyRegistrant (Object result, Throwable exception){
          //通过Handler传递消息
        Handler h = getHandler();
        Message msg = Message.obtain();
        msg.what = what;
        msg.obj = new AsyncResult(userObj, result, exception);
        h.sendMessage(msg);
        }
    } 

      这里说直接使用Handler,来实现了一个Observer模式,但是Handler是处理线程的框架类,实现异步的处理消息,具有更强的功能。

    所以看到Telephony中很多类都是从Handler继承下来的,就是为了监听事件发生,状态变化等消息。

  • 相关阅读:
    PPK提供的浏览器类型及版本检测方法
    从KPI到OKR,高阶产品人如何推动业务高速增长
    线上流量越发昂贵,如何通过裂变营销实现业务增长?
    快速了解云原生架构
    阿里巴巴超大规模中台型团队研发提效实践
    如何通过数据智能玩转私域流量新生态
    Serverless Kubernetes:理想,现实与未来
    这只猫在云端定居了?边缘计算在天猫精灵云应用上的落地实践
    阿里毕玄:提升代码能力的4段经历
    你女朋友在买买买时,程序员小哥在干嘛?
  • 原文地址:https://www.cnblogs.com/bastard/p/2783229.html
Copyright © 2011-2022 走看看