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