11-02-2020 12:38 AM
Hello:
I am using the latest C code provided in the gitHub repository: bme680.c, bme680.h, and bme680_defs.h
I have built a functional code module to configure and read the BME680. It configures good, I get back a 0x61 for the module type, and no other errors during the initialization or setup as I check the "rslt" flag each time.
The controller is a STM32L4 series and the I2C seems to be functioning good. I have an array of 30 bytes in which to contain the return data after a read.
This is passed back to the BME software via the read and write calls:
int8_t user_i2c_read(uint8_t dev_addr, uint8_t reg_addr, uint8_t *reg_data, uint16_t cnt)
int8_t user_i2c_read(uint8_t dev_addr, uint8_t reg_addr, uint8_t *reg_data, uint16_t cnt)
I am using the exact example code as provided on the page: https://github.com/BoschSensortec/BME680_driver, in the section "Example for reading all sensor data"
The read at an interval of 1 second. below is the first 12 prints from the conversion, along with the status byte.
[0]T: 21.61 degC, P: 940.05 hPa, H 100.00 %rH
status = 80
[1]T: 21.61 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
[2]T: 21.61 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
[3]T: 21.60 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
[4]T: 21.60 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
[5]T: 21.61 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
[6]T: 21.60 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
[7]T: 21.60 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
[8]T: 21.60 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
[9]T: 21.60 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
[10]T: 21.60 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
[11]T: 21.60 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
[12]T: 21.60 degC, P: 648.99 hPa, H 100.00 %rH
status = 80
The temperature is very accurate, and it responds perfectly to any changes. However, the RH and Humidity seem to be incorrect. Humidity never moves from 100%, and the pressure (649hPa=65kPa)) should be close to the current value of 100kpA .
Can anyone provide some help on what the issue might be?
Thank you,
Gary
Solved! Go to Solution.
11-13-2020 05:39 PM
Hi,
I'll reply to my own question and post the answer here as this will probably help anyone using an STM32 controller. Below is the I2C send and receive functions. Happy coding.
****************************************************************************************************************************************************************
int8_t user_i2c_read(uint8_t dev_id, uint8_t reg_addr, uint8_t *reg_data, uint16_t len)
{
int8_t rslt = 0; /* Return 0 for Success, non-zero for failure */
HAL_StatusTypeDef status;
// The device address is shared with I2C and SPI.
// When using SPI, it works on 7 bit mode.
// When using I2C, it works on 8 bit mode and we have to left shift the 7 bits.
// DOCS REFS: Datasheet Sections 6.
// Waiting for I2C to get freed from HAL bondage
while(HAL_I2C_IsDeviceReady(&hi2c1, (uint16_t) (dev_id << 1), 1, 100) != HAL_OK);
//HAL is never Ok, but we'll accept it
if(HAL_I2C_IsDeviceReady(&hi2c1, (uint16_t) (dev_id << 1), 1, 100) == HAL_OK)
{
// Writing register address to the slave
status = HAL_I2C_Master_Transmit(&hi2c1, (uint16_t) (dev_id << 1), ®_addr, sizeof(reg_addr), 100);
if(status != HAL_OK) rslt = -1;
// Reading registers starting from the sent address to the len
status = HAL_I2C_Master_Receive(&hi2c1, (uint16_t) (dev_id << 1), reg_data, len, 100);
if(status != HAL_OK) rslt = -1;
}
else
{
//do something, anything. print optional
//printf("I2C is busy...\r\n");
rslt = -1;
}
return rslt;
}
int8_t user_i2c_write(uint8_t dev_id, uint8_t reg_addr, uint8_t *reg_data, uint16_t len)
{
int8_t rslt = 0; /* Return 0 for Success, non-zero for failure */
// The device address is shared with I2C and SPI.
// When using SPI, it works on 7 bit mode.
// When using I2C, it works on 8 bit mode and we have to left shift the 7 bits.
// DOCS REFS: Datasheet Sections 6.
// Waiting for I2C to get freed
while(HAL_I2C_IsDeviceReady(&hi2c1, (uint16_t) (dev_id << 1), 1, 100) != HAL_OK);
if(HAL_I2C_IsDeviceReady(&hi2c1, (uint16_t) (dev_id << 1), 1, 100) == HAL_OK)
{
// We dont need to send stop bit when writing to sensor, a blocking mode direct write can be called here.
HAL_I2C_Mem_Write(&hi2c1, (uint16_t) (dev_id << 1), reg_addr, sizeof(reg_addr), reg_data, len, 100);
}
else
{
//printf("I2C is busy...\r\n");
rslt = -1;
}
return rslt;
}