Android 9.0 Framework系列--Sensor框架(一)

前言

研究代码永远是学习进入的最好方式,因为本人更多的工作内容还是在farmework层,这里把之前的一些研究也总结一下。所有的研究都是基于

Android 9.0。

一、Sensor框架概述

关于Sensor框架在网上描述的也挺多的,我也不做深入分析了,这里把自己的思考在这里做一下总结。

整个Android的思路都是server-client的思路,Sensor也不例外,Sensor框架也分为两部分,

1.1 client --SensorManager(frameworks\base\core\java\android\hardware)SensorManager类,它提供给客户实际操作。围绕SystemSensorManager,还有一系列相关类

1.1.1 java层

➢SensorManager.java --虚类

➢LegacySensorManager--9.0已废除

➢SensorListener.java --监听类

➢Sensor.java ---单个sensor的抽象,用户通过该类对Sensor进行具体实现

➢SystemSensorManager--SensorManager的实现类,实际上上层对Sensor的控制都在SystemSensorManager

1.1.2 jni层 

android_hardware_SensorManager.cpp(frameworks\base\core\jni)

1.2 server--SensorService(frameworks\native\services\sensorservice)

SensorService及其一系列代码的主要功能是实现对hal层的的访问,实现虚拟传感器的的相关算法SensorService.cpp --传感器服务

SensorDevice.cpp-管理传感器

RotationVectorSensor.cpp-虚拟传感器

1.3 Hal层

hal层是由厂家自己实现的,它对上提供给SensorService访问,对下直接访问驱动,每一款不同的SOC写法不一样,但都遵照了相Android的相关规则。这里后续描述。

1.4 驱动层

驱动实现了sensor的具体的功能,比如加速度传感器主要是获得xyz的加速度等等。

二、启动

2.1 SensorService的启动

Android启动过程中,先启动SensorService,然后调用hal层进行相关初始化,并进入相关轮询状态。

2.1.1 startBootstrapServices() frameworks\base\services\java\com\android\server\SystemServer.java


/**
  * Start the sensor service. This is a blocking call and can take time.
  */
private static native void startSensorService();
    
private void startBootstrapServices() {
        .............................

        // The sensor service needs access to package manager service, app ops
        // service, and permissions service, therefore we start it after them.
        // Start sensor service in a separate thread. Completion should be checked
        // before using it.
        mSensorServiceStart = SystemServerInitThreadPool.get().submit(() -> {
            TimingsTraceLog traceLog = new TimingsTraceLog(
                    SYSTEM_SERVER_TIMING_ASYNC_TAG, Trace.TRACE_TAG_SYSTEM_SERVER);
            traceLog.traceBegin(START_SENSOR_SERVICE);
            //启动sensor,在jni中实现
            startSensorService();
            traceLog.traceEnd();
        }, START_SENSOR_SERVICE);
    }

2.1.2 startSensorService()

frameworks\base\services\core\jni\com_android_server_SystemServer.cpp 

startSensorService直接在jni中实现

/*
 * JNI registration.
 */
static const JNINativeMethod gMethods[] = {
    /* name, signature, funcPtr */
    { "startSensorService", "()V", (void*) android_server_SystemServer_startSensorService },
    { "startHidlServices", "()V", (void*) android_server_SystemServer_startHidlServices },
};

static void android_server_SystemServer_startSensorService(JNIEnv* /* env */, jobject /* clazz */) {
    char propBuf[PROPERTY_VALUE_MAX];
    property_get("system_init.startsensorservice", propBuf, "1");
    if (strcmp(propBuf, "1") == 0) {
        //直接调用SensorService::instantiate()
        SensorService::instantiate();
    }

}

2.1.3 SensorService::instantiate()

SensorService继承自BinderService,SensorService::instantiate()会进一步执行BinderService::instantiate,在BinderService中会执行addService,然后将SensorService加入到ServiceManager中。

2.1.4 SensorService::onFirstRef()

SensorService还继承了RefBase,所以会在第一次调用时,调用onFirstRef,而SensorService的初始化就是在onFirstRef中完成。onFirstRef中,比较重要的初始化内容包括:

