1 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2 ;; UrForth level
1: self
-hosting
32-bit Forth compiler
4 ;; Copyright
(C
) 2020 Ketmar Dark
// Invisible Vector
6 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
8 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
9 ;; currently
, debug info is very simple
, it contains only PC
->LINE mapping
12 ;; dw itemcount
; files with more that
64kb lines?
'cmon!
13 ;; dw firstline ; files with more that 64kb lines? 'cmon
!
14 ;; dd filename
-c1strz
; this points
to special hidden buffer word
, or
0
17 ;; db pcoffs
; offset from the previous PC
(first
: from the CFA
)
18 ;; db lineofs
; offset from the previous line
20 ;; if lineofs is
255, next word is
16-bit line offset
21 ;; if pcofs is
255, next word is
16-bit line offset
23 ;; the compiler doesn
't store each PC, it only stores line changes
24 ;; that is, the range for the line lasts until the next item
25 ;; items should be sorted by PC (but the code should not fail on
29 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
30 ;; list of known source files
35 0 var tc-(dbg-file-list-head)
38 : tc-(dbg-add-file) ( addr count -- straddr )
40 tc-(dbg-file-list-head) @ over !
41 dup tc-(dbg-file-list-head) ! cell+
44 dup 1+ tc-n-allot dup >r
45 2dup tc-c! 1+ tc->real swap 0 max cmove
50 : tc-(dbg-find-or-add-file) ( addr count -- straddr )
51 str-extract-name ?dup if
52 tc-(dbg-file-list-head)
56 >r 2dup r@ cell+ @ tc->real bcount s= if
69 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
70 ;; create compressed debug info, set dfa
72 ;; let's use globals here
, because why not?
73 0 value tc
-(dbginfo
-cpbuf
-start
)
74 0 value tc
-(dbginfo
-cpbuf
-curpos
)
75 0 value tc
-(dbginfo
-cpbuf
-currline
)
76 0 value tc
-(dbginfo
-cpbuf
-currpc
)
78 : tc
-(dbginfo
-build
-byte
) ( b
-- )
79 tc
-(dbginfo
-cpbuf
-curpos
) c
!
80 tc
-(dbginfo
-cpbuf
-curpos
) 1+ to tc
-(dbginfo
-cpbuf
-curpos
)
83 : tc
-(dbginfo
-build
-word
) ( w
-- )
84 dup
0xff and tc
-(dbginfo
-build
-byte
)
85 8 rshift tc
-(dbginfo
-build
-byte
)
88 : tc
-(dbginfo
-build
-dword
) ( dw
-- )
89 dup
0xffff and tc
-(dbginfo
-build
-word
)
90 16 rshift tc
-(dbginfo
-build
-word
)
94 ;; prerequisite
: debug info must exist
, and must not be empty
95 : tc
-(dbginfo
-build
-compressed
) ( destbuf
-- destbuf size
)
96 ;; build file name
(do it here
, because it may allocate at here
)
97 forth
:(tib
-curr
-fname
) count tc
-(dbg
-find
-or
-add
-file
) >r
99 dup
to tc
-(dbginfo
-cpbuf
-start
)
100 to tc
-(dbginfo
-cpbuf
-curpos
)
102 tc
-(dbgbuf
-base
-addr
) @
to tc
-(dbginfo
-cpbuf
-currline
)
104 tc
-latest
-cfa
to tc
-(dbginfo
-cpbuf
-currpc
)
106 ;; item count
(we know that in advance
)
107 tc
-(dbgbuf
-curr
-addr
) @ tc
-(dbgbuf
-base
-addr
) - 3 rshift tc
-(dbginfo
-build
-word
)
109 tc
-(dbginfo
-cpbuf
-currline
) tc
-(dbginfo
-build
-word
)
111 r
> tc
-(dbginfo
-build
-dword
)
112 tc
-(dbgbuf
-curr
-addr
) @ tc
-(dbgbuf
-base
-addr
) do
113 ;; db pcoffs
; offset from the previous PC
(first
: from the CFA
)
114 ;; db lineofs
; offset from the previous line
116 ;; if lineofs is
255, next word is
16-bit line offset
117 ;; if pcofs is
255, next word is
16-bit line offset
119 i cell
+ @ tc
-(dbginfo
-cpbuf
-currpc
) - dup
255 < if
121 tc
-(dbginfo
-build
-byte
)
124 255 tc
-(dbginfo
-build
-byte
)
125 tc
-(dbginfo
-build
-word
)
128 i cell
+ @
to tc
-(dbginfo
-cpbuf
-currpc
)
130 i @ tc
-(dbginfo
-cpbuf
-currline
) - dup
255 < if
132 tc
-(dbginfo
-build
-byte
)
135 255 tc
-(dbginfo
-build
-byte
)
136 tc
-(dbginfo
-build
-word
)
138 ;; update current line
139 \ endcr i @
. tc
-(dbginfo
-cpbuf
-currline
) . cr
140 i @
to tc
-(dbginfo
-cpbuf
-currline
)
142 ;; return addr and size
143 tc
-(dbginfo
-cpbuf
-start
) tc
-(dbginfo
-cpbuf
-curpos
) over
-
146 : tc
-(dbginfo
-finalize
-and
-copy
) ( -- )
147 tc
-(dbginfo
-active?
) tc
-(dbginfo
-enabled?
) logand
if
148 tc
-(dbgbuf
-base
-addr
) ?dup
if
151 tc
-(dbgbuf
-curr
-addr
) @
0! tc
-(dbginfo
-add
-here
)
152 ;; compressed should never be bigger than the original
153 tc
-(dbgbuf
-curr
-addr
) @ tc
-(dbgbuf
-base
-addr
) - 4 +cells dup
>r
154 os
:prot
-r
/w os
:mmap not
-?abort
" out of memory" dup
>r
155 tc
-(dbginfo
-build
-compressed
)
156 \ endcr
." debug: from " tc
-(dbgbuf
-curr
-addr
) @ tc
-(dbgbuf
-base
-addr
) - . ." to " dup
. cr
157 ;; save here
to debug info field
158 tc
-here tc
-latest
-nfa tc
-nfa
->dfa tc
-!
159 dup tc
-n
-allot
;; ( addr bytes rva
-newaddr
)
160 tc
->real swap
0 max cmove
161 r
> r
> swap os
:munmap drop