Semantics of register actions Author: Markus Mock Written: March 4, 1996 Last Update: March 6, 1996 Changelog: -------------------------------------------------- RTC run time constant NIY not implemented yey -------------------------------------------------- 1. RA_REMOVE Purpose: directs the stitcher to remove an instruction (eg a load) either unconditionally (second field = 0) or conditionally based on the value of some rtc. Typical use: check an rtc that hold some value n. If n is in some range remove the load for stack[n] (when stack[0] .. stack[k] are allocated in registers). Format: 0x16 ; ra code loop ; if 0 -> unconditional remove off ; loop off: table index of rtc to check for removal k ; 0 <= rtc <= k and remove will be done 0x0 ; unused Label; label pointing to instruction to be removed 0x0 ; unused 0x0 ; Example: ;directive starts .long 0x16; ; remove 16 .long 0x1 ; dyn const to check .long 0x18 ; .long 2 ; should be 0 .. 2 .long 0x0 .long LRA44.1 .long .long 0x0 Note: Currently the check if the remove is done is based on the constant k. This could instead be a pointer to a table where the decision really is made (in case not a preallocated number of registers is used but rather a more complex register allocation at stitch time were done). 2. RA_STORE Purpose: Insert a store at the currently written location Typical use: Used to store some register allocated stack values back to memory before leaving the dynamic region. Format: .long 0x17 ; register store .long sreg ; from reg sreg .long treg ; to P(treg) .long P ; offset P .long 0x0 .long label ; at instruction location label .long 0x0 .long 0x0 ; unconditional store for conditional store: .long 0x17 ; register store .long treg ; target register .long baseoff ; base offset .long offset ; offset relative to baseoff .long 0x0 ; .long label ; at instruction location label .long 0x0 .long 0x1 ; conditional store .long 0x17 ; register store .long loop ; rtc to check .long off ; at loop off .lonf 0x0 ; .long 0x0 ; .long label ; at instruction location label .long 0x0 .long default ; default source register Semantics: if rtc is within range generate stl reg(rtc), (baseoff + offset) (treg) otherwise stl default, (baseoff + offset)(treg) Examples: ; RA-directive .long 0x17 ; register store .long 20 ; from reg 20 .long 27 ; to reg (27) .long 0 ; offset 0 .long 0x0 .long LRA39.2 .long 0x0 .long 0x0 ; unconditional store For conditional store: ; RA-directive .long 0x17 ; register store .long 30 ; (sp) [r30 = sp] .long 0x10 ; array stack starts at 0x10(sp) .long 4 ; access stack[1] at 0x14(sp) .long 0x0 .long LRA39.2 .long 0x0 .long 0x1 ; conditional store ; RA-directive .long 0x17 ; register store .long 0x1 ; rtconst to check .long 0x1a ; .long 0 ; .long 0x0 .long LRA39.2 .long 0x0 .long 0x27 ; default reg assuming stack[0] .. stack[2] are mapped and rtc=3 stl r27, 0x14(sp) will be generated 3. RA_OP Purpose: rewrite an (integer) operation to adjust the register operands based on some rtcs. It replaces the operation pointed to by the label. Typical use: after getting rid of some loads and allocating some stack values in registers the operations have to be adjusted in order to have the values in the right registers. Format: .long 0x18 ; RA_OP .long loop1 ; dyn const to check .long off1 ; .long k ; .long 0x0 .long label .long .long 0x1 ; operand 1 .long 0x18; ; RA_OP .long loop2 ; dyn const to check .long off2 ; .long l ; .long 0x0 .long label .long .long 0x2 ; operand 2 ;directive starts .long 0x18 ; RA_OP .long loop3 ; dyn const to check .long off3 ; .long m ; should be 0 .. 2 .long 0x0 .long label .long .long 0x3 ; operand 3 semantics: adjust an operand 1 (2,3) if 0 <= rtc1 (2,3) <= k (l,m) Example: ;directive starts .long 0x18; ; OP operand 1 .long 0x1 ; dyn const to check .long 0x18 ; .long 2 ; should be 0 .. 2 .long 0x0 .long LRA44.6 .long .long 0x1 ; operand 1 ;directive starts .long 0x18; ; OP operand 2 .long 0x1 ; dyn const to check .long 0x19 ; .long 2 ; should be 0 .. 2 .long 0x0 .long LRA44.6 .long .long 0x2 ;directive starts .long 0x18; ; OP operand 3 .long 0x1 ; dyn const to check .long 0x19 ; .long 2 ; should be 0 .. 2 .long 0x0 .long LRA44.6 .long .long 0x3 4. RA_MOVE Purpose: Replace a store (stl) instruction by a register move usually based on the value of some rtc. Typical Use: Replace a load from memory with a register move if a particular stack location is register allocated. Format: a) Conditional move a.1 .long 0x19 ; RA_MOVE .long loop1 ; dyn const to check .long off1 ; for dest .long k ; 0 <= rtc1 <= k .long 0x0 .long label .long .long 0x1 ; move is conditional or .long 0x19 ; RA_MOVE .long ? .long ? .long 255 ; destination is static .long 0x0 .long label .long .long treg ; target register a.2 .long 0x19 ; move .long loop2 ; dyn const to check .long off2 ; .long l ; 0 <= rtc2 <= l .long 0x0 .long label .long .long sreg ; default source register Semantics: give a stl r1, p(r2): 1. if 0 <= rtc1 <= k then replace the stl by a move otherwise leave in place as the destination is not register allocated in case k=255 then the move is done but the target register ist fixed (treg) 2. (given 1) if 0 <= rtc2 <= l generate move regmap[rtc2] regmap[rtc1] else generate move sreg regmap[rtc1] where regmap[i] is the register corresponding to the constant i. Currently there is a fixed register allocation/mapping table of the reserved registers. Example: ;directive starts 44.7 .long 0x19 ; move .long 0x1 ; dyn const to check .long 0x1a ; for dest .long 2 ; should be 0 .. 2 .long 0x0 .long LRA44.7 .long .long 0x1 ; move is conditional ;directive starts 44.7 ; destination ok find out where source .long 0x19 ; move .long 0x1 ; dyn const to check .long 0x19 ; .long 2 ; should be 0 .. 2 .long 0x0 .long LRA44.7 .long .long 24 ; default register LRA44.7: .line 44 stl r24,0(r27) assuming rtc(1,1a) = 1 rtc(1,19) = 2 regmap[1] = 19 regmap[2] = 18 would result in move r18, r19 assuming rtc(1,1a) = 1 rtc(1,19) = 3 regmap[1] = 19 move r24, r19 b) Unconditional move .long 0x19; ; register move 19 .long sreg ; source register sreg .long treg ; target register treg .long 0x0 ; .long 0x0 .long label .long 0x0 .long 0x0 ; unconditional move generate a move sreg, treg Example: .long 0x19; ; register move 19 .long 20 ; from reg 20 .long 2 ; to reg 2 .long 0x0 ; .long 0x0 .long LRA39.1 .long 0x0 .long 0x0 ; unconditional move generates: move r20, r2 5. RA_LOAD Purpose: Insert a load instruction Typical use: E.g. for initialization of register allocated stack values: make sure initital values on the stack are copied into the registers first Format: .long 0x1a ; RA_LOAD .long reg .long baseoff .long offset ; generate ldl rreg, (baseoff+offset)(sp) .long 0x0 .long label .long .long 0x0 Example: .long 0x1a ; RA_LOAD .long 20 .long 0x10 .long 0 ; stack[0] in r20 .long 0x0 .long DYN_BEGIN._eval$2rtc_anchor.0 .long .long 0x0 6. RA_COND_LDA Purpose: ldas that are used to build addressed for loads that are removed should also be marked for removal with this directive. Typical use: change standard lda_hole directives to ra_cond_lda directive if the lda is only used to build an address for a load that wil be removed with a conditional removed based on a rtc. Note: This could be done with a ra_remove directive too so it is in fact not strictly necessary. Format: ;directive starts .long 0x1b ; ra_cond_lda .long loop .long off ; rtc location .long 0x0 .long 0x0 .long label .long .long k ; remove lda if 0 <= rtc <= k Example: ;directive starts .long 0x1b ; ra_cond_lda .long 0x1 .long 0x1a .long 0x0 .long 0x0 .long template_instr$LOOP1OFF26.14 .long .long 2