2.1.4.1.创建SensorDevice,SensorDevice是负责与Hal层连接的关键类

2.1.4.2.从SensorDevice获得当前的传感器列表,并判断当前系统存在哪些传感器,创建对应的相关类,

2.1.4.3 根据当前传感器,创建虚拟传感器类。

从代码上看,一些虚拟传感器的创建关系如下:

加速度/地磁/陀螺仪都有:

RotationVectorSensor

OrientationSensor

LinearAccelerationSensor

CorrectedGyroSensor

GyroDriftSensor

加速度/陀螺仪:

GameRotationVectorSensor

GravitySensor

加速度/地磁:

GeoMagRotationVectorSensor

void SensorService::onFirstRef() {
    ALOGD("nuSensorService starting...");
    //2.1.4.1===
    SensorDevice& dev(SensorDevice::getInstance());

    sHmacGlobalKeyIsValid = initializeHmacKey();

    if (dev.initCheck() == NO_ERROR) {
        sensor_t const* list;
       //2.1.4.2===传感器创建
        ssize_t count = dev.getSensorList(&list);
        if (count > 0) {
            ssize_t orientationIndex = -1;
            bool hasGyro = false, hasAccel = false, hasMag = false;
            uint32_t virtualSensorsNeeds =
                    (1<<SENSOR_TYPE_GRAVITY) |
                    (1<<SENSOR_TYPE_LINEAR_ACCELERATION) |
                    (1<<SENSOR_TYPE_ROTATION_VECTOR) |
                    (1<<SENSOR_TYPE_GEOMAGNETIC_ROTATION_VECTOR) |
                    (1<<SENSOR_TYPE_GAME_ROTATION_VECTOR);

            for (ssize_t i=0 ; i<count ; i++) {
                bool useThisSensor=true;

                switch (list[i].type) {
                    case SENSOR_TYPE_ACCELEROMETER:
                        hasAccel = true;
                        break;
                    case SENSOR_TYPE_MAGNETIC_FIELD:
                        hasMag = true;
                        break;
                    case SENSOR_TYPE_ORIENTATION:
                        orientationIndex = i;
                        break;
                    case SENSOR_TYPE_GYROSCOPE:
                    case SENSOR_TYPE_GYROSCOPE_UNCALIBRATED:
                        hasGyro = true;
                        break;
                    case SENSOR_TYPE_GRAVITY:
                    case SENSOR_TYPE_LINEAR_ACCELERATION:
                    case SENSOR_TYPE_ROTATION_VECTOR:
                    case SENSOR_TYPE_GEOMAGNETIC_ROTATION_VECTOR:
                    case SENSOR_TYPE_GAME_ROTATION_VECTOR:
                        if (IGNORE_HARDWARE_FUSION) {
                            useThisSensor = false;
                        } else {
                            virtualSensorsNeeds &= ~(1<<list[i].type);
                        }
                        break;
                }
                if (useThisSensor) {
                    registerSensor( new HardwareSensor(list[i]) );
                }
            }

            // it's safe to instantiate the SensorFusion object here
            // (it wants to be instantiated after h/w sensors have been
            // registered)
            SensorFusion::getInstance();
                 //2.1.4.3===虚拟传感器创建
            if (hasGyro && hasAccel && hasMag) {
                // Add Android virtual sensors if they're not already
                // available in the HAL
                bool needRotationVector =
                        (virtualSensorsNeeds & (1<<SENSOR_TYPE_ROTATION_VECTOR)) != 0;

                registerSensor(new RotationVectorSensor(), !needRotationVector, true);
                registerSensor(new OrientationSensor(), !needRotationVector, true);

                bool needLinearAcceleration =
                        (virtualSensorsNeeds & (1<<SENSOR_TYPE_LINEAR_ACCELERATION)) != 0;

                registerSensor(new LinearAccelerationSensor(list, count),
                               !needLinearAcceleration, true);

                // virtual debugging sensors are not for user
                registerSensor( new CorrectedGyroSensor(list, count), true, true);
                registerSensor( new GyroDriftSensor(), true, true);
            }

            if (hasAccel && hasGyro) {
                bool needGravitySensor = (virtualSensorsNeeds & (1<<SENSOR_TYPE_GRAVITY)) != 0;
                registerSensor(new GravitySensor(list, count), !needGravitySensor, true);

                bool needGameRotationVector =
                        (virtualSensorsNeeds & (1<<SENSOR_TYPE_GAME_ROTATION_VECTOR)) != 0;
                registerSensor(new GameRotationVectorSensor(), !needGameRotationVector, true);
            }

            if (hasAccel && hasMag) {
                bool needGeoMagRotationVector =
                        (virtualSensorsNeeds & (1<<SENSOR_TYPE_GEOMAGNETIC_ROTATION_VECTOR)) != 0;
                registerSensor(new GeoMagRotationVectorSensor(), !needGeoMagRotationVector, true);
            }

            // Check if the device really supports batching by looking at the FIFO event
            // counts for each sensor.
            bool batchingSupported = false;
            mSensors.forEachSensor(
                    [&batchingSupported] (const Sensor& s) -> bool {
                        if (s.getFifoMaxEventCount() > 0) {
                            batchingSupported = true;
                        }
                        return !batchingSupported;
                    });

            if (batchingSupported) {
                // Increase socket buffer size to a max of 100 KB for batching capabilities.
                mSocketBufferSize = MAX_SOCKET_BUFFER_SIZE_BATCHED;
            } else {
                mSocketBufferSize = SOCKET_BUFFER_SIZE_NON_BATCHED;
            }

            // Compare the socketBufferSize value against the system limits and limit
            // it to maxSystemSocketBufferSize if necessary.
            FILE *fp = fopen("/proc/sys/net/core/wmem_max", "r");
            char line[128];
            if (fp != NULL && fgets(line, sizeof(line), fp) != NULL) {
                line[sizeof(line) - 1] = '\0';
                size_t maxSystemSocketBufferSize;
                sscanf(line, "%zu", &maxSystemSocketBufferSize);
                if (mSocketBufferSize > maxSystemSocketBufferSize) {
                    mSocketBufferSize = maxSystemSocketBufferSize;
                }
            }
            if (fp) {
                fclose(fp);
            }

            mWakeLockAcquired = false;
            mLooper = new Looper(false);
            const size_t minBufferSize = SensorEventQueue::MAX_RECEIVE_BUFFER_EVENT_COUNT;
            mSensorEventBuffer = new sensors_event_t[minBufferSize];
            mSensorEventScratch = new sensors_event_t[minBufferSize];
            mMapFlushEventsToConnections = new wp<const SensorEventConnection> [minBufferSize];
            mCurrentOperatingMode = NORMAL;

            mNextSensorRegIndex = 0;
            for (int i = 0; i < SENSOR_REGISTRATIONS_BUF_SIZE; ++i) {
                mLastNSensorRegistrations.push();
            }
            
            //2.1.4.4===运行
            //会启动threadLoop
            mInitCheck = NO_ERROR;
            mAckReceiver = new SensorEventAckReceiver(this);
            mAckReceiver->run("SensorEventAckReceiver", PRIORITY_URGENT_DISPLAY);
            run("SensorService", PRIORITY_URGENT_DISPLAY);

            // priority can only be changed after run
            enableSchedFifoMode();

            // Start watching UID changes to apply policy.
            mUidPolicy->registerSelf();
        }
    }
}

