I have tried writing a simple program that converts 2 digit Roman numbers into 1 digit Arabic number. I don't know where the error could be. I double checked everything multiple times.
According to GNU debugger, the values of AL and BL are as intended. I think that the sys_write fails most of the time. Also, please don't complain about repetitive instructions, I just hate making subroutines.
SECTION .data
zprava db 'rimske cislo:'
znakyzprava equ $-zprava
linefeed db 0xA
SECTION .bss
inputcislo resb 2
SECTION .text
global _start
_start:
mov edx,znakyzprava
mov ecx,zprava
mov ebx,1
mov eax,4
int 80h
mov edx,2
mov ecx,inputcislo
mov ebx,0
mov eax,3
int 80h
uzmamdata:
mov al,[inputcislo]
mov bl,[inputcislo+1]
hodnotyznaku:
cmp al,73
jz ali
cmp al,86
jz alv
cmp al,88
jz alx
pulka:
cmp bl,73
jz ahi
cmp bl,86
jz ahv
cmp bl,88
jz ahx
jmp konechodnot
ali:
mov al,1
jmp pulka
alv:
mov al,5
jmp pulka
alx:
mov al,10
jmp pulka
ahi:
mov bl,1
jmp konechodnot
ahv:
mov bl,5
jmp konechodnot
ahx:
mov bl,10
jmp konechodnot
konechodnot:
cmp al,bl
jg alvet ;kdyz je al vetsi nez ah
jl almen
alvet:
sub al,bl
jmp dale
almen:
add al,bl
jmp dale
dale:
add al,48
mov edx,1
mov ecx,0
add cl,al
mov ebx,1
mov eax,4
int 80h
mov edx,1
mov ecx,linefeed
mov ebx,1
mov eax,4
int 80h
konec:
mov ebx,0
mov eax,1
int 80h
The problem is much the same as it was in your previous question! My answer already explained that you should use a memory buffer, so you can pass its address to sys_write
. Make it a sufficiently large general purpose buffer, and set it up in the .bss
section:
SECTION .bss
buffer resb 4096
Your program should never be relying on any pre-existing contents in that buffer. And to actually demonstrate that it is indeed "general purpose", you can use the same buffer for your input too, meaning you can omit that inputcislo resb 2
reservation.
mov edx, znakyzprava
mov ecx, zprava
mov ebx, 1
mov eax, 4
int 80h
mov edx, 2
mov ecx, buffer
mov ebx, 0
mov eax, 3
int 80h
mov al, [buffer]
mov bl, [buffer+1]
...
add al, 48 ; Convert single digit into character
mov [buffer], al ; Store to memory
mov byte [buffer+1], 10 ; Put a newline behind it
mov edx, 2 ; Write both together, you don't need the separate 'linefeed' anymore
mov ecx, buffer
mov ebx, 1
mov eax, 4
int 80h
konec:
mov ebx, 0
mov eax, 1
int 80h
cmp al,bl jg alvet ;kdyz je al vetsi nez ah jl almen alvet: sub al,bl jmp dale almen: add al,bl jmp dale
Unrelated, but I think you have the 'addition' and 'subtraction' operations reversed!
Take the roman number "VI" where you should be adding (5 + 1), or the roman number "IX" where you should be reversed subtracting (10 - 1).
And you forgot to deal with equal digits; For the roman number "II" you need to add (1 + 1), so not the subtraction that would happen now.
cmp al, bl
jge almen
alvet:
xchg al, bl ; Put the greater digit in AL first
sub al, bl
jmp dale
almen:
add al, bl
jmp dale