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

I2C clock cannot go below 30MHz as prescaler is not calculated #495

Open
ladyada opened this issue Jul 31, 2022 · 1 comment
Open

I2C clock cannot go below 30MHz as prescaler is not calculated #495

ladyada opened this issue Jul 31, 2022 · 1 comment

Comments

@ladyada
Copy link

ladyada commented Jul 31, 2022

https://github.com/arduino/ArduinoCore-avr/blob/master/libraries/Wire/src/utility/twi.c#L139
doesn't calculate/change the TWSR prescaler, which means that we can't get below approx 16mhz / 255*2 = 30KHz
i'm happy to submit a PR, would look like this (TWSR is write-only on the two lowest bits)

  // calculate TWBR correctly
  uint8_t prescaler = 1;
  uint32_t atwbr = ((F_CPU / desiredclk) - 16) / 2;
  if (atwbr <= 255) {
    prescaler = 1;
    TWSR = 0x0;
  } else if (atwbr <= 1020) {
    atwbr /= 4;
    prescaler = 4;
    TWSR = 0x1;
  } else if (atwbr <= 4080) {
    atwbr /= 16;
    prescaler = 16;
    TWSR = 0x2;
  } else if (atwbr <= 16320) {
    atwbr /= 64;
    prescaler = 64;
    TWSR = 0x3;
  }
  TWBR = atwbr;
@RobTillaart
Copy link

@per1234
+1 for this issue. Important to connect to low speed devices e.g. AGS02MA
Such a solution would allow support for I2C bus speed from ~30 KHz down to 500 Hz (also think long wires)

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

2 participants