?? emc-epprom.txt
字號(hào):
;******************************************
;** 24CXX 接口I2C總線讀/寫的程序
;** (所有時(shí)序均基于4MHZ晶體震蕩器頻率)
;******************************************
/*
;****************************
;隨機(jī)讀寫測(cè)試程序(示范程序)
;****************************
TEST:
MOV A,@0XAE ;A2=A1=A0=1
MOV SLAVE_24,A ;設(shè)置器件碼
MOV A,@2 ;R/W LOC. = 2
MOV ADDR_24,A ;設(shè)置地址碼
MOV A,@55 ;
MOV DATA_24,A ;寫55到E2PROM
CALL WRBYTE ;寫一個(gè)字節(jié)
CALL DL10MS ;延時(shí)10MS,等待寫操作完成(注意,此語句非常重要)
CALL RDBYTE ;讀回原數(shù)據(jù)
MOV A,@55 ;
XOR A,DATA_24 ;
JBS R3,Z ;讀出數(shù)據(jù)=寫入數(shù)據(jù)跳
WRONG:
JMP WRONG ;校驗(yàn)失敗
CORRECT:
JMP CORRECT ;校驗(yàn)通過
DL10MS:
RET
;****************************
;存儲(chǔ)器定義
;****************************
PROT_I2C EQU 0X05 ;I2C操作口
SDA EQU 3 ;數(shù)據(jù)腳
SCL EQU 2 ;時(shí)鐘腳
ADDR_24 EQU 0X1B ;地址寄存器
DATA_24 EQU 0X1C ;寫入/讀自I2C的數(shù)據(jù)寄存器
SLAVE_24 EQU 0X1D ;從器件地址寄存器(1010XXX0)
DBUF_24 EQU 0X1E ;發(fā)送/接受自SDA口的數(shù)據(jù)緩沖器
COUNT_24 EQU 0X1F ;位計(jì)數(shù)器
TT_24 EQU 0X20 ;標(biāo)志寄存器
REND_24 EQU 1 ;讀完畢標(biāo)志(0=未完畢,1=完畢)
NUM_24 EQU 0X21 ;頁寫/頁讀字節(jié)數(shù)
*/
;****************************
;宏定義
;****************************
;=================
;設(shè)置SCL,SDA為輸出口
;=================
SDA_OUT MACRO
MOV A,@0B00000001
IOW PROT_I2C
ENDM
;=================
;設(shè)置SCL為輸出口,SDA為輸入口
;=================
SDA_IN MACRO
MOV A,@0B00001001
IOW PROT_I2C
ENDM
;****************************
;字節(jié)寫程序
;功能: 寫一個(gè)字節(jié)到EEPROM器件
;入口: DATA_24 =要寫的數(shù)據(jù)
; ADDR_24 =數(shù)據(jù)地址
; SLAVE_24=從器件地址1010XXX0)
;****************************
WRBYTE:
MOV A,SLAVE_24
MOV DBUF_24,A
CALL BSTART ;送起始位
CALL TX ;送從器件地址并檢測(cè)應(yīng)答信號(hào)
MOV A,ADDR_24
MOV DBUF_24,A
CALL TX ;送數(shù)據(jù)地址并檢測(cè)應(yīng)答信號(hào)
MOV A,DATA_24
MOV DBUF_24,A
CALL TX ;送數(shù)據(jù)并檢測(cè)應(yīng)答信號(hào)
CALL BSTOP ;送停止位
RET
;****************************
;字節(jié)讀程序
;功能: 從EEPROM器件讀一個(gè)字節(jié)
;入口: ADDR_24 =數(shù)據(jù)地址
; SLAVE_24=從器件地址(1010XXX0)
;出口: DATA_24 =讀到的數(shù)據(jù)
;****************************
RDBYTE:
MOV A,SLAVE_24
MOV DBUF_24,A
CALL BSTART ;送起始位
CALL TX ;送從器件地址并檢測(cè)應(yīng)答信號(hào)
MOV A,ADDR_24
MOV DBUF_24,A
CALL TX ;送數(shù)據(jù)地址并檢測(cè)應(yīng)答信號(hào)
;轉(zhuǎn)入讀狀態(tài)
CALL BSTART ;送起始位
MOV A,SLAVE_24
MOV DBUF_24,A
BS DBUF_24,0
CALL TX ;送從器件地址并檢測(cè)應(yīng)答信號(hào)
BS TT_24,REND_24
CALL RX ;讀數(shù)據(jù)并發(fā)送應(yīng)答信號(hào)
CALL BSTOP ;送停止位
MOV A,DBUF_24
MOV DATA_24,A ;保存數(shù)據(jù)到DATA_24
RET
;****************************
;頁寫程序
;功能: 寫一個(gè)字節(jié)到EEPROM器件
;入口: R4 =要寫的數(shù)據(jù)在RAM中存放首地址
; NUM_24 =字節(jié)數(shù)
; ADDR_24 =數(shù)據(jù)地址
; SLAVE_24=從器件地址1010XXX0)
;****************************
WRPAGE:
MOV A,SLAVE_24
MOV DBUF_24,A
CALL BSTART ;送起始位
CALL TX ;送從器件地址并檢測(cè)應(yīng)答信號(hào)
MOV A,ADDR_24
MOV DBUF_24,A
CALL TX ;送數(shù)據(jù)地址并檢測(cè)應(yīng)答信號(hào)
WRPAGE1:
MOV A,R0
MOV DBUF_24,A
CALL TX ;送數(shù)據(jù)并檢測(cè)應(yīng)答信號(hào)
INC R4
DJZ NUM_24
JMP WRPAGE1 ;未寫完繼續(xù)
CALL BSTOP ;送停止位
RET
;****************************
;頁讀程序
;功能: 從EEPROM器件讀一個(gè)字節(jié)
;入口: ADDR_24 =數(shù)據(jù)地址
; SLAVE_24=從器件地址(1010XXX0)
; NUM_24 =字節(jié)數(shù)
;出口: R4 =讀到的數(shù)據(jù)在RAM中存放首地址
;****************************
RDPAGE:
MOV A,SLAVE_24
MOV DBUF_24,A
CALL BSTART ;送起始位
CALL TX ;送從器件地址并檢測(cè)應(yīng)答信號(hào)
MOV A,ADDR_24
MOV DBUF_24,A
CALL TX ;送數(shù)據(jù)地址并檢測(cè)應(yīng)答信號(hào)
;轉(zhuǎn)入讀狀態(tài)
CALL BSTART ;送起始位
MOV A,SLAVE_24
MOV DBUF_24,A
BS DBUF_24,0
CALL TX ;送從器件地址并檢測(cè)應(yīng)答信號(hào)
RDPAGE1:
MOV A,@1
XOR A,NUM_24
BS TT_24,REND_24
JBS R3,Z ;NUM_24=1跳;判斷是否最后一個(gè)字節(jié),決定應(yīng)答信號(hào)
BC TT_24,REND_24
CALL RX ;讀數(shù)據(jù)并發(fā)送應(yīng)答信號(hào)
MOV A,DBUF_24
MOV R0,A ;保存數(shù)據(jù)到R0
INC R4
DJZ NUM_24
JMP RDPAGE1 ;未讀完繼續(xù)
CALL BSTOP ;送停止位
RET
;****************************
;I2C操作子程序(時(shí)序)集合
;****************************
;=================
;發(fā)送起始位程序
;說明: 當(dāng)SCL=1時(shí),向SDA發(fā)一個(gè)下降沿
;=================
BSTART:
SDA_OUT ;設(shè)置SDA為輸出口
BS PROT_I2C,SDA ;SDA=1
NOP ;延時(shí)0.6US
BS PROT_I2C,SCL ;SCL=1
NOP ;延時(shí)0.6US
BC PROT_I2C,SDA ;SDA=0
NOP ;延時(shí)0.6US
BC PROT_I2C,SCL ;SCL=0
NOP ;延時(shí)0.6US
RET
;=================
;發(fā)送結(jié)束位程序
;說明: 當(dāng)SCL=1時(shí),向SDA發(fā)一個(gè)上升沿
;=================
BSTOP:
SDA_OUT ;設(shè)置SDA為輸出口
BC PROT_I2C,SDA ;SDA=0
NOP ;延時(shí)0.6US
BS PROT_I2C,SCL ;SCL=1
NOP ;延時(shí)0.6US
BS PROT_I2C,SDA ;SDA=1
NOP ;延時(shí)0.6US
RET
;=================
;位輸入子程序
;說明: 當(dāng)SCL=1時(shí),從SDA上讀電平
;出口: C=從SDA上讀入的位值
;=================
BITIN:
SDA_IN ;設(shè)置SDA為輸入口
BS PROT_I2C,SDA ;SDA=1
NOP ;延時(shí)0.6US
BS PROT_I2C,SCL ;SCL=1
NOP ;延時(shí)0.6US
BC R3,C
JBC PROT_I2C,SDA
BS R3,C ;C=SDA
NOP ;延時(shí)0.6US
BC PROT_I2C,SCL ;SCL=0
NOP ;延時(shí)0.6US
RET
;=================
;位輸出子程序
;說明: 每當(dāng)SCL=0時(shí),改寫SDA上的電平
;入口: C=要寫到SDA上的位值
;=================
BITOUT:
SDA_OUT ;設(shè)置SDA為輸出口
JBS R3,C
JMP BIT0
BS PROT_I2C,SDA ;SDA=C=1
JMP CLK1
BIT0:
BC PROT_I2C,SDA ;SDA=C=0
CLK1:
NOP ;延時(shí)0.6US
BS PROT_I2C,SCL ;SCL=1
BIT2:
NOP
NOP
BC PROT_I2C,SCL ;SCL=0
RET
;============================
;接收數(shù)據(jù)子程序
;入口: TT_24.REND_24 =讀完畢標(biāo)志
;出口: DBUF_24 =接受到的數(shù)據(jù)(8_BIT)
;============================
RX:
MOV A,@8 ;循環(huán)次數(shù)=8
MOV COUNT_24,A
CLR DBUF_24
RXLP:
CALL BITIN ;輸入1_BIT
RLC DBUF_24 ;左移(帶C)
DJZ COUNT_24 ;循環(huán)結(jié)束?
JMP RXLP
;設(shè)置應(yīng)答信號(hào)位,如果讀完畢則送1(NO_ACK)停止接受,否則送0(ACK)繼續(xù)接受
BS R3,C
JBS TT_24,REND_24 ;讀完畢信號(hào)->C
BC R3,C
CALL BITOUT ;應(yīng)答
RET
;============================
;發(fā)送數(shù)據(jù)子程序
;入口: DBUF_24 =要發(fā)送的數(shù)據(jù)(8_BIT)
;============================
TX:
MOV A,@8 ;循環(huán)次數(shù)=8
MOV COUNT_24,A
TXLP:
RLC DBUF_24 ;左移(帶C)
CALL BITOUT ;輸出1_BIT
DJZ COUNT_24 ;循環(huán)結(jié)束?
JMP TXLP
CALL BITIN ;讀應(yīng)答信號(hào)
RET
;****************************
;I2C總線讀/寫的程序全部結(jié)束 !
;****************************
簽名:
如果你的‘芯’是一座作坊,
我愿做那不知疲倦的程序匠……
?? 快捷鍵說明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號(hào)
Ctrl + =
減小字號(hào)
Ctrl + -