⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 24c02.asm

📁 上课老师给的8086仿真器
💻 ASM
字号:
ACK    BIT 20H
SLA    EQU 30H
SUBA    DATA 31H
NUMBYTE DATA 32H
MTD     EQU  40H
MRD     EQU  50H
SCL     EQU  0B0H
SDA     EQU  0B1H
EEROM02 EQU 0A0H
	  ORG 0000H
           AJMP MAIN
          ORG 0030H
MAIN  :   MOV SP,#60H
          MOV A,#55H
          MOV R0,#MTD
          MOV R1,#08H
LOOP1:    MOV @R0,A
          INC R0
          INC A
          DJNZ R1,LOOP1
WR24C02:  MOV SLA,#EEROM02
          MOV SUBA,#00H
          MOV NUMBYTE,#08H
          LCALL IWRNBYTE
          LCALL DELAY
          NOP
          NOP
RD24C02:  MOV SLA,#EEROM02
          MOV SUBA,#00H
          MOV NUMBYTE,#08H
          LCALL IRDNBYTE
          LCALL DELAY
          MOV DPTR,#7000H
          MOV R0,#MRD
          MOV R1,#08H
LOOP2:    MOV A,@R0
          MOVX @DPTR,A
          INC DPTR
          INC R0
          DJNZ R1,LOOP2
          NOP
          SJMP $
;--------------------------------------------------------------------------------------------------------
;VI2C_ASM.ASM
;I2C 软件包的底层子程序,使用前要定义好SCL和SDA。在标准80C51模式
;(12 Clock)下,对主频要求是不高于12MHz(1个机器周期1us);若Fosc>12MHz
;则要增加相应的NOP指令数。在使用本软件包时,请在你的程序的未尾加入
;INCLUDE (VI2C_ASM.ASM)即可。
;--------------------------------------------------------------------------------------------------------
;启动I2C总线子程序

 DY:	  MOV R7,#1H
	  DJNZ R7,$
	  RET
 DELAY:   MOV R3,#10H
 DELAY0:  MOV R4,#0F0H
          DJNZ R4,$
          DJNZ R3,DELAY0
          RET

;启动I2C总线子程序
START:    SETB  SDA
          NOP
          SETB  SCL     			 ;起始条件建立时间大于4.7us
          LCALL DY
          CLR  SDA
          LCALL DY
          CLR   SCL     		 	;钳住总线,准备发数据
          NOP
          RET

;结束总线子程序
STOP:     CLR    SDA
          NOP
          SETB   SCL    			;发送结束条件的时钟信号
          LCALL DY
          SETB  SDA    			;结束总线
          LCALL DY
          RET

;发送应答信号子程序
MACK:     CLR  	SDA      		;将SDA置0
          NOP
          NOP
          SETB 	SCL
          LCALL DY
          CLR  	SCL
          NOP
          NOP
          RET

;发送非应答信号
MNACK:    SETB 	SDA          	;将SDA置1
          NOP
          NOP
          SETB 	SCL
          LCALL DY
          CLR  SCL
          NOP
          NOP
          RET

; 检查应答位子程序
; 返回值,ACK=1时表示有应答
CACK:	SETB  SDA
        NOP
        NOP
        SETB  SCL
        CLR   ACK
        NOP
        NOP
        MOV  C,SDA
        JC    CEND
        SETB  ACK           		 ;判断应答位
CEND:	NOP
        CLR  SCL
        NOP
        RET

;发送字节子程序
;字节数据放入ACC
;每发送一字节要调用一次CACK子程序,取应答位
WRBYTE:; PUSH 00H
        MOV  R0,#08H
WLP: 	RLC   A              		;取数据位
        JC     WR1
        SJMP  WR0            		;判断数据位
WLP1:   DJNZ  R0,WLP
        NOP
        RET
WR1:    SETB  SDA            		;发送1
        NOP
        SETB  SCL
        LCALL DY
        CLR   SCL
        SJMP  WLP1
WR0:  	CLR   SDA            		;发送0
        NOP
        SETB  SCL
        LCALL DY
        CLR  SCL
        SJMP WLP1
       ; POP 00H
        RET

;读取字节子程序
;读出的值在ACC
;每取一字节要发送一个应答/非应答信号
RDBYTE: ;PUSH 00H
        MOV  R0,#08H
RLP:    SETB  SDA
        NOP
        SETB  SCL         		 ;时钟线为高,接收数据位
        NOP
        NOP
        MOV  C,SDA        		 ;读取数据位
        MOV  A,R2
        CLR   SCL          		 ;将SCL拉低,时间大于4.7us
        RLC   A            		 ;进行数据位的处理
        MOV  R2,A
        NOP
        NOP
        NOP
        DJNZ  R0,RLP
        ;POP 00H        		 ;未够8位,再来一次
        RET

; 无子地址器件写字节数据
; 入口参数: 数据为ACC、器件从地址SLA
; 占用:  A、R0、CY
IWRBYTE: ;PUSH   00H
         PUSH   ACC
IWBLOOP: LCALL  START      		;起动总线
         MOV    A,SLA
         LCALL  WRBYTE     		;发送器件从地址
         LCALL  CACK
         JNB     ACK,RETWRB      ;无应答则跳转
         POP     ACC       		;写数据
         LCALL  WRBYTE
         LCALL  CACK
         LCALL  STOP
         RET
RETWRB:  POP     ACC
         LCALL  STOP
         ;POP    00H
         RET

;无子地址器件读字节数据
;入口参数: 器件从地址SLA
;出口参数: 数据为ACC
;占用 A 、R0、R2 、CY
IRDBYTE:
         LCALL  START
         MOV    A,SLA        		;发送器件从地址
         INC     A
         LCALL  WRBYTE
         LCALL  CACK
       JNB     ACK,RETRDB
         LCALL  RDBYTE       	;进行读字节操作
         LCALL  MNACK          	;发送非应信号
RETRDB:  LCALL  STOP             	;结束总线

         RET

;向器件指定子地址写N个数据
;入口参数:  器件从地址SLA、器件子地址SUBA 、发送数据缓冲区MTD、发送字节数NUMBYTE
; 占用:  A 、R0 、R1 、R3 、CY
IWRNBYTE: PUSH 00H
          PUSH 01H
          PUSH 03H
          MOV    A,NUMBYTE
          MOV    R3,A
          LCALL  START        	;起动总线
          MOV    A,SLA
          LCALL  WRBYTE       	;发送器件从地址
          LCALL  CACK
          JNB    ACK,RETWRN	 ;无应答则退出
          MOV    A,SUBA       	 ;指定子地址
          LCALL  WRBYTE
          LCALL  CACK
          MOV    R1,#MTD
WRDA:     MOV    A,@R1
          LCALL  WRBYTE       	;开始写入数据
          LCALL  CACK
          JNB     ACK,IWRNBYTE
          INC     R1
          DJNZ    R3,WRDA      	;判断写完没有
RETWRN:   LCALL  STOP
          POP 03H
          POP 01H
          POP 00H
          RET

;向器件指定子地址读取N个数据
;入口参数:  器件从地址SLA、器件子地址SUBA、接收字节数NUMBYTE
;出口参数:  接收数据缓冲区MTD
;占用:A、 R0、 R1、 R2、 R3、 CY
IRDNBYTE: ;PUSH 00H
          ;PUSH 01H
          ;PUSH 03H
            MOV    R3,NUMBYTE
           LCALL  START
           MOV    A,SLA
           LCALL  WRBYTE        ;发送器件从地址
           LCALL  CACK
           JNB     ACK,RETRDN
           MOV    A,SUBA        	;指定子地址
           LCALL  WRBYTE
           LCALL  CACK
           LCALL  START         	;重新起动总线
           MOV    A,SLA
           INC     A             	;准备进行读操作
           LCALL  WRBYTE
           LCALL  CACK
           JNB     ACK,IRDNBYTE
           MOV    R1,#MRD
RDN1:      LCALL  RDBYTE      	;读操作开始
           MOV    @R1,A
           DJNZ    R3,SACK
           LCALL  MNACK       	;最后一字节发非应答位
RETRDN:    LCALL  STOP
          ; POP 03H
          ; POP 01H
           ;POP 00H			;并结束总线
           RET
;********************************
SACK:      LCALL  MACK
           INC     R1
           SJMP   RDN1

           RET
;*********************************************************************************************
;                         请注意
;
;占用内部资源:         R0,R1,R2,R3,ACC,Cy。
;    在你的程序里要做以下定义:
;使用前须定义变量:  SLA 器件从地址  SUBA器件子地址  NUMBYTE读/写的字节数 ,位变量ACK
;使用前须定义常量:  SDA SCL 总线位  MTD 发送数据缓冲区首址    MRD 接收数据缓冲区首址
;(ACK为调试/测试位,ACK为0时表示无器件应答)
;
;*************************
END

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -