|
From: <cg...@wo...> - 2003-03-11 18:39:41
|
Jaaaaaa!!!!!!
I achieved to do it right!!!!
The correct code, with comments, for those who could be interested in=20
the subject:
/*Veamos c=F3mo se ensambla esto*/
#.include "asm_io.S"
.data
mensaje4: .ascii "Introduzca un n=FAmero\n\0" # Template strings for
#=20
printf and scanf
mensaje5: .ascii "El doble es: \0"
string1: .ascii "%d\n\0"
string2: .ascii "%d\0"
string3: .ascii "%s\0" =20
string4: .ascii "%s\n\0"
string5: .ascii "%c\n\0"
numer: .long 1 #I've not achieved to use this variable yet
# I only can output it, but not input a value
# from stdin
.bss
.comm entero, 4 # Here I'll put an integer number from stdin
# using scanf, then I'll sum it by itself and=20
output
# the result
.comm string, 255 # A string, I'll input a phrase and output it
# and the second character from it.
.text
numer =3D 200 #I set numer to be =3D 200, without this line
# it is not =3D!, but to whatever value
#entero =3D 100 ##if I add this line, then I get an
## error when input.
.global _asm_main
.extern _printf
.extern scanf # I forgot the underscore, but it works
_asm_main:
enter $0, $0
pusha
movl $mensaje4, %eax
pushl %eax
call _printf
addl $4, %esp # I changed the number added to %esp
movl $entero, %ebx # I pass the variable
# If I pass numer here
# I have use the template
# "%l" for printf
pushl %ebx
movl $string2, %eax # "%d"
pushl %eax
call _scanf
addl $8, %esp
movl entero(,1), %eax # I pass the direction of entero
# With numer, I use $numer
# and it is accepted (with numer(,1)
# it generates an error and
# is closed by windows
# But its value is still 200, not the
# new input from stdin.
pushl %eax
movl $string1, %eax # "%d"
push %eax
call _printf
addl $8, %esp
movl entero(,1), %eax
addl %eax, %eax # sum it by itself
pushl %eax # And print the result
# But I don't store it
# back to the variable
movl $string1, %eax
pushl %eax
call _printf
addl $8, %esp
mov $string, %ebx # I pass the string variable
push %ebx
movl $string3, %eax
push %eax
call _scanf # And read from stdin
addl $8, %esp
movl $string, %eax
push %eax
movl $string4, %eax
push %eax
call _printf # I display the whole string
# If you use a string with whitespaces
# you'll see that, as C, it's printed only
# till the last char before the space
# And that's what where stored in the
# string variable from input
addl $8, %esp
movl $1, %ebx # I pass the index I want to %ebx
mov string(,%ebx,1), %ecx # I pass to %ecx the
# value which in C would
# be denoted by string[1]
push %ecx
movl $string5, %eax # "%c\n\0"
push %eax
call _printf # I print the second char of string
addl $8, %esp
popa
movl $0, %eax
leave
ret
Regarding the objection by Per Westernak (Thank you!) You were right,=20
it worked fine till I used the last paragraph of code, there I had added=20
so many to %esp it returned access violation, I changed the numbers,=20
assuming that the functions printf and scanf had done yet the removal of=20
the returning address and restored and popped out its %ebp (Which is the=20
correct, %ebp is restored an popped out explicitly by the callee and the=20
return address is popped implicitly by ret, just as it was implicitly=20
pushed with call. I forgot this).
|