]> git.ipfire.org Git - thirdparty/gcc.git/commit
RISC-V: far-branch: Handle far jumps and branches for functions larger than 1MB
authorAndrew Waterman <andrew@sifive.com>
Tue, 10 Oct 2023 18:34:04 +0000 (12:34 -0600)
committerJeff Law <jlaw@ventanamicro.com>
Tue, 10 Oct 2023 22:10:30 +0000 (16:10 -0600)
commit71f906498ada9ec2780660b03bd6e27a93ad350c
tree4ac244ad959572f39c2d8da42577f724423f238c
parentbd5719bd7f7cb23e5ed96a1f1a28efbb3dec4a31
RISC-V: far-branch: Handle far jumps and branches for functions larger than 1MB

On RISC-V, branches further than +/-1MB require a longer instruction
sequence (3 instructions): we can reuse the jump-construction in the
assmbler (which clobbers $ra) and a temporary to set up the jump
destination.

gcc/ChangeLog:

* config/riscv/riscv.cc (struct machine_function): Track if a
far-branch/jump is used within a function (and $ra needs to be
saved).
(riscv_print_operand): Implement 'N' (inverse integer branch).
(riscv_far_jump_used_p): Implement.
(riscv_save_return_addr_reg_p): New function.
(riscv_save_reg_p): Use riscv_save_return_addr_reg_p.
* config/riscv/riscv.h (FIXED_REGISTERS): Update $ra.
(CALL_USED_REGISTERS): Update $ra.
* config/riscv/riscv.md: Add new types "ret" and "jalr".
(length attribute): Handle long conditional and unconditional
branches.
(conditional branch pattern): Handle case where jump can not
reach the intended target.
(indirect_jump, tablejump): Use new "jalr" type.
(simple_return): Use new "ret" type.
(simple_return_internal, eh_return_internal): Likewise.
(gpr_restore_return, riscv_mret): Likewise.
(riscv_uret, riscv_sret): Likewise.
* config/riscv/generic.md (generic_branch): Also recognize jalr & ret
types.
* config/riscv/sifive-7.md (sifive_7_jump): Likewise.

Co-authored-by: Philipp Tomsich <philipp.tomsich@vrull.eu>
Co-authored-by: Jeff Law <jlaw@ventanamicro.com>
gcc/config/riscv/generic.md
gcc/config/riscv/riscv.cc
gcc/config/riscv/riscv.h
gcc/config/riscv/riscv.md
gcc/config/riscv/sifive-7.md