zoukankan      html  css  js  c++  java
  • android sensor架构

    Android Sensor 架构深入剖析

    作者:倪键树,华清远见嵌入式学院讲师。

    1、Android sensor架构

    Android4.0系统内置对传感器的支持达13种,它们分别是:加速度传感器 (accelerometer)、磁力传感器(magnetic field)、方向传感器(orientation)、陀螺仪(gyroscope)、环境光照传感器(light)、压力传感器(pressure)、温度传感器(temperature)和距离传感器(proximity)等。

    Android实现传感器系统包括以下几个部分:

    各部分之间架构图如下:

    2、Sensor HAL层接口

    Google为Sensor提供了统一的HAL接口,不同的硬件厂商需要根据该接口来实现并完成具体的硬件抽象层,Android中Sensor的HAL接口定义在:hardware/libhardware/include/hardware/sensors.h

    对传感器类型的定义:

    传感器模块的定义结构体如下:

    该接口的定义实际上是对标准的硬件模块hw_module_t的一个扩展,增加了一个get_sensors_list函数,用于获取传感器的列表。

    对任意一个sensor设备都会有一个sensor_t结构体,其定义如下:

    每个传感器的数据由sensors_event_t结构体表示,定义如下:

    其中,sensor为传感器的标志符,而不同的传感器则采用union方式来表示,sensors_vec_t结构体用来表示不同传感器的数据,sensors_vec_t定义如下:

    Sensor设备结构体sensors_poll_device_t,对标准硬件设备 hw_device_t结构体的扩展,主要完成读取底层数据,并将数据存储在struct sensors_poll_device_t结构体中,poll函数用来获取底层数据,调用时将被阻塞定义如下:

    控制设备打开/关闭结构体定义如下:

    3、Sensor HAL实现(以LM75温度传感器为例子)

    (1)打开设备流程图

    (2)实现代码分析

    在代码中含有两个传感器ADC电位器和LM75温度传感器,所以在sensor.c中,首先需要定义传感器数组device_sensor_list[],其实就是初始化struct sensor_t结构体,初始化如下:

    定义open_sensors函数,来打开Sensor模块,代码如下:

    在这个方法中,首先需要为hw_device_t分配内存空间,并对其初始化,设置重要方法的实现。

    control_open_data_source()打开传感器并使能设备:

    调用sensor__data_poll方法读取数据:

    /*轮询读取数据*/
            static int sensors__data_poll(struct sensors_data_context_t *dev, sensors_data_t * values)
            {
                int n;
                int mag;
                float temp;
                char buf[10];
                while (1) {
                if(count % 3 == 2) // 读取ADC值
                {
                    if( read(dev->event_fd[0], &mag, sizeof(mag)) < 0)
                    {
                       LOGE("read adc error");
                    }else{ 
                    dev->sensors[ID_MAGNETIC_FIELD].magnetic.v[0] =(float)mag; 
                    LOGE("read adc %f ",(float)mag);
                    *values = dev->sensors[ID_MAGNETIC_FIELD];
                    values->sensor = ID_MAGNETIC_FIELD;
                    count++;
                    }
                    usleep(500000);
                    return ID_MAGNETIC_FIELD;
                    }
                    else if(count%3 == 1) //读取温度传感器值
                     {
                    memset(buf, 0 ,sizeof(buf));
                    if((n = read(dev->event_fd[1], buf, 10)) < 0)
                    {
                        LOGE("read temp error");
                        }else{
                        buf[n - 1] = '';
                        temp =(float) (atoi(buf) / 1000);
                        dev->sensors[ID_TEMPERATURE].temperature = temp;
                        LOGE("read temp %f ",temp);
                        *values = dev->sensors[ID_TEMPERATURE];
                        values->sensor = ID_TEMPERATURE;
                        count++;
                    }
                        close(dev->event_fd[1]);
                        dev->event_fd[1]= open("/sys/bus/i2c/devices/0-0048/temp1_input", O_RDONLY);
                        usleep(500000);
                        return ID_TEMPERATURE;
                   }
                   else if(count%3 == 0) //读取方向传感器模拟值
                     {
                        LOGI("read orientation ");
                        /* fill up data of orientation */
                        dev->sensors[ID_ORIENTATION].orientation.azimuth = x + 5;
                        dev->sensors[ID_ORIENTATION].orientation.pitch = y + 5;
                        dev->sensors[ID_ORIENTATION].orientation.roll = z + 5;
                        *values = dev->sensors[ID_ORIENTATION];
                        values->sensor = ID_ORIENTATION;
                        count++;
                        x += 0.0001; y += 0.0001; z += 0.0001;
                        usleep (500000);
                        return ID_ORIENTATION;
                  }
                }
            }

     
     
    下面是另外的博主写的内容
     

    1. 体系结构

    2. 数据结构

    3. 四大函数


    本文以重力感应器装置G-sensor为例探索Android的各层次结构。

    1. 体系结构

        Android的体系结构可分为4个层次。

    • 第一层次  底层驱动层,包括标准Linux,Android核心驱动,Android相关设备驱动,G-sensor的设备驱动程序即存在于此
    • 第二层次 Android标准C/C++库,包括硬件抽象层,Android各底层库,本地库,JNI
    • 第三层次 Android Java Framwork框架层
    • 第四层次 Java应用程序

    本文重点关注硬件抽象层,JNI以及Framework。

    1.1 硬件抽象层

          硬件抽象层通过例如open(), read(), write(), ioctl(), poll()等函数调用的方式,与底层设备驱动程序进行交互,而这些函数调用是底层设备驱动程序事先准备好的。

          用于交互的关键是文件描述符fd,fd通过open()打开G-sensor设备节点而得到,即 fd = open ("/dev/bma220", O_RDONLY);而/dev/bma220这个设备节点是在底层设备驱动中注册完成的。

          其他的函数调用如read(), write()等都通过该文件描述符fd对G-sensor设备进行操作。

    1.2 JNI (Java Native Interface)

          JNI层可以认为是整个体系结构中的配角,概括地讲,它就完成了一项任务,既实现从C++语言到Java语言的转换。JNI层为Java Framework层提供一系列接口,而这些接口函数的具体实现中,利用例如module->methods->open(), sSensorDevice->data_open(), sSensorDevice->poll()等回调函数与硬件抽象层进行交互。而这些open(), poll()回调函数在硬件抽象层中具体实现。

    1.3 Java Framework

          Framework层提供各种类和类的对象,可作为系统的守护进程运行,也可供上层应用程序的使用。

          例如类SensorManager,它作为系统的守护进程在初始化的时候开始运行,其子类SensorThread中的子类SensorThreadRunnable通过sensors_data_poll()实现了对G-sensor数据的轮训访问,而sensors_data_poll()通过JNI层转换到硬件抽象层去具体实现poll()。

    2 数据结构

         一般境况下,硬件抽象层对硬件的描述都分为control和data两大类。

    2.1 sensors_control_context_t

    struct sensors_control_context_t {
        struct sensors_control_device_t device;

        int fd;
    };

    struct sensors_control_device_t {
        struct 
    hw_device_t 
    common;
        int (*open_data_source)(struct sensors_control_device_t *dev);
        int (*activate)(struct sensors_control_device_t *dev, int handle, int enabled);
        int (*set_delay)(struct sensors_control_device_t *dev, int32_t ms);

        int (*wake)(struct sensors_control_device_t *dev);
    };

    2.2 sensors_data_context_t

    struct sensors_data_context_t {
        struct sensors_data_device_t device;

        int fd;
    };

    struct sensors_data_device_t {
        struct hw_device_t common;

        int (*data_open)(struct sensors_data_device_t *dev, int fd);
        int (*data_close)(struct sensors_data_device_t *dev);
        int (*poll)(struct sensors_data_device_t *dev,
                sensors_data_t* data);
    }

    struct hw_device_t {
        uint32_t tag; uint32_t version;

        struct hw_module_t* module;

        int (*close)(struct hw_device_t* device);
    };

    struct hw_module_t {
        uint32_t tag; uint16_t version_major; uint16_t version_minor;

        const char *id; const char *name; const char *author;

        struct hw_module_methods_t* methods;
    };

    struct hw_module_methods_t {
        int (*open)(const struct hw_module_t* module, const char* id,
                struct hw_device_t** device);
    };

    下文将通过对(*open), (*open_data_source), (*data_open)和(*poll)的代码分析,探索Android的各层次架构。

    3 四大函数

    3.1 module->methods->open()

    1) Framework

        SensorService作为系统守护进程运行,其类的构造函数实现_sensors_control_init()。

    2) JNI

        为_sensors_control_init()提供接口android_init(),并执行回调函数module->methods->open();

    3) 硬件抽象层

        具体实现(*open),该函数为所有G-sensor回调函数的指针赋值。

    3.2 sSensorDevice->open_data_source()

    1) Framework

        SensorService作为系统守护进程运行,其类的一个公有成员ParcelFileDescriptor通过实现_sensors_control_open()得到设备的文件描述符。

    2) JNI

        为_sensors_control_open()提供接口android_open(),并执行回调函数sSensorDevice->open_data_source();

    3) 硬件抽象层

        具体实现(*open_data_source),该函数通过打开G-sensor的设备节点得到文件描述符fd = open ("/dev/bma220", O_RDONLY);

    4) 设备驱动层

        通过misc_register()对G-sensor设备进行注册,建立设备节点。

    3.3 sSensorDevice->data_open()

    1) Framework

        SensorManager作为系统守护进程运行,其子类SensorThreadRunnable的行为函数run()实现sensors_data_open()。

    2) JNI

        为sensors_data_open()提供接口sensors_data_open(),并执行回调函数sSensorDevice->data_open();

    3) 硬件抽象层

        具体实现(*data_open),该函数的功能就是将已经得到的文件描述符fd复制一份到sensors_data_context结构体中的dev->fd,以便为处理数据的回调函数如(*poll)使用。

    3.4 sSensorDevice->poll()

     

    1) Framework

        SensorManager作为系统守护进程运行,其子类SensorThreadRunnable的行为函数run()实现sensors_data_poll(values, status, timestamp),其目的是通过此函数得到从底层传上来的有关G-sensor的数据values, status和timestamp,再通过此类的一个行为函数listener.onSensorChangedLocked(sensorObject, values, timestamp, accuracy);为上层应用程序提供了得到G-sensor设备数据的接口函数。

    2) JNI

        为sensors_data_poll()提供接口sensors_data_poll(),并执行回调函数sSensorDevice->poll(sSensorDevice, &data);其中,得到的data就是从底层传上来的G-sensor数据,然后通过下图的方式将data中对应的数据分别赋给values, status和timestamp。

     

    3) 硬件抽象层

        具体实现(*poll),该函数通过ioctl()实现与底层驱动程序的交互。

        ioctl(dev->fd, BMA220_GET_ORIENTATION, &orient_value);

        其中,dev->fd即刚才由(*data_open)得到的文件描述符,BMA220_GET_ORIENTATION为ioctl的一个命令,具体实现由底层驱动程序完成,orient_value即得到的G-sensor数据,它通过下图的方式将相对应的数据赋给了data结构体中的values, status和time,从而最终实现了从底层到上层的数据通信。

    4) 设备驱动层

        与硬件抽象层交互的read(), write(), ioctl()函数由设备驱动实现。以ioctl()的一条命令BMA220_GET_ORIENTATION为例,

    通过bma220_get_orientation(data)得到G-sensor的数据data,然后将其从内核空间上传到用户空间的arg.

     

     

    继续添加一些基础知识

     

    转自:

    http://yueguc.iteye.com/blog/814000

    1.使G-sensor正常工作需要做的事:
    G-sensor driver文件包括:
    driver/i2c/chips/lis331dl.c
    driver/i2c/chips/sensorioctl.h
    include/linux/lis331dl.h
    并在/kernel/arch/arm/mach-s3c6410/mach-ur6410.c文件中i2c chanel1的结构变量i2c_devs1[] __initdata中需要添加G-sensor的设备信息,
    以使driver成功加载。
    同时在该文件中添加一个结构变量
    //JayLin add for Gsensor
    struct lis331dl_platform_data lisGsensor_platform_data={
    .name="lis331dl",
    .pin_clk=0,
    .pin_data=0,
    .open_drain=1,
    .interrupt=IRQ_EINT(3),
    };
    该结构变量在i2c_devs1[] __initdata中被引用。
    /kernel/arch/arm/mach-s3c6410/mach-ur6410.c 中需要包含lis331dl.h。
    在rootfs/system/etc/init.board.sh的最后一行加上mknod /dev/sensorioctl c 51 201&创建节点供ioctl使用。
    编译后的sensor.so放在/rootfs/system/lib/hw下。
    sensor.so和driver之间通过ioctl实现对G-sensor的状态控制。ioctl的命令编号定义在头文件sensorioctl.h中,分别放在
    kernel/include/linux下
    androidsourcecode/hardware/libhardware/include/hardware下
    供driver和sensor.so使用。
    G-sensor driver工作的大致流程:
    系统开机后,先加载i2c总线驱动,然后加载设备驱动。
    在设备驱动中的init函数中通过调用i2c_add_driver(&lis331dl_i2c_driver)注册i2c_driver;此函数将driver注册到i2c_bus_type的总线上,此总线的匹配规则是利用i2c_client的名称和
    i2c_driver中id_table中的名称作匹配。
    其中i2c_client是注册板载信息是系统自动创建的,注册板载信息的过程就是在/kernel/arch/arm/mach-s3c6410 /mach-ur6410.c文件中i2c chanel1的结构变量i2c_devs1[] __initdata中需要添加G-sensor的设备信息。
    当匹配成功时,i2c_driver中的probe()函数开始执行。
    Probe()函数主要完成以下功能:
    1.从i2c_client结构中得到初始化信息
    2.创建G-sensor的工作队列
    2.注册input_device设备
    3.读取Chip ID
    4.设置寄存器,使能G-sensor
    5.设置并启动中断
    当G-sensor上报数据的时候会触发中断,然后在中断处理函数中提交一个报值的任务到队列中并禁止中断。
    在工作队列中读数G-sensor的数据并上报到input子系统中,最后使能中断。
    2.android上层应用apk到G-sensor driver的大致流程:
    Android对于Sensor的API定义在 hardware/libhardware/include/hardware/sensor.h中, 要求在sensor.so提供以下8个API函数
    [控制方面]
    int (*open_data_source)(struct sensors_control_device_t *dev);
    int (*activate)(struct sensors_control_device_t *dev, int handle, int enabled);
    int (*set_delay)(struct sensors_control_device_t *dev, int32_t ms);
    int (*wake)(struct sensors_control_device_t *dev);
    [数据方面]
    int (*data_open)(struct sensors_data_device_t *dev, int fd);
    int (*data_close)(struct sensors_data_device_t *dev);
    int (*poll)(struct sensors_data_device_t *dev, sensors_data_t* data);
    [模块方面]
    int (*get_sensors_list)(struct sensors_module_t* module, struct sensor_t const** list);
    在Java层Sensor的状态控制由SensorService来负责,它的java代码和JNI代码分别位于:
    frameworks/base/services/java/com/android/server/SensorService.java
    frameworks/base/services/jni/com_android_server_SensorService.cpp
    在Java层Sensor的数据控制由SensorManager来负责,它的java代码和JNI代码分别位于:
    frameworks/base/core/java/android/hardware/SensorManager.java
    frameworks/base/core/jni/android_hardware_SensorManager.cpp
    android framework中与sensor通信的是sensorService.java和sensorManager.java。
    sensorService.java的具体通信是通过JNI调用sensorService.cpp中的方法实现的。
    sensorManager.java的具体通信是通过JNI调用sensorManager.cpp中的方法实现的。
    sensorService.cpp和sensorManger.cpp通过hardware.c与sensor.so通信。其中sensorService.cpp实现对sensor的状态控制,sensorManger.cpp实现对sensor的数据控制。
    sensor.so通过ioctl控制sensor driver的状态,通过打开sensor driver对应的设备文件读取G-sensor采集的数据。
    android SDK提供了4个类来于sensor通信,分别为 sensor,sensorEvent,sensorEventListener,sensorManager.其中 sensorEventListener用来在sensorManager中注册需要监听的sensor类型。
    sensorManager.java提供registrater(),unregistrater()接口供sensorEventListener使用。
    sensorManager.java不断轮询从sensor.so中取数据。取到数据后送给负责监听此类型sensor的 sensorEventListener.java。sensorEventListener.java通过在sensorManager.java中注 册可以监听特定类型的sensor传来的数据。
    系统启动时执行systemProcess,会启动sensorService.java,在sensorService.java的构造函数中调用JNI方法_sensor_control_init()。
    sensorService.cpp中相应的方法android_int()会被执行。该函数会调用hardware.c中的方法hw_get_module()此函数又通过调用load()函数在system/lib/hw下查找sensor.so
    查找时会根据harware.c中定义好的sensor.*.so的扩展名的顺序查找,找到第一个匹配的时候即停止,并将该sensor.so中定义好的一个全局变量HAL_MODULE_INFO_SYM带回。该变量包含的一个
    重要信息是它的一个成员结构变量中包含的一个函数指针open,该指针所指函数会对一个device结构变量赋值,从而带出sensorService.cpp 和sensorManager.cpp与sensor通信所需要的全部信息。
    device结构变量有两种变体分别供sensorService.cpp和sensorManaer.cpp使用。其中主要是一些函数指针指向与sensor通信的函数。
    sensorService.cpp和sensorManager.cpp在得到HAL_MODULE_INFO_SYM结构后都会调用 sensors.h的inline函数open()通过HAL_MODULE_INFO_SYM的open函数指针将所需的device信息取回。
    系统在启动activityManager.java时,它会启动sensorManager.java,它也会调用hardware.c中的方法hw_get_module()带回HAL_MODULE_INFO_SYM。
    3.关于Rotate的实现:
    系统启动windowManger.java时,它会启动phoneWindowManager.java,该类有一个内部类myOrientationListener扩展自windowOrientationListener.java。
    windowOrientationListener.java是一个辅助类,当device的方向发生变化时,供windowManger.java调用,用来接收数据。
    windowOrientationListener.java 内部在sensorManger.java中进行了注册,它回监听G-sensor传来的数据,即x,y,z方向的加速度,收到数据后经过转换处理,若满足Roate条件则调用
    IwindowManager接口的实现类windowManagerService.java中的setRotation()方法实现转屏。
    SensorManager通过polling的方式从设备得到Sensor数据, Sensor数据的结构定义在sensor.h里,
    其中SensorManager只处理了 vector.v, vector.status, time三个域, 分发给已注册的对这些消息的监听者
    比如第一项 vector.v包含x,y,z三个方向的信息值,就是由 WindowOrientataionLister注册的,
    当 SensorManager获取到这三个值之后,会传递给 WindowOrientataionLister,后者代码位于:
    frameworkd/base/core/java/android/view/WindowOrientationListener.java
    WindowOrientataionLister接收到这三个值之后,会计算出设备对应的orientation,并且执行 onOrientationChanged函数进一步上传
    WindowOrientataionLister是个纯虚类,如果在APK里需要控制方向,可以重载一个实例,
    而Android的系统实例对应在 PhoneWindowManager.java里,名字为MyOrientationListener
    frameworks/policies/base/phone/com/android/internal/policy/impl/PhoneWindowManager.java
    如果需要旋转, MyOrientationListener则会调用以下代码进行窗口旋转:
    mWindowManager.setRotation(rotation, false, mFancyRotationAnimation);
    问题总结:
    1.将lis302 G-sensor driver从spi总线移植到lis331 i2c总线时遇到的一些问题:
    a).lis331用的中断管脚与lis302不同,通过硬件原理图可知lis331用的是GPN3.故需要在driver的probe中设置 writel((readl(S3C64XX_GPNCON) & ~(0xc0)) | (0x80), S3C64XX_GPNCON);
    b).通过硬件原理图可知lis331的时钟线和数据线用的是i2c chanel1。故需要在/kernel/arch/arm/mach-s3c6410/mach-ur6410.c文件中i2c chanel1即结构变量i2c_devs1[] __initdata中
    添加G-sensor的设备信息,以使driver成功加载。
    c).lis331 driver是中断驱动的,每次G-sensor搜集到新数据都会产生中断,driver要在中断中通过i2cbus将数据从G-sensor中取回。由 于i2cbus的读写操作是可能休眠的,而中断中不允许调用可能休眠的函数,故通过linux提供的延迟机制work_queue来解决。
    问题b)的原理:
    i2c驱动包括总线驱动和设备驱动
    总线驱动只是提供对一条特定总线的读写机制,本身并不会去做通信。通过i2c总线驱动提供的函数,设备驱动可以忽略不同总线控制器的差异,不考虑其细节的与硬件设备通讯。
    一个总线驱动通常需要2个模块:struct i2c_adapter和struct i2c_algorithm 定义在include/linux/i2c.h中
    struct i2c_algorithm是为了i2c总线驱动和具体的i2c总线能够对话。很多i2c总线驱动定义和使用它们自己的algorithm.对于一些i2c总线驱动来说,很多algorithm已经写好了。
    drivers/i2c/buses中包含所有的i2c总线驱动,drivers/i2c/algos中包含了所有的algorithm.
    设备驱动通过总线驱动中的读写函数同具体的i2c设备通信,一个设备驱动用两个模块来描述:struct i2c_driver 和struct i2c_client.
    i2c_client代表着位于adapter总线上地址为address,使用driver来驱动的一个设备。它将总线驱动,设备驱动以及设备地址绑定到了一起。
    2.实现sensor.so与driver之间的ioctl时遇到的问题:
    sensor.so中pull数据时打开的文件是input子系统中逻辑input设备的表示层即event handler层中的evdev.c创建的,如果通过此文件描述符实现ioctl,则只能实现与event handler通信,无法实际控制
    Gsnsor driver. event handler层与物理设备的实际driver是通过input.c联系起来的,但input.c中没有实现将event handler层的ioctl传递到实际driver中。
    故采用另创建一个设备节点用来实现sensor.so与driver之间的ioctl.

     

    下面关于sensor转自:

    http://blog.csdn.net/myarrow/article/details/9044689
     

    1. 简介

        在了解Sensor工作流程以前,一直以为其事件是通过Event Hub来进行输送的,可是研究完Android4.0代码之后,才发现自己错了。

        其主要框架如下图所示:

     

    2.功能模块

    2.1 SensorManager.java

    与下层接口功能:
    1) 在SensorManager函数中
       (1) 调用native sensors_module_init初始化sensor list,即实例化native中的SensorManager

       (2) 创建SensorThread线程

    2) 在类SensorThread中
       (1) 调用native sensors_create_queue创建队列
       (2) 在线程中dead loop地调用native sensors_data_poll以从队列sQueue中获取事件(float[] values = new float[3];)
       (3) 收到事件之后,报告sensor event给所有注册且关心此事件的listener

     

    与上层的接口功能:

    1) 在onPause时取消listener注册

    2) 在onResume时注册listener

    3) 把收到的事件报告给注册的listener

    2.2 android_hardware_SensorManager.cpp

          实现SensorManager.java中的native函数,它主要调用SenrsorManager.cpp和SensorEventQueue.cpp中的类来完成相关的工作。

    2.3 SensorManager.cpp

    1. class SensorManager :  
    2.     public ASensorManager,  
    3.     public Singleton<SensorManager>  
    4. {  
    5. public:  
    6.     SensorManager(); //调用assertStateLocked
        
    7.     ~SensorManager();  
    8.     //调用assertStateLocked,并返回mSensorList 
        
    9.     ssize_t getSensorList(Sensor constconst** list) const;  
    10.   
    11.     // 返回mSensorList中第一个类型与type一致的sensor    
        
    12.     Sensor const* getDefaultSensor(int type);  
    13.   
    14.     // 调用mSensorServer->createSensorEventConnection创建一个连接(ISensorEventConnection)
        
    15.     // 并用此连接做为参数创建一个SensorEventQueue对象并返回
        
    16.     sp<SensorEventQueue> createEventQueue();  
    17.   
    18. private:  
    19.     // DeathRecipient interface
        
    20.     void sensorManagerDied();  
    21.     // 调用getService获取SensorService客户端并保存在mSensorServer中
        
    22.     // 调用mSensorServer->getSensorList获取sensor列表,并保存在mSensors和mSensorList中
        
    23.     status_t assertStateLocked() const;  
    24.   
    25. private:  
    26.     mutable Mutex mLock;  
    27.     mutable sp<ISensorServer> mSensorServer; // SensorService客户端
        
    28.     mutable Sensor const** mSensorList; // sensor列表
        
    29.     mutable Vector<Sensor> mSensors;    // sensor列表
        
    30.     mutable sp<IBinder::DeathRecipient> mDeathObserver;  
    31. }  

     

    1. class ISensorEventConnection : public IInterface  
    2. {  
    3. public:  
    4.     DECLARE_META_INTERFACE(SensorEventConnection);  
    5.   
    6.     virtual sp<SensorChannel> getSensorChannel() const = 0;  
    7.     virtual status_t enableDisable(int handle, bool enabled) = 0;  
    8.     virtual status_t setEventRate(int handle, nsecs_t ns) = 0;  
    9. };  

    2.4 SensorService.cpp

           SensorService作为一个轻量级的system service,它运行于SystemServer内,即在system_init<system_init.cpp>调用SensorService::instantiate();

          SensorService主要功能如下:
              1) SensorService::instantiate创建实例对象,并增加到ServiceManager中,且创建并启动线程,并执行threadLoop
              2) threadLoop从sensor驱动获取原始数据,然后通过SensorEventConnection把事件发送给客户端
              3) BnSensorServer的成员函数负责让客户端获取sensor列表和创建SensorEventConnection

          SensorService与客户端的接口定义如下:

    1. class ISensorServer : public IInterface  
    2. {  
    3. public:  
    4.     DECLARE_META_INTERFACE(SensorServer);  
    5.   
    6.     virtual Vector<Sensor> getSensorList() = 0;  
    7.     virtual sp<ISensorEventConnection> createSensorEventConnection() = 0;  
    8. };  

        SensorService定义如下:

    1. class SensorService :  
    2.         public BinderService<SensorService>, //创建SensorService对象,并增加到ServiceManager中
        
    3.         public BnSensorServer, // 申明了SensorService与客户端(SensorManager)间的binder接口
        
    4.         protected Thread // 线程辅助类,调用run创建并启动线程,然后在线程主函数内回调threadLoop函数,
        
    5.                          // 所以在使用它时,做一个派生,并根据需要重写threadLoop即可
        
    6.                       
    7. {  
    8.    friend class BinderService<SensorService>;  
    9.   
    10.    static const nsecs_t MINIMUM_EVENTS_PERIOD =   1000000; // 1000 Hz
        
    11.   
    12.             SensorService();  
    13.     virtual ~SensorService();  
    14.      
    15.     /* 
    16.     在addService时,第一次构建sp强引用对象时,会调用onFirstRef函数 
    17.      实现功能如下: 
    18.      1) 获取SensorDevice实例 
    19.      2) 调用SensorDevice.getSensorList获取sensor_t列表 
    20.      3) 根据硬件sensor_t创建HardwareSensor,然后加入mSensorList(Sensor) 
    21.             和mSensorMap(HardwareSensor)中 
    22.      4) 根据硬件sensor_t创建对应的senosr(如GravitySensor), 
    23.             然后加入mVirtualSensorList和mSensorList中 
    24.      5) mUserSensorList = mSensorList; 
    25.      6) run("SensorService", PRIORITY_URGENT_DISPLAY);运行线程,并执行threadLoop 
    26.     */  
    27.     virtual void onFirstRef();   
    28.   
    29.     // Thread interface 
        
    30.     /* 
    31.       1) 调用SensorDevice.poll获取sensors_event_t事件 
    32.       2) 获取已经激活的sensor列表mActiveVirtualSensors 
    33.       3) 对每一个事件,执行SensorFusion.process 
    34.       4) 对每一个事件,执行HardwareSensor.process(事件无变化,直接copy) 
    35.       5) 调用SensorService::SensorEventConnection::sendEvents,把事件发 
    36.              送给所有的listener 
    37.     */  
    38.     virtual bool threadLoop();  
    39.   
    40.     // ISensorServer interface   
    41.     // 返回mUserSensorList 
        
    42.     virtual Vector<Sensor> getSensorList();  
    43.       
    44.     // 实例化SensorEventConnection并返回 
        
    45.     virtual sp<ISensorEventConnection> createSensorEventConnection();  
    46.   
    47.     virtual status_t dump(int fd, const Vector<String16>& args);  
    48.   
    49.     //====================================================================
        
    50.     //============== SensorEventConnection  start ========================
        
    51.     class SensorEventConnection : public BnSensorEventConnection {  
    52.   
    53.         virtual ~SensorEventConnection();  
    54.         virtual void onFirstRef();  
    55.   
    56.     // 返回mChannel   
    57.         virtual sp<SensorChannel> getSensorChannel() const;  
    58.   
    59.     // 调用SensorService::enable或SensorService::disable
        
    60.         virtual status_t enableDisable(int handle, bool enabled);  
    61.   
    62.         // 调用SensorService::setEventRate 
        
    63.         virtual status_t setEventRate(int handle, nsecs_t ns);  
    64.   
    65.         sp<SensorService> const mService; // 保存当前SensorService实例
        
    66.         sp<SensorChannel> const mChannel; // SensorChannel实例
        
    67.         mutable Mutex mConnectionLock;  
    68.   
    69.         // protected by SensorService::mLock
        
    70.         SortedVector<int> mSensorInfo;  
    71.   
    72.     public:  
    73.         /* 
    74.           1) 把当前service保存在mService中 
    75.           2) 创建SensorChannel实例,并保存在mChannel中 
    76.              (在SensorChannel::SensorChannel中创建pipe,并把收和发都设置非阻塞) 
    77.         */  
    78.         SensorEventConnection(const sp<SensorService>& service);  
    79.   
    80.         // 调用连接中的mChannel->write (SensorChannel::write),把符合条件的事件写入pipe
        
    81.         status_t sendEvents(sensors_event_t const* buffer, size_t count,  
    82.                 sensors_event_t* scratch = NULL);  
    83.   
    84.         bool hasSensor(int32_t handle) const//检查handle是否在mSensorInfo中
        
    85.         bool hasAnySensor() const;   //检查mSensorInfo中是否有sensor
        
    86.         bool addSensor(int32_t handle); //把handle增加到mSensorInfo列表中
        
    87.         bool removeSensor(int32_t handle); //把handle从mSensorInfo中删除
        
    88.     };  
    89.     //============== SensorEventConnection  end ========================
        
    90.     //====================================================================
        
    91.   
    92.     class SensorRecord {  
    93.         SortedVector< wp<SensorEventConnection> > mConnections;  
    94.     public:  
    95.         SensorRecord(const sp<SensorEventConnection>& connection);  
    96.         bool addConnection(const sp<SensorEventConnection>& connection);  
    97.         bool removeConnection(const wp<SensorEventConnection>& connection);  
    98.         size_t getNumConnections() const { return mConnections.size(); }  
    99.     };  
    100.   
    101.     SortedVector< wp<SensorEventConnection> > getActiveConnections() const;  
    102.     DefaultKeyedVector<int, SensorInterface*> getActiveVirtualSensors() const;  
    103.   
    104.     String8 getSensorName(int handle) const;  
    105.     void recordLastValue(sensors_event_t const * buffer, size_t count);  
    106.     static void sortEventBuffer(sensors_event_t* buffer, size_t count);  
    107.     void registerSensor(SensorInterface* sensor);  
    108.     void registerVirtualSensor(SensorInterface* sensor);  
    109.   
    110.     // constants   
    111.     Vector<Sensor> mSensorList;  // Sensor列表
        
    112.     Vector<Sensor> mUserSensorList; //与mSensorList一样
        
    113.     DefaultKeyedVector<int, SensorInterface*> mSensorMap; //其成员为HardwareSensor
        
    114.     Vector<SensorInterface *> mVirtualSensorList; //其成员为HardwareSensor
        
    115.     status_t mInitCheck;  
    116.   
    117.     // protected by mLock 
        
    118.     mutable Mutex mLock;  
    119.     DefaultKeyedVector<int, SensorRecord*> mActiveSensors; //成员为SensorRecord
        
    120.     DefaultKeyedVector<int, SensorInterface*> mActiveVirtualSensors; //成员为HardwareSensor
        
    121.     SortedVector< wp<SensorEventConnection> > mActiveConnections;  
    122.   
    123.     // The size of this vector is constant, only the items are mutable
        
    124.     KeyedVector<int32_t, sensors_event_t> mLastEventSeen;  
    125.   
    126. public:  
    127.     static char const* getServiceName() { return "sensorservice"; }  
    128.   
    129.     void cleanupConnection(SensorEventConnection* connection);  
    130.   
    131.     /* 
    132.       1) 调用HardwareSensor::activate,即SensorDevice::activate 
    133.       2) 然后创建SensorRecord并增加到列表mActiveSensors 
    134.       3) 把此HardwareSensor增加到连接的mSensorInfo 
    135.       4) 把此连接增加到mActiveConnections中 
    136.     */  
    137.     status_t enable(const sp<SensorEventConnection>& connection, int handle);  
    138.   
    139.     /* 
    140.        1) 把此sensor从连接的mSensorInfo中删除 
    141.        2) 把此连接从mActiveConnections中删除 
    142.        3) 调用HardwareSensor::activate,即SensorDevice::activate 
    143.     */  
    144.     status_t disable(const sp<SensorEventConnection>& connection, int handle);  
    145.     /* 
    146.        1)调用HardwareSensor::setDelay,即SensorDevice::setDelay 
    147.      */  
    148.     status_t setEventRate(const sp<SensorEventConnection>& connection, int handle, nsecs_t ns);  
    149. }  


    2.5 SensorDevice.cpp

          SensorDevice封装了对SensorHAL层代码的调用,主要包含以下功能:
             1) 获取sensor列表(getSensorList)
             2) 获取sensor事件(poll)
             3) Enable或Disable sensor (activate)
             4) 设置delay时间

     

    1. class SensorDevice : public Singleton<SensorDevice> {  
    2.   
    3.     friend class Singleton<SensorDevice>;  
    4.   
    5.     struct sensors_poll_device_t* mSensorDevice; // sensor设备
        
    6.   
    7.     struct sensors_module_t* mSensorModule;  
    8.   
    9.     mutable Mutex mLock; // protect mActivationCount[].rates
        
    10.     // fixed-size array after construction
        
    11.     struct Info {  
    12.         Info() : delay(0) { }  
    13.         KeyedVector<void*, nsecs_t> rates;  
    14.         nsecs_t delay;  
    15.         status_t setDelayForIdent(void* ident, int64_t ns);  
    16.         nsecs_t selectDelay();  
    17.     };  
    18.     DefaultKeyedVector<int, Info> mActivationCount;  
    19.   
    20.     /* 
    21.       1) 调用hw_get_module(SENSORS_HARDWARE_MODULE_ID,..)获取sensors_module_t, 
    22.              并保存在mSensorModule中 
    23.       2) 调用mSensorModule->common->methods->open,以返回sensors_poll_device_t, 
    24.              并保存在mSensorDevice中 
    25.       3) 调用mSensorModule->get_sensors_list所有可访问的sensor_t 
    26.       4) 调用mSensorDevice->activate激活所有的sensor 
    27.     */  
    28.     SensorDevice();  
    29. public:  
    30.     // 调用mSensorModule->get_sensors_list实现
        
    31.     ssize_t getSensorList(sensor_t const** list);  
    32.   
    33.     status_t initCheck() const;  
    34.   
    35.     // 调用mSensorDevice->poll实现
        
    36.     ssize_t poll(sensors_event_t* buffer, size_t count);  
    37.   
    38.     // 调用mSensorDevice->activate实现 
        
    39.     status_t activate(void* ident, int handle, int enabled);  
    40.       
    41.     // 调用mSensorDevice->setDelay实现
        
    42.     status_t setDelay(void* ident, int handle, int64_t ns);  
    43.     void dump(String8& result, char* buffer, size_t SIZE);  
    44. };  

    2.6 Sensor HAL

    定义:/hardware/libhardware/include/hardware/sensors.h

    实现:/hardware/mychip/sensor/st/sensors.c

    2.6.1 struct sensors_poll_device_t 定义     

    1. struct sensors_poll_device_t {  
    2.     struct hw_device_t common;  
    3.   
    4.     // Activate/deactivate one sensor. 
        
    5.     int (*activate)(struct sensors_poll_device_t *dev,  
    6.             int handle, int enabled);  
    7.   
    8.     // Set the delay between sensor events in nanoseconds for a given sensor.
        
    9.     int (*setDelay)(struct sensors_poll_device_t *dev,  
    10.             int handle, int64_t ns);  
    11.   
    12.     // Returns an array of sensor data. 
        
    13.     int (*poll)(struct sensors_poll_device_t *dev,  
    14.             sensors_event_t* data, int count);  
    15. };  

    2.6.2 struct sensors_module_t  定义

    1. struct sensors_module_t {  
    2.     struct hw_module_t common;  
    3.   
    4.     /** 
    5.      * Enumerate all available sensors. The list is returned in "list". 
    6.      * @return number of sensors in the list 
    7.      */  
    8.     int (*get_sensors_list)(struct sensors_module_t* module,  
    9.             struct sensor_t const** list);  
    10. };  

    2.6.3  struct sensor_t 定义

    1. struct sensor_t {  
    2.     /* name of this sensors */  
    3.     const char*     name;  
    4.     /* vendor of the hardware part */  
    5.     const char*     vendor;  
    6.     /* version of the hardware part + driver. The value of this field 
    7.      * must increase when the driver is updated in a way that changes the 
    8.      * output of this sensor. This is important for fused sensors when the 
    9.      * fusion algorithm is updated. 
    10.      */      
    11.     int             version;  
    12.     /* handle that identifies this sensors. This handle is used to activate 
    13.      * and deactivate this sensor. The value of the handle must be 8 bits 
    14.      * in this version of the API.  
    15.      */  
    16.     int             handle;  
    17.     /* this sensor's type. */  
    18.     int             type;  
    19.     /* maximaum range of this sensor's value in SI units */  
    20.     float           maxRange;  
    21.     /* smallest difference between two values reported by this sensor */  
    22.     float           resolution;  
    23.     /* rough estimate of this sensor's power consumption in mA */  
    24.     float           power;  
    25.     /* minimum delay allowed between events in microseconds. A value of zero 
    26.      * means that this sensor doesn't report events at a constant rate, but 
    27.      * rather only when a new data is available */  
    28.     int32_t         minDelay;  
    29.     /* reserved fields, must be zero */  
    30.     void*           reserved[8];  
    31. };  

    2.6.4 struct sensors_event_t 定义

    1. typedef struct {  
    2.     union {  
    3.         float v[3];  
    4.         struct {  
    5.             float x;  
    6.             float y;  
    7.             float z;  
    8.         };  
    9.         struct {  
    10.             float azimuth;  
    11.             float pitch;  
    12.             float roll;  
    13.         };  
    14.     };  
    15.     int8_t status;  
    16.     uint8_t reserved[3];  
    17. } sensors_vec_t;  
    18.   
    19. /** 
    20.  * Union of the various types of sensor data 
    21.  * that can be returned. 
    22.  */  
    23. typedef struct sensors_event_t {  
    24.     /* must be sizeof(struct sensors_event_t) */  
    25.     int32_t version;  
    26.   
    27.     /* sensor identifier */  
    28.     int32_t sensor;  
    29.   
    30.     /* sensor type */  
    31.     int32_t type;  
    32.   
    33.     /* reserved */  
    34.     int32_t reserved0;  
    35.   
    36.     /* time is in nanosecond */  
    37.     int64_t timestamp;  
    38.   
    39.     union {  
    40.         float           data[16];  
    41.   
    42.         /* acceleration values are in meter per second per second (m/s^2) */  
    43.         sensors_vec_t   acceleration;  
    44.   
    45.         /* magnetic vector values are in micro-Tesla (uT) */  
    46.         sensors_vec_t   magnetic;  
    47.   
    48.         /* orientation values are in degrees */  
    49.         sensors_vec_t   orientation;  
    50.   
    51.         /* gyroscope values are in rad/s */  
    52.         sensors_vec_t   gyro;  
    53.   
    54.         /* temperature is in degrees centigrade (Celsius) */  
    55.         float           temperature;  
    56.   
    57.         /* distance in centimeters */  
    58.         float           distance;  
    59.   
    60.         /* light in SI lux units */  
    61.         float           light;  
    62.   
    63.         /* pressure in hectopascal (hPa) */  
    64.         float           pressure;  
    65.   
    66.         /* relative humidity in percent */  
    67.         float           relative_humidity;  
    68.     };  
    69.     uint32_t        reserved1[4];  
    70. } sensors_event_t;  

    2.6.5 struct sensors_module_t 实现

    1. #include <hardware/sensors.h> 
        
    2. #include "nusensors.h"   
    3.   
    4. /* 
    5.  * the AK8973 has a 8-bit ADC but the firmware seems to average 16 samples, 
    6.  * or at least makes its calibration on 12-bits values. This increases the 
    7.  * resolution by 4 bits. 
    8.  */  
    9. static const struct sensor_t sSensorList[] = {  
    10.         { "MMA8452Q 3-axis Accelerometer",      
    11.                 "Freescale Semiconductor",  
    12.                 1, SENSORS_HANDLE_BASE+ID_A,  
    13.                 SENSOR_TYPE_ACCELEROMETER, 4.0f*9.81f, (4.0f*9.81f)/256.0f, 0.2f, 0, { } },  
    14.         { "AK8975 3-axis Magnetic field sensor",  
    15.                 "Asahi Kasei",  
    16.                 1, SENSORS_HANDLE_BASE+ID_M,  
    17.                 SENSOR_TYPE_MAGNETIC_FIELD, 2000.0f, 1.0f/16.0f, 6.8f, 0, { } },  
    18.         { "AK8975 Orientation sensor",  
    19.                 "Asahi Kasei",  
    20.                 1, SENSORS_HANDLE_BASE+ID_O,  
    21.                 SENSOR_TYPE_ORIENTATION, 360.0f, 1.0f, 7.0f, 0, { } },   
    22.   
    23.     { "ST 3-axis Gyroscope sensor",  
    24.           "STMicroelectronics",  
    25.           1, SENSORS_HANDLE_BASE+ID_GY,  
    26.           SENSOR_TYPE_GYROSCOPE, RANGE_GYRO, CONVERT_GYRO, 6.1f, 1190, { } },  
    27.               
    28.     { "AL3006Proximity sensor",  
    29.         "Dyna Image Corporation",  
    30.         1, SENSORS_HANDLE_BASE+ID_P,  
    31.         SENSOR_TYPE_PROXIMITY,  
    32.         PROXIMITY_THRESHOLD_CM, PROXIMITY_THRESHOLD_CM,  
    33.         0.5f, 0, { } },  
    34.           
    35.         { "AL3006 light sensor",  
    36.                 "Dyna Image Corporation",  
    37.                 1, SENSORS_HANDLE_BASE+ID_L,  
    38.                 SENSOR_TYPE_LIGHT, 10240.0f, 1.0f, 0.5f, 0, { } },  
    39.   
    40. };  
    41.   
    42. static int open_sensors(const struct hw_module_t* module, const char* name,  
    43.         struct hw_device_t** device);  
    44.   
    45. static int sensors__get_sensors_list(struct sensors_module_t* module,  
    46.         struct sensor_t const** list)  
    47. {  
    48.     *list = sSensorList;  
    49.     return ARRAY_SIZE(sSensorList);  
    50. }  
    51.   
    52. static struct hw_module_methods_t sensors_module_methods = {  
    53.     .open = open_sensors  
    54. };  
    55.   
    56. const struct sensors_module_t HAL_MODULE_INFO_SYM = {  
    57.     .common = {  
    58.         .tag = HARDWARE_MODULE_TAG,  
    59.         .version_major = 1,  
    60.         .version_minor = 0,  
    61.         .id = SENSORS_HARDWARE_MODULE_ID,  
    62.         .name = "MMA8451Q & AK8973A & gyro Sensors Module",  
    63.         .author = "The Android Project",  
    64.         .methods = &sensors_module_methods,  
    65.     },  
    66.     .get_sensors_list = sensors__get_sensors_list  
    67. };  
    68.   
    69. static int open_sensors(const struct hw_module_t* module, const char* name,  
    70.         struct hw_device_t** device)  
    71. {  
    72.     return init_nusensors(module, device); //待后面讲解
        
    73. }  

    2.6.6 struct sensors_poll_device_t 实现

        实现代码位于:/hardware/mychip/sensor/st/nusensors.cpp

        从上面的代码中可以看出,当调用init_nusensors时,它将返回sensors_poll_device_t,然后就可以调用sensors_poll_device_t 的以下方法进行相关操作:

          1) activate  
          2) setDelay
          3) poll

    6.1) struct sensors_poll_context_t 定义 

    1. struct sensors_poll_context_t {  
    2.     struct sensors_poll_device_t device; // must be first
        
    3.   
    4.         sensors_poll_context_t();  
    5.         ~sensors_poll_context_t();  
    6.     int activate(int handle, int enabled);  
    7.     int setDelay(int handle, int64_t ns);  
    8.     int pollEvents(sensors_event_t* data, int count);  
    9.   
    10. private:  
    11.     enum {        
    12.         light           = 0,  
    13.         proximity       = 1,  
    14.         mma             = 2,  
    15.         akm             = 3,  
    16.         gyro            = 4,  
    17.         numSensorDrivers,  
    18.         numFds,  
    19.     };  
    20.   
    21.     static const size_t wake = numFds - 1;  
    22.     static const char WAKE_MESSAGE = 'W';  
    23.     struct pollfd mPollFds[numFds];  
    24.     int mWritePipeFd;  
    25.     SensorBase* mSensors[numSensorDrivers];  
    26.   
    27.     int handleToDriver(int handle) const {  
    28.         switch (handle) {  
    29.             case ID_A:  
    30.                 return mma;  
    31.             case ID_M:  
    32.             case ID_O:  
    33.                 return akm;   
    34.             case ID_P:  
    35.                 return proximity;  
    36.             case ID_L:  
    37.                 return light;     
    38.             case ID_GY:  
    39.                 return gyro;  
    40.         }  
    41.         return -EINVAL;  
    42.     }  
    43. }  

    6.2) init_nusensors 实现

    1. int init_nusensors(hw_module_t const* module, hw_device_t** device)  
    2. {  
    3.     int status = -EINVAL;  
    4.   
    5.     sensors_poll_context_t *dev = new sensors_poll_context_t();  
    6.     memset(&dev->device, 0, sizeof(sensors_poll_device_t));  
    7.   
    8.     dev->device.common.tag = HARDWARE_DEVICE_TAG;  
    9.     dev->device.common.version  = 0;  
    10.     dev->device.common.module   = const_cast<hw_module_t*>(module);  
    11.     dev->device.common.close    = poll__close;  
    12.     dev->device.activate        = poll__activate;  
    13.     dev->device.setDelay        = poll__setDelay;  
    14.     dev->device.poll            = poll__poll;  
    15.   
    16.     *device = &dev->device.common;  
    17.     status = 0;  
    18.     return status;  
    19. }  

         由以上代码可见,sensors_poll_device_t的activate、setDelay和poll的实现函数分别为:

            (1)  poll__activate

            (2)   poll__setDelay

            (3)   poll__poll

         下面讲解以上三个关键函数的实现

    6.3) struct sensors_poll_context_t 的实现

    1. sensors_poll_context_t::sensors_poll_context_t()  
    2. {     
    3.     mSensors[light] = new LightSensor();  
    4.     mPollFds[light].fd = mSensors[light]->getFd();  
    5.     mPollFds[light].events = POLLIN;  
    6.     mPollFds[light].revents = 0;  
    7.   
    8.     mSensors[proximity] = new ProximitySensor();  
    9.     mPollFds[proximity].fd = mSensors[proximity]->getFd();  
    10.     mPollFds[proximity].events = POLLIN;  
    11.     mPollFds[proximity].revents = 0;  
    12.       
    13.   
    14.     mSensors[mma] = new MmaSensor();  //下面MmmaSensor为例进行分析
        
    15.     mPollFds[mma].fd = mSensors[mma]->getFd();  
    16.     mPollFds[mma].events = POLLIN;  
    17.     mPollFds[mma].revents = 0;  
    18.   
    19.     mSensors[akm] = new AkmSensor();  
    20.     mPollFds[akm].fd = mSensors[akm]->getFd();  
    21.     mPollFds[akm].events = POLLIN;  
    22.     mPollFds[akm].revents = 0;  
    23.   
    24.     mSensors[gyro] = new GyroSensor();  
    25.     mPollFds[gyro].fd = mSensors[gyro]->getFd();  
    26.     mPollFds[gyro].events = POLLIN;  
    27.     mPollFds[gyro].revents = 0;  
    28.   
    29.     int wakeFds[2];  
    30.     int result = pipe(wakeFds);  
    31.     LOGE_IF(result<0, "error creating wake pipe (%s)", strerror(errno));  
    32.     fcntl(wakeFds[0], F_SETFL, O_NONBLOCK);  
    33.     fcntl(wakeFds[1], F_SETFL, O_NONBLOCK);  
    34.     mWritePipeFd = wakeFds[1];  
    35.   
    36.     mPollFds[wake].fd = wakeFds[0];  
    37.     mPollFds[wake].events = POLLIN;  
    38.     mPollFds[wake].revents = 0;  
    39. }  
    40.   
    41. sensors_poll_context_t::~sensors_poll_context_t() {  
    42.     for (int i=0 ; i<numSensorDrivers ; i++) {  
    43.         delete mSensors[i];  
    44.     }  
    45.     close(mPollFds[wake].fd);  
    46.     close(mWritePipeFd);  
    47. }  
    48.   
    49. int sensors_poll_context_t::activate(int handle, int enabled) {  
    50.     int index = handleToDriver(handle);  
    51.     if (index < 0) return index;  
    52.     int err =  mSensors[index]->enable(handle, enabled);  
    53.     if (enabled && !err) {  
    54.         const char wakeMessage(WAKE_MESSAGE);  
    55.         int result = write(mWritePipeFd, &wakeMessage, 1);  
    56.         LOGE_IF(result<0, "error sending wake message (%s)", strerror(errno));  
    57.     }  
    58.     return err;  
    59. }  
    60.   
    61. int sensors_poll_context_t::setDelay(int handle, int64_t ns) {  
    62.   
    63.     int index = handleToDriver(handle);  
    64.     if (index < 0) return index;  
    65.     return mSensors[index]->setDelay(handle, ns);  
    66. }  
    67.   
    68. int sensors_poll_context_t::pollEvents(sensors_event_t* data, int count)  
    69. {  
    70.     int nbEvents = 0;  
    71.     int n = 0;  
    72.   
    73.     do {  
    74.         // see if we have some leftover from the last poll()
        
    75.         for (int i=0 ; count && i<numSensorDrivers ; i++) {  
    76.             SensorBase* const sensor(mSensors[i]);  
    77.             if ((mPollFds[i].revents & POLLIN) || (sensor->hasPendingEvents())) {  
    78.                 int nb = sensor->readEvents(data, count);    // num of evens received.
        
    79.                 D("nb = %d.", nb);  
    80.                 if (nb < count) {  
    81.                     // no more data for this sensor
        
    82.                     mPollFds[i].revents = 0;  
    83.                 }  
    84.                 count -= nb;  
    85.                 nbEvents += nb;  
    86.                 data += nb;  
    87.             }  
    88.         }  
    89.   
    90.         if (count) {  
    91.             // we still have some room, so try to see if we can get
        
    92.             // some events immediately or just wait if we don't have
        
    93.             // anything to return
        
    94.             n = poll(mPollFds, numFds, nbEvents ? 0 : -1);  
    95.             if (n<0) {  
    96.                 LOGE("poll() failed (%s)", strerror(errno));  
    97.                 return -errno;  
    98.             }  
    99.             if (mPollFds[wake].revents & POLLIN) {  
    100.                 char msg;  
    101.                 int result = read(mPollFds[wake].fd, &msg, 1);  
    102.                 LOGE_IF(result<0, "error reading from wake pipe (%s)", strerror(errno));  
    103.                 LOGE_IF(msg != WAKE_MESSAGE, "unknown message on wake queue (0x%02x)"int(msg));  
    104.                 mPollFds[wake].revents = 0;  
    105.             }  
    106.         }  
    107.         // if we have events and space, go read them
        
    108.     } while (n && count);  
    109.   
    110.     return nbEvents;  
    111. }  
    112.   
    113. /*****************************************************************************/  
    114.   
    115. static int poll__close(struct hw_device_t *dev)  
    116. {  
    117.     sensors_poll_context_t *ctx = (sensors_poll_context_t *)dev;  
    118.     if (ctx) {  
    119.         delete ctx;  
    120.     }  
    121.     return 0;  
    122. }  
    123.   
    124. static int poll__activate(struct sensors_poll_device_t *dev,  
    125.         int handle, int enabled) {  
    126.     sensors_poll_context_t *ctx = (sensors_poll_context_t *)dev;  
    127.     return ctx->activate(handle, enabled);  
    128. }  
    129.   
    130. static int poll__setDelay(struct sensors_poll_device_t *dev,  
    131.         int handle, int64_t ns) {  
    132.     sensors_poll_context_t *ctx = (sensors_poll_context_t *)dev;  
    133.     return ctx->setDelay(handle, ns);  
    134. }  
    135.   
    136. static int poll__poll(struct sensors_poll_device_t *dev,  
    137.         sensors_event_t* data, int count) {  
    138.     sensors_poll_context_t *ctx = (sensors_poll_context_t *)dev;  
    139.     return ctx->pollEvents(data, count);  
    140. }  

    下面MmaSensor为例进行分析。

    2.7 MmaSensor.cpp

    1)  SensorBase的实现(SensorBase.cpp)

    1. class SensorBase {  
    2. protected:  
    3.     const char* dev_name; // "/dev/mma8452_daemon"
        
    4.     const char* data_name; // "gsensor"
        
    5.     int         dev_fd; // 打开设备"/dev/mma8452_daemon"的fd
        
    6.       
    7.     // 打开事件"/dev/input/eventx"的fd,其驱动的名字为"gsensor"
        
    8.     int         data_fd;   
    9.       
    10.     // 打开与"gsensor"对应的事件"/dev/input/eventx"
        
    11.     static int openInput(const char* inputName);   
    12.   
    13.     //通过clock_gettime获取当前时间 
        
    14.     static int64_t getTimestamp();   
    15.   
    16.   
    17.     static int64_t timevalToNano(timeval const& t) {  
    18.         return t.tv_sec*1000000000LL + t.tv_usec*1000;  
    19.     }  
    20.   
    21.     int open_device(); //打开设备"dev/mma8452_daemon"
        
    22.     int close_device(); //关闭设备"dev/mma8452_daemon"
        
    23.   
    24. public:  
    25.     // 调用openInput   
    26.             SensorBase(  
    27.                     const char* dev_name,  
    28.                     const char* data_name);  
    29.   
    30.     virtual ~SensorBase();  
    31.   
    32.     virtual int readEvents(sensors_event_t* data, int count) = 0;  
    33.     virtual bool hasPendingEvents() const;  
    34.     virtual int getFd() const;  //返回data_fd
        
    35.     virtual int setDelay(int32_t handle, int64_t ns);  
    36.     virtual int enable(int32_t handle, int enabled) = 0;  
    37. };  

    2) MmaSensor的实现

    1. class MmaSensor : public SensorBase {  
    2. public:  
    3.     /* 
    4.       1) 设置dev_name为 "/dev/mma8452_daemon" 
    5.       2) 设置data_name为 "gsensor" 
    6.       3) open设备 "/dev/mma8452_daemon" 
    7.     */  
    8.             MmaSensor();  
    9.     virtual ~MmaSensor();  
    10.   
    11.     enum {  
    12.         Accelerometer   = 0,  
    13.         numSensors  
    14.     };  
    15.   
    16.     // 调用ioctl(MMA_IOCTL_APP_SET_RATE) 
        
    17.     virtual int setDelay(int32_t handle, int64_t ns);  
    18.   
    19.     /* 
    20.       1) Activate: ioctl(MMA_IOCTL_START) 
    21.       2) Deactivate: ioctl(MMA_IOCTL_CLOSE) 
    22.     */  
    23.     virtual int enable(int32_t handle, int enabled);  
    24.       
    25.     /* 
    26.       1) 从data_fd read input_event 
    27.       2) 调用processEvent对事件进行处理 
    28.       3) 把事件通过data返回 
    29.     */  
    30.     virtual int readEvents(sensors_event_t* data, int count);  
    31.   
    32.     void processEvent(int code, int value);  
    33.   
    34. private:  
    35.     int update_delay();  
    36.     uint32_t mEnabled;  
    37.     uint32_t mPendingMask;  
    38.     InputEventCircularReader mInputReader;  
    39.     sensors_event_t mPendingEvents[numSensors];  
    40.     uint64_t mDelays[numSensors];  
    41. };  

    3. 加载HAL

    HAL 为一个.so库,其加载过程相关代码如下:

    1. #define HAL_LIBRARY_PATH1 "/system/lib/hw"
        
    2. #define HAL_LIBRARY_PATH2 "/vendor/lib/hw"
        
    3. #define SENSORS_HARDWARE_MODULE_ID "sensors"
        
    4.   
    5. SensorDevice::SensorDevice()  
    6.     :  mSensorDevice(0),  
    7.        mSensorModule(0)  
    8. {  
    9.     status_t err = hw_get_module(SENSORS_HARDWARE_MODULE_ID,  
    10.             (hw_module_t const**)&mSensorModule);  
    11.   
    12.     ALOGE_IF(err, "couldn't load %s module (%s)",  
    13.             SENSORS_HARDWARE_MODULE_ID, strerror(-err));  
    14.   
    15.     if (mSensorModule) {  
    16.         err = sensors_open(&mSensorModule->common, &mSensorDevice);  
    17.   
    18.         ALOGE_IF(err, "couldn't open device for module %s (%s)",  
    19.                 SENSORS_HARDWARE_MODULE_ID, strerror(-err));  
    20.   
    21.         if (mSensorDevice) {  
    22.             sensor_t const* list;  
    23.             ssize_t count = mSensorModule->get_sensors_list(mSensorModule, &list);  
    24.             mActivationCount.setCapacity(count);  
    25.             Info model;  
    26.             for (size_t i=0 ; i<size_t(count) ; i++) {  
    27.                 mActivationCount.add(list[i].handle, model);  
    28.                 mSensorDevice->activate(mSensorDevice, list[i].handle, 0);  
    29.             }  
    30.         }  
    31.     }  
    32. }  
    33.   
    34. int hw_get_module(const char *id, const struct hw_module_t **module)  
    35. {  
    36.     return hw_get_module_by_class(id, NULL, module);  
    37. }  
    38.   
    39.   
    40. int hw_get_module_by_class(const char *class_id, const char *inst,  
    41.                            const struct hw_module_t **module)  
    42. {  
    43.     int status;  
    44.     int i;  
    45.     const struct hw_module_t *hmi = NULL;  
    46.     char prop[PATH_MAX];  
    47.     char path[PATH_MAX];  
    48.     char name[PATH_MAX];  
    49.   
    50.     if (inst)  
    51.         snprintf(name, PATH_MAX, "%s.%s", class_id, inst);  
    52.     else  
    53.         strlcpy(name, class_id, PATH_MAX);  
    54.   
    55.     /* 
    56.      * Here we rely on the fact that calling dlopen multiple times on 
    57.      * the same .so will simply increment a refcount (and not load 
    58.      * a new copy of the library). 
    59.      * We also assume that dlopen() is thread-safe. 
    60.      */  
    61.   
    62.     /* Loop through the configuration variants looking for a module */  
    63.     for (i=0 ; i<HAL_VARIANT_KEYS_COUNT+1 ; i++) {  
    64.         if (i < HAL_VARIANT_KEYS_COUNT) {  
    65.             if (property_get(variant_keys[i], prop, NULL) == 0) {  
    66.                 continue;  
    67.             }  
    68.             snprintf(path, sizeof(path), "%s/%s.%s.so",  
    69.                      HAL_LIBRARY_PATH2, name, prop);  
    70.             if (access(path, R_OK) == 0) break;  
    71.   
    72.             snprintf(path, sizeof(path), "%s/%s.%s.so",  
    73.                      HAL_LIBRARY_PATH1, name, prop);  
    74.             if (access(path, R_OK) == 0) break;  
    75.         } else {  
    76.             snprintf(path, sizeof(path), "%s/%s.default.so",  
    77.                      HAL_LIBRARY_PATH1, name);  
    78.             if (access(path, R_OK) == 0) break;  
    79.         }  
    80.     }  
    81.   
    82.     status = -ENOENT;  
    83.     if (i < HAL_VARIANT_KEYS_COUNT+1) {  
    84.         /* load the module, if this fails, we're doomed, and we should not try 
    85.          * to load a different variant. */  
    86.         status = load(class_id, path, module);  
    87.     }  
    88.   
    89.     return status;  
    90. }  

    4. 启动SensorService

        SensorService在SystemServer中启动(system_init.cpp),其相关代码如下:

    1. extern "C" status_t system_init()  
    2. {  
    3.     ....  
    4.     property_get("system_init.startsensorservice", propBuf, "1");  
    5.     if (strcmp(propBuf, "1") == 0) {  
    6.         // Start the sensor service 
        
    7.         SensorService::instantiate();  
    8.     }  
    9.     ...  
    10.     return NO_ERROR;  
    11. }  

    5. SensorManager注册Listener过程

    1. private SensorManager mSensorManager = (SensorManager) getSystemService(SENSOR_SERVICE);  
    2. registerListener(SensorManager.java)->  
    3.  registerListenerImpl (SystemSensorManager.java)->  
    4.   enableSensorLocked(SystemSensorManager.java)->  
    5.    sensors_enable_sensor(android_hardware_SensorManager.cpp)->  
    6.     SensorEventQueue::enableSensor(SensorEventQueue.cpp)->  
    7.      1>SensorService::SensorEventConnection::enableDisable(handle, true) (SensorService.cpp)->  
    8.          SensorService::enable(SensorService.cpp)->  
    9.            HardwareSensor::activate(SensorInterface.cpp)->  
    10.              SensorDevice::activate(SensorDevice.cpp)->  
    11.                sensors_poll_device_t::activate(HAL)  
    12.            
    13.      2>SensorService::SensorEventConnection::setEventRate(SensorService.cpp)->  
    14.        
  • 相关阅读:
    java基础之分辨final,static, abstract
    HTML DOM
    Zero Copy-转载201604
    Zero Copy
    java 虚拟机
    Spring Junit4
    【转】Java的序列化和反序列化总结
    【转】SQL Server 查询处理中的各个阶段(SQL执行顺序)
    【转】linux sar命令详解
    【转】linux top命令详解
  • 原文地址:https://www.cnblogs.com/liang123/p/6325224.html
Copyright © 2011-2022 走看看