深入浅出 - Android系统移植与平台开发- Sensor HAL框架分析之三

转自:http://blog.csdn.net/mr_raptor/article/details/8128912

让我们来看看SensorManager的代码

SensorManager框架层代码

@frameworks/base/core/java/android/hardware/SensorManager.java

[java] view plain copy print ?
  1. public SensorManager(Looper mainLooper) { 
  2.        mMainLooper = mainLooper;    // 上面说了,这是Activity的Looper 
  3.  
  4.        synchronized(sListeners) { 
  5.             if(!sSensorModuleInitialized) { 
  6.                 sSensorModuleInitialized = true
  7.                 nativeClassInit();        // 好像是调用本地方法初始化 
  8.                   sWindowManager = IWindowManager.Stub.asInterface( 
  9.                        ServiceManager.getService("window"));  // 获得Windows服务,不管它 
  10.                   if (sWindowManager != null) { 
  11.                    // if it's null we're running in the system process 
  12.                    // which won't get the rotated values 
  13.                    try
  14.                        sRotation = sWindowManager.watchRotation( 
  15.                                 newIRotationWatcher.Stub() { 
  16.                                     public voidonRotationChanged(int rotation) { 
  17.                                        SensorManager.this.onRotationChanged(rotation); 
  18.                                     } 
  19.                                 } 
  20.                         ); 
  21.                    } catch (RemoteException e) { 
  22.                    } 
  23.                 } 
  24.  
  25.                // initialize the sensor list 
  26.                sensors_module_init();         // 初始化sensor module 
  27.                final ArrayList<Sensor> fullList = sFullSensorsList;  // SensorManager维护的Sensor列表 
  28.                  int i = 0
  29.                do
  30.                    Sensor sensor = new Sensor(); // 创建sensor对象,这个是传递给App的哦 
  31.                    //调用module的方法,获得每一个sensor设备 
  32.                    i = sensors_module_get_next_sensor(sensor, i);  
  33.                 if (i>=0) { 
  34.                        //Log.d(TAG, "found sensor: " + sensor.getName() + 
  35.                        //        ", handle=" +sensor.getHandle()); 
  36.                        sensor.setLegacyType(getLegacySensorType(sensor.getType())); 
  37.                        fullList.add(sensor); // 添加到SM维护的Sensor列表(嘿嘿) 
  38.                        sHandleToSensor.append(sensor.getHandle(), sensor); 
  39.                    } 
  40.                 }while (i>0); 
  41.  
  42.                 sPool= new SensorEventPool( sFullSensorsList.size()*2 ); 
  43.                sSensorThread = new SensorThread(); // 哟,创建线程了好像 
  44.             } 
  45.         } 
  46.     } 

很明显nativeClassInit(),sensors_module_init(),sensors_module_get_next_sensor()都是本地实现的方法。

[java] view plain copy print ?
  1. private static native void nativeClassInit(); 
  2. private static native int sensors_module_init(); 
  3. private static native intsensors_module_get_next_sensor(Sensor sensor, int next); 

根据之前看代码的经验可知,很可能在frameworks/base/core/对应一个jni目录下的存在其对应的本地代码:

[java] view plain copy print ?
  1. frameworks/base/core/java/android/hardware/SensorManager.java 
  2. frameworks/base/core/jni/android_hardware_SensorManager.cpp 

果不其然,在jni存在其本地代码,让我们来看下nativeClassInit函数:

@frameworks/base/core/jni/android_hardware_SensorManager.cpp

[cpp] view plain copy print ?
  1. static void 
  2. nativeClassInit (JNIEnv *_env, jclass _this) 
  3.    jclasssensorClass = _env->FindClass("android/hardware/Sensor"); 
  4.    SensorOffsets& sensorOffsets = gSensorOffsets; 
  5.    sensorOffsets.name        =_env->GetFieldID(sensorClass, "mName",      "Ljava/lang/String;"); 
  6.    sensorOffsets.vendor      =_env->GetFieldID(sensorClass, "mVendor",    "Ljava/lang/String;"); 
  7.    sensorOffsets.version     =_env->GetFieldID(sensorClass, "mVersion",   "I"); 
  8.    sensorOffsets.handle      =_env->GetFieldID(sensorClass, "mHandle",    "I"); 
  9.    sensorOffsets.type        = _env->GetFieldID(sensorClass,"mType",      "I"); 
  10.    sensorOffsets.range       =_env->GetFieldID(sensorClass, "mMaxRange""F"); 
  11.    sensorOffsets.resolution  =_env->GetFieldID(sensorClass, "mResolution","F"); 
  12.    sensorOffsets.power       =_env->GetFieldID(sensorClass, "mPower",     "F"); 
  13.    sensorOffsets.minDelay    =_env->GetFieldID(sensorClass, "mMinDelay""I"); 

