DS3231 and I2C problem

I got a DS3231 clock module a few days a go when a friend of my Dad brought a sensor kit from the States (I currently live in Argentina). I have been trying quite a lot to get it work: tried many different sketches and libraries, used different Arduinos, changed connection cables, used both 5v and 3.3v, tried another 3v button battery for the module, changed the Wire addresses, and finally, after a long while of not getting results, I used the I2c scanner to see if the board actually found the device. Unfortunately, it didn´t (neither the 0x68 nor the 0x57, addresses of both ICs on the PCB). I only remember having connected the Vcc and Gnd incorrectly once or twice (switched them accidentally), but the LED still lights up on the DS3231. Any Ideas please?
*I believe the problem is not software related. Could a faulty battery contact be to blame?

P.S.: I would really like if I didn´t have to buy a new one, since here in Argentina they aren´t exactly cheap and I would like to use it soon for some of my projects.

Why did you think your question has something to do with the way this Forum works?

I am suggesting to the Moderator to move it to the Project Guidance section.

…R

Thread moved.

It could be that the I2C bus has locked up (or if not, a problem you may hit downstream). It was a problem I had with a DS3231 (and a 1307) sharing the I2C bus with a BME280 (temp, pressure, humidity). Had me head scratching for a couple of days. Googled around and eventually ended up with three functions:

  • Check status of the bus and reset by calling…
  • Modified i2C scan
  • Reset i2Cbus

You will need to modify the code for your processor (SDA and SCL pins - I was running it on a nodemcu). Note - logf is a function writing to an error log file. None of it is original - all ‘borrowed’ from the web and modified. If nothing else, it should help establish whether you have trashed the DS3231.

/*------------------------------------------------------
 * FUNCTION - wireCheck()
 * checks the status of the i2c bus and if no available devices
 * resets the bus and restarts wire
 * 
 --------------------------------------------------------*/
void wireCheck() {
  byte status;
  status = I2Cscan(); /* scan I2C bus for connected devices - RTC and BME280 */
  if(i2cstatus == 0){ /* no connected I2C devices */
    logf("I2C bus - no devices, resetting...");
    I2C_ClearBus(); /* try to reset the I2C bus */
    Wire.begin();
    Serial.println("Second attempt at starting I2C bus");
    status = I2Cscan(); 
    if(i2cstatus == 0){logf("Failed to restart I2C bus");}
    }
} /* end function wireCheck() */
/*------------------------------------------------------
 * FUNCTION - I2C_ClearBus
 * (http://www.forward.com.au/pfod/ArduinoProgramming/I2C_ClearBus/index.html)
 * (c)2014 Forward Computing and Control Pty. Ltd.
 * NSW Australia, www.forward.com.au
 * This code may be freely used for both private and commerical use
 *
 * This routine turns off the I2C bus and clears it
 * on return SCA and SCL pins are tri-state inputs.
 * You need to call Wire.begin() after this to re-enable I2C
 * This routine does NOT use the Wire library at all.
 *
 * returns 0 if bus cleared
 *         1 if SCL held low.
 *         2 if SDA held low by slave clock stretch for > 2sec
 *         3 if SDA held low after 20 clocks.
 *         
 *  mapping for the esp8266
 *    D0 = GPIO16;
 *    D1 = GPIO5; this is the default for wire for SCL
 *    D2 = GPIO4; confirmed with test as how i2c setup = SDA
 *                this is also the default for wire
 *    D3 = GPIO0;
 *    D4 = GPIO2; on the esp8266 this is the blue led
 *    D5 = GPIO14; 
 *    D6 = GPIO12;
 *    D7 = GPIO13;
 *    D8 = GPIO15;
 *    D9 = GPIO3;
 *    D10 = GPIO1;
 *    LED_BUILTIN = GPIO16 (auxiliary constant for the board LED, not a board pin);
 --------------------------------------------------------*/
