News for hackers. Stuff that matters.
Re:Five Tips to Writing RISC-V Assembly by 1vuio0pswjnm7 on Sunday May 23, 2021 @07:45PM (#27259685)
Re:Five Tips to Writing RISC-V Assembly by bombcar on Sunday May 23, 2021 @09:33PM (#27260310)
Understandable the architecture calling conventions are important - if registers are marked as destroyed you must treat them as such, even if in your code it seems they’re preserved.

Single-stepping debuggers have caused weird side effects in the past (the trap instruction coincidentally keeps a register with a “sane” value and so it’s not noticed that in normal operation it gets scrambled).

Re:Five Tips to Writing RISC-V Assembly by brucehoult on Tuesday May 25, 2021 @02:04AM (#27273284)
Note that the base RISC-V ISA (IMA extensions) doesn't say anything about calling conventions or functions (calls and returns) or even a stack. All X registers except X0 are interchangeable.

Which registers are caller save or callee save or even which is the stack pointer or function return address is all purely a software convention in a particular OS and/or compiler.

(the C extension gives greater program compression if used with an ABI that uses X1 as the Return Address and X2 as the Stack Pointer, and X8-X15 as the most commonly used registers, but even then nothing breaks if you don't)

Re:Five Tips to Writing RISC-V Assembly by dreamcompiler on Monday May 24, 2021 @11:52AM (#27265841)
This is imprecise wrt the point of view of caller vs callee.

> All a (argument) and t (temporary) registers must be considered destroyed after a function call. All s (saved) registers can be considered saved after a function call.

Who must do the considering here? The caller or the callee? I expect it's the caller because that makes the most sense, but I'd like to see it spelled out.

If my assumption is correct, that implies that callees are required to restore the s registers before returning but they are not required to restore a or t registers before returning. Correct?

Re:Five Tips to Writing RISC-V Assembly by pavehawk2007 on Monday May 24, 2021 @12:27PM (#27266327)
A and T are "caller saved", meaning that if I want their value after I make a function call, I, the caller, must save the registers. So,

li t0, 10 call somefunc # Must consider t0 destroyed here unless we save it first

The saved registers are different li s0, 10 call somefunc # Can consider s0 = 10 here.

However, if we use the s registers, we have to make sure we put it back the way we found it. So, before li s0, 10, I need to save the old value of s0.