Skip to content

Instantly share code, notes, and snippets.

@felixge

felixge/wc.asm

Created Feb 20, 2020
Embed
What would you like to do?
global main
extern printf
section .text
main:
sub rdi, 1 ; argc includes program name, so substract 1 to get arg count
cmp rdi, 1 ; check if we got exactly 1 arg
jne bad_arg_count ; if not, jump to bad_arg_count
mov r15, [rsi+8] ; main's argv[1]
mov r14, 0 ; index (also byte count)
mov r13, 0 ; line count
mov r12, 0 ; word count
mov r11, 0 ; wasSpace
loop:
cmp byte [r15+r14], 32 ; is space
je space
cmp byte [r15+r14], 10 ; is newline
je newline
jmp other_char
newline:
add r13, 1
space:
cmp r11, 0
jne continue
mov r11, 1 ; wasSpace = true
add r12, 1 ; inc word count
jmp continue
other_char:
mov r11, 0
continue:
add r14, 1 ; inc byte count
cmp byte [r15+r14], 0
jne loop
finalize:
cmp r11, 1 ; was last char a space?
je print_result ; if yes, print_result
add r12, 1 ; otherwise increment word count by 1
print_result:
mov rdi, format; arg1
mov rsi, r13 ; arg2 = line count
mov rdx, r12 ; arg3 = word count
mov rcx, r14 ; arg4 = byte count
mov rax, 0 ; 0 floating point params to variadic printf function
call printf
mov rax, 0 ; exit code 0
ret
; print error message
bad_arg_count:
mov rsi, rdi ; arg 2
mov rdi, args_str ; arg1
mov rax, 0 ; 0 floating point params to variadic printf function
call printf
mov rax, 1 ; exit code 1
ret
format:
db "%d %d %d", 10, 0 ; world, line, byte count
args_str:
db "expected 1 argument, got %d", 10, 0
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment