fa61988aa40a241920fda982d91f5a7d749a497d
[deliverable/binutils-gdb.git] / gas / config / tc-arm.c
1 /* tc-arm.c -- Assemble for the ARM
2 Copyright (C) 1994, 95, 96, 97, 98, 1999 Free Software Foundation, Inc.
3 Contributed by Richard Earnshaw (rwe@pegasus.esprit.ec.org)
4 Modified by David Taylor (dtaylor@armltd.co.uk)
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 2, 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, 59 Temple Place - Suite 330, Boston, MA
21 02111-1307, USA. */
22
23 #include <ctype.h>
24 #include <string.h>
25 #define NO_RELOC 0
26 #include "as.h"
27
28 /* need TARGET_CPU */
29 #include "config.h"
30 #include "subsegs.h"
31 #include "obstack.h"
32 #include "symbols.h"
33 #include "listing.h"
34
35 #ifdef OBJ_ELF
36 #include "elf/arm.h"
37 #endif
38
39 /* Types of processor to assemble for. */
40 #define ARM_1 0x00000001
41 #define ARM_2 0x00000002
42 #define ARM_3 0x00000004
43 #define ARM_250 ARM_3
44 #define ARM_6 0x00000008
45 #define ARM_7 ARM_6 /* same core instruction set */
46 #define ARM_8 ARM_6 /* same core instruction set */
47 #define ARM_9 ARM_6 /* same core instruction set */
48 #define ARM_CPU_MASK 0x0000000f
49
50 /* The following bitmasks control CPU extensions (ARM7 onwards): */
51 #define ARM_LONGMUL 0x00000010 /* allow long multiplies */
52 #define ARM_HALFWORD 0x00000020 /* allow half word loads */
53 #define ARM_THUMB 0x00000040 /* allow BX instruction */
54 #define ARM_EXT_V5 0x00000080 /* allow CLZ etc */
55 #define ARM_EXT_V5E 0x00000200 /* "El Segundo" */
56
57 /* Architectures are the sum of the base and extensions */
58 #define ARM_ARCH_V4 (ARM_7 | ARM_LONGMUL | ARM_HALFWORD)
59 #define ARM_ARCH_V4T (ARM_ARCH_V4 | ARM_THUMB)
60 #define ARM_ARCH_V5 (ARM_ARCH_V4 | ARM_EXT_V5 )
61 #define ARM_ARCH_V5T (ARM_ARCH_V5 | ARM_THUMB)
62
63 /* Some useful combinations: */
64 #define ARM_ANY 0x00ffffff
65 #define ARM_2UP (ARM_ANY - ARM_1)
66 #define ARM_ALL ARM_2UP /* Not arm1 only */
67 #define ARM_3UP 0x00fffffc
68 #define ARM_6UP 0x00fffff8 /* Includes ARM7 */
69
70 #define FPU_CORE 0x80000000
71 #define FPU_FPA10 0x40000000
72 #define FPU_FPA11 0x40000000
73 #define FPU_NONE 0
74
75 /* Some useful combinations */
76 #define FPU_ALL 0xff000000 /* Note this is ~ARM_ANY */
77 #define FPU_MEMMULTI 0x7f000000 /* Not fpu_core */
78
79
80 #ifndef CPU_DEFAULT
81 #if defined __thumb__
82 #define CPU_DEFAULT (ARM_ARCH_V4 | ARM_THUMB)
83 #else
84 #define CPU_DEFAULT ARM_ALL
85 #endif
86 #endif
87
88 #ifndef FPU_DEFAULT
89 #define FPU_DEFAULT FPU_ALL
90 #endif
91
92 #define streq(a, b) (strcmp (a, b) == 0)
93 #define skip_whitespace(str) while (* (str) == ' ') ++ (str)
94
95 static unsigned long cpu_variant = CPU_DEFAULT | FPU_DEFAULT;
96 static int target_oabi = 0;
97
98 #if defined OBJ_COFF || defined OBJ_ELF
99 /* Flags stored in private area of BFD structure */
100 static boolean uses_apcs_26 = false;
101 static boolean support_interwork = false;
102 static boolean uses_apcs_float = false;
103 static boolean pic_code = false;
104 #endif
105
106 /* This array holds the chars that always start a comment. If the
107 pre-processor is disabled, these aren't very useful */
108 CONST char comment_chars[] = "@";
109
110 /* This array holds the chars that only start a comment at the beginning of
111 a line. If the line seems to have the form '# 123 filename'
112 .line and .file directives will appear in the pre-processed output */
113 /* Note that input_file.c hand checks for '#' at the beginning of the
114 first line of the input file. This is because the compiler outputs
115 #NO_APP at the beginning of its output. */
116 /* Also note that comments like this one will always work. */
117 CONST char line_comment_chars[] = "#";
118
119 #ifdef TE_LINUX
120 CONST char line_separator_chars[] = ";";
121 #else
122 CONST char line_separator_chars[] = "";
123 #endif
124
125 /* Chars that can be used to separate mant from exp in floating point nums */
126 CONST char EXP_CHARS[] = "eE";
127
128 /* Chars that mean this number is a floating point constant */
129 /* As in 0f12.456 */
130 /* or 0d1.2345e12 */
131
132 CONST char FLT_CHARS[] = "rRsSfFdDxXeEpP";
133
134 /* Prefix characters that indicate the start of an immediate
135 value. */
136 #define is_immediate_prefix(C) ((C) == '#' || (C) == '$')
137
138 #ifdef OBJ_ELF
139 symbolS * GOT_symbol; /* Pre-defined "_GLOBAL_OFFSET_TABLE_" */
140 #endif
141
142 CONST int md_reloc_size = 8; /* Size of relocation record */
143
144 static int thumb_mode = 0; /* non-zero if assembling thumb instructions */
145
146 typedef struct arm_fix
147 {
148 int thumb_mode;
149 } arm_fix_data;
150
151 struct arm_it
152 {
153 CONST char * error;
154 unsigned long instruction;
155 int suffix;
156 int size;
157 struct
158 {
159 bfd_reloc_code_real_type type;
160 expressionS exp;
161 int pc_rel;
162 } reloc;
163 };
164
165 struct arm_it inst;
166
167 struct asm_shift
168 {
169 CONST char * template;
170 unsigned long value;
171 };
172
173 static CONST struct asm_shift shift[] =
174 {
175 {"asl", 0},
176 {"lsl", 0},
177 {"lsr", 0x00000020},
178 {"asr", 0x00000040},
179 {"ror", 0x00000060},
180 {"rrx", 0x00000060},
181 {"ASL", 0},
182 {"LSL", 0},
183 {"LSR", 0x00000020},
184 {"ASR", 0x00000040},
185 {"ROR", 0x00000060},
186 {"RRX", 0x00000060}
187 };
188
189 #define NO_SHIFT_RESTRICT 1
190 #define SHIFT_RESTRICT 0
191
192 #define NUM_FLOAT_VALS 8
193
194 CONST char * fp_const[] =
195 {
196 "0.0", "1.0", "2.0", "3.0", "4.0", "5.0", "0.5", "10.0", 0
197 };
198
199 /* Number of littlenums required to hold an extended precision number */
200 #define MAX_LITTLENUMS 6
201
202 LITTLENUM_TYPE fp_values[NUM_FLOAT_VALS][MAX_LITTLENUMS];
203
204 #define FAIL (-1)
205 #define SUCCESS (0)
206
207 #define SUFF_S 1
208 #define SUFF_D 2
209 #define SUFF_E 3
210 #define SUFF_P 4
211
212 #define CP_T_X 0x00008000
213 #define CP_T_Y 0x00400000
214 #define CP_T_Pre 0x01000000
215 #define CP_T_UD 0x00800000
216 #define CP_T_WB 0x00200000
217
218 #define CONDS_BIT (0x00100000)
219 #define LOAD_BIT (0x00100000)
220 #define TRANS_BIT (0x00200000)
221
222 struct asm_cond
223 {
224 CONST char * template;
225 unsigned long value;
226 };
227
228 /* This is to save a hash look-up in the common case */
229 #define COND_ALWAYS 0xe0000000
230
231 static CONST struct asm_cond conds[] =
232 {
233 {"eq", 0x00000000},
234 {"ne", 0x10000000},
235 {"cs", 0x20000000}, {"hs", 0x20000000},
236 {"cc", 0x30000000}, {"ul", 0x30000000}, {"lo", 0x30000000},
237 {"mi", 0x40000000},
238 {"pl", 0x50000000},
239 {"vs", 0x60000000},
240 {"vc", 0x70000000},
241 {"hi", 0x80000000},
242 {"ls", 0x90000000},
243 {"ge", 0xa0000000},
244 {"lt", 0xb0000000},
245 {"gt", 0xc0000000},
246 {"le", 0xd0000000},
247 {"al", 0xe0000000},
248 {"nv", 0xf0000000}
249 };
250
251 /* Warning: If the top bit of the set_bits is set, then the standard
252 instruction bitmask is ignored, and the new bitmask is taken from
253 the set_bits: */
254 struct asm_flg
255 {
256 CONST char * template; /* Basic flag string */
257 unsigned long set_bits; /* Bits to set */
258 };
259
260 static CONST struct asm_flg s_flag[] =
261 {
262 {"s", CONDS_BIT},
263 {NULL, 0}
264 };
265
266 static CONST struct asm_flg ldr_flags[] =
267 {
268 {"b", 0x00400000},
269 {"t", TRANS_BIT},
270 {"bt", 0x00400000 | TRANS_BIT},
271 {"h", 0x801000b0},
272 {"sh", 0x801000f0},
273 {"sb", 0x801000d0},
274 {NULL, 0}
275 };
276
277 static CONST struct asm_flg str_flags[] =
278 {
279 {"b", 0x00400000},
280 {"t", TRANS_BIT},
281 {"bt", 0x00400000 | TRANS_BIT},
282 {"h", 0x800000b0},
283 {NULL, 0}
284 };
285
286 static CONST struct asm_flg byte_flag[] =
287 {
288 {"b", 0x00400000},
289 {NULL, 0}
290 };
291
292 static CONST struct asm_flg cmp_flags[] =
293 {
294 {"s", CONDS_BIT},
295 {"p", 0x0010f000},
296 {NULL, 0}
297 };
298
299 static CONST struct asm_flg ldm_flags[] =
300 {
301 {"ed", 0x01800000},
302 {"fd", 0x00800000},
303 {"ea", 0x01000000},
304 {"fa", 0x08000000},
305 {"ib", 0x01800000},
306 {"ia", 0x00800000},
307 {"db", 0x01000000},
308 {"da", 0x08000000},
309 {NULL, 0}
310 };
311
312 static CONST struct asm_flg stm_flags[] =
313 {
314 {"ed", 0x08000000},
315 {"fd", 0x01000000},
316 {"ea", 0x00800000},
317 {"fa", 0x01800000},
318 {"ib", 0x01800000},
319 {"ia", 0x00800000},
320 {"db", 0x01000000},
321 {"da", 0x08000000},
322 {NULL, 0}
323 };
324
325 static CONST struct asm_flg lfm_flags[] =
326 {
327 {"fd", 0x00800000},
328 {"ea", 0x01000000},
329 {NULL, 0}
330 };
331
332 static CONST struct asm_flg sfm_flags[] =
333 {
334 {"fd", 0x01000000},
335 {"ea", 0x00800000},
336 {NULL, 0}
337 };
338
339 static CONST struct asm_flg round_flags[] =
340 {
341 {"p", 0x00000020},
342 {"m", 0x00000040},
343 {"z", 0x00000060},
344 {NULL, 0}
345 };
346
347 /* The implementation of the FIX instruction is broken on some assemblers,
348 in that it accepts a precision specifier as well as a rounding specifier,
349 despite the fact that this is meaningless. To be more compatible, we
350 accept it as well, though of course it does not set any bits. */
351 static CONST struct asm_flg fix_flags[] =
352 {
353 {"p", 0x00000020},
354 {"m", 0x00000040},
355 {"z", 0x00000060},
356 {"sp", 0x00000020},
357 {"sm", 0x00000040},
358 {"sz", 0x00000060},
359 {"dp", 0x00000020},
360 {"dm", 0x00000040},
361 {"dz", 0x00000060},
362 {"ep", 0x00000020},
363 {"em", 0x00000040},
364 {"ez", 0x00000060},
365 {NULL, 0}
366 };
367
368 static CONST struct asm_flg except_flag[] =
369 {
370 {"e", 0x00400000},
371 {NULL, 0}
372 };
373
374 static CONST struct asm_flg cplong_flag[] =
375 {
376 {"l", 0x00400000},
377 {NULL, 0}
378 };
379
380 struct asm_psr
381 {
382 CONST char * template;
383 unsigned long number;
384 };
385
386 #define PSR_FIELD_MASK 0x000f0000
387
388 #define PSR_FLAGS 0x00080000
389 #define PSR_CONTROL 0x00010000 /* Undocumented instruction, its use is discouraged by ARM */
390 #define PSR_ALL 0x00090000
391
392 #define CPSR_ALL 0
393 #define SPSR_ALL 1
394 #define CPSR_FLG 2
395 #define SPSR_FLG 3
396 #define CPSR_CTL 4
397 #define SPSR_CTL 5
398
399 static CONST struct asm_psr psrs[] =
400 {
401 /* Valid <psr>'s */
402 {"cpsr", CPSR_ALL},
403 {"cpsr_all", CPSR_ALL},
404 {"spsr", SPSR_ALL},
405 {"spsr_all", SPSR_ALL},
406
407 /* Valid <psrf>'s */
408 {"cpsr_flg", CPSR_FLG},
409 {"spsr_flg", SPSR_FLG},
410
411 /* Valid <psrc>'s */
412 {"cpsr_c", CPSR_CTL},
413 {"cpsr_ctl", CPSR_CTL},
414 {"spsr_c", SPSR_CTL},
415 {"spsr_ctl", SPSR_CTL}
416 };
417
418 /* Functions called by parser */
419 /* ARM instructions */
420 static void do_arit PARAMS ((char *, unsigned long));
421 static void do_cmp PARAMS ((char *, unsigned long));
422 static void do_mov PARAMS ((char *, unsigned long));
423 static void do_ldst PARAMS ((char *, unsigned long));
424 static void do_ldmstm PARAMS ((char *, unsigned long));
425 static void do_branch PARAMS ((char *, unsigned long));
426 static void do_swi PARAMS ((char *, unsigned long));
427 /* Pseudo Op codes */
428 static void do_adr PARAMS ((char *, unsigned long));
429 static void do_adrl PARAMS ((char *, unsigned long));
430 static void do_nop PARAMS ((char *, unsigned long));
431 /* ARM 2 */
432 static void do_mul PARAMS ((char *, unsigned long));
433 static void do_mla PARAMS ((char *, unsigned long));
434 /* ARM 3 */
435 static void do_swap PARAMS ((char *, unsigned long));
436 /* ARM 6 */
437 static void do_msr PARAMS ((char *, unsigned long));
438 static void do_mrs PARAMS ((char *, unsigned long));
439 /* ARM 7M */
440 static void do_mull PARAMS ((char *, unsigned long));
441 /* ARM THUMB */
442 static void do_bx PARAMS ((char *, unsigned long));
443
444
445 /* Coprocessor Instructions */
446 static void do_cdp PARAMS ((char *, unsigned long));
447 static void do_lstc PARAMS ((char *, unsigned long));
448 static void do_co_reg PARAMS ((char *, unsigned long));
449 static void do_fp_ctrl PARAMS ((char *, unsigned long));
450 static void do_fp_ldst PARAMS ((char *, unsigned long));
451 static void do_fp_ldmstm PARAMS ((char *, unsigned long));
452 static void do_fp_dyadic PARAMS ((char *, unsigned long));
453 static void do_fp_monadic PARAMS ((char *, unsigned long));
454 static void do_fp_cmp PARAMS ((char *, unsigned long));
455 static void do_fp_from_reg PARAMS ((char *, unsigned long));
456 static void do_fp_to_reg PARAMS ((char *, unsigned long));
457
458 static void fix_new_arm PARAMS ((fragS *, int, short, expressionS *, int, int));
459 static int arm_reg_parse PARAMS ((char **));
460 static int arm_psr_parse PARAMS ((char **));
461 static void symbol_locate PARAMS ((symbolS *, CONST char *, segT, valueT, fragS *));
462 static int add_to_lit_pool PARAMS ((void));
463 static unsigned validate_immediate PARAMS ((unsigned));
464 static unsigned validate_immediate_twopart PARAMS ((unsigned int, unsigned int *));
465 static int validate_offset_imm PARAMS ((unsigned int, int));
466 static void opcode_select PARAMS ((int));
467 static void end_of_line PARAMS ((char *));
468 static int reg_required_here PARAMS ((char **, int));
469 static int psr_required_here PARAMS ((char **, int, int));
470 static int co_proc_number PARAMS ((char **));
471 static int cp_opc_expr PARAMS ((char **, int, int));
472 static int cp_reg_required_here PARAMS ((char **, int));
473 static int fp_reg_required_here PARAMS ((char **, int));
474 static int cp_address_offset PARAMS ((char **));
475 static int cp_address_required_here PARAMS ((char **));
476 static int my_get_float_expression PARAMS ((char **));
477 static int skip_past_comma PARAMS ((char **));
478 static int walk_no_bignums PARAMS ((symbolS *));
479 static int negate_data_op PARAMS ((unsigned long *, unsigned long));
480 static int data_op2 PARAMS ((char **));
481 static int fp_op2 PARAMS ((char **));
482 static long reg_list PARAMS ((char **));
483 static void thumb_load_store PARAMS ((char *, int, int));
484 static int decode_shift PARAMS ((char **, int));
485 static int ldst_extend PARAMS ((char **, int));
486 static void thumb_add_sub PARAMS ((char *, int));
487 static void insert_reg PARAMS ((int));
488 static void thumb_shift PARAMS ((char *, int));
489 static void thumb_mov_compare PARAMS ((char *, int));
490 static void set_constant_flonums PARAMS ((void));
491 static valueT md_chars_to_number PARAMS ((char *, int));
492 static void insert_reg_alias PARAMS ((char *, int));
493 static void output_inst PARAMS ((void));
494 #ifdef OBJ_ELF
495 static bfd_reloc_code_real_type arm_parse_reloc PARAMS ((void));
496 #endif
497
498 /* ARM instructions take 4bytes in the object file, Thumb instructions
499 take 2: */
500 #define INSN_SIZE 4
501
502 /* LONGEST_INST is the longest basic instruction name without conditions or
503 * flags.
504 * ARM7M has 4 of length 5
505 */
506
507 #define LONGEST_INST 5
508
509
510 struct asm_opcode
511 {
512 CONST char * template; /* Basic string to match */
513 unsigned long value; /* Basic instruction code */
514
515 /* Compulsory suffix that must follow conds. If "", then the
516 instruction is not conditional and must have no suffix. */
517 CONST char * comp_suffix;
518
519 CONST struct asm_flg * flags; /* Bits to toggle if flag 'n' set */
520 unsigned long variants; /* Which CPU variants this exists for */
521 /* Function to call to parse args */
522 void (* parms) PARAMS ((char *, unsigned long));
523 };
524
525 static CONST struct asm_opcode insns[] =
526 {
527 /* ARM Instructions */
528 {"and", 0x00000000, NULL, s_flag, ARM_ANY, do_arit},
529 {"eor", 0x00200000, NULL, s_flag, ARM_ANY, do_arit},
530 {"sub", 0x00400000, NULL, s_flag, ARM_ANY, do_arit},
531 {"rsb", 0x00600000, NULL, s_flag, ARM_ANY, do_arit},
532 {"add", 0x00800000, NULL, s_flag, ARM_ANY, do_arit},
533 {"adc", 0x00a00000, NULL, s_flag, ARM_ANY, do_arit},
534 {"sbc", 0x00c00000, NULL, s_flag, ARM_ANY, do_arit},
535 {"rsc", 0x00e00000, NULL, s_flag, ARM_ANY, do_arit},
536 {"orr", 0x01800000, NULL, s_flag, ARM_ANY, do_arit},
537 {"bic", 0x01c00000, NULL, s_flag, ARM_ANY, do_arit},
538 {"tst", 0x01000000, NULL, cmp_flags, ARM_ANY, do_cmp},
539 {"teq", 0x01200000, NULL, cmp_flags, ARM_ANY, do_cmp},
540 {"cmp", 0x01400000, NULL, cmp_flags, ARM_ANY, do_cmp},
541 {"cmn", 0x01600000, NULL, cmp_flags, ARM_ANY, do_cmp},
542 {"mov", 0x01a00000, NULL, s_flag, ARM_ANY, do_mov},
543 {"mvn", 0x01e00000, NULL, s_flag, ARM_ANY, do_mov},
544 {"str", 0x04000000, NULL, str_flags, ARM_ANY, do_ldst},
545 {"ldr", 0x04100000, NULL, ldr_flags, ARM_ANY, do_ldst},
546 {"stm", 0x08000000, NULL, stm_flags, ARM_ANY, do_ldmstm},
547 {"ldm", 0x08100000, NULL, ldm_flags, ARM_ANY, do_ldmstm},
548 {"swi", 0x0f000000, NULL, NULL, ARM_ANY, do_swi},
549 {"bl", 0x0bfffffe, NULL, NULL, ARM_ANY, do_branch},
550 {"b", 0x0afffffe, NULL, NULL, ARM_ANY, do_branch},
551
552 /* Pseudo ops */
553 {"adr", 0x028f0000, NULL, NULL, ARM_ANY, do_adr},
554 {"adrl", 0x028f0000, NULL, NULL, ARM_ANY, do_adrl},
555 {"nop", 0x01a00000, NULL, NULL, ARM_ANY, do_nop},
556
557 /* ARM 2 multiplies */
558 {"mul", 0x00000090, NULL, s_flag, ARM_2UP, do_mul},
559 {"mla", 0x00200090, NULL, s_flag, ARM_2UP, do_mla},
560
561 /* ARM 3 - swp instructions */
562 {"swp", 0x01000090, NULL, byte_flag, ARM_3UP, do_swap},
563
564 /* ARM 6 Coprocessor instructions */
565 {"mrs", 0x010f0000, NULL, NULL, ARM_6UP, do_mrs},
566 {"msr", 0x0120f000, NULL, NULL, ARM_6UP, do_msr},
567 /* ScottB: our code uses 0x0128f000 for msr.
568 NickC: but this is wrong because the bits 16 and 19 are handled
569 by the PSR_xxx defines above. */
570
571 /* ARM 7M long multiplies - need signed/unsigned flags! */
572 {"smull", 0x00c00090, NULL, s_flag, ARM_LONGMUL, do_mull},
573 {"umull", 0x00800090, NULL, s_flag, ARM_LONGMUL, do_mull},
574 {"smlal", 0x00e00090, NULL, s_flag, ARM_LONGMUL, do_mull},
575 {"umlal", 0x00a00090, NULL, s_flag, ARM_LONGMUL, do_mull},
576
577 /* ARM THUMB interworking */
578 {"bx", 0x012fff10, NULL, NULL, ARM_THUMB, do_bx},
579
580 /* Floating point instructions */
581 {"wfs", 0x0e200110, NULL, NULL, FPU_ALL, do_fp_ctrl},
582 {"rfs", 0x0e300110, NULL, NULL, FPU_ALL, do_fp_ctrl},
583 {"wfc", 0x0e400110, NULL, NULL, FPU_ALL, do_fp_ctrl},
584 {"rfc", 0x0e500110, NULL, NULL, FPU_ALL, do_fp_ctrl},
585 {"ldf", 0x0c100100, "sdep", NULL, FPU_ALL, do_fp_ldst},
586 {"stf", 0x0c000100, "sdep", NULL, FPU_ALL, do_fp_ldst},
587 {"lfm", 0x0c100200, NULL, lfm_flags, FPU_MEMMULTI, do_fp_ldmstm},
588 {"sfm", 0x0c000200, NULL, sfm_flags, FPU_MEMMULTI, do_fp_ldmstm},
589 {"mvf", 0x0e008100, "sde", round_flags, FPU_ALL, do_fp_monadic},
590 {"mnf", 0x0e108100, "sde", round_flags, FPU_ALL, do_fp_monadic},
591 {"abs", 0x0e208100, "sde", round_flags, FPU_ALL, do_fp_monadic},
592 {"rnd", 0x0e308100, "sde", round_flags, FPU_ALL, do_fp_monadic},
593 {"sqt", 0x0e408100, "sde", round_flags, FPU_ALL, do_fp_monadic},
594 {"log", 0x0e508100, "sde", round_flags, FPU_ALL, do_fp_monadic},
595 {"lgn", 0x0e608100, "sde", round_flags, FPU_ALL, do_fp_monadic},
596 {"exp", 0x0e708100, "sde", round_flags, FPU_ALL, do_fp_monadic},
597 {"sin", 0x0e808100, "sde", round_flags, FPU_ALL, do_fp_monadic},
598 {"cos", 0x0e908100, "sde", round_flags, FPU_ALL, do_fp_monadic},
599 {"tan", 0x0ea08100, "sde", round_flags, FPU_ALL, do_fp_monadic},
600 {"asn", 0x0eb08100, "sde", round_flags, FPU_ALL, do_fp_monadic},
601 {"acs", 0x0ec08100, "sde", round_flags, FPU_ALL, do_fp_monadic},
602 {"atn", 0x0ed08100, "sde", round_flags, FPU_ALL, do_fp_monadic},
603 {"urd", 0x0ee08100, "sde", round_flags, FPU_ALL, do_fp_monadic},
604 {"nrm", 0x0ef08100, "sde", round_flags, FPU_ALL, do_fp_monadic},
605 {"adf", 0x0e000100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
606 {"suf", 0x0e200100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
607 {"rsf", 0x0e300100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
608 {"muf", 0x0e100100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
609 {"dvf", 0x0e400100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
610 {"rdf", 0x0e500100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
611 {"pow", 0x0e600100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
612 {"rpw", 0x0e700100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
613 {"rmf", 0x0e800100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
614 {"fml", 0x0e900100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
615 {"fdv", 0x0ea00100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
616 {"frd", 0x0eb00100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
617 {"pol", 0x0ec00100, "sde", round_flags, FPU_ALL, do_fp_dyadic},
618 {"cmf", 0x0e90f110, NULL, except_flag, FPU_ALL, do_fp_cmp},
619 {"cnf", 0x0eb0f110, NULL, except_flag, FPU_ALL, do_fp_cmp},
620 /* The FPA10 data sheet suggests that the 'E' of cmfe/cnfe should not
621 be an optional suffix, but part of the instruction. To be compatible,
622 we accept either. */
623 {"cmfe", 0x0ed0f110, NULL, NULL, FPU_ALL, do_fp_cmp},
624 {"cnfe", 0x0ef0f110, NULL, NULL, FPU_ALL, do_fp_cmp},
625 {"flt", 0x0e000110, "sde", round_flags, FPU_ALL, do_fp_from_reg},
626 {"fix", 0x0e100110, NULL, fix_flags, FPU_ALL, do_fp_to_reg},
627
628 /* Generic copressor instructions */
629 {"cdp", 0x0e000000, NULL, NULL, ARM_2UP, do_cdp},
630 {"ldc", 0x0c100000, NULL, cplong_flag, ARM_2UP, do_lstc},
631 {"stc", 0x0c000000, NULL, cplong_flag, ARM_2UP, do_lstc},
632 {"mcr", 0x0e000010, NULL, NULL, ARM_2UP, do_co_reg},
633 {"mrc", 0x0e100010, NULL, NULL, ARM_2UP, do_co_reg},
634 };
635
636 /* defines for various bits that we will want to toggle */
637
638 #define INST_IMMEDIATE 0x02000000
639 #define OFFSET_REG 0x02000000
640 #define HWOFFSET_IMM 0x00400000
641 #define SHIFT_BY_REG 0x00000010
642 #define PRE_INDEX 0x01000000
643 #define INDEX_UP 0x00800000
644 #define WRITE_BACK 0x00200000
645 #define LDM_TYPE_2_OR_3 0x00400000
646
647 #define LITERAL_MASK 0xf000f000
648 #define COND_MASK 0xf0000000
649 #define OPCODE_MASK 0xfe1fffff
650 #define DATA_OP_SHIFT 21
651
652 /* Codes to distinguish the arithmetic instructions */
653
654 #define OPCODE_AND 0
655 #define OPCODE_EOR 1
656 #define OPCODE_SUB 2
657 #define OPCODE_RSB 3
658 #define OPCODE_ADD 4
659 #define OPCODE_ADC 5
660 #define OPCODE_SBC 6
661 #define OPCODE_RSC 7
662 #define OPCODE_TST 8
663 #define OPCODE_TEQ 9
664 #define OPCODE_CMP 10
665 #define OPCODE_CMN 11
666 #define OPCODE_ORR 12
667 #define OPCODE_MOV 13
668 #define OPCODE_BIC 14
669 #define OPCODE_MVN 15
670
671 static void do_t_nop PARAMS ((char *));
672 static void do_t_arit PARAMS ((char *));
673 static void do_t_add PARAMS ((char *));
674 static void do_t_asr PARAMS ((char *));
675 static void do_t_branch9 PARAMS ((char *));
676 static void do_t_branch12 PARAMS ((char *));
677 static void do_t_branch23 PARAMS ((char *));
678 static void do_t_bx PARAMS ((char *));
679 static void do_t_compare PARAMS ((char *));
680 static void do_t_ldmstm PARAMS ((char *));
681 static void do_t_ldr PARAMS ((char *));
682 static void do_t_ldrb PARAMS ((char *));
683 static void do_t_ldrh PARAMS ((char *));
684 static void do_t_lds PARAMS ((char *));
685 static void do_t_lsl PARAMS ((char *));
686 static void do_t_lsr PARAMS ((char *));
687 static void do_t_mov PARAMS ((char *));
688 static void do_t_push_pop PARAMS ((char *));
689 static void do_t_str PARAMS ((char *));
690 static void do_t_strb PARAMS ((char *));
691 static void do_t_strh PARAMS ((char *));
692 static void do_t_sub PARAMS ((char *));
693 static void do_t_swi PARAMS ((char *));
694 static void do_t_adr PARAMS ((char *));
695
696 #define T_OPCODE_MUL 0x4340
697 #define T_OPCODE_TST 0x4200
698 #define T_OPCODE_CMN 0x42c0
699 #define T_OPCODE_NEG 0x4240
700 #define T_OPCODE_MVN 0x43c0
701
702 #define T_OPCODE_ADD_R3 0x1800
703 #define T_OPCODE_SUB_R3 0x1a00
704 #define T_OPCODE_ADD_HI 0x4400
705 #define T_OPCODE_ADD_ST 0xb000
706 #define T_OPCODE_SUB_ST 0xb080
707 #define T_OPCODE_ADD_SP 0xa800
708 #define T_OPCODE_ADD_PC 0xa000
709 #define T_OPCODE_ADD_I8 0x3000
710 #define T_OPCODE_SUB_I8 0x3800
711 #define T_OPCODE_ADD_I3 0x1c00
712 #define T_OPCODE_SUB_I3 0x1e00
713
714 #define T_OPCODE_ASR_R 0x4100
715 #define T_OPCODE_LSL_R 0x4080
716 #define T_OPCODE_LSR_R 0x40c0
717 #define T_OPCODE_ASR_I 0x1000
718 #define T_OPCODE_LSL_I 0x0000
719 #define T_OPCODE_LSR_I 0x0800
720
721 #define T_OPCODE_MOV_I8 0x2000
722 #define T_OPCODE_CMP_I8 0x2800
723 #define T_OPCODE_CMP_LR 0x4280
724 #define T_OPCODE_MOV_HR 0x4600
725 #define T_OPCODE_CMP_HR 0x4500
726
727 #define T_OPCODE_LDR_PC 0x4800
728 #define T_OPCODE_LDR_SP 0x9800
729 #define T_OPCODE_STR_SP 0x9000
730 #define T_OPCODE_LDR_IW 0x6800
731 #define T_OPCODE_STR_IW 0x6000
732 #define T_OPCODE_LDR_IH 0x8800
733 #define T_OPCODE_STR_IH 0x8000
734 #define T_OPCODE_LDR_IB 0x7800
735 #define T_OPCODE_STR_IB 0x7000
736 #define T_OPCODE_LDR_RW 0x5800
737 #define T_OPCODE_STR_RW 0x5000
738 #define T_OPCODE_LDR_RH 0x5a00
739 #define T_OPCODE_STR_RH 0x5200
740 #define T_OPCODE_LDR_RB 0x5c00
741 #define T_OPCODE_STR_RB 0x5400
742
743 #define T_OPCODE_PUSH 0xb400
744 #define T_OPCODE_POP 0xbc00
745
746 #define T_OPCODE_BRANCH 0xe7fe
747
748 static int thumb_reg PARAMS ((char ** str, int hi_lo));
749
750 #define THUMB_SIZE 2 /* Size of thumb instruction */
751 #define THUMB_REG_LO 0x1
752 #define THUMB_REG_HI 0x2
753 #define THUMB_REG_ANY 0x3
754
755 #define THUMB_H1 0x0080
756 #define THUMB_H2 0x0040
757
758 #define THUMB_ASR 0
759 #define THUMB_LSL 1
760 #define THUMB_LSR 2
761
762 #define THUMB_MOVE 0
763 #define THUMB_COMPARE 1
764
765 #define THUMB_LOAD 0
766 #define THUMB_STORE 1
767
768 #define THUMB_PP_PC_LR 0x0100
769
770 /* These three are used for immediate shifts, do not alter */
771 #define THUMB_WORD 2
772 #define THUMB_HALFWORD 1
773 #define THUMB_BYTE 0
774
775 struct thumb_opcode
776 {
777 CONST char * template; /* Basic string to match */
778 unsigned long value; /* Basic instruction code */
779 int size;
780 unsigned long variants; /* Which CPU variants this exists for */
781 void (* parms) PARAMS ((char *)); /* Function to call to parse args */
782 };
783
784 static CONST struct thumb_opcode tinsns[] =
785 {
786 {"adc", 0x4140, 2, ARM_THUMB, do_t_arit},
787 {"add", 0x0000, 2, ARM_THUMB, do_t_add},
788 {"and", 0x4000, 2, ARM_THUMB, do_t_arit},
789 {"asr", 0x0000, 2, ARM_THUMB, do_t_asr},
790 {"b", T_OPCODE_BRANCH, 2, ARM_THUMB, do_t_branch12},
791 {"beq", 0xd0fe, 2, ARM_THUMB, do_t_branch9},
792 {"bne", 0xd1fe, 2, ARM_THUMB, do_t_branch9},
793 {"bcs", 0xd2fe, 2, ARM_THUMB, do_t_branch9},
794 {"bhs", 0xd2fe, 2, ARM_THUMB, do_t_branch9},
795 {"bcc", 0xd3fe, 2, ARM_THUMB, do_t_branch9},
796 {"bul", 0xd3fe, 2, ARM_THUMB, do_t_branch9},
797 {"blo", 0xd3fe, 2, ARM_THUMB, do_t_branch9},
798 {"bmi", 0xd4fe, 2, ARM_THUMB, do_t_branch9},
799 {"bpl", 0xd5fe, 2, ARM_THUMB, do_t_branch9},
800 {"bvs", 0xd6fe, 2, ARM_THUMB, do_t_branch9},
801 {"bvc", 0xd7fe, 2, ARM_THUMB, do_t_branch9},
802 {"bhi", 0xd8fe, 2, ARM_THUMB, do_t_branch9},
803 {"bls", 0xd9fe, 2, ARM_THUMB, do_t_branch9},
804 {"bge", 0xdafe, 2, ARM_THUMB, do_t_branch9},
805 {"blt", 0xdbfe, 2, ARM_THUMB, do_t_branch9},
806 {"bgt", 0xdcfe, 2, ARM_THUMB, do_t_branch9},
807 {"ble", 0xddfe, 2, ARM_THUMB, do_t_branch9},
808 {"bic", 0x4380, 2, ARM_THUMB, do_t_arit},
809 {"bl", 0xf7fffffe, 4, ARM_THUMB, do_t_branch23},
810 {"bx", 0x4700, 2, ARM_THUMB, do_t_bx},
811 {"cmn", T_OPCODE_CMN, 2, ARM_THUMB, do_t_arit},
812 {"cmp", 0x0000, 2, ARM_THUMB, do_t_compare},
813 {"eor", 0x4040, 2, ARM_THUMB, do_t_arit},
814 {"ldmia", 0xc800, 2, ARM_THUMB, do_t_ldmstm},
815 {"ldr", 0x0000, 2, ARM_THUMB, do_t_ldr},
816 {"ldrb", 0x0000, 2, ARM_THUMB, do_t_ldrb},
817 {"ldrh", 0x0000, 2, ARM_THUMB, do_t_ldrh},
818 {"ldrsb", 0x5600, 2, ARM_THUMB, do_t_lds},
819 {"ldrsh", 0x5e00, 2, ARM_THUMB, do_t_lds},
820 {"ldsb", 0x5600, 2, ARM_THUMB, do_t_lds},
821 {"ldsh", 0x5e00, 2, ARM_THUMB, do_t_lds},
822 {"lsl", 0x0000, 2, ARM_THUMB, do_t_lsl},
823 {"lsr", 0x0000, 2, ARM_THUMB, do_t_lsr},
824 {"mov", 0x0000, 2, ARM_THUMB, do_t_mov},
825 {"mul", T_OPCODE_MUL, 2, ARM_THUMB, do_t_arit},
826 {"mvn", T_OPCODE_MVN, 2, ARM_THUMB, do_t_arit},
827 {"neg", T_OPCODE_NEG, 2, ARM_THUMB, do_t_arit},
828 {"orr", 0x4300, 2, ARM_THUMB, do_t_arit},
829 {"pop", 0xbc00, 2, ARM_THUMB, do_t_push_pop},
830 {"push", 0xb400, 2, ARM_THUMB, do_t_push_pop},
831 {"ror", 0x41c0, 2, ARM_THUMB, do_t_arit},
832 {"sbc", 0x4180, 2, ARM_THUMB, do_t_arit},
833 {"stmia", 0xc000, 2, ARM_THUMB, do_t_ldmstm},
834 {"str", 0x0000, 2, ARM_THUMB, do_t_str},
835 {"strb", 0x0000, 2, ARM_THUMB, do_t_strb},
836 {"strh", 0x0000, 2, ARM_THUMB, do_t_strh},
837 {"swi", 0xdf00, 2, ARM_THUMB, do_t_swi},
838 {"sub", 0x0000, 2, ARM_THUMB, do_t_sub},
839 {"tst", T_OPCODE_TST, 2, ARM_THUMB, do_t_arit},
840 /* Pseudo ops: */
841 {"adr", 0x0000, 2, ARM_THUMB, do_t_adr},
842 {"nop", 0x46C0, 2, ARM_THUMB, do_t_nop}, /* mov r8,r8 */
843 };
844
845 struct reg_entry
846 {
847 CONST char * name;
848 int number;
849 };
850
851 #define int_register(reg) ((reg) >= 0 && (reg) <= 15)
852 #define cp_register(reg) ((reg) >= 32 && (reg) <= 47)
853 #define fp_register(reg) ((reg) >= 16 && (reg) <= 23)
854
855 #define REG_PC 15
856 #define REG_LR 14
857 #define REG_SP 13
858
859 /* These are the standard names; Users can add aliases with .req */
860 static CONST struct reg_entry reg_table[] =
861 {
862 /* Processor Register Numbers */
863 {"r0", 0}, {"r1", 1}, {"r2", 2}, {"r3", 3},
864 {"r4", 4}, {"r5", 5}, {"r6", 6}, {"r7", 7},
865 {"r8", 8}, {"r9", 9}, {"r10", 10}, {"r11", 11},
866 {"r12", 12}, {"r13", REG_SP},{"r14", REG_LR},{"r15", REG_PC},
867 /* APCS conventions */
868 {"a1", 0}, {"a2", 1}, {"a3", 2}, {"a4", 3},
869 {"v1", 4}, {"v2", 5}, {"v3", 6}, {"v4", 7}, {"v5", 8},
870 {"v6", 9}, {"sb", 9}, {"v7", 10}, {"sl", 10},
871 {"fp", 11}, {"ip", 12}, {"sp", REG_SP},{"lr", REG_LR},{"pc", REG_PC},
872 /* FP Registers */
873 {"f0", 16}, {"f1", 17}, {"f2", 18}, {"f3", 19},
874 {"f4", 20}, {"f5", 21}, {"f6", 22}, {"f7", 23},
875 {"c0", 32}, {"c1", 33}, {"c2", 34}, {"c3", 35},
876 {"c4", 36}, {"c5", 37}, {"c6", 38}, {"c7", 39},
877 {"c8", 40}, {"c9", 41}, {"c10", 42}, {"c11", 43},
878 {"c12", 44}, {"c13", 45}, {"c14", 46}, {"c15", 47},
879 {"cr0", 32}, {"cr1", 33}, {"cr2", 34}, {"cr3", 35},
880 {"cr4", 36}, {"cr5", 37}, {"cr6", 38}, {"cr7", 39},
881 {"cr8", 40}, {"cr9", 41}, {"cr10", 42}, {"cr11", 43},
882 {"cr12", 44}, {"cr13", 45}, {"cr14", 46}, {"cr15", 47},
883 {NULL, 0}
884 };
885
886 #define BAD_ARGS _("Bad arguments to instruction")
887 #define BAD_PC _("r15 not allowed here")
888 #define BAD_FLAGS _("Instruction should not have flags")
889 #define BAD_COND _("Instruction is not conditional")
890
891 static struct hash_control * arm_ops_hsh = NULL;
892 static struct hash_control * arm_tops_hsh = NULL;
893 static struct hash_control * arm_cond_hsh = NULL;
894 static struct hash_control * arm_shift_hsh = NULL;
895 static struct hash_control * arm_reg_hsh = NULL;
896 static struct hash_control * arm_psr_hsh = NULL;
897
898 /* This table describes all the machine specific pseudo-ops the assembler
899 has to support. The fields are:
900 pseudo-op name without dot
901 function to call to execute this pseudo-op
902 Integer arg to pass to the function
903 */
904
905 static void s_req PARAMS ((int));
906 static void s_align PARAMS ((int));
907 static void s_bss PARAMS ((int));
908 static void s_even PARAMS ((int));
909 static void s_ltorg PARAMS ((int));
910 static void s_arm PARAMS ((int));
911 static void s_thumb PARAMS ((int));
912 static void s_code PARAMS ((int));
913 static void s_force_thumb PARAMS ((int));
914 static void s_thumb_func PARAMS ((int));
915 static void s_thumb_set PARAMS ((int));
916 static void arm_s_text PARAMS ((int));
917 static void arm_s_data PARAMS ((int));
918 #ifdef OBJ_ELF
919 static void arm_s_section PARAMS ((int));
920 static void s_arm_elf_cons PARAMS ((int));
921 #endif
922
923 static int my_get_expression PARAMS ((expressionS *, char **));
924
925 CONST pseudo_typeS md_pseudo_table[] =
926 {
927 { "req", s_req, 0 }, /* Never called becasue '.req' does not start line */
928 { "bss", s_bss, 0 },
929 { "align", s_align, 0 },
930 { "arm", s_arm, 0 },
931 { "thumb", s_thumb, 0 },
932 { "code", s_code, 0 },
933 { "force_thumb", s_force_thumb, 0 },
934 { "thumb_func", s_thumb_func, 0 },
935 { "thumb_set", s_thumb_set, 0 },
936 { "even", s_even, 0 },
937 { "ltorg", s_ltorg, 0 },
938 { "pool", s_ltorg, 0 },
939 /* Allow for the effect of section changes. */
940 { "text", arm_s_text, 0 },
941 { "data", arm_s_data, 0 },
942 #ifdef OBJ_ELF
943 { "section", arm_s_section, 0 },
944 { "section.s", arm_s_section, 0 },
945 { "sect", arm_s_section, 0 },
946 { "sect.s", arm_s_section, 0 },
947 { "word", s_arm_elf_cons, 4 },
948 { "long", s_arm_elf_cons, 4 },
949 #else
950 { "word", cons, 4},
951 #endif
952 { "extend", float_cons, 'x' },
953 { "ldouble", float_cons, 'x' },
954 { "packed", float_cons, 'p' },
955 { 0, 0, 0 }
956 };
957
958 /* Stuff needed to resolve the label ambiguity
959 As:
960 ...
961 label: <insn>
962 may differ from:
963 ...
964 label:
965 <insn>
966 */
967
968 symbolS * last_label_seen;
969 static int label_is_thumb_function_name = false;
970
971 /* Literal stuff */
972
973 #define MAX_LITERAL_POOL_SIZE 1024
974
975 typedef struct literalS
976 {
977 struct expressionS exp;
978 struct arm_it * inst;
979 } literalT;
980
981 literalT literals[MAX_LITERAL_POOL_SIZE];
982 int next_literal_pool_place = 0; /* Next free entry in the pool */
983 int lit_pool_num = 1; /* Next literal pool number */
984 symbolS * current_poolP = NULL;
985
986 static int
987 add_to_lit_pool ()
988 {
989 int lit_count = 0;
990
991 if (current_poolP == NULL)
992 current_poolP = symbol_create (FAKE_LABEL_NAME, undefined_section,
993 (valueT) 0, &zero_address_frag);
994
995 /* Check if this literal value is already in the pool: */
996 while (lit_count < next_literal_pool_place)
997 {
998 if (literals[lit_count].exp.X_op == inst.reloc.exp.X_op
999 && inst.reloc.exp.X_op == O_constant
1000 && literals[lit_count].exp.X_add_number == inst.reloc.exp.X_add_number
1001 && literals[lit_count].exp.X_unsigned == inst.reloc.exp.X_unsigned)
1002 break;
1003 lit_count++;
1004 }
1005
1006 if (lit_count == next_literal_pool_place) /* new entry */
1007 {
1008 if (next_literal_pool_place > MAX_LITERAL_POOL_SIZE)
1009 {
1010 inst.error = _("Literal Pool Overflow");
1011 return FAIL;
1012 }
1013
1014 literals[next_literal_pool_place].exp = inst.reloc.exp;
1015 lit_count = next_literal_pool_place++;
1016 }
1017
1018 inst.reloc.exp.X_op = O_symbol;
1019 inst.reloc.exp.X_add_number = (lit_count) * 4 - 8;
1020 inst.reloc.exp.X_add_symbol = current_poolP;
1021
1022 return SUCCESS;
1023 }
1024
1025 /* Can't use symbol_new here, so have to create a symbol and then at
1026 a later date assign it a value. Thats what these functions do. */
1027 static void
1028 symbol_locate (symbolP, name, segment, valu, frag)
1029 symbolS * symbolP;
1030 CONST char * name; /* It is copied, the caller can modify */
1031 segT segment; /* Segment identifier (SEG_<something>) */
1032 valueT valu; /* Symbol value */
1033 fragS * frag; /* Associated fragment */
1034 {
1035 unsigned int name_length;
1036 char * preserved_copy_of_name;
1037
1038 name_length = strlen (name) + 1; /* +1 for \0 */
1039 obstack_grow (&notes, name, name_length);
1040 preserved_copy_of_name = obstack_finish (&notes);
1041 #ifdef STRIP_UNDERSCORE
1042 if (preserved_copy_of_name[0] == '_')
1043 preserved_copy_of_name++;
1044 #endif
1045
1046 #ifdef tc_canonicalize_symbol_name
1047 preserved_copy_of_name =
1048 tc_canonicalize_symbol_name (preserved_copy_of_name);
1049 #endif
1050
1051 S_SET_NAME (symbolP, preserved_copy_of_name);
1052
1053 S_SET_SEGMENT (symbolP, segment);
1054 S_SET_VALUE (symbolP, valu);
1055 symbol_clear_list_pointers(symbolP);
1056
1057 symbol_set_frag (symbolP, frag);
1058
1059 /* Link to end of symbol chain. */
1060 {
1061 extern int symbol_table_frozen;
1062 if (symbol_table_frozen)
1063 abort ();
1064 }
1065
1066 symbol_append (symbolP, symbol_lastP, & symbol_rootP, & symbol_lastP);
1067
1068 obj_symbol_new_hook (symbolP);
1069
1070 #ifdef tc_symbol_new_hook
1071 tc_symbol_new_hook (symbolP);
1072 #endif
1073
1074 #ifdef DEBUG_SYMS
1075 verify_symbol_chain (symbol_rootP, symbol_lastP);
1076 #endif /* DEBUG_SYMS */
1077 }
1078
1079 /* Check that an immediate is valid, and if so, convert it to the right format. */
1080
1081 static unsigned int
1082 validate_immediate (val)
1083 unsigned int val;
1084 {
1085 unsigned int a;
1086 unsigned int i;
1087
1088 #define rotate_left(v, n) (v << n | v >> (32 - n))
1089
1090 for (i = 0; i < 32; i += 2)
1091 if ((a = rotate_left (val, i)) <= 0xff)
1092 return a | (i << 7); /* 12-bit pack: [shift-cnt,const] */
1093
1094 return FAIL;
1095 }
1096
1097 /* Check to see if an immediate can be computed as two seperate immediate
1098 values, added together. We already know that this value cannot be
1099 computed by just one ARM instruction. */
1100
1101 static unsigned int
1102 validate_immediate_twopart (val, highpart)
1103 unsigned int val;
1104 unsigned int * highpart;
1105 {
1106 unsigned int a;
1107 unsigned int i;
1108
1109 for (i = 0; i < 32; i += 2)
1110 if (((a = rotate_left (val, i)) & 0xff) != 0)
1111 {
1112 if (a & 0xff00)
1113 {
1114 if (a & ~ 0xffff)
1115 continue;
1116 * highpart = (a >> 8) | ((i + 24) << 7);
1117 }
1118 else if (a & 0xff0000)
1119 {
1120 if (a & 0xff000000)
1121 continue;
1122
1123 * highpart = (a >> 16) | ((i + 16) << 7);
1124 }
1125 else
1126 {
1127 assert (a & 0xff000000);
1128
1129 * highpart = (a >> 24) | ((i + 8) << 7);
1130 }
1131
1132 return (a & 0xff) | (i << 7);
1133 }
1134
1135 return FAIL;
1136 }
1137
1138 static int
1139 validate_offset_imm (val, hwse)
1140 unsigned int val;
1141 int hwse;
1142 {
1143 if ((hwse && val > 255) || val > 4095)
1144 return FAIL;
1145 return val;
1146 }
1147
1148
1149 static void
1150 s_req (a)
1151 int a;
1152 {
1153 as_bad (_("Invalid syntax for .req directive."));
1154 }
1155
1156 static void
1157 s_bss (ignore)
1158 int ignore;
1159 {
1160 /* We don't support putting frags in the BSS segment, we fake it by
1161 marking in_bss, then looking at s_skip for clues?.. */
1162 subseg_set (bss_section, 0);
1163 demand_empty_rest_of_line ();
1164 }
1165
1166 static void
1167 s_even (ignore)
1168 int ignore;
1169 {
1170 if (!need_pass_2) /* Never make frag if expect extra pass. */
1171 frag_align (1, 0, 0);
1172
1173 record_alignment (now_seg, 1);
1174
1175 demand_empty_rest_of_line ();
1176 }
1177
1178 static void
1179 s_ltorg (ignored)
1180 int ignored;
1181 {
1182 int lit_count = 0;
1183 char sym_name[20];
1184
1185 if (current_poolP == NULL)
1186 return;
1187
1188 /* Align pool as you have word accesses */
1189 /* Only make a frag if we have to ... */
1190 if (!need_pass_2)
1191 frag_align (2, 0, 0);
1192
1193 record_alignment (now_seg, 2);
1194
1195 sprintf (sym_name, "$$lit_\002%x", lit_pool_num++);
1196
1197 symbol_locate (current_poolP, sym_name, now_seg,
1198 (valueT) frag_now_fix (), frag_now);
1199 symbol_table_insert (current_poolP);
1200
1201 ARM_SET_THUMB (current_poolP, thumb_mode);
1202
1203 #if defined OBJ_COFF || defined OBJ_ELF
1204 ARM_SET_INTERWORK (current_poolP, support_interwork);
1205 #endif
1206
1207 while (lit_count < next_literal_pool_place)
1208 /* First output the expression in the instruction to the pool */
1209 emit_expr (&(literals[lit_count++].exp), 4); /* .word */
1210
1211 next_literal_pool_place = 0;
1212 current_poolP = NULL;
1213 }
1214
1215 static void
1216 s_align (unused) /* Same as s_align_ptwo but align 0 => align 2 */
1217 int unused;
1218 {
1219 register int temp;
1220 register long temp_fill;
1221 long max_alignment = 15;
1222
1223 temp = get_absolute_expression ();
1224 if (temp > max_alignment)
1225 as_bad (_("Alignment too large: %d. assumed."), temp = max_alignment);
1226 else if (temp < 0)
1227 {
1228 as_bad (_("Alignment negative. 0 assumed."));
1229 temp = 0;
1230 }
1231
1232 if (*input_line_pointer == ',')
1233 {
1234 input_line_pointer++;
1235 temp_fill = get_absolute_expression ();
1236 }
1237 else
1238 temp_fill = 0;
1239
1240 if (!temp)
1241 temp = 2;
1242
1243 /* Only make a frag if we HAVE to. . . */
1244 if (temp && !need_pass_2)
1245 frag_align (temp, (int) temp_fill, 0);
1246 demand_empty_rest_of_line ();
1247
1248 record_alignment (now_seg, temp);
1249 }
1250
1251 static void
1252 s_force_thumb (ignore)
1253 int ignore;
1254 {
1255 /* If we are not already in thumb mode go into it, EVEN if
1256 the target processor does not support thumb instructions.
1257 This is used by gcc/config/arm/lib1funcs.asm for example
1258 to compile interworking support functions even if the
1259 target processor should not support interworking. */
1260
1261 if (! thumb_mode)
1262 {
1263 thumb_mode = 1;
1264
1265 record_alignment (now_seg, 1);
1266 }
1267
1268 demand_empty_rest_of_line ();
1269 }
1270
1271 static void
1272 s_thumb_func (ignore)
1273 int ignore;
1274 {
1275 /* The following label is the name/address of the start of a Thumb function.
1276 We need to know this for the interworking support. */
1277
1278 label_is_thumb_function_name = true;
1279
1280 demand_empty_rest_of_line ();
1281 }
1282
1283 /* Perform a .set directive, but also mark the alias as
1284 being a thumb function. */
1285
1286 static void
1287 s_thumb_set (equiv)
1288 int equiv;
1289 {
1290 /* XXX the following is a duplicate of the code for s_set() in read.c
1291 We cannot just call that code as we need to get at the symbol that
1292 is created. */
1293 register char * name;
1294 register char delim;
1295 register char * end_name;
1296 register symbolS * symbolP;
1297
1298 /*
1299 * Especial apologies for the random logic:
1300 * this just grew, and could be parsed much more simply!
1301 * Dean in haste.
1302 */
1303 name = input_line_pointer;
1304 delim = get_symbol_end ();
1305 end_name = input_line_pointer;
1306 *end_name = delim;
1307
1308 SKIP_WHITESPACE ();
1309
1310 if (*input_line_pointer != ',')
1311 {
1312 *end_name = 0;
1313 as_bad (_("Expected comma after name \"%s\""), name);
1314 *end_name = delim;
1315 ignore_rest_of_line ();
1316 return;
1317 }
1318
1319 input_line_pointer++;
1320 *end_name = 0;
1321
1322 if (name[0] == '.' && name[1] == '\0')
1323 {
1324 /* XXX - this should not happen to .thumb_set */
1325 abort ();
1326 }
1327
1328 if ((symbolP = symbol_find (name)) == NULL
1329 && (symbolP = md_undefined_symbol (name)) == NULL)
1330 {
1331 #ifndef NO_LISTING
1332 /* When doing symbol listings, play games with dummy fragments living
1333 outside the normal fragment chain to record the file and line info
1334 for this symbol. */
1335 if (listing & LISTING_SYMBOLS)
1336 {
1337 extern struct list_info_struct * listing_tail;
1338 fragS * dummy_frag = (fragS *) xmalloc (sizeof(fragS));
1339 memset (dummy_frag, 0, sizeof(fragS));
1340 dummy_frag->fr_type = rs_fill;
1341 dummy_frag->line = listing_tail;
1342 symbolP = symbol_new (name, undefined_section, 0, dummy_frag);
1343 dummy_frag->fr_symbol = symbolP;
1344 }
1345 else
1346 #endif
1347 symbolP = symbol_new (name, undefined_section, 0, &zero_address_frag);
1348
1349 #ifdef OBJ_COFF
1350 /* "set" symbols are local unless otherwise specified. */
1351 SF_SET_LOCAL (symbolP);
1352 #endif /* OBJ_COFF */
1353 } /* make a new symbol */
1354
1355 symbol_table_insert (symbolP);
1356
1357 * end_name = delim;
1358
1359 if (equiv
1360 && S_IS_DEFINED (symbolP)
1361 && S_GET_SEGMENT (symbolP) != reg_section)
1362 as_bad (_("symbol `%s' already defined"), S_GET_NAME (symbolP));
1363
1364 pseudo_set (symbolP);
1365
1366 demand_empty_rest_of_line ();
1367
1368 /* XXX Now we come to the Thumb specific bit of code. */
1369
1370 THUMB_SET_FUNC (symbolP, 1);
1371 ARM_SET_THUMB (symbolP, 1);
1372 #if defined OBJ_ELF || defined OBJ_COFF
1373 ARM_SET_INTERWORK (symbolP, support_interwork);
1374 #endif
1375 }
1376
1377 /* If we change section we must dump the literal pool first. */
1378 static void
1379 arm_s_text (ignore)
1380 int ignore;
1381 {
1382 if (now_seg != text_section)
1383 s_ltorg (0);
1384
1385 s_text (ignore);
1386 }
1387
1388 static void
1389 arm_s_data (ignore)
1390 int ignore;
1391 {
1392 if (flag_readonly_data_in_text)
1393 {
1394 if (now_seg != text_section)
1395 s_ltorg (0);
1396 }
1397 else if (now_seg != data_section)
1398 s_ltorg (0);
1399
1400 s_data (ignore);
1401 }
1402
1403 #ifdef OBJ_ELF
1404 static void
1405 arm_s_section (ignore)
1406 int ignore;
1407 {
1408 s_ltorg (0);
1409
1410 obj_elf_section (ignore);
1411 }
1412 #endif
1413
1414 static void
1415 opcode_select (width)
1416 int width;
1417 {
1418 switch (width)
1419 {
1420 case 16:
1421 if (! thumb_mode)
1422 {
1423 if (! (cpu_variant & ARM_THUMB))
1424 as_bad (_("selected processor does not support THUMB opcodes"));
1425 thumb_mode = 1;
1426 /* No need to force the alignment, since we will have been
1427 coming from ARM mode, which is word-aligned. */
1428 record_alignment (now_seg, 1);
1429 }
1430 break;
1431
1432 case 32:
1433 if (thumb_mode)
1434 {
1435 if ((cpu_variant & ARM_ANY) == ARM_THUMB)
1436 as_bad (_("selected processor does not support ARM opcodes"));
1437 thumb_mode = 0;
1438 if (!need_pass_2)
1439 frag_align (2, 0, 0);
1440 record_alignment (now_seg, 1);
1441 }
1442 break;
1443
1444 default:
1445 as_bad (_("invalid instruction size selected (%d)"), width);
1446 }
1447 }
1448
1449 static void
1450 s_arm (ignore)
1451 int ignore;
1452 {
1453 opcode_select (32);
1454 demand_empty_rest_of_line ();
1455 }
1456
1457 static void
1458 s_thumb (ignore)
1459 int ignore;
1460 {
1461 opcode_select (16);
1462 demand_empty_rest_of_line ();
1463 }
1464
1465 static void
1466 s_code (unused)
1467 int unused;
1468 {
1469 register int temp;
1470
1471 temp = get_absolute_expression ();
1472 switch (temp)
1473 {
1474 case 16:
1475 case 32:
1476 opcode_select (temp);
1477 break;
1478
1479 default:
1480 as_bad (_("invalid operand to .code directive (%d) (expecting 16 or 32)"), temp);
1481 }
1482 }
1483
1484 static void
1485 end_of_line (str)
1486 char * str;
1487 {
1488 skip_whitespace (str);
1489
1490 if (* str != '\0')
1491 inst.error = _("Garbage following instruction");
1492 }
1493
1494 static int
1495 skip_past_comma (str)
1496 char ** str;
1497 {
1498 char *p = *str, c;
1499 int comma = 0;
1500
1501 while ((c = *p) == ' ' || c == ',')
1502 {
1503 p++;
1504 if (c == ',' && comma++)
1505 return FAIL;
1506 }
1507
1508 if (c == '\0')
1509 return FAIL;
1510
1511 *str = p;
1512 return comma ? SUCCESS : FAIL;
1513 }
1514
1515 /* A standard register must be given at this point.
1516 Shift is the place to put it in inst.instruction.
1517 Restores input start point on err.
1518 Returns the reg#, or FAIL. */
1519
1520 static int
1521 reg_required_here (str, shift)
1522 char ** str;
1523 int shift;
1524 {
1525 static char buff [128]; /* XXX */
1526 int reg;
1527 char * start = *str;
1528
1529 if ((reg = arm_reg_parse (str)) != FAIL && int_register (reg))
1530 {
1531 if (shift >= 0)
1532 inst.instruction |= reg << shift;
1533 return reg;
1534 }
1535
1536 /* Restore the start point, we may have got a reg of the wrong class. */
1537 *str = start;
1538
1539 /* In the few cases where we might be able to accept something else
1540 this error can be overridden. */
1541 sprintf (buff, _("Register expected, not '%.100s'"), start);
1542 inst.error = buff;
1543
1544 return FAIL;
1545 }
1546
1547 static int
1548 psr_required_here (str, cpsr, spsr)
1549 char ** str;
1550 int cpsr;
1551 int spsr;
1552 {
1553 int psr;
1554 char * start = *str;
1555 psr = arm_psr_parse (str);
1556
1557 if (psr == cpsr || psr == spsr)
1558 {
1559 if (psr == spsr)
1560 inst.instruction |= 1 << 22;
1561
1562 return SUCCESS;
1563 }
1564
1565 /* In the few cases where we might be able to accept something else
1566 this error can be overridden. */
1567 inst.error = _("<psr(f)> expected");
1568
1569 /* Restore the start point. */
1570 *str = start;
1571 return FAIL;
1572 }
1573
1574 static int
1575 co_proc_number (str)
1576 char ** str;
1577 {
1578 int processor, pchar;
1579
1580 skip_whitespace (* str);
1581
1582 /* The data sheet seems to imply that just a number on its own is valid
1583 here, but the RISC iX assembler seems to accept a prefix 'p'. We will
1584 accept either. */
1585 if (**str == 'p' || **str == 'P')
1586 (*str)++;
1587
1588 pchar = *(*str)++;
1589 if (pchar >= '0' && pchar <= '9')
1590 {
1591 processor = pchar - '0';
1592 if (**str >= '0' && **str <= '9')
1593 {
1594 processor = processor * 10 + *(*str)++ - '0';
1595 if (processor > 15)
1596 {
1597 inst.error = _("Illegal co-processor number");
1598 return FAIL;
1599 }
1600 }
1601 }
1602 else
1603 {
1604 inst.error = _("Bad or missing co-processor number");
1605 return FAIL;
1606 }
1607
1608 inst.instruction |= processor << 8;
1609 return SUCCESS;
1610 }
1611
1612 static int
1613 cp_opc_expr (str, where, length)
1614 char ** str;
1615 int where;
1616 int length;
1617 {
1618 expressionS expr;
1619
1620 skip_whitespace (* str);
1621
1622 memset (&expr, '\0', sizeof (expr));
1623
1624 if (my_get_expression (&expr, str))
1625 return FAIL;
1626 if (expr.X_op != O_constant)
1627 {
1628 inst.error = _("bad or missing expression");
1629 return FAIL;
1630 }
1631
1632 if ((expr.X_add_number & ((1 << length) - 1)) != expr.X_add_number)
1633 {
1634 inst.error = _("immediate co-processor expression too large");
1635 return FAIL;
1636 }
1637
1638 inst.instruction |= expr.X_add_number << where;
1639 return SUCCESS;
1640 }
1641
1642 static int
1643 cp_reg_required_here (str, where)
1644 char ** str;
1645 int where;
1646 {
1647 int reg;
1648 char * start = *str;
1649
1650 if ((reg = arm_reg_parse (str)) != FAIL && cp_register (reg))
1651 {
1652 reg &= 15;
1653 inst.instruction |= reg << where;
1654 return reg;
1655 }
1656
1657 /* In the few cases where we might be able to accept something else
1658 this error can be overridden. */
1659 inst.error = _("Co-processor register expected");
1660
1661 /* Restore the start point. */
1662 *str = start;
1663 return FAIL;
1664 }
1665
1666 static int
1667 fp_reg_required_here (str, where)
1668 char ** str;
1669 int where;
1670 {
1671 int reg;
1672 char * start = *str;
1673
1674 if ((reg = arm_reg_parse (str)) != FAIL && fp_register (reg))
1675 {
1676 reg &= 7;
1677 inst.instruction |= reg << where;
1678 return reg;
1679 }
1680
1681 /* In the few cases where we might be able to accept something else
1682 this error can be overridden. */
1683 inst.error = _("Floating point register expected");
1684
1685 /* Restore the start point. */
1686 *str = start;
1687 return FAIL;
1688 }
1689
1690 static int
1691 cp_address_offset (str)
1692 char ** str;
1693 {
1694 int offset;
1695
1696 skip_whitespace (* str);
1697
1698 if (! is_immediate_prefix (**str))
1699 {
1700 inst.error = _("immediate expression expected");
1701 return FAIL;
1702 }
1703
1704 (*str)++;
1705
1706 if (my_get_expression (& inst.reloc.exp, str))
1707 return FAIL;
1708
1709 if (inst.reloc.exp.X_op == O_constant)
1710 {
1711 offset = inst.reloc.exp.X_add_number;
1712
1713 if (offset & 3)
1714 {
1715 inst.error = _("co-processor address must be word aligned");
1716 return FAIL;
1717 }
1718
1719 if (offset > 1023 || offset < -1023)
1720 {
1721 inst.error = _("offset too large");
1722 return FAIL;
1723 }
1724
1725 if (offset >= 0)
1726 inst.instruction |= INDEX_UP;
1727 else
1728 offset = -offset;
1729
1730 inst.instruction |= offset >> 2;
1731 }
1732 else
1733 inst.reloc.type = BFD_RELOC_ARM_CP_OFF_IMM;
1734
1735 return SUCCESS;
1736 }
1737
1738 static int
1739 cp_address_required_here (str)
1740 char ** str;
1741 {
1742 char * p = * str;
1743 int pre_inc = 0;
1744 int write_back = 0;
1745
1746 if (*p == '[')
1747 {
1748 int reg;
1749
1750 p++;
1751 skip_whitespace (p);
1752
1753 if ((reg = reg_required_here (& p, 16)) == FAIL)
1754 return FAIL;
1755
1756 skip_whitespace (p);
1757
1758 if (*p == ']')
1759 {
1760 p++;
1761
1762 if (skip_past_comma (& p) == SUCCESS)
1763 {
1764 /* [Rn], #expr */
1765 write_back = WRITE_BACK;
1766
1767 if (reg == REG_PC)
1768 {
1769 inst.error = _("pc may not be used in post-increment");
1770 return FAIL;
1771 }
1772
1773 if (cp_address_offset (& p) == FAIL)
1774 return FAIL;
1775 }
1776 else
1777 pre_inc = PRE_INDEX | INDEX_UP;
1778 }
1779 else
1780 {
1781 /* '['Rn, #expr']'[!] */
1782
1783 if (skip_past_comma (& p) == FAIL)
1784 {
1785 inst.error = _("pre-indexed expression expected");
1786 return FAIL;
1787 }
1788
1789 pre_inc = PRE_INDEX;
1790
1791 if (cp_address_offset (& p) == FAIL)
1792 return FAIL;
1793
1794 skip_whitespace (p);
1795
1796 if (*p++ != ']')
1797 {
1798 inst.error = _("missing ]");
1799 return FAIL;
1800 }
1801
1802 skip_whitespace (p);
1803
1804 if (*p == '!')
1805 {
1806 if (reg == REG_PC)
1807 {
1808 inst.error = _("pc may not be used with write-back");
1809 return FAIL;
1810 }
1811
1812 p++;
1813 write_back = WRITE_BACK;
1814 }
1815 }
1816 }
1817 else
1818 {
1819 if (my_get_expression (&inst.reloc.exp, &p))
1820 return FAIL;
1821
1822 inst.reloc.type = BFD_RELOC_ARM_CP_OFF_IMM;
1823 inst.reloc.exp.X_add_number -= 8; /* PC rel adjust */
1824 inst.reloc.pc_rel = 1;
1825 inst.instruction |= (REG_PC << 16);
1826 pre_inc = PRE_INDEX;
1827 }
1828
1829 inst.instruction |= write_back | pre_inc;
1830 *str = p;
1831 return SUCCESS;
1832 }
1833
1834 static void
1835 do_nop (str, flags)
1836 char * str;
1837 unsigned long flags;
1838 {
1839 /* Do nothing really. */
1840 inst.instruction |= flags; /* This is pointless. */
1841 end_of_line (str);
1842 return;
1843 }
1844
1845 static void
1846 do_mrs (str, flags)
1847 char *str;
1848 unsigned long flags;
1849 {
1850 /* Only one syntax. */
1851 skip_whitespace (str);
1852
1853 if (reg_required_here (&str, 12) == FAIL)
1854 {
1855 inst.error = BAD_ARGS;
1856 return;
1857 }
1858
1859 if (skip_past_comma (&str) == FAIL
1860 || psr_required_here (& str, CPSR_ALL, SPSR_ALL) == FAIL)
1861 {
1862 inst.error = _("<psr> expected");
1863 return;
1864 }
1865
1866 inst.instruction |= flags;
1867 end_of_line (str);
1868 return;
1869 }
1870
1871 /* Three possible forms: "<psr>, Rm", "<psrf>, Rm", "<psrf>, #expression". */
1872 static void
1873 do_msr (str, flags)
1874 char * str;
1875 unsigned long flags;
1876 {
1877 int reg;
1878
1879 skip_whitespace (str);
1880
1881 if (psr_required_here (&str, CPSR_ALL, SPSR_ALL) == SUCCESS)
1882 {
1883 inst.instruction |= PSR_ALL;
1884
1885 /* Sytax should be "<psr>, Rm" */
1886 if (skip_past_comma (&str) == FAIL
1887 || (reg = reg_required_here (&str, 0)) == FAIL)
1888 {
1889 inst.error = BAD_ARGS;
1890 return;
1891 }
1892 }
1893 else
1894 {
1895 if (psr_required_here (& str, CPSR_FLG, SPSR_FLG) == SUCCESS)
1896 inst.instruction |= PSR_FLAGS;
1897 else if (psr_required_here (& str, CPSR_CTL, SPSR_CTL) == SUCCESS)
1898 inst.instruction |= PSR_CONTROL;
1899 else
1900 {
1901 inst.error = BAD_ARGS;
1902 return;
1903 }
1904
1905 if (skip_past_comma (&str) == FAIL)
1906 {
1907 inst.error = BAD_ARGS;
1908 return;
1909 }
1910
1911 /* Syntax could be "<psrf>, rm", "<psrf>, #expression" */
1912
1913 if ((reg = reg_required_here (& str, 0)) != FAIL)
1914 ;
1915 /* Immediate expression. */
1916 else if (is_immediate_prefix (* str))
1917 {
1918 str ++;
1919 inst.error = NULL;
1920
1921 if (my_get_expression (& inst.reloc.exp, & str))
1922 {
1923 inst.error = _("Register or shift expression expected");
1924 return;
1925 }
1926
1927 if (inst.reloc.exp.X_add_symbol)
1928 {
1929 inst.reloc.type = BFD_RELOC_ARM_IMMEDIATE;
1930 inst.reloc.pc_rel = 0;
1931 }
1932 else
1933 {
1934 unsigned value = validate_immediate (inst.reloc.exp.X_add_number);
1935 if (value == FAIL)
1936 {
1937 inst.error = _("Invalid constant");
1938 return;
1939 }
1940
1941 inst.instruction |= value;
1942 }
1943
1944 flags |= INST_IMMEDIATE;
1945 }
1946 else
1947 {
1948 inst.error = _("Error: unrecognised syntax for second argument to msr instruction");
1949 return;
1950 }
1951 }
1952
1953 inst.error = NULL;
1954 inst.instruction |= flags;
1955 end_of_line (str);
1956 return;
1957 }
1958
1959 /* Long Multiply Parser
1960 UMULL RdLo, RdHi, Rm, Rs
1961 SMULL RdLo, RdHi, Rm, Rs
1962 UMLAL RdLo, RdHi, Rm, Rs
1963 SMLAL RdLo, RdHi, Rm, Rs
1964 */
1965 static void
1966 do_mull (str, flags)
1967 char * str;
1968 unsigned long flags;
1969 {
1970 int rdlo, rdhi, rm, rs;
1971
1972 /* Only one format "rdlo, rdhi, rm, rs" */
1973 skip_whitespace (str);
1974
1975 if ((rdlo = reg_required_here (&str, 12)) == FAIL)
1976 {
1977 inst.error = BAD_ARGS;
1978 return;
1979 }
1980
1981 if (skip_past_comma (&str) == FAIL
1982 || (rdhi = reg_required_here (&str, 16)) == FAIL)
1983 {
1984 inst.error = BAD_ARGS;
1985 return;
1986 }
1987
1988 if (skip_past_comma (&str) == FAIL
1989 || (rm = reg_required_here (&str, 0)) == FAIL)
1990 {
1991 inst.error = BAD_ARGS;
1992 return;
1993 }
1994
1995 /* rdhi, rdlo and rm must all be different */
1996 if (rdlo == rdhi || rdlo == rm || rdhi == rm)
1997 as_tsktsk (_("rdhi, rdlo and rm must all be different"));
1998
1999 if (skip_past_comma (&str) == FAIL
2000 || (rs = reg_required_here (&str, 8)) == FAIL)
2001 {
2002 inst.error = BAD_ARGS;
2003 return;
2004 }
2005
2006 if (rdhi == REG_PC || rdhi == REG_PC || rdhi == REG_PC || rdhi == REG_PC)
2007 {
2008 inst.error = BAD_PC;
2009 return;
2010 }
2011
2012 inst.instruction |= flags;
2013 end_of_line (str);
2014 return;
2015 }
2016
2017 static void
2018 do_mul (str, flags)
2019 char * str;
2020 unsigned long flags;
2021 {
2022 int rd, rm;
2023
2024 /* Only one format "rd, rm, rs" */
2025 skip_whitespace (str);
2026
2027 if ((rd = reg_required_here (&str, 16)) == FAIL)
2028 {
2029 inst.error = BAD_ARGS;
2030 return;
2031 }
2032
2033 if (rd == REG_PC)
2034 {
2035 inst.error = BAD_PC;
2036 return;
2037 }
2038
2039 if (skip_past_comma (&str) == FAIL
2040 || (rm = reg_required_here (&str, 0)) == FAIL)
2041 {
2042 inst.error = BAD_ARGS;
2043 return;
2044 }
2045
2046 if (rm == REG_PC)
2047 {
2048 inst.error = BAD_PC;
2049 return;
2050 }
2051
2052 if (rm == rd)
2053 as_tsktsk (_("rd and rm should be different in mul"));
2054
2055 if (skip_past_comma (&str) == FAIL
2056 || (rm = reg_required_here (&str, 8)) == FAIL)
2057 {
2058 inst.error = BAD_ARGS;
2059 return;
2060 }
2061
2062 if (rm == REG_PC)
2063 {
2064 inst.error = BAD_PC;
2065 return;
2066 }
2067
2068 inst.instruction |= flags;
2069 end_of_line (str);
2070 return;
2071 }
2072
2073 static void
2074 do_mla (str, flags)
2075 char * str;
2076 unsigned long flags;
2077 {
2078 int rd, rm;
2079
2080 /* Only one format "rd, rm, rs, rn" */
2081 skip_whitespace (str);
2082
2083 if ((rd = reg_required_here (&str, 16)) == FAIL)
2084 {
2085 inst.error = BAD_ARGS;
2086 return;
2087 }
2088
2089 if (rd == REG_PC)
2090 {
2091 inst.error = BAD_PC;
2092 return;
2093 }
2094
2095 if (skip_past_comma (&str) == FAIL
2096 || (rm = reg_required_here (&str, 0)) == FAIL)
2097 {
2098 inst.error = BAD_ARGS;
2099 return;
2100 }
2101
2102 if (rm == REG_PC)
2103 {
2104 inst.error = BAD_PC;
2105 return;
2106 }
2107
2108 if (rm == rd)
2109 as_tsktsk (_("rd and rm should be different in mla"));
2110
2111 if (skip_past_comma (&str) == FAIL
2112 || (rd = reg_required_here (&str, 8)) == FAIL
2113 || skip_past_comma (&str) == FAIL
2114 || (rm = reg_required_here (&str, 12)) == FAIL)
2115 {
2116 inst.error = BAD_ARGS;
2117 return;
2118 }
2119
2120 if (rd == REG_PC || rm == REG_PC)
2121 {
2122 inst.error = BAD_PC;
2123 return;
2124 }
2125
2126 inst.instruction |= flags;
2127 end_of_line (str);
2128 return;
2129 }
2130
2131 /* Returns the index into fp_values of a floating point number, or -1 if
2132 not in the table. */
2133 static int
2134 my_get_float_expression (str)
2135 char ** str;
2136 {
2137 LITTLENUM_TYPE words[MAX_LITTLENUMS];
2138 char * save_in;
2139 expressionS exp;
2140 int i;
2141 int j;
2142
2143 memset (words, 0, MAX_LITTLENUMS * sizeof (LITTLENUM_TYPE));
2144 /* Look for a raw floating point number */
2145 if ((save_in = atof_ieee (*str, 'x', words)) != NULL
2146 && (is_end_of_line [(int)(*save_in)] || *save_in == '\0'))
2147 {
2148 for (i = 0; i < NUM_FLOAT_VALS; i++)
2149 {
2150 for (j = 0; j < MAX_LITTLENUMS; j++)
2151 {
2152 if (words[j] != fp_values[i][j])
2153 break;
2154 }
2155
2156 if (j == MAX_LITTLENUMS)
2157 {
2158 *str = save_in;
2159 return i;
2160 }
2161 }
2162 }
2163
2164 /* Try and parse a more complex expression, this will probably fail
2165 unless the code uses a floating point prefix (eg "0f") */
2166 save_in = input_line_pointer;
2167 input_line_pointer = *str;
2168 if (expression (&exp) == absolute_section
2169 && exp.X_op == O_big
2170 && exp.X_add_number < 0)
2171 {
2172 /* FIXME: 5 = X_PRECISION, should be #define'd where we can use it.
2173 Ditto for 15. */
2174 if (gen_to_words (words, 5, (long)15) == 0)
2175 {
2176 for (i = 0; i < NUM_FLOAT_VALS; i++)
2177 {
2178 for (j = 0; j < MAX_LITTLENUMS; j++)
2179 {
2180 if (words[j] != fp_values[i][j])
2181 break;
2182 }
2183
2184 if (j == MAX_LITTLENUMS)
2185 {
2186 *str = input_line_pointer;
2187 input_line_pointer = save_in;
2188 return i;
2189 }
2190 }
2191 }
2192 }
2193
2194 *str = input_line_pointer;
2195 input_line_pointer = save_in;
2196 return -1;
2197 }
2198
2199 /* Return true if anything in the expression is a bignum */
2200 static int
2201 walk_no_bignums (sp)
2202 symbolS * sp;
2203 {
2204 if (symbol_get_value_expression (sp)->X_op == O_big)
2205 return 1;
2206
2207 if (symbol_get_value_expression (sp)->X_add_symbol)
2208 {
2209 return (walk_no_bignums (symbol_get_value_expression (sp)->X_add_symbol)
2210 || (symbol_get_value_expression (sp)->X_op_symbol
2211 && walk_no_bignums (symbol_get_value_expression (sp)->X_op_symbol)));
2212 }
2213
2214 return 0;
2215 }
2216
2217 static int
2218 my_get_expression (ep, str)
2219 expressionS * ep;
2220 char ** str;
2221 {
2222 char * save_in;
2223 segT seg;
2224
2225 save_in = input_line_pointer;
2226 input_line_pointer = *str;
2227 seg = expression (ep);
2228
2229 #ifdef OBJ_AOUT
2230 if (seg != absolute_section
2231 && seg != text_section
2232 && seg != data_section
2233 && seg != bss_section
2234 && seg != undefined_section)
2235 {
2236 inst.error = _("bad_segment");
2237 *str = input_line_pointer;
2238 input_line_pointer = save_in;
2239 return 1;
2240 }
2241 #endif
2242
2243 /* Get rid of any bignums now, so that we don't generate an error for which
2244 we can't establish a line number later on. Big numbers are never valid
2245 in instructions, which is where this routine is always called. */
2246 if (ep->X_op == O_big
2247 || (ep->X_add_symbol
2248 && (walk_no_bignums (ep->X_add_symbol)
2249 || (ep->X_op_symbol
2250 && walk_no_bignums (ep->X_op_symbol)))))
2251 {
2252 inst.error = _("Invalid constant");
2253 *str = input_line_pointer;
2254 input_line_pointer = save_in;
2255 return 1;
2256 }
2257
2258 *str = input_line_pointer;
2259 input_line_pointer = save_in;
2260 return 0;
2261 }
2262
2263 /* unrestrict should be one if <shift> <register> is permitted for this
2264 instruction */
2265
2266 static int
2267 decode_shift (str, unrestrict)
2268 char ** str;
2269 int unrestrict;
2270 {
2271 struct asm_shift * shft;
2272 char * p;
2273 char c;
2274
2275 skip_whitespace (* str);
2276
2277 for (p = *str; isalpha (*p); p++)
2278 ;
2279
2280 if (p == *str)
2281 {
2282 inst.error = _("Shift expression expected");
2283 return FAIL;
2284 }
2285
2286 c = *p;
2287 *p = '\0';
2288 shft = (struct asm_shift *) hash_find (arm_shift_hsh, *str);
2289 *p = c;
2290 if (shft)
2291 {
2292 if (!strncmp (*str, "rrx", 3)
2293 || !strncmp (*str, "RRX", 3))
2294 {
2295 *str = p;
2296 inst.instruction |= shft->value;
2297 return SUCCESS;
2298 }
2299
2300 skip_whitespace (p);
2301
2302 if (unrestrict && reg_required_here (&p, 8) != FAIL)
2303 {
2304 inst.instruction |= shft->value | SHIFT_BY_REG;
2305 *str = p;
2306 return SUCCESS;
2307 }
2308 else if (is_immediate_prefix (* p))
2309 {
2310 inst.error = NULL;
2311 p++;
2312 if (my_get_expression (&inst.reloc.exp, &p))
2313 return FAIL;
2314
2315 /* Validate some simple #expressions */
2316 if (inst.reloc.exp.X_op == O_constant)
2317 {
2318 unsigned num = inst.reloc.exp.X_add_number;
2319
2320 /* Reject operations greater than 32, or lsl #32 */
2321 if (num > 32 || (num == 32 && shft->value == 0))
2322 {
2323 inst.error = _("Invalid immediate shift");
2324 return FAIL;
2325 }
2326
2327 /* Shifts of zero should be converted to lsl (which is zero)*/
2328 if (num == 0)
2329 {
2330 *str = p;
2331 return SUCCESS;
2332 }
2333
2334 /* Shifts of 32 are encoded as 0, for those shifts that
2335 support it. */
2336 if (num == 32)
2337 num = 0;
2338
2339 inst.instruction |= (num << 7) | shft->value;
2340 *str = p;
2341 return SUCCESS;
2342 }
2343
2344 inst.reloc.type = BFD_RELOC_ARM_SHIFT_IMM;
2345 inst.reloc.pc_rel = 0;
2346 inst.instruction |= shft->value;
2347 *str = p;
2348 return SUCCESS;
2349 }
2350 else
2351 {
2352 inst.error = unrestrict ? _("shift requires register or #expression")
2353 : _("shift requires #expression");
2354 *str = p;
2355 return FAIL;
2356 }
2357 }
2358
2359 inst.error = _("Shift expression expected");
2360 return FAIL;
2361 }
2362
2363 /* Do those data_ops which can take a negative immediate constant */
2364 /* by altering the instuction. A bit of a hack really */
2365 /* MOV <-> MVN
2366 AND <-> BIC
2367 ADC <-> SBC
2368 by inverting the second operand, and
2369 ADD <-> SUB
2370 CMP <-> CMN
2371 by negating the second operand.
2372 */
2373 static int
2374 negate_data_op (instruction, value)
2375 unsigned long * instruction;
2376 unsigned long value;
2377 {
2378 int op, new_inst;
2379 unsigned long negated, inverted;
2380
2381 negated = validate_immediate (-value);
2382 inverted = validate_immediate (~value);
2383
2384 op = (*instruction >> DATA_OP_SHIFT) & 0xf;
2385 switch (op)
2386 {
2387 /* First negates */
2388 case OPCODE_SUB: /* ADD <-> SUB */
2389 new_inst = OPCODE_ADD;
2390 value = negated;
2391 break;
2392
2393 case OPCODE_ADD:
2394 new_inst = OPCODE_SUB;
2395 value = negated;
2396 break;
2397
2398 case OPCODE_CMP: /* CMP <-> CMN */
2399 new_inst = OPCODE_CMN;
2400 value = negated;
2401 break;
2402
2403 case OPCODE_CMN:
2404 new_inst = OPCODE_CMP;
2405 value = negated;
2406 break;
2407
2408 /* Now Inverted ops */
2409 case OPCODE_MOV: /* MOV <-> MVN */
2410 new_inst = OPCODE_MVN;
2411 value = inverted;
2412 break;
2413
2414 case OPCODE_MVN:
2415 new_inst = OPCODE_MOV;
2416 value = inverted;
2417 break;
2418
2419 case OPCODE_AND: /* AND <-> BIC */
2420 new_inst = OPCODE_BIC;
2421 value = inverted;
2422 break;
2423
2424 case OPCODE_BIC:
2425 new_inst = OPCODE_AND;
2426 value = inverted;
2427 break;
2428
2429 case OPCODE_ADC: /* ADC <-> SBC */
2430 new_inst = OPCODE_SBC;
2431 value = inverted;
2432 break;
2433
2434 case OPCODE_SBC:
2435 new_inst = OPCODE_ADC;
2436 value = inverted;
2437 break;
2438
2439 /* We cannot do anything */
2440 default:
2441 return FAIL;
2442 }
2443
2444 if (value == FAIL)
2445 return FAIL;
2446
2447 *instruction &= OPCODE_MASK;
2448 *instruction |= new_inst << DATA_OP_SHIFT;
2449 return value;
2450 }
2451
2452 static int
2453 data_op2 (str)
2454 char ** str;
2455 {
2456 int value;
2457 expressionS expr;
2458
2459 skip_whitespace (* str);
2460
2461 if (reg_required_here (str, 0) != FAIL)
2462 {
2463 if (skip_past_comma (str) == SUCCESS)
2464 /* Shift operation on register. */
2465 return decode_shift (str, NO_SHIFT_RESTRICT);
2466
2467 return SUCCESS;
2468 }
2469 else
2470 {
2471 /* Immediate expression */
2472 if (is_immediate_prefix (**str))
2473 {
2474 (*str)++;
2475 inst.error = NULL;
2476
2477 if (my_get_expression (&inst.reloc.exp, str))
2478 return FAIL;
2479
2480 if (inst.reloc.exp.X_add_symbol)
2481 {
2482 inst.reloc.type = BFD_RELOC_ARM_IMMEDIATE;
2483 inst.reloc.pc_rel = 0;
2484 }
2485 else
2486 {
2487 if (skip_past_comma (str) == SUCCESS)
2488 {
2489 /* #x, y -- ie explicit rotation by Y */
2490 if (my_get_expression (&expr, str))
2491 return FAIL;
2492
2493 if (expr.X_op != O_constant)
2494 {
2495 inst.error = _("Constant expression expected");
2496 return FAIL;
2497 }
2498
2499 /* Rotate must be a multiple of 2 */
2500 if (((unsigned) expr.X_add_number) > 30
2501 || (expr.X_add_number & 1) != 0
2502 || ((unsigned) inst.reloc.exp.X_add_number) > 255)
2503 {
2504 inst.error = _("Invalid constant");
2505 return FAIL;
2506 }
2507 inst.instruction |= INST_IMMEDIATE;
2508 inst.instruction |= inst.reloc.exp.X_add_number;
2509 inst.instruction |= expr.X_add_number << 7;
2510 return SUCCESS;
2511 }
2512
2513 /* Implicit rotation, select a suitable one */
2514 value = validate_immediate (inst.reloc.exp.X_add_number);
2515
2516 if (value == FAIL)
2517 {
2518 /* Can't be done, perhaps the code reads something like
2519 "add Rd, Rn, #-n", where "sub Rd, Rn, #n" would be ok */
2520 if ((value = negate_data_op (&inst.instruction,
2521 inst.reloc.exp.X_add_number))
2522 == FAIL)
2523 {
2524 inst.error = _("Invalid constant");
2525 return FAIL;
2526 }
2527 }
2528
2529 inst.instruction |= value;
2530 }
2531
2532 inst.instruction |= INST_IMMEDIATE;
2533 return SUCCESS;
2534 }
2535
2536 (*str)++;
2537 inst.error = _("Register or shift expression expected");
2538 return FAIL;
2539 }
2540 }
2541
2542 static int
2543 fp_op2 (str)
2544 char ** str;
2545 {
2546 skip_whitespace (* str);
2547
2548 if (fp_reg_required_here (str, 0) != FAIL)
2549 return SUCCESS;
2550 else
2551 {
2552 /* Immediate expression */
2553 if (*((*str)++) == '#')
2554 {
2555 int i;
2556
2557 inst.error = NULL;
2558
2559 skip_whitespace (* str);
2560
2561 /* First try and match exact strings, this is to guarantee that
2562 some formats will work even for cross assembly */
2563
2564 for (i = 0; fp_const[i]; i++)
2565 {
2566 if (strncmp (*str, fp_const[i], strlen (fp_const[i])) == 0)
2567 {
2568 char *start = *str;
2569
2570 *str += strlen (fp_const[i]);
2571 if (is_end_of_line[(int)**str] || **str == '\0')
2572 {
2573 inst.instruction |= i + 8;
2574 return SUCCESS;
2575 }
2576 *str = start;
2577 }
2578 }
2579
2580 /* Just because we didn't get a match doesn't mean that the
2581 constant isn't valid, just that it is in a format that we
2582 don't automatically recognize. Try parsing it with
2583 the standard expression routines. */
2584 if ((i = my_get_float_expression (str)) >= 0)
2585 {
2586 inst.instruction |= i + 8;
2587 return SUCCESS;
2588 }
2589
2590 inst.error = _("Invalid floating point immediate expression");
2591 return FAIL;
2592 }
2593 inst.error = _("Floating point register or immediate expression expected");
2594 return FAIL;
2595 }
2596 }
2597
2598 static void
2599 do_arit (str, flags)
2600 char * str;
2601 unsigned long flags;
2602 {
2603 skip_whitespace (str);
2604
2605 if (reg_required_here (&str, 12) == FAIL
2606 || skip_past_comma (&str) == FAIL
2607 || reg_required_here (&str, 16) == FAIL
2608 || skip_past_comma (&str) == FAIL
2609 || data_op2 (&str) == FAIL)
2610 {
2611 if (!inst.error)
2612 inst.error = BAD_ARGS;
2613 return;
2614 }
2615
2616 inst.instruction |= flags;
2617 end_of_line (str);
2618 return;
2619 }
2620
2621 static void
2622 do_adr (str, flags)
2623 char * str;
2624 unsigned long flags;
2625 {
2626 /* This is a pseudo-op of the form "adr rd, label" to be converted
2627 into a relative address of the form "add rd, pc, #label-.-8" */
2628
2629 skip_whitespace (str);
2630
2631 if (reg_required_here (&str, 12) == FAIL
2632 || skip_past_comma (&str) == FAIL
2633 || my_get_expression (&inst.reloc.exp, &str))
2634 {
2635 if (!inst.error)
2636 inst.error = BAD_ARGS;
2637 return;
2638 }
2639 /* Frag hacking will turn this into a sub instruction if the offset turns
2640 out to be negative. */
2641 inst.reloc.type = BFD_RELOC_ARM_IMMEDIATE;
2642 inst.reloc.exp.X_add_number -= 8; /* PC relative adjust */
2643 inst.reloc.pc_rel = 1;
2644 inst.instruction |= flags;
2645 end_of_line (str);
2646 return;
2647 }
2648
2649 static void
2650 do_adrl (str, flags)
2651 char * str;
2652 unsigned long flags;
2653 {
2654 /* This is a pseudo-op of the form "adrl rd, label" to be converted
2655 into a relative address of the form:
2656 add rd, pc, #low(label-.-8)"
2657 add rd, rd, #high(label-.-8)" */
2658
2659 skip_whitespace (str);
2660
2661 if (reg_required_here (& str, 12) == FAIL
2662 || skip_past_comma (& str) == FAIL
2663 || my_get_expression (& inst.reloc.exp, & str))
2664 {
2665 if (!inst.error)
2666 inst.error = BAD_ARGS;
2667 return;
2668 }
2669
2670 end_of_line (str);
2671
2672 /* Frag hacking will turn this into a sub instruction if the offset turns
2673 out to be negative. */
2674 inst.reloc.type = BFD_RELOC_ARM_ADRL_IMMEDIATE;
2675 inst.reloc.exp.X_add_number -= 8; /* PC relative adjust */
2676 inst.reloc.pc_rel = 1;
2677 inst.instruction |= flags;
2678 inst.size = INSN_SIZE * 2;
2679
2680 return;
2681 }
2682
2683 static void
2684 do_cmp (str, flags)
2685 char * str;
2686 unsigned long flags;
2687 {
2688 skip_whitespace (str);
2689
2690 if (reg_required_here (&str, 16) == FAIL)
2691 {
2692 if (!inst.error)
2693 inst.error = BAD_ARGS;
2694 return;
2695 }
2696
2697 if (skip_past_comma (&str) == FAIL
2698 || data_op2 (&str) == FAIL)
2699 {
2700 if (!inst.error)
2701 inst.error = BAD_ARGS;
2702 return;
2703 }
2704
2705 inst.instruction |= flags;
2706 if ((flags & 0x0000f000) == 0)
2707 inst.instruction |= CONDS_BIT;
2708
2709 end_of_line (str);
2710 return;
2711 }
2712
2713 static void
2714 do_mov (str, flags)
2715 char * str;
2716 unsigned long flags;
2717 {
2718 skip_whitespace (str);
2719
2720 if (reg_required_here (&str, 12) == FAIL)
2721 {
2722 if (!inst.error)
2723 inst.error = BAD_ARGS;
2724 return;
2725 }
2726
2727 if (skip_past_comma (&str) == FAIL
2728 || data_op2 (&str) == FAIL)
2729 {
2730 if (!inst.error)
2731 inst.error = BAD_ARGS;
2732 return;
2733 }
2734
2735 inst.instruction |= flags;
2736 end_of_line (str);
2737 return;
2738 }
2739
2740 static int
2741 ldst_extend (str, hwse)
2742 char ** str;
2743 int hwse;
2744 {
2745 int add = INDEX_UP;
2746
2747 switch (**str)
2748 {
2749 case '#':
2750 case '$':
2751 (*str)++;
2752 if (my_get_expression (& inst.reloc.exp, str))
2753 return FAIL;
2754
2755 if (inst.reloc.exp.X_op == O_constant)
2756 {
2757 int value = inst.reloc.exp.X_add_number;
2758
2759 if ((hwse && (value < -255 || value > 255))
2760 || (value < -4095 || value > 4095))
2761 {
2762 inst.error = _("address offset too large");
2763 return FAIL;
2764 }
2765
2766 if (value < 0)
2767 {
2768 value = -value;
2769 add = 0;
2770 }
2771
2772 /* Halfword and signextension instructions have the
2773 immediate value split across bits 11..8 and bits 3..0 */
2774 if (hwse)
2775 inst.instruction |= add | HWOFFSET_IMM | ((value >> 4) << 8) | (value & 0xF);
2776 else
2777 inst.instruction |= add | value;
2778 }
2779 else
2780 {
2781 if (hwse)
2782 {
2783 inst.instruction |= HWOFFSET_IMM;
2784 inst.reloc.type = BFD_RELOC_ARM_OFFSET_IMM8;
2785 }
2786 else
2787 inst.reloc.type = BFD_RELOC_ARM_OFFSET_IMM;
2788 inst.reloc.pc_rel = 0;
2789 }
2790 return SUCCESS;
2791
2792 case '-':
2793 add = 0; /* and fall through */
2794 case '+':
2795 (*str)++; /* and fall through */
2796 default:
2797 if (reg_required_here (str, 0) == FAIL)
2798 return FAIL;
2799
2800 if (hwse)
2801 inst.instruction |= add;
2802 else
2803 {
2804 inst.instruction |= add | OFFSET_REG;
2805 if (skip_past_comma (str) == SUCCESS)
2806 return decode_shift (str, SHIFT_RESTRICT);
2807 }
2808
2809 return SUCCESS;
2810 }
2811 }
2812
2813 static void
2814 do_ldst (str, flags)
2815 char * str;
2816 unsigned long flags;
2817 {
2818 int halfword = 0;
2819 int pre_inc = 0;
2820 int conflict_reg;
2821 int value;
2822
2823 /* This is not ideal, but it is the simplest way of dealing with the
2824 ARM7T halfword instructions (since they use a different
2825 encoding, but the same mnemonic): */
2826 halfword = (flags & 0x80000000) != 0;
2827 if (halfword)
2828 {
2829 /* This is actually a load/store of a halfword, or a
2830 signed-extension load */
2831 if ((cpu_variant & ARM_HALFWORD) == 0)
2832 {
2833 inst.error
2834 = _("Processor does not support halfwords or signed bytes");
2835 return;
2836 }
2837
2838 inst.instruction = (inst.instruction & COND_MASK)
2839 | (flags & ~COND_MASK);
2840
2841 flags = 0;
2842 }
2843
2844 skip_whitespace (str);
2845
2846 if ((conflict_reg = reg_required_here (& str, 12)) == FAIL)
2847 {
2848 if (!inst.error)
2849 inst.error = BAD_ARGS;
2850 return;
2851 }
2852
2853 if (skip_past_comma (& str) == FAIL)
2854 {
2855 inst.error = _("Address expected");
2856 return;
2857 }
2858
2859 if (*str == '[')
2860 {
2861 int reg;
2862
2863 str++;
2864
2865 skip_whitespace (str);
2866
2867 if ((reg = reg_required_here (&str, 16)) == FAIL)
2868 return;
2869
2870 /* Conflicts can occur on stores as well as loads. */
2871 conflict_reg = (conflict_reg == reg);
2872
2873 skip_whitespace (str);
2874
2875 if (*str == ']')
2876 {
2877 str ++;
2878
2879 if (skip_past_comma (&str) == SUCCESS)
2880 {
2881 /* [Rn],... (post inc) */
2882 if (ldst_extend (&str, halfword) == FAIL)
2883 return;
2884 if (conflict_reg)
2885 as_warn (_("%s register same as write-back base"),
2886 (inst.instruction & LOAD_BIT) ? _("destination") : _("source") );
2887 }
2888 else
2889 {
2890 /* [Rn] */
2891 if (halfword)
2892 inst.instruction |= HWOFFSET_IMM;
2893
2894 skip_whitespace (str);
2895
2896 if (*str == '!')
2897 {
2898 if (conflict_reg)
2899 as_warn (_("%s register same as write-back base"),
2900 (inst.instruction & LOAD_BIT) ? _("destination") : _("source") );
2901 str++;
2902 inst.instruction |= WRITE_BACK;
2903 }
2904
2905 flags |= INDEX_UP;
2906 if (! (flags & TRANS_BIT))
2907 pre_inc = 1;
2908 }
2909 }
2910 else
2911 {
2912 /* [Rn,...] */
2913 if (skip_past_comma (&str) == FAIL)
2914 {
2915 inst.error = _("pre-indexed expression expected");
2916 return;
2917 }
2918
2919 pre_inc = 1;
2920 if (ldst_extend (&str, halfword) == FAIL)
2921 return;
2922
2923 skip_whitespace (str);
2924
2925 if (*str++ != ']')
2926 {
2927 inst.error = _("missing ]");
2928 return;
2929 }
2930
2931 skip_whitespace (str);
2932
2933 if (*str == '!')
2934 {
2935 if (conflict_reg)
2936 as_warn (_("%s register same as write-back base"),
2937 (inst.instruction & LOAD_BIT) ? _("destination") : _("source") );
2938 str++;
2939 inst.instruction |= WRITE_BACK;
2940 }
2941 }
2942 }
2943 else if (*str == '=')
2944 {
2945 /* Parse an "ldr Rd, =expr" instruction; this is another pseudo op */
2946 str++;
2947
2948 skip_whitespace (str);
2949
2950 if (my_get_expression (&inst.reloc.exp, &str))
2951 return;
2952
2953 if (inst.reloc.exp.X_op != O_constant
2954 && inst.reloc.exp.X_op != O_symbol)
2955 {
2956 inst.error = _("Constant expression expected");
2957 return;
2958 }
2959
2960 if (inst.reloc.exp.X_op == O_constant
2961 && (value = validate_immediate(inst.reloc.exp.X_add_number)) != FAIL)
2962 {
2963 /* This can be done with a mov instruction */
2964 inst.instruction &= LITERAL_MASK;
2965 inst.instruction |= INST_IMMEDIATE | (OPCODE_MOV << DATA_OP_SHIFT);
2966 inst.instruction |= (flags & COND_MASK) | (value & 0xfff);
2967 end_of_line(str);
2968 return;
2969 }
2970 else
2971 {
2972 /* Insert into literal pool */
2973 if (add_to_lit_pool () == FAIL)
2974 {
2975 if (!inst.error)
2976 inst.error = _("literal pool insertion failed");
2977 return;
2978 }
2979
2980 /* Change the instruction exp to point to the pool */
2981 if (halfword)
2982 {
2983 inst.instruction |= HWOFFSET_IMM;
2984 inst.reloc.type = BFD_RELOC_ARM_HWLITERAL;
2985 }
2986 else
2987 inst.reloc.type = BFD_RELOC_ARM_LITERAL;
2988 inst.reloc.pc_rel = 1;
2989 inst.instruction |= (REG_PC << 16);
2990 pre_inc = 1;
2991 }
2992 }
2993 else
2994 {
2995 if (my_get_expression (&inst.reloc.exp, &str))
2996 return;
2997
2998 if (halfword)
2999 {
3000 inst.instruction |= HWOFFSET_IMM;
3001 inst.reloc.type = BFD_RELOC_ARM_OFFSET_IMM8;
3002 }
3003 else
3004 inst.reloc.type = BFD_RELOC_ARM_OFFSET_IMM;
3005 inst.reloc.exp.X_add_number -= 8; /* PC rel adjust */
3006 inst.reloc.pc_rel = 1;
3007 inst.instruction |= (REG_PC << 16);
3008 pre_inc = 1;
3009 }
3010
3011 if (pre_inc && (flags & TRANS_BIT))
3012 inst.error = _("Pre-increment instruction with translate");
3013
3014 inst.instruction |= flags | (pre_inc ? PRE_INDEX : 0);
3015 end_of_line (str);
3016 return;
3017 }
3018
3019 static long
3020 reg_list (strp)
3021 char ** strp;
3022 {
3023 char * str = *strp;
3024 long range = 0;
3025 int another_range;
3026
3027 /* We come back here if we get ranges concatenated by '+' or '|' */
3028 do
3029 {
3030 another_range = 0;
3031
3032 if (*str == '{')
3033 {
3034 int in_range = 0;
3035 int cur_reg = -1;
3036
3037 str++;
3038 do
3039 {
3040 int reg;
3041
3042 skip_whitespace (str);
3043
3044 if ((reg = reg_required_here (& str, -1)) == FAIL)
3045 return FAIL;
3046
3047 if (in_range)
3048 {
3049 int i;
3050
3051 if (reg <= cur_reg)
3052 {
3053 inst.error = _("Bad range in register list");
3054 return FAIL;
3055 }
3056
3057 for (i = cur_reg + 1; i < reg; i++)
3058 {
3059 if (range & (1 << i))
3060 as_tsktsk
3061 (_("Warning: Duplicated register (r%d) in register list"),
3062 i);
3063 else
3064 range |= 1 << i;
3065 }
3066 in_range = 0;
3067 }
3068
3069 if (range & (1 << reg))
3070 as_tsktsk (_("Warning: Duplicated register (r%d) in register list"),
3071 reg);
3072 else if (reg <= cur_reg)
3073 as_tsktsk (_("Warning: Register range not in ascending order"));
3074
3075 range |= 1 << reg;
3076 cur_reg = reg;
3077 } while (skip_past_comma (&str) != FAIL
3078 || (in_range = 1, *str++ == '-'));
3079 str--;
3080 skip_whitespace (str);
3081
3082 if (*str++ != '}')
3083 {
3084 inst.error = _("Missing `}'");
3085 return FAIL;
3086 }
3087 }
3088 else
3089 {
3090 expressionS expr;
3091
3092 if (my_get_expression (&expr, &str))
3093 return FAIL;
3094
3095 if (expr.X_op == O_constant)
3096 {
3097 if (expr.X_add_number
3098 != (expr.X_add_number & 0x0000ffff))
3099 {
3100 inst.error = _("invalid register mask");
3101 return FAIL;
3102 }
3103
3104 if ((range & expr.X_add_number) != 0)
3105 {
3106 int regno = range & expr.X_add_number;
3107
3108 regno &= -regno;
3109 regno = (1 << regno) - 1;
3110 as_tsktsk
3111 (_("Warning: Duplicated register (r%d) in register list"),
3112 regno);
3113 }
3114
3115 range |= expr.X_add_number;
3116 }
3117 else
3118 {
3119 if (inst.reloc.type != 0)
3120 {
3121 inst.error = _("expression too complex");
3122 return FAIL;
3123 }
3124
3125 memcpy (&inst.reloc.exp, &expr, sizeof (expressionS));
3126 inst.reloc.type = BFD_RELOC_ARM_MULTI;
3127 inst.reloc.pc_rel = 0;
3128 }
3129 }
3130
3131 skip_whitespace (str);
3132
3133 if (*str == '|' || *str == '+')
3134 {
3135 str++;
3136 another_range = 1;
3137 }
3138 } while (another_range);
3139
3140 *strp = str;
3141 return range;
3142 }
3143
3144 static void
3145 do_ldmstm (str, flags)
3146 char * str;
3147 unsigned long flags;
3148 {
3149 int base_reg;
3150 long range;
3151
3152 skip_whitespace (str);
3153
3154 if ((base_reg = reg_required_here (&str, 16)) == FAIL)
3155 return;
3156
3157 if (base_reg == REG_PC)
3158 {
3159 inst.error = _("r15 not allowed as base register");
3160 return;
3161 }
3162
3163 skip_whitespace (str);
3164
3165 if (*str == '!')
3166 {
3167 flags |= WRITE_BACK;
3168 str++;
3169 }
3170
3171 if (skip_past_comma (&str) == FAIL
3172 || (range = reg_list (&str)) == FAIL)
3173 {
3174 if (! inst.error)
3175 inst.error = BAD_ARGS;
3176 return;
3177 }
3178
3179 if (*str == '^')
3180 {
3181 str++;
3182 flags |= LDM_TYPE_2_OR_3;
3183 }
3184
3185 inst.instruction |= flags | range;
3186 end_of_line (str);
3187 return;
3188 }
3189
3190 static void
3191 do_swi (str, flags)
3192 char * str;
3193 unsigned long flags;
3194 {
3195 skip_whitespace (str);
3196
3197 /* Allow optional leading '#'. */
3198 if (is_immediate_prefix (*str))
3199 str++;
3200
3201 if (my_get_expression (& inst.reloc.exp, & str))
3202 return;
3203
3204 inst.reloc.type = BFD_RELOC_ARM_SWI;
3205 inst.reloc.pc_rel = 0;
3206 inst.instruction |= flags;
3207
3208 end_of_line (str);
3209
3210 return;
3211 }
3212
3213 static void
3214 do_swap (str, flags)
3215 char * str;
3216 unsigned long flags;
3217 {
3218 int reg;
3219
3220 skip_whitespace (str);
3221
3222 if ((reg = reg_required_here (&str, 12)) == FAIL)
3223 return;
3224
3225 if (reg == REG_PC)
3226 {
3227 inst.error = _("r15 not allowed in swap");
3228 return;
3229 }
3230
3231 if (skip_past_comma (&str) == FAIL
3232 || (reg = reg_required_here (&str, 0)) == FAIL)
3233 {
3234 if (!inst.error)
3235 inst.error = BAD_ARGS;
3236 return;
3237 }
3238
3239 if (reg == REG_PC)
3240 {
3241 inst.error = _("r15 not allowed in swap");
3242 return;
3243 }
3244
3245 if (skip_past_comma (&str) == FAIL
3246 || *str++ != '[')
3247 {
3248 inst.error = BAD_ARGS;
3249 return;
3250 }
3251
3252 skip_whitespace (str);
3253
3254 if ((reg = reg_required_here (&str, 16)) == FAIL)
3255 return;
3256
3257 if (reg == REG_PC)
3258 {
3259 inst.error = BAD_PC;
3260 return;
3261 }
3262
3263 skip_whitespace (str);
3264
3265 if (*str++ != ']')
3266 {
3267 inst.error = _("missing ]");
3268 return;
3269 }
3270
3271 inst.instruction |= flags;
3272 end_of_line (str);
3273 return;
3274 }
3275
3276 static void
3277 do_branch (str, flags)
3278 char * str;
3279 unsigned long flags;
3280 {
3281 if (my_get_expression (&inst.reloc.exp, &str))
3282 return;
3283
3284 #ifdef OBJ_ELF
3285 {
3286 char * save_in;
3287
3288 /* ScottB: February 5, 1998 */
3289 /* Check to see of PLT32 reloc required for the instruction. */
3290
3291 /* arm_parse_reloc() works on input_line_pointer.
3292 We actually want to parse the operands to the branch instruction
3293 passed in 'str'. Save the input pointer and restore it later. */
3294 save_in = input_line_pointer;
3295 input_line_pointer = str;
3296 if (inst.reloc.exp.X_op == O_symbol
3297 && *str == '('
3298 && arm_parse_reloc () == BFD_RELOC_ARM_PLT32)
3299 {
3300 inst.reloc.type = BFD_RELOC_ARM_PLT32;
3301 inst.reloc.pc_rel = 0;
3302 /* Modify str to point to after parsed operands, otherwise
3303 end_of_line() will complain about the (PLT) left in str. */
3304 str = input_line_pointer;
3305 }
3306 else
3307 {
3308 inst.reloc.type = BFD_RELOC_ARM_PCREL_BRANCH;
3309 inst.reloc.pc_rel = 1;
3310 }
3311 input_line_pointer = save_in;
3312 }
3313 #else
3314 inst.reloc.type = BFD_RELOC_ARM_PCREL_BRANCH;
3315 inst.reloc.pc_rel = 1;
3316 #endif /* OBJ_ELF */
3317
3318 end_of_line (str);
3319 return;
3320 }
3321
3322 static void
3323 do_bx (str, flags)
3324 char * str;
3325 unsigned long flags;
3326 {
3327 int reg;
3328
3329 skip_whitespace (str);
3330
3331 if ((reg = reg_required_here (&str, 0)) == FAIL)
3332 {
3333 inst.error = BAD_ARGS;
3334 return;
3335 }
3336
3337 if (reg == REG_PC)
3338 inst.error = BAD_PC;
3339
3340 end_of_line (str);
3341 }
3342
3343 static void
3344 do_cdp (str, flags)
3345 char * str;
3346 unsigned long flags;
3347 {
3348 /* Co-processor data operation.
3349 Format: CDP{cond} CP#,<expr>,CRd,CRn,CRm{,<expr>} */
3350 skip_whitespace (str);
3351
3352 if (co_proc_number (&str) == FAIL)
3353 {
3354 if (!inst.error)
3355 inst.error = BAD_ARGS;
3356 return;
3357 }
3358
3359 if (skip_past_comma (&str) == FAIL
3360 || cp_opc_expr (&str, 20,4) == FAIL)
3361 {
3362 if (!inst.error)
3363 inst.error = BAD_ARGS;
3364 return;
3365 }
3366
3367 if (skip_past_comma (&str) == FAIL
3368 || cp_reg_required_here (&str, 12) == FAIL)
3369 {
3370 if (!inst.error)
3371 inst.error = BAD_ARGS;
3372 return;
3373 }
3374
3375 if (skip_past_comma (&str) == FAIL
3376 || cp_reg_required_here (&str, 16) == FAIL)
3377 {
3378 if (!inst.error)
3379 inst.error = BAD_ARGS;
3380 return;
3381 }
3382
3383 if (skip_past_comma (&str) == FAIL
3384 || cp_reg_required_here (&str, 0) == FAIL)
3385 {
3386 if (!inst.error)
3387 inst.error = BAD_ARGS;
3388 return;
3389 }
3390
3391 if (skip_past_comma (&str) == SUCCESS)
3392 {
3393 if (cp_opc_expr (&str, 5, 3) == FAIL)
3394 {
3395 if (!inst.error)
3396 inst.error = BAD_ARGS;
3397 return;
3398 }
3399 }
3400
3401 end_of_line (str);
3402 return;
3403 }
3404
3405 static void
3406 do_lstc (str, flags)
3407 char * str;
3408 unsigned long flags;
3409 {
3410 /* Co-processor register load/store.
3411 Format: <LDC|STC{cond}[L] CP#,CRd,<address> */
3412
3413 skip_whitespace (str);
3414
3415 if (co_proc_number (&str) == FAIL)
3416 {
3417 if (!inst.error)
3418 inst.error = BAD_ARGS;
3419 return;
3420 }
3421
3422 if (skip_past_comma (&str) == FAIL
3423 || cp_reg_required_here (&str, 12) == FAIL)
3424 {
3425 if (!inst.error)
3426 inst.error = BAD_ARGS;
3427 return;
3428 }
3429
3430 if (skip_past_comma (&str) == FAIL
3431 || cp_address_required_here (&str) == FAIL)
3432 {
3433 if (! inst.error)
3434 inst.error = BAD_ARGS;
3435 return;
3436 }
3437
3438 inst.instruction |= flags;
3439 end_of_line (str);
3440 return;
3441 }
3442
3443 static void
3444 do_co_reg (str, flags)
3445 char * str;
3446 unsigned long flags;
3447 {
3448 /* Co-processor register transfer.
3449 Format: <MCR|MRC>{cond} CP#,<expr1>,Rd,CRn,CRm{,<expr2>} */
3450
3451 skip_whitespace (str);
3452
3453 if (co_proc_number (&str) == FAIL)
3454 {
3455 if (!inst.error)
3456 inst.error = BAD_ARGS;
3457 return;
3458 }
3459
3460 if (skip_past_comma (&str) == FAIL
3461 || cp_opc_expr (&str, 21, 3) == FAIL)
3462 {
3463 if (!inst.error)
3464 inst.error = BAD_ARGS;
3465 return;
3466 }
3467
3468 if (skip_past_comma (&str) == FAIL
3469 || reg_required_here (&str, 12) == FAIL)
3470 {
3471 if (!inst.error)
3472 inst.error = BAD_ARGS;
3473 return;
3474 }
3475
3476 if (skip_past_comma (&str) == FAIL
3477 || cp_reg_required_here (&str, 16) == FAIL)
3478 {
3479 if (!inst.error)
3480 inst.error = BAD_ARGS;
3481 return;
3482 }
3483
3484 if (skip_past_comma (&str) == FAIL
3485 || cp_reg_required_here (&str, 0) == FAIL)
3486 {
3487 if (!inst.error)
3488 inst.error = BAD_ARGS;
3489 return;
3490 }
3491
3492 if (skip_past_comma (&str) == SUCCESS)
3493 {
3494 if (cp_opc_expr (&str, 5, 3) == FAIL)
3495 {
3496 if (!inst.error)
3497 inst.error = BAD_ARGS;
3498 return;
3499 }
3500 }
3501 if (flags)
3502 {
3503 inst.error = BAD_COND;
3504 }
3505
3506 end_of_line (str);
3507 return;
3508 }
3509
3510 static void
3511 do_fp_ctrl (str, flags)
3512 char * str;
3513 unsigned long flags;
3514 {
3515 /* FP control registers.
3516 Format: <WFS|RFS|WFC|RFC>{cond} Rn */
3517
3518 skip_whitespace (str);
3519
3520 if (reg_required_here (&str, 12) == FAIL)
3521 {
3522 if (!inst.error)
3523 inst.error = BAD_ARGS;
3524 return;
3525 }
3526
3527 end_of_line (str);
3528 return;
3529 }
3530
3531 static void
3532 do_fp_ldst (str, flags)
3533 char * str;
3534 unsigned long flags;
3535 {
3536 skip_whitespace (str);
3537
3538 switch (inst.suffix)
3539 {
3540 case SUFF_S:
3541 break;
3542 case SUFF_D:
3543 inst.instruction |= CP_T_X;
3544 break;
3545 case SUFF_E:
3546 inst.instruction |= CP_T_Y;
3547 break;
3548 case SUFF_P:
3549 inst.instruction |= CP_T_X | CP_T_Y;
3550 break;
3551 default:
3552 abort ();
3553 }
3554
3555 if (fp_reg_required_here (&str, 12) == FAIL)
3556 {
3557 if (!inst.error)
3558 inst.error = BAD_ARGS;
3559 return;
3560 }
3561
3562 if (skip_past_comma (&str) == FAIL
3563 || cp_address_required_here (&str) == FAIL)
3564 {
3565 if (!inst.error)
3566 inst.error = BAD_ARGS;
3567 return;
3568 }
3569
3570 end_of_line (str);
3571 }
3572
3573 static void
3574 do_fp_ldmstm (str, flags)
3575 char * str;
3576 unsigned long flags;
3577 {
3578 int num_regs;
3579
3580 skip_whitespace (str);
3581
3582 if (fp_reg_required_here (&str, 12) == FAIL)
3583 {
3584 if (! inst.error)
3585 inst.error = BAD_ARGS;
3586 return;
3587 }
3588
3589 /* Get Number of registers to transfer */
3590 if (skip_past_comma (&str) == FAIL
3591 || my_get_expression (&inst.reloc.exp, &str))
3592 {
3593 if (! inst.error)
3594 inst.error = _("constant expression expected");
3595 return;
3596 }
3597
3598 if (inst.reloc.exp.X_op != O_constant)
3599 {
3600 inst.error = _("Constant value required for number of registers");
3601 return;
3602 }
3603
3604 num_regs = inst.reloc.exp.X_add_number;
3605
3606 if (num_regs < 1 || num_regs > 4)
3607 {
3608 inst.error = _("number of registers must be in the range [1:4]");
3609 return;
3610 }
3611
3612 switch (num_regs)
3613 {
3614 case 1:
3615 inst.instruction |= CP_T_X;
3616 break;
3617 case 2:
3618 inst.instruction |= CP_T_Y;
3619 break;
3620 case 3:
3621 inst.instruction |= CP_T_Y | CP_T_X;
3622 break;
3623 case 4:
3624 break;
3625 default:
3626 abort ();
3627 }
3628
3629 if (flags)
3630 {
3631 int reg;
3632 int write_back;
3633 int offset;
3634
3635 /* The instruction specified "ea" or "fd", so we can only accept
3636 [Rn]{!}. The instruction does not really support stacking or
3637 unstacking, so we have to emulate these by setting appropriate
3638 bits and offsets. */
3639 if (skip_past_comma (&str) == FAIL
3640 || *str != '[')
3641 {
3642 if (! inst.error)
3643 inst.error = BAD_ARGS;
3644 return;
3645 }
3646
3647 str++;
3648 skip_whitespace (str);
3649
3650 if ((reg = reg_required_here (&str, 16)) == FAIL)
3651 return;
3652
3653 skip_whitespace (str);
3654
3655 if (*str != ']')
3656 {
3657 inst.error = BAD_ARGS;
3658 return;
3659 }
3660
3661 str++;
3662 if (*str == '!')
3663 {
3664 write_back = 1;
3665 str++;
3666 if (reg == REG_PC)
3667 {
3668 inst.error = _("R15 not allowed as base register with write-back");
3669 return;
3670 }
3671 }
3672 else
3673 write_back = 0;
3674
3675 if (flags & CP_T_Pre)
3676 {
3677 /* Pre-decrement */
3678 offset = 3 * num_regs;
3679 if (write_back)
3680 flags |= CP_T_WB;
3681 }
3682 else
3683 {
3684 /* Post-increment */
3685 if (write_back)
3686 {
3687 flags |= CP_T_WB;
3688 offset = 3 * num_regs;
3689 }
3690 else
3691 {
3692 /* No write-back, so convert this into a standard pre-increment
3693 instruction -- aesthetically more pleasing. */
3694 flags = CP_T_Pre | CP_T_UD;
3695 offset = 0;
3696 }
3697 }
3698
3699 inst.instruction |= flags | offset;
3700 }
3701 else if (skip_past_comma (&str) == FAIL
3702 || cp_address_required_here (&str) == FAIL)
3703 {
3704 if (! inst.error)
3705 inst.error = BAD_ARGS;
3706 return;
3707 }
3708
3709 end_of_line (str);
3710 }
3711
3712 static void
3713 do_fp_dyadic (str, flags)
3714 char * str;
3715 unsigned long flags;
3716 {
3717 skip_whitespace (str);
3718
3719 switch (inst.suffix)
3720 {
3721 case SUFF_S:
3722 break;
3723 case SUFF_D:
3724 inst.instruction |= 0x00000080;
3725 break;
3726 case SUFF_E:
3727 inst.instruction |= 0x00080000;
3728 break;
3729 default:
3730 abort ();
3731 }
3732
3733 if (fp_reg_required_here (&str, 12) == FAIL)
3734 {
3735 if (! inst.error)
3736 inst.error = BAD_ARGS;
3737 return;
3738 }
3739
3740 if (skip_past_comma (&str) == FAIL
3741 || fp_reg_required_here (&str, 16) == FAIL)
3742 {
3743 if (! inst.error)
3744 inst.error = BAD_ARGS;
3745 return;
3746 }
3747
3748 if (skip_past_comma (&str) == FAIL
3749 || fp_op2 (&str) == FAIL)
3750 {
3751 if (! inst.error)
3752 inst.error = BAD_ARGS;
3753 return;
3754 }
3755
3756 inst.instruction |= flags;
3757 end_of_line (str);
3758 return;
3759 }
3760
3761 static void
3762 do_fp_monadic (str, flags)
3763 char * str;
3764 unsigned long flags;
3765 {
3766 skip_whitespace (str);
3767
3768 switch (inst.suffix)
3769 {
3770 case SUFF_S:
3771 break;
3772 case SUFF_D:
3773 inst.instruction |= 0x00000080;
3774 break;
3775 case SUFF_E:
3776 inst.instruction |= 0x00080000;
3777 break;
3778 default:
3779 abort ();
3780 }
3781
3782 if (fp_reg_required_here (&str, 12) == FAIL)
3783 {
3784 if (! inst.error)
3785 inst.error = BAD_ARGS;
3786 return;
3787 }
3788
3789 if (skip_past_comma (&str) == FAIL
3790 || fp_op2 (&str) == FAIL)
3791 {
3792 if (! inst.error)
3793 inst.error = BAD_ARGS;
3794 return;
3795 }
3796
3797 inst.instruction |= flags;
3798 end_of_line (str);
3799 return;
3800 }
3801
3802 static void
3803 do_fp_cmp (str, flags)
3804 char * str;
3805 unsigned long flags;
3806 {
3807 skip_whitespace (str);
3808
3809 if (fp_reg_required_here (&str, 16) == FAIL)
3810 {
3811 if (! inst.error)
3812 inst.error = BAD_ARGS;
3813 return;
3814 }
3815
3816 if (skip_past_comma (&str) == FAIL
3817 || fp_op2 (&str) == FAIL)
3818 {
3819 if (! inst.error)
3820 inst.error = BAD_ARGS;
3821 return;
3822 }
3823
3824 inst.instruction |= flags;
3825 end_of_line (str);
3826 return;
3827 }
3828
3829 static void
3830 do_fp_from_reg (str, flags)
3831 char * str;
3832 unsigned long flags;
3833 {
3834 skip_whitespace (str);
3835
3836 switch (inst.suffix)
3837 {
3838 case SUFF_S:
3839 break;
3840 case SUFF_D:
3841 inst.instruction |= 0x00000080;
3842 break;
3843 case SUFF_E:
3844 inst.instruction |= 0x00080000;
3845 break;
3846 default:
3847 abort ();
3848 }
3849
3850 if (fp_reg_required_here (&str, 16) == FAIL)
3851 {
3852 if (! inst.error)
3853 inst.error = BAD_ARGS;
3854 return;
3855 }
3856
3857 if (skip_past_comma (&str) == FAIL
3858 || reg_required_here (&str, 12) == FAIL)
3859 {
3860 if (! inst.error)
3861 inst.error = BAD_ARGS;
3862 return;
3863 }
3864
3865 inst.instruction |= flags;
3866 end_of_line (str);
3867 return;
3868 }
3869
3870 static void
3871 do_fp_to_reg (str, flags)
3872 char * str;
3873 unsigned long flags;
3874 {
3875 skip_whitespace (str);
3876
3877 if (reg_required_here (&str, 12) == FAIL)
3878 return;
3879
3880 if (skip_past_comma (&str) == FAIL
3881 || fp_reg_required_here (&str, 0) == FAIL)
3882 {
3883 if (! inst.error)
3884 inst.error = BAD_ARGS;
3885 return;
3886 }
3887
3888 inst.instruction |= flags;
3889 end_of_line (str);
3890 return;
3891 }
3892
3893 /* Thumb specific routines */
3894
3895 /* Parse and validate that a register is of the right form, this saves
3896 repeated checking of this information in many similar cases.
3897 Unlike the 32-bit case we do not insert the register into the opcode
3898 here, since the position is often unknown until the full instruction
3899 has been parsed. */
3900 static int
3901 thumb_reg (strp, hi_lo)
3902 char ** strp;
3903 int hi_lo;
3904 {
3905 int reg;
3906
3907 if ((reg = reg_required_here (strp, -1)) == FAIL)
3908 return FAIL;
3909
3910 switch (hi_lo)
3911 {
3912 case THUMB_REG_LO:
3913 if (reg > 7)
3914 {
3915 inst.error = _("lo register required");
3916 return FAIL;
3917 }
3918 break;
3919
3920 case THUMB_REG_HI:
3921 if (reg < 8)
3922 {
3923 inst.error = _("hi register required");
3924 return FAIL;
3925 }
3926 break;
3927
3928 default:
3929 break;
3930 }
3931
3932 return reg;
3933 }
3934
3935 /* Parse an add or subtract instruction, SUBTRACT is non-zero if the opcode
3936 was SUB. */
3937 static void
3938 thumb_add_sub (str, subtract)
3939 char * str;
3940 int subtract;
3941 {
3942 int Rd, Rs, Rn = FAIL;
3943
3944 skip_whitespace (str);
3945
3946 if ((Rd = thumb_reg (&str, THUMB_REG_ANY)) == FAIL
3947 || skip_past_comma (&str) == FAIL)
3948 {
3949 if (! inst.error)
3950 inst.error = BAD_ARGS;
3951 return;
3952 }
3953
3954 if (is_immediate_prefix (*str))
3955 {
3956 Rs = Rd;
3957 str++;
3958 if (my_get_expression (&inst.reloc.exp, &str))
3959 return;
3960 }
3961 else
3962 {
3963 if ((Rs = thumb_reg (&str, THUMB_REG_ANY)) == FAIL)
3964 return;
3965
3966 if (skip_past_comma (&str) == FAIL)
3967 {
3968 /* Two operand format, shuffle the registers and pretend there
3969 are 3 */
3970 Rn = Rs;
3971 Rs = Rd;
3972 }
3973 else if (is_immediate_prefix (*str))
3974 {
3975 str++;
3976 if (my_get_expression (&inst.reloc.exp, &str))
3977 return;
3978 }
3979 else if ((Rn = thumb_reg (&str, THUMB_REG_ANY)) == FAIL)
3980 return;
3981 }
3982
3983 /* We now have Rd and Rs set to registers, and Rn set to a register or FAIL;
3984 for the latter case, EXPR contains the immediate that was found. */
3985 if (Rn != FAIL)
3986 {
3987 /* All register format. */
3988 if (Rd > 7 || Rs > 7 || Rn > 7)
3989 {
3990 if (Rs != Rd)
3991 {
3992 inst.error = _("dest and source1 must be the same register");
3993 return;
3994 }
3995
3996 /* Can't do this for SUB */
3997 if (subtract)
3998 {
3999 inst.error = _("subtract valid only on lo regs");
4000 return;
4001 }
4002
4003 inst.instruction = (T_OPCODE_ADD_HI
4004 | (Rd > 7 ? THUMB_H1 : 0)
4005 | (Rn > 7 ? THUMB_H2 : 0));
4006 inst.instruction |= (Rd & 7) | ((Rn & 7) << 3);
4007 }
4008 else
4009 {
4010 inst.instruction = subtract ? T_OPCODE_SUB_R3 : T_OPCODE_ADD_R3;
4011 inst.instruction |= Rd | (Rs << 3) | (Rn << 6);
4012 }
4013 }
4014 else
4015 {
4016 /* Immediate expression, now things start to get nasty. */
4017
4018 /* First deal with HI regs, only very restricted cases allowed:
4019 Adjusting SP, and using PC or SP to get an address. */
4020 if ((Rd > 7 && (Rd != REG_SP || Rs != REG_SP))
4021 || (Rs > 7 && Rs != REG_SP && Rs != REG_PC))
4022 {
4023 inst.error = _("invalid Hi register with immediate");
4024 return;
4025 }
4026
4027 if (inst.reloc.exp.X_op != O_constant)
4028 {
4029 /* Value isn't known yet, all we can do is store all the fragments
4030 we know about in the instruction and let the reloc hacking
4031 work it all out. */
4032 inst.instruction = (subtract ? 0x8000 : 0) | (Rd << 4) | Rs;
4033 inst.reloc.type = BFD_RELOC_ARM_THUMB_ADD;
4034 }
4035 else
4036 {
4037 int offset = inst.reloc.exp.X_add_number;
4038
4039 if (subtract)
4040 offset = -offset;
4041
4042 if (offset < 0)
4043 {
4044 offset = -offset;
4045 subtract = 1;
4046
4047 /* Quick check, in case offset is MIN_INT */
4048 if (offset < 0)
4049 {
4050 inst.error = _("immediate value out of range");
4051 return;
4052 }
4053 }
4054 else
4055 subtract = 0;
4056
4057 if (Rd == REG_SP)
4058 {
4059 if (offset & ~0x1fc)
4060 {
4061 inst.error = _("invalid immediate value for stack adjust");
4062 return;
4063 }
4064 inst.instruction = subtract ? T_OPCODE_SUB_ST : T_OPCODE_ADD_ST;
4065 inst.instruction |= offset >> 2;
4066 }
4067 else if (Rs == REG_PC || Rs == REG_SP)
4068 {
4069 if (subtract
4070 || (offset & ~0x3fc))
4071 {
4072 inst.error = _("invalid immediate for address calculation");
4073 return;
4074 }
4075 inst.instruction = (Rs == REG_PC ? T_OPCODE_ADD_PC
4076 : T_OPCODE_ADD_SP);
4077 inst.instruction |= (Rd << 8) | (offset >> 2);
4078 }
4079 else if (Rs == Rd)
4080 {
4081 if (offset & ~0xff)
4082 {
4083 inst.error = _("immediate value out of range");
4084 return;
4085 }
4086 inst.instruction = subtract ? T_OPCODE_SUB_I8 : T_OPCODE_ADD_I8;
4087 inst.instruction |= (Rd << 8) | offset;
4088 }
4089 else
4090 {
4091 if (offset & ~0x7)
4092 {
4093 inst.error = _("immediate value out of range");
4094 return;
4095 }
4096 inst.instruction = subtract ? T_OPCODE_SUB_I3 : T_OPCODE_ADD_I3;
4097 inst.instruction |= Rd | (Rs << 3) | (offset << 6);
4098 }
4099 }
4100 }
4101 end_of_line (str);
4102 }
4103
4104 static void
4105 thumb_shift (str, shift)
4106 char * str;
4107 int shift;
4108 {
4109 int Rd, Rs, Rn = FAIL;
4110
4111 skip_whitespace (str);
4112
4113 if ((Rd = thumb_reg (&str, THUMB_REG_LO)) == FAIL
4114 || skip_past_comma (&str) == FAIL)
4115 {
4116 if (! inst.error)
4117 inst.error = BAD_ARGS;
4118 return;
4119 }
4120
4121 if (is_immediate_prefix (*str))
4122 {
4123 /* Two operand immediate format, set Rs to Rd. */
4124 Rs = Rd;
4125 str++;
4126 if (my_get_expression (&inst.reloc.exp, &str))
4127 return;
4128 }
4129 else
4130 {
4131 if ((Rs = thumb_reg (&str, THUMB_REG_LO)) == FAIL)
4132 return;
4133
4134 if (skip_past_comma (&str) == FAIL)
4135 {
4136 /* Two operand format, shuffle the registers and pretend there
4137 are 3 */
4138 Rn = Rs;
4139 Rs = Rd;
4140 }
4141 else if (is_immediate_prefix (*str))
4142 {
4143 str++;
4144 if (my_get_expression (&inst.reloc.exp, &str))
4145 return;
4146 }
4147 else if ((Rn = thumb_reg (&str, THUMB_REG_LO)) == FAIL)
4148 return;
4149 }
4150
4151 /* We now have Rd and Rs set to registers, and Rn set to a register or FAIL;
4152 for the latter case, EXPR contains the immediate that was found. */
4153
4154 if (Rn != FAIL)
4155 {
4156 if (Rs != Rd)
4157 {
4158 inst.error = _("source1 and dest must be same register");
4159 return;
4160 }
4161
4162 switch (shift)
4163 {
4164 case THUMB_ASR: inst.instruction = T_OPCODE_ASR_R; break;
4165 case THUMB_LSL: inst.instruction = T_OPCODE_LSL_R; break;
4166 case THUMB_LSR: inst.instruction = T_OPCODE_LSR_R; break;
4167 }
4168
4169 inst.instruction |= Rd | (Rn << 3);
4170 }
4171 else
4172 {
4173 switch (shift)
4174 {
4175 case THUMB_ASR: inst.instruction = T_OPCODE_ASR_I; break;
4176 case THUMB_LSL: inst.instruction = T_OPCODE_LSL_I; break;
4177 case THUMB_LSR: inst.instruction = T_OPCODE_LSR_I; break;
4178 }
4179
4180 if (inst.reloc.exp.X_op != O_constant)
4181 {
4182 /* Value isn't known yet, create a dummy reloc and let reloc
4183 hacking fix it up */
4184
4185 inst.reloc.type = BFD_RELOC_ARM_THUMB_SHIFT;
4186 }
4187 else
4188 {
4189 unsigned shift_value = inst.reloc.exp.X_add_number;
4190
4191 if (shift_value > 32 || (shift_value == 32 && shift == THUMB_LSL))
4192 {
4193 inst.error = _("Invalid immediate for shift");
4194 return;
4195 }
4196
4197 /* Shifts of zero are handled by converting to LSL */
4198 if (shift_value == 0)
4199 inst.instruction = T_OPCODE_LSL_I;
4200
4201 /* Shifts of 32 are encoded as a shift of zero */
4202 if (shift_value == 32)
4203 shift_value = 0;
4204
4205 inst.instruction |= shift_value << 6;
4206 }
4207
4208 inst.instruction |= Rd | (Rs << 3);
4209 }
4210 end_of_line (str);
4211 }
4212
4213 static void
4214 thumb_mov_compare (str, move)
4215 char * str;
4216 int move;
4217 {
4218 int Rd, Rs = FAIL;
4219
4220 skip_whitespace (str);
4221
4222 if ((Rd = thumb_reg (&str, THUMB_REG_ANY)) == FAIL
4223 || skip_past_comma (&str) == FAIL)
4224 {
4225 if (! inst.error)
4226 inst.error = BAD_ARGS;
4227 return;
4228 }
4229
4230 if (is_immediate_prefix (*str))
4231 {
4232 str++;
4233 if (my_get_expression (&inst.reloc.exp, &str))
4234 return;
4235 }
4236 else if ((Rs = thumb_reg (&str, THUMB_REG_ANY)) == FAIL)
4237 return;
4238
4239 if (Rs != FAIL)
4240 {
4241 if (Rs < 8 && Rd < 8)
4242 {
4243 if (move == THUMB_MOVE)
4244 /* A move of two lowregs is encoded as ADD Rd, Rs, #0
4245 since a MOV instruction produces unpredictable results */
4246 inst.instruction = T_OPCODE_ADD_I3;
4247 else
4248 inst.instruction = T_OPCODE_CMP_LR;
4249 inst.instruction |= Rd | (Rs << 3);
4250 }
4251 else
4252 {
4253 if (move == THUMB_MOVE)
4254 inst.instruction = T_OPCODE_MOV_HR;
4255 else
4256 inst.instruction = T_OPCODE_CMP_HR;
4257
4258 if (Rd > 7)
4259 inst.instruction |= THUMB_H1;
4260
4261 if (Rs > 7)
4262 inst.instruction |= THUMB_H2;
4263
4264 inst.instruction |= (Rd & 7) | ((Rs & 7) << 3);
4265 }
4266 }
4267 else
4268 {
4269 if (Rd > 7)
4270 {
4271 inst.error = _("only lo regs allowed with immediate");
4272 return;
4273 }
4274
4275 if (move == THUMB_MOVE)
4276 inst.instruction = T_OPCODE_MOV_I8;
4277 else
4278 inst.instruction = T_OPCODE_CMP_I8;
4279
4280 inst.instruction |= Rd << 8;
4281
4282 if (inst.reloc.exp.X_op != O_constant)
4283 inst.reloc.type = BFD_RELOC_ARM_THUMB_IMM;
4284 else
4285 {
4286 unsigned value = inst.reloc.exp.X_add_number;
4287
4288 if (value > 255)
4289 {
4290 inst.error = _("invalid immediate");
4291 return;
4292 }
4293
4294 inst.instruction |= value;
4295 }
4296 }
4297
4298 end_of_line (str);
4299 }
4300
4301 static void
4302 thumb_load_store (str, load_store, size)
4303 char * str;
4304 int load_store;
4305 int size;
4306 {
4307 int Rd, Rb, Ro = FAIL;
4308
4309 skip_whitespace (str);
4310
4311 if ((Rd = thumb_reg (&str, THUMB_REG_LO)) == FAIL
4312 || skip_past_comma (&str) == FAIL)
4313 {
4314 if (! inst.error)
4315 inst.error = BAD_ARGS;
4316 return;
4317 }
4318
4319 if (*str == '[')
4320 {
4321 str++;
4322 if ((Rb = thumb_reg (&str, THUMB_REG_ANY)) == FAIL)
4323 return;
4324
4325 if (skip_past_comma (&str) != FAIL)
4326 {
4327 if (is_immediate_prefix (*str))
4328 {
4329 str++;
4330 if (my_get_expression (&inst.reloc.exp, &str))
4331 return;
4332 }
4333 else if ((Ro = thumb_reg (&str, THUMB_REG_LO)) == FAIL)
4334 return;
4335 }
4336 else
4337 {
4338 inst.reloc.exp.X_op = O_constant;
4339 inst.reloc.exp.X_add_number = 0;
4340 }
4341
4342 if (*str != ']')
4343 {
4344 inst.error = _("expected ']'");
4345 return;
4346 }
4347 str++;
4348 }
4349 else if (*str == '=')
4350 {
4351 /* Parse an "ldr Rd, =expr" instruction; this is another pseudo op */
4352 str++;
4353
4354 skip_whitespace (str);
4355
4356 if (my_get_expression (& inst.reloc.exp, & str))
4357 return;
4358
4359 end_of_line (str);
4360
4361 if ( inst.reloc.exp.X_op != O_constant
4362 && inst.reloc.exp.X_op != O_symbol)
4363 {
4364 inst.error = "Constant expression expected";
4365 return;
4366 }
4367
4368 if (inst.reloc.exp.X_op == O_constant
4369 && ((inst.reloc.exp.X_add_number & ~0xFF) == 0))
4370 {
4371 /* This can be done with a mov instruction */
4372
4373 inst.instruction = T_OPCODE_MOV_I8 | (Rd << 8);
4374 inst.instruction |= inst.reloc.exp.X_add_number;
4375 return;
4376 }
4377
4378 /* Insert into literal pool */
4379 if (add_to_lit_pool () == FAIL)
4380 {
4381 if (!inst.error)
4382 inst.error = "literal pool insertion failed";
4383 return;
4384 }
4385
4386 inst.reloc.type = BFD_RELOC_ARM_THUMB_OFFSET;
4387 inst.reloc.pc_rel = 1;
4388 inst.instruction = T_OPCODE_LDR_PC | (Rd << 8);
4389 inst.reloc.exp.X_add_number += 4; /* Adjust ARM pipeline offset to Thumb */
4390
4391 return;
4392 }
4393 else
4394 {
4395 if (my_get_expression (&inst.reloc.exp, &str))
4396 return;
4397
4398 inst.instruction = T_OPCODE_LDR_PC | (Rd << 8);
4399 inst.reloc.pc_rel = 1;
4400 inst.reloc.exp.X_add_number -= 4; /* Pipeline offset */
4401 inst.reloc.type = BFD_RELOC_ARM_THUMB_OFFSET;
4402 end_of_line (str);
4403 return;
4404 }
4405
4406 if (Rb == REG_PC || Rb == REG_SP)
4407 {
4408 if (size != THUMB_WORD)
4409 {
4410 inst.error = _("byte or halfword not valid for base register");
4411 return;
4412 }
4413 else if (Rb == REG_PC && load_store != THUMB_LOAD)
4414 {
4415 inst.error = _("R15 based store not allowed");
4416 return;
4417 }
4418 else if (Ro != FAIL)
4419 {
4420 inst.error = _("Invalid base register for register offset");
4421 return;
4422 }
4423
4424 if (Rb == REG_PC)
4425 inst.instruction = T_OPCODE_LDR_PC;
4426 else if (load_store == THUMB_LOAD)
4427 inst.instruction = T_OPCODE_LDR_SP;
4428 else
4429 inst.instruction = T_OPCODE_STR_SP;
4430
4431 inst.instruction |= Rd << 8;
4432 if (inst.reloc.exp.X_op == O_constant)
4433 {
4434 unsigned offset = inst.reloc.exp.X_add_number;
4435
4436 if (offset & ~0x3fc)
4437 {
4438 inst.error = _("invalid offset");
4439 return;
4440 }
4441
4442 inst.instruction |= offset >> 2;
4443 }
4444 else
4445 inst.reloc.type = BFD_RELOC_ARM_THUMB_OFFSET;
4446 }
4447 else if (Rb > 7)
4448 {
4449 inst.error = _("invalid base register in load/store");
4450 return;
4451 }
4452 else if (Ro == FAIL)
4453 {
4454 /* Immediate offset */
4455 if (size == THUMB_WORD)
4456 inst.instruction = (load_store == THUMB_LOAD
4457 ? T_OPCODE_LDR_IW : T_OPCODE_STR_IW);
4458 else if (size == THUMB_HALFWORD)
4459 inst.instruction = (load_store == THUMB_LOAD
4460 ? T_OPCODE_LDR_IH : T_OPCODE_STR_IH);
4461 else
4462 inst.instruction = (load_store == THUMB_LOAD
4463 ? T_OPCODE_LDR_IB : T_OPCODE_STR_IB);
4464
4465 inst.instruction |= Rd | (Rb << 3);
4466
4467 if (inst.reloc.exp.X_op == O_constant)
4468 {
4469 unsigned offset = inst.reloc.exp.X_add_number;
4470
4471 if (offset & ~(0x1f << size))
4472 {
4473 inst.error = _("Invalid offset");
4474 return;
4475 }
4476 inst.instruction |= (offset >> size) << 6;
4477 }
4478 else
4479 inst.reloc.type = BFD_RELOC_ARM_THUMB_OFFSET;
4480 }
4481 else
4482 {
4483 /* Register offset */
4484 if (size == THUMB_WORD)
4485 inst.instruction = (load_store == THUMB_LOAD
4486 ? T_OPCODE_LDR_RW : T_OPCODE_STR_RW);
4487 else if (size == THUMB_HALFWORD)
4488 inst.instruction = (load_store == THUMB_LOAD
4489 ? T_OPCODE_LDR_RH : T_OPCODE_STR_RH);
4490 else
4491 inst.instruction = (load_store == THUMB_LOAD
4492 ? T_OPCODE_LDR_RB : T_OPCODE_STR_RB);
4493
4494 inst.instruction |= Rd | (Rb << 3) | (Ro << 6);
4495 }
4496
4497 end_of_line (str);
4498 }
4499
4500 static void
4501 do_t_nop (str)
4502 char * str;
4503 {
4504 /* Do nothing */
4505 end_of_line (str);
4506 return;
4507 }
4508
4509 /* Handle the Format 4 instructions that do not have equivalents in other
4510 formats. That is, ADC, AND, EOR, SBC, ROR, TST, NEG, CMN, ORR, MUL,
4511 BIC and MVN. */
4512 static void
4513 do_t_arit (str)
4514 char * str;
4515 {
4516 int Rd, Rs, Rn;
4517
4518 skip_whitespace (str);
4519
4520 if ((Rd = thumb_reg (&str, THUMB_REG_LO)) == FAIL
4521 || skip_past_comma (&str) == FAIL
4522 || (Rs = thumb_reg (&str, THUMB_REG_LO)) == FAIL)
4523 {
4524 inst.error = BAD_ARGS;
4525 return;
4526 }
4527
4528 if (skip_past_comma (&str) != FAIL)
4529 {
4530 /* Three operand format not allowed for TST, CMN, NEG and MVN.
4531 (It isn't allowed for CMP either, but that isn't handled by this
4532 function.) */
4533 if (inst.instruction == T_OPCODE_TST
4534 || inst.instruction == T_OPCODE_CMN
4535 || inst.instruction == T_OPCODE_NEG
4536 || inst.instruction == T_OPCODE_MVN)
4537 {
4538 inst.error = BAD_ARGS;
4539 return;
4540 }
4541
4542 if ((Rn = thumb_reg (&str, THUMB_REG_LO)) == FAIL)
4543 return;
4544
4545 if (Rs != Rd)
4546 {
4547 inst.error = _("dest and source1 one must be the same register");
4548 return;
4549 }
4550 Rs = Rn;
4551 }
4552
4553 if (inst.instruction == T_OPCODE_MUL
4554 && Rs == Rd)
4555 as_tsktsk (_("Rs and Rd must be different in MUL"));
4556
4557 inst.instruction |= Rd | (Rs << 3);
4558 end_of_line (str);
4559 }
4560
4561 static void
4562 do_t_add (str)
4563 char * str;
4564 {
4565 thumb_add_sub (str, 0);
4566 }
4567
4568 static void
4569 do_t_asr (str)
4570 char * str;
4571 {
4572 thumb_shift (str, THUMB_ASR);
4573 }
4574
4575 static void
4576 do_t_branch9 (str)
4577 char * str;
4578 {
4579 if (my_get_expression (&inst.reloc.exp, &str))
4580 return;
4581 inst.reloc.type = BFD_RELOC_THUMB_PCREL_BRANCH9;
4582 inst.reloc.pc_rel = 1;
4583 end_of_line (str);
4584 }
4585
4586 static void
4587 do_t_branch12 (str)
4588 char * str;
4589 {
4590 if (my_get_expression (&inst.reloc.exp, &str))
4591 return;
4592 inst.reloc.type = BFD_RELOC_THUMB_PCREL_BRANCH12;
4593 inst.reloc.pc_rel = 1;
4594 end_of_line (str);
4595 }
4596
4597 /* Find the real, Thumb encoded start of a Thumb function. */
4598
4599 static symbolS *
4600 find_real_start (symbolP)
4601 symbolS * symbolP;
4602 {
4603 char * real_start;
4604 const char * name = S_GET_NAME (symbolP);
4605 symbolS * new_target;
4606
4607 /* This definiton must agree with the one in gcc/config/arm/thumb.c */
4608 #define STUB_NAME ".real_start_of"
4609
4610 if (name == NULL)
4611 abort();
4612
4613 /* Names that start with '.' are local labels, not function entry points.
4614 The compiler may generate BL instructions to these labels because it
4615 needs to perform a branch to a far away location. */
4616 if (name[0] == '.')
4617 return symbolP;
4618
4619 real_start = malloc (strlen (name) + strlen (STUB_NAME) + 1);
4620 sprintf (real_start, "%s%s", STUB_NAME, name);
4621
4622 new_target = symbol_find (real_start);
4623
4624 if (new_target == NULL)
4625 {
4626 as_warn ("Failed to find real start of function: %s\n", name);
4627 new_target = symbolP;
4628 }
4629
4630 free (real_start);
4631
4632 return new_target;
4633 }
4634
4635
4636 static void
4637 do_t_branch23 (str)
4638 char * str;
4639 {
4640 if (my_get_expression (& inst.reloc.exp, & str))
4641 return;
4642
4643 inst.reloc.type = BFD_RELOC_THUMB_PCREL_BRANCH23;
4644 inst.reloc.pc_rel = 1;
4645 end_of_line (str);
4646
4647 /* If the destination of the branch is a defined symbol which does not have
4648 the THUMB_FUNC attribute, then we must be calling a function which has
4649 the (interfacearm) attribute. We look for the Thumb entry point to that
4650 function and change the branch to refer to that function instead. */
4651 if ( inst.reloc.exp.X_op == O_symbol
4652 && inst.reloc.exp.X_add_symbol != NULL
4653 && S_IS_DEFINED (inst.reloc.exp.X_add_symbol)
4654 && ! THUMB_IS_FUNC (inst.reloc.exp.X_add_symbol))
4655 inst.reloc.exp.X_add_symbol = find_real_start (inst.reloc.exp.X_add_symbol);
4656 }
4657
4658 static void
4659 do_t_bx (str)
4660 char * str;
4661 {
4662 int reg;
4663
4664 skip_whitespace (str);
4665
4666 if ((reg = thumb_reg (&str, THUMB_REG_ANY)) == FAIL)
4667 return;
4668
4669 /* This sets THUMB_H2 from the top bit of reg. */
4670 inst.instruction |= reg << 3;
4671
4672 /* ??? FIXME: Should add a hacky reloc here if reg is REG_PC. The reloc
4673 should cause the alignment to be checked once it is known. This is
4674 because BX PC only works if the instruction is word aligned. */
4675
4676 end_of_line (str);
4677 }
4678
4679 static void
4680 do_t_compare (str)
4681 char * str;
4682 {
4683 thumb_mov_compare (str, THUMB_COMPARE);
4684 }
4685
4686 static void
4687 do_t_ldmstm (str)
4688 char * str;
4689 {
4690 int Rb;
4691 long range;
4692
4693 skip_whitespace (str);
4694
4695 if ((Rb = thumb_reg (&str, THUMB_REG_LO)) == FAIL)
4696 return;
4697
4698 if (*str != '!')
4699 as_warn (_("Inserted missing '!': load/store multiple always writes back base register"));
4700 else
4701 str++;
4702
4703 if (skip_past_comma (&str) == FAIL
4704 || (range = reg_list (&str)) == FAIL)
4705 {
4706 if (! inst.error)
4707 inst.error = BAD_ARGS;
4708 return;
4709 }
4710
4711 if (inst.reloc.type != BFD_RELOC_NONE)
4712 {
4713 /* This really doesn't seem worth it. */
4714 inst.reloc.type = BFD_RELOC_NONE;
4715 inst.error = _("Expression too complex");
4716 return;
4717 }
4718
4719 if (range & ~0xff)
4720 {
4721 inst.error = _("only lo-regs valid in load/store multiple");
4722 return;
4723 }
4724
4725 inst.instruction |= (Rb << 8) | range;
4726 end_of_line (str);
4727 }
4728
4729 static void
4730 do_t_ldr (str)
4731 char * str;
4732 {
4733 thumb_load_store (str, THUMB_LOAD, THUMB_WORD);
4734 }
4735
4736 static void
4737 do_t_ldrb (str)
4738 char * str;
4739 {
4740 thumb_load_store (str, THUMB_LOAD, THUMB_BYTE);
4741 }
4742
4743 static void
4744 do_t_ldrh (str)
4745 char * str;
4746 {
4747 thumb_load_store (str, THUMB_LOAD, THUMB_HALFWORD);
4748 }
4749
4750 static void
4751 do_t_lds (str)
4752 char * str;
4753 {
4754 int Rd, Rb, Ro;
4755
4756 skip_whitespace (str);
4757
4758 if ((Rd = thumb_reg (&str, THUMB_REG_LO)) == FAIL
4759 || skip_past_comma (&str) == FAIL
4760 || *str++ != '['
4761 || (Rb = thumb_reg (&str, THUMB_REG_LO)) == FAIL
4762 || skip_past_comma (&str) == FAIL
4763 || (Ro = thumb_reg (&str, THUMB_REG_LO)) == FAIL
4764 || *str++ != ']')
4765 {
4766 if (! inst.error)
4767 inst.error = _("Syntax: ldrs[b] Rd, [Rb, Ro]");
4768 return;
4769 }
4770
4771 inst.instruction |= Rd | (Rb << 3) | (Ro << 6);
4772 end_of_line (str);
4773 }
4774
4775 static void
4776 do_t_lsl (str)
4777 char * str;
4778 {
4779 thumb_shift (str, THUMB_LSL);
4780 }
4781
4782 static void
4783 do_t_lsr (str)
4784 char * str;
4785 {
4786 thumb_shift (str, THUMB_LSR);
4787 }
4788
4789 static void
4790 do_t_mov (str)
4791 char * str;
4792 {
4793 thumb_mov_compare (str, THUMB_MOVE);
4794 }
4795
4796 static void
4797 do_t_push_pop (str)
4798 char * str;
4799 {
4800 long range;
4801
4802 skip_whitespace (str);
4803
4804 if ((range = reg_list (&str)) == FAIL)
4805 {
4806 if (! inst.error)
4807 inst.error = BAD_ARGS;
4808 return;
4809 }
4810
4811 if (inst.reloc.type != BFD_RELOC_NONE)
4812 {
4813 /* This really doesn't seem worth it. */
4814 inst.reloc.type = BFD_RELOC_NONE;
4815 inst.error = _("Expression too complex");
4816 return;
4817 }
4818
4819 if (range & ~0xff)
4820 {
4821 if ((inst.instruction == T_OPCODE_PUSH
4822 && (range & ~0xff) == 1 << REG_LR)
4823 || (inst.instruction == T_OPCODE_POP
4824 && (range & ~0xff) == 1 << REG_PC))
4825 {
4826 inst.instruction |= THUMB_PP_PC_LR;
4827 range &= 0xff;
4828 }
4829 else
4830 {
4831 inst.error = _("invalid register list to push/pop instruction");
4832 return;
4833 }
4834 }
4835
4836 inst.instruction |= range;
4837 end_of_line (str);
4838 }
4839
4840 static void
4841 do_t_str (str)
4842 char * str;
4843 {
4844 thumb_load_store (str, THUMB_STORE, THUMB_WORD);
4845 }
4846
4847 static void
4848 do_t_strb (str)
4849 char * str;
4850 {
4851 thumb_load_store (str, THUMB_STORE, THUMB_BYTE);
4852 }
4853
4854 static void
4855 do_t_strh (str)
4856 char * str;
4857 {
4858 thumb_load_store (str, THUMB_STORE, THUMB_HALFWORD);
4859 }
4860
4861 static void
4862 do_t_sub (str)
4863 char * str;
4864 {
4865 thumb_add_sub (str, 1);
4866 }
4867
4868 static void
4869 do_t_swi (str)
4870 char * str;
4871 {
4872 skip_whitespace (str);
4873
4874 if (my_get_expression (&inst.reloc.exp, &str))
4875 return;
4876
4877 inst.reloc.type = BFD_RELOC_ARM_SWI;
4878 end_of_line (str);
4879 return;
4880 }
4881
4882 static void
4883 do_t_adr (str)
4884 char * str;
4885 {
4886 /* This is a pseudo-op of the form "adr rd, label" to be converted
4887 into a relative address of the form "add rd, pc, #label-.-4" */
4888 skip_whitespace (str);
4889
4890 if (reg_required_here (&str, 4) == FAIL /* Store Rd in temporary location inside instruction. */
4891 || skip_past_comma (&str) == FAIL
4892 || my_get_expression (&inst.reloc.exp, &str))
4893 {
4894 if (!inst.error)
4895 inst.error = BAD_ARGS;
4896 return;
4897 }
4898
4899 inst.reloc.type = BFD_RELOC_ARM_THUMB_ADD;
4900 inst.reloc.exp.X_add_number -= 4; /* PC relative adjust */
4901 inst.reloc.pc_rel = 1;
4902 inst.instruction |= REG_PC; /* Rd is already placed into the instruction */
4903 end_of_line (str);
4904 }
4905
4906 static void
4907 insert_reg (entry)
4908 int entry;
4909 {
4910 int len = strlen (reg_table[entry].name) + 2;
4911 char * buf = (char *) xmalloc (len);
4912 char * buf2 = (char *) xmalloc (len);
4913 int i = 0;
4914
4915 #ifdef REGISTER_PREFIX
4916 buf[i++] = REGISTER_PREFIX;
4917 #endif
4918
4919 strcpy (buf + i, reg_table[entry].name);
4920
4921 for (i = 0; buf[i]; i++)
4922 buf2[i] = islower (buf[i]) ? toupper (buf[i]) : buf[i];
4923
4924 buf2[i] = '\0';
4925
4926 hash_insert (arm_reg_hsh, buf, (PTR) &reg_table[entry]);
4927 hash_insert (arm_reg_hsh, buf2, (PTR) &reg_table[entry]);
4928 }
4929
4930 static void
4931 insert_reg_alias (str, regnum)
4932 char *str;
4933 int regnum;
4934 {
4935 struct reg_entry *new =
4936 (struct reg_entry *)xmalloc (sizeof (struct reg_entry));
4937 char *name = xmalloc (strlen (str) + 1);
4938 strcpy (name, str);
4939
4940 new->name = name;
4941 new->number = regnum;
4942
4943 hash_insert (arm_reg_hsh, name, (PTR) new);
4944 }
4945
4946 static void
4947 set_constant_flonums ()
4948 {
4949 int i;
4950
4951 for (i = 0; i < NUM_FLOAT_VALS; i++)
4952 if (atof_ieee ((char *)fp_const[i], 'x', fp_values[i]) == NULL)
4953 abort ();
4954 }
4955
4956 void
4957 md_begin ()
4958 {
4959 int i;
4960
4961 if ( (arm_ops_hsh = hash_new ()) == NULL
4962 || (arm_tops_hsh = hash_new ()) == NULL
4963 || (arm_cond_hsh = hash_new ()) == NULL
4964 || (arm_shift_hsh = hash_new ()) == NULL
4965 || (arm_reg_hsh = hash_new ()) == NULL
4966 || (arm_psr_hsh = hash_new ()) == NULL)
4967 as_fatal (_("Virtual memory exhausted"));
4968
4969 for (i = 0; i < sizeof (insns) / sizeof (struct asm_opcode); i++)
4970 hash_insert (arm_ops_hsh, insns[i].template, (PTR) (insns + i));
4971 for (i = 0; i < sizeof (tinsns) / sizeof (struct thumb_opcode); i++)
4972 hash_insert (arm_tops_hsh, tinsns[i].template, (PTR) (tinsns + i));
4973 for (i = 0; i < sizeof (conds) / sizeof (struct asm_cond); i++)
4974 hash_insert (arm_cond_hsh, conds[i].template, (PTR) (conds + i));
4975 for (i = 0; i < sizeof (shift) / sizeof (struct asm_shift); i++)
4976 hash_insert (arm_shift_hsh, shift[i].template, (PTR) (shift + i));
4977 for (i = 0; i < sizeof (psrs) / sizeof (struct asm_psr); i++)
4978 hash_insert (arm_psr_hsh, psrs[i].template, (PTR) (psrs + i));
4979
4980 for (i = 0; reg_table[i].name; i++)
4981 insert_reg (i);
4982
4983 set_constant_flonums ();
4984
4985 #if defined OBJ_COFF || defined OBJ_ELF
4986 {
4987 unsigned int flags = 0;
4988
4989 /* Set the flags in the private structure */
4990 if (uses_apcs_26) flags |= F_APCS26;
4991 if (support_interwork) flags |= F_INTERWORK;
4992 if (uses_apcs_float) flags |= F_APCS_FLOAT;
4993 if (pic_code) flags |= F_PIC;
4994 if ((cpu_variant & FPU_ALL) == FPU_NONE) flags |= F_SOFT_FLOAT;
4995
4996 bfd_set_private_flags (stdoutput, flags);
4997 }
4998 #endif
4999
5000 {
5001 unsigned mach;
5002
5003 /* Record the CPU type as well */
5004 switch (cpu_variant & ARM_CPU_MASK)
5005 {
5006 case ARM_2:
5007 mach = bfd_mach_arm_2;
5008 break;
5009
5010 case ARM_3: /* also ARM_250 */
5011 mach = bfd_mach_arm_2a;
5012 break;
5013
5014 default:
5015 case ARM_6 | ARM_3 | ARM_2: /* Actually no CPU type defined */
5016 mach = bfd_mach_arm_4;
5017 break;
5018
5019 case ARM_7: /* also ARM_6 */
5020 mach = bfd_mach_arm_3;
5021 break;
5022 }
5023
5024 /* Catch special cases. */
5025 if (cpu_variant != (FPU_DEFAULT | CPU_DEFAULT))
5026 {
5027 if (cpu_variant & (ARM_EXT_V5 & ARM_THUMB))
5028 mach = bfd_mach_arm_5T;
5029 else if (cpu_variant & ARM_EXT_V5)
5030 mach = bfd_mach_arm_5;
5031 else if (cpu_variant & ARM_THUMB)
5032 mach = bfd_mach_arm_4T;
5033 else if ((cpu_variant & ARM_ARCH_V4) == ARM_ARCH_V4)
5034 mach = bfd_mach_arm_4;
5035 else if (cpu_variant & ARM_LONGMUL)
5036 mach = bfd_mach_arm_3M;
5037 }
5038
5039 bfd_set_arch_mach (stdoutput, TARGET_ARCH, mach);
5040 }
5041 }
5042
5043 /* Turn an integer of n bytes (in val) into a stream of bytes appropriate
5044 for use in the a.out file, and stores them in the array pointed to by buf.
5045 This knows about the endian-ness of the target machine and does
5046 THE RIGHT THING, whatever it is. Possible values for n are 1 (byte)
5047 2 (short) and 4 (long) Floating numbers are put out as a series of
5048 LITTLENUMS (shorts, here at least). */
5049 void
5050 md_number_to_chars (buf, val, n)
5051 char * buf;
5052 valueT val;
5053 int n;
5054 {
5055 if (target_big_endian)
5056 number_to_chars_bigendian (buf, val, n);
5057 else
5058 number_to_chars_littleendian (buf, val, n);
5059 }
5060
5061 static valueT
5062 md_chars_to_number (buf, n)
5063 char * buf;
5064 int n;
5065 {
5066 valueT result = 0;
5067 unsigned char * where = (unsigned char *) buf;
5068
5069 if (target_big_endian)
5070 {
5071 while (n--)
5072 {
5073 result <<= 8;
5074 result |= (*where++ & 255);
5075 }
5076 }
5077 else
5078 {
5079 while (n--)
5080 {
5081 result <<= 8;
5082 result |= (where[n] & 255);
5083 }
5084 }
5085
5086 return result;
5087 }
5088
5089 /* Turn a string in input_line_pointer into a floating point constant
5090 of type TYPE, and store the appropriate bytes in *litP. The number
5091 of LITTLENUMS emitted is stored in *sizeP . An error message is
5092 returned, or NULL on OK.
5093
5094 Note that fp constants aren't represent in the normal way on the ARM.
5095 In big endian mode, things are as expected. However, in little endian
5096 mode fp constants are big-endian word-wise, and little-endian byte-wise
5097 within the words. For example, (double) 1.1 in big endian mode is
5098 the byte sequence 3f f1 99 99 99 99 99 9a, and in little endian mode is
5099 the byte sequence 99 99 f1 3f 9a 99 99 99.
5100
5101 ??? The format of 12 byte floats is uncertain according to gcc's arm.h. */
5102
5103 char *
5104 md_atof (type, litP, sizeP)
5105 char type;
5106 char * litP;
5107 int * sizeP;
5108 {
5109 int prec;
5110 LITTLENUM_TYPE words[MAX_LITTLENUMS];
5111 char *t;
5112 int i;
5113
5114 switch (type)
5115 {
5116 case 'f':
5117 case 'F':
5118 case 's':
5119 case 'S':
5120 prec = 2;
5121 break;
5122
5123 case 'd':
5124 case 'D':
5125 case 'r':
5126 case 'R':
5127 prec = 4;
5128 break;
5129
5130 case 'x':
5131 case 'X':
5132 prec = 6;
5133 break;
5134
5135 case 'p':
5136 case 'P':
5137 prec = 6;
5138 break;
5139
5140 default:
5141 *sizeP = 0;
5142 return _("Bad call to MD_ATOF()");
5143 }
5144
5145 t = atof_ieee (input_line_pointer, type, words);
5146 if (t)
5147 input_line_pointer = t;
5148 *sizeP = prec * 2;
5149
5150 if (target_big_endian)
5151 {
5152 for (i = 0; i < prec; i++)
5153 {
5154 md_number_to_chars (litP, (valueT) words[i], 2);
5155 litP += 2;
5156 }
5157 }
5158 else
5159 {
5160 /* For a 4 byte float the order of elements in `words' is 1 0. For an
5161 8 byte float the order is 1 0 3 2. */
5162 for (i = 0; i < prec; i += 2)
5163 {
5164 md_number_to_chars (litP, (valueT) words[i + 1], 2);
5165 md_number_to_chars (litP + 2, (valueT) words[i], 2);
5166 litP += 4;
5167 }
5168 }
5169
5170 return 0;
5171 }
5172
5173 /* The knowledge of the PC's pipeline offset is built into the insns themselves. */
5174 long
5175 md_pcrel_from (fixP)
5176 fixS * fixP;
5177 {
5178 if ( fixP->fx_addsy
5179 && S_GET_SEGMENT (fixP->fx_addsy) == undefined_section
5180 && fixP->fx_subsy == NULL)
5181 return 0;
5182
5183 if (fixP->fx_pcrel && (fixP->fx_r_type == BFD_RELOC_ARM_THUMB_ADD))
5184 {
5185 /* PC relative addressing on the Thumb is slightly odd
5186 as the bottom two bits of the PC are forced to zero
5187 for the calculation. */
5188 return (fixP->fx_where + fixP->fx_frag->fr_address) & ~3;
5189 }
5190
5191 return fixP->fx_where + fixP->fx_frag->fr_address;
5192 }
5193
5194 /* Round up a section size to the appropriate boundary. */
5195 valueT
5196 md_section_align (segment, size)
5197 segT segment;
5198 valueT size;
5199 {
5200 #ifdef OBJ_ELF
5201 return size;
5202 #else
5203 /* Round all sects to multiple of 4 */
5204 return (size + 3) & ~3;
5205 #endif
5206 }
5207
5208 /* Under ELF we need to default _GLOBAL_OFFSET_TABLE. Otherwise
5209 we have no need to default values of symbols. */
5210
5211 /* ARGSUSED */
5212 symbolS *
5213 md_undefined_symbol (name)
5214 char * name;
5215 {
5216 #ifdef OBJ_ELF
5217 if (name[0] == '_' && name[1] == 'G'
5218 && streq (name, GLOBAL_OFFSET_TABLE_NAME))
5219 {
5220 if (!GOT_symbol)
5221 {
5222 if (symbol_find (name))
5223 as_bad ("GOT already in the symbol table");
5224
5225 GOT_symbol = symbol_new (name, undefined_section,
5226 (valueT)0, & zero_address_frag);
5227 }
5228
5229 return GOT_symbol;
5230 }
5231 #endif
5232
5233 return 0;
5234 }
5235
5236 /* arm_reg_parse () := if it looks like a register, return its token and
5237 advance the pointer. */
5238
5239 static int
5240 arm_reg_parse (ccp)
5241 register char ** ccp;
5242 {
5243 char * start = * ccp;
5244 char c;
5245 char * p;
5246 struct reg_entry * reg;
5247
5248 #ifdef REGISTER_PREFIX
5249 if (*start != REGISTER_PREFIX)
5250 return FAIL;
5251 p = start + 1;
5252 #else
5253 p = start;
5254 #ifdef OPTIONAL_REGISTER_PREFIX
5255 if (*p == OPTIONAL_REGISTER_PREFIX)
5256 p++, start++;
5257 #endif
5258 #endif
5259 if (!isalpha (*p) || !is_name_beginner (*p))
5260 return FAIL;
5261
5262 c = *p++;
5263 while (isalpha (c) || isdigit (c) || c == '_')
5264 c = *p++;
5265
5266 *--p = 0;
5267 reg = (struct reg_entry *) hash_find (arm_reg_hsh, start);
5268 *p = c;
5269
5270 if (reg)
5271 {
5272 *ccp = p;
5273 return reg->number;
5274 }
5275
5276 return FAIL;
5277 }
5278
5279 static int
5280 arm_psr_parse (ccp)
5281 register char ** ccp;
5282 {
5283 char * start = * ccp;
5284 char c;
5285 char * p;
5286 CONST struct asm_psr * psr;
5287
5288 p = start;
5289 c = *p++;
5290 while (isalpha (c) || c == '_')
5291 c = *p++;
5292
5293 *--p = 0;
5294 psr = (CONST struct asm_psr *) hash_find (arm_psr_hsh, start);
5295 *p = c;
5296
5297 if (psr)
5298 {
5299 *ccp = p;
5300 return psr->number;
5301 }
5302
5303 return FAIL;
5304 }
5305
5306 int
5307 md_apply_fix3 (fixP, val, seg)
5308 fixS * fixP;
5309 valueT * val;
5310 segT seg;
5311 {
5312 offsetT value = * val;
5313 offsetT newval;
5314 unsigned int newimm;
5315 unsigned long temp;
5316 int sign;
5317 char * buf = fixP->fx_where + fixP->fx_frag->fr_literal;
5318 arm_fix_data * arm_data = (arm_fix_data *) fixP->tc_fix_data;
5319
5320 assert (fixP->fx_r_type < BFD_RELOC_UNUSED);
5321
5322 /* Note whether this will delete the relocation. */
5323 #if 0 /* patch from REarnshaw to JDavis (disabled for the moment, since it doesn't work fully) */
5324 if ((fixP->fx_addsy == 0 || symbol_constant_p (fixP->fx_addsy))
5325 && !fixP->fx_pcrel)
5326 #else
5327 if (fixP->fx_addsy == 0 && !fixP->fx_pcrel)
5328 #endif
5329 fixP->fx_done = 1;
5330
5331 /* If this symbol is in a different section then we need to leave it for
5332 the linker to deal with. Unfortunately, md_pcrel_from can't tell,
5333 so we have to undo it's effects here. */
5334 if (fixP->fx_pcrel)
5335 {
5336 if (fixP->fx_addsy != NULL
5337 && S_IS_DEFINED (fixP->fx_addsy)
5338 && S_GET_SEGMENT (fixP->fx_addsy) != seg)
5339 {
5340 if (target_oabi
5341 && (fixP->fx_r_type == BFD_RELOC_ARM_PCREL_BRANCH
5342 ))
5343 value = 0;
5344 else
5345 value += md_pcrel_from (fixP);
5346 }
5347 }
5348
5349 fixP->fx_addnumber = value; /* Remember value for emit_reloc. */
5350
5351 switch (fixP->fx_r_type)
5352 {
5353 case BFD_RELOC_ARM_IMMEDIATE:
5354 newimm = validate_immediate (value);
5355 temp = md_chars_to_number (buf, INSN_SIZE);
5356
5357 /* If the instruction will fail, see if we can fix things up by
5358 changing the opcode. */
5359 if (newimm == (unsigned int) FAIL
5360 && (newimm = negate_data_op (&temp, value)) == (unsigned int) FAIL)
5361 {
5362 as_bad_where (fixP->fx_file, fixP->fx_line,
5363 _("invalid constant (%lx) after fixup"),
5364 (unsigned long) value);
5365 break;
5366 }
5367
5368 newimm |= (temp & 0xfffff000);
5369 md_number_to_chars (buf, (valueT) newimm, INSN_SIZE);
5370 break;
5371
5372 case BFD_RELOC_ARM_ADRL_IMMEDIATE:
5373 {
5374 unsigned int highpart = 0;
5375 unsigned int newinsn = 0xe1a00000; /* nop */
5376 newimm = validate_immediate (value);
5377 temp = md_chars_to_number (buf, INSN_SIZE);
5378
5379 /* If the instruction will fail, see if we can fix things up by
5380 changing the opcode. */
5381 if (newimm == (unsigned int) FAIL
5382 && (newimm = negate_data_op (& temp, value)) == (unsigned int) FAIL)
5383 {
5384 /* No ? OK - try using two ADD instructions to generate the value. */
5385 newimm = validate_immediate_twopart (value, & highpart);
5386
5387 /* Yes - then make sure that the second instruction is also an add. */
5388 if (newimm != (unsigned int) FAIL)
5389 newinsn = temp;
5390 /* Still No ? Try using a negated value. */
5391 else if (validate_immediate_twopart (- value, & highpart) != (unsigned int) FAIL)
5392 temp = newinsn = (temp & OPCODE_MASK) | OPCODE_SUB << DATA_OP_SHIFT;
5393 /* Otherwise - give up. */
5394 else
5395 {
5396 as_bad_where (fixP->fx_file, fixP->fx_line,
5397 _("Unable to compute ADRL instructions for PC offset of 0x%x"), value);
5398 break;
5399 }
5400
5401 /* Replace the first operand in the 2nd instruction (which is the PC)
5402 with the destination register. We have already added in the PC in the
5403 first instruction and we do not want to do it again. */
5404 newinsn &= ~ 0xf0000;
5405 newinsn |= ((newinsn & 0x0f000) << 4);
5406 }
5407
5408 newimm |= (temp & 0xfffff000);
5409 md_number_to_chars (buf, (valueT) newimm, INSN_SIZE);
5410
5411 highpart |= (newinsn & 0xfffff000);
5412 md_number_to_chars (buf + INSN_SIZE, (valueT) highpart, INSN_SIZE);
5413 }
5414 break;
5415
5416 case BFD_RELOC_ARM_OFFSET_IMM:
5417 sign = value >= 0;
5418
5419 if (value < 0)
5420 value = - value;
5421
5422 if (validate_offset_imm (value, 0) == FAIL)
5423 {
5424 as_bad_where (fixP->fx_file, fixP->fx_line,
5425 _("bad immediate value for offset (%ld)"), (long) value);
5426 break;
5427 }
5428
5429 newval = md_chars_to_number (buf, INSN_SIZE);
5430 newval &= 0xff7ff000;
5431 newval |= value | (sign ? INDEX_UP : 0);
5432 md_number_to_chars (buf, newval, INSN_SIZE);
5433 break;
5434
5435 case BFD_RELOC_ARM_OFFSET_IMM8:
5436 case BFD_RELOC_ARM_HWLITERAL:
5437 sign = value >= 0;
5438
5439 if (value < 0)
5440 value = - value;
5441
5442 if (validate_offset_imm (value, 1) == FAIL)
5443 {
5444 if (fixP->fx_r_type == BFD_RELOC_ARM_HWLITERAL)
5445 as_bad_where (fixP->fx_file, fixP->fx_line,
5446 _("invalid literal constant: pool needs to be closer"));
5447 else
5448 as_bad (_("bad immediate value for half-word offset (%ld)"),
5449 (long) value);
5450 break;
5451 }
5452
5453 newval = md_chars_to_number (buf, INSN_SIZE);
5454 newval &= 0xff7ff0f0;
5455 newval |= ((value >> 4) << 8) | (value & 0xf) | (sign ? INDEX_UP : 0);
5456 md_number_to_chars (buf, newval, INSN_SIZE);
5457 break;
5458
5459 case BFD_RELOC_ARM_LITERAL:
5460 sign = value >= 0;
5461
5462 if (value < 0)
5463 value = - value;
5464
5465 if (validate_offset_imm (value, 0) == FAIL)
5466 {
5467 as_bad_where (fixP->fx_file, fixP->fx_line,
5468 _("invalid literal constant: pool needs to be closer"));
5469 break;
5470 }
5471
5472 newval = md_chars_to_number (buf, INSN_SIZE);
5473 newval &= 0xff7ff000;
5474 newval |= value | (sign ? INDEX_UP : 0);
5475 md_number_to_chars (buf, newval, INSN_SIZE);
5476 break;
5477
5478 case BFD_RELOC_ARM_SHIFT_IMM:
5479 newval = md_chars_to_number (buf, INSN_SIZE);
5480 if (((unsigned long) value) > 32
5481 || (value == 32
5482 && (((newval & 0x60) == 0) || (newval & 0x60) == 0x60)))
5483 {
5484 as_bad_where (fixP->fx_file, fixP->fx_line,
5485 _("shift expression is too large"));
5486 break;
5487 }
5488
5489 if (value == 0)
5490 newval &= ~0x60; /* Shifts of zero must be done as lsl */
5491 else if (value == 32)
5492 value = 0;
5493 newval &= 0xfffff07f;
5494 newval |= (value & 0x1f) << 7;
5495 md_number_to_chars (buf, newval , INSN_SIZE);
5496 break;
5497
5498 case BFD_RELOC_ARM_SWI:
5499 if (arm_data->thumb_mode)
5500 {
5501 if (((unsigned long) value) > 0xff)
5502 as_bad_where (fixP->fx_file, fixP->fx_line,
5503 _("Invalid swi expression"));
5504 newval = md_chars_to_number (buf, THUMB_SIZE) & 0xff00;
5505 newval |= value;
5506 md_number_to_chars (buf, newval, THUMB_SIZE);
5507 }
5508 else
5509 {
5510 if (((unsigned long) value) > 0x00ffffff)
5511 as_bad_where (fixP->fx_file, fixP->fx_line,
5512 _("Invalid swi expression"));
5513 newval = md_chars_to_number (buf, INSN_SIZE) & 0xff000000;
5514 newval |= value;
5515 md_number_to_chars (buf, newval , INSN_SIZE);
5516 }
5517 break;
5518
5519 case BFD_RELOC_ARM_MULTI:
5520 if (((unsigned long) value) > 0xffff)
5521 as_bad_where (fixP->fx_file, fixP->fx_line,
5522 _("Invalid expression in load/store multiple"));
5523 newval = value | md_chars_to_number (buf, INSN_SIZE);
5524 md_number_to_chars (buf, newval, INSN_SIZE);
5525 break;
5526
5527 case BFD_RELOC_ARM_PCREL_BRANCH:
5528 newval = md_chars_to_number (buf, INSN_SIZE);
5529
5530 #ifdef OBJ_ELF
5531 if (! target_oabi)
5532 value = fixP->fx_offset;
5533 #endif
5534 value = (value >> 2) & 0x00ffffff;
5535 value = (value + (newval & 0x00ffffff)) & 0x00ffffff;
5536 newval = value | (newval & 0xff000000);
5537 md_number_to_chars (buf, newval, INSN_SIZE);
5538 break;
5539
5540
5541 case BFD_RELOC_THUMB_PCREL_BRANCH9: /* conditional branch */
5542 newval = md_chars_to_number (buf, THUMB_SIZE);
5543 {
5544 addressT diff = (newval & 0xff) << 1;
5545 if (diff & 0x100)
5546 diff |= ~0xff;
5547
5548 value += diff;
5549 if ((value & ~0xff) && ((value & ~0xff) != ~0xff))
5550 as_bad_where (fixP->fx_file, fixP->fx_line,
5551 _("Branch out of range"));
5552 newval = (newval & 0xff00) | ((value & 0x1ff) >> 1);
5553 }
5554 md_number_to_chars (buf, newval, THUMB_SIZE);
5555 break;
5556
5557 case BFD_RELOC_THUMB_PCREL_BRANCH12: /* unconditional branch */
5558 newval = md_chars_to_number (buf, THUMB_SIZE);
5559 {
5560 addressT diff = (newval & 0x7ff) << 1;
5561 if (diff & 0x800)
5562 diff |= ~0x7ff;
5563
5564 value += diff;
5565 if ((value & ~0x7ff) && ((value & ~0x7ff) != ~0x7ff))
5566 as_bad_where (fixP->fx_file, fixP->fx_line,
5567 _("Branch out of range"));
5568 newval = (newval & 0xf800) | ((value & 0xfff) >> 1);
5569 }
5570 md_number_to_chars (buf, newval, THUMB_SIZE);
5571 break;
5572
5573 case BFD_RELOC_THUMB_PCREL_BRANCH23:
5574 {
5575 offsetT newval2;
5576 addressT diff;
5577
5578 newval = md_chars_to_number (buf, THUMB_SIZE);
5579 newval2 = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE);
5580 diff = ((newval & 0x7ff) << 12) | ((newval2 & 0x7ff) << 1);
5581 if (diff & 0x400000)
5582 diff |= ~0x3fffff;
5583 #ifdef OBJ_ELF
5584 value = fixP->fx_offset;
5585 #endif
5586 value += diff;
5587 if ((value & ~0x3fffff) && ((value & ~0x3fffff) != ~0x3fffff))
5588 as_bad_where (fixP->fx_file, fixP->fx_line,
5589 _("Branch with link out of range"));
5590
5591 newval = (newval & 0xf800) | ((value & 0x7fffff) >> 12);
5592 newval2 = (newval2 & 0xf800) | ((value & 0xfff) >> 1);
5593 md_number_to_chars (buf, newval, THUMB_SIZE);
5594 md_number_to_chars (buf + THUMB_SIZE, newval2, THUMB_SIZE);
5595 }
5596 break;
5597
5598 case BFD_RELOC_8:
5599 if (fixP->fx_done || fixP->fx_pcrel)
5600 md_number_to_chars (buf, value, 1);
5601 #ifdef OBJ_ELF
5602 else if (!target_oabi)
5603 {
5604 value = fixP->fx_offset;
5605 md_number_to_chars (buf, value, 1);
5606 }
5607 #endif
5608 break;
5609
5610 case BFD_RELOC_16:
5611 if (fixP->fx_done || fixP->fx_pcrel)
5612 md_number_to_chars (buf, value, 2);
5613 #ifdef OBJ_ELF
5614 else if (!target_oabi)
5615 {
5616 value = fixP->fx_offset;
5617 md_number_to_chars (buf, value, 2);
5618 }
5619 #endif
5620 break;
5621
5622 #ifdef OBJ_ELF
5623 case BFD_RELOC_ARM_GOT32:
5624 case BFD_RELOC_ARM_GOTOFF:
5625 md_number_to_chars (buf, 0, 4);
5626 break;
5627 #endif
5628
5629 case BFD_RELOC_RVA:
5630 case BFD_RELOC_32:
5631 if (fixP->fx_done || fixP->fx_pcrel)
5632 md_number_to_chars (buf, value, 4);
5633 #ifdef OBJ_ELF
5634 else if (!target_oabi)
5635 {
5636 value = fixP->fx_offset;
5637 md_number_to_chars (buf, value, 4);
5638 }
5639 #endif
5640 break;
5641
5642 #ifdef OBJ_ELF
5643 case BFD_RELOC_ARM_PLT32:
5644 /* It appears the instruction is fully prepared at this point. */
5645 break;
5646 #endif
5647
5648 case BFD_RELOC_ARM_GOTPC:
5649 md_number_to_chars (buf, value, 4);
5650 break;
5651
5652 case BFD_RELOC_ARM_CP_OFF_IMM:
5653 sign = value >= 0;
5654 if (value < -1023 || value > 1023 || (value & 3))
5655 as_bad_where (fixP->fx_file, fixP->fx_line,
5656 _("Illegal value for co-processor offset"));
5657 if (value < 0)
5658 value = -value;
5659 newval = md_chars_to_number (buf, INSN_SIZE) & 0xff7fff00;
5660 newval |= (value >> 2) | (sign ? INDEX_UP : 0);
5661 md_number_to_chars (buf, newval , INSN_SIZE);
5662 break;
5663
5664 case BFD_RELOC_ARM_THUMB_OFFSET:
5665 newval = md_chars_to_number (buf, THUMB_SIZE);
5666 /* Exactly what ranges, and where the offset is inserted depends on
5667 the type of instruction, we can establish this from the top 4 bits */
5668 switch (newval >> 12)
5669 {
5670 case 4: /* PC load */
5671 /* Thumb PC loads are somewhat odd, bit 1 of the PC is
5672 forced to zero for these loads, so we will need to round
5673 up the offset if the instruction address is not word
5674 aligned (since the final address produced must be, and
5675 we can only describe word-aligned immediate offsets). */
5676
5677 if ((fixP->fx_frag->fr_address + fixP->fx_where + value) & 3)
5678 as_bad_where (fixP->fx_file, fixP->fx_line,
5679 _("Invalid offset, target not word aligned (0x%08X)"),
5680 (unsigned int)(fixP->fx_frag->fr_address + fixP->fx_where + value));
5681
5682 if ((value + 2) & ~0x3fe)
5683 as_bad_where (fixP->fx_file, fixP->fx_line,
5684 _("Invalid offset, value too big (0x%08X)"), value);
5685
5686 /* Round up, since pc will be rounded down. */
5687 newval |= (value + 2) >> 2;
5688 break;
5689
5690 case 9: /* SP load/store */
5691 if (value & ~0x3fc)
5692 as_bad_where (fixP->fx_file, fixP->fx_line,
5693 _("Invalid offset, value too big (0x%08X)"), value);
5694 newval |= value >> 2;
5695 break;
5696
5697 case 6: /* Word load/store */
5698 if (value & ~0x7c)
5699 as_bad_where (fixP->fx_file, fixP->fx_line,
5700 _("Invalid offset, value too big (0x%08X)"), value);
5701 newval |= value << 4; /* 6 - 2 */
5702 break;
5703
5704 case 7: /* Byte load/store */
5705 if (value & ~0x1f)
5706 as_bad_where (fixP->fx_file, fixP->fx_line,
5707 _("Invalid offset, value too big (0x%08X)"), value);
5708 newval |= value << 6;
5709 break;
5710
5711 case 8: /* Halfword load/store */
5712 if (value & ~0x3e)
5713 as_bad_where (fixP->fx_file, fixP->fx_line,
5714 _("Invalid offset, value too big (0x%08X)"), value);
5715 newval |= value << 5; /* 6 - 1 */
5716 break;
5717
5718 default:
5719 as_bad_where (fixP->fx_file, fixP->fx_line,
5720 "Unable to process relocation for thumb opcode: %lx",
5721 (unsigned long) newval);
5722 break;
5723 }
5724 md_number_to_chars (buf, newval, THUMB_SIZE);
5725 break;
5726
5727 case BFD_RELOC_ARM_THUMB_ADD:
5728 /* This is a complicated relocation, since we use it for all of
5729 the following immediate relocations:
5730 3bit ADD/SUB
5731 8bit ADD/SUB
5732 9bit ADD/SUB SP word-aligned
5733 10bit ADD PC/SP word-aligned
5734
5735 The type of instruction being processed is encoded in the
5736 instruction field:
5737 0x8000 SUB
5738 0x00F0 Rd
5739 0x000F Rs
5740 */
5741 newval = md_chars_to_number (buf, THUMB_SIZE);
5742 {
5743 int rd = (newval >> 4) & 0xf;
5744 int rs = newval & 0xf;
5745 int subtract = newval & 0x8000;
5746
5747 if (rd == REG_SP)
5748 {
5749 if (value & ~0x1fc)
5750 as_bad_where (fixP->fx_file, fixP->fx_line,
5751 _("Invalid immediate for stack address calculation"));
5752 newval = subtract ? T_OPCODE_SUB_ST : T_OPCODE_ADD_ST;
5753 newval |= value >> 2;
5754 }
5755 else if (rs == REG_PC || rs == REG_SP)
5756 {
5757 if (subtract ||
5758 value & ~0x3fc)
5759 as_bad_where (fixP->fx_file, fixP->fx_line,
5760 _("Invalid immediate for address calculation (value = 0x%08lX)"),
5761 (unsigned long) value);
5762 newval = (rs == REG_PC ? T_OPCODE_ADD_PC : T_OPCODE_ADD_SP);
5763 newval |= rd << 8;
5764 newval |= value >> 2;
5765 }
5766 else if (rs == rd)
5767 {
5768 if (value & ~0xff)
5769 as_bad_where (fixP->fx_file, fixP->fx_line,
5770 _("Invalid 8bit immediate"));
5771 newval = subtract ? T_OPCODE_SUB_I8 : T_OPCODE_ADD_I8;
5772 newval |= (rd << 8) | value;
5773 }
5774 else
5775 {
5776 if (value & ~0x7)
5777 as_bad_where (fixP->fx_file, fixP->fx_line,
5778 _("Invalid 3bit immediate"));
5779 newval = subtract ? T_OPCODE_SUB_I3 : T_OPCODE_ADD_I3;
5780 newval |= rd | (rs << 3) | (value << 6);
5781 }
5782 }
5783 md_number_to_chars (buf, newval , THUMB_SIZE);
5784 break;
5785
5786 case BFD_RELOC_ARM_THUMB_IMM:
5787 newval = md_chars_to_number (buf, THUMB_SIZE);
5788 switch (newval >> 11)
5789 {
5790 case 0x04: /* 8bit immediate MOV */
5791 case 0x05: /* 8bit immediate CMP */
5792 if (value < 0 || value > 255)
5793 as_bad_where (fixP->fx_file, fixP->fx_line,
5794 _("Invalid immediate: %ld is too large"),
5795 (long) value);
5796 newval |= value;
5797 break;
5798
5799 default:
5800 abort ();
5801 }
5802 md_number_to_chars (buf, newval , THUMB_SIZE);
5803 break;
5804
5805 case BFD_RELOC_ARM_THUMB_SHIFT:
5806 /* 5bit shift value (0..31) */
5807 if (value < 0 || value > 31)
5808 as_bad_where (fixP->fx_file, fixP->fx_line,
5809 _("Illegal Thumb shift value: %ld"), (long) value);
5810 newval = md_chars_to_number (buf, THUMB_SIZE) & 0xf03f;
5811 newval |= value << 6;
5812 md_number_to_chars (buf, newval , THUMB_SIZE);
5813 break;
5814
5815 case BFD_RELOC_VTABLE_INHERIT:
5816 case BFD_RELOC_VTABLE_ENTRY:
5817 fixP->fx_done = 0;
5818 return 1;
5819
5820 case BFD_RELOC_NONE:
5821 default:
5822 as_bad_where (fixP->fx_file, fixP->fx_line,
5823 _("Bad relocation fixup type (%d)"), fixP->fx_r_type);
5824 }
5825
5826 return 1;
5827 }
5828
5829 /* Translate internal representation of relocation info to BFD target
5830 format. */
5831 arelent *
5832 tc_gen_reloc (section, fixp)
5833 asection * section;
5834 fixS * fixp;
5835 {
5836 arelent * reloc;
5837 bfd_reloc_code_real_type code;
5838
5839 reloc = (arelent *) xmalloc (sizeof (arelent));
5840
5841 reloc->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
5842 *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
5843 reloc->address = fixp->fx_frag->fr_address + fixp->fx_where;
5844
5845 /* @@ Why fx_addnumber sometimes and fx_offset other times? */
5846 #ifndef OBJ_ELF
5847 if (fixp->fx_pcrel == 0)
5848 reloc->addend = fixp->fx_offset;
5849 else
5850 reloc->addend = fixp->fx_offset = reloc->address;
5851 #else /* OBJ_ELF */
5852 reloc->addend = fixp->fx_offset;
5853 #endif
5854
5855 switch (fixp->fx_r_type)
5856 {
5857 case BFD_RELOC_8:
5858 if (fixp->fx_pcrel)
5859 {
5860 code = BFD_RELOC_8_PCREL;
5861 break;
5862 }
5863
5864 case BFD_RELOC_16:
5865 if (fixp->fx_pcrel)
5866 {
5867 code = BFD_RELOC_16_PCREL;
5868 break;
5869 }
5870
5871 case BFD_RELOC_32:
5872 if (fixp->fx_pcrel)
5873 {
5874 code = BFD_RELOC_32_PCREL;
5875 break;
5876 }
5877
5878 case BFD_RELOC_ARM_PCREL_BRANCH:
5879 case BFD_RELOC_RVA:
5880 case BFD_RELOC_THUMB_PCREL_BRANCH9:
5881 case BFD_RELOC_THUMB_PCREL_BRANCH12:
5882 case BFD_RELOC_THUMB_PCREL_BRANCH23:
5883 case BFD_RELOC_VTABLE_ENTRY:
5884 case BFD_RELOC_VTABLE_INHERIT:
5885 code = fixp->fx_r_type;
5886 break;
5887
5888 case BFD_RELOC_ARM_LITERAL:
5889 case BFD_RELOC_ARM_HWLITERAL:
5890 /* If this is called then the a literal has been referenced across
5891 a section boundary - possibly due to an implicit dump */
5892 as_bad_where (fixp->fx_file, fixp->fx_line,
5893 _("Literal referenced across section boundary (Implicit dump?)"));
5894 return NULL;
5895
5896 #ifdef OBJ_ELF
5897 case BFD_RELOC_ARM_GOT32:
5898 case BFD_RELOC_ARM_GOTOFF:
5899 case BFD_RELOC_ARM_PLT32:
5900 code = fixp->fx_r_type;
5901 break;
5902 #endif
5903
5904 case BFD_RELOC_ARM_IMMEDIATE:
5905 as_bad_where (fixp->fx_file, fixp->fx_line,
5906 _("Internal_relocation (type %d) not fixed up (IMMEDIATE)"),
5907 fixp->fx_r_type);
5908 return NULL;
5909
5910 case BFD_RELOC_ARM_ADRL_IMMEDIATE:
5911 as_bad_where (fixp->fx_file, fixp->fx_line,
5912 _("ADRL used for a symbol not defined in the same file"),
5913 fixp->fx_r_type);
5914 return NULL;
5915
5916 case BFD_RELOC_ARM_OFFSET_IMM:
5917 as_bad_where (fixp->fx_file, fixp->fx_line,
5918 _("Internal_relocation (type %d) not fixed up (OFFSET_IMM)"),
5919 fixp->fx_r_type);
5920 return NULL;
5921
5922 default:
5923 {
5924 char * type;
5925 switch (fixp->fx_r_type)
5926 {
5927 case BFD_RELOC_ARM_IMMEDIATE: type = "IMMEDIATE"; break;
5928 case BFD_RELOC_ARM_OFFSET_IMM: type = "OFFSET_IMM"; break;
5929 case BFD_RELOC_ARM_OFFSET_IMM8: type = "OFFSET_IMM8"; break;
5930 case BFD_RELOC_ARM_SHIFT_IMM: type = "SHIFT_IMM"; break;
5931 case BFD_RELOC_ARM_SWI: type = "SWI"; break;
5932 case BFD_RELOC_ARM_MULTI: type = "MULTI"; break;
5933 case BFD_RELOC_ARM_CP_OFF_IMM: type = "CP_OFF_IMM"; break;
5934 case BFD_RELOC_ARM_THUMB_ADD: type = "THUMB_ADD"; break;
5935 case BFD_RELOC_ARM_THUMB_SHIFT: type = "THUMB_SHIFT"; break;
5936 case BFD_RELOC_ARM_THUMB_IMM: type = "THUMB_IMM"; break;
5937 case BFD_RELOC_ARM_THUMB_OFFSET: type = "THUMB_OFFSET"; break;
5938 default: type = _("<unknown>"); break;
5939 }
5940 as_bad_where (fixp->fx_file, fixp->fx_line,
5941 _("Can not represent %s relocation in this object file format (%d)"),
5942 type, fixp->fx_pcrel);
5943 return NULL;
5944 }
5945 }
5946
5947 #ifdef OBJ_ELF
5948 if (code == BFD_RELOC_32_PCREL
5949 && GOT_symbol
5950 && fixp->fx_addsy == GOT_symbol)
5951 {
5952 code = BFD_RELOC_ARM_GOTPC;
5953 reloc->addend = fixp->fx_offset = reloc->address;
5954 }
5955 #endif
5956
5957 reloc->howto = bfd_reloc_type_lookup (stdoutput, code);
5958
5959 if (reloc->howto == NULL)
5960 {
5961 as_bad_where (fixp->fx_file, fixp->fx_line,
5962 _("Can not represent %s relocation in this object file format"),
5963 bfd_get_reloc_code_name (code));
5964 return NULL;
5965 }
5966
5967 /* HACK: Since arm ELF uses Rel instead of Rela, encode the
5968 vtable entry to be used in the relocation's section offset. */
5969 if (fixp->fx_r_type == BFD_RELOC_VTABLE_ENTRY)
5970 reloc->address = fixp->fx_offset;
5971
5972 return reloc;
5973 }
5974
5975 int
5976 md_estimate_size_before_relax (fragP, segtype)
5977 fragS * fragP;
5978 segT segtype;
5979 {
5980 as_fatal (_("md_estimate_size_before_relax\n"));
5981 return 1;
5982 }
5983
5984 static void
5985 output_inst PARAMS ((void))
5986 {
5987 char * to = NULL;
5988
5989 if (inst.error)
5990 {
5991 as_bad (inst.error);
5992 return;
5993 }
5994
5995 to = frag_more (inst.size);
5996
5997 if (thumb_mode && (inst.size > THUMB_SIZE))
5998 {
5999 assert (inst.size == (2 * THUMB_SIZE));
6000 md_number_to_chars (to, inst.instruction >> 16, THUMB_SIZE);
6001 md_number_to_chars (to + THUMB_SIZE, inst.instruction, THUMB_SIZE);
6002 }
6003 else if (inst.size > INSN_SIZE)
6004 {
6005 assert (inst.size == (2 * INSN_SIZE));
6006 md_number_to_chars (to, inst.instruction, INSN_SIZE);
6007 md_number_to_chars (to + INSN_SIZE, inst.instruction, INSN_SIZE);
6008 }
6009 else
6010 md_number_to_chars (to, inst.instruction, inst.size);
6011
6012 if (inst.reloc.type != BFD_RELOC_NONE)
6013 fix_new_arm (frag_now, to - frag_now->fr_literal,
6014 inst.size, & inst.reloc.exp, inst.reloc.pc_rel,
6015 inst.reloc.type);
6016
6017 return;
6018 }
6019
6020 void
6021 md_assemble (str)
6022 char * str;
6023 {
6024 char c;
6025 char * p;
6026 char * q;
6027 char * start;
6028
6029 /* Align the instruction.
6030 This may not be the right thing to do but ... */
6031 /* arm_align (2, 0); */
6032 listing_prev_line (); /* Defined in listing.h */
6033
6034 /* Align the previous label if needed. */
6035 if (last_label_seen != NULL)
6036 {
6037 symbol_set_frag (last_label_seen, frag_now);
6038 S_SET_VALUE (last_label_seen, (valueT) frag_now_fix ());
6039 S_SET_SEGMENT (last_label_seen, now_seg);
6040 }
6041
6042 memset (&inst, '\0', sizeof (inst));
6043 inst.reloc.type = BFD_RELOC_NONE;
6044
6045 skip_whitespace (str);
6046
6047 /* Scan up to the end of the op-code, which must end in white space or
6048 end of string. */
6049 for (start = p = str; *p != '\0'; p++)
6050 if (*p == ' ')
6051 break;
6052
6053 if (p == str)
6054 {
6055 as_bad (_("No operator -- statement `%s'\n"), str);
6056 return;
6057 }
6058
6059 if (thumb_mode)
6060 {
6061 CONST struct thumb_opcode * opcode;
6062
6063 c = *p;
6064 *p = '\0';
6065 opcode = (CONST struct thumb_opcode *) hash_find (arm_tops_hsh, str);
6066 *p = c;
6067
6068 if (opcode)
6069 {
6070 /* Check that this instruction is supported for this CPU. */
6071 if ((opcode->variants & cpu_variant) == 0)
6072 {
6073 as_bad (_("selected processor does not support this opcode"));
6074 return;
6075 }
6076
6077 inst.instruction = opcode->value;
6078 inst.size = opcode->size;
6079 (*opcode->parms)(p);
6080 output_inst ();
6081 return;
6082 }
6083 }
6084 else
6085 {
6086 CONST struct asm_opcode * opcode;
6087 unsigned long cond_code;
6088
6089 inst.size = INSN_SIZE;
6090 /* p now points to the end of the opcode, probably white space, but we
6091 have to break the opcode up in case it contains condionals and flags;
6092 keep trying with progressively smaller basic instructions until one
6093 matches, or we run out of opcode. */
6094 q = (p - str > LONGEST_INST) ? str + LONGEST_INST : p;
6095 for (; q != str; q--)
6096 {
6097 c = *q;
6098 *q = '\0';
6099 opcode = (CONST struct asm_opcode *) hash_find (arm_ops_hsh, str);
6100 *q = c;
6101
6102 if (opcode && opcode->template)
6103 {
6104 unsigned long flag_bits = 0;
6105 char * r;
6106
6107 /* Check that this instruction is supported for this CPU. */
6108 if ((opcode->variants & cpu_variant) == 0)
6109 goto try_shorter;
6110
6111 inst.instruction = opcode->value;
6112 if (q == p) /* Just a simple opcode. */
6113 {
6114 if (opcode->comp_suffix)
6115 {
6116 if (*opcode->comp_suffix != '\0')
6117 as_bad (_("Opcode `%s' must have suffix from <%s>\n"),
6118 str, opcode->comp_suffix);
6119 else
6120 /* Not a conditional instruction. */
6121 (*opcode->parms)(q, 0);
6122 }
6123 else
6124 {
6125 /* A conditional instruction with default condition. */
6126 inst.instruction |= COND_ALWAYS;
6127 (*opcode->parms)(q, 0);
6128 }
6129 output_inst ();
6130 return;
6131 }
6132
6133 /* Not just a simple opcode. Check if extra is a conditional. */
6134 r = q;
6135 if (p - r >= 2)
6136 {
6137 CONST struct asm_cond *cond;
6138 char d = *(r + 2);
6139
6140 *(r + 2) = '\0';
6141 cond = (CONST struct asm_cond *) hash_find (arm_cond_hsh, r);
6142 *(r + 2) = d;
6143 if (cond)
6144 {
6145 if (cond->value == 0xf0000000)
6146 as_tsktsk (
6147 _("Warning: Use of the 'nv' conditional is deprecated\n"));
6148
6149 cond_code = cond->value;
6150 r += 2;
6151 }
6152 else
6153 cond_code = COND_ALWAYS;
6154 }
6155 else
6156 cond_code = COND_ALWAYS;
6157
6158
6159 /* Apply the conditional, or complain it's not allowed. */
6160 if (opcode->comp_suffix && *opcode->comp_suffix == '\0')
6161 {
6162 /* Instruction isn't conditional */
6163 if (cond_code != COND_ALWAYS)
6164 {
6165 as_bad (_("Opcode `%s' is unconditional\n"), str);
6166 return;
6167 }
6168 }
6169 else
6170 /* Instruction is conditional: set the condition into it. */
6171 inst.instruction |= cond_code;
6172
6173
6174 /* If there is a compulsory suffix, it should come here, before
6175 any optional flags. */
6176 if (opcode->comp_suffix && *opcode->comp_suffix != '\0')
6177 {
6178 CONST char *s = opcode->comp_suffix;
6179
6180 while (*s)
6181 {
6182 inst.suffix++;
6183 if (*r == *s)
6184 break;
6185 s++;
6186 }
6187
6188 if (*s == '\0')
6189 {
6190 as_bad (_("Opcode `%s' must have suffix from <%s>\n"), str,
6191 opcode->comp_suffix);
6192 return;
6193 }
6194
6195 r++;
6196 }
6197
6198 /* The remainder, if any should now be flags for the instruction;
6199 Scan these checking each one found with the opcode. */
6200 if (r != p)
6201 {
6202 char d;
6203 CONST struct asm_flg *flag = opcode->flags;
6204
6205 if (flag)
6206 {
6207 int flagno;
6208
6209 d = *p;
6210 *p = '\0';
6211
6212 for (flagno = 0; flag[flagno].template; flagno++)
6213 {
6214 if (streq (r, flag[flagno].template))
6215 {
6216 flag_bits |= flag[flagno].set_bits;
6217 break;
6218 }
6219 }
6220
6221 *p = d;
6222 if (! flag[flagno].template)
6223 goto try_shorter;
6224 }
6225 else
6226 goto try_shorter;
6227 }
6228
6229 (*opcode->parms) (p, flag_bits);
6230 output_inst ();
6231 return;
6232 }
6233
6234 try_shorter:
6235 ;
6236 }
6237 }
6238
6239 /* It wasn't an instruction, but it might be a register alias of the form
6240 alias .req reg */
6241 q = p;
6242 skip_whitespace (q);
6243
6244 c = *p;
6245 *p = '\0';
6246
6247 if (*q && !strncmp (q, ".req ", 4))
6248 {
6249 int reg;
6250 char * copy_of_str = str;
6251 char * r;
6252
6253 q += 4;
6254 skip_whitespace (q);
6255
6256 for (r = q; *r != '\0'; r++)
6257 if (*r == ' ')
6258 break;
6259
6260 if (r != q)
6261 {
6262 int regnum;
6263 char d = *r;
6264
6265 *r = '\0';
6266 regnum = arm_reg_parse (& q);
6267 *r = d;
6268
6269 reg = arm_reg_parse (& str);
6270
6271 if (reg == FAIL)
6272 {
6273 if (regnum != FAIL)
6274 insert_reg_alias (str, regnum);
6275 else
6276 as_warn (_("register '%s' does not exist\n"), q);
6277 }
6278 else if (regnum != FAIL)
6279 {
6280 if (reg != regnum)
6281 as_warn (_("ignoring redefinition of register alias '%s'"), copy_of_str );
6282
6283 /* Do not warn about redefinitions to the same alias. */
6284 }
6285 else
6286 as_warn (_("ignoring redefinition of register alias '%s' to non-existant register '%s'"),
6287 copy_of_str, q);
6288 }
6289 else
6290 as_warn (_("ignoring incomplete .req pseuso op"));
6291
6292 *p = c;
6293 return;
6294 }
6295
6296 *p = c;
6297 as_bad (_("bad instruction `%s'"), start);
6298 }
6299
6300 /*
6301 * md_parse_option
6302 * Invocation line includes a switch not recognized by the base assembler.
6303 * See if it's a processor-specific option. These are:
6304 * Cpu variants, the arm part is optional:
6305 * -m[arm]1 Currently not supported.
6306 * -m[arm]2, -m[arm]250 Arm 2 and Arm 250 processor
6307 * -m[arm]3 Arm 3 processor
6308 * -m[arm]6[xx], Arm 6 processors
6309 * -m[arm]7[xx][t][[d]m] Arm 7 processors
6310 * -m[arm]8[10] Arm 8 processors
6311 * -m[arm]9[20][tdmi] Arm 9 processors
6312 * -mstrongarm[110[0]] StrongARM processors
6313 * -m[arm]v[2345] Arm architectures
6314 * -mall All (except the ARM1)
6315 * FP variants:
6316 * -mfpa10, -mfpa11 FPA10 and 11 co-processor instructions
6317 * -mfpe-old (No float load/store multiples)
6318 * -mno-fpu Disable all floating point instructions
6319 * Run-time endian selection:
6320 * -EB big endian cpu
6321 * -EL little endian cpu
6322 * ARM Procedure Calling Standard:
6323 * -mapcs-32 32 bit APCS
6324 * -mapcs-26 26 bit APCS
6325 * -mapcs-float Pass floats in float regs
6326 * -mapcs-reentrant Position independent code
6327 * -mthumb-interwork Code supports Arm/Thumb interworking
6328 * -moabi Old ELF ABI
6329 */
6330
6331 CONST char * md_shortopts = "m:k";
6332 struct option md_longopts[] =
6333 {
6334 #ifdef ARM_BI_ENDIAN
6335 #define OPTION_EB (OPTION_MD_BASE + 0)
6336 {"EB", no_argument, NULL, OPTION_EB},
6337 #define OPTION_EL (OPTION_MD_BASE + 1)
6338 {"EL", no_argument, NULL, OPTION_EL},
6339 #ifdef OBJ_ELF
6340 #define OPTION_OABI (OPTION_MD_BASE +2)
6341 {"oabi", no_argument, NULL, OPTION_OABI},
6342 #endif
6343 #endif
6344 {NULL, no_argument, NULL, 0}
6345 };
6346 size_t md_longopts_size = sizeof (md_longopts);
6347
6348 int
6349 md_parse_option (c, arg)
6350 int c;
6351 char * arg;
6352 {
6353 char * str = arg;
6354
6355 switch (c)
6356 {
6357 #ifdef ARM_BI_ENDIAN
6358 case OPTION_EB:
6359 target_big_endian = 1;
6360 break;
6361 case OPTION_EL:
6362 target_big_endian = 0;
6363 break;
6364 #endif
6365
6366 case 'm':
6367 switch (*str)
6368 {
6369 case 'f':
6370 if (streq (str, "fpa10"))
6371 cpu_variant = (cpu_variant & ~FPU_ALL) | FPU_FPA10;
6372 else if (streq (str, "fpa11"))
6373 cpu_variant = (cpu_variant & ~FPU_ALL) | FPU_FPA11;
6374 else if (streq (str, "fpe-old"))
6375 cpu_variant = (cpu_variant & ~FPU_ALL) | FPU_CORE;
6376 else
6377 goto bad;
6378 break;
6379
6380 case 'n':
6381 if (streq (str, "no-fpu"))
6382 cpu_variant &= ~FPU_ALL;
6383 break;
6384
6385 #ifdef OBJ_ELF
6386 case 'o':
6387 if (streq (str, "oabi"))
6388 target_oabi = true;
6389 break;
6390 #endif
6391
6392 case 't':
6393 /* Limit assembler to generating only Thumb instructions: */
6394 if (streq (str, "thumb"))
6395 {
6396 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_THUMB;
6397 cpu_variant = (cpu_variant & ~FPU_ALL) | FPU_NONE;
6398 thumb_mode = 1;
6399 }
6400 else if (streq (str, "thumb-interwork"))
6401 {
6402 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_THUMB | ARM_ARCH_V4;
6403 #if defined OBJ_COFF || defined OBJ_ELF
6404 support_interwork = true;
6405 #endif
6406 }
6407 else
6408 goto bad;
6409 break;
6410
6411 default:
6412 if (streq (str, "all"))
6413 {
6414 cpu_variant = ARM_ALL | FPU_ALL;
6415 return 1;
6416 }
6417 #if defined OBJ_COFF || defined OBJ_ELF
6418 if (! strncmp (str, "apcs-", 5))
6419 {
6420 /* GCC passes on all command line options starting "-mapcs-..."
6421 to us, so we must parse them here. */
6422
6423 str += 5;
6424
6425 if (streq (str, "32"))
6426 {
6427 uses_apcs_26 = false;
6428 return 1;
6429 }
6430 else if (streq (str, "26"))
6431 {
6432 uses_apcs_26 = true;
6433 return 1;
6434 }
6435 else if (streq (str, "frame"))
6436 {
6437 /* Stack frames are being generated - does not affect
6438 linkage of code. */
6439 return 1;
6440 }
6441 else if (streq (str, "stack-check"))
6442 {
6443 /* Stack checking is being performed - does not affect
6444 linkage, but does require that the functions
6445 __rt_stkovf_split_small and __rt_stkovf_split_big be
6446 present in the final link. */
6447
6448 return 1;
6449 }
6450 else if (streq (str, "float"))
6451 {
6452 /* Floating point arguments are being passed in the floating
6453 point registers. This does affect linking, since this
6454 version of the APCS is incompatible with the version that
6455 passes floating points in the integer registers. */
6456
6457 uses_apcs_float = true;
6458 return 1;
6459 }
6460 else if (streq (str, "reentrant"))
6461 {
6462 /* Reentrant code has been generated. This does affect
6463 linking, since there is no point in linking reentrant/
6464 position independent code with absolute position code. */
6465 pic_code = true;
6466 return 1;
6467 }
6468
6469 as_bad (_("Unrecognised APCS switch -m%s"), arg);
6470 return 0;
6471 }
6472 #endif
6473 /* Strip off optional "arm" */
6474 if (! strncmp (str, "arm", 3))
6475 str += 3;
6476
6477 switch (*str)
6478 {
6479 case '1':
6480 if (streq (str, "1"))
6481 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_1;
6482 else
6483 goto bad;
6484 break;
6485
6486 case '2':
6487 if (streq (str, "2"))
6488 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_2;
6489 else if (streq (str, "250"))
6490 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_250;
6491 else
6492 goto bad;
6493 break;
6494
6495 case '3':
6496 if (streq (str, "3"))
6497 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_3;
6498 else
6499 goto bad;
6500 break;
6501
6502 case '6':
6503 switch (strtol (str, NULL, 10))
6504 {
6505 case 6:
6506 case 60:
6507 case 600:
6508 case 610:
6509 case 620:
6510 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_6;
6511 break;
6512 default:
6513 goto bad;
6514 }
6515 break;
6516
6517 case '7':
6518 switch (strtol (str, & str, 10)) /* Eat the processor name */
6519 {
6520 case 7:
6521 case 70:
6522 case 700:
6523 case 710:
6524 case 7100:
6525 case 7500:
6526 break;
6527 default:
6528 goto bad;
6529 }
6530 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_7;
6531 for (; *str; str++)
6532 {
6533 switch (* str)
6534 {
6535 case 't':
6536 cpu_variant |= (ARM_THUMB | ARM_ARCH_V4);
6537 break;
6538
6539 case 'm':
6540 cpu_variant |= ARM_LONGMUL;
6541 break;
6542
6543 case 'f': /* fe => fp enabled cpu. */
6544 if (str[1] == 'e')
6545 ++ str;
6546 else
6547 goto bad;
6548
6549 case 'c': /* Left over from 710c processor name. */
6550 case 'd': /* Debug */
6551 case 'i': /* Embedded ICE */
6552 /* Included for completeness in ARM processor naming. */
6553 break;
6554
6555 default:
6556 goto bad;
6557 }
6558 }
6559 break;
6560
6561 case '8':
6562 if (streq (str, "8") || streq (str, "810"))
6563 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_8 | ARM_ARCH_V4 | ARM_LONGMUL;
6564 else
6565 goto bad;
6566 break;
6567
6568 case '9':
6569 if (streq (str, "9"))
6570 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_9 | ARM_ARCH_V4 | ARM_LONGMUL | ARM_THUMB;
6571 else if (streq (str, "920"))
6572 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_9 | ARM_ARCH_V4 | ARM_LONGMUL;
6573 else if (streq (str, "920t"))
6574 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_9 | ARM_ARCH_V4 | ARM_LONGMUL | ARM_THUMB;
6575 else if (streq (str, "9tdmi"))
6576 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_9 | ARM_ARCH_V4 | ARM_LONGMUL | ARM_THUMB;
6577 else
6578 goto bad;
6579 break;
6580
6581
6582 case 's':
6583 if (streq (str, "strongarm")
6584 || streq (str, "strongarm110")
6585 || streq (str, "strongarm1100"))
6586 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_8 | ARM_ARCH_V4 | ARM_LONGMUL;
6587 else
6588 goto bad;
6589 break;
6590
6591 case 'v':
6592 /* Select variant based on architecture rather than processor */
6593 switch (*++str)
6594 {
6595 case '2':
6596 switch (*++str)
6597 {
6598 case 'a': cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_3; break;
6599 case 0: cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_2; break;
6600 default: as_bad (_("Invalid architecture variant -m%s"), arg); break;
6601 }
6602 break;
6603
6604 case '3':
6605 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_7;
6606
6607 switch (*++str)
6608 {
6609 case 'm': cpu_variant |= ARM_LONGMUL; break;
6610 case 0: break;
6611 default: as_bad (_("Invalid architecture variant -m%s"), arg); break;
6612 }
6613 break;
6614
6615 case '4':
6616 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_ARCH_V4;
6617
6618 switch (*++str)
6619 {
6620 case 't': cpu_variant |= ARM_THUMB; break;
6621 case 0: break;
6622 default: as_bad (_("Invalid architecture variant -m%s"), arg); break;
6623 }
6624 break;
6625
6626 case '5':
6627 cpu_variant = (cpu_variant & ~ARM_ANY) | ARM_ARCH_V5;
6628 switch (*++str)
6629 {
6630 case 't': cpu_variant |= ARM_THUMB; break;
6631 case 'e': cpu_variant |= ARM_EXT_V5E; break;
6632 case 0: break;
6633 default: as_bad (_("Invalid architecture variant -m%s"), arg); break;
6634 }
6635 break;
6636
6637
6638 default:
6639 as_bad (_("Invalid architecture variant -m%s"), arg);
6640 break;
6641 }
6642 break;
6643
6644 default:
6645 bad:
6646 as_bad (_("Invalid processor variant -m%s"), arg);
6647 return 0;
6648 }
6649 }
6650 break;
6651
6652 #if defined OBJ_ELF || defined OBJ_COFF
6653 case 'k':
6654 pic_code = 1;
6655 break;
6656 #endif
6657
6658 default:
6659 return 0;
6660 }
6661
6662 return 1;
6663 }
6664
6665 void
6666 md_show_usage (fp)
6667 FILE * fp;
6668 {
6669 fprintf (fp,
6670 _("\
6671 ARM Specific Assembler Options:\n\
6672 -m[arm][<processor name>] select processor variant\n\
6673 -m[arm]v[2|2a|3|3m|4|4t|5]select architecture variant\n\
6674 -mthumb only allow Thumb instructions\n\
6675 -mthumb-interwork mark the assembled code as supporting interworking\n\
6676 -mall allow any instruction\n\
6677 -mfpa10, -mfpa11 select floating point architecture\n\
6678 -mfpe-old don't allow floating-point multiple instructions\n\
6679 -mno-fpu don't allow any floating-point instructions.\n"));
6680 fprintf (fp,
6681 _("\
6682 -k generate PIC code.\n"));
6683 #if defined OBJ_COFF || defined OBJ_ELF
6684 fprintf (fp,
6685 _("\
6686 -mapcs-32, -mapcs-26 specify which ARM Procedure Calling Standard to use\n"));
6687 fprintf (fp,
6688 _("\
6689 -mapcs-float floating point args are passed in FP regs\n"));
6690 fprintf (fp,
6691 _("\
6692 -mapcs-reentrant the code is position independent/reentrant\n"));
6693 #endif
6694 #ifdef OBJ_ELF
6695 fprintf (fp,
6696 _("\
6697 -moabi support the old ELF ABI\n"));
6698 #endif
6699 #ifdef ARM_BI_ENDIAN
6700 fprintf (fp,
6701 _("\
6702 -EB assemble code for a big endian cpu\n\
6703 -EL assemble code for a little endian cpu\n"));
6704 #endif
6705 }
6706
6707 /* We need to be able to fix up arbitrary expressions in some statements.
6708 This is so that we can handle symbols that are an arbitrary distance from
6709 the pc. The most common cases are of the form ((+/-sym -/+ . - 8) & mask),
6710 which returns part of an address in a form which will be valid for
6711 a data instruction. We do this by pushing the expression into a symbol
6712 in the expr_section, and creating a fix for that. */
6713
6714 static void
6715 fix_new_arm (frag, where, size, exp, pc_rel, reloc)
6716 fragS * frag;
6717 int where;
6718 short int size;
6719 expressionS * exp;
6720 int pc_rel;
6721 int reloc;
6722 {
6723 fixS * new_fix;
6724 arm_fix_data * arm_data;
6725
6726 switch (exp->X_op)
6727 {
6728 case O_constant:
6729 case O_symbol:
6730 case O_add:
6731 case O_subtract:
6732 new_fix = fix_new_exp (frag, where, size, exp, pc_rel, reloc);
6733 break;
6734
6735 default:
6736 new_fix = fix_new (frag, where, size, make_expr_symbol (exp), 0,
6737 pc_rel, reloc);
6738 break;
6739 }
6740
6741 /* Mark whether the fix is to a THUMB instruction, or an ARM instruction */
6742 arm_data = (arm_fix_data *) obstack_alloc (& notes, sizeof (arm_fix_data));
6743 new_fix->tc_fix_data = (PTR) arm_data;
6744 arm_data->thumb_mode = thumb_mode;
6745
6746 return;
6747 }
6748
6749
6750 /* This fix_new is called by cons via TC_CONS_FIX_NEW. */
6751 void
6752 cons_fix_new_arm (frag, where, size, exp)
6753 fragS * frag;
6754 int where;
6755 int size;
6756 expressionS * exp;
6757 {
6758 bfd_reloc_code_real_type type;
6759 int pcrel = 0;
6760
6761 /* Pick a reloc ...
6762 *
6763 * @@ Should look at CPU word size.
6764 */
6765 switch (size)
6766 {
6767 case 2:
6768 type = BFD_RELOC_16;
6769 break;
6770 case 4:
6771 default:
6772 type = BFD_RELOC_32;
6773 break;
6774 case 8:
6775 type = BFD_RELOC_64;
6776 break;
6777 }
6778
6779 fix_new_exp (frag, where, (int) size, exp, pcrel, type);
6780 }
6781
6782 /* A good place to do this, although this was probably not intended
6783 for this kind of use. We need to dump the literal pool before
6784 references are made to a null symbol pointer. */
6785 void
6786 arm_cleanup ()
6787 {
6788 if (current_poolP == NULL)
6789 return;
6790
6791 subseg_set (text_section, 0); /* Put it at the end of text section. */
6792 s_ltorg (0);
6793 listing_prev_line ();
6794 }
6795
6796 void
6797 arm_start_line_hook ()
6798 {
6799 last_label_seen = NULL;
6800 }
6801
6802 void
6803 arm_frob_label (sym)
6804 symbolS * sym;
6805 {
6806 last_label_seen = sym;
6807
6808 ARM_SET_THUMB (sym, thumb_mode);
6809
6810 #if defined OBJ_COFF || defined OBJ_ELF
6811 ARM_SET_INTERWORK (sym, support_interwork);
6812 #endif
6813
6814 if (label_is_thumb_function_name)
6815 {
6816 /* When the address of a Thumb function is taken the bottom
6817 bit of that address should be set. This will allow
6818 interworking between Arm and Thumb functions to work
6819 correctly. */
6820
6821 THUMB_SET_FUNC (sym, 1);
6822
6823 label_is_thumb_function_name = false;
6824 }
6825 }
6826
6827 /* Adjust the symbol table. This marks Thumb symbols as distinct from
6828 ARM ones. */
6829
6830 void
6831 arm_adjust_symtab ()
6832 {
6833 #ifdef OBJ_COFF
6834 symbolS * sym;
6835
6836 for (sym = symbol_rootP; sym != NULL; sym = symbol_next (sym))
6837 {
6838 if (ARM_IS_THUMB (sym))
6839 {
6840 if (THUMB_IS_FUNC (sym))
6841 {
6842 /* Mark the symbol as a Thumb function. */
6843 if ( S_GET_STORAGE_CLASS (sym) == C_STAT
6844 || S_GET_STORAGE_CLASS (sym) == C_LABEL) /* This can happen! */
6845 S_SET_STORAGE_CLASS (sym, C_THUMBSTATFUNC);
6846
6847 else if (S_GET_STORAGE_CLASS (sym) == C_EXT)
6848 S_SET_STORAGE_CLASS (sym, C_THUMBEXTFUNC);
6849 else
6850 as_bad (_("%s: unexpected function type: %d"),
6851 S_GET_NAME (sym), S_GET_STORAGE_CLASS (sym));
6852 }
6853 else switch (S_GET_STORAGE_CLASS (sym))
6854 {
6855 case C_EXT:
6856 S_SET_STORAGE_CLASS (sym, C_THUMBEXT);
6857 break;
6858 case C_STAT:
6859 S_SET_STORAGE_CLASS (sym, C_THUMBSTAT);
6860 break;
6861 case C_LABEL:
6862 S_SET_STORAGE_CLASS (sym, C_THUMBLABEL);
6863 break;
6864 default: /* do nothing */
6865 break;
6866 }
6867 }
6868
6869 if (ARM_IS_INTERWORK (sym))
6870 coffsymbol (symbol_get_bfdsym (sym))->native->u.syment.n_flags = 0xFF;
6871 }
6872 #endif
6873 #ifdef OBJ_ELF
6874 symbolS * sym;
6875 elf_symbol_type * elf_sym;
6876 char bind;
6877
6878 for (sym = symbol_rootP; sym != NULL; sym = symbol_next (sym))
6879 {
6880 if (ARM_IS_THUMB (sym))
6881 {
6882 if (THUMB_IS_FUNC (sym))
6883 {
6884 elf_sym = elf_symbol (symbol_get_bfdsym (sym));
6885 bind = ELF_ST_BIND (elf_sym);
6886 elf_sym->internal_elf_sym.st_info = ELF_ST_INFO (bind, STT_ARM_TFUNC);
6887 }
6888 }
6889 }
6890 #endif
6891 }
6892
6893 int
6894 arm_data_in_code ()
6895 {
6896 if (thumb_mode && ! strncmp (input_line_pointer + 1, "data:", 5))
6897 {
6898 *input_line_pointer = '/';
6899 input_line_pointer += 5;
6900 *input_line_pointer = 0;
6901 return 1;
6902 }
6903
6904 return 0;
6905 }
6906
6907 char *
6908 arm_canonicalize_symbol_name (name)
6909 char * name;
6910 {
6911 int len;
6912
6913 if (thumb_mode && (len = strlen (name)) > 5
6914 && streq (name + len - 5, "/data"))
6915 *(name + len - 5) = 0;
6916
6917 return name;
6918 }
6919
6920 boolean
6921 arm_validate_fix (fixP)
6922 fixS * fixP;
6923 {
6924 /* If the destination of the branch is a defined symbol which does not have
6925 the THUMB_FUNC attribute, then we must be calling a function which has
6926 the (interfacearm) attribute. We look for the Thumb entry point to that
6927 function and change the branch to refer to that function instead. */
6928 if ( fixP->fx_r_type == BFD_RELOC_THUMB_PCREL_BRANCH23
6929 && fixP->fx_addsy != NULL
6930 && S_IS_DEFINED (fixP->fx_addsy)
6931 && ! THUMB_IS_FUNC (fixP->fx_addsy))
6932 {
6933 fixP->fx_addsy = find_real_start (fixP->fx_addsy);
6934 return true;
6935 }
6936
6937 return false;
6938 }
6939
6940 #ifdef OBJ_ELF
6941 /* Relocations against Thumb function names must be left unadjusted,
6942 so that the linker can use this information to correctly set the
6943 bottom bit of their addresses. The MIPS version of this function
6944 also prevents relocations that are mips-16 specific, but I do not
6945 know why it does this.
6946
6947 FIXME:
6948 There is one other problem that ought to be addressed here, but
6949 which currently is not: Taking the address of a label (rather
6950 than a function) and then later jumping to that address. Such
6951 addresses also ought to have their bottom bit set (assuming that
6952 they reside in Thumb code), but at the moment they will not. */
6953
6954 boolean
6955 arm_fix_adjustable (fixP)
6956 fixS * fixP;
6957 {
6958 if (fixP->fx_addsy == NULL)
6959 return 1;
6960
6961 /* Prevent all adjustments to global symbols. */
6962 if (S_IS_EXTERN (fixP->fx_addsy))
6963 return 0;
6964
6965 if (S_IS_WEAK (fixP->fx_addsy))
6966 return 0;
6967
6968 if (THUMB_IS_FUNC (fixP->fx_addsy)
6969 && fixP->fx_subsy == NULL)
6970 return 0;
6971
6972 /* We need the symbol name for the VTABLE entries */
6973 if ( fixP->fx_r_type == BFD_RELOC_VTABLE_INHERIT
6974 || fixP->fx_r_type == BFD_RELOC_VTABLE_ENTRY)
6975 return 0;
6976
6977 return 1;
6978 }
6979
6980 const char *
6981 elf32_arm_target_format ()
6982 {
6983 if (target_big_endian)
6984 if (target_oabi)
6985 return "elf32-bigarm-oabi";
6986 else
6987 return "elf32-bigarm";
6988 else
6989 if (target_oabi)
6990 return "elf32-littlearm-oabi";
6991 else
6992 return "elf32-littlearm";
6993 }
6994
6995 void
6996 armelf_frob_symbol (symp, puntp)
6997 symbolS * symp;
6998 int * puntp;
6999 {
7000 elf_frob_symbol (symp, puntp);
7001 }
7002
7003 int
7004 arm_force_relocation (fixp)
7005 struct fix * fixp;
7006 {
7007 if ( fixp->fx_r_type == BFD_RELOC_VTABLE_INHERIT
7008 || fixp->fx_r_type == BFD_RELOC_VTABLE_ENTRY
7009 || fixp->fx_r_type == BFD_RELOC_ARM_PCREL_BRANCH
7010 || fixp->fx_r_type == BFD_RELOC_THUMB_PCREL_BRANCH23)
7011 return 1;
7012
7013 return 0;
7014 }
7015
7016 static bfd_reloc_code_real_type
7017 arm_parse_reloc ()
7018 {
7019 char id[16];
7020 char * ip;
7021 int i;
7022 static struct
7023 {
7024 char * str;
7025 int len;
7026 bfd_reloc_code_real_type reloc;
7027 }
7028 reloc_map[] =
7029 {
7030 #define MAP(str,reloc) { str, sizeof (str)-1, reloc }
7031 MAP ("(got)", BFD_RELOC_ARM_GOT32),
7032 MAP ("(gotoff)", BFD_RELOC_ARM_GOTOFF),
7033 /* ScottB: Jan 30, 1998 */
7034 /* Added support for parsing "var(PLT)" branch instructions */
7035 /* generated by GCC for PLT relocs */
7036 MAP ("(plt)", BFD_RELOC_ARM_PLT32),
7037 { NULL, 0, BFD_RELOC_UNUSED }
7038 #undef MAP
7039 };
7040
7041 for (i = 0, ip = input_line_pointer;
7042 i < sizeof (id) && (isalnum (*ip) || ispunct (*ip));
7043 i++, ip++)
7044 id[i] = tolower (*ip);
7045
7046 for (i = 0; reloc_map[i].str; i++)
7047 if (strncmp (id, reloc_map[i].str, reloc_map[i].len) == 0)
7048 break;
7049
7050 input_line_pointer += reloc_map[i].len;
7051
7052 return reloc_map[i].reloc;
7053 }
7054
7055 static void
7056 s_arm_elf_cons (nbytes)
7057 int nbytes;
7058 {
7059 expressionS exp;
7060
7061 #ifdef md_flush_pending_output
7062 md_flush_pending_output ();
7063 #endif
7064
7065 if (is_it_end_of_statement ())
7066 {
7067 demand_empty_rest_of_line ();
7068 return;
7069 }
7070
7071 #ifdef md_cons_align
7072 md_cons_align (nbytes);
7073 #endif
7074
7075 do
7076 {
7077 bfd_reloc_code_real_type reloc;
7078
7079 expression (& exp);
7080
7081 if (exp.X_op == O_symbol
7082 && * input_line_pointer == '('
7083 && (reloc = arm_parse_reloc()) != BFD_RELOC_UNUSED)
7084 {
7085 reloc_howto_type * howto = bfd_reloc_type_lookup (stdoutput, reloc);
7086 int size = bfd_get_reloc_size (howto);
7087
7088 if (size > nbytes)
7089 as_bad ("%s relocations do not fit in %d bytes", howto->name, nbytes);
7090 else
7091 {
7092 register char * p = frag_more ((int) nbytes);
7093 int offset = nbytes - size;
7094
7095 fix_new_exp (frag_now, p - frag_now->fr_literal + offset, size,
7096 & exp, 0, reloc);
7097 }
7098 }
7099 else
7100 emit_expr (& exp, (unsigned int) nbytes);
7101 }
7102 while (*input_line_pointer++ == ',');
7103
7104 input_line_pointer--; /* Put terminator back into stream. */
7105 demand_empty_rest_of_line ();
7106 }
7107
7108 #endif /* OBJ_ELF */
This page took 0.175547 seconds and 4 git commands to generate.