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
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