NASM Echo Program (64 bit Linux)

Reading time ~2 minutes

NASM Echo Program

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
%define BUFFSIZE    256
global _start

section .data
error   db  "Please enter one or less parameters.", 0xA, 0x0
errlen  equ     $-error

section .bss
buffer  resb    BUFFSIZE

section .text
_start:
    ; test for arguments
    cmp qword[rsp], 0x2
stop1:
    jl  _cliread
    jg  _error

    ; calculate length of string
    mov     rdi, [rsp+16]   ; destination index
    xor     rcx, rcx        ; rcx = -1
    not     rcx             ; rcx = -1
    xor     al,al
    cld                     ; process String from lowest to highest address
                            ; (clear diretion flag)
    ;SCASB: Compare AL with byte at RDI then set status flags.
    ;REPNZ: Repeats a string instruction RCX times or until ZF = 1
    repnz   scasb           ; get the string length (dec rcx through NUL)
    not     rcx             ; rev all bits of negative results in absolute value
    dec     rcx             ; -1 to skip the null-terminator, rcx contains
                            ; length
    ; initialize source for write
    mov     rsi, [rsp+16]   ; read from [rsp+16]
    mov     rdx, rcx        ; read rcx bytes
    jmp     _cliwrite

_cliread:
    ; read (0) from stdin (0)
    mov rax, 0
    mov rdi, 0
    mov rsi, buffer
    mov rdx, BUFFSIZE
    syscall
    ; initialize source for write
    mov rsi, buffer
    mov rdx, BUFFSIZE
    jmp _cliwrite

_error:
    ; initialize source for write
    mov rsi, error
    mov rdx, errlen

_cliwrite:
    ; write (1) to stdout (1)
    mov rax, 1
    mov rdi, 1
    syscall

_end:
    mov rax, 60
    mov rdi, 1
    syscall