From 35a11734e26492bcbc994b29f47452d8f1ed45e4 Mon Sep 17 00:00:00 2001 From: bruno Date: Tue, 15 Apr 2025 16:32:28 +0200 Subject: [PATCH] fixes --- .vscode/settings.json | 7 +++-- dependencies.lock | 2 +- main/components/sensors.c | 39 +++++++++++++---------- main/hw/bme680b.c | 4 +-- main/hw/ccs811.c | 4 +-- main/hw/ina260.c | 66 +++++++++++++++++++++++++++++---------- main/hw/ina260.h | 64 +++++++++++++++++++++++++++++++++++-- main/hw/mpu9250.c | 14 ++++----- 8 files changed, 150 insertions(+), 50 deletions(-) diff --git a/.vscode/settings.json b/.vscode/settings.json index 8bbbd02..8a3cc7c 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -1,13 +1,13 @@ { "C_Cpp.intelliSenseEngine": "default", - "idf.espIdfPath": "/home/bruno/esp/master/esp-idf", + "idf.espIdfPath": "/home/bruno/esp/v5.4.1/esp-idf", "idf.pythonInstallPath": "/usr/bin/python", "idf.openOcdConfigs": [ "board/esp32s3-builtin.cfg" ], "idf.port": "/dev/ttyACM0", "idf.toolsPath": "/home/bruno/.espressif", - "idf.flashType": "JTAG", + "idf.flashType": "UART", "idf.customExtraVars": { "OPENOCD_SCRIPTS": "/home/bruno/.espressif/tools/openocd-esp32/v0.12.0-esp32-20240821/openocd-esp32/share/openocd/scripts", "ESP_ROM_ELF_DIR": "/home/bruno/.espressif/tools/esp-rom-elfs/20240305/", @@ -28,6 +28,7 @@ "ccs811.h": "c", "esp_mac.h": "c", "gpio.h": "c", - "chrono": "c" + "chrono": "c", + "cstdint": "c" } } diff --git a/dependencies.lock b/dependencies.lock index 2a59adb..20bbb23 100644 --- a/dependencies.lock +++ b/dependencies.lock @@ -2,7 +2,7 @@ dependencies: idf: source: type: idf - version: 5.5.0 + version: 5.4.1 k0i05/esp_bme680: component_hash: 2df0cb14d4425565a8745d4a96bfaa8ff7e90bbec3e208a073821406dded23c8 dependencies: diff --git a/main/components/sensors.c b/main/components/sensors.c index e23c050..843ca34 100644 --- a/main/components/sensors.c +++ b/main/components/sensors.c @@ -30,9 +30,9 @@ void i2c_sensors_task(void *pvParameters) float accel_f[3], gyro_f[3], temp_f; uint16_t eCO2; uint16_t tvoc; - uint32_t volts; - uint32_t current; - uint32_t power; + uint16_t volts; + uint16_t current; + uint16_t power; // task loop entry point for (;;) @@ -40,21 +40,26 @@ void i2c_sensors_task(void *pvParameters) // // handle sensor - bme680_data_t data; - esp_err_t result = bme680_get_data(BME680_DEV_HANDLE, &data); - if (result != ESP_OK) + if (BME680_DEV_HANDLE) { - ESP_LOGE(TAG_BME, "bme680 device read failed (%s)", esp_err_to_name(result)); - } - else - { - data.barometric_pressure = data.barometric_pressure / 100; - // ESP_LOGI(TAG, "dewpoint temperature:%.2f °C", data.dewpoint_temperature); - ESP_LOGI(TAG_BME, "air temperature: %.2f °C", data.air_temperature); - ESP_LOGI(TAG_BME, "relative humidity: %.2f %%", data.relative_humidity); - ESP_LOGI(TAG_BME, "barometric pressure: %.2f hPa", data.barometric_pressure); - // ESP_LOGI(TAG, "gas resistance: %.2f kOhms", data.gas_resistance / 1000); - // ESP_LOGI(TAG, "iaq score: %u (%s)", data.iaq_score, bme680_air_quality_to_string(data.iaq_score)); + bme680_data_t data; + esp_err_t result = bme680_get_data(BME680_DEV_HANDLE, &data); + if (result != ESP_OK) + { + ESP_LOGE(TAG_BME, "bme680 device read failed (%s)", esp_err_to_name(result)); + } + else + { + data.barometric_pressure = data.barometric_pressure / 100; + // ESP_LOGI(TAG, "dewpoint temperature:%.2f °C", data.dewpoint_temperature); + ESP_LOGI(TAG_BME, "air temperature: %.2f °C", data.air_temperature); + ESP_LOGI(TAG_BME, "relative humidity: %.2f %%", data.relative_humidity); + ESP_LOGI(TAG_BME, "barometric pressure: %.2f hPa", data.barometric_pressure); + // ESP_LOGI(TAG, "gas resistance: %.2f kOhms", data.gas_resistance / 1000); + // ESP_LOGI(TAG, "iaq score: %u (%s)", data.iaq_score, bme680_air_quality_to_string(data.iaq_score)); + } + } else { + bme680b_init(); } ccs811_get_data(&eCO2, &tvoc); diff --git a/main/hw/bme680b.c b/main/hw/bme680b.c index fdfae9e..19fb30a 100644 --- a/main/hw/bme680b.c +++ b/main/hw/bme680b.c @@ -44,8 +44,8 @@ void bme680b_init() { if (BME680_DEV_HANDLE == NULL) { ESP_LOGE(TAG_BME, "bme680 handle init failed"); - assert(BME680_DEV_HANDLE); + } else { + bme680_print_registers(BME680_DEV_HANDLE); } - bme680_print_registers(BME680_DEV_HANDLE); } \ No newline at end of file diff --git a/main/hw/ccs811.c b/main/hw/ccs811.c index 04680ef..54948e6 100644 --- a/main/hw/ccs811.c +++ b/main/hw/ccs811.c @@ -38,8 +38,8 @@ esp_err_t ccs811_get_data(uint16_t * eCO2, uint16_t * tvoc) esp_err_t ret = i2c_read_register(CCS811_DEV_HANDLE, 0x05, ccsResult, 8); if (ret == ESP_OK) { - *eCO2 = (ccsResult[0] << 8) | ccsResult[1]; - *tvoc = (ccsResult[2] << 8) | ccsResult[3]; + *eCO2 = (((uint16_t)(ccsResult[0] & 0xFF)) << 8) | (ccsResult[1] & 0xFF); + *tvoc = (((uint16_t)(ccsResult[2] & 0xFF)) << 8) | (ccsResult[3] & 0xFF); ESP_LOGI(TAG_CCS, "CCS Status: %d, Error %d", ccsResult[4], ccsResult[5]); } return ret; diff --git a/main/hw/ina260.c b/main/hw/ina260.c index c7da4b0..9e4fd82 100644 --- a/main/hw/ina260.c +++ b/main/hw/ina260.c @@ -8,46 +8,80 @@ i2c_device_config_t INA260_DEV_CFG = { i2c_master_dev_handle_t INA260_DEV_HANDLE; -void ina260_init() -{ - ESP_ERROR_CHECK(i2c_master_bus_add_device(i2c0_bus_hdl, &INA260_DEV_CFG, &INA260_DEV_HANDLE)); + +void ina260_reset() { i2c_write_register_16(INA260_DEV_HANDLE, 0x00, 0x0FFF); // set ina max averaging and max time } -void ina260_readParams(uint32_t *volt, uint32_t *cur, uint32_t *pow) +void ina260_init() { + ESP_ERROR_CHECK(i2c_master_bus_add_device(i2c0_bus_hdl, &INA260_DEV_CFG, &INA260_DEV_HANDLE)); + i2c_write_register_16(INA260_DEV_HANDLE, INA260_CONFIG_REGISTER, 0x0FFF); // set ina max averaging and max time +} + + +esp_err_t i2c_master_read_register_transmit_receive(i2c_master_dev_handle_t device_handle, uint8_t reg_addr, uint8_t *data, size_t data_len) { + esp_err_t ret; + + // The register address is what we want to send first (the "transmit" part) + uint8_t write_buffer[1] = {reg_addr}; + size_t write_size = 1; + + // The data we read will be stored in the 'data' buffer (the "receive" part) + uint8_t read_buffer[data_len]; + size_t read_size = data_len; + + // Perform the combined write (register address) and read (register value) + ret = i2c_master_transmit_receive(INA260_DEV_HANDLE, + write_buffer, write_size, + read_buffer, read_size, + I2C_TIMEOUT_MS_VALUE); + + if (ret == ESP_OK) { + // Copy the data from the temporary read buffer to the output buffer + memcpy(data, read_buffer, read_size); + } + + return ret; +} + +void ina260_readParams(uint16_t *volt, uint16_t *cur, uint16_t *pow) +{ + *volt = 0; + *cur = 0; + *pow = 0; for (uint8_t reg_addr = 1; reg_addr <= 3; reg_addr++) { uint8_t reg_value[2] = {0}; // Buffer for storing register data + ESP_ERROR_CHECK(i2c_master_read_register_transmit_receive(INA260_DEV_HANDLE, reg_addr, reg_value, sizeof(reg_value))); // Perform the register read - ESP_ERROR_CHECK(i2c_master_transmit_receive(INA260_DEV_HANDLE, ®_addr, 1, reg_value, sizeof(reg_value), I2C_TIMEOUT_MS_VALUE)); switch (reg_addr) { case 1: - *cur = *((uint16_t *)reg_value); - + *cur = (((uint16_t)(reg_value[0] & 0xFF)) << 8) | (reg_value[1] & 0xFF); + //*cur = *((uint16_t *)reg_value); break; case 2: - *volt = *((uint16_t *)reg_value); - + *volt = (((uint16_t)(reg_value[0] & 0xFF)) << 8) | (reg_value[1] & 0xFF); break; case 3: - *pow = *((uint16_t *)reg_value); + *pow = (((uint16_t)(reg_value[0] & 0xFF)) << 8) | (reg_value[1] & 0xFF); break; - default: break; } } } -void ina260_printParams(uint32_t volt, uint32_t cur, uint32_t pow) +void ina260_printParams(uint16_t volt, uint16_t cur, uint16_t pow) { + float miliVolts = volt * 1.25; + float miliAmps = cur * 1.25; + float power = pow * 10; cur *= 125; - ESP_LOGI(TAG_INA, "Current: %ld.%ld mA", cur / 10000, cur % 10000); + ESP_LOGI(TAG_INA, "Current: %.3f mA (raw %d)", miliAmps, volt); cur *= 125; - ESP_LOGI(TAG_INA, "Voltage: %ld.%ld V", volt / 10000, volt % 10000); - - ESP_LOGI(TAG_INA, "Power: %ld.%ld W", pow / 10000, pow % 10000); + ESP_LOGI(TAG_INA, "Voltage: %.3f mV (raw %d)", miliVolts, cur); + ESP_LOGI(TAG_INA, "Power: %.3f mW (raw %d)", power, pow); } \ No newline at end of file diff --git a/main/hw/ina260.h b/main/hw/ina260.h index b56beb5..5d931d5 100644 --- a/main/hw/ina260.h +++ b/main/hw/ina260.h @@ -6,10 +6,70 @@ extern i2c_device_config_t INA260_DEV_CFG; extern i2c_master_dev_handle_t INA260_DEV_HANDLE; +#define INA260_CONFIG_REGISTER (0x00) +#define INA260_CURRENT_REGISTER (0x01) +#define INA260_VOLTAGE_REGISTER (0x02) +#define INA260_POWER_REGISTER (0x03) +#define INA260_MASK_ENABLE_REGISTER (0x06) +#define INA260_ALERT_LIMIT_REGISTER (0x07) +#define INA260_MANUFACTURER_ID_REGISTER (0xFE) +#define INA260_DIE_ID_REGISTER (0xFF) + +// Bit masks +#define CONFIG_RST_BIT (1 << 15) +#define CONFIG_AVG_MASK (0x7 << 9) +#define CONFIG_VBUSCT_MASK (0x7 << 6) +#define CONFIG_ISHCT_MASK (0x7 << 3) +#define CONFIG_MODE_MASK (0x7 << 0) + +// Read-only bits +#define CONFIG_RESERVED_BITS (0x7 << 12) // Bits 14–12 = 110b + +// Averaging modes (AVG) +#define CONFIG_AVG_1 (0x0 << 9) +#define CONFIG_AVG_4 (0x1 << 9) +#define CONFIG_AVG_16 (0x2 << 9) +#define CONFIG_AVG_64 (0x3 << 9) +#define CONFIG_AVG_128 (0x4 << 9) +#define CONFIG_AVG_256 (0x5 << 9) +#define CONFIG_AVG_512 (0x6 << 9) +#define CONFIG_AVG_1024 (0x7 << 9) + +// Bus voltage conversion time (VBUSCT) +#define CONFIG_VBUSCT_140US (0x0 << 6) +#define CONFIG_VBUSCT_204US (0x1 << 6) +#define CONFIG_VBUSCT_332US (0x2 << 6) +#define CONFIG_VBUSCT_588US (0x3 << 6) +#define CONFIG_VBUSCT_1_1MS (0x4 << 6) +#define CONFIG_VBUSCT_2_116MS (0x5 << 6) +#define CONFIG_VBUSCT_4_156MS (0x6 << 6) +#define CONFIG_VBUSCT_8_244MS (0x7 << 6) + +// Shunt current conversion time (ISHCT) +#define CONFIG_ISHCT_140US (0x0 << 3) +#define CONFIG_ISHCT_204US (0x1 << 3) +#define CONFIG_ISHCT_332US (0x2 << 3) +#define CONFIG_ISHCT_588US (0x3 << 3) +#define CONFIG_ISHCT_1_1MS (0x4 << 3) +#define CONFIG_ISHCT_2_116MS (0x5 << 3) +#define CONFIG_ISHCT_4_156MS (0x6 << 3) +#define CONFIG_ISHCT_8_244MS (0x7 << 3) + +// Operating mode (MODE) +#define CONFIG_MODE_POWERDOWN (0x0 << 0) +#define CONFIG_MODE_CURRENT_TRIGGER (0x1 << 0) +#define CONFIG_MODE_VOLTAGE_TRIGGER (0x2 << 0) +#define CONFIG_MODE_CURRENT_VOLTAGE_TRIGGER (0x3 << 0) +#define CONFIG_MODE_POWERDOWN2 (0x4 << 0) +#define CONFIG_MODE_POWERDOWN (0x5 << 0) +#define CONFIG_MODE_POWERDOWN (0x6 << 0) +#define CONFIG_MODE_POWERDOWN (0x7 << 0) + + void ina260_init(); -void ina260_readParams(uint32_t *volt, uint32_t *cur, uint32_t *pow); -void ina260_printParams(uint32_t volt, uint32_t cur, uint32_t pow); +void ina260_readParams(uint16_t *volt, uint16_t *cur, uint16_t *pow); +void ina260_printParams(uint16_t volt, uint16_t cur, uint16_t pow); #endif \ No newline at end of file diff --git a/main/hw/mpu9250.c b/main/hw/mpu9250.c index 99a6034..8fa616b 100644 --- a/main/hw/mpu9250.c +++ b/main/hw/mpu9250.c @@ -16,13 +16,13 @@ esp_err_t mpu9250_read_sensor_data(i2c_master_dev_handle_t dev_handle, int16_t * return ret; // Convert raw data (Big-Endian) - accel[0] = (buffer[0] << 8) | buffer[1]; // Accel X - accel[1] = (buffer[2] << 8) | buffer[3]; // Accel Y - accel[2] = (buffer[4] << 8) | buffer[5]; // Accel Z - *temp = (buffer[6] << 8) | buffer[7]; // Temperature - gyro[0] = (buffer[8] << 8) | buffer[9]; // Gyro X - gyro[1] = (buffer[10] << 8) | buffer[11]; // Gyro Y - gyro[2] = (buffer[12] << 8) | buffer[13]; // Gyro Z + accel[0] = (((uint16_t)(buffer[0] & 0xFF)) << 8) | (buffer[1] & 0xFF); // Accel X + accel[1] = (((uint16_t)(buffer[2] & 0xFF)) << 8) | (buffer[3] & 0xFF); // Accel Y + accel[2] = (((uint16_t)(buffer[4] & 0xFF)) << 8) | (buffer[5] & 0xFF); // Accel Z + *temp = (((uint16_t)(buffer[6] & 0xFF)) << 8) | (buffer[7] & 0xFF); // Temperature + gyro[0] = (((uint16_t)(buffer[8] & 0xFF)) << 8) | (buffer[9] & 0xFF);; // Gyro X + gyro[1] = (((uint16_t)(buffer[10] & 0xFF)) << 8) | (buffer[11] & 0xFF);; // Gyro Y + gyro[2] = (((uint16_t)(buffer[12] & 0xFF)) << 8) | (buffer[13] & 0xFF);; // Gyro Z return ESP_OK; }