Unable to get range data from Devantech SRF10 -Solved

I’ve spent untold hours trying to get range data from this ultrasonic device. I2C communications appear to function for e.g. reading the firmware version, or changing the device address. And judging by the blinking LED on the SRF10 and the serial output, the ranging function is being started. But the Wire.available(), Wire.read() command sequence always returns 0.

  Wire.requestFrom(SRF_ADDRESS, 2);                // Request 2 bytes from SRF module
 while(Wire.available() < 2)                      // Wait for data to arrive
 highByte = Wire.read();                        // Get high byte
 lowByte = Wire.read();                         // Get low byte

 range = (highByte << 8) + lowByte;               // Put them together
 return(range);                                   // Returns Range

This is straight from example code provided for SRF I2C sensors.
I also tried using the SoftI2CMaster.h library; which always returns 1280 ( I suspect this represents the firmware version (5, from register 0x00) x 256 operation which is supposed to produce the high byte of the range ). Changing pull-up resistors, gain, delay intervals (“waiting for the ranging to be complete”), power supplies, and even downloading and using the version 1.0 Arduino IDE has been fruitless. I have two of the devices that I’ve tested and they both behave the same way.
My online research made me suspect that the Wire.h library could be broken in some sense – and that these problems started with a release in the 2011 - 2012 timeframe. Going back to version 1.0 seemingly would discredit that theory. I’m not really at a level where I can rewrite libraries in any case. I could surely use some help.


while(Wire.available() < 2) // Wait for data to arrive
highByte = Wire.read();

should be

while(Wire.available() < 2)   {}                 // Wait for data to arrive
 highByte = Wire.read();

Please provide us all the information: a link to the sensor please; which Arduino board do you use; a full sketch; how long are the I2C wires; what kind of cable is used for the I2C; and so on.

The Wire library is not broken.

The piece of code you gave could be wrong in 6 ways, it depends on the rest of the code : http://snippets-r-us.com/

I don't like to shift a 8-bit variable 8 times to the left. I would use integers for highbyte and lowbyte. I also prefer to check if 2 bytes are received. Waiting for bytes is not needed, after the Wire.requestFrom() returns, the complete I2C transmission has fully ended. I disagree with knut_ny, since there is nothing to wait for.

Start with the i2c_scanner : http://playground.arduino.cc/Main/I2cScanner Let it run for a while. Is it stable ?

The sensor module has no pullup resistors. Add 4k7 pullup resistors to 5V.

Next test is to request the firmware version in a loop. It that stable ? After that you can request the data. Does the sensor need time to get the resulting data ? Is a delay needed ? Is there a ready bit ? In the examples, there is only 1 ms delay.

Thanks to both of you for your replies. Turns out knut_ny was correct in saying I need braces after the while statement. I'm now receiving beautiful range readings! (You can't imagine how many little code variations I tried -- only never the correct one!) Bless You :)