调用过程中涉及到的文件
Driver: ft5x0x.cà
HAL: SensorGTP.cpp à sensors.cpp à SensorDevice.cpp à
Framework: SensorService.cppàSensorManager.cppà android_hardware_SensorManager.cpp à
SensorManager.java à PowerManagerService.java
本文分几个部分:
1、驱动层:tp驱动中实现感应开关
2、HAL层:打开/dev/proximity字符设备,并实现感应开关操作,相当于linux应用程序开发层。
3、framework层:涉及到SensorManager.java与PowerManagerService.java两个文件,主要是负责背光亮灭与sensor开启关闭。
4、app层:主要是PhoneApp接通电话开关感应。
关于android分层架构都应该知道:如下图
第一部分:TP驱动实现距离感应开关实现代码
1、 首先在probe函数中增加一段程序,组要是注册一个混杂字符设备
- #include <linux/miscdevice.h>
- #include <linux/wakelock.h>
- //#include <linux/eventstore.h>
- #include <linux/fs.h>
- //#include <linux/miscdevice.h>
- #include <linux/ioctl.h>
- #define GTP_PROXIMITY 1 //宏开关
- static int gtp_proximity_start = 0; /* 0 is stop, 1 is start */
- #define GTP_IOCTL_MAGIC 0x5D
- #define GTP_IOCTL_PROX_ON _IO(GTP_IOCTL_MAGIC, 7)
- #define GTP_IOCTL_PROX_OFF _IO(GTP_IOCTL_MAGIC, 8)
- #define FT5X0X_SENSOR_NAME "gtp_proximity" //新增字符设备名称
- #if GTP_PROXIMITY
- err = misc_register(>p_proximity_misc);
- if (err < 0)
- {
- pr_err("%s: could not register misc device\n", __func__);
- }
- #endif
- static struct miscdevice gtp_proximity_misc = {
- .minor = MISC_DYNAMIC_MINOR,
- .name = FT5X0X_SENSOR_NAME,
- .fops = >p_proximity_fops,
- };
- static const struct file_operations gtp_proximity_fops = {
- .owner = THIS_MODULE,
- .open = <span style="font-family: Arial, Helvetica, sans-serif;">FT5X0X</span><span style="font-family: Arial, Helvetica, sans-serif;">_proximity_open,</span>
- .release = NULL,//_proximity_release,
- .ioctl = FT5X0X_proximity_ioctl,
- /*.ioctl = FT5X0x_proximity_ioctl,unlocked_ioctl*/
- };
- static int ft5x0x_proximity_open(struct inode *inode, struct file *file)
- {
- int err;
- err = nonseekable_open(inode, file);
- if (err < 0)
- return err;
- file->private_data = i2c_get_clientdata(this_client);
- printk("ft5x0x_proximity_open-file->private_data=%x\r\n",file->private_data);
- return 0;
- }
- HAL层会根据幻数调用ft5x0x_proximity_ioctl中是否打开距离感应。
- static int ft5x0x_proximity_ioctl(struct inode *inode, struct file *file,unsigned int cmd, unsigned long arg)
- {
- //printk("ft5x0x_proximity_ioctl");
- switch (cmd) {
- case GTP_IOCTL_PROX_ON:
- //gtp_proximity_open();
- ft5x0x_proximity_set_enable(1);
- gtp_proximity_start = 1; /* 0 is stop, 1 is start */
- printk("ft5x0x_proximity_ioctl--on\r\n");
- break;
- case GTP_IOCTL_PROX_OFF:
- //gtp_proximity_release();
- ft5x0x_proximity_set_enable(0);
- gtp_proximity_start = 0;
- printk("ft5x0x_proximity_ioctl--off\r\n");
- break;
- default:
- //pr_err("%s: invalid cmd %d\n", __func__, _IOC_NR(cmd));
- printk("ft5x0x_proximity_ioctl--error\r\n");
- return -EINVAL;
- }
- return 0;
- }
关于如何判断是否接近,可以向FAE咨询,让他们提供说明文档,改哪些寄存器的值实现。
ft5x0x 类型的TP实现:Enable 脸部接近感应功能,拨出电话并且已经开始连线时或者是来电接通电话时启
动此项功能,手机启动触摸IC进入大面积感应发出的I2C指令如下:Write(0xB0,0x01)
操作说明:主控向TP的0xB0 单元写0x01 数据,写入成功后TP即进入脸部接近感应功能;
- static void ft5x0x_proximity_set_enable(int enable)
- {
- if(enable == 1)
- {
- gtp_proximity_start = 1;
- }else{
- gtp_proximity_start = 0;
- }
- ft5x0x_write_reg(0xB0, enable);
- }
- 在probe函数中
- INIT_WORK(&ft5x0x_ts->pen_event_work, ft5x0x_ts_pen_irq_work);
- static void ft5x0x_ts_pen_irq_work(struct work_struct *work)
- {
- #if 1
- int ret = -1;
- // printk("==work 1=\n");
- #ifdef GTP_PROXIMITY
- printk("_ts_pen_irq_work---\r\n");
- ft5x0x_ts_proximity_work();
- #endif
- ret = ft5x0x_read_data();
- if (ret == 0) {
- ft5x0x_report_value();
- }
- // else printk("data package read error\n");
- // printk("==work 2=\n");
- // msleep(1);
- #endif
- enable_irq(this_client->irq);
- }
2,TP当在手机“Enable脸部接近接触感应”模式时:
2.1 听筒端靠近人体距离小于8mm时(具体距离以实测为准),主机端会收到如下数据包:
I2C start +I2C地址+0x00+0xc0+其它相关数据+ I2Cstop(0xc0 是以手势码的形式发出的)
2.2 听筒端移开人体超过8mm时(具体距离以实测为准),主机端会收到如下数据包:
I2C start + I2C地址+0x00+0xe0+其它相关数据+ I2Cstop(0xe0 是以手势码的形式发出的)
3,Disable脸部接近感应(预设) 结束通话时退出大面积感应功能。手机发出的I2C数据:
Write(0xb0,0x00)
操作说明:主机向从机0xb0 地址写0x00数据,写入成功后退出大面积感应功能。
mso- Wat����ily:宋体;mso-fareast-theme-font:minor-fareast;mso-hansi-font-family:Calibri;mso-hansi-theme-font:minor-latin'>开启关闭。4、app层:主要是PhoneApp接通电话开关感应。
- static void ft5x0x_ts_proximity_work(void)
- {
- static int value_temp = 0;
- int value;
- char buffer[30]={0};
- struct ft5x0x_ts_data *data = i2c_get_clientdata(this_client);
- i2c_smbus_read_i2c_block_data(this_client, 0x00, 8, &(buffer[0]));
- printk("-ft5x0x_ts_proximity_work-buffer[1] =-%x\n", buffer[1]);
- if(gtp_proximity_start == 1)
- {
- if (buffer[1]==0xC0)
- {
- input_report_abs(data->input_dev, ABS_DISTANCE, 0); //report far
- //input_sync(data->input_dev);
- //value_temp = value;
- printk("-ft5x0x_ts_proximity_work--near\r\n");
- }
- else if(buffer[1]==0xE0)
- {
- input_report_abs(data->input_dev, ABS_DISTANCE, 1); //report far
- printk("-ft5x0x_ts_proximity_work--far\r\n");
- }
- }}
- 在suspend与resume不走tp正常流程。
- static void ft5x0x_ts_suspend(struct early_suspend *handler)
- {
- #if GTP_PROXIMITY
- if (gtp_proximity_start == 1)
- return;
- #endif
- … …
- }
- static void ft5x0x_ts_resume(struct early_suspend *handler)
- {
- printk("==%s==\n", __FUNCTION__);
- #if GTP_PROXIMITY
- if (gtp_proximity_start == 1)
- return;
- #endif
- … …
- }
TP驱动层距离感应已经实现,下一步就是HAL层调用驱动了。
第二部:HAL层实现调用驱动程序,向上层提供接口。
- SensorGTP.cpp
- #include <fcntl.h>
- #include <errno.h>
- #include <math.h>
- #include <poll.h>
- #include <unistd.h>
- #include <dirent.h>
- #include <sys/select.h>
- #include <cutils/log.h>
- #include "SensorGTP.h"
- #include "sensors.h"
- #define ft5x0x_DEVICE_NAME "/dev/gtp_proximity" //设备节点
- #define GTP_IOCTL_MAGIC 0x5D
- #define GTP_IOCTL_GET_PFLAG _IOR(GTP_IOCTL_MAGIC, 1, int)
- #define GTP_IOCTL_GET_LFLAG _IOR(GTP_IOCTL_MAGIC, 2, int)
- #define GTP_IOCTL_SET_PFLAG _IOW(GTP_IOCTL_MAGIC, 3, int)
- #define GTP_IOCTL_SET_LFLAG _IOW(GTP_IOCTL_MAGIC, 4, int)
- #define GTP_IOCTL_GET_DATA _IOW(GTP_IOCTL_MAGIC, 5, unsigned char)
- #define GTP_IOCTL_PROX_ON _IO(GTP_IOCTL_MAGIC, 7)
- #define GTP_IOCTL_PROX_OFF _IO(GTP_IOCTL_MAGIC, 8)
- /*****************************************************************************/
- SensorGTP::SensorGTP()
- : SensorBase(ft5x0x_DEVICE_NAME, "ft5x0x_ts"),
- mEnabled(0),
- mPendingMask(0),
- mInputReader(32),
- mHasPendingEvent(false)
- {
- memset(mPendingEvents, 0, sizeof(mPendingEvents));
- mPendingEvents[Proximity].version = sizeof(sensors_event_t);
- mPendingEvents[Proximity].sensor = ID_P;
- mPendingEvents[Proximity].type = SENSOR_TYPE_PROXIMITY;
- for (int i=0 ; i<numSensors ; i++)
- mDelays[i] = 200000000; // 200 ms by default
- }
- SensorGTP::~SensorGTP()
- {
- }
- bool SensorGTP::hasPendingEvents() const
- {
- return mHasPendingEvent;
- }
- int SensorGTP::setDelay(int32_t handle, int64_t ns)
- {
- return 0;
- }
- int SensorGTP::setEnable(int32_t handle, int en)
- {
- int what = -1;
- int cmd;
- int err = 0;
- int newState = en ? 1 : 0;
- switch (handle) {
- case ID_P: what = Proximity; break;
- }
- if (uint32_t(what) >= numSensors)
- return -EINVAL;
- if (!mEnabled)
- open_device();
- switch (what)
- {
- case Proximity: //将调用驱动层的ioctol实现开关距离感应
- if (newState)
- {
- cmd = GTP_IOCTL_PROX_ON;
- }
- else
- {
- cmd = GTP_IOCTL_PROX_OFF;
- }
- break;
- }
- int flags = newState;
- err = ioctl(dev_fd, cmd, &flags);
- LOGD("ioctl,err=%d\n",err);
- err = err < 0 ? -errno : 0;
- LOGD("SensorGTP::enable what=%d; flags=%d; err=%d\n", what, flags, err);
- LOGE_IF(err, "ECS_IOCTL_APP_SET_XXX failed (%s)", strerror(-err));
- if (!err)
- {
- mEnabled &= ~(1 << what);
- mEnabled |= (uint32_t(flags) << what);
- }
- LOGD("SensorGTP::mEnabled=0x%x\n", mEnabled);
- if (!mEnabled)
- close_device();
- return err;
- }
- int SensorGTP::getEnable(int32_t handle)
- {
- int enable=0;
- int what = -1;
- switch (handle) {
- case ID_P: what = Proximity; break;
- }
- if (uint32_t(what) >= numSensors)
- return -EINVAL;
- enable = mEnabled & (1 << what);
- if(enable > 0)
- enable = 1;
- LOGD("SensorGTP::mEnabled=0x%x; enable=%d\n", mEnabled, enable);
- return enable;
- }
- int SensorGTP::readEvents(sensors_event_t* data, int count)
- {
- if (count < 1)
- return -EINVAL;
- ssize_t n = mInputReader.fill(data_fd);
- if (n < 0)
- return n;
- int numEventReceived = 0;
- input_event const* event;
- while (count && mInputReader.readEvent(&event)) {
- int type = event->type;
- if (type == EV_ABS) {
- processEvent(event->code, event->value);
- mInputReader.next();
- } else if (type == EV_SYN) {
- int64_t time = timevalToNano(event->time);
- for (int j=0 ; count && mPendingMask && j<numSensors ; j++) {
- if (mPendingMask & (1<<j)) {
- mPendingMask &= ~(1<<j);
- mPendingEvents[j].timestamp = time;
- if (mEnabled & (1<<j)) {
- *data++ = mPendingEvents[j];
- count--;
- numEventReceived++;
- }
- }
- }
- if (!mPendingMask) {
- mInputReader.next();
- }
- } else {
- LOGE("Apds9900Sensor: unknown event (type=%d, code=%d)",
- type, event->code);
- mInputReader.next();
- }
- }
- return numEventReceived;
- }
- void SensorGTP::processEvent(int code, int value)
- {
- switch (code) {
- case EVENT_TYPE_PROXIMITY:
- mPendingMask |= 1<<Proximity;
- mPendingEvents[Proximity].distance = value;
- LOGD("SensorGTP: mPendingEvents[Proximity].distance = %f",mPendingEvents[Proximity].distance);
- break;
- default:
- LOGD("SensorGTP: default value = %d",value);
- break;
- }
- }
- SensorGTP.h
- #ifndef ANDROID_GTP_SENSOR_H
- #define ANDROID_GTP_SENSOR_H
- #include <stdint.h>
- #include <errno.h>
- #include <sys/cdefs.h>
- #include <sys/types.h>
- #include "sensors.h"
- #include "SensorBase.h"
- #include "InputEventReader.h"
- /*****************************************************************************/
- struct input_event;
- class SensorGTP : public SensorBase
- {
- public:
- SensorGTP();
- virtual ~SensorGTP();
- enum
- {
- Light = 0,
- Proximity = 1,
- numSensors
- };
- virtual int setDelay(int32_t handle, int64_t ns);
- virtual int setEnable(int32_t handle, int enabled);
- virtual bool hasPendingEvents() const;
- virtual int readEvents(sensors_event_t* data, int count);
- virtual int getEnable(int32_t handle);
- void processEvent(int code, int value);
- private:
- int update_delay();
- uint32_t mEnabled;
- bool mHasPendingEvent;
- uint32_t mPendingMask;
- InputEventCircularReader mInputReader;
- sensors_event_t mPendingEvents[numSensors];
- uint64_t mDelays[numSensors];
- };
- /*****************************************************************************/
- #endif // ANDROID_GT8XX_SENSOR_H
此函数初始化将在sensors.cpp函数中实现,关于此阶段的说明,先来看下SensorDevice.cpp文件中的函数,此文件中实现了SensorDevice的初始化并且通过
hw_get_module(SENSORS_HARDWARE_MODULE_ID,(hw_module_tconst**)&mSensorModule);获取sensor模块,将sensor打开。
- SensorDevice::SensorDevice()
- : mSensorDevice(0),
- mSensorModule(0)
- {
- 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) {
- err = sensors_open(&mSensorModule->common, &mSensorDevice);
- //1、此函数将会调用sensors.cpp文件中的open_sensors函数。
- LOGE_IF(err, "couldn't open device for module %s (%s)",
- SENSORS_HARDWARE_MODULE_ID, strerror(-err));
- if (mSensorDevice) {
- sensor_t const* list;
- //2、此函数将调用sensors.cpp中的sensors__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);//3、
- }
- }
- }
- }
- 在上面一个函数标志1中函数将会调用:
- struct sensors_module_t HAL_MODULE_INFO_SYM = {
- common: {
- tag: HARDWARE_MODULE_TAG,
- version_major: 1,
- version_minor: 0,
- id: SENSORS_HARDWARE_MODULE_ID,
- name: "AKM Sensor module",
- author: "Asahi Kasei Microdevices",
- methods: &sensors_module_methods,
- },
- get_sensors_list: sensors__get_sensors_list,
- };
- static struct hw_module_methods_t sensors_module_methods = {
- open: open_sensors
- };
- static int open_sensors(const struct hw_module_t* module, const char* id,
- struct hw_device_t** device)
- {
- int status = -EINVAL;
- //new 一个sensors_poll_context_t并初始化
- sensors_poll_context_t *dev = new sensors_poll_context_t();
- memset(&dev->device, 0, sizeof(sensors_poll_device_t));
- dev->device.common.tag = HARDWARE_DEVICE_TAG;
- dev->device.common.version = 0;
- dev->device.common.module = const_cast<hw_module_t*>(module);
- dev->device.common.close = poll__close;
- dev->device.activate = poll__activate;
- dev->device.setDelay = poll__setDelay;
- dev->device.poll = poll__poll;
- *device = &dev->device.common;
- status = 0;
- return status;
- }
- 在sensors_poll_context_t *dev = new sensors_poll_context_t();函数中
- sensors_poll_context_t::sensors_poll_context_t()
- {
- //new 并初始化SensorGTP()
- mSensors[gtp_proximity] = new SensorGTP();
- mPollFds[gtp_proximity].fd = mSensors[gtp_proximity]->getFd();
- mPollFds[gtp_proximity].events = POLLIN;
- mPollFds[gtp_proximity].revents = 0;
- int wakeFds[2];
- int result = pipe(wakeFds);
- LOGE_IF(result<0, "error creating wake pipe (%s)", strerror(errno));
- fcntl(wakeFds[0], F_SETFL, O_NONBLOCK);
- fcntl(wakeFds[1], F_SETFL, O_NONBLOCK);
- mWritePipeFd = wakeFds[1];
- mPollFds[wake].fd = wakeFds[0];
- mPollFds[wake].events = POLLIN;
- mPollFds[wake].revents = 0;
- }
- 3、在上一个函数中mSensorDevice->activate(mSensorDevice, list[i].handle, 0);
- 此函数调用了:
- int sensors_poll_context_t::activate(int handle, int enabled) {
- /*将根据handle返回哪个sensor。Handle有ID_A:acc;ID_M:ID_O:mag;ID_L:ID_P:
- gtp_proximity; al3006_pls;*/
- int drv = handleToDriver(handle);
- int err;
- err = mSensors[drv]->setEnable(handle, enabled);
- if (enabled && !err) {
- const char wakeMessage(WAKE_MESSAGE);
- int result = write(mWritePipeFd, &wakeMessage, 1);
- LOGE_IF(result<0, "error sending wake message (%s)", strerror(errno));
- }
- return err;
- }
- err = mSensors[drv]->setEnable(handle, enabled);
- 将调用int SensorGTP::setEnable(int32_t handle, int en)使能距离感应。
- 现在分析第二部分中的第2步:
- SensorService.cppSensorManager.cpp android_hardware_SensorManager.cpp
- —> SensorManager.java
- 在SensorService.cpp中初始化SensorDevice是在如下函数中:
- void SensorService::onFirstRef()
- {
- LOGD("nuSensorService starting...");
- SensorDevice& dev(SensorDevice::getInstance());
- 在SensorManager.cpp中
- SensorManager::SensorManager()
- : mSensorList(0)
- {
- //获取sensorservice服务
- const String16 name("sensorservice");
- while (getService(name, &mSensorServer) != NO_ERROR) {
- usleep(250000);
- }
- //获取sensor项
- mSensors = mSensorServer->getSensorList();
- size_t count = mSensors.size();
- mSensorList = (Sensor const**)malloc(count * sizeof(Sensor*));
- for (size_t i=0 ; i<count ; i++) {
- mSensorList[i] = mSensors.array() + i;
- }
- }
- JNI层android_hardware_SensorManager.cpp
- framework层SensorManager.java
- 在PowerManagerService.java中
- public void acquireWakeLockLocked(int flags, IBinder lock, int uid, int pid, String tag,WorkSource ws) {
- … …
- if (isScreenLock(flags)) {
- // if this causes a wakeup, we reactivate all of the locks and
- // set it to whatever they want. otherwise, we modulate that
- // by the current state so we never turn it more on than
- // it already is.
- if ((flags & LOCK_MASK) == PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK) {
- mProximityWakeLockCount++;
- if (mProximityWakeLockCount == 1) {
- enableProximityLockLocked();//打开距离感应函数
- }
- } else {
- if ((wl.flags & PowerManager.ACQUIRE_CAUSES_WAKEUP) != 0) {
- int oldWakeLockState = mWakeLockState;
- mWakeLockState = mLocks.reactivateScreenLocksLocked();
- // Disable proximity sensor if if user presses power key while we are in the
- // "waiting for proximity sensor to go negative" state.
- if ((mWakeLockState & SCREEN_ON_BIT) != 0
- && mProximitySensorActive && mProximityWakeLockCount == 0) {
- mProximitySensorActive = false;
- }
- if (mSpew) {
- Slog.d(TAG, "wakeup here mUserState=0x" + Integer.toHexString(mUserState)
- + " mWakeLockState=0x"
- + Integer.toHexString(mWakeLockState)
- + " previous wakeLockState=0x"
- + Integer.toHexString(oldWakeLockState));
- }
- } else {
- if (mSpew) {
- Slog.d(TAG, "here mUserState=0x" + Integer.toHexString(mUserState)
- + " mLocks.gatherState()=0x"
- + Integer.toHexString(mLocks.gatherState())
- + " mWakeLockState=0x" + Integer.toHexString(mWakeLockState));
- }
- mWakeLockState = (mUserState | mWakeLockState) & mLocks.gatherState();
- }
- setPowerState(mWakeLockState | mUserState);
- }
- }
- else if ((flags & LOCK_MASK) == PowerManager.PARTIAL_WAKE_LOCK) {
- if (newlock) {
- mPartialCount++;
- if (mPartialCount == 1) {
- if (LOG_PARTIAL_WL) EventLog.writeEvent(EventLogTags.POWER_PARTIAL_WAKE_STATE, 1, tag);
- }
- }
- Power.acquireWakeLock(Power.PARTIAL_WAKE_LOCK,PARTIAL_NAME);
- }
- 在函数中
- private void enableProximityLockLocked() {
- if (mDebugProximitySensor) {
- Slog.d(TAG, "enableProximityLockLocked");
- }
- if (!mProximitySensorEnabled) {
- // clear calling identity so sensor manager battery stats are accurate
- long identity = Binder.clearCallingIdentity();
- try {
- //注册监听器mProximityListener
- mSensorManager.registerListener(mProximityListener, mProximitySensor,
- SensorManager.SENSOR_DELAY_NORMAL);
- mProximitySensorEnabled = true;
- } finally {
- Binder.restoreCallingIdentity(identity);
- }
- }
- }
- 在函数中
- SensorEventListener mProximityListener = new SensorEventListener() {
- public void onSensorChanged(SensorEvent event) {
- long milliseconds = SystemClock.elapsedRealtime();
- synchronized (mLocks) {
- float distance = event.values[0];
- long timeSinceLastEvent = milliseconds - mLastProximityEventTime;
- mLastProximityEventTime = milliseconds;
- mHandler.removeCallbacks(mProximityTask);
- boolean proximityTaskQueued = false;
- // compare against getMaximumRange to support sensors that only return 0 or 1
- //比较接近距离,是否开启感应(0< distance < 5 cm&&)
- boolean active = (distance >= 0.0 && distance < PROXIMITY_THRESHOLD &&
- distance < mProximitySensor.getMaximumRange());
- if (mDebugProximitySensor) {
- Slog.d(TAG, "mProximityListener.onSensorChanged active: " + active);
- }
- if (timeSinceLastEvent < PROXIMITY_SENSOR_DELAY) {
- // enforce delaying atleast PROXIMITY_SENSOR_DELAY before processing
- mProximityPendingValue = (active ? 1 : 0);
- mHandler.postDelayed(mProximityTask, PROXIMITY_SENSOR_DELAY - timeSinceLastEvent);
- proximityTaskQueued = true;
- } else {
- // process the value immediately
- mProximityPendingValue = -1;
- proximityChangedLocked(active);//改变距离感应状态
- }
- // update mProximityPartialLock state
- boolean held = mProximityPartialLock.isHeld();
- if (!held && proximityTaskQueued) {
- // hold wakelock until mProximityTask runs
- mProximityPartialLock.acquire();
- } else if (held && !proximityTaskQueued) {
- mProximityPartialLock.release();
- }
- }
- }
- public void onAccuracyChanged(Sensor sensor, int accuracy) {
- // ignore
- }
- };
- 将会进入
- private void proximityChangedLocked(boolean active) {
- if (mDebugProximitySensor) {
- Slog.d(TAG, "proximityChangedLocked, active: " + active);
- }
- if (!mProximitySensorEnabled) {
- Slog.d(TAG, "Ignoring proximity change after sensor is disabled");
- return;
- }
- if (active) {
- if (mDebugProximitySensor) {
- Slog.d(TAG, "b mProxIgnoredBecauseScreenTurnedOff="
- + mProxIgnoredBecauseScreenTurnedOff);
- }
- if (!mProxIgnoredBecauseScreenTurnedOff) {
- //会进入此函数
- goToSleepLocked(SystemClock.uptimeMillis(),
- WindowManagerPolicy.OFF_BECAUSE_OF_PROX_SENSOR);
- }
- mProximitySensorActive = true;
- } else {
- // proximity sensor negative events trigger as user activity.
- // temporarily set mUserActivityAllowed to true so this will work
- // even when the keyguard is on.
- mProximitySensorActive = false;
- if (mDebugProximitySensor) {
- Slog.d(TAG, "b mProxIgnoredBecauseScreenTurnedOff="
- + mProxIgnoredBecauseScreenTurnedOff);
- }
- if (!mProxIgnoredBecauseScreenTurnedOff) {
- forceUserActivityLocked();
- }
- if (mProximityWakeLockCount == 0) {
- // disable sensor if we have no listeners left after proximity negative
- disableProximityLockLocked();
- }
- }
- }
- private void goToSleepLocked(long time, int reason) {
- if (mLastEventTime <= time) {
- mLastEventTime = time;
- // cancel all of the wake locks
- mWakeLockState = SCREEN_OFF;
- int N = mLocks.size();
- int numCleared = 0;
- boolean proxLock = false;
- for (int i=0; i<N; i++) {
- WakeLock wl = mLocks.get(i);
- if (isScreenLock(wl.flags)) {
- if (((wl.flags & LOCK_MASK) == PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK)
- && reason == WindowManagerPolicy.OFF_BECAUSE_OF_PROX_SENSOR) {
- proxLock = true;
- } else {
- mLocks.get(i).activated = false;
- numCleared++;
- }
- }
- }
- if (!proxLock) {
- mProxIgnoredBecauseScreenTurnedOff = true;
- if (mDebugProximitySensor) {
- Slog.d(TAG, "setting mProxIgnoredBecauseScreenTurnedOff");
- }
- }
- EventLog.writeEvent(EventLogTags.POWER_SLEEP_REQUESTED, numCleared);
- mStillNeedSleepNotification = true;
- mUserState = SCREEN_OFF;
- //设置供电状态
- setPowerState(SCREEN_OFF, false, reason);
- cancelTimerLocked();
- }
- }
上述阶段是指LCD背光开灭状态控制。
下面来分析最后一个阶段PhoneApp如何调用。
- 在OnCreate()中
- // Wake lock used to control proximity sensor behavior.
- if ((pm.getSupportedWakeLockFlags()
- & PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK) != 0x0) {
- mProximityWakeLock =
- pm.newWakeLock(PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK, LOG_TAG);
- }
- if (DBG) Log.d(LOG_TAG, "onCreate: mProximityWakeLock: " + mProximityWakeLock);
- // create mAccelerometerListener only if we are using the proximity sensor
- if (proximitySensorModeEnabled()) {
- mAccelerometerListener = new AccelerometerListener(this, this);
- }
- /* package */ void setBeginningCall(boolean beginning) {
- // Note that we are beginning a new call, for proximity sensor support
- mBeginningCall = beginning;
- // Update the Proximity sensor based on mBeginningCall state
- //更新距离感应状态
- updateProximitySensorMode(mCM.getState());
- }
- /* package */ void updateProximitySensorMode(Phone.State state) {
- if (VDBG) Log.d(LOG_TAG, "updateProximitySensorMode: state = " + state);
- if (proximitySensorModeEnabled()) {
- synchronized (mProximityWakeLock) {
- // turn proximity sensor off and turn screen on immediately if
- // we are using a headset, the keyboard is open, or the device
- // is being held in a horizontal position.
- boolean screenOnImmediately = (isHeadsetPlugged()
- || PhoneUtils.isSpeakerOn(this)
- || ((mBtHandsfree != null) && mBtHandsfree.isAudioOn())
- || mIsHardKeyboardOpen);
- // We do not keep the screen off when we are horizontal, but we do not force it
- // on when we become horizontal until the proximity sensor goes negative.
- // boolean horizontal = (mOrientation == AccelerometerListener.ORIENTATION_HORIZONTAL);
- // && !horizontal
- if ((((!PhoneUtils.isVideoCall()) && (state == Phone.State.OFFHOOK)) || mBeginningCall) && !screenOnImmediately ) {
- // Phone is in use! Arrange for the screen to turn off
- // automatically when the sensor detects a close object.
- if (!mProximityWakeLock.isHeld()) {
- if (DBG) Log.d(LOG_TAG, "updateProximitySensorMode: acquiring...");
- //注意此函数
- mProximityWakeLock.acquire();
- } else {
- if (VDBG) Log.d(LOG_TAG, "updateProximitySensorMode: lock already held.");
- }
- } else {
- // Phone is either idle, or ringing. We don't want any
- // special proximity sensor behavior in either case.
- if (mProximityWakeLock.isHeld()) {
- if (DBG) Log.d(LOG_TAG, "updateProximitySensorMode: releasing...");
- // Wait until user has moved the phone away from his head if we are
- // releasing due to the phone call ending.
- // Qtherwise, turn screen on immediately
- int flags =
- (screenOnImmediately ? 0 : PowerManager.WAIT_FOR_PROXIMITY_NEGATIVE);
- mProximityWakeLock.release(flags);
- } else {
- if (VDBG) {
- Log.d(LOG_TAG, "updateProximitySensorMode: lock already released.");
- }
- }
- }
- }
- }
- }
- mProximityWakeLock.acquire();将调用PowerManagerService.java中的 public void acquire() {
- if (!mRefCounted || mCount++ == 0) {
- long ident = Binder.clearCallingIdentity();
- try {
- PowerManagerService.this.acquireWakeLockLocked(mFlags, mToken,
- MY_UID, MY_PID, mTag, null);
- mHeld = true;
- } finally {
- Binder.restoreCallingIdentity(ident);
- }
- }
- }
- 然后调用
- public void acquireWakeLockLocked(int flags, IBinder lock, int uid, int pid, String tag,
- WorkSource ws) {
- … …
- if (isScreenLock(flags)) {
- // if this causes a wakeup, we reactivate all of the locks and
- // set it to whatever they want. otherwise, we modulate that
- // by the current state so we never turn it more on than
- // it already is.
- if ((flags & LOCK_MASK) == PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK) {
- mProximityWakeLockCount++;
- if (mProximityWakeLockCount == 1) {
- enableProximityLockLocked();
- }
- } else {
- if ((wl.flags & PowerManager.ACQUIRE_CAUSES_WAKEUP) != 0) {
- int oldWakeLockState = mWakeLockState;
- mWakeLockState = mLocks.reactivateScreenLocksLocked();
- if (mSpew) {
- Slog.d(TAG, "wakeup here mUserState=0x" + Integer.toHexString(mUserState)
- + " mWakeLockState=0x"
- + Integer.toHexString(mWakeLockState)
- + " previous wakeLockState=0x"
- + Integer.toHexString(oldWakeLockState));
- }
- } else {
- if (mSpew) {
- Slog.d(TAG, "here mUserState=0x" + Integer.toHexString(mUserState)
- + " mLocks.gatherState()=0x"
- + Integer.toHexString(mLocks.gatherState())
- + " mWakeLockState=0x" + Integer.toHexString(mWakeLockState));
- }
- mWakeLockState = (mUserState | mWakeLockState) & mLocks.gatherState();
- }
- setPowerState(mWakeLockState | mUserState);
- }
- }
- else if ((flags & LOCK_MASK) == PowerManager.PARTIAL_WAKE_LOCK) {
- if (newlock) {
- mPartialCount++;
- if (mPartialCount == 1) {
- if (LOG_PARTIAL_WL) EventLog.writeEvent(EventLogTags.POWER_PARTIAL_WAKE_STATE, 1, tag);
- }
- }
- Power.acquireWakeLock(Power.PARTIAL_WAKE_LOCK,PARTIAL_NAME);
- }
- … …
- }