Reputation: 1
can someone please show me a code for multiplying two WORD-SIZE digits. I've been searching everywhere and i've tried everything but it either results in a segmentation fault, wrong result, or not exceeding 256.
All of the variables are word-size, resw.
mov ah, 0
mov al, [num2]
mov bl, 10
mul bl
add al, [num1]
mov word[num1], ax
This one results to not exceeding 256.
mov ax, 10
mul word[num2]
add [num1], ax
This one results to a segmentation fault, or probably just a wrong result, i'm not sure.
EDIT
Here's my whole code
section .data
number db 'Enter a number: '
numberLen equ $-number
fibo db' -----Fibonacci Sequence----- ', 10
fibolen equ $-fibo
newline db '', 10
newlinelen equ $-newline
space db ' '
spacelen equ $-space
section .bss
num1 resw 1
num2 resw 1
no1 resw 1
no2 resw 1
no3 resw 1
section .text
global _start
_start:
mov eax, 4
mov ebx, 1
mov ecx, number
mov edx, numberLen
int 80h
mov eax, 3
mov ebx, 0
mov ecx, num2
mov edx, 1
int 80h
mov eax, 3
mov ebx, 0
mov ecx, num1
mov edx, 2
int 80h
sub word[num1], 30h
sub byte[num2], 30h
mov ah,0
mov al,[num2]
mov bl,10
mul bl
add al,[num1]
mov word[num1],ax
mov eax, 4
mov ebx, 1
mov ecx, fibo
mov edx, fibolen
int 80h
cmp word[num1], 0
je skip
sub esp, 4
push word[num1]
call getfibo
pop cx
pop dx
skip:
mov eax, 4
mov ebx, 1
mov ecx, newline
mov edx, newlinelen
int 80h
exit:
mov eax, 1
mov ebx, 0
int 80h
getfibo:
mov ebp, esp
cmp word[ebp + 4], 1
je fibo_end
mov cx, [ebp+4]
dec cx
sub esp, 4
push cx
call getfibo
pop cx
pop dx
mov ebp, esp
add cx, dx
mov word[ebp + 6], dx
mov word[ebp + 8], cx
mov ax, word[ebp + 8]
mov dx, 0
mov ah, 0
mov bx, 100
div bx
mov [no3], ax
mov [no2], dx
mov ax, [no2]
mov dx, 0
mov ah, 0
mov bx, 10
div bx
mov [no2], ax
mov [no1], dx
add word[no3], 30h
add word[no2], 30h
add word[no1], 30h
mov eax, 4
mov ebx, 1
mov ecx, no3
mov edx, 1
int 80h
mov eax, 4
mov ebx, 1
mov ecx, no2
mov edx, 1
int 80h
mov eax, 4
mov ebx, 1
mov ecx, no1
mov edx, 1
int 80h
mov eax, 4
mov ebx, 1
mov ecx, space
mov edx, spacelen
int 80h
ret 2
fibo_end:
mov word[ebp + 6], 1
mov word[ebp + 8], 1
mov ax, word[ebp + 8]
mov dx, 0
mov ah, 0
mov bx, 100
div bx
mov [no3], ax
mov [no2], dx
mov ax, [no2]
mov dx, 0
mov ah, 0
mov bx, 10
div bx
mov [no2], ax
mov [no1], dx
add word[no3], 30h
add word[no2], 30h
add word[no1], 30h
mov eax, 4
mov ebx, 1
mov ecx, no3
mov edx, 1
int 80h
mov eax, 4
mov ebx, 1
mov ecx, no2
mov edx, 1
int 80h
mov eax, 4
mov ebx, 1
mov ecx, no1
mov edx, 1
int 80h
mov eax, 4
mov ebx, 1
mov ecx, space
mov edx, spacelen
int 80h
ret 2
It shows the fibonacci sequence, the number input determines how many of the sequence will show up. The parts that I'm having trouble are these two.
add cx, dx
mov word[ebp + 6], dx
mov word[ebp + 8], cx
mov ah,0
mov al,[num2]
mov bl,10
mul bl
add al,[num1]
mov word[num1],ax
For now, it's not exceeding 256, When I input 12, it goes up to 233, but when i input 13, it goes from 233, then 121.
Upvotes: 0
Views: 674
Reputation: 134055
It seems like you have a bug in your first example. The result of the mul bl
instruction will be a word-sized result in the AX register. But then you add the value at memory address num1
to the AL register. That's going to mess up your result if the addition results in a carry (i.e. makes AL roll past 255). Consider, for example, if the [num2]
contains 30. The result of the mul bl
instruction, then, will be a value of 300 (0x012C) in the AX register. If the value at [num1]
is equal to 212 (0xD4), then the result of the add al,[num1]
instruction will be (0x100), because you're doing an 8-bit addition. But the result should be 0x200.
It appears you're trying to multiply two 8-bit values to get a 16-bit result, and add that result to the value at [num1]
. The correct code would be:
mov ah,0
mov al,[num2]
mov bl,10
mul bl
add ax,[num1]
mov [num1],ax
You can simplify that to:
mov ax,10
mul byte [num2]
add [num1],ax
Which is probably what you meant to do with your second example. Your second example has mul word[num2]
, which is going to be a problem (give you a wrong result) if num2
is defined as a one-byte value. It could give you a segmentation fault if the byte after [num2]
is outside your process's valid memory space.
When you multiply two word-sized values, the result is a dword. The low word is stored in AX, and the high word is in DX. But if you just care about the low word, then you can ignore the value in DX.
What you have in your second example is equivalent to this C code:
int num1, num2;
num1 = num1 + (num2 * 10);
If what you really want is:
num1 = num2 * 10;
Then you need to change that add [num],ax
to mov [num],ax
.
Upvotes: 1