Search code examples
assemblycalculatorx86-16masm32

32 bit Calculator in 8086 Assembly


CALCULATOR 32 Bit

Can someone help me with my 32 bit calculator in MASM32. i think the adding and subtracting is OK but i cant print the number in decimal;

0002FFFF - 10005 = 1fffa

In MEMORY :0001 0FFFA

PRINTING: 165530 in decimal

DATA_HERE     SEGMENT       

    mult1 dw 0002H
          dw 0FFFFH
    mult2 dw 0001H
          dw 0005H
    ans   dw 0,0

DATA_HERE    ENDS

STACK_HERE     SEGMENT STACK
    DW 40 DUP(0)
STACK_HERE    ENDS

CODE_HERE    SEGMENT
    ASSUME CS:CODE_HERE, DS:DATA_HERE, SS: STACK_HERE

INICIO:
MOV AX,DATA_HERE
MOV DS,AX   

ADD:

MOV AX,mult1+2 ; take lower 16-bit of NUM1; take 
ADD AX,mult2+2 ; AX = AX + lower 16-bit of NUM2
MOV ans+2,AX ; Store lower 16-bit result at ans

MOV AX,mult1 ; take higher 16-bit of NUM1 in AX; 
ADC AX,mult2 ; AX = AX + NUM2 + CF (add with carry)
MOV ans,AX ; Store higher 16-bit result at ans


SUBTRACT:


MOV AX,mult1+2 ; take lower 16-bit of NUM1 in AX ; 
SUB AX,mult2+2 ; AX = AX - lower 16-bit of NUM2
MOV ans+2,AX ; Store lower 16-bit result at ans

MOV AX,mult1 ; take higher 16-bit of NUM1 in AX; 
SUB AX,mult2 ; AX = AX - NUM2
MOV ans,AX ; Store higher 16-bit result at ans

xor si,si
mov si,0   

ciclo:        
   mov AX, ans[si];          
   call display ; print AX
   add si, 2

cmp si, 2
JLE ciclo

mov ax,4C00h
int 21h        

display   proc  
  ;push CX     
  ;Beginning of procedure
  MOV BX, 10     ;Initializes divisor
  ;MOV DX, 0000H    ;Clears DX
  MOV CX, 0000H    ;Clears CX
      ;Splitting process starts here
.Dloop1:  
   MOV DX, 0000H    ;Clears DX during jump
   DIV BX      ;Divides AX by BX
   PUSH DX     ;Pushes DX(remainder) to stack
   INC CX      ;Increments counter to track the number of digits
   CMP AX, 0     ;Checks if there is still something in AX to divide
   JNE .Dloop1     ;Jumps if AX is not zero

.Dloop2:  POP DX      ;Pops from stack to DX
   ADD DX, 30H     ;Converts to it's ASCII equivalent
   MOV AH, 02H     
   INT 21H      ;calls DOS to display character
LOOP .Dloop2    ;Loops till CX equals zero

   ;pop CX
   RET       ;returns control
display  ENDP



CODE_HERE    ENDS
END INICIO

Solution

  • You first print the lower 16 Bit as a decimal FFFA -> 65530 and the 1 from the second word.

    1 65530.

    If you have a 32 Bit Processor you can perform you division with EAX/EDX registers.

    If not it is more complicated. Then you have to simulate a 32 Bit divission. That's no fun ;-).

    Here's a hint: http://en.wikipedia.org/wiki/Division_algorithm (yes you must handle bits)

    If you write a C programm that divides a long value by 10L, compile it for your processor (16 Bit) and dissasemble the output then, you can see how they do it. It's just an idea. I have not tried it myself. You must asure that your long value is big enough so that the compiler has no chance to optimize. ;-)