I2C Address Scanner

I have a project with multiple i2c devices deployed in the field reporting to the cloud via UDP. The service I’m using doesn’t accept HEX only integers.

For some strange reason a few of my sensors are changing address (I wish I could figure this out too but not the subject of this post). I’d like to flash OTA a sketch to check the addresses find the address which is wrong and then flash another code to change it back.

I do NOT have direct access to the devices.

I have been trying to use int variables to store the addresses. I can use a converter back on my end to translate from DEC to HEX.

What I am running into is I can only read the FIRST or LAST sensor address but no others.

Admittedly my understandings of loops sucks. Not for lack of trying. Any assistance would be much appreciated.

Thanks!

-Roger

#include <Wire.h>

const int numsensors = 127;
uint8_t SensorAdr[numsensors];
uint8_t adr1, adr2, adr3, adr4;

void setup()
{
  Wire.begin();
 
  Serial.begin(9600);
  while (!Serial);             // Leonardo: wait for serial monitor
  Serial.println("\nI2C Scanner");
}
 
 
void loop()
{
  byte error, address;
  int nDevices;
  int j;
  Serial.println("Scanning...");
  
    for(j=0; j<numsensors; j++);
  {
    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)
      {
       Serial.print("I2C device found at address 0x");
        if (address<16)
          Serial.print("0");
          Serial.print(address,HEX);
          SensorAdr[numsensors] = (address,DEC);
          Serial.println("  !");
       j++;
       }
      else if (error==4)
      {
        Serial.print("Unknown error at address 0x");
        if (address<16)
          Serial.print("0");
         Serial.println(address,HEX);
      }    

    }
  }

  

  delay(5000);           // wait 5 seconds for next scan

  

  Serial.println("Sensor Adresses:");
  Serial.println(SensorAdr[numsensors]);
  Serial.println(adr1);
  Serial.println(adr2);
  Serial.println(adr3);
  Serial.println(adr4);
  
}

This is my Serial read out:
Sensor Adresses:
11:02:45.955 → 10
11:02:45.955 → 0
11:02:45.955 → 0
11:02:45.955 → 0
11:02:45.955 → 0
11:02:45.955 → Scanning…
11:02:45.955 → I2C device found at address 0x20 !
11:02:45.955 → I2C device found at address 0x25 !
11:02:45.955 → I2C device found at address 0x30 !
11:02:45.955 → I2C device found at address 0x44 !
11:02:45.955 → No I2C devices found
11:02:45.955 →

    for(j=0; j<numsensors; j++);

This isn’t going to get you very far. Get rid of the semicolon at the end of the line.

But then, why do you have nested for loops? If you go through the inner loop once and find the responding addresses, it won’t find anything different the second and subsequent times.

Pete

Thanks Pete

I removed the semicolon.

I was modeling it off of the scanner from: Arduino Playground - I2cScanner.

I don't get the addresses except from the Serial.print(address,HEX);

I can't use serial print for my application because my sensors are 4 hours away. If I could find out the address of the sensor which is wrong I could fix it remotely.