Skip to content
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

ULP reads one additional invalid bit from I2C chip register #938

Closed
Mucka opened this issue Aug 28, 2017 · 5 comments
Closed

ULP reads one additional invalid bit from I2C chip register #938

Mucka opened this issue Aug 28, 2017 · 5 comments

Comments

@Mucka
Copy link

Mucka commented Aug 28, 2017

I am using ULP coprocessor to read data from digital mems sensor. But i2c_rd ulp instruction seems to work incorrectly. Every time I am reading external device register I am receiving data shifted left and stuffed with 1 bit, for example I see on oscilloscope correct transmission with 0x33 byte sent by device but on ULP side I see 0x67 byte, when I see 0xFB on oscilloscope I see 0xF7 on ULP side. My code is simple:

void print_axis_x() {
    uint32_t *axis_x = &ulp_acc_axis_x;
    for (int i = 0; i < 256; i++) {
        printf("X[%03d]: %08x\n", i, (uint32_t)axis_x[i]);
    }
}
.bss

.global acc_axis_x
acc_axis_x:
    .space 1024

.global counter
counter:
    .long 0

.set RTC_CNTL_STATE0_REG, 0x6
.text
.global entry
entry:
    wait 1000
    /* Read acc axis X */
    move r0, 0x0000
    i2c_rd 0x0F, 7, 0, 0 // Who Am I register
    /* Store acc axis x in acc_axis_x array offset counter */
    move r1, counterani to ani to
    ld r2, r1, 0x0
    move r3, acc_axis_x
    add r2, r2, r3
    st r0, r2, 0x0  // Save acc sample to memory
    /* Increment sample counter */
    move r1, counter
    ld r0, r1, 0x0
    add r0, r0, 0x1
    st r0, r1, 0x0
    jumpr quit, 256, ge
    halt
quit:
    // Disable ULP timer
    // RTC_CNTL_ULP_CP_SLP_TIMER_EN -> Bit 24
    reg_wr RTC_CNTL_STATE0_REG, 24, 24, 0x0
    wake
    halt

When starting ULP I am using option

    ESP_ERROR_CHECK( esp_deep_sleep_pd_config(ESP_PD_DOMAIN_RTC_PERIPH, ESP_PD_OPTION_ON) );

which was mentioned in one of previous issues about ULP I2C, maybe this is a problem (but without this line I am unable to wake up main CPU anyway). I am receiving output:

X[000]: 00e200F7
X[001]: 00e200F7
X[002]: 00e200F7
X[003]: 00e200F7
X[004]: 00e200F7
X[005]: 00e200F7
X[006]: 00e200F7
X[007]: 00e200F7
X[008]: 00e200F7

when I clearly (I2C transmission on oscilloscope is correct) should receive 0x7B so my most significant bit is lost.

I have used I2C configuration from previous issue so I hope it is not a problem:

    WRITE_PERI_REG(SENS_SAR_I2C_CTRL_REG, 0);
    WRITE_PERI_REG(RTC_I2C_SCL_LOW_PERIOD_REG, 40);
    WRITE_PERI_REG(RTC_I2C_SCL_HIGH_PERIOD_REG, 40);
    WRITE_PERI_REG(RTC_I2C_SDA_DUTY_REG, 16);
    WRITE_PERI_REG(RTC_I2C_SCL_START_PERIOD_REG, 30);
    WRITE_PERI_REG(RTC_I2C_SCL_STOP_PERIOD_REG, 44);
    WRITE_PERI_REG(RTC_I2C_TIMEOUT_REG, 1000);	
    WRITE_PERI_REG(RTC_I2C_CTRL_REG, 0x00000010);

but as I mentioned, communication on I2C lines is perfectly fine, only data stored in memory is incorrect. I have also noticed that bit mask field of i2c_rd instruction does not work, I can put there any numbers and instruction works exactly the same (no bits are masked or anything).

@igrr
Copy link
Member

igrr commented Aug 28, 2017

The issue is that RTC I2C controller samples SDA on the falling edge of SCL, rather than on the rising edge (as a well-behaving I2C device should). This is mentioned in section 26.6.2.1 of the TRM (v2.3)

The RTC_I2C peripheral samples the SDA signals on the falling edge of SCL. If the slave changes SDA in less than 0.38 microseconds, the master will receive incorrect data.

@Mucka
Copy link
Author

Mucka commented Aug 30, 2017

@igrr Thanks, that dispelled my doubts.

@FayeY
Copy link
Collaborator

FayeY commented Sep 4, 2017

@Mucka , is this issue solved? Can we close it?

@Mucka
Copy link
Author

Mucka commented Sep 4, 2017

Sorry, for leaving it open.

@Mucka Mucka closed this as completed Sep 4, 2017
@vaibhav810
Copy link

Same issue

  1. data is always shifted by 1 bit( & on top of it, sometimes that bit is also flipped )
  2. bit mask field is also not working

So data on Logic analyser and data on R0 register are not matching

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