;看到网上有人求“四字节除以三字节”的子程序,随手把我以前写的程序改了改,发表在下面。
;自我感觉不错,自认为是一个能够完成该功能的,最简短的程序。
;程序如下,呵呵,献丑了。
;=============================================
ORG 0000H
LJMP START
ORG 0030H ;主程序开始
START:
MOV R7, #05H ;设定一个32位的被除数
MOV R6, #0F5H ;05 F5 E0 FFH
MOV R5, #0E0H ;=99 999 999
MOV R4, #0FFH
; MOV R3, #69H
MOV R2, #98H ;设定一个24位的除数
MOV R1, #96H ;98 96 80H
MOV R0, #80H ;=10 000 000
CALL DIV_32_24 ;调用除法子程序
SJMP $ ;商,可以用计算器验证:00 00 00 09H
;余数为:98 96 7FH = 9 999 999
;****************************************************
;* 四字节/三字节无符号数除法程序 *
;* 已经测试通过 *
;****************************************************
; R7R6R5R4 / R2R1R0 --> R7R6R5R4...32H31H30H
;
;被除数 R7R6R5R4, 除数 R2R1R0
; 商 R7R6R5R4, 余数 32H31H30H
;因为数字较大, 本程序使用了:A、B、33H 和 32H 31H 30H
;对这些单元的保护工作, 应该在主程序中进行
;-----------------------------------------------------------
DIV_32_24:
CLR A
MOV 30H, A
MOV 31H, A
MOV 32H, A
MOV R3, #32 ;循环次数
;---------------------------------------------------
CLR C
DIV_LOOP:
CALL SL_R7_R4
CALL SL_32_30
;(32H31H30H <-- R7R6R5R4 <-- C) 左移一位
MOV F0, C
;---------------------
CLR C ;IF (32H31H30H >= R2R1R0) 32H31H30H -= R2R1R0;
MOV A, 30H
SUBB A, R0
MOV 33H, A
MOV A, 31H
SUBB A, R1
MOV B, A
MOV A, 32H
SUBB A, R2
JNC DIV_2
JNB F0, CPL_C ;不够减就不保存差
CPL C
DIV_2:
MOV 30H, 33H
MOV 31H, B
MOV 32H, A
CPL_C:
CPL C
DJNZ R3, DIV_LOOP
;---------------------------------------------------
SL_R7_R4:
MOV A, R4
RLC A
MOV R4, A
MOV A, R5
RLC A
MOV R5, A
MOV A, R6
RLC A
MOV R6, A
MOV A, R7
RLC A
MOV R7, A
RET
;---------------------
SL_32_30:
MOV A, 30H
RLC A
MOV 30H, A
MOV A, 31H
RLC A
MOV 31H, A
MOV A, 32H
RLC A
MOV 32H, A
RET
;---------------------------------------------------
END
;=============================================