count words
This commit is contained in:
parent
00bd026d74
commit
980b66cae9
@ -1,9 +1,16 @@
|
|||||||
SRC := asem.s
|
SRCDIR := src
|
||||||
|
SRC := $(addprefix $(SRCDIR)/, $(addsuffix .s, asem balloc split))
|
||||||
|
|
||||||
OBJDIR := obj
|
OBJDIR := obj
|
||||||
OBJ := $(OBJDIR)/$(SRC:.s=.o)
|
OBJ := $(addprefix $(OBJDIR)/, $(notdir $(SRC:.s=.o)))
|
||||||
|
|
||||||
all:
|
$(shell mkdir -p $(OBJDIR))
|
||||||
nasm -felf64 -g $(SRC) -o $(OBJ)
|
|
||||||
|
all: $(OBJ)
|
||||||
ld -o debug $(OBJ) -nostdlib -static
|
ld -o debug $(OBJ) -nostdlib -static
|
||||||
|
|
||||||
|
$(OBJDIR)/%.o: $(SRCDIR)/%.s
|
||||||
|
nasm -felf64 -g $< -o $@
|
||||||
|
|
||||||
|
clean:
|
||||||
|
rm -rf $(OBJDIR) debug
|
||||||
|
|||||||
49
lang/asem.s
49
lang/asem.s
@ -1,49 +0,0 @@
|
|||||||
%define DEF_BUFFER_LEN 4096
|
|
||||||
%define INPUT_LENGTH 64
|
|
||||||
|
|
||||||
; rax -- syscall
|
|
||||||
|
|
||||||
; type widths
|
|
||||||
|
|
||||||
section .data
|
|
||||||
message: db "Hello World!", 0xA, 0 ; hello
|
|
||||||
message_length: equ $-message
|
|
||||||
|
|
||||||
section .bss
|
|
||||||
arr: resb DEF_BUFFER_LEN
|
|
||||||
|
|
||||||
section .text
|
|
||||||
global _start
|
|
||||||
|
|
||||||
print_string:
|
|
||||||
push rbp
|
|
||||||
push rdx
|
|
||||||
mov rbp, rsp ; set up stack frame
|
|
||||||
|
|
||||||
mov rax, 1 ; sys_write
|
|
||||||
|
|
||||||
pop rdx
|
|
||||||
pop rbp
|
|
||||||
|
|
||||||
exit:
|
|
||||||
mov rax, 60
|
|
||||||
syscall
|
|
||||||
|
|
||||||
strlen:
|
|
||||||
push rcx
|
|
||||||
xor rcx, rcx
|
|
||||||
.loop:
|
|
||||||
cmp byte [rdi + rcx], 0
|
|
||||||
jz .done
|
|
||||||
inc rcx
|
|
||||||
jmp .loop
|
|
||||||
.done:
|
|
||||||
mov rax, rcx
|
|
||||||
pop rcx
|
|
||||||
ret
|
|
||||||
|
|
||||||
_start:
|
|
||||||
mov rdi, message ; prepare first arg -> string addr to rdi
|
|
||||||
call strlen
|
|
||||||
mov rdi, rax
|
|
||||||
call exit
|
|
||||||
BIN
lang/debug
BIN
lang/debug
Binary file not shown.
BIN
lang/obj/asem.o
BIN
lang/obj/asem.o
Binary file not shown.
BIN
lang/obj/balloc.o
Normal file
BIN
lang/obj/balloc.o
Normal file
Binary file not shown.
BIN
lang/obj/split.o
Normal file
BIN
lang/obj/split.o
Normal file
Binary file not shown.
100
lang/src/asem.s
Normal file
100
lang/src/asem.s
Normal file
@ -0,0 +1,100 @@
|
|||||||
|
%define DEF_BUFFER_LEN 4096
|
||||||
|
%define INPUT_LENGTH 64
|
||||||
|
|
||||||
|
extern split
|
||||||
|
|
||||||
|
section .data
|
||||||
|
message: db "Hello World!", 0xA, 0
|
||||||
|
message_length: equ $-message
|
||||||
|
filepath: db "./test.c"
|
||||||
|
|
||||||
|
section .bss
|
||||||
|
file_content_buffer: resb DEF_BUFFER_LEN
|
||||||
|
|
||||||
|
section .text
|
||||||
|
global _start
|
||||||
|
|
||||||
|
open_file:
|
||||||
|
mov rax, 2 ; sys_open
|
||||||
|
|
||||||
|
syscall
|
||||||
|
ret
|
||||||
|
|
||||||
|
close_file:
|
||||||
|
mov rax, 3 ; sys_close
|
||||||
|
|
||||||
|
syscall
|
||||||
|
ret
|
||||||
|
|
||||||
|
read_file_bytes: ; read(RDI: int fd, RSI: char *buffer, RDX: size_t size)
|
||||||
|
mov rax, 0 ; sys_read
|
||||||
|
syscall ;
|
||||||
|
ret
|
||||||
|
|
||||||
|
print_string: ; print_string(RDI: char *string)
|
||||||
|
call strlen
|
||||||
|
|
||||||
|
mov rdx, rax ; string length
|
||||||
|
|
||||||
|
mov rsi, rdi
|
||||||
|
mov rdi, 1 ; stdout
|
||||||
|
mov rax, 1 ; sys_write
|
||||||
|
syscall
|
||||||
|
|
||||||
|
ret
|
||||||
|
|
||||||
|
exit:
|
||||||
|
mov rax, 60
|
||||||
|
syscall
|
||||||
|
|
||||||
|
strlen: ; strlen(RDI: char *str)
|
||||||
|
push rcx ; save counter
|
||||||
|
xor rcx, rcx
|
||||||
|
.loop: ; loop until '\0' character
|
||||||
|
cmp byte [rdi + rcx], 0
|
||||||
|
jz .done
|
||||||
|
inc rcx
|
||||||
|
jmp .loop
|
||||||
|
.done:
|
||||||
|
mov rax, rcx ; mov return value to rax
|
||||||
|
pop rcx ; restore counter
|
||||||
|
ret
|
||||||
|
|
||||||
|
_start:
|
||||||
|
mov rdi, message ; prepare first arg -> string addr to rdi
|
||||||
|
call print_string
|
||||||
|
|
||||||
|
mov rdi, rax
|
||||||
|
push rax ; save rax
|
||||||
|
push rdi ; save rdi since arg comes into it
|
||||||
|
|
||||||
|
mov rdi, filepath ; filepath for open call
|
||||||
|
mov rsi, 0 ; O_RDONLY flag
|
||||||
|
call open_file
|
||||||
|
|
||||||
|
mov rbx, rax ; mov new fd to rbx
|
||||||
|
|
||||||
|
mov rdi, rbx ; first arg: mov fd to rdi for read call
|
||||||
|
mov rsi, file_content_buffer ; 2nd arg: buffer
|
||||||
|
mov rdx, 15 ; 3rd arg: read len
|
||||||
|
|
||||||
|
call read_file_bytes
|
||||||
|
mov byte [file_content_buffer + 15], 0xA ; newline
|
||||||
|
mov byte [file_content_buffer + 16], 0x0 ; 0 terminate string
|
||||||
|
|
||||||
|
push rdi ; save fd
|
||||||
|
mov rdi, rsi ; stdout fd
|
||||||
|
|
||||||
|
call print_string
|
||||||
|
pop rdi ; restore fd
|
||||||
|
|
||||||
|
call close_file
|
||||||
|
|
||||||
|
mov rdi, rsi
|
||||||
|
mov rsi, 0x20 ; ' ' space character
|
||||||
|
call split
|
||||||
|
|
||||||
|
.exit_early:
|
||||||
|
mov rdi, rax
|
||||||
|
|
||||||
|
call exit
|
||||||
26
lang/src/balloc.s
Normal file
26
lang/src/balloc.s
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
global balloc
|
||||||
|
|
||||||
|
brk_find_break: ; RAX: long brk(0)
|
||||||
|
mov rdi, 0x0
|
||||||
|
mov rax, 0xC ; sys_brk
|
||||||
|
syscall
|
||||||
|
ret
|
||||||
|
|
||||||
|
balloc: ; RAX: long basic_malloc(RDI: size_t n, RSI void **heap_begin_ptr)
|
||||||
|
cmp dword [rsi], 0 ; check if heap_begin_ptr exist
|
||||||
|
jne .allocate ; allocate normally if exists
|
||||||
|
|
||||||
|
push rdi
|
||||||
|
|
||||||
|
call brk_find_break
|
||||||
|
|
||||||
|
mov qword [rsi], rax ; get heap beginning
|
||||||
|
pop rdi
|
||||||
|
|
||||||
|
.allocate:
|
||||||
|
mov rax, qword [rsi]
|
||||||
|
add rdi, rax
|
||||||
|
mov rax, 0xC ; sys_brk
|
||||||
|
|
||||||
|
syscall
|
||||||
|
ret
|
||||||
43
lang/src/split.s
Normal file
43
lang/src/split.s
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
global split ; export split
|
||||||
|
|
||||||
|
section .text
|
||||||
|
|
||||||
|
count_splits: ; RAX: int count_splits(RDI: char *, RSI: int c)
|
||||||
|
push rbx
|
||||||
|
xor rcx, rcx
|
||||||
|
xor rbx, rbx
|
||||||
|
.loop:
|
||||||
|
cmp byte [rdi + rcx], 0
|
||||||
|
jz .done
|
||||||
|
cmp byte [rdi + rcx], sil
|
||||||
|
jne .skip
|
||||||
|
inc rbx
|
||||||
|
.skip:
|
||||||
|
inc rcx
|
||||||
|
jmp .loop
|
||||||
|
.done:
|
||||||
|
mov rax, rbx
|
||||||
|
pop rbx
|
||||||
|
ret
|
||||||
|
|
||||||
|
split: ; RAX: char ** split(RDI: char *str, RSI: int c)
|
||||||
|
push rbp
|
||||||
|
mov rbp, rsp ; save base pointer
|
||||||
|
|
||||||
|
; int count = [ rbp - 4 ]
|
||||||
|
|
||||||
|
sub rsp, 4 ; allocate local vars
|
||||||
|
|
||||||
|
call count_splits
|
||||||
|
|
||||||
|
mov rsp, rbp
|
||||||
|
pop rbp
|
||||||
|
|
||||||
|
ret
|
||||||
|
|
||||||
|
; count = count_splits()
|
||||||
|
mov [rbp - 4], rax
|
||||||
|
|
||||||
|
pop rbp
|
||||||
|
|
||||||
|
ret
|
||||||
Loading…
x
Reference in New Issue
Block a user