[PATCH] RISC-V: Fixed missed GOT relocation against a symbol that has a defined value

Nelson Chu nelson@rivosinc.com
Thu Sep 4 08:44:12 GMT 2025


Committed, thanks.

Nelson

On Thu, Aug 14, 2025 at 12:01 PM Nelson Chu <nelson@rivosinc.com> wrote:

> SImilar to aarch64, commit eac4eb8ecb26
>
> There are two problems when GOT relocation against a symbol that has a
> defined
> value,
> 1. Pesudo la with pic and pseudo lga lost the relocations.
> 2. %got_pcrel_hi generates R_RISCV_GOT_HI20 with addend, which is wrong
> since
>    commit 50331d64f108.
>
> The solution is to use deferred_expression for GOT relocation.  Maybe other
> relocations also have same problem and need the deferred_expression, but
> we can
> add in the future patches.
> ---
>  gas/config/tc-riscv.c                 | 85 +++++++++++++++------------
>  gas/testsuite/gas/riscv/force_reloc.d | 47 +++++++++++++++
>  gas/testsuite/gas/riscv/force_reloc.s | 22 +++++++
>  3 files changed, 117 insertions(+), 37 deletions(-)
>  create mode 100644 gas/testsuite/gas/riscv/force_reloc.d
>  create mode 100644 gas/testsuite/gas/riscv/force_reloc.s
>
> diff --git a/gas/config/tc-riscv.c b/gas/config/tc-riscv.c
> index 8a3356888d2..df60c206b82 100644
> --- a/gas/config/tc-riscv.c
> +++ b/gas/config/tc-riscv.c
> @@ -2518,13 +2518,16 @@ parse_relocation (char **str,
> bfd_reloc_code_real_type *reloc,
>  }
>
>  static void
> -my_getExpression (expressionS *ep, char *str)
> +my_getExpression (expressionS *ep, char *str, bool defer)
>  {
>    char *save_in;
>
>    save_in = input_line_pointer;
>    input_line_pointer = str;
> -  expression (ep);
> +  if (defer)
> +    deferred_expression (ep);
> +  else
> +    expression (ep);
>    expr_parse_end = input_line_pointer;
>    input_line_pointer = save_in;
>  }
> @@ -2543,6 +2546,7 @@ my_getSmallExpression (expressionS *ep,
> bfd_reloc_code_real_type *reloc,
>    size_t reloc_index;
>    unsigned crux_depth, str_depth;
>    bool orig_probing = probing_insn_operands;
> +  bool force_reloc = false;
>    char *crux;
>
>    /* Search for the start of the main expression.
> @@ -2582,7 +2586,10 @@ my_getSmallExpression (expressionS *ep,
> bfd_reloc_code_real_type *reloc,
>    if (str_depth || reloc_index)
>      probing_insn_operands = false;
>
> -  my_getExpression (ep, crux);
> +  if (*reloc == BFD_RELOC_RISCV_GOT_HI20)
> +    force_reloc = true;
> +
> +  my_getExpression (ep, crux, force_reloc);
>    str = expr_parse_end;
>
>    probing_insn_operands = orig_probing;
> @@ -2674,7 +2681,7 @@ my_getVsetvliExpression (expressionS *ep, char *str)
>      }
>    else
>      {
> -      my_getExpression (ep, str);
> +      my_getExpression (ep, str, false/* defer */);
>        str = expr_parse_end;
>      }
>  }
> @@ -2727,7 +2734,7 @@ my_getThVsetvliExpression (expressionS *ep, char
> *str)
>      }
>    else
>      {
> -      my_getExpression (ep, str);
> +      my_getExpression (ep, str, false/* defer */);
>        str = expr_parse_end;
>      }
>  }
> @@ -2851,6 +2858,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>    error.missing_ext = NULL;
>    /* Indicate we are assembling instruction with CSR.  */
>    bool insn_with_csr = false;
> +  bool force_reloc = false;
>
>    /* Parse the name of the instruction.  Terminate the string if
> whitespace
>       is found so that str_hash_find only sees the name part of the
> string.  */
> @@ -3353,7 +3361,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                   continue;
>
>                 case 'i': /* vector arith signed immediate */
> -                 my_getExpression (imm_expr, asarg);
> +                 my_getExpression (imm_expr, asarg, force_reloc);
>                   check_absolute_expr (ip, imm_expr, FALSE);
>                   if (imm_expr->X_add_number > 15
>                       || imm_expr->X_add_number < -16)
> @@ -3365,7 +3373,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                   continue;
>
>                 case 'j': /* vector arith unsigned immediate */
> -                 my_getExpression (imm_expr, asarg);
> +                 my_getExpression (imm_expr, asarg, force_reloc);
>                   check_absolute_expr (ip, imm_expr, FALSE);
>                   if (imm_expr->X_add_number < 0
>                       || imm_expr->X_add_number >= 32)
> @@ -3377,7 +3385,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                   continue;
>
>                 case 'k': /* vector arith signed immediate, minus 1 */
> -                 my_getExpression (imm_expr, asarg);
> +                 my_getExpression (imm_expr, asarg, force_reloc);
>                   check_absolute_expr (ip, imm_expr, FALSE);
>                   if (imm_expr->X_add_number > 16
>                       || imm_expr->X_add_number < -15)
> @@ -3389,7 +3397,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                   continue;
>
>                 case 'l': /* 6-bit vector arith unsigned immediate */
> -                 my_getExpression (imm_expr, asarg);
> +                 my_getExpression (imm_expr, asarg, force_reloc);
>                   check_absolute_expr (ip, imm_expr, FALSE);
>                   if (imm_expr->X_add_number < 0
>                       || imm_expr->X_add_number >= 64)
> @@ -3453,7 +3461,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>               break;
>
>             case '<': /* Shift amount, 0 - 31.  */
> -             my_getExpression (imm_expr, asarg);
> +             my_getExpression (imm_expr, asarg, force_reloc);
>               check_absolute_expr (ip, imm_expr, false);
>               if ((unsigned long) imm_expr->X_add_number > 31)
>                 as_bad (_("improper shift amount (%"PRIu64")"),
> @@ -3464,7 +3472,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>               continue;
>
>             case '>': /* Shift amount, 0 - (XLEN-1).  */
> -             my_getExpression (imm_expr, asarg);
> +             my_getExpression (imm_expr, asarg, force_reloc);
>               check_absolute_expr (ip, imm_expr, false);
>               if ((unsigned long) imm_expr->X_add_number >= xlen)
>                 as_bad (_("improper shift amount (%"PRIu64")"),
> @@ -3475,7 +3483,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>               continue;
>
>             case 'Z': /* CSRRxI immediate.  */
> -             my_getExpression (imm_expr, asarg);
> +             my_getExpression (imm_expr, asarg, force_reloc);
>               check_absolute_expr (ip, imm_expr, false);
>               if ((unsigned long) imm_expr->X_add_number > 31)
>                 as_bad (_("improper CSRxI immediate (%"PRIu64")"),
> @@ -3492,7 +3500,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                 INSERT_OPERAND (CSR, *ip, regno);
>               else
>                 {
> -                 my_getExpression (imm_expr, asarg);
> +                 my_getExpression (imm_expr, asarg, force_reloc);
>                   check_absolute_expr (ip, imm_expr, true);
>                   if ((unsigned long) imm_expr->X_add_number > 0xfff)
>                     as_bad (_("improper CSR address (%"PRIu64")"),
> @@ -3591,7 +3599,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>               break;
>
>             case 'I':
> -             my_getExpression (imm_expr, asarg);
> +             my_getExpression (imm_expr, asarg, force_reloc);
>               if (imm_expr->X_op != O_big
>                   && imm_expr->X_op != O_constant)
>                 break;
> @@ -3600,7 +3608,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>               continue;
>
>             case 'A':
> -             my_getExpression (imm_expr, asarg);
> +             my_getExpression (imm_expr, asarg, force_reloc);
>               normalize_constant_expr (imm_expr);
>               /* The 'A' format specifier must be a symbol.  */
>               if (imm_expr->X_op != O_symbol)
> @@ -3610,7 +3618,10 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>               continue;
>
>             case 'B':
> -             my_getExpression (imm_expr, asarg);
> +             if (ip->insn_mo->mask == M_LGA
> +                 || (riscv_opts.pic && ip->insn_mo->mask == M_LA))
> +               force_reloc = true;
> +             my_getExpression (imm_expr, asarg, force_reloc);
>               normalize_constant_expr (imm_expr);
>               /* The 'B' format specifier must be a symbol or a constant.
> */
>               if (imm_expr->X_op != O_symbol && imm_expr->X_op !=
> O_constant)
> @@ -3662,7 +3673,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>             case 'p': /* PC-relative offset.  */
>             branch:
>               *imm_reloc = BFD_RELOC_12_PCREL;
> -             my_getExpression (imm_expr, asarg);
> +             my_getExpression (imm_expr, asarg, force_reloc);
>               asarg = expr_parse_end;
>               continue;
>
> @@ -3685,13 +3696,13 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>
>             case 'a': /* 20-bit PC-relative offset.  */
>             jump:
> -             my_getExpression (imm_expr, asarg);
> +             my_getExpression (imm_expr, asarg, force_reloc);
>               asarg = expr_parse_end;
>               *imm_reloc = BFD_RELOC_RISCV_JMP;
>               continue;
>
>             case 'c':
> -             my_getExpression (imm_expr, asarg);
> +             my_getExpression (imm_expr, asarg, force_reloc);
>               asarg = expr_parse_end;
>               if (strcmp (asarg, "@plt") == 0)
>                 asarg += 4;
> @@ -3792,7 +3803,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>               break;
>
>             case 'y': /* bs immediate */
> -             my_getExpression (imm_expr, asarg);
> +             my_getExpression (imm_expr, asarg, force_reloc);
>               check_absolute_expr (ip, imm_expr, FALSE);
>               if ((unsigned long)imm_expr->X_add_number > 3)
>                 as_bad(_("Improper bs immediate (%lu)"),
> @@ -3803,7 +3814,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>               continue;
>
>             case 'Y': /* rnum immediate */
> -             my_getExpression (imm_expr, asarg);
> +             my_getExpression (imm_expr, asarg, force_reloc);
>               check_absolute_expr (ip, imm_expr, FALSE);
>               if ((unsigned long)imm_expr->X_add_number > 10)
>                 as_bad(_("Improper rnum immediate (%lu)"),
> @@ -3833,7 +3844,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                          pseudo S-type but lower 5-bits zero.  */
>                       if (riscv_handle_implicit_zero_offset (imm_expr,
> asarg))
>                         continue;
> -                     my_getExpression (imm_expr, asarg);
> +                     my_getExpression (imm_expr, asarg, force_reloc);
>                       check_absolute_expr (ip, imm_expr, false);
>                       if (((unsigned) (imm_expr->X_add_number) & 0x1fU)
>                           || imm_expr->X_add_number >= RISCV_IMM_REACH / 2
> @@ -4025,7 +4036,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                         s = strtol (oparg + 1, (char **)&oparg, 10);
>                         oparg--;
>
> -                       my_getExpression (imm_expr, asarg);
> +                       my_getExpression (imm_expr, asarg, force_reloc);
>                         check_absolute_expr (ip, imm_expr, false);
>                         if (!sign)
>                           {
> @@ -4053,7 +4064,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                   switch (*++oparg)
>                     {
>                       case '2':
> -                       my_getExpression (imm_expr, asarg);
> +                       my_getExpression (imm_expr, asarg, force_reloc);
>                         check_absolute_expr (ip, imm_expr, FALSE);
>                         asarg = expr_parse_end;
>                         if (imm_expr->X_add_number<0
> @@ -4063,7 +4074,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                             |= ENCODE_CV_IS2_UIMM5
> (imm_expr->X_add_number);
>                           continue;
>                       case '3':
> -                       my_getExpression (imm_expr, asarg);
> +                       my_getExpression (imm_expr, asarg, force_reloc);
>                         check_absolute_expr (ip, imm_expr, FALSE);
>                         asarg = expr_parse_end;
>                         if (imm_expr->X_add_number < 0
> @@ -4073,7 +4084,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                             |= ENCODE_CV_IS3_UIMM5
> (imm_expr->X_add_number);
>                         continue;
>                       case '4':
> -                       my_getExpression (imm_expr, asarg);
> +                       my_getExpression (imm_expr, asarg, force_reloc);
>                         check_absolute_expr (ip, imm_expr, FALSE);
>                         asarg = expr_parse_end;
>                         if (imm_expr->X_add_number < -16
> @@ -4083,7 +4094,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                             |= ENCODE_CV_IS2_UIMM5
> (imm_expr->X_add_number);
>                         continue;
>                       case '5':
> -                       my_getExpression (imm_expr, asarg);
> +                       my_getExpression (imm_expr, asarg, force_reloc);
>                         check_absolute_expr (ip, imm_expr, FALSE);
>                         asarg = expr_parse_end;
>                         if (imm_expr->X_add_number < -32
> @@ -4093,7 +4104,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                             |= ENCODE_CV_SIMD_IMM6
> (imm_expr->X_add_number);
>                         continue;
>                       case '6':
> -                       my_getExpression (imm_expr, asarg);
> +                       my_getExpression (imm_expr, asarg, force_reloc);
>                         check_absolute_expr (ip, imm_expr, FALSE);
>                         asarg = expr_parse_end;
>                         if (imm_expr->X_add_number < 0
> @@ -4103,7 +4114,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                             |= ENCODE_CV_BITMANIP_UIMM5
> (imm_expr->X_add_number);
>                         continue;
>                       case '7':
> -                       my_getExpression (imm_expr, asarg);
> +                       my_getExpression (imm_expr, asarg, force_reloc);
>                         check_absolute_expr (ip, imm_expr, FALSE);
>                         asarg = expr_parse_end;
>                         if (imm_expr->X_add_number < 0
> @@ -4113,7 +4124,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                             |= ENCODE_CV_BITMANIP_UIMM2
> (imm_expr->X_add_number);
>                         continue;
>                       case '8':
> -                       my_getExpression (imm_expr, asarg);
> +                       my_getExpression (imm_expr, asarg, force_reloc);
>                         check_absolute_expr (ip, imm_expr, FALSE);
>                         asarg = expr_parse_end;
>                         ++oparg;
> @@ -4194,7 +4205,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                   switch (*++oparg)
>                     {
>                     case '@': /* hint 0 - 31.  */
> -                     my_getExpression (imm_expr, asarg);
> +                     my_getExpression (imm_expr, asarg, force_reloc);
>                       check_absolute_expr (ip, imm_expr, FALSE);
>                       if ((unsigned long)imm_expr->X_add_number > 31)
>                         as_bad(_("Improper hint amount (%lu)"),
> @@ -4205,7 +4216,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                       continue;
>
>                     case '#': /* immediate 0 - 511.  */
> -                     my_getExpression (imm_expr, asarg);
> +                     my_getExpression (imm_expr, asarg, force_reloc);
>                       check_absolute_expr (ip, imm_expr, FALSE);
>                       if ((unsigned long)imm_expr->X_add_number > 511)
>                         as_bad(_("Improper immediate amount (%lu)"),
> @@ -4216,7 +4227,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                       continue;
>
>                     case '$': /* LDP offset 0 to (1<<7)-8.  */
> -                     my_getExpression (imm_expr, asarg);
> +                     my_getExpression (imm_expr, asarg, force_reloc);
>                       check_absolute_expr (ip, imm_expr, FALSE);
>                       if ((unsigned long)imm_expr->X_add_number >= (1 << 7)
>                           || ((unsigned long)imm_expr->X_add_number & 0x7)
> != 0)
> @@ -4229,7 +4240,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                       continue;
>
>                     case '%': /* LWP offset 0 to (1<<7)-4.  */
> -                     my_getExpression (imm_expr, asarg);
> +                     my_getExpression (imm_expr, asarg, force_reloc);
>                       check_absolute_expr (ip, imm_expr, FALSE);
>                       if ((unsigned long)imm_expr->X_add_number >= (1 << 7)
>                           || ((unsigned long)imm_expr->X_add_number & 0x3)
> != 0)
> @@ -4242,7 +4253,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                       continue;
>
>                     case '^': /* SDP offset 0 to (1<<7)-8.  */
> -                     my_getExpression (imm_expr, asarg);
> +                     my_getExpression (imm_expr, asarg, force_reloc);
>                       check_absolute_expr (ip, imm_expr, FALSE);
>                       if ((unsigned long)imm_expr->X_add_number >= (1 << 7)
>                           || ((unsigned long)imm_expr->X_add_number & 0x7)
> != 0)
> @@ -4257,7 +4268,7 @@ riscv_ip (char *str, struct riscv_cl_insn *ip,
> expressionS *imm_expr,
>                       continue;
>
>                     case '&': /* SWP offset 0 to (1<<7)-4.  */
> -                     my_getExpression (imm_expr, asarg);
> +                     my_getExpression (imm_expr, asarg, force_reloc);
>                       check_absolute_expr (ip, imm_expr, FALSE);
>                       if ((unsigned long)imm_expr->X_add_number >= (1 << 7)
>                           || ((unsigned long)imm_expr->X_add_number & 0x3)
> != 0)
> @@ -4613,7 +4624,7 @@ bool riscv_parse_name (const char *name, struct
> expressionS *ep,
>    if (!probing_insn_operands)
>      return false;
>
> -  gas_assert (mode == expr_normal);
> +  gas_assert (mode == expr_normal || expr_defer_p (mode));
>
>    regno = reg_lookup_internal (name, RCLASS_GPR);
>    if (regno == -1u)
> diff --git a/gas/testsuite/gas/riscv/force_reloc.d
> b/gas/testsuite/gas/riscv/force_reloc.d
> new file mode 100644
> index 00000000000..df37a60d203
> --- /dev/null
> +++ b/gas/testsuite/gas/riscv/force_reloc.d
> @@ -0,0 +1,47 @@
> +#as:
> +#objdump: -dr -Mnumeric,no-aliases
> +
> +.*:[   ]+file format .*
> +
> +
> +Disassembly of section .text:
> +
> +0+ <_start>:
> +[      ]+0:[   ]+[0-9a-f]+[    ]+auipc[        ]+x1,0x0
> +[      ]+0:[   ]+R_RISCV_GOT_HI20[     ]+sym_abs_before
> +[      ]+0:[   ]+R_RISCV_RELAX.*
> +[      ]+4:[   ]+[0-9a-f]+[    ]+(lw|ld)[      ]+x1,0\(x1\) # 0 .*
> +[      ]+4:[   ]+R_RISCV_PCREL_LO12_I[         ]+.L0.*
> +[      ]+4:[   ]+R_RISCV_RELAX.*
> +[      ]+8:[   ]+[0-9a-f]+[    ]+auipc[        ]+x2,0x0
> +[      ]+8:[   ]+R_RISCV_GOT_HI20[     ]+sym_abs_before
> +[      ]+8:[   ]+R_RISCV_RELAX.*
> +[      ]+c:[   ]+[0-9a-f]+[    ]+(lw|ld)[      ]+x2,0\(x2\) # 8 .*
> +[      ]+c:[   ]+R_RISCV_PCREL_LO12_I[         ]+.L0.*
> +[      ]+c:[   ]+R_RISCV_RELAX.*
> +
> +0+10 <.L1>:
> +[      ]+10:[  ]+[0-9a-f]+[    ]+auipc[        ]+x3,0x0
> +[      ]+10:[  ]+R_RISCV_GOT_HI20[     ]+sym_abs_before
> +[      ]+14:[  ]+[0-9a-f]+[    ]+addi[         ]+x3,x3,0 # 10 .*
> +[      ]+14:[  ]+R_RISCV_PCREL_LO12_I[         ]+.L1.*
> +[      ]+14:[  ]+R_RISCV_RELAX.*
> +[      ]+18:[  ]+[0-9a-f]+[    ]+auipc[        ]+x4,0x0
> +[      ]+18:[  ]+R_RISCV_GOT_HI20[     ]+sym_abs_after
> +[      ]+18:[  ]+R_RISCV_RELAX.*
> +[      ]+1c:[  ]+[0-9a-f]+[    ]+(lw|ld)[      ]+x4,0\(x4\) # 18 .*
> +[      ]+1c:[  ]+R_RISCV_PCREL_LO12_I[         ]+.L0.*
> +[      ]+1c:[  ]+R_RISCV_RELAX.*
> +[      ]+20:[  ]+[0-9a-f]+[    ]+auipc[        ]+x5,0x0
> +[      ]+20:[  ]+R_RISCV_GOT_HI20[     ]+sym_abs_after
> +[      ]+20:[  ]+R_RISCV_RELAX.*
> +[      ]+24:[  ]+[0-9a-f]+[    ]+(lw|ld)[      ]+x5,0\(x5\) # 20 .*
> +[      ]+24:[  ]+R_RISCV_PCREL_LO12_I[         ]+.L0.*
> +[      ]+24:[  ]+R_RISCV_RELAX.*
> +
> +0+28 <.L2>:
> +[      ]+28:[  ]+[0-9a-f]+[    ]+auipc[        ]+x6,0x0
> +[      ]+28:[  ]+R_RISCV_GOT_HI20[     ]+sym_abs_after
> +[      ]+2c:[  ]+[0-9a-f]+[    ]+addi[         ]+x6,x6,0 # 28 .*
> +[      ]+2c:[  ]+R_RISCV_PCREL_LO12_I[         ]+.L2.*
> +[      ]+2c:[  ]+R_RISCV_RELAX.*
> diff --git a/gas/testsuite/gas/riscv/force_reloc.s
> b/gas/testsuite/gas/riscv/force_reloc.s
> new file mode 100644
> index 00000000000..787c419c182
> --- /dev/null
> +++ b/gas/testsuite/gas/riscv/force_reloc.s
> @@ -0,0 +1,22 @@
> +.option pic
> +.option norvc
> +
> +.global sym_abs_before
> +.set sym_abs_before, 42
> +
> +.text
> +.global _start
> +_start:
> +# Need defer expression
> +la  x1, sym_abs_before
> +lga x2, sym_abs_before
> +.L1: auipc x3, %got_pcrel_hi (sym_abs_before)
> +     addi  x3, x3, %pcrel_lo (.L1)
> +# This is fine
> +la  x4, sym_abs_after
> +lga x5, sym_abs_after
> +.L2: auipc x6, %got_pcrel_hi (sym_abs_after)
> +     addi  x6, x6, %pcrel_lo (.L2)
> +
> +.global sym_abs_after
> +.set sym_abs_after, 42
> --
> 2.39.5 (Apple Git-154)
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://sourceware.org/pipermail/binutils/attachments/20250904/f0a51bba/attachment-0001.htm>


More information about the Binutils mailing list