TITLE   Octal-to-binary conversion using shifts   OCT_BIN.ASM
COMMENT |
        Objective: To convert an 8-bit octal number to the
                   binary equivalent using shift instruction.
            Input: Requests an 8-bit octal number from user.
           Output: Prints the decimal equivalent of the input
|                  octal number.
.MODEL SMALL
.STACK 100H
.DATA
octal_number   DB  4 DUP (?) ; to store octal number
input_prompt   DB  'Please input an octal number: ',0
out_msg1       DB  'The decimal value is: ',0
query_msg      DB  'Do you want to quit (Y/N): ',0

.CODE
.486
INCLUDE io.mac
main  PROC
      .STARTUP
read_input:
      PutStr  input_prompt    ; request an octal number
      GetStr  octal_number,4  ; read input number
      nwln
      mov     BX,OFFSET octal_number ; pass octal # pointer
      call    to_binary    ; returns binary value in AX
      PutStr  out_msg1
      PutInt  AX           ; display the result
      nwln
      PutStr  query_msg    ; query user whether to terminate
      GetCh   AL           ; read response
      nwln
      cmp     AL,'Y'       ; if response is not 'Y'
      jne     read_input   ; read another number
done:                      ; otherwise, terminate program
      .EXIT
main  ENDP

;-----------------------------------------------------------
; to_binary receives a pointer to an octal number string in
; BX register and returns the binary equivalent in AL (AH is
; set to zero). Uses SHL for multiplication by 8. Preserves
; all registers, except AX.
;-----------------------------------------------------------
to_binary     PROC
      push    BX           ; save registers
      push    CX
      push    DX
      xor     AX,AX        ; result := 0
      mov     CX,3         ; max. number of octal digits
repeat1:
      ; loop itarates a maximum of 3 times;
      ; but a NULL can terminates it early
      mov     DL,[BX]      ; read the octal digit
      cmp     DL,0         ; is it NULL?
      je      finished     ; if so, terminate loop
      and     DL,0FH       ; else, convert char. to numeric
      shl     AL,3         ; multiply by 8 and add to binary
      add     AL,DL        
      inc     BX           ; move to next octal digit 
      loop    repeat1      ; and repeat
finished:
      pop     DX            ; restore registers
      pop     CX
      pop     BX
      ret
to_binary     ENDP
      END     main
