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.
I'm writting to AT24C128 serial eeprom as shown by the datasheet and the read command shown below works, while the write command doesn't. I wrote to the chip using external programmer and it was ok, reading from it works fine, but writting doesn't. Can anyone check this code for me ? /****************************************************************************** * NAME: readAt * * DESCRIPTION: This function reads a byte at a specified address * ******************************************************************************/ unsigned char readAt(unsigned int address) { unsigned char data1; i2c_Start(); // make a start condition i2c_SendAddress(ROM, 0); // 0 write 1 read i2c_ReadAcknowledge(); // wait for acknowledge from eeprom i2c_SendByte(address >> 8); // send upper byte of address to eeprom i2c_ReadAcknowledge(); // wait for acknowledge from eeprom i2c_SendByte(address & 0xff); // send lower byte of address to eeprom i2c_ReadAcknowledge(); // wait for acknowledge from eeprom i2c_Start(); // make a start condition i2c_SendAddress(ROM, 1); // issue read command i2c_ReadAcknowledge(); // wait for acknowledge from eeprom data1 = (char)i2c_ReadByte(); // get data out of eeprom i2c_Stop(); // finish the process return(data1); // give data back to caller } /****************************************************************************** * NAME: writeAt * * DESCRIPTION: This function writes a byte to a specified address * ******************************************************************************/ void writeAt(unsigned int addr, unsigned char data) { i2c_Start(); // start condition i2c_SendAddress(ROM, 0); // 0 = write, 1 = read, ROM is 0xA0 i2c_ReadAcknowledge(); // wait for acknowledge from EEPROM i2c_SendByte(addr >> 8); // send upper address byte i2c_ReadAcknowledge(); // wait for acknowledge from EEPROM i2c_SendByte(addr & 0xff); // send lower address byte i2c_ReadAcknowledge(); // wait for acknowledge from EEPROM i2c_SendByte(data); // write the data to EEPROM i2c_ReadAcknowledge(); // wait for acknowledge from eeprom i2c_Stop(); // stop } I connected the WP to gnd, but the chip seems not to write either for error in the datasheet or I tried to make a memory reset function as indicated by the datasheet but I still have this problem. Thanks Mahmood
Can you post the code for the i2c_Stop routine? I would kind of suspect it. You only issue it in your read command AFTER you already have the data. If it is wrong you still have your read data. On the other hand, it it is wrong in your write command, the data will not be written.
Mahmood had posted on the 8052.com forum as well as here and it was there that he announced that his problem was solved. http://www.8052.com/forum/read.phtml?id=71829
Yes the problem was solved by finding another library on the internet that worked. the reason was I had a deadline and had to finish one project in that day. Now since I delivered my project and earned some cash (paid it all to a mechanic to repair a major engine damage in my car haha!) I don't mind fixing the errors in this library for future use because it looks nice. Here is the requested code: void i2c_Stop(void) { /* don't assume SCL is high on entry */ SDA_LOW(); /* ensure data is low first */ SCL_HIGH(); DelayUs(I2C_TM_DATA_SU); SCL_DIR = I2C_INPUT; /* float clock high */ DelayUs(I2C_TM_STOP_SU); SDA_HIGH(); /* the low->high data transistion */ DelayUs(I2C_TM_BUS_FREE); /* bus free time before next start */ SDA_DIR = I2C_INPUT; /* float data high */ return; } and here is the code for byte write unsigned char i2c_SendByte(unsigned char byte) { signed char i; for(i=7; i>=0; i--) { SCL_LOW(); /* drive clock low */ /* data hold time = 0, send data now */ SDA_DIR = ((byte>>i)&0x01); if ((byte>>i)&0x01) { /* bit to send */ SDA_HIGH(); } else { SDA_LOW(); } DelayUs(I2C_TM_DATA_SU); SCL_DIR = I2C_INPUT; /* float clock high */ if(i2c_WaitForSCL()) /* wait for clock release */ return TRUE; /* bus error */ DelayUs(I2C_TM_SCL_HIGH); /* clock high time */ } return FALSE; } Regards Mahmood