Android Sensor 4 - Sensor Device

Sensor本地封装类SensorDevice

SensorDevice是在本地代码中SensorService对Sensor设备的抽象类型封装,它封装了传感器硬件的硬件操作,该类继承了Singleton类,通过getInstance方法获得单例模式设备操作对象:

@frameworks/base/services/sensorservice/SensorDevice.h

class SensorDevice : public Singleton<SensorDevice> {
    friend class Singleton<SensorDevice>;
    struct sensors_poll_device_t* mSensorDevice;
    struct sensors_module_t* mSensorModule;
    mutable Mutex mLock;     // protect mActivationCount[].rates
    // fixed-size array after construction
    struct Info {
        Info() : delay(0) { }
        KeyedVector<void*, nsecs_t> rates;
        nsecs_t delay;
     status_t setDelayForIdent(void* ident, int64_t ns);
        nsecs_t selectDelay();
    };
    DefaultKeyedVector<int, Info> mActivationCount;
   SensorDevice();
public:
    ssize_t getSensorList(sensor_t const** list);
    status_t initCheck() const;
    ssize_t poll(sensors_event_t* buffer, size_t count);
    status_t activate(void* ident, int handle, int enabled);
    status_t setDelay(void* ident, int handle, int64_t ns);
    void dump(String8& result, char* buffer, size_t SIZE);
};

通过SensorDevice类的定义可看到它包含的属性和方法:

属性:

mSensorDevice:Sensor设备HAL层操作接口封装结构

mSensorModule:Sensor设备HAL硬件模块封装结构

mActivationCount:保存激活Sensor设备向量表

方法:

SensorDevice:构造方法

getSensorList:获得Sensor设备列表方法

poll:Sensor设备多路监听方法

activate:设备激活方法

setDelay:设备Sensor设备延迟方法

由前面分析可知,SensorDevice是单例模型,其构造方法仅会调用一次:

@frameworks/base/services/sensorservice/SensorDevice.cpp

SensorDevice::SensorDevice()
    :  mSensorDevice(0), mSensorModule(0)
{
        // 终于看到hw_get_module了,幸福,高兴,开心,相见时难别亦难…
    status_t err = hw_get_module(SENSORS_HARDWARE_MODULE_ID,
            (hw_module_t const**)&mSensorModule);
    LOGE_IF(err, "couldn‘t load %s module (%s)",
            SENSORS_HARDWARE_MODULE_ID, strerror(-err));
    if (mSensorModule) {
            //打开module设备,返回module设备的操作接口,保存在mSensorDevice中
        err = sensors_open(&mSensorModule->common, &mSensorDevice);
        LOGE_IF(err, "couldn‘t open device for module %s (%s)",
                SENSORS_HARDWARE_MODULE_ID, strerror(-err));
        if (mSensorDevice) {
            sensor_t const* list;
              // 调用module设备的get_sensors_list接口
            ssize_t count = mSensorModule->get_sensors_list(mSensorModule, &list);
            mActivationCount.setCapacity(count);
            Info model;
            for (size_t i=0 ; i<size_t(count) ; i++) {
                mActivationCount.add(list[i].handle, model);
                mSensorDevice->activate(mSensorDevice, list[i].handle, 0);
            }
        }
    }
}

在SensorDevice构造方法里调用HAL架构的hw_get_module来获得Sensor设备模块,之后调用sensors_open这个工具函数,打开Sensor设备模块(调用其methods->open函数指针),返回Sensor设备的操作接口(这些接口在HAL层实现),保存在mSensorDevice中,调用Sensor模块的get_sensors_list方法获得传感器列表,然后依次激活这些设备并且添加到mActivationCount设备信息向量中。

Sensor HAL模块代码及打开模块工具函数sensors_open:

@hardware/libhardware/include/hardware/sensors.h

struct sensors_module_t {
    struct hw_module_t common;
    /**     * Enumerate all available sensors. The list is returned in "list".
     * @return number of sensors in the list
     */
    int (*get_sensors_list)(struct sensors_module_t* module,
            struct sensor_t const** list);
};
……
static inline int sensors_open(const struct hw_module_t* module,
        struct sensors_poll_device_t** device) {
    return module->methods->open(module,
            SENSORS_HARDWARE_POLL, (struct hw_device_t**)device);
}

SensorDevice其它几个方法比较简单:

ssize_t SensorDevice::getSensorList(sensor_t const** list) {
    if (!mSensorModule) return NO_INIT;
       // 直接调用模块的get_sensors_list方法获得Sensor列表
    ssize_t count = mSensorModule->get_sensors_list(mSensorModule, list);
    return count;
}

ssize_t SensorDevice::poll(sensors_event_t* buffer, size_t count) {
    if (!mSensorDevice) return NO_INIT;
    ssize_t c;
    do {
           // 调用Sensor设备的poll操作接口,该接口实现在HAL层
        c = mSensorDevice->poll(mSensorDevice, buffer, count);
    } while (c == -EINTR);
    return c;
}

status_t SensorDevice::activate(void* ident, int handle, int enabled)
{
    if (!mSensorDevice) return NO_INIT;
    status_t err(NO_ERROR);
    bool actuateHardware = false;

    Info& info( mActivationCount.editValueFor(handle) );

    LOGD_IF(DEBUG_CONNECTIONS,
            "SensorDevice::activate: ident=%p, handle=0x%08x, enabled=%d, count=%d",
            ident, handle, enabled, info.rates.size());

    if (enabled) {
        Mutex::Autolock _l(mLock);
        LOGD_IF(DEBUG_CONNECTIONS, "... index=%ld",
                info.rates.indexOfKey(ident));
           // 设置设备为默认延迟级别
        if (info.rates.indexOfKey(ident) < 0) {
            info.rates.add(ident, DEFAULT_EVENTS_PERIOD);
            if (info.rates.size() == 1) {
                actuateHardware = true;
            }
        } else {
            // sensor was already activated for this ident
        }
    } else {
        Mutex::Autolock _l(mLock);
        LOGD_IF(DEBUG_CONNECTIONS, "... index=%ld",
                info.rates.indexOfKey(ident));

        ssize_t idx = info.rates.removeItem(ident);
        if (idx >= 0) {
            if (info.rates.size() == 0) {
                actuateHardware = true;
            }
        } else {
            // sensor wasn‘t enabled for this ident
        }
    }

    if (actuateHardware) {
        LOGD_IF(DEBUG_CONNECTIONS, "\t>>> actuating h/w");
          // 调用Sensor设备activate操作接口,其实现在HAL层
        err = mSensorDevice->activate(mSensorDevice, handle, enabled);
        if (enabled) {
            LOGE_IF(err, "Error activating sensor %d (%s)", handle, strerror(-err));
            if (err == 0) {
                 // 在电池服务中使能Sensor电源
                BatteryService::getInstance().enableSensor(handle);
            }
        } else {
            if (err == 0) {
                 // 在电池服务中关闭Sensor电源
                BatteryService::getInstance().disableSensor(handle);
            }
        }
    }

    { // scope for the lock
        Mutex::Autolock _l(mLock);
        nsecs_t ns = info.selectDelay();
          // 设置延迟值
        mSensorDevice->setDelay(mSensorDevice, handle, ns);
    }

    return err;
}

由这几个SensorDevice的方法可知,其具体的实现全部由mSensorDevice 封装的设备操作接口函数实现,这些设备操作接口在HAL层实现,其实SensorDevice只是SensorService的设备操作对象,封装了设备的操作,而这些操作实际“干活的”的是HAL层代码。

一路分析过来,已经到了HAL层了,我们回顾下前面所学的东西。

让我们从Java应用层到框架层再到本地代码来总结下:

1. Android的应用程序调用getSystemService方法获得SensorManager对象,该方法实现在ContextImpl.java中,它是Activity的抽象父类Context的实现类。

2. 在应用程序(Activity)初始化时调用registerService创建并注册SensorManager

3. 创建SensorManager

4. 在SensorManager的构造方法中,调用了本地方法:nativeClassInit(),它用来初始化了Java对象Sensor在本地的引用,方便本地代码对Java对象操作。

5. 在SensorManager的构造方法中,调用sensors_module_init()来创建SensorManager本地对象。

8. 调用sensors_module_get_next_sensor()方法,通过nativeClassInit中初始化的Sensor引用填充Sensor设备列表,返回给Java框架层。

12. 将sensors_module_get_next_sensor()获得的设备列表保存在sFullSensorsList中。

13. 创建SensorThread线程准备监听Sensor硬件事件变化。

14. 应用程序通过getDefaultSensor来获得指定类型传感器的对象

16. 通过registerListener注册Sensor监听器。

Android Sensor 4 - Sensor Device

时间: 2024-08-13 04:33:42

Android Sensor 4 - Sensor Device的相关文章

深入理解Android之设备加密Device Encryption

深入理解Android之设备加密Device Encryption Android从4.4开始就支持一项功能,那就是对设备进行加密.加密自然是为了安全性考虑,由于/system目录是只读的,手机里那些存储设备分区中需要保护的就剩下/data/分区和sdcard了.显然,/data/和sdcard大量存储了用户数据(比如app运行时存储的数据),对他们进行加密非常非常有必要. Android 5.0发布后,为了Android设备在企业中的使用,设备加密这个功能默认就必须启用,但是加密这玩意还是对功

Android Studio关于USB device not found的解决办法

Android Studio关于USB device not found的解决办法 我们使用Android Studio进行Android开发时,当我们使用真机进行调试时,很可能会出现USB device not found的问题.网上提出了很多决解办法,很多都是错误的.现给出正确的解决方法: 1. If yon don't have Android SDK installed, please install it first. 2. Open Start menu. Select Androi

Android Studio关于USB device not found的解决的方法

Android Studio关于USB device not found的解决的方法 我们使用Android Studio进行Android开发时.当我们使用真机进行调试时.非常可能会出现USB device not found的问题.网上提出了非常多决解办法.非常多都是错误的.现给出正确的解决方法: 1. If yon don't have Android SDK installed, please install it first. 2. Open Start menu. Select An

android驱动程序之 - sensor

上图是android系统架构图,从中可以得知,sensor必贯穿架构的各个层次.按照架构层次,下面从五个方面来分析sensor架构: 1. sensor架构之App层: 2. sensor架构之Framework层: 3. sensor架构之Libraries层: 4. sensor架构之HAL层: 5. sensor架构之Driver. 1. sensor架构之App层 下面以g-sensor为例,写一个简单的apk,看一下sensor在App层到底是如何工作的,一般需要下面四个步骤来实现一个

Android中传感器Sensor的使用

Android中传感器Senso的使用 1.Sensor类型 Android中有多种传感器,目前Android SDK支持的传感器有:光线传感器,旋转向量传感器,压力传感器,陀螺仪传感器,加速度传感器,重力传感器,方向传感器,磁场传感器,近程传感器等.但并不是所有手机都具有全部传感器,一般高端手机具有大多数传感器,毕竟传感器都需要money的,价格自然不菲. 2.Sensor实际应用  那么在Android开发中,如何使用传感器,将传感器功能添加到Android应用中呢,例如微信的摇一摇,通过加

安卓系统广播暴露设备信息-Android System Broadcasts Expose Device Information

Android device details are being exposed to running applications via Wi-Fi broadcasts in the mobile operating system, Nightwatch Cybersecurity has discovered. The exposed information includes the WiFi network name, BSSID, local IP addresses, DNS serv

Android Sensor感应器介绍(三)获取用户移动方向,指南针原理

最新版的SDK加上了这么一句话“TYPE_ORIENTATION     This constant is deprecated. use SensorManager.getOrientation() instead. ”也就是说,这种方式已经被取消,要开发者使用SensorManager.getOrientation()来获取原来的数据. 实际上,android获取方向是通过磁场感应器和加速度感应器共同获得的,至于具体的算法SDK已经封装好了.也就是说现在获取用户方向有两种方式,一是官方推荐的

Android Orientation Sensor(方向传感器)详解与应用

一.前言 本篇blog是我的"Android进阶"的第一篇文章,从初学Android到现在断断续续也有4个多月时间了,也算是有了一些自己的心得体会,也能自己独立做一些东西了,这都要感谢我们公司的安卓开发璟博和无所不能的鸿洋给我的帮助和指点.本系列blog将记录我在开发中.学习中遇到的较为重点的.值得记录的知识点和技巧,简单的说就不再是基础教程了.由于项目中需要用到方向传感器,所以就借此机会来学一学Android的传感器部分的知识了,自然也就是本篇blog的内容了. 二.传感器基础 官方

关于android各种sensor的思考(Accelerometer,Magnetometer,Gy

关于android各种sensor的思考(Accelerometer,Magnetometer,Gyroscope) 芯片选型主要考虑方面 key-parameter:1)Power performance 功耗,不仅仅是芯片本身的功耗(这个一般很小),更大的功耗是这个driver和其daemon(algorithm library)的算法复杂度问题,越复杂,越需要大量的MIPS(兆指令每秒),cpu频率要求越高,cpu功耗越高.2)Physical size 芯片尺寸3)Accuracy准确度