Mira&Luna's nursery lab

旅乙女と発明娘の子供部屋

外付けメモリ †EEPROM† を使ってデータを保存する。

f:id:miraluna:20180105114819j:plain:w130 Mira
記憶媒体 外付けEEPROM[24LC64]をArduinoにつないでメモリをいっぱい記憶できるようにする。
     f:id:miraluna:20180105150256j:plain:w400
これはいつも使っているマイクロコンピュータ(マイクロコントローラ)のATmega328P-PU。あだ名は「みつは」よ。

書き込めるプログラム容量は32KBytes。でもブートローダを書き込むからめいっぱいは使えないわ。
SRAMは2KB。
それに内蔵EEPROMをもっていて、それは1KB。
このちっちゃな体の中にそれだけの容量を入れて電子部品をコントロールできるんだからえらい子。
でもこの子たちのすごいところは、本人がもっているポテンシャルだけではなくて、他のパーツを接続すればそのパーツのもつ性能も自分のもののようにコントロールできちゃうこと。
今回は情報を記憶するためのメモリとしてのパーツ、EEPROMをArduinoにつなげてメモリをいっぱい増やしてみようと思います。

     f:id:miraluna:20190422193438j:plain:w300
この子がEEPROMの「24LC64-I/P」。
性能は ・I²Cで2線接続。
    ・64Kビット(8KBytes)のメモリ容量。
    ・通信速度は400KHzまで。
    ・動作電圧は2.5v~5.5v。
    ・100万回書き換えができる。
    ・データ保存は200年まで。
    ・耐えられる温度は-40℃から85℃まで。
     etc...
性能についての情報はいろいろあるけど、重要なのはマイコンと2線で接続できる I²C接続ということと、8KBの記憶容量があるということね。32KBのEEPROMも私持ってる。
そして8pinDIPの姿をしているというところも重要。私にとっては扱いやすい姿。

この「24LC64」の役割は情報の記憶。つまりUSBメモリやSDカードやメモリーカードのように情報を入れておける倉庫みたいなものね。人間でいうところの海馬。それもみつはがもともともっているEEPROMが1KBのところ、なんといっきに8KBも増設できちゃう。お値段は秋月さんで50円。32KBの[24FC256-I/P]は90円。なんだか素敵だと思いませんか?



それでは早速ブレッドボードで配線をしていきましょう。

◆ 24LC64のPIN配置図(データシートより)
  f:id:miraluna:20190427125616p:plain
これが「24LC64」のPIN配置です。
以下のようにArduinoにつなぎます。

  EEPROM側    Arduino
 〇 Vcc        5v
 〇 Vss        GND
 〇 SCL        SCL(位置は下の写真を見てね)(1番上のピン(黄))
 〇 SDA(2KΩを分岐して)SDA(位置は下の写真を見てね)(2番目のピン(緑))
 〇 WP        GND(書込み時GND接続、Vcc接続で書込み禁止)
 〇 (SDAから分岐した2kΩ) 5v
                          ※2021.9.20. 修正

 <ここでちょっとチップセレクトのお話>
今回はA0,A1,A2をつないでいません。この3つのpinはチップセレクトピンで、GNDにつなぐかVccにつなぐかで"0"か"1"に選択します。このつなぎ方を変えることで、そのデバイスにアドレスをふることができます。
3つともつながないとチップセレクトは"0,0,0"となります(正しくはGNDにつなぎます)。そこに「24LC64」や「24FC256」などのコントロールコードである"1010"を頭に加えた"1010000"から"1010111"までがデバイスアドレスになるの。
2進法の"1010000"は16進法の"0x50"なので、3つともつながなかった場合のデバイスアドレスは"0x50"となるわけ。「このEEPROMは"0x50"さんですよ」って。(後述のプログラムスケッチにもデバイスアドレス"0x50"さんが登場しますよ)
チップセレクトの順番は1010,A2,A1,A0だから、A0だけVccにつないで"1"を選択すれば、アドレスは"1010001"になる。16進法の"0x51"だから、そのつなぎ方をしたEEPROMは"0x51"さんね。3つのpinのつなぎ方は8通りあるから、デバイスアドレスは"0x50"から"0x57"までふることができて、なんと8つのデバイスを接続することができるの。
もしI²Cのこのチップセレクト機能を使いこなせたら、きっといろいろな可能性が広がるんでしょうね。私はまだ使いこなせず勉強中です。



実際につないでみるとこんな感じ。
f:id:miraluna:20210920092845j:plain
あっぷ。
f:id:miraluna:20210920092904j:plain
ちゃんとチップセレクトピンをつないだところ。
f:id:miraluna:20210920092925j:plain
EEPROM-Arduino 配線図(ブザーは関係ないので、見なかったことに......。)
f:id:miraluna:20210920085453p:plain

これで配線準備が完了しました(∂_∂🎀y


次はスケッチね。
【データ書き込み用プログラム】

//EEPROM 書込みスケッチ
#include<Wire.h>

void eep_write(int device_add, unsigned int eep_add, int data){
Wire.beginTransmission(device_add);//指定したデバイスへ移動
Wire.write((int)(eep_add >> 8));
Wire.write((int)(eep_add & 0xff));
Wire.write(data);
Wire.endTransmission();
}

void setup() {
Wire.begin();
for(int i=0; i<100; i++){
eep_write(0x50,i,i);//0~99までの数字(データ)を、アドレス0~99に書き込む
delay(5);//書込み待ち
}
}

void loop() {

}

これはEEPROMのデータ番地(アドレス)の0~99番に、0~99という数値のデータを書き込むプログラム。
最後にdelayで書き込むのを待ってあげるのが、きれいに書き込むコツよ。

ArduinoとEEPROMをつないだ状態でArduinoにこのスケッチを書き込めば、EEPROMにデータが書き込まれるはず。
次は書き込まれたデータを読み込むスケッチです。

【データ読み込み用プログラム】

//EEPROM 読込みスケッチ
#include<Wire.h>

int eep_read(int device_add, unsigned int eep_add){
Wire.beginTransmission(device_add);
Wire.write((int)(eep_add >> 8));
Wire.write((int)(eep_add & 0xff));
Wire.endTransmission();

Wire.requestFrom(device_add,1);
if(Wire.available()){}
return Wire.read();
}

void setup() {
Wire.begin();
Serial.begin(9600);
for(int i=0; i<100; i++){
int val = eep_read(0x50,i);//アドレス0~99までのデータを読み込む
Serial.println(val);//シリアルモニタに表示する
delay(5);//読み込み待ち
}
}

void loop() {

}

こっちはEEPROMに書かれた0~99までのアドレスにあるデータを読み込んでシリアルモニタに表示させるプログラム。最後の読み込み待ちは必要ないけど、書き込み待ちに合わせて遊び心で書いてみたの。

さっき書き込みをしたEEPROMをArduinoにつないだままこのプログラムを書き込むと、シリアルモニタにEEPROMのデータが映し出されます。
こんなふうに。
f:id:miraluna:20190422125151p:plain
ずらっとアドレス99番地まで。
f:id:miraluna:20190422125150p:plain

初めの「?????????????」の行は、読み込みに少し時間がかかるから文字化けするけれど、気にする必要はないわ。

これでたくさんのデータをメモリに格納できる。
やったね。

またひとつできることが増えてうれしいな(∂_<🎀/