37款傳感器與執行器的提法,在網絡上廣泛流傳,其實Arduino能夠兼容的傳感器模塊肯定是不止這37種的。鑒於本人手頭積累了一些傳感器和執行器模塊,依照實踐出真知(一定要動手做)的理念,以學習和交流為目的,這里准備逐一動手嘗試系列實驗,不管成功(程序走通)與否,都會記錄下來---小小的進步或是搞不掂的問題,希望能夠拋磚引玉。
【Arduino】168種傳感器模塊系列實驗(資料+代碼+圖形+仿真)
實驗六十八:AT24C256 I2C接口 EEPROM 存儲模塊 IIC

AT24C256
是ATMEL公司256kbit串行電可擦的可編程只讀存儲器,8引腳雙排直插式封裝,具有結構緊湊、存儲容量大等特點,可以在2線總線上並接4片該IC,特別適用於具有高容量數據儲存要求的數據采集系統。AT24C256采用SOP-8封裝。

芯片參數
芯片有3種工作電壓;
5.0V(VCC=4.5V~5.5V)
2.7V(VCC=2.7V~5.5V)
1.8V(VCC=1.8V~3.6V)
特性:
內部可以組成32k×8存儲單元
2線串行接口
斯密特觸發,濾波輸入抑制噪聲
雙向數據傳送協議
硬件寫保護引腳和軟件數據保護功能
具有64字節頁寫模式


A0、A1:地址選擇輸入端。在串行總線結構中,可以連接4個AT24C256IC。用A0、A1來區分各IC。A0、A1懸空時為0。
SCL:串行時鍾輸入。上升沿將SDA上的數據寫入存儲器,下降沿從存儲器讀出數據送SDA上。
SDA:雙向串行數據輸入輸出口。用於存儲器與單片機之間的數據交換。
WP:寫保護輸入。此引腳與地相連時,允許寫操作;與VCC相連時,所有的寫存儲器操作被禁止。如果不連,芯片內部下拉到地。
VCC:電源。
GND:地。
NC:空。

AT24C256的工作原理
AT24C256內部有512頁,每一頁為64字節,任一單元的地址為15位。地址范圍0000H~7FFFH。
芯片工作狀態
1)時鍾和數據傳送
一般情況下,SDA被外部的設備拉到高,只有當SCL為低電平時,SDA上的數據變化,表示要傳送數據。SCL為高時SDA變化表示狀態變化。
2)開始狀態(START)
當SCL為高時,SDA由高到低表示數據傳送開始,這一狀態必須在所有命令之前。
3)結束狀態(STOP)
當SCL為高時,SDA由低到高表示數據傳送結束狀態。
4)應答狀態(ACK)
所有的地址和數據都是以8位的形式串行傳送給存儲器或從存儲器讀出的。存儲器在第9個時鍾周期SDA發零信號表示已經收到8位數據。見圖總線協議圖。

AT24C256 I2C接口 EEPROM 存儲模塊

1.板載芯片AT24C256進口芯片;
2.板載I2C通訊所需的上拉電阻;
3.所有管腳均引出並標注;
4.PCB板子尺寸:1.9(CM)x1.1(CM)

模塊電原理圖

/*
【Arduino】168種傳感器模塊系列實驗(資料+代碼+圖形+仿真)
實驗六十八:AT24C256 I2C接口 EEPROM 存儲模塊 IIC
*/
#include <Wire.h>
#define ADDRESS_AT24C256 0x50
word wordAddress = 0x0F00;
char str[] = "This is ZLBG.";
byte buffer[30];
int i;
void setup()
{
Wire.begin();
Serial.begin(9600);
//write
Wire.beginTransmission(ADDRESS_AT24C256);
Wire.write(highByte(wordAddress));
Wire.write(lowByte(wordAddress));
for (i = 0; i < sizeof(str); i++)
{
Wire.write(byte(str));
}
Wire.endTransmission();
delay(10);
}
void loop()
{
Wire.beginTransmission(ADDRESS_AT24C256);
Wire.write(highByte(wordAddress));
Wire.write(lowByte(wordAddress));
Wire.endTransmission();
Wire.requestFrom(ADDRESS_AT24C256, sizeof(str));
if(Wire.available() >= sizeof(str))
{
for (i = 0; i < sizeof(str); i++)
{
buffer = Wire.read();
}
}
for(i = 0; i < sizeof(str); i++)
{
Serial.print(char(buffer));
}
Serial.println();
delay(2000);
}

/*
【Arduino】168種傳感器模塊系列實驗(資料+代碼+圖形+仿真)
實驗六十八:AT24C256 I2C接口 EEPROM 存儲模塊 IIC
程序之二
*/
#include <Wire.h>
#define EEPROM_ADDR 0x50
void setup()
{
Wire.begin();
Serial.begin(9600);
// TESTS FOR EACH FUNCTION BEGIN HERE
Serial.println("Writing Test:");
for (int i=0; i<20; i++){
i2c_eeprom_write_byte(EEPROM_ADDR,i,i+65);
Serial.print(". ");
delay(10);
}
Serial.println("");
delay(500);
Serial.println("Reading Test:");
for (int i=0; i<20; i++){
Serial.write(i2c_eeprom_read_byte(EEPROM_ADDR, i));
Serial.print(" ");
}
byte PageData[30];
byte PageRead[30];
for (int i=0; i<30; i++){
PageData = 0;
PageRead = 0;
}
Serial.println("");
for (int i=0; i<30; i++) PageData = i+33;
Serial.println("Writing Page Test:");
i2c_eeprom_write_page(EEPROM_ADDR, 100, PageData, 28 );
Serial.println("Reading Page Test:");
i2c_eeprom_read_buffer( EEPROM_ADDR, 100, PageRead, 28);
for (int i=0; i<28; i++){
Serial.write(PageRead);
Serial.print(" ");
}
}
void loop()
{
}
void i2c_eeprom_write_byte( int deviceaddress, unsigned int eeaddress, byte data )
{
int rdata = data;
Wire.beginTransmission(deviceaddress);
Wire.write((int)(eeaddress >> 8));
Wire.write((int)(eeaddress & 0xFF));
Wire.write(rdata);
Wire.endTransmission();
}
void i2c_eeprom_write_page
( int deviceaddress, unsigned int eeaddresspage, byte* data, byte length )
{
Wire.beginTransmission(deviceaddress);
Wire.write((int)(eeaddresspage >> 8));
Wire.write((int)(eeaddresspage & 0xFF));
byte c;
for ( c = 0; c < length; c++)
Wire.write(data[c]);
Wire.endTransmission();
delay(10);
}
byte i2c_eeprom_read_byte( int deviceaddress, unsigned int eeaddress )
{
byte rdata = 0xFF;
Wire.beginTransmission(deviceaddress);
Wire.write((int)(eeaddress >> 8));
Wire.write((int)(eeaddress & 0xFF));
Wire.endTransmission();
Wire.requestFrom(deviceaddress,1);
if (Wire.available()) rdata = Wire.read();
return rdata;
}
void i2c_eeprom_read_buffer( int deviceaddress, unsigned int eeaddress, byte *buffer, int length )
{
Wire.beginTransmission(deviceaddress);
Wire.write((int)(eeaddress >> 8));
Wire.write((int)(eeaddress & 0xFF));
Wire.endTransmission();
Wire.requestFrom(deviceaddress,length);
for ( int c = 0; c < length; c++ )
if (Wire.available()) buffer[c] = Wire.read();
}