其代码比较简单,将Java框架层的Sensor类中的成员保存在本地代码中的gSensorOffsets 结构体中将来使用。

         sensors_module_init()本地方法的实现:

[cpp] view plain copy print ?
  1. static jint 
  2. sensors_module_ini(JNIEnv *env, jclass clazz) 
  3.    SensorManager::getInstance(); 
  4.     return 0; 

         在本地代码中调用了SensorManager的getInstance方法,这又是一个典型的单例模式获得类的对象,注意这儿的SensorManager是本地的类,而不是Java层的SensorManager类。

本地SensorManager的定义

@frameworks/base/include/gui/SensorManager.h

[cpp] view plain copy print ?
  1. class SensorManager : 
  2.     publicASensorManager, 
  3.     publicSingleton<SensorManager> 
  4. public
  5.    SensorManager(); 
  6.    ~SensorManager(); 
  7.  
  8.     ssize_tgetSensorList(Sensor const* const** list) const
  9.  
  10.     Sensor const*getDefaultSensor(int type); 
  11.    sp<SensorEventQueue> createEventQueue(); 
  12. private
  13.     //DeathRecipient interface 
  14.     voidsensorManagerDied(); 
  15.     status_tassertStateLocked() const
  16. private
  17.     mutable MutexmLock; 
  18.     mutablesp<ISensorServer> mSensorServer; 
  19.     mutableSensor const** mSensorList; 
  20.     mutableVector<Sensor> mSensors; 
  21.     mutablesp<IBinder::DeathRecipient> mDeathObserver; 
  22. }; 

注意SensorManager又继承了ASensorManager和泛型类Singleton<SensorManager>,而SensorManager类定义里没有getInstance所以其定义肯定是在ASensorManager或Singleton中。

@frameworks/base/include/utils/Singleton.h

[cpp] view plain copy print ?
  1. template <typename TYPE> 
  2. class ANDROID_API Singleton 
  3. public
  4.  
  5.     staticTYPE& getInstance() { 
  6.        Mutex::Autolock _l(sLock); 
  7.         TYPE*instance = sInstance; 
  8.         if(instance == 0) { 
  9.            instance = new TYPE(); 
  10.            sInstance = instance; 
  11.         } 
  12.  
  13.         return*instance; 
  14.     } 
  15.  
  16.     static boolhasInstance() { 
  17.        Mutex::Autolock _l(sLock); 
  18.         returnsInstance != 0; 
  19.     } 
  20.  
  21. protected
  22.     ~Singleton(){ }; 
  23.     Singleton() {}; 
  24.  
  25. private
  26.    Singleton(const Singleton&); 
  27.    Singleton& operator = (const Singleton&); 
  28.     static MutexsLock; 
  29.     static TYPE*sInstance; 
  30. }; 
  31. //--------------------------------------------------------------------------- 
  32. }; // namespace android 

第一次调用getInstance方法时,创建泛型对象即:SensorManager,随后再调用该方法时返回第一次创建的泛型对象。

1)    本地SensorManager的创建

本地SensorManager是一个单例模式,其构造方法相对比较简单,它的主要工作交给了assertStateLocked方法:

@frameworks/base/libs/gui/SensorManager.cpp

