Publicidade:

terça-feira, 12 de abril de 2016

Arduino - Memória EEPROM - AT24C256

Essa semana postei um artigo no site sistemas embarcados. O Assunto foi memória EEPROM, interna e externa. No caso da memória externa foi abordado o CI AT24C256. Segue o link para o artigo completo: http://www.sistemasembarcados.org/2016/04/arduino-memoria-eeprom.html

Veja também o vídeo sobre o AT24C256.



Veja também o vídeo que mostra a classe feita para facilitar a gravação e leitura da memória:



Código-fonte:

/*
Baseado nos exemplos abaixo:
http://hobbytronics.co.uk/eeprom-page-write
http://playground.arduino.cc/Code/EEPROMWriteAnything

Fabiano A. Arndt
www.youtube.com/fabianoallex
www.facebook.com/dicasarduino
*/

#include <Wire.h>

/*************************************************************************************************************
*******************************CLASSE EE24CXXX - CI I2C EEPROM AT24C128/256***********************************
**************************************************************************************************************/
class EE24CXXX {
  private:
    byte _device_address;
  public:
    EE24CXXX(byte device_address){ _device_address = device_address; }
    void write(unsigned int eeaddress, unsigned char * data, unsigned int data_len);
    void read (unsigned int eeaddress, unsigned char * data, unsigned int data_len);
    
    template <class T> int write(unsigned int eeaddress, const T& value);
    template <class T> int read(unsigned int eeaddress, T& value);
};

void EE24CXXX::write(unsigned int eeaddress, unsigned char * data, unsigned int data_len) {
  unsigned int  address;
  unsigned int  page_space;
  unsigned int  page=0;
  unsigned int  num_writes;
  unsigned char first_write_size;
  unsigned char last_write_size;  
  unsigned char write_size;  
  
  page_space = int(((eeaddress/64) + 1)*64)-eeaddress;      // Calculate space available in first page

  if (page_space>16) {                                      // Calculate first write size
     first_write_size = page_space-((page_space/16)*16);
     if (first_write_size==0) { first_write_size=16; }
  } else {
    first_write_size = page_space; 
  }
  if (data_len>first_write_size)  { last_write_size = (data_len-first_write_size)%16;   }      // calculate size of last write  
  num_writes = (data_len>first_write_size) ? ((data_len-first_write_size)/16)+2 : 1;           // Calculate how many writes we need
     
  unsigned char i=0, counter=0;
  address = eeaddress;
  for (page=0; page<num_writes; page++)  {
    if (page == 0) { 
      write_size = first_write_size; 
    } else if(page == (num_writes-1)) { 
      write_size = last_write_size;
    } else { 
      write_size = 16;
    }
 
    Wire.beginTransmission(_device_address);
    Wire.write((int)((address) >> 8));   // MSB
    Wire.write((int)((address) & 0xFF)); // LSB
    counter = 0;
    do { 
      Wire.write((byte) data[i++]);
      counter++;
    } while(counter<write_size);
    Wire.endTransmission();
    address += write_size;   // Increment address for next write
     
    delay(5);  // needs 5ms for page write
  }
}

void EE24CXXX::read(unsigned int eeaddress, unsigned char * data, unsigned int data_len){
  unsigned char i = 0;
  unsigned int size = data_len;
  unsigned int j=0;
  while (size > 0){
    Wire.beginTransmission(_device_address);
    eeaddress += j*28;
    
    Wire.write((int)(eeaddress >> 8));   // MSB
    Wire.write((int)(eeaddress & 0xFF)); // LSB
    Wire.endTransmission();
    
    if (size >= 28) { 
      Wire.requestFrom(_device_address, (unsigned int) 28);
      size -= 28;
    } else {
      Wire.requestFrom(_device_address, (unsigned int) size);
      size = 0;
    }
    while(Wire.available()) { data[i++] = Wire.read(); }
    j++;
  }
}

template <class T> int EE24CXXX::write(unsigned int eeaddress, const T& value) {
  const byte* p = (const byte*)(const void*)&value;
  unsigned char data[sizeof(value)+1];
  for (int i=0; i<sizeof(value); i++) { data[i] = *p++; }
  data[sizeof(value)] = '\n';
  write(eeaddress, data, sizeof(value));
  return sizeof(value);
}

template <class T> int EE24CXXX::read(unsigned int eeaddress, T& value) {
  byte * p = (byte*)(void*)&value;
  unsigned char c[sizeof(value)];
  read(eeaddress, c, sizeof(value));
  for (int i=0; i<sizeof(value); i++) { *p++ = c[i]; }
  return sizeof(value);
}
/*************************************************************************************************************
*******************************FIM - CLASSE EE24CXXX - CI I2C EEPROM AT24C128/256*****************************
**************************************************************************************************************/

EE24CXXX m(0x50);

struct teste{
  int a;
  int b;
  int c;
};

void setup() {
  Serial.begin(9600);
  Wire.begin();  
  
  char i[] = {"1234567890"};
  char j[10];

  m.write(18522, i);              //grava na memória a quantidade de bytes ocupada pelo tipo de dados passado
  
  int count = m.read(18522, j);   //carrega da memória a quantidade de bytes 
  
  Serial.print("Quant: ");
  Serial.println(count);
  Serial.print("Valor: ");
  Serial.println(j);
}

void loop() { }


Nenhum comentário:

Postar um comentário