2.1.5 SensorService::threadLoop()

SensorService::threadLoop()主要实现对sensor的poll,轮询sensor上报的相关事件

2.2 SensorService传感器的激活

SensorService除了了启动,还需要将已有的传感器进行activate,通常再底层驱动的实现过程中,只有activate后的传感器才会向上上报数据。

从代码跟踪上看Android启动过程中会向SystemSensorManager.注册registerListener,并进一步调用registerListenerImpl。

registerListenerImpl会获得SensorEventQueue ,并调用SensorEventQueue 的addSensor。

 /** @hide */
    @Override
    protected boolean registerListenerImpl(SensorEventListener listener, Sensor sensor,
            int delayUs, Handler handler, int maxBatchReportLatencyUs, int reservedFlags) {
           ................

        // Invariants to preserve:
        // - one Looper per SensorEventListener
        // - one Looper per SensorEventQueue
        // We map SensorEventListener to a SensorEventQueue, which holds the looper
        synchronized (mSensorListeners) {
            //获得SensorEventQueue 
            SensorEventQueue queue = mSensorListeners.get(listener);
            if (queue == null) {
                Looper looper = (handler != null) ? handler.getLooper() : mMainLooper;
                final String fullClassName =
                        listener.getClass().getEnclosingClass() != null
                            ? listener.getClass().getEnclosingClass().getName()
                            : listener.getClass().getName();
                queue = new SensorEventQueue(listener, looper, this, fullClassName);
				//向queue 中添加要监听的传感器
                if (!queue.addSensor(sensor, delayUs, maxBatchReportLatencyUs)) {
                    queue.dispose();
                    return false;
                }
                mSensorListeners.put(listener, queue);
                return true;
            } else {
								Log.e(TAG, "registerListenerImpl33333");
                return queue.addSensor(sensor, delayUs, maxBatchReportLatencyUs);
            }
        }
    }

   