short I2C_ClearBus() {
  pinMode(SDA, INPUT_PULLUP); /* Make SDA (data) and SCL (clock) pins Inputs with pullup. */
  pinMode(SCL, INPUT_PULLUP);

  delay(2500);  /* Wait 2.5 secs. This is strictly only necessary on the first power
                 * up of the DS3231 module to allow it to initialize properly,
                 * but is also assists in reliable programming of FioV3 boards as it gives the
                 * IDE a chance to start uploaded the program  before existing sketch 
                 * confuses the IDE by sending Serial data. */

  boolean SCL_LOW = (digitalRead(SCL) == LOW); // Check is SCL is Low.
  if (SCL_LOW) { return 1; } /* I2C bus error. Could not clear SCL clock line held low */
                             /* If it is held low Arduno cannot become the I2C master. */ 
  boolean SDA_LOW = (digitalRead(SDA) == LOW);  // vi. Check SDA input.
  int clockCount = 20; // > 2x9 clock

  while (SDA_LOW && (clockCount > 0)) { /*  vii. If SDA is Low, */
    clockCount--;
    /* Note: I2C bus is open collector so do NOT drive SCL or SDA high. */
    pinMode(SCL, INPUT);   /* release SCL pullup so that when made output it will be LOW */
    pinMode(SCL, OUTPUT);  /* then clock SCL Low */
    delayMicroseconds(10); /* for >5uS */
    pinMode(SCL, INPUT); // release SCL LOW
    pinMode(SCL, INPUT_PULLUP); /* turn on pullup resistors again */
    /* do not force high as slave may be holding it low for clock stretching. */
    delayMicroseconds(10); /* for >5uS */
    /* The >5uS is so that even the slowest I2C devices are handled. */
    SCL_LOW = (digitalRead(SCL) == LOW); /* Check if SCL is Low. */
    int counter = 20;
    while (SCL_LOW && (counter > 0)) {  /* loop waiting for SCL to become High only wait 2sec. */
      counter--;
      delay(100);
      SCL_LOW = (digitalRead(SCL) == LOW); }
    if (SCL_LOW) { return 2; }
    /* still low after 2 sec error I2C bus error. Could not clear. SCL clock line 
     * held low by slave clock stretch for >2sec */
    SDA_LOW = (digitalRead(SDA) == LOW); //   and check SDA input again and loop
  } /* end while */
  if (SDA_LOW) { return 3; }
  /* still low,I2C bus error. Could not clear. SDA data line held low */
 
  /* else pull SDA line low for Start or Repeated Start */
  pinMode(SDA, INPUT); /* remove pullup. */
  pinMode(SDA, OUTPUT);  /* and then make it LOW i.e. send an I2C Start or Repeated start control.
                          * When there is only one I2C master a Start or Repeat Start has the same 
                          * function as a Stop and clears the bus. A Repeat Start is a Start 
                          * occurring after a Start with no intervening Stop. */
  delayMicroseconds(10); /* wait >5uS */
  pinMode(SDA, INPUT);   /* remove output low */
  pinMode(SDA, INPUT_PULLUP); /* and make SDA high i.e. send I2C STOP control. */
  delayMicroseconds(10);      /* x. wait >5uS */
  pinMode(SDA, INPUT);   /* and reset pins as tri-state inputs which is the default state on reset */
  pinMode(SCL, INPUT);
  return 0; /* all ok */
} /* end function I2C_ClearBus() */
*------------------------------------------------------
 * FUNCTION - I2Cscan
 * A startup function, scans the I2C bus for connected devices
 * with the RTC and BME connected three should be found
 *  0x57 - this is the RTC according to amazon
 *  0x68 - so what is this
 *  0x76 - BME280
 *  
 *  Results written to serial
 --------------------------------------------------------*/
byte I2Cscan() {
  byte error, address;
  byte adds[5] = {0,0,0,0,0}; /* to contain adddresses of devices found */
  int nDevices, i; /*loop counters */

  Serial.println("Scanning I2C bus (for max 5 devices)...");

  nDevices = 0;
  for(address = 1; address < 127; address++ ) {
    /* The i2c_scanner uses the return value of
     * the Write.endTransmisstion to see if
     * a device did acknowledge to the address. */
    Wire.beginTransmission(address);
    error = Wire.endTransmission();
    if (error == 0) {
      adds[nDevices] = address;
      nDevices++; 
      if(nDevices > 5) nDevices = 5;}
    }    
  if (nDevices == 0) {
    Serial.println("No I2C devices found\n"); }
  else {
    Serial.print("Number of I2C devices found = ");
    Serial.println(nDevices);
    Serial.print("Addresses ");
    for (i = 0; i < nDevices; i++) {
      Serial.print("0x");
      Serial.print(adds[i],HEX);
      Serial.print(", "); }
  }
  Serial.println();
  return nDevices;
} /* end function I2Cscan */

I only remember having connected the Vcc and Gnd incorrectly once or twice (switched them accidentally), but the LED still lights up on the DS3231.

It is probably dead. The LED won't necessarily be destroyed by connecting the power backwards, but the chips will be.