1
2
3
4
5
6
7
8
9
10
11
12 get "bcpl_cg_head"
13 get "bcpl_opcodes"
14
15
16
17 let LoadRegister (t, r) = valof
18 $( let q = FindInRegister (t, r)
19 if q ne 0 resultis Preserve (q)
20 if r = Ar | r = Qr then if FindInRegister (t, Qr + Ar - r) ne 0 do
21 $( SwapAandQ ()
22 resultis Preserve (r)
23 $)
24 if IsNumber (t) resultis LoadNumber (EvalNumber (t!0, t!1), r, t!2)
25 r := GetRegister (r)
26 Makeaddressable (t)
27 Outop (r = EAQr -> Fld, FormOpcode (Lda, r))
28 IndicatorsSetBy := r
29 resultis Preserve (r)
30 $)
31 and LoadNumber (n, r, c) = valof
32 $( r := GetRegister (r)
33 let Op = Lda
34 test r = EAQr
35 then Op := Fld
36 or if n < 0 then unless n = (1 lshift 35) do Op, n := Lca, - n
37 Literal (n, c)
38 Outop (FormOpcode (Op, r))
39 IndicatorsSetBy := r
40 resultis Preserve (r)
41 $)
42 and SwapAandQ () be
43 $( Outop4 (Llr, 36, 0, "exchange A and Q")
44 IndicatorsSetBy := 0
45 let p, q = RegisterTemps!Ar, RegisterTemps!Qr
46 RegisterTemps!Ar, RegisterTemps!Qr := q, p
47 if p ne 0 do p!2 := Qr
48 if q ne 0 do q!2 := Ar
49 $)
50 and LoadPointer (t, r) = valof
51 $( let q = FindInRegister (t, r)
52 if q ne 0 resultis Preserve (q)
53 r := GetRegister (r)
54 test IsAddress (t)
55 then $( SetupAddr (t)
56 Outop (FormOpcode (Eapap, r))
57 $)
58 or $( Makeaddressable (t)
59 Outop (FormOpcode (Lprpap, r))
60 $)
61 resultis Preserve (r)
62 $)
63 and LoadIndex (t, r) = valof
64 $( let q = FindInRegister (t, r)
65 if q = 0 & r = AnyXr do q := FindInRegister (t, AorQr)
66 if q ne 0 resultis Preserve (q)
67 r := GetRegister (r)
68 test IsAddress (t)
69 then $( SetupAddr (t)
70 Outop (FormOpcode (Eax0, r))
71 $)
72 or $( Makeaddressable (t)
73 Outop (FormOpcode (Lxl0, r))
74 $)
75 IndicatorsSetBy := r
76 resultis Preserve (r)
77 $)
78 and LoadAppropriateRegister (t, r) = valof
79 $( if r = 0 do
80 $( r := FindInRegister (t, AorQr)
81 if r = 0 do r := FindInRegister (t, AnyPr)
82 if r = 0 do r := FindInRegister (t, EAQr)
83 if r ne 0 resultis Preserve (r)
84 r := IsAddress (t) -> AnyPr, AorQr
85 $)
86 if r = AorQr | Satisfactory (r, AorQr) | r = EAQr resultis LoadRegister (t, r)
87 if r = AnyPr | Satisfactory (r, AnyPr) resultis LoadPointer (t, r)
88 CGreport (UnexpectedCase, r, "LoadAppropriateRegister")
89 resultis Ar
90 $)
91
92 and Makeaddressable (t) be
93 $( test IsNumber (t)
94 then Literal (EvalNumber (t!0, t!1), t!2)
95 or test IsStored (t)
96 then SetATP (t)
97 or $( let u = list LV_GLOBAL, 0, 0
98 Store (t, u)
99 Address, Tag, Param := 0, Sp, 0
100 $)
101 unless t!2 = 0 do Comment := t!2
102 $)
103 and SetupAddr (t) be
104 $( test IsAddress (t)
105 then SetATP (t)
106 or $( let r = LoadPointer (t, AnyPr)
107 Address, Tag, Param := 0, FormTag (r), 0
108 $)
109 unless t!2 = 0 do Comment := t!2
110 $)
111 and SetATP (t) be
112 $( Address, Tag, Param := 0, 0, 0
113 switchon t!0 into
114 $( case GLOBAL_S: case LV_GLOBAL:
115 Address, Tag := t!1, Sp
116 endcase
117 case TEMP_S:
118 let h = LookupTemp (t!1)
119 if h ne 0 then if h!1 = VECAP_S | h!1 = LVECAP_S do
120 $( CombineAddress (lv h!2, lv h!5, h!8)
121 endcase
122 $)
123 case LOCAL_S: case LV_LOCAL:
124 case LV_TEMP:
125 Address, Tag := t!1 + SaveSpaceSize, StackRefTag
126 endcase
127 case LV_ARG_OUT:
128 Address, Tag, Param := t!1 + SaveSpaceSize, StackRefTag, LabMaxSSP
129 endcase
130 case STATIC_S: case LV_STATIC:
131 Address, Tag := t!1 + 8, Lp
132 endcase
133 case EXTERNAL_S:
134 Tag, Param := Lp | Star, Compexternal (t!1)
135 endcase
136 case LABEL_S: case RTDEF_S:
137 Param := t!1
138 endcase
139 case STRINGCONST_S:
140 Compstring (t!1)
141 endcase
142 case TABLE_S:
143 Comptable (t!1)
144 endcase
145 default: CGreport (UnexpectedCase, t!0, "SetATP")
146 $)
147 CheckAddr ()
148 $)
149 and CompareToZero (t) be
150 $( let r = FindInRegister (t, AorQr)
151 test r ne 0
152 then unless r = IndicatorsSetBy do
153 $( Outop3 (FormOpcode (Cmpa, r), 0, Dl)
154 IndicatorsSetBy := r
155 $)
156 or $( Makeaddressable (t)
157 Outop (Szn)
158 IndicatorsSetBy := 0
159 $)
160 $)
161
162 and StoreRegister (r, To) be
163 $( let Op = valof switchon r into
164 $( case Ar: case Qr:
165 default:
166 resultis Sta
167 case Apr: case Abr: case Bpr: case Bbr: case Lbr:
168 resultis Sprpap
169 case EAQr:
170 resultis Fstr
171 $)
172 SetupAddr (To)
173 test Machine = 645 & Op = Sprpap
174 then $( let A, T, P = Address, Tag, Param
175 Outop (FormOpcode (Sprpap, r + 1))
176 Outop3 (Eax0, 0, FormTag (r))
177 Address, Tag, Param := A, T, P
178 Outop (Sxl0)
179 $)
180 or Outop (FormOpcode (Op, r))
181 RegisterUsage!r := 0
182 $)
183 and Store (From, To) be
184 test IsZero (From)
185 then $( SetupAddr (To)
186 Outop (Stz)
187 $)
188 or $( let r = LoadAppropriateRegister (From, 0)
189 StoreRegister (r, To)
190 $)
191
192 and Preserve (r) = valof
193 $( UsageCounter := UsageCounter + 1
194 RegisterUsage!r := UsageCounter
195 resultis r
196 $)
197 and GetRegister (r) = valof
198 $( switchon r into
199 $( default: CGreport (UnexpectedCase, r, "GetRegister")
200 r := Ar
201
202 case Ar: case Qr:
203 MakeAvailable (EAQr)
204 endcase
205
206 case EAQr:
207 MakeAvailable (Ar)
208 MakeAvailable (Qr)
209 endcase
210
211 case Xr2: case Xr3: case Xr4: case Xr5: case Xr6:
212 case Apr: case Abr: case Bpr: case Bbr: case Lbr:
213 endcase
214
215 case AorQr:
216 r := RegisterUsage!Ar < RegisterUsage!Qr -> Ar, Qr
217 MakeAvailable (EAQr)
218 endcase
219
220 case AnyPr:
221 r := RegisterUsage!Bpr < RegisterUsage!Apr -> Bpr, Apr
222 if Machine = 6180 do
223 $( let T = table Abr, Bbr, Lbr
224 for i = 0 to 2 if RegisterUsage!(T!i) < RegisterUsage!r do r := T!i
225 $)
226 endcase
227
228 case AnyXr:
229 r := Xr2
230 let T = table Xr3, Xr4, Xr5, Xr6
231 for i = 0 to 3 if RegisterUsage!(T!i) < RegisterUsage!r do r := T!i
232 endcase
233 $)
234 MakeAvailable (r)
235 resultis r
236 $)
237 and Satisfactory (r, q) = valof
238 $( switchon q into
239 $( case AnyXr:
240 if r = Xr2 | r = Xr3 | r = Xr4 | r = Xr5 | r = Xr6 resultis true
241 resultis false
242 case AorQr:
243 if r = Ar | r = Qr resultis true
244 resultis false
245 case AnyPr:
246 if r = Apr | r = Abr | r = Bpr | r = Bbr | r = Lbr resultis true
247 resultis false
248 default: resultis r = q
249 $)
250 $)
251 and MakeAvailable (r) be
252 $( let h = RegisterTemps!r
253 if h = 0 return
254 let To = list LV_TEMP, h!0, "temporary"
255 StoreRegister (r, To)
256 RegisterTemps!r, RegisterUsage!r := 0, 0
257 h!0 := -1
258 $)
259
260 and Literal (n, c) be
261 $( Address, Tag, Param, Comment := n & $8777777, Dl, 0, c
262 if Address = n return
263 test Address = 0
264 then Address, Tag := n rshift 18, Du
265 or AddLiteral (lv n, 1, c, 0)
266 $)