SensorEventQueue是SystemSensorManager的内部类,具体实现类是InjectEventQueue。

SensorEventQueue中的addSensor,会将上层要监听的sensor加入到监听队列中,并调用enableSensor使能对应的传感器

        public boolean addSensor(
                Sensor sensor, int delayUs, int maxBatchReportLatencyUs) {
            // Check if already present.
            int handle = sensor.getHandle();
            if (mActiveSensors.get(handle)) return false;

            // Get ready to receive events before calling enable.
            mActiveSensors.put(handle, true);
            //添加监听队列
            addSensorEvent(sensor);
            //使能传感器
            if (enableSensor(sensor, delayUs, maxBatchReportLatencyUs) != 0) {
                // Try continuous mode if batching fails.
                if (maxBatchReportLatencyUs == 0
                        || maxBatchReportLatencyUs > 0 && enableSensor(sensor, delayUs, 0) != 0) {
                    removeSensor(sensor, false);
                    return false;
                }
            }
            return true;
        }


        private int enableSensor(
                Sensor sensor, int rateUs, int maxBatchReportLatencyUs) {
            if (mNativeSensorEventQueue == 0) throw new NullPointerException();
            if (sensor == null) throw new NullPointerException();
            //调用android_hardware_SensorManager.cpp jni使能传感器
            return nativeEnableSensor(mNativeSensorEventQueue, sensor.getHandle(), rateUs,
                    maxBatchReportLatencyUs);
        }

android_hardware_SensorManager.cpp jni使能传感器 开始调用SensorEventQueue

static jint nativeEnableSensor(JNIEnv *env, jclass clazz, jlong eventQ, jint handle, jint rate_us,
                               jint maxBatchReportLatency) {
    sp<Receiver> receiver(reinterpret_cast<Receiver *>(eventQ));
	    ALOGI("nativeEnableSensor");
    return receiver->getSensorEventQueue()->enableSensor(handle, rate_us, maxBatchReportLatency,
                                                         0);
}

SensorEventQueue会调用SensorEventConnection

status_t SensorEventQueue::enableSensor(Sensor const* sensor, int32_t samplingPeriodUs) const {
	    ALOGE("SensorEventQueue enableSensor");
    return mSensorEventConnection->enableDisable(sensor->getHandle(), true,
                                                 us2ns(samplingPeriodUs), 0, 0);
}

SensorEventConnection会调用SensorService进行传感器激活

status_t SensorService::SensorEventConnection::enableDisable(
        int handle, bool enabled, nsecs_t samplingPeriodNs, nsecs_t maxBatchReportLatencyNs,
        int reservedFlags)
{
    status_t err;
    if (enabled) {
		  ALOGE("SensorEventConnection::enableDisabl");
        err = mService->enable(this, handle, samplingPeriodNs, maxBatchReportLatencyNs,
                               reservedFlags, mOpPackageName);

    } else {
        err = mService->disable(this, handle);
    }
    return err;
}

 

