From f3747875647352e2742b56d711f2e318a947aaca Mon Sep 17 00:00:00 2001 From: "Ben V. Brown" Date: Fri, 18 Sep 2020 19:50:50 +1000 Subject: [PATCH] Simplify I2C initalisation --- .../TS100/Core/BSP/Miniware/Model_Config.h | 4 +- .../TS100/Core/BSP/Pine64/I2C_Wrapper.cpp | 23 ++++--- workspace/TS100/Core/Drivers/BMA223.cpp | 18 ++++++ workspace/TS100/Core/Drivers/BMA223.hpp | 42 +++++++++++++ workspace/TS100/Core/Drivers/I2C_Wrapper.hpp | 16 +++-- workspace/TS100/Core/Drivers/LIS2DH12.cpp | 37 +++++------ workspace/TS100/Core/Drivers/LIS2DH12.hpp | 3 +- workspace/TS100/Core/Drivers/MMA8652FC.cpp | 61 ++++++------------- 8 files changed, 120 insertions(+), 84 deletions(-) create mode 100644 workspace/TS100/Core/Drivers/BMA223.cpp create mode 100644 workspace/TS100/Core/Drivers/BMA223.hpp diff --git a/workspace/TS100/Core/BSP/Miniware/Model_Config.h b/workspace/TS100/Core/BSP/Miniware/Model_Config.h index 6cb69a94..0ed53702 100644 --- a/workspace/TS100/Core/BSP/Miniware/Model_Config.h +++ b/workspace/TS100/Core/BSP/Miniware/Model_Config.h @@ -27,7 +27,7 @@ #define ACCEL_LIS #define POW_QC #define TEMP_TMP36 -#define LIS_ORI_FLIP +#define ACCEL_ORI_FLIP #define OLED_FLIP #endif @@ -37,7 +37,7 @@ #define POW_QC #define TEMP_NTC #define I2C_SOFT -#define LIS_ORI_FLIP +#define ACCEL_ORI_FLIP #define OLED_FLIP #endif diff --git a/workspace/TS100/Core/BSP/Pine64/I2C_Wrapper.cpp b/workspace/TS100/Core/BSP/Pine64/I2C_Wrapper.cpp index 6d62cee2..2fba6154 100644 --- a/workspace/TS100/Core/BSP/Pine64/I2C_Wrapper.cpp +++ b/workspace/TS100/Core/BSP/Pine64/I2C_Wrapper.cpp @@ -121,8 +121,7 @@ int i2c_byte_write(int data) { /* wait until the byte is transmitted */ timeout = FLAG_TIMEOUT; - while (((i2c_flag_get(I2C0, I2C_FLAG_TBE)) == RESET) - || ((i2c_flag_get(I2C0, I2C_FLAG_BTC)) == RESET)) { + while (((i2c_flag_get(I2C0, I2C_FLAG_TBE)) == RESET) || ((i2c_flag_get(I2C0, I2C_FLAG_BTC)) == RESET)) { if ((timeout--) == 0) { return 2; } @@ -131,8 +130,7 @@ int i2c_byte_write(int data) { return 1; } -bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress, - uint8_t *pData, uint16_t Size) { +bool FRToSI2C::Mem_Read(uint16_t DevAddress, uint16_t MemAddress, uint8_t *pData, uint16_t Size) { if (!lock()) return false; @@ -253,8 +251,7 @@ uint8_t FRToSI2C::I2C_RegisterRead(uint8_t add, uint8_t reg) { Mem_Read(add, reg, &temp, 1); return temp; } -bool FRToSI2C::Mem_Write(uint16_t DevAddress, uint16_t MemAddress, - uint8_t *pData, uint16_t Size) { +bool FRToSI2C::Mem_Write(uint16_t DevAddress, uint16_t MemAddress, uint8_t *pData, uint16_t Size) { if (!lock()) return false; @@ -397,8 +394,7 @@ bool FRToSI2C::probe(uint16_t DevAddress) { /* wait until ADDSEND bit is set */ int timeout = FLAG_TIMEOUT; while (!i2c_flag_get(I2C0, I2C_FLAG_ADDSEND)) { - if (i2c_flag_get(I2C0, I2C_FLAG_AERR) - || i2c_flag_get(I2C0, I2C_FLAG_BERR)) { + if (i2c_flag_get(I2C0, I2C_FLAG_AERR) || i2c_flag_get(I2C0, I2C_FLAG_BERR)) { i2c_stop(); unlock(); return false; @@ -451,3 +447,14 @@ void FRToSI2C::unlock2() { return; xSemaphoreGive(I2CSemaphore2); } + +bool FRToSI2C::writeRegistersBulk(const uint8_t address, const I2C_REG* registers, const uint8_t registersLength) { + for (int index = 0; index < registersLength; index++) { + if (!I2C_RegisterWrite(address, registers[index].reg, registers[index].val)) { + return false; + } + if (registers[index].pause_ms) + delay_ms(registers[index].pause_ms); + } + return true; +} diff --git a/workspace/TS100/Core/Drivers/BMA223.cpp b/workspace/TS100/Core/Drivers/BMA223.cpp new file mode 100644 index 00000000..9b415f28 --- /dev/null +++ b/workspace/TS100/Core/Drivers/BMA223.cpp @@ -0,0 +1,18 @@ +/* + * BMA223.cpp + * + * Created on: 18 Sep. 2020 + * Author: Ralim + */ + +#include + + +bool BMA223::detect() { +} + +void BMA223::initalize() { +} + +void BMA223::getAxisReadings(int16_t& x, int16_t& y, int16_t& z) { +} diff --git a/workspace/TS100/Core/Drivers/BMA223.hpp b/workspace/TS100/Core/Drivers/BMA223.hpp new file mode 100644 index 00000000..5578d89a --- /dev/null +++ b/workspace/TS100/Core/Drivers/BMA223.hpp @@ -0,0 +1,42 @@ +/* + * BMA223.hpp + * + * Created on: 18 Sep. 2020 + * Author: Ralim + */ + +#ifndef CORE_DRIVERS_BMA223_HPP_ +#define CORE_DRIVERS_BMA223_HPP_ +#include "I2C_Wrapper.hpp" +#include "LIS2DH12_defines.hpp" +#include "BSP.h" + + +class BMA223 { +public: + static bool detect(); + static void initalize(); + //1 = rh, 2,=lh, 8=flat + static Orientation getOrientation() { +#ifdef ACCEL_ORI_FLIP + uint8_t val = (FRToSI2C::I2C_RegisterRead(LIS2DH_I2C_ADDRESS, + LIS_INT2_SRC) >> 2); + if (val == 8) + val = 3; + else if (val == 1) + val = 1; + else if (val == 2) + val = 0; + else + val = 3; + return static_cast(val); +#else + return static_cast((FRToSI2C::I2C_RegisterRead(LIS2DH_I2C_ADDRESS,LIS_INT2_SRC) >> 2) - 1); +#endif + } + static void getAxisReadings(int16_t& x, int16_t& y, int16_t& z); + +private: +}; + +#endif /* CORE_DRIVERS_BMA223_HPP_ */ diff --git a/workspace/TS100/Core/Drivers/I2C_Wrapper.hpp b/workspace/TS100/Core/Drivers/I2C_Wrapper.hpp index d7ed3e66..88be5e62 100644 --- a/workspace/TS100/Core/Drivers/I2C_Wrapper.hpp +++ b/workspace/TS100/Core/Drivers/I2C_Wrapper.hpp @@ -30,22 +30,26 @@ public: static void CpltCallback(); //Normal Tx Callback - static bool Mem_Read(uint16_t DevAddress, uint16_t MemAddress, - uint8_t *pData, uint16_t Size); - static bool Mem_Write(uint16_t DevAddress, uint16_t MemAddress, - uint8_t *pData, uint16_t Size); + static bool Mem_Read(uint16_t DevAddress, uint16_t MemAddress, uint8_t *pData, uint16_t Size); + static bool Mem_Write(uint16_t DevAddress, uint16_t MemAddress, uint8_t *pData, uint16_t Size); //Returns true if device ACK's being addressed static bool probe(uint16_t DevAddress); static bool Transmit(uint16_t DevAddress, uint8_t *pData, uint16_t Size); static void Receive(uint16_t DevAddress, uint8_t *pData, uint16_t Size); - static void TransmitReceive(uint16_t DevAddress, uint8_t *pData_tx, - uint16_t Size_tx, uint8_t *pData_rx, uint16_t Size_rx); + static void TransmitReceive(uint16_t DevAddress, uint8_t *pData_tx, uint16_t Size_tx, uint8_t *pData_rx, uint16_t Size_rx); static bool I2C_RegisterWrite(uint8_t address, uint8_t reg, uint8_t data); static uint8_t I2C_RegisterRead(uint8_t address, uint8_t reg); static void unlock2(); static bool lock2(); + + typedef struct { + const uint8_t reg; // The register to write to + const uint8_t val; // The value to write to this register + const uint8_t pause_ms; //How many ms to pause _after_ writing this reg + } I2C_REG; + static bool writeRegistersBulk(const uint8_t address, const I2C_REG* registers, const uint8_t registersLength); private: static void unlock(); static bool lock(); diff --git a/workspace/TS100/Core/Drivers/LIS2DH12.cpp b/workspace/TS100/Core/Drivers/LIS2DH12.cpp index 888e1231..89cdd9a6 100644 --- a/workspace/TS100/Core/Drivers/LIS2DH12.cpp +++ b/workspace/TS100/Core/Drivers/LIS2DH12.cpp @@ -10,37 +10,28 @@ #include "LIS2DH12.hpp" #include "cmsis_os.h" -typedef struct { - const uint8_t reg; - const uint8_t value; -} LIS_REG; - -static const LIS_REG i2c_registers[] = { { LIS_CTRL_REG1, 0x17 }, // 25Hz - { LIS_CTRL_REG2, 0b00001000 }, // Highpass filter off - { LIS_CTRL_REG3, 0b01100000 }, // Setup interrupt pins - { LIS_CTRL_REG4, 0b00001000 }, // Block update mode off, HR on - { LIS_CTRL_REG5, 0b00000010 }, { LIS_CTRL_REG6, 0b01100010 }, +static const FRToSI2C::I2C_REG i2c_registers[] = { { LIS_CTRL_REG1, 0x17, 0 }, // 25Hz + { LIS_CTRL_REG2, 0b00001000, 0 }, // Highpass filter off + { LIS_CTRL_REG3, 0b01100000, 0 }, // Setup interrupt pins + { LIS_CTRL_REG4, 0b00001000, 0 }, // Block update mode off, HR on + { LIS_CTRL_REG5, 0b00000010, 0 }, // + { LIS_CTRL_REG6, 0b01100010, 0 }, //Basically setup the unit to run, and enable 4D orientation detection - { LIS_INT2_CFG, 0b01111110 }, //setup for movement detection - { LIS_INT2_THS, 0x28 }, { LIS_INT2_DURATION, 64 }, { - LIS_INT1_CFG, 0b01111110 }, { LIS_INT1_THS, 0x28 }, { - LIS_INT1_DURATION, 64 } }; + { LIS_INT2_CFG, 0b01111110, 0 }, //setup for movement detection + { LIS_INT2_THS, 0x28, 0 }, // + { LIS_INT2_DURATION, 64, 0 }, // + { LIS_INT1_CFG, 0b01111110, 0 }, // + { LIS_INT1_THS, 0x28, 0 }, // + { LIS_INT1_DURATION, 64, 0 } }; void LIS2DH12::initalize() { - for (size_t index = 0; - index < (sizeof(i2c_registers) / sizeof(i2c_registers[0])); - index++) { - FRToSI2C::I2C_RegisterWrite(LIS2DH_I2C_ADDRESS, - i2c_registers[index].reg, i2c_registers[index].value); - } + FRToSI2C::writeRegistersBulk(LIS2DH_I2C_ADDRESS, i2c_registers, sizeof(i2c_registers) / sizeof(i2c_registers[0])); } void LIS2DH12::getAxisReadings(int16_t &x, int16_t &y, int16_t &z) { std::array sensorData; - FRToSI2C::Mem_Read(LIS2DH_I2C_ADDRESS, 0xA8, - reinterpret_cast(sensorData.begin()), - sensorData.size() * sizeof(int16_t)); + FRToSI2C::Mem_Read(LIS2DH_I2C_ADDRESS, 0xA8, reinterpret_cast(sensorData.begin()), sensorData.size() * sizeof(int16_t)); x = sensorData[0]; y = sensorData[1]; diff --git a/workspace/TS100/Core/Drivers/LIS2DH12.hpp b/workspace/TS100/Core/Drivers/LIS2DH12.hpp index 79346e98..8586ec21 100644 --- a/workspace/TS100/Core/Drivers/LIS2DH12.hpp +++ b/workspace/TS100/Core/Drivers/LIS2DH12.hpp @@ -29,8 +29,7 @@ public: else val = 3; return static_cast(val); -#endif -#ifdef MODEL_TS100 +#else return static_cast((FRToSI2C::I2C_RegisterRead(LIS2DH_I2C_ADDRESS,LIS_INT2_SRC) >> 2) - 1); #endif } diff --git a/workspace/TS100/Core/Drivers/MMA8652FC.cpp b/workspace/TS100/Core/Drivers/MMA8652FC.cpp index cd41488a..83e922e1 100644 --- a/workspace/TS100/Core/Drivers/MMA8652FC.cpp +++ b/workspace/TS100/Core/Drivers/MMA8652FC.cpp @@ -10,45 +10,25 @@ #include "MMA8652FC.hpp" #include "cmsis_os.h" -typedef struct { - const uint8_t reg; - const uint8_t val; -} MMA_REG; -static const MMA_REG i2c_registers[] = { { CTRL_REG2, 0 }, //Normal mode - { CTRL_REG2, 0x40 }, // Reset all registers to POR values - { FF_MT_CFG_REG, 0x78 }, // Enable motion detection for X, Y, Z axis, latch disabled - { PL_CFG_REG, 0x40 }, //Enable the orientation detection - { PL_COUNT_REG, 200 }, //200 count debounce - { PL_BF_ZCOMP_REG, 0b01000111 }, //Set the threshold to 42 degrees - { P_L_THS_REG, 0b10011100 }, //Up the trip angles - { CTRL_REG4, 0x01 | (1 << 4) }, // Enable dataready interrupt & orientation interrupt - { CTRL_REG5, 0x01 }, // Route data ready interrupts to INT1 ->PB5 ->EXTI5, leaving orientation routed to INT2 - { CTRL_REG2, 0x12 }, //Set maximum resolution oversampling - { XYZ_DATA_CFG_REG, (1 << 4) }, //select high pass filtered data - { HP_FILTER_CUTOFF_REG, 0x03 }, //select high pass filtered data - { CTRL_REG1, 0x19 } // ODR=12 Hz, Active mode +static const FRToSI2C::I2C_REG i2c_registers[] = { { CTRL_REG2, 0, 0 }, //Normal mode + { CTRL_REG2, 0x40, 2 }, // Reset all registers to POR values + { FF_MT_CFG_REG, 0x78, 0 }, // Enable motion detection for X, Y, Z axis, latch disabled + { PL_CFG_REG, 0x40, 0 }, //Enable the orientation detection + { PL_COUNT_REG, 200, 0 }, //200 count debounce + { PL_BF_ZCOMP_REG, 0b01000111, 0 }, //Set the threshold to 42 degrees + { P_L_THS_REG, 0b10011100, 0 }, //Up the trip angles + { CTRL_REG4, 0x01 | (1 << 4), 0 }, // Enable dataready interrupt & orientation interrupt + { CTRL_REG5, 0x01, 0 }, // Route data ready interrupts to INT1 ->PB5 ->EXTI5, leaving orientation routed to INT2 + { CTRL_REG2, 0x12, 0 }, //Set maximum resolution oversampling + { XYZ_DATA_CFG_REG, (1 << 4), 0 }, //select high pass filtered data + { HP_FILTER_CUTOFF_REG, 0x03, 0 }, //select high pass filtered data + { CTRL_REG1, 0x19, 0 } // ODR=12 Hz, Active mode }; void MMA8652FC::initalize() { - size_t index = 0; + FRToSI2C::writeRegistersBulk(MMA8652FC_I2C_ADDRESS, i2c_registers, sizeof(i2c_registers) / sizeof(i2c_registers[0])); - //send all the init commands to the unit - - FRToSI2C::I2C_RegisterWrite(MMA8652FC_I2C_ADDRESS, i2c_registers[index].reg, - i2c_registers[index].val); - index++; - FRToSI2C::I2C_RegisterWrite(MMA8652FC_I2C_ADDRESS, i2c_registers[index].reg, - i2c_registers[index].val); - index++; - - delay_ms(2); // ~1ms delay - - while (index < (sizeof(i2c_registers) / sizeof(i2c_registers[0]))) { - FRToSI2C::I2C_RegisterWrite(MMA8652FC_I2C_ADDRESS, - i2c_registers[index].reg, i2c_registers[index].val); - index++; - } } Orientation MMA8652FC::getOrientation() { @@ -71,16 +51,11 @@ Orientation MMA8652FC::getOrientation() { void MMA8652FC::getAxisReadings(int16_t &x, int16_t &y, int16_t &z) { std::array sensorData; - FRToSI2C::Mem_Read(MMA8652FC_I2C_ADDRESS, OUT_X_MSB_REG, - reinterpret_cast(sensorData.begin()), - sensorData.size() * sizeof(int16_t)); + FRToSI2C::Mem_Read(MMA8652FC_I2C_ADDRESS, OUT_X_MSB_REG, reinterpret_cast(sensorData.begin()), sensorData.size() * sizeof(int16_t)); - x = static_cast(__builtin_bswap16( - *reinterpret_cast(&sensorData[0]))); - y = static_cast(__builtin_bswap16( - *reinterpret_cast(&sensorData[1]))); - z = static_cast(__builtin_bswap16( - *reinterpret_cast(&sensorData[2]))); + x = static_cast(__builtin_bswap16(*reinterpret_cast(&sensorData[0]))); + y = static_cast(__builtin_bswap16(*reinterpret_cast(&sensorData[1]))); + z = static_cast(__builtin_bswap16(*reinterpret_cast(&sensorData[2]))); } bool MMA8652FC::detect() {