handle master side communication of openIMU300ZI module

Dependencies:   mbed

Dependents:   VDU_2021

Committer:
Arithemetica
Date:
Thu Dec 19 14:41:25 2019 +0000
Revision:
24:275e886bd61c
Parent:
23:3626c7d73505
Child:
25:3dfd686ae315
wait more time for robustness

Who changed what in which revision?

UserRevisionLine numberNew contents of line
Arithemetica 7:224ffdacb240 1 /**
Arithemetica 7:224ffdacb240 2 * @file imu_driver.hpp
Arithemetica 10:d8223969c541 3 * @brief ImuDriver class and other data storage struct definition. The C language version
Arithemetica 10:d8223969c541 4 * can be found at <A HREF="https://github.com/osjacky430/imu_driver">this github website</A>
Arithemetica 7:224ffdacb240 5 */
Arithemetica 7:224ffdacb240 6
Arithemetica 1:8e31413068af 7 #ifndef IMU_DRIVER_HPP_
Arithemetica 1:8e31413068af 8 #define IMU_DRIVER_HPP_
Arithemetica 1:8e31413068af 9
Arithemetica 0:8c01a98a2812 10 #include <mbed.h>
Arithemetica 0:8c01a98a2812 11 #include <cstdint>
Arithemetica 0:8c01a98a2812 12
Arithemetica 14:6c31a7ab45f0 13 typedef enum ImuExtiConfig {
Arithemetica 14:6c31a7ab45f0 14 ImuExtiRcvNotUsed = 0b00,
Arithemetica 14:6c31a7ab45f0 15 ImuExtiRcvNormalMsg = 0b01,
Arithemetica 23:3626c7d73505 16 ImuExtiRcvAhrsMsg = 0b10,
Arithemetica 23:3626c7d73505 17 ImuExtiRcvBothMsg = 0b11
Arithemetica 14:6c31a7ab45f0 18 } ImuExtiConfig;
Arithemetica 14:6c31a7ab45f0 19
Arithemetica 20:19f5c94f8660 20 /* this needs to be extended (IMO) */
Arithemetica 19:3ee54f9a56f3 21 inline ImuExtiConfig operator |(ImuExtiConfig const& left, ImuExtiConfig const& right)
Arithemetica 19:3ee54f9a56f3 22 {
Arithemetica 19:3ee54f9a56f3 23 return ImuExtiConfig(left | right);
Arithemetica 19:3ee54f9a56f3 24 }
Arithemetica 19:3ee54f9a56f3 25
Arithemetica 17:629b2f317d0a 26 /**
Arithemetica 17:629b2f317d0a 27 * @brief ImuDriverStatus
Arithemetica 17:629b2f317d0a 28 */
Arithemetica 12:bb490978e153 29 typedef enum ImuDriverStatus {
Arithemetica 14:6c31a7ab45f0 30 ImuDriverStatusOK,
Arithemetica 14:6c31a7ab45f0 31 ImuDriverStatusDataNotReady,
Arithemetica 14:6c31a7ab45f0 32 ImuDriverStatusInvalidCall
Arithemetica 14:6c31a7ab45f0 33 } ImuDriverStatus;
Arithemetica 12:bb490978e153 34
Arithemetica 0:8c01a98a2812 35 typedef enum ImuDriverRegister {
Arithemetica 0:8c01a98a2812 36 ReadAhrsBurstDataRegister = 0x3D,
Arithemetica 0:8c01a98a2812 37 ReadBurstDataRegister = 0x3E,
Arithemetica 0:8c01a98a2812 38 ReadExtBurstDataRegister = 0x3F
Arithemetica 0:8c01a98a2812 39 } ImuDriverRegister;
Arithemetica 0:8c01a98a2812 40
Arithemetica 0:8c01a98a2812 41 typedef struct AhrsRawData {
Arithemetica 0:8c01a98a2812 42 std::uint16_t status;
Arithemetica 0:8c01a98a2812 43 std::int16_t attitude[3];
Arithemetica 0:8c01a98a2812 44 std::int16_t temperature;
Arithemetica 0:8c01a98a2812 45 } AhrsRawData;
Arithemetica 0:8c01a98a2812 46
Arithemetica 10:d8223969c541 47 /**
Arithemetica 12:bb490978e153 48 * @brief AhrsProcessedData is data storage class fpr processed AHRS data
Arithemetica 14:6c31a7ab45f0 49 *
Arithemetica 11:866dd73e4ab3 50 * The data storage struct consists of:
Arithemetica 11:866dd73e4ab3 51 *
Arithemetica 10:d8223969c541 52 * - attitude: pitch, roll, yaw in deg, range from -180 ~ +180 deg
Arithemetica 10:d8223969c541 53 */
Arithemetica 0:8c01a98a2812 54 typedef struct AhrsProcessedData {
Arithemetica 0:8c01a98a2812 55 float attitude[3];
Arithemetica 0:8c01a98a2812 56 } AhrsProcessedData;
Arithemetica 0:8c01a98a2812 57
Arithemetica 0:8c01a98a2812 58 typedef struct ImuRawData {
Arithemetica 0:8c01a98a2812 59 std::uint16_t status;
Arithemetica 0:8c01a98a2812 60 std::int16_t rate[3];
Arithemetica 0:8c01a98a2812 61 std::int16_t accel[3];
Arithemetica 0:8c01a98a2812 62 std::int16_t temperature;
Arithemetica 0:8c01a98a2812 63 } ImuRawData;
Arithemetica 0:8c01a98a2812 64
Arithemetica 10:d8223969c541 65 /**
Arithemetica 11:866dd73e4ab3 66 * @brief ImuProcessedData is data storage class for processed imu data
Arithemetica 10:d8223969c541 67 *
Arithemetica 11:866dd73e4ab3 68 * This data storage class consists of:
Arithemetica 14:6c31a7ab45f0 69 *
Arithemetica 10:d8223969c541 70 * - status: if status = 0x0010 (over range error), status = 0 (no error)
Arithemetica 10:d8223969c541 71 * - gyroscope: deg/s, range from -300 deg/s ~ 300 deg/s
Arithemetica 10:d8223969c541 72 * - accelerometer: g, range from -4.5g ~ 4.5g
Arithemetica 10:d8223969c541 73 * - temperature: Celcius
Arithemetica 10:d8223969c541 74 */
Arithemetica 0:8c01a98a2812 75 typedef struct ImuProcessedData {
Arithemetica 0:8c01a98a2812 76 std::uint16_t status;
Arithemetica 0:8c01a98a2812 77
Arithemetica 0:8c01a98a2812 78 float rate[3];
Arithemetica 0:8c01a98a2812 79 float accel[3];
Arithemetica 0:8c01a98a2812 80
Arithemetica 0:8c01a98a2812 81 std::int16_t temperature;
Arithemetica 0:8c01a98a2812 82 } ImuProcessedData;
Arithemetica 0:8c01a98a2812 83
Arithemetica 0:8c01a98a2812 84 /**
Arithemetica 12:bb490978e153 85 * @brief ImuDriver is used to handle the master side of SPI communication of openIMU300ZI module, the
Arithemetica 2:f3a7def7a7e1 86 * default setups are:
Arithemetica 0:8c01a98a2812 87 *
Arithemetica 2:f3a7def7a7e1 88 * - Data frame: 16 bits
Arithemetica 2:f3a7def7a7e1 89 * - CPOL: High (1)
Arithemetica 2:f3a7def7a7e1 90 * - CPHA: 2 Edge (1)
Arithemetica 17:629b2f317d0a 91 * - Frequency: 1 MHz (Default frequency of spi)
Arithemetica 2:f3a7def7a7e1 92 * - Endian: MSB first (Mbed only support MSB AFAIK)
Arithemetica 5:e71931fcae33 93 *
Arithemetica 10:d8223969c541 94 * According to <A HREF="https://openimu.readthedocs.io/en/latest/software/SPImessaging.html">openIMU300ZI SPI framework</A>:
Arithemetica 5:e71931fcae33 95 *
Arithemetica 3:8552e26cd162 96 * - Data transferred in 16-bit word-length and MSB-first
Arithemetica 5:e71931fcae33 97 * - fCLK ≤ 2.0 MHz
Arithemetica 3:8552e26cd162 98 * - CPOL = 1 (clock polarity) and CPHA = 1 (clock phase)
Arithemetica 0:8c01a98a2812 99 *
Arithemetica 2:f3a7def7a7e1 100 * @tparam spi SPI comm instance, ImuDriver currently support only SPI framework
Arithemetica 2:f3a7def7a7e1 101 * @tparam rst Reset pin name, this is used to reset the openIMU300ZI module
Arithemetica 2:f3a7def7a7e1 102 * @tparam drdy Data ready pin name, this is used as indication of data readiness
Arithemetica 2:f3a7def7a7e1 103 * @tparam ss Slave select pin name, this is used as slave select, pull low to initiate
Arithemetica 2:f3a7def7a7e1 104 * communication process.
Arithemetica 5:e71931fcae33 105 *
Arithemetica 7:224ffdacb240 106 * @todo Attach to exti in the future, and make user able to choose
Arithemetica 7:224ffdacb240 107 *
Arithemetica 0:8c01a98a2812 108 * Example of using ImuDriver:
Arithemetica 0:8c01a98a2812 109 *
Arithemetica 0:8c01a98a2812 110 * @code
Arithemetica 0:8c01a98a2812 111 * #include "imu_driver.hpp"
Arithemetica 0:8c01a98a2812 112 *
Arithemetica 0:8c01a98a2812 113 * SPI spi3(PB_5, PB_6, PB_3); // declare SPI instance globally
Arithemetica 0:8c01a98a2812 114 * Serial pc(USBTX, USBRX, 115200); // print debug message
Arithemetica 0:8c01a98a2812 115 *
Arithemetica 0:8c01a98a2812 116 * int main()
Arithemetica 0:8c01a98a2812 117 * {
Arithemetica 5:e71931fcae33 118 * // SPI instance, reset, data ready, slave select
Arithemetica 17:629b2f317d0a 119 * ImuDriver<spi3, PA_10, PA_8, PA_9> imu(ImuExtiRcvNormalMsg);
Arithemetica 0:8c01a98a2812 120 *
Arithemetica 0:8c01a98a2812 121 * while(true)
Arithemetica 0:8c01a98a2812 122 * {
Arithemetica 17:629b2f317d0a 123 * pc.printf("%.3f, %.3f, %.3f\n\r", imu.imuProcessedData.rate[0], imu.imuProcessedData.rate[1], imu.imuProcessedData.rate[2]);
Arithemetica 0:8c01a98a2812 124 * }
Arithemetica 0:8c01a98a2812 125 * }
Arithemetica 5:e71931fcae33 126 *
Arithemetica 0:8c01a98a2812 127 * @endcode
Arithemetica 0:8c01a98a2812 128 */
Arithemetica 2:f3a7def7a7e1 129 template <SPI& Spi, PinName rst, PinName drdy, PinName ss>
Arithemetica 0:8c01a98a2812 130 class ImuDriver
Arithemetica 0:8c01a98a2812 131 {
Arithemetica 0:8c01a98a2812 132 private:
Arithemetica 14:6c31a7ab45f0 133 ImuExtiConfig m_extiConfig;
Arithemetica 14:6c31a7ab45f0 134
Arithemetica 0:8c01a98a2812 135 SPI& m_spi;
Arithemetica 0:8c01a98a2812 136 DigitalOut m_rst, m_ss;
Arithemetica 0:8c01a98a2812 137 DigitalIn m_drdy;
Arithemetica 2:f3a7def7a7e1 138 InterruptIn m_drdyExti;
Arithemetica 5:e71931fcae33 139
Arithemetica 0:8c01a98a2812 140 float m_gyroScaler[3];
Arithemetica 0:8c01a98a2812 141 float m_accelScaler[3];
Arithemetica 0:8c01a98a2812 142 float m_ahrsScaler[3];
Arithemetica 23:3626c7d73505 143
Arithemetica 23:3626c7d73505 144 ImuDriver(); // cannot initialize via default constructor
Arithemetica 23:3626c7d73505 145
Arithemetica 0:8c01a98a2812 146 std::uint16_t m_imuSpiWrite(const std::uint16_t val) const
Arithemetica 0:8c01a98a2812 147 {
Arithemetica 0:8c01a98a2812 148 // RAII
Arithemetica 0:8c01a98a2812 149 class SpiLock
Arithemetica 0:8c01a98a2812 150 {
Arithemetica 0:8c01a98a2812 151 private:
Arithemetica 0:8c01a98a2812 152 SPI& m_spi;
Arithemetica 0:8c01a98a2812 153 public:
Arithemetica 0:8c01a98a2812 154 SpiLock(SPI& t_spi) : m_spi(t_spi)
Arithemetica 0:8c01a98a2812 155 {
Arithemetica 0:8c01a98a2812 156 m_spi.lock();
Arithemetica 0:8c01a98a2812 157 }
Arithemetica 0:8c01a98a2812 158
Arithemetica 0:8c01a98a2812 159 ~SpiLock()
Arithemetica 0:8c01a98a2812 160 {
Arithemetica 0:8c01a98a2812 161 m_spi.unlock();
Arithemetica 0:8c01a98a2812 162 }
Arithemetica 0:8c01a98a2812 163 };
Arithemetica 0:8c01a98a2812 164
Arithemetica 0:8c01a98a2812 165 SpiLock lock(m_spi);
Arithemetica 0:8c01a98a2812 166 return m_spi.write(val);
Arithemetica 0:8c01a98a2812 167 }
Arithemetica 0:8c01a98a2812 168
Arithemetica 0:8c01a98a2812 169 inline std::uint16_t m_spiGenerateReadCmd(const std::uint8_t t_val) const
Arithemetica 0:8c01a98a2812 170 {
Arithemetica 0:8c01a98a2812 171 return t_val << 8U;
Arithemetica 0:8c01a98a2812 172 }
Arithemetica 0:8c01a98a2812 173
Arithemetica 0:8c01a98a2812 174 inline bool m_spiIsDataReady()
Arithemetica 0:8c01a98a2812 175 {
Arithemetica 0:8c01a98a2812 176 return m_drdy.read() == 0;
Arithemetica 0:8c01a98a2812 177 }
Arithemetica 0:8c01a98a2812 178
Arithemetica 0:8c01a98a2812 179 inline void m_processImuRawData()
Arithemetica 0:8c01a98a2812 180 {
Arithemetica 0:8c01a98a2812 181 for (int i = 0; i < 3; ++i) {
Arithemetica 0:8c01a98a2812 182 imuProcessedData.accel[i] = imuRawData.accel[i] / m_accelScaler[i];
Arithemetica 0:8c01a98a2812 183 imuProcessedData.rate[i] = imuRawData.rate[i] / m_gyroScaler[i];
Arithemetica 0:8c01a98a2812 184 }
Arithemetica 0:8c01a98a2812 185 }
Arithemetica 0:8c01a98a2812 186
Arithemetica 0:8c01a98a2812 187 inline void m_processAhrsRawData()
Arithemetica 0:8c01a98a2812 188 {
Arithemetica 0:8c01a98a2812 189 for (int i = 0; i < 3; ++i) {
Arithemetica 0:8c01a98a2812 190 ahrsProcessedData.attitude[i] = ahrsRawData.attitude[i] / m_ahrsScaler[i];
Arithemetica 0:8c01a98a2812 191 }
Arithemetica 0:8c01a98a2812 192 }
Arithemetica 5:e71931fcae33 193
Arithemetica 14:6c31a7ab45f0 194 void m_dataReadyExtiCallback()
Arithemetica 2:f3a7def7a7e1 195 {
Arithemetica 23:3626c7d73505 196 if (m_extiConfig == ImuExtiRcvBothMsg) {
Arithemetica 14:6c31a7ab45f0 197 receiveBurstMsgImpl();
Arithemetica 24:275e886bd61c 198 wait_us(2);
Arithemetica 23:3626c7d73505 199 receiveAhrsMsgImpl();
Arithemetica 23:3626c7d73505 200 } else if (m_extiConfig == ImuExtiRcvNormalMsg) {
Arithemetica 23:3626c7d73505 201 receiveBurstMsgImpl();
Arithemetica 23:3626c7d73505 202 } else if (m_extiConfig == ImuExtiRcvAhrsMsg) {
Arithemetica 16:6583ad08d0d0 203 receiveAhrsMsgImpl();
Arithemetica 14:6c31a7ab45f0 204 }
Arithemetica 2:f3a7def7a7e1 205 }
Arithemetica 16:6583ad08d0d0 206
Arithemetica 14:6c31a7ab45f0 207 ImuDriverStatus receiveBurstMsgImpl(bool t_extended = false)
Arithemetica 15:ca49fdec90fc 208 {
Arithemetica 0:8c01a98a2812 209 if (m_spiIsDataReady()) {
Arithemetica 0:8c01a98a2812 210 std::uint16_t max_data = 0U;
Arithemetica 0:8c01a98a2812 211 std::uint16_t burst_reg = 0U;
Arithemetica 23:3626c7d73505 212 std::uint8_t data_rcved = 0U;
Arithemetica 0:8c01a98a2812 213
Arithemetica 0:8c01a98a2812 214 if (!t_extended) {
Arithemetica 0:8c01a98a2812 215 max_data = 8U;
Arithemetica 0:8c01a98a2812 216 burst_reg = m_spiGenerateReadCmd(ReadBurstDataRegister);
Arithemetica 0:8c01a98a2812 217 } else {
Arithemetica 0:8c01a98a2812 218 max_data = 11U;
Arithemetica 0:8c01a98a2812 219 burst_reg = m_spiGenerateReadCmd(ReadExtBurstDataRegister);
Arithemetica 0:8c01a98a2812 220 }
Arithemetica 0:8c01a98a2812 221
Arithemetica 0:8c01a98a2812 222 m_ss.write(0); // start transfer
Arithemetica 0:8c01a98a2812 223 m_imuSpiWrite(burst_reg);
Arithemetica 23:3626c7d73505 224
Arithemetica 0:8c01a98a2812 225 while(data_rcved < max_data) {
Arithemetica 0:8c01a98a2812 226 const std::uint16_t spi_data = m_imuSpiWrite(0x0000);
Arithemetica 0:8c01a98a2812 227 switch(data_rcved) {
Arithemetica 0:8c01a98a2812 228 case 0:
Arithemetica 0:8c01a98a2812 229 imuRawData.status = spi_data;
Arithemetica 0:8c01a98a2812 230 break;
Arithemetica 0:8c01a98a2812 231 case 1:
Arithemetica 0:8c01a98a2812 232 case 2:
Arithemetica 0:8c01a98a2812 233 case 3:
Arithemetica 0:8c01a98a2812 234 imuRawData.rate[data_rcved - 1] = spi_data;
Arithemetica 0:8c01a98a2812 235 break;
Arithemetica 0:8c01a98a2812 236 case 4:
Arithemetica 0:8c01a98a2812 237 case 5:
Arithemetica 0:8c01a98a2812 238 case 6:
Arithemetica 0:8c01a98a2812 239 imuRawData.accel[data_rcved - 4] = spi_data;
Arithemetica 0:8c01a98a2812 240 break;
Arithemetica 0:8c01a98a2812 241 case 7:
Arithemetica 0:8c01a98a2812 242 imuRawData.temperature = spi_data;
Arithemetica 0:8c01a98a2812 243 break;
Arithemetica 0:8c01a98a2812 244 default:
Arithemetica 0:8c01a98a2812 245 break;
Arithemetica 0:8c01a98a2812 246 }
Arithemetica 0:8c01a98a2812 247
Arithemetica 0:8c01a98a2812 248 ++data_rcved;
Arithemetica 0:8c01a98a2812 249 }
Arithemetica 0:8c01a98a2812 250
Arithemetica 0:8c01a98a2812 251 m_ss.write(1);
Arithemetica 0:8c01a98a2812 252
Arithemetica 0:8c01a98a2812 253 m_processImuRawData();
Arithemetica 0:8c01a98a2812 254 return ImuDriverStatusOK;
Arithemetica 0:8c01a98a2812 255 } else {
Arithemetica 0:8c01a98a2812 256 return ImuDriverStatusDataNotReady;
Arithemetica 0:8c01a98a2812 257 }
Arithemetica 0:8c01a98a2812 258 }
Arithemetica 15:ca49fdec90fc 259
Arithemetica 15:ca49fdec90fc 260 ImuDriverStatus receiveAhrsMsgImpl()
Arithemetica 15:ca49fdec90fc 261 {
Arithemetica 15:ca49fdec90fc 262 if (m_spiIsDataReady()) {
Arithemetica 23:3626c7d73505 263 std::uint8_t data_rcved = 0U;
Arithemetica 15:ca49fdec90fc 264 const std::uint8_t max_data = 5U;
Arithemetica 15:ca49fdec90fc 265 const std::uint16_t ahrs_reg = m_spiGenerateReadCmd(ReadAhrsBurstDataRegister);
Arithemetica 15:ca49fdec90fc 266
Arithemetica 15:ca49fdec90fc 267 m_ss.write(0);
Arithemetica 15:ca49fdec90fc 268 m_imuSpiWrite(ahrs_reg);
Arithemetica 15:ca49fdec90fc 269
Arithemetica 15:ca49fdec90fc 270 while(data_rcved < max_data) {
Arithemetica 15:ca49fdec90fc 271 const std::uint16_t spi_data = m_imuSpiWrite(0x0000);
Arithemetica 15:ca49fdec90fc 272 switch(data_rcved) {
Arithemetica 15:ca49fdec90fc 273 case 0:
Arithemetica 15:ca49fdec90fc 274 ahrsRawData.status = spi_data;
Arithemetica 15:ca49fdec90fc 275 break;
Arithemetica 15:ca49fdec90fc 276 case 1:
Arithemetica 15:ca49fdec90fc 277 case 2:
Arithemetica 15:ca49fdec90fc 278 case 3:
Arithemetica 15:ca49fdec90fc 279 ahrsRawData.attitude[data_rcved - 1] = spi_data;
Arithemetica 15:ca49fdec90fc 280 break;
Arithemetica 15:ca49fdec90fc 281 case 4:
Arithemetica 15:ca49fdec90fc 282 ahrsRawData.temperature = spi_data;
Arithemetica 15:ca49fdec90fc 283 break;
Arithemetica 15:ca49fdec90fc 284 default:
Arithemetica 15:ca49fdec90fc 285 break;
Arithemetica 15:ca49fdec90fc 286 }
Arithemetica 15:ca49fdec90fc 287
Arithemetica 15:ca49fdec90fc 288 ++data_rcved;
Arithemetica 17:629b2f317d0a 289
Arithemetica 15:ca49fdec90fc 290 }
Arithemetica 15:ca49fdec90fc 291
Arithemetica 15:ca49fdec90fc 292 m_ss.write(1);
Arithemetica 15:ca49fdec90fc 293
Arithemetica 15:ca49fdec90fc 294 m_processAhrsRawData();
Arithemetica 15:ca49fdec90fc 295 return ImuDriverStatusOK;
Arithemetica 15:ca49fdec90fc 296 } else {
Arithemetica 15:ca49fdec90fc 297 return ImuDriverStatusDataNotReady;
Arithemetica 15:ca49fdec90fc 298 }
Arithemetica 15:ca49fdec90fc 299 }
Arithemetica 14:6c31a7ab45f0 300 public:
Arithemetica 14:6c31a7ab45f0 301 /**
Arithemetica 14:6c31a7ab45f0 302 * imuRawData contains raw data received from @ref receiveBurstMsg(bool t_extended)
Arithemetica 14:6c31a7ab45f0 303 */
Arithemetica 14:6c31a7ab45f0 304 ImuRawData imuRawData;
Arithemetica 14:6c31a7ab45f0 305
Arithemetica 14:6c31a7ab45f0 306 /**
Arithemetica 14:6c31a7ab45f0 307 * imuProcessedData contains processed data, which is merely scaling operation
Arithemetica 14:6c31a7ab45f0 308 */
Arithemetica 14:6c31a7ab45f0 309 ImuProcessedData imuProcessedData;
Arithemetica 14:6c31a7ab45f0 310
Arithemetica 14:6c31a7ab45f0 311 /**
Arithemetica 14:6c31a7ab45f0 312 * ahrsRawaData contains raw data received from @ref receiveAhrsMsg()
Arithemetica 14:6c31a7ab45f0 313 */
Arithemetica 14:6c31a7ab45f0 314 AhrsRawData ahrsRawData;
Arithemetica 14:6c31a7ab45f0 315
Arithemetica 14:6c31a7ab45f0 316 /**
Arithemetica 14:6c31a7ab45f0 317 * ahrsProcessedData contains processed data, which is merely scaling operation
Arithemetica 14:6c31a7ab45f0 318 */
Arithemetica 14:6c31a7ab45f0 319 AhrsProcessedData ahrsProcessedData;
Arithemetica 14:6c31a7ab45f0 320
Arithemetica 14:6c31a7ab45f0 321 static const int DEFAULT_IMU_ACCEL_SCALER = 4000;
Arithemetica 14:6c31a7ab45f0 322 static const int DEFAULT_IMU_GYRO_SCALER = 100;
Arithemetica 14:6c31a7ab45f0 323 static const int DEFAULT_AHRS_ATTITUDE_SCALER = 90;
Arithemetica 23:3626c7d73505 324
Arithemetica 23:3626c7d73505 325 /**
Arithemetica 23:3626c7d73505 326 *
Arithemetica 23:3626c7d73505 327 */
Arithemetica 14:6c31a7ab45f0 328 explicit ImuDriver(const ImuExtiConfig t_exti_config) : m_extiConfig(t_exti_config), m_spi(Spi), m_rst(rst), m_ss(ss), m_drdy(drdy), m_drdyExti(drdy)
Arithemetica 14:6c31a7ab45f0 329 {
Arithemetica 14:6c31a7ab45f0 330 for (int i = 0; i < 3; ++i) {
Arithemetica 14:6c31a7ab45f0 331 m_gyroScaler[i] = static_cast<float>(DEFAULT_IMU_GYRO_SCALER); // what an idiotic way of initialization LUL
Arithemetica 14:6c31a7ab45f0 332 m_accelScaler[i] = static_cast<float>(DEFAULT_IMU_ACCEL_SCALER); // Oh, I forgot that mbed os2 still stucks at c++98,
Arithemetica 14:6c31a7ab45f0 333 m_ahrsScaler[i] = static_cast<float>(DEFAULT_AHRS_ATTITUDE_SCALER); // how unfortunate LUL
Arithemetica 14:6c31a7ab45f0 334 }
Arithemetica 14:6c31a7ab45f0 335
Arithemetica 14:6c31a7ab45f0 336 if (t_exti_config != ImuExtiRcvNotUsed) {
Arithemetica 14:6c31a7ab45f0 337 m_drdyExti.fall(this, &ImuDriver<Spi, rst, drdy, ss>::m_dataReadyExtiCallback);
Arithemetica 17:629b2f317d0a 338 m_drdyExti.enable_irq();
Arithemetica 14:6c31a7ab45f0 339 }
Arithemetica 14:6c31a7ab45f0 340
Arithemetica 14:6c31a7ab45f0 341 m_spi.format(16, 3);
Arithemetica 17:629b2f317d0a 342 m_spi.frequency();
Arithemetica 14:6c31a7ab45f0 343 }
Arithemetica 14:6c31a7ab45f0 344
Arithemetica 14:6c31a7ab45f0 345 /**
Arithemetica 14:6c31a7ab45f0 346 * @brief This function handles the receiving of burst message function, burst message
Arithemetica 14:6c31a7ab45f0 347 * contains accelerometer (g), gyroscope (deg/s), status and temperature data (Celcius)
Arithemetica 14:6c31a7ab45f0 348 *
Arithemetica 14:6c31a7ab45f0 349 * @param t_extended bool to indicate the message type is extended or not, default false
Arithemetica 14:6c31a7ab45f0 350 *
Arithemetica 14:6c31a7ab45f0 351 * @return ImuDriverStatus to indicate the result of the receive operation
Arithemetica 14:6c31a7ab45f0 352 */
Arithemetica 15:ca49fdec90fc 353 ImuDriverStatus receiveBurstMsg(bool t_extended = false)
Arithemetica 15:ca49fdec90fc 354 {
Arithemetica 15:ca49fdec90fc 355 return (m_extiConfig & ImuExtiRcvNormalMsg ? ImuDriverStatusInvalidCall : receiveBurstMsgImpl(t_extended));
Arithemetica 14:6c31a7ab45f0 356 }
Arithemetica 0:8c01a98a2812 357
Arithemetica 0:8c01a98a2812 358 /**
Arithemetica 5:e71931fcae33 359 * @brief This function handles the receiving of AHRS burst message function, AHRS
Arithemetica 10:d8223969c541 360 * burst message contains the attitude in euler angle (deg).
Arithemetica 0:8c01a98a2812 361 *
Arithemetica 0:8c01a98a2812 362 * @return ImuDriverStatus to indicate the result of the receive operation
Arithemetica 0:8c01a98a2812 363 *
Arithemetica 0:8c01a98a2812 364 * @note This is only suitable for AHRS app, and additional procedure needs to be done
Arithemetica 0:8c01a98a2812 365 * in order to make it work
Arithemetica 0:8c01a98a2812 366 */
Arithemetica 0:8c01a98a2812 367 ImuDriverStatus receiveAhrsMsg()
Arithemetica 0:8c01a98a2812 368 {
Arithemetica 15:ca49fdec90fc 369 return (m_extiConfig & ImuExtiRcvAhrsMsg ? ImuDriverStatusInvalidCall : receiveAhrsMsgImpl());
Arithemetica 15:ca49fdec90fc 370 }
Arithemetica 0:8c01a98a2812 371
Arithemetica 17:629b2f317d0a 372 /**
Arithemetica 17:629b2f317d0a 373 * @brief This function handles the external interrupt option, whether receive AHRS
Arithemetica 17:629b2f317d0a 374 * burst message or normal imu message.
Arithemetica 17:629b2f317d0a 375 *
Arithemetica 17:629b2f317d0a 376 * @return ImuDriverStatus to indicate the result of the receive operation
Arithemetica 17:629b2f317d0a 377 *
Arithemetica 17:629b2f317d0a 378 * @note Never try receiving two messages at the same time
Arithemetica 17:629b2f317d0a 379 */
Arithemetica 21:9430046ebd9d 380 ImuDriverStatus configExti(ImuExtiConfig const& t_exti_config)
Arithemetica 15:ca49fdec90fc 381 {
Arithemetica 14:6c31a7ab45f0 382 m_extiConfig = t_exti_config;
Arithemetica 17:629b2f317d0a 383
Arithemetica 17:629b2f317d0a 384 if (m_extoConfig == ImuExtiRcvNotUsed) {
Arithemetica 17:629b2f317d0a 385 m_drdyExti.disable_irq();
Arithemetica 17:629b2f317d0a 386 } else {
Arithemetica 17:629b2f317d0a 387 m_drdyExti.enable_irq();
Arithemetica 17:629b2f317d0a 388 }
Arithemetica 17:629b2f317d0a 389
Arithemetica 17:629b2f317d0a 390 return ImuDriverStatusOK;
Arithemetica 14:6c31a7ab45f0 391 }
Arithemetica 1:8e31413068af 392 };
Arithemetica 1:8e31413068af 393
Arithemetica 1:8e31413068af 394 #endif // IMU_DRIVER_HPP_