2

I'm learning assembly now, and I had to write a code that's multiply two number by two number (like 23*45 = 1035) but I need to read every number to different register (like 2 goes to ah , and 3 goes to al.. for example). Now I saw online the aam instruction but I can't manage to use it on my code, I would like for some help and an explanation how to use it right.

.MODEL small    ;DS <= 64KB, CS <= 64KB
.STACK 100h
.DATA

msg1    db 13,10,'Enter two numbers: $'
msg2    db 13,10,'Invalid value$'
msg3    db 13,10,'  *  =       $'
msg4    db 13,10,'Hit every key to exit$'
dig1    db 0
dig2    db 0
dig3    db 0
dig4    db 0
char1   db 0
char2   db 0
result1 db 0
result2 db 0
result3 db 0
result4 db 0
crlf    db 13,10,'$'

.CODE
    mov AX, @data
    mov DS, AX  

main:    
    lea DX, msg1    ;Show msg1
    mov AH, 09h     ;AH=9 - "print string" sub function
    int 21h         ;call DOS services


    ;Reading the numbers

    mov AH, 01h     ;Read first character
    int 21h
    mov dig1, AL
    cmp dig1, '0'   ;If character less than 0 - invalid
    jb invalid      ;JB - Jump if Beneath
    cmp dig1, '9'   ;if character greater than 9 - invalid
    ja invalid      ;JA - Jump if Above      

    mov AH, 01h     ;Read second character
    int 21h
    mov dig2, AL
    cmp dig2, '0'   ;If character less than 0 - invalid
    jb invalid      ;JB - Jump if Beneath
    cmp dig2, '9'   ;if character greater than 9 - invalid
    ja invalid      ;JA - Jump if Above   

    mov AH, 02h     ;space between the number
    mov DL, ' '
    int 21h                            

    mov AH, 01h     ;Read third character
    int 21h
    mov dig3, AL
    cmp dig3, '0'   ;If character less than 0 - invalid
    jb invalid      ;JB - Jump if Beneath
    cmp dig3, '9'   ;if character greater than 9 - invalid
    ja invalid      ;JA - Jump if Above      

    mov AH, 01h     ;Read fouth character
    int 21h
    mov dig4, AL
    cmp dig4, '0'   ;If character less than 0 - invalid
    jb invalid      ;JB - Jump if Beneath
    cmp dig4, '9'   ;if character greater than 9 - invalid
    ja invalid      ;JA - Jump if Above  


    ;check if the promgram ends
    mov CL, dig1
    add CL, dig2
    add CL, dig3
    add CL, dig4
    cmp CL, 192
    je exit


    ;calculating the numbers

    mov CX, 0
    sub dig1,'0'
    sub dig2,'0'
    sub dig3,'0'
    sub dig4,'0'

    mov AL,dig1          ;make dig1 tenth
    mov BL,10
    mul BL
    add AL,dig2          
    mov char1,AL         ;making char1 the first num 

    mov AL,dig3          ;make dig3 tenth
    mov BL,10
    mul BL
    add AL,dig4          
    mov char2,AL         ;making char2 the second num

    mov AL, char1
    mov BL, char2
    mul BL

    mov DX,0             ;on mul/div with 16bit must clean DX
    mov BX, 1000
    div BX               ;On 16bit: AX=result , DX=remainder  
    mov CX, DX
    mov result1, AL

    mov BL, 100
    mov AX, CX
    div BL
    mov result2, AL
    mov CL, AH           ;On 8bit: AL=result , AH=remainder
    mov BL, 10
    mov AH, 0
    mov AL, CL
    div BL
    mov result3, AL
    mov result4, AH

    add dig1,'0'
    add dig2,'0'
    add dig3,'0'
    add dig4,'0'
    add result1,'0'
    add result2,'0'
    add result3,'0'
    add result4,'0'


    ;printing the result

    lea DX, crlf        ;New line
    mov AH, 09h
    int 21h

    lea BX, msg3        ;Place msg3's address in BX
    mov AL, dig1        ;Put first number in AL
    mov [BX + 2], AL    ;Put first number in msg3
    mov AL, dig2        ;Put second number in AL
    mov [BX + 3], AL    ;Put second number in msg3
    mov AL, dig3        ;Put third number in AL
    mov [BX + 5], AL    ;Put third number in msg3
    mov AL, dig4        ;Put fourth number in AL
    mov [BX + 6], AL    ;Put fourth number in msg3
    mov AL, result1     ;Put first number of result in AL
    mov [BX + 8], AL    ;Put first number of result in msg3
    mov AL, result2     ;Put second number of result in AL
    mov [BX + 9], AL    ;Put second number of result in msg3
    mov AL, result3     ;Put third number of result in AL
    mov [BX + 10], AL   ;Put third number of result in msg3
    mov AL, result4     ;Put fourth number of result in AL
    mov [BX + 11], AL   ;Put fourth number of result in msg3
    lea DX, msg3    ;Show msg3
    mov AH, 09h
    int 21h

    jmp main

invalid:
    lea DX, msg2    ;Show msg2
    mov AH, 09h
    int 21h
    jmp main

exit:
    lea DX, msg4    ;Show msg4
    mov AH, 09h
    int 21h

    mov AH, 01h     ;Read a character
    int 21h

    mov AH, 4Ch     ;Kill the program
    int 21h

END
WillingMost7
  • 35
  • 1
  • 7

1 Answers1

1

To use AAM, start off with two single digit operands (0 through 9) and multiply them, so that the result ends up in the lower 8 bits of the AX register. Then the AAM instruction will set AH = AL/10, AL = AL%10. So in hex, 0x9 · 0x9 = 0x51 in AX. Then using AAM instruction will change this to 0x0801, an unpacked BCD result.

rcgldr
  • 27,407
  • 3
  • 36
  • 61
  • It would turn AL=0x51 into AX = 0x0801. As you say, AAM puts its results in AH and AL, unpacked like ASCII, *not packed BCD*. That's why it's called AAM (ASCII adjust After Multiply) not DAM (Decimal ...). https://www.felixcloutier.com/x86/aam – Peter Cordes Jan 22 '20 at 08:14
  • @PeterCordes - missed an edit, fixed my answer now. – rcgldr Jan 22 '20 at 15:21
  • I know how to use it if I multiply two digits only (like 3*5), but how to use it in my code? 'cause there I multiply four digits (like for example 34*21) - rcgldr – WillingMost7 Jan 23 '20 at 06:08
  • Now I'm thinking that's maybe because it's a 32bit number (which means it uses also DX and not only AX) `AAM` it does not work. – WillingMost7 Jan 23 '20 at 06:14
  • @user9756213 - AAM only works on AX. To work with larger number's you'll have to separate them into single unpacked BCD digits. You'll also need AAA to adjust for addition to add the sub-products of larger BCD numbers. – rcgldr Jan 23 '20 at 09:38