Read 2048 Bytes from FRAM

// Started this new thread after posting to a year old thread

Hi,

I bought a FRAM module on ebay , it is based on a FM24CL16B chip and is 16 kilobits ( 2 K bytes obviously ) ( more here http://www.waveshare.com/wiki/FM24CLXX-FRAM-Board_Datasheets )

After trying 3 or 4 FRAM 'libraries', including a failed attempt at the supplied code from above website (was C code, but not 'IDE'), I found code (by casemod) and it works up to 256 bytes !!

May I please ask how to extend the code to 2048 bytes?

The datasheet (attached) for the FM24CL16Bchip says that the FRAM memory is organised as 8 pages of 256 bytes each, so the attached code seems to be working for page 0.

The datasheet states that the pages are addressed by setting A2,A1,A0 in the slave address.

The slave address 8 bit format is 1 0 1 0 A2 A1 A0 R/W

Where 1010.... is the I2C address i.e 0x50 or decimal 80. ( So A2=A1=A0=0 so page is 0 ...I guess)

I have interpreted that to get to page 1, A0 must be set to 1, so the slave address is 0x51.

Hence page 2 is 0x52 ..... and page 7 is 0x57.

I understand that the R/W bit must be set 1 or 0 for read or write and am trusting it is already working in the code as it does work.

So for testing I replaced the following code from casemod's code

#define DEVICEADDRESS   0x57
.
.
.

Wire.beginTransmission(DEVICEADDRESS);
Wire.write(theMemoryAddress);

with

#define FRAMADDRESS   0x57
.
.
.
FramAddress = FRAMADDRESS + int( theMemoryAddress / 256 );  // Converts theMemoryAddress to FRAMaddress +  page address
WordAddress = theMemoryAddress % 256;                        // Converts theMemoryAddress to word address

    Wire.beginTransmission(FramAddress);
    Wire.write(WordAddress);

where memory address is any of 0 to 2047

but it does not work above 256 bytes - it looks like A2,A1,A0 are ignored.

Incidentally, while testing I had one time had FRAMADDRESS = 0x50 instead on 0x57 and got the same result. Only the first 256 bytes are writeable/readable. I am not entirely sure which is the correct I2C address but datasheet implies 0x50.

Any advise please, please consider me a wire.h newb, as I usually rely on libraries?

Thanks

/// casemod code which works for first 256 bytes //////////

#include <Wire.h>
#define DEVICEADDRESS   0x57 

//int temp = 0;
uint16_t temp = 0;
uint16_t test = 0b1111100101011000;

void setup() {
  // put your setup code here, to run once:
Serial.begin(9600);
Wire.begin();
}

void loop() {
  
  EepromWrite(0x05, test); 
  
  temp = EepromRead(0x05);
  
  Serial.println(temp, BIN);
  //Serial.println(temp1, BIN);
  delay(2000);
  
} 

void EepromWrite(uint8_t theMemoryAddress, uint16_t u16Byte) 
{
  
    uint8_t lowByte = ((u16Byte) & 0xFF);
    Serial.println(lowByte);
    uint8_t highByte = ((u16Byte >> 8) & 0xFF);
    Serial.println(highByte);
    
    Wire.beginTransmission(DEVICEADDRESS);
    Wire.write(theMemoryAddress);
    Wire.write(lowByte);
    Wire.write(highByte);
    Wire.endTransmission();
}

// ----------------------------------------------------------------

uint16_t EepromRead(uint8_t theMemoryAddress) 
{
  Wire.beginTransmission(DEVICEADDRESS);
  Wire.write(theMemoryAddress);
  Wire.endTransmission();
  
  Wire.requestFrom(DEVICEADDRESS,2);
  uint8_t lowByte = Wire.read();
  uint8_t highByte = Wire.read();

  return ((lowByte) & 0xFF) + ((highByte << 8) & 0xFF00);
}

FM24CL16B.pdf (282 KB)

I just realised that by adding the R/W bit to the slave address ....

that 1010.... is decimal 0xA0 not 0x50.

I am guessing the wire library shifts the bits internally ......... I hope !!!!!

cblx5:
I just realised that by adding the R/W bit to the slave address ....

that 1010.... is decimal 0xA0 not 0x50.

I am guessing the wire library shifts the bits internally ......... I hope !!!!!

The wire library appends the Read/Write bit to the user supplied address, so the standard 23LCxx EEPROMs addresses are 0x50 .. 0x57, the WIRE library adds the READ/write bit. The 8bit first I2C byte becomes 0xA0 .. 0xAF. Depending on whither it is a READ or a write, and the actual address.

Any time your are read I2C device data sheets look for the 7bit address.

Chuck.