Copyright © https://mongoose-os.com

Mongoose OS Forum

frame

Getting Started Problem with BME280 (I2C)

gadams999gadams999 Atlanta, GA

Hi,

I'm trying to understand the I2C setup for Mongoose on an esp8266. I have the sensor hooked up to GPIO 12 and 14, and from the datasheet have the following:

Address: 0x76 (118)
Chip Id Register: 0xD0 (208)
Chip Id value when read: 0x60 (96)

When I do mos call I2C.ReadRegB on the sensor, I get alternating responses:

$ mos call I2C.ReadRegB '{"addr": 118, "reg": 208}'
{
  "value": 96
}
$ mos call I2C.ReadRegB '{"addr": 118, "reg": 208}'
{
  "value": 3
}

When I should be getting the same response value of 96 (decimal). I've verified the sensor is working correctly on an RPi.

I see similar responses when making calls from C also:

b = mgos_i2c_read_reg_b(i2c, 0x76, 0xD0);
 LOG(LL_INFO, ("ID: 0xD0: 0x%02X", b));

Trying to understand what's going on here.

Side note, is there a reason when the RPC call I2C.Read only references an address and length, but not starting register?

Comments

  • rojerrojer Dublin, Ireland
    edited April 6

    for the latter - yes, the reason is that I2C.Read is a generic I2C read, it's basically "start, select device for reading, read N bytes, stop".

    as for the former... hard to say. set i2c.debug=true and set debug.level=3, it will show bit values that are read.

  • gadams999gadams999 Atlanta, GA

    Level 3 debug turned up nothing not expected. Here's the results from two calls 5 seconds apart (i2c_read_cb line is my print of the uint8_b read byte:

    mgos_i2c_start       12 14, addr 0x76, mode W => ab 0xec
    mgos_i2c_send_byte   sent 0xec, got ACK
    mgos_i2c_send_byte   sent 0xd0, got ACK
    mgos_i2c_start       12 14, addr 0x76, mode R => ab 0xed
    mgos_i2c_send_byte   sent 0xed, got ACK
    mgos_i2c_read_byte   read 0x03
    mgos_i2c_send_ack    sent ACK
    mgos_i2c_stop        stopped
    i2c_read_cb          ID: 0xD0: 0x03
    mgos_i2c_start       12 14, addr 0x76, mode W => ab 0xec
    mgos_i2c_send_byte   sent 0xec, got ACK
    mgos_i2c_send_byte   sent 0xd0, got ACK
    mgos_i2c_start       12 14, addr 0x76, mode R => ab 0xed
    mgos_i2c_send_byte   sent 0xed, got ACK
    mgos_i2c_read_byte   read 0x60
    mgos_i2c_send_ack    sent ACK
    mgos_i2c_stop        stopped
    i2c_read_cb          ID: 0xD0: 0x60

    The write and read registers are correct (reg << 1|mode). Is the Arduino compatibility to the point I could try Wiring?
  • rojerrojer Dublin, Ireland

    Wiring support is coming soon, but when it does, it will be using the same I2C implementation.
    while a bug in it is of course possible, i should say that it has been tested quite extensively. 0x60 is not even close to 0x03 in terms of hamming distance, it doesn't look like a bit error... what if you run it in a loop? is the error random?

  • gadams999gadams999 Atlanta, GA
    edited April 7

    The results are consistent. Alternating 0x60 and 0x03 being returned. I dropped in a few executions in the callback and the same result.

    `static void i2c_read_cb() {
    uint8_t b;
    int i;
    /* build i2c pointer to global settings */
    struct mgos_i2c *i2c = mgos_i2c_get_global();

    /* for BME280, address 0x76 and register 0xD0 should return 0x60 */
    for (i = 0; i < 10; i++) {
    b = mgos_i2c_read_reg_b(i2c, (uint16_t)0x76, (uint8_t)0xD0);
    LOG(LL_INFO, ("ID: 0xD0: 0x%02x", b));
    }
    }

    enum mgos_app_init_result mgos_app_init(void) {

    { /* Set up the blinky timer. /
    mgos_gpio_set_mode(LED_GPIO, MGOS_GPIO_MODE_OUTPUT);
    mgos_set_timer(1000 /
    ms /, true / repeat */, blink_timer_cb, NULL);
    }

    { /* Read I2C Bus /
    mgos_set_timer(5000, true /
    repeat */, i2c_read_cb, NULL);
    }

    return MGOS_APP_INIT_SUCCESS;
    }
    `
    I'll keep digging, will try SPI and see if that makes a difference.

  • rojerrojer Dublin, Ireland

    alternating between 0x03 and 0x60? this makes no sense to me. what if you read another register, like config?

  • I have a BMP280 and also plan to use it. I tried reading with RPC and got consistent values:

    # test read dig_T1 and dig_T2:
    
    mike@xenial:~$ umos call --port "http://esp-a.lan/rpc" I2C.ReadRegW '{"addr":118, "reg":136}'
    {
      "value": 17773
    }
    mike@xenial:~$ umos call --port "http://esp-a.lan/rpc" I2C.ReadRegW '{"addr":118, "reg":138}'
    {
      "value": 56166
    }
    

    But sometimes it fails with these in log:

    mg_rpc_send_frame    0x3ffef5e4 SEND FRAME (99): {"id":12670454
    01095,"src":"esp-a","dst":"mos","error":{"code":503,"message":"error reading value"}} ->
     1
    
    
  • rojerrojer Dublin, Ireland
    edited April 7

    @michaelfung can you test the vendor id (register 208)?

    wrt error - please turn on i2c.debug and set debug.level=3, let's see where the error happens.

  • @rojer said:
    michaelfung can you test the vendor id (register 208)?

    Repeated read get 88, 3, 88, 3, ...

    wrt error - please turn on i2c.debug and set debug.level=3, let's see where the error happens.

    mg_rpc_ev_handler    0x3fff17ec GOT FRAME (87): {"src":"mos","id":1314254187545,"method":"I2C.ReadRegW","args":{"addr":118,"reg":136}}
    
    mg_rpc_parse_frame   1314254187545 'mos' '' 'I2C.ReadRegW'
    mgos_i2c_start       12 14, addr 0x76, mode W => ab 0xec
    mgos_i2c_send_byte   sent 0xec, got NAK
    mgos_i2c_stop        stopped
    mg_rpc_send_frame    0x3fff17ec SEND FRAME (99): {"id":1314254187545,"src":"esp-a","dst":"mos","error":{"code":503,"message":"error reading value"}} -> 1
    
  • rojerrojer Dublin, Ireland

    something fishy is going on. i ordered a BME280 and will take a look once it's on my desk.

  • gadams999gadams999 Atlanta, GA

    Thanks rojer. FYI, this is the one I got (well, two since I thought my first one was b0rked): https://smile.amazon.com/gp/product/B01N47LZ4P/ref=oh_aui_detailpage_o01_s00?ie=UTF8&psc=1

  • @rojer , FYI: after I replaced firmware with esp8266/Arduino project, there is no read error.

    The sample sketch loop to gives these readings without error:

    Temperature = 27.54 *C
    Pressure = 100023.07 Pa
    Approx altitude = 108.96 m
    
  • rojerrojer Dublin, Ireland

    yes, i think there's something wrong with i2c timings and BME280 is just (more?) sensitive to it. i'll dig into it.

  • rojerrojer Dublin, Ireland

    BME280 arrived this morning and i've got to play with it. turns out, I2C read was not being finalized properly: last byte of the read should be NAK'd if master does not intend to read more. instead, mOS would ack all the bytes, including the last one, and then issue a stop condition.
    normally stop condition resets the slave and it would forget whatever it was doing, but not BME280 - despite master's STOP, it would continue holding the bus, waiting for more clock pulses to read more bytes.
    8cf71ae fixes this.

  • gadams999gadams999 Atlanta, GA

    Yessir, fixed!

    mgos_i2c_start       14 12, addr 0x76, mode W => ab 0xec
    mgos_i2c_send_byte   sent 0xec, got ACK
    mgos_i2c_send_byte   sent 0xd0, got ACK
    mgos_i2c_start       14 12, addr 0x76, mode R => ab 0xed
    mgos_i2c_send_byte   sent 0xed, got ACK
    mgos_i2c_read_byte   read 0x60
    mgos_i2c_send_ack    sent NAK
    mgos_i2c_stop        stopped
    i2c_read_cb          ID: 0xD0: 0x60
    mgos_i2c_start       14 12, addr 0x76, mode W => ab 0xec
    mgos_i2c_send_byte   sent 0xec, got ACK
    mgos_i2c_send_byte   sent 0xd0, got ACK
    mgos_i2c_start       14 12, addr 0x76, mode R => ab 0xed
    mgos_i2c_send_byte   sent 0xed, got ACK
    mgos_i2c_read_byte   read 0x60
    mgos_i2c_send_ack    sent NAK
    mgos_i2c_stop        stopped
    i2c_read_cb          ID: 0xD0: 0x60
  • Hi @gadams999 , would you share your code after you finish? Cause I am lazy and don't want to re-invent the wheel :wink: Otherwise, I need to adapt Adafruit's code.

  • @gadams999 said:
    michaelfung - Here's some working code for the BME280:
    https://github.com/gadams999/mongoose-examples/tree/master/bme280

    That's great! Many thanks! I will try it with my BMP280 with some adjustment.

Sign In or Register to comment.