From 3ee67e335626610219a3c08ba38263547f5afff8 Mon Sep 17 00:00:00 2001 From: Ralph Ronnquist Date: Wed, 5 May 2021 14:00:22 +1000 Subject: [PATCH] reformat to 80 columns --- src/impl.asm | 36 ++++++++------ src/main.asm | 131 ++++++++++++++++++++++++++++++--------------------- src/uefi.asm | 55 ++++++++++++--------- 3 files changed, 130 insertions(+), 92 deletions(-) diff --git a/src/impl.asm b/src/impl.asm index 6267b3e..2e7a037 100644 --- a/src/impl.asm +++ b/src/impl.asm @@ -43,32 +43,35 @@ find: .loop: movzx rcx, byte [rsi + 8 + 1] ; Length of word being looked at cmp rcx, [.search_length] - jne .next ; If the words don't have the same length, we have the wrong word + jne .next ; If the words don't have the same length, we have the + ; wrong word ;; Otherwise, we need to compare strings - lea rdx, [rsi + 8 + 1 + 1] ; Location of character being compared in entry - mov rdi, [.search_buffer] ; Location of character being compared in search buffer + lea rdx, [rsi + 8 + 1 + 1] ; Location of character being compared in entry + mov rdi, [.search_buffer] ; Location of character being compared in + ; search buffer .compare_char: mov al, [rdx] mov ah, [rdi] cmp al, ah - jne .next ; They don't match; try again - inc rdx ; These characters match; look at the next ones + jne .next ; They don't match; try again + inc rdx ; These characters match; look at the + ; next ones inc rdi loop .compare_char - jmp .found ; They match! We are done. + jmp .found ; They match! We are done. .next: - mov rsi, [rsi] ; Look at the previous entry + mov rsi, [rsi] ; Look at the previous entry cmp rsi, 0 - jnz .loop ; If there is no previous word, exit and return 0 + jnz .loop ; If there is no previous word, exit and return 0 .found: ret -;; Read a word from a buffer. Returns the buffer without the word, as well as -;; the word that was read (including lengths). +;; Read a word from a buffer. Returns the buffer without the word, as +;; well as the word that was read (including lengths). ;; ;; Inputs: ;; * rsi = Input buffer @@ -88,13 +91,15 @@ pop_word: je .got_whitespace jmp .alpha .got_whitespace: - ;; The buffer starts with whitespace; discard the first character from the buffer. + ;; The buffer starts with whitespace; discard the first character + ;; from the buffer. inc rsi dec rcx jmp .skip_whitespace .alpha: - ;; We got a character that wasn't whitespace. Now read the actual word. + ;; We got a character that wasn't whitespace. Now read the actual + ;; word. mov rdi, rsi ; This is where the word starts mov rdx, 1 ; Length of word @@ -134,8 +139,8 @@ pop_word: parse_number: mov r8, 0 ; Result - ;; Add (10^(rcx-1) * parse_char(rdi[length - rcx])) to the accumulated value - ;; for each rcx. + ;; Add (10^(rcx-1) * parse_char(rdi[length - rcx])) to the + ;; accumulated value for each rcx. mov [.length], rcx .loop: ;; First, calcuate 10^(rcx - 1) @@ -162,7 +167,8 @@ parse_number: cmp rbx, 10 jae .error - ;; Multiply this value by rax to get (10^(rcx-1) * parse_char(rdi[length - rcx])), + ;; Multiply this value by rax to get + ;; (10^(rcx-1) * parse_char(rdi[length - rcx])) ;; then add this to the result. mul rbx diff --git a/src/main.asm b/src/main.asm index d1d89fb..3af5713 100644 --- a/src/main.asm +++ b/src/main.asm @@ -1,5 +1,6 @@ -;; The UEFI module defines the following functions. Each of these functions -;; preserve the value of RSI and RSP. They may use other registers as they like. +;; The UEFI module defines the following functions. Each of these +;; functions preserve the value of RSI and RSP. They may use other +;; registers as they like. ;; ;; os_initialize ;; Called at initialization. @@ -14,6 +15,7 @@ ;; ;; os_terminate ;; Shut down the system, returning the error code given in RAX. + include 'src/uefi.asm' ;; The code in this macro is placed at the end of each Forth word. When we are @@ -66,7 +68,8 @@ label: initial_latest_entry = label#_entry } -;; Define a Forth word that is implemented in assembly. See 'header' for details. +;; Define a Forth word that is implemented in assembly. See 'header' +;; for details. macro forth_asm label, name, immediate { header label, name, immediate dq .start @@ -79,7 +82,7 @@ include "impl.asm" ; Misc. subroutines include "bootstrap.asm" ; Forth words encoded in Assembly main: - cld ; Clear direction flag so LODSQ does the right thing. + cld ; Clear direction flag so LODSQ does the right thing. mov rbp, return_stack_top ; Initialize return stack call os_initialize @@ -89,12 +92,15 @@ main: program: dq MAIN -;; The codeword is the code that will be executed at the beginning of a forth -;; word. It needs to save the old RSI and update it to point to the next word to -;; execute. +;; The codeword is the code that will be executed at the beginning of +;; a forth word. It needs to save the old RSI and update it to point +;; to the next word to execute. header DOCOL, 'DOCOL' - pushr rsi ; Save old value of RSI on return stack; we will continue execution there after we are done executing this word - lea rsi, [rax + 8] ; RAX currently points to the address of the codeword, so we want to continue at RAX+8 + pushr rsi ; Save old value of RSI on return stack; we + ; will continue execution there after we are + ; done executing this word + lea rsi, [rax + 8] ; RAX currently points to the address of the + ; codeword, so we want to continue at RAX+8 next ; Execute word pointed to by RSI ;; This word is called at the end of a Forth definition. It just needs to @@ -103,16 +109,16 @@ forth_asm EXIT, 'EXIT' popr rsi next -;; LIT is a special word that reads the next "word pointer" and causes it to be -;; placed on the stack rather than executed. +;; LIT is a special word that reads the next "word pointer" and causes +;; it to be placed on the stack rather than executed. forth_asm LIT, 'LIT' lodsq push rax next -;; When LITSTRING is encountered while executing a word, it instead reads a -;; string from the definition of that word, and places that string on the stack -;; as (buffer, length). +;; When LITSTRING is encountered while executing a word, it instead +;; reads a string from the definition of that word, and places that +;; string on the stack as (buffer, length). forth_asm LITSTRING, 'LITSTRING' lodsb push rsi ; Buffer @@ -121,8 +127,9 @@ forth_asm LITSTRING, 'LITSTRING' add rsi, rax ; Skip over string before resuming execution next -;; Given a string (a pointer following by a size), return the location of the -;; dictionary entry for that word. If no such word exists, return 0. +;; Given a string (a pointer following by a size), return the location +;; of the dictionary entry for that word. If no such word exists, +;; return 0. forth_asm FIND, 'FIND' mov [.rsi], rsi @@ -139,8 +146,8 @@ forth_asm FIND, 'FIND' mov rsi, [.rsi] next -;; Given an entry in the dictionary, return a pointer to the codeword of that -;; entry. +;; Given an entry in the dictionary, return a pointer to the codeword +;; of that entry. forth_asm TCFA, '>CFA' pop rax add rax, 8 + 1 ; [rax] = length of name @@ -150,22 +157,25 @@ forth_asm TCFA, '>CFA' push rax next -;; BRANCH is the fundamental mechanism for branching. BRANCH reads the next word -;; as a signed integer literal and jumps by that offset. +;; BRANCH is the fundamental mechanism for branching. BRANCH reads the +;; next word as a signed integer literal and jumps by that offset. + forth_asm BRANCH, 'BRANCH' - add rsi, [rsi] ; [RSI], which is the next word, contains the offset; we add this to the instruction pointer. + add rsi, [rsi] ; [RSI], which is the next word, contains the offset + ; we add this to the instruction pointer. next ; Then, we can just continue execution as normal -;; 0BRANCH is like BRANCH, but it jumps only if the top of the stack is zero. +;; 0BRANCH is like BRANCH, but it jumps only if the top of the stack +;; is zero. forth_asm ZBRANCH, '0BRANCH' - ;; Compare top of stack to see if we should branch pop rax - cmp rax, 0 + cmp rax, 0 ; Compare top of stack to see if we should branch jnz .dont_branch .do_branch: jmp BRANCH.start .dont_branch: - add rsi, 8 ; We need to skip over the next word, which contains the offset. + add rsi, 8 ; We need to skip over the next word, which contains + ; the offset. next ;; Duplicate the top of the stack. @@ -192,10 +202,10 @@ forth_asm EMIT, 'EMIT' popr rsi next -;; Read a single character from the current input stream. Usually, this will wait -;; for the user to press a key, and then return the corresponding character. When -;; reading from a special buffer, it will instead return the next characater from -;; that buffer. +;; Read a single character from the current input stream. Usually, +;; this will wait for the user to press a key, and then return the +;; corresponding character. When reading from a special buffer, it +;; will instead return the next characater from that buffer. ;; ;; The ASCII character code is placed on the stack. forth_asm KEY, 'KEY' @@ -222,8 +232,8 @@ forth_asm KEY, 'KEY' dec [input_buffer_length] ret -;; Read a word and push it onto the stack as a pointer and a size. The pointer -;; is valid until the next call to READ_WORD. +;; Read a word and push it onto the stack as a pointer and a size. The +;; pointer is valid until the next call to READ_WORD. forth_asm READ_WORD, 'READ-WORD' push rsi .skip_whitespace: @@ -260,8 +270,8 @@ forth_asm READ_WORD, 'READ-WORD' next -;; Takes a string on the stack and replaces it with the decimal number that the -;; string represents. +;; Takes a string on the stack and replaces it with the decimal number +;; that the string represents. forth_asm PARSE_NUMBER, 'PARSE-NUMBER' pop rcx ; Length pop rdi ; String pointer @@ -419,8 +429,8 @@ forth_asm PLUS, '+' push rax next -;; Calculate difference between two integers on the stack. The second number is -;; subtracted from the first. +;; Calculate difference between two integers on the stack. The second +;; number is subtracted from the first. forth_asm MINUS, '-' pop rax pop rbx @@ -439,9 +449,10 @@ forth_asm TIMESMOD, '/MOD' push rdx ; a % b next -;; Read input until next " character is found. Push a string containing the -;; input on the stack as (buffer length). Note that the buffer is only valid -;; until the next call to S" and that no more than 255 characters can be read. +;; Read input until next " character is found. Push a string +;; containing the input on the stack as (buffer length). Note that the +;; buffer is only valid until the next call to S" and that no more +;; than 255 characters can be read. forth_asm READ_STRING, 'S"' ;; If the input buffer is set, we should read from there instead. cmp [input_buffer], 0 @@ -504,11 +515,12 @@ read_string_buffer: next -;; CREATE inserts a new header in the dictionary, and updates LATEST so that it -;; points to the header. To compile a word, the user can then call ',' to -;; continue to append data after the header. +;; CREATE inserts a new header in the dictionary, and updates LATEST +;; so that it points to the header. To compile a word, the user can +;; then call ',' to continue to append data after the header. ;; -;; It takes the name of the word as a string (address length) on the stack. +;; It takes the name of the word as a string (address length) on the +;; stack. forth_asm CREATE, 'CREATE' pop rcx ; Word string length pop rdx ; Word string pointer @@ -583,6 +595,16 @@ forth EFI_SYSTEM_TABLE_CONSTANT, 'SystemTable' dq LIT, system_table, GET dq EXIT +forth_asm EFICALL1, 'EFICALL1' + pop rax ; function pointer + pop rcx ; 1st argument + + sub rsp, 32 + call rax + add rsp, 32 + + next + forth_asm EFICALL2, 'EFICALL2' pop rax ; function pointer pop rdx ; 2nd argument @@ -669,18 +691,18 @@ forth INPUT_LENGTH, 'INPUT-LENGTH' section '.data' readable writable -;; The LATEST variable holds a pointer to the word that was last added to the -;; dictionary. This pointer is updated as new words are added, and its value is -;; used by FIND to look up words. +;; The LATEST variable holds a pointer to the word that was last added +;; to the dictionary. This pointer is updated as new words are added, +;; and its value is used by FIND to look up words. latest_entry dq initial_latest_entry -;; The STATE variable is 0 when the interpreter is executing, and non-zero when -;; it is compiling. +;; The STATE variable is 0 when the interpreter is executing, and +;; non-zero when it is compiling. var_STATE dq 0 -;; The interpreter can read either from standard input or from a buffer. When -;; input-buffer is set (non-null), words like READ-WORD and S" will use this -;; buffer instead of reading user input. +;; The interpreter can read either from standard input or from a +;; buffer. When input-buffer is set (non-null), words like READ-WORD +;; and S" will use this buffer instead of reading user input. input_buffer dq 0 input_buffer_length dq 0 @@ -694,7 +716,7 @@ READ_STRING.buffer rb $FF READ_STRING.length dq ? DOTU.chars db '0123456789ABCDEF' -DOTU.buffer rq 16 ; 64-bit number has no more than 16 digits in hex +DOTU.buffer rq 16 ; 64-bit number has no more than 16 digits in hex DOTU.rbuffer rq 16 DOTU.length dq ? DOTU.printed_length dq ? @@ -712,9 +734,10 @@ here_top rq $4000 rq $2000 return_stack_top: -;; We store some Forth code in sys.f that defined common words that the user -;; would expect to have available at startup. To execute these words, we just -;; include the file directly in the binary, and then interpret it at startup. +;; We store some Forth code in sys.f that defined common words that +;; the user would expect to have available at startup. To execute +;; these words, we just include the file directly in the binary, and +;; then interpret it at startup. sysf: file '../init/sys.f' file '../init/uefi.f' diff --git a/src/uefi.asm b/src/uefi.asm index 16fc85d..aca71de 100644 --- a/src/uefi.asm +++ b/src/uefi.asm @@ -1,5 +1,3 @@ -;; vim: syntax=fasm - format pe64 dll efi entry main @@ -27,11 +25,16 @@ struc EFI_SYSTEM_TABLE { .FirmwareVendor dq ? ; CHAR16* .FirmwareRevision dd ? ; UINT32 align 8 - .ConsoleInHandle dq ? ; EFI_HANDLE - .ConIn dq ? ; EFI_SIMPLE_TEXT_INPUT_PROTOCOL* - .ConsoleOutHandle dq ? ; EFI_HANDLE - .ConOut dq ? ; EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL* - ; ... + .ConsoleInHandle dq ? ; EFI_HANDLE + .ConIn dq ? ; EFI_SIMPLE_TEXT_INPUT_PROTOCOL* + .ConsoleOutHandle dq ? ; EFI_HANDLE + .ConOut dq ? ; EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL* + .StandardErroHandle dq ? ; EFI_HANDLE + .StdErr dq ? ; EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL* + .RuntimeServices dq ? ; EFI_RUNTIME_SERVICES* + .BootServices dq ? ; EFI_BOOT_SERVICES* + .NumberOfTableEntries dq ? ; UINTN (native width!!) + .ConfigurationTable dq ? ; EFI_CONFIGURATION_TABLE* } struct EFI_SYSTEM_TABLE @@ -66,13 +69,15 @@ os_initialize: ret os_print_string: - ;; We take an input string of bytes without any terminator. We need to turn - ;; this string into a string of words, terminated by a null character. + ;; We take an input string of bytes without any terminator. We need + ;; to turn this string into a string of words, terminated by a null + ;; character. mov rdi, .output_buffer ; Current location in output string .copy_byte: - ;; When there are no characters left in the input string, we are done. + ;; When there are no characters left in the input string, we are + ;; done. cmp rdx, 0 je .done @@ -100,14 +105,14 @@ os_print_string: mov byte [rdi], al inc rdi - ;; The output string has words rather than bytes for charactesr, so we need - ;; to add an extra zero: + ;; The output string has words rather than bytes for charactesr, so + ;; we need to add an extra zero: mov byte [rdi], 0 inc rdi .pop: - ;; We finished copying character to output string, so pop it from the input - ;; string. + ;; We finished copying character to output string, so pop it from + ;; the input string. inc rcx dec rdx @@ -116,13 +121,15 @@ os_print_string: ;; Append a final null-word: mov word [rdi], 0 - ; At this point we have our null-terminated word-string at .output_buffer. Now - ; we just need to print it. + ; At this point we have our null-terminated word-string at + ; .output_buffer. Now we just need to print it. - mov rcx, [system_table] ; EFI_SYSTEM_TABLE* rcx - mov rcx, [rcx + EFI_SYSTEM_TABLE.ConOut] ; EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL* rcx + mov rcx, [system_table] ; EFI_SYSTEM_TABLE* rcx + mov rcx, [rcx + EFI_SYSTEM_TABLE.ConOut] + ; EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL* rcx mov rdx, .output_buffer - mov rbx, [rcx + EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL.OutputString] ; EFI_TEXT_STRING rbx + mov rbx, [rcx + EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL.OutputString] + ; EFI_TEXT_STRING rbx sub rsp, 32 call rbx add rsp, 32 @@ -130,10 +137,12 @@ os_print_string: os_read_char: .read_key: - mov rcx, [system_table] ; EFI_SYSTEM_TABLE* rcx - mov rcx, [rcx + EFI_SYSTEM_TABLE.ConIn] ; EFI_SIMPLE_TEXT_INPUT_PROTOCOL* rcx - mov rbx, [rcx + EFI_SIMPLE_TEXT_INPUT_PROTOCOL.ReadKeyStroke] ; EFI_INPUT_READ_KEY rbx - mov rdx, input_key ; EFI_INPUT_KEY* rdx + mov rcx, [system_table] ; EFI_SYSTEM_TABLE* rcx + mov rcx, [rcx + EFI_SYSTEM_TABLE.ConIn] + ; EFI_SIMPLE_TEXT_INPUT_PROTOCOL* rcx + mov rbx, [rcx + EFI_SIMPLE_TEXT_INPUT_PROTOCOL.ReadKeyStroke] + ; EFI_INPUT_READ_KEY rbx + mov rdx, input_key ; EFI_INPUT_KEY* rdx sub rsp, 32 call rbx add rsp, 32 -- 2.39.2