1 ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2 ;; and now
for something completely different
...
3 ;; UrForth
/C Forth Engine
!
4 ;; Copyright
(C
) 2023 Ketmar Dark
// Invisible Vector
6 ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
7 ;; local variables support
8 ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
19 here
, "args:" will declare local variables
, and automatically fill them
20 with arguments from the data stack
. "locals:" declare
"free" locals
.
21 there can be more than one
"locals:" section
, but all such sections should
22 come before anything else. to use local, you must prepend its name with a
23 colon. the usual "TO" word is used to set local values.
26 VOCABULARY
(LOCALS
-SUPPORT
)
27 ALSO
(LOCALS
-SUPPORT
) DEFINITIONS
29 ;; offset in temp
(user
) dict
30 ;; should be enough
for now
;-)
31 65536 CONSTANT LOCALS
-TEMP
-VOC
-OFFSET
33 0 VALUE LOCALS
-DP
-TEMP
36 : NEW
-LOCALS
-WORDLIST
( -- )
37 FORTH
:(DP
-TEMP
) @
;; save it
38 FORTH
:(ADDR
-TEMP
-BIT
) LOCALS
-TEMP
-VOC
-OFFSET
+ FORTH
:(DP
-TEMP
) !
39 0 FALSE FORTH
:(NEW
-WORDLIST
) TO LOCALS
-VOCID
40 HERE
TO LOCALS
-DP
-TEMP
45 ;; low byte of loccount is total number of locals
46 ;; high byte is the number of args
48 : LATEST
-HAS
-LOCALS?
( -- bool
)
49 LATEST
-PFA DUP HERE
= IF DROP FALSE
50 ELSE @
['] FORTH:(L-ENTER) =
56 LATEST-HAS-LOCALS? " \`locals:\` or \`args:\` should be the first word" ?NOT-ERROR
58 NEW-LOCALS-WORDLIST COMPILE FORTH:(L-ENTER) 0 ,
62 : ADD-LOCAL ( addr count -- )
64 LATEST-PFA CELL+ DUP C@ 255 = " too many locals" ?ERROR
65 1 OVER +! C@ >R ;; save current local number to RSTACK
66 ;; now create access word
67 FORTH:(DP-TEMP) @ CURRENT @
68 LOCALS-DP-TEMP FORTH:(DP-TEMP) ! LOCALS-VOCID CURRENT !
69 \ ." DP: " FORTH:(DP) @ . CR
70 \ ." DP-TEMP: " FORTH:(DP-TEMP) @ . CR
71 \ ." HERE: " HERE . CR
74 COMPILER:(CREATE-HEADER)
75 COMPILER:(CFAIDX-DO-CONST) , ;; why not
78 FORTH:(DP-TEMP) @ HERE <> " WTF?!" ?ERROR ;; assertion
79 HERE TO LOCALS-DP-TEMP
81 CURRENT ! FORTH:(DP-TEMP) !
84 ;; create local access words, adjust "(L-ENTER)"
85 : ADD-ARG ( addr count -- )
86 ADD-LOCAL 0x01_00 LATEST-PFA CELL+ +!
89 : PARSE-LOC-LIST ( regcfa -- )
91 PARSE-SKIP-LINE-COMMENTS
100 ..: FORTH:(EXIT-EXTENDER) ( -- )
101 LATEST-HAS-LOCALS? IF COMPILE FORTH:(L-LEAVE) ENDIF
105 : FIND-LOCAL ( addr count -- addr count FALSE / idx TRUE )
107 2DUP 1 > SWAP C@ [CHAR] : = AND IF
108 LATEST-HAS-LOCALS? IF ( addr count | ret-flag )
109 OVER 1+ OVER 1- LOCALS-VOCID FIND-WORD-IN-VOC
111 >R 2DROP R> CFA->PFA @
119 ..: FORTH:(TO-EXTENDER) ( addr count FALSE -- addr count FALSE / TRUE )
122 FIND-LOCAL IF LITERAL COMPILE FORTH:(LOCAL!) TRUE
130 ..: FORTH:(INTERPRET-CHECK-WORD) ( addr count FALSE -- addr count FALSE / TRUE )
133 FIND-LOCAL IF LITERAL COMPILE FORTH:(LOCAL@) TRUE
144 : ARGS: ['] (LOCALS
-SUPPORT
):ADD
-ARG
(LOCALS
-SUPPORT
):PARSE
-LOC
-LIST
; IMMEDIATE
145 : LOCALS
: ['] (LOCALS-SUPPORT):ADD-LOCAL (LOCALS-SUPPORT):PARSE-LOC-LIST ; IMMEDIATE