1 /* tc-riscv.c -- RISC-V assembler
2 Copyright (C) 2011-2018 Free Software Foundation, Inc.
4 Contributed by Andrew Waterman (andrew@sifive.com).
7 This file is part of GAS.
9 GAS is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 3, or (at your option)
14 GAS is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program; see the file COPYING3. If not,
21 see <http://www.gnu.org/licenses/>. */
26 #include "safe-ctype.h"
29 #include "dwarf2dbg.h"
30 #include "dw2gencfi.h"
31 #include "struc-symbol.h"
33 #include "elf/riscv.h"
34 #include "opcode/riscv.h"
38 /* Information about an instruction, including its format, operands
42 /* The opcode's entry in riscv_opcodes. */
43 const struct riscv_opcode
*insn_mo
;
45 /* The encoded instruction bits. */
48 /* The frag that contains the instruction. */
51 /* The offset into FRAG of the first instruction byte. */
54 /* The relocs associated with the instruction, if any. */
59 #define DEFAULT_ARCH "riscv64"
62 static const char default_arch
[] = DEFAULT_ARCH
;
64 static unsigned xlen
= 0; /* width of an x-register */
65 static unsigned abi_xlen
= 0; /* width of a pointer in the ABI */
66 static bfd_boolean rve_abi
= FALSE
;
68 #define LOAD_ADDRESS_INSN (abi_xlen == 64 ? "ld" : "lw")
69 #define ADD32_INSN (xlen == 64 ? "addiw" : "addi")
71 static unsigned elf_flags
= 0;
73 /* This is the set of options which the .option pseudo-op may modify. */
75 struct riscv_set_options
77 int pic
; /* Generate position-independent code. */
78 int rvc
; /* Generate RVC code. */
79 int rve
; /* Generate RVE code. */
80 int relax
; /* Emit relocs the linker is allowed to relax. */
83 static struct riscv_set_options riscv_opts
=
92 riscv_set_rvc (bfd_boolean rvc_value
)
95 elf_flags
|= EF_RISCV_RVC
;
97 riscv_opts
.rvc
= rvc_value
;
101 riscv_set_rve (bfd_boolean rve_value
)
103 riscv_opts
.rve
= rve_value
;
110 struct riscv_subset
*next
;
113 static struct riscv_subset
*riscv_subsets
;
116 riscv_subset_supports (const char *feature
)
118 struct riscv_subset
*s
;
120 unsigned xlen_required
= strtoul (feature
, &p
, 10);
122 if (xlen_required
&& xlen
!= xlen_required
)
125 for (s
= riscv_subsets
; s
!= NULL
; s
= s
->next
)
126 if (strcasecmp (s
->name
, p
) == 0)
133 riscv_clear_subsets (void)
135 while (riscv_subsets
!= NULL
)
137 struct riscv_subset
*next
= riscv_subsets
->next
;
138 free ((void *) riscv_subsets
->name
);
139 free (riscv_subsets
);
140 riscv_subsets
= next
;
145 riscv_add_subset (const char *subset
)
147 struct riscv_subset
*s
= xmalloc (sizeof *s
);
149 s
->name
= xstrdup (subset
);
150 s
->next
= riscv_subsets
;
154 /* Set which ISA and extensions are available. */
157 riscv_set_arch (const char *s
)
159 const char *all_subsets
= "imafdqc";
160 char *extension
= NULL
;
163 riscv_clear_subsets();
165 if (strncmp (p
, "rv32", 4) == 0)
170 else if (strncmp (p
, "rv64", 4) == 0)
176 as_fatal ("-march=%s: ISA string must begin with rv32 or rv64", s
);
185 riscv_add_subset ("e");
186 riscv_add_subset ("i");
189 as_fatal ("-march=%s: rv%de is not a valid base ISA", s
, xlen
);
195 for ( ; *all_subsets
!= 'q'; all_subsets
++)
197 const char subset
[] = {*all_subsets
, '\0'};
198 riscv_add_subset (subset
);
203 as_fatal ("-march=%s: first ISA subset must be `e', `i' or `g'", s
);
210 char *subset
= xstrdup (p
);
213 while (*++q
!= '\0' && *q
!= '_')
218 as_fatal ("-march=%s: only one non-standard extension is supported"
219 " (found `%s' and `%s')", s
, extension
, subset
);
221 riscv_add_subset (subset
);
222 p
+= strlen (subset
);
226 else if ((all_subsets
= strchr (all_subsets
, *p
)) != NULL
)
228 const char subset
[] = {*p
, 0};
229 riscv_add_subset (subset
);
234 as_fatal ("-march=%s: unsupported ISA subset `%c'", s
, *p
);
237 if (riscv_subset_supports ("e") && riscv_subset_supports ("f"))
238 as_fatal ("-march=%s: rv32e does not support the `f' extension", s
);
240 if (riscv_subset_supports ("d") && !riscv_subset_supports ("f"))
241 as_fatal ("-march=%s: `d' extension requires `f' extension", s
);
243 if (riscv_subset_supports ("q") && !riscv_subset_supports ("d"))
244 as_fatal ("-march=%s: `q' extension requires `d' extension", s
);
246 if (riscv_subset_supports ("q") && xlen
< 64)
247 as_fatal ("-march=%s: rv32 does not support the `q' extension", s
);
252 /* Handle of the OPCODE hash table. */
253 static struct hash_control
*op_hash
= NULL
;
255 /* Handle of the type of .insn hash table. */
256 static struct hash_control
*insn_type_hash
= NULL
;
258 /* This array holds the chars that always start a comment. If the
259 pre-processor is disabled, these aren't very useful */
260 const char comment_chars
[] = "#";
262 /* This array holds the chars that only start a comment at the beginning of
263 a line. If the line seems to have the form '# 123 filename'
264 .line and .file directives will appear in the pre-processed output */
265 /* Note that input_file.c hand checks for '#' at the beginning of the
266 first line of the input file. This is because the compiler outputs
267 #NO_APP at the beginning of its output. */
268 /* Also note that C style comments are always supported. */
269 const char line_comment_chars
[] = "#";
271 /* This array holds machine specific line separator characters. */
272 const char line_separator_chars
[] = ";";
274 /* Chars that can be used to separate mant from exp in floating point nums */
275 const char EXP_CHARS
[] = "eE";
277 /* Chars that mean this number is a floating point constant */
280 const char FLT_CHARS
[] = "rRsSfFdDxXpP";
282 /* Macros for encoding relaxation state for RVC branches and far jumps. */
283 #define RELAX_BRANCH_ENCODE(uncond, rvc, length) \
286 | ((uncond) ? 1 : 0) \
289 #define RELAX_BRANCH_P(i) (((i) & 0xf0000000) == 0xc0000000)
290 #define RELAX_BRANCH_LENGTH(i) (((i) >> 2) & 0xF)
291 #define RELAX_BRANCH_RVC(i) (((i) & 2) != 0)
292 #define RELAX_BRANCH_UNCOND(i) (((i) & 1) != 0)
294 /* Is the given value a sign-extended 32-bit value? */
295 #define IS_SEXT_32BIT_NUM(x) \
296 (((x) &~ (offsetT) 0x7fffffff) == 0 \
297 || (((x) &~ (offsetT) 0x7fffffff) == ~ (offsetT) 0x7fffffff))
299 /* Is the given value a zero-extended 32-bit value? Or a negated one? */
300 #define IS_ZEXT_32BIT_NUM(x) \
301 (((x) &~ (offsetT) 0xffffffff) == 0 \
302 || (((x) &~ (offsetT) 0xffffffff) == ~ (offsetT) 0xffffffff))
304 /* Change INSN's opcode so that the operand given by FIELD has value VALUE.
305 INSN is a riscv_cl_insn structure and VALUE is evaluated exactly once. */
306 #define INSERT_OPERAND(FIELD, INSN, VALUE) \
307 INSERT_BITS ((INSN).insn_opcode, VALUE, OP_MASK_##FIELD, OP_SH_##FIELD)
309 /* Determine if an instruction matches an opcode. */
310 #define OPCODE_MATCHES(OPCODE, OP) \
311 (((OPCODE) & MASK_##OP) == MATCH_##OP)
313 static char *expr_end
;
315 /* The default target format to use. */
318 riscv_target_format (void)
320 return xlen
== 64 ? "elf64-littleriscv" : "elf32-littleriscv";
323 /* Return the length of instruction INSN. */
325 static inline unsigned int
326 insn_length (const struct riscv_cl_insn
*insn
)
328 return riscv_insn_length (insn
->insn_opcode
);
331 /* Initialise INSN from opcode entry MO. Leave its position unspecified. */
334 create_insn (struct riscv_cl_insn
*insn
, const struct riscv_opcode
*mo
)
337 insn
->insn_opcode
= mo
->match
;
343 /* Install INSN at the location specified by its "frag" and "where" fields. */
346 install_insn (const struct riscv_cl_insn
*insn
)
348 char *f
= insn
->frag
->fr_literal
+ insn
->where
;
349 md_number_to_chars (f
, insn
->insn_opcode
, insn_length (insn
));
352 /* Move INSN to offset WHERE in FRAG. Adjust the fixups accordingly
353 and install the opcode in the new location. */
356 move_insn (struct riscv_cl_insn
*insn
, fragS
*frag
, long where
)
360 if (insn
->fixp
!= NULL
)
362 insn
->fixp
->fx_frag
= frag
;
363 insn
->fixp
->fx_where
= where
;
368 /* Add INSN to the end of the output. */
371 add_fixed_insn (struct riscv_cl_insn
*insn
)
373 char *f
= frag_more (insn_length (insn
));
374 move_insn (insn
, frag_now
, f
- frag_now
->fr_literal
);
378 add_relaxed_insn (struct riscv_cl_insn
*insn
, int max_chars
, int var
,
379 relax_substateT subtype
, symbolS
*symbol
, offsetT offset
)
381 frag_grow (max_chars
);
382 move_insn (insn
, frag_now
, frag_more (0) - frag_now
->fr_literal
);
383 frag_var (rs_machine_dependent
, max_chars
, var
,
384 subtype
, symbol
, offset
, NULL
);
387 /* Compute the length of a branch sequence, and adjust the stored length
388 accordingly. If FRAGP is NULL, the worst-case length is returned. */
391 relaxed_branch_length (fragS
*fragp
, asection
*sec
, int update
)
393 int jump
, rvc
, length
= 8;
398 jump
= RELAX_BRANCH_UNCOND (fragp
->fr_subtype
);
399 rvc
= RELAX_BRANCH_RVC (fragp
->fr_subtype
);
400 length
= RELAX_BRANCH_LENGTH (fragp
->fr_subtype
);
402 /* Assume jumps are in range; the linker will catch any that aren't. */
403 length
= jump
? 4 : 8;
405 if (fragp
->fr_symbol
!= NULL
406 && S_IS_DEFINED (fragp
->fr_symbol
)
407 && !S_IS_WEAK (fragp
->fr_symbol
)
408 && sec
== S_GET_SEGMENT (fragp
->fr_symbol
))
410 offsetT val
= S_GET_VALUE (fragp
->fr_symbol
) + fragp
->fr_offset
;
411 bfd_vma rvc_range
= jump
? RVC_JUMP_REACH
: RVC_BRANCH_REACH
;
412 val
-= fragp
->fr_address
+ fragp
->fr_fix
;
414 if (rvc
&& (bfd_vma
)(val
+ rvc_range
/2) < rvc_range
)
416 else if ((bfd_vma
)(val
+ RISCV_BRANCH_REACH
/2) < RISCV_BRANCH_REACH
)
418 else if (!jump
&& rvc
)
423 fragp
->fr_subtype
= RELAX_BRANCH_ENCODE (jump
, rvc
, length
);
428 /* Information about an opcode name, mnemonics and its value. */
435 /* List for all supported opcode name. */
436 static const struct opcode_name_t opcode_name_list
[] =
481 /* Hash table for lookup opcode name. */
482 static struct hash_control
*opcode_names_hash
= NULL
;
484 /* Initialization for hash table of opcode name. */
486 init_opcode_names_hash (void)
489 const struct opcode_name_t
*opcode
;
491 for (opcode
= &opcode_name_list
[0]; opcode
->name
!= NULL
; ++opcode
)
493 retval
= hash_insert (opcode_names_hash
, opcode
->name
, (void *)opcode
);
496 as_fatal (_("internal error: can't hash `%s': %s"),
497 opcode
->name
, retval
);
501 /* Find `s` is a valid opcode name or not,
502 return the opcode name info if found. */
503 static const struct opcode_name_t
*
504 opcode_name_lookup (char **s
)
508 struct opcode_name_t
*o
;
510 /* Find end of name. */
512 if (is_name_beginner (*e
))
514 while (is_part_of_name (*e
))
517 /* Terminate name. */
521 o
= (struct opcode_name_t
*) hash_find (opcode_names_hash
, *s
);
523 /* Advance to next token if one was recognized. */
547 static struct hash_control
*reg_names_hash
= NULL
;
549 #define ENCODE_REG_HASH(cls, n) \
550 ((void *)(uintptr_t)((n) * RCLASS_MAX + (cls) + 1))
551 #define DECODE_REG_CLASS(hash) (((uintptr_t)(hash) - 1) % RCLASS_MAX)
552 #define DECODE_REG_NUM(hash) (((uintptr_t)(hash) - 1) / RCLASS_MAX)
555 hash_reg_name (enum reg_class
class, const char *name
, unsigned n
)
557 void *hash
= ENCODE_REG_HASH (class, n
);
558 const char *retval
= hash_insert (reg_names_hash
, name
, hash
);
561 as_fatal (_("internal error: can't hash `%s': %s"), name
, retval
);
565 hash_reg_names (enum reg_class
class, const char * const names
[], unsigned n
)
569 for (i
= 0; i
< n
; i
++)
570 hash_reg_name (class, names
[i
], i
);
574 reg_lookup_internal (const char *s
, enum reg_class
class)
576 struct regname
*r
= (struct regname
*) hash_find (reg_names_hash
, s
);
578 if (r
== NULL
|| DECODE_REG_CLASS (r
) != class)
581 if (riscv_opts
.rve
&& class == RCLASS_GPR
&& DECODE_REG_NUM (r
) > 15)
584 return DECODE_REG_NUM (r
);
588 reg_lookup (char **s
, enum reg_class
class, unsigned int *regnop
)
594 /* Find end of name. */
596 if (is_name_beginner (*e
))
598 while (is_part_of_name (*e
))
601 /* Terminate name. */
605 /* Look for the register. Advance to next token if one was recognized. */
606 if ((reg
= reg_lookup_internal (*s
, class)) >= 0)
616 arg_lookup (char **s
, const char *const *array
, size_t size
, unsigned *regnop
)
618 const char *p
= strchr (*s
, ',');
619 size_t i
, len
= p
? (size_t)(p
- *s
) : strlen (*s
);
624 for (i
= 0; i
< size
; i
++)
625 if (array
[i
] != NULL
&& strncmp (array
[i
], *s
, len
) == 0)
635 /* For consistency checking, verify that all bits are specified either
636 by the match/mask part of the instruction definition, or by the
639 `length` could be 0, 4 or 8, 0 for auto detection. */
641 validate_riscv_insn (const struct riscv_opcode
*opc
, int length
)
643 const char *p
= opc
->args
;
645 insn_t used_bits
= opc
->mask
;
647 insn_t required_bits
;
650 insn_width
= 8 * riscv_insn_length (opc
->match
);
652 insn_width
= 8 * length
;
654 required_bits
= ~0ULL >> (64 - insn_width
);
656 if ((used_bits
& opc
->match
) != (opc
->match
& required_bits
))
658 as_bad (_("internal: bad RISC-V opcode (mask error): %s %s"),
659 opc
->name
, opc
->args
);
663 #define USE_BITS(mask,shift) (used_bits |= ((insn_t)(mask) << (shift)))
670 case 'a': used_bits
|= ENCODE_RVC_J_IMM (-1U); break;
671 case 'c': break; /* RS1, constrained to equal sp */
672 case 'i': used_bits
|= ENCODE_RVC_SIMM3(-1U); break;
673 case 'j': used_bits
|= ENCODE_RVC_IMM (-1U); break;
674 case 'o': used_bits
|= ENCODE_RVC_IMM (-1U); break;
675 case 'k': used_bits
|= ENCODE_RVC_LW_IMM (-1U); break;
676 case 'l': used_bits
|= ENCODE_RVC_LD_IMM (-1U); break;
677 case 'm': used_bits
|= ENCODE_RVC_LWSP_IMM (-1U); break;
678 case 'n': used_bits
|= ENCODE_RVC_LDSP_IMM (-1U); break;
679 case 'p': used_bits
|= ENCODE_RVC_B_IMM (-1U); break;
680 case 's': USE_BITS (OP_MASK_CRS1S
, OP_SH_CRS1S
); break;
681 case 't': USE_BITS (OP_MASK_CRS2S
, OP_SH_CRS2S
); break;
682 case 'u': used_bits
|= ENCODE_RVC_IMM (-1U); break;
683 case 'v': used_bits
|= ENCODE_RVC_IMM (-1U); break;
684 case 'w': break; /* RS1S, constrained to equal RD */
685 case 'x': break; /* RS2S, constrained to equal RD */
686 case 'K': used_bits
|= ENCODE_RVC_ADDI4SPN_IMM (-1U); break;
687 case 'L': used_bits
|= ENCODE_RVC_ADDI16SP_IMM (-1U); break;
688 case 'M': used_bits
|= ENCODE_RVC_SWSP_IMM (-1U); break;
689 case 'N': used_bits
|= ENCODE_RVC_SDSP_IMM (-1U); break;
690 case 'U': break; /* RS1, constrained to equal RD */
691 case 'V': USE_BITS (OP_MASK_CRS2
, OP_SH_CRS2
); break;
692 case '<': used_bits
|= ENCODE_RVC_IMM (-1U); break;
693 case '>': used_bits
|= ENCODE_RVC_IMM (-1U); break;
694 case '8': used_bits
|= ENCODE_RVC_UIMM8 (-1U); break;
695 case 'S': USE_BITS (OP_MASK_CRS1S
, OP_SH_CRS1S
); break;
696 case 'T': USE_BITS (OP_MASK_CRS2
, OP_SH_CRS2
); break;
697 case 'D': USE_BITS (OP_MASK_CRS2S
, OP_SH_CRS2S
); break;
698 case 'F': /* funct */
701 case '4': USE_BITS (OP_MASK_CFUNCT4
, OP_SH_CFUNCT4
); break;
702 case '3': USE_BITS (OP_MASK_CFUNCT3
, OP_SH_CFUNCT3
); break;
704 as_bad (_("internal: bad RISC-V opcode"
705 " (unknown operand type `CF%c'): %s %s"),
706 c
, opc
->name
, opc
->args
);
711 as_bad (_("internal: bad RISC-V opcode (unknown operand type `C%c'): %s %s"),
712 c
, opc
->name
, opc
->args
);
719 case '<': USE_BITS (OP_MASK_SHAMTW
, OP_SH_SHAMTW
); break;
720 case '>': USE_BITS (OP_MASK_SHAMT
, OP_SH_SHAMT
); break;
722 case 'D': USE_BITS (OP_MASK_RD
, OP_SH_RD
); break;
723 case 'Z': USE_BITS (OP_MASK_RS1
, OP_SH_RS1
); break;
724 case 'E': USE_BITS (OP_MASK_CSR
, OP_SH_CSR
); break;
726 case 'R': USE_BITS (OP_MASK_RS3
, OP_SH_RS3
); break;
727 case 'S': USE_BITS (OP_MASK_RS1
, OP_SH_RS1
); break;
728 case 'U': USE_BITS (OP_MASK_RS1
, OP_SH_RS1
); /* fallthru */
729 case 'T': USE_BITS (OP_MASK_RS2
, OP_SH_RS2
); break;
730 case 'd': USE_BITS (OP_MASK_RD
, OP_SH_RD
); break;
731 case 'm': USE_BITS (OP_MASK_RM
, OP_SH_RM
); break;
732 case 's': USE_BITS (OP_MASK_RS1
, OP_SH_RS1
); break;
733 case 't': USE_BITS (OP_MASK_RS2
, OP_SH_RS2
); break;
734 case 'r': USE_BITS (OP_MASK_RS3
, OP_SH_RS3
); break;
735 case 'P': USE_BITS (OP_MASK_PRED
, OP_SH_PRED
); break;
736 case 'Q': USE_BITS (OP_MASK_SUCC
, OP_SH_SUCC
); break;
738 case 'j': used_bits
|= ENCODE_ITYPE_IMM (-1U); break;
739 case 'a': used_bits
|= ENCODE_UJTYPE_IMM (-1U); break;
740 case 'p': used_bits
|= ENCODE_SBTYPE_IMM (-1U); break;
741 case 'q': used_bits
|= ENCODE_STYPE_IMM (-1U); break;
742 case 'u': used_bits
|= ENCODE_UTYPE_IMM (-1U); break;
747 case 'F': /* funct */
750 case '7': USE_BITS (OP_MASK_FUNCT7
, OP_SH_FUNCT7
); break;
751 case '3': USE_BITS (OP_MASK_FUNCT3
, OP_SH_FUNCT3
); break;
752 case '2': USE_BITS (OP_MASK_FUNCT2
, OP_SH_FUNCT2
); break;
754 as_bad (_("internal: bad RISC-V opcode"
755 " (unknown operand type `F%c'): %s %s"),
756 c
, opc
->name
, opc
->args
);
760 case 'O': /* opcode */
763 case '4': USE_BITS (OP_MASK_OP
, OP_SH_OP
); break;
764 case '2': USE_BITS (OP_MASK_OP2
, OP_SH_OP2
); break;
766 as_bad (_("internal: bad RISC-V opcode"
767 " (unknown operand type `F%c'): %s %s"),
768 c
, opc
->name
, opc
->args
);
773 as_bad (_("internal: bad RISC-V opcode "
774 "(unknown operand type `%c'): %s %s"),
775 c
, opc
->name
, opc
->args
);
779 if (used_bits
!= required_bits
)
781 as_bad (_("internal: bad RISC-V opcode (bits 0x%lx undefined): %s %s"),
782 ~(unsigned long)(used_bits
& required_bits
),
783 opc
->name
, opc
->args
);
789 struct percent_op_match
792 bfd_reloc_code_real_type reloc
;
795 /* Common hash table initialization function for
796 instruction and .insn directive. */
797 static struct hash_control
*
798 init_opcode_hash (const struct riscv_opcode
*opcodes
,
799 bfd_boolean insn_directive_p
)
803 struct hash_control
*hash
= hash_new ();
804 while (opcodes
[i
].name
)
806 const char *name
= opcodes
[i
].name
;
807 const char *hash_error
=
808 hash_insert (hash
, name
, (void *) &opcodes
[i
]);
812 fprintf (stderr
, _("internal error: can't hash `%s': %s\n"),
813 opcodes
[i
].name
, hash_error
);
814 /* Probably a memory allocation problem? Give up now. */
815 as_fatal (_("Broken assembler. No assembly attempted."));
820 if (opcodes
[i
].pinfo
!= INSN_MACRO
)
822 if (insn_directive_p
)
823 length
= ((name
[0] == 'c') ? 2 : 4);
825 length
= 0; /* Let assembler determine the length. */
826 if (!validate_riscv_insn (&opcodes
[i
], length
))
827 as_fatal (_("Broken assembler. No assembly attempted."));
830 gas_assert (!insn_directive_p
);
833 while (opcodes
[i
].name
&& !strcmp (opcodes
[i
].name
, name
));
839 /* This function is called once, at assembler startup time. It should set up
840 all the tables, etc. that the MD part of the assembler will need. */
845 unsigned long mach
= xlen
== 64 ? bfd_mach_riscv64
: bfd_mach_riscv32
;
847 if (! bfd_set_arch_mach (stdoutput
, bfd_arch_riscv
, mach
))
848 as_warn (_("Could not set architecture and machine"));
850 op_hash
= init_opcode_hash (riscv_opcodes
, FALSE
);
851 insn_type_hash
= init_opcode_hash (riscv_insn_types
, TRUE
);
853 reg_names_hash
= hash_new ();
854 hash_reg_names (RCLASS_GPR
, riscv_gpr_names_numeric
, NGPR
);
855 hash_reg_names (RCLASS_GPR
, riscv_gpr_names_abi
, NGPR
);
856 hash_reg_names (RCLASS_FPR
, riscv_fpr_names_numeric
, NFPR
);
857 hash_reg_names (RCLASS_FPR
, riscv_fpr_names_abi
, NFPR
);
859 /* Add "fp" as an alias for "s0". */
860 hash_reg_name (RCLASS_GPR
, "fp", 8);
862 opcode_names_hash
= hash_new ();
863 init_opcode_names_hash ();
865 #define DECLARE_CSR(name, num) hash_reg_name (RCLASS_CSR, #name, num);
866 #define DECLARE_CSR_ALIAS(name, num) DECLARE_CSR(name, num);
867 #include "opcode/riscv-opc.h"
870 /* Set the default alignment for the text section. */
871 record_alignment (text_section
, riscv_opts
.rvc
? 1 : 2);
875 riscv_apply_const_reloc (bfd_reloc_code_real_type reloc_type
, bfd_vma value
)
882 case BFD_RELOC_RISCV_HI20
:
883 return ENCODE_UTYPE_IMM (RISCV_CONST_HIGH_PART (value
));
885 case BFD_RELOC_RISCV_LO12_S
:
886 return ENCODE_STYPE_IMM (value
);
888 case BFD_RELOC_RISCV_LO12_I
:
889 return ENCODE_ITYPE_IMM (value
);
896 /* Output an instruction. IP is the instruction information.
897 ADDRESS_EXPR is an operand of the instruction to be used with
901 append_insn (struct riscv_cl_insn
*ip
, expressionS
*address_expr
,
902 bfd_reloc_code_real_type reloc_type
)
904 dwarf2_emit_insn (0);
906 if (reloc_type
!= BFD_RELOC_UNUSED
)
908 reloc_howto_type
*howto
;
910 gas_assert (address_expr
);
911 if (reloc_type
== BFD_RELOC_12_PCREL
912 || reloc_type
== BFD_RELOC_RISCV_JMP
)
914 int j
= reloc_type
== BFD_RELOC_RISCV_JMP
;
915 int best_case
= riscv_insn_length (ip
->insn_opcode
);
916 unsigned worst_case
= relaxed_branch_length (NULL
, NULL
, 0);
917 add_relaxed_insn (ip
, worst_case
, best_case
,
918 RELAX_BRANCH_ENCODE (j
, best_case
== 2, worst_case
),
919 address_expr
->X_add_symbol
,
920 address_expr
->X_add_number
);
925 howto
= bfd_reloc_type_lookup (stdoutput
, reloc_type
);
927 as_bad (_("Unsupported RISC-V relocation number %d"), reloc_type
);
929 ip
->fixp
= fix_new_exp (ip
->frag
, ip
->where
,
930 bfd_get_reloc_size (howto
),
931 address_expr
, FALSE
, reloc_type
);
933 ip
->fixp
->fx_tcbit
= riscv_opts
.relax
;
940 /* We need to start a new frag after any instruction that can be
941 optimized away or compressed by the linker during relaxation, to prevent
942 the assembler from computing static offsets across such an instruction.
943 This is necessary to get correct EH info. */
944 if (reloc_type
== BFD_RELOC_RISCV_CALL
945 || reloc_type
== BFD_RELOC_RISCV_CALL_PLT
946 || reloc_type
== BFD_RELOC_RISCV_HI20
947 || reloc_type
== BFD_RELOC_RISCV_PCREL_HI20
948 || reloc_type
== BFD_RELOC_RISCV_TPREL_HI20
949 || reloc_type
== BFD_RELOC_RISCV_TPREL_ADD
)
951 frag_wane (frag_now
);
956 /* Build an instruction created by a macro expansion. This is passed
957 a pointer to the count of instructions created so far, an
958 expression, the name of the instruction to build, an operand format
959 string, and corresponding arguments. */
962 macro_build (expressionS
*ep
, const char *name
, const char *fmt
, ...)
964 const struct riscv_opcode
*mo
;
965 struct riscv_cl_insn insn
;
966 bfd_reloc_code_real_type r
;
969 va_start (args
, fmt
);
971 r
= BFD_RELOC_UNUSED
;
972 mo
= (struct riscv_opcode
*) hash_find (op_hash
, name
);
975 /* Find a non-RVC variant of the instruction. append_insn will compress
977 while (riscv_insn_length (mo
->match
) < 4)
979 gas_assert (strcmp (name
, mo
->name
) == 0);
981 create_insn (&insn
, mo
);
987 INSERT_OPERAND (RD
, insn
, va_arg (args
, int));
991 INSERT_OPERAND (RS1
, insn
, va_arg (args
, int));
995 INSERT_OPERAND (RS2
, insn
, va_arg (args
, int));
999 INSERT_OPERAND (SHAMT
, insn
, va_arg (args
, int));
1005 gas_assert (ep
!= NULL
);
1006 r
= va_arg (args
, int);
1014 as_fatal (_("internal error: invalid macro"));
1019 gas_assert (r
== BFD_RELOC_UNUSED
? ep
== NULL
: ep
!= NULL
);
1021 append_insn (&insn
, ep
, r
);
1024 /* Sign-extend 32-bit mode constants that have bit 31 set and all higher bits
1027 normalize_constant_expr (expressionS
*ex
)
1031 if ((ex
->X_op
== O_constant
|| ex
->X_op
== O_symbol
)
1032 && IS_ZEXT_32BIT_NUM (ex
->X_add_number
))
1033 ex
->X_add_number
= (((ex
->X_add_number
& 0xffffffff) ^ 0x80000000)
1037 /* Fail if an expression EX is not a constant. IP is the instruction using EX.
1038 MAYBE_CSR is true if the symbol may be an unrecognized CSR name. */
1041 check_absolute_expr (struct riscv_cl_insn
*ip
, expressionS
*ex
,
1042 bfd_boolean maybe_csr
)
1044 if (ex
->X_op
== O_big
)
1045 as_bad (_("unsupported large constant"));
1046 else if (maybe_csr
&& ex
->X_op
== O_symbol
)
1047 as_bad (_("unknown CSR `%s'"),
1048 S_GET_NAME (ex
->X_add_symbol
));
1049 else if (ex
->X_op
!= O_constant
)
1050 as_bad (_("Instruction %s requires absolute expression"),
1052 normalize_constant_expr (ex
);
1056 make_internal_label (void)
1058 return (symbolS
*) local_symbol_make (FAKE_LABEL_NAME
, now_seg
,
1059 (valueT
) frag_now_fix (), frag_now
);
1062 /* Load an entry from the GOT. */
1064 pcrel_access (int destreg
, int tempreg
, expressionS
*ep
,
1065 const char *lo_insn
, const char *lo_pattern
,
1066 bfd_reloc_code_real_type hi_reloc
,
1067 bfd_reloc_code_real_type lo_reloc
)
1070 ep2
.X_op
= O_symbol
;
1071 ep2
.X_add_symbol
= make_internal_label ();
1072 ep2
.X_add_number
= 0;
1074 macro_build (ep
, "auipc", "d,u", tempreg
, hi_reloc
);
1075 macro_build (&ep2
, lo_insn
, lo_pattern
, destreg
, tempreg
, lo_reloc
);
1079 pcrel_load (int destreg
, int tempreg
, expressionS
*ep
, const char *lo_insn
,
1080 bfd_reloc_code_real_type hi_reloc
,
1081 bfd_reloc_code_real_type lo_reloc
)
1083 pcrel_access (destreg
, tempreg
, ep
, lo_insn
, "d,s,j", hi_reloc
, lo_reloc
);
1087 pcrel_store (int srcreg
, int tempreg
, expressionS
*ep
, const char *lo_insn
,
1088 bfd_reloc_code_real_type hi_reloc
,
1089 bfd_reloc_code_real_type lo_reloc
)
1091 pcrel_access (srcreg
, tempreg
, ep
, lo_insn
, "t,s,q", hi_reloc
, lo_reloc
);
1094 /* PC-relative function call using AUIPC/JALR, relaxed to JAL. */
1096 riscv_call (int destreg
, int tempreg
, expressionS
*ep
,
1097 bfd_reloc_code_real_type reloc
)
1099 macro_build (ep
, "auipc", "d,u", tempreg
, reloc
);
1100 macro_build (NULL
, "jalr", "d,s", destreg
, tempreg
);
1103 /* Load an integer constant into a register. */
1106 load_const (int reg
, expressionS
*ep
)
1108 int shift
= RISCV_IMM_BITS
;
1109 expressionS upper
= *ep
, lower
= *ep
;
1110 lower
.X_add_number
= (int32_t) ep
->X_add_number
<< (32-shift
) >> (32-shift
);
1111 upper
.X_add_number
-= lower
.X_add_number
;
1113 if (ep
->X_op
!= O_constant
)
1115 as_bad (_("unsupported large constant"));
1119 if (xlen
> 32 && !IS_SEXT_32BIT_NUM (ep
->X_add_number
))
1121 /* Reduce to a signed 32-bit constant using SLLI and ADDI. */
1122 while (((upper
.X_add_number
>> shift
) & 1) == 0)
1125 upper
.X_add_number
= (int64_t) upper
.X_add_number
>> shift
;
1126 load_const (reg
, &upper
);
1128 macro_build (NULL
, "slli", "d,s,>", reg
, reg
, shift
);
1129 if (lower
.X_add_number
!= 0)
1130 macro_build (&lower
, "addi", "d,s,j", reg
, reg
, BFD_RELOC_RISCV_LO12_I
);
1134 /* Simply emit LUI and/or ADDI to build a 32-bit signed constant. */
1137 if (upper
.X_add_number
!= 0)
1139 macro_build (ep
, "lui", "d,u", reg
, BFD_RELOC_RISCV_HI20
);
1143 if (lower
.X_add_number
!= 0 || hi_reg
== 0)
1144 macro_build (ep
, ADD32_INSN
, "d,s,j", reg
, hi_reg
,
1145 BFD_RELOC_RISCV_LO12_I
);
1149 /* Expand RISC-V assembly macros into one or more instructions. */
1151 macro (struct riscv_cl_insn
*ip
, expressionS
*imm_expr
,
1152 bfd_reloc_code_real_type
*imm_reloc
)
1154 int rd
= (ip
->insn_opcode
>> OP_SH_RD
) & OP_MASK_RD
;
1155 int rs1
= (ip
->insn_opcode
>> OP_SH_RS1
) & OP_MASK_RS1
;
1156 int rs2
= (ip
->insn_opcode
>> OP_SH_RS2
) & OP_MASK_RS2
;
1157 int mask
= ip
->insn_mo
->mask
;
1162 load_const (rd
, imm_expr
);
1167 /* Load the address of a symbol into a register. */
1168 if (!IS_SEXT_32BIT_NUM (imm_expr
->X_add_number
))
1169 as_bad (_("offset too large"));
1171 if (imm_expr
->X_op
== O_constant
)
1172 load_const (rd
, imm_expr
);
1173 else if (riscv_opts
.pic
&& mask
== M_LA
) /* Global PIC symbol */
1174 pcrel_load (rd
, rd
, imm_expr
, LOAD_ADDRESS_INSN
,
1175 BFD_RELOC_RISCV_GOT_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1176 else /* Local PIC symbol, or any non-PIC symbol */
1177 pcrel_load (rd
, rd
, imm_expr
, "addi",
1178 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1182 pcrel_load (rd
, rd
, imm_expr
, "addi",
1183 BFD_RELOC_RISCV_TLS_GD_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1187 pcrel_load (rd
, rd
, imm_expr
, LOAD_ADDRESS_INSN
,
1188 BFD_RELOC_RISCV_TLS_GOT_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1192 pcrel_load (rd
, rd
, imm_expr
, "lb",
1193 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1197 pcrel_load (rd
, rd
, imm_expr
, "lbu",
1198 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1202 pcrel_load (rd
, rd
, imm_expr
, "lh",
1203 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1207 pcrel_load (rd
, rd
, imm_expr
, "lhu",
1208 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1212 pcrel_load (rd
, rd
, imm_expr
, "lw",
1213 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1217 pcrel_load (rd
, rd
, imm_expr
, "lwu",
1218 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1222 pcrel_load (rd
, rd
, imm_expr
, "ld",
1223 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1227 pcrel_load (rd
, rs1
, imm_expr
, "flw",
1228 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1232 pcrel_load (rd
, rs1
, imm_expr
, "fld",
1233 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_I
);
1237 pcrel_store (rs2
, rs1
, imm_expr
, "sb",
1238 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_S
);
1242 pcrel_store (rs2
, rs1
, imm_expr
, "sh",
1243 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_S
);
1247 pcrel_store (rs2
, rs1
, imm_expr
, "sw",
1248 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_S
);
1252 pcrel_store (rs2
, rs1
, imm_expr
, "sd",
1253 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_S
);
1257 pcrel_store (rs2
, rs1
, imm_expr
, "fsw",
1258 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_S
);
1262 pcrel_store (rs2
, rs1
, imm_expr
, "fsd",
1263 BFD_RELOC_RISCV_PCREL_HI20
, BFD_RELOC_RISCV_PCREL_LO12_S
);
1267 riscv_call (rd
, rs1
, imm_expr
, *imm_reloc
);
1271 as_bad (_("Macro %s not implemented"), ip
->insn_mo
->name
);
1276 static const struct percent_op_match percent_op_utype
[] =
1278 {"%tprel_hi", BFD_RELOC_RISCV_TPREL_HI20
},
1279 {"%pcrel_hi", BFD_RELOC_RISCV_PCREL_HI20
},
1280 {"%tls_ie_pcrel_hi", BFD_RELOC_RISCV_TLS_GOT_HI20
},
1281 {"%tls_gd_pcrel_hi", BFD_RELOC_RISCV_TLS_GD_HI20
},
1282 {"%hi", BFD_RELOC_RISCV_HI20
},
1286 static const struct percent_op_match percent_op_itype
[] =
1288 {"%lo", BFD_RELOC_RISCV_LO12_I
},
1289 {"%tprel_lo", BFD_RELOC_RISCV_TPREL_LO12_I
},
1290 {"%pcrel_lo", BFD_RELOC_RISCV_PCREL_LO12_I
},
1294 static const struct percent_op_match percent_op_stype
[] =
1296 {"%lo", BFD_RELOC_RISCV_LO12_S
},
1297 {"%tprel_lo", BFD_RELOC_RISCV_TPREL_LO12_S
},
1298 {"%pcrel_lo", BFD_RELOC_RISCV_PCREL_LO12_S
},
1302 static const struct percent_op_match percent_op_rtype
[] =
1304 {"%tprel_add", BFD_RELOC_RISCV_TPREL_ADD
},
1308 /* Return true if *STR points to a relocation operator. When returning true,
1309 move *STR over the operator and store its relocation code in *RELOC.
1310 Leave both *STR and *RELOC alone when returning false. */
1313 parse_relocation (char **str
, bfd_reloc_code_real_type
*reloc
,
1314 const struct percent_op_match
*percent_op
)
1316 for ( ; percent_op
->str
; percent_op
++)
1317 if (strncasecmp (*str
, percent_op
->str
, strlen (percent_op
->str
)) == 0)
1319 int len
= strlen (percent_op
->str
);
1321 if (!ISSPACE ((*str
)[len
]) && (*str
)[len
] != '(')
1324 *str
+= strlen (percent_op
->str
);
1325 *reloc
= percent_op
->reloc
;
1327 /* Check whether the output BFD supports this relocation.
1328 If not, issue an error and fall back on something safe. */
1329 if (*reloc
!= BFD_RELOC_UNUSED
1330 && !bfd_reloc_type_lookup (stdoutput
, *reloc
))
1332 as_bad ("relocation %s isn't supported by the current ABI",
1334 *reloc
= BFD_RELOC_UNUSED
;
1342 my_getExpression (expressionS
*ep
, char *str
)
1346 save_in
= input_line_pointer
;
1347 input_line_pointer
= str
;
1349 expr_end
= input_line_pointer
;
1350 input_line_pointer
= save_in
;
1353 /* Parse string STR as a 16-bit relocatable operand. Store the
1354 expression in *EP and the relocation, if any, in RELOC.
1355 Return the number of relocation operators used (0 or 1).
1357 On exit, EXPR_END points to the first character after the expression. */
1360 my_getSmallExpression (expressionS
*ep
, bfd_reloc_code_real_type
*reloc
,
1361 char *str
, const struct percent_op_match
*percent_op
)
1364 unsigned crux_depth
, str_depth
, regno
;
1367 /* First, check for integer registers. */
1368 if (reg_lookup (&str
, RCLASS_GPR
, ®no
))
1370 ep
->X_op
= O_register
;
1371 ep
->X_add_number
= regno
;
1375 /* Search for the start of the main expression.
1376 End the loop with CRUX pointing to the start
1377 of the main expression and with CRUX_DEPTH containing the number
1378 of open brackets at that point. */
1385 crux_depth
= str_depth
;
1387 /* Skip over whitespace and brackets, keeping count of the number
1389 while (*str
== ' ' || *str
== '\t' || *str
== '(')
1395 && parse_relocation (&str
, reloc
, percent_op
));
1397 my_getExpression (ep
, crux
);
1400 /* Match every open bracket. */
1401 while (crux_depth
> 0 && (*str
== ')' || *str
== ' ' || *str
== '\t'))
1406 as_bad ("unclosed '('");
1413 /* Parse opcode name, could be an mnemonics or number. */
1415 my_getOpcodeExpression (expressionS
*ep
, bfd_reloc_code_real_type
*reloc
,
1416 char *str
, const struct percent_op_match
*percent_op
)
1418 const struct opcode_name_t
*o
= opcode_name_lookup (&str
);
1422 ep
->X_op
= O_constant
;
1423 ep
->X_add_number
= o
->val
;
1427 return my_getSmallExpression (ep
, reloc
, str
, percent_op
);
1430 /* Detect and handle implicitly zero load-store offsets. For example,
1431 "lw t0, (t1)" is shorthand for "lw t0, 0(t1)". Return TRUE iff such
1432 an implicit offset was detected. */
1435 riscv_handle_implicit_zero_offset (expressionS
*ep
, const char *s
)
1437 /* Check whether there is only a single bracketed expression left.
1438 If so, it must be the base register and the constant must be zero. */
1439 if (*s
== '(' && strchr (s
+ 1, '(') == 0)
1441 ep
->X_op
= O_constant
;
1442 ep
->X_add_number
= 0;
1449 /* This routine assembles an instruction into its binary format. As a
1450 side effect, it sets the global variable imm_reloc to the type of
1451 relocation to do if one of the operands is an address expression. */
1454 riscv_ip (char *str
, struct riscv_cl_insn
*ip
, expressionS
*imm_expr
,
1455 bfd_reloc_code_real_type
*imm_reloc
, struct hash_control
*hash
)
1460 struct riscv_opcode
*insn
;
1465 const struct percent_op_match
*p
;
1466 const char *error
= "unrecognized opcode";
1468 /* Parse the name of the instruction. Terminate the string if whitespace
1469 is found so that hash_find only sees the name part of the string. */
1470 for (s
= str
; *s
!= '\0'; ++s
)
1478 insn
= (struct riscv_opcode
*) hash_find (hash
, str
);
1481 for ( ; insn
&& insn
->name
&& strcmp (insn
->name
, str
) == 0; insn
++)
1483 if (!riscv_subset_supports (insn
->subset
))
1486 create_insn (ip
, insn
);
1489 imm_expr
->X_op
= O_absent
;
1490 *imm_reloc
= BFD_RELOC_UNUSED
;
1491 p
= percent_op_itype
;
1493 for (args
= insn
->args
;; ++args
)
1495 s
+= strspn (s
, " \t");
1498 case '\0': /* End of args. */
1499 if (insn
->pinfo
!= INSN_MACRO
)
1501 if (!insn
->match_func (insn
, ip
->insn_opcode
))
1504 /* For .insn, insn->match and insn->mask are 0. */
1505 if (riscv_insn_length ((insn
->match
== 0 && insn
->mask
== 0)
1513 /* Successful assembly. */
1520 case 's': /* RS1 x8-x15 */
1521 if (!reg_lookup (&s
, RCLASS_GPR
, ®no
)
1522 || !(regno
>= 8 && regno
<= 15))
1524 INSERT_OPERAND (CRS1S
, *ip
, regno
% 8);
1526 case 'w': /* RS1 x8-x15, constrained to equal RD x8-x15. */
1527 if (!reg_lookup (&s
, RCLASS_GPR
, ®no
)
1528 || EXTRACT_OPERAND (CRS1S
, ip
->insn_opcode
) + 8 != regno
)
1531 case 't': /* RS2 x8-x15 */
1532 if (!reg_lookup (&s
, RCLASS_GPR
, ®no
)
1533 || !(regno
>= 8 && regno
<= 15))
1535 INSERT_OPERAND (CRS2S
, *ip
, regno
% 8);
1537 case 'x': /* RS2 x8-x15, constrained to equal RD x8-x15. */
1538 if (!reg_lookup (&s
, RCLASS_GPR
, ®no
)
1539 || EXTRACT_OPERAND (CRS2S
, ip
->insn_opcode
) + 8 != regno
)
1542 case 'U': /* RS1, constrained to equal RD. */
1543 if (!reg_lookup (&s
, RCLASS_GPR
, ®no
)
1544 || EXTRACT_OPERAND (RD
, ip
->insn_opcode
) != regno
)
1548 if (!reg_lookup (&s
, RCLASS_GPR
, ®no
))
1550 INSERT_OPERAND (CRS2
, *ip
, regno
);
1552 case 'c': /* RS1, constrained to equal sp. */
1553 if (!reg_lookup (&s
, RCLASS_GPR
, ®no
)
1558 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1559 || imm_expr
->X_op
!= O_constant
1560 || imm_expr
->X_add_number
<= 0
1561 || imm_expr
->X_add_number
>= 64)
1563 ip
->insn_opcode
|= ENCODE_RVC_IMM (imm_expr
->X_add_number
);
1566 imm_expr
->X_op
= O_absent
;
1569 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1570 || imm_expr
->X_op
!= O_constant
1571 || !VALID_RVC_IMM (imm_expr
->X_add_number
)
1572 || imm_expr
->X_add_number
<= 0
1573 || imm_expr
->X_add_number
>= 32)
1575 ip
->insn_opcode
|= ENCODE_RVC_IMM (imm_expr
->X_add_number
);
1578 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1579 || imm_expr
->X_op
!= O_constant
1580 || !VALID_RVC_UIMM8 (imm_expr
->X_add_number
)
1581 || imm_expr
->X_add_number
< 0
1582 || imm_expr
->X_add_number
>= 256)
1584 ip
->insn_opcode
|= ENCODE_RVC_UIMM8 (imm_expr
->X_add_number
);
1587 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1588 || imm_expr
->X_op
!= O_constant
1589 || imm_expr
->X_add_number
== 0
1590 || !VALID_RVC_SIMM3 (imm_expr
->X_add_number
))
1592 ip
->insn_opcode
|= ENCODE_RVC_SIMM3 (imm_expr
->X_add_number
);
1595 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1596 || imm_expr
->X_op
!= O_constant
1597 || imm_expr
->X_add_number
== 0
1598 || !VALID_RVC_IMM (imm_expr
->X_add_number
))
1600 ip
->insn_opcode
|= ENCODE_RVC_IMM (imm_expr
->X_add_number
);
1603 if (riscv_handle_implicit_zero_offset (imm_expr
, s
))
1605 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1606 || imm_expr
->X_op
!= O_constant
1607 || !VALID_RVC_LW_IMM (imm_expr
->X_add_number
))
1609 ip
->insn_opcode
|= ENCODE_RVC_LW_IMM (imm_expr
->X_add_number
);
1612 if (riscv_handle_implicit_zero_offset (imm_expr
, s
))
1614 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1615 || imm_expr
->X_op
!= O_constant
1616 || !VALID_RVC_LD_IMM (imm_expr
->X_add_number
))
1618 ip
->insn_opcode
|= ENCODE_RVC_LD_IMM (imm_expr
->X_add_number
);
1621 if (riscv_handle_implicit_zero_offset (imm_expr
, s
))
1623 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1624 || imm_expr
->X_op
!= O_constant
1625 || !VALID_RVC_LWSP_IMM (imm_expr
->X_add_number
))
1628 ENCODE_RVC_LWSP_IMM (imm_expr
->X_add_number
);
1631 if (riscv_handle_implicit_zero_offset (imm_expr
, s
))
1633 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1634 || imm_expr
->X_op
!= O_constant
1635 || !VALID_RVC_LDSP_IMM (imm_expr
->X_add_number
))
1638 ENCODE_RVC_LDSP_IMM (imm_expr
->X_add_number
);
1641 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1642 || imm_expr
->X_op
!= O_constant
1643 /* C.addiw, c.li, and c.andi allow zero immediate.
1644 C.addi allows zero immediate as hint. Otherwise this
1646 || !VALID_RVC_IMM (imm_expr
->X_add_number
))
1648 ip
->insn_opcode
|= ENCODE_RVC_IMM (imm_expr
->X_add_number
);
1651 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1652 || imm_expr
->X_op
!= O_constant
1653 || !VALID_RVC_ADDI4SPN_IMM (imm_expr
->X_add_number
)
1654 || imm_expr
->X_add_number
== 0)
1657 ENCODE_RVC_ADDI4SPN_IMM (imm_expr
->X_add_number
);
1660 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1661 || imm_expr
->X_op
!= O_constant
1662 || !VALID_RVC_ADDI16SP_IMM (imm_expr
->X_add_number
)
1663 || imm_expr
->X_add_number
== 0)
1666 ENCODE_RVC_ADDI16SP_IMM (imm_expr
->X_add_number
);
1669 if (riscv_handle_implicit_zero_offset (imm_expr
, s
))
1671 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1672 || imm_expr
->X_op
!= O_constant
1673 || !VALID_RVC_SWSP_IMM (imm_expr
->X_add_number
))
1676 ENCODE_RVC_SWSP_IMM (imm_expr
->X_add_number
);
1679 if (riscv_handle_implicit_zero_offset (imm_expr
, s
))
1681 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1682 || imm_expr
->X_op
!= O_constant
1683 || !VALID_RVC_SDSP_IMM (imm_expr
->X_add_number
))
1686 ENCODE_RVC_SDSP_IMM (imm_expr
->X_add_number
);
1689 p
= percent_op_utype
;
1690 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
))
1693 if (imm_expr
->X_op
!= O_constant
1694 || imm_expr
->X_add_number
<= 0
1695 || imm_expr
->X_add_number
>= RISCV_BIGIMM_REACH
1696 || (imm_expr
->X_add_number
>= RISCV_RVC_IMM_REACH
/ 2
1697 && (imm_expr
->X_add_number
<
1698 RISCV_BIGIMM_REACH
- RISCV_RVC_IMM_REACH
/ 2)))
1700 ip
->insn_opcode
|= ENCODE_RVC_IMM (imm_expr
->X_add_number
);
1703 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1704 || (imm_expr
->X_add_number
& (RISCV_IMM_REACH
- 1))
1705 || ((int32_t)imm_expr
->X_add_number
1706 != imm_expr
->X_add_number
))
1708 imm_expr
->X_add_number
=
1709 ((uint32_t) imm_expr
->X_add_number
) >> RISCV_IMM_BITS
;
1715 case 'S': /* Floating-point RS1 x8-x15. */
1716 if (!reg_lookup (&s
, RCLASS_FPR
, ®no
)
1717 || !(regno
>= 8 && regno
<= 15))
1719 INSERT_OPERAND (CRS1S
, *ip
, regno
% 8);
1721 case 'D': /* Floating-point RS2 x8-x15. */
1722 if (!reg_lookup (&s
, RCLASS_FPR
, ®no
)
1723 || !(regno
>= 8 && regno
<= 15))
1725 INSERT_OPERAND (CRS2S
, *ip
, regno
% 8);
1727 case 'T': /* Floating-point RS2. */
1728 if (!reg_lookup (&s
, RCLASS_FPR
, ®no
))
1730 INSERT_OPERAND (CRS2
, *ip
, regno
);
1736 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1737 || imm_expr
->X_op
!= O_constant
1738 || imm_expr
->X_add_number
< 0
1739 || imm_expr
->X_add_number
>= 16)
1741 as_bad (_("bad value for funct4 field, "
1742 "value must be 0...15"));
1746 INSERT_OPERAND (CFUNCT4
, *ip
, imm_expr
->X_add_number
);
1747 imm_expr
->X_op
= O_absent
;
1751 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
1752 || imm_expr
->X_op
!= O_constant
1753 || imm_expr
->X_add_number
< 0
1754 || imm_expr
->X_add_number
>= 8)
1756 as_bad (_("bad value for funct3 field, "
1757 "value must be 0...7"));
1760 INSERT_OPERAND (CFUNCT3
, *ip
, imm_expr
->X_add_number
);
1761 imm_expr
->X_op
= O_absent
;
1765 as_bad (_("bad compressed FUNCT field"
1766 " specifier 'CF%c'\n"),
1772 as_bad (_("bad RVC field specifier 'C%c'\n"), *args
);
1791 case '<': /* Shift amount, 0 - 31. */
1792 my_getExpression (imm_expr
, s
);
1793 check_absolute_expr (ip
, imm_expr
, FALSE
);
1794 if ((unsigned long) imm_expr
->X_add_number
> 31)
1795 as_bad (_("Improper shift amount (%lu)"),
1796 (unsigned long) imm_expr
->X_add_number
);
1797 INSERT_OPERAND (SHAMTW
, *ip
, imm_expr
->X_add_number
);
1798 imm_expr
->X_op
= O_absent
;
1802 case '>': /* Shift amount, 0 - (XLEN-1). */
1803 my_getExpression (imm_expr
, s
);
1804 check_absolute_expr (ip
, imm_expr
, FALSE
);
1805 if ((unsigned long) imm_expr
->X_add_number
>= xlen
)
1806 as_bad (_("Improper shift amount (%lu)"),
1807 (unsigned long) imm_expr
->X_add_number
);
1808 INSERT_OPERAND (SHAMT
, *ip
, imm_expr
->X_add_number
);
1809 imm_expr
->X_op
= O_absent
;
1813 case 'Z': /* CSRRxI immediate. */
1814 my_getExpression (imm_expr
, s
);
1815 check_absolute_expr (ip
, imm_expr
, FALSE
);
1816 if ((unsigned long) imm_expr
->X_add_number
> 31)
1817 as_bad (_("Improper CSRxI immediate (%lu)"),
1818 (unsigned long) imm_expr
->X_add_number
);
1819 INSERT_OPERAND (RS1
, *ip
, imm_expr
->X_add_number
);
1820 imm_expr
->X_op
= O_absent
;
1824 case 'E': /* Control register. */
1825 if (reg_lookup (&s
, RCLASS_CSR
, ®no
))
1826 INSERT_OPERAND (CSR
, *ip
, regno
);
1829 my_getExpression (imm_expr
, s
);
1830 check_absolute_expr (ip
, imm_expr
, TRUE
);
1831 if ((unsigned long) imm_expr
->X_add_number
> 0xfff)
1832 as_bad (_("Improper CSR address (%lu)"),
1833 (unsigned long) imm_expr
->X_add_number
);
1834 INSERT_OPERAND (CSR
, *ip
, imm_expr
->X_add_number
);
1835 imm_expr
->X_op
= O_absent
;
1840 case 'm': /* Rounding mode. */
1841 if (arg_lookup (&s
, riscv_rm
, ARRAY_SIZE (riscv_rm
), ®no
))
1843 INSERT_OPERAND (RM
, *ip
, regno
);
1849 case 'Q': /* Fence predecessor/successor. */
1850 if (arg_lookup (&s
, riscv_pred_succ
, ARRAY_SIZE (riscv_pred_succ
),
1854 INSERT_OPERAND (PRED
, *ip
, regno
);
1856 INSERT_OPERAND (SUCC
, *ip
, regno
);
1861 case 'd': /* Destination register. */
1862 case 's': /* Source register. */
1863 case 't': /* Target register. */
1864 case 'r': /* rs3. */
1865 if (reg_lookup (&s
, RCLASS_GPR
, ®no
))
1871 /* Now that we have assembled one operand, we use the args
1872 string to figure out where it goes in the instruction. */
1876 INSERT_OPERAND (RS1
, *ip
, regno
);
1879 INSERT_OPERAND (RD
, *ip
, regno
);
1882 INSERT_OPERAND (RS2
, *ip
, regno
);
1885 INSERT_OPERAND (RS3
, *ip
, regno
);
1892 case 'D': /* Floating point rd. */
1893 case 'S': /* Floating point rs1. */
1894 case 'T': /* Floating point rs2. */
1895 case 'U': /* Floating point rs1 and rs2. */
1896 case 'R': /* Floating point rs3. */
1897 if (reg_lookup (&s
, RCLASS_FPR
, ®no
))
1905 INSERT_OPERAND (RD
, *ip
, regno
);
1908 INSERT_OPERAND (RS1
, *ip
, regno
);
1911 INSERT_OPERAND (RS1
, *ip
, regno
);
1914 INSERT_OPERAND (RS2
, *ip
, regno
);
1917 INSERT_OPERAND (RS3
, *ip
, regno
);
1926 my_getExpression (imm_expr
, s
);
1927 if (imm_expr
->X_op
!= O_big
1928 && imm_expr
->X_op
!= O_constant
)
1930 normalize_constant_expr (imm_expr
);
1935 my_getExpression (imm_expr
, s
);
1936 normalize_constant_expr (imm_expr
);
1937 /* The 'A' format specifier must be a symbol. */
1938 if (imm_expr
->X_op
!= O_symbol
)
1940 *imm_reloc
= BFD_RELOC_32
;
1945 my_getExpression (imm_expr
, s
);
1946 normalize_constant_expr (imm_expr
);
1947 /* The 'B' format specifier must be a symbol or a constant. */
1948 if (imm_expr
->X_op
!= O_symbol
&& imm_expr
->X_op
!= O_constant
)
1950 if (imm_expr
->X_op
== O_symbol
)
1951 *imm_reloc
= BFD_RELOC_32
;
1955 case 'j': /* Sign-extended immediate. */
1956 *imm_reloc
= BFD_RELOC_RISCV_LO12_I
;
1957 p
= percent_op_itype
;
1959 case 'q': /* Store displacement. */
1960 p
= percent_op_stype
;
1961 *imm_reloc
= BFD_RELOC_RISCV_LO12_S
;
1963 case 'o': /* Load displacement. */
1964 p
= percent_op_itype
;
1965 *imm_reloc
= BFD_RELOC_RISCV_LO12_I
;
1967 case '0': /* AMO "displacement," which must be zero. */
1968 p
= percent_op_rtype
;
1969 *imm_reloc
= BFD_RELOC_UNUSED
;
1971 if (riscv_handle_implicit_zero_offset (imm_expr
, s
))
1974 /* If this value won't fit into a 16 bit offset, then go
1975 find a macro that will generate the 32 bit offset
1977 if (!my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
))
1979 normalize_constant_expr (imm_expr
);
1980 if (imm_expr
->X_op
!= O_constant
1981 || (*args
== '0' && imm_expr
->X_add_number
!= 0)
1982 || imm_expr
->X_add_number
>= (signed)RISCV_IMM_REACH
/2
1983 || imm_expr
->X_add_number
< -(signed)RISCV_IMM_REACH
/2)
1990 case 'p': /* PC-relative offset. */
1992 *imm_reloc
= BFD_RELOC_12_PCREL
;
1993 my_getExpression (imm_expr
, s
);
1997 case 'u': /* Upper 20 bits. */
1998 p
= percent_op_utype
;
1999 if (!my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
2000 && imm_expr
->X_op
== O_constant
)
2002 if (imm_expr
->X_add_number
< 0
2003 || imm_expr
->X_add_number
>= (signed)RISCV_BIGIMM_REACH
)
2004 as_bad (_("lui expression not in range 0..1048575"));
2006 *imm_reloc
= BFD_RELOC_RISCV_HI20
;
2007 imm_expr
->X_add_number
<<= RISCV_IMM_BITS
;
2012 case 'a': /* 20-bit PC-relative offset. */
2014 my_getExpression (imm_expr
, s
);
2016 *imm_reloc
= BFD_RELOC_RISCV_JMP
;
2020 my_getExpression (imm_expr
, s
);
2022 if (strcmp (s
, "@plt") == 0)
2024 *imm_reloc
= BFD_RELOC_RISCV_CALL_PLT
;
2028 *imm_reloc
= BFD_RELOC_RISCV_CALL
;
2034 if (my_getOpcodeExpression (imm_expr
, imm_reloc
, s
, p
)
2035 || imm_expr
->X_op
!= O_constant
2036 || imm_expr
->X_add_number
< 0
2037 || imm_expr
->X_add_number
>= 128
2038 || (imm_expr
->X_add_number
& 0x3) != 3)
2040 as_bad (_("bad value for opcode field, "
2041 "value must be 0...127 and "
2042 "lower 2 bits must be 0x3"));
2046 INSERT_OPERAND (OP
, *ip
, imm_expr
->X_add_number
);
2047 imm_expr
->X_op
= O_absent
;
2051 if (my_getOpcodeExpression (imm_expr
, imm_reloc
, s
, p
)
2052 || imm_expr
->X_op
!= O_constant
2053 || imm_expr
->X_add_number
< 0
2054 || imm_expr
->X_add_number
>= 3)
2056 as_bad (_("bad value for opcode field, "
2057 "value must be 0...2"));
2061 INSERT_OPERAND (OP2
, *ip
, imm_expr
->X_add_number
);
2062 imm_expr
->X_op
= O_absent
;
2066 as_bad (_("bad Opcode field specifier 'O%c'\n"), *args
);
2074 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
2075 || imm_expr
->X_op
!= O_constant
2076 || imm_expr
->X_add_number
< 0
2077 || imm_expr
->X_add_number
>= 128)
2079 as_bad (_("bad value for funct7 field, "
2080 "value must be 0...127"));
2084 INSERT_OPERAND (FUNCT7
, *ip
, imm_expr
->X_add_number
);
2085 imm_expr
->X_op
= O_absent
;
2089 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
2090 || imm_expr
->X_op
!= O_constant
2091 || imm_expr
->X_add_number
< 0
2092 || imm_expr
->X_add_number
>= 8)
2094 as_bad (_("bad value for funct3 field, "
2095 "value must be 0...7"));
2099 INSERT_OPERAND (FUNCT3
, *ip
, imm_expr
->X_add_number
);
2100 imm_expr
->X_op
= O_absent
;
2104 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
2105 || imm_expr
->X_op
!= O_constant
2106 || imm_expr
->X_add_number
< 0
2107 || imm_expr
->X_add_number
>= 4)
2109 as_bad (_("bad value for funct2 field, "
2110 "value must be 0...3"));
2114 INSERT_OPERAND (FUNCT2
, *ip
, imm_expr
->X_add_number
);
2115 imm_expr
->X_op
= O_absent
;
2120 as_bad (_("bad FUNCT field specifier 'F%c'\n"), *args
);
2125 if (my_getSmallExpression (imm_expr
, imm_reloc
, s
, p
)
2126 || imm_expr
->X_op
!= O_constant
2127 || imm_expr
->X_add_number
!= 0)
2130 imm_expr
->X_op
= O_absent
;
2134 as_fatal (_("internal error: bad argument type %c"), *args
);
2139 error
= _("illegal operands");
2143 /* Restore the character we might have clobbered above. */
2145 *(argsStart
- 1) = save_c
;
2151 md_assemble (char *str
)
2153 struct riscv_cl_insn insn
;
2154 expressionS imm_expr
;
2155 bfd_reloc_code_real_type imm_reloc
= BFD_RELOC_UNUSED
;
2157 const char *error
= riscv_ip (str
, &insn
, &imm_expr
, &imm_reloc
, op_hash
);
2161 as_bad ("%s `%s'", error
, str
);
2165 if (insn
.insn_mo
->pinfo
== INSN_MACRO
)
2166 macro (&insn
, &imm_expr
, &imm_reloc
);
2168 append_insn (&insn
, &imm_expr
, imm_reloc
);
2172 md_atof (int type
, char *litP
, int *sizeP
)
2174 return ieee_md_atof (type
, litP
, sizeP
, TARGET_BYTES_BIG_ENDIAN
);
2178 md_number_to_chars (char *buf
, valueT val
, int n
)
2180 number_to_chars_littleendian (buf
, val
, n
);
2183 const char *md_shortopts
= "O::g::G:";
2187 OPTION_MARCH
= OPTION_MD_BASE
,
2196 struct option md_longopts
[] =
2198 {"march", required_argument
, NULL
, OPTION_MARCH
},
2199 {"fPIC", no_argument
, NULL
, OPTION_PIC
},
2200 {"fpic", no_argument
, NULL
, OPTION_PIC
},
2201 {"fno-pic", no_argument
, NULL
, OPTION_NO_PIC
},
2202 {"mabi", required_argument
, NULL
, OPTION_MABI
},
2203 {"mrelax", no_argument
, NULL
, OPTION_RELAX
},
2204 {"mno-relax", no_argument
, NULL
, OPTION_NO_RELAX
},
2206 {NULL
, no_argument
, NULL
, 0}
2208 size_t md_longopts_size
= sizeof (md_longopts
);
2211 FLOAT_ABI_DEFAULT
= -1,
2217 static enum float_abi float_abi
= FLOAT_ABI_DEFAULT
;
2220 riscv_set_abi (unsigned new_xlen
, enum float_abi new_float_abi
, bfd_boolean rve
)
2222 abi_xlen
= new_xlen
;
2223 float_abi
= new_float_abi
;
2228 md_parse_option (int c
, const char *arg
)
2233 riscv_set_arch (arg
);
2237 riscv_opts
.pic
= FALSE
;
2241 riscv_opts
.pic
= TRUE
;
2245 if (strcmp (arg
, "ilp32") == 0)
2246 riscv_set_abi (32, FLOAT_ABI_SOFT
, FALSE
);
2247 else if (strcmp (arg
, "ilp32e") == 0)
2248 riscv_set_abi (32, FLOAT_ABI_SOFT
, TRUE
);
2249 else if (strcmp (arg
, "ilp32f") == 0)
2250 riscv_set_abi (32, FLOAT_ABI_SINGLE
, FALSE
);
2251 else if (strcmp (arg
, "ilp32d") == 0)
2252 riscv_set_abi (32, FLOAT_ABI_DOUBLE
, FALSE
);
2253 else if (strcmp (arg
, "ilp32q") == 0)
2254 riscv_set_abi (32, FLOAT_ABI_QUAD
, FALSE
);
2255 else if (strcmp (arg
, "lp64") == 0)
2256 riscv_set_abi (64, FLOAT_ABI_SOFT
, FALSE
);
2257 else if (strcmp (arg
, "lp64f") == 0)
2258 riscv_set_abi (64, FLOAT_ABI_SINGLE
, FALSE
);
2259 else if (strcmp (arg
, "lp64d") == 0)
2260 riscv_set_abi (64, FLOAT_ABI_DOUBLE
, FALSE
);
2261 else if (strcmp (arg
, "lp64q") == 0)
2262 riscv_set_abi (64, FLOAT_ABI_QUAD
, FALSE
);
2268 riscv_opts
.relax
= TRUE
;
2271 case OPTION_NO_RELAX
:
2272 riscv_opts
.relax
= FALSE
;
2283 riscv_after_parse_args (void)
2287 if (strcmp (default_arch
, "riscv32") == 0)
2289 else if (strcmp (default_arch
, "riscv64") == 0)
2292 as_bad ("unknown default architecture `%s'", default_arch
);
2295 if (riscv_subsets
== NULL
)
2296 riscv_set_arch (xlen
== 64 ? "rv64g" : "rv32g");
2298 /* Add the RVC extension, regardless of -march, to support .option rvc. */
2299 riscv_set_rvc (FALSE
);
2300 if (riscv_subset_supports ("c"))
2301 riscv_set_rvc (TRUE
);
2303 riscv_add_subset ("c");
2305 /* Enable RVE if specified by the -march option. */
2306 riscv_set_rve (FALSE
);
2307 if (riscv_subset_supports ("e"))
2308 riscv_set_rve (TRUE
);
2310 /* Infer ABI from ISA if not specified on command line. */
2313 else if (abi_xlen
> xlen
)
2314 as_bad ("can't have %d-bit ABI on %d-bit ISA", abi_xlen
, xlen
);
2315 else if (abi_xlen
< xlen
)
2316 as_bad ("%d-bit ABI not yet supported on %d-bit ISA", abi_xlen
, xlen
);
2318 if (float_abi
== FLOAT_ABI_DEFAULT
)
2320 struct riscv_subset
*subset
;
2322 /* Assume soft-float unless D extension is present. */
2323 float_abi
= FLOAT_ABI_SOFT
;
2325 for (subset
= riscv_subsets
; subset
!= NULL
; subset
= subset
->next
)
2327 if (strcasecmp (subset
->name
, "D") == 0)
2328 float_abi
= FLOAT_ABI_DOUBLE
;
2329 if (strcasecmp (subset
->name
, "Q") == 0)
2330 float_abi
= FLOAT_ABI_QUAD
;
2335 elf_flags
|= EF_RISCV_RVE
;
2337 /* Insert float_abi into the EF_RISCV_FLOAT_ABI field of elf_flags. */
2338 elf_flags
|= float_abi
* (EF_RISCV_FLOAT_ABI
& ~(EF_RISCV_FLOAT_ABI
<< 1));
2342 md_pcrel_from (fixS
*fixP
)
2344 return fixP
->fx_where
+ fixP
->fx_frag
->fr_address
;
2347 /* Apply a fixup to the object file. */
2350 md_apply_fix (fixS
*fixP
, valueT
*valP
, segT seg ATTRIBUTE_UNUSED
)
2352 unsigned int subtype
;
2353 bfd_byte
*buf
= (bfd_byte
*) (fixP
->fx_frag
->fr_literal
+ fixP
->fx_where
);
2354 bfd_boolean relaxable
= FALSE
;
2358 /* Remember value for tc_gen_reloc. */
2359 fixP
->fx_addnumber
= *valP
;
2361 switch (fixP
->fx_r_type
)
2363 case BFD_RELOC_RISCV_HI20
:
2364 case BFD_RELOC_RISCV_LO12_I
:
2365 case BFD_RELOC_RISCV_LO12_S
:
2366 bfd_putl32 (riscv_apply_const_reloc (fixP
->fx_r_type
, *valP
)
2367 | bfd_getl32 (buf
), buf
);
2368 if (fixP
->fx_addsy
== NULL
)
2369 fixP
->fx_done
= TRUE
;
2373 case BFD_RELOC_RISCV_GOT_HI20
:
2374 case BFD_RELOC_RISCV_ADD8
:
2375 case BFD_RELOC_RISCV_ADD16
:
2376 case BFD_RELOC_RISCV_ADD32
:
2377 case BFD_RELOC_RISCV_ADD64
:
2378 case BFD_RELOC_RISCV_SUB6
:
2379 case BFD_RELOC_RISCV_SUB8
:
2380 case BFD_RELOC_RISCV_SUB16
:
2381 case BFD_RELOC_RISCV_SUB32
:
2382 case BFD_RELOC_RISCV_SUB64
:
2383 case BFD_RELOC_RISCV_RELAX
:
2386 case BFD_RELOC_RISCV_TPREL_HI20
:
2387 case BFD_RELOC_RISCV_TPREL_LO12_I
:
2388 case BFD_RELOC_RISCV_TPREL_LO12_S
:
2389 case BFD_RELOC_RISCV_TPREL_ADD
:
2393 case BFD_RELOC_RISCV_TLS_GOT_HI20
:
2394 case BFD_RELOC_RISCV_TLS_GD_HI20
:
2395 case BFD_RELOC_RISCV_TLS_DTPREL32
:
2396 case BFD_RELOC_RISCV_TLS_DTPREL64
:
2397 if (fixP
->fx_addsy
!= NULL
)
2398 S_SET_THREAD_LOCAL (fixP
->fx_addsy
);
2400 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
2401 _("TLS relocation against a constant"));
2405 /* Use pc-relative relocation for FDE initial location.
2406 The symbol address in .eh_frame may be adjusted in
2407 _bfd_elf_discard_section_eh_frame, and the content of
2408 .eh_frame will be adjusted in _bfd_elf_write_section_eh_frame.
2409 Therefore, we cannot insert a relocation whose addend symbol is
2410 in .eh_frame. Othrewise, the value may be adjusted twice.*/
2411 if (fixP
->fx_addsy
&& fixP
->fx_subsy
2412 && (sub_segment
= S_GET_SEGMENT (fixP
->fx_subsy
))
2413 && strcmp (sub_segment
->name
, ".eh_frame") == 0
2414 && S_GET_VALUE (fixP
->fx_subsy
)
2415 == fixP
->fx_frag
->fr_address
+ fixP
->fx_where
)
2417 fixP
->fx_r_type
= BFD_RELOC_RISCV_32_PCREL
;
2418 fixP
->fx_subsy
= NULL
;
2425 case BFD_RELOC_RISCV_CFA
:
2426 if (fixP
->fx_addsy
&& fixP
->fx_subsy
)
2428 fixP
->fx_next
= xmemdup (fixP
, sizeof (*fixP
), sizeof (*fixP
));
2429 fixP
->fx_next
->fx_addsy
= fixP
->fx_subsy
;
2430 fixP
->fx_next
->fx_subsy
= NULL
;
2431 fixP
->fx_next
->fx_offset
= 0;
2432 fixP
->fx_subsy
= NULL
;
2434 switch (fixP
->fx_r_type
)
2437 fixP
->fx_r_type
= BFD_RELOC_RISCV_ADD64
;
2438 fixP
->fx_next
->fx_r_type
= BFD_RELOC_RISCV_SUB64
;
2442 fixP
->fx_r_type
= BFD_RELOC_RISCV_ADD32
;
2443 fixP
->fx_next
->fx_r_type
= BFD_RELOC_RISCV_SUB32
;
2447 fixP
->fx_r_type
= BFD_RELOC_RISCV_ADD16
;
2448 fixP
->fx_next
->fx_r_type
= BFD_RELOC_RISCV_SUB16
;
2452 fixP
->fx_r_type
= BFD_RELOC_RISCV_ADD8
;
2453 fixP
->fx_next
->fx_r_type
= BFD_RELOC_RISCV_SUB8
;
2456 case BFD_RELOC_RISCV_CFA
:
2457 /* Load the byte to get the subtype. */
2458 subtype
= bfd_get_8 (NULL
, &((fragS
*) (fixP
->fx_frag
->fr_opcode
))->fr_literal
[fixP
->fx_where
]);
2459 loc
= fixP
->fx_frag
->fr_fix
- (subtype
& 7);
2462 case DW_CFA_advance_loc1
:
2463 fixP
->fx_where
= loc
+ 1;
2464 fixP
->fx_next
->fx_where
= loc
+ 1;
2465 fixP
->fx_r_type
= BFD_RELOC_RISCV_SET8
;
2466 fixP
->fx_next
->fx_r_type
= BFD_RELOC_RISCV_SUB8
;
2469 case DW_CFA_advance_loc2
:
2471 fixP
->fx_next
->fx_size
= 2;
2472 fixP
->fx_where
= loc
+ 1;
2473 fixP
->fx_next
->fx_where
= loc
+ 1;
2474 fixP
->fx_r_type
= BFD_RELOC_RISCV_SET16
;
2475 fixP
->fx_next
->fx_r_type
= BFD_RELOC_RISCV_SUB16
;
2478 case DW_CFA_advance_loc4
:
2480 fixP
->fx_next
->fx_size
= 4;
2481 fixP
->fx_where
= loc
;
2482 fixP
->fx_next
->fx_where
= loc
;
2483 fixP
->fx_r_type
= BFD_RELOC_RISCV_SET32
;
2484 fixP
->fx_next
->fx_r_type
= BFD_RELOC_RISCV_SUB32
;
2488 if (subtype
< 0x80 && (subtype
& 0x40))
2490 /* DW_CFA_advance_loc */
2491 fixP
->fx_frag
= (fragS
*) fixP
->fx_frag
->fr_opcode
;
2492 fixP
->fx_next
->fx_frag
= fixP
->fx_frag
;
2493 fixP
->fx_r_type
= BFD_RELOC_RISCV_SET6
;
2494 fixP
->fx_next
->fx_r_type
= BFD_RELOC_RISCV_SUB6
;
2497 as_fatal (_("internal error: bad CFA value #%d"), subtype
);
2503 /* This case is unreachable. */
2510 /* If we are deleting this reloc entry, we must fill in the
2511 value now. This can happen if we have a .word which is not
2512 resolved when it appears but is later defined. */
2513 if (fixP
->fx_addsy
== NULL
)
2515 gas_assert (fixP
->fx_size
<= sizeof (valueT
));
2516 md_number_to_chars ((char *) buf
, *valP
, fixP
->fx_size
);
2521 case BFD_RELOC_RISCV_JMP
:
2524 /* Fill in a tentative value to improve objdump readability. */
2525 bfd_vma target
= S_GET_VALUE (fixP
->fx_addsy
) + *valP
;
2526 bfd_vma delta
= target
- md_pcrel_from (fixP
);
2527 bfd_putl32 (bfd_getl32 (buf
) | ENCODE_UJTYPE_IMM (delta
), buf
);
2531 case BFD_RELOC_12_PCREL
:
2534 /* Fill in a tentative value to improve objdump readability. */
2535 bfd_vma target
= S_GET_VALUE (fixP
->fx_addsy
) + *valP
;
2536 bfd_vma delta
= target
- md_pcrel_from (fixP
);
2537 bfd_putl32 (bfd_getl32 (buf
) | ENCODE_SBTYPE_IMM (delta
), buf
);
2541 case BFD_RELOC_RISCV_RVC_BRANCH
:
2544 /* Fill in a tentative value to improve objdump readability. */
2545 bfd_vma target
= S_GET_VALUE (fixP
->fx_addsy
) + *valP
;
2546 bfd_vma delta
= target
- md_pcrel_from (fixP
);
2547 bfd_putl16 (bfd_getl16 (buf
) | ENCODE_RVC_B_IMM (delta
), buf
);
2551 case BFD_RELOC_RISCV_RVC_JUMP
:
2554 /* Fill in a tentative value to improve objdump readability. */
2555 bfd_vma target
= S_GET_VALUE (fixP
->fx_addsy
) + *valP
;
2556 bfd_vma delta
= target
- md_pcrel_from (fixP
);
2557 bfd_putl16 (bfd_getl16 (buf
) | ENCODE_RVC_J_IMM (delta
), buf
);
2561 case BFD_RELOC_RISCV_CALL
:
2562 case BFD_RELOC_RISCV_CALL_PLT
:
2566 case BFD_RELOC_RISCV_PCREL_HI20
:
2567 case BFD_RELOC_RISCV_PCREL_LO12_S
:
2568 case BFD_RELOC_RISCV_PCREL_LO12_I
:
2569 relaxable
= riscv_opts
.relax
;
2572 case BFD_RELOC_RISCV_ALIGN
:
2576 /* We ignore generic BFD relocations we don't know about. */
2577 if (bfd_reloc_type_lookup (stdoutput
, fixP
->fx_r_type
) != NULL
)
2578 as_fatal (_("internal error: bad relocation #%d"), fixP
->fx_r_type
);
2581 if (fixP
->fx_subsy
!= NULL
)
2582 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
2583 _("unsupported symbol subtraction"));
2585 /* Add an R_RISCV_RELAX reloc if the reloc is relaxable. */
2586 if (relaxable
&& fixP
->fx_tcbit
&& fixP
->fx_addsy
!= NULL
)
2588 fixP
->fx_next
= xmemdup (fixP
, sizeof (*fixP
), sizeof (*fixP
));
2589 fixP
->fx_next
->fx_addsy
= fixP
->fx_next
->fx_subsy
= NULL
;
2590 fixP
->fx_next
->fx_r_type
= BFD_RELOC_RISCV_RELAX
;
2594 /* Because the value of .cfi_remember_state may changed after relaxation,
2595 we insert a fix to relocate it again in link-time. */
2598 riscv_pre_output_hook (void)
2600 const frchainS
*frch
;
2603 for (s
= stdoutput
->sections
; s
; s
= s
->next
)
2604 for (frch
= seg_info (s
)->frchainP
; frch
; frch
= frch
->frch_next
)
2608 for (frag
= frch
->frch_root
; frag
; frag
= frag
->fr_next
)
2610 if (frag
->fr_type
== rs_cfa
)
2614 symbolS
*add_symbol
= frag
->fr_symbol
->sy_value
.X_add_symbol
;
2615 symbolS
*op_symbol
= frag
->fr_symbol
->sy_value
.X_op_symbol
;
2617 exp
.X_op
= O_subtract
;
2618 exp
.X_add_symbol
= add_symbol
;
2619 exp
.X_add_number
= 0;
2620 exp
.X_op_symbol
= op_symbol
;
2622 fix_new_exp (frag
, (int) frag
->fr_offset
, 1, &exp
, 0,
2623 BFD_RELOC_RISCV_CFA
);
2630 /* This structure is used to hold a stack of .option values. */
2632 struct riscv_option_stack
2634 struct riscv_option_stack
*next
;
2635 struct riscv_set_options options
;
2638 static struct riscv_option_stack
*riscv_opts_stack
;
2640 /* Handle the .option pseudo-op. */
2643 s_riscv_option (int x ATTRIBUTE_UNUSED
)
2645 char *name
= input_line_pointer
, ch
;
2647 while (!is_end_of_line
[(unsigned char) *input_line_pointer
])
2648 ++input_line_pointer
;
2649 ch
= *input_line_pointer
;
2650 *input_line_pointer
= '\0';
2652 if (strcmp (name
, "rvc") == 0)
2653 riscv_set_rvc (TRUE
);
2654 else if (strcmp (name
, "norvc") == 0)
2655 riscv_set_rvc (FALSE
);
2656 else if (strcmp (name
, "pic") == 0)
2657 riscv_opts
.pic
= TRUE
;
2658 else if (strcmp (name
, "nopic") == 0)
2659 riscv_opts
.pic
= FALSE
;
2660 else if (strcmp (name
, "relax") == 0)
2661 riscv_opts
.relax
= TRUE
;
2662 else if (strcmp (name
, "norelax") == 0)
2663 riscv_opts
.relax
= FALSE
;
2664 else if (strcmp (name
, "push") == 0)
2666 struct riscv_option_stack
*s
;
2668 s
= (struct riscv_option_stack
*) xmalloc (sizeof *s
);
2669 s
->next
= riscv_opts_stack
;
2670 s
->options
= riscv_opts
;
2671 riscv_opts_stack
= s
;
2673 else if (strcmp (name
, "pop") == 0)
2675 struct riscv_option_stack
*s
;
2677 s
= riscv_opts_stack
;
2679 as_bad (_(".option pop with no .option push"));
2682 riscv_opts
= s
->options
;
2683 riscv_opts_stack
= s
->next
;
2689 as_warn (_("Unrecognized .option directive: %s\n"), name
);
2691 *input_line_pointer
= ch
;
2692 demand_empty_rest_of_line ();
2695 /* Handle the .dtprelword and .dtpreldword pseudo-ops. They generate
2696 a 32-bit or 64-bit DTP-relative relocation (BYTES says which) for
2697 use in DWARF debug information. */
2700 s_dtprel (int bytes
)
2707 if (ex
.X_op
!= O_symbol
)
2709 as_bad (_("Unsupported use of %s"), (bytes
== 8
2712 ignore_rest_of_line ();
2715 p
= frag_more (bytes
);
2716 md_number_to_chars (p
, 0, bytes
);
2717 fix_new_exp (frag_now
, p
- frag_now
->fr_literal
, bytes
, &ex
, FALSE
,
2719 ? BFD_RELOC_RISCV_TLS_DTPREL64
2720 : BFD_RELOC_RISCV_TLS_DTPREL32
));
2722 demand_empty_rest_of_line ();
2725 /* Handle the .bss pseudo-op. */
2728 s_bss (int ignore ATTRIBUTE_UNUSED
)
2730 subseg_set (bss_section
, 0);
2731 demand_empty_rest_of_line ();
2735 riscv_make_nops (char *buf
, bfd_vma bytes
)
2739 /* RISC-V instructions cannot begin or end on odd addresses, so this case
2740 means we are not within a valid instruction sequence. It is thus safe
2741 to use a zero byte, even though that is not a valid instruction. */
2745 /* Use at most one 2-byte NOP. */
2746 if ((bytes
- i
) % 4 == 2)
2748 md_number_to_chars (buf
+ i
, RVC_NOP
, 2);
2752 /* Fill the remainder with 4-byte NOPs. */
2753 for ( ; i
< bytes
; i
+= 4)
2754 md_number_to_chars (buf
+ i
, RISCV_NOP
, 4);
2757 /* Called from md_do_align. Used to create an alignment frag in a
2758 code section by emitting a worst-case NOP sequence that the linker
2759 will later relax to the correct number of NOPs. We can't compute
2760 the correct alignment now because of other linker relaxations. */
2763 riscv_frag_align_code (int n
)
2765 bfd_vma bytes
= (bfd_vma
) 1 << n
;
2766 bfd_vma insn_alignment
= riscv_opts
.rvc
? 2 : 4;
2767 bfd_vma worst_case_bytes
= bytes
- insn_alignment
;
2771 /* If we are moving to a smaller alignment than the instruction size, then no
2772 alignment is required. */
2773 if (bytes
<= insn_alignment
)
2776 /* When not relaxing, riscv_handle_align handles code alignment. */
2777 if (!riscv_opts
.relax
)
2780 nops
= frag_more (worst_case_bytes
);
2782 ex
.X_op
= O_constant
;
2783 ex
.X_add_number
= worst_case_bytes
;
2785 riscv_make_nops (nops
, worst_case_bytes
);
2787 fix_new_exp (frag_now
, nops
- frag_now
->fr_literal
, 0,
2788 &ex
, FALSE
, BFD_RELOC_RISCV_ALIGN
);
2793 /* Implement HANDLE_ALIGN. */
2796 riscv_handle_align (fragS
*fragP
)
2798 switch (fragP
->fr_type
)
2801 /* When relaxing, riscv_frag_align_code handles code alignment. */
2802 if (!riscv_opts
.relax
)
2804 bfd_signed_vma bytes
= (fragP
->fr_next
->fr_address
2805 - fragP
->fr_address
- fragP
->fr_fix
);
2806 /* We have 4 byte uncompressed nops. */
2807 bfd_signed_vma size
= 4;
2808 bfd_signed_vma excess
= bytes
% size
;
2809 char *p
= fragP
->fr_literal
+ fragP
->fr_fix
;
2814 /* Insert zeros or compressed nops to get 4 byte alignment. */
2817 riscv_make_nops (p
, excess
);
2818 fragP
->fr_fix
+= excess
;
2822 /* Insert variable number of 4 byte uncompressed nops. */
2823 riscv_make_nops (p
, size
);
2824 fragP
->fr_var
= size
;
2834 md_estimate_size_before_relax (fragS
*fragp
, asection
*segtype
)
2836 return (fragp
->fr_var
= relaxed_branch_length (fragp
, segtype
, FALSE
));
2839 /* Translate internal representation of relocation info to BFD target
2843 tc_gen_reloc (asection
*section ATTRIBUTE_UNUSED
, fixS
*fixp
)
2845 arelent
*reloc
= (arelent
*) xmalloc (sizeof (arelent
));
2847 reloc
->sym_ptr_ptr
= (asymbol
**) xmalloc (sizeof (asymbol
*));
2848 *reloc
->sym_ptr_ptr
= symbol_get_bfdsym (fixp
->fx_addsy
);
2849 reloc
->address
= fixp
->fx_frag
->fr_address
+ fixp
->fx_where
;
2850 reloc
->addend
= fixp
->fx_addnumber
;
2852 reloc
->howto
= bfd_reloc_type_lookup (stdoutput
, fixp
->fx_r_type
);
2853 if (reloc
->howto
== NULL
)
2855 if ((fixp
->fx_r_type
== BFD_RELOC_16
|| fixp
->fx_r_type
== BFD_RELOC_8
)
2856 && fixp
->fx_addsy
!= NULL
&& fixp
->fx_subsy
!= NULL
)
2858 /* We don't have R_RISCV_8/16, but for this special case,
2859 we can use R_RISCV_ADD8/16 with R_RISCV_SUB8/16. */
2863 as_bad_where (fixp
->fx_file
, fixp
->fx_line
,
2864 _("cannot represent %s relocation in object file"),
2865 bfd_get_reloc_code_name (fixp
->fx_r_type
));
2873 riscv_relax_frag (asection
*sec
, fragS
*fragp
, long stretch ATTRIBUTE_UNUSED
)
2875 if (RELAX_BRANCH_P (fragp
->fr_subtype
))
2877 offsetT old_var
= fragp
->fr_var
;
2878 fragp
->fr_var
= relaxed_branch_length (fragp
, sec
, TRUE
);
2879 return fragp
->fr_var
- old_var
;
2885 /* Expand far branches to multi-instruction sequences. */
2888 md_convert_frag_branch (fragS
*fragp
)
2896 buf
= (bfd_byte
*)fragp
->fr_literal
+ fragp
->fr_fix
;
2898 exp
.X_op
= O_symbol
;
2899 exp
.X_add_symbol
= fragp
->fr_symbol
;
2900 exp
.X_add_number
= fragp
->fr_offset
;
2902 gas_assert (fragp
->fr_var
== RELAX_BRANCH_LENGTH (fragp
->fr_subtype
));
2904 if (RELAX_BRANCH_RVC (fragp
->fr_subtype
))
2906 switch (RELAX_BRANCH_LENGTH (fragp
->fr_subtype
))
2910 /* Expand the RVC branch into a RISC-V one. */
2911 insn
= bfd_getl16 (buf
);
2912 rs1
= 8 + ((insn
>> OP_SH_CRS1S
) & OP_MASK_CRS1S
);
2913 if ((insn
& MASK_C_J
) == MATCH_C_J
)
2915 else if ((insn
& MASK_C_JAL
) == MATCH_C_JAL
)
2916 insn
= MATCH_JAL
| (X_RA
<< OP_SH_RD
);
2917 else if ((insn
& MASK_C_BEQZ
) == MATCH_C_BEQZ
)
2918 insn
= MATCH_BEQ
| (rs1
<< OP_SH_RS1
);
2919 else if ((insn
& MASK_C_BNEZ
) == MATCH_C_BNEZ
)
2920 insn
= MATCH_BNE
| (rs1
<< OP_SH_RS1
);
2923 bfd_putl32 (insn
, buf
);
2927 /* Invert the branch condition. Branch over the jump. */
2928 insn
= bfd_getl16 (buf
);
2929 insn
^= MATCH_C_BEQZ
^ MATCH_C_BNEZ
;
2930 insn
|= ENCODE_RVC_B_IMM (6);
2931 bfd_putl16 (insn
, buf
);
2936 /* Just keep the RVC branch. */
2937 reloc
= RELAX_BRANCH_UNCOND (fragp
->fr_subtype
)
2938 ? BFD_RELOC_RISCV_RVC_JUMP
: BFD_RELOC_RISCV_RVC_BRANCH
;
2939 fixp
= fix_new_exp (fragp
, buf
- (bfd_byte
*)fragp
->fr_literal
,
2940 2, &exp
, FALSE
, reloc
);
2949 switch (RELAX_BRANCH_LENGTH (fragp
->fr_subtype
))
2952 gas_assert (!RELAX_BRANCH_UNCOND (fragp
->fr_subtype
));
2954 /* Invert the branch condition. Branch over the jump. */
2955 insn
= bfd_getl32 (buf
);
2956 insn
^= MATCH_BEQ
^ MATCH_BNE
;
2957 insn
|= ENCODE_SBTYPE_IMM (8);
2958 md_number_to_chars ((char *) buf
, insn
, 4);
2962 /* Jump to the target. */
2963 fixp
= fix_new_exp (fragp
, buf
- (bfd_byte
*)fragp
->fr_literal
,
2964 4, &exp
, FALSE
, BFD_RELOC_RISCV_JMP
);
2965 md_number_to_chars ((char *) buf
, MATCH_JAL
, 4);
2970 reloc
= RELAX_BRANCH_UNCOND (fragp
->fr_subtype
)
2971 ? BFD_RELOC_RISCV_JMP
: BFD_RELOC_12_PCREL
;
2972 fixp
= fix_new_exp (fragp
, buf
- (bfd_byte
*)fragp
->fr_literal
,
2973 4, &exp
, FALSE
, reloc
);
2982 fixp
->fx_file
= fragp
->fr_file
;
2983 fixp
->fx_line
= fragp
->fr_line
;
2985 gas_assert (buf
== (bfd_byte
*)fragp
->fr_literal
2986 + fragp
->fr_fix
+ fragp
->fr_var
);
2988 fragp
->fr_fix
+= fragp
->fr_var
;
2991 /* Relax a machine dependent frag. This returns the amount by which
2992 the current size of the frag should change. */
2995 md_convert_frag (bfd
*abfd ATTRIBUTE_UNUSED
, segT asec ATTRIBUTE_UNUSED
,
2998 gas_assert (RELAX_BRANCH_P (fragp
->fr_subtype
));
2999 md_convert_frag_branch (fragp
);
3003 md_show_usage (FILE *stream
)
3005 fprintf (stream
, _("\
3007 -fpic generate position-independent code\n\
3008 -fno-pic don't generate position-independent code (default)\n\
3009 -march=ISA set the RISC-V architecture\n\
3010 -mabi=ABI set the RISC-V ABI\n\
3011 -mrelax enable relax (default)\n\
3012 -mno-relax disable relax\n\
3016 /* Standard calling conventions leave the CFA at SP on entry. */
3018 riscv_cfi_frame_initial_instructions (void)
3020 cfi_add_CFA_def_cfa_register (X_SP
);
3024 tc_riscv_regname_to_dw2regnum (char *regname
)
3028 if ((reg
= reg_lookup_internal (regname
, RCLASS_GPR
)) >= 0)
3031 if ((reg
= reg_lookup_internal (regname
, RCLASS_FPR
)) >= 0)
3034 as_bad (_("unknown register `%s'"), regname
);
3039 riscv_elf_final_processing (void)
3041 elf_elfheader (stdoutput
)->e_flags
|= elf_flags
;
3044 /* Parse the .sleb128 and .uleb128 pseudos. Only allow constant expressions,
3045 since these directives break relaxation when used with symbol deltas. */
3048 s_riscv_leb128 (int sign
)
3051 char *save_in
= input_line_pointer
;
3054 if (exp
.X_op
!= O_constant
)
3055 as_bad (_("non-constant .%cleb128 is not supported"), sign
? 's' : 'u');
3056 demand_empty_rest_of_line ();
3058 input_line_pointer
= save_in
;
3059 return s_leb128 (sign
);
3062 /* Parse the .insn directive. */
3065 s_riscv_insn (int x ATTRIBUTE_UNUSED
)
3067 char *str
= input_line_pointer
;
3068 struct riscv_cl_insn insn
;
3069 expressionS imm_expr
;
3070 bfd_reloc_code_real_type imm_reloc
= BFD_RELOC_UNUSED
;
3073 while (!is_end_of_line
[(unsigned char) *input_line_pointer
])
3074 ++input_line_pointer
;
3076 save_c
= *input_line_pointer
;
3077 *input_line_pointer
= '\0';
3079 const char *error
= riscv_ip (str
, &insn
, &imm_expr
,
3080 &imm_reloc
, insn_type_hash
);
3084 as_bad ("%s `%s'", error
, str
);
3088 gas_assert (insn
.insn_mo
->pinfo
!= INSN_MACRO
);
3089 append_insn (&insn
, &imm_expr
, imm_reloc
);
3092 *input_line_pointer
= save_c
;
3093 demand_empty_rest_of_line ();
3096 /* Pseudo-op table. */
3098 static const pseudo_typeS riscv_pseudo_table
[] =
3100 /* RISC-V-specific pseudo-ops. */
3101 {"option", s_riscv_option
, 0},
3105 {"dtprelword", s_dtprel
, 4},
3106 {"dtpreldword", s_dtprel
, 8},
3108 {"uleb128", s_riscv_leb128
, 0},
3109 {"sleb128", s_riscv_leb128
, 1},
3110 {"insn", s_riscv_insn
, 0},
3116 riscv_pop_insert (void)
3118 extern void pop_insert (const pseudo_typeS
*);
3120 pop_insert (riscv_pseudo_table
);