Help Please - I2C Addressing
Hello All...
I am trying to address a Silicon Labs (www.silabs.com) Si570 LVDS clock generator (P/N 570CAC000141DG) via I2C. The part is on dedicated propeller pins with 10k pull-ups. I also have a 24LC256 EEPROM on the same bus.
The application is based on James Burrows's I2C demo object from ObEx, which uses a slightly modified version of Mike Green's Basic_I2C_Driver. The EEPROM's device address is 1010_0010, the Si570's address is 55h or 1010_101X per the I2C spec where the addresses are 7 digits left-justified and the LSB is the R/W bit. I used AAh or 1010_1010 for the I2C address in the propeller application.
I can write/read to/from the EEPROM just fine. At first I couldn't read the Si570 at the expected register locations of 7 through 12 decimal. So I did an I2C bus scan. I know what the startup values of registers 7 through 12 should look like. Voila, I found them via the bus scan. Here's what I found:
Each register value appears for 256 bits of location range. Other users of this chip say this is wrong, I should read register 07 at location 07h, and register 12 at Ch. I've looked at the Si570's ANSI C reference software for 8051 from Silicon Labs, that code seems to confirm the register locations are one-to-one with the register number.
But with propeller, not only am I seeing the registers at much higher locations, even the "alignment" of the registers seems off by at least one in the MSBs! When I read and write to the EEPROM, the data and locations are as expected - unlike the Si570.
The Si570 data sheet says the register location addresses auto-increment. Maybe this is causing it? I'm using one readByte per register.
I haven't tried writing to the Si570 yet, I would like to get this read problem fixed first.
Has anyone seen this before? Any suggestions? This is the first time I've dealt with I2C. I have read the NXP I2C manual, but the act of reading doesn't always guarantee complete absorption!
Thanks & Best Regards,
David
Post Edited (Drone) : 5/21/2008 4:06:46 PM GMT
I am trying to address a Silicon Labs (www.silabs.com) Si570 LVDS clock generator (P/N 570CAC000141DG) via I2C. The part is on dedicated propeller pins with 10k pull-ups. I also have a 24LC256 EEPROM on the same bus.
The application is based on James Burrows's I2C demo object from ObEx, which uses a slightly modified version of Mike Green's Basic_I2C_Driver. The EEPROM's device address is 1010_0010, the Si570's address is 55h or 1010_101X per the I2C spec where the addresses are 7 digits left-justified and the LSB is the R/W bit. I used AAh or 1010_1010 for the I2C address in the propeller application.
I can write/read to/from the EEPROM just fine. At first I couldn't read the Si570 at the expected register locations of 7 through 12 decimal. So I did an I2C bus scan. I know what the startup values of registers 7 through 12 should look like. Voila, I found them via the bus scan. Here's what I found:
Reg, Addresses, Val ------------------- R07, 600h-6FFh, E1h R08, 700h-7FFh, C2h R09, 800h-8FFh, 86h R10, 900h-9FFh, 16h R11, A00h-AFFh, A9h R12, B00h-BFFh, 9Dh
Each register value appears for 256 bits of location range. Other users of this chip say this is wrong, I should read register 07 at location 07h, and register 12 at Ch. I've looked at the Si570's ANSI C reference software for 8051 from Silicon Labs, that code seems to confirm the register locations are one-to-one with the register number.
But with propeller, not only am I seeing the registers at much higher locations, even the "alignment" of the registers seems off by at least one in the MSBs! When I read and write to the EEPROM, the data and locations are as expected - unlike the Si570.
The Si570 data sheet says the register location addresses auto-increment. Maybe this is causing it? I'm using one readByte per register.
I haven't tried writing to the Si570 yet, I would like to get this read problem fixed first.
Has anyone seen this before? Any suggestions? This is the first time I've dealt with I2C. I have read the NXP I2C manual, but the act of reading doesn't always guarantee complete absorption!
Thanks & Best Regards,
David
Post Edited (Drone) : 5/21/2008 4:06:46 PM GMT
Comments
Mike, I'm using ReadByte and WriteByte with the Si570. Hmmm...
The basic_I2C_driver seems to use 16 bit addresses as you mentioned, how to use 8 bit addresses (looking at the driver source more carefully now - should have done that in the first place).
Rgds, David
Post Edited (Drone) : 5/21/2008 4:11:42 PM GMT
Will you share these drivers with us? Are they already in ObEx?
Rgds, David
It took very little time to get correct byte reads from the Si570 calling your i2c drivers; nice! I'll try writes tomorrow. Indeed the Si570's register locations match their names (at lest reg07 - reg12) using your driver. Very nice how you profile devices in Open vs. OpenRaw.
Many Thanks - David
Now Si570 reads and writes are working, as well as new frequency writes to the part using either OpenRaw and #0 CON enumeration with your driver. I'm using the Protoboard version driver with the pull-ups on dedicated pins for the Si570. This is probably a stupid question, but I'll throw it out anyway... If you have a driver that can handle I2C without pull-ups, why do you need to have a separate driver without pull-ups? In-practice, I've used Mike Green's driver which supports parts without pull-ups and it works if I have have pull-ups both with a 24LC256 and the Si570 (Si570 bus-scan only, and native offset 16 bit addressing with Mike's driver), using dedicated I2C pins separate from the main EEPROM.
Rgds, David
The hard-drive which works with or without SCL pull-up cannot support clock-stretching nor multi-master mode and is less safe for use.
This has always concerned me - Given that the Propeller hard-drives the SCL line during booting ( even with a pull-up ), if there's an I2C device on that bus which is in a fault mode it can be pulling a high SCL down and that would present a short to 0V on the SCL pin which could damage the Propeller.
It seems a strange design decision to have made despite the risk being low. The worst case is where a master driver of a user's application has set its SCL high and is waiting for the SCL line to go high with no timeout while another device is holding SCL low.