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