]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blame - gas/config/tc-riscv.c
Fix a const-safety issue on GCC-4.9 and above
[thirdparty/binutils-gdb.git] / gas / config / tc-riscv.c
CommitLineData
e23eba97
NC
1/* tc-riscv.c -- RISC-V assembler
2 Copyright 2011-2016 Free Software Foundation, Inc.
3
4 Contributed by Andrew Waterman (andrew@sifive.com).
5 Based on MIPS target.
6
7 This file is part of GAS.
8
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)
12 any later version.
13
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.
18
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/>. */
22
23#include "as.h"
24#include "config.h"
25#include "subsegs.h"
26#include "safe-ctype.h"
27
28#include "itbl-ops.h"
29#include "dwarf2dbg.h"
30#include "dw2gencfi.h"
1d65abb5 31#include "struc-symbol.h"
e23eba97
NC
32
33#include "elf/riscv.h"
34#include "opcode/riscv.h"
35
36#include <stdint.h>
37
38/* Information about an instruction, including its format, operands
39 and fixups. */
40struct riscv_cl_insn
41{
42 /* The opcode's entry in riscv_opcodes. */
43 const struct riscv_opcode *insn_mo;
44
45 /* The encoded instruction bits. */
46 insn_t insn_opcode;
47
48 /* The frag that contains the instruction. */
49 struct frag *frag;
50
51 /* The offset into FRAG of the first instruction byte. */
52 long where;
53
54 /* The relocs associated with the instruction, if any. */
55 fixS *fixp;
56};
57
58#ifndef DEFAULT_ARCH
59#define DEFAULT_ARCH "riscv64"
60#endif
61
62static const char default_arch[] = DEFAULT_ARCH;
63
2922d21d
AW
64static unsigned xlen = 0; /* width of an x-register */
65static unsigned abi_xlen = 0; /* width of a pointer in the ABI */
e23eba97 66
2922d21d 67#define LOAD_ADDRESS_INSN (abi_xlen == 64 ? "ld" : "lw")
e23eba97
NC
68#define ADD32_INSN (xlen == 64 ? "addiw" : "addi")
69
70static unsigned elf_flags = 0;
71
72/* This is the set of options which the .option pseudo-op may modify. */
73
74struct riscv_set_options
75{
76 int pic; /* Generate position-independent code. */
77 int rvc; /* Generate RVC code. */
45f76423 78 int relax; /* Emit relocs the linker is allowed to relax. */
e23eba97
NC
79};
80
81static struct riscv_set_options riscv_opts =
82{
83 0, /* pic */
84 0, /* rvc */
45f76423 85 1, /* relax */
e23eba97
NC
86};
87
88static void
89riscv_set_rvc (bfd_boolean rvc_value)
90{
91 if (rvc_value)
92 elf_flags |= EF_RISCV_RVC;
93
94 riscv_opts.rvc = rvc_value;
95}
96
97struct riscv_subset
98{
99 const char *name;
100
101 struct riscv_subset *next;
102};
103
104static struct riscv_subset *riscv_subsets;
105
106static bfd_boolean
107riscv_subset_supports (const char *feature)
108{
109 struct riscv_subset *s;
110 char *p;
111 unsigned xlen_required = strtoul (feature, &p, 10);
112
113 if (xlen_required && xlen != xlen_required)
114 return FALSE;
115
116 for (s = riscv_subsets; s != NULL; s = s->next)
117 if (strcasecmp (s->name, p) == 0)
118 return TRUE;
119
120 return FALSE;
121}
122
123static void
124riscv_add_subset (const char *subset)
125{
126 struct riscv_subset *s = xmalloc (sizeof *s);
127
128 s->name = xstrdup (subset);
129 s->next = riscv_subsets;
130 riscv_subsets = s;
131}
132
2922d21d 133/* Set which ISA and extensions are available. */
e23eba97 134
e23eba97 135static void
2922d21d 136riscv_set_arch (const char *s)
e23eba97 137{
2922d21d 138 const char *all_subsets = "imafdc";
e23eba97 139 const char *extension = NULL;
2922d21d 140 const char *p = s;
e23eba97 141
2922d21d 142 if (strncmp (p, "rv32", 4) == 0)
e23eba97
NC
143 {
144 xlen = 32;
145 p += 4;
146 }
2922d21d 147 else if (strncmp (p, "rv64", 4) == 0)
e23eba97
NC
148 {
149 xlen = 64;
150 p += 4;
151 }
2922d21d
AW
152 else
153 as_fatal ("-march=%s: ISA string must begin with rv32 or rv64", s);
e23eba97 154
2922d21d 155 switch (*p)
e23eba97 156 {
2922d21d 157 case 'i':
e23eba97
NC
158 break;
159
2922d21d 160 case 'g':
e23eba97 161 p++;
2922d21d 162 for ( ; *all_subsets != 'c'; all_subsets++)
e23eba97 163 {
2922d21d 164 const char subset[] = {*all_subsets, '\0'};
e23eba97
NC
165 riscv_add_subset (subset);
166 }
167 break;
168
169 default:
2922d21d 170 as_fatal ("-march=%s: first ISA subset must be `i' or `g'", s);
e23eba97
NC
171 }
172
173 while (*p)
174 {
2922d21d 175 if (*p == 'x')
e23eba97
NC
176 {
177 char *subset = xstrdup (p), *q = subset;
178
179 while (*++q != '\0' && *q != '_')
180 ;
181 *q = '\0';
182
183 if (extension)
2922d21d
AW
184 as_fatal ("-march=%s: only one non-standard extension is supported"
185 " (found `%s' and `%s')", s, extension, subset);
e23eba97
NC
186 extension = subset;
187 riscv_add_subset (subset);
188 p += strlen (subset);
189 free (subset);
190 }
191 else if (*p == '_')
192 p++;
193 else if ((all_subsets = strchr (all_subsets, *p)) != NULL)
194 {
195 const char subset[] = {*p, 0};
196 riscv_add_subset (subset);
e23eba97
NC
197 all_subsets++;
198 p++;
199 }
200 else
2922d21d 201 as_fatal ("-march=%s: unsupported ISA subset `%c'", s, *p);
e23eba97
NC
202 }
203}
204
205/* Handle of the OPCODE hash table. */
206static struct hash_control *op_hash = NULL;
207
208/* This array holds the chars that always start a comment. If the
209 pre-processor is disabled, these aren't very useful */
210const char comment_chars[] = "#";
211
212/* This array holds the chars that only start a comment at the beginning of
213 a line. If the line seems to have the form '# 123 filename'
214 .line and .file directives will appear in the pre-processed output */
215/* Note that input_file.c hand checks for '#' at the beginning of the
216 first line of the input file. This is because the compiler outputs
217 #NO_APP at the beginning of its output. */
218/* Also note that C style comments are always supported. */
219const char line_comment_chars[] = "#";
220
221/* This array holds machine specific line separator characters. */
222const char line_separator_chars[] = ";";
223
224/* Chars that can be used to separate mant from exp in floating point nums */
225const char EXP_CHARS[] = "eE";
226
227/* Chars that mean this number is a floating point constant */
228/* As in 0f12.456 */
229/* or 0d1.2345e12 */
230const char FLT_CHARS[] = "rRsSfFdDxXpP";
231
232/* Macros for encoding relaxation state for RVC branches and far jumps. */
233#define RELAX_BRANCH_ENCODE(uncond, rvc, length) \
234 ((relax_substateT) \
235 (0xc0000000 \
236 | ((uncond) ? 1 : 0) \
237 | ((rvc) ? 2 : 0) \
238 | ((length) << 2)))
239#define RELAX_BRANCH_P(i) (((i) & 0xf0000000) == 0xc0000000)
240#define RELAX_BRANCH_LENGTH(i) (((i) >> 2) & 0xF)
241#define RELAX_BRANCH_RVC(i) (((i) & 2) != 0)
242#define RELAX_BRANCH_UNCOND(i) (((i) & 1) != 0)
243
244/* Is the given value a sign-extended 32-bit value? */
245#define IS_SEXT_32BIT_NUM(x) \
246 (((x) &~ (offsetT) 0x7fffffff) == 0 \
247 || (((x) &~ (offsetT) 0x7fffffff) == ~ (offsetT) 0x7fffffff))
248
249/* Is the given value a zero-extended 32-bit value? Or a negated one? */
250#define IS_ZEXT_32BIT_NUM(x) \
251 (((x) &~ (offsetT) 0xffffffff) == 0 \
252 || (((x) &~ (offsetT) 0xffffffff) == ~ (offsetT) 0xffffffff))
253
254/* Change INSN's opcode so that the operand given by FIELD has value VALUE.
255 INSN is a riscv_cl_insn structure and VALUE is evaluated exactly once. */
256#define INSERT_OPERAND(FIELD, INSN, VALUE) \
257 INSERT_BITS ((INSN).insn_opcode, VALUE, OP_MASK_##FIELD, OP_SH_##FIELD)
258
259/* Determine if an instruction matches an opcode. */
260#define OPCODE_MATCHES(OPCODE, OP) \
261 (((OPCODE) & MASK_##OP) == MATCH_##OP)
262
263static char *expr_end;
264
265/* The default target format to use. */
266
267const char *
268riscv_target_format (void)
269{
270 return xlen == 64 ? "elf64-littleriscv" : "elf32-littleriscv";
271}
272
273/* Return the length of instruction INSN. */
274
275static inline unsigned int
276insn_length (const struct riscv_cl_insn *insn)
277{
278 return riscv_insn_length (insn->insn_opcode);
279}
280
281/* Initialise INSN from opcode entry MO. Leave its position unspecified. */
282
283static void
284create_insn (struct riscv_cl_insn *insn, const struct riscv_opcode *mo)
285{
286 insn->insn_mo = mo;
287 insn->insn_opcode = mo->match;
288 insn->frag = NULL;
289 insn->where = 0;
290 insn->fixp = NULL;
291}
292
293/* Install INSN at the location specified by its "frag" and "where" fields. */
294
295static void
296install_insn (const struct riscv_cl_insn *insn)
297{
298 char *f = insn->frag->fr_literal + insn->where;
299 md_number_to_chars (f, insn->insn_opcode, insn_length (insn));
300}
301
302/* Move INSN to offset WHERE in FRAG. Adjust the fixups accordingly
303 and install the opcode in the new location. */
304
305static void
306move_insn (struct riscv_cl_insn *insn, fragS *frag, long where)
307{
308 insn->frag = frag;
309 insn->where = where;
310 if (insn->fixp != NULL)
311 {
312 insn->fixp->fx_frag = frag;
313 insn->fixp->fx_where = where;
314 }
315 install_insn (insn);
316}
317
318/* Add INSN to the end of the output. */
319
320static void
321add_fixed_insn (struct riscv_cl_insn *insn)
322{
323 char *f = frag_more (insn_length (insn));
324 move_insn (insn, frag_now, f - frag_now->fr_literal);
325}
326
327static void
328add_relaxed_insn (struct riscv_cl_insn *insn, int max_chars, int var,
329 relax_substateT subtype, symbolS *symbol, offsetT offset)
330{
331 frag_grow (max_chars);
332 move_insn (insn, frag_now, frag_more (0) - frag_now->fr_literal);
333 frag_var (rs_machine_dependent, max_chars, var,
334 subtype, symbol, offset, NULL);
335}
336
337/* Compute the length of a branch sequence, and adjust the stored length
338 accordingly. If FRAGP is NULL, the worst-case length is returned. */
339
340static unsigned
341relaxed_branch_length (fragS *fragp, asection *sec, int update)
342{
343 int jump, rvc, length = 8;
344
345 if (!fragp)
346 return length;
347
348 jump = RELAX_BRANCH_UNCOND (fragp->fr_subtype);
349 rvc = RELAX_BRANCH_RVC (fragp->fr_subtype);
350 length = RELAX_BRANCH_LENGTH (fragp->fr_subtype);
351
352 /* Assume jumps are in range; the linker will catch any that aren't. */
353 length = jump ? 4 : 8;
354
355 if (fragp->fr_symbol != NULL
356 && S_IS_DEFINED (fragp->fr_symbol)
357 && sec == S_GET_SEGMENT (fragp->fr_symbol))
358 {
359 offsetT val = S_GET_VALUE (fragp->fr_symbol) + fragp->fr_offset;
360 bfd_vma rvc_range = jump ? RVC_JUMP_REACH : RVC_BRANCH_REACH;
361 val -= fragp->fr_address + fragp->fr_fix;
362
363 if (rvc && (bfd_vma)(val + rvc_range/2) < rvc_range)
364 length = 2;
365 else if ((bfd_vma)(val + RISCV_BRANCH_REACH/2) < RISCV_BRANCH_REACH)
366 length = 4;
367 else if (!jump && rvc)
368 length = 6;
369 }
370
371 if (update)
372 fragp->fr_subtype = RELAX_BRANCH_ENCODE (jump, rvc, length);
373
374 return length;
375}
376
377struct regname
378{
379 const char *name;
380 unsigned int num;
381};
382
383enum reg_class
384{
385 RCLASS_GPR,
386 RCLASS_FPR,
387 RCLASS_CSR,
388 RCLASS_MAX
389};
390
391static struct hash_control *reg_names_hash = NULL;
392
393#define ENCODE_REG_HASH(cls, n) \
394 ((void *)(uintptr_t)((n) * RCLASS_MAX + (cls) + 1))
395#define DECODE_REG_CLASS(hash) (((uintptr_t)(hash) - 1) % RCLASS_MAX)
396#define DECODE_REG_NUM(hash) (((uintptr_t)(hash) - 1) / RCLASS_MAX)
397
398static void
399hash_reg_name (enum reg_class class, const char *name, unsigned n)
400{
401 void *hash = ENCODE_REG_HASH (class, n);
402 const char *retval = hash_insert (reg_names_hash, name, hash);
403
404 if (retval != NULL)
405 as_fatal (_("internal error: can't hash `%s': %s"), name, retval);
406}
407
408static void
409hash_reg_names (enum reg_class class, const char * const names[], unsigned n)
410{
411 unsigned i;
412
413 for (i = 0; i < n; i++)
414 hash_reg_name (class, names[i], i);
415}
416
417static unsigned int
418reg_lookup_internal (const char *s, enum reg_class class)
419{
420 struct regname *r = (struct regname *) hash_find (reg_names_hash, s);
421
422 if (r == NULL || DECODE_REG_CLASS (r) != class)
423 return -1;
424 return DECODE_REG_NUM (r);
425}
426
427static bfd_boolean
428reg_lookup (char **s, enum reg_class class, unsigned int *regnop)
429{
430 char *e;
431 char save_c;
432 int reg = -1;
433
434 /* Find end of name. */
435 e = *s;
436 if (is_name_beginner (*e))
437 ++e;
438 while (is_part_of_name (*e))
439 ++e;
440
441 /* Terminate name. */
442 save_c = *e;
443 *e = '\0';
444
445 /* Look for the register. Advance to next token if one was recognized. */
446 if ((reg = reg_lookup_internal (*s, class)) >= 0)
447 *s = e;
448
449 *e = save_c;
450 if (regnop)
451 *regnop = reg;
452 return reg >= 0;
453}
454
455static bfd_boolean
456arg_lookup (char **s, const char *const *array, size_t size, unsigned *regnop)
457{
458 const char *p = strchr (*s, ',');
459 size_t i, len = p ? (size_t)(p - *s) : strlen (*s);
460
461 for (i = 0; i < size; i++)
462 if (array[i] != NULL && strncmp (array[i], *s, len) == 0)
463 {
464 *regnop = i;
465 *s += len;
466 return TRUE;
467 }
468
469 return FALSE;
470}
471
472/* For consistency checking, verify that all bits are specified either
473 by the match/mask part of the instruction definition, or by the
474 operand list. */
475static bfd_boolean
476validate_riscv_insn (const struct riscv_opcode *opc)
477{
478 const char *p = opc->args;
479 char c;
480 insn_t used_bits = opc->mask;
481 int insn_width = 8 * riscv_insn_length (opc->match);
482 insn_t required_bits = ~0ULL >> (64 - insn_width);
483
484 if ((used_bits & opc->match) != (opc->match & required_bits))
485 {
486 as_bad (_("internal: bad RISC-V opcode (mask error): %s %s"),
487 opc->name, opc->args);
488 return FALSE;
489 }
490
491#define USE_BITS(mask,shift) (used_bits |= ((insn_t)(mask) << (shift)))
492 while (*p)
493 switch (c = *p++)
494 {
495 case 'C': /* RVC */
496 switch (c = *p++)
497 {
1d65abb5 498 case 'a': used_bits |= ENCODE_RVC_J_IMM (-1U); break;
e23eba97
NC
499 case 'c': break; /* RS1, constrained to equal sp */
500 case 'i': used_bits |= ENCODE_RVC_SIMM3(-1U); break;
1d65abb5
AW
501 case 'j': used_bits |= ENCODE_RVC_IMM (-1U); break;
502 case 'k': used_bits |= ENCODE_RVC_LW_IMM (-1U); break;
503 case 'l': used_bits |= ENCODE_RVC_LD_IMM (-1U); break;
504 case 'm': used_bits |= ENCODE_RVC_LWSP_IMM (-1U); break;
505 case 'n': used_bits |= ENCODE_RVC_LDSP_IMM (-1U); break;
506 case 'p': used_bits |= ENCODE_RVC_B_IMM (-1U); break;
e23eba97
NC
507 case 's': USE_BITS (OP_MASK_CRS1S, OP_SH_CRS1S); break;
508 case 't': USE_BITS (OP_MASK_CRS2S, OP_SH_CRS2S); break;
1d65abb5
AW
509 case 'u': used_bits |= ENCODE_RVC_IMM (-1U); break;
510 case 'v': used_bits |= ENCODE_RVC_IMM (-1U); break;
e23eba97
NC
511 case 'w': break; /* RS1S, constrained to equal RD */
512 case 'x': break; /* RS2S, constrained to equal RD */
1d65abb5
AW
513 case 'K': used_bits |= ENCODE_RVC_ADDI4SPN_IMM (-1U); break;
514 case 'L': used_bits |= ENCODE_RVC_ADDI16SP_IMM (-1U); break;
515 case 'M': used_bits |= ENCODE_RVC_SWSP_IMM (-1U); break;
516 case 'N': used_bits |= ENCODE_RVC_SDSP_IMM (-1U); break;
e23eba97
NC
517 case 'U': break; /* RS1, constrained to equal RD */
518 case 'V': USE_BITS (OP_MASK_CRS2, OP_SH_CRS2); break;
1d65abb5
AW
519 case '<': used_bits |= ENCODE_RVC_IMM (-1U); break;
520 case '>': used_bits |= ENCODE_RVC_IMM (-1U); break;
e23eba97
NC
521 case 'T': USE_BITS (OP_MASK_CRS2, OP_SH_CRS2); break;
522 case 'D': USE_BITS (OP_MASK_CRS2S, OP_SH_CRS2S); break;
523 default:
524 as_bad (_("internal: bad RISC-V opcode (unknown operand type `C%c'): %s %s"),
525 c, opc->name, opc->args);
526 return FALSE;
527 }
528 break;
529 case ',': break;
530 case '(': break;
531 case ')': break;
532 case '<': USE_BITS (OP_MASK_SHAMTW, OP_SH_SHAMTW); break;
533 case '>': USE_BITS (OP_MASK_SHAMT, OP_SH_SHAMT); break;
534 case 'A': break;
535 case 'D': USE_BITS (OP_MASK_RD, OP_SH_RD); break;
536 case 'Z': USE_BITS (OP_MASK_RS1, OP_SH_RS1); break;
537 case 'E': USE_BITS (OP_MASK_CSR, OP_SH_CSR); break;
538 case 'I': break;
539 case 'R': USE_BITS (OP_MASK_RS3, OP_SH_RS3); break;
540 case 'S': USE_BITS (OP_MASK_RS1, OP_SH_RS1); break;
541 case 'U': USE_BITS (OP_MASK_RS1, OP_SH_RS1); /* fallthru */
542 case 'T': USE_BITS (OP_MASK_RS2, OP_SH_RS2); break;
543 case 'd': USE_BITS (OP_MASK_RD, OP_SH_RD); break;
544 case 'm': USE_BITS (OP_MASK_RM, OP_SH_RM); break;
545 case 's': USE_BITS (OP_MASK_RS1, OP_SH_RS1); break;
546 case 't': USE_BITS (OP_MASK_RS2, OP_SH_RS2); break;
547 case 'P': USE_BITS (OP_MASK_PRED, OP_SH_PRED); break;
548 case 'Q': USE_BITS (OP_MASK_SUCC, OP_SH_SUCC); break;
549 case 'o':
1d65abb5
AW
550 case 'j': used_bits |= ENCODE_ITYPE_IMM (-1U); break;
551 case 'a': used_bits |= ENCODE_UJTYPE_IMM (-1U); break;
552 case 'p': used_bits |= ENCODE_SBTYPE_IMM (-1U); break;
553 case 'q': used_bits |= ENCODE_STYPE_IMM (-1U); break;
554 case 'u': used_bits |= ENCODE_UTYPE_IMM (-1U); break;
e23eba97
NC
555 case '[': break;
556 case ']': break;
557 case '0': break;
558 default:
559 as_bad (_("internal: bad RISC-V opcode "
560 "(unknown operand type `%c'): %s %s"),
561 c, opc->name, opc->args);
562 return FALSE;
563 }
564#undef USE_BITS
565 if (used_bits != required_bits)
566 {
567 as_bad (_("internal: bad RISC-V opcode (bits 0x%lx undefined): %s %s"),
568 ~(unsigned long)(used_bits & required_bits),
569 opc->name, opc->args);
570 return FALSE;
571 }
572 return TRUE;
573}
574
575struct percent_op_match
576{
577 const char *str;
578 bfd_reloc_code_real_type reloc;
579};
580
581/* This function is called once, at assembler startup time. It should set up
582 all the tables, etc. that the MD part of the assembler will need. */
583
584void
585md_begin (void)
586{
587 int i = 0;
2922d21d 588 unsigned long mach = xlen == 64 ? bfd_mach_riscv64 : bfd_mach_riscv32;
e23eba97 589
2922d21d 590 if (! bfd_set_arch_mach (stdoutput, bfd_arch_riscv, mach))
e23eba97
NC
591 as_warn (_("Could not set architecture and machine"));
592
593 op_hash = hash_new ();
594
595 while (riscv_opcodes[i].name)
596 {
597 const char *name = riscv_opcodes[i].name;
598 const char *hash_error =
599 hash_insert (op_hash, name, (void *) &riscv_opcodes[i]);
600
601 if (hash_error)
602 {
603 fprintf (stderr, _("internal error: can't hash `%s': %s\n"),
604 riscv_opcodes[i].name, hash_error);
605 /* Probably a memory allocation problem? Give up now. */
606 as_fatal (_("Broken assembler. No assembly attempted."));
607 }
608
609 do
610 {
611 if (riscv_opcodes[i].pinfo != INSN_MACRO)
612 {
613 if (!validate_riscv_insn (&riscv_opcodes[i]))
614 as_fatal (_("Broken assembler. No assembly attempted."));
615 }
616 ++i;
617 }
618 while (riscv_opcodes[i].name && !strcmp (riscv_opcodes[i].name, name));
619 }
620
621 reg_names_hash = hash_new ();
622 hash_reg_names (RCLASS_GPR, riscv_gpr_names_numeric, NGPR);
623 hash_reg_names (RCLASS_GPR, riscv_gpr_names_abi, NGPR);
624 hash_reg_names (RCLASS_FPR, riscv_fpr_names_numeric, NFPR);
625 hash_reg_names (RCLASS_FPR, riscv_fpr_names_abi, NFPR);
626
627#define DECLARE_CSR(name, num) hash_reg_name (RCLASS_CSR, #name, num);
628#include "opcode/riscv-opc.h"
629#undef DECLARE_CSR
630
631 /* Set the default alignment for the text section. */
632 record_alignment (text_section, riscv_opts.rvc ? 1 : 2);
633}
634
45f76423
AW
635static insn_t
636riscv_apply_const_reloc (bfd_reloc_code_real_type reloc_type, bfd_vma value)
637{
638 switch (reloc_type)
639 {
640 case BFD_RELOC_32:
641 return value;
642
643 case BFD_RELOC_RISCV_HI20:
644 return ENCODE_UTYPE_IMM (RISCV_CONST_HIGH_PART (value));
645
646 case BFD_RELOC_RISCV_LO12_S:
647 return ENCODE_STYPE_IMM (value);
648
649 case BFD_RELOC_RISCV_LO12_I:
650 return ENCODE_ITYPE_IMM (value);
651
652 default:
653 abort ();
654 }
655}
656
e23eba97
NC
657/* Output an instruction. IP is the instruction information.
658 ADDRESS_EXPR is an operand of the instruction to be used with
659 RELOC_TYPE. */
660
661static void
662append_insn (struct riscv_cl_insn *ip, expressionS *address_expr,
663 bfd_reloc_code_real_type reloc_type)
664{
665 dwarf2_emit_insn (0);
666
667 if (reloc_type != BFD_RELOC_UNUSED)
668 {
669 reloc_howto_type *howto;
670
1d65abb5 671 gas_assert (address_expr);
e23eba97
NC
672 if (reloc_type == BFD_RELOC_12_PCREL
673 || reloc_type == BFD_RELOC_RISCV_JMP)
674 {
675 int j = reloc_type == BFD_RELOC_RISCV_JMP;
676 int best_case = riscv_insn_length (ip->insn_opcode);
677 unsigned worst_case = relaxed_branch_length (NULL, NULL, 0);
678 add_relaxed_insn (ip, worst_case, best_case,
679 RELAX_BRANCH_ENCODE (j, best_case == 2, worst_case),
680 address_expr->X_add_symbol,
681 address_expr->X_add_number);
682 return;
683 }
684 else if (address_expr->X_op == O_constant)
45f76423
AW
685 ip->insn_opcode |= riscv_apply_const_reloc (reloc_type,
686 address_expr->X_add_number);
687 else
e23eba97 688 {
45f76423
AW
689 howto = bfd_reloc_type_lookup (stdoutput, reloc_type);
690 if (howto == NULL)
691 as_bad (_("Unsupported RISC-V relocation number %d"), reloc_type);
e23eba97 692
45f76423
AW
693 ip->fixp = fix_new_exp (ip->frag, ip->where,
694 bfd_get_reloc_size (howto),
695 address_expr, FALSE, reloc_type);
e23eba97 696
45f76423 697 ip->fixp->fx_tcbit = riscv_opts.relax;
e23eba97 698 }
e23eba97
NC
699 }
700
e23eba97
NC
701 add_fixed_insn (ip);
702 install_insn (ip);
703}
704
705/* Build an instruction created by a macro expansion. This is passed
706 a pointer to the count of instructions created so far, an
707 expression, the name of the instruction to build, an operand format
708 string, and corresponding arguments. */
709
710static void
711macro_build (expressionS *ep, const char *name, const char *fmt, ...)
712{
713 const struct riscv_opcode *mo;
714 struct riscv_cl_insn insn;
715 bfd_reloc_code_real_type r;
716 va_list args;
717
718 va_start (args, fmt);
719
720 r = BFD_RELOC_UNUSED;
721 mo = (struct riscv_opcode *) hash_find (op_hash, name);
722 gas_assert (mo);
723
724 /* Find a non-RVC variant of the instruction. append_insn will compress
725 it if possible. */
726 while (riscv_insn_length (mo->match) < 4)
727 mo++;
728 gas_assert (strcmp (name, mo->name) == 0);
729
730 create_insn (&insn, mo);
731 for (;;)
732 {
733 switch (*fmt++)
734 {
735 case 'd':
736 INSERT_OPERAND (RD, insn, va_arg (args, int));
737 continue;
738
739 case 's':
740 INSERT_OPERAND (RS1, insn, va_arg (args, int));
741 continue;
742
743 case 't':
744 INSERT_OPERAND (RS2, insn, va_arg (args, int));
745 continue;
746
747 case '>':
748 INSERT_OPERAND (SHAMT, insn, va_arg (args, int));
749 continue;
750
751 case 'j':
752 case 'u':
753 case 'q':
754 gas_assert (ep != NULL);
755 r = va_arg (args, int);
756 continue;
757
758 case '\0':
759 break;
760 case ',':
761 continue;
762 default:
763 as_fatal (_("internal error: invalid macro"));
764 }
765 break;
766 }
767 va_end (args);
768 gas_assert (r == BFD_RELOC_UNUSED ? ep == NULL : ep != NULL);
769
770 append_insn (&insn, ep, r);
771}
772
773/* Sign-extend 32-bit mode constants that have bit 31 set and all higher bits
774 unset. */
775static void
776normalize_constant_expr (expressionS *ex)
777{
778 if (xlen > 32)
779 return;
780 if ((ex->X_op == O_constant || ex->X_op == O_symbol)
781 && IS_ZEXT_32BIT_NUM (ex->X_add_number))
782 ex->X_add_number = (((ex->X_add_number & 0xffffffff) ^ 0x80000000)
783 - 0x80000000);
784}
785
786/* Fail if an expression is not a constant. */
787
788static void
789check_absolute_expr (struct riscv_cl_insn *ip, expressionS *ex)
790{
791 if (ex->X_op == O_big)
792 as_bad (_("unsupported large constant"));
793 else if (ex->X_op != O_constant)
794 as_bad (_("Instruction %s requires absolute expression"),
795 ip->insn_mo->name);
796 normalize_constant_expr (ex);
797}
798
799static symbolS *
800make_internal_label (void)
801{
802 return (symbolS *) local_symbol_make (FAKE_LABEL_NAME, now_seg,
1d65abb5 803 (valueT) frag_now_fix (), frag_now);
e23eba97
NC
804}
805
806/* Load an entry from the GOT. */
807static void
808pcrel_access (int destreg, int tempreg, expressionS *ep,
809 const char *lo_insn, const char *lo_pattern,
810 bfd_reloc_code_real_type hi_reloc,
811 bfd_reloc_code_real_type lo_reloc)
812{
813 expressionS ep2;
814 ep2.X_op = O_symbol;
815 ep2.X_add_symbol = make_internal_label ();
816 ep2.X_add_number = 0;
817
818 macro_build (ep, "auipc", "d,u", tempreg, hi_reloc);
819 macro_build (&ep2, lo_insn, lo_pattern, destreg, tempreg, lo_reloc);
820}
821
822static void
823pcrel_load (int destreg, int tempreg, expressionS *ep, const char *lo_insn,
824 bfd_reloc_code_real_type hi_reloc,
825 bfd_reloc_code_real_type lo_reloc)
826{
827 pcrel_access (destreg, tempreg, ep, lo_insn, "d,s,j", hi_reloc, lo_reloc);
828}
829
830static void
831pcrel_store (int srcreg, int tempreg, expressionS *ep, const char *lo_insn,
832 bfd_reloc_code_real_type hi_reloc,
833 bfd_reloc_code_real_type lo_reloc)
834{
835 pcrel_access (srcreg, tempreg, ep, lo_insn, "t,s,q", hi_reloc, lo_reloc);
836}
837
838/* PC-relative function call using AUIPC/JALR, relaxed to JAL. */
839static void
840riscv_call (int destreg, int tempreg, expressionS *ep,
841 bfd_reloc_code_real_type reloc)
842{
843 macro_build (ep, "auipc", "d,u", tempreg, reloc);
844 macro_build (NULL, "jalr", "d,s", destreg, tempreg);
845}
846
847/* Load an integer constant into a register. */
848
849static void
850load_const (int reg, expressionS *ep)
851{
852 int shift = RISCV_IMM_BITS;
853 expressionS upper = *ep, lower = *ep;
854 lower.X_add_number = (int32_t) ep->X_add_number << (32-shift) >> (32-shift);
855 upper.X_add_number -= lower.X_add_number;
856
857 if (ep->X_op != O_constant)
858 {
859 as_bad (_("unsupported large constant"));
860 return;
861 }
862
1d65abb5 863 if (xlen > 32 && !IS_SEXT_32BIT_NUM (ep->X_add_number))
e23eba97
NC
864 {
865 /* Reduce to a signed 32-bit constant using SLLI and ADDI. */
866 while (((upper.X_add_number >> shift) & 1) == 0)
867 shift++;
868
869 upper.X_add_number = (int64_t) upper.X_add_number >> shift;
1d65abb5 870 load_const (reg, &upper);
e23eba97
NC
871
872 macro_build (NULL, "slli", "d,s,>", reg, reg, shift);
873 if (lower.X_add_number != 0)
874 macro_build (&lower, "addi", "d,s,j", reg, reg, BFD_RELOC_RISCV_LO12_I);
875 }
876 else
877 {
878 /* Simply emit LUI and/or ADDI to build a 32-bit signed constant. */
879 int hi_reg = 0;
880
881 if (upper.X_add_number != 0)
882 {
883 macro_build (ep, "lui", "d,u", reg, BFD_RELOC_RISCV_HI20);
884 hi_reg = reg;
885 }
886
887 if (lower.X_add_number != 0 || hi_reg == 0)
888 macro_build (ep, ADD32_INSN, "d,s,j", reg, hi_reg,
889 BFD_RELOC_RISCV_LO12_I);
890 }
891}
892
893/* Expand RISC-V assembly macros into one or more instructions. */
894static void
895macro (struct riscv_cl_insn *ip, expressionS *imm_expr,
896 bfd_reloc_code_real_type *imm_reloc)
897{
898 int rd = (ip->insn_opcode >> OP_SH_RD) & OP_MASK_RD;
899 int rs1 = (ip->insn_opcode >> OP_SH_RS1) & OP_MASK_RS1;
900 int rs2 = (ip->insn_opcode >> OP_SH_RS2) & OP_MASK_RS2;
901 int mask = ip->insn_mo->mask;
902
903 switch (mask)
904 {
905 case M_LI:
906 load_const (rd, imm_expr);
907 break;
908
909 case M_LA:
910 case M_LLA:
911 /* Load the address of a symbol into a register. */
912 if (!IS_SEXT_32BIT_NUM (imm_expr->X_add_number))
913 as_bad (_("offset too large"));
914
915 if (imm_expr->X_op == O_constant)
916 load_const (rd, imm_expr);
917 else if (riscv_opts.pic && mask == M_LA) /* Global PIC symbol */
918 pcrel_load (rd, rd, imm_expr, LOAD_ADDRESS_INSN,
919 BFD_RELOC_RISCV_GOT_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
920 else /* Local PIC symbol, or any non-PIC symbol */
921 pcrel_load (rd, rd, imm_expr, "addi",
922 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
923 break;
924
925 case M_LA_TLS_GD:
926 pcrel_load (rd, rd, imm_expr, "addi",
927 BFD_RELOC_RISCV_TLS_GD_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
928 break;
929
930 case M_LA_TLS_IE:
931 pcrel_load (rd, rd, imm_expr, LOAD_ADDRESS_INSN,
932 BFD_RELOC_RISCV_TLS_GOT_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
933 break;
934
935 case M_LB:
936 pcrel_load (rd, rd, imm_expr, "lb",
937 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
938 break;
939
940 case M_LBU:
941 pcrel_load (rd, rd, imm_expr, "lbu",
942 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
943 break;
944
945 case M_LH:
946 pcrel_load (rd, rd, imm_expr, "lh",
947 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
948 break;
949
950 case M_LHU:
951 pcrel_load (rd, rd, imm_expr, "lhu",
952 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
953 break;
954
955 case M_LW:
956 pcrel_load (rd, rd, imm_expr, "lw",
957 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
958 break;
959
960 case M_LWU:
961 pcrel_load (rd, rd, imm_expr, "lwu",
962 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
963 break;
964
965 case M_LD:
966 pcrel_load (rd, rd, imm_expr, "ld",
967 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
968 break;
969
970 case M_FLW:
971 pcrel_load (rd, rs1, imm_expr, "flw",
972 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
973 break;
974
975 case M_FLD:
976 pcrel_load (rd, rs1, imm_expr, "fld",
977 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_I);
978 break;
979
980 case M_SB:
981 pcrel_store (rs2, rs1, imm_expr, "sb",
982 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_S);
983 break;
984
985 case M_SH:
986 pcrel_store (rs2, rs1, imm_expr, "sh",
987 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_S);
988 break;
989
990 case M_SW:
991 pcrel_store (rs2, rs1, imm_expr, "sw",
992 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_S);
993 break;
994
995 case M_SD:
996 pcrel_store (rs2, rs1, imm_expr, "sd",
997 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_S);
998 break;
999
1000 case M_FSW:
1001 pcrel_store (rs2, rs1, imm_expr, "fsw",
1002 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_S);
1003 break;
1004
1005 case M_FSD:
1006 pcrel_store (rs2, rs1, imm_expr, "fsd",
1007 BFD_RELOC_RISCV_PCREL_HI20, BFD_RELOC_RISCV_PCREL_LO12_S);
1008 break;
1009
1010 case M_CALL:
1011 riscv_call (rd, rs1, imm_expr, *imm_reloc);
1012 break;
1013
1014 default:
1015 as_bad (_("Macro %s not implemented"), ip->insn_mo->name);
1016 break;
1017 }
1018}
1019
1020static const struct percent_op_match percent_op_utype[] =
1021{
1022 {"%tprel_hi", BFD_RELOC_RISCV_TPREL_HI20},
1023 {"%pcrel_hi", BFD_RELOC_RISCV_PCREL_HI20},
1024 {"%tls_ie_pcrel_hi", BFD_RELOC_RISCV_TLS_GOT_HI20},
1025 {"%tls_gd_pcrel_hi", BFD_RELOC_RISCV_TLS_GD_HI20},
1026 {"%hi", BFD_RELOC_RISCV_HI20},
1027 {0, 0}
1028};
1029
1030static const struct percent_op_match percent_op_itype[] =
1031{
1032 {"%lo", BFD_RELOC_RISCV_LO12_I},
1033 {"%tprel_lo", BFD_RELOC_RISCV_TPREL_LO12_I},
1034 {"%pcrel_lo", BFD_RELOC_RISCV_PCREL_LO12_I},
1035 {0, 0}
1036};
1037
1038static const struct percent_op_match percent_op_stype[] =
1039{
1040 {"%lo", BFD_RELOC_RISCV_LO12_S},
1041 {"%tprel_lo", BFD_RELOC_RISCV_TPREL_LO12_S},
1042 {"%pcrel_lo", BFD_RELOC_RISCV_PCREL_LO12_S},
1043 {0, 0}
1044};
1045
1046static const struct percent_op_match percent_op_rtype[] =
1047{
1048 {"%tprel_add", BFD_RELOC_RISCV_TPREL_ADD},
1049 {0, 0}
1050};
1051
1052/* Return true if *STR points to a relocation operator. When returning true,
1053 move *STR over the operator and store its relocation code in *RELOC.
1054 Leave both *STR and *RELOC alone when returning false. */
1055
1056static bfd_boolean
1057parse_relocation (char **str, bfd_reloc_code_real_type *reloc,
1058 const struct percent_op_match *percent_op)
1059{
1060 for ( ; percent_op->str; percent_op++)
1061 if (strncasecmp (*str, percent_op->str, strlen (percent_op->str)) == 0)
1062 {
1063 int len = strlen (percent_op->str);
1064
1065 if (!ISSPACE ((*str)[len]) && (*str)[len] != '(')
1066 continue;
1067
1068 *str += strlen (percent_op->str);
1069 *reloc = percent_op->reloc;
1070
1071 /* Check whether the output BFD supports this relocation.
1072 If not, issue an error and fall back on something safe. */
45f76423
AW
1073 if (*reloc != BFD_RELOC_UNUSED
1074 && !bfd_reloc_type_lookup (stdoutput, *reloc))
e23eba97
NC
1075 {
1076 as_bad ("relocation %s isn't supported by the current ABI",
1077 percent_op->str);
1078 *reloc = BFD_RELOC_UNUSED;
1079 }
1080 return TRUE;
1081 }
1082 return FALSE;
1083}
1084
1085static void
1086my_getExpression (expressionS *ep, char *str)
1087{
1088 char *save_in;
1089
1090 save_in = input_line_pointer;
1091 input_line_pointer = str;
1092 expression (ep);
1093 expr_end = input_line_pointer;
1094 input_line_pointer = save_in;
1095}
1096
1097/* Parse string STR as a 16-bit relocatable operand. Store the
1098 expression in *EP and the relocation, if any, in RELOC.
1099 Return the number of relocation operators used (0 or 1).
1100
1101 On exit, EXPR_END points to the first character after the expression. */
1102
1103static size_t
1104my_getSmallExpression (expressionS *ep, bfd_reloc_code_real_type *reloc,
1105 char *str, const struct percent_op_match *percent_op)
1106{
1107 size_t reloc_index;
1108 unsigned crux_depth, str_depth, regno;
1109 char *crux;
1110
1111 /* First, check for integer registers. */
1112 if (reg_lookup (&str, RCLASS_GPR, &regno))
1113 {
1114 ep->X_op = O_register;
1115 ep->X_add_number = regno;
1116 return 0;
1117 }
1118
1119 /* Search for the start of the main expression.
1120 End the loop with CRUX pointing to the start
1121 of the main expression and with CRUX_DEPTH containing the number
1122 of open brackets at that point. */
1123 reloc_index = -1;
1124 str_depth = 0;
1125 do
1126 {
1127 reloc_index++;
1128 crux = str;
1129 crux_depth = str_depth;
1130
1131 /* Skip over whitespace and brackets, keeping count of the number
1132 of brackets. */
1133 while (*str == ' ' || *str == '\t' || *str == '(')
1134 if (*str++ == '(')
1135 str_depth++;
1136 }
1137 while (*str == '%'
1138 && reloc_index < 1
1139 && parse_relocation (&str, reloc, percent_op));
1140
1141 my_getExpression (ep, crux);
1142 str = expr_end;
1143
1144 /* Match every open bracket. */
1145 while (crux_depth > 0 && (*str == ')' || *str == ' ' || *str == '\t'))
1146 if (*str++ == ')')
1147 crux_depth--;
1148
1149 if (crux_depth > 0)
1150 as_bad ("unclosed '('");
1151
1152 expr_end = str;
1153
1154 return reloc_index;
1155}
1156
1157/* This routine assembles an instruction into its binary format. As a
1158 side effect, it sets the global variable imm_reloc to the type of
1159 relocation to do if one of the operands is an address expression. */
1160
1161static const char *
1162riscv_ip (char *str, struct riscv_cl_insn *ip, expressionS *imm_expr,
1163 bfd_reloc_code_real_type *imm_reloc)
1164{
1165 char *s;
1166 const char *args;
1167 char c = 0;
1168 struct riscv_opcode *insn;
1169 char *argsStart;
1170 unsigned int regno;
1171 char save_c = 0;
1172 int argnum;
1173 const struct percent_op_match *p;
1174 const char *error = "unrecognized opcode";
1175
1176 /* Parse the name of the instruction. Terminate the string if whitespace
1177 is found so that hash_find only sees the name part of the string. */
1178 for (s = str; *s != '\0'; ++s)
1179 if (ISSPACE (*s))
1180 {
1181 save_c = *s;
1182 *s++ = '\0';
1183 break;
1184 }
1185
1186 insn = (struct riscv_opcode *) hash_find (op_hash, str);
1187
1188 argsStart = s;
1189 for ( ; insn && insn->name && strcmp (insn->name, str) == 0; insn++)
1190 {
1191 if (!riscv_subset_supports (insn->subset))
1192 continue;
1193
1194 create_insn (ip, insn);
1195 argnum = 1;
1196
1197 imm_expr->X_op = O_absent;
1198 *imm_reloc = BFD_RELOC_UNUSED;
1199 p = percent_op_itype;
1200
1201 for (args = insn->args;; ++args)
1202 {
1203 s += strspn (s, " \t");
1204 switch (*args)
1205 {
1206 case '\0': /* End of args. */
1207 if (insn->pinfo != INSN_MACRO)
1208 {
1209 if (!insn->match_func (insn, ip->insn_opcode))
1210 break;
1211 if (riscv_insn_length (insn->match) == 2 && !riscv_opts.rvc)
1212 break;
1213 }
1214 if (*s != '\0')
1215 break;
1216 /* Successful assembly. */
1217 error = NULL;
1218 goto out;
1219
1220 case 'C': /* RVC */
1221 switch (*++args)
1222 {
1223 case 's': /* RS1 x8-x15 */
1224 if (!reg_lookup (&s, RCLASS_GPR, &regno)
1225 || !(regno >= 8 && regno <= 15))
1226 break;
1227 INSERT_OPERAND (CRS1S, *ip, regno % 8);
1228 continue;
1229 case 'w': /* RS1 x8-x15, constrained to equal RD x8-x15. */
1230 if (!reg_lookup (&s, RCLASS_GPR, &regno)
1231 || EXTRACT_OPERAND (CRS1S, ip->insn_opcode) + 8 != regno)
1232 break;
1233 continue;
1234 case 't': /* RS2 x8-x15 */
1235 if (!reg_lookup (&s, RCLASS_GPR, &regno)
1236 || !(regno >= 8 && regno <= 15))
1237 break;
1238 INSERT_OPERAND (CRS2S, *ip, regno % 8);
1239 continue;
1240 case 'x': /* RS2 x8-x15, constrained to equal RD x8-x15. */
1241 if (!reg_lookup (&s, RCLASS_GPR, &regno)
1242 || EXTRACT_OPERAND (CRS2S, ip->insn_opcode) + 8 != regno)
1243 break;
1244 continue;
1245 case 'U': /* RS1, constrained to equal RD. */
1246 if (!reg_lookup (&s, RCLASS_GPR, &regno)
1247 || EXTRACT_OPERAND (RD, ip->insn_opcode) != regno)
1248 break;
1249 continue;
1250 case 'V': /* RS2 */
1251 if (!reg_lookup (&s, RCLASS_GPR, &regno))
1252 break;
1253 INSERT_OPERAND (CRS2, *ip, regno);
1254 continue;
1255 case 'c': /* RS1, constrained to equal sp. */
1256 if (!reg_lookup (&s, RCLASS_GPR, &regno)
1257 || regno != X_SP)
1258 break;
1259 continue;
1260 case '>':
1261 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1262 || imm_expr->X_op != O_constant
1263 || imm_expr->X_add_number <= 0
1264 || imm_expr->X_add_number >= 64)
1265 break;
1266 ip->insn_opcode |= ENCODE_RVC_IMM (imm_expr->X_add_number);
1267rvc_imm_done:
1268 s = expr_end;
1269 imm_expr->X_op = O_absent;
1270 continue;
1271 case '<':
1272 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1273 || imm_expr->X_op != O_constant
1274 || !VALID_RVC_IMM (imm_expr->X_add_number)
1275 || imm_expr->X_add_number <= 0
1276 || imm_expr->X_add_number >= 32)
1277 break;
1278 ip->insn_opcode |= ENCODE_RVC_IMM (imm_expr->X_add_number);
1279 goto rvc_imm_done;
1280 case 'i':
1281 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1282 || imm_expr->X_op != O_constant
1283 || imm_expr->X_add_number == 0
1284 || !VALID_RVC_SIMM3 (imm_expr->X_add_number))
1285 break;
1286 ip->insn_opcode |= ENCODE_RVC_SIMM3 (imm_expr->X_add_number);
1287 goto rvc_imm_done;
1288 case 'j':
1289 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1290 || imm_expr->X_op != O_constant
1291 || imm_expr->X_add_number == 0
1292 || !VALID_RVC_IMM (imm_expr->X_add_number))
1293 break;
1294 ip->insn_opcode |= ENCODE_RVC_IMM (imm_expr->X_add_number);
1295 goto rvc_imm_done;
1296 case 'k':
1297 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1298 || imm_expr->X_op != O_constant
1299 || !VALID_RVC_LW_IMM (imm_expr->X_add_number))
1300 break;
1301 ip->insn_opcode |= ENCODE_RVC_LW_IMM (imm_expr->X_add_number);
1302 goto rvc_imm_done;
1303 case 'l':
1304 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1305 || imm_expr->X_op != O_constant
1306 || !VALID_RVC_LD_IMM (imm_expr->X_add_number))
1307 break;
1308 ip->insn_opcode |= ENCODE_RVC_LD_IMM (imm_expr->X_add_number);
1309 goto rvc_imm_done;
1310 case 'm':
1311 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1312 || imm_expr->X_op != O_constant
1313 || !VALID_RVC_LWSP_IMM (imm_expr->X_add_number))
1314 break;
1315 ip->insn_opcode |=
1316 ENCODE_RVC_LWSP_IMM (imm_expr->X_add_number);
1317 goto rvc_imm_done;
1318 case 'n':
1319 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1320 || imm_expr->X_op != O_constant
1321 || !VALID_RVC_LDSP_IMM (imm_expr->X_add_number))
1322 break;
1323 ip->insn_opcode |=
1324 ENCODE_RVC_LDSP_IMM (imm_expr->X_add_number);
1325 goto rvc_imm_done;
1326 case 'K':
1327 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1328 || imm_expr->X_op != O_constant
1329 || !VALID_RVC_ADDI4SPN_IMM (imm_expr->X_add_number)
1330 || imm_expr->X_add_number == 0)
1331 break;
1332 ip->insn_opcode |=
1333 ENCODE_RVC_ADDI4SPN_IMM (imm_expr->X_add_number);
1334 goto rvc_imm_done;
1335 case 'L':
1336 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1337 || imm_expr->X_op != O_constant
1338 || !VALID_RVC_ADDI16SP_IMM (imm_expr->X_add_number)
1339 || imm_expr->X_add_number == 0)
1340 break;
1341 ip->insn_opcode |=
1342 ENCODE_RVC_ADDI16SP_IMM (imm_expr->X_add_number);
1343 goto rvc_imm_done;
1344 case 'M':
1345 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1346 || imm_expr->X_op != O_constant
1347 || !VALID_RVC_SWSP_IMM (imm_expr->X_add_number))
1348 break;
1349 ip->insn_opcode |=
1350 ENCODE_RVC_SWSP_IMM (imm_expr->X_add_number);
1351 goto rvc_imm_done;
1352 case 'N':
1353 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1354 || imm_expr->X_op != O_constant
1355 || !VALID_RVC_SDSP_IMM (imm_expr->X_add_number))
1356 break;
1357 ip->insn_opcode |=
1358 ENCODE_RVC_SDSP_IMM (imm_expr->X_add_number);
1359 goto rvc_imm_done;
1360 case 'u':
1361 p = percent_op_utype;
1362 if (my_getSmallExpression (imm_expr, imm_reloc, s, p))
1363 break;
1364rvc_lui:
1365 if (imm_expr->X_op != O_constant
1366 || imm_expr->X_add_number <= 0
1367 || imm_expr->X_add_number >= RISCV_BIGIMM_REACH
1368 || (imm_expr->X_add_number >= RISCV_RVC_IMM_REACH / 2
1369 && (imm_expr->X_add_number <
1370 RISCV_BIGIMM_REACH - RISCV_RVC_IMM_REACH / 2)))
1371 break;
1372 ip->insn_opcode |= ENCODE_RVC_IMM (imm_expr->X_add_number);
1373 goto rvc_imm_done;
1374 case 'v':
1375 if (my_getSmallExpression (imm_expr, imm_reloc, s, p)
1376 || (imm_expr->X_add_number & (RISCV_IMM_REACH - 1))
1377 || ((int32_t)imm_expr->X_add_number
1378 != imm_expr->X_add_number))
1379 break;
1380 imm_expr->X_add_number =
1381 ((uint32_t) imm_expr->X_add_number) >> RISCV_IMM_BITS;
1382 goto rvc_lui;
1383 case 'p':
1384 goto branch;
1385 case 'a':
1386 goto jump;
1387 case 'D': /* Floating-point RS2 x8-x15. */
1388 if (!reg_lookup (&s, RCLASS_FPR, &regno)
1389 || !(regno >= 8 && regno <= 15))
1390 break;
1391 INSERT_OPERAND (CRS2S, *ip, regno % 8);
1392 continue;
1393 case 'T': /* Floating-point RS2. */
1394 if (!reg_lookup (&s, RCLASS_FPR, &regno))
1395 break;
1396 INSERT_OPERAND (CRS2, *ip, regno);
1397 continue;
1398 default:
1399 as_bad (_("bad RVC field specifier 'C%c'\n"), *args);
1400 }
1401 break;
1402
1403 case ',':
1404 ++argnum;
1405 if (*s++ == *args)
1406 continue;
1407 s--;
1408 break;
1409
1410 case '(':
1411 case ')':
1412 case '[':
1413 case ']':
1414 if (*s++ == *args)
1415 continue;
1416 break;
1417
1418 case '<': /* Shift amount, 0 - 31. */
1419 my_getExpression (imm_expr, s);
1420 check_absolute_expr (ip, imm_expr);
1421 if ((unsigned long) imm_expr->X_add_number > 31)
1422 as_warn (_("Improper shift amount (%lu)"),
1423 (unsigned long) imm_expr->X_add_number);
1424 INSERT_OPERAND (SHAMTW, *ip, imm_expr->X_add_number);
1425 imm_expr->X_op = O_absent;
1426 s = expr_end;
1427 continue;
1428
1429 case '>': /* Shift amount, 0 - (XLEN-1). */
1430 my_getExpression (imm_expr, s);
1431 check_absolute_expr (ip, imm_expr);
1432 if ((unsigned long) imm_expr->X_add_number >= xlen)
1433 as_warn (_("Improper shift amount (%lu)"),
1434 (unsigned long) imm_expr->X_add_number);
1435 INSERT_OPERAND (SHAMT, *ip, imm_expr->X_add_number);
1436 imm_expr->X_op = O_absent;
1437 s = expr_end;
1438 continue;
1439
1440 case 'Z': /* CSRRxI immediate. */
1441 my_getExpression (imm_expr, s);
1442 check_absolute_expr (ip, imm_expr);
1443 if ((unsigned long) imm_expr->X_add_number > 31)
1444 as_warn (_("Improper CSRxI immediate (%lu)"),
1445 (unsigned long) imm_expr->X_add_number);
1446 INSERT_OPERAND (RS1, *ip, imm_expr->X_add_number);
1447 imm_expr->X_op = O_absent;
1448 s = expr_end;
1449 continue;
1450
1451 case 'E': /* Control register. */
1452 if (reg_lookup (&s, RCLASS_CSR, &regno))
1453 INSERT_OPERAND (CSR, *ip, regno);
1454 else
1455 {
1456 my_getExpression (imm_expr, s);
1457 check_absolute_expr (ip, imm_expr);
1458 if ((unsigned long) imm_expr->X_add_number > 0xfff)
1d65abb5
AW
1459 as_warn (_("Improper CSR address (%lu)"),
1460 (unsigned long) imm_expr->X_add_number);
e23eba97
NC
1461 INSERT_OPERAND (CSR, *ip, imm_expr->X_add_number);
1462 imm_expr->X_op = O_absent;
1463 s = expr_end;
1464 }
1465 continue;
1466
1467 case 'm': /* Rounding mode. */
1468 if (arg_lookup (&s, riscv_rm, ARRAY_SIZE (riscv_rm), &regno))
1469 {
1470 INSERT_OPERAND (RM, *ip, regno);
1471 continue;
1472 }
1473 break;
1474
1475 case 'P':
1476 case 'Q': /* Fence predecessor/successor. */
1477 if (arg_lookup (&s, riscv_pred_succ, ARRAY_SIZE (riscv_pred_succ),
1478 &regno))
1479 {
1480 if (*args == 'P')
1481 INSERT_OPERAND (PRED, *ip, regno);
1482 else
1483 INSERT_OPERAND (SUCC, *ip, regno);
1484 continue;
1485 }
1486 break;
1487
1488 case 'd': /* Destination register. */
1489 case 's': /* Source register. */
1490 case 't': /* Target register. */
1491 if (reg_lookup (&s, RCLASS_GPR, &regno))
1492 {
1493 c = *args;
1494 if (*s == ' ')
1495 ++s;
1496
1497 /* Now that we have assembled one operand, we use the args
1498 string to figure out where it goes in the instruction. */
1499 switch (c)
1500 {
1501 case 's':
1502 INSERT_OPERAND (RS1, *ip, regno);
1503 break;
1504 case 'd':
1505 INSERT_OPERAND (RD, *ip, regno);
1506 break;
1507 case 't':
1508 INSERT_OPERAND (RS2, *ip, regno);
1509 break;
1510 }
1511 continue;
1512 }
1513 break;
1514
1515 case 'D': /* Floating point rd. */
1516 case 'S': /* Floating point rs1. */
1517 case 'T': /* Floating point rs2. */
1518 case 'U': /* Floating point rs1 and rs2. */
1519 case 'R': /* Floating point rs3. */
1520 if (reg_lookup (&s, RCLASS_FPR, &regno))
1521 {
1522 c = *args;
1523 if (*s == ' ')
1524 ++s;
1525 switch (c)
1526 {
1527 case 'D':
1528 INSERT_OPERAND (RD, *ip, regno);
1529 break;
1530 case 'S':
1531 INSERT_OPERAND (RS1, *ip, regno);
1532 break;
1533 case 'U':
1534 INSERT_OPERAND (RS1, *ip, regno);
1535 /* fallthru */
1536 case 'T':
1537 INSERT_OPERAND (RS2, *ip, regno);
1538 break;
1539 case 'R':
1540 INSERT_OPERAND (RS3, *ip, regno);
1541 break;
1542 }
1543 continue;
1544 }
1545
1546 break;
1547
1548 case 'I':
1549 my_getExpression (imm_expr, s);
1550 if (imm_expr->X_op != O_big
1551 && imm_expr->X_op != O_constant)
1552 break;
1553 normalize_constant_expr (imm_expr);
1554 s = expr_end;
1555 continue;
1556
1557 case 'A':
1558 my_getExpression (imm_expr, s);
1559 normalize_constant_expr (imm_expr);
1560 /* The 'A' format specifier must be a symbol. */
1561 if (imm_expr->X_op != O_symbol)
1562 break;
1563 *imm_reloc = BFD_RELOC_32;
1564 s = expr_end;
1565 continue;
1566
1567 case 'j': /* Sign-extended immediate. */
1568 *imm_reloc = BFD_RELOC_RISCV_LO12_I;
1569 p = percent_op_itype;
1570 goto alu_op;
1571 case 'q': /* Store displacement. */
1572 p = percent_op_stype;
1573 *imm_reloc = BFD_RELOC_RISCV_LO12_S;
1574 goto load_store;
1575 case 'o': /* Load displacement. */
1576 p = percent_op_itype;
1577 *imm_reloc = BFD_RELOC_RISCV_LO12_I;
1578 goto load_store;
1579 case '0': /* AMO "displacement," which must be zero. */
1580 p = percent_op_rtype;
1581 *imm_reloc = BFD_RELOC_UNUSED;
1582load_store:
1583 /* Check whether there is only a single bracketed expression
1584 left. If so, it must be the base register and the
1585 constant must be zero. */
1586 imm_expr->X_op = O_constant;
1587 imm_expr->X_add_number = 0;
1588 if (*s == '(' && strchr (s + 1, '(') == 0)
1589 continue;
1590alu_op:
1591 /* If this value won't fit into a 16 bit offset, then go
1592 find a macro that will generate the 32 bit offset
1593 code pattern. */
1594 if (!my_getSmallExpression (imm_expr, imm_reloc, s, p))
1595 {
1596 normalize_constant_expr (imm_expr);
1597 if (imm_expr->X_op != O_constant
1598 || (*args == '0' && imm_expr->X_add_number != 0)
1599 || imm_expr->X_add_number >= (signed)RISCV_IMM_REACH/2
1600 || imm_expr->X_add_number < -(signed)RISCV_IMM_REACH/2)
1601 break;
1602 }
1603
1604 s = expr_end;
1605 continue;
1606
1607 case 'p': /* PC-relative offset. */
1608branch:
1609 *imm_reloc = BFD_RELOC_12_PCREL;
1610 my_getExpression (imm_expr, s);
1611 s = expr_end;
1612 continue;
1613
1614 case 'u': /* Upper 20 bits. */
1615 p = percent_op_utype;
1616 if (!my_getSmallExpression (imm_expr, imm_reloc, s, p)
1617 && imm_expr->X_op == O_constant)
1618 {
1619 if (imm_expr->X_add_number < 0
1620 || imm_expr->X_add_number >= (signed)RISCV_BIGIMM_REACH)
1621 as_bad (_("lui expression not in range 0..1048575"));
1622
1623 *imm_reloc = BFD_RELOC_RISCV_HI20;
1624 imm_expr->X_add_number <<= RISCV_IMM_BITS;
1625 }
1626 s = expr_end;
1627 continue;
1628
1629 case 'a': /* 20-bit PC-relative offset. */
1630jump:
1631 my_getExpression (imm_expr, s);
1632 s = expr_end;
1633 *imm_reloc = BFD_RELOC_RISCV_JMP;
1634 continue;
1635
1636 case 'c':
1637 my_getExpression (imm_expr, s);
1638 s = expr_end;
1639 if (strcmp (s, "@plt") == 0)
1640 {
1641 *imm_reloc = BFD_RELOC_RISCV_CALL_PLT;
1642 s += 4;
1643 }
1644 else
1645 *imm_reloc = BFD_RELOC_RISCV_CALL;
1646 continue;
1647
1648 default:
1649 as_fatal (_("internal error: bad argument type %c"), *args);
1650 }
1651 break;
1652 }
1653 s = argsStart;
1654 error = _("illegal operands");
1655 }
1656
1657out:
1658 /* Restore the character we might have clobbered above. */
1659 if (save_c)
1660 *(argsStart - 1) = save_c;
1661
1662 return error;
1663}
1664
1665void
1666md_assemble (char *str)
1667{
1668 struct riscv_cl_insn insn;
1669 expressionS imm_expr;
1670 bfd_reloc_code_real_type imm_reloc = BFD_RELOC_UNUSED;
1671
1672 const char *error = riscv_ip (str, &insn, &imm_expr, &imm_reloc);
1673
1674 if (error)
1675 {
1676 as_bad ("%s `%s'", error, str);
1677 return;
1678 }
1679
1680 if (insn.insn_mo->pinfo == INSN_MACRO)
1681 macro (&insn, &imm_expr, &imm_reloc);
1682 else
1683 append_insn (&insn, &imm_expr, imm_reloc);
1684}
1685
1686const char *
1687md_atof (int type, char *litP, int *sizeP)
1688{
1689 return ieee_md_atof (type, litP, sizeP, TARGET_BYTES_BIG_ENDIAN);
1690}
1691
1692void
1693md_number_to_chars (char *buf, valueT val, int n)
1694{
1695 number_to_chars_littleendian (buf, val, n);
1696}
1697
1698const char *md_shortopts = "O::g::G:";
1699
1700enum options
1701{
2922d21d 1702 OPTION_MARCH = OPTION_MD_BASE,
e23eba97
NC
1703 OPTION_PIC,
1704 OPTION_NO_PIC,
2922d21d 1705 OPTION_MABI,
e23eba97
NC
1706 OPTION_END_OF_ENUM
1707};
1708
1709struct option md_longopts[] =
1710{
e23eba97
NC
1711 {"march", required_argument, NULL, OPTION_MARCH},
1712 {"fPIC", no_argument, NULL, OPTION_PIC},
1713 {"fpic", no_argument, NULL, OPTION_PIC},
1714 {"fno-pic", no_argument, NULL, OPTION_NO_PIC},
2922d21d 1715 {"mabi", required_argument, NULL, OPTION_MABI},
e23eba97
NC
1716
1717 {NULL, no_argument, NULL, 0}
1718};
1719size_t md_longopts_size = sizeof (md_longopts);
1720
2922d21d
AW
1721enum float_abi {
1722 FLOAT_ABI_DEFAULT = -1,
1723 FLOAT_ABI_SOFT,
1724 FLOAT_ABI_SINGLE,
1725 FLOAT_ABI_DOUBLE,
1726 FLOAT_ABI_QUAD
e23eba97 1727};
2922d21d
AW
1728static enum float_abi float_abi = FLOAT_ABI_DEFAULT;
1729
1730static void
1731riscv_set_abi (unsigned new_xlen, enum float_abi new_float_abi)
1732{
1733 abi_xlen = new_xlen;
1734 float_abi = new_float_abi;
1735}
e23eba97
NC
1736
1737int
1738md_parse_option (int c, const char *arg)
1739{
1740 switch (c)
1741 {
e23eba97
NC
1742 case OPTION_MARCH:
1743 riscv_set_arch (arg);
1744 break;
1745
1746 case OPTION_NO_PIC:
1747 riscv_opts.pic = FALSE;
1748 break;
1749
1750 case OPTION_PIC:
1751 riscv_opts.pic = TRUE;
1752 break;
1753
2922d21d
AW
1754 case OPTION_MABI:
1755 if (strcmp (arg, "ilp32") == 0)
1756 riscv_set_abi (32, FLOAT_ABI_SOFT);
1757 else if (strcmp (arg, "ilp32f") == 0)
1758 riscv_set_abi (32, FLOAT_ABI_SINGLE);
1759 else if (strcmp (arg, "ilp32d") == 0)
1760 riscv_set_abi (32, FLOAT_ABI_DOUBLE);
1761 else if (strcmp (arg, "ilp32q") == 0)
1762 riscv_set_abi (32, FLOAT_ABI_QUAD);
1763 else if (strcmp (arg, "lp64") == 0)
1764 riscv_set_abi (64, FLOAT_ABI_SOFT);
1765 else if (strcmp (arg, "lp64f") == 0)
1766 riscv_set_abi (64, FLOAT_ABI_SINGLE);
1767 else if (strcmp (arg, "lp64d") == 0)
1768 riscv_set_abi (64, FLOAT_ABI_DOUBLE);
1769 else if (strcmp (arg, "lp64q") == 0)
1770 riscv_set_abi (64, FLOAT_ABI_QUAD);
1771 else
1772 return 0;
1773 break;
1774
e23eba97
NC
1775 default:
1776 return 0;
1777 }
1778
1779 return 1;
1780}
1781
1782void
1783riscv_after_parse_args (void)
1784{
e23eba97
NC
1785 if (xlen == 0)
1786 {
1787 if (strcmp (default_arch, "riscv32") == 0)
1788 xlen = 32;
1789 else if (strcmp (default_arch, "riscv64") == 0)
1790 xlen = 64;
1791 else
1792 as_bad ("unknown default architecture `%s'", default_arch);
1793 }
2922d21d
AW
1794
1795 if (riscv_subsets == NULL)
1796 riscv_set_arch (xlen == 64 ? "rv64g" : "rv32g");
1797
1798 /* Add the RVC extension, regardless of -march, to support .option rvc. */
1799 if (riscv_subset_supports ("c"))
1800 riscv_set_rvc (TRUE);
1801 else
1802 riscv_add_subset ("c");
1803
1804 /* Infer ABI from ISA if not specified on command line. */
1805 if (abi_xlen == 0)
1806 abi_xlen = xlen;
1807 else if (abi_xlen > xlen)
1808 as_bad ("can't have %d-bit ABI on %d-bit ISA", abi_xlen, xlen);
1809 else if (abi_xlen < xlen)
1810 as_bad ("%d-bit ABI not yet supported on %d-bit ISA", abi_xlen, xlen);
1811
1812 if (float_abi == FLOAT_ABI_DEFAULT)
1813 {
1814 struct riscv_subset *subset;
1815
1816 /* Assume soft-float unless D extension is present. */
1817 float_abi = FLOAT_ABI_SOFT;
1818
1819 for (subset = riscv_subsets; subset != NULL; subset = subset->next)
1820 if (strcasecmp (subset->name, "D") == 0)
1821 float_abi = FLOAT_ABI_DOUBLE;
1822 }
1823
1824 /* Insert float_abi into the EF_RISCV_FLOAT_ABI field of elf_flags. */
1825 elf_flags |= float_abi * (EF_RISCV_FLOAT_ABI & ~(EF_RISCV_FLOAT_ABI << 1));
e23eba97
NC
1826}
1827
1828long
1829md_pcrel_from (fixS *fixP)
1830{
1831 return fixP->fx_where + fixP->fx_frag->fr_address;
1832}
1833
1834/* Apply a fixup to the object file. */
1835
1836void
1837md_apply_fix (fixS *fixP, valueT *valP, segT seg ATTRIBUTE_UNUSED)
1838{
45f76423 1839 unsigned int subtype;
e23eba97 1840 bfd_byte *buf = (bfd_byte *) (fixP->fx_frag->fr_literal + fixP->fx_where);
45f76423 1841 bfd_boolean relaxable = FALSE;
e23eba97
NC
1842
1843 /* Remember value for tc_gen_reloc. */
1844 fixP->fx_addnumber = *valP;
1845
1846 switch (fixP->fx_r_type)
1847 {
e23eba97
NC
1848 case BFD_RELOC_RISCV_HI20:
1849 case BFD_RELOC_RISCV_LO12_I:
1850 case BFD_RELOC_RISCV_LO12_S:
45f76423
AW
1851 bfd_putl32 (riscv_apply_const_reloc (fixP->fx_r_type, *valP)
1852 | bfd_getl32 (buf), buf);
1853 relaxable = TRUE;
1854 break;
1855
1856 case BFD_RELOC_RISCV_GOT_HI20:
1857 case BFD_RELOC_RISCV_PCREL_HI20:
e23eba97
NC
1858 case BFD_RELOC_RISCV_ADD8:
1859 case BFD_RELOC_RISCV_ADD16:
1860 case BFD_RELOC_RISCV_ADD32:
1861 case BFD_RELOC_RISCV_ADD64:
45f76423 1862 case BFD_RELOC_RISCV_SUB6:
e23eba97
NC
1863 case BFD_RELOC_RISCV_SUB8:
1864 case BFD_RELOC_RISCV_SUB16:
1865 case BFD_RELOC_RISCV_SUB32:
1866 case BFD_RELOC_RISCV_SUB64:
45f76423
AW
1867 case BFD_RELOC_RISCV_RELAX:
1868 break;
1869
1870 case BFD_RELOC_RISCV_TPREL_HI20:
1871 case BFD_RELOC_RISCV_TPREL_LO12_I:
1872 case BFD_RELOC_RISCV_TPREL_LO12_S:
1873 case BFD_RELOC_RISCV_TPREL_ADD:
1874 relaxable = TRUE;
1875 /* Fall through. */
1876
1877 case BFD_RELOC_RISCV_TLS_GOT_HI20:
1878 case BFD_RELOC_RISCV_TLS_GD_HI20:
1879 case BFD_RELOC_RISCV_TLS_DTPREL32:
1880 case BFD_RELOC_RISCV_TLS_DTPREL64:
1881 S_SET_THREAD_LOCAL (fixP->fx_addsy);
e23eba97
NC
1882 break;
1883
1884 case BFD_RELOC_64:
1885 case BFD_RELOC_32:
1886 case BFD_RELOC_16:
1887 case BFD_RELOC_8:
45f76423 1888 case BFD_RELOC_RISCV_CFA:
e23eba97
NC
1889 if (fixP->fx_addsy && fixP->fx_subsy)
1890 {
1891 fixP->fx_next = xmemdup (fixP, sizeof (*fixP), sizeof (*fixP));
1892 fixP->fx_next->fx_addsy = fixP->fx_subsy;
1893 fixP->fx_next->fx_subsy = NULL;
1894 fixP->fx_next->fx_offset = 0;
1895 fixP->fx_subsy = NULL;
1896
1897 switch (fixP->fx_r_type)
1898 {
1899 case BFD_RELOC_64:
1900 fixP->fx_r_type = BFD_RELOC_RISCV_ADD64;
1901 fixP->fx_next->fx_r_type = BFD_RELOC_RISCV_SUB64;
1902 break;
1903
1904 case BFD_RELOC_32:
1905 fixP->fx_r_type = BFD_RELOC_RISCV_ADD32;
1906 fixP->fx_next->fx_r_type = BFD_RELOC_RISCV_SUB32;
1907 break;
1908
1909 case BFD_RELOC_16:
1910 fixP->fx_r_type = BFD_RELOC_RISCV_ADD16;
1911 fixP->fx_next->fx_r_type = BFD_RELOC_RISCV_SUB16;
1912 break;
1913
1914 case BFD_RELOC_8:
1915 fixP->fx_r_type = BFD_RELOC_RISCV_ADD8;
1916 fixP->fx_next->fx_r_type = BFD_RELOC_RISCV_SUB8;
073808ed 1917 break;
e23eba97 1918
45f76423
AW
1919 case BFD_RELOC_RISCV_CFA:
1920 /* Load the byte to get the subtype. */
1921 subtype = bfd_get_8 (NULL, &fixP->fx_frag->fr_literal[fixP->fx_where]);
1922 switch (subtype)
1923 {
1924 case DW_CFA_advance_loc1:
1925 fixP->fx_where++;
1926 fixP->fx_next->fx_where++;
1927 fixP->fx_r_type = BFD_RELOC_RISCV_SET8;
1928 fixP->fx_next->fx_r_type = BFD_RELOC_RISCV_SUB8;
1929 break;
1930
1931 case DW_CFA_advance_loc2:
1932 fixP->fx_size = 2;
1933 fixP->fx_where++;
1934 fixP->fx_next->fx_size = 2;
1935 fixP->fx_next->fx_where++;
1936 fixP->fx_r_type = BFD_RELOC_RISCV_SET16;
1937 fixP->fx_next->fx_r_type = BFD_RELOC_RISCV_SUB16;
1938 break;
1939
1940 case DW_CFA_advance_loc4:
1941 fixP->fx_size = 4;
1942 fixP->fx_where++;
1943 fixP->fx_next->fx_size = 4;
1944 fixP->fx_next->fx_where++;
1945 fixP->fx_r_type = BFD_RELOC_RISCV_SET32;
1946 fixP->fx_next->fx_r_type = BFD_RELOC_RISCV_SUB32;
1947 break;
1948
1949 default:
1950 if (subtype < 0x80 && (subtype & 0x40))
1951 {
1952 /* DW_CFA_advance_loc */
1953 fixP->fx_r_type = BFD_RELOC_RISCV_SET6;
1954 fixP->fx_next->fx_r_type = BFD_RELOC_RISCV_SUB6;
1955 }
1956 else
1957 as_fatal (_("internal error: bad CFA value #%d"), subtype);
1958 break;
1959 }
1960 break;
1961
e23eba97
NC
1962 default:
1963 /* This case is unreachable. */
1964 abort ();
1965 }
1966 }
1967 /* Fall through. */
1968
1969 case BFD_RELOC_RVA:
1970 /* If we are deleting this reloc entry, we must fill in the
1971 value now. This can happen if we have a .word which is not
1972 resolved when it appears but is later defined. */
1973 if (fixP->fx_addsy == NULL)
1974 {
1975 gas_assert (fixP->fx_size <= sizeof (valueT));
1976 md_number_to_chars ((char *) buf, *valP, fixP->fx_size);
1977 fixP->fx_done = 1;
1978 }
1979 break;
1980
1981 case BFD_RELOC_RISCV_JMP:
1982 if (fixP->fx_addsy)
1983 {
1984 /* Fill in a tentative value to improve objdump readability. */
1985 bfd_vma target = S_GET_VALUE (fixP->fx_addsy) + *valP;
1986 bfd_vma delta = target - md_pcrel_from (fixP);
1987 bfd_putl32 (bfd_getl32 (buf) | ENCODE_UJTYPE_IMM (delta), buf);
1988 }
1989 break;
1990
1991 case BFD_RELOC_12_PCREL:
1992 if (fixP->fx_addsy)
1993 {
1994 /* Fill in a tentative value to improve objdump readability. */
1995 bfd_vma target = S_GET_VALUE (fixP->fx_addsy) + *valP;
1996 bfd_vma delta = target - md_pcrel_from (fixP);
1997 bfd_putl32 (bfd_getl32 (buf) | ENCODE_SBTYPE_IMM (delta), buf);
1998 }
1999 break;
2000
2001 case BFD_RELOC_RISCV_RVC_BRANCH:
2002 if (fixP->fx_addsy)
2003 {
2004 /* Fill in a tentative value to improve objdump readability. */
2005 bfd_vma target = S_GET_VALUE (fixP->fx_addsy) + *valP;
2006 bfd_vma delta = target - md_pcrel_from (fixP);
2007 bfd_putl16 (bfd_getl16 (buf) | ENCODE_RVC_B_IMM (delta), buf);
2008 }
2009 break;
2010
2011 case BFD_RELOC_RISCV_RVC_JUMP:
2012 if (fixP->fx_addsy)
2013 {
2014 /* Fill in a tentative value to improve objdump readability. */
2015 bfd_vma target = S_GET_VALUE (fixP->fx_addsy) + *valP;
2016 bfd_vma delta = target - md_pcrel_from (fixP);
2017 bfd_putl16 (bfd_getl16 (buf) | ENCODE_RVC_J_IMM (delta), buf);
2018 }
2019 break;
2020
e23eba97
NC
2021 case BFD_RELOC_RISCV_CALL:
2022 case BFD_RELOC_RISCV_CALL_PLT:
45f76423
AW
2023 relaxable = TRUE;
2024 break;
2025
2026 case BFD_RELOC_RISCV_PCREL_LO12_S:
2027 case BFD_RELOC_RISCV_PCREL_LO12_I:
e23eba97
NC
2028 case BFD_RELOC_RISCV_ALIGN:
2029 break;
2030
2031 default:
2032 /* We ignore generic BFD relocations we don't know about. */
2033 if (bfd_reloc_type_lookup (stdoutput, fixP->fx_r_type) != NULL)
2034 as_fatal (_("internal error: bad relocation #%d"), fixP->fx_r_type);
2035 }
45f76423
AW
2036
2037 /* Add an R_RISCV_RELAX reloc if the reloc is relaxable. */
2038 if (relaxable && fixP->fx_tcbit && fixP->fx_addsy != NULL)
2039 {
2040 fixP->fx_next = xmemdup (fixP, sizeof (*fixP), sizeof (*fixP));
2041 fixP->fx_next->fx_addsy = fixP->fx_next->fx_subsy = NULL;
2042 fixP->fx_next->fx_r_type = BFD_RELOC_RISCV_RELAX;
2043 }
2044}
2045
2046/* Because the value of .cfi_remember_state may changed after relaxation,
2047 we insert a fix to relocate it again in link-time. */
2048
2049void
2050riscv_pre_output_hook (void)
2051{
2052 const frchainS *frch;
2053 const asection *s;
2054
2055 for (s = stdoutput->sections; s; s = s->next)
2056 for (frch = seg_info (s)->frchainP; frch; frch = frch->frch_next)
2057 {
2058 const fragS *frag;
2059
2060 for (frag = frch->frch_root; frag; frag = frag->fr_next)
2061 {
2062 if (frag->fr_type == rs_cfa)
2063 {
ad5bc882 2064 fragS *loc4_frag;
45f76423
AW
2065 expressionS exp;
2066
2067 symbolS *add_symbol = frag->fr_symbol->sy_value.X_add_symbol;
2068 symbolS *op_symbol = frag->fr_symbol->sy_value.X_op_symbol;
2069
2070 exp.X_op = O_subtract;
2071 exp.X_add_symbol = add_symbol;
2072 exp.X_add_number = 0;
2073 exp.X_op_symbol = op_symbol;
2074
2075 loc4_frag = (fragS *) frag->fr_opcode;
2076 fix_new_exp (loc4_frag, (int) frag->fr_offset, 1, &exp, 0,
2077 BFD_RELOC_RISCV_CFA);
2078 }
2079 }
2080 }
e23eba97
NC
2081}
2082
45f76423 2083
e23eba97
NC
2084/* This structure is used to hold a stack of .option values. */
2085
2086struct riscv_option_stack
2087{
2088 struct riscv_option_stack *next;
2089 struct riscv_set_options options;
2090};
2091
2092static struct riscv_option_stack *riscv_opts_stack;
2093
2094/* Handle the .option pseudo-op. */
2095
2096static void
2097s_riscv_option (int x ATTRIBUTE_UNUSED)
2098{
2099 char *name = input_line_pointer, ch;
2100
2101 while (!is_end_of_line[(unsigned char) *input_line_pointer])
2102 ++input_line_pointer;
2103 ch = *input_line_pointer;
2104 *input_line_pointer = '\0';
2105
2106 if (strcmp (name, "rvc") == 0)
2107 riscv_set_rvc (TRUE);
2108 else if (strcmp (name, "norvc") == 0)
2109 riscv_set_rvc (FALSE);
2110 else if (strcmp (name, "pic") == 0)
2111 riscv_opts.pic = TRUE;
2112 else if (strcmp (name, "nopic") == 0)
2113 riscv_opts.pic = FALSE;
45f76423
AW
2114 else if (strcmp (name, "relax") == 0)
2115 riscv_opts.relax = TRUE;
2116 else if (strcmp (name, "norelax") == 0)
2117 riscv_opts.relax = FALSE;
e23eba97
NC
2118 else if (strcmp (name, "push") == 0)
2119 {
2120 struct riscv_option_stack *s;
2121
2122 s = (struct riscv_option_stack *) xmalloc (sizeof *s);
2123 s->next = riscv_opts_stack;
2124 s->options = riscv_opts;
2125 riscv_opts_stack = s;
2126 }
2127 else if (strcmp (name, "pop") == 0)
2128 {
2129 struct riscv_option_stack *s;
2130
2131 s = riscv_opts_stack;
2132 if (s == NULL)
2133 as_bad (_(".option pop with no .option push"));
2134 else
2135 {
2136 riscv_opts = s->options;
2137 riscv_opts_stack = s->next;
2138 free (s);
2139 }
2140 }
2141 else
2142 {
2143 as_warn (_("Unrecognized .option directive: %s\n"), name);
2144 }
2145 *input_line_pointer = ch;
2146 demand_empty_rest_of_line ();
2147}
2148
2149/* Handle the .dtprelword and .dtpreldword pseudo-ops. They generate
2150 a 32-bit or 64-bit DTP-relative relocation (BYTES says which) for
2151 use in DWARF debug information. */
2152
2153static void
2154s_dtprel (int bytes)
2155{
2156 expressionS ex;
2157 char *p;
2158
2159 expression (&ex);
2160
2161 if (ex.X_op != O_symbol)
2162 {
2163 as_bad (_("Unsupported use of %s"), (bytes == 8
2164 ? ".dtpreldword"
2165 : ".dtprelword"));
2166 ignore_rest_of_line ();
2167 }
2168
2169 p = frag_more (bytes);
2170 md_number_to_chars (p, 0, bytes);
2171 fix_new_exp (frag_now, p - frag_now->fr_literal, bytes, &ex, FALSE,
2172 (bytes == 8
2173 ? BFD_RELOC_RISCV_TLS_DTPREL64
2174 : BFD_RELOC_RISCV_TLS_DTPREL32));
2175
2176 demand_empty_rest_of_line ();
2177}
2178
2179/* Handle the .bss pseudo-op. */
2180
2181static void
2182s_bss (int ignore ATTRIBUTE_UNUSED)
2183{
2184 subseg_set (bss_section, 0);
2185 demand_empty_rest_of_line ();
2186}
2187
e23eba97 2188static void
d115ab8e 2189riscv_make_nops (char *buf, bfd_vma bytes)
e23eba97 2190{
d115ab8e 2191 bfd_vma i = 0;
e23eba97 2192
d115ab8e 2193 if (bytes % 4 == 2)
e23eba97 2194 {
d115ab8e
AW
2195 md_number_to_chars (buf, RVC_NOP, 2);
2196 i += 2;
e23eba97
NC
2197 }
2198
d115ab8e 2199 gas_assert ((bytes - i) % 4 == 0);
e23eba97 2200
d115ab8e
AW
2201 for ( ; i < bytes; i += 4)
2202 md_number_to_chars (buf + i, RISCV_NOP, 4);
2203}
e23eba97 2204
d115ab8e
AW
2205/* Called from md_do_align. Used to create an alignment frag in a
2206 code section by emitting a worst-case NOP sequence that the linker
2207 will later relax to the correct number of NOPs. We can't compute
2208 the correct alignment now because of other linker relaxations. */
2209
2210bfd_boolean
2211riscv_frag_align_code (int n)
2212{
2213 bfd_vma bytes = (bfd_vma)1 << n;
2214 bfd_vma min_text_alignment = riscv_opts.rvc ? 2 : 4;
2215
2216 /* When not relaxing, riscv_handle_align handles code alignment. */
2217 if (!riscv_opts.relax)
2218 return FALSE;
e23eba97 2219
d115ab8e 2220 if (bytes > min_text_alignment)
e23eba97 2221 {
d115ab8e 2222 bfd_vma worst_case_bytes = bytes - min_text_alignment;
e23eba97 2223 char *nops = frag_more (worst_case_bytes);
e23eba97 2224 expressionS ex;
d115ab8e 2225
e23eba97
NC
2226 ex.X_op = O_constant;
2227 ex.X_add_number = worst_case_bytes;
2228
d115ab8e
AW
2229 riscv_make_nops (nops, worst_case_bytes);
2230
e23eba97
NC
2231 fix_new_exp (frag_now, nops - frag_now->fr_literal, 0,
2232 &ex, FALSE, BFD_RELOC_RISCV_ALIGN);
2233 }
e23eba97 2234
d115ab8e
AW
2235 return TRUE;
2236}
e23eba97 2237
d115ab8e
AW
2238/* Implement HANDLE_ALIGN. */
2239
2240void
2241riscv_handle_align (fragS *fragP)
2242{
2243 switch (fragP->fr_type)
2244 {
2245 case rs_align_code:
2246 /* When relaxing, riscv_frag_align_code handles code alignment. */
2247 if (!riscv_opts.relax)
2248 {
2249 bfd_signed_vma count = fragP->fr_next->fr_address
2250 - fragP->fr_address - fragP->fr_fix;
2251
2252 if (count <= 0)
2253 break;
2254
2255 count &= MAX_MEM_FOR_RS_ALIGN_CODE;
2256 riscv_make_nops (fragP->fr_literal + fragP->fr_fix, count);
2257 fragP->fr_var = count;
2258 }
2259 break;
2260
2261 default:
2262 break;
2263 }
e23eba97
NC
2264}
2265
2266int
2267md_estimate_size_before_relax (fragS *fragp, asection *segtype)
2268{
2269 return (fragp->fr_var = relaxed_branch_length (fragp, segtype, FALSE));
2270}
2271
2272/* Translate internal representation of relocation info to BFD target
2273 format. */
2274
2275arelent *
2276tc_gen_reloc (asection *section ATTRIBUTE_UNUSED, fixS *fixp)
2277{
2278 arelent *reloc = (arelent *) xmalloc (sizeof (arelent));
2279
2280 reloc->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
2281 *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
2282 reloc->address = fixp->fx_frag->fr_address + fixp->fx_where;
2283 reloc->addend = fixp->fx_addnumber;
2284
2285 reloc->howto = bfd_reloc_type_lookup (stdoutput, fixp->fx_r_type);
2286 if (reloc->howto == NULL)
2287 {
2288 if ((fixp->fx_r_type == BFD_RELOC_16 || fixp->fx_r_type == BFD_RELOC_8)
2289 && fixp->fx_addsy != NULL && fixp->fx_subsy != NULL)
2290 {
2291 /* We don't have R_RISCV_8/16, but for this special case,
2292 we can use R_RISCV_ADD8/16 with R_RISCV_SUB8/16. */
2293 return reloc;
2294 }
2295
2296 as_bad_where (fixp->fx_file, fixp->fx_line,
2297 _("cannot represent %s relocation in object file"),
2298 bfd_get_reloc_code_name (fixp->fx_r_type));
2299 return NULL;
2300 }
2301
2302 return reloc;
2303}
2304
2305int
2306riscv_relax_frag (asection *sec, fragS *fragp, long stretch ATTRIBUTE_UNUSED)
2307{
2308 if (RELAX_BRANCH_P (fragp->fr_subtype))
2309 {
2310 offsetT old_var = fragp->fr_var;
2311 fragp->fr_var = relaxed_branch_length (fragp, sec, TRUE);
2312 return fragp->fr_var - old_var;
2313 }
2314
2315 return 0;
2316}
2317
2318/* Expand far branches to multi-instruction sequences. */
2319
2320static void
2321md_convert_frag_branch (fragS *fragp)
2322{
2323 bfd_byte *buf;
2324 expressionS exp;
2325 fixS *fixp;
2326 insn_t insn;
2327 int rs1, reloc;
2328
2329 buf = (bfd_byte *)fragp->fr_literal + fragp->fr_fix;
2330
2331 exp.X_op = O_symbol;
2332 exp.X_add_symbol = fragp->fr_symbol;
2333 exp.X_add_number = fragp->fr_offset;
2334
2335 gas_assert (fragp->fr_var == RELAX_BRANCH_LENGTH (fragp->fr_subtype));
2336
2337 if (RELAX_BRANCH_RVC (fragp->fr_subtype))
2338 {
2339 switch (RELAX_BRANCH_LENGTH (fragp->fr_subtype))
2340 {
2341 case 8:
2342 case 4:
2343 /* Expand the RVC branch into a RISC-V one. */
2344 insn = bfd_getl16 (buf);
2345 rs1 = 8 + ((insn >> OP_SH_CRS1S) & OP_MASK_CRS1S);
2346 if ((insn & MASK_C_J) == MATCH_C_J)
2347 insn = MATCH_JAL;
2348 else if ((insn & MASK_C_JAL) == MATCH_C_JAL)
2349 insn = MATCH_JAL | (X_RA << OP_SH_RD);
2350 else if ((insn & MASK_C_BEQZ) == MATCH_C_BEQZ)
2351 insn = MATCH_BEQ | (rs1 << OP_SH_RS1);
2352 else if ((insn & MASK_C_BNEZ) == MATCH_C_BNEZ)
2353 insn = MATCH_BNE | (rs1 << OP_SH_RS1);
2354 else
2355 abort ();
2356 bfd_putl32 (insn, buf);
2357 break;
2358
2359 case 6:
2360 /* Invert the branch condition. Branch over the jump. */
2361 insn = bfd_getl16 (buf);
2362 insn ^= MATCH_C_BEQZ ^ MATCH_C_BNEZ;
2363 insn |= ENCODE_RVC_B_IMM (6);
2364 bfd_putl16 (insn, buf);
2365 buf += 2;
2366 goto jump;
2367
2368 case 2:
2369 /* Just keep the RVC branch. */
2370 reloc = RELAX_BRANCH_UNCOND (fragp->fr_subtype)
2371 ? BFD_RELOC_RISCV_RVC_JUMP : BFD_RELOC_RISCV_RVC_BRANCH;
2372 fixp = fix_new_exp (fragp, buf - (bfd_byte *)fragp->fr_literal,
2373 2, &exp, FALSE, reloc);
2374 buf += 2;
2375 goto done;
2376
2377 default:
1d65abb5 2378 abort ();
e23eba97
NC
2379 }
2380 }
2381
2382 switch (RELAX_BRANCH_LENGTH (fragp->fr_subtype))
2383 {
2384 case 8:
2385 gas_assert (!RELAX_BRANCH_UNCOND (fragp->fr_subtype));
2386
2387 /* Invert the branch condition. Branch over the jump. */
2388 insn = bfd_getl32 (buf);
2389 insn ^= MATCH_BEQ ^ MATCH_BNE;
2390 insn |= ENCODE_SBTYPE_IMM (8);
2391 md_number_to_chars ((char *) buf, insn, 4);
2392 buf += 4;
2393
2394jump:
2395 /* Jump to the target. */
2396 fixp = fix_new_exp (fragp, buf - (bfd_byte *)fragp->fr_literal,
2397 4, &exp, FALSE, BFD_RELOC_RISCV_JMP);
2398 md_number_to_chars ((char *) buf, MATCH_JAL, 4);
2399 buf += 4;
2400 break;
2401
2402 case 4:
2403 reloc = RELAX_BRANCH_UNCOND (fragp->fr_subtype)
2404 ? BFD_RELOC_RISCV_JMP : BFD_RELOC_12_PCREL;
2405 fixp = fix_new_exp (fragp, buf - (bfd_byte *)fragp->fr_literal,
2406 4, &exp, FALSE, reloc);
2407 buf += 4;
2408 break;
2409
2410 default:
2411 abort ();
2412 }
2413
2414done:
2415 fixp->fx_file = fragp->fr_file;
2416 fixp->fx_line = fragp->fr_line;
2417
2418 gas_assert (buf == (bfd_byte *)fragp->fr_literal
2419 + fragp->fr_fix + fragp->fr_var);
2420
2421 fragp->fr_fix += fragp->fr_var;
2422}
2423
2424/* Relax a machine dependent frag. This returns the amount by which
2425 the current size of the frag should change. */
2426
2427void
2428md_convert_frag (bfd *abfd ATTRIBUTE_UNUSED, segT asec ATTRIBUTE_UNUSED,
2429 fragS *fragp)
2430{
2431 gas_assert (RELAX_BRANCH_P (fragp->fr_subtype));
2432 md_convert_frag_branch (fragp);
2433}
2434
2435void
2436md_show_usage (FILE *stream)
2437{
2438 fprintf (stream, _("\
2439RISC-V options:\n\
2440 -m32 assemble RV32 code\n\
2441 -m64 assemble RV64 code (default)\n\
2442 -fpic generate position-independent code\n\
2443 -fno-pic don't generate position-independent code (default)\n\
2444 -msoft-float don't use F registers for floating-point values\n\
2445 -mhard-float use F registers for floating-point values (default)\n\
2446 -mno-rvc disable the C extension for compressed instructions (default)\n\
2447 -mrvc enable the C extension for compressed instructions\n\
2448 -march=ISA set the RISC-V architecture, RV64IMAFD by default\n\
2449"));
2450}
2451
2452/* Standard calling conventions leave the CFA at SP on entry. */
2453void
2454riscv_cfi_frame_initial_instructions (void)
2455{
2456 cfi_add_CFA_def_cfa_register (X_SP);
2457}
2458
2459int
2460tc_riscv_regname_to_dw2regnum (char *regname)
2461{
2462 int reg;
2463
2464 if ((reg = reg_lookup_internal (regname, RCLASS_GPR)) >= 0)
2465 return reg;
2466
2467 if ((reg = reg_lookup_internal (regname, RCLASS_FPR)) >= 0)
2468 return reg + 32;
2469
2470 as_bad (_("unknown register `%s'"), regname);
2471 return -1;
2472}
2473
2474void
2475riscv_elf_final_processing (void)
2476{
e23eba97 2477 elf_elfheader (stdoutput)->e_flags |= elf_flags;
e23eba97
NC
2478}
2479
2480/* Parse the .sleb128 and .uleb128 pseudos. Only allow constant expressions,
2481 since these directives break relaxation when used with symbol deltas. */
2482
2483static void
2484s_riscv_leb128 (int sign)
2485{
2486 expressionS exp;
2487 char *save_in = input_line_pointer;
2488
2489 expression (&exp);
2490 if (exp.X_op != O_constant)
2491 as_bad (_("non-constant .%cleb128 is not supported"), sign ? 's' : 'u');
2492 demand_empty_rest_of_line ();
2493
2494 input_line_pointer = save_in;
2495 return s_leb128 (sign);
2496}
2497
2498/* Pseudo-op table. */
2499
2500static const pseudo_typeS riscv_pseudo_table[] =
2501{
2502 /* RISC-V-specific pseudo-ops. */
2503 {"option", s_riscv_option, 0},
2504 {"half", cons, 2},
2505 {"word", cons, 4},
2506 {"dword", cons, 8},
2507 {"dtprelword", s_dtprel, 4},
2508 {"dtpreldword", s_dtprel, 8},
2509 {"bss", s_bss, 0},
e23eba97
NC
2510 {"uleb128", s_riscv_leb128, 0},
2511 {"sleb128", s_riscv_leb128, 1},
2512
2513 { NULL, NULL, 0 },
2514};
2515
2516void
2517riscv_pop_insert (void)
2518{
2519 extern void pop_insert (const pseudo_typeS *);
2520
2521 pop_insert (riscv_pseudo_table);
2522}