Android 以太网服务启动流程

本文详细解析了Android系统中以太网服务的启动流程,涵盖了EthernetService、EthernetNetworkFactory与ConnectivityService间的交互机制,并深入探讨了AsyncChannel在通信中的应用。
Android 以太网服务启动流程

一、引言

  阅读本文需要对Android系统的启动流程有一定的了解。如果读者还没有这方面的知识,建议大家先了解一下这方面的知识,鄙人后面也会专门做相关系列文章。这里先大概简单阐述一下(这里我们重点关注init以上的进程服务),方便阅读本文章。Android 在kernel内核启动后会加载启动Init进程,在Init进程中启动各种服务,包括显示系统的SurfaceFlinger,音频系统AudioFlinger,网络守护进程Netd等等,其中最重要一个进程是system_server进程,其是所有Framework层级系统服务的发动机。Init启动system_server后,会进入system_server的主方法,并且在主方法中调用startOtherService方法启动非关键的一些服务,而我们以太网服务就是从该方法启动。图1-1所示是以太网服务启动的整体流程。下面我们将具体分析各个服务的启动以及相互之间作用关系。
在这里插入图片描述

图1-1 Android以太网服务启动流程

名称解释:

ENF:EthernetNetworkFactory;

ES:EthernetService

ESI:EthernetServiceImpl

CS:ConnectivityService

NMS:NetworkManagementService

NF:NetworkFactory

二 以太网服务的启动流程

2.1 ES的角度分析以太网服务的启动

2.1.1 ES的启动流程

  根据前面的分析及图1-1的流程图,我们知道EthernetService是在SystemServer的startOtherService的方法中启动,下面我们来具体分析一下启动流程。

//framework/base/services/java/com/android/server/SystemServer.java
public final class SystemServer {
   
   
    private static final String ETHERNET_SERVICE_CLASS =  
        "com.android.server.ethernet.EthernetService";
    //Init进程启动System_Server,进入SystemServer的主方法
    public static void main(String[] args) {
   
   
        new SystemServer().run();
    }
    private void run() {
   
   
        startOtherService()
    }
    private void startOtherServices() {
   
   
        //Feature特性,具体定义在Android源码的frameworks/native/data/etc/下
        if (mPackageManager.hasSystemFeature(PackageManager.FEATURE_ETHERNET) ||    
          mPackageManager.hasSystemFeature(PackageManager.FEATURE_USB_HOST)) {
   
   
             traceBeginAndSlog("StartEthernet");
             mSystemServiceManager.startService(ETHERNET_SERVICE_CLASS);
             traceEnd();
         }
    }
}

这里是通过SystemServiceManager的方式启动ES服务的,这里就不详细介绍。这里在启动ES的时候使用了Feature控制,具体定义在Android源码/frameworks/native/data/etc/下。

<!--frameworks/native/data/etc-->
android.hardware.ethernet.xml
<permissions>
    <feature name="android.hardware.ethernet" />
</permissions>

在设备中的位置是在/vendor/etc/permissions/,该目录保存了大部分厂商的配置的文件:

Mate:/ # ls -l ./vendor/etc/permissions/
total 80
-rw-r--r-- 1 root root  820 2009-01-01 08:00 android.hardware.bluetooth.xml
-rw-r--r-- 1 root root  830 2009-01-01 08:00 android.hardware.bluetooth_le.xml
-rw-r--r-- 1 root root  877 2009-01-01 08:00 android.hardware.camera.front.xml
-rw-r--r-- 1 root root  877 2009-01-01 08:00 android.hardware.camera.xml
-rw-r--r-- 1 root root  834 2009-01-01 08:00 android.hardware.ethernet.xml
-rw-r--r-- 1 root root  870 2009-01-01 08:00 android.hardware.opengles.aep.xml
-rw-r--r-- 1 root root  824 2009-01-01 08:00 android.hardware.sensor.accelerometer.xml
-rw-r--r-- 1 root root 1035 2009-01-01 08:00 android.hardware.touchscreen.multitouch.xml
-rw-r--r-- 1 root root  845 2009-01-01 08:00 android.hardware.usb.accessory.xml
-rw-r--r-- 1 root root  868 2009-01-01 08:00 android.hardware.usb.host.xml
-rw-r--r-- 1 root root  904 2009-01-01 08:00 android.hardware.vulkan.version.xml
-rw-r--r-- 1 root root  843 2009-01-01 08:00 android.hardware.wifi.direct.xml
-rw-r--r-- 1 root root  845 2009-01-01 08:00 android.hardware.wifi.passpoint.xml
-rw-r--r-- 1 root root  829 2009-01-01 08:00 android.hardware.wifi.xml
-rw-r--r-- 1 root root  747 2009-01-01 08:00 android.software.backup.xml
-rw-r--r-- 1 root root  875 2009-01-01 08:00 android.software.ipsec_tunnels.xml
-rw-r--r-- 1 root root  745 2009-01-01 08:00 android.software.midi.xml
-rw-r--r-- 1 root root  753 2009-01-01 08:00 android.software.verified_boot.xml
-rw-r--r-- 1 root root 1093 2009-01-01 08:00 sensor_feature.xml
-rw-r--r-- 1 root root 2555 2009-01-01 08:00 tablet_core_hardware.xml

  设备在系统开机过程中会读取/vendor/etc/permissions/目录下对应的配置文件,然后在SystemServer中启动相关服务的时候会通过该配置文件进行匹配,依此来决定是否启动相关服务,正如我们ES一样。我们平时系统服务裁剪,就可以通过配置Feature的方式决定是否启动对应的服务。

  下面我们具体看下ES的启动流程:

