RESTORE u[, dst1 [, dst2 [, ...]]] # jr=0 implied |
nanoMIPS, availability varies by format. |
Restore callee saved registers/Restore callee saved registers and Jump to Return address, |
RESTORE.JRC u[, dst1 [, dst2 [, ...]]] # jr=1 implied |
nanoMIPS, availability varies by format. |
Restore callee saved registers/Restore callee saved registers and Jump to Return address, |
Restore callee saved registers/Restore callee saved registers and Jump to Return address,Compact. Restore registers dst1, [dst2,...]from addresses at the top of the local stack frame ($29 +
u - 4, $29 + u - 8, ...), then point register $29 back to the caller’s stack frame by adding offset u. For RESTORE.JRC, return from the current subroutine by jumping to the address in $31.
nanoMIPS, availability varies by format.
100000 |
rt |
0 |
count |
0011 |
u[11:3] |
gp |
10 |
6 |
5 |
1 |
4 |
4 |
9 |
1 |
2 |
jr = 0
000111 |
rt1 |
1 |
u[7:4] |
count |
6 |
1 |
1 |
4 |
4 |
rt = 30 if rt1 == 0 else 31 gp = 0 jr = 1
100000 |
rt |
0 |
count |
0011 |
u[11:3] |
gp |
11 |
6 |
5 |
1 |
4 |
4 |
9 |
1 |
2 |
jr = 1
if gp and C0.Config5.NMS: raise exception('RI') i = 0 while i != count: this_rt = ( 28 if gp and (i + 1 == count) else rt + i if rt + i < 32 else rt + i - 16 ) this_offset = u - ( (i+1) << 2 ) va = effective_address(GPR[29], this_offset, 'Load') if va & 3: raise exception('ADEL', badva=va) data = read_memory_at_va(va, nbytes=4) GPR[this_rt] = sign_extend(data, from_nbits=32) if this_rt == 29: raise UNPREDICTABLE() i += 1 GPR[29] = effective_address(GPR[29], u) if jr: CPU.next_pc = GPR[31]
The purpose of the RESTORE and RESTORE.JRC instructions is to restore callee saved registers from the stack on exit from a subroutine, adjust the stack pointer register $29 to point to the caller’s stack
frame, and for RESTORE.JRC to return from the subroutine by jumping to the address in register $31. RESTORE/RESTORE.JRC will usually be paired with a matching SAVE instruction at the start of the
subroutine, and SAVE and RESTORE take the same arguments.
The arguments for RESTORE/RESTORE.JRC consist of the amount to increment the stack by, and a list of registers to restore from to the stack. The increment is a double word aligned immediate value u
in the range 0 to 4092. The register list can contain up to 16 consecutive registers. The count of the number of registers is encoded in the instruction’s count field. The first register in the list is encoded
in the rt field of the instruction.
The register list is allowed to wrap around from register $31 back to register $16 and still be considered consecutive; this allows fp ($30) and ra ($31) and the saved temporary registers s0-s7 ($16 - $23) to
be restored in one instruction.
Additionally, $28 (the global pointer register) will be used in place of last register in the sequence if the ’gp’ bit in the instruction encoding is set. This feature (which is not available for NMS cores) makes it
possible to treat $28 as a callee saved register for environments such as Linux which require it.
The restored registers are read from memory addresses $29+ u -4, $29 + u -8, $29 + u -12,... etc,i.e. at the top of the local stack frame. The stack pointer is then adjusted by adding the size u of
the local stack frame, so that it points back to the caller’s stack frame.
RESTORE.JRC with count=0 adjusts the stack pointer and jumps to the address in $31, but does not restore any registers from memory.Thus the RESTORE.JRC[16]instruction format can be used to
provide ADDIU $29, $29,u; JRC $31 behavior using a single 16 bit instruction.
The result of a RESTORE instruction is UNPREDICTABLE if the register list includes register $29.
RESTORE/RESTORE.JRC must be implemented in such a way as to make the instructions restartable,
butthe implementation does not need to be fully atomic.Forinstance,itis allowable for a RESTORE/RESTORE.JRC instruction to be aborted by an exception after a subset of the register updates
have occurred. To ensure restartability, the write to GPR $29 and the jump (for RESTORE.JRC) must be completed atomically, that is, the instruction must graduate if and only if those writes occur.
Address Error. Bus Error. Reserved Instruction for gp=1 cases on NMS cores. TLB Invalid. TLB Read Inhibit. TLB Refill. Watch.