Hi! I'm programming an EEPROM with the i2c protocol, and i'm having problems with it. I'm trying to write one byte in the EEPROM to read it, but the problem is that I'm not able to read that byte.
Waching it with an osciloscope, seems like al the data it's sent right, but when reading it, the value that it returns is FFh even when I set 00h as the byte to write. In the Datasheet it is speficied that the power-on default value for the EEPROM is FFh.
After some modifications I achieve to return a 00h, but again, now always returns a 00h even if a write for example a 50h.
I've been searching a lot about this EEPROM but there is few information about it. This is my code for wrting and reading:
void I2C1ByteWriteM24256( _SOFT_U8BITS u8deviceaddress, _SOFT_U8BITS u8highaddress, _SOFT_U8BITS u8lowaddress, _SOFT_U8BITS u8bytevalue){
_SOFT_U8BITS u8address
u8address = u8deviceaddress;
u8address = u8address << 1;
u8address = u8address | 0x00;
i2c1_Start();
I2C1_D = u8address;//((u8deviceaddress << 1) | 0x00);//Write mode
i2c1_Wait();
I2C1_D = u8highaddress;
i2c1_Wait();
I2C1_D = u8lowaddress;
i2c1_Wait();
I2C1_D = u8bytevalue;
i2c1_Wait();
i2c1_Stop();
Pause();
_SOFT_U8BITS I2C1RandomAddresSReadM24256( _SOFT_U8BITS u8deviceaddress, _SOFT_U8BITS u8highaddress, _SOFT_U8BITS u8lowaddress){
_SOFT_U8BITS u8address;
_SOFT_U8BITS u8addressW;
_SOFT_U8BITS u8addressR;
_SOFT_U8BITS u8return_value;
u8address = u8deviceaddress;
u8addressW = (u8address << 1) | MWSR; //0x00 Para escritura
u8address = u8deviceaddress;
u8addressR = (u8address << 1) | MRSW; //0x01 Para lectura
i2c1_Start();
i2c1_write_byte (u8addressW);
i2c1_Wait();
i2c1_write_byte (u8highaddress);
i2c1_Wait();
i2c1_write_byte (u8lowaddress);
i2c1_Wait();
i2c1_RepeatedStart();
i2c1_write_byte (u8addressR);
i2c1_Wait();
i2c1_EnterRxMode();
u8return_value = i2c_read_byte();
i2c1_Wait();
i2c1_DisableAck();
i2c1_Stop();
u8return_value = i2c_read_byte();
Pause();
return(u8return_value);
Hard to say if your functions do the correct things, but I will tell you this - after writing to an EEPROM chip, the chip has to re-write the entire sector and it take quite a bit of time. While this is happening, the chip will NAK you until it is ready again, so you need to loop on getting NACKS to tell when it is done re-writing the sector.
Again, I have no idea what your code is doing, but the "pause" should be something on the order of 10ms.
You are not even checking the status bits (at least as far as I can tell) - you need to know if you are getting ACKs or not in the writes.
It is not clear that the writes are working....
I'll try to explain the code a little bit so that way maybe we can get to the solution.
I've checked the i2c signal with the scope and the datasheet specs and it seems to do it right, at least it sends right ACKs. At first it reads FFh (default power-on value), meaning that it didn’t write the byte. Now, it reads always 00h, indepenent of the value that I send.
Maybe I’m forgeting some code or doing something wrong, but I don’t see it.
void I2C1ByteWriteM24256( _SOFT_U8BITS u8deviceaddress, _SOFT_U8BITS u8highaddress, _SOFT_U8BITS u8lowaddress, _SOFT_U8BITS u8bytevalue){ //Write function code
_SOFT_U8BITS u8address
u8address = u8deviceaddress; //This part only configures the address for write mode
u8address = u8address << 1;
u8address = u8address | 0x00;
i2c1_Start(); //Star condition
I2C1_D = u8address;//((u8deviceaddress << 1) | 0x00);//Write mode //Device address in write mode
i2c1_Wait(); //Wait for ack
I2C1_D = u8highaddress; //Memory high address
i2c1_Wait();
I2C1_D = u8lowaddress; //Memory low address
i2c1_Wait();
I2C1_D = u8bytevalue; //Sent byte
i2c1_Wait();
i2c1_Stop(); //Stop condition
Pause(); //Small counter to wait to the function response
_SOFT_U8BITS I2C1RandomAddresSReadM24256( _SOFT_U8BITS u8deviceaddress, _SOFT_U8BITS u8highaddress, _SOFT_U8BITS u8lowaddress){ //Read function code
_SOFT_U8BITS u8address;
_SOFT_U8BITS u8addressW;
_SOFT_U8BITS u8addressR;
_SOFT_U8BITS u8return_value;
u8address = u8deviceaddress;
u8addressW = (u8address << 1) | MWSR; //0x00 Para escritura //Address for write mode
u8address = u8deviceaddress;
u8addressR = (u8address << 1) | MRSW; //0x01 Para lectura //Adress for read mode
i2c1_Start();
i2c1_write_byte (u8addressW); //This part is same as for write
i2c1_Wait();
i2c1_write_byte (u8highaddress);
i2c1_Wait();
i2c1_write_byte (u8lowaddress);
i2c1_Wait();
i2c1_RepeatedStart(); //Second star condition
i2c1_write_byte (u8addressR); //Device adress in read mode
i2c1_Wait();
i2c1_EnterRxMode(); //We set the micro in read mode
u8return_value = i2c_read_byte(); //Clears micro data register and initiates read sequence
i2c1_Wait();
i2c1_DisableAck(); //Makes no ack
i2c1_Stop();
u8return_value = i2c_read_byte(); //Reads actual data
Pause();
return(u8return_value); //Returns the function value
I use a Pause function to wait for the response if that is what you mean. I think that the trouble may be on the read function, but i'm going crazy tho find it.