94 lines
1.7 KiB
ArmAsm
94 lines
1.7 KiB
ArmAsm
# hello.s
|
|
#
|
|
# Ask for the user's name, then print:
|
|
# Hello <name>
|
|
# five times.
|
|
|
|
.section .rodata
|
|
|
|
prompt:
|
|
.ascii "What is your name? "
|
|
prompt_end:
|
|
|
|
hello:
|
|
.ascii "Hello "
|
|
hello_end:
|
|
|
|
newline:
|
|
.byte 10 # ASCII newline: '\n'
|
|
|
|
|
|
.section .bss
|
|
|
|
.align 16
|
|
name_buf:
|
|
.skip 64 # Reserve 64 bytes for the name
|
|
|
|
|
|
.section .text
|
|
|
|
.global _start
|
|
|
|
_start:
|
|
# write(STDOUT, prompt, prompt_length)
|
|
mov $1, %rax # syscall 1: write
|
|
mov $1, %rdi # file descriptor 1: stdout
|
|
lea prompt(%rip), %rsi # address of prompt
|
|
mov $(prompt_end - prompt), %rdx
|
|
syscall
|
|
|
|
# read(STDIN, name_buf, 63)
|
|
xor %rax, %rax # syscall 0: read
|
|
xor %rdi, %rdi # file descriptor 0: stdin
|
|
lea name_buf(%rip), %rsi
|
|
mov $63, %rdx
|
|
syscall
|
|
|
|
# RAX contains the number of bytes read.
|
|
# Exit if read returned zero or an error.
|
|
test %rax, %rax
|
|
jle exit
|
|
|
|
# Save the length of the name in R12.
|
|
mov %rax, %r12
|
|
|
|
# Remove the trailing newline entered by the user.
|
|
lea name_buf(%rip), %rbx
|
|
cmpb $10, -1(%rbx,%r12)
|
|
jne repeat_setup
|
|
dec %r12
|
|
|
|
repeat_setup:
|
|
mov $5, %r13 # Loop counter
|
|
|
|
repeat_loop:
|
|
# Write "Hello "
|
|
mov $1, %rax
|
|
mov $1, %rdi
|
|
lea hello(%rip), %rsi
|
|
mov $(hello_end - hello), %rdx
|
|
syscall
|
|
|
|
# Write the user's name
|
|
mov $1, %rax
|
|
mov $1, %rdi
|
|
lea name_buf(%rip), %rsi
|
|
mov %r12, %rdx
|
|
syscall
|
|
|
|
# Write newline
|
|
mov $1, %rax
|
|
mov $1, %rdi
|
|
lea newline(%rip), %rsi
|
|
mov $1, %rdx
|
|
syscall
|
|
|
|
dec %r13
|
|
jne repeat_loop
|
|
|
|
exit:
|
|
# exit(0)
|
|
mov $60, %rax # syscall 60: exit
|
|
xor %rdi, %rdi # exit status 0
|
|
syscall
|