74 changes: 67 additions & 7 deletions llvm/test/MC/RISCV/pcrel-fixups.s
Original file line number Diff line number Diff line change
Expand Up @@ -12,41 +12,101 @@
# RUN: | FileCheck --check-prefix RELAX %s

# Fixups for %pcrel_hi / %pcrel_lo can be evaluated within a section,
# regardless of the fragment containing the target address.
# regardless of the fragment containing the target address, provided symbol
# binding allows it.

function:
.Lpcrel_label1:
auipc a0, %pcrel_hi(other_function)
auipc a0, %pcrel_hi(local_function)
addi a1, a0, %pcrel_lo(.Lpcrel_label1)
# NORELAX: auipc a0, 0
# NORELAX-NOT: R_RISCV
# NORELAX: addi a1, a0, 16
# NORELAX-NOT: R_RISCV

# RELAX: auipc a0, 0
# RELAX: R_RISCV_PCREL_HI20 other_function
# RELAX: R_RISCV_PCREL_HI20 local_function
# RELAX: R_RISCV_RELAX *ABS*
# RELAX: addi a1, a0, 0
# RELAX: R_RISCV_PCREL_LO12_I .Lpcrel_label1
# RELAX: R_RISCV_RELAX *ABS*

.p2align 2 # Cause a new fragment be emitted here
.Lpcrel_label2:
auipc a0, %pcrel_hi(other_function)
auipc a0, %pcrel_hi(local_function)
addi a1, a0, %pcrel_lo(.Lpcrel_label2)
# NORELAX: auipc a0, 0
# NORELAX-NOT: R_RISCV
# NORELAX: addi a1, a0, 8
# NORELAX-NOT: R_RISCV

# RELAX: auipc a0, 0
# RELAX: R_RISCV_PCREL_HI20 other_function
# RELAX: R_RISCV_PCREL_HI20 local_function
# RELAX: R_RISCV_RELAX *ABS*
# RELAX: addi a1, a0, 0
# RELAX: R_RISCV_PCREL_LO12_I .Lpcrel_label2
# RELAX: R_RISCV_RELAX *ABS*

.type other_function,@function
other_function:
.type local_function,@function
local_function:
ret

# Check we correctly evaluate when fixups are in different fragments

.Lpcrel_label3:
auipc a0, %pcrel_hi(local_function)
.p2align 2 # Cause a new fragment be emitted here
addi a1, a0, %pcrel_lo(.Lpcrel_label3)
# NORELAX: auipc a0, 0
# NORELAX-NOT: R_RISCV
# NORELAX: addi a1, a0, -4
# NORELAX-NOT: R_RISCV

# RELAX: auipc a0, 0
# RELAX: R_RISCV_PCREL_HI20 local_function
# RELAX: R_RISCV_RELAX *ABS*
# RELAX: addi a1, a0, 0
# RELAX: R_RISCV_PCREL_LO12_I .Lpcrel_label3
# RELAX: R_RISCV_RELAX *ABS*

# Check handling of symbol binding.

.Lpcrel_label4:
auipc a0, %pcrel_hi(global_function)
addi a1, a0, %pcrel_lo(.Lpcrel_label4)
# NORELAX: auipc a0, 0
# NORELAX: R_RISCV_PCREL_HI20 global_function
# NORELAX: addi a1, a0, 0
# NORELAX: R_RISCV_PCREL_LO12_I .Lpcrel_label4

# RELAX: auipc a0, 0
# RELAX: R_RISCV_PCREL_HI20 global_function
# RELAX: R_RISCV_RELAX *ABS*
# RELAX: addi a1, a0, 0
# RELAX: R_RISCV_PCREL_LO12_I .Lpcrel_label4
# RELAX: R_RISCV_RELAX *ABS*

.Lpcrel_label5:
auipc a0, %pcrel_hi(weak_function)
addi a1, a0, %pcrel_lo(.Lpcrel_label5)
# NORELAX: auipc a0, 0
# NORELAX: R_RISCV_PCREL_HI20 weak_function
# NORELAX: addi a1, a0, 0
# NORELAX: R_RISCV_PCREL_LO12_I .Lpcrel_label5

# RELAX: auipc a0, 0
# RELAX: R_RISCV_PCREL_HI20 weak_function
# RELAX: R_RISCV_RELAX *ABS*
# RELAX: addi a1, a0, 0
# RELAX: R_RISCV_PCREL_LO12_I .Lpcrel_label5
# RELAX: R_RISCV_RELAX *ABS*

.global global_function
.type global_function,@function
global_function:
ret

.weak weak_function
.type weak_function,@function
weak_function:
ret
2 changes: 2 additions & 0 deletions llvm/test/MC/RISCV/pcrel-lo12-invalid.s
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,5 @@

