commit a51e3023252990a63e7edd8c406b46abc739a307
parent 2b483904003bbec46c3ce450406f96edefe40fe7
Author: Christian Ermann <christianermann@gmail.com>
Date: Sun, 17 Nov 2024 16:53:24 -0800
Store top of stack in 'w' register
Diffstat:
| M | forth.s | | | 327 | +++++++++++++++++++++++++++++++++---------------------------------------------- |
1 file changed, 138 insertions(+), 189 deletions(-)
diff --git a/forth.s b/forth.s
@@ -34,13 +34,13 @@
.endm
.macro push_addr addr
- la w, version_string
push w
+ la w, \addr
.endm
.macro push_imm imm
- li w, \imm
push w
+ li w, \imm
.endm
.macro push reg
@@ -150,13 +150,14 @@ _\label:
.endm
dovar:
- push ra
+ push w
+ mv w, ra
pop_ret ra
ret
docon:
- load_cell w, 0(ra)
push w
+ load_cell w, 0(ra)
pop_ret ra
ret
@@ -213,30 +214,28 @@ defvar "source-id", source_id, 0x965ED1E2
# -----------------------------------------------------------------------------
defcode "type", type, 0x5127F14D
- pop a1 # length
- pop a0 # address
+ mv x, w
+ pop w
push_ret ra
jal uart_put_string
pop_ret ra
+ pop w
next
defcode "emit", emit, 0x2D88474A
- pop a0
jal uart_put_char
+ pop w
next
defcode "key", key, 0x6815C86C
jal uart_get_char
- push a0
next
defcode "accept", accept, 0x08247E29
- pop w # max len
pop x # address
push_ret ra
jal accept_impl
pop_ret ra
- push w # recv'd len
next
accept_impl:
@@ -308,20 +307,20 @@ defword "source", source, 0x1BCF29D8
defcode "tib", tib, 0xC90B0194
# ( -- addr len )
+ push w
la w, _tib
push w
la w, _tib_len
load_cell w, 0(w)
- push w
next
defcode "fib", fib, 0xBCE49236
# ( -- addr len )
+ push w
la w, _fib
push w
la w, _fib_len
load_cell w, 0(w)
- push w
next
defword "skip-while", skip_while, 0xBBFD4B86
@@ -413,8 +412,8 @@ defword "parse-word", parse_word, 0xB218226F
exit
defcode ">number", to_number, 0x2F770E4C
- pop x # word len
- pop w # word addr
+ mv x, w
+ pop w
mv y, zero # initial value
mv s3, zero # sign flag
la s4, _base
@@ -464,13 +463,11 @@ _to_number_sign:
_to_number_done:
push y
- push x
+ mv w, x
next
defcode "word>hash", word_to_hash, 0x50E0A245
- pop w # word address
load_cell w, hash_offset(w)
- push w # word hash
next
defword "find", find, 0xBDF0855A
@@ -506,67 +503,66 @@ _find_next_word:
.int _find_loop
defcode ">cfa", to_cfa, 0x8CAC3233
- pop w
addi w, w, code_offset
- push w
next
defcode "execute", execute, 0xA01E3D98
- pop w
load_cell x, 0(w)
+ pop w
jr x
# 'next' should be called by the executed word
defword "interpret", interpret, 0x1F98C57A
_interpret_start:
jal parse_word
- load_cell w, 0(psp) # dup, ?branch
beqz w, _interpret_parse_area_empty
jal two_dup
jal find
- load_cell w, 0(psp) # dup, ?branch
beqz w, _interpret_word_not_found
+_interpret_word_found:
addi psp, psp, 2 * cell # nip, nip
- store_cell w, 0(psp)
- jal to_cfa
- la w, _state # compiling? ?branch
+ addi w, w, code_offset
load_cell w, 0(w)
- beqz w, _interpret_execute_word
- load_cell w, 0(psp) # dup immediate? 0= branch?
- addi w, w, flag_offset - code_offset
- lb w, 0(w)
- andi w, w, flag_immediate
- bnez w, _interpret_execute_word
+ # compiling?
+ la x, _state
+ load_cell x, 0(x)
+ beqz x, _interpret_execute_word
+ # immediate?
+ addi x, w, flag_offset - code_offset
+ lb x, 0(x)
+ andi x, x, flag_immediate
+ bnez x, _interpret_execute_word
_interpret_compile_word:
- jal fetch
jal jal_to
jal comma
j _interpret_start
_interpret_execute_word:
- jal execute
- jal branch
- .int _interpret_start
+ mv x, w
+ pop w
+ jalr x
+ j _interpret_start
_interpret_word_not_found:
- addi psp, psp, cell
- jal to_number
pop w
+ jal to_number
bnez w, _interpret_retry
- jal compiling_q
- jal q_branch
- .int _interpret_start
+ pop w
+ # compiling?
+ la x, _state
+ load_cell x, 0(x)
+ beqz x, _interpret_start
_interpret_compile_number:
jal lit
.int lit
jal comma
jal comma
- jal branch
- .int _interpret_start
+ j _interpret_start
_interpret_retry:
- jal drop
- jal branch
- .int _interpret_start
+ addi psp, psp, cell
+ load_cell w, 0(psp)
+ j _interpret_start
_interpret_parse_area_empty:
- addi psp, psp, 2 * cell
+ addi psp, psp, cell
+ pop w
exit
defword "evaluate", evaluate, 0xACE4360A
@@ -589,34 +585,37 @@ _evaluate_done:
exit
defcode "branch", branch, 0xB6873945
- load_cell w, 0(ra)
- mv ra, w
+ load_cell ra, 0(ra)
next
defcode "?branch", q_branch, 0x6AF3C1DE
- pop w
bnez w, _branch_done
- load_cell w, 0(ra)
- mv ra, w
+ pop w
+ load_cell ra, 0(ra)
next
_branch_done:
+ pop w
addi ra, ra, cell
next
defcode "prompt", prompt, 0xDFE6493B
+ push w
la w, _prompt
la x, _prompt_len
push_ret ra
call uart_put_string
pop_ret ra
+ pop w
next
defcode "okay", okay, 0xBA9EEB49
+ push w
la w, _okay
la x, _okay_len
push_ret ra
call uart_put_string
pop_ret ra
+ pop w
next
defword "quit", quit, 0x47878736
@@ -640,72 +639,62 @@ defword "abort", abort, 0xA52BCAF9
# -----------------------------------------------------------------------------
defcode "!", store, 0x240C8DEC
- pop w # address
- pop x # value
+ pop x
store_cell x, 0(w)
+ pop w
next
defcode "@", fetch, 0xC50BF85F
- pop w # address
- load_cell x, 0(w)
- push x
+ load_cell w, 0(w)
next
defcode "c!", char_store, 0x9829F909
- pop w
pop x
sb x, 0(w)
+ pop w
next
defcode "c@", char_fetch, 0x37296056
- pop w
- lb x, 0(w)
- push x
+ lb w, 0(w)
next
defcode "2!", two_store, 0x9CF2B11C
- pop w
pop x
pop y
store_cell x, 0(w)
store_cell y, cell(w)
+ pop w
next
defcode "2@", two_fetch, 0x3DF21B8F
- pop w
- load_cell x, 0(w)
load_cell y, cell(w)
+ load_cell w, 0(w)
push y
- push x
next
defcode "+!", add_store, 0x08DC01D1
- pop w # address
- pop x # value to add
- load_cell t0, 0(w)
- add t0, t0, x
- store_cell t0, 0(w)
+ pop x
+ load_cell y, 0(w)
+ add y, y, x
+ store_cell y, 0(w)
+ pop w
next
defcode "-!", sub_store, 0x24CD235B
- pop w # address
- pop x # value to add
- load_cell t0, 0(w)
- sub t0, t0, x
- store_cell t0, 0(w)
+ pop x
+ load_cell y, 0(w)
+ sub y, y, x
+ store_cell y, 0(w)
+ pop w
next
defcode "cells", cells, 0xD94ACBB2
- pop w
li x, cell
mul w, w, x
- push w
next
defcode "cell+", cell_plus, 0xB14A8CBA
- pop w
addi w, w, cell
- push w
next
# -----------------------------------------------------------------------------
@@ -718,12 +707,12 @@ defword "here", here, 0x213B65CB
exit
defcode "lit", lit, 0x404CD5B6
+ push w
load_cell w, 0(ra)
addi ra, ra, cell
- push w
next
-defcode "lit-string", lit_string, 0xC7BE567C # TODO: ip -> ra
+defcode "lit-string", lit_string, 0xC7BE567C # TODO: ip -> ra, w=tos
load_cell x, 0(ip) # len
addi ip, ip, cell
mv w, ip # addr
@@ -741,21 +730,21 @@ defword "allot", allot, 0xADB1A69F
exit
defcode ",", comma, 0x290C95CB
- pop w
la y, _dp
load_cell x, 0(y)
store_cell w, 0(x)
addi x, x, cell
store_cell x, 0(y)
+ pop w
next
defcode "c,", char_comma, 0xA32A0A5A
- pop w
la y, _dp
load_cell x, 0(y)
sb w, 0(x)
addi x, x, 1
store_cell x, 0(y)
+ pop w
next
defword "align", align, 0x602C63DE
@@ -778,102 +767,97 @@ defword "align", align, 0x602C63DE
defcode "sp@", sp_fetch, 0xFC419F82
# ( -- addr )
- mv w, psp
push w
+ mv w, psp
next
defcode "sp!", sp_store, 0x1D41D375
# ( addr -- )
- pop w
mv psp, w
+ pop w
next
defcode "rp@", rp_fetch, 0x7AD905AD
# ( -- addr )
- mv w, rsp
push w
+ mv w, rsp
next
defcode "rp!", rp_store, 0x99D9367A
# ( addr -- )
- pop w
mv rsp, w
+ pop w
next
defcode ">r", to_ret, 0x47FCB8A9
- pop w
push_ret w
+ pop w
next
defcode "r>", from_ret, 0x135408B1
- pop_ret w
push w
+ pop_ret w
next
defcode "2>r" two_to_ret, 0x69F5D439
- pop w
pop x
push_ret x
push_ret w
+ pop w
next
defcode "2r>", two_from_ret, 0xB54DEDC1
+ push w
pop_ret w
pop_ret x
push x
- push w
next
defcode "dup", dup, 0xD330F226
- load_cell w, 0(psp)
push w
+ load_cell w, 0(psp)
next
defcode "?dup", q_dup, 0xFD2928D3
- load_cell w, 0(psp)
beqz w, _q_dup_done
push w
_q_dup_done:
next
defcode "swap", swap, 0x64ED874E
- pop w
- pop x
- push w
- push x
+ load_cell x, 0(psp)
+ store_cell w, 0(psp)
+ mv w, x
next
defcode "drop", drop, 0xA9A58D8C
- addi psp, psp, cell
+ pop w
next
defcode "over", over, 0x31F6520F
- load_cell w, cell(psp)
push w
+ load_cell w, cell(psp)
next
defcode "nip", nip, 0x21A41868
- pop w
- store_cell w, 0(psp)
+ addi psp, psp, cell
next
defcode "tuck", tuck, 0x8E26FCE8
- pop w
- pop x
- push w
+ load_cell x, 0(psp)
+ store_cell w, 0(psp)
push x
- push w
next
defcode "2dup", two_dup, 0x5E46F4D6
- load_cell w, 0(psp)
- load_cell x, cell(psp)
- push x
+ load_cell x, 0(psp)
push w
+ push x
next
defcode "2drop", two_drop, 0xECFD129C
- addi psp, psp, 2 * cell
+ addi psp, psp, cell
+ pop w
next
# -----------------------------------------------------------------------------
@@ -881,66 +865,48 @@ defcode "2drop", two_drop, 0xECFD129C
# -----------------------------------------------------------------------------
defcode "+", plus, 0x2E0C9DAA
- pop w
pop x
- add w, w, x
- push w
+ add w, x, w
next
defcode "-", minus, 0x280C9438
pop x
- pop w
- sub w, w, x
- push w
+ sub w, x, w
next
defcode "*", times, 0x2F0C9F3D
- pop w
pop x
- mul w, w, x
- push w
+ mul w, x, w
next
defcode "or", or_, 0x5D342984
- pop w
pop x
- or w, w, x
- push w
+ or w, x, w
next
defcode "and", and_, 0x0F29C2A6
- pop w
pop x
- and w, w, x
- push w
+ and w, x, w
next
defcode "lshift", lshift, 0x8DA53719
- pop w
pop x
- sll x, x, w
- push x
+ sll w, x, w
next
defcode "rshift", rshift, 0x86294EF7
- pop w
pop x
- srl x, x, w
- push x
+ srl w, x, w
next
defcode "ashift", ashift, 0x46A0EC68
- pop w
pop x
- sra x, x, w
- push x
+ sra w, x, w
next
defcode "aligned", aligned, 0xC73174DF
- pop w
- addi w, w, 3
- andi w, w, 0xFFFFFFFC
- push w
+ addi w, w, cell - 1
+ andi w, w, -cell
next
# -----------------------------------------------------------------------------
@@ -948,65 +914,55 @@ defcode "aligned", aligned, 0xC73174DF
# -----------------------------------------------------------------------------
defcode "0=", zero_equal, 0x14ED5DD6
- pop w
mv x, zero
bnez w, _zero_done
addi x, x, -1
_zero_done:
- push x
+ mv w, x
next
defcode "=", equal, 0x380CAD68
- pop w
pop x
beq w, x, _equal
- push zero
+ mv w, zero
next
_equal:
- push_imm -1
+ li w, -1
next
defcode "<>", not_equal, 0x93F7201F
- pop w
pop x
bne w, x, _not_equal
- push zero
+ mv w, zero
next
_not_equal:
- push_imm -1
+ li w, -1
next
defcode ">", greater_than, 0x3B0CB221
- pop w
pop x
bgt x, w, _greater_than
- push zero
+ mv w, zero
next
_greater_than:
- push_imm -1
+ li w, -1
next
defcode "<", less_than, 0x390CAEFB
- pop w
pop x
blt x, w, _less_than
- push zero
+ mv w, zero
next
_less_than:
- push_imm -1
+ li w, -1
next
-defword "min", min, 0xC98F4557
- jal two_dup
- jal less_than
- jal q_branch
- .int _min_b
-_min_a:
- jal drop
- exit
-_min_b:
- jal nip
- exit
+defcode "min", min, 0xC98F4557
+ pop x
+ bgt x, w, _min_greater_than
+ mv w, x
+_min_greater_than:
+ next
# -----------------------------------------------------------------------------
# compiler
@@ -1014,7 +970,7 @@ _min_b:
defcode "jal-immed", jal_immed, 0xA914EF13
# encode a value as an immediate for a 'jal' instruction
- pop x
+ mv x, w
li y, 0x000FF000 # imm[19:12]
and w, x, y
li y, 0x00100000 # imm[20]
@@ -1028,26 +984,21 @@ defcode "jal-immed", jal_immed, 0xA914EF13
andi y, x, 0x000007FE # imm[10:1]
slli y, y, 20
add w, w, y
- push w
next
defword "jal-to", jal_to, 0xC38EF054
# generate a 'jal ra, addr' instruction
- pop w
la x, _dp
load_cell x, 0(x)
sub w, w, x
- push w
jal jal_immed
- pop w
addi w, w, 0x000000EF # jal ra, imm
- push w
exit
defword "jal-dovar", jal_dovar, 0x668658A5
# generate a 'jal ra, dovar' instruction
- la w, dovar
push w
+ la w, dovar
jal jal_to
exit
@@ -1057,23 +1008,23 @@ defword "dovar,", dovar_comma, 0x1F514E5B
exit
defword "docol,", docol_comma, 0xFAE1EE9E
- li w, 0xFE192E23 # sw ra, -4(s2)
push w
+ li w, 0xFE192E23 # sw ra, -4(s2)
jal comma
- li w, 0xFFC90913 # addi s2, s2, -4
push w
+ li w, 0xFFC90913 # addi s2, s2, -4
jal comma
exit
defword "exit,", exit_comma, 0xD540F80B
- li w, 0x00092083 # lw ra, 0(s2)
push w
+ li w, 0x00092083 # lw ra, 0(s2)
jal comma
- li w, 0x00490913 # addi s2, s2, 4
push w
+ li w, 0x00490913 # addi s2, s2, 4
jal comma
- li w, 0x00008067 # ret
push w
+ li w, 0x00008067 # ret
jal comma
exit
@@ -1106,12 +1057,11 @@ defword "create", create, 0x26BB595D
exit
defcode "hash", hash, 0xEDBF0FE3
- pop x # string length
- pop w # string address
+ mv x, w
+ pop w
push_ret ra
jal hash_impl
pop_ret ra
- push w # string hash
next
hash_impl: # 32-bit fnv1a
@@ -1128,37 +1078,34 @@ _hash_char:
ret
defcode "[", l_bracket, 0xDE0C1FBA, flags=flag_immediate
- la w, _state
- li x, state_immediate
- store_cell x, 0(w)
+ la x, _state
+ li y, state_immediate
+ store_cell y, 0(x)
next
defcode "]", r_bracket, 0xD80C1648
- la w, _state
- li x, state_compile
- store_cell x, 0(w)
+ la x, _state
+ li y, state_compile
+ store_cell y, 0(x)
next
defcode "hidden", hidden, 0xF618F139
- pop w
addi w, w, flag_offset
lb x, 0(w)
xori x, x, flag_hidden
sb x, 0(w)
+ pop w
next
defcode "hidden?", hidden_q, 0x6F436C72
- pop w
addi w, w, flag_offset
- lb x, 0(w)
- andi x, x, flag_hidden
- push x
+ lb w, 0(w)
+ andi w, w, flag_hidden
next
defword ":", colon, 0x3F0CB86D
jal create # create header
- jal lit
- .int -cell
+ push_imm -cell
jal allot
jal docol_comma # append 'docol'
jal latest
@@ -1191,6 +1138,7 @@ defcode "immediate?", immediate_q, 0x89F23E9F
next
# TODO: everything after this needs updated to work with subroutine threading
+# and with w=tos
defword "postpone", postpone, 0x933F531F, flags=flag_immediate
.int parse_word, find # TODO: was word actually found?
@@ -1354,6 +1302,7 @@ start:
la psp, __stacktop
la rsp, __stacktop_ret
la ip, program
+ li w, 0xDEADC0DE
push_addr version_string
push_imm version_string_len