[cpp] view plain copy print ?
  1. SensorManager::SensorManager()       
  2.     :mSensorList(0) 
  3.     // okay we'renot locked here, but it's not needed during construction 
  4.    assertStateLocked(); 
  5.  
  6. status_t SensorManager::assertStateLocked() const
  7.     if(mSensorServer == NULL) { 
  8.         // try for one second 
  9.         constString16 name("sensorservice"); 
  10.         for (inti=0 ; i<4 ; i++) { 
  11.             status_t err = getService(name,&mSensorServer); 
  12.             if(err == NAME_NOT_FOUND) { 
  13.                usleep(250000); 
  14.                continue
  15.             } 
  16.  
  17.             if(err != NO_ERROR) { 
  18.                return err; 
  19.             } 
  20.             break
  21.         } 
  22.  
  23.         classDeathObserver : public IBinder::DeathRecipient { 
  24.            SensorManager& mSensorManger; 
  25.            virtual void binderDied(const wp<IBinder>& who) { 
  26.                LOGW("sensorservice died [%p]", who.unsafe_get()); 
  27.                mSensorManger.sensorManagerDied(); 
  28.             } 
  29.         public
  30.            DeathObserver(SensorManager& mgr) : mSensorManger(mgr) { } 
  31.         }; 
  32.  
  33.        mDeathObserver = new DeathObserver(*const_cast<SensorManager*>(this)); 
  34.         mSensorServer->asBinder()->linkToDeath(mDeathObserver); 
  35.  
  36.         mSensors= mSensorServer->getSensorList(); 
  37.        size_tcount = mSensors.size(); 
  38.        mSensorList = (Sensor const**)malloc(count * sizeof(Sensor*)); 
  39.         for(size_t i=0 ; i<count ; i++) { 
  40.            mSensorList[i] = mSensors.array() + i; 
  41.         } 
  42.     } 
  43.  
  44.     returnNO_ERROR; 

在assertStateLocked方法里,先通过getService获得SensorService对象,然后注册了对SensorService的死亡监听器,SensorManager与SensorService不求同年同月同日,只求同年同月同日死。拜完了兄弟之后,调用getSensorList得到所有传感器的对象,存放到mSensorList中,保存在本地空间里。

2)    本地SensorManager中列表的获取

在上面函数调用中首先调用getService来获得SensorService服务,然后执行mSensorServer->getSensorList来获得服务提供的传感器列表:

[cpp] view plain copy print ?
  1. Vector<Sensor> SensorService::getSensorList() 
  2.     return mUserSensorList; 

大家要注意啊,上面的getSensorList函数只是返回了mUserSensorList,而这个变量是在什么时候初始化的呢?

根据2.1节可知,SensorService在本地被初始化时,构造函数里并没有对mUserSensorList进行初始化,而SensorService里有一个onFirstRef方法,这个方法当SensorService第一次被强引用时被自动调用。那SensorService第一次被强引用是在什么时候呢?

在SensorManager::assertStateLocked方法里调用getService获得SensorService保存到mSensorServer成员变量中。

mSensorServer的定义在frameworks/base/include/gui/SensorManager.h中:

[cpp] view plain copy print ?
  1. class SensorManager : 
  2.     public ASensorManager, 
  3.     public Singleton<SensorManager> 
  4. mutable sp<ISensorServer>mSensorServer; 
  5. mutable Sensorconst** mSensorList; 
  6. mutable Vector<Sensor> mSensors; 
  7. }; 

可以看出mSensroServer为强引用类型。所以在创建本地中的SensorManager类对象时,自动强引用SensorService,自动调用onFirstRef方法:

@frameworks/base/services/sensorservice/SensorService.cpp的onFirstRef简化方法如下:

