arc: Improve error messages when assembling
[deliverable/binutils-gdb.git] / gas / config / tc-arc.c
1 /* tc-arc.c -- Assembler for the ARC
2 Copyright (C) 1994-2020 Free Software Foundation, Inc.
3
4 Contributor: Claudiu Zissulescu <claziss@synopsys.com>
5
6 This file is part of GAS, the GNU Assembler.
7
8 GAS is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3, or (at your option)
11 any later version.
12
13 GAS is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with GAS; see the file COPYING. If not, write to the Free
20 Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
21 02110-1301, USA. */
22
23 #include "as.h"
24 #include "subsegs.h"
25 #include "dwarf2dbg.h"
26 #include "dw2gencfi.h"
27 #include "safe-ctype.h"
28
29 #include "opcode/arc.h"
30 #include "opcode/arc-attrs.h"
31 #include "elf/arc.h"
32 #include "../opcodes/arc-ext.h"
33
34 /* Defines section. */
35
36 #define MAX_INSN_FIXUPS 2
37 #define MAX_CONSTR_STR 20
38 #define FRAG_MAX_GROWTH 8
39
40 #ifdef DEBUG
41 # define pr_debug(fmt, args...) fprintf (stderr, fmt, ##args)
42 #else
43 # define pr_debug(fmt, args...)
44 #endif
45
46 #define MAJOR_OPCODE(x) (((x) & 0xF8000000) >> 27)
47 #define SUB_OPCODE(x) (((x) & 0x003F0000) >> 16)
48 #define LP_INSN(x) ((MAJOR_OPCODE (x) == 0x4) \
49 && (SUB_OPCODE (x) == 0x28))
50
51 #ifndef TARGET_WITH_CPU
52 #define TARGET_WITH_CPU "arc700"
53 #endif /* TARGET_WITH_CPU */
54
55 #define ARC_GET_FLAG(s) (*symbol_get_tc (s))
56 #define ARC_SET_FLAG(s,v) (*symbol_get_tc (s) |= (v))
57 #define streq(a, b) (strcmp (a, b) == 0)
58
59 /* Enum used to enumerate the relaxable ins operands. */
60 enum rlx_operand_type
61 {
62 EMPTY = 0,
63 REGISTER,
64 REGISTER_S, /* Register for short instruction(s). */
65 REGISTER_NO_GP, /* Is a register but not gp register specifically. */
66 REGISTER_DUP, /* Duplication of previous operand of type register. */
67 IMMEDIATE,
68 BRACKET
69 };
70
71 enum arc_rlx_types
72 {
73 ARC_RLX_NONE = 0,
74 ARC_RLX_BL_S,
75 ARC_RLX_BL,
76 ARC_RLX_B_S,
77 ARC_RLX_B,
78 ARC_RLX_ADD_U3,
79 ARC_RLX_ADD_U6,
80 ARC_RLX_ADD_LIMM,
81 ARC_RLX_LD_U7,
82 ARC_RLX_LD_S9,
83 ARC_RLX_LD_LIMM,
84 ARC_RLX_MOV_U8,
85 ARC_RLX_MOV_S12,
86 ARC_RLX_MOV_LIMM,
87 ARC_RLX_SUB_U3,
88 ARC_RLX_SUB_U6,
89 ARC_RLX_SUB_LIMM,
90 ARC_RLX_MPY_U6,
91 ARC_RLX_MPY_LIMM,
92 ARC_RLX_MOV_RU6,
93 ARC_RLX_MOV_RLIMM,
94 ARC_RLX_ADD_RRU6,
95 ARC_RLX_ADD_RRLIMM,
96 };
97
98 /* Macros section. */
99
100 #define regno(x) ((x) & 0x3F)
101 #define is_ir_num(x) (((x) & ~0x3F) == 0)
102 #define is_code_density_p(sc) (((sc) == CD1 || (sc) == CD2))
103 #define is_spfp_p(op) (((sc) == SPX))
104 #define is_dpfp_p(op) (((sc) == DPX))
105 #define is_fpuda_p(op) (((sc) == DPA))
106 #define is_br_jmp_insn_p(op) (((op)->insn_class == BRANCH \
107 || (op)->insn_class == JUMP \
108 || (op)->insn_class == BRCC \
109 || (op)->insn_class == BBIT0 \
110 || (op)->insn_class == BBIT1 \
111 || (op)->insn_class == BI \
112 || (op)->insn_class == EI \
113 || (op)->insn_class == ENTER \
114 || (op)->insn_class == JLI \
115 || (op)->insn_class == LOOP \
116 || (op)->insn_class == LEAVE \
117 ))
118 #define is_kernel_insn_p(op) (((op)->insn_class == KERNEL))
119 #define is_nps400_p(op) (((sc) == NPS400))
120
121 /* Generic assembler global variables which must be defined by all
122 targets. */
123
124 /* Characters which always start a comment. */
125 const char comment_chars[] = "#;";
126
127 /* Characters which start a comment at the beginning of a line. */
128 const char line_comment_chars[] = "#";
129
130 /* Characters which may be used to separate multiple commands on a
131 single line. */
132 const char line_separator_chars[] = "`";
133
134 /* Characters which are used to indicate an exponent in a floating
135 point number. */
136 const char EXP_CHARS[] = "eE";
137
138 /* Chars that mean this number is a floating point constant
139 As in 0f12.456 or 0d1.2345e12. */
140 const char FLT_CHARS[] = "rRsSfFdD";
141
142 /* Byte order. */
143 extern int target_big_endian;
144 const char *arc_target_format = DEFAULT_TARGET_FORMAT;
145 static int byte_order = DEFAULT_BYTE_ORDER;
146
147 /* Arc extension section. */
148 static segT arcext_section;
149
150 /* By default relaxation is disabled. */
151 static int relaxation_state = 0;
152
153 extern int arc_get_mach (char *);
154
155 /* Forward declarations. */
156 static void arc_lcomm (int);
157 static void arc_option (int);
158 static void arc_extra_reloc (int);
159 static void arc_extinsn (int);
160 static void arc_extcorereg (int);
161 static void arc_attribute (int);
162
163 const pseudo_typeS md_pseudo_table[] =
164 {
165 /* Make sure that .word is 32 bits. */
166 { "word", cons, 4 },
167
168 { "align", s_align_bytes, 0 }, /* Defaulting is invalid (0). */
169 { "lcomm", arc_lcomm, 0 },
170 { "lcommon", arc_lcomm, 0 },
171 { "cpu", arc_option, 0 },
172
173 { "arc_attribute", arc_attribute, 0 },
174 { "extinstruction", arc_extinsn, 0 },
175 { "extcoreregister", arc_extcorereg, EXT_CORE_REGISTER },
176 { "extauxregister", arc_extcorereg, EXT_AUX_REGISTER },
177 { "extcondcode", arc_extcorereg, EXT_COND_CODE },
178
179 { "tls_gd_ld", arc_extra_reloc, BFD_RELOC_ARC_TLS_GD_LD },
180 { "tls_gd_call", arc_extra_reloc, BFD_RELOC_ARC_TLS_GD_CALL },
181
182 { NULL, NULL, 0 }
183 };
184
185 const char *md_shortopts = "";
186
187 enum options
188 {
189 OPTION_EB = OPTION_MD_BASE,
190 OPTION_EL,
191
192 OPTION_ARC600,
193 OPTION_ARC601,
194 OPTION_ARC700,
195 OPTION_ARCEM,
196 OPTION_ARCHS,
197
198 OPTION_MCPU,
199 OPTION_CD,
200 OPTION_RELAX,
201 OPTION_NPS400,
202
203 OPTION_SPFP,
204 OPTION_DPFP,
205 OPTION_FPUDA,
206
207 /* The following options are deprecated and provided here only for
208 compatibility reasons. */
209 OPTION_USER_MODE,
210 OPTION_LD_EXT_MASK,
211 OPTION_SWAP,
212 OPTION_NORM,
213 OPTION_BARREL_SHIFT,
214 OPTION_MIN_MAX,
215 OPTION_NO_MPY,
216 OPTION_EA,
217 OPTION_MUL64,
218 OPTION_SIMD,
219 OPTION_XMAC_D16,
220 OPTION_XMAC_24,
221 OPTION_DSP_PACKA,
222 OPTION_CRC,
223 OPTION_DVBF,
224 OPTION_TELEPHONY,
225 OPTION_XYMEMORY,
226 OPTION_LOCK,
227 OPTION_SWAPE,
228 OPTION_RTSC
229 };
230
231 struct option md_longopts[] =
232 {
233 { "EB", no_argument, NULL, OPTION_EB },
234 { "EL", no_argument, NULL, OPTION_EL },
235 { "mcpu", required_argument, NULL, OPTION_MCPU },
236 { "mA6", no_argument, NULL, OPTION_ARC600 },
237 { "mARC600", no_argument, NULL, OPTION_ARC600 },
238 { "mARC601", no_argument, NULL, OPTION_ARC601 },
239 { "mARC700", no_argument, NULL, OPTION_ARC700 },
240 { "mA7", no_argument, NULL, OPTION_ARC700 },
241 { "mEM", no_argument, NULL, OPTION_ARCEM },
242 { "mHS", no_argument, NULL, OPTION_ARCHS },
243 { "mcode-density", no_argument, NULL, OPTION_CD },
244 { "mrelax", no_argument, NULL, OPTION_RELAX },
245 { "mnps400", no_argument, NULL, OPTION_NPS400 },
246
247 /* Floating point options */
248 { "mspfp", no_argument, NULL, OPTION_SPFP},
249 { "mspfp-compact", no_argument, NULL, OPTION_SPFP},
250 { "mspfp_compact", no_argument, NULL, OPTION_SPFP},
251 { "mspfp-fast", no_argument, NULL, OPTION_SPFP},
252 { "mspfp_fast", no_argument, NULL, OPTION_SPFP},
253 { "mdpfp", no_argument, NULL, OPTION_DPFP},
254 { "mdpfp-compact", no_argument, NULL, OPTION_DPFP},
255 { "mdpfp_compact", no_argument, NULL, OPTION_DPFP},
256 { "mdpfp-fast", no_argument, NULL, OPTION_DPFP},
257 { "mdpfp_fast", no_argument, NULL, OPTION_DPFP},
258 { "mfpuda", no_argument, NULL, OPTION_FPUDA},
259
260 /* The following options are deprecated and provided here only for
261 compatibility reasons. */
262 { "mav2em", no_argument, NULL, OPTION_ARCEM },
263 { "mav2hs", no_argument, NULL, OPTION_ARCHS },
264 { "muser-mode-only", no_argument, NULL, OPTION_USER_MODE },
265 { "mld-extension-reg-mask", required_argument, NULL, OPTION_LD_EXT_MASK },
266 { "mswap", no_argument, NULL, OPTION_SWAP },
267 { "mnorm", no_argument, NULL, OPTION_NORM },
268 { "mbarrel-shifter", no_argument, NULL, OPTION_BARREL_SHIFT },
269 { "mbarrel_shifter", no_argument, NULL, OPTION_BARREL_SHIFT },
270 { "mmin-max", no_argument, NULL, OPTION_MIN_MAX },
271 { "mmin_max", no_argument, NULL, OPTION_MIN_MAX },
272 { "mno-mpy", no_argument, NULL, OPTION_NO_MPY },
273 { "mea", no_argument, NULL, OPTION_EA },
274 { "mEA", no_argument, NULL, OPTION_EA },
275 { "mmul64", no_argument, NULL, OPTION_MUL64 },
276 { "msimd", no_argument, NULL, OPTION_SIMD},
277 { "mmac-d16", no_argument, NULL, OPTION_XMAC_D16},
278 { "mmac_d16", no_argument, NULL, OPTION_XMAC_D16},
279 { "mmac-24", no_argument, NULL, OPTION_XMAC_24},
280 { "mmac_24", no_argument, NULL, OPTION_XMAC_24},
281 { "mdsp-packa", no_argument, NULL, OPTION_DSP_PACKA},
282 { "mdsp_packa", no_argument, NULL, OPTION_DSP_PACKA},
283 { "mcrc", no_argument, NULL, OPTION_CRC},
284 { "mdvbf", no_argument, NULL, OPTION_DVBF},
285 { "mtelephony", no_argument, NULL, OPTION_TELEPHONY},
286 { "mxy", no_argument, NULL, OPTION_XYMEMORY},
287 { "mlock", no_argument, NULL, OPTION_LOCK},
288 { "mswape", no_argument, NULL, OPTION_SWAPE},
289 { "mrtsc", no_argument, NULL, OPTION_RTSC},
290
291 { NULL, no_argument, NULL, 0 }
292 };
293
294 size_t md_longopts_size = sizeof (md_longopts);
295
296 /* Local data and data types. */
297
298 /* Used since new relocation types are introduced in this
299 file (DUMMY_RELOC_LITUSE_*). */
300 typedef int extended_bfd_reloc_code_real_type;
301
302 struct arc_fixup
303 {
304 expressionS exp;
305
306 extended_bfd_reloc_code_real_type reloc;
307
308 /* index into arc_operands. */
309 unsigned int opindex;
310
311 /* PC-relative, used by internals fixups. */
312 unsigned char pcrel;
313
314 /* TRUE if this fixup is for LIMM operand. */
315 bfd_boolean islong;
316 };
317
318 struct arc_insn
319 {
320 unsigned long long int insn;
321 int nfixups;
322 struct arc_fixup fixups[MAX_INSN_FIXUPS];
323 long limm;
324 unsigned int len; /* Length of instruction in bytes. */
325 bfd_boolean has_limm; /* Boolean value: TRUE if limm field is
326 valid. */
327 bfd_boolean relax; /* Boolean value: TRUE if needs
328 relaxation. */
329 };
330
331 /* Structure to hold any last two instructions. */
332 static struct arc_last_insn
333 {
334 /* Saved instruction opcode. */
335 const struct arc_opcode *opcode;
336
337 /* Boolean value: TRUE if current insn is short. */
338 bfd_boolean has_limm;
339
340 /* Boolean value: TRUE if current insn has delay slot. */
341 bfd_boolean has_delay_slot;
342 } arc_last_insns[2];
343
344 /* Extension instruction suffix classes. */
345 typedef struct
346 {
347 const char *name;
348 int len;
349 int attr_class;
350 } attributes_t;
351
352 static const attributes_t suffixclass[] =
353 {
354 { "SUFFIX_FLAG", 11, ARC_SUFFIX_FLAG },
355 { "SUFFIX_COND", 11, ARC_SUFFIX_COND },
356 { "SUFFIX_NONE", 11, ARC_SUFFIX_NONE }
357 };
358
359 /* Extension instruction syntax classes. */
360 static const attributes_t syntaxclass[] =
361 {
362 { "SYNTAX_3OP", 10, ARC_SYNTAX_3OP },
363 { "SYNTAX_2OP", 10, ARC_SYNTAX_2OP },
364 { "SYNTAX_1OP", 10, ARC_SYNTAX_1OP },
365 { "SYNTAX_NOP", 10, ARC_SYNTAX_NOP }
366 };
367
368 /* Extension instruction syntax classes modifiers. */
369 static const attributes_t syntaxclassmod[] =
370 {
371 { "OP1_IMM_IMPLIED" , 15, ARC_OP1_IMM_IMPLIED },
372 { "OP1_MUST_BE_IMM" , 15, ARC_OP1_MUST_BE_IMM }
373 };
374
375 /* Extension register type. */
376 typedef struct
377 {
378 char *name;
379 int number;
380 int imode;
381 } extRegister_t;
382
383 /* A structure to hold the additional conditional codes. */
384 static struct
385 {
386 struct arc_flag_operand *arc_ext_condcode;
387 int size;
388 } ext_condcode = { NULL, 0 };
389
390 /* Structure to hold an entry in ARC_OPCODE_HASH. */
391 struct arc_opcode_hash_entry
392 {
393 /* The number of pointers in the OPCODE list. */
394 size_t count;
395
396 /* Points to a list of opcode pointers. */
397 const struct arc_opcode **opcode;
398 };
399
400 /* Structure used for iterating through an arc_opcode_hash_entry. */
401 struct arc_opcode_hash_entry_iterator
402 {
403 /* Index into the OPCODE element of the arc_opcode_hash_entry. */
404 size_t index;
405
406 /* The specific ARC_OPCODE from the ARC_OPCODES table that was last
407 returned by this iterator. */
408 const struct arc_opcode *opcode;
409 };
410
411 /* Forward declaration. */
412 static void assemble_insn
413 (const struct arc_opcode *, const expressionS *, int,
414 const struct arc_flags *, int, struct arc_insn *);
415
416 /* The selection of the machine type can come from different sources. This
417 enum is used to track how the selection was made in order to perform
418 error checks. */
419 enum mach_selection_type
420 {
421 MACH_SELECTION_NONE,
422 MACH_SELECTION_FROM_DEFAULT,
423 MACH_SELECTION_FROM_CPU_DIRECTIVE,
424 MACH_SELECTION_FROM_COMMAND_LINE
425 };
426
427 /* How the current machine type was selected. */
428 static enum mach_selection_type mach_selection_mode = MACH_SELECTION_NONE;
429
430 /* The hash table of instruction opcodes. */
431 static struct hash_control *arc_opcode_hash;
432
433 /* The hash table of register symbols. */
434 static struct hash_control *arc_reg_hash;
435
436 /* The hash table of aux register symbols. */
437 static struct hash_control *arc_aux_hash;
438
439 /* The hash table of address types. */
440 static struct hash_control *arc_addrtype_hash;
441
442 #define ARC_CPU_TYPE_A6xx(NAME,EXTRA) \
443 { #NAME, ARC_OPCODE_ARC600, bfd_mach_arc_arc600, \
444 E_ARC_MACH_ARC600, EXTRA}
445 #define ARC_CPU_TYPE_A7xx(NAME,EXTRA) \
446 { #NAME, ARC_OPCODE_ARC700, bfd_mach_arc_arc700, \
447 E_ARC_MACH_ARC700, EXTRA}
448 #define ARC_CPU_TYPE_AV2EM(NAME,EXTRA) \
449 { #NAME, ARC_OPCODE_ARCv2EM, bfd_mach_arc_arcv2, \
450 EF_ARC_CPU_ARCV2EM, EXTRA}
451 #define ARC_CPU_TYPE_AV2HS(NAME,EXTRA) \
452 { #NAME, ARC_OPCODE_ARCv2HS, bfd_mach_arc_arcv2, \
453 EF_ARC_CPU_ARCV2HS, EXTRA}
454 #define ARC_CPU_TYPE_NONE \
455 { 0, 0, 0, 0, 0 }
456
457 /* A table of CPU names and opcode sets. */
458 static const struct cpu_type
459 {
460 const char *name;
461 unsigned flags;
462 int mach;
463 unsigned eflags;
464 unsigned features;
465 }
466 cpu_types[] =
467 {
468 #include "elf/arc-cpu.def"
469 };
470
471 /* Information about the cpu/variant we're assembling for. */
472 static struct cpu_type selected_cpu = { 0, 0, 0, E_ARC_OSABI_CURRENT, 0 };
473
474 /* TRUE if current assembly code uses RF16 only registers. */
475 static bfd_boolean rf16_only = TRUE;
476
477 /* MPY option. */
478 static unsigned mpy_option = 0;
479
480 /* Use PIC. */
481 static unsigned pic_option = 0;
482
483 /* Use small data. */
484 static unsigned sda_option = 0;
485
486 /* Use TLS. */
487 static unsigned tls_option = 0;
488
489 /* Command line given features. */
490 static unsigned cl_features = 0;
491
492 /* Used by the arc_reloc_op table. Order is important. */
493 #define O_gotoff O_md1 /* @gotoff relocation. */
494 #define O_gotpc O_md2 /* @gotpc relocation. */
495 #define O_plt O_md3 /* @plt relocation. */
496 #define O_sda O_md4 /* @sda relocation. */
497 #define O_pcl O_md5 /* @pcl relocation. */
498 #define O_tlsgd O_md6 /* @tlsgd relocation. */
499 #define O_tlsie O_md7 /* @tlsie relocation. */
500 #define O_tpoff9 O_md8 /* @tpoff9 relocation. */
501 #define O_tpoff O_md9 /* @tpoff relocation. */
502 #define O_dtpoff9 O_md10 /* @dtpoff9 relocation. */
503 #define O_dtpoff O_md11 /* @dtpoff relocation. */
504 #define O_last O_dtpoff
505
506 /* Used to define a bracket as operand in tokens. */
507 #define O_bracket O_md32
508
509 /* Used to define a colon as an operand in tokens. */
510 #define O_colon O_md31
511
512 /* Used to define address types in nps400. */
513 #define O_addrtype O_md30
514
515 /* Dummy relocation, to be sorted out. */
516 #define DUMMY_RELOC_ARC_ENTRY (BFD_RELOC_UNUSED + 1)
517
518 #define USER_RELOC_P(R) ((R) >= O_gotoff && (R) <= O_last)
519
520 /* A table to map the spelling of a relocation operand into an appropriate
521 bfd_reloc_code_real_type type. The table is assumed to be ordered such
522 that op-O_literal indexes into it. */
523 #define ARC_RELOC_TABLE(op) \
524 (&arc_reloc_op[ ((!USER_RELOC_P (op)) \
525 ? (abort (), 0) \
526 : (int) (op) - (int) O_gotoff) ])
527
528 #define DEF(NAME, RELOC, REQ) \
529 { #NAME, sizeof (#NAME)-1, O_##NAME, RELOC, REQ}
530
531 static const struct arc_reloc_op_tag
532 {
533 /* String to lookup. */
534 const char *name;
535 /* Size of the string. */
536 size_t length;
537 /* Which operator to use. */
538 operatorT op;
539 extended_bfd_reloc_code_real_type reloc;
540 /* Allows complex relocation expression like identifier@reloc +
541 const. */
542 unsigned int complex_expr : 1;
543 }
544 arc_reloc_op[] =
545 {
546 DEF (gotoff, BFD_RELOC_ARC_GOTOFF, 1),
547 DEF (gotpc, BFD_RELOC_ARC_GOTPC32, 0),
548 DEF (plt, BFD_RELOC_ARC_PLT32, 0),
549 DEF (sda, DUMMY_RELOC_ARC_ENTRY, 1),
550 DEF (pcl, BFD_RELOC_ARC_PC32, 1),
551 DEF (tlsgd, BFD_RELOC_ARC_TLS_GD_GOT, 0),
552 DEF (tlsie, BFD_RELOC_ARC_TLS_IE_GOT, 0),
553 DEF (tpoff9, BFD_RELOC_ARC_TLS_LE_S9, 0),
554 DEF (tpoff, BFD_RELOC_ARC_TLS_LE_32, 1),
555 DEF (dtpoff9, BFD_RELOC_ARC_TLS_DTPOFF_S9, 0),
556 DEF (dtpoff, BFD_RELOC_ARC_TLS_DTPOFF, 1),
557 };
558
559 static const int arc_num_reloc_op
560 = sizeof (arc_reloc_op) / sizeof (*arc_reloc_op);
561
562 /* Structure for relaxable instruction that have to be swapped with a
563 smaller alternative instruction. */
564 struct arc_relaxable_ins
565 {
566 /* Mnemonic that should be checked. */
567 const char *mnemonic_r;
568
569 /* Operands that should be checked.
570 Indexes of operands from operand array. */
571 enum rlx_operand_type operands[6];
572
573 /* Flags that should be checked. */
574 unsigned flag_classes[5];
575
576 /* Mnemonic (smaller) alternative to be used later for relaxation. */
577 const char *mnemonic_alt;
578
579 /* Index of operand that generic relaxation has to check. */
580 unsigned opcheckidx;
581
582 /* Base subtype index used. */
583 enum arc_rlx_types subtype;
584 };
585
586 #define RELAX_TABLE_ENTRY(BITS, ISSIGNED, SIZE, NEXT) \
587 { (ISSIGNED) ? ((1 << ((BITS) - 1)) - 1) : ((1 << (BITS)) - 1), \
588 (ISSIGNED) ? -(1 << ((BITS) - 1)) : 0, \
589 (SIZE), \
590 (NEXT) } \
591
592 #define RELAX_TABLE_ENTRY_MAX(ISSIGNED, SIZE, NEXT) \
593 { (ISSIGNED) ? 0x7FFFFFFF : 0xFFFFFFFF, \
594 (ISSIGNED) ? -(0x7FFFFFFF) : 0, \
595 (SIZE), \
596 (NEXT) } \
597
598
599 /* ARC relaxation table. */
600 const relax_typeS md_relax_table[] =
601 {
602 /* Fake entry. */
603 {0, 0, 0, 0},
604
605 /* BL_S s13 ->
606 BL s25. */
607 RELAX_TABLE_ENTRY (13, 1, 2, ARC_RLX_BL),
608 RELAX_TABLE_ENTRY (25, 1, 4, ARC_RLX_NONE),
609
610 /* B_S s10 ->
611 B s25. */
612 RELAX_TABLE_ENTRY (10, 1, 2, ARC_RLX_B),
613 RELAX_TABLE_ENTRY (25, 1, 4, ARC_RLX_NONE),
614
615 /* ADD_S c,b, u3 ->
616 ADD<.f> a,b,u6 ->
617 ADD<.f> a,b,limm. */
618 RELAX_TABLE_ENTRY (3, 0, 2, ARC_RLX_ADD_U6),
619 RELAX_TABLE_ENTRY (6, 0, 4, ARC_RLX_ADD_LIMM),
620 RELAX_TABLE_ENTRY_MAX (0, 8, ARC_RLX_NONE),
621
622 /* LD_S a, [b, u7] ->
623 LD<zz><.x><.aa><.di> a, [b, s9] ->
624 LD<zz><.x><.aa><.di> a, [b, limm] */
625 RELAX_TABLE_ENTRY (7, 0, 2, ARC_RLX_LD_S9),
626 RELAX_TABLE_ENTRY (9, 1, 4, ARC_RLX_LD_LIMM),
627 RELAX_TABLE_ENTRY_MAX (1, 8, ARC_RLX_NONE),
628
629 /* MOV_S b, u8 ->
630 MOV<.f> b, s12 ->
631 MOV<.f> b, limm. */
632 RELAX_TABLE_ENTRY (8, 0, 2, ARC_RLX_MOV_S12),
633 RELAX_TABLE_ENTRY (8, 0, 4, ARC_RLX_MOV_LIMM),
634 RELAX_TABLE_ENTRY_MAX (0, 8, ARC_RLX_NONE),
635
636 /* SUB_S c, b, u3 ->
637 SUB<.f> a, b, u6 ->
638 SUB<.f> a, b, limm. */
639 RELAX_TABLE_ENTRY (3, 0, 2, ARC_RLX_SUB_U6),
640 RELAX_TABLE_ENTRY (6, 0, 4, ARC_RLX_SUB_LIMM),
641 RELAX_TABLE_ENTRY_MAX (0, 8, ARC_RLX_NONE),
642
643 /* MPY<.f> a, b, u6 ->
644 MPY<.f> a, b, limm. */
645 RELAX_TABLE_ENTRY (6, 0, 4, ARC_RLX_MPY_LIMM),
646 RELAX_TABLE_ENTRY_MAX (0, 8, ARC_RLX_NONE),
647
648 /* MOV<.f><.cc> b, u6 ->
649 MOV<.f><.cc> b, limm. */
650 RELAX_TABLE_ENTRY (6, 0, 4, ARC_RLX_MOV_RLIMM),
651 RELAX_TABLE_ENTRY_MAX (0, 8, ARC_RLX_NONE),
652
653 /* ADD<.f><.cc> b, b, u6 ->
654 ADD<.f><.cc> b, b, limm. */
655 RELAX_TABLE_ENTRY (6, 0, 4, ARC_RLX_ADD_RRLIMM),
656 RELAX_TABLE_ENTRY_MAX (0, 8, ARC_RLX_NONE),
657 };
658
659 /* Order of this table's entries matters! */
660 const struct arc_relaxable_ins arc_relaxable_insns[] =
661 {
662 { "bl", { IMMEDIATE }, { 0 }, "bl_s", 0, ARC_RLX_BL_S },
663 { "b", { IMMEDIATE }, { 0 }, "b_s", 0, ARC_RLX_B_S },
664 { "add", { REGISTER, REGISTER_DUP, IMMEDIATE }, { 5, 1, 0 }, "add",
665 2, ARC_RLX_ADD_RRU6},
666 { "add", { REGISTER_S, REGISTER_S, IMMEDIATE }, { 0 }, "add_s", 2,
667 ARC_RLX_ADD_U3 },
668 { "add", { REGISTER, REGISTER, IMMEDIATE }, { 5, 0 }, "add", 2,
669 ARC_RLX_ADD_U6 },
670 { "ld", { REGISTER_S, BRACKET, REGISTER_S, IMMEDIATE, BRACKET },
671 { 0 }, "ld_s", 3, ARC_RLX_LD_U7 },
672 { "ld", { REGISTER, BRACKET, REGISTER_NO_GP, IMMEDIATE, BRACKET },
673 { 11, 4, 14, 17, 0 }, "ld", 3, ARC_RLX_LD_S9 },
674 { "mov", { REGISTER_S, IMMEDIATE }, { 0 }, "mov_s", 1, ARC_RLX_MOV_U8 },
675 { "mov", { REGISTER, IMMEDIATE }, { 5, 0 }, "mov", 1, ARC_RLX_MOV_S12 },
676 { "mov", { REGISTER, IMMEDIATE }, { 5, 1, 0 },"mov", 1, ARC_RLX_MOV_RU6 },
677 { "sub", { REGISTER_S, REGISTER_S, IMMEDIATE }, { 0 }, "sub_s", 2,
678 ARC_RLX_SUB_U3 },
679 { "sub", { REGISTER, REGISTER, IMMEDIATE }, { 5, 0 }, "sub", 2,
680 ARC_RLX_SUB_U6 },
681 { "mpy", { REGISTER, REGISTER, IMMEDIATE }, { 5, 0 }, "mpy", 2,
682 ARC_RLX_MPY_U6 },
683 };
684
685 const unsigned arc_num_relaxable_ins = ARRAY_SIZE (arc_relaxable_insns);
686
687 /* Pre-defined "_GLOBAL_OFFSET_TABLE_". */
688 symbolS * GOT_symbol = 0;
689
690 /* Set to TRUE when we assemble instructions. */
691 static bfd_boolean assembling_insn = FALSE;
692
693 /* List with attributes set explicitly. */
694 static bfd_boolean attributes_set_explicitly[NUM_KNOWN_OBJ_ATTRIBUTES];
695
696 /* Functions implementation. */
697
698 /* Return a pointer to ARC_OPCODE_HASH_ENTRY that identifies all
699 ARC_OPCODE entries in ARC_OPCODE_HASH that match NAME, or NULL if there
700 are no matching entries in ARC_OPCODE_HASH. */
701
702 static const struct arc_opcode_hash_entry *
703 arc_find_opcode (const char *name)
704 {
705 const struct arc_opcode_hash_entry *entry;
706
707 entry = hash_find (arc_opcode_hash, name);
708 return entry;
709 }
710
711 /* Initialise the iterator ITER. */
712
713 static void
714 arc_opcode_hash_entry_iterator_init (struct arc_opcode_hash_entry_iterator *iter)
715 {
716 iter->index = 0;
717 iter->opcode = NULL;
718 }
719
720 /* Return the next ARC_OPCODE from ENTRY, using ITER to hold state between
721 calls to this function. Return NULL when all ARC_OPCODE entries have
722 been returned. */
723
724 static const struct arc_opcode *
725 arc_opcode_hash_entry_iterator_next (const struct arc_opcode_hash_entry *entry,
726 struct arc_opcode_hash_entry_iterator *iter)
727 {
728 if (iter->opcode == NULL && iter->index == 0)
729 {
730 gas_assert (entry->count > 0);
731 iter->opcode = entry->opcode[iter->index];
732 }
733 else if (iter->opcode != NULL)
734 {
735 const char *old_name = iter->opcode->name;
736
737 iter->opcode++;
738 if (iter->opcode->name == NULL
739 || strcmp (old_name, iter->opcode->name) != 0)
740 {
741 iter->index++;
742 if (iter->index == entry->count)
743 iter->opcode = NULL;
744 else
745 iter->opcode = entry->opcode[iter->index];
746 }
747 }
748
749 return iter->opcode;
750 }
751
752 /* Insert an opcode into opcode hash structure. */
753
754 static void
755 arc_insert_opcode (const struct arc_opcode *opcode)
756 {
757 const char *name, *retval;
758 struct arc_opcode_hash_entry *entry;
759 name = opcode->name;
760
761 entry = hash_find (arc_opcode_hash, name);
762 if (entry == NULL)
763 {
764 entry = XNEW (struct arc_opcode_hash_entry);
765 entry->count = 0;
766 entry->opcode = NULL;
767
768 retval = hash_insert (arc_opcode_hash, name, (void *) entry);
769 if (retval)
770 as_fatal (_("internal error: can't hash opcode '%s': %s"),
771 name, retval);
772 }
773
774 entry->opcode = XRESIZEVEC (const struct arc_opcode *, entry->opcode,
775 entry->count + 1);
776
777 if (entry->opcode == NULL)
778 as_fatal (_("Virtual memory exhausted"));
779
780 entry->opcode[entry->count] = opcode;
781 entry->count++;
782 }
783
784
785 /* Like md_number_to_chars but for middle-endian values. The 4-byte limm
786 value, is encoded as 'middle-endian' for a little-endian target. This
787 function is used for regular 4, 6, and 8 byte instructions as well. */
788
789 static void
790 md_number_to_chars_midend (char *buf, unsigned long long val, int n)
791 {
792 switch (n)
793 {
794 case 2:
795 md_number_to_chars (buf, val, n);
796 break;
797 case 6:
798 md_number_to_chars (buf, (val & 0xffff00000000ull) >> 32, 2);
799 md_number_to_chars_midend (buf + 2, (val & 0xffffffff), 4);
800 break;
801 case 4:
802 md_number_to_chars (buf, (val & 0xffff0000) >> 16, 2);
803 md_number_to_chars (buf + 2, (val & 0xffff), 2);
804 break;
805 case 8:
806 md_number_to_chars_midend (buf, (val & 0xffffffff00000000ull) >> 32, 4);
807 md_number_to_chars_midend (buf + 4, (val & 0xffffffff), 4);
808 break;
809 default:
810 abort ();
811 }
812 }
813
814 /* Check if a feature is allowed for a specific CPU. */
815
816 static void
817 arc_check_feature (void)
818 {
819 unsigned i;
820
821 if (!selected_cpu.features
822 || !selected_cpu.name)
823 return;
824
825 for (i = 0; i < ARRAY_SIZE (feature_list); i++)
826 if ((selected_cpu.features & feature_list[i].feature)
827 && !(selected_cpu.flags & feature_list[i].cpus))
828 as_bad (_("invalid %s option for %s cpu"), feature_list[i].name,
829 selected_cpu.name);
830
831 for (i = 0; i < ARRAY_SIZE (conflict_list); i++)
832 if ((selected_cpu.features & conflict_list[i]) == conflict_list[i])
833 as_bad(_("conflicting ISA extension attributes."));
834 }
835
836 /* Select an appropriate entry from CPU_TYPES based on ARG and initialise
837 the relevant static global variables. Parameter SEL describes where
838 this selection originated from. */
839
840 static void
841 arc_select_cpu (const char *arg, enum mach_selection_type sel)
842 {
843 int i;
844 static struct cpu_type old_cpu = { 0, 0, 0, E_ARC_OSABI_CURRENT, 0 };
845
846 /* We should only set a default if we've not made a selection from some
847 other source. */
848 gas_assert (sel != MACH_SELECTION_FROM_DEFAULT
849 || mach_selection_mode == MACH_SELECTION_NONE);
850
851 if ((mach_selection_mode == MACH_SELECTION_FROM_CPU_DIRECTIVE)
852 && (sel == MACH_SELECTION_FROM_CPU_DIRECTIVE))
853 as_bad (_("Multiple .cpu directives found"));
854
855 /* Look for a matching entry in CPU_TYPES array. */
856 for (i = 0; cpu_types[i].name; ++i)
857 {
858 if (!strcasecmp (cpu_types[i].name, arg))
859 {
860 /* If a previous selection was made on the command line, then we
861 allow later selections on the command line to override earlier
862 ones. However, a selection from a '.cpu NAME' directive must
863 match the command line selection, or we give a warning. */
864 if (mach_selection_mode == MACH_SELECTION_FROM_COMMAND_LINE)
865 {
866 gas_assert (sel == MACH_SELECTION_FROM_COMMAND_LINE
867 || sel == MACH_SELECTION_FROM_CPU_DIRECTIVE);
868 if (sel == MACH_SELECTION_FROM_CPU_DIRECTIVE
869 && selected_cpu.mach != cpu_types[i].mach)
870 {
871 as_warn (_("Command-line value overrides \".cpu\" directive"));
872 }
873 return;
874 }
875 /* Initialise static global data about selected machine type. */
876 selected_cpu.flags = cpu_types[i].flags;
877 selected_cpu.name = cpu_types[i].name;
878 selected_cpu.features = cpu_types[i].features | cl_features;
879 selected_cpu.mach = cpu_types[i].mach;
880 selected_cpu.eflags = ((selected_cpu.eflags & ~EF_ARC_MACH_MSK)
881 | cpu_types[i].eflags);
882 break;
883 }
884 }
885
886 if (!cpu_types[i].name)
887 as_fatal (_("unknown architecture: %s\n"), arg);
888
889 /* Check if set features are compatible with the chosen CPU. */
890 arc_check_feature ();
891
892 /* If we change the CPU, we need to re-init the bfd. */
893 if (mach_selection_mode != MACH_SELECTION_NONE
894 && (old_cpu.mach != selected_cpu.mach))
895 {
896 bfd_find_target (arc_target_format, stdoutput);
897 if (! bfd_set_arch_mach (stdoutput, bfd_arch_arc, selected_cpu.mach))
898 as_warn (_("Could not set architecture and machine"));
899 }
900
901 mach_selection_mode = sel;
902 old_cpu = selected_cpu;
903 }
904
905 /* Here ends all the ARCompact extension instruction assembling
906 stuff. */
907
908 static void
909 arc_extra_reloc (int r_type)
910 {
911 char *sym_name, c;
912 symbolS *sym, *lab = NULL;
913
914 if (*input_line_pointer == '@')
915 input_line_pointer++;
916 c = get_symbol_name (&sym_name);
917 sym = symbol_find_or_make (sym_name);
918 restore_line_pointer (c);
919 if (c == ',' && r_type == BFD_RELOC_ARC_TLS_GD_LD)
920 {
921 ++input_line_pointer;
922 char *lab_name;
923 c = get_symbol_name (&lab_name);
924 lab = symbol_find_or_make (lab_name);
925 restore_line_pointer (c);
926 }
927
928 /* These relocations exist as a mechanism for the compiler to tell the
929 linker how to patch the code if the tls model is optimised. However,
930 the relocation itself does not require any space within the assembler
931 fragment, and so we pass a size of 0.
932
933 The lines that generate these relocations look like this:
934
935 .tls_gd_ld @.tdata`bl __tls_get_addr@plt
936
937 The '.tls_gd_ld @.tdata' is processed first and generates the
938 additional relocation, while the 'bl __tls_get_addr@plt' is processed
939 second and generates the additional branch.
940
941 It is possible that the additional relocation generated by the
942 '.tls_gd_ld @.tdata' will be attached at the very end of one fragment,
943 while the 'bl __tls_get_addr@plt' will be generated as the first thing
944 in the next fragment. This will be fine; both relocations will still
945 appear to be at the same address in the generated object file.
946 However, this only works as the additional relocation is generated
947 with size of 0 bytes. */
948 fixS *fixP
949 = fix_new (frag_now, /* Which frag? */
950 frag_now_fix (), /* Where in that frag? */
951 0, /* size: 1, 2, or 4 usually. */
952 sym, /* X_add_symbol. */
953 0, /* X_add_number. */
954 FALSE, /* TRUE if PC-relative relocation. */
955 r_type /* Relocation type. */);
956 fixP->fx_subsy = lab;
957 }
958
959 static symbolS *
960 arc_lcomm_internal (int ignore ATTRIBUTE_UNUSED,
961 symbolS *symbolP, addressT size)
962 {
963 addressT align = 0;
964 SKIP_WHITESPACE ();
965
966 if (*input_line_pointer == ',')
967 {
968 align = parse_align (1);
969
970 if (align == (addressT) -1)
971 return NULL;
972 }
973 else
974 {
975 if (size >= 8)
976 align = 3;
977 else if (size >= 4)
978 align = 2;
979 else if (size >= 2)
980 align = 1;
981 else
982 align = 0;
983 }
984
985 bss_alloc (symbolP, size, align);
986 S_CLEAR_EXTERNAL (symbolP);
987
988 return symbolP;
989 }
990
991 static void
992 arc_lcomm (int ignore)
993 {
994 symbolS *symbolP = s_comm_internal (ignore, arc_lcomm_internal);
995
996 if (symbolP)
997 symbol_get_bfdsym (symbolP)->flags |= BSF_OBJECT;
998 }
999
1000 /* Select the cpu we're assembling for. */
1001
1002 static void
1003 arc_option (int ignore ATTRIBUTE_UNUSED)
1004 {
1005 char c;
1006 char *cpu;
1007 const char *cpu_name;
1008
1009 c = get_symbol_name (&cpu);
1010
1011 cpu_name = cpu;
1012 if ((!strcmp ("ARC600", cpu))
1013 || (!strcmp ("ARC601", cpu))
1014 || (!strcmp ("A6", cpu)))
1015 cpu_name = "arc600";
1016 else if ((!strcmp ("ARC700", cpu))
1017 || (!strcmp ("A7", cpu)))
1018 cpu_name = "arc700";
1019 else if (!strcmp ("EM", cpu))
1020 cpu_name = "arcem";
1021 else if (!strcmp ("HS", cpu))
1022 cpu_name = "archs";
1023 else if (!strcmp ("NPS400", cpu))
1024 cpu_name = "nps400";
1025
1026 arc_select_cpu (cpu_name, MACH_SELECTION_FROM_CPU_DIRECTIVE);
1027
1028 restore_line_pointer (c);
1029 demand_empty_rest_of_line ();
1030 }
1031
1032 /* Smartly print an expression. */
1033
1034 static void
1035 debug_exp (expressionS *t)
1036 {
1037 const char *name ATTRIBUTE_UNUSED;
1038 const char *namemd ATTRIBUTE_UNUSED;
1039
1040 pr_debug ("debug_exp: ");
1041
1042 switch (t->X_op)
1043 {
1044 default: name = "unknown"; break;
1045 case O_illegal: name = "O_illegal"; break;
1046 case O_absent: name = "O_absent"; break;
1047 case O_constant: name = "O_constant"; break;
1048 case O_symbol: name = "O_symbol"; break;
1049 case O_symbol_rva: name = "O_symbol_rva"; break;
1050 case O_register: name = "O_register"; break;
1051 case O_big: name = "O_big"; break;
1052 case O_uminus: name = "O_uminus"; break;
1053 case O_bit_not: name = "O_bit_not"; break;
1054 case O_logical_not: name = "O_logical_not"; break;
1055 case O_multiply: name = "O_multiply"; break;
1056 case O_divide: name = "O_divide"; break;
1057 case O_modulus: name = "O_modulus"; break;
1058 case O_left_shift: name = "O_left_shift"; break;
1059 case O_right_shift: name = "O_right_shift"; break;
1060 case O_bit_inclusive_or: name = "O_bit_inclusive_or"; break;
1061 case O_bit_or_not: name = "O_bit_or_not"; break;
1062 case O_bit_exclusive_or: name = "O_bit_exclusive_or"; break;
1063 case O_bit_and: name = "O_bit_and"; break;
1064 case O_add: name = "O_add"; break;
1065 case O_subtract: name = "O_subtract"; break;
1066 case O_eq: name = "O_eq"; break;
1067 case O_ne: name = "O_ne"; break;
1068 case O_lt: name = "O_lt"; break;
1069 case O_le: name = "O_le"; break;
1070 case O_ge: name = "O_ge"; break;
1071 case O_gt: name = "O_gt"; break;
1072 case O_logical_and: name = "O_logical_and"; break;
1073 case O_logical_or: name = "O_logical_or"; break;
1074 case O_index: name = "O_index"; break;
1075 case O_bracket: name = "O_bracket"; break;
1076 case O_colon: name = "O_colon"; break;
1077 case O_addrtype: name = "O_addrtype"; break;
1078 }
1079
1080 switch (t->X_md)
1081 {
1082 default: namemd = "unknown"; break;
1083 case O_gotoff: namemd = "O_gotoff"; break;
1084 case O_gotpc: namemd = "O_gotpc"; break;
1085 case O_plt: namemd = "O_plt"; break;
1086 case O_sda: namemd = "O_sda"; break;
1087 case O_pcl: namemd = "O_pcl"; break;
1088 case O_tlsgd: namemd = "O_tlsgd"; break;
1089 case O_tlsie: namemd = "O_tlsie"; break;
1090 case O_tpoff9: namemd = "O_tpoff9"; break;
1091 case O_tpoff: namemd = "O_tpoff"; break;
1092 case O_dtpoff9: namemd = "O_dtpoff9"; break;
1093 case O_dtpoff: namemd = "O_dtpoff"; break;
1094 }
1095
1096 pr_debug ("%s (%s, %s, %d, %s)", name,
1097 (t->X_add_symbol) ? S_GET_NAME (t->X_add_symbol) : "--",
1098 (t->X_op_symbol) ? S_GET_NAME (t->X_op_symbol) : "--",
1099 (int) t->X_add_number,
1100 (t->X_md) ? namemd : "--");
1101 pr_debug ("\n");
1102 fflush (stderr);
1103 }
1104
1105 /* Helper for parsing an argument, used for sorting out the relocation
1106 type. */
1107
1108 static void
1109 parse_reloc_symbol (expressionS *resultP)
1110 {
1111 char *reloc_name, c, *sym_name;
1112 size_t len;
1113 int i;
1114 const struct arc_reloc_op_tag *r;
1115 expressionS right;
1116 symbolS *base;
1117
1118 /* A relocation operand has the following form
1119 @identifier@relocation_type. The identifier is already in
1120 tok! */
1121 if (resultP->X_op != O_symbol)
1122 {
1123 as_bad (_("No valid label relocation operand"));
1124 resultP->X_op = O_illegal;
1125 return;
1126 }
1127
1128 /* Parse @relocation_type. */
1129 input_line_pointer++;
1130 c = get_symbol_name (&reloc_name);
1131 len = input_line_pointer - reloc_name;
1132 if (len == 0)
1133 {
1134 as_bad (_("No relocation operand"));
1135 resultP->X_op = O_illegal;
1136 return;
1137 }
1138
1139 /* Go through known relocation and try to find a match. */
1140 r = &arc_reloc_op[0];
1141 for (i = arc_num_reloc_op - 1; i >= 0; i--, r++)
1142 if (len == r->length
1143 && memcmp (reloc_name, r->name, len) == 0)
1144 break;
1145 if (i < 0)
1146 {
1147 as_bad (_("Unknown relocation operand: @%s"), reloc_name);
1148 resultP->X_op = O_illegal;
1149 return;
1150 }
1151
1152 *input_line_pointer = c;
1153 SKIP_WHITESPACE_AFTER_NAME ();
1154 /* Extra check for TLS: base. */
1155 if (*input_line_pointer == '@')
1156 {
1157 if (resultP->X_op_symbol != NULL
1158 || resultP->X_op != O_symbol)
1159 {
1160 as_bad (_("Unable to parse TLS base: %s"),
1161 input_line_pointer);
1162 resultP->X_op = O_illegal;
1163 return;
1164 }
1165 input_line_pointer++;
1166 c = get_symbol_name (&sym_name);
1167 base = symbol_find_or_make (sym_name);
1168 resultP->X_op = O_subtract;
1169 resultP->X_op_symbol = base;
1170 restore_line_pointer (c);
1171 right.X_add_number = 0;
1172 }
1173
1174 if ((*input_line_pointer != '+')
1175 && (*input_line_pointer != '-'))
1176 right.X_add_number = 0;
1177 else
1178 {
1179 /* Parse the constant of a complex relocation expression
1180 like @identifier@reloc +/- const. */
1181 if (! r->complex_expr)
1182 {
1183 as_bad (_("@%s is not a complex relocation."), r->name);
1184 resultP->X_op = O_illegal;
1185 return;
1186 }
1187 expression (&right);
1188 if (right.X_op != O_constant)
1189 {
1190 as_bad (_("Bad expression: @%s + %s."),
1191 r->name, input_line_pointer);
1192 resultP->X_op = O_illegal;
1193 return;
1194 }
1195 }
1196
1197 resultP->X_md = r->op;
1198 resultP->X_add_number = right.X_add_number;
1199 }
1200
1201 /* Parse the arguments to an opcode. */
1202
1203 static int
1204 tokenize_arguments (char *str,
1205 expressionS *tok,
1206 int ntok)
1207 {
1208 char *old_input_line_pointer;
1209 bfd_boolean saw_comma = FALSE;
1210 bfd_boolean saw_arg = FALSE;
1211 int brk_lvl = 0;
1212 int num_args = 0;
1213
1214 memset (tok, 0, sizeof (*tok) * ntok);
1215
1216 /* Save and restore input_line_pointer around this function. */
1217 old_input_line_pointer = input_line_pointer;
1218 input_line_pointer = str;
1219
1220 while (*input_line_pointer)
1221 {
1222 SKIP_WHITESPACE ();
1223 switch (*input_line_pointer)
1224 {
1225 case '\0':
1226 goto fini;
1227
1228 case ',':
1229 input_line_pointer++;
1230 if (saw_comma || !saw_arg)
1231 goto err;
1232 saw_comma = TRUE;
1233 break;
1234
1235 case '}':
1236 case ']':
1237 ++input_line_pointer;
1238 --brk_lvl;
1239 if (!saw_arg || num_args == ntok)
1240 goto err;
1241 tok->X_op = O_bracket;
1242 ++tok;
1243 ++num_args;
1244 break;
1245
1246 case '{':
1247 case '[':
1248 input_line_pointer++;
1249 if (brk_lvl || num_args == ntok)
1250 goto err;
1251 ++brk_lvl;
1252 tok->X_op = O_bracket;
1253 ++tok;
1254 ++num_args;
1255 break;
1256
1257 case ':':
1258 input_line_pointer++;
1259 if (!saw_arg || num_args == ntok)
1260 goto err;
1261 tok->X_op = O_colon;
1262 saw_arg = FALSE;
1263 ++tok;
1264 ++num_args;
1265 break;
1266
1267 case '@':
1268 /* We have labels, function names and relocations, all
1269 starting with @ symbol. Sort them out. */
1270 if ((saw_arg && !saw_comma) || num_args == ntok)
1271 goto err;
1272
1273 /* Parse @label. */
1274 input_line_pointer++;
1275 tok->X_op = O_symbol;
1276 tok->X_md = O_absent;
1277 expression (tok);
1278
1279 if (*input_line_pointer == '@')
1280 parse_reloc_symbol (tok);
1281
1282 debug_exp (tok);
1283
1284 if (tok->X_op == O_illegal
1285 || tok->X_op == O_absent
1286 || num_args == ntok)
1287 goto err;
1288
1289 saw_comma = FALSE;
1290 saw_arg = TRUE;
1291 tok++;
1292 num_args++;
1293 break;
1294
1295 case '%':
1296 /* Can be a register. */
1297 ++input_line_pointer;
1298 /* Fall through. */
1299 default:
1300
1301 if ((saw_arg && !saw_comma) || num_args == ntok)
1302 goto err;
1303
1304 tok->X_op = O_absent;
1305 tok->X_md = O_absent;
1306 expression (tok);
1307
1308 /* Legacy: There are cases when we have
1309 identifier@relocation_type, if it is the case parse the
1310 relocation type as well. */
1311 if (*input_line_pointer == '@')
1312 parse_reloc_symbol (tok);
1313
1314 debug_exp (tok);
1315
1316 if (tok->X_op == O_illegal
1317 || tok->X_op == O_absent
1318 || num_args == ntok)
1319 goto err;
1320
1321 saw_comma = FALSE;
1322 saw_arg = TRUE;
1323 tok++;
1324 num_args++;
1325 break;
1326 }
1327 }
1328
1329 fini:
1330 if (saw_comma || brk_lvl)
1331 goto err;
1332 input_line_pointer = old_input_line_pointer;
1333
1334 return num_args;
1335
1336 err:
1337 if (brk_lvl)
1338 as_bad (_("Brackets in operand field incorrect"));
1339 else if (saw_comma)
1340 as_bad (_("extra comma"));
1341 else if (!saw_arg)
1342 as_bad (_("missing argument"));
1343 else
1344 as_bad (_("missing comma or colon"));
1345 input_line_pointer = old_input_line_pointer;
1346 return -1;
1347 }
1348
1349 /* Parse the flags to a structure. */
1350
1351 static int
1352 tokenize_flags (const char *str,
1353 struct arc_flags flags[],
1354 int nflg)
1355 {
1356 char *old_input_line_pointer;
1357 bfd_boolean saw_flg = FALSE;
1358 bfd_boolean saw_dot = FALSE;
1359 int num_flags = 0;
1360 size_t flgnamelen;
1361
1362 memset (flags, 0, sizeof (*flags) * nflg);
1363
1364 /* Save and restore input_line_pointer around this function. */
1365 old_input_line_pointer = input_line_pointer;
1366 input_line_pointer = (char *) str;
1367
1368 while (*input_line_pointer)
1369 {
1370 switch (*input_line_pointer)
1371 {
1372 case ' ':
1373 case '\0':
1374 goto fini;
1375
1376 case '.':
1377 input_line_pointer++;
1378 if (saw_dot)
1379 goto err;
1380 saw_dot = TRUE;
1381 saw_flg = FALSE;
1382 break;
1383
1384 default:
1385 if (saw_flg && !saw_dot)
1386 goto err;
1387
1388 if (num_flags >= nflg)
1389 goto err;
1390
1391 flgnamelen = strspn (input_line_pointer,
1392 "abcdefghijklmnopqrstuvwxyz0123456789");
1393 if (flgnamelen > MAX_FLAG_NAME_LENGTH)
1394 goto err;
1395
1396 memcpy (flags->name, input_line_pointer, flgnamelen);
1397
1398 input_line_pointer += flgnamelen;
1399 flags++;
1400 saw_dot = FALSE;
1401 saw_flg = TRUE;
1402 num_flags++;
1403 break;
1404 }
1405 }
1406
1407 fini:
1408 input_line_pointer = old_input_line_pointer;
1409 return num_flags;
1410
1411 err:
1412 if (saw_dot)
1413 as_bad (_("extra dot"));
1414 else if (!saw_flg)
1415 as_bad (_("unrecognized flag"));
1416 else
1417 as_bad (_("failed to parse flags"));
1418 input_line_pointer = old_input_line_pointer;
1419 return -1;
1420 }
1421
1422 /* Apply the fixups in order. */
1423
1424 static void
1425 apply_fixups (struct arc_insn *insn, fragS *fragP, int fix)
1426 {
1427 int i;
1428
1429 for (i = 0; i < insn->nfixups; i++)
1430 {
1431 struct arc_fixup *fixup = &insn->fixups[i];
1432 int size, pcrel, offset = 0;
1433
1434 /* FIXME! the reloc size is wrong in the BFD file.
1435 When it is fixed please delete me. */
1436 size = ((insn->len == 2) && !fixup->islong) ? 2 : 4;
1437
1438 if (fixup->islong)
1439 offset = insn->len;
1440
1441 /* Some fixups are only used internally, thus no howto. */
1442 if ((int) fixup->reloc == 0)
1443 as_fatal (_("Unhandled reloc type"));
1444
1445 if ((int) fixup->reloc < 0)
1446 {
1447 /* FIXME! the reloc size is wrong in the BFD file.
1448 When it is fixed please enable me.
1449 size = ((insn->len == 2 && !fixup->islong) ? 2 : 4; */
1450 pcrel = fixup->pcrel;
1451 }
1452 else
1453 {
1454 reloc_howto_type *reloc_howto =
1455 bfd_reloc_type_lookup (stdoutput,
1456 (bfd_reloc_code_real_type) fixup->reloc);
1457 gas_assert (reloc_howto);
1458
1459 /* FIXME! the reloc size is wrong in the BFD file.
1460 When it is fixed please enable me.
1461 size = bfd_get_reloc_size (reloc_howto); */
1462 pcrel = reloc_howto->pc_relative;
1463 }
1464
1465 pr_debug ("%s:%d: apply_fixups: new %s fixup (PCrel:%s) of size %d @ \
1466 offset %d + %d\n",
1467 fragP->fr_file, fragP->fr_line,
1468 (fixup->reloc < 0) ? "Internal" :
1469 bfd_get_reloc_code_name (fixup->reloc),
1470 pcrel ? "Y" : "N",
1471 size, fix, offset);
1472 fix_new_exp (fragP, fix + offset,
1473 size, &fixup->exp, pcrel, fixup->reloc);
1474
1475 /* Check for ZOLs, and update symbol info if any. */
1476 if (LP_INSN (insn->insn))
1477 {
1478 gas_assert (fixup->exp.X_add_symbol);
1479 ARC_SET_FLAG (fixup->exp.X_add_symbol, ARC_FLAG_ZOL);
1480 }
1481 }
1482 }
1483
1484 /* Actually output an instruction with its fixup. */
1485
1486 static void
1487 emit_insn0 (struct arc_insn *insn, char *where, bfd_boolean relax)
1488 {
1489 char *f = where;
1490 size_t total_len;
1491
1492 pr_debug ("Emit insn : 0x%llx\n", insn->insn);
1493 pr_debug ("\tLength : 0x%d\n", insn->len);
1494 pr_debug ("\tLong imm: 0x%lx\n", insn->limm);
1495
1496 /* Write out the instruction. */
1497 total_len = insn->len + (insn->has_limm ? 4 : 0);
1498 if (!relax)
1499 f = frag_more (total_len);
1500
1501 md_number_to_chars_midend(f, insn->insn, insn->len);
1502
1503 if (insn->has_limm)
1504 md_number_to_chars_midend (f + insn->len, insn->limm, 4);
1505 dwarf2_emit_insn (total_len);
1506
1507 if (!relax)
1508 apply_fixups (insn, frag_now, (f - frag_now->fr_literal));
1509 }
1510
1511 static void
1512 emit_insn1 (struct arc_insn *insn)
1513 {
1514 /* How frag_var's args are currently configured:
1515 - rs_machine_dependent, to dictate it's a relaxation frag.
1516 - FRAG_MAX_GROWTH, maximum size of instruction
1517 - 0, variable size that might grow...unused by generic relaxation.
1518 - frag_now->fr_subtype, fr_subtype starting value, set previously.
1519 - s, opand expression.
1520 - 0, offset but it's unused.
1521 - 0, opcode but it's unused. */
1522 symbolS *s = make_expr_symbol (&insn->fixups[0].exp);
1523 frag_now->tc_frag_data.pcrel = insn->fixups[0].pcrel;
1524
1525 if (frag_room () < FRAG_MAX_GROWTH)
1526 {
1527 /* Handle differently when frag literal memory is exhausted.
1528 This is used because when there's not enough memory left in
1529 the current frag, a new frag is created and the information
1530 we put into frag_now->tc_frag_data is disregarded. */
1531
1532 struct arc_relax_type relax_info_copy;
1533 relax_substateT subtype = frag_now->fr_subtype;
1534
1535 memcpy (&relax_info_copy, &frag_now->tc_frag_data,
1536 sizeof (struct arc_relax_type));
1537
1538 frag_wane (frag_now);
1539 frag_grow (FRAG_MAX_GROWTH);
1540
1541 memcpy (&frag_now->tc_frag_data, &relax_info_copy,
1542 sizeof (struct arc_relax_type));
1543
1544 frag_var (rs_machine_dependent, FRAG_MAX_GROWTH, 0,
1545 subtype, s, 0, 0);
1546 }
1547 else
1548 frag_var (rs_machine_dependent, FRAG_MAX_GROWTH, 0,
1549 frag_now->fr_subtype, s, 0, 0);
1550 }
1551
1552 static void
1553 emit_insn (struct arc_insn *insn)
1554 {
1555 if (insn->relax)
1556 emit_insn1 (insn);
1557 else
1558 emit_insn0 (insn, NULL, FALSE);
1559 }
1560
1561 /* Check whether a symbol involves a register. */
1562
1563 static bfd_boolean
1564 contains_register (symbolS *sym)
1565 {
1566 if (sym)
1567 {
1568 expressionS *ex = symbol_get_value_expression (sym);
1569
1570 return ((O_register == ex->X_op)
1571 && !contains_register (ex->X_add_symbol)
1572 && !contains_register (ex->X_op_symbol));
1573 }
1574
1575 return FALSE;
1576 }
1577
1578 /* Returns the register number within a symbol. */
1579
1580 static int
1581 get_register (symbolS *sym)
1582 {
1583 if (!contains_register (sym))
1584 return -1;
1585
1586 expressionS *ex = symbol_get_value_expression (sym);
1587 return regno (ex->X_add_number);
1588 }
1589
1590 /* Return true if a RELOC is generic. A generic reloc is PC-rel of a
1591 simple ME relocation (e.g. RELOC_ARC_32_ME, BFD_RELOC_ARC_PC32. */
1592
1593 static bfd_boolean
1594 generic_reloc_p (extended_bfd_reloc_code_real_type reloc)
1595 {
1596 if (!reloc)
1597 return FALSE;
1598
1599 switch (reloc)
1600 {
1601 case BFD_RELOC_ARC_SDA_LDST:
1602 case BFD_RELOC_ARC_SDA_LDST1:
1603 case BFD_RELOC_ARC_SDA_LDST2:
1604 case BFD_RELOC_ARC_SDA16_LD:
1605 case BFD_RELOC_ARC_SDA16_LD1:
1606 case BFD_RELOC_ARC_SDA16_LD2:
1607 case BFD_RELOC_ARC_SDA16_ST2:
1608 case BFD_RELOC_ARC_SDA32_ME:
1609 return FALSE;
1610 default:
1611 return TRUE;
1612 }
1613 }
1614
1615 /* Allocates a tok entry. */
1616
1617 static int
1618 allocate_tok (expressionS *tok, int ntok, int cidx)
1619 {
1620 if (ntok > MAX_INSN_ARGS - 2)
1621 return 0; /* No space left. */
1622
1623 if (cidx > ntok)
1624 return 0; /* Incorrect args. */
1625
1626 memcpy (&tok[ntok+1], &tok[ntok], sizeof (*tok));
1627
1628 if (cidx == ntok)
1629 return 1; /* Success. */
1630 return allocate_tok (tok, ntok - 1, cidx);
1631 }
1632
1633 /* Check if an particular ARC feature is enabled. */
1634
1635 static bfd_boolean
1636 check_cpu_feature (insn_subclass_t sc)
1637 {
1638 if (is_code_density_p (sc) && !(selected_cpu.features & CD))
1639 return FALSE;
1640
1641 if (is_spfp_p (sc) && !(selected_cpu.features & SPX))
1642 return FALSE;
1643
1644 if (is_dpfp_p (sc) && !(selected_cpu.features & DPX))
1645 return FALSE;
1646
1647 if (is_fpuda_p (sc) && !(selected_cpu.features & DPA))
1648 return FALSE;
1649
1650 if (is_nps400_p (sc) && !(selected_cpu.features & NPS400))
1651 return FALSE;
1652
1653 return TRUE;
1654 }
1655
1656 /* Parse the flags described by FIRST_PFLAG and NFLGS against the flag
1657 operands in OPCODE. Stores the matching OPCODES into the FIRST_PFLAG
1658 array and returns TRUE if the flag operands all match, otherwise,
1659 returns FALSE, in which case the FIRST_PFLAG array may have been
1660 modified. */
1661
1662 static bfd_boolean
1663 parse_opcode_flags (const struct arc_opcode *opcode,
1664 int nflgs,
1665 struct arc_flags *first_pflag)
1666 {
1667 int lnflg, i;
1668 const unsigned char *flgidx;
1669
1670 lnflg = nflgs;
1671 for (i = 0; i < nflgs; i++)
1672 first_pflag[i].flgp = NULL;
1673
1674 /* Check the flags. Iterate over the valid flag classes. */
1675 for (flgidx = opcode->flags; *flgidx; ++flgidx)
1676 {
1677 /* Get a valid flag class. */
1678 const struct arc_flag_class *cl_flags = &arc_flag_classes[*flgidx];
1679 const unsigned *flgopridx;
1680 int cl_matches = 0;
1681 struct arc_flags *pflag = NULL;
1682
1683 /* Check if opcode has implicit flag classes. */
1684 if (cl_flags->flag_class & F_CLASS_IMPLICIT)
1685 continue;
1686
1687 /* Check for extension conditional codes. */
1688 if (ext_condcode.arc_ext_condcode
1689 && cl_flags->flag_class & F_CLASS_EXTEND)
1690 {
1691 struct arc_flag_operand *pf = ext_condcode.arc_ext_condcode;
1692 while (pf->name)
1693 {
1694 pflag = first_pflag;
1695 for (i = 0; i < nflgs; i++, pflag++)
1696 {
1697 if (!strcmp (pf->name, pflag->name))
1698 {
1699 if (pflag->flgp != NULL)
1700 return FALSE;
1701 /* Found it. */
1702 cl_matches++;
1703 pflag->flgp = pf;
1704 lnflg--;
1705 break;
1706 }
1707 }
1708 pf++;
1709 }
1710 }
1711
1712 for (flgopridx = cl_flags->flags; *flgopridx; ++flgopridx)
1713 {
1714 const struct arc_flag_operand *flg_operand;
1715
1716 pflag = first_pflag;
1717 flg_operand = &arc_flag_operands[*flgopridx];
1718 for (i = 0; i < nflgs; i++, pflag++)
1719 {
1720 /* Match against the parsed flags. */
1721 if (!strcmp (flg_operand->name, pflag->name))
1722 {
1723 if (pflag->flgp != NULL)
1724 return FALSE;
1725 cl_matches++;
1726 pflag->flgp = flg_operand;
1727 lnflg--;
1728 break; /* goto next flag class and parsed flag. */
1729 }
1730 }
1731 }
1732
1733 if ((cl_flags->flag_class & F_CLASS_REQUIRED) && cl_matches == 0)
1734 return FALSE;
1735 if ((cl_flags->flag_class & F_CLASS_OPTIONAL) && cl_matches > 1)
1736 return FALSE;
1737 }
1738
1739 /* Did I check all the parsed flags? */
1740 return lnflg ? FALSE : TRUE;
1741 }
1742
1743
1744 /* Search forward through all variants of an opcode looking for a
1745 syntax match. */
1746
1747 static const struct arc_opcode *
1748 find_opcode_match (const struct arc_opcode_hash_entry *entry,
1749 expressionS *tok,
1750 int *pntok,
1751 struct arc_flags *first_pflag,
1752 int nflgs,
1753 int *pcpumatch,
1754 const char **errmsg)
1755 {
1756 const struct arc_opcode *opcode;
1757 struct arc_opcode_hash_entry_iterator iter;
1758 int ntok = *pntok;
1759 int got_cpu_match = 0;
1760 expressionS bktok[MAX_INSN_ARGS];
1761 int bkntok, maxerridx = 0;
1762 expressionS emptyE;
1763 const char *tmpmsg = NULL;
1764
1765 arc_opcode_hash_entry_iterator_init (&iter);
1766 memset (&emptyE, 0, sizeof (emptyE));
1767 memcpy (bktok, tok, MAX_INSN_ARGS * sizeof (*tok));
1768 bkntok = ntok;
1769
1770 for (opcode = arc_opcode_hash_entry_iterator_next (entry, &iter);
1771 opcode != NULL;
1772 opcode = arc_opcode_hash_entry_iterator_next (entry, &iter))
1773 {
1774 const unsigned char *opidx;
1775 int tokidx = 0;
1776 const expressionS *t = &emptyE;
1777
1778 pr_debug ("%s:%d: find_opcode_match: trying opcode 0x%08llX ",
1779 frag_now->fr_file, frag_now->fr_line, opcode->opcode);
1780
1781 /* Don't match opcodes that don't exist on this
1782 architecture. */
1783 if (!(opcode->cpu & selected_cpu.flags))
1784 goto match_failed;
1785
1786 if (!check_cpu_feature (opcode->subclass))
1787 goto match_failed;
1788
1789 got_cpu_match = 1;
1790 pr_debug ("cpu ");
1791
1792 /* Check the operands. */
1793 for (opidx = opcode->operands; *opidx; ++opidx)
1794 {
1795 const struct arc_operand *operand = &arc_operands[*opidx];
1796
1797 /* Only take input from real operands. */
1798 if (ARC_OPERAND_IS_FAKE (operand))
1799 continue;
1800
1801 /* When we expect input, make sure we have it. */
1802 if (tokidx >= ntok)
1803 goto match_failed;
1804
1805 /* Match operand type with expression type. */
1806 switch (operand->flags & ARC_OPERAND_TYPECHECK_MASK)
1807 {
1808 case ARC_OPERAND_ADDRTYPE:
1809 {
1810 tmpmsg = NULL;
1811
1812 /* Check to be an address type. */
1813 if (tok[tokidx].X_op != O_addrtype)
1814 goto match_failed;
1815
1816 /* All address type operands need to have an insert
1817 method in order to check that we have the correct
1818 address type. */
1819 gas_assert (operand->insert != NULL);
1820 (*operand->insert) (0, tok[tokidx].X_add_number,
1821 &tmpmsg);
1822 if (tmpmsg != NULL)
1823 goto match_failed;
1824 }
1825 break;
1826
1827 case ARC_OPERAND_IR:
1828 /* Check to be a register. */
1829 if ((tok[tokidx].X_op != O_register
1830 || !is_ir_num (tok[tokidx].X_add_number))
1831 && !(operand->flags & ARC_OPERAND_IGNORE))
1832 goto match_failed;
1833
1834 /* If expect duplicate, make sure it is duplicate. */
1835 if (operand->flags & ARC_OPERAND_DUPLICATE)
1836 {
1837 /* Check for duplicate. */
1838 if (t->X_op != O_register
1839 || !is_ir_num (t->X_add_number)
1840 || (regno (t->X_add_number) !=
1841 regno (tok[tokidx].X_add_number)))
1842 goto match_failed;
1843 }
1844
1845 /* Special handling? */
1846 if (operand->insert)
1847 {
1848 tmpmsg = NULL;
1849 (*operand->insert)(0,
1850 regno (tok[tokidx].X_add_number),
1851 &tmpmsg);
1852 if (tmpmsg)
1853 {
1854 if (operand->flags & ARC_OPERAND_IGNORE)
1855 {
1856 /* Missing argument, create one. */
1857 if (!allocate_tok (tok, ntok - 1, tokidx))
1858 goto match_failed;
1859
1860 tok[tokidx].X_op = O_absent;
1861 ++ntok;
1862 }
1863 else
1864 goto match_failed;
1865 }
1866 }
1867
1868 t = &tok[tokidx];
1869 break;
1870
1871 case ARC_OPERAND_BRAKET:
1872 /* Check if bracket is also in opcode table as
1873 operand. */
1874 if (tok[tokidx].X_op != O_bracket)
1875 goto match_failed;
1876 break;
1877
1878 case ARC_OPERAND_COLON:
1879 /* Check if colon is also in opcode table as operand. */
1880 if (tok[tokidx].X_op != O_colon)
1881 goto match_failed;
1882 break;
1883
1884 case ARC_OPERAND_LIMM:
1885 case ARC_OPERAND_SIGNED:
1886 case ARC_OPERAND_UNSIGNED:
1887 switch (tok[tokidx].X_op)
1888 {
1889 case O_illegal:
1890 case O_absent:
1891 case O_register:
1892 goto match_failed;
1893
1894 case O_bracket:
1895 /* Got an (too) early bracket, check if it is an
1896 ignored operand. N.B. This procedure works only
1897 when bracket is the last operand! */
1898 if (!(operand->flags & ARC_OPERAND_IGNORE))
1899 goto match_failed;
1900 /* Insert the missing operand. */
1901 if (!allocate_tok (tok, ntok - 1, tokidx))
1902 goto match_failed;
1903
1904 tok[tokidx].X_op = O_absent;
1905 ++ntok;
1906 break;
1907
1908 case O_symbol:
1909 {
1910 const char *p;
1911 char *tmpp, *pp;
1912 const struct arc_aux_reg *auxr;
1913
1914 if (opcode->insn_class != AUXREG)
1915 goto de_fault;
1916 p = S_GET_NAME (tok[tokidx].X_add_symbol);
1917
1918 /* For compatibility reasons, an aux register can
1919 be spelled with upper or lower case
1920 letters. */
1921 tmpp = strdup (p);
1922 for (pp = tmpp; *pp; ++pp) *pp = TOLOWER (*pp);
1923
1924 auxr = hash_find (arc_aux_hash, tmpp);
1925 if (auxr)
1926 {
1927 /* We modify the token array here, safe in the
1928 knowledge, that if this was the wrong
1929 choice then the original contents will be
1930 restored from BKTOK. */
1931 tok[tokidx].X_op = O_constant;
1932 tok[tokidx].X_add_number = auxr->address;
1933 ARC_SET_FLAG (tok[tokidx].X_add_symbol, ARC_FLAG_AUX);
1934 }
1935 free (tmpp);
1936
1937 if (tok[tokidx].X_op != O_constant)
1938 goto de_fault;
1939 }
1940 /* Fall through. */
1941 case O_constant:
1942 /* Check the range. */
1943 if (operand->bits != 32
1944 && !(operand->flags & ARC_OPERAND_NCHK))
1945 {
1946 offsetT min, max, val;
1947 val = tok[tokidx].X_add_number;
1948
1949 if (operand->flags & ARC_OPERAND_SIGNED)
1950 {
1951 max = (1 << (operand->bits - 1)) - 1;
1952 min = -(1 << (operand->bits - 1));
1953 }
1954 else
1955 {
1956 max = (1 << operand->bits) - 1;
1957 min = 0;
1958 }
1959
1960 if (val < min || val > max)
1961 {
1962 tmpmsg = _("immediate is out of bounds");
1963 goto match_failed;
1964 }
1965
1966 /* Check alignments. */
1967 if ((operand->flags & ARC_OPERAND_ALIGNED32)
1968 && (val & 0x03))
1969 {
1970 tmpmsg = _("immediate is not 32bit aligned");
1971 goto match_failed;
1972 }
1973
1974 if ((operand->flags & ARC_OPERAND_ALIGNED16)
1975 && (val & 0x01))
1976 {
1977 tmpmsg = _("immediate is not 16bit aligned");
1978 goto match_failed;
1979 }
1980 }
1981 else if (operand->flags & ARC_OPERAND_NCHK)
1982 {
1983 if (operand->insert)
1984 {
1985 tmpmsg = NULL;
1986 (*operand->insert)(0,
1987 tok[tokidx].X_add_number,
1988 &tmpmsg);
1989 if (tmpmsg)
1990 goto match_failed;
1991 }
1992 else if (!(operand->flags & ARC_OPERAND_IGNORE))
1993 goto match_failed;
1994 }
1995 break;
1996
1997 case O_subtract:
1998 /* Check if it is register range. */
1999 if ((tok[tokidx].X_add_number == 0)
2000 && contains_register (tok[tokidx].X_add_symbol)
2001 && contains_register (tok[tokidx].X_op_symbol))
2002 {
2003 int regs;
2004
2005 regs = get_register (tok[tokidx].X_add_symbol);
2006 regs <<= 16;
2007 regs |= get_register (tok[tokidx].X_op_symbol);
2008 if (operand->insert)
2009 {
2010 tmpmsg = NULL;
2011 (*operand->insert)(0,
2012 regs,
2013 &tmpmsg);
2014 if (tmpmsg)
2015 goto match_failed;
2016 }
2017 else
2018 goto match_failed;
2019 break;
2020 }
2021 /* Fall through. */
2022 default:
2023 de_fault:
2024 if (operand->default_reloc == 0)
2025 goto match_failed; /* The operand needs relocation. */
2026
2027 /* Relocs requiring long immediate. FIXME! make it
2028 generic and move it to a function. */
2029 switch (tok[tokidx].X_md)
2030 {
2031 case O_gotoff:
2032 case O_gotpc:
2033 case O_pcl:
2034 case O_tpoff:
2035 case O_dtpoff:
2036 case O_tlsgd:
2037 case O_tlsie:
2038 if (!(operand->flags & ARC_OPERAND_LIMM))
2039 goto match_failed;
2040 /* Fall through. */
2041 case O_absent:
2042 if (!generic_reloc_p (operand->default_reloc))
2043 goto match_failed;
2044 break;
2045 default:
2046 break;
2047 }
2048 break;
2049 }
2050 /* If expect duplicate, make sure it is duplicate. */
2051 if (operand->flags & ARC_OPERAND_DUPLICATE)
2052 {
2053 if (t->X_op == O_illegal
2054 || t->X_op == O_absent
2055 || t->X_op == O_register
2056 || (t->X_add_number != tok[tokidx].X_add_number))
2057 {
2058 tmpmsg = _("operand is not duplicate of the "
2059 "previous one");
2060 goto match_failed;
2061 }
2062 }
2063 t = &tok[tokidx];
2064 break;
2065
2066 default:
2067 /* Everything else should have been fake. */
2068 abort ();
2069 }
2070
2071 ++tokidx;
2072 }
2073 pr_debug ("opr ");
2074
2075 /* Setup ready for flag parsing. */
2076 if (!parse_opcode_flags (opcode, nflgs, first_pflag))
2077 {
2078 tmpmsg = _("flag mismatch");
2079 goto match_failed;
2080 }
2081
2082 pr_debug ("flg");
2083 /* Possible match -- did we use all of our input? */
2084 if (tokidx == ntok)
2085 {
2086 *pntok = ntok;
2087 pr_debug ("\n");
2088 return opcode;
2089 }
2090 tmpmsg = _("too many arguments");
2091
2092 match_failed:;
2093 pr_debug ("\n");
2094 /* Restore the original parameters. */
2095 memcpy (tok, bktok, MAX_INSN_ARGS * sizeof (*tok));
2096 ntok = bkntok;
2097 if (tokidx >= maxerridx
2098 && tmpmsg)
2099 {
2100 maxerridx = tokidx;
2101 *errmsg = tmpmsg;
2102 }
2103 }
2104
2105 if (*pcpumatch)
2106 *pcpumatch = got_cpu_match;
2107
2108 return NULL;
2109 }
2110
2111 /* Swap operand tokens. */
2112
2113 static void
2114 swap_operand (expressionS *operand_array,
2115 unsigned source,
2116 unsigned destination)
2117 {
2118 expressionS cpy_operand;
2119 expressionS *src_operand;
2120 expressionS *dst_operand;
2121 size_t size;
2122
2123 if (source == destination)
2124 return;
2125
2126 src_operand = &operand_array[source];
2127 dst_operand = &operand_array[destination];
2128 size = sizeof (expressionS);
2129
2130 /* Make copy of operand to swap with and swap. */
2131 memcpy (&cpy_operand, dst_operand, size);
2132 memcpy (dst_operand, src_operand, size);
2133 memcpy (src_operand, &cpy_operand, size);
2134 }
2135
2136 /* Check if *op matches *tok type.
2137 Returns FALSE if they don't match, TRUE if they match. */
2138
2139 static bfd_boolean
2140 pseudo_operand_match (const expressionS *tok,
2141 const struct arc_operand_operation *op)
2142 {
2143 offsetT min, max, val;
2144 bfd_boolean ret;
2145 const struct arc_operand *operand_real = &arc_operands[op->operand_idx];
2146
2147 ret = FALSE;
2148 switch (tok->X_op)
2149 {
2150 case O_constant:
2151 if (operand_real->bits == 32 && (operand_real->flags & ARC_OPERAND_LIMM))
2152 ret = 1;
2153 else if (!(operand_real->flags & ARC_OPERAND_IR))
2154 {
2155 val = tok->X_add_number + op->count;
2156 if (operand_real->flags & ARC_OPERAND_SIGNED)
2157 {
2158 max = (1 << (operand_real->bits - 1)) - 1;
2159 min = -(1 << (operand_real->bits - 1));
2160 }
2161 else
2162 {
2163 max = (1 << operand_real->bits) - 1;
2164 min = 0;
2165 }
2166 if (min <= val && val <= max)
2167 ret = TRUE;
2168 }
2169 break;
2170
2171 case O_symbol:
2172 /* Handle all symbols as long immediates or signed 9. */
2173 if (operand_real->flags & ARC_OPERAND_LIMM
2174 || ((operand_real->flags & ARC_OPERAND_SIGNED)
2175 && operand_real->bits == 9))
2176 ret = TRUE;
2177 break;
2178
2179 case O_register:
2180 if (operand_real->flags & ARC_OPERAND_IR)
2181 ret = TRUE;
2182 break;
2183
2184 case O_bracket:
2185 if (operand_real->flags & ARC_OPERAND_BRAKET)
2186 ret = TRUE;
2187 break;
2188
2189 default:
2190 /* Unknown. */
2191 break;
2192 }
2193 return ret;
2194 }
2195
2196 /* Find pseudo instruction in array. */
2197
2198 static const struct arc_pseudo_insn *
2199 find_pseudo_insn (const char *opname,
2200 int ntok,
2201 const expressionS *tok)
2202 {
2203 const struct arc_pseudo_insn *pseudo_insn = NULL;
2204 const struct arc_operand_operation *op;
2205 unsigned int i;
2206 int j;
2207
2208 for (i = 0; i < arc_num_pseudo_insn; ++i)
2209 {
2210 pseudo_insn = &arc_pseudo_insns[i];
2211 if (strcmp (pseudo_insn->mnemonic_p, opname) == 0)
2212 {
2213 op = pseudo_insn->operand;
2214 for (j = 0; j < ntok; ++j)
2215 if (!pseudo_operand_match (&tok[j], &op[j]))
2216 break;
2217
2218 /* Found the right instruction. */
2219 if (j == ntok)
2220 return pseudo_insn;
2221 }
2222 }
2223 return NULL;
2224 }
2225
2226 /* Assumes the expressionS *tok is of sufficient size. */
2227
2228 static const struct arc_opcode_hash_entry *
2229 find_special_case_pseudo (const char *opname,
2230 int *ntok,
2231 expressionS *tok,
2232 int *nflgs,
2233 struct arc_flags *pflags)
2234 {
2235 const struct arc_pseudo_insn *pseudo_insn = NULL;
2236 const struct arc_operand_operation *operand_pseudo;
2237 const struct arc_operand *operand_real;
2238 unsigned i;
2239 char construct_operand[MAX_CONSTR_STR];
2240
2241 /* Find whether opname is in pseudo instruction array. */
2242 pseudo_insn = find_pseudo_insn (opname, *ntok, tok);
2243
2244 if (pseudo_insn == NULL)
2245 return NULL;
2246
2247 /* Handle flag, Limited to one flag at the moment. */
2248 if (pseudo_insn->flag_r != NULL)
2249 *nflgs += tokenize_flags (pseudo_insn->flag_r, &pflags[*nflgs],
2250 MAX_INSN_FLGS - *nflgs);
2251
2252 /* Handle operand operations. */
2253 for (i = 0; i < pseudo_insn->operand_cnt; ++i)
2254 {
2255 operand_pseudo = &pseudo_insn->operand[i];
2256 operand_real = &arc_operands[operand_pseudo->operand_idx];
2257
2258 if (operand_real->flags & ARC_OPERAND_BRAKET
2259 && !operand_pseudo->needs_insert)
2260 continue;
2261
2262 /* Has to be inserted (i.e. this token does not exist yet). */
2263 if (operand_pseudo->needs_insert)
2264 {
2265 if (operand_real->flags & ARC_OPERAND_BRAKET)
2266 {
2267 tok[i].X_op = O_bracket;
2268 ++(*ntok);
2269 continue;
2270 }
2271
2272 /* Check if operand is a register or constant and handle it
2273 by type. */
2274 if (operand_real->flags & ARC_OPERAND_IR)
2275 snprintf (construct_operand, MAX_CONSTR_STR, "r%d",
2276 operand_pseudo->count);
2277 else
2278 snprintf (construct_operand, MAX_CONSTR_STR, "%d",
2279 operand_pseudo->count);
2280
2281 tokenize_arguments (construct_operand, &tok[i], 1);
2282 ++(*ntok);
2283 }
2284
2285 else if (operand_pseudo->count)
2286 {
2287 /* Operand number has to be adjusted accordingly (by operand
2288 type). */
2289 switch (tok[i].X_op)
2290 {
2291 case O_constant:
2292 tok[i].X_add_number += operand_pseudo->count;
2293 break;
2294
2295 case O_symbol:
2296 break;
2297
2298 default:
2299 /* Ignored. */
2300 break;
2301 }
2302 }
2303 }
2304
2305 /* Swap operands if necessary. Only supports one swap at the
2306 moment. */
2307 for (i = 0; i < pseudo_insn->operand_cnt; ++i)
2308 {
2309 operand_pseudo = &pseudo_insn->operand[i];
2310
2311 if (operand_pseudo->swap_operand_idx == i)
2312 continue;
2313
2314 swap_operand (tok, i, operand_pseudo->swap_operand_idx);
2315
2316 /* Prevent a swap back later by breaking out. */
2317 break;
2318 }
2319
2320 return arc_find_opcode (pseudo_insn->mnemonic_r);
2321 }
2322
2323 static const struct arc_opcode_hash_entry *
2324 find_special_case_flag (const char *opname,
2325 int *nflgs,
2326 struct arc_flags *pflags)
2327 {
2328 unsigned int i;
2329 const char *flagnm;
2330 unsigned flag_idx, flag_arr_idx;
2331 size_t flaglen, oplen;
2332 const struct arc_flag_special *arc_flag_special_opcode;
2333 const struct arc_opcode_hash_entry *entry;
2334
2335 /* Search for special case instruction. */
2336 for (i = 0; i < arc_num_flag_special; i++)
2337 {
2338 arc_flag_special_opcode = &arc_flag_special_cases[i];
2339 oplen = strlen (arc_flag_special_opcode->name);
2340
2341 if (strncmp (opname, arc_flag_special_opcode->name, oplen) != 0)
2342 continue;
2343
2344 /* Found a potential special case instruction, now test for
2345 flags. */
2346 for (flag_arr_idx = 0;; ++flag_arr_idx)
2347 {
2348 flag_idx = arc_flag_special_opcode->flags[flag_arr_idx];
2349 if (flag_idx == 0)
2350 break; /* End of array, nothing found. */
2351
2352 flagnm = arc_flag_operands[flag_idx].name;
2353 flaglen = strlen (flagnm);
2354 if (strcmp (opname + oplen, flagnm) == 0)
2355 {
2356 entry = arc_find_opcode (arc_flag_special_opcode->name);
2357
2358 if (*nflgs + 1 > MAX_INSN_FLGS)
2359 break;
2360 memcpy (pflags[*nflgs].name, flagnm, flaglen);
2361 pflags[*nflgs].name[flaglen] = '\0';
2362 (*nflgs)++;
2363 return entry;
2364 }
2365 }
2366 }
2367 return NULL;
2368 }
2369
2370 /* Used to find special case opcode. */
2371
2372 static const struct arc_opcode_hash_entry *
2373 find_special_case (const char *opname,
2374 int *nflgs,
2375 struct arc_flags *pflags,
2376 expressionS *tok,
2377 int *ntok)
2378 {
2379 const struct arc_opcode_hash_entry *entry;
2380
2381 entry = find_special_case_pseudo (opname, ntok, tok, nflgs, pflags);
2382
2383 if (entry == NULL)
2384 entry = find_special_case_flag (opname, nflgs, pflags);
2385
2386 return entry;
2387 }
2388
2389 /* Autodetect cpu attribute list. */
2390
2391 static void
2392 autodetect_attributes (const struct arc_opcode *opcode,
2393 const expressionS *tok,
2394 int ntok)
2395 {
2396 unsigned i;
2397 struct mpy_type
2398 {
2399 unsigned feature;
2400 unsigned encoding;
2401 } mpy_list[] = {{ MPY1E, 1 }, { MPY6E, 6 }, { MPY7E, 7 }, { MPY8E, 8 },
2402 { MPY9E, 9 }};
2403
2404 for (i = 0; i < ARRAY_SIZE (feature_list); i++)
2405 if (opcode->subclass == feature_list[i].feature)
2406 selected_cpu.features |= feature_list[i].feature;
2407
2408 for (i = 0; i < ARRAY_SIZE (mpy_list); i++)
2409 if (opcode->subclass == mpy_list[i].feature)
2410 mpy_option = mpy_list[i].encoding;
2411
2412 for (i = 0; i < (unsigned) ntok; i++)
2413 {
2414 switch (tok[i].X_md)
2415 {
2416 case O_gotoff:
2417 case O_gotpc:
2418 case O_plt:
2419 pic_option = 2;
2420 break;
2421 case O_sda:
2422 sda_option = 2;
2423 break;
2424 case O_tlsgd:
2425 case O_tlsie:
2426 case O_tpoff9:
2427 case O_tpoff:
2428 case O_dtpoff9:
2429 case O_dtpoff:
2430 tls_option = 1;
2431 break;
2432 default:
2433 break;
2434 }
2435
2436 switch (tok[i].X_op)
2437 {
2438 case O_register:
2439 if ((tok[i].X_add_number >= 4 && tok[i].X_add_number <= 9)
2440 || (tok[i].X_add_number >= 16 && tok[i].X_add_number <= 25))
2441 rf16_only = FALSE;
2442 break;
2443 default:
2444 break;
2445 }
2446 }
2447 }
2448
2449 /* Given an opcode name, pre-tockenized set of argumenst and the
2450 opcode flags, take it all the way through emission. */
2451
2452 static void
2453 assemble_tokens (const char *opname,
2454 expressionS *tok,
2455 int ntok,
2456 struct arc_flags *pflags,
2457 int nflgs)
2458 {
2459 bfd_boolean found_something = FALSE;
2460 const struct arc_opcode_hash_entry *entry;
2461 int cpumatch = 1;
2462 const char *errmsg = NULL;
2463
2464 /* Search opcodes. */
2465 entry = arc_find_opcode (opname);
2466
2467 /* Couldn't find opcode conventional way, try special cases. */
2468 if (entry == NULL)
2469 entry = find_special_case (opname, &nflgs, pflags, tok, &ntok);
2470
2471 if (entry != NULL)
2472 {
2473 const struct arc_opcode *opcode;
2474
2475 pr_debug ("%s:%d: assemble_tokens: %s\n",
2476 frag_now->fr_file, frag_now->fr_line, opname);
2477 found_something = TRUE;
2478 opcode = find_opcode_match (entry, tok, &ntok, pflags,
2479 nflgs, &cpumatch, &errmsg);
2480 if (opcode != NULL)
2481 {
2482 struct arc_insn insn;
2483
2484 autodetect_attributes (opcode, tok, ntok);
2485 assemble_insn (opcode, tok, ntok, pflags, nflgs, &insn);
2486 emit_insn (&insn);
2487 return;
2488 }
2489 }
2490
2491 if (found_something)
2492 {
2493 if (cpumatch)
2494 if (errmsg)
2495 as_bad (_("%s for instruction '%s'"), errmsg, opname);
2496 else
2497 as_bad (_("inappropriate arguments for opcode '%s'"), opname);
2498 else
2499 as_bad (_("opcode '%s' not supported for target %s"), opname,
2500 selected_cpu.name);
2501 }
2502 else
2503 as_bad (_("unknown opcode '%s'"), opname);
2504 }
2505
2506 /* The public interface to the instruction assembler. */
2507
2508 void
2509 md_assemble (char *str)
2510 {
2511 char *opname;
2512 expressionS tok[MAX_INSN_ARGS];
2513 int ntok, nflg;
2514 size_t opnamelen;
2515 struct arc_flags flags[MAX_INSN_FLGS];
2516
2517 /* Split off the opcode. */
2518 opnamelen = strspn (str, "abcdefghijklmnopqrstuvwxyz_0123468");
2519 opname = xmemdup0 (str, opnamelen);
2520
2521 /* Signalize we are assembling the instructions. */
2522 assembling_insn = TRUE;
2523
2524 /* Tokenize the flags. */
2525 if ((nflg = tokenize_flags (str + opnamelen, flags, MAX_INSN_FLGS)) == -1)
2526 {
2527 as_bad (_("syntax error"));
2528 return;
2529 }
2530
2531 /* Scan up to the end of the mnemonic which must end in space or end
2532 of string. */
2533 str += opnamelen;
2534 for (; *str != '\0'; str++)
2535 if (*str == ' ')
2536 break;
2537
2538 /* Tokenize the rest of the line. */
2539 if ((ntok = tokenize_arguments (str, tok, MAX_INSN_ARGS)) < 0)
2540 {
2541 as_bad (_("syntax error"));
2542 return;
2543 }
2544
2545 /* Finish it off. */
2546 assemble_tokens (opname, tok, ntok, flags, nflg);
2547 assembling_insn = FALSE;
2548 }
2549
2550 /* Callback to insert a register into the hash table. */
2551
2552 static void
2553 declare_register (const char *name, int number)
2554 {
2555 const char *err;
2556 symbolS *regS = symbol_create (name, reg_section,
2557 number, &zero_address_frag);
2558
2559 err = hash_insert (arc_reg_hash, S_GET_NAME (regS), (void *) regS);
2560 if (err)
2561 as_fatal (_("Inserting \"%s\" into register table failed: %s"),
2562 name, err);
2563 }
2564
2565 /* Construct symbols for each of the general registers. */
2566
2567 static void
2568 declare_register_set (void)
2569 {
2570 int i;
2571 for (i = 0; i < 64; ++i)
2572 {
2573 char name[7];
2574
2575 sprintf (name, "r%d", i);
2576 declare_register (name, i);
2577 if ((i & 0x01) == 0)
2578 {
2579 sprintf (name, "r%dr%d", i, i+1);
2580 declare_register (name, i);
2581 }
2582 }
2583 }
2584
2585 /* Construct a symbol for an address type. */
2586
2587 static void
2588 declare_addrtype (const char *name, int number)
2589 {
2590 const char *err;
2591 symbolS *addrtypeS = symbol_create (name, undefined_section,
2592 number, &zero_address_frag);
2593
2594 err = hash_insert (arc_addrtype_hash, S_GET_NAME (addrtypeS),
2595 (void *) addrtypeS);
2596 if (err)
2597 as_fatal (_("Inserting \"%s\" into address type table failed: %s"),
2598 name, err);
2599 }
2600
2601 /* Port-specific assembler initialization. This function is called
2602 once, at assembler startup time. */
2603
2604 void
2605 md_begin (void)
2606 {
2607 const struct arc_opcode *opcode = arc_opcodes;
2608
2609 if (mach_selection_mode == MACH_SELECTION_NONE)
2610 arc_select_cpu (TARGET_WITH_CPU, MACH_SELECTION_FROM_DEFAULT);
2611
2612 /* The endianness can be chosen "at the factory". */
2613 target_big_endian = byte_order == BIG_ENDIAN;
2614
2615 if (!bfd_set_arch_mach (stdoutput, bfd_arch_arc, selected_cpu.mach))
2616 as_warn (_("could not set architecture and machine"));
2617
2618 /* Set elf header flags. */
2619 bfd_set_private_flags (stdoutput, selected_cpu.eflags);
2620
2621 /* Set up a hash table for the instructions. */
2622 arc_opcode_hash = hash_new ();
2623 if (arc_opcode_hash == NULL)
2624 as_fatal (_("Virtual memory exhausted"));
2625
2626 /* Initialize the hash table with the insns. */
2627 do
2628 {
2629 const char *name = opcode->name;
2630
2631 arc_insert_opcode (opcode);
2632
2633 while (++opcode && opcode->name
2634 && (opcode->name == name
2635 || !strcmp (opcode->name, name)))
2636 continue;
2637 }while (opcode->name);
2638
2639 /* Register declaration. */
2640 arc_reg_hash = hash_new ();
2641 if (arc_reg_hash == NULL)
2642 as_fatal (_("Virtual memory exhausted"));
2643
2644 declare_register_set ();
2645 declare_register ("gp", 26);
2646 declare_register ("fp", 27);
2647 declare_register ("sp", 28);
2648 declare_register ("ilink", 29);
2649 declare_register ("ilink1", 29);
2650 declare_register ("ilink2", 30);
2651 declare_register ("blink", 31);
2652
2653 /* XY memory registers. */
2654 declare_register ("x0_u0", 32);
2655 declare_register ("x0_u1", 33);
2656 declare_register ("x1_u0", 34);
2657 declare_register ("x1_u1", 35);
2658 declare_register ("x2_u0", 36);
2659 declare_register ("x2_u1", 37);
2660 declare_register ("x3_u0", 38);
2661 declare_register ("x3_u1", 39);
2662 declare_register ("y0_u0", 40);
2663 declare_register ("y0_u1", 41);
2664 declare_register ("y1_u0", 42);
2665 declare_register ("y1_u1", 43);
2666 declare_register ("y2_u0", 44);
2667 declare_register ("y2_u1", 45);
2668 declare_register ("y3_u0", 46);
2669 declare_register ("y3_u1", 47);
2670 declare_register ("x0_nu", 48);
2671 declare_register ("x1_nu", 49);
2672 declare_register ("x2_nu", 50);
2673 declare_register ("x3_nu", 51);
2674 declare_register ("y0_nu", 52);
2675 declare_register ("y1_nu", 53);
2676 declare_register ("y2_nu", 54);
2677 declare_register ("y3_nu", 55);
2678
2679 declare_register ("mlo", 57);
2680 declare_register ("mmid", 58);
2681 declare_register ("mhi", 59);
2682
2683 declare_register ("acc1", 56);
2684 declare_register ("acc2", 57);
2685
2686 declare_register ("lp_count", 60);
2687 declare_register ("pcl", 63);
2688
2689 /* Initialize the last instructions. */
2690 memset (&arc_last_insns[0], 0, sizeof (arc_last_insns));
2691
2692 /* Aux register declaration. */
2693 arc_aux_hash = hash_new ();
2694 if (arc_aux_hash == NULL)
2695 as_fatal (_("Virtual memory exhausted"));
2696
2697 const struct arc_aux_reg *auxr = &arc_aux_regs[0];
2698 unsigned int i;
2699 for (i = 0; i < arc_num_aux_regs; i++, auxr++)
2700 {
2701 const char *retval;
2702
2703 if (!(auxr->cpu & selected_cpu.flags))
2704 continue;
2705
2706 if ((auxr->subclass != NONE)
2707 && !check_cpu_feature (auxr->subclass))
2708 continue;
2709
2710 retval = hash_insert (arc_aux_hash, auxr->name, (void *) auxr);
2711 if (retval)
2712 as_fatal (_("internal error: can't hash aux register '%s': %s"),
2713 auxr->name, retval);
2714 }
2715
2716 /* Address type declaration. */
2717 arc_addrtype_hash = hash_new ();
2718 if (arc_addrtype_hash == NULL)
2719 as_fatal (_("Virtual memory exhausted"));
2720
2721 declare_addrtype ("bd", ARC_NPS400_ADDRTYPE_BD);
2722 declare_addrtype ("jid", ARC_NPS400_ADDRTYPE_JID);
2723 declare_addrtype ("lbd", ARC_NPS400_ADDRTYPE_LBD);
2724 declare_addrtype ("mbd", ARC_NPS400_ADDRTYPE_MBD);
2725 declare_addrtype ("sd", ARC_NPS400_ADDRTYPE_SD);
2726 declare_addrtype ("sm", ARC_NPS400_ADDRTYPE_SM);
2727 declare_addrtype ("xa", ARC_NPS400_ADDRTYPE_XA);
2728 declare_addrtype ("xd", ARC_NPS400_ADDRTYPE_XD);
2729 declare_addrtype ("cd", ARC_NPS400_ADDRTYPE_CD);
2730 declare_addrtype ("cbd", ARC_NPS400_ADDRTYPE_CBD);
2731 declare_addrtype ("cjid", ARC_NPS400_ADDRTYPE_CJID);
2732 declare_addrtype ("clbd", ARC_NPS400_ADDRTYPE_CLBD);
2733 declare_addrtype ("cm", ARC_NPS400_ADDRTYPE_CM);
2734 declare_addrtype ("csd", ARC_NPS400_ADDRTYPE_CSD);
2735 declare_addrtype ("cxa", ARC_NPS400_ADDRTYPE_CXA);
2736 declare_addrtype ("cxd", ARC_NPS400_ADDRTYPE_CXD);
2737 }
2738
2739 /* Write a value out to the object file, using the appropriate
2740 endianness. */
2741
2742 void
2743 md_number_to_chars (char *buf,
2744 valueT val,
2745 int n)
2746 {
2747 if (target_big_endian)
2748 number_to_chars_bigendian (buf, val, n);
2749 else
2750 number_to_chars_littleendian (buf, val, n);
2751 }
2752
2753 /* Round up a section size to the appropriate boundary. */
2754
2755 valueT
2756 md_section_align (segT segment,
2757 valueT size)
2758 {
2759 int align = bfd_section_alignment (segment);
2760
2761 return ((size + (1 << align) - 1) & (-((valueT) 1 << align)));
2762 }
2763
2764 /* The location from which a PC relative jump should be calculated,
2765 given a PC relative reloc. */
2766
2767 long
2768 md_pcrel_from_section (fixS *fixP,
2769 segT sec)
2770 {
2771 offsetT base = fixP->fx_where + fixP->fx_frag->fr_address;
2772
2773 pr_debug ("pcrel_from_section, fx_offset = %d\n", (int) fixP->fx_offset);
2774
2775 if (fixP->fx_addsy != (symbolS *) NULL
2776 && (!S_IS_DEFINED (fixP->fx_addsy)
2777 || S_GET_SEGMENT (fixP->fx_addsy) != sec))
2778 {
2779 pr_debug ("Unknown pcrel symbol: %s\n", S_GET_NAME (fixP->fx_addsy));
2780
2781 /* The symbol is undefined (or is defined but not in this section).
2782 Let the linker figure it out. */
2783 return 0;
2784 }
2785
2786 if ((int) fixP->fx_r_type < 0)
2787 {
2788 /* These are the "internal" relocations. Align them to
2789 32 bit boundary (PCL), for the moment. */
2790 base &= ~3;
2791 }
2792 else
2793 {
2794 switch (fixP->fx_r_type)
2795 {
2796 case BFD_RELOC_ARC_PC32:
2797 /* The hardware calculates relative to the start of the
2798 insn, but this relocation is relative to location of the
2799 LIMM, compensate. The base always needs to be
2800 subtracted by 4 as we do not support this type of PCrel
2801 relocation for short instructions. */
2802 base -= 4;
2803 /* Fall through. */
2804 case BFD_RELOC_ARC_PLT32:
2805 case BFD_RELOC_ARC_S25H_PCREL_PLT:
2806 case BFD_RELOC_ARC_S21H_PCREL_PLT:
2807 case BFD_RELOC_ARC_S25W_PCREL_PLT:
2808 case BFD_RELOC_ARC_S21W_PCREL_PLT:
2809
2810 case BFD_RELOC_ARC_S21H_PCREL:
2811 case BFD_RELOC_ARC_S25H_PCREL:
2812 case BFD_RELOC_ARC_S13_PCREL:
2813 case BFD_RELOC_ARC_S21W_PCREL:
2814 case BFD_RELOC_ARC_S25W_PCREL:
2815 base &= ~3;
2816 break;
2817 default:
2818 as_bad_where (fixP->fx_file, fixP->fx_line,
2819 _("unhandled reloc %s in md_pcrel_from_section"),
2820 bfd_get_reloc_code_name (fixP->fx_r_type));
2821 break;
2822 }
2823 }
2824
2825 pr_debug ("pcrel from %"BFD_VMA_FMT"x + %lx = %"BFD_VMA_FMT"x, "
2826 "symbol: %s (%"BFD_VMA_FMT"x)\n",
2827 fixP->fx_frag->fr_address, fixP->fx_where, base,
2828 fixP->fx_addsy ? S_GET_NAME (fixP->fx_addsy) : "(null)",
2829 fixP->fx_addsy ? S_GET_VALUE (fixP->fx_addsy) : 0);
2830
2831 return base;
2832 }
2833
2834 /* Given a BFD relocation find the corresponding operand. */
2835
2836 static const struct arc_operand *
2837 find_operand_for_reloc (extended_bfd_reloc_code_real_type reloc)
2838 {
2839 unsigned i;
2840
2841 for (i = 0; i < arc_num_operands; i++)
2842 if (arc_operands[i].default_reloc == reloc)
2843 return &arc_operands[i];
2844 return NULL;
2845 }
2846
2847 /* Insert an operand value into an instruction. */
2848
2849 static unsigned long long
2850 insert_operand (unsigned long long insn,
2851 const struct arc_operand *operand,
2852 long long val,
2853 const char *file,
2854 unsigned line)
2855 {
2856 offsetT min = 0, max = 0;
2857
2858 if (operand->bits != 32
2859 && !(operand->flags & ARC_OPERAND_NCHK)
2860 && !(operand->flags & ARC_OPERAND_FAKE))
2861 {
2862 if (operand->flags & ARC_OPERAND_SIGNED)
2863 {
2864 max = (1 << (operand->bits - 1)) - 1;
2865 min = -(1 << (operand->bits - 1));
2866 }
2867 else
2868 {
2869 max = (1 << operand->bits) - 1;
2870 min = 0;
2871 }
2872
2873 if (val < min || val > max)
2874 as_bad_value_out_of_range (_("operand"),
2875 val, min, max, file, line);
2876 }
2877
2878 pr_debug ("insert field: %ld <= %lld <= %ld in 0x%08llx\n",
2879 min, val, max, insn);
2880
2881 if ((operand->flags & ARC_OPERAND_ALIGNED32)
2882 && (val & 0x03))
2883 as_bad_where (file, line,
2884 _("Unaligned operand. Needs to be 32bit aligned"));
2885
2886 if ((operand->flags & ARC_OPERAND_ALIGNED16)
2887 && (val & 0x01))
2888 as_bad_where (file, line,
2889 _("Unaligned operand. Needs to be 16bit aligned"));
2890
2891 if (operand->insert)
2892 {
2893 const char *errmsg = NULL;
2894
2895 insn = (*operand->insert) (insn, val, &errmsg);
2896 if (errmsg)
2897 as_warn_where (file, line, "%s", errmsg);
2898 }
2899 else
2900 {
2901 if (operand->flags & ARC_OPERAND_TRUNCATE)
2902 {
2903 if (operand->flags & ARC_OPERAND_ALIGNED32)
2904 val >>= 2;
2905 if (operand->flags & ARC_OPERAND_ALIGNED16)
2906 val >>= 1;
2907 }
2908 insn |= ((val & ((1 << operand->bits) - 1)) << operand->shift);
2909 }
2910 return insn;
2911 }
2912
2913 /* Apply a fixup to the object code. At this point all symbol values
2914 should be fully resolved, and we attempt to completely resolve the
2915 reloc. If we can not do that, we determine the correct reloc code
2916 and put it back in the fixup. To indicate that a fixup has been
2917 eliminated, set fixP->fx_done. */
2918
2919 void
2920 md_apply_fix (fixS *fixP,
2921 valueT *valP,
2922 segT seg)
2923 {
2924 char * const fixpos = fixP->fx_frag->fr_literal + fixP->fx_where;
2925 valueT value = *valP;
2926 unsigned insn = 0;
2927 symbolS *fx_addsy, *fx_subsy;
2928 offsetT fx_offset;
2929 segT add_symbol_segment = absolute_section;
2930 segT sub_symbol_segment = absolute_section;
2931 const struct arc_operand *operand = NULL;
2932 extended_bfd_reloc_code_real_type reloc;
2933
2934 pr_debug ("%s:%u: apply_fix: r_type=%d (%s) value=0x%lX offset=0x%lX\n",
2935 fixP->fx_file, fixP->fx_line, fixP->fx_r_type,
2936 ((int) fixP->fx_r_type < 0) ? "Internal":
2937 bfd_get_reloc_code_name (fixP->fx_r_type), value,
2938 fixP->fx_offset);
2939
2940 fx_addsy = fixP->fx_addsy;
2941 fx_subsy = fixP->fx_subsy;
2942 fx_offset = 0;
2943
2944 if (fx_addsy)
2945 {
2946 add_symbol_segment = S_GET_SEGMENT (fx_addsy);
2947 }
2948
2949 if (fx_subsy
2950 && fixP->fx_r_type != BFD_RELOC_ARC_TLS_DTPOFF
2951 && fixP->fx_r_type != BFD_RELOC_ARC_TLS_DTPOFF_S9
2952 && fixP->fx_r_type != BFD_RELOC_ARC_TLS_GD_LD)
2953 {
2954 resolve_symbol_value (fx_subsy);
2955 sub_symbol_segment = S_GET_SEGMENT (fx_subsy);
2956
2957 if (sub_symbol_segment == absolute_section)
2958 {
2959 /* The symbol is really a constant. */
2960 fx_offset -= S_GET_VALUE (fx_subsy);
2961 fx_subsy = NULL;
2962 }
2963 else
2964 {
2965 as_bad_where (fixP->fx_file, fixP->fx_line,
2966 _("can't resolve `%s' {%s section} - `%s' {%s section}"),
2967 fx_addsy ? S_GET_NAME (fx_addsy) : "0",
2968 segment_name (add_symbol_segment),
2969 S_GET_NAME (fx_subsy),
2970 segment_name (sub_symbol_segment));
2971 return;
2972 }
2973 }
2974
2975 if (fx_addsy
2976 && !S_IS_WEAK (fx_addsy))
2977 {
2978 if (add_symbol_segment == seg
2979 && fixP->fx_pcrel)
2980 {
2981 value += S_GET_VALUE (fx_addsy);
2982 value -= md_pcrel_from_section (fixP, seg);
2983 fx_addsy = NULL;
2984 fixP->fx_pcrel = FALSE;
2985 }
2986 else if (add_symbol_segment == absolute_section)
2987 {
2988 value = fixP->fx_offset;
2989 fx_offset += S_GET_VALUE (fixP->fx_addsy);
2990 fx_addsy = NULL;
2991 fixP->fx_pcrel = FALSE;
2992 }
2993 }
2994
2995 if (!fx_addsy)
2996 fixP->fx_done = TRUE;
2997
2998 if (fixP->fx_pcrel)
2999 {
3000 if (fx_addsy
3001 && ((S_IS_DEFINED (fx_addsy)
3002 && S_GET_SEGMENT (fx_addsy) != seg)
3003 || S_IS_WEAK (fx_addsy)))
3004 value += md_pcrel_from_section (fixP, seg);
3005
3006 switch (fixP->fx_r_type)
3007 {
3008 case BFD_RELOC_ARC_32_ME:
3009 /* This is a pc-relative value in a LIMM. Adjust it to the
3010 address of the instruction not to the address of the
3011 LIMM. Note: it is not any longer valid this affirmation as
3012 the linker consider ARC_PC32 a fixup to entire 64 bit
3013 insn. */
3014 fixP->fx_offset += fixP->fx_frag->fr_address;
3015 /* Fall through. */
3016 case BFD_RELOC_32:
3017 fixP->fx_r_type = BFD_RELOC_ARC_PC32;
3018 /* Fall through. */
3019 case BFD_RELOC_ARC_PC32:
3020 /* fixP->fx_offset += fixP->fx_where - fixP->fx_dot_value; */
3021 break;
3022 default:
3023 if ((int) fixP->fx_r_type < 0)
3024 as_bad_where (fixP->fx_file, fixP->fx_line,
3025 _("PC relative relocation not allowed for (internal)"
3026 " type %d"),
3027 fixP->fx_r_type);
3028 break;
3029 }
3030 }
3031
3032 pr_debug ("%s:%u: apply_fix: r_type=%d (%s) value=0x%lX offset=0x%lX\n",
3033 fixP->fx_file, fixP->fx_line, fixP->fx_r_type,
3034 ((int) fixP->fx_r_type < 0) ? "Internal":
3035 bfd_get_reloc_code_name (fixP->fx_r_type), value,
3036 fixP->fx_offset);
3037
3038
3039 /* Now check for TLS relocations. */
3040 reloc = fixP->fx_r_type;
3041 switch (reloc)
3042 {
3043 case BFD_RELOC_ARC_TLS_DTPOFF:
3044 case BFD_RELOC_ARC_TLS_LE_32:
3045 if (fixP->fx_done)
3046 break;
3047 /* Fall through. */
3048 case BFD_RELOC_ARC_TLS_GD_GOT:
3049 case BFD_RELOC_ARC_TLS_IE_GOT:
3050 S_SET_THREAD_LOCAL (fixP->fx_addsy);
3051 break;
3052
3053 case BFD_RELOC_ARC_TLS_GD_LD:
3054 gas_assert (!fixP->fx_offset);
3055 if (fixP->fx_subsy)
3056 fixP->fx_offset
3057 = (S_GET_VALUE (fixP->fx_subsy)
3058 - fixP->fx_frag->fr_address- fixP->fx_where);
3059 fixP->fx_subsy = NULL;
3060 /* Fall through. */
3061 case BFD_RELOC_ARC_TLS_GD_CALL:
3062 /* These two relocs are there just to allow ld to change the tls
3063 model for this symbol, by patching the code. The offset -
3064 and scale, if any - will be installed by the linker. */
3065 S_SET_THREAD_LOCAL (fixP->fx_addsy);
3066 break;
3067
3068 case BFD_RELOC_ARC_TLS_LE_S9:
3069 case BFD_RELOC_ARC_TLS_DTPOFF_S9:
3070 as_bad (_("TLS_*_S9 relocs are not supported yet"));
3071 break;
3072
3073 default:
3074 break;
3075 }
3076
3077 if (!fixP->fx_done)
3078 {
3079 return;
3080 }
3081
3082 /* Adjust the value if we have a constant. */
3083 value += fx_offset;
3084
3085 /* For hosts with longs bigger than 32-bits make sure that the top
3086 bits of a 32-bit negative value read in by the parser are set,
3087 so that the correct comparisons are made. */
3088 if (value & 0x80000000)
3089 value |= (-1UL << 31);
3090
3091 reloc = fixP->fx_r_type;
3092 switch (reloc)
3093 {
3094 case BFD_RELOC_8:
3095 case BFD_RELOC_16:
3096 case BFD_RELOC_24:
3097 case BFD_RELOC_32:
3098 case BFD_RELOC_64:
3099 case BFD_RELOC_ARC_32_PCREL:
3100 md_number_to_chars (fixpos, value, fixP->fx_size);
3101 return;
3102
3103 case BFD_RELOC_ARC_GOTPC32:
3104 /* I cannot fix an GOTPC relocation because I need to relax it
3105 from ld rx,[pcl,@sym@gotpc] to add rx,pcl,@sym@gotpc. */
3106 as_bad (_("Unsupported operation on reloc"));
3107 return;
3108
3109 case BFD_RELOC_ARC_TLS_DTPOFF:
3110 case BFD_RELOC_ARC_TLS_LE_32:
3111 gas_assert (!fixP->fx_addsy);
3112 gas_assert (!fixP->fx_subsy);
3113 /* Fall through. */
3114
3115 case BFD_RELOC_ARC_GOTOFF:
3116 case BFD_RELOC_ARC_32_ME:
3117 case BFD_RELOC_ARC_PC32:
3118 md_number_to_chars_midend (fixpos, value, fixP->fx_size);
3119 return;
3120
3121 case BFD_RELOC_ARC_PLT32:
3122 md_number_to_chars_midend (fixpos, value, fixP->fx_size);
3123 return;
3124
3125 case BFD_RELOC_ARC_S25H_PCREL_PLT:
3126 reloc = BFD_RELOC_ARC_S25W_PCREL;
3127 goto solve_plt;
3128
3129 case BFD_RELOC_ARC_S21H_PCREL_PLT:
3130 reloc = BFD_RELOC_ARC_S21H_PCREL;
3131 goto solve_plt;
3132
3133 case BFD_RELOC_ARC_S25W_PCREL_PLT:
3134 reloc = BFD_RELOC_ARC_S25W_PCREL;
3135 goto solve_plt;
3136
3137 case BFD_RELOC_ARC_S21W_PCREL_PLT:
3138 reloc = BFD_RELOC_ARC_S21W_PCREL;
3139 /* Fall through. */
3140
3141 case BFD_RELOC_ARC_S25W_PCREL:
3142 case BFD_RELOC_ARC_S21W_PCREL:
3143 case BFD_RELOC_ARC_S21H_PCREL:
3144 case BFD_RELOC_ARC_S25H_PCREL:
3145 case BFD_RELOC_ARC_S13_PCREL:
3146 solve_plt:
3147 operand = find_operand_for_reloc (reloc);
3148 gas_assert (operand);
3149 break;
3150
3151 default:
3152 {
3153 if ((int) fixP->fx_r_type >= 0)
3154 as_fatal (_("unhandled relocation type %s"),
3155 bfd_get_reloc_code_name (fixP->fx_r_type));
3156
3157 /* The rest of these fixups needs to be completely resolved as
3158 constants. */
3159 if (fixP->fx_addsy != 0
3160 && S_GET_SEGMENT (fixP->fx_addsy) != absolute_section)
3161 as_bad_where (fixP->fx_file, fixP->fx_line,
3162 _("non-absolute expression in constant field"));
3163
3164 gas_assert (-(int) fixP->fx_r_type < (int) arc_num_operands);
3165 operand = &arc_operands[-(int) fixP->fx_r_type];
3166 break;
3167 }
3168 }
3169
3170 if (target_big_endian)
3171 {
3172 switch (fixP->fx_size)
3173 {
3174 case 4:
3175 insn = bfd_getb32 (fixpos);
3176 break;
3177 case 2:
3178 insn = bfd_getb16 (fixpos);
3179 break;
3180 default:
3181 as_bad_where (fixP->fx_file, fixP->fx_line,
3182 _("unknown fixup size"));
3183 }
3184 }
3185 else
3186 {
3187 insn = 0;
3188 switch (fixP->fx_size)
3189 {
3190 case 4:
3191 insn = bfd_getl16 (fixpos) << 16 | bfd_getl16 (fixpos + 2);
3192 break;
3193 case 2:
3194 insn = bfd_getl16 (fixpos);
3195 break;
3196 default:
3197 as_bad_where (fixP->fx_file, fixP->fx_line,
3198 _("unknown fixup size"));
3199 }
3200 }
3201
3202 insn = insert_operand (insn, operand, (offsetT) value,
3203 fixP->fx_file, fixP->fx_line);
3204
3205 md_number_to_chars_midend (fixpos, insn, fixP->fx_size);
3206 }
3207
3208 /* Prepare machine-dependent frags for relaxation.
3209
3210 Called just before relaxation starts. Any symbol that is now undefined
3211 will not become defined.
3212
3213 Return the correct fr_subtype in the frag.
3214
3215 Return the initial "guess for fr_var" to caller. The guess for fr_var
3216 is *actually* the growth beyond fr_fix. Whatever we do to grow fr_fix
3217 or fr_var contributes to our returned value.
3218
3219 Although it may not be explicit in the frag, pretend
3220 fr_var starts with a value. */
3221
3222 int
3223 md_estimate_size_before_relax (fragS *fragP,
3224 segT segment)
3225 {
3226 int growth;
3227
3228 /* If the symbol is not located within the same section AND it's not
3229 an absolute section, use the maximum. OR if the symbol is a
3230 constant AND the insn is by nature not pc-rel, use the maximum.
3231 OR if the symbol is being equated against another symbol, use the
3232 maximum. OR if the symbol is weak use the maximum. */
3233 if ((S_GET_SEGMENT (fragP->fr_symbol) != segment
3234 && S_GET_SEGMENT (fragP->fr_symbol) != absolute_section)
3235 || (symbol_constant_p (fragP->fr_symbol)
3236 && !fragP->tc_frag_data.pcrel)
3237 || symbol_equated_p (fragP->fr_symbol)
3238 || S_IS_WEAK (fragP->fr_symbol))
3239 {
3240 while (md_relax_table[fragP->fr_subtype].rlx_more != ARC_RLX_NONE)
3241 ++fragP->fr_subtype;
3242 }
3243
3244 growth = md_relax_table[fragP->fr_subtype].rlx_length;
3245 fragP->fr_var = growth;
3246
3247 pr_debug ("%s:%d: md_estimate_size_before_relax: %d\n",
3248 fragP->fr_file, fragP->fr_line, growth);
3249
3250 return growth;
3251 }
3252
3253 /* Translate internal representation of relocation info to BFD target
3254 format. */
3255
3256 arelent *
3257 tc_gen_reloc (asection *section ATTRIBUTE_UNUSED,
3258 fixS *fixP)
3259 {
3260 arelent *reloc;
3261 bfd_reloc_code_real_type code;
3262
3263 reloc = XNEW (arelent);
3264 reloc->sym_ptr_ptr = XNEW (asymbol *);
3265 *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixP->fx_addsy);
3266 reloc->address = fixP->fx_frag->fr_address + fixP->fx_where;
3267
3268 /* Make sure none of our internal relocations make it this far.
3269 They'd better have been fully resolved by this point. */
3270 gas_assert ((int) fixP->fx_r_type > 0);
3271
3272 code = fixP->fx_r_type;
3273
3274 /* if we have something like add gp, pcl,
3275 _GLOBAL_OFFSET_TABLE_@gotpc. */
3276 if (code == BFD_RELOC_ARC_GOTPC32
3277 && GOT_symbol
3278 && fixP->fx_addsy == GOT_symbol)
3279 code = BFD_RELOC_ARC_GOTPC;
3280
3281 reloc->howto = bfd_reloc_type_lookup (stdoutput, code);
3282 if (reloc->howto == NULL)
3283 {
3284 as_bad_where (fixP->fx_file, fixP->fx_line,
3285 _("cannot represent `%s' relocation in object file"),
3286 bfd_get_reloc_code_name (code));
3287 return NULL;
3288 }
3289
3290 if (!fixP->fx_pcrel != !reloc->howto->pc_relative)
3291 as_fatal (_("internal error? cannot generate `%s' relocation"),
3292 bfd_get_reloc_code_name (code));
3293
3294 gas_assert (!fixP->fx_pcrel == !reloc->howto->pc_relative);
3295
3296 reloc->addend = fixP->fx_offset;
3297
3298 return reloc;
3299 }
3300
3301 /* Perform post-processing of machine-dependent frags after relaxation.
3302 Called after relaxation is finished.
3303 In: Address of frag.
3304 fr_type == rs_machine_dependent.
3305 fr_subtype is what the address relaxed to.
3306
3307 Out: Any fixS:s and constants are set up. */
3308
3309 void
3310 md_convert_frag (bfd *abfd ATTRIBUTE_UNUSED,
3311 segT segment ATTRIBUTE_UNUSED,
3312 fragS *fragP)
3313 {
3314 const relax_typeS *table_entry;
3315 char *dest;
3316 const struct arc_opcode *opcode;
3317 struct arc_insn insn;
3318 int size, fix;
3319 struct arc_relax_type *relax_arg = &fragP->tc_frag_data;
3320
3321 fix = fragP->fr_fix;
3322 dest = fragP->fr_literal + fix;
3323 table_entry = TC_GENERIC_RELAX_TABLE + fragP->fr_subtype;
3324
3325 pr_debug ("%s:%d: md_convert_frag, subtype: %d, fix: %d, "
3326 "var: %"BFD_VMA_FMT"d\n",
3327 fragP->fr_file, fragP->fr_line,
3328 fragP->fr_subtype, fix, fragP->fr_var);
3329
3330 if (fragP->fr_subtype <= 0
3331 && fragP->fr_subtype >= arc_num_relax_opcodes)
3332 as_fatal (_("no relaxation found for this instruction."));
3333
3334 opcode = &arc_relax_opcodes[fragP->fr_subtype];
3335
3336 assemble_insn (opcode, relax_arg->tok, relax_arg->ntok, relax_arg->pflags,
3337 relax_arg->nflg, &insn);
3338
3339 apply_fixups (&insn, fragP, fix);
3340
3341 size = insn.len + (insn.has_limm ? 4 : 0);
3342 gas_assert (table_entry->rlx_length == size);
3343 emit_insn0 (&insn, dest, TRUE);
3344
3345 fragP->fr_fix += table_entry->rlx_length;
3346 fragP->fr_var = 0;
3347 }
3348
3349 /* We have no need to default values of symbols. We could catch
3350 register names here, but that is handled by inserting them all in
3351 the symbol table to begin with. */
3352
3353 symbolS *
3354 md_undefined_symbol (char *name)
3355 {
3356 /* The arc abi demands that a GOT[0] should be referencible as
3357 [pc+_DYNAMIC@gotpc]. Hence we convert a _DYNAMIC@gotpc to a
3358 GOTPC reference to _GLOBAL_OFFSET_TABLE_. */
3359 if (((*name == '_')
3360 && (*(name+1) == 'G')
3361 && (strcmp (name, GLOBAL_OFFSET_TABLE_NAME) == 0)))
3362 {
3363 if (!GOT_symbol)
3364 {
3365 if (symbol_find (name))
3366 as_bad ("GOT already in symbol table");
3367
3368 GOT_symbol = symbol_new (GLOBAL_OFFSET_TABLE_NAME, undefined_section,
3369 (valueT) 0, &zero_address_frag);
3370 };
3371 return GOT_symbol;
3372 }
3373 return NULL;
3374 }
3375
3376 /* Turn a string in input_line_pointer into a floating point constant
3377 of type type, and store the appropriate bytes in *litP. The number
3378 of LITTLENUMS emitted is stored in *sizeP. An error message is
3379 returned, or NULL on OK. */
3380
3381 const char *
3382 md_atof (int type, char *litP, int *sizeP)
3383 {
3384 return ieee_md_atof (type, litP, sizeP, target_big_endian);
3385 }
3386
3387 /* Called for any expression that can not be recognized. When the
3388 function is called, `input_line_pointer' will point to the start of
3389 the expression. We use it when we have complex operations like
3390 @label1 - @label2. */
3391
3392 void
3393 md_operand (expressionS *expressionP)
3394 {
3395 char *p = input_line_pointer;
3396 if (*p == '@')
3397 {
3398 input_line_pointer++;
3399 expressionP->X_op = O_symbol;
3400 expressionP->X_md = O_absent;
3401 expression (expressionP);
3402 }
3403 }
3404
3405 /* This function is called from the function 'expression', it attempts
3406 to parse special names (in our case register names). It fills in
3407 the expression with the identified register. It returns TRUE if
3408 it is a register and FALSE otherwise. */
3409
3410 bfd_boolean
3411 arc_parse_name (const char *name,
3412 struct expressionS *e)
3413 {
3414 struct symbol *sym;
3415
3416 if (!assembling_insn)
3417 return FALSE;
3418
3419 if (e->X_op == O_symbol
3420 && e->X_md == O_absent)
3421 return FALSE;
3422
3423 sym = hash_find (arc_reg_hash, name);
3424 if (sym)
3425 {
3426 e->X_op = O_register;
3427 e->X_add_number = S_GET_VALUE (sym);
3428 return TRUE;
3429 }
3430
3431 sym = hash_find (arc_addrtype_hash, name);
3432 if (sym)
3433 {
3434 e->X_op = O_addrtype;
3435 e->X_add_number = S_GET_VALUE (sym);
3436 return TRUE;
3437 }
3438
3439 return FALSE;
3440 }
3441
3442 /* md_parse_option
3443 Invocation line includes a switch not recognized by the base assembler.
3444 See if it's a processor-specific option.
3445
3446 New options (supported) are:
3447
3448 -mcpu=<cpu name> Assemble for selected processor
3449 -EB/-mbig-endian Big-endian
3450 -EL/-mlittle-endian Little-endian
3451 -mrelax Enable relaxation
3452
3453 The following CPU names are recognized:
3454 arc600, arc700, arcem, archs, nps400. */
3455
3456 int
3457 md_parse_option (int c, const char *arg ATTRIBUTE_UNUSED)
3458 {
3459 switch (c)
3460 {
3461 case OPTION_ARC600:
3462 case OPTION_ARC601:
3463 return md_parse_option (OPTION_MCPU, "arc600");
3464
3465 case OPTION_ARC700:
3466 return md_parse_option (OPTION_MCPU, "arc700");
3467
3468 case OPTION_ARCEM:
3469 return md_parse_option (OPTION_MCPU, "arcem");
3470
3471 case OPTION_ARCHS:
3472 return md_parse_option (OPTION_MCPU, "archs");
3473
3474 case OPTION_MCPU:
3475 {
3476 arc_select_cpu (arg, MACH_SELECTION_FROM_COMMAND_LINE);
3477 break;
3478 }
3479
3480 case OPTION_EB:
3481 arc_target_format = "elf32-bigarc";
3482 byte_order = BIG_ENDIAN;
3483 break;
3484
3485 case OPTION_EL:
3486 arc_target_format = "elf32-littlearc";
3487 byte_order = LITTLE_ENDIAN;
3488 break;
3489
3490 case OPTION_CD:
3491 selected_cpu.features |= CD;
3492 cl_features |= CD;
3493 arc_check_feature ();
3494 break;
3495
3496 case OPTION_RELAX:
3497 relaxation_state = 1;
3498 break;
3499
3500 case OPTION_NPS400:
3501 selected_cpu.features |= NPS400;
3502 cl_features |= NPS400;
3503 arc_check_feature ();
3504 break;
3505
3506 case OPTION_SPFP:
3507 selected_cpu.features |= SPX;
3508 cl_features |= SPX;
3509 arc_check_feature ();
3510 break;
3511
3512 case OPTION_DPFP:
3513 selected_cpu.features |= DPX;
3514 cl_features |= DPX;
3515 arc_check_feature ();
3516 break;
3517
3518 case OPTION_FPUDA:
3519 selected_cpu.features |= DPA;
3520 cl_features |= DPA;
3521 arc_check_feature ();
3522 break;
3523
3524 /* Dummy options are accepted but have no effect. */
3525 case OPTION_USER_MODE:
3526 case OPTION_LD_EXT_MASK:
3527 case OPTION_SWAP:
3528 case OPTION_NORM:
3529 case OPTION_BARREL_SHIFT:
3530 case OPTION_MIN_MAX:
3531 case OPTION_NO_MPY:
3532 case OPTION_EA:
3533 case OPTION_MUL64:
3534 case OPTION_SIMD:
3535 case OPTION_XMAC_D16:
3536 case OPTION_XMAC_24:
3537 case OPTION_DSP_PACKA:
3538 case OPTION_CRC:
3539 case OPTION_DVBF:
3540 case OPTION_TELEPHONY:
3541 case OPTION_XYMEMORY:
3542 case OPTION_LOCK:
3543 case OPTION_SWAPE:
3544 case OPTION_RTSC:
3545 break;
3546
3547 default:
3548 return 0;
3549 }
3550
3551 return 1;
3552 }
3553
3554 /* Display the list of cpu names for use in the help text. */
3555
3556 static void
3557 arc_show_cpu_list (FILE *stream)
3558 {
3559 int i, offset;
3560 static const char *space_buf = " ";
3561
3562 fprintf (stream, "%s", space_buf);
3563 offset = strlen (space_buf);
3564 for (i = 0; cpu_types[i].name != NULL; ++i)
3565 {
3566 bfd_boolean last = (cpu_types[i + 1].name == NULL);
3567
3568 /* If displaying the new cpu name string, and the ', ' (for all
3569 but the last one) will take us past a target width of 80
3570 characters, then it's time for a new line. */
3571 if (offset + strlen (cpu_types[i].name) + (last ? 0 : 2) > 80)
3572 {
3573 fprintf (stream, "\n%s", space_buf);
3574 offset = strlen (space_buf);
3575 }
3576
3577 fprintf (stream, "%s%s", cpu_types[i].name, (last ? "\n" : ", "));
3578 offset += strlen (cpu_types [i].name) + (last ? 0 : 2);
3579 }
3580 }
3581
3582 void
3583 md_show_usage (FILE *stream)
3584 {
3585 fprintf (stream, _("ARC-specific assembler options:\n"));
3586
3587 fprintf (stream, " -mcpu=<cpu name>\t (default: %s), assemble for"
3588 " CPU <cpu name>, one of:\n", TARGET_WITH_CPU);
3589 arc_show_cpu_list (stream);
3590 fprintf (stream, "\n");
3591 fprintf (stream, " -mA6/-mARC600/-mARC601 same as -mcpu=arc600\n");
3592 fprintf (stream, " -mA7/-mARC700\t\t same as -mcpu=arc700\n");
3593 fprintf (stream, " -mEM\t\t\t same as -mcpu=arcem\n");
3594 fprintf (stream, " -mHS\t\t\t same as -mcpu=archs\n");
3595
3596 fprintf (stream, " -mnps400\t\t enable NPS-400 extended instructions\n");
3597 fprintf (stream, " -mspfp\t\t enable single-precision floating point"
3598 " instructions\n");
3599 fprintf (stream, " -mdpfp\t\t enable double-precision floating point"
3600 " instructions\n");
3601 fprintf (stream, " -mfpuda\t\t enable double-precision assist floating "
3602 "point\n\t\t\t instructions for ARC EM\n");
3603
3604 fprintf (stream,
3605 " -mcode-density\t enable code density option for ARC EM\n");
3606
3607 fprintf (stream, _("\
3608 -EB assemble code for a big-endian cpu\n"));
3609 fprintf (stream, _("\
3610 -EL assemble code for a little-endian cpu\n"));
3611 fprintf (stream, _("\
3612 -mrelax enable relaxation\n"));
3613
3614 fprintf (stream, _("The following ARC-specific assembler options are "
3615 "deprecated and are accepted\nfor compatibility only:\n"));
3616
3617 fprintf (stream, _(" -mEA\n"
3618 " -mbarrel-shifter\n"
3619 " -mbarrel_shifter\n"
3620 " -mcrc\n"
3621 " -mdsp-packa\n"
3622 " -mdsp_packa\n"
3623 " -mdvbf\n"
3624 " -mld-extension-reg-mask\n"
3625 " -mlock\n"
3626 " -mmac-24\n"
3627 " -mmac-d16\n"
3628 " -mmac_24\n"
3629 " -mmac_d16\n"
3630 " -mmin-max\n"
3631 " -mmin_max\n"
3632 " -mmul64\n"
3633 " -mno-mpy\n"
3634 " -mnorm\n"
3635 " -mrtsc\n"
3636 " -msimd\n"
3637 " -mswap\n"
3638 " -mswape\n"
3639 " -mtelephony\n"
3640 " -muser-mode-only\n"
3641 " -mxy\n"));
3642 }
3643
3644 /* Find the proper relocation for the given opcode. */
3645
3646 static extended_bfd_reloc_code_real_type
3647 find_reloc (const char *name,
3648 const char *opcodename,
3649 const struct arc_flags *pflags,
3650 int nflg,
3651 extended_bfd_reloc_code_real_type reloc)
3652 {
3653 unsigned int i;
3654 int j;
3655 bfd_boolean found_flag, tmp;
3656 extended_bfd_reloc_code_real_type ret = BFD_RELOC_UNUSED;
3657
3658 for (i = 0; i < arc_num_equiv_tab; i++)
3659 {
3660 const struct arc_reloc_equiv_tab *r = &arc_reloc_equiv[i];
3661
3662 /* Find the entry. */
3663 if (strcmp (name, r->name))
3664 continue;
3665 if (r->mnemonic && (strcmp (r->mnemonic, opcodename)))
3666 continue;
3667 if (r->flags[0])
3668 {
3669 if (!nflg)
3670 continue;
3671 found_flag = FALSE;
3672 unsigned * psflg = (unsigned *)r->flags;
3673 do
3674 {
3675 tmp = FALSE;
3676 for (j = 0; j < nflg; j++)
3677 if (!strcmp (pflags[j].name,
3678 arc_flag_operands[*psflg].name))
3679 {
3680 tmp = TRUE;
3681 break;
3682 }
3683 if (!tmp)
3684 {
3685 found_flag = FALSE;
3686 break;
3687 }
3688 else
3689 {
3690 found_flag = TRUE;
3691 }
3692 ++ psflg;
3693 } while (*psflg);
3694
3695 if (!found_flag)
3696 continue;
3697 }
3698
3699 if (reloc != r->oldreloc)
3700 continue;
3701 /* Found it. */
3702 ret = r->newreloc;
3703 break;
3704 }
3705
3706 if (ret == BFD_RELOC_UNUSED)
3707 as_bad (_("Unable to find %s relocation for instruction %s"),
3708 name, opcodename);
3709 return ret;
3710 }
3711
3712 /* All the symbol types that are allowed to be used for
3713 relaxation. */
3714
3715 static bfd_boolean
3716 may_relax_expr (expressionS tok)
3717 {
3718 /* Check if we have unrelaxable relocs. */
3719 switch (tok.X_md)
3720 {
3721 default:
3722 break;
3723 case O_plt:
3724 return FALSE;
3725 }
3726
3727 switch (tok.X_op)
3728 {
3729 case O_symbol:
3730 case O_multiply:
3731 case O_divide:
3732 case O_modulus:
3733 case O_add:
3734 case O_subtract:
3735 break;
3736
3737 default:
3738 return FALSE;
3739 }
3740 return TRUE;
3741 }
3742
3743 /* Checks if flags are in line with relaxable insn. */
3744
3745 static bfd_boolean
3746 relaxable_flag (const struct arc_relaxable_ins *ins,
3747 const struct arc_flags *pflags,
3748 int nflgs)
3749 {
3750 unsigned flag_class,
3751 flag,
3752 flag_class_idx = 0,
3753 flag_idx = 0;
3754
3755 const struct arc_flag_operand *flag_opand;
3756 int i, counttrue = 0;
3757
3758 /* Iterate through flags classes. */
3759 while ((flag_class = ins->flag_classes[flag_class_idx]) != 0)
3760 {
3761 /* Iterate through flags in flag class. */
3762 while ((flag = arc_flag_classes[flag_class].flags[flag_idx])
3763 != 0)
3764 {
3765 flag_opand = &arc_flag_operands[flag];
3766 /* Iterate through flags in ins to compare. */
3767 for (i = 0; i < nflgs; ++i)
3768 {
3769 if (strcmp (flag_opand->name, pflags[i].name) == 0)
3770 ++counttrue;
3771 }
3772
3773 ++flag_idx;
3774 }
3775
3776 ++flag_class_idx;
3777 flag_idx = 0;
3778 }
3779
3780 /* If counttrue == nflgs, then all flags have been found. */
3781 return (counttrue == nflgs ? TRUE : FALSE);
3782 }
3783
3784 /* Checks if operands are in line with relaxable insn. */
3785
3786 static bfd_boolean
3787 relaxable_operand (const struct arc_relaxable_ins *ins,
3788 const expressionS *tok,
3789 int ntok)
3790 {
3791 const enum rlx_operand_type *operand = &ins->operands[0];
3792 int i = 0;
3793
3794 while (*operand != EMPTY)
3795 {
3796 const expressionS *epr = &tok[i];
3797
3798 if (i != 0 && i >= ntok)
3799 return FALSE;
3800
3801 switch (*operand)
3802 {
3803 case IMMEDIATE:
3804 if (!(epr->X_op == O_multiply
3805 || epr->X_op == O_divide
3806 || epr->X_op == O_modulus
3807 || epr->X_op == O_add
3808 || epr->X_op == O_subtract
3809 || epr->X_op == O_symbol))
3810 return FALSE;
3811 break;
3812
3813 case REGISTER_DUP:
3814 if ((i <= 0)
3815 || (epr->X_add_number != tok[i - 1].X_add_number))
3816 return FALSE;
3817 /* Fall through. */
3818 case REGISTER:
3819 if (epr->X_op != O_register)
3820 return FALSE;
3821 break;
3822
3823 case REGISTER_S:
3824 if (epr->X_op != O_register)
3825 return FALSE;
3826
3827 switch (epr->X_add_number)
3828 {
3829 case 0: case 1: case 2: case 3:
3830 case 12: case 13: case 14: case 15:
3831 break;
3832 default:
3833 return FALSE;
3834 }
3835 break;
3836
3837 case REGISTER_NO_GP:
3838 if ((epr->X_op != O_register)
3839 || (epr->X_add_number == 26)) /* 26 is the gp register. */
3840 return FALSE;
3841 break;
3842
3843 case BRACKET:
3844 if (epr->X_op != O_bracket)
3845 return FALSE;
3846 break;
3847
3848 default:
3849 /* Don't understand, bail out. */
3850 return FALSE;
3851 break;
3852 }
3853
3854 ++i;
3855 operand = &ins->operands[i];
3856 }
3857
3858 return (i == ntok ? TRUE : FALSE);
3859 }
3860
3861 /* Return TRUE if this OPDCODE is a candidate for relaxation. */
3862
3863 static bfd_boolean
3864 relax_insn_p (const struct arc_opcode *opcode,
3865 const expressionS *tok,
3866 int ntok,
3867 const struct arc_flags *pflags,
3868 int nflg)
3869 {
3870 unsigned i;
3871 bfd_boolean rv = FALSE;
3872
3873 /* Check the relaxation table. */
3874 for (i = 0; i < arc_num_relaxable_ins && relaxation_state; ++i)
3875 {
3876 const struct arc_relaxable_ins *arc_rlx_ins = &arc_relaxable_insns[i];
3877
3878 if ((strcmp (opcode->name, arc_rlx_ins->mnemonic_r) == 0)
3879 && may_relax_expr (tok[arc_rlx_ins->opcheckidx])
3880 && relaxable_operand (arc_rlx_ins, tok, ntok)
3881 && relaxable_flag (arc_rlx_ins, pflags, nflg))
3882 {
3883 rv = TRUE;
3884 frag_now->fr_subtype = arc_relaxable_insns[i].subtype;
3885 memcpy (&frag_now->tc_frag_data.tok, tok,
3886 sizeof (expressionS) * ntok);
3887 memcpy (&frag_now->tc_frag_data.pflags, pflags,
3888 sizeof (struct arc_flags) * nflg);
3889 frag_now->tc_frag_data.nflg = nflg;
3890 frag_now->tc_frag_data.ntok = ntok;
3891 break;
3892 }
3893 }
3894
3895 return rv;
3896 }
3897
3898 /* Turn an opcode description and a set of arguments into
3899 an instruction and a fixup. */
3900
3901 static void
3902 assemble_insn (const struct arc_opcode *opcode,
3903 const expressionS *tok,
3904 int ntok,
3905 const struct arc_flags *pflags,
3906 int nflg,
3907 struct arc_insn *insn)
3908 {
3909 const expressionS *reloc_exp = NULL;
3910 unsigned long long image;
3911 const unsigned char *argidx;
3912 int i;
3913 int tokidx = 0;
3914 unsigned char pcrel = 0;
3915 bfd_boolean needGOTSymbol;
3916 bfd_boolean has_delay_slot = FALSE;
3917 extended_bfd_reloc_code_real_type reloc = BFD_RELOC_UNUSED;
3918
3919 memset (insn, 0, sizeof (*insn));
3920 image = opcode->opcode;
3921
3922 pr_debug ("%s:%d: assemble_insn: %s using opcode %llx\n",
3923 frag_now->fr_file, frag_now->fr_line, opcode->name,
3924 opcode->opcode);
3925
3926 /* Handle operands. */
3927 for (argidx = opcode->operands; *argidx; ++argidx)
3928 {
3929 const struct arc_operand *operand = &arc_operands[*argidx];
3930 const expressionS *t = (const expressionS *) 0;
3931
3932 if (ARC_OPERAND_IS_FAKE (operand))
3933 continue;
3934
3935 if (operand->flags & ARC_OPERAND_DUPLICATE)
3936 {
3937 /* Duplicate operand, already inserted. */
3938 tokidx ++;
3939 continue;
3940 }
3941
3942 if (tokidx >= ntok)
3943 {
3944 abort ();
3945 }
3946 else
3947 t = &tok[tokidx++];
3948
3949 /* Regardless if we have a reloc or not mark the instruction
3950 limm if it is the case. */
3951 if (operand->flags & ARC_OPERAND_LIMM)
3952 insn->has_limm = TRUE;
3953
3954 switch (t->X_op)
3955 {
3956 case O_register:
3957 image = insert_operand (image, operand, regno (t->X_add_number),
3958 NULL, 0);
3959 break;
3960
3961 case O_constant:
3962 image = insert_operand (image, operand, t->X_add_number, NULL, 0);
3963 reloc_exp = t;
3964 if (operand->flags & ARC_OPERAND_LIMM)
3965 insn->limm = t->X_add_number;
3966 break;
3967
3968 case O_bracket:
3969 case O_colon:
3970 case O_addrtype:
3971 /* Ignore brackets, colons, and address types. */
3972 break;
3973
3974 case O_absent:
3975 gas_assert (operand->flags & ARC_OPERAND_IGNORE);
3976 break;
3977
3978 case O_subtract:
3979 /* Maybe register range. */
3980 if ((t->X_add_number == 0)
3981 && contains_register (t->X_add_symbol)
3982 && contains_register (t->X_op_symbol))
3983 {
3984 int regs;
3985
3986 regs = get_register (t->X_add_symbol);
3987 regs <<= 16;
3988 regs |= get_register (t->X_op_symbol);
3989 image = insert_operand (image, operand, regs, NULL, 0);
3990 break;
3991 }
3992 /* Fall through. */
3993
3994 default:
3995 /* This operand needs a relocation. */
3996 needGOTSymbol = FALSE;
3997
3998 switch (t->X_md)
3999 {
4000 case O_plt:
4001 if (opcode->insn_class == JUMP)
4002 as_bad (_("Unable to use @plt relocation for insn %s"),
4003 opcode->name);
4004 needGOTSymbol = TRUE;
4005 reloc = find_reloc ("plt", opcode->name,
4006 pflags, nflg,
4007 operand->default_reloc);
4008 break;
4009
4010 case O_gotoff:
4011 case O_gotpc:
4012 needGOTSymbol = TRUE;
4013 reloc = ARC_RELOC_TABLE (t->X_md)->reloc;
4014 break;
4015 case O_pcl:
4016 if (operand->flags & ARC_OPERAND_LIMM)
4017 {
4018 reloc = ARC_RELOC_TABLE (t->X_md)->reloc;
4019 if (arc_opcode_len (opcode) == 2
4020 || opcode->insn_class == JUMP)
4021 as_bad (_("Unable to use @pcl relocation for insn %s"),
4022 opcode->name);
4023 }
4024 else
4025 {
4026 /* This is a relaxed operand which initially was
4027 limm, choose whatever we have defined in the
4028 opcode as reloc. */
4029 reloc = operand->default_reloc;
4030 }
4031 break;
4032 case O_sda:
4033 reloc = find_reloc ("sda", opcode->name,
4034 pflags, nflg,
4035 operand->default_reloc);
4036 break;
4037 case O_tlsgd:
4038 case O_tlsie:
4039 needGOTSymbol = TRUE;
4040 /* Fall-through. */
4041
4042 case O_tpoff:
4043 case O_dtpoff:
4044 reloc = ARC_RELOC_TABLE (t->X_md)->reloc;
4045 break;
4046
4047 case O_tpoff9: /*FIXME! Check for the conditionality of
4048 the insn. */
4049 case O_dtpoff9: /*FIXME! Check for the conditionality of
4050 the insn. */
4051 as_bad (_("TLS_*_S9 relocs are not supported yet"));
4052 break;
4053
4054 default:
4055 /* Just consider the default relocation. */
4056 reloc = operand->default_reloc;
4057 break;
4058 }
4059
4060 if (needGOTSymbol && (GOT_symbol == NULL))
4061 GOT_symbol = symbol_find_or_make (GLOBAL_OFFSET_TABLE_NAME);
4062
4063 reloc_exp = t;
4064
4065 #if 0
4066 if (reloc > 0)
4067 {
4068 /* sanity checks. */
4069 reloc_howto_type *reloc_howto
4070 = bfd_reloc_type_lookup (stdoutput,
4071 (bfd_reloc_code_real_type) reloc);
4072 unsigned reloc_bitsize = reloc_howto->bitsize;
4073 if (reloc_howto->rightshift)
4074 reloc_bitsize -= reloc_howto->rightshift;
4075 if (reloc_bitsize != operand->bits)
4076 {
4077 as_bad (_("invalid relocation %s for field"),
4078 bfd_get_reloc_code_name (reloc));
4079 return;
4080 }
4081 }
4082 #endif
4083 if (insn->nfixups >= MAX_INSN_FIXUPS)
4084 as_fatal (_("too many fixups"));
4085
4086 struct arc_fixup *fixup;
4087 fixup = &insn->fixups[insn->nfixups++];
4088 fixup->exp = *t;
4089 fixup->reloc = reloc;
4090 if ((int) reloc < 0)
4091 pcrel = (operand->flags & ARC_OPERAND_PCREL) ? 1 : 0;
4092 else
4093 {
4094 reloc_howto_type *reloc_howto =
4095 bfd_reloc_type_lookup (stdoutput,
4096 (bfd_reloc_code_real_type) fixup->reloc);
4097 pcrel = reloc_howto->pc_relative;
4098 }
4099 fixup->pcrel = pcrel;
4100 fixup->islong = (operand->flags & ARC_OPERAND_LIMM) ?
4101 TRUE : FALSE;
4102 break;
4103 }
4104 }
4105
4106 /* Handle flags. */
4107 for (i = 0; i < nflg; i++)
4108 {
4109 const struct arc_flag_operand *flg_operand = pflags[i].flgp;
4110
4111 /* Check if the instruction has a delay slot. */
4112 if (!strcmp (flg_operand->name, "d"))
4113 has_delay_slot = TRUE;
4114
4115 /* There is an exceptional case when we cannot insert a flag just as
4116 it is. On ARCv2 the '.t' and '.nt' flags must be handled in
4117 relation with the relative address. Unfortunately, some of the
4118 ARC700 extensions (NPS400) also have a '.nt' flag that should be
4119 handled in the normal way.
4120
4121 Flag operands don't have an architecture field, so we can't
4122 directly validate that FLAG_OPERAND is valid for the current
4123 architecture, what we do instead is just validate that we're
4124 assembling for an ARCv2 architecture. */
4125 if ((selected_cpu.flags & ARC_OPCODE_ARCV2)
4126 && (!strcmp (flg_operand->name, "t")
4127 || !strcmp (flg_operand->name, "nt")))
4128 {
4129 unsigned bitYoperand = 0;
4130 /* FIXME! move selection bbit/brcc in arc-opc.c. */
4131 if (!strcmp (flg_operand->name, "t"))
4132 if (!strcmp (opcode->name, "bbit0")
4133 || !strcmp (opcode->name, "bbit1"))
4134 bitYoperand = arc_NToperand;
4135 else
4136 bitYoperand = arc_Toperand;
4137 else
4138 if (!strcmp (opcode->name, "bbit0")
4139 || !strcmp (opcode->name, "bbit1"))
4140 bitYoperand = arc_Toperand;
4141 else
4142 bitYoperand = arc_NToperand;
4143
4144 gas_assert (reloc_exp != NULL);
4145 if (reloc_exp->X_op == O_constant)
4146 {
4147 /* Check if we have a constant and solved it
4148 immediately. */
4149 offsetT val = reloc_exp->X_add_number;
4150 image |= insert_operand (image, &arc_operands[bitYoperand],
4151 val, NULL, 0);
4152 }
4153 else
4154 {
4155 struct arc_fixup *fixup;
4156
4157 if (insn->nfixups >= MAX_INSN_FIXUPS)
4158 as_fatal (_("too many fixups"));
4159
4160 fixup = &insn->fixups[insn->nfixups++];
4161 fixup->exp = *reloc_exp;
4162 fixup->reloc = -bitYoperand;
4163 fixup->pcrel = pcrel;
4164 fixup->islong = FALSE;
4165 }
4166 }
4167 else
4168 image |= (flg_operand->code & ((1 << flg_operand->bits) - 1))
4169 << flg_operand->shift;
4170 }
4171
4172 insn->relax = relax_insn_p (opcode, tok, ntok, pflags, nflg);
4173
4174 /* Instruction length. */
4175 insn->len = arc_opcode_len (opcode);
4176
4177 insn->insn = image;
4178
4179 /* Update last insn status. */
4180 arc_last_insns[1] = arc_last_insns[0];
4181 arc_last_insns[0].opcode = opcode;
4182 arc_last_insns[0].has_limm = insn->has_limm;
4183 arc_last_insns[0].has_delay_slot = has_delay_slot;
4184
4185 /* Check if the current instruction is legally used. */
4186 if (arc_last_insns[1].has_delay_slot
4187 && is_br_jmp_insn_p (arc_last_insns[0].opcode))
4188 as_bad (_("Insn %s has a jump/branch instruction %s in its delay slot."),
4189 arc_last_insns[1].opcode->name,
4190 arc_last_insns[0].opcode->name);
4191 if (arc_last_insns[1].has_delay_slot
4192 && arc_last_insns[0].has_limm)
4193 as_bad (_("Insn %s has an instruction %s with limm in its delay slot."),
4194 arc_last_insns[1].opcode->name,
4195 arc_last_insns[0].opcode->name);
4196 }
4197
4198 void
4199 arc_handle_align (fragS* fragP)
4200 {
4201 if ((fragP)->fr_type == rs_align_code)
4202 {
4203 char *dest = (fragP)->fr_literal + (fragP)->fr_fix;
4204 valueT count = ((fragP)->fr_next->fr_address
4205 - (fragP)->fr_address - (fragP)->fr_fix);
4206
4207 (fragP)->fr_var = 2;
4208
4209 if (count & 1)/* Padding in the gap till the next 2-byte
4210 boundary with 0s. */
4211 {
4212 (fragP)->fr_fix++;
4213 *dest++ = 0;
4214 }
4215 /* Writing nop_s. */
4216 md_number_to_chars (dest, NOP_OPCODE_S, 2);
4217 }
4218 }
4219
4220 /* Here we decide which fixups can be adjusted to make them relative
4221 to the beginning of the section instead of the symbol. Basically
4222 we need to make sure that the dynamic relocations are done
4223 correctly, so in some cases we force the original symbol to be
4224 used. */
4225
4226 int
4227 tc_arc_fix_adjustable (fixS *fixP)
4228 {
4229
4230 /* Prevent all adjustments to global symbols. */
4231 if (S_IS_EXTERNAL (fixP->fx_addsy))
4232 return 0;
4233 if (S_IS_WEAK (fixP->fx_addsy))
4234 return 0;
4235
4236 /* Adjust_reloc_syms doesn't know about the GOT. */
4237 switch (fixP->fx_r_type)
4238 {
4239 case BFD_RELOC_ARC_GOTPC32:
4240 case BFD_RELOC_ARC_PLT32:
4241 case BFD_RELOC_ARC_S25H_PCREL_PLT:
4242 case BFD_RELOC_ARC_S21H_PCREL_PLT:
4243 case BFD_RELOC_ARC_S25W_PCREL_PLT:
4244 case BFD_RELOC_ARC_S21W_PCREL_PLT:
4245 return 0;
4246
4247 default:
4248 break;
4249 }
4250
4251 return 1;
4252 }
4253
4254 /* Compute the reloc type of an expression EXP. */
4255
4256 static void
4257 arc_check_reloc (expressionS *exp,
4258 bfd_reloc_code_real_type *r_type_p)
4259 {
4260 if (*r_type_p == BFD_RELOC_32
4261 && exp->X_op == O_subtract
4262 && exp->X_op_symbol != NULL
4263 && S_GET_SEGMENT (exp->X_op_symbol) == now_seg)
4264 *r_type_p = BFD_RELOC_ARC_32_PCREL;
4265 }
4266
4267
4268 /* Add expression EXP of SIZE bytes to offset OFF of fragment FRAG. */
4269
4270 void
4271 arc_cons_fix_new (fragS *frag,
4272 int off,
4273 int size,
4274 expressionS *exp,
4275 bfd_reloc_code_real_type r_type)
4276 {
4277 r_type = BFD_RELOC_UNUSED;
4278
4279 switch (size)
4280 {
4281 case 1:
4282 r_type = BFD_RELOC_8;
4283 break;
4284
4285 case 2:
4286 r_type = BFD_RELOC_16;
4287 break;
4288
4289 case 3:
4290 r_type = BFD_RELOC_24;
4291 break;
4292
4293 case 4:
4294 r_type = BFD_RELOC_32;
4295 arc_check_reloc (exp, &r_type);
4296 break;
4297
4298 case 8:
4299 r_type = BFD_RELOC_64;
4300 break;
4301
4302 default:
4303 as_bad (_("unsupported BFD relocation size %u"), size);
4304 r_type = BFD_RELOC_UNUSED;
4305 }
4306
4307 fix_new_exp (frag, off, size, exp, 0, r_type);
4308 }
4309
4310 /* The actual routine that checks the ZOL conditions. */
4311
4312 static void
4313 check_zol (symbolS *s)
4314 {
4315 switch (selected_cpu.mach)
4316 {
4317 case bfd_mach_arc_arcv2:
4318 if (selected_cpu.flags & ARC_OPCODE_ARCv2EM)
4319 return;
4320
4321 if (is_br_jmp_insn_p (arc_last_insns[0].opcode)
4322 || arc_last_insns[1].has_delay_slot)
4323 as_bad (_("Jump/Branch instruction detected at the end of the ZOL label @%s"),
4324 S_GET_NAME (s));
4325
4326 break;
4327 case bfd_mach_arc_arc600:
4328
4329 if (is_kernel_insn_p (arc_last_insns[0].opcode))
4330 as_bad (_("Kernel instruction detected at the end of the ZOL label @%s"),
4331 S_GET_NAME (s));
4332
4333 if (arc_last_insns[0].has_limm
4334 && is_br_jmp_insn_p (arc_last_insns[0].opcode))
4335 as_bad (_("A jump instruction with long immediate detected at the \
4336 end of the ZOL label @%s"), S_GET_NAME (s));
4337
4338 /* Fall through. */
4339 case bfd_mach_arc_arc700:
4340 if (arc_last_insns[0].has_delay_slot)
4341 as_bad (_("An illegal use of delay slot detected at the end of the ZOL label @%s"),
4342 S_GET_NAME (s));
4343
4344 break;
4345 default:
4346 break;
4347 }
4348 }
4349
4350 /* If ZOL end check the last two instruction for illegals. */
4351 void
4352 arc_frob_label (symbolS * sym)
4353 {
4354 if (ARC_GET_FLAG (sym) & ARC_FLAG_ZOL)
4355 check_zol (sym);
4356
4357 dwarf2_emit_label (sym);
4358 }
4359
4360 /* Used because generic relaxation assumes a pc-rel value whilst we
4361 also relax instructions that use an absolute value resolved out of
4362 relative values (if that makes any sense). An example: 'add r1,
4363 r2, @.L2 - .' The symbols . and @.L2 are relative to the section
4364 but if they're in the same section we can subtract the section
4365 offset relocation which ends up in a resolved value. So if @.L2 is
4366 .text + 0x50 and . is .text + 0x10, we can say that .text + 0x50 -
4367 .text + 0x40 = 0x10. */
4368 int
4369 arc_pcrel_adjust (fragS *fragP)
4370 {
4371 pr_debug ("arc_pcrel_adjust: address=%ld, fix=%ld, PCrel %s\n",
4372 fragP->fr_address, fragP->fr_fix,
4373 fragP->tc_frag_data.pcrel ? "Y" : "N");
4374
4375 if (!fragP->tc_frag_data.pcrel)
4376 return fragP->fr_address + fragP->fr_fix;
4377
4378 /* Take into account the PCL rounding. */
4379 return (fragP->fr_address + fragP->fr_fix) & 0x03;
4380 }
4381
4382 /* Initialize the DWARF-2 unwind information for this procedure. */
4383
4384 void
4385 tc_arc_frame_initial_instructions (void)
4386 {
4387 /* Stack pointer is register 28. */
4388 cfi_add_CFA_def_cfa (28, 0);
4389 }
4390
4391 int
4392 tc_arc_regname_to_dw2regnum (char *regname)
4393 {
4394 struct symbol *sym;
4395
4396 sym = hash_find (arc_reg_hash, regname);
4397 if (sym)
4398 return S_GET_VALUE (sym);
4399
4400 return -1;
4401 }
4402
4403 /* Adjust the symbol table. Delete found AUX register symbols. */
4404
4405 void
4406 arc_adjust_symtab (void)
4407 {
4408 symbolS * sym;
4409
4410 for (sym = symbol_rootP; sym != NULL; sym = symbol_next (sym))
4411 {
4412 /* I've created a symbol during parsing process. Now, remove
4413 the symbol as it is found to be an AUX register. */
4414 if (ARC_GET_FLAG (sym) & ARC_FLAG_AUX)
4415 symbol_remove (sym, &symbol_rootP, &symbol_lastP);
4416 }
4417
4418 /* Now do generic ELF adjustments. */
4419 elf_adjust_symtab ();
4420 }
4421
4422 static void
4423 tokenize_extinsn (extInstruction_t *einsn)
4424 {
4425 char *p, c;
4426 char *insn_name;
4427 unsigned char major_opcode;
4428 unsigned char sub_opcode;
4429 unsigned char syntax_class = 0;
4430 unsigned char syntax_class_modifiers = 0;
4431 unsigned char suffix_class = 0;
4432 unsigned int i;
4433
4434 SKIP_WHITESPACE ();
4435
4436 /* 1st: get instruction name. */
4437 p = input_line_pointer;
4438 c = get_symbol_name (&p);
4439
4440 insn_name = xstrdup (p);
4441 restore_line_pointer (c);
4442
4443 /* Convert to lower case. */
4444 for (p = insn_name; *p; ++p)
4445 *p = TOLOWER (*p);
4446
4447 /* 2nd: get major opcode. */
4448 if (*input_line_pointer != ',')
4449 {
4450 as_bad (_("expected comma after instruction name"));
4451 ignore_rest_of_line ();
4452 return;
4453 }
4454 input_line_pointer++;
4455 major_opcode = get_absolute_expression ();
4456
4457 /* 3rd: get sub-opcode. */
4458 SKIP_WHITESPACE ();
4459
4460 if (*input_line_pointer != ',')
4461 {
4462 as_bad (_("expected comma after major opcode"));
4463 ignore_rest_of_line ();
4464 return;
4465 }
4466 input_line_pointer++;
4467 sub_opcode = get_absolute_expression ();
4468
4469 /* 4th: get suffix class. */
4470 SKIP_WHITESPACE ();
4471
4472 if (*input_line_pointer != ',')
4473 {
4474 as_bad ("expected comma after sub opcode");
4475 ignore_rest_of_line ();
4476 return;
4477 }
4478 input_line_pointer++;
4479
4480 while (1)
4481 {
4482 SKIP_WHITESPACE ();
4483
4484 for (i = 0; i < ARRAY_SIZE (suffixclass); i++)
4485 {
4486 if (!strncmp (suffixclass[i].name, input_line_pointer,
4487 suffixclass[i].len))
4488 {
4489 suffix_class |= suffixclass[i].attr_class;
4490 input_line_pointer += suffixclass[i].len;
4491 break;
4492 }
4493 }
4494
4495 if (i == ARRAY_SIZE (suffixclass))
4496 {
4497 as_bad ("invalid suffix class");
4498 ignore_rest_of_line ();
4499 return;
4500 }
4501
4502 SKIP_WHITESPACE ();
4503
4504 if (*input_line_pointer == '|')
4505 input_line_pointer++;
4506 else
4507 break;
4508 }
4509
4510 /* 5th: get syntax class and syntax class modifiers. */
4511 if (*input_line_pointer != ',')
4512 {
4513 as_bad ("expected comma after suffix class");
4514 ignore_rest_of_line ();
4515 return;
4516 }
4517 input_line_pointer++;
4518
4519 while (1)
4520 {
4521 SKIP_WHITESPACE ();
4522
4523 for (i = 0; i < ARRAY_SIZE (syntaxclassmod); i++)
4524 {
4525 if (!strncmp (syntaxclassmod[i].name,
4526 input_line_pointer,
4527 syntaxclassmod[i].len))
4528 {
4529 syntax_class_modifiers |= syntaxclassmod[i].attr_class;
4530 input_line_pointer += syntaxclassmod[i].len;
4531 break;
4532 }
4533 }
4534
4535 if (i == ARRAY_SIZE (syntaxclassmod))
4536 {
4537 for (i = 0; i < ARRAY_SIZE (syntaxclass); i++)
4538 {
4539 if (!strncmp (syntaxclass[i].name,
4540 input_line_pointer,
4541 syntaxclass[i].len))
4542 {
4543 syntax_class |= syntaxclass[i].attr_class;
4544 input_line_pointer += syntaxclass[i].len;
4545 break;
4546 }
4547 }
4548
4549 if (i == ARRAY_SIZE (syntaxclass))
4550 {
4551 as_bad ("missing syntax class");
4552 ignore_rest_of_line ();
4553 return;
4554 }
4555 }
4556
4557 SKIP_WHITESPACE ();
4558
4559 if (*input_line_pointer == '|')
4560 input_line_pointer++;
4561 else
4562 break;
4563 }
4564
4565 demand_empty_rest_of_line ();
4566
4567 einsn->name = insn_name;
4568 einsn->major = major_opcode;
4569 einsn->minor = sub_opcode;
4570 einsn->syntax = syntax_class;
4571 einsn->modsyn = syntax_class_modifiers;
4572 einsn->suffix = suffix_class;
4573 einsn->flags = syntax_class
4574 | (syntax_class_modifiers & ARC_OP1_IMM_IMPLIED ? 0x10 : 0);
4575 }
4576
4577 /* Generate an extension section. */
4578
4579 static int
4580 arc_set_ext_seg (void)
4581 {
4582 if (!arcext_section)
4583 {
4584 arcext_section = subseg_new (".arcextmap", 0);
4585 bfd_set_section_flags (arcext_section, SEC_READONLY | SEC_HAS_CONTENTS);
4586 }
4587 else
4588 subseg_set (arcext_section, 0);
4589 return 1;
4590 }
4591
4592 /* Create an extension instruction description in the arc extension
4593 section of the output file.
4594 The structure for an instruction is like this:
4595 [0]: Length of the record.
4596 [1]: Type of the record.
4597
4598 [2]: Major opcode.
4599 [3]: Sub-opcode.
4600 [4]: Syntax (flags).
4601 [5]+ Name instruction.
4602
4603 The sequence is terminated by an empty entry. */
4604
4605 static void
4606 create_extinst_section (extInstruction_t *einsn)
4607 {
4608
4609 segT old_sec = now_seg;
4610 int old_subsec = now_subseg;
4611 char *p;
4612 int name_len = strlen (einsn->name);
4613
4614 arc_set_ext_seg ();
4615
4616 p = frag_more (1);
4617 *p = 5 + name_len + 1;
4618 p = frag_more (1);
4619 *p = EXT_INSTRUCTION;
4620 p = frag_more (1);
4621 *p = einsn->major;
4622 p = frag_more (1);
4623 *p = einsn->minor;
4624 p = frag_more (1);
4625 *p = einsn->flags;
4626 p = frag_more (name_len + 1);
4627 strcpy (p, einsn->name);
4628
4629 subseg_set (old_sec, old_subsec);
4630 }
4631
4632 /* Handler .extinstruction pseudo-op. */
4633
4634 static void
4635 arc_extinsn (int ignore ATTRIBUTE_UNUSED)
4636 {
4637 extInstruction_t einsn;
4638 struct arc_opcode *arc_ext_opcodes;
4639 const char *errmsg = NULL;
4640 unsigned char moplow, mophigh;
4641
4642 memset (&einsn, 0, sizeof (einsn));
4643 tokenize_extinsn (&einsn);
4644
4645 /* Check if the name is already used. */
4646 if (arc_find_opcode (einsn.name))
4647 as_warn (_("Pseudocode already used %s"), einsn.name);
4648
4649 /* Check the opcode ranges. */
4650 moplow = 0x05;
4651 mophigh = (selected_cpu.flags & (ARC_OPCODE_ARCv2EM
4652 | ARC_OPCODE_ARCv2HS)) ? 0x07 : 0x0a;
4653
4654 if ((einsn.major > mophigh) || (einsn.major < moplow))
4655 as_fatal (_("major opcode not in range [0x%02x - 0x%02x]"), moplow, mophigh);
4656
4657 if ((einsn.minor > 0x3f) && (einsn.major != 0x0a)
4658 && (einsn.major != 5) && (einsn.major != 9))
4659 as_fatal (_("minor opcode not in range [0x00 - 0x3f]"));
4660
4661 switch (einsn.syntax & ARC_SYNTAX_MASK)
4662 {
4663 case ARC_SYNTAX_3OP:
4664 if (einsn.modsyn & ARC_OP1_IMM_IMPLIED)
4665 as_fatal (_("Improper use of OP1_IMM_IMPLIED"));
4666 break;
4667 case ARC_SYNTAX_2OP:
4668 case ARC_SYNTAX_1OP:
4669 case ARC_SYNTAX_NOP:
4670 if (einsn.modsyn & ARC_OP1_MUST_BE_IMM)
4671 as_fatal (_("Improper use of OP1_MUST_BE_IMM"));
4672 break;
4673 default:
4674 break;
4675 }
4676
4677 arc_ext_opcodes = arcExtMap_genOpcode (&einsn, selected_cpu.flags, &errmsg);
4678 if (arc_ext_opcodes == NULL)
4679 {
4680 if (errmsg)
4681 as_fatal ("%s", errmsg);
4682 else
4683 as_fatal (_("Couldn't generate extension instruction opcodes"));
4684 }
4685 else if (errmsg)
4686 as_warn ("%s", errmsg);
4687
4688 /* Insert the extension instruction. */
4689 arc_insert_opcode ((const struct arc_opcode *) arc_ext_opcodes);
4690
4691 create_extinst_section (&einsn);
4692 }
4693
4694 static bfd_boolean
4695 tokenize_extregister (extRegister_t *ereg, int opertype)
4696 {
4697 char *name;
4698 char *mode;
4699 char c;
4700 char *p;
4701 int number, imode = 0;
4702 bfd_boolean isCore_p = (opertype == EXT_CORE_REGISTER) ? TRUE : FALSE;
4703 bfd_boolean isReg_p = (opertype == EXT_CORE_REGISTER
4704 || opertype == EXT_AUX_REGISTER) ? TRUE : FALSE;
4705
4706 /* 1st: get register name. */
4707 SKIP_WHITESPACE ();
4708 p = input_line_pointer;
4709 c = get_symbol_name (&p);
4710
4711 name = xstrdup (p);
4712 restore_line_pointer (c);
4713
4714 /* 2nd: get register number. */
4715 SKIP_WHITESPACE ();
4716
4717 if (*input_line_pointer != ',')
4718 {
4719 as_bad (_("expected comma after name"));
4720 ignore_rest_of_line ();
4721 free (name);
4722 return FALSE;
4723 }
4724 input_line_pointer++;
4725 number = get_absolute_expression ();
4726
4727 if ((number < 0)
4728 && (opertype != EXT_AUX_REGISTER))
4729 {
4730 as_bad (_("%s second argument cannot be a negative number %d"),
4731 isCore_p ? "extCoreRegister's" : "extCondCode's",
4732 number);
4733 ignore_rest_of_line ();
4734 free (name);
4735 return FALSE;
4736 }
4737
4738 if (isReg_p)
4739 {
4740 /* 3rd: get register mode. */
4741 SKIP_WHITESPACE ();
4742
4743 if (*input_line_pointer != ',')
4744 {
4745 as_bad (_("expected comma after register number"));
4746 ignore_rest_of_line ();
4747 free (name);
4748 return FALSE;
4749 }
4750
4751 input_line_pointer++;
4752 mode = input_line_pointer;
4753
4754 if (!strncmp (mode, "r|w", 3))
4755 {
4756 imode = 0;
4757 input_line_pointer += 3;
4758 }
4759 else if (!strncmp (mode, "r", 1))
4760 {
4761 imode = ARC_REGISTER_READONLY;
4762 input_line_pointer += 1;
4763 }
4764 else if (strncmp (mode, "w", 1))
4765 {
4766 as_bad (_("invalid mode"));
4767 ignore_rest_of_line ();
4768 free (name);
4769 return FALSE;
4770 }
4771 else
4772 {
4773 imode = ARC_REGISTER_WRITEONLY;
4774 input_line_pointer += 1;
4775 }
4776 }
4777
4778 if (isCore_p)
4779 {
4780 /* 4th: get core register shortcut. */
4781 SKIP_WHITESPACE ();
4782 if (*input_line_pointer != ',')
4783 {
4784 as_bad (_("expected comma after register mode"));
4785 ignore_rest_of_line ();
4786 free (name);
4787 return FALSE;
4788 }
4789
4790 input_line_pointer++;
4791
4792 if (!strncmp (input_line_pointer, "cannot_shortcut", 15))
4793 {
4794 imode |= ARC_REGISTER_NOSHORT_CUT;
4795 input_line_pointer += 15;
4796 }
4797 else if (strncmp (input_line_pointer, "can_shortcut", 12))
4798 {
4799 as_bad (_("shortcut designator invalid"));
4800 ignore_rest_of_line ();
4801 free (name);
4802 return FALSE;
4803 }
4804 else
4805 {
4806 input_line_pointer += 12;
4807 }
4808 }
4809 demand_empty_rest_of_line ();
4810
4811 ereg->name = name;
4812 ereg->number = number;
4813 ereg->imode = imode;
4814 return TRUE;
4815 }
4816
4817 /* Create an extension register/condition description in the arc
4818 extension section of the output file.
4819
4820 The structure for an instruction is like this:
4821 [0]: Length of the record.
4822 [1]: Type of the record.
4823
4824 For core regs and condition codes:
4825 [2]: Value.
4826 [3]+ Name.
4827
4828 For auxiliary registers:
4829 [2..5]: Value.
4830 [6]+ Name
4831
4832 The sequence is terminated by an empty entry. */
4833
4834 static void
4835 create_extcore_section (extRegister_t *ereg, int opertype)
4836 {
4837 segT old_sec = now_seg;
4838 int old_subsec = now_subseg;
4839 char *p;
4840 int name_len = strlen (ereg->name);
4841
4842 arc_set_ext_seg ();
4843
4844 switch (opertype)
4845 {
4846 case EXT_COND_CODE:
4847 case EXT_CORE_REGISTER:
4848 p = frag_more (1);
4849 *p = 3 + name_len + 1;
4850 p = frag_more (1);
4851 *p = opertype;
4852 p = frag_more (1);
4853 *p = ereg->number;
4854 break;
4855 case EXT_AUX_REGISTER:
4856 p = frag_more (1);
4857 *p = 6 + name_len + 1;
4858 p = frag_more (1);
4859 *p = EXT_AUX_REGISTER;
4860 p = frag_more (1);
4861 *p = (ereg->number >> 24) & 0xff;
4862 p = frag_more (1);
4863 *p = (ereg->number >> 16) & 0xff;
4864 p = frag_more (1);
4865 *p = (ereg->number >> 8) & 0xff;
4866 p = frag_more (1);
4867 *p = (ereg->number) & 0xff;
4868 break;
4869 default:
4870 break;
4871 }
4872
4873 p = frag_more (name_len + 1);
4874 strcpy (p, ereg->name);
4875
4876 subseg_set (old_sec, old_subsec);
4877 }
4878
4879 /* Handler .extCoreRegister pseudo-op. */
4880
4881 static void
4882 arc_extcorereg (int opertype)
4883 {
4884 extRegister_t ereg;
4885 struct arc_aux_reg *auxr;
4886 const char *retval;
4887 struct arc_flag_operand *ccode;
4888
4889 memset (&ereg, 0, sizeof (ereg));
4890 if (!tokenize_extregister (&ereg, opertype))
4891 return;
4892
4893 switch (opertype)
4894 {
4895 case EXT_CORE_REGISTER:
4896 /* Core register. */
4897 if (ereg.number > 60)
4898 as_bad (_("core register %s value (%d) too large"), ereg.name,
4899 ereg.number);
4900 declare_register (ereg.name, ereg.number);
4901 break;
4902 case EXT_AUX_REGISTER:
4903 /* Auxiliary register. */
4904 auxr = XNEW (struct arc_aux_reg);
4905 auxr->name = ereg.name;
4906 auxr->cpu = selected_cpu.flags;
4907 auxr->subclass = NONE;
4908 auxr->address = ereg.number;
4909 retval = hash_insert (arc_aux_hash, auxr->name, (void *) auxr);
4910 if (retval)
4911 as_fatal (_("internal error: can't hash aux register '%s': %s"),
4912 auxr->name, retval);
4913 break;
4914 case EXT_COND_CODE:
4915 /* Condition code. */
4916 if (ereg.number > 31)
4917 as_bad (_("condition code %s value (%d) too large"), ereg.name,
4918 ereg.number);
4919 ext_condcode.size ++;
4920 ext_condcode.arc_ext_condcode =
4921 XRESIZEVEC (struct arc_flag_operand, ext_condcode.arc_ext_condcode,
4922 ext_condcode.size + 1);
4923 if (ext_condcode.arc_ext_condcode == NULL)
4924 as_fatal (_("Virtual memory exhausted"));
4925
4926 ccode = ext_condcode.arc_ext_condcode + ext_condcode.size - 1;
4927 ccode->name = ereg.name;
4928 ccode->code = ereg.number;
4929 ccode->bits = 5;
4930 ccode->shift = 0;
4931 ccode->favail = 0; /* not used. */
4932 ccode++;
4933 memset (ccode, 0, sizeof (struct arc_flag_operand));
4934 break;
4935 default:
4936 as_bad (_("Unknown extension"));
4937 break;
4938 }
4939 create_extcore_section (&ereg, opertype);
4940 }
4941
4942 /* Parse a .arc_attribute directive. */
4943
4944 static void
4945 arc_attribute (int ignored ATTRIBUTE_UNUSED)
4946 {
4947 int tag = obj_elf_vendor_attribute (OBJ_ATTR_PROC);
4948
4949 if (tag < NUM_KNOWN_OBJ_ATTRIBUTES)
4950 attributes_set_explicitly[tag] = TRUE;
4951 }
4952
4953 /* Set an attribute if it has not already been set by the user. */
4954
4955 static void
4956 arc_set_attribute_int (int tag, int value)
4957 {
4958 if (tag < 1
4959 || tag >= NUM_KNOWN_OBJ_ATTRIBUTES
4960 || !attributes_set_explicitly[tag])
4961 bfd_elf_add_proc_attr_int (stdoutput, tag, value);
4962 }
4963
4964 static void
4965 arc_set_attribute_string (int tag, const char *value)
4966 {
4967 if (tag < 1
4968 || tag >= NUM_KNOWN_OBJ_ATTRIBUTES
4969 || !attributes_set_explicitly[tag])
4970 bfd_elf_add_proc_attr_string (stdoutput, tag, value);
4971 }
4972
4973 /* Allocate and concatenate two strings. s1 can be NULL but not
4974 s2. s1 pointer is freed at end of this procedure. */
4975
4976 static char *
4977 arc_stralloc (char * s1, const char * s2)
4978 {
4979 char * p;
4980 int len = 0;
4981
4982 if (s1)
4983 len = strlen (s1) + 1;
4984
4985 /* Only s1 can be null. */
4986 gas_assert (s2);
4987 len += strlen (s2) + 1;
4988
4989 p = (char *) xmalloc (len);
4990 if (p == NULL)
4991 as_fatal (_("Virtual memory exhausted"));
4992
4993 if (s1)
4994 {
4995 strcpy (p, s1);
4996 strcat (p, ",");
4997 strcat (p, s2);
4998 free (s1);
4999 }
5000 else
5001 strcpy (p, s2);
5002
5003 return p;
5004 }
5005
5006 /* Set the public ARC object attributes. */
5007
5008 static void
5009 arc_set_public_attributes (void)
5010 {
5011 int base = 0;
5012 char *s = NULL;
5013 unsigned int i;
5014
5015 /* Tag_ARC_CPU_name. */
5016 arc_set_attribute_string (Tag_ARC_CPU_name, selected_cpu.name);
5017
5018 /* Tag_ARC_CPU_base. */
5019 switch (selected_cpu.eflags & EF_ARC_MACH_MSK)
5020 {
5021 case E_ARC_MACH_ARC600:
5022 case E_ARC_MACH_ARC601:
5023 base = TAG_CPU_ARC6xx;
5024 break;
5025 case E_ARC_MACH_ARC700:
5026 base = TAG_CPU_ARC7xx;
5027 break;
5028 case EF_ARC_CPU_ARCV2EM:
5029 base = TAG_CPU_ARCEM;
5030 break;
5031 case EF_ARC_CPU_ARCV2HS:
5032 base = TAG_CPU_ARCHS;
5033 break;
5034 default:
5035 base = 0;
5036 break;
5037 }
5038 if (attributes_set_explicitly[Tag_ARC_CPU_base]
5039 && (base != bfd_elf_get_obj_attr_int (stdoutput, OBJ_ATTR_PROC,
5040 Tag_ARC_CPU_base)))
5041 as_warn (_("Overwrite explicitly set Tag_ARC_CPU_base"));
5042 bfd_elf_add_proc_attr_int (stdoutput, Tag_ARC_CPU_base, base);
5043
5044 /* Tag_ARC_ABI_osver. */
5045 if (attributes_set_explicitly[Tag_ARC_ABI_osver])
5046 {
5047 int val = bfd_elf_get_obj_attr_int (stdoutput, OBJ_ATTR_PROC,
5048 Tag_ARC_ABI_osver);
5049
5050 selected_cpu.eflags = ((selected_cpu.eflags & ~EF_ARC_OSABI_MSK)
5051 | (val & 0x0f << 8));
5052 }
5053 else
5054 {
5055 arc_set_attribute_int (Tag_ARC_ABI_osver, E_ARC_OSABI_CURRENT >> 8);
5056 }
5057
5058 /* Tag_ARC_ISA_config. */
5059 arc_check_feature();
5060
5061 for (i = 0; i < ARRAY_SIZE (feature_list); i++)
5062 if (selected_cpu.features & feature_list[i].feature)
5063 s = arc_stralloc (s, feature_list[i].attr);
5064
5065 if (s)
5066 arc_set_attribute_string (Tag_ARC_ISA_config, s);
5067
5068 /* Tag_ARC_ISA_mpy_option. */
5069 arc_set_attribute_int (Tag_ARC_ISA_mpy_option, mpy_option);
5070
5071 /* Tag_ARC_ABI_pic. */
5072 arc_set_attribute_int (Tag_ARC_ABI_pic, pic_option);
5073
5074 /* Tag_ARC_ABI_sda. */
5075 arc_set_attribute_int (Tag_ARC_ABI_sda, sda_option);
5076
5077 /* Tag_ARC_ABI_tls. */
5078 arc_set_attribute_int (Tag_ARC_ABI_tls, tls_option);
5079
5080 /* Tag_ARC_ATR_version. */
5081 arc_set_attribute_int (Tag_ARC_ATR_version, 1);
5082
5083 /* Tag_ARC_ABI_rf16. */
5084 if (attributes_set_explicitly[Tag_ARC_ABI_rf16]
5085 && bfd_elf_get_obj_attr_int (stdoutput, OBJ_ATTR_PROC,
5086 Tag_ARC_ABI_rf16)
5087 && !rf16_only)
5088 {
5089 as_warn (_("Overwrite explicitly set Tag_ARC_ABI_rf16 to full "
5090 "register file"));
5091 bfd_elf_add_proc_attr_int (stdoutput, Tag_ARC_ABI_rf16, 0);
5092 }
5093 }
5094
5095 /* Add the default contents for the .ARC.attributes section. */
5096
5097 void
5098 arc_md_end (void)
5099 {
5100 arc_set_public_attributes ();
5101
5102 if (!bfd_set_arch_mach (stdoutput, bfd_arch_arc, selected_cpu.mach))
5103 as_fatal (_("could not set architecture and machine"));
5104
5105 bfd_set_private_flags (stdoutput, selected_cpu.eflags);
5106 }
5107
5108 void arc_copy_symbol_attributes (symbolS *dest, symbolS *src)
5109 {
5110 ARC_GET_FLAG (dest) = ARC_GET_FLAG (src);
5111 }
5112
5113 int arc_convert_symbolic_attribute (const char *name)
5114 {
5115 static const struct
5116 {
5117 const char * name;
5118 const int tag;
5119 }
5120 attribute_table[] =
5121 {
5122 #define T(tag) {#tag, tag}
5123 T (Tag_ARC_PCS_config),
5124 T (Tag_ARC_CPU_base),
5125 T (Tag_ARC_CPU_variation),
5126 T (Tag_ARC_CPU_name),
5127 T (Tag_ARC_ABI_rf16),
5128 T (Tag_ARC_ABI_osver),
5129 T (Tag_ARC_ABI_sda),
5130 T (Tag_ARC_ABI_pic),
5131 T (Tag_ARC_ABI_tls),
5132 T (Tag_ARC_ABI_enumsize),
5133 T (Tag_ARC_ABI_exceptions),
5134 T (Tag_ARC_ABI_double_size),
5135 T (Tag_ARC_ISA_config),
5136 T (Tag_ARC_ISA_apex),
5137 T (Tag_ARC_ISA_mpy_option),
5138 T (Tag_ARC_ATR_version)
5139 #undef T
5140 };
5141 unsigned int i;
5142
5143 if (name == NULL)
5144 return -1;
5145
5146 for (i = 0; i < ARRAY_SIZE (attribute_table); i++)
5147 if (streq (name, attribute_table[i].name))
5148 return attribute_table[i].tag;
5149
5150 return -1;
5151 }
5152
5153 /* Local variables:
5154 eval: (c-set-style "gnu")
5155 indent-tabs-mode: t
5156 End: */
This page took 0.160172 seconds and 4 git commands to generate.