Skip to content

The pio_i2c example's write operation corrupt every subsequent transaction. #168

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
ithinuel opened this issue Oct 19, 2021 · 2 comments
Assignees

Comments

@ithinuel
Copy link

Tested using an NXP LM75B temperature sensor.

Minimal code to reproduce:

#include <stdio.h>

#include "pico/stdlib.h"
#include "pio_i2c.h"

#define PIN_SDA 20
#define PIN_SCL 21

// data must be at least 2 bytes long.
void print_temperature(uint8_t *data) {
    int16_t data_i16 = ((int16_t)data[0]) << 8 | (data[1] & 0xE0);
    float temp = (float)data_i16 * 0.125;
    printf("%0.2fC\n", temp);
}

int main() {
    stdio_init_all();

    PIO pio = pio0;
    uint sm = 0;
    uint offset = pio_add_program(pio, &i2c_program);
    i2c_program_init(pio, sm, offset, PIN_SDA, PIN_SCL);

    uint8_t data[2] = {0};
    // LM75B's default pointer is to temperature register.
    pio_i2c_read_blocking(pio, sm, 0x48, data, 2);
    print_temperature(data);

    // Set pointer register to Temperature register.
    data[0] = 0x0;
    pio_i2c_write_blocking(pio, sm, 0x48, data, 1);

    // Read again temperature now corrupted
    pio_i2c_read_blocking(pio, sm, 0x48, data, 2);
    print_temperature(data);

    printf("Done.\n");
    return 0;
}
@ithinuel ithinuel changed the title The pio_i2c example's write operation do not work and corrupt every subsequent transaction. The pio_i2c example's write operation corrupt every subsequent transaction. Oct 19, 2021
@ithinuel
Copy link
Author

The issue seems to lie in the ISR's state after a write operation (where autopush is disabled but the ISR isn't cleared).

@yiding
Copy link

yiding commented Jul 25, 2024

I noticed this as well. adding a mov isr, null to the beginning of do_byte in i2c.pio seems to resolve this...

There's also additional posts in the RPI forums about this issue:
https://forums.raspberrypi.com/viewtopic.php?t=340111
https://forums.raspberrypi.com/viewtopic.php?p=2138637

In the forum discussions it's not clear how ISR count can end up in a de-synchronized state, since the pio program will always loop 8 bits.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants