📄 new51pro.a51
字号:
;开机复位:RESET
;主 循 环:MAIN_LOOP
$EP(ERROR.TXT)
$INCLUDE(New51Pro.H51)
;**********************************************
ORG 0000H
BEGIN: LJMP RESET
ORG 0023H ;SERIAL INTERRUPT
UARTI: LJMP S_INTR
ORG 0030H
DB "My Small Progam!"
;************************************************
;****** 上电复位代码 ******************************
;************************************************
ORG 0040H
RESET: MOV SP,#50H
CLR_RAM:CLR A
MOV R0,#0FFH
MOV @R0,A
DJNZ R0,$-1
LCALL INI_FSR
INI_SYS:CLR IO_SW0 ;开机状态:40 Pins
MOV RX_CNT,#0
MOV TX_CNT,#0
MOV RX_PIN,#RXD_HAD
MOV TX_PIN,#TXD_HAD
DEL_mS 200 ;=200mS
START: SETB TR1
SETB EA
HELLO: MOV DPTR,#MSG_HELLO
LCALL SEND_MSG
;*************************************************
;******* 命令处理程序 ******************************
;*************************************************
MAIN_LOOP: ;
JB OK_RXD,ANS_COMMAND
;-----------------------
;JNB RI,MAIN_LOOP
;LCALL S_INTR
;-----------------------
SJMP MAIN_LOOP
;-------------------------------------------------
ANS_COMMAND:
CLR OK_RXD ;
MOV DPTR,#CMD_TAB ;
MOV A,RX_CODE
ANL A,#07H
RL A ;
JMP @A+DPTR
CMD_TAB:
SJMP CMD_REST ;0
SJMP CMD_BANK ;1
SJMP CMD_READ ;2
SJMP CMD_PROG ;3
SJMP CMD_ERAS ;4
SJMP CMD_LOCK ;5
SJMP CMD_SETT ;6
SJMP CMD_SING ;7
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
CMD_REST: ;复位、握手
SJMP RESET
CMD_BANK: ;查空
LCALL CHECK_BANK
SJMP CMD_END
CMD_READ: ;读出
LCALL READ_ROM
SJMP CMD_END
CMD_PROG: ;编程
LCALL PROG_ROM
SJMP CMD_END
CMD_ERAS: ;擦除
LCALL ERASE_ROM
SJMP CMD_END
CMD_LOCK: ;加密
LCALL LOCK_CHIP
SJMP CMD_END
CMD_SETT: ;设置
LCALL SET_TYPE
SJMP CMD_END
CMD_SING: ;检测
LCALL TEST_SING
CMD_END:SJMP MAIN_LOOP
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;***********************************************
;****** 功能主程序 ******************************
;***********************************************
;====== ROM 查空 ================================
;一律文本应答
CHECK_BANK:
MOV R0,#RXD_BUF ;
MOV R1,#(RXD_BUF+1) ;
MOV SADD_H,RX_PAR1 ;起始地址
MOV SADD_L,RX_PAR2 ;
MOV EADD_H,@R0 ;保存总结束地址
MOV EADD_L,@R1 ;
BAK_INI:MOV A,TYPE
;这里扩展其他类型
bank_2: CJNE A,#W_E5xx,bank_1
LCALL BANK_E5xx ;IS W78E5x
SJMP BANK_OK
bank_1: CJNE A,#A_C5xx,bank_0 ;
LCALL BANK_C5xx ;IS AT89C5x
SJMP BANK_OK
bank_0: CJNE A,#A_x051,BANK_END ;
LCALL BANK_x051 ;IS AT89Cx051
BANK_OK:JC NO_BANK
IS_BANK:MOV DPTR,#MSG_BANK
SJMP BANK_OV
NO_BANK:MOV DPTR,#MSG_UNBAK
BANK_OV:LCALL SEND_MSG
SETB REN
BANK_END:
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;====== 擦除 ROM 程序 ===============================
;一律文本应答
ERASE_ROM:
MOV A,TYPE
;这里扩展其他类型
eras_1: CJNE A,#W_E5xx,eras_2 ;
LCALL ERS_E5xx ;IS W78E5x
SJMP ERAS_OK
eras_2: CJNE A,#A_C5xx,eras_3 ;
LCALL ERS_C5xx ;IS AT89C5x
SJMP ERAS_OK
eras_3: CJNE A,#A_x051,ERAS_END ;
LCALL ERS_x051 ;IS AT89Cx051
ERAS_OK:MOV DPTR,#MSG_ERASE
LCALL SEND_MSG
SETB REN
ERAS_END:
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;====== 设定芯片 =================================
;一律文本应答
SET_TYPE:
MOV TYPE,RX_PAR1
MOV A,RX_PAR2
ANL A,#0FH
MOV VPP,A
MOV A,RX_PAR2
SWAP A
ANL A,#0FH
MOV VEP,A
TYP_INI:MOV A,TYPE
;这里扩展其他类型
SET_E5x:CJNE A,#W_E5xx,SET_C5x
CLR IO_SW0 ;Select 40Pins
SJMP TYPE_OK
SET_C5x:CJNE A,#A_C5xx,SET_x05
CLR IO_SW0 ;Select 40Pins
SJMP TYPE_OK
SET_x05:CJNE A,#A_x051,TYPE_OK
SETB IO_SW0
TYPE_OK:VPP_05V
MOV DPTR,#MSG_TYPE
LCALL SEND_MSG
SETB REN
TYPE_END:
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;====== 测试芯片参数 ==========================
;一律文本应答
TEST_SING: ;
MOV A,TYPE
;这里扩展其他类型
S_E5x: CJNE A,#W_E5xx,S_C5x
LCALL GET_E5x ;暂缺
SJMP SING_OK
S_C5x: CJNE A,#A_C5xx,S_x051
LCALL GET_C5xx
SJMP SING_OK
S_x051: CJNE A,#A_x051,TEST_END
LCALL GET_x051
SING_OK:SETB REN ;开放接收
TEST_END:
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;====== 读出 ROM 程序 ===========================
;FUN: 每次调用读一帧(总是16字节)ROM
;SADD: 跟踪每帧起始地址
;CADD: 跟踪每帧结束地址
;EADD: 保存总的结束地址
READ_ROM:
MOV R0,#RXD_BUF ;=4: 读预备命令
MOV R1,#(RXD_BUF+1) ;=4: 读预备命令
MOV A,RX_LENG
RED_PER:MOV SADD_H,RX_PAR1 ;起始地址
MOV SADD_L,RX_PAR2 ;
RED_ST: CJNE A,#4,RED_INI ;<4: 读数据命令
MOV EADD_H,@R0 ;保存总结束地址
MOV EADD_L,@R1 ;
CLR IN_RED ;准备进入读状态
MOV A,#R_CODE ;
ANSWER 0 ;短应答
SJMP RED_END
RED_INI:MOV A,TYPE
;这里扩展其他类型
read_2: CJNE A,#W_E5xx,read_1
LCALL READ_E5xx ;IS W78E5x
SJMP RED_OK
read_1: CJNE A,#A_C5xx,read_0 ;
LCALL READ_C5xx ;IS AT89C5x
SJMP RED_OK
read_0: CJNE A,#A_x051,RED_END ;
LCALL READ_x051 ;IS AT89Cx051
RED_OK: MOV TX_PAR1,SADD_H ;每16字节上传
MOV TX_PAR2,SADD_L
MOV A,#R_CODE
CK_ROV: LCALL CHK_OVE ;结束?
JNC RED_NXT ;
RED_OVE:CLR IN_RED ;
SETB ACC.4 ;末帧!插入结束标志
RED_NXT:
ANSWER 18 ;长应答: 读出数据上传!
RED_END:
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;====== 写入 ROM 程序 ===========================
;FUN: 每次调用写一帧(最多16字节)ROM
;SADD: 跟踪每帧起始地址
;CADD: 跟踪每帧结束地址
;EADD: 保存总的结束地址
PROG_ROM:
MOV R0,#RXD_BUF ;=4: 写预备命令
MOV R1,#(RXD_BUF+1) ;=4: 写预备命令
PRG_PER:MOV SADD_H,RX_PAR1 ;
MOV SADD_L,RX_PAR2
PRG_ST: MOV A,RX_LENG
CJNE A,#4,PRG_INI ;>4: 写数据命令
MOV EADD_H,@R0 ;保存总结束地址
MOV EADD_L,@R1 ;
CLR IN_PRG ;准备进入编程状态
MOV A,#W_CODE
SJMP PRG_NXT
PRG_INI:MOV A,TYPE
;这里扩展其他类型
prog_2: CJNE A,#W_E5xx,prog_1 ;
LCALL PROG_E5X ;IS W78E5x
SJMP PRG_OK
prog_1: CJNE A,#A_C5xx,prog_0 ;
LCALL PROG_C5X ;IS AT89C5x
SJMP PRG_OK
prog_0: CJNE A,#A_x051,PRG_END ;
LCALL PROG_051 ;IS AT89Cx051
PRG_OK: MOV A,#W_CODE
CK_POV: LCALL CHK_OVE
JNC PRG_NXT ;结束?
PRG_OVE:CLR IN_PRG
LCALL Read_ini ;编程结束
MOV A,#W_CODE
SETB ACC.4 ;末帧!插入结束标记
PRG_NXT:
ANSWER 0 ;返回进度
PRG_END:
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;--------------------------------------------------
Read_ini:
VPP_05V
MOV A,TYPE
RDI_2: CJNE A,#W_E5xx,RDI_1
LCALL Read_E5x_ini
SJMP RDI_END
RDI_1: CJNE A,#A_C5xx,RDI_0
LCALL Read_C5x_ini
SJMP RDI_END
RDI_0: CJNE A,#A_x051,RDI_END
LCALL Read_x051_ini
;SJMP RDI_END
RDI_END:RET
;====== 加密 芯片 程序 =============================
;一律文本应答
LOCK_CHIP:
MOV A,TYPE
;这里扩展其他类型
lock_2: CJNE A,#W_E5xx,lock_1 ;
LCALL LOCK_E5xx ;IS W78E5x
SJMP LOCK_OK
lock_1: CJNE A,#A_C5xx,lock_0 ;
LCALL LOCK_C5xx ;IS AT89C5x
SJMP LOCK_OK
lock_0: CJNE A,#A_x051,LOCK_END ;
LCALL LOCK_x051 ;IS AT89Cx051
LOCK_OK:MOV DPTR,#MSG_LOCK
LCALL SEND_MSG
SETB REN
LOCK_END:
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;*********************************************
;****** 针对 AT89Cx051 的功能子程序 ************
;*********************************************
;====== AT89Cx051 读出子程序 ==================
;一次性读完,读出量由结束地址 EADD 控制
READ_x051:
JB IN_RED,R05_INI
Rx05_PRE:
VPP_00V
VPP_05V
LCALL Read_x051_ini ;IO init
SETB IN_RED
;开始读出循环
R05_INI:MOV DPH,SADD_H ;总的起始地址
MOV DPL,SADD_L
MOV R0,#TXD_BUF
MOV R2,#10H
R05_LOP:MOV P0,#0FFH ;帧内循环
READ_x051_DATA
MOV @R0,A ;Move Data
INC R0 ;
MOV CADD_H,DPH ;保存末地址
MOV CADD_L,DPL ;
INC DPTR ;
INC_x051_ADDR ;地址增一
DJNZ R2,R05_LOP ;帧内循环
R05_END:RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;====== AT89Cx051 烧写子程序 ================
PROG_051:
JB IN_PRG,P05_INI
LCALL P05_PRE
P05_INI:MOV DPH,SADD_H
MOV DPL,SADD_L
MOV R0,#RXD_BUF ;数据指针
MOV R2,RX_LENG ;计数器
DEC_n R2,2
P05_LOP:MOV A,@R0 ;Get Data
INC R0 ;Move Point
LCALL X051_DATA ;Reversal
MOV P0,A ;Out Data
SET_x05_PROG
INC_x051_ADDR
MOV CADD_H,DPH
MOV CADD_L,DPL
INC DPTR ;内部地址计数
DJNZ R2,P05_LOP
P05_END:SETB IN_PRG
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;---------------------------------
P05_PRE:VPP_00V
VPP_05V
LCALL Prog_x051_ini
SETB IN_PRG
SEL_VPP VPP
RET
;====== AT89CX051 擦除子程序 ================
ERS_x051:
VPP_05V ;-
VPP_12V ;/ ;Vpp=12V
LCALL Eras_x051_ini
CLR IO_prg ;
DEL_mS 20 ;>10mS
SETB IO_prg ;
VPP_05V
LCALL Read_x051_ini
E05_END:RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;====== AT89Cx051 取参数子程序 ==================
GET_x051:
VPP_00V
VPP_05V
LCALL Sing_x051_ini
x051_CORP:
MOV P0,#0FFH
READ_x051_DATA
CJNE A,#1EH,NO_x0AT
IS_x0AT:MOV DPTR,#MSG_ISAT
SJMP AS_x0AT
NO_x0AT:MOV DPTR,#MSG_NOAT
AS_x0AT:LCALL SEND_MSG
x051_SIZE:
INC_x051_ADDR
MOV P0,#0FFH
READ_x051_DATA
ANL A,#0F0H
LCALL SEND_BYTE
MOV A,#51H
LCALL SEND_BYTE
GET_x051_END:
VPP_05V
LCALL Read_x051_ini
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;====== AT89Cx051 加密功能子程序 ============
LOCK_x051:
MOV A,RX_PAR1
LK_x05_Bit0:
JB ACC.0,LK_x051_B0
LJMP LK_x05_Bit1
LK_x051_B0:
VPP_05V
LCALL LK0_x051_ini
SEL_VPP VPP
SET_x05_PROG
LK_x05_Bit1:
JB ACC.1,LK_x051_B1
LJMP LK05_END
LK_x051_B1:
VPP_05V
LCALL LK1_x051_ini
SEL_VPP VPP
SET_x05_PROG
LK05_END:
VPP_05V
LCALL Read_x051_ini
RET
;====== AT89Cx051 查空子程序 ==================
;一次性读完,读出量由结束地址 EADD 控制
BANK_x051:
VPP_00V
VPP_05V
LCALL Read_x051_ini ;IO init
MOV DPH,SADD_H ;
MOV DPL,SADD_L
B05_LOP:MOV P0,#0FFH ;开始读出循环
READ_x051_DATA
CPL A
B05_CHK:JNZ B05_END ;非空!
MOV CADD_H,DPH ;
MOV CADD_L,DPL ;
LCALL CHK_OVE
JC B05_END ;结束
B05_NXT:INC DPTR ;Address Increment
INC_x051_ADDR ;地址增一
SJMP B05_LOP
B05_END:CPL C
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;====== IO 初始化子程序 =======================
;--------------------------------------------
Read_x051_ini:
SETB IO_bsy ;set free
SETB IO_prg ;set free
CLR IO_p33 ;\
SETB IO_p35 ;-Read and Writ Enabled
SETB IO_p37 ;/
SETB IO_p34 ;Read Line prep.
CLR IO_xt1
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;--------------------------------------------
Sing_x051_ini:
SETB IO_bsy
SETB IO_prg ;READ SIGN
CLR IO_p33
SETB IO_p34 ;Read Line prep.
CLR IO_p35
CLR IO_p37
CLR IO_xt1
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;--------------------------------------------
Prog_x051_ini:
SETB IO_bsy ;set free
CLR IO_p33 ;\
SETB IO_p34 ;-Writ state
SETB IO_p35 ;-Writ state
SETB IO_p37 ;/
SETB IO_prg ;-Writ line prep.
CLR IO_xt1 ;/
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;--------------------------------------------
Eras_x051_ini:
SETB IO_bsy ;\
SETB IO_xt1 ;-set free
SETB IO_prg ;/
SETB IO_p33
CLR IO_p34
CLR IO_p35
CLR IO_p37
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;--------------------------------------------
LK0_x051_ini:
SETB IO_bsy
SETB IO_xt1
SETB IO_p33
SETB IO_p34
SETB IO_p35
SETB IO_p37
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;--------------------------------------------
LK1_x051_ini:
SETB IO_bsy
SETB IO_xt1
SETB IO_p33
SETB IO_p34
CLR IO_p35
CLR IO_p37
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;*********************************************
;****** 针对 AT89C5x 的功能子程序 **************
;*********************************************
;====== AT89C5X 读出子程序 ====================
;一次性读完,读出量有 RX_PAR2 控制
READ_C5xx:
JB IN_RED,RC5_INI
RC5_PRE:VPP_05V
LCALL Read_C5x_ini ;
SETB IN_RED
;开始读出循环
RC5_INI:MOV DPH,SADD_H
MOV DPL,SADD_L
MOV R0,#TXD_BUF
MOV R2,#10H
RC5_LOP:MOV P0,#0FFH ;帧内循环
READ_C5xx_DATA
MOV @R0,A ;Move Data
INC R0 ;Move Point
MOV CADD_H,DPH
MOV CADD_L,DPL
INC DPTR ;Address Increment
DJNZ R2,RC5_LOP ;帧内循环
RC5_END:RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;====== AT89C5X 烧写子程序 ==================
PROG_C5X:
JB IN_PRG,PC5_INI
LCALL PC5_PRE
PC5_INI:MOV DPH,SADD_H
MOV DPL,SADD_L
MOV R0,#RXD_BUF ;数据指针
MOV R2,RX_LENG ;计数器
DEC_n R2,2
PC5_LOP:MOV A,@R0 ;Get Data
MOV P0,A ;Out Data
INC R0 ;
LCALL AT_ADDR ;Out Address
MOV CADD_H,DPH
MOV CADD_L,DPL
INC DPTR ;
SET_C5x_PROG
DJNZ R2,PC5_LOP ;Next Loop
PC5_END:SETB IN_PRG
RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;----------------------------------------------
PC5_PRE:VPP_05V
LCALL Prog_C5x_ini
SETB IN_PRG
SEL_VPP VPP
RET
;====== AT89C5X 擦除子程序 ================
ERS_C5xx:
VPP_12V ;VPP=12.5V
LCALL Eras_C5x_ini
CLR AT_PRG ;
DEL_mS 20 ;>10mS
SETB AT_PRG ;
VPP_05V
LCALL Read_C5x_ini
E5X_END:RET
;;;;;;; TRAP ;;;;;;;;;;;;;
NOP
NOP
LJMP RESET
;====== AT89C5X 取参数子程序 ================
GET_C5xx:
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -