Binder源码分析之Native层(原)

        前面两节中介绍了Binder机制中的 ServiceManagerBinder驱动,在这一节中,我们来介绍Native中的Binder通讯。

        为了更好的理解过程,我们挑选Native中的MediaServer进行分析。


一、MediaServer加载过程

        Android启动过程中会去执行init.rc脚本,在这个脚本中将会启动一些关键的系统服务,其中之一就是MediaServer:
    @init.rc(google-code\system\core\rootdir\init.rc)
    service media /system/bin/mediaserver
        class main
        user media
        group audio camera inet net_bt net_bt_admin net_bw_acct drmrpc
        ioprio rt 4
        这个脚本包含了几个重要信息:
        1、需要启动一个media的service,路径在/system/bin/mediaserver
        2、该服务的入口函数为main
        3、该服务运行在media的用户名下
        4、该服务属于以下组:audio camera inet等

        这些信息中,我们只关心service的名字(mediaserver)和入口函数(main),那么这个服务的入口函数究竟在那个文件里面呢?
        我们打开mediaserver模块,在模块的Android.mk文件中找到了这个Service的加载信息:
    @Android.mk(google-code\frameworks\av\media\mediaserver\)
    LOCAL_PATH:= $(call my-dir)
    include $(CLEAR_VARS)
    LOCAL_SRC_FILES:= main_mediaserver.cpp 
    LOCAL_MODULE:= mediaserver
        在这个脚本中,将main_mediaserver.cpp加载为mediaserver模块,因此,main_mediaserver.cpp文件就是我们要找的入口文件,而这个文件中的main函数就是我们要找的入口函数:
    @main_mediaserver.cpp
    int main(int argc, char** argv) {
        sp<ProcessState> proc(ProcessState::self());
        //得到ServiceManager
        sp<IServiceManager> sm = defaultServiceManager();
        //三个Service自身的初始化
        AudioFlinger::instantiate();
        MediaPlayerService::instantiate();
        CameraService::instantiate();
        AudioPolicyService::instantiate();
        ProcessState::self()->startThreadPool();
        IPCThreadState::self()->joinThreadPool();
    }

        下面我们就来详细看一下整个Service启动的流程。


二、ProcessState的初始化

        我们先来分析main中的第一步,也就是ProcessState::self()的过程。
    @ProcessState.cpp(google-code\frameworks\native\libs\binder\)
    sp<ProcessState> ProcessState::self() {
        if (gProcess != NULL) return gProcess;

        AutoMutex _l(gProcessMutex);
        if (gProcess == NULL) gProcess = new ProcessState;
        return gProcess;
    }
        这里我们看到, ProcessState是一个单例模式,所有的进程共享同一个ProcessState对象。如果初始化过了(gProcess!=NULL),就直接返回给客户端使用即可,没有的话需要创建ProcessState对象。这里我们假设当前没有被初始化过,那么就会调用他的构造函数:
    ProcessState::ProcessState()
        : mDriverFD(open_driver())
        , mVMStart(MAP_FAILED)
        , mManagesContexts(false)
        , mBinderContextCheckFunc(NULL)
        , mBinderContextUserData(NULL)
        , mThreadPoolStarted(false)
        , mThreadPoolSeq(1) 
    {
        if (mDriverFD >= 0) {
            //映射内存
            mVMStart = mmap(0, BINDER_VM_SIZE, PROT_READ, MAP_PRIVATE | MAP_NORESERVE, mDriverFD, 0);
            if (mVMStart == MAP_FAILED) {
                close(mDriverFD);
                mDriverFD = -1;
            }
        }
    }
        在他的初始化过程中,主要完成了两个重要步骤:
        1、 通过open_driver打开binder驱动,并把binder设备句柄传给mDriverFD
        2、 通过mmap()将一块内核地址映射到用户空间,作为buffer传输数据

        由此,就完成了ProcessState的初始化工作。


三、得到ServiceManager代理对象的过程

        main函数的下一个动作就是要得到ServiceManager的对象:
        sp<IServiceManager> sm = defaultServiceManager();
        那么是如何得到ServiceManager对象呢?得到的对象就是ServiceManager本身吗?我们从代码中找答案。
    @IServiceManager.cpp(google-code\frameworks\native\libs\binder\)
    sp<IServiceManager> defaultServiceManager() {
        if (gDefaultServiceManager != NULL) return gDefaultServiceManager;
        AutoMutex _l(gDefaultServiceManagerLock);
        if (gDefaultServiceManager == NULL) {
            //得到ServiceManager
            gDefaultServiceManager = interface_cast<IServiceManager>( ProcessState::self()->getContextObject(NULL));
        }
        return gDefaultServiceManager;
    }
        这里我们发现,defaultServiceManager()也是单例模式,就是说,如果其他Service已经申请到了ServiceManager,其他Service就可以直接使用,这里我们假设是第一次申请,那么就要通过下面方法申请:
        gDefaultServiceManager = interface_cast<IServiceManager>( ProcessState::self()->getContextObject(NULL));
        这个步骤稍微复杂,我们拆开分析:
        ProcessState::self()->getContextObject(NULL)
        interface_cast<IServiceManager>()

        上面第一步可以得到ServiceManager的BpBinder对象,第二步把得到的BpBinder对象转换为IServiceManager对象,下面我们逐步分析这两个过程。

3.1、得到ServiceManager的BpBinder对象

        ProcessState::self()->getContextObject(NULL)
        在第二节中我们介绍过,ProcessState::self()的过程就是完成ProcessState的初始化,然后返回ProcessState对象,因此,上面的代码相当于:
        ProcessState->getContextObject(NULL);
        我们来看这个过程:
    @ProcessState.cpp
    sp<IBinder> ProcessState::getContextObject(const sp<IBinder>& caller) {
        return getStrongProxyForHandle(0);
    }
        继续看getStrongProxyForHandle(),记住,传递下去的参数为0:
    sp<IBinder> ProcessState::getStrongProxyForHandle(int32_t handle) {
        sp<IBinder> result;
        //从数组中查找handle_entry,不存在的话就创建一个
        handle_entry* e = lookupHandleLocked(handle);
        if (e != NULL) {
            IBinder* b = e->binder;
            if (b == NULL || !e->refs->attemptIncWeak(this)) {
                //new一个BpBinder返回给调用者
                b = new BpBinder(handle); 
                e->binder = b;
                if (b) e->refs = b->getWeakRefs();
                result = b;
            } else {
                result.force_set(b);
                e->refs->decWeak(this);
            }
        }
        return result;
    }
        在这一步中,要先通过lookupHandleLocked()去查找当前handle的handle_entry对象,如果没有找到的话就会创建一个handle_entry,用于后续的Service使用,而且新建的handle_entry的binder变量为空,当前我们假设得到的就是新建的handle_entry对象,那么由于其e->binder为空,因此将会new一个BpBinder的对象作为其binder变量。
        这样一来,getStrongProxyForHandle()所返回的result就相当于我们刚刚new出来的BpBinder对象:
    sp<IBinder> ProcessState::getStrongProxyForHandle(int32_t handle) {
        return new BpBinder(handle); 
    }
        也就是说, 我们通过getStrongProxyForHandle()得到的就是BpBinder对象,不仅如此,而且我们得到的是 handle为0的BpBinder对象
        由此我们知道,通过:
        ProcessState::self()->getContextObject(NULL)
        我们得到的是BpBinder(0)的对象。

        下面我们来看如何将这个对象转换为ServiceManager对象。

3.2、得到ServiceManager的BpServiceManager对象

        经过3.1的分析,我们可以将第三节中的:
        gDefaultServiceManager = interface_cast<IServiceManager>( ProcessState::self()->getContextObject(NULL));
        转换为:
        gDefaultServiceManager = interface_cast<IServiceManager>(BpBinder(0));
        下面我们来分析interface_cast是如何将BpBinder对象进行转换的。

3.2.1、函数模版转换

        我们先来看一下这个函数模版:
    @IInterface.h(google-code\frameworks\native\include\binder\)
    template<typename INTERFACE>
    inline sp<INTERFACE> interface_cast(const sp<IBinder>& obj)
    {
        return INTERFACE::asInterface(obj);
    }
        这里要补充一下函数模版的知识。上面这个函数组成了一个标准的函数模版功能。
            首先,他表示一个函数,这个函数名就叫interface_cast,参数必须是const类型的IBinder指针。
            其次,既然是“模版”,就说明他只提供了一个框架(或者一种形式),可以适应多种环境调用。
        具体来说就是, 这个函数名叫interface_cast,调用这个函数必须传递进来一个IBinder的指针,但是他的返回值可以是不固定的,是根据传递进来的INTERFACE而定的。同时,返回值的具体值就是INTERFACE::asInterface(obj)。
        结合上面的代码来说,下面的语句:
        gDefaultServiceManager = interface_cast<IServiceManager>(BpBinder(0));
        其实包含了4个信息:
            1、调用名叫interface_cast函数模版
            2、模版参数为IServiceManager
            3、函数参数为BpBinder(0)
            4、返回值赋值给了gDefaultServiceManager
        这样一来,这个函数模版就相当于:
    sp<IServiceManager> interface_cast(const sp<IBinder>& obj)
    {
        return IServiceManager::asInterface(obj);
    }
        这里要求asInterface的参数obj是IBinder,而我们前面分析过我们得到的BpBinder对象就是IBinder类型的ServiceManager。因此,当初的:
        gDefaultServiceManager = interface_cast<IServiceManager>(BpBinder(0));
        将会等价于:
        gDefaultServiceManager = IServiceManager::asInterface(BpBinder(0));
        下面我们来看IServiceManager的asInterface()函数。

3.2.2、IServiceManager的asInterface函数

        在IServiceManager.cpp中我们并没有找到asInterface函数,但是在IServiceManager.h中却找到了一个宏控:
    @IServiceManager.h
    class IServiceManager : public IInterface {
        DECLARE_META_INTERFACE(ServiceManager);
    };
        我们查看这个宏控的定义:
    @IInterface.h(google-code\frameworks\native\include\binder\)
    #define DECLARE_META_INTERFACE(INTERFACE)                               \
            static const android::String16 descriptor;                          \
            static android::sp<I##INTERFACE> asInterface(                       \
                const android::sp<android::IBinder>& obj);                  \
            virtual const android::String16& getInterfaceDescriptor() const;    \
            I##INTERFACE();                                                     \
            virtual ~I##INTERFACE();
        这是一个宏定义可以看出,其中的asInterface()函数被宏定义为了:
        static android::sp<I##INTERFACE> asInterface(const android::sp<android::IBinder>& obj);
        替换掉INTERFACE可以得到:
        static android::sp<IServiceManager> asInterface(const android::sp<android::IBinder>& obj);
        也就是说,这段宏声明了asInterface函数,但是asInterface的定义呢?
    #define IMPLEMENT_META_INTERFACE(INTERFACE, NAME)                       \
        const android::String16 I##INTERFACE::descriptor(NAME);             \
        const android::String16&                                            \
                I##INTERFACE::getInterfaceDescriptor() const {              \
            return I##INTERFACE::descriptor;                                \
        }                                                                   \
        android::sp<I##INTERFACE> I##INTERFACE::asInterface(                \
                const android::sp<android::IBinder>& obj)                   \
        {                                                                   \
            android::sp
  • 3
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 7
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值