1 /* 2 * Copyright (c) 2023 Google LLC 3 * 4 * SPDX-License-Identifier: Apache-2.0 5 */ 6 7 #ifndef ZEPHYR_INCLUDE_DRIVERS_SENSOR_DATA_TYPES_H 8 #define ZEPHYR_INCLUDE_DRIVERS_SENSOR_DATA_TYPES_H 9 10 #include <zephyr/dsp/types.h> 11 #include <zephyr/dsp/print_format.h> 12 13 #include <inttypes.h> 14 15 #ifdef __cplusplus 16 extern "C" { 17 #endif 18 19 struct sensor_data_header { 20 /** 21 * The closest timestamp for when the first frame was generated as attained by 22 * :c:func:`k_uptime_ticks`. 23 */ 24 uint64_t base_timestamp_ns; 25 /** 26 * The number of elements in the 'readings' array. 27 * 28 * This must be at least 1 29 */ 30 uint16_t reading_count; 31 }; 32 33 /** 34 * Data for a sensor channel which reports on three axes. This is used by: 35 * - :c:enum:`SENSOR_CHAN_ACCEL_X` 36 * - :c:enum:`SENSOR_CHAN_ACCEL_Y` 37 * - :c:enum:`SENSOR_CHAN_ACCEL_Z` 38 * - :c:enum:`SENSOR_CHAN_ACCEL_XYZ` 39 * - :c:enum:`SENSOR_CHAN_GYRO_X` 40 * - :c:enum:`SENSOR_CHAN_GYRO_Y` 41 * - :c:enum:`SENSOR_CHAN_GYRO_Z` 42 * - :c:enum:`SENSOR_CHAN_GYRO_XYZ` 43 * - :c:enum:`SENSOR_CHAN_MAGN_X` 44 * - :c:enum:`SENSOR_CHAN_MAGN_Y` 45 * - :c:enum:`SENSOR_CHAN_MAGN_Z` 46 * - :c:enum:`SENSOR_CHAN_MAGN_XYZ` 47 * - :c:enum:`SENSOR_CHAN_POS_DX` 48 * - :c:enum:`SENSOR_CHAN_POS_DY` 49 * - :c:enum:`SENSOR_CHAN_POS_DZ` 50 * - :c:enum:`SENSOR_CHAN_POS_DXYZ` 51 */ 52 struct sensor_three_axis_data { 53 struct sensor_data_header header; 54 int8_t shift; 55 struct sensor_three_axis_sample_data { 56 uint32_t timestamp_delta; 57 union { 58 q31_t values[3]; 59 q31_t v[3]; 60 struct { 61 q31_t x; 62 q31_t y; 63 q31_t z; 64 }; 65 }; 66 } readings[1]; 67 }; 68 69 #define PRIsensor_three_axis_data PRIu64 "ns, (%" PRIq(6) ", %" PRIq(6) ", %" PRIq(6) ")" 70 71 #define PRIsensor_three_axis_data_arg(data_, readings_offset_) \ 72 (data_).header.base_timestamp_ns + (data_).readings[(readings_offset_)].timestamp_delta, \ 73 PRIq_arg((data_).readings[(readings_offset_)].x, 6, (data_).shift), \ 74 PRIq_arg((data_).readings[(readings_offset_)].y, 6, (data_).shift), \ 75 PRIq_arg((data_).readings[(readings_offset_)].z, 6, (data_).shift) 76 77 /** 78 * Data for a sensor channel which reports game rotation vector data. This is used by: 79 * - :c:enum:`SENSOR_CHAN_GAME_ROTATION_VECTOR` 80 */ 81 struct sensor_game_rotation_vector_data { 82 struct sensor_data_header header; 83 int8_t shift; 84 struct sensor_game_rotation_vector_sample_data { 85 uint32_t timestamp_delta; 86 union { 87 q31_t values[4]; 88 q31_t v[4]; 89 struct { 90 q31_t x; 91 q31_t y; 92 q31_t z; 93 q31_t w; 94 }; 95 }; 96 } readings[1]; 97 }; 98 99 #define PRIsensor_game_rotation_vector_data PRIu64 \ 100 "ns, (%" PRIq(6) ", %" PRIq(6) ", %" PRIq(6) ", %" PRIq(6) ")" 101 102 #define PRIsensor_game_rotation_vector_data_arg(data_, readings_offset_) \ 103 (data_).header.base_timestamp_ns + (data_).readings[(readings_offset_)].timestamp_delta, \ 104 PRIq_arg((data_).readings[(readings_offset_)].x, 6, (data_).shift), \ 105 PRIq_arg((data_).readings[(readings_offset_)].y, 6, (data_).shift), \ 106 PRIq_arg((data_).readings[(readings_offset_)].z, 6, (data_).shift), \ 107 PRIq_arg((data_).readings[(readings_offset_)].w, 6, (data_).shift) 108 109 /** 110 * Data from a sensor where we only care about an event occurring. This is used to report triggers. 111 */ 112 struct sensor_occurrence_data { 113 struct sensor_data_header header; 114 struct sensor_occurrence_sample_data { 115 uint32_t timestamp_delta; 116 } readings[1]; 117 }; 118 119 #define PRIsensor_occurrence_data PRIu64 "ns" 120 121 #define PRIsensor_occurrence_data_arg(data_, readings_offset_) \ 122 (data_).header.base_timestamp_ns + (data_).readings[(readings_offset_)].timestamp_delta 123 124 struct sensor_q31_data { 125 struct sensor_data_header header; 126 int8_t shift; 127 struct sensor_q31_sample_data { 128 uint32_t timestamp_delta; 129 union { 130 q31_t value; 131 q31_t light; /**< Unit: lux */ 132 q31_t pressure; /**< Unit: kilopascal */ 133 q31_t temperature; /**< Unit: degrees Celsius */ 134 q31_t percent; /**< Unit: percent */ 135 q31_t distance; /**< Unit: meters */ 136 q31_t density; /**< Unit: ug/m^3 */ 137 q31_t density_ppm; /**< Unit: parts per million */ 138 q31_t density_ppb; /**< Unit: parts per billion */ 139 q31_t resistance; /**< Unit: ohms */ 140 q31_t voltage; /**< Unit: volts */ 141 q31_t current; /**< Unit: amps */ 142 q31_t power; /**< Unit: watts */ 143 q31_t angle; /**< Unit: degrees */ 144 q31_t electric_charge; /**< Unit: mAh */ 145 q31_t humidity; /**< Unit: RH */ 146 }; 147 } readings[1]; 148 }; 149 150 #define PRIsensor_q31_data PRIu64 "ns (%" PRIq(6) ")" 151 152 #define PRIsensor_q31_data_arg(data_, readings_offset_) \ 153 (data_).header.base_timestamp_ns + (data_).readings[(readings_offset_)].timestamp_delta, \ 154 PRIq_arg((data_).readings[(readings_offset_)].value, 6, (data_).shift) 155 156 /** 157 * Data from a sensor that produces a byte of data. This is used by: 158 * - :c:enum:`SENSOR_CHAN_PROX` 159 */ 160 struct sensor_byte_data { 161 struct sensor_data_header header; 162 struct sensor_byte_sample_data { 163 uint32_t timestamp_delta; 164 union { 165 uint8_t value; 166 struct { 167 uint8_t is_near: 1; 168 uint8_t padding: 7; 169 }; 170 }; 171 } readings[1]; 172 }; 173 174 #define PRIsensor_byte_data(field_name_) PRIu64 "ns (" STRINGIFY(field_name_) " = %" PRIu8 ")" 175 176 #define PRIsensor_byte_data_arg(data_, readings_offset_, field_name_) \ 177 (data_).header.base_timestamp_ns + (data_).readings[(readings_offset_)].timestamp_delta, \ 178 (data_).readings[(readings_offset_)].field_name_ 179 180 /** 181 * Data from a sensor that produces a count like value. This is used by: 182 * - :c:enum:`SENSOR_CHAN_GAUGE_CYCLE_COUNT` 183 */ 184 struct sensor_uint64_data { 185 struct sensor_data_header header; 186 struct sensor_uint64_sample_data { 187 uint32_t timestamp_delta; 188 uint64_t value; 189 } readings[1]; 190 }; 191 192 #define PRIsensor_uint64_data PRIu64 "ns (%" PRIu64 ")" 193 194 #define PRIsensor_uint64_data_arg(data_, readings_offset_) \ 195 (data_).header.base_timestamp_ns + (data_).readings[(readings_offset_)].timestamp_delta, \ 196 (data_).readings[(readings_offset_)].value 197 198 #ifdef __cplusplus 199 } 200 #endif 201 202 #endif /* ZEPHYR_INCLUDE_DRIVERS_SENSOR_DATA_TYPES_H */ 203