1 /*
2  * Copyright (C) 2018 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 
17 /*
18  * This module provides the component definitions used to represent sensor
19  * calibration data, labeled flags/enumerators, and the callback functionality
20  * employed by the online sensor calibration algorithms.
21  */
22 
23 #ifndef LOCATION_LBS_CONTEXTHUB_NANOAPPS_CALIBRATION_ONLINE_CALIBRATION_COMMON_DATA_CALIBRATION_DATA_H_
24 #define LOCATION_LBS_CONTEXTHUB_NANOAPPS_CALIBRATION_ONLINE_CALIBRATION_COMMON_DATA_CALIBRATION_DATA_H_
25 
26 #include <stdint.h>
27 #include <string.h>
28 #include <sys/types.h>
29 
30 #include "calibration/online_calibration/common_data/calibration_quality.h"
31 #include "calibration/online_calibration/common_data/sensor_data.h"
32 #include "calibration/over_temp/over_temp_model.h"
33 
34 namespace online_calibration {
35 
36 /*
37  * Bitmask used to indicate which calibration values have changed for a given
38  * calibration update.
39  *
40  * [Bit Flag]   | [Affected Sensor Calibration Value]
41  * BIAS             - Quasi-static non-zero sensor output (offset), given
42  *                    conditions where the sensor should ideally output zero.
43  *                    Includes corrections for over-temperature compensation.
44  * SCALE_FACTOR     - Sensor axis scaling (ideally unity).
45  * CROSS_AXIS       - Output sensitivity due to variations of perpendicular
46  *                    sensing axes (ideally zero).
47  * OVER_TEMP        - Model parameters that capture variations in sensor
48  *                    behavior with temperature (e.g., linear bias sensitivity
49  *                    model).
50  * QUALITY_DEGRADED - Indicates a degradation in calibration quality.
51  */
52 enum class CalibrationTypeFlags : uint8_t {
53   NONE = 0x00,
54   BIAS = 0x01,
55   SCALE_FACTOR = 0x02,
56   CROSS_AXIS = 0x04,
57   OVER_TEMP = 0x08,
58   QUALITY_DEGRADED = 0x10,
59   ALL = 0xFF
60 };
61 
62 // Logic operators to assist with common bitmask setting/checking.
63 CalibrationTypeFlags operator|(CalibrationTypeFlags lhs,
64                                CalibrationTypeFlags rhs);
65 
66 bool operator&(CalibrationTypeFlags lhs, CalibrationTypeFlags rhs);
67 
68 CalibrationTypeFlags& operator|=(CalibrationTypeFlags& lhs,
69                                  CalibrationTypeFlags rhs);
70 
71 /*
72  * Defines the calibration data specific to a prototypical three-axis sensing
73  * device (e.g., accelerometer, gyroscope, magnetometer).
74  *
75  * Calibration correction may be applied as:
76  *   corrected_data = scale_skew_matrix * (input_data - offset);
77  *
78  * 'offset' is the sensor bias estimate (with temperature compensation applied
79  * when supported by the underlying calibration algorithm).
80  *
81  * The 'scale_skew_matrix' is assumed to be in lower diagonal form where the
82  * sensor frame reference definition is such that cross-axis sensitivities
83  * cross_axis_xy, cross_axis_xz, and cross_axis_yz are set to zero.
84  *
85  *   scale_skew_matrix = [scale_factor_x    0                 0
86  *                        cross_axis_yx     scale_factor_y    0
87  *                        cross_axis_zx     cross_axis_zy     scale_factor_z]
88  *
89  * NOTE1: If over-temperature compensation is provided, then temperature
90  * compensation is already applied to the 'offset'. Coefficients representative
91  * of the sensor's temperature dependency model are provided, and may be used
92  * for model initialization after a system restart.
93  *
94  *   temp_sensitivity - Modeled temperature sensitivity (i.e., linear slope).
95  *   temp_intercept   - Linear model intercept.
96  *
97  * The model equation for the over-temperature compensated offset:
98  *   compensated_offset = temp_sensitivity * current_temp + temp_intercept
99  *
100  * NOTE2: Unless otherwise stated, 3-dimensional array indices: 0=x, 1=y, 2=z.
101  */
102 struct CalibrationDataThreeAxis {
103   // Timestamp for the most recent calibration update.
104   uint64_t cal_update_time_nanos = 0;
105 
106   // The sensor's offset (i.e., bias) in the x-, y-, z-axes at
107   // 'offset_temp_celsius'.
108   float offset[3];
109 
110   // The temperature associated with the sensor offset.
111   float offset_temp_celsius;
112 
113   // The temperature sensitivity of the offset.
114   float temp_sensitivity[3];  // [sensor_units/Celsius]
115 
116   // The sensor's offset at zero degrees Celsius.
117   float temp_intercept[3];  // [sensor_units]
118 
119   // The sensor's scale factor for each axis.
120   float scale_factor[3];
121 
122   // The cross-axis factors in order: [0=yx, 1=zx, 2=zy].
123   float cross_axis[3];
124 
125   // Metrics used for the reported calibration accuracy. The behavior and
126   // definition depends on the sensor calibration type. See the calibration
127   // algorithm documentation for details.
128   CalibrationQuality calibration_quality;
129 
130   // Indicates the type of sensing device being calibrated.
131   SensorType type = SensorType::kUndefined;
132 
133   // Optional pointer to an array of over-temperature model data (null when not
134   // used).
135   OverTempModelThreeAxis* otc_model_data = nullptr;
136   int16_t num_model_pts = 0;  // Length of otc_model_data array.
137 
138   // Helper function that resets the calibration data to a set of neutral
139   // reference values where no calibration correction would be applied if used.
resetCalibrationDataThreeAxis140   void reset() {
141     otc_model_data = nullptr;
142     calibration_quality.reset();
143     offset_temp_celsius = 0.0f;
144     scale_factor[0] = 1.0f;
145     scale_factor[1] = 1.0f;
146     scale_factor[2] = 1.0f;
147     memset(offset, 0, sizeof(offset));
148     memset(temp_sensitivity, 0, sizeof(temp_sensitivity));
149     memset(temp_intercept, 0, sizeof(temp_intercept));
150     memset(cross_axis, 0, sizeof(cross_axis));
151   }
152 
CalibrationDataThreeAxisCalibrationDataThreeAxis153   CalibrationDataThreeAxis() { reset(); }
154 };
155 
156 /*
157  * Defines the calibration data for single dimensional sensing device (e.g.,
158  * thermometer, barometer).
159  *
160  * Calibration correction may be applied as:
161  *   corrected_data = scale_factor * (input_data - offset);
162  *
163  * 'offset' is the sensor bias estimate (with temperature compensation applied,
164  * if supported by the underlying calibration algorithm).
165  *
166  * NOTE: If over-temperature compensation is provided, then temperature
167  * compensation is already applied to the 'offset'. Coefficients representative
168  * of the sensor's temperature dependency model are provided, and may be used
169  * for model initialization after a system restart.
170  *
171  *   temp_sensitivity - Modeled temperature sensitivity (i.e., linear slope).
172  *   temp_intercept   - Linear model intercept.
173  *
174  * The model equation for the over-temperature compensated offset:
175  *   compensated_offset = temp_sensitivity * current_temp + temp_intercept
176  */
177 struct CalibrationDataSingleAxis {
178   // Timestamp for the most recent calibration update.
179   uint64_t cal_update_time_nanos = 0;
180 
181   // The sensor's offset (i.e., bias) at temperature, 'offset_temp_celsius'.
182   float offset;
183 
184   // The temperature associated with the sensor offset.
185   float offset_temp_celsius;
186 
187   // The temperature sensitivity of the offset.
188   float temp_sensitivity;  // [sensor_units/Celsius]
189 
190   // The sensor's offset at zero degrees Celsius.
191   float temp_intercept;  // [sensor_units]
192 
193   // The sensor's scale factor.
194   float scale_factor;
195 
196   // Metrics used for the reported calibration accuracy. The behavior and
197   // definition depends on the sensor calibration type. See the calibration
198   // algorithm documentation for details.
199   CalibrationQuality calibration_quality;
200 
201   // Indicates the type of sensing device being calibrated.
202   SensorType type = SensorType::kUndefined;
203 
204   // Optional pointer to an array of over-temperature model data (null when not
205   // used).
206   OverTempModelSingleAxis* otc_model_data = nullptr;
207   int16_t num_model_pts = 0;  // Length of otc_model_data array.
208 
209   // Helper function that resets the calibration data to a set of neutral
210   // reference values where no calibration correction would be applied if used.
resetCalibrationDataSingleAxis211   void reset() {
212     otc_model_data = nullptr;
213     calibration_quality.reset();
214     scale_factor = 1.0f;
215     offset_temp_celsius = 0.0f;
216     offset = 0.0f;
217     temp_sensitivity = 0.0f;
218     temp_intercept = 0.0f;
219   }
220 
CalibrationDataSingleAxisCalibrationDataSingleAxis221   CalibrationDataSingleAxis() { reset(); }
222 };
223 
224 }  // namespace online_calibration
225 
226 #endif  // LOCATION_LBS_CONTEXTHUB_NANOAPPS_CALIBRATION_ONLINE_CALIBRATION_COMMON_DATA_CALIBRATION_DATA_H_
227