blob: de0321db67331cd04a3bc432102bcd8e36a0bf7f [file] [log] [blame]
Mathias Agopianf001c922010-11-11 17:58:51 -08001/*
2 * Copyright (C) 2010 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
Mathias Agopianf001c922010-11-11 17:58:51 -080017
Steven Morelandd3335112016-12-20 11:14:50 -080018#include "SensorDevice.h"
19#include "SensorService.h"
20
Steven Morelandd3335112016-12-20 11:14:50 -080021
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +000022#include <binder/BinderService.h>
23#include <binder/Parcel.h>
24#include <binder/IServiceManager.h>
25#include <cutils/ashmem.h>
26#include <hardware/sensors.h>
27#include <utils/Atomic.h>
28#include <utils/Errors.h>
29#include <utils/Singleton.h>
Steven Morelandd3335112016-12-20 11:14:50 -080030
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +000031#include <inttypes.h>
32#include <math.h>
33#include <sys/mman.h>
34#include <stdint.h>
35#include <sys/types.h>
36#include <sstream>
37#include <unistd.h>
Mathias Agopianf001c922010-11-11 17:58:51 -080038
39namespace android {
40// ---------------------------------------------------------------------------
Mathias Agopianf001c922010-11-11 17:58:51 -080041
42ANDROID_SINGLETON_STATIC_INSTANCE(SensorDevice)
43
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +000044SensorDevice::SensorDevice()
45 : mSensorDevice(0),
46 mSensorModule(0) {
47 status_t err = hw_get_module(SENSORS_HARDWARE_MODULE_ID,
48 (hw_module_t const**)&mSensorModule);
49
50 ALOGE_IF(err, "couldn't load %s module (%s)",
51 SENSORS_HARDWARE_MODULE_ID, strerror(-err));
52
53 if (mSensorModule) {
54 err = sensors_open_1(&mSensorModule->common, &mSensorDevice);
55
56 ALOGE_IF(err, "couldn't open device for module %s (%s)",
57 SENSORS_HARDWARE_MODULE_ID, strerror(-err));
58
59 if (mSensorDevice) {
60
61 sensor_t const* list;
62 ssize_t count = mSensorModule->get_sensors_list(mSensorModule, &list);
63
64 if (mSensorDevice->common.version < SENSORS_DEVICE_API_VERSION_1_3) {
65 ALOGE(">>>> WARNING <<< Upgrade sensor HAL to version 1_3, ignoring sensors reported by this device");
66 count = 0;
67 }
68
69 mActivationCount.setCapacity(count);
70 Info model;
71 for (size_t i=0 ; i<size_t(count) ; i++) {
72 mActivationCount.add(list[i].handle, model);
73 mSensorDevice->activate(
74 reinterpret_cast<struct sensors_poll_device_t *>(mSensorDevice),
75 list[i].handle, 0);
76 }
77 }
Mathias Agopianf001c922010-11-11 17:58:51 -080078 }
79}
80
Peng Xu2576cb62016-01-20 00:22:09 -080081void SensorDevice::handleDynamicSensorConnection(int handle, bool connected) {
82 if (connected) {
83 Info model;
84 mActivationCount.add(handle, model);
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +000085 mSensorDevice->activate(
86 reinterpret_cast<struct sensors_poll_device_t *>(mSensorDevice), handle, 0);
Peng Xu2576cb62016-01-20 00:22:09 -080087 } else {
88 mActivationCount.removeItem(handle);
89 }
90}
91
Peng Xu6a2d3a02015-12-21 12:00:23 -080092std::string SensorDevice::dump() const {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +000093 if (!mSensorModule) return "HAL not initialized\n";
Mathias Agopianf001c922010-11-11 17:58:51 -080094
Peng Xu6a2d3a02015-12-21 12:00:23 -080095 String8 result;
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +000096 sensor_t const* list;
97 int count = mSensorModule->get_sensors_list(mSensorModule, &list);
Peng Xu6a2d3a02015-12-21 12:00:23 -080098
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +000099 result.appendFormat("HAL: %s (%s), version %#010x\n",
100 mSensorModule->common.name,
101 mSensorModule->common.author,
102 getHalDeviceVersion());
103 result.appendFormat("Total %d h/w sensors, %zu running:\n", count, mActivationCount.size());
Mathias Agopianf001c922010-11-11 17:58:51 -0800104
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000105 Mutex::Autolock _l(mLock);
106 for (int i = 0 ; i < count ; i++) {
107 const Info& info = mActivationCount.valueFor(list[i].handle);
108 if (info.batchParams.isEmpty()) continue;
109 result.appendFormat("0x%08x) active-count = %zu; ", list[i].handle,
110 info.batchParams.size());
Peng Xu6a2d3a02015-12-21 12:00:23 -0800111
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000112 result.append("sampling_period(ms) = {");
113 for (size_t j = 0; j < info.batchParams.size(); j++) {
114 const BatchParams& params = info.batchParams.valueAt(j);
115 result.appendFormat("%.1f%s", params.batchDelay / 1e6f,
116 j < info.batchParams.size() - 1 ? ", " : "");
117 }
118 result.appendFormat("}, selected = %.1f ms; ", info.bestBatchParams.batchDelay / 1e6f);
Aravind Akella724d91d2013-06-27 12:04:23 -0700119
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000120 result.append("batching_period(ms) = {");
121 for (size_t j = 0; j < info.batchParams.size(); j++) {
122 BatchParams params = info.batchParams.valueAt(j);
123 result.appendFormat("%.1f%s", params.batchTimeout / 1e6f,
124 j < info.batchParams.size() - 1 ? ", " : "");
125 }
126 result.appendFormat("}, selected = %.1f ms\n", info.bestBatchParams.batchTimeout / 1e6f);
127 }
Peng Xu6a2d3a02015-12-21 12:00:23 -0800128 return result.string();
Mathias Agopianf001c922010-11-11 17:58:51 -0800129}
130
131ssize_t SensorDevice::getSensorList(sensor_t const** list) {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000132 if (!mSensorModule) return NO_INIT;
133 ssize_t count = mSensorModule->get_sensors_list(mSensorModule, list);
134 return count;
Mathias Agopianf001c922010-11-11 17:58:51 -0800135}
136
137status_t SensorDevice::initCheck() const {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000138 return mSensorDevice && mSensorModule ? NO_ERROR : NO_INIT;
Mathias Agopianf001c922010-11-11 17:58:51 -0800139}
140
141ssize_t SensorDevice::poll(sensors_event_t* buffer, size_t count) {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000142 if (!mSensorDevice) return NO_INIT;
143 ssize_t c;
144 do {
145 c = mSensorDevice->poll(reinterpret_cast<struct sensors_poll_device_t *> (mSensorDevice),
146 buffer, count);
147 } while (c == -EINTR);
148 return c;
Mathias Agopianf001c922010-11-11 17:58:51 -0800149}
150
Mathias Agopianac9a96d2013-07-12 02:01:16 -0700151void SensorDevice::autoDisable(void *ident, int handle) {
152 Info& info( mActivationCount.editValueFor(handle) );
Jaikumar Ganesh4c01b1a2013-04-16 15:52:23 -0700153 Mutex::Autolock _l(mLock);
Aravind Akella724d91d2013-06-27 12:04:23 -0700154 info.removeBatchParamsForIdent(ident);
Jaikumar Ganesh4c01b1a2013-04-16 15:52:23 -0700155}
156
Peng Xu6a2d3a02015-12-21 12:00:23 -0800157status_t SensorDevice::activate(void* ident, int handle, int enabled) {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000158 if (!mSensorDevice) return NO_INIT;
Mathias Agopianf001c922010-11-11 17:58:51 -0800159 status_t err(NO_ERROR);
160 bool actuateHardware = false;
161
Aravind Akella724d91d2013-06-27 12:04:23 -0700162 Mutex::Autolock _l(mLock);
Mathias Agopianf001c922010-11-11 17:58:51 -0800163 Info& info( mActivationCount.editValueFor(handle) );
Mathias Agopiana1b7db92011-05-27 16:23:58 -0700164
Steve Blocka5512372011-12-20 16:23:08 +0000165 ALOGD_IF(DEBUG_CONNECTIONS,
Mark Salyzyndb458612014-06-10 14:50:02 -0700166 "SensorDevice::activate: ident=%p, handle=0x%08x, enabled=%d, count=%zu",
Aravind Akella724d91d2013-06-27 12:04:23 -0700167 ident, handle, enabled, info.batchParams.size());
Mathias Agopiana1b7db92011-05-27 16:23:58 -0700168
Mathias Agopianf001c922010-11-11 17:58:51 -0800169 if (enabled) {
Mark Salyzyndb458612014-06-10 14:50:02 -0700170 ALOGD_IF(DEBUG_CONNECTIONS, "enable index=%zd", info.batchParams.indexOfKey(ident));
Mathias Agopiana1b7db92011-05-27 16:23:58 -0700171
Aravind Akella4949c502015-02-11 15:54:35 -0800172 if (isClientDisabledLocked(ident)) {
Peng Xu966fa882016-09-01 16:13:15 -0700173 ALOGE("SensorDevice::activate, isClientDisabledLocked(%p):true, handle:%d",
174 ident, handle);
Aravind Akella4949c502015-02-11 15:54:35 -0800175 return INVALID_OPERATION;
176 }
177
Aravind Akella724d91d2013-06-27 12:04:23 -0700178 if (info.batchParams.indexOfKey(ident) >= 0) {
Aravind Akella4949c502015-02-11 15:54:35 -0800179 if (info.numActiveClients() == 1) {
Aravind Akella724d91d2013-06-27 12:04:23 -0700180 // This is the first connection, we need to activate the underlying h/w sensor.
181 actuateHardware = true;
182 }
Mathias Agopian50b66762010-11-29 17:26:51 -0800183 } else {
Aravind Akella724d91d2013-06-27 12:04:23 -0700184 // Log error. Every activate call should be preceded by a batch() call.
185 ALOGE("\t >>>ERROR: activate called without batch");
Mathias Agopianf001c922010-11-11 17:58:51 -0800186 }
187 } else {
Mark Salyzyndb458612014-06-10 14:50:02 -0700188 ALOGD_IF(DEBUG_CONNECTIONS, "disable index=%zd", info.batchParams.indexOfKey(ident));
Mathias Agopiana1b7db92011-05-27 16:23:58 -0700189
Aravind Akella724d91d2013-06-27 12:04:23 -0700190 if (info.removeBatchParamsForIdent(ident) >= 0) {
Aravind Akella4949c502015-02-11 15:54:35 -0800191 if (info.numActiveClients() == 0) {
Aravind Akella724d91d2013-06-27 12:04:23 -0700192 // This is the last connection, we need to de-activate the underlying h/w sensor.
Mathias Agopian50b66762010-11-29 17:26:51 -0800193 actuateHardware = true;
Aravind Akella724d91d2013-06-27 12:04:23 -0700194 } else {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000195 const int halVersion = getHalDeviceVersion();
196 if (halVersion >= SENSORS_DEVICE_API_VERSION_1_1) {
197 // Call batch for this sensor with the previously calculated best effort
198 // batch_rate and timeout. One of the apps has unregistered for sensor
199 // events, and the best effort batch parameters might have changed.
200 ALOGD_IF(DEBUG_CONNECTIONS,
201 "\t>>> actuating h/w batch %d %d %" PRId64 " %" PRId64, handle,
202 info.bestBatchParams.flags, info.bestBatchParams.batchDelay,
203 info.bestBatchParams.batchTimeout);
204 mSensorDevice->batch(mSensorDevice, handle,info.bestBatchParams.flags,
205 info.bestBatchParams.batchDelay,
206 info.bestBatchParams.batchTimeout);
207 }
Mathias Agopian50b66762010-11-29 17:26:51 -0800208 }
209 } else {
210 // sensor wasn't enabled for this ident
211 }
Aravind Akella4949c502015-02-11 15:54:35 -0800212
213 if (isClientDisabledLocked(ident)) {
214 return NO_ERROR;
215 }
Mathias Agopianf001c922010-11-11 17:58:51 -0800216 }
Mathias Agopian50b66762010-11-29 17:26:51 -0800217
Mathias Agopianf001c922010-11-11 17:58:51 -0800218 if (actuateHardware) {
Aravind Akella4949c502015-02-11 15:54:35 -0800219 ALOGD_IF(DEBUG_CONNECTIONS, "\t>>> actuating h/w activate handle=%d enabled=%d", handle,
220 enabled);
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000221 err = mSensorDevice->activate(
222 reinterpret_cast<struct sensors_poll_device_t *> (mSensorDevice), handle, enabled);
Aravind Akella724d91d2013-06-27 12:04:23 -0700223 ALOGE_IF(err, "Error %s sensor %d (%s)", enabled ? "activating" : "disabling", handle,
224 strerror(-err));
Mathias Agopiana1b7db92011-05-27 16:23:58 -0700225
Aravind Akella724d91d2013-06-27 12:04:23 -0700226 if (err != NO_ERROR && enabled) {
227 // Failure when enabling the sensor. Clean up on failure.
228 info.removeBatchParamsForIdent(ident);
Mathias Agopianac9a96d2013-07-12 02:01:16 -0700229 }
Mathias Agopianf001c922010-11-11 17:58:51 -0800230 }
231
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000232 // On older devices which do not support batch, call setDelay().
233 if (getHalDeviceVersion() < SENSORS_DEVICE_API_VERSION_1_1 && info.numActiveClients() > 0) {
234 ALOGD_IF(DEBUG_CONNECTIONS, "\t>>> actuating h/w setDelay %d %" PRId64, handle,
235 info.bestBatchParams.batchDelay);
236 mSensorDevice->setDelay(
237 reinterpret_cast<struct sensors_poll_device_t *>(mSensorDevice),
238 handle, info.bestBatchParams.batchDelay);
239 }
Mathias Agopianf001c922010-11-11 17:58:51 -0800240 return err;
241}
242
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000243status_t SensorDevice::batch(void* ident, int handle, int flags, int64_t samplingPeriodNs,
244 int64_t maxBatchReportLatencyNs) {
245 if (!mSensorDevice) return NO_INIT;
Aravind Akella724d91d2013-06-27 12:04:23 -0700246
247 if (samplingPeriodNs < MINIMUM_EVENTS_PERIOD) {
248 samplingPeriodNs = MINIMUM_EVENTS_PERIOD;
249 }
250
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000251 const int halVersion = getHalDeviceVersion();
252 if (halVersion < SENSORS_DEVICE_API_VERSION_1_1 && maxBatchReportLatencyNs != 0) {
253 // Batch is not supported on older devices return invalid operation.
254 return INVALID_OPERATION;
255 }
256
Aravind Akella724d91d2013-06-27 12:04:23 -0700257 ALOGD_IF(DEBUG_CONNECTIONS,
Mark Salyzyndb458612014-06-10 14:50:02 -0700258 "SensorDevice::batch: ident=%p, handle=0x%08x, flags=%d, period_ns=%" PRId64 " timeout=%" PRId64,
Aravind Akella724d91d2013-06-27 12:04:23 -0700259 ident, handle, flags, samplingPeriodNs, maxBatchReportLatencyNs);
260
261 Mutex::Autolock _l(mLock);
262 Info& info(mActivationCount.editValueFor(handle));
263
264 if (info.batchParams.indexOfKey(ident) < 0) {
265 BatchParams params(flags, samplingPeriodNs, maxBatchReportLatencyNs);
266 info.batchParams.add(ident, params);
267 } else {
268 // A batch has already been called with this ident. Update the batch parameters.
269 info.setBatchParamsForIdent(ident, flags, samplingPeriodNs, maxBatchReportLatencyNs);
270 }
271
272 BatchParams prevBestBatchParams = info.bestBatchParams;
273 // Find the minimum of all timeouts and batch_rates for this sensor.
274 info.selectBatchParams();
275
276 ALOGD_IF(DEBUG_CONNECTIONS,
Mark Salyzyndb458612014-06-10 14:50:02 -0700277 "\t>>> curr_period=%" PRId64 " min_period=%" PRId64
278 " curr_timeout=%" PRId64 " min_timeout=%" PRId64,
Aravind Akella724d91d2013-06-27 12:04:23 -0700279 prevBestBatchParams.batchDelay, info.bestBatchParams.batchDelay,
280 prevBestBatchParams.batchTimeout, info.bestBatchParams.batchTimeout);
281
282 status_t err(NO_ERROR);
283 // If the min period or min timeout has changed since the last batch call, call batch.
284 if (prevBestBatchParams != info.bestBatchParams) {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000285 if (halVersion >= SENSORS_DEVICE_API_VERSION_1_1) {
286 ALOGD_IF(DEBUG_CONNECTIONS, "\t>>> actuating h/w BATCH %d %d %" PRId64 " %" PRId64, handle,
287 info.bestBatchParams.flags, info.bestBatchParams.batchDelay,
288 info.bestBatchParams.batchTimeout);
289 err = mSensorDevice->batch(mSensorDevice, handle, info.bestBatchParams.flags,
290 info.bestBatchParams.batchDelay,
291 info.bestBatchParams.batchTimeout);
292 } else {
293 // For older devices which do not support batch, call setDelay() after activate() is
294 // called. Some older devices may not support calling setDelay before activate(), so
295 // call setDelay in SensorDevice::activate() method.
296 }
Aravind Akella724d91d2013-06-27 12:04:23 -0700297 if (err != NO_ERROR) {
Mark Salyzyndb458612014-06-10 14:50:02 -0700298 ALOGE("sensor batch failed %p %d %d %" PRId64 " %" PRId64 " err=%s",
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000299 mSensorDevice, handle,
Aravind Akella724d91d2013-06-27 12:04:23 -0700300 info.bestBatchParams.flags, info.bestBatchParams.batchDelay,
301 info.bestBatchParams.batchTimeout, strerror(-err));
302 info.removeBatchParamsForIdent(ident);
303 }
304 }
305 return err;
306}
307
Peng Xu6a2d3a02015-12-21 12:00:23 -0800308status_t SensorDevice::setDelay(void* ident, int handle, int64_t samplingPeriodNs) {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000309 if (!mSensorDevice) return NO_INIT;
Aravind Akella724d91d2013-06-27 12:04:23 -0700310 if (samplingPeriodNs < MINIMUM_EVENTS_PERIOD) {
311 samplingPeriodNs = MINIMUM_EVENTS_PERIOD;
312 }
Mathias Agopian667102f2011-09-14 16:43:34 -0700313 Mutex::Autolock _l(mLock);
Aravind Akella4949c502015-02-11 15:54:35 -0800314 if (isClientDisabledLocked(ident)) return INVALID_OPERATION;
Mathias Agopianf001c922010-11-11 17:58:51 -0800315 Info& info( mActivationCount.editValueFor(handle) );
Aravind Akella724d91d2013-06-27 12:04:23 -0700316 // If the underlying sensor is NOT in continuous mode, setDelay() should return an error.
317 // Calling setDelay() in batch mode is an invalid operation.
318 if (info.bestBatchParams.batchTimeout != 0) {
319 return INVALID_OPERATION;
320 }
321 ssize_t index = info.batchParams.indexOfKey(ident);
322 if (index < 0) {
323 return BAD_INDEX;
324 }
325 BatchParams& params = info.batchParams.editValueAt(index);
326 params.batchDelay = samplingPeriodNs;
327 info.selectBatchParams();
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000328 return mSensorDevice->setDelay(reinterpret_cast<struct sensors_poll_device_t *>(mSensorDevice),
329 handle, info.bestBatchParams.batchDelay);
Mathias Agopian667102f2011-09-14 16:43:34 -0700330}
331
Jaikumar Ganesh4342fdf2013-04-08 16:43:12 -0700332int SensorDevice::getHalDeviceVersion() const {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000333 if (!mSensorDevice) return -1;
334 return mSensorDevice->common.version;
Jaikumar Ganesh4342fdf2013-04-08 16:43:12 -0700335}
336
Aravind Akella9a844cf2014-02-11 18:58:52 -0800337status_t SensorDevice::flush(void* ident, int handle) {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000338 if (getHalDeviceVersion() < SENSORS_DEVICE_API_VERSION_1_1) {
339 return INVALID_OPERATION;
340 }
Aravind Akella4949c502015-02-11 15:54:35 -0800341 if (isClientDisabled(ident)) return INVALID_OPERATION;
Aravind Akella724d91d2013-06-27 12:04:23 -0700342 ALOGD_IF(DEBUG_CONNECTIONS, "\t>>> actuating h/w flush %d", handle);
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000343 return mSensorDevice->flush(mSensorDevice, handle);
Aravind Akella724d91d2013-06-27 12:04:23 -0700344}
345
Aravind Akella4949c502015-02-11 15:54:35 -0800346bool SensorDevice::isClientDisabled(void* ident) {
347 Mutex::Autolock _l(mLock);
348 return isClientDisabledLocked(ident);
349}
350
351bool SensorDevice::isClientDisabledLocked(void* ident) {
352 return mDisabledClients.indexOf(ident) >= 0;
353}
354
355void SensorDevice::enableAllSensors() {
356 Mutex::Autolock _l(mLock);
357 mDisabledClients.clear();
Peng Xu966fa882016-09-01 16:13:15 -0700358 ALOGI("cleared mDisabledClients");
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000359 const int halVersion = getHalDeviceVersion();
Aravind Akella4949c502015-02-11 15:54:35 -0800360 for (size_t i = 0; i< mActivationCount.size(); ++i) {
361 Info& info = mActivationCount.editValueAt(i);
362 if (info.batchParams.isEmpty()) continue;
363 info.selectBatchParams();
364 const int sensor_handle = mActivationCount.keyAt(i);
365 ALOGD_IF(DEBUG_CONNECTIONS, "\t>> reenable actuating h/w sensor enable handle=%d ",
366 sensor_handle);
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000367 status_t err(NO_ERROR);
368 if (halVersion > SENSORS_DEVICE_API_VERSION_1_0) {
369 err = mSensorDevice->batch(mSensorDevice, sensor_handle,
370 info.bestBatchParams.flags, info.bestBatchParams.batchDelay,
371 info.bestBatchParams.batchTimeout);
372 ALOGE_IF(err, "Error calling batch on sensor %d (%s)", sensor_handle, strerror(-err));
373 }
Aravind Akella4949c502015-02-11 15:54:35 -0800374
375 if (err == NO_ERROR) {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000376 err = mSensorDevice->activate(
377 reinterpret_cast<struct sensors_poll_device_t *>(mSensorDevice),
378 sensor_handle, 1);
Aravind Akella4949c502015-02-11 15:54:35 -0800379 ALOGE_IF(err, "Error activating sensor %d (%s)", sensor_handle, strerror(-err));
380 }
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000381
382 if (halVersion <= SENSORS_DEVICE_API_VERSION_1_0) {
383 err = mSensorDevice->setDelay(
384 reinterpret_cast<struct sensors_poll_device_t *>(mSensorDevice),
385 sensor_handle, info.bestBatchParams.batchDelay);
386 ALOGE_IF(err, "Error calling setDelay sensor %d (%s)", sensor_handle, strerror(-err));
387 }
Aravind Akella4949c502015-02-11 15:54:35 -0800388 }
389}
390
391void SensorDevice::disableAllSensors() {
392 Mutex::Autolock _l(mLock);
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000393 for (size_t i = 0; i< mActivationCount.size(); ++i) {
Aravind Akella4949c502015-02-11 15:54:35 -0800394 const Info& info = mActivationCount.valueAt(i);
395 // Check if this sensor has been activated previously and disable it.
396 if (info.batchParams.size() > 0) {
397 const int sensor_handle = mActivationCount.keyAt(i);
398 ALOGD_IF(DEBUG_CONNECTIONS, "\t>> actuating h/w sensor disable handle=%d ",
399 sensor_handle);
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000400 mSensorDevice->activate(
401 reinterpret_cast<struct sensors_poll_device_t *> (mSensorDevice),
402 sensor_handle, 0);
Aravind Akella4949c502015-02-11 15:54:35 -0800403 // Add all the connections that were registered for this sensor to the disabled
404 // clients list.
Svetoslavb412f6e2015-04-29 16:50:41 -0700405 for (size_t j = 0; j < info.batchParams.size(); ++j) {
Aravind Akella4949c502015-02-11 15:54:35 -0800406 mDisabledClients.add(info.batchParams.keyAt(j));
Peng Xu966fa882016-09-01 16:13:15 -0700407 ALOGI("added %p to mDisabledClients", info.batchParams.keyAt(j));
Aravind Akella4949c502015-02-11 15:54:35 -0800408 }
409 }
410 }
411}
412
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000413status_t SensorDevice::injectSensorData(const sensors_event_t *injected_sensor_event) {
414 ALOGD_IF(DEBUG_CONNECTIONS,
415 "sensor_event handle=%d ts=%" PRId64 " data=%.2f, %.2f, %.2f %.2f %.2f %.2f",
416 injected_sensor_event->sensor,
417 injected_sensor_event->timestamp, injected_sensor_event->data[0],
418 injected_sensor_event->data[1], injected_sensor_event->data[2],
419 injected_sensor_event->data[3], injected_sensor_event->data[4],
420 injected_sensor_event->data[5]);
421 if (getHalDeviceVersion() < SENSORS_DEVICE_API_VERSION_1_4) {
422 return INVALID_OPERATION;
423 }
424 return mSensorDevice->inject_sensor_data(mSensorDevice, injected_sensor_event);
Aravind Akellaa9e6cc32015-04-16 18:57:31 -0700425}
426
427status_t SensorDevice::setMode(uint32_t mode) {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000428 if (getHalDeviceVersion() < SENSORS_DEVICE_API_VERSION_1_4) {
429 return INVALID_OPERATION;
430 }
431 return mSensorModule->set_operation_mode(mode);
Aravind Akellaa9e6cc32015-04-16 18:57:31 -0700432}
433
Mathias Agopian667102f2011-09-14 16:43:34 -0700434// ---------------------------------------------------------------------------
435
Aravind Akella4949c502015-02-11 15:54:35 -0800436int SensorDevice::Info::numActiveClients() {
437 SensorDevice& device(SensorDevice::getInstance());
438 int num = 0;
439 for (size_t i = 0; i < batchParams.size(); ++i) {
440 if (!device.isClientDisabledLocked(batchParams.keyAt(i))) {
441 ++num;
442 }
443 }
444 return num;
445}
446
Aravind Akella724d91d2013-06-27 12:04:23 -0700447status_t SensorDevice::Info::setBatchParamsForIdent(void* ident, int flags,
448 int64_t samplingPeriodNs,
449 int64_t maxBatchReportLatencyNs) {
450 ssize_t index = batchParams.indexOfKey(ident);
Mathias Agopian667102f2011-09-14 16:43:34 -0700451 if (index < 0) {
Mark Salyzyndb458612014-06-10 14:50:02 -0700452 ALOGE("Info::setBatchParamsForIdent(ident=%p, period_ns=%" PRId64 " timeout=%" PRId64 ") failed (%s)",
Aravind Akella724d91d2013-06-27 12:04:23 -0700453 ident, samplingPeriodNs, maxBatchReportLatencyNs, strerror(-index));
Mathias Agopian667102f2011-09-14 16:43:34 -0700454 return BAD_INDEX;
455 }
Aravind Akella724d91d2013-06-27 12:04:23 -0700456 BatchParams& params = batchParams.editValueAt(index);
457 params.flags = flags;
458 params.batchDelay = samplingPeriodNs;
459 params.batchTimeout = maxBatchReportLatencyNs;
Mathias Agopian667102f2011-09-14 16:43:34 -0700460 return NO_ERROR;
461}
462
Aravind Akella724d91d2013-06-27 12:04:23 -0700463void SensorDevice::Info::selectBatchParams() {
Aravind Akella4949c502015-02-11 15:54:35 -0800464 BatchParams bestParams(0, -1, -1);
465 SensorDevice& device(SensorDevice::getInstance());
Aravind Akella724d91d2013-06-27 12:04:23 -0700466
Aravind Akella4949c502015-02-11 15:54:35 -0800467 for (size_t i = 0; i < batchParams.size(); ++i) {
468 if (device.isClientDisabledLocked(batchParams.keyAt(i))) continue;
Aravind Akella724d91d2013-06-27 12:04:23 -0700469 BatchParams params = batchParams.valueAt(i);
Aravind Akella4949c502015-02-11 15:54:35 -0800470 if (bestParams.batchDelay == -1 || params.batchDelay < bestParams.batchDelay) {
Aravind Akella724d91d2013-06-27 12:04:23 -0700471 bestParams.batchDelay = params.batchDelay;
472 }
Aravind Akella4949c502015-02-11 15:54:35 -0800473 if (bestParams.batchTimeout == -1 || params.batchTimeout < bestParams.batchTimeout) {
Aravind Akella724d91d2013-06-27 12:04:23 -0700474 bestParams.batchTimeout = params.batchTimeout;
Mathias Agopianf001c922010-11-11 17:58:51 -0800475 }
476 }
Aravind Akella724d91d2013-06-27 12:04:23 -0700477 bestBatchParams = bestParams;
478}
479
480ssize_t SensorDevice::Info::removeBatchParamsForIdent(void* ident) {
481 ssize_t idx = batchParams.removeItem(ident);
482 if (idx >= 0) {
483 selectBatchParams();
484 }
485 return idx;
Mathias Agopianf001c922010-11-11 17:58:51 -0800486}
487
Peng Xu4f707f82016-09-26 11:28:32 -0700488void SensorDevice::notifyConnectionDestroyed(void* ident) {
489 Mutex::Autolock _l(mLock);
490 mDisabledClients.remove(ident);
491}
492
Peng Xue36e3472016-11-03 11:57:10 -0700493int32_t SensorDevice::registerDirectChannel(const sensors_direct_mem_t* memory) {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000494
495 if (!isDirectReportSupported()) {
496 return INVALID_OPERATION;
497 }
498
Peng Xue36e3472016-11-03 11:57:10 -0700499 Mutex::Autolock _l(mLock);
500
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000501 int32_t channelHandle = mSensorDevice->register_direct_channel(
502 mSensorDevice, memory, -1 /*channel_handle*/);
503 return channelHandle;
Peng Xue36e3472016-11-03 11:57:10 -0700504}
505
506void SensorDevice::unregisterDirectChannel(int32_t channelHandle) {
507 Mutex::Autolock _l(mLock);
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000508
509 mSensorDevice->register_direct_channel(mSensorDevice, nullptr, channelHandle);
Peng Xue36e3472016-11-03 11:57:10 -0700510}
511
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000512int32_t SensorDevice::configureDirectChannel(int32_t sensorHandle, int32_t channelHandle,
513 const struct sensors_direct_cfg_t *config) {
Peng Xue36e3472016-11-03 11:57:10 -0700514
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000515 if (!isDirectReportSupported()) {
516 return INVALID_OPERATION;
Steven Morelandd3335112016-12-20 11:14:50 -0800517 }
518
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000519 Mutex::Autolock _l(mLock);
Steven Morelandd3335112016-12-20 11:14:50 -0800520
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000521 int32_t ret = mSensorDevice->config_direct_report(
522 mSensorDevice, sensorHandle, channelHandle, config);
523 ALOGE_IF(ret < 0, "SensorDevice::configureDirectChannel ret %d", ret);
Peng Xue36e3472016-11-03 11:57:10 -0700524 return ret;
525}
Peng Xu53632542017-01-23 20:06:27 -0800526
527bool SensorDevice::isDirectReportSupported() const {
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000528 bool ret = mSensorDevice->register_direct_channel != nullptr
529 && mSensorDevice->config_direct_report != nullptr;
530 return ret;
Peng Xu53632542017-01-23 20:06:27 -0800531}
Mathias Agopianf001c922010-11-11 17:58:51 -0800532// ---------------------------------------------------------------------------
533}; // namespace android
Ashutosh Joshi5cafc1e2017-02-09 21:44:04 +0000534