diff --git a/defs.inc b/defs.inc index 586023f..f65259f 100644 --- a/defs.inc +++ b/defs.inc @@ -12,3 +12,12 @@ _code_buffer: .base dq 1 .here dq 1 .entry dd 1 + +_dictionary: + .prev_word_offset = 8 + .entry_code_offset = 16 + .word_offset = 24 + .length = 4096 + .base dq 1 + .here dq 1 + .latest dq 1 diff --git a/dictionary.inc b/dictionary.inc new file mode 100644 index 0000000..c72e975 --- /dev/null +++ b/dictionary.inc @@ -0,0 +1,105 @@ +; +; entry: +; +; 08 - 1 byte flags +; - 1 byte word len +; - 6 bytes reserved +; 08 - prev addr +; 08 - code addr +; ?? - word chars (padded to dq) +; ?? - stack effects +; + +DE_HIDDEN = 1 +DE_IMMEDIATE = 2 + +_core_words: + .b_comma: + db DE_IMMEDIATE + db 2 + dw 0 + dd 0 + dq 0 + dq _core_code.b_comma + dq 'b,' + dq 0 ; TODO: stack effects (( b al -- | rdi )) + + .latest: + .d_comma: + db DE_IMMEDIATE + db 2 + dw 0 + dd 0 + dq .b_comma + dq _core_code.d_comma + dq 'd,' + dq 0 ; TODO: stack effects (( d ax -- | rdi )) + +dictionary_init: + mov esi, _dictionary.length + mov edx, PROT_RW + call mmap_buffer + + mov rdi, _dictionary.base + stosq + stosq + + mov [_dictionary.latest], _core_words.latest + + ret + +dictionary_deinit: + mov esi, _dictionary.length + mov rdi, [_dictionary.base] + mov eax, SYS_MUNMAP + syscall + + ret + +; +; expects +; - properly configured blue structure with non zero word len +; +dictionary_find: + mov rdi, [_dictionary.latest] + + .find: + push rdi + + test byte [edi], DE_HIDDEN + jnz .next + + inc edi + mov rsi, _blue.word_len + mov ecx, [esi] + + lodsb + cmp al, byte [edi] + jne .next + + add edi, _dictionary.word_offset - 1 + + .check_word: + lodsb + cmp al, byte [edi] + jne .next + + inc edi + dec ecx + js .check_word + + pop rax + jmp .done + + .next: + pop rdi + add edi, _dictionary.prev_word_offset + mov rdi, [rdi] + + test rdi, rdi + jnz .find + + xor eax, eax + + .done: + ret diff --git a/dictionary_test.asm b/dictionary_test.asm new file mode 100644 index 0000000..4d98e74 --- /dev/null +++ b/dictionary_test.asm @@ -0,0 +1,64 @@ +format elf64 executable 3 + +macro tc1 tib, tib_len, expected { + mov [_blue.tib], tib + mov [_blue.tib_len], tib_len + mov [_blue.tib_in], 0 + + call parser_next_word + call dictionary_find + + inc [test_num] + cmp rax, expected + jne failure +} + +segment readable writeable + +include "defs.inc" + +test_num db 1 + +segment readable executable + +include "linux.inc" +include "code_buffer.inc" +include "dictionary.inc" +include "parser.inc" + +entry $ + mov [test_num], 0 + + call dictionary_init + + inc [test_num] + mov rax, [_dictionary.base] + cmp rax, [_dictionary.here] + jne failure + + inc [test_num] + mov rax, [_dictionary.latest] + cmp rax, _core_words.latest + jne failure + + tc1 unknown, 4, 0 + tc1 d_comma, 2, _core_words.d_comma + tc1 b_comma, 2, _core_words.b_comma + + call dictionary_deinit + + xor edi, edi + +exit: + mov eax, 60 + syscall + +failure: + mov dil, [test_num] + jmp exit + +segment readable + +unknown db '!@#$' +b_comma db 'b,' +d_comma db 'd,' diff --git a/scratch/dictionary.inc b/scratch/dictionary.inc deleted file mode 100644 index c212337..0000000 --- a/scratch/dictionary.inc +++ /dev/null @@ -1,49 +0,0 @@ -; -; entry: -; -; 08 - 1 byte flags -; - 1 byte word length -; - 6 bytes first chars -; 08 - prev addr -; 08 - code addr -; 08 - 1 byte length of remaining word chars -; - 7 bytes reserved -; ?? - remaining word chars -; ?? - stack effects -; - -DE_VIS = 1 -DE_IMMED = 2 - -_core_words: - .b_comma: - db DE_VIS or DE_IMMED, 2, 'b,', 0, 0, 0, 0 - dq 0 - dq _core_code.b_comma - dq 0 - dq 0 ; TODO: stack effects (( b al -- | rdi )) - - .latest: - .d_comma: - db DE_VIS or DE_IMMED, 2, 'd,', 0, 0, 0, 0 - dq .b_comma - dq _core_code.d_comma - dq 0 - dq 0 ; TODO: stack effects (( d ax -- | rdi )) - -dictionary: - .entry_code_offset = 16 - - .init: - mmap_buffer _dictionary.length, PROT_RW - - mov [_dictionary.base], rax - mov [_dictionary.here], rax - mov [_dictionary.latest], _core_words.latest - ret - - .deinit: - mov esi, _dictionary.length - mov rdi, [_dictionary.base] - call mmap.unmap - ret diff --git a/scratch/dictionary_test.inc b/scratch/dictionary_test.inc deleted file mode 100644 index 500fe5b..0000000 --- a/scratch/dictionary_test.inc +++ /dev/null @@ -1,23 +0,0 @@ - -dictionary_test: - call dictionary.init - - ; test dictionary init's properly - - mov edi, 1 - mov rax, [_dictionary.base] - cmp rax, [_dictionary.here] - jne .fail - - mov edi, 2 - mov rax, [_dictionary.latest] - cmp rax, _core_words.latest - jne .fail - - call dictionary.deinit - ret - - .fail: - mov eax, 60 - syscall - ret diff --git a/test.mk b/test.mk index c0abcc3..eb44e46 100644 --- a/test.mk +++ b/test.mk @@ -2,6 +2,7 @@ TESTS := \ code_buffer_test \ parser_test \ + dictionary_test \ elf_test \ elf_test_hello_world