[cpp] view plain copy print ?
  1. void SensorService::onFirstRef() 
  2. {    
  3.    LOGD("nuSensorService starting..."); 
  4.    SensorDevice& dev(SensorDevice::getInstance());                //创建SensorDevice对象dev 
  5.      
  6.  
  7.     if(dev.initCheck() == NO_ERROR) { 
  8.         sensor_tconst* list; 
  9.         ssize_tcount = dev.getSensorList(&list);                          //获得传感器设备列表 
  10.         if (count> 0) { 
  11.             …  
  12.             for(ssize_t i=0 ; i<count ; i++) { 
  13.                 registerSensor( new HardwareSensor(list[i]) );  // 注册在本地获得的传感器 
  14.                            … 
  15.                       } 
  16.             constSensorFusion& fusion(SensorFusion::getInstance()); 
  17.                       
  18.             if(hasGyro) {            // 如果有陀螺仪设备,则先注册和陀螺仪有关的虚拟传感器设备 
  19.                 registerVirtualSensor( newRotationVectorSensor() );     // 虚拟旋转传感器 
  20.                registerVirtualSensor( new GravitySensor(list, count) ); // 虚拟重力传感器 
  21.                registerVirtualSensor( new LinearAccelerationSensor(list, count) ); // 虚拟加速器 
  22.  
  23.                 // these are optional 
  24.                registerVirtualSensor( new OrientationSensor() ); // 虚拟方向传感器 
  25.                registerVirtualSensor( new CorrectedGyroSensor(list, count) );        // 真正陀螺仪 
  26.  
  27.                // virtual debugging sensors... 
  28.                 char value[PROPERTY_VALUE_MAX]; 
  29.                property_get("debug.sensors", value, "0"); 
  30.                if (atoi(value)) { 
  31.                    registerVirtualSensor( new GyroDriftSensor() );      // 虚拟陀螺测漂传感器 
  32.                 } 
  33.             } 
  34.                      
  35.             // build the sensor list returned tousers 
  36.             mUserSensorList = mSensorList; 
  37.             if(hasGyro && 
  38.                    (virtualSensorsNeeds & (1<<SENSOR_TYPE_ROTATION_VECTOR))) { 
  39.                // if we have the fancy sensor fusion, and it's not provided by the 
  40.                // HAL, use our own (fused) orientation sensor by removing the 
  41.                // HAL supplied one form the user list. 
  42.                if (orientationIndex >= 0) { 
  43.                    mUserSensorList.removeItemsAt(orientationIndex); 
  44.                 } 
  45.             } 
  46.  
  47.             run("SensorService",PRIORITY_URGENT_DISPLAY); 
  48.            mInitCheck = NO_ERROR; 
  49.         } 
  50.     } 

上面代码首先通过SensorDevice::getInstance()创建对象dev,调用dev.getSensorList(&list)获得传感器列表,将取出的sensor_t类型list传感器列表,塑造了HardwareSensor对象,传递给了registerSensor方法,通过registerSensor注册传感器,然后通过单例模型创建了SensorFusion对象,创建并注册了一系列的虚拟传感器,疑惑,极大的疑惑,怎么传感器还有虚拟的??其实你注意看这几个传感器最前面的条件,if(hasGyro),表示如果存在陀螺仪的话,会创建这些虚拟设备,再看这些虚拟设备:旋转,重力,加速器,方向等,这些设备都对应一个物理硬件:陀螺仪,所以这些逻辑上存在,物理上不存在的设备叫虚拟设备。在初始化了虚拟设备后,将mSensorList传感器列表赋值给mUserSensorList,mSensorList是由registerSensor初始化的,mUserSensorList是要提交给Java框架层的传感器列表,最后通过run方法运行了SensorService线程,我们先来看下registerSensor的代码:

[cpp] view plain copy print ?
  1. void SensorService::registerSensor(SensorInterface* s) 
  2.     sensors_event_t event; 
  3.     memset(&event,0, sizeof(event)); 
  4.  
  5.     const Sensorsensor(s->getSensor()); 
  6.     // add to thesensor list (returned to clients) 
  7.     mSensorList.add(sensor); 
  8.     // add to ourhandle->SensorInterface mapping 
  9.    mSensorMap.add(sensor.getHandle(), s); 
  10.     // create anentry in the mLastEventSeen array 
  11.    mLastEventSeen.add(sensor.getHandle(), event); 

通过分析上面代码可知,将传入的HardwareSensor对象塑造了Sensor,添加到mSensorList向量表里,然后将HardwareSensor对象添加到mSensroMap键值对里,将新建的传感器事件数据封装对象event添加到mLastEventSeen键值对中。

我们通过下面的时序图来看下Sensor列表的获取过程。

深入浅出 - Android系统移植与平台开发- Sensor HAL框架分析之三_第1张图片

1)    SensorService监听线程及传感器事件的捕获

让我们再来看看SensorService线程,还记得前面SensorService的父类中有一个Thread类,当调用run方法时会创建线程并调用threadLoop方法。