//frameworks/opt/net/ethernet/java/com/android/server/ethernet/EthernetService.java
public final class EthernetService extends SystemService {
   
               

    private static final String TAG = "EthernetService";
    //这里是以太网服务的真正核心实现
    final EthernetServiceImpl mImpl;
    public EthernetService(Context context) {
   
                            
        super(context); 
        //初始化EthernetServiceImpl服务
        mImpl = new EthernetServiceImpl(context);
    }
                                                                      
    @Override                                                         
    public void onStart() {
   
   
        Log.i(TAG, "Registering service " + Context.ETHERNET_SERVICE);
        publishBinderService(Context.ETHERNET_SERVICE, mImpl);
    }

    @Override                                                         
    public void onBootPhase(int phase) {
   
   
        //在系统SYSTEM_SERVICES_READY阶段,调用EthernetServiceImpl服务的start方法
        if (phase == SystemService.PHASE_SYSTEM_SERVICES_READY) {
   
   
            mImpl.start();
        }
    }
}                                                                     

  ES服务并不复杂,真正起作用的是ESImpl服务。在EthernetService服务的构造方法中创建了ESI对象。该对象在ES的onStart方法中通过publishBinderService将其注册到SystemManager中以供客户端使用。至此用户就可以通过对外暴露接口来使用以太网的服务了。然后在系统SYSTEM_SERVICES_READY阶段,调用ESI服务的start方法进行初始化的工作。而ESImpl又委托给EthernetTracker来完成以太网的具体工作。

//frameworks/opt/net/ethernet/java/com/android/server/ethernet/EthernetServiceImp.java
public class EthernetServiceImpl extends IEthernetManager.Stub {
   
    
    private static final String TAG = "EthernetServiceImpl";
    private EthernetTracker mTracker;
    
    public void start() {
   
   
       Log.i(TAG, "Starting Ethernet service");
       HandlerThread handlerThread = new HandlerThread("EthernetServiceThread");
       handlerThread.start();
       mHandler = new Handler(handlerThread.getLooper());
       //创建EthernetTracker对象,注意此时的mHandler的looper,后面ENS和CS之间的通信会用的着
       mTracker = new EthernetTracker(mContext, mHandler);
       mTracker.start();            
    }
}

  该构造方法比较简单,主要创建一个EthernetTracker这个对象。该类是以太网络连接的管理对象,Android 以太网框架源码分析启动篇正如中介绍一样,该对象在以太网服务中扮演着重要角色。EthernetTracker可以持有NMS对象mNMService,通过mNMService可以访问到Netd的接口。另外mFactory对象又可以和CS进行相互通信。因此,该对象是整个以太网的中枢所在。

//frameworks/opt/net/ethernet/java/com/android/server/ethernet/EthernetTracker.java
final class EthernetTracker {
   
   
    //NMS对象,通过该对象访问Netd的相关接口
    private final INetworkManagementService mNMService;
    private final Handler mHandler;
    //主要更新网络连接状,链路配置,网络能力给ConnectivityService,同时接受来自ConnectivityService
    //禁止自动连接,网络有效性等信息
    private final EthernetNetworkFactory mFactory;
    //存储以太网配置信息,
    private final EthernetConfigStore mConfigStore;
    
    EthernetTracker(Context context, Handler handler) {
   
   
       // The services we use.
       IBinder b = ServiceManager.getService(Context.NETWORKMANAGEMENT_SERVICE);
       mNMService = INetworkManagementService.Stub.asInterface
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

GitFranc

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值