1 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2 ;; UrForth level
1: self
-hosting
32-bit Forth compiler
3 ;; Copyright
(C
) 2020 Ketmar Dark
// Invisible Vector
5 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
7 $uservar
"(EXC-FRAME-PTR)" ua_ofs_exc_frame_ptr
0
10 ;; reset all exception frames
11 : (EXC0
!) ( -- ) ... (exc
-frame
-ptr
) 0! ; (hidden
)
13 ;; this should save all necessary data
to the
return stack
14 ;; the
format is
: ( ...data restorecfa
)
15 ;; restorecfa
: ( restoreflag
-- )
16 ;; if "restoreflag" is
0, drop the data
17 : (CATCH
-SAVER
) ( -- ) ... ; (hidden
)
20 : CATCH
( i
* x xt
-- j
* x
0 | i
* x n
)
21 ;; this is using
return stack
to hold previous catch frame
22 ;; of course
, this prevents Very Smart
return stack manipulation
, but idc
(for now
)
23 ;; exception frame consists of
:
24 ;; return-to-catch EIP
(return stack TOS
)
25 ;; sp
(frame points here
)
28 ;; return-to-catch
-caller EIP
29 ;; create exception frame
31 ;; section
to save various custom data
35 ;; custom data section
end
37 rp@
(exc
-frame
-ptr
) ! ;; update exception frame pointer
38 execute
;; and execute
39 ;; we will
return here only
if no exception was thrown
40 rdrop begin r
> ?dup
while false swap execute repeat
41 ;;3 nrdrop
;; drop spdepth
, locptr
, self
42 r
> (exc
-frame
-ptr
) ! ;; restore previous exception frame
43 0 ;; exception code
(none
)
47 : THROW
( k
* x n
-- k
* x | i
* x n
)
49 ;; check
if we have exception frame set
50 (exc
-frame
-ptr
) @ ?dup ifnot
53 state
0! ;; just in case
54 fatal
-error
;; err
-throw
-without
-catch
(error
)
55 1 n
-bye
;; just in case
57 ;; check
if return stack is not exhausted
61 state
0! ;; just in case
62 err
-throw
-chain
-corrupted fatal
-error
63 1 n
-bye
;; just in case
65 rp
! ;; restore
return stack
66 r
> swap
>r
;; exchange
return stack top and data stack top
(save exception code
, and pop sp
to data stack
)
67 ;; blindly restore data stack
(let
's hope it is not too badly trashed)
68 sp! drop ;; drop the thing that was CFA
69 r> ;; restore exception code
70 ;; restore custom data
71 begin r> ?dup while true swap execute repeat
74 ;; restore previous exception frame
76 ;; now EXIT will return to CATCH caller