1 /*
2 * Copyright (C) 2012 Invensense, Inc.
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
17 #ifndef ANDROID_MPL_SENSOR_H
18 #define ANDROID_MPL_SENSOR_H
19
20 #include <stdint.h>
21 #include <errno.h>
22 #include <sys/cdefs.h>
23 #include <sys/types.h>
24 #include <poll.h>
25 #include <time.h>
26 #include <utils/Vector.h>
27 #include <utils/KeyedVector.h>
28 #include <utils/String8.h>
29 #include "sensors.h"
30 #include "SensorBase.h"
31 #include "InputEventReader.h"
32
33 #ifndef INVENSENSE_COMPASS_CAL
34 #pragma message("unified HAL for AKM")
35 #include "CompassSensor.AKM.h"
36 #endif
37
38 #ifdef SENSOR_ON_PRIMARY_BUS
39 #pragma message("Sensor on Primary Bus")
40 #include "CompassSensor.IIO.primary.h"
41 #else
42 #pragma message("Sensor on Secondary Bus")
43 #include "CompassSensor.IIO.9150.h"
44 #endif
45
46 class PressureSensor;
47
48 /*****************************************************************************/
49 /* Sensors Enable/Disable Mask
50 *****************************************************************************/
51 #define MAX_CHIP_ID_LEN (20)
52
53 #define INV_THREE_AXIS_GYRO (0x000F)
54 #define INV_THREE_AXIS_ACCEL (0x0070)
55 #define INV_THREE_AXIS_COMPASS (0x0380)
56 #define INV_ONE_AXIS_PRESSURE (0x0400)
57 #define INV_ALL_SENSORS (0x7FFF)
58
59 #ifdef INVENSENSE_COMPASS_CAL
60 #define ALL_MPL_SENSORS_NP (INV_THREE_AXIS_ACCEL \
61 | INV_THREE_AXIS_COMPASS \
62 | INV_THREE_AXIS_GYRO)
63 #else
64 #define ALL_MPL_SENSORS_NP (INV_THREE_AXIS_ACCEL \
65 | INV_THREE_AXIS_COMPASS \
66 | INV_THREE_AXIS_GYRO)
67 #endif
68
69 // bit mask of current active features (mMplFeatureActiveMask)
70 #define INV_COMPASS_CAL 0x01
71 #define INV_COMPASS_FIT 0x02
72 // bit mask of current active features (mFeatureActiveMask)
73 #define INV_DMP_QUATERNION 0x001 //3 elements without real part, 32 bit each
74 #define INV_DMP_DISPL_ORIENTATION 0x002
75 #define INV_DMP_SIGNIFICANT_MOTION 0x004
76 #define INV_DMP_PEDOMETER 0x008
77 #define INV_DMP_PEDOMETER_STEP 0x010
78 #define INV_DMP_PED_STANDALONE 0x020 //timestamps only
79 #define INV_DMP_6AXIS_QUATERNION 0x040 //3 elements without real part, 32 bit each
80 #define INV_DMP_PED_QUATERNION 0x080 //3 elements without real part, 16 bit each
81 #define INV_DMP_PED_INDICATOR 0x100 //tag along header with step indciator
82 #define INV_DMP_BATCH_MODE 0x200
83 #define INV_DMP_ACCEL_PED (0xffff)
84
85 // bit mask of whether screen orientation is on
86 /*#define SCREEN_ORIENTATION_MASK ( \
87 (isDmpDisplayOrientationOn() \
88 && ((1 << INV_DMP_DISPL_ORIENTATION) \
89 || !isDmpScreenAutoRotationEnabled())) \
90 )*/
91 // bit mask of whether DMP should be turned on
92 #define DMP_FEATURE_MASK ( \
93 (INV_DMP_QUATERNION) \
94 | (INV_DMP_DISPL_ORIENTATION) \
95 | (INV_DMP_SIGNIFICANT_MOTION) \
96 | (INV_DMP_PEDOMETER) \
97 | (INV_DMP_PEDOMETER_STEP) \
98 | (INV_DMP_6AXIS_QUATERNION) \
99 | (INV_DMP_PED_QUATERNION) \
100 | (INV_DMP_BATCH_MODE) \
101 )
102 // bit mask of DMP features as sensors
103 #define DMP_SENSOR_MASK ( \
104 (INV_DMP_DISPL_ORIENTATION) \
105 | (INV_DMP_SIGNIFICANT_MOTION) \
106 | (INV_DMP_PEDOMETER) \
107 | (INV_DMP_PEDOMETER_STEP) \
108 | (INV_DMP_6AXIS_QUATERNION) \
109 )
110 // data header format used by kernel driver.
111 #define DATA_FORMAT_STEP 0x0001
112 #define DATA_FORMAT_MARKER 0x0010
113 #define DATA_FORMAT_PED_STANDALONE 0x0100
114 #define DATA_FORMAT_PED_QUAT 0x0200
115 #define DATA_FORMAT_6_AXIS 0x0400
116 #define DATA_FORMAT_QUAT 0x0800
117 #define DATA_FORMAT_COMPASS 0x1000
118 #define DATA_FORMAT_GYRO 0x2000
119 #define DATA_FORMAT_ACCEL 0x4000
120 #define DATA_FORMAT_PRESSURE 0x8000
121 #define DATA_FORMAT_MASK 0xffff
122
123 #define BYTES_PER_SENSOR 8
124 #define BYTES_PER_SENSOR_PACKET 16
125 #define QUAT_ONLY_LAST_PACKET_OFFSET 16
126 #define BYTES_QUAT_DATA 24
127 #define MAX_SUSPEND_BATCH_PACKET_SIZE 1024
128 #define MAX_PACKET_SIZE 80 //8 * 4 + (2 * 24)
129
130 /* Uncomment to enable Low Power Quaternion */
131 #define ENABLE_LP_QUAT_FEAT
132
133 /* Uncomment to enable DMP display orientation
134 (within the HAL, see below for Java framework) */
135 //#define ENABLE_DMP_DISPL_ORIENT_FEAT
136
137 #ifdef ENABLE_DMP_DISPL_ORIENT_FEAT
138 /* Uncomment following to expose the SENSOR_TYPE_SCREEN_ORIENTATION
139 sensor type (DMP screen orientation) to the Java framework.
140 NOTE:
141 need Invensense customized
142 'hardware/libhardware/include/hardware/sensors.h' to compile correctly.
143 NOTE:
144 need Invensense java framework changes to:
145 'frameworks/base/core/java/android/view/WindowOrientationListener.java'
146 'frameworks/base/core/java/android/hardware/Sensor.java'
147 'frameworks/base/core/java/android/hardware/SensorEvent.java'
148 for the 'Auto-rotate screen' to use this feature.
149 */
150 #define ENABLE_DMP_SCREEN_AUTO_ROTATION
151 #pragma message("ENABLE_DMP_DISPL_ORIENT_FEAT is defined, framework changes are necessary for HAL to work properly")
152 #endif
153
154 /* Enable Pressure sensor support */
155 #define ENABLE_PRESSURE
156
isDmpScreenAutoRotationEnabled()157 int isDmpScreenAutoRotationEnabled()
158 {
159 #ifdef ENABLE_DMP_SCREEN_AUTO_ROTATION
160 return 1;
161 #else
162 return 0;
163 #endif
164 }
165
166 int (*m_pt2AccelCalLoadFunc)(long *bias) = NULL;
167 /*****************************************************************************/
168 /** MPLSensor implementation which fits into the HAL example for crespo provided
169 * by Google.
170 * WARNING: there may only be one instance of MPLSensor, ever.
171 */
172
173 class MPLSensor: public SensorBase
174 {
175 typedef int (MPLSensor::*hfunc_t)(sensors_event_t*);
176
177 public:
178
179 enum {
180 Gyro = 0,
181 RawGyro,
182 Accelerometer,
183 MagneticField,
184 RawMagneticField,
185 Pressure,
186 Orientation,
187 RotationVector,
188 GameRotationVector,
189 LinearAccel,
190 Gravity,
191 SignificantMotion,
192 StepDetector,
193 StepCounter,
194 GeomagneticRotationVector,
195 NumSensors
196 };
197
198 MPLSensor(CompassSensor *, int (*m_pt2AccelCalLoadFunc)(long*) = 0);
199 virtual ~MPLSensor();
200
201 virtual int setDelay(int32_t handle, int64_t ns);
202 virtual int enable(int32_t handle, int enabled);
203 virtual int batch(int handle, int flags, int64_t period_ns, int64_t timeout);
204 virtual int flush(int handle);
205 int checkBatchEnabled();
206 int setBatch(int en, int toggleEnable);
getEnableMask()207 int32_t getEnableMask() { return mEnabled; }
208 void getHandle(int32_t handle, int &what, android::String8 &sname);
209
210 virtual int readEvents(sensors_event_t *data, int count);
211 virtual int getFd() const;
212 virtual int getAccelFd() const;
213 virtual int getCompassFd() const;
214 virtual int getPollTime();
215 virtual int getStepCountPollTime();
216 virtual bool hasPendingEvents() const;
217 virtual bool hasStepCountPendingEvents();
218 virtual void sleepEvent();
219 virtual void wakeEvent();
220 int populateSensorList(struct sensor_t *list, int len);
221 void cbProcData();
222
223 //static pointer to the object that will handle callbacks
224 static MPLSensor* gMPLSensor;
225
226 int readAccelEvents(sensors_event_t* data, int count);
227 void buildCompassEvent();
228 void buildMpuEvent();
229
230 int turnOffAccelFifo();
231 int turnOffGyroFifo();
232 int enableDmpOrientation(int);
233 int dmpOrientHandler(int);
234 int readDmpOrientEvents(sensors_event_t* data, int count);
235 int getDmpOrientFd();
236 int openDmpOrientFd();
237 int closeDmpOrientFd();
238
239 int getDmpRate(int64_t *);
240 int checkDMPOrientation();
241
242 int getDmpSignificantMotionFd();
243 int readDmpSignificantMotionEvents(sensors_event_t* data, int count);
244 int enableDmpSignificantMotion(int);
245 int significantMotionHandler(sensors_event_t* data);
checkSmdSupport()246 bool checkSmdSupport(){return (mDmpSignificantMotionEnabled);};
247
248 int enableDmpPedometer(int, int);
249 int readDmpPedometerEvents(sensors_event_t* data, int count, int32_t id, int32_t type, int outputType);
250 int getDmpPedometerFd();
checkPedometerSupport()251 bool checkPedometerSupport() {return (mDmpPedometerEnabled || mDmpStepCountEnabled);};
checkOrientationSupport()252 bool checkOrientationSupport() {return ((isDmpDisplayOrientationOn()
253 && (mDmpOrientationEnabled
254 || !isDmpScreenAutoRotationEnabled())));};
255
256 protected:
257 CompassSensor *mCompassSensor;
258 PressureSensor *mPressureSensor;
259
260 int gyroHandler(sensors_event_t *data);
261 int rawGyroHandler(sensors_event_t *data);
262 int accelHandler(sensors_event_t *data);
263 int compassHandler(sensors_event_t *data);
264 int rawCompassHandler(sensors_event_t *data);
265 int rvHandler(sensors_event_t *data);
266 int grvHandler(sensors_event_t *data);
267 int laHandler(sensors_event_t *data);
268 int gravHandler(sensors_event_t *data);
269 int orienHandler(sensors_event_t *data);
270 int smHandler(sensors_event_t *data);
271 int pHandler(sensors_event_t *data);
272 int scHandler(sensors_event_t *data);
273 int gmHandler(sensors_event_t *data);
274 int psHandler(sensors_event_t *data);
275 int metaHandler(sensors_event_t *data, int flags);
276 void calcOrientationSensor(float *Rx, float *Val);
277 virtual int update_delay();
278
279 void inv_set_device_properties();
280 int inv_constructor_init();
281 int inv_constructor_default_enable();
282 int setGyroInitialState();
283 int setAccelInitialState();
284 int masterEnable(int en);
285 int enablePedStandalone(int en);
286 int enablePedStandaloneData(int en);
287 int enablePedQuaternion(int);
288 int enablePedQuaternionData(int);
289 int enable6AxisQuaternion(int);
290 int enable6AxisQuaternionData(int);
291 int enableLPQuaternion(int);
292 int enableQuaternionData(int);
293 int enableAccelPedometer(int);
294 int enableAccelPedData(int);
295 int onDmp(int);
296 int enableGyro(int en);
297 int enableLowPowerAccel(int en);
298 int enableAccel(int en);
299 int enableCompass(int en, int rawSensorOn);
300 int enablePressure(int en);
301 int enableBatch(int64_t timeout);
302 void computeLocalSensorMask(int enabled_sensors);
303 int computeBatchSensorMask(int enableSensor, int checkNewBatchSensor);
304 int computeBatchDataOutput();
305 int enableSensors(unsigned long sensors, int en, uint32_t changed);
306 int inv_read_gyro_buffer(int fd, short *data, long long *timestamp);
307 int inv_float_to_q16(float *fdata, long *ldata);
308 int inv_long_to_q16(long *fdata, long *ldata);
309 int inv_float_to_round(float *fdata, long *ldata);
310 int inv_float_to_round2(float *fdata, short *sdata);
311 int inv_long_to_float(long *ldata, float *fdata);
312 int inv_read_temperature(long long *data);
313 int inv_read_dmp_state(int fd);
314 int inv_read_sensor_bias(int fd, long *data);
315 void inv_get_sensors_orientation(void);
316 int inv_init_sysfs_attributes(void);
317 int resetCompass(void);
318 void setCompassDelay(int64_t ns);
319 void enable_iio_sysfs(void);
320 int enablePedometer(int);
321 int enablePedIndicator(int en);
322 int checkPedStandaloneEnabled(void);
323 int checkPedQuatEnabled();
324 int check6AxisQuatEnabled();
325 int checkLPQRateSupported();
326 int checkLPQuaternion();
327 int checkAccelPed();
328 void setInitial6QuatValue();
329 int writeSignificantMotionParams(bool toggleEnable,
330 uint32_t delayThreshold1, uint32_t delayThreshold2,
331 uint32_t motionThreshold);
332
333 int mNewData; // flag indicating that the MPL calculated new output values
334 int mDmpStarted;
335 long mMasterSensorMask;
336 long mLocalSensorMask;
337 int mPollTime;
338 int mStepCountPollTime;
339 bool mHaveGoodMpuCal; // flag indicating that the cal file can be written
340 int mGyroAccuracy; // value indicating the quality of the gyro calibr.
341 int mAccelAccuracy; // value indicating the quality of the accel calibr.
342 int mCompassAccuracy; // value indicating the quality of the compass calibr.
343 struct pollfd mPollFds[5];
344 int mSampleCount;
345 pthread_mutex_t mMplMutex;
346 pthread_mutex_t mHALMutex;
347
348 char mIIOBuffer[(16 + 8 * 3 + 8) * IIO_BUFFER_LENGTH];
349
350 int iio_fd;
351 int accel_fd;
352 int mpufifo_fd;
353 int gyro_temperature_fd;
354 int accel_x_offset_fd;
355 int accel_y_offset_fd;
356 int accel_z_offset_fd;
357
358 int accel_x_dmp_bias_fd;
359 int accel_y_dmp_bias_fd;
360 int accel_z_dmp_bias_fd;
361
362 int gyro_x_offset_fd;
363 int gyro_y_offset_fd;
364 int gyro_z_offset_fd;
365
366 int gyro_x_dmp_bias_fd;
367 int gyro_y_dmp_bias_fd;
368 int gyro_z_dmp_bias_fd;
369
370 int dmp_orient_fd;
371 int mDmpOrientationEnabled;
372
373 int dmp_sign_motion_fd;
374 int mDmpSignificantMotionEnabled;
375
376 int dmp_pedometer_fd;
377 int mDmpPedometerEnabled;
378 int mDmpStepCountEnabled;
379
380 uint32_t mEnabled;
381 uint32_t mBatchEnabled;
382 int32_t mFlushEnabled;
383 uint32_t mOldBatchEnabledMask;
384 int64_t mBatchTimeoutInMs;
385 sensors_event_t mPendingEvents[NumSensors];
386 int64_t mDelays[NumSensors];
387 int64_t mBatchDelays[NumSensors];
388 int64_t mBatchTimeouts[NumSensors];
389 hfunc_t mHandlers[NumSensors];
390 short mCachedGyroData[3];
391 long mCachedAccelData[3];
392 long mCachedCompassData[3];
393 long mCachedQuaternionData[3];
394 long mCached6AxisQuaternionData[3];
395 long mCachedPedQuaternionData[3];
396 long mCachedPressureData;
397 android::KeyedVector<int, int> mIrqFds;
398
399 InputEventCircularReader mAccelInputReader;
400 InputEventCircularReader mGyroInputReader;
401
402 bool mFirstRead;
403 short mTempScale;
404 short mTempOffset;
405 int64_t mTempCurrentTime;
406 int mAccelScale;
407 long mAccelSelfTestScale;
408 long mGyroScale;
409 long mGyroSelfTestScale;
410 long mCompassScale;
411 float mCompassBias[3];
412 bool mFactoryGyroBiasAvailable;
413 long mFactoryGyroBias[3];
414 bool mGyroBiasAvailable;
415 bool mGyroBiasApplied;
416 float mGyroBias[3]; //in body frame
417 long mGyroChipBias[3]; //in chip frame
418 bool mFactoryAccelBiasAvailable;
419 long mFactoryAccelBias[3];
420 bool mAccelBiasAvailable;
421 bool mAccelBiasApplied;
422 long mAccelBias[3]; //in chip frame
423
424 uint32_t mPendingMask;
425 unsigned long mSensorMask;
426
427 char chip_ID[MAX_CHIP_ID_LEN];
428 char mSysfsPath[MAX_SYSFS_NAME_LEN];
429
430 signed char mGyroOrientation[9];
431 signed char mAccelOrientation[9];
432
433 int64_t mSensorTimestamp;
434 int64_t mCompassTimestamp;
435 int64_t mPressureTimestamp;
436
437 struct sysfs_attrbs {
438 char *chip_enable;
439 char *power_state;
440 char *master_enable;
441 char *dmp_firmware;
442 char *firmware_loaded;
443 char *dmp_on;
444 char *dmp_int_on;
445 char *dmp_event_int_on;
446 char *tap_on;
447 char *key;
448 char *self_test;
449 char *temperature;
450
451 char *gyro_enable;
452 char *gyro_fifo_rate;
453 char *gyro_fsr;
454 char *gyro_orient;
455 char *gyro_fifo_enable;
456 char *gyro_rate;
457
458 char *accel_enable;
459 char *accel_fifo_rate;
460 char *accel_fsr;
461 char *accel_bias;
462 char *accel_orient;
463 char *accel_fifo_enable;
464 char *accel_rate;
465
466 char *three_axis_q_on; //formerly quaternion_on
467 char *three_axis_q_rate;
468
469 char *six_axis_q_on;
470 char *six_axis_q_rate;
471
472 char *six_axis_q_value;
473
474 char *ped_q_on;
475 char *ped_q_rate;
476
477 char *step_detector_on;
478 char *step_indicator_on;
479
480 char *in_timestamp_en;
481 char *in_timestamp_index;
482 char *in_timestamp_type;
483
484 char *buffer_length;
485
486 char *display_orientation_on;
487 char *event_display_orientation;
488
489 char *in_accel_x_offset;
490 char *in_accel_y_offset;
491 char *in_accel_z_offset;
492 char *in_accel_self_test_scale;
493
494 char *in_accel_x_dmp_bias;
495 char *in_accel_y_dmp_bias;
496 char *in_accel_z_dmp_bias;
497
498 char *in_gyro_x_offset;
499 char *in_gyro_y_offset;
500 char *in_gyro_z_offset;
501 char *in_gyro_self_test_scale;
502
503 char *in_gyro_x_dmp_bias;
504 char *in_gyro_y_dmp_bias;
505 char *in_gyro_z_dmp_bias;
506
507 char *event_smd;
508 char *smd_enable;
509 char *smd_delay_threshold;
510 char *smd_delay_threshold2;
511 char *smd_threshold;
512 char *batchmode_timeout;
513 char *batchmode_wake_fifo_full_on;
514 char *flush_batch;
515
516 char *pedometer_on;
517 char *pedometer_int_on;
518 char *event_pedometer;
519 char *pedometer_steps;
520
521 char *motion_lpa_on;
522 } mpu;
523
524 char *sysfs_names_ptr;
525 int mMplFeatureActiveMask;
526 uint64_t mFeatureActiveMask;
527 bool mDmpOn;
528 int mPedUpdate;
529 int mPressureUpdate;
530 int64_t mQuatSensorTimestamp;
531 int64_t mStepSensorTimestamp;
532 uint64_t mLastStepCount;
533 int mLeftOverBufferSize;
534 char mLeftOverBuffer[24];
535 bool mInitial6QuatValueAvailable;
536 long mInitial6QuatValue[4];
537 bool mFlushBatchSet;
538 uint32_t mSkipReadEvents;
539
540 private:
541 /* added for dynamic get sensor list */
542 void fillAccel(const char* accel, struct sensor_t *list);
543 void fillGyro(const char* gyro, struct sensor_t *list);
544 void fillRV(struct sensor_t *list);
545 void fillGMRV(struct sensor_t *list);
546 void fillGRV(struct sensor_t *list);
547 void fillOrientation(struct sensor_t *list);
548 void fillGravity(struct sensor_t *list);
549 void fillLinearAccel(struct sensor_t *list);
550 void fillSignificantMotion(struct sensor_t *list);
551 #ifdef ENABLE_DMP_SCREEN_AUTO_ROTATION
552 void fillScreenOrientation(struct sensor_t *list);
553 #endif
554 void storeCalibration();
555 void loadDMP();
556 bool isMpuNonDmp();
557 int isLowPowerQuatEnabled();
558 int isDmpDisplayOrientationOn();
559 void getCompassBias();
560 void getFactoryGyroBias();
561 void setFactoryGyroBias();
562 void getGyroBias();
563 void setGyroBias();
564 void getFactoryAccelBias();
565 void setFactoryAccelBias();
566 void getAccelBias();
567 void setAccelBias();
568 int isCompassDisabled();
569 int setBatchDataRates();
570 int resetDataRates();
571 void initBias();
572 void sys_dump(bool fileMode);
573 };
574
575 extern "C" {
576 void setCallbackObject(MPLSensor*);
577 MPLSensor *getCallbackObject();
578 }
579
580 #endif // ANDROID_MPL_SENSOR_H
581