%TITLE          "Convert Hexadecimal Data to Digital Characters - CHiPS bv 1998"
;**********************************************************************
;**                                                                  **
;**  Program   : HEX2DIGI                                            **
;**  Purpose   : Convert Hexadecimal Data to Digital Characters      **
;**                                                                  **
;**  Author    : B.F. Schreurs                                       **
;**              Computer High Performance Software (CHiPS) bv       **
;**  Date      : Januari 27th, 1998                                  **
;**                                                                  **
;**  Calls     : [None]                                              **
;**                                                                  **
;**  Language  : Turbo Assembler                                     **
;**                                                                  **
;**  Returncode: 0 - Conversion OK                                   **
;**                                                                  **
;**********************************************************************
        IDEAL
        JUMPS

;----------------------------------------------------------------------
;--  Functions which can be called                                   --
;----------------------------------------------------------------------
        PUBLIC  HEX2DIGI

;----------------------------------------------------------------------
;--  Equates                                                         --
;----------------------------------------------------------------------
include ".\equ\dos.equ"
include ".\equ\sysdep.equ"

FILE_SIZE_INIT_LENGTH   EQU  15

;**********************************************************************
SEGMENT SSeg Para Stack 'STACK'
;**********************************************************************

        db        64 dup (0)            ; Stack

ENDS    SSeg



;**********************************************************************
SEGMENT DSeg Word Public 'DATA'
;**********************************************************************

;----------------------------------------------------------------------
;--  Working Storage                                                 --
;----------------------------------------------------------------------
GLOBAL Return_Code:Byte:1

Parm_Format_ptr_es      DW    1 dup (NULL)      ; 1 = With Thousand Seperator
Parm_Format_ptr_di      DW    1 dup (NULL)      ; 2 = Without Thousand Seperator

Parm_Hex_Digit_ptr_es   DW    1 dup (NULL)
Parm_Hex_Digit_ptr_di   DW    1 dup (NULL)

File_Size_Init          DB   "000,000,000"
File_Size_Init_No_Sep   DB   "  000000000"

ENDS    DSeg



;**********************************************************************
SEGMENT CSeg Word Public 'CODE'
;**********************************************************************

;**********************************************************************
PROC    HEX2DIGI
;**********************************************************************
        ASSUME  cs:CSeg
        ASSUME  ds:DSeg
        mov     ax, DSeg                    ; Initialize DS to address
        mov     ds, ax                      ; of data segment

        mov     bx, sp

;
; Parameter Hex data (Digit data is placed in the same area)
;
        mov     di, [ss:bx+2]
        mov     es, [ss:bx+4]

        mov     [Parm_Hex_Digit_ptr_es], es
        mov     [Parm_Hex_Digit_ptr_di], di

;
; Parameter Format
;
        mov     di, [ss:bx+6]
        mov     es, [ss:bx+8]

        mov     [Parm_Format_ptr_es], es
        mov     [Parm_Format_ptr_di], di

;
; Init return code
;
        mov     al, NULL
        mov     [Return_Code], al

;
; Load Ax en Dx with Hex number to be converted
;
        mov     es, [Parm_Hex_Digit_ptr_es]     ; Assume Hex 12345678
        mov     di, [Parm_Hex_Digit_ptr_di]

        mov     dh, [byte es:di]                ; Would be hex 12
        mov     dl, [byte es:di + 1]            ;          hex 34
        mov     ah, [byte es:di + 2]            ;          hex 56
        mov     al, [byte es:di + 3]            ;          hex 78

;
; Init Text Field
;
        mov     si, offset File_Size_Init

        push    es di

        mov     es, [Parm_Format_ptr_es]        ; Assume with thousand seperator
        mov     di, [Parm_Format_ptr_di]
        cmp     [byte es:di], "1"               ; Convert with seperator?
        je      @@05                            ; Yes
                                                ; No, so
        mov     si, offset File_Size_Init_No_Sep

@@05:
        pop     di es
        mov     cx, DIGITS_TEXT_LENGTH
        rep     movsb

;
; Go to end of conversion string
;
        dec     di

;
; Determine
;
        mov     bx, 10000                   ; Split value
        div     bx
        mov     cx, ax                      ; Save value above 10000
        mov     ax, dx                      ; First convert value below 10000
        mov     bx, 10                      ; Extract digits

; Convert hexadecimal size to textual digits
@@10:
        call    Extract_Digit               ; Convert value below 10000
        call    Extract_Digit
        call    Extract_Digit
        call    Extract_Digit
        mov     ax, cx                      ; Now convert value above 10000
        call    Extract_Digit               ; Convert value above 10000
        call    Extract_Digit
        call    Extract_Digit
        call    Extract_Digit
        call    Extract_Digit

; Surpress leading zeroes
        mov     bx, 10                      ; Value contains 11 characters
                                            ;       but we don't surpress
                                            ;       the last zero
@@20:                
        inc     di                          ; Move to digital character
        cmp     [byte es:di], THOUSAND_SEPERATOR ; Character is decimal?
        jne     @@30                        ; No
                                            ; Yes, so
        mov     [byte es:di], SPACE         ; Replace decimal by space
        jmp     @@40                        ; Process next character

@@30:
        cmp     [byte es:di], ZERO          ; Character is leading zero?
        jne     @@99                        ; No
                                            ; Yes, so
        mov     [byte es:di], SPACE         ; Replace leading zero by space

@@40:
        dec     bx                          ; More characters to check?
        jnz     @@20                        ; Yes
                                            ; No, so
@@99:
        ret

ENDP    HEX2DIGI


;**********************************************************************
PROC    Extract_Digit
;**********************************************************************
        xor     dx, dx                      ; Reset result
        div     bx                          ; Extract digit
        add     dx, 030h                    ; Turn digit into character
        cmp     [byte es:di], THOUSAND_SEPERATOR ; Character is decimal?
        jne     @@10                        ; No
                                            ; Yes, so
        dec     di                          ; Move to previous character

@@10:
        mov     [byte es:di], dl            ; Move character to text
        dec     di                          ; Move to previous character
        ret

ENDP    Extract_Digit



ENDS    CSeg                                ; End of Code segment

END                                         ; End of Program
