;; MPPUTDEC.ASM--Display a multiple-precision number on the CRT ;; in decimal. Positive numbers only are accepted. No error ;; checking is done. ;; ;; Calling Sequence: ;; ;; push pointer to number ;; push words in number ;; EXTRN MPPutDec : NEAR ;; call MPPutDec ;; ;; Library source text from "Assembly Language for the IBM PC Family" by ;; William B. Jones, (c) Copyright 1992, 1997, Scott/Jones Inc. ;; INCLUDE PCMAC.INC .MODEL SMALL .CODE PUBLIC MPPutDec APtr EQU DWORD PTR [bp+6] Len EQU WORD PTR [bp+4] NZD EQU BYTE PTR [bp-3] ; Has a non-zero digit occurred DigCt EQU BYTE PTR [bp-4] ; Number of digits pushed onto stack NumLeft EQU -6 ; Offset to left word of number to put MPPutDec PROC push bp mov bp, sp push ds sub sp, 2 ; Storage for DigCt, NZD ; ; First--move the number to local storage, where it can be altered ; mov ax, Len mov cx, ax shl ax, 1 ; Get number of bytes sub sp, ax ; .and allocate that much space on stack mov bx, sp ; Offset to first word of dest on stack lds si, APtr ; ds:si --> A sub bx, si ; bx := stack offset - A MovIn: mov ax, [si] mov ss:[bx + si], ax ; note ss: override!! add si, 2 loop MovIn mov DigCt, 0 mov bx, 10 ; The divisor ; ; repeat ... until NZD = 0 ; DigLoop: mov NZD, 0 ; indicates no non-zero digits in quotient ; ; compute NumLeft := NumLeft div 10; remainder --> dx ; mov si, NumLeft ; Left end in fixed position rel bp mov cx, Len mov dx, 0 ; Initial high-order bits of dividend MPDivideBy10: mov ax, [bp+si] ; dx:ax := prev remdr:brought down ; next digit div bx mov [bp+si], ax test ax, ax jz ZeroResult mov NZD, 1 ; Quotient is non-zero; another step needed ZeroResult: sub si, 2 loop MPDivideBy10 ; End of divide by 10 add dl, '0' ; Convert final remainder to ASCII digit push dx inc DigCt cmp NZD, 0 jne DigLoop ; End of repeat ... until ; ; All digits computed and pushed on the stack ; mov cl, DigCt sub ch, ch PutLoop: pop ax _PutCh al loop PutLoop mov ds, [bp-2] ; Restore and quit mov sp, bp pop bp ret 6 MPPutDec ENDP END