diff --git a/radio/src/CMakeLists.txt b/radio/src/CMakeLists.txt index 4b7a7457d..4c602f75e 100644 --- a/radio/src/CMakeLists.txt +++ b/radio/src/CMakeLists.txt @@ -349,6 +349,10 @@ if(FLYSKY_HALL_STICKS_REVERSE) add_definitions(-DFLYSKY_HALL_STICKS_REVERSE) endif() +if(IMU_LSM6DS33) + add_definitions(-DIMU_LSM6DS33) +endif() + if(EEPROM_VARIANT_NEEDED) add_definitions(-DEEPROM_VARIANT=${EEPROM_VARIANT}) endif() diff --git a/radio/src/gui/colorlcd/radio_diaganas.cpp b/radio/src/gui/colorlcd/radio_diaganas.cpp index 25f7f2544..879a19376 100644 --- a/radio/src/gui/colorlcd/radio_diaganas.cpp +++ b/radio/src/gui/colorlcd/radio_diaganas.cpp @@ -22,6 +22,10 @@ #include "radio_diaganas.h" #include "libopenui.h" +#if defined(IMU_LSM6DS33) +#include "imu_lsm6ds33.h" +#endif + constexpr coord_t ANA_OFFSET = 150; class RadioAnalogsDiagsWindow: public Window { @@ -53,6 +57,20 @@ class RadioAnalogsDiagsWindow: public Window { dc->drawNumber(x + ANA_OFFSET, y, (int16_t) calibratedAnalogs[CONVERT_MODE(i)] * 25 / 256, RIGHT); } +#if !defined(SIMU) && defined(IMU_LSM6DS33) + coord_t yimu = MENU_CONTENT_TOP + 3 * FH; + coord_t ximu = MENUS_MARGIN_LEFT; + char imudata[80]; + sprintf(imudata, "IMU temp.: %.2f deg.C, Gyro XYZ [rad/s]: %.2f, %.2f, %.2f", + IMUoutput.fTemperatureDegC, + IMUoutput.fGyroXradps, IMUoutput.fGyroYradps, IMUoutput.fGyroZradps); + dc->drawText(ximu, yimu, imudata); + yimu = MENU_CONTENT_TOP + 4 * FH; + sprintf(imudata, "Linear acceleration XYZ [m/s^2]: %.2f %.2f %.2f", + IMUoutput.fAccX, IMUoutput.fAccY, IMUoutput.fAccZ); + dc->drawText(ximu, yimu, imudata); +#endif + #if defined(HARDWARE_TOUCH) constexpr coord_t y = MENU_CONTENT_TOP + 5 * FH; diff --git a/radio/src/options.h b/radio/src/options.h index 9918baa60..1e56afb69 100644 --- a/radio/src/options.h +++ b/radio/src/options.h @@ -101,6 +101,9 @@ static const char * const options[] = { #if defined(FLYSKY_HALL_STICKS) "flyskyhallsticks", #endif +#if defined(IMU_LSM6DS33) + "lsm6ds33", +#endif #if defined(BIND_KEY) "bindkey", #endif diff --git a/radio/src/targets/common/arm/stm32/bootloader/boot.cpp b/radio/src/targets/common/arm/stm32/bootloader/boot.cpp index 0d6383752..3bbcc3b20 100644 --- a/radio/src/targets/common/arm/stm32/bootloader/boot.cpp +++ b/radio/src/targets/common/arm/stm32/bootloader/boot.cpp @@ -205,11 +205,11 @@ int main() RCC_AHB1PeriphClockCmd(PWR_RCC_AHB1Periph | KEYS_RCC_AHB1Periph | LCD_RCC_AHB1Periph | BACKLIGHT_RCC_AHB1Periph | AUX_SERIAL_RCC_AHB1Periph | AUX2_SERIAL_RCC_AHB1Periph | - I2C_RCC_AHB1Periph | KEYS_BACKLIGHT_RCC_AHB1Periph | + I2C_B1_RCC_AHB1Periph | KEYS_BACKLIGHT_RCC_AHB1Periph | SD_RCC_AHB1Periph, ENABLE); RCC_APB1PeriphClockCmd(ROTARY_ENCODER_RCC_APB1Periph | LCD_RCC_APB1Periph | BACKLIGHT_RCC_APB1Periph | - INTERRUPT_xMS_RCC_APB1Periph | I2C_RCC_APB1Periph | + INTERRUPT_xMS_RCC_APB1Periph | I2C_B1_RCC_APB1Periph | AUX_SERIAL_RCC_APB1Periph | AUX2_SERIAL_RCC_APB1Periph | SD_RCC_APB1Periph, ENABLE); diff --git a/radio/src/targets/common/arm/stm32/lsm6ds_driver.cpp b/radio/src/targets/common/arm/stm32/lsm6ds_driver.cpp index 4a33009b4..d547ac2b3 100644 --- a/radio/src/targets/common/arm/stm32/lsm6ds_driver.cpp +++ b/radio/src/targets/common/arm/stm32/lsm6ds_driver.cpp @@ -193,38 +193,38 @@ static const char configure[][2] = { static void i2c2Init() { - I2C_DeInit(I2CX); + I2C_DeInit(I2C_B2); I2C_InitTypeDef I2C_InitStructure; - I2C_InitStructure.I2C_ClockSpeed = I2CX_SPEED; + I2C_InitStructure.I2C_ClockSpeed = I2C_B2_SPEED; I2C_InitStructure.I2C_DutyCycle = I2C_DutyCycle_2; I2C_InitStructure.I2C_OwnAddress1 = 0x00; I2C_InitStructure.I2C_Mode = I2C_Mode_I2C; I2C_InitStructure.I2C_Ack = I2C_Ack_Enable; I2C_InitStructure.I2C_AcknowledgedAddress = I2C_AcknowledgedAddress_7bit; - I2C_Init(I2CX, &I2C_InitStructure); - I2C_Cmd(I2CX, ENABLE); + I2C_Init(I2C_B2, &I2C_InitStructure); + I2C_Cmd(I2C_B2, ENABLE); - GPIO_PinAFConfig(I2CX_SCL_GPIO, I2CX_SCL_GPIO_PinSource, I2CX_GPIO_AF); - GPIO_PinAFConfig(I2CX_SDA_GPIO, I2CX_SDA_GPIO_PinSource, I2CX_GPIO_AF); + GPIO_PinAFConfig(I2C_B2_SCL_GPIO, I2C_B2_SCL_GPIO_PinSource, I2C_B2_GPIO_AF); + GPIO_PinAFConfig(I2C_B2_SDA_GPIO, I2C_B2_SDA_GPIO_PinSource, I2C_B2_GPIO_AF); GPIO_InitTypeDef GPIO_InitStructure; - GPIO_InitStructure.GPIO_Pin = I2CX_SCL_GPIO_PIN; + GPIO_InitStructure.GPIO_Pin = I2C_B2_SCL_GPIO_PIN; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF; GPIO_InitStructure.GPIO_OType = GPIO_OType_OD; GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; - GPIO_Init(I2CX_SCL_GPIO, &GPIO_InitStructure); + GPIO_Init(I2C_B2_SCL_GPIO, &GPIO_InitStructure); - GPIO_InitStructure.GPIO_Pin = I2CX_SDA_GPIO_PIN; - GPIO_Init(I2CX_SDA_GPIO, &GPIO_InitStructure); + GPIO_InitStructure.GPIO_Pin = I2C_B2_SDA_GPIO_PIN; + GPIO_Init(I2C_B2_SDA_GPIO, &GPIO_InitStructure); } #define I2C_TIMEOUT_MAX 10000 bool I2C2_WaitEvent(uint32_t event) { uint32_t timeout = I2C_TIMEOUT_MAX; - while (!I2C_CheckEvent(I2CX, event)) { + while (!I2C_CheckEvent(I2C_B2, event)) { if ((timeout--) == 0) return false; } return true; @@ -233,7 +233,7 @@ bool I2C2_WaitEvent(uint32_t event) bool I2C2_WaitEventCleared(uint32_t event) { uint32_t timeout = I2C_TIMEOUT_MAX; - while (I2C_CheckEvent(I2CX, event)) { + while (I2C_CheckEvent(I2C_B2, event)) { if ((timeout--) == 0) { TRACE("I2C Timeout!"); return false; @@ -247,23 +247,23 @@ int setGyroRegister(uint8_t address, uint8_t value) if (!I2C2_WaitEventCleared(I2C_FLAG_BUSY)) return -1; - I2C_GenerateSTART(I2CX, ENABLE); + I2C_GenerateSTART(I2C_B2, ENABLE); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) return -1; - I2C_Send7bitAddress(I2CX, LSM6DS_ADDRESS, I2C_Direction_Transmitter); + I2C_Send7bitAddress(I2C_B2, LSM6DS_ADDRESS, I2C_Direction_Transmitter); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)) return -1; - I2C_SendData(I2CX, address); + I2C_SendData(I2C_B2, address); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTING)) return -1; - I2C_SendData(I2CX, value); + I2C_SendData(I2C_B2, value); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTED)) return -1; - I2C_GenerateSTOP(I2CX, ENABLE); + I2C_GenerateSTOP(I2C_B2, ENABLE); return 0; } @@ -273,31 +273,31 @@ int readGyroRegister(uint8_t address) if (!I2C2_WaitEventCleared(I2C_FLAG_BUSY)) return -1; - I2C_GenerateSTART(I2CX, ENABLE); + I2C_GenerateSTART(I2C_B2, ENABLE); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) return -1; - I2C_Send7bitAddress(I2CX, LSM6DS_ADDRESS, I2C_Direction_Transmitter); + I2C_Send7bitAddress(I2C_B2, LSM6DS_ADDRESS, I2C_Direction_Transmitter); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)) return -1; - I2C_SendData(I2CX, address); + I2C_SendData(I2C_B2, address); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTED)) return -1; - I2C_GenerateSTART(I2CX, ENABLE); + I2C_GenerateSTART(I2C_B2, ENABLE); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) return -1; - I2C_Send7bitAddress(I2CX, LSM6DS_ADDRESS, I2C_Direction_Receiver); + I2C_Send7bitAddress(I2C_B2, LSM6DS_ADDRESS, I2C_Direction_Receiver); - I2C_AcknowledgeConfig(I2CX, DISABLE); + I2C_AcknowledgeConfig(I2C_B2, DISABLE); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_BYTE_RECEIVED)) return -1; - uint8_t value = I2C_ReceiveData(I2CX); + uint8_t value = I2C_ReceiveData(I2C_B2); - I2C_GenerateSTOP(I2CX, ENABLE); + I2C_GenerateSTOP(I2C_B2, ENABLE); return value; } @@ -328,33 +328,33 @@ int gyroRead(uint8_t buffer[GYRO_BUFFER_LENGTH]) if (!I2C2_WaitEventCleared(I2C_FLAG_BUSY)) return -1; - I2C_GenerateSTART(I2CX, ENABLE); + I2C_GenerateSTART(I2C_B2, ENABLE); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) return -1; - I2C_Send7bitAddress(I2CX, LSM6DS_ADDRESS, I2C_Direction_Transmitter); + I2C_Send7bitAddress(I2C_B2, LSM6DS_ADDRESS, I2C_Direction_Transmitter); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)) return -1; - I2C_SendData(I2CX, LSM6DS_GYRO_OUT_X_L_ADDR); + I2C_SendData(I2C_B2, LSM6DS_GYRO_OUT_X_L_ADDR); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTED)) return -1; - I2C_GenerateSTART(I2CX, ENABLE); + I2C_GenerateSTART(I2C_B2, ENABLE); if (!I2C2_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) return -1; - I2C_Send7bitAddress(I2CX, LSM6DS_ADDRESS, I2C_Direction_Receiver); + I2C_Send7bitAddress(I2C_B2, LSM6DS_ADDRESS, I2C_Direction_Receiver); - I2C_AcknowledgeConfig(I2CX, ENABLE); + I2C_AcknowledgeConfig(I2C_B2, ENABLE); for (uint8_t i=0; iInstance==I2C1) || (hi2c->Instance==I2C3)) // TP + { + GPIO_PinAFConfig(I2C_B1_GPIO, I2C_B1_SCL_GPIO_PinSource, I2C_B1_GPIO_AF); + GPIO_PinAFConfig(I2C_B1_GPIO, I2C_B1_SDA_GPIO_PinSource, I2C_B1_GPIO_AF); + + GPIO_InitStruct.GPIO_Pin = I2C_B1_SCL_GPIO_PIN | I2C_B1_SDA_GPIO_PIN; GPIO_InitStruct.GPIO_Speed = GPIO_Speed_2MHz; GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF; GPIO_InitStruct.GPIO_OType = GPIO_OType_OD; GPIO_InitStruct.GPIO_PuPd = GPIO_PuPd_NOPULL; - GPIO_Init(I2C_GPIO, &GPIO_InitStruct); + GPIO_Init(I2C_B1_GPIO, &GPIO_InitStruct); + } - /* Peripheral clock enable */ - if (I2C == I2C1) - __HAL_RCC_I2C1_CLK_ENABLE(); - else if (I2C == I2C2) - __HAL_RCC_I2C2_CLK_ENABLE(); - else if (I2C == I2C3) - __HAL_RCC_I2C3_CLK_ENABLE(); - else - TRACE("I2C ERROR: HAL_I2C_MspInit() I2C misconfiguration"); +#if defined(IMU_LSM6DS33) + if (hi2c->Instance==I2C2) // IMU + { + GPIO_PinAFConfig(I2C_B2_GPIO, I2C_B2_SCL_GPIO_PinSource, I2C_B2_GPIO_AF); + GPIO_PinAFConfig(I2C_B2_GPIO, I2C_B2_SDA_GPIO_PinSource, I2C_B2_GPIO_AF); + + GPIO_InitStruct.GPIO_Pin = I2C_B2_SCL_GPIO_PIN | I2C_B2_SDA_GPIO_PIN; + GPIO_InitStruct.GPIO_Speed = GPIO_Speed_2MHz; + GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF; + GPIO_InitStruct.GPIO_OType = GPIO_OType_OD; + GPIO_InitStruct.GPIO_PuPd = GPIO_PuPd_NOPULL; + GPIO_Init(I2C_B2_GPIO, &GPIO_InitStruct); + } +#endif + + /* Peripheral clock enable */ + if (I2C_B1 == I2C1) + __HAL_RCC_I2C1_CLK_ENABLE(); + else if (I2C_B1 == I2C2) + __HAL_RCC_I2C2_CLK_ENABLE(); + else if (I2C_B1 == I2C3) + __HAL_RCC_I2C3_CLK_ENABLE(); + else + TRACE("I2C B1 ERROR: HAL_I2C_MspInit() I2C misconfiguration"); + +#if defined(IMU_LSM6DS33) + /* Peripheral clock enable */ + if (I2C_B2 == I2C1) + __HAL_RCC_I2C1_CLK_ENABLE(); + else if (I2C_B2 == I2C2) + __HAL_RCC_I2C2_CLK_ENABLE(); + else if (I2C_B2 == I2C3) + __HAL_RCC_I2C3_CLK_ENABLE(); + else + TRACE("I2C B2 ERROR: HAL_I2C_MspInit() I2C misconfiguration"); +#endif } /* De-initializes the GPIOx peripheral registers to their default reset values. @@ -154,15 +198,15 @@ void HAL_I2C_MspDeInit(I2C_HandleTypeDef* hi2c) GPIO_InitTypeDef GPIO_InitStructure; /* Configure the default Alternate Function in current IO */ - GPIO_PinAFConfig(I2C_GPIO, I2C_SCL_GPIO_PinSource, 0); - GPIO_PinAFConfig(I2C_GPIO, I2C_SDA_GPIO_PinSource, 0); + GPIO_PinAFConfig(I2C_B1_GPIO, I2C_B1_SCL_GPIO_PinSource, 0); + GPIO_PinAFConfig(I2C_B1_GPIO, I2C_B1_SDA_GPIO_PinSource, 0); - GPIO_InitStructure.GPIO_Pin = I2C_SCL_GPIO_PIN | I2C_SDA_GPIO_PIN; + GPIO_InitStructure.GPIO_Pin = I2C_B1_SCL_GPIO_PIN | I2C_B1_SDA_GPIO_PIN; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; /* Configure a low value for IO Speed */ GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; /* Configure IO Direction in Input Floating Mode */ GPIO_InitStructure.GPIO_OType = GPIO_OType_OD; /* Leave the configuration to Open Drain */ GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; /* Deactivate the Pull-up and Pull-down resistor for the current IO */ - GPIO_Init(I2C_GPIO, &GPIO_InitStructure); + GPIO_Init(I2C_B1_GPIO, &GPIO_InitStructure); } /* Initializes the I2C according to the specified parameters @@ -199,7 +243,7 @@ HAL_StatusTypeDef HAL_I2C_Init(I2C_HandleTypeDef *hi2c) hi2c->Lock = HAL_UNLOCKED; /* Init the low level hardware : GPIO, CLOCK, NVIC */ - HAL_I2C_MspInit(hi2c); + I2C_MspInit(hi2c); } hi2c->State = HAL_I2C_STATE_BUSY; diff --git a/radio/src/targets/horus/imu_lsm6ds33.cpp b/radio/src/targets/horus/imu_lsm6ds33.cpp new file mode 100644 index 000000000..2493207b8 --- /dev/null +++ b/radio/src/targets/horus/imu_lsm6ds33.cpp @@ -0,0 +1,263 @@ +/* + * Copyright (C) EdgeTX + * + * Based on code named + * opentx - https://github.com/opentx/opentx + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include "opentx.h" +#include "i2c_driver.h" +#include "imu_lsm6ds33.h" + +I2C_HandleTypeDef hi2c2; + +sIMUsettings IMUsettings = {-1, -1.0, -1, -1, -1.0}; +sIMUoutput IMUoutput = {0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0}; + +float fIMUtemp = 0.0; + +bool I2C_LSM6DS33_ReadRegister(uint8_t reg, uint8_t * buf, uint8_t len) +{ + if (HAL_I2C_Master_Transmit(&hi2c2, LSM6DS33_I2C_ADDR << 1, ®, 1, 10000) != HAL_OK) + { + TRACE("I2C B2 ERROR: ReadRegister write reg. address failed"); + return false; + } + + if (HAL_I2C_Master_Receive(&hi2c2, LSM6DS33_I2C_ADDR << 1, buf, len, 10000) != HAL_OK) + { + TRACE("I2C B2 ERROR: ReadRegister read register failed"); + return false; + } + return true; +} + +bool I2C_LSM6DS33_WriteRegister(uint8_t reg, uint8_t * buf, uint8_t len) +{ + uint8_t uAddrAndBuf[15]; + uAddrAndBuf[0] = reg; + + if (len > 0) + { + for (int i = 0;i < len;i++) + { + uAddrAndBuf[i + 1] = buf[i]; + } + } + + if (HAL_I2C_Master_Transmit(&hi2c2, LSM6DS33_I2C_ADDR << 1, uAddrAndBuf, len + 1, 10000) != HAL_OK) + { + TRACE("I2C B2 ERROR: WriteRegister failed"); + return false; + } + return true; +} + +bool IMUgetConf(void) +{ + uint8_t ui8_regs[2] = {0}; + + if (!I2C_LSM6DS33_ReadRegister(LSM6DS33_CTRL1_XL_ADDR, ui8_regs, 2)) + { + TRACE("ERROR: LSM6DS33 did not respond to I2C address"); + return false; + } + + switch ((ui8_regs[0] >> 4) & 0x0F) // CTRL1_XL + { + case LSM6DS33_ODR_0Hz: IMUsettings.linacc_odr = 0; TRACE("LSM6DS33 lin. acc. output turned off"); break; + case LSM6DS33_ODR_12_5Hz: IMUsettings.linacc_odr = 13; break; + case LSM6DS33_ODR_26Hz: IMUsettings.linacc_odr = 26; break; + case LSM6DS33_ODR_52Hz: IMUsettings.linacc_odr = 52; break; + case LSM6DS33_ODR_104Hz: IMUsettings.linacc_odr = 104; break; + case LSM6DS33_ODR_208Hz: IMUsettings.linacc_odr = 208; break; + case LSM6DS33_ODR_416Hz: IMUsettings.linacc_odr = 417; break; + case LSM6DS33_ODR_833Hz: IMUsettings.linacc_odr = 833; break; + case LSM6DS33_ODR_1_66kHz: IMUsettings.linacc_odr = 1667; break; + case LSM6DS33_ODR_3_33kHz: IMUsettings.linacc_odr = 3333; break; + case LSM6DS33_ODR_6_66kHz: IMUsettings.linacc_odr = 6667; break; + default: TRACE("ERROR: LSM6DS33 lin.acc. output data rate at illegal setting"); return false; break; + } + if (IMUsettings.linacc_odr > 0) TRACE("LSM6DS33 lin. acc. output at %i Hz", IMUsettings.linacc_odr); + + switch ((ui8_regs[0] >> 2) & 0x03) + { + case LSM6DS33_LA_FS_2G: IMUsettings.linacc_mG = 0.061; break; + case LSM6DS33_LA_FS_4G: IMUsettings.linacc_mG = 0.122; break; + case LSM6DS33_LA_FS_8G: IMUsettings.linacc_mG = 0.244; break; + case LSM6DS33_LA_FS_16G: IMUsettings.linacc_mG = 0.488; break; + default: TRACE("ERROR: LSM6DS33 lin. acc full scale value at illegal setting"); return false; break; + } + TRACE("LSM6DS33 lin. acc. resolution %.2f G", IMUsettings.linacc_mG); + + switch ((ui8_regs[0] >> 2) & 0x03) + { + case LSM6DS33_LA_AABW_400Hz: IMUsettings.linacc_aabw = 400; break; + case LSM6DS33_LA_AABW_200Hz: IMUsettings.linacc_aabw = 200; break; + case LSM6DS33_LA_AABW_100Hz: IMUsettings.linacc_aabw = 100; break; + case LSM6DS33_LA_AABW_50Hz: IMUsettings.linacc_aabw = 50; break; + default: TRACE("ERROR: LSM6DS33 lin. acc anti aliasing bandwidth at illegal setting"); return false; break; + } + TRACE("LSM6DS33 lin. acc. anti aliasing bandwidth at %i Hz", IMUsettings.linacc_aabw); + + switch ((ui8_regs[1] >> 4) & 0x0F) // CTRL2_G + { + case LSM6DS33_ODR_0Hz: IMUsettings.gyro_odr = 0; TRACE("LSM6DS33 gyro output turned off"); break; + case LSM6DS33_ODR_12_5Hz: IMUsettings.gyro_odr = 13; break; + case LSM6DS33_ODR_26Hz: IMUsettings.gyro_odr = 26; break; + case LSM6DS33_ODR_52Hz: IMUsettings.gyro_odr = 52; break; + case LSM6DS33_ODR_104Hz: IMUsettings.gyro_odr = 104; break; + case LSM6DS33_ODR_208Hz: IMUsettings.gyro_odr = 208; break; + case LSM6DS33_ODR_416Hz: IMUsettings.gyro_odr = 417; break; + case LSM6DS33_ODR_833Hz: IMUsettings.gyro_odr = 833; break; + case LSM6DS33_ODR_1_66kHz: IMUsettings.gyro_odr = 1667; break; + default: TRACE("ERROR: LSM6DS33 gyro output data rate at illegal setting"); return false; break; + } + if (IMUsettings.gyro_odr > 0) TRACE("LSM6DS33 gyro output at %i Hz", IMUsettings.gyro_odr); + + switch ((ui8_regs[1] >> 1) & 0x07) + { + case LSM6DS33_GY_FS_125dps: IMUsettings.gyro_mDPS = 4.375; break; + case LSM6DS33_GY_FS_250dps: IMUsettings.gyro_mDPS = 8.75; break; + case LSM6DS33_GY_FS_500dps: IMUsettings.gyro_mDPS = 17.5; break; + case LSM6DS33_GY_FS_1000dps: IMUsettings.gyro_mDPS = 35.0; break; + case LSM6DS33_GY_FS_2000dps: IMUsettings.gyro_mDPS = 70.0; break; + default: TRACE("ERROR: LSM6DS33 gyro full scale value at illegal setting"); return false; break; + } + TRACE("LSM6DS33 raw gyro resolution: %.2f milli-degrees/sec.", IMUsettings.gyro_mDPS); + return true; +} + +void init_imu_i2c(void) +{ + TRACE("I2C IMU Init"); + + hi2c2.Instance = I2C_B2; + hi2c2.Init.ClockSpeed = I2C_B2_CLK_RATE; + hi2c2.Init.DutyCycle = I2C_DUTYCYCLE_2; + hi2c2.Init.OwnAddress1 = 0; + hi2c2.Init.AddressingMode = I2C_ADDRESSINGMODE_7BIT; + hi2c2.Init.DualAddressMode = I2C_DUALADDRESS_DISABLE; + hi2c2.Init.OwnAddress2 = 0; + hi2c2.Init.GeneralCallMode = I2C_GENERALCALL_DISABLE; + hi2c2.Init.NoStretchMode = I2C_NOSTRETCH_DISABLE; + if (HAL_I2C_Init(&hi2c2) != HAL_OK) + { + TRACE("I2C B2 ERROR: HAL_I2C_Init() failed"); + } + // Configure Analogue filter + if (HAL_I2CEx_ConfigAnalogFilter(&hi2c2, I2C_ANALOGFILTER_ENABLE) != HAL_OK) + { + TRACE("I2C B2 ERROR: HAL_I2CEx_ConfigAnalogFilter() failed"); + } + // Configure Digital filter + if (HAL_I2CEx_ConfigDigitalFilter(&hi2c2, 0) != HAL_OK) + { + TRACE("I2C B2 ERROR: HAL_I2CEx_ConfigDigitalFilter() failed"); + } +} + +bool imu_lsm6ds33_init(void) +{ + uint8_t ui8_reg[2] = {0}; + + GPIO_SetBits(AUX_I2C_B2_PWR_GPIO, AUX_I2C_B2_PWR_GPIO_PIN); // Turn on AUX1 power + + init_imu_i2c(); + + if (!I2C_LSM6DS33_ReadRegister(LSM6DS33_WHO_AM_I_ADDR, ui8_reg, 1)) + { + TRACE("ERROR: LSM6DS33 did not respond to I2C address"); + return false; + } + if (ui8_reg[0] != LSM6DS33_WHOAMI) + { + TRACE("LSM6DS33 ERROR: Product ID read failes"); + return false; + } + TRACE("LSM6DS33 detected"); + + // Set IMU configuration + ui8_reg[0] = (LSM6DS33_ODR_104Hz << 4) | (LSM6DS33_LA_FS_4G << 2) | LSM6DS33_LA_AABW_100Hz; // Linear acceleration configuration + ui8_reg[1] = (LSM6DS33_ODR_104Hz << 4) | (LSM6DS33_GY_FS_125dps < 1); // Gyro configuration + if (!I2C_LSM6DS33_WriteRegister(LSM6DS33_CTRL1_XL_ADDR, ui8_reg, 2)) + { + TRACE("ERROR: Failed to write LSM6DS33 configuration"); + return false; + } + + if (!IMUgetConf()) + { + TRACE("ERROR: Failed ro read LSM6DS33 configuration"); + return false; + } + return true; +} + +bool imu_lsm6ds33_read() +{ + uint8_t ui8_regs[14] = {0}; + + int16_t i16_rawTemperature = 0; + int16_t i16_rawGyroX = 0; + int16_t i16_rawGyroY = 0; + int16_t i16_rawGyroZ = 0; + int16_t i16_rawAccX = 0; + int16_t i16_rawAccY = 0; + int16_t i16_rawAccZ = 0; + + // Check first if new data is available + if (!I2C_LSM6DS33_ReadRegister(LSM6DS33_STATUS_REG_ADDR, ui8_regs, 1)) + { + TRACE("ERROR: LSM6DS33 did not respond to I2C address"); + return false; + } + if ((ui8_regs[0] & 0x07) != 0x07) + { + TRACE("ERROR: LSM6DS33 has no new data available yet"); + return false; + } + + if (!I2C_LSM6DS33_ReadRegister(LSM6DS33_OUT_TEMP_L_ADDR, ui8_regs, 14)) + { + TRACE("ERROR: LSM6DS33 did not respond to I2C address"); + return false; + } + + i16_rawTemperature = (ui8_regs[1] << 8) | ui8_regs[0]; + i16_rawGyroX = (ui8_regs[3] << 8) | ui8_regs[2]; + i16_rawGyroY = (ui8_regs[5] << 8) | ui8_regs[4]; + i16_rawGyroZ = (ui8_regs[7] << 8) | ui8_regs[6]; + i16_rawAccX = (ui8_regs[9] << 8) | ui8_regs[8]; + i16_rawAccY = (ui8_regs[11] << 8) | ui8_regs[10]; + i16_rawAccZ = (ui8_regs[13] << 8) | ui8_regs[12]; + + IMUoutput.fGyroXradps = i16_rawGyroX * IMUsettings.gyro_mDPS * M_PI/180.0 / 1000.0; + IMUoutput.fGyroYradps = i16_rawGyroY * IMUsettings.gyro_mDPS * M_PI/180.0 / 1000.0; + IMUoutput.fGyroZradps = i16_rawGyroZ * IMUsettings.gyro_mDPS * M_PI/180.0 / 1000.0; + + IMUoutput.fAccX = i16_rawAccX * IMUsettings.linacc_mG * GRAVITY_EARTH / 1000.0; + IMUoutput.fAccY = i16_rawAccY * IMUsettings.linacc_mG * GRAVITY_EARTH / 1000.0; + IMUoutput.fAccZ = i16_rawAccZ * IMUsettings.linacc_mG * GRAVITY_EARTH / 1000.0; + + IMUoutput.fTemperatureDegC = (float)i16_rawTemperature / 16.0 + 25.0; + /*TRACE("LSM6DS33: %.2f deg.C, GyroXYZ [rad/s]: %.2f, %.2f, %.2f, AccXYZ [m/s^2]: %.2f %.2f %.2f", + IMUoutput.fTemperatureDegC, + IMUoutput.fGyroXradps, IMUoutput.fGyroYradps, IMUoutput.fGyroZradps, + IMUoutput.fAccX, IMUoutput.fAccY, IMUoutput.fAccZ); */ + return true; +} diff --git a/radio/src/targets/horus/imu_lsm6ds33.h b/radio/src/targets/horus/imu_lsm6ds33.h new file mode 100644 index 000000000..16ec03f8b --- /dev/null +++ b/radio/src/targets/horus/imu_lsm6ds33.h @@ -0,0 +1,139 @@ +/* + * Copyright (C) EdgeTX + * + * Based on code named + * opentx - https://github.com/opentx/opentx + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#pragma once + +#include "i2c_driver.h" + +#define GRAVITY_EARTH 9.80665F // m/s^2 + +#define LSM6DS33_I2C_ADDR 0x6A +#define LSM6DS33_WHOAMI 0x69 +#define LSM6DS33_TIMEOUT 3 // 3ms + +// LSM6DS33 register map +#define LSM6DS33_FUNC_CFG_ACCESS_ADDR 0x01 +#define LSM6DS33_FIFO_CTRL1_ADDR 0x06 +#define LSM6DS33_FIFO_CTRL2_ADDR 0x07 +#define LSM6DS33_FIFO_CTRL3_ADDR 0x08 +#define LSM6DS33_FIFO_CTRL4_ADDR 0x09 +#define LSM6DS33_FIFO_CTRL5_ADDR 0x0A +#define LSM6DS33_ORIENT_CFG_G_ADDR 0x0B +#define LSM6DS33_INT1_CTRL_ADDR 0x0D +#define LSM6DS33_INT2_CTRL_ADDR 0x0E +#define LSM6DS33_WHO_AM_I_ADDR 0x0F +#define LSM6DS33_CTRL1_XL_ADDR 0x10 +#define LSM6DS33_CTRL2_G_ADDR 0x11 +#define LSM6DS33_CTRL3_C_ADDR 0x12 +#define LSM6DS33_CTRL4_C_ADDR 0x13 +#define LSM6DS33_CTRL5_C_ADDR 0x14 +#define LSM6DS33_CTRL6_C_ADDR 0x15 +#define LSM6DS33_CTRL7_G_ADDR 0x16 +#define LSM6DS33_CTRL8_XL_ADDR 0x17 +#define LSM6DS33_CTRL9_XL_ADDR 0x18 +#define LSM6DS33_CTRL10_C_ADDR 0x19 +#define LSM6DS33_WAKE_UP_SRC_ADDR 0x1B +#define LSM6DS33_TAP_SRC_ADDR 0x1C +#define LSM6DS33_D6D_SRC_ADDR 0x1D +#define LSM6DS33_STATUS_REG_ADDR 0x1E +#define LSM6DS33_OUT_TEMP_L_ADDR 0x20 +#define LSM6DS33_OUT_TEMP_H_ADDR 0x21 +#define LSM6DS33_OUTX_L_G_ADDR 0x22 +#define LSM6DS33_OUTX_H_G_ADDR 0x23 +#define LSM6DS33_OUTY_L_G_ADDR 0x24 +#define LSM6DS33_OUTY_H_G_ADDR 0x25 +#define LSM6DS33_OUTZ_L_G_ADDR 0x26 +#define LSM6DS33_OUTZ_H_G_ADDR 0x27 +#define LSM6DS33_OUTX_L_XL_ADDR 0x28 +#define LSM6DS33_OUTX_H_XL_ADDR 0x29 +#define LSM6DS33_OUTY_L_XL_ADDR 0x2A +#define LSM6DS33_OUTY_H_XL_ADDR 0x2B +#define LSM6DS33_OUTZ_L_XL_ADDR 0x2C +#define LSM6DS33_OUTZ_H_XL_ADDR 0x2D +#define LSM6DS33_FIFO_STATUS1_ADDR 0x3A +#define LSM6DS33_FIFO_STATUS2_ADDR 0x3B +#define LSM6DS33_FIFO_STATUS3_ADDR 0x3C +#define LSM6DS33_FIFO_STATUS4_ADDR 0x3D +#define LSM6DS33_FIFO_DATA_OUT_L_ADDR 0x3E +#define LSM6DS33_FIFO_DATA_OUT_H_ADDR 0x3F +#define LSM6DS33_TIMESTAMP0_REG_ADDR 0x40 +#define LSM6DS33_TIMESTAMP1_REG_ADDR 0x41 +#define LSM6DS33_TIMESTAMP2_REG_ADDR 0x42 +#define LSM6DS33_STEP_TIMESTAMP_L_ADDR 0x49 +#define LSM6DS33_STEP_TIMESTAMP_H_ADDR 0x4A +#define LSM6DS33_STEP_COUNTER_L_ADDR 0x4B +#define LSM6DS33_STEP_COUNTER_H_ADDR 0x4C +#define LSM6DS33_FUNC_SRC_ADDR 0x53 +#define LSM6DS33_TAP_CFG_ADDR 0x58 +#define LSM6DS33_TAP_THS_6D_ADDR 0x59 +#define LSM6DS33_INT_DUR2_ADDR 0x5A +#define LSM6DS33_WAKE_UP_THS_ADDR 0x5B +#define LSM6DS33_WAKE_UP_DUR_ADDR 0x5C +#define LSM6DS33_FREE_FALL_ADDR 0x5D +#define LSM6DS33_MD1_CFG_ADDR 0x5E +#define LSM6DS33_MD2_CFG_ADDR 0x5F + +#define LSM6DS33_ODR_0Hz 0x00 +#define LSM6DS33_ODR_12_5Hz 0x01 +#define LSM6DS33_ODR_26Hz 0x02 +#define LSM6DS33_ODR_52Hz 0x03 +#define LSM6DS33_ODR_104Hz 0x04 +#define LSM6DS33_ODR_208Hz 0x05 +#define LSM6DS33_ODR_416Hz 0x06 +#define LSM6DS33_ODR_833Hz 0x07 +#define LSM6DS33_ODR_1_66kHz 0x08 +#define LSM6DS33_ODR_3_33kHz 0x09 +#define LSM6DS33_ODR_6_66kHz 0x0A + +#define LSM6DS33_LA_FS_2G 0x00 +#define LSM6DS33_LA_FS_16G 0x01 +#define LSM6DS33_LA_FS_4G 0x02 +#define LSM6DS33_LA_FS_8G 0x03 + +#define LSM6DS33_LA_AABW_400Hz 0x00 +#define LSM6DS33_LA_AABW_200Hz 0x01 +#define LSM6DS33_LA_AABW_100Hz 0x02 +#define LSM6DS33_LA_AABW_50Hz 0x03 + +#define LSM6DS33_GY_FS_125dps 0x01 +#define LSM6DS33_GY_FS_250dps 0x00 +#define LSM6DS33_GY_FS_500dps 0x02 +#define LSM6DS33_GY_FS_1000dps 0x04 +#define LSM6DS33_GY_FS_2000dps 0x05 + +typedef struct { + int16_t linacc_odr; + float linacc_mG; // milli G per Bit + int16_t linacc_aabw; + int16_t gyro_odr; + float gyro_mDPS; // milli degrees per second per Bit +} sIMUsettings; + +typedef struct { + float fTemperatureDegC; //°C + float fAccX, fAccY, fAccZ; // m/s^2 + float fGyroXradps, fGyroYradps, fGyroZradps; // rad/s +} sIMUoutput; + +extern sIMUoutput IMUoutput; + +bool imu_lsm6ds33_init(void); +bool imu_lsm6ds33_read(); diff --git a/radio/src/targets/horus/tp_gt911.cpp b/radio/src/targets/horus/tp_gt911.cpp index 667df4b50..611152362 100644 --- a/radio/src/targets/horus/tp_gt911.cpp +++ b/radio/src/targets/horus/tp_gt911.cpp @@ -489,10 +489,10 @@ void TOUCH_AF_INT_Change(void) void I2C_Init_Radio(void) { - TRACE("I2C Init"); + TRACE("I2C B1 Init"); - hi2c1.Instance = I2C; - hi2c1.Init.ClockSpeed = I2C_CLK_RATE; + hi2c1.Instance = I2C_B1; + hi2c1.Init.ClockSpeed = I2C_B1_CLK_RATE; hi2c1.Init.DutyCycle = I2C_DUTYCYCLE_16_9; hi2c1.Init.OwnAddress1 = 0; hi2c1.Init.AddressingMode = I2C_ADDRESSINGMODE_7BIT; @@ -502,17 +502,17 @@ void I2C_Init_Radio(void) hi2c1.Init.NoStretchMode = I2C_NOSTRETCH_DISABLE; if (HAL_I2C_Init(&hi2c1) != HAL_OK) { - TRACE("I2C ERROR: HAL_I2C_Init() failed"); + TRACE("I2C B1 ERROR: HAL_I2C_Init() failed"); } // Configure Analogue filter if (HAL_I2CEx_ConfigAnalogFilter(&hi2c1, I2C_ANALOGFILTER_ENABLE) != HAL_OK) { - TRACE("I2C ERROR: HAL_I2CEx_ConfigAnalogFilter() failed"); + TRACE("I2C B1 ERROR: HAL_I2CEx_ConfigAnalogFilter() failed"); } // Configure Digital filter if (HAL_I2CEx_ConfigDigitalFilter(&hi2c1, 0) != HAL_OK) { - TRACE("I2C ERROR: HAL_I2CEx_ConfigDigitalFilter() failed"); + TRACE("I2C B1 ERROR: HAL_I2CEx_ConfigDigitalFilter() failed"); } } @@ -532,7 +532,7 @@ bool I2C_GT911_WriteRegister(uint16_t reg, uint8_t * buf, uint8_t len) if (HAL_I2C_Master_Transmit(&hi2c1, GT911_I2C_ADDR << 1, uAddrAndBuf, len + 2, 100) != HAL_OK) { - TRACE("I2C ERROR: WriteRegister failed"); + TRACE("I2C B1 ERROR: WriteRegister failed"); return false; } return true; @@ -546,13 +546,13 @@ bool I2C_GT911_ReadRegister(uint16_t reg, uint8_t * buf, uint8_t len) if (HAL_I2C_Master_Transmit(&hi2c1, GT911_I2C_ADDR << 1, uRegAddr, 2, 10) != HAL_OK) { - TRACE("I2C ERROR: ReadRegister write reg address failed"); + TRACE("I2C B1 ERROR: ReadRegister write reg address failed"); return false; } if (HAL_I2C_Master_Receive(&hi2c1, GT911_I2C_ADDR << 1, buf, len, 100) != HAL_OK) { - TRACE("I2C ERROR: ReadRegister read reg address failed"); + TRACE("I2C B1 ERROR: ReadRegister read reg address failed"); return false; } return true; @@ -677,15 +677,15 @@ bool touchPanelInit(void) bool I2C_ReInit(void) { - TRACE("I2C ReInit"); + TRACE("I2C B1 ReInit"); touchPanelDeInit(); if (HAL_I2C_DeInit(&hi2c1) != HAL_OK) - TRACE("I2C ReInit - I2C DeInit failed"); + TRACE("I2C B1 ReInit - I2C DeInit failed"); // If DeInit fails, try to re-init anyway if (!touchPanelInit()) { - TRACE("I2C ReInit - touchPanelInit failed"); + TRACE("I2C B1 ReInit - touchPanelInit failed"); return false; } return true; @@ -728,7 +728,7 @@ void touchPanelRead() touchGT911hiccups++; TRACE("GT911 I2C read XY error"); if (!I2C_ReInit()) - TRACE("I2C ReInit failed"); + TRACE("I2C B1 ReInit failed"); return; } @@ -750,7 +750,7 @@ void touchPanelRead() touchGT911hiccups++; TRACE("GT911 I2C data read error"); if (!I2C_ReInit()) - TRACE("I2C ReInit failed"); + TRACE("I2C B1 ReInit failed"); return; } if (touchState.event == TE_NONE || touchState.event == TE_UP || diff --git a/radio/src/targets/nv14/hal.h b/radio/src/targets/nv14/hal.h index c7c04d858..2492d48cb 100644 --- a/radio/src/targets/nv14/hal.h +++ b/radio/src/targets/nv14/hal.h @@ -353,8 +353,8 @@ #define AUDIO_SPI_MOSI_GPIO_PinSource GPIO_PinSource5 // I2C Bus -#define I2C_RCC_AHB1Periph 0 -#define I2C_RCC_APB1Periph 0 +#define I2C_B1_RCC_AHB1Periph 0 +#define I2C_B1_RCC_APB1Periph 0 // Haptic: TIM1_CH1 #define HAPTIC_PWM diff --git a/radio/src/targets/taranis/board.cpp b/radio/src/targets/taranis/board.cpp index db8d4cebb..a6ec36094 100644 --- a/radio/src/targets/taranis/board.cpp +++ b/radio/src/targets/taranis/board.cpp @@ -84,7 +84,7 @@ void boardInit() AUDIO_RCC_AHB1Periph | BACKLIGHT_RCC_AHB1Periph | ADC_RCC_AHB1Periph | - I2C_RCC_AHB1Periph | + I2C_B1_RCC_AHB1Periph | SD_RCC_AHB1Periph | HAPTIC_RCC_AHB1Periph | INTMODULE_RCC_AHB1Periph | @@ -95,7 +95,7 @@ void boardInit() TRAINER_RCC_AHB1Periph | TRAINER_MODULE_RCC_AHB1Periph | BT_RCC_AHB1Periph | - GYRO_RCC_AHB1Periph | + I2C_B2_RCC_AHB1Periph | USB_CHARGER_RCC_AHB1Periph, ENABLE); @@ -107,7 +107,7 @@ void boardInit() HAPTIC_RCC_APB1Periph | INTERRUPT_xMS_RCC_APB1Periph | TIMER_2MHz_RCC_APB1Periph | - I2C_RCC_APB1Periph | + I2C_B1_RCC_APB1Periph | SD_RCC_APB1Periph | TRAINER_RCC_APB1Periph | TELEMETRY_RCC_APB1Periph | @@ -116,7 +116,7 @@ void boardInit() TRAINER_MODULE_RCC_APB1Periph | MIXER_SCHEDULER_TIMER_RCC_APB1Periph | BT_RCC_APB1Periph | - GYRO_RCC_APB1Periph, + I2C_B2_RCC_APB1Periph, ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2Periph_SYSCFG | diff --git a/radio/src/targets/taranis/hal.h b/radio/src/targets/taranis/hal.h index 93873f5dd..fad9ec607 100644 --- a/radio/src/targets/taranis/hal.h +++ b/radio/src/targets/taranis/hal.h @@ -1920,67 +1920,67 @@ #define LCD_RCC_APB2Periph 0 // I2C Bus: EEPROM and CAT5137 digital pot for volume control -#define I2C_RCC_APB1Periph RCC_APB1Periph_I2C1 -#define I2C I2C1 -#define I2C_GPIO_AF GPIO_AF_I2C1 +#define I2C_B1_RCC_APB1Periph RCC_APB1Periph_I2C1 +#define I2C_B1 I2C1 +#define I2C_B1_GPIO_AF GPIO_AF_I2C1 #if defined(PCBXLITE) || defined(PCBX9LITE) - #define I2C_RCC_AHB1Periph (RCC_AHB1Periph_GPIOB | RCC_AHB1Periph_GPIOD) - #define I2C_SPI_GPIO GPIOB - #define I2C_SDA_GPIO_PIN GPIO_Pin_9 // PB.09 - #define I2C_SCL_GPIO_PIN GPIO_Pin_8 // PB.08 - #define I2C_WP_GPIO GPIOD - #define I2C_WP_GPIO_PIN GPIO_Pin_7 // PD.07 - #define I2C_SCL_GPIO_PinSource GPIO_PinSource8 - #define I2C_SDA_GPIO_PinSource GPIO_PinSource9 + #define I2C_B1_RCC_AHB1Periph (RCC_AHB1Periph_GPIOB | RCC_AHB1Periph_GPIOD) + #define I2C_B1_SPI_GPIO GPIOB + #define I2C_B1_SDA_GPIO_PIN GPIO_Pin_9 // PB.09 + #define I2C_B1_SCL_GPIO_PIN GPIO_Pin_8 // PB.08 + #define I2C_B1_WP_GPIO GPIOD + #define I2C_B1_WP_GPIO_PIN GPIO_Pin_7 // PD.07 + #define I2C_B1_SCL_GPIO_PinSource GPIO_PinSource8 + #define I2C_B1_SDA_GPIO_PinSource GPIO_PinSource9 #elif defined(PCBX7ACCESS) - #define I2C_RCC_AHB1Periph RCC_AHB1Periph_GPIOB - #define I2C_SPI_GPIO GPIOB - #define I2C_SDA_GPIO_PIN GPIO_Pin_9 // PB.09 - #define I2C_SCL_GPIO_PIN GPIO_Pin_8 // PB.08 - #define I2C_WP_GPIO GPIOB - #define I2C_WP_GPIO_PIN GPIO_Pin_5 // PB.05 - #define I2C_SDA_GPIO_PinSource GPIO_PinSource9 - #define I2C_SCL_GPIO_PinSource GPIO_PinSource8 + #define I2C_B1_RCC_AHB1Periph RCC_AHB1Periph_GPIOB + #define I2C_B1_SPI_GPIO GPIOB + #define I2C_B1_SDA_GPIO_PIN GPIO_Pin_9 // PB.09 + #define I2C_B1_SCL_GPIO_PIN GPIO_Pin_8 // PB.08 + #define I2C_B1_WP_GPIO GPIOB + #define I2C_B1_WP_GPIO_PIN GPIO_Pin_5 // PB.05 + #define I2C_B1_SDA_GPIO_PinSource GPIO_PinSource9 + #define I2C_B1_SCL_GPIO_PinSource GPIO_PinSource8 #elif defined(RADIO_X9DP2019) - #define I2C_RCC_AHB1Periph (RCC_AHB1Periph_GPIOB | RCC_AHB1Periph_GPIOF) - #define I2C_SPI_GPIO GPIOB - #define I2C_SDA_GPIO_PIN GPIO_Pin_9 // PB.09 - #define I2C_SCL_GPIO_PIN GPIO_Pin_8 // PB.08 - #define I2C_WP_GPIO GPIOF - #define I2C_WP_GPIO_PIN GPIO_Pin_0 // PF.00 - #define I2C_SCL_GPIO_PinSource GPIO_PinSource8 - #define I2C_SDA_GPIO_PinSource GPIO_PinSource9 + #define I2C_B1_RCC_AHB1Periph (RCC_AHB1Periph_GPIOB | RCC_AHB1Periph_GPIOF) + #define I2C_B1_SPI_GPIO GPIOB + #define I2C_B1_SDA_GPIO_PIN GPIO_Pin_9 // PB.09 + #define I2C_B1_SCL_GPIO_PIN GPIO_Pin_8 // PB.08 + #define I2C_B1_WP_GPIO GPIOF + #define I2C_B1_WP_GPIO_PIN GPIO_Pin_0 // PF.00 + #define I2C_B1_SCL_GPIO_PinSource GPIO_PinSource8 + #define I2C_B1_SDA_GPIO_PinSource GPIO_PinSource9 #else - #define I2C_RCC_AHB1Periph RCC_AHB1Periph_GPIOB - #define I2C_SPI_GPIO GPIOB - #define I2C_SCL_GPIO_PIN GPIO_Pin_6 // PB.06 - #define I2C_SDA_GPIO_PIN GPIO_Pin_7 // PB.07 - #define I2C_WP_GPIO GPIOB - #define I2C_WP_GPIO_PIN GPIO_Pin_9 // PB.09 - #define I2C_SCL_GPIO_PinSource GPIO_PinSource6 - #define I2C_SDA_GPIO_PinSource GPIO_PinSource7 + #define I2C_B1_RCC_AHB1Periph RCC_AHB1Periph_GPIOB + #define I2C_B1_SPI_GPIO GPIOB + #define I2C_B1_SCL_GPIO_PIN GPIO_Pin_6 // PB.06 + #define I2C_B1_SDA_GPIO_PIN GPIO_Pin_7 // PB.07 + #define I2C_B1_WP_GPIO GPIOB + #define I2C_B1_WP_GPIO_PIN GPIO_Pin_9 // PB.09 + #define I2C_B1_SCL_GPIO_PinSource GPIO_PinSource6 + #define I2C_B1_SDA_GPIO_PinSource GPIO_PinSource7 #define I2C_ADDRESS_VOLUME 0x5C #endif -#define I2C_CLK_RATE 400000 +#define I2C_B1_CLK_RATE 400000 #define I2C_ADDRESS_EEPROM 0xA2 #define I2C_FLASH_PAGESIZE 64 // Second I2C Bus: IMU #if defined(PCBXLITES) - #define GYRO_RCC_AHB1Periph (RCC_AHB1Periph_GPIOA | RCC_AHB1Periph_GPIOC) - #define GYRO_RCC_APB1Periph RCC_APB1Periph_I2C3 - #define I2CX I2C3 - #define I2CX_SCL_GPIO GPIOA - #define I2CX_SCL_GPIO_PIN GPIO_Pin_8 // PA.08 - #define I2CX_SDA_GPIO GPIOC - #define I2CX_SDA_GPIO_PIN GPIO_Pin_9 // PC.09 - #define I2CX_GPIO_AF GPIO_AF_I2C3 - #define I2CX_SCL_GPIO_PinSource GPIO_PinSource8 - #define I2CX_SDA_GPIO_PinSource GPIO_PinSource9 - #define I2CX_SPEED 400000 + #define I2C_B2_RCC_AHB1Periph (RCC_AHB1Periph_GPIOA | RCC_AHB1Periph_GPIOC) + #define I2C_B2_RCC_APB1Periph RCC_APB1Periph_I2C3 + #define I2C_B2 I2C3 + #define I2C_B2_SCL_GPIO GPIOA + #define I2C_B2_SCL_GPIO_PIN GPIO_Pin_8 // PA.08 + #define I2C_B2_SDA_GPIO GPIOC + #define I2C_B2_SDA_GPIO_PIN GPIO_Pin_9 // PC.09 + #define I2C_B2_GPIO_AF GPIO_AF_I2C3 + #define I2C_B2_SCL_GPIO_PinSource GPIO_PinSource8 + #define I2C_B2_SDA_GPIO_PinSource GPIO_PinSource9 + #define I2C_B2_SPEED 400000 #else - #define GYRO_RCC_AHB1Periph 0 - #define GYRO_RCC_APB1Periph 0 + #define I2C_B2_RCC_AHB1Periph 0 + #define I2C_B2_RCC_APB1Periph 0 #endif // SD - SPI2 diff --git a/radio/src/targets/taranis/i2c_driver.cpp b/radio/src/targets/taranis/i2c_driver.cpp index 24d15a2c0..6b4e72c3c 100644 --- a/radio/src/targets/taranis/i2c_driver.cpp +++ b/radio/src/targets/taranis/i2c_driver.cpp @@ -25,43 +25,43 @@ void eepromWaitEepromStandbyState(void); void i2cInit() { - I2C_DeInit(I2C); + I2C_DeInit(I2C_B1); GPIO_InitTypeDef GPIO_InitStructure; - GPIO_InitStructure.GPIO_Pin = I2C_WP_GPIO_PIN; + GPIO_InitStructure.GPIO_Pin = I2C_B1_WP_GPIO_PIN; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; GPIO_InitStructure.GPIO_OType = GPIO_OType_OD; GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; - GPIO_Init(I2C_WP_GPIO, &GPIO_InitStructure); - GPIO_ResetBits(I2C_WP_GPIO, I2C_WP_GPIO_PIN); + GPIO_Init(I2C_B1_WP_GPIO, &GPIO_InitStructure); + GPIO_ResetBits(I2C_B1_WP_GPIO, I2C_B1_WP_GPIO_PIN); I2C_InitTypeDef I2C_InitStructure; - I2C_InitStructure.I2C_ClockSpeed = I2C_CLK_RATE; + I2C_InitStructure.I2C_ClockSpeed = I2C_B1_CLK_RATE; I2C_InitStructure.I2C_DutyCycle = I2C_DutyCycle_2; I2C_InitStructure.I2C_OwnAddress1 = 0x00; I2C_InitStructure.I2C_Mode = I2C_Mode_I2C; I2C_InitStructure.I2C_Ack = I2C_Ack_Enable; I2C_InitStructure.I2C_AcknowledgedAddress = I2C_AcknowledgedAddress_7bit; - I2C_Init(I2C, &I2C_InitStructure); - I2C_Cmd(I2C, ENABLE); + I2C_Init(I2C_B1, &I2C_InitStructure); + I2C_Cmd(I2C_B1, ENABLE); - GPIO_PinAFConfig(I2C_SPI_GPIO, I2C_SCL_GPIO_PinSource, I2C_GPIO_AF); - GPIO_PinAFConfig(I2C_SPI_GPIO, I2C_SDA_GPIO_PinSource, I2C_GPIO_AF); + GPIO_PinAFConfig(I2C_B1_SPI_GPIO, I2C_B1_SCL_GPIO_PinSource, I2C_B1_GPIO_AF); + GPIO_PinAFConfig(I2C_B1_SPI_GPIO, I2C_B1_SDA_GPIO_PinSource, I2C_B1_GPIO_AF); - GPIO_InitStructure.GPIO_Pin = I2C_SCL_GPIO_PIN | I2C_SDA_GPIO_PIN; + GPIO_InitStructure.GPIO_Pin = I2C_B1_SCL_GPIO_PIN | I2C_B1_SDA_GPIO_PIN; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF; GPIO_InitStructure.GPIO_OType = GPIO_OType_OD; GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; - GPIO_Init(I2C_SPI_GPIO, &GPIO_InitStructure); + GPIO_Init(I2C_B1_SPI_GPIO, &GPIO_InitStructure); } #define I2C_TIMEOUT_MAX 1000 bool I2C_WaitEvent(uint32_t event) { uint32_t timeout = I2C_TIMEOUT_MAX; - while (!I2C_CheckEvent(I2C, event)) { + while (!I2C_CheckEvent(I2C_B1, event)) { if ((timeout--) == 0) return false; } return true; @@ -70,7 +70,7 @@ bool I2C_WaitEvent(uint32_t event) bool I2C_WaitEventCleared(uint32_t event) { uint32_t timeout = I2C_TIMEOUT_MAX; - while (I2C_CheckEvent(I2C, event)) { + while (I2C_CheckEvent(I2C_B1, event)) { if ((timeout--) == 0) return false; } return true; @@ -89,44 +89,44 @@ bool I2C_EE_ReadBlock(uint8_t* pBuffer, uint16_t ReadAddr, uint16_t NumByteToRea if (!I2C_WaitEventCleared(I2C_FLAG_BUSY)) return false; - I2C_GenerateSTART(I2C, ENABLE); + I2C_GenerateSTART(I2C_B1, ENABLE); if (!I2C_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) return false; - I2C_Send7bitAddress(I2C, I2C_ADDRESS_EEPROM, I2C_Direction_Transmitter); + I2C_Send7bitAddress(I2C_B1, I2C_ADDRESS_EEPROM, I2C_Direction_Transmitter); if (!I2C_WaitEvent(I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)) return false; - I2C_SendData(I2C, (uint8_t)((ReadAddr & 0xFF00) >> 8)); + I2C_SendData(I2C_B1, (uint8_t)((ReadAddr & 0xFF00) >> 8)); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTING)) return false; - I2C_SendData(I2C, (uint8_t)(ReadAddr & 0x00FF)); + I2C_SendData(I2C_B1, (uint8_t)(ReadAddr & 0x00FF)); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTED)) return false; - I2C_GenerateSTART(I2C, ENABLE); + I2C_GenerateSTART(I2C_B1, ENABLE); if (!I2C_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) return false; - I2C_Send7bitAddress(I2C, I2C_ADDRESS_EEPROM, I2C_Direction_Receiver); + I2C_Send7bitAddress(I2C_B1, I2C_ADDRESS_EEPROM, I2C_Direction_Receiver); if (!I2C_WaitEvent(I2C_EVENT_MASTER_RECEIVER_MODE_SELECTED)) return false; if (NumByteToRead > 1) { - I2C_AcknowledgeConfig(I2C, ENABLE); + I2C_AcknowledgeConfig(I2C_B1, ENABLE); } while (NumByteToRead) { if (NumByteToRead == 1) { - I2C_AcknowledgeConfig(I2C, DISABLE); + I2C_AcknowledgeConfig(I2C_B1, DISABLE); } if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_RECEIVED)) return false; - *pBuffer++ = I2C_ReceiveData(I2C); + *pBuffer++ = I2C_ReceiveData(I2C_B1); NumByteToRead--; } - I2C_GenerateSTOP(I2C, ENABLE); + I2C_GenerateSTOP(I2C_B1, ENABLE); return true; } @@ -184,24 +184,24 @@ bool I2C_EE_PageWrite(uint8_t * pBuffer, uint16_t WriteAddr, uint8_t NumByteToWr if (!I2C_WaitEventCleared(I2C_FLAG_BUSY)) return false; - I2C_GenerateSTART(I2C, ENABLE); + I2C_GenerateSTART(I2C_B1, ENABLE); if (!I2C_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) return false; - I2C_Send7bitAddress(I2C, I2C_ADDRESS_EEPROM, I2C_Direction_Transmitter); + I2C_Send7bitAddress(I2C_B1, I2C_ADDRESS_EEPROM, I2C_Direction_Transmitter); if (!I2C_WaitEvent(I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)) return false; - I2C_SendData(I2C, (uint8_t)((WriteAddr & 0xFF00) >> 8)); + I2C_SendData(I2C_B1, (uint8_t)((WriteAddr & 0xFF00) >> 8)); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTING)) return false; - I2C_SendData(I2C, (uint8_t)(WriteAddr & 0x00FF)); + I2C_SendData(I2C_B1, (uint8_t)(WriteAddr & 0x00FF)); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTING)) return false; /* While there is data to be written */ while (NumByteToWrite--) { - I2C_SendData(I2C, *pBuffer); + I2C_SendData(I2C_B1, *pBuffer); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTING)) return false; pBuffer++; @@ -210,7 +210,7 @@ bool I2C_EE_PageWrite(uint8_t * pBuffer, uint16_t WriteAddr, uint8_t NumByteToWr if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTED)) return false; - I2C_GenerateSTOP(I2C, ENABLE); + I2C_GenerateSTOP(I2C_B1, ENABLE); return true; } @@ -229,14 +229,14 @@ void eepromPageWrite(uint8_t* pBuffer, uint16_t WriteAddr, uint8_t NumByteToWrit bool I2C_EE_WaitEepromStandbyState(void) { do { - I2C_GenerateSTART(I2C, ENABLE); + I2C_GenerateSTART(I2C_B1, ENABLE); if (!I2C_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) return false; - I2C_Send7bitAddress(I2C, I2C_ADDRESS_EEPROM, I2C_Direction_Transmitter); + I2C_Send7bitAddress(I2C_B1, I2C_ADDRESS_EEPROM, I2C_Direction_Transmitter); } while (!I2C_WaitEvent(I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)); - I2C_GenerateSTOP(I2C, ENABLE); + I2C_GenerateSTOP(I2C_B1, ENABLE); return true; } @@ -267,22 +267,22 @@ void setVolume(uint8_t volume) if (!I2C_WaitEventCleared(I2C_FLAG_BUSY)) return; - I2C_GenerateSTART(I2C, ENABLE); + I2C_GenerateSTART(I2C_B1, ENABLE); if (!I2C_WaitEvent(I2C_EVENT_MASTER_MODE_SELECT)) return; - I2C_Send7bitAddress(I2C, I2C_ADDRESS_VOLUME, I2C_Direction_Transmitter); + I2C_Send7bitAddress(I2C_B1, I2C_ADDRESS_VOLUME, I2C_Direction_Transmitter); if (!I2C_WaitEvent(I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED)) return; - I2C_SendData(I2C, 0); + I2C_SendData(I2C_B1, 0); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTING)) return; - I2C_SendData(I2C, volume); + I2C_SendData(I2C_B1, volume); if (!I2C_WaitEvent(I2C_EVENT_MASTER_BYTE_TRANSMITTED)) return; - I2C_GenerateSTOP(I2C, ENABLE); + I2C_GenerateSTOP(I2C_B1, ENABLE); } int32_t getVolume()