[cpp] view plain copy print ?
  1. bool SensorService::threadLoop() 
  2.    LOGD("nuSensorService thread starting..."); 
  3.  
  4.     const size_tnumEventMax = 16 * (1 + mVirtualSensorList.size()); 
  5.    sensors_event_t buffer[numEventMax]; 
  6.    sensors_event_t scratch[numEventMax]; 
  7.    SensorDevice& device(SensorDevice::getInstance()); 
  8.     const size_tvcount = mVirtualSensorList.size(); 
  9.  
  10.     ssize_tcount; 
  11.     do
  12.              // 调用SensorDevice的poll方法看样子要多路监听了 
  13.         count = device.poll(buffer,numEventMax);      
  14.         if(count<0) { 
  15.            LOGE("sensor poll failed (%s)", strerror(-count)); 
  16.            break
  17.         } 
  18.               // 记录poll返回的每一个传感器中的最后一个数据信息到mLastEventSeen中 
  19.         recordLastValue(buffer, count); 
  20.  
  21.         // handlevirtual sensors 处理虚拟传感器数据 
  22.         if (count&& vcount) { 
  23.            sensors_event_t const * const event = buffer; 
  24.                       // 获得虚拟传感器列表 
  25.             constDefaultKeyedVector<int, SensorInterface*> virtualSensors( 
  26.                    getActiveVirtualSensors()); 
  27.             constsize_t activeVirtualSensorCount = virtualSensors.size();  // 虚拟传感器个数 
  28.             if(activeVirtualSensorCount) { 
  29.                size_t k = 0; 
  30.                SensorFusion& fusion(SensorFusion::getInstance()); 
  31.                if (fusion.isEnabled()) { 
  32.                    for (size_t i=0 ; i<size_t(count) ; i++) { 
  33.                        fusion.process(event[i]);              //处理虚拟传感器设备事件 
  34.                     } 
  35.                 } 
  36.                for (size_t i=0 ; i<size_t(count) ; i++) { 
  37.                    for (size_t j=0 ; j<activeVirtualSensorCount ; j++) { 
  38.                        sensors_event_t out; 
  39.                        if (virtualSensors.valueAt(j)->process(&out, event[i])) { 
  40.                             buffer[count + k] =out; 
  41.                             k++; 
  42.                        } 
  43.                    } 
  44.                 } 
  45.                if (k) { 
  46.                    // record the last synthesized values 
  47.                    recordLastValue(&buffer[count], k); 
  48.                    count += k; 
  49.                    // sort the buffer by time-stamps 
  50.                    sortEventBuffer(buffer, count); 
  51.                 } 
  52.             } 
  53.         } 
  54.  
  55.         // sendour events to clients...  
  56.              // 获得传感器连接对象列表 
  57.         constSortedVector< wp<SensorEventConnection> > activeConnections( 
  58.                getActiveConnections()); 
  59.         size_tnumConnections = activeConnections.size(); 
  60.         for(size_t i=0 ; i<numConnections ; i++) { 
  61.            sp<SensorEventConnection> connection( 
  62.                    activeConnections[i].promote()); 
  63.             if(connection != 0) { 
  64.                                // 向指定的传感器连接客户端发送传感器数据信息 
  65.                 connection->sendEvents(buffer, count, scratch); 
  66.             } 
  67.         } 
  68.     } while (count>= 0 || Thread::exitPending());   // 传感器循环监听线程 
  69.  
  70.    LOGW("Exiting SensorService::threadLoop => aborting..."); 
  71.     abort(); 
  72.     return false

我们看到device.poll方法,阻塞在了SensorDevice的poll方法上,它肯定就是读取Sensor硬件上的数据了,将传感器数据保存在buff中,然后调用recordLastValue方法,只保存同一类型传感器的最新数据(最后采集的一组数据)到键值对象mLastEventSeen里对应传感器的值域中。如果传感器设备是虚拟设备则调用SensorFusion.Process()方法对虚拟设备数据进行处理。SensorFusion关联一个SensorDevice,它是虚拟传感器设备的一个加工类,负责虚拟传感器数据的计算、处理、设备激活、设置延迟、获得功耗信息等操作。

让我们来回顾下整个过程吧。

深入浅出 - Android系统移植与平台开发- Sensor HAL框架分析之三_第2张图片

1. SensorManager对象创建并调用assertStateLocked方法

2. 在assertStateLocked方法中调用getService,获得SensorService服务

3. 当SensorService第一次强引用时,自动调用OnFirstRef方法

4.获得SensorDevice单例对象

6. 调用SensorDevice.getSensorList方法sensor_t列表保存在SensorService中

8. 调用registerSensor注册传感器,添加到mSensorList列表中

9. 启动SensorService线程,准备监听所有注册的传感器设备

12. 多路监听注册的传感器设备,当有传感器事件时,返回sensor_event_t封装的事件信息

16. 记录产生传感器事件的设备信息

17. 调用getActiveConnections获得所有的活动的客户端SensorEventConnection类对象

19.向客户端发送传感器事件信息

你可能感兴趣的:(深入浅出 - Android系统移植与平台开发- Sensor HAL框架分析之三)