CALL
only takes a relative address (a label) and automatically saves the current PC
(later used to calculate the return address) into %o7
. JMPL
on the other hand only takes an absolute address in a register, and can store the current PC
in an arbitrary register.
The function calling convention is the same in both cases. CALL
is more convenient for labels and JMPL
for function pointers. The latter can be used to emulate the former by loading the target address into a register first.
As for returning, both RET
and RETL
are synthetic instructions that will be turned into a JMPL
by the assembler, using the correct return register: RET
becomes JMPL %i7+8,%g0
and RETL
becomes JMPL %o7+8,%g0
. RET
assumes you have set up a new register window (thus the original %o7
is now %i7
) and you should follow it with a RESTORE
instruction in the delay slot.
Update:
The RETURN
instruction has apparently been introduced in sparc v9, and it combines a JMPL
(having second operand %g0
) and a RESTORE
(with no operands). As such it can be conveniently used to end a non-leaf function, where you would normally use a RET; RESTORE
pair.