We are running a survey to help us improve the experience for all of our members. If you see the survey appear, please take the time to tell us about your experience if you can.
hi friends, this is my very first post in this forum. I'm trying to interface a 32Kbits EEprom 24c32 with AT89c52, but i'm not able to achieve the goal. I found this code for 24c256 EEPROM on net which i'm using, but i think there should'nt be a difference for 24c32.
//--------------------------------------- // 24LC256 I2C EEPROM driver // http://www.GetMicro.com //--------------------------------------- #include<reg8252.h> #include<intrins.h> # #define ACK 1 #define NO_ACK 0 unsigned char i; sbit SDA = P2^1; // connect to SDA pin (Data) sbit SCL = P2^0; // connect to SCL pin (Clock) //------------------------------- // start I2C //------------------------------- void Start(void) { SDA = 1; SCL = 1; _nop_();_nop_(); SDA = 0; _nop_();_nop_(); SCL = 0; _nop_();_nop_(); } //------------------------------- // stop I2C //------------------------------- void Stop(void) { SDA = 0; _nop_();_nop_(); SCL = 1; _nop_();_nop_(); SDA = 1; } //------------------------------- // Write I2C //------------------------------- void WriteI2C(unsigned char Data) { for (i=0;i<8;i++) { SDA = (Data & 0x80) ? 1:0; SCL=1;SCL=0; Data<<=1; } SCL = 1; _nop_();_nop_(); SCL = 0; } //------------------------------- // Read I2C //------------------------------- unsigned char ReadI2C(bit ACK_Bit) { unsigned char Data=0; SDA = 1; for (i=0;i<8;i++) { SCL = 1; Data<<= 1; Data = (Data | SDA); SCL = 0; _nop_(); } if (ACK_Bit == 1) SDA = 0; // Send ACK else SDA = 1; // Send NO ACK _nop_();_nop_(); SCL = 1; _nop_();_nop_(); SCL = 0; return Data; } //------------------------------- // Read 1 byte form I2C //------------------------------- unsigned char ReadBYTE(unsigned int Addr) { unsigned char Data; Start(); WriteI2C(0xA0); WriteI2C((unsigned char)(Addr>>8)&0xFF); WriteI2C((unsigned char)Addr&0xFF); Start(); WriteI2C(0xA1); Data = ReadI2C(NO_ACK); Stop(); return(Data); } //------------------------------- // Write 1 byte to I2C //------------------------------- void WriteBYTE(unsigned int Addr,unsigned char Data) { Start(); WriteI2C(0xA0); WriteI2C((unsigned char)(Addr>>8)&0xFF); // send address high WriteI2C((unsigned char)Addr&0xFF); // send address low WriteI2C(Data); Stop(); }
Please help me out.
Thanks
With best regards Neelam
Hi,
At the very least I would add a few _nop_(); in your ReadI2C and WriteI2C routines between all changes to SDA and SCL lines because - unless you are using a very slow processor XTAL - you will probably be toggling the lines at >400kHz for 'High Speed' I2C and most definitly >100kHz for the 'standard' I2C.
So check your processors XTAL so you can work out how long it takes to execute a nop instruction then check the I2C timing requirements and add (more than) enough nops to bring the I2C bus timings into spec.
Mark.
I would like to help you, but I do not have the time to decipher your scribbles.
scribbles: NOTHING without comments can be called 'code'
Erik