Rev 8097 | Go to most recent revision | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 8097 | Rev 8859 | ||
---|---|---|---|
Line 1... | Line 1... | ||
1 | (* |
1 | (* |
2 | BSD 2-Clause License |
2 | BSD 2-Clause License |
Line 3... | Line 3... | ||
3 | 3 | ||
4 | Copyright (c) 2018-2020, Anton Krotov |
4 | Copyright (c) 2018-2021, Anton Krotov |
5 | All rights reserved. |
5 | All rights reserved. |
Line 6... | Line 6... | ||
6 | *) |
6 | *) |
Line 15... | Line 15... | ||
15 | R0* = 0; R1* = 1; R2* = 2; R3* = 3; |
15 | R0* = 0; R1* = 1; R2* = 2; R3* = 3; |
16 | R4* = 4; R5* = 5; R6* = 6; R7* = 7; |
16 | R4* = 4; R5* = 5; R6* = 6; R7* = 7; |
17 | R8* = 8; R9* = 9; R10* = 10; R11* = 11; |
17 | R8* = 8; R9* = 9; R10* = 10; R11* = 11; |
18 | R12* = 12; R13* = 13; R14* = 14; R15* = 15; |
18 | R12* = 12; R13* = 13; R14* = 14; R15* = 15; |
Line 19... | Line -... | ||
19 | - | ||
20 | NVR = 32; |
- | |
Line 21... | Line 19... | ||
21 | 19 | ||
Line 22... | Line 20... | ||
22 | 20 | ||
23 | TYPE |
21 | TYPE |
24 | - | ||
Line 25... | Line 22... | ||
25 | OP1 = PROCEDURE (arg: INTEGER); |
22 | |
Line 26... | Line 23... | ||
26 | OP2 = PROCEDURE (arg1, arg2: INTEGER); |
23 | OP1 = PROCEDURE (arg: INTEGER); |
27 | OP3 = PROCEDURE (arg1, arg2, arg3: INTEGER); |
24 | OP2 = PROCEDURE (arg1, arg2: INTEGER); |
28 | 25 | ||
29 | REGS* = RECORD |
26 | REGS* = RECORD |
Line 30... | Line -... | ||
30 | - | ||
31 | regs*: SET; |
- | |
32 | stk*: ARRAY N OF INTEGER; |
- | |
33 | top*: INTEGER; |
- | |
34 | pushed*: INTEGER; |
27 | |
35 | 28 | regs*: SET; |
|
36 | vregs*: SET; |
- | |
Line 37... | Line 29... | ||
37 | offs: ARRAY NVR OF INTEGER; |
29 | stk*: ARRAY N OF INTEGER; |
Line 38... | Line 30... | ||
38 | size: ARRAY NVR OF INTEGER; |
30 | top*: INTEGER; |
Line 76... | Line 68... | ||
76 | END pop; |
68 | END pop; |
Line 77... | Line 69... | ||
77 | 69 | ||
78 | 70 | ||
79 | PROCEDURE InStk (R: REGS; reg: INTEGER): INTEGER; |
71 | PROCEDURE InStk (R: REGS; reg: INTEGER): INTEGER; |
Line 80... | Line 72... | ||
80 | VAR |
72 | VAR |
81 | i, n: INTEGER; |
- | |
82 | 73 | i: INTEGER; |
|
83 | BEGIN |
74 | |
84 | i := 0; |
75 | BEGIN |
85 | n := R.top; |
- | |
86 | WHILE (i <= n) & (R.stk[i] # reg) DO |
- | |
87 | INC(i) |
- | |
88 | END; |
- | |
89 | 76 | i := R.top; |
|
Line 90... | Line 77... | ||
90 | IF i > n THEN |
77 | WHILE (i >= 0) & (R.stk[i] # reg) DO |
91 | i := -1 |
78 | DEC(i) |
Line 204... | Line 191... | ||
204 | VAR |
191 | VAR |
205 | n1, n2: INTEGER; |
192 | n1, n2: INTEGER; |
206 | res: BOOLEAN; |
193 | res: BOOLEAN; |
Line 207... | Line 194... | ||
207 | 194 | ||
208 | BEGIN |
195 | BEGIN |
Line 209... | Line 196... | ||
209 | res := FALSE; |
196 | res := TRUE; |
210 | 197 | ||
211 | IF reg1 # reg2 THEN |
198 | IF reg1 # reg2 THEN |
Line 212... | Line 199... | ||
212 | n1 := InStk(R, reg1); |
199 | n1 := InStk(R, reg1); |
213 | n2 := InStk(R, reg2); |
200 | n2 := InStk(R, reg2); |
214 | 201 | ||
215 | IF (n1 # -1) & (n2 # -1) THEN |
202 | IF (n1 # -1) & (n2 # -1) THEN |
216 | R.stk[n1] := reg2; |
- | |
217 | R.stk[n2] := reg1; |
203 | R.stk[n1] := reg2; |
218 | R.xch(reg2, reg1); |
204 | R.stk[n2] := reg1; |
219 | res := TRUE |
205 | R.xch(reg2, reg1) |
220 | ELSIF (n1 # -1) & (reg2 IN R.regs) THEN |
206 | ELSIF (n1 # -1) & (reg2 IN R.regs) THEN |
221 | R.stk[n1] := reg2; |
207 | R.stk[n1] := reg2; |
222 | INCL(R.regs, reg1); |
- | |
223 | EXCL(R.regs, reg2); |
208 | INCL(R.regs, reg1); |
224 | R.mov(reg2, reg1); |
209 | EXCL(R.regs, reg2); |
225 | res := TRUE |
210 | R.mov(reg2, reg1) |
226 | ELSIF (n2 # -1) & (reg1 IN R.regs) THEN |
211 | ELSIF (n2 # -1) & (reg1 IN R.regs) THEN |
227 | R.stk[n2] := reg1; |
212 | R.stk[n2] := reg1; |
228 | EXCL(R.regs, reg1); |
- | |
229 | INCL(R.regs, reg2); |
- | |
230 | R.mov(reg1, reg2); |
213 | EXCL(R.regs, reg1); |
231 | res := TRUE |
214 | INCL(R.regs, reg2); |
- | 215 | R.mov(reg1, reg2) |
|
232 | END |
216 | ELSE |
Line 233... | Line 217... | ||
233 | ELSE |
217 | res := FALSE |
234 | res := TRUE |
218 | END |
Line 250... | Line 234... | ||
250 | IF R.top > 0 THEN |
234 | IF R.top > 0 THEN |
251 | reg1 := R.stk[R.top - 1]; |
235 | reg1 := R.stk[R.top - 1]; |
252 | reg2 := R.stk[R.top] |
236 | reg2 := R.stk[R.top] |
253 | ELSIF R.top = 0 THEN |
237 | ELSIF R.top = 0 THEN |
254 | reg1 := PopAnyReg(R); |
238 | reg1 := PopAnyReg(R); |
255 | reg2 := R.stk[R.top] |
239 | reg2 := R.stk[1] |
256 | ELSIF R.top < 0 THEN |
240 | ELSE (* R.top = -1 *) |
257 | reg2 := PopAnyReg(R); |
241 | reg2 := PopAnyReg(R); |
258 | reg1 := PopAnyReg(R) |
242 | reg1 := PopAnyReg(R) |
259 | END |
243 | END |
260 | END BinOp; |
244 | END BinOp; |
Line 284... | Line 268... | ||
284 | push(R) |
268 | push(R) |
285 | END |
269 | END |
286 | END PushAll_1; |
270 | END PushAll_1; |
Line 287... | Line -... | ||
287 | - | ||
288 | - | ||
289 | PROCEDURE Lock* (VAR R: REGS; reg, offs, size: INTEGER); |
- | |
290 | BEGIN |
- | |
291 | ASSERT(reg IN R.vregs); |
- | |
292 | ASSERT(offs # 0); |
- | |
293 | ASSERT(size IN {1, 2, 4, 8}); |
- | |
294 | R.offs[reg] := offs; |
- | |
295 | R.size[reg] := size |
- | |
296 | END Lock; |
- | |
297 | - | ||
298 | - | ||
299 | PROCEDURE Release* (VAR R: REGS; reg: INTEGER); |
- | |
300 | BEGIN |
- | |
301 | ASSERT(reg IN R.vregs); |
- | |
302 | R.offs[reg] := 0 |
- | |
303 | END Release; |
- | |
304 | - | ||
305 | - | ||
306 | PROCEDURE Load* (R: REGS; reg: INTEGER); |
- | |
307 | VAR |
- | |
308 | offs: INTEGER; |
- | |
309 | - | ||
310 | BEGIN |
- | |
311 | ASSERT(reg IN R.vregs); |
- | |
312 | offs := R.offs[reg]; |
- | |
313 | IF offs # 0 THEN |
- | |
314 | R.load(reg, offs, R.size[reg]) |
- | |
315 | END |
- | |
316 | END Load; |
- | |
317 | - | ||
318 | - | ||
319 | PROCEDURE Save* (R: REGS; reg: INTEGER); |
- | |
320 | VAR |
- | |
321 | offs: INTEGER; |
- | |
322 | - | ||
323 | BEGIN |
- | |
324 | ASSERT(reg IN R.vregs); |
- | |
325 | offs := R.offs[reg]; |
- | |
326 | IF offs # 0 THEN |
- | |
327 | R.save(reg, offs, R.size[reg]) |
- | |
328 | END |
- | |
329 | END Save; |
- | |
330 | - | ||
331 | - | ||
332 | PROCEDURE Store* (R: REGS); |
- | |
333 | VAR |
- | |
334 | i: INTEGER; |
- | |
335 | - | ||
336 | BEGIN |
- | |
337 | FOR i := 0 TO NVR - 1 DO |
- | |
338 | IF i IN R.vregs THEN |
- | |
339 | Save(R, i) |
- | |
340 | END |
- | |
341 | END |
- | |
342 | END Store; |
- | |
343 | - | ||
344 | - | ||
345 | PROCEDURE Restore* (R: REGS); |
- | |
346 | VAR |
- | |
347 | i: INTEGER; |
- | |
348 | - | ||
349 | BEGIN |
- | |
350 | FOR i := 0 TO NVR - 1 DO |
- | |
351 | IF i IN R.vregs THEN |
- | |
352 | Load(R, i) |
- | |
353 | END |
- | |
354 | END |
- | |
355 | END Restore; |
- | |
356 | - | ||
357 | - | ||
358 | PROCEDURE Reset* (VAR R: REGS); |
- | |
359 | VAR |
- | |
360 | i: INTEGER; |
- | |
361 | - | ||
362 | BEGIN |
- | |
363 | FOR i := 0 TO NVR - 1 DO |
- | |
364 | IF i IN R.vregs THEN |
- | |
365 | R.offs[i] := 0 |
- | |
366 | END |
- | |
367 | END |
- | |
368 | END Reset; |
- | |
369 | - | ||
370 | - | ||
371 | PROCEDURE GetVarReg* (R: REGS; offs: INTEGER): INTEGER; |
- | |
372 | VAR |
- | |
373 | i, res: INTEGER; |
- | |
374 | - | ||
375 | BEGIN |
- | |
376 | res := -1; |
- | |
377 | i := 0; |
- | |
378 | WHILE i < NVR DO |
- | |
379 | IF (i IN R.vregs) & (R.offs[i] = offs) THEN |
- | |
380 | res := i; |
- | |
381 | i := NVR |
- | |
382 | END; |
- | |
383 | INC(i) |
- | |
384 | END |
- | |
385 | - | ||
386 | RETURN res |
- | |
387 | END GetVarReg; |
- | |
388 | - | ||
389 | - | ||
390 | PROCEDURE GetAnyVarReg* (R: REGS): INTEGER; |
- | |
391 | VAR |
- | |
392 | i, res: INTEGER; |
- | |
393 | - | ||
394 | BEGIN |
- | |
395 | res := -1; |
- | |
396 | i := 0; |
- | |
397 | WHILE i < NVR DO |
- | |
398 | IF (i IN R.vregs) & (R.offs[i] = 0) THEN |
- | |
399 | res := i; |
- | |
400 | i := NVR |
- | |
401 | END; |
- | |
402 | INC(i) |
- | |
403 | END |
- | |
404 | - | ||
405 | RETURN res |
- | |
406 | END GetAnyVarReg; |
- | |
407 | 271 | ||
408 | - | ||
409 | PROCEDURE Init* (VAR R: REGS; push, pop: OP1; mov, xch: OP2; load, save: OP3; regs, vregs: SET); |
- | |
410 | VAR |
- | |
411 | i: INTEGER; |
272 | |
412 | 273 | PROCEDURE Init* (VAR R: REGS; push, pop: OP1; mov, xch: OP2; regs: SET); |
|
413 | BEGIN |
274 | BEGIN |
414 | R.regs := regs; |
275 | R.regs := regs; |
Line 415... | Line 276... | ||
415 | R.pushed := 0; |
276 | R.pushed := 0; |
416 | R.top := -1; |
277 | R.top := -1; |
417 | 278 | ||
418 | R.push := push; |
279 | R.push := push; |
419 | R.pop := pop; |
- | |
420 | R.mov := mov; |
- | |
421 | R.xch := xch; |
- | |
422 | R.load := load; |
- | |
423 | R.save := save; |
- | |
424 | - | ||
425 | R.vregs := vregs; |
- | |
426 | - | ||
427 | FOR i := 0 TO NVR - 1 DO |
- | |
428 | R.offs[i] := 0; |
- | |
429 | R.size[i] := 0 |
280 | R.pop := pop; |
Line 430... | Line 281... | ||
430 | END |
281 | R.mov := mov; |
431 | 282 | R.xch := xch; |