1:
addi a0, a0, %pcrel_lo(1b) # CHECK: :[[@LINE]]:3: error: could not find corresponding %pcrel_hi
addi a0, a0, %pcrel_lo(0x123456) # CHECK: :[[@LINE]]:3: error: could not find corresponding %pcrel_hi
addi a0, a0, %pcrel_lo(foo) # CHECK: :[[@LINE]]:3: error: could not find corresponding %pcrel_hi
7 changes: 3 additions & 4 deletions llvm/test/MC/RISCV/rv32i-aliases-valid.s
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@
# CHECK-ALIAS....Match the alias (tests instr. to alias mapping)
# CHECK-EXPAND...Match canonical instr. unconditionally (tests alias expansion)

# Needed for testing valid %pcrel_lo expressions
.Lpcrel_hi0: auipc a0, %pcrel_hi(foo)

# CHECK-INST: addi a0, zero, 0
# CHECK-ALIAS: mv a0, zero
Expand Down Expand Up @@ -71,16 +73,13 @@ li x12, 0xFFFFFFFF

# CHECK-EXPAND: addi a0, zero, 1110
li a0, %lo(0x123456)
# CHECK-OBJ-NOALIAS: addi a0, zero, 0
# CHECK-OBJ: R_RISCV_PCREL_LO12
li a0, %pcrel_lo(0x123456)

# CHECK-OBJ-NOALIAS: addi a0, zero, 0
# CHECK-OBJ: R_RISCV_LO12
li a0, %lo(foo)
# CHECK-OBJ-NOALIAS: addi a0, zero, 0
# CHECK-OBJ: R_RISCV_PCREL_LO12
li a0, %pcrel_lo(foo)
li a0, %pcrel_lo(.Lpcrel_hi0)

.equ CONST, 0x123456
# CHECK-EXPAND: lui a0, 291
Expand Down
7 changes: 5 additions & 2 deletions llvm/test/MC/RISCV/rv32i-valid.s
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,9 @@

.equ CONST, 30

# Needed for testing valid %pcrel_lo expressions
.Lpcrel_hi0: auipc a0, %pcrel_hi(foo)

# CHECK-ASM-AND-OBJ: lui a0, 2
# CHECK-ASM: encoding: [0x37,0x25,0x00,0x00]
lui a0, 2
Expand Down Expand Up @@ -161,11 +164,11 @@ lw a0, 97(a2)
# CHECK-OBJ: lbu s5, 0(s6)
# CHECK-OBJ: R_RISCV_LO12
lbu s5, %lo(foo)(s6)
# CHECK-ASM: lhu t3, %pcrel_lo(foo)(t3)
# CHECK-ASM: lhu t3, %pcrel_lo(.Lpcrel_hi0)(t3)
# CHECK-ASM: encoding: [0x03,0x5e,0bAAAA1110,A]
# CHECK-OBJ: lhu t3, 0(t3)
# CHECK-OBJ: R_RISCV_PCREL_LO12
lhu t3, %pcrel_lo(foo)(t3)
lhu t3, %pcrel_lo(.Lpcrel_hi0)(t3)
# CHECK-ASM-AND-OBJ: lb t0, 30(t1)
# CHECK-ASM: encoding: [0x83,0x02,0xe3,0x01]
lb t0, CONST(t1)
Expand Down
8 changes: 4 additions & 4 deletions llvm/test/MC/RISCV/rv64i-aliases-valid.s
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,9 @@
# TODO ld
# TODO sd

# Needed for testing valid %pcrel_lo expressions
.Lpcrel_hi0: auipc a0, %pcrel_hi(foo)

# CHECK-INST: addi a0, zero, 0
# CHECK-ALIAS: mv a0, zero
li x10, 0
Expand Down Expand Up @@ -107,16 +110,13 @@ li t5, 0xFFFFFFFFFFFFFFFF

# CHECK-EXPAND: addi a0, zero, 1110
li a0, %lo(0x123456)
# CHECK-OBJ-NOALIAS: addi a0, zero, 0
# CHECK-OBJ: R_RISCV_PCREL_LO12
li a0, %pcrel_lo(0x123456)

# CHECK-OBJ-NOALIAS: addi a0, zero, 0
# CHECK-OBJ: R_RISCV_LO12
li a0, %lo(foo)
# CHECK-OBJ-NOALIAS: addi a0, zero, 0
# CHECK-OBJ: R_RISCV_PCREL_LO12
li a0, %pcrel_lo(foo)
li a0, %pcrel_lo(.Lpcrel_hi0)

.equ CONST, 0x123456
# CHECK-EXPAND: lui a0, 291
Expand Down