중급 예제

약간은 익숙하시거나 익숙해지셨나요? 그렇다면 조금더 깊이 다뤄볼까요?

EEPROM

2014-08-12 11:37:39

EEPROM을 사용해 보자


메모리는 데이터가 저장되는 공간으로 크게 휘발성 메모리비휘발성 메모리로 나누어 진다. 
휘발성 메모리는 한번 저장되었다가 장치가 꺼지게 되면 저장되었던 데이터가 다 날라가는 메모리로 쉽게 컴퓨터의 RAM을 생각하면 편하다. 
그에 반해서 비휘발성 메모리는 한번 저장된 데이터는 직접 삭제하기 전까지는 메모리에 남아있어 장치가 꺼져도 남아있는 메모리이다. 예를 들면 컴퓨터 하드디스크를 생각하면 편하다.

아두이노도 작은 컴퓨터이기 때문에 이런 메모리가 내장되어 있다. 휘발성메모리 비휘발성 메모리 둘 다 존재하지만 그 중에서
EEPROM(Electrocally Erasable Programmable Read-Only Memory)비휘발성 메모리로 저장하고 싶은 작은 변수값이나 상태를 저장하기에 사용하기 좋은 메모리이다.  


다만 사용횟수에 제한이 있고(약 10만번 정도) 용량이 일반 하드디스크를 생각한다면 터무니없이 작기 때문에 삽입할 데이터의 크기와 메모리의 크기를 비교하여 잘 사용하여야 한다.

아두이노 우노에는 1KB의 EEPROM이 존재하며 아두이노 메가에는 4KB의 EEPROM이 존재한다.
아두이노로 EEPROM을 사용하기 위해서는 EEPROM라이브러리를 사용하여야 하며 EEPROM라이브러리는 내장라이브러리로 존재한다.
 

EEPROM

NO 함수 정보
1 read(address) 해당하는 주소에 있는 값을 읽어온다
2 write(address, value) 해당하는 주소에 value에 해당하는 값을 쓴다
 

EEPROM_Write


쉽게 예제소스를 사용해 보자. 예제 소스 중 eeprom_write을 읽어오자.

 
/*
 * EEPROM Write
 *
 * Stores values read from analog input 0 into the EEPROM.
 * These values will stay in the EEPROM when the board is
 * turned off and may be retrieved later by another sketch.
 */

#include <EEPROM.h>

//EEPROM의 처음 시작할 주소 지정
int addr = 0;

void setup()
{
  Serial.begin(9600);
}

void loop()
{
  //아날로그 데이터는 1부터 1023까지 받을 수 있지만
  //EEPROM은 255까지 밖에 못받기 때문에 / 4를 한다
  int val = analogRead(0) / 4;
  Serial.println(val);
  
  //EEPROM에 아날로그 0번핀에서 받는 값을 입력한다
  //이 값들은 전원이 나가도 저장된다
  EEPROM.write(addr, val);
  
  //주소를 1씩 증가시켜 다음 주소를 가져온다
  //주소가 512가 되면 다시 0부터 시작한다
  addr = addr + 1;
  if (addr == 512)
    addr = 0;
  
  delay(100);
}
예제소스 eeprom_write를 불러오면 위 소스가 보이는데 (시리얼 모니터로 값이 쓰이는 모습을 보기위해 예제소스에 시리얼통신 추가함)

소스를 분석하면 아날로그 0번핀에서 읽어오는 값을 4등분하여 그 값들을 차례대로 EEPROM 0번 주소부터 512번 주소까지 값을 쓰는것이다. 
  //아날로그 데이터는 1부터 1023까지 받을 수 있지만
  //EEPROM은 255까지 밖에 못받기 때문에 / 4를 한다
  int val = analogRead(0) / 4;
  Serial.println(val);
  
  //EEPROM에 아날로그 0번핀에서 받는 값을 입력한다
  //이 값들은 전원이 나가도 저장된다
  EEPROM.write(addr, val);
위 부분이 아날로그 0번핀에서 읽어오는 값을 4등분하여 EEPROM에 0번주소부터 차례대로 값을 입력하는 부분이다.

EEPROM은 바이트단위로 읽기때문에 데이터는 한 바이트로 표현가능한 0부터 255까지밖에 기록하지 못한다.
그렇기 때문에 아날로그핀에서 입력받은 0부터 1023까지의 데이터를 4등분하여 입력한다.

시리얼 모니터로 확인하면 아래와 같은 랜덤한 값들이 쓰이는것을 볼 수 있다.

EEPROM_Read


이제는 쓰인 값들이 제대로 쓰였는지 볼 차례다.

똑같이 예제를 불러오는데 이번에는 eeprom_read을 읽어오자.

/*
 * EEPROM Read
 *
 * Reads the value of each byte of the EEPROM and prints it 
 * to the computer.
 * This example code is in the public domain.
 */

#include <EEPROM.h>

//주소는 0부터 시작하기 때문에 주소 초기값으로 0으로 지정
int address = 0;
byte value;

void setup()
{
  //시리얼 통신을 시작하기 위해 초기화하고 속도를 9600으로 설정
  Serial.begin(9600);
  while (!Serial) {
    ; // 시리얼포트가 연결될 때까지 기다린다. 레오나르도 보드만 필요한 부분
  }
}

void loop()
{
  // EEPROM의 현재 주소에 있는 값을 value로 읽어 온다
  value = EEPROM.read(address);
  
  Serial.print(address);
  Serial.print("\t");
  Serial.print(value, DEC);
  Serial.println();
  
  // 현재주소에서 1 증가시켜서 다음 주소를 가져온다
  address = address + 1;
  
  // 주소가 512가 되면 주소를 다시 0으로 바꾼다
  if (address == 512)
    address = 0;
    
  delay(500);
}
read소스는 EEPROM에 쓰여있는 값들을 반대로 read함수를 통해 읽어오는 소스이다. 0번 주소부터 512번주소까지 쓰인값들을 차례대로 읽어와서 시리얼모니터에 출력하게 된다.

시리얼 모니터창을 키게 되면 0번 주소부터 차례대로 쓰인값들을 볼 수 있다.

EEPROM_Clear


이제는 EEPROM에 쓰인 값들을 Clear해보자

예제소스에 있는 eeprom_clear을 불러와서 실행해보자.
/*
 * EEPROM Clear
 *
 * Sets all of the bytes of the EEPROM to 0.
 * This example code is in the public domain.

 */

#include <EEPROM.h>

void setup()
{
  // 0부터 512까지의 주소에 있는 값을 0으로 변경한다
  for (int i = 0; i < 512; i++)
    EEPROM.write(i, 0);
    
  // 변경이 완료되면 13번 LED를 깜빡거린다
  digitalWrite(13, HIGH);
}

void loop()
{
}
클리어는 데이터를 삭제하는것이 아닌 EEPROM에 0을 입력함으로써 데이터를 clear하는 형식으로 한다. 
예제소스에서는 for loop를 통해 0번 주소부터 512번 주소까지 데이터를 0을 입력하고 입력이 완료되면 13번 내장 LED를 켜는 방식으로 EEPROM을 clear시켰다.
 
 

 
EEPROM 클리어 결과를 시리얼모니터로 확인하면 데이터가 0으로 바뀌었음을 알 수 있다.

kocoafabeditor

항상 진취적이고, 새로운 것을 추구하는 코코아팹 에디터입니다!

EEPROM, 아두이노, 기타