Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Parser #48

Merged
merged 14 commits into from
Jun 20, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions defs.inc
Original file line number Diff line number Diff line change
@@ -1,4 +1,12 @@

_blue:
.tib dq 1
.tib_len dd 1
.tib_in dd 1
.word_len db 1
.word rb 255
.mode db 1

_code_buffer:
.length = 4096
.base dq 1
Expand Down
4 changes: 4 additions & 0 deletions linux.inc
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,10 @@ PROT_RWX = PROT_RW or PROT_EXEC
MAP_ANONYMOUS = 32
MAP_PRIVATE = 2

STDIN_FILENO = 0
STDOUT_FILENO = 1
STDERR_FILENO = 2

;
; expects
; - buffer length in esi
Expand Down
59 changes: 59 additions & 0 deletions parser.inc
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@

;
; expects
; - properly configured _blue structure
;
parser_next_word:
mov [_blue.word_len], 0

mov ecx, [_blue.tib_len]
test ecx, ecx
jz .done

mov eax, [_blue.tib_in]
sub ecx, eax
jng .done

and ecx, 0xFF
push rcx

mov rsi, [_blue.tib]
add esi, eax
mov rdi, _blue.word

call _skip_ws

test ecx, ecx
jz .set_tib_in

.loop:
cmp byte [esi], 32
jle .loop_done

movsb

dec ecx
jnz .loop

.loop_done:
sub rdi, _blue.word
mov [_blue.word_len], dil

.set_tib_in:
pop rax
sub eax, ecx
add [_blue.tib_in], eax

.done:
ret

_skip_ws:
cmp byte [esi], 32
jg .done

inc rsi
dec ecx
jnz _skip_ws

.done:
ret
112 changes: 112 additions & 0 deletions parser_test.asm
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
format elf64 executable 3

macro tc2 word_in, word_len {
call parser_next_word

inc [test_num]
xor eax, eax
mov al, [_blue.word_len]
cmp al, word_len
jne failure

mov ecx, eax
mov eax, word_in
call check_word
}

macro tc1 tib, tib_len, word_in, word_len {
mov [_blue.tib], tib
mov [_blue.tib_len], tib_len
mov [_blue.tib_in], 0

tc2 word_in, word_len
}

segment readable writeable

include "defs.inc"

test_num db 1

segment readable executable

include "linux.inc"
include "parser.inc"

entry $
mov [test_num], 0

tc1 nothing, 0, 0, 0

tc1 space, 1, 0, 0
tc1 tab, 1, 0, 0
tc1 newline, 1, 0, 0
tc1 spaces, 2, 0, 0
tc1 ws_4, 4, 0, 0

tc1 six, 1, 0, 1
tc1 space_a, 2, 1, 1
tc1 a_space, 2, 0, 1
tc1 abc, 3, 0, 3
tc1 ws_abc_ws, 7, 2, 3

tc1 toks_2, 3, 0, 1
tc2 2, 1

tc1 toks_3, 20, 3, 4
tc2 9, 4
tc2 14, 6

xor edi, edi

exit:
mov eax, 60
syscall

failure:
mov dil, [test_num]
jmp exit

failure2:
mov dil, [test_num]
add dil, 100
jmp exit

;
; expects
; - word_len in ecx
; - word_in in al
;
check_word:
test cl, cl
jz .done

mov rsi, [_blue.tib]
add esi, eax
mov rdi, _blue.word

.loop:
cmpsb
jne failure2

dec ecx
jnz .loop

.done:
ret

segment readable

nothing db 0
space db 32
tab db 9
newline db 10
spaces db 32, 32
ws_4 db 32, 9, 10, 32
six db '6'
space_a db ' a'
a_space db 'a '
abc db 'abc'
ws_abc_ws db 10, 32, 'abc', 9, 10
toks_2 db 'a b'
toks_3 db ' some more tokens'
3 changes: 2 additions & 1 deletion test.mk
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@

TESTS := \
code_buffer_test \
parser_test \
elf_test \
elf_test_hello_world

$(TESTS):
echo "Testing $@... " && \
@echo "Testing $@... " && \
make WHAT=$@ compile run && \
rm -f $@ && \
echo ""
Expand Down
Loading