03-20 11:12:18.037  3509  3524 D SensorService: Calling batch handle==0 flags=0rate=66667000 timeout== 100000000
03-20 11:12:18.037  3509  3524 D SensorService: Calling batch handle==0 flags=0rate=66667000 timeout== 100000000
03-20 11:12:18.037  3509  3524 D SensorService: SensorDevice::batch: ident=0x9a4d1180, handle=0x00000000, flags=0, period_ns=66667000 timeout=100000000
03-20 11:12:18.037  3509  3524 D SensorService:         >>> curr_period=9223372036854775807 min_period=66667000 curr_timeout=9223372036854775807 min_timeout=100000000
03-20 11:12:18.037  3509  3524 D SensorService:         >>> actuating h/w BATCH 0x00000000 66667000 100000000
03-20 11:12:18.038  3509  3524 D SensorService: Calling activate on 0
03-20 11[   26.291237@2] sensors 2-006b: sensor on: starting poll sensor data 64ms
:12:18.038  3509  3524 D SensorService: SensorDevice::activate: ident=0x9a4d1180, handle=0x00000000, enabled=1, count=1
03-20 11:12:18.038  3509  3524 D SensorService: enable index=0
03-20 11:12:18.038  3509  3524 D SensorService:         >>> actuating h/w activate handle=0 enabled=1

### 回答1: android-x86_64-9.0-r2-k49.iso是一个Android操作系统的镜像文件,专为64位PC和笔记本电脑而设计。该操作系统基于谷歌的Android Open Source Project(AOSP)构建,并且可以在x86、AMD和Intel设备上运行,支持UEFI USB和Legacy-BIOS引导方式。 这个镜像文件是第9版Android操作系统的第2个修订版本,其中包含了最新的安全补丁程序和功能更新。该版本的Android系统最初于2019年10月发布,旨在改善性能、增强隐私保护和加强系统稳定性,同时提供更多的自定义选项和新功能。 这个镜像文件具有实用性,可作为装备在个人计算机和笔记本电脑上的操作系统。用户可以通过下载这个镜像文件并将其安装在电脑上,轻松地运行Android应用程序,并在个人电脑上获得更好的使用体验。同时,该操作系统还可以用于应用程序开发和测试,以确保Android应用程序在不同设备上的兼容性和性能。 总之,android-x86_64-9.0-r2-k49.iso是一个可靠和实用的Android操作系统的扩展,具有更好的性能、安全和用户体验,是适用于PC和笔记本电脑的优秀操作系统。 ### 回答2: android-x86_64-9.0-r2-k49.iso 是一个 Android 操作系统的 64 位版本,主要针对 x86 架构的计算机或虚拟机而设计。其中的 9.0-r2 表示这是基于 Android 9.0 版本的第二个版本,而 k49 则是表明该版本为基于 Linux Kernel 4.9 的版本。 Android-x86_64-9.0-r2-k49.iso 的最大特点是可以在个人电脑上或者虚拟机上直接安装运行,让普通计算机用户也可以享受到 Android 系统的特性。用户可以在其上安装和运行普通的 Android 应用程序,通过模拟 Android 手机的界面让用户体验更加舒适自然。同时,这个版本还具备较高的兼容性和适应性,兼容广泛的硬件设备,同时支持多种存储方式,例如 U 盘、SSD 硬盘等。 与 Android 手机不同,Android-x86_64-9.0-r2-k49.iso 也启动了类似于 Grub 的引导程序,用户可以通过键盘选择和启动其它操作系统或者直接运行安装的 Android 操作系统。同时,安装过程也需要用户进行操作,用户需要选择安装到哪个磁盘,是否格式化磁盘等。在使用上,用户也需要注意一些特殊的设置,例如键位设置等,以便更好地适应 Android 系统的操作方式。 总之,Android-x86_64-9.0-r2-k49.iso 版本是一个非常有趣和实用的 Android 操作系统,它可以让 PC 用户更好的体验 Android 操作系统,同时也带来更多的选择和便利性。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值