📄 try.asm
字号:
DATOUT EQU P2
SDA EQU P3.7
SCL EQU P3.6
NUMB EQU 30H
ADDRH EQU 31H
ADDRL EQU 32H
ADDR EQU 33H
DATH EQU 34H
DATL EQU 35H
ORG 0000H
LJMP MAIN
ORG 0030H
MAIN:
MOV C,P2.0
JC NEXT
JMP MAIN
NEXT:
MOV R2,P2
MOV A,R2
ANL A,#0EH
MOV R2,A
CJNE R2,#00H,N1
LCALL RHIADD ;读7~4位地址
JMP MAIN
N1:
CJNE R2,#02H,N2
LCALL RLADD ;读3~0位地址
JMP MAIN
N2:
CJNE R2,#04H,N3 ;读高四位数据
LCALL RDATAH
JMP MAIN
N3:
CJNE R2,#06H,N4 ;读低四位数据
LCALL RDATAL
JMP MAIN
N4:
CJNE R2,#08H,N5
LCALL DATASHOW ;给CPLD显示数据
JMP MAIN
N5:
LCALL WRDATA ;将CPLD送入的数据写入外存
JMP MAIN
ORG 0100H
RHIADD: ;读7~4位地址
MOV ADDRH,P2
MOV A,ADDRH
ANL A,#0F0H
MOV ADDRH,A
RET
RLADD: ;读3~0位地址
MOV A,P2
ANL A,#0F0H
SWAP A
MOV ADDRL,A
RET
WRDATA: ;将CPLD送入的数据写入外存
MOV A,ADDRL
ADD A,ADDRH
MOV ADDR,A
MOV A,DATL
ADD A,DATH
MOV NUMB,A
LCALL WR_1B
RET
DATASHOW: ;给CPLD显示数据
MOV A,ADDRL
ADD A,ADDRH
MOV ADDR,A
LCALL RD_1B
MOV P1,R7
RET
RDATAH: ;读高四位数据
MOV DATH,P2
MOV A,DATH
ANL A,#0F0H
MOV DATH,A
RET
RDATAL: ;读低四位数据
MOV DATL,P2
MOV A,DATL
ANL A,#0F0H
SWAP A
MOV DATL,A
RET
WR_1B: SETB SDA ;初始状态
SETB SCL ;置SDA&SCL=1
ACALL START ;启动I2C总线
MOV R7,#0A0H ;写命令
ACALL WR8BIT ;按位写入1个字节
ACALL CACK ;应答检查
MOV ACC,#40H ;取芯片地址
MOV R7,ACC ;送芯片地址
ACALL WR8BIT ;写芯片地址
ACALL CACK ;应答检查
MOV ACC,ADDR;取芯片地址
MOV R7,ACC ;送芯片地址
ACALL WR8BIT ;写芯片地址
ACALL CACK ;应答检查
MOV ACC,NUMB ;取待写数据
MOV R7,ACC ;送数据
ACALL WR8BIT ;写数据
ACALL CACK ;应答检查
ACALL STOP ;停止
ACALL DEL10MS ;等待内部写周期完成
RET
;*********************************读存储芯片指定地址的单元***************************
RD_1B:
LCALL START ;启动总线
MOV R7,#0A0H ;写命令
LCALL WR8BIT ;写写命令
LCALL CACK ;应答检查
MOV A,#40H ;取地址
MOV R7,A ;送地址
LCALL WR8BIT ;写地址
LCALL CACK ;应答检查
MOV A,ADDR ;取地址
MOV R7,A ;送地址
LCALL WR8BIT ;写地址
LCALL CACK ;应答检查
SETB SDA ;
SETB SCL ; 保证启动条件
LCALL START ;再次启动总线,以便进行读操作
MOV R7,#0A1H ;送芯片地址+写命令
LCALL WR8BIT ;写芯片地址+写命令
LCALL CACK ;应答检查
LCALL RD8BIT ;读8位数
LCALL STOP ;关闭总线
RET
START: LCALL DEL5US ;对2402操作开始
CLR SDA ;在SCL=1时,SDA由1变为0表示开始
LCALL DEL5US
CLR SCL
LCALL DEL5US
RET
;***************************写8比特*****************************
WR8BIT: MOV A,R7 ;将R7中的数发送出去
MOV R6,#08H ;数据位数
WR1BIT: RLC A ;将A中的数据移到数据线上
MOV SDA,C ;送出数据
LCALL DEL5US ;延时5US
SETB SCL ;发送串行时钟进行写操作
LCALL DEL5US
CLR SCL
DJNZ R6,WR1BIT ;串行发送8BIT
SETB SDA ;准备接收ACK
LCALL DEL5US
SETB SCL ;接收ACK的时钟
LCALL DEL5US
RET
CACK: MOV R1,#05 ;检测应答
CACK1: MOV C,SDA
DJNZ R1,Y1
LJMP Y2
Y1: JC $ ;有应答的时候应为低电平
AJMP Y3
Y2: MOV R1,#06H
Y3: CLR SCL ;为下一步其他操作做准备
CLR SDA ;
LCALL DEL1MS ;等待内部写完
RET
;***************************读8比特*****************************
RD8BIT: PUSH ACC ;保存 ACC
MOV R6,#08H
RD1B: SETB SDA ;置数据线=1
LCALL DEL5US
SETB SCL ;输出一个串行时钟
LCALL DEL5US
MOV C,SDA ;读数据线上的数据到C
RLC A ;移到ACC
LCALL DEL5US
CLR SCL
DJNZ R6,RD1B ;读8BIT数据
LCALL DEL5US
CLR SDA
MOV R7,ACC ;将接收到的数据保存到R7
POP ACC ;还原ACC
RET
STOP: LCALL DEL5US ;对2402操作结束
SETB SCL ;在 SCL =1时,SDA由0变为1表示结束
LCALL DEL5US
SETB SDA
LCALL DEL5US
RET
DEL5US: NOP
NOP
NOP
NOP
RET
DEL1MS: MOV R4,#200
NOP
NOP
NOP
DJNZ R4,$-3
RET
DEL10MS: MOV 3FH,#10
LCALL DEL1MS
DJNZ 3FH,$-3
RET
END
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -