Hi everybody,
I am creating an llvm backend for a custom architecture, and I am struggling
with the generation of a 'call to register', used when doing a call
through a function pointer.
The problem is the following:
- the architecture uses a link register R15 for function calls.
- But, it has no special 'branch and link' instruction that accepts a
register destination.
I try to implement this by replacing a call to register by:
- splitting the basic block around the call.
- replacing the call (which is at the end of the first basic block) with :
-- Loading the link register with the address of the new basic block
-- and generating a 'CALL_R' which in the end results in a 'branch
to register'
(but, for llvm, it is treated as a call)
So:
__BB_2:
...
call_to_reg Rx
...
results in:
__BB_2:
...
load_immediate R15, __BB_3
branch_to_reg Rx
__BB_3:
...
where __BB_2 falls through to __BB__3
This works when the optimization level is low.
At higher optimization levels I am observing the following :
load_immediate R15, __BB_3
branch_to_reg Rx
__BB_3:
branch_to __BB_22
is converted into
load_immediate R15, "__BB_-1" // basic block 3 was removed
branch_to_reg Rx
__BB_22:
...
How do I learn my backend that, when the successor of __BB_2 changes,
that it also needs to update the 'load_immediate' with the new successor
?
(Or maybe, there is a different way to achieve this ?)
Thanks,
Jeroen Dobbelaere