[PATCH 4/57][Arm][GAS] Add support for MVE instructions: vabav, vmladav and vmlsdav
[deliverable/binutils-gdb.git] / gas / config / tc-arm.c
CommitLineData
b99bd4ef 1/* tc-arm.c -- Assemble for the ARM
82704155 2 Copyright (C) 1994-2019 Free Software Foundation, Inc.
b99bd4ef
NC
3 Contributed by Richard Earnshaw (rwe@pegasus.esprit.ec.org)
4 Modified by David Taylor (dtaylor@armltd.co.uk)
22d9c8c5 5 Cirrus coprocessor mods by Aldy Hernandez (aldyh@redhat.com)
34920d91
NC
6 Cirrus coprocessor fixes by Petko Manolov (petkan@nucleusys.com)
7 Cirrus coprocessor fixes by Vladimir Ivanov (vladitx@nucleusys.com)
b99bd4ef
NC
8
9 This file is part of GAS, the GNU Assembler.
10
11 GAS is free software; you can redistribute it and/or modify
12 it under the terms of the GNU General Public License as published by
ec2655a6 13 the Free Software Foundation; either version 3, or (at your option)
b99bd4ef
NC
14 any later version.
15
16 GAS is distributed in the hope that it will be useful,
17 but WITHOUT ANY WARRANTY; without even the implied warranty of
c19d1205 18 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
b99bd4ef
NC
19 GNU General Public License for more details.
20
21 You should have received a copy of the GNU General Public License
22 along with GAS; see the file COPYING. If not, write to the Free
699d2810
NC
23 Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
24 02110-1301, USA. */
b99bd4ef 25
42a68e18 26#include "as.h"
5287ad62 27#include <limits.h>
037e8744 28#include <stdarg.h>
c19d1205 29#define NO_RELOC 0
3882b010 30#include "safe-ctype.h"
b99bd4ef
NC
31#include "subsegs.h"
32#include "obstack.h"
3da1d841 33#include "libiberty.h"
f263249b
RE
34#include "opcode/arm.h"
35
b99bd4ef
NC
36#ifdef OBJ_ELF
37#include "elf/arm.h"
a394c00f 38#include "dw2gencfi.h"
b99bd4ef
NC
39#endif
40
f0927246
NC
41#include "dwarf2dbg.h"
42
7ed4c4c5
NC
43#ifdef OBJ_ELF
44/* Must be at least the size of the largest unwind opcode (currently two). */
45#define ARM_OPCODE_CHUNK_SIZE 8
46
47/* This structure holds the unwinding state. */
48
49static struct
50{
c19d1205
ZW
51 symbolS * proc_start;
52 symbolS * table_entry;
53 symbolS * personality_routine;
54 int personality_index;
7ed4c4c5 55 /* The segment containing the function. */
c19d1205
ZW
56 segT saved_seg;
57 subsegT saved_subseg;
7ed4c4c5
NC
58 /* Opcodes generated from this function. */
59 unsigned char * opcodes;
c19d1205
ZW
60 int opcode_count;
61 int opcode_alloc;
7ed4c4c5 62 /* The number of bytes pushed to the stack. */
c19d1205 63 offsetT frame_size;
7ed4c4c5
NC
64 /* We don't add stack adjustment opcodes immediately so that we can merge
65 multiple adjustments. We can also omit the final adjustment
66 when using a frame pointer. */
c19d1205 67 offsetT pending_offset;
7ed4c4c5 68 /* These two fields are set by both unwind_movsp and unwind_setfp. They
c19d1205
ZW
69 hold the reg+offset to use when restoring sp from a frame pointer. */
70 offsetT fp_offset;
71 int fp_reg;
7ed4c4c5 72 /* Nonzero if an unwind_setfp directive has been seen. */
c19d1205 73 unsigned fp_used:1;
7ed4c4c5 74 /* Nonzero if the last opcode restores sp from fp_reg. */
c19d1205 75 unsigned sp_restored:1;
7ed4c4c5
NC
76} unwind;
77
18a20338
CL
78/* Whether --fdpic was given. */
79static int arm_fdpic;
80
8b1ad454
NC
81#endif /* OBJ_ELF */
82
4962c51a
MS
83/* Results from operand parsing worker functions. */
84
85typedef enum
86{
87 PARSE_OPERAND_SUCCESS,
88 PARSE_OPERAND_FAIL,
89 PARSE_OPERAND_FAIL_NO_BACKTRACK
90} parse_operand_result;
91
33a392fb
PB
92enum arm_float_abi
93{
94 ARM_FLOAT_ABI_HARD,
95 ARM_FLOAT_ABI_SOFTFP,
96 ARM_FLOAT_ABI_SOFT
97};
98
c19d1205 99/* Types of processor to assemble for. */
b99bd4ef 100#ifndef CPU_DEFAULT
8a59fff3 101/* The code that was here used to select a default CPU depending on compiler
fa94de6b 102 pre-defines which were only present when doing native builds, thus
8a59fff3
MGD
103 changing gas' default behaviour depending upon the build host.
104
105 If you have a target that requires a default CPU option then the you
106 should define CPU_DEFAULT here. */
b99bd4ef
NC
107#endif
108
109#ifndef FPU_DEFAULT
c820d418
MM
110# ifdef TE_LINUX
111# define FPU_DEFAULT FPU_ARCH_FPA
112# elif defined (TE_NetBSD)
113# ifdef OBJ_ELF
114# define FPU_DEFAULT FPU_ARCH_VFP /* Soft-float, but VFP order. */
115# else
116 /* Legacy a.out format. */
117# define FPU_DEFAULT FPU_ARCH_FPA /* Soft-float, but FPA order. */
118# endif
4e7fd91e
PB
119# elif defined (TE_VXWORKS)
120# define FPU_DEFAULT FPU_ARCH_VFP /* Soft-float, VFP order. */
c820d418
MM
121# else
122 /* For backwards compatibility, default to FPA. */
123# define FPU_DEFAULT FPU_ARCH_FPA
124# endif
125#endif /* ifndef FPU_DEFAULT */
b99bd4ef 126
c19d1205 127#define streq(a, b) (strcmp (a, b) == 0)
b99bd4ef 128
4d354d8b
TP
129/* Current set of feature bits available (CPU+FPU). Different from
130 selected_cpu + selected_fpu in case of autodetection since the CPU
131 feature bits are then all set. */
e74cfd16 132static arm_feature_set cpu_variant;
4d354d8b
TP
133/* Feature bits used in each execution state. Used to set build attribute
134 (in particular Tag_*_ISA_use) in CPU autodetection mode. */
e74cfd16
PB
135static arm_feature_set arm_arch_used;
136static arm_feature_set thumb_arch_used;
b99bd4ef 137
b99bd4ef 138/* Flags stored in private area of BFD structure. */
c19d1205
ZW
139static int uses_apcs_26 = FALSE;
140static int atpcs = FALSE;
b34976b6
AM
141static int support_interwork = FALSE;
142static int uses_apcs_float = FALSE;
c19d1205 143static int pic_code = FALSE;
845b51d6 144static int fix_v4bx = FALSE;
278df34e
NS
145/* Warn on using deprecated features. */
146static int warn_on_deprecated = TRUE;
147
2e6976a8
DG
148/* Understand CodeComposer Studio assembly syntax. */
149bfd_boolean codecomposer_syntax = FALSE;
03b1477f
RE
150
151/* Variables that we set while parsing command-line options. Once all
152 options have been read we re-process these values to set the real
153 assembly flags. */
4d354d8b
TP
154
155/* CPU and FPU feature bits set for legacy CPU and FPU options (eg. -marm1
156 instead of -mcpu=arm1). */
157static const arm_feature_set *legacy_cpu = NULL;
158static const arm_feature_set *legacy_fpu = NULL;
159
160/* CPU, extension and FPU feature bits selected by -mcpu. */
161static const arm_feature_set *mcpu_cpu_opt = NULL;
162static arm_feature_set *mcpu_ext_opt = NULL;
163static const arm_feature_set *mcpu_fpu_opt = NULL;
164
165/* CPU, extension and FPU feature bits selected by -march. */
166static const arm_feature_set *march_cpu_opt = NULL;
167static arm_feature_set *march_ext_opt = NULL;
168static const arm_feature_set *march_fpu_opt = NULL;
169
170/* Feature bits selected by -mfpu. */
171static const arm_feature_set *mfpu_opt = NULL;
e74cfd16
PB
172
173/* Constants for known architecture features. */
174static const arm_feature_set fpu_default = FPU_DEFAULT;
f85d59c3 175static const arm_feature_set fpu_arch_vfp_v1 ATTRIBUTE_UNUSED = FPU_ARCH_VFP_V1;
e74cfd16 176static const arm_feature_set fpu_arch_vfp_v2 = FPU_ARCH_VFP_V2;
f85d59c3
KT
177static const arm_feature_set fpu_arch_vfp_v3 ATTRIBUTE_UNUSED = FPU_ARCH_VFP_V3;
178static const arm_feature_set fpu_arch_neon_v1 ATTRIBUTE_UNUSED = FPU_ARCH_NEON_V1;
e74cfd16
PB
179static const arm_feature_set fpu_arch_fpa = FPU_ARCH_FPA;
180static const arm_feature_set fpu_any_hard = FPU_ANY_HARD;
69c9e028 181#ifdef OBJ_ELF
e74cfd16 182static const arm_feature_set fpu_arch_maverick = FPU_ARCH_MAVERICK;
69c9e028 183#endif
e74cfd16
PB
184static const arm_feature_set fpu_endian_pure = FPU_ARCH_ENDIAN_PURE;
185
186#ifdef CPU_DEFAULT
187static const arm_feature_set cpu_default = CPU_DEFAULT;
188#endif
189
823d2571 190static const arm_feature_set arm_ext_v1 = ARM_FEATURE_CORE_LOW (ARM_EXT_V1);
4070243b 191static const arm_feature_set arm_ext_v2 = ARM_FEATURE_CORE_LOW (ARM_EXT_V2);
823d2571
TG
192static const arm_feature_set arm_ext_v2s = ARM_FEATURE_CORE_LOW (ARM_EXT_V2S);
193static const arm_feature_set arm_ext_v3 = ARM_FEATURE_CORE_LOW (ARM_EXT_V3);
194static const arm_feature_set arm_ext_v3m = ARM_FEATURE_CORE_LOW (ARM_EXT_V3M);
195static const arm_feature_set arm_ext_v4 = ARM_FEATURE_CORE_LOW (ARM_EXT_V4);
196static const arm_feature_set arm_ext_v4t = ARM_FEATURE_CORE_LOW (ARM_EXT_V4T);
197static const arm_feature_set arm_ext_v5 = ARM_FEATURE_CORE_LOW (ARM_EXT_V5);
e74cfd16 198static const arm_feature_set arm_ext_v4t_5 =
823d2571
TG
199 ARM_FEATURE_CORE_LOW (ARM_EXT_V4T | ARM_EXT_V5);
200static const arm_feature_set arm_ext_v5t = ARM_FEATURE_CORE_LOW (ARM_EXT_V5T);
201static const arm_feature_set arm_ext_v5e = ARM_FEATURE_CORE_LOW (ARM_EXT_V5E);
202static const arm_feature_set arm_ext_v5exp = ARM_FEATURE_CORE_LOW (ARM_EXT_V5ExP);
203static const arm_feature_set arm_ext_v5j = ARM_FEATURE_CORE_LOW (ARM_EXT_V5J);
204static const arm_feature_set arm_ext_v6 = ARM_FEATURE_CORE_LOW (ARM_EXT_V6);
205static const arm_feature_set arm_ext_v6k = ARM_FEATURE_CORE_LOW (ARM_EXT_V6K);
206static const arm_feature_set arm_ext_v6t2 = ARM_FEATURE_CORE_LOW (ARM_EXT_V6T2);
55e8aae7
SP
207/* Only for compatability of hint instructions. */
208static const arm_feature_set arm_ext_v6k_v6t2 =
209 ARM_FEATURE_CORE_LOW (ARM_EXT_V6K | ARM_EXT_V6T2);
823d2571
TG
210static const arm_feature_set arm_ext_v6_notm =
211 ARM_FEATURE_CORE_LOW (ARM_EXT_V6_NOTM);
212static const arm_feature_set arm_ext_v6_dsp =
213 ARM_FEATURE_CORE_LOW (ARM_EXT_V6_DSP);
214static const arm_feature_set arm_ext_barrier =
215 ARM_FEATURE_CORE_LOW (ARM_EXT_BARRIER);
216static const arm_feature_set arm_ext_msr =
217 ARM_FEATURE_CORE_LOW (ARM_EXT_THUMB_MSR);
218static const arm_feature_set arm_ext_div = ARM_FEATURE_CORE_LOW (ARM_EXT_DIV);
219static const arm_feature_set arm_ext_v7 = ARM_FEATURE_CORE_LOW (ARM_EXT_V7);
220static const arm_feature_set arm_ext_v7a = ARM_FEATURE_CORE_LOW (ARM_EXT_V7A);
221static const arm_feature_set arm_ext_v7r = ARM_FEATURE_CORE_LOW (ARM_EXT_V7R);
69c9e028 222#ifdef OBJ_ELF
e7d39ed3 223static const arm_feature_set ATTRIBUTE_UNUSED arm_ext_v7m = ARM_FEATURE_CORE_LOW (ARM_EXT_V7M);
69c9e028 224#endif
823d2571 225static const arm_feature_set arm_ext_v8 = ARM_FEATURE_CORE_LOW (ARM_EXT_V8);
7e806470 226static const arm_feature_set arm_ext_m =
173205ca 227 ARM_FEATURE_CORE (ARM_EXT_V6M | ARM_EXT_V7M,
16a1fa25 228 ARM_EXT2_V8M | ARM_EXT2_V8M_MAIN);
823d2571
TG
229static const arm_feature_set arm_ext_mp = ARM_FEATURE_CORE_LOW (ARM_EXT_MP);
230static const arm_feature_set arm_ext_sec = ARM_FEATURE_CORE_LOW (ARM_EXT_SEC);
231static const arm_feature_set arm_ext_os = ARM_FEATURE_CORE_LOW (ARM_EXT_OS);
232static const arm_feature_set arm_ext_adiv = ARM_FEATURE_CORE_LOW (ARM_EXT_ADIV);
233static const arm_feature_set arm_ext_virt = ARM_FEATURE_CORE_LOW (ARM_EXT_VIRT);
ddfded2f 234static const arm_feature_set arm_ext_pan = ARM_FEATURE_CORE_HIGH (ARM_EXT2_PAN);
4ed7ed8d 235static const arm_feature_set arm_ext_v8m = ARM_FEATURE_CORE_HIGH (ARM_EXT2_V8M);
16a1fa25
TP
236static const arm_feature_set arm_ext_v8m_main =
237 ARM_FEATURE_CORE_HIGH (ARM_EXT2_V8M_MAIN);
e12437dc
AV
238static const arm_feature_set arm_ext_v8_1m_main =
239ARM_FEATURE_CORE_HIGH (ARM_EXT2_V8_1M_MAIN);
16a1fa25
TP
240/* Instructions in ARMv8-M only found in M profile architectures. */
241static const arm_feature_set arm_ext_v8m_m_only =
242 ARM_FEATURE_CORE_HIGH (ARM_EXT2_V8M | ARM_EXT2_V8M_MAIN);
ff8646ee
TP
243static const arm_feature_set arm_ext_v6t2_v8m =
244 ARM_FEATURE_CORE_HIGH (ARM_EXT2_V6T2_V8M);
4ed7ed8d
TP
245/* Instructions shared between ARMv8-A and ARMv8-M. */
246static const arm_feature_set arm_ext_atomics =
247 ARM_FEATURE_CORE_HIGH (ARM_EXT2_ATOMICS);
69c9e028 248#ifdef OBJ_ELF
15afaa63
TP
249/* DSP instructions Tag_DSP_extension refers to. */
250static const arm_feature_set arm_ext_dsp =
251 ARM_FEATURE_CORE_LOW (ARM_EXT_V5E | ARM_EXT_V5ExP | ARM_EXT_V6_DSP);
69c9e028 252#endif
4d1464f2
MW
253static const arm_feature_set arm_ext_ras =
254 ARM_FEATURE_CORE_HIGH (ARM_EXT2_RAS);
b8ec4e87
JW
255/* FP16 instructions. */
256static const arm_feature_set arm_ext_fp16 =
257 ARM_FEATURE_CORE_HIGH (ARM_EXT2_FP16_INST);
01f48020
TC
258static const arm_feature_set arm_ext_fp16_fml =
259 ARM_FEATURE_CORE_HIGH (ARM_EXT2_FP16_FML);
dec41383
JW
260static const arm_feature_set arm_ext_v8_2 =
261 ARM_FEATURE_CORE_HIGH (ARM_EXT2_V8_2A);
49e8a725
SN
262static const arm_feature_set arm_ext_v8_3 =
263 ARM_FEATURE_CORE_HIGH (ARM_EXT2_V8_3A);
7fadb25d
SD
264static const arm_feature_set arm_ext_sb =
265 ARM_FEATURE_CORE_HIGH (ARM_EXT2_SB);
dad0c3bf
SD
266static const arm_feature_set arm_ext_predres =
267 ARM_FEATURE_CORE_HIGH (ARM_EXT2_PREDRES);
e74cfd16
PB
268
269static const arm_feature_set arm_arch_any = ARM_ANY;
49fa50ef 270#ifdef OBJ_ELF
2c6b98ea 271static const arm_feature_set fpu_any = FPU_ANY;
49fa50ef 272#endif
f85d59c3 273static const arm_feature_set arm_arch_full ATTRIBUTE_UNUSED = ARM_FEATURE (-1, -1, -1);
e74cfd16
PB
274static const arm_feature_set arm_arch_t2 = ARM_ARCH_THUMB2;
275static const arm_feature_set arm_arch_none = ARM_ARCH_NONE;
276
2d447fca 277static const arm_feature_set arm_cext_iwmmxt2 =
823d2571 278 ARM_FEATURE_COPROC (ARM_CEXT_IWMMXT2);
e74cfd16 279static const arm_feature_set arm_cext_iwmmxt =
823d2571 280 ARM_FEATURE_COPROC (ARM_CEXT_IWMMXT);
e74cfd16 281static const arm_feature_set arm_cext_xscale =
823d2571 282 ARM_FEATURE_COPROC (ARM_CEXT_XSCALE);
e74cfd16 283static const arm_feature_set arm_cext_maverick =
823d2571
TG
284 ARM_FEATURE_COPROC (ARM_CEXT_MAVERICK);
285static const arm_feature_set fpu_fpa_ext_v1 =
286 ARM_FEATURE_COPROC (FPU_FPA_EXT_V1);
287static const arm_feature_set fpu_fpa_ext_v2 =
288 ARM_FEATURE_COPROC (FPU_FPA_EXT_V2);
e74cfd16 289static const arm_feature_set fpu_vfp_ext_v1xd =
823d2571
TG
290 ARM_FEATURE_COPROC (FPU_VFP_EXT_V1xD);
291static const arm_feature_set fpu_vfp_ext_v1 =
292 ARM_FEATURE_COPROC (FPU_VFP_EXT_V1);
293static const arm_feature_set fpu_vfp_ext_v2 =
294 ARM_FEATURE_COPROC (FPU_VFP_EXT_V2);
295static const arm_feature_set fpu_vfp_ext_v3xd =
296 ARM_FEATURE_COPROC (FPU_VFP_EXT_V3xD);
297static const arm_feature_set fpu_vfp_ext_v3 =
298 ARM_FEATURE_COPROC (FPU_VFP_EXT_V3);
b1cc4aeb 299static const arm_feature_set fpu_vfp_ext_d32 =
823d2571
TG
300 ARM_FEATURE_COPROC (FPU_VFP_EXT_D32);
301static const arm_feature_set fpu_neon_ext_v1 =
302 ARM_FEATURE_COPROC (FPU_NEON_EXT_V1);
5287ad62 303static const arm_feature_set fpu_vfp_v3_or_neon_ext =
823d2571 304 ARM_FEATURE_COPROC (FPU_NEON_EXT_V1 | FPU_VFP_EXT_V3);
a7ad558c
AV
305static const arm_feature_set mve_ext =
306 ARM_FEATURE_COPROC (FPU_MVE);
307static const arm_feature_set mve_fp_ext =
308 ARM_FEATURE_COPROC (FPU_MVE_FP);
69c9e028 309#ifdef OBJ_ELF
823d2571
TG
310static const arm_feature_set fpu_vfp_fp16 =
311 ARM_FEATURE_COPROC (FPU_VFP_EXT_FP16);
312static const arm_feature_set fpu_neon_ext_fma =
313 ARM_FEATURE_COPROC (FPU_NEON_EXT_FMA);
69c9e028 314#endif
823d2571
TG
315static const arm_feature_set fpu_vfp_ext_fma =
316 ARM_FEATURE_COPROC (FPU_VFP_EXT_FMA);
bca38921 317static const arm_feature_set fpu_vfp_ext_armv8 =
823d2571 318 ARM_FEATURE_COPROC (FPU_VFP_EXT_ARMV8);
a715796b 319static const arm_feature_set fpu_vfp_ext_armv8xd =
823d2571 320 ARM_FEATURE_COPROC (FPU_VFP_EXT_ARMV8xD);
bca38921 321static const arm_feature_set fpu_neon_ext_armv8 =
823d2571 322 ARM_FEATURE_COPROC (FPU_NEON_EXT_ARMV8);
bca38921 323static const arm_feature_set fpu_crypto_ext_armv8 =
823d2571 324 ARM_FEATURE_COPROC (FPU_CRYPTO_EXT_ARMV8);
dd5181d5 325static const arm_feature_set crc_ext_armv8 =
823d2571 326 ARM_FEATURE_COPROC (CRC_EXT_ARMV8);
d6b4b13e 327static const arm_feature_set fpu_neon_ext_v8_1 =
643afb90 328 ARM_FEATURE_COPROC (FPU_NEON_EXT_RDMA);
c604a79a
JW
329static const arm_feature_set fpu_neon_ext_dotprod =
330 ARM_FEATURE_COPROC (FPU_NEON_EXT_DOTPROD);
e74cfd16 331
33a392fb 332static int mfloat_abi_opt = -1;
4d354d8b
TP
333/* Architecture feature bits selected by the last -mcpu/-march or .cpu/.arch
334 directive. */
335static arm_feature_set selected_arch = ARM_ARCH_NONE;
336/* Extension feature bits selected by the last -mcpu/-march or .arch_extension
337 directive. */
338static arm_feature_set selected_ext = ARM_ARCH_NONE;
339/* Feature bits selected by the last -mcpu/-march or by the combination of the
340 last .cpu/.arch directive .arch_extension directives since that
341 directive. */
e74cfd16 342static arm_feature_set selected_cpu = ARM_ARCH_NONE;
4d354d8b
TP
343/* FPU feature bits selected by the last -mfpu or .fpu directive. */
344static arm_feature_set selected_fpu = FPU_NONE;
345/* Feature bits selected by the last .object_arch directive. */
346static arm_feature_set selected_object_arch = ARM_ARCH_NONE;
ee065d83 347/* Must be long enough to hold any of the names in arm_cpus. */
ef8e6722 348static char selected_cpu_name[20];
8d67f500 349
aacf0b33
KT
350extern FLONUM_TYPE generic_floating_point_number;
351
8d67f500
NC
352/* Return if no cpu was selected on command-line. */
353static bfd_boolean
354no_cpu_selected (void)
355{
823d2571 356 return ARM_FEATURE_EQUAL (selected_cpu, arm_arch_none);
8d67f500
NC
357}
358
7cc69913 359#ifdef OBJ_ELF
deeaaff8
DJ
360# ifdef EABI_DEFAULT
361static int meabi_flags = EABI_DEFAULT;
362# else
d507cf36 363static int meabi_flags = EF_ARM_EABI_UNKNOWN;
deeaaff8 364# endif
e1da3f5b 365
ee3c0378
AS
366static int attributes_set_explicitly[NUM_KNOWN_OBJ_ATTRIBUTES];
367
e1da3f5b 368bfd_boolean
5f4273c7 369arm_is_eabi (void)
e1da3f5b
PB
370{
371 return (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4);
372}
7cc69913 373#endif
b99bd4ef 374
b99bd4ef 375#ifdef OBJ_ELF
c19d1205 376/* Pre-defined "_GLOBAL_OFFSET_TABLE_" */
b99bd4ef
NC
377symbolS * GOT_symbol;
378#endif
379
b99bd4ef
NC
380/* 0: assemble for ARM,
381 1: assemble for Thumb,
382 2: assemble for Thumb even though target CPU does not support thumb
383 instructions. */
384static int thumb_mode = 0;
8dc2430f
NC
385/* A value distinct from the possible values for thumb_mode that we
386 can use to record whether thumb_mode has been copied into the
387 tc_frag_data field of a frag. */
388#define MODE_RECORDED (1 << 4)
b99bd4ef 389
e07e6e58
NC
390/* Specifies the intrinsic IT insn behavior mode. */
391enum implicit_it_mode
392{
393 IMPLICIT_IT_MODE_NEVER = 0x00,
394 IMPLICIT_IT_MODE_ARM = 0x01,
395 IMPLICIT_IT_MODE_THUMB = 0x02,
396 IMPLICIT_IT_MODE_ALWAYS = (IMPLICIT_IT_MODE_ARM | IMPLICIT_IT_MODE_THUMB)
397};
398static int implicit_it_mode = IMPLICIT_IT_MODE_ARM;
399
c19d1205
ZW
400/* If unified_syntax is true, we are processing the new unified
401 ARM/Thumb syntax. Important differences from the old ARM mode:
402
403 - Immediate operands do not require a # prefix.
404 - Conditional affixes always appear at the end of the
405 instruction. (For backward compatibility, those instructions
406 that formerly had them in the middle, continue to accept them
407 there.)
408 - The IT instruction may appear, and if it does is validated
409 against subsequent conditional affixes. It does not generate
410 machine code.
411
412 Important differences from the old Thumb mode:
413
414 - Immediate operands do not require a # prefix.
415 - Most of the V6T2 instructions are only available in unified mode.
416 - The .N and .W suffixes are recognized and honored (it is an error
417 if they cannot be honored).
418 - All instructions set the flags if and only if they have an 's' affix.
419 - Conditional affixes may be used. They are validated against
420 preceding IT instructions. Unlike ARM mode, you cannot use a
421 conditional affix except in the scope of an IT instruction. */
422
423static bfd_boolean unified_syntax = FALSE;
b99bd4ef 424
bacebabc
RM
425/* An immediate operand can start with #, and ld*, st*, pld operands
426 can contain [ and ]. We need to tell APP not to elide whitespace
477330fc
RM
427 before a [, which can appear as the first operand for pld.
428 Likewise, a { can appear as the first operand for push, pop, vld*, etc. */
429const char arm_symbol_chars[] = "#[]{}";
bacebabc 430
5287ad62
JB
431enum neon_el_type
432{
dcbf9037 433 NT_invtype,
5287ad62
JB
434 NT_untyped,
435 NT_integer,
436 NT_float,
437 NT_poly,
438 NT_signed,
dcbf9037 439 NT_unsigned
5287ad62
JB
440};
441
442struct neon_type_el
443{
444 enum neon_el_type type;
445 unsigned size;
446};
447
448#define NEON_MAX_TYPE_ELS 4
449
450struct neon_type
451{
452 struct neon_type_el el[NEON_MAX_TYPE_ELS];
453 unsigned elems;
454};
455
5ee91343 456enum pred_instruction_type
e07e6e58 457{
5ee91343
AV
458 OUTSIDE_PRED_INSN,
459 INSIDE_VPT_INSN,
e07e6e58
NC
460 INSIDE_IT_INSN,
461 INSIDE_IT_LAST_INSN,
462 IF_INSIDE_IT_LAST_INSN, /* Either outside or inside;
477330fc 463 if inside, should be the last one. */
e07e6e58 464 NEUTRAL_IT_INSN, /* This could be either inside or outside,
477330fc 465 i.e. BKPT and NOP. */
5ee91343
AV
466 IT_INSN, /* The IT insn has been parsed. */
467 VPT_INSN, /* The VPT/VPST insn has been parsed. */
468 MVE_OUTSIDE_PRED_INSN /* Instruction to indicate a MVE instruction without
469 a predication code. */
e07e6e58
NC
470};
471
ad6cec43
MGD
472/* The maximum number of operands we need. */
473#define ARM_IT_MAX_OPERANDS 6
e2b0ab59 474#define ARM_IT_MAX_RELOCS 3
ad6cec43 475
b99bd4ef
NC
476struct arm_it
477{
c19d1205 478 const char * error;
b99bd4ef 479 unsigned long instruction;
c19d1205
ZW
480 int size;
481 int size_req;
482 int cond;
037e8744
JB
483 /* "uncond_value" is set to the value in place of the conditional field in
484 unconditional versions of the instruction, or -1 if nothing is
485 appropriate. */
486 int uncond_value;
5287ad62 487 struct neon_type vectype;
88714cb8
DG
488 /* This does not indicate an actual NEON instruction, only that
489 the mnemonic accepts neon-style type suffixes. */
490 int is_neon;
0110f2b8
PB
491 /* Set to the opcode if the instruction needs relaxation.
492 Zero if the instruction is not relaxed. */
493 unsigned long relax;
b99bd4ef
NC
494 struct
495 {
496 bfd_reloc_code_real_type type;
c19d1205
ZW
497 expressionS exp;
498 int pc_rel;
e2b0ab59 499 } relocs[ARM_IT_MAX_RELOCS];
b99bd4ef 500
5ee91343 501 enum pred_instruction_type pred_insn_type;
e07e6e58 502
c19d1205
ZW
503 struct
504 {
505 unsigned reg;
ca3f61f7 506 signed int imm;
dcbf9037 507 struct neon_type_el vectype;
ca3f61f7
NC
508 unsigned present : 1; /* Operand present. */
509 unsigned isreg : 1; /* Operand was a register. */
510 unsigned immisreg : 1; /* .imm field is a second register. */
5287ad62
JB
511 unsigned isscalar : 1; /* Operand is a (Neon) scalar. */
512 unsigned immisalign : 1; /* Immediate is an alignment specifier. */
c96612cc 513 unsigned immisfloat : 1; /* Immediate was parsed as a float. */
5287ad62
JB
514 /* Note: we abuse "regisimm" to mean "is Neon register" in VMOV
515 instructions. This allows us to disambiguate ARM <-> vector insns. */
516 unsigned regisimm : 1; /* 64-bit immediate, reg forms high 32 bits. */
037e8744 517 unsigned isvec : 1; /* Is a single, double or quad VFP/Neon reg. */
5ee91343 518 unsigned isquad : 1; /* Operand is SIMD quad register. */
037e8744 519 unsigned issingle : 1; /* Operand is VFP single-precision register. */
ca3f61f7
NC
520 unsigned hasreloc : 1; /* Operand has relocation suffix. */
521 unsigned writeback : 1; /* Operand has trailing ! */
522 unsigned preind : 1; /* Preindexed address. */
523 unsigned postind : 1; /* Postindexed address. */
524 unsigned negative : 1; /* Index register was negated. */
525 unsigned shifted : 1; /* Shift applied to operation. */
526 unsigned shift_kind : 3; /* Shift operation (enum shift_kind). */
ad6cec43 527 } operands[ARM_IT_MAX_OPERANDS];
b99bd4ef
NC
528};
529
c19d1205 530static struct arm_it inst;
b99bd4ef
NC
531
532#define NUM_FLOAT_VALS 8
533
05d2d07e 534const char * fp_const[] =
b99bd4ef
NC
535{
536 "0.0", "1.0", "2.0", "3.0", "4.0", "5.0", "0.5", "10.0", 0
537};
538
b99bd4ef
NC
539LITTLENUM_TYPE fp_values[NUM_FLOAT_VALS][MAX_LITTLENUMS];
540
541#define FAIL (-1)
542#define SUCCESS (0)
543
544#define SUFF_S 1
545#define SUFF_D 2
546#define SUFF_E 3
547#define SUFF_P 4
548
c19d1205
ZW
549#define CP_T_X 0x00008000
550#define CP_T_Y 0x00400000
b99bd4ef 551
c19d1205
ZW
552#define CONDS_BIT 0x00100000
553#define LOAD_BIT 0x00100000
b99bd4ef
NC
554
555#define DOUBLE_LOAD_FLAG 0x00000001
556
557struct asm_cond
558{
d3ce72d0 559 const char * template_name;
c921be7d 560 unsigned long value;
b99bd4ef
NC
561};
562
c19d1205 563#define COND_ALWAYS 0xE
b99bd4ef 564
b99bd4ef
NC
565struct asm_psr
566{
d3ce72d0 567 const char * template_name;
c921be7d 568 unsigned long field;
b99bd4ef
NC
569};
570
62b3e311
PB
571struct asm_barrier_opt
572{
e797f7e0
MGD
573 const char * template_name;
574 unsigned long value;
575 const arm_feature_set arch;
62b3e311
PB
576};
577
2d2255b5 578/* The bit that distinguishes CPSR and SPSR. */
b99bd4ef
NC
579#define SPSR_BIT (1 << 22)
580
c19d1205
ZW
581/* The individual PSR flag bits. */
582#define PSR_c (1 << 16)
583#define PSR_x (1 << 17)
584#define PSR_s (1 << 18)
585#define PSR_f (1 << 19)
b99bd4ef 586
c19d1205 587struct reloc_entry
bfae80f2 588{
0198d5e6 589 const char * name;
c921be7d 590 bfd_reloc_code_real_type reloc;
bfae80f2
RE
591};
592
5287ad62 593enum vfp_reg_pos
bfae80f2 594{
5287ad62
JB
595 VFP_REG_Sd, VFP_REG_Sm, VFP_REG_Sn,
596 VFP_REG_Dd, VFP_REG_Dm, VFP_REG_Dn
bfae80f2
RE
597};
598
599enum vfp_ldstm_type
600{
601 VFP_LDSTMIA, VFP_LDSTMDB, VFP_LDSTMIAX, VFP_LDSTMDBX
602};
603
dcbf9037
JB
604/* Bits for DEFINED field in neon_typed_alias. */
605#define NTA_HASTYPE 1
606#define NTA_HASINDEX 2
607
608struct neon_typed_alias
609{
c921be7d
NC
610 unsigned char defined;
611 unsigned char index;
612 struct neon_type_el eltype;
dcbf9037
JB
613};
614
c19d1205 615/* ARM register categories. This includes coprocessor numbers and various
5aa75429
TP
616 architecture extensions' registers. Each entry should have an error message
617 in reg_expected_msgs below. */
c19d1205 618enum arm_reg_type
bfae80f2 619{
c19d1205
ZW
620 REG_TYPE_RN,
621 REG_TYPE_CP,
622 REG_TYPE_CN,
623 REG_TYPE_FN,
624 REG_TYPE_VFS,
625 REG_TYPE_VFD,
5287ad62 626 REG_TYPE_NQ,
037e8744 627 REG_TYPE_VFSD,
5287ad62 628 REG_TYPE_NDQ,
dec41383 629 REG_TYPE_NSD,
037e8744 630 REG_TYPE_NSDQ,
c19d1205
ZW
631 REG_TYPE_VFC,
632 REG_TYPE_MVF,
633 REG_TYPE_MVD,
634 REG_TYPE_MVFX,
635 REG_TYPE_MVDX,
636 REG_TYPE_MVAX,
5ee91343 637 REG_TYPE_MQ,
c19d1205
ZW
638 REG_TYPE_DSPSC,
639 REG_TYPE_MMXWR,
640 REG_TYPE_MMXWC,
641 REG_TYPE_MMXWCG,
642 REG_TYPE_XSCALE,
5ee91343 643 REG_TYPE_RNB,
bfae80f2
RE
644};
645
dcbf9037
JB
646/* Structure for a hash table entry for a register.
647 If TYPE is REG_TYPE_VFD or REG_TYPE_NQ, the NEON field can point to extra
648 information which states whether a vector type or index is specified (for a
649 register alias created with .dn or .qn). Otherwise NEON should be NULL. */
6c43fab6
RE
650struct reg_entry
651{
c921be7d 652 const char * name;
90ec0d68 653 unsigned int number;
c921be7d
NC
654 unsigned char type;
655 unsigned char builtin;
656 struct neon_typed_alias * neon;
6c43fab6
RE
657};
658
c19d1205 659/* Diagnostics used when we don't get a register of the expected type. */
c921be7d 660const char * const reg_expected_msgs[] =
c19d1205 661{
5aa75429
TP
662 [REG_TYPE_RN] = N_("ARM register expected"),
663 [REG_TYPE_CP] = N_("bad or missing co-processor number"),
664 [REG_TYPE_CN] = N_("co-processor register expected"),
665 [REG_TYPE_FN] = N_("FPA register expected"),
666 [REG_TYPE_VFS] = N_("VFP single precision register expected"),
667 [REG_TYPE_VFD] = N_("VFP/Neon double precision register expected"),
668 [REG_TYPE_NQ] = N_("Neon quad precision register expected"),
669 [REG_TYPE_VFSD] = N_("VFP single or double precision register expected"),
670 [REG_TYPE_NDQ] = N_("Neon double or quad precision register expected"),
671 [REG_TYPE_NSD] = N_("Neon single or double precision register expected"),
672 [REG_TYPE_NSDQ] = N_("VFP single, double or Neon quad precision register"
673 " expected"),
674 [REG_TYPE_VFC] = N_("VFP system register expected"),
675 [REG_TYPE_MVF] = N_("Maverick MVF register expected"),
676 [REG_TYPE_MVD] = N_("Maverick MVD register expected"),
677 [REG_TYPE_MVFX] = N_("Maverick MVFX register expected"),
678 [REG_TYPE_MVDX] = N_("Maverick MVDX register expected"),
679 [REG_TYPE_MVAX] = N_("Maverick MVAX register expected"),
680 [REG_TYPE_DSPSC] = N_("Maverick DSPSC register expected"),
681 [REG_TYPE_MMXWR] = N_("iWMMXt data register expected"),
682 [REG_TYPE_MMXWC] = N_("iWMMXt control register expected"),
683 [REG_TYPE_MMXWCG] = N_("iWMMXt scalar register expected"),
684 [REG_TYPE_XSCALE] = N_("XScale accumulator register expected"),
5ee91343 685 [REG_TYPE_MQ] = N_("MVE vector register expected"),
5aa75429 686 [REG_TYPE_RNB] = N_("")
6c43fab6
RE
687};
688
c19d1205 689/* Some well known registers that we refer to directly elsewhere. */
bd340a04 690#define REG_R12 12
c19d1205
ZW
691#define REG_SP 13
692#define REG_LR 14
693#define REG_PC 15
404ff6b5 694
b99bd4ef
NC
695/* ARM instructions take 4bytes in the object file, Thumb instructions
696 take 2: */
c19d1205 697#define INSN_SIZE 4
b99bd4ef
NC
698
699struct asm_opcode
700{
701 /* Basic string to match. */
d3ce72d0 702 const char * template_name;
c19d1205
ZW
703
704 /* Parameters to instruction. */
5be8be5d 705 unsigned int operands[8];
c19d1205
ZW
706
707 /* Conditional tag - see opcode_lookup. */
708 unsigned int tag : 4;
b99bd4ef
NC
709
710 /* Basic instruction code. */
a302e574 711 unsigned int avalue;
b99bd4ef 712
c19d1205
ZW
713 /* Thumb-format instruction code. */
714 unsigned int tvalue;
b99bd4ef 715
90e4755a 716 /* Which architecture variant provides this instruction. */
c921be7d
NC
717 const arm_feature_set * avariant;
718 const arm_feature_set * tvariant;
c19d1205
ZW
719
720 /* Function to call to encode instruction in ARM format. */
721 void (* aencode) (void);
b99bd4ef 722
c19d1205
ZW
723 /* Function to call to encode instruction in Thumb format. */
724 void (* tencode) (void);
5ee91343
AV
725
726 /* Indicates whether this instruction may be vector predicated. */
727 unsigned int mayBeVecPred : 1;
b99bd4ef
NC
728};
729
a737bd4d
NC
730/* Defines for various bits that we will want to toggle. */
731#define INST_IMMEDIATE 0x02000000
732#define OFFSET_REG 0x02000000
c19d1205 733#define HWOFFSET_IMM 0x00400000
a737bd4d
NC
734#define SHIFT_BY_REG 0x00000010
735#define PRE_INDEX 0x01000000
736#define INDEX_UP 0x00800000
737#define WRITE_BACK 0x00200000
738#define LDM_TYPE_2_OR_3 0x00400000
a028a6f5 739#define CPSI_MMOD 0x00020000
90e4755a 740
a737bd4d
NC
741#define LITERAL_MASK 0xf000f000
742#define OPCODE_MASK 0xfe1fffff
743#define V4_STR_BIT 0x00000020
8335d6aa 744#define VLDR_VMOV_SAME 0x0040f000
90e4755a 745
efd81785
PB
746#define T2_SUBS_PC_LR 0xf3de8f00
747
a737bd4d 748#define DATA_OP_SHIFT 21
bada4342 749#define SBIT_SHIFT 20
90e4755a 750
ef8d22e6
PB
751#define T2_OPCODE_MASK 0xfe1fffff
752#define T2_DATA_OP_SHIFT 21
bada4342 753#define T2_SBIT_SHIFT 20
ef8d22e6 754
6530b175
NC
755#define A_COND_MASK 0xf0000000
756#define A_PUSH_POP_OP_MASK 0x0fff0000
757
758/* Opcodes for pushing/poping registers to/from the stack. */
759#define A1_OPCODE_PUSH 0x092d0000
760#define A2_OPCODE_PUSH 0x052d0004
761#define A2_OPCODE_POP 0x049d0004
762
a737bd4d
NC
763/* Codes to distinguish the arithmetic instructions. */
764#define OPCODE_AND 0
765#define OPCODE_EOR 1
766#define OPCODE_SUB 2
767#define OPCODE_RSB 3
768#define OPCODE_ADD 4
769#define OPCODE_ADC 5
770#define OPCODE_SBC 6
771#define OPCODE_RSC 7
772#define OPCODE_TST 8
773#define OPCODE_TEQ 9
774#define OPCODE_CMP 10
775#define OPCODE_CMN 11
776#define OPCODE_ORR 12
777#define OPCODE_MOV 13
778#define OPCODE_BIC 14
779#define OPCODE_MVN 15
90e4755a 780
ef8d22e6
PB
781#define T2_OPCODE_AND 0
782#define T2_OPCODE_BIC 1
783#define T2_OPCODE_ORR 2
784#define T2_OPCODE_ORN 3
785#define T2_OPCODE_EOR 4
786#define T2_OPCODE_ADD 8
787#define T2_OPCODE_ADC 10
788#define T2_OPCODE_SBC 11
789#define T2_OPCODE_SUB 13
790#define T2_OPCODE_RSB 14
791
a737bd4d
NC
792#define T_OPCODE_MUL 0x4340
793#define T_OPCODE_TST 0x4200
794#define T_OPCODE_CMN 0x42c0
795#define T_OPCODE_NEG 0x4240
796#define T_OPCODE_MVN 0x43c0
90e4755a 797
a737bd4d
NC
798#define T_OPCODE_ADD_R3 0x1800
799#define T_OPCODE_SUB_R3 0x1a00
800#define T_OPCODE_ADD_HI 0x4400
801#define T_OPCODE_ADD_ST 0xb000
802#define T_OPCODE_SUB_ST 0xb080
803#define T_OPCODE_ADD_SP 0xa800
804#define T_OPCODE_ADD_PC 0xa000
805#define T_OPCODE_ADD_I8 0x3000
806#define T_OPCODE_SUB_I8 0x3800
807#define T_OPCODE_ADD_I3 0x1c00
808#define T_OPCODE_SUB_I3 0x1e00
b99bd4ef 809
a737bd4d
NC
810#define T_OPCODE_ASR_R 0x4100
811#define T_OPCODE_LSL_R 0x4080
c19d1205
ZW
812#define T_OPCODE_LSR_R 0x40c0
813#define T_OPCODE_ROR_R 0x41c0
a737bd4d
NC
814#define T_OPCODE_ASR_I 0x1000
815#define T_OPCODE_LSL_I 0x0000
816#define T_OPCODE_LSR_I 0x0800
b99bd4ef 817
a737bd4d
NC
818#define T_OPCODE_MOV_I8 0x2000
819#define T_OPCODE_CMP_I8 0x2800
820#define T_OPCODE_CMP_LR 0x4280
821#define T_OPCODE_MOV_HR 0x4600
822#define T_OPCODE_CMP_HR 0x4500
b99bd4ef 823
a737bd4d
NC
824#define T_OPCODE_LDR_PC 0x4800
825#define T_OPCODE_LDR_SP 0x9800
826#define T_OPCODE_STR_SP 0x9000
827#define T_OPCODE_LDR_IW 0x6800
828#define T_OPCODE_STR_IW 0x6000
829#define T_OPCODE_LDR_IH 0x8800
830#define T_OPCODE_STR_IH 0x8000
831#define T_OPCODE_LDR_IB 0x7800
832#define T_OPCODE_STR_IB 0x7000
833#define T_OPCODE_LDR_RW 0x5800
834#define T_OPCODE_STR_RW 0x5000
835#define T_OPCODE_LDR_RH 0x5a00
836#define T_OPCODE_STR_RH 0x5200
837#define T_OPCODE_LDR_RB 0x5c00
838#define T_OPCODE_STR_RB 0x5400
c9b604bd 839
a737bd4d
NC
840#define T_OPCODE_PUSH 0xb400
841#define T_OPCODE_POP 0xbc00
b99bd4ef 842
2fc8bdac 843#define T_OPCODE_BRANCH 0xe000
b99bd4ef 844
a737bd4d 845#define THUMB_SIZE 2 /* Size of thumb instruction. */
a737bd4d 846#define THUMB_PP_PC_LR 0x0100
c19d1205 847#define THUMB_LOAD_BIT 0x0800
53365c0d 848#define THUMB2_LOAD_BIT 0x00100000
c19d1205 849
5ee91343 850#define BAD_SYNTAX _("syntax error")
c19d1205 851#define BAD_ARGS _("bad arguments to instruction")
fdfde340 852#define BAD_SP _("r13 not allowed here")
c19d1205 853#define BAD_PC _("r15 not allowed here")
a302e574
AV
854#define BAD_ODD _("Odd register not allowed here")
855#define BAD_EVEN _("Even register not allowed here")
c19d1205
ZW
856#define BAD_COND _("instruction cannot be conditional")
857#define BAD_OVERLAP _("registers may not be the same")
858#define BAD_HIREG _("lo register required")
859#define BAD_THUMB32 _("instruction not supported in Thumb16 mode")
01cfc07f 860#define BAD_ADDR_MODE _("instruction does not accept this addressing mode");
dfa9f0d5 861#define BAD_BRANCH _("branch must be last instruction in IT block")
e12437dc 862#define BAD_BRANCH_OFF _("branch out of range or not a multiple of 2")
dfa9f0d5 863#define BAD_NOT_IT _("instruction not allowed in IT block")
5ee91343 864#define BAD_NOT_VPT _("instruction missing MVE vector predication code")
037e8744 865#define BAD_FPU _("selected FPU does not support instruction")
e07e6e58 866#define BAD_OUT_IT _("thumb conditional instruction should be in IT block")
5ee91343
AV
867#define BAD_OUT_VPT \
868 _("vector predicated instruction should be in VPT/VPST block")
e07e6e58 869#define BAD_IT_COND _("incorrect condition in IT block")
5ee91343 870#define BAD_VPT_COND _("incorrect condition in VPT/VPST block")
e07e6e58 871#define BAD_IT_IT _("IT falling in the range of a previous IT block")
921e5f0a 872#define MISSING_FNSTART _("missing .fnstart before unwinding directive")
5be8be5d
DG
873#define BAD_PC_ADDRESSING \
874 _("cannot use register index with PC-relative addressing")
875#define BAD_PC_WRITEBACK \
876 _("cannot use writeback with PC-relative addressing")
9db2f6b4
RL
877#define BAD_RANGE _("branch out of range")
878#define BAD_FP16 _("selected processor does not support fp16 instruction")
dd5181d5 879#define UNPRED_REG(R) _("using " R " results in unpredictable behaviour")
a9f02af8 880#define THUMB1_RELOC_ONLY _("relocation valid in thumb1 code only")
5ee91343
AV
881#define MVE_NOT_IT _("Warning: instruction is UNPREDICTABLE in an IT " \
882 "block")
883#define MVE_NOT_VPT _("Warning: instruction is UNPREDICTABLE in a VPT " \
884 "block")
885#define MVE_BAD_PC _("Warning: instruction is UNPREDICTABLE with PC" \
886 " operand")
887#define MVE_BAD_SP _("Warning: instruction is UNPREDICTABLE with SP" \
888 " operand")
a302e574 889#define BAD_SIMD_TYPE _("bad type in SIMD instruction")
c19d1205 890
c921be7d
NC
891static struct hash_control * arm_ops_hsh;
892static struct hash_control * arm_cond_hsh;
5ee91343 893static struct hash_control * arm_vcond_hsh;
c921be7d
NC
894static struct hash_control * arm_shift_hsh;
895static struct hash_control * arm_psr_hsh;
896static struct hash_control * arm_v7m_psr_hsh;
897static struct hash_control * arm_reg_hsh;
898static struct hash_control * arm_reloc_hsh;
899static struct hash_control * arm_barrier_opt_hsh;
b99bd4ef 900
b99bd4ef
NC
901/* Stuff needed to resolve the label ambiguity
902 As:
903 ...
904 label: <insn>
905 may differ from:
906 ...
907 label:
5f4273c7 908 <insn> */
b99bd4ef
NC
909
910symbolS * last_label_seen;
b34976b6 911static int label_is_thumb_function_name = FALSE;
e07e6e58 912
3d0c9500
NC
913/* Literal pool structure. Held on a per-section
914 and per-sub-section basis. */
a737bd4d 915
c19d1205 916#define MAX_LITERAL_POOL_SIZE 1024
3d0c9500 917typedef struct literal_pool
b99bd4ef 918{
c921be7d
NC
919 expressionS literals [MAX_LITERAL_POOL_SIZE];
920 unsigned int next_free_entry;
921 unsigned int id;
922 symbolS * symbol;
923 segT section;
924 subsegT sub_section;
a8040cf2
NC
925#ifdef OBJ_ELF
926 struct dwarf2_line_info locs [MAX_LITERAL_POOL_SIZE];
927#endif
c921be7d 928 struct literal_pool * next;
8335d6aa 929 unsigned int alignment;
3d0c9500 930} literal_pool;
b99bd4ef 931
3d0c9500
NC
932/* Pointer to a linked list of literal pools. */
933literal_pool * list_of_pools = NULL;
e27ec89e 934
2e6976a8
DG
935typedef enum asmfunc_states
936{
937 OUTSIDE_ASMFUNC,
938 WAITING_ASMFUNC_NAME,
939 WAITING_ENDASMFUNC
940} asmfunc_states;
941
942static asmfunc_states asmfunc_state = OUTSIDE_ASMFUNC;
943
e07e6e58 944#ifdef OBJ_ELF
5ee91343 945# define now_pred seg_info (now_seg)->tc_segment_info_data.current_pred
e07e6e58 946#else
5ee91343 947static struct current_pred now_pred;
e07e6e58
NC
948#endif
949
950static inline int
5ee91343 951now_pred_compatible (int cond)
e07e6e58 952{
5ee91343 953 return (cond & ~1) == (now_pred.cc & ~1);
e07e6e58
NC
954}
955
956static inline int
957conditional_insn (void)
958{
959 return inst.cond != COND_ALWAYS;
960}
961
5ee91343 962static int in_pred_block (void);
e07e6e58 963
5ee91343 964static int handle_pred_state (void);
e07e6e58
NC
965
966static void force_automatic_it_block_close (void);
967
c921be7d
NC
968static void it_fsm_post_encode (void);
969
5ee91343 970#define set_pred_insn_type(type) \
e07e6e58
NC
971 do \
972 { \
5ee91343
AV
973 inst.pred_insn_type = type; \
974 if (handle_pred_state () == FAIL) \
477330fc 975 return; \
e07e6e58
NC
976 } \
977 while (0)
978
5ee91343 979#define set_pred_insn_type_nonvoid(type, failret) \
c921be7d
NC
980 do \
981 { \
5ee91343
AV
982 inst.pred_insn_type = type; \
983 if (handle_pred_state () == FAIL) \
477330fc 984 return failret; \
c921be7d
NC
985 } \
986 while(0)
987
5ee91343 988#define set_pred_insn_type_last() \
e07e6e58
NC
989 do \
990 { \
991 if (inst.cond == COND_ALWAYS) \
5ee91343 992 set_pred_insn_type (IF_INSIDE_IT_LAST_INSN); \
e07e6e58 993 else \
5ee91343 994 set_pred_insn_type (INSIDE_IT_LAST_INSN); \
e07e6e58
NC
995 } \
996 while (0)
997
c19d1205 998/* Pure syntax. */
b99bd4ef 999
c19d1205
ZW
1000/* This array holds the chars that always start a comment. If the
1001 pre-processor is disabled, these aren't very useful. */
2e6976a8 1002char arm_comment_chars[] = "@";
3d0c9500 1003
c19d1205
ZW
1004/* This array holds the chars that only start a comment at the beginning of
1005 a line. If the line seems to have the form '# 123 filename'
1006 .line and .file directives will appear in the pre-processed output. */
1007/* Note that input_file.c hand checks for '#' at the beginning of the
1008 first line of the input file. This is because the compiler outputs
1009 #NO_APP at the beginning of its output. */
1010/* Also note that comments like this one will always work. */
1011const char line_comment_chars[] = "#";
3d0c9500 1012
2e6976a8 1013char arm_line_separator_chars[] = ";";
b99bd4ef 1014
c19d1205
ZW
1015/* Chars that can be used to separate mant
1016 from exp in floating point numbers. */
1017const char EXP_CHARS[] = "eE";
3d0c9500 1018
c19d1205
ZW
1019/* Chars that mean this number is a floating point constant. */
1020/* As in 0f12.456 */
1021/* or 0d1.2345e12 */
b99bd4ef 1022
c19d1205 1023const char FLT_CHARS[] = "rRsSfFdDxXeEpP";
3d0c9500 1024
c19d1205
ZW
1025/* Prefix characters that indicate the start of an immediate
1026 value. */
1027#define is_immediate_prefix(C) ((C) == '#' || (C) == '$')
3d0c9500 1028
c19d1205
ZW
1029/* Separator character handling. */
1030
1031#define skip_whitespace(str) do { if (*(str) == ' ') ++(str); } while (0)
1032
1033static inline int
1034skip_past_char (char ** str, char c)
1035{
8ab8155f
NC
1036 /* PR gas/14987: Allow for whitespace before the expected character. */
1037 skip_whitespace (*str);
427d0db6 1038
c19d1205
ZW
1039 if (**str == c)
1040 {
1041 (*str)++;
1042 return SUCCESS;
3d0c9500 1043 }
c19d1205
ZW
1044 else
1045 return FAIL;
1046}
c921be7d 1047
c19d1205 1048#define skip_past_comma(str) skip_past_char (str, ',')
3d0c9500 1049
c19d1205
ZW
1050/* Arithmetic expressions (possibly involving symbols). */
1051
1052/* Return TRUE if anything in the expression is a bignum. */
1053
0198d5e6 1054static bfd_boolean
c19d1205
ZW
1055walk_no_bignums (symbolS * sp)
1056{
1057 if (symbol_get_value_expression (sp)->X_op == O_big)
0198d5e6 1058 return TRUE;
c19d1205
ZW
1059
1060 if (symbol_get_value_expression (sp)->X_add_symbol)
3d0c9500 1061 {
c19d1205
ZW
1062 return (walk_no_bignums (symbol_get_value_expression (sp)->X_add_symbol)
1063 || (symbol_get_value_expression (sp)->X_op_symbol
1064 && walk_no_bignums (symbol_get_value_expression (sp)->X_op_symbol)));
3d0c9500
NC
1065 }
1066
0198d5e6 1067 return FALSE;
3d0c9500
NC
1068}
1069
0198d5e6 1070static bfd_boolean in_my_get_expression = FALSE;
c19d1205
ZW
1071
1072/* Third argument to my_get_expression. */
1073#define GE_NO_PREFIX 0
1074#define GE_IMM_PREFIX 1
1075#define GE_OPT_PREFIX 2
5287ad62
JB
1076/* This is a bit of a hack. Use an optional prefix, and also allow big (64-bit)
1077 immediates, as can be used in Neon VMVN and VMOV immediate instructions. */
1078#define GE_OPT_PREFIX_BIG 3
a737bd4d 1079
b99bd4ef 1080static int
c19d1205 1081my_get_expression (expressionS * ep, char ** str, int prefix_mode)
b99bd4ef 1082{
c19d1205 1083 char * save_in;
b99bd4ef 1084
c19d1205
ZW
1085 /* In unified syntax, all prefixes are optional. */
1086 if (unified_syntax)
5287ad62 1087 prefix_mode = (prefix_mode == GE_OPT_PREFIX_BIG) ? prefix_mode
477330fc 1088 : GE_OPT_PREFIX;
b99bd4ef 1089
c19d1205 1090 switch (prefix_mode)
b99bd4ef 1091 {
c19d1205
ZW
1092 case GE_NO_PREFIX: break;
1093 case GE_IMM_PREFIX:
1094 if (!is_immediate_prefix (**str))
1095 {
1096 inst.error = _("immediate expression requires a # prefix");
1097 return FAIL;
1098 }
1099 (*str)++;
1100 break;
1101 case GE_OPT_PREFIX:
5287ad62 1102 case GE_OPT_PREFIX_BIG:
c19d1205
ZW
1103 if (is_immediate_prefix (**str))
1104 (*str)++;
1105 break;
0198d5e6
TC
1106 default:
1107 abort ();
c19d1205 1108 }
b99bd4ef 1109
c19d1205 1110 memset (ep, 0, sizeof (expressionS));
b99bd4ef 1111
c19d1205
ZW
1112 save_in = input_line_pointer;
1113 input_line_pointer = *str;
0198d5e6 1114 in_my_get_expression = TRUE;
2ac93be7 1115 expression (ep);
0198d5e6 1116 in_my_get_expression = FALSE;
c19d1205 1117
f86adc07 1118 if (ep->X_op == O_illegal || ep->X_op == O_absent)
b99bd4ef 1119 {
f86adc07 1120 /* We found a bad or missing expression in md_operand(). */
c19d1205
ZW
1121 *str = input_line_pointer;
1122 input_line_pointer = save_in;
1123 if (inst.error == NULL)
f86adc07
NS
1124 inst.error = (ep->X_op == O_absent
1125 ? _("missing expression") :_("bad expression"));
c19d1205
ZW
1126 return 1;
1127 }
b99bd4ef 1128
c19d1205
ZW
1129 /* Get rid of any bignums now, so that we don't generate an error for which
1130 we can't establish a line number later on. Big numbers are never valid
1131 in instructions, which is where this routine is always called. */
5287ad62
JB
1132 if (prefix_mode != GE_OPT_PREFIX_BIG
1133 && (ep->X_op == O_big
477330fc 1134 || (ep->X_add_symbol
5287ad62 1135 && (walk_no_bignums (ep->X_add_symbol)
477330fc 1136 || (ep->X_op_symbol
5287ad62 1137 && walk_no_bignums (ep->X_op_symbol))))))
c19d1205
ZW
1138 {
1139 inst.error = _("invalid constant");
1140 *str = input_line_pointer;
1141 input_line_pointer = save_in;
1142 return 1;
1143 }
b99bd4ef 1144
c19d1205
ZW
1145 *str = input_line_pointer;
1146 input_line_pointer = save_in;
0198d5e6 1147 return SUCCESS;
b99bd4ef
NC
1148}
1149
c19d1205
ZW
1150/* Turn a string in input_line_pointer into a floating point constant
1151 of type TYPE, and store the appropriate bytes in *LITP. The number
1152 of LITTLENUMS emitted is stored in *SIZEP. An error message is
1153 returned, or NULL on OK.
b99bd4ef 1154
c19d1205
ZW
1155 Note that fp constants aren't represent in the normal way on the ARM.
1156 In big endian mode, things are as expected. However, in little endian
1157 mode fp constants are big-endian word-wise, and little-endian byte-wise
1158 within the words. For example, (double) 1.1 in big endian mode is
1159 the byte sequence 3f f1 99 99 99 99 99 9a, and in little endian mode is
1160 the byte sequence 99 99 f1 3f 9a 99 99 99.
b99bd4ef 1161
c19d1205 1162 ??? The format of 12 byte floats is uncertain according to gcc's arm.h. */
b99bd4ef 1163
6d4af3c2 1164const char *
c19d1205
ZW
1165md_atof (int type, char * litP, int * sizeP)
1166{
1167 int prec;
1168 LITTLENUM_TYPE words[MAX_LITTLENUMS];
1169 char *t;
1170 int i;
b99bd4ef 1171
c19d1205
ZW
1172 switch (type)
1173 {
1174 case 'f':
1175 case 'F':
1176 case 's':
1177 case 'S':
1178 prec = 2;
1179 break;
b99bd4ef 1180
c19d1205
ZW
1181 case 'd':
1182 case 'D':
1183 case 'r':
1184 case 'R':
1185 prec = 4;
1186 break;
b99bd4ef 1187
c19d1205
ZW
1188 case 'x':
1189 case 'X':
499ac353 1190 prec = 5;
c19d1205 1191 break;
b99bd4ef 1192
c19d1205
ZW
1193 case 'p':
1194 case 'P':
499ac353 1195 prec = 5;
c19d1205 1196 break;
a737bd4d 1197
c19d1205
ZW
1198 default:
1199 *sizeP = 0;
499ac353 1200 return _("Unrecognized or unsupported floating point constant");
c19d1205 1201 }
b99bd4ef 1202
c19d1205
ZW
1203 t = atof_ieee (input_line_pointer, type, words);
1204 if (t)
1205 input_line_pointer = t;
499ac353 1206 *sizeP = prec * sizeof (LITTLENUM_TYPE);
b99bd4ef 1207
c19d1205
ZW
1208 if (target_big_endian)
1209 {
1210 for (i = 0; i < prec; i++)
1211 {
499ac353
NC
1212 md_number_to_chars (litP, (valueT) words[i], sizeof (LITTLENUM_TYPE));
1213 litP += sizeof (LITTLENUM_TYPE);
c19d1205
ZW
1214 }
1215 }
1216 else
1217 {
e74cfd16 1218 if (ARM_CPU_HAS_FEATURE (cpu_variant, fpu_endian_pure))
c19d1205
ZW
1219 for (i = prec - 1; i >= 0; i--)
1220 {
499ac353
NC
1221 md_number_to_chars (litP, (valueT) words[i], sizeof (LITTLENUM_TYPE));
1222 litP += sizeof (LITTLENUM_TYPE);
c19d1205
ZW
1223 }
1224 else
1225 /* For a 4 byte float the order of elements in `words' is 1 0.
1226 For an 8 byte float the order is 1 0 3 2. */
1227 for (i = 0; i < prec; i += 2)
1228 {
499ac353
NC
1229 md_number_to_chars (litP, (valueT) words[i + 1],
1230 sizeof (LITTLENUM_TYPE));
1231 md_number_to_chars (litP + sizeof (LITTLENUM_TYPE),
1232 (valueT) words[i], sizeof (LITTLENUM_TYPE));
1233 litP += 2 * sizeof (LITTLENUM_TYPE);
c19d1205
ZW
1234 }
1235 }
b99bd4ef 1236
499ac353 1237 return NULL;
c19d1205 1238}
b99bd4ef 1239
c19d1205
ZW
1240/* We handle all bad expressions here, so that we can report the faulty
1241 instruction in the error message. */
0198d5e6 1242
c19d1205 1243void
91d6fa6a 1244md_operand (expressionS * exp)
c19d1205
ZW
1245{
1246 if (in_my_get_expression)
91d6fa6a 1247 exp->X_op = O_illegal;
b99bd4ef
NC
1248}
1249
c19d1205 1250/* Immediate values. */
b99bd4ef 1251
0198d5e6 1252#ifdef OBJ_ELF
c19d1205
ZW
1253/* Generic immediate-value read function for use in directives.
1254 Accepts anything that 'expression' can fold to a constant.
1255 *val receives the number. */
0198d5e6 1256
c19d1205
ZW
1257static int
1258immediate_for_directive (int *val)
b99bd4ef 1259{
c19d1205
ZW
1260 expressionS exp;
1261 exp.X_op = O_illegal;
b99bd4ef 1262
c19d1205
ZW
1263 if (is_immediate_prefix (*input_line_pointer))
1264 {
1265 input_line_pointer++;
1266 expression (&exp);
1267 }
b99bd4ef 1268
c19d1205
ZW
1269 if (exp.X_op != O_constant)
1270 {
1271 as_bad (_("expected #constant"));
1272 ignore_rest_of_line ();
1273 return FAIL;
1274 }
1275 *val = exp.X_add_number;
1276 return SUCCESS;
b99bd4ef 1277}
c19d1205 1278#endif
b99bd4ef 1279
c19d1205 1280/* Register parsing. */
b99bd4ef 1281
c19d1205
ZW
1282/* Generic register parser. CCP points to what should be the
1283 beginning of a register name. If it is indeed a valid register
1284 name, advance CCP over it and return the reg_entry structure;
1285 otherwise return NULL. Does not issue diagnostics. */
1286
1287static struct reg_entry *
1288arm_reg_parse_multi (char **ccp)
b99bd4ef 1289{
c19d1205
ZW
1290 char *start = *ccp;
1291 char *p;
1292 struct reg_entry *reg;
b99bd4ef 1293
477330fc
RM
1294 skip_whitespace (start);
1295
c19d1205
ZW
1296#ifdef REGISTER_PREFIX
1297 if (*start != REGISTER_PREFIX)
01cfc07f 1298 return NULL;
c19d1205
ZW
1299 start++;
1300#endif
1301#ifdef OPTIONAL_REGISTER_PREFIX
1302 if (*start == OPTIONAL_REGISTER_PREFIX)
1303 start++;
1304#endif
b99bd4ef 1305
c19d1205
ZW
1306 p = start;
1307 if (!ISALPHA (*p) || !is_name_beginner (*p))
1308 return NULL;
b99bd4ef 1309
c19d1205
ZW
1310 do
1311 p++;
1312 while (ISALPHA (*p) || ISDIGIT (*p) || *p == '_');
1313
1314 reg = (struct reg_entry *) hash_find_n (arm_reg_hsh, start, p - start);
1315
1316 if (!reg)
1317 return NULL;
1318
1319 *ccp = p;
1320 return reg;
b99bd4ef
NC
1321}
1322
1323static int
dcbf9037 1324arm_reg_alt_syntax (char **ccp, char *start, struct reg_entry *reg,
477330fc 1325 enum arm_reg_type type)
b99bd4ef 1326{
c19d1205
ZW
1327 /* Alternative syntaxes are accepted for a few register classes. */
1328 switch (type)
1329 {
1330 case REG_TYPE_MVF:
1331 case REG_TYPE_MVD:
1332 case REG_TYPE_MVFX:
1333 case REG_TYPE_MVDX:
1334 /* Generic coprocessor register names are allowed for these. */
79134647 1335 if (reg && reg->type == REG_TYPE_CN)
c19d1205
ZW
1336 return reg->number;
1337 break;
69b97547 1338
c19d1205
ZW
1339 case REG_TYPE_CP:
1340 /* For backward compatibility, a bare number is valid here. */
1341 {
1342 unsigned long processor = strtoul (start, ccp, 10);
1343 if (*ccp != start && processor <= 15)
1344 return processor;
1345 }
1a0670f3 1346 /* Fall through. */
6057a28f 1347
c19d1205
ZW
1348 case REG_TYPE_MMXWC:
1349 /* WC includes WCG. ??? I'm not sure this is true for all
1350 instructions that take WC registers. */
79134647 1351 if (reg && reg->type == REG_TYPE_MMXWCG)
c19d1205 1352 return reg->number;
6057a28f 1353 break;
c19d1205 1354
6057a28f 1355 default:
c19d1205 1356 break;
6057a28f
NC
1357 }
1358
dcbf9037
JB
1359 return FAIL;
1360}
1361
1362/* As arm_reg_parse_multi, but the register must be of type TYPE, and the
1363 return value is the register number or FAIL. */
1364
1365static int
1366arm_reg_parse (char **ccp, enum arm_reg_type type)
1367{
1368 char *start = *ccp;
1369 struct reg_entry *reg = arm_reg_parse_multi (ccp);
1370 int ret;
1371
1372 /* Do not allow a scalar (reg+index) to parse as a register. */
1373 if (reg && reg->neon && (reg->neon->defined & NTA_HASINDEX))
1374 return FAIL;
1375
1376 if (reg && reg->type == type)
1377 return reg->number;
1378
1379 if ((ret = arm_reg_alt_syntax (ccp, start, reg, type)) != FAIL)
1380 return ret;
1381
c19d1205
ZW
1382 *ccp = start;
1383 return FAIL;
1384}
69b97547 1385
dcbf9037
JB
1386/* Parse a Neon type specifier. *STR should point at the leading '.'
1387 character. Does no verification at this stage that the type fits the opcode
1388 properly. E.g.,
1389
1390 .i32.i32.s16
1391 .s32.f32
1392 .u16
1393
1394 Can all be legally parsed by this function.
1395
1396 Fills in neon_type struct pointer with parsed information, and updates STR
1397 to point after the parsed type specifier. Returns SUCCESS if this was a legal
1398 type, FAIL if not. */
1399
1400static int
1401parse_neon_type (struct neon_type *type, char **str)
1402{
1403 char *ptr = *str;
1404
1405 if (type)
1406 type->elems = 0;
1407
1408 while (type->elems < NEON_MAX_TYPE_ELS)
1409 {
1410 enum neon_el_type thistype = NT_untyped;
1411 unsigned thissize = -1u;
1412
1413 if (*ptr != '.')
1414 break;
1415
1416 ptr++;
1417
1418 /* Just a size without an explicit type. */
1419 if (ISDIGIT (*ptr))
1420 goto parsesize;
1421
1422 switch (TOLOWER (*ptr))
1423 {
1424 case 'i': thistype = NT_integer; break;
1425 case 'f': thistype = NT_float; break;
1426 case 'p': thistype = NT_poly; break;
1427 case 's': thistype = NT_signed; break;
1428 case 'u': thistype = NT_unsigned; break;
477330fc
RM
1429 case 'd':
1430 thistype = NT_float;
1431 thissize = 64;
1432 ptr++;
1433 goto done;
dcbf9037
JB
1434 default:
1435 as_bad (_("unexpected character `%c' in type specifier"), *ptr);
1436 return FAIL;
1437 }
1438
1439 ptr++;
1440
1441 /* .f is an abbreviation for .f32. */
1442 if (thistype == NT_float && !ISDIGIT (*ptr))
1443 thissize = 32;
1444 else
1445 {
1446 parsesize:
1447 thissize = strtoul (ptr, &ptr, 10);
1448
1449 if (thissize != 8 && thissize != 16 && thissize != 32
477330fc
RM
1450 && thissize != 64)
1451 {
1452 as_bad (_("bad size %d in type specifier"), thissize);
dcbf9037
JB
1453 return FAIL;
1454 }
1455 }
1456
037e8744 1457 done:
dcbf9037 1458 if (type)
477330fc
RM
1459 {
1460 type->el[type->elems].type = thistype;
dcbf9037
JB
1461 type->el[type->elems].size = thissize;
1462 type->elems++;
1463 }
1464 }
1465
1466 /* Empty/missing type is not a successful parse. */
1467 if (type->elems == 0)
1468 return FAIL;
1469
1470 *str = ptr;
1471
1472 return SUCCESS;
1473}
1474
1475/* Errors may be set multiple times during parsing or bit encoding
1476 (particularly in the Neon bits), but usually the earliest error which is set
1477 will be the most meaningful. Avoid overwriting it with later (cascading)
1478 errors by calling this function. */
1479
1480static void
1481first_error (const char *err)
1482{
1483 if (!inst.error)
1484 inst.error = err;
1485}
1486
1487/* Parse a single type, e.g. ".s32", leading period included. */
1488static int
1489parse_neon_operand_type (struct neon_type_el *vectype, char **ccp)
1490{
1491 char *str = *ccp;
1492 struct neon_type optype;
1493
1494 if (*str == '.')
1495 {
1496 if (parse_neon_type (&optype, &str) == SUCCESS)
477330fc
RM
1497 {
1498 if (optype.elems == 1)
1499 *vectype = optype.el[0];
1500 else
1501 {
1502 first_error (_("only one type should be specified for operand"));
1503 return FAIL;
1504 }
1505 }
dcbf9037 1506 else
477330fc
RM
1507 {
1508 first_error (_("vector type expected"));
1509 return FAIL;
1510 }
dcbf9037
JB
1511 }
1512 else
1513 return FAIL;
5f4273c7 1514
dcbf9037 1515 *ccp = str;
5f4273c7 1516
dcbf9037
JB
1517 return SUCCESS;
1518}
1519
1520/* Special meanings for indices (which have a range of 0-7), which will fit into
1521 a 4-bit integer. */
1522
1523#define NEON_ALL_LANES 15
1524#define NEON_INTERLEAVE_LANES 14
1525
5ee91343
AV
1526/* Record a use of the given feature. */
1527static void
1528record_feature_use (const arm_feature_set *feature)
1529{
1530 if (thumb_mode)
1531 ARM_MERGE_FEATURE_SETS (thumb_arch_used, thumb_arch_used, *feature);
1532 else
1533 ARM_MERGE_FEATURE_SETS (arm_arch_used, arm_arch_used, *feature);
1534}
1535
1536/* If the given feature available in the selected CPU, mark it as used.
1537 Returns TRUE iff feature is available. */
1538static bfd_boolean
1539mark_feature_used (const arm_feature_set *feature)
1540{
1541 /* Ensure the option is valid on the current architecture. */
1542 if (!ARM_CPU_HAS_FEATURE (cpu_variant, *feature))
1543 return FALSE;
1544
1545 /* Add the appropriate architecture feature for the barrier option used.
1546 */
1547 record_feature_use (feature);
1548
1549 return TRUE;
1550}
1551
dcbf9037
JB
1552/* Parse either a register or a scalar, with an optional type. Return the
1553 register number, and optionally fill in the actual type of the register
1554 when multiple alternatives were given (NEON_TYPE_NDQ) in *RTYPE, and
1555 type/index information in *TYPEINFO. */
1556
1557static int
1558parse_typed_reg_or_scalar (char **ccp, enum arm_reg_type type,
477330fc
RM
1559 enum arm_reg_type *rtype,
1560 struct neon_typed_alias *typeinfo)
dcbf9037
JB
1561{
1562 char *str = *ccp;
1563 struct reg_entry *reg = arm_reg_parse_multi (&str);
1564 struct neon_typed_alias atype;
1565 struct neon_type_el parsetype;
1566
1567 atype.defined = 0;
1568 atype.index = -1;
1569 atype.eltype.type = NT_invtype;
1570 atype.eltype.size = -1;
1571
1572 /* Try alternate syntax for some types of register. Note these are mutually
1573 exclusive with the Neon syntax extensions. */
1574 if (reg == NULL)
1575 {
1576 int altreg = arm_reg_alt_syntax (&str, *ccp, reg, type);
1577 if (altreg != FAIL)
477330fc 1578 *ccp = str;
dcbf9037 1579 if (typeinfo)
477330fc 1580 *typeinfo = atype;
dcbf9037
JB
1581 return altreg;
1582 }
1583
037e8744
JB
1584 /* Undo polymorphism when a set of register types may be accepted. */
1585 if ((type == REG_TYPE_NDQ
1586 && (reg->type == REG_TYPE_NQ || reg->type == REG_TYPE_VFD))
1587 || (type == REG_TYPE_VFSD
477330fc 1588 && (reg->type == REG_TYPE_VFS || reg->type == REG_TYPE_VFD))
037e8744 1589 || (type == REG_TYPE_NSDQ
477330fc
RM
1590 && (reg->type == REG_TYPE_VFS || reg->type == REG_TYPE_VFD
1591 || reg->type == REG_TYPE_NQ))
dec41383
JW
1592 || (type == REG_TYPE_NSD
1593 && (reg->type == REG_TYPE_VFS || reg->type == REG_TYPE_VFD))
f512f76f
NC
1594 || (type == REG_TYPE_MMXWC
1595 && (reg->type == REG_TYPE_MMXWCG)))
21d799b5 1596 type = (enum arm_reg_type) reg->type;
dcbf9037 1597
5ee91343
AV
1598 if (type == REG_TYPE_MQ)
1599 {
1600 if (!ARM_CPU_HAS_FEATURE (cpu_variant, mve_ext))
1601 return FAIL;
1602
1603 if (!reg || reg->type != REG_TYPE_NQ)
1604 return FAIL;
1605
1606 if (reg->number > 14 && !mark_feature_used (&fpu_vfp_ext_d32))
1607 {
1608 first_error (_("expected MVE register [q0..q7]"));
1609 return FAIL;
1610 }
1611 type = REG_TYPE_NQ;
1612 }
1613 else if (ARM_CPU_HAS_FEATURE (cpu_variant, mve_ext)
1614 && (type == REG_TYPE_NQ))
1615 return FAIL;
1616
1617
dcbf9037
JB
1618 if (type != reg->type)
1619 return FAIL;
1620
1621 if (reg->neon)
1622 atype = *reg->neon;
5f4273c7 1623
dcbf9037
JB
1624 if (parse_neon_operand_type (&parsetype, &str) == SUCCESS)
1625 {
1626 if ((atype.defined & NTA_HASTYPE) != 0)
477330fc
RM
1627 {
1628 first_error (_("can't redefine type for operand"));
1629 return FAIL;
1630 }
dcbf9037
JB
1631 atype.defined |= NTA_HASTYPE;
1632 atype.eltype = parsetype;
1633 }
5f4273c7 1634
dcbf9037
JB
1635 if (skip_past_char (&str, '[') == SUCCESS)
1636 {
dec41383
JW
1637 if (type != REG_TYPE_VFD
1638 && !(type == REG_TYPE_VFS
1639 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v8_2)))
477330fc
RM
1640 {
1641 first_error (_("only D registers may be indexed"));
1642 return FAIL;
1643 }
5f4273c7 1644
dcbf9037 1645 if ((atype.defined & NTA_HASINDEX) != 0)
477330fc
RM
1646 {
1647 first_error (_("can't change index for operand"));
1648 return FAIL;
1649 }
dcbf9037
JB
1650
1651 atype.defined |= NTA_HASINDEX;
1652
1653 if (skip_past_char (&str, ']') == SUCCESS)
477330fc 1654 atype.index = NEON_ALL_LANES;
dcbf9037 1655 else
477330fc
RM
1656 {
1657 expressionS exp;
dcbf9037 1658
477330fc 1659 my_get_expression (&exp, &str, GE_NO_PREFIX);
dcbf9037 1660
477330fc
RM
1661 if (exp.X_op != O_constant)
1662 {
1663 first_error (_("constant expression required"));
1664 return FAIL;
1665 }
dcbf9037 1666
477330fc
RM
1667 if (skip_past_char (&str, ']') == FAIL)
1668 return FAIL;
dcbf9037 1669
477330fc
RM
1670 atype.index = exp.X_add_number;
1671 }
dcbf9037 1672 }
5f4273c7 1673
dcbf9037
JB
1674 if (typeinfo)
1675 *typeinfo = atype;
5f4273c7 1676
dcbf9037
JB
1677 if (rtype)
1678 *rtype = type;
5f4273c7 1679
dcbf9037 1680 *ccp = str;
5f4273c7 1681
dcbf9037
JB
1682 return reg->number;
1683}
1684
efd6b359 1685/* Like arm_reg_parse, but also allow the following extra features:
dcbf9037
JB
1686 - If RTYPE is non-zero, return the (possibly restricted) type of the
1687 register (e.g. Neon double or quad reg when either has been requested).
1688 - If this is a Neon vector type with additional type information, fill
1689 in the struct pointed to by VECTYPE (if non-NULL).
5f4273c7 1690 This function will fault on encountering a scalar. */
dcbf9037
JB
1691
1692static int
1693arm_typed_reg_parse (char **ccp, enum arm_reg_type type,
477330fc 1694 enum arm_reg_type *rtype, struct neon_type_el *vectype)
dcbf9037
JB
1695{
1696 struct neon_typed_alias atype;
1697 char *str = *ccp;
1698 int reg = parse_typed_reg_or_scalar (&str, type, rtype, &atype);
1699
1700 if (reg == FAIL)
1701 return FAIL;
1702
0855e32b
NS
1703 /* Do not allow regname(... to parse as a register. */
1704 if (*str == '(')
1705 return FAIL;
1706
dcbf9037
JB
1707 /* Do not allow a scalar (reg+index) to parse as a register. */
1708 if ((atype.defined & NTA_HASINDEX) != 0)
1709 {
1710 first_error (_("register operand expected, but got scalar"));
1711 return FAIL;
1712 }
1713
1714 if (vectype)
1715 *vectype = atype.eltype;
1716
1717 *ccp = str;
1718
1719 return reg;
1720}
1721
1722#define NEON_SCALAR_REG(X) ((X) >> 4)
1723#define NEON_SCALAR_INDEX(X) ((X) & 15)
1724
5287ad62
JB
1725/* Parse a Neon scalar. Most of the time when we're parsing a scalar, we don't
1726 have enough information to be able to do a good job bounds-checking. So, we
1727 just do easy checks here, and do further checks later. */
1728
1729static int
dcbf9037 1730parse_scalar (char **ccp, int elsize, struct neon_type_el *type)
5287ad62 1731{
dcbf9037 1732 int reg;
5287ad62 1733 char *str = *ccp;
dcbf9037 1734 struct neon_typed_alias atype;
dec41383
JW
1735 enum arm_reg_type reg_type = REG_TYPE_VFD;
1736
1737 if (elsize == 4)
1738 reg_type = REG_TYPE_VFS;
5f4273c7 1739
dec41383 1740 reg = parse_typed_reg_or_scalar (&str, reg_type, NULL, &atype);
5f4273c7 1741
dcbf9037 1742 if (reg == FAIL || (atype.defined & NTA_HASINDEX) == 0)
5287ad62 1743 return FAIL;
5f4273c7 1744
dcbf9037 1745 if (atype.index == NEON_ALL_LANES)
5287ad62 1746 {
dcbf9037 1747 first_error (_("scalar must have an index"));
5287ad62
JB
1748 return FAIL;
1749 }
dcbf9037 1750 else if (atype.index >= 64 / elsize)
5287ad62 1751 {
dcbf9037 1752 first_error (_("scalar index out of range"));
5287ad62
JB
1753 return FAIL;
1754 }
5f4273c7 1755
dcbf9037
JB
1756 if (type)
1757 *type = atype.eltype;
5f4273c7 1758
5287ad62 1759 *ccp = str;
5f4273c7 1760
dcbf9037 1761 return reg * 16 + atype.index;
5287ad62
JB
1762}
1763
4b5a202f
AV
1764/* Types of registers in a list. */
1765
1766enum reg_list_els
1767{
1768 REGLIST_RN,
1769 REGLIST_CLRM,
1770 REGLIST_VFP_S,
efd6b359 1771 REGLIST_VFP_S_VPR,
4b5a202f 1772 REGLIST_VFP_D,
efd6b359 1773 REGLIST_VFP_D_VPR,
4b5a202f
AV
1774 REGLIST_NEON_D
1775};
1776
c19d1205 1777/* Parse an ARM register list. Returns the bitmask, or FAIL. */
e07e6e58 1778
c19d1205 1779static long
4b5a202f 1780parse_reg_list (char ** strp, enum reg_list_els etype)
c19d1205 1781{
4b5a202f
AV
1782 char *str = *strp;
1783 long range = 0;
1784 int another_range;
1785
1786 gas_assert (etype == REGLIST_RN || etype == REGLIST_CLRM);
a737bd4d 1787
c19d1205
ZW
1788 /* We come back here if we get ranges concatenated by '+' or '|'. */
1789 do
6057a28f 1790 {
477330fc
RM
1791 skip_whitespace (str);
1792
c19d1205 1793 another_range = 0;
a737bd4d 1794
c19d1205
ZW
1795 if (*str == '{')
1796 {
1797 int in_range = 0;
1798 int cur_reg = -1;
a737bd4d 1799
c19d1205
ZW
1800 str++;
1801 do
1802 {
1803 int reg;
4b5a202f
AV
1804 const char apsr_str[] = "apsr";
1805 int apsr_str_len = strlen (apsr_str);
6057a28f 1806
4b5a202f
AV
1807 reg = arm_reg_parse (&str, REGLIST_RN);
1808 if (etype == REGLIST_CLRM)
c19d1205 1809 {
4b5a202f
AV
1810 if (reg == REG_SP || reg == REG_PC)
1811 reg = FAIL;
1812 else if (reg == FAIL
1813 && !strncasecmp (str, apsr_str, apsr_str_len)
1814 && !ISALPHA (*(str + apsr_str_len)))
1815 {
1816 reg = 15;
1817 str += apsr_str_len;
1818 }
1819
1820 if (reg == FAIL)
1821 {
1822 first_error (_("r0-r12, lr or APSR expected"));
1823 return FAIL;
1824 }
1825 }
1826 else /* etype == REGLIST_RN. */
1827 {
1828 if (reg == FAIL)
1829 {
1830 first_error (_(reg_expected_msgs[REGLIST_RN]));
1831 return FAIL;
1832 }
c19d1205 1833 }
a737bd4d 1834
c19d1205
ZW
1835 if (in_range)
1836 {
1837 int i;
a737bd4d 1838
c19d1205
ZW
1839 if (reg <= cur_reg)
1840 {
dcbf9037 1841 first_error (_("bad range in register list"));
c19d1205
ZW
1842 return FAIL;
1843 }
40a18ebd 1844
c19d1205
ZW
1845 for (i = cur_reg + 1; i < reg; i++)
1846 {
1847 if (range & (1 << i))
1848 as_tsktsk
1849 (_("Warning: duplicated register (r%d) in register list"),
1850 i);
1851 else
1852 range |= 1 << i;
1853 }
1854 in_range = 0;
1855 }
a737bd4d 1856
c19d1205
ZW
1857 if (range & (1 << reg))
1858 as_tsktsk (_("Warning: duplicated register (r%d) in register list"),
1859 reg);
1860 else if (reg <= cur_reg)
1861 as_tsktsk (_("Warning: register range not in ascending order"));
a737bd4d 1862
c19d1205
ZW
1863 range |= 1 << reg;
1864 cur_reg = reg;
1865 }
1866 while (skip_past_comma (&str) != FAIL
1867 || (in_range = 1, *str++ == '-'));
1868 str--;
a737bd4d 1869
d996d970 1870 if (skip_past_char (&str, '}') == FAIL)
c19d1205 1871 {
dcbf9037 1872 first_error (_("missing `}'"));
c19d1205
ZW
1873 return FAIL;
1874 }
1875 }
4b5a202f 1876 else if (etype == REGLIST_RN)
c19d1205 1877 {
91d6fa6a 1878 expressionS exp;
40a18ebd 1879
91d6fa6a 1880 if (my_get_expression (&exp, &str, GE_NO_PREFIX))
c19d1205 1881 return FAIL;
40a18ebd 1882
91d6fa6a 1883 if (exp.X_op == O_constant)
c19d1205 1884 {
91d6fa6a
NC
1885 if (exp.X_add_number
1886 != (exp.X_add_number & 0x0000ffff))
c19d1205
ZW
1887 {
1888 inst.error = _("invalid register mask");
1889 return FAIL;
1890 }
a737bd4d 1891
91d6fa6a 1892 if ((range & exp.X_add_number) != 0)
c19d1205 1893 {
91d6fa6a 1894 int regno = range & exp.X_add_number;
a737bd4d 1895
c19d1205
ZW
1896 regno &= -regno;
1897 regno = (1 << regno) - 1;
1898 as_tsktsk
1899 (_("Warning: duplicated register (r%d) in register list"),
1900 regno);
1901 }
a737bd4d 1902
91d6fa6a 1903 range |= exp.X_add_number;
c19d1205
ZW
1904 }
1905 else
1906 {
e2b0ab59 1907 if (inst.relocs[0].type != 0)
c19d1205
ZW
1908 {
1909 inst.error = _("expression too complex");
1910 return FAIL;
1911 }
a737bd4d 1912
e2b0ab59
AV
1913 memcpy (&inst.relocs[0].exp, &exp, sizeof (expressionS));
1914 inst.relocs[0].type = BFD_RELOC_ARM_MULTI;
1915 inst.relocs[0].pc_rel = 0;
c19d1205
ZW
1916 }
1917 }
a737bd4d 1918
c19d1205
ZW
1919 if (*str == '|' || *str == '+')
1920 {
1921 str++;
1922 another_range = 1;
1923 }
a737bd4d 1924 }
c19d1205 1925 while (another_range);
a737bd4d 1926
c19d1205
ZW
1927 *strp = str;
1928 return range;
a737bd4d
NC
1929}
1930
c19d1205
ZW
1931/* Parse a VFP register list. If the string is invalid return FAIL.
1932 Otherwise return the number of registers, and set PBASE to the first
5287ad62
JB
1933 register. Parses registers of type ETYPE.
1934 If REGLIST_NEON_D is used, several syntax enhancements are enabled:
1935 - Q registers can be used to specify pairs of D registers
1936 - { } can be omitted from around a singleton register list
477330fc
RM
1937 FIXME: This is not implemented, as it would require backtracking in
1938 some cases, e.g.:
1939 vtbl.8 d3,d4,d5
1940 This could be done (the meaning isn't really ambiguous), but doesn't
1941 fit in well with the current parsing framework.
dcbf9037
JB
1942 - 32 D registers may be used (also true for VFPv3).
1943 FIXME: Types are ignored in these register lists, which is probably a
1944 bug. */
6057a28f 1945
c19d1205 1946static int
efd6b359
AV
1947parse_vfp_reg_list (char **ccp, unsigned int *pbase, enum reg_list_els etype,
1948 bfd_boolean *partial_match)
6057a28f 1949{
037e8744 1950 char *str = *ccp;
c19d1205
ZW
1951 int base_reg;
1952 int new_base;
21d799b5 1953 enum arm_reg_type regtype = (enum arm_reg_type) 0;
5287ad62 1954 int max_regs = 0;
c19d1205
ZW
1955 int count = 0;
1956 int warned = 0;
1957 unsigned long mask = 0;
a737bd4d 1958 int i;
efd6b359
AV
1959 bfd_boolean vpr_seen = FALSE;
1960 bfd_boolean expect_vpr =
1961 (etype == REGLIST_VFP_S_VPR) || (etype == REGLIST_VFP_D_VPR);
6057a28f 1962
477330fc 1963 if (skip_past_char (&str, '{') == FAIL)
5287ad62
JB
1964 {
1965 inst.error = _("expecting {");
1966 return FAIL;
1967 }
6057a28f 1968
5287ad62 1969 switch (etype)
c19d1205 1970 {
5287ad62 1971 case REGLIST_VFP_S:
efd6b359 1972 case REGLIST_VFP_S_VPR:
c19d1205
ZW
1973 regtype = REG_TYPE_VFS;
1974 max_regs = 32;
5287ad62 1975 break;
5f4273c7 1976
5287ad62 1977 case REGLIST_VFP_D:
efd6b359 1978 case REGLIST_VFP_D_VPR:
5287ad62 1979 regtype = REG_TYPE_VFD;
b7fc2769 1980 break;
5f4273c7 1981
b7fc2769
JB
1982 case REGLIST_NEON_D:
1983 regtype = REG_TYPE_NDQ;
1984 break;
4b5a202f
AV
1985
1986 default:
1987 gas_assert (0);
b7fc2769
JB
1988 }
1989
efd6b359 1990 if (etype != REGLIST_VFP_S && etype != REGLIST_VFP_S_VPR)
b7fc2769 1991 {
b1cc4aeb
PB
1992 /* VFPv3 allows 32 D registers, except for the VFPv3-D16 variant. */
1993 if (ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_d32))
477330fc
RM
1994 {
1995 max_regs = 32;
1996 if (thumb_mode)
1997 ARM_MERGE_FEATURE_SETS (thumb_arch_used, thumb_arch_used,
1998 fpu_vfp_ext_d32);
1999 else
2000 ARM_MERGE_FEATURE_SETS (arm_arch_used, arm_arch_used,
2001 fpu_vfp_ext_d32);
2002 }
5287ad62 2003 else
477330fc 2004 max_regs = 16;
c19d1205 2005 }
6057a28f 2006
c19d1205 2007 base_reg = max_regs;
efd6b359 2008 *partial_match = FALSE;
a737bd4d 2009
c19d1205
ZW
2010 do
2011 {
5287ad62 2012 int setmask = 1, addregs = 1;
efd6b359
AV
2013 const char vpr_str[] = "vpr";
2014 int vpr_str_len = strlen (vpr_str);
dcbf9037 2015
037e8744 2016 new_base = arm_typed_reg_parse (&str, regtype, &regtype, NULL);
dcbf9037 2017
efd6b359
AV
2018 if (expect_vpr)
2019 {
2020 if (new_base == FAIL
2021 && !strncasecmp (str, vpr_str, vpr_str_len)
2022 && !ISALPHA (*(str + vpr_str_len))
2023 && !vpr_seen)
2024 {
2025 vpr_seen = TRUE;
2026 str += vpr_str_len;
2027 if (count == 0)
2028 base_reg = 0; /* Canonicalize VPR only on d0 with 0 regs. */
2029 }
2030 else if (vpr_seen)
2031 {
2032 first_error (_("VPR expected last"));
2033 return FAIL;
2034 }
2035 else if (new_base == FAIL)
2036 {
2037 if (regtype == REG_TYPE_VFS)
2038 first_error (_("VFP single precision register or VPR "
2039 "expected"));
2040 else /* regtype == REG_TYPE_VFD. */
2041 first_error (_("VFP/Neon double precision register or VPR "
2042 "expected"));
2043 return FAIL;
2044 }
2045 }
2046 else if (new_base == FAIL)
a737bd4d 2047 {
dcbf9037 2048 first_error (_(reg_expected_msgs[regtype]));
c19d1205
ZW
2049 return FAIL;
2050 }
5f4273c7 2051
efd6b359
AV
2052 *partial_match = TRUE;
2053 if (vpr_seen)
2054 continue;
2055
b7fc2769 2056 if (new_base >= max_regs)
477330fc
RM
2057 {
2058 first_error (_("register out of range in list"));
2059 return FAIL;
2060 }
5f4273c7 2061
5287ad62
JB
2062 /* Note: a value of 2 * n is returned for the register Q<n>. */
2063 if (regtype == REG_TYPE_NQ)
477330fc
RM
2064 {
2065 setmask = 3;
2066 addregs = 2;
2067 }
5287ad62 2068
c19d1205
ZW
2069 if (new_base < base_reg)
2070 base_reg = new_base;
a737bd4d 2071
5287ad62 2072 if (mask & (setmask << new_base))
c19d1205 2073 {
dcbf9037 2074 first_error (_("invalid register list"));
c19d1205 2075 return FAIL;
a737bd4d 2076 }
a737bd4d 2077
efd6b359 2078 if ((mask >> new_base) != 0 && ! warned && !vpr_seen)
c19d1205
ZW
2079 {
2080 as_tsktsk (_("register list not in ascending order"));
2081 warned = 1;
2082 }
0bbf2aa4 2083
5287ad62
JB
2084 mask |= setmask << new_base;
2085 count += addregs;
0bbf2aa4 2086
037e8744 2087 if (*str == '-') /* We have the start of a range expression */
c19d1205
ZW
2088 {
2089 int high_range;
0bbf2aa4 2090
037e8744 2091 str++;
0bbf2aa4 2092
037e8744 2093 if ((high_range = arm_typed_reg_parse (&str, regtype, NULL, NULL))
477330fc 2094 == FAIL)
c19d1205
ZW
2095 {
2096 inst.error = gettext (reg_expected_msgs[regtype]);
2097 return FAIL;
2098 }
0bbf2aa4 2099
477330fc
RM
2100 if (high_range >= max_regs)
2101 {
2102 first_error (_("register out of range in list"));
2103 return FAIL;
2104 }
b7fc2769 2105
477330fc
RM
2106 if (regtype == REG_TYPE_NQ)
2107 high_range = high_range + 1;
5287ad62 2108
c19d1205
ZW
2109 if (high_range <= new_base)
2110 {
2111 inst.error = _("register range not in ascending order");
2112 return FAIL;
2113 }
0bbf2aa4 2114
5287ad62 2115 for (new_base += addregs; new_base <= high_range; new_base += addregs)
0bbf2aa4 2116 {
5287ad62 2117 if (mask & (setmask << new_base))
0bbf2aa4 2118 {
c19d1205
ZW
2119 inst.error = _("invalid register list");
2120 return FAIL;
0bbf2aa4 2121 }
c19d1205 2122
5287ad62
JB
2123 mask |= setmask << new_base;
2124 count += addregs;
0bbf2aa4 2125 }
0bbf2aa4 2126 }
0bbf2aa4 2127 }
037e8744 2128 while (skip_past_comma (&str) != FAIL);
0bbf2aa4 2129
037e8744 2130 str++;
0bbf2aa4 2131
c19d1205 2132 /* Sanity check -- should have raised a parse error above. */
efd6b359 2133 if ((!vpr_seen && count == 0) || count > max_regs)
c19d1205
ZW
2134 abort ();
2135
2136 *pbase = base_reg;
2137
efd6b359
AV
2138 if (expect_vpr && !vpr_seen)
2139 {
2140 first_error (_("VPR expected last"));
2141 return FAIL;
2142 }
2143
c19d1205
ZW
2144 /* Final test -- the registers must be consecutive. */
2145 mask >>= base_reg;
2146 for (i = 0; i < count; i++)
2147 {
2148 if ((mask & (1u << i)) == 0)
2149 {
2150 inst.error = _("non-contiguous register range");
2151 return FAIL;
2152 }
2153 }
2154
037e8744
JB
2155 *ccp = str;
2156
c19d1205 2157 return count;
b99bd4ef
NC
2158}
2159
dcbf9037
JB
2160/* True if two alias types are the same. */
2161
c921be7d 2162static bfd_boolean
dcbf9037
JB
2163neon_alias_types_same (struct neon_typed_alias *a, struct neon_typed_alias *b)
2164{
2165 if (!a && !b)
c921be7d 2166 return TRUE;
5f4273c7 2167
dcbf9037 2168 if (!a || !b)
c921be7d 2169 return FALSE;
dcbf9037
JB
2170
2171 if (a->defined != b->defined)
c921be7d 2172 return FALSE;
5f4273c7 2173
dcbf9037
JB
2174 if ((a->defined & NTA_HASTYPE) != 0
2175 && (a->eltype.type != b->eltype.type
477330fc 2176 || a->eltype.size != b->eltype.size))
c921be7d 2177 return FALSE;
dcbf9037
JB
2178
2179 if ((a->defined & NTA_HASINDEX) != 0
2180 && (a->index != b->index))
c921be7d 2181 return FALSE;
5f4273c7 2182
c921be7d 2183 return TRUE;
dcbf9037
JB
2184}
2185
5287ad62
JB
2186/* Parse element/structure lists for Neon VLD<n> and VST<n> instructions.
2187 The base register is put in *PBASE.
dcbf9037 2188 The lane (or one of the NEON_*_LANES constants) is placed in bits [3:0] of
5287ad62
JB
2189 the return value.
2190 The register stride (minus one) is put in bit 4 of the return value.
dcbf9037
JB
2191 Bits [6:5] encode the list length (minus one).
2192 The type of the list elements is put in *ELTYPE, if non-NULL. */
5287ad62 2193
5287ad62 2194#define NEON_LANE(X) ((X) & 0xf)
dcbf9037 2195#define NEON_REG_STRIDE(X) ((((X) >> 4) & 1) + 1)
5287ad62
JB
2196#define NEON_REGLIST_LENGTH(X) ((((X) >> 5) & 3) + 1)
2197
2198static int
dcbf9037 2199parse_neon_el_struct_list (char **str, unsigned *pbase,
477330fc 2200 struct neon_type_el *eltype)
5287ad62
JB
2201{
2202 char *ptr = *str;
2203 int base_reg = -1;
2204 int reg_incr = -1;
2205 int count = 0;
2206 int lane = -1;
2207 int leading_brace = 0;
2208 enum arm_reg_type rtype = REG_TYPE_NDQ;
20203fb9
NC
2209 const char *const incr_error = _("register stride must be 1 or 2");
2210 const char *const type_error = _("mismatched element/structure types in list");
dcbf9037 2211 struct neon_typed_alias firsttype;
f85d59c3
KT
2212 firsttype.defined = 0;
2213 firsttype.eltype.type = NT_invtype;
2214 firsttype.eltype.size = -1;
2215 firsttype.index = -1;
5f4273c7 2216
5287ad62
JB
2217 if (skip_past_char (&ptr, '{') == SUCCESS)
2218 leading_brace = 1;
5f4273c7 2219
5287ad62
JB
2220 do
2221 {
dcbf9037
JB
2222 struct neon_typed_alias atype;
2223 int getreg = parse_typed_reg_or_scalar (&ptr, rtype, &rtype, &atype);
2224
5287ad62 2225 if (getreg == FAIL)
477330fc
RM
2226 {
2227 first_error (_(reg_expected_msgs[rtype]));
2228 return FAIL;
2229 }
5f4273c7 2230
5287ad62 2231 if (base_reg == -1)
477330fc
RM
2232 {
2233 base_reg = getreg;
2234 if (rtype == REG_TYPE_NQ)
2235 {
2236 reg_incr = 1;
2237 }
2238 firsttype = atype;
2239 }
5287ad62 2240 else if (reg_incr == -1)
477330fc
RM
2241 {
2242 reg_incr = getreg - base_reg;
2243 if (reg_incr < 1 || reg_incr > 2)
2244 {
2245 first_error (_(incr_error));
2246 return FAIL;
2247 }
2248 }
5287ad62 2249 else if (getreg != base_reg + reg_incr * count)
477330fc
RM
2250 {
2251 first_error (_(incr_error));
2252 return FAIL;
2253 }
dcbf9037 2254
c921be7d 2255 if (! neon_alias_types_same (&atype, &firsttype))
477330fc
RM
2256 {
2257 first_error (_(type_error));
2258 return FAIL;
2259 }
5f4273c7 2260
5287ad62 2261 /* Handle Dn-Dm or Qn-Qm syntax. Can only be used with non-indexed list
477330fc 2262 modes. */
5287ad62 2263 if (ptr[0] == '-')
477330fc
RM
2264 {
2265 struct neon_typed_alias htype;
2266 int hireg, dregs = (rtype == REG_TYPE_NQ) ? 2 : 1;
2267 if (lane == -1)
2268 lane = NEON_INTERLEAVE_LANES;
2269 else if (lane != NEON_INTERLEAVE_LANES)
2270 {
2271 first_error (_(type_error));
2272 return FAIL;
2273 }
2274 if (reg_incr == -1)
2275 reg_incr = 1;
2276 else if (reg_incr != 1)
2277 {
2278 first_error (_("don't use Rn-Rm syntax with non-unit stride"));
2279 return FAIL;
2280 }
2281 ptr++;
2282 hireg = parse_typed_reg_or_scalar (&ptr, rtype, NULL, &htype);
2283 if (hireg == FAIL)
2284 {
2285 first_error (_(reg_expected_msgs[rtype]));
2286 return FAIL;
2287 }
2288 if (! neon_alias_types_same (&htype, &firsttype))
2289 {
2290 first_error (_(type_error));
2291 return FAIL;
2292 }
2293 count += hireg + dregs - getreg;
2294 continue;
2295 }
5f4273c7 2296
5287ad62
JB
2297 /* If we're using Q registers, we can't use [] or [n] syntax. */
2298 if (rtype == REG_TYPE_NQ)
477330fc
RM
2299 {
2300 count += 2;
2301 continue;
2302 }
5f4273c7 2303
dcbf9037 2304 if ((atype.defined & NTA_HASINDEX) != 0)
477330fc
RM
2305 {
2306 if (lane == -1)
2307 lane = atype.index;
2308 else if (lane != atype.index)
2309 {
2310 first_error (_(type_error));
2311 return FAIL;
2312 }
2313 }
5287ad62 2314 else if (lane == -1)
477330fc 2315 lane = NEON_INTERLEAVE_LANES;
5287ad62 2316 else if (lane != NEON_INTERLEAVE_LANES)
477330fc
RM
2317 {
2318 first_error (_(type_error));
2319 return FAIL;
2320 }
5287ad62
JB
2321 count++;
2322 }
2323 while ((count != 1 || leading_brace) && skip_past_comma (&ptr) != FAIL);
5f4273c7 2324
5287ad62
JB
2325 /* No lane set by [x]. We must be interleaving structures. */
2326 if (lane == -1)
2327 lane = NEON_INTERLEAVE_LANES;
5f4273c7 2328
5287ad62
JB
2329 /* Sanity check. */
2330 if (lane == -1 || base_reg == -1 || count < 1 || count > 4
2331 || (count > 1 && reg_incr == -1))
2332 {
dcbf9037 2333 first_error (_("error parsing element/structure list"));
5287ad62
JB
2334 return FAIL;
2335 }
2336
2337 if ((count > 1 || leading_brace) && skip_past_char (&ptr, '}') == FAIL)
2338 {
dcbf9037 2339 first_error (_("expected }"));
5287ad62
JB
2340 return FAIL;
2341 }
5f4273c7 2342
5287ad62
JB
2343 if (reg_incr == -1)
2344 reg_incr = 1;
2345
dcbf9037
JB
2346 if (eltype)
2347 *eltype = firsttype.eltype;
2348
5287ad62
JB
2349 *pbase = base_reg;
2350 *str = ptr;
5f4273c7 2351
5287ad62
JB
2352 return lane | ((reg_incr - 1) << 4) | ((count - 1) << 5);
2353}
2354
c19d1205
ZW
2355/* Parse an explicit relocation suffix on an expression. This is
2356 either nothing, or a word in parentheses. Note that if !OBJ_ELF,
2357 arm_reloc_hsh contains no entries, so this function can only
2358 succeed if there is no () after the word. Returns -1 on error,
2359 BFD_RELOC_UNUSED if there wasn't any suffix. */
3da1d841 2360
c19d1205
ZW
2361static int
2362parse_reloc (char **str)
b99bd4ef 2363{
c19d1205
ZW
2364 struct reloc_entry *r;
2365 char *p, *q;
b99bd4ef 2366
c19d1205
ZW
2367 if (**str != '(')
2368 return BFD_RELOC_UNUSED;
b99bd4ef 2369
c19d1205
ZW
2370 p = *str + 1;
2371 q = p;
2372
2373 while (*q && *q != ')' && *q != ',')
2374 q++;
2375 if (*q != ')')
2376 return -1;
2377
21d799b5
NC
2378 if ((r = (struct reloc_entry *)
2379 hash_find_n (arm_reloc_hsh, p, q - p)) == NULL)
c19d1205
ZW
2380 return -1;
2381
2382 *str = q + 1;
2383 return r->reloc;
b99bd4ef
NC
2384}
2385
c19d1205
ZW
2386/* Directives: register aliases. */
2387
dcbf9037 2388static struct reg_entry *
90ec0d68 2389insert_reg_alias (char *str, unsigned number, int type)
b99bd4ef 2390{
d3ce72d0 2391 struct reg_entry *new_reg;
c19d1205 2392 const char *name;
b99bd4ef 2393
d3ce72d0 2394 if ((new_reg = (struct reg_entry *) hash_find (arm_reg_hsh, str)) != 0)
c19d1205 2395 {
d3ce72d0 2396 if (new_reg->builtin)
c19d1205 2397 as_warn (_("ignoring attempt to redefine built-in register '%s'"), str);
b99bd4ef 2398
c19d1205
ZW
2399 /* Only warn about a redefinition if it's not defined as the
2400 same register. */
d3ce72d0 2401 else if (new_reg->number != number || new_reg->type != type)
c19d1205 2402 as_warn (_("ignoring redefinition of register alias '%s'"), str);
69b97547 2403
d929913e 2404 return NULL;
c19d1205 2405 }
b99bd4ef 2406
c19d1205 2407 name = xstrdup (str);
325801bd 2408 new_reg = XNEW (struct reg_entry);
b99bd4ef 2409
d3ce72d0
NC
2410 new_reg->name = name;
2411 new_reg->number = number;
2412 new_reg->type = type;
2413 new_reg->builtin = FALSE;
2414 new_reg->neon = NULL;
b99bd4ef 2415
d3ce72d0 2416 if (hash_insert (arm_reg_hsh, name, (void *) new_reg))
c19d1205 2417 abort ();
5f4273c7 2418
d3ce72d0 2419 return new_reg;
dcbf9037
JB
2420}
2421
2422static void
2423insert_neon_reg_alias (char *str, int number, int type,
477330fc 2424 struct neon_typed_alias *atype)
dcbf9037
JB
2425{
2426 struct reg_entry *reg = insert_reg_alias (str, number, type);
5f4273c7 2427
dcbf9037
JB
2428 if (!reg)
2429 {
2430 first_error (_("attempt to redefine typed alias"));
2431 return;
2432 }
5f4273c7 2433
dcbf9037
JB
2434 if (atype)
2435 {
325801bd 2436 reg->neon = XNEW (struct neon_typed_alias);
dcbf9037
JB
2437 *reg->neon = *atype;
2438 }
c19d1205 2439}
b99bd4ef 2440
c19d1205 2441/* Look for the .req directive. This is of the form:
b99bd4ef 2442
c19d1205 2443 new_register_name .req existing_register_name
b99bd4ef 2444
c19d1205 2445 If we find one, or if it looks sufficiently like one that we want to
d929913e 2446 handle any error here, return TRUE. Otherwise return FALSE. */
b99bd4ef 2447
d929913e 2448static bfd_boolean
c19d1205
ZW
2449create_register_alias (char * newname, char *p)
2450{
2451 struct reg_entry *old;
2452 char *oldname, *nbuf;
2453 size_t nlen;
b99bd4ef 2454
c19d1205
ZW
2455 /* The input scrubber ensures that whitespace after the mnemonic is
2456 collapsed to single spaces. */
2457 oldname = p;
2458 if (strncmp (oldname, " .req ", 6) != 0)
d929913e 2459 return FALSE;
b99bd4ef 2460
c19d1205
ZW
2461 oldname += 6;
2462 if (*oldname == '\0')
d929913e 2463 return FALSE;
b99bd4ef 2464
21d799b5 2465 old = (struct reg_entry *) hash_find (arm_reg_hsh, oldname);
c19d1205 2466 if (!old)
b99bd4ef 2467 {
c19d1205 2468 as_warn (_("unknown register '%s' -- .req ignored"), oldname);
d929913e 2469 return TRUE;
b99bd4ef
NC
2470 }
2471
c19d1205
ZW
2472 /* If TC_CASE_SENSITIVE is defined, then newname already points to
2473 the desired alias name, and p points to its end. If not, then
2474 the desired alias name is in the global original_case_string. */
2475#ifdef TC_CASE_SENSITIVE
2476 nlen = p - newname;
2477#else
2478 newname = original_case_string;
2479 nlen = strlen (newname);
2480#endif
b99bd4ef 2481
29a2809e 2482 nbuf = xmemdup0 (newname, nlen);
b99bd4ef 2483
c19d1205
ZW
2484 /* Create aliases under the new name as stated; an all-lowercase
2485 version of the new name; and an all-uppercase version of the new
2486 name. */
d929913e
NC
2487 if (insert_reg_alias (nbuf, old->number, old->type) != NULL)
2488 {
2489 for (p = nbuf; *p; p++)
2490 *p = TOUPPER (*p);
c19d1205 2491
d929913e
NC
2492 if (strncmp (nbuf, newname, nlen))
2493 {
2494 /* If this attempt to create an additional alias fails, do not bother
2495 trying to create the all-lower case alias. We will fail and issue
2496 a second, duplicate error message. This situation arises when the
2497 programmer does something like:
2498 foo .req r0
2499 Foo .req r1
2500 The second .req creates the "Foo" alias but then fails to create
5f4273c7 2501 the artificial FOO alias because it has already been created by the
d929913e
NC
2502 first .req. */
2503 if (insert_reg_alias (nbuf, old->number, old->type) == NULL)
e1fa0163
NC
2504 {
2505 free (nbuf);
2506 return TRUE;
2507 }
d929913e 2508 }
c19d1205 2509
d929913e
NC
2510 for (p = nbuf; *p; p++)
2511 *p = TOLOWER (*p);
c19d1205 2512
d929913e
NC
2513 if (strncmp (nbuf, newname, nlen))
2514 insert_reg_alias (nbuf, old->number, old->type);
2515 }
c19d1205 2516
e1fa0163 2517 free (nbuf);
d929913e 2518 return TRUE;
b99bd4ef
NC
2519}
2520
dcbf9037
JB
2521/* Create a Neon typed/indexed register alias using directives, e.g.:
2522 X .dn d5.s32[1]
2523 Y .qn 6.s16
2524 Z .dn d7
2525 T .dn Z[0]
2526 These typed registers can be used instead of the types specified after the
2527 Neon mnemonic, so long as all operands given have types. Types can also be
2528 specified directly, e.g.:
5f4273c7 2529 vadd d0.s32, d1.s32, d2.s32 */
dcbf9037 2530
c921be7d 2531static bfd_boolean
dcbf9037
JB
2532create_neon_reg_alias (char *newname, char *p)
2533{
2534 enum arm_reg_type basetype;
2535 struct reg_entry *basereg;
2536 struct reg_entry mybasereg;
2537 struct neon_type ntype;
2538 struct neon_typed_alias typeinfo;
12d6b0b7 2539 char *namebuf, *nameend ATTRIBUTE_UNUSED;
dcbf9037 2540 int namelen;
5f4273c7 2541
dcbf9037
JB
2542 typeinfo.defined = 0;
2543 typeinfo.eltype.type = NT_invtype;
2544 typeinfo.eltype.size = -1;
2545 typeinfo.index = -1;
5f4273c7 2546
dcbf9037 2547 nameend = p;
5f4273c7 2548
dcbf9037
JB
2549 if (strncmp (p, " .dn ", 5) == 0)
2550 basetype = REG_TYPE_VFD;
2551 else if (strncmp (p, " .qn ", 5) == 0)
2552 basetype = REG_TYPE_NQ;
2553 else
c921be7d 2554 return FALSE;
5f4273c7 2555
dcbf9037 2556 p += 5;
5f4273c7 2557
dcbf9037 2558 if (*p == '\0')
c921be7d 2559 return FALSE;
5f4273c7 2560
dcbf9037
JB
2561 basereg = arm_reg_parse_multi (&p);
2562
2563 if (basereg && basereg->type != basetype)
2564 {
2565 as_bad (_("bad type for register"));
c921be7d 2566 return FALSE;
dcbf9037
JB
2567 }
2568
2569 if (basereg == NULL)
2570 {
2571 expressionS exp;
2572 /* Try parsing as an integer. */
2573 my_get_expression (&exp, &p, GE_NO_PREFIX);
2574 if (exp.X_op != O_constant)
477330fc
RM
2575 {
2576 as_bad (_("expression must be constant"));
2577 return FALSE;
2578 }
dcbf9037
JB
2579 basereg = &mybasereg;
2580 basereg->number = (basetype == REG_TYPE_NQ) ? exp.X_add_number * 2
477330fc 2581 : exp.X_add_number;
dcbf9037
JB
2582 basereg->neon = 0;
2583 }
2584
2585 if (basereg->neon)
2586 typeinfo = *basereg->neon;
2587
2588 if (parse_neon_type (&ntype, &p) == SUCCESS)
2589 {
2590 /* We got a type. */
2591 if (typeinfo.defined & NTA_HASTYPE)
477330fc
RM
2592 {
2593 as_bad (_("can't redefine the type of a register alias"));
2594 return FALSE;
2595 }
5f4273c7 2596
dcbf9037
JB
2597 typeinfo.defined |= NTA_HASTYPE;
2598 if (ntype.elems != 1)
477330fc
RM
2599 {
2600 as_bad (_("you must specify a single type only"));
2601 return FALSE;
2602 }
dcbf9037
JB
2603 typeinfo.eltype = ntype.el[0];
2604 }
5f4273c7 2605
dcbf9037
JB
2606 if (skip_past_char (&p, '[') == SUCCESS)
2607 {
2608 expressionS exp;
2609 /* We got a scalar index. */
5f4273c7 2610
dcbf9037 2611 if (typeinfo.defined & NTA_HASINDEX)
477330fc
RM
2612 {
2613 as_bad (_("can't redefine the index of a scalar alias"));
2614 return FALSE;
2615 }
5f4273c7 2616
dcbf9037 2617 my_get_expression (&exp, &p, GE_NO_PREFIX);
5f4273c7 2618
dcbf9037 2619 if (exp.X_op != O_constant)
477330fc
RM
2620 {
2621 as_bad (_("scalar index must be constant"));
2622 return FALSE;
2623 }
5f4273c7 2624
dcbf9037
JB
2625 typeinfo.defined |= NTA_HASINDEX;
2626 typeinfo.index = exp.X_add_number;
5f4273c7 2627
dcbf9037 2628 if (skip_past_char (&p, ']') == FAIL)
477330fc
RM
2629 {
2630 as_bad (_("expecting ]"));
2631 return FALSE;
2632 }
dcbf9037
JB
2633 }
2634
15735687
NS
2635 /* If TC_CASE_SENSITIVE is defined, then newname already points to
2636 the desired alias name, and p points to its end. If not, then
2637 the desired alias name is in the global original_case_string. */
2638#ifdef TC_CASE_SENSITIVE
dcbf9037 2639 namelen = nameend - newname;
15735687
NS
2640#else
2641 newname = original_case_string;
2642 namelen = strlen (newname);
2643#endif
2644
29a2809e 2645 namebuf = xmemdup0 (newname, namelen);
5f4273c7 2646
dcbf9037 2647 insert_neon_reg_alias (namebuf, basereg->number, basetype,
477330fc 2648 typeinfo.defined != 0 ? &typeinfo : NULL);
5f4273c7 2649
dcbf9037
JB
2650 /* Insert name in all uppercase. */
2651 for (p = namebuf; *p; p++)
2652 *p = TOUPPER (*p);
5f4273c7 2653
dcbf9037
JB
2654 if (strncmp (namebuf, newname, namelen))
2655 insert_neon_reg_alias (namebuf, basereg->number, basetype,
477330fc 2656 typeinfo.defined != 0 ? &typeinfo : NULL);
5f4273c7 2657
dcbf9037
JB
2658 /* Insert name in all lowercase. */
2659 for (p = namebuf; *p; p++)
2660 *p = TOLOWER (*p);
5f4273c7 2661
dcbf9037
JB
2662 if (strncmp (namebuf, newname, namelen))
2663 insert_neon_reg_alias (namebuf, basereg->number, basetype,
477330fc 2664 typeinfo.defined != 0 ? &typeinfo : NULL);
5f4273c7 2665
e1fa0163 2666 free (namebuf);
c921be7d 2667 return TRUE;
dcbf9037
JB
2668}
2669
c19d1205
ZW
2670/* Should never be called, as .req goes between the alias and the
2671 register name, not at the beginning of the line. */
c921be7d 2672
b99bd4ef 2673static void
c19d1205 2674s_req (int a ATTRIBUTE_UNUSED)
b99bd4ef 2675{
c19d1205
ZW
2676 as_bad (_("invalid syntax for .req directive"));
2677}
b99bd4ef 2678
dcbf9037
JB
2679static void
2680s_dn (int a ATTRIBUTE_UNUSED)
2681{
2682 as_bad (_("invalid syntax for .dn directive"));
2683}
2684
2685static void
2686s_qn (int a ATTRIBUTE_UNUSED)
2687{
2688 as_bad (_("invalid syntax for .qn directive"));
2689}
2690
c19d1205
ZW
2691/* The .unreq directive deletes an alias which was previously defined
2692 by .req. For example:
b99bd4ef 2693
c19d1205
ZW
2694 my_alias .req r11
2695 .unreq my_alias */
b99bd4ef
NC
2696
2697static void
c19d1205 2698s_unreq (int a ATTRIBUTE_UNUSED)
b99bd4ef 2699{
c19d1205
ZW
2700 char * name;
2701 char saved_char;
b99bd4ef 2702
c19d1205
ZW
2703 name = input_line_pointer;
2704
2705 while (*input_line_pointer != 0
2706 && *input_line_pointer != ' '
2707 && *input_line_pointer != '\n')
2708 ++input_line_pointer;
2709
2710 saved_char = *input_line_pointer;
2711 *input_line_pointer = 0;
2712
2713 if (!*name)
2714 as_bad (_("invalid syntax for .unreq directive"));
2715 else
2716 {
21d799b5 2717 struct reg_entry *reg = (struct reg_entry *) hash_find (arm_reg_hsh,
477330fc 2718 name);
c19d1205
ZW
2719
2720 if (!reg)
2721 as_bad (_("unknown register alias '%s'"), name);
2722 else if (reg->builtin)
a1727c1a 2723 as_warn (_("ignoring attempt to use .unreq on fixed register name: '%s'"),
c19d1205
ZW
2724 name);
2725 else
2726 {
d929913e
NC
2727 char * p;
2728 char * nbuf;
2729
db0bc284 2730 hash_delete (arm_reg_hsh, name, FALSE);
c19d1205 2731 free ((char *) reg->name);
477330fc
RM
2732 if (reg->neon)
2733 free (reg->neon);
c19d1205 2734 free (reg);
d929913e
NC
2735
2736 /* Also locate the all upper case and all lower case versions.
2737 Do not complain if we cannot find one or the other as it
2738 was probably deleted above. */
5f4273c7 2739
d929913e
NC
2740 nbuf = strdup (name);
2741 for (p = nbuf; *p; p++)
2742 *p = TOUPPER (*p);
21d799b5 2743 reg = (struct reg_entry *) hash_find (arm_reg_hsh, nbuf);
d929913e
NC
2744 if (reg)
2745 {
db0bc284 2746 hash_delete (arm_reg_hsh, nbuf, FALSE);
d929913e
NC
2747 free ((char *) reg->name);
2748 if (reg->neon)
2749 free (reg->neon);
2750 free (reg);
2751 }
2752
2753 for (p = nbuf; *p; p++)
2754 *p = TOLOWER (*p);
21d799b5 2755 reg = (struct reg_entry *) hash_find (arm_reg_hsh, nbuf);
d929913e
NC
2756 if (reg)
2757 {
db0bc284 2758 hash_delete (arm_reg_hsh, nbuf, FALSE);
d929913e
NC
2759 free ((char *) reg->name);
2760 if (reg->neon)
2761 free (reg->neon);
2762 free (reg);
2763 }
2764
2765 free (nbuf);
c19d1205
ZW
2766 }
2767 }
b99bd4ef 2768
c19d1205 2769 *input_line_pointer = saved_char;
b99bd4ef
NC
2770 demand_empty_rest_of_line ();
2771}
2772
c19d1205
ZW
2773/* Directives: Instruction set selection. */
2774
2775#ifdef OBJ_ELF
2776/* This code is to handle mapping symbols as defined in the ARM ELF spec.
2777 (See "Mapping symbols", section 4.5.5, ARM AAELF version 1.0).
2778 Note that previously, $a and $t has type STT_FUNC (BSF_OBJECT flag),
2779 and $d has type STT_OBJECT (BSF_OBJECT flag). Now all three are untyped. */
2780
cd000bff
DJ
2781/* Create a new mapping symbol for the transition to STATE. */
2782
2783static void
2784make_mapping_symbol (enum mstate state, valueT value, fragS *frag)
b99bd4ef 2785{
a737bd4d 2786 symbolS * symbolP;
c19d1205
ZW
2787 const char * symname;
2788 int type;
b99bd4ef 2789
c19d1205 2790 switch (state)
b99bd4ef 2791 {
c19d1205
ZW
2792 case MAP_DATA:
2793 symname = "$d";
2794 type = BSF_NO_FLAGS;
2795 break;
2796 case MAP_ARM:
2797 symname = "$a";
2798 type = BSF_NO_FLAGS;
2799 break;
2800 case MAP_THUMB:
2801 symname = "$t";
2802 type = BSF_NO_FLAGS;
2803 break;
c19d1205
ZW
2804 default:
2805 abort ();
2806 }
2807
cd000bff 2808 symbolP = symbol_new (symname, now_seg, value, frag);
c19d1205
ZW
2809 symbol_get_bfdsym (symbolP)->flags |= type | BSF_LOCAL;
2810
2811 switch (state)
2812 {
2813 case MAP_ARM:
2814 THUMB_SET_FUNC (symbolP, 0);
2815 ARM_SET_THUMB (symbolP, 0);
2816 ARM_SET_INTERWORK (symbolP, support_interwork);
2817 break;
2818
2819 case MAP_THUMB:
2820 THUMB_SET_FUNC (symbolP, 1);
2821 ARM_SET_THUMB (symbolP, 1);
2822 ARM_SET_INTERWORK (symbolP, support_interwork);
2823 break;
2824
2825 case MAP_DATA:
2826 default:
cd000bff
DJ
2827 break;
2828 }
2829
2830 /* Save the mapping symbols for future reference. Also check that
2831 we do not place two mapping symbols at the same offset within a
2832 frag. We'll handle overlap between frags in
2de7820f
JZ
2833 check_mapping_symbols.
2834
2835 If .fill or other data filling directive generates zero sized data,
2836 the mapping symbol for the following code will have the same value
2837 as the one generated for the data filling directive. In this case,
2838 we replace the old symbol with the new one at the same address. */
cd000bff
DJ
2839 if (value == 0)
2840 {
2de7820f
JZ
2841 if (frag->tc_frag_data.first_map != NULL)
2842 {
2843 know (S_GET_VALUE (frag->tc_frag_data.first_map) == 0);
2844 symbol_remove (frag->tc_frag_data.first_map, &symbol_rootP, &symbol_lastP);
2845 }
cd000bff
DJ
2846 frag->tc_frag_data.first_map = symbolP;
2847 }
2848 if (frag->tc_frag_data.last_map != NULL)
0f020cef
JZ
2849 {
2850 know (S_GET_VALUE (frag->tc_frag_data.last_map) <= S_GET_VALUE (symbolP));
0f020cef
JZ
2851 if (S_GET_VALUE (frag->tc_frag_data.last_map) == S_GET_VALUE (symbolP))
2852 symbol_remove (frag->tc_frag_data.last_map, &symbol_rootP, &symbol_lastP);
2853 }
cd000bff
DJ
2854 frag->tc_frag_data.last_map = symbolP;
2855}
2856
2857/* We must sometimes convert a region marked as code to data during
2858 code alignment, if an odd number of bytes have to be padded. The
2859 code mapping symbol is pushed to an aligned address. */
2860
2861static void
2862insert_data_mapping_symbol (enum mstate state,
2863 valueT value, fragS *frag, offsetT bytes)
2864{
2865 /* If there was already a mapping symbol, remove it. */
2866 if (frag->tc_frag_data.last_map != NULL
2867 && S_GET_VALUE (frag->tc_frag_data.last_map) == frag->fr_address + value)
2868 {
2869 symbolS *symp = frag->tc_frag_data.last_map;
2870
2871 if (value == 0)
2872 {
2873 know (frag->tc_frag_data.first_map == symp);
2874 frag->tc_frag_data.first_map = NULL;
2875 }
2876 frag->tc_frag_data.last_map = NULL;
2877 symbol_remove (symp, &symbol_rootP, &symbol_lastP);
c19d1205 2878 }
cd000bff
DJ
2879
2880 make_mapping_symbol (MAP_DATA, value, frag);
2881 make_mapping_symbol (state, value + bytes, frag);
2882}
2883
2884static void mapping_state_2 (enum mstate state, int max_chars);
2885
2886/* Set the mapping state to STATE. Only call this when about to
2887 emit some STATE bytes to the file. */
2888
4e9aaefb 2889#define TRANSITION(from, to) (mapstate == (from) && state == (to))
cd000bff
DJ
2890void
2891mapping_state (enum mstate state)
2892{
940b5ce0
DJ
2893 enum mstate mapstate = seg_info (now_seg)->tc_segment_info_data.mapstate;
2894
cd000bff
DJ
2895 if (mapstate == state)
2896 /* The mapping symbol has already been emitted.
2897 There is nothing else to do. */
2898 return;
49c62a33
NC
2899
2900 if (state == MAP_ARM || state == MAP_THUMB)
2901 /* PR gas/12931
2902 All ARM instructions require 4-byte alignment.
2903 (Almost) all Thumb instructions require 2-byte alignment.
2904
2905 When emitting instructions into any section, mark the section
2906 appropriately.
2907
2908 Some Thumb instructions are alignment-sensitive modulo 4 bytes,
2909 but themselves require 2-byte alignment; this applies to some
33eaf5de 2910 PC- relative forms. However, these cases will involve implicit
49c62a33
NC
2911 literal pool generation or an explicit .align >=2, both of
2912 which will cause the section to me marked with sufficient
2913 alignment. Thus, we don't handle those cases here. */
2914 record_alignment (now_seg, state == MAP_ARM ? 2 : 1);
2915
2916 if (TRANSITION (MAP_UNDEFINED, MAP_DATA))
4e9aaefb 2917 /* This case will be evaluated later. */
cd000bff 2918 return;
cd000bff
DJ
2919
2920 mapping_state_2 (state, 0);
cd000bff
DJ
2921}
2922
2923/* Same as mapping_state, but MAX_CHARS bytes have already been
2924 allocated. Put the mapping symbol that far back. */
2925
2926static void
2927mapping_state_2 (enum mstate state, int max_chars)
2928{
940b5ce0
DJ
2929 enum mstate mapstate = seg_info (now_seg)->tc_segment_info_data.mapstate;
2930
2931 if (!SEG_NORMAL (now_seg))
2932 return;
2933
cd000bff
DJ
2934 if (mapstate == state)
2935 /* The mapping symbol has already been emitted.
2936 There is nothing else to do. */
2937 return;
2938
4e9aaefb
SA
2939 if (TRANSITION (MAP_UNDEFINED, MAP_ARM)
2940 || TRANSITION (MAP_UNDEFINED, MAP_THUMB))
2941 {
2942 struct frag * const frag_first = seg_info (now_seg)->frchainP->frch_root;
2943 const int add_symbol = (frag_now != frag_first) || (frag_now_fix () > 0);
2944
2945 if (add_symbol)
2946 make_mapping_symbol (MAP_DATA, (valueT) 0, frag_first);
2947 }
2948
cd000bff
DJ
2949 seg_info (now_seg)->tc_segment_info_data.mapstate = state;
2950 make_mapping_symbol (state, (valueT) frag_now_fix () - max_chars, frag_now);
c19d1205 2951}
4e9aaefb 2952#undef TRANSITION
c19d1205 2953#else
d3106081
NS
2954#define mapping_state(x) ((void)0)
2955#define mapping_state_2(x, y) ((void)0)
c19d1205
ZW
2956#endif
2957
2958/* Find the real, Thumb encoded start of a Thumb function. */
2959
4343666d 2960#ifdef OBJ_COFF
c19d1205
ZW
2961static symbolS *
2962find_real_start (symbolS * symbolP)
2963{
2964 char * real_start;
2965 const char * name = S_GET_NAME (symbolP);
2966 symbolS * new_target;
2967
2968 /* This definition must agree with the one in gcc/config/arm/thumb.c. */
2969#define STUB_NAME ".real_start_of"
2970
2971 if (name == NULL)
2972 abort ();
2973
37f6032b
ZW
2974 /* The compiler may generate BL instructions to local labels because
2975 it needs to perform a branch to a far away location. These labels
2976 do not have a corresponding ".real_start_of" label. We check
2977 both for S_IS_LOCAL and for a leading dot, to give a way to bypass
2978 the ".real_start_of" convention for nonlocal branches. */
2979 if (S_IS_LOCAL (symbolP) || name[0] == '.')
c19d1205
ZW
2980 return symbolP;
2981
e1fa0163 2982 real_start = concat (STUB_NAME, name, NULL);
c19d1205 2983 new_target = symbol_find (real_start);
e1fa0163 2984 free (real_start);
c19d1205
ZW
2985
2986 if (new_target == NULL)
2987 {
bd3ba5d1 2988 as_warn (_("Failed to find real start of function: %s\n"), name);
c19d1205
ZW
2989 new_target = symbolP;
2990 }
2991
c19d1205
ZW
2992 return new_target;
2993}
4343666d 2994#endif
c19d1205
ZW
2995
2996static void
2997opcode_select (int width)
2998{
2999 switch (width)
3000 {
3001 case 16:
3002 if (! thumb_mode)
3003 {
e74cfd16 3004 if (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v4t))
c19d1205
ZW
3005 as_bad (_("selected processor does not support THUMB opcodes"));
3006
3007 thumb_mode = 1;
3008 /* No need to force the alignment, since we will have been
3009 coming from ARM mode, which is word-aligned. */
3010 record_alignment (now_seg, 1);
3011 }
c19d1205
ZW
3012 break;
3013
3014 case 32:
3015 if (thumb_mode)
3016 {
e74cfd16 3017 if (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v1))
c19d1205
ZW
3018 as_bad (_("selected processor does not support ARM opcodes"));
3019
3020 thumb_mode = 0;
3021
3022 if (!need_pass_2)
3023 frag_align (2, 0, 0);
3024
3025 record_alignment (now_seg, 1);
3026 }
c19d1205
ZW
3027 break;
3028
3029 default:
3030 as_bad (_("invalid instruction size selected (%d)"), width);
3031 }
3032}
3033
3034static void
3035s_arm (int ignore ATTRIBUTE_UNUSED)
3036{
3037 opcode_select (32);
3038 demand_empty_rest_of_line ();
3039}
3040
3041static void
3042s_thumb (int ignore ATTRIBUTE_UNUSED)
3043{
3044 opcode_select (16);
3045 demand_empty_rest_of_line ();
3046}
3047
3048static void
3049s_code (int unused ATTRIBUTE_UNUSED)
3050{
3051 int temp;
3052
3053 temp = get_absolute_expression ();
3054 switch (temp)
3055 {
3056 case 16:
3057 case 32:
3058 opcode_select (temp);
3059 break;
3060
3061 default:
3062 as_bad (_("invalid operand to .code directive (%d) (expecting 16 or 32)"), temp);
3063 }
3064}
3065
3066static void
3067s_force_thumb (int ignore ATTRIBUTE_UNUSED)
3068{
3069 /* If we are not already in thumb mode go into it, EVEN if
3070 the target processor does not support thumb instructions.
3071 This is used by gcc/config/arm/lib1funcs.asm for example
3072 to compile interworking support functions even if the
3073 target processor should not support interworking. */
3074 if (! thumb_mode)
3075 {
3076 thumb_mode = 2;
3077 record_alignment (now_seg, 1);
3078 }
3079
3080 demand_empty_rest_of_line ();
3081}
3082
3083static void
3084s_thumb_func (int ignore ATTRIBUTE_UNUSED)
3085{
3086 s_thumb (0);
3087
3088 /* The following label is the name/address of the start of a Thumb function.
3089 We need to know this for the interworking support. */
3090 label_is_thumb_function_name = TRUE;
3091}
3092
3093/* Perform a .set directive, but also mark the alias as
3094 being a thumb function. */
3095
3096static void
3097s_thumb_set (int equiv)
3098{
3099 /* XXX the following is a duplicate of the code for s_set() in read.c
3100 We cannot just call that code as we need to get at the symbol that
3101 is created. */
3102 char * name;
3103 char delim;
3104 char * end_name;
3105 symbolS * symbolP;
3106
3107 /* Especial apologies for the random logic:
3108 This just grew, and could be parsed much more simply!
3109 Dean - in haste. */
d02603dc 3110 delim = get_symbol_name (& name);
c19d1205 3111 end_name = input_line_pointer;
d02603dc 3112 (void) restore_line_pointer (delim);
c19d1205
ZW
3113
3114 if (*input_line_pointer != ',')
3115 {
3116 *end_name = 0;
3117 as_bad (_("expected comma after name \"%s\""), name);
b99bd4ef
NC
3118 *end_name = delim;
3119 ignore_rest_of_line ();
3120 return;
3121 }
3122
3123 input_line_pointer++;
3124 *end_name = 0;
3125
3126 if (name[0] == '.' && name[1] == '\0')
3127 {
3128 /* XXX - this should not happen to .thumb_set. */
3129 abort ();
3130 }
3131
3132 if ((symbolP = symbol_find (name)) == NULL
3133 && (symbolP = md_undefined_symbol (name)) == NULL)
3134 {
3135#ifndef NO_LISTING
3136 /* When doing symbol listings, play games with dummy fragments living
3137 outside the normal fragment chain to record the file and line info
c19d1205 3138 for this symbol. */
b99bd4ef
NC
3139 if (listing & LISTING_SYMBOLS)
3140 {
3141 extern struct list_info_struct * listing_tail;
21d799b5 3142 fragS * dummy_frag = (fragS * ) xmalloc (sizeof (fragS));
b99bd4ef
NC
3143
3144 memset (dummy_frag, 0, sizeof (fragS));
3145 dummy_frag->fr_type = rs_fill;
3146 dummy_frag->line = listing_tail;
3147 symbolP = symbol_new (name, undefined_section, 0, dummy_frag);
3148 dummy_frag->fr_symbol = symbolP;
3149 }
3150 else
3151#endif
3152 symbolP = symbol_new (name, undefined_section, 0, &zero_address_frag);
3153
3154#ifdef OBJ_COFF
3155 /* "set" symbols are local unless otherwise specified. */
3156 SF_SET_LOCAL (symbolP);
3157#endif /* OBJ_COFF */
3158 } /* Make a new symbol. */
3159
3160 symbol_table_insert (symbolP);
3161
3162 * end_name = delim;
3163
3164 if (equiv
3165 && S_IS_DEFINED (symbolP)
3166 && S_GET_SEGMENT (symbolP) != reg_section)
3167 as_bad (_("symbol `%s' already defined"), S_GET_NAME (symbolP));
3168
3169 pseudo_set (symbolP);
3170
3171 demand_empty_rest_of_line ();
3172
c19d1205 3173 /* XXX Now we come to the Thumb specific bit of code. */
b99bd4ef
NC
3174
3175 THUMB_SET_FUNC (symbolP, 1);
3176 ARM_SET_THUMB (symbolP, 1);
3177#if defined OBJ_ELF || defined OBJ_COFF
3178 ARM_SET_INTERWORK (symbolP, support_interwork);
3179#endif
3180}
3181
c19d1205 3182/* Directives: Mode selection. */
b99bd4ef 3183
c19d1205
ZW
3184/* .syntax [unified|divided] - choose the new unified syntax
3185 (same for Arm and Thumb encoding, modulo slight differences in what
3186 can be represented) or the old divergent syntax for each mode. */
b99bd4ef 3187static void
c19d1205 3188s_syntax (int unused ATTRIBUTE_UNUSED)
b99bd4ef 3189{
c19d1205
ZW
3190 char *name, delim;
3191
d02603dc 3192 delim = get_symbol_name (& name);
c19d1205
ZW
3193
3194 if (!strcasecmp (name, "unified"))
3195 unified_syntax = TRUE;
3196 else if (!strcasecmp (name, "divided"))
3197 unified_syntax = FALSE;
3198 else
3199 {
3200 as_bad (_("unrecognized syntax mode \"%s\""), name);
3201 return;
3202 }
d02603dc 3203 (void) restore_line_pointer (delim);
b99bd4ef
NC
3204 demand_empty_rest_of_line ();
3205}
3206
c19d1205
ZW
3207/* Directives: sectioning and alignment. */
3208
c19d1205
ZW
3209static void
3210s_bss (int ignore ATTRIBUTE_UNUSED)
b99bd4ef 3211{
c19d1205
ZW
3212 /* We don't support putting frags in the BSS segment, we fake it by
3213 marking in_bss, then looking at s_skip for clues. */
3214 subseg_set (bss_section, 0);
3215 demand_empty_rest_of_line ();
cd000bff
DJ
3216
3217#ifdef md_elf_section_change_hook
3218 md_elf_section_change_hook ();
3219#endif
c19d1205 3220}
b99bd4ef 3221
c19d1205
ZW
3222static void
3223s_even (int ignore ATTRIBUTE_UNUSED)
3224{
3225 /* Never make frag if expect extra pass. */
3226 if (!need_pass_2)
3227 frag_align (1, 0, 0);
b99bd4ef 3228
c19d1205 3229 record_alignment (now_seg, 1);
b99bd4ef 3230
c19d1205 3231 demand_empty_rest_of_line ();
b99bd4ef
NC
3232}
3233
2e6976a8
DG
3234/* Directives: CodeComposer Studio. */
3235
3236/* .ref (for CodeComposer Studio syntax only). */
3237static void
3238s_ccs_ref (int unused ATTRIBUTE_UNUSED)
3239{
3240 if (codecomposer_syntax)
3241 ignore_rest_of_line ();
3242 else
3243 as_bad (_(".ref pseudo-op only available with -mccs flag."));
3244}
3245
3246/* If name is not NULL, then it is used for marking the beginning of a
2b0f3761 3247 function, whereas if it is NULL then it means the function end. */
2e6976a8
DG
3248static void
3249asmfunc_debug (const char * name)
3250{
3251 static const char * last_name = NULL;
3252
3253 if (name != NULL)
3254 {
3255 gas_assert (last_name == NULL);
3256 last_name = name;
3257
3258 if (debug_type == DEBUG_STABS)
3259 stabs_generate_asm_func (name, name);
3260 }
3261 else
3262 {
3263 gas_assert (last_name != NULL);
3264
3265 if (debug_type == DEBUG_STABS)
3266 stabs_generate_asm_endfunc (last_name, last_name);
3267
3268 last_name = NULL;
3269 }
3270}
3271
3272static void
3273s_ccs_asmfunc (int unused ATTRIBUTE_UNUSED)
3274{
3275 if (codecomposer_syntax)
3276 {
3277 switch (asmfunc_state)
3278 {
3279 case OUTSIDE_ASMFUNC:
3280 asmfunc_state = WAITING_ASMFUNC_NAME;
3281 break;
3282
3283 case WAITING_ASMFUNC_NAME:
3284 as_bad (_(".asmfunc repeated."));
3285 break;
3286
3287 case WAITING_ENDASMFUNC:
3288 as_bad (_(".asmfunc without function."));
3289 break;
3290 }
3291 demand_empty_rest_of_line ();
3292 }
3293 else
3294 as_bad (_(".asmfunc pseudo-op only available with -mccs flag."));
3295}
3296
3297static void
3298s_ccs_endasmfunc (int unused ATTRIBUTE_UNUSED)
3299{
3300 if (codecomposer_syntax)
3301 {
3302 switch (asmfunc_state)
3303 {
3304 case OUTSIDE_ASMFUNC:
3305 as_bad (_(".endasmfunc without a .asmfunc."));
3306 break;
3307
3308 case WAITING_ASMFUNC_NAME:
3309 as_bad (_(".endasmfunc without function."));
3310 break;
3311
3312 case WAITING_ENDASMFUNC:
3313 asmfunc_state = OUTSIDE_ASMFUNC;
3314 asmfunc_debug (NULL);
3315 break;
3316 }
3317 demand_empty_rest_of_line ();
3318 }
3319 else
3320 as_bad (_(".endasmfunc pseudo-op only available with -mccs flag."));
3321}
3322
3323static void
3324s_ccs_def (int name)
3325{
3326 if (codecomposer_syntax)
3327 s_globl (name);
3328 else
3329 as_bad (_(".def pseudo-op only available with -mccs flag."));
3330}
3331
c19d1205 3332/* Directives: Literal pools. */
a737bd4d 3333
c19d1205
ZW
3334static literal_pool *
3335find_literal_pool (void)
a737bd4d 3336{
c19d1205 3337 literal_pool * pool;
a737bd4d 3338
c19d1205 3339 for (pool = list_of_pools; pool != NULL; pool = pool->next)
a737bd4d 3340 {
c19d1205
ZW
3341 if (pool->section == now_seg
3342 && pool->sub_section == now_subseg)
3343 break;
a737bd4d
NC
3344 }
3345
c19d1205 3346 return pool;
a737bd4d
NC
3347}
3348
c19d1205
ZW
3349static literal_pool *
3350find_or_make_literal_pool (void)
a737bd4d 3351{
c19d1205
ZW
3352 /* Next literal pool ID number. */
3353 static unsigned int latest_pool_num = 1;
3354 literal_pool * pool;
a737bd4d 3355
c19d1205 3356 pool = find_literal_pool ();
a737bd4d 3357
c19d1205 3358 if (pool == NULL)
a737bd4d 3359 {
c19d1205 3360 /* Create a new pool. */
325801bd 3361 pool = XNEW (literal_pool);
c19d1205
ZW
3362 if (! pool)
3363 return NULL;
a737bd4d 3364
c19d1205
ZW
3365 pool->next_free_entry = 0;
3366 pool->section = now_seg;
3367 pool->sub_section = now_subseg;
3368 pool->next = list_of_pools;
3369 pool->symbol = NULL;
8335d6aa 3370 pool->alignment = 2;
c19d1205
ZW
3371
3372 /* Add it to the list. */
3373 list_of_pools = pool;
a737bd4d 3374 }
a737bd4d 3375
c19d1205
ZW
3376 /* New pools, and emptied pools, will have a NULL symbol. */
3377 if (pool->symbol == NULL)
a737bd4d 3378 {
c19d1205
ZW
3379 pool->symbol = symbol_create (FAKE_LABEL_NAME, undefined_section,
3380 (valueT) 0, &zero_address_frag);
3381 pool->id = latest_pool_num ++;
a737bd4d
NC
3382 }
3383
c19d1205
ZW
3384 /* Done. */
3385 return pool;
a737bd4d
NC
3386}
3387
c19d1205 3388/* Add the literal in the global 'inst'
5f4273c7 3389 structure to the relevant literal pool. */
b99bd4ef
NC
3390
3391static int
8335d6aa 3392add_to_lit_pool (unsigned int nbytes)
b99bd4ef 3393{
8335d6aa
JW
3394#define PADDING_SLOT 0x1
3395#define LIT_ENTRY_SIZE_MASK 0xFF
c19d1205 3396 literal_pool * pool;
8335d6aa
JW
3397 unsigned int entry, pool_size = 0;
3398 bfd_boolean padding_slot_p = FALSE;
e56c722b 3399 unsigned imm1 = 0;
8335d6aa
JW
3400 unsigned imm2 = 0;
3401
3402 if (nbytes == 8)
3403 {
3404 imm1 = inst.operands[1].imm;
3405 imm2 = (inst.operands[1].regisimm ? inst.operands[1].reg
e2b0ab59 3406 : inst.relocs[0].exp.X_unsigned ? 0
2569ceb0 3407 : ((bfd_int64_t) inst.operands[1].imm) >> 32);
8335d6aa
JW
3408 if (target_big_endian)
3409 {
3410 imm1 = imm2;
3411 imm2 = inst.operands[1].imm;
3412 }
3413 }
b99bd4ef 3414
c19d1205
ZW
3415 pool = find_or_make_literal_pool ();
3416
3417 /* Check if this literal value is already in the pool. */
3418 for (entry = 0; entry < pool->next_free_entry; entry ++)
b99bd4ef 3419 {
8335d6aa
JW
3420 if (nbytes == 4)
3421 {
e2b0ab59
AV
3422 if ((pool->literals[entry].X_op == inst.relocs[0].exp.X_op)
3423 && (inst.relocs[0].exp.X_op == O_constant)
8335d6aa 3424 && (pool->literals[entry].X_add_number
e2b0ab59 3425 == inst.relocs[0].exp.X_add_number)
8335d6aa
JW
3426 && (pool->literals[entry].X_md == nbytes)
3427 && (pool->literals[entry].X_unsigned
e2b0ab59 3428 == inst.relocs[0].exp.X_unsigned))
8335d6aa
JW
3429 break;
3430
e2b0ab59
AV
3431 if ((pool->literals[entry].X_op == inst.relocs[0].exp.X_op)
3432 && (inst.relocs[0].exp.X_op == O_symbol)
8335d6aa 3433 && (pool->literals[entry].X_add_number
e2b0ab59 3434 == inst.relocs[0].exp.X_add_number)
8335d6aa 3435 && (pool->literals[entry].X_add_symbol
e2b0ab59 3436 == inst.relocs[0].exp.X_add_symbol)
8335d6aa 3437 && (pool->literals[entry].X_op_symbol
e2b0ab59 3438 == inst.relocs[0].exp.X_op_symbol)
8335d6aa
JW
3439 && (pool->literals[entry].X_md == nbytes))
3440 break;
3441 }
3442 else if ((nbytes == 8)
3443 && !(pool_size & 0x7)
3444 && ((entry + 1) != pool->next_free_entry)
3445 && (pool->literals[entry].X_op == O_constant)
19f2f6a9 3446 && (pool->literals[entry].X_add_number == (offsetT) imm1)
8335d6aa 3447 && (pool->literals[entry].X_unsigned
e2b0ab59 3448 == inst.relocs[0].exp.X_unsigned)
8335d6aa 3449 && (pool->literals[entry + 1].X_op == O_constant)
19f2f6a9 3450 && (pool->literals[entry + 1].X_add_number == (offsetT) imm2)
8335d6aa 3451 && (pool->literals[entry + 1].X_unsigned
e2b0ab59 3452 == inst.relocs[0].exp.X_unsigned))
c19d1205
ZW
3453 break;
3454
8335d6aa
JW
3455 padding_slot_p = ((pool->literals[entry].X_md >> 8) == PADDING_SLOT);
3456 if (padding_slot_p && (nbytes == 4))
c19d1205 3457 break;
8335d6aa
JW
3458
3459 pool_size += 4;
b99bd4ef
NC
3460 }
3461
c19d1205
ZW
3462 /* Do we need to create a new entry? */
3463 if (entry == pool->next_free_entry)
3464 {
3465 if (entry >= MAX_LITERAL_POOL_SIZE)
3466 {
3467 inst.error = _("literal pool overflow");
3468 return FAIL;
3469 }
3470
8335d6aa
JW
3471 if (nbytes == 8)
3472 {
3473 /* For 8-byte entries, we align to an 8-byte boundary,
3474 and split it into two 4-byte entries, because on 32-bit
3475 host, 8-byte constants are treated as big num, thus
3476 saved in "generic_bignum" which will be overwritten
3477 by later assignments.
3478
3479 We also need to make sure there is enough space for
3480 the split.
3481
3482 We also check to make sure the literal operand is a
3483 constant number. */
e2b0ab59
AV
3484 if (!(inst.relocs[0].exp.X_op == O_constant
3485 || inst.relocs[0].exp.X_op == O_big))
8335d6aa
JW
3486 {
3487 inst.error = _("invalid type for literal pool");
3488 return FAIL;
3489 }
3490 else if (pool_size & 0x7)
3491 {
3492 if ((entry + 2) >= MAX_LITERAL_POOL_SIZE)
3493 {
3494 inst.error = _("literal pool overflow");
3495 return FAIL;
3496 }
3497
e2b0ab59 3498 pool->literals[entry] = inst.relocs[0].exp;
a6684f0d 3499 pool->literals[entry].X_op = O_constant;
8335d6aa
JW
3500 pool->literals[entry].X_add_number = 0;
3501 pool->literals[entry++].X_md = (PADDING_SLOT << 8) | 4;
3502 pool->next_free_entry += 1;
3503 pool_size += 4;
3504 }
3505 else if ((entry + 1) >= MAX_LITERAL_POOL_SIZE)
3506 {
3507 inst.error = _("literal pool overflow");
3508 return FAIL;
3509 }
3510
e2b0ab59 3511 pool->literals[entry] = inst.relocs[0].exp;
8335d6aa
JW
3512 pool->literals[entry].X_op = O_constant;
3513 pool->literals[entry].X_add_number = imm1;
e2b0ab59 3514 pool->literals[entry].X_unsigned = inst.relocs[0].exp.X_unsigned;
8335d6aa 3515 pool->literals[entry++].X_md = 4;
e2b0ab59 3516 pool->literals[entry] = inst.relocs[0].exp;
8335d6aa
JW
3517 pool->literals[entry].X_op = O_constant;
3518 pool->literals[entry].X_add_number = imm2;
e2b0ab59 3519 pool->literals[entry].X_unsigned = inst.relocs[0].exp.X_unsigned;
8335d6aa
JW
3520 pool->literals[entry].X_md = 4;
3521 pool->alignment = 3;
3522 pool->next_free_entry += 1;
3523 }
3524 else
3525 {
e2b0ab59 3526 pool->literals[entry] = inst.relocs[0].exp;
8335d6aa
JW
3527 pool->literals[entry].X_md = 4;
3528 }
3529
a8040cf2
NC
3530#ifdef OBJ_ELF
3531 /* PR ld/12974: Record the location of the first source line to reference
3532 this entry in the literal pool. If it turns out during linking that the
3533 symbol does not exist we will be able to give an accurate line number for
3534 the (first use of the) missing reference. */
3535 if (debug_type == DEBUG_DWARF2)
3536 dwarf2_where (pool->locs + entry);
3537#endif
c19d1205
ZW
3538 pool->next_free_entry += 1;
3539 }
8335d6aa
JW
3540 else if (padding_slot_p)
3541 {
e2b0ab59 3542 pool->literals[entry] = inst.relocs[0].exp;
8335d6aa
JW
3543 pool->literals[entry].X_md = nbytes;
3544 }
b99bd4ef 3545
e2b0ab59
AV
3546 inst.relocs[0].exp.X_op = O_symbol;
3547 inst.relocs[0].exp.X_add_number = pool_size;
3548 inst.relocs[0].exp.X_add_symbol = pool->symbol;
b99bd4ef 3549
c19d1205 3550 return SUCCESS;
b99bd4ef
NC
3551}
3552
2e6976a8 3553bfd_boolean
2e57ce7b 3554tc_start_label_without_colon (void)
2e6976a8
DG
3555{
3556 bfd_boolean ret = TRUE;
3557
3558 if (codecomposer_syntax && asmfunc_state == WAITING_ASMFUNC_NAME)
3559 {
2e57ce7b 3560 const char *label = input_line_pointer;
2e6976a8
DG
3561
3562 while (!is_end_of_line[(int) label[-1]])
3563 --label;
3564
3565 if (*label == '.')
3566 {
3567 as_bad (_("Invalid label '%s'"), label);
3568 ret = FALSE;
3569 }
3570
3571 asmfunc_debug (label);
3572
3573 asmfunc_state = WAITING_ENDASMFUNC;
3574 }
3575
3576 return ret;
3577}
3578
c19d1205 3579/* Can't use symbol_new here, so have to create a symbol and then at
33eaf5de 3580 a later date assign it a value. That's what these functions do. */
e16bb312 3581
c19d1205
ZW
3582static void
3583symbol_locate (symbolS * symbolP,
3584 const char * name, /* It is copied, the caller can modify. */
3585 segT segment, /* Segment identifier (SEG_<something>). */
3586 valueT valu, /* Symbol value. */
3587 fragS * frag) /* Associated fragment. */
3588{
e57e6ddc 3589 size_t name_length;
c19d1205 3590 char * preserved_copy_of_name;
e16bb312 3591
c19d1205
ZW
3592 name_length = strlen (name) + 1; /* +1 for \0. */
3593 obstack_grow (&notes, name, name_length);
21d799b5 3594 preserved_copy_of_name = (char *) obstack_finish (&notes);
e16bb312 3595
c19d1205
ZW
3596#ifdef tc_canonicalize_symbol_name
3597 preserved_copy_of_name =
3598 tc_canonicalize_symbol_name (preserved_copy_of_name);
3599#endif
b99bd4ef 3600
c19d1205 3601 S_SET_NAME (symbolP, preserved_copy_of_name);
b99bd4ef 3602
c19d1205
ZW
3603 S_SET_SEGMENT (symbolP, segment);
3604 S_SET_VALUE (symbolP, valu);
3605 symbol_clear_list_pointers (symbolP);
b99bd4ef 3606
c19d1205 3607 symbol_set_frag (symbolP, frag);
b99bd4ef 3608
c19d1205
ZW
3609 /* Link to end of symbol chain. */
3610 {
3611 extern int symbol_table_frozen;
b99bd4ef 3612
c19d1205
ZW
3613 if (symbol_table_frozen)
3614 abort ();
3615 }
b99bd4ef 3616
c19d1205 3617 symbol_append (symbolP, symbol_lastP, & symbol_rootP, & symbol_lastP);
b99bd4ef 3618
c19d1205 3619 obj_symbol_new_hook (symbolP);
b99bd4ef 3620
c19d1205
ZW
3621#ifdef tc_symbol_new_hook
3622 tc_symbol_new_hook (symbolP);
3623#endif
3624
3625#ifdef DEBUG_SYMS
3626 verify_symbol_chain (symbol_rootP, symbol_lastP);
3627#endif /* DEBUG_SYMS */
b99bd4ef
NC
3628}
3629
c19d1205
ZW
3630static void
3631s_ltorg (int ignored ATTRIBUTE_UNUSED)
b99bd4ef 3632{
c19d1205
ZW
3633 unsigned int entry;
3634 literal_pool * pool;
3635 char sym_name[20];
b99bd4ef 3636
c19d1205
ZW
3637 pool = find_literal_pool ();
3638 if (pool == NULL
3639 || pool->symbol == NULL
3640 || pool->next_free_entry == 0)
3641 return;
b99bd4ef 3642
c19d1205
ZW
3643 /* Align pool as you have word accesses.
3644 Only make a frag if we have to. */
3645 if (!need_pass_2)
8335d6aa 3646 frag_align (pool->alignment, 0, 0);
b99bd4ef 3647
c19d1205 3648 record_alignment (now_seg, 2);
b99bd4ef 3649
aaca88ef 3650#ifdef OBJ_ELF
47fc6e36
WN
3651 seg_info (now_seg)->tc_segment_info_data.mapstate = MAP_DATA;
3652 make_mapping_symbol (MAP_DATA, (valueT) frag_now_fix (), frag_now);
aaca88ef 3653#endif
c19d1205 3654 sprintf (sym_name, "$$lit_\002%x", pool->id);
b99bd4ef 3655
c19d1205
ZW
3656 symbol_locate (pool->symbol, sym_name, now_seg,
3657 (valueT) frag_now_fix (), frag_now);
3658 symbol_table_insert (pool->symbol);
b99bd4ef 3659
c19d1205 3660 ARM_SET_THUMB (pool->symbol, thumb_mode);
b99bd4ef 3661
c19d1205
ZW
3662#if defined OBJ_COFF || defined OBJ_ELF
3663 ARM_SET_INTERWORK (pool->symbol, support_interwork);
3664#endif
6c43fab6 3665
c19d1205 3666 for (entry = 0; entry < pool->next_free_entry; entry ++)
a8040cf2
NC
3667 {
3668#ifdef OBJ_ELF
3669 if (debug_type == DEBUG_DWARF2)
3670 dwarf2_gen_line_info (frag_now_fix (), pool->locs + entry);
3671#endif
3672 /* First output the expression in the instruction to the pool. */
8335d6aa
JW
3673 emit_expr (&(pool->literals[entry]),
3674 pool->literals[entry].X_md & LIT_ENTRY_SIZE_MASK);
a8040cf2 3675 }
b99bd4ef 3676
c19d1205
ZW
3677 /* Mark the pool as empty. */
3678 pool->next_free_entry = 0;
3679 pool->symbol = NULL;
b99bd4ef
NC
3680}
3681
c19d1205
ZW
3682#ifdef OBJ_ELF
3683/* Forward declarations for functions below, in the MD interface
3684 section. */
3685static void fix_new_arm (fragS *, int, short, expressionS *, int, int);
3686static valueT create_unwind_entry (int);
3687static void start_unwind_section (const segT, int);
3688static void add_unwind_opcode (valueT, int);
3689static void flush_pending_unwind (void);
b99bd4ef 3690
c19d1205 3691/* Directives: Data. */
b99bd4ef 3692
c19d1205
ZW
3693static void
3694s_arm_elf_cons (int nbytes)
3695{
3696 expressionS exp;
b99bd4ef 3697
c19d1205
ZW
3698#ifdef md_flush_pending_output
3699 md_flush_pending_output ();
3700#endif
b99bd4ef 3701
c19d1205 3702 if (is_it_end_of_statement ())
b99bd4ef 3703 {
c19d1205
ZW
3704 demand_empty_rest_of_line ();
3705 return;
b99bd4ef
NC
3706 }
3707
c19d1205
ZW
3708#ifdef md_cons_align
3709 md_cons_align (nbytes);
3710#endif
b99bd4ef 3711
c19d1205
ZW
3712 mapping_state (MAP_DATA);
3713 do
b99bd4ef 3714 {
c19d1205
ZW
3715 int reloc;
3716 char *base = input_line_pointer;
b99bd4ef 3717
c19d1205 3718 expression (& exp);
b99bd4ef 3719
c19d1205
ZW
3720 if (exp.X_op != O_symbol)
3721 emit_expr (&exp, (unsigned int) nbytes);
3722 else
3723 {
3724 char *before_reloc = input_line_pointer;
3725 reloc = parse_reloc (&input_line_pointer);
3726 if (reloc == -1)
3727 {
3728 as_bad (_("unrecognized relocation suffix"));
3729 ignore_rest_of_line ();
3730 return;
3731 }
3732 else if (reloc == BFD_RELOC_UNUSED)
3733 emit_expr (&exp, (unsigned int) nbytes);
3734 else
3735 {
21d799b5 3736 reloc_howto_type *howto = (reloc_howto_type *)
477330fc
RM
3737 bfd_reloc_type_lookup (stdoutput,
3738 (bfd_reloc_code_real_type) reloc);
c19d1205 3739 int size = bfd_get_reloc_size (howto);
b99bd4ef 3740
2fc8bdac
ZW
3741 if (reloc == BFD_RELOC_ARM_PLT32)
3742 {
3743 as_bad (_("(plt) is only valid on branch targets"));
3744 reloc = BFD_RELOC_UNUSED;
3745 size = 0;
3746 }
3747
c19d1205 3748 if (size > nbytes)
992a06ee
AM
3749 as_bad (ngettext ("%s relocations do not fit in %d byte",
3750 "%s relocations do not fit in %d bytes",
3751 nbytes),
c19d1205
ZW
3752 howto->name, nbytes);
3753 else
3754 {
3755 /* We've parsed an expression stopping at O_symbol.
3756 But there may be more expression left now that we
3757 have parsed the relocation marker. Parse it again.
3758 XXX Surely there is a cleaner way to do this. */
3759 char *p = input_line_pointer;
3760 int offset;
325801bd 3761 char *save_buf = XNEWVEC (char, input_line_pointer - base);
e1fa0163 3762
c19d1205
ZW
3763 memcpy (save_buf, base, input_line_pointer - base);
3764 memmove (base + (input_line_pointer - before_reloc),
3765 base, before_reloc - base);
3766
3767 input_line_pointer = base + (input_line_pointer-before_reloc);
3768 expression (&exp);
3769 memcpy (base, save_buf, p - base);
3770
3771 offset = nbytes - size;
4b1a927e
AM
3772 p = frag_more (nbytes);
3773 memset (p, 0, nbytes);
c19d1205 3774 fix_new_exp (frag_now, p - frag_now->fr_literal + offset,
21d799b5 3775 size, &exp, 0, (enum bfd_reloc_code_real) reloc);
e1fa0163 3776 free (save_buf);
c19d1205
ZW
3777 }
3778 }
3779 }
b99bd4ef 3780 }
c19d1205 3781 while (*input_line_pointer++ == ',');
b99bd4ef 3782
c19d1205
ZW
3783 /* Put terminator back into stream. */
3784 input_line_pointer --;
3785 demand_empty_rest_of_line ();
b99bd4ef
NC
3786}
3787
c921be7d
NC
3788/* Emit an expression containing a 32-bit thumb instruction.
3789 Implementation based on put_thumb32_insn. */
3790
3791static void
3792emit_thumb32_expr (expressionS * exp)
3793{
3794 expressionS exp_high = *exp;
3795
3796 exp_high.X_add_number = (unsigned long)exp_high.X_add_number >> 16;
3797 emit_expr (& exp_high, (unsigned int) THUMB_SIZE);
3798 exp->X_add_number &= 0xffff;
3799 emit_expr (exp, (unsigned int) THUMB_SIZE);
3800}
3801
3802/* Guess the instruction size based on the opcode. */
3803
3804static int
3805thumb_insn_size (int opcode)
3806{
3807 if ((unsigned int) opcode < 0xe800u)
3808 return 2;
3809 else if ((unsigned int) opcode >= 0xe8000000u)
3810 return 4;
3811 else
3812 return 0;
3813}
3814
3815static bfd_boolean
3816emit_insn (expressionS *exp, int nbytes)
3817{
3818 int size = 0;
3819
3820 if (exp->X_op == O_constant)
3821 {
3822 size = nbytes;
3823
3824 if (size == 0)
3825 size = thumb_insn_size (exp->X_add_number);
3826
3827 if (size != 0)
3828 {
3829 if (size == 2 && (unsigned int)exp->X_add_number > 0xffffu)
3830 {
3831 as_bad (_(".inst.n operand too big. "\
3832 "Use .inst.w instead"));
3833 size = 0;
3834 }
3835 else
3836 {
5ee91343
AV
3837 if (now_pred.state == AUTOMATIC_PRED_BLOCK)
3838 set_pred_insn_type_nonvoid (OUTSIDE_PRED_INSN, 0);
c921be7d 3839 else
5ee91343 3840 set_pred_insn_type_nonvoid (NEUTRAL_IT_INSN, 0);
c921be7d
NC
3841
3842 if (thumb_mode && (size > THUMB_SIZE) && !target_big_endian)
3843 emit_thumb32_expr (exp);
3844 else
3845 emit_expr (exp, (unsigned int) size);
3846
3847 it_fsm_post_encode ();
3848 }
3849 }
3850 else
3851 as_bad (_("cannot determine Thumb instruction size. " \
3852 "Use .inst.n/.inst.w instead"));
3853 }
3854 else
3855 as_bad (_("constant expression required"));
3856
3857 return (size != 0);
3858}
3859
3860/* Like s_arm_elf_cons but do not use md_cons_align and
3861 set the mapping state to MAP_ARM/MAP_THUMB. */
3862
3863static void
3864s_arm_elf_inst (int nbytes)
3865{
3866 if (is_it_end_of_statement ())
3867 {
3868 demand_empty_rest_of_line ();
3869 return;
3870 }
3871
3872 /* Calling mapping_state () here will not change ARM/THUMB,
3873 but will ensure not to be in DATA state. */
3874
3875 if (thumb_mode)
3876 mapping_state (MAP_THUMB);
3877 else
3878 {
3879 if (nbytes != 0)
3880 {
3881 as_bad (_("width suffixes are invalid in ARM mode"));
3882 ignore_rest_of_line ();
3883 return;
3884 }
3885
3886 nbytes = 4;
3887
3888 mapping_state (MAP_ARM);
3889 }
3890
3891 do
3892 {
3893 expressionS exp;
3894
3895 expression (& exp);
3896
3897 if (! emit_insn (& exp, nbytes))
3898 {
3899 ignore_rest_of_line ();
3900 return;
3901 }
3902 }
3903 while (*input_line_pointer++ == ',');
3904
3905 /* Put terminator back into stream. */
3906 input_line_pointer --;
3907 demand_empty_rest_of_line ();
3908}
b99bd4ef 3909
c19d1205 3910/* Parse a .rel31 directive. */
b99bd4ef 3911
c19d1205
ZW
3912static void
3913s_arm_rel31 (int ignored ATTRIBUTE_UNUSED)
3914{
3915 expressionS exp;
3916 char *p;
3917 valueT highbit;
b99bd4ef 3918
c19d1205
ZW
3919 highbit = 0;
3920 if (*input_line_pointer == '1')
3921 highbit = 0x80000000;
3922 else if (*input_line_pointer != '0')
3923 as_bad (_("expected 0 or 1"));
b99bd4ef 3924
c19d1205
ZW
3925 input_line_pointer++;
3926 if (*input_line_pointer != ',')
3927 as_bad (_("missing comma"));
3928 input_line_pointer++;
b99bd4ef 3929
c19d1205
ZW
3930#ifdef md_flush_pending_output
3931 md_flush_pending_output ();
3932#endif
b99bd4ef 3933
c19d1205
ZW
3934#ifdef md_cons_align
3935 md_cons_align (4);
3936#endif
b99bd4ef 3937
c19d1205 3938 mapping_state (MAP_DATA);
b99bd4ef 3939
c19d1205 3940 expression (&exp);
b99bd4ef 3941
c19d1205
ZW
3942 p = frag_more (4);
3943 md_number_to_chars (p, highbit, 4);
3944 fix_new_arm (frag_now, p - frag_now->fr_literal, 4, &exp, 1,
3945 BFD_RELOC_ARM_PREL31);
b99bd4ef 3946
c19d1205 3947 demand_empty_rest_of_line ();
b99bd4ef
NC
3948}
3949
c19d1205 3950/* Directives: AEABI stack-unwind tables. */
b99bd4ef 3951
c19d1205 3952/* Parse an unwind_fnstart directive. Simply records the current location. */
b99bd4ef 3953
c19d1205
ZW
3954static void
3955s_arm_unwind_fnstart (int ignored ATTRIBUTE_UNUSED)
3956{
3957 demand_empty_rest_of_line ();
921e5f0a
PB
3958 if (unwind.proc_start)
3959 {
c921be7d 3960 as_bad (_("duplicate .fnstart directive"));
921e5f0a
PB
3961 return;
3962 }
3963
c19d1205
ZW
3964 /* Mark the start of the function. */
3965 unwind.proc_start = expr_build_dot ();
b99bd4ef 3966
c19d1205
ZW
3967 /* Reset the rest of the unwind info. */
3968 unwind.opcode_count = 0;
3969 unwind.table_entry = NULL;
3970 unwind.personality_routine = NULL;
3971 unwind.personality_index = -1;
3972 unwind.frame_size = 0;
3973 unwind.fp_offset = 0;
fdfde340 3974 unwind.fp_reg = REG_SP;
c19d1205
ZW
3975 unwind.fp_used = 0;
3976 unwind.sp_restored = 0;
3977}
b99bd4ef 3978
b99bd4ef 3979
c19d1205
ZW
3980/* Parse a handlerdata directive. Creates the exception handling table entry
3981 for the function. */
b99bd4ef 3982
c19d1205
ZW
3983static void
3984s_arm_unwind_handlerdata (int ignored ATTRIBUTE_UNUSED)
3985{
3986 demand_empty_rest_of_line ();
921e5f0a 3987 if (!unwind.proc_start)
c921be7d 3988 as_bad (MISSING_FNSTART);
921e5f0a 3989
c19d1205 3990 if (unwind.table_entry)
6decc662 3991 as_bad (_("duplicate .handlerdata directive"));
f02232aa 3992
c19d1205
ZW
3993 create_unwind_entry (1);
3994}
a737bd4d 3995
c19d1205 3996/* Parse an unwind_fnend directive. Generates the index table entry. */
b99bd4ef 3997
c19d1205
ZW
3998static void
3999s_arm_unwind_fnend (int ignored ATTRIBUTE_UNUSED)
4000{
4001 long where;
4002 char *ptr;
4003 valueT val;
940b5ce0 4004 unsigned int marked_pr_dependency;
f02232aa 4005
c19d1205 4006 demand_empty_rest_of_line ();
f02232aa 4007
921e5f0a
PB
4008 if (!unwind.proc_start)
4009 {
c921be7d 4010 as_bad (_(".fnend directive without .fnstart"));
921e5f0a
PB
4011 return;
4012 }
4013
c19d1205
ZW
4014 /* Add eh table entry. */
4015 if (unwind.table_entry == NULL)
4016 val = create_unwind_entry (0);
4017 else
4018 val = 0;
f02232aa 4019
c19d1205
ZW
4020 /* Add index table entry. This is two words. */
4021 start_unwind_section (unwind.saved_seg, 1);
4022 frag_align (2, 0, 0);
4023 record_alignment (now_seg, 2);
b99bd4ef 4024
c19d1205 4025 ptr = frag_more (8);
5011093d 4026 memset (ptr, 0, 8);
c19d1205 4027 where = frag_now_fix () - 8;
f02232aa 4028
c19d1205
ZW
4029 /* Self relative offset of the function start. */
4030 fix_new (frag_now, where, 4, unwind.proc_start, 0, 1,
4031 BFD_RELOC_ARM_PREL31);
f02232aa 4032
c19d1205
ZW
4033 /* Indicate dependency on EHABI-defined personality routines to the
4034 linker, if it hasn't been done already. */
940b5ce0
DJ
4035 marked_pr_dependency
4036 = seg_info (now_seg)->tc_segment_info_data.marked_pr_dependency;
c19d1205
ZW
4037 if (unwind.personality_index >= 0 && unwind.personality_index < 3
4038 && !(marked_pr_dependency & (1 << unwind.personality_index)))
4039 {
5f4273c7
NC
4040 static const char *const name[] =
4041 {
4042 "__aeabi_unwind_cpp_pr0",
4043 "__aeabi_unwind_cpp_pr1",
4044 "__aeabi_unwind_cpp_pr2"
4045 };
c19d1205
ZW
4046 symbolS *pr = symbol_find_or_make (name[unwind.personality_index]);
4047 fix_new (frag_now, where, 0, pr, 0, 1, BFD_RELOC_NONE);
c19d1205 4048 seg_info (now_seg)->tc_segment_info_data.marked_pr_dependency
940b5ce0 4049 |= 1 << unwind.personality_index;
c19d1205 4050 }
f02232aa 4051
c19d1205
ZW
4052 if (val)
4053 /* Inline exception table entry. */
4054 md_number_to_chars (ptr + 4, val, 4);
4055 else
4056 /* Self relative offset of the table entry. */
4057 fix_new (frag_now, where + 4, 4, unwind.table_entry, 0, 1,
4058 BFD_RELOC_ARM_PREL31);
f02232aa 4059
c19d1205
ZW
4060 /* Restore the original section. */
4061 subseg_set (unwind.saved_seg, unwind.saved_subseg);
921e5f0a
PB
4062
4063 unwind.proc_start = NULL;
c19d1205 4064}
f02232aa 4065
f02232aa 4066
c19d1205 4067/* Parse an unwind_cantunwind directive. */
b99bd4ef 4068
c19d1205
ZW
4069static void
4070s_arm_unwind_cantunwind (int ignored ATTRIBUTE_UNUSED)
4071{
4072 demand_empty_rest_of_line ();
921e5f0a 4073 if (!unwind.proc_start)
c921be7d 4074 as_bad (MISSING_FNSTART);
921e5f0a 4075
c19d1205
ZW
4076 if (unwind.personality_routine || unwind.personality_index != -1)
4077 as_bad (_("personality routine specified for cantunwind frame"));
b99bd4ef 4078
c19d1205
ZW
4079 unwind.personality_index = -2;
4080}
b99bd4ef 4081
b99bd4ef 4082
c19d1205 4083/* Parse a personalityindex directive. */
b99bd4ef 4084
c19d1205
ZW
4085static void
4086s_arm_unwind_personalityindex (int ignored ATTRIBUTE_UNUSED)
4087{
4088 expressionS exp;
b99bd4ef 4089
921e5f0a 4090 if (!unwind.proc_start)
c921be7d 4091 as_bad (MISSING_FNSTART);
921e5f0a 4092
c19d1205
ZW
4093 if (unwind.personality_routine || unwind.personality_index != -1)
4094 as_bad (_("duplicate .personalityindex directive"));
b99bd4ef 4095
c19d1205 4096 expression (&exp);
b99bd4ef 4097
c19d1205
ZW
4098 if (exp.X_op != O_constant
4099 || exp.X_add_number < 0 || exp.X_add_number > 15)
b99bd4ef 4100 {
c19d1205
ZW
4101 as_bad (_("bad personality routine number"));
4102 ignore_rest_of_line ();
4103 return;
b99bd4ef
NC
4104 }
4105
c19d1205 4106 unwind.personality_index = exp.X_add_number;
b99bd4ef 4107
c19d1205
ZW
4108 demand_empty_rest_of_line ();
4109}
e16bb312 4110
e16bb312 4111
c19d1205 4112/* Parse a personality directive. */
e16bb312 4113
c19d1205
ZW
4114static void
4115s_arm_unwind_personality (int ignored ATTRIBUTE_UNUSED)
4116{
4117 char *name, *p, c;
a737bd4d 4118
921e5f0a 4119 if (!unwind.proc_start)
c921be7d 4120 as_bad (MISSING_FNSTART);
921e5f0a 4121
c19d1205
ZW
4122 if (unwind.personality_routine || unwind.personality_index != -1)
4123 as_bad (_("duplicate .personality directive"));
a737bd4d 4124
d02603dc 4125 c = get_symbol_name (& name);
c19d1205 4126 p = input_line_pointer;
d02603dc
NC
4127 if (c == '"')
4128 ++ input_line_pointer;
c19d1205
ZW
4129 unwind.personality_routine = symbol_find_or_make (name);
4130 *p = c;
4131 demand_empty_rest_of_line ();
4132}
e16bb312 4133
e16bb312 4134
c19d1205 4135/* Parse a directive saving core registers. */
e16bb312 4136
c19d1205
ZW
4137static void
4138s_arm_unwind_save_core (void)
e16bb312 4139{
c19d1205
ZW
4140 valueT op;
4141 long range;
4142 int n;
e16bb312 4143
4b5a202f 4144 range = parse_reg_list (&input_line_pointer, REGLIST_RN);
c19d1205 4145 if (range == FAIL)
e16bb312 4146 {
c19d1205
ZW
4147 as_bad (_("expected register list"));
4148 ignore_rest_of_line ();
4149 return;
4150 }
e16bb312 4151
c19d1205 4152 demand_empty_rest_of_line ();
e16bb312 4153
c19d1205
ZW
4154 /* Turn .unwind_movsp ip followed by .unwind_save {..., ip, ...}
4155 into .unwind_save {..., sp...}. We aren't bothered about the value of
4156 ip because it is clobbered by calls. */
4157 if (unwind.sp_restored && unwind.fp_reg == 12
4158 && (range & 0x3000) == 0x1000)
4159 {
4160 unwind.opcode_count--;
4161 unwind.sp_restored = 0;
4162 range = (range | 0x2000) & ~0x1000;
4163 unwind.pending_offset = 0;
4164 }
e16bb312 4165
01ae4198
DJ
4166 /* Pop r4-r15. */
4167 if (range & 0xfff0)
c19d1205 4168 {
01ae4198
DJ
4169 /* See if we can use the short opcodes. These pop a block of up to 8
4170 registers starting with r4, plus maybe r14. */
4171 for (n = 0; n < 8; n++)
4172 {
4173 /* Break at the first non-saved register. */
4174 if ((range & (1 << (n + 4))) == 0)
4175 break;
4176 }
4177 /* See if there are any other bits set. */
4178 if (n == 0 || (range & (0xfff0 << n) & 0xbff0) != 0)
4179 {
4180 /* Use the long form. */
4181 op = 0x8000 | ((range >> 4) & 0xfff);
4182 add_unwind_opcode (op, 2);
4183 }
0dd132b6 4184 else
01ae4198
DJ
4185 {
4186 /* Use the short form. */
4187 if (range & 0x4000)
4188 op = 0xa8; /* Pop r14. */
4189 else
4190 op = 0xa0; /* Do not pop r14. */
4191 op |= (n - 1);
4192 add_unwind_opcode (op, 1);
4193 }
c19d1205 4194 }
0dd132b6 4195
c19d1205
ZW
4196 /* Pop r0-r3. */
4197 if (range & 0xf)
4198 {
4199 op = 0xb100 | (range & 0xf);
4200 add_unwind_opcode (op, 2);
0dd132b6
NC
4201 }
4202
c19d1205
ZW
4203 /* Record the number of bytes pushed. */
4204 for (n = 0; n < 16; n++)
4205 {
4206 if (range & (1 << n))
4207 unwind.frame_size += 4;
4208 }
0dd132b6
NC
4209}
4210
c19d1205
ZW
4211
4212/* Parse a directive saving FPA registers. */
b99bd4ef
NC
4213
4214static void
c19d1205 4215s_arm_unwind_save_fpa (int reg)
b99bd4ef 4216{
c19d1205
ZW
4217 expressionS exp;
4218 int num_regs;
4219 valueT op;
b99bd4ef 4220
c19d1205
ZW
4221 /* Get Number of registers to transfer. */
4222 if (skip_past_comma (&input_line_pointer) != FAIL)
4223 expression (&exp);
4224 else
4225 exp.X_op = O_illegal;
b99bd4ef 4226
c19d1205 4227 if (exp.X_op != O_constant)
b99bd4ef 4228 {
c19d1205
ZW
4229 as_bad (_("expected , <constant>"));
4230 ignore_rest_of_line ();
b99bd4ef
NC
4231 return;
4232 }
4233
c19d1205
ZW
4234 num_regs = exp.X_add_number;
4235
4236 if (num_regs < 1 || num_regs > 4)
b99bd4ef 4237 {
c19d1205
ZW
4238 as_bad (_("number of registers must be in the range [1:4]"));
4239 ignore_rest_of_line ();
b99bd4ef
NC
4240 return;
4241 }
4242
c19d1205 4243 demand_empty_rest_of_line ();
b99bd4ef 4244
c19d1205
ZW
4245 if (reg == 4)
4246 {
4247 /* Short form. */
4248 op = 0xb4 | (num_regs - 1);
4249 add_unwind_opcode (op, 1);
4250 }
b99bd4ef
NC
4251 else
4252 {
c19d1205
ZW
4253 /* Long form. */
4254 op = 0xc800 | (reg << 4) | (num_regs - 1);
4255 add_unwind_opcode (op, 2);
b99bd4ef 4256 }
c19d1205 4257 unwind.frame_size += num_regs * 12;
b99bd4ef
NC
4258}
4259
c19d1205 4260
fa073d69
MS
4261/* Parse a directive saving VFP registers for ARMv6 and above. */
4262
4263static void
4264s_arm_unwind_save_vfp_armv6 (void)
4265{
4266 int count;
4267 unsigned int start;
4268 valueT op;
4269 int num_vfpv3_regs = 0;
4270 int num_regs_below_16;
efd6b359 4271 bfd_boolean partial_match;
fa073d69 4272
efd6b359
AV
4273 count = parse_vfp_reg_list (&input_line_pointer, &start, REGLIST_VFP_D,
4274 &partial_match);
fa073d69
MS
4275 if (count == FAIL)
4276 {
4277 as_bad (_("expected register list"));
4278 ignore_rest_of_line ();
4279 return;
4280 }
4281
4282 demand_empty_rest_of_line ();
4283
4284 /* We always generate FSTMD/FLDMD-style unwinding opcodes (rather
4285 than FSTMX/FLDMX-style ones). */
4286
4287 /* Generate opcode for (VFPv3) registers numbered in the range 16 .. 31. */
4288 if (start >= 16)
4289 num_vfpv3_regs = count;
4290 else if (start + count > 16)
4291 num_vfpv3_regs = start + count - 16;
4292
4293 if (num_vfpv3_regs > 0)
4294 {
4295 int start_offset = start > 16 ? start - 16 : 0;
4296 op = 0xc800 | (start_offset << 4) | (num_vfpv3_regs - 1);
4297 add_unwind_opcode (op, 2);
4298 }
4299
4300 /* Generate opcode for registers numbered in the range 0 .. 15. */
4301 num_regs_below_16 = num_vfpv3_regs > 0 ? 16 - (int) start : count;
9c2799c2 4302 gas_assert (num_regs_below_16 + num_vfpv3_regs == count);
fa073d69
MS
4303 if (num_regs_below_16 > 0)
4304 {
4305 op = 0xc900 | (start << 4) | (num_regs_below_16 - 1);
4306 add_unwind_opcode (op, 2);
4307 }
4308
4309 unwind.frame_size += count * 8;
4310}
4311
4312
4313/* Parse a directive saving VFP registers for pre-ARMv6. */
b99bd4ef
NC
4314
4315static void
c19d1205 4316s_arm_unwind_save_vfp (void)
b99bd4ef 4317{
c19d1205 4318 int count;
ca3f61f7 4319 unsigned int reg;
c19d1205 4320 valueT op;
efd6b359 4321 bfd_boolean partial_match;
b99bd4ef 4322
efd6b359
AV
4323 count = parse_vfp_reg_list (&input_line_pointer, &reg, REGLIST_VFP_D,
4324 &partial_match);
c19d1205 4325 if (count == FAIL)
b99bd4ef 4326 {
c19d1205
ZW
4327 as_bad (_("expected register list"));
4328 ignore_rest_of_line ();
b99bd4ef
NC
4329 return;
4330 }
4331
c19d1205 4332 demand_empty_rest_of_line ();
b99bd4ef 4333
c19d1205 4334 if (reg == 8)
b99bd4ef 4335 {
c19d1205
ZW
4336 /* Short form. */
4337 op = 0xb8 | (count - 1);
4338 add_unwind_opcode (op, 1);
b99bd4ef 4339 }
c19d1205 4340 else
b99bd4ef 4341 {
c19d1205
ZW
4342 /* Long form. */
4343 op = 0xb300 | (reg << 4) | (count - 1);
4344 add_unwind_opcode (op, 2);
b99bd4ef 4345 }
c19d1205
ZW
4346 unwind.frame_size += count * 8 + 4;
4347}
b99bd4ef 4348
b99bd4ef 4349
c19d1205
ZW
4350/* Parse a directive saving iWMMXt data registers. */
4351
4352static void
4353s_arm_unwind_save_mmxwr (void)
4354{
4355 int reg;
4356 int hi_reg;
4357 int i;
4358 unsigned mask = 0;
4359 valueT op;
b99bd4ef 4360
c19d1205
ZW
4361 if (*input_line_pointer == '{')
4362 input_line_pointer++;
b99bd4ef 4363
c19d1205 4364 do
b99bd4ef 4365 {
dcbf9037 4366 reg = arm_reg_parse (&input_line_pointer, REG_TYPE_MMXWR);
b99bd4ef 4367
c19d1205 4368 if (reg == FAIL)
b99bd4ef 4369 {
9b7132d3 4370 as_bad ("%s", _(reg_expected_msgs[REG_TYPE_MMXWR]));
c19d1205 4371 goto error;
b99bd4ef
NC
4372 }
4373
c19d1205
ZW
4374 if (mask >> reg)
4375 as_tsktsk (_("register list not in ascending order"));
4376 mask |= 1 << reg;
b99bd4ef 4377
c19d1205
ZW
4378 if (*input_line_pointer == '-')
4379 {
4380 input_line_pointer++;
dcbf9037 4381 hi_reg = arm_reg_parse (&input_line_pointer, REG_TYPE_MMXWR);
c19d1205
ZW
4382 if (hi_reg == FAIL)
4383 {
9b7132d3 4384 as_bad ("%s", _(reg_expected_msgs[REG_TYPE_MMXWR]));
c19d1205
ZW
4385 goto error;
4386 }
4387 else if (reg >= hi_reg)
4388 {
4389 as_bad (_("bad register range"));
4390 goto error;
4391 }
4392 for (; reg < hi_reg; reg++)
4393 mask |= 1 << reg;
4394 }
4395 }
4396 while (skip_past_comma (&input_line_pointer) != FAIL);
b99bd4ef 4397
d996d970 4398 skip_past_char (&input_line_pointer, '}');
b99bd4ef 4399
c19d1205 4400 demand_empty_rest_of_line ();
b99bd4ef 4401
708587a4 4402 /* Generate any deferred opcodes because we're going to be looking at
c19d1205
ZW
4403 the list. */
4404 flush_pending_unwind ();
b99bd4ef 4405
c19d1205 4406 for (i = 0; i < 16; i++)
b99bd4ef 4407 {
c19d1205
ZW
4408 if (mask & (1 << i))
4409 unwind.frame_size += 8;
b99bd4ef
NC
4410 }
4411
c19d1205
ZW
4412 /* Attempt to combine with a previous opcode. We do this because gcc
4413 likes to output separate unwind directives for a single block of
4414 registers. */
4415 if (unwind.opcode_count > 0)
b99bd4ef 4416 {
c19d1205
ZW
4417 i = unwind.opcodes[unwind.opcode_count - 1];
4418 if ((i & 0xf8) == 0xc0)
4419 {
4420 i &= 7;
4421 /* Only merge if the blocks are contiguous. */
4422 if (i < 6)
4423 {
4424 if ((mask & 0xfe00) == (1 << 9))
4425 {
4426 mask |= ((1 << (i + 11)) - 1) & 0xfc00;
4427 unwind.opcode_count--;
4428 }
4429 }
4430 else if (i == 6 && unwind.opcode_count >= 2)
4431 {
4432 i = unwind.opcodes[unwind.opcode_count - 2];
4433 reg = i >> 4;
4434 i &= 0xf;
b99bd4ef 4435
c19d1205
ZW
4436 op = 0xffff << (reg - 1);
4437 if (reg > 0
87a1fd79 4438 && ((mask & op) == (1u << (reg - 1))))
c19d1205
ZW
4439 {
4440 op = (1 << (reg + i + 1)) - 1;
4441 op &= ~((1 << reg) - 1);
4442 mask |= op;
4443 unwind.opcode_count -= 2;
4444 }
4445 }
4446 }
b99bd4ef
NC
4447 }
4448
c19d1205
ZW
4449 hi_reg = 15;
4450 /* We want to generate opcodes in the order the registers have been
4451 saved, ie. descending order. */
4452 for (reg = 15; reg >= -1; reg--)
b99bd4ef 4453 {
c19d1205
ZW
4454 /* Save registers in blocks. */
4455 if (reg < 0
4456 || !(mask & (1 << reg)))
4457 {
4458 /* We found an unsaved reg. Generate opcodes to save the
5f4273c7 4459 preceding block. */
c19d1205
ZW
4460 if (reg != hi_reg)
4461 {
4462 if (reg == 9)
4463 {
4464 /* Short form. */
4465 op = 0xc0 | (hi_reg - 10);
4466 add_unwind_opcode (op, 1);
4467 }
4468 else
4469 {
4470 /* Long form. */
4471 op = 0xc600 | ((reg + 1) << 4) | ((hi_reg - reg) - 1);
4472 add_unwind_opcode (op, 2);
4473 }
4474 }
4475 hi_reg = reg - 1;
4476 }
b99bd4ef
NC
4477 }
4478
c19d1205
ZW
4479 return;
4480error:
4481 ignore_rest_of_line ();
b99bd4ef
NC
4482}
4483
4484static void
c19d1205 4485s_arm_unwind_save_mmxwcg (void)
b99bd4ef 4486{
c19d1205
ZW
4487 int reg;
4488 int hi_reg;
4489 unsigned mask = 0;
4490 valueT op;
b99bd4ef 4491
c19d1205
ZW
4492 if (*input_line_pointer == '{')
4493 input_line_pointer++;
b99bd4ef 4494
477330fc
RM
4495 skip_whitespace (input_line_pointer);
4496
c19d1205 4497 do
b99bd4ef 4498 {
dcbf9037 4499 reg = arm_reg_parse (&input_line_pointer, REG_TYPE_MMXWCG);
b99bd4ef 4500
c19d1205
ZW
4501 if (reg == FAIL)
4502 {
9b7132d3 4503 as_bad ("%s", _(reg_expected_msgs[REG_TYPE_MMXWCG]));
c19d1205
ZW
4504 goto error;
4505 }
b99bd4ef 4506
c19d1205
ZW
4507 reg -= 8;
4508 if (mask >> reg)
4509 as_tsktsk (_("register list not in ascending order"));
4510 mask |= 1 << reg;
b99bd4ef 4511
c19d1205
ZW
4512 if (*input_line_pointer == '-')
4513 {
4514 input_line_pointer++;
dcbf9037 4515 hi_reg = arm_reg_parse (&input_line_pointer, REG_TYPE_MMXWCG);
c19d1205
ZW
4516 if (hi_reg == FAIL)
4517 {
9b7132d3 4518 as_bad ("%s", _(reg_expected_msgs[REG_TYPE_MMXWCG]));
c19d1205
ZW
4519 goto error;
4520 }
4521 else if (reg >= hi_reg)
4522 {
4523 as_bad (_("bad register range"));
4524 goto error;
4525 }
4526 for (; reg < hi_reg; reg++)
4527 mask |= 1 << reg;
4528 }
b99bd4ef 4529 }
c19d1205 4530 while (skip_past_comma (&input_line_pointer) != FAIL);
b99bd4ef 4531
d996d970 4532 skip_past_char (&input_line_pointer, '}');
b99bd4ef 4533
c19d1205
ZW
4534 demand_empty_rest_of_line ();
4535
708587a4 4536 /* Generate any deferred opcodes because we're going to be looking at
c19d1205
ZW
4537 the list. */
4538 flush_pending_unwind ();
b99bd4ef 4539
c19d1205 4540 for (reg = 0; reg < 16; reg++)
b99bd4ef 4541 {
c19d1205
ZW
4542 if (mask & (1 << reg))
4543 unwind.frame_size += 4;
b99bd4ef 4544 }
c19d1205
ZW
4545 op = 0xc700 | mask;
4546 add_unwind_opcode (op, 2);
4547 return;
4548error:
4549 ignore_rest_of_line ();
b99bd4ef
NC
4550}
4551
c19d1205 4552
fa073d69
MS
4553/* Parse an unwind_save directive.
4554 If the argument is non-zero, this is a .vsave directive. */
c19d1205 4555
b99bd4ef 4556static void
fa073d69 4557s_arm_unwind_save (int arch_v6)
b99bd4ef 4558{
c19d1205
ZW
4559 char *peek;
4560 struct reg_entry *reg;
4561 bfd_boolean had_brace = FALSE;
b99bd4ef 4562
921e5f0a 4563 if (!unwind.proc_start)
c921be7d 4564 as_bad (MISSING_FNSTART);
921e5f0a 4565
c19d1205
ZW
4566 /* Figure out what sort of save we have. */
4567 peek = input_line_pointer;
b99bd4ef 4568
c19d1205 4569 if (*peek == '{')
b99bd4ef 4570 {
c19d1205
ZW
4571 had_brace = TRUE;
4572 peek++;
b99bd4ef
NC
4573 }
4574
c19d1205 4575 reg = arm_reg_parse_multi (&peek);
b99bd4ef 4576
c19d1205 4577 if (!reg)
b99bd4ef 4578 {
c19d1205
ZW
4579 as_bad (_("register expected"));
4580 ignore_rest_of_line ();
b99bd4ef
NC
4581 return;
4582 }
4583
c19d1205 4584 switch (reg->type)
b99bd4ef 4585 {
c19d1205
ZW
4586 case REG_TYPE_FN:
4587 if (had_brace)
4588 {
4589 as_bad (_("FPA .unwind_save does not take a register list"));
4590 ignore_rest_of_line ();
4591 return;
4592 }
93ac2687 4593 input_line_pointer = peek;
c19d1205 4594 s_arm_unwind_save_fpa (reg->number);
b99bd4ef 4595 return;
c19d1205 4596
1f5afe1c
NC
4597 case REG_TYPE_RN:
4598 s_arm_unwind_save_core ();
4599 return;
4600
fa073d69
MS
4601 case REG_TYPE_VFD:
4602 if (arch_v6)
477330fc 4603 s_arm_unwind_save_vfp_armv6 ();
fa073d69 4604 else
477330fc 4605 s_arm_unwind_save_vfp ();
fa073d69 4606 return;
1f5afe1c
NC
4607
4608 case REG_TYPE_MMXWR:
4609 s_arm_unwind_save_mmxwr ();
4610 return;
4611
4612 case REG_TYPE_MMXWCG:
4613 s_arm_unwind_save_mmxwcg ();
4614 return;
c19d1205
ZW
4615
4616 default:
4617 as_bad (_(".unwind_save does not support this kind of register"));
4618 ignore_rest_of_line ();
b99bd4ef 4619 }
c19d1205 4620}
b99bd4ef 4621
b99bd4ef 4622
c19d1205
ZW
4623/* Parse an unwind_movsp directive. */
4624
4625static void
4626s_arm_unwind_movsp (int ignored ATTRIBUTE_UNUSED)
4627{
4628 int reg;
4629 valueT op;
4fa3602b 4630 int offset;
c19d1205 4631
921e5f0a 4632 if (!unwind.proc_start)
c921be7d 4633 as_bad (MISSING_FNSTART);
921e5f0a 4634
dcbf9037 4635 reg = arm_reg_parse (&input_line_pointer, REG_TYPE_RN);
c19d1205 4636 if (reg == FAIL)
b99bd4ef 4637 {
9b7132d3 4638 as_bad ("%s", _(reg_expected_msgs[REG_TYPE_RN]));
c19d1205 4639 ignore_rest_of_line ();
b99bd4ef
NC
4640 return;
4641 }
4fa3602b
PB
4642
4643 /* Optional constant. */
4644 if (skip_past_comma (&input_line_pointer) != FAIL)
4645 {
4646 if (immediate_for_directive (&offset) == FAIL)
4647 return;
4648 }
4649 else
4650 offset = 0;
4651
c19d1205 4652 demand_empty_rest_of_line ();
b99bd4ef 4653
c19d1205 4654 if (reg == REG_SP || reg == REG_PC)
b99bd4ef 4655 {
c19d1205 4656 as_bad (_("SP and PC not permitted in .unwind_movsp directive"));
b99bd4ef
NC
4657 return;
4658 }
4659
c19d1205
ZW
4660 if (unwind.fp_reg != REG_SP)
4661 as_bad (_("unexpected .unwind_movsp directive"));
b99bd4ef 4662
c19d1205
ZW
4663 /* Generate opcode to restore the value. */
4664 op = 0x90 | reg;
4665 add_unwind_opcode (op, 1);
4666
4667 /* Record the information for later. */
4668 unwind.fp_reg = reg;
4fa3602b 4669 unwind.fp_offset = unwind.frame_size - offset;
c19d1205 4670 unwind.sp_restored = 1;
b05fe5cf
ZW
4671}
4672
c19d1205
ZW
4673/* Parse an unwind_pad directive. */
4674
b05fe5cf 4675static void
c19d1205 4676s_arm_unwind_pad (int ignored ATTRIBUTE_UNUSED)
b05fe5cf 4677{
c19d1205 4678 int offset;
b05fe5cf 4679
921e5f0a 4680 if (!unwind.proc_start)
c921be7d 4681 as_bad (MISSING_FNSTART);
921e5f0a 4682
c19d1205
ZW
4683 if (immediate_for_directive (&offset) == FAIL)
4684 return;
b99bd4ef 4685
c19d1205
ZW
4686 if (offset & 3)
4687 {
4688 as_bad (_("stack increment must be multiple of 4"));
4689 ignore_rest_of_line ();
4690 return;
4691 }
b99bd4ef 4692
c19d1205
ZW
4693 /* Don't generate any opcodes, just record the details for later. */
4694 unwind.frame_size += offset;
4695 unwind.pending_offset += offset;
4696
4697 demand_empty_rest_of_line ();
4698}
4699
4700/* Parse an unwind_setfp directive. */
4701
4702static void
4703s_arm_unwind_setfp (int ignored ATTRIBUTE_UNUSED)
b99bd4ef 4704{
c19d1205
ZW
4705 int sp_reg;
4706 int fp_reg;
4707 int offset;
4708
921e5f0a 4709 if (!unwind.proc_start)
c921be7d 4710 as_bad (MISSING_FNSTART);
921e5f0a 4711
dcbf9037 4712 fp_reg = arm_reg_parse (&input_line_pointer, REG_TYPE_RN);
c19d1205
ZW
4713 if (skip_past_comma (&input_line_pointer) == FAIL)
4714 sp_reg = FAIL;
4715 else
dcbf9037 4716 sp_reg = arm_reg_parse (&input_line_pointer, REG_TYPE_RN);
b99bd4ef 4717
c19d1205
ZW
4718 if (fp_reg == FAIL || sp_reg == FAIL)
4719 {
4720 as_bad (_("expected <reg>, <reg>"));
4721 ignore_rest_of_line ();
4722 return;
4723 }
b99bd4ef 4724
c19d1205
ZW
4725 /* Optional constant. */
4726 if (skip_past_comma (&input_line_pointer) != FAIL)
4727 {
4728 if (immediate_for_directive (&offset) == FAIL)
4729 return;
4730 }
4731 else
4732 offset = 0;
a737bd4d 4733
c19d1205 4734 demand_empty_rest_of_line ();
a737bd4d 4735
fdfde340 4736 if (sp_reg != REG_SP && sp_reg != unwind.fp_reg)
a737bd4d 4737 {
c19d1205
ZW
4738 as_bad (_("register must be either sp or set by a previous"
4739 "unwind_movsp directive"));
4740 return;
a737bd4d
NC
4741 }
4742
c19d1205
ZW
4743 /* Don't generate any opcodes, just record the information for later. */
4744 unwind.fp_reg = fp_reg;
4745 unwind.fp_used = 1;
fdfde340 4746 if (sp_reg == REG_SP)
c19d1205
ZW
4747 unwind.fp_offset = unwind.frame_size - offset;
4748 else
4749 unwind.fp_offset -= offset;
a737bd4d
NC
4750}
4751
c19d1205
ZW
4752/* Parse an unwind_raw directive. */
4753
4754static void
4755s_arm_unwind_raw (int ignored ATTRIBUTE_UNUSED)
a737bd4d 4756{
c19d1205 4757 expressionS exp;
708587a4 4758 /* This is an arbitrary limit. */
c19d1205
ZW
4759 unsigned char op[16];
4760 int count;
a737bd4d 4761
921e5f0a 4762 if (!unwind.proc_start)
c921be7d 4763 as_bad (MISSING_FNSTART);
921e5f0a 4764
c19d1205
ZW
4765 expression (&exp);
4766 if (exp.X_op == O_constant
4767 && skip_past_comma (&input_line_pointer) != FAIL)
a737bd4d 4768 {
c19d1205
ZW
4769 unwind.frame_size += exp.X_add_number;
4770 expression (&exp);
4771 }
4772 else
4773 exp.X_op = O_illegal;
a737bd4d 4774
c19d1205
ZW
4775 if (exp.X_op != O_constant)
4776 {
4777 as_bad (_("expected <offset>, <opcode>"));
4778 ignore_rest_of_line ();
4779 return;
4780 }
a737bd4d 4781
c19d1205 4782 count = 0;
a737bd4d 4783
c19d1205
ZW
4784 /* Parse the opcode. */
4785 for (;;)
4786 {
4787 if (count >= 16)
4788 {
4789 as_bad (_("unwind opcode too long"));
4790 ignore_rest_of_line ();
a737bd4d 4791 }
c19d1205 4792 if (exp.X_op != O_constant || exp.X_add_number & ~0xff)
a737bd4d 4793 {
c19d1205
ZW
4794 as_bad (_("invalid unwind opcode"));
4795 ignore_rest_of_line ();
4796 return;
a737bd4d 4797 }
c19d1205 4798 op[count++] = exp.X_add_number;
a737bd4d 4799
c19d1205
ZW
4800 /* Parse the next byte. */
4801 if (skip_past_comma (&input_line_pointer) == FAIL)
4802 break;
a737bd4d 4803
c19d1205
ZW
4804 expression (&exp);
4805 }
b99bd4ef 4806
c19d1205
ZW
4807 /* Add the opcode bytes in reverse order. */
4808 while (count--)
4809 add_unwind_opcode (op[count], 1);
b99bd4ef 4810
c19d1205 4811 demand_empty_rest_of_line ();
b99bd4ef 4812}
ee065d83
PB
4813
4814
4815/* Parse a .eabi_attribute directive. */
4816
4817static void
4818s_arm_eabi_attribute (int ignored ATTRIBUTE_UNUSED)
4819{
0420f52b 4820 int tag = obj_elf_vendor_attribute (OBJ_ATTR_PROC);
ee3c0378 4821
3076e594 4822 if (tag >= 0 && tag < NUM_KNOWN_OBJ_ATTRIBUTES)
ee3c0378 4823 attributes_set_explicitly[tag] = 1;
ee065d83
PB
4824}
4825
0855e32b
NS
4826/* Emit a tls fix for the symbol. */
4827
4828static void
4829s_arm_tls_descseq (int ignored ATTRIBUTE_UNUSED)
4830{
4831 char *p;
4832 expressionS exp;
4833#ifdef md_flush_pending_output
4834 md_flush_pending_output ();
4835#endif
4836
4837#ifdef md_cons_align
4838 md_cons_align (4);
4839#endif
4840
4841 /* Since we're just labelling the code, there's no need to define a
4842 mapping symbol. */
4843 expression (&exp);
4844 p = obstack_next_free (&frchain_now->frch_obstack);
4845 fix_new_arm (frag_now, p - frag_now->fr_literal, 4, &exp, 0,
4846 thumb_mode ? BFD_RELOC_ARM_THM_TLS_DESCSEQ
4847 : BFD_RELOC_ARM_TLS_DESCSEQ);
4848}
cdf9ccec 4849#endif /* OBJ_ELF */
0855e32b 4850
ee065d83 4851static void s_arm_arch (int);
7a1d4c38 4852static void s_arm_object_arch (int);
ee065d83
PB
4853static void s_arm_cpu (int);
4854static void s_arm_fpu (int);
69133863 4855static void s_arm_arch_extension (int);
b99bd4ef 4856
f0927246
NC
4857#ifdef TE_PE
4858
4859static void
5f4273c7 4860pe_directive_secrel (int dummy ATTRIBUTE_UNUSED)
f0927246
NC
4861{
4862 expressionS exp;
4863
4864 do
4865 {
4866 expression (&exp);
4867 if (exp.X_op == O_symbol)
4868 exp.X_op = O_secrel;
4869
4870 emit_expr (&exp, 4);
4871 }
4872 while (*input_line_pointer++ == ',');
4873
4874 input_line_pointer--;
4875 demand_empty_rest_of_line ();
4876}
4877#endif /* TE_PE */
4878
c19d1205
ZW
4879/* This table describes all the machine specific pseudo-ops the assembler
4880 has to support. The fields are:
4881 pseudo-op name without dot
4882 function to call to execute this pseudo-op
4883 Integer arg to pass to the function. */
b99bd4ef 4884
c19d1205 4885const pseudo_typeS md_pseudo_table[] =
b99bd4ef 4886{
c19d1205
ZW
4887 /* Never called because '.req' does not start a line. */
4888 { "req", s_req, 0 },
dcbf9037
JB
4889 /* Following two are likewise never called. */
4890 { "dn", s_dn, 0 },
4891 { "qn", s_qn, 0 },
c19d1205
ZW
4892 { "unreq", s_unreq, 0 },
4893 { "bss", s_bss, 0 },
db2ed2e0 4894 { "align", s_align_ptwo, 2 },
c19d1205
ZW
4895 { "arm", s_arm, 0 },
4896 { "thumb", s_thumb, 0 },
4897 { "code", s_code, 0 },
4898 { "force_thumb", s_force_thumb, 0 },
4899 { "thumb_func", s_thumb_func, 0 },
4900 { "thumb_set", s_thumb_set, 0 },
4901 { "even", s_even, 0 },
4902 { "ltorg", s_ltorg, 0 },
4903 { "pool", s_ltorg, 0 },
4904 { "syntax", s_syntax, 0 },
8463be01
PB
4905 { "cpu", s_arm_cpu, 0 },
4906 { "arch", s_arm_arch, 0 },
7a1d4c38 4907 { "object_arch", s_arm_object_arch, 0 },
8463be01 4908 { "fpu", s_arm_fpu, 0 },
69133863 4909 { "arch_extension", s_arm_arch_extension, 0 },
c19d1205 4910#ifdef OBJ_ELF
c921be7d
NC
4911 { "word", s_arm_elf_cons, 4 },
4912 { "long", s_arm_elf_cons, 4 },
4913 { "inst.n", s_arm_elf_inst, 2 },
4914 { "inst.w", s_arm_elf_inst, 4 },
4915 { "inst", s_arm_elf_inst, 0 },
4916 { "rel31", s_arm_rel31, 0 },
c19d1205
ZW
4917 { "fnstart", s_arm_unwind_fnstart, 0 },
4918 { "fnend", s_arm_unwind_fnend, 0 },
4919 { "cantunwind", s_arm_unwind_cantunwind, 0 },
4920 { "personality", s_arm_unwind_personality, 0 },
4921 { "personalityindex", s_arm_unwind_personalityindex, 0 },
4922 { "handlerdata", s_arm_unwind_handlerdata, 0 },
4923 { "save", s_arm_unwind_save, 0 },
fa073d69 4924 { "vsave", s_arm_unwind_save, 1 },
c19d1205
ZW
4925 { "movsp", s_arm_unwind_movsp, 0 },
4926 { "pad", s_arm_unwind_pad, 0 },
4927 { "setfp", s_arm_unwind_setfp, 0 },
4928 { "unwind_raw", s_arm_unwind_raw, 0 },
ee065d83 4929 { "eabi_attribute", s_arm_eabi_attribute, 0 },
0855e32b 4930 { "tlsdescseq", s_arm_tls_descseq, 0 },
c19d1205
ZW
4931#else
4932 { "word", cons, 4},
f0927246
NC
4933
4934 /* These are used for dwarf. */
4935 {"2byte", cons, 2},
4936 {"4byte", cons, 4},
4937 {"8byte", cons, 8},
4938 /* These are used for dwarf2. */
68d20676 4939 { "file", dwarf2_directive_file, 0 },
f0927246
NC
4940 { "loc", dwarf2_directive_loc, 0 },
4941 { "loc_mark_labels", dwarf2_directive_loc_mark_labels, 0 },
c19d1205
ZW
4942#endif
4943 { "extend", float_cons, 'x' },
4944 { "ldouble", float_cons, 'x' },
4945 { "packed", float_cons, 'p' },
f0927246
NC
4946#ifdef TE_PE
4947 {"secrel32", pe_directive_secrel, 0},
4948#endif
2e6976a8
DG
4949
4950 /* These are for compatibility with CodeComposer Studio. */
4951 {"ref", s_ccs_ref, 0},
4952 {"def", s_ccs_def, 0},
4953 {"asmfunc", s_ccs_asmfunc, 0},
4954 {"endasmfunc", s_ccs_endasmfunc, 0},
4955
c19d1205
ZW
4956 { 0, 0, 0 }
4957};
4958\f
4959/* Parser functions used exclusively in instruction operands. */
b99bd4ef 4960
c19d1205
ZW
4961/* Generic immediate-value read function for use in insn parsing.
4962 STR points to the beginning of the immediate (the leading #);
4963 VAL receives the value; if the value is outside [MIN, MAX]
4964 issue an error. PREFIX_OPT is true if the immediate prefix is
4965 optional. */
b99bd4ef 4966
c19d1205
ZW
4967static int
4968parse_immediate (char **str, int *val, int min, int max,
4969 bfd_boolean prefix_opt)
4970{
4971 expressionS exp;
0198d5e6 4972
c19d1205
ZW
4973 my_get_expression (&exp, str, prefix_opt ? GE_OPT_PREFIX : GE_IMM_PREFIX);
4974 if (exp.X_op != O_constant)
b99bd4ef 4975 {
c19d1205
ZW
4976 inst.error = _("constant expression required");
4977 return FAIL;
4978 }
b99bd4ef 4979
c19d1205
ZW
4980 if (exp.X_add_number < min || exp.X_add_number > max)
4981 {
4982 inst.error = _("immediate value out of range");
4983 return FAIL;
4984 }
b99bd4ef 4985
c19d1205
ZW
4986 *val = exp.X_add_number;
4987 return SUCCESS;
4988}
b99bd4ef 4989
5287ad62 4990/* Less-generic immediate-value read function with the possibility of loading a
036dc3f7 4991 big (64-bit) immediate, as required by Neon VMOV, VMVN and logic immediate
5287ad62
JB
4992 instructions. Puts the result directly in inst.operands[i]. */
4993
4994static int
8335d6aa
JW
4995parse_big_immediate (char **str, int i, expressionS *in_exp,
4996 bfd_boolean allow_symbol_p)
5287ad62
JB
4997{
4998 expressionS exp;
8335d6aa 4999 expressionS *exp_p = in_exp ? in_exp : &exp;
5287ad62
JB
5000 char *ptr = *str;
5001
8335d6aa 5002 my_get_expression (exp_p, &ptr, GE_OPT_PREFIX_BIG);
5287ad62 5003
8335d6aa 5004 if (exp_p->X_op == O_constant)
036dc3f7 5005 {
8335d6aa 5006 inst.operands[i].imm = exp_p->X_add_number & 0xffffffff;
036dc3f7
PB
5007 /* If we're on a 64-bit host, then a 64-bit number can be returned using
5008 O_constant. We have to be careful not to break compilation for
5009 32-bit X_add_number, though. */
8335d6aa 5010 if ((exp_p->X_add_number & ~(offsetT)(0xffffffffU)) != 0)
036dc3f7 5011 {
8335d6aa
JW
5012 /* X >> 32 is illegal if sizeof (exp_p->X_add_number) == 4. */
5013 inst.operands[i].reg = (((exp_p->X_add_number >> 16) >> 16)
5014 & 0xffffffff);
036dc3f7
PB
5015 inst.operands[i].regisimm = 1;
5016 }
5017 }
8335d6aa
JW
5018 else if (exp_p->X_op == O_big
5019 && LITTLENUM_NUMBER_OF_BITS * exp_p->X_add_number > 32)
5287ad62
JB
5020 {
5021 unsigned parts = 32 / LITTLENUM_NUMBER_OF_BITS, j, idx = 0;
95b75c01 5022
5287ad62 5023 /* Bignums have their least significant bits in
477330fc
RM
5024 generic_bignum[0]. Make sure we put 32 bits in imm and
5025 32 bits in reg, in a (hopefully) portable way. */
9c2799c2 5026 gas_assert (parts != 0);
95b75c01
NC
5027
5028 /* Make sure that the number is not too big.
5029 PR 11972: Bignums can now be sign-extended to the
5030 size of a .octa so check that the out of range bits
5031 are all zero or all one. */
8335d6aa 5032 if (LITTLENUM_NUMBER_OF_BITS * exp_p->X_add_number > 64)
95b75c01
NC
5033 {
5034 LITTLENUM_TYPE m = -1;
5035
5036 if (generic_bignum[parts * 2] != 0
5037 && generic_bignum[parts * 2] != m)
5038 return FAIL;
5039
8335d6aa 5040 for (j = parts * 2 + 1; j < (unsigned) exp_p->X_add_number; j++)
95b75c01
NC
5041 if (generic_bignum[j] != generic_bignum[j-1])
5042 return FAIL;
5043 }
5044
5287ad62
JB
5045 inst.operands[i].imm = 0;
5046 for (j = 0; j < parts; j++, idx++)
477330fc
RM
5047 inst.operands[i].imm |= generic_bignum[idx]
5048 << (LITTLENUM_NUMBER_OF_BITS * j);
5287ad62
JB
5049 inst.operands[i].reg = 0;
5050 for (j = 0; j < parts; j++, idx++)
477330fc
RM
5051 inst.operands[i].reg |= generic_bignum[idx]
5052 << (LITTLENUM_NUMBER_OF_BITS * j);
5287ad62
JB
5053 inst.operands[i].regisimm = 1;
5054 }
8335d6aa 5055 else if (!(exp_p->X_op == O_symbol && allow_symbol_p))
5287ad62 5056 return FAIL;
5f4273c7 5057
5287ad62
JB
5058 *str = ptr;
5059
5060 return SUCCESS;
5061}
5062
c19d1205
ZW
5063/* Returns the pseudo-register number of an FPA immediate constant,
5064 or FAIL if there isn't a valid constant here. */
b99bd4ef 5065
c19d1205
ZW
5066static int
5067parse_fpa_immediate (char ** str)
5068{
5069 LITTLENUM_TYPE words[MAX_LITTLENUMS];
5070 char * save_in;
5071 expressionS exp;
5072 int i;
5073 int j;
b99bd4ef 5074
c19d1205
ZW
5075 /* First try and match exact strings, this is to guarantee
5076 that some formats will work even for cross assembly. */
b99bd4ef 5077
c19d1205
ZW
5078 for (i = 0; fp_const[i]; i++)
5079 {
5080 if (strncmp (*str, fp_const[i], strlen (fp_const[i])) == 0)
b99bd4ef 5081 {
c19d1205 5082 char *start = *str;
b99bd4ef 5083
c19d1205
ZW
5084 *str += strlen (fp_const[i]);
5085 if (is_end_of_line[(unsigned char) **str])
5086 return i + 8;
5087 *str = start;
5088 }
5089 }
b99bd4ef 5090
c19d1205
ZW
5091 /* Just because we didn't get a match doesn't mean that the constant
5092 isn't valid, just that it is in a format that we don't
5093 automatically recognize. Try parsing it with the standard
5094 expression routines. */
b99bd4ef 5095
c19d1205 5096 memset (words, 0, MAX_LITTLENUMS * sizeof (LITTLENUM_TYPE));
b99bd4ef 5097
c19d1205
ZW
5098 /* Look for a raw floating point number. */
5099 if ((save_in = atof_ieee (*str, 'x', words)) != NULL
5100 && is_end_of_line[(unsigned char) *save_in])
5101 {
5102 for (i = 0; i < NUM_FLOAT_VALS; i++)
5103 {
5104 for (j = 0; j < MAX_LITTLENUMS; j++)
b99bd4ef 5105 {
c19d1205
ZW
5106 if (words[j] != fp_values[i][j])
5107 break;
b99bd4ef
NC
5108 }
5109
c19d1205 5110 if (j == MAX_LITTLENUMS)
b99bd4ef 5111 {
c19d1205
ZW
5112 *str = save_in;
5113 return i + 8;
b99bd4ef
NC
5114 }
5115 }
5116 }
b99bd4ef 5117
c19d1205
ZW
5118 /* Try and parse a more complex expression, this will probably fail
5119 unless the code uses a floating point prefix (eg "0f"). */
5120 save_in = input_line_pointer;
5121 input_line_pointer = *str;
5122 if (expression (&exp) == absolute_section
5123 && exp.X_op == O_big
5124 && exp.X_add_number < 0)
5125 {
5126 /* FIXME: 5 = X_PRECISION, should be #define'd where we can use it.
5127 Ditto for 15. */
ba592044
AM
5128#define X_PRECISION 5
5129#define E_PRECISION 15L
5130 if (gen_to_words (words, X_PRECISION, E_PRECISION) == 0)
c19d1205
ZW
5131 {
5132 for (i = 0; i < NUM_FLOAT_VALS; i++)
5133 {
5134 for (j = 0; j < MAX_LITTLENUMS; j++)
5135 {
5136 if (words[j] != fp_values[i][j])
5137 break;
5138 }
b99bd4ef 5139
c19d1205
ZW
5140 if (j == MAX_LITTLENUMS)
5141 {
5142 *str = input_line_pointer;
5143 input_line_pointer = save_in;
5144 return i + 8;
5145 }
5146 }
5147 }
b99bd4ef
NC
5148 }
5149
c19d1205
ZW
5150 *str = input_line_pointer;
5151 input_line_pointer = save_in;
5152 inst.error = _("invalid FPA immediate expression");
5153 return FAIL;
b99bd4ef
NC
5154}
5155
136da414
JB
5156/* Returns 1 if a number has "quarter-precision" float format
5157 0baBbbbbbc defgh000 00000000 00000000. */
5158
5159static int
5160is_quarter_float (unsigned imm)
5161{
5162 int bs = (imm & 0x20000000) ? 0x3e000000 : 0x40000000;
5163 return (imm & 0x7ffff) == 0 && ((imm & 0x7e000000) ^ bs) == 0;
5164}
5165
aacf0b33
KT
5166
5167/* Detect the presence of a floating point or integer zero constant,
5168 i.e. #0.0 or #0. */
5169
5170static bfd_boolean
5171parse_ifimm_zero (char **in)
5172{
5173 int error_code;
5174
5175 if (!is_immediate_prefix (**in))
3c6452ae
TP
5176 {
5177 /* In unified syntax, all prefixes are optional. */
5178 if (!unified_syntax)
5179 return FALSE;
5180 }
5181 else
5182 ++*in;
0900a05b
JW
5183
5184 /* Accept #0x0 as a synonym for #0. */
5185 if (strncmp (*in, "0x", 2) == 0)
5186 {
5187 int val;
5188 if (parse_immediate (in, &val, 0, 0, TRUE) == FAIL)
5189 return FALSE;
5190 return TRUE;
5191 }
5192
aacf0b33
KT
5193 error_code = atof_generic (in, ".", EXP_CHARS,
5194 &generic_floating_point_number);
5195
5196 if (!error_code
5197 && generic_floating_point_number.sign == '+'
5198 && (generic_floating_point_number.low
5199 > generic_floating_point_number.leader))
5200 return TRUE;
5201
5202 return FALSE;
5203}
5204
136da414
JB
5205/* Parse an 8-bit "quarter-precision" floating point number of the form:
5206 0baBbbbbbc defgh000 00000000 00000000.
c96612cc
JB
5207 The zero and minus-zero cases need special handling, since they can't be
5208 encoded in the "quarter-precision" float format, but can nonetheless be
5209 loaded as integer constants. */
136da414
JB
5210
5211static unsigned
5212parse_qfloat_immediate (char **ccp, int *immed)
5213{
5214 char *str = *ccp;
c96612cc 5215 char *fpnum;
136da414 5216 LITTLENUM_TYPE words[MAX_LITTLENUMS];
c96612cc 5217 int found_fpchar = 0;
5f4273c7 5218
136da414 5219 skip_past_char (&str, '#');
5f4273c7 5220
c96612cc
JB
5221 /* We must not accidentally parse an integer as a floating-point number. Make
5222 sure that the value we parse is not an integer by checking for special
5223 characters '.' or 'e'.
5224 FIXME: This is a horrible hack, but doing better is tricky because type
5225 information isn't in a very usable state at parse time. */
5226 fpnum = str;
5227 skip_whitespace (fpnum);
5228
5229 if (strncmp (fpnum, "0x", 2) == 0)
5230 return FAIL;
5231 else
5232 {
5233 for (; *fpnum != '\0' && *fpnum != ' ' && *fpnum != '\n'; fpnum++)
477330fc
RM
5234 if (*fpnum == '.' || *fpnum == 'e' || *fpnum == 'E')
5235 {
5236 found_fpchar = 1;
5237 break;
5238 }
c96612cc
JB
5239
5240 if (!found_fpchar)
477330fc 5241 return FAIL;
c96612cc 5242 }
5f4273c7 5243
136da414
JB
5244 if ((str = atof_ieee (str, 's', words)) != NULL)
5245 {
5246 unsigned fpword = 0;
5247 int i;
5f4273c7 5248
136da414
JB
5249 /* Our FP word must be 32 bits (single-precision FP). */
5250 for (i = 0; i < 32 / LITTLENUM_NUMBER_OF_BITS; i++)
477330fc
RM
5251 {
5252 fpword <<= LITTLENUM_NUMBER_OF_BITS;
5253 fpword |= words[i];
5254 }
5f4273c7 5255
c96612cc 5256 if (is_quarter_float (fpword) || (fpword & 0x7fffffff) == 0)
477330fc 5257 *immed = fpword;
136da414 5258 else
477330fc 5259 return FAIL;
136da414
JB
5260
5261 *ccp = str;
5f4273c7 5262
136da414
JB
5263 return SUCCESS;
5264 }
5f4273c7 5265
136da414
JB
5266 return FAIL;
5267}
5268
c19d1205
ZW
5269/* Shift operands. */
5270enum shift_kind
b99bd4ef 5271{
c19d1205
ZW
5272 SHIFT_LSL, SHIFT_LSR, SHIFT_ASR, SHIFT_ROR, SHIFT_RRX
5273};
b99bd4ef 5274
c19d1205
ZW
5275struct asm_shift_name
5276{
5277 const char *name;
5278 enum shift_kind kind;
5279};
b99bd4ef 5280
c19d1205
ZW
5281/* Third argument to parse_shift. */
5282enum parse_shift_mode
5283{
5284 NO_SHIFT_RESTRICT, /* Any kind of shift is accepted. */
5285 SHIFT_IMMEDIATE, /* Shift operand must be an immediate. */
5286 SHIFT_LSL_OR_ASR_IMMEDIATE, /* Shift must be LSL or ASR immediate. */
5287 SHIFT_ASR_IMMEDIATE, /* Shift must be ASR immediate. */
5288 SHIFT_LSL_IMMEDIATE, /* Shift must be LSL immediate. */
5289};
b99bd4ef 5290
c19d1205
ZW
5291/* Parse a <shift> specifier on an ARM data processing instruction.
5292 This has three forms:
b99bd4ef 5293
c19d1205
ZW
5294 (LSL|LSR|ASL|ASR|ROR) Rs
5295 (LSL|LSR|ASL|ASR|ROR) #imm
5296 RRX
b99bd4ef 5297
c19d1205
ZW
5298 Note that ASL is assimilated to LSL in the instruction encoding, and
5299 RRX to ROR #0 (which cannot be written as such). */
b99bd4ef 5300
c19d1205
ZW
5301static int
5302parse_shift (char **str, int i, enum parse_shift_mode mode)
b99bd4ef 5303{
c19d1205
ZW
5304 const struct asm_shift_name *shift_name;
5305 enum shift_kind shift;
5306 char *s = *str;
5307 char *p = s;
5308 int reg;
b99bd4ef 5309
c19d1205
ZW
5310 for (p = *str; ISALPHA (*p); p++)
5311 ;
b99bd4ef 5312
c19d1205 5313 if (p == *str)
b99bd4ef 5314 {
c19d1205
ZW
5315 inst.error = _("shift expression expected");
5316 return FAIL;
b99bd4ef
NC
5317 }
5318
21d799b5 5319 shift_name = (const struct asm_shift_name *) hash_find_n (arm_shift_hsh, *str,
477330fc 5320 p - *str);
c19d1205
ZW
5321
5322 if (shift_name == NULL)
b99bd4ef 5323 {
c19d1205
ZW
5324 inst.error = _("shift expression expected");
5325 return FAIL;
b99bd4ef
NC
5326 }
5327
c19d1205 5328 shift = shift_name->kind;
b99bd4ef 5329
c19d1205
ZW
5330 switch (mode)
5331 {
5332 case NO_SHIFT_RESTRICT:
5333 case SHIFT_IMMEDIATE: break;
b99bd4ef 5334
c19d1205
ZW
5335 case SHIFT_LSL_OR_ASR_IMMEDIATE:
5336 if (shift != SHIFT_LSL && shift != SHIFT_ASR)
5337 {
5338 inst.error = _("'LSL' or 'ASR' required");
5339 return FAIL;
5340 }
5341 break;
b99bd4ef 5342
c19d1205
ZW
5343 case SHIFT_LSL_IMMEDIATE:
5344 if (shift != SHIFT_LSL)
5345 {
5346 inst.error = _("'LSL' required");
5347 return FAIL;
5348 }
5349 break;
b99bd4ef 5350
c19d1205
ZW
5351 case SHIFT_ASR_IMMEDIATE:
5352 if (shift != SHIFT_ASR)
5353 {
5354 inst.error = _("'ASR' required");
5355 return FAIL;
5356 }
5357 break;
b99bd4ef 5358
c19d1205
ZW
5359 default: abort ();
5360 }
b99bd4ef 5361
c19d1205
ZW
5362 if (shift != SHIFT_RRX)
5363 {
5364 /* Whitespace can appear here if the next thing is a bare digit. */
5365 skip_whitespace (p);
b99bd4ef 5366
c19d1205 5367 if (mode == NO_SHIFT_RESTRICT
dcbf9037 5368 && (reg = arm_reg_parse (&p, REG_TYPE_RN)) != FAIL)
c19d1205
ZW
5369 {
5370 inst.operands[i].imm = reg;
5371 inst.operands[i].immisreg = 1;
5372 }
e2b0ab59 5373 else if (my_get_expression (&inst.relocs[0].exp, &p, GE_IMM_PREFIX))
c19d1205
ZW
5374 return FAIL;
5375 }
5376 inst.operands[i].shift_kind = shift;
5377 inst.operands[i].shifted = 1;
5378 *str = p;
5379 return SUCCESS;
b99bd4ef
NC
5380}
5381
c19d1205 5382/* Parse a <shifter_operand> for an ARM data processing instruction:
b99bd4ef 5383
c19d1205
ZW
5384 #<immediate>
5385 #<immediate>, <rotate>
5386 <Rm>
5387 <Rm>, <shift>
b99bd4ef 5388
c19d1205
ZW
5389 where <shift> is defined by parse_shift above, and <rotate> is a
5390 multiple of 2 between 0 and 30. Validation of immediate operands
55cf6793 5391 is deferred to md_apply_fix. */
b99bd4ef 5392
c19d1205
ZW
5393static int
5394parse_shifter_operand (char **str, int i)
5395{
5396 int value;
91d6fa6a 5397 expressionS exp;
b99bd4ef 5398
dcbf9037 5399 if ((value = arm_reg_parse (str, REG_TYPE_RN)) != FAIL)
c19d1205
ZW
5400 {
5401 inst.operands[i].reg = value;
5402 inst.operands[i].isreg = 1;
b99bd4ef 5403
c19d1205 5404 /* parse_shift will override this if appropriate */
e2b0ab59
AV
5405 inst.relocs[0].exp.X_op = O_constant;
5406 inst.relocs[0].exp.X_add_number = 0;
b99bd4ef 5407
c19d1205
ZW
5408 if (skip_past_comma (str) == FAIL)
5409 return SUCCESS;
b99bd4ef 5410
c19d1205
ZW
5411 /* Shift operation on register. */
5412 return parse_shift (str, i, NO_SHIFT_RESTRICT);
b99bd4ef
NC
5413 }
5414
e2b0ab59 5415 if (my_get_expression (&inst.relocs[0].exp, str, GE_IMM_PREFIX))
c19d1205 5416 return FAIL;
b99bd4ef 5417
c19d1205 5418 if (skip_past_comma (str) == SUCCESS)
b99bd4ef 5419 {
c19d1205 5420 /* #x, y -- ie explicit rotation by Y. */
91d6fa6a 5421 if (my_get_expression (&exp, str, GE_NO_PREFIX))
c19d1205 5422 return FAIL;
b99bd4ef 5423
e2b0ab59 5424 if (exp.X_op != O_constant || inst.relocs[0].exp.X_op != O_constant)
c19d1205
ZW
5425 {
5426 inst.error = _("constant expression expected");
5427 return FAIL;
5428 }
b99bd4ef 5429
91d6fa6a 5430 value = exp.X_add_number;
c19d1205
ZW
5431 if (value < 0 || value > 30 || value % 2 != 0)
5432 {
5433 inst.error = _("invalid rotation");
5434 return FAIL;
5435 }
e2b0ab59
AV
5436 if (inst.relocs[0].exp.X_add_number < 0
5437 || inst.relocs[0].exp.X_add_number > 255)
c19d1205
ZW
5438 {
5439 inst.error = _("invalid constant");
5440 return FAIL;
5441 }
09d92015 5442
a415b1cd 5443 /* Encode as specified. */
e2b0ab59 5444 inst.operands[i].imm = inst.relocs[0].exp.X_add_number | value << 7;
a415b1cd 5445 return SUCCESS;
09d92015
MM
5446 }
5447
e2b0ab59
AV
5448 inst.relocs[0].type = BFD_RELOC_ARM_IMMEDIATE;
5449 inst.relocs[0].pc_rel = 0;
c19d1205 5450 return SUCCESS;
09d92015
MM
5451}
5452
4962c51a
MS
5453/* Group relocation information. Each entry in the table contains the
5454 textual name of the relocation as may appear in assembler source
5455 and must end with a colon.
5456 Along with this textual name are the relocation codes to be used if
5457 the corresponding instruction is an ALU instruction (ADD or SUB only),
5458 an LDR, an LDRS, or an LDC. */
5459
5460struct group_reloc_table_entry
5461{
5462 const char *name;
5463 int alu_code;
5464 int ldr_code;
5465 int ldrs_code;
5466 int ldc_code;
5467};
5468
5469typedef enum
5470{
5471 /* Varieties of non-ALU group relocation. */
5472
5473 GROUP_LDR,
5474 GROUP_LDRS,
5475 GROUP_LDC
5476} group_reloc_type;
5477
5478static struct group_reloc_table_entry group_reloc_table[] =
5479 { /* Program counter relative: */
5480 { "pc_g0_nc",
5481 BFD_RELOC_ARM_ALU_PC_G0_NC, /* ALU */
5482 0, /* LDR */
5483 0, /* LDRS */
5484 0 }, /* LDC */
5485 { "pc_g0",
5486 BFD_RELOC_ARM_ALU_PC_G0, /* ALU */
5487 BFD_RELOC_ARM_LDR_PC_G0, /* LDR */
5488 BFD_RELOC_ARM_LDRS_PC_G0, /* LDRS */
5489 BFD_RELOC_ARM_LDC_PC_G0 }, /* LDC */
5490 { "pc_g1_nc",
5491 BFD_RELOC_ARM_ALU_PC_G1_NC, /* ALU */
5492 0, /* LDR */
5493 0, /* LDRS */
5494 0 }, /* LDC */
5495 { "pc_g1",
5496 BFD_RELOC_ARM_ALU_PC_G1, /* ALU */
5497 BFD_RELOC_ARM_LDR_PC_G1, /* LDR */
5498 BFD_RELOC_ARM_LDRS_PC_G1, /* LDRS */
5499 BFD_RELOC_ARM_LDC_PC_G1 }, /* LDC */
5500 { "pc_g2",
5501 BFD_RELOC_ARM_ALU_PC_G2, /* ALU */
5502 BFD_RELOC_ARM_LDR_PC_G2, /* LDR */
5503 BFD_RELOC_ARM_LDRS_PC_G2, /* LDRS */
5504 BFD_RELOC_ARM_LDC_PC_G2 }, /* LDC */
5505 /* Section base relative */
5506 { "sb_g0_nc",
5507 BFD_RELOC_ARM_ALU_SB_G0_NC, /* ALU */
5508 0, /* LDR */
5509 0, /* LDRS */
5510 0 }, /* LDC */
5511 { "sb_g0",
5512 BFD_RELOC_ARM_ALU_SB_G0, /* ALU */
5513 BFD_RELOC_ARM_LDR_SB_G0, /* LDR */
5514 BFD_RELOC_ARM_LDRS_SB_G0, /* LDRS */
5515 BFD_RELOC_ARM_LDC_SB_G0 }, /* LDC */
5516 { "sb_g1_nc",
5517 BFD_RELOC_ARM_ALU_SB_G1_NC, /* ALU */
5518 0, /* LDR */
5519 0, /* LDRS */
5520 0 }, /* LDC */
5521 { "sb_g1",
5522 BFD_RELOC_ARM_ALU_SB_G1, /* ALU */
5523 BFD_RELOC_ARM_LDR_SB_G1, /* LDR */
5524 BFD_RELOC_ARM_LDRS_SB_G1, /* LDRS */
5525 BFD_RELOC_ARM_LDC_SB_G1 }, /* LDC */
5526 { "sb_g2",
5527 BFD_RELOC_ARM_ALU_SB_G2, /* ALU */
5528 BFD_RELOC_ARM_LDR_SB_G2, /* LDR */
5529 BFD_RELOC_ARM_LDRS_SB_G2, /* LDRS */
72d98d16
MG
5530 BFD_RELOC_ARM_LDC_SB_G2 }, /* LDC */
5531 /* Absolute thumb alu relocations. */
5532 { "lower0_7",
5533 BFD_RELOC_ARM_THUMB_ALU_ABS_G0_NC,/* ALU. */
5534 0, /* LDR. */
5535 0, /* LDRS. */
5536 0 }, /* LDC. */
5537 { "lower8_15",
5538 BFD_RELOC_ARM_THUMB_ALU_ABS_G1_NC,/* ALU. */
5539 0, /* LDR. */
5540 0, /* LDRS. */
5541 0 }, /* LDC. */
5542 { "upper0_7",
5543 BFD_RELOC_ARM_THUMB_ALU_ABS_G2_NC,/* ALU. */
5544 0, /* LDR. */
5545 0, /* LDRS. */
5546 0 }, /* LDC. */
5547 { "upper8_15",
5548 BFD_RELOC_ARM_THUMB_ALU_ABS_G3_NC,/* ALU. */
5549 0, /* LDR. */
5550 0, /* LDRS. */
5551 0 } }; /* LDC. */
4962c51a
MS
5552
5553/* Given the address of a pointer pointing to the textual name of a group
5554 relocation as may appear in assembler source, attempt to find its details
5555 in group_reloc_table. The pointer will be updated to the character after
5556 the trailing colon. On failure, FAIL will be returned; SUCCESS
5557 otherwise. On success, *entry will be updated to point at the relevant
5558 group_reloc_table entry. */
5559
5560static int
5561find_group_reloc_table_entry (char **str, struct group_reloc_table_entry **out)
5562{
5563 unsigned int i;
5564 for (i = 0; i < ARRAY_SIZE (group_reloc_table); i++)
5565 {
5566 int length = strlen (group_reloc_table[i].name);
5567
5f4273c7
NC
5568 if (strncasecmp (group_reloc_table[i].name, *str, length) == 0
5569 && (*str)[length] == ':')
477330fc
RM
5570 {
5571 *out = &group_reloc_table[i];
5572 *str += (length + 1);
5573 return SUCCESS;
5574 }
4962c51a
MS
5575 }
5576
5577 return FAIL;
5578}
5579
5580/* Parse a <shifter_operand> for an ARM data processing instruction
5581 (as for parse_shifter_operand) where group relocations are allowed:
5582
5583 #<immediate>
5584 #<immediate>, <rotate>
5585 #:<group_reloc>:<expression>
5586 <Rm>
5587 <Rm>, <shift>
5588
5589 where <group_reloc> is one of the strings defined in group_reloc_table.
5590 The hashes are optional.
5591
5592 Everything else is as for parse_shifter_operand. */
5593
5594static parse_operand_result
5595parse_shifter_operand_group_reloc (char **str, int i)
5596{
5597 /* Determine if we have the sequence of characters #: or just :
5598 coming next. If we do, then we check for a group relocation.
5599 If we don't, punt the whole lot to parse_shifter_operand. */
5600
5601 if (((*str)[0] == '#' && (*str)[1] == ':')
5602 || (*str)[0] == ':')
5603 {
5604 struct group_reloc_table_entry *entry;
5605
5606 if ((*str)[0] == '#')
477330fc 5607 (*str) += 2;
4962c51a 5608 else
477330fc 5609 (*str)++;
4962c51a
MS
5610
5611 /* Try to parse a group relocation. Anything else is an error. */
5612 if (find_group_reloc_table_entry (str, &entry) == FAIL)
477330fc
RM
5613 {
5614 inst.error = _("unknown group relocation");
5615 return PARSE_OPERAND_FAIL_NO_BACKTRACK;
5616 }
4962c51a
MS
5617
5618 /* We now have the group relocation table entry corresponding to
477330fc 5619 the name in the assembler source. Next, we parse the expression. */
e2b0ab59 5620 if (my_get_expression (&inst.relocs[0].exp, str, GE_NO_PREFIX))
477330fc 5621 return PARSE_OPERAND_FAIL_NO_BACKTRACK;
4962c51a
MS
5622
5623 /* Record the relocation type (always the ALU variant here). */
e2b0ab59
AV
5624 inst.relocs[0].type = (bfd_reloc_code_real_type) entry->alu_code;
5625 gas_assert (inst.relocs[0].type != 0);
4962c51a
MS
5626
5627 return PARSE_OPERAND_SUCCESS;
5628 }
5629 else
5630 return parse_shifter_operand (str, i) == SUCCESS
477330fc 5631 ? PARSE_OPERAND_SUCCESS : PARSE_OPERAND_FAIL;
4962c51a
MS
5632
5633 /* Never reached. */
5634}
5635
8e560766
MGD
5636/* Parse a Neon alignment expression. Information is written to
5637 inst.operands[i]. We assume the initial ':' has been skipped.
fa94de6b 5638
8e560766
MGD
5639 align .imm = align << 8, .immisalign=1, .preind=0 */
5640static parse_operand_result
5641parse_neon_alignment (char **str, int i)
5642{
5643 char *p = *str;
5644 expressionS exp;
5645
5646 my_get_expression (&exp, &p, GE_NO_PREFIX);
5647
5648 if (exp.X_op != O_constant)
5649 {
5650 inst.error = _("alignment must be constant");
5651 return PARSE_OPERAND_FAIL;
5652 }
5653
5654 inst.operands[i].imm = exp.X_add_number << 8;
5655 inst.operands[i].immisalign = 1;
5656 /* Alignments are not pre-indexes. */
5657 inst.operands[i].preind = 0;
5658
5659 *str = p;
5660 return PARSE_OPERAND_SUCCESS;
5661}
5662
c19d1205 5663/* Parse all forms of an ARM address expression. Information is written
e2b0ab59 5664 to inst.operands[i] and/or inst.relocs[0].
09d92015 5665
c19d1205 5666 Preindexed addressing (.preind=1):
09d92015 5667
e2b0ab59 5668 [Rn, #offset] .reg=Rn .relocs[0].exp=offset
c19d1205
ZW
5669 [Rn, +/-Rm] .reg=Rn .imm=Rm .immisreg=1 .negative=0/1
5670 [Rn, +/-Rm, shift] .reg=Rn .imm=Rm .immisreg=1 .negative=0/1
e2b0ab59 5671 .shift_kind=shift .relocs[0].exp=shift_imm
09d92015 5672
c19d1205 5673 These three may have a trailing ! which causes .writeback to be set also.
09d92015 5674
c19d1205 5675 Postindexed addressing (.postind=1, .writeback=1):
09d92015 5676
e2b0ab59 5677 [Rn], #offset .reg=Rn .relocs[0].exp=offset
c19d1205
ZW
5678 [Rn], +/-Rm .reg=Rn .imm=Rm .immisreg=1 .negative=0/1
5679 [Rn], +/-Rm, shift .reg=Rn .imm=Rm .immisreg=1 .negative=0/1
e2b0ab59 5680 .shift_kind=shift .relocs[0].exp=shift_imm
09d92015 5681
c19d1205 5682 Unindexed addressing (.preind=0, .postind=0):
09d92015 5683
c19d1205 5684 [Rn], {option} .reg=Rn .imm=option .immisreg=0
09d92015 5685
c19d1205 5686 Other:
09d92015 5687
c19d1205 5688 [Rn]{!} shorthand for [Rn,#0]{!}
e2b0ab59
AV
5689 =immediate .isreg=0 .relocs[0].exp=immediate
5690 label .reg=PC .relocs[0].pc_rel=1 .relocs[0].exp=label
09d92015 5691
c19d1205 5692 It is the caller's responsibility to check for addressing modes not
e2b0ab59 5693 supported by the instruction, and to set inst.relocs[0].type. */
c19d1205 5694
4962c51a
MS
5695static parse_operand_result
5696parse_address_main (char **str, int i, int group_relocations,
477330fc 5697 group_reloc_type group_type)
09d92015 5698{
c19d1205
ZW
5699 char *p = *str;
5700 int reg;
09d92015 5701
c19d1205 5702 if (skip_past_char (&p, '[') == FAIL)
09d92015 5703 {
c19d1205
ZW
5704 if (skip_past_char (&p, '=') == FAIL)
5705 {
974da60d 5706 /* Bare address - translate to PC-relative offset. */
e2b0ab59 5707 inst.relocs[0].pc_rel = 1;
c19d1205
ZW
5708 inst.operands[i].reg = REG_PC;
5709 inst.operands[i].isreg = 1;
5710 inst.operands[i].preind = 1;
09d92015 5711
e2b0ab59 5712 if (my_get_expression (&inst.relocs[0].exp, &p, GE_OPT_PREFIX_BIG))
8335d6aa
JW
5713 return PARSE_OPERAND_FAIL;
5714 }
e2b0ab59 5715 else if (parse_big_immediate (&p, i, &inst.relocs[0].exp,
8335d6aa 5716 /*allow_symbol_p=*/TRUE))
4962c51a 5717 return PARSE_OPERAND_FAIL;
09d92015 5718
c19d1205 5719 *str = p;
4962c51a 5720 return PARSE_OPERAND_SUCCESS;
09d92015
MM
5721 }
5722
8ab8155f
NC
5723 /* PR gas/14887: Allow for whitespace after the opening bracket. */
5724 skip_whitespace (p);
5725
dcbf9037 5726 if ((reg = arm_reg_parse (&p, REG_TYPE_RN)) == FAIL)
09d92015 5727 {
c19d1205 5728 inst.error = _(reg_expected_msgs[REG_TYPE_RN]);
4962c51a 5729 return PARSE_OPERAND_FAIL;
09d92015 5730 }
c19d1205
ZW
5731 inst.operands[i].reg = reg;
5732 inst.operands[i].isreg = 1;
09d92015 5733
c19d1205 5734 if (skip_past_comma (&p) == SUCCESS)
09d92015 5735 {
c19d1205 5736 inst.operands[i].preind = 1;
09d92015 5737
c19d1205
ZW
5738 if (*p == '+') p++;
5739 else if (*p == '-') p++, inst.operands[i].negative = 1;
5740
dcbf9037 5741 if ((reg = arm_reg_parse (&p, REG_TYPE_RN)) != FAIL)
09d92015 5742 {
c19d1205
ZW
5743 inst.operands[i].imm = reg;
5744 inst.operands[i].immisreg = 1;
5745
5746 if (skip_past_comma (&p) == SUCCESS)
5747 if (parse_shift (&p, i, SHIFT_IMMEDIATE) == FAIL)
4962c51a 5748 return PARSE_OPERAND_FAIL;
c19d1205 5749 }
5287ad62 5750 else if (skip_past_char (&p, ':') == SUCCESS)
8e560766
MGD
5751 {
5752 /* FIXME: '@' should be used here, but it's filtered out by generic
5753 code before we get to see it here. This may be subject to
5754 change. */
5755 parse_operand_result result = parse_neon_alignment (&p, i);
fa94de6b 5756
8e560766
MGD
5757 if (result != PARSE_OPERAND_SUCCESS)
5758 return result;
5759 }
c19d1205
ZW
5760 else
5761 {
5762 if (inst.operands[i].negative)
5763 {
5764 inst.operands[i].negative = 0;
5765 p--;
5766 }
4962c51a 5767
5f4273c7
NC
5768 if (group_relocations
5769 && ((*p == '#' && *(p + 1) == ':') || *p == ':'))
4962c51a
MS
5770 {
5771 struct group_reloc_table_entry *entry;
5772
477330fc
RM
5773 /* Skip over the #: or : sequence. */
5774 if (*p == '#')
5775 p += 2;
5776 else
5777 p++;
4962c51a
MS
5778
5779 /* Try to parse a group relocation. Anything else is an
477330fc 5780 error. */
4962c51a
MS
5781 if (find_group_reloc_table_entry (&p, &entry) == FAIL)
5782 {
5783 inst.error = _("unknown group relocation");
5784 return PARSE_OPERAND_FAIL_NO_BACKTRACK;
5785 }
5786
5787 /* We now have the group relocation table entry corresponding to
5788 the name in the assembler source. Next, we parse the
477330fc 5789 expression. */
e2b0ab59 5790 if (my_get_expression (&inst.relocs[0].exp, &p, GE_NO_PREFIX))
4962c51a
MS
5791 return PARSE_OPERAND_FAIL_NO_BACKTRACK;
5792
5793 /* Record the relocation type. */
477330fc
RM
5794 switch (group_type)
5795 {
5796 case GROUP_LDR:
e2b0ab59
AV
5797 inst.relocs[0].type
5798 = (bfd_reloc_code_real_type) entry->ldr_code;
477330fc 5799 break;
4962c51a 5800
477330fc 5801 case GROUP_LDRS:
e2b0ab59
AV
5802 inst.relocs[0].type
5803 = (bfd_reloc_code_real_type) entry->ldrs_code;
477330fc 5804 break;
4962c51a 5805
477330fc 5806 case GROUP_LDC:
e2b0ab59
AV
5807 inst.relocs[0].type
5808 = (bfd_reloc_code_real_type) entry->ldc_code;
477330fc 5809 break;
4962c51a 5810
477330fc
RM
5811 default:
5812 gas_assert (0);
5813 }
4962c51a 5814
e2b0ab59 5815 if (inst.relocs[0].type == 0)
4962c51a
MS
5816 {
5817 inst.error = _("this group relocation is not allowed on this instruction");
5818 return PARSE_OPERAND_FAIL_NO_BACKTRACK;
5819 }
477330fc
RM
5820 }
5821 else
26d97720
NS
5822 {
5823 char *q = p;
0198d5e6 5824
e2b0ab59 5825 if (my_get_expression (&inst.relocs[0].exp, &p, GE_IMM_PREFIX))
26d97720
NS
5826 return PARSE_OPERAND_FAIL;
5827 /* If the offset is 0, find out if it's a +0 or -0. */
e2b0ab59
AV
5828 if (inst.relocs[0].exp.X_op == O_constant
5829 && inst.relocs[0].exp.X_add_number == 0)
26d97720
NS
5830 {
5831 skip_whitespace (q);
5832 if (*q == '#')
5833 {
5834 q++;
5835 skip_whitespace (q);
5836 }
5837 if (*q == '-')
5838 inst.operands[i].negative = 1;
5839 }
5840 }
09d92015
MM
5841 }
5842 }
8e560766
MGD
5843 else if (skip_past_char (&p, ':') == SUCCESS)
5844 {
5845 /* FIXME: '@' should be used here, but it's filtered out by generic code
5846 before we get to see it here. This may be subject to change. */
5847 parse_operand_result result = parse_neon_alignment (&p, i);
fa94de6b 5848
8e560766
MGD
5849 if (result != PARSE_OPERAND_SUCCESS)
5850 return result;
5851 }
09d92015 5852
c19d1205 5853 if (skip_past_char (&p, ']') == FAIL)
09d92015 5854 {
c19d1205 5855 inst.error = _("']' expected");
4962c51a 5856 return PARSE_OPERAND_FAIL;
09d92015
MM
5857 }
5858
c19d1205
ZW
5859 if (skip_past_char (&p, '!') == SUCCESS)
5860 inst.operands[i].writeback = 1;
09d92015 5861
c19d1205 5862 else if (skip_past_comma (&p) == SUCCESS)
09d92015 5863 {
c19d1205
ZW
5864 if (skip_past_char (&p, '{') == SUCCESS)
5865 {
5866 /* [Rn], {expr} - unindexed, with option */
5867 if (parse_immediate (&p, &inst.operands[i].imm,
ca3f61f7 5868 0, 255, TRUE) == FAIL)
4962c51a 5869 return PARSE_OPERAND_FAIL;
09d92015 5870
c19d1205
ZW
5871 if (skip_past_char (&p, '}') == FAIL)
5872 {
5873 inst.error = _("'}' expected at end of 'option' field");
4962c51a 5874 return PARSE_OPERAND_FAIL;
c19d1205
ZW
5875 }
5876 if (inst.operands[i].preind)
5877 {
5878 inst.error = _("cannot combine index with option");
4962c51a 5879 return PARSE_OPERAND_FAIL;
c19d1205
ZW
5880 }
5881 *str = p;
4962c51a 5882 return PARSE_OPERAND_SUCCESS;
09d92015 5883 }
c19d1205
ZW
5884 else
5885 {
5886 inst.operands[i].postind = 1;
5887 inst.operands[i].writeback = 1;
09d92015 5888
c19d1205
ZW
5889 if (inst.operands[i].preind)
5890 {
5891 inst.error = _("cannot combine pre- and post-indexing");
4962c51a 5892 return PARSE_OPERAND_FAIL;
c19d1205 5893 }
09d92015 5894
c19d1205
ZW
5895 if (*p == '+') p++;
5896 else if (*p == '-') p++, inst.operands[i].negative = 1;
a737bd4d 5897
dcbf9037 5898 if ((reg = arm_reg_parse (&p, REG_TYPE_RN)) != FAIL)
c19d1205 5899 {
477330fc
RM
5900 /* We might be using the immediate for alignment already. If we
5901 are, OR the register number into the low-order bits. */
5902 if (inst.operands[i].immisalign)
5903 inst.operands[i].imm |= reg;
5904 else
5905 inst.operands[i].imm = reg;
c19d1205 5906 inst.operands[i].immisreg = 1;
a737bd4d 5907
c19d1205
ZW
5908 if (skip_past_comma (&p) == SUCCESS)
5909 if (parse_shift (&p, i, SHIFT_IMMEDIATE) == FAIL)
4962c51a 5910 return PARSE_OPERAND_FAIL;
c19d1205
ZW
5911 }
5912 else
5913 {
26d97720 5914 char *q = p;
0198d5e6 5915
c19d1205
ZW
5916 if (inst.operands[i].negative)
5917 {
5918 inst.operands[i].negative = 0;
5919 p--;
5920 }
e2b0ab59 5921 if (my_get_expression (&inst.relocs[0].exp, &p, GE_IMM_PREFIX))
4962c51a 5922 return PARSE_OPERAND_FAIL;
26d97720 5923 /* If the offset is 0, find out if it's a +0 or -0. */
e2b0ab59
AV
5924 if (inst.relocs[0].exp.X_op == O_constant
5925 && inst.relocs[0].exp.X_add_number == 0)
26d97720
NS
5926 {
5927 skip_whitespace (q);
5928 if (*q == '#')
5929 {
5930 q++;
5931 skip_whitespace (q);
5932 }
5933 if (*q == '-')
5934 inst.operands[i].negative = 1;
5935 }
c19d1205
ZW
5936 }
5937 }
a737bd4d
NC
5938 }
5939
c19d1205
ZW
5940 /* If at this point neither .preind nor .postind is set, we have a
5941 bare [Rn]{!}, which is shorthand for [Rn,#0]{!}. */
5942 if (inst.operands[i].preind == 0 && inst.operands[i].postind == 0)
5943 {
5944 inst.operands[i].preind = 1;
e2b0ab59
AV
5945 inst.relocs[0].exp.X_op = O_constant;
5946 inst.relocs[0].exp.X_add_number = 0;
c19d1205
ZW
5947 }
5948 *str = p;
4962c51a
MS
5949 return PARSE_OPERAND_SUCCESS;
5950}
5951
5952static int
5953parse_address (char **str, int i)
5954{
21d799b5 5955 return parse_address_main (str, i, 0, GROUP_LDR) == PARSE_OPERAND_SUCCESS
477330fc 5956 ? SUCCESS : FAIL;
4962c51a
MS
5957}
5958
5959static parse_operand_result
5960parse_address_group_reloc (char **str, int i, group_reloc_type type)
5961{
5962 return parse_address_main (str, i, 1, type);
a737bd4d
NC
5963}
5964
b6895b4f
PB
5965/* Parse an operand for a MOVW or MOVT instruction. */
5966static int
5967parse_half (char **str)
5968{
5969 char * p;
5f4273c7 5970
b6895b4f
PB
5971 p = *str;
5972 skip_past_char (&p, '#');
5f4273c7 5973 if (strncasecmp (p, ":lower16:", 9) == 0)
e2b0ab59 5974 inst.relocs[0].type = BFD_RELOC_ARM_MOVW;
b6895b4f 5975 else if (strncasecmp (p, ":upper16:", 9) == 0)
e2b0ab59 5976 inst.relocs[0].type = BFD_RELOC_ARM_MOVT;
b6895b4f 5977
e2b0ab59 5978 if (inst.relocs[0].type != BFD_RELOC_UNUSED)
b6895b4f
PB
5979 {
5980 p += 9;
5f4273c7 5981 skip_whitespace (p);
b6895b4f
PB
5982 }
5983
e2b0ab59 5984 if (my_get_expression (&inst.relocs[0].exp, &p, GE_NO_PREFIX))
b6895b4f
PB
5985 return FAIL;
5986
e2b0ab59 5987 if (inst.relocs[0].type == BFD_RELOC_UNUSED)
b6895b4f 5988 {
e2b0ab59 5989 if (inst.relocs[0].exp.X_op != O_constant)
b6895b4f
PB
5990 {
5991 inst.error = _("constant expression expected");
5992 return FAIL;
5993 }
e2b0ab59
AV
5994 if (inst.relocs[0].exp.X_add_number < 0
5995 || inst.relocs[0].exp.X_add_number > 0xffff)
b6895b4f
PB
5996 {
5997 inst.error = _("immediate value out of range");
5998 return FAIL;
5999 }
6000 }
6001 *str = p;
6002 return SUCCESS;
6003}
6004
c19d1205 6005/* Miscellaneous. */
a737bd4d 6006
c19d1205
ZW
6007/* Parse a PSR flag operand. The value returned is FAIL on syntax error,
6008 or a bitmask suitable to be or-ed into the ARM msr instruction. */
6009static int
d2cd1205 6010parse_psr (char **str, bfd_boolean lhs)
09d92015 6011{
c19d1205
ZW
6012 char *p;
6013 unsigned long psr_field;
62b3e311
PB
6014 const struct asm_psr *psr;
6015 char *start;
d2cd1205 6016 bfd_boolean is_apsr = FALSE;
ac7f631b 6017 bfd_boolean m_profile = ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_m);
09d92015 6018
a4482bb6
NC
6019 /* PR gas/12698: If the user has specified -march=all then m_profile will
6020 be TRUE, but we want to ignore it in this case as we are building for any
6021 CPU type, including non-m variants. */
823d2571 6022 if (ARM_FEATURE_CORE_EQUAL (selected_cpu, arm_arch_any))
a4482bb6
NC
6023 m_profile = FALSE;
6024
c19d1205
ZW
6025 /* CPSR's and SPSR's can now be lowercase. This is just a convenience
6026 feature for ease of use and backwards compatibility. */
6027 p = *str;
62b3e311 6028 if (strncasecmp (p, "SPSR", 4) == 0)
d2cd1205
JB
6029 {
6030 if (m_profile)
6031 goto unsupported_psr;
fa94de6b 6032
d2cd1205
JB
6033 psr_field = SPSR_BIT;
6034 }
6035 else if (strncasecmp (p, "CPSR", 4) == 0)
6036 {
6037 if (m_profile)
6038 goto unsupported_psr;
6039
6040 psr_field = 0;
6041 }
6042 else if (strncasecmp (p, "APSR", 4) == 0)
6043 {
6044 /* APSR[_<bits>] can be used as a synonym for CPSR[_<flags>] on ARMv7-A
6045 and ARMv7-R architecture CPUs. */
6046 is_apsr = TRUE;
6047 psr_field = 0;
6048 }
6049 else if (m_profile)
62b3e311
PB
6050 {
6051 start = p;
6052 do
6053 p++;
6054 while (ISALNUM (*p) || *p == '_');
6055
d2cd1205
JB
6056 if (strncasecmp (start, "iapsr", 5) == 0
6057 || strncasecmp (start, "eapsr", 5) == 0
6058 || strncasecmp (start, "xpsr", 4) == 0
6059 || strncasecmp (start, "psr", 3) == 0)
6060 p = start + strcspn (start, "rR") + 1;
6061
21d799b5 6062 psr = (const struct asm_psr *) hash_find_n (arm_v7m_psr_hsh, start,
477330fc 6063 p - start);
d2cd1205 6064
62b3e311
PB
6065 if (!psr)
6066 return FAIL;
09d92015 6067
d2cd1205
JB
6068 /* If APSR is being written, a bitfield may be specified. Note that
6069 APSR itself is handled above. */
6070 if (psr->field <= 3)
6071 {
6072 psr_field = psr->field;
6073 is_apsr = TRUE;
6074 goto check_suffix;
6075 }
6076
62b3e311 6077 *str = p;
d2cd1205
JB
6078 /* M-profile MSR instructions have the mask field set to "10", except
6079 *PSR variants which modify APSR, which may use a different mask (and
6080 have been handled already). Do that by setting the PSR_f field
6081 here. */
6082 return psr->field | (lhs ? PSR_f : 0);
62b3e311 6083 }
d2cd1205
JB
6084 else
6085 goto unsupported_psr;
09d92015 6086
62b3e311 6087 p += 4;
d2cd1205 6088check_suffix:
c19d1205
ZW
6089 if (*p == '_')
6090 {
6091 /* A suffix follows. */
c19d1205
ZW
6092 p++;
6093 start = p;
a737bd4d 6094
c19d1205
ZW
6095 do
6096 p++;
6097 while (ISALNUM (*p) || *p == '_');
a737bd4d 6098
d2cd1205
JB
6099 if (is_apsr)
6100 {
6101 /* APSR uses a notation for bits, rather than fields. */
6102 unsigned int nzcvq_bits = 0;
6103 unsigned int g_bit = 0;
6104 char *bit;
fa94de6b 6105
d2cd1205
JB
6106 for (bit = start; bit != p; bit++)
6107 {
6108 switch (TOLOWER (*bit))
477330fc 6109 {
d2cd1205
JB
6110 case 'n':
6111 nzcvq_bits |= (nzcvq_bits & 0x01) ? 0x20 : 0x01;
6112 break;
6113
6114 case 'z':
6115 nzcvq_bits |= (nzcvq_bits & 0x02) ? 0x20 : 0x02;
6116 break;
6117
6118 case 'c':
6119 nzcvq_bits |= (nzcvq_bits & 0x04) ? 0x20 : 0x04;
6120 break;
6121
6122 case 'v':
6123 nzcvq_bits |= (nzcvq_bits & 0x08) ? 0x20 : 0x08;
6124 break;
fa94de6b 6125
d2cd1205
JB
6126 case 'q':
6127 nzcvq_bits |= (nzcvq_bits & 0x10) ? 0x20 : 0x10;
6128 break;
fa94de6b 6129
d2cd1205
JB
6130 case 'g':
6131 g_bit |= (g_bit & 0x1) ? 0x2 : 0x1;
6132 break;
fa94de6b 6133
d2cd1205
JB
6134 default:
6135 inst.error = _("unexpected bit specified after APSR");
6136 return FAIL;
6137 }
6138 }
fa94de6b 6139
d2cd1205
JB
6140 if (nzcvq_bits == 0x1f)
6141 psr_field |= PSR_f;
fa94de6b 6142
d2cd1205
JB
6143 if (g_bit == 0x1)
6144 {
6145 if (!ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6_dsp))
477330fc 6146 {
d2cd1205
JB
6147 inst.error = _("selected processor does not "
6148 "support DSP extension");
6149 return FAIL;
6150 }
6151
6152 psr_field |= PSR_s;
6153 }
fa94de6b 6154
d2cd1205
JB
6155 if ((nzcvq_bits & 0x20) != 0
6156 || (nzcvq_bits != 0x1f && nzcvq_bits != 0)
6157 || (g_bit & 0x2) != 0)
6158 {
6159 inst.error = _("bad bitmask specified after APSR");
6160 return FAIL;
6161 }
6162 }
6163 else
477330fc 6164 {
d2cd1205 6165 psr = (const struct asm_psr *) hash_find_n (arm_psr_hsh, start,
477330fc 6166 p - start);
d2cd1205 6167 if (!psr)
477330fc 6168 goto error;
a737bd4d 6169
d2cd1205
JB
6170 psr_field |= psr->field;
6171 }
a737bd4d 6172 }
c19d1205 6173 else
a737bd4d 6174 {
c19d1205
ZW
6175 if (ISALNUM (*p))
6176 goto error; /* Garbage after "[CS]PSR". */
6177
d2cd1205 6178 /* Unadorned APSR is equivalent to APSR_nzcvq/CPSR_f (for writes). This
477330fc 6179 is deprecated, but allow it anyway. */
d2cd1205
JB
6180 if (is_apsr && lhs)
6181 {
6182 psr_field |= PSR_f;
6183 as_tsktsk (_("writing to APSR without specifying a bitmask is "
6184 "deprecated"));
6185 }
6186 else if (!m_profile)
6187 /* These bits are never right for M-profile devices: don't set them
6188 (only code paths which read/write APSR reach here). */
6189 psr_field |= (PSR_c | PSR_f);
a737bd4d 6190 }
c19d1205
ZW
6191 *str = p;
6192 return psr_field;
a737bd4d 6193
d2cd1205
JB
6194 unsupported_psr:
6195 inst.error = _("selected processor does not support requested special "
6196 "purpose register");
6197 return FAIL;
6198
c19d1205
ZW
6199 error:
6200 inst.error = _("flag for {c}psr instruction expected");
6201 return FAIL;
a737bd4d
NC
6202}
6203
32c36c3c
AV
6204static int
6205parse_sys_vldr_vstr (char **str)
6206{
6207 unsigned i;
6208 int val = FAIL;
6209 struct {
6210 const char *name;
6211 int regl;
6212 int regh;
6213 } sysregs[] = {
6214 {"FPSCR", 0x1, 0x0},
6215 {"FPSCR_nzcvqc", 0x2, 0x0},
6216 {"VPR", 0x4, 0x1},
6217 {"P0", 0x5, 0x1},
6218 {"FPCXTNS", 0x6, 0x1},
6219 {"FPCXTS", 0x7, 0x1}
6220 };
6221 char *op_end = strchr (*str, ',');
6222 size_t op_strlen = op_end - *str;
6223
6224 for (i = 0; i < sizeof (sysregs) / sizeof (sysregs[0]); i++)
6225 {
6226 if (!strncmp (*str, sysregs[i].name, op_strlen))
6227 {
6228 val = sysregs[i].regl | (sysregs[i].regh << 3);
6229 *str = op_end;
6230 break;
6231 }
6232 }
6233
6234 return val;
6235}
6236
c19d1205
ZW
6237/* Parse the flags argument to CPSI[ED]. Returns FAIL on error, or a
6238 value suitable for splatting into the AIF field of the instruction. */
a737bd4d 6239
c19d1205
ZW
6240static int
6241parse_cps_flags (char **str)
a737bd4d 6242{
c19d1205
ZW
6243 int val = 0;
6244 int saw_a_flag = 0;
6245 char *s = *str;
a737bd4d 6246
c19d1205
ZW
6247 for (;;)
6248 switch (*s++)
6249 {
6250 case '\0': case ',':
6251 goto done;
a737bd4d 6252
c19d1205
ZW
6253 case 'a': case 'A': saw_a_flag = 1; val |= 0x4; break;
6254 case 'i': case 'I': saw_a_flag = 1; val |= 0x2; break;
6255 case 'f': case 'F': saw_a_flag = 1; val |= 0x1; break;
a737bd4d 6256
c19d1205
ZW
6257 default:
6258 inst.error = _("unrecognized CPS flag");
6259 return FAIL;
6260 }
a737bd4d 6261
c19d1205
ZW
6262 done:
6263 if (saw_a_flag == 0)
a737bd4d 6264 {
c19d1205
ZW
6265 inst.error = _("missing CPS flags");
6266 return FAIL;
a737bd4d 6267 }
a737bd4d 6268
c19d1205
ZW
6269 *str = s - 1;
6270 return val;
a737bd4d
NC
6271}
6272
c19d1205
ZW
6273/* Parse an endian specifier ("BE" or "LE", case insensitive);
6274 returns 0 for big-endian, 1 for little-endian, FAIL for an error. */
a737bd4d
NC
6275
6276static int
c19d1205 6277parse_endian_specifier (char **str)
a737bd4d 6278{
c19d1205
ZW
6279 int little_endian;
6280 char *s = *str;
a737bd4d 6281
c19d1205
ZW
6282 if (strncasecmp (s, "BE", 2))
6283 little_endian = 0;
6284 else if (strncasecmp (s, "LE", 2))
6285 little_endian = 1;
6286 else
a737bd4d 6287 {
c19d1205 6288 inst.error = _("valid endian specifiers are be or le");
a737bd4d
NC
6289 return FAIL;
6290 }
6291
c19d1205 6292 if (ISALNUM (s[2]) || s[2] == '_')
a737bd4d 6293 {
c19d1205 6294 inst.error = _("valid endian specifiers are be or le");
a737bd4d
NC
6295 return FAIL;
6296 }
6297
c19d1205
ZW
6298 *str = s + 2;
6299 return little_endian;
6300}
a737bd4d 6301
c19d1205
ZW
6302/* Parse a rotation specifier: ROR #0, #8, #16, #24. *val receives a
6303 value suitable for poking into the rotate field of an sxt or sxta
6304 instruction, or FAIL on error. */
6305
6306static int
6307parse_ror (char **str)
6308{
6309 int rot;
6310 char *s = *str;
6311
6312 if (strncasecmp (s, "ROR", 3) == 0)
6313 s += 3;
6314 else
a737bd4d 6315 {
c19d1205 6316 inst.error = _("missing rotation field after comma");
a737bd4d
NC
6317 return FAIL;
6318 }
c19d1205
ZW
6319
6320 if (parse_immediate (&s, &rot, 0, 24, FALSE) == FAIL)
6321 return FAIL;
6322
6323 switch (rot)
a737bd4d 6324 {
c19d1205
ZW
6325 case 0: *str = s; return 0x0;
6326 case 8: *str = s; return 0x1;
6327 case 16: *str = s; return 0x2;
6328 case 24: *str = s; return 0x3;
6329
6330 default:
6331 inst.error = _("rotation can only be 0, 8, 16, or 24");
a737bd4d
NC
6332 return FAIL;
6333 }
c19d1205 6334}
a737bd4d 6335
c19d1205
ZW
6336/* Parse a conditional code (from conds[] below). The value returned is in the
6337 range 0 .. 14, or FAIL. */
6338static int
6339parse_cond (char **str)
6340{
c462b453 6341 char *q;
c19d1205 6342 const struct asm_cond *c;
c462b453
PB
6343 int n;
6344 /* Condition codes are always 2 characters, so matching up to
6345 3 characters is sufficient. */
6346 char cond[3];
a737bd4d 6347
c462b453
PB
6348 q = *str;
6349 n = 0;
6350 while (ISALPHA (*q) && n < 3)
6351 {
e07e6e58 6352 cond[n] = TOLOWER (*q);
c462b453
PB
6353 q++;
6354 n++;
6355 }
a737bd4d 6356
21d799b5 6357 c = (const struct asm_cond *) hash_find_n (arm_cond_hsh, cond, n);
c19d1205 6358 if (!c)
a737bd4d 6359 {
c19d1205 6360 inst.error = _("condition required");
a737bd4d
NC
6361 return FAIL;
6362 }
6363
c19d1205
ZW
6364 *str = q;
6365 return c->value;
6366}
6367
62b3e311
PB
6368/* Parse an option for a barrier instruction. Returns the encoding for the
6369 option, or FAIL. */
6370static int
6371parse_barrier (char **str)
6372{
6373 char *p, *q;
6374 const struct asm_barrier_opt *o;
6375
6376 p = q = *str;
6377 while (ISALPHA (*q))
6378 q++;
6379
21d799b5 6380 o = (const struct asm_barrier_opt *) hash_find_n (arm_barrier_opt_hsh, p,
477330fc 6381 q - p);
62b3e311
PB
6382 if (!o)
6383 return FAIL;
6384
e797f7e0
MGD
6385 if (!mark_feature_used (&o->arch))
6386 return FAIL;
6387
62b3e311
PB
6388 *str = q;
6389 return o->value;
6390}
6391
92e90b6e
PB
6392/* Parse the operands of a table branch instruction. Similar to a memory
6393 operand. */
6394static int
6395parse_tb (char **str)
6396{
6397 char * p = *str;
6398 int reg;
6399
6400 if (skip_past_char (&p, '[') == FAIL)
ab1eb5fe
PB
6401 {
6402 inst.error = _("'[' expected");
6403 return FAIL;
6404 }
92e90b6e 6405
dcbf9037 6406 if ((reg = arm_reg_parse (&p, REG_TYPE_RN)) == FAIL)
92e90b6e
PB
6407 {
6408 inst.error = _(reg_expected_msgs[REG_TYPE_RN]);
6409 return FAIL;
6410 }
6411 inst.operands[0].reg = reg;
6412
6413 if (skip_past_comma (&p) == FAIL)
ab1eb5fe
PB
6414 {
6415 inst.error = _("',' expected");
6416 return FAIL;
6417 }
5f4273c7 6418
dcbf9037 6419 if ((reg = arm_reg_parse (&p, REG_TYPE_RN)) == FAIL)
92e90b6e
PB
6420 {
6421 inst.error = _(reg_expected_msgs[REG_TYPE_RN]);
6422 return FAIL;
6423 }
6424 inst.operands[0].imm = reg;
6425
6426 if (skip_past_comma (&p) == SUCCESS)
6427 {
6428 if (parse_shift (&p, 0, SHIFT_LSL_IMMEDIATE) == FAIL)
6429 return FAIL;
e2b0ab59 6430 if (inst.relocs[0].exp.X_add_number != 1)
92e90b6e
PB
6431 {
6432 inst.error = _("invalid shift");
6433 return FAIL;
6434 }
6435 inst.operands[0].shifted = 1;
6436 }
6437
6438 if (skip_past_char (&p, ']') == FAIL)
6439 {
6440 inst.error = _("']' expected");
6441 return FAIL;
6442 }
6443 *str = p;
6444 return SUCCESS;
6445}
6446
5287ad62
JB
6447/* Parse the operands of a Neon VMOV instruction. See do_neon_mov for more
6448 information on the types the operands can take and how they are encoded.
037e8744
JB
6449 Up to four operands may be read; this function handles setting the
6450 ".present" field for each read operand itself.
5287ad62
JB
6451 Updates STR and WHICH_OPERAND if parsing is successful and returns SUCCESS,
6452 else returns FAIL. */
6453
6454static int
6455parse_neon_mov (char **str, int *which_operand)
6456{
6457 int i = *which_operand, val;
6458 enum arm_reg_type rtype;
6459 char *ptr = *str;
dcbf9037 6460 struct neon_type_el optype;
5f4273c7 6461
dcbf9037 6462 if ((val = parse_scalar (&ptr, 8, &optype)) != FAIL)
5287ad62
JB
6463 {
6464 /* Case 4: VMOV<c><q>.<size> <Dn[x]>, <Rd>. */
6465 inst.operands[i].reg = val;
6466 inst.operands[i].isscalar = 1;
dcbf9037 6467 inst.operands[i].vectype = optype;
5287ad62
JB
6468 inst.operands[i++].present = 1;
6469
6470 if (skip_past_comma (&ptr) == FAIL)
477330fc 6471 goto wanted_comma;
5f4273c7 6472
dcbf9037 6473 if ((val = arm_reg_parse (&ptr, REG_TYPE_RN)) == FAIL)
477330fc 6474 goto wanted_arm;
5f4273c7 6475
5287ad62
JB
6476 inst.operands[i].reg = val;
6477 inst.operands[i].isreg = 1;
6478 inst.operands[i].present = 1;
6479 }
037e8744 6480 else if ((val = arm_typed_reg_parse (&ptr, REG_TYPE_NSDQ, &rtype, &optype))
477330fc 6481 != FAIL)
5287ad62
JB
6482 {
6483 /* Cases 0, 1, 2, 3, 5 (D only). */
6484 if (skip_past_comma (&ptr) == FAIL)
477330fc 6485 goto wanted_comma;
5f4273c7 6486
5287ad62
JB
6487 inst.operands[i].reg = val;
6488 inst.operands[i].isreg = 1;
6489 inst.operands[i].isquad = (rtype == REG_TYPE_NQ);
037e8744
JB
6490 inst.operands[i].issingle = (rtype == REG_TYPE_VFS);
6491 inst.operands[i].isvec = 1;
dcbf9037 6492 inst.operands[i].vectype = optype;
5287ad62
JB
6493 inst.operands[i++].present = 1;
6494
dcbf9037 6495 if ((val = arm_reg_parse (&ptr, REG_TYPE_RN)) != FAIL)
477330fc
RM
6496 {
6497 /* Case 5: VMOV<c><q> <Dm>, <Rd>, <Rn>.
6498 Case 13: VMOV <Sd>, <Rm> */
6499 inst.operands[i].reg = val;
6500 inst.operands[i].isreg = 1;
6501 inst.operands[i].present = 1;
6502
6503 if (rtype == REG_TYPE_NQ)
6504 {
6505 first_error (_("can't use Neon quad register here"));
6506 return FAIL;
6507 }
6508 else if (rtype != REG_TYPE_VFS)
6509 {
6510 i++;
6511 if (skip_past_comma (&ptr) == FAIL)
6512 goto wanted_comma;
6513 if ((val = arm_reg_parse (&ptr, REG_TYPE_RN)) == FAIL)
6514 goto wanted_arm;
6515 inst.operands[i].reg = val;
6516 inst.operands[i].isreg = 1;
6517 inst.operands[i].present = 1;
6518 }
6519 }
037e8744 6520 else if ((val = arm_typed_reg_parse (&ptr, REG_TYPE_NSDQ, &rtype,
477330fc
RM
6521 &optype)) != FAIL)
6522 {
6523 /* Case 0: VMOV<c><q> <Qd>, <Qm>
6524 Case 1: VMOV<c><q> <Dd>, <Dm>
6525 Case 8: VMOV.F32 <Sd>, <Sm>
6526 Case 15: VMOV <Sd>, <Se>, <Rn>, <Rm> */
6527
6528 inst.operands[i].reg = val;
6529 inst.operands[i].isreg = 1;
6530 inst.operands[i].isquad = (rtype == REG_TYPE_NQ);
6531 inst.operands[i].issingle = (rtype == REG_TYPE_VFS);
6532 inst.operands[i].isvec = 1;
6533 inst.operands[i].vectype = optype;
6534 inst.operands[i].present = 1;
6535
6536 if (skip_past_comma (&ptr) == SUCCESS)
6537 {
6538 /* Case 15. */
6539 i++;
6540
6541 if ((val = arm_reg_parse (&ptr, REG_TYPE_RN)) == FAIL)
6542 goto wanted_arm;
6543
6544 inst.operands[i].reg = val;
6545 inst.operands[i].isreg = 1;
6546 inst.operands[i++].present = 1;
6547
6548 if (skip_past_comma (&ptr) == FAIL)
6549 goto wanted_comma;
6550
6551 if ((val = arm_reg_parse (&ptr, REG_TYPE_RN)) == FAIL)
6552 goto wanted_arm;
6553
6554 inst.operands[i].reg = val;
6555 inst.operands[i].isreg = 1;
6556 inst.operands[i].present = 1;
6557 }
6558 }
4641781c 6559 else if (parse_qfloat_immediate (&ptr, &inst.operands[i].imm) == SUCCESS)
477330fc
RM
6560 /* Case 2: VMOV<c><q>.<dt> <Qd>, #<float-imm>
6561 Case 3: VMOV<c><q>.<dt> <Dd>, #<float-imm>
6562 Case 10: VMOV.F32 <Sd>, #<imm>
6563 Case 11: VMOV.F64 <Dd>, #<imm> */
6564 inst.operands[i].immisfloat = 1;
8335d6aa
JW
6565 else if (parse_big_immediate (&ptr, i, NULL, /*allow_symbol_p=*/FALSE)
6566 == SUCCESS)
477330fc
RM
6567 /* Case 2: VMOV<c><q>.<dt> <Qd>, #<imm>
6568 Case 3: VMOV<c><q>.<dt> <Dd>, #<imm> */
6569 ;
5287ad62 6570 else
477330fc
RM
6571 {
6572 first_error (_("expected <Rm> or <Dm> or <Qm> operand"));
6573 return FAIL;
6574 }
5287ad62 6575 }
dcbf9037 6576 else if ((val = arm_reg_parse (&ptr, REG_TYPE_RN)) != FAIL)
5287ad62
JB
6577 {
6578 /* Cases 6, 7. */
6579 inst.operands[i].reg = val;
6580 inst.operands[i].isreg = 1;
6581 inst.operands[i++].present = 1;
5f4273c7 6582
5287ad62 6583 if (skip_past_comma (&ptr) == FAIL)
477330fc 6584 goto wanted_comma;
5f4273c7 6585
dcbf9037 6586 if ((val = parse_scalar (&ptr, 8, &optype)) != FAIL)
477330fc
RM
6587 {
6588 /* Case 6: VMOV<c><q>.<dt> <Rd>, <Dn[x]> */
6589 inst.operands[i].reg = val;
6590 inst.operands[i].isscalar = 1;
6591 inst.operands[i].present = 1;
6592 inst.operands[i].vectype = optype;
6593 }
dcbf9037 6594 else if ((val = arm_reg_parse (&ptr, REG_TYPE_RN)) != FAIL)
477330fc
RM
6595 {
6596 /* Case 7: VMOV<c><q> <Rd>, <Rn>, <Dm> */
6597 inst.operands[i].reg = val;
6598 inst.operands[i].isreg = 1;
6599 inst.operands[i++].present = 1;
6600
6601 if (skip_past_comma (&ptr) == FAIL)
6602 goto wanted_comma;
6603
6604 if ((val = arm_typed_reg_parse (&ptr, REG_TYPE_VFSD, &rtype, &optype))
6605 == FAIL)
6606 {
6607 first_error (_(reg_expected_msgs[REG_TYPE_VFSD]));
6608 return FAIL;
6609 }
6610
6611 inst.operands[i].reg = val;
6612 inst.operands[i].isreg = 1;
6613 inst.operands[i].isvec = 1;
6614 inst.operands[i].issingle = (rtype == REG_TYPE_VFS);
6615 inst.operands[i].vectype = optype;
6616 inst.operands[i].present = 1;
6617
6618 if (rtype == REG_TYPE_VFS)
6619 {
6620 /* Case 14. */
6621 i++;
6622 if (skip_past_comma (&ptr) == FAIL)
6623 goto wanted_comma;
6624 if ((val = arm_typed_reg_parse (&ptr, REG_TYPE_VFS, NULL,
6625 &optype)) == FAIL)
6626 {
6627 first_error (_(reg_expected_msgs[REG_TYPE_VFS]));
6628 return FAIL;
6629 }
6630 inst.operands[i].reg = val;
6631 inst.operands[i].isreg = 1;
6632 inst.operands[i].isvec = 1;
6633 inst.operands[i].issingle = 1;
6634 inst.operands[i].vectype = optype;
6635 inst.operands[i].present = 1;
6636 }
6637 }
037e8744 6638 else if ((val = arm_typed_reg_parse (&ptr, REG_TYPE_VFS, NULL, &optype))
477330fc
RM
6639 != FAIL)
6640 {
6641 /* Case 13. */
6642 inst.operands[i].reg = val;
6643 inst.operands[i].isreg = 1;
6644 inst.operands[i].isvec = 1;
6645 inst.operands[i].issingle = 1;
6646 inst.operands[i].vectype = optype;
6647 inst.operands[i].present = 1;
6648 }
5287ad62
JB
6649 }
6650 else
6651 {
dcbf9037 6652 first_error (_("parse error"));
5287ad62
JB
6653 return FAIL;
6654 }
6655
6656 /* Successfully parsed the operands. Update args. */
6657 *which_operand = i;
6658 *str = ptr;
6659 return SUCCESS;
6660
5f4273c7 6661 wanted_comma:
dcbf9037 6662 first_error (_("expected comma"));
5287ad62 6663 return FAIL;
5f4273c7
NC
6664
6665 wanted_arm:
dcbf9037 6666 first_error (_(reg_expected_msgs[REG_TYPE_RN]));
5287ad62 6667 return FAIL;
5287ad62
JB
6668}
6669
5be8be5d
DG
6670/* Use this macro when the operand constraints are different
6671 for ARM and THUMB (e.g. ldrd). */
6672#define MIX_ARM_THUMB_OPERANDS(arm_operand, thumb_operand) \
6673 ((arm_operand) | ((thumb_operand) << 16))
6674
c19d1205
ZW
6675/* Matcher codes for parse_operands. */
6676enum operand_parse_code
6677{
6678 OP_stop, /* end of line */
6679
6680 OP_RR, /* ARM register */
6681 OP_RRnpc, /* ARM register, not r15 */
5be8be5d 6682 OP_RRnpcsp, /* ARM register, neither r15 nor r13 (a.k.a. 'BadReg') */
c19d1205 6683 OP_RRnpcb, /* ARM register, not r15, in square brackets */
fa94de6b 6684 OP_RRnpctw, /* ARM register, not r15 in Thumb-state or with writeback,
55881a11 6685 optional trailing ! */
c19d1205
ZW
6686 OP_RRw, /* ARM register, not r15, optional trailing ! */
6687 OP_RCP, /* Coprocessor number */
6688 OP_RCN, /* Coprocessor register */
6689 OP_RF, /* FPA register */
6690 OP_RVS, /* VFP single precision register */
5287ad62
JB
6691 OP_RVD, /* VFP double precision register (0..15) */
6692 OP_RND, /* Neon double precision register (0..31) */
5ee91343
AV
6693 OP_RNDMQ, /* Neon double precision (0..31) or MVE vector register. */
6694 OP_RNDMQR, /* Neon double precision (0..31), MVE vector or ARM register.
6695 */
5287ad62 6696 OP_RNQ, /* Neon quad precision register */
5ee91343 6697 OP_RNQMQ, /* Neon quad or MVE vector register. */
037e8744 6698 OP_RVSD, /* VFP single or double precision register */
dec41383 6699 OP_RNSD, /* Neon single or double precision register */
5287ad62 6700 OP_RNDQ, /* Neon double or quad precision register */
5ee91343 6701 OP_RNDQMQ, /* Neon double, quad or MVE vector register. */
037e8744 6702 OP_RNSDQ, /* Neon single, double or quad precision register */
5287ad62 6703 OP_RNSC, /* Neon scalar D[X] */
c19d1205
ZW
6704 OP_RVC, /* VFP control register */
6705 OP_RMF, /* Maverick F register */
6706 OP_RMD, /* Maverick D register */
6707 OP_RMFX, /* Maverick FX register */
6708 OP_RMDX, /* Maverick DX register */
6709 OP_RMAX, /* Maverick AX register */
6710 OP_RMDS, /* Maverick DSPSC register */
6711 OP_RIWR, /* iWMMXt wR register */
6712 OP_RIWC, /* iWMMXt wC register */
6713 OP_RIWG, /* iWMMXt wCG register */
6714 OP_RXA, /* XScale accumulator register */
6715
5ee91343
AV
6716 OP_RNSDQMQ, /* Neon single, double or quad register or MVE vector register
6717 */
6718 OP_RNSDQMQR, /* Neon single, double or quad register, MVE vector register or
6719 GPR (no SP/SP) */
a302e574
AV
6720 OP_RMQ, /* MVE vector register. */
6721
60f993ce
AV
6722 /* New operands for Armv8.1-M Mainline. */
6723 OP_LR, /* ARM LR register */
a302e574
AV
6724 OP_RRe, /* ARM register, only even numbered. */
6725 OP_RRo, /* ARM register, only odd numbered, not r13 or r15. */
60f993ce
AV
6726 OP_RRnpcsp_I32, /* ARM register (no BadReg) or literal 1 .. 32 */
6727
c19d1205 6728 OP_REGLST, /* ARM register list */
4b5a202f 6729 OP_CLRMLST, /* CLRM register list */
c19d1205
ZW
6730 OP_VRSLST, /* VFP single-precision register list */
6731 OP_VRDLST, /* VFP double-precision register list */
037e8744 6732 OP_VRSDLST, /* VFP single or double-precision register list (& quad) */
5287ad62
JB
6733 OP_NRDLST, /* Neon double-precision register list (d0-d31, qN aliases) */
6734 OP_NSTRLST, /* Neon element/structure list */
efd6b359 6735 OP_VRSDVLST, /* VFP single or double-precision register list and VPR */
5287ad62 6736
5287ad62 6737 OP_RNDQ_I0, /* Neon D or Q reg, or immediate zero. */
037e8744 6738 OP_RVSD_I0, /* VFP S or D reg, or immediate zero. */
aacf0b33 6739 OP_RSVD_FI0, /* VFP S or D reg, or floating point immediate zero. */
5287ad62 6740 OP_RR_RNSC, /* ARM reg or Neon scalar. */
dec41383 6741 OP_RNSD_RNSC, /* Neon S or D reg, or Neon scalar. */
037e8744 6742 OP_RNSDQ_RNSC, /* Vector S, D or Q reg, or Neon scalar. */
5287ad62
JB
6743 OP_RNDQ_RNSC, /* Neon D or Q reg, or Neon scalar. */
6744 OP_RND_RNSC, /* Neon D reg, or Neon scalar. */
6745 OP_VMOV, /* Neon VMOV operands. */
4316f0d2 6746 OP_RNDQ_Ibig, /* Neon D or Q reg, or big immediate for logic and VMVN. */
5287ad62 6747 OP_RNDQ_I63b, /* Neon D or Q reg, or immediate for shift. */
2d447fca 6748 OP_RIWR_I32z, /* iWMMXt wR register, or immediate 0 .. 32 for iWMMXt2. */
32c36c3c 6749 OP_VLDR, /* VLDR operand. */
5287ad62
JB
6750
6751 OP_I0, /* immediate zero */
c19d1205
ZW
6752 OP_I7, /* immediate value 0 .. 7 */
6753 OP_I15, /* 0 .. 15 */
6754 OP_I16, /* 1 .. 16 */
5287ad62 6755 OP_I16z, /* 0 .. 16 */
c19d1205
ZW
6756 OP_I31, /* 0 .. 31 */
6757 OP_I31w, /* 0 .. 31, optional trailing ! */
6758 OP_I32, /* 1 .. 32 */
5287ad62
JB
6759 OP_I32z, /* 0 .. 32 */
6760 OP_I63, /* 0 .. 63 */
c19d1205 6761 OP_I63s, /* -64 .. 63 */
5287ad62
JB
6762 OP_I64, /* 1 .. 64 */
6763 OP_I64z, /* 0 .. 64 */
c19d1205 6764 OP_I255, /* 0 .. 255 */
c19d1205
ZW
6765
6766 OP_I4b, /* immediate, prefix optional, 1 .. 4 */
6767 OP_I7b, /* 0 .. 7 */
6768 OP_I15b, /* 0 .. 15 */
6769 OP_I31b, /* 0 .. 31 */
6770
6771 OP_SH, /* shifter operand */
4962c51a 6772 OP_SHG, /* shifter operand with possible group relocation */
c19d1205 6773 OP_ADDR, /* Memory address expression (any mode) */
4962c51a
MS
6774 OP_ADDRGLDR, /* Mem addr expr (any mode) with possible LDR group reloc */
6775 OP_ADDRGLDRS, /* Mem addr expr (any mode) with possible LDRS group reloc */
6776 OP_ADDRGLDC, /* Mem addr expr (any mode) with possible LDC group reloc */
c19d1205
ZW
6777 OP_EXP, /* arbitrary expression */
6778 OP_EXPi, /* same, with optional immediate prefix */
6779 OP_EXPr, /* same, with optional relocation suffix */
e2b0ab59 6780 OP_EXPs, /* same, with optional non-first operand relocation suffix */
b6895b4f 6781 OP_HALF, /* 0 .. 65535 or low/high reloc. */
c28eeff2
SN
6782 OP_IROT1, /* VCADD rotate immediate: 90, 270. */
6783 OP_IROT2, /* VCMLA rotate immediate: 0, 90, 180, 270. */
c19d1205
ZW
6784
6785 OP_CPSF, /* CPS flags */
6786 OP_ENDI, /* Endianness specifier */
d2cd1205
JB
6787 OP_wPSR, /* CPSR/SPSR/APSR mask for msr (writing). */
6788 OP_rPSR, /* CPSR/SPSR/APSR mask for msr (reading). */
c19d1205 6789 OP_COND, /* conditional code */
92e90b6e 6790 OP_TB, /* Table branch. */
c19d1205 6791
037e8744
JB
6792 OP_APSR_RR, /* ARM register or "APSR_nzcv". */
6793
c19d1205 6794 OP_RRnpc_I0, /* ARM register or literal 0 */
33eaf5de 6795 OP_RR_EXr, /* ARM register or expression with opt. reloc stuff. */
c19d1205
ZW
6796 OP_RR_EXi, /* ARM register or expression with imm prefix */
6797 OP_RF_IF, /* FPA register or immediate */
6798 OP_RIWR_RIWC, /* iWMMXt R or C reg */
41adaa5c 6799 OP_RIWC_RIWG, /* iWMMXt wC or wCG reg */
c19d1205
ZW
6800
6801 /* Optional operands. */
6802 OP_oI7b, /* immediate, prefix optional, 0 .. 7 */
6803 OP_oI31b, /* 0 .. 31 */
5287ad62 6804 OP_oI32b, /* 1 .. 32 */
5f1af56b 6805 OP_oI32z, /* 0 .. 32 */
c19d1205
ZW
6806 OP_oIffffb, /* 0 .. 65535 */
6807 OP_oI255c, /* curly-brace enclosed, 0 .. 255 */
6808
6809 OP_oRR, /* ARM register */
60f993ce 6810 OP_oLR, /* ARM LR register */
c19d1205 6811 OP_oRRnpc, /* ARM register, not the PC */
5be8be5d 6812 OP_oRRnpcsp, /* ARM register, neither the PC nor the SP (a.k.a. BadReg) */
b6702015 6813 OP_oRRw, /* ARM register, not r15, optional trailing ! */
5287ad62
JB
6814 OP_oRND, /* Optional Neon double precision register */
6815 OP_oRNQ, /* Optional Neon quad precision register */
5ee91343 6816 OP_oRNDQMQ, /* Optional Neon double, quad or MVE vector register. */
5287ad62 6817 OP_oRNDQ, /* Optional Neon double or quad precision register */
037e8744 6818 OP_oRNSDQ, /* Optional single, double or quad precision vector register */
5ee91343
AV
6819 OP_oRNSDQMQ, /* Optional single, double or quad register or MVE vector
6820 register. */
c19d1205
ZW
6821 OP_oSHll, /* LSL immediate */
6822 OP_oSHar, /* ASR immediate */
6823 OP_oSHllar, /* LSL or ASR immediate */
6824 OP_oROR, /* ROR 0/8/16/24 */
52e7f43d 6825 OP_oBARRIER_I15, /* Option argument for a barrier instruction. */
c19d1205 6826
5be8be5d
DG
6827 /* Some pre-defined mixed (ARM/THUMB) operands. */
6828 OP_RR_npcsp = MIX_ARM_THUMB_OPERANDS (OP_RR, OP_RRnpcsp),
6829 OP_RRnpc_npcsp = MIX_ARM_THUMB_OPERANDS (OP_RRnpc, OP_RRnpcsp),
6830 OP_oRRnpc_npcsp = MIX_ARM_THUMB_OPERANDS (OP_oRRnpc, OP_oRRnpcsp),
6831
c19d1205
ZW
6832 OP_FIRST_OPTIONAL = OP_oI7b
6833};
a737bd4d 6834
c19d1205
ZW
6835/* Generic instruction operand parser. This does no encoding and no
6836 semantic validation; it merely squirrels values away in the inst
6837 structure. Returns SUCCESS or FAIL depending on whether the
6838 specified grammar matched. */
6839static int
5be8be5d 6840parse_operands (char *str, const unsigned int *pattern, bfd_boolean thumb)
c19d1205 6841{
5be8be5d 6842 unsigned const int *upat = pattern;
c19d1205
ZW
6843 char *backtrack_pos = 0;
6844 const char *backtrack_error = 0;
99aad254 6845 int i, val = 0, backtrack_index = 0;
5287ad62 6846 enum arm_reg_type rtype;
4962c51a 6847 parse_operand_result result;
5be8be5d 6848 unsigned int op_parse_code;
efd6b359 6849 bfd_boolean partial_match;
c19d1205 6850
e07e6e58
NC
6851#define po_char_or_fail(chr) \
6852 do \
6853 { \
6854 if (skip_past_char (&str, chr) == FAIL) \
477330fc 6855 goto bad_args; \
e07e6e58
NC
6856 } \
6857 while (0)
c19d1205 6858
e07e6e58
NC
6859#define po_reg_or_fail(regtype) \
6860 do \
dcbf9037 6861 { \
e07e6e58 6862 val = arm_typed_reg_parse (& str, regtype, & rtype, \
477330fc 6863 & inst.operands[i].vectype); \
e07e6e58 6864 if (val == FAIL) \
477330fc
RM
6865 { \
6866 first_error (_(reg_expected_msgs[regtype])); \
6867 goto failure; \
6868 } \
e07e6e58
NC
6869 inst.operands[i].reg = val; \
6870 inst.operands[i].isreg = 1; \
6871 inst.operands[i].isquad = (rtype == REG_TYPE_NQ); \
6872 inst.operands[i].issingle = (rtype == REG_TYPE_VFS); \
6873 inst.operands[i].isvec = (rtype == REG_TYPE_VFS \
477330fc
RM
6874 || rtype == REG_TYPE_VFD \
6875 || rtype == REG_TYPE_NQ); \
dcbf9037 6876 } \
e07e6e58
NC
6877 while (0)
6878
6879#define po_reg_or_goto(regtype, label) \
6880 do \
6881 { \
6882 val = arm_typed_reg_parse (& str, regtype, & rtype, \
6883 & inst.operands[i].vectype); \
6884 if (val == FAIL) \
6885 goto label; \
dcbf9037 6886 \
e07e6e58
NC
6887 inst.operands[i].reg = val; \
6888 inst.operands[i].isreg = 1; \
6889 inst.operands[i].isquad = (rtype == REG_TYPE_NQ); \
6890 inst.operands[i].issingle = (rtype == REG_TYPE_VFS); \
6891 inst.operands[i].isvec = (rtype == REG_TYPE_VFS \
477330fc 6892 || rtype == REG_TYPE_VFD \
e07e6e58
NC
6893 || rtype == REG_TYPE_NQ); \
6894 } \
6895 while (0)
6896
6897#define po_imm_or_fail(min, max, popt) \
6898 do \
6899 { \
6900 if (parse_immediate (&str, &val, min, max, popt) == FAIL) \
6901 goto failure; \
6902 inst.operands[i].imm = val; \
6903 } \
6904 while (0)
6905
6906#define po_scalar_or_goto(elsz, label) \
6907 do \
6908 { \
6909 val = parse_scalar (& str, elsz, & inst.operands[i].vectype); \
6910 if (val == FAIL) \
6911 goto label; \
6912 inst.operands[i].reg = val; \
6913 inst.operands[i].isscalar = 1; \
6914 } \
6915 while (0)
6916
6917#define po_misc_or_fail(expr) \
6918 do \
6919 { \
6920 if (expr) \
6921 goto failure; \
6922 } \
6923 while (0)
6924
6925#define po_misc_or_fail_no_backtrack(expr) \
6926 do \
6927 { \
6928 result = expr; \
6929 if (result == PARSE_OPERAND_FAIL_NO_BACKTRACK) \
6930 backtrack_pos = 0; \
6931 if (result != PARSE_OPERAND_SUCCESS) \
6932 goto failure; \
6933 } \
6934 while (0)
4962c51a 6935
52e7f43d
RE
6936#define po_barrier_or_imm(str) \
6937 do \
6938 { \
6939 val = parse_barrier (&str); \
ccb84d65
JB
6940 if (val == FAIL && ! ISALPHA (*str)) \
6941 goto immediate; \
6942 if (val == FAIL \
6943 /* ISB can only take SY as an option. */ \
6944 || ((inst.instruction & 0xf0) == 0x60 \
6945 && val != 0xf)) \
52e7f43d 6946 { \
ccb84d65
JB
6947 inst.error = _("invalid barrier type"); \
6948 backtrack_pos = 0; \
6949 goto failure; \
52e7f43d
RE
6950 } \
6951 } \
6952 while (0)
6953
c19d1205
ZW
6954 skip_whitespace (str);
6955
6956 for (i = 0; upat[i] != OP_stop; i++)
6957 {
5be8be5d
DG
6958 op_parse_code = upat[i];
6959 if (op_parse_code >= 1<<16)
6960 op_parse_code = thumb ? (op_parse_code >> 16)
6961 : (op_parse_code & ((1<<16)-1));
6962
6963 if (op_parse_code >= OP_FIRST_OPTIONAL)
c19d1205
ZW
6964 {
6965 /* Remember where we are in case we need to backtrack. */
9c2799c2 6966 gas_assert (!backtrack_pos);
c19d1205
ZW
6967 backtrack_pos = str;
6968 backtrack_error = inst.error;
6969 backtrack_index = i;
6970 }
6971
b6702015 6972 if (i > 0 && (i > 1 || inst.operands[0].present))
c19d1205
ZW
6973 po_char_or_fail (',');
6974
5be8be5d 6975 switch (op_parse_code)
c19d1205
ZW
6976 {
6977 /* Registers */
6978 case OP_oRRnpc:
5be8be5d 6979 case OP_oRRnpcsp:
c19d1205 6980 case OP_RRnpc:
5be8be5d 6981 case OP_RRnpcsp:
c19d1205 6982 case OP_oRR:
a302e574
AV
6983 case OP_RRe:
6984 case OP_RRo:
60f993ce
AV
6985 case OP_LR:
6986 case OP_oLR:
c19d1205
ZW
6987 case OP_RR: po_reg_or_fail (REG_TYPE_RN); break;
6988 case OP_RCP: po_reg_or_fail (REG_TYPE_CP); break;
6989 case OP_RCN: po_reg_or_fail (REG_TYPE_CN); break;
6990 case OP_RF: po_reg_or_fail (REG_TYPE_FN); break;
6991 case OP_RVS: po_reg_or_fail (REG_TYPE_VFS); break;
6992 case OP_RVD: po_reg_or_fail (REG_TYPE_VFD); break;
477330fc 6993 case OP_oRND:
5ee91343
AV
6994 case OP_RNDMQR:
6995 po_reg_or_goto (REG_TYPE_RN, try_rndmq);
6996 break;
6997 try_rndmq:
6998 case OP_RNDMQ:
6999 po_reg_or_goto (REG_TYPE_MQ, try_rnd);
7000 break;
7001 try_rnd:
5287ad62 7002 case OP_RND: po_reg_or_fail (REG_TYPE_VFD); break;
cd2cf30b
PB
7003 case OP_RVC:
7004 po_reg_or_goto (REG_TYPE_VFC, coproc_reg);
7005 break;
7006 /* Also accept generic coprocessor regs for unknown registers. */
7007 coproc_reg:
7008 po_reg_or_fail (REG_TYPE_CN);
7009 break;
c19d1205
ZW
7010 case OP_RMF: po_reg_or_fail (REG_TYPE_MVF); break;
7011 case OP_RMD: po_reg_or_fail (REG_TYPE_MVD); break;
7012 case OP_RMFX: po_reg_or_fail (REG_TYPE_MVFX); break;
7013 case OP_RMDX: po_reg_or_fail (REG_TYPE_MVDX); break;
7014 case OP_RMAX: po_reg_or_fail (REG_TYPE_MVAX); break;
7015 case OP_RMDS: po_reg_or_fail (REG_TYPE_DSPSC); break;
7016 case OP_RIWR: po_reg_or_fail (REG_TYPE_MMXWR); break;
7017 case OP_RIWC: po_reg_or_fail (REG_TYPE_MMXWC); break;
7018 case OP_RIWG: po_reg_or_fail (REG_TYPE_MMXWCG); break;
7019 case OP_RXA: po_reg_or_fail (REG_TYPE_XSCALE); break;
477330fc 7020 case OP_oRNQ:
5ee91343
AV
7021 case OP_RNQMQ:
7022 po_reg_or_goto (REG_TYPE_MQ, try_nq);
7023 break;
7024 try_nq:
5287ad62 7025 case OP_RNQ: po_reg_or_fail (REG_TYPE_NQ); break;
dec41383 7026 case OP_RNSD: po_reg_or_fail (REG_TYPE_NSD); break;
5ee91343
AV
7027 case OP_oRNDQMQ:
7028 case OP_RNDQMQ:
7029 po_reg_or_goto (REG_TYPE_MQ, try_rndq);
7030 break;
7031 try_rndq:
477330fc 7032 case OP_oRNDQ:
5287ad62 7033 case OP_RNDQ: po_reg_or_fail (REG_TYPE_NDQ); break;
477330fc
RM
7034 case OP_RVSD: po_reg_or_fail (REG_TYPE_VFSD); break;
7035 case OP_oRNSDQ:
7036 case OP_RNSDQ: po_reg_or_fail (REG_TYPE_NSDQ); break;
5ee91343
AV
7037 case OP_RNSDQMQR:
7038 po_reg_or_goto (REG_TYPE_RN, try_mq);
7039 break;
7040 try_mq:
7041 case OP_oRNSDQMQ:
7042 case OP_RNSDQMQ:
7043 po_reg_or_goto (REG_TYPE_MQ, try_nsdq2);
7044 break;
7045 try_nsdq2:
7046 po_reg_or_fail (REG_TYPE_NSDQ);
7047 inst.error = 0;
7048 break;
a302e574
AV
7049 case OP_RMQ:
7050 po_reg_or_fail (REG_TYPE_MQ);
7051 break;
477330fc
RM
7052 /* Neon scalar. Using an element size of 8 means that some invalid
7053 scalars are accepted here, so deal with those in later code. */
7054 case OP_RNSC: po_scalar_or_goto (8, failure); break;
7055
7056 case OP_RNDQ_I0:
7057 {
7058 po_reg_or_goto (REG_TYPE_NDQ, try_imm0);
7059 break;
7060 try_imm0:
7061 po_imm_or_fail (0, 0, TRUE);
7062 }
7063 break;
7064
7065 case OP_RVSD_I0:
7066 po_reg_or_goto (REG_TYPE_VFSD, try_imm0);
7067 break;
7068
aacf0b33
KT
7069 case OP_RSVD_FI0:
7070 {
7071 po_reg_or_goto (REG_TYPE_VFSD, try_ifimm0);
7072 break;
7073 try_ifimm0:
7074 if (parse_ifimm_zero (&str))
7075 inst.operands[i].imm = 0;
7076 else
7077 {
7078 inst.error
7079 = _("only floating point zero is allowed as immediate value");
7080 goto failure;
7081 }
7082 }
7083 break;
7084
477330fc
RM
7085 case OP_RR_RNSC:
7086 {
7087 po_scalar_or_goto (8, try_rr);
7088 break;
7089 try_rr:
7090 po_reg_or_fail (REG_TYPE_RN);
7091 }
7092 break;
7093
7094 case OP_RNSDQ_RNSC:
7095 {
7096 po_scalar_or_goto (8, try_nsdq);
7097 break;
7098 try_nsdq:
7099 po_reg_or_fail (REG_TYPE_NSDQ);
7100 }
7101 break;
7102
dec41383
JW
7103 case OP_RNSD_RNSC:
7104 {
7105 po_scalar_or_goto (8, try_s_scalar);
7106 break;
7107 try_s_scalar:
7108 po_scalar_or_goto (4, try_nsd);
7109 break;
7110 try_nsd:
7111 po_reg_or_fail (REG_TYPE_NSD);
7112 }
7113 break;
7114
477330fc
RM
7115 case OP_RNDQ_RNSC:
7116 {
7117 po_scalar_or_goto (8, try_ndq);
7118 break;
7119 try_ndq:
7120 po_reg_or_fail (REG_TYPE_NDQ);
7121 }
7122 break;
7123
7124 case OP_RND_RNSC:
7125 {
7126 po_scalar_or_goto (8, try_vfd);
7127 break;
7128 try_vfd:
7129 po_reg_or_fail (REG_TYPE_VFD);
7130 }
7131 break;
7132
7133 case OP_VMOV:
7134 /* WARNING: parse_neon_mov can move the operand counter, i. If we're
7135 not careful then bad things might happen. */
7136 po_misc_or_fail (parse_neon_mov (&str, &i) == FAIL);
7137 break;
7138
7139 case OP_RNDQ_Ibig:
7140 {
7141 po_reg_or_goto (REG_TYPE_NDQ, try_immbig);
7142 break;
7143 try_immbig:
7144 /* There's a possibility of getting a 64-bit immediate here, so
7145 we need special handling. */
8335d6aa
JW
7146 if (parse_big_immediate (&str, i, NULL, /*allow_symbol_p=*/FALSE)
7147 == FAIL)
477330fc
RM
7148 {
7149 inst.error = _("immediate value is out of range");
7150 goto failure;
7151 }
7152 }
7153 break;
7154
7155 case OP_RNDQ_I63b:
7156 {
7157 po_reg_or_goto (REG_TYPE_NDQ, try_shimm);
7158 break;
7159 try_shimm:
7160 po_imm_or_fail (0, 63, TRUE);
7161 }
7162 break;
c19d1205
ZW
7163
7164 case OP_RRnpcb:
7165 po_char_or_fail ('[');
7166 po_reg_or_fail (REG_TYPE_RN);
7167 po_char_or_fail (']');
7168 break;
a737bd4d 7169
55881a11 7170 case OP_RRnpctw:
c19d1205 7171 case OP_RRw:
b6702015 7172 case OP_oRRw:
c19d1205
ZW
7173 po_reg_or_fail (REG_TYPE_RN);
7174 if (skip_past_char (&str, '!') == SUCCESS)
7175 inst.operands[i].writeback = 1;
7176 break;
7177
7178 /* Immediates */
7179 case OP_I7: po_imm_or_fail ( 0, 7, FALSE); break;
7180 case OP_I15: po_imm_or_fail ( 0, 15, FALSE); break;
7181 case OP_I16: po_imm_or_fail ( 1, 16, FALSE); break;
477330fc 7182 case OP_I16z: po_imm_or_fail ( 0, 16, FALSE); break;
c19d1205
ZW
7183 case OP_I31: po_imm_or_fail ( 0, 31, FALSE); break;
7184 case OP_I32: po_imm_or_fail ( 1, 32, FALSE); break;
477330fc 7185 case OP_I32z: po_imm_or_fail ( 0, 32, FALSE); break;
c19d1205 7186 case OP_I63s: po_imm_or_fail (-64, 63, FALSE); break;
477330fc
RM
7187 case OP_I63: po_imm_or_fail ( 0, 63, FALSE); break;
7188 case OP_I64: po_imm_or_fail ( 1, 64, FALSE); break;
7189 case OP_I64z: po_imm_or_fail ( 0, 64, FALSE); break;
c19d1205 7190 case OP_I255: po_imm_or_fail ( 0, 255, FALSE); break;
c19d1205
ZW
7191
7192 case OP_I4b: po_imm_or_fail ( 1, 4, TRUE); break;
7193 case OP_oI7b:
7194 case OP_I7b: po_imm_or_fail ( 0, 7, TRUE); break;
7195 case OP_I15b: po_imm_or_fail ( 0, 15, TRUE); break;
7196 case OP_oI31b:
7197 case OP_I31b: po_imm_or_fail ( 0, 31, TRUE); break;
477330fc
RM
7198 case OP_oI32b: po_imm_or_fail ( 1, 32, TRUE); break;
7199 case OP_oI32z: po_imm_or_fail ( 0, 32, TRUE); break;
c19d1205
ZW
7200 case OP_oIffffb: po_imm_or_fail ( 0, 0xffff, TRUE); break;
7201
7202 /* Immediate variants */
7203 case OP_oI255c:
7204 po_char_or_fail ('{');
7205 po_imm_or_fail (0, 255, TRUE);
7206 po_char_or_fail ('}');
7207 break;
7208
7209 case OP_I31w:
7210 /* The expression parser chokes on a trailing !, so we have
7211 to find it first and zap it. */
7212 {
7213 char *s = str;
7214 while (*s && *s != ',')
7215 s++;
7216 if (s[-1] == '!')
7217 {
7218 s[-1] = '\0';
7219 inst.operands[i].writeback = 1;
7220 }
7221 po_imm_or_fail (0, 31, TRUE);
7222 if (str == s - 1)
7223 str = s;
7224 }
7225 break;
7226
7227 /* Expressions */
7228 case OP_EXPi: EXPi:
e2b0ab59 7229 po_misc_or_fail (my_get_expression (&inst.relocs[0].exp, &str,
c19d1205
ZW
7230 GE_OPT_PREFIX));
7231 break;
7232
7233 case OP_EXP:
e2b0ab59 7234 po_misc_or_fail (my_get_expression (&inst.relocs[0].exp, &str,
c19d1205
ZW
7235 GE_NO_PREFIX));
7236 break;
7237
7238 case OP_EXPr: EXPr:
e2b0ab59 7239 po_misc_or_fail (my_get_expression (&inst.relocs[0].exp, &str,
c19d1205 7240 GE_NO_PREFIX));
e2b0ab59 7241 if (inst.relocs[0].exp.X_op == O_symbol)
a737bd4d 7242 {
c19d1205
ZW
7243 val = parse_reloc (&str);
7244 if (val == -1)
7245 {
7246 inst.error = _("unrecognized relocation suffix");
7247 goto failure;
7248 }
7249 else if (val != BFD_RELOC_UNUSED)
7250 {
7251 inst.operands[i].imm = val;
7252 inst.operands[i].hasreloc = 1;
7253 }
a737bd4d 7254 }
c19d1205 7255 break;
a737bd4d 7256
e2b0ab59
AV
7257 case OP_EXPs:
7258 po_misc_or_fail (my_get_expression (&inst.relocs[i].exp, &str,
7259 GE_NO_PREFIX));
7260 if (inst.relocs[i].exp.X_op == O_symbol)
7261 {
7262 inst.operands[i].hasreloc = 1;
7263 }
7264 else if (inst.relocs[i].exp.X_op == O_constant)
7265 {
7266 inst.operands[i].imm = inst.relocs[i].exp.X_add_number;
7267 inst.operands[i].hasreloc = 0;
7268 }
7269 break;
7270
b6895b4f
PB
7271 /* Operand for MOVW or MOVT. */
7272 case OP_HALF:
7273 po_misc_or_fail (parse_half (&str));
7274 break;
7275
e07e6e58 7276 /* Register or expression. */
c19d1205
ZW
7277 case OP_RR_EXr: po_reg_or_goto (REG_TYPE_RN, EXPr); break;
7278 case OP_RR_EXi: po_reg_or_goto (REG_TYPE_RN, EXPi); break;
a737bd4d 7279
e07e6e58 7280 /* Register or immediate. */
c19d1205
ZW
7281 case OP_RRnpc_I0: po_reg_or_goto (REG_TYPE_RN, I0); break;
7282 I0: po_imm_or_fail (0, 0, FALSE); break;
a737bd4d 7283
c19d1205
ZW
7284 case OP_RF_IF: po_reg_or_goto (REG_TYPE_FN, IF); break;
7285 IF:
7286 if (!is_immediate_prefix (*str))
7287 goto bad_args;
7288 str++;
7289 val = parse_fpa_immediate (&str);
7290 if (val == FAIL)
7291 goto failure;
7292 /* FPA immediates are encoded as registers 8-15.
7293 parse_fpa_immediate has already applied the offset. */
7294 inst.operands[i].reg = val;
7295 inst.operands[i].isreg = 1;
7296 break;
09d92015 7297
2d447fca
JM
7298 case OP_RIWR_I32z: po_reg_or_goto (REG_TYPE_MMXWR, I32z); break;
7299 I32z: po_imm_or_fail (0, 32, FALSE); break;
7300
e07e6e58 7301 /* Two kinds of register. */
c19d1205
ZW
7302 case OP_RIWR_RIWC:
7303 {
7304 struct reg_entry *rege = arm_reg_parse_multi (&str);
97f87066
JM
7305 if (!rege
7306 || (rege->type != REG_TYPE_MMXWR
7307 && rege->type != REG_TYPE_MMXWC
7308 && rege->type != REG_TYPE_MMXWCG))
c19d1205
ZW
7309 {
7310 inst.error = _("iWMMXt data or control register expected");
7311 goto failure;
7312 }
7313 inst.operands[i].reg = rege->number;
7314 inst.operands[i].isreg = (rege->type == REG_TYPE_MMXWR);
7315 }
7316 break;
09d92015 7317
41adaa5c
JM
7318 case OP_RIWC_RIWG:
7319 {
7320 struct reg_entry *rege = arm_reg_parse_multi (&str);
7321 if (!rege
7322 || (rege->type != REG_TYPE_MMXWC
7323 && rege->type != REG_TYPE_MMXWCG))
7324 {
7325 inst.error = _("iWMMXt control register expected");
7326 goto failure;
7327 }
7328 inst.operands[i].reg = rege->number;
7329 inst.operands[i].isreg = 1;
7330 }
7331 break;
7332
c19d1205
ZW
7333 /* Misc */
7334 case OP_CPSF: val = parse_cps_flags (&str); break;
7335 case OP_ENDI: val = parse_endian_specifier (&str); break;
7336 case OP_oROR: val = parse_ror (&str); break;
c19d1205 7337 case OP_COND: val = parse_cond (&str); break;
52e7f43d
RE
7338 case OP_oBARRIER_I15:
7339 po_barrier_or_imm (str); break;
7340 immediate:
7341 if (parse_immediate (&str, &val, 0, 15, TRUE) == FAIL)
477330fc 7342 goto failure;
52e7f43d 7343 break;
c19d1205 7344
fa94de6b 7345 case OP_wPSR:
d2cd1205 7346 case OP_rPSR:
90ec0d68
MGD
7347 po_reg_or_goto (REG_TYPE_RNB, try_psr);
7348 if (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_virt))
7349 {
7350 inst.error = _("Banked registers are not available with this "
7351 "architecture.");
7352 goto failure;
7353 }
7354 break;
d2cd1205
JB
7355 try_psr:
7356 val = parse_psr (&str, op_parse_code == OP_wPSR);
7357 break;
037e8744 7358
32c36c3c
AV
7359 case OP_VLDR:
7360 po_reg_or_goto (REG_TYPE_VFSD, try_sysreg);
7361 break;
7362 try_sysreg:
7363 val = parse_sys_vldr_vstr (&str);
7364 break;
7365
477330fc
RM
7366 case OP_APSR_RR:
7367 po_reg_or_goto (REG_TYPE_RN, try_apsr);
7368 break;
7369 try_apsr:
7370 /* Parse "APSR_nvzc" operand (for FMSTAT-equivalent MRS
7371 instruction). */
7372 if (strncasecmp (str, "APSR_", 5) == 0)
7373 {
7374 unsigned found = 0;
7375 str += 5;
7376 while (found < 15)
7377 switch (*str++)
7378 {
7379 case 'c': found = (found & 1) ? 16 : found | 1; break;
7380 case 'n': found = (found & 2) ? 16 : found | 2; break;
7381 case 'z': found = (found & 4) ? 16 : found | 4; break;
7382 case 'v': found = (found & 8) ? 16 : found | 8; break;
7383 default: found = 16;
7384 }
7385 if (found != 15)
7386 goto failure;
7387 inst.operands[i].isvec = 1;
f7c21dc7
NC
7388 /* APSR_nzcv is encoded in instructions as if it were the REG_PC. */
7389 inst.operands[i].reg = REG_PC;
477330fc
RM
7390 }
7391 else
7392 goto failure;
7393 break;
037e8744 7394
92e90b6e
PB
7395 case OP_TB:
7396 po_misc_or_fail (parse_tb (&str));
7397 break;
7398
e07e6e58 7399 /* Register lists. */
c19d1205 7400 case OP_REGLST:
4b5a202f 7401 val = parse_reg_list (&str, REGLIST_RN);
c19d1205
ZW
7402 if (*str == '^')
7403 {
5e0d7f77 7404 inst.operands[i].writeback = 1;
c19d1205
ZW
7405 str++;
7406 }
7407 break;
09d92015 7408
4b5a202f
AV
7409 case OP_CLRMLST:
7410 val = parse_reg_list (&str, REGLIST_CLRM);
7411 break;
7412
c19d1205 7413 case OP_VRSLST:
efd6b359
AV
7414 val = parse_vfp_reg_list (&str, &inst.operands[i].reg, REGLIST_VFP_S,
7415 &partial_match);
c19d1205 7416 break;
09d92015 7417
c19d1205 7418 case OP_VRDLST:
efd6b359
AV
7419 val = parse_vfp_reg_list (&str, &inst.operands[i].reg, REGLIST_VFP_D,
7420 &partial_match);
c19d1205 7421 break;
a737bd4d 7422
477330fc
RM
7423 case OP_VRSDLST:
7424 /* Allow Q registers too. */
7425 val = parse_vfp_reg_list (&str, &inst.operands[i].reg,
efd6b359 7426 REGLIST_NEON_D, &partial_match);
477330fc
RM
7427 if (val == FAIL)
7428 {
7429 inst.error = NULL;
7430 val = parse_vfp_reg_list (&str, &inst.operands[i].reg,
efd6b359
AV
7431 REGLIST_VFP_S, &partial_match);
7432 inst.operands[i].issingle = 1;
7433 }
7434 break;
7435
7436 case OP_VRSDVLST:
7437 val = parse_vfp_reg_list (&str, &inst.operands[i].reg,
7438 REGLIST_VFP_D_VPR, &partial_match);
7439 if (val == FAIL && !partial_match)
7440 {
7441 inst.error = NULL;
7442 val = parse_vfp_reg_list (&str, &inst.operands[i].reg,
7443 REGLIST_VFP_S_VPR, &partial_match);
477330fc
RM
7444 inst.operands[i].issingle = 1;
7445 }
7446 break;
7447
7448 case OP_NRDLST:
7449 val = parse_vfp_reg_list (&str, &inst.operands[i].reg,
efd6b359 7450 REGLIST_NEON_D, &partial_match);
477330fc 7451 break;
5287ad62
JB
7452
7453 case OP_NSTRLST:
477330fc
RM
7454 val = parse_neon_el_struct_list (&str, &inst.operands[i].reg,
7455 &inst.operands[i].vectype);
7456 break;
5287ad62 7457
c19d1205
ZW
7458 /* Addressing modes */
7459 case OP_ADDR:
7460 po_misc_or_fail (parse_address (&str, i));
7461 break;
09d92015 7462
4962c51a
MS
7463 case OP_ADDRGLDR:
7464 po_misc_or_fail_no_backtrack (
477330fc 7465 parse_address_group_reloc (&str, i, GROUP_LDR));
4962c51a
MS
7466 break;
7467
7468 case OP_ADDRGLDRS:
7469 po_misc_or_fail_no_backtrack (
477330fc 7470 parse_address_group_reloc (&str, i, GROUP_LDRS));
4962c51a
MS
7471 break;
7472
7473 case OP_ADDRGLDC:
7474 po_misc_or_fail_no_backtrack (
477330fc 7475 parse_address_group_reloc (&str, i, GROUP_LDC));
4962c51a
MS
7476 break;
7477
c19d1205
ZW
7478 case OP_SH:
7479 po_misc_or_fail (parse_shifter_operand (&str, i));
7480 break;
09d92015 7481
4962c51a
MS
7482 case OP_SHG:
7483 po_misc_or_fail_no_backtrack (
477330fc 7484 parse_shifter_operand_group_reloc (&str, i));
4962c51a
MS
7485 break;
7486
c19d1205
ZW
7487 case OP_oSHll:
7488 po_misc_or_fail (parse_shift (&str, i, SHIFT_LSL_IMMEDIATE));
7489 break;
09d92015 7490
c19d1205
ZW
7491 case OP_oSHar:
7492 po_misc_or_fail (parse_shift (&str, i, SHIFT_ASR_IMMEDIATE));
7493 break;
09d92015 7494
c19d1205
ZW
7495 case OP_oSHllar:
7496 po_misc_or_fail (parse_shift (&str, i, SHIFT_LSL_OR_ASR_IMMEDIATE));
7497 break;
09d92015 7498
c19d1205 7499 default:
5be8be5d 7500 as_fatal (_("unhandled operand code %d"), op_parse_code);
c19d1205 7501 }
09d92015 7502
c19d1205
ZW
7503 /* Various value-based sanity checks and shared operations. We
7504 do not signal immediate failures for the register constraints;
7505 this allows a syntax error to take precedence. */
5be8be5d 7506 switch (op_parse_code)
c19d1205
ZW
7507 {
7508 case OP_oRRnpc:
7509 case OP_RRnpc:
7510 case OP_RRnpcb:
7511 case OP_RRw:
b6702015 7512 case OP_oRRw:
c19d1205
ZW
7513 case OP_RRnpc_I0:
7514 if (inst.operands[i].isreg && inst.operands[i].reg == REG_PC)
7515 inst.error = BAD_PC;
7516 break;
09d92015 7517
5be8be5d
DG
7518 case OP_oRRnpcsp:
7519 case OP_RRnpcsp:
7520 if (inst.operands[i].isreg)
7521 {
7522 if (inst.operands[i].reg == REG_PC)
7523 inst.error = BAD_PC;
5c8ed6a4
JW
7524 else if (inst.operands[i].reg == REG_SP
7525 /* The restriction on Rd/Rt/Rt2 on Thumb mode has been
7526 relaxed since ARMv8-A. */
7527 && !ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v8))
7528 {
7529 gas_assert (thumb);
7530 inst.error = BAD_SP;
7531 }
5be8be5d
DG
7532 }
7533 break;
7534
55881a11 7535 case OP_RRnpctw:
fa94de6b
RM
7536 if (inst.operands[i].isreg
7537 && inst.operands[i].reg == REG_PC
55881a11
MGD
7538 && (inst.operands[i].writeback || thumb))
7539 inst.error = BAD_PC;
7540 break;
7541
32c36c3c
AV
7542 case OP_VLDR:
7543 if (inst.operands[i].isreg)
7544 break;
7545 /* fall through. */
c19d1205
ZW
7546 case OP_CPSF:
7547 case OP_ENDI:
7548 case OP_oROR:
d2cd1205
JB
7549 case OP_wPSR:
7550 case OP_rPSR:
c19d1205 7551 case OP_COND:
52e7f43d 7552 case OP_oBARRIER_I15:
c19d1205 7553 case OP_REGLST:
4b5a202f 7554 case OP_CLRMLST:
c19d1205
ZW
7555 case OP_VRSLST:
7556 case OP_VRDLST:
477330fc 7557 case OP_VRSDLST:
efd6b359 7558 case OP_VRSDVLST:
477330fc
RM
7559 case OP_NRDLST:
7560 case OP_NSTRLST:
c19d1205
ZW
7561 if (val == FAIL)
7562 goto failure;
7563 inst.operands[i].imm = val;
7564 break;
a737bd4d 7565
60f993ce
AV
7566 case OP_LR:
7567 case OP_oLR:
7568 if (inst.operands[i].reg != REG_LR)
7569 inst.error = _("operand must be LR register");
7570 break;
7571
a302e574
AV
7572 case OP_RRe:
7573 if (inst.operands[i].isreg
7574 && (inst.operands[i].reg & 0x00000001) != 0)
7575 inst.error = BAD_ODD;
7576 break;
7577
7578 case OP_RRo:
7579 if (inst.operands[i].isreg)
7580 {
7581 if ((inst.operands[i].reg & 0x00000001) != 1)
7582 inst.error = BAD_EVEN;
7583 else if (inst.operands[i].reg == REG_SP)
7584 as_tsktsk (MVE_BAD_SP);
7585 else if (inst.operands[i].reg == REG_PC)
7586 inst.error = BAD_PC;
7587 }
7588 break;
7589
c19d1205
ZW
7590 default:
7591 break;
7592 }
09d92015 7593
c19d1205
ZW
7594 /* If we get here, this operand was successfully parsed. */
7595 inst.operands[i].present = 1;
7596 continue;
09d92015 7597
c19d1205 7598 bad_args:
09d92015 7599 inst.error = BAD_ARGS;
c19d1205
ZW
7600
7601 failure:
7602 if (!backtrack_pos)
d252fdde
PB
7603 {
7604 /* The parse routine should already have set inst.error, but set a
5f4273c7 7605 default here just in case. */
d252fdde 7606 if (!inst.error)
5ee91343 7607 inst.error = BAD_SYNTAX;
d252fdde
PB
7608 return FAIL;
7609 }
c19d1205
ZW
7610
7611 /* Do not backtrack over a trailing optional argument that
7612 absorbed some text. We will only fail again, with the
7613 'garbage following instruction' error message, which is
7614 probably less helpful than the current one. */
7615 if (backtrack_index == i && backtrack_pos != str
7616 && upat[i+1] == OP_stop)
d252fdde
PB
7617 {
7618 if (!inst.error)
5ee91343 7619 inst.error = BAD_SYNTAX;
d252fdde
PB
7620 return FAIL;
7621 }
c19d1205
ZW
7622
7623 /* Try again, skipping the optional argument at backtrack_pos. */
7624 str = backtrack_pos;
7625 inst.error = backtrack_error;
7626 inst.operands[backtrack_index].present = 0;
7627 i = backtrack_index;
7628 backtrack_pos = 0;
09d92015 7629 }
09d92015 7630
c19d1205
ZW
7631 /* Check that we have parsed all the arguments. */
7632 if (*str != '\0' && !inst.error)
7633 inst.error = _("garbage following instruction");
09d92015 7634
c19d1205 7635 return inst.error ? FAIL : SUCCESS;
09d92015
MM
7636}
7637
c19d1205
ZW
7638#undef po_char_or_fail
7639#undef po_reg_or_fail
7640#undef po_reg_or_goto
7641#undef po_imm_or_fail
5287ad62 7642#undef po_scalar_or_fail
52e7f43d 7643#undef po_barrier_or_imm
e07e6e58 7644
c19d1205 7645/* Shorthand macro for instruction encoding functions issuing errors. */
e07e6e58
NC
7646#define constraint(expr, err) \
7647 do \
c19d1205 7648 { \
e07e6e58
NC
7649 if (expr) \
7650 { \
7651 inst.error = err; \
7652 return; \
7653 } \
c19d1205 7654 } \
e07e6e58 7655 while (0)
c19d1205 7656
fdfde340
JM
7657/* Reject "bad registers" for Thumb-2 instructions. Many Thumb-2
7658 instructions are unpredictable if these registers are used. This
5c8ed6a4
JW
7659 is the BadReg predicate in ARM's Thumb-2 documentation.
7660
7661 Before ARMv8-A, REG_PC and REG_SP were not allowed in quite a few
7662 places, while the restriction on REG_SP was relaxed since ARMv8-A. */
7663#define reject_bad_reg(reg) \
7664 do \
7665 if (reg == REG_PC) \
7666 { \
7667 inst.error = BAD_PC; \
7668 return; \
7669 } \
7670 else if (reg == REG_SP \
7671 && !ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v8)) \
7672 { \
7673 inst.error = BAD_SP; \
7674 return; \
7675 } \
fdfde340
JM
7676 while (0)
7677
94206790
MM
7678/* If REG is R13 (the stack pointer), warn that its use is
7679 deprecated. */
7680#define warn_deprecated_sp(reg) \
7681 do \
7682 if (warn_on_deprecated && reg == REG_SP) \
5c3696f8 7683 as_tsktsk (_("use of r13 is deprecated")); \
94206790
MM
7684 while (0)
7685
c19d1205
ZW
7686/* Functions for operand encoding. ARM, then Thumb. */
7687
d840c081 7688#define rotate_left(v, n) (v << (n & 31) | v >> ((32 - n) & 31))
c19d1205 7689
9db2f6b4
RL
7690/* If the current inst is scalar ARMv8.2 fp16 instruction, do special encoding.
7691
7692 The only binary encoding difference is the Coprocessor number. Coprocessor
7693 9 is used for half-precision calculations or conversions. The format of the
2b0f3761 7694 instruction is the same as the equivalent Coprocessor 10 instruction that
9db2f6b4
RL
7695 exists for Single-Precision operation. */
7696
7697static void
7698do_scalar_fp16_v82_encode (void)
7699{
5ee91343 7700 if (inst.cond < COND_ALWAYS)
9db2f6b4
RL
7701 as_warn (_("ARMv8.2 scalar fp16 instruction cannot be conditional,"
7702 " the behaviour is UNPREDICTABLE"));
7703 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_fp16),
7704 _(BAD_FP16));
7705
7706 inst.instruction = (inst.instruction & 0xfffff0ff) | 0x900;
7707 mark_feature_used (&arm_ext_fp16);
7708}
7709
c19d1205
ZW
7710/* If VAL can be encoded in the immediate field of an ARM instruction,
7711 return the encoded form. Otherwise, return FAIL. */
7712
7713static unsigned int
7714encode_arm_immediate (unsigned int val)
09d92015 7715{
c19d1205
ZW
7716 unsigned int a, i;
7717
4f1d6205
L
7718 if (val <= 0xff)
7719 return val;
7720
7721 for (i = 2; i < 32; i += 2)
c19d1205
ZW
7722 if ((a = rotate_left (val, i)) <= 0xff)
7723 return a | (i << 7); /* 12-bit pack: [shift-cnt,const]. */
7724
7725 return FAIL;
09d92015
MM
7726}
7727
c19d1205
ZW
7728/* If VAL can be encoded in the immediate field of a Thumb32 instruction,
7729 return the encoded form. Otherwise, return FAIL. */
7730static unsigned int
7731encode_thumb32_immediate (unsigned int val)
09d92015 7732{
c19d1205 7733 unsigned int a, i;
09d92015 7734
9c3c69f2 7735 if (val <= 0xff)
c19d1205 7736 return val;
a737bd4d 7737
9c3c69f2 7738 for (i = 1; i <= 24; i++)
09d92015 7739 {
9c3c69f2
PB
7740 a = val >> i;
7741 if ((val & ~(0xff << i)) == 0)
7742 return ((val >> i) & 0x7f) | ((32 - i) << 7);
09d92015 7743 }
a737bd4d 7744
c19d1205
ZW
7745 a = val & 0xff;
7746 if (val == ((a << 16) | a))
7747 return 0x100 | a;
7748 if (val == ((a << 24) | (a << 16) | (a << 8) | a))
7749 return 0x300 | a;
09d92015 7750
c19d1205
ZW
7751 a = val & 0xff00;
7752 if (val == ((a << 16) | a))
7753 return 0x200 | (a >> 8);
a737bd4d 7754
c19d1205 7755 return FAIL;
09d92015 7756}
5287ad62 7757/* Encode a VFP SP or DP register number into inst.instruction. */
09d92015
MM
7758
7759static void
5287ad62
JB
7760encode_arm_vfp_reg (int reg, enum vfp_reg_pos pos)
7761{
7762 if ((pos == VFP_REG_Dd || pos == VFP_REG_Dn || pos == VFP_REG_Dm)
7763 && reg > 15)
7764 {
b1cc4aeb 7765 if (ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_d32))
477330fc
RM
7766 {
7767 if (thumb_mode)
7768 ARM_MERGE_FEATURE_SETS (thumb_arch_used, thumb_arch_used,
7769 fpu_vfp_ext_d32);
7770 else
7771 ARM_MERGE_FEATURE_SETS (arm_arch_used, arm_arch_used,
7772 fpu_vfp_ext_d32);
7773 }
5287ad62 7774 else
477330fc
RM
7775 {
7776 first_error (_("D register out of range for selected VFP version"));
7777 return;
7778 }
5287ad62
JB
7779 }
7780
c19d1205 7781 switch (pos)
09d92015 7782 {
c19d1205
ZW
7783 case VFP_REG_Sd:
7784 inst.instruction |= ((reg >> 1) << 12) | ((reg & 1) << 22);
7785 break;
7786
7787 case VFP_REG_Sn:
7788 inst.instruction |= ((reg >> 1) << 16) | ((reg & 1) << 7);
7789 break;
7790
7791 case VFP_REG_Sm:
7792 inst.instruction |= ((reg >> 1) << 0) | ((reg & 1) << 5);
7793 break;
7794
5287ad62
JB
7795 case VFP_REG_Dd:
7796 inst.instruction |= ((reg & 15) << 12) | ((reg >> 4) << 22);
7797 break;
5f4273c7 7798
5287ad62
JB
7799 case VFP_REG_Dn:
7800 inst.instruction |= ((reg & 15) << 16) | ((reg >> 4) << 7);
7801 break;
5f4273c7 7802
5287ad62
JB
7803 case VFP_REG_Dm:
7804 inst.instruction |= (reg & 15) | ((reg >> 4) << 5);
7805 break;
7806
c19d1205
ZW
7807 default:
7808 abort ();
09d92015 7809 }
09d92015
MM
7810}
7811
c19d1205 7812/* Encode a <shift> in an ARM-format instruction. The immediate,
55cf6793 7813 if any, is handled by md_apply_fix. */
09d92015 7814static void
c19d1205 7815encode_arm_shift (int i)
09d92015 7816{
008a97ef
RL
7817 /* register-shifted register. */
7818 if (inst.operands[i].immisreg)
7819 {
bf355b69
MR
7820 int op_index;
7821 for (op_index = 0; op_index <= i; ++op_index)
008a97ef 7822 {
5689c942
RL
7823 /* Check the operand only when it's presented. In pre-UAL syntax,
7824 if the destination register is the same as the first operand, two
7825 register form of the instruction can be used. */
bf355b69
MR
7826 if (inst.operands[op_index].present && inst.operands[op_index].isreg
7827 && inst.operands[op_index].reg == REG_PC)
008a97ef
RL
7828 as_warn (UNPRED_REG ("r15"));
7829 }
7830
7831 if (inst.operands[i].imm == REG_PC)
7832 as_warn (UNPRED_REG ("r15"));
7833 }
7834
c19d1205
ZW
7835 if (inst.operands[i].shift_kind == SHIFT_RRX)
7836 inst.instruction |= SHIFT_ROR << 5;
7837 else
09d92015 7838 {
c19d1205
ZW
7839 inst.instruction |= inst.operands[i].shift_kind << 5;
7840 if (inst.operands[i].immisreg)
7841 {
7842 inst.instruction |= SHIFT_BY_REG;
7843 inst.instruction |= inst.operands[i].imm << 8;
7844 }
7845 else
e2b0ab59 7846 inst.relocs[0].type = BFD_RELOC_ARM_SHIFT_IMM;
09d92015 7847 }
c19d1205 7848}
09d92015 7849
c19d1205
ZW
7850static void
7851encode_arm_shifter_operand (int i)
7852{
7853 if (inst.operands[i].isreg)
09d92015 7854 {
c19d1205
ZW
7855 inst.instruction |= inst.operands[i].reg;
7856 encode_arm_shift (i);
09d92015 7857 }
c19d1205 7858 else
a415b1cd
JB
7859 {
7860 inst.instruction |= INST_IMMEDIATE;
e2b0ab59 7861 if (inst.relocs[0].type != BFD_RELOC_ARM_IMMEDIATE)
a415b1cd
JB
7862 inst.instruction |= inst.operands[i].imm;
7863 }
09d92015
MM
7864}
7865
c19d1205 7866/* Subroutine of encode_arm_addr_mode_2 and encode_arm_addr_mode_3. */
09d92015 7867static void
c19d1205 7868encode_arm_addr_mode_common (int i, bfd_boolean is_t)
09d92015 7869{
2b2f5df9
NC
7870 /* PR 14260:
7871 Generate an error if the operand is not a register. */
7872 constraint (!inst.operands[i].isreg,
7873 _("Instruction does not support =N addresses"));
7874
c19d1205 7875 inst.instruction |= inst.operands[i].reg << 16;
a737bd4d 7876
c19d1205 7877 if (inst.operands[i].preind)
09d92015 7878 {
c19d1205
ZW
7879 if (is_t)
7880 {
7881 inst.error = _("instruction does not accept preindexed addressing");
7882 return;
7883 }
7884 inst.instruction |= PRE_INDEX;
7885 if (inst.operands[i].writeback)
7886 inst.instruction |= WRITE_BACK;
09d92015 7887
c19d1205
ZW
7888 }
7889 else if (inst.operands[i].postind)
7890 {
9c2799c2 7891 gas_assert (inst.operands[i].writeback);
c19d1205
ZW
7892 if (is_t)
7893 inst.instruction |= WRITE_BACK;
7894 }
7895 else /* unindexed - only for coprocessor */
09d92015 7896 {
c19d1205 7897 inst.error = _("instruction does not accept unindexed addressing");
09d92015
MM
7898 return;
7899 }
7900
c19d1205
ZW
7901 if (((inst.instruction & WRITE_BACK) || !(inst.instruction & PRE_INDEX))
7902 && (((inst.instruction & 0x000f0000) >> 16)
7903 == ((inst.instruction & 0x0000f000) >> 12)))
7904 as_warn ((inst.instruction & LOAD_BIT)
7905 ? _("destination register same as write-back base")
7906 : _("source register same as write-back base"));
09d92015
MM
7907}
7908
c19d1205
ZW
7909/* inst.operands[i] was set up by parse_address. Encode it into an
7910 ARM-format mode 2 load or store instruction. If is_t is true,
7911 reject forms that cannot be used with a T instruction (i.e. not
7912 post-indexed). */
a737bd4d 7913static void
c19d1205 7914encode_arm_addr_mode_2 (int i, bfd_boolean is_t)
09d92015 7915{
5be8be5d
DG
7916 const bfd_boolean is_pc = (inst.operands[i].reg == REG_PC);
7917
c19d1205 7918 encode_arm_addr_mode_common (i, is_t);
a737bd4d 7919
c19d1205 7920 if (inst.operands[i].immisreg)
09d92015 7921 {
5be8be5d
DG
7922 constraint ((inst.operands[i].imm == REG_PC
7923 || (is_pc && inst.operands[i].writeback)),
7924 BAD_PC_ADDRESSING);
c19d1205
ZW
7925 inst.instruction |= INST_IMMEDIATE; /* yes, this is backwards */
7926 inst.instruction |= inst.operands[i].imm;
7927 if (!inst.operands[i].negative)
7928 inst.instruction |= INDEX_UP;
7929 if (inst.operands[i].shifted)
7930 {
7931 if (inst.operands[i].shift_kind == SHIFT_RRX)
7932 inst.instruction |= SHIFT_ROR << 5;
7933 else
7934 {
7935 inst.instruction |= inst.operands[i].shift_kind << 5;
e2b0ab59 7936 inst.relocs[0].type = BFD_RELOC_ARM_SHIFT_IMM;
c19d1205
ZW
7937 }
7938 }
09d92015 7939 }
e2b0ab59 7940 else /* immediate offset in inst.relocs[0] */
09d92015 7941 {
e2b0ab59 7942 if (is_pc && !inst.relocs[0].pc_rel)
5be8be5d
DG
7943 {
7944 const bfd_boolean is_load = ((inst.instruction & LOAD_BIT) != 0);
23a10334
JZ
7945
7946 /* If is_t is TRUE, it's called from do_ldstt. ldrt/strt
7947 cannot use PC in addressing.
7948 PC cannot be used in writeback addressing, either. */
7949 constraint ((is_t || inst.operands[i].writeback),
5be8be5d 7950 BAD_PC_ADDRESSING);
23a10334 7951
dc5ec521 7952 /* Use of PC in str is deprecated for ARMv7. */
23a10334
JZ
7953 if (warn_on_deprecated
7954 && !is_load
7955 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v7))
5c3696f8 7956 as_tsktsk (_("use of PC in this instruction is deprecated"));
5be8be5d
DG
7957 }
7958
e2b0ab59 7959 if (inst.relocs[0].type == BFD_RELOC_UNUSED)
26d97720
NS
7960 {
7961 /* Prefer + for zero encoded value. */
7962 if (!inst.operands[i].negative)
7963 inst.instruction |= INDEX_UP;
e2b0ab59 7964 inst.relocs[0].type = BFD_RELOC_ARM_OFFSET_IMM;
26d97720 7965 }
09d92015 7966 }
09d92015
MM
7967}
7968
c19d1205
ZW
7969/* inst.operands[i] was set up by parse_address. Encode it into an
7970 ARM-format mode 3 load or store instruction. Reject forms that
7971 cannot be used with such instructions. If is_t is true, reject
7972 forms that cannot be used with a T instruction (i.e. not
7973 post-indexed). */
7974static void
7975encode_arm_addr_mode_3 (int i, bfd_boolean is_t)
09d92015 7976{
c19d1205 7977 if (inst.operands[i].immisreg && inst.operands[i].shifted)
09d92015 7978 {
c19d1205
ZW
7979 inst.error = _("instruction does not accept scaled register index");
7980 return;
09d92015 7981 }
a737bd4d 7982
c19d1205 7983 encode_arm_addr_mode_common (i, is_t);
a737bd4d 7984
c19d1205
ZW
7985 if (inst.operands[i].immisreg)
7986 {
5be8be5d 7987 constraint ((inst.operands[i].imm == REG_PC
eb9f3f00 7988 || (is_t && inst.operands[i].reg == REG_PC)),
5be8be5d 7989 BAD_PC_ADDRESSING);
eb9f3f00
JB
7990 constraint (inst.operands[i].reg == REG_PC && inst.operands[i].writeback,
7991 BAD_PC_WRITEBACK);
c19d1205
ZW
7992 inst.instruction |= inst.operands[i].imm;
7993 if (!inst.operands[i].negative)
7994 inst.instruction |= INDEX_UP;
7995 }
e2b0ab59 7996 else /* immediate offset in inst.relocs[0] */
c19d1205 7997 {
e2b0ab59 7998 constraint ((inst.operands[i].reg == REG_PC && !inst.relocs[0].pc_rel
5be8be5d
DG
7999 && inst.operands[i].writeback),
8000 BAD_PC_WRITEBACK);
c19d1205 8001 inst.instruction |= HWOFFSET_IMM;
e2b0ab59 8002 if (inst.relocs[0].type == BFD_RELOC_UNUSED)
26d97720
NS
8003 {
8004 /* Prefer + for zero encoded value. */
8005 if (!inst.operands[i].negative)
8006 inst.instruction |= INDEX_UP;
8007
e2b0ab59 8008 inst.relocs[0].type = BFD_RELOC_ARM_OFFSET_IMM8;
26d97720 8009 }
c19d1205 8010 }
a737bd4d
NC
8011}
8012
8335d6aa
JW
8013/* Write immediate bits [7:0] to the following locations:
8014
8015 |28/24|23 19|18 16|15 4|3 0|
8016 | a |x x x x x|b c d|x x x x x x x x x x x x|e f g h|
8017
8018 This function is used by VMOV/VMVN/VORR/VBIC. */
8019
8020static void
8021neon_write_immbits (unsigned immbits)
8022{
8023 inst.instruction |= immbits & 0xf;
8024 inst.instruction |= ((immbits >> 4) & 0x7) << 16;
8025 inst.instruction |= ((immbits >> 7) & 0x1) << (thumb_mode ? 28 : 24);
8026}
8027
8028/* Invert low-order SIZE bits of XHI:XLO. */
8029
8030static void
8031neon_invert_size (unsigned *xlo, unsigned *xhi, int size)
8032{
8033 unsigned immlo = xlo ? *xlo : 0;
8034 unsigned immhi = xhi ? *xhi : 0;
8035
8036 switch (size)
8037 {
8038 case 8:
8039 immlo = (~immlo) & 0xff;
8040 break;
8041
8042 case 16:
8043 immlo = (~immlo) & 0xffff;
8044 break;
8045
8046 case 64:
8047 immhi = (~immhi) & 0xffffffff;
8048 /* fall through. */
8049
8050 case 32:
8051 immlo = (~immlo) & 0xffffffff;
8052 break;
8053
8054 default:
8055 abort ();
8056 }
8057
8058 if (xlo)
8059 *xlo = immlo;
8060
8061 if (xhi)
8062 *xhi = immhi;
8063}
8064
8065/* True if IMM has form 0bAAAAAAAABBBBBBBBCCCCCCCCDDDDDDDD for bits
8066 A, B, C, D. */
09d92015 8067
c19d1205 8068static int
8335d6aa 8069neon_bits_same_in_bytes (unsigned imm)
09d92015 8070{
8335d6aa
JW
8071 return ((imm & 0x000000ff) == 0 || (imm & 0x000000ff) == 0x000000ff)
8072 && ((imm & 0x0000ff00) == 0 || (imm & 0x0000ff00) == 0x0000ff00)
8073 && ((imm & 0x00ff0000) == 0 || (imm & 0x00ff0000) == 0x00ff0000)
8074 && ((imm & 0xff000000) == 0 || (imm & 0xff000000) == 0xff000000);
8075}
a737bd4d 8076
8335d6aa 8077/* For immediate of above form, return 0bABCD. */
09d92015 8078
8335d6aa
JW
8079static unsigned
8080neon_squash_bits (unsigned imm)
8081{
8082 return (imm & 0x01) | ((imm & 0x0100) >> 7) | ((imm & 0x010000) >> 14)
8083 | ((imm & 0x01000000) >> 21);
8084}
8085
8086/* Compress quarter-float representation to 0b...000 abcdefgh. */
8087
8088static unsigned
8089neon_qfloat_bits (unsigned imm)
8090{
8091 return ((imm >> 19) & 0x7f) | ((imm >> 24) & 0x80);
8092}
8093
8094/* Returns CMODE. IMMBITS [7:0] is set to bits suitable for inserting into
8095 the instruction. *OP is passed as the initial value of the op field, and
8096 may be set to a different value depending on the constant (i.e.
8097 "MOV I64, 0bAAAAAAAABBBB..." which uses OP = 1 despite being MOV not
8098 MVN). If the immediate looks like a repeated pattern then also
8099 try smaller element sizes. */
8100
8101static int
8102neon_cmode_for_move_imm (unsigned immlo, unsigned immhi, int float_p,
8103 unsigned *immbits, int *op, int size,
8104 enum neon_el_type type)
8105{
8106 /* Only permit float immediates (including 0.0/-0.0) if the operand type is
8107 float. */
8108 if (type == NT_float && !float_p)
8109 return FAIL;
8110
8111 if (type == NT_float && is_quarter_float (immlo) && immhi == 0)
09d92015 8112 {
8335d6aa
JW
8113 if (size != 32 || *op == 1)
8114 return FAIL;
8115 *immbits = neon_qfloat_bits (immlo);
8116 return 0xf;
8117 }
8118
8119 if (size == 64)
8120 {
8121 if (neon_bits_same_in_bytes (immhi)
8122 && neon_bits_same_in_bytes (immlo))
c19d1205 8123 {
8335d6aa
JW
8124 if (*op == 1)
8125 return FAIL;
8126 *immbits = (neon_squash_bits (immhi) << 4)
8127 | neon_squash_bits (immlo);
8128 *op = 1;
8129 return 0xe;
c19d1205 8130 }
a737bd4d 8131
8335d6aa
JW
8132 if (immhi != immlo)
8133 return FAIL;
8134 }
a737bd4d 8135
8335d6aa 8136 if (size >= 32)
09d92015 8137 {
8335d6aa 8138 if (immlo == (immlo & 0x000000ff))
c19d1205 8139 {
8335d6aa
JW
8140 *immbits = immlo;
8141 return 0x0;
c19d1205 8142 }
8335d6aa 8143 else if (immlo == (immlo & 0x0000ff00))
c19d1205 8144 {
8335d6aa
JW
8145 *immbits = immlo >> 8;
8146 return 0x2;
c19d1205 8147 }
8335d6aa
JW
8148 else if (immlo == (immlo & 0x00ff0000))
8149 {
8150 *immbits = immlo >> 16;
8151 return 0x4;
8152 }
8153 else if (immlo == (immlo & 0xff000000))
8154 {
8155 *immbits = immlo >> 24;
8156 return 0x6;
8157 }
8158 else if (immlo == ((immlo & 0x0000ff00) | 0x000000ff))
8159 {
8160 *immbits = (immlo >> 8) & 0xff;
8161 return 0xc;
8162 }
8163 else if (immlo == ((immlo & 0x00ff0000) | 0x0000ffff))
8164 {
8165 *immbits = (immlo >> 16) & 0xff;
8166 return 0xd;
8167 }
8168
8169 if ((immlo & 0xffff) != (immlo >> 16))
8170 return FAIL;
8171 immlo &= 0xffff;
09d92015 8172 }
a737bd4d 8173
8335d6aa 8174 if (size >= 16)
4962c51a 8175 {
8335d6aa
JW
8176 if (immlo == (immlo & 0x000000ff))
8177 {
8178 *immbits = immlo;
8179 return 0x8;
8180 }
8181 else if (immlo == (immlo & 0x0000ff00))
8182 {
8183 *immbits = immlo >> 8;
8184 return 0xa;
8185 }
8186
8187 if ((immlo & 0xff) != (immlo >> 8))
8188 return FAIL;
8189 immlo &= 0xff;
4962c51a
MS
8190 }
8191
8335d6aa
JW
8192 if (immlo == (immlo & 0x000000ff))
8193 {
8194 /* Don't allow MVN with 8-bit immediate. */
8195 if (*op == 1)
8196 return FAIL;
8197 *immbits = immlo;
8198 return 0xe;
8199 }
26d97720 8200
8335d6aa 8201 return FAIL;
c19d1205 8202}
a737bd4d 8203
5fc177c8 8204#if defined BFD_HOST_64_BIT
ba592044
AM
8205/* Returns TRUE if double precision value V may be cast
8206 to single precision without loss of accuracy. */
8207
8208static bfd_boolean
5fc177c8 8209is_double_a_single (bfd_int64_t v)
ba592044 8210{
5fc177c8 8211 int exp = (int)((v >> 52) & 0x7FF);
8fe3f3d6 8212 bfd_int64_t mantissa = (v & (bfd_int64_t)0xFFFFFFFFFFFFFULL);
ba592044
AM
8213
8214 return (exp == 0 || exp == 0x7FF
8215 || (exp >= 1023 - 126 && exp <= 1023 + 127))
8216 && (mantissa & 0x1FFFFFFFl) == 0;
8217}
8218
3739860c 8219/* Returns a double precision value casted to single precision
ba592044
AM
8220 (ignoring the least significant bits in exponent and mantissa). */
8221
8222static int
5fc177c8 8223double_to_single (bfd_int64_t v)
ba592044
AM
8224{
8225 int sign = (int) ((v >> 63) & 1l);
5fc177c8 8226 int exp = (int) ((v >> 52) & 0x7FF);
8fe3f3d6 8227 bfd_int64_t mantissa = (v & (bfd_int64_t)0xFFFFFFFFFFFFFULL);
ba592044
AM
8228
8229 if (exp == 0x7FF)
8230 exp = 0xFF;
8231 else
8232 {
8233 exp = exp - 1023 + 127;
8234 if (exp >= 0xFF)
8235 {
8236 /* Infinity. */
8237 exp = 0x7F;
8238 mantissa = 0;
8239 }
8240 else if (exp < 0)
8241 {
8242 /* No denormalized numbers. */
8243 exp = 0;
8244 mantissa = 0;
8245 }
8246 }
8247 mantissa >>= 29;
8248 return (sign << 31) | (exp << 23) | mantissa;
8249}
5fc177c8 8250#endif /* BFD_HOST_64_BIT */
ba592044 8251
8335d6aa
JW
8252enum lit_type
8253{
8254 CONST_THUMB,
8255 CONST_ARM,
8256 CONST_VEC
8257};
8258
ba592044
AM
8259static void do_vfp_nsyn_opcode (const char *);
8260
e2b0ab59 8261/* inst.relocs[0].exp describes an "=expr" load pseudo-operation.
c19d1205
ZW
8262 Determine whether it can be performed with a move instruction; if
8263 it can, convert inst.instruction to that move instruction and
c921be7d
NC
8264 return TRUE; if it can't, convert inst.instruction to a literal-pool
8265 load and return FALSE. If this is not a valid thing to do in the
8266 current context, set inst.error and return TRUE.
a737bd4d 8267
c19d1205
ZW
8268 inst.operands[i] describes the destination register. */
8269
c921be7d 8270static bfd_boolean
8335d6aa 8271move_or_literal_pool (int i, enum lit_type t, bfd_boolean mode_3)
c19d1205 8272{
53365c0d 8273 unsigned long tbit;
8335d6aa
JW
8274 bfd_boolean thumb_p = (t == CONST_THUMB);
8275 bfd_boolean arm_p = (t == CONST_ARM);
53365c0d
PB
8276
8277 if (thumb_p)
8278 tbit = (inst.instruction > 0xffff) ? THUMB2_LOAD_BIT : THUMB_LOAD_BIT;
8279 else
8280 tbit = LOAD_BIT;
8281
8282 if ((inst.instruction & tbit) == 0)
09d92015 8283 {
c19d1205 8284 inst.error = _("invalid pseudo operation");
c921be7d 8285 return TRUE;
09d92015 8286 }
ba592044 8287
e2b0ab59
AV
8288 if (inst.relocs[0].exp.X_op != O_constant
8289 && inst.relocs[0].exp.X_op != O_symbol
8290 && inst.relocs[0].exp.X_op != O_big)
09d92015
MM
8291 {
8292 inst.error = _("constant expression expected");
c921be7d 8293 return TRUE;
09d92015 8294 }
ba592044 8295
e2b0ab59
AV
8296 if (inst.relocs[0].exp.X_op == O_constant
8297 || inst.relocs[0].exp.X_op == O_big)
8335d6aa 8298 {
5fc177c8
NC
8299#if defined BFD_HOST_64_BIT
8300 bfd_int64_t v;
8301#else
ba592044 8302 offsetT v;
5fc177c8 8303#endif
e2b0ab59 8304 if (inst.relocs[0].exp.X_op == O_big)
8335d6aa 8305 {
ba592044
AM
8306 LITTLENUM_TYPE w[X_PRECISION];
8307 LITTLENUM_TYPE * l;
8308
e2b0ab59 8309 if (inst.relocs[0].exp.X_add_number == -1)
8335d6aa 8310 {
ba592044
AM
8311 gen_to_words (w, X_PRECISION, E_PRECISION);
8312 l = w;
8313 /* FIXME: Should we check words w[2..5] ? */
8335d6aa 8314 }
ba592044
AM
8315 else
8316 l = generic_bignum;
3739860c 8317
5fc177c8
NC
8318#if defined BFD_HOST_64_BIT
8319 v =
8320 ((((((((bfd_int64_t) l[3] & LITTLENUM_MASK)
8321 << LITTLENUM_NUMBER_OF_BITS)
8322 | ((bfd_int64_t) l[2] & LITTLENUM_MASK))
8323 << LITTLENUM_NUMBER_OF_BITS)
8324 | ((bfd_int64_t) l[1] & LITTLENUM_MASK))
8325 << LITTLENUM_NUMBER_OF_BITS)
8326 | ((bfd_int64_t) l[0] & LITTLENUM_MASK));
8327#else
ba592044
AM
8328 v = ((l[1] & LITTLENUM_MASK) << LITTLENUM_NUMBER_OF_BITS)
8329 | (l[0] & LITTLENUM_MASK);
5fc177c8 8330#endif
8335d6aa 8331 }
ba592044 8332 else
e2b0ab59 8333 v = inst.relocs[0].exp.X_add_number;
ba592044
AM
8334
8335 if (!inst.operands[i].issingle)
8335d6aa 8336 {
12569877 8337 if (thumb_p)
8335d6aa 8338 {
53445554
TP
8339 /* LDR should not use lead in a flag-setting instruction being
8340 chosen so we do not check whether movs can be used. */
12569877 8341
53445554 8342 if ((ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6t2)
ff8646ee 8343 || ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6t2_v8m))
53445554
TP
8344 && inst.operands[i].reg != 13
8345 && inst.operands[i].reg != 15)
12569877 8346 {
fc289b0a
TP
8347 /* Check if on thumb2 it can be done with a mov.w, mvn or
8348 movw instruction. */
12569877
AM
8349 unsigned int newimm;
8350 bfd_boolean isNegated;
8351
8352 newimm = encode_thumb32_immediate (v);
8353 if (newimm != (unsigned int) FAIL)
8354 isNegated = FALSE;
8355 else
8356 {
582cfe03 8357 newimm = encode_thumb32_immediate (~v);
12569877
AM
8358 if (newimm != (unsigned int) FAIL)
8359 isNegated = TRUE;
8360 }
8361
fc289b0a
TP
8362 /* The number can be loaded with a mov.w or mvn
8363 instruction. */
ff8646ee
TP
8364 if (newimm != (unsigned int) FAIL
8365 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6t2))
12569877 8366 {
fc289b0a 8367 inst.instruction = (0xf04f0000 /* MOV.W. */
582cfe03 8368 | (inst.operands[i].reg << 8));
fc289b0a 8369 /* Change to MOVN. */
582cfe03 8370 inst.instruction |= (isNegated ? 0x200000 : 0);
12569877
AM
8371 inst.instruction |= (newimm & 0x800) << 15;
8372 inst.instruction |= (newimm & 0x700) << 4;
8373 inst.instruction |= (newimm & 0x0ff);
8374 return TRUE;
8375 }
fc289b0a 8376 /* The number can be loaded with a movw instruction. */
ff8646ee
TP
8377 else if ((v & ~0xFFFF) == 0
8378 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6t2_v8m))
3739860c 8379 {
582cfe03 8380 int imm = v & 0xFFFF;
12569877 8381
582cfe03 8382 inst.instruction = 0xf2400000; /* MOVW. */
12569877
AM
8383 inst.instruction |= (inst.operands[i].reg << 8);
8384 inst.instruction |= (imm & 0xf000) << 4;
8385 inst.instruction |= (imm & 0x0800) << 15;
8386 inst.instruction |= (imm & 0x0700) << 4;
8387 inst.instruction |= (imm & 0x00ff);
8388 return TRUE;
8389 }
8390 }
8335d6aa 8391 }
12569877 8392 else if (arm_p)
ba592044
AM
8393 {
8394 int value = encode_arm_immediate (v);
12569877 8395
ba592044
AM
8396 if (value != FAIL)
8397 {
8398 /* This can be done with a mov instruction. */
8399 inst.instruction &= LITERAL_MASK;
8400 inst.instruction |= INST_IMMEDIATE | (OPCODE_MOV << DATA_OP_SHIFT);
8401 inst.instruction |= value & 0xfff;
8402 return TRUE;
8403 }
8335d6aa 8404
ba592044
AM
8405 value = encode_arm_immediate (~ v);
8406 if (value != FAIL)
8407 {
8408 /* This can be done with a mvn instruction. */
8409 inst.instruction &= LITERAL_MASK;
8410 inst.instruction |= INST_IMMEDIATE | (OPCODE_MVN << DATA_OP_SHIFT);
8411 inst.instruction |= value & 0xfff;
8412 return TRUE;
8413 }
8414 }
934c2632 8415 else if (t == CONST_VEC && ARM_CPU_HAS_FEATURE (cpu_variant, fpu_neon_ext_v1))
8335d6aa 8416 {
ba592044
AM
8417 int op = 0;
8418 unsigned immbits = 0;
8419 unsigned immlo = inst.operands[1].imm;
8420 unsigned immhi = inst.operands[1].regisimm
8421 ? inst.operands[1].reg
e2b0ab59 8422 : inst.relocs[0].exp.X_unsigned
ba592044
AM
8423 ? 0
8424 : ((bfd_int64_t)((int) immlo)) >> 32;
8425 int cmode = neon_cmode_for_move_imm (immlo, immhi, FALSE, &immbits,
8426 &op, 64, NT_invtype);
8427
8428 if (cmode == FAIL)
8429 {
8430 neon_invert_size (&immlo, &immhi, 64);
8431 op = !op;
8432 cmode = neon_cmode_for_move_imm (immlo, immhi, FALSE, &immbits,
8433 &op, 64, NT_invtype);
8434 }
8435
8436 if (cmode != FAIL)
8437 {
8438 inst.instruction = (inst.instruction & VLDR_VMOV_SAME)
8439 | (1 << 23)
8440 | (cmode << 8)
8441 | (op << 5)
8442 | (1 << 4);
8443
8444 /* Fill other bits in vmov encoding for both thumb and arm. */
8445 if (thumb_mode)
eff0bc54 8446 inst.instruction |= (0x7U << 29) | (0xF << 24);
ba592044 8447 else
eff0bc54 8448 inst.instruction |= (0xFU << 28) | (0x1 << 25);
ba592044
AM
8449 neon_write_immbits (immbits);
8450 return TRUE;
8451 }
8335d6aa
JW
8452 }
8453 }
8335d6aa 8454
ba592044
AM
8455 if (t == CONST_VEC)
8456 {
8457 /* Check if vldr Rx, =constant could be optimized to vmov Rx, #constant. */
8458 if (inst.operands[i].issingle
8459 && is_quarter_float (inst.operands[1].imm)
8460 && ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_v3xd))
8335d6aa 8461 {
ba592044
AM
8462 inst.operands[1].imm =
8463 neon_qfloat_bits (v);
8464 do_vfp_nsyn_opcode ("fconsts");
8465 return TRUE;
8335d6aa 8466 }
5fc177c8
NC
8467
8468 /* If our host does not support a 64-bit type then we cannot perform
8469 the following optimization. This mean that there will be a
8470 discrepancy between the output produced by an assembler built for
8471 a 32-bit-only host and the output produced from a 64-bit host, but
8472 this cannot be helped. */
8473#if defined BFD_HOST_64_BIT
ba592044
AM
8474 else if (!inst.operands[1].issingle
8475 && ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_v3))
8335d6aa 8476 {
ba592044
AM
8477 if (is_double_a_single (v)
8478 && is_quarter_float (double_to_single (v)))
8479 {
8480 inst.operands[1].imm =
8481 neon_qfloat_bits (double_to_single (v));
8482 do_vfp_nsyn_opcode ("fconstd");
8483 return TRUE;
8484 }
8335d6aa 8485 }
5fc177c8 8486#endif
8335d6aa
JW
8487 }
8488 }
8489
8490 if (add_to_lit_pool ((!inst.operands[i].isvec
8491 || inst.operands[i].issingle) ? 4 : 8) == FAIL)
8492 return TRUE;
8493
8494 inst.operands[1].reg = REG_PC;
8495 inst.operands[1].isreg = 1;
8496 inst.operands[1].preind = 1;
e2b0ab59
AV
8497 inst.relocs[0].pc_rel = 1;
8498 inst.relocs[0].type = (thumb_p
8335d6aa
JW
8499 ? BFD_RELOC_ARM_THUMB_OFFSET
8500 : (mode_3
8501 ? BFD_RELOC_ARM_HWLITERAL
8502 : BFD_RELOC_ARM_LITERAL));
8503 return FALSE;
8504}
8505
8506/* inst.operands[i] was set up by parse_address. Encode it into an
8507 ARM-format instruction. Reject all forms which cannot be encoded
8508 into a coprocessor load/store instruction. If wb_ok is false,
8509 reject use of writeback; if unind_ok is false, reject use of
8510 unindexed addressing. If reloc_override is not 0, use it instead
8511 of BFD_ARM_CP_OFF_IMM, unless the initial relocation is a group one
8512 (in which case it is preserved). */
8513
8514static int
8515encode_arm_cp_address (int i, int wb_ok, int unind_ok, int reloc_override)
8516{
8517 if (!inst.operands[i].isreg)
8518 {
99b2a2dd
NC
8519 /* PR 18256 */
8520 if (! inst.operands[0].isvec)
8521 {
8522 inst.error = _("invalid co-processor operand");
8523 return FAIL;
8524 }
8335d6aa
JW
8525 if (move_or_literal_pool (0, CONST_VEC, /*mode_3=*/FALSE))
8526 return SUCCESS;
8527 }
8528
8529 inst.instruction |= inst.operands[i].reg << 16;
8530
8531 gas_assert (!(inst.operands[i].preind && inst.operands[i].postind));
8532
8533 if (!inst.operands[i].preind && !inst.operands[i].postind) /* unindexed */
8534 {
8535 gas_assert (!inst.operands[i].writeback);
8536 if (!unind_ok)
8537 {
8538 inst.error = _("instruction does not support unindexed addressing");
8539 return FAIL;
8540 }
8541 inst.instruction |= inst.operands[i].imm;
8542 inst.instruction |= INDEX_UP;
8543 return SUCCESS;
8544 }
8545
8546 if (inst.operands[i].preind)
8547 inst.instruction |= PRE_INDEX;
8548
8549 if (inst.operands[i].writeback)
09d92015 8550 {
8335d6aa 8551 if (inst.operands[i].reg == REG_PC)
c19d1205 8552 {
8335d6aa
JW
8553 inst.error = _("pc may not be used with write-back");
8554 return FAIL;
c19d1205 8555 }
8335d6aa 8556 if (!wb_ok)
c19d1205 8557 {
8335d6aa
JW
8558 inst.error = _("instruction does not support writeback");
8559 return FAIL;
c19d1205 8560 }
8335d6aa 8561 inst.instruction |= WRITE_BACK;
09d92015
MM
8562 }
8563
8335d6aa 8564 if (reloc_override)
e2b0ab59
AV
8565 inst.relocs[0].type = (bfd_reloc_code_real_type) reloc_override;
8566 else if ((inst.relocs[0].type < BFD_RELOC_ARM_ALU_PC_G0_NC
8567 || inst.relocs[0].type > BFD_RELOC_ARM_LDC_SB_G2)
8568 && inst.relocs[0].type != BFD_RELOC_ARM_LDR_PC_G0)
c19d1205 8569 {
8335d6aa 8570 if (thumb_mode)
e2b0ab59 8571 inst.relocs[0].type = BFD_RELOC_ARM_T32_CP_OFF_IMM;
8335d6aa 8572 else
e2b0ab59 8573 inst.relocs[0].type = BFD_RELOC_ARM_CP_OFF_IMM;
c19d1205 8574 }
8335d6aa
JW
8575
8576 /* Prefer + for zero encoded value. */
8577 if (!inst.operands[i].negative)
8578 inst.instruction |= INDEX_UP;
8579
8580 return SUCCESS;
09d92015
MM
8581}
8582
5f4273c7 8583/* Functions for instruction encoding, sorted by sub-architecture.
c19d1205
ZW
8584 First some generics; their names are taken from the conventional
8585 bit positions for register arguments in ARM format instructions. */
09d92015 8586
a737bd4d 8587static void
c19d1205 8588do_noargs (void)
09d92015 8589{
c19d1205 8590}
a737bd4d 8591
c19d1205
ZW
8592static void
8593do_rd (void)
8594{
8595 inst.instruction |= inst.operands[0].reg << 12;
8596}
a737bd4d 8597
16a1fa25
TP
8598static void
8599do_rn (void)
8600{
8601 inst.instruction |= inst.operands[0].reg << 16;
8602}
8603
c19d1205
ZW
8604static void
8605do_rd_rm (void)
8606{
8607 inst.instruction |= inst.operands[0].reg << 12;
8608 inst.instruction |= inst.operands[1].reg;
8609}
09d92015 8610
9eb6c0f1
MGD
8611static void
8612do_rm_rn (void)
8613{
8614 inst.instruction |= inst.operands[0].reg;
8615 inst.instruction |= inst.operands[1].reg << 16;
8616}
8617
c19d1205
ZW
8618static void
8619do_rd_rn (void)
8620{
8621 inst.instruction |= inst.operands[0].reg << 12;
8622 inst.instruction |= inst.operands[1].reg << 16;
8623}
a737bd4d 8624
c19d1205
ZW
8625static void
8626do_rn_rd (void)
8627{
8628 inst.instruction |= inst.operands[0].reg << 16;
8629 inst.instruction |= inst.operands[1].reg << 12;
8630}
09d92015 8631
4ed7ed8d
TP
8632static void
8633do_tt (void)
8634{
8635 inst.instruction |= inst.operands[0].reg << 8;
8636 inst.instruction |= inst.operands[1].reg << 16;
8637}
8638
59d09be6
MGD
8639static bfd_boolean
8640check_obsolete (const arm_feature_set *feature, const char *msg)
8641{
8642 if (ARM_CPU_IS_ANY (cpu_variant))
8643 {
5c3696f8 8644 as_tsktsk ("%s", msg);
59d09be6
MGD
8645 return TRUE;
8646 }
8647 else if (ARM_CPU_HAS_FEATURE (cpu_variant, *feature))
8648 {
8649 as_bad ("%s", msg);
8650 return TRUE;
8651 }
8652
8653 return FALSE;
8654}
8655
c19d1205
ZW
8656static void
8657do_rd_rm_rn (void)
8658{
9a64e435 8659 unsigned Rn = inst.operands[2].reg;
708587a4 8660 /* Enforce restrictions on SWP instruction. */
9a64e435 8661 if ((inst.instruction & 0x0fbfffff) == 0x01000090)
56adecf4
DG
8662 {
8663 constraint (Rn == inst.operands[0].reg || Rn == inst.operands[1].reg,
8664 _("Rn must not overlap other operands"));
8665
59d09be6
MGD
8666 /* SWP{b} is obsolete for ARMv8-A, and deprecated for ARMv6* and ARMv7.
8667 */
8668 if (!check_obsolete (&arm_ext_v8,
8669 _("swp{b} use is obsoleted for ARMv8 and later"))
8670 && warn_on_deprecated
8671 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6))
5c3696f8 8672 as_tsktsk (_("swp{b} use is deprecated for ARMv6 and ARMv7"));
56adecf4 8673 }
59d09be6 8674
c19d1205
ZW
8675 inst.instruction |= inst.operands[0].reg << 12;
8676 inst.instruction |= inst.operands[1].reg;
9a64e435 8677 inst.instruction |= Rn << 16;
c19d1205 8678}
09d92015 8679
c19d1205
ZW
8680static void
8681do_rd_rn_rm (void)
8682{
8683 inst.instruction |= inst.operands[0].reg << 12;
8684 inst.instruction |= inst.operands[1].reg << 16;
8685 inst.instruction |= inst.operands[2].reg;
8686}
a737bd4d 8687
c19d1205
ZW
8688static void
8689do_rm_rd_rn (void)
8690{
5be8be5d 8691 constraint ((inst.operands[2].reg == REG_PC), BAD_PC);
e2b0ab59
AV
8692 constraint (((inst.relocs[0].exp.X_op != O_constant
8693 && inst.relocs[0].exp.X_op != O_illegal)
8694 || inst.relocs[0].exp.X_add_number != 0),
5be8be5d 8695 BAD_ADDR_MODE);
c19d1205
ZW
8696 inst.instruction |= inst.operands[0].reg;
8697 inst.instruction |= inst.operands[1].reg << 12;
8698 inst.instruction |= inst.operands[2].reg << 16;
8699}
09d92015 8700
c19d1205
ZW
8701static void
8702do_imm0 (void)
8703{
8704 inst.instruction |= inst.operands[0].imm;
8705}
09d92015 8706
c19d1205
ZW
8707static void
8708do_rd_cpaddr (void)
8709{
8710 inst.instruction |= inst.operands[0].reg << 12;
8711 encode_arm_cp_address (1, TRUE, TRUE, 0);
09d92015 8712}
a737bd4d 8713
c19d1205
ZW
8714/* ARM instructions, in alphabetical order by function name (except
8715 that wrapper functions appear immediately after the function they
8716 wrap). */
09d92015 8717
c19d1205
ZW
8718/* This is a pseudo-op of the form "adr rd, label" to be converted
8719 into a relative address of the form "add rd, pc, #label-.-8". */
09d92015
MM
8720
8721static void
c19d1205 8722do_adr (void)
09d92015 8723{
c19d1205 8724 inst.instruction |= (inst.operands[0].reg << 12); /* Rd */
a737bd4d 8725
c19d1205
ZW
8726 /* Frag hacking will turn this into a sub instruction if the offset turns
8727 out to be negative. */
e2b0ab59
AV
8728 inst.relocs[0].type = BFD_RELOC_ARM_IMMEDIATE;
8729 inst.relocs[0].pc_rel = 1;
8730 inst.relocs[0].exp.X_add_number -= 8;
52a86f84 8731
fc6141f0 8732 if (support_interwork
e2b0ab59
AV
8733 && inst.relocs[0].exp.X_op == O_symbol
8734 && inst.relocs[0].exp.X_add_symbol != NULL
8735 && S_IS_DEFINED (inst.relocs[0].exp.X_add_symbol)
8736 && THUMB_IS_FUNC (inst.relocs[0].exp.X_add_symbol))
8737 inst.relocs[0].exp.X_add_number |= 1;
c19d1205 8738}
b99bd4ef 8739
c19d1205
ZW
8740/* This is a pseudo-op of the form "adrl rd, label" to be converted
8741 into a relative address of the form:
8742 add rd, pc, #low(label-.-8)"
8743 add rd, rd, #high(label-.-8)" */
b99bd4ef 8744
c19d1205
ZW
8745static void
8746do_adrl (void)
8747{
8748 inst.instruction |= (inst.operands[0].reg << 12); /* Rd */
a737bd4d 8749
c19d1205
ZW
8750 /* Frag hacking will turn this into a sub instruction if the offset turns
8751 out to be negative. */
e2b0ab59
AV
8752 inst.relocs[0].type = BFD_RELOC_ARM_ADRL_IMMEDIATE;
8753 inst.relocs[0].pc_rel = 1;
c19d1205 8754 inst.size = INSN_SIZE * 2;
e2b0ab59 8755 inst.relocs[0].exp.X_add_number -= 8;
52a86f84 8756
fc6141f0 8757 if (support_interwork
e2b0ab59
AV
8758 && inst.relocs[0].exp.X_op == O_symbol
8759 && inst.relocs[0].exp.X_add_symbol != NULL
8760 && S_IS_DEFINED (inst.relocs[0].exp.X_add_symbol)
8761 && THUMB_IS_FUNC (inst.relocs[0].exp.X_add_symbol))
8762 inst.relocs[0].exp.X_add_number |= 1;
b99bd4ef
NC
8763}
8764
b99bd4ef 8765static void
c19d1205 8766do_arit (void)
b99bd4ef 8767{
e2b0ab59
AV
8768 constraint (inst.relocs[0].type >= BFD_RELOC_ARM_THUMB_ALU_ABS_G0_NC
8769 && inst.relocs[0].type <= BFD_RELOC_ARM_THUMB_ALU_ABS_G3_NC ,
a9f02af8 8770 THUMB1_RELOC_ONLY);
c19d1205
ZW
8771 if (!inst.operands[1].present)
8772 inst.operands[1].reg = inst.operands[0].reg;
8773 inst.instruction |= inst.operands[0].reg << 12;
8774 inst.instruction |= inst.operands[1].reg << 16;
8775 encode_arm_shifter_operand (2);
8776}
b99bd4ef 8777
62b3e311
PB
8778static void
8779do_barrier (void)
8780{
8781 if (inst.operands[0].present)
ccb84d65 8782 inst.instruction |= inst.operands[0].imm;
62b3e311
PB
8783 else
8784 inst.instruction |= 0xf;
8785}
8786
c19d1205
ZW
8787static void
8788do_bfc (void)
8789{
8790 unsigned int msb = inst.operands[1].imm + inst.operands[2].imm;
8791 constraint (msb > 32, _("bit-field extends past end of register"));
8792 /* The instruction encoding stores the LSB and MSB,
8793 not the LSB and width. */
8794 inst.instruction |= inst.operands[0].reg << 12;
8795 inst.instruction |= inst.operands[1].imm << 7;
8796 inst.instruction |= (msb - 1) << 16;
8797}
b99bd4ef 8798
c19d1205
ZW
8799static void
8800do_bfi (void)
8801{
8802 unsigned int msb;
b99bd4ef 8803
c19d1205
ZW
8804 /* #0 in second position is alternative syntax for bfc, which is
8805 the same instruction but with REG_PC in the Rm field. */
8806 if (!inst.operands[1].isreg)
8807 inst.operands[1].reg = REG_PC;
b99bd4ef 8808
c19d1205
ZW
8809 msb = inst.operands[2].imm + inst.operands[3].imm;
8810 constraint (msb > 32, _("bit-field extends past end of register"));
8811 /* The instruction encoding stores the LSB and MSB,
8812 not the LSB and width. */
8813 inst.instruction |= inst.operands[0].reg << 12;
8814 inst.instruction |= inst.operands[1].reg;
8815 inst.instruction |= inst.operands[2].imm << 7;
8816 inst.instruction |= (msb - 1) << 16;
b99bd4ef
NC
8817}
8818
b99bd4ef 8819static void
c19d1205 8820do_bfx (void)
b99bd4ef 8821{
c19d1205
ZW
8822 constraint (inst.operands[2].imm + inst.operands[3].imm > 32,
8823 _("bit-field extends past end of register"));
8824 inst.instruction |= inst.operands[0].reg << 12;
8825 inst.instruction |= inst.operands[1].reg;
8826 inst.instruction |= inst.operands[2].imm << 7;
8827 inst.instruction |= (inst.operands[3].imm - 1) << 16;
8828}
09d92015 8829
c19d1205
ZW
8830/* ARM V5 breakpoint instruction (argument parse)
8831 BKPT <16 bit unsigned immediate>
8832 Instruction is not conditional.
8833 The bit pattern given in insns[] has the COND_ALWAYS condition,
8834 and it is an error if the caller tried to override that. */
b99bd4ef 8835
c19d1205
ZW
8836static void
8837do_bkpt (void)
8838{
8839 /* Top 12 of 16 bits to bits 19:8. */
8840 inst.instruction |= (inst.operands[0].imm & 0xfff0) << 4;
09d92015 8841
c19d1205
ZW
8842 /* Bottom 4 of 16 bits to bits 3:0. */
8843 inst.instruction |= inst.operands[0].imm & 0xf;
8844}
09d92015 8845
c19d1205
ZW
8846static void
8847encode_branch (int default_reloc)
8848{
8849 if (inst.operands[0].hasreloc)
8850 {
0855e32b
NS
8851 constraint (inst.operands[0].imm != BFD_RELOC_ARM_PLT32
8852 && inst.operands[0].imm != BFD_RELOC_ARM_TLS_CALL,
8853 _("the only valid suffixes here are '(plt)' and '(tlscall)'"));
e2b0ab59 8854 inst.relocs[0].type = inst.operands[0].imm == BFD_RELOC_ARM_PLT32
0855e32b
NS
8855 ? BFD_RELOC_ARM_PLT32
8856 : thumb_mode ? BFD_RELOC_ARM_THM_TLS_CALL : BFD_RELOC_ARM_TLS_CALL;
c19d1205 8857 }
b99bd4ef 8858 else
e2b0ab59
AV
8859 inst.relocs[0].type = (bfd_reloc_code_real_type) default_reloc;
8860 inst.relocs[0].pc_rel = 1;
b99bd4ef
NC
8861}
8862
b99bd4ef 8863static void
c19d1205 8864do_branch (void)
b99bd4ef 8865{
39b41c9c
PB
8866#ifdef OBJ_ELF
8867 if (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4)
8868 encode_branch (BFD_RELOC_ARM_PCREL_JUMP);
8869 else
8870#endif
8871 encode_branch (BFD_RELOC_ARM_PCREL_BRANCH);
8872}
8873
8874static void
8875do_bl (void)
8876{
8877#ifdef OBJ_ELF
8878 if (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4)
8879 {
8880 if (inst.cond == COND_ALWAYS)
8881 encode_branch (BFD_RELOC_ARM_PCREL_CALL);
8882 else
8883 encode_branch (BFD_RELOC_ARM_PCREL_JUMP);
8884 }
8885 else
8886#endif
8887 encode_branch (BFD_RELOC_ARM_PCREL_BRANCH);
c19d1205 8888}
b99bd4ef 8889
c19d1205
ZW
8890/* ARM V5 branch-link-exchange instruction (argument parse)
8891 BLX <target_addr> ie BLX(1)
8892 BLX{<condition>} <Rm> ie BLX(2)
8893 Unfortunately, there are two different opcodes for this mnemonic.
8894 So, the insns[].value is not used, and the code here zaps values
8895 into inst.instruction.
8896 Also, the <target_addr> can be 25 bits, hence has its own reloc. */
b99bd4ef 8897
c19d1205
ZW
8898static void
8899do_blx (void)
8900{
8901 if (inst.operands[0].isreg)
b99bd4ef 8902 {
c19d1205
ZW
8903 /* Arg is a register; the opcode provided by insns[] is correct.
8904 It is not illegal to do "blx pc", just useless. */
8905 if (inst.operands[0].reg == REG_PC)
8906 as_tsktsk (_("use of r15 in blx in ARM mode is not really useful"));
b99bd4ef 8907
c19d1205
ZW
8908 inst.instruction |= inst.operands[0].reg;
8909 }
8910 else
b99bd4ef 8911 {
c19d1205 8912 /* Arg is an address; this instruction cannot be executed
267bf995
RR
8913 conditionally, and the opcode must be adjusted.
8914 We retain the BFD_RELOC_ARM_PCREL_BLX till the very end
8915 where we generate out a BFD_RELOC_ARM_PCREL_CALL instead. */
c19d1205 8916 constraint (inst.cond != COND_ALWAYS, BAD_COND);
2fc8bdac 8917 inst.instruction = 0xfa000000;
267bf995 8918 encode_branch (BFD_RELOC_ARM_PCREL_BLX);
b99bd4ef 8919 }
c19d1205
ZW
8920}
8921
8922static void
8923do_bx (void)
8924{
845b51d6
PB
8925 bfd_boolean want_reloc;
8926
c19d1205
ZW
8927 if (inst.operands[0].reg == REG_PC)
8928 as_tsktsk (_("use of r15 in bx in ARM mode is not really useful"));
b99bd4ef 8929
c19d1205 8930 inst.instruction |= inst.operands[0].reg;
845b51d6
PB
8931 /* Output R_ARM_V4BX relocations if is an EABI object that looks like
8932 it is for ARMv4t or earlier. */
8933 want_reloc = !ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5);
4d354d8b
TP
8934 if (!ARM_FEATURE_ZERO (selected_object_arch)
8935 && !ARM_CPU_HAS_FEATURE (selected_object_arch, arm_ext_v5))
845b51d6
PB
8936 want_reloc = TRUE;
8937
5ad34203 8938#ifdef OBJ_ELF
845b51d6 8939 if (EF_ARM_EABI_VERSION (meabi_flags) < EF_ARM_EABI_VER4)
5ad34203 8940#endif
584206db 8941 want_reloc = FALSE;
845b51d6
PB
8942
8943 if (want_reloc)
e2b0ab59 8944 inst.relocs[0].type = BFD_RELOC_ARM_V4BX;
09d92015
MM
8945}
8946
c19d1205
ZW
8947
8948/* ARM v5TEJ. Jump to Jazelle code. */
a737bd4d
NC
8949
8950static void
c19d1205 8951do_bxj (void)
a737bd4d 8952{
c19d1205
ZW
8953 if (inst.operands[0].reg == REG_PC)
8954 as_tsktsk (_("use of r15 in bxj is not really useful"));
8955
8956 inst.instruction |= inst.operands[0].reg;
a737bd4d
NC
8957}
8958
c19d1205
ZW
8959/* Co-processor data operation:
8960 CDP{cond} <coproc>, <opcode_1>, <CRd>, <CRn>, <CRm>{, <opcode_2>}
8961 CDP2 <coproc>, <opcode_1>, <CRd>, <CRn>, <CRm>{, <opcode_2>} */
8962static void
8963do_cdp (void)
8964{
8965 inst.instruction |= inst.operands[0].reg << 8;
8966 inst.instruction |= inst.operands[1].imm << 20;
8967 inst.instruction |= inst.operands[2].reg << 12;
8968 inst.instruction |= inst.operands[3].reg << 16;
8969 inst.instruction |= inst.operands[4].reg;
8970 inst.instruction |= inst.operands[5].imm << 5;
8971}
a737bd4d
NC
8972
8973static void
c19d1205 8974do_cmp (void)
a737bd4d 8975{
c19d1205
ZW
8976 inst.instruction |= inst.operands[0].reg << 16;
8977 encode_arm_shifter_operand (1);
a737bd4d
NC
8978}
8979
c19d1205
ZW
8980/* Transfer between coprocessor and ARM registers.
8981 MRC{cond} <coproc>, <opcode_1>, <Rd>, <CRn>, <CRm>{, <opcode_2>}
8982 MRC2
8983 MCR{cond}
8984 MCR2
8985
8986 No special properties. */
09d92015 8987
dcbd0d71
MGD
8988struct deprecated_coproc_regs_s
8989{
8990 unsigned cp;
8991 int opc1;
8992 unsigned crn;
8993 unsigned crm;
8994 int opc2;
8995 arm_feature_set deprecated;
8996 arm_feature_set obsoleted;
8997 const char *dep_msg;
8998 const char *obs_msg;
8999};
9000
9001#define DEPR_ACCESS_V8 \
9002 N_("This coprocessor register access is deprecated in ARMv8")
9003
9004/* Table of all deprecated coprocessor registers. */
9005static struct deprecated_coproc_regs_s deprecated_coproc_regs[] =
9006{
9007 {15, 0, 7, 10, 5, /* CP15DMB. */
823d2571 9008 ARM_FEATURE_CORE_LOW (ARM_EXT_V8), ARM_ARCH_NONE,
dcbd0d71
MGD
9009 DEPR_ACCESS_V8, NULL},
9010 {15, 0, 7, 10, 4, /* CP15DSB. */
823d2571 9011 ARM_FEATURE_CORE_LOW (ARM_EXT_V8), ARM_ARCH_NONE,
dcbd0d71
MGD
9012 DEPR_ACCESS_V8, NULL},
9013 {15, 0, 7, 5, 4, /* CP15ISB. */
823d2571 9014 ARM_FEATURE_CORE_LOW (ARM_EXT_V8), ARM_ARCH_NONE,
dcbd0d71
MGD
9015 DEPR_ACCESS_V8, NULL},
9016 {14, 6, 1, 0, 0, /* TEEHBR. */
823d2571 9017 ARM_FEATURE_CORE_LOW (ARM_EXT_V8), ARM_ARCH_NONE,
dcbd0d71
MGD
9018 DEPR_ACCESS_V8, NULL},
9019 {14, 6, 0, 0, 0, /* TEECR. */
823d2571 9020 ARM_FEATURE_CORE_LOW (ARM_EXT_V8), ARM_ARCH_NONE,
dcbd0d71
MGD
9021 DEPR_ACCESS_V8, NULL},
9022};
9023
9024#undef DEPR_ACCESS_V8
9025
9026static const size_t deprecated_coproc_reg_count =
9027 sizeof (deprecated_coproc_regs) / sizeof (deprecated_coproc_regs[0]);
9028
09d92015 9029static void
c19d1205 9030do_co_reg (void)
09d92015 9031{
fdfde340 9032 unsigned Rd;
dcbd0d71 9033 size_t i;
fdfde340
JM
9034
9035 Rd = inst.operands[2].reg;
9036 if (thumb_mode)
9037 {
9038 if (inst.instruction == 0xee000010
9039 || inst.instruction == 0xfe000010)
9040 /* MCR, MCR2 */
9041 reject_bad_reg (Rd);
5c8ed6a4 9042 else if (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v8))
fdfde340
JM
9043 /* MRC, MRC2 */
9044 constraint (Rd == REG_SP, BAD_SP);
9045 }
9046 else
9047 {
9048 /* MCR */
9049 if (inst.instruction == 0xe000010)
9050 constraint (Rd == REG_PC, BAD_PC);
9051 }
9052
dcbd0d71
MGD
9053 for (i = 0; i < deprecated_coproc_reg_count; ++i)
9054 {
9055 const struct deprecated_coproc_regs_s *r =
9056 deprecated_coproc_regs + i;
9057
9058 if (inst.operands[0].reg == r->cp
9059 && inst.operands[1].imm == r->opc1
9060 && inst.operands[3].reg == r->crn
9061 && inst.operands[4].reg == r->crm
9062 && inst.operands[5].imm == r->opc2)
9063 {
b10bf8c5 9064 if (! ARM_CPU_IS_ANY (cpu_variant)
477330fc 9065 && warn_on_deprecated
dcbd0d71 9066 && ARM_CPU_HAS_FEATURE (cpu_variant, r->deprecated))
5c3696f8 9067 as_tsktsk ("%s", r->dep_msg);
dcbd0d71
MGD
9068 }
9069 }
fdfde340 9070
c19d1205
ZW
9071 inst.instruction |= inst.operands[0].reg << 8;
9072 inst.instruction |= inst.operands[1].imm << 21;
fdfde340 9073 inst.instruction |= Rd << 12;
c19d1205
ZW
9074 inst.instruction |= inst.operands[3].reg << 16;
9075 inst.instruction |= inst.operands[4].reg;
9076 inst.instruction |= inst.operands[5].imm << 5;
9077}
09d92015 9078
c19d1205
ZW
9079/* Transfer between coprocessor register and pair of ARM registers.
9080 MCRR{cond} <coproc>, <opcode>, <Rd>, <Rn>, <CRm>.
9081 MCRR2
9082 MRRC{cond}
9083 MRRC2
b99bd4ef 9084
c19d1205 9085 Two XScale instructions are special cases of these:
09d92015 9086
c19d1205
ZW
9087 MAR{cond} acc0, <RdLo>, <RdHi> == MCRR{cond} p0, #0, <RdLo>, <RdHi>, c0
9088 MRA{cond} acc0, <RdLo>, <RdHi> == MRRC{cond} p0, #0, <RdLo>, <RdHi>, c0
b99bd4ef 9089
5f4273c7 9090 Result unpredictable if Rd or Rn is R15. */
a737bd4d 9091
c19d1205
ZW
9092static void
9093do_co_reg2c (void)
9094{
fdfde340
JM
9095 unsigned Rd, Rn;
9096
9097 Rd = inst.operands[2].reg;
9098 Rn = inst.operands[3].reg;
9099
9100 if (thumb_mode)
9101 {
9102 reject_bad_reg (Rd);
9103 reject_bad_reg (Rn);
9104 }
9105 else
9106 {
9107 constraint (Rd == REG_PC, BAD_PC);
9108 constraint (Rn == REG_PC, BAD_PC);
9109 }
9110
873f10f0
TC
9111 /* Only check the MRRC{2} variants. */
9112 if ((inst.instruction & 0x0FF00000) == 0x0C500000)
9113 {
9114 /* If Rd == Rn, error that the operation is
9115 unpredictable (example MRRC p3,#1,r1,r1,c4). */
9116 constraint (Rd == Rn, BAD_OVERLAP);
9117 }
9118
c19d1205
ZW
9119 inst.instruction |= inst.operands[0].reg << 8;
9120 inst.instruction |= inst.operands[1].imm << 4;
fdfde340
JM
9121 inst.instruction |= Rd << 12;
9122 inst.instruction |= Rn << 16;
c19d1205 9123 inst.instruction |= inst.operands[4].reg;
b99bd4ef
NC
9124}
9125
c19d1205
ZW
9126static void
9127do_cpsi (void)
9128{
9129 inst.instruction |= inst.operands[0].imm << 6;
a028a6f5
PB
9130 if (inst.operands[1].present)
9131 {
9132 inst.instruction |= CPSI_MMOD;
9133 inst.instruction |= inst.operands[1].imm;
9134 }
c19d1205 9135}
b99bd4ef 9136
62b3e311
PB
9137static void
9138do_dbg (void)
9139{
9140 inst.instruction |= inst.operands[0].imm;
9141}
9142
eea54501
MGD
9143static void
9144do_div (void)
9145{
9146 unsigned Rd, Rn, Rm;
9147
9148 Rd = inst.operands[0].reg;
9149 Rn = (inst.operands[1].present
9150 ? inst.operands[1].reg : Rd);
9151 Rm = inst.operands[2].reg;
9152
9153 constraint ((Rd == REG_PC), BAD_PC);
9154 constraint ((Rn == REG_PC), BAD_PC);
9155 constraint ((Rm == REG_PC), BAD_PC);
9156
9157 inst.instruction |= Rd << 16;
9158 inst.instruction |= Rn << 0;
9159 inst.instruction |= Rm << 8;
9160}
9161
b99bd4ef 9162static void
c19d1205 9163do_it (void)
b99bd4ef 9164{
c19d1205 9165 /* There is no IT instruction in ARM mode. We
e07e6e58
NC
9166 process it to do the validation as if in
9167 thumb mode, just in case the code gets
9168 assembled for thumb using the unified syntax. */
9169
c19d1205 9170 inst.size = 0;
e07e6e58
NC
9171 if (unified_syntax)
9172 {
5ee91343
AV
9173 set_pred_insn_type (IT_INSN);
9174 now_pred.mask = (inst.instruction & 0xf) | 0x10;
9175 now_pred.cc = inst.operands[0].imm;
e07e6e58 9176 }
09d92015 9177}
b99bd4ef 9178
6530b175
NC
9179/* If there is only one register in the register list,
9180 then return its register number. Otherwise return -1. */
9181static int
9182only_one_reg_in_list (int range)
9183{
9184 int i = ffs (range) - 1;
9185 return (i > 15 || range != (1 << i)) ? -1 : i;
9186}
9187
09d92015 9188static void
6530b175 9189encode_ldmstm(int from_push_pop_mnem)
ea6ef066 9190{
c19d1205
ZW
9191 int base_reg = inst.operands[0].reg;
9192 int range = inst.operands[1].imm;
6530b175 9193 int one_reg;
ea6ef066 9194
c19d1205
ZW
9195 inst.instruction |= base_reg << 16;
9196 inst.instruction |= range;
ea6ef066 9197
c19d1205
ZW
9198 if (inst.operands[1].writeback)
9199 inst.instruction |= LDM_TYPE_2_OR_3;
09d92015 9200
c19d1205 9201 if (inst.operands[0].writeback)
ea6ef066 9202 {
c19d1205
ZW
9203 inst.instruction |= WRITE_BACK;
9204 /* Check for unpredictable uses of writeback. */
9205 if (inst.instruction & LOAD_BIT)
09d92015 9206 {
c19d1205
ZW
9207 /* Not allowed in LDM type 2. */
9208 if ((inst.instruction & LDM_TYPE_2_OR_3)
9209 && ((range & (1 << REG_PC)) == 0))
9210 as_warn (_("writeback of base register is UNPREDICTABLE"));
9211 /* Only allowed if base reg not in list for other types. */
9212 else if (range & (1 << base_reg))
9213 as_warn (_("writeback of base register when in register list is UNPREDICTABLE"));
9214 }
9215 else /* STM. */
9216 {
9217 /* Not allowed for type 2. */
9218 if (inst.instruction & LDM_TYPE_2_OR_3)
9219 as_warn (_("writeback of base register is UNPREDICTABLE"));
9220 /* Only allowed if base reg not in list, or first in list. */
9221 else if ((range & (1 << base_reg))
9222 && (range & ((1 << base_reg) - 1)))
9223 as_warn (_("if writeback register is in list, it must be the lowest reg in the list"));
09d92015 9224 }
ea6ef066 9225 }
6530b175
NC
9226
9227 /* If PUSH/POP has only one register, then use the A2 encoding. */
9228 one_reg = only_one_reg_in_list (range);
9229 if (from_push_pop_mnem && one_reg >= 0)
9230 {
9231 int is_push = (inst.instruction & A_PUSH_POP_OP_MASK) == A1_OPCODE_PUSH;
9232
4f588891
NC
9233 if (is_push && one_reg == 13 /* SP */)
9234 /* PR 22483: The A2 encoding cannot be used when
9235 pushing the stack pointer as this is UNPREDICTABLE. */
9236 return;
9237
6530b175
NC
9238 inst.instruction &= A_COND_MASK;
9239 inst.instruction |= is_push ? A2_OPCODE_PUSH : A2_OPCODE_POP;
9240 inst.instruction |= one_reg << 12;
9241 }
9242}
9243
9244static void
9245do_ldmstm (void)
9246{
9247 encode_ldmstm (/*from_push_pop_mnem=*/FALSE);
a737bd4d
NC
9248}
9249
c19d1205
ZW
9250/* ARMv5TE load-consecutive (argument parse)
9251 Mode is like LDRH.
9252
9253 LDRccD R, mode
9254 STRccD R, mode. */
9255
a737bd4d 9256static void
c19d1205 9257do_ldrd (void)
a737bd4d 9258{
c19d1205 9259 constraint (inst.operands[0].reg % 2 != 0,
c56791bb 9260 _("first transfer register must be even"));
c19d1205
ZW
9261 constraint (inst.operands[1].present
9262 && inst.operands[1].reg != inst.operands[0].reg + 1,
c56791bb 9263 _("can only transfer two consecutive registers"));
c19d1205
ZW
9264 constraint (inst.operands[0].reg == REG_LR, _("r14 not allowed here"));
9265 constraint (!inst.operands[2].isreg, _("'[' expected"));
a737bd4d 9266
c19d1205
ZW
9267 if (!inst.operands[1].present)
9268 inst.operands[1].reg = inst.operands[0].reg + 1;
5f4273c7 9269
c56791bb
RE
9270 /* encode_arm_addr_mode_3 will diagnose overlap between the base
9271 register and the first register written; we have to diagnose
9272 overlap between the base and the second register written here. */
ea6ef066 9273
c56791bb
RE
9274 if (inst.operands[2].reg == inst.operands[1].reg
9275 && (inst.operands[2].writeback || inst.operands[2].postind))
9276 as_warn (_("base register written back, and overlaps "
9277 "second transfer register"));
b05fe5cf 9278
c56791bb
RE
9279 if (!(inst.instruction & V4_STR_BIT))
9280 {
c19d1205 9281 /* For an index-register load, the index register must not overlap the
c56791bb
RE
9282 destination (even if not write-back). */
9283 if (inst.operands[2].immisreg
9284 && ((unsigned) inst.operands[2].imm == inst.operands[0].reg
9285 || (unsigned) inst.operands[2].imm == inst.operands[1].reg))
9286 as_warn (_("index register overlaps transfer register"));
b05fe5cf 9287 }
c19d1205
ZW
9288 inst.instruction |= inst.operands[0].reg << 12;
9289 encode_arm_addr_mode_3 (2, /*is_t=*/FALSE);
b05fe5cf
ZW
9290}
9291
9292static void
c19d1205 9293do_ldrex (void)
b05fe5cf 9294{
c19d1205
ZW
9295 constraint (!inst.operands[1].isreg || !inst.operands[1].preind
9296 || inst.operands[1].postind || inst.operands[1].writeback
9297 || inst.operands[1].immisreg || inst.operands[1].shifted
01cfc07f
NC
9298 || inst.operands[1].negative
9299 /* This can arise if the programmer has written
9300 strex rN, rM, foo
9301 or if they have mistakenly used a register name as the last
9302 operand, eg:
9303 strex rN, rM, rX
9304 It is very difficult to distinguish between these two cases
9305 because "rX" might actually be a label. ie the register
9306 name has been occluded by a symbol of the same name. So we
9307 just generate a general 'bad addressing mode' type error
9308 message and leave it up to the programmer to discover the
9309 true cause and fix their mistake. */
9310 || (inst.operands[1].reg == REG_PC),
9311 BAD_ADDR_MODE);
b05fe5cf 9312
e2b0ab59
AV
9313 constraint (inst.relocs[0].exp.X_op != O_constant
9314 || inst.relocs[0].exp.X_add_number != 0,
c19d1205 9315 _("offset must be zero in ARM encoding"));
b05fe5cf 9316
5be8be5d
DG
9317 constraint ((inst.operands[1].reg == REG_PC), BAD_PC);
9318
c19d1205
ZW
9319 inst.instruction |= inst.operands[0].reg << 12;
9320 inst.instruction |= inst.operands[1].reg << 16;
e2b0ab59 9321 inst.relocs[0].type = BFD_RELOC_UNUSED;
b05fe5cf
ZW
9322}
9323
9324static void
c19d1205 9325do_ldrexd (void)
b05fe5cf 9326{
c19d1205
ZW
9327 constraint (inst.operands[0].reg % 2 != 0,
9328 _("even register required"));
9329 constraint (inst.operands[1].present
9330 && inst.operands[1].reg != inst.operands[0].reg + 1,
9331 _("can only load two consecutive registers"));
9332 /* If op 1 were present and equal to PC, this function wouldn't
9333 have been called in the first place. */
9334 constraint (inst.operands[0].reg == REG_LR, _("r14 not allowed here"));
b05fe5cf 9335
c19d1205
ZW
9336 inst.instruction |= inst.operands[0].reg << 12;
9337 inst.instruction |= inst.operands[2].reg << 16;
b05fe5cf
ZW
9338}
9339
1be5fd2e
NC
9340/* In both ARM and thumb state 'ldr pc, #imm' with an immediate
9341 which is not a multiple of four is UNPREDICTABLE. */
9342static void
9343check_ldr_r15_aligned (void)
9344{
9345 constraint (!(inst.operands[1].immisreg)
9346 && (inst.operands[0].reg == REG_PC
9347 && inst.operands[1].reg == REG_PC
e2b0ab59 9348 && (inst.relocs[0].exp.X_add_number & 0x3)),
de194d85 9349 _("ldr to register 15 must be 4-byte aligned"));
1be5fd2e
NC
9350}
9351
b05fe5cf 9352static void
c19d1205 9353do_ldst (void)
b05fe5cf 9354{
c19d1205
ZW
9355 inst.instruction |= inst.operands[0].reg << 12;
9356 if (!inst.operands[1].isreg)
8335d6aa 9357 if (move_or_literal_pool (0, CONST_ARM, /*mode_3=*/FALSE))
b05fe5cf 9358 return;
c19d1205 9359 encode_arm_addr_mode_2 (1, /*is_t=*/FALSE);
1be5fd2e 9360 check_ldr_r15_aligned ();
b05fe5cf
ZW
9361}
9362
9363static void
c19d1205 9364do_ldstt (void)
b05fe5cf 9365{
c19d1205
ZW
9366 /* ldrt/strt always use post-indexed addressing. Turn [Rn] into [Rn]! and
9367 reject [Rn,...]. */
9368 if (inst.operands[1].preind)
b05fe5cf 9369 {
e2b0ab59
AV
9370 constraint (inst.relocs[0].exp.X_op != O_constant
9371 || inst.relocs[0].exp.X_add_number != 0,
c19d1205 9372 _("this instruction requires a post-indexed address"));
b05fe5cf 9373
c19d1205
ZW
9374 inst.operands[1].preind = 0;
9375 inst.operands[1].postind = 1;
9376 inst.operands[1].writeback = 1;
b05fe5cf 9377 }
c19d1205
ZW
9378 inst.instruction |= inst.operands[0].reg << 12;
9379 encode_arm_addr_mode_2 (1, /*is_t=*/TRUE);
9380}
b05fe5cf 9381
c19d1205 9382/* Halfword and signed-byte load/store operations. */
b05fe5cf 9383
c19d1205
ZW
9384static void
9385do_ldstv4 (void)
9386{
ff4a8d2b 9387 constraint (inst.operands[0].reg == REG_PC, BAD_PC);
c19d1205
ZW
9388 inst.instruction |= inst.operands[0].reg << 12;
9389 if (!inst.operands[1].isreg)
8335d6aa 9390 if (move_or_literal_pool (0, CONST_ARM, /*mode_3=*/TRUE))
b05fe5cf 9391 return;
c19d1205 9392 encode_arm_addr_mode_3 (1, /*is_t=*/FALSE);
b05fe5cf
ZW
9393}
9394
9395static void
c19d1205 9396do_ldsttv4 (void)
b05fe5cf 9397{
c19d1205
ZW
9398 /* ldrt/strt always use post-indexed addressing. Turn [Rn] into [Rn]! and
9399 reject [Rn,...]. */
9400 if (inst.operands[1].preind)
b05fe5cf 9401 {
e2b0ab59
AV
9402 constraint (inst.relocs[0].exp.X_op != O_constant
9403 || inst.relocs[0].exp.X_add_number != 0,
c19d1205 9404 _("this instruction requires a post-indexed address"));
b05fe5cf 9405
c19d1205
ZW
9406 inst.operands[1].preind = 0;
9407 inst.operands[1].postind = 1;
9408 inst.operands[1].writeback = 1;
b05fe5cf 9409 }
c19d1205
ZW
9410 inst.instruction |= inst.operands[0].reg << 12;
9411 encode_arm_addr_mode_3 (1, /*is_t=*/TRUE);
9412}
b05fe5cf 9413
c19d1205
ZW
9414/* Co-processor register load/store.
9415 Format: <LDC|STC>{cond}[L] CP#,CRd,<address> */
9416static void
9417do_lstc (void)
9418{
9419 inst.instruction |= inst.operands[0].reg << 8;
9420 inst.instruction |= inst.operands[1].reg << 12;
9421 encode_arm_cp_address (2, TRUE, TRUE, 0);
b05fe5cf
ZW
9422}
9423
b05fe5cf 9424static void
c19d1205 9425do_mlas (void)
b05fe5cf 9426{
8fb9d7b9 9427 /* This restriction does not apply to mls (nor to mla in v6 or later). */
c19d1205 9428 if (inst.operands[0].reg == inst.operands[1].reg
8fb9d7b9 9429 && !ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6)
c19d1205 9430 && !(inst.instruction & 0x00400000))
8fb9d7b9 9431 as_tsktsk (_("Rd and Rm should be different in mla"));
b05fe5cf 9432
c19d1205
ZW
9433 inst.instruction |= inst.operands[0].reg << 16;
9434 inst.instruction |= inst.operands[1].reg;
9435 inst.instruction |= inst.operands[2].reg << 8;
9436 inst.instruction |= inst.operands[3].reg << 12;
c19d1205 9437}
b05fe5cf 9438
c19d1205
ZW
9439static void
9440do_mov (void)
9441{
e2b0ab59
AV
9442 constraint (inst.relocs[0].type >= BFD_RELOC_ARM_THUMB_ALU_ABS_G0_NC
9443 && inst.relocs[0].type <= BFD_RELOC_ARM_THUMB_ALU_ABS_G3_NC ,
a9f02af8 9444 THUMB1_RELOC_ONLY);
c19d1205
ZW
9445 inst.instruction |= inst.operands[0].reg << 12;
9446 encode_arm_shifter_operand (1);
9447}
b05fe5cf 9448
c19d1205
ZW
9449/* ARM V6T2 16-bit immediate register load: MOV[WT]{cond} Rd, #<imm16>. */
9450static void
9451do_mov16 (void)
9452{
b6895b4f
PB
9453 bfd_vma imm;
9454 bfd_boolean top;
9455
9456 top = (inst.instruction & 0x00400000) != 0;
e2b0ab59 9457 constraint (top && inst.relocs[0].type == BFD_RELOC_ARM_MOVW,
33eaf5de 9458 _(":lower16: not allowed in this instruction"));
e2b0ab59 9459 constraint (!top && inst.relocs[0].type == BFD_RELOC_ARM_MOVT,
33eaf5de 9460 _(":upper16: not allowed in this instruction"));
c19d1205 9461 inst.instruction |= inst.operands[0].reg << 12;
e2b0ab59 9462 if (inst.relocs[0].type == BFD_RELOC_UNUSED)
b6895b4f 9463 {
e2b0ab59 9464 imm = inst.relocs[0].exp.X_add_number;
b6895b4f
PB
9465 /* The value is in two pieces: 0:11, 16:19. */
9466 inst.instruction |= (imm & 0x00000fff);
9467 inst.instruction |= (imm & 0x0000f000) << 4;
9468 }
b05fe5cf 9469}
b99bd4ef 9470
037e8744
JB
9471static int
9472do_vfp_nsyn_mrs (void)
9473{
9474 if (inst.operands[0].isvec)
9475 {
9476 if (inst.operands[1].reg != 1)
477330fc 9477 first_error (_("operand 1 must be FPSCR"));
037e8744
JB
9478 memset (&inst.operands[0], '\0', sizeof (inst.operands[0]));
9479 memset (&inst.operands[1], '\0', sizeof (inst.operands[1]));
9480 do_vfp_nsyn_opcode ("fmstat");
9481 }
9482 else if (inst.operands[1].isvec)
9483 do_vfp_nsyn_opcode ("fmrx");
9484 else
9485 return FAIL;
5f4273c7 9486
037e8744
JB
9487 return SUCCESS;
9488}
9489
9490static int
9491do_vfp_nsyn_msr (void)
9492{
9493 if (inst.operands[0].isvec)
9494 do_vfp_nsyn_opcode ("fmxr");
9495 else
9496 return FAIL;
9497
9498 return SUCCESS;
9499}
9500
f7c21dc7
NC
9501static void
9502do_vmrs (void)
9503{
9504 unsigned Rt = inst.operands[0].reg;
fa94de6b 9505
16d02dc9 9506 if (thumb_mode && Rt == REG_SP)
f7c21dc7
NC
9507 {
9508 inst.error = BAD_SP;
9509 return;
9510 }
9511
40c7d507
RR
9512 /* MVFR2 is only valid at ARMv8-A. */
9513 if (inst.operands[1].reg == 5)
9514 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_armv8),
9515 _(BAD_FPU));
9516
f7c21dc7 9517 /* APSR_ sets isvec. All other refs to PC are illegal. */
16d02dc9 9518 if (!inst.operands[0].isvec && Rt == REG_PC)
f7c21dc7
NC
9519 {
9520 inst.error = BAD_PC;
9521 return;
9522 }
9523
16d02dc9
JB
9524 /* If we get through parsing the register name, we just insert the number
9525 generated into the instruction without further validation. */
9526 inst.instruction |= (inst.operands[1].reg << 16);
f7c21dc7
NC
9527 inst.instruction |= (Rt << 12);
9528}
9529
9530static void
9531do_vmsr (void)
9532{
9533 unsigned Rt = inst.operands[1].reg;
fa94de6b 9534
f7c21dc7
NC
9535 if (thumb_mode)
9536 reject_bad_reg (Rt);
9537 else if (Rt == REG_PC)
9538 {
9539 inst.error = BAD_PC;
9540 return;
9541 }
9542
40c7d507
RR
9543 /* MVFR2 is only valid for ARMv8-A. */
9544 if (inst.operands[0].reg == 5)
9545 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_armv8),
9546 _(BAD_FPU));
9547
16d02dc9
JB
9548 /* If we get through parsing the register name, we just insert the number
9549 generated into the instruction without further validation. */
9550 inst.instruction |= (inst.operands[0].reg << 16);
f7c21dc7
NC
9551 inst.instruction |= (Rt << 12);
9552}
9553
b99bd4ef 9554static void
c19d1205 9555do_mrs (void)
b99bd4ef 9556{
90ec0d68
MGD
9557 unsigned br;
9558
037e8744
JB
9559 if (do_vfp_nsyn_mrs () == SUCCESS)
9560 return;
9561
ff4a8d2b 9562 constraint (inst.operands[0].reg == REG_PC, BAD_PC);
c19d1205 9563 inst.instruction |= inst.operands[0].reg << 12;
90ec0d68
MGD
9564
9565 if (inst.operands[1].isreg)
9566 {
9567 br = inst.operands[1].reg;
806ab1c0 9568 if (((br & 0x200) == 0) && ((br & 0xf0000) != 0xf0000))
90ec0d68
MGD
9569 as_bad (_("bad register for mrs"));
9570 }
9571 else
9572 {
9573 /* mrs only accepts CPSR/SPSR/CPSR_all/SPSR_all. */
9574 constraint ((inst.operands[1].imm & (PSR_c|PSR_x|PSR_s|PSR_f))
9575 != (PSR_c|PSR_f),
d2cd1205 9576 _("'APSR', 'CPSR' or 'SPSR' expected"));
90ec0d68
MGD
9577 br = (15<<16) | (inst.operands[1].imm & SPSR_BIT);
9578 }
9579
9580 inst.instruction |= br;
c19d1205 9581}
b99bd4ef 9582
c19d1205
ZW
9583/* Two possible forms:
9584 "{C|S}PSR_<field>, Rm",
9585 "{C|S}PSR_f, #expression". */
b99bd4ef 9586
c19d1205
ZW
9587static void
9588do_msr (void)
9589{
037e8744
JB
9590 if (do_vfp_nsyn_msr () == SUCCESS)
9591 return;
9592
c19d1205
ZW
9593 inst.instruction |= inst.operands[0].imm;
9594 if (inst.operands[1].isreg)
9595 inst.instruction |= inst.operands[1].reg;
9596 else
b99bd4ef 9597 {
c19d1205 9598 inst.instruction |= INST_IMMEDIATE;
e2b0ab59
AV
9599 inst.relocs[0].type = BFD_RELOC_ARM_IMMEDIATE;
9600 inst.relocs[0].pc_rel = 0;
b99bd4ef 9601 }
b99bd4ef
NC
9602}
9603
c19d1205
ZW
9604static void
9605do_mul (void)
a737bd4d 9606{
ff4a8d2b
NC
9607 constraint (inst.operands[2].reg == REG_PC, BAD_PC);
9608
c19d1205
ZW
9609 if (!inst.operands[2].present)
9610 inst.operands[2].reg = inst.operands[0].reg;
9611 inst.instruction |= inst.operands[0].reg << 16;
9612 inst.instruction |= inst.operands[1].reg;
9613 inst.instruction |= inst.operands[2].reg << 8;
a737bd4d 9614
8fb9d7b9
MS
9615 if (inst.operands[0].reg == inst.operands[1].reg
9616 && !ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6))
9617 as_tsktsk (_("Rd and Rm should be different in mul"));
a737bd4d
NC
9618}
9619
c19d1205
ZW
9620/* Long Multiply Parser
9621 UMULL RdLo, RdHi, Rm, Rs
9622 SMULL RdLo, RdHi, Rm, Rs
9623 UMLAL RdLo, RdHi, Rm, Rs
9624 SMLAL RdLo, RdHi, Rm, Rs. */
b99bd4ef
NC
9625
9626static void
c19d1205 9627do_mull (void)
b99bd4ef 9628{
c19d1205
ZW
9629 inst.instruction |= inst.operands[0].reg << 12;
9630 inst.instruction |= inst.operands[1].reg << 16;
9631 inst.instruction |= inst.operands[2].reg;
9632 inst.instruction |= inst.operands[3].reg << 8;
b99bd4ef 9633
682b27ad
PB
9634 /* rdhi and rdlo must be different. */
9635 if (inst.operands[0].reg == inst.operands[1].reg)
9636 as_tsktsk (_("rdhi and rdlo must be different"));
9637
9638 /* rdhi, rdlo and rm must all be different before armv6. */
9639 if ((inst.operands[0].reg == inst.operands[2].reg
c19d1205 9640 || inst.operands[1].reg == inst.operands[2].reg)
682b27ad 9641 && !ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6))
c19d1205
ZW
9642 as_tsktsk (_("rdhi, rdlo and rm must all be different"));
9643}
b99bd4ef 9644
c19d1205
ZW
9645static void
9646do_nop (void)
9647{
e7495e45
NS
9648 if (inst.operands[0].present
9649 || ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6k))
c19d1205
ZW
9650 {
9651 /* Architectural NOP hints are CPSR sets with no bits selected. */
9652 inst.instruction &= 0xf0000000;
e7495e45
NS
9653 inst.instruction |= 0x0320f000;
9654 if (inst.operands[0].present)
9655 inst.instruction |= inst.operands[0].imm;
c19d1205 9656 }
b99bd4ef
NC
9657}
9658
c19d1205
ZW
9659/* ARM V6 Pack Halfword Bottom Top instruction (argument parse).
9660 PKHBT {<cond>} <Rd>, <Rn>, <Rm> {, LSL #<shift_imm>}
9661 Condition defaults to COND_ALWAYS.
9662 Error if Rd, Rn or Rm are R15. */
b99bd4ef
NC
9663
9664static void
c19d1205 9665do_pkhbt (void)
b99bd4ef 9666{
c19d1205
ZW
9667 inst.instruction |= inst.operands[0].reg << 12;
9668 inst.instruction |= inst.operands[1].reg << 16;
9669 inst.instruction |= inst.operands[2].reg;
9670 if (inst.operands[3].present)
9671 encode_arm_shift (3);
9672}
b99bd4ef 9673
c19d1205 9674/* ARM V6 PKHTB (Argument Parse). */
b99bd4ef 9675
c19d1205
ZW
9676static void
9677do_pkhtb (void)
9678{
9679 if (!inst.operands[3].present)
b99bd4ef 9680 {
c19d1205
ZW
9681 /* If the shift specifier is omitted, turn the instruction
9682 into pkhbt rd, rm, rn. */
9683 inst.instruction &= 0xfff00010;
9684 inst.instruction |= inst.operands[0].reg << 12;
9685 inst.instruction |= inst.operands[1].reg;
9686 inst.instruction |= inst.operands[2].reg << 16;
b99bd4ef
NC
9687 }
9688 else
9689 {
c19d1205
ZW
9690 inst.instruction |= inst.operands[0].reg << 12;
9691 inst.instruction |= inst.operands[1].reg << 16;
9692 inst.instruction |= inst.operands[2].reg;
9693 encode_arm_shift (3);
b99bd4ef
NC
9694 }
9695}
9696
c19d1205 9697/* ARMv5TE: Preload-Cache
60e5ef9f 9698 MP Extensions: Preload for write
c19d1205 9699
60e5ef9f 9700 PLD(W) <addr_mode>
c19d1205
ZW
9701
9702 Syntactically, like LDR with B=1, W=0, L=1. */
b99bd4ef
NC
9703
9704static void
c19d1205 9705do_pld (void)
b99bd4ef 9706{
c19d1205
ZW
9707 constraint (!inst.operands[0].isreg,
9708 _("'[' expected after PLD mnemonic"));
9709 constraint (inst.operands[0].postind,
9710 _("post-indexed expression used in preload instruction"));
9711 constraint (inst.operands[0].writeback,
9712 _("writeback used in preload instruction"));
9713 constraint (!inst.operands[0].preind,
9714 _("unindexed addressing used in preload instruction"));
c19d1205
ZW
9715 encode_arm_addr_mode_2 (0, /*is_t=*/FALSE);
9716}
b99bd4ef 9717
62b3e311
PB
9718/* ARMv7: PLI <addr_mode> */
9719static void
9720do_pli (void)
9721{
9722 constraint (!inst.operands[0].isreg,
9723 _("'[' expected after PLI mnemonic"));
9724 constraint (inst.operands[0].postind,
9725 _("post-indexed expression used in preload instruction"));
9726 constraint (inst.operands[0].writeback,
9727 _("writeback used in preload instruction"));
9728 constraint (!inst.operands[0].preind,
9729 _("unindexed addressing used in preload instruction"));
9730 encode_arm_addr_mode_2 (0, /*is_t=*/FALSE);
9731 inst.instruction &= ~PRE_INDEX;
9732}
9733
c19d1205
ZW
9734static void
9735do_push_pop (void)
9736{
5e0d7f77
MP
9737 constraint (inst.operands[0].writeback,
9738 _("push/pop do not support {reglist}^"));
c19d1205
ZW
9739 inst.operands[1] = inst.operands[0];
9740 memset (&inst.operands[0], 0, sizeof inst.operands[0]);
9741 inst.operands[0].isreg = 1;
9742 inst.operands[0].writeback = 1;
9743 inst.operands[0].reg = REG_SP;
6530b175 9744 encode_ldmstm (/*from_push_pop_mnem=*/TRUE);
c19d1205 9745}
b99bd4ef 9746
c19d1205
ZW
9747/* ARM V6 RFE (Return from Exception) loads the PC and CPSR from the
9748 word at the specified address and the following word
9749 respectively.
9750 Unconditionally executed.
9751 Error if Rn is R15. */
b99bd4ef 9752
c19d1205
ZW
9753static void
9754do_rfe (void)
9755{
9756 inst.instruction |= inst.operands[0].reg << 16;
9757 if (inst.operands[0].writeback)
9758 inst.instruction |= WRITE_BACK;
9759}
b99bd4ef 9760
c19d1205 9761/* ARM V6 ssat (argument parse). */
b99bd4ef 9762
c19d1205
ZW
9763static void
9764do_ssat (void)
9765{
9766 inst.instruction |= inst.operands[0].reg << 12;
9767 inst.instruction |= (inst.operands[1].imm - 1) << 16;
9768 inst.instruction |= inst.operands[2].reg;
b99bd4ef 9769
c19d1205
ZW
9770 if (inst.operands[3].present)
9771 encode_arm_shift (3);
b99bd4ef
NC
9772}
9773
c19d1205 9774/* ARM V6 usat (argument parse). */
b99bd4ef
NC
9775
9776static void
c19d1205 9777do_usat (void)
b99bd4ef 9778{
c19d1205
ZW
9779 inst.instruction |= inst.operands[0].reg << 12;
9780 inst.instruction |= inst.operands[1].imm << 16;
9781 inst.instruction |= inst.operands[2].reg;
b99bd4ef 9782
c19d1205
ZW
9783 if (inst.operands[3].present)
9784 encode_arm_shift (3);
b99bd4ef
NC
9785}
9786
c19d1205 9787/* ARM V6 ssat16 (argument parse). */
09d92015
MM
9788
9789static void
c19d1205 9790do_ssat16 (void)
09d92015 9791{
c19d1205
ZW
9792 inst.instruction |= inst.operands[0].reg << 12;
9793 inst.instruction |= ((inst.operands[1].imm - 1) << 16);
9794 inst.instruction |= inst.operands[2].reg;
09d92015
MM
9795}
9796
c19d1205
ZW
9797static void
9798do_usat16 (void)
a737bd4d 9799{
c19d1205
ZW
9800 inst.instruction |= inst.operands[0].reg << 12;
9801 inst.instruction |= inst.operands[1].imm << 16;
9802 inst.instruction |= inst.operands[2].reg;
9803}
a737bd4d 9804
c19d1205
ZW
9805/* ARM V6 SETEND (argument parse). Sets the E bit in the CPSR while
9806 preserving the other bits.
a737bd4d 9807
c19d1205
ZW
9808 setend <endian_specifier>, where <endian_specifier> is either
9809 BE or LE. */
a737bd4d 9810
c19d1205
ZW
9811static void
9812do_setend (void)
9813{
12e37cbc
MGD
9814 if (warn_on_deprecated
9815 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v8))
5c3696f8 9816 as_tsktsk (_("setend use is deprecated for ARMv8"));
12e37cbc 9817
c19d1205
ZW
9818 if (inst.operands[0].imm)
9819 inst.instruction |= 0x200;
a737bd4d
NC
9820}
9821
9822static void
c19d1205 9823do_shift (void)
a737bd4d 9824{
c19d1205
ZW
9825 unsigned int Rm = (inst.operands[1].present
9826 ? inst.operands[1].reg
9827 : inst.operands[0].reg);
a737bd4d 9828
c19d1205
ZW
9829 inst.instruction |= inst.operands[0].reg << 12;
9830 inst.instruction |= Rm;
9831 if (inst.operands[2].isreg) /* Rd, {Rm,} Rs */
a737bd4d 9832 {
c19d1205
ZW
9833 inst.instruction |= inst.operands[2].reg << 8;
9834 inst.instruction |= SHIFT_BY_REG;
94342ec3
NC
9835 /* PR 12854: Error on extraneous shifts. */
9836 constraint (inst.operands[2].shifted,
9837 _("extraneous shift as part of operand to shift insn"));
a737bd4d
NC
9838 }
9839 else
e2b0ab59 9840 inst.relocs[0].type = BFD_RELOC_ARM_SHIFT_IMM;
a737bd4d
NC
9841}
9842
09d92015 9843static void
3eb17e6b 9844do_smc (void)
09d92015 9845{
e2b0ab59
AV
9846 inst.relocs[0].type = BFD_RELOC_ARM_SMC;
9847 inst.relocs[0].pc_rel = 0;
09d92015
MM
9848}
9849
90ec0d68
MGD
9850static void
9851do_hvc (void)
9852{
e2b0ab59
AV
9853 inst.relocs[0].type = BFD_RELOC_ARM_HVC;
9854 inst.relocs[0].pc_rel = 0;
90ec0d68
MGD
9855}
9856
09d92015 9857static void
c19d1205 9858do_swi (void)
09d92015 9859{
e2b0ab59
AV
9860 inst.relocs[0].type = BFD_RELOC_ARM_SWI;
9861 inst.relocs[0].pc_rel = 0;
09d92015
MM
9862}
9863
ddfded2f
MW
9864static void
9865do_setpan (void)
9866{
9867 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_pan),
9868 _("selected processor does not support SETPAN instruction"));
9869
9870 inst.instruction |= ((inst.operands[0].imm & 1) << 9);
9871}
9872
9873static void
9874do_t_setpan (void)
9875{
9876 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_pan),
9877 _("selected processor does not support SETPAN instruction"));
9878
9879 inst.instruction |= (inst.operands[0].imm << 3);
9880}
9881
c19d1205
ZW
9882/* ARM V5E (El Segundo) signed-multiply-accumulate (argument parse)
9883 SMLAxy{cond} Rd,Rm,Rs,Rn
9884 SMLAWy{cond} Rd,Rm,Rs,Rn
9885 Error if any register is R15. */
e16bb312 9886
c19d1205
ZW
9887static void
9888do_smla (void)
e16bb312 9889{
c19d1205
ZW
9890 inst.instruction |= inst.operands[0].reg << 16;
9891 inst.instruction |= inst.operands[1].reg;
9892 inst.instruction |= inst.operands[2].reg << 8;
9893 inst.instruction |= inst.operands[3].reg << 12;
9894}
a737bd4d 9895
c19d1205
ZW
9896/* ARM V5E (El Segundo) signed-multiply-accumulate-long (argument parse)
9897 SMLALxy{cond} Rdlo,Rdhi,Rm,Rs
9898 Error if any register is R15.
9899 Warning if Rdlo == Rdhi. */
a737bd4d 9900
c19d1205
ZW
9901static void
9902do_smlal (void)
9903{
9904 inst.instruction |= inst.operands[0].reg << 12;
9905 inst.instruction |= inst.operands[1].reg << 16;
9906 inst.instruction |= inst.operands[2].reg;
9907 inst.instruction |= inst.operands[3].reg << 8;
a737bd4d 9908
c19d1205
ZW
9909 if (inst.operands[0].reg == inst.operands[1].reg)
9910 as_tsktsk (_("rdhi and rdlo must be different"));
9911}
a737bd4d 9912
c19d1205
ZW
9913/* ARM V5E (El Segundo) signed-multiply (argument parse)
9914 SMULxy{cond} Rd,Rm,Rs
9915 Error if any register is R15. */
a737bd4d 9916
c19d1205
ZW
9917static void
9918do_smul (void)
9919{
9920 inst.instruction |= inst.operands[0].reg << 16;
9921 inst.instruction |= inst.operands[1].reg;
9922 inst.instruction |= inst.operands[2].reg << 8;
9923}
a737bd4d 9924
b6702015
PB
9925/* ARM V6 srs (argument parse). The variable fields in the encoding are
9926 the same for both ARM and Thumb-2. */
a737bd4d 9927
c19d1205
ZW
9928static void
9929do_srs (void)
9930{
b6702015
PB
9931 int reg;
9932
9933 if (inst.operands[0].present)
9934 {
9935 reg = inst.operands[0].reg;
fdfde340 9936 constraint (reg != REG_SP, _("SRS base register must be r13"));
b6702015
PB
9937 }
9938 else
fdfde340 9939 reg = REG_SP;
b6702015
PB
9940
9941 inst.instruction |= reg << 16;
9942 inst.instruction |= inst.operands[1].imm;
9943 if (inst.operands[0].writeback || inst.operands[1].writeback)
c19d1205
ZW
9944 inst.instruction |= WRITE_BACK;
9945}
a737bd4d 9946
c19d1205 9947/* ARM V6 strex (argument parse). */
a737bd4d 9948
c19d1205
ZW
9949static void
9950do_strex (void)
9951{
9952 constraint (!inst.operands[2].isreg || !inst.operands[2].preind
9953 || inst.operands[2].postind || inst.operands[2].writeback
9954 || inst.operands[2].immisreg || inst.operands[2].shifted
01cfc07f
NC
9955 || inst.operands[2].negative
9956 /* See comment in do_ldrex(). */
9957 || (inst.operands[2].reg == REG_PC),
9958 BAD_ADDR_MODE);
a737bd4d 9959
c19d1205
ZW
9960 constraint (inst.operands[0].reg == inst.operands[1].reg
9961 || inst.operands[0].reg == inst.operands[2].reg, BAD_OVERLAP);
a737bd4d 9962
e2b0ab59
AV
9963 constraint (inst.relocs[0].exp.X_op != O_constant
9964 || inst.relocs[0].exp.X_add_number != 0,
c19d1205 9965 _("offset must be zero in ARM encoding"));
a737bd4d 9966
c19d1205
ZW
9967 inst.instruction |= inst.operands[0].reg << 12;
9968 inst.instruction |= inst.operands[1].reg;
9969 inst.instruction |= inst.operands[2].reg << 16;
e2b0ab59 9970 inst.relocs[0].type = BFD_RELOC_UNUSED;
e16bb312
NC
9971}
9972
877807f8
NC
9973static void
9974do_t_strexbh (void)
9975{
9976 constraint (!inst.operands[2].isreg || !inst.operands[2].preind
9977 || inst.operands[2].postind || inst.operands[2].writeback
9978 || inst.operands[2].immisreg || inst.operands[2].shifted
9979 || inst.operands[2].negative,
9980 BAD_ADDR_MODE);
9981
9982 constraint (inst.operands[0].reg == inst.operands[1].reg
9983 || inst.operands[0].reg == inst.operands[2].reg, BAD_OVERLAP);
9984
9985 do_rm_rd_rn ();
9986}
9987
e16bb312 9988static void
c19d1205 9989do_strexd (void)
e16bb312 9990{
c19d1205
ZW
9991 constraint (inst.operands[1].reg % 2 != 0,
9992 _("even register required"));
9993 constraint (inst.operands[2].present
9994 && inst.operands[2].reg != inst.operands[1].reg + 1,
9995 _("can only store two consecutive registers"));
9996 /* If op 2 were present and equal to PC, this function wouldn't
9997 have been called in the first place. */
9998 constraint (inst.operands[1].reg == REG_LR, _("r14 not allowed here"));
e16bb312 9999
c19d1205
ZW
10000 constraint (inst.operands[0].reg == inst.operands[1].reg
10001 || inst.operands[0].reg == inst.operands[1].reg + 1
10002 || inst.operands[0].reg == inst.operands[3].reg,
10003 BAD_OVERLAP);
e16bb312 10004
c19d1205
ZW
10005 inst.instruction |= inst.operands[0].reg << 12;
10006 inst.instruction |= inst.operands[1].reg;
10007 inst.instruction |= inst.operands[3].reg << 16;
e16bb312
NC
10008}
10009
9eb6c0f1
MGD
10010/* ARM V8 STRL. */
10011static void
4b8c8c02 10012do_stlex (void)
9eb6c0f1
MGD
10013{
10014 constraint (inst.operands[0].reg == inst.operands[1].reg
10015 || inst.operands[0].reg == inst.operands[2].reg, BAD_OVERLAP);
10016
10017 do_rd_rm_rn ();
10018}
10019
10020static void
4b8c8c02 10021do_t_stlex (void)
9eb6c0f1
MGD
10022{
10023 constraint (inst.operands[0].reg == inst.operands[1].reg
10024 || inst.operands[0].reg == inst.operands[2].reg, BAD_OVERLAP);
10025
10026 do_rm_rd_rn ();
10027}
10028
c19d1205
ZW
10029/* ARM V6 SXTAH extracts a 16-bit value from a register, sign
10030 extends it to 32-bits, and adds the result to a value in another
10031 register. You can specify a rotation by 0, 8, 16, or 24 bits
10032 before extracting the 16-bit value.
10033 SXTAH{<cond>} <Rd>, <Rn>, <Rm>{, <rotation>}
10034 Condition defaults to COND_ALWAYS.
10035 Error if any register uses R15. */
10036
e16bb312 10037static void
c19d1205 10038do_sxtah (void)
e16bb312 10039{
c19d1205
ZW
10040 inst.instruction |= inst.operands[0].reg << 12;
10041 inst.instruction |= inst.operands[1].reg << 16;
10042 inst.instruction |= inst.operands[2].reg;
10043 inst.instruction |= inst.operands[3].imm << 10;
10044}
e16bb312 10045
c19d1205 10046/* ARM V6 SXTH.
e16bb312 10047
c19d1205
ZW
10048 SXTH {<cond>} <Rd>, <Rm>{, <rotation>}
10049 Condition defaults to COND_ALWAYS.
10050 Error if any register uses R15. */
e16bb312
NC
10051
10052static void
c19d1205 10053do_sxth (void)
e16bb312 10054{
c19d1205
ZW
10055 inst.instruction |= inst.operands[0].reg << 12;
10056 inst.instruction |= inst.operands[1].reg;
10057 inst.instruction |= inst.operands[2].imm << 10;
e16bb312 10058}
c19d1205
ZW
10059\f
10060/* VFP instructions. In a logical order: SP variant first, monad
10061 before dyad, arithmetic then move then load/store. */
e16bb312
NC
10062
10063static void
c19d1205 10064do_vfp_sp_monadic (void)
e16bb312 10065{
5287ad62
JB
10066 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Sd);
10067 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Sm);
e16bb312
NC
10068}
10069
10070static void
c19d1205 10071do_vfp_sp_dyadic (void)
e16bb312 10072{
5287ad62
JB
10073 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Sd);
10074 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Sn);
10075 encode_arm_vfp_reg (inst.operands[2].reg, VFP_REG_Sm);
e16bb312
NC
10076}
10077
10078static void
c19d1205 10079do_vfp_sp_compare_z (void)
e16bb312 10080{
5287ad62 10081 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Sd);
e16bb312
NC
10082}
10083
10084static void
c19d1205 10085do_vfp_dp_sp_cvt (void)
e16bb312 10086{
5287ad62
JB
10087 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Dd);
10088 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Sm);
e16bb312
NC
10089}
10090
10091static void
c19d1205 10092do_vfp_sp_dp_cvt (void)
e16bb312 10093{
5287ad62
JB
10094 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Sd);
10095 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Dm);
e16bb312
NC
10096}
10097
10098static void
c19d1205 10099do_vfp_reg_from_sp (void)
e16bb312 10100{
c19d1205 10101 inst.instruction |= inst.operands[0].reg << 12;
5287ad62 10102 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Sn);
e16bb312
NC
10103}
10104
10105static void
c19d1205 10106do_vfp_reg2_from_sp2 (void)
e16bb312 10107{
c19d1205
ZW
10108 constraint (inst.operands[2].imm != 2,
10109 _("only two consecutive VFP SP registers allowed here"));
10110 inst.instruction |= inst.operands[0].reg << 12;
10111 inst.instruction |= inst.operands[1].reg << 16;
5287ad62 10112 encode_arm_vfp_reg (inst.operands[2].reg, VFP_REG_Sm);
e16bb312
NC
10113}
10114
10115static void
c19d1205 10116do_vfp_sp_from_reg (void)
e16bb312 10117{
5287ad62 10118 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Sn);
c19d1205 10119 inst.instruction |= inst.operands[1].reg << 12;
e16bb312
NC
10120}
10121
10122static void
c19d1205 10123do_vfp_sp2_from_reg2 (void)
e16bb312 10124{
c19d1205
ZW
10125 constraint (inst.operands[0].imm != 2,
10126 _("only two consecutive VFP SP registers allowed here"));
5287ad62 10127 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Sm);
c19d1205
ZW
10128 inst.instruction |= inst.operands[1].reg << 12;
10129 inst.instruction |= inst.operands[2].reg << 16;
e16bb312
NC
10130}
10131
10132static void
c19d1205 10133do_vfp_sp_ldst (void)
e16bb312 10134{
5287ad62 10135 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Sd);
c19d1205 10136 encode_arm_cp_address (1, FALSE, TRUE, 0);
e16bb312
NC
10137}
10138
10139static void
c19d1205 10140do_vfp_dp_ldst (void)
e16bb312 10141{
5287ad62 10142 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Dd);
c19d1205 10143 encode_arm_cp_address (1, FALSE, TRUE, 0);
e16bb312
NC
10144}
10145
c19d1205 10146
e16bb312 10147static void
c19d1205 10148vfp_sp_ldstm (enum vfp_ldstm_type ldstm_type)
e16bb312 10149{
c19d1205
ZW
10150 if (inst.operands[0].writeback)
10151 inst.instruction |= WRITE_BACK;
10152 else
10153 constraint (ldstm_type != VFP_LDSTMIA,
10154 _("this addressing mode requires base-register writeback"));
10155 inst.instruction |= inst.operands[0].reg << 16;
5287ad62 10156 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Sd);
c19d1205 10157 inst.instruction |= inst.operands[1].imm;
e16bb312
NC
10158}
10159
10160static void
c19d1205 10161vfp_dp_ldstm (enum vfp_ldstm_type ldstm_type)
e16bb312 10162{
c19d1205 10163 int count;
e16bb312 10164
c19d1205
ZW
10165 if (inst.operands[0].writeback)
10166 inst.instruction |= WRITE_BACK;
10167 else
10168 constraint (ldstm_type != VFP_LDSTMIA && ldstm_type != VFP_LDSTMIAX,
10169 _("this addressing mode requires base-register writeback"));
e16bb312 10170
c19d1205 10171 inst.instruction |= inst.operands[0].reg << 16;
5287ad62 10172 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Dd);
e16bb312 10173
c19d1205
ZW
10174 count = inst.operands[1].imm << 1;
10175 if (ldstm_type == VFP_LDSTMIAX || ldstm_type == VFP_LDSTMDBX)
10176 count += 1;
e16bb312 10177
c19d1205 10178 inst.instruction |= count;
e16bb312
NC
10179}
10180
10181static void
c19d1205 10182do_vfp_sp_ldstmia (void)
e16bb312 10183{
c19d1205 10184 vfp_sp_ldstm (VFP_LDSTMIA);
e16bb312
NC
10185}
10186
10187static void
c19d1205 10188do_vfp_sp_ldstmdb (void)
e16bb312 10189{
c19d1205 10190 vfp_sp_ldstm (VFP_LDSTMDB);
e16bb312
NC
10191}
10192
10193static void
c19d1205 10194do_vfp_dp_ldstmia (void)
e16bb312 10195{
c19d1205 10196 vfp_dp_ldstm (VFP_LDSTMIA);
e16bb312
NC
10197}
10198
10199static void
c19d1205 10200do_vfp_dp_ldstmdb (void)
e16bb312 10201{
c19d1205 10202 vfp_dp_ldstm (VFP_LDSTMDB);
e16bb312
NC
10203}
10204
10205static void
c19d1205 10206do_vfp_xp_ldstmia (void)
e16bb312 10207{
c19d1205
ZW
10208 vfp_dp_ldstm (VFP_LDSTMIAX);
10209}
e16bb312 10210
c19d1205
ZW
10211static void
10212do_vfp_xp_ldstmdb (void)
10213{
10214 vfp_dp_ldstm (VFP_LDSTMDBX);
e16bb312 10215}
5287ad62
JB
10216
10217static void
10218do_vfp_dp_rd_rm (void)
10219{
10220 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Dd);
10221 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Dm);
10222}
10223
10224static void
10225do_vfp_dp_rn_rd (void)
10226{
10227 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Dn);
10228 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Dd);
10229}
10230
10231static void
10232do_vfp_dp_rd_rn (void)
10233{
10234 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Dd);
10235 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Dn);
10236}
10237
10238static void
10239do_vfp_dp_rd_rn_rm (void)
10240{
10241 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Dd);
10242 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Dn);
10243 encode_arm_vfp_reg (inst.operands[2].reg, VFP_REG_Dm);
10244}
10245
10246static void
10247do_vfp_dp_rd (void)
10248{
10249 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Dd);
10250}
10251
10252static void
10253do_vfp_dp_rm_rd_rn (void)
10254{
10255 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Dm);
10256 encode_arm_vfp_reg (inst.operands[1].reg, VFP_REG_Dd);
10257 encode_arm_vfp_reg (inst.operands[2].reg, VFP_REG_Dn);
10258}
10259
10260/* VFPv3 instructions. */
10261static void
10262do_vfp_sp_const (void)
10263{
10264 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Sd);
00249aaa
PB
10265 inst.instruction |= (inst.operands[1].imm & 0xf0) << 12;
10266 inst.instruction |= (inst.operands[1].imm & 0x0f);
5287ad62
JB
10267}
10268
10269static void
10270do_vfp_dp_const (void)
10271{
10272 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Dd);
00249aaa
PB
10273 inst.instruction |= (inst.operands[1].imm & 0xf0) << 12;
10274 inst.instruction |= (inst.operands[1].imm & 0x0f);
5287ad62
JB
10275}
10276
10277static void
10278vfp_conv (int srcsize)
10279{
5f1af56b
MGD
10280 int immbits = srcsize - inst.operands[1].imm;
10281
fa94de6b
RM
10282 if (srcsize == 16 && !(immbits >= 0 && immbits <= srcsize))
10283 {
5f1af56b 10284 /* If srcsize is 16, inst.operands[1].imm must be in the range 0-16.
477330fc 10285 i.e. immbits must be in range 0 - 16. */
5f1af56b
MGD
10286 inst.error = _("immediate value out of range, expected range [0, 16]");
10287 return;
10288 }
fa94de6b 10289 else if (srcsize == 32 && !(immbits >= 0 && immbits < srcsize))
5f1af56b
MGD
10290 {
10291 /* If srcsize is 32, inst.operands[1].imm must be in the range 1-32.
477330fc 10292 i.e. immbits must be in range 0 - 31. */
5f1af56b
MGD
10293 inst.error = _("immediate value out of range, expected range [1, 32]");
10294 return;
10295 }
10296
5287ad62
JB
10297 inst.instruction |= (immbits & 1) << 5;
10298 inst.instruction |= (immbits >> 1);
10299}
10300
10301static void
10302do_vfp_sp_conv_16 (void)
10303{
10304 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Sd);
10305 vfp_conv (16);
10306}
10307
10308static void
10309do_vfp_dp_conv_16 (void)
10310{
10311 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Dd);
10312 vfp_conv (16);
10313}
10314
10315static void
10316do_vfp_sp_conv_32 (void)
10317{
10318 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Sd);
10319 vfp_conv (32);
10320}
10321
10322static void
10323do_vfp_dp_conv_32 (void)
10324{
10325 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Dd);
10326 vfp_conv (32);
10327}
c19d1205
ZW
10328\f
10329/* FPA instructions. Also in a logical order. */
e16bb312 10330
c19d1205
ZW
10331static void
10332do_fpa_cmp (void)
10333{
10334 inst.instruction |= inst.operands[0].reg << 16;
10335 inst.instruction |= inst.operands[1].reg;
10336}
b99bd4ef
NC
10337
10338static void
c19d1205 10339do_fpa_ldmstm (void)
b99bd4ef 10340{
c19d1205
ZW
10341 inst.instruction |= inst.operands[0].reg << 12;
10342 switch (inst.operands[1].imm)
10343 {
10344 case 1: inst.instruction |= CP_T_X; break;
10345 case 2: inst.instruction |= CP_T_Y; break;
10346 case 3: inst.instruction |= CP_T_Y | CP_T_X; break;
10347 case 4: break;
10348 default: abort ();
10349 }
b99bd4ef 10350
c19d1205
ZW
10351 if (inst.instruction & (PRE_INDEX | INDEX_UP))
10352 {
10353 /* The instruction specified "ea" or "fd", so we can only accept
10354 [Rn]{!}. The instruction does not really support stacking or
10355 unstacking, so we have to emulate these by setting appropriate
10356 bits and offsets. */
e2b0ab59
AV
10357 constraint (inst.relocs[0].exp.X_op != O_constant
10358 || inst.relocs[0].exp.X_add_number != 0,
c19d1205 10359 _("this instruction does not support indexing"));
b99bd4ef 10360
c19d1205 10361 if ((inst.instruction & PRE_INDEX) || inst.operands[2].writeback)
e2b0ab59 10362 inst.relocs[0].exp.X_add_number = 12 * inst.operands[1].imm;
b99bd4ef 10363
c19d1205 10364 if (!(inst.instruction & INDEX_UP))
e2b0ab59 10365 inst.relocs[0].exp.X_add_number = -inst.relocs[0].exp.X_add_number;
b99bd4ef 10366
c19d1205
ZW
10367 if (!(inst.instruction & PRE_INDEX) && inst.operands[2].writeback)
10368 {
10369 inst.operands[2].preind = 0;
10370 inst.operands[2].postind = 1;
10371 }
10372 }
b99bd4ef 10373
c19d1205 10374 encode_arm_cp_address (2, TRUE, TRUE, 0);
b99bd4ef 10375}
c19d1205
ZW
10376\f
10377/* iWMMXt instructions: strictly in alphabetical order. */
b99bd4ef 10378
c19d1205
ZW
10379static void
10380do_iwmmxt_tandorc (void)
10381{
10382 constraint (inst.operands[0].reg != REG_PC, _("only r15 allowed here"));
10383}
b99bd4ef 10384
c19d1205
ZW
10385static void
10386do_iwmmxt_textrc (void)
10387{
10388 inst.instruction |= inst.operands[0].reg << 12;
10389 inst.instruction |= inst.operands[1].imm;
10390}
b99bd4ef
NC
10391
10392static void
c19d1205 10393do_iwmmxt_textrm (void)
b99bd4ef 10394{
c19d1205
ZW
10395 inst.instruction |= inst.operands[0].reg << 12;
10396 inst.instruction |= inst.operands[1].reg << 16;
10397 inst.instruction |= inst.operands[2].imm;
10398}
b99bd4ef 10399
c19d1205
ZW
10400static void
10401do_iwmmxt_tinsr (void)
10402{
10403 inst.instruction |= inst.operands[0].reg << 16;
10404 inst.instruction |= inst.operands[1].reg << 12;
10405 inst.instruction |= inst.operands[2].imm;
10406}
b99bd4ef 10407
c19d1205
ZW
10408static void
10409do_iwmmxt_tmia (void)
10410{
10411 inst.instruction |= inst.operands[0].reg << 5;
10412 inst.instruction |= inst.operands[1].reg;
10413 inst.instruction |= inst.operands[2].reg << 12;
10414}
b99bd4ef 10415
c19d1205
ZW
10416static void
10417do_iwmmxt_waligni (void)
10418{
10419 inst.instruction |= inst.operands[0].reg << 12;
10420 inst.instruction |= inst.operands[1].reg << 16;
10421 inst.instruction |= inst.operands[2].reg;
10422 inst.instruction |= inst.operands[3].imm << 20;
10423}
b99bd4ef 10424
2d447fca
JM
10425static void
10426do_iwmmxt_wmerge (void)
10427{
10428 inst.instruction |= inst.operands[0].reg << 12;
10429 inst.instruction |= inst.operands[1].reg << 16;
10430 inst.instruction |= inst.operands[2].reg;
10431 inst.instruction |= inst.operands[3].imm << 21;
10432}
10433
c19d1205
ZW
10434static void
10435do_iwmmxt_wmov (void)
10436{
10437 /* WMOV rD, rN is an alias for WOR rD, rN, rN. */
10438 inst.instruction |= inst.operands[0].reg << 12;
10439 inst.instruction |= inst.operands[1].reg << 16;
10440 inst.instruction |= inst.operands[1].reg;
10441}
b99bd4ef 10442
c19d1205
ZW
10443static void
10444do_iwmmxt_wldstbh (void)
10445{
8f06b2d8 10446 int reloc;
c19d1205 10447 inst.instruction |= inst.operands[0].reg << 12;
8f06b2d8
PB
10448 if (thumb_mode)
10449 reloc = BFD_RELOC_ARM_T32_CP_OFF_IMM_S2;
10450 else
10451 reloc = BFD_RELOC_ARM_CP_OFF_IMM_S2;
10452 encode_arm_cp_address (1, TRUE, FALSE, reloc);
b99bd4ef
NC
10453}
10454
c19d1205
ZW
10455static void
10456do_iwmmxt_wldstw (void)
10457{
10458 /* RIWR_RIWC clears .isreg for a control register. */
10459 if (!inst.operands[0].isreg)
10460 {
10461 constraint (inst.cond != COND_ALWAYS, BAD_COND);
10462 inst.instruction |= 0xf0000000;
10463 }
b99bd4ef 10464
c19d1205
ZW
10465 inst.instruction |= inst.operands[0].reg << 12;
10466 encode_arm_cp_address (1, TRUE, TRUE, 0);
10467}
b99bd4ef
NC
10468
10469static void
c19d1205 10470do_iwmmxt_wldstd (void)
b99bd4ef 10471{
c19d1205 10472 inst.instruction |= inst.operands[0].reg << 12;
2d447fca
JM
10473 if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_cext_iwmmxt2)
10474 && inst.operands[1].immisreg)
10475 {
10476 inst.instruction &= ~0x1a000ff;
eff0bc54 10477 inst.instruction |= (0xfU << 28);
2d447fca
JM
10478 if (inst.operands[1].preind)
10479 inst.instruction |= PRE_INDEX;
10480 if (!inst.operands[1].negative)
10481 inst.instruction |= INDEX_UP;
10482 if (inst.operands[1].writeback)
10483 inst.instruction |= WRITE_BACK;
10484 inst.instruction |= inst.operands[1].reg << 16;
e2b0ab59 10485 inst.instruction |= inst.relocs[0].exp.X_add_number << 4;
2d447fca
JM
10486 inst.instruction |= inst.operands[1].imm;
10487 }
10488 else
10489 encode_arm_cp_address (1, TRUE, FALSE, 0);
c19d1205 10490}
b99bd4ef 10491
c19d1205
ZW
10492static void
10493do_iwmmxt_wshufh (void)
10494{
10495 inst.instruction |= inst.operands[0].reg << 12;
10496 inst.instruction |= inst.operands[1].reg << 16;
10497 inst.instruction |= ((inst.operands[2].imm & 0xf0) << 16);
10498 inst.instruction |= (inst.operands[2].imm & 0x0f);
10499}
b99bd4ef 10500
c19d1205
ZW
10501static void
10502do_iwmmxt_wzero (void)
10503{
10504 /* WZERO reg is an alias for WANDN reg, reg, reg. */
10505 inst.instruction |= inst.operands[0].reg;
10506 inst.instruction |= inst.operands[0].reg << 12;
10507 inst.instruction |= inst.operands[0].reg << 16;
10508}
2d447fca
JM
10509
10510static void
10511do_iwmmxt_wrwrwr_or_imm5 (void)
10512{
10513 if (inst.operands[2].isreg)
10514 do_rd_rn_rm ();
10515 else {
10516 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_cext_iwmmxt2),
10517 _("immediate operand requires iWMMXt2"));
10518 do_rd_rn ();
10519 if (inst.operands[2].imm == 0)
10520 {
10521 switch ((inst.instruction >> 20) & 0xf)
10522 {
10523 case 4:
10524 case 5:
10525 case 6:
5f4273c7 10526 case 7:
2d447fca
JM
10527 /* w...h wrd, wrn, #0 -> wrorh wrd, wrn, #16. */
10528 inst.operands[2].imm = 16;
10529 inst.instruction = (inst.instruction & 0xff0fffff) | (0x7 << 20);
10530 break;
10531 case 8:
10532 case 9:
10533 case 10:
10534 case 11:
10535 /* w...w wrd, wrn, #0 -> wrorw wrd, wrn, #32. */
10536 inst.operands[2].imm = 32;
10537 inst.instruction = (inst.instruction & 0xff0fffff) | (0xb << 20);
10538 break;
10539 case 12:
10540 case 13:
10541 case 14:
10542 case 15:
10543 {
10544 /* w...d wrd, wrn, #0 -> wor wrd, wrn, wrn. */
10545 unsigned long wrn;
10546 wrn = (inst.instruction >> 16) & 0xf;
10547 inst.instruction &= 0xff0fff0f;
10548 inst.instruction |= wrn;
10549 /* Bail out here; the instruction is now assembled. */
10550 return;
10551 }
10552 }
10553 }
10554 /* Map 32 -> 0, etc. */
10555 inst.operands[2].imm &= 0x1f;
eff0bc54 10556 inst.instruction |= (0xfU << 28) | ((inst.operands[2].imm & 0x10) << 4) | (inst.operands[2].imm & 0xf);
2d447fca
JM
10557 }
10558}
c19d1205
ZW
10559\f
10560/* Cirrus Maverick instructions. Simple 2-, 3-, and 4-register
10561 operations first, then control, shift, and load/store. */
b99bd4ef 10562
c19d1205 10563/* Insns like "foo X,Y,Z". */
b99bd4ef 10564
c19d1205
ZW
10565static void
10566do_mav_triple (void)
10567{
10568 inst.instruction |= inst.operands[0].reg << 16;
10569 inst.instruction |= inst.operands[1].reg;
10570 inst.instruction |= inst.operands[2].reg << 12;
10571}
b99bd4ef 10572
c19d1205
ZW
10573/* Insns like "foo W,X,Y,Z".
10574 where W=MVAX[0:3] and X,Y,Z=MVFX[0:15]. */
a737bd4d 10575
c19d1205
ZW
10576static void
10577do_mav_quad (void)
10578{
10579 inst.instruction |= inst.operands[0].reg << 5;
10580 inst.instruction |= inst.operands[1].reg << 12;
10581 inst.instruction |= inst.operands[2].reg << 16;
10582 inst.instruction |= inst.operands[3].reg;
a737bd4d
NC
10583}
10584
c19d1205
ZW
10585/* cfmvsc32<cond> DSPSC,MVDX[15:0]. */
10586static void
10587do_mav_dspsc (void)
a737bd4d 10588{
c19d1205
ZW
10589 inst.instruction |= inst.operands[1].reg << 12;
10590}
a737bd4d 10591
c19d1205
ZW
10592/* Maverick shift immediate instructions.
10593 cfsh32<cond> MVFX[15:0],MVFX[15:0],Shift[6:0].
10594 cfsh64<cond> MVDX[15:0],MVDX[15:0],Shift[6:0]. */
a737bd4d 10595
c19d1205
ZW
10596static void
10597do_mav_shift (void)
10598{
10599 int imm = inst.operands[2].imm;
a737bd4d 10600
c19d1205
ZW
10601 inst.instruction |= inst.operands[0].reg << 12;
10602 inst.instruction |= inst.operands[1].reg << 16;
a737bd4d 10603
c19d1205
ZW
10604 /* Bits 0-3 of the insn should have bits 0-3 of the immediate.
10605 Bits 5-7 of the insn should have bits 4-6 of the immediate.
10606 Bit 4 should be 0. */
10607 imm = (imm & 0xf) | ((imm & 0x70) << 1);
a737bd4d 10608
c19d1205
ZW
10609 inst.instruction |= imm;
10610}
10611\f
10612/* XScale instructions. Also sorted arithmetic before move. */
a737bd4d 10613
c19d1205
ZW
10614/* Xscale multiply-accumulate (argument parse)
10615 MIAcc acc0,Rm,Rs
10616 MIAPHcc acc0,Rm,Rs
10617 MIAxycc acc0,Rm,Rs. */
a737bd4d 10618
c19d1205
ZW
10619static void
10620do_xsc_mia (void)
10621{
10622 inst.instruction |= inst.operands[1].reg;
10623 inst.instruction |= inst.operands[2].reg << 12;
10624}
a737bd4d 10625
c19d1205 10626/* Xscale move-accumulator-register (argument parse)
a737bd4d 10627
c19d1205 10628 MARcc acc0,RdLo,RdHi. */
b99bd4ef 10629
c19d1205
ZW
10630static void
10631do_xsc_mar (void)
10632{
10633 inst.instruction |= inst.operands[1].reg << 12;
10634 inst.instruction |= inst.operands[2].reg << 16;
b99bd4ef
NC
10635}
10636
c19d1205 10637/* Xscale move-register-accumulator (argument parse)
b99bd4ef 10638
c19d1205 10639 MRAcc RdLo,RdHi,acc0. */
b99bd4ef
NC
10640
10641static void
c19d1205 10642do_xsc_mra (void)
b99bd4ef 10643{
c19d1205
ZW
10644 constraint (inst.operands[0].reg == inst.operands[1].reg, BAD_OVERLAP);
10645 inst.instruction |= inst.operands[0].reg << 12;
10646 inst.instruction |= inst.operands[1].reg << 16;
10647}
10648\f
10649/* Encoding functions relevant only to Thumb. */
b99bd4ef 10650
c19d1205
ZW
10651/* inst.operands[i] is a shifted-register operand; encode
10652 it into inst.instruction in the format used by Thumb32. */
10653
10654static void
10655encode_thumb32_shifted_operand (int i)
10656{
e2b0ab59 10657 unsigned int value = inst.relocs[0].exp.X_add_number;
c19d1205 10658 unsigned int shift = inst.operands[i].shift_kind;
b99bd4ef 10659
9c3c69f2
PB
10660 constraint (inst.operands[i].immisreg,
10661 _("shift by register not allowed in thumb mode"));
c19d1205
ZW
10662 inst.instruction |= inst.operands[i].reg;
10663 if (shift == SHIFT_RRX)
10664 inst.instruction |= SHIFT_ROR << 4;
10665 else
b99bd4ef 10666 {
e2b0ab59 10667 constraint (inst.relocs[0].exp.X_op != O_constant,
c19d1205
ZW
10668 _("expression too complex"));
10669
10670 constraint (value > 32
10671 || (value == 32 && (shift == SHIFT_LSL
10672 || shift == SHIFT_ROR)),
10673 _("shift expression is too large"));
10674
10675 if (value == 0)
10676 shift = SHIFT_LSL;
10677 else if (value == 32)
10678 value = 0;
10679
10680 inst.instruction |= shift << 4;
10681 inst.instruction |= (value & 0x1c) << 10;
10682 inst.instruction |= (value & 0x03) << 6;
b99bd4ef 10683 }
c19d1205 10684}
b99bd4ef 10685
b99bd4ef 10686
c19d1205
ZW
10687/* inst.operands[i] was set up by parse_address. Encode it into a
10688 Thumb32 format load or store instruction. Reject forms that cannot
10689 be used with such instructions. If is_t is true, reject forms that
10690 cannot be used with a T instruction; if is_d is true, reject forms
5be8be5d
DG
10691 that cannot be used with a D instruction. If it is a store insn,
10692 reject PC in Rn. */
b99bd4ef 10693
c19d1205
ZW
10694static void
10695encode_thumb32_addr_mode (int i, bfd_boolean is_t, bfd_boolean is_d)
10696{
5be8be5d 10697 const bfd_boolean is_pc = (inst.operands[i].reg == REG_PC);
c19d1205
ZW
10698
10699 constraint (!inst.operands[i].isreg,
53365c0d 10700 _("Instruction does not support =N addresses"));
b99bd4ef 10701
c19d1205
ZW
10702 inst.instruction |= inst.operands[i].reg << 16;
10703 if (inst.operands[i].immisreg)
b99bd4ef 10704 {
5be8be5d 10705 constraint (is_pc, BAD_PC_ADDRESSING);
c19d1205
ZW
10706 constraint (is_t || is_d, _("cannot use register index with this instruction"));
10707 constraint (inst.operands[i].negative,
10708 _("Thumb does not support negative register indexing"));
10709 constraint (inst.operands[i].postind,
10710 _("Thumb does not support register post-indexing"));
10711 constraint (inst.operands[i].writeback,
10712 _("Thumb does not support register indexing with writeback"));
10713 constraint (inst.operands[i].shifted && inst.operands[i].shift_kind != SHIFT_LSL,
10714 _("Thumb supports only LSL in shifted register indexing"));
b99bd4ef 10715
f40d1643 10716 inst.instruction |= inst.operands[i].imm;
c19d1205 10717 if (inst.operands[i].shifted)
b99bd4ef 10718 {
e2b0ab59 10719 constraint (inst.relocs[0].exp.X_op != O_constant,
c19d1205 10720 _("expression too complex"));
e2b0ab59
AV
10721 constraint (inst.relocs[0].exp.X_add_number < 0
10722 || inst.relocs[0].exp.X_add_number > 3,
c19d1205 10723 _("shift out of range"));
e2b0ab59 10724 inst.instruction |= inst.relocs[0].exp.X_add_number << 4;
c19d1205 10725 }
e2b0ab59 10726 inst.relocs[0].type = BFD_RELOC_UNUSED;
c19d1205
ZW
10727 }
10728 else if (inst.operands[i].preind)
10729 {
5be8be5d 10730 constraint (is_pc && inst.operands[i].writeback, BAD_PC_WRITEBACK);
f40d1643 10731 constraint (is_t && inst.operands[i].writeback,
c19d1205 10732 _("cannot use writeback with this instruction"));
4755303e
WN
10733 constraint (is_pc && ((inst.instruction & THUMB2_LOAD_BIT) == 0),
10734 BAD_PC_ADDRESSING);
c19d1205
ZW
10735
10736 if (is_d)
10737 {
10738 inst.instruction |= 0x01000000;
10739 if (inst.operands[i].writeback)
10740 inst.instruction |= 0x00200000;
b99bd4ef 10741 }
c19d1205 10742 else
b99bd4ef 10743 {
c19d1205
ZW
10744 inst.instruction |= 0x00000c00;
10745 if (inst.operands[i].writeback)
10746 inst.instruction |= 0x00000100;
b99bd4ef 10747 }
e2b0ab59 10748 inst.relocs[0].type = BFD_RELOC_ARM_T32_OFFSET_IMM;
b99bd4ef 10749 }
c19d1205 10750 else if (inst.operands[i].postind)
b99bd4ef 10751 {
9c2799c2 10752 gas_assert (inst.operands[i].writeback);
c19d1205
ZW
10753 constraint (is_pc, _("cannot use post-indexing with PC-relative addressing"));
10754 constraint (is_t, _("cannot use post-indexing with this instruction"));
10755
10756 if (is_d)
10757 inst.instruction |= 0x00200000;
10758 else
10759 inst.instruction |= 0x00000900;
e2b0ab59 10760 inst.relocs[0].type = BFD_RELOC_ARM_T32_OFFSET_IMM;
c19d1205
ZW
10761 }
10762 else /* unindexed - only for coprocessor */
10763 inst.error = _("instruction does not accept unindexed addressing");
10764}
10765
10766/* Table of Thumb instructions which exist in both 16- and 32-bit
10767 encodings (the latter only in post-V6T2 cores). The index is the
10768 value used in the insns table below. When there is more than one
10769 possible 16-bit encoding for the instruction, this table always
0110f2b8
PB
10770 holds variant (1).
10771 Also contains several pseudo-instructions used during relaxation. */
c19d1205 10772#define T16_32_TAB \
21d799b5
NC
10773 X(_adc, 4140, eb400000), \
10774 X(_adcs, 4140, eb500000), \
10775 X(_add, 1c00, eb000000), \
10776 X(_adds, 1c00, eb100000), \
10777 X(_addi, 0000, f1000000), \
10778 X(_addis, 0000, f1100000), \
10779 X(_add_pc,000f, f20f0000), \
10780 X(_add_sp,000d, f10d0000), \
10781 X(_adr, 000f, f20f0000), \
10782 X(_and, 4000, ea000000), \
10783 X(_ands, 4000, ea100000), \
10784 X(_asr, 1000, fa40f000), \
10785 X(_asrs, 1000, fa50f000), \
10786 X(_b, e000, f000b000), \
10787 X(_bcond, d000, f0008000), \
4389b29a 10788 X(_bf, 0000, f040e001), \
f6b2b12d 10789 X(_bfcsel,0000, f000e001), \
f1c7f421 10790 X(_bfx, 0000, f060e001), \
65d1bc05 10791 X(_bfl, 0000, f000c001), \
f1c7f421 10792 X(_bflx, 0000, f070e001), \
21d799b5
NC
10793 X(_bic, 4380, ea200000), \
10794 X(_bics, 4380, ea300000), \
10795 X(_cmn, 42c0, eb100f00), \
10796 X(_cmp, 2800, ebb00f00), \
10797 X(_cpsie, b660, f3af8400), \
10798 X(_cpsid, b670, f3af8600), \
10799 X(_cpy, 4600, ea4f0000), \
10800 X(_dec_sp,80dd, f1ad0d00), \
60f993ce 10801 X(_dls, 0000, f040e001), \
21d799b5
NC
10802 X(_eor, 4040, ea800000), \
10803 X(_eors, 4040, ea900000), \
10804 X(_inc_sp,00dd, f10d0d00), \
10805 X(_ldmia, c800, e8900000), \
10806 X(_ldr, 6800, f8500000), \
10807 X(_ldrb, 7800, f8100000), \
10808 X(_ldrh, 8800, f8300000), \
10809 X(_ldrsb, 5600, f9100000), \
10810 X(_ldrsh, 5e00, f9300000), \
10811 X(_ldr_pc,4800, f85f0000), \
10812 X(_ldr_pc2,4800, f85f0000), \
10813 X(_ldr_sp,9800, f85d0000), \
60f993ce 10814 X(_le, 0000, f00fc001), \
21d799b5
NC
10815 X(_lsl, 0000, fa00f000), \
10816 X(_lsls, 0000, fa10f000), \
10817 X(_lsr, 0800, fa20f000), \
10818 X(_lsrs, 0800, fa30f000), \
10819 X(_mov, 2000, ea4f0000), \
10820 X(_movs, 2000, ea5f0000), \
10821 X(_mul, 4340, fb00f000), \
10822 X(_muls, 4340, ffffffff), /* no 32b muls */ \
10823 X(_mvn, 43c0, ea6f0000), \
10824 X(_mvns, 43c0, ea7f0000), \
10825 X(_neg, 4240, f1c00000), /* rsb #0 */ \
10826 X(_negs, 4240, f1d00000), /* rsbs #0 */ \
10827 X(_orr, 4300, ea400000), \
10828 X(_orrs, 4300, ea500000), \
10829 X(_pop, bc00, e8bd0000), /* ldmia sp!,... */ \
10830 X(_push, b400, e92d0000), /* stmdb sp!,... */ \
10831 X(_rev, ba00, fa90f080), \
10832 X(_rev16, ba40, fa90f090), \
10833 X(_revsh, bac0, fa90f0b0), \
10834 X(_ror, 41c0, fa60f000), \
10835 X(_rors, 41c0, fa70f000), \
10836 X(_sbc, 4180, eb600000), \
10837 X(_sbcs, 4180, eb700000), \
10838 X(_stmia, c000, e8800000), \
10839 X(_str, 6000, f8400000), \
10840 X(_strb, 7000, f8000000), \
10841 X(_strh, 8000, f8200000), \
10842 X(_str_sp,9000, f84d0000), \
10843 X(_sub, 1e00, eba00000), \
10844 X(_subs, 1e00, ebb00000), \
10845 X(_subi, 8000, f1a00000), \
10846 X(_subis, 8000, f1b00000), \
10847 X(_sxtb, b240, fa4ff080), \
10848 X(_sxth, b200, fa0ff080), \
10849 X(_tst, 4200, ea100f00), \
10850 X(_uxtb, b2c0, fa5ff080), \
10851 X(_uxth, b280, fa1ff080), \
10852 X(_nop, bf00, f3af8000), \
10853 X(_yield, bf10, f3af8001), \
10854 X(_wfe, bf20, f3af8002), \
10855 X(_wfi, bf30, f3af8003), \
60f993ce 10856 X(_wls, 0000, f040c001), \
53c4b28b 10857 X(_sev, bf40, f3af8004), \
74db7efb
NC
10858 X(_sevl, bf50, f3af8005), \
10859 X(_udf, de00, f7f0a000)
c19d1205
ZW
10860
10861/* To catch errors in encoding functions, the codes are all offset by
10862 0xF800, putting them in one of the 32-bit prefix ranges, ergo undefined
10863 as 16-bit instructions. */
21d799b5 10864#define X(a,b,c) T_MNEM##a
c19d1205
ZW
10865enum t16_32_codes { T16_32_OFFSET = 0xF7FF, T16_32_TAB };
10866#undef X
10867
10868#define X(a,b,c) 0x##b
10869static const unsigned short thumb_op16[] = { T16_32_TAB };
10870#define THUMB_OP16(n) (thumb_op16[(n) - (T16_32_OFFSET + 1)])
10871#undef X
10872
10873#define X(a,b,c) 0x##c
10874static const unsigned int thumb_op32[] = { T16_32_TAB };
c921be7d
NC
10875#define THUMB_OP32(n) (thumb_op32[(n) - (T16_32_OFFSET + 1)])
10876#define THUMB_SETS_FLAGS(n) (THUMB_OP32 (n) & 0x00100000)
c19d1205
ZW
10877#undef X
10878#undef T16_32_TAB
10879
10880/* Thumb instruction encoders, in alphabetical order. */
10881
92e90b6e 10882/* ADDW or SUBW. */
c921be7d 10883
92e90b6e
PB
10884static void
10885do_t_add_sub_w (void)
10886{
10887 int Rd, Rn;
10888
10889 Rd = inst.operands[0].reg;
10890 Rn = inst.operands[1].reg;
10891
539d4391
NC
10892 /* If Rn is REG_PC, this is ADR; if Rn is REG_SP, then this
10893 is the SP-{plus,minus}-immediate form of the instruction. */
10894 if (Rn == REG_SP)
10895 constraint (Rd == REG_PC, BAD_PC);
10896 else
10897 reject_bad_reg (Rd);
fdfde340 10898
92e90b6e 10899 inst.instruction |= (Rn << 16) | (Rd << 8);
e2b0ab59 10900 inst.relocs[0].type = BFD_RELOC_ARM_T32_IMM12;
92e90b6e
PB
10901}
10902
c19d1205 10903/* Parse an add or subtract instruction. We get here with inst.instruction
33eaf5de 10904 equaling any of THUMB_OPCODE_add, adds, sub, or subs. */
c19d1205
ZW
10905
10906static void
10907do_t_add_sub (void)
10908{
10909 int Rd, Rs, Rn;
10910
10911 Rd = inst.operands[0].reg;
10912 Rs = (inst.operands[1].present
10913 ? inst.operands[1].reg /* Rd, Rs, foo */
10914 : inst.operands[0].reg); /* Rd, foo -> Rd, Rd, foo */
10915
e07e6e58 10916 if (Rd == REG_PC)
5ee91343 10917 set_pred_insn_type_last ();
e07e6e58 10918
c19d1205
ZW
10919 if (unified_syntax)
10920 {
0110f2b8
PB
10921 bfd_boolean flags;
10922 bfd_boolean narrow;
10923 int opcode;
10924
10925 flags = (inst.instruction == T_MNEM_adds
10926 || inst.instruction == T_MNEM_subs);
10927 if (flags)
5ee91343 10928 narrow = !in_pred_block ();
0110f2b8 10929 else
5ee91343 10930 narrow = in_pred_block ();
c19d1205 10931 if (!inst.operands[2].isreg)
b99bd4ef 10932 {
16805f35
PB
10933 int add;
10934
5c8ed6a4
JW
10935 if (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v8))
10936 constraint (Rd == REG_SP && Rs != REG_SP, BAD_SP);
fdfde340 10937
16805f35
PB
10938 add = (inst.instruction == T_MNEM_add
10939 || inst.instruction == T_MNEM_adds);
0110f2b8
PB
10940 opcode = 0;
10941 if (inst.size_req != 4)
10942 {
0110f2b8 10943 /* Attempt to use a narrow opcode, with relaxation if
477330fc 10944 appropriate. */
0110f2b8
PB
10945 if (Rd == REG_SP && Rs == REG_SP && !flags)
10946 opcode = add ? T_MNEM_inc_sp : T_MNEM_dec_sp;
10947 else if (Rd <= 7 && Rs == REG_SP && add && !flags)
10948 opcode = T_MNEM_add_sp;
10949 else if (Rd <= 7 && Rs == REG_PC && add && !flags)
10950 opcode = T_MNEM_add_pc;
10951 else if (Rd <= 7 && Rs <= 7 && narrow)
10952 {
10953 if (flags)
10954 opcode = add ? T_MNEM_addis : T_MNEM_subis;
10955 else
10956 opcode = add ? T_MNEM_addi : T_MNEM_subi;
10957 }
10958 if (opcode)
10959 {
10960 inst.instruction = THUMB_OP16(opcode);
10961 inst.instruction |= (Rd << 4) | Rs;
e2b0ab59
AV
10962 if (inst.relocs[0].type < BFD_RELOC_ARM_THUMB_ALU_ABS_G0_NC
10963 || (inst.relocs[0].type
10964 > BFD_RELOC_ARM_THUMB_ALU_ABS_G3_NC))
a9f02af8
MG
10965 {
10966 if (inst.size_req == 2)
e2b0ab59 10967 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_ADD;
a9f02af8
MG
10968 else
10969 inst.relax = opcode;
10970 }
0110f2b8
PB
10971 }
10972 else
10973 constraint (inst.size_req == 2, BAD_HIREG);
10974 }
10975 if (inst.size_req == 4
10976 || (inst.size_req != 2 && !opcode))
10977 {
e2b0ab59
AV
10978 constraint ((inst.relocs[0].type
10979 >= BFD_RELOC_ARM_THUMB_ALU_ABS_G0_NC)
10980 && (inst.relocs[0].type
10981 <= BFD_RELOC_ARM_THUMB_ALU_ABS_G3_NC) ,
a9f02af8 10982 THUMB1_RELOC_ONLY);
efd81785
PB
10983 if (Rd == REG_PC)
10984 {
fdfde340 10985 constraint (add, BAD_PC);
efd81785
PB
10986 constraint (Rs != REG_LR || inst.instruction != T_MNEM_subs,
10987 _("only SUBS PC, LR, #const allowed"));
e2b0ab59 10988 constraint (inst.relocs[0].exp.X_op != O_constant,
efd81785 10989 _("expression too complex"));
e2b0ab59
AV
10990 constraint (inst.relocs[0].exp.X_add_number < 0
10991 || inst.relocs[0].exp.X_add_number > 0xff,
efd81785
PB
10992 _("immediate value out of range"));
10993 inst.instruction = T2_SUBS_PC_LR
e2b0ab59
AV
10994 | inst.relocs[0].exp.X_add_number;
10995 inst.relocs[0].type = BFD_RELOC_UNUSED;
efd81785
PB
10996 return;
10997 }
10998 else if (Rs == REG_PC)
16805f35
PB
10999 {
11000 /* Always use addw/subw. */
11001 inst.instruction = add ? 0xf20f0000 : 0xf2af0000;
e2b0ab59 11002 inst.relocs[0].type = BFD_RELOC_ARM_T32_IMM12;
16805f35
PB
11003 }
11004 else
11005 {
11006 inst.instruction = THUMB_OP32 (inst.instruction);
11007 inst.instruction = (inst.instruction & 0xe1ffffff)
11008 | 0x10000000;
11009 if (flags)
e2b0ab59 11010 inst.relocs[0].type = BFD_RELOC_ARM_T32_IMMEDIATE;
16805f35 11011 else
e2b0ab59 11012 inst.relocs[0].type = BFD_RELOC_ARM_T32_ADD_IMM;
16805f35 11013 }
dc4503c6
PB
11014 inst.instruction |= Rd << 8;
11015 inst.instruction |= Rs << 16;
0110f2b8 11016 }
b99bd4ef 11017 }
c19d1205
ZW
11018 else
11019 {
e2b0ab59 11020 unsigned int value = inst.relocs[0].exp.X_add_number;
5f4cb198
NC
11021 unsigned int shift = inst.operands[2].shift_kind;
11022
c19d1205
ZW
11023 Rn = inst.operands[2].reg;
11024 /* See if we can do this with a 16-bit instruction. */
11025 if (!inst.operands[2].shifted && inst.size_req != 4)
11026 {
e27ec89e
PB
11027 if (Rd > 7 || Rs > 7 || Rn > 7)
11028 narrow = FALSE;
11029
11030 if (narrow)
c19d1205 11031 {
e27ec89e
PB
11032 inst.instruction = ((inst.instruction == T_MNEM_adds
11033 || inst.instruction == T_MNEM_add)
c19d1205
ZW
11034 ? T_OPCODE_ADD_R3
11035 : T_OPCODE_SUB_R3);
11036 inst.instruction |= Rd | (Rs << 3) | (Rn << 6);
11037 return;
11038 }
b99bd4ef 11039
7e806470 11040 if (inst.instruction == T_MNEM_add && (Rd == Rs || Rd == Rn))
c19d1205 11041 {
7e806470
PB
11042 /* Thumb-1 cores (except v6-M) require at least one high
11043 register in a narrow non flag setting add. */
11044 if (Rd > 7 || Rn > 7
11045 || ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6t2)
11046 || ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_msr))
c19d1205 11047 {
7e806470
PB
11048 if (Rd == Rn)
11049 {
11050 Rn = Rs;
11051 Rs = Rd;
11052 }
c19d1205
ZW
11053 inst.instruction = T_OPCODE_ADD_HI;
11054 inst.instruction |= (Rd & 8) << 4;
11055 inst.instruction |= (Rd & 7);
11056 inst.instruction |= Rn << 3;
11057 return;
11058 }
c19d1205
ZW
11059 }
11060 }
c921be7d 11061
fdfde340 11062 constraint (Rd == REG_PC, BAD_PC);
5c8ed6a4
JW
11063 if (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v8))
11064 constraint (Rd == REG_SP && Rs != REG_SP, BAD_SP);
fdfde340
JM
11065 constraint (Rs == REG_PC, BAD_PC);
11066 reject_bad_reg (Rn);
11067
c19d1205
ZW
11068 /* If we get here, it can't be done in 16 bits. */
11069 constraint (inst.operands[2].shifted && inst.operands[2].immisreg,
11070 _("shift must be constant"));
11071 inst.instruction = THUMB_OP32 (inst.instruction);
11072 inst.instruction |= Rd << 8;
11073 inst.instruction |= Rs << 16;
5f4cb198
NC
11074 constraint (Rd == REG_SP && Rs == REG_SP && value > 3,
11075 _("shift value over 3 not allowed in thumb mode"));
11076 constraint (Rd == REG_SP && Rs == REG_SP && shift != SHIFT_LSL,
11077 _("only LSL shift allowed in thumb mode"));
c19d1205
ZW
11078 encode_thumb32_shifted_operand (2);
11079 }
11080 }
11081 else
11082 {
11083 constraint (inst.instruction == T_MNEM_adds
11084 || inst.instruction == T_MNEM_subs,
11085 BAD_THUMB32);
b99bd4ef 11086
c19d1205 11087 if (!inst.operands[2].isreg) /* Rd, Rs, #imm */
b99bd4ef 11088 {
c19d1205
ZW
11089 constraint ((Rd > 7 && (Rd != REG_SP || Rs != REG_SP))
11090 || (Rs > 7 && Rs != REG_SP && Rs != REG_PC),
11091 BAD_HIREG);
11092
11093 inst.instruction = (inst.instruction == T_MNEM_add
11094 ? 0x0000 : 0x8000);
11095 inst.instruction |= (Rd << 4) | Rs;
e2b0ab59 11096 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_ADD;
b99bd4ef
NC
11097 return;
11098 }
11099
c19d1205
ZW
11100 Rn = inst.operands[2].reg;
11101 constraint (inst.operands[2].shifted, _("unshifted register required"));
b99bd4ef 11102
c19d1205
ZW
11103 /* We now have Rd, Rs, and Rn set to registers. */
11104 if (Rd > 7 || Rs > 7 || Rn > 7)
b99bd4ef 11105 {
c19d1205
ZW
11106 /* Can't do this for SUB. */
11107 constraint (inst.instruction == T_MNEM_sub, BAD_HIREG);
11108 inst.instruction = T_OPCODE_ADD_HI;
11109 inst.instruction |= (Rd & 8) << 4;
11110 inst.instruction |= (Rd & 7);
11111 if (Rs == Rd)
11112 inst.instruction |= Rn << 3;
11113 else if (Rn == Rd)
11114 inst.instruction |= Rs << 3;
11115 else
11116 constraint (1, _("dest must overlap one source register"));
11117 }
11118 else
11119 {
11120 inst.instruction = (inst.instruction == T_MNEM_add
11121 ? T_OPCODE_ADD_R3 : T_OPCODE_SUB_R3);
11122 inst.instruction |= Rd | (Rs << 3) | (Rn << 6);
b99bd4ef 11123 }
b99bd4ef 11124 }
b99bd4ef
NC
11125}
11126
c19d1205
ZW
11127static void
11128do_t_adr (void)
11129{
fdfde340
JM
11130 unsigned Rd;
11131
11132 Rd = inst.operands[0].reg;
11133 reject_bad_reg (Rd);
11134
11135 if (unified_syntax && inst.size_req == 0 && Rd <= 7)
0110f2b8
PB
11136 {
11137 /* Defer to section relaxation. */
11138 inst.relax = inst.instruction;
11139 inst.instruction = THUMB_OP16 (inst.instruction);
fdfde340 11140 inst.instruction |= Rd << 4;
0110f2b8
PB
11141 }
11142 else if (unified_syntax && inst.size_req != 2)
e9f89963 11143 {
0110f2b8 11144 /* Generate a 32-bit opcode. */
e9f89963 11145 inst.instruction = THUMB_OP32 (inst.instruction);
fdfde340 11146 inst.instruction |= Rd << 8;
e2b0ab59
AV
11147 inst.relocs[0].type = BFD_RELOC_ARM_T32_ADD_PC12;
11148 inst.relocs[0].pc_rel = 1;
e9f89963
PB
11149 }
11150 else
11151 {
0110f2b8 11152 /* Generate a 16-bit opcode. */
e9f89963 11153 inst.instruction = THUMB_OP16 (inst.instruction);
e2b0ab59
AV
11154 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_ADD;
11155 inst.relocs[0].exp.X_add_number -= 4; /* PC relative adjust. */
11156 inst.relocs[0].pc_rel = 1;
fdfde340 11157 inst.instruction |= Rd << 4;
e9f89963 11158 }
52a86f84 11159
e2b0ab59
AV
11160 if (inst.relocs[0].exp.X_op == O_symbol
11161 && inst.relocs[0].exp.X_add_symbol != NULL
11162 && S_IS_DEFINED (inst.relocs[0].exp.X_add_symbol)
11163 && THUMB_IS_FUNC (inst.relocs[0].exp.X_add_symbol))
11164 inst.relocs[0].exp.X_add_number += 1;
c19d1205 11165}
b99bd4ef 11166
c19d1205
ZW
11167/* Arithmetic instructions for which there is just one 16-bit
11168 instruction encoding, and it allows only two low registers.
11169 For maximal compatibility with ARM syntax, we allow three register
11170 operands even when Thumb-32 instructions are not available, as long
11171 as the first two are identical. For instance, both "sbc r0,r1" and
11172 "sbc r0,r0,r1" are allowed. */
b99bd4ef 11173static void
c19d1205 11174do_t_arit3 (void)
b99bd4ef 11175{
c19d1205 11176 int Rd, Rs, Rn;
b99bd4ef 11177
c19d1205
ZW
11178 Rd = inst.operands[0].reg;
11179 Rs = (inst.operands[1].present
11180 ? inst.operands[1].reg /* Rd, Rs, foo */
11181 : inst.operands[0].reg); /* Rd, foo -> Rd, Rd, foo */
11182 Rn = inst.operands[2].reg;
b99bd4ef 11183
fdfde340
JM
11184 reject_bad_reg (Rd);
11185 reject_bad_reg (Rs);
11186 if (inst.operands[2].isreg)
11187 reject_bad_reg (Rn);
11188
c19d1205 11189 if (unified_syntax)
b99bd4ef 11190 {
c19d1205
ZW
11191 if (!inst.operands[2].isreg)
11192 {
11193 /* For an immediate, we always generate a 32-bit opcode;
11194 section relaxation will shrink it later if possible. */
11195 inst.instruction = THUMB_OP32 (inst.instruction);
11196 inst.instruction = (inst.instruction & 0xe1ffffff) | 0x10000000;
11197 inst.instruction |= Rd << 8;
11198 inst.instruction |= Rs << 16;
e2b0ab59 11199 inst.relocs[0].type = BFD_RELOC_ARM_T32_IMMEDIATE;
c19d1205
ZW
11200 }
11201 else
11202 {
e27ec89e
PB
11203 bfd_boolean narrow;
11204
c19d1205 11205 /* See if we can do this with a 16-bit instruction. */
e27ec89e 11206 if (THUMB_SETS_FLAGS (inst.instruction))
5ee91343 11207 narrow = !in_pred_block ();
e27ec89e 11208 else
5ee91343 11209 narrow = in_pred_block ();
e27ec89e
PB
11210
11211 if (Rd > 7 || Rn > 7 || Rs > 7)
11212 narrow = FALSE;
11213 if (inst.operands[2].shifted)
11214 narrow = FALSE;
11215 if (inst.size_req == 4)
11216 narrow = FALSE;
11217
11218 if (narrow
c19d1205
ZW
11219 && Rd == Rs)
11220 {
11221 inst.instruction = THUMB_OP16 (inst.instruction);
11222 inst.instruction |= Rd;
11223 inst.instruction |= Rn << 3;
11224 return;
11225 }
b99bd4ef 11226
c19d1205
ZW
11227 /* If we get here, it can't be done in 16 bits. */
11228 constraint (inst.operands[2].shifted
11229 && inst.operands[2].immisreg,
11230 _("shift must be constant"));
11231 inst.instruction = THUMB_OP32 (inst.instruction);
11232 inst.instruction |= Rd << 8;
11233 inst.instruction |= Rs << 16;
11234 encode_thumb32_shifted_operand (2);
11235 }
a737bd4d 11236 }
c19d1205 11237 else
b99bd4ef 11238 {
c19d1205
ZW
11239 /* On its face this is a lie - the instruction does set the
11240 flags. However, the only supported mnemonic in this mode
11241 says it doesn't. */
11242 constraint (THUMB_SETS_FLAGS (inst.instruction), BAD_THUMB32);
a737bd4d 11243
c19d1205
ZW
11244 constraint (!inst.operands[2].isreg || inst.operands[2].shifted,
11245 _("unshifted register required"));
11246 constraint (Rd > 7 || Rs > 7 || Rn > 7, BAD_HIREG);
11247 constraint (Rd != Rs,
11248 _("dest and source1 must be the same register"));
a737bd4d 11249
c19d1205
ZW
11250 inst.instruction = THUMB_OP16 (inst.instruction);
11251 inst.instruction |= Rd;
11252 inst.instruction |= Rn << 3;
b99bd4ef 11253 }
a737bd4d 11254}
b99bd4ef 11255
c19d1205
ZW
11256/* Similarly, but for instructions where the arithmetic operation is
11257 commutative, so we can allow either of them to be different from
11258 the destination operand in a 16-bit instruction. For instance, all
11259 three of "adc r0,r1", "adc r0,r0,r1", and "adc r0,r1,r0" are
11260 accepted. */
11261static void
11262do_t_arit3c (void)
a737bd4d 11263{
c19d1205 11264 int Rd, Rs, Rn;
b99bd4ef 11265
c19d1205
ZW
11266 Rd = inst.operands[0].reg;
11267 Rs = (inst.operands[1].present
11268 ? inst.operands[1].reg /* Rd, Rs, foo */
11269 : inst.operands[0].reg); /* Rd, foo -> Rd, Rd, foo */
11270 Rn = inst.operands[2].reg;
c921be7d 11271
fdfde340
JM
11272 reject_bad_reg (Rd);
11273 reject_bad_reg (Rs);
11274 if (inst.operands[2].isreg)
11275 reject_bad_reg (Rn);
a737bd4d 11276
c19d1205 11277 if (unified_syntax)
a737bd4d 11278 {
c19d1205 11279 if (!inst.operands[2].isreg)
b99bd4ef 11280 {
c19d1205
ZW
11281 /* For an immediate, we always generate a 32-bit opcode;
11282 section relaxation will shrink it later if possible. */
11283 inst.instruction = THUMB_OP32 (inst.instruction);
11284 inst.instruction = (inst.instruction & 0xe1ffffff) | 0x10000000;
11285 inst.instruction |= Rd << 8;
11286 inst.instruction |= Rs << 16;
e2b0ab59 11287 inst.relocs[0].type = BFD_RELOC_ARM_T32_IMMEDIATE;
b99bd4ef 11288 }
c19d1205 11289 else
a737bd4d 11290 {
e27ec89e
PB
11291 bfd_boolean narrow;
11292
c19d1205 11293 /* See if we can do this with a 16-bit instruction. */
e27ec89e 11294 if (THUMB_SETS_FLAGS (inst.instruction))
5ee91343 11295 narrow = !in_pred_block ();
e27ec89e 11296 else
5ee91343 11297 narrow = in_pred_block ();
e27ec89e
PB
11298
11299 if (Rd > 7 || Rn > 7 || Rs > 7)
11300 narrow = FALSE;
11301 if (inst.operands[2].shifted)
11302 narrow = FALSE;
11303 if (inst.size_req == 4)
11304 narrow = FALSE;
11305
11306 if (narrow)
a737bd4d 11307 {
c19d1205 11308 if (Rd == Rs)
a737bd4d 11309 {
c19d1205
ZW
11310 inst.instruction = THUMB_OP16 (inst.instruction);
11311 inst.instruction |= Rd;
11312 inst.instruction |= Rn << 3;
11313 return;
a737bd4d 11314 }
c19d1205 11315 if (Rd == Rn)
a737bd4d 11316 {
c19d1205
ZW
11317 inst.instruction = THUMB_OP16 (inst.instruction);
11318 inst.instruction |= Rd;
11319 inst.instruction |= Rs << 3;
11320 return;
a737bd4d
NC
11321 }
11322 }
c19d1205
ZW
11323
11324 /* If we get here, it can't be done in 16 bits. */
11325 constraint (inst.operands[2].shifted
11326 && inst.operands[2].immisreg,
11327 _("shift must be constant"));
11328 inst.instruction = THUMB_OP32 (inst.instruction);
11329 inst.instruction |= Rd << 8;
11330 inst.instruction |= Rs << 16;
11331 encode_thumb32_shifted_operand (2);
a737bd4d 11332 }
b99bd4ef 11333 }
c19d1205
ZW
11334 else
11335 {
11336 /* On its face this is a lie - the instruction does set the
11337 flags. However, the only supported mnemonic in this mode
11338 says it doesn't. */
11339 constraint (THUMB_SETS_FLAGS (inst.instruction), BAD_THUMB32);
a737bd4d 11340
c19d1205
ZW
11341 constraint (!inst.operands[2].isreg || inst.operands[2].shifted,
11342 _("unshifted register required"));
11343 constraint (Rd > 7 || Rs > 7 || Rn > 7, BAD_HIREG);
11344
11345 inst.instruction = THUMB_OP16 (inst.instruction);
11346 inst.instruction |= Rd;
11347
11348 if (Rd == Rs)
11349 inst.instruction |= Rn << 3;
11350 else if (Rd == Rn)
11351 inst.instruction |= Rs << 3;
11352 else
11353 constraint (1, _("dest must overlap one source register"));
11354 }
a737bd4d
NC
11355}
11356
c19d1205
ZW
11357static void
11358do_t_bfc (void)
a737bd4d 11359{
fdfde340 11360 unsigned Rd;
c19d1205
ZW
11361 unsigned int msb = inst.operands[1].imm + inst.operands[2].imm;
11362 constraint (msb > 32, _("bit-field extends past end of register"));
11363 /* The instruction encoding stores the LSB and MSB,
11364 not the LSB and width. */
fdfde340
JM
11365 Rd = inst.operands[0].reg;
11366 reject_bad_reg (Rd);
11367 inst.instruction |= Rd << 8;
c19d1205
ZW
11368 inst.instruction |= (inst.operands[1].imm & 0x1c) << 10;
11369 inst.instruction |= (inst.operands[1].imm & 0x03) << 6;
11370 inst.instruction |= msb - 1;
b99bd4ef
NC
11371}
11372
c19d1205
ZW
11373static void
11374do_t_bfi (void)
b99bd4ef 11375{
fdfde340 11376 int Rd, Rn;
c19d1205 11377 unsigned int msb;
b99bd4ef 11378
fdfde340
JM
11379 Rd = inst.operands[0].reg;
11380 reject_bad_reg (Rd);
11381
c19d1205
ZW
11382 /* #0 in second position is alternative syntax for bfc, which is
11383 the same instruction but with REG_PC in the Rm field. */
11384 if (!inst.operands[1].isreg)
fdfde340
JM
11385 Rn = REG_PC;
11386 else
11387 {
11388 Rn = inst.operands[1].reg;
11389 reject_bad_reg (Rn);
11390 }
b99bd4ef 11391
c19d1205
ZW
11392 msb = inst.operands[2].imm + inst.operands[3].imm;
11393 constraint (msb > 32, _("bit-field extends past end of register"));
11394 /* The instruction encoding stores the LSB and MSB,
11395 not the LSB and width. */
fdfde340
JM
11396 inst.instruction |= Rd << 8;
11397 inst.instruction |= Rn << 16;
c19d1205
ZW
11398 inst.instruction |= (inst.operands[2].imm & 0x1c) << 10;
11399 inst.instruction |= (inst.operands[2].imm & 0x03) << 6;
11400 inst.instruction |= msb - 1;
b99bd4ef
NC
11401}
11402
c19d1205
ZW
11403static void
11404do_t_bfx (void)
b99bd4ef 11405{
fdfde340
JM
11406 unsigned Rd, Rn;
11407
11408 Rd = inst.operands[0].reg;
11409 Rn = inst.operands[1].reg;
11410
11411 reject_bad_reg (Rd);
11412 reject_bad_reg (Rn);
11413
c19d1205
ZW
11414 constraint (inst.operands[2].imm + inst.operands[3].imm > 32,
11415 _("bit-field extends past end of register"));
fdfde340
JM
11416 inst.instruction |= Rd << 8;
11417 inst.instruction |= Rn << 16;
c19d1205
ZW
11418 inst.instruction |= (inst.operands[2].imm & 0x1c) << 10;
11419 inst.instruction |= (inst.operands[2].imm & 0x03) << 6;
11420 inst.instruction |= inst.operands[3].imm - 1;
11421}
b99bd4ef 11422
c19d1205
ZW
11423/* ARM V5 Thumb BLX (argument parse)
11424 BLX <target_addr> which is BLX(1)
11425 BLX <Rm> which is BLX(2)
11426 Unfortunately, there are two different opcodes for this mnemonic.
11427 So, the insns[].value is not used, and the code here zaps values
11428 into inst.instruction.
b99bd4ef 11429
c19d1205
ZW
11430 ??? How to take advantage of the additional two bits of displacement
11431 available in Thumb32 mode? Need new relocation? */
b99bd4ef 11432
c19d1205
ZW
11433static void
11434do_t_blx (void)
11435{
5ee91343 11436 set_pred_insn_type_last ();
e07e6e58 11437
c19d1205 11438 if (inst.operands[0].isreg)
fdfde340
JM
11439 {
11440 constraint (inst.operands[0].reg == REG_PC, BAD_PC);
11441 /* We have a register, so this is BLX(2). */
11442 inst.instruction |= inst.operands[0].reg << 3;
11443 }
b99bd4ef
NC
11444 else
11445 {
c19d1205 11446 /* No register. This must be BLX(1). */
2fc8bdac 11447 inst.instruction = 0xf000e800;
0855e32b 11448 encode_branch (BFD_RELOC_THUMB_PCREL_BLX);
b99bd4ef
NC
11449 }
11450}
11451
c19d1205
ZW
11452static void
11453do_t_branch (void)
b99bd4ef 11454{
0110f2b8 11455 int opcode;
dfa9f0d5 11456 int cond;
2fe88214 11457 bfd_reloc_code_real_type reloc;
dfa9f0d5 11458
e07e6e58 11459 cond = inst.cond;
5ee91343 11460 set_pred_insn_type (IF_INSIDE_IT_LAST_INSN);
e07e6e58 11461
5ee91343 11462 if (in_pred_block ())
dfa9f0d5
PB
11463 {
11464 /* Conditional branches inside IT blocks are encoded as unconditional
477330fc 11465 branches. */
dfa9f0d5 11466 cond = COND_ALWAYS;
dfa9f0d5
PB
11467 }
11468 else
11469 cond = inst.cond;
11470
11471 if (cond != COND_ALWAYS)
0110f2b8
PB
11472 opcode = T_MNEM_bcond;
11473 else
11474 opcode = inst.instruction;
11475
12d6b0b7
RS
11476 if (unified_syntax
11477 && (inst.size_req == 4
10960bfb
PB
11478 || (inst.size_req != 2
11479 && (inst.operands[0].hasreloc
e2b0ab59 11480 || inst.relocs[0].exp.X_op == O_constant))))
c19d1205 11481 {
0110f2b8 11482 inst.instruction = THUMB_OP32(opcode);
dfa9f0d5 11483 if (cond == COND_ALWAYS)
9ae92b05 11484 reloc = BFD_RELOC_THUMB_PCREL_BRANCH25;
c19d1205
ZW
11485 else
11486 {
ff8646ee
TP
11487 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6t2),
11488 _("selected architecture does not support "
11489 "wide conditional branch instruction"));
11490
9c2799c2 11491 gas_assert (cond != 0xF);
dfa9f0d5 11492 inst.instruction |= cond << 22;
9ae92b05 11493 reloc = BFD_RELOC_THUMB_PCREL_BRANCH20;
c19d1205
ZW
11494 }
11495 }
b99bd4ef
NC
11496 else
11497 {
0110f2b8 11498 inst.instruction = THUMB_OP16(opcode);
dfa9f0d5 11499 if (cond == COND_ALWAYS)
9ae92b05 11500 reloc = BFD_RELOC_THUMB_PCREL_BRANCH12;
c19d1205 11501 else
b99bd4ef 11502 {
dfa9f0d5 11503 inst.instruction |= cond << 8;
9ae92b05 11504 reloc = BFD_RELOC_THUMB_PCREL_BRANCH9;
b99bd4ef 11505 }
0110f2b8
PB
11506 /* Allow section relaxation. */
11507 if (unified_syntax && inst.size_req != 2)
11508 inst.relax = opcode;
b99bd4ef 11509 }
e2b0ab59
AV
11510 inst.relocs[0].type = reloc;
11511 inst.relocs[0].pc_rel = 1;
b99bd4ef
NC
11512}
11513
8884b720 11514/* Actually do the work for Thumb state bkpt and hlt. The only difference
bacebabc 11515 between the two is the maximum immediate allowed - which is passed in
8884b720 11516 RANGE. */
b99bd4ef 11517static void
8884b720 11518do_t_bkpt_hlt1 (int range)
b99bd4ef 11519{
dfa9f0d5
PB
11520 constraint (inst.cond != COND_ALWAYS,
11521 _("instruction is always unconditional"));
c19d1205 11522 if (inst.operands[0].present)
b99bd4ef 11523 {
8884b720 11524 constraint (inst.operands[0].imm > range,
c19d1205
ZW
11525 _("immediate value out of range"));
11526 inst.instruction |= inst.operands[0].imm;
b99bd4ef 11527 }
8884b720 11528
5ee91343 11529 set_pred_insn_type (NEUTRAL_IT_INSN);
8884b720
MGD
11530}
11531
11532static void
11533do_t_hlt (void)
11534{
11535 do_t_bkpt_hlt1 (63);
11536}
11537
11538static void
11539do_t_bkpt (void)
11540{
11541 do_t_bkpt_hlt1 (255);
b99bd4ef
NC
11542}
11543
11544static void
c19d1205 11545do_t_branch23 (void)
b99bd4ef 11546{
5ee91343 11547 set_pred_insn_type_last ();
0855e32b 11548 encode_branch (BFD_RELOC_THUMB_PCREL_BRANCH23);
fa94de6b 11549
0855e32b
NS
11550 /* md_apply_fix blows up with 'bl foo(PLT)' where foo is defined in
11551 this file. We used to simply ignore the PLT reloc type here --
11552 the branch encoding is now needed to deal with TLSCALL relocs.
11553 So if we see a PLT reloc now, put it back to how it used to be to
11554 keep the preexisting behaviour. */
e2b0ab59
AV
11555 if (inst.relocs[0].type == BFD_RELOC_ARM_PLT32)
11556 inst.relocs[0].type = BFD_RELOC_THUMB_PCREL_BRANCH23;
90e4755a 11557
4343666d 11558#if defined(OBJ_COFF)
c19d1205
ZW
11559 /* If the destination of the branch is a defined symbol which does not have
11560 the THUMB_FUNC attribute, then we must be calling a function which has
11561 the (interfacearm) attribute. We look for the Thumb entry point to that
11562 function and change the branch to refer to that function instead. */
e2b0ab59
AV
11563 if ( inst.relocs[0].exp.X_op == O_symbol
11564 && inst.relocs[0].exp.X_add_symbol != NULL
11565 && S_IS_DEFINED (inst.relocs[0].exp.X_add_symbol)
11566 && ! THUMB_IS_FUNC (inst.relocs[0].exp.X_add_symbol))
11567 inst.relocs[0].exp.X_add_symbol
11568 = find_real_start (inst.relocs[0].exp.X_add_symbol);
4343666d 11569#endif
90e4755a
RE
11570}
11571
11572static void
c19d1205 11573do_t_bx (void)
90e4755a 11574{
5ee91343 11575 set_pred_insn_type_last ();
c19d1205
ZW
11576 inst.instruction |= inst.operands[0].reg << 3;
11577 /* ??? FIXME: Should add a hacky reloc here if reg is REG_PC. The reloc
11578 should cause the alignment to be checked once it is known. This is
11579 because BX PC only works if the instruction is word aligned. */
11580}
90e4755a 11581
c19d1205
ZW
11582static void
11583do_t_bxj (void)
11584{
fdfde340 11585 int Rm;
90e4755a 11586
5ee91343 11587 set_pred_insn_type_last ();
fdfde340
JM
11588 Rm = inst.operands[0].reg;
11589 reject_bad_reg (Rm);
11590 inst.instruction |= Rm << 16;
90e4755a
RE
11591}
11592
11593static void
c19d1205 11594do_t_clz (void)
90e4755a 11595{
fdfde340
JM
11596 unsigned Rd;
11597 unsigned Rm;
11598
11599 Rd = inst.operands[0].reg;
11600 Rm = inst.operands[1].reg;
11601
11602 reject_bad_reg (Rd);
11603 reject_bad_reg (Rm);
11604
11605 inst.instruction |= Rd << 8;
11606 inst.instruction |= Rm << 16;
11607 inst.instruction |= Rm;
c19d1205 11608}
90e4755a 11609
91d8b670
JG
11610static void
11611do_t_csdb (void)
11612{
5ee91343 11613 set_pred_insn_type (OUTSIDE_PRED_INSN);
91d8b670
JG
11614}
11615
dfa9f0d5
PB
11616static void
11617do_t_cps (void)
11618{
5ee91343 11619 set_pred_insn_type (OUTSIDE_PRED_INSN);
dfa9f0d5
PB
11620 inst.instruction |= inst.operands[0].imm;
11621}
11622
c19d1205
ZW
11623static void
11624do_t_cpsi (void)
11625{
5ee91343 11626 set_pred_insn_type (OUTSIDE_PRED_INSN);
c19d1205 11627 if (unified_syntax
62b3e311
PB
11628 && (inst.operands[1].present || inst.size_req == 4)
11629 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6_notm))
90e4755a 11630 {
c19d1205
ZW
11631 unsigned int imod = (inst.instruction & 0x0030) >> 4;
11632 inst.instruction = 0xf3af8000;
11633 inst.instruction |= imod << 9;
11634 inst.instruction |= inst.operands[0].imm << 5;
11635 if (inst.operands[1].present)
11636 inst.instruction |= 0x100 | inst.operands[1].imm;
90e4755a 11637 }
c19d1205 11638 else
90e4755a 11639 {
62b3e311
PB
11640 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v1)
11641 && (inst.operands[0].imm & 4),
11642 _("selected processor does not support 'A' form "
11643 "of this instruction"));
11644 constraint (inst.operands[1].present || inst.size_req == 4,
c19d1205
ZW
11645 _("Thumb does not support the 2-argument "
11646 "form of this instruction"));
11647 inst.instruction |= inst.operands[0].imm;
90e4755a 11648 }
90e4755a
RE
11649}
11650
c19d1205
ZW
11651/* THUMB CPY instruction (argument parse). */
11652
90e4755a 11653static void
c19d1205 11654do_t_cpy (void)
90e4755a 11655{
c19d1205 11656 if (inst.size_req == 4)
90e4755a 11657 {
c19d1205
ZW
11658 inst.instruction = THUMB_OP32 (T_MNEM_mov);
11659 inst.instruction |= inst.operands[0].reg << 8;
11660 inst.instruction |= inst.operands[1].reg;
90e4755a 11661 }
c19d1205 11662 else
90e4755a 11663 {
c19d1205
ZW
11664 inst.instruction |= (inst.operands[0].reg & 0x8) << 4;
11665 inst.instruction |= (inst.operands[0].reg & 0x7);
11666 inst.instruction |= inst.operands[1].reg << 3;
90e4755a 11667 }
90e4755a
RE
11668}
11669
90e4755a 11670static void
25fe350b 11671do_t_cbz (void)
90e4755a 11672{
5ee91343 11673 set_pred_insn_type (OUTSIDE_PRED_INSN);
c19d1205
ZW
11674 constraint (inst.operands[0].reg > 7, BAD_HIREG);
11675 inst.instruction |= inst.operands[0].reg;
e2b0ab59
AV
11676 inst.relocs[0].pc_rel = 1;
11677 inst.relocs[0].type = BFD_RELOC_THUMB_PCREL_BRANCH7;
c19d1205 11678}
90e4755a 11679
62b3e311
PB
11680static void
11681do_t_dbg (void)
11682{
11683 inst.instruction |= inst.operands[0].imm;
11684}
11685
11686static void
11687do_t_div (void)
11688{
fdfde340
JM
11689 unsigned Rd, Rn, Rm;
11690
11691 Rd = inst.operands[0].reg;
11692 Rn = (inst.operands[1].present
11693 ? inst.operands[1].reg : Rd);
11694 Rm = inst.operands[2].reg;
11695
11696 reject_bad_reg (Rd);
11697 reject_bad_reg (Rn);
11698 reject_bad_reg (Rm);
11699
11700 inst.instruction |= Rd << 8;
11701 inst.instruction |= Rn << 16;
11702 inst.instruction |= Rm;
62b3e311
PB
11703}
11704
c19d1205
ZW
11705static void
11706do_t_hint (void)
11707{
11708 if (unified_syntax && inst.size_req == 4)
11709 inst.instruction = THUMB_OP32 (inst.instruction);
11710 else
11711 inst.instruction = THUMB_OP16 (inst.instruction);
11712}
90e4755a 11713
c19d1205
ZW
11714static void
11715do_t_it (void)
11716{
11717 unsigned int cond = inst.operands[0].imm;
e27ec89e 11718
5ee91343
AV
11719 set_pred_insn_type (IT_INSN);
11720 now_pred.mask = (inst.instruction & 0xf) | 0x10;
11721 now_pred.cc = cond;
11722 now_pred.warn_deprecated = FALSE;
11723 now_pred.type = SCALAR_PRED;
e27ec89e
PB
11724
11725 /* If the condition is a negative condition, invert the mask. */
c19d1205 11726 if ((cond & 0x1) == 0x0)
90e4755a 11727 {
c19d1205 11728 unsigned int mask = inst.instruction & 0x000f;
90e4755a 11729
c19d1205 11730 if ((mask & 0x7) == 0)
5a01bb1d
MGD
11731 {
11732 /* No conversion needed. */
5ee91343 11733 now_pred.block_length = 1;
5a01bb1d 11734 }
c19d1205 11735 else if ((mask & 0x3) == 0)
5a01bb1d
MGD
11736 {
11737 mask ^= 0x8;
5ee91343 11738 now_pred.block_length = 2;
5a01bb1d 11739 }
e27ec89e 11740 else if ((mask & 0x1) == 0)
5a01bb1d
MGD
11741 {
11742 mask ^= 0xC;
5ee91343 11743 now_pred.block_length = 3;
5a01bb1d 11744 }
c19d1205 11745 else
5a01bb1d
MGD
11746 {
11747 mask ^= 0xE;
5ee91343 11748 now_pred.block_length = 4;
5a01bb1d 11749 }
90e4755a 11750
e27ec89e
PB
11751 inst.instruction &= 0xfff0;
11752 inst.instruction |= mask;
c19d1205 11753 }
90e4755a 11754
c19d1205
ZW
11755 inst.instruction |= cond << 4;
11756}
90e4755a 11757
5ee91343
AV
11758static void
11759do_mve_vpt (void)
11760{
11761 /* We are dealing with a vector predicated block. */
11762 set_pred_insn_type (VPT_INSN);
11763 now_pred.cc = 0;
11764 now_pred.mask = ((inst.instruction & 0x00400000) >> 19)
11765 | ((inst.instruction & 0xe000) >> 13);
11766 now_pred.warn_deprecated = FALSE;
11767 now_pred.type = VECTOR_PRED;
11768}
11769
3c707909
PB
11770/* Helper function used for both push/pop and ldm/stm. */
11771static void
4b5a202f
AV
11772encode_thumb2_multi (bfd_boolean do_io, int base, unsigned mask,
11773 bfd_boolean writeback)
3c707909 11774{
4b5a202f 11775 bfd_boolean load, store;
3c707909 11776
4b5a202f
AV
11777 gas_assert (base != -1 || !do_io);
11778 load = do_io && ((inst.instruction & (1 << 20)) != 0);
11779 store = do_io && !load;
3c707909
PB
11780
11781 if (mask & (1 << 13))
11782 inst.error = _("SP not allowed in register list");
1e5b0379 11783
4b5a202f 11784 if (do_io && (mask & (1 << base)) != 0
1e5b0379
NC
11785 && writeback)
11786 inst.error = _("having the base register in the register list when "
11787 "using write back is UNPREDICTABLE");
11788
3c707909
PB
11789 if (load)
11790 {
e07e6e58 11791 if (mask & (1 << 15))
477330fc
RM
11792 {
11793 if (mask & (1 << 14))
11794 inst.error = _("LR and PC should not both be in register list");
11795 else
5ee91343 11796 set_pred_insn_type_last ();
477330fc 11797 }
3c707909 11798 }
4b5a202f 11799 else if (store)
3c707909
PB
11800 {
11801 if (mask & (1 << 15))
11802 inst.error = _("PC not allowed in register list");
3c707909
PB
11803 }
11804
4b5a202f 11805 if (do_io && ((mask & (mask - 1)) == 0))
3c707909
PB
11806 {
11807 /* Single register transfers implemented as str/ldr. */
11808 if (writeback)
11809 {
11810 if (inst.instruction & (1 << 23))
11811 inst.instruction = 0x00000b04; /* ia! -> [base], #4 */
11812 else
11813 inst.instruction = 0x00000d04; /* db! -> [base, #-4]! */
11814 }
11815 else
11816 {
11817 if (inst.instruction & (1 << 23))
11818 inst.instruction = 0x00800000; /* ia -> [base] */
11819 else
11820 inst.instruction = 0x00000c04; /* db -> [base, #-4] */
11821 }
11822
11823 inst.instruction |= 0xf8400000;
11824 if (load)
11825 inst.instruction |= 0x00100000;
11826
5f4273c7 11827 mask = ffs (mask) - 1;
3c707909
PB
11828 mask <<= 12;
11829 }
11830 else if (writeback)
11831 inst.instruction |= WRITE_BACK;
11832
11833 inst.instruction |= mask;
4b5a202f
AV
11834 if (do_io)
11835 inst.instruction |= base << 16;
3c707909
PB
11836}
11837
c19d1205
ZW
11838static void
11839do_t_ldmstm (void)
11840{
11841 /* This really doesn't seem worth it. */
e2b0ab59 11842 constraint (inst.relocs[0].type != BFD_RELOC_UNUSED,
c19d1205
ZW
11843 _("expression too complex"));
11844 constraint (inst.operands[1].writeback,
11845 _("Thumb load/store multiple does not support {reglist}^"));
90e4755a 11846
c19d1205
ZW
11847 if (unified_syntax)
11848 {
3c707909
PB
11849 bfd_boolean narrow;
11850 unsigned mask;
11851
11852 narrow = FALSE;
c19d1205
ZW
11853 /* See if we can use a 16-bit instruction. */
11854 if (inst.instruction < 0xffff /* not ldmdb/stmdb */
11855 && inst.size_req != 4
3c707909 11856 && !(inst.operands[1].imm & ~0xff))
90e4755a 11857 {
3c707909 11858 mask = 1 << inst.operands[0].reg;
90e4755a 11859
eab4f823 11860 if (inst.operands[0].reg <= 7)
90e4755a 11861 {
3c707909 11862 if (inst.instruction == T_MNEM_stmia
eab4f823
MGD
11863 ? inst.operands[0].writeback
11864 : (inst.operands[0].writeback
11865 == !(inst.operands[1].imm & mask)))
477330fc 11866 {
eab4f823
MGD
11867 if (inst.instruction == T_MNEM_stmia
11868 && (inst.operands[1].imm & mask)
11869 && (inst.operands[1].imm & (mask - 1)))
11870 as_warn (_("value stored for r%d is UNKNOWN"),
11871 inst.operands[0].reg);
3c707909 11872
eab4f823
MGD
11873 inst.instruction = THUMB_OP16 (inst.instruction);
11874 inst.instruction |= inst.operands[0].reg << 8;
11875 inst.instruction |= inst.operands[1].imm;
11876 narrow = TRUE;
11877 }
11878 else if ((inst.operands[1].imm & (inst.operands[1].imm-1)) == 0)
11879 {
11880 /* This means 1 register in reg list one of 3 situations:
11881 1. Instruction is stmia, but without writeback.
11882 2. lmdia without writeback, but with Rn not in
477330fc 11883 reglist.
eab4f823
MGD
11884 3. ldmia with writeback, but with Rn in reglist.
11885 Case 3 is UNPREDICTABLE behaviour, so we handle
11886 case 1 and 2 which can be converted into a 16-bit
11887 str or ldr. The SP cases are handled below. */
11888 unsigned long opcode;
11889 /* First, record an error for Case 3. */
11890 if (inst.operands[1].imm & mask
11891 && inst.operands[0].writeback)
fa94de6b 11892 inst.error =
eab4f823
MGD
11893 _("having the base register in the register list when "
11894 "using write back is UNPREDICTABLE");
fa94de6b
RM
11895
11896 opcode = (inst.instruction == T_MNEM_stmia ? T_MNEM_str
eab4f823
MGD
11897 : T_MNEM_ldr);
11898 inst.instruction = THUMB_OP16 (opcode);
11899 inst.instruction |= inst.operands[0].reg << 3;
11900 inst.instruction |= (ffs (inst.operands[1].imm)-1);
11901 narrow = TRUE;
11902 }
90e4755a 11903 }
eab4f823 11904 else if (inst.operands[0] .reg == REG_SP)
90e4755a 11905 {
eab4f823
MGD
11906 if (inst.operands[0].writeback)
11907 {
fa94de6b 11908 inst.instruction =
eab4f823 11909 THUMB_OP16 (inst.instruction == T_MNEM_stmia
477330fc 11910 ? T_MNEM_push : T_MNEM_pop);
eab4f823 11911 inst.instruction |= inst.operands[1].imm;
477330fc 11912 narrow = TRUE;
eab4f823
MGD
11913 }
11914 else if ((inst.operands[1].imm & (inst.operands[1].imm-1)) == 0)
11915 {
fa94de6b 11916 inst.instruction =
eab4f823 11917 THUMB_OP16 (inst.instruction == T_MNEM_stmia
477330fc 11918 ? T_MNEM_str_sp : T_MNEM_ldr_sp);
eab4f823 11919 inst.instruction |= ((ffs (inst.operands[1].imm)-1) << 8);
477330fc 11920 narrow = TRUE;
eab4f823 11921 }
90e4755a 11922 }
3c707909
PB
11923 }
11924
11925 if (!narrow)
11926 {
c19d1205
ZW
11927 if (inst.instruction < 0xffff)
11928 inst.instruction = THUMB_OP32 (inst.instruction);
3c707909 11929
4b5a202f
AV
11930 encode_thumb2_multi (TRUE /* do_io */, inst.operands[0].reg,
11931 inst.operands[1].imm,
11932 inst.operands[0].writeback);
90e4755a
RE
11933 }
11934 }
c19d1205 11935 else
90e4755a 11936 {
c19d1205
ZW
11937 constraint (inst.operands[0].reg > 7
11938 || (inst.operands[1].imm & ~0xff), BAD_HIREG);
1198ca51
PB
11939 constraint (inst.instruction != T_MNEM_ldmia
11940 && inst.instruction != T_MNEM_stmia,
11941 _("Thumb-2 instruction only valid in unified syntax"));
c19d1205 11942 if (inst.instruction == T_MNEM_stmia)
f03698e6 11943 {
c19d1205
ZW
11944 if (!inst.operands[0].writeback)
11945 as_warn (_("this instruction will write back the base register"));
11946 if ((inst.operands[1].imm & (1 << inst.operands[0].reg))
11947 && (inst.operands[1].imm & ((1 << inst.operands[0].reg) - 1)))
1e5b0379 11948 as_warn (_("value stored for r%d is UNKNOWN"),
c19d1205 11949 inst.operands[0].reg);
f03698e6 11950 }
c19d1205 11951 else
90e4755a 11952 {
c19d1205
ZW
11953 if (!inst.operands[0].writeback
11954 && !(inst.operands[1].imm & (1 << inst.operands[0].reg)))
11955 as_warn (_("this instruction will write back the base register"));
11956 else if (inst.operands[0].writeback
11957 && (inst.operands[1].imm & (1 << inst.operands[0].reg)))
11958 as_warn (_("this instruction will not write back the base register"));
90e4755a
RE
11959 }
11960
c19d1205
ZW
11961 inst.instruction = THUMB_OP16 (inst.instruction);
11962 inst.instruction |= inst.operands[0].reg << 8;
11963 inst.instruction |= inst.operands[1].imm;
11964 }
11965}
e28cd48c 11966
c19d1205
ZW
11967static void
11968do_t_ldrex (void)
11969{
11970 constraint (!inst.operands[1].isreg || !inst.operands[1].preind
11971 || inst.operands[1].postind || inst.operands[1].writeback
11972 || inst.operands[1].immisreg || inst.operands[1].shifted
11973 || inst.operands[1].negative,
01cfc07f 11974 BAD_ADDR_MODE);
e28cd48c 11975
5be8be5d
DG
11976 constraint ((inst.operands[1].reg == REG_PC), BAD_PC);
11977
c19d1205
ZW
11978 inst.instruction |= inst.operands[0].reg << 12;
11979 inst.instruction |= inst.operands[1].reg << 16;
e2b0ab59 11980 inst.relocs[0].type = BFD_RELOC_ARM_T32_OFFSET_U8;
c19d1205 11981}
e28cd48c 11982
c19d1205
ZW
11983static void
11984do_t_ldrexd (void)
11985{
11986 if (!inst.operands[1].present)
1cac9012 11987 {
c19d1205
ZW
11988 constraint (inst.operands[0].reg == REG_LR,
11989 _("r14 not allowed as first register "
11990 "when second register is omitted"));
11991 inst.operands[1].reg = inst.operands[0].reg + 1;
b99bd4ef 11992 }
c19d1205
ZW
11993 constraint (inst.operands[0].reg == inst.operands[1].reg,
11994 BAD_OVERLAP);
b99bd4ef 11995
c19d1205
ZW
11996 inst.instruction |= inst.operands[0].reg << 12;
11997 inst.instruction |= inst.operands[1].reg << 8;
11998 inst.instruction |= inst.operands[2].reg << 16;
b99bd4ef
NC
11999}
12000
12001static void
c19d1205 12002do_t_ldst (void)
b99bd4ef 12003{
0110f2b8
PB
12004 unsigned long opcode;
12005 int Rn;
12006
e07e6e58
NC
12007 if (inst.operands[0].isreg
12008 && !inst.operands[0].preind
12009 && inst.operands[0].reg == REG_PC)
5ee91343 12010 set_pred_insn_type_last ();
e07e6e58 12011
0110f2b8 12012 opcode = inst.instruction;
c19d1205 12013 if (unified_syntax)
b99bd4ef 12014 {
53365c0d
PB
12015 if (!inst.operands[1].isreg)
12016 {
12017 if (opcode <= 0xffff)
12018 inst.instruction = THUMB_OP32 (opcode);
8335d6aa 12019 if (move_or_literal_pool (0, CONST_THUMB, /*mode_3=*/FALSE))
53365c0d
PB
12020 return;
12021 }
0110f2b8
PB
12022 if (inst.operands[1].isreg
12023 && !inst.operands[1].writeback
c19d1205
ZW
12024 && !inst.operands[1].shifted && !inst.operands[1].postind
12025 && !inst.operands[1].negative && inst.operands[0].reg <= 7
0110f2b8
PB
12026 && opcode <= 0xffff
12027 && inst.size_req != 4)
c19d1205 12028 {
0110f2b8
PB
12029 /* Insn may have a 16-bit form. */
12030 Rn = inst.operands[1].reg;
12031 if (inst.operands[1].immisreg)
12032 {
12033 inst.instruction = THUMB_OP16 (opcode);
5f4273c7 12034 /* [Rn, Rik] */
0110f2b8
PB
12035 if (Rn <= 7 && inst.operands[1].imm <= 7)
12036 goto op16;
5be8be5d
DG
12037 else if (opcode != T_MNEM_ldr && opcode != T_MNEM_str)
12038 reject_bad_reg (inst.operands[1].imm);
0110f2b8
PB
12039 }
12040 else if ((Rn <= 7 && opcode != T_MNEM_ldrsh
12041 && opcode != T_MNEM_ldrsb)
12042 || ((Rn == REG_PC || Rn == REG_SP) && opcode == T_MNEM_ldr)
12043 || (Rn == REG_SP && opcode == T_MNEM_str))
12044 {
12045 /* [Rn, #const] */
12046 if (Rn > 7)
12047 {
12048 if (Rn == REG_PC)
12049 {
e2b0ab59 12050 if (inst.relocs[0].pc_rel)
0110f2b8
PB
12051 opcode = T_MNEM_ldr_pc2;
12052 else
12053 opcode = T_MNEM_ldr_pc;
12054 }
12055 else
12056 {
12057 if (opcode == T_MNEM_ldr)
12058 opcode = T_MNEM_ldr_sp;
12059 else
12060 opcode = T_MNEM_str_sp;
12061 }
12062 inst.instruction = inst.operands[0].reg << 8;
12063 }
12064 else
12065 {
12066 inst.instruction = inst.operands[0].reg;
12067 inst.instruction |= inst.operands[1].reg << 3;
12068 }
12069 inst.instruction |= THUMB_OP16 (opcode);
12070 if (inst.size_req == 2)
e2b0ab59 12071 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_OFFSET;
0110f2b8
PB
12072 else
12073 inst.relax = opcode;
12074 return;
12075 }
c19d1205 12076 }
0110f2b8 12077 /* Definitely a 32-bit variant. */
5be8be5d 12078
8d67f500
NC
12079 /* Warning for Erratum 752419. */
12080 if (opcode == T_MNEM_ldr
12081 && inst.operands[0].reg == REG_SP
12082 && inst.operands[1].writeback == 1
12083 && !inst.operands[1].immisreg)
12084 {
12085 if (no_cpu_selected ()
12086 || (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v7)
477330fc
RM
12087 && !ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v7a)
12088 && !ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v7r)))
8d67f500
NC
12089 as_warn (_("This instruction may be unpredictable "
12090 "if executed on M-profile cores "
12091 "with interrupts enabled."));
12092 }
12093
5be8be5d 12094 /* Do some validations regarding addressing modes. */
1be5fd2e 12095 if (inst.operands[1].immisreg)
5be8be5d
DG
12096 reject_bad_reg (inst.operands[1].imm);
12097
1be5fd2e
NC
12098 constraint (inst.operands[1].writeback == 1
12099 && inst.operands[0].reg == inst.operands[1].reg,
12100 BAD_OVERLAP);
12101
0110f2b8 12102 inst.instruction = THUMB_OP32 (opcode);
c19d1205
ZW
12103 inst.instruction |= inst.operands[0].reg << 12;
12104 encode_thumb32_addr_mode (1, /*is_t=*/FALSE, /*is_d=*/FALSE);
1be5fd2e 12105 check_ldr_r15_aligned ();
b99bd4ef
NC
12106 return;
12107 }
12108
c19d1205
ZW
12109 constraint (inst.operands[0].reg > 7, BAD_HIREG);
12110
12111 if (inst.instruction == T_MNEM_ldrsh || inst.instruction == T_MNEM_ldrsb)
b99bd4ef 12112 {
c19d1205
ZW
12113 /* Only [Rn,Rm] is acceptable. */
12114 constraint (inst.operands[1].reg > 7 || inst.operands[1].imm > 7, BAD_HIREG);
12115 constraint (!inst.operands[1].isreg || !inst.operands[1].immisreg
12116 || inst.operands[1].postind || inst.operands[1].shifted
12117 || inst.operands[1].negative,
12118 _("Thumb does not support this addressing mode"));
12119 inst.instruction = THUMB_OP16 (inst.instruction);
12120 goto op16;
b99bd4ef 12121 }
5f4273c7 12122
c19d1205
ZW
12123 inst.instruction = THUMB_OP16 (inst.instruction);
12124 if (!inst.operands[1].isreg)
8335d6aa 12125 if (move_or_literal_pool (0, CONST_THUMB, /*mode_3=*/FALSE))
c19d1205 12126 return;
b99bd4ef 12127
c19d1205
ZW
12128 constraint (!inst.operands[1].preind
12129 || inst.operands[1].shifted
12130 || inst.operands[1].writeback,
12131 _("Thumb does not support this addressing mode"));
12132 if (inst.operands[1].reg == REG_PC || inst.operands[1].reg == REG_SP)
90e4755a 12133 {
c19d1205
ZW
12134 constraint (inst.instruction & 0x0600,
12135 _("byte or halfword not valid for base register"));
12136 constraint (inst.operands[1].reg == REG_PC
12137 && !(inst.instruction & THUMB_LOAD_BIT),
12138 _("r15 based store not allowed"));
12139 constraint (inst.operands[1].immisreg,
12140 _("invalid base register for register offset"));
b99bd4ef 12141
c19d1205
ZW
12142 if (inst.operands[1].reg == REG_PC)
12143 inst.instruction = T_OPCODE_LDR_PC;
12144 else if (inst.instruction & THUMB_LOAD_BIT)
12145 inst.instruction = T_OPCODE_LDR_SP;
12146 else
12147 inst.instruction = T_OPCODE_STR_SP;
b99bd4ef 12148
c19d1205 12149 inst.instruction |= inst.operands[0].reg << 8;
e2b0ab59 12150 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_OFFSET;
c19d1205
ZW
12151 return;
12152 }
90e4755a 12153
c19d1205
ZW
12154 constraint (inst.operands[1].reg > 7, BAD_HIREG);
12155 if (!inst.operands[1].immisreg)
12156 {
12157 /* Immediate offset. */
12158 inst.instruction |= inst.operands[0].reg;
12159 inst.instruction |= inst.operands[1].reg << 3;
e2b0ab59 12160 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_OFFSET;
c19d1205
ZW
12161 return;
12162 }
90e4755a 12163
c19d1205
ZW
12164 /* Register offset. */
12165 constraint (inst.operands[1].imm > 7, BAD_HIREG);
12166 constraint (inst.operands[1].negative,
12167 _("Thumb does not support this addressing mode"));
90e4755a 12168
c19d1205
ZW
12169 op16:
12170 switch (inst.instruction)
12171 {
12172 case T_OPCODE_STR_IW: inst.instruction = T_OPCODE_STR_RW; break;
12173 case T_OPCODE_STR_IH: inst.instruction = T_OPCODE_STR_RH; break;
12174 case T_OPCODE_STR_IB: inst.instruction = T_OPCODE_STR_RB; break;
12175 case T_OPCODE_LDR_IW: inst.instruction = T_OPCODE_LDR_RW; break;
12176 case T_OPCODE_LDR_IH: inst.instruction = T_OPCODE_LDR_RH; break;
12177 case T_OPCODE_LDR_IB: inst.instruction = T_OPCODE_LDR_RB; break;
12178 case 0x5600 /* ldrsb */:
12179 case 0x5e00 /* ldrsh */: break;
12180 default: abort ();
12181 }
90e4755a 12182
c19d1205
ZW
12183 inst.instruction |= inst.operands[0].reg;
12184 inst.instruction |= inst.operands[1].reg << 3;
12185 inst.instruction |= inst.operands[1].imm << 6;
12186}
90e4755a 12187
c19d1205
ZW
12188static void
12189do_t_ldstd (void)
12190{
12191 if (!inst.operands[1].present)
b99bd4ef 12192 {
c19d1205
ZW
12193 inst.operands[1].reg = inst.operands[0].reg + 1;
12194 constraint (inst.operands[0].reg == REG_LR,
12195 _("r14 not allowed here"));
bd340a04 12196 constraint (inst.operands[0].reg == REG_R12,
477330fc 12197 _("r12 not allowed here"));
b99bd4ef 12198 }
bd340a04
MGD
12199
12200 if (inst.operands[2].writeback
12201 && (inst.operands[0].reg == inst.operands[2].reg
12202 || inst.operands[1].reg == inst.operands[2].reg))
12203 as_warn (_("base register written back, and overlaps "
477330fc 12204 "one of transfer registers"));
bd340a04 12205
c19d1205
ZW
12206 inst.instruction |= inst.operands[0].reg << 12;
12207 inst.instruction |= inst.operands[1].reg << 8;
12208 encode_thumb32_addr_mode (2, /*is_t=*/FALSE, /*is_d=*/TRUE);
b99bd4ef
NC
12209}
12210
c19d1205
ZW
12211static void
12212do_t_ldstt (void)
12213{
12214 inst.instruction |= inst.operands[0].reg << 12;
12215 encode_thumb32_addr_mode (1, /*is_t=*/TRUE, /*is_d=*/FALSE);
12216}
a737bd4d 12217
b99bd4ef 12218static void
c19d1205 12219do_t_mla (void)
b99bd4ef 12220{
fdfde340 12221 unsigned Rd, Rn, Rm, Ra;
c921be7d 12222
fdfde340
JM
12223 Rd = inst.operands[0].reg;
12224 Rn = inst.operands[1].reg;
12225 Rm = inst.operands[2].reg;
12226 Ra = inst.operands[3].reg;
12227
12228 reject_bad_reg (Rd);
12229 reject_bad_reg (Rn);
12230 reject_bad_reg (Rm);
12231 reject_bad_reg (Ra);
12232
12233 inst.instruction |= Rd << 8;
12234 inst.instruction |= Rn << 16;
12235 inst.instruction |= Rm;
12236 inst.instruction |= Ra << 12;
c19d1205 12237}
b99bd4ef 12238
c19d1205
ZW
12239static void
12240do_t_mlal (void)
12241{
fdfde340
JM
12242 unsigned RdLo, RdHi, Rn, Rm;
12243
12244 RdLo = inst.operands[0].reg;
12245 RdHi = inst.operands[1].reg;
12246 Rn = inst.operands[2].reg;
12247 Rm = inst.operands[3].reg;
12248
12249 reject_bad_reg (RdLo);
12250 reject_bad_reg (RdHi);
12251 reject_bad_reg (Rn);
12252 reject_bad_reg (Rm);
12253
12254 inst.instruction |= RdLo << 12;
12255 inst.instruction |= RdHi << 8;
12256 inst.instruction |= Rn << 16;
12257 inst.instruction |= Rm;
c19d1205 12258}
b99bd4ef 12259
c19d1205
ZW
12260static void
12261do_t_mov_cmp (void)
12262{
fdfde340
JM
12263 unsigned Rn, Rm;
12264
12265 Rn = inst.operands[0].reg;
12266 Rm = inst.operands[1].reg;
12267
e07e6e58 12268 if (Rn == REG_PC)
5ee91343 12269 set_pred_insn_type_last ();
e07e6e58 12270
c19d1205 12271 if (unified_syntax)
b99bd4ef 12272 {
c19d1205
ZW
12273 int r0off = (inst.instruction == T_MNEM_mov
12274 || inst.instruction == T_MNEM_movs) ? 8 : 16;
0110f2b8 12275 unsigned long opcode;
3d388997
PB
12276 bfd_boolean narrow;
12277 bfd_boolean low_regs;
12278
fdfde340 12279 low_regs = (Rn <= 7 && Rm <= 7);
0110f2b8 12280 opcode = inst.instruction;
5ee91343 12281 if (in_pred_block ())
0110f2b8 12282 narrow = opcode != T_MNEM_movs;
3d388997 12283 else
0110f2b8 12284 narrow = opcode != T_MNEM_movs || low_regs;
3d388997
PB
12285 if (inst.size_req == 4
12286 || inst.operands[1].shifted)
12287 narrow = FALSE;
12288
efd81785
PB
12289 /* MOVS PC, LR is encoded as SUBS PC, LR, #0. */
12290 if (opcode == T_MNEM_movs && inst.operands[1].isreg
12291 && !inst.operands[1].shifted
fdfde340
JM
12292 && Rn == REG_PC
12293 && Rm == REG_LR)
efd81785
PB
12294 {
12295 inst.instruction = T2_SUBS_PC_LR;
12296 return;
12297 }
12298
fdfde340
JM
12299 if (opcode == T_MNEM_cmp)
12300 {
12301 constraint (Rn == REG_PC, BAD_PC);
94206790
MM
12302 if (narrow)
12303 {
12304 /* In the Thumb-2 ISA, use of R13 as Rm is deprecated,
12305 but valid. */
12306 warn_deprecated_sp (Rm);
12307 /* R15 was documented as a valid choice for Rm in ARMv6,
12308 but as UNPREDICTABLE in ARMv7. ARM's proprietary
12309 tools reject R15, so we do too. */
12310 constraint (Rm == REG_PC, BAD_PC);
12311 }
12312 else
12313 reject_bad_reg (Rm);
fdfde340
JM
12314 }
12315 else if (opcode == T_MNEM_mov
12316 || opcode == T_MNEM_movs)
12317 {
12318 if (inst.operands[1].isreg)
12319 {
12320 if (opcode == T_MNEM_movs)
12321 {
12322 reject_bad_reg (Rn);
12323 reject_bad_reg (Rm);
12324 }
76fa04a4
MGD
12325 else if (narrow)
12326 {
12327 /* This is mov.n. */
12328 if ((Rn == REG_SP || Rn == REG_PC)
12329 && (Rm == REG_SP || Rm == REG_PC))
12330 {
5c3696f8 12331 as_tsktsk (_("Use of r%u as a source register is "
76fa04a4
MGD
12332 "deprecated when r%u is the destination "
12333 "register."), Rm, Rn);
12334 }
12335 }
12336 else
12337 {
12338 /* This is mov.w. */
12339 constraint (Rn == REG_PC, BAD_PC);
12340 constraint (Rm == REG_PC, BAD_PC);
5c8ed6a4
JW
12341 if (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v8))
12342 constraint (Rn == REG_SP && Rm == REG_SP, BAD_SP);
76fa04a4 12343 }
fdfde340
JM
12344 }
12345 else
12346 reject_bad_reg (Rn);
12347 }
12348
c19d1205
ZW
12349 if (!inst.operands[1].isreg)
12350 {
0110f2b8 12351 /* Immediate operand. */
5ee91343 12352 if (!in_pred_block () && opcode == T_MNEM_mov)
0110f2b8
PB
12353 narrow = 0;
12354 if (low_regs && narrow)
12355 {
12356 inst.instruction = THUMB_OP16 (opcode);
fdfde340 12357 inst.instruction |= Rn << 8;
e2b0ab59
AV
12358 if (inst.relocs[0].type < BFD_RELOC_ARM_THUMB_ALU_ABS_G0_NC
12359 || inst.relocs[0].type > BFD_RELOC_ARM_THUMB_ALU_ABS_G3_NC)
72d98d16 12360 {
a9f02af8 12361 if (inst.size_req == 2)
e2b0ab59 12362 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_IMM;
a9f02af8
MG
12363 else
12364 inst.relax = opcode;
72d98d16 12365 }
0110f2b8
PB
12366 }
12367 else
12368 {
e2b0ab59
AV
12369 constraint ((inst.relocs[0].type
12370 >= BFD_RELOC_ARM_THUMB_ALU_ABS_G0_NC)
12371 && (inst.relocs[0].type
12372 <= BFD_RELOC_ARM_THUMB_ALU_ABS_G3_NC) ,
a9f02af8
MG
12373 THUMB1_RELOC_ONLY);
12374
0110f2b8
PB
12375 inst.instruction = THUMB_OP32 (inst.instruction);
12376 inst.instruction = (inst.instruction & 0xe1ffffff) | 0x10000000;
fdfde340 12377 inst.instruction |= Rn << r0off;
e2b0ab59 12378 inst.relocs[0].type = BFD_RELOC_ARM_T32_IMMEDIATE;
0110f2b8 12379 }
c19d1205 12380 }
728ca7c9
PB
12381 else if (inst.operands[1].shifted && inst.operands[1].immisreg
12382 && (inst.instruction == T_MNEM_mov
12383 || inst.instruction == T_MNEM_movs))
12384 {
12385 /* Register shifts are encoded as separate shift instructions. */
12386 bfd_boolean flags = (inst.instruction == T_MNEM_movs);
12387
5ee91343 12388 if (in_pred_block ())
728ca7c9
PB
12389 narrow = !flags;
12390 else
12391 narrow = flags;
12392
12393 if (inst.size_req == 4)
12394 narrow = FALSE;
12395
12396 if (!low_regs || inst.operands[1].imm > 7)
12397 narrow = FALSE;
12398
fdfde340 12399 if (Rn != Rm)
728ca7c9
PB
12400 narrow = FALSE;
12401
12402 switch (inst.operands[1].shift_kind)
12403 {
12404 case SHIFT_LSL:
12405 opcode = narrow ? T_OPCODE_LSL_R : THUMB_OP32 (T_MNEM_lsl);
12406 break;
12407 case SHIFT_ASR:
12408 opcode = narrow ? T_OPCODE_ASR_R : THUMB_OP32 (T_MNEM_asr);
12409 break;
12410 case SHIFT_LSR:
12411 opcode = narrow ? T_OPCODE_LSR_R : THUMB_OP32 (T_MNEM_lsr);
12412 break;
12413 case SHIFT_ROR:
12414 opcode = narrow ? T_OPCODE_ROR_R : THUMB_OP32 (T_MNEM_ror);
12415 break;
12416 default:
5f4273c7 12417 abort ();
728ca7c9
PB
12418 }
12419
12420 inst.instruction = opcode;
12421 if (narrow)
12422 {
fdfde340 12423 inst.instruction |= Rn;
728ca7c9
PB
12424 inst.instruction |= inst.operands[1].imm << 3;
12425 }
12426 else
12427 {
12428 if (flags)
12429 inst.instruction |= CONDS_BIT;
12430
fdfde340
JM
12431 inst.instruction |= Rn << 8;
12432 inst.instruction |= Rm << 16;
728ca7c9
PB
12433 inst.instruction |= inst.operands[1].imm;
12434 }
12435 }
3d388997 12436 else if (!narrow)
c19d1205 12437 {
728ca7c9
PB
12438 /* Some mov with immediate shift have narrow variants.
12439 Register shifts are handled above. */
12440 if (low_regs && inst.operands[1].shifted
12441 && (inst.instruction == T_MNEM_mov
12442 || inst.instruction == T_MNEM_movs))
12443 {
5ee91343 12444 if (in_pred_block ())
728ca7c9
PB
12445 narrow = (inst.instruction == T_MNEM_mov);
12446 else
12447 narrow = (inst.instruction == T_MNEM_movs);
12448 }
12449
12450 if (narrow)
12451 {
12452 switch (inst.operands[1].shift_kind)
12453 {
12454 case SHIFT_LSL: inst.instruction = T_OPCODE_LSL_I; break;
12455 case SHIFT_LSR: inst.instruction = T_OPCODE_LSR_I; break;
12456 case SHIFT_ASR: inst.instruction = T_OPCODE_ASR_I; break;
12457 default: narrow = FALSE; break;
12458 }
12459 }
12460
12461 if (narrow)
12462 {
fdfde340
JM
12463 inst.instruction |= Rn;
12464 inst.instruction |= Rm << 3;
e2b0ab59 12465 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_SHIFT;
728ca7c9
PB
12466 }
12467 else
12468 {
12469 inst.instruction = THUMB_OP32 (inst.instruction);
fdfde340 12470 inst.instruction |= Rn << r0off;
728ca7c9
PB
12471 encode_thumb32_shifted_operand (1);
12472 }
c19d1205
ZW
12473 }
12474 else
12475 switch (inst.instruction)
12476 {
12477 case T_MNEM_mov:
837b3435 12478 /* In v4t or v5t a move of two lowregs produces unpredictable
c6400f8a
MGD
12479 results. Don't allow this. */
12480 if (low_regs)
12481 {
12482 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6),
12483 "MOV Rd, Rs with two low registers is not "
12484 "permitted on this architecture");
fa94de6b 12485 ARM_MERGE_FEATURE_SETS (thumb_arch_used, thumb_arch_used,
c6400f8a
MGD
12486 arm_ext_v6);
12487 }
12488
c19d1205 12489 inst.instruction = T_OPCODE_MOV_HR;
fdfde340
JM
12490 inst.instruction |= (Rn & 0x8) << 4;
12491 inst.instruction |= (Rn & 0x7);
12492 inst.instruction |= Rm << 3;
c19d1205 12493 break;
b99bd4ef 12494
c19d1205
ZW
12495 case T_MNEM_movs:
12496 /* We know we have low registers at this point.
941a8a52
MGD
12497 Generate LSLS Rd, Rs, #0. */
12498 inst.instruction = T_OPCODE_LSL_I;
fdfde340
JM
12499 inst.instruction |= Rn;
12500 inst.instruction |= Rm << 3;
c19d1205
ZW
12501 break;
12502
12503 case T_MNEM_cmp:
3d388997 12504 if (low_regs)
c19d1205
ZW
12505 {
12506 inst.instruction = T_OPCODE_CMP_LR;
fdfde340
JM
12507 inst.instruction |= Rn;
12508 inst.instruction |= Rm << 3;
c19d1205
ZW
12509 }
12510 else
12511 {
12512 inst.instruction = T_OPCODE_CMP_HR;
fdfde340
JM
12513 inst.instruction |= (Rn & 0x8) << 4;
12514 inst.instruction |= (Rn & 0x7);
12515 inst.instruction |= Rm << 3;
c19d1205
ZW
12516 }
12517 break;
12518 }
b99bd4ef
NC
12519 return;
12520 }
12521
c19d1205 12522 inst.instruction = THUMB_OP16 (inst.instruction);
539d4391
NC
12523
12524 /* PR 10443: Do not silently ignore shifted operands. */
12525 constraint (inst.operands[1].shifted,
12526 _("shifts in CMP/MOV instructions are only supported in unified syntax"));
12527
c19d1205 12528 if (inst.operands[1].isreg)
b99bd4ef 12529 {
fdfde340 12530 if (Rn < 8 && Rm < 8)
b99bd4ef 12531 {
c19d1205
ZW
12532 /* A move of two lowregs is encoded as ADD Rd, Rs, #0
12533 since a MOV instruction produces unpredictable results. */
12534 if (inst.instruction == T_OPCODE_MOV_I8)
12535 inst.instruction = T_OPCODE_ADD_I3;
b99bd4ef 12536 else
c19d1205 12537 inst.instruction = T_OPCODE_CMP_LR;
b99bd4ef 12538
fdfde340
JM
12539 inst.instruction |= Rn;
12540 inst.instruction |= Rm << 3;
b99bd4ef
NC
12541 }
12542 else
12543 {
c19d1205
ZW
12544 if (inst.instruction == T_OPCODE_MOV_I8)
12545 inst.instruction = T_OPCODE_MOV_HR;
12546 else
12547 inst.instruction = T_OPCODE_CMP_HR;
12548 do_t_cpy ();
b99bd4ef
NC
12549 }
12550 }
c19d1205 12551 else
b99bd4ef 12552 {
fdfde340 12553 constraint (Rn > 7,
c19d1205 12554 _("only lo regs allowed with immediate"));
fdfde340 12555 inst.instruction |= Rn << 8;
e2b0ab59 12556 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_IMM;
c19d1205
ZW
12557 }
12558}
b99bd4ef 12559
c19d1205
ZW
12560static void
12561do_t_mov16 (void)
12562{
fdfde340 12563 unsigned Rd;
b6895b4f
PB
12564 bfd_vma imm;
12565 bfd_boolean top;
12566
12567 top = (inst.instruction & 0x00800000) != 0;
e2b0ab59 12568 if (inst.relocs[0].type == BFD_RELOC_ARM_MOVW)
b6895b4f 12569 {
33eaf5de 12570 constraint (top, _(":lower16: not allowed in this instruction"));
e2b0ab59 12571 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_MOVW;
b6895b4f 12572 }
e2b0ab59 12573 else if (inst.relocs[0].type == BFD_RELOC_ARM_MOVT)
b6895b4f 12574 {
33eaf5de 12575 constraint (!top, _(":upper16: not allowed in this instruction"));
e2b0ab59 12576 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_MOVT;
b6895b4f
PB
12577 }
12578
fdfde340
JM
12579 Rd = inst.operands[0].reg;
12580 reject_bad_reg (Rd);
12581
12582 inst.instruction |= Rd << 8;
e2b0ab59 12583 if (inst.relocs[0].type == BFD_RELOC_UNUSED)
b6895b4f 12584 {
e2b0ab59 12585 imm = inst.relocs[0].exp.X_add_number;
b6895b4f
PB
12586 inst.instruction |= (imm & 0xf000) << 4;
12587 inst.instruction |= (imm & 0x0800) << 15;
12588 inst.instruction |= (imm & 0x0700) << 4;
12589 inst.instruction |= (imm & 0x00ff);
12590 }
c19d1205 12591}
b99bd4ef 12592
c19d1205
ZW
12593static void
12594do_t_mvn_tst (void)
12595{
fdfde340 12596 unsigned Rn, Rm;
c921be7d 12597
fdfde340
JM
12598 Rn = inst.operands[0].reg;
12599 Rm = inst.operands[1].reg;
12600
12601 if (inst.instruction == T_MNEM_cmp
12602 || inst.instruction == T_MNEM_cmn)
12603 constraint (Rn == REG_PC, BAD_PC);
12604 else
12605 reject_bad_reg (Rn);
12606 reject_bad_reg (Rm);
12607
c19d1205
ZW
12608 if (unified_syntax)
12609 {
12610 int r0off = (inst.instruction == T_MNEM_mvn
12611 || inst.instruction == T_MNEM_mvns) ? 8 : 16;
3d388997
PB
12612 bfd_boolean narrow;
12613
12614 if (inst.size_req == 4
12615 || inst.instruction > 0xffff
12616 || inst.operands[1].shifted
fdfde340 12617 || Rn > 7 || Rm > 7)
3d388997 12618 narrow = FALSE;
fe8b4cc3
KT
12619 else if (inst.instruction == T_MNEM_cmn
12620 || inst.instruction == T_MNEM_tst)
3d388997
PB
12621 narrow = TRUE;
12622 else if (THUMB_SETS_FLAGS (inst.instruction))
5ee91343 12623 narrow = !in_pred_block ();
3d388997 12624 else
5ee91343 12625 narrow = in_pred_block ();
3d388997 12626
c19d1205 12627 if (!inst.operands[1].isreg)
b99bd4ef 12628 {
c19d1205
ZW
12629 /* For an immediate, we always generate a 32-bit opcode;
12630 section relaxation will shrink it later if possible. */
12631 if (inst.instruction < 0xffff)
12632 inst.instruction = THUMB_OP32 (inst.instruction);
12633 inst.instruction = (inst.instruction & 0xe1ffffff) | 0x10000000;
fdfde340 12634 inst.instruction |= Rn << r0off;
e2b0ab59 12635 inst.relocs[0].type = BFD_RELOC_ARM_T32_IMMEDIATE;
b99bd4ef 12636 }
c19d1205 12637 else
b99bd4ef 12638 {
c19d1205 12639 /* See if we can do this with a 16-bit instruction. */
3d388997 12640 if (narrow)
b99bd4ef 12641 {
c19d1205 12642 inst.instruction = THUMB_OP16 (inst.instruction);
fdfde340
JM
12643 inst.instruction |= Rn;
12644 inst.instruction |= Rm << 3;
b99bd4ef 12645 }
c19d1205 12646 else
b99bd4ef 12647 {
c19d1205
ZW
12648 constraint (inst.operands[1].shifted
12649 && inst.operands[1].immisreg,
12650 _("shift must be constant"));
12651 if (inst.instruction < 0xffff)
12652 inst.instruction = THUMB_OP32 (inst.instruction);
fdfde340 12653 inst.instruction |= Rn << r0off;
c19d1205 12654 encode_thumb32_shifted_operand (1);
b99bd4ef 12655 }
b99bd4ef
NC
12656 }
12657 }
12658 else
12659 {
c19d1205
ZW
12660 constraint (inst.instruction > 0xffff
12661 || inst.instruction == T_MNEM_mvns, BAD_THUMB32);
12662 constraint (!inst.operands[1].isreg || inst.operands[1].shifted,
12663 _("unshifted register required"));
fdfde340 12664 constraint (Rn > 7 || Rm > 7,
c19d1205 12665 BAD_HIREG);
b99bd4ef 12666
c19d1205 12667 inst.instruction = THUMB_OP16 (inst.instruction);
fdfde340
JM
12668 inst.instruction |= Rn;
12669 inst.instruction |= Rm << 3;
b99bd4ef 12670 }
b99bd4ef
NC
12671}
12672
b05fe5cf 12673static void
c19d1205 12674do_t_mrs (void)
b05fe5cf 12675{
fdfde340 12676 unsigned Rd;
037e8744
JB
12677
12678 if (do_vfp_nsyn_mrs () == SUCCESS)
12679 return;
12680
90ec0d68
MGD
12681 Rd = inst.operands[0].reg;
12682 reject_bad_reg (Rd);
12683 inst.instruction |= Rd << 8;
12684
12685 if (inst.operands[1].isreg)
62b3e311 12686 {
90ec0d68
MGD
12687 unsigned br = inst.operands[1].reg;
12688 if (((br & 0x200) == 0) && ((br & 0xf000) != 0xf000))
12689 as_bad (_("bad register for mrs"));
12690
12691 inst.instruction |= br & (0xf << 16);
12692 inst.instruction |= (br & 0x300) >> 4;
12693 inst.instruction |= (br & SPSR_BIT) >> 2;
62b3e311
PB
12694 }
12695 else
12696 {
90ec0d68 12697 int flags = inst.operands[1].imm & (PSR_c|PSR_x|PSR_s|PSR_f|SPSR_BIT);
5f4273c7 12698
d2cd1205 12699 if (ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_m))
1a43faaf
NC
12700 {
12701 /* PR gas/12698: The constraint is only applied for m_profile.
12702 If the user has specified -march=all, we want to ignore it as
12703 we are building for any CPU type, including non-m variants. */
823d2571
TG
12704 bfd_boolean m_profile =
12705 !ARM_FEATURE_CORE_EQUAL (selected_cpu, arm_arch_any);
1a43faaf
NC
12706 constraint ((flags != 0) && m_profile, _("selected processor does "
12707 "not support requested special purpose register"));
12708 }
90ec0d68 12709 else
d2cd1205
JB
12710 /* mrs only accepts APSR/CPSR/SPSR/CPSR_all/SPSR_all (for non-M profile
12711 devices). */
12712 constraint ((flags & ~SPSR_BIT) != (PSR_c|PSR_f),
12713 _("'APSR', 'CPSR' or 'SPSR' expected"));
fdfde340 12714
90ec0d68
MGD
12715 inst.instruction |= (flags & SPSR_BIT) >> 2;
12716 inst.instruction |= inst.operands[1].imm & 0xff;
12717 inst.instruction |= 0xf0000;
12718 }
c19d1205 12719}
b05fe5cf 12720
c19d1205
ZW
12721static void
12722do_t_msr (void)
12723{
62b3e311 12724 int flags;
fdfde340 12725 unsigned Rn;
62b3e311 12726
037e8744
JB
12727 if (do_vfp_nsyn_msr () == SUCCESS)
12728 return;
12729
c19d1205
ZW
12730 constraint (!inst.operands[1].isreg,
12731 _("Thumb encoding does not support an immediate here"));
90ec0d68
MGD
12732
12733 if (inst.operands[0].isreg)
12734 flags = (int)(inst.operands[0].reg);
12735 else
12736 flags = inst.operands[0].imm;
12737
d2cd1205 12738 if (ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_m))
62b3e311 12739 {
d2cd1205
JB
12740 int bits = inst.operands[0].imm & (PSR_c|PSR_x|PSR_s|PSR_f|SPSR_BIT);
12741
1a43faaf 12742 /* PR gas/12698: The constraint is only applied for m_profile.
477330fc
RM
12743 If the user has specified -march=all, we want to ignore it as
12744 we are building for any CPU type, including non-m variants. */
823d2571
TG
12745 bfd_boolean m_profile =
12746 !ARM_FEATURE_CORE_EQUAL (selected_cpu, arm_arch_any);
1a43faaf 12747 constraint (((ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6_dsp)
477330fc
RM
12748 && (bits & ~(PSR_s | PSR_f)) != 0)
12749 || (!ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6_dsp)
12750 && bits != PSR_f)) && m_profile,
12751 _("selected processor does not support requested special "
12752 "purpose register"));
62b3e311
PB
12753 }
12754 else
d2cd1205
JB
12755 constraint ((flags & 0xff) != 0, _("selected processor does not support "
12756 "requested special purpose register"));
c921be7d 12757
fdfde340
JM
12758 Rn = inst.operands[1].reg;
12759 reject_bad_reg (Rn);
12760
62b3e311 12761 inst.instruction |= (flags & SPSR_BIT) >> 2;
90ec0d68
MGD
12762 inst.instruction |= (flags & 0xf0000) >> 8;
12763 inst.instruction |= (flags & 0x300) >> 4;
62b3e311 12764 inst.instruction |= (flags & 0xff);
fdfde340 12765 inst.instruction |= Rn << 16;
c19d1205 12766}
b05fe5cf 12767
c19d1205
ZW
12768static void
12769do_t_mul (void)
12770{
17828f45 12771 bfd_boolean narrow;
fdfde340 12772 unsigned Rd, Rn, Rm;
17828f45 12773
c19d1205
ZW
12774 if (!inst.operands[2].present)
12775 inst.operands[2].reg = inst.operands[0].reg;
b05fe5cf 12776
fdfde340
JM
12777 Rd = inst.operands[0].reg;
12778 Rn = inst.operands[1].reg;
12779 Rm = inst.operands[2].reg;
12780
17828f45 12781 if (unified_syntax)
b05fe5cf 12782 {
17828f45 12783 if (inst.size_req == 4
fdfde340
JM
12784 || (Rd != Rn
12785 && Rd != Rm)
12786 || Rn > 7
12787 || Rm > 7)
17828f45
JM
12788 narrow = FALSE;
12789 else if (inst.instruction == T_MNEM_muls)
5ee91343 12790 narrow = !in_pred_block ();
17828f45 12791 else
5ee91343 12792 narrow = in_pred_block ();
b05fe5cf 12793 }
c19d1205 12794 else
b05fe5cf 12795 {
17828f45 12796 constraint (inst.instruction == T_MNEM_muls, BAD_THUMB32);
fdfde340 12797 constraint (Rn > 7 || Rm > 7,
c19d1205 12798 BAD_HIREG);
17828f45
JM
12799 narrow = TRUE;
12800 }
b05fe5cf 12801
17828f45
JM
12802 if (narrow)
12803 {
12804 /* 16-bit MULS/Conditional MUL. */
c19d1205 12805 inst.instruction = THUMB_OP16 (inst.instruction);
fdfde340 12806 inst.instruction |= Rd;
b05fe5cf 12807
fdfde340
JM
12808 if (Rd == Rn)
12809 inst.instruction |= Rm << 3;
12810 else if (Rd == Rm)
12811 inst.instruction |= Rn << 3;
c19d1205
ZW
12812 else
12813 constraint (1, _("dest must overlap one source register"));
12814 }
17828f45
JM
12815 else
12816 {
e07e6e58
NC
12817 constraint (inst.instruction != T_MNEM_mul,
12818 _("Thumb-2 MUL must not set flags"));
17828f45
JM
12819 /* 32-bit MUL. */
12820 inst.instruction = THUMB_OP32 (inst.instruction);
fdfde340
JM
12821 inst.instruction |= Rd << 8;
12822 inst.instruction |= Rn << 16;
12823 inst.instruction |= Rm << 0;
12824
12825 reject_bad_reg (Rd);
12826 reject_bad_reg (Rn);
12827 reject_bad_reg (Rm);
17828f45 12828 }
c19d1205 12829}
b05fe5cf 12830
c19d1205
ZW
12831static void
12832do_t_mull (void)
12833{
fdfde340 12834 unsigned RdLo, RdHi, Rn, Rm;
b05fe5cf 12835
fdfde340
JM
12836 RdLo = inst.operands[0].reg;
12837 RdHi = inst.operands[1].reg;
12838 Rn = inst.operands[2].reg;
12839 Rm = inst.operands[3].reg;
12840
12841 reject_bad_reg (RdLo);
12842 reject_bad_reg (RdHi);
12843 reject_bad_reg (Rn);
12844 reject_bad_reg (Rm);
12845
12846 inst.instruction |= RdLo << 12;
12847 inst.instruction |= RdHi << 8;
12848 inst.instruction |= Rn << 16;
12849 inst.instruction |= Rm;
12850
12851 if (RdLo == RdHi)
c19d1205
ZW
12852 as_tsktsk (_("rdhi and rdlo must be different"));
12853}
b05fe5cf 12854
c19d1205
ZW
12855static void
12856do_t_nop (void)
12857{
5ee91343 12858 set_pred_insn_type (NEUTRAL_IT_INSN);
e07e6e58 12859
c19d1205
ZW
12860 if (unified_syntax)
12861 {
12862 if (inst.size_req == 4 || inst.operands[0].imm > 15)
b05fe5cf 12863 {
c19d1205
ZW
12864 inst.instruction = THUMB_OP32 (inst.instruction);
12865 inst.instruction |= inst.operands[0].imm;
12866 }
12867 else
12868 {
bc2d1808
NC
12869 /* PR9722: Check for Thumb2 availability before
12870 generating a thumb2 nop instruction. */
afa62d5e 12871 if (ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v6t2))
bc2d1808
NC
12872 {
12873 inst.instruction = THUMB_OP16 (inst.instruction);
12874 inst.instruction |= inst.operands[0].imm << 4;
12875 }
12876 else
12877 inst.instruction = 0x46c0;
c19d1205
ZW
12878 }
12879 }
12880 else
12881 {
12882 constraint (inst.operands[0].present,
12883 _("Thumb does not support NOP with hints"));
12884 inst.instruction = 0x46c0;
12885 }
12886}
b05fe5cf 12887
c19d1205
ZW
12888static void
12889do_t_neg (void)
12890{
12891 if (unified_syntax)
12892 {
3d388997
PB
12893 bfd_boolean narrow;
12894
12895 if (THUMB_SETS_FLAGS (inst.instruction))
5ee91343 12896 narrow = !in_pred_block ();
3d388997 12897 else
5ee91343 12898 narrow = in_pred_block ();
3d388997
PB
12899 if (inst.operands[0].reg > 7 || inst.operands[1].reg > 7)
12900 narrow = FALSE;
12901 if (inst.size_req == 4)
12902 narrow = FALSE;
12903
12904 if (!narrow)
c19d1205
ZW
12905 {
12906 inst.instruction = THUMB_OP32 (inst.instruction);
12907 inst.instruction |= inst.operands[0].reg << 8;
12908 inst.instruction |= inst.operands[1].reg << 16;
b05fe5cf
ZW
12909 }
12910 else
12911 {
c19d1205
ZW
12912 inst.instruction = THUMB_OP16 (inst.instruction);
12913 inst.instruction |= inst.operands[0].reg;
12914 inst.instruction |= inst.operands[1].reg << 3;
b05fe5cf
ZW
12915 }
12916 }
12917 else
12918 {
c19d1205
ZW
12919 constraint (inst.operands[0].reg > 7 || inst.operands[1].reg > 7,
12920 BAD_HIREG);
12921 constraint (THUMB_SETS_FLAGS (inst.instruction), BAD_THUMB32);
12922
12923 inst.instruction = THUMB_OP16 (inst.instruction);
12924 inst.instruction |= inst.operands[0].reg;
12925 inst.instruction |= inst.operands[1].reg << 3;
12926 }
12927}
12928
1c444d06
JM
12929static void
12930do_t_orn (void)
12931{
12932 unsigned Rd, Rn;
12933
12934 Rd = inst.operands[0].reg;
12935 Rn = inst.operands[1].present ? inst.operands[1].reg : Rd;
12936
fdfde340
JM
12937 reject_bad_reg (Rd);
12938 /* Rn == REG_SP is unpredictable; Rn == REG_PC is MVN. */
12939 reject_bad_reg (Rn);
12940
1c444d06
JM
12941 inst.instruction |= Rd << 8;
12942 inst.instruction |= Rn << 16;
12943
12944 if (!inst.operands[2].isreg)
12945 {
12946 inst.instruction = (inst.instruction & 0xe1ffffff) | 0x10000000;
e2b0ab59 12947 inst.relocs[0].type = BFD_RELOC_ARM_T32_IMMEDIATE;
1c444d06
JM
12948 }
12949 else
12950 {
12951 unsigned Rm;
12952
12953 Rm = inst.operands[2].reg;
fdfde340 12954 reject_bad_reg (Rm);
1c444d06
JM
12955
12956 constraint (inst.operands[2].shifted
12957 && inst.operands[2].immisreg,
12958 _("shift must be constant"));
12959 encode_thumb32_shifted_operand (2);
12960 }
12961}
12962
c19d1205
ZW
12963static void
12964do_t_pkhbt (void)
12965{
fdfde340
JM
12966 unsigned Rd, Rn, Rm;
12967
12968 Rd = inst.operands[0].reg;
12969 Rn = inst.operands[1].reg;
12970 Rm = inst.operands[2].reg;
12971
12972 reject_bad_reg (Rd);
12973 reject_bad_reg (Rn);
12974 reject_bad_reg (Rm);
12975
12976 inst.instruction |= Rd << 8;
12977 inst.instruction |= Rn << 16;
12978 inst.instruction |= Rm;
c19d1205
ZW
12979 if (inst.operands[3].present)
12980 {
e2b0ab59
AV
12981 unsigned int val = inst.relocs[0].exp.X_add_number;
12982 constraint (inst.relocs[0].exp.X_op != O_constant,
c19d1205
ZW
12983 _("expression too complex"));
12984 inst.instruction |= (val & 0x1c) << 10;
12985 inst.instruction |= (val & 0x03) << 6;
b05fe5cf 12986 }
c19d1205 12987}
b05fe5cf 12988
c19d1205
ZW
12989static void
12990do_t_pkhtb (void)
12991{
12992 if (!inst.operands[3].present)
1ef52f49
NC
12993 {
12994 unsigned Rtmp;
12995
12996 inst.instruction &= ~0x00000020;
12997
12998 /* PR 10168. Swap the Rm and Rn registers. */
12999 Rtmp = inst.operands[1].reg;
13000 inst.operands[1].reg = inst.operands[2].reg;
13001 inst.operands[2].reg = Rtmp;
13002 }
c19d1205 13003 do_t_pkhbt ();
b05fe5cf
ZW
13004}
13005
c19d1205
ZW
13006static void
13007do_t_pld (void)
13008{
fdfde340
JM
13009 if (inst.operands[0].immisreg)
13010 reject_bad_reg (inst.operands[0].imm);
13011
c19d1205
ZW
13012 encode_thumb32_addr_mode (0, /*is_t=*/FALSE, /*is_d=*/FALSE);
13013}
b05fe5cf 13014
c19d1205
ZW
13015static void
13016do_t_push_pop (void)
b99bd4ef 13017{
e9f89963 13018 unsigned mask;
5f4273c7 13019
c19d1205
ZW
13020 constraint (inst.operands[0].writeback,
13021 _("push/pop do not support {reglist}^"));
e2b0ab59 13022 constraint (inst.relocs[0].type != BFD_RELOC_UNUSED,
c19d1205 13023 _("expression too complex"));
b99bd4ef 13024
e9f89963 13025 mask = inst.operands[0].imm;
d3bfe16e 13026 if (inst.size_req != 4 && (mask & ~0xff) == 0)
3c707909 13027 inst.instruction = THUMB_OP16 (inst.instruction) | mask;
d3bfe16e 13028 else if (inst.size_req != 4
c6025a80 13029 && (mask & ~0xff) == (1U << (inst.instruction == T_MNEM_push
d3bfe16e 13030 ? REG_LR : REG_PC)))
b99bd4ef 13031 {
c19d1205
ZW
13032 inst.instruction = THUMB_OP16 (inst.instruction);
13033 inst.instruction |= THUMB_PP_PC_LR;
3c707909 13034 inst.instruction |= mask & 0xff;
c19d1205
ZW
13035 }
13036 else if (unified_syntax)
13037 {
3c707909 13038 inst.instruction = THUMB_OP32 (inst.instruction);
4b5a202f
AV
13039 encode_thumb2_multi (TRUE /* do_io */, 13, mask, TRUE);
13040 }
13041 else
13042 {
13043 inst.error = _("invalid register list to push/pop instruction");
13044 return;
c19d1205 13045 }
4b5a202f
AV
13046}
13047
13048static void
13049do_t_clrm (void)
13050{
13051 if (unified_syntax)
13052 encode_thumb2_multi (FALSE /* do_io */, -1, inst.operands[0].imm, FALSE);
c19d1205
ZW
13053 else
13054 {
13055 inst.error = _("invalid register list to push/pop instruction");
13056 return;
13057 }
c19d1205 13058}
b99bd4ef 13059
efd6b359
AV
13060static void
13061do_t_vscclrm (void)
13062{
13063 if (inst.operands[0].issingle)
13064 {
13065 inst.instruction |= (inst.operands[0].reg & 0x1) << 22;
13066 inst.instruction |= (inst.operands[0].reg & 0x1e) << 11;
13067 inst.instruction |= inst.operands[0].imm;
13068 }
13069 else
13070 {
13071 inst.instruction |= (inst.operands[0].reg & 0x10) << 18;
13072 inst.instruction |= (inst.operands[0].reg & 0xf) << 12;
13073 inst.instruction |= 1 << 8;
13074 inst.instruction |= inst.operands[0].imm << 1;
13075 }
13076}
13077
c19d1205
ZW
13078static void
13079do_t_rbit (void)
13080{
fdfde340
JM
13081 unsigned Rd, Rm;
13082
13083 Rd = inst.operands[0].reg;
13084 Rm = inst.operands[1].reg;
13085
13086 reject_bad_reg (Rd);
13087 reject_bad_reg (Rm);
13088
13089 inst.instruction |= Rd << 8;
13090 inst.instruction |= Rm << 16;
13091 inst.instruction |= Rm;
c19d1205 13092}
b99bd4ef 13093
c19d1205
ZW
13094static void
13095do_t_rev (void)
13096{
fdfde340
JM
13097 unsigned Rd, Rm;
13098
13099 Rd = inst.operands[0].reg;
13100 Rm = inst.operands[1].reg;
13101
13102 reject_bad_reg (Rd);
13103 reject_bad_reg (Rm);
13104
13105 if (Rd <= 7 && Rm <= 7
c19d1205
ZW
13106 && inst.size_req != 4)
13107 {
13108 inst.instruction = THUMB_OP16 (inst.instruction);
fdfde340
JM
13109 inst.instruction |= Rd;
13110 inst.instruction |= Rm << 3;
c19d1205
ZW
13111 }
13112 else if (unified_syntax)
13113 {
13114 inst.instruction = THUMB_OP32 (inst.instruction);
fdfde340
JM
13115 inst.instruction |= Rd << 8;
13116 inst.instruction |= Rm << 16;
13117 inst.instruction |= Rm;
c19d1205
ZW
13118 }
13119 else
13120 inst.error = BAD_HIREG;
13121}
b99bd4ef 13122
1c444d06
JM
13123static void
13124do_t_rrx (void)
13125{
13126 unsigned Rd, Rm;
13127
13128 Rd = inst.operands[0].reg;
13129 Rm = inst.operands[1].reg;
13130
fdfde340
JM
13131 reject_bad_reg (Rd);
13132 reject_bad_reg (Rm);
c921be7d 13133
1c444d06
JM
13134 inst.instruction |= Rd << 8;
13135 inst.instruction |= Rm;
13136}
13137
c19d1205
ZW
13138static void
13139do_t_rsb (void)
13140{
fdfde340 13141 unsigned Rd, Rs;
b99bd4ef 13142
c19d1205
ZW
13143 Rd = inst.operands[0].reg;
13144 Rs = (inst.operands[1].present
13145 ? inst.operands[1].reg /* Rd, Rs, foo */
13146 : inst.operands[0].reg); /* Rd, foo -> Rd, Rd, foo */
b99bd4ef 13147
fdfde340
JM
13148 reject_bad_reg (Rd);
13149 reject_bad_reg (Rs);
13150 if (inst.operands[2].isreg)
13151 reject_bad_reg (inst.operands[2].reg);
13152
c19d1205
ZW
13153 inst.instruction |= Rd << 8;
13154 inst.instruction |= Rs << 16;
13155 if (!inst.operands[2].isreg)
13156 {
026d3abb
PB
13157 bfd_boolean narrow;
13158
13159 if ((inst.instruction & 0x00100000) != 0)
5ee91343 13160 narrow = !in_pred_block ();
026d3abb 13161 else
5ee91343 13162 narrow = in_pred_block ();
026d3abb
PB
13163
13164 if (Rd > 7 || Rs > 7)
13165 narrow = FALSE;
13166
13167 if (inst.size_req == 4 || !unified_syntax)
13168 narrow = FALSE;
13169
e2b0ab59
AV
13170 if (inst.relocs[0].exp.X_op != O_constant
13171 || inst.relocs[0].exp.X_add_number != 0)
026d3abb
PB
13172 narrow = FALSE;
13173
13174 /* Turn rsb #0 into 16-bit neg. We should probably do this via
477330fc 13175 relaxation, but it doesn't seem worth the hassle. */
026d3abb
PB
13176 if (narrow)
13177 {
e2b0ab59 13178 inst.relocs[0].type = BFD_RELOC_UNUSED;
026d3abb
PB
13179 inst.instruction = THUMB_OP16 (T_MNEM_negs);
13180 inst.instruction |= Rs << 3;
13181 inst.instruction |= Rd;
13182 }
13183 else
13184 {
13185 inst.instruction = (inst.instruction & 0xe1ffffff) | 0x10000000;
e2b0ab59 13186 inst.relocs[0].type = BFD_RELOC_ARM_T32_IMMEDIATE;
026d3abb 13187 }
c19d1205
ZW
13188 }
13189 else
13190 encode_thumb32_shifted_operand (2);
13191}
b99bd4ef 13192
c19d1205
ZW
13193static void
13194do_t_setend (void)
13195{
12e37cbc
MGD
13196 if (warn_on_deprecated
13197 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v8))
5c3696f8 13198 as_tsktsk (_("setend use is deprecated for ARMv8"));
12e37cbc 13199
5ee91343 13200 set_pred_insn_type (OUTSIDE_PRED_INSN);
c19d1205
ZW
13201 if (inst.operands[0].imm)
13202 inst.instruction |= 0x8;
13203}
b99bd4ef 13204
c19d1205
ZW
13205static void
13206do_t_shift (void)
13207{
13208 if (!inst.operands[1].present)
13209 inst.operands[1].reg = inst.operands[0].reg;
13210
13211 if (unified_syntax)
13212 {
3d388997
PB
13213 bfd_boolean narrow;
13214 int shift_kind;
13215
13216 switch (inst.instruction)
13217 {
13218 case T_MNEM_asr:
13219 case T_MNEM_asrs: shift_kind = SHIFT_ASR; break;
13220 case T_MNEM_lsl:
13221 case T_MNEM_lsls: shift_kind = SHIFT_LSL; break;
13222 case T_MNEM_lsr:
13223 case T_MNEM_lsrs: shift_kind = SHIFT_LSR; break;
13224 case T_MNEM_ror:
13225 case T_MNEM_rors: shift_kind = SHIFT_ROR; break;
13226 default: abort ();
13227 }
13228
13229 if (THUMB_SETS_FLAGS (inst.instruction))
5ee91343 13230 narrow = !in_pred_block ();
3d388997 13231 else
5ee91343 13232 narrow = in_pred_block ();
3d388997
PB
13233 if (inst.operands[0].reg > 7 || inst.operands[1].reg > 7)
13234 narrow = FALSE;
13235 if (!inst.operands[2].isreg && shift_kind == SHIFT_ROR)
13236 narrow = FALSE;
13237 if (inst.operands[2].isreg
13238 && (inst.operands[1].reg != inst.operands[0].reg
13239 || inst.operands[2].reg > 7))
13240 narrow = FALSE;
13241 if (inst.size_req == 4)
13242 narrow = FALSE;
13243
fdfde340
JM
13244 reject_bad_reg (inst.operands[0].reg);
13245 reject_bad_reg (inst.operands[1].reg);
c921be7d 13246
3d388997 13247 if (!narrow)
c19d1205
ZW
13248 {
13249 if (inst.operands[2].isreg)
b99bd4ef 13250 {
fdfde340 13251 reject_bad_reg (inst.operands[2].reg);
c19d1205
ZW
13252 inst.instruction = THUMB_OP32 (inst.instruction);
13253 inst.instruction |= inst.operands[0].reg << 8;
13254 inst.instruction |= inst.operands[1].reg << 16;
13255 inst.instruction |= inst.operands[2].reg;
94342ec3
NC
13256
13257 /* PR 12854: Error on extraneous shifts. */
13258 constraint (inst.operands[2].shifted,
13259 _("extraneous shift as part of operand to shift insn"));
c19d1205
ZW
13260 }
13261 else
13262 {
13263 inst.operands[1].shifted = 1;
3d388997 13264 inst.operands[1].shift_kind = shift_kind;
c19d1205
ZW
13265 inst.instruction = THUMB_OP32 (THUMB_SETS_FLAGS (inst.instruction)
13266 ? T_MNEM_movs : T_MNEM_mov);
13267 inst.instruction |= inst.operands[0].reg << 8;
13268 encode_thumb32_shifted_operand (1);
13269 /* Prevent the incorrect generation of an ARM_IMMEDIATE fixup. */
e2b0ab59 13270 inst.relocs[0].type = BFD_RELOC_UNUSED;
b99bd4ef
NC
13271 }
13272 }
13273 else
13274 {
c19d1205 13275 if (inst.operands[2].isreg)
b99bd4ef 13276 {
3d388997 13277 switch (shift_kind)
b99bd4ef 13278 {
3d388997
PB
13279 case SHIFT_ASR: inst.instruction = T_OPCODE_ASR_R; break;
13280 case SHIFT_LSL: inst.instruction = T_OPCODE_LSL_R; break;
13281 case SHIFT_LSR: inst.instruction = T_OPCODE_LSR_R; break;
13282 case SHIFT_ROR: inst.instruction = T_OPCODE_ROR_R; break;
c19d1205 13283 default: abort ();
b99bd4ef 13284 }
5f4273c7 13285
c19d1205
ZW
13286 inst.instruction |= inst.operands[0].reg;
13287 inst.instruction |= inst.operands[2].reg << 3;
af199b06
NC
13288
13289 /* PR 12854: Error on extraneous shifts. */
13290 constraint (inst.operands[2].shifted,
13291 _("extraneous shift as part of operand to shift insn"));
b99bd4ef
NC
13292 }
13293 else
13294 {
3d388997 13295 switch (shift_kind)
b99bd4ef 13296 {
3d388997
PB
13297 case SHIFT_ASR: inst.instruction = T_OPCODE_ASR_I; break;
13298 case SHIFT_LSL: inst.instruction = T_OPCODE_LSL_I; break;
13299 case SHIFT_LSR: inst.instruction = T_OPCODE_LSR_I; break;
c19d1205 13300 default: abort ();
b99bd4ef 13301 }
e2b0ab59 13302 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_SHIFT;
c19d1205
ZW
13303 inst.instruction |= inst.operands[0].reg;
13304 inst.instruction |= inst.operands[1].reg << 3;
b99bd4ef
NC
13305 }
13306 }
c19d1205
ZW
13307 }
13308 else
13309 {
13310 constraint (inst.operands[0].reg > 7
13311 || inst.operands[1].reg > 7, BAD_HIREG);
13312 constraint (THUMB_SETS_FLAGS (inst.instruction), BAD_THUMB32);
b99bd4ef 13313
c19d1205
ZW
13314 if (inst.operands[2].isreg) /* Rd, {Rs,} Rn */
13315 {
13316 constraint (inst.operands[2].reg > 7, BAD_HIREG);
13317 constraint (inst.operands[0].reg != inst.operands[1].reg,
13318 _("source1 and dest must be same register"));
b99bd4ef 13319
c19d1205
ZW
13320 switch (inst.instruction)
13321 {
13322 case T_MNEM_asr: inst.instruction = T_OPCODE_ASR_R; break;
13323 case T_MNEM_lsl: inst.instruction = T_OPCODE_LSL_R; break;
13324 case T_MNEM_lsr: inst.instruction = T_OPCODE_LSR_R; break;
13325 case T_MNEM_ror: inst.instruction = T_OPCODE_ROR_R; break;
13326 default: abort ();
13327 }
5f4273c7 13328
c19d1205
ZW
13329 inst.instruction |= inst.operands[0].reg;
13330 inst.instruction |= inst.operands[2].reg << 3;
af199b06
NC
13331
13332 /* PR 12854: Error on extraneous shifts. */
13333 constraint (inst.operands[2].shifted,
13334 _("extraneous shift as part of operand to shift insn"));
c19d1205
ZW
13335 }
13336 else
b99bd4ef 13337 {
c19d1205
ZW
13338 switch (inst.instruction)
13339 {
13340 case T_MNEM_asr: inst.instruction = T_OPCODE_ASR_I; break;
13341 case T_MNEM_lsl: inst.instruction = T_OPCODE_LSL_I; break;
13342 case T_MNEM_lsr: inst.instruction = T_OPCODE_LSR_I; break;
13343 case T_MNEM_ror: inst.error = _("ror #imm not supported"); return;
13344 default: abort ();
13345 }
e2b0ab59 13346 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_SHIFT;
c19d1205
ZW
13347 inst.instruction |= inst.operands[0].reg;
13348 inst.instruction |= inst.operands[1].reg << 3;
b99bd4ef
NC
13349 }
13350 }
b99bd4ef
NC
13351}
13352
13353static void
c19d1205 13354do_t_simd (void)
b99bd4ef 13355{
fdfde340
JM
13356 unsigned Rd, Rn, Rm;
13357
13358 Rd = inst.operands[0].reg;
13359 Rn = inst.operands[1].reg;
13360 Rm = inst.operands[2].reg;
13361
13362 reject_bad_reg (Rd);
13363 reject_bad_reg (Rn);
13364 reject_bad_reg (Rm);
13365
13366 inst.instruction |= Rd << 8;
13367 inst.instruction |= Rn << 16;
13368 inst.instruction |= Rm;
c19d1205 13369}
b99bd4ef 13370
03ee1b7f
NC
13371static void
13372do_t_simd2 (void)
13373{
13374 unsigned Rd, Rn, Rm;
13375
13376 Rd = inst.operands[0].reg;
13377 Rm = inst.operands[1].reg;
13378 Rn = inst.operands[2].reg;
13379
13380 reject_bad_reg (Rd);
13381 reject_bad_reg (Rn);
13382 reject_bad_reg (Rm);
13383
13384 inst.instruction |= Rd << 8;
13385 inst.instruction |= Rn << 16;
13386 inst.instruction |= Rm;
13387}
13388
c19d1205 13389static void
3eb17e6b 13390do_t_smc (void)
c19d1205 13391{
e2b0ab59 13392 unsigned int value = inst.relocs[0].exp.X_add_number;
f4c65163
MGD
13393 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v7a),
13394 _("SMC is not permitted on this architecture"));
e2b0ab59 13395 constraint (inst.relocs[0].exp.X_op != O_constant,
c19d1205 13396 _("expression too complex"));
e2b0ab59 13397 inst.relocs[0].type = BFD_RELOC_UNUSED;
c19d1205
ZW
13398 inst.instruction |= (value & 0xf000) >> 12;
13399 inst.instruction |= (value & 0x0ff0);
13400 inst.instruction |= (value & 0x000f) << 16;
24382199 13401 /* PR gas/15623: SMC instructions must be last in an IT block. */
5ee91343 13402 set_pred_insn_type_last ();
c19d1205 13403}
b99bd4ef 13404
90ec0d68
MGD
13405static void
13406do_t_hvc (void)
13407{
e2b0ab59 13408 unsigned int value = inst.relocs[0].exp.X_add_number;
90ec0d68 13409
e2b0ab59 13410 inst.relocs[0].type = BFD_RELOC_UNUSED;
90ec0d68
MGD
13411 inst.instruction |= (value & 0x0fff);
13412 inst.instruction |= (value & 0xf000) << 4;
13413}
13414
c19d1205 13415static void
3a21c15a 13416do_t_ssat_usat (int bias)
c19d1205 13417{
fdfde340
JM
13418 unsigned Rd, Rn;
13419
13420 Rd = inst.operands[0].reg;
13421 Rn = inst.operands[2].reg;
13422
13423 reject_bad_reg (Rd);
13424 reject_bad_reg (Rn);
13425
13426 inst.instruction |= Rd << 8;
3a21c15a 13427 inst.instruction |= inst.operands[1].imm - bias;
fdfde340 13428 inst.instruction |= Rn << 16;
b99bd4ef 13429
c19d1205 13430 if (inst.operands[3].present)
b99bd4ef 13431 {
e2b0ab59 13432 offsetT shift_amount = inst.relocs[0].exp.X_add_number;
3a21c15a 13433
e2b0ab59 13434 inst.relocs[0].type = BFD_RELOC_UNUSED;
3a21c15a 13435
e2b0ab59 13436 constraint (inst.relocs[0].exp.X_op != O_constant,
c19d1205 13437 _("expression too complex"));
b99bd4ef 13438
3a21c15a 13439 if (shift_amount != 0)
6189168b 13440 {
3a21c15a
NC
13441 constraint (shift_amount > 31,
13442 _("shift expression is too large"));
13443
c19d1205 13444 if (inst.operands[3].shift_kind == SHIFT_ASR)
3a21c15a
NC
13445 inst.instruction |= 0x00200000; /* sh bit. */
13446
13447 inst.instruction |= (shift_amount & 0x1c) << 10;
13448 inst.instruction |= (shift_amount & 0x03) << 6;
6189168b
NC
13449 }
13450 }
b99bd4ef 13451}
c921be7d 13452
3a21c15a
NC
13453static void
13454do_t_ssat (void)
13455{
13456 do_t_ssat_usat (1);
13457}
b99bd4ef 13458
0dd132b6 13459static void
c19d1205 13460do_t_ssat16 (void)
0dd132b6 13461{
fdfde340
JM
13462 unsigned Rd, Rn;
13463
13464 Rd = inst.operands[0].reg;
13465 Rn = inst.operands[2].reg;
13466
13467 reject_bad_reg (Rd);
13468 reject_bad_reg (Rn);
13469
13470 inst.instruction |= Rd << 8;
c19d1205 13471 inst.instruction |= inst.operands[1].imm - 1;
fdfde340 13472 inst.instruction |= Rn << 16;
c19d1205 13473}
0dd132b6 13474
c19d1205
ZW
13475static void
13476do_t_strex (void)
13477{
13478 constraint (!inst.operands[2].isreg || !inst.operands[2].preind
13479 || inst.operands[2].postind || inst.operands[2].writeback
13480 || inst.operands[2].immisreg || inst.operands[2].shifted
13481 || inst.operands[2].negative,
01cfc07f 13482 BAD_ADDR_MODE);
0dd132b6 13483
5be8be5d
DG
13484 constraint (inst.operands[2].reg == REG_PC, BAD_PC);
13485
c19d1205
ZW
13486 inst.instruction |= inst.operands[0].reg << 8;
13487 inst.instruction |= inst.operands[1].reg << 12;
13488 inst.instruction |= inst.operands[2].reg << 16;
e2b0ab59 13489 inst.relocs[0].type = BFD_RELOC_ARM_T32_OFFSET_U8;
0dd132b6
NC
13490}
13491
b99bd4ef 13492static void
c19d1205 13493do_t_strexd (void)
b99bd4ef 13494{
c19d1205
ZW
13495 if (!inst.operands[2].present)
13496 inst.operands[2].reg = inst.operands[1].reg + 1;
b99bd4ef 13497
c19d1205
ZW
13498 constraint (inst.operands[0].reg == inst.operands[1].reg
13499 || inst.operands[0].reg == inst.operands[2].reg
f8a8e9d6 13500 || inst.operands[0].reg == inst.operands[3].reg,
c19d1205 13501 BAD_OVERLAP);
b99bd4ef 13502
c19d1205
ZW
13503 inst.instruction |= inst.operands[0].reg;
13504 inst.instruction |= inst.operands[1].reg << 12;
13505 inst.instruction |= inst.operands[2].reg << 8;
13506 inst.instruction |= inst.operands[3].reg << 16;
b99bd4ef
NC
13507}
13508
13509static void
c19d1205 13510do_t_sxtah (void)
b99bd4ef 13511{
fdfde340
JM
13512 unsigned Rd, Rn, Rm;
13513
13514 Rd = inst.operands[0].reg;
13515 Rn = inst.operands[1].reg;
13516 Rm = inst.operands[2].reg;
13517
13518 reject_bad_reg (Rd);
13519 reject_bad_reg (Rn);
13520 reject_bad_reg (Rm);
13521
13522 inst.instruction |= Rd << 8;
13523 inst.instruction |= Rn << 16;
13524 inst.instruction |= Rm;
c19d1205
ZW
13525 inst.instruction |= inst.operands[3].imm << 4;
13526}
b99bd4ef 13527
c19d1205
ZW
13528static void
13529do_t_sxth (void)
13530{
fdfde340
JM
13531 unsigned Rd, Rm;
13532
13533 Rd = inst.operands[0].reg;
13534 Rm = inst.operands[1].reg;
13535
13536 reject_bad_reg (Rd);
13537 reject_bad_reg (Rm);
c921be7d
NC
13538
13539 if (inst.instruction <= 0xffff
13540 && inst.size_req != 4
fdfde340 13541 && Rd <= 7 && Rm <= 7
c19d1205 13542 && (!inst.operands[2].present || inst.operands[2].imm == 0))
b99bd4ef 13543 {
c19d1205 13544 inst.instruction = THUMB_OP16 (inst.instruction);
fdfde340
JM
13545 inst.instruction |= Rd;
13546 inst.instruction |= Rm << 3;
b99bd4ef 13547 }
c19d1205 13548 else if (unified_syntax)
b99bd4ef 13549 {
c19d1205
ZW
13550 if (inst.instruction <= 0xffff)
13551 inst.instruction = THUMB_OP32 (inst.instruction);
fdfde340
JM
13552 inst.instruction |= Rd << 8;
13553 inst.instruction |= Rm;
c19d1205 13554 inst.instruction |= inst.operands[2].imm << 4;
b99bd4ef 13555 }
c19d1205 13556 else
b99bd4ef 13557 {
c19d1205
ZW
13558 constraint (inst.operands[2].present && inst.operands[2].imm != 0,
13559 _("Thumb encoding does not support rotation"));
13560 constraint (1, BAD_HIREG);
b99bd4ef 13561 }
c19d1205 13562}
b99bd4ef 13563
c19d1205
ZW
13564static void
13565do_t_swi (void)
13566{
e2b0ab59 13567 inst.relocs[0].type = BFD_RELOC_ARM_SWI;
c19d1205 13568}
b99bd4ef 13569
92e90b6e
PB
13570static void
13571do_t_tb (void)
13572{
fdfde340 13573 unsigned Rn, Rm;
92e90b6e
PB
13574 int half;
13575
13576 half = (inst.instruction & 0x10) != 0;
5ee91343 13577 set_pred_insn_type_last ();
dfa9f0d5
PB
13578 constraint (inst.operands[0].immisreg,
13579 _("instruction requires register index"));
fdfde340
JM
13580
13581 Rn = inst.operands[0].reg;
13582 Rm = inst.operands[0].imm;
c921be7d 13583
5c8ed6a4
JW
13584 if (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v8))
13585 constraint (Rn == REG_SP, BAD_SP);
fdfde340
JM
13586 reject_bad_reg (Rm);
13587
92e90b6e
PB
13588 constraint (!half && inst.operands[0].shifted,
13589 _("instruction does not allow shifted index"));
fdfde340 13590 inst.instruction |= (Rn << 16) | Rm;
92e90b6e
PB
13591}
13592
74db7efb
NC
13593static void
13594do_t_udf (void)
13595{
13596 if (!inst.operands[0].present)
13597 inst.operands[0].imm = 0;
13598
13599 if ((unsigned int) inst.operands[0].imm > 255 || inst.size_req == 4)
13600 {
13601 constraint (inst.size_req == 2,
13602 _("immediate value out of range"));
13603 inst.instruction = THUMB_OP32 (inst.instruction);
13604 inst.instruction |= (inst.operands[0].imm & 0xf000u) << 4;
13605 inst.instruction |= (inst.operands[0].imm & 0x0fffu) << 0;
13606 }
13607 else
13608 {
13609 inst.instruction = THUMB_OP16 (inst.instruction);
13610 inst.instruction |= inst.operands[0].imm;
13611 }
13612
5ee91343 13613 set_pred_insn_type (NEUTRAL_IT_INSN);
74db7efb
NC
13614}
13615
13616
c19d1205
ZW
13617static void
13618do_t_usat (void)
13619{
3a21c15a 13620 do_t_ssat_usat (0);
b99bd4ef
NC
13621}
13622
13623static void
c19d1205 13624do_t_usat16 (void)
b99bd4ef 13625{
fdfde340
JM
13626 unsigned Rd, Rn;
13627
13628 Rd = inst.operands[0].reg;
13629 Rn = inst.operands[2].reg;
13630
13631 reject_bad_reg (Rd);
13632 reject_bad_reg (Rn);
13633
13634 inst.instruction |= Rd << 8;
c19d1205 13635 inst.instruction |= inst.operands[1].imm;
fdfde340 13636 inst.instruction |= Rn << 16;
b99bd4ef 13637}
c19d1205 13638
e12437dc
AV
13639/* Checking the range of the branch offset (VAL) with NBITS bits
13640 and IS_SIGNED signedness. Also checks the LSB to be 0. */
13641static int
13642v8_1_branch_value_check (int val, int nbits, int is_signed)
13643{
13644 gas_assert (nbits > 0 && nbits <= 32);
13645 if (is_signed)
13646 {
13647 int cmp = (1 << (nbits - 1));
13648 if ((val < -cmp) || (val >= cmp) || (val & 0x01))
13649 return FAIL;
13650 }
13651 else
13652 {
13653 if ((val <= 0) || (val >= (1 << nbits)) || (val & 0x1))
13654 return FAIL;
13655 }
13656 return SUCCESS;
13657}
13658
4389b29a
AV
13659/* For branches in Armv8.1-M Mainline. */
13660static void
13661do_t_branch_future (void)
13662{
13663 unsigned long insn = inst.instruction;
13664
13665 inst.instruction = THUMB_OP32 (inst.instruction);
13666 if (inst.operands[0].hasreloc == 0)
13667 {
13668 if (v8_1_branch_value_check (inst.operands[0].imm, 5, FALSE) == FAIL)
13669 as_bad (BAD_BRANCH_OFF);
13670
13671 inst.instruction |= ((inst.operands[0].imm & 0x1f) >> 1) << 23;
13672 }
13673 else
13674 {
13675 inst.relocs[0].type = BFD_RELOC_THUMB_PCREL_BRANCH5;
13676 inst.relocs[0].pc_rel = 1;
13677 }
13678
13679 switch (insn)
13680 {
13681 case T_MNEM_bf:
13682 if (inst.operands[1].hasreloc == 0)
13683 {
13684 int val = inst.operands[1].imm;
13685 if (v8_1_branch_value_check (inst.operands[1].imm, 17, TRUE) == FAIL)
13686 as_bad (BAD_BRANCH_OFF);
13687
13688 int immA = (val & 0x0001f000) >> 12;
13689 int immB = (val & 0x00000ffc) >> 2;
13690 int immC = (val & 0x00000002) >> 1;
13691 inst.instruction |= (immA << 16) | (immB << 1) | (immC << 11);
13692 }
13693 else
13694 {
13695 inst.relocs[1].type = BFD_RELOC_ARM_THUMB_BF17;
13696 inst.relocs[1].pc_rel = 1;
13697 }
13698 break;
13699
65d1bc05
AV
13700 case T_MNEM_bfl:
13701 if (inst.operands[1].hasreloc == 0)
13702 {
13703 int val = inst.operands[1].imm;
13704 if (v8_1_branch_value_check (inst.operands[1].imm, 19, TRUE) == FAIL)
13705 as_bad (BAD_BRANCH_OFF);
13706
13707 int immA = (val & 0x0007f000) >> 12;
13708 int immB = (val & 0x00000ffc) >> 2;
13709 int immC = (val & 0x00000002) >> 1;
13710 inst.instruction |= (immA << 16) | (immB << 1) | (immC << 11);
13711 }
13712 else
13713 {
13714 inst.relocs[1].type = BFD_RELOC_ARM_THUMB_BF19;
13715 inst.relocs[1].pc_rel = 1;
13716 }
13717 break;
13718
f6b2b12d
AV
13719 case T_MNEM_bfcsel:
13720 /* Operand 1. */
13721 if (inst.operands[1].hasreloc == 0)
13722 {
13723 int val = inst.operands[1].imm;
13724 int immA = (val & 0x00001000) >> 12;
13725 int immB = (val & 0x00000ffc) >> 2;
13726 int immC = (val & 0x00000002) >> 1;
13727 inst.instruction |= (immA << 16) | (immB << 1) | (immC << 11);
13728 }
13729 else
13730 {
13731 inst.relocs[1].type = BFD_RELOC_ARM_THUMB_BF13;
13732 inst.relocs[1].pc_rel = 1;
13733 }
13734
13735 /* Operand 2. */
13736 if (inst.operands[2].hasreloc == 0)
13737 {
13738 constraint ((inst.operands[0].hasreloc != 0), BAD_ARGS);
13739 int val2 = inst.operands[2].imm;
13740 int val0 = inst.operands[0].imm & 0x1f;
13741 int diff = val2 - val0;
13742 if (diff == 4)
13743 inst.instruction |= 1 << 17; /* T bit. */
13744 else if (diff != 2)
13745 as_bad (_("out of range label-relative fixup value"));
13746 }
13747 else
13748 {
13749 constraint ((inst.operands[0].hasreloc == 0), BAD_ARGS);
13750 inst.relocs[2].type = BFD_RELOC_THUMB_PCREL_BFCSEL;
13751 inst.relocs[2].pc_rel = 1;
13752 }
13753
13754 /* Operand 3. */
13755 constraint (inst.cond != COND_ALWAYS, BAD_COND);
13756 inst.instruction |= (inst.operands[3].imm & 0xf) << 18;
13757 break;
13758
f1c7f421
AV
13759 case T_MNEM_bfx:
13760 case T_MNEM_bflx:
13761 inst.instruction |= inst.operands[1].reg << 16;
13762 break;
13763
4389b29a
AV
13764 default: abort ();
13765 }
13766}
13767
60f993ce
AV
13768/* Helper function for do_t_loloop to handle relocations. */
13769static void
13770v8_1_loop_reloc (int is_le)
13771{
13772 if (inst.relocs[0].exp.X_op == O_constant)
13773 {
13774 int value = inst.relocs[0].exp.X_add_number;
13775 value = (is_le) ? -value : value;
13776
13777 if (v8_1_branch_value_check (value, 12, FALSE) == FAIL)
13778 as_bad (BAD_BRANCH_OFF);
13779
13780 int imml, immh;
13781
13782 immh = (value & 0x00000ffc) >> 2;
13783 imml = (value & 0x00000002) >> 1;
13784
13785 inst.instruction |= (imml << 11) | (immh << 1);
13786 }
13787 else
13788 {
13789 inst.relocs[0].type = BFD_RELOC_ARM_THUMB_LOOP12;
13790 inst.relocs[0].pc_rel = 1;
13791 }
13792}
13793
13794/* To handle the Scalar Low Overhead Loop instructions
13795 in Armv8.1-M Mainline. */
13796static void
13797do_t_loloop (void)
13798{
13799 unsigned long insn = inst.instruction;
13800
5ee91343 13801 set_pred_insn_type (OUTSIDE_PRED_INSN);
60f993ce
AV
13802 inst.instruction = THUMB_OP32 (inst.instruction);
13803
13804 switch (insn)
13805 {
13806 case T_MNEM_le:
13807 /* le <label>. */
13808 if (!inst.operands[0].present)
13809 inst.instruction |= 1 << 21;
13810
13811 v8_1_loop_reloc (TRUE);
13812 break;
13813
13814 case T_MNEM_wls:
13815 v8_1_loop_reloc (FALSE);
13816 /* Fall through. */
13817 case T_MNEM_dls:
13818 constraint (inst.operands[1].isreg != 1, BAD_ARGS);
13819 inst.instruction |= (inst.operands[1].reg << 16);
13820 break;
13821
13822 default: abort();
13823 }
13824}
13825
a302e574
AV
13826/* MVE instruction encoder helpers. */
13827#define M_MNEM_vabav 0xee800f01
13828#define M_MNEM_vmladav 0xeef00e00
13829#define M_MNEM_vmladava 0xeef00e20
13830#define M_MNEM_vmladavx 0xeef01e00
13831#define M_MNEM_vmladavax 0xeef01e20
13832#define M_MNEM_vmlsdav 0xeef00e01
13833#define M_MNEM_vmlsdava 0xeef00e21
13834#define M_MNEM_vmlsdavx 0xeef01e01
13835#define M_MNEM_vmlsdavax 0xeef01e21
13836
5287ad62 13837/* Neon instruction encoder helpers. */
5f4273c7 13838
5287ad62 13839/* Encodings for the different types for various Neon opcodes. */
b99bd4ef 13840
5287ad62
JB
13841/* An "invalid" code for the following tables. */
13842#define N_INV -1u
13843
13844struct neon_tab_entry
b99bd4ef 13845{
5287ad62
JB
13846 unsigned integer;
13847 unsigned float_or_poly;
13848 unsigned scalar_or_imm;
13849};
5f4273c7 13850
5287ad62
JB
13851/* Map overloaded Neon opcodes to their respective encodings. */
13852#define NEON_ENC_TAB \
13853 X(vabd, 0x0000700, 0x1200d00, N_INV), \
5ee91343 13854 X(vabdl, 0x0800700, N_INV, N_INV), \
5287ad62
JB
13855 X(vmax, 0x0000600, 0x0000f00, N_INV), \
13856 X(vmin, 0x0000610, 0x0200f00, N_INV), \
13857 X(vpadd, 0x0000b10, 0x1000d00, N_INV), \
13858 X(vpmax, 0x0000a00, 0x1000f00, N_INV), \
13859 X(vpmin, 0x0000a10, 0x1200f00, N_INV), \
13860 X(vadd, 0x0000800, 0x0000d00, N_INV), \
5ee91343 13861 X(vaddl, 0x0800000, N_INV, N_INV), \
5287ad62 13862 X(vsub, 0x1000800, 0x0200d00, N_INV), \
5ee91343 13863 X(vsubl, 0x0800200, N_INV, N_INV), \
5287ad62
JB
13864 X(vceq, 0x1000810, 0x0000e00, 0x1b10100), \
13865 X(vcge, 0x0000310, 0x1000e00, 0x1b10080), \
13866 X(vcgt, 0x0000300, 0x1200e00, 0x1b10000), \
13867 /* Register variants of the following two instructions are encoded as
e07e6e58 13868 vcge / vcgt with the operands reversed. */ \
92559b5b
PB
13869 X(vclt, 0x0000300, 0x1200e00, 0x1b10200), \
13870 X(vcle, 0x0000310, 0x1000e00, 0x1b10180), \
62f3b8c8
PB
13871 X(vfma, N_INV, 0x0000c10, N_INV), \
13872 X(vfms, N_INV, 0x0200c10, N_INV), \
5287ad62
JB
13873 X(vmla, 0x0000900, 0x0000d10, 0x0800040), \
13874 X(vmls, 0x1000900, 0x0200d10, 0x0800440), \
13875 X(vmul, 0x0000910, 0x1000d10, 0x0800840), \
13876 X(vmull, 0x0800c00, 0x0800e00, 0x0800a40), /* polynomial not float. */ \
13877 X(vmlal, 0x0800800, N_INV, 0x0800240), \
13878 X(vmlsl, 0x0800a00, N_INV, 0x0800640), \
13879 X(vqdmlal, 0x0800900, N_INV, 0x0800340), \
13880 X(vqdmlsl, 0x0800b00, N_INV, 0x0800740), \
13881 X(vqdmull, 0x0800d00, N_INV, 0x0800b40), \
13882 X(vqdmulh, 0x0000b00, N_INV, 0x0800c40), \
13883 X(vqrdmulh, 0x1000b00, N_INV, 0x0800d40), \
d6b4b13e
MW
13884 X(vqrdmlah, 0x3000b10, N_INV, 0x0800e40), \
13885 X(vqrdmlsh, 0x3000c10, N_INV, 0x0800f40), \
5287ad62
JB
13886 X(vshl, 0x0000400, N_INV, 0x0800510), \
13887 X(vqshl, 0x0000410, N_INV, 0x0800710), \
13888 X(vand, 0x0000110, N_INV, 0x0800030), \
13889 X(vbic, 0x0100110, N_INV, 0x0800030), \
13890 X(veor, 0x1000110, N_INV, N_INV), \
13891 X(vorn, 0x0300110, N_INV, 0x0800010), \
13892 X(vorr, 0x0200110, N_INV, 0x0800010), \
13893 X(vmvn, 0x1b00580, N_INV, 0x0800030), \
13894 X(vshll, 0x1b20300, N_INV, 0x0800a10), /* max shift, immediate. */ \
13895 X(vcvt, 0x1b30600, N_INV, 0x0800e10), /* integer, fixed-point. */ \
13896 X(vdup, 0xe800b10, N_INV, 0x1b00c00), /* arm, scalar. */ \
13897 X(vld1, 0x0200000, 0x0a00000, 0x0a00c00), /* interlv, lane, dup. */ \
13898 X(vst1, 0x0000000, 0x0800000, N_INV), \
13899 X(vld2, 0x0200100, 0x0a00100, 0x0a00d00), \
13900 X(vst2, 0x0000100, 0x0800100, N_INV), \
13901 X(vld3, 0x0200200, 0x0a00200, 0x0a00e00), \
13902 X(vst3, 0x0000200, 0x0800200, N_INV), \
13903 X(vld4, 0x0200300, 0x0a00300, 0x0a00f00), \
13904 X(vst4, 0x0000300, 0x0800300, N_INV), \
13905 X(vmovn, 0x1b20200, N_INV, N_INV), \
13906 X(vtrn, 0x1b20080, N_INV, N_INV), \
13907 X(vqmovn, 0x1b20200, N_INV, N_INV), \
037e8744
JB
13908 X(vqmovun, 0x1b20240, N_INV, N_INV), \
13909 X(vnmul, 0xe200a40, 0xe200b40, N_INV), \
e6655fda
PB
13910 X(vnmla, 0xe100a40, 0xe100b40, N_INV), \
13911 X(vnmls, 0xe100a00, 0xe100b00, N_INV), \
62f3b8c8
PB
13912 X(vfnma, 0xe900a40, 0xe900b40, N_INV), \
13913 X(vfnms, 0xe900a00, 0xe900b00, N_INV), \
037e8744
JB
13914 X(vcmp, 0xeb40a40, 0xeb40b40, N_INV), \
13915 X(vcmpz, 0xeb50a40, 0xeb50b40, N_INV), \
13916 X(vcmpe, 0xeb40ac0, 0xeb40bc0, N_INV), \
33399f07
MGD
13917 X(vcmpez, 0xeb50ac0, 0xeb50bc0, N_INV), \
13918 X(vseleq, 0xe000a00, N_INV, N_INV), \
13919 X(vselvs, 0xe100a00, N_INV, N_INV), \
13920 X(vselge, 0xe200a00, N_INV, N_INV), \
73924fbc
MGD
13921 X(vselgt, 0xe300a00, N_INV, N_INV), \
13922 X(vmaxnm, 0xe800a00, 0x3000f10, N_INV), \
7e8e6784 13923 X(vminnm, 0xe800a40, 0x3200f10, N_INV), \
30bdf752
MGD
13924 X(vcvta, 0xebc0a40, 0x3bb0000, N_INV), \
13925 X(vrintr, 0xeb60a40, 0x3ba0400, N_INV), \
91ff7894 13926 X(vrinta, 0xeb80a40, 0x3ba0400, N_INV), \
48adcd8e 13927 X(aes, 0x3b00300, N_INV, N_INV), \
3c9017d2
MGD
13928 X(sha3op, 0x2000c00, N_INV, N_INV), \
13929 X(sha1h, 0x3b902c0, N_INV, N_INV), \
13930 X(sha2op, 0x3ba0380, N_INV, N_INV)
5287ad62
JB
13931
13932enum neon_opc
13933{
13934#define X(OPC,I,F,S) N_MNEM_##OPC
13935NEON_ENC_TAB
13936#undef X
13937};
b99bd4ef 13938
5287ad62
JB
13939static const struct neon_tab_entry neon_enc_tab[] =
13940{
13941#define X(OPC,I,F,S) { (I), (F), (S) }
13942NEON_ENC_TAB
13943#undef X
13944};
b99bd4ef 13945
88714cb8
DG
13946/* Do not use these macros; instead, use NEON_ENCODE defined below. */
13947#define NEON_ENC_INTEGER_(X) (neon_enc_tab[(X) & 0x0fffffff].integer)
13948#define NEON_ENC_ARMREG_(X) (neon_enc_tab[(X) & 0x0fffffff].integer)
13949#define NEON_ENC_POLY_(X) (neon_enc_tab[(X) & 0x0fffffff].float_or_poly)
13950#define NEON_ENC_FLOAT_(X) (neon_enc_tab[(X) & 0x0fffffff].float_or_poly)
13951#define NEON_ENC_SCALAR_(X) (neon_enc_tab[(X) & 0x0fffffff].scalar_or_imm)
13952#define NEON_ENC_IMMED_(X) (neon_enc_tab[(X) & 0x0fffffff].scalar_or_imm)
13953#define NEON_ENC_INTERLV_(X) (neon_enc_tab[(X) & 0x0fffffff].integer)
13954#define NEON_ENC_LANE_(X) (neon_enc_tab[(X) & 0x0fffffff].float_or_poly)
13955#define NEON_ENC_DUP_(X) (neon_enc_tab[(X) & 0x0fffffff].scalar_or_imm)
13956#define NEON_ENC_SINGLE_(X) \
037e8744 13957 ((neon_enc_tab[(X) & 0x0fffffff].integer) | ((X) & 0xf0000000))
88714cb8 13958#define NEON_ENC_DOUBLE_(X) \
037e8744 13959 ((neon_enc_tab[(X) & 0x0fffffff].float_or_poly) | ((X) & 0xf0000000))
33399f07
MGD
13960#define NEON_ENC_FPV8_(X) \
13961 ((neon_enc_tab[(X) & 0x0fffffff].integer) | ((X) & 0xf000000))
5287ad62 13962
88714cb8
DG
13963#define NEON_ENCODE(type, inst) \
13964 do \
13965 { \
13966 inst.instruction = NEON_ENC_##type##_ (inst.instruction); \
13967 inst.is_neon = 1; \
13968 } \
13969 while (0)
13970
13971#define check_neon_suffixes \
13972 do \
13973 { \
13974 if (!inst.error && inst.vectype.elems > 0 && !inst.is_neon) \
13975 { \
13976 as_bad (_("invalid neon suffix for non neon instruction")); \
13977 return; \
13978 } \
13979 } \
13980 while (0)
13981
037e8744
JB
13982/* Define shapes for instruction operands. The following mnemonic characters
13983 are used in this table:
5287ad62 13984
037e8744 13985 F - VFP S<n> register
5287ad62
JB
13986 D - Neon D<n> register
13987 Q - Neon Q<n> register
13988 I - Immediate
13989 S - Scalar
13990 R - ARM register
13991 L - D<n> register list
5f4273c7 13992
037e8744
JB
13993 This table is used to generate various data:
13994 - enumerations of the form NS_DDR to be used as arguments to
13995 neon_select_shape.
13996 - a table classifying shapes into single, double, quad, mixed.
5f4273c7 13997 - a table used to drive neon_select_shape. */
b99bd4ef 13998
037e8744 13999#define NEON_SHAPE_DEF \
a302e574 14000 X(3, (R, Q, Q), QUAD), \
037e8744
JB
14001 X(3, (D, D, D), DOUBLE), \
14002 X(3, (Q, Q, Q), QUAD), \
14003 X(3, (D, D, I), DOUBLE), \
14004 X(3, (Q, Q, I), QUAD), \
14005 X(3, (D, D, S), DOUBLE), \
14006 X(3, (Q, Q, S), QUAD), \
5ee91343 14007 X(3, (Q, Q, R), QUAD), \
037e8744
JB
14008 X(2, (D, D), DOUBLE), \
14009 X(2, (Q, Q), QUAD), \
14010 X(2, (D, S), DOUBLE), \
14011 X(2, (Q, S), QUAD), \
14012 X(2, (D, R), DOUBLE), \
14013 X(2, (Q, R), QUAD), \
14014 X(2, (D, I), DOUBLE), \
14015 X(2, (Q, I), QUAD), \
14016 X(3, (D, L, D), DOUBLE), \
14017 X(2, (D, Q), MIXED), \
14018 X(2, (Q, D), MIXED), \
14019 X(3, (D, Q, I), MIXED), \
14020 X(3, (Q, D, I), MIXED), \
14021 X(3, (Q, D, D), MIXED), \
14022 X(3, (D, Q, Q), MIXED), \
14023 X(3, (Q, Q, D), MIXED), \
14024 X(3, (Q, D, S), MIXED), \
14025 X(3, (D, Q, S), MIXED), \
14026 X(4, (D, D, D, I), DOUBLE), \
14027 X(4, (Q, Q, Q, I), QUAD), \
c28eeff2
SN
14028 X(4, (D, D, S, I), DOUBLE), \
14029 X(4, (Q, Q, S, I), QUAD), \
037e8744
JB
14030 X(2, (F, F), SINGLE), \
14031 X(3, (F, F, F), SINGLE), \
14032 X(2, (F, I), SINGLE), \
14033 X(2, (F, D), MIXED), \
14034 X(2, (D, F), MIXED), \
14035 X(3, (F, F, I), MIXED), \
14036 X(4, (R, R, F, F), SINGLE), \
14037 X(4, (F, F, R, R), SINGLE), \
14038 X(3, (D, R, R), DOUBLE), \
14039 X(3, (R, R, D), DOUBLE), \
14040 X(2, (S, R), SINGLE), \
14041 X(2, (R, S), SINGLE), \
14042 X(2, (F, R), SINGLE), \
d54af2d0
RL
14043 X(2, (R, F), SINGLE), \
14044/* Half float shape supported so far. */\
14045 X (2, (H, D), MIXED), \
14046 X (2, (D, H), MIXED), \
14047 X (2, (H, F), MIXED), \
14048 X (2, (F, H), MIXED), \
14049 X (2, (H, H), HALF), \
14050 X (2, (H, R), HALF), \
14051 X (2, (R, H), HALF), \
14052 X (2, (H, I), HALF), \
14053 X (3, (H, H, H), HALF), \
14054 X (3, (H, F, I), MIXED), \
dec41383
JW
14055 X (3, (F, H, I), MIXED), \
14056 X (3, (D, H, H), MIXED), \
14057 X (3, (D, H, S), MIXED)
037e8744
JB
14058
14059#define S2(A,B) NS_##A##B
14060#define S3(A,B,C) NS_##A##B##C
14061#define S4(A,B,C,D) NS_##A##B##C##D
14062
14063#define X(N, L, C) S##N L
14064
5287ad62
JB
14065enum neon_shape
14066{
037e8744
JB
14067 NEON_SHAPE_DEF,
14068 NS_NULL
5287ad62 14069};
b99bd4ef 14070
037e8744
JB
14071#undef X
14072#undef S2
14073#undef S3
14074#undef S4
14075
14076enum neon_shape_class
14077{
d54af2d0 14078 SC_HALF,
037e8744
JB
14079 SC_SINGLE,
14080 SC_DOUBLE,
14081 SC_QUAD,
14082 SC_MIXED
14083};
14084
14085#define X(N, L, C) SC_##C
14086
14087static enum neon_shape_class neon_shape_class[] =
14088{
14089 NEON_SHAPE_DEF
14090};
14091
14092#undef X
14093
14094enum neon_shape_el
14095{
d54af2d0 14096 SE_H,
037e8744
JB
14097 SE_F,
14098 SE_D,
14099 SE_Q,
14100 SE_I,
14101 SE_S,
14102 SE_R,
14103 SE_L
14104};
14105
14106/* Register widths of above. */
14107static unsigned neon_shape_el_size[] =
14108{
d54af2d0 14109 16,
037e8744
JB
14110 32,
14111 64,
14112 128,
14113 0,
14114 32,
14115 32,
14116 0
14117};
14118
14119struct neon_shape_info
14120{
14121 unsigned els;
14122 enum neon_shape_el el[NEON_MAX_TYPE_ELS];
14123};
14124
14125#define S2(A,B) { SE_##A, SE_##B }
14126#define S3(A,B,C) { SE_##A, SE_##B, SE_##C }
14127#define S4(A,B,C,D) { SE_##A, SE_##B, SE_##C, SE_##D }
14128
14129#define X(N, L, C) { N, S##N L }
14130
14131static struct neon_shape_info neon_shape_tab[] =
14132{
14133 NEON_SHAPE_DEF
14134};
14135
14136#undef X
14137#undef S2
14138#undef S3
14139#undef S4
14140
5287ad62
JB
14141/* Bit masks used in type checking given instructions.
14142 'N_EQK' means the type must be the same as (or based on in some way) the key
14143 type, which itself is marked with the 'N_KEY' bit. If the 'N_EQK' bit is
14144 set, various other bits can be set as well in order to modify the meaning of
14145 the type constraint. */
14146
14147enum neon_type_mask
14148{
8e79c3df
CM
14149 N_S8 = 0x0000001,
14150 N_S16 = 0x0000002,
14151 N_S32 = 0x0000004,
14152 N_S64 = 0x0000008,
14153 N_U8 = 0x0000010,
14154 N_U16 = 0x0000020,
14155 N_U32 = 0x0000040,
14156 N_U64 = 0x0000080,
14157 N_I8 = 0x0000100,
14158 N_I16 = 0x0000200,
14159 N_I32 = 0x0000400,
14160 N_I64 = 0x0000800,
14161 N_8 = 0x0001000,
14162 N_16 = 0x0002000,
14163 N_32 = 0x0004000,
14164 N_64 = 0x0008000,
14165 N_P8 = 0x0010000,
14166 N_P16 = 0x0020000,
14167 N_F16 = 0x0040000,
14168 N_F32 = 0x0080000,
14169 N_F64 = 0x0100000,
4f51b4bd 14170 N_P64 = 0x0200000,
c921be7d
NC
14171 N_KEY = 0x1000000, /* Key element (main type specifier). */
14172 N_EQK = 0x2000000, /* Given operand has the same type & size as the key. */
8e79c3df 14173 N_VFP = 0x4000000, /* VFP mode: operand size must match register width. */
91ff7894 14174 N_UNT = 0x8000000, /* Must be explicitly untyped. */
c921be7d
NC
14175 N_DBL = 0x0000001, /* If N_EQK, this operand is twice the size. */
14176 N_HLF = 0x0000002, /* If N_EQK, this operand is half the size. */
14177 N_SGN = 0x0000004, /* If N_EQK, this operand is forced to be signed. */
14178 N_UNS = 0x0000008, /* If N_EQK, this operand is forced to be unsigned. */
14179 N_INT = 0x0000010, /* If N_EQK, this operand is forced to be integer. */
14180 N_FLT = 0x0000020, /* If N_EQK, this operand is forced to be float. */
14181 N_SIZ = 0x0000040, /* If N_EQK, this operand is forced to be size-only. */
5287ad62 14182 N_UTYP = 0,
4f51b4bd 14183 N_MAX_NONSPECIAL = N_P64
5287ad62
JB
14184};
14185
dcbf9037
JB
14186#define N_ALLMODS (N_DBL | N_HLF | N_SGN | N_UNS | N_INT | N_FLT | N_SIZ)
14187
5287ad62
JB
14188#define N_SU_ALL (N_S8 | N_S16 | N_S32 | N_S64 | N_U8 | N_U16 | N_U32 | N_U64)
14189#define N_SU_32 (N_S8 | N_S16 | N_S32 | N_U8 | N_U16 | N_U32)
14190#define N_SU_16_64 (N_S16 | N_S32 | N_S64 | N_U16 | N_U32 | N_U64)
cc933301
JW
14191#define N_S_32 (N_S8 | N_S16 | N_S32)
14192#define N_F_16_32 (N_F16 | N_F32)
14193#define N_SUF_32 (N_SU_32 | N_F_16_32)
5287ad62 14194#define N_I_ALL (N_I8 | N_I16 | N_I32 | N_I64)
cc933301 14195#define N_IF_32 (N_I8 | N_I16 | N_I32 | N_F16 | N_F32)
d54af2d0 14196#define N_F_ALL (N_F16 | N_F32 | N_F64)
5ee91343
AV
14197#define N_I_MVE (N_I8 | N_I16 | N_I32)
14198#define N_F_MVE (N_F16 | N_F32)
14199#define N_SU_MVE (N_S8 | N_S16 | N_S32 | N_U8 | N_U16 | N_U32)
5287ad62
JB
14200
14201/* Pass this as the first type argument to neon_check_type to ignore types
14202 altogether. */
14203#define N_IGNORE_TYPE (N_KEY | N_EQK)
14204
037e8744
JB
14205/* Select a "shape" for the current instruction (describing register types or
14206 sizes) from a list of alternatives. Return NS_NULL if the current instruction
14207 doesn't fit. For non-polymorphic shapes, checking is usually done as a
14208 function of operand parsing, so this function doesn't need to be called.
14209 Shapes should be listed in order of decreasing length. */
5287ad62
JB
14210
14211static enum neon_shape
037e8744 14212neon_select_shape (enum neon_shape shape, ...)
5287ad62 14213{
037e8744
JB
14214 va_list ap;
14215 enum neon_shape first_shape = shape;
5287ad62
JB
14216
14217 /* Fix missing optional operands. FIXME: we don't know at this point how
14218 many arguments we should have, so this makes the assumption that we have
14219 > 1. This is true of all current Neon opcodes, I think, but may not be
14220 true in the future. */
14221 if (!inst.operands[1].present)
14222 inst.operands[1] = inst.operands[0];
14223
037e8744 14224 va_start (ap, shape);
5f4273c7 14225
21d799b5 14226 for (; shape != NS_NULL; shape = (enum neon_shape) va_arg (ap, int))
037e8744
JB
14227 {
14228 unsigned j;
14229 int matches = 1;
14230
14231 for (j = 0; j < neon_shape_tab[shape].els; j++)
477330fc
RM
14232 {
14233 if (!inst.operands[j].present)
14234 {
14235 matches = 0;
14236 break;
14237 }
14238
14239 switch (neon_shape_tab[shape].el[j])
14240 {
d54af2d0
RL
14241 /* If a .f16, .16, .u16, .s16 type specifier is given over
14242 a VFP single precision register operand, it's essentially
14243 means only half of the register is used.
14244
14245 If the type specifier is given after the mnemonics, the
14246 information is stored in inst.vectype. If the type specifier
14247 is given after register operand, the information is stored
14248 in inst.operands[].vectype.
14249
14250 When there is only one type specifier, and all the register
14251 operands are the same type of hardware register, the type
14252 specifier applies to all register operands.
14253
14254 If no type specifier is given, the shape is inferred from
14255 operand information.
14256
14257 for example:
14258 vadd.f16 s0, s1, s2: NS_HHH
14259 vabs.f16 s0, s1: NS_HH
14260 vmov.f16 s0, r1: NS_HR
14261 vmov.f16 r0, s1: NS_RH
14262 vcvt.f16 r0, s1: NS_RH
14263 vcvt.f16.s32 s2, s2, #29: NS_HFI
14264 vcvt.f16.s32 s2, s2: NS_HF
14265 */
14266 case SE_H:
14267 if (!(inst.operands[j].isreg
14268 && inst.operands[j].isvec
14269 && inst.operands[j].issingle
14270 && !inst.operands[j].isquad
14271 && ((inst.vectype.elems == 1
14272 && inst.vectype.el[0].size == 16)
14273 || (inst.vectype.elems > 1
14274 && inst.vectype.el[j].size == 16)
14275 || (inst.vectype.elems == 0
14276 && inst.operands[j].vectype.type != NT_invtype
14277 && inst.operands[j].vectype.size == 16))))
14278 matches = 0;
14279 break;
14280
477330fc
RM
14281 case SE_F:
14282 if (!(inst.operands[j].isreg
14283 && inst.operands[j].isvec
14284 && inst.operands[j].issingle
d54af2d0
RL
14285 && !inst.operands[j].isquad
14286 && ((inst.vectype.elems == 1 && inst.vectype.el[0].size == 32)
14287 || (inst.vectype.elems > 1 && inst.vectype.el[j].size == 32)
14288 || (inst.vectype.elems == 0
14289 && (inst.operands[j].vectype.size == 32
14290 || inst.operands[j].vectype.type == NT_invtype)))))
477330fc
RM
14291 matches = 0;
14292 break;
14293
14294 case SE_D:
14295 if (!(inst.operands[j].isreg
14296 && inst.operands[j].isvec
14297 && !inst.operands[j].isquad
14298 && !inst.operands[j].issingle))
14299 matches = 0;
14300 break;
14301
14302 case SE_R:
14303 if (!(inst.operands[j].isreg
14304 && !inst.operands[j].isvec))
14305 matches = 0;
14306 break;
14307
14308 case SE_Q:
14309 if (!(inst.operands[j].isreg
14310 && inst.operands[j].isvec
14311 && inst.operands[j].isquad
14312 && !inst.operands[j].issingle))
14313 matches = 0;
14314 break;
14315
14316 case SE_I:
14317 if (!(!inst.operands[j].isreg
14318 && !inst.operands[j].isscalar))
14319 matches = 0;
14320 break;
14321
14322 case SE_S:
14323 if (!(!inst.operands[j].isreg
14324 && inst.operands[j].isscalar))
14325 matches = 0;
14326 break;
14327
14328 case SE_L:
14329 break;
14330 }
3fde54a2
JZ
14331 if (!matches)
14332 break;
477330fc 14333 }
ad6cec43
MGD
14334 if (matches && (j >= ARM_IT_MAX_OPERANDS || !inst.operands[j].present))
14335 /* We've matched all the entries in the shape table, and we don't
14336 have any left over operands which have not been matched. */
477330fc 14337 break;
037e8744 14338 }
5f4273c7 14339
037e8744 14340 va_end (ap);
5287ad62 14341
037e8744
JB
14342 if (shape == NS_NULL && first_shape != NS_NULL)
14343 first_error (_("invalid instruction shape"));
5287ad62 14344
037e8744
JB
14345 return shape;
14346}
5287ad62 14347
037e8744
JB
14348/* True if SHAPE is predominantly a quadword operation (most of the time, this
14349 means the Q bit should be set). */
14350
14351static int
14352neon_quad (enum neon_shape shape)
14353{
14354 return neon_shape_class[shape] == SC_QUAD;
5287ad62 14355}
037e8744 14356
5287ad62
JB
14357static void
14358neon_modify_type_size (unsigned typebits, enum neon_el_type *g_type,
477330fc 14359 unsigned *g_size)
5287ad62
JB
14360{
14361 /* Allow modification to be made to types which are constrained to be
14362 based on the key element, based on bits set alongside N_EQK. */
14363 if ((typebits & N_EQK) != 0)
14364 {
14365 if ((typebits & N_HLF) != 0)
14366 *g_size /= 2;
14367 else if ((typebits & N_DBL) != 0)
14368 *g_size *= 2;
14369 if ((typebits & N_SGN) != 0)
14370 *g_type = NT_signed;
14371 else if ((typebits & N_UNS) != 0)
477330fc 14372 *g_type = NT_unsigned;
5287ad62 14373 else if ((typebits & N_INT) != 0)
477330fc 14374 *g_type = NT_integer;
5287ad62 14375 else if ((typebits & N_FLT) != 0)
477330fc 14376 *g_type = NT_float;
dcbf9037 14377 else if ((typebits & N_SIZ) != 0)
477330fc 14378 *g_type = NT_untyped;
5287ad62
JB
14379 }
14380}
5f4273c7 14381
5287ad62
JB
14382/* Return operand OPNO promoted by bits set in THISARG. KEY should be the "key"
14383 operand type, i.e. the single type specified in a Neon instruction when it
14384 is the only one given. */
14385
14386static struct neon_type_el
14387neon_type_promote (struct neon_type_el *key, unsigned thisarg)
14388{
14389 struct neon_type_el dest = *key;
5f4273c7 14390
9c2799c2 14391 gas_assert ((thisarg & N_EQK) != 0);
5f4273c7 14392
5287ad62
JB
14393 neon_modify_type_size (thisarg, &dest.type, &dest.size);
14394
14395 return dest;
14396}
14397
14398/* Convert Neon type and size into compact bitmask representation. */
14399
14400static enum neon_type_mask
14401type_chk_of_el_type (enum neon_el_type type, unsigned size)
14402{
14403 switch (type)
14404 {
14405 case NT_untyped:
14406 switch (size)
477330fc
RM
14407 {
14408 case 8: return N_8;
14409 case 16: return N_16;
14410 case 32: return N_32;
14411 case 64: return N_64;
14412 default: ;
14413 }
5287ad62
JB
14414 break;
14415
14416 case NT_integer:
14417 switch (size)
477330fc
RM
14418 {
14419 case 8: return N_I8;
14420 case 16: return N_I16;
14421 case 32: return N_I32;
14422 case 64: return N_I64;
14423 default: ;
14424 }
5287ad62
JB
14425 break;
14426
14427 case NT_float:
037e8744 14428 switch (size)
477330fc 14429 {
8e79c3df 14430 case 16: return N_F16;
477330fc
RM
14431 case 32: return N_F32;
14432 case 64: return N_F64;
14433 default: ;
14434 }
5287ad62
JB
14435 break;
14436
14437 case NT_poly:
14438 switch (size)
477330fc
RM
14439 {
14440 case 8: return N_P8;
14441 case 16: return N_P16;
4f51b4bd 14442 case 64: return N_P64;
477330fc
RM
14443 default: ;
14444 }
5287ad62
JB
14445 break;
14446
14447 case NT_signed:
14448 switch (size)
477330fc
RM
14449 {
14450 case 8: return N_S8;
14451 case 16: return N_S16;
14452 case 32: return N_S32;
14453 case 64: return N_S64;
14454 default: ;
14455 }
5287ad62
JB
14456 break;
14457
14458 case NT_unsigned:
14459 switch (size)
477330fc
RM
14460 {
14461 case 8: return N_U8;
14462 case 16: return N_U16;
14463 case 32: return N_U32;
14464 case 64: return N_U64;
14465 default: ;
14466 }
5287ad62
JB
14467 break;
14468
14469 default: ;
14470 }
5f4273c7 14471
5287ad62
JB
14472 return N_UTYP;
14473}
14474
14475/* Convert compact Neon bitmask type representation to a type and size. Only
14476 handles the case where a single bit is set in the mask. */
14477
dcbf9037 14478static int
5287ad62 14479el_type_of_type_chk (enum neon_el_type *type, unsigned *size,
477330fc 14480 enum neon_type_mask mask)
5287ad62 14481{
dcbf9037
JB
14482 if ((mask & N_EQK) != 0)
14483 return FAIL;
14484
5287ad62
JB
14485 if ((mask & (N_S8 | N_U8 | N_I8 | N_8 | N_P8)) != 0)
14486 *size = 8;
c70a8987 14487 else if ((mask & (N_S16 | N_U16 | N_I16 | N_16 | N_F16 | N_P16)) != 0)
5287ad62 14488 *size = 16;
dcbf9037 14489 else if ((mask & (N_S32 | N_U32 | N_I32 | N_32 | N_F32)) != 0)
5287ad62 14490 *size = 32;
4f51b4bd 14491 else if ((mask & (N_S64 | N_U64 | N_I64 | N_64 | N_F64 | N_P64)) != 0)
5287ad62 14492 *size = 64;
dcbf9037
JB
14493 else
14494 return FAIL;
14495
5287ad62
JB
14496 if ((mask & (N_S8 | N_S16 | N_S32 | N_S64)) != 0)
14497 *type = NT_signed;
dcbf9037 14498 else if ((mask & (N_U8 | N_U16 | N_U32 | N_U64)) != 0)
5287ad62 14499 *type = NT_unsigned;
dcbf9037 14500 else if ((mask & (N_I8 | N_I16 | N_I32 | N_I64)) != 0)
5287ad62 14501 *type = NT_integer;
dcbf9037 14502 else if ((mask & (N_8 | N_16 | N_32 | N_64)) != 0)
5287ad62 14503 *type = NT_untyped;
4f51b4bd 14504 else if ((mask & (N_P8 | N_P16 | N_P64)) != 0)
5287ad62 14505 *type = NT_poly;
d54af2d0 14506 else if ((mask & (N_F_ALL)) != 0)
5287ad62 14507 *type = NT_float;
dcbf9037
JB
14508 else
14509 return FAIL;
5f4273c7 14510
dcbf9037 14511 return SUCCESS;
5287ad62
JB
14512}
14513
14514/* Modify a bitmask of allowed types. This is only needed for type
14515 relaxation. */
14516
14517static unsigned
14518modify_types_allowed (unsigned allowed, unsigned mods)
14519{
14520 unsigned size;
14521 enum neon_el_type type;
14522 unsigned destmask;
14523 int i;
5f4273c7 14524
5287ad62 14525 destmask = 0;
5f4273c7 14526
5287ad62
JB
14527 for (i = 1; i <= N_MAX_NONSPECIAL; i <<= 1)
14528 {
21d799b5 14529 if (el_type_of_type_chk (&type, &size,
477330fc
RM
14530 (enum neon_type_mask) (allowed & i)) == SUCCESS)
14531 {
14532 neon_modify_type_size (mods, &type, &size);
14533 destmask |= type_chk_of_el_type (type, size);
14534 }
5287ad62 14535 }
5f4273c7 14536
5287ad62
JB
14537 return destmask;
14538}
14539
14540/* Check type and return type classification.
14541 The manual states (paraphrase): If one datatype is given, it indicates the
14542 type given in:
14543 - the second operand, if there is one
14544 - the operand, if there is no second operand
14545 - the result, if there are no operands.
14546 This isn't quite good enough though, so we use a concept of a "key" datatype
14547 which is set on a per-instruction basis, which is the one which matters when
14548 only one data type is written.
14549 Note: this function has side-effects (e.g. filling in missing operands). All
037e8744 14550 Neon instructions should call it before performing bit encoding. */
5287ad62
JB
14551
14552static struct neon_type_el
14553neon_check_type (unsigned els, enum neon_shape ns, ...)
14554{
14555 va_list ap;
14556 unsigned i, pass, key_el = 0;
14557 unsigned types[NEON_MAX_TYPE_ELS];
14558 enum neon_el_type k_type = NT_invtype;
14559 unsigned k_size = -1u;
14560 struct neon_type_el badtype = {NT_invtype, -1};
14561 unsigned key_allowed = 0;
14562
14563 /* Optional registers in Neon instructions are always (not) in operand 1.
14564 Fill in the missing operand here, if it was omitted. */
14565 if (els > 1 && !inst.operands[1].present)
14566 inst.operands[1] = inst.operands[0];
14567
14568 /* Suck up all the varargs. */
14569 va_start (ap, ns);
14570 for (i = 0; i < els; i++)
14571 {
14572 unsigned thisarg = va_arg (ap, unsigned);
14573 if (thisarg == N_IGNORE_TYPE)
477330fc
RM
14574 {
14575 va_end (ap);
14576 return badtype;
14577 }
5287ad62
JB
14578 types[i] = thisarg;
14579 if ((thisarg & N_KEY) != 0)
477330fc 14580 key_el = i;
5287ad62
JB
14581 }
14582 va_end (ap);
14583
dcbf9037
JB
14584 if (inst.vectype.elems > 0)
14585 for (i = 0; i < els; i++)
14586 if (inst.operands[i].vectype.type != NT_invtype)
477330fc
RM
14587 {
14588 first_error (_("types specified in both the mnemonic and operands"));
14589 return badtype;
14590 }
dcbf9037 14591
5287ad62
JB
14592 /* Duplicate inst.vectype elements here as necessary.
14593 FIXME: No idea if this is exactly the same as the ARM assembler,
14594 particularly when an insn takes one register and one non-register
14595 operand. */
14596 if (inst.vectype.elems == 1 && els > 1)
14597 {
14598 unsigned j;
14599 inst.vectype.elems = els;
14600 inst.vectype.el[key_el] = inst.vectype.el[0];
14601 for (j = 0; j < els; j++)
477330fc
RM
14602 if (j != key_el)
14603 inst.vectype.el[j] = neon_type_promote (&inst.vectype.el[key_el],
14604 types[j]);
dcbf9037
JB
14605 }
14606 else if (inst.vectype.elems == 0 && els > 0)
14607 {
14608 unsigned j;
14609 /* No types were given after the mnemonic, so look for types specified
477330fc
RM
14610 after each operand. We allow some flexibility here; as long as the
14611 "key" operand has a type, we can infer the others. */
dcbf9037 14612 for (j = 0; j < els; j++)
477330fc
RM
14613 if (inst.operands[j].vectype.type != NT_invtype)
14614 inst.vectype.el[j] = inst.operands[j].vectype;
dcbf9037
JB
14615
14616 if (inst.operands[key_el].vectype.type != NT_invtype)
477330fc
RM
14617 {
14618 for (j = 0; j < els; j++)
14619 if (inst.operands[j].vectype.type == NT_invtype)
14620 inst.vectype.el[j] = neon_type_promote (&inst.vectype.el[key_el],
14621 types[j]);
14622 }
dcbf9037 14623 else
477330fc
RM
14624 {
14625 first_error (_("operand types can't be inferred"));
14626 return badtype;
14627 }
5287ad62
JB
14628 }
14629 else if (inst.vectype.elems != els)
14630 {
dcbf9037 14631 first_error (_("type specifier has the wrong number of parts"));
5287ad62
JB
14632 return badtype;
14633 }
14634
14635 for (pass = 0; pass < 2; pass++)
14636 {
14637 for (i = 0; i < els; i++)
477330fc
RM
14638 {
14639 unsigned thisarg = types[i];
14640 unsigned types_allowed = ((thisarg & N_EQK) != 0 && pass != 0)
14641 ? modify_types_allowed (key_allowed, thisarg) : thisarg;
14642 enum neon_el_type g_type = inst.vectype.el[i].type;
14643 unsigned g_size = inst.vectype.el[i].size;
14644
14645 /* Decay more-specific signed & unsigned types to sign-insensitive
5287ad62 14646 integer types if sign-specific variants are unavailable. */
477330fc 14647 if ((g_type == NT_signed || g_type == NT_unsigned)
5287ad62
JB
14648 && (types_allowed & N_SU_ALL) == 0)
14649 g_type = NT_integer;
14650
477330fc 14651 /* If only untyped args are allowed, decay any more specific types to
5287ad62
JB
14652 them. Some instructions only care about signs for some element
14653 sizes, so handle that properly. */
477330fc 14654 if (((types_allowed & N_UNT) == 0)
91ff7894
MGD
14655 && ((g_size == 8 && (types_allowed & N_8) != 0)
14656 || (g_size == 16 && (types_allowed & N_16) != 0)
14657 || (g_size == 32 && (types_allowed & N_32) != 0)
14658 || (g_size == 64 && (types_allowed & N_64) != 0)))
5287ad62
JB
14659 g_type = NT_untyped;
14660
477330fc
RM
14661 if (pass == 0)
14662 {
14663 if ((thisarg & N_KEY) != 0)
14664 {
14665 k_type = g_type;
14666 k_size = g_size;
14667 key_allowed = thisarg & ~N_KEY;
cc933301
JW
14668
14669 /* Check architecture constraint on FP16 extension. */
14670 if (k_size == 16
14671 && k_type == NT_float
14672 && ! ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_fp16))
14673 {
14674 inst.error = _(BAD_FP16);
14675 return badtype;
14676 }
477330fc
RM
14677 }
14678 }
14679 else
14680 {
14681 if ((thisarg & N_VFP) != 0)
14682 {
14683 enum neon_shape_el regshape;
14684 unsigned regwidth, match;
99b253c5
NC
14685
14686 /* PR 11136: Catch the case where we are passed a shape of NS_NULL. */
14687 if (ns == NS_NULL)
14688 {
14689 first_error (_("invalid instruction shape"));
14690 return badtype;
14691 }
477330fc
RM
14692 regshape = neon_shape_tab[ns].el[i];
14693 regwidth = neon_shape_el_size[regshape];
14694
14695 /* In VFP mode, operands must match register widths. If we
14696 have a key operand, use its width, else use the width of
14697 the current operand. */
14698 if (k_size != -1u)
14699 match = k_size;
14700 else
14701 match = g_size;
14702
9db2f6b4
RL
14703 /* FP16 will use a single precision register. */
14704 if (regwidth == 32 && match == 16)
14705 {
14706 if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_fp16))
14707 match = regwidth;
14708 else
14709 {
14710 inst.error = _(BAD_FP16);
14711 return badtype;
14712 }
14713 }
14714
477330fc
RM
14715 if (regwidth != match)
14716 {
14717 first_error (_("operand size must match register width"));
14718 return badtype;
14719 }
14720 }
14721
14722 if ((thisarg & N_EQK) == 0)
14723 {
14724 unsigned given_type = type_chk_of_el_type (g_type, g_size);
14725
14726 if ((given_type & types_allowed) == 0)
14727 {
a302e574 14728 first_error (BAD_SIMD_TYPE);
477330fc
RM
14729 return badtype;
14730 }
14731 }
14732 else
14733 {
14734 enum neon_el_type mod_k_type = k_type;
14735 unsigned mod_k_size = k_size;
14736 neon_modify_type_size (thisarg, &mod_k_type, &mod_k_size);
14737 if (g_type != mod_k_type || g_size != mod_k_size)
14738 {
14739 first_error (_("inconsistent types in Neon instruction"));
14740 return badtype;
14741 }
14742 }
14743 }
14744 }
5287ad62
JB
14745 }
14746
14747 return inst.vectype.el[key_el];
14748}
14749
037e8744 14750/* Neon-style VFP instruction forwarding. */
5287ad62 14751
037e8744
JB
14752/* Thumb VFP instructions have 0xE in the condition field. */
14753
14754static void
14755do_vfp_cond_or_thumb (void)
5287ad62 14756{
88714cb8
DG
14757 inst.is_neon = 1;
14758
5287ad62 14759 if (thumb_mode)
037e8744 14760 inst.instruction |= 0xe0000000;
5287ad62 14761 else
037e8744 14762 inst.instruction |= inst.cond << 28;
5287ad62
JB
14763}
14764
037e8744
JB
14765/* Look up and encode a simple mnemonic, for use as a helper function for the
14766 Neon-style VFP syntax. This avoids duplication of bits of the insns table,
14767 etc. It is assumed that operand parsing has already been done, and that the
14768 operands are in the form expected by the given opcode (this isn't necessarily
14769 the same as the form in which they were parsed, hence some massaging must
14770 take place before this function is called).
14771 Checks current arch version against that in the looked-up opcode. */
5287ad62 14772
037e8744
JB
14773static void
14774do_vfp_nsyn_opcode (const char *opname)
5287ad62 14775{
037e8744 14776 const struct asm_opcode *opcode;
5f4273c7 14777
21d799b5 14778 opcode = (const struct asm_opcode *) hash_find (arm_ops_hsh, opname);
5287ad62 14779
037e8744
JB
14780 if (!opcode)
14781 abort ();
5287ad62 14782
037e8744 14783 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant,
477330fc
RM
14784 thumb_mode ? *opcode->tvariant : *opcode->avariant),
14785 _(BAD_FPU));
5287ad62 14786
88714cb8
DG
14787 inst.is_neon = 1;
14788
037e8744
JB
14789 if (thumb_mode)
14790 {
14791 inst.instruction = opcode->tvalue;
14792 opcode->tencode ();
14793 }
14794 else
14795 {
14796 inst.instruction = (inst.cond << 28) | opcode->avalue;
14797 opcode->aencode ();
14798 }
14799}
5287ad62
JB
14800
14801static void
037e8744 14802do_vfp_nsyn_add_sub (enum neon_shape rs)
5287ad62 14803{
037e8744
JB
14804 int is_add = (inst.instruction & 0x0fffffff) == N_MNEM_vadd;
14805
9db2f6b4 14806 if (rs == NS_FFF || rs == NS_HHH)
037e8744
JB
14807 {
14808 if (is_add)
477330fc 14809 do_vfp_nsyn_opcode ("fadds");
037e8744 14810 else
477330fc 14811 do_vfp_nsyn_opcode ("fsubs");
9db2f6b4
RL
14812
14813 /* ARMv8.2 fp16 instruction. */
14814 if (rs == NS_HHH)
14815 do_scalar_fp16_v82_encode ();
037e8744
JB
14816 }
14817 else
14818 {
14819 if (is_add)
477330fc 14820 do_vfp_nsyn_opcode ("faddd");
037e8744 14821 else
477330fc 14822 do_vfp_nsyn_opcode ("fsubd");
037e8744
JB
14823 }
14824}
14825
14826/* Check operand types to see if this is a VFP instruction, and if so call
14827 PFN (). */
14828
14829static int
14830try_vfp_nsyn (int args, void (*pfn) (enum neon_shape))
14831{
14832 enum neon_shape rs;
14833 struct neon_type_el et;
14834
14835 switch (args)
14836 {
14837 case 2:
9db2f6b4
RL
14838 rs = neon_select_shape (NS_HH, NS_FF, NS_DD, NS_NULL);
14839 et = neon_check_type (2, rs, N_EQK | N_VFP, N_F_ALL | N_KEY | N_VFP);
037e8744 14840 break;
5f4273c7 14841
037e8744 14842 case 3:
9db2f6b4
RL
14843 rs = neon_select_shape (NS_HHH, NS_FFF, NS_DDD, NS_NULL);
14844 et = neon_check_type (3, rs, N_EQK | N_VFP, N_EQK | N_VFP,
14845 N_F_ALL | N_KEY | N_VFP);
037e8744
JB
14846 break;
14847
14848 default:
14849 abort ();
14850 }
14851
14852 if (et.type != NT_invtype)
14853 {
14854 pfn (rs);
14855 return SUCCESS;
14856 }
037e8744 14857
99b253c5 14858 inst.error = NULL;
037e8744
JB
14859 return FAIL;
14860}
14861
14862static void
14863do_vfp_nsyn_mla_mls (enum neon_shape rs)
14864{
14865 int is_mla = (inst.instruction & 0x0fffffff) == N_MNEM_vmla;
5f4273c7 14866
9db2f6b4 14867 if (rs == NS_FFF || rs == NS_HHH)
037e8744
JB
14868 {
14869 if (is_mla)
477330fc 14870 do_vfp_nsyn_opcode ("fmacs");
037e8744 14871 else
477330fc 14872 do_vfp_nsyn_opcode ("fnmacs");
9db2f6b4
RL
14873
14874 /* ARMv8.2 fp16 instruction. */
14875 if (rs == NS_HHH)
14876 do_scalar_fp16_v82_encode ();
037e8744
JB
14877 }
14878 else
14879 {
14880 if (is_mla)
477330fc 14881 do_vfp_nsyn_opcode ("fmacd");
037e8744 14882 else
477330fc 14883 do_vfp_nsyn_opcode ("fnmacd");
037e8744
JB
14884 }
14885}
14886
62f3b8c8
PB
14887static void
14888do_vfp_nsyn_fma_fms (enum neon_shape rs)
14889{
14890 int is_fma = (inst.instruction & 0x0fffffff) == N_MNEM_vfma;
14891
9db2f6b4 14892 if (rs == NS_FFF || rs == NS_HHH)
62f3b8c8
PB
14893 {
14894 if (is_fma)
477330fc 14895 do_vfp_nsyn_opcode ("ffmas");
62f3b8c8 14896 else
477330fc 14897 do_vfp_nsyn_opcode ("ffnmas");
9db2f6b4
RL
14898
14899 /* ARMv8.2 fp16 instruction. */
14900 if (rs == NS_HHH)
14901 do_scalar_fp16_v82_encode ();
62f3b8c8
PB
14902 }
14903 else
14904 {
14905 if (is_fma)
477330fc 14906 do_vfp_nsyn_opcode ("ffmad");
62f3b8c8 14907 else
477330fc 14908 do_vfp_nsyn_opcode ("ffnmad");
62f3b8c8
PB
14909 }
14910}
14911
037e8744
JB
14912static void
14913do_vfp_nsyn_mul (enum neon_shape rs)
14914{
9db2f6b4
RL
14915 if (rs == NS_FFF || rs == NS_HHH)
14916 {
14917 do_vfp_nsyn_opcode ("fmuls");
14918
14919 /* ARMv8.2 fp16 instruction. */
14920 if (rs == NS_HHH)
14921 do_scalar_fp16_v82_encode ();
14922 }
037e8744
JB
14923 else
14924 do_vfp_nsyn_opcode ("fmuld");
14925}
14926
14927static void
14928do_vfp_nsyn_abs_neg (enum neon_shape rs)
14929{
14930 int is_neg = (inst.instruction & 0x80) != 0;
9db2f6b4 14931 neon_check_type (2, rs, N_EQK | N_VFP, N_F_ALL | N_VFP | N_KEY);
037e8744 14932
9db2f6b4 14933 if (rs == NS_FF || rs == NS_HH)
037e8744
JB
14934 {
14935 if (is_neg)
477330fc 14936 do_vfp_nsyn_opcode ("fnegs");
037e8744 14937 else
477330fc 14938 do_vfp_nsyn_opcode ("fabss");
9db2f6b4
RL
14939
14940 /* ARMv8.2 fp16 instruction. */
14941 if (rs == NS_HH)
14942 do_scalar_fp16_v82_encode ();
037e8744
JB
14943 }
14944 else
14945 {
14946 if (is_neg)
477330fc 14947 do_vfp_nsyn_opcode ("fnegd");
037e8744 14948 else
477330fc 14949 do_vfp_nsyn_opcode ("fabsd");
037e8744
JB
14950 }
14951}
14952
14953/* Encode single-precision (only!) VFP fldm/fstm instructions. Double precision
14954 insns belong to Neon, and are handled elsewhere. */
14955
14956static void
14957do_vfp_nsyn_ldm_stm (int is_dbmode)
14958{
14959 int is_ldm = (inst.instruction & (1 << 20)) != 0;
14960 if (is_ldm)
14961 {
14962 if (is_dbmode)
477330fc 14963 do_vfp_nsyn_opcode ("fldmdbs");
037e8744 14964 else
477330fc 14965 do_vfp_nsyn_opcode ("fldmias");
037e8744
JB
14966 }
14967 else
14968 {
14969 if (is_dbmode)
477330fc 14970 do_vfp_nsyn_opcode ("fstmdbs");
037e8744 14971 else
477330fc 14972 do_vfp_nsyn_opcode ("fstmias");
037e8744
JB
14973 }
14974}
14975
037e8744
JB
14976static void
14977do_vfp_nsyn_sqrt (void)
14978{
9db2f6b4
RL
14979 enum neon_shape rs = neon_select_shape (NS_HH, NS_FF, NS_DD, NS_NULL);
14980 neon_check_type (2, rs, N_EQK | N_VFP, N_F_ALL | N_KEY | N_VFP);
5f4273c7 14981
9db2f6b4
RL
14982 if (rs == NS_FF || rs == NS_HH)
14983 {
14984 do_vfp_nsyn_opcode ("fsqrts");
14985
14986 /* ARMv8.2 fp16 instruction. */
14987 if (rs == NS_HH)
14988 do_scalar_fp16_v82_encode ();
14989 }
037e8744
JB
14990 else
14991 do_vfp_nsyn_opcode ("fsqrtd");
14992}
14993
14994static void
14995do_vfp_nsyn_div (void)
14996{
9db2f6b4 14997 enum neon_shape rs = neon_select_shape (NS_HHH, NS_FFF, NS_DDD, NS_NULL);
037e8744 14998 neon_check_type (3, rs, N_EQK | N_VFP, N_EQK | N_VFP,
9db2f6b4 14999 N_F_ALL | N_KEY | N_VFP);
5f4273c7 15000
9db2f6b4
RL
15001 if (rs == NS_FFF || rs == NS_HHH)
15002 {
15003 do_vfp_nsyn_opcode ("fdivs");
15004
15005 /* ARMv8.2 fp16 instruction. */
15006 if (rs == NS_HHH)
15007 do_scalar_fp16_v82_encode ();
15008 }
037e8744
JB
15009 else
15010 do_vfp_nsyn_opcode ("fdivd");
15011}
15012
15013static void
15014do_vfp_nsyn_nmul (void)
15015{
9db2f6b4 15016 enum neon_shape rs = neon_select_shape (NS_HHH, NS_FFF, NS_DDD, NS_NULL);
037e8744 15017 neon_check_type (3, rs, N_EQK | N_VFP, N_EQK | N_VFP,
9db2f6b4 15018 N_F_ALL | N_KEY | N_VFP);
5f4273c7 15019
9db2f6b4 15020 if (rs == NS_FFF || rs == NS_HHH)
037e8744 15021 {
88714cb8 15022 NEON_ENCODE (SINGLE, inst);
037e8744 15023 do_vfp_sp_dyadic ();
9db2f6b4
RL
15024
15025 /* ARMv8.2 fp16 instruction. */
15026 if (rs == NS_HHH)
15027 do_scalar_fp16_v82_encode ();
037e8744
JB
15028 }
15029 else
15030 {
88714cb8 15031 NEON_ENCODE (DOUBLE, inst);
037e8744
JB
15032 do_vfp_dp_rd_rn_rm ();
15033 }
15034 do_vfp_cond_or_thumb ();
9db2f6b4 15035
037e8744
JB
15036}
15037
15038static void
15039do_vfp_nsyn_cmp (void)
15040{
9db2f6b4 15041 enum neon_shape rs;
037e8744
JB
15042 if (inst.operands[1].isreg)
15043 {
9db2f6b4
RL
15044 rs = neon_select_shape (NS_HH, NS_FF, NS_DD, NS_NULL);
15045 neon_check_type (2, rs, N_EQK | N_VFP, N_F_ALL | N_KEY | N_VFP);
5f4273c7 15046
9db2f6b4 15047 if (rs == NS_FF || rs == NS_HH)
477330fc
RM
15048 {
15049 NEON_ENCODE (SINGLE, inst);
15050 do_vfp_sp_monadic ();
15051 }
037e8744 15052 else
477330fc
RM
15053 {
15054 NEON_ENCODE (DOUBLE, inst);
15055 do_vfp_dp_rd_rm ();
15056 }
037e8744
JB
15057 }
15058 else
15059 {
9db2f6b4
RL
15060 rs = neon_select_shape (NS_HI, NS_FI, NS_DI, NS_NULL);
15061 neon_check_type (2, rs, N_F_ALL | N_KEY | N_VFP, N_EQK);
037e8744
JB
15062
15063 switch (inst.instruction & 0x0fffffff)
477330fc
RM
15064 {
15065 case N_MNEM_vcmp:
15066 inst.instruction += N_MNEM_vcmpz - N_MNEM_vcmp;
15067 break;
15068 case N_MNEM_vcmpe:
15069 inst.instruction += N_MNEM_vcmpez - N_MNEM_vcmpe;
15070 break;
15071 default:
15072 abort ();
15073 }
5f4273c7 15074
9db2f6b4 15075 if (rs == NS_FI || rs == NS_HI)
477330fc
RM
15076 {
15077 NEON_ENCODE (SINGLE, inst);
15078 do_vfp_sp_compare_z ();
15079 }
037e8744 15080 else
477330fc
RM
15081 {
15082 NEON_ENCODE (DOUBLE, inst);
15083 do_vfp_dp_rd ();
15084 }
037e8744
JB
15085 }
15086 do_vfp_cond_or_thumb ();
9db2f6b4
RL
15087
15088 /* ARMv8.2 fp16 instruction. */
15089 if (rs == NS_HI || rs == NS_HH)
15090 do_scalar_fp16_v82_encode ();
037e8744
JB
15091}
15092
15093static void
15094nsyn_insert_sp (void)
15095{
15096 inst.operands[1] = inst.operands[0];
15097 memset (&inst.operands[0], '\0', sizeof (inst.operands[0]));
fdfde340 15098 inst.operands[0].reg = REG_SP;
037e8744
JB
15099 inst.operands[0].isreg = 1;
15100 inst.operands[0].writeback = 1;
15101 inst.operands[0].present = 1;
15102}
15103
15104static void
15105do_vfp_nsyn_push (void)
15106{
15107 nsyn_insert_sp ();
b126985e
NC
15108
15109 constraint (inst.operands[1].imm < 1 || inst.operands[1].imm > 16,
15110 _("register list must contain at least 1 and at most 16 "
15111 "registers"));
15112
037e8744
JB
15113 if (inst.operands[1].issingle)
15114 do_vfp_nsyn_opcode ("fstmdbs");
15115 else
15116 do_vfp_nsyn_opcode ("fstmdbd");
15117}
15118
15119static void
15120do_vfp_nsyn_pop (void)
15121{
15122 nsyn_insert_sp ();
b126985e
NC
15123
15124 constraint (inst.operands[1].imm < 1 || inst.operands[1].imm > 16,
15125 _("register list must contain at least 1 and at most 16 "
15126 "registers"));
15127
037e8744 15128 if (inst.operands[1].issingle)
22b5b651 15129 do_vfp_nsyn_opcode ("fldmias");
037e8744 15130 else
22b5b651 15131 do_vfp_nsyn_opcode ("fldmiad");
037e8744
JB
15132}
15133
15134/* Fix up Neon data-processing instructions, ORing in the correct bits for
15135 ARM mode or Thumb mode and moving the encoded bit 24 to bit 28. */
15136
88714cb8
DG
15137static void
15138neon_dp_fixup (struct arm_it* insn)
037e8744 15139{
88714cb8
DG
15140 unsigned int i = insn->instruction;
15141 insn->is_neon = 1;
15142
037e8744
JB
15143 if (thumb_mode)
15144 {
15145 /* The U bit is at bit 24 by default. Move to bit 28 in Thumb mode. */
15146 if (i & (1 << 24))
477330fc 15147 i |= 1 << 28;
5f4273c7 15148
037e8744 15149 i &= ~(1 << 24);
5f4273c7 15150
037e8744
JB
15151 i |= 0xef000000;
15152 }
15153 else
15154 i |= 0xf2000000;
5f4273c7 15155
88714cb8 15156 insn->instruction = i;
037e8744
JB
15157}
15158
15159/* Turn a size (8, 16, 32, 64) into the respective bit number minus 3
15160 (0, 1, 2, 3). */
15161
15162static unsigned
15163neon_logbits (unsigned x)
15164{
15165 return ffs (x) - 4;
15166}
15167
15168#define LOW4(R) ((R) & 0xf)
15169#define HI1(R) (((R) >> 4) & 1)
15170
5ee91343
AV
15171static void
15172mve_encode_qqr (int size, int fp)
15173{
15174 if (inst.operands[2].reg == REG_SP)
15175 as_tsktsk (MVE_BAD_SP);
15176 else if (inst.operands[2].reg == REG_PC)
15177 as_tsktsk (MVE_BAD_PC);
15178
15179 if (fp)
15180 {
15181 /* vadd. */
15182 if (((unsigned)inst.instruction) == 0xd00)
15183 inst.instruction = 0xee300f40;
15184 /* vsub. */
15185 else if (((unsigned)inst.instruction) == 0x200d00)
15186 inst.instruction = 0xee301f40;
15187
15188 /* Setting size which is 1 for F16 and 0 for F32. */
15189 inst.instruction |= (size == 16) << 28;
15190 }
15191 else
15192 {
15193 /* vadd. */
15194 if (((unsigned)inst.instruction) == 0x800)
15195 inst.instruction = 0xee010f40;
15196 /* vsub. */
15197 else if (((unsigned)inst.instruction) == 0x1000800)
15198 inst.instruction = 0xee011f40;
15199 /* Setting bits for size. */
15200 inst.instruction |= neon_logbits (size) << 20;
15201 }
15202 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
15203 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
15204 inst.instruction |= LOW4 (inst.operands[1].reg) << 16;
15205 inst.instruction |= HI1 (inst.operands[1].reg) << 7;
15206 inst.instruction |= inst.operands[2].reg;
15207 inst.is_neon = 1;
15208}
15209
a302e574
AV
15210static void
15211mve_encode_rqq (unsigned bit28, unsigned size)
15212{
15213 inst.instruction |= bit28 << 28;
15214 inst.instruction |= neon_logbits (size) << 20;
15215 inst.instruction |= LOW4 (inst.operands[1].reg) << 16;
15216 inst.instruction |= inst.operands[0].reg << 12;
15217 inst.instruction |= HI1 (inst.operands[1].reg) << 7;
15218 inst.instruction |= HI1 (inst.operands[2].reg) << 5;
15219 inst.instruction |= LOW4 (inst.operands[2].reg);
15220 inst.is_neon = 1;
15221}
15222
037e8744
JB
15223/* Encode insns with bit pattern:
15224
15225 |28/24|23|22 |21 20|19 16|15 12|11 8|7|6|5|4|3 0|
15226 | U |x |D |size | Rn | Rd |x x x x|N|Q|M|x| Rm |
5f4273c7 15227
037e8744
JB
15228 SIZE is passed in bits. -1 means size field isn't changed, in case it has a
15229 different meaning for some instruction. */
15230
15231static void
15232neon_three_same (int isquad, int ubit, int size)
15233{
15234 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
15235 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
15236 inst.instruction |= LOW4 (inst.operands[1].reg) << 16;
15237 inst.instruction |= HI1 (inst.operands[1].reg) << 7;
15238 inst.instruction |= LOW4 (inst.operands[2].reg);
15239 inst.instruction |= HI1 (inst.operands[2].reg) << 5;
15240 inst.instruction |= (isquad != 0) << 6;
15241 inst.instruction |= (ubit != 0) << 24;
15242 if (size != -1)
15243 inst.instruction |= neon_logbits (size) << 20;
5f4273c7 15244
88714cb8 15245 neon_dp_fixup (&inst);
037e8744
JB
15246}
15247
15248/* Encode instructions of the form:
15249
15250 |28/24|23|22|21 20|19 18|17 16|15 12|11 7|6|5|4|3 0|
15251 | U |x |D |x x |size |x x | Rd |x x x x x|Q|M|x| Rm |
5287ad62
JB
15252
15253 Don't write size if SIZE == -1. */
15254
15255static void
15256neon_two_same (int qbit, int ubit, int size)
15257{
15258 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
15259 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
15260 inst.instruction |= LOW4 (inst.operands[1].reg);
15261 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
15262 inst.instruction |= (qbit != 0) << 6;
15263 inst.instruction |= (ubit != 0) << 24;
15264
15265 if (size != -1)
15266 inst.instruction |= neon_logbits (size) << 18;
15267
88714cb8 15268 neon_dp_fixup (&inst);
5287ad62
JB
15269}
15270
15271/* Neon instruction encoders, in approximate order of appearance. */
15272
15273static void
15274do_neon_dyadic_i_su (void)
15275{
037e8744 15276 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
5287ad62
JB
15277 struct neon_type_el et = neon_check_type (3, rs,
15278 N_EQK, N_EQK, N_SU_32 | N_KEY);
037e8744 15279 neon_three_same (neon_quad (rs), et.type == NT_unsigned, et.size);
5287ad62
JB
15280}
15281
15282static void
15283do_neon_dyadic_i64_su (void)
15284{
037e8744 15285 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
5287ad62
JB
15286 struct neon_type_el et = neon_check_type (3, rs,
15287 N_EQK, N_EQK, N_SU_ALL | N_KEY);
037e8744 15288 neon_three_same (neon_quad (rs), et.type == NT_unsigned, et.size);
5287ad62
JB
15289}
15290
15291static void
15292neon_imm_shift (int write_ubit, int uval, int isquad, struct neon_type_el et,
477330fc 15293 unsigned immbits)
5287ad62
JB
15294{
15295 unsigned size = et.size >> 3;
15296 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
15297 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
15298 inst.instruction |= LOW4 (inst.operands[1].reg);
15299 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
15300 inst.instruction |= (isquad != 0) << 6;
15301 inst.instruction |= immbits << 16;
15302 inst.instruction |= (size >> 3) << 7;
15303 inst.instruction |= (size & 0x7) << 19;
15304 if (write_ubit)
15305 inst.instruction |= (uval != 0) << 24;
15306
88714cb8 15307 neon_dp_fixup (&inst);
5287ad62
JB
15308}
15309
15310static void
15311do_neon_shl_imm (void)
15312{
15313 if (!inst.operands[2].isreg)
15314 {
037e8744 15315 enum neon_shape rs = neon_select_shape (NS_DDI, NS_QQI, NS_NULL);
5287ad62 15316 struct neon_type_el et = neon_check_type (2, rs, N_EQK, N_KEY | N_I_ALL);
cb3b1e65
JB
15317 int imm = inst.operands[2].imm;
15318
15319 constraint (imm < 0 || (unsigned)imm >= et.size,
15320 _("immediate out of range for shift"));
88714cb8 15321 NEON_ENCODE (IMMED, inst);
cb3b1e65 15322 neon_imm_shift (FALSE, 0, neon_quad (rs), et, imm);
5287ad62
JB
15323 }
15324 else
15325 {
037e8744 15326 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
5287ad62 15327 struct neon_type_el et = neon_check_type (3, rs,
477330fc 15328 N_EQK, N_SU_ALL | N_KEY, N_EQK | N_SGN);
627907b7
JB
15329 unsigned int tmp;
15330
15331 /* VSHL/VQSHL 3-register variants have syntax such as:
477330fc
RM
15332 vshl.xx Dd, Dm, Dn
15333 whereas other 3-register operations encoded by neon_three_same have
15334 syntax like:
15335 vadd.xx Dd, Dn, Dm
15336 (i.e. with Dn & Dm reversed). Swap operands[1].reg and operands[2].reg
15337 here. */
627907b7
JB
15338 tmp = inst.operands[2].reg;
15339 inst.operands[2].reg = inst.operands[1].reg;
15340 inst.operands[1].reg = tmp;
88714cb8 15341 NEON_ENCODE (INTEGER, inst);
037e8744 15342 neon_three_same (neon_quad (rs), et.type == NT_unsigned, et.size);
5287ad62
JB
15343 }
15344}
15345
15346static void
15347do_neon_qshl_imm (void)
15348{
15349 if (!inst.operands[2].isreg)
15350 {
037e8744 15351 enum neon_shape rs = neon_select_shape (NS_DDI, NS_QQI, NS_NULL);
5287ad62 15352 struct neon_type_el et = neon_check_type (2, rs, N_EQK, N_SU_ALL | N_KEY);
cb3b1e65 15353 int imm = inst.operands[2].imm;
627907b7 15354
cb3b1e65
JB
15355 constraint (imm < 0 || (unsigned)imm >= et.size,
15356 _("immediate out of range for shift"));
88714cb8 15357 NEON_ENCODE (IMMED, inst);
cb3b1e65 15358 neon_imm_shift (TRUE, et.type == NT_unsigned, neon_quad (rs), et, imm);
5287ad62
JB
15359 }
15360 else
15361 {
037e8744 15362 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
5287ad62 15363 struct neon_type_el et = neon_check_type (3, rs,
477330fc 15364 N_EQK, N_SU_ALL | N_KEY, N_EQK | N_SGN);
627907b7
JB
15365 unsigned int tmp;
15366
15367 /* See note in do_neon_shl_imm. */
15368 tmp = inst.operands[2].reg;
15369 inst.operands[2].reg = inst.operands[1].reg;
15370 inst.operands[1].reg = tmp;
88714cb8 15371 NEON_ENCODE (INTEGER, inst);
037e8744 15372 neon_three_same (neon_quad (rs), et.type == NT_unsigned, et.size);
5287ad62
JB
15373 }
15374}
15375
627907b7
JB
15376static void
15377do_neon_rshl (void)
15378{
15379 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
15380 struct neon_type_el et = neon_check_type (3, rs,
15381 N_EQK, N_EQK, N_SU_ALL | N_KEY);
15382 unsigned int tmp;
15383
15384 tmp = inst.operands[2].reg;
15385 inst.operands[2].reg = inst.operands[1].reg;
15386 inst.operands[1].reg = tmp;
15387 neon_three_same (neon_quad (rs), et.type == NT_unsigned, et.size);
15388}
15389
5287ad62
JB
15390static int
15391neon_cmode_for_logic_imm (unsigned immediate, unsigned *immbits, int size)
15392{
036dc3f7
PB
15393 /* Handle .I8 pseudo-instructions. */
15394 if (size == 8)
5287ad62 15395 {
5287ad62 15396 /* Unfortunately, this will make everything apart from zero out-of-range.
477330fc
RM
15397 FIXME is this the intended semantics? There doesn't seem much point in
15398 accepting .I8 if so. */
5287ad62
JB
15399 immediate |= immediate << 8;
15400 size = 16;
036dc3f7
PB
15401 }
15402
15403 if (size >= 32)
15404 {
15405 if (immediate == (immediate & 0x000000ff))
15406 {
15407 *immbits = immediate;
15408 return 0x1;
15409 }
15410 else if (immediate == (immediate & 0x0000ff00))
15411 {
15412 *immbits = immediate >> 8;
15413 return 0x3;
15414 }
15415 else if (immediate == (immediate & 0x00ff0000))
15416 {
15417 *immbits = immediate >> 16;
15418 return 0x5;
15419 }
15420 else if (immediate == (immediate & 0xff000000))
15421 {
15422 *immbits = immediate >> 24;
15423 return 0x7;
15424 }
15425 if ((immediate & 0xffff) != (immediate >> 16))
15426 goto bad_immediate;
15427 immediate &= 0xffff;
5287ad62
JB
15428 }
15429
15430 if (immediate == (immediate & 0x000000ff))
15431 {
15432 *immbits = immediate;
036dc3f7 15433 return 0x9;
5287ad62
JB
15434 }
15435 else if (immediate == (immediate & 0x0000ff00))
15436 {
15437 *immbits = immediate >> 8;
036dc3f7 15438 return 0xb;
5287ad62
JB
15439 }
15440
15441 bad_immediate:
dcbf9037 15442 first_error (_("immediate value out of range"));
5287ad62
JB
15443 return FAIL;
15444}
15445
5287ad62
JB
15446static void
15447do_neon_logic (void)
15448{
15449 if (inst.operands[2].present && inst.operands[2].isreg)
15450 {
037e8744 15451 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
5287ad62
JB
15452 neon_check_type (3, rs, N_IGNORE_TYPE);
15453 /* U bit and size field were set as part of the bitmask. */
88714cb8 15454 NEON_ENCODE (INTEGER, inst);
037e8744 15455 neon_three_same (neon_quad (rs), 0, -1);
5287ad62
JB
15456 }
15457 else
15458 {
4316f0d2
DG
15459 const int three_ops_form = (inst.operands[2].present
15460 && !inst.operands[2].isreg);
15461 const int immoperand = (three_ops_form ? 2 : 1);
15462 enum neon_shape rs = (three_ops_form
15463 ? neon_select_shape (NS_DDI, NS_QQI, NS_NULL)
15464 : neon_select_shape (NS_DI, NS_QI, NS_NULL));
037e8744 15465 struct neon_type_el et = neon_check_type (2, rs,
477330fc 15466 N_I8 | N_I16 | N_I32 | N_I64 | N_F32 | N_KEY, N_EQK);
21d799b5 15467 enum neon_opc opcode = (enum neon_opc) inst.instruction & 0x0fffffff;
5287ad62
JB
15468 unsigned immbits;
15469 int cmode;
5f4273c7 15470
5287ad62 15471 if (et.type == NT_invtype)
477330fc 15472 return;
5f4273c7 15473
4316f0d2
DG
15474 if (three_ops_form)
15475 constraint (inst.operands[0].reg != inst.operands[1].reg,
15476 _("first and second operands shall be the same register"));
15477
88714cb8 15478 NEON_ENCODE (IMMED, inst);
5287ad62 15479
4316f0d2 15480 immbits = inst.operands[immoperand].imm;
036dc3f7
PB
15481 if (et.size == 64)
15482 {
15483 /* .i64 is a pseudo-op, so the immediate must be a repeating
15484 pattern. */
4316f0d2
DG
15485 if (immbits != (inst.operands[immoperand].regisimm ?
15486 inst.operands[immoperand].reg : 0))
036dc3f7
PB
15487 {
15488 /* Set immbits to an invalid constant. */
15489 immbits = 0xdeadbeef;
15490 }
15491 }
15492
5287ad62 15493 switch (opcode)
477330fc
RM
15494 {
15495 case N_MNEM_vbic:
15496 cmode = neon_cmode_for_logic_imm (immbits, &immbits, et.size);
15497 break;
15498
15499 case N_MNEM_vorr:
15500 cmode = neon_cmode_for_logic_imm (immbits, &immbits, et.size);
15501 break;
15502
15503 case N_MNEM_vand:
15504 /* Pseudo-instruction for VBIC. */
15505 neon_invert_size (&immbits, 0, et.size);
15506 cmode = neon_cmode_for_logic_imm (immbits, &immbits, et.size);
15507 break;
15508
15509 case N_MNEM_vorn:
15510 /* Pseudo-instruction for VORR. */
15511 neon_invert_size (&immbits, 0, et.size);
15512 cmode = neon_cmode_for_logic_imm (immbits, &immbits, et.size);
15513 break;
15514
15515 default:
15516 abort ();
15517 }
5287ad62
JB
15518
15519 if (cmode == FAIL)
477330fc 15520 return;
5287ad62 15521
037e8744 15522 inst.instruction |= neon_quad (rs) << 6;
5287ad62
JB
15523 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
15524 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
15525 inst.instruction |= cmode << 8;
15526 neon_write_immbits (immbits);
5f4273c7 15527
88714cb8 15528 neon_dp_fixup (&inst);
5287ad62
JB
15529 }
15530}
15531
15532static void
15533do_neon_bitfield (void)
15534{
037e8744 15535 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
dcbf9037 15536 neon_check_type (3, rs, N_IGNORE_TYPE);
037e8744 15537 neon_three_same (neon_quad (rs), 0, -1);
5287ad62
JB
15538}
15539
15540static void
dcbf9037 15541neon_dyadic_misc (enum neon_el_type ubit_meaning, unsigned types,
477330fc 15542 unsigned destbits)
5287ad62 15543{
5ee91343 15544 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_QQR, NS_NULL);
dcbf9037 15545 struct neon_type_el et = neon_check_type (3, rs, N_EQK | destbits, N_EQK,
477330fc 15546 types | N_KEY);
5287ad62
JB
15547 if (et.type == NT_float)
15548 {
88714cb8 15549 NEON_ENCODE (FLOAT, inst);
5ee91343
AV
15550 if (rs == NS_QQR)
15551 mve_encode_qqr (et.size, 1);
15552 else
15553 neon_three_same (neon_quad (rs), 0, et.size == 16 ? (int) et.size : -1);
5287ad62
JB
15554 }
15555 else
15556 {
88714cb8 15557 NEON_ENCODE (INTEGER, inst);
5ee91343
AV
15558 if (rs == NS_QQR)
15559 mve_encode_qqr (et.size, 0);
15560 else
15561 neon_three_same (neon_quad (rs), et.type == ubit_meaning, et.size);
5287ad62
JB
15562 }
15563}
15564
5287ad62
JB
15565
15566static void
15567do_neon_dyadic_if_su_d (void)
15568{
15569 /* This version only allow D registers, but that constraint is enforced during
15570 operand parsing so we don't need to do anything extra here. */
dcbf9037 15571 neon_dyadic_misc (NT_unsigned, N_SUF_32, 0);
5287ad62
JB
15572}
15573
5287ad62
JB
15574static void
15575do_neon_dyadic_if_i_d (void)
15576{
428e3f1f
PB
15577 /* The "untyped" case can't happen. Do this to stop the "U" bit being
15578 affected if we specify unsigned args. */
15579 neon_dyadic_misc (NT_untyped, N_IF_32, 0);
5287ad62
JB
15580}
15581
037e8744
JB
15582enum vfp_or_neon_is_neon_bits
15583{
15584 NEON_CHECK_CC = 1,
73924fbc
MGD
15585 NEON_CHECK_ARCH = 2,
15586 NEON_CHECK_ARCH8 = 4
037e8744
JB
15587};
15588
15589/* Call this function if an instruction which may have belonged to the VFP or
15590 Neon instruction sets, but turned out to be a Neon instruction (due to the
15591 operand types involved, etc.). We have to check and/or fix-up a couple of
15592 things:
15593
15594 - Make sure the user hasn't attempted to make a Neon instruction
15595 conditional.
15596 - Alter the value in the condition code field if necessary.
15597 - Make sure that the arch supports Neon instructions.
15598
15599 Which of these operations take place depends on bits from enum
15600 vfp_or_neon_is_neon_bits.
15601
15602 WARNING: This function has side effects! If NEON_CHECK_CC is used and the
15603 current instruction's condition is COND_ALWAYS, the condition field is
15604 changed to inst.uncond_value. This is necessary because instructions shared
15605 between VFP and Neon may be conditional for the VFP variants only, and the
15606 unconditional Neon version must have, e.g., 0xF in the condition field. */
15607
15608static int
15609vfp_or_neon_is_neon (unsigned check)
15610{
15611 /* Conditions are always legal in Thumb mode (IT blocks). */
15612 if (!thumb_mode && (check & NEON_CHECK_CC))
15613 {
15614 if (inst.cond != COND_ALWAYS)
477330fc
RM
15615 {
15616 first_error (_(BAD_COND));
15617 return FAIL;
15618 }
037e8744 15619 if (inst.uncond_value != -1)
477330fc 15620 inst.instruction |= inst.uncond_value << 28;
037e8744 15621 }
5f4273c7 15622
5ee91343
AV
15623
15624 if (((check & NEON_CHECK_ARCH) && !mark_feature_used (&fpu_neon_ext_v1))
15625 || ((check & NEON_CHECK_ARCH8)
15626 && !mark_feature_used (&fpu_neon_ext_armv8)))
15627 {
15628 first_error (_(BAD_FPU));
15629 return FAIL;
15630 }
15631
15632 return SUCCESS;
15633}
15634
15635static int
15636check_simd_pred_availability (int fp, unsigned check)
15637{
15638 if (inst.cond > COND_ALWAYS)
73924fbc 15639 {
5ee91343
AV
15640 if (!ARM_CPU_HAS_FEATURE (cpu_variant, mve_ext))
15641 {
15642 inst.error = BAD_FPU;
15643 return 1;
15644 }
15645 inst.pred_insn_type = INSIDE_VPT_INSN;
73924fbc 15646 }
5ee91343 15647 else if (inst.cond < COND_ALWAYS)
037e8744 15648 {
5ee91343
AV
15649 if (ARM_CPU_HAS_FEATURE (cpu_variant, mve_ext))
15650 inst.pred_insn_type = MVE_OUTSIDE_PRED_INSN;
15651 else if (vfp_or_neon_is_neon (check) == FAIL)
15652 return 2;
037e8744 15653 }
5ee91343
AV
15654 else
15655 {
15656 if (!ARM_CPU_HAS_FEATURE (cpu_variant, fp ? mve_fp_ext : mve_ext)
15657 && vfp_or_neon_is_neon (check) == FAIL)
15658 return 3;
5f4273c7 15659
5ee91343
AV
15660 if (ARM_CPU_HAS_FEATURE (cpu_variant, mve_ext))
15661 inst.pred_insn_type = MVE_OUTSIDE_PRED_INSN;
15662 }
15663 return 0;
037e8744
JB
15664}
15665
5287ad62 15666static void
5ee91343 15667do_neon_dyadic_if_su (void)
5287ad62 15668{
5ee91343
AV
15669 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_QQR, NS_NULL);
15670 struct neon_type_el et = neon_check_type (3, rs, N_EQK , N_EQK,
15671 N_SUF_32 | N_KEY);
15672
15673 if (check_simd_pred_availability (et.type == NT_float,
15674 NEON_CHECK_ARCH | NEON_CHECK_CC))
037e8744
JB
15675 return;
15676
5ee91343
AV
15677 neon_dyadic_misc (NT_unsigned, N_SUF_32, 0);
15678}
15679
15680static void
15681do_neon_addsub_if_i (void)
15682{
15683 if (ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_v1xd)
15684 && try_vfp_nsyn (3, do_vfp_nsyn_add_sub) == SUCCESS)
037e8744
JB
15685 return;
15686
5ee91343
AV
15687 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_QQR, NS_NULL);
15688 struct neon_type_el et = neon_check_type (3, rs, N_EQK,
15689 N_EQK, N_IF_32 | N_I64 | N_KEY);
15690
15691 constraint (rs == NS_QQR && et.size == 64, BAD_FPU);
15692 /* If we are parsing Q registers and the element types match MVE, which NEON
15693 also supports, then we must check whether this is an instruction that can
15694 be used by both MVE/NEON. This distinction can be made based on whether
15695 they are predicated or not. */
15696 if ((rs == NS_QQQ || rs == NS_QQR) && et.size != 64)
15697 {
15698 if (check_simd_pred_availability (et.type == NT_float,
15699 NEON_CHECK_ARCH | NEON_CHECK_CC))
15700 return;
15701 }
15702 else
15703 {
15704 /* If they are either in a D register or are using an unsupported. */
15705 if (rs != NS_QQR
15706 && vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH) == FAIL)
15707 return;
15708 }
15709
5287ad62
JB
15710 /* The "untyped" case can't happen. Do this to stop the "U" bit being
15711 affected if we specify unsigned args. */
dcbf9037 15712 neon_dyadic_misc (NT_untyped, N_IF_32 | N_I64, 0);
5287ad62
JB
15713}
15714
15715/* Swaps operands 1 and 2. If operand 1 (optional arg) was omitted, we want the
15716 result to be:
15717 V<op> A,B (A is operand 0, B is operand 2)
15718 to mean:
15719 V<op> A,B,A
15720 not:
15721 V<op> A,B,B
15722 so handle that case specially. */
15723
15724static void
15725neon_exchange_operands (void)
15726{
5287ad62
JB
15727 if (inst.operands[1].present)
15728 {
e1fa0163
NC
15729 void *scratch = xmalloc (sizeof (inst.operands[0]));
15730
5287ad62
JB
15731 /* Swap operands[1] and operands[2]. */
15732 memcpy (scratch, &inst.operands[1], sizeof (inst.operands[0]));
15733 inst.operands[1] = inst.operands[2];
15734 memcpy (&inst.operands[2], scratch, sizeof (inst.operands[0]));
e1fa0163 15735 free (scratch);
5287ad62
JB
15736 }
15737 else
15738 {
15739 inst.operands[1] = inst.operands[2];
15740 inst.operands[2] = inst.operands[0];
15741 }
15742}
15743
15744static void
15745neon_compare (unsigned regtypes, unsigned immtypes, int invert)
15746{
15747 if (inst.operands[2].isreg)
15748 {
15749 if (invert)
477330fc 15750 neon_exchange_operands ();
dcbf9037 15751 neon_dyadic_misc (NT_unsigned, regtypes, N_SIZ);
5287ad62
JB
15752 }
15753 else
15754 {
037e8744 15755 enum neon_shape rs = neon_select_shape (NS_DDI, NS_QQI, NS_NULL);
dcbf9037 15756 struct neon_type_el et = neon_check_type (2, rs,
477330fc 15757 N_EQK | N_SIZ, immtypes | N_KEY);
5287ad62 15758
88714cb8 15759 NEON_ENCODE (IMMED, inst);
5287ad62
JB
15760 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
15761 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
15762 inst.instruction |= LOW4 (inst.operands[1].reg);
15763 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
037e8744 15764 inst.instruction |= neon_quad (rs) << 6;
5287ad62
JB
15765 inst.instruction |= (et.type == NT_float) << 10;
15766 inst.instruction |= neon_logbits (et.size) << 18;
5f4273c7 15767
88714cb8 15768 neon_dp_fixup (&inst);
5287ad62
JB
15769 }
15770}
15771
15772static void
15773do_neon_cmp (void)
15774{
cc933301 15775 neon_compare (N_SUF_32, N_S_32 | N_F_16_32, FALSE);
5287ad62
JB
15776}
15777
15778static void
15779do_neon_cmp_inv (void)
15780{
cc933301 15781 neon_compare (N_SUF_32, N_S_32 | N_F_16_32, TRUE);
5287ad62
JB
15782}
15783
15784static void
15785do_neon_ceq (void)
15786{
15787 neon_compare (N_IF_32, N_IF_32, FALSE);
15788}
15789
15790/* For multiply instructions, we have the possibility of 16-bit or 32-bit
15791 scalars, which are encoded in 5 bits, M : Rm.
15792 For 16-bit scalars, the register is encoded in Rm[2:0] and the index in
15793 M:Rm[3], and for 32-bit scalars, the register is encoded in Rm[3:0] and the
c604a79a
JW
15794 index in M.
15795
15796 Dot Product instructions are similar to multiply instructions except elsize
15797 should always be 32.
15798
15799 This function translates SCALAR, which is GAS's internal encoding of indexed
15800 scalar register, to raw encoding. There is also register and index range
15801 check based on ELSIZE. */
5287ad62
JB
15802
15803static unsigned
15804neon_scalar_for_mul (unsigned scalar, unsigned elsize)
15805{
dcbf9037
JB
15806 unsigned regno = NEON_SCALAR_REG (scalar);
15807 unsigned elno = NEON_SCALAR_INDEX (scalar);
5287ad62
JB
15808
15809 switch (elsize)
15810 {
15811 case 16:
15812 if (regno > 7 || elno > 3)
477330fc 15813 goto bad_scalar;
5287ad62 15814 return regno | (elno << 3);
5f4273c7 15815
5287ad62
JB
15816 case 32:
15817 if (regno > 15 || elno > 1)
477330fc 15818 goto bad_scalar;
5287ad62
JB
15819 return regno | (elno << 4);
15820
15821 default:
15822 bad_scalar:
dcbf9037 15823 first_error (_("scalar out of range for multiply instruction"));
5287ad62
JB
15824 }
15825
15826 return 0;
15827}
15828
15829/* Encode multiply / multiply-accumulate scalar instructions. */
15830
15831static void
15832neon_mul_mac (struct neon_type_el et, int ubit)
15833{
dcbf9037
JB
15834 unsigned scalar;
15835
15836 /* Give a more helpful error message if we have an invalid type. */
15837 if (et.type == NT_invtype)
15838 return;
5f4273c7 15839
dcbf9037 15840 scalar = neon_scalar_for_mul (inst.operands[2].reg, et.size);
5287ad62
JB
15841 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
15842 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
15843 inst.instruction |= LOW4 (inst.operands[1].reg) << 16;
15844 inst.instruction |= HI1 (inst.operands[1].reg) << 7;
15845 inst.instruction |= LOW4 (scalar);
15846 inst.instruction |= HI1 (scalar) << 5;
15847 inst.instruction |= (et.type == NT_float) << 8;
15848 inst.instruction |= neon_logbits (et.size) << 20;
15849 inst.instruction |= (ubit != 0) << 24;
15850
88714cb8 15851 neon_dp_fixup (&inst);
5287ad62
JB
15852}
15853
15854static void
15855do_neon_mac_maybe_scalar (void)
15856{
037e8744
JB
15857 if (try_vfp_nsyn (3, do_vfp_nsyn_mla_mls) == SUCCESS)
15858 return;
15859
15860 if (vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH) == FAIL)
15861 return;
15862
5287ad62
JB
15863 if (inst.operands[2].isscalar)
15864 {
037e8744 15865 enum neon_shape rs = neon_select_shape (NS_DDS, NS_QQS, NS_NULL);
5287ad62 15866 struct neon_type_el et = neon_check_type (3, rs,
589a7d88 15867 N_EQK, N_EQK, N_I16 | N_I32 | N_F_16_32 | N_KEY);
88714cb8 15868 NEON_ENCODE (SCALAR, inst);
037e8744 15869 neon_mul_mac (et, neon_quad (rs));
5287ad62
JB
15870 }
15871 else
428e3f1f
PB
15872 {
15873 /* The "untyped" case can't happen. Do this to stop the "U" bit being
15874 affected if we specify unsigned args. */
15875 neon_dyadic_misc (NT_untyped, N_IF_32, 0);
15876 }
5287ad62
JB
15877}
15878
62f3b8c8
PB
15879static void
15880do_neon_fmac (void)
15881{
15882 if (try_vfp_nsyn (3, do_vfp_nsyn_fma_fms) == SUCCESS)
15883 return;
15884
15885 if (vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH) == FAIL)
15886 return;
15887
15888 neon_dyadic_misc (NT_untyped, N_IF_32, 0);
15889}
15890
5287ad62
JB
15891static void
15892do_neon_tst (void)
15893{
037e8744 15894 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
5287ad62
JB
15895 struct neon_type_el et = neon_check_type (3, rs,
15896 N_EQK, N_EQK, N_8 | N_16 | N_32 | N_KEY);
037e8744 15897 neon_three_same (neon_quad (rs), 0, et.size);
5287ad62
JB
15898}
15899
15900/* VMUL with 3 registers allows the P8 type. The scalar version supports the
15901 same types as the MAC equivalents. The polynomial type for this instruction
15902 is encoded the same as the integer type. */
15903
15904static void
15905do_neon_mul (void)
15906{
037e8744
JB
15907 if (try_vfp_nsyn (3, do_vfp_nsyn_mul) == SUCCESS)
15908 return;
15909
15910 if (vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH) == FAIL)
15911 return;
15912
5287ad62
JB
15913 if (inst.operands[2].isscalar)
15914 do_neon_mac_maybe_scalar ();
15915 else
cc933301 15916 neon_dyadic_misc (NT_poly, N_I8 | N_I16 | N_I32 | N_F16 | N_F32 | N_P8, 0);
5287ad62
JB
15917}
15918
15919static void
15920do_neon_qdmulh (void)
15921{
15922 if (inst.operands[2].isscalar)
15923 {
037e8744 15924 enum neon_shape rs = neon_select_shape (NS_DDS, NS_QQS, NS_NULL);
5287ad62 15925 struct neon_type_el et = neon_check_type (3, rs,
477330fc 15926 N_EQK, N_EQK, N_S16 | N_S32 | N_KEY);
88714cb8 15927 NEON_ENCODE (SCALAR, inst);
037e8744 15928 neon_mul_mac (et, neon_quad (rs));
5287ad62
JB
15929 }
15930 else
15931 {
037e8744 15932 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
5287ad62 15933 struct neon_type_el et = neon_check_type (3, rs,
477330fc 15934 N_EQK, N_EQK, N_S16 | N_S32 | N_KEY);
88714cb8 15935 NEON_ENCODE (INTEGER, inst);
5287ad62 15936 /* The U bit (rounding) comes from bit mask. */
037e8744 15937 neon_three_same (neon_quad (rs), 0, et.size);
5287ad62
JB
15938 }
15939}
15940
a302e574
AV
15941static void
15942do_mve_vabav (void)
15943{
15944 enum neon_shape rs = neon_select_shape (NS_RQQ, NS_NULL);
15945
15946 if (rs == NS_NULL)
15947 return;
15948
15949 if (!ARM_CPU_HAS_FEATURE (cpu_variant, mve_ext))
15950 return;
15951
15952 struct neon_type_el et = neon_check_type (2, NS_NULL, N_EQK, N_KEY | N_S8
15953 | N_S16 | N_S32 | N_U8 | N_U16
15954 | N_U32);
15955
15956 if (inst.cond > COND_ALWAYS)
15957 inst.pred_insn_type = INSIDE_VPT_INSN;
15958 else
15959 inst.pred_insn_type = MVE_OUTSIDE_PRED_INSN;
15960
15961 mve_encode_rqq (et.type == NT_unsigned, et.size);
15962}
15963
15964static void
15965do_mve_vmladav (void)
15966{
15967 enum neon_shape rs = neon_select_shape (NS_RQQ, NS_NULL);
15968 struct neon_type_el et = neon_check_type (3, rs,
15969 N_EQK, N_EQK, N_SU_MVE | N_KEY);
15970
15971 if (et.type == NT_unsigned
15972 && (inst.instruction == M_MNEM_vmladavx
15973 || inst.instruction == M_MNEM_vmladavax
15974 || inst.instruction == M_MNEM_vmlsdav
15975 || inst.instruction == M_MNEM_vmlsdava
15976 || inst.instruction == M_MNEM_vmlsdavx
15977 || inst.instruction == M_MNEM_vmlsdavax))
15978 first_error (BAD_SIMD_TYPE);
15979
15980 constraint (inst.operands[2].reg > 14,
15981 _("MVE vector register in the range [Q0..Q7] expected"));
15982
15983 if (inst.cond > COND_ALWAYS)
15984 inst.pred_insn_type = INSIDE_VPT_INSN;
15985 else
15986 inst.pred_insn_type = MVE_OUTSIDE_PRED_INSN;
15987
15988 if (inst.instruction == M_MNEM_vmlsdav
15989 || inst.instruction == M_MNEM_vmlsdava
15990 || inst.instruction == M_MNEM_vmlsdavx
15991 || inst.instruction == M_MNEM_vmlsdavax)
15992 inst.instruction |= (et.size == 8) << 28;
15993 else
15994 inst.instruction |= (et.size == 8) << 8;
15995
15996 mve_encode_rqq (et.type == NT_unsigned, 64);
15997 inst.instruction |= (et.size == 32) << 16;
15998}
15999
643afb90
MW
16000static void
16001do_neon_qrdmlah (void)
16002{
16003 /* Check we're on the correct architecture. */
16004 if (!mark_feature_used (&fpu_neon_ext_armv8))
16005 inst.error =
16006 _("instruction form not available on this architecture.");
16007 else if (!mark_feature_used (&fpu_neon_ext_v8_1))
16008 {
16009 as_warn (_("this instruction implies use of ARMv8.1 AdvSIMD."));
16010 record_feature_use (&fpu_neon_ext_v8_1);
16011 }
16012
16013 if (inst.operands[2].isscalar)
16014 {
16015 enum neon_shape rs = neon_select_shape (NS_DDS, NS_QQS, NS_NULL);
16016 struct neon_type_el et = neon_check_type (3, rs,
16017 N_EQK, N_EQK, N_S16 | N_S32 | N_KEY);
16018 NEON_ENCODE (SCALAR, inst);
16019 neon_mul_mac (et, neon_quad (rs));
16020 }
16021 else
16022 {
16023 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
16024 struct neon_type_el et = neon_check_type (3, rs,
16025 N_EQK, N_EQK, N_S16 | N_S32 | N_KEY);
16026 NEON_ENCODE (INTEGER, inst);
16027 /* The U bit (rounding) comes from bit mask. */
16028 neon_three_same (neon_quad (rs), 0, et.size);
16029 }
16030}
16031
5287ad62
JB
16032static void
16033do_neon_fcmp_absolute (void)
16034{
037e8744 16035 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
cc933301
JW
16036 struct neon_type_el et = neon_check_type (3, rs, N_EQK, N_EQK,
16037 N_F_16_32 | N_KEY);
5287ad62 16038 /* Size field comes from bit mask. */
cc933301 16039 neon_three_same (neon_quad (rs), 1, et.size == 16 ? (int) et.size : -1);
5287ad62
JB
16040}
16041
16042static void
16043do_neon_fcmp_absolute_inv (void)
16044{
16045 neon_exchange_operands ();
16046 do_neon_fcmp_absolute ();
16047}
16048
16049static void
16050do_neon_step (void)
16051{
037e8744 16052 enum neon_shape rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
cc933301
JW
16053 struct neon_type_el et = neon_check_type (3, rs, N_EQK, N_EQK,
16054 N_F_16_32 | N_KEY);
16055 neon_three_same (neon_quad (rs), 0, et.size == 16 ? (int) et.size : -1);
5287ad62
JB
16056}
16057
16058static void
16059do_neon_abs_neg (void)
16060{
037e8744
JB
16061 enum neon_shape rs;
16062 struct neon_type_el et;
5f4273c7 16063
037e8744
JB
16064 if (try_vfp_nsyn (2, do_vfp_nsyn_abs_neg) == SUCCESS)
16065 return;
16066
037e8744 16067 rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
cc933301 16068 et = neon_check_type (2, rs, N_EQK, N_S_32 | N_F_16_32 | N_KEY);
5f4273c7 16069
485dee97
AV
16070 if (check_simd_pred_availability (et.type == NT_float,
16071 NEON_CHECK_ARCH | NEON_CHECK_CC))
16072 return;
16073
5287ad62
JB
16074 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
16075 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
16076 inst.instruction |= LOW4 (inst.operands[1].reg);
16077 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
037e8744 16078 inst.instruction |= neon_quad (rs) << 6;
5287ad62
JB
16079 inst.instruction |= (et.type == NT_float) << 10;
16080 inst.instruction |= neon_logbits (et.size) << 18;
5f4273c7 16081
88714cb8 16082 neon_dp_fixup (&inst);
5287ad62
JB
16083}
16084
16085static void
16086do_neon_sli (void)
16087{
037e8744 16088 enum neon_shape rs = neon_select_shape (NS_DDI, NS_QQI, NS_NULL);
5287ad62
JB
16089 struct neon_type_el et = neon_check_type (2, rs,
16090 N_EQK, N_8 | N_16 | N_32 | N_64 | N_KEY);
16091 int imm = inst.operands[2].imm;
16092 constraint (imm < 0 || (unsigned)imm >= et.size,
477330fc 16093 _("immediate out of range for insert"));
037e8744 16094 neon_imm_shift (FALSE, 0, neon_quad (rs), et, imm);
5287ad62
JB
16095}
16096
16097static void
16098do_neon_sri (void)
16099{
037e8744 16100 enum neon_shape rs = neon_select_shape (NS_DDI, NS_QQI, NS_NULL);
5287ad62
JB
16101 struct neon_type_el et = neon_check_type (2, rs,
16102 N_EQK, N_8 | N_16 | N_32 | N_64 | N_KEY);
16103 int imm = inst.operands[2].imm;
16104 constraint (imm < 1 || (unsigned)imm > et.size,
477330fc 16105 _("immediate out of range for insert"));
037e8744 16106 neon_imm_shift (FALSE, 0, neon_quad (rs), et, et.size - imm);
5287ad62
JB
16107}
16108
16109static void
16110do_neon_qshlu_imm (void)
16111{
037e8744 16112 enum neon_shape rs = neon_select_shape (NS_DDI, NS_QQI, NS_NULL);
5287ad62
JB
16113 struct neon_type_el et = neon_check_type (2, rs,
16114 N_EQK | N_UNS, N_S8 | N_S16 | N_S32 | N_S64 | N_KEY);
16115 int imm = inst.operands[2].imm;
16116 constraint (imm < 0 || (unsigned)imm >= et.size,
477330fc 16117 _("immediate out of range for shift"));
5287ad62
JB
16118 /* Only encodes the 'U present' variant of the instruction.
16119 In this case, signed types have OP (bit 8) set to 0.
16120 Unsigned types have OP set to 1. */
16121 inst.instruction |= (et.type == NT_unsigned) << 8;
16122 /* The rest of the bits are the same as other immediate shifts. */
037e8744 16123 neon_imm_shift (FALSE, 0, neon_quad (rs), et, imm);
5287ad62
JB
16124}
16125
16126static void
16127do_neon_qmovn (void)
16128{
16129 struct neon_type_el et = neon_check_type (2, NS_DQ,
16130 N_EQK | N_HLF, N_SU_16_64 | N_KEY);
16131 /* Saturating move where operands can be signed or unsigned, and the
16132 destination has the same signedness. */
88714cb8 16133 NEON_ENCODE (INTEGER, inst);
5287ad62
JB
16134 if (et.type == NT_unsigned)
16135 inst.instruction |= 0xc0;
16136 else
16137 inst.instruction |= 0x80;
16138 neon_two_same (0, 1, et.size / 2);
16139}
16140
16141static void
16142do_neon_qmovun (void)
16143{
16144 struct neon_type_el et = neon_check_type (2, NS_DQ,
16145 N_EQK | N_HLF | N_UNS, N_S16 | N_S32 | N_S64 | N_KEY);
16146 /* Saturating move with unsigned results. Operands must be signed. */
88714cb8 16147 NEON_ENCODE (INTEGER, inst);
5287ad62
JB
16148 neon_two_same (0, 1, et.size / 2);
16149}
16150
16151static void
16152do_neon_rshift_sat_narrow (void)
16153{
16154 /* FIXME: Types for narrowing. If operands are signed, results can be signed
16155 or unsigned. If operands are unsigned, results must also be unsigned. */
16156 struct neon_type_el et = neon_check_type (2, NS_DQI,
16157 N_EQK | N_HLF, N_SU_16_64 | N_KEY);
16158 int imm = inst.operands[2].imm;
16159 /* This gets the bounds check, size encoding and immediate bits calculation
16160 right. */
16161 et.size /= 2;
5f4273c7 16162
5287ad62
JB
16163 /* VQ{R}SHRN.I<size> <Dd>, <Qm>, #0 is a synonym for
16164 VQMOVN.I<size> <Dd>, <Qm>. */
16165 if (imm == 0)
16166 {
16167 inst.operands[2].present = 0;
16168 inst.instruction = N_MNEM_vqmovn;
16169 do_neon_qmovn ();
16170 return;
16171 }
5f4273c7 16172
5287ad62 16173 constraint (imm < 1 || (unsigned)imm > et.size,
477330fc 16174 _("immediate out of range"));
5287ad62
JB
16175 neon_imm_shift (TRUE, et.type == NT_unsigned, 0, et, et.size - imm);
16176}
16177
16178static void
16179do_neon_rshift_sat_narrow_u (void)
16180{
16181 /* FIXME: Types for narrowing. If operands are signed, results can be signed
16182 or unsigned. If operands are unsigned, results must also be unsigned. */
16183 struct neon_type_el et = neon_check_type (2, NS_DQI,
16184 N_EQK | N_HLF | N_UNS, N_S16 | N_S32 | N_S64 | N_KEY);
16185 int imm = inst.operands[2].imm;
16186 /* This gets the bounds check, size encoding and immediate bits calculation
16187 right. */
16188 et.size /= 2;
16189
16190 /* VQSHRUN.I<size> <Dd>, <Qm>, #0 is a synonym for
16191 VQMOVUN.I<size> <Dd>, <Qm>. */
16192 if (imm == 0)
16193 {
16194 inst.operands[2].present = 0;
16195 inst.instruction = N_MNEM_vqmovun;
16196 do_neon_qmovun ();
16197 return;
16198 }
16199
16200 constraint (imm < 1 || (unsigned)imm > et.size,
477330fc 16201 _("immediate out of range"));
5287ad62
JB
16202 /* FIXME: The manual is kind of unclear about what value U should have in
16203 VQ{R}SHRUN instructions, but U=0, op=0 definitely encodes VRSHR, so it
16204 must be 1. */
16205 neon_imm_shift (TRUE, 1, 0, et, et.size - imm);
16206}
16207
16208static void
16209do_neon_movn (void)
16210{
16211 struct neon_type_el et = neon_check_type (2, NS_DQ,
16212 N_EQK | N_HLF, N_I16 | N_I32 | N_I64 | N_KEY);
88714cb8 16213 NEON_ENCODE (INTEGER, inst);
5287ad62
JB
16214 neon_two_same (0, 1, et.size / 2);
16215}
16216
16217static void
16218do_neon_rshift_narrow (void)
16219{
16220 struct neon_type_el et = neon_check_type (2, NS_DQI,
16221 N_EQK | N_HLF, N_I16 | N_I32 | N_I64 | N_KEY);
16222 int imm = inst.operands[2].imm;
16223 /* This gets the bounds check, size encoding and immediate bits calculation
16224 right. */
16225 et.size /= 2;
5f4273c7 16226
5287ad62
JB
16227 /* If immediate is zero then we are a pseudo-instruction for
16228 VMOVN.I<size> <Dd>, <Qm> */
16229 if (imm == 0)
16230 {
16231 inst.operands[2].present = 0;
16232 inst.instruction = N_MNEM_vmovn;
16233 do_neon_movn ();
16234 return;
16235 }
5f4273c7 16236
5287ad62 16237 constraint (imm < 1 || (unsigned)imm > et.size,
477330fc 16238 _("immediate out of range for narrowing operation"));
5287ad62
JB
16239 neon_imm_shift (FALSE, 0, 0, et, et.size - imm);
16240}
16241
16242static void
16243do_neon_shll (void)
16244{
16245 /* FIXME: Type checking when lengthening. */
16246 struct neon_type_el et = neon_check_type (2, NS_QDI,
16247 N_EQK | N_DBL, N_I8 | N_I16 | N_I32 | N_KEY);
16248 unsigned imm = inst.operands[2].imm;
16249
16250 if (imm == et.size)
16251 {
16252 /* Maximum shift variant. */
88714cb8 16253 NEON_ENCODE (INTEGER, inst);
5287ad62
JB
16254 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
16255 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
16256 inst.instruction |= LOW4 (inst.operands[1].reg);
16257 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
16258 inst.instruction |= neon_logbits (et.size) << 18;
5f4273c7 16259
88714cb8 16260 neon_dp_fixup (&inst);
5287ad62
JB
16261 }
16262 else
16263 {
16264 /* A more-specific type check for non-max versions. */
16265 et = neon_check_type (2, NS_QDI,
477330fc 16266 N_EQK | N_DBL, N_SU_32 | N_KEY);
88714cb8 16267 NEON_ENCODE (IMMED, inst);
5287ad62
JB
16268 neon_imm_shift (TRUE, et.type == NT_unsigned, 0, et, imm);
16269 }
16270}
16271
037e8744 16272/* Check the various types for the VCVT instruction, and return which version
5287ad62
JB
16273 the current instruction is. */
16274
6b9a8b67
MGD
16275#define CVT_FLAVOUR_VAR \
16276 CVT_VAR (s32_f32, N_S32, N_F32, whole_reg, "ftosls", "ftosis", "ftosizs") \
16277 CVT_VAR (u32_f32, N_U32, N_F32, whole_reg, "ftouls", "ftouis", "ftouizs") \
16278 CVT_VAR (f32_s32, N_F32, N_S32, whole_reg, "fsltos", "fsitos", NULL) \
16279 CVT_VAR (f32_u32, N_F32, N_U32, whole_reg, "fultos", "fuitos", NULL) \
16280 /* Half-precision conversions. */ \
cc933301
JW
16281 CVT_VAR (s16_f16, N_S16, N_F16 | N_KEY, whole_reg, NULL, NULL, NULL) \
16282 CVT_VAR (u16_f16, N_U16, N_F16 | N_KEY, whole_reg, NULL, NULL, NULL) \
16283 CVT_VAR (f16_s16, N_F16 | N_KEY, N_S16, whole_reg, NULL, NULL, NULL) \
16284 CVT_VAR (f16_u16, N_F16 | N_KEY, N_U16, whole_reg, NULL, NULL, NULL) \
6b9a8b67
MGD
16285 CVT_VAR (f32_f16, N_F32, N_F16, whole_reg, NULL, NULL, NULL) \
16286 CVT_VAR (f16_f32, N_F16, N_F32, whole_reg, NULL, NULL, NULL) \
9db2f6b4
RL
16287 /* New VCVT instructions introduced by ARMv8.2 fp16 extension. \
16288 Compared with single/double precision variants, only the co-processor \
16289 field is different, so the encoding flow is reused here. */ \
16290 CVT_VAR (f16_s32, N_F16 | N_KEY, N_S32, N_VFP, "fsltos", "fsitos", NULL) \
16291 CVT_VAR (f16_u32, N_F16 | N_KEY, N_U32, N_VFP, "fultos", "fuitos", NULL) \
16292 CVT_VAR (u32_f16, N_U32, N_F16 | N_KEY, N_VFP, "ftouls", "ftouis", "ftouizs")\
16293 CVT_VAR (s32_f16, N_S32, N_F16 | N_KEY, N_VFP, "ftosls", "ftosis", "ftosizs")\
6b9a8b67
MGD
16294 /* VFP instructions. */ \
16295 CVT_VAR (f32_f64, N_F32, N_F64, N_VFP, NULL, "fcvtsd", NULL) \
16296 CVT_VAR (f64_f32, N_F64, N_F32, N_VFP, NULL, "fcvtds", NULL) \
16297 CVT_VAR (s32_f64, N_S32, N_F64 | key, N_VFP, "ftosld", "ftosid", "ftosizd") \
16298 CVT_VAR (u32_f64, N_U32, N_F64 | key, N_VFP, "ftould", "ftouid", "ftouizd") \
16299 CVT_VAR (f64_s32, N_F64 | key, N_S32, N_VFP, "fsltod", "fsitod", NULL) \
16300 CVT_VAR (f64_u32, N_F64 | key, N_U32, N_VFP, "fultod", "fuitod", NULL) \
16301 /* VFP instructions with bitshift. */ \
16302 CVT_VAR (f32_s16, N_F32 | key, N_S16, N_VFP, "fshtos", NULL, NULL) \
16303 CVT_VAR (f32_u16, N_F32 | key, N_U16, N_VFP, "fuhtos", NULL, NULL) \
16304 CVT_VAR (f64_s16, N_F64 | key, N_S16, N_VFP, "fshtod", NULL, NULL) \
16305 CVT_VAR (f64_u16, N_F64 | key, N_U16, N_VFP, "fuhtod", NULL, NULL) \
16306 CVT_VAR (s16_f32, N_S16, N_F32 | key, N_VFP, "ftoshs", NULL, NULL) \
16307 CVT_VAR (u16_f32, N_U16, N_F32 | key, N_VFP, "ftouhs", NULL, NULL) \
16308 CVT_VAR (s16_f64, N_S16, N_F64 | key, N_VFP, "ftoshd", NULL, NULL) \
16309 CVT_VAR (u16_f64, N_U16, N_F64 | key, N_VFP, "ftouhd", NULL, NULL)
16310
16311#define CVT_VAR(C, X, Y, R, BSN, CN, ZN) \
16312 neon_cvt_flavour_##C,
16313
16314/* The different types of conversions we can do. */
16315enum neon_cvt_flavour
16316{
16317 CVT_FLAVOUR_VAR
16318 neon_cvt_flavour_invalid,
16319 neon_cvt_flavour_first_fp = neon_cvt_flavour_f32_f64
16320};
16321
16322#undef CVT_VAR
16323
16324static enum neon_cvt_flavour
16325get_neon_cvt_flavour (enum neon_shape rs)
5287ad62 16326{
6b9a8b67
MGD
16327#define CVT_VAR(C,X,Y,R,BSN,CN,ZN) \
16328 et = neon_check_type (2, rs, (R) | (X), (R) | (Y)); \
16329 if (et.type != NT_invtype) \
16330 { \
16331 inst.error = NULL; \
16332 return (neon_cvt_flavour_##C); \
5287ad62 16333 }
6b9a8b67 16334
5287ad62 16335 struct neon_type_el et;
037e8744 16336 unsigned whole_reg = (rs == NS_FFI || rs == NS_FD || rs == NS_DF
477330fc 16337 || rs == NS_FF) ? N_VFP : 0;
037e8744
JB
16338 /* The instruction versions which take an immediate take one register
16339 argument, which is extended to the width of the full register. Thus the
16340 "source" and "destination" registers must have the same width. Hack that
16341 here by making the size equal to the key (wider, in this case) operand. */
16342 unsigned key = (rs == NS_QQI || rs == NS_DDI || rs == NS_FFI) ? N_KEY : 0;
5f4273c7 16343
6b9a8b67
MGD
16344 CVT_FLAVOUR_VAR;
16345
16346 return neon_cvt_flavour_invalid;
5287ad62
JB
16347#undef CVT_VAR
16348}
16349
7e8e6784
MGD
16350enum neon_cvt_mode
16351{
16352 neon_cvt_mode_a,
16353 neon_cvt_mode_n,
16354 neon_cvt_mode_p,
16355 neon_cvt_mode_m,
16356 neon_cvt_mode_z,
30bdf752
MGD
16357 neon_cvt_mode_x,
16358 neon_cvt_mode_r
7e8e6784
MGD
16359};
16360
037e8744
JB
16361/* Neon-syntax VFP conversions. */
16362
5287ad62 16363static void
6b9a8b67 16364do_vfp_nsyn_cvt (enum neon_shape rs, enum neon_cvt_flavour flavour)
5287ad62 16365{
037e8744 16366 const char *opname = 0;
5f4273c7 16367
d54af2d0
RL
16368 if (rs == NS_DDI || rs == NS_QQI || rs == NS_FFI
16369 || rs == NS_FHI || rs == NS_HFI)
5287ad62 16370 {
037e8744
JB
16371 /* Conversions with immediate bitshift. */
16372 const char *enc[] =
477330fc 16373 {
6b9a8b67
MGD
16374#define CVT_VAR(C,A,B,R,BSN,CN,ZN) BSN,
16375 CVT_FLAVOUR_VAR
16376 NULL
16377#undef CVT_VAR
477330fc 16378 };
037e8744 16379
6b9a8b67 16380 if (flavour < (int) ARRAY_SIZE (enc))
477330fc
RM
16381 {
16382 opname = enc[flavour];
16383 constraint (inst.operands[0].reg != inst.operands[1].reg,
16384 _("operands 0 and 1 must be the same register"));
16385 inst.operands[1] = inst.operands[2];
16386 memset (&inst.operands[2], '\0', sizeof (inst.operands[2]));
16387 }
5287ad62
JB
16388 }
16389 else
16390 {
037e8744
JB
16391 /* Conversions without bitshift. */
16392 const char *enc[] =
477330fc 16393 {
6b9a8b67
MGD
16394#define CVT_VAR(C,A,B,R,BSN,CN,ZN) CN,
16395 CVT_FLAVOUR_VAR
16396 NULL
16397#undef CVT_VAR
477330fc 16398 };
037e8744 16399
6b9a8b67 16400 if (flavour < (int) ARRAY_SIZE (enc))
477330fc 16401 opname = enc[flavour];
037e8744
JB
16402 }
16403
16404 if (opname)
16405 do_vfp_nsyn_opcode (opname);
9db2f6b4
RL
16406
16407 /* ARMv8.2 fp16 VCVT instruction. */
16408 if (flavour == neon_cvt_flavour_s32_f16
16409 || flavour == neon_cvt_flavour_u32_f16
16410 || flavour == neon_cvt_flavour_f16_u32
16411 || flavour == neon_cvt_flavour_f16_s32)
16412 do_scalar_fp16_v82_encode ();
037e8744
JB
16413}
16414
16415static void
16416do_vfp_nsyn_cvtz (void)
16417{
d54af2d0 16418 enum neon_shape rs = neon_select_shape (NS_FH, NS_FF, NS_FD, NS_NULL);
6b9a8b67 16419 enum neon_cvt_flavour flavour = get_neon_cvt_flavour (rs);
037e8744
JB
16420 const char *enc[] =
16421 {
6b9a8b67
MGD
16422#define CVT_VAR(C,A,B,R,BSN,CN,ZN) ZN,
16423 CVT_FLAVOUR_VAR
16424 NULL
16425#undef CVT_VAR
037e8744
JB
16426 };
16427
6b9a8b67 16428 if (flavour < (int) ARRAY_SIZE (enc) && enc[flavour])
037e8744
JB
16429 do_vfp_nsyn_opcode (enc[flavour]);
16430}
f31fef98 16431
037e8744 16432static void
bacebabc 16433do_vfp_nsyn_cvt_fpv8 (enum neon_cvt_flavour flavour,
7e8e6784
MGD
16434 enum neon_cvt_mode mode)
16435{
16436 int sz, op;
16437 int rm;
16438
a715796b
TG
16439 /* Targets like FPv5-SP-D16 don't support FP v8 instructions with
16440 D register operands. */
16441 if (flavour == neon_cvt_flavour_s32_f64
16442 || flavour == neon_cvt_flavour_u32_f64)
16443 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_armv8),
16444 _(BAD_FPU));
16445
9db2f6b4
RL
16446 if (flavour == neon_cvt_flavour_s32_f16
16447 || flavour == neon_cvt_flavour_u32_f16)
16448 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_fp16),
16449 _(BAD_FP16));
16450
5ee91343 16451 set_pred_insn_type (OUTSIDE_PRED_INSN);
7e8e6784
MGD
16452
16453 switch (flavour)
16454 {
16455 case neon_cvt_flavour_s32_f64:
16456 sz = 1;
827f64ff 16457 op = 1;
7e8e6784
MGD
16458 break;
16459 case neon_cvt_flavour_s32_f32:
16460 sz = 0;
16461 op = 1;
16462 break;
9db2f6b4
RL
16463 case neon_cvt_flavour_s32_f16:
16464 sz = 0;
16465 op = 1;
16466 break;
7e8e6784
MGD
16467 case neon_cvt_flavour_u32_f64:
16468 sz = 1;
16469 op = 0;
16470 break;
16471 case neon_cvt_flavour_u32_f32:
16472 sz = 0;
16473 op = 0;
16474 break;
9db2f6b4
RL
16475 case neon_cvt_flavour_u32_f16:
16476 sz = 0;
16477 op = 0;
16478 break;
7e8e6784
MGD
16479 default:
16480 first_error (_("invalid instruction shape"));
16481 return;
16482 }
16483
16484 switch (mode)
16485 {
16486 case neon_cvt_mode_a: rm = 0; break;
16487 case neon_cvt_mode_n: rm = 1; break;
16488 case neon_cvt_mode_p: rm = 2; break;
16489 case neon_cvt_mode_m: rm = 3; break;
16490 default: first_error (_("invalid rounding mode")); return;
16491 }
16492
16493 NEON_ENCODE (FPV8, inst);
16494 encode_arm_vfp_reg (inst.operands[0].reg, VFP_REG_Sd);
16495 encode_arm_vfp_reg (inst.operands[1].reg, sz == 1 ? VFP_REG_Dm : VFP_REG_Sm);
16496 inst.instruction |= sz << 8;
9db2f6b4
RL
16497
16498 /* ARMv8.2 fp16 VCVT instruction. */
16499 if (flavour == neon_cvt_flavour_s32_f16
16500 ||flavour == neon_cvt_flavour_u32_f16)
16501 do_scalar_fp16_v82_encode ();
7e8e6784
MGD
16502 inst.instruction |= op << 7;
16503 inst.instruction |= rm << 16;
16504 inst.instruction |= 0xf0000000;
16505 inst.is_neon = TRUE;
16506}
16507
16508static void
16509do_neon_cvt_1 (enum neon_cvt_mode mode)
037e8744
JB
16510{
16511 enum neon_shape rs = neon_select_shape (NS_DDI, NS_QQI, NS_FFI, NS_DD, NS_QQ,
d54af2d0
RL
16512 NS_FD, NS_DF, NS_FF, NS_QD, NS_DQ,
16513 NS_FH, NS_HF, NS_FHI, NS_HFI,
16514 NS_NULL);
6b9a8b67 16515 enum neon_cvt_flavour flavour = get_neon_cvt_flavour (rs);
037e8744 16516
cc933301
JW
16517 if (flavour == neon_cvt_flavour_invalid)
16518 return;
16519
e3e535bc 16520 /* PR11109: Handle round-to-zero for VCVT conversions. */
7e8e6784 16521 if (mode == neon_cvt_mode_z
e3e535bc 16522 && ARM_CPU_HAS_FEATURE (cpu_variant, fpu_arch_vfp_v2)
cc933301
JW
16523 && (flavour == neon_cvt_flavour_s16_f16
16524 || flavour == neon_cvt_flavour_u16_f16
16525 || flavour == neon_cvt_flavour_s32_f32
bacebabc
RM
16526 || flavour == neon_cvt_flavour_u32_f32
16527 || flavour == neon_cvt_flavour_s32_f64
6b9a8b67 16528 || flavour == neon_cvt_flavour_u32_f64)
e3e535bc
NC
16529 && (rs == NS_FD || rs == NS_FF))
16530 {
16531 do_vfp_nsyn_cvtz ();
16532 return;
16533 }
16534
9db2f6b4
RL
16535 /* ARMv8.2 fp16 VCVT conversions. */
16536 if (mode == neon_cvt_mode_z
16537 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_fp16)
16538 && (flavour == neon_cvt_flavour_s32_f16
16539 || flavour == neon_cvt_flavour_u32_f16)
16540 && (rs == NS_FH))
16541 {
16542 do_vfp_nsyn_cvtz ();
16543 do_scalar_fp16_v82_encode ();
16544 return;
16545 }
16546
037e8744 16547 /* VFP rather than Neon conversions. */
6b9a8b67 16548 if (flavour >= neon_cvt_flavour_first_fp)
037e8744 16549 {
7e8e6784
MGD
16550 if (mode == neon_cvt_mode_x || mode == neon_cvt_mode_z)
16551 do_vfp_nsyn_cvt (rs, flavour);
16552 else
16553 do_vfp_nsyn_cvt_fpv8 (flavour, mode);
16554
037e8744
JB
16555 return;
16556 }
16557
16558 switch (rs)
16559 {
16560 case NS_DDI:
16561 case NS_QQI:
16562 {
477330fc 16563 unsigned immbits;
cc933301
JW
16564 unsigned enctab[] = {0x0000100, 0x1000100, 0x0, 0x1000000,
16565 0x0000100, 0x1000100, 0x0, 0x1000000};
35997600 16566
477330fc
RM
16567 if (vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH) == FAIL)
16568 return;
037e8744 16569
477330fc
RM
16570 /* Fixed-point conversion with #0 immediate is encoded as an
16571 integer conversion. */
16572 if (inst.operands[2].present && inst.operands[2].imm == 0)
16573 goto int_encode;
477330fc
RM
16574 NEON_ENCODE (IMMED, inst);
16575 if (flavour != neon_cvt_flavour_invalid)
16576 inst.instruction |= enctab[flavour];
16577 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
16578 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
16579 inst.instruction |= LOW4 (inst.operands[1].reg);
16580 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
16581 inst.instruction |= neon_quad (rs) << 6;
16582 inst.instruction |= 1 << 21;
cc933301
JW
16583 if (flavour < neon_cvt_flavour_s16_f16)
16584 {
16585 inst.instruction |= 1 << 21;
16586 immbits = 32 - inst.operands[2].imm;
16587 inst.instruction |= immbits << 16;
16588 }
16589 else
16590 {
16591 inst.instruction |= 3 << 20;
16592 immbits = 16 - inst.operands[2].imm;
16593 inst.instruction |= immbits << 16;
16594 inst.instruction &= ~(1 << 9);
16595 }
477330fc
RM
16596
16597 neon_dp_fixup (&inst);
037e8744
JB
16598 }
16599 break;
16600
16601 case NS_DD:
16602 case NS_QQ:
7e8e6784
MGD
16603 if (mode != neon_cvt_mode_x && mode != neon_cvt_mode_z)
16604 {
16605 NEON_ENCODE (FLOAT, inst);
5ee91343 16606 set_pred_insn_type (OUTSIDE_PRED_INSN);
7e8e6784
MGD
16607
16608 if (vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH8) == FAIL)
16609 return;
16610
16611 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
16612 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
16613 inst.instruction |= LOW4 (inst.operands[1].reg);
16614 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
16615 inst.instruction |= neon_quad (rs) << 6;
cc933301
JW
16616 inst.instruction |= (flavour == neon_cvt_flavour_u16_f16
16617 || flavour == neon_cvt_flavour_u32_f32) << 7;
7e8e6784 16618 inst.instruction |= mode << 8;
cc933301
JW
16619 if (flavour == neon_cvt_flavour_u16_f16
16620 || flavour == neon_cvt_flavour_s16_f16)
16621 /* Mask off the original size bits and reencode them. */
16622 inst.instruction = ((inst.instruction & 0xfff3ffff) | (1 << 18));
16623
7e8e6784
MGD
16624 if (thumb_mode)
16625 inst.instruction |= 0xfc000000;
16626 else
16627 inst.instruction |= 0xf0000000;
16628 }
16629 else
16630 {
037e8744 16631 int_encode:
7e8e6784 16632 {
cc933301
JW
16633 unsigned enctab[] = { 0x100, 0x180, 0x0, 0x080,
16634 0x100, 0x180, 0x0, 0x080};
037e8744 16635
7e8e6784 16636 NEON_ENCODE (INTEGER, inst);
037e8744 16637
7e8e6784
MGD
16638 if (vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH) == FAIL)
16639 return;
037e8744 16640
7e8e6784
MGD
16641 if (flavour != neon_cvt_flavour_invalid)
16642 inst.instruction |= enctab[flavour];
037e8744 16643
7e8e6784
MGD
16644 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
16645 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
16646 inst.instruction |= LOW4 (inst.operands[1].reg);
16647 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
16648 inst.instruction |= neon_quad (rs) << 6;
cc933301
JW
16649 if (flavour >= neon_cvt_flavour_s16_f16
16650 && flavour <= neon_cvt_flavour_f16_u16)
16651 /* Half precision. */
16652 inst.instruction |= 1 << 18;
16653 else
16654 inst.instruction |= 2 << 18;
037e8744 16655
7e8e6784
MGD
16656 neon_dp_fixup (&inst);
16657 }
16658 }
16659 break;
037e8744 16660
8e79c3df
CM
16661 /* Half-precision conversions for Advanced SIMD -- neon. */
16662 case NS_QD:
16663 case NS_DQ:
bc52d49c
MM
16664 if (vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH) == FAIL)
16665 return;
8e79c3df
CM
16666
16667 if ((rs == NS_DQ)
16668 && (inst.vectype.el[0].size != 16 || inst.vectype.el[1].size != 32))
16669 {
16670 as_bad (_("operand size must match register width"));
16671 break;
16672 }
16673
16674 if ((rs == NS_QD)
16675 && ((inst.vectype.el[0].size != 32 || inst.vectype.el[1].size != 16)))
16676 {
16677 as_bad (_("operand size must match register width"));
16678 break;
16679 }
16680
16681 if (rs == NS_DQ)
477330fc 16682 inst.instruction = 0x3b60600;
8e79c3df
CM
16683 else
16684 inst.instruction = 0x3b60700;
16685
16686 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
16687 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
16688 inst.instruction |= LOW4 (inst.operands[1].reg);
16689 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
88714cb8 16690 neon_dp_fixup (&inst);
8e79c3df
CM
16691 break;
16692
037e8744
JB
16693 default:
16694 /* Some VFP conversions go here (s32 <-> f32, u32 <-> f32). */
7e8e6784
MGD
16695 if (mode == neon_cvt_mode_x || mode == neon_cvt_mode_z)
16696 do_vfp_nsyn_cvt (rs, flavour);
16697 else
16698 do_vfp_nsyn_cvt_fpv8 (flavour, mode);
5287ad62 16699 }
5287ad62
JB
16700}
16701
e3e535bc
NC
16702static void
16703do_neon_cvtr (void)
16704{
7e8e6784 16705 do_neon_cvt_1 (neon_cvt_mode_x);
e3e535bc
NC
16706}
16707
16708static void
16709do_neon_cvt (void)
16710{
7e8e6784
MGD
16711 do_neon_cvt_1 (neon_cvt_mode_z);
16712}
16713
16714static void
16715do_neon_cvta (void)
16716{
16717 do_neon_cvt_1 (neon_cvt_mode_a);
16718}
16719
16720static void
16721do_neon_cvtn (void)
16722{
16723 do_neon_cvt_1 (neon_cvt_mode_n);
16724}
16725
16726static void
16727do_neon_cvtp (void)
16728{
16729 do_neon_cvt_1 (neon_cvt_mode_p);
16730}
16731
16732static void
16733do_neon_cvtm (void)
16734{
16735 do_neon_cvt_1 (neon_cvt_mode_m);
e3e535bc
NC
16736}
16737
8e79c3df 16738static void
c70a8987 16739do_neon_cvttb_2 (bfd_boolean t, bfd_boolean to, bfd_boolean is_double)
8e79c3df 16740{
c70a8987
MGD
16741 if (is_double)
16742 mark_feature_used (&fpu_vfp_ext_armv8);
8e79c3df 16743
c70a8987
MGD
16744 encode_arm_vfp_reg (inst.operands[0].reg,
16745 (is_double && !to) ? VFP_REG_Dd : VFP_REG_Sd);
16746 encode_arm_vfp_reg (inst.operands[1].reg,
16747 (is_double && to) ? VFP_REG_Dm : VFP_REG_Sm);
16748 inst.instruction |= to ? 0x10000 : 0;
16749 inst.instruction |= t ? 0x80 : 0;
16750 inst.instruction |= is_double ? 0x100 : 0;
16751 do_vfp_cond_or_thumb ();
16752}
8e79c3df 16753
c70a8987
MGD
16754static void
16755do_neon_cvttb_1 (bfd_boolean t)
16756{
d54af2d0
RL
16757 enum neon_shape rs = neon_select_shape (NS_HF, NS_HD, NS_FH, NS_FF, NS_FD,
16758 NS_DF, NS_DH, NS_NULL);
8e79c3df 16759
c70a8987
MGD
16760 if (rs == NS_NULL)
16761 return;
16762 else if (neon_check_type (2, rs, N_F16, N_F32 | N_VFP).type != NT_invtype)
16763 {
16764 inst.error = NULL;
16765 do_neon_cvttb_2 (t, /*to=*/TRUE, /*is_double=*/FALSE);
16766 }
16767 else if (neon_check_type (2, rs, N_F32 | N_VFP, N_F16).type != NT_invtype)
16768 {
16769 inst.error = NULL;
16770 do_neon_cvttb_2 (t, /*to=*/FALSE, /*is_double=*/FALSE);
16771 }
16772 else if (neon_check_type (2, rs, N_F16, N_F64 | N_VFP).type != NT_invtype)
16773 {
a715796b
TG
16774 /* The VCVTB and VCVTT instructions with D-register operands
16775 don't work for SP only targets. */
16776 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_armv8),
16777 _(BAD_FPU));
16778
c70a8987
MGD
16779 inst.error = NULL;
16780 do_neon_cvttb_2 (t, /*to=*/TRUE, /*is_double=*/TRUE);
16781 }
16782 else if (neon_check_type (2, rs, N_F64 | N_VFP, N_F16).type != NT_invtype)
16783 {
a715796b
TG
16784 /* The VCVTB and VCVTT instructions with D-register operands
16785 don't work for SP only targets. */
16786 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_armv8),
16787 _(BAD_FPU));
16788
c70a8987
MGD
16789 inst.error = NULL;
16790 do_neon_cvttb_2 (t, /*to=*/FALSE, /*is_double=*/TRUE);
16791 }
16792 else
16793 return;
16794}
16795
16796static void
16797do_neon_cvtb (void)
16798{
16799 do_neon_cvttb_1 (FALSE);
8e79c3df
CM
16800}
16801
16802
16803static void
16804do_neon_cvtt (void)
16805{
c70a8987 16806 do_neon_cvttb_1 (TRUE);
8e79c3df
CM
16807}
16808
5287ad62
JB
16809static void
16810neon_move_immediate (void)
16811{
037e8744
JB
16812 enum neon_shape rs = neon_select_shape (NS_DI, NS_QI, NS_NULL);
16813 struct neon_type_el et = neon_check_type (2, rs,
16814 N_I8 | N_I16 | N_I32 | N_I64 | N_F32 | N_KEY, N_EQK);
5287ad62 16815 unsigned immlo, immhi = 0, immbits;
c96612cc 16816 int op, cmode, float_p;
5287ad62 16817
037e8744 16818 constraint (et.type == NT_invtype,
477330fc 16819 _("operand size must be specified for immediate VMOV"));
037e8744 16820
5287ad62
JB
16821 /* We start out as an MVN instruction if OP = 1, MOV otherwise. */
16822 op = (inst.instruction & (1 << 5)) != 0;
16823
16824 immlo = inst.operands[1].imm;
16825 if (inst.operands[1].regisimm)
16826 immhi = inst.operands[1].reg;
16827
16828 constraint (et.size < 32 && (immlo & ~((1 << et.size) - 1)) != 0,
477330fc 16829 _("immediate has bits set outside the operand size"));
5287ad62 16830
c96612cc
JB
16831 float_p = inst.operands[1].immisfloat;
16832
16833 if ((cmode = neon_cmode_for_move_imm (immlo, immhi, float_p, &immbits, &op,
477330fc 16834 et.size, et.type)) == FAIL)
5287ad62
JB
16835 {
16836 /* Invert relevant bits only. */
16837 neon_invert_size (&immlo, &immhi, et.size);
16838 /* Flip from VMOV/VMVN to VMVN/VMOV. Some immediate types are unavailable
477330fc
RM
16839 with one or the other; those cases are caught by
16840 neon_cmode_for_move_imm. */
5287ad62 16841 op = !op;
c96612cc
JB
16842 if ((cmode = neon_cmode_for_move_imm (immlo, immhi, float_p, &immbits,
16843 &op, et.size, et.type)) == FAIL)
477330fc
RM
16844 {
16845 first_error (_("immediate out of range"));
16846 return;
16847 }
5287ad62
JB
16848 }
16849
16850 inst.instruction &= ~(1 << 5);
16851 inst.instruction |= op << 5;
16852
16853 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
16854 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
037e8744 16855 inst.instruction |= neon_quad (rs) << 6;
5287ad62
JB
16856 inst.instruction |= cmode << 8;
16857
16858 neon_write_immbits (immbits);
16859}
16860
16861static void
16862do_neon_mvn (void)
16863{
16864 if (inst.operands[1].isreg)
16865 {
037e8744 16866 enum neon_shape rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
5f4273c7 16867
88714cb8 16868 NEON_ENCODE (INTEGER, inst);
5287ad62
JB
16869 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
16870 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
16871 inst.instruction |= LOW4 (inst.operands[1].reg);
16872 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
037e8744 16873 inst.instruction |= neon_quad (rs) << 6;
5287ad62
JB
16874 }
16875 else
16876 {
88714cb8 16877 NEON_ENCODE (IMMED, inst);
5287ad62
JB
16878 neon_move_immediate ();
16879 }
16880
88714cb8 16881 neon_dp_fixup (&inst);
5287ad62
JB
16882}
16883
16884/* Encode instructions of form:
16885
16886 |28/24|23|22|21 20|19 16|15 12|11 8|7|6|5|4|3 0|
5f4273c7 16887 | U |x |D |size | Rn | Rd |x x x x|N|x|M|x| Rm | */
5287ad62
JB
16888
16889static void
16890neon_mixed_length (struct neon_type_el et, unsigned size)
16891{
16892 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
16893 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
16894 inst.instruction |= LOW4 (inst.operands[1].reg) << 16;
16895 inst.instruction |= HI1 (inst.operands[1].reg) << 7;
16896 inst.instruction |= LOW4 (inst.operands[2].reg);
16897 inst.instruction |= HI1 (inst.operands[2].reg) << 5;
16898 inst.instruction |= (et.type == NT_unsigned) << 24;
16899 inst.instruction |= neon_logbits (size) << 20;
5f4273c7 16900
88714cb8 16901 neon_dp_fixup (&inst);
5287ad62
JB
16902}
16903
16904static void
16905do_neon_dyadic_long (void)
16906{
5ee91343
AV
16907 enum neon_shape rs = neon_select_shape (NS_QDD, NS_QQQ, NS_QQR, NS_NULL);
16908 if (rs == NS_QDD)
16909 {
16910 if (vfp_or_neon_is_neon (NEON_CHECK_ARCH | NEON_CHECK_CC) == FAIL)
16911 return;
16912
16913 NEON_ENCODE (INTEGER, inst);
16914 /* FIXME: Type checking for lengthening op. */
16915 struct neon_type_el et = neon_check_type (3, NS_QDD,
16916 N_EQK | N_DBL, N_EQK, N_SU_32 | N_KEY);
16917 neon_mixed_length (et, et.size);
16918 }
16919 else if (ARM_CPU_HAS_FEATURE (cpu_variant, mve_ext)
16920 && (inst.cond == 0xf || inst.cond == 0x10))
16921 {
16922 /* If parsing for MVE, vaddl/vsubl/vabdl{e,t} can only be vadd/vsub/vabd
16923 in an IT block with le/lt conditions. */
16924
16925 if (inst.cond == 0xf)
16926 inst.cond = 0xb;
16927 else if (inst.cond == 0x10)
16928 inst.cond = 0xd;
16929
16930 inst.pred_insn_type = INSIDE_IT_INSN;
16931
16932 if (inst.instruction == N_MNEM_vaddl)
16933 {
16934 inst.instruction = N_MNEM_vadd;
16935 do_neon_addsub_if_i ();
16936 }
16937 else if (inst.instruction == N_MNEM_vsubl)
16938 {
16939 inst.instruction = N_MNEM_vsub;
16940 do_neon_addsub_if_i ();
16941 }
16942 else if (inst.instruction == N_MNEM_vabdl)
16943 {
16944 inst.instruction = N_MNEM_vabd;
16945 do_neon_dyadic_if_su ();
16946 }
16947 }
16948 else
16949 first_error (BAD_FPU);
5287ad62
JB
16950}
16951
16952static void
16953do_neon_abal (void)
16954{
16955 struct neon_type_el et = neon_check_type (3, NS_QDD,
16956 N_EQK | N_INT | N_DBL, N_EQK, N_SU_32 | N_KEY);
16957 neon_mixed_length (et, et.size);
16958}
16959
16960static void
16961neon_mac_reg_scalar_long (unsigned regtypes, unsigned scalartypes)
16962{
16963 if (inst.operands[2].isscalar)
16964 {
dcbf9037 16965 struct neon_type_el et = neon_check_type (3, NS_QDS,
477330fc 16966 N_EQK | N_DBL, N_EQK, regtypes | N_KEY);
88714cb8 16967 NEON_ENCODE (SCALAR, inst);
5287ad62
JB
16968 neon_mul_mac (et, et.type == NT_unsigned);
16969 }
16970 else
16971 {
16972 struct neon_type_el et = neon_check_type (3, NS_QDD,
477330fc 16973 N_EQK | N_DBL, N_EQK, scalartypes | N_KEY);
88714cb8 16974 NEON_ENCODE (INTEGER, inst);
5287ad62
JB
16975 neon_mixed_length (et, et.size);
16976 }
16977}
16978
16979static void
16980do_neon_mac_maybe_scalar_long (void)
16981{
16982 neon_mac_reg_scalar_long (N_S16 | N_S32 | N_U16 | N_U32, N_SU_32);
16983}
16984
dec41383
JW
16985/* Like neon_scalar_for_mul, this function generate Rm encoding from GAS's
16986 internal SCALAR. QUAD_P is 1 if it's for Q format, otherwise it's 0. */
16987
16988static unsigned
16989neon_scalar_for_fmac_fp16_long (unsigned scalar, unsigned quad_p)
16990{
16991 unsigned regno = NEON_SCALAR_REG (scalar);
16992 unsigned elno = NEON_SCALAR_INDEX (scalar);
16993
16994 if (quad_p)
16995 {
16996 if (regno > 7 || elno > 3)
16997 goto bad_scalar;
16998
16999 return ((regno & 0x7)
17000 | ((elno & 0x1) << 3)
17001 | (((elno >> 1) & 0x1) << 5));
17002 }
17003 else
17004 {
17005 if (regno > 15 || elno > 1)
17006 goto bad_scalar;
17007
17008 return (((regno & 0x1) << 5)
17009 | ((regno >> 1) & 0x7)
17010 | ((elno & 0x1) << 3));
17011 }
17012
17013bad_scalar:
17014 first_error (_("scalar out of range for multiply instruction"));
17015 return 0;
17016}
17017
17018static void
17019do_neon_fmac_maybe_scalar_long (int subtype)
17020{
17021 enum neon_shape rs;
17022 int high8;
17023 /* NOTE: vfmal/vfmsl use slightly different NEON three-same encoding. 'size"
17024 field (bits[21:20]) has different meaning. For scalar index variant, it's
17025 used to differentiate add and subtract, otherwise it's with fixed value
17026 0x2. */
17027 int size = -1;
17028
17029 if (inst.cond != COND_ALWAYS)
17030 as_warn (_("vfmal/vfmsl with FP16 type cannot be conditional, the "
17031 "behaviour is UNPREDICTABLE"));
17032
01f48020 17033 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_fp16_fml),
dec41383
JW
17034 _(BAD_FP16));
17035
17036 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_neon_ext_armv8),
17037 _(BAD_FPU));
17038
17039 /* vfmal/vfmsl are in three-same D/Q register format or the third operand can
17040 be a scalar index register. */
17041 if (inst.operands[2].isscalar)
17042 {
17043 high8 = 0xfe000000;
17044 if (subtype)
17045 size = 16;
17046 rs = neon_select_shape (NS_DHS, NS_QDS, NS_NULL);
17047 }
17048 else
17049 {
17050 high8 = 0xfc000000;
17051 size = 32;
17052 if (subtype)
17053 inst.instruction |= (0x1 << 23);
17054 rs = neon_select_shape (NS_DHH, NS_QDD, NS_NULL);
17055 }
17056
17057 neon_check_type (3, rs, N_EQK, N_EQK, N_KEY | N_F16);
17058
17059 /* "opcode" from template has included "ubit", so simply pass 0 here. Also,
17060 the "S" bit in size field has been reused to differentiate vfmal and vfmsl,
17061 so we simply pass -1 as size. */
17062 unsigned quad_p = (rs == NS_QDD || rs == NS_QDS);
17063 neon_three_same (quad_p, 0, size);
17064
17065 /* Undo neon_dp_fixup. Redo the high eight bits. */
17066 inst.instruction &= 0x00ffffff;
17067 inst.instruction |= high8;
17068
17069#define LOW1(R) ((R) & 0x1)
17070#define HI4(R) (((R) >> 1) & 0xf)
17071 /* Unlike usually NEON three-same, encoding for Vn and Vm will depend on
17072 whether the instruction is in Q form and whether Vm is a scalar indexed
17073 operand. */
17074 if (inst.operands[2].isscalar)
17075 {
17076 unsigned rm
17077 = neon_scalar_for_fmac_fp16_long (inst.operands[2].reg, quad_p);
17078 inst.instruction &= 0xffffffd0;
17079 inst.instruction |= rm;
17080
17081 if (!quad_p)
17082 {
17083 /* Redo Rn as well. */
17084 inst.instruction &= 0xfff0ff7f;
17085 inst.instruction |= HI4 (inst.operands[1].reg) << 16;
17086 inst.instruction |= LOW1 (inst.operands[1].reg) << 7;
17087 }
17088 }
17089 else if (!quad_p)
17090 {
17091 /* Redo Rn and Rm. */
17092 inst.instruction &= 0xfff0ff50;
17093 inst.instruction |= HI4 (inst.operands[1].reg) << 16;
17094 inst.instruction |= LOW1 (inst.operands[1].reg) << 7;
17095 inst.instruction |= HI4 (inst.operands[2].reg);
17096 inst.instruction |= LOW1 (inst.operands[2].reg) << 5;
17097 }
17098}
17099
17100static void
17101do_neon_vfmal (void)
17102{
17103 return do_neon_fmac_maybe_scalar_long (0);
17104}
17105
17106static void
17107do_neon_vfmsl (void)
17108{
17109 return do_neon_fmac_maybe_scalar_long (1);
17110}
17111
5287ad62
JB
17112static void
17113do_neon_dyadic_wide (void)
17114{
17115 struct neon_type_el et = neon_check_type (3, NS_QQD,
17116 N_EQK | N_DBL, N_EQK | N_DBL, N_SU_32 | N_KEY);
17117 neon_mixed_length (et, et.size);
17118}
17119
17120static void
17121do_neon_dyadic_narrow (void)
17122{
17123 struct neon_type_el et = neon_check_type (3, NS_QDD,
17124 N_EQK | N_DBL, N_EQK, N_I16 | N_I32 | N_I64 | N_KEY);
428e3f1f
PB
17125 /* Operand sign is unimportant, and the U bit is part of the opcode,
17126 so force the operand type to integer. */
17127 et.type = NT_integer;
5287ad62
JB
17128 neon_mixed_length (et, et.size / 2);
17129}
17130
17131static void
17132do_neon_mul_sat_scalar_long (void)
17133{
17134 neon_mac_reg_scalar_long (N_S16 | N_S32, N_S16 | N_S32);
17135}
17136
17137static void
17138do_neon_vmull (void)
17139{
17140 if (inst.operands[2].isscalar)
17141 do_neon_mac_maybe_scalar_long ();
17142 else
17143 {
17144 struct neon_type_el et = neon_check_type (3, NS_QDD,
477330fc 17145 N_EQK | N_DBL, N_EQK, N_SU_32 | N_P8 | N_P64 | N_KEY);
4f51b4bd 17146
5287ad62 17147 if (et.type == NT_poly)
477330fc 17148 NEON_ENCODE (POLY, inst);
5287ad62 17149 else
477330fc 17150 NEON_ENCODE (INTEGER, inst);
4f51b4bd
MGD
17151
17152 /* For polynomial encoding the U bit must be zero, and the size must
17153 be 8 (encoded as 0b00) or, on ARMv8 or later 64 (encoded, non
17154 obviously, as 0b10). */
17155 if (et.size == 64)
17156 {
17157 /* Check we're on the correct architecture. */
17158 if (!mark_feature_used (&fpu_crypto_ext_armv8))
17159 inst.error =
17160 _("Instruction form not available on this architecture.");
17161
17162 et.size = 32;
17163 }
17164
5287ad62
JB
17165 neon_mixed_length (et, et.size);
17166 }
17167}
17168
17169static void
17170do_neon_ext (void)
17171{
037e8744 17172 enum neon_shape rs = neon_select_shape (NS_DDDI, NS_QQQI, NS_NULL);
5287ad62
JB
17173 struct neon_type_el et = neon_check_type (3, rs,
17174 N_EQK, N_EQK, N_8 | N_16 | N_32 | N_64 | N_KEY);
17175 unsigned imm = (inst.operands[3].imm * et.size) / 8;
35997600
NC
17176
17177 constraint (imm >= (unsigned) (neon_quad (rs) ? 16 : 8),
17178 _("shift out of range"));
5287ad62
JB
17179 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
17180 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
17181 inst.instruction |= LOW4 (inst.operands[1].reg) << 16;
17182 inst.instruction |= HI1 (inst.operands[1].reg) << 7;
17183 inst.instruction |= LOW4 (inst.operands[2].reg);
17184 inst.instruction |= HI1 (inst.operands[2].reg) << 5;
037e8744 17185 inst.instruction |= neon_quad (rs) << 6;
5287ad62 17186 inst.instruction |= imm << 8;
5f4273c7 17187
88714cb8 17188 neon_dp_fixup (&inst);
5287ad62
JB
17189}
17190
17191static void
17192do_neon_rev (void)
17193{
037e8744 17194 enum neon_shape rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
5287ad62
JB
17195 struct neon_type_el et = neon_check_type (2, rs,
17196 N_EQK, N_8 | N_16 | N_32 | N_KEY);
17197 unsigned op = (inst.instruction >> 7) & 3;
17198 /* N (width of reversed regions) is encoded as part of the bitmask. We
17199 extract it here to check the elements to be reversed are smaller.
17200 Otherwise we'd get a reserved instruction. */
17201 unsigned elsize = (op == 2) ? 16 : (op == 1) ? 32 : (op == 0) ? 64 : 0;
9c2799c2 17202 gas_assert (elsize != 0);
5287ad62 17203 constraint (et.size >= elsize,
477330fc 17204 _("elements must be smaller than reversal region"));
037e8744 17205 neon_two_same (neon_quad (rs), 1, et.size);
5287ad62
JB
17206}
17207
17208static void
17209do_neon_dup (void)
17210{
17211 if (inst.operands[1].isscalar)
17212 {
037e8744 17213 enum neon_shape rs = neon_select_shape (NS_DS, NS_QS, NS_NULL);
dcbf9037 17214 struct neon_type_el et = neon_check_type (2, rs,
477330fc 17215 N_EQK, N_8 | N_16 | N_32 | N_KEY);
5287ad62 17216 unsigned sizebits = et.size >> 3;
dcbf9037 17217 unsigned dm = NEON_SCALAR_REG (inst.operands[1].reg);
5287ad62 17218 int logsize = neon_logbits (et.size);
dcbf9037 17219 unsigned x = NEON_SCALAR_INDEX (inst.operands[1].reg) << logsize;
037e8744
JB
17220
17221 if (vfp_or_neon_is_neon (NEON_CHECK_CC) == FAIL)
477330fc 17222 return;
037e8744 17223
88714cb8 17224 NEON_ENCODE (SCALAR, inst);
5287ad62
JB
17225 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
17226 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
17227 inst.instruction |= LOW4 (dm);
17228 inst.instruction |= HI1 (dm) << 5;
037e8744 17229 inst.instruction |= neon_quad (rs) << 6;
5287ad62
JB
17230 inst.instruction |= x << 17;
17231 inst.instruction |= sizebits << 16;
5f4273c7 17232
88714cb8 17233 neon_dp_fixup (&inst);
5287ad62
JB
17234 }
17235 else
17236 {
037e8744
JB
17237 enum neon_shape rs = neon_select_shape (NS_DR, NS_QR, NS_NULL);
17238 struct neon_type_el et = neon_check_type (2, rs,
477330fc 17239 N_8 | N_16 | N_32 | N_KEY, N_EQK);
5287ad62 17240 /* Duplicate ARM register to lanes of vector. */
88714cb8 17241 NEON_ENCODE (ARMREG, inst);
5287ad62 17242 switch (et.size)
477330fc
RM
17243 {
17244 case 8: inst.instruction |= 0x400000; break;
17245 case 16: inst.instruction |= 0x000020; break;
17246 case 32: inst.instruction |= 0x000000; break;
17247 default: break;
17248 }
5287ad62
JB
17249 inst.instruction |= LOW4 (inst.operands[1].reg) << 12;
17250 inst.instruction |= LOW4 (inst.operands[0].reg) << 16;
17251 inst.instruction |= HI1 (inst.operands[0].reg) << 7;
037e8744 17252 inst.instruction |= neon_quad (rs) << 21;
5287ad62 17253 /* The encoding for this instruction is identical for the ARM and Thumb
477330fc 17254 variants, except for the condition field. */
037e8744 17255 do_vfp_cond_or_thumb ();
5287ad62
JB
17256 }
17257}
17258
17259/* VMOV has particularly many variations. It can be one of:
17260 0. VMOV<c><q> <Qd>, <Qm>
17261 1. VMOV<c><q> <Dd>, <Dm>
17262 (Register operations, which are VORR with Rm = Rn.)
17263 2. VMOV<c><q>.<dt> <Qd>, #<imm>
17264 3. VMOV<c><q>.<dt> <Dd>, #<imm>
17265 (Immediate loads.)
17266 4. VMOV<c><q>.<size> <Dn[x]>, <Rd>
17267 (ARM register to scalar.)
17268 5. VMOV<c><q> <Dm>, <Rd>, <Rn>
17269 (Two ARM registers to vector.)
17270 6. VMOV<c><q>.<dt> <Rd>, <Dn[x]>
17271 (Scalar to ARM register.)
17272 7. VMOV<c><q> <Rd>, <Rn>, <Dm>
17273 (Vector to two ARM registers.)
037e8744
JB
17274 8. VMOV.F32 <Sd>, <Sm>
17275 9. VMOV.F64 <Dd>, <Dm>
17276 (VFP register moves.)
17277 10. VMOV.F32 <Sd>, #imm
17278 11. VMOV.F64 <Dd>, #imm
17279 (VFP float immediate load.)
17280 12. VMOV <Rd>, <Sm>
17281 (VFP single to ARM reg.)
17282 13. VMOV <Sd>, <Rm>
17283 (ARM reg to VFP single.)
17284 14. VMOV <Rd>, <Re>, <Sn>, <Sm>
17285 (Two ARM regs to two VFP singles.)
17286 15. VMOV <Sd>, <Se>, <Rn>, <Rm>
17287 (Two VFP singles to two ARM regs.)
5f4273c7 17288
037e8744
JB
17289 These cases can be disambiguated using neon_select_shape, except cases 1/9
17290 and 3/11 which depend on the operand type too.
5f4273c7 17291
5287ad62 17292 All the encoded bits are hardcoded by this function.
5f4273c7 17293
b7fc2769
JB
17294 Cases 4, 6 may be used with VFPv1 and above (only 32-bit transfers!).
17295 Cases 5, 7 may be used with VFPv2 and above.
5f4273c7 17296
5287ad62 17297 FIXME: Some of the checking may be a bit sloppy (in a couple of cases you
5f4273c7 17298 can specify a type where it doesn't make sense to, and is ignored). */
5287ad62
JB
17299
17300static void
17301do_neon_mov (void)
17302{
037e8744 17303 enum neon_shape rs = neon_select_shape (NS_RRFF, NS_FFRR, NS_DRR, NS_RRD,
9db2f6b4
RL
17304 NS_QQ, NS_DD, NS_QI, NS_DI, NS_SR,
17305 NS_RS, NS_FF, NS_FI, NS_RF, NS_FR,
17306 NS_HR, NS_RH, NS_HI, NS_NULL);
037e8744
JB
17307 struct neon_type_el et;
17308 const char *ldconst = 0;
5287ad62 17309
037e8744 17310 switch (rs)
5287ad62 17311 {
037e8744
JB
17312 case NS_DD: /* case 1/9. */
17313 et = neon_check_type (2, rs, N_EQK, N_F64 | N_KEY);
17314 /* It is not an error here if no type is given. */
17315 inst.error = NULL;
17316 if (et.type == NT_float && et.size == 64)
477330fc
RM
17317 {
17318 do_vfp_nsyn_opcode ("fcpyd");
17319 break;
17320 }
037e8744 17321 /* fall through. */
5287ad62 17322
037e8744
JB
17323 case NS_QQ: /* case 0/1. */
17324 {
477330fc
RM
17325 if (vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH) == FAIL)
17326 return;
17327 /* The architecture manual I have doesn't explicitly state which
17328 value the U bit should have for register->register moves, but
17329 the equivalent VORR instruction has U = 0, so do that. */
17330 inst.instruction = 0x0200110;
17331 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
17332 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
17333 inst.instruction |= LOW4 (inst.operands[1].reg);
17334 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
17335 inst.instruction |= LOW4 (inst.operands[1].reg) << 16;
17336 inst.instruction |= HI1 (inst.operands[1].reg) << 7;
17337 inst.instruction |= neon_quad (rs) << 6;
17338
17339 neon_dp_fixup (&inst);
037e8744
JB
17340 }
17341 break;
5f4273c7 17342
037e8744
JB
17343 case NS_DI: /* case 3/11. */
17344 et = neon_check_type (2, rs, N_EQK, N_F64 | N_KEY);
17345 inst.error = NULL;
17346 if (et.type == NT_float && et.size == 64)
477330fc
RM
17347 {
17348 /* case 11 (fconstd). */
17349 ldconst = "fconstd";
17350 goto encode_fconstd;
17351 }
037e8744
JB
17352 /* fall through. */
17353
17354 case NS_QI: /* case 2/3. */
17355 if (vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH) == FAIL)
477330fc 17356 return;
037e8744
JB
17357 inst.instruction = 0x0800010;
17358 neon_move_immediate ();
88714cb8 17359 neon_dp_fixup (&inst);
5287ad62 17360 break;
5f4273c7 17361
037e8744
JB
17362 case NS_SR: /* case 4. */
17363 {
477330fc
RM
17364 unsigned bcdebits = 0;
17365 int logsize;
17366 unsigned dn = NEON_SCALAR_REG (inst.operands[0].reg);
17367 unsigned x = NEON_SCALAR_INDEX (inst.operands[0].reg);
037e8744 17368
05ac0ffb
JB
17369 /* .<size> is optional here, defaulting to .32. */
17370 if (inst.vectype.elems == 0
17371 && inst.operands[0].vectype.type == NT_invtype
17372 && inst.operands[1].vectype.type == NT_invtype)
17373 {
17374 inst.vectype.el[0].type = NT_untyped;
17375 inst.vectype.el[0].size = 32;
17376 inst.vectype.elems = 1;
17377 }
17378
477330fc
RM
17379 et = neon_check_type (2, NS_NULL, N_8 | N_16 | N_32 | N_KEY, N_EQK);
17380 logsize = neon_logbits (et.size);
17381
17382 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_v1),
17383 _(BAD_FPU));
17384 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_neon_ext_v1)
17385 && et.size != 32, _(BAD_FPU));
17386 constraint (et.type == NT_invtype, _("bad type for scalar"));
17387 constraint (x >= 64 / et.size, _("scalar index out of range"));
17388
17389 switch (et.size)
17390 {
17391 case 8: bcdebits = 0x8; break;
17392 case 16: bcdebits = 0x1; break;
17393 case 32: bcdebits = 0x0; break;
17394 default: ;
17395 }
17396
17397 bcdebits |= x << logsize;
17398
17399 inst.instruction = 0xe000b10;
17400 do_vfp_cond_or_thumb ();
17401 inst.instruction |= LOW4 (dn) << 16;
17402 inst.instruction |= HI1 (dn) << 7;
17403 inst.instruction |= inst.operands[1].reg << 12;
17404 inst.instruction |= (bcdebits & 3) << 5;
17405 inst.instruction |= (bcdebits >> 2) << 21;
037e8744
JB
17406 }
17407 break;
5f4273c7 17408
037e8744 17409 case NS_DRR: /* case 5 (fmdrr). */
b7fc2769 17410 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_v2),
477330fc 17411 _(BAD_FPU));
b7fc2769 17412
037e8744
JB
17413 inst.instruction = 0xc400b10;
17414 do_vfp_cond_or_thumb ();
17415 inst.instruction |= LOW4 (inst.operands[0].reg);
17416 inst.instruction |= HI1 (inst.operands[0].reg) << 5;
17417 inst.instruction |= inst.operands[1].reg << 12;
17418 inst.instruction |= inst.operands[2].reg << 16;
17419 break;
5f4273c7 17420
037e8744
JB
17421 case NS_RS: /* case 6. */
17422 {
477330fc
RM
17423 unsigned logsize;
17424 unsigned dn = NEON_SCALAR_REG (inst.operands[1].reg);
17425 unsigned x = NEON_SCALAR_INDEX (inst.operands[1].reg);
17426 unsigned abcdebits = 0;
037e8744 17427
05ac0ffb
JB
17428 /* .<dt> is optional here, defaulting to .32. */
17429 if (inst.vectype.elems == 0
17430 && inst.operands[0].vectype.type == NT_invtype
17431 && inst.operands[1].vectype.type == NT_invtype)
17432 {
17433 inst.vectype.el[0].type = NT_untyped;
17434 inst.vectype.el[0].size = 32;
17435 inst.vectype.elems = 1;
17436 }
17437
91d6fa6a
NC
17438 et = neon_check_type (2, NS_NULL,
17439 N_EQK, N_S8 | N_S16 | N_U8 | N_U16 | N_32 | N_KEY);
477330fc
RM
17440 logsize = neon_logbits (et.size);
17441
17442 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_v1),
17443 _(BAD_FPU));
17444 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_neon_ext_v1)
17445 && et.size != 32, _(BAD_FPU));
17446 constraint (et.type == NT_invtype, _("bad type for scalar"));
17447 constraint (x >= 64 / et.size, _("scalar index out of range"));
17448
17449 switch (et.size)
17450 {
17451 case 8: abcdebits = (et.type == NT_signed) ? 0x08 : 0x18; break;
17452 case 16: abcdebits = (et.type == NT_signed) ? 0x01 : 0x11; break;
17453 case 32: abcdebits = 0x00; break;
17454 default: ;
17455 }
17456
17457 abcdebits |= x << logsize;
17458 inst.instruction = 0xe100b10;
17459 do_vfp_cond_or_thumb ();
17460 inst.instruction |= LOW4 (dn) << 16;
17461 inst.instruction |= HI1 (dn) << 7;
17462 inst.instruction |= inst.operands[0].reg << 12;
17463 inst.instruction |= (abcdebits & 3) << 5;
17464 inst.instruction |= (abcdebits >> 2) << 21;
037e8744
JB
17465 }
17466 break;
5f4273c7 17467
037e8744
JB
17468 case NS_RRD: /* case 7 (fmrrd). */
17469 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_v2),
477330fc 17470 _(BAD_FPU));
037e8744
JB
17471
17472 inst.instruction = 0xc500b10;
17473 do_vfp_cond_or_thumb ();
17474 inst.instruction |= inst.operands[0].reg << 12;
17475 inst.instruction |= inst.operands[1].reg << 16;
17476 inst.instruction |= LOW4 (inst.operands[2].reg);
17477 inst.instruction |= HI1 (inst.operands[2].reg) << 5;
17478 break;
5f4273c7 17479
037e8744
JB
17480 case NS_FF: /* case 8 (fcpys). */
17481 do_vfp_nsyn_opcode ("fcpys");
17482 break;
5f4273c7 17483
9db2f6b4 17484 case NS_HI:
037e8744
JB
17485 case NS_FI: /* case 10 (fconsts). */
17486 ldconst = "fconsts";
4ef4710f 17487 encode_fconstd:
58ed5c38
TC
17488 if (!inst.operands[1].immisfloat)
17489 {
4ef4710f 17490 unsigned new_imm;
58ed5c38 17491 /* Immediate has to fit in 8 bits so float is enough. */
4ef4710f
NC
17492 float imm = (float) inst.operands[1].imm;
17493 memcpy (&new_imm, &imm, sizeof (float));
17494 /* But the assembly may have been written to provide an integer
17495 bit pattern that equates to a float, so check that the
17496 conversion has worked. */
17497 if (is_quarter_float (new_imm))
17498 {
17499 if (is_quarter_float (inst.operands[1].imm))
17500 as_warn (_("immediate constant is valid both as a bit-pattern and a floating point value (using the fp value)"));
17501
17502 inst.operands[1].imm = new_imm;
17503 inst.operands[1].immisfloat = 1;
17504 }
58ed5c38
TC
17505 }
17506
037e8744 17507 if (is_quarter_float (inst.operands[1].imm))
477330fc
RM
17508 {
17509 inst.operands[1].imm = neon_qfloat_bits (inst.operands[1].imm);
17510 do_vfp_nsyn_opcode (ldconst);
9db2f6b4
RL
17511
17512 /* ARMv8.2 fp16 vmov.f16 instruction. */
17513 if (rs == NS_HI)
17514 do_scalar_fp16_v82_encode ();
477330fc 17515 }
5287ad62 17516 else
477330fc 17517 first_error (_("immediate out of range"));
037e8744 17518 break;
5f4273c7 17519
9db2f6b4 17520 case NS_RH:
037e8744
JB
17521 case NS_RF: /* case 12 (fmrs). */
17522 do_vfp_nsyn_opcode ("fmrs");
9db2f6b4
RL
17523 /* ARMv8.2 fp16 vmov.f16 instruction. */
17524 if (rs == NS_RH)
17525 do_scalar_fp16_v82_encode ();
037e8744 17526 break;
5f4273c7 17527
9db2f6b4 17528 case NS_HR:
037e8744
JB
17529 case NS_FR: /* case 13 (fmsr). */
17530 do_vfp_nsyn_opcode ("fmsr");
9db2f6b4
RL
17531 /* ARMv8.2 fp16 vmov.f16 instruction. */
17532 if (rs == NS_HR)
17533 do_scalar_fp16_v82_encode ();
037e8744 17534 break;
5f4273c7 17535
037e8744
JB
17536 /* The encoders for the fmrrs and fmsrr instructions expect three operands
17537 (one of which is a list), but we have parsed four. Do some fiddling to
17538 make the operands what do_vfp_reg2_from_sp2 and do_vfp_sp2_from_reg2
17539 expect. */
17540 case NS_RRFF: /* case 14 (fmrrs). */
17541 constraint (inst.operands[3].reg != inst.operands[2].reg + 1,
477330fc 17542 _("VFP registers must be adjacent"));
037e8744
JB
17543 inst.operands[2].imm = 2;
17544 memset (&inst.operands[3], '\0', sizeof (inst.operands[3]));
17545 do_vfp_nsyn_opcode ("fmrrs");
17546 break;
5f4273c7 17547
037e8744
JB
17548 case NS_FFRR: /* case 15 (fmsrr). */
17549 constraint (inst.operands[1].reg != inst.operands[0].reg + 1,
477330fc 17550 _("VFP registers must be adjacent"));
037e8744
JB
17551 inst.operands[1] = inst.operands[2];
17552 inst.operands[2] = inst.operands[3];
17553 inst.operands[0].imm = 2;
17554 memset (&inst.operands[3], '\0', sizeof (inst.operands[3]));
17555 do_vfp_nsyn_opcode ("fmsrr");
5287ad62 17556 break;
5f4273c7 17557
4c261dff
NC
17558 case NS_NULL:
17559 /* neon_select_shape has determined that the instruction
17560 shape is wrong and has already set the error message. */
17561 break;
17562
5287ad62
JB
17563 default:
17564 abort ();
17565 }
17566}
17567
17568static void
17569do_neon_rshift_round_imm (void)
17570{
037e8744 17571 enum neon_shape rs = neon_select_shape (NS_DDI, NS_QQI, NS_NULL);
5287ad62
JB
17572 struct neon_type_el et = neon_check_type (2, rs, N_EQK, N_SU_ALL | N_KEY);
17573 int imm = inst.operands[2].imm;
17574
17575 /* imm == 0 case is encoded as VMOV for V{R}SHR. */
17576 if (imm == 0)
17577 {
17578 inst.operands[2].present = 0;
17579 do_neon_mov ();
17580 return;
17581 }
17582
17583 constraint (imm < 1 || (unsigned)imm > et.size,
477330fc 17584 _("immediate out of range for shift"));
037e8744 17585 neon_imm_shift (TRUE, et.type == NT_unsigned, neon_quad (rs), et,
477330fc 17586 et.size - imm);
5287ad62
JB
17587}
17588
9db2f6b4
RL
17589static void
17590do_neon_movhf (void)
17591{
17592 enum neon_shape rs = neon_select_shape (NS_HH, NS_NULL);
17593 constraint (rs != NS_HH, _("invalid suffix"));
17594
7bdf778b
ASDV
17595 if (inst.cond != COND_ALWAYS)
17596 {
17597 if (thumb_mode)
17598 {
17599 as_warn (_("ARMv8.2 scalar fp16 instruction cannot be conditional,"
17600 " the behaviour is UNPREDICTABLE"));
17601 }
17602 else
17603 {
17604 inst.error = BAD_COND;
17605 return;
17606 }
17607 }
17608
9db2f6b4
RL
17609 do_vfp_sp_monadic ();
17610
17611 inst.is_neon = 1;
17612 inst.instruction |= 0xf0000000;
17613}
17614
5287ad62
JB
17615static void
17616do_neon_movl (void)
17617{
17618 struct neon_type_el et = neon_check_type (2, NS_QD,
17619 N_EQK | N_DBL, N_SU_32 | N_KEY);
17620 unsigned sizebits = et.size >> 3;
17621 inst.instruction |= sizebits << 19;
17622 neon_two_same (0, et.type == NT_unsigned, -1);
17623}
17624
17625static void
17626do_neon_trn (void)
17627{
037e8744 17628 enum neon_shape rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
5287ad62
JB
17629 struct neon_type_el et = neon_check_type (2, rs,
17630 N_EQK, N_8 | N_16 | N_32 | N_KEY);
88714cb8 17631 NEON_ENCODE (INTEGER, inst);
037e8744 17632 neon_two_same (neon_quad (rs), 1, et.size);
5287ad62
JB
17633}
17634
17635static void
17636do_neon_zip_uzp (void)
17637{
037e8744 17638 enum neon_shape rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
5287ad62
JB
17639 struct neon_type_el et = neon_check_type (2, rs,
17640 N_EQK, N_8 | N_16 | N_32 | N_KEY);
17641 if (rs == NS_DD && et.size == 32)
17642 {
17643 /* Special case: encode as VTRN.32 <Dd>, <Dm>. */
17644 inst.instruction = N_MNEM_vtrn;
17645 do_neon_trn ();
17646 return;
17647 }
037e8744 17648 neon_two_same (neon_quad (rs), 1, et.size);
5287ad62
JB
17649}
17650
17651static void
17652do_neon_sat_abs_neg (void)
17653{
037e8744 17654 enum neon_shape rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
5287ad62
JB
17655 struct neon_type_el et = neon_check_type (2, rs,
17656 N_EQK, N_S8 | N_S16 | N_S32 | N_KEY);
037e8744 17657 neon_two_same (neon_quad (rs), 1, et.size);
5287ad62
JB
17658}
17659
17660static void
17661do_neon_pair_long (void)
17662{
037e8744 17663 enum neon_shape rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
5287ad62
JB
17664 struct neon_type_el et = neon_check_type (2, rs, N_EQK, N_SU_32 | N_KEY);
17665 /* Unsigned is encoded in OP field (bit 7) for these instruction. */
17666 inst.instruction |= (et.type == NT_unsigned) << 7;
037e8744 17667 neon_two_same (neon_quad (rs), 1, et.size);
5287ad62
JB
17668}
17669
17670static void
17671do_neon_recip_est (void)
17672{
037e8744 17673 enum neon_shape rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
5287ad62 17674 struct neon_type_el et = neon_check_type (2, rs,
cc933301 17675 N_EQK | N_FLT, N_F_16_32 | N_U32 | N_KEY);
5287ad62 17676 inst.instruction |= (et.type == NT_float) << 8;
037e8744 17677 neon_two_same (neon_quad (rs), 1, et.size);
5287ad62
JB
17678}
17679
17680static void
17681do_neon_cls (void)
17682{
037e8744 17683 enum neon_shape rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
5287ad62
JB
17684 struct neon_type_el et = neon_check_type (2, rs,
17685 N_EQK, N_S8 | N_S16 | N_S32 | N_KEY);
037e8744 17686 neon_two_same (neon_quad (rs), 1, et.size);
5287ad62
JB
17687}
17688
17689static void
17690do_neon_clz (void)
17691{
037e8744 17692 enum neon_shape rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
5287ad62
JB
17693 struct neon_type_el et = neon_check_type (2, rs,
17694 N_EQK, N_I8 | N_I16 | N_I32 | N_KEY);
037e8744 17695 neon_two_same (neon_quad (rs), 1, et.size);
5287ad62
JB
17696}
17697
17698static void
17699do_neon_cnt (void)
17700{
037e8744 17701 enum neon_shape rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
5287ad62
JB
17702 struct neon_type_el et = neon_check_type (2, rs,
17703 N_EQK | N_INT, N_8 | N_KEY);
037e8744 17704 neon_two_same (neon_quad (rs), 1, et.size);
5287ad62
JB
17705}
17706
17707static void
17708do_neon_swp (void)
17709{
037e8744
JB
17710 enum neon_shape rs = neon_select_shape (NS_DD, NS_QQ, NS_NULL);
17711 neon_two_same (neon_quad (rs), 1, -1);
5287ad62
JB
17712}
17713
17714static void
17715do_neon_tbl_tbx (void)
17716{
17717 unsigned listlenbits;
dcbf9037 17718 neon_check_type (3, NS_DLD, N_EQK, N_EQK, N_8 | N_KEY);
5f4273c7 17719
5287ad62
JB
17720 if (inst.operands[1].imm < 1 || inst.operands[1].imm > 4)
17721 {
dcbf9037 17722 first_error (_("bad list length for table lookup"));
5287ad62
JB
17723 return;
17724 }
5f4273c7 17725
5287ad62
JB
17726 listlenbits = inst.operands[1].imm - 1;
17727 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
17728 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
17729 inst.instruction |= LOW4 (inst.operands[1].reg) << 16;
17730 inst.instruction |= HI1 (inst.operands[1].reg) << 7;
17731 inst.instruction |= LOW4 (inst.operands[2].reg);
17732 inst.instruction |= HI1 (inst.operands[2].reg) << 5;
17733 inst.instruction |= listlenbits << 8;
5f4273c7 17734
88714cb8 17735 neon_dp_fixup (&inst);
5287ad62
JB
17736}
17737
17738static void
17739do_neon_ldm_stm (void)
17740{
17741 /* P, U and L bits are part of bitmask. */
17742 int is_dbmode = (inst.instruction & (1 << 24)) != 0;
17743 unsigned offsetbits = inst.operands[1].imm * 2;
17744
037e8744
JB
17745 if (inst.operands[1].issingle)
17746 {
17747 do_vfp_nsyn_ldm_stm (is_dbmode);
17748 return;
17749 }
17750
5287ad62 17751 constraint (is_dbmode && !inst.operands[0].writeback,
477330fc 17752 _("writeback (!) must be used for VLDMDB and VSTMDB"));
5287ad62
JB
17753
17754 constraint (inst.operands[1].imm < 1 || inst.operands[1].imm > 16,
477330fc
RM
17755 _("register list must contain at least 1 and at most 16 "
17756 "registers"));
5287ad62
JB
17757
17758 inst.instruction |= inst.operands[0].reg << 16;
17759 inst.instruction |= inst.operands[0].writeback << 21;
17760 inst.instruction |= LOW4 (inst.operands[1].reg) << 12;
17761 inst.instruction |= HI1 (inst.operands[1].reg) << 22;
17762
17763 inst.instruction |= offsetbits;
5f4273c7 17764
037e8744 17765 do_vfp_cond_or_thumb ();
5287ad62
JB
17766}
17767
17768static void
17769do_neon_ldr_str (void)
17770{
5287ad62 17771 int is_ldr = (inst.instruction & (1 << 20)) != 0;
5f4273c7 17772
6844b2c2
MGD
17773 /* Use of PC in vstr in ARM mode is deprecated in ARMv7.
17774 And is UNPREDICTABLE in thumb mode. */
fa94de6b 17775 if (!is_ldr
6844b2c2 17776 && inst.operands[1].reg == REG_PC
ba86b375 17777 && (ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v7) || thumb_mode))
6844b2c2 17778 {
94dcf8bf 17779 if (thumb_mode)
6844b2c2 17780 inst.error = _("Use of PC here is UNPREDICTABLE");
94dcf8bf 17781 else if (warn_on_deprecated)
5c3696f8 17782 as_tsktsk (_("Use of PC here is deprecated"));
6844b2c2
MGD
17783 }
17784
037e8744
JB
17785 if (inst.operands[0].issingle)
17786 {
cd2f129f 17787 if (is_ldr)
477330fc 17788 do_vfp_nsyn_opcode ("flds");
cd2f129f 17789 else
477330fc 17790 do_vfp_nsyn_opcode ("fsts");
9db2f6b4
RL
17791
17792 /* ARMv8.2 vldr.16/vstr.16 instruction. */
17793 if (inst.vectype.el[0].size == 16)
17794 do_scalar_fp16_v82_encode ();
5287ad62
JB
17795 }
17796 else
5287ad62 17797 {
cd2f129f 17798 if (is_ldr)
477330fc 17799 do_vfp_nsyn_opcode ("fldd");
5287ad62 17800 else
477330fc 17801 do_vfp_nsyn_opcode ("fstd");
5287ad62 17802 }
5287ad62
JB
17803}
17804
32c36c3c
AV
17805static void
17806do_t_vldr_vstr_sysreg (void)
17807{
17808 int fp_vldr_bitno = 20, sysreg_vldr_bitno = 20;
17809 bfd_boolean is_vldr = ((inst.instruction & (1 << fp_vldr_bitno)) != 0);
17810
17811 /* Use of PC is UNPREDICTABLE. */
17812 if (inst.operands[1].reg == REG_PC)
17813 inst.error = _("Use of PC here is UNPREDICTABLE");
17814
17815 if (inst.operands[1].immisreg)
17816 inst.error = _("instruction does not accept register index");
17817
17818 if (!inst.operands[1].isreg)
17819 inst.error = _("instruction does not accept PC-relative addressing");
17820
17821 if (abs (inst.operands[1].imm) >= (1 << 7))
17822 inst.error = _("immediate value out of range");
17823
17824 inst.instruction = 0xec000f80;
17825 if (is_vldr)
17826 inst.instruction |= 1 << sysreg_vldr_bitno;
17827 encode_arm_cp_address (1, TRUE, FALSE, BFD_RELOC_ARM_T32_VLDR_VSTR_OFF_IMM);
17828 inst.instruction |= (inst.operands[0].imm & 0x7) << 13;
17829 inst.instruction |= (inst.operands[0].imm & 0x8) << 19;
17830}
17831
17832static void
17833do_vldr_vstr (void)
17834{
17835 bfd_boolean sysreg_op = !inst.operands[0].isreg;
17836
17837 /* VLDR/VSTR (System Register). */
17838 if (sysreg_op)
17839 {
17840 if (!mark_feature_used (&arm_ext_v8_1m_main))
17841 as_bad (_("Instruction not permitted on this architecture"));
17842
17843 do_t_vldr_vstr_sysreg ();
17844 }
17845 /* VLDR/VSTR. */
17846 else
17847 {
17848 if (!mark_feature_used (&fpu_vfp_ext_v1xd))
17849 as_bad (_("Instruction not permitted on this architecture"));
17850 do_neon_ldr_str ();
17851 }
17852}
17853
5287ad62
JB
17854/* "interleave" version also handles non-interleaving register VLD1/VST1
17855 instructions. */
17856
17857static void
17858do_neon_ld_st_interleave (void)
17859{
037e8744 17860 struct neon_type_el et = neon_check_type (1, NS_NULL,
477330fc 17861 N_8 | N_16 | N_32 | N_64);
5287ad62
JB
17862 unsigned alignbits = 0;
17863 unsigned idx;
17864 /* The bits in this table go:
17865 0: register stride of one (0) or two (1)
17866 1,2: register list length, minus one (1, 2, 3, 4).
17867 3,4: <n> in instruction type, minus one (VLD<n> / VST<n>).
17868 We use -1 for invalid entries. */
17869 const int typetable[] =
17870 {
17871 0x7, -1, 0xa, -1, 0x6, -1, 0x2, -1, /* VLD1 / VST1. */
17872 -1, -1, 0x8, 0x9, -1, -1, 0x3, -1, /* VLD2 / VST2. */
17873 -1, -1, -1, -1, 0x4, 0x5, -1, -1, /* VLD3 / VST3. */
17874 -1, -1, -1, -1, -1, -1, 0x0, 0x1 /* VLD4 / VST4. */
17875 };
17876 int typebits;
17877
dcbf9037
JB
17878 if (et.type == NT_invtype)
17879 return;
17880
5287ad62
JB
17881 if (inst.operands[1].immisalign)
17882 switch (inst.operands[1].imm >> 8)
17883 {
17884 case 64: alignbits = 1; break;
17885 case 128:
477330fc 17886 if (NEON_REGLIST_LENGTH (inst.operands[0].imm) != 2
e23c0ad8 17887 && NEON_REGLIST_LENGTH (inst.operands[0].imm) != 4)
477330fc
RM
17888 goto bad_alignment;
17889 alignbits = 2;
17890 break;
5287ad62 17891 case 256:
477330fc
RM
17892 if (NEON_REGLIST_LENGTH (inst.operands[0].imm) != 4)
17893 goto bad_alignment;
17894 alignbits = 3;
17895 break;
5287ad62
JB
17896 default:
17897 bad_alignment:
477330fc
RM
17898 first_error (_("bad alignment"));
17899 return;
5287ad62
JB
17900 }
17901
17902 inst.instruction |= alignbits << 4;
17903 inst.instruction |= neon_logbits (et.size) << 6;
17904
17905 /* Bits [4:6] of the immediate in a list specifier encode register stride
17906 (minus 1) in bit 4, and list length in bits [5:6]. We put the <n> of
17907 VLD<n>/VST<n> in bits [9:8] of the initial bitmask. Suck it out here, look
17908 up the right value for "type" in a table based on this value and the given
17909 list style, then stick it back. */
17910 idx = ((inst.operands[0].imm >> 4) & 7)
477330fc 17911 | (((inst.instruction >> 8) & 3) << 3);
5287ad62
JB
17912
17913 typebits = typetable[idx];
5f4273c7 17914
5287ad62 17915 constraint (typebits == -1, _("bad list type for instruction"));
1d50d57c
WN
17916 constraint (((inst.instruction >> 8) & 3) && et.size == 64,
17917 _("bad element type for instruction"));
5287ad62
JB
17918
17919 inst.instruction &= ~0xf00;
17920 inst.instruction |= typebits << 8;
17921}
17922
17923/* Check alignment is valid for do_neon_ld_st_lane and do_neon_ld_dup.
17924 *DO_ALIGN is set to 1 if the relevant alignment bit should be set, 0
17925 otherwise. The variable arguments are a list of pairs of legal (size, align)
17926 values, terminated with -1. */
17927
17928static int
aa8a0863 17929neon_alignment_bit (int size, int align, int *do_alignment, ...)
5287ad62
JB
17930{
17931 va_list ap;
17932 int result = FAIL, thissize, thisalign;
5f4273c7 17933
5287ad62
JB
17934 if (!inst.operands[1].immisalign)
17935 {
aa8a0863 17936 *do_alignment = 0;
5287ad62
JB
17937 return SUCCESS;
17938 }
5f4273c7 17939
aa8a0863 17940 va_start (ap, do_alignment);
5287ad62
JB
17941
17942 do
17943 {
17944 thissize = va_arg (ap, int);
17945 if (thissize == -1)
477330fc 17946 break;
5287ad62
JB
17947 thisalign = va_arg (ap, int);
17948
17949 if (size == thissize && align == thisalign)
477330fc 17950 result = SUCCESS;
5287ad62
JB
17951 }
17952 while (result != SUCCESS);
17953
17954 va_end (ap);
17955
17956 if (result == SUCCESS)
aa8a0863 17957 *do_alignment = 1;
5287ad62 17958 else
dcbf9037 17959 first_error (_("unsupported alignment for instruction"));
5f4273c7 17960
5287ad62
JB
17961 return result;
17962}
17963
17964static void
17965do_neon_ld_st_lane (void)
17966{
037e8744 17967 struct neon_type_el et = neon_check_type (1, NS_NULL, N_8 | N_16 | N_32);
aa8a0863 17968 int align_good, do_alignment = 0;
5287ad62
JB
17969 int logsize = neon_logbits (et.size);
17970 int align = inst.operands[1].imm >> 8;
17971 int n = (inst.instruction >> 8) & 3;
17972 int max_el = 64 / et.size;
5f4273c7 17973
dcbf9037
JB
17974 if (et.type == NT_invtype)
17975 return;
5f4273c7 17976
5287ad62 17977 constraint (NEON_REGLIST_LENGTH (inst.operands[0].imm) != n + 1,
477330fc 17978 _("bad list length"));
5287ad62 17979 constraint (NEON_LANE (inst.operands[0].imm) >= max_el,
477330fc 17980 _("scalar index out of range"));
5287ad62 17981 constraint (n != 0 && NEON_REG_STRIDE (inst.operands[0].imm) == 2
477330fc
RM
17982 && et.size == 8,
17983 _("stride of 2 unavailable when element size is 8"));
5f4273c7 17984
5287ad62
JB
17985 switch (n)
17986 {
17987 case 0: /* VLD1 / VST1. */
aa8a0863 17988 align_good = neon_alignment_bit (et.size, align, &do_alignment, 16, 16,
477330fc 17989 32, 32, -1);
5287ad62 17990 if (align_good == FAIL)
477330fc 17991 return;
aa8a0863 17992 if (do_alignment)
477330fc
RM
17993 {
17994 unsigned alignbits = 0;
17995 switch (et.size)
17996 {
17997 case 16: alignbits = 0x1; break;
17998 case 32: alignbits = 0x3; break;
17999 default: ;
18000 }
18001 inst.instruction |= alignbits << 4;
18002 }
5287ad62
JB
18003 break;
18004
18005 case 1: /* VLD2 / VST2. */
aa8a0863
TS
18006 align_good = neon_alignment_bit (et.size, align, &do_alignment, 8, 16,
18007 16, 32, 32, 64, -1);
5287ad62 18008 if (align_good == FAIL)
477330fc 18009 return;
aa8a0863 18010 if (do_alignment)
477330fc 18011 inst.instruction |= 1 << 4;
5287ad62
JB
18012 break;
18013
18014 case 2: /* VLD3 / VST3. */
18015 constraint (inst.operands[1].immisalign,
477330fc 18016 _("can't use alignment with this instruction"));
5287ad62
JB
18017 break;
18018
18019 case 3: /* VLD4 / VST4. */
aa8a0863 18020 align_good = neon_alignment_bit (et.size, align, &do_alignment, 8, 32,
477330fc 18021 16, 64, 32, 64, 32, 128, -1);
5287ad62 18022 if (align_good == FAIL)
477330fc 18023 return;
aa8a0863 18024 if (do_alignment)
477330fc
RM
18025 {
18026 unsigned alignbits = 0;
18027 switch (et.size)
18028 {
18029 case 8: alignbits = 0x1; break;
18030 case 16: alignbits = 0x1; break;
18031 case 32: alignbits = (align == 64) ? 0x1 : 0x2; break;
18032 default: ;
18033 }
18034 inst.instruction |= alignbits << 4;
18035 }
5287ad62
JB
18036 break;
18037
18038 default: ;
18039 }
18040
18041 /* Reg stride of 2 is encoded in bit 5 when size==16, bit 6 when size==32. */
18042 if (n != 0 && NEON_REG_STRIDE (inst.operands[0].imm) == 2)
18043 inst.instruction |= 1 << (4 + logsize);
5f4273c7 18044
5287ad62
JB
18045 inst.instruction |= NEON_LANE (inst.operands[0].imm) << (logsize + 5);
18046 inst.instruction |= logsize << 10;
18047}
18048
18049/* Encode single n-element structure to all lanes VLD<n> instructions. */
18050
18051static void
18052do_neon_ld_dup (void)
18053{
037e8744 18054 struct neon_type_el et = neon_check_type (1, NS_NULL, N_8 | N_16 | N_32);
aa8a0863 18055 int align_good, do_alignment = 0;
5287ad62 18056
dcbf9037
JB
18057 if (et.type == NT_invtype)
18058 return;
18059
5287ad62
JB
18060 switch ((inst.instruction >> 8) & 3)
18061 {
18062 case 0: /* VLD1. */
9c2799c2 18063 gas_assert (NEON_REG_STRIDE (inst.operands[0].imm) != 2);
5287ad62 18064 align_good = neon_alignment_bit (et.size, inst.operands[1].imm >> 8,
aa8a0863 18065 &do_alignment, 16, 16, 32, 32, -1);
5287ad62 18066 if (align_good == FAIL)
477330fc 18067 return;
5287ad62 18068 switch (NEON_REGLIST_LENGTH (inst.operands[0].imm))
477330fc
RM
18069 {
18070 case 1: break;
18071 case 2: inst.instruction |= 1 << 5; break;
18072 default: first_error (_("bad list length")); return;
18073 }
5287ad62
JB
18074 inst.instruction |= neon_logbits (et.size) << 6;
18075 break;
18076
18077 case 1: /* VLD2. */
18078 align_good = neon_alignment_bit (et.size, inst.operands[1].imm >> 8,
aa8a0863
TS
18079 &do_alignment, 8, 16, 16, 32, 32, 64,
18080 -1);
5287ad62 18081 if (align_good == FAIL)
477330fc 18082 return;
5287ad62 18083 constraint (NEON_REGLIST_LENGTH (inst.operands[0].imm) != 2,
477330fc 18084 _("bad list length"));
5287ad62 18085 if (NEON_REG_STRIDE (inst.operands[0].imm) == 2)
477330fc 18086 inst.instruction |= 1 << 5;
5287ad62
JB
18087 inst.instruction |= neon_logbits (et.size) << 6;
18088 break;
18089
18090 case 2: /* VLD3. */
18091 constraint (inst.operands[1].immisalign,
477330fc 18092 _("can't use alignment with this instruction"));
5287ad62 18093 constraint (NEON_REGLIST_LENGTH (inst.operands[0].imm) != 3,
477330fc 18094 _("bad list length"));
5287ad62 18095 if (NEON_REG_STRIDE (inst.operands[0].imm) == 2)
477330fc 18096 inst.instruction |= 1 << 5;
5287ad62
JB
18097 inst.instruction |= neon_logbits (et.size) << 6;
18098 break;
18099
18100 case 3: /* VLD4. */
18101 {
477330fc 18102 int align = inst.operands[1].imm >> 8;
aa8a0863 18103 align_good = neon_alignment_bit (et.size, align, &do_alignment, 8, 32,
477330fc
RM
18104 16, 64, 32, 64, 32, 128, -1);
18105 if (align_good == FAIL)
18106 return;
18107 constraint (NEON_REGLIST_LENGTH (inst.operands[0].imm) != 4,
18108 _("bad list length"));
18109 if (NEON_REG_STRIDE (inst.operands[0].imm) == 2)
18110 inst.instruction |= 1 << 5;
18111 if (et.size == 32 && align == 128)
18112 inst.instruction |= 0x3 << 6;
18113 else
18114 inst.instruction |= neon_logbits (et.size) << 6;
5287ad62
JB
18115 }
18116 break;
18117
18118 default: ;
18119 }
18120
aa8a0863 18121 inst.instruction |= do_alignment << 4;
5287ad62
JB
18122}
18123
18124/* Disambiguate VLD<n> and VST<n> instructions, and fill in common bits (those
18125 apart from bits [11:4]. */
18126
18127static void
18128do_neon_ldx_stx (void)
18129{
b1a769ed
DG
18130 if (inst.operands[1].isreg)
18131 constraint (inst.operands[1].reg == REG_PC, BAD_PC);
18132
5287ad62
JB
18133 switch (NEON_LANE (inst.operands[0].imm))
18134 {
18135 case NEON_INTERLEAVE_LANES:
88714cb8 18136 NEON_ENCODE (INTERLV, inst);
5287ad62
JB
18137 do_neon_ld_st_interleave ();
18138 break;
5f4273c7 18139
5287ad62 18140 case NEON_ALL_LANES:
88714cb8 18141 NEON_ENCODE (DUP, inst);
2d51fb74
JB
18142 if (inst.instruction == N_INV)
18143 {
18144 first_error ("only loads support such operands");
18145 break;
18146 }
5287ad62
JB
18147 do_neon_ld_dup ();
18148 break;
5f4273c7 18149
5287ad62 18150 default:
88714cb8 18151 NEON_ENCODE (LANE, inst);
5287ad62
JB
18152 do_neon_ld_st_lane ();
18153 }
18154
18155 /* L bit comes from bit mask. */
18156 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
18157 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
18158 inst.instruction |= inst.operands[1].reg << 16;
5f4273c7 18159
5287ad62
JB
18160 if (inst.operands[1].postind)
18161 {
18162 int postreg = inst.operands[1].imm & 0xf;
18163 constraint (!inst.operands[1].immisreg,
477330fc 18164 _("post-index must be a register"));
5287ad62 18165 constraint (postreg == 0xd || postreg == 0xf,
477330fc 18166 _("bad register for post-index"));
5287ad62
JB
18167 inst.instruction |= postreg;
18168 }
4f2374c7 18169 else
5287ad62 18170 {
4f2374c7 18171 constraint (inst.operands[1].immisreg, BAD_ADDR_MODE);
e2b0ab59
AV
18172 constraint (inst.relocs[0].exp.X_op != O_constant
18173 || inst.relocs[0].exp.X_add_number != 0,
4f2374c7
WN
18174 BAD_ADDR_MODE);
18175
18176 if (inst.operands[1].writeback)
18177 {
18178 inst.instruction |= 0xd;
18179 }
18180 else
18181 inst.instruction |= 0xf;
5287ad62 18182 }
5f4273c7 18183
5287ad62
JB
18184 if (thumb_mode)
18185 inst.instruction |= 0xf9000000;
18186 else
18187 inst.instruction |= 0xf4000000;
18188}
33399f07
MGD
18189
18190/* FP v8. */
18191static void
18192do_vfp_nsyn_fpv8 (enum neon_shape rs)
18193{
a715796b
TG
18194 /* Targets like FPv5-SP-D16 don't support FP v8 instructions with
18195 D register operands. */
18196 if (neon_shape_class[rs] == SC_DOUBLE)
18197 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_armv8),
18198 _(BAD_FPU));
18199
33399f07
MGD
18200 NEON_ENCODE (FPV8, inst);
18201
9db2f6b4
RL
18202 if (rs == NS_FFF || rs == NS_HHH)
18203 {
18204 do_vfp_sp_dyadic ();
18205
18206 /* ARMv8.2 fp16 instruction. */
18207 if (rs == NS_HHH)
18208 do_scalar_fp16_v82_encode ();
18209 }
33399f07
MGD
18210 else
18211 do_vfp_dp_rd_rn_rm ();
18212
18213 if (rs == NS_DDD)
18214 inst.instruction |= 0x100;
18215
18216 inst.instruction |= 0xf0000000;
18217}
18218
18219static void
18220do_vsel (void)
18221{
5ee91343 18222 set_pred_insn_type (OUTSIDE_PRED_INSN);
33399f07
MGD
18223
18224 if (try_vfp_nsyn (3, do_vfp_nsyn_fpv8) != SUCCESS)
18225 first_error (_("invalid instruction shape"));
18226}
18227
73924fbc
MGD
18228static void
18229do_vmaxnm (void)
18230{
5ee91343 18231 set_pred_insn_type (OUTSIDE_PRED_INSN);
73924fbc
MGD
18232
18233 if (try_vfp_nsyn (3, do_vfp_nsyn_fpv8) == SUCCESS)
18234 return;
18235
18236 if (vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH8) == FAIL)
18237 return;
18238
cc933301 18239 neon_dyadic_misc (NT_untyped, N_F_16_32, 0);
73924fbc
MGD
18240}
18241
30bdf752
MGD
18242static void
18243do_vrint_1 (enum neon_cvt_mode mode)
18244{
9db2f6b4 18245 enum neon_shape rs = neon_select_shape (NS_HH, NS_FF, NS_DD, NS_QQ, NS_NULL);
30bdf752
MGD
18246 struct neon_type_el et;
18247
18248 if (rs == NS_NULL)
18249 return;
18250
a715796b
TG
18251 /* Targets like FPv5-SP-D16 don't support FP v8 instructions with
18252 D register operands. */
18253 if (neon_shape_class[rs] == SC_DOUBLE)
18254 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_armv8),
18255 _(BAD_FPU));
18256
9db2f6b4
RL
18257 et = neon_check_type (2, rs, N_EQK | N_VFP, N_F_ALL | N_KEY
18258 | N_VFP);
30bdf752
MGD
18259 if (et.type != NT_invtype)
18260 {
18261 /* VFP encodings. */
18262 if (mode == neon_cvt_mode_a || mode == neon_cvt_mode_n
18263 || mode == neon_cvt_mode_p || mode == neon_cvt_mode_m)
5ee91343 18264 set_pred_insn_type (OUTSIDE_PRED_INSN);
30bdf752
MGD
18265
18266 NEON_ENCODE (FPV8, inst);
9db2f6b4 18267 if (rs == NS_FF || rs == NS_HH)
30bdf752
MGD
18268 do_vfp_sp_monadic ();
18269 else
18270 do_vfp_dp_rd_rm ();
18271
18272 switch (mode)
18273 {
18274 case neon_cvt_mode_r: inst.instruction |= 0x00000000; break;
18275 case neon_cvt_mode_z: inst.instruction |= 0x00000080; break;
18276 case neon_cvt_mode_x: inst.instruction |= 0x00010000; break;
18277 case neon_cvt_mode_a: inst.instruction |= 0xf0000000; break;
18278 case neon_cvt_mode_n: inst.instruction |= 0xf0010000; break;
18279 case neon_cvt_mode_p: inst.instruction |= 0xf0020000; break;
18280 case neon_cvt_mode_m: inst.instruction |= 0xf0030000; break;
18281 default: abort ();
18282 }
18283
18284 inst.instruction |= (rs == NS_DD) << 8;
18285 do_vfp_cond_or_thumb ();
9db2f6b4
RL
18286
18287 /* ARMv8.2 fp16 vrint instruction. */
18288 if (rs == NS_HH)
18289 do_scalar_fp16_v82_encode ();
30bdf752
MGD
18290 }
18291 else
18292 {
18293 /* Neon encodings (or something broken...). */
18294 inst.error = NULL;
cc933301 18295 et = neon_check_type (2, rs, N_EQK, N_F_16_32 | N_KEY);
30bdf752
MGD
18296
18297 if (et.type == NT_invtype)
18298 return;
18299
5ee91343 18300 set_pred_insn_type (OUTSIDE_PRED_INSN);
30bdf752
MGD
18301 NEON_ENCODE (FLOAT, inst);
18302
18303 if (vfp_or_neon_is_neon (NEON_CHECK_CC | NEON_CHECK_ARCH8) == FAIL)
18304 return;
18305
18306 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
18307 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
18308 inst.instruction |= LOW4 (inst.operands[1].reg);
18309 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
18310 inst.instruction |= neon_quad (rs) << 6;
cc933301
JW
18311 /* Mask off the original size bits and reencode them. */
18312 inst.instruction = ((inst.instruction & 0xfff3ffff)
18313 | neon_logbits (et.size) << 18);
18314
30bdf752
MGD
18315 switch (mode)
18316 {
18317 case neon_cvt_mode_z: inst.instruction |= 3 << 7; break;
18318 case neon_cvt_mode_x: inst.instruction |= 1 << 7; break;
18319 case neon_cvt_mode_a: inst.instruction |= 2 << 7; break;
18320 case neon_cvt_mode_n: inst.instruction |= 0 << 7; break;
18321 case neon_cvt_mode_p: inst.instruction |= 7 << 7; break;
18322 case neon_cvt_mode_m: inst.instruction |= 5 << 7; break;
18323 case neon_cvt_mode_r: inst.error = _("invalid rounding mode"); break;
18324 default: abort ();
18325 }
18326
18327 if (thumb_mode)
18328 inst.instruction |= 0xfc000000;
18329 else
18330 inst.instruction |= 0xf0000000;
18331 }
18332}
18333
18334static void
18335do_vrintx (void)
18336{
18337 do_vrint_1 (neon_cvt_mode_x);
18338}
18339
18340static void
18341do_vrintz (void)
18342{
18343 do_vrint_1 (neon_cvt_mode_z);
18344}
18345
18346static void
18347do_vrintr (void)
18348{
18349 do_vrint_1 (neon_cvt_mode_r);
18350}
18351
18352static void
18353do_vrinta (void)
18354{
18355 do_vrint_1 (neon_cvt_mode_a);
18356}
18357
18358static void
18359do_vrintn (void)
18360{
18361 do_vrint_1 (neon_cvt_mode_n);
18362}
18363
18364static void
18365do_vrintp (void)
18366{
18367 do_vrint_1 (neon_cvt_mode_p);
18368}
18369
18370static void
18371do_vrintm (void)
18372{
18373 do_vrint_1 (neon_cvt_mode_m);
18374}
18375
c28eeff2
SN
18376static unsigned
18377neon_scalar_for_vcmla (unsigned opnd, unsigned elsize)
18378{
18379 unsigned regno = NEON_SCALAR_REG (opnd);
18380 unsigned elno = NEON_SCALAR_INDEX (opnd);
18381
18382 if (elsize == 16 && elno < 2 && regno < 16)
18383 return regno | (elno << 4);
18384 else if (elsize == 32 && elno == 0)
18385 return regno;
18386
18387 first_error (_("scalar out of range"));
18388 return 0;
18389}
18390
18391static void
18392do_vcmla (void)
18393{
18394 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_neon_ext_armv8),
18395 _(BAD_FPU));
e2b0ab59
AV
18396 constraint (inst.relocs[0].exp.X_op != O_constant,
18397 _("expression too complex"));
18398 unsigned rot = inst.relocs[0].exp.X_add_number;
c28eeff2
SN
18399 constraint (rot != 0 && rot != 90 && rot != 180 && rot != 270,
18400 _("immediate out of range"));
18401 rot /= 90;
18402 if (inst.operands[2].isscalar)
18403 {
18404 enum neon_shape rs = neon_select_shape (NS_DDSI, NS_QQSI, NS_NULL);
18405 unsigned size = neon_check_type (3, rs, N_EQK, N_EQK,
18406 N_KEY | N_F16 | N_F32).size;
18407 unsigned m = neon_scalar_for_vcmla (inst.operands[2].reg, size);
18408 inst.is_neon = 1;
18409 inst.instruction = 0xfe000800;
18410 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
18411 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
18412 inst.instruction |= LOW4 (inst.operands[1].reg) << 16;
18413 inst.instruction |= HI1 (inst.operands[1].reg) << 7;
18414 inst.instruction |= LOW4 (m);
18415 inst.instruction |= HI1 (m) << 5;
18416 inst.instruction |= neon_quad (rs) << 6;
18417 inst.instruction |= rot << 20;
18418 inst.instruction |= (size == 32) << 23;
18419 }
18420 else
18421 {
18422 enum neon_shape rs = neon_select_shape (NS_DDDI, NS_QQQI, NS_NULL);
18423 unsigned size = neon_check_type (3, rs, N_EQK, N_EQK,
18424 N_KEY | N_F16 | N_F32).size;
18425 neon_three_same (neon_quad (rs), 0, -1);
18426 inst.instruction &= 0x00ffffff; /* Undo neon_dp_fixup. */
18427 inst.instruction |= 0xfc200800;
18428 inst.instruction |= rot << 23;
18429 inst.instruction |= (size == 32) << 20;
18430 }
18431}
18432
18433static void
18434do_vcadd (void)
18435{
18436 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_neon_ext_armv8),
18437 _(BAD_FPU));
e2b0ab59
AV
18438 constraint (inst.relocs[0].exp.X_op != O_constant,
18439 _("expression too complex"));
18440 unsigned rot = inst.relocs[0].exp.X_add_number;
c28eeff2
SN
18441 constraint (rot != 90 && rot != 270, _("immediate out of range"));
18442 enum neon_shape rs = neon_select_shape (NS_DDDI, NS_QQQI, NS_NULL);
18443 unsigned size = neon_check_type (3, rs, N_EQK, N_EQK,
18444 N_KEY | N_F16 | N_F32).size;
18445 neon_three_same (neon_quad (rs), 0, -1);
18446 inst.instruction &= 0x00ffffff; /* Undo neon_dp_fixup. */
18447 inst.instruction |= 0xfc800800;
18448 inst.instruction |= (rot == 270) << 24;
18449 inst.instruction |= (size == 32) << 20;
18450}
18451
c604a79a
JW
18452/* Dot Product instructions encoding support. */
18453
18454static void
18455do_neon_dotproduct (int unsigned_p)
18456{
18457 enum neon_shape rs;
18458 unsigned scalar_oprd2 = 0;
18459 int high8;
18460
18461 if (inst.cond != COND_ALWAYS)
18462 as_warn (_("Dot Product instructions cannot be conditional, the behaviour "
18463 "is UNPREDICTABLE"));
18464
18465 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_neon_ext_armv8),
18466 _(BAD_FPU));
18467
18468 /* Dot Product instructions are in three-same D/Q register format or the third
18469 operand can be a scalar index register. */
18470 if (inst.operands[2].isscalar)
18471 {
18472 scalar_oprd2 = neon_scalar_for_mul (inst.operands[2].reg, 32);
18473 high8 = 0xfe000000;
18474 rs = neon_select_shape (NS_DDS, NS_QQS, NS_NULL);
18475 }
18476 else
18477 {
18478 high8 = 0xfc000000;
18479 rs = neon_select_shape (NS_DDD, NS_QQQ, NS_NULL);
18480 }
18481
18482 if (unsigned_p)
18483 neon_check_type (3, rs, N_EQK, N_EQK, N_KEY | N_U8);
18484 else
18485 neon_check_type (3, rs, N_EQK, N_EQK, N_KEY | N_S8);
18486
18487 /* The "U" bit in traditional Three Same encoding is fixed to 0 for Dot
18488 Product instruction, so we pass 0 as the "ubit" parameter. And the
18489 "Size" field are fixed to 0x2, so we pass 32 as the "size" parameter. */
18490 neon_three_same (neon_quad (rs), 0, 32);
18491
18492 /* Undo neon_dp_fixup. Dot Product instructions are using a slightly
18493 different NEON three-same encoding. */
18494 inst.instruction &= 0x00ffffff;
18495 inst.instruction |= high8;
18496 /* Encode 'U' bit which indicates signedness. */
18497 inst.instruction |= (unsigned_p ? 1 : 0) << 4;
18498 /* Re-encode operand2 if it's indexed scalar operand. What has been encoded
18499 from inst.operand[2].reg in neon_three_same is GAS's internal encoding, not
18500 the instruction encoding. */
18501 if (inst.operands[2].isscalar)
18502 {
18503 inst.instruction &= 0xffffffd0;
18504 inst.instruction |= LOW4 (scalar_oprd2);
18505 inst.instruction |= HI1 (scalar_oprd2) << 5;
18506 }
18507}
18508
18509/* Dot Product instructions for signed integer. */
18510
18511static void
18512do_neon_dotproduct_s (void)
18513{
18514 return do_neon_dotproduct (0);
18515}
18516
18517/* Dot Product instructions for unsigned integer. */
18518
18519static void
18520do_neon_dotproduct_u (void)
18521{
18522 return do_neon_dotproduct (1);
18523}
18524
91ff7894
MGD
18525/* Crypto v1 instructions. */
18526static void
18527do_crypto_2op_1 (unsigned elttype, int op)
18528{
5ee91343 18529 set_pred_insn_type (OUTSIDE_PRED_INSN);
91ff7894
MGD
18530
18531 if (neon_check_type (2, NS_QQ, N_EQK | N_UNT, elttype | N_UNT | N_KEY).type
18532 == NT_invtype)
18533 return;
18534
18535 inst.error = NULL;
18536
18537 NEON_ENCODE (INTEGER, inst);
18538 inst.instruction |= LOW4 (inst.operands[0].reg) << 12;
18539 inst.instruction |= HI1 (inst.operands[0].reg) << 22;
18540 inst.instruction |= LOW4 (inst.operands[1].reg);
18541 inst.instruction |= HI1 (inst.operands[1].reg) << 5;
18542 if (op != -1)
18543 inst.instruction |= op << 6;
18544
18545 if (thumb_mode)
18546 inst.instruction |= 0xfc000000;
18547 else
18548 inst.instruction |= 0xf0000000;
18549}
18550
48adcd8e
MGD
18551static void
18552do_crypto_3op_1 (int u, int op)
18553{
5ee91343 18554 set_pred_insn_type (OUTSIDE_PRED_INSN);
48adcd8e
MGD
18555
18556 if (neon_check_type (3, NS_QQQ, N_EQK | N_UNT, N_EQK | N_UNT,
18557 N_32 | N_UNT | N_KEY).type == NT_invtype)
18558 return;
18559
18560 inst.error = NULL;
18561
18562 NEON_ENCODE (INTEGER, inst);
18563 neon_three_same (1, u, 8 << op);
18564}
18565
91ff7894
MGD
18566static void
18567do_aese (void)
18568{
18569 do_crypto_2op_1 (N_8, 0);
18570}
18571
18572static void
18573do_aesd (void)
18574{
18575 do_crypto_2op_1 (N_8, 1);
18576}
18577
18578static void
18579do_aesmc (void)
18580{
18581 do_crypto_2op_1 (N_8, 2);
18582}
18583
18584static void
18585do_aesimc (void)
18586{
18587 do_crypto_2op_1 (N_8, 3);
18588}
18589
48adcd8e
MGD
18590static void
18591do_sha1c (void)
18592{
18593 do_crypto_3op_1 (0, 0);
18594}
18595
18596static void
18597do_sha1p (void)
18598{
18599 do_crypto_3op_1 (0, 1);
18600}
18601
18602static void
18603do_sha1m (void)
18604{
18605 do_crypto_3op_1 (0, 2);
18606}
18607
18608static void
18609do_sha1su0 (void)
18610{
18611 do_crypto_3op_1 (0, 3);
18612}
91ff7894 18613
48adcd8e
MGD
18614static void
18615do_sha256h (void)
18616{
18617 do_crypto_3op_1 (1, 0);
18618}
18619
18620static void
18621do_sha256h2 (void)
18622{
18623 do_crypto_3op_1 (1, 1);
18624}
18625
18626static void
18627do_sha256su1 (void)
18628{
18629 do_crypto_3op_1 (1, 2);
18630}
3c9017d2
MGD
18631
18632static void
18633do_sha1h (void)
18634{
18635 do_crypto_2op_1 (N_32, -1);
18636}
18637
18638static void
18639do_sha1su1 (void)
18640{
18641 do_crypto_2op_1 (N_32, 0);
18642}
18643
18644static void
18645do_sha256su0 (void)
18646{
18647 do_crypto_2op_1 (N_32, 1);
18648}
dd5181d5
KT
18649
18650static void
18651do_crc32_1 (unsigned int poly, unsigned int sz)
18652{
18653 unsigned int Rd = inst.operands[0].reg;
18654 unsigned int Rn = inst.operands[1].reg;
18655 unsigned int Rm = inst.operands[2].reg;
18656
5ee91343 18657 set_pred_insn_type (OUTSIDE_PRED_INSN);
dd5181d5
KT
18658 inst.instruction |= LOW4 (Rd) << (thumb_mode ? 8 : 12);
18659 inst.instruction |= LOW4 (Rn) << 16;
18660 inst.instruction |= LOW4 (Rm);
18661 inst.instruction |= sz << (thumb_mode ? 4 : 21);
18662 inst.instruction |= poly << (thumb_mode ? 20 : 9);
18663
18664 if (Rd == REG_PC || Rn == REG_PC || Rm == REG_PC)
18665 as_warn (UNPRED_REG ("r15"));
dd5181d5
KT
18666}
18667
18668static void
18669do_crc32b (void)
18670{
18671 do_crc32_1 (0, 0);
18672}
18673
18674static void
18675do_crc32h (void)
18676{
18677 do_crc32_1 (0, 1);
18678}
18679
18680static void
18681do_crc32w (void)
18682{
18683 do_crc32_1 (0, 2);
18684}
18685
18686static void
18687do_crc32cb (void)
18688{
18689 do_crc32_1 (1, 0);
18690}
18691
18692static void
18693do_crc32ch (void)
18694{
18695 do_crc32_1 (1, 1);
18696}
18697
18698static void
18699do_crc32cw (void)
18700{
18701 do_crc32_1 (1, 2);
18702}
18703
49e8a725
SN
18704static void
18705do_vjcvt (void)
18706{
18707 constraint (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_vfp_ext_armv8),
18708 _(BAD_FPU));
18709 neon_check_type (2, NS_FD, N_S32, N_F64);
18710 do_vfp_sp_dp_cvt ();
18711 do_vfp_cond_or_thumb ();
18712}
18713
5287ad62
JB
18714\f
18715/* Overall per-instruction processing. */
18716
18717/* We need to be able to fix up arbitrary expressions in some statements.
18718 This is so that we can handle symbols that are an arbitrary distance from
18719 the pc. The most common cases are of the form ((+/-sym -/+ . - 8) & mask),
18720 which returns part of an address in a form which will be valid for
18721 a data instruction. We do this by pushing the expression into a symbol
18722 in the expr_section, and creating a fix for that. */
18723
18724static void
18725fix_new_arm (fragS * frag,
18726 int where,
18727 short int size,
18728 expressionS * exp,
18729 int pc_rel,
18730 int reloc)
18731{
18732 fixS * new_fix;
18733
18734 switch (exp->X_op)
18735 {
18736 case O_constant:
6e7ce2cd
PB
18737 if (pc_rel)
18738 {
18739 /* Create an absolute valued symbol, so we have something to
477330fc
RM
18740 refer to in the object file. Unfortunately for us, gas's
18741 generic expression parsing will already have folded out
18742 any use of .set foo/.type foo %function that may have
18743 been used to set type information of the target location,
18744 that's being specified symbolically. We have to presume
18745 the user knows what they are doing. */
6e7ce2cd
PB
18746 char name[16 + 8];
18747 symbolS *symbol;
18748
18749 sprintf (name, "*ABS*0x%lx", (unsigned long)exp->X_add_number);
18750
18751 symbol = symbol_find_or_make (name);
18752 S_SET_SEGMENT (symbol, absolute_section);
18753 symbol_set_frag (symbol, &zero_address_frag);
18754 S_SET_VALUE (symbol, exp->X_add_number);
18755 exp->X_op = O_symbol;
18756 exp->X_add_symbol = symbol;
18757 exp->X_add_number = 0;
18758 }
18759 /* FALLTHROUGH */
5287ad62
JB
18760 case O_symbol:
18761 case O_add:
18762 case O_subtract:
21d799b5 18763 new_fix = fix_new_exp (frag, where, size, exp, pc_rel,
477330fc 18764 (enum bfd_reloc_code_real) reloc);
5287ad62
JB
18765 break;
18766
18767 default:
21d799b5 18768 new_fix = (fixS *) fix_new (frag, where, size, make_expr_symbol (exp), 0,
477330fc 18769 pc_rel, (enum bfd_reloc_code_real) reloc);
5287ad62
JB
18770 break;
18771 }
18772
18773 /* Mark whether the fix is to a THUMB instruction, or an ARM
18774 instruction. */
18775 new_fix->tc_fix_data = thumb_mode;
18776}
18777
18778/* Create a frg for an instruction requiring relaxation. */
18779static void
18780output_relax_insn (void)
18781{
18782 char * to;
18783 symbolS *sym;
0110f2b8
PB
18784 int offset;
18785
6e1cb1a6
PB
18786 /* The size of the instruction is unknown, so tie the debug info to the
18787 start of the instruction. */
18788 dwarf2_emit_insn (0);
6e1cb1a6 18789
e2b0ab59 18790 switch (inst.relocs[0].exp.X_op)
0110f2b8
PB
18791 {
18792 case O_symbol:
e2b0ab59
AV
18793 sym = inst.relocs[0].exp.X_add_symbol;
18794 offset = inst.relocs[0].exp.X_add_number;
0110f2b8
PB
18795 break;
18796 case O_constant:
18797 sym = NULL;
e2b0ab59 18798 offset = inst.relocs[0].exp.X_add_number;
0110f2b8
PB
18799 break;
18800 default:
e2b0ab59 18801 sym = make_expr_symbol (&inst.relocs[0].exp);
0110f2b8
PB
18802 offset = 0;
18803 break;
18804 }
18805 to = frag_var (rs_machine_dependent, INSN_SIZE, THUMB_SIZE,
18806 inst.relax, sym, offset, NULL/*offset, opcode*/);
18807 md_number_to_chars (to, inst.instruction, THUMB_SIZE);
0110f2b8
PB
18808}
18809
18810/* Write a 32-bit thumb instruction to buf. */
18811static void
18812put_thumb32_insn (char * buf, unsigned long insn)
18813{
18814 md_number_to_chars (buf, insn >> 16, THUMB_SIZE);
18815 md_number_to_chars (buf + THUMB_SIZE, insn, THUMB_SIZE);
18816}
18817
b99bd4ef 18818static void
c19d1205 18819output_inst (const char * str)
b99bd4ef 18820{
c19d1205 18821 char * to = NULL;
b99bd4ef 18822
c19d1205 18823 if (inst.error)
b99bd4ef 18824 {
c19d1205 18825 as_bad ("%s -- `%s'", inst.error, str);
b99bd4ef
NC
18826 return;
18827 }
5f4273c7
NC
18828 if (inst.relax)
18829 {
18830 output_relax_insn ();
0110f2b8 18831 return;
5f4273c7 18832 }
c19d1205
ZW
18833 if (inst.size == 0)
18834 return;
b99bd4ef 18835
c19d1205 18836 to = frag_more (inst.size);
8dc2430f
NC
18837 /* PR 9814: Record the thumb mode into the current frag so that we know
18838 what type of NOP padding to use, if necessary. We override any previous
18839 setting so that if the mode has changed then the NOPS that we use will
18840 match the encoding of the last instruction in the frag. */
cd000bff 18841 frag_now->tc_frag_data.thumb_mode = thumb_mode | MODE_RECORDED;
c19d1205
ZW
18842
18843 if (thumb_mode && (inst.size > THUMB_SIZE))
b99bd4ef 18844 {
9c2799c2 18845 gas_assert (inst.size == (2 * THUMB_SIZE));
0110f2b8 18846 put_thumb32_insn (to, inst.instruction);
b99bd4ef 18847 }
c19d1205 18848 else if (inst.size > INSN_SIZE)
b99bd4ef 18849 {
9c2799c2 18850 gas_assert (inst.size == (2 * INSN_SIZE));
c19d1205
ZW
18851 md_number_to_chars (to, inst.instruction, INSN_SIZE);
18852 md_number_to_chars (to + INSN_SIZE, inst.instruction, INSN_SIZE);
b99bd4ef 18853 }
c19d1205
ZW
18854 else
18855 md_number_to_chars (to, inst.instruction, inst.size);
b99bd4ef 18856
e2b0ab59
AV
18857 int r;
18858 for (r = 0; r < ARM_IT_MAX_RELOCS; r++)
18859 {
18860 if (inst.relocs[r].type != BFD_RELOC_UNUSED)
18861 fix_new_arm (frag_now, to - frag_now->fr_literal,
18862 inst.size, & inst.relocs[r].exp, inst.relocs[r].pc_rel,
18863 inst.relocs[r].type);
18864 }
b99bd4ef 18865
c19d1205 18866 dwarf2_emit_insn (inst.size);
c19d1205 18867}
b99bd4ef 18868
e07e6e58
NC
18869static char *
18870output_it_inst (int cond, int mask, char * to)
18871{
18872 unsigned long instruction = 0xbf00;
18873
18874 mask &= 0xf;
18875 instruction |= mask;
18876 instruction |= cond << 4;
18877
18878 if (to == NULL)
18879 {
18880 to = frag_more (2);
18881#ifdef OBJ_ELF
18882 dwarf2_emit_insn (2);
18883#endif
18884 }
18885
18886 md_number_to_chars (to, instruction, 2);
18887
18888 return to;
18889}
18890
c19d1205
ZW
18891/* Tag values used in struct asm_opcode's tag field. */
18892enum opcode_tag
18893{
18894 OT_unconditional, /* Instruction cannot be conditionalized.
18895 The ARM condition field is still 0xE. */
18896 OT_unconditionalF, /* Instruction cannot be conditionalized
18897 and carries 0xF in its ARM condition field. */
18898 OT_csuffix, /* Instruction takes a conditional suffix. */
5ee91343
AV
18899 OT_csuffixF, /* Some forms of the instruction take a scalar
18900 conditional suffix, others place 0xF where the
18901 condition field would be, others take a vector
18902 conditional suffix. */
c19d1205
ZW
18903 OT_cinfix3, /* Instruction takes a conditional infix,
18904 beginning at character index 3. (In
18905 unified mode, it becomes a suffix.) */
088fa78e
KH
18906 OT_cinfix3_deprecated, /* The same as OT_cinfix3. This is used for
18907 tsts, cmps, cmns, and teqs. */
e3cb604e
PB
18908 OT_cinfix3_legacy, /* Legacy instruction takes a conditional infix at
18909 character index 3, even in unified mode. Used for
18910 legacy instructions where suffix and infix forms
18911 may be ambiguous. */
c19d1205 18912 OT_csuf_or_in3, /* Instruction takes either a conditional
e3cb604e 18913 suffix or an infix at character index 3. */
c19d1205
ZW
18914 OT_odd_infix_unc, /* This is the unconditional variant of an
18915 instruction that takes a conditional infix
18916 at an unusual position. In unified mode,
18917 this variant will accept a suffix. */
18918 OT_odd_infix_0 /* Values greater than or equal to OT_odd_infix_0
18919 are the conditional variants of instructions that
18920 take conditional infixes in unusual positions.
18921 The infix appears at character index
18922 (tag - OT_odd_infix_0). These are not accepted
18923 in unified mode. */
18924};
b99bd4ef 18925
c19d1205
ZW
18926/* Subroutine of md_assemble, responsible for looking up the primary
18927 opcode from the mnemonic the user wrote. STR points to the
18928 beginning of the mnemonic.
18929
18930 This is not simply a hash table lookup, because of conditional
18931 variants. Most instructions have conditional variants, which are
18932 expressed with a _conditional affix_ to the mnemonic. If we were
18933 to encode each conditional variant as a literal string in the opcode
18934 table, it would have approximately 20,000 entries.
18935
18936 Most mnemonics take this affix as a suffix, and in unified syntax,
18937 'most' is upgraded to 'all'. However, in the divided syntax, some
18938 instructions take the affix as an infix, notably the s-variants of
18939 the arithmetic instructions. Of those instructions, all but six
18940 have the infix appear after the third character of the mnemonic.
18941
18942 Accordingly, the algorithm for looking up primary opcodes given
18943 an identifier is:
18944
18945 1. Look up the identifier in the opcode table.
18946 If we find a match, go to step U.
18947
18948 2. Look up the last two characters of the identifier in the
18949 conditions table. If we find a match, look up the first N-2
18950 characters of the identifier in the opcode table. If we
18951 find a match, go to step CE.
18952
18953 3. Look up the fourth and fifth characters of the identifier in
18954 the conditions table. If we find a match, extract those
18955 characters from the identifier, and look up the remaining
18956 characters in the opcode table. If we find a match, go
18957 to step CM.
18958
18959 4. Fail.
18960
18961 U. Examine the tag field of the opcode structure, in case this is
18962 one of the six instructions with its conditional infix in an
18963 unusual place. If it is, the tag tells us where to find the
18964 infix; look it up in the conditions table and set inst.cond
18965 accordingly. Otherwise, this is an unconditional instruction.
18966 Again set inst.cond accordingly. Return the opcode structure.
18967
18968 CE. Examine the tag field to make sure this is an instruction that
18969 should receive a conditional suffix. If it is not, fail.
18970 Otherwise, set inst.cond from the suffix we already looked up,
18971 and return the opcode structure.
18972
18973 CM. Examine the tag field to make sure this is an instruction that
18974 should receive a conditional infix after the third character.
18975 If it is not, fail. Otherwise, undo the edits to the current
18976 line of input and proceed as for case CE. */
18977
18978static const struct asm_opcode *
18979opcode_lookup (char **str)
18980{
18981 char *end, *base;
18982 char *affix;
18983 const struct asm_opcode *opcode;
18984 const struct asm_cond *cond;
e3cb604e 18985 char save[2];
c19d1205
ZW
18986
18987 /* Scan up to the end of the mnemonic, which must end in white space,
721a8186 18988 '.' (in unified mode, or for Neon/VFP instructions), or end of string. */
c19d1205 18989 for (base = end = *str; *end != '\0'; end++)
721a8186 18990 if (*end == ' ' || *end == '.')
c19d1205 18991 break;
b99bd4ef 18992
c19d1205 18993 if (end == base)
c921be7d 18994 return NULL;
b99bd4ef 18995
5287ad62 18996 /* Handle a possible width suffix and/or Neon type suffix. */
c19d1205 18997 if (end[0] == '.')
b99bd4ef 18998 {
5287ad62 18999 int offset = 2;
5f4273c7 19000
267d2029 19001 /* The .w and .n suffixes are only valid if the unified syntax is in
477330fc 19002 use. */
267d2029 19003 if (unified_syntax && end[1] == 'w')
c19d1205 19004 inst.size_req = 4;
267d2029 19005 else if (unified_syntax && end[1] == 'n')
c19d1205
ZW
19006 inst.size_req = 2;
19007 else
477330fc 19008 offset = 0;
5287ad62
JB
19009
19010 inst.vectype.elems = 0;
19011
19012 *str = end + offset;
b99bd4ef 19013
5f4273c7 19014 if (end[offset] == '.')
5287ad62 19015 {
267d2029 19016 /* See if we have a Neon type suffix (possible in either unified or
477330fc
RM
19017 non-unified ARM syntax mode). */
19018 if (parse_neon_type (&inst.vectype, str) == FAIL)
c921be7d 19019 return NULL;
477330fc 19020 }
5287ad62 19021 else if (end[offset] != '\0' && end[offset] != ' ')
477330fc 19022 return NULL;
b99bd4ef 19023 }
c19d1205
ZW
19024 else
19025 *str = end;
b99bd4ef 19026
c19d1205 19027 /* Look for unaffixed or special-case affixed mnemonic. */
21d799b5 19028 opcode = (const struct asm_opcode *) hash_find_n (arm_ops_hsh, base,
477330fc 19029 end - base);
c19d1205 19030 if (opcode)
b99bd4ef 19031 {
c19d1205
ZW
19032 /* step U */
19033 if (opcode->tag < OT_odd_infix_0)
b99bd4ef 19034 {
c19d1205
ZW
19035 inst.cond = COND_ALWAYS;
19036 return opcode;
b99bd4ef 19037 }
b99bd4ef 19038
278df34e 19039 if (warn_on_deprecated && unified_syntax)
5c3696f8 19040 as_tsktsk (_("conditional infixes are deprecated in unified syntax"));
c19d1205 19041 affix = base + (opcode->tag - OT_odd_infix_0);
21d799b5 19042 cond = (const struct asm_cond *) hash_find_n (arm_cond_hsh, affix, 2);
9c2799c2 19043 gas_assert (cond);
b99bd4ef 19044
c19d1205
ZW
19045 inst.cond = cond->value;
19046 return opcode;
19047 }
5ee91343
AV
19048 if (ARM_CPU_HAS_FEATURE (cpu_variant, mve_ext))
19049 {
19050 /* Cannot have a conditional suffix on a mnemonic of less than a character.
19051 */
19052 if (end - base < 2)
19053 return NULL;
19054 affix = end - 1;
19055 cond = (const struct asm_cond *) hash_find_n (arm_vcond_hsh, affix, 1);
19056 opcode = (const struct asm_opcode *) hash_find_n (arm_ops_hsh, base,
19057 affix - base);
19058 /* If this opcode can not be vector predicated then don't accept it with a
19059 vector predication code. */
19060 if (opcode && !opcode->mayBeVecPred)
19061 opcode = NULL;
19062 }
19063 if (!opcode || !cond)
19064 {
19065 /* Cannot have a conditional suffix on a mnemonic of less than two
19066 characters. */
19067 if (end - base < 3)
19068 return NULL;
b99bd4ef 19069
5ee91343
AV
19070 /* Look for suffixed mnemonic. */
19071 affix = end - 2;
19072 cond = (const struct asm_cond *) hash_find_n (arm_cond_hsh, affix, 2);
19073 opcode = (const struct asm_opcode *) hash_find_n (arm_ops_hsh, base,
19074 affix - base);
19075 }
b99bd4ef 19076
c19d1205
ZW
19077 if (opcode && cond)
19078 {
19079 /* step CE */
19080 switch (opcode->tag)
19081 {
e3cb604e
PB
19082 case OT_cinfix3_legacy:
19083 /* Ignore conditional suffixes matched on infix only mnemonics. */
19084 break;
19085
c19d1205 19086 case OT_cinfix3:
088fa78e 19087 case OT_cinfix3_deprecated:
c19d1205
ZW
19088 case OT_odd_infix_unc:
19089 if (!unified_syntax)
0198d5e6 19090 return NULL;
1a0670f3 19091 /* Fall through. */
c19d1205
ZW
19092
19093 case OT_csuffix:
477330fc 19094 case OT_csuffixF:
c19d1205
ZW
19095 case OT_csuf_or_in3:
19096 inst.cond = cond->value;
19097 return opcode;
19098
19099 case OT_unconditional:
19100 case OT_unconditionalF:
dfa9f0d5 19101 if (thumb_mode)
c921be7d 19102 inst.cond = cond->value;
dfa9f0d5
PB
19103 else
19104 {
c921be7d 19105 /* Delayed diagnostic. */
dfa9f0d5
PB
19106 inst.error = BAD_COND;
19107 inst.cond = COND_ALWAYS;
19108 }
c19d1205 19109 return opcode;
b99bd4ef 19110
c19d1205 19111 default:
c921be7d 19112 return NULL;
c19d1205
ZW
19113 }
19114 }
b99bd4ef 19115
c19d1205
ZW
19116 /* Cannot have a usual-position infix on a mnemonic of less than
19117 six characters (five would be a suffix). */
19118 if (end - base < 6)
c921be7d 19119 return NULL;
b99bd4ef 19120
c19d1205
ZW
19121 /* Look for infixed mnemonic in the usual position. */
19122 affix = base + 3;
21d799b5 19123 cond = (const struct asm_cond *) hash_find_n (arm_cond_hsh, affix, 2);
e3cb604e 19124 if (!cond)
c921be7d 19125 return NULL;
e3cb604e
PB
19126
19127 memcpy (save, affix, 2);
19128 memmove (affix, affix + 2, (end - affix) - 2);
21d799b5 19129 opcode = (const struct asm_opcode *) hash_find_n (arm_ops_hsh, base,
477330fc 19130 (end - base) - 2);
e3cb604e
PB
19131 memmove (affix + 2, affix, (end - affix) - 2);
19132 memcpy (affix, save, 2);
19133
088fa78e
KH
19134 if (opcode
19135 && (opcode->tag == OT_cinfix3
19136 || opcode->tag == OT_cinfix3_deprecated
19137 || opcode->tag == OT_csuf_or_in3
19138 || opcode->tag == OT_cinfix3_legacy))
b99bd4ef 19139 {
c921be7d 19140 /* Step CM. */
278df34e 19141 if (warn_on_deprecated && unified_syntax
088fa78e
KH
19142 && (opcode->tag == OT_cinfix3
19143 || opcode->tag == OT_cinfix3_deprecated))
5c3696f8 19144 as_tsktsk (_("conditional infixes are deprecated in unified syntax"));
c19d1205
ZW
19145
19146 inst.cond = cond->value;
19147 return opcode;
b99bd4ef
NC
19148 }
19149
c921be7d 19150 return NULL;
b99bd4ef
NC
19151}
19152
e07e6e58
NC
19153/* This function generates an initial IT instruction, leaving its block
19154 virtually open for the new instructions. Eventually,
5ee91343 19155 the mask will be updated by now_pred_add_mask () each time
e07e6e58
NC
19156 a new instruction needs to be included in the IT block.
19157 Finally, the block is closed with close_automatic_it_block ().
19158 The block closure can be requested either from md_assemble (),
19159 a tencode (), or due to a label hook. */
19160
19161static void
19162new_automatic_it_block (int cond)
19163{
5ee91343
AV
19164 now_pred.state = AUTOMATIC_PRED_BLOCK;
19165 now_pred.mask = 0x18;
19166 now_pred.cc = cond;
19167 now_pred.block_length = 1;
cd000bff 19168 mapping_state (MAP_THUMB);
5ee91343
AV
19169 now_pred.insn = output_it_inst (cond, now_pred.mask, NULL);
19170 now_pred.warn_deprecated = FALSE;
19171 now_pred.insn_cond = TRUE;
e07e6e58
NC
19172}
19173
19174/* Close an automatic IT block.
19175 See comments in new_automatic_it_block (). */
19176
19177static void
19178close_automatic_it_block (void)
19179{
5ee91343
AV
19180 now_pred.mask = 0x10;
19181 now_pred.block_length = 0;
e07e6e58
NC
19182}
19183
19184/* Update the mask of the current automatically-generated IT
19185 instruction. See comments in new_automatic_it_block (). */
19186
19187static void
5ee91343 19188now_pred_add_mask (int cond)
e07e6e58
NC
19189{
19190#define CLEAR_BIT(value, nbit) ((value) & ~(1 << (nbit)))
19191#define SET_BIT_VALUE(value, bitvalue, nbit) (CLEAR_BIT (value, nbit) \
477330fc 19192 | ((bitvalue) << (nbit)))
e07e6e58 19193 const int resulting_bit = (cond & 1);
c921be7d 19194
5ee91343
AV
19195 now_pred.mask &= 0xf;
19196 now_pred.mask = SET_BIT_VALUE (now_pred.mask,
477330fc 19197 resulting_bit,
5ee91343
AV
19198 (5 - now_pred.block_length));
19199 now_pred.mask = SET_BIT_VALUE (now_pred.mask,
477330fc 19200 1,
5ee91343
AV
19201 ((5 - now_pred.block_length) - 1));
19202 output_it_inst (now_pred.cc, now_pred.mask, now_pred.insn);
e07e6e58
NC
19203
19204#undef CLEAR_BIT
19205#undef SET_BIT_VALUE
e07e6e58
NC
19206}
19207
19208/* The IT blocks handling machinery is accessed through the these functions:
19209 it_fsm_pre_encode () from md_assemble ()
5ee91343
AV
19210 set_pred_insn_type () optional, from the tencode functions
19211 set_pred_insn_type_last () ditto
19212 in_pred_block () ditto
e07e6e58 19213 it_fsm_post_encode () from md_assemble ()
33eaf5de 19214 force_automatic_it_block_close () from label handling functions
e07e6e58
NC
19215
19216 Rationale:
19217 1) md_assemble () calls it_fsm_pre_encode () before calling tencode (),
477330fc
RM
19218 initializing the IT insn type with a generic initial value depending
19219 on the inst.condition.
e07e6e58 19220 2) During the tencode function, two things may happen:
477330fc 19221 a) The tencode function overrides the IT insn type by
5ee91343
AV
19222 calling either set_pred_insn_type (type) or
19223 set_pred_insn_type_last ().
477330fc 19224 b) The tencode function queries the IT block state by
5ee91343 19225 calling in_pred_block () (i.e. to determine narrow/not narrow mode).
477330fc 19226
5ee91343
AV
19227 Both set_pred_insn_type and in_pred_block run the internal FSM state
19228 handling function (handle_pred_state), because: a) setting the IT insn
477330fc
RM
19229 type may incur in an invalid state (exiting the function),
19230 and b) querying the state requires the FSM to be updated.
19231 Specifically we want to avoid creating an IT block for conditional
19232 branches, so it_fsm_pre_encode is actually a guess and we can't
19233 determine whether an IT block is required until the tencode () routine
19234 has decided what type of instruction this actually it.
5ee91343
AV
19235 Because of this, if set_pred_insn_type and in_pred_block have to be
19236 used, set_pred_insn_type has to be called first.
477330fc 19237
5ee91343
AV
19238 set_pred_insn_type_last () is a wrapper of set_pred_insn_type (type),
19239 that determines the insn IT type depending on the inst.cond code.
477330fc
RM
19240 When a tencode () routine encodes an instruction that can be
19241 either outside an IT block, or, in the case of being inside, has to be
5ee91343 19242 the last one, set_pred_insn_type_last () will determine the proper
477330fc 19243 IT instruction type based on the inst.cond code. Otherwise,
5ee91343 19244 set_pred_insn_type can be called for overriding that logic or
477330fc
RM
19245 for covering other cases.
19246
5ee91343
AV
19247 Calling handle_pred_state () may not transition the IT block state to
19248 OUTSIDE_PRED_BLOCK immediately, since the (current) state could be
477330fc 19249 still queried. Instead, if the FSM determines that the state should
5ee91343 19250 be transitioned to OUTSIDE_PRED_BLOCK, a flag is marked to be closed
477330fc
RM
19251 after the tencode () function: that's what it_fsm_post_encode () does.
19252
5ee91343 19253 Since in_pred_block () calls the state handling function to get an
477330fc
RM
19254 updated state, an error may occur (due to invalid insns combination).
19255 In that case, inst.error is set.
19256 Therefore, inst.error has to be checked after the execution of
19257 the tencode () routine.
e07e6e58
NC
19258
19259 3) Back in md_assemble(), it_fsm_post_encode () is called to commit
477330fc 19260 any pending state change (if any) that didn't take place in
5ee91343 19261 handle_pred_state () as explained above. */
e07e6e58
NC
19262
19263static void
19264it_fsm_pre_encode (void)
19265{
19266 if (inst.cond != COND_ALWAYS)
5ee91343 19267 inst.pred_insn_type = INSIDE_IT_INSN;
e07e6e58 19268 else
5ee91343 19269 inst.pred_insn_type = OUTSIDE_PRED_INSN;
e07e6e58 19270
5ee91343 19271 now_pred.state_handled = 0;
e07e6e58
NC
19272}
19273
19274/* IT state FSM handling function. */
5ee91343
AV
19275/* MVE instructions and non-MVE instructions are handled differently because of
19276 the introduction of VPT blocks.
19277 Specifications say that any non-MVE instruction inside a VPT block is
19278 UNPREDICTABLE, with the exception of the BKPT instruction. Whereas most MVE
19279 instructions are deemed to be UNPREDICTABLE if inside an IT block. For the
19280 few exceptions this will be handled at their respective handler functions.
19281 The error messages provided depending on the different combinations possible
19282 are described in the cases below:
19283 For 'most' MVE instructions:
19284 1) In an IT block, with an IT code: syntax error
19285 2) In an IT block, with a VPT code: error: must be in a VPT block
19286 3) In an IT block, with no code: warning: UNPREDICTABLE
19287 4) In a VPT block, with an IT code: syntax error
19288 5) In a VPT block, with a VPT code: OK!
19289 6) In a VPT block, with no code: error: missing code
19290 7) Outside a pred block, with an IT code: error: syntax error
19291 8) Outside a pred block, with a VPT code: error: should be in a VPT block
19292 9) Outside a pred block, with no code: OK!
19293 For non-MVE instructions:
19294 10) In an IT block, with an IT code: OK!
19295 11) In an IT block, with a VPT code: syntax error
19296 12) In an IT block, with no code: error: missing code
19297 13) In a VPT block, with an IT code: error: should be in an IT block
19298 14) In a VPT block, with a VPT code: syntax error
19299 15) In a VPT block, with no code: UNPREDICTABLE
19300 16) Outside a pred block, with an IT code: error: should be in an IT block
19301 17) Outside a pred block, with a VPT code: syntax error
19302 18) Outside a pred block, with no code: OK!
19303 */
19304
e07e6e58
NC
19305
19306static int
5ee91343 19307handle_pred_state (void)
e07e6e58 19308{
5ee91343
AV
19309 now_pred.state_handled = 1;
19310 now_pred.insn_cond = FALSE;
e07e6e58 19311
5ee91343 19312 switch (now_pred.state)
e07e6e58 19313 {
5ee91343
AV
19314 case OUTSIDE_PRED_BLOCK:
19315 switch (inst.pred_insn_type)
e07e6e58 19316 {
5ee91343
AV
19317 case MVE_OUTSIDE_PRED_INSN:
19318 if (inst.cond < COND_ALWAYS)
19319 {
19320 /* Case 7: Outside a pred block, with an IT code: error: syntax
19321 error. */
19322 inst.error = BAD_SYNTAX;
19323 return FAIL;
19324 }
19325 /* Case 9: Outside a pred block, with no code: OK! */
19326 break;
19327 case OUTSIDE_PRED_INSN:
19328 if (inst.cond > COND_ALWAYS)
19329 {
19330 /* Case 17: Outside a pred block, with a VPT code: syntax error.
19331 */
19332 inst.error = BAD_SYNTAX;
19333 return FAIL;
19334 }
19335 /* Case 18: Outside a pred block, with no code: OK! */
e07e6e58
NC
19336 break;
19337
5ee91343
AV
19338 case INSIDE_VPT_INSN:
19339 /* Case 8: Outside a pred block, with a VPT code: error: should be in
19340 a VPT block. */
19341 inst.error = BAD_OUT_VPT;
19342 return FAIL;
19343
e07e6e58
NC
19344 case INSIDE_IT_INSN:
19345 case INSIDE_IT_LAST_INSN:
5ee91343 19346 if (inst.cond < COND_ALWAYS)
e07e6e58 19347 {
5ee91343
AV
19348 /* Case 16: Outside a pred block, with an IT code: error: should
19349 be in an IT block. */
19350 if (thumb_mode == 0)
e07e6e58 19351 {
5ee91343
AV
19352 if (unified_syntax
19353 && !(implicit_it_mode & IMPLICIT_IT_MODE_ARM))
19354 as_tsktsk (_("Warning: conditional outside an IT block"\
19355 " for Thumb."));
e07e6e58
NC
19356 }
19357 else
19358 {
5ee91343
AV
19359 if ((implicit_it_mode & IMPLICIT_IT_MODE_THUMB)
19360 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6t2))
19361 {
19362 /* Automatically generate the IT instruction. */
19363 new_automatic_it_block (inst.cond);
19364 if (inst.pred_insn_type == INSIDE_IT_LAST_INSN)
19365 close_automatic_it_block ();
19366 }
19367 else
19368 {
19369 inst.error = BAD_OUT_IT;
19370 return FAIL;
19371 }
e07e6e58 19372 }
5ee91343 19373 break;
e07e6e58 19374 }
5ee91343
AV
19375 else if (inst.cond > COND_ALWAYS)
19376 {
19377 /* Case 17: Outside a pred block, with a VPT code: syntax error.
19378 */
19379 inst.error = BAD_SYNTAX;
19380 return FAIL;
19381 }
19382 else
19383 gas_assert (0);
e07e6e58
NC
19384 case IF_INSIDE_IT_LAST_INSN:
19385 case NEUTRAL_IT_INSN:
19386 break;
19387
5ee91343
AV
19388 case VPT_INSN:
19389 if (inst.cond != COND_ALWAYS)
19390 first_error (BAD_SYNTAX);
19391 now_pred.state = MANUAL_PRED_BLOCK;
19392 now_pred.block_length = 0;
19393 now_pred.type = VECTOR_PRED;
19394 now_pred.cc = 0;
19395 break;
e07e6e58 19396 case IT_INSN:
5ee91343
AV
19397 now_pred.state = MANUAL_PRED_BLOCK;
19398 now_pred.block_length = 0;
19399 now_pred.type = SCALAR_PRED;
e07e6e58
NC
19400 break;
19401 }
19402 break;
19403
5ee91343 19404 case AUTOMATIC_PRED_BLOCK:
e07e6e58
NC
19405 /* Three things may happen now:
19406 a) We should increment current it block size;
19407 b) We should close current it block (closing insn or 4 insns);
19408 c) We should close current it block and start a new one (due
19409 to incompatible conditions or
19410 4 insns-length block reached). */
19411
5ee91343 19412 switch (inst.pred_insn_type)
e07e6e58 19413 {
5ee91343
AV
19414 case INSIDE_VPT_INSN:
19415 case VPT_INSN:
19416 case MVE_OUTSIDE_PRED_INSN:
19417 gas_assert (0);
19418 case OUTSIDE_PRED_INSN:
2b0f3761 19419 /* The closure of the block shall happen immediately,
5ee91343 19420 so any in_pred_block () call reports the block as closed. */
e07e6e58
NC
19421 force_automatic_it_block_close ();
19422 break;
19423
19424 case INSIDE_IT_INSN:
19425 case INSIDE_IT_LAST_INSN:
19426 case IF_INSIDE_IT_LAST_INSN:
5ee91343 19427 now_pred.block_length++;
e07e6e58 19428
5ee91343
AV
19429 if (now_pred.block_length > 4
19430 || !now_pred_compatible (inst.cond))
e07e6e58
NC
19431 {
19432 force_automatic_it_block_close ();
5ee91343 19433 if (inst.pred_insn_type != IF_INSIDE_IT_LAST_INSN)
e07e6e58
NC
19434 new_automatic_it_block (inst.cond);
19435 }
19436 else
19437 {
5ee91343
AV
19438 now_pred.insn_cond = TRUE;
19439 now_pred_add_mask (inst.cond);
e07e6e58
NC
19440 }
19441
5ee91343
AV
19442 if (now_pred.state == AUTOMATIC_PRED_BLOCK
19443 && (inst.pred_insn_type == INSIDE_IT_LAST_INSN
19444 || inst.pred_insn_type == IF_INSIDE_IT_LAST_INSN))
e07e6e58
NC
19445 close_automatic_it_block ();
19446 break;
19447
19448 case NEUTRAL_IT_INSN:
5ee91343
AV
19449 now_pred.block_length++;
19450 now_pred.insn_cond = TRUE;
e07e6e58 19451
5ee91343 19452 if (now_pred.block_length > 4)
e07e6e58
NC
19453 force_automatic_it_block_close ();
19454 else
5ee91343 19455 now_pred_add_mask (now_pred.cc & 1);
e07e6e58
NC
19456 break;
19457
19458 case IT_INSN:
19459 close_automatic_it_block ();
5ee91343 19460 now_pred.state = MANUAL_PRED_BLOCK;
e07e6e58
NC
19461 break;
19462 }
19463 break;
19464
5ee91343 19465 case MANUAL_PRED_BLOCK:
e07e6e58 19466 {
5ee91343
AV
19467 int cond, is_last;
19468 if (now_pred.type == SCALAR_PRED)
e07e6e58 19469 {
5ee91343
AV
19470 /* Check conditional suffixes. */
19471 cond = now_pred.cc ^ ((now_pred.mask >> 4) & 1) ^ 1;
19472 now_pred.mask <<= 1;
19473 now_pred.mask &= 0x1f;
19474 is_last = (now_pred.mask == 0x10);
19475 }
19476 else
19477 {
19478 now_pred.cc ^= (now_pred.mask >> 4);
19479 cond = now_pred.cc + 0xf;
19480 now_pred.mask <<= 1;
19481 now_pred.mask &= 0x1f;
19482 is_last = now_pred.mask == 0x10;
19483 }
19484 now_pred.insn_cond = TRUE;
e07e6e58 19485
5ee91343
AV
19486 switch (inst.pred_insn_type)
19487 {
19488 case OUTSIDE_PRED_INSN:
19489 if (now_pred.type == SCALAR_PRED)
19490 {
19491 if (inst.cond == COND_ALWAYS)
19492 {
19493 /* Case 12: In an IT block, with no code: error: missing
19494 code. */
19495 inst.error = BAD_NOT_IT;
19496 return FAIL;
19497 }
19498 else if (inst.cond > COND_ALWAYS)
19499 {
19500 /* Case 11: In an IT block, with a VPT code: syntax error.
19501 */
19502 inst.error = BAD_SYNTAX;
19503 return FAIL;
19504 }
19505 else if (thumb_mode)
19506 {
19507 /* This is for some special cases where a non-MVE
19508 instruction is not allowed in an IT block, such as cbz,
19509 but are put into one with a condition code.
19510 You could argue this should be a syntax error, but we
19511 gave the 'not allowed in IT block' diagnostic in the
19512 past so we will keep doing so. */
19513 inst.error = BAD_NOT_IT;
19514 return FAIL;
19515 }
19516 break;
19517 }
19518 else
19519 {
19520 /* Case 15: In a VPT block, with no code: UNPREDICTABLE. */
19521 as_tsktsk (MVE_NOT_VPT);
19522 return SUCCESS;
19523 }
19524 case MVE_OUTSIDE_PRED_INSN:
19525 if (now_pred.type == SCALAR_PRED)
19526 {
19527 if (inst.cond == COND_ALWAYS)
19528 {
19529 /* Case 3: In an IT block, with no code: warning:
19530 UNPREDICTABLE. */
19531 as_tsktsk (MVE_NOT_IT);
19532 return SUCCESS;
19533 }
19534 else if (inst.cond < COND_ALWAYS)
19535 {
19536 /* Case 1: In an IT block, with an IT code: syntax error.
19537 */
19538 inst.error = BAD_SYNTAX;
19539 return FAIL;
19540 }
19541 else
19542 gas_assert (0);
19543 }
19544 else
19545 {
19546 if (inst.cond < COND_ALWAYS)
19547 {
19548 /* Case 4: In a VPT block, with an IT code: syntax error.
19549 */
19550 inst.error = BAD_SYNTAX;
19551 return FAIL;
19552 }
19553 else if (inst.cond == COND_ALWAYS)
19554 {
19555 /* Case 6: In a VPT block, with no code: error: missing
19556 code. */
19557 inst.error = BAD_NOT_VPT;
19558 return FAIL;
19559 }
19560 else
19561 {
19562 gas_assert (0);
19563 }
19564 }
e07e6e58 19565 case INSIDE_IT_INSN:
5ee91343 19566 if (inst.cond > COND_ALWAYS)
e07e6e58 19567 {
5ee91343
AV
19568 /* Case 11: In an IT block, with a VPT code: syntax error. */
19569 /* Case 14: In a VPT block, with a VPT code: syntax error. */
19570 inst.error = BAD_SYNTAX;
19571 return FAIL;
19572 }
19573 else if (now_pred.type == SCALAR_PRED)
19574 {
19575 /* Case 10: In an IT block, with an IT code: OK! */
19576 if (cond != inst.cond)
19577 {
19578 inst.error = now_pred.type == SCALAR_PRED ? BAD_IT_COND :
19579 BAD_VPT_COND;
19580 return FAIL;
19581 }
19582 }
19583 else
19584 {
19585 /* Case 13: In a VPT block, with an IT code: error: should be
19586 in an IT block. */
19587 inst.error = BAD_OUT_IT;
e07e6e58
NC
19588 return FAIL;
19589 }
19590 break;
19591
5ee91343
AV
19592 case INSIDE_VPT_INSN:
19593 if (now_pred.type == SCALAR_PRED)
19594 {
19595 /* Case 2: In an IT block, with a VPT code: error: must be in a
19596 VPT block. */
19597 inst.error = BAD_OUT_VPT;
19598 return FAIL;
19599 }
19600 /* Case 5: In a VPT block, with a VPT code: OK! */
19601 else if (cond != inst.cond)
19602 {
19603 inst.error = BAD_VPT_COND;
19604 return FAIL;
19605 }
19606 break;
e07e6e58
NC
19607 case INSIDE_IT_LAST_INSN:
19608 case IF_INSIDE_IT_LAST_INSN:
5ee91343
AV
19609 if (now_pred.type == VECTOR_PRED || inst.cond > COND_ALWAYS)
19610 {
19611 /* Case 4: In a VPT block, with an IT code: syntax error. */
19612 /* Case 11: In an IT block, with a VPT code: syntax error. */
19613 inst.error = BAD_SYNTAX;
19614 return FAIL;
19615 }
19616 else if (cond != inst.cond)
e07e6e58
NC
19617 {
19618 inst.error = BAD_IT_COND;
19619 return FAIL;
19620 }
19621 if (!is_last)
19622 {
19623 inst.error = BAD_BRANCH;
19624 return FAIL;
19625 }
19626 break;
19627
19628 case NEUTRAL_IT_INSN:
5ee91343
AV
19629 /* The BKPT instruction is unconditional even in a IT or VPT
19630 block. */
e07e6e58
NC
19631 break;
19632
19633 case IT_INSN:
5ee91343
AV
19634 if (now_pred.type == SCALAR_PRED)
19635 {
19636 inst.error = BAD_IT_IT;
19637 return FAIL;
19638 }
19639 /* fall through. */
19640 case VPT_INSN:
19641 if (inst.cond == COND_ALWAYS)
19642 {
19643 /* Executing a VPT/VPST instruction inside an IT block or a
19644 VPT/VPST/IT instruction inside a VPT block is UNPREDICTABLE.
19645 */
19646 if (now_pred.type == SCALAR_PRED)
19647 as_tsktsk (MVE_NOT_IT);
19648 else
19649 as_tsktsk (MVE_NOT_VPT);
19650 return SUCCESS;
19651 }
19652 else
19653 {
19654 /* VPT/VPST do not accept condition codes. */
19655 inst.error = BAD_SYNTAX;
19656 return FAIL;
19657 }
e07e6e58 19658 }
5ee91343 19659 }
e07e6e58
NC
19660 break;
19661 }
19662
19663 return SUCCESS;
19664}
19665
5a01bb1d
MGD
19666struct depr_insn_mask
19667{
19668 unsigned long pattern;
19669 unsigned long mask;
19670 const char* description;
19671};
19672
19673/* List of 16-bit instruction patterns deprecated in an IT block in
19674 ARMv8. */
19675static const struct depr_insn_mask depr_it_insns[] = {
19676 { 0xc000, 0xc000, N_("Short branches, Undefined, SVC, LDM/STM") },
19677 { 0xb000, 0xb000, N_("Miscellaneous 16-bit instructions") },
19678 { 0xa000, 0xb800, N_("ADR") },
19679 { 0x4800, 0xf800, N_("Literal loads") },
19680 { 0x4478, 0xf478, N_("Hi-register ADD, MOV, CMP, BX, BLX using pc") },
19681 { 0x4487, 0xfc87, N_("Hi-register ADD, MOV, CMP using pc") },
c8de034b
JW
19682 /* NOTE: 0x00dd is not the real encoding, instead, it is the 'tvalue'
19683 field in asm_opcode. 'tvalue' is used at the stage this check happen. */
19684 { 0x00dd, 0x7fff, N_("ADD/SUB sp, sp #imm") },
5a01bb1d
MGD
19685 { 0, 0, NULL }
19686};
19687
e07e6e58
NC
19688static void
19689it_fsm_post_encode (void)
19690{
19691 int is_last;
19692
5ee91343
AV
19693 if (!now_pred.state_handled)
19694 handle_pred_state ();
e07e6e58 19695
5ee91343
AV
19696 if (now_pred.insn_cond
19697 && !now_pred.warn_deprecated
5a01bb1d 19698 && warn_on_deprecated
df9909b8
TP
19699 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v8)
19700 && !ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_m))
5a01bb1d
MGD
19701 {
19702 if (inst.instruction >= 0x10000)
19703 {
5c3696f8 19704 as_tsktsk (_("IT blocks containing 32-bit Thumb instructions are "
df9909b8 19705 "performance deprecated in ARMv8-A and ARMv8-R"));
5ee91343 19706 now_pred.warn_deprecated = TRUE;
5a01bb1d
MGD
19707 }
19708 else
19709 {
19710 const struct depr_insn_mask *p = depr_it_insns;
19711
19712 while (p->mask != 0)
19713 {
19714 if ((inst.instruction & p->mask) == p->pattern)
19715 {
df9909b8
TP
19716 as_tsktsk (_("IT blocks containing 16-bit Thumb "
19717 "instructions of the following class are "
19718 "performance deprecated in ARMv8-A and "
19719 "ARMv8-R: %s"), p->description);
5ee91343 19720 now_pred.warn_deprecated = TRUE;
5a01bb1d
MGD
19721 break;
19722 }
19723
19724 ++p;
19725 }
19726 }
19727
5ee91343 19728 if (now_pred.block_length > 1)
5a01bb1d 19729 {
5c3696f8 19730 as_tsktsk (_("IT blocks containing more than one conditional "
df9909b8
TP
19731 "instruction are performance deprecated in ARMv8-A and "
19732 "ARMv8-R"));
5ee91343 19733 now_pred.warn_deprecated = TRUE;
5a01bb1d
MGD
19734 }
19735 }
19736
5ee91343
AV
19737 is_last = (now_pred.mask == 0x10);
19738 if (is_last)
19739 {
19740 now_pred.state = OUTSIDE_PRED_BLOCK;
19741 now_pred.mask = 0;
19742 }
e07e6e58
NC
19743}
19744
19745static void
19746force_automatic_it_block_close (void)
19747{
5ee91343 19748 if (now_pred.state == AUTOMATIC_PRED_BLOCK)
e07e6e58
NC
19749 {
19750 close_automatic_it_block ();
5ee91343
AV
19751 now_pred.state = OUTSIDE_PRED_BLOCK;
19752 now_pred.mask = 0;
e07e6e58
NC
19753 }
19754}
19755
19756static int
5ee91343 19757in_pred_block (void)
e07e6e58 19758{
5ee91343
AV
19759 if (!now_pred.state_handled)
19760 handle_pred_state ();
e07e6e58 19761
5ee91343 19762 return now_pred.state != OUTSIDE_PRED_BLOCK;
e07e6e58
NC
19763}
19764
ff8646ee
TP
19765/* Whether OPCODE only has T32 encoding. Since this function is only used by
19766 t32_insn_ok, OPCODE enabled by v6t2 extension bit do not need to be listed
19767 here, hence the "known" in the function name. */
fc289b0a
TP
19768
19769static bfd_boolean
ff8646ee 19770known_t32_only_insn (const struct asm_opcode *opcode)
fc289b0a
TP
19771{
19772 /* Original Thumb-1 wide instruction. */
19773 if (opcode->tencode == do_t_blx
19774 || opcode->tencode == do_t_branch23
19775 || ARM_CPU_HAS_FEATURE (*opcode->tvariant, arm_ext_msr)
19776 || ARM_CPU_HAS_FEATURE (*opcode->tvariant, arm_ext_barrier))
19777 return TRUE;
19778
16a1fa25
TP
19779 /* Wide-only instruction added to ARMv8-M Baseline. */
19780 if (ARM_CPU_HAS_FEATURE (*opcode->tvariant, arm_ext_v8m_m_only)
ff8646ee
TP
19781 || ARM_CPU_HAS_FEATURE (*opcode->tvariant, arm_ext_atomics)
19782 || ARM_CPU_HAS_FEATURE (*opcode->tvariant, arm_ext_v6t2_v8m)
19783 || ARM_CPU_HAS_FEATURE (*opcode->tvariant, arm_ext_div))
19784 return TRUE;
19785
19786 return FALSE;
19787}
19788
19789/* Whether wide instruction variant can be used if available for a valid OPCODE
19790 in ARCH. */
19791
19792static bfd_boolean
19793t32_insn_ok (arm_feature_set arch, const struct asm_opcode *opcode)
19794{
19795 if (known_t32_only_insn (opcode))
19796 return TRUE;
19797
19798 /* Instruction with narrow and wide encoding added to ARMv8-M. Availability
19799 of variant T3 of B.W is checked in do_t_branch. */
19800 if (ARM_CPU_HAS_FEATURE (arch, arm_ext_v8m)
19801 && opcode->tencode == do_t_branch)
19802 return TRUE;
19803
bada4342
JW
19804 /* MOV accepts T1/T3 encodings under Baseline, T3 encoding is 32bit. */
19805 if (ARM_CPU_HAS_FEATURE (arch, arm_ext_v8m)
19806 && opcode->tencode == do_t_mov_cmp
19807 /* Make sure CMP instruction is not affected. */
19808 && opcode->aencode == do_mov)
19809 return TRUE;
19810
ff8646ee
TP
19811 /* Wide instruction variants of all instructions with narrow *and* wide
19812 variants become available with ARMv6t2. Other opcodes are either
19813 narrow-only or wide-only and are thus available if OPCODE is valid. */
19814 if (ARM_CPU_HAS_FEATURE (arch, arm_ext_v6t2))
19815 return TRUE;
19816
19817 /* OPCODE with narrow only instruction variant or wide variant not
19818 available. */
fc289b0a
TP
19819 return FALSE;
19820}
19821
c19d1205
ZW
19822void
19823md_assemble (char *str)
b99bd4ef 19824{
c19d1205
ZW
19825 char *p = str;
19826 const struct asm_opcode * opcode;
b99bd4ef 19827
c19d1205
ZW
19828 /* Align the previous label if needed. */
19829 if (last_label_seen != NULL)
b99bd4ef 19830 {
c19d1205
ZW
19831 symbol_set_frag (last_label_seen, frag_now);
19832 S_SET_VALUE (last_label_seen, (valueT) frag_now_fix ());
19833 S_SET_SEGMENT (last_label_seen, now_seg);
b99bd4ef
NC
19834 }
19835
c19d1205 19836 memset (&inst, '\0', sizeof (inst));
e2b0ab59
AV
19837 int r;
19838 for (r = 0; r < ARM_IT_MAX_RELOCS; r++)
19839 inst.relocs[r].type = BFD_RELOC_UNUSED;
b99bd4ef 19840
c19d1205
ZW
19841 opcode = opcode_lookup (&p);
19842 if (!opcode)
b99bd4ef 19843 {
c19d1205 19844 /* It wasn't an instruction, but it might be a register alias of
dcbf9037 19845 the form alias .req reg, or a Neon .dn/.qn directive. */
c921be7d 19846 if (! create_register_alias (str, p)
477330fc 19847 && ! create_neon_reg_alias (str, p))
c19d1205 19848 as_bad (_("bad instruction `%s'"), str);
b99bd4ef 19849
b99bd4ef
NC
19850 return;
19851 }
19852
278df34e 19853 if (warn_on_deprecated && opcode->tag == OT_cinfix3_deprecated)
5c3696f8 19854 as_tsktsk (_("s suffix on comparison instruction is deprecated"));
088fa78e 19855
037e8744
JB
19856 /* The value which unconditional instructions should have in place of the
19857 condition field. */
19858 inst.uncond_value = (opcode->tag == OT_csuffixF) ? 0xf : -1;
19859
c19d1205 19860 if (thumb_mode)
b99bd4ef 19861 {
e74cfd16 19862 arm_feature_set variant;
8f06b2d8
PB
19863
19864 variant = cpu_variant;
19865 /* Only allow coprocessor instructions on Thumb-2 capable devices. */
e74cfd16
PB
19866 if (!ARM_CPU_HAS_FEATURE (variant, arm_arch_t2))
19867 ARM_CLEAR_FEATURE (variant, variant, fpu_any_hard);
c19d1205 19868 /* Check that this instruction is supported for this CPU. */
62b3e311
PB
19869 if (!opcode->tvariant
19870 || (thumb_mode == 1
19871 && !ARM_CPU_HAS_FEATURE (variant, *opcode->tvariant)))
b99bd4ef 19872 {
173205ca
TP
19873 if (opcode->tencode == do_t_swi)
19874 as_bad (_("SVC is not permitted on this architecture"));
19875 else
19876 as_bad (_("selected processor does not support `%s' in Thumb mode"), str);
b99bd4ef
NC
19877 return;
19878 }
c19d1205
ZW
19879 if (inst.cond != COND_ALWAYS && !unified_syntax
19880 && opcode->tencode != do_t_branch)
b99bd4ef 19881 {
c19d1205 19882 as_bad (_("Thumb does not support conditional execution"));
b99bd4ef
NC
19883 return;
19884 }
19885
fc289b0a
TP
19886 /* Two things are addressed here:
19887 1) Implicit require narrow instructions on Thumb-1.
19888 This avoids relaxation accidentally introducing Thumb-2
19889 instructions.
19890 2) Reject wide instructions in non Thumb-2 cores.
19891
19892 Only instructions with narrow and wide variants need to be handled
19893 but selecting all non wide-only instructions is easier. */
19894 if (!ARM_CPU_HAS_FEATURE (variant, arm_ext_v6t2)
ff8646ee 19895 && !t32_insn_ok (variant, opcode))
076d447c 19896 {
fc289b0a
TP
19897 if (inst.size_req == 0)
19898 inst.size_req = 2;
19899 else if (inst.size_req == 4)
752d5da4 19900 {
ff8646ee
TP
19901 if (ARM_CPU_HAS_FEATURE (variant, arm_ext_v8m))
19902 as_bad (_("selected processor does not support 32bit wide "
19903 "variant of instruction `%s'"), str);
19904 else
19905 as_bad (_("selected processor does not support `%s' in "
19906 "Thumb-2 mode"), str);
fc289b0a 19907 return;
752d5da4 19908 }
076d447c
PB
19909 }
19910
c19d1205
ZW
19911 inst.instruction = opcode->tvalue;
19912
5be8be5d 19913 if (!parse_operands (p, opcode->operands, /*thumb=*/TRUE))
477330fc 19914 {
5ee91343 19915 /* Prepare the pred_insn_type for those encodings that don't set
477330fc
RM
19916 it. */
19917 it_fsm_pre_encode ();
c19d1205 19918
477330fc 19919 opcode->tencode ();
e07e6e58 19920
477330fc
RM
19921 it_fsm_post_encode ();
19922 }
e27ec89e 19923
0110f2b8 19924 if (!(inst.error || inst.relax))
b99bd4ef 19925 {
9c2799c2 19926 gas_assert (inst.instruction < 0xe800 || inst.instruction > 0xffff);
c19d1205
ZW
19927 inst.size = (inst.instruction > 0xffff ? 4 : 2);
19928 if (inst.size_req && inst.size_req != inst.size)
b99bd4ef 19929 {
c19d1205 19930 as_bad (_("cannot honor width suffix -- `%s'"), str);
b99bd4ef
NC
19931 return;
19932 }
19933 }
076d447c
PB
19934
19935 /* Something has gone badly wrong if we try to relax a fixed size
477330fc 19936 instruction. */
9c2799c2 19937 gas_assert (inst.size_req == 0 || !inst.relax);
076d447c 19938
e74cfd16
PB
19939 ARM_MERGE_FEATURE_SETS (thumb_arch_used, thumb_arch_used,
19940 *opcode->tvariant);
ee065d83 19941 /* Many Thumb-2 instructions also have Thumb-1 variants, so explicitly
fc289b0a
TP
19942 set those bits when Thumb-2 32-bit instructions are seen. The impact
19943 of relaxable instructions will be considered later after we finish all
19944 relaxation. */
ff8646ee
TP
19945 if (ARM_FEATURE_CORE_EQUAL (cpu_variant, arm_arch_any))
19946 variant = arm_arch_none;
19947 else
19948 variant = cpu_variant;
19949 if (inst.size == 4 && !t32_insn_ok (variant, opcode))
e74cfd16
PB
19950 ARM_MERGE_FEATURE_SETS (thumb_arch_used, thumb_arch_used,
19951 arm_ext_v6t2);
cd000bff 19952
88714cb8
DG
19953 check_neon_suffixes;
19954
cd000bff 19955 if (!inst.error)
c877a2f2
NC
19956 {
19957 mapping_state (MAP_THUMB);
19958 }
c19d1205 19959 }
3e9e4fcf 19960 else if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v1))
c19d1205 19961 {
845b51d6
PB
19962 bfd_boolean is_bx;
19963
19964 /* bx is allowed on v5 cores, and sometimes on v4 cores. */
19965 is_bx = (opcode->aencode == do_bx);
19966
c19d1205 19967 /* Check that this instruction is supported for this CPU. */
845b51d6
PB
19968 if (!(is_bx && fix_v4bx)
19969 && !(opcode->avariant &&
19970 ARM_CPU_HAS_FEATURE (cpu_variant, *opcode->avariant)))
b99bd4ef 19971 {
84b52b66 19972 as_bad (_("selected processor does not support `%s' in ARM mode"), str);
c19d1205 19973 return;
b99bd4ef 19974 }
c19d1205 19975 if (inst.size_req)
b99bd4ef 19976 {
c19d1205
ZW
19977 as_bad (_("width suffixes are invalid in ARM mode -- `%s'"), str);
19978 return;
b99bd4ef
NC
19979 }
19980
c19d1205
ZW
19981 inst.instruction = opcode->avalue;
19982 if (opcode->tag == OT_unconditionalF)
eff0bc54 19983 inst.instruction |= 0xFU << 28;
c19d1205
ZW
19984 else
19985 inst.instruction |= inst.cond << 28;
19986 inst.size = INSN_SIZE;
5be8be5d 19987 if (!parse_operands (p, opcode->operands, /*thumb=*/FALSE))
477330fc
RM
19988 {
19989 it_fsm_pre_encode ();
19990 opcode->aencode ();
19991 it_fsm_post_encode ();
19992 }
ee065d83 19993 /* Arm mode bx is marked as both v4T and v5 because it's still required
477330fc 19994 on a hypothetical non-thumb v5 core. */
845b51d6 19995 if (is_bx)
e74cfd16 19996 ARM_MERGE_FEATURE_SETS (arm_arch_used, arm_arch_used, arm_ext_v4t);
ee065d83 19997 else
e74cfd16
PB
19998 ARM_MERGE_FEATURE_SETS (arm_arch_used, arm_arch_used,
19999 *opcode->avariant);
88714cb8
DG
20000
20001 check_neon_suffixes;
20002
cd000bff 20003 if (!inst.error)
c877a2f2
NC
20004 {
20005 mapping_state (MAP_ARM);
20006 }
b99bd4ef 20007 }
3e9e4fcf
JB
20008 else
20009 {
20010 as_bad (_("attempt to use an ARM instruction on a Thumb-only processor "
20011 "-- `%s'"), str);
20012 return;
20013 }
c19d1205
ZW
20014 output_inst (str);
20015}
b99bd4ef 20016
e07e6e58 20017static void
5ee91343 20018check_pred_blocks_finished (void)
e07e6e58
NC
20019{
20020#ifdef OBJ_ELF
20021 asection *sect;
20022
20023 for (sect = stdoutput->sections; sect != NULL; sect = sect->next)
5ee91343
AV
20024 if (seg_info (sect)->tc_segment_info_data.current_pred.state
20025 == MANUAL_PRED_BLOCK)
e07e6e58 20026 {
5ee91343
AV
20027 if (now_pred.type == SCALAR_PRED)
20028 as_warn (_("section '%s' finished with an open IT block."),
20029 sect->name);
20030 else
20031 as_warn (_("section '%s' finished with an open VPT/VPST block."),
20032 sect->name);
e07e6e58
NC
20033 }
20034#else
5ee91343
AV
20035 if (now_pred.state == MANUAL_PRED_BLOCK)
20036 {
20037 if (now_pred.type == SCALAR_PRED)
20038 as_warn (_("file finished with an open IT block."));
20039 else
20040 as_warn (_("file finished with an open VPT/VPST block."));
20041 }
e07e6e58
NC
20042#endif
20043}
20044
c19d1205
ZW
20045/* Various frobbings of labels and their addresses. */
20046
20047void
20048arm_start_line_hook (void)
20049{
20050 last_label_seen = NULL;
b99bd4ef
NC
20051}
20052
c19d1205
ZW
20053void
20054arm_frob_label (symbolS * sym)
b99bd4ef 20055{
c19d1205 20056 last_label_seen = sym;
b99bd4ef 20057
c19d1205 20058 ARM_SET_THUMB (sym, thumb_mode);
b99bd4ef 20059
c19d1205
ZW
20060#if defined OBJ_COFF || defined OBJ_ELF
20061 ARM_SET_INTERWORK (sym, support_interwork);
20062#endif
b99bd4ef 20063
e07e6e58
NC
20064 force_automatic_it_block_close ();
20065
5f4273c7 20066 /* Note - do not allow local symbols (.Lxxx) to be labelled
c19d1205
ZW
20067 as Thumb functions. This is because these labels, whilst
20068 they exist inside Thumb code, are not the entry points for
20069 possible ARM->Thumb calls. Also, these labels can be used
20070 as part of a computed goto or switch statement. eg gcc
20071 can generate code that looks like this:
b99bd4ef 20072
c19d1205
ZW
20073 ldr r2, [pc, .Laaa]
20074 lsl r3, r3, #2
20075 ldr r2, [r3, r2]
20076 mov pc, r2
b99bd4ef 20077
c19d1205
ZW
20078 .Lbbb: .word .Lxxx
20079 .Lccc: .word .Lyyy
20080 ..etc...
20081 .Laaa: .word Lbbb
b99bd4ef 20082
c19d1205
ZW
20083 The first instruction loads the address of the jump table.
20084 The second instruction converts a table index into a byte offset.
20085 The third instruction gets the jump address out of the table.
20086 The fourth instruction performs the jump.
b99bd4ef 20087
c19d1205
ZW
20088 If the address stored at .Laaa is that of a symbol which has the
20089 Thumb_Func bit set, then the linker will arrange for this address
20090 to have the bottom bit set, which in turn would mean that the
20091 address computation performed by the third instruction would end
20092 up with the bottom bit set. Since the ARM is capable of unaligned
20093 word loads, the instruction would then load the incorrect address
20094 out of the jump table, and chaos would ensue. */
20095 if (label_is_thumb_function_name
20096 && (S_GET_NAME (sym)[0] != '.' || S_GET_NAME (sym)[1] != 'L')
20097 && (bfd_get_section_flags (stdoutput, now_seg) & SEC_CODE) != 0)
b99bd4ef 20098 {
c19d1205
ZW
20099 /* When the address of a Thumb function is taken the bottom
20100 bit of that address should be set. This will allow
20101 interworking between Arm and Thumb functions to work
20102 correctly. */
b99bd4ef 20103
c19d1205 20104 THUMB_SET_FUNC (sym, 1);
b99bd4ef 20105
c19d1205 20106 label_is_thumb_function_name = FALSE;
b99bd4ef 20107 }
07a53e5c 20108
07a53e5c 20109 dwarf2_emit_label (sym);
b99bd4ef
NC
20110}
20111
c921be7d 20112bfd_boolean
c19d1205 20113arm_data_in_code (void)
b99bd4ef 20114{
c19d1205 20115 if (thumb_mode && ! strncmp (input_line_pointer + 1, "data:", 5))
b99bd4ef 20116 {
c19d1205
ZW
20117 *input_line_pointer = '/';
20118 input_line_pointer += 5;
20119 *input_line_pointer = 0;
c921be7d 20120 return TRUE;
b99bd4ef
NC
20121 }
20122
c921be7d 20123 return FALSE;
b99bd4ef
NC
20124}
20125
c19d1205
ZW
20126char *
20127arm_canonicalize_symbol_name (char * name)
b99bd4ef 20128{
c19d1205 20129 int len;
b99bd4ef 20130
c19d1205
ZW
20131 if (thumb_mode && (len = strlen (name)) > 5
20132 && streq (name + len - 5, "/data"))
20133 *(name + len - 5) = 0;
b99bd4ef 20134
c19d1205 20135 return name;
b99bd4ef 20136}
c19d1205
ZW
20137\f
20138/* Table of all register names defined by default. The user can
20139 define additional names with .req. Note that all register names
20140 should appear in both upper and lowercase variants. Some registers
20141 also have mixed-case names. */
b99bd4ef 20142
dcbf9037 20143#define REGDEF(s,n,t) { #s, n, REG_TYPE_##t, TRUE, 0 }
c19d1205 20144#define REGNUM(p,n,t) REGDEF(p##n, n, t)
5287ad62 20145#define REGNUM2(p,n,t) REGDEF(p##n, 2 * n, t)
c19d1205
ZW
20146#define REGSET(p,t) \
20147 REGNUM(p, 0,t), REGNUM(p, 1,t), REGNUM(p, 2,t), REGNUM(p, 3,t), \
20148 REGNUM(p, 4,t), REGNUM(p, 5,t), REGNUM(p, 6,t), REGNUM(p, 7,t), \
20149 REGNUM(p, 8,t), REGNUM(p, 9,t), REGNUM(p,10,t), REGNUM(p,11,t), \
20150 REGNUM(p,12,t), REGNUM(p,13,t), REGNUM(p,14,t), REGNUM(p,15,t)
5287ad62
JB
20151#define REGSETH(p,t) \
20152 REGNUM(p,16,t), REGNUM(p,17,t), REGNUM(p,18,t), REGNUM(p,19,t), \
20153 REGNUM(p,20,t), REGNUM(p,21,t), REGNUM(p,22,t), REGNUM(p,23,t), \
20154 REGNUM(p,24,t), REGNUM(p,25,t), REGNUM(p,26,t), REGNUM(p,27,t), \
20155 REGNUM(p,28,t), REGNUM(p,29,t), REGNUM(p,30,t), REGNUM(p,31,t)
20156#define REGSET2(p,t) \
20157 REGNUM2(p, 0,t), REGNUM2(p, 1,t), REGNUM2(p, 2,t), REGNUM2(p, 3,t), \
20158 REGNUM2(p, 4,t), REGNUM2(p, 5,t), REGNUM2(p, 6,t), REGNUM2(p, 7,t), \
20159 REGNUM2(p, 8,t), REGNUM2(p, 9,t), REGNUM2(p,10,t), REGNUM2(p,11,t), \
20160 REGNUM2(p,12,t), REGNUM2(p,13,t), REGNUM2(p,14,t), REGNUM2(p,15,t)
90ec0d68
MGD
20161#define SPLRBANK(base,bank,t) \
20162 REGDEF(lr_##bank, 768|((base+0)<<16), t), \
20163 REGDEF(sp_##bank, 768|((base+1)<<16), t), \
20164 REGDEF(spsr_##bank, 768|(base<<16)|SPSR_BIT, t), \
20165 REGDEF(LR_##bank, 768|((base+0)<<16), t), \
20166 REGDEF(SP_##bank, 768|((base+1)<<16), t), \
20167 REGDEF(SPSR_##bank, 768|(base<<16)|SPSR_BIT, t)
7ed4c4c5 20168
c19d1205 20169static const struct reg_entry reg_names[] =
7ed4c4c5 20170{
c19d1205
ZW
20171 /* ARM integer registers. */
20172 REGSET(r, RN), REGSET(R, RN),
7ed4c4c5 20173
c19d1205
ZW
20174 /* ATPCS synonyms. */
20175 REGDEF(a1,0,RN), REGDEF(a2,1,RN), REGDEF(a3, 2,RN), REGDEF(a4, 3,RN),
20176 REGDEF(v1,4,RN), REGDEF(v2,5,RN), REGDEF(v3, 6,RN), REGDEF(v4, 7,RN),
20177 REGDEF(v5,8,RN), REGDEF(v6,9,RN), REGDEF(v7,10,RN), REGDEF(v8,11,RN),
7ed4c4c5 20178
c19d1205
ZW
20179 REGDEF(A1,0,RN), REGDEF(A2,1,RN), REGDEF(A3, 2,RN), REGDEF(A4, 3,RN),
20180 REGDEF(V1,4,RN), REGDEF(V2,5,RN), REGDEF(V3, 6,RN), REGDEF(V4, 7,RN),
20181 REGDEF(V5,8,RN), REGDEF(V6,9,RN), REGDEF(V7,10,RN), REGDEF(V8,11,RN),
7ed4c4c5 20182
c19d1205
ZW
20183 /* Well-known aliases. */
20184 REGDEF(wr, 7,RN), REGDEF(sb, 9,RN), REGDEF(sl,10,RN), REGDEF(fp,11,RN),
20185 REGDEF(ip,12,RN), REGDEF(sp,13,RN), REGDEF(lr,14,RN), REGDEF(pc,15,RN),
20186
20187 REGDEF(WR, 7,RN), REGDEF(SB, 9,RN), REGDEF(SL,10,RN), REGDEF(FP,11,RN),
20188 REGDEF(IP,12,RN), REGDEF(SP,13,RN), REGDEF(LR,14,RN), REGDEF(PC,15,RN),
20189
20190 /* Coprocessor numbers. */
20191 REGSET(p, CP), REGSET(P, CP),
20192
20193 /* Coprocessor register numbers. The "cr" variants are for backward
20194 compatibility. */
20195 REGSET(c, CN), REGSET(C, CN),
20196 REGSET(cr, CN), REGSET(CR, CN),
20197
90ec0d68
MGD
20198 /* ARM banked registers. */
20199 REGDEF(R8_usr,512|(0<<16),RNB), REGDEF(r8_usr,512|(0<<16),RNB),
20200 REGDEF(R9_usr,512|(1<<16),RNB), REGDEF(r9_usr,512|(1<<16),RNB),
20201 REGDEF(R10_usr,512|(2<<16),RNB), REGDEF(r10_usr,512|(2<<16),RNB),
20202 REGDEF(R11_usr,512|(3<<16),RNB), REGDEF(r11_usr,512|(3<<16),RNB),
20203 REGDEF(R12_usr,512|(4<<16),RNB), REGDEF(r12_usr,512|(4<<16),RNB),
20204 REGDEF(SP_usr,512|(5<<16),RNB), REGDEF(sp_usr,512|(5<<16),RNB),
20205 REGDEF(LR_usr,512|(6<<16),RNB), REGDEF(lr_usr,512|(6<<16),RNB),
20206
20207 REGDEF(R8_fiq,512|(8<<16),RNB), REGDEF(r8_fiq,512|(8<<16),RNB),
20208 REGDEF(R9_fiq,512|(9<<16),RNB), REGDEF(r9_fiq,512|(9<<16),RNB),
20209 REGDEF(R10_fiq,512|(10<<16),RNB), REGDEF(r10_fiq,512|(10<<16),RNB),
20210 REGDEF(R11_fiq,512|(11<<16),RNB), REGDEF(r11_fiq,512|(11<<16),RNB),
20211 REGDEF(R12_fiq,512|(12<<16),RNB), REGDEF(r12_fiq,512|(12<<16),RNB),
1472d06f 20212 REGDEF(SP_fiq,512|(13<<16),RNB), REGDEF(sp_fiq,512|(13<<16),RNB),
90ec0d68
MGD
20213 REGDEF(LR_fiq,512|(14<<16),RNB), REGDEF(lr_fiq,512|(14<<16),RNB),
20214 REGDEF(SPSR_fiq,512|(14<<16)|SPSR_BIT,RNB), REGDEF(spsr_fiq,512|(14<<16)|SPSR_BIT,RNB),
20215
20216 SPLRBANK(0,IRQ,RNB), SPLRBANK(0,irq,RNB),
20217 SPLRBANK(2,SVC,RNB), SPLRBANK(2,svc,RNB),
20218 SPLRBANK(4,ABT,RNB), SPLRBANK(4,abt,RNB),
20219 SPLRBANK(6,UND,RNB), SPLRBANK(6,und,RNB),
20220 SPLRBANK(12,MON,RNB), SPLRBANK(12,mon,RNB),
20221 REGDEF(elr_hyp,768|(14<<16),RNB), REGDEF(ELR_hyp,768|(14<<16),RNB),
20222 REGDEF(sp_hyp,768|(15<<16),RNB), REGDEF(SP_hyp,768|(15<<16),RNB),
fa94de6b 20223 REGDEF(spsr_hyp,768|(14<<16)|SPSR_BIT,RNB),
90ec0d68
MGD
20224 REGDEF(SPSR_hyp,768|(14<<16)|SPSR_BIT,RNB),
20225
c19d1205
ZW
20226 /* FPA registers. */
20227 REGNUM(f,0,FN), REGNUM(f,1,FN), REGNUM(f,2,FN), REGNUM(f,3,FN),
20228 REGNUM(f,4,FN), REGNUM(f,5,FN), REGNUM(f,6,FN), REGNUM(f,7, FN),
20229
20230 REGNUM(F,0,FN), REGNUM(F,1,FN), REGNUM(F,2,FN), REGNUM(F,3,FN),
20231 REGNUM(F,4,FN), REGNUM(F,5,FN), REGNUM(F,6,FN), REGNUM(F,7, FN),
20232
20233 /* VFP SP registers. */
5287ad62
JB
20234 REGSET(s,VFS), REGSET(S,VFS),
20235 REGSETH(s,VFS), REGSETH(S,VFS),
c19d1205
ZW
20236
20237 /* VFP DP Registers. */
5287ad62
JB
20238 REGSET(d,VFD), REGSET(D,VFD),
20239 /* Extra Neon DP registers. */
20240 REGSETH(d,VFD), REGSETH(D,VFD),
20241
20242 /* Neon QP registers. */
20243 REGSET2(q,NQ), REGSET2(Q,NQ),
c19d1205
ZW
20244
20245 /* VFP control registers. */
20246 REGDEF(fpsid,0,VFC), REGDEF(fpscr,1,VFC), REGDEF(fpexc,8,VFC),
20247 REGDEF(FPSID,0,VFC), REGDEF(FPSCR,1,VFC), REGDEF(FPEXC,8,VFC),
cd2cf30b
PB
20248 REGDEF(fpinst,9,VFC), REGDEF(fpinst2,10,VFC),
20249 REGDEF(FPINST,9,VFC), REGDEF(FPINST2,10,VFC),
20250 REGDEF(mvfr0,7,VFC), REGDEF(mvfr1,6,VFC),
20251 REGDEF(MVFR0,7,VFC), REGDEF(MVFR1,6,VFC),
40c7d507 20252 REGDEF(mvfr2,5,VFC), REGDEF(MVFR2,5,VFC),
c19d1205
ZW
20253
20254 /* Maverick DSP coprocessor registers. */
20255 REGSET(mvf,MVF), REGSET(mvd,MVD), REGSET(mvfx,MVFX), REGSET(mvdx,MVDX),
20256 REGSET(MVF,MVF), REGSET(MVD,MVD), REGSET(MVFX,MVFX), REGSET(MVDX,MVDX),
20257
20258 REGNUM(mvax,0,MVAX), REGNUM(mvax,1,MVAX),
20259 REGNUM(mvax,2,MVAX), REGNUM(mvax,3,MVAX),
20260 REGDEF(dspsc,0,DSPSC),
20261
20262 REGNUM(MVAX,0,MVAX), REGNUM(MVAX,1,MVAX),
20263 REGNUM(MVAX,2,MVAX), REGNUM(MVAX,3,MVAX),
20264 REGDEF(DSPSC,0,DSPSC),
20265
20266 /* iWMMXt data registers - p0, c0-15. */
20267 REGSET(wr,MMXWR), REGSET(wR,MMXWR), REGSET(WR, MMXWR),
20268
20269 /* iWMMXt control registers - p1, c0-3. */
20270 REGDEF(wcid, 0,MMXWC), REGDEF(wCID, 0,MMXWC), REGDEF(WCID, 0,MMXWC),
20271 REGDEF(wcon, 1,MMXWC), REGDEF(wCon, 1,MMXWC), REGDEF(WCON, 1,MMXWC),
20272 REGDEF(wcssf, 2,MMXWC), REGDEF(wCSSF, 2,MMXWC), REGDEF(WCSSF, 2,MMXWC),
20273 REGDEF(wcasf, 3,MMXWC), REGDEF(wCASF, 3,MMXWC), REGDEF(WCASF, 3,MMXWC),
20274
20275 /* iWMMXt scalar (constant/offset) registers - p1, c8-11. */
20276 REGDEF(wcgr0, 8,MMXWCG), REGDEF(wCGR0, 8,MMXWCG), REGDEF(WCGR0, 8,MMXWCG),
20277 REGDEF(wcgr1, 9,MMXWCG), REGDEF(wCGR1, 9,MMXWCG), REGDEF(WCGR1, 9,MMXWCG),
20278 REGDEF(wcgr2,10,MMXWCG), REGDEF(wCGR2,10,MMXWCG), REGDEF(WCGR2,10,MMXWCG),
20279 REGDEF(wcgr3,11,MMXWCG), REGDEF(wCGR3,11,MMXWCG), REGDEF(WCGR3,11,MMXWCG),
20280
20281 /* XScale accumulator registers. */
20282 REGNUM(acc,0,XSCALE), REGNUM(ACC,0,XSCALE),
20283};
20284#undef REGDEF
20285#undef REGNUM
20286#undef REGSET
7ed4c4c5 20287
c19d1205
ZW
20288/* Table of all PSR suffixes. Bare "CPSR" and "SPSR" are handled
20289 within psr_required_here. */
20290static const struct asm_psr psrs[] =
20291{
20292 /* Backward compatibility notation. Note that "all" is no longer
20293 truly all possible PSR bits. */
20294 {"all", PSR_c | PSR_f},
20295 {"flg", PSR_f},
20296 {"ctl", PSR_c},
20297
20298 /* Individual flags. */
20299 {"f", PSR_f},
20300 {"c", PSR_c},
20301 {"x", PSR_x},
20302 {"s", PSR_s},
59b42a0d 20303
c19d1205
ZW
20304 /* Combinations of flags. */
20305 {"fs", PSR_f | PSR_s},
20306 {"fx", PSR_f | PSR_x},
20307 {"fc", PSR_f | PSR_c},
20308 {"sf", PSR_s | PSR_f},
20309 {"sx", PSR_s | PSR_x},
20310 {"sc", PSR_s | PSR_c},
20311 {"xf", PSR_x | PSR_f},
20312 {"xs", PSR_x | PSR_s},
20313 {"xc", PSR_x | PSR_c},
20314 {"cf", PSR_c | PSR_f},
20315 {"cs", PSR_c | PSR_s},
20316 {"cx", PSR_c | PSR_x},
20317 {"fsx", PSR_f | PSR_s | PSR_x},
20318 {"fsc", PSR_f | PSR_s | PSR_c},
20319 {"fxs", PSR_f | PSR_x | PSR_s},
20320 {"fxc", PSR_f | PSR_x | PSR_c},
20321 {"fcs", PSR_f | PSR_c | PSR_s},
20322 {"fcx", PSR_f | PSR_c | PSR_x},
20323 {"sfx", PSR_s | PSR_f | PSR_x},
20324 {"sfc", PSR_s | PSR_f | PSR_c},
20325 {"sxf", PSR_s | PSR_x | PSR_f},
20326 {"sxc", PSR_s | PSR_x | PSR_c},
20327 {"scf", PSR_s | PSR_c | PSR_f},
20328 {"scx", PSR_s | PSR_c | PSR_x},
20329 {"xfs", PSR_x | PSR_f | PSR_s},
20330 {"xfc", PSR_x | PSR_f | PSR_c},
20331 {"xsf", PSR_x | PSR_s | PSR_f},
20332 {"xsc", PSR_x | PSR_s | PSR_c},
20333 {"xcf", PSR_x | PSR_c | PSR_f},
20334 {"xcs", PSR_x | PSR_c | PSR_s},
20335 {"cfs", PSR_c | PSR_f | PSR_s},
20336 {"cfx", PSR_c | PSR_f | PSR_x},
20337 {"csf", PSR_c | PSR_s | PSR_f},
20338 {"csx", PSR_c | PSR_s | PSR_x},
20339 {"cxf", PSR_c | PSR_x | PSR_f},
20340 {"cxs", PSR_c | PSR_x | PSR_s},
20341 {"fsxc", PSR_f | PSR_s | PSR_x | PSR_c},
20342 {"fscx", PSR_f | PSR_s | PSR_c | PSR_x},
20343 {"fxsc", PSR_f | PSR_x | PSR_s | PSR_c},
20344 {"fxcs", PSR_f | PSR_x | PSR_c | PSR_s},
20345 {"fcsx", PSR_f | PSR_c | PSR_s | PSR_x},
20346 {"fcxs", PSR_f | PSR_c | PSR_x | PSR_s},
20347 {"sfxc", PSR_s | PSR_f | PSR_x | PSR_c},
20348 {"sfcx", PSR_s | PSR_f | PSR_c | PSR_x},
20349 {"sxfc", PSR_s | PSR_x | PSR_f | PSR_c},
20350 {"sxcf", PSR_s | PSR_x | PSR_c | PSR_f},
20351 {"scfx", PSR_s | PSR_c | PSR_f | PSR_x},
20352 {"scxf", PSR_s | PSR_c | PSR_x | PSR_f},
20353 {"xfsc", PSR_x | PSR_f | PSR_s | PSR_c},
20354 {"xfcs", PSR_x | PSR_f | PSR_c | PSR_s},
20355 {"xsfc", PSR_x | PSR_s | PSR_f | PSR_c},
20356 {"xscf", PSR_x | PSR_s | PSR_c | PSR_f},
20357 {"xcfs", PSR_x | PSR_c | PSR_f | PSR_s},
20358 {"xcsf", PSR_x | PSR_c | PSR_s | PSR_f},
20359 {"cfsx", PSR_c | PSR_f | PSR_s | PSR_x},
20360 {"cfxs", PSR_c | PSR_f | PSR_x | PSR_s},
20361 {"csfx", PSR_c | PSR_s | PSR_f | PSR_x},
20362 {"csxf", PSR_c | PSR_s | PSR_x | PSR_f},
20363 {"cxfs", PSR_c | PSR_x | PSR_f | PSR_s},
20364 {"cxsf", PSR_c | PSR_x | PSR_s | PSR_f},
20365};
20366
62b3e311
PB
20367/* Table of V7M psr names. */
20368static const struct asm_psr v7m_psrs[] =
20369{
1a336194
TP
20370 {"apsr", 0x0 }, {"APSR", 0x0 },
20371 {"iapsr", 0x1 }, {"IAPSR", 0x1 },
20372 {"eapsr", 0x2 }, {"EAPSR", 0x2 },
20373 {"psr", 0x3 }, {"PSR", 0x3 },
20374 {"xpsr", 0x3 }, {"XPSR", 0x3 }, {"xPSR", 3 },
20375 {"ipsr", 0x5 }, {"IPSR", 0x5 },
20376 {"epsr", 0x6 }, {"EPSR", 0x6 },
20377 {"iepsr", 0x7 }, {"IEPSR", 0x7 },
20378 {"msp", 0x8 }, {"MSP", 0x8 },
20379 {"psp", 0x9 }, {"PSP", 0x9 },
20380 {"msplim", 0xa }, {"MSPLIM", 0xa },
20381 {"psplim", 0xb }, {"PSPLIM", 0xb },
20382 {"primask", 0x10}, {"PRIMASK", 0x10},
20383 {"basepri", 0x11}, {"BASEPRI", 0x11},
20384 {"basepri_max", 0x12}, {"BASEPRI_MAX", 0x12},
1a336194
TP
20385 {"faultmask", 0x13}, {"FAULTMASK", 0x13},
20386 {"control", 0x14}, {"CONTROL", 0x14},
20387 {"msp_ns", 0x88}, {"MSP_NS", 0x88},
20388 {"psp_ns", 0x89}, {"PSP_NS", 0x89},
20389 {"msplim_ns", 0x8a}, {"MSPLIM_NS", 0x8a},
20390 {"psplim_ns", 0x8b}, {"PSPLIM_NS", 0x8b},
20391 {"primask_ns", 0x90}, {"PRIMASK_NS", 0x90},
20392 {"basepri_ns", 0x91}, {"BASEPRI_NS", 0x91},
20393 {"faultmask_ns", 0x93}, {"FAULTMASK_NS", 0x93},
20394 {"control_ns", 0x94}, {"CONTROL_NS", 0x94},
20395 {"sp_ns", 0x98}, {"SP_NS", 0x98 }
62b3e311
PB
20396};
20397
c19d1205
ZW
20398/* Table of all shift-in-operand names. */
20399static const struct asm_shift_name shift_names [] =
b99bd4ef 20400{
c19d1205
ZW
20401 { "asl", SHIFT_LSL }, { "ASL", SHIFT_LSL },
20402 { "lsl", SHIFT_LSL }, { "LSL", SHIFT_LSL },
20403 { "lsr", SHIFT_LSR }, { "LSR", SHIFT_LSR },
20404 { "asr", SHIFT_ASR }, { "ASR", SHIFT_ASR },
20405 { "ror", SHIFT_ROR }, { "ROR", SHIFT_ROR },
20406 { "rrx", SHIFT_RRX }, { "RRX", SHIFT_RRX }
20407};
b99bd4ef 20408
c19d1205
ZW
20409/* Table of all explicit relocation names. */
20410#ifdef OBJ_ELF
20411static struct reloc_entry reloc_names[] =
20412{
20413 { "got", BFD_RELOC_ARM_GOT32 }, { "GOT", BFD_RELOC_ARM_GOT32 },
20414 { "gotoff", BFD_RELOC_ARM_GOTOFF }, { "GOTOFF", BFD_RELOC_ARM_GOTOFF },
20415 { "plt", BFD_RELOC_ARM_PLT32 }, { "PLT", BFD_RELOC_ARM_PLT32 },
20416 { "target1", BFD_RELOC_ARM_TARGET1 }, { "TARGET1", BFD_RELOC_ARM_TARGET1 },
20417 { "target2", BFD_RELOC_ARM_TARGET2 }, { "TARGET2", BFD_RELOC_ARM_TARGET2 },
20418 { "sbrel", BFD_RELOC_ARM_SBREL32 }, { "SBREL", BFD_RELOC_ARM_SBREL32 },
20419 { "tlsgd", BFD_RELOC_ARM_TLS_GD32}, { "TLSGD", BFD_RELOC_ARM_TLS_GD32},
20420 { "tlsldm", BFD_RELOC_ARM_TLS_LDM32}, { "TLSLDM", BFD_RELOC_ARM_TLS_LDM32},
20421 { "tlsldo", BFD_RELOC_ARM_TLS_LDO32}, { "TLSLDO", BFD_RELOC_ARM_TLS_LDO32},
20422 { "gottpoff",BFD_RELOC_ARM_TLS_IE32}, { "GOTTPOFF",BFD_RELOC_ARM_TLS_IE32},
b43420e6 20423 { "tpoff", BFD_RELOC_ARM_TLS_LE32}, { "TPOFF", BFD_RELOC_ARM_TLS_LE32},
0855e32b
NS
20424 { "got_prel", BFD_RELOC_ARM_GOT_PREL}, { "GOT_PREL", BFD_RELOC_ARM_GOT_PREL},
20425 { "tlsdesc", BFD_RELOC_ARM_TLS_GOTDESC},
477330fc 20426 { "TLSDESC", BFD_RELOC_ARM_TLS_GOTDESC},
0855e32b 20427 { "tlscall", BFD_RELOC_ARM_TLS_CALL},
477330fc 20428 { "TLSCALL", BFD_RELOC_ARM_TLS_CALL},
0855e32b 20429 { "tlsdescseq", BFD_RELOC_ARM_TLS_DESCSEQ},
188fd7ae
CL
20430 { "TLSDESCSEQ", BFD_RELOC_ARM_TLS_DESCSEQ},
20431 { "gotfuncdesc", BFD_RELOC_ARM_GOTFUNCDESC },
20432 { "GOTFUNCDESC", BFD_RELOC_ARM_GOTFUNCDESC },
20433 { "gotofffuncdesc", BFD_RELOC_ARM_GOTOFFFUNCDESC },
20434 { "GOTOFFFUNCDESC", BFD_RELOC_ARM_GOTOFFFUNCDESC },
20435 { "funcdesc", BFD_RELOC_ARM_FUNCDESC },
5c5a4843
CL
20436 { "FUNCDESC", BFD_RELOC_ARM_FUNCDESC },
20437 { "tlsgd_fdpic", BFD_RELOC_ARM_TLS_GD32_FDPIC }, { "TLSGD_FDPIC", BFD_RELOC_ARM_TLS_GD32_FDPIC },
20438 { "tlsldm_fdpic", BFD_RELOC_ARM_TLS_LDM32_FDPIC }, { "TLSLDM_FDPIC", BFD_RELOC_ARM_TLS_LDM32_FDPIC },
20439 { "gottpoff_fdpic", BFD_RELOC_ARM_TLS_IE32_FDPIC }, { "GOTTPOFF_FDIC", BFD_RELOC_ARM_TLS_IE32_FDPIC },
c19d1205
ZW
20440};
20441#endif
b99bd4ef 20442
5ee91343 20443/* Table of all conditional affixes. */
c19d1205
ZW
20444static const struct asm_cond conds[] =
20445{
20446 {"eq", 0x0},
20447 {"ne", 0x1},
20448 {"cs", 0x2}, {"hs", 0x2},
20449 {"cc", 0x3}, {"ul", 0x3}, {"lo", 0x3},
20450 {"mi", 0x4},
20451 {"pl", 0x5},
20452 {"vs", 0x6},
20453 {"vc", 0x7},
20454 {"hi", 0x8},
20455 {"ls", 0x9},
20456 {"ge", 0xa},
20457 {"lt", 0xb},
20458 {"gt", 0xc},
20459 {"le", 0xd},
20460 {"al", 0xe}
20461};
5ee91343
AV
20462static const struct asm_cond vconds[] =
20463{
20464 {"t", 0xf},
20465 {"e", 0x10}
20466};
bfae80f2 20467
e797f7e0 20468#define UL_BARRIER(L,U,CODE,FEAT) \
823d2571
TG
20469 { L, CODE, ARM_FEATURE_CORE_LOW (FEAT) }, \
20470 { U, CODE, ARM_FEATURE_CORE_LOW (FEAT) }
e797f7e0 20471
62b3e311
PB
20472static struct asm_barrier_opt barrier_opt_names[] =
20473{
e797f7e0
MGD
20474 UL_BARRIER ("sy", "SY", 0xf, ARM_EXT_BARRIER),
20475 UL_BARRIER ("st", "ST", 0xe, ARM_EXT_BARRIER),
20476 UL_BARRIER ("ld", "LD", 0xd, ARM_EXT_V8),
20477 UL_BARRIER ("ish", "ISH", 0xb, ARM_EXT_BARRIER),
20478 UL_BARRIER ("sh", "SH", 0xb, ARM_EXT_BARRIER),
20479 UL_BARRIER ("ishst", "ISHST", 0xa, ARM_EXT_BARRIER),
20480 UL_BARRIER ("shst", "SHST", 0xa, ARM_EXT_BARRIER),
20481 UL_BARRIER ("ishld", "ISHLD", 0x9, ARM_EXT_V8),
20482 UL_BARRIER ("un", "UN", 0x7, ARM_EXT_BARRIER),
20483 UL_BARRIER ("nsh", "NSH", 0x7, ARM_EXT_BARRIER),
20484 UL_BARRIER ("unst", "UNST", 0x6, ARM_EXT_BARRIER),
20485 UL_BARRIER ("nshst", "NSHST", 0x6, ARM_EXT_BARRIER),
20486 UL_BARRIER ("nshld", "NSHLD", 0x5, ARM_EXT_V8),
20487 UL_BARRIER ("osh", "OSH", 0x3, ARM_EXT_BARRIER),
20488 UL_BARRIER ("oshst", "OSHST", 0x2, ARM_EXT_BARRIER),
20489 UL_BARRIER ("oshld", "OSHLD", 0x1, ARM_EXT_V8)
62b3e311
PB
20490};
20491
e797f7e0
MGD
20492#undef UL_BARRIER
20493
c19d1205
ZW
20494/* Table of ARM-format instructions. */
20495
20496/* Macros for gluing together operand strings. N.B. In all cases
20497 other than OPS0, the trailing OP_stop comes from default
20498 zero-initialization of the unspecified elements of the array. */
20499#define OPS0() { OP_stop, }
20500#define OPS1(a) { OP_##a, }
20501#define OPS2(a,b) { OP_##a,OP_##b, }
20502#define OPS3(a,b,c) { OP_##a,OP_##b,OP_##c, }
20503#define OPS4(a,b,c,d) { OP_##a,OP_##b,OP_##c,OP_##d, }
20504#define OPS5(a,b,c,d,e) { OP_##a,OP_##b,OP_##c,OP_##d,OP_##e, }
20505#define OPS6(a,b,c,d,e,f) { OP_##a,OP_##b,OP_##c,OP_##d,OP_##e,OP_##f, }
20506
5be8be5d
DG
20507/* These macros are similar to the OPSn, but do not prepend the OP_ prefix.
20508 This is useful when mixing operands for ARM and THUMB, i.e. using the
20509 MIX_ARM_THUMB_OPERANDS macro.
20510 In order to use these macros, prefix the number of operands with _
20511 e.g. _3. */
20512#define OPS_1(a) { a, }
20513#define OPS_2(a,b) { a,b, }
20514#define OPS_3(a,b,c) { a,b,c, }
20515#define OPS_4(a,b,c,d) { a,b,c,d, }
20516#define OPS_5(a,b,c,d,e) { a,b,c,d,e, }
20517#define OPS_6(a,b,c,d,e,f) { a,b,c,d,e,f, }
20518
c19d1205
ZW
20519/* These macros abstract out the exact format of the mnemonic table and
20520 save some repeated characters. */
20521
20522/* The normal sort of mnemonic; has a Thumb variant; takes a conditional suffix. */
20523#define TxCE(mnem, op, top, nops, ops, ae, te) \
21d799b5 20524 { mnem, OPS##nops ops, OT_csuffix, 0x##op, top, ARM_VARIANT, \
5ee91343 20525 THUMB_VARIANT, do_##ae, do_##te, 0 }
c19d1205
ZW
20526
20527/* Two variants of the above - TCE for a numeric Thumb opcode, tCE for
20528 a T_MNEM_xyz enumerator. */
20529#define TCE(mnem, aop, top, nops, ops, ae, te) \
e07e6e58 20530 TxCE (mnem, aop, 0x##top, nops, ops, ae, te)
c19d1205 20531#define tCE(mnem, aop, top, nops, ops, ae, te) \
21d799b5 20532 TxCE (mnem, aop, T_MNEM##top, nops, ops, ae, te)
c19d1205
ZW
20533
20534/* Second most common sort of mnemonic: has a Thumb variant, takes a conditional
20535 infix after the third character. */
20536#define TxC3(mnem, op, top, nops, ops, ae, te) \
21d799b5 20537 { mnem, OPS##nops ops, OT_cinfix3, 0x##op, top, ARM_VARIANT, \
5ee91343 20538 THUMB_VARIANT, do_##ae, do_##te, 0 }
088fa78e 20539#define TxC3w(mnem, op, top, nops, ops, ae, te) \
21d799b5 20540 { mnem, OPS##nops ops, OT_cinfix3_deprecated, 0x##op, top, ARM_VARIANT, \
5ee91343 20541 THUMB_VARIANT, do_##ae, do_##te, 0 }
c19d1205 20542#define TC3(mnem, aop, top, nops, ops, ae, te) \
e07e6e58 20543 TxC3 (mnem, aop, 0x##top, nops, ops, ae, te)
088fa78e 20544#define TC3w(mnem, aop, top, nops, ops, ae, te) \
e07e6e58 20545 TxC3w (mnem, aop, 0x##top, nops, ops, ae, te)
c19d1205 20546#define tC3(mnem, aop, top, nops, ops, ae, te) \
21d799b5 20547 TxC3 (mnem, aop, T_MNEM##top, nops, ops, ae, te)
088fa78e 20548#define tC3w(mnem, aop, top, nops, ops, ae, te) \
21d799b5 20549 TxC3w (mnem, aop, T_MNEM##top, nops, ops, ae, te)
c19d1205 20550
c19d1205 20551/* Mnemonic that cannot be conditionalized. The ARM condition-code
dfa9f0d5
PB
20552 field is still 0xE. Many of the Thumb variants can be executed
20553 conditionally, so this is checked separately. */
c19d1205 20554#define TUE(mnem, op, top, nops, ops, ae, te) \
21d799b5 20555 { mnem, OPS##nops ops, OT_unconditional, 0x##op, 0x##top, ARM_VARIANT, \
5ee91343 20556 THUMB_VARIANT, do_##ae, do_##te, 0 }
c19d1205 20557
dd5181d5
KT
20558/* Same as TUE but the encoding function for ARM and Thumb modes is the same.
20559 Used by mnemonics that have very minimal differences in the encoding for
20560 ARM and Thumb variants and can be handled in a common function. */
20561#define TUEc(mnem, op, top, nops, ops, en) \
20562 { mnem, OPS##nops ops, OT_unconditional, 0x##op, 0x##top, ARM_VARIANT, \
5ee91343 20563 THUMB_VARIANT, do_##en, do_##en, 0 }
dd5181d5 20564
c19d1205
ZW
20565/* Mnemonic that cannot be conditionalized, and bears 0xF in its ARM
20566 condition code field. */
20567#define TUF(mnem, op, top, nops, ops, ae, te) \
21d799b5 20568 { mnem, OPS##nops ops, OT_unconditionalF, 0x##op, 0x##top, ARM_VARIANT, \
5ee91343 20569 THUMB_VARIANT, do_##ae, do_##te, 0 }
c19d1205
ZW
20570
20571/* ARM-only variants of all the above. */
6a86118a 20572#define CE(mnem, op, nops, ops, ae) \
5ee91343 20573 { mnem, OPS##nops ops, OT_csuffix, 0x##op, 0x0, ARM_VARIANT, 0, do_##ae, NULL, 0 }
6a86118a
NC
20574
20575#define C3(mnem, op, nops, ops, ae) \
5ee91343 20576 { #mnem, OPS##nops ops, OT_cinfix3, 0x##op, 0x0, ARM_VARIANT, 0, do_##ae, NULL, 0 }
6a86118a 20577
cf3cf39d
TP
20578/* Thumb-only variants of TCE and TUE. */
20579#define ToC(mnem, top, nops, ops, te) \
20580 { mnem, OPS##nops ops, OT_csuffix, 0x0, 0x##top, 0, THUMB_VARIANT, NULL, \
5ee91343 20581 do_##te, 0 }
cf3cf39d
TP
20582
20583#define ToU(mnem, top, nops, ops, te) \
20584 { mnem, OPS##nops ops, OT_unconditional, 0x0, 0x##top, 0, THUMB_VARIANT, \
5ee91343 20585 NULL, do_##te, 0 }
cf3cf39d 20586
4389b29a
AV
20587/* T_MNEM_xyz enumerator variants of ToC. */
20588#define toC(mnem, top, nops, ops, te) \
20589 { mnem, OPS##nops ops, OT_csuffix, 0x0, T_MNEM##top, 0, THUMB_VARIANT, NULL, \
5ee91343 20590 do_##te, 0 }
4389b29a 20591
f6b2b12d
AV
20592/* T_MNEM_xyz enumerator variants of ToU. */
20593#define toU(mnem, top, nops, ops, te) \
20594 { mnem, OPS##nops ops, OT_unconditional, 0x0, T_MNEM##top, 0, THUMB_VARIANT, \
5ee91343 20595 NULL, do_##te, 0 }
f6b2b12d 20596
e3cb604e
PB
20597/* Legacy mnemonics that always have conditional infix after the third
20598 character. */
20599#define CL(mnem, op, nops, ops, ae) \
21d799b5 20600 { mnem, OPS##nops ops, OT_cinfix3_legacy, \
5ee91343 20601 0x##op, 0x0, ARM_VARIANT, 0, do_##ae, NULL, 0 }
e3cb604e 20602
8f06b2d8
PB
20603/* Coprocessor instructions. Isomorphic between Arm and Thumb-2. */
20604#define cCE(mnem, op, nops, ops, ae) \
5ee91343 20605 { mnem, OPS##nops ops, OT_csuffix, 0x##op, 0xe##op, ARM_VARIANT, ARM_VARIANT, do_##ae, do_##ae, 0 }
8f06b2d8 20606
e3cb604e
PB
20607/* Legacy coprocessor instructions where conditional infix and conditional
20608 suffix are ambiguous. For consistency this includes all FPA instructions,
20609 not just the potentially ambiguous ones. */
20610#define cCL(mnem, op, nops, ops, ae) \
21d799b5 20611 { mnem, OPS##nops ops, OT_cinfix3_legacy, \
5ee91343 20612 0x##op, 0xe##op, ARM_VARIANT, ARM_VARIANT, do_##ae, do_##ae, 0 }
e3cb604e
PB
20613
20614/* Coprocessor, takes either a suffix or a position-3 infix
20615 (for an FPA corner case). */
20616#define C3E(mnem, op, nops, ops, ae) \
21d799b5 20617 { mnem, OPS##nops ops, OT_csuf_or_in3, \
5ee91343 20618 0x##op, 0xe##op, ARM_VARIANT, ARM_VARIANT, do_##ae, do_##ae, 0 }
8f06b2d8 20619
6a86118a 20620#define xCM_(m1, m2, m3, op, nops, ops, ae) \
21d799b5
NC
20621 { m1 #m2 m3, OPS##nops ops, \
20622 sizeof (#m2) == 1 ? OT_odd_infix_unc : OT_odd_infix_0 + sizeof (m1) - 1, \
5ee91343 20623 0x##op, 0x0, ARM_VARIANT, 0, do_##ae, NULL, 0 }
6a86118a
NC
20624
20625#define CM(m1, m2, op, nops, ops, ae) \
e07e6e58
NC
20626 xCM_ (m1, , m2, op, nops, ops, ae), \
20627 xCM_ (m1, eq, m2, op, nops, ops, ae), \
20628 xCM_ (m1, ne, m2, op, nops, ops, ae), \
20629 xCM_ (m1, cs, m2, op, nops, ops, ae), \
20630 xCM_ (m1, hs, m2, op, nops, ops, ae), \
20631 xCM_ (m1, cc, m2, op, nops, ops, ae), \
20632 xCM_ (m1, ul, m2, op, nops, ops, ae), \
20633 xCM_ (m1, lo, m2, op, nops, ops, ae), \
20634 xCM_ (m1, mi, m2, op, nops, ops, ae), \
20635 xCM_ (m1, pl, m2, op, nops, ops, ae), \
20636 xCM_ (m1, vs, m2, op, nops, ops, ae), \
20637 xCM_ (m1, vc, m2, op, nops, ops, ae), \
20638 xCM_ (m1, hi, m2, op, nops, ops, ae), \
20639 xCM_ (m1, ls, m2, op, nops, ops, ae), \
20640 xCM_ (m1, ge, m2, op, nops, ops, ae), \
20641 xCM_ (m1, lt, m2, op, nops, ops, ae), \
20642 xCM_ (m1, gt, m2, op, nops, ops, ae), \
20643 xCM_ (m1, le, m2, op, nops, ops, ae), \
20644 xCM_ (m1, al, m2, op, nops, ops, ae)
6a86118a
NC
20645
20646#define UE(mnem, op, nops, ops, ae) \
5ee91343 20647 { #mnem, OPS##nops ops, OT_unconditional, 0x##op, 0, ARM_VARIANT, 0, do_##ae, NULL, 0 }
6a86118a
NC
20648
20649#define UF(mnem, op, nops, ops, ae) \
5ee91343 20650 { #mnem, OPS##nops ops, OT_unconditionalF, 0x##op, 0, ARM_VARIANT, 0, do_##ae, NULL, 0 }
6a86118a 20651
5287ad62
JB
20652/* Neon data-processing. ARM versions are unconditional with cond=0xf.
20653 The Thumb and ARM variants are mostly the same (bits 0-23 and 24/28), so we
20654 use the same encoding function for each. */
20655#define NUF(mnem, op, nops, ops, enc) \
20656 { #mnem, OPS##nops ops, OT_unconditionalF, 0x##op, 0x##op, \
5ee91343 20657 ARM_VARIANT, THUMB_VARIANT, do_##enc, do_##enc, 0 }
5287ad62
JB
20658
20659/* Neon data processing, version which indirects through neon_enc_tab for
20660 the various overloaded versions of opcodes. */
20661#define nUF(mnem, op, nops, ops, enc) \
21d799b5 20662 { #mnem, OPS##nops ops, OT_unconditionalF, N_MNEM##op, N_MNEM##op, \
5ee91343 20663 ARM_VARIANT, THUMB_VARIANT, do_##enc, do_##enc, 0 }
5287ad62
JB
20664
20665/* Neon insn with conditional suffix for the ARM version, non-overloaded
20666 version. */
5ee91343 20667#define NCE_tag(mnem, op, nops, ops, enc, tag, mve_p) \
037e8744 20668 { #mnem, OPS##nops ops, tag, 0x##op, 0x##op, ARM_VARIANT, \
5ee91343 20669 THUMB_VARIANT, do_##enc, do_##enc, mve_p }
5287ad62 20670
037e8744 20671#define NCE(mnem, op, nops, ops, enc) \
5ee91343 20672 NCE_tag (mnem, op, nops, ops, enc, OT_csuffix, 0)
037e8744
JB
20673
20674#define NCEF(mnem, op, nops, ops, enc) \
5ee91343 20675 NCE_tag (mnem, op, nops, ops, enc, OT_csuffixF, 0)
037e8744 20676
5287ad62 20677/* Neon insn with conditional suffix for the ARM version, overloaded types. */
5ee91343 20678#define nCE_tag(mnem, op, nops, ops, enc, tag, mve_p) \
21d799b5 20679 { #mnem, OPS##nops ops, tag, N_MNEM##op, N_MNEM##op, \
5ee91343 20680 ARM_VARIANT, THUMB_VARIANT, do_##enc, do_##enc, mve_p }
5287ad62 20681
037e8744 20682#define nCE(mnem, op, nops, ops, enc) \
5ee91343 20683 nCE_tag (mnem, op, nops, ops, enc, OT_csuffix, 0)
037e8744
JB
20684
20685#define nCEF(mnem, op, nops, ops, enc) \
5ee91343
AV
20686 nCE_tag (mnem, op, nops, ops, enc, OT_csuffixF, 0)
20687
20688/* */
20689#define mCEF(mnem, op, nops, ops, enc) \
a302e574 20690 { #mnem, OPS##nops ops, OT_csuffixF, M_MNEM##op, M_MNEM##op, \
5ee91343
AV
20691 ARM_VARIANT, THUMB_VARIANT, do_##enc, do_##enc, 1 }
20692
20693
20694/* nCEF but for MVE predicated instructions. */
20695#define mnCEF(mnem, op, nops, ops, enc) \
20696 nCE_tag (mnem, op, nops, ops, enc, OT_csuffixF, 1)
20697
20698/* nCE but for MVE predicated instructions. */
20699#define mnCE(mnem, op, nops, ops, enc) \
20700 nCE_tag (mnem, op, nops, ops, enc, OT_csuffix, 1)
037e8744 20701
5ee91343
AV
20702/* NUF but for potentially MVE predicated instructions. */
20703#define MNUF(mnem, op, nops, ops, enc) \
20704 { #mnem, OPS##nops ops, OT_unconditionalF, 0x##op, 0x##op, \
20705 ARM_VARIANT, THUMB_VARIANT, do_##enc, do_##enc, 1 }
20706
20707/* nUF but for potentially MVE predicated instructions. */
20708#define mnUF(mnem, op, nops, ops, enc) \
20709 { #mnem, OPS##nops ops, OT_unconditionalF, N_MNEM##op, N_MNEM##op, \
20710 ARM_VARIANT, THUMB_VARIANT, do_##enc, do_##enc, 1 }
20711
20712/* ToC but for potentially MVE predicated instructions. */
20713#define mToC(mnem, top, nops, ops, te) \
20714 { mnem, OPS##nops ops, OT_csuffix, 0x0, 0x##top, 0, THUMB_VARIANT, NULL, \
20715 do_##te, 1 }
20716
20717/* NCE but for MVE predicated instructions. */
20718#define MNCE(mnem, op, nops, ops, enc) \
20719 NCE_tag (mnem, op, nops, ops, enc, OT_csuffix, 1)
20720
20721/* NCEF but for MVE predicated instructions. */
20722#define MNCEF(mnem, op, nops, ops, enc) \
20723 NCE_tag (mnem, op, nops, ops, enc, OT_csuffixF, 1)
c19d1205
ZW
20724#define do_0 0
20725
c19d1205 20726static const struct asm_opcode insns[] =
bfae80f2 20727{
74db7efb
NC
20728#define ARM_VARIANT & arm_ext_v1 /* Core ARM Instructions. */
20729#define THUMB_VARIANT & arm_ext_v4t
21d799b5
NC
20730 tCE("and", 0000000, _and, 3, (RR, oRR, SH), arit, t_arit3c),
20731 tC3("ands", 0100000, _ands, 3, (RR, oRR, SH), arit, t_arit3c),
20732 tCE("eor", 0200000, _eor, 3, (RR, oRR, SH), arit, t_arit3c),
20733 tC3("eors", 0300000, _eors, 3, (RR, oRR, SH), arit, t_arit3c),
20734 tCE("sub", 0400000, _sub, 3, (RR, oRR, SH), arit, t_add_sub),
20735 tC3("subs", 0500000, _subs, 3, (RR, oRR, SH), arit, t_add_sub),
20736 tCE("add", 0800000, _add, 3, (RR, oRR, SHG), arit, t_add_sub),
20737 tC3("adds", 0900000, _adds, 3, (RR, oRR, SHG), arit, t_add_sub),
20738 tCE("adc", 0a00000, _adc, 3, (RR, oRR, SH), arit, t_arit3c),
20739 tC3("adcs", 0b00000, _adcs, 3, (RR, oRR, SH), arit, t_arit3c),
20740 tCE("sbc", 0c00000, _sbc, 3, (RR, oRR, SH), arit, t_arit3),
20741 tC3("sbcs", 0d00000, _sbcs, 3, (RR, oRR, SH), arit, t_arit3),
20742 tCE("orr", 1800000, _orr, 3, (RR, oRR, SH), arit, t_arit3c),
20743 tC3("orrs", 1900000, _orrs, 3, (RR, oRR, SH), arit, t_arit3c),
20744 tCE("bic", 1c00000, _bic, 3, (RR, oRR, SH), arit, t_arit3),
20745 tC3("bics", 1d00000, _bics, 3, (RR, oRR, SH), arit, t_arit3),
c19d1205
ZW
20746
20747 /* The p-variants of tst/cmp/cmn/teq (below) are the pre-V6 mechanism
20748 for setting PSR flag bits. They are obsolete in V6 and do not
20749 have Thumb equivalents. */
21d799b5
NC
20750 tCE("tst", 1100000, _tst, 2, (RR, SH), cmp, t_mvn_tst),
20751 tC3w("tsts", 1100000, _tst, 2, (RR, SH), cmp, t_mvn_tst),
20752 CL("tstp", 110f000, 2, (RR, SH), cmp),
20753 tCE("cmp", 1500000, _cmp, 2, (RR, SH), cmp, t_mov_cmp),
20754 tC3w("cmps", 1500000, _cmp, 2, (RR, SH), cmp, t_mov_cmp),
20755 CL("cmpp", 150f000, 2, (RR, SH), cmp),
20756 tCE("cmn", 1700000, _cmn, 2, (RR, SH), cmp, t_mvn_tst),
20757 tC3w("cmns", 1700000, _cmn, 2, (RR, SH), cmp, t_mvn_tst),
20758 CL("cmnp", 170f000, 2, (RR, SH), cmp),
20759
20760 tCE("mov", 1a00000, _mov, 2, (RR, SH), mov, t_mov_cmp),
72d98d16 20761 tC3("movs", 1b00000, _movs, 2, (RR, SHG), mov, t_mov_cmp),
21d799b5
NC
20762 tCE("mvn", 1e00000, _mvn, 2, (RR, SH), mov, t_mvn_tst),
20763 tC3("mvns", 1f00000, _mvns, 2, (RR, SH), mov, t_mvn_tst),
20764
20765 tCE("ldr", 4100000, _ldr, 2, (RR, ADDRGLDR),ldst, t_ldst),
5be8be5d
DG
20766 tC3("ldrb", 4500000, _ldrb, 2, (RRnpc_npcsp, ADDRGLDR),ldst, t_ldst),
20767 tCE("str", 4000000, _str, _2, (MIX_ARM_THUMB_OPERANDS (OP_RR,
20768 OP_RRnpc),
20769 OP_ADDRGLDR),ldst, t_ldst),
20770 tC3("strb", 4400000, _strb, 2, (RRnpc_npcsp, ADDRGLDR),ldst, t_ldst),
21d799b5
NC
20771
20772 tCE("stm", 8800000, _stmia, 2, (RRw, REGLST), ldmstm, t_ldmstm),
20773 tC3("stmia", 8800000, _stmia, 2, (RRw, REGLST), ldmstm, t_ldmstm),
20774 tC3("stmea", 8800000, _stmia, 2, (RRw, REGLST), ldmstm, t_ldmstm),
20775 tCE("ldm", 8900000, _ldmia, 2, (RRw, REGLST), ldmstm, t_ldmstm),
20776 tC3("ldmia", 8900000, _ldmia, 2, (RRw, REGLST), ldmstm, t_ldmstm),
20777 tC3("ldmfd", 8900000, _ldmia, 2, (RRw, REGLST), ldmstm, t_ldmstm),
20778
21d799b5
NC
20779 tCE("b", a000000, _b, 1, (EXPr), branch, t_branch),
20780 TCE("bl", b000000, f000f800, 1, (EXPr), bl, t_branch23),
bfae80f2 20781
c19d1205 20782 /* Pseudo ops. */
21d799b5 20783 tCE("adr", 28f0000, _adr, 2, (RR, EXP), adr, t_adr),
2fc8bdac 20784 C3(adrl, 28f0000, 2, (RR, EXP), adrl),
21d799b5 20785 tCE("nop", 1a00000, _nop, 1, (oI255c), nop, t_nop),
74db7efb 20786 tCE("udf", 7f000f0, _udf, 1, (oIffffb), bkpt, t_udf),
c19d1205
ZW
20787
20788 /* Thumb-compatibility pseudo ops. */
21d799b5
NC
20789 tCE("lsl", 1a00000, _lsl, 3, (RR, oRR, SH), shift, t_shift),
20790 tC3("lsls", 1b00000, _lsls, 3, (RR, oRR, SH), shift, t_shift),
20791 tCE("lsr", 1a00020, _lsr, 3, (RR, oRR, SH), shift, t_shift),
20792 tC3("lsrs", 1b00020, _lsrs, 3, (RR, oRR, SH), shift, t_shift),
20793 tCE("asr", 1a00040, _asr, 3, (RR, oRR, SH), shift, t_shift),
20794 tC3("asrs", 1b00040, _asrs, 3, (RR, oRR, SH), shift, t_shift),
20795 tCE("ror", 1a00060, _ror, 3, (RR, oRR, SH), shift, t_shift),
20796 tC3("rors", 1b00060, _rors, 3, (RR, oRR, SH), shift, t_shift),
20797 tCE("neg", 2600000, _neg, 2, (RR, RR), rd_rn, t_neg),
20798 tC3("negs", 2700000, _negs, 2, (RR, RR), rd_rn, t_neg),
20799 tCE("push", 92d0000, _push, 1, (REGLST), push_pop, t_push_pop),
20800 tCE("pop", 8bd0000, _pop, 1, (REGLST), push_pop, t_push_pop),
c19d1205 20801
16a4cf17 20802 /* These may simplify to neg. */
21d799b5
NC
20803 TCE("rsb", 0600000, ebc00000, 3, (RR, oRR, SH), arit, t_rsb),
20804 TC3("rsbs", 0700000, ebd00000, 3, (RR, oRR, SH), arit, t_rsb),
16a4cf17 20805
173205ca
TP
20806#undef THUMB_VARIANT
20807#define THUMB_VARIANT & arm_ext_os
20808
20809 TCE("swi", f000000, df00, 1, (EXPi), swi, t_swi),
20810 TCE("svc", f000000, df00, 1, (EXPi), swi, t_swi),
20811
c921be7d
NC
20812#undef THUMB_VARIANT
20813#define THUMB_VARIANT & arm_ext_v6
20814
21d799b5 20815 TCE("cpy", 1a00000, 4600, 2, (RR, RR), rd_rm, t_cpy),
c19d1205
ZW
20816
20817 /* V1 instructions with no Thumb analogue prior to V6T2. */
c921be7d
NC
20818#undef THUMB_VARIANT
20819#define THUMB_VARIANT & arm_ext_v6t2
20820
21d799b5
NC
20821 TCE("teq", 1300000, ea900f00, 2, (RR, SH), cmp, t_mvn_tst),
20822 TC3w("teqs", 1300000, ea900f00, 2, (RR, SH), cmp, t_mvn_tst),
20823 CL("teqp", 130f000, 2, (RR, SH), cmp),
c19d1205 20824
5be8be5d
DG
20825 TC3("ldrt", 4300000, f8500e00, 2, (RRnpc_npcsp, ADDR),ldstt, t_ldstt),
20826 TC3("ldrbt", 4700000, f8100e00, 2, (RRnpc_npcsp, ADDR),ldstt, t_ldstt),
20827 TC3("strt", 4200000, f8400e00, 2, (RR_npcsp, ADDR), ldstt, t_ldstt),
20828 TC3("strbt", 4600000, f8000e00, 2, (RRnpc_npcsp, ADDR),ldstt, t_ldstt),
c19d1205 20829
21d799b5
NC
20830 TC3("stmdb", 9000000, e9000000, 2, (RRw, REGLST), ldmstm, t_ldmstm),
20831 TC3("stmfd", 9000000, e9000000, 2, (RRw, REGLST), ldmstm, t_ldmstm),
c19d1205 20832
21d799b5
NC
20833 TC3("ldmdb", 9100000, e9100000, 2, (RRw, REGLST), ldmstm, t_ldmstm),
20834 TC3("ldmea", 9100000, e9100000, 2, (RRw, REGLST), ldmstm, t_ldmstm),
c19d1205
ZW
20835
20836 /* V1 instructions with no Thumb analogue at all. */
21d799b5 20837 CE("rsc", 0e00000, 3, (RR, oRR, SH), arit),
c19d1205
ZW
20838 C3(rscs, 0f00000, 3, (RR, oRR, SH), arit),
20839
20840 C3(stmib, 9800000, 2, (RRw, REGLST), ldmstm),
20841 C3(stmfa, 9800000, 2, (RRw, REGLST), ldmstm),
20842 C3(stmda, 8000000, 2, (RRw, REGLST), ldmstm),
20843 C3(stmed, 8000000, 2, (RRw, REGLST), ldmstm),
20844 C3(ldmib, 9900000, 2, (RRw, REGLST), ldmstm),
20845 C3(ldmed, 9900000, 2, (RRw, REGLST), ldmstm),
20846 C3(ldmda, 8100000, 2, (RRw, REGLST), ldmstm),
20847 C3(ldmfa, 8100000, 2, (RRw, REGLST), ldmstm),
20848
c921be7d
NC
20849#undef ARM_VARIANT
20850#define ARM_VARIANT & arm_ext_v2 /* ARM 2 - multiplies. */
20851#undef THUMB_VARIANT
20852#define THUMB_VARIANT & arm_ext_v4t
20853
21d799b5
NC
20854 tCE("mul", 0000090, _mul, 3, (RRnpc, RRnpc, oRR), mul, t_mul),
20855 tC3("muls", 0100090, _muls, 3, (RRnpc, RRnpc, oRR), mul, t_mul),
c19d1205 20856
c921be7d
NC
20857#undef THUMB_VARIANT
20858#define THUMB_VARIANT & arm_ext_v6t2
20859
21d799b5 20860 TCE("mla", 0200090, fb000000, 4, (RRnpc, RRnpc, RRnpc, RRnpc), mlas, t_mla),
c19d1205
ZW
20861 C3(mlas, 0300090, 4, (RRnpc, RRnpc, RRnpc, RRnpc), mlas),
20862
20863 /* Generic coprocessor instructions. */
21d799b5
NC
20864 TCE("cdp", e000000, ee000000, 6, (RCP, I15b, RCN, RCN, RCN, oI7b), cdp, cdp),
20865 TCE("ldc", c100000, ec100000, 3, (RCP, RCN, ADDRGLDC), lstc, lstc),
20866 TC3("ldcl", c500000, ec500000, 3, (RCP, RCN, ADDRGLDC), lstc, lstc),
20867 TCE("stc", c000000, ec000000, 3, (RCP, RCN, ADDRGLDC), lstc, lstc),
20868 TC3("stcl", c400000, ec400000, 3, (RCP, RCN, ADDRGLDC), lstc, lstc),
20869 TCE("mcr", e000010, ee000010, 6, (RCP, I7b, RR, RCN, RCN, oI7b), co_reg, co_reg),
db472d6f 20870 TCE("mrc", e100010, ee100010, 6, (RCP, I7b, APSR_RR, RCN, RCN, oI7b), co_reg, co_reg),
c19d1205 20871
c921be7d
NC
20872#undef ARM_VARIANT
20873#define ARM_VARIANT & arm_ext_v2s /* ARM 3 - swp instructions. */
20874
21d799b5 20875 CE("swp", 1000090, 3, (RRnpc, RRnpc, RRnpcb), rd_rm_rn),
c19d1205
ZW
20876 C3(swpb, 1400090, 3, (RRnpc, RRnpc, RRnpcb), rd_rm_rn),
20877
c921be7d
NC
20878#undef ARM_VARIANT
20879#define ARM_VARIANT & arm_ext_v3 /* ARM 6 Status register instructions. */
20880#undef THUMB_VARIANT
20881#define THUMB_VARIANT & arm_ext_msr
20882
d2cd1205
JB
20883 TCE("mrs", 1000000, f3e08000, 2, (RRnpc, rPSR), mrs, t_mrs),
20884 TCE("msr", 120f000, f3808000, 2, (wPSR, RR_EXi), msr, t_msr),
c19d1205 20885
c921be7d
NC
20886#undef ARM_VARIANT
20887#define ARM_VARIANT & arm_ext_v3m /* ARM 7M long multiplies. */
20888#undef THUMB_VARIANT
20889#define THUMB_VARIANT & arm_ext_v6t2
20890
21d799b5
NC
20891 TCE("smull", 0c00090, fb800000, 4, (RRnpc, RRnpc, RRnpc, RRnpc), mull, t_mull),
20892 CM("smull","s", 0d00090, 4, (RRnpc, RRnpc, RRnpc, RRnpc), mull),
20893 TCE("umull", 0800090, fba00000, 4, (RRnpc, RRnpc, RRnpc, RRnpc), mull, t_mull),
20894 CM("umull","s", 0900090, 4, (RRnpc, RRnpc, RRnpc, RRnpc), mull),
20895 TCE("smlal", 0e00090, fbc00000, 4, (RRnpc, RRnpc, RRnpc, RRnpc), mull, t_mull),
20896 CM("smlal","s", 0f00090, 4, (RRnpc, RRnpc, RRnpc, RRnpc), mull),
20897 TCE("umlal", 0a00090, fbe00000, 4, (RRnpc, RRnpc, RRnpc, RRnpc), mull, t_mull),
20898 CM("umlal","s", 0b00090, 4, (RRnpc, RRnpc, RRnpc, RRnpc), mull),
c19d1205 20899
c921be7d
NC
20900#undef ARM_VARIANT
20901#define ARM_VARIANT & arm_ext_v4 /* ARM Architecture 4. */
20902#undef THUMB_VARIANT
20903#define THUMB_VARIANT & arm_ext_v4t
20904
5be8be5d
DG
20905 tC3("ldrh", 01000b0, _ldrh, 2, (RRnpc_npcsp, ADDRGLDRS), ldstv4, t_ldst),
20906 tC3("strh", 00000b0, _strh, 2, (RRnpc_npcsp, ADDRGLDRS), ldstv4, t_ldst),
20907 tC3("ldrsh", 01000f0, _ldrsh, 2, (RRnpc_npcsp, ADDRGLDRS), ldstv4, t_ldst),
20908 tC3("ldrsb", 01000d0, _ldrsb, 2, (RRnpc_npcsp, ADDRGLDRS), ldstv4, t_ldst),
56c0a61f
RE
20909 tC3("ldsh", 01000f0, _ldrsh, 2, (RRnpc_npcsp, ADDRGLDRS), ldstv4, t_ldst),
20910 tC3("ldsb", 01000d0, _ldrsb, 2, (RRnpc_npcsp, ADDRGLDRS), ldstv4, t_ldst),
c19d1205 20911
c921be7d
NC
20912#undef ARM_VARIANT
20913#define ARM_VARIANT & arm_ext_v4t_5
20914
c19d1205
ZW
20915 /* ARM Architecture 4T. */
20916 /* Note: bx (and blx) are required on V5, even if the processor does
20917 not support Thumb. */
21d799b5 20918 TCE("bx", 12fff10, 4700, 1, (RR), bx, t_bx),
c19d1205 20919
c921be7d
NC
20920#undef ARM_VARIANT
20921#define ARM_VARIANT & arm_ext_v5 /* ARM Architecture 5T. */
20922#undef THUMB_VARIANT
20923#define THUMB_VARIANT & arm_ext_v5t
20924
c19d1205
ZW
20925 /* Note: blx has 2 variants; the .value coded here is for
20926 BLX(2). Only this variant has conditional execution. */
21d799b5
NC
20927 TCE("blx", 12fff30, 4780, 1, (RR_EXr), blx, t_blx),
20928 TUE("bkpt", 1200070, be00, 1, (oIffffb), bkpt, t_bkpt),
c19d1205 20929
c921be7d
NC
20930#undef THUMB_VARIANT
20931#define THUMB_VARIANT & arm_ext_v6t2
20932
21d799b5
NC
20933 TCE("clz", 16f0f10, fab0f080, 2, (RRnpc, RRnpc), rd_rm, t_clz),
20934 TUF("ldc2", c100000, fc100000, 3, (RCP, RCN, ADDRGLDC), lstc, lstc),
20935 TUF("ldc2l", c500000, fc500000, 3, (RCP, RCN, ADDRGLDC), lstc, lstc),
20936 TUF("stc2", c000000, fc000000, 3, (RCP, RCN, ADDRGLDC), lstc, lstc),
20937 TUF("stc2l", c400000, fc400000, 3, (RCP, RCN, ADDRGLDC), lstc, lstc),
20938 TUF("cdp2", e000000, fe000000, 6, (RCP, I15b, RCN, RCN, RCN, oI7b), cdp, cdp),
20939 TUF("mcr2", e000010, fe000010, 6, (RCP, I7b, RR, RCN, RCN, oI7b), co_reg, co_reg),
20940 TUF("mrc2", e100010, fe100010, 6, (RCP, I7b, RR, RCN, RCN, oI7b), co_reg, co_reg),
c19d1205 20941
c921be7d 20942#undef ARM_VARIANT
74db7efb
NC
20943#define ARM_VARIANT & arm_ext_v5exp /* ARM Architecture 5TExP. */
20944#undef THUMB_VARIANT
20945#define THUMB_VARIANT & arm_ext_v5exp
c921be7d 20946
21d799b5
NC
20947 TCE("smlabb", 1000080, fb100000, 4, (RRnpc, RRnpc, RRnpc, RRnpc), smla, t_mla),
20948 TCE("smlatb", 10000a0, fb100020, 4, (RRnpc, RRnpc, RRnpc, RRnpc), smla, t_mla),
20949 TCE("smlabt", 10000c0, fb100010, 4, (RRnpc, RRnpc, RRnpc, RRnpc), smla, t_mla),
20950 TCE("smlatt", 10000e0, fb100030, 4, (RRnpc, RRnpc, RRnpc, RRnpc), smla, t_mla),
c19d1205 20951
21d799b5
NC
20952 TCE("smlawb", 1200080, fb300000, 4, (RRnpc, RRnpc, RRnpc, RRnpc), smla, t_mla),
20953 TCE("smlawt", 12000c0, fb300010, 4, (RRnpc, RRnpc, RRnpc, RRnpc), smla, t_mla),
c19d1205 20954
21d799b5
NC
20955 TCE("smlalbb", 1400080, fbc00080, 4, (RRnpc, RRnpc, RRnpc, RRnpc), smlal, t_mlal),
20956 TCE("smlaltb", 14000a0, fbc000a0, 4, (RRnpc, RRnpc, RRnpc, RRnpc), smlal, t_mlal),
20957 TCE("smlalbt", 14000c0, fbc00090, 4, (RRnpc, RRnpc, RRnpc, RRnpc), smlal, t_mlal),
20958 TCE("smlaltt", 14000e0, fbc000b0, 4, (RRnpc, RRnpc, RRnpc, RRnpc), smlal, t_mlal),
c19d1205 20959
21d799b5
NC
20960 TCE("smulbb", 1600080, fb10f000, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
20961 TCE("smultb", 16000a0, fb10f020, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
20962 TCE("smulbt", 16000c0, fb10f010, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
20963 TCE("smultt", 16000e0, fb10f030, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
c19d1205 20964
21d799b5
NC
20965 TCE("smulwb", 12000a0, fb30f000, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
20966 TCE("smulwt", 12000e0, fb30f010, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
c19d1205 20967
03ee1b7f
NC
20968 TCE("qadd", 1000050, fa80f080, 3, (RRnpc, RRnpc, RRnpc), rd_rm_rn, t_simd2),
20969 TCE("qdadd", 1400050, fa80f090, 3, (RRnpc, RRnpc, RRnpc), rd_rm_rn, t_simd2),
20970 TCE("qsub", 1200050, fa80f0a0, 3, (RRnpc, RRnpc, RRnpc), rd_rm_rn, t_simd2),
20971 TCE("qdsub", 1600050, fa80f0b0, 3, (RRnpc, RRnpc, RRnpc), rd_rm_rn, t_simd2),
c19d1205 20972
c921be7d 20973#undef ARM_VARIANT
74db7efb
NC
20974#define ARM_VARIANT & arm_ext_v5e /* ARM Architecture 5TE. */
20975#undef THUMB_VARIANT
20976#define THUMB_VARIANT & arm_ext_v6t2
c921be7d 20977
21d799b5 20978 TUF("pld", 450f000, f810f000, 1, (ADDR), pld, t_pld),
5be8be5d
DG
20979 TC3("ldrd", 00000d0, e8500000, 3, (RRnpc_npcsp, oRRnpc_npcsp, ADDRGLDRS),
20980 ldrd, t_ldstd),
20981 TC3("strd", 00000f0, e8400000, 3, (RRnpc_npcsp, oRRnpc_npcsp,
20982 ADDRGLDRS), ldrd, t_ldstd),
c19d1205 20983
21d799b5
NC
20984 TCE("mcrr", c400000, ec400000, 5, (RCP, I15b, RRnpc, RRnpc, RCN), co_reg2c, co_reg2c),
20985 TCE("mrrc", c500000, ec500000, 5, (RCP, I15b, RRnpc, RRnpc, RCN), co_reg2c, co_reg2c),
c19d1205 20986
c921be7d
NC
20987#undef ARM_VARIANT
20988#define ARM_VARIANT & arm_ext_v5j /* ARM Architecture 5TEJ. */
20989
21d799b5 20990 TCE("bxj", 12fff20, f3c08f00, 1, (RR), bxj, t_bxj),
c19d1205 20991
c921be7d
NC
20992#undef ARM_VARIANT
20993#define ARM_VARIANT & arm_ext_v6 /* ARM V6. */
20994#undef THUMB_VARIANT
20995#define THUMB_VARIANT & arm_ext_v6
20996
21d799b5
NC
20997 TUF("cpsie", 1080000, b660, 2, (CPSF, oI31b), cpsi, t_cpsi),
20998 TUF("cpsid", 10c0000, b670, 2, (CPSF, oI31b), cpsi, t_cpsi),
20999 tCE("rev", 6bf0f30, _rev, 2, (RRnpc, RRnpc), rd_rm, t_rev),
21000 tCE("rev16", 6bf0fb0, _rev16, 2, (RRnpc, RRnpc), rd_rm, t_rev),
21001 tCE("revsh", 6ff0fb0, _revsh, 2, (RRnpc, RRnpc), rd_rm, t_rev),
21002 tCE("sxth", 6bf0070, _sxth, 3, (RRnpc, RRnpc, oROR), sxth, t_sxth),
21003 tCE("uxth", 6ff0070, _uxth, 3, (RRnpc, RRnpc, oROR), sxth, t_sxth),
21004 tCE("sxtb", 6af0070, _sxtb, 3, (RRnpc, RRnpc, oROR), sxth, t_sxth),
21005 tCE("uxtb", 6ef0070, _uxtb, 3, (RRnpc, RRnpc, oROR), sxth, t_sxth),
21006 TUF("setend", 1010000, b650, 1, (ENDI), setend, t_setend),
c19d1205 21007
c921be7d 21008#undef THUMB_VARIANT
ff8646ee 21009#define THUMB_VARIANT & arm_ext_v6t2_v8m
c921be7d 21010
5be8be5d
DG
21011 TCE("ldrex", 1900f9f, e8500f00, 2, (RRnpc_npcsp, ADDR), ldrex, t_ldrex),
21012 TCE("strex", 1800f90, e8400000, 3, (RRnpc_npcsp, RRnpc_npcsp, ADDR),
21013 strex, t_strex),
ff8646ee
TP
21014#undef THUMB_VARIANT
21015#define THUMB_VARIANT & arm_ext_v6t2
21016
21d799b5
NC
21017 TUF("mcrr2", c400000, fc400000, 5, (RCP, I15b, RRnpc, RRnpc, RCN), co_reg2c, co_reg2c),
21018 TUF("mrrc2", c500000, fc500000, 5, (RCP, I15b, RRnpc, RRnpc, RCN), co_reg2c, co_reg2c),
62b3e311 21019
21d799b5
NC
21020 TCE("ssat", 6a00010, f3000000, 4, (RRnpc, I32, RRnpc, oSHllar),ssat, t_ssat),
21021 TCE("usat", 6e00010, f3800000, 4, (RRnpc, I31, RRnpc, oSHllar),usat, t_usat),
62b3e311 21022
9e3c6df6 21023/* ARM V6 not included in V7M. */
c921be7d
NC
21024#undef THUMB_VARIANT
21025#define THUMB_VARIANT & arm_ext_v6_notm
9e3c6df6 21026 TUF("rfeia", 8900a00, e990c000, 1, (RRw), rfe, rfe),
d709e4e6 21027 TUF("rfe", 8900a00, e990c000, 1, (RRw), rfe, rfe),
9e3c6df6
PB
21028 UF(rfeib, 9900a00, 1, (RRw), rfe),
21029 UF(rfeda, 8100a00, 1, (RRw), rfe),
21030 TUF("rfedb", 9100a00, e810c000, 1, (RRw), rfe, rfe),
21031 TUF("rfefd", 8900a00, e990c000, 1, (RRw), rfe, rfe),
d709e4e6
RE
21032 UF(rfefa, 8100a00, 1, (RRw), rfe),
21033 TUF("rfeea", 9100a00, e810c000, 1, (RRw), rfe, rfe),
21034 UF(rfeed, 9900a00, 1, (RRw), rfe),
9e3c6df6 21035 TUF("srsia", 8c00500, e980c000, 2, (oRRw, I31w), srs, srs),
d709e4e6
RE
21036 TUF("srs", 8c00500, e980c000, 2, (oRRw, I31w), srs, srs),
21037 TUF("srsea", 8c00500, e980c000, 2, (oRRw, I31w), srs, srs),
9e3c6df6 21038 UF(srsib, 9c00500, 2, (oRRw, I31w), srs),
d709e4e6 21039 UF(srsfa, 9c00500, 2, (oRRw, I31w), srs),
9e3c6df6 21040 UF(srsda, 8400500, 2, (oRRw, I31w), srs),
d709e4e6 21041 UF(srsed, 8400500, 2, (oRRw, I31w), srs),
9e3c6df6 21042 TUF("srsdb", 9400500, e800c000, 2, (oRRw, I31w), srs, srs),
d709e4e6 21043 TUF("srsfd", 9400500, e800c000, 2, (oRRw, I31w), srs, srs),
941c9cad 21044 TUF("cps", 1020000, f3af8100, 1, (I31b), imm0, t_cps),
c921be7d 21045
9e3c6df6
PB
21046/* ARM V6 not included in V7M (eg. integer SIMD). */
21047#undef THUMB_VARIANT
21048#define THUMB_VARIANT & arm_ext_v6_dsp
21d799b5
NC
21049 TCE("pkhbt", 6800010, eac00000, 4, (RRnpc, RRnpc, RRnpc, oSHll), pkhbt, t_pkhbt),
21050 TCE("pkhtb", 6800050, eac00020, 4, (RRnpc, RRnpc, RRnpc, oSHar), pkhtb, t_pkhtb),
21051 TCE("qadd16", 6200f10, fa90f010, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21052 TCE("qadd8", 6200f90, fa80f010, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21053 TCE("qasx", 6200f30, faa0f010, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21054 /* Old name for QASX. */
74db7efb 21055 TCE("qaddsubx",6200f30, faa0f010, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21d799b5 21056 TCE("qsax", 6200f50, fae0f010, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21057 /* Old name for QSAX. */
74db7efb 21058 TCE("qsubaddx",6200f50, fae0f010, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21d799b5
NC
21059 TCE("qsub16", 6200f70, fad0f010, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21060 TCE("qsub8", 6200ff0, fac0f010, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21061 TCE("sadd16", 6100f10, fa90f000, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21062 TCE("sadd8", 6100f90, fa80f000, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21063 TCE("sasx", 6100f30, faa0f000, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21064 /* Old name for SASX. */
74db7efb 21065 TCE("saddsubx",6100f30, faa0f000, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21d799b5
NC
21066 TCE("shadd16", 6300f10, fa90f020, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21067 TCE("shadd8", 6300f90, fa80f020, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
74db7efb 21068 TCE("shasx", 6300f30, faa0f020, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21069 /* Old name for SHASX. */
21d799b5 21070 TCE("shaddsubx", 6300f30, faa0f020, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
74db7efb 21071 TCE("shsax", 6300f50, fae0f020, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21072 /* Old name for SHSAX. */
21d799b5
NC
21073 TCE("shsubaddx", 6300f50, fae0f020, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21074 TCE("shsub16", 6300f70, fad0f020, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21075 TCE("shsub8", 6300ff0, fac0f020, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21076 TCE("ssax", 6100f50, fae0f000, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21077 /* Old name for SSAX. */
74db7efb 21078 TCE("ssubaddx",6100f50, fae0f000, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21d799b5
NC
21079 TCE("ssub16", 6100f70, fad0f000, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21080 TCE("ssub8", 6100ff0, fac0f000, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21081 TCE("uadd16", 6500f10, fa90f040, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21082 TCE("uadd8", 6500f90, fa80f040, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21083 TCE("uasx", 6500f30, faa0f040, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21084 /* Old name for UASX. */
74db7efb 21085 TCE("uaddsubx",6500f30, faa0f040, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21d799b5
NC
21086 TCE("uhadd16", 6700f10, fa90f060, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21087 TCE("uhadd8", 6700f90, fa80f060, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
74db7efb 21088 TCE("uhasx", 6700f30, faa0f060, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21089 /* Old name for UHASX. */
21d799b5
NC
21090 TCE("uhaddsubx", 6700f30, faa0f060, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21091 TCE("uhsax", 6700f50, fae0f060, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21092 /* Old name for UHSAX. */
21d799b5
NC
21093 TCE("uhsubaddx", 6700f50, fae0f060, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21094 TCE("uhsub16", 6700f70, fad0f060, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21095 TCE("uhsub8", 6700ff0, fac0f060, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21096 TCE("uqadd16", 6600f10, fa90f050, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21097 TCE("uqadd8", 6600f90, fa80f050, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
74db7efb 21098 TCE("uqasx", 6600f30, faa0f050, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21099 /* Old name for UQASX. */
21d799b5
NC
21100 TCE("uqaddsubx", 6600f30, faa0f050, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21101 TCE("uqsax", 6600f50, fae0f050, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21102 /* Old name for UQSAX. */
21d799b5
NC
21103 TCE("uqsubaddx", 6600f50, fae0f050, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21104 TCE("uqsub16", 6600f70, fad0f050, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21105 TCE("uqsub8", 6600ff0, fac0f050, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21106 TCE("usub16", 6500f70, fad0f040, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21107 TCE("usax", 6500f50, fae0f040, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
4f80ef3e 21108 /* Old name for USAX. */
74db7efb 21109 TCE("usubaddx",6500f50, fae0f040, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21d799b5 21110 TCE("usub8", 6500ff0, fac0f040, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21d799b5
NC
21111 TCE("sxtah", 6b00070, fa00f080, 4, (RRnpc, RRnpc, RRnpc, oROR), sxtah, t_sxtah),
21112 TCE("sxtab16", 6800070, fa20f080, 4, (RRnpc, RRnpc, RRnpc, oROR), sxtah, t_sxtah),
21113 TCE("sxtab", 6a00070, fa40f080, 4, (RRnpc, RRnpc, RRnpc, oROR), sxtah, t_sxtah),
21114 TCE("sxtb16", 68f0070, fa2ff080, 3, (RRnpc, RRnpc, oROR), sxth, t_sxth),
21115 TCE("uxtah", 6f00070, fa10f080, 4, (RRnpc, RRnpc, RRnpc, oROR), sxtah, t_sxtah),
21116 TCE("uxtab16", 6c00070, fa30f080, 4, (RRnpc, RRnpc, RRnpc, oROR), sxtah, t_sxtah),
21117 TCE("uxtab", 6e00070, fa50f080, 4, (RRnpc, RRnpc, RRnpc, oROR), sxtah, t_sxtah),
21118 TCE("uxtb16", 6cf0070, fa3ff080, 3, (RRnpc, RRnpc, oROR), sxth, t_sxth),
21119 TCE("sel", 6800fb0, faa0f080, 3, (RRnpc, RRnpc, RRnpc), rd_rn_rm, t_simd),
21120 TCE("smlad", 7000010, fb200000, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smla, t_mla),
21121 TCE("smladx", 7000030, fb200010, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smla, t_mla),
21122 TCE("smlald", 7400010, fbc000c0, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smlal,t_mlal),
21123 TCE("smlaldx", 7400030, fbc000d0, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smlal,t_mlal),
21124 TCE("smlsd", 7000050, fb400000, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smla, t_mla),
21125 TCE("smlsdx", 7000070, fb400010, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smla, t_mla),
21126 TCE("smlsld", 7400050, fbd000c0, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smlal,t_mlal),
21127 TCE("smlsldx", 7400070, fbd000d0, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smlal,t_mlal),
21128 TCE("smmla", 7500010, fb500000, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smla, t_mla),
21129 TCE("smmlar", 7500030, fb500010, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smla, t_mla),
21130 TCE("smmls", 75000d0, fb600000, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smla, t_mla),
21131 TCE("smmlsr", 75000f0, fb600010, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smla, t_mla),
21132 TCE("smmul", 750f010, fb50f000, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
21133 TCE("smmulr", 750f030, fb50f010, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
21134 TCE("smuad", 700f010, fb20f000, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
21135 TCE("smuadx", 700f030, fb20f010, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
21136 TCE("smusd", 700f050, fb40f000, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
21137 TCE("smusdx", 700f070, fb40f010, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
21d799b5
NC
21138 TCE("ssat16", 6a00f30, f3200000, 3, (RRnpc, I16, RRnpc), ssat16, t_ssat16),
21139 TCE("umaal", 0400090, fbe00060, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smlal, t_mlal),
21140 TCE("usad8", 780f010, fb70f000, 3, (RRnpc, RRnpc, RRnpc), smul, t_simd),
21141 TCE("usada8", 7800010, fb700000, 4, (RRnpc, RRnpc, RRnpc, RRnpc),smla, t_mla),
21142 TCE("usat16", 6e00f30, f3a00000, 3, (RRnpc, I15, RRnpc), usat16, t_usat16),
c19d1205 21143
c921be7d 21144#undef ARM_VARIANT
55e8aae7 21145#define ARM_VARIANT & arm_ext_v6k_v6t2
c921be7d 21146#undef THUMB_VARIANT
55e8aae7 21147#define THUMB_VARIANT & arm_ext_v6k_v6t2
c921be7d 21148
21d799b5
NC
21149 tCE("yield", 320f001, _yield, 0, (), noargs, t_hint),
21150 tCE("wfe", 320f002, _wfe, 0, (), noargs, t_hint),
21151 tCE("wfi", 320f003, _wfi, 0, (), noargs, t_hint),
21152 tCE("sev", 320f004, _sev, 0, (), noargs, t_hint),
c19d1205 21153
c921be7d
NC
21154#undef THUMB_VARIANT
21155#define THUMB_VARIANT & arm_ext_v6_notm
5be8be5d
DG
21156 TCE("ldrexd", 1b00f9f, e8d0007f, 3, (RRnpc_npcsp, oRRnpc_npcsp, RRnpcb),
21157 ldrexd, t_ldrexd),
21158 TCE("strexd", 1a00f90, e8c00070, 4, (RRnpc_npcsp, RRnpc_npcsp, oRRnpc_npcsp,
21159 RRnpcb), strexd, t_strexd),
ebdca51a 21160
c921be7d 21161#undef THUMB_VARIANT
ff8646ee 21162#define THUMB_VARIANT & arm_ext_v6t2_v8m
5be8be5d
DG
21163 TCE("ldrexb", 1d00f9f, e8d00f4f, 2, (RRnpc_npcsp,RRnpcb),
21164 rd_rn, rd_rn),
21165 TCE("ldrexh", 1f00f9f, e8d00f5f, 2, (RRnpc_npcsp, RRnpcb),
21166 rd_rn, rd_rn),
21167 TCE("strexb", 1c00f90, e8c00f40, 3, (RRnpc_npcsp, RRnpc_npcsp, ADDR),
877807f8 21168 strex, t_strexbh),
5be8be5d 21169 TCE("strexh", 1e00f90, e8c00f50, 3, (RRnpc_npcsp, RRnpc_npcsp, ADDR),
877807f8 21170 strex, t_strexbh),
21d799b5 21171 TUF("clrex", 57ff01f, f3bf8f2f, 0, (), noargs, noargs),
c19d1205 21172
c921be7d 21173#undef ARM_VARIANT
f4c65163 21174#define ARM_VARIANT & arm_ext_sec
74db7efb 21175#undef THUMB_VARIANT
f4c65163 21176#define THUMB_VARIANT & arm_ext_sec
c921be7d 21177
21d799b5 21178 TCE("smc", 1600070, f7f08000, 1, (EXPi), smc, t_smc),
c19d1205 21179
90ec0d68
MGD
21180#undef ARM_VARIANT
21181#define ARM_VARIANT & arm_ext_virt
21182#undef THUMB_VARIANT
21183#define THUMB_VARIANT & arm_ext_virt
21184
21185 TCE("hvc", 1400070, f7e08000, 1, (EXPi), hvc, t_hvc),
21186 TCE("eret", 160006e, f3de8f00, 0, (), noargs, noargs),
21187
ddfded2f
MW
21188#undef ARM_VARIANT
21189#define ARM_VARIANT & arm_ext_pan
21190#undef THUMB_VARIANT
21191#define THUMB_VARIANT & arm_ext_pan
21192
21193 TUF("setpan", 1100000, b610, 1, (I7), setpan, t_setpan),
21194
c921be7d 21195#undef ARM_VARIANT
74db7efb 21196#define ARM_VARIANT & arm_ext_v6t2
f4c65163
MGD
21197#undef THUMB_VARIANT
21198#define THUMB_VARIANT & arm_ext_v6t2
c921be7d 21199
21d799b5
NC
21200 TCE("bfc", 7c0001f, f36f0000, 3, (RRnpc, I31, I32), bfc, t_bfc),
21201 TCE("bfi", 7c00010, f3600000, 4, (RRnpc, RRnpc_I0, I31, I32), bfi, t_bfi),
21202 TCE("sbfx", 7a00050, f3400000, 4, (RR, RR, I31, I32), bfx, t_bfx),
21203 TCE("ubfx", 7e00050, f3c00000, 4, (RR, RR, I31, I32), bfx, t_bfx),
c19d1205 21204
21d799b5 21205 TCE("mls", 0600090, fb000010, 4, (RRnpc, RRnpc, RRnpc, RRnpc), mlas, t_mla),
21d799b5 21206 TCE("rbit", 6ff0f30, fa90f0a0, 2, (RR, RR), rd_rm, t_rbit),
c19d1205 21207
5be8be5d
DG
21208 TC3("ldrht", 03000b0, f8300e00, 2, (RRnpc_npcsp, ADDR), ldsttv4, t_ldstt),
21209 TC3("ldrsht", 03000f0, f9300e00, 2, (RRnpc_npcsp, ADDR), ldsttv4, t_ldstt),
21210 TC3("ldrsbt", 03000d0, f9100e00, 2, (RRnpc_npcsp, ADDR), ldsttv4, t_ldstt),
21211 TC3("strht", 02000b0, f8200e00, 2, (RRnpc_npcsp, ADDR), ldsttv4, t_ldstt),
c19d1205 21212
91d8b670
JG
21213#undef ARM_VARIANT
21214#define ARM_VARIANT & arm_ext_v3
21215#undef THUMB_VARIANT
21216#define THUMB_VARIANT & arm_ext_v6t2
21217
21218 TUE("csdb", 320f014, f3af8014, 0, (), noargs, t_csdb),
c597cc3d
SD
21219 TUF("ssbb", 57ff040, f3bf8f40, 0, (), noargs, t_csdb),
21220 TUF("pssbb", 57ff044, f3bf8f44, 0, (), noargs, t_csdb),
91d8b670
JG
21221
21222#undef ARM_VARIANT
21223#define ARM_VARIANT & arm_ext_v6t2
ff8646ee
TP
21224#undef THUMB_VARIANT
21225#define THUMB_VARIANT & arm_ext_v6t2_v8m
21226 TCE("movw", 3000000, f2400000, 2, (RRnpc, HALF), mov16, t_mov16),
21227 TCE("movt", 3400000, f2c00000, 2, (RRnpc, HALF), mov16, t_mov16),
21228
bf3eeda7 21229 /* Thumb-only instructions. */
74db7efb 21230#undef ARM_VARIANT
bf3eeda7
NS
21231#define ARM_VARIANT NULL
21232 TUE("cbnz", 0, b900, 2, (RR, EXP), 0, t_cbz),
21233 TUE("cbz", 0, b100, 2, (RR, EXP), 0, t_cbz),
c921be7d
NC
21234
21235 /* ARM does not really have an IT instruction, so always allow it.
21236 The opcode is copied from Thumb in order to allow warnings in
21237 -mimplicit-it=[never | arm] modes. */
21238#undef ARM_VARIANT
21239#define ARM_VARIANT & arm_ext_v1
ff8646ee
TP
21240#undef THUMB_VARIANT
21241#define THUMB_VARIANT & arm_ext_v6t2
c921be7d 21242
21d799b5
NC
21243 TUE("it", bf08, bf08, 1, (COND), it, t_it),
21244 TUE("itt", bf0c, bf0c, 1, (COND), it, t_it),
21245 TUE("ite", bf04, bf04, 1, (COND), it, t_it),
21246 TUE("ittt", bf0e, bf0e, 1, (COND), it, t_it),
21247 TUE("itet", bf06, bf06, 1, (COND), it, t_it),
21248 TUE("itte", bf0a, bf0a, 1, (COND), it, t_it),
21249 TUE("itee", bf02, bf02, 1, (COND), it, t_it),
21250 TUE("itttt", bf0f, bf0f, 1, (COND), it, t_it),
21251 TUE("itett", bf07, bf07, 1, (COND), it, t_it),
21252 TUE("ittet", bf0b, bf0b, 1, (COND), it, t_it),
21253 TUE("iteet", bf03, bf03, 1, (COND), it, t_it),
21254 TUE("ittte", bf0d, bf0d, 1, (COND), it, t_it),
21255 TUE("itete", bf05, bf05, 1, (COND), it, t_it),
21256 TUE("ittee", bf09, bf09, 1, (COND), it, t_it),
21257 TUE("iteee", bf01, bf01, 1, (COND), it, t_it),
1c444d06 21258 /* ARM/Thumb-2 instructions with no Thumb-1 equivalent. */
21d799b5
NC
21259 TC3("rrx", 01a00060, ea4f0030, 2, (RR, RR), rd_rm, t_rrx),
21260 TC3("rrxs", 01b00060, ea5f0030, 2, (RR, RR), rd_rm, t_rrx),
c19d1205 21261
92e90b6e 21262 /* Thumb2 only instructions. */
c921be7d
NC
21263#undef ARM_VARIANT
21264#define ARM_VARIANT NULL
92e90b6e 21265
21d799b5
NC
21266 TCE("addw", 0, f2000000, 3, (RR, RR, EXPi), 0, t_add_sub_w),
21267 TCE("subw", 0, f2a00000, 3, (RR, RR, EXPi), 0, t_add_sub_w),
21268 TCE("orn", 0, ea600000, 3, (RR, oRR, SH), 0, t_orn),
21269 TCE("orns", 0, ea700000, 3, (RR, oRR, SH), 0, t_orn),
21270 TCE("tbb", 0, e8d0f000, 1, (TB), 0, t_tb),
21271 TCE("tbh", 0, e8d0f010, 1, (TB), 0, t_tb),
92e90b6e 21272
eea54501
MGD
21273 /* Hardware division instructions. */
21274#undef ARM_VARIANT
21275#define ARM_VARIANT & arm_ext_adiv
c921be7d
NC
21276#undef THUMB_VARIANT
21277#define THUMB_VARIANT & arm_ext_div
21278
eea54501
MGD
21279 TCE("sdiv", 710f010, fb90f0f0, 3, (RR, oRR, RR), div, t_div),
21280 TCE("udiv", 730f010, fbb0f0f0, 3, (RR, oRR, RR), div, t_div),
62b3e311 21281
7e806470 21282 /* ARM V6M/V7 instructions. */
c921be7d
NC
21283#undef ARM_VARIANT
21284#define ARM_VARIANT & arm_ext_barrier
21285#undef THUMB_VARIANT
21286#define THUMB_VARIANT & arm_ext_barrier
21287
ccb84d65
JB
21288 TUF("dmb", 57ff050, f3bf8f50, 1, (oBARRIER_I15), barrier, barrier),
21289 TUF("dsb", 57ff040, f3bf8f40, 1, (oBARRIER_I15), barrier, barrier),
21290 TUF("isb", 57ff060, f3bf8f60, 1, (oBARRIER_I15), barrier, barrier),
7e806470 21291
62b3e311 21292 /* ARM V7 instructions. */
c921be7d
NC
21293#undef ARM_VARIANT
21294#define ARM_VARIANT & arm_ext_v7
21295#undef THUMB_VARIANT
21296#define THUMB_VARIANT & arm_ext_v7
21297
21d799b5
NC
21298 TUF("pli", 450f000, f910f000, 1, (ADDR), pli, t_pld),
21299 TCE("dbg", 320f0f0, f3af80f0, 1, (I15), dbg, t_dbg),
62b3e311 21300
74db7efb 21301#undef ARM_VARIANT
60e5ef9f 21302#define ARM_VARIANT & arm_ext_mp
74db7efb 21303#undef THUMB_VARIANT
60e5ef9f
MGD
21304#define THUMB_VARIANT & arm_ext_mp
21305
21306 TUF("pldw", 410f000, f830f000, 1, (ADDR), pld, t_pld),
21307
53c4b28b
MGD
21308 /* AArchv8 instructions. */
21309#undef ARM_VARIANT
21310#define ARM_VARIANT & arm_ext_v8
4ed7ed8d
TP
21311
21312/* Instructions shared between armv8-a and armv8-m. */
53c4b28b 21313#undef THUMB_VARIANT
4ed7ed8d 21314#define THUMB_VARIANT & arm_ext_atomics
53c4b28b 21315
4ed7ed8d
TP
21316 TCE("lda", 1900c9f, e8d00faf, 2, (RRnpc, RRnpcb), rd_rn, rd_rn),
21317 TCE("ldab", 1d00c9f, e8d00f8f, 2, (RRnpc, RRnpcb), rd_rn, rd_rn),
21318 TCE("ldah", 1f00c9f, e8d00f9f, 2, (RRnpc, RRnpcb), rd_rn, rd_rn),
21319 TCE("stl", 180fc90, e8c00faf, 2, (RRnpc, RRnpcb), rm_rn, rd_rn),
21320 TCE("stlb", 1c0fc90, e8c00f8f, 2, (RRnpc, RRnpcb), rm_rn, rd_rn),
21321 TCE("stlh", 1e0fc90, e8c00f9f, 2, (RRnpc, RRnpcb), rm_rn, rd_rn),
4b8c8c02 21322 TCE("ldaex", 1900e9f, e8d00fef, 2, (RRnpc, RRnpcb), rd_rn, rd_rn),
4b8c8c02
RE
21323 TCE("ldaexb", 1d00e9f, e8d00fcf, 2, (RRnpc,RRnpcb), rd_rn, rd_rn),
21324 TCE("ldaexh", 1f00e9f, e8d00fdf, 2, (RRnpc, RRnpcb), rd_rn, rd_rn),
21325 TCE("stlex", 1800e90, e8c00fe0, 3, (RRnpc, RRnpc, RRnpcb),
21326 stlex, t_stlex),
4b8c8c02
RE
21327 TCE("stlexb", 1c00e90, e8c00fc0, 3, (RRnpc, RRnpc, RRnpcb),
21328 stlex, t_stlex),
21329 TCE("stlexh", 1e00e90, e8c00fd0, 3, (RRnpc, RRnpc, RRnpcb),
21330 stlex, t_stlex),
4ed7ed8d
TP
21331#undef THUMB_VARIANT
21332#define THUMB_VARIANT & arm_ext_v8
53c4b28b 21333
4ed7ed8d 21334 tCE("sevl", 320f005, _sevl, 0, (), noargs, t_hint),
4ed7ed8d
TP
21335 TCE("ldaexd", 1b00e9f, e8d000ff, 3, (RRnpc, oRRnpc, RRnpcb),
21336 ldrexd, t_ldrexd),
21337 TCE("stlexd", 1a00e90, e8c000f0, 4, (RRnpc, RRnpc, oRRnpc, RRnpcb),
21338 strexd, t_strexd),
f7dd2fb2
TC
21339
21340/* Defined in V8 but is in undefined encoding space for earlier
21341 architectures. However earlier architectures are required to treat
21342 this instuction as a semihosting trap as well. Hence while not explicitly
21343 defined as such, it is in fact correct to define the instruction for all
21344 architectures. */
21345#undef THUMB_VARIANT
21346#define THUMB_VARIANT & arm_ext_v1
21347#undef ARM_VARIANT
21348#define ARM_VARIANT & arm_ext_v1
21349 TUE("hlt", 1000070, ba80, 1, (oIffffb), bkpt, t_hlt),
21350
8884b720 21351 /* ARMv8 T32 only. */
74db7efb 21352#undef ARM_VARIANT
b79f7053
MGD
21353#define ARM_VARIANT NULL
21354 TUF("dcps1", 0, f78f8001, 0, (), noargs, noargs),
21355 TUF("dcps2", 0, f78f8002, 0, (), noargs, noargs),
21356 TUF("dcps3", 0, f78f8003, 0, (), noargs, noargs),
21357
33399f07
MGD
21358 /* FP for ARMv8. */
21359#undef ARM_VARIANT
a715796b 21360#define ARM_VARIANT & fpu_vfp_ext_armv8xd
33399f07 21361#undef THUMB_VARIANT
a715796b 21362#define THUMB_VARIANT & fpu_vfp_ext_armv8xd
33399f07
MGD
21363
21364 nUF(vseleq, _vseleq, 3, (RVSD, RVSD, RVSD), vsel),
21365 nUF(vselvs, _vselvs, 3, (RVSD, RVSD, RVSD), vsel),
21366 nUF(vselge, _vselge, 3, (RVSD, RVSD, RVSD), vsel),
21367 nUF(vselgt, _vselgt, 3, (RVSD, RVSD, RVSD), vsel),
73924fbc
MGD
21368 nUF(vmaxnm, _vmaxnm, 3, (RNSDQ, oRNSDQ, RNSDQ), vmaxnm),
21369 nUF(vminnm, _vminnm, 3, (RNSDQ, oRNSDQ, RNSDQ), vmaxnm),
7e8e6784
MGD
21370 nUF(vcvta, _vcvta, 2, (RNSDQ, oRNSDQ), neon_cvta),
21371 nUF(vcvtn, _vcvta, 2, (RNSDQ, oRNSDQ), neon_cvtn),
21372 nUF(vcvtp, _vcvta, 2, (RNSDQ, oRNSDQ), neon_cvtp),
21373 nUF(vcvtm, _vcvta, 2, (RNSDQ, oRNSDQ), neon_cvtm),
30bdf752
MGD
21374 nCE(vrintr, _vrintr, 2, (RNSDQ, oRNSDQ), vrintr),
21375 nCE(vrintz, _vrintr, 2, (RNSDQ, oRNSDQ), vrintz),
21376 nCE(vrintx, _vrintr, 2, (RNSDQ, oRNSDQ), vrintx),
21377 nUF(vrinta, _vrinta, 2, (RNSDQ, oRNSDQ), vrinta),
21378 nUF(vrintn, _vrinta, 2, (RNSDQ, oRNSDQ), vrintn),
21379 nUF(vrintp, _vrinta, 2, (RNSDQ, oRNSDQ), vrintp),
21380 nUF(vrintm, _vrinta, 2, (RNSDQ, oRNSDQ), vrintm),
33399f07 21381
91ff7894
MGD
21382 /* Crypto v1 extensions. */
21383#undef ARM_VARIANT
21384#define ARM_VARIANT & fpu_crypto_ext_armv8
21385#undef THUMB_VARIANT
21386#define THUMB_VARIANT & fpu_crypto_ext_armv8
21387
21388 nUF(aese, _aes, 2, (RNQ, RNQ), aese),
21389 nUF(aesd, _aes, 2, (RNQ, RNQ), aesd),
21390 nUF(aesmc, _aes, 2, (RNQ, RNQ), aesmc),
21391 nUF(aesimc, _aes, 2, (RNQ, RNQ), aesimc),
48adcd8e
MGD
21392 nUF(sha1c, _sha3op, 3, (RNQ, RNQ, RNQ), sha1c),
21393 nUF(sha1p, _sha3op, 3, (RNQ, RNQ, RNQ), sha1p),
21394 nUF(sha1m, _sha3op, 3, (RNQ, RNQ, RNQ), sha1m),
21395 nUF(sha1su0, _sha3op, 3, (RNQ, RNQ, RNQ), sha1su0),
21396 nUF(sha256h, _sha3op, 3, (RNQ, RNQ, RNQ), sha256h),
21397 nUF(sha256h2, _sha3op, 3, (RNQ, RNQ, RNQ), sha256h2),
21398 nUF(sha256su1, _sha3op, 3, (RNQ, RNQ, RNQ), sha256su1),
3c9017d2
MGD
21399 nUF(sha1h, _sha1h, 2, (RNQ, RNQ), sha1h),
21400 nUF(sha1su1, _sha2op, 2, (RNQ, RNQ), sha1su1),
21401 nUF(sha256su0, _sha2op, 2, (RNQ, RNQ), sha256su0),
91ff7894 21402
dd5181d5 21403#undef ARM_VARIANT
74db7efb 21404#define ARM_VARIANT & crc_ext_armv8
dd5181d5
KT
21405#undef THUMB_VARIANT
21406#define THUMB_VARIANT & crc_ext_armv8
21407 TUEc("crc32b", 1000040, fac0f080, 3, (RR, oRR, RR), crc32b),
21408 TUEc("crc32h", 1200040, fac0f090, 3, (RR, oRR, RR), crc32h),
21409 TUEc("crc32w", 1400040, fac0f0a0, 3, (RR, oRR, RR), crc32w),
21410 TUEc("crc32cb",1000240, fad0f080, 3, (RR, oRR, RR), crc32cb),
21411 TUEc("crc32ch",1200240, fad0f090, 3, (RR, oRR, RR), crc32ch),
21412 TUEc("crc32cw",1400240, fad0f0a0, 3, (RR, oRR, RR), crc32cw),
21413
105bde57
MW
21414 /* ARMv8.2 RAS extension. */
21415#undef ARM_VARIANT
4d1464f2 21416#define ARM_VARIANT & arm_ext_ras
105bde57 21417#undef THUMB_VARIANT
4d1464f2 21418#define THUMB_VARIANT & arm_ext_ras
105bde57
MW
21419 TUE ("esb", 320f010, f3af8010, 0, (), noargs, noargs),
21420
49e8a725
SN
21421#undef ARM_VARIANT
21422#define ARM_VARIANT & arm_ext_v8_3
21423#undef THUMB_VARIANT
21424#define THUMB_VARIANT & arm_ext_v8_3
21425 NCE (vjcvt, eb90bc0, 2, (RVS, RVD), vjcvt),
c28eeff2
SN
21426 NUF (vcmla, 0, 4, (RNDQ, RNDQ, RNDQ_RNSC, EXPi), vcmla),
21427 NUF (vcadd, 0, 4, (RNDQ, RNDQ, RNDQ, EXPi), vcadd),
49e8a725 21428
c604a79a
JW
21429#undef ARM_VARIANT
21430#define ARM_VARIANT & fpu_neon_ext_dotprod
21431#undef THUMB_VARIANT
21432#define THUMB_VARIANT & fpu_neon_ext_dotprod
21433 NUF (vsdot, d00, 3, (RNDQ, RNDQ, RNDQ_RNSC), neon_dotproduct_s),
21434 NUF (vudot, d00, 3, (RNDQ, RNDQ, RNDQ_RNSC), neon_dotproduct_u),
21435
c921be7d
NC
21436#undef ARM_VARIANT
21437#define ARM_VARIANT & fpu_fpa_ext_v1 /* Core FPA instruction set (V1). */
53c4b28b
MGD
21438#undef THUMB_VARIANT
21439#define THUMB_VARIANT NULL
c921be7d 21440
21d799b5
NC
21441 cCE("wfs", e200110, 1, (RR), rd),
21442 cCE("rfs", e300110, 1, (RR), rd),
21443 cCE("wfc", e400110, 1, (RR), rd),
21444 cCE("rfc", e500110, 1, (RR), rd),
21445
21446 cCL("ldfs", c100100, 2, (RF, ADDRGLDC), rd_cpaddr),
21447 cCL("ldfd", c108100, 2, (RF, ADDRGLDC), rd_cpaddr),
21448 cCL("ldfe", c500100, 2, (RF, ADDRGLDC), rd_cpaddr),
21449 cCL("ldfp", c508100, 2, (RF, ADDRGLDC), rd_cpaddr),
21450
21451 cCL("stfs", c000100, 2, (RF, ADDRGLDC), rd_cpaddr),
21452 cCL("stfd", c008100, 2, (RF, ADDRGLDC), rd_cpaddr),
21453 cCL("stfe", c400100, 2, (RF, ADDRGLDC), rd_cpaddr),
21454 cCL("stfp", c408100, 2, (RF, ADDRGLDC), rd_cpaddr),
21455
21456 cCL("mvfs", e008100, 2, (RF, RF_IF), rd_rm),
21457 cCL("mvfsp", e008120, 2, (RF, RF_IF), rd_rm),
21458 cCL("mvfsm", e008140, 2, (RF, RF_IF), rd_rm),
21459 cCL("mvfsz", e008160, 2, (RF, RF_IF), rd_rm),
21460 cCL("mvfd", e008180, 2, (RF, RF_IF), rd_rm),
21461 cCL("mvfdp", e0081a0, 2, (RF, RF_IF), rd_rm),
21462 cCL("mvfdm", e0081c0, 2, (RF, RF_IF), rd_rm),
21463 cCL("mvfdz", e0081e0, 2, (RF, RF_IF), rd_rm),
21464 cCL("mvfe", e088100, 2, (RF, RF_IF), rd_rm),
21465 cCL("mvfep", e088120, 2, (RF, RF_IF), rd_rm),
21466 cCL("mvfem", e088140, 2, (RF, RF_IF), rd_rm),
21467 cCL("mvfez", e088160, 2, (RF, RF_IF), rd_rm),
21468
21469 cCL("mnfs", e108100, 2, (RF, RF_IF), rd_rm),
21470 cCL("mnfsp", e108120, 2, (RF, RF_IF), rd_rm),
21471 cCL("mnfsm", e108140, 2, (RF, RF_IF), rd_rm),
21472 cCL("mnfsz", e108160, 2, (RF, RF_IF), rd_rm),
21473 cCL("mnfd", e108180, 2, (RF, RF_IF), rd_rm),
21474 cCL("mnfdp", e1081a0, 2, (RF, RF_IF), rd_rm),
21475 cCL("mnfdm", e1081c0, 2, (RF, RF_IF), rd_rm),
21476 cCL("mnfdz", e1081e0, 2, (RF, RF_IF), rd_rm),
21477 cCL("mnfe", e188100, 2, (RF, RF_IF), rd_rm),
21478 cCL("mnfep", e188120, 2, (RF, RF_IF), rd_rm),
21479 cCL("mnfem", e188140, 2, (RF, RF_IF), rd_rm),
21480 cCL("mnfez", e188160, 2, (RF, RF_IF), rd_rm),
21481
21482 cCL("abss", e208100, 2, (RF, RF_IF), rd_rm),
21483 cCL("abssp", e208120, 2, (RF, RF_IF), rd_rm),
21484 cCL("abssm", e208140, 2, (RF, RF_IF), rd_rm),
21485 cCL("abssz", e208160, 2, (RF, RF_IF), rd_rm),
21486 cCL("absd", e208180, 2, (RF, RF_IF), rd_rm),
21487 cCL("absdp", e2081a0, 2, (RF, RF_IF), rd_rm),
21488 cCL("absdm", e2081c0, 2, (RF, RF_IF), rd_rm),
21489 cCL("absdz", e2081e0, 2, (RF, RF_IF), rd_rm),
21490 cCL("abse", e288100, 2, (RF, RF_IF), rd_rm),
21491 cCL("absep", e288120, 2, (RF, RF_IF), rd_rm),
21492 cCL("absem", e288140, 2, (RF, RF_IF), rd_rm),
21493 cCL("absez", e288160, 2, (RF, RF_IF), rd_rm),
21494
21495 cCL("rnds", e308100, 2, (RF, RF_IF), rd_rm),
21496 cCL("rndsp", e308120, 2, (RF, RF_IF), rd_rm),
21497 cCL("rndsm", e308140, 2, (RF, RF_IF), rd_rm),
21498 cCL("rndsz", e308160, 2, (RF, RF_IF), rd_rm),
21499 cCL("rndd", e308180, 2, (RF, RF_IF), rd_rm),
21500 cCL("rnddp", e3081a0, 2, (RF, RF_IF), rd_rm),
21501 cCL("rnddm", e3081c0, 2, (RF, RF_IF), rd_rm),
21502 cCL("rnddz", e3081e0, 2, (RF, RF_IF), rd_rm),
21503 cCL("rnde", e388100, 2, (RF, RF_IF), rd_rm),
21504 cCL("rndep", e388120, 2, (RF, RF_IF), rd_rm),
21505 cCL("rndem", e388140, 2, (RF, RF_IF), rd_rm),
21506 cCL("rndez", e388160, 2, (RF, RF_IF), rd_rm),
21507
21508 cCL("sqts", e408100, 2, (RF, RF_IF), rd_rm),
21509 cCL("sqtsp", e408120, 2, (RF, RF_IF), rd_rm),
21510 cCL("sqtsm", e408140, 2, (RF, RF_IF), rd_rm),
21511 cCL("sqtsz", e408160, 2, (RF, RF_IF), rd_rm),
21512 cCL("sqtd", e408180, 2, (RF, RF_IF), rd_rm),
21513 cCL("sqtdp", e4081a0, 2, (RF, RF_IF), rd_rm),
21514 cCL("sqtdm", e4081c0, 2, (RF, RF_IF), rd_rm),
21515 cCL("sqtdz", e4081e0, 2, (RF, RF_IF), rd_rm),
21516 cCL("sqte", e488100, 2, (RF, RF_IF), rd_rm),
21517 cCL("sqtep", e488120, 2, (RF, RF_IF), rd_rm),
21518 cCL("sqtem", e488140, 2, (RF, RF_IF), rd_rm),
21519 cCL("sqtez", e488160, 2, (RF, RF_IF), rd_rm),
21520
21521 cCL("logs", e508100, 2, (RF, RF_IF), rd_rm),
21522 cCL("logsp", e508120, 2, (RF, RF_IF), rd_rm),
21523 cCL("logsm", e508140, 2, (RF, RF_IF), rd_rm),
21524 cCL("logsz", e508160, 2, (RF, RF_IF), rd_rm),
21525 cCL("logd", e508180, 2, (RF, RF_IF), rd_rm),
21526 cCL("logdp", e5081a0, 2, (RF, RF_IF), rd_rm),
21527 cCL("logdm", e5081c0, 2, (RF, RF_IF), rd_rm),
21528 cCL("logdz", e5081e0, 2, (RF, RF_IF), rd_rm),
21529 cCL("loge", e588100, 2, (RF, RF_IF), rd_rm),
21530 cCL("logep", e588120, 2, (RF, RF_IF), rd_rm),
21531 cCL("logem", e588140, 2, (RF, RF_IF), rd_rm),
21532 cCL("logez", e588160, 2, (RF, RF_IF), rd_rm),
21533
21534 cCL("lgns", e608100, 2, (RF, RF_IF), rd_rm),
21535 cCL("lgnsp", e608120, 2, (RF, RF_IF), rd_rm),
21536 cCL("lgnsm", e608140, 2, (RF, RF_IF), rd_rm),
21537 cCL("lgnsz", e608160, 2, (RF, RF_IF), rd_rm),
21538 cCL("lgnd", e608180, 2, (RF, RF_IF), rd_rm),
21539 cCL("lgndp", e6081a0, 2, (RF, RF_IF), rd_rm),
21540 cCL("lgndm", e6081c0, 2, (RF, RF_IF), rd_rm),
21541 cCL("lgndz", e6081e0, 2, (RF, RF_IF), rd_rm),
21542 cCL("lgne", e688100, 2, (RF, RF_IF), rd_rm),
21543 cCL("lgnep", e688120, 2, (RF, RF_IF), rd_rm),
21544 cCL("lgnem", e688140, 2, (RF, RF_IF), rd_rm),
21545 cCL("lgnez", e688160, 2, (RF, RF_IF), rd_rm),
21546
21547 cCL("exps", e708100, 2, (RF, RF_IF), rd_rm),
21548 cCL("expsp", e708120, 2, (RF, RF_IF), rd_rm),
21549 cCL("expsm", e708140, 2, (RF, RF_IF), rd_rm),
21550 cCL("expsz", e708160, 2, (RF, RF_IF), rd_rm),
21551 cCL("expd", e708180, 2, (RF, RF_IF), rd_rm),
21552 cCL("expdp", e7081a0, 2, (RF, RF_IF), rd_rm),
21553 cCL("expdm", e7081c0, 2, (RF, RF_IF), rd_rm),
21554 cCL("expdz", e7081e0, 2, (RF, RF_IF), rd_rm),
21555 cCL("expe", e788100, 2, (RF, RF_IF), rd_rm),
21556 cCL("expep", e788120, 2, (RF, RF_IF), rd_rm),
21557 cCL("expem", e788140, 2, (RF, RF_IF), rd_rm),
21558 cCL("expdz", e788160, 2, (RF, RF_IF), rd_rm),
21559
21560 cCL("sins", e808100, 2, (RF, RF_IF), rd_rm),
21561 cCL("sinsp", e808120, 2, (RF, RF_IF), rd_rm),
21562 cCL("sinsm", e808140, 2, (RF, RF_IF), rd_rm),
21563 cCL("sinsz", e808160, 2, (RF, RF_IF), rd_rm),
21564 cCL("sind", e808180, 2, (RF, RF_IF), rd_rm),
21565 cCL("sindp", e8081a0, 2, (RF, RF_IF), rd_rm),
21566 cCL("sindm", e8081c0, 2, (RF, RF_IF), rd_rm),
21567 cCL("sindz", e8081e0, 2, (RF, RF_IF), rd_rm),
21568 cCL("sine", e888100, 2, (RF, RF_IF), rd_rm),
21569 cCL("sinep", e888120, 2, (RF, RF_IF), rd_rm),
21570 cCL("sinem", e888140, 2, (RF, RF_IF), rd_rm),
21571 cCL("sinez", e888160, 2, (RF, RF_IF), rd_rm),
21572
21573 cCL("coss", e908100, 2, (RF, RF_IF), rd_rm),
21574 cCL("cossp", e908120, 2, (RF, RF_IF), rd_rm),
21575 cCL("cossm", e908140, 2, (RF, RF_IF), rd_rm),
21576 cCL("cossz", e908160, 2, (RF, RF_IF), rd_rm),
21577 cCL("cosd", e908180, 2, (RF, RF_IF), rd_rm),
21578 cCL("cosdp", e9081a0, 2, (RF, RF_IF), rd_rm),
21579 cCL("cosdm", e9081c0, 2, (RF, RF_IF), rd_rm),
21580 cCL("cosdz", e9081e0, 2, (RF, RF_IF), rd_rm),
21581 cCL("cose", e988100, 2, (RF, RF_IF), rd_rm),
21582 cCL("cosep", e988120, 2, (RF, RF_IF), rd_rm),
21583 cCL("cosem", e988140, 2, (RF, RF_IF), rd_rm),
21584 cCL("cosez", e988160, 2, (RF, RF_IF), rd_rm),
21585
21586 cCL("tans", ea08100, 2, (RF, RF_IF), rd_rm),
21587 cCL("tansp", ea08120, 2, (RF, RF_IF), rd_rm),
21588 cCL("tansm", ea08140, 2, (RF, RF_IF), rd_rm),
21589 cCL("tansz", ea08160, 2, (RF, RF_IF), rd_rm),
21590 cCL("tand", ea08180, 2, (RF, RF_IF), rd_rm),
21591 cCL("tandp", ea081a0, 2, (RF, RF_IF), rd_rm),
21592 cCL("tandm", ea081c0, 2, (RF, RF_IF), rd_rm),
21593 cCL("tandz", ea081e0, 2, (RF, RF_IF), rd_rm),
21594 cCL("tane", ea88100, 2, (RF, RF_IF), rd_rm),
21595 cCL("tanep", ea88120, 2, (RF, RF_IF), rd_rm),
21596 cCL("tanem", ea88140, 2, (RF, RF_IF), rd_rm),
21597 cCL("tanez", ea88160, 2, (RF, RF_IF), rd_rm),
21598
21599 cCL("asns", eb08100, 2, (RF, RF_IF), rd_rm),
21600 cCL("asnsp", eb08120, 2, (RF, RF_IF), rd_rm),
21601 cCL("asnsm", eb08140, 2, (RF, RF_IF), rd_rm),
21602 cCL("asnsz", eb08160, 2, (RF, RF_IF), rd_rm),
21603 cCL("asnd", eb08180, 2, (RF, RF_IF), rd_rm),
21604 cCL("asndp", eb081a0, 2, (RF, RF_IF), rd_rm),
21605 cCL("asndm", eb081c0, 2, (RF, RF_IF), rd_rm),
21606 cCL("asndz", eb081e0, 2, (RF, RF_IF), rd_rm),
21607 cCL("asne", eb88100, 2, (RF, RF_IF), rd_rm),
21608 cCL("asnep", eb88120, 2, (RF, RF_IF), rd_rm),
21609 cCL("asnem", eb88140, 2, (RF, RF_IF), rd_rm),
21610 cCL("asnez", eb88160, 2, (RF, RF_IF), rd_rm),
21611
21612 cCL("acss", ec08100, 2, (RF, RF_IF), rd_rm),
21613 cCL("acssp", ec08120, 2, (RF, RF_IF), rd_rm),
21614 cCL("acssm", ec08140, 2, (RF, RF_IF), rd_rm),
21615 cCL("acssz", ec08160, 2, (RF, RF_IF), rd_rm),
21616 cCL("acsd", ec08180, 2, (RF, RF_IF), rd_rm),
21617 cCL("acsdp", ec081a0, 2, (RF, RF_IF), rd_rm),
21618 cCL("acsdm", ec081c0, 2, (RF, RF_IF), rd_rm),
21619 cCL("acsdz", ec081e0, 2, (RF, RF_IF), rd_rm),
21620 cCL("acse", ec88100, 2, (RF, RF_IF), rd_rm),
21621 cCL("acsep", ec88120, 2, (RF, RF_IF), rd_rm),
21622 cCL("acsem", ec88140, 2, (RF, RF_IF), rd_rm),
21623 cCL("acsez", ec88160, 2, (RF, RF_IF), rd_rm),
21624
21625 cCL("atns", ed08100, 2, (RF, RF_IF), rd_rm),
21626 cCL("atnsp", ed08120, 2, (RF, RF_IF), rd_rm),
21627 cCL("atnsm", ed08140, 2, (RF, RF_IF), rd_rm),
21628 cCL("atnsz", ed08160, 2, (RF, RF_IF), rd_rm),
21629 cCL("atnd", ed08180, 2, (RF, RF_IF), rd_rm),
21630 cCL("atndp", ed081a0, 2, (RF, RF_IF), rd_rm),
21631 cCL("atndm", ed081c0, 2, (RF, RF_IF), rd_rm),
21632 cCL("atndz", ed081e0, 2, (RF, RF_IF), rd_rm),
21633 cCL("atne", ed88100, 2, (RF, RF_IF), rd_rm),
21634 cCL("atnep", ed88120, 2, (RF, RF_IF), rd_rm),
21635 cCL("atnem", ed88140, 2, (RF, RF_IF), rd_rm),
21636 cCL("atnez", ed88160, 2, (RF, RF_IF), rd_rm),
21637
21638 cCL("urds", ee08100, 2, (RF, RF_IF), rd_rm),
21639 cCL("urdsp", ee08120, 2, (RF, RF_IF), rd_rm),
21640 cCL("urdsm", ee08140, 2, (RF, RF_IF), rd_rm),
21641 cCL("urdsz", ee08160, 2, (RF, RF_IF), rd_rm),
21642 cCL("urdd", ee08180, 2, (RF, RF_IF), rd_rm),
21643 cCL("urddp", ee081a0, 2, (RF, RF_IF), rd_rm),
21644 cCL("urddm", ee081c0, 2, (RF, RF_IF), rd_rm),
21645 cCL("urddz", ee081e0, 2, (RF, RF_IF), rd_rm),
21646 cCL("urde", ee88100, 2, (RF, RF_IF), rd_rm),
21647 cCL("urdep", ee88120, 2, (RF, RF_IF), rd_rm),
21648 cCL("urdem", ee88140, 2, (RF, RF_IF), rd_rm),
21649 cCL("urdez", ee88160, 2, (RF, RF_IF), rd_rm),
21650
21651 cCL("nrms", ef08100, 2, (RF, RF_IF), rd_rm),
21652 cCL("nrmsp", ef08120, 2, (RF, RF_IF), rd_rm),
21653 cCL("nrmsm", ef08140, 2, (RF, RF_IF), rd_rm),
21654 cCL("nrmsz", ef08160, 2, (RF, RF_IF), rd_rm),
21655 cCL("nrmd", ef08180, 2, (RF, RF_IF), rd_rm),
21656 cCL("nrmdp", ef081a0, 2, (RF, RF_IF), rd_rm),
21657 cCL("nrmdm", ef081c0, 2, (RF, RF_IF), rd_rm),
21658 cCL("nrmdz", ef081e0, 2, (RF, RF_IF), rd_rm),
21659 cCL("nrme", ef88100, 2, (RF, RF_IF), rd_rm),
21660 cCL("nrmep", ef88120, 2, (RF, RF_IF), rd_rm),
21661 cCL("nrmem", ef88140, 2, (RF, RF_IF), rd_rm),
21662 cCL("nrmez", ef88160, 2, (RF, RF_IF), rd_rm),
21663
21664 cCL("adfs", e000100, 3, (RF, RF, RF_IF), rd_rn_rm),
21665 cCL("adfsp", e000120, 3, (RF, RF, RF_IF), rd_rn_rm),
21666 cCL("adfsm", e000140, 3, (RF, RF, RF_IF), rd_rn_rm),
21667 cCL("adfsz", e000160, 3, (RF, RF, RF_IF), rd_rn_rm),
21668 cCL("adfd", e000180, 3, (RF, RF, RF_IF), rd_rn_rm),
21669 cCL("adfdp", e0001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21670 cCL("adfdm", e0001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21671 cCL("adfdz", e0001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21672 cCL("adfe", e080100, 3, (RF, RF, RF_IF), rd_rn_rm),
21673 cCL("adfep", e080120, 3, (RF, RF, RF_IF), rd_rn_rm),
21674 cCL("adfem", e080140, 3, (RF, RF, RF_IF), rd_rn_rm),
21675 cCL("adfez", e080160, 3, (RF, RF, RF_IF), rd_rn_rm),
21676
21677 cCL("sufs", e200100, 3, (RF, RF, RF_IF), rd_rn_rm),
21678 cCL("sufsp", e200120, 3, (RF, RF, RF_IF), rd_rn_rm),
21679 cCL("sufsm", e200140, 3, (RF, RF, RF_IF), rd_rn_rm),
21680 cCL("sufsz", e200160, 3, (RF, RF, RF_IF), rd_rn_rm),
21681 cCL("sufd", e200180, 3, (RF, RF, RF_IF), rd_rn_rm),
21682 cCL("sufdp", e2001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21683 cCL("sufdm", e2001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21684 cCL("sufdz", e2001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21685 cCL("sufe", e280100, 3, (RF, RF, RF_IF), rd_rn_rm),
21686 cCL("sufep", e280120, 3, (RF, RF, RF_IF), rd_rn_rm),
21687 cCL("sufem", e280140, 3, (RF, RF, RF_IF), rd_rn_rm),
21688 cCL("sufez", e280160, 3, (RF, RF, RF_IF), rd_rn_rm),
21689
21690 cCL("rsfs", e300100, 3, (RF, RF, RF_IF), rd_rn_rm),
21691 cCL("rsfsp", e300120, 3, (RF, RF, RF_IF), rd_rn_rm),
21692 cCL("rsfsm", e300140, 3, (RF, RF, RF_IF), rd_rn_rm),
21693 cCL("rsfsz", e300160, 3, (RF, RF, RF_IF), rd_rn_rm),
21694 cCL("rsfd", e300180, 3, (RF, RF, RF_IF), rd_rn_rm),
21695 cCL("rsfdp", e3001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21696 cCL("rsfdm", e3001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21697 cCL("rsfdz", e3001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21698 cCL("rsfe", e380100, 3, (RF, RF, RF_IF), rd_rn_rm),
21699 cCL("rsfep", e380120, 3, (RF, RF, RF_IF), rd_rn_rm),
21700 cCL("rsfem", e380140, 3, (RF, RF, RF_IF), rd_rn_rm),
21701 cCL("rsfez", e380160, 3, (RF, RF, RF_IF), rd_rn_rm),
21702
21703 cCL("mufs", e100100, 3, (RF, RF, RF_IF), rd_rn_rm),
21704 cCL("mufsp", e100120, 3, (RF, RF, RF_IF), rd_rn_rm),
21705 cCL("mufsm", e100140, 3, (RF, RF, RF_IF), rd_rn_rm),
21706 cCL("mufsz", e100160, 3, (RF, RF, RF_IF), rd_rn_rm),
21707 cCL("mufd", e100180, 3, (RF, RF, RF_IF), rd_rn_rm),
21708 cCL("mufdp", e1001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21709 cCL("mufdm", e1001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21710 cCL("mufdz", e1001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21711 cCL("mufe", e180100, 3, (RF, RF, RF_IF), rd_rn_rm),
21712 cCL("mufep", e180120, 3, (RF, RF, RF_IF), rd_rn_rm),
21713 cCL("mufem", e180140, 3, (RF, RF, RF_IF), rd_rn_rm),
21714 cCL("mufez", e180160, 3, (RF, RF, RF_IF), rd_rn_rm),
21715
21716 cCL("dvfs", e400100, 3, (RF, RF, RF_IF), rd_rn_rm),
21717 cCL("dvfsp", e400120, 3, (RF, RF, RF_IF), rd_rn_rm),
21718 cCL("dvfsm", e400140, 3, (RF, RF, RF_IF), rd_rn_rm),
21719 cCL("dvfsz", e400160, 3, (RF, RF, RF_IF), rd_rn_rm),
21720 cCL("dvfd", e400180, 3, (RF, RF, RF_IF), rd_rn_rm),
21721 cCL("dvfdp", e4001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21722 cCL("dvfdm", e4001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21723 cCL("dvfdz", e4001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21724 cCL("dvfe", e480100, 3, (RF, RF, RF_IF), rd_rn_rm),
21725 cCL("dvfep", e480120, 3, (RF, RF, RF_IF), rd_rn_rm),
21726 cCL("dvfem", e480140, 3, (RF, RF, RF_IF), rd_rn_rm),
21727 cCL("dvfez", e480160, 3, (RF, RF, RF_IF), rd_rn_rm),
21728
21729 cCL("rdfs", e500100, 3, (RF, RF, RF_IF), rd_rn_rm),
21730 cCL("rdfsp", e500120, 3, (RF, RF, RF_IF), rd_rn_rm),
21731 cCL("rdfsm", e500140, 3, (RF, RF, RF_IF), rd_rn_rm),
21732 cCL("rdfsz", e500160, 3, (RF, RF, RF_IF), rd_rn_rm),
21733 cCL("rdfd", e500180, 3, (RF, RF, RF_IF), rd_rn_rm),
21734 cCL("rdfdp", e5001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21735 cCL("rdfdm", e5001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21736 cCL("rdfdz", e5001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21737 cCL("rdfe", e580100, 3, (RF, RF, RF_IF), rd_rn_rm),
21738 cCL("rdfep", e580120, 3, (RF, RF, RF_IF), rd_rn_rm),
21739 cCL("rdfem", e580140, 3, (RF, RF, RF_IF), rd_rn_rm),
21740 cCL("rdfez", e580160, 3, (RF, RF, RF_IF), rd_rn_rm),
21741
21742 cCL("pows", e600100, 3, (RF, RF, RF_IF), rd_rn_rm),
21743 cCL("powsp", e600120, 3, (RF, RF, RF_IF), rd_rn_rm),
21744 cCL("powsm", e600140, 3, (RF, RF, RF_IF), rd_rn_rm),
21745 cCL("powsz", e600160, 3, (RF, RF, RF_IF), rd_rn_rm),
21746 cCL("powd", e600180, 3, (RF, RF, RF_IF), rd_rn_rm),
21747 cCL("powdp", e6001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21748 cCL("powdm", e6001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21749 cCL("powdz", e6001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21750 cCL("powe", e680100, 3, (RF, RF, RF_IF), rd_rn_rm),
21751 cCL("powep", e680120, 3, (RF, RF, RF_IF), rd_rn_rm),
21752 cCL("powem", e680140, 3, (RF, RF, RF_IF), rd_rn_rm),
21753 cCL("powez", e680160, 3, (RF, RF, RF_IF), rd_rn_rm),
21754
21755 cCL("rpws", e700100, 3, (RF, RF, RF_IF), rd_rn_rm),
21756 cCL("rpwsp", e700120, 3, (RF, RF, RF_IF), rd_rn_rm),
21757 cCL("rpwsm", e700140, 3, (RF, RF, RF_IF), rd_rn_rm),
21758 cCL("rpwsz", e700160, 3, (RF, RF, RF_IF), rd_rn_rm),
21759 cCL("rpwd", e700180, 3, (RF, RF, RF_IF), rd_rn_rm),
21760 cCL("rpwdp", e7001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21761 cCL("rpwdm", e7001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21762 cCL("rpwdz", e7001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21763 cCL("rpwe", e780100, 3, (RF, RF, RF_IF), rd_rn_rm),
21764 cCL("rpwep", e780120, 3, (RF, RF, RF_IF), rd_rn_rm),
21765 cCL("rpwem", e780140, 3, (RF, RF, RF_IF), rd_rn_rm),
21766 cCL("rpwez", e780160, 3, (RF, RF, RF_IF), rd_rn_rm),
21767
21768 cCL("rmfs", e800100, 3, (RF, RF, RF_IF), rd_rn_rm),
21769 cCL("rmfsp", e800120, 3, (RF, RF, RF_IF), rd_rn_rm),
21770 cCL("rmfsm", e800140, 3, (RF, RF, RF_IF), rd_rn_rm),
21771 cCL("rmfsz", e800160, 3, (RF, RF, RF_IF), rd_rn_rm),
21772 cCL("rmfd", e800180, 3, (RF, RF, RF_IF), rd_rn_rm),
21773 cCL("rmfdp", e8001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21774 cCL("rmfdm", e8001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21775 cCL("rmfdz", e8001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21776 cCL("rmfe", e880100, 3, (RF, RF, RF_IF), rd_rn_rm),
21777 cCL("rmfep", e880120, 3, (RF, RF, RF_IF), rd_rn_rm),
21778 cCL("rmfem", e880140, 3, (RF, RF, RF_IF), rd_rn_rm),
21779 cCL("rmfez", e880160, 3, (RF, RF, RF_IF), rd_rn_rm),
21780
21781 cCL("fmls", e900100, 3, (RF, RF, RF_IF), rd_rn_rm),
21782 cCL("fmlsp", e900120, 3, (RF, RF, RF_IF), rd_rn_rm),
21783 cCL("fmlsm", e900140, 3, (RF, RF, RF_IF), rd_rn_rm),
21784 cCL("fmlsz", e900160, 3, (RF, RF, RF_IF), rd_rn_rm),
21785 cCL("fmld", e900180, 3, (RF, RF, RF_IF), rd_rn_rm),
21786 cCL("fmldp", e9001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21787 cCL("fmldm", e9001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21788 cCL("fmldz", e9001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21789 cCL("fmle", e980100, 3, (RF, RF, RF_IF), rd_rn_rm),
21790 cCL("fmlep", e980120, 3, (RF, RF, RF_IF), rd_rn_rm),
21791 cCL("fmlem", e980140, 3, (RF, RF, RF_IF), rd_rn_rm),
21792 cCL("fmlez", e980160, 3, (RF, RF, RF_IF), rd_rn_rm),
21793
21794 cCL("fdvs", ea00100, 3, (RF, RF, RF_IF), rd_rn_rm),
21795 cCL("fdvsp", ea00120, 3, (RF, RF, RF_IF), rd_rn_rm),
21796 cCL("fdvsm", ea00140, 3, (RF, RF, RF_IF), rd_rn_rm),
21797 cCL("fdvsz", ea00160, 3, (RF, RF, RF_IF), rd_rn_rm),
21798 cCL("fdvd", ea00180, 3, (RF, RF, RF_IF), rd_rn_rm),
21799 cCL("fdvdp", ea001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21800 cCL("fdvdm", ea001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21801 cCL("fdvdz", ea001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21802 cCL("fdve", ea80100, 3, (RF, RF, RF_IF), rd_rn_rm),
21803 cCL("fdvep", ea80120, 3, (RF, RF, RF_IF), rd_rn_rm),
21804 cCL("fdvem", ea80140, 3, (RF, RF, RF_IF), rd_rn_rm),
21805 cCL("fdvez", ea80160, 3, (RF, RF, RF_IF), rd_rn_rm),
21806
21807 cCL("frds", eb00100, 3, (RF, RF, RF_IF), rd_rn_rm),
21808 cCL("frdsp", eb00120, 3, (RF, RF, RF_IF), rd_rn_rm),
21809 cCL("frdsm", eb00140, 3, (RF, RF, RF_IF), rd_rn_rm),
21810 cCL("frdsz", eb00160, 3, (RF, RF, RF_IF), rd_rn_rm),
21811 cCL("frdd", eb00180, 3, (RF, RF, RF_IF), rd_rn_rm),
21812 cCL("frddp", eb001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21813 cCL("frddm", eb001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21814 cCL("frddz", eb001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21815 cCL("frde", eb80100, 3, (RF, RF, RF_IF), rd_rn_rm),
21816 cCL("frdep", eb80120, 3, (RF, RF, RF_IF), rd_rn_rm),
21817 cCL("frdem", eb80140, 3, (RF, RF, RF_IF), rd_rn_rm),
21818 cCL("frdez", eb80160, 3, (RF, RF, RF_IF), rd_rn_rm),
21819
21820 cCL("pols", ec00100, 3, (RF, RF, RF_IF), rd_rn_rm),
21821 cCL("polsp", ec00120, 3, (RF, RF, RF_IF), rd_rn_rm),
21822 cCL("polsm", ec00140, 3, (RF, RF, RF_IF), rd_rn_rm),
21823 cCL("polsz", ec00160, 3, (RF, RF, RF_IF), rd_rn_rm),
21824 cCL("pold", ec00180, 3, (RF, RF, RF_IF), rd_rn_rm),
21825 cCL("poldp", ec001a0, 3, (RF, RF, RF_IF), rd_rn_rm),
21826 cCL("poldm", ec001c0, 3, (RF, RF, RF_IF), rd_rn_rm),
21827 cCL("poldz", ec001e0, 3, (RF, RF, RF_IF), rd_rn_rm),
21828 cCL("pole", ec80100, 3, (RF, RF, RF_IF), rd_rn_rm),
21829 cCL("polep", ec80120, 3, (RF, RF, RF_IF), rd_rn_rm),
21830 cCL("polem", ec80140, 3, (RF, RF, RF_IF), rd_rn_rm),
21831 cCL("polez", ec80160, 3, (RF, RF, RF_IF), rd_rn_rm),
21832
21833 cCE("cmf", e90f110, 2, (RF, RF_IF), fpa_cmp),
21834 C3E("cmfe", ed0f110, 2, (RF, RF_IF), fpa_cmp),
21835 cCE("cnf", eb0f110, 2, (RF, RF_IF), fpa_cmp),
21836 C3E("cnfe", ef0f110, 2, (RF, RF_IF), fpa_cmp),
21837
21838 cCL("flts", e000110, 2, (RF, RR), rn_rd),
21839 cCL("fltsp", e000130, 2, (RF, RR), rn_rd),
21840 cCL("fltsm", e000150, 2, (RF, RR), rn_rd),
21841 cCL("fltsz", e000170, 2, (RF, RR), rn_rd),
21842 cCL("fltd", e000190, 2, (RF, RR), rn_rd),
21843 cCL("fltdp", e0001b0, 2, (RF, RR), rn_rd),
21844 cCL("fltdm", e0001d0, 2, (RF, RR), rn_rd),
21845 cCL("fltdz", e0001f0, 2, (RF, RR), rn_rd),
21846 cCL("flte", e080110, 2, (RF, RR), rn_rd),
21847 cCL("fltep", e080130, 2, (RF, RR), rn_rd),
21848 cCL("fltem", e080150, 2, (RF, RR), rn_rd),
21849 cCL("fltez", e080170, 2, (RF, RR), rn_rd),
b99bd4ef 21850
c19d1205
ZW
21851 /* The implementation of the FIX instruction is broken on some
21852 assemblers, in that it accepts a precision specifier as well as a
21853 rounding specifier, despite the fact that this is meaningless.
21854 To be more compatible, we accept it as well, though of course it
21855 does not set any bits. */
21d799b5
NC
21856 cCE("fix", e100110, 2, (RR, RF), rd_rm),
21857 cCL("fixp", e100130, 2, (RR, RF), rd_rm),
21858 cCL("fixm", e100150, 2, (RR, RF), rd_rm),
21859 cCL("fixz", e100170, 2, (RR, RF), rd_rm),
21860 cCL("fixsp", e100130, 2, (RR, RF), rd_rm),
21861 cCL("fixsm", e100150, 2, (RR, RF), rd_rm),
21862 cCL("fixsz", e100170, 2, (RR, RF), rd_rm),
21863 cCL("fixdp", e100130, 2, (RR, RF), rd_rm),
21864 cCL("fixdm", e100150, 2, (RR, RF), rd_rm),
21865 cCL("fixdz", e100170, 2, (RR, RF), rd_rm),
21866 cCL("fixep", e100130, 2, (RR, RF), rd_rm),
21867 cCL("fixem", e100150, 2, (RR, RF), rd_rm),
21868 cCL("fixez", e100170, 2, (RR, RF), rd_rm),
bfae80f2 21869
c19d1205 21870 /* Instructions that were new with the real FPA, call them V2. */
c921be7d
NC
21871#undef ARM_VARIANT
21872#define ARM_VARIANT & fpu_fpa_ext_v2
21873
21d799b5
NC
21874 cCE("lfm", c100200, 3, (RF, I4b, ADDR), fpa_ldmstm),
21875 cCL("lfmfd", c900200, 3, (RF, I4b, ADDR), fpa_ldmstm),
21876 cCL("lfmea", d100200, 3, (RF, I4b, ADDR), fpa_ldmstm),
21877 cCE("sfm", c000200, 3, (RF, I4b, ADDR), fpa_ldmstm),
21878 cCL("sfmfd", d000200, 3, (RF, I4b, ADDR), fpa_ldmstm),
21879 cCL("sfmea", c800200, 3, (RF, I4b, ADDR), fpa_ldmstm),
c19d1205 21880
c921be7d
NC
21881#undef ARM_VARIANT
21882#define ARM_VARIANT & fpu_vfp_ext_v1xd /* VFP V1xD (single precision). */
21883
c19d1205 21884 /* Moves and type conversions. */
21d799b5
NC
21885 cCE("fcpys", eb00a40, 2, (RVS, RVS), vfp_sp_monadic),
21886 cCE("fmrs", e100a10, 2, (RR, RVS), vfp_reg_from_sp),
21887 cCE("fmsr", e000a10, 2, (RVS, RR), vfp_sp_from_reg),
21888 cCE("fmstat", ef1fa10, 0, (), noargs),
7465e07a
NC
21889 cCE("vmrs", ef00a10, 2, (APSR_RR, RVC), vmrs),
21890 cCE("vmsr", ee00a10, 2, (RVC, RR), vmsr),
21d799b5
NC
21891 cCE("fsitos", eb80ac0, 2, (RVS, RVS), vfp_sp_monadic),
21892 cCE("fuitos", eb80a40, 2, (RVS, RVS), vfp_sp_monadic),
21893 cCE("ftosis", ebd0a40, 2, (RVS, RVS), vfp_sp_monadic),
21894 cCE("ftosizs", ebd0ac0, 2, (RVS, RVS), vfp_sp_monadic),
21895 cCE("ftouis", ebc0a40, 2, (RVS, RVS), vfp_sp_monadic),
21896 cCE("ftouizs", ebc0ac0, 2, (RVS, RVS), vfp_sp_monadic),
21897 cCE("fmrx", ef00a10, 2, (RR, RVC), rd_rn),
21898 cCE("fmxr", ee00a10, 2, (RVC, RR), rn_rd),
c19d1205
ZW
21899
21900 /* Memory operations. */
21d799b5
NC
21901 cCE("flds", d100a00, 2, (RVS, ADDRGLDC), vfp_sp_ldst),
21902 cCE("fsts", d000a00, 2, (RVS, ADDRGLDC), vfp_sp_ldst),
55881a11
MGD
21903 cCE("fldmias", c900a00, 2, (RRnpctw, VRSLST), vfp_sp_ldstmia),
21904 cCE("fldmfds", c900a00, 2, (RRnpctw, VRSLST), vfp_sp_ldstmia),
21905 cCE("fldmdbs", d300a00, 2, (RRnpctw, VRSLST), vfp_sp_ldstmdb),
21906 cCE("fldmeas", d300a00, 2, (RRnpctw, VRSLST), vfp_sp_ldstmdb),
21907 cCE("fldmiax", c900b00, 2, (RRnpctw, VRDLST), vfp_xp_ldstmia),
21908 cCE("fldmfdx", c900b00, 2, (RRnpctw, VRDLST), vfp_xp_ldstmia),
21909 cCE("fldmdbx", d300b00, 2, (RRnpctw, VRDLST), vfp_xp_ldstmdb),
21910 cCE("fldmeax", d300b00, 2, (RRnpctw, VRDLST), vfp_xp_ldstmdb),
21911 cCE("fstmias", c800a00, 2, (RRnpctw, VRSLST), vfp_sp_ldstmia),
21912 cCE("fstmeas", c800a00, 2, (RRnpctw, VRSLST), vfp_sp_ldstmia),
21913 cCE("fstmdbs", d200a00, 2, (RRnpctw, VRSLST), vfp_sp_ldstmdb),
21914 cCE("fstmfds", d200a00, 2, (RRnpctw, VRSLST), vfp_sp_ldstmdb),
21915 cCE("fstmiax", c800b00, 2, (RRnpctw, VRDLST), vfp_xp_ldstmia),
21916 cCE("fstmeax", c800b00, 2, (RRnpctw, VRDLST), vfp_xp_ldstmia),
21917 cCE("fstmdbx", d200b00, 2, (RRnpctw, VRDLST), vfp_xp_ldstmdb),
21918 cCE("fstmfdx", d200b00, 2, (RRnpctw, VRDLST), vfp_xp_ldstmdb),
bfae80f2 21919
c19d1205 21920 /* Monadic operations. */
21d799b5
NC
21921 cCE("fabss", eb00ac0, 2, (RVS, RVS), vfp_sp_monadic),
21922 cCE("fnegs", eb10a40, 2, (RVS, RVS), vfp_sp_monadic),
21923 cCE("fsqrts", eb10ac0, 2, (RVS, RVS), vfp_sp_monadic),
c19d1205
ZW
21924
21925 /* Dyadic operations. */
21d799b5
NC
21926 cCE("fadds", e300a00, 3, (RVS, RVS, RVS), vfp_sp_dyadic),
21927 cCE("fsubs", e300a40, 3, (RVS, RVS, RVS), vfp_sp_dyadic),
21928 cCE("fmuls", e200a00, 3, (RVS, RVS, RVS), vfp_sp_dyadic),
21929 cCE("fdivs", e800a00, 3, (RVS, RVS, RVS), vfp_sp_dyadic),
21930 cCE("fmacs", e000a00, 3, (RVS, RVS, RVS), vfp_sp_dyadic),
21931 cCE("fmscs", e100a00, 3, (RVS, RVS, RVS), vfp_sp_dyadic),
21932 cCE("fnmuls", e200a40, 3, (RVS, RVS, RVS), vfp_sp_dyadic),
21933 cCE("fnmacs", e000a40, 3, (RVS, RVS, RVS), vfp_sp_dyadic),
21934 cCE("fnmscs", e100a40, 3, (RVS, RVS, RVS), vfp_sp_dyadic),
b99bd4ef 21935
c19d1205 21936 /* Comparisons. */
21d799b5
NC
21937 cCE("fcmps", eb40a40, 2, (RVS, RVS), vfp_sp_monadic),
21938 cCE("fcmpzs", eb50a40, 1, (RVS), vfp_sp_compare_z),
21939 cCE("fcmpes", eb40ac0, 2, (RVS, RVS), vfp_sp_monadic),
21940 cCE("fcmpezs", eb50ac0, 1, (RVS), vfp_sp_compare_z),
b99bd4ef 21941
62f3b8c8
PB
21942 /* Double precision load/store are still present on single precision
21943 implementations. */
21944 cCE("fldd", d100b00, 2, (RVD, ADDRGLDC), vfp_dp_ldst),
21945 cCE("fstd", d000b00, 2, (RVD, ADDRGLDC), vfp_dp_ldst),
55881a11
MGD
21946 cCE("fldmiad", c900b00, 2, (RRnpctw, VRDLST), vfp_dp_ldstmia),
21947 cCE("fldmfdd", c900b00, 2, (RRnpctw, VRDLST), vfp_dp_ldstmia),
21948 cCE("fldmdbd", d300b00, 2, (RRnpctw, VRDLST), vfp_dp_ldstmdb),
21949 cCE("fldmead", d300b00, 2, (RRnpctw, VRDLST), vfp_dp_ldstmdb),
21950 cCE("fstmiad", c800b00, 2, (RRnpctw, VRDLST), vfp_dp_ldstmia),
21951 cCE("fstmead", c800b00, 2, (RRnpctw, VRDLST), vfp_dp_ldstmia),
21952 cCE("fstmdbd", d200b00, 2, (RRnpctw, VRDLST), vfp_dp_ldstmdb),
21953 cCE("fstmfdd", d200b00, 2, (RRnpctw, VRDLST), vfp_dp_ldstmdb),
62f3b8c8 21954
c921be7d
NC
21955#undef ARM_VARIANT
21956#define ARM_VARIANT & fpu_vfp_ext_v1 /* VFP V1 (Double precision). */
21957
c19d1205 21958 /* Moves and type conversions. */
21d799b5
NC
21959 cCE("fcpyd", eb00b40, 2, (RVD, RVD), vfp_dp_rd_rm),
21960 cCE("fcvtds", eb70ac0, 2, (RVD, RVS), vfp_dp_sp_cvt),
21961 cCE("fcvtsd", eb70bc0, 2, (RVS, RVD), vfp_sp_dp_cvt),
21962 cCE("fmdhr", e200b10, 2, (RVD, RR), vfp_dp_rn_rd),
21963 cCE("fmdlr", e000b10, 2, (RVD, RR), vfp_dp_rn_rd),
21964 cCE("fmrdh", e300b10, 2, (RR, RVD), vfp_dp_rd_rn),
21965 cCE("fmrdl", e100b10, 2, (RR, RVD), vfp_dp_rd_rn),
21966 cCE("fsitod", eb80bc0, 2, (RVD, RVS), vfp_dp_sp_cvt),
21967 cCE("fuitod", eb80b40, 2, (RVD, RVS), vfp_dp_sp_cvt),
21968 cCE("ftosid", ebd0b40, 2, (RVS, RVD), vfp_sp_dp_cvt),
21969 cCE("ftosizd", ebd0bc0, 2, (RVS, RVD), vfp_sp_dp_cvt),
21970 cCE("ftouid", ebc0b40, 2, (RVS, RVD), vfp_sp_dp_cvt),
21971 cCE("ftouizd", ebc0bc0, 2, (RVS, RVD), vfp_sp_dp_cvt),
c19d1205 21972
c19d1205 21973 /* Monadic operations. */
21d799b5
NC
21974 cCE("fabsd", eb00bc0, 2, (RVD, RVD), vfp_dp_rd_rm),
21975 cCE("fnegd", eb10b40, 2, (RVD, RVD), vfp_dp_rd_rm),
21976 cCE("fsqrtd", eb10bc0, 2, (RVD, RVD), vfp_dp_rd_rm),
c19d1205
ZW
21977
21978 /* Dyadic operations. */
21d799b5
NC
21979 cCE("faddd", e300b00, 3, (RVD, RVD, RVD), vfp_dp_rd_rn_rm),
21980 cCE("fsubd", e300b40, 3, (RVD, RVD, RVD), vfp_dp_rd_rn_rm),
21981 cCE("fmuld", e200b00, 3, (RVD, RVD, RVD), vfp_dp_rd_rn_rm),
21982 cCE("fdivd", e800b00, 3, (RVD, RVD, RVD), vfp_dp_rd_rn_rm),
21983 cCE("fmacd", e000b00, 3, (RVD, RVD, RVD), vfp_dp_rd_rn_rm),
21984 cCE("fmscd", e100b00, 3, (RVD, RVD, RVD), vfp_dp_rd_rn_rm),
21985 cCE("fnmuld", e200b40, 3, (RVD, RVD, RVD), vfp_dp_rd_rn_rm),
21986 cCE("fnmacd", e000b40, 3, (RVD, RVD, RVD), vfp_dp_rd_rn_rm),
21987 cCE("fnmscd", e100b40, 3, (RVD, RVD, RVD), vfp_dp_rd_rn_rm),
b99bd4ef 21988
c19d1205 21989 /* Comparisons. */
21d799b5
NC
21990 cCE("fcmpd", eb40b40, 2, (RVD, RVD), vfp_dp_rd_rm),
21991 cCE("fcmpzd", eb50b40, 1, (RVD), vfp_dp_rd),
21992 cCE("fcmped", eb40bc0, 2, (RVD, RVD), vfp_dp_rd_rm),
21993 cCE("fcmpezd", eb50bc0, 1, (RVD), vfp_dp_rd),
c19d1205 21994
c921be7d
NC
21995#undef ARM_VARIANT
21996#define ARM_VARIANT & fpu_vfp_ext_v2
21997
21d799b5
NC
21998 cCE("fmsrr", c400a10, 3, (VRSLST, RR, RR), vfp_sp2_from_reg2),
21999 cCE("fmrrs", c500a10, 3, (RR, RR, VRSLST), vfp_reg2_from_sp2),
22000 cCE("fmdrr", c400b10, 3, (RVD, RR, RR), vfp_dp_rm_rd_rn),
22001 cCE("fmrrd", c500b10, 3, (RR, RR, RVD), vfp_dp_rd_rn_rm),
5287ad62 22002
037e8744
JB
22003/* Instructions which may belong to either the Neon or VFP instruction sets.
22004 Individual encoder functions perform additional architecture checks. */
c921be7d
NC
22005#undef ARM_VARIANT
22006#define ARM_VARIANT & fpu_vfp_ext_v1xd
22007#undef THUMB_VARIANT
22008#define THUMB_VARIANT & fpu_vfp_ext_v1xd
22009
037e8744
JB
22010 /* These mnemonics are unique to VFP. */
22011 NCE(vsqrt, 0, 2, (RVSD, RVSD), vfp_nsyn_sqrt),
22012 NCE(vdiv, 0, 3, (RVSD, RVSD, RVSD), vfp_nsyn_div),
21d799b5
NC
22013 nCE(vnmul, _vnmul, 3, (RVSD, RVSD, RVSD), vfp_nsyn_nmul),
22014 nCE(vnmla, _vnmla, 3, (RVSD, RVSD, RVSD), vfp_nsyn_nmul),
22015 nCE(vnmls, _vnmls, 3, (RVSD, RVSD, RVSD), vfp_nsyn_nmul),
aacf0b33
KT
22016 nCE(vcmp, _vcmp, 2, (RVSD, RSVD_FI0), vfp_nsyn_cmp),
22017 nCE(vcmpe, _vcmpe, 2, (RVSD, RSVD_FI0), vfp_nsyn_cmp),
037e8744
JB
22018 NCE(vpush, 0, 1, (VRSDLST), vfp_nsyn_push),
22019 NCE(vpop, 0, 1, (VRSDLST), vfp_nsyn_pop),
22020 NCE(vcvtz, 0, 2, (RVSD, RVSD), vfp_nsyn_cvtz),
22021
22022 /* Mnemonics shared by Neon and VFP. */
21d799b5
NC
22023 nCEF(vmul, _vmul, 3, (RNSDQ, oRNSDQ, RNSDQ_RNSC), neon_mul),
22024 nCEF(vmla, _vmla, 3, (RNSDQ, oRNSDQ, RNSDQ_RNSC), neon_mac_maybe_scalar),
22025 nCEF(vmls, _vmls, 3, (RNSDQ, oRNSDQ, RNSDQ_RNSC), neon_mac_maybe_scalar),
037e8744 22026
55881a11
MGD
22027 NCE(vldm, c900b00, 2, (RRnpctw, VRSDLST), neon_ldm_stm),
22028 NCE(vldmia, c900b00, 2, (RRnpctw, VRSDLST), neon_ldm_stm),
22029 NCE(vldmdb, d100b00, 2, (RRnpctw, VRSDLST), neon_ldm_stm),
22030 NCE(vstm, c800b00, 2, (RRnpctw, VRSDLST), neon_ldm_stm),
22031 NCE(vstmia, c800b00, 2, (RRnpctw, VRSDLST), neon_ldm_stm),
22032 NCE(vstmdb, d000b00, 2, (RRnpctw, VRSDLST), neon_ldm_stm),
037e8744 22033
5f1af56b 22034 nCEF(vcvt, _vcvt, 3, (RNSDQ, RNSDQ, oI32z), neon_cvt),
e3e535bc 22035 nCEF(vcvtr, _vcvt, 2, (RNSDQ, RNSDQ), neon_cvtr),
c70a8987
MGD
22036 NCEF(vcvtb, eb20a40, 2, (RVSD, RVSD), neon_cvtb),
22037 NCEF(vcvtt, eb20a40, 2, (RVSD, RVSD), neon_cvtt),
f31fef98 22038
037e8744
JB
22039
22040 /* NOTE: All VMOV encoding is special-cased! */
22041 NCE(vmov, 0, 1, (VMOV), neon_mov),
22042 NCE(vmovq, 0, 1, (VMOV), neon_mov),
22043
32c36c3c
AV
22044#undef THUMB_VARIANT
22045/* Could be either VLDR/VSTR or VLDR/VSTR (system register) which are guarded
22046 by different feature bits. Since we are setting the Thumb guard, we can
22047 require Thumb-1 which makes it a nop guard and set the right feature bit in
22048 do_vldr_vstr (). */
22049#define THUMB_VARIANT & arm_ext_v4t
22050 NCE(vldr, d100b00, 2, (VLDR, ADDRGLDC), vldr_vstr),
22051 NCE(vstr, d000b00, 2, (VLDR, ADDRGLDC), vldr_vstr),
22052
9db2f6b4
RL
22053#undef ARM_VARIANT
22054#define ARM_VARIANT & arm_ext_fp16
22055#undef THUMB_VARIANT
22056#define THUMB_VARIANT & arm_ext_fp16
22057 /* New instructions added from v8.2, allowing the extraction and insertion of
22058 the upper 16 bits of a 32-bit vector register. */
22059 NCE (vmovx, eb00a40, 2, (RVS, RVS), neon_movhf),
22060 NCE (vins, eb00ac0, 2, (RVS, RVS), neon_movhf),
22061
dec41383
JW
22062 /* New backported fma/fms instructions optional in v8.2. */
22063 NCE (vfmal, 810, 3, (RNDQ, RNSD, RNSD_RNSC), neon_vfmal),
22064 NCE (vfmsl, 810, 3, (RNDQ, RNSD, RNSD_RNSC), neon_vfmsl),
22065
c921be7d
NC
22066#undef THUMB_VARIANT
22067#define THUMB_VARIANT & fpu_neon_ext_v1
22068#undef ARM_VARIANT
22069#define ARM_VARIANT & fpu_neon_ext_v1
22070
5287ad62
JB
22071 /* Data processing with three registers of the same length. */
22072 /* integer ops, valid types S8 S16 S32 U8 U16 U32. */
22073 NUF(vaba, 0000710, 3, (RNDQ, RNDQ, RNDQ), neon_dyadic_i_su),
22074 NUF(vabaq, 0000710, 3, (RNQ, RNQ, RNQ), neon_dyadic_i_su),
22075 NUF(vhadd, 0000000, 3, (RNDQ, oRNDQ, RNDQ), neon_dyadic_i_su),
22076 NUF(vhaddq, 0000000, 3, (RNQ, oRNQ, RNQ), neon_dyadic_i_su),
22077 NUF(vrhadd, 0000100, 3, (RNDQ, oRNDQ, RNDQ), neon_dyadic_i_su),
22078 NUF(vrhaddq, 0000100, 3, (RNQ, oRNQ, RNQ), neon_dyadic_i_su),
22079 NUF(vhsub, 0000200, 3, (RNDQ, oRNDQ, RNDQ), neon_dyadic_i_su),
22080 NUF(vhsubq, 0000200, 3, (RNQ, oRNQ, RNQ), neon_dyadic_i_su),
22081 /* integer ops, valid types S8 S16 S32 S64 U8 U16 U32 U64. */
22082 NUF(vqadd, 0000010, 3, (RNDQ, oRNDQ, RNDQ), neon_dyadic_i64_su),
22083 NUF(vqaddq, 0000010, 3, (RNQ, oRNQ, RNQ), neon_dyadic_i64_su),
22084 NUF(vqsub, 0000210, 3, (RNDQ, oRNDQ, RNDQ), neon_dyadic_i64_su),
22085 NUF(vqsubq, 0000210, 3, (RNQ, oRNQ, RNQ), neon_dyadic_i64_su),
627907b7
JB
22086 NUF(vrshl, 0000500, 3, (RNDQ, oRNDQ, RNDQ), neon_rshl),
22087 NUF(vrshlq, 0000500, 3, (RNQ, oRNQ, RNQ), neon_rshl),
22088 NUF(vqrshl, 0000510, 3, (RNDQ, oRNDQ, RNDQ), neon_rshl),
22089 NUF(vqrshlq, 0000510, 3, (RNQ, oRNQ, RNQ), neon_rshl),
5287ad62
JB
22090 /* If not immediate, fall back to neon_dyadic_i64_su.
22091 shl_imm should accept I8 I16 I32 I64,
22092 qshl_imm should accept S8 S16 S32 S64 U8 U16 U32 U64. */
21d799b5
NC
22093 nUF(vshl, _vshl, 3, (RNDQ, oRNDQ, RNDQ_I63b), neon_shl_imm),
22094 nUF(vshlq, _vshl, 3, (RNQ, oRNQ, RNDQ_I63b), neon_shl_imm),
22095 nUF(vqshl, _vqshl, 3, (RNDQ, oRNDQ, RNDQ_I63b), neon_qshl_imm),
22096 nUF(vqshlq, _vqshl, 3, (RNQ, oRNQ, RNDQ_I63b), neon_qshl_imm),
5287ad62 22097 /* Logic ops, types optional & ignored. */
4316f0d2
DG
22098 nUF(vand, _vand, 3, (RNDQ, oRNDQ, RNDQ_Ibig), neon_logic),
22099 nUF(vandq, _vand, 3, (RNQ, oRNQ, RNDQ_Ibig), neon_logic),
22100 nUF(vbic, _vbic, 3, (RNDQ, oRNDQ, RNDQ_Ibig), neon_logic),
22101 nUF(vbicq, _vbic, 3, (RNQ, oRNQ, RNDQ_Ibig), neon_logic),
22102 nUF(vorr, _vorr, 3, (RNDQ, oRNDQ, RNDQ_Ibig), neon_logic),
22103 nUF(vorrq, _vorr, 3, (RNQ, oRNQ, RNDQ_Ibig), neon_logic),
22104 nUF(vorn, _vorn, 3, (RNDQ, oRNDQ, RNDQ_Ibig), neon_logic),
22105 nUF(vornq, _vorn, 3, (RNQ, oRNQ, RNDQ_Ibig), neon_logic),
22106 nUF(veor, _veor, 3, (RNDQ, oRNDQ, RNDQ), neon_logic),
22107 nUF(veorq, _veor, 3, (RNQ, oRNQ, RNQ), neon_logic),
5287ad62
JB
22108 /* Bitfield ops, untyped. */
22109 NUF(vbsl, 1100110, 3, (RNDQ, RNDQ, RNDQ), neon_bitfield),
22110 NUF(vbslq, 1100110, 3, (RNQ, RNQ, RNQ), neon_bitfield),
22111 NUF(vbit, 1200110, 3, (RNDQ, RNDQ, RNDQ), neon_bitfield),
22112 NUF(vbitq, 1200110, 3, (RNQ, RNQ, RNQ), neon_bitfield),
22113 NUF(vbif, 1300110, 3, (RNDQ, RNDQ, RNDQ), neon_bitfield),
22114 NUF(vbifq, 1300110, 3, (RNQ, RNQ, RNQ), neon_bitfield),
cc933301 22115 /* Int and float variants, types S8 S16 S32 U8 U16 U32 F16 F32. */
21d799b5
NC
22116 nUF(vabdq, _vabd, 3, (RNQ, oRNQ, RNQ), neon_dyadic_if_su),
22117 nUF(vmax, _vmax, 3, (RNDQ, oRNDQ, RNDQ), neon_dyadic_if_su),
22118 nUF(vmaxq, _vmax, 3, (RNQ, oRNQ, RNQ), neon_dyadic_if_su),
22119 nUF(vmin, _vmin, 3, (RNDQ, oRNDQ, RNDQ), neon_dyadic_if_su),
22120 nUF(vminq, _vmin, 3, (RNQ, oRNQ, RNQ), neon_dyadic_if_su),
5287ad62
JB
22121 /* Comparisons. Types S8 S16 S32 U8 U16 U32 F32. Non-immediate versions fall
22122 back to neon_dyadic_if_su. */
21d799b5
NC
22123 nUF(vcge, _vcge, 3, (RNDQ, oRNDQ, RNDQ_I0), neon_cmp),
22124 nUF(vcgeq, _vcge, 3, (RNQ, oRNQ, RNDQ_I0), neon_cmp),
22125 nUF(vcgt, _vcgt, 3, (RNDQ, oRNDQ, RNDQ_I0), neon_cmp),
22126 nUF(vcgtq, _vcgt, 3, (RNQ, oRNQ, RNDQ_I0), neon_cmp),
22127 nUF(vclt, _vclt, 3, (RNDQ, oRNDQ, RNDQ_I0), neon_cmp_inv),
22128 nUF(vcltq, _vclt, 3, (RNQ, oRNQ, RNDQ_I0), neon_cmp_inv),
22129 nUF(vcle, _vcle, 3, (RNDQ, oRNDQ, RNDQ_I0), neon_cmp_inv),
22130 nUF(vcleq, _vcle, 3, (RNQ, oRNQ, RNDQ_I0), neon_cmp_inv),
428e3f1f 22131 /* Comparison. Type I8 I16 I32 F32. */
21d799b5
NC
22132 nUF(vceq, _vceq, 3, (RNDQ, oRNDQ, RNDQ_I0), neon_ceq),
22133 nUF(vceqq, _vceq, 3, (RNQ, oRNQ, RNDQ_I0), neon_ceq),
5287ad62 22134 /* As above, D registers only. */
21d799b5
NC
22135 nUF(vpmax, _vpmax, 3, (RND, oRND, RND), neon_dyadic_if_su_d),
22136 nUF(vpmin, _vpmin, 3, (RND, oRND, RND), neon_dyadic_if_su_d),
5287ad62 22137 /* Int and float variants, signedness unimportant. */
21d799b5
NC
22138 nUF(vmlaq, _vmla, 3, (RNQ, oRNQ, RNDQ_RNSC), neon_mac_maybe_scalar),
22139 nUF(vmlsq, _vmls, 3, (RNQ, oRNQ, RNDQ_RNSC), neon_mac_maybe_scalar),
22140 nUF(vpadd, _vpadd, 3, (RND, oRND, RND), neon_dyadic_if_i_d),
5287ad62 22141 /* Add/sub take types I8 I16 I32 I64 F32. */
21d799b5
NC
22142 nUF(vaddq, _vadd, 3, (RNQ, oRNQ, RNQ), neon_addsub_if_i),
22143 nUF(vsubq, _vsub, 3, (RNQ, oRNQ, RNQ), neon_addsub_if_i),
5287ad62
JB
22144 /* vtst takes sizes 8, 16, 32. */
22145 NUF(vtst, 0000810, 3, (RNDQ, oRNDQ, RNDQ), neon_tst),
22146 NUF(vtstq, 0000810, 3, (RNQ, oRNQ, RNQ), neon_tst),
22147 /* VMUL takes I8 I16 I32 F32 P8. */
21d799b5 22148 nUF(vmulq, _vmul, 3, (RNQ, oRNQ, RNDQ_RNSC), neon_mul),
5287ad62 22149 /* VQD{R}MULH takes S16 S32. */
21d799b5
NC
22150 nUF(vqdmulh, _vqdmulh, 3, (RNDQ, oRNDQ, RNDQ_RNSC), neon_qdmulh),
22151 nUF(vqdmulhq, _vqdmulh, 3, (RNQ, oRNQ, RNDQ_RNSC), neon_qdmulh),
22152 nUF(vqrdmulh, _vqrdmulh, 3, (RNDQ, oRNDQ, RNDQ_RNSC), neon_qdmulh),
22153 nUF(vqrdmulhq, _vqrdmulh, 3, (RNQ, oRNQ, RNDQ_RNSC), neon_qdmulh),
5287ad62
JB
22154 NUF(vacge, 0000e10, 3, (RNDQ, oRNDQ, RNDQ), neon_fcmp_absolute),
22155 NUF(vacgeq, 0000e10, 3, (RNQ, oRNQ, RNQ), neon_fcmp_absolute),
22156 NUF(vacgt, 0200e10, 3, (RNDQ, oRNDQ, RNDQ), neon_fcmp_absolute),
22157 NUF(vacgtq, 0200e10, 3, (RNQ, oRNQ, RNQ), neon_fcmp_absolute),
92559b5b
PB
22158 NUF(vaclt, 0200e10, 3, (RNDQ, oRNDQ, RNDQ), neon_fcmp_absolute_inv),
22159 NUF(vacltq, 0200e10, 3, (RNQ, oRNQ, RNQ), neon_fcmp_absolute_inv),
22160 NUF(vacle, 0000e10, 3, (RNDQ, oRNDQ, RNDQ), neon_fcmp_absolute_inv),
22161 NUF(vacleq, 0000e10, 3, (RNQ, oRNQ, RNQ), neon_fcmp_absolute_inv),
5287ad62
JB
22162 NUF(vrecps, 0000f10, 3, (RNDQ, oRNDQ, RNDQ), neon_step),
22163 NUF(vrecpsq, 0000f10, 3, (RNQ, oRNQ, RNQ), neon_step),
22164 NUF(vrsqrts, 0200f10, 3, (RNDQ, oRNDQ, RNDQ), neon_step),
22165 NUF(vrsqrtsq, 0200f10, 3, (RNQ, oRNQ, RNQ), neon_step),
d6b4b13e 22166 /* ARM v8.1 extension. */
643afb90
MW
22167 nUF (vqrdmlah, _vqrdmlah, 3, (RNDQ, oRNDQ, RNDQ_RNSC), neon_qrdmlah),
22168 nUF (vqrdmlahq, _vqrdmlah, 3, (RNQ, oRNQ, RNDQ_RNSC), neon_qrdmlah),
22169 nUF (vqrdmlsh, _vqrdmlsh, 3, (RNDQ, oRNDQ, RNDQ_RNSC), neon_qrdmlah),
22170 nUF (vqrdmlshq, _vqrdmlsh, 3, (RNQ, oRNQ, RNDQ_RNSC), neon_qrdmlah),
5287ad62
JB
22171
22172 /* Two address, int/float. Types S8 S16 S32 F32. */
5287ad62 22173 NUF(vabsq, 1b10300, 2, (RNQ, RNQ), neon_abs_neg),
5287ad62
JB
22174 NUF(vnegq, 1b10380, 2, (RNQ, RNQ), neon_abs_neg),
22175
22176 /* Data processing with two registers and a shift amount. */
22177 /* Right shifts, and variants with rounding.
22178 Types accepted S8 S16 S32 S64 U8 U16 U32 U64. */
22179 NUF(vshr, 0800010, 3, (RNDQ, oRNDQ, I64z), neon_rshift_round_imm),
22180 NUF(vshrq, 0800010, 3, (RNQ, oRNQ, I64z), neon_rshift_round_imm),
22181 NUF(vrshr, 0800210, 3, (RNDQ, oRNDQ, I64z), neon_rshift_round_imm),
22182 NUF(vrshrq, 0800210, 3, (RNQ, oRNQ, I64z), neon_rshift_round_imm),
22183 NUF(vsra, 0800110, 3, (RNDQ, oRNDQ, I64), neon_rshift_round_imm),
22184 NUF(vsraq, 0800110, 3, (RNQ, oRNQ, I64), neon_rshift_round_imm),
22185 NUF(vrsra, 0800310, 3, (RNDQ, oRNDQ, I64), neon_rshift_round_imm),
22186 NUF(vrsraq, 0800310, 3, (RNQ, oRNQ, I64), neon_rshift_round_imm),
22187 /* Shift and insert. Sizes accepted 8 16 32 64. */
22188 NUF(vsli, 1800510, 3, (RNDQ, oRNDQ, I63), neon_sli),
22189 NUF(vsliq, 1800510, 3, (RNQ, oRNQ, I63), neon_sli),
22190 NUF(vsri, 1800410, 3, (RNDQ, oRNDQ, I64), neon_sri),
22191 NUF(vsriq, 1800410, 3, (RNQ, oRNQ, I64), neon_sri),
22192 /* QSHL{U} immediate accepts S8 S16 S32 S64 U8 U16 U32 U64. */
22193 NUF(vqshlu, 1800610, 3, (RNDQ, oRNDQ, I63), neon_qshlu_imm),
22194 NUF(vqshluq, 1800610, 3, (RNQ, oRNQ, I63), neon_qshlu_imm),
22195 /* Right shift immediate, saturating & narrowing, with rounding variants.
22196 Types accepted S16 S32 S64 U16 U32 U64. */
22197 NUF(vqshrn, 0800910, 3, (RND, RNQ, I32z), neon_rshift_sat_narrow),
22198 NUF(vqrshrn, 0800950, 3, (RND, RNQ, I32z), neon_rshift_sat_narrow),
22199 /* As above, unsigned. Types accepted S16 S32 S64. */
22200 NUF(vqshrun, 0800810, 3, (RND, RNQ, I32z), neon_rshift_sat_narrow_u),
22201 NUF(vqrshrun, 0800850, 3, (RND, RNQ, I32z), neon_rshift_sat_narrow_u),
22202 /* Right shift narrowing. Types accepted I16 I32 I64. */
22203 NUF(vshrn, 0800810, 3, (RND, RNQ, I32z), neon_rshift_narrow),
22204 NUF(vrshrn, 0800850, 3, (RND, RNQ, I32z), neon_rshift_narrow),
22205 /* Special case. Types S8 S16 S32 U8 U16 U32. Handles max shift variant. */
21d799b5 22206 nUF(vshll, _vshll, 3, (RNQ, RND, I32), neon_shll),
5287ad62 22207 /* CVT with optional immediate for fixed-point variant. */
21d799b5 22208 nUF(vcvtq, _vcvt, 3, (RNQ, RNQ, oI32b), neon_cvt),
b7fc2769 22209
4316f0d2
DG
22210 nUF(vmvn, _vmvn, 2, (RNDQ, RNDQ_Ibig), neon_mvn),
22211 nUF(vmvnq, _vmvn, 2, (RNQ, RNDQ_Ibig), neon_mvn),
5287ad62
JB
22212
22213 /* Data processing, three registers of different lengths. */
22214 /* Dyadic, long insns. Types S8 S16 S32 U8 U16 U32. */
22215 NUF(vabal, 0800500, 3, (RNQ, RND, RND), neon_abal),
5287ad62
JB
22216 /* If not scalar, fall back to neon_dyadic_long.
22217 Vector types as above, scalar types S16 S32 U16 U32. */
21d799b5
NC
22218 nUF(vmlal, _vmlal, 3, (RNQ, RND, RND_RNSC), neon_mac_maybe_scalar_long),
22219 nUF(vmlsl, _vmlsl, 3, (RNQ, RND, RND_RNSC), neon_mac_maybe_scalar_long),
5287ad62
JB
22220 /* Dyadic, widening insns. Types S8 S16 S32 U8 U16 U32. */
22221 NUF(vaddw, 0800100, 3, (RNQ, oRNQ, RND), neon_dyadic_wide),
22222 NUF(vsubw, 0800300, 3, (RNQ, oRNQ, RND), neon_dyadic_wide),
22223 /* Dyadic, narrowing insns. Types I16 I32 I64. */
22224 NUF(vaddhn, 0800400, 3, (RND, RNQ, RNQ), neon_dyadic_narrow),
22225 NUF(vraddhn, 1800400, 3, (RND, RNQ, RNQ), neon_dyadic_narrow),
22226 NUF(vsubhn, 0800600, 3, (RND, RNQ, RNQ), neon_dyadic_narrow),
22227 NUF(vrsubhn, 1800600, 3, (RND, RNQ, RNQ), neon_dyadic_narrow),
22228 /* Saturating doubling multiplies. Types S16 S32. */
21d799b5
NC
22229 nUF(vqdmlal, _vqdmlal, 3, (RNQ, RND, RND_RNSC), neon_mul_sat_scalar_long),
22230 nUF(vqdmlsl, _vqdmlsl, 3, (RNQ, RND, RND_RNSC), neon_mul_sat_scalar_long),
22231 nUF(vqdmull, _vqdmull, 3, (RNQ, RND, RND_RNSC), neon_mul_sat_scalar_long),
5287ad62
JB
22232 /* VMULL. Vector types S8 S16 S32 U8 U16 U32 P8, scalar types
22233 S16 S32 U16 U32. */
21d799b5 22234 nUF(vmull, _vmull, 3, (RNQ, RND, RND_RNSC), neon_vmull),
5287ad62
JB
22235
22236 /* Extract. Size 8. */
3b8d421e
PB
22237 NUF(vext, 0b00000, 4, (RNDQ, oRNDQ, RNDQ, I15), neon_ext),
22238 NUF(vextq, 0b00000, 4, (RNQ, oRNQ, RNQ, I15), neon_ext),
5287ad62
JB
22239
22240 /* Two registers, miscellaneous. */
22241 /* Reverse. Sizes 8 16 32 (must be < size in opcode). */
22242 NUF(vrev64, 1b00000, 2, (RNDQ, RNDQ), neon_rev),
22243 NUF(vrev64q, 1b00000, 2, (RNQ, RNQ), neon_rev),
22244 NUF(vrev32, 1b00080, 2, (RNDQ, RNDQ), neon_rev),
22245 NUF(vrev32q, 1b00080, 2, (RNQ, RNQ), neon_rev),
22246 NUF(vrev16, 1b00100, 2, (RNDQ, RNDQ), neon_rev),
22247 NUF(vrev16q, 1b00100, 2, (RNQ, RNQ), neon_rev),
22248 /* Vector replicate. Sizes 8 16 32. */
21d799b5
NC
22249 nCE(vdup, _vdup, 2, (RNDQ, RR_RNSC), neon_dup),
22250 nCE(vdupq, _vdup, 2, (RNQ, RR_RNSC), neon_dup),
5287ad62
JB
22251 /* VMOVL. Types S8 S16 S32 U8 U16 U32. */
22252 NUF(vmovl, 0800a10, 2, (RNQ, RND), neon_movl),
22253 /* VMOVN. Types I16 I32 I64. */
21d799b5 22254 nUF(vmovn, _vmovn, 2, (RND, RNQ), neon_movn),
5287ad62 22255 /* VQMOVN. Types S16 S32 S64 U16 U32 U64. */
21d799b5 22256 nUF(vqmovn, _vqmovn, 2, (RND, RNQ), neon_qmovn),
5287ad62 22257 /* VQMOVUN. Types S16 S32 S64. */
21d799b5 22258 nUF(vqmovun, _vqmovun, 2, (RND, RNQ), neon_qmovun),
5287ad62
JB
22259 /* VZIP / VUZP. Sizes 8 16 32. */
22260 NUF(vzip, 1b20180, 2, (RNDQ, RNDQ), neon_zip_uzp),
22261 NUF(vzipq, 1b20180, 2, (RNQ, RNQ), neon_zip_uzp),
22262 NUF(vuzp, 1b20100, 2, (RNDQ, RNDQ), neon_zip_uzp),
22263 NUF(vuzpq, 1b20100, 2, (RNQ, RNQ), neon_zip_uzp),
22264 /* VQABS / VQNEG. Types S8 S16 S32. */
22265 NUF(vqabs, 1b00700, 2, (RNDQ, RNDQ), neon_sat_abs_neg),
22266 NUF(vqabsq, 1b00700, 2, (RNQ, RNQ), neon_sat_abs_neg),
22267 NUF(vqneg, 1b00780, 2, (RNDQ, RNDQ), neon_sat_abs_neg),
22268 NUF(vqnegq, 1b00780, 2, (RNQ, RNQ), neon_sat_abs_neg),
22269 /* Pairwise, lengthening. Types S8 S16 S32 U8 U16 U32. */
22270 NUF(vpadal, 1b00600, 2, (RNDQ, RNDQ), neon_pair_long),
22271 NUF(vpadalq, 1b00600, 2, (RNQ, RNQ), neon_pair_long),
22272 NUF(vpaddl, 1b00200, 2, (RNDQ, RNDQ), neon_pair_long),
22273 NUF(vpaddlq, 1b00200, 2, (RNQ, RNQ), neon_pair_long),
cc933301 22274 /* Reciprocal estimates. Types U32 F16 F32. */
5287ad62
JB
22275 NUF(vrecpe, 1b30400, 2, (RNDQ, RNDQ), neon_recip_est),
22276 NUF(vrecpeq, 1b30400, 2, (RNQ, RNQ), neon_recip_est),
22277 NUF(vrsqrte, 1b30480, 2, (RNDQ, RNDQ), neon_recip_est),
22278 NUF(vrsqrteq, 1b30480, 2, (RNQ, RNQ), neon_recip_est),
22279 /* VCLS. Types S8 S16 S32. */
22280 NUF(vcls, 1b00400, 2, (RNDQ, RNDQ), neon_cls),
22281 NUF(vclsq, 1b00400, 2, (RNQ, RNQ), neon_cls),
22282 /* VCLZ. Types I8 I16 I32. */
22283 NUF(vclz, 1b00480, 2, (RNDQ, RNDQ), neon_clz),
22284 NUF(vclzq, 1b00480, 2, (RNQ, RNQ), neon_clz),
22285 /* VCNT. Size 8. */
22286 NUF(vcnt, 1b00500, 2, (RNDQ, RNDQ), neon_cnt),
22287 NUF(vcntq, 1b00500, 2, (RNQ, RNQ), neon_cnt),
22288 /* Two address, untyped. */
22289 NUF(vswp, 1b20000, 2, (RNDQ, RNDQ), neon_swp),
22290 NUF(vswpq, 1b20000, 2, (RNQ, RNQ), neon_swp),
22291 /* VTRN. Sizes 8 16 32. */
21d799b5
NC
22292 nUF(vtrn, _vtrn, 2, (RNDQ, RNDQ), neon_trn),
22293 nUF(vtrnq, _vtrn, 2, (RNQ, RNQ), neon_trn),
5287ad62
JB
22294
22295 /* Table lookup. Size 8. */
22296 NUF(vtbl, 1b00800, 3, (RND, NRDLST, RND), neon_tbl_tbx),
22297 NUF(vtbx, 1b00840, 3, (RND, NRDLST, RND), neon_tbl_tbx),
22298
c921be7d
NC
22299#undef THUMB_VARIANT
22300#define THUMB_VARIANT & fpu_vfp_v3_or_neon_ext
22301#undef ARM_VARIANT
22302#define ARM_VARIANT & fpu_vfp_v3_or_neon_ext
22303
5287ad62 22304 /* Neon element/structure load/store. */
21d799b5
NC
22305 nUF(vld1, _vld1, 2, (NSTRLST, ADDR), neon_ldx_stx),
22306 nUF(vst1, _vst1, 2, (NSTRLST, ADDR), neon_ldx_stx),
22307 nUF(vld2, _vld2, 2, (NSTRLST, ADDR), neon_ldx_stx),
22308 nUF(vst2, _vst2, 2, (NSTRLST, ADDR), neon_ldx_stx),
22309 nUF(vld3, _vld3, 2, (NSTRLST, ADDR), neon_ldx_stx),
22310 nUF(vst3, _vst3, 2, (NSTRLST, ADDR), neon_ldx_stx),
22311 nUF(vld4, _vld4, 2, (NSTRLST, ADDR), neon_ldx_stx),
22312 nUF(vst4, _vst4, 2, (NSTRLST, ADDR), neon_ldx_stx),
5287ad62 22313
c921be7d 22314#undef THUMB_VARIANT
74db7efb
NC
22315#define THUMB_VARIANT & fpu_vfp_ext_v3xd
22316#undef ARM_VARIANT
22317#define ARM_VARIANT & fpu_vfp_ext_v3xd
62f3b8c8
PB
22318 cCE("fconsts", eb00a00, 2, (RVS, I255), vfp_sp_const),
22319 cCE("fshtos", eba0a40, 2, (RVS, I16z), vfp_sp_conv_16),
22320 cCE("fsltos", eba0ac0, 2, (RVS, I32), vfp_sp_conv_32),
22321 cCE("fuhtos", ebb0a40, 2, (RVS, I16z), vfp_sp_conv_16),
22322 cCE("fultos", ebb0ac0, 2, (RVS, I32), vfp_sp_conv_32),
22323 cCE("ftoshs", ebe0a40, 2, (RVS, I16z), vfp_sp_conv_16),
22324 cCE("ftosls", ebe0ac0, 2, (RVS, I32), vfp_sp_conv_32),
22325 cCE("ftouhs", ebf0a40, 2, (RVS, I16z), vfp_sp_conv_16),
22326 cCE("ftouls", ebf0ac0, 2, (RVS, I32), vfp_sp_conv_32),
22327
74db7efb 22328#undef THUMB_VARIANT
c921be7d
NC
22329#define THUMB_VARIANT & fpu_vfp_ext_v3
22330#undef ARM_VARIANT
22331#define ARM_VARIANT & fpu_vfp_ext_v3
22332
21d799b5 22333 cCE("fconstd", eb00b00, 2, (RVD, I255), vfp_dp_const),
21d799b5 22334 cCE("fshtod", eba0b40, 2, (RVD, I16z), vfp_dp_conv_16),
21d799b5 22335 cCE("fsltod", eba0bc0, 2, (RVD, I32), vfp_dp_conv_32),
21d799b5 22336 cCE("fuhtod", ebb0b40, 2, (RVD, I16z), vfp_dp_conv_16),
21d799b5 22337 cCE("fultod", ebb0bc0, 2, (RVD, I32), vfp_dp_conv_32),
21d799b5 22338 cCE("ftoshd", ebe0b40, 2, (RVD, I16z), vfp_dp_conv_16),
21d799b5 22339 cCE("ftosld", ebe0bc0, 2, (RVD, I32), vfp_dp_conv_32),
21d799b5 22340 cCE("ftouhd", ebf0b40, 2, (RVD, I16z), vfp_dp_conv_16),
21d799b5 22341 cCE("ftould", ebf0bc0, 2, (RVD, I32), vfp_dp_conv_32),
c19d1205 22342
74db7efb
NC
22343#undef ARM_VARIANT
22344#define ARM_VARIANT & fpu_vfp_ext_fma
22345#undef THUMB_VARIANT
22346#define THUMB_VARIANT & fpu_vfp_ext_fma
62f3b8c8
PB
22347 /* Mnemonics shared by Neon and VFP. These are included in the
22348 VFP FMA variant; NEON and VFP FMA always includes the NEON
22349 FMA instructions. */
22350 nCEF(vfma, _vfma, 3, (RNSDQ, oRNSDQ, RNSDQ), neon_fmac),
22351 nCEF(vfms, _vfms, 3, (RNSDQ, oRNSDQ, RNSDQ), neon_fmac),
22352 /* ffmas/ffmad/ffmss/ffmsd are dummy mnemonics to satisfy gas;
22353 the v form should always be used. */
22354 cCE("ffmas", ea00a00, 3, (RVS, RVS, RVS), vfp_sp_dyadic),
22355 cCE("ffnmas", ea00a40, 3, (RVS, RVS, RVS), vfp_sp_dyadic),
22356 cCE("ffmad", ea00b00, 3, (RVD, RVD, RVD), vfp_dp_rd_rn_rm),
22357 cCE("ffnmad", ea00b40, 3, (RVD, RVD, RVD), vfp_dp_rd_rn_rm),
22358 nCE(vfnma, _vfnma, 3, (RVSD, RVSD, RVSD), vfp_nsyn_nmul),
22359 nCE(vfnms, _vfnms, 3, (RVSD, RVSD, RVSD), vfp_nsyn_nmul),
22360
5287ad62 22361#undef THUMB_VARIANT
c921be7d
NC
22362#undef ARM_VARIANT
22363#define ARM_VARIANT & arm_cext_xscale /* Intel XScale extensions. */
22364
21d799b5
NC
22365 cCE("mia", e200010, 3, (RXA, RRnpc, RRnpc), xsc_mia),
22366 cCE("miaph", e280010, 3, (RXA, RRnpc, RRnpc), xsc_mia),
22367 cCE("miabb", e2c0010, 3, (RXA, RRnpc, RRnpc), xsc_mia),
22368 cCE("miabt", e2d0010, 3, (RXA, RRnpc, RRnpc), xsc_mia),
22369 cCE("miatb", e2e0010, 3, (RXA, RRnpc, RRnpc), xsc_mia),
22370 cCE("miatt", e2f0010, 3, (RXA, RRnpc, RRnpc), xsc_mia),
22371 cCE("mar", c400000, 3, (RXA, RRnpc, RRnpc), xsc_mar),
22372 cCE("mra", c500000, 3, (RRnpc, RRnpc, RXA), xsc_mra),
c19d1205 22373
c921be7d
NC
22374#undef ARM_VARIANT
22375#define ARM_VARIANT & arm_cext_iwmmxt /* Intel Wireless MMX technology. */
22376
21d799b5
NC
22377 cCE("tandcb", e13f130, 1, (RR), iwmmxt_tandorc),
22378 cCE("tandch", e53f130, 1, (RR), iwmmxt_tandorc),
22379 cCE("tandcw", e93f130, 1, (RR), iwmmxt_tandorc),
22380 cCE("tbcstb", e400010, 2, (RIWR, RR), rn_rd),
22381 cCE("tbcsth", e400050, 2, (RIWR, RR), rn_rd),
22382 cCE("tbcstw", e400090, 2, (RIWR, RR), rn_rd),
22383 cCE("textrcb", e130170, 2, (RR, I7), iwmmxt_textrc),
22384 cCE("textrch", e530170, 2, (RR, I7), iwmmxt_textrc),
22385 cCE("textrcw", e930170, 2, (RR, I7), iwmmxt_textrc),
74db7efb
NC
22386 cCE("textrmub",e100070, 3, (RR, RIWR, I7), iwmmxt_textrm),
22387 cCE("textrmuh",e500070, 3, (RR, RIWR, I7), iwmmxt_textrm),
22388 cCE("textrmuw",e900070, 3, (RR, RIWR, I7), iwmmxt_textrm),
22389 cCE("textrmsb",e100078, 3, (RR, RIWR, I7), iwmmxt_textrm),
22390 cCE("textrmsh",e500078, 3, (RR, RIWR, I7), iwmmxt_textrm),
22391 cCE("textrmsw",e900078, 3, (RR, RIWR, I7), iwmmxt_textrm),
21d799b5
NC
22392 cCE("tinsrb", e600010, 3, (RIWR, RR, I7), iwmmxt_tinsr),
22393 cCE("tinsrh", e600050, 3, (RIWR, RR, I7), iwmmxt_tinsr),
22394 cCE("tinsrw", e600090, 3, (RIWR, RR, I7), iwmmxt_tinsr),
22395 cCE("tmcr", e000110, 2, (RIWC_RIWG, RR), rn_rd),
22396 cCE("tmcrr", c400000, 3, (RIWR, RR, RR), rm_rd_rn),
22397 cCE("tmia", e200010, 3, (RIWR, RR, RR), iwmmxt_tmia),
22398 cCE("tmiaph", e280010, 3, (RIWR, RR, RR), iwmmxt_tmia),
22399 cCE("tmiabb", e2c0010, 3, (RIWR, RR, RR), iwmmxt_tmia),
22400 cCE("tmiabt", e2d0010, 3, (RIWR, RR, RR), iwmmxt_tmia),
22401 cCE("tmiatb", e2e0010, 3, (RIWR, RR, RR), iwmmxt_tmia),
22402 cCE("tmiatt", e2f0010, 3, (RIWR, RR, RR), iwmmxt_tmia),
74db7efb
NC
22403 cCE("tmovmskb",e100030, 2, (RR, RIWR), rd_rn),
22404 cCE("tmovmskh",e500030, 2, (RR, RIWR), rd_rn),
22405 cCE("tmovmskw",e900030, 2, (RR, RIWR), rd_rn),
21d799b5
NC
22406 cCE("tmrc", e100110, 2, (RR, RIWC_RIWG), rd_rn),
22407 cCE("tmrrc", c500000, 3, (RR, RR, RIWR), rd_rn_rm),
22408 cCE("torcb", e13f150, 1, (RR), iwmmxt_tandorc),
22409 cCE("torch", e53f150, 1, (RR), iwmmxt_tandorc),
22410 cCE("torcw", e93f150, 1, (RR), iwmmxt_tandorc),
22411 cCE("waccb", e0001c0, 2, (RIWR, RIWR), rd_rn),
22412 cCE("wacch", e4001c0, 2, (RIWR, RIWR), rd_rn),
22413 cCE("waccw", e8001c0, 2, (RIWR, RIWR), rd_rn),
22414 cCE("waddbss", e300180, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22415 cCE("waddb", e000180, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22416 cCE("waddbus", e100180, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22417 cCE("waddhss", e700180, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22418 cCE("waddh", e400180, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22419 cCE("waddhus", e500180, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22420 cCE("waddwss", eb00180, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22421 cCE("waddw", e800180, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22422 cCE("waddwus", e900180, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22423 cCE("waligni", e000020, 4, (RIWR, RIWR, RIWR, I7), iwmmxt_waligni),
74db7efb
NC
22424 cCE("walignr0",e800020, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22425 cCE("walignr1",e900020, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22426 cCE("walignr2",ea00020, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22427 cCE("walignr3",eb00020, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
21d799b5
NC
22428 cCE("wand", e200000, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22429 cCE("wandn", e300000, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22430 cCE("wavg2b", e800000, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22431 cCE("wavg2br", e900000, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22432 cCE("wavg2h", ec00000, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22433 cCE("wavg2hr", ed00000, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22434 cCE("wcmpeqb", e000060, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22435 cCE("wcmpeqh", e400060, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22436 cCE("wcmpeqw", e800060, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
74db7efb
NC
22437 cCE("wcmpgtub",e100060, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22438 cCE("wcmpgtuh",e500060, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22439 cCE("wcmpgtuw",e900060, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22440 cCE("wcmpgtsb",e300060, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22441 cCE("wcmpgtsh",e700060, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22442 cCE("wcmpgtsw",eb00060, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
21d799b5
NC
22443 cCE("wldrb", c100000, 2, (RIWR, ADDR), iwmmxt_wldstbh),
22444 cCE("wldrh", c500000, 2, (RIWR, ADDR), iwmmxt_wldstbh),
22445 cCE("wldrw", c100100, 2, (RIWR_RIWC, ADDR), iwmmxt_wldstw),
22446 cCE("wldrd", c500100, 2, (RIWR, ADDR), iwmmxt_wldstd),
22447 cCE("wmacs", e600100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22448 cCE("wmacsz", e700100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22449 cCE("wmacu", e400100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22450 cCE("wmacuz", e500100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22451 cCE("wmadds", ea00100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22452 cCE("wmaddu", e800100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22453 cCE("wmaxsb", e200160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22454 cCE("wmaxsh", e600160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22455 cCE("wmaxsw", ea00160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22456 cCE("wmaxub", e000160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22457 cCE("wmaxuh", e400160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22458 cCE("wmaxuw", e800160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22459 cCE("wminsb", e300160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22460 cCE("wminsh", e700160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22461 cCE("wminsw", eb00160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22462 cCE("wminub", e100160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22463 cCE("wminuh", e500160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22464 cCE("wminuw", e900160, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22465 cCE("wmov", e000000, 2, (RIWR, RIWR), iwmmxt_wmov),
22466 cCE("wmulsm", e300100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22467 cCE("wmulsl", e200100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22468 cCE("wmulum", e100100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22469 cCE("wmulul", e000100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22470 cCE("wor", e000000, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
74db7efb
NC
22471 cCE("wpackhss",e700080, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22472 cCE("wpackhus",e500080, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22473 cCE("wpackwss",eb00080, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22474 cCE("wpackwus",e900080, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22475 cCE("wpackdss",ef00080, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22476 cCE("wpackdus",ed00080, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
21d799b5
NC
22477 cCE("wrorh", e700040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22478 cCE("wrorhg", e700148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22479 cCE("wrorw", eb00040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22480 cCE("wrorwg", eb00148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22481 cCE("wrord", ef00040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22482 cCE("wrordg", ef00148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22483 cCE("wsadb", e000120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22484 cCE("wsadbz", e100120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22485 cCE("wsadh", e400120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22486 cCE("wsadhz", e500120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22487 cCE("wshufh", e0001e0, 3, (RIWR, RIWR, I255), iwmmxt_wshufh),
22488 cCE("wsllh", e500040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22489 cCE("wsllhg", e500148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22490 cCE("wsllw", e900040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22491 cCE("wsllwg", e900148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22492 cCE("wslld", ed00040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22493 cCE("wslldg", ed00148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22494 cCE("wsrah", e400040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22495 cCE("wsrahg", e400148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22496 cCE("wsraw", e800040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22497 cCE("wsrawg", e800148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22498 cCE("wsrad", ec00040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22499 cCE("wsradg", ec00148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22500 cCE("wsrlh", e600040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22501 cCE("wsrlhg", e600148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22502 cCE("wsrlw", ea00040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22503 cCE("wsrlwg", ea00148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22504 cCE("wsrld", ee00040, 3, (RIWR, RIWR, RIWR_I32z),iwmmxt_wrwrwr_or_imm5),
22505 cCE("wsrldg", ee00148, 3, (RIWR, RIWR, RIWG), rd_rn_rm),
22506 cCE("wstrb", c000000, 2, (RIWR, ADDR), iwmmxt_wldstbh),
22507 cCE("wstrh", c400000, 2, (RIWR, ADDR), iwmmxt_wldstbh),
22508 cCE("wstrw", c000100, 2, (RIWR_RIWC, ADDR), iwmmxt_wldstw),
22509 cCE("wstrd", c400100, 2, (RIWR, ADDR), iwmmxt_wldstd),
22510 cCE("wsubbss", e3001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22511 cCE("wsubb", e0001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22512 cCE("wsubbus", e1001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22513 cCE("wsubhss", e7001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22514 cCE("wsubh", e4001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22515 cCE("wsubhus", e5001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22516 cCE("wsubwss", eb001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22517 cCE("wsubw", e8001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22518 cCE("wsubwus", e9001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22519 cCE("wunpckehub",e0000c0, 2, (RIWR, RIWR), rd_rn),
22520 cCE("wunpckehuh",e4000c0, 2, (RIWR, RIWR), rd_rn),
22521 cCE("wunpckehuw",e8000c0, 2, (RIWR, RIWR), rd_rn),
22522 cCE("wunpckehsb",e2000c0, 2, (RIWR, RIWR), rd_rn),
22523 cCE("wunpckehsh",e6000c0, 2, (RIWR, RIWR), rd_rn),
22524 cCE("wunpckehsw",ea000c0, 2, (RIWR, RIWR), rd_rn),
22525 cCE("wunpckihb", e1000c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22526 cCE("wunpckihh", e5000c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22527 cCE("wunpckihw", e9000c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22528 cCE("wunpckelub",e0000e0, 2, (RIWR, RIWR), rd_rn),
22529 cCE("wunpckeluh",e4000e0, 2, (RIWR, RIWR), rd_rn),
22530 cCE("wunpckeluw",e8000e0, 2, (RIWR, RIWR), rd_rn),
22531 cCE("wunpckelsb",e2000e0, 2, (RIWR, RIWR), rd_rn),
22532 cCE("wunpckelsh",e6000e0, 2, (RIWR, RIWR), rd_rn),
22533 cCE("wunpckelsw",ea000e0, 2, (RIWR, RIWR), rd_rn),
22534 cCE("wunpckilb", e1000e0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22535 cCE("wunpckilh", e5000e0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22536 cCE("wunpckilw", e9000e0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22537 cCE("wxor", e100000, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22538 cCE("wzero", e300000, 1, (RIWR), iwmmxt_wzero),
c19d1205 22539
c921be7d
NC
22540#undef ARM_VARIANT
22541#define ARM_VARIANT & arm_cext_iwmmxt2 /* Intel Wireless MMX technology, version 2. */
22542
21d799b5
NC
22543 cCE("torvscb", e12f190, 1, (RR), iwmmxt_tandorc),
22544 cCE("torvsch", e52f190, 1, (RR), iwmmxt_tandorc),
22545 cCE("torvscw", e92f190, 1, (RR), iwmmxt_tandorc),
22546 cCE("wabsb", e2001c0, 2, (RIWR, RIWR), rd_rn),
22547 cCE("wabsh", e6001c0, 2, (RIWR, RIWR), rd_rn),
22548 cCE("wabsw", ea001c0, 2, (RIWR, RIWR), rd_rn),
22549 cCE("wabsdiffb", e1001c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22550 cCE("wabsdiffh", e5001c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22551 cCE("wabsdiffw", e9001c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22552 cCE("waddbhusl", e2001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22553 cCE("waddbhusm", e6001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22554 cCE("waddhc", e600180, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22555 cCE("waddwc", ea00180, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22556 cCE("waddsubhx", ea001a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22557 cCE("wavg4", e400000, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22558 cCE("wavg4r", e500000, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22559 cCE("wmaddsn", ee00100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22560 cCE("wmaddsx", eb00100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22561 cCE("wmaddun", ec00100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22562 cCE("wmaddux", e900100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22563 cCE("wmerge", e000080, 4, (RIWR, RIWR, RIWR, I7), iwmmxt_wmerge),
22564 cCE("wmiabb", e0000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22565 cCE("wmiabt", e1000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22566 cCE("wmiatb", e2000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22567 cCE("wmiatt", e3000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22568 cCE("wmiabbn", e4000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22569 cCE("wmiabtn", e5000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22570 cCE("wmiatbn", e6000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22571 cCE("wmiattn", e7000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22572 cCE("wmiawbb", e800120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22573 cCE("wmiawbt", e900120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22574 cCE("wmiawtb", ea00120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22575 cCE("wmiawtt", eb00120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22576 cCE("wmiawbbn", ec00120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22577 cCE("wmiawbtn", ed00120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22578 cCE("wmiawtbn", ee00120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22579 cCE("wmiawttn", ef00120, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22580 cCE("wmulsmr", ef00100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22581 cCE("wmulumr", ed00100, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22582 cCE("wmulwumr", ec000c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22583 cCE("wmulwsmr", ee000c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22584 cCE("wmulwum", ed000c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22585 cCE("wmulwsm", ef000c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22586 cCE("wmulwl", eb000c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22587 cCE("wqmiabb", e8000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22588 cCE("wqmiabt", e9000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22589 cCE("wqmiatb", ea000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22590 cCE("wqmiatt", eb000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22591 cCE("wqmiabbn", ec000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22592 cCE("wqmiabtn", ed000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22593 cCE("wqmiatbn", ee000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22594 cCE("wqmiattn", ef000a0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22595 cCE("wqmulm", e100080, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22596 cCE("wqmulmr", e300080, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22597 cCE("wqmulwm", ec000e0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22598 cCE("wqmulwmr", ee000e0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
22599 cCE("wsubaddhx", ed001c0, 3, (RIWR, RIWR, RIWR), rd_rn_rm),
2d447fca 22600
c921be7d
NC
22601#undef ARM_VARIANT
22602#define ARM_VARIANT & arm_cext_maverick /* Cirrus Maverick instructions. */
22603
21d799b5
NC
22604 cCE("cfldrs", c100400, 2, (RMF, ADDRGLDC), rd_cpaddr),
22605 cCE("cfldrd", c500400, 2, (RMD, ADDRGLDC), rd_cpaddr),
22606 cCE("cfldr32", c100500, 2, (RMFX, ADDRGLDC), rd_cpaddr),
22607 cCE("cfldr64", c500500, 2, (RMDX, ADDRGLDC), rd_cpaddr),
22608 cCE("cfstrs", c000400, 2, (RMF, ADDRGLDC), rd_cpaddr),
22609 cCE("cfstrd", c400400, 2, (RMD, ADDRGLDC), rd_cpaddr),
22610 cCE("cfstr32", c000500, 2, (RMFX, ADDRGLDC), rd_cpaddr),
22611 cCE("cfstr64", c400500, 2, (RMDX, ADDRGLDC), rd_cpaddr),
22612 cCE("cfmvsr", e000450, 2, (RMF, RR), rn_rd),
22613 cCE("cfmvrs", e100450, 2, (RR, RMF), rd_rn),
22614 cCE("cfmvdlr", e000410, 2, (RMD, RR), rn_rd),
22615 cCE("cfmvrdl", e100410, 2, (RR, RMD), rd_rn),
22616 cCE("cfmvdhr", e000430, 2, (RMD, RR), rn_rd),
22617 cCE("cfmvrdh", e100430, 2, (RR, RMD), rd_rn),
74db7efb
NC
22618 cCE("cfmv64lr",e000510, 2, (RMDX, RR), rn_rd),
22619 cCE("cfmvr64l",e100510, 2, (RR, RMDX), rd_rn),
22620 cCE("cfmv64hr",e000530, 2, (RMDX, RR), rn_rd),
22621 cCE("cfmvr64h",e100530, 2, (RR, RMDX), rd_rn),
22622 cCE("cfmval32",e200440, 2, (RMAX, RMFX), rd_rn),
22623 cCE("cfmv32al",e100440, 2, (RMFX, RMAX), rd_rn),
22624 cCE("cfmvam32",e200460, 2, (RMAX, RMFX), rd_rn),
22625 cCE("cfmv32am",e100460, 2, (RMFX, RMAX), rd_rn),
22626 cCE("cfmvah32",e200480, 2, (RMAX, RMFX), rd_rn),
22627 cCE("cfmv32ah",e100480, 2, (RMFX, RMAX), rd_rn),
21d799b5
NC
22628 cCE("cfmva32", e2004a0, 2, (RMAX, RMFX), rd_rn),
22629 cCE("cfmv32a", e1004a0, 2, (RMFX, RMAX), rd_rn),
22630 cCE("cfmva64", e2004c0, 2, (RMAX, RMDX), rd_rn),
22631 cCE("cfmv64a", e1004c0, 2, (RMDX, RMAX), rd_rn),
74db7efb
NC
22632 cCE("cfmvsc32",e2004e0, 2, (RMDS, RMDX), mav_dspsc),
22633 cCE("cfmv32sc",e1004e0, 2, (RMDX, RMDS), rd),
21d799b5
NC
22634 cCE("cfcpys", e000400, 2, (RMF, RMF), rd_rn),
22635 cCE("cfcpyd", e000420, 2, (RMD, RMD), rd_rn),
22636 cCE("cfcvtsd", e000460, 2, (RMD, RMF), rd_rn),
22637 cCE("cfcvtds", e000440, 2, (RMF, RMD), rd_rn),
74db7efb
NC
22638 cCE("cfcvt32s",e000480, 2, (RMF, RMFX), rd_rn),
22639 cCE("cfcvt32d",e0004a0, 2, (RMD, RMFX), rd_rn),
22640 cCE("cfcvt64s",e0004c0, 2, (RMF, RMDX), rd_rn),
22641 cCE("cfcvt64d",e0004e0, 2, (RMD, RMDX), rd_rn),
22642 cCE("cfcvts32",e100580, 2, (RMFX, RMF), rd_rn),
22643 cCE("cfcvtd32",e1005a0, 2, (RMFX, RMD), rd_rn),
21d799b5
NC
22644 cCE("cftruncs32",e1005c0, 2, (RMFX, RMF), rd_rn),
22645 cCE("cftruncd32",e1005e0, 2, (RMFX, RMD), rd_rn),
74db7efb
NC
22646 cCE("cfrshl32",e000550, 3, (RMFX, RMFX, RR), mav_triple),
22647 cCE("cfrshl64",e000570, 3, (RMDX, RMDX, RR), mav_triple),
21d799b5
NC
22648 cCE("cfsh32", e000500, 3, (RMFX, RMFX, I63s), mav_shift),
22649 cCE("cfsh64", e200500, 3, (RMDX, RMDX, I63s), mav_shift),
22650 cCE("cfcmps", e100490, 3, (RR, RMF, RMF), rd_rn_rm),
22651 cCE("cfcmpd", e1004b0, 3, (RR, RMD, RMD), rd_rn_rm),
22652 cCE("cfcmp32", e100590, 3, (RR, RMFX, RMFX), rd_rn_rm),
22653 cCE("cfcmp64", e1005b0, 3, (RR, RMDX, RMDX), rd_rn_rm),
22654 cCE("cfabss", e300400, 2, (RMF, RMF), rd_rn),
22655 cCE("cfabsd", e300420, 2, (RMD, RMD), rd_rn),
22656 cCE("cfnegs", e300440, 2, (RMF, RMF), rd_rn),
22657 cCE("cfnegd", e300460, 2, (RMD, RMD), rd_rn),
22658 cCE("cfadds", e300480, 3, (RMF, RMF, RMF), rd_rn_rm),
22659 cCE("cfaddd", e3004a0, 3, (RMD, RMD, RMD), rd_rn_rm),
22660 cCE("cfsubs", e3004c0, 3, (RMF, RMF, RMF), rd_rn_rm),
22661 cCE("cfsubd", e3004e0, 3, (RMD, RMD, RMD), rd_rn_rm),
22662 cCE("cfmuls", e100400, 3, (RMF, RMF, RMF), rd_rn_rm),
22663 cCE("cfmuld", e100420, 3, (RMD, RMD, RMD), rd_rn_rm),
22664 cCE("cfabs32", e300500, 2, (RMFX, RMFX), rd_rn),
22665 cCE("cfabs64", e300520, 2, (RMDX, RMDX), rd_rn),
22666 cCE("cfneg32", e300540, 2, (RMFX, RMFX), rd_rn),
22667 cCE("cfneg64", e300560, 2, (RMDX, RMDX), rd_rn),
22668 cCE("cfadd32", e300580, 3, (RMFX, RMFX, RMFX), rd_rn_rm),
22669 cCE("cfadd64", e3005a0, 3, (RMDX, RMDX, RMDX), rd_rn_rm),
22670 cCE("cfsub32", e3005c0, 3, (RMFX, RMFX, RMFX), rd_rn_rm),
22671 cCE("cfsub64", e3005e0, 3, (RMDX, RMDX, RMDX), rd_rn_rm),
22672 cCE("cfmul32", e100500, 3, (RMFX, RMFX, RMFX), rd_rn_rm),
22673 cCE("cfmul64", e100520, 3, (RMDX, RMDX, RMDX), rd_rn_rm),
22674 cCE("cfmac32", e100540, 3, (RMFX, RMFX, RMFX), rd_rn_rm),
22675 cCE("cfmsc32", e100560, 3, (RMFX, RMFX, RMFX), rd_rn_rm),
74db7efb
NC
22676 cCE("cfmadd32",e000600, 4, (RMAX, RMFX, RMFX, RMFX), mav_quad),
22677 cCE("cfmsub32",e100600, 4, (RMAX, RMFX, RMFX, RMFX), mav_quad),
21d799b5
NC
22678 cCE("cfmadda32", e200600, 4, (RMAX, RMAX, RMFX, RMFX), mav_quad),
22679 cCE("cfmsuba32", e300600, 4, (RMAX, RMAX, RMFX, RMFX), mav_quad),
4ed7ed8d 22680
7fadb25d
SD
22681 /* ARMv8.5-A instructions. */
22682#undef ARM_VARIANT
22683#define ARM_VARIANT & arm_ext_sb
22684#undef THUMB_VARIANT
22685#define THUMB_VARIANT & arm_ext_sb
22686 TUF("sb", 57ff070, f3bf8f70, 0, (), noargs, noargs),
22687
dad0c3bf
SD
22688#undef ARM_VARIANT
22689#define ARM_VARIANT & arm_ext_predres
22690#undef THUMB_VARIANT
22691#define THUMB_VARIANT & arm_ext_predres
22692 CE("cfprctx", e070f93, 1, (RRnpc), rd),
22693 CE("dvprctx", e070fb3, 1, (RRnpc), rd),
22694 CE("cpprctx", e070ff3, 1, (RRnpc), rd),
22695
16a1fa25 22696 /* ARMv8-M instructions. */
4ed7ed8d
TP
22697#undef ARM_VARIANT
22698#define ARM_VARIANT NULL
22699#undef THUMB_VARIANT
22700#define THUMB_VARIANT & arm_ext_v8m
cf3cf39d
TP
22701 ToU("sg", e97fe97f, 0, (), noargs),
22702 ToC("blxns", 4784, 1, (RRnpc), t_blx),
22703 ToC("bxns", 4704, 1, (RRnpc), t_bx),
22704 ToC("tt", e840f000, 2, (RRnpc, RRnpc), tt),
22705 ToC("ttt", e840f040, 2, (RRnpc, RRnpc), tt),
22706 ToC("tta", e840f080, 2, (RRnpc, RRnpc), tt),
22707 ToC("ttat", e840f0c0, 2, (RRnpc, RRnpc), tt),
16a1fa25
TP
22708
22709 /* FP for ARMv8-M Mainline. Enabled for ARMv8-M Mainline because the
22710 instructions behave as nop if no VFP is present. */
22711#undef THUMB_VARIANT
22712#define THUMB_VARIANT & arm_ext_v8m_main
cf3cf39d
TP
22713 ToC("vlldm", ec300a00, 1, (RRnpc), rn),
22714 ToC("vlstm", ec200a00, 1, (RRnpc), rn),
4389b29a
AV
22715
22716 /* Armv8.1-M Mainline instructions. */
22717#undef THUMB_VARIANT
22718#define THUMB_VARIANT & arm_ext_v8_1m_main
22719 toC("bf", _bf, 2, (EXPs, EXPs), t_branch_future),
f6b2b12d 22720 toU("bfcsel", _bfcsel, 4, (EXPs, EXPs, EXPs, COND), t_branch_future),
f1c7f421 22721 toC("bfx", _bfx, 2, (EXPs, RRnpcsp), t_branch_future),
65d1bc05 22722 toC("bfl", _bfl, 2, (EXPs, EXPs), t_branch_future),
f1c7f421 22723 toC("bflx", _bflx, 2, (EXPs, RRnpcsp), t_branch_future),
60f993ce
AV
22724
22725 toU("dls", _dls, 2, (LR, RRnpcsp), t_loloop),
22726 toU("wls", _wls, 3, (LR, RRnpcsp, EXP), t_loloop),
22727 toU("le", _le, 2, (oLR, EXP), t_loloop),
4b5a202f 22728
efd6b359 22729 ToC("clrm", e89f0000, 1, (CLRMLST), t_clrm),
5ee91343
AV
22730 ToC("vscclrm", ec9f0a00, 1, (VRSDVLST), t_vscclrm),
22731
22732#undef THUMB_VARIANT
22733#define THUMB_VARIANT & mve_ext
22734 ToC("vpst", fe710f4d, 0, (), mve_vpt),
22735 ToC("vpstt", fe318f4d, 0, (), mve_vpt),
22736 ToC("vpste", fe718f4d, 0, (), mve_vpt),
22737 ToC("vpsttt", fe314f4d, 0, (), mve_vpt),
22738 ToC("vpstte", fe31cf4d, 0, (), mve_vpt),
22739 ToC("vpstet", fe71cf4d, 0, (), mve_vpt),
22740 ToC("vpstee", fe714f4d, 0, (), mve_vpt),
22741 ToC("vpstttt", fe312f4d, 0, (), mve_vpt),
22742 ToC("vpsttte", fe316f4d, 0, (), mve_vpt),
22743 ToC("vpsttet", fe31ef4d, 0, (), mve_vpt),
22744 ToC("vpsttee", fe31af4d, 0, (), mve_vpt),
22745 ToC("vpstett", fe71af4d, 0, (), mve_vpt),
22746 ToC("vpstete", fe71ef4d, 0, (), mve_vpt),
22747 ToC("vpsteet", fe716f4d, 0, (), mve_vpt),
22748 ToC("vpsteee", fe712f4d, 0, (), mve_vpt),
22749
a302e574
AV
22750 /* MVE and MVE FP only. */
22751 mCEF(vabav, _vabav, 3, (RRnpcsp, RMQ, RMQ), mve_vabav),
22752 mCEF(vmladav, _vmladav, 3, (RRe, RMQ, RMQ), mve_vmladav),
22753 mCEF(vmladava, _vmladava, 3, (RRe, RMQ, RMQ), mve_vmladav),
22754 mCEF(vmladavx, _vmladavx, 3, (RRe, RMQ, RMQ), mve_vmladav),
22755 mCEF(vmladavax, _vmladavax, 3, (RRe, RMQ, RMQ), mve_vmladav),
22756 mCEF(vmlav, _vmladav, 3, (RRe, RMQ, RMQ), mve_vmladav),
22757 mCEF(vmlava, _vmladava, 3, (RRe, RMQ, RMQ), mve_vmladav),
22758 mCEF(vmlsdav, _vmlsdav, 3, (RRe, RMQ, RMQ), mve_vmladav),
22759 mCEF(vmlsdava, _vmlsdava, 3, (RRe, RMQ, RMQ), mve_vmladav),
22760 mCEF(vmlsdavx, _vmlsdavx, 3, (RRe, RMQ, RMQ), mve_vmladav),
22761 mCEF(vmlsdavax, _vmlsdavax, 3, (RRe, RMQ, RMQ), mve_vmladav),
22762
5ee91343
AV
22763#undef ARM_VARIANT
22764#define ARM_VARIANT & fpu_vfp_ext_v1xd
22765#undef THUMB_VARIANT
22766#define THUMB_VARIANT & arm_ext_v6t2
22767
22768 mnCEF(vadd, _vadd, 3, (RNSDQMQ, oRNSDQMQ, RNSDQMQR), neon_addsub_if_i),
22769 mnCEF(vsub, _vsub, 3, (RNSDQMQ, oRNSDQMQ, RNSDQMQR), neon_addsub_if_i),
22770
485dee97
AV
22771 MNCEF(vabs, 1b10300, 2, (RNSDQMQ, RNSDQMQ), neon_abs_neg),
22772 MNCEF(vneg, 1b10380, 2, (RNSDQMQ, RNSDQMQ), neon_abs_neg),
22773
5ee91343
AV
22774#undef ARM_VARIANT
22775#define ARM_VARIANT & fpu_neon_ext_v1
22776 mnUF(vabd, _vabd, 3, (RNDQMQ, oRNDQMQ, RNDQMQ), neon_dyadic_if_su),
22777 mnUF(vabdl, _vabdl, 3, (RNQMQ, RNDMQ, RNDMQ), neon_dyadic_long),
22778 mnUF(vaddl, _vaddl, 3, (RNQMQ, RNDMQ, RNDMQR), neon_dyadic_long),
22779 mnUF(vsubl, _vsubl, 3, (RNQMQ, RNDMQ, RNDMQR), neon_dyadic_long),
c19d1205
ZW
22780};
22781#undef ARM_VARIANT
22782#undef THUMB_VARIANT
22783#undef TCE
c19d1205
ZW
22784#undef TUE
22785#undef TUF
22786#undef TCC
8f06b2d8 22787#undef cCE
e3cb604e
PB
22788#undef cCL
22789#undef C3E
4389b29a 22790#undef C3
c19d1205
ZW
22791#undef CE
22792#undef CM
4389b29a 22793#undef CL
c19d1205
ZW
22794#undef UE
22795#undef UF
22796#undef UT
5287ad62
JB
22797#undef NUF
22798#undef nUF
22799#undef NCE
22800#undef nCE
c19d1205
ZW
22801#undef OPS0
22802#undef OPS1
22803#undef OPS2
22804#undef OPS3
22805#undef OPS4
22806#undef OPS5
22807#undef OPS6
22808#undef do_0
4389b29a
AV
22809#undef ToC
22810#undef toC
22811#undef ToU
f6b2b12d 22812#undef toU
c19d1205
ZW
22813\f
22814/* MD interface: bits in the object file. */
bfae80f2 22815
c19d1205
ZW
22816/* Turn an integer of n bytes (in val) into a stream of bytes appropriate
22817 for use in the a.out file, and stores them in the array pointed to by buf.
22818 This knows about the endian-ness of the target machine and does
22819 THE RIGHT THING, whatever it is. Possible values for n are 1 (byte)
22820 2 (short) and 4 (long) Floating numbers are put out as a series of
22821 LITTLENUMS (shorts, here at least). */
b99bd4ef 22822
c19d1205
ZW
22823void
22824md_number_to_chars (char * buf, valueT val, int n)
22825{
22826 if (target_big_endian)
22827 number_to_chars_bigendian (buf, val, n);
22828 else
22829 number_to_chars_littleendian (buf, val, n);
bfae80f2
RE
22830}
22831
c19d1205
ZW
22832static valueT
22833md_chars_to_number (char * buf, int n)
bfae80f2 22834{
c19d1205
ZW
22835 valueT result = 0;
22836 unsigned char * where = (unsigned char *) buf;
bfae80f2 22837
c19d1205 22838 if (target_big_endian)
b99bd4ef 22839 {
c19d1205
ZW
22840 while (n--)
22841 {
22842 result <<= 8;
22843 result |= (*where++ & 255);
22844 }
b99bd4ef 22845 }
c19d1205 22846 else
b99bd4ef 22847 {
c19d1205
ZW
22848 while (n--)
22849 {
22850 result <<= 8;
22851 result |= (where[n] & 255);
22852 }
bfae80f2 22853 }
b99bd4ef 22854
c19d1205 22855 return result;
bfae80f2 22856}
b99bd4ef 22857
c19d1205 22858/* MD interface: Sections. */
b99bd4ef 22859
fa94de6b
RM
22860/* Calculate the maximum variable size (i.e., excluding fr_fix)
22861 that an rs_machine_dependent frag may reach. */
22862
22863unsigned int
22864arm_frag_max_var (fragS *fragp)
22865{
22866 /* We only use rs_machine_dependent for variable-size Thumb instructions,
22867 which are either THUMB_SIZE (2) or INSN_SIZE (4).
22868
22869 Note that we generate relaxable instructions even for cases that don't
22870 really need it, like an immediate that's a trivial constant. So we're
22871 overestimating the instruction size for some of those cases. Rather
22872 than putting more intelligence here, it would probably be better to
22873 avoid generating a relaxation frag in the first place when it can be
22874 determined up front that a short instruction will suffice. */
22875
22876 gas_assert (fragp->fr_type == rs_machine_dependent);
22877 return INSN_SIZE;
22878}
22879
0110f2b8
PB
22880/* Estimate the size of a frag before relaxing. Assume everything fits in
22881 2 bytes. */
22882
c19d1205 22883int
0110f2b8 22884md_estimate_size_before_relax (fragS * fragp,
c19d1205
ZW
22885 segT segtype ATTRIBUTE_UNUSED)
22886{
0110f2b8
PB
22887 fragp->fr_var = 2;
22888 return 2;
22889}
22890
22891/* Convert a machine dependent frag. */
22892
22893void
22894md_convert_frag (bfd *abfd, segT asec ATTRIBUTE_UNUSED, fragS *fragp)
22895{
22896 unsigned long insn;
22897 unsigned long old_op;
22898 char *buf;
22899 expressionS exp;
22900 fixS *fixp;
22901 int reloc_type;
22902 int pc_rel;
22903 int opcode;
22904
22905 buf = fragp->fr_literal + fragp->fr_fix;
22906
22907 old_op = bfd_get_16(abfd, buf);
5f4273c7
NC
22908 if (fragp->fr_symbol)
22909 {
0110f2b8
PB
22910 exp.X_op = O_symbol;
22911 exp.X_add_symbol = fragp->fr_symbol;
5f4273c7
NC
22912 }
22913 else
22914 {
0110f2b8 22915 exp.X_op = O_constant;
5f4273c7 22916 }
0110f2b8
PB
22917 exp.X_add_number = fragp->fr_offset;
22918 opcode = fragp->fr_subtype;
22919 switch (opcode)
22920 {
22921 case T_MNEM_ldr_pc:
22922 case T_MNEM_ldr_pc2:
22923 case T_MNEM_ldr_sp:
22924 case T_MNEM_str_sp:
22925 case T_MNEM_ldr:
22926 case T_MNEM_ldrb:
22927 case T_MNEM_ldrh:
22928 case T_MNEM_str:
22929 case T_MNEM_strb:
22930 case T_MNEM_strh:
22931 if (fragp->fr_var == 4)
22932 {
5f4273c7 22933 insn = THUMB_OP32 (opcode);
0110f2b8
PB
22934 if ((old_op >> 12) == 4 || (old_op >> 12) == 9)
22935 {
22936 insn |= (old_op & 0x700) << 4;
22937 }
22938 else
22939 {
22940 insn |= (old_op & 7) << 12;
22941 insn |= (old_op & 0x38) << 13;
22942 }
22943 insn |= 0x00000c00;
22944 put_thumb32_insn (buf, insn);
22945 reloc_type = BFD_RELOC_ARM_T32_OFFSET_IMM;
22946 }
22947 else
22948 {
22949 reloc_type = BFD_RELOC_ARM_THUMB_OFFSET;
22950 }
22951 pc_rel = (opcode == T_MNEM_ldr_pc2);
22952 break;
22953 case T_MNEM_adr:
22954 if (fragp->fr_var == 4)
22955 {
22956 insn = THUMB_OP32 (opcode);
22957 insn |= (old_op & 0xf0) << 4;
22958 put_thumb32_insn (buf, insn);
22959 reloc_type = BFD_RELOC_ARM_T32_ADD_PC12;
22960 }
22961 else
22962 {
22963 reloc_type = BFD_RELOC_ARM_THUMB_ADD;
22964 exp.X_add_number -= 4;
22965 }
22966 pc_rel = 1;
22967 break;
22968 case T_MNEM_mov:
22969 case T_MNEM_movs:
22970 case T_MNEM_cmp:
22971 case T_MNEM_cmn:
22972 if (fragp->fr_var == 4)
22973 {
22974 int r0off = (opcode == T_MNEM_mov
22975 || opcode == T_MNEM_movs) ? 0 : 8;
22976 insn = THUMB_OP32 (opcode);
22977 insn = (insn & 0xe1ffffff) | 0x10000000;
22978 insn |= (old_op & 0x700) << r0off;
22979 put_thumb32_insn (buf, insn);
22980 reloc_type = BFD_RELOC_ARM_T32_IMMEDIATE;
22981 }
22982 else
22983 {
22984 reloc_type = BFD_RELOC_ARM_THUMB_IMM;
22985 }
22986 pc_rel = 0;
22987 break;
22988 case T_MNEM_b:
22989 if (fragp->fr_var == 4)
22990 {
22991 insn = THUMB_OP32(opcode);
22992 put_thumb32_insn (buf, insn);
22993 reloc_type = BFD_RELOC_THUMB_PCREL_BRANCH25;
22994 }
22995 else
22996 reloc_type = BFD_RELOC_THUMB_PCREL_BRANCH12;
22997 pc_rel = 1;
22998 break;
22999 case T_MNEM_bcond:
23000 if (fragp->fr_var == 4)
23001 {
23002 insn = THUMB_OP32(opcode);
23003 insn |= (old_op & 0xf00) << 14;
23004 put_thumb32_insn (buf, insn);
23005 reloc_type = BFD_RELOC_THUMB_PCREL_BRANCH20;
23006 }
23007 else
23008 reloc_type = BFD_RELOC_THUMB_PCREL_BRANCH9;
23009 pc_rel = 1;
23010 break;
23011 case T_MNEM_add_sp:
23012 case T_MNEM_add_pc:
23013 case T_MNEM_inc_sp:
23014 case T_MNEM_dec_sp:
23015 if (fragp->fr_var == 4)
23016 {
23017 /* ??? Choose between add and addw. */
23018 insn = THUMB_OP32 (opcode);
23019 insn |= (old_op & 0xf0) << 4;
23020 put_thumb32_insn (buf, insn);
16805f35
PB
23021 if (opcode == T_MNEM_add_pc)
23022 reloc_type = BFD_RELOC_ARM_T32_IMM12;
23023 else
23024 reloc_type = BFD_RELOC_ARM_T32_ADD_IMM;
0110f2b8
PB
23025 }
23026 else
23027 reloc_type = BFD_RELOC_ARM_THUMB_ADD;
23028 pc_rel = 0;
23029 break;
23030
23031 case T_MNEM_addi:
23032 case T_MNEM_addis:
23033 case T_MNEM_subi:
23034 case T_MNEM_subis:
23035 if (fragp->fr_var == 4)
23036 {
23037 insn = THUMB_OP32 (opcode);
23038 insn |= (old_op & 0xf0) << 4;
23039 insn |= (old_op & 0xf) << 16;
23040 put_thumb32_insn (buf, insn);
16805f35
PB
23041 if (insn & (1 << 20))
23042 reloc_type = BFD_RELOC_ARM_T32_ADD_IMM;
23043 else
23044 reloc_type = BFD_RELOC_ARM_T32_IMMEDIATE;
0110f2b8
PB
23045 }
23046 else
23047 reloc_type = BFD_RELOC_ARM_THUMB_ADD;
23048 pc_rel = 0;
23049 break;
23050 default:
5f4273c7 23051 abort ();
0110f2b8
PB
23052 }
23053 fixp = fix_new_exp (fragp, fragp->fr_fix, fragp->fr_var, &exp, pc_rel,
21d799b5 23054 (enum bfd_reloc_code_real) reloc_type);
0110f2b8
PB
23055 fixp->fx_file = fragp->fr_file;
23056 fixp->fx_line = fragp->fr_line;
23057 fragp->fr_fix += fragp->fr_var;
3cfdb781
TG
23058
23059 /* Set whether we use thumb-2 ISA based on final relaxation results. */
23060 if (thumb_mode && fragp->fr_var == 4 && no_cpu_selected ()
23061 && !ARM_CPU_HAS_FEATURE (thumb_arch_used, arm_arch_t2))
23062 ARM_MERGE_FEATURE_SETS (arm_arch_used, thumb_arch_used, arm_ext_v6t2);
0110f2b8
PB
23063}
23064
23065/* Return the size of a relaxable immediate operand instruction.
23066 SHIFT and SIZE specify the form of the allowable immediate. */
23067static int
23068relax_immediate (fragS *fragp, int size, int shift)
23069{
23070 offsetT offset;
23071 offsetT mask;
23072 offsetT low;
23073
23074 /* ??? Should be able to do better than this. */
23075 if (fragp->fr_symbol)
23076 return 4;
23077
23078 low = (1 << shift) - 1;
23079 mask = (1 << (shift + size)) - (1 << shift);
23080 offset = fragp->fr_offset;
23081 /* Force misaligned offsets to 32-bit variant. */
23082 if (offset & low)
5e77afaa 23083 return 4;
0110f2b8
PB
23084 if (offset & ~mask)
23085 return 4;
23086 return 2;
23087}
23088
5e77afaa
PB
23089/* Get the address of a symbol during relaxation. */
23090static addressT
5f4273c7 23091relaxed_symbol_addr (fragS *fragp, long stretch)
5e77afaa
PB
23092{
23093 fragS *sym_frag;
23094 addressT addr;
23095 symbolS *sym;
23096
23097 sym = fragp->fr_symbol;
23098 sym_frag = symbol_get_frag (sym);
23099 know (S_GET_SEGMENT (sym) != absolute_section
23100 || sym_frag == &zero_address_frag);
23101 addr = S_GET_VALUE (sym) + fragp->fr_offset;
23102
23103 /* If frag has yet to be reached on this pass, assume it will
23104 move by STRETCH just as we did. If this is not so, it will
23105 be because some frag between grows, and that will force
23106 another pass. */
23107
23108 if (stretch != 0
23109 && sym_frag->relax_marker != fragp->relax_marker)
4396b686
PB
23110 {
23111 fragS *f;
23112
23113 /* Adjust stretch for any alignment frag. Note that if have
23114 been expanding the earlier code, the symbol may be
23115 defined in what appears to be an earlier frag. FIXME:
23116 This doesn't handle the fr_subtype field, which specifies
23117 a maximum number of bytes to skip when doing an
23118 alignment. */
23119 for (f = fragp; f != NULL && f != sym_frag; f = f->fr_next)
23120 {
23121 if (f->fr_type == rs_align || f->fr_type == rs_align_code)
23122 {
23123 if (stretch < 0)
23124 stretch = - ((- stretch)
23125 & ~ ((1 << (int) f->fr_offset) - 1));
23126 else
23127 stretch &= ~ ((1 << (int) f->fr_offset) - 1);
23128 if (stretch == 0)
23129 break;
23130 }
23131 }
23132 if (f != NULL)
23133 addr += stretch;
23134 }
5e77afaa
PB
23135
23136 return addr;
23137}
23138
0110f2b8
PB
23139/* Return the size of a relaxable adr pseudo-instruction or PC-relative
23140 load. */
23141static int
5e77afaa 23142relax_adr (fragS *fragp, asection *sec, long stretch)
0110f2b8
PB
23143{
23144 addressT addr;
23145 offsetT val;
23146
23147 /* Assume worst case for symbols not known to be in the same section. */
974da60d
NC
23148 if (fragp->fr_symbol == NULL
23149 || !S_IS_DEFINED (fragp->fr_symbol)
77db8e2e
NC
23150 || sec != S_GET_SEGMENT (fragp->fr_symbol)
23151 || S_IS_WEAK (fragp->fr_symbol))
0110f2b8
PB
23152 return 4;
23153
5f4273c7 23154 val = relaxed_symbol_addr (fragp, stretch);
0110f2b8
PB
23155 addr = fragp->fr_address + fragp->fr_fix;
23156 addr = (addr + 4) & ~3;
5e77afaa 23157 /* Force misaligned targets to 32-bit variant. */
0110f2b8 23158 if (val & 3)
5e77afaa 23159 return 4;
0110f2b8
PB
23160 val -= addr;
23161 if (val < 0 || val > 1020)
23162 return 4;
23163 return 2;
23164}
23165
23166/* Return the size of a relaxable add/sub immediate instruction. */
23167static int
23168relax_addsub (fragS *fragp, asection *sec)
23169{
23170 char *buf;
23171 int op;
23172
23173 buf = fragp->fr_literal + fragp->fr_fix;
23174 op = bfd_get_16(sec->owner, buf);
23175 if ((op & 0xf) == ((op >> 4) & 0xf))
23176 return relax_immediate (fragp, 8, 0);
23177 else
23178 return relax_immediate (fragp, 3, 0);
23179}
23180
e83a675f
RE
23181/* Return TRUE iff the definition of symbol S could be pre-empted
23182 (overridden) at link or load time. */
23183static bfd_boolean
23184symbol_preemptible (symbolS *s)
23185{
23186 /* Weak symbols can always be pre-empted. */
23187 if (S_IS_WEAK (s))
23188 return TRUE;
23189
23190 /* Non-global symbols cannot be pre-empted. */
23191 if (! S_IS_EXTERNAL (s))
23192 return FALSE;
23193
23194#ifdef OBJ_ELF
23195 /* In ELF, a global symbol can be marked protected, or private. In that
23196 case it can't be pre-empted (other definitions in the same link unit
23197 would violate the ODR). */
23198 if (ELF_ST_VISIBILITY (S_GET_OTHER (s)) > STV_DEFAULT)
23199 return FALSE;
23200#endif
23201
23202 /* Other global symbols might be pre-empted. */
23203 return TRUE;
23204}
0110f2b8
PB
23205
23206/* Return the size of a relaxable branch instruction. BITS is the
23207 size of the offset field in the narrow instruction. */
23208
23209static int
5e77afaa 23210relax_branch (fragS *fragp, asection *sec, int bits, long stretch)
0110f2b8
PB
23211{
23212 addressT addr;
23213 offsetT val;
23214 offsetT limit;
23215
23216 /* Assume worst case for symbols not known to be in the same section. */
5f4273c7 23217 if (!S_IS_DEFINED (fragp->fr_symbol)
77db8e2e
NC
23218 || sec != S_GET_SEGMENT (fragp->fr_symbol)
23219 || S_IS_WEAK (fragp->fr_symbol))
0110f2b8
PB
23220 return 4;
23221
267bf995 23222#ifdef OBJ_ELF
e83a675f 23223 /* A branch to a function in ARM state will require interworking. */
267bf995
RR
23224 if (S_IS_DEFINED (fragp->fr_symbol)
23225 && ARM_IS_FUNC (fragp->fr_symbol))
23226 return 4;
e83a675f 23227#endif
0d9b4b55 23228
e83a675f 23229 if (symbol_preemptible (fragp->fr_symbol))
0d9b4b55 23230 return 4;
267bf995 23231
5f4273c7 23232 val = relaxed_symbol_addr (fragp, stretch);
0110f2b8
PB
23233 addr = fragp->fr_address + fragp->fr_fix + 4;
23234 val -= addr;
23235
23236 /* Offset is a signed value *2 */
23237 limit = 1 << bits;
23238 if (val >= limit || val < -limit)
23239 return 4;
23240 return 2;
23241}
23242
23243
23244/* Relax a machine dependent frag. This returns the amount by which
23245 the current size of the frag should change. */
23246
23247int
5e77afaa 23248arm_relax_frag (asection *sec, fragS *fragp, long stretch)
0110f2b8
PB
23249{
23250 int oldsize;
23251 int newsize;
23252
23253 oldsize = fragp->fr_var;
23254 switch (fragp->fr_subtype)
23255 {
23256 case T_MNEM_ldr_pc2:
5f4273c7 23257 newsize = relax_adr (fragp, sec, stretch);
0110f2b8
PB
23258 break;
23259 case T_MNEM_ldr_pc:
23260 case T_MNEM_ldr_sp:
23261 case T_MNEM_str_sp:
5f4273c7 23262 newsize = relax_immediate (fragp, 8, 2);
0110f2b8
PB
23263 break;
23264 case T_MNEM_ldr:
23265 case T_MNEM_str:
5f4273c7 23266 newsize = relax_immediate (fragp, 5, 2);
0110f2b8
PB
23267 break;
23268 case T_MNEM_ldrh:
23269 case T_MNEM_strh:
5f4273c7 23270 newsize = relax_immediate (fragp, 5, 1);
0110f2b8
PB
23271 break;
23272 case T_MNEM_ldrb:
23273 case T_MNEM_strb:
5f4273c7 23274 newsize = relax_immediate (fragp, 5, 0);
0110f2b8
PB
23275 break;
23276 case T_MNEM_adr:
5f4273c7 23277 newsize = relax_adr (fragp, sec, stretch);
0110f2b8
PB
23278 break;
23279 case T_MNEM_mov:
23280 case T_MNEM_movs:
23281 case T_MNEM_cmp:
23282 case T_MNEM_cmn:
5f4273c7 23283 newsize = relax_immediate (fragp, 8, 0);
0110f2b8
PB
23284 break;
23285 case T_MNEM_b:
5f4273c7 23286 newsize = relax_branch (fragp, sec, 11, stretch);
0110f2b8
PB
23287 break;
23288 case T_MNEM_bcond:
5f4273c7 23289 newsize = relax_branch (fragp, sec, 8, stretch);
0110f2b8
PB
23290 break;
23291 case T_MNEM_add_sp:
23292 case T_MNEM_add_pc:
23293 newsize = relax_immediate (fragp, 8, 2);
23294 break;
23295 case T_MNEM_inc_sp:
23296 case T_MNEM_dec_sp:
23297 newsize = relax_immediate (fragp, 7, 2);
23298 break;
23299 case T_MNEM_addi:
23300 case T_MNEM_addis:
23301 case T_MNEM_subi:
23302 case T_MNEM_subis:
23303 newsize = relax_addsub (fragp, sec);
23304 break;
23305 default:
5f4273c7 23306 abort ();
0110f2b8 23307 }
5e77afaa
PB
23308
23309 fragp->fr_var = newsize;
23310 /* Freeze wide instructions that are at or before the same location as
23311 in the previous pass. This avoids infinite loops.
5f4273c7
NC
23312 Don't freeze them unconditionally because targets may be artificially
23313 misaligned by the expansion of preceding frags. */
5e77afaa 23314 if (stretch <= 0 && newsize > 2)
0110f2b8 23315 {
0110f2b8 23316 md_convert_frag (sec->owner, sec, fragp);
5f4273c7 23317 frag_wane (fragp);
0110f2b8 23318 }
5e77afaa 23319
0110f2b8 23320 return newsize - oldsize;
c19d1205 23321}
b99bd4ef 23322
c19d1205 23323/* Round up a section size to the appropriate boundary. */
b99bd4ef 23324
c19d1205
ZW
23325valueT
23326md_section_align (segT segment ATTRIBUTE_UNUSED,
23327 valueT size)
23328{
6844c0cc 23329 return size;
bfae80f2 23330}
b99bd4ef 23331
c19d1205
ZW
23332/* This is called from HANDLE_ALIGN in write.c. Fill in the contents
23333 of an rs_align_code fragment. */
23334
23335void
23336arm_handle_align (fragS * fragP)
bfae80f2 23337{
d9235011 23338 static unsigned char const arm_noop[2][2][4] =
e7495e45
NS
23339 {
23340 { /* ARMv1 */
23341 {0x00, 0x00, 0xa0, 0xe1}, /* LE */
23342 {0xe1, 0xa0, 0x00, 0x00}, /* BE */
23343 },
23344 { /* ARMv6k */
23345 {0x00, 0xf0, 0x20, 0xe3}, /* LE */
23346 {0xe3, 0x20, 0xf0, 0x00}, /* BE */
23347 },
23348 };
d9235011 23349 static unsigned char const thumb_noop[2][2][2] =
e7495e45
NS
23350 {
23351 { /* Thumb-1 */
23352 {0xc0, 0x46}, /* LE */
23353 {0x46, 0xc0}, /* BE */
23354 },
23355 { /* Thumb-2 */
23356 {0x00, 0xbf}, /* LE */
23357 {0xbf, 0x00} /* BE */
23358 }
23359 };
d9235011 23360 static unsigned char const wide_thumb_noop[2][4] =
e7495e45
NS
23361 { /* Wide Thumb-2 */
23362 {0xaf, 0xf3, 0x00, 0x80}, /* LE */
23363 {0xf3, 0xaf, 0x80, 0x00}, /* BE */
23364 };
c921be7d 23365
e7495e45 23366 unsigned bytes, fix, noop_size;
c19d1205 23367 char * p;
d9235011
TS
23368 const unsigned char * noop;
23369 const unsigned char *narrow_noop = NULL;
cd000bff
DJ
23370#ifdef OBJ_ELF
23371 enum mstate state;
23372#endif
bfae80f2 23373
c19d1205 23374 if (fragP->fr_type != rs_align_code)
bfae80f2
RE
23375 return;
23376
c19d1205
ZW
23377 bytes = fragP->fr_next->fr_address - fragP->fr_address - fragP->fr_fix;
23378 p = fragP->fr_literal + fragP->fr_fix;
23379 fix = 0;
bfae80f2 23380
c19d1205
ZW
23381 if (bytes > MAX_MEM_FOR_RS_ALIGN_CODE)
23382 bytes &= MAX_MEM_FOR_RS_ALIGN_CODE;
bfae80f2 23383
cd000bff 23384 gas_assert ((fragP->tc_frag_data.thumb_mode & MODE_RECORDED) != 0);
8dc2430f 23385
cd000bff 23386 if (fragP->tc_frag_data.thumb_mode & (~ MODE_RECORDED))
a737bd4d 23387 {
7f78eb34
JW
23388 if (ARM_CPU_HAS_FEATURE (selected_cpu_name[0]
23389 ? selected_cpu : arm_arch_none, arm_ext_v6t2))
e7495e45
NS
23390 {
23391 narrow_noop = thumb_noop[1][target_big_endian];
23392 noop = wide_thumb_noop[target_big_endian];
23393 }
c19d1205 23394 else
e7495e45
NS
23395 noop = thumb_noop[0][target_big_endian];
23396 noop_size = 2;
cd000bff
DJ
23397#ifdef OBJ_ELF
23398 state = MAP_THUMB;
23399#endif
7ed4c4c5
NC
23400 }
23401 else
23402 {
7f78eb34
JW
23403 noop = arm_noop[ARM_CPU_HAS_FEATURE (selected_cpu_name[0]
23404 ? selected_cpu : arm_arch_none,
23405 arm_ext_v6k) != 0]
e7495e45
NS
23406 [target_big_endian];
23407 noop_size = 4;
cd000bff
DJ
23408#ifdef OBJ_ELF
23409 state = MAP_ARM;
23410#endif
7ed4c4c5 23411 }
c921be7d 23412
e7495e45 23413 fragP->fr_var = noop_size;
c921be7d 23414
c19d1205 23415 if (bytes & (noop_size - 1))
7ed4c4c5 23416 {
c19d1205 23417 fix = bytes & (noop_size - 1);
cd000bff
DJ
23418#ifdef OBJ_ELF
23419 insert_data_mapping_symbol (state, fragP->fr_fix, fragP, fix);
23420#endif
c19d1205
ZW
23421 memset (p, 0, fix);
23422 p += fix;
23423 bytes -= fix;
a737bd4d 23424 }
a737bd4d 23425
e7495e45
NS
23426 if (narrow_noop)
23427 {
23428 if (bytes & noop_size)
23429 {
23430 /* Insert a narrow noop. */
23431 memcpy (p, narrow_noop, noop_size);
23432 p += noop_size;
23433 bytes -= noop_size;
23434 fix += noop_size;
23435 }
23436
23437 /* Use wide noops for the remainder */
23438 noop_size = 4;
23439 }
23440
c19d1205 23441 while (bytes >= noop_size)
a737bd4d 23442 {
c19d1205
ZW
23443 memcpy (p, noop, noop_size);
23444 p += noop_size;
23445 bytes -= noop_size;
23446 fix += noop_size;
a737bd4d
NC
23447 }
23448
c19d1205 23449 fragP->fr_fix += fix;
a737bd4d
NC
23450}
23451
c19d1205
ZW
23452/* Called from md_do_align. Used to create an alignment
23453 frag in a code section. */
23454
23455void
23456arm_frag_align_code (int n, int max)
bfae80f2 23457{
c19d1205 23458 char * p;
7ed4c4c5 23459
c19d1205 23460 /* We assume that there will never be a requirement
6ec8e702 23461 to support alignments greater than MAX_MEM_FOR_RS_ALIGN_CODE bytes. */
c19d1205 23462 if (max > MAX_MEM_FOR_RS_ALIGN_CODE)
6ec8e702
NC
23463 {
23464 char err_msg[128];
23465
fa94de6b 23466 sprintf (err_msg,
477330fc
RM
23467 _("alignments greater than %d bytes not supported in .text sections."),
23468 MAX_MEM_FOR_RS_ALIGN_CODE + 1);
20203fb9 23469 as_fatal ("%s", err_msg);
6ec8e702 23470 }
bfae80f2 23471
c19d1205
ZW
23472 p = frag_var (rs_align_code,
23473 MAX_MEM_FOR_RS_ALIGN_CODE,
23474 1,
23475 (relax_substateT) max,
23476 (symbolS *) NULL,
23477 (offsetT) n,
23478 (char *) NULL);
23479 *p = 0;
23480}
bfae80f2 23481
8dc2430f
NC
23482/* Perform target specific initialisation of a frag.
23483 Note - despite the name this initialisation is not done when the frag
23484 is created, but only when its type is assigned. A frag can be created
23485 and used a long time before its type is set, so beware of assuming that
33eaf5de 23486 this initialisation is performed first. */
bfae80f2 23487
cd000bff
DJ
23488#ifndef OBJ_ELF
23489void
23490arm_init_frag (fragS * fragP, int max_chars ATTRIBUTE_UNUSED)
23491{
23492 /* Record whether this frag is in an ARM or a THUMB area. */
2e98972e 23493 fragP->tc_frag_data.thumb_mode = thumb_mode | MODE_RECORDED;
cd000bff
DJ
23494}
23495
23496#else /* OBJ_ELF is defined. */
c19d1205 23497void
cd000bff 23498arm_init_frag (fragS * fragP, int max_chars)
c19d1205 23499{
e8d84ca1 23500 bfd_boolean frag_thumb_mode;
b968d18a 23501
8dc2430f
NC
23502 /* If the current ARM vs THUMB mode has not already
23503 been recorded into this frag then do so now. */
cd000bff 23504 if ((fragP->tc_frag_data.thumb_mode & MODE_RECORDED) == 0)
b968d18a
JW
23505 fragP->tc_frag_data.thumb_mode = thumb_mode | MODE_RECORDED;
23506
e8d84ca1
NC
23507 /* PR 21809: Do not set a mapping state for debug sections
23508 - it just confuses other tools. */
23509 if (bfd_get_section_flags (NULL, now_seg) & SEC_DEBUGGING)
23510 return;
23511
b968d18a 23512 frag_thumb_mode = fragP->tc_frag_data.thumb_mode ^ MODE_RECORDED;
cd000bff 23513
f9c1b181
RL
23514 /* Record a mapping symbol for alignment frags. We will delete this
23515 later if the alignment ends up empty. */
23516 switch (fragP->fr_type)
23517 {
23518 case rs_align:
23519 case rs_align_test:
23520 case rs_fill:
23521 mapping_state_2 (MAP_DATA, max_chars);
23522 break;
23523 case rs_align_code:
b968d18a 23524 mapping_state_2 (frag_thumb_mode ? MAP_THUMB : MAP_ARM, max_chars);
f9c1b181
RL
23525 break;
23526 default:
23527 break;
cd000bff 23528 }
bfae80f2
RE
23529}
23530
c19d1205
ZW
23531/* When we change sections we need to issue a new mapping symbol. */
23532
23533void
23534arm_elf_change_section (void)
bfae80f2 23535{
c19d1205
ZW
23536 /* Link an unlinked unwind index table section to the .text section. */
23537 if (elf_section_type (now_seg) == SHT_ARM_EXIDX
23538 && elf_linked_to_section (now_seg) == NULL)
23539 elf_linked_to_section (now_seg) = text_section;
bfae80f2
RE
23540}
23541
c19d1205
ZW
23542int
23543arm_elf_section_type (const char * str, size_t len)
e45d0630 23544{
c19d1205
ZW
23545 if (len == 5 && strncmp (str, "exidx", 5) == 0)
23546 return SHT_ARM_EXIDX;
e45d0630 23547
c19d1205
ZW
23548 return -1;
23549}
23550\f
23551/* Code to deal with unwinding tables. */
e45d0630 23552
c19d1205 23553static void add_unwind_adjustsp (offsetT);
e45d0630 23554
5f4273c7 23555/* Generate any deferred unwind frame offset. */
e45d0630 23556
bfae80f2 23557static void
c19d1205 23558flush_pending_unwind (void)
bfae80f2 23559{
c19d1205 23560 offsetT offset;
bfae80f2 23561
c19d1205
ZW
23562 offset = unwind.pending_offset;
23563 unwind.pending_offset = 0;
23564 if (offset != 0)
23565 add_unwind_adjustsp (offset);
bfae80f2
RE
23566}
23567
c19d1205
ZW
23568/* Add an opcode to this list for this function. Two-byte opcodes should
23569 be passed as op[0] << 8 | op[1]. The list of opcodes is built in reverse
23570 order. */
23571
bfae80f2 23572static void
c19d1205 23573add_unwind_opcode (valueT op, int length)
bfae80f2 23574{
c19d1205
ZW
23575 /* Add any deferred stack adjustment. */
23576 if (unwind.pending_offset)
23577 flush_pending_unwind ();
bfae80f2 23578
c19d1205 23579 unwind.sp_restored = 0;
bfae80f2 23580
c19d1205 23581 if (unwind.opcode_count + length > unwind.opcode_alloc)
bfae80f2 23582 {
c19d1205
ZW
23583 unwind.opcode_alloc += ARM_OPCODE_CHUNK_SIZE;
23584 if (unwind.opcodes)
325801bd
TS
23585 unwind.opcodes = XRESIZEVEC (unsigned char, unwind.opcodes,
23586 unwind.opcode_alloc);
c19d1205 23587 else
325801bd 23588 unwind.opcodes = XNEWVEC (unsigned char, unwind.opcode_alloc);
bfae80f2 23589 }
c19d1205 23590 while (length > 0)
bfae80f2 23591 {
c19d1205
ZW
23592 length--;
23593 unwind.opcodes[unwind.opcode_count] = op & 0xff;
23594 op >>= 8;
23595 unwind.opcode_count++;
bfae80f2 23596 }
bfae80f2
RE
23597}
23598
c19d1205
ZW
23599/* Add unwind opcodes to adjust the stack pointer. */
23600
bfae80f2 23601static void
c19d1205 23602add_unwind_adjustsp (offsetT offset)
bfae80f2 23603{
c19d1205 23604 valueT op;
bfae80f2 23605
c19d1205 23606 if (offset > 0x200)
bfae80f2 23607 {
c19d1205
ZW
23608 /* We need at most 5 bytes to hold a 32-bit value in a uleb128. */
23609 char bytes[5];
23610 int n;
23611 valueT o;
bfae80f2 23612
c19d1205
ZW
23613 /* Long form: 0xb2, uleb128. */
23614 /* This might not fit in a word so add the individual bytes,
23615 remembering the list is built in reverse order. */
23616 o = (valueT) ((offset - 0x204) >> 2);
23617 if (o == 0)
23618 add_unwind_opcode (0, 1);
bfae80f2 23619
c19d1205
ZW
23620 /* Calculate the uleb128 encoding of the offset. */
23621 n = 0;
23622 while (o)
23623 {
23624 bytes[n] = o & 0x7f;
23625 o >>= 7;
23626 if (o)
23627 bytes[n] |= 0x80;
23628 n++;
23629 }
23630 /* Add the insn. */
23631 for (; n; n--)
23632 add_unwind_opcode (bytes[n - 1], 1);
23633 add_unwind_opcode (0xb2, 1);
23634 }
23635 else if (offset > 0x100)
bfae80f2 23636 {
c19d1205
ZW
23637 /* Two short opcodes. */
23638 add_unwind_opcode (0x3f, 1);
23639 op = (offset - 0x104) >> 2;
23640 add_unwind_opcode (op, 1);
bfae80f2 23641 }
c19d1205
ZW
23642 else if (offset > 0)
23643 {
23644 /* Short opcode. */
23645 op = (offset - 4) >> 2;
23646 add_unwind_opcode (op, 1);
23647 }
23648 else if (offset < 0)
bfae80f2 23649 {
c19d1205
ZW
23650 offset = -offset;
23651 while (offset > 0x100)
bfae80f2 23652 {
c19d1205
ZW
23653 add_unwind_opcode (0x7f, 1);
23654 offset -= 0x100;
bfae80f2 23655 }
c19d1205
ZW
23656 op = ((offset - 4) >> 2) | 0x40;
23657 add_unwind_opcode (op, 1);
bfae80f2 23658 }
bfae80f2
RE
23659}
23660
c19d1205 23661/* Finish the list of unwind opcodes for this function. */
0198d5e6 23662
c19d1205
ZW
23663static void
23664finish_unwind_opcodes (void)
bfae80f2 23665{
c19d1205 23666 valueT op;
bfae80f2 23667
c19d1205 23668 if (unwind.fp_used)
bfae80f2 23669 {
708587a4 23670 /* Adjust sp as necessary. */
c19d1205
ZW
23671 unwind.pending_offset += unwind.fp_offset - unwind.frame_size;
23672 flush_pending_unwind ();
bfae80f2 23673
c19d1205
ZW
23674 /* After restoring sp from the frame pointer. */
23675 op = 0x90 | unwind.fp_reg;
23676 add_unwind_opcode (op, 1);
23677 }
23678 else
23679 flush_pending_unwind ();
bfae80f2
RE
23680}
23681
bfae80f2 23682
c19d1205
ZW
23683/* Start an exception table entry. If idx is nonzero this is an index table
23684 entry. */
bfae80f2
RE
23685
23686static void
c19d1205 23687start_unwind_section (const segT text_seg, int idx)
bfae80f2 23688{
c19d1205
ZW
23689 const char * text_name;
23690 const char * prefix;
23691 const char * prefix_once;
23692 const char * group_name;
c19d1205 23693 char * sec_name;
c19d1205
ZW
23694 int type;
23695 int flags;
23696 int linkonce;
bfae80f2 23697
c19d1205 23698 if (idx)
bfae80f2 23699 {
c19d1205
ZW
23700 prefix = ELF_STRING_ARM_unwind;
23701 prefix_once = ELF_STRING_ARM_unwind_once;
23702 type = SHT_ARM_EXIDX;
bfae80f2 23703 }
c19d1205 23704 else
bfae80f2 23705 {
c19d1205
ZW
23706 prefix = ELF_STRING_ARM_unwind_info;
23707 prefix_once = ELF_STRING_ARM_unwind_info_once;
23708 type = SHT_PROGBITS;
bfae80f2
RE
23709 }
23710
c19d1205
ZW
23711 text_name = segment_name (text_seg);
23712 if (streq (text_name, ".text"))
23713 text_name = "";
23714
23715 if (strncmp (text_name, ".gnu.linkonce.t.",
23716 strlen (".gnu.linkonce.t.")) == 0)
bfae80f2 23717 {
c19d1205
ZW
23718 prefix = prefix_once;
23719 text_name += strlen (".gnu.linkonce.t.");
bfae80f2
RE
23720 }
23721
29a2809e 23722 sec_name = concat (prefix, text_name, (char *) NULL);
bfae80f2 23723
c19d1205
ZW
23724 flags = SHF_ALLOC;
23725 linkonce = 0;
23726 group_name = 0;
bfae80f2 23727
c19d1205
ZW
23728 /* Handle COMDAT group. */
23729 if (prefix != prefix_once && (text_seg->flags & SEC_LINK_ONCE) != 0)
bfae80f2 23730 {
c19d1205
ZW
23731 group_name = elf_group_name (text_seg);
23732 if (group_name == NULL)
23733 {
bd3ba5d1 23734 as_bad (_("Group section `%s' has no group signature"),
c19d1205
ZW
23735 segment_name (text_seg));
23736 ignore_rest_of_line ();
23737 return;
23738 }
23739 flags |= SHF_GROUP;
23740 linkonce = 1;
bfae80f2
RE
23741 }
23742
a91e1603
L
23743 obj_elf_change_section (sec_name, type, 0, flags, 0, group_name,
23744 linkonce, 0);
bfae80f2 23745
5f4273c7 23746 /* Set the section link for index tables. */
c19d1205
ZW
23747 if (idx)
23748 elf_linked_to_section (now_seg) = text_seg;
bfae80f2
RE
23749}
23750
bfae80f2 23751
c19d1205
ZW
23752/* Start an unwind table entry. HAVE_DATA is nonzero if we have additional
23753 personality routine data. Returns zero, or the index table value for
cad0da33 23754 an inline entry. */
c19d1205
ZW
23755
23756static valueT
23757create_unwind_entry (int have_data)
bfae80f2 23758{
c19d1205
ZW
23759 int size;
23760 addressT where;
23761 char *ptr;
23762 /* The current word of data. */
23763 valueT data;
23764 /* The number of bytes left in this word. */
23765 int n;
bfae80f2 23766
c19d1205 23767 finish_unwind_opcodes ();
bfae80f2 23768
c19d1205
ZW
23769 /* Remember the current text section. */
23770 unwind.saved_seg = now_seg;
23771 unwind.saved_subseg = now_subseg;
bfae80f2 23772
c19d1205 23773 start_unwind_section (now_seg, 0);
bfae80f2 23774
c19d1205 23775 if (unwind.personality_routine == NULL)
bfae80f2 23776 {
c19d1205
ZW
23777 if (unwind.personality_index == -2)
23778 {
23779 if (have_data)
5f4273c7 23780 as_bad (_("handlerdata in cantunwind frame"));
c19d1205
ZW
23781 return 1; /* EXIDX_CANTUNWIND. */
23782 }
bfae80f2 23783
c19d1205
ZW
23784 /* Use a default personality routine if none is specified. */
23785 if (unwind.personality_index == -1)
23786 {
23787 if (unwind.opcode_count > 3)
23788 unwind.personality_index = 1;
23789 else
23790 unwind.personality_index = 0;
23791 }
bfae80f2 23792
c19d1205
ZW
23793 /* Space for the personality routine entry. */
23794 if (unwind.personality_index == 0)
23795 {
23796 if (unwind.opcode_count > 3)
23797 as_bad (_("too many unwind opcodes for personality routine 0"));
bfae80f2 23798
c19d1205
ZW
23799 if (!have_data)
23800 {
23801 /* All the data is inline in the index table. */
23802 data = 0x80;
23803 n = 3;
23804 while (unwind.opcode_count > 0)
23805 {
23806 unwind.opcode_count--;
23807 data = (data << 8) | unwind.opcodes[unwind.opcode_count];
23808 n--;
23809 }
bfae80f2 23810
c19d1205
ZW
23811 /* Pad with "finish" opcodes. */
23812 while (n--)
23813 data = (data << 8) | 0xb0;
bfae80f2 23814
c19d1205
ZW
23815 return data;
23816 }
23817 size = 0;
23818 }
23819 else
23820 /* We get two opcodes "free" in the first word. */
23821 size = unwind.opcode_count - 2;
23822 }
23823 else
5011093d 23824 {
cad0da33
NC
23825 /* PR 16765: Missing or misplaced unwind directives can trigger this. */
23826 if (unwind.personality_index != -1)
23827 {
23828 as_bad (_("attempt to recreate an unwind entry"));
23829 return 1;
23830 }
5011093d
NC
23831
23832 /* An extra byte is required for the opcode count. */
23833 size = unwind.opcode_count + 1;
23834 }
bfae80f2 23835
c19d1205
ZW
23836 size = (size + 3) >> 2;
23837 if (size > 0xff)
23838 as_bad (_("too many unwind opcodes"));
bfae80f2 23839
c19d1205
ZW
23840 frag_align (2, 0, 0);
23841 record_alignment (now_seg, 2);
23842 unwind.table_entry = expr_build_dot ();
23843
23844 /* Allocate the table entry. */
23845 ptr = frag_more ((size << 2) + 4);
74929e7b
NC
23846 /* PR 13449: Zero the table entries in case some of them are not used. */
23847 memset (ptr, 0, (size << 2) + 4);
c19d1205 23848 where = frag_now_fix () - ((size << 2) + 4);
bfae80f2 23849
c19d1205 23850 switch (unwind.personality_index)
bfae80f2 23851 {
c19d1205
ZW
23852 case -1:
23853 /* ??? Should this be a PLT generating relocation? */
23854 /* Custom personality routine. */
23855 fix_new (frag_now, where, 4, unwind.personality_routine, 0, 1,
23856 BFD_RELOC_ARM_PREL31);
bfae80f2 23857
c19d1205
ZW
23858 where += 4;
23859 ptr += 4;
bfae80f2 23860
c19d1205 23861 /* Set the first byte to the number of additional words. */
5011093d 23862 data = size > 0 ? size - 1 : 0;
c19d1205
ZW
23863 n = 3;
23864 break;
bfae80f2 23865
c19d1205
ZW
23866 /* ABI defined personality routines. */
23867 case 0:
23868 /* Three opcodes bytes are packed into the first word. */
23869 data = 0x80;
23870 n = 3;
23871 break;
bfae80f2 23872
c19d1205
ZW
23873 case 1:
23874 case 2:
23875 /* The size and first two opcode bytes go in the first word. */
23876 data = ((0x80 + unwind.personality_index) << 8) | size;
23877 n = 2;
23878 break;
bfae80f2 23879
c19d1205
ZW
23880 default:
23881 /* Should never happen. */
23882 abort ();
23883 }
bfae80f2 23884
c19d1205
ZW
23885 /* Pack the opcodes into words (MSB first), reversing the list at the same
23886 time. */
23887 while (unwind.opcode_count > 0)
23888 {
23889 if (n == 0)
23890 {
23891 md_number_to_chars (ptr, data, 4);
23892 ptr += 4;
23893 n = 4;
23894 data = 0;
23895 }
23896 unwind.opcode_count--;
23897 n--;
23898 data = (data << 8) | unwind.opcodes[unwind.opcode_count];
23899 }
23900
23901 /* Finish off the last word. */
23902 if (n < 4)
23903 {
23904 /* Pad with "finish" opcodes. */
23905 while (n--)
23906 data = (data << 8) | 0xb0;
23907
23908 md_number_to_chars (ptr, data, 4);
23909 }
23910
23911 if (!have_data)
23912 {
23913 /* Add an empty descriptor if there is no user-specified data. */
23914 ptr = frag_more (4);
23915 md_number_to_chars (ptr, 0, 4);
23916 }
23917
23918 return 0;
bfae80f2
RE
23919}
23920
f0927246
NC
23921
23922/* Initialize the DWARF-2 unwind information for this procedure. */
23923
23924void
23925tc_arm_frame_initial_instructions (void)
23926{
23927 cfi_add_CFA_def_cfa (REG_SP, 0);
23928}
23929#endif /* OBJ_ELF */
23930
c19d1205
ZW
23931/* Convert REGNAME to a DWARF-2 register number. */
23932
23933int
1df69f4f 23934tc_arm_regname_to_dw2regnum (char *regname)
bfae80f2 23935{
1df69f4f 23936 int reg = arm_reg_parse (&regname, REG_TYPE_RN);
1f5afe1c
NC
23937 if (reg != FAIL)
23938 return reg;
c19d1205 23939
1f5afe1c
NC
23940 /* PR 16694: Allow VFP registers as well. */
23941 reg = arm_reg_parse (&regname, REG_TYPE_VFS);
23942 if (reg != FAIL)
23943 return 64 + reg;
c19d1205 23944
1f5afe1c
NC
23945 reg = arm_reg_parse (&regname, REG_TYPE_VFD);
23946 if (reg != FAIL)
23947 return reg + 256;
23948
0198d5e6 23949 return FAIL;
bfae80f2
RE
23950}
23951
f0927246 23952#ifdef TE_PE
c19d1205 23953void
f0927246 23954tc_pe_dwarf2_emit_offset (symbolS *symbol, unsigned int size)
bfae80f2 23955{
91d6fa6a 23956 expressionS exp;
bfae80f2 23957
91d6fa6a
NC
23958 exp.X_op = O_secrel;
23959 exp.X_add_symbol = symbol;
23960 exp.X_add_number = 0;
23961 emit_expr (&exp, size);
f0927246
NC
23962}
23963#endif
bfae80f2 23964
c19d1205 23965/* MD interface: Symbol and relocation handling. */
bfae80f2 23966
2fc8bdac
ZW
23967/* Return the address within the segment that a PC-relative fixup is
23968 relative to. For ARM, PC-relative fixups applied to instructions
23969 are generally relative to the location of the fixup plus 8 bytes.
23970 Thumb branches are offset by 4, and Thumb loads relative to PC
23971 require special handling. */
bfae80f2 23972
c19d1205 23973long
2fc8bdac 23974md_pcrel_from_section (fixS * fixP, segT seg)
bfae80f2 23975{
2fc8bdac
ZW
23976 offsetT base = fixP->fx_where + fixP->fx_frag->fr_address;
23977
23978 /* If this is pc-relative and we are going to emit a relocation
23979 then we just want to put out any pipeline compensation that the linker
53baae48
NC
23980 will need. Otherwise we want to use the calculated base.
23981 For WinCE we skip the bias for externals as well, since this
23982 is how the MS ARM-CE assembler behaves and we want to be compatible. */
5f4273c7 23983 if (fixP->fx_pcrel
2fc8bdac 23984 && ((fixP->fx_addsy && S_GET_SEGMENT (fixP->fx_addsy) != seg)
53baae48
NC
23985 || (arm_force_relocation (fixP)
23986#ifdef TE_WINCE
23987 && !S_IS_EXTERNAL (fixP->fx_addsy)
23988#endif
23989 )))
2fc8bdac 23990 base = 0;
bfae80f2 23991
267bf995 23992
c19d1205 23993 switch (fixP->fx_r_type)
bfae80f2 23994 {
2fc8bdac
ZW
23995 /* PC relative addressing on the Thumb is slightly odd as the
23996 bottom two bits of the PC are forced to zero for the
23997 calculation. This happens *after* application of the
23998 pipeline offset. However, Thumb adrl already adjusts for
23999 this, so we need not do it again. */
c19d1205 24000 case BFD_RELOC_ARM_THUMB_ADD:
2fc8bdac 24001 return base & ~3;
c19d1205
ZW
24002
24003 case BFD_RELOC_ARM_THUMB_OFFSET:
24004 case BFD_RELOC_ARM_T32_OFFSET_IMM:
e9f89963 24005 case BFD_RELOC_ARM_T32_ADD_PC12:
8f06b2d8 24006 case BFD_RELOC_ARM_T32_CP_OFF_IMM:
2fc8bdac 24007 return (base + 4) & ~3;
c19d1205 24008
2fc8bdac 24009 /* Thumb branches are simply offset by +4. */
e12437dc 24010 case BFD_RELOC_THUMB_PCREL_BRANCH5:
2fc8bdac
ZW
24011 case BFD_RELOC_THUMB_PCREL_BRANCH7:
24012 case BFD_RELOC_THUMB_PCREL_BRANCH9:
24013 case BFD_RELOC_THUMB_PCREL_BRANCH12:
24014 case BFD_RELOC_THUMB_PCREL_BRANCH20:
2fc8bdac 24015 case BFD_RELOC_THUMB_PCREL_BRANCH25:
f6b2b12d 24016 case BFD_RELOC_THUMB_PCREL_BFCSEL:
e5d6e09e 24017 case BFD_RELOC_ARM_THUMB_BF17:
1caf72a5 24018 case BFD_RELOC_ARM_THUMB_BF19:
1889da70 24019 case BFD_RELOC_ARM_THUMB_BF13:
60f993ce 24020 case BFD_RELOC_ARM_THUMB_LOOP12:
2fc8bdac 24021 return base + 4;
bfae80f2 24022
267bf995 24023 case BFD_RELOC_THUMB_PCREL_BRANCH23:
486499d0
CL
24024 if (fixP->fx_addsy
24025 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
34e77a92 24026 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
267bf995 24027 && ARM_IS_FUNC (fixP->fx_addsy)
477330fc
RM
24028 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t))
24029 base = fixP->fx_where + fixP->fx_frag->fr_address;
267bf995
RR
24030 return base + 4;
24031
00adf2d4
JB
24032 /* BLX is like branches above, but forces the low two bits of PC to
24033 zero. */
486499d0
CL
24034 case BFD_RELOC_THUMB_PCREL_BLX:
24035 if (fixP->fx_addsy
24036 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
34e77a92 24037 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
477330fc
RM
24038 && THUMB_IS_FUNC (fixP->fx_addsy)
24039 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t))
24040 base = fixP->fx_where + fixP->fx_frag->fr_address;
00adf2d4
JB
24041 return (base + 4) & ~3;
24042
2fc8bdac
ZW
24043 /* ARM mode branches are offset by +8. However, the Windows CE
24044 loader expects the relocation not to take this into account. */
267bf995 24045 case BFD_RELOC_ARM_PCREL_BLX:
486499d0
CL
24046 if (fixP->fx_addsy
24047 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
34e77a92 24048 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
477330fc
RM
24049 && ARM_IS_FUNC (fixP->fx_addsy)
24050 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t))
24051 base = fixP->fx_where + fixP->fx_frag->fr_address;
486499d0 24052 return base + 8;
267bf995 24053
486499d0
CL
24054 case BFD_RELOC_ARM_PCREL_CALL:
24055 if (fixP->fx_addsy
24056 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
34e77a92 24057 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
477330fc
RM
24058 && THUMB_IS_FUNC (fixP->fx_addsy)
24059 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t))
24060 base = fixP->fx_where + fixP->fx_frag->fr_address;
486499d0 24061 return base + 8;
267bf995 24062
2fc8bdac 24063 case BFD_RELOC_ARM_PCREL_BRANCH:
39b41c9c 24064 case BFD_RELOC_ARM_PCREL_JUMP:
2fc8bdac 24065 case BFD_RELOC_ARM_PLT32:
c19d1205 24066#ifdef TE_WINCE
5f4273c7 24067 /* When handling fixups immediately, because we have already
477330fc 24068 discovered the value of a symbol, or the address of the frag involved
53baae48 24069 we must account for the offset by +8, as the OS loader will never see the reloc.
477330fc
RM
24070 see fixup_segment() in write.c
24071 The S_IS_EXTERNAL test handles the case of global symbols.
24072 Those need the calculated base, not just the pipe compensation the linker will need. */
53baae48
NC
24073 if (fixP->fx_pcrel
24074 && fixP->fx_addsy != NULL
24075 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
24076 && (S_IS_EXTERNAL (fixP->fx_addsy) || !arm_force_relocation (fixP)))
24077 return base + 8;
2fc8bdac 24078 return base;
c19d1205 24079#else
2fc8bdac 24080 return base + 8;
c19d1205 24081#endif
2fc8bdac 24082
267bf995 24083
2fc8bdac
ZW
24084 /* ARM mode loads relative to PC are also offset by +8. Unlike
24085 branches, the Windows CE loader *does* expect the relocation
24086 to take this into account. */
24087 case BFD_RELOC_ARM_OFFSET_IMM:
24088 case BFD_RELOC_ARM_OFFSET_IMM8:
24089 case BFD_RELOC_ARM_HWLITERAL:
24090 case BFD_RELOC_ARM_LITERAL:
24091 case BFD_RELOC_ARM_CP_OFF_IMM:
24092 return base + 8;
24093
24094
24095 /* Other PC-relative relocations are un-offset. */
24096 default:
24097 return base;
24098 }
bfae80f2
RE
24099}
24100
8b2d793c
NC
24101static bfd_boolean flag_warn_syms = TRUE;
24102
ae8714c2
NC
24103bfd_boolean
24104arm_tc_equal_in_insn (int c ATTRIBUTE_UNUSED, char * name)
bfae80f2 24105{
8b2d793c
NC
24106 /* PR 18347 - Warn if the user attempts to create a symbol with the same
24107 name as an ARM instruction. Whilst strictly speaking it is allowed, it
24108 does mean that the resulting code might be very confusing to the reader.
24109 Also this warning can be triggered if the user omits an operand before
24110 an immediate address, eg:
24111
24112 LDR =foo
24113
24114 GAS treats this as an assignment of the value of the symbol foo to a
24115 symbol LDR, and so (without this code) it will not issue any kind of
24116 warning or error message.
24117
24118 Note - ARM instructions are case-insensitive but the strings in the hash
24119 table are all stored in lower case, so we must first ensure that name is
ae8714c2
NC
24120 lower case too. */
24121 if (flag_warn_syms && arm_ops_hsh)
8b2d793c
NC
24122 {
24123 char * nbuf = strdup (name);
24124 char * p;
24125
24126 for (p = nbuf; *p; p++)
24127 *p = TOLOWER (*p);
24128 if (hash_find (arm_ops_hsh, nbuf) != NULL)
24129 {
24130 static struct hash_control * already_warned = NULL;
24131
24132 if (already_warned == NULL)
24133 already_warned = hash_new ();
24134 /* Only warn about the symbol once. To keep the code
24135 simple we let hash_insert do the lookup for us. */
3076e594 24136 if (hash_insert (already_warned, nbuf, NULL) == NULL)
ae8714c2 24137 as_warn (_("[-mwarn-syms]: Assignment makes a symbol match an ARM instruction: %s"), name);
8b2d793c
NC
24138 }
24139 else
24140 free (nbuf);
24141 }
3739860c 24142
ae8714c2
NC
24143 return FALSE;
24144}
24145
24146/* Under ELF we need to default _GLOBAL_OFFSET_TABLE.
24147 Otherwise we have no need to default values of symbols. */
24148
24149symbolS *
24150md_undefined_symbol (char * name ATTRIBUTE_UNUSED)
24151{
24152#ifdef OBJ_ELF
24153 if (name[0] == '_' && name[1] == 'G'
24154 && streq (name, GLOBAL_OFFSET_TABLE_NAME))
24155 {
24156 if (!GOT_symbol)
24157 {
24158 if (symbol_find (name))
24159 as_bad (_("GOT already in the symbol table"));
24160
24161 GOT_symbol = symbol_new (name, undefined_section,
24162 (valueT) 0, & zero_address_frag);
24163 }
24164
24165 return GOT_symbol;
24166 }
24167#endif
24168
c921be7d 24169 return NULL;
bfae80f2
RE
24170}
24171
55cf6793 24172/* Subroutine of md_apply_fix. Check to see if an immediate can be
c19d1205
ZW
24173 computed as two separate immediate values, added together. We
24174 already know that this value cannot be computed by just one ARM
24175 instruction. */
24176
24177static unsigned int
24178validate_immediate_twopart (unsigned int val,
24179 unsigned int * highpart)
bfae80f2 24180{
c19d1205
ZW
24181 unsigned int a;
24182 unsigned int i;
bfae80f2 24183
c19d1205
ZW
24184 for (i = 0; i < 32; i += 2)
24185 if (((a = rotate_left (val, i)) & 0xff) != 0)
24186 {
24187 if (a & 0xff00)
24188 {
24189 if (a & ~ 0xffff)
24190 continue;
24191 * highpart = (a >> 8) | ((i + 24) << 7);
24192 }
24193 else if (a & 0xff0000)
24194 {
24195 if (a & 0xff000000)
24196 continue;
24197 * highpart = (a >> 16) | ((i + 16) << 7);
24198 }
24199 else
24200 {
9c2799c2 24201 gas_assert (a & 0xff000000);
c19d1205
ZW
24202 * highpart = (a >> 24) | ((i + 8) << 7);
24203 }
bfae80f2 24204
c19d1205
ZW
24205 return (a & 0xff) | (i << 7);
24206 }
bfae80f2 24207
c19d1205 24208 return FAIL;
bfae80f2
RE
24209}
24210
c19d1205
ZW
24211static int
24212validate_offset_imm (unsigned int val, int hwse)
24213{
24214 if ((hwse && val > 255) || val > 4095)
24215 return FAIL;
24216 return val;
24217}
bfae80f2 24218
55cf6793 24219/* Subroutine of md_apply_fix. Do those data_ops which can take a
c19d1205
ZW
24220 negative immediate constant by altering the instruction. A bit of
24221 a hack really.
24222 MOV <-> MVN
24223 AND <-> BIC
24224 ADC <-> SBC
24225 by inverting the second operand, and
24226 ADD <-> SUB
24227 CMP <-> CMN
24228 by negating the second operand. */
bfae80f2 24229
c19d1205
ZW
24230static int
24231negate_data_op (unsigned long * instruction,
24232 unsigned long value)
bfae80f2 24233{
c19d1205
ZW
24234 int op, new_inst;
24235 unsigned long negated, inverted;
bfae80f2 24236
c19d1205
ZW
24237 negated = encode_arm_immediate (-value);
24238 inverted = encode_arm_immediate (~value);
bfae80f2 24239
c19d1205
ZW
24240 op = (*instruction >> DATA_OP_SHIFT) & 0xf;
24241 switch (op)
bfae80f2 24242 {
c19d1205
ZW
24243 /* First negates. */
24244 case OPCODE_SUB: /* ADD <-> SUB */
24245 new_inst = OPCODE_ADD;
24246 value = negated;
24247 break;
bfae80f2 24248
c19d1205
ZW
24249 case OPCODE_ADD:
24250 new_inst = OPCODE_SUB;
24251 value = negated;
24252 break;
bfae80f2 24253
c19d1205
ZW
24254 case OPCODE_CMP: /* CMP <-> CMN */
24255 new_inst = OPCODE_CMN;
24256 value = negated;
24257 break;
bfae80f2 24258
c19d1205
ZW
24259 case OPCODE_CMN:
24260 new_inst = OPCODE_CMP;
24261 value = negated;
24262 break;
bfae80f2 24263
c19d1205
ZW
24264 /* Now Inverted ops. */
24265 case OPCODE_MOV: /* MOV <-> MVN */
24266 new_inst = OPCODE_MVN;
24267 value = inverted;
24268 break;
bfae80f2 24269
c19d1205
ZW
24270 case OPCODE_MVN:
24271 new_inst = OPCODE_MOV;
24272 value = inverted;
24273 break;
bfae80f2 24274
c19d1205
ZW
24275 case OPCODE_AND: /* AND <-> BIC */
24276 new_inst = OPCODE_BIC;
24277 value = inverted;
24278 break;
bfae80f2 24279
c19d1205
ZW
24280 case OPCODE_BIC:
24281 new_inst = OPCODE_AND;
24282 value = inverted;
24283 break;
bfae80f2 24284
c19d1205
ZW
24285 case OPCODE_ADC: /* ADC <-> SBC */
24286 new_inst = OPCODE_SBC;
24287 value = inverted;
24288 break;
bfae80f2 24289
c19d1205
ZW
24290 case OPCODE_SBC:
24291 new_inst = OPCODE_ADC;
24292 value = inverted;
24293 break;
bfae80f2 24294
c19d1205
ZW
24295 /* We cannot do anything. */
24296 default:
24297 return FAIL;
b99bd4ef
NC
24298 }
24299
c19d1205
ZW
24300 if (value == (unsigned) FAIL)
24301 return FAIL;
24302
24303 *instruction &= OPCODE_MASK;
24304 *instruction |= new_inst << DATA_OP_SHIFT;
24305 return value;
b99bd4ef
NC
24306}
24307
ef8d22e6
PB
24308/* Like negate_data_op, but for Thumb-2. */
24309
24310static unsigned int
16dd5e42 24311thumb32_negate_data_op (offsetT *instruction, unsigned int value)
ef8d22e6
PB
24312{
24313 int op, new_inst;
24314 int rd;
16dd5e42 24315 unsigned int negated, inverted;
ef8d22e6
PB
24316
24317 negated = encode_thumb32_immediate (-value);
24318 inverted = encode_thumb32_immediate (~value);
24319
24320 rd = (*instruction >> 8) & 0xf;
24321 op = (*instruction >> T2_DATA_OP_SHIFT) & 0xf;
24322 switch (op)
24323 {
24324 /* ADD <-> SUB. Includes CMP <-> CMN. */
24325 case T2_OPCODE_SUB:
24326 new_inst = T2_OPCODE_ADD;
24327 value = negated;
24328 break;
24329
24330 case T2_OPCODE_ADD:
24331 new_inst = T2_OPCODE_SUB;
24332 value = negated;
24333 break;
24334
24335 /* ORR <-> ORN. Includes MOV <-> MVN. */
24336 case T2_OPCODE_ORR:
24337 new_inst = T2_OPCODE_ORN;
24338 value = inverted;
24339 break;
24340
24341 case T2_OPCODE_ORN:
24342 new_inst = T2_OPCODE_ORR;
24343 value = inverted;
24344 break;
24345
24346 /* AND <-> BIC. TST has no inverted equivalent. */
24347 case T2_OPCODE_AND:
24348 new_inst = T2_OPCODE_BIC;
24349 if (rd == 15)
24350 value = FAIL;
24351 else
24352 value = inverted;
24353 break;
24354
24355 case T2_OPCODE_BIC:
24356 new_inst = T2_OPCODE_AND;
24357 value = inverted;
24358 break;
24359
24360 /* ADC <-> SBC */
24361 case T2_OPCODE_ADC:
24362 new_inst = T2_OPCODE_SBC;
24363 value = inverted;
24364 break;
24365
24366 case T2_OPCODE_SBC:
24367 new_inst = T2_OPCODE_ADC;
24368 value = inverted;
24369 break;
24370
24371 /* We cannot do anything. */
24372 default:
24373 return FAIL;
24374 }
24375
16dd5e42 24376 if (value == (unsigned int)FAIL)
ef8d22e6
PB
24377 return FAIL;
24378
24379 *instruction &= T2_OPCODE_MASK;
24380 *instruction |= new_inst << T2_DATA_OP_SHIFT;
24381 return value;
24382}
24383
8f06b2d8 24384/* Read a 32-bit thumb instruction from buf. */
0198d5e6 24385
8f06b2d8
PB
24386static unsigned long
24387get_thumb32_insn (char * buf)
24388{
24389 unsigned long insn;
24390 insn = md_chars_to_number (buf, THUMB_SIZE) << 16;
24391 insn |= md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE);
24392
24393 return insn;
24394}
24395
a8bc6c78
PB
24396/* We usually want to set the low bit on the address of thumb function
24397 symbols. In particular .word foo - . should have the low bit set.
24398 Generic code tries to fold the difference of two symbols to
24399 a constant. Prevent this and force a relocation when the first symbols
24400 is a thumb function. */
c921be7d
NC
24401
24402bfd_boolean
a8bc6c78
PB
24403arm_optimize_expr (expressionS *l, operatorT op, expressionS *r)
24404{
24405 if (op == O_subtract
24406 && l->X_op == O_symbol
24407 && r->X_op == O_symbol
24408 && THUMB_IS_FUNC (l->X_add_symbol))
24409 {
24410 l->X_op = O_subtract;
24411 l->X_op_symbol = r->X_add_symbol;
24412 l->X_add_number -= r->X_add_number;
c921be7d 24413 return TRUE;
a8bc6c78 24414 }
c921be7d 24415
a8bc6c78 24416 /* Process as normal. */
c921be7d 24417 return FALSE;
a8bc6c78
PB
24418}
24419
4a42ebbc
RR
24420/* Encode Thumb2 unconditional branches and calls. The encoding
24421 for the 2 are identical for the immediate values. */
24422
24423static void
24424encode_thumb2_b_bl_offset (char * buf, offsetT value)
24425{
24426#define T2I1I2MASK ((1 << 13) | (1 << 11))
24427 offsetT newval;
24428 offsetT newval2;
24429 addressT S, I1, I2, lo, hi;
24430
24431 S = (value >> 24) & 0x01;
24432 I1 = (value >> 23) & 0x01;
24433 I2 = (value >> 22) & 0x01;
24434 hi = (value >> 12) & 0x3ff;
fa94de6b 24435 lo = (value >> 1) & 0x7ff;
4a42ebbc
RR
24436 newval = md_chars_to_number (buf, THUMB_SIZE);
24437 newval2 = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE);
24438 newval |= (S << 10) | hi;
24439 newval2 &= ~T2I1I2MASK;
24440 newval2 |= (((I1 ^ S) << 13) | ((I2 ^ S) << 11) | lo) ^ T2I1I2MASK;
24441 md_number_to_chars (buf, newval, THUMB_SIZE);
24442 md_number_to_chars (buf + THUMB_SIZE, newval2, THUMB_SIZE);
24443}
24444
c19d1205 24445void
55cf6793 24446md_apply_fix (fixS * fixP,
c19d1205
ZW
24447 valueT * valP,
24448 segT seg)
24449{
24450 offsetT value = * valP;
24451 offsetT newval;
24452 unsigned int newimm;
24453 unsigned long temp;
24454 int sign;
24455 char * buf = fixP->fx_where + fixP->fx_frag->fr_literal;
b99bd4ef 24456
9c2799c2 24457 gas_assert (fixP->fx_r_type <= BFD_RELOC_UNUSED);
b99bd4ef 24458
c19d1205 24459 /* Note whether this will delete the relocation. */
4962c51a 24460
c19d1205
ZW
24461 if (fixP->fx_addsy == 0 && !fixP->fx_pcrel)
24462 fixP->fx_done = 1;
b99bd4ef 24463
adbaf948 24464 /* On a 64-bit host, silently truncate 'value' to 32 bits for
5f4273c7 24465 consistency with the behaviour on 32-bit hosts. Remember value
adbaf948
ZW
24466 for emit_reloc. */
24467 value &= 0xffffffff;
24468 value ^= 0x80000000;
5f4273c7 24469 value -= 0x80000000;
adbaf948
ZW
24470
24471 *valP = value;
c19d1205 24472 fixP->fx_addnumber = value;
b99bd4ef 24473
adbaf948
ZW
24474 /* Same treatment for fixP->fx_offset. */
24475 fixP->fx_offset &= 0xffffffff;
24476 fixP->fx_offset ^= 0x80000000;
24477 fixP->fx_offset -= 0x80000000;
24478
c19d1205 24479 switch (fixP->fx_r_type)
b99bd4ef 24480 {
c19d1205
ZW
24481 case BFD_RELOC_NONE:
24482 /* This will need to go in the object file. */
24483 fixP->fx_done = 0;
24484 break;
b99bd4ef 24485
c19d1205
ZW
24486 case BFD_RELOC_ARM_IMMEDIATE:
24487 /* We claim that this fixup has been processed here,
24488 even if in fact we generate an error because we do
24489 not have a reloc for it, so tc_gen_reloc will reject it. */
24490 fixP->fx_done = 1;
b99bd4ef 24491
77db8e2e 24492 if (fixP->fx_addsy)
b99bd4ef 24493 {
77db8e2e 24494 const char *msg = 0;
b99bd4ef 24495
77db8e2e
NC
24496 if (! S_IS_DEFINED (fixP->fx_addsy))
24497 msg = _("undefined symbol %s used as an immediate value");
24498 else if (S_GET_SEGMENT (fixP->fx_addsy) != seg)
24499 msg = _("symbol %s is in a different section");
24500 else if (S_IS_WEAK (fixP->fx_addsy))
24501 msg = _("symbol %s is weak and may be overridden later");
24502
24503 if (msg)
24504 {
24505 as_bad_where (fixP->fx_file, fixP->fx_line,
24506 msg, S_GET_NAME (fixP->fx_addsy));
24507 break;
24508 }
42e5fcbf
AS
24509 }
24510
c19d1205
ZW
24511 temp = md_chars_to_number (buf, INSN_SIZE);
24512
5e73442d
SL
24513 /* If the offset is negative, we should use encoding A2 for ADR. */
24514 if ((temp & 0xfff0000) == 0x28f0000 && value < 0)
24515 newimm = negate_data_op (&temp, value);
24516 else
24517 {
24518 newimm = encode_arm_immediate (value);
24519
24520 /* If the instruction will fail, see if we can fix things up by
24521 changing the opcode. */
24522 if (newimm == (unsigned int) FAIL)
24523 newimm = negate_data_op (&temp, value);
bada4342
JW
24524 /* MOV accepts both ARM modified immediate (A1 encoding) and
24525 UINT16 (A2 encoding) when possible, MOVW only accepts UINT16.
24526 When disassembling, MOV is preferred when there is no encoding
24527 overlap. */
24528 if (newimm == (unsigned int) FAIL
24529 && ((temp >> DATA_OP_SHIFT) & 0xf) == OPCODE_MOV
24530 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6t2)
24531 && !((temp >> SBIT_SHIFT) & 0x1)
24532 && value >= 0 && value <= 0xffff)
24533 {
24534 /* Clear bits[23:20] to change encoding from A1 to A2. */
24535 temp &= 0xff0fffff;
24536 /* Encoding high 4bits imm. Code below will encode the remaining
24537 low 12bits. */
24538 temp |= (value & 0x0000f000) << 4;
24539 newimm = value & 0x00000fff;
24540 }
5e73442d
SL
24541 }
24542
24543 if (newimm == (unsigned int) FAIL)
b99bd4ef 24544 {
c19d1205
ZW
24545 as_bad_where (fixP->fx_file, fixP->fx_line,
24546 _("invalid constant (%lx) after fixup"),
24547 (unsigned long) value);
24548 break;
b99bd4ef 24549 }
b99bd4ef 24550
c19d1205
ZW
24551 newimm |= (temp & 0xfffff000);
24552 md_number_to_chars (buf, (valueT) newimm, INSN_SIZE);
24553 break;
b99bd4ef 24554
c19d1205
ZW
24555 case BFD_RELOC_ARM_ADRL_IMMEDIATE:
24556 {
24557 unsigned int highpart = 0;
24558 unsigned int newinsn = 0xe1a00000; /* nop. */
b99bd4ef 24559
77db8e2e 24560 if (fixP->fx_addsy)
42e5fcbf 24561 {
77db8e2e 24562 const char *msg = 0;
42e5fcbf 24563
77db8e2e
NC
24564 if (! S_IS_DEFINED (fixP->fx_addsy))
24565 msg = _("undefined symbol %s used as an immediate value");
24566 else if (S_GET_SEGMENT (fixP->fx_addsy) != seg)
24567 msg = _("symbol %s is in a different section");
24568 else if (S_IS_WEAK (fixP->fx_addsy))
24569 msg = _("symbol %s is weak and may be overridden later");
42e5fcbf 24570
77db8e2e
NC
24571 if (msg)
24572 {
24573 as_bad_where (fixP->fx_file, fixP->fx_line,
24574 msg, S_GET_NAME (fixP->fx_addsy));
24575 break;
24576 }
24577 }
fa94de6b 24578
c19d1205
ZW
24579 newimm = encode_arm_immediate (value);
24580 temp = md_chars_to_number (buf, INSN_SIZE);
b99bd4ef 24581
c19d1205
ZW
24582 /* If the instruction will fail, see if we can fix things up by
24583 changing the opcode. */
24584 if (newimm == (unsigned int) FAIL
24585 && (newimm = negate_data_op (& temp, value)) == (unsigned int) FAIL)
24586 {
24587 /* No ? OK - try using two ADD instructions to generate
24588 the value. */
24589 newimm = validate_immediate_twopart (value, & highpart);
b99bd4ef 24590
c19d1205
ZW
24591 /* Yes - then make sure that the second instruction is
24592 also an add. */
24593 if (newimm != (unsigned int) FAIL)
24594 newinsn = temp;
24595 /* Still No ? Try using a negated value. */
24596 else if ((newimm = validate_immediate_twopart (- value, & highpart)) != (unsigned int) FAIL)
24597 temp = newinsn = (temp & OPCODE_MASK) | OPCODE_SUB << DATA_OP_SHIFT;
24598 /* Otherwise - give up. */
24599 else
24600 {
24601 as_bad_where (fixP->fx_file, fixP->fx_line,
24602 _("unable to compute ADRL instructions for PC offset of 0x%lx"),
24603 (long) value);
24604 break;
24605 }
b99bd4ef 24606
c19d1205
ZW
24607 /* Replace the first operand in the 2nd instruction (which
24608 is the PC) with the destination register. We have
24609 already added in the PC in the first instruction and we
24610 do not want to do it again. */
24611 newinsn &= ~ 0xf0000;
24612 newinsn |= ((newinsn & 0x0f000) << 4);
24613 }
b99bd4ef 24614
c19d1205
ZW
24615 newimm |= (temp & 0xfffff000);
24616 md_number_to_chars (buf, (valueT) newimm, INSN_SIZE);
b99bd4ef 24617
c19d1205
ZW
24618 highpart |= (newinsn & 0xfffff000);
24619 md_number_to_chars (buf + INSN_SIZE, (valueT) highpart, INSN_SIZE);
24620 }
24621 break;
b99bd4ef 24622
c19d1205 24623 case BFD_RELOC_ARM_OFFSET_IMM:
00a97672
RS
24624 if (!fixP->fx_done && seg->use_rela_p)
24625 value = 0;
1a0670f3 24626 /* Fall through. */
00a97672 24627
c19d1205 24628 case BFD_RELOC_ARM_LITERAL:
26d97720 24629 sign = value > 0;
b99bd4ef 24630
c19d1205
ZW
24631 if (value < 0)
24632 value = - value;
b99bd4ef 24633
c19d1205 24634 if (validate_offset_imm (value, 0) == FAIL)
f03698e6 24635 {
c19d1205
ZW
24636 if (fixP->fx_r_type == BFD_RELOC_ARM_LITERAL)
24637 as_bad_where (fixP->fx_file, fixP->fx_line,
24638 _("invalid literal constant: pool needs to be closer"));
24639 else
24640 as_bad_where (fixP->fx_file, fixP->fx_line,
24641 _("bad immediate value for offset (%ld)"),
24642 (long) value);
24643 break;
f03698e6
RE
24644 }
24645
c19d1205 24646 newval = md_chars_to_number (buf, INSN_SIZE);
26d97720
NS
24647 if (value == 0)
24648 newval &= 0xfffff000;
24649 else
24650 {
24651 newval &= 0xff7ff000;
24652 newval |= value | (sign ? INDEX_UP : 0);
24653 }
c19d1205
ZW
24654 md_number_to_chars (buf, newval, INSN_SIZE);
24655 break;
b99bd4ef 24656
c19d1205
ZW
24657 case BFD_RELOC_ARM_OFFSET_IMM8:
24658 case BFD_RELOC_ARM_HWLITERAL:
26d97720 24659 sign = value > 0;
b99bd4ef 24660
c19d1205
ZW
24661 if (value < 0)
24662 value = - value;
b99bd4ef 24663
c19d1205 24664 if (validate_offset_imm (value, 1) == FAIL)
b99bd4ef 24665 {
c19d1205
ZW
24666 if (fixP->fx_r_type == BFD_RELOC_ARM_HWLITERAL)
24667 as_bad_where (fixP->fx_file, fixP->fx_line,
24668 _("invalid literal constant: pool needs to be closer"));
24669 else
427d0db6
RM
24670 as_bad_where (fixP->fx_file, fixP->fx_line,
24671 _("bad immediate value for 8-bit offset (%ld)"),
24672 (long) value);
c19d1205 24673 break;
b99bd4ef
NC
24674 }
24675
c19d1205 24676 newval = md_chars_to_number (buf, INSN_SIZE);
26d97720
NS
24677 if (value == 0)
24678 newval &= 0xfffff0f0;
24679 else
24680 {
24681 newval &= 0xff7ff0f0;
24682 newval |= ((value >> 4) << 8) | (value & 0xf) | (sign ? INDEX_UP : 0);
24683 }
c19d1205
ZW
24684 md_number_to_chars (buf, newval, INSN_SIZE);
24685 break;
b99bd4ef 24686
c19d1205
ZW
24687 case BFD_RELOC_ARM_T32_OFFSET_U8:
24688 if (value < 0 || value > 1020 || value % 4 != 0)
24689 as_bad_where (fixP->fx_file, fixP->fx_line,
24690 _("bad immediate value for offset (%ld)"), (long) value);
24691 value /= 4;
b99bd4ef 24692
c19d1205 24693 newval = md_chars_to_number (buf+2, THUMB_SIZE);
c19d1205
ZW
24694 newval |= value;
24695 md_number_to_chars (buf+2, newval, THUMB_SIZE);
24696 break;
b99bd4ef 24697
c19d1205
ZW
24698 case BFD_RELOC_ARM_T32_OFFSET_IMM:
24699 /* This is a complicated relocation used for all varieties of Thumb32
24700 load/store instruction with immediate offset:
24701
24702 1110 100P u1WL NNNN XXXX YYYY iiii iiii - +/-(U) pre/post(P) 8-bit,
477330fc 24703 *4, optional writeback(W)
c19d1205
ZW
24704 (doubleword load/store)
24705
24706 1111 100S uTTL 1111 XXXX iiii iiii iiii - +/-(U) 12-bit PC-rel
24707 1111 100S 0TTL NNNN XXXX 1Pu1 iiii iiii - +/-(U) pre/post(P) 8-bit
24708 1111 100S 0TTL NNNN XXXX 1110 iiii iiii - positive 8-bit (T instruction)
24709 1111 100S 1TTL NNNN XXXX iiii iiii iiii - positive 12-bit
24710 1111 100S 0TTL NNNN XXXX 1100 iiii iiii - negative 8-bit
24711
24712 Uppercase letters indicate bits that are already encoded at
24713 this point. Lowercase letters are our problem. For the
24714 second block of instructions, the secondary opcode nybble
24715 (bits 8..11) is present, and bit 23 is zero, even if this is
24716 a PC-relative operation. */
24717 newval = md_chars_to_number (buf, THUMB_SIZE);
24718 newval <<= 16;
24719 newval |= md_chars_to_number (buf+THUMB_SIZE, THUMB_SIZE);
b99bd4ef 24720
c19d1205 24721 if ((newval & 0xf0000000) == 0xe0000000)
b99bd4ef 24722 {
c19d1205
ZW
24723 /* Doubleword load/store: 8-bit offset, scaled by 4. */
24724 if (value >= 0)
24725 newval |= (1 << 23);
24726 else
24727 value = -value;
24728 if (value % 4 != 0)
24729 {
24730 as_bad_where (fixP->fx_file, fixP->fx_line,
24731 _("offset not a multiple of 4"));
24732 break;
24733 }
24734 value /= 4;
216d22bc 24735 if (value > 0xff)
c19d1205
ZW
24736 {
24737 as_bad_where (fixP->fx_file, fixP->fx_line,
24738 _("offset out of range"));
24739 break;
24740 }
24741 newval &= ~0xff;
b99bd4ef 24742 }
c19d1205 24743 else if ((newval & 0x000f0000) == 0x000f0000)
b99bd4ef 24744 {
c19d1205
ZW
24745 /* PC-relative, 12-bit offset. */
24746 if (value >= 0)
24747 newval |= (1 << 23);
24748 else
24749 value = -value;
216d22bc 24750 if (value > 0xfff)
c19d1205
ZW
24751 {
24752 as_bad_where (fixP->fx_file, fixP->fx_line,
24753 _("offset out of range"));
24754 break;
24755 }
24756 newval &= ~0xfff;
b99bd4ef 24757 }
c19d1205 24758 else if ((newval & 0x00000100) == 0x00000100)
b99bd4ef 24759 {
c19d1205
ZW
24760 /* Writeback: 8-bit, +/- offset. */
24761 if (value >= 0)
24762 newval |= (1 << 9);
24763 else
24764 value = -value;
216d22bc 24765 if (value > 0xff)
c19d1205
ZW
24766 {
24767 as_bad_where (fixP->fx_file, fixP->fx_line,
24768 _("offset out of range"));
24769 break;
24770 }
24771 newval &= ~0xff;
b99bd4ef 24772 }
c19d1205 24773 else if ((newval & 0x00000f00) == 0x00000e00)
b99bd4ef 24774 {
c19d1205 24775 /* T-instruction: positive 8-bit offset. */
216d22bc 24776 if (value < 0 || value > 0xff)
b99bd4ef 24777 {
c19d1205
ZW
24778 as_bad_where (fixP->fx_file, fixP->fx_line,
24779 _("offset out of range"));
24780 break;
b99bd4ef 24781 }
c19d1205
ZW
24782 newval &= ~0xff;
24783 newval |= value;
b99bd4ef
NC
24784 }
24785 else
b99bd4ef 24786 {
c19d1205
ZW
24787 /* Positive 12-bit or negative 8-bit offset. */
24788 int limit;
24789 if (value >= 0)
b99bd4ef 24790 {
c19d1205
ZW
24791 newval |= (1 << 23);
24792 limit = 0xfff;
24793 }
24794 else
24795 {
24796 value = -value;
24797 limit = 0xff;
24798 }
24799 if (value > limit)
24800 {
24801 as_bad_where (fixP->fx_file, fixP->fx_line,
24802 _("offset out of range"));
24803 break;
b99bd4ef 24804 }
c19d1205 24805 newval &= ~limit;
b99bd4ef 24806 }
b99bd4ef 24807
c19d1205
ZW
24808 newval |= value;
24809 md_number_to_chars (buf, (newval >> 16) & 0xffff, THUMB_SIZE);
24810 md_number_to_chars (buf + THUMB_SIZE, newval & 0xffff, THUMB_SIZE);
24811 break;
404ff6b5 24812
c19d1205
ZW
24813 case BFD_RELOC_ARM_SHIFT_IMM:
24814 newval = md_chars_to_number (buf, INSN_SIZE);
24815 if (((unsigned long) value) > 32
24816 || (value == 32
24817 && (((newval & 0x60) == 0) || (newval & 0x60) == 0x60)))
24818 {
24819 as_bad_where (fixP->fx_file, fixP->fx_line,
24820 _("shift expression is too large"));
24821 break;
24822 }
404ff6b5 24823
c19d1205
ZW
24824 if (value == 0)
24825 /* Shifts of zero must be done as lsl. */
24826 newval &= ~0x60;
24827 else if (value == 32)
24828 value = 0;
24829 newval &= 0xfffff07f;
24830 newval |= (value & 0x1f) << 7;
24831 md_number_to_chars (buf, newval, INSN_SIZE);
24832 break;
404ff6b5 24833
c19d1205 24834 case BFD_RELOC_ARM_T32_IMMEDIATE:
16805f35 24835 case BFD_RELOC_ARM_T32_ADD_IMM:
92e90b6e 24836 case BFD_RELOC_ARM_T32_IMM12:
e9f89963 24837 case BFD_RELOC_ARM_T32_ADD_PC12:
c19d1205
ZW
24838 /* We claim that this fixup has been processed here,
24839 even if in fact we generate an error because we do
24840 not have a reloc for it, so tc_gen_reloc will reject it. */
24841 fixP->fx_done = 1;
404ff6b5 24842
c19d1205
ZW
24843 if (fixP->fx_addsy
24844 && ! S_IS_DEFINED (fixP->fx_addsy))
24845 {
24846 as_bad_where (fixP->fx_file, fixP->fx_line,
24847 _("undefined symbol %s used as an immediate value"),
24848 S_GET_NAME (fixP->fx_addsy));
24849 break;
24850 }
404ff6b5 24851
c19d1205
ZW
24852 newval = md_chars_to_number (buf, THUMB_SIZE);
24853 newval <<= 16;
24854 newval |= md_chars_to_number (buf+2, THUMB_SIZE);
404ff6b5 24855
16805f35 24856 newimm = FAIL;
bada4342
JW
24857 if ((fixP->fx_r_type == BFD_RELOC_ARM_T32_IMMEDIATE
24858 /* ARMv8-M Baseline MOV will reach here, but it doesn't support
24859 Thumb2 modified immediate encoding (T2). */
24860 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6t2))
16805f35 24861 || fixP->fx_r_type == BFD_RELOC_ARM_T32_ADD_IMM)
ef8d22e6
PB
24862 {
24863 newimm = encode_thumb32_immediate (value);
24864 if (newimm == (unsigned int) FAIL)
24865 newimm = thumb32_negate_data_op (&newval, value);
24866 }
bada4342 24867 if (newimm == (unsigned int) FAIL)
92e90b6e 24868 {
bada4342 24869 if (fixP->fx_r_type != BFD_RELOC_ARM_T32_IMMEDIATE)
e9f89963 24870 {
bada4342
JW
24871 /* Turn add/sum into addw/subw. */
24872 if (fixP->fx_r_type == BFD_RELOC_ARM_T32_ADD_IMM)
24873 newval = (newval & 0xfeffffff) | 0x02000000;
24874 /* No flat 12-bit imm encoding for addsw/subsw. */
24875 if ((newval & 0x00100000) == 0)
40f246e3 24876 {
bada4342
JW
24877 /* 12 bit immediate for addw/subw. */
24878 if (value < 0)
24879 {
24880 value = -value;
24881 newval ^= 0x00a00000;
24882 }
24883 if (value > 0xfff)
24884 newimm = (unsigned int) FAIL;
24885 else
24886 newimm = value;
24887 }
24888 }
24889 else
24890 {
24891 /* MOV accepts both Thumb2 modified immediate (T2 encoding) and
24892 UINT16 (T3 encoding), MOVW only accepts UINT16. When
24893 disassembling, MOV is preferred when there is no encoding
db7bf105 24894 overlap. */
bada4342 24895 if (((newval >> T2_DATA_OP_SHIFT) & 0xf) == T2_OPCODE_ORR
db7bf105
NC
24896 /* NOTE: MOV uses the ORR opcode in Thumb 2 mode
24897 but with the Rn field [19:16] set to 1111. */
24898 && (((newval >> 16) & 0xf) == 0xf)
bada4342
JW
24899 && ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6t2_v8m)
24900 && !((newval >> T2_SBIT_SHIFT) & 0x1)
db7bf105 24901 && value >= 0 && value <= 0xffff)
bada4342
JW
24902 {
24903 /* Toggle bit[25] to change encoding from T2 to T3. */
24904 newval ^= 1 << 25;
24905 /* Clear bits[19:16]. */
24906 newval &= 0xfff0ffff;
24907 /* Encoding high 4bits imm. Code below will encode the
24908 remaining low 12bits. */
24909 newval |= (value & 0x0000f000) << 4;
24910 newimm = value & 0x00000fff;
40f246e3 24911 }
e9f89963 24912 }
92e90b6e 24913 }
cc8a6dd0 24914
c19d1205 24915 if (newimm == (unsigned int)FAIL)
3631a3c8 24916 {
c19d1205
ZW
24917 as_bad_where (fixP->fx_file, fixP->fx_line,
24918 _("invalid constant (%lx) after fixup"),
24919 (unsigned long) value);
24920 break;
3631a3c8
NC
24921 }
24922
c19d1205
ZW
24923 newval |= (newimm & 0x800) << 15;
24924 newval |= (newimm & 0x700) << 4;
24925 newval |= (newimm & 0x0ff);
cc8a6dd0 24926
c19d1205
ZW
24927 md_number_to_chars (buf, (valueT) ((newval >> 16) & 0xffff), THUMB_SIZE);
24928 md_number_to_chars (buf+2, (valueT) (newval & 0xffff), THUMB_SIZE);
24929 break;
a737bd4d 24930
3eb17e6b 24931 case BFD_RELOC_ARM_SMC:
c19d1205
ZW
24932 if (((unsigned long) value) > 0xffff)
24933 as_bad_where (fixP->fx_file, fixP->fx_line,
3eb17e6b 24934 _("invalid smc expression"));
2fc8bdac 24935 newval = md_chars_to_number (buf, INSN_SIZE);
c19d1205
ZW
24936 newval |= (value & 0xf) | ((value & 0xfff0) << 4);
24937 md_number_to_chars (buf, newval, INSN_SIZE);
24938 break;
a737bd4d 24939
90ec0d68
MGD
24940 case BFD_RELOC_ARM_HVC:
24941 if (((unsigned long) value) > 0xffff)
24942 as_bad_where (fixP->fx_file, fixP->fx_line,
24943 _("invalid hvc expression"));
24944 newval = md_chars_to_number (buf, INSN_SIZE);
24945 newval |= (value & 0xf) | ((value & 0xfff0) << 4);
24946 md_number_to_chars (buf, newval, INSN_SIZE);
24947 break;
24948
c19d1205 24949 case BFD_RELOC_ARM_SWI:
adbaf948 24950 if (fixP->tc_fix_data != 0)
c19d1205
ZW
24951 {
24952 if (((unsigned long) value) > 0xff)
24953 as_bad_where (fixP->fx_file, fixP->fx_line,
24954 _("invalid swi expression"));
2fc8bdac 24955 newval = md_chars_to_number (buf, THUMB_SIZE);
c19d1205
ZW
24956 newval |= value;
24957 md_number_to_chars (buf, newval, THUMB_SIZE);
24958 }
24959 else
24960 {
24961 if (((unsigned long) value) > 0x00ffffff)
24962 as_bad_where (fixP->fx_file, fixP->fx_line,
24963 _("invalid swi expression"));
2fc8bdac 24964 newval = md_chars_to_number (buf, INSN_SIZE);
c19d1205
ZW
24965 newval |= value;
24966 md_number_to_chars (buf, newval, INSN_SIZE);
24967 }
24968 break;
a737bd4d 24969
c19d1205
ZW
24970 case BFD_RELOC_ARM_MULTI:
24971 if (((unsigned long) value) > 0xffff)
24972 as_bad_where (fixP->fx_file, fixP->fx_line,
24973 _("invalid expression in load/store multiple"));
24974 newval = value | md_chars_to_number (buf, INSN_SIZE);
24975 md_number_to_chars (buf, newval, INSN_SIZE);
24976 break;
a737bd4d 24977
c19d1205 24978#ifdef OBJ_ELF
39b41c9c 24979 case BFD_RELOC_ARM_PCREL_CALL:
267bf995
RR
24980
24981 if (ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t)
24982 && fixP->fx_addsy
34e77a92 24983 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
267bf995
RR
24984 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
24985 && THUMB_IS_FUNC (fixP->fx_addsy))
24986 /* Flip the bl to blx. This is a simple flip
24987 bit here because we generate PCREL_CALL for
24988 unconditional bls. */
24989 {
24990 newval = md_chars_to_number (buf, INSN_SIZE);
24991 newval = newval | 0x10000000;
24992 md_number_to_chars (buf, newval, INSN_SIZE);
24993 temp = 1;
24994 fixP->fx_done = 1;
24995 }
39b41c9c
PB
24996 else
24997 temp = 3;
24998 goto arm_branch_common;
24999
25000 case BFD_RELOC_ARM_PCREL_JUMP:
267bf995
RR
25001 if (ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t)
25002 && fixP->fx_addsy
34e77a92 25003 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
267bf995
RR
25004 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
25005 && THUMB_IS_FUNC (fixP->fx_addsy))
25006 {
25007 /* This would map to a bl<cond>, b<cond>,
25008 b<always> to a Thumb function. We
25009 need to force a relocation for this particular
25010 case. */
25011 newval = md_chars_to_number (buf, INSN_SIZE);
25012 fixP->fx_done = 0;
25013 }
1a0670f3 25014 /* Fall through. */
267bf995 25015
2fc8bdac 25016 case BFD_RELOC_ARM_PLT32:
c19d1205 25017#endif
39b41c9c
PB
25018 case BFD_RELOC_ARM_PCREL_BRANCH:
25019 temp = 3;
25020 goto arm_branch_common;
a737bd4d 25021
39b41c9c 25022 case BFD_RELOC_ARM_PCREL_BLX:
267bf995 25023
39b41c9c 25024 temp = 1;
267bf995
RR
25025 if (ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t)
25026 && fixP->fx_addsy
34e77a92 25027 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
267bf995
RR
25028 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
25029 && ARM_IS_FUNC (fixP->fx_addsy))
25030 {
25031 /* Flip the blx to a bl and warn. */
25032 const char *name = S_GET_NAME (fixP->fx_addsy);
25033 newval = 0xeb000000;
25034 as_warn_where (fixP->fx_file, fixP->fx_line,
25035 _("blx to '%s' an ARM ISA state function changed to bl"),
25036 name);
25037 md_number_to_chars (buf, newval, INSN_SIZE);
25038 temp = 3;
25039 fixP->fx_done = 1;
25040 }
25041
25042#ifdef OBJ_ELF
25043 if (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4)
477330fc 25044 fixP->fx_r_type = BFD_RELOC_ARM_PCREL_CALL;
267bf995
RR
25045#endif
25046
39b41c9c 25047 arm_branch_common:
c19d1205 25048 /* We are going to store value (shifted right by two) in the
39b41c9c
PB
25049 instruction, in a 24 bit, signed field. Bits 26 through 32 either
25050 all clear or all set and bit 0 must be clear. For B/BL bit 1 must
de194d85 25051 also be clear. */
39b41c9c 25052 if (value & temp)
c19d1205 25053 as_bad_where (fixP->fx_file, fixP->fx_line,
2fc8bdac
ZW
25054 _("misaligned branch destination"));
25055 if ((value & (offsetT)0xfe000000) != (offsetT)0
25056 && (value & (offsetT)0xfe000000) != (offsetT)0xfe000000)
08f10d51 25057 as_bad_where (fixP->fx_file, fixP->fx_line, BAD_RANGE);
a737bd4d 25058
2fc8bdac 25059 if (fixP->fx_done || !seg->use_rela_p)
c19d1205 25060 {
2fc8bdac
ZW
25061 newval = md_chars_to_number (buf, INSN_SIZE);
25062 newval |= (value >> 2) & 0x00ffffff;
7ae2971b
PB
25063 /* Set the H bit on BLX instructions. */
25064 if (temp == 1)
25065 {
25066 if (value & 2)
25067 newval |= 0x01000000;
25068 else
25069 newval &= ~0x01000000;
25070 }
2fc8bdac 25071 md_number_to_chars (buf, newval, INSN_SIZE);
c19d1205 25072 }
c19d1205 25073 break;
a737bd4d 25074
25fe350b
MS
25075 case BFD_RELOC_THUMB_PCREL_BRANCH7: /* CBZ */
25076 /* CBZ can only branch forward. */
a737bd4d 25077
738755b0 25078 /* Attempts to use CBZ to branch to the next instruction
477330fc
RM
25079 (which, strictly speaking, are prohibited) will be turned into
25080 no-ops.
738755b0
MS
25081
25082 FIXME: It may be better to remove the instruction completely and
25083 perform relaxation. */
25084 if (value == -2)
2fc8bdac
ZW
25085 {
25086 newval = md_chars_to_number (buf, THUMB_SIZE);
738755b0 25087 newval = 0xbf00; /* NOP encoding T1 */
2fc8bdac
ZW
25088 md_number_to_chars (buf, newval, THUMB_SIZE);
25089 }
738755b0
MS
25090 else
25091 {
25092 if (value & ~0x7e)
08f10d51 25093 as_bad_where (fixP->fx_file, fixP->fx_line, BAD_RANGE);
738755b0 25094
477330fc 25095 if (fixP->fx_done || !seg->use_rela_p)
738755b0
MS
25096 {
25097 newval = md_chars_to_number (buf, THUMB_SIZE);
25098 newval |= ((value & 0x3e) << 2) | ((value & 0x40) << 3);
25099 md_number_to_chars (buf, newval, THUMB_SIZE);
25100 }
25101 }
c19d1205 25102 break;
a737bd4d 25103
c19d1205 25104 case BFD_RELOC_THUMB_PCREL_BRANCH9: /* Conditional branch. */
2fc8bdac 25105 if ((value & ~0xff) && ((value & ~0xff) != ~0xff))
08f10d51 25106 as_bad_where (fixP->fx_file, fixP->fx_line, BAD_RANGE);
a737bd4d 25107
2fc8bdac
ZW
25108 if (fixP->fx_done || !seg->use_rela_p)
25109 {
25110 newval = md_chars_to_number (buf, THUMB_SIZE);
25111 newval |= (value & 0x1ff) >> 1;
25112 md_number_to_chars (buf, newval, THUMB_SIZE);
25113 }
c19d1205 25114 break;
a737bd4d 25115
c19d1205 25116 case BFD_RELOC_THUMB_PCREL_BRANCH12: /* Unconditional branch. */
2fc8bdac 25117 if ((value & ~0x7ff) && ((value & ~0x7ff) != ~0x7ff))
08f10d51 25118 as_bad_where (fixP->fx_file, fixP->fx_line, BAD_RANGE);
a737bd4d 25119
2fc8bdac
ZW
25120 if (fixP->fx_done || !seg->use_rela_p)
25121 {
25122 newval = md_chars_to_number (buf, THUMB_SIZE);
25123 newval |= (value & 0xfff) >> 1;
25124 md_number_to_chars (buf, newval, THUMB_SIZE);
25125 }
c19d1205 25126 break;
a737bd4d 25127
c19d1205 25128 case BFD_RELOC_THUMB_PCREL_BRANCH20:
267bf995
RR
25129 if (fixP->fx_addsy
25130 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
34e77a92 25131 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
267bf995
RR
25132 && ARM_IS_FUNC (fixP->fx_addsy)
25133 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t))
25134 {
25135 /* Force a relocation for a branch 20 bits wide. */
25136 fixP->fx_done = 0;
25137 }
08f10d51 25138 if ((value & ~0x1fffff) && ((value & ~0x0fffff) != ~0x0fffff))
2fc8bdac
ZW
25139 as_bad_where (fixP->fx_file, fixP->fx_line,
25140 _("conditional branch out of range"));
404ff6b5 25141
2fc8bdac
ZW
25142 if (fixP->fx_done || !seg->use_rela_p)
25143 {
25144 offsetT newval2;
25145 addressT S, J1, J2, lo, hi;
404ff6b5 25146
2fc8bdac
ZW
25147 S = (value & 0x00100000) >> 20;
25148 J2 = (value & 0x00080000) >> 19;
25149 J1 = (value & 0x00040000) >> 18;
25150 hi = (value & 0x0003f000) >> 12;
25151 lo = (value & 0x00000ffe) >> 1;
6c43fab6 25152
2fc8bdac
ZW
25153 newval = md_chars_to_number (buf, THUMB_SIZE);
25154 newval2 = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE);
25155 newval |= (S << 10) | hi;
25156 newval2 |= (J1 << 13) | (J2 << 11) | lo;
25157 md_number_to_chars (buf, newval, THUMB_SIZE);
25158 md_number_to_chars (buf + THUMB_SIZE, newval2, THUMB_SIZE);
25159 }
c19d1205 25160 break;
6c43fab6 25161
c19d1205 25162 case BFD_RELOC_THUMB_PCREL_BLX:
267bf995
RR
25163 /* If there is a blx from a thumb state function to
25164 another thumb function flip this to a bl and warn
25165 about it. */
25166
25167 if (fixP->fx_addsy
34e77a92 25168 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
267bf995
RR
25169 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
25170 && THUMB_IS_FUNC (fixP->fx_addsy))
25171 {
25172 const char *name = S_GET_NAME (fixP->fx_addsy);
25173 as_warn_where (fixP->fx_file, fixP->fx_line,
25174 _("blx to Thumb func '%s' from Thumb ISA state changed to bl"),
25175 name);
25176 newval = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE);
25177 newval = newval | 0x1000;
25178 md_number_to_chars (buf+THUMB_SIZE, newval, THUMB_SIZE);
25179 fixP->fx_r_type = BFD_RELOC_THUMB_PCREL_BRANCH23;
25180 fixP->fx_done = 1;
25181 }
25182
25183
25184 goto thumb_bl_common;
25185
c19d1205 25186 case BFD_RELOC_THUMB_PCREL_BRANCH23:
267bf995
RR
25187 /* A bl from Thumb state ISA to an internal ARM state function
25188 is converted to a blx. */
25189 if (fixP->fx_addsy
25190 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
34e77a92 25191 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
267bf995
RR
25192 && ARM_IS_FUNC (fixP->fx_addsy)
25193 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t))
25194 {
25195 newval = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE);
25196 newval = newval & ~0x1000;
25197 md_number_to_chars (buf+THUMB_SIZE, newval, THUMB_SIZE);
25198 fixP->fx_r_type = BFD_RELOC_THUMB_PCREL_BLX;
25199 fixP->fx_done = 1;
25200 }
25201
25202 thumb_bl_common:
25203
2fc8bdac
ZW
25204 if (fixP->fx_r_type == BFD_RELOC_THUMB_PCREL_BLX)
25205 /* For a BLX instruction, make sure that the relocation is rounded up
25206 to a word boundary. This follows the semantics of the instruction
25207 which specifies that bit 1 of the target address will come from bit
25208 1 of the base address. */
d406f3e4
JB
25209 value = (value + 3) & ~ 3;
25210
25211#ifdef OBJ_ELF
25212 if (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4
25213 && fixP->fx_r_type == BFD_RELOC_THUMB_PCREL_BLX)
25214 fixP->fx_r_type = BFD_RELOC_THUMB_PCREL_BRANCH23;
25215#endif
404ff6b5 25216
2b2f5df9
NC
25217 if ((value & ~0x3fffff) && ((value & ~0x3fffff) != ~0x3fffff))
25218 {
fc289b0a 25219 if (!(ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v6t2)))
2b2f5df9
NC
25220 as_bad_where (fixP->fx_file, fixP->fx_line, BAD_RANGE);
25221 else if ((value & ~0x1ffffff)
25222 && ((value & ~0x1ffffff) != ~0x1ffffff))
25223 as_bad_where (fixP->fx_file, fixP->fx_line,
25224 _("Thumb2 branch out of range"));
25225 }
4a42ebbc
RR
25226
25227 if (fixP->fx_done || !seg->use_rela_p)
25228 encode_thumb2_b_bl_offset (buf, value);
25229
c19d1205 25230 break;
404ff6b5 25231
c19d1205 25232 case BFD_RELOC_THUMB_PCREL_BRANCH25:
08f10d51
NC
25233 if ((value & ~0x0ffffff) && ((value & ~0x0ffffff) != ~0x0ffffff))
25234 as_bad_where (fixP->fx_file, fixP->fx_line, BAD_RANGE);
6c43fab6 25235
2fc8bdac 25236 if (fixP->fx_done || !seg->use_rela_p)
4a42ebbc 25237 encode_thumb2_b_bl_offset (buf, value);
6c43fab6 25238
2fc8bdac 25239 break;
a737bd4d 25240
2fc8bdac
ZW
25241 case BFD_RELOC_8:
25242 if (fixP->fx_done || !seg->use_rela_p)
4b1a927e 25243 *buf = value;
c19d1205 25244 break;
a737bd4d 25245
c19d1205 25246 case BFD_RELOC_16:
2fc8bdac 25247 if (fixP->fx_done || !seg->use_rela_p)
c19d1205 25248 md_number_to_chars (buf, value, 2);
c19d1205 25249 break;
a737bd4d 25250
c19d1205 25251#ifdef OBJ_ELF
0855e32b
NS
25252 case BFD_RELOC_ARM_TLS_CALL:
25253 case BFD_RELOC_ARM_THM_TLS_CALL:
25254 case BFD_RELOC_ARM_TLS_DESCSEQ:
25255 case BFD_RELOC_ARM_THM_TLS_DESCSEQ:
0855e32b 25256 case BFD_RELOC_ARM_TLS_GOTDESC:
c19d1205
ZW
25257 case BFD_RELOC_ARM_TLS_GD32:
25258 case BFD_RELOC_ARM_TLS_LE32:
25259 case BFD_RELOC_ARM_TLS_IE32:
25260 case BFD_RELOC_ARM_TLS_LDM32:
25261 case BFD_RELOC_ARM_TLS_LDO32:
25262 S_SET_THREAD_LOCAL (fixP->fx_addsy);
4b1a927e 25263 break;
6c43fab6 25264
5c5a4843
CL
25265 /* Same handling as above, but with the arm_fdpic guard. */
25266 case BFD_RELOC_ARM_TLS_GD32_FDPIC:
25267 case BFD_RELOC_ARM_TLS_IE32_FDPIC:
25268 case BFD_RELOC_ARM_TLS_LDM32_FDPIC:
25269 if (arm_fdpic)
25270 {
25271 S_SET_THREAD_LOCAL (fixP->fx_addsy);
25272 }
25273 else
25274 {
25275 as_bad_where (fixP->fx_file, fixP->fx_line,
25276 _("Relocation supported only in FDPIC mode"));
25277 }
25278 break;
25279
c19d1205
ZW
25280 case BFD_RELOC_ARM_GOT32:
25281 case BFD_RELOC_ARM_GOTOFF:
c19d1205 25282 break;
b43420e6
NC
25283
25284 case BFD_RELOC_ARM_GOT_PREL:
25285 if (fixP->fx_done || !seg->use_rela_p)
477330fc 25286 md_number_to_chars (buf, value, 4);
b43420e6
NC
25287 break;
25288
9a6f4e97
NS
25289 case BFD_RELOC_ARM_TARGET2:
25290 /* TARGET2 is not partial-inplace, so we need to write the
477330fc
RM
25291 addend here for REL targets, because it won't be written out
25292 during reloc processing later. */
9a6f4e97
NS
25293 if (fixP->fx_done || !seg->use_rela_p)
25294 md_number_to_chars (buf, fixP->fx_offset, 4);
25295 break;
188fd7ae
CL
25296
25297 /* Relocations for FDPIC. */
25298 case BFD_RELOC_ARM_GOTFUNCDESC:
25299 case BFD_RELOC_ARM_GOTOFFFUNCDESC:
25300 case BFD_RELOC_ARM_FUNCDESC:
25301 if (arm_fdpic)
25302 {
25303 if (fixP->fx_done || !seg->use_rela_p)
25304 md_number_to_chars (buf, 0, 4);
25305 }
25306 else
25307 {
25308 as_bad_where (fixP->fx_file, fixP->fx_line,
25309 _("Relocation supported only in FDPIC mode"));
25310 }
25311 break;
c19d1205 25312#endif
6c43fab6 25313
c19d1205
ZW
25314 case BFD_RELOC_RVA:
25315 case BFD_RELOC_32:
25316 case BFD_RELOC_ARM_TARGET1:
25317 case BFD_RELOC_ARM_ROSEGREL32:
25318 case BFD_RELOC_ARM_SBREL32:
25319 case BFD_RELOC_32_PCREL:
f0927246
NC
25320#ifdef TE_PE
25321 case BFD_RELOC_32_SECREL:
25322#endif
2fc8bdac 25323 if (fixP->fx_done || !seg->use_rela_p)
53baae48
NC
25324#ifdef TE_WINCE
25325 /* For WinCE we only do this for pcrel fixups. */
25326 if (fixP->fx_done || fixP->fx_pcrel)
25327#endif
25328 md_number_to_chars (buf, value, 4);
c19d1205 25329 break;
6c43fab6 25330
c19d1205
ZW
25331#ifdef OBJ_ELF
25332 case BFD_RELOC_ARM_PREL31:
2fc8bdac 25333 if (fixP->fx_done || !seg->use_rela_p)
c19d1205
ZW
25334 {
25335 newval = md_chars_to_number (buf, 4) & 0x80000000;
25336 if ((value ^ (value >> 1)) & 0x40000000)
25337 {
25338 as_bad_where (fixP->fx_file, fixP->fx_line,
25339 _("rel31 relocation overflow"));
25340 }
25341 newval |= value & 0x7fffffff;
25342 md_number_to_chars (buf, newval, 4);
25343 }
25344 break;
c19d1205 25345#endif
a737bd4d 25346
c19d1205 25347 case BFD_RELOC_ARM_CP_OFF_IMM:
8f06b2d8 25348 case BFD_RELOC_ARM_T32_CP_OFF_IMM:
32c36c3c 25349 case BFD_RELOC_ARM_T32_VLDR_VSTR_OFF_IMM:
9db2f6b4
RL
25350 if (fixP->fx_r_type == BFD_RELOC_ARM_CP_OFF_IMM)
25351 newval = md_chars_to_number (buf, INSN_SIZE);
25352 else
25353 newval = get_thumb32_insn (buf);
25354 if ((newval & 0x0f200f00) == 0x0d000900)
25355 {
25356 /* This is a fp16 vstr/vldr. The immediate offset in the mnemonic
25357 has permitted values that are multiples of 2, in the range 0
25358 to 510. */
25359 if (value < -510 || value > 510 || (value & 1))
25360 as_bad_where (fixP->fx_file, fixP->fx_line,
25361 _("co-processor offset out of range"));
25362 }
32c36c3c
AV
25363 else if ((newval & 0xfe001f80) == 0xec000f80)
25364 {
25365 if (value < -511 || value > 512 || (value & 3))
25366 as_bad_where (fixP->fx_file, fixP->fx_line,
25367 _("co-processor offset out of range"));
25368 }
9db2f6b4 25369 else if (value < -1023 || value > 1023 || (value & 3))
c19d1205
ZW
25370 as_bad_where (fixP->fx_file, fixP->fx_line,
25371 _("co-processor offset out of range"));
25372 cp_off_common:
26d97720 25373 sign = value > 0;
c19d1205
ZW
25374 if (value < 0)
25375 value = -value;
8f06b2d8
PB
25376 if (fixP->fx_r_type == BFD_RELOC_ARM_CP_OFF_IMM
25377 || fixP->fx_r_type == BFD_RELOC_ARM_CP_OFF_IMM_S2)
25378 newval = md_chars_to_number (buf, INSN_SIZE);
25379 else
25380 newval = get_thumb32_insn (buf);
26d97720 25381 if (value == 0)
32c36c3c
AV
25382 {
25383 if (fixP->fx_r_type == BFD_RELOC_ARM_T32_VLDR_VSTR_OFF_IMM)
25384 newval &= 0xffffff80;
25385 else
25386 newval &= 0xffffff00;
25387 }
26d97720
NS
25388 else
25389 {
32c36c3c
AV
25390 if (fixP->fx_r_type == BFD_RELOC_ARM_T32_VLDR_VSTR_OFF_IMM)
25391 newval &= 0xff7fff80;
25392 else
25393 newval &= 0xff7fff00;
9db2f6b4
RL
25394 if ((newval & 0x0f200f00) == 0x0d000900)
25395 {
25396 /* This is a fp16 vstr/vldr.
25397
25398 It requires the immediate offset in the instruction is shifted
25399 left by 1 to be a half-word offset.
25400
25401 Here, left shift by 1 first, and later right shift by 2
25402 should get the right offset. */
25403 value <<= 1;
25404 }
26d97720
NS
25405 newval |= (value >> 2) | (sign ? INDEX_UP : 0);
25406 }
8f06b2d8
PB
25407 if (fixP->fx_r_type == BFD_RELOC_ARM_CP_OFF_IMM
25408 || fixP->fx_r_type == BFD_RELOC_ARM_CP_OFF_IMM_S2)
25409 md_number_to_chars (buf, newval, INSN_SIZE);
25410 else
25411 put_thumb32_insn (buf, newval);
c19d1205 25412 break;
a737bd4d 25413
c19d1205 25414 case BFD_RELOC_ARM_CP_OFF_IMM_S2:
8f06b2d8 25415 case BFD_RELOC_ARM_T32_CP_OFF_IMM_S2:
c19d1205
ZW
25416 if (value < -255 || value > 255)
25417 as_bad_where (fixP->fx_file, fixP->fx_line,
25418 _("co-processor offset out of range"));
df7849c5 25419 value *= 4;
c19d1205 25420 goto cp_off_common;
6c43fab6 25421
c19d1205
ZW
25422 case BFD_RELOC_ARM_THUMB_OFFSET:
25423 newval = md_chars_to_number (buf, THUMB_SIZE);
25424 /* Exactly what ranges, and where the offset is inserted depends
25425 on the type of instruction, we can establish this from the
25426 top 4 bits. */
25427 switch (newval >> 12)
25428 {
25429 case 4: /* PC load. */
25430 /* Thumb PC loads are somewhat odd, bit 1 of the PC is
25431 forced to zero for these loads; md_pcrel_from has already
25432 compensated for this. */
25433 if (value & 3)
25434 as_bad_where (fixP->fx_file, fixP->fx_line,
25435 _("invalid offset, target not word aligned (0x%08lX)"),
0359e808
NC
25436 (((unsigned long) fixP->fx_frag->fr_address
25437 + (unsigned long) fixP->fx_where) & ~3)
25438 + (unsigned long) value);
a737bd4d 25439
c19d1205
ZW
25440 if (value & ~0x3fc)
25441 as_bad_where (fixP->fx_file, fixP->fx_line,
25442 _("invalid offset, value too big (0x%08lX)"),
25443 (long) value);
a737bd4d 25444
c19d1205
ZW
25445 newval |= value >> 2;
25446 break;
a737bd4d 25447
c19d1205
ZW
25448 case 9: /* SP load/store. */
25449 if (value & ~0x3fc)
25450 as_bad_where (fixP->fx_file, fixP->fx_line,
25451 _("invalid offset, value too big (0x%08lX)"),
25452 (long) value);
25453 newval |= value >> 2;
25454 break;
6c43fab6 25455
c19d1205
ZW
25456 case 6: /* Word load/store. */
25457 if (value & ~0x7c)
25458 as_bad_where (fixP->fx_file, fixP->fx_line,
25459 _("invalid offset, value too big (0x%08lX)"),
25460 (long) value);
25461 newval |= value << 4; /* 6 - 2. */
25462 break;
a737bd4d 25463
c19d1205
ZW
25464 case 7: /* Byte load/store. */
25465 if (value & ~0x1f)
25466 as_bad_where (fixP->fx_file, fixP->fx_line,
25467 _("invalid offset, value too big (0x%08lX)"),
25468 (long) value);
25469 newval |= value << 6;
25470 break;
a737bd4d 25471
c19d1205
ZW
25472 case 8: /* Halfword load/store. */
25473 if (value & ~0x3e)
25474 as_bad_where (fixP->fx_file, fixP->fx_line,
25475 _("invalid offset, value too big (0x%08lX)"),
25476 (long) value);
25477 newval |= value << 5; /* 6 - 1. */
25478 break;
a737bd4d 25479
c19d1205
ZW
25480 default:
25481 as_bad_where (fixP->fx_file, fixP->fx_line,
25482 "Unable to process relocation for thumb opcode: %lx",
25483 (unsigned long) newval);
25484 break;
25485 }
25486 md_number_to_chars (buf, newval, THUMB_SIZE);
25487 break;
a737bd4d 25488
c19d1205
ZW
25489 case BFD_RELOC_ARM_THUMB_ADD:
25490 /* This is a complicated relocation, since we use it for all of
25491 the following immediate relocations:
a737bd4d 25492
c19d1205
ZW
25493 3bit ADD/SUB
25494 8bit ADD/SUB
25495 9bit ADD/SUB SP word-aligned
25496 10bit ADD PC/SP word-aligned
a737bd4d 25497
c19d1205
ZW
25498 The type of instruction being processed is encoded in the
25499 instruction field:
a737bd4d 25500
c19d1205
ZW
25501 0x8000 SUB
25502 0x00F0 Rd
25503 0x000F Rs
25504 */
25505 newval = md_chars_to_number (buf, THUMB_SIZE);
25506 {
25507 int rd = (newval >> 4) & 0xf;
25508 int rs = newval & 0xf;
25509 int subtract = !!(newval & 0x8000);
a737bd4d 25510
c19d1205
ZW
25511 /* Check for HI regs, only very restricted cases allowed:
25512 Adjusting SP, and using PC or SP to get an address. */
25513 if ((rd > 7 && (rd != REG_SP || rs != REG_SP))
25514 || (rs > 7 && rs != REG_SP && rs != REG_PC))
25515 as_bad_where (fixP->fx_file, fixP->fx_line,
25516 _("invalid Hi register with immediate"));
a737bd4d 25517
c19d1205
ZW
25518 /* If value is negative, choose the opposite instruction. */
25519 if (value < 0)
25520 {
25521 value = -value;
25522 subtract = !subtract;
25523 if (value < 0)
25524 as_bad_where (fixP->fx_file, fixP->fx_line,
25525 _("immediate value out of range"));
25526 }
a737bd4d 25527
c19d1205
ZW
25528 if (rd == REG_SP)
25529 {
75c11999 25530 if (value & ~0x1fc)
c19d1205
ZW
25531 as_bad_where (fixP->fx_file, fixP->fx_line,
25532 _("invalid immediate for stack address calculation"));
25533 newval = subtract ? T_OPCODE_SUB_ST : T_OPCODE_ADD_ST;
25534 newval |= value >> 2;
25535 }
25536 else if (rs == REG_PC || rs == REG_SP)
25537 {
c12d2c9d
NC
25538 /* PR gas/18541. If the addition is for a defined symbol
25539 within range of an ADR instruction then accept it. */
25540 if (subtract
25541 && value == 4
25542 && fixP->fx_addsy != NULL)
25543 {
25544 subtract = 0;
25545
25546 if (! S_IS_DEFINED (fixP->fx_addsy)
25547 || S_GET_SEGMENT (fixP->fx_addsy) != seg
25548 || S_IS_WEAK (fixP->fx_addsy))
25549 {
25550 as_bad_where (fixP->fx_file, fixP->fx_line,
25551 _("address calculation needs a strongly defined nearby symbol"));
25552 }
25553 else
25554 {
25555 offsetT v = fixP->fx_where + fixP->fx_frag->fr_address;
25556
25557 /* Round up to the next 4-byte boundary. */
25558 if (v & 3)
25559 v = (v + 3) & ~ 3;
25560 else
25561 v += 4;
25562 v = S_GET_VALUE (fixP->fx_addsy) - v;
25563
25564 if (v & ~0x3fc)
25565 {
25566 as_bad_where (fixP->fx_file, fixP->fx_line,
25567 _("symbol too far away"));
25568 }
25569 else
25570 {
25571 fixP->fx_done = 1;
25572 value = v;
25573 }
25574 }
25575 }
25576
c19d1205
ZW
25577 if (subtract || value & ~0x3fc)
25578 as_bad_where (fixP->fx_file, fixP->fx_line,
25579 _("invalid immediate for address calculation (value = 0x%08lX)"),
5fc177c8 25580 (unsigned long) (subtract ? - value : value));
c19d1205
ZW
25581 newval = (rs == REG_PC ? T_OPCODE_ADD_PC : T_OPCODE_ADD_SP);
25582 newval |= rd << 8;
25583 newval |= value >> 2;
25584 }
25585 else if (rs == rd)
25586 {
25587 if (value & ~0xff)
25588 as_bad_where (fixP->fx_file, fixP->fx_line,
25589 _("immediate value out of range"));
25590 newval = subtract ? T_OPCODE_SUB_I8 : T_OPCODE_ADD_I8;
25591 newval |= (rd << 8) | value;
25592 }
25593 else
25594 {
25595 if (value & ~0x7)
25596 as_bad_where (fixP->fx_file, fixP->fx_line,
25597 _("immediate value out of range"));
25598 newval = subtract ? T_OPCODE_SUB_I3 : T_OPCODE_ADD_I3;
25599 newval |= rd | (rs << 3) | (value << 6);
25600 }
25601 }
25602 md_number_to_chars (buf, newval, THUMB_SIZE);
25603 break;
a737bd4d 25604
c19d1205
ZW
25605 case BFD_RELOC_ARM_THUMB_IMM:
25606 newval = md_chars_to_number (buf, THUMB_SIZE);
25607 if (value < 0 || value > 255)
25608 as_bad_where (fixP->fx_file, fixP->fx_line,
4e6e072b 25609 _("invalid immediate: %ld is out of range"),
c19d1205
ZW
25610 (long) value);
25611 newval |= value;
25612 md_number_to_chars (buf, newval, THUMB_SIZE);
25613 break;
a737bd4d 25614
c19d1205
ZW
25615 case BFD_RELOC_ARM_THUMB_SHIFT:
25616 /* 5bit shift value (0..32). LSL cannot take 32. */
25617 newval = md_chars_to_number (buf, THUMB_SIZE) & 0xf83f;
25618 temp = newval & 0xf800;
25619 if (value < 0 || value > 32 || (value == 32 && temp == T_OPCODE_LSL_I))
25620 as_bad_where (fixP->fx_file, fixP->fx_line,
25621 _("invalid shift value: %ld"), (long) value);
25622 /* Shifts of zero must be encoded as LSL. */
25623 if (value == 0)
25624 newval = (newval & 0x003f) | T_OPCODE_LSL_I;
25625 /* Shifts of 32 are encoded as zero. */
25626 else if (value == 32)
25627 value = 0;
25628 newval |= value << 6;
25629 md_number_to_chars (buf, newval, THUMB_SIZE);
25630 break;
a737bd4d 25631
c19d1205
ZW
25632 case BFD_RELOC_VTABLE_INHERIT:
25633 case BFD_RELOC_VTABLE_ENTRY:
25634 fixP->fx_done = 0;
25635 return;
6c43fab6 25636
b6895b4f
PB
25637 case BFD_RELOC_ARM_MOVW:
25638 case BFD_RELOC_ARM_MOVT:
25639 case BFD_RELOC_ARM_THUMB_MOVW:
25640 case BFD_RELOC_ARM_THUMB_MOVT:
25641 if (fixP->fx_done || !seg->use_rela_p)
25642 {
25643 /* REL format relocations are limited to a 16-bit addend. */
25644 if (!fixP->fx_done)
25645 {
39623e12 25646 if (value < -0x8000 || value > 0x7fff)
b6895b4f 25647 as_bad_where (fixP->fx_file, fixP->fx_line,
ff5075ca 25648 _("offset out of range"));
b6895b4f
PB
25649 }
25650 else if (fixP->fx_r_type == BFD_RELOC_ARM_MOVT
25651 || fixP->fx_r_type == BFD_RELOC_ARM_THUMB_MOVT)
25652 {
25653 value >>= 16;
25654 }
25655
25656 if (fixP->fx_r_type == BFD_RELOC_ARM_THUMB_MOVW
25657 || fixP->fx_r_type == BFD_RELOC_ARM_THUMB_MOVT)
25658 {
25659 newval = get_thumb32_insn (buf);
25660 newval &= 0xfbf08f00;
25661 newval |= (value & 0xf000) << 4;
25662 newval |= (value & 0x0800) << 15;
25663 newval |= (value & 0x0700) << 4;
25664 newval |= (value & 0x00ff);
25665 put_thumb32_insn (buf, newval);
25666 }
25667 else
25668 {
25669 newval = md_chars_to_number (buf, 4);
25670 newval &= 0xfff0f000;
25671 newval |= value & 0x0fff;
25672 newval |= (value & 0xf000) << 4;
25673 md_number_to_chars (buf, newval, 4);
25674 }
25675 }
25676 return;
25677
72d98d16
MG
25678 case BFD_RELOC_ARM_THUMB_ALU_ABS_G0_NC:
25679 case BFD_RELOC_ARM_THUMB_ALU_ABS_G1_NC:
25680 case BFD_RELOC_ARM_THUMB_ALU_ABS_G2_NC:
25681 case BFD_RELOC_ARM_THUMB_ALU_ABS_G3_NC:
25682 gas_assert (!fixP->fx_done);
25683 {
25684 bfd_vma insn;
25685 bfd_boolean is_mov;
25686 bfd_vma encoded_addend = value;
25687
25688 /* Check that addend can be encoded in instruction. */
25689 if (!seg->use_rela_p && (value < 0 || value > 255))
25690 as_bad_where (fixP->fx_file, fixP->fx_line,
25691 _("the offset 0x%08lX is not representable"),
25692 (unsigned long) encoded_addend);
25693
25694 /* Extract the instruction. */
25695 insn = md_chars_to_number (buf, THUMB_SIZE);
25696 is_mov = (insn & 0xf800) == 0x2000;
25697
25698 /* Encode insn. */
25699 if (is_mov)
25700 {
25701 if (!seg->use_rela_p)
25702 insn |= encoded_addend;
25703 }
25704 else
25705 {
25706 int rd, rs;
25707
25708 /* Extract the instruction. */
25709 /* Encoding is the following
25710 0x8000 SUB
25711 0x00F0 Rd
25712 0x000F Rs
25713 */
25714 /* The following conditions must be true :
25715 - ADD
25716 - Rd == Rs
25717 - Rd <= 7
25718 */
25719 rd = (insn >> 4) & 0xf;
25720 rs = insn & 0xf;
25721 if ((insn & 0x8000) || (rd != rs) || rd > 7)
25722 as_bad_where (fixP->fx_file, fixP->fx_line,
25723 _("Unable to process relocation for thumb opcode: %lx"),
25724 (unsigned long) insn);
25725
25726 /* Encode as ADD immediate8 thumb 1 code. */
25727 insn = 0x3000 | (rd << 8);
25728
25729 /* Place the encoded addend into the first 8 bits of the
25730 instruction. */
25731 if (!seg->use_rela_p)
25732 insn |= encoded_addend;
25733 }
25734
25735 /* Update the instruction. */
25736 md_number_to_chars (buf, insn, THUMB_SIZE);
25737 }
25738 break;
25739
4962c51a
MS
25740 case BFD_RELOC_ARM_ALU_PC_G0_NC:
25741 case BFD_RELOC_ARM_ALU_PC_G0:
25742 case BFD_RELOC_ARM_ALU_PC_G1_NC:
25743 case BFD_RELOC_ARM_ALU_PC_G1:
25744 case BFD_RELOC_ARM_ALU_PC_G2:
25745 case BFD_RELOC_ARM_ALU_SB_G0_NC:
25746 case BFD_RELOC_ARM_ALU_SB_G0:
25747 case BFD_RELOC_ARM_ALU_SB_G1_NC:
25748 case BFD_RELOC_ARM_ALU_SB_G1:
25749 case BFD_RELOC_ARM_ALU_SB_G2:
9c2799c2 25750 gas_assert (!fixP->fx_done);
4962c51a
MS
25751 if (!seg->use_rela_p)
25752 {
477330fc
RM
25753 bfd_vma insn;
25754 bfd_vma encoded_addend;
3ca4a8ec 25755 bfd_vma addend_abs = llabs (value);
477330fc
RM
25756
25757 /* Check that the absolute value of the addend can be
25758 expressed as an 8-bit constant plus a rotation. */
25759 encoded_addend = encode_arm_immediate (addend_abs);
25760 if (encoded_addend == (unsigned int) FAIL)
4962c51a 25761 as_bad_where (fixP->fx_file, fixP->fx_line,
477330fc
RM
25762 _("the offset 0x%08lX is not representable"),
25763 (unsigned long) addend_abs);
25764
25765 /* Extract the instruction. */
25766 insn = md_chars_to_number (buf, INSN_SIZE);
25767
25768 /* If the addend is positive, use an ADD instruction.
25769 Otherwise use a SUB. Take care not to destroy the S bit. */
25770 insn &= 0xff1fffff;
25771 if (value < 0)
25772 insn |= 1 << 22;
25773 else
25774 insn |= 1 << 23;
25775
25776 /* Place the encoded addend into the first 12 bits of the
25777 instruction. */
25778 insn &= 0xfffff000;
25779 insn |= encoded_addend;
25780
25781 /* Update the instruction. */
25782 md_number_to_chars (buf, insn, INSN_SIZE);
4962c51a
MS
25783 }
25784 break;
25785
25786 case BFD_RELOC_ARM_LDR_PC_G0:
25787 case BFD_RELOC_ARM_LDR_PC_G1:
25788 case BFD_RELOC_ARM_LDR_PC_G2:
25789 case BFD_RELOC_ARM_LDR_SB_G0:
25790 case BFD_RELOC_ARM_LDR_SB_G1:
25791 case BFD_RELOC_ARM_LDR_SB_G2:
9c2799c2 25792 gas_assert (!fixP->fx_done);
4962c51a 25793 if (!seg->use_rela_p)
477330fc
RM
25794 {
25795 bfd_vma insn;
3ca4a8ec 25796 bfd_vma addend_abs = llabs (value);
4962c51a 25797
477330fc
RM
25798 /* Check that the absolute value of the addend can be
25799 encoded in 12 bits. */
25800 if (addend_abs >= 0x1000)
4962c51a 25801 as_bad_where (fixP->fx_file, fixP->fx_line,
477330fc
RM
25802 _("bad offset 0x%08lX (only 12 bits available for the magnitude)"),
25803 (unsigned long) addend_abs);
25804
25805 /* Extract the instruction. */
25806 insn = md_chars_to_number (buf, INSN_SIZE);
25807
25808 /* If the addend is negative, clear bit 23 of the instruction.
25809 Otherwise set it. */
25810 if (value < 0)
25811 insn &= ~(1 << 23);
25812 else
25813 insn |= 1 << 23;
25814
25815 /* Place the absolute value of the addend into the first 12 bits
25816 of the instruction. */
25817 insn &= 0xfffff000;
25818 insn |= addend_abs;
25819
25820 /* Update the instruction. */
25821 md_number_to_chars (buf, insn, INSN_SIZE);
25822 }
4962c51a
MS
25823 break;
25824
25825 case BFD_RELOC_ARM_LDRS_PC_G0:
25826 case BFD_RELOC_ARM_LDRS_PC_G1:
25827 case BFD_RELOC_ARM_LDRS_PC_G2:
25828 case BFD_RELOC_ARM_LDRS_SB_G0:
25829 case BFD_RELOC_ARM_LDRS_SB_G1:
25830 case BFD_RELOC_ARM_LDRS_SB_G2:
9c2799c2 25831 gas_assert (!fixP->fx_done);
4962c51a 25832 if (!seg->use_rela_p)
477330fc
RM
25833 {
25834 bfd_vma insn;
3ca4a8ec 25835 bfd_vma addend_abs = llabs (value);
4962c51a 25836
477330fc
RM
25837 /* Check that the absolute value of the addend can be
25838 encoded in 8 bits. */
25839 if (addend_abs >= 0x100)
4962c51a 25840 as_bad_where (fixP->fx_file, fixP->fx_line,
477330fc
RM
25841 _("bad offset 0x%08lX (only 8 bits available for the magnitude)"),
25842 (unsigned long) addend_abs);
25843
25844 /* Extract the instruction. */
25845 insn = md_chars_to_number (buf, INSN_SIZE);
25846
25847 /* If the addend is negative, clear bit 23 of the instruction.
25848 Otherwise set it. */
25849 if (value < 0)
25850 insn &= ~(1 << 23);
25851 else
25852 insn |= 1 << 23;
25853
25854 /* Place the first four bits of the absolute value of the addend
25855 into the first 4 bits of the instruction, and the remaining
25856 four into bits 8 .. 11. */
25857 insn &= 0xfffff0f0;
25858 insn |= (addend_abs & 0xf) | ((addend_abs & 0xf0) << 4);
25859
25860 /* Update the instruction. */
25861 md_number_to_chars (buf, insn, INSN_SIZE);
25862 }
4962c51a
MS
25863 break;
25864
25865 case BFD_RELOC_ARM_LDC_PC_G0:
25866 case BFD_RELOC_ARM_LDC_PC_G1:
25867 case BFD_RELOC_ARM_LDC_PC_G2:
25868 case BFD_RELOC_ARM_LDC_SB_G0:
25869 case BFD_RELOC_ARM_LDC_SB_G1:
25870 case BFD_RELOC_ARM_LDC_SB_G2:
9c2799c2 25871 gas_assert (!fixP->fx_done);
4962c51a 25872 if (!seg->use_rela_p)
477330fc
RM
25873 {
25874 bfd_vma insn;
3ca4a8ec 25875 bfd_vma addend_abs = llabs (value);
4962c51a 25876
477330fc
RM
25877 /* Check that the absolute value of the addend is a multiple of
25878 four and, when divided by four, fits in 8 bits. */
25879 if (addend_abs & 0x3)
4962c51a 25880 as_bad_where (fixP->fx_file, fixP->fx_line,
477330fc
RM
25881 _("bad offset 0x%08lX (must be word-aligned)"),
25882 (unsigned long) addend_abs);
4962c51a 25883
477330fc 25884 if ((addend_abs >> 2) > 0xff)
4962c51a 25885 as_bad_where (fixP->fx_file, fixP->fx_line,
477330fc
RM
25886 _("bad offset 0x%08lX (must be an 8-bit number of words)"),
25887 (unsigned long) addend_abs);
25888
25889 /* Extract the instruction. */
25890 insn = md_chars_to_number (buf, INSN_SIZE);
25891
25892 /* If the addend is negative, clear bit 23 of the instruction.
25893 Otherwise set it. */
25894 if (value < 0)
25895 insn &= ~(1 << 23);
25896 else
25897 insn |= 1 << 23;
25898
25899 /* Place the addend (divided by four) into the first eight
25900 bits of the instruction. */
25901 insn &= 0xfffffff0;
25902 insn |= addend_abs >> 2;
25903
25904 /* Update the instruction. */
25905 md_number_to_chars (buf, insn, INSN_SIZE);
25906 }
4962c51a
MS
25907 break;
25908
e12437dc
AV
25909 case BFD_RELOC_THUMB_PCREL_BRANCH5:
25910 if (fixP->fx_addsy
25911 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
25912 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
25913 && ARM_IS_FUNC (fixP->fx_addsy)
25914 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v8_1m_main))
25915 {
25916 /* Force a relocation for a branch 5 bits wide. */
25917 fixP->fx_done = 0;
25918 }
25919 if (v8_1_branch_value_check (value, 5, FALSE) == FAIL)
25920 as_bad_where (fixP->fx_file, fixP->fx_line,
25921 BAD_BRANCH_OFF);
25922
25923 if (fixP->fx_done || !seg->use_rela_p)
25924 {
25925 addressT boff = value >> 1;
25926
25927 newval = md_chars_to_number (buf, THUMB_SIZE);
25928 newval |= (boff << 7);
25929 md_number_to_chars (buf, newval, THUMB_SIZE);
25930 }
25931 break;
25932
f6b2b12d
AV
25933 case BFD_RELOC_THUMB_PCREL_BFCSEL:
25934 if (fixP->fx_addsy
25935 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
25936 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
25937 && ARM_IS_FUNC (fixP->fx_addsy)
25938 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v8_1m_main))
25939 {
25940 fixP->fx_done = 0;
25941 }
25942 if ((value & ~0x7f) && ((value & ~0x3f) != ~0x3f))
25943 as_bad_where (fixP->fx_file, fixP->fx_line,
25944 _("branch out of range"));
25945
25946 if (fixP->fx_done || !seg->use_rela_p)
25947 {
25948 newval = md_chars_to_number (buf, THUMB_SIZE);
25949
25950 addressT boff = ((newval & 0x0780) >> 7) << 1;
25951 addressT diff = value - boff;
25952
25953 if (diff == 4)
25954 {
25955 newval |= 1 << 1; /* T bit. */
25956 }
25957 else if (diff != 2)
25958 {
25959 as_bad_where (fixP->fx_file, fixP->fx_line,
25960 _("out of range label-relative fixup value"));
25961 }
25962 md_number_to_chars (buf, newval, THUMB_SIZE);
25963 }
25964 break;
25965
e5d6e09e
AV
25966 case BFD_RELOC_ARM_THUMB_BF17:
25967 if (fixP->fx_addsy
25968 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
25969 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
25970 && ARM_IS_FUNC (fixP->fx_addsy)
25971 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v8_1m_main))
25972 {
25973 /* Force a relocation for a branch 17 bits wide. */
25974 fixP->fx_done = 0;
25975 }
25976
25977 if (v8_1_branch_value_check (value, 17, TRUE) == FAIL)
25978 as_bad_where (fixP->fx_file, fixP->fx_line,
25979 BAD_BRANCH_OFF);
25980
25981 if (fixP->fx_done || !seg->use_rela_p)
25982 {
25983 offsetT newval2;
25984 addressT immA, immB, immC;
25985
25986 immA = (value & 0x0001f000) >> 12;
25987 immB = (value & 0x00000ffc) >> 2;
25988 immC = (value & 0x00000002) >> 1;
25989
25990 newval = md_chars_to_number (buf, THUMB_SIZE);
25991 newval2 = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE);
25992 newval |= immA;
25993 newval2 |= (immC << 11) | (immB << 1);
25994 md_number_to_chars (buf, newval, THUMB_SIZE);
25995 md_number_to_chars (buf + THUMB_SIZE, newval2, THUMB_SIZE);
25996 }
25997 break;
25998
1caf72a5
AV
25999 case BFD_RELOC_ARM_THUMB_BF19:
26000 if (fixP->fx_addsy
26001 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
26002 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
26003 && ARM_IS_FUNC (fixP->fx_addsy)
26004 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v8_1m_main))
26005 {
26006 /* Force a relocation for a branch 19 bits wide. */
26007 fixP->fx_done = 0;
26008 }
26009
26010 if (v8_1_branch_value_check (value, 19, TRUE) == FAIL)
26011 as_bad_where (fixP->fx_file, fixP->fx_line,
26012 BAD_BRANCH_OFF);
26013
26014 if (fixP->fx_done || !seg->use_rela_p)
26015 {
26016 offsetT newval2;
26017 addressT immA, immB, immC;
26018
26019 immA = (value & 0x0007f000) >> 12;
26020 immB = (value & 0x00000ffc) >> 2;
26021 immC = (value & 0x00000002) >> 1;
26022
26023 newval = md_chars_to_number (buf, THUMB_SIZE);
26024 newval2 = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE);
26025 newval |= immA;
26026 newval2 |= (immC << 11) | (immB << 1);
26027 md_number_to_chars (buf, newval, THUMB_SIZE);
26028 md_number_to_chars (buf + THUMB_SIZE, newval2, THUMB_SIZE);
26029 }
26030 break;
26031
1889da70
AV
26032 case BFD_RELOC_ARM_THUMB_BF13:
26033 if (fixP->fx_addsy
26034 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
26035 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
26036 && ARM_IS_FUNC (fixP->fx_addsy)
26037 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v8_1m_main))
26038 {
26039 /* Force a relocation for a branch 13 bits wide. */
26040 fixP->fx_done = 0;
26041 }
26042
26043 if (v8_1_branch_value_check (value, 13, TRUE) == FAIL)
26044 as_bad_where (fixP->fx_file, fixP->fx_line,
26045 BAD_BRANCH_OFF);
26046
26047 if (fixP->fx_done || !seg->use_rela_p)
26048 {
26049 offsetT newval2;
26050 addressT immA, immB, immC;
26051
26052 immA = (value & 0x00001000) >> 12;
26053 immB = (value & 0x00000ffc) >> 2;
26054 immC = (value & 0x00000002) >> 1;
26055
26056 newval = md_chars_to_number (buf, THUMB_SIZE);
26057 newval2 = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE);
26058 newval |= immA;
26059 newval2 |= (immC << 11) | (immB << 1);
26060 md_number_to_chars (buf, newval, THUMB_SIZE);
26061 md_number_to_chars (buf + THUMB_SIZE, newval2, THUMB_SIZE);
26062 }
26063 break;
26064
60f993ce
AV
26065 case BFD_RELOC_ARM_THUMB_LOOP12:
26066 if (fixP->fx_addsy
26067 && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
26068 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
26069 && ARM_IS_FUNC (fixP->fx_addsy)
26070 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v8_1m_main))
26071 {
26072 /* Force a relocation for a branch 12 bits wide. */
26073 fixP->fx_done = 0;
26074 }
26075
26076 bfd_vma insn = get_thumb32_insn (buf);
26077 /* le lr, <label> or le <label> */
26078 if (((insn & 0xffffffff) == 0xf00fc001)
26079 || ((insn & 0xffffffff) == 0xf02fc001))
26080 value = -value;
26081
26082 if (v8_1_branch_value_check (value, 12, FALSE) == FAIL)
26083 as_bad_where (fixP->fx_file, fixP->fx_line,
26084 BAD_BRANCH_OFF);
26085 if (fixP->fx_done || !seg->use_rela_p)
26086 {
26087 addressT imml, immh;
26088
26089 immh = (value & 0x00000ffc) >> 2;
26090 imml = (value & 0x00000002) >> 1;
26091
26092 newval = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE);
26093 newval |= (imml << 11) | (immh << 1);
26094 md_number_to_chars (buf + THUMB_SIZE, newval, THUMB_SIZE);
26095 }
26096 break;
26097
845b51d6
PB
26098 case BFD_RELOC_ARM_V4BX:
26099 /* This will need to go in the object file. */
26100 fixP->fx_done = 0;
26101 break;
26102
c19d1205
ZW
26103 case BFD_RELOC_UNUSED:
26104 default:
26105 as_bad_where (fixP->fx_file, fixP->fx_line,
26106 _("bad relocation fixup type (%d)"), fixP->fx_r_type);
26107 }
6c43fab6
RE
26108}
26109
c19d1205
ZW
26110/* Translate internal representation of relocation info to BFD target
26111 format. */
a737bd4d 26112
c19d1205 26113arelent *
00a97672 26114tc_gen_reloc (asection *section, fixS *fixp)
a737bd4d 26115{
c19d1205
ZW
26116 arelent * reloc;
26117 bfd_reloc_code_real_type code;
a737bd4d 26118
325801bd 26119 reloc = XNEW (arelent);
a737bd4d 26120
325801bd 26121 reloc->sym_ptr_ptr = XNEW (asymbol *);
c19d1205
ZW
26122 *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
26123 reloc->address = fixp->fx_frag->fr_address + fixp->fx_where;
a737bd4d 26124
2fc8bdac 26125 if (fixp->fx_pcrel)
00a97672
RS
26126 {
26127 if (section->use_rela_p)
26128 fixp->fx_offset -= md_pcrel_from_section (fixp, section);
26129 else
26130 fixp->fx_offset = reloc->address;
26131 }
c19d1205 26132 reloc->addend = fixp->fx_offset;
a737bd4d 26133
c19d1205 26134 switch (fixp->fx_r_type)
a737bd4d 26135 {
c19d1205
ZW
26136 case BFD_RELOC_8:
26137 if (fixp->fx_pcrel)
26138 {
26139 code = BFD_RELOC_8_PCREL;
26140 break;
26141 }
1a0670f3 26142 /* Fall through. */
a737bd4d 26143
c19d1205
ZW
26144 case BFD_RELOC_16:
26145 if (fixp->fx_pcrel)
26146 {
26147 code = BFD_RELOC_16_PCREL;
26148 break;
26149 }
1a0670f3 26150 /* Fall through. */
6c43fab6 26151
c19d1205
ZW
26152 case BFD_RELOC_32:
26153 if (fixp->fx_pcrel)
26154 {
26155 code = BFD_RELOC_32_PCREL;
26156 break;
26157 }
1a0670f3 26158 /* Fall through. */
a737bd4d 26159
b6895b4f
PB
26160 case BFD_RELOC_ARM_MOVW:
26161 if (fixp->fx_pcrel)
26162 {
26163 code = BFD_RELOC_ARM_MOVW_PCREL;
26164 break;
26165 }
1a0670f3 26166 /* Fall through. */
b6895b4f
PB
26167
26168 case BFD_RELOC_ARM_MOVT:
26169 if (fixp->fx_pcrel)
26170 {
26171 code = BFD_RELOC_ARM_MOVT_PCREL;
26172 break;
26173 }
1a0670f3 26174 /* Fall through. */
b6895b4f
PB
26175
26176 case BFD_RELOC_ARM_THUMB_MOVW:
26177 if (fixp->fx_pcrel)
26178 {
26179 code = BFD_RELOC_ARM_THUMB_MOVW_PCREL;
26180 break;
26181 }
1a0670f3 26182 /* Fall through. */
b6895b4f
PB
26183
26184 case BFD_RELOC_ARM_THUMB_MOVT:
26185 if (fixp->fx_pcrel)
26186 {
26187 code = BFD_RELOC_ARM_THUMB_MOVT_PCREL;
26188 break;
26189 }
1a0670f3 26190 /* Fall through. */
b6895b4f 26191
c19d1205
ZW
26192 case BFD_RELOC_NONE:
26193 case BFD_RELOC_ARM_PCREL_BRANCH:
26194 case BFD_RELOC_ARM_PCREL_BLX:
26195 case BFD_RELOC_RVA:
26196 case BFD_RELOC_THUMB_PCREL_BRANCH7:
26197 case BFD_RELOC_THUMB_PCREL_BRANCH9:
26198 case BFD_RELOC_THUMB_PCREL_BRANCH12:
26199 case BFD_RELOC_THUMB_PCREL_BRANCH20:
26200 case BFD_RELOC_THUMB_PCREL_BRANCH23:
26201 case BFD_RELOC_THUMB_PCREL_BRANCH25:
c19d1205
ZW
26202 case BFD_RELOC_VTABLE_ENTRY:
26203 case BFD_RELOC_VTABLE_INHERIT:
f0927246
NC
26204#ifdef TE_PE
26205 case BFD_RELOC_32_SECREL:
26206#endif
c19d1205
ZW
26207 code = fixp->fx_r_type;
26208 break;
a737bd4d 26209
00adf2d4
JB
26210 case BFD_RELOC_THUMB_PCREL_BLX:
26211#ifdef OBJ_ELF
26212 if (EF_ARM_EABI_VERSION (meabi_flags) >= EF_ARM_EABI_VER4)
26213 code = BFD_RELOC_THUMB_PCREL_BRANCH23;
26214 else
26215#endif
26216 code = BFD_RELOC_THUMB_PCREL_BLX;
26217 break;
26218
c19d1205
ZW
26219 case BFD_RELOC_ARM_LITERAL:
26220 case BFD_RELOC_ARM_HWLITERAL:
26221 /* If this is called then the a literal has
26222 been referenced across a section boundary. */
26223 as_bad_where (fixp->fx_file, fixp->fx_line,
26224 _("literal referenced across section boundary"));
26225 return NULL;
a737bd4d 26226
c19d1205 26227#ifdef OBJ_ELF
0855e32b
NS
26228 case BFD_RELOC_ARM_TLS_CALL:
26229 case BFD_RELOC_ARM_THM_TLS_CALL:
26230 case BFD_RELOC_ARM_TLS_DESCSEQ:
26231 case BFD_RELOC_ARM_THM_TLS_DESCSEQ:
c19d1205
ZW
26232 case BFD_RELOC_ARM_GOT32:
26233 case BFD_RELOC_ARM_GOTOFF:
b43420e6 26234 case BFD_RELOC_ARM_GOT_PREL:
c19d1205
ZW
26235 case BFD_RELOC_ARM_PLT32:
26236 case BFD_RELOC_ARM_TARGET1:
26237 case BFD_RELOC_ARM_ROSEGREL32:
26238 case BFD_RELOC_ARM_SBREL32:
26239 case BFD_RELOC_ARM_PREL31:
26240 case BFD_RELOC_ARM_TARGET2:
c19d1205 26241 case BFD_RELOC_ARM_TLS_LDO32:
39b41c9c
PB
26242 case BFD_RELOC_ARM_PCREL_CALL:
26243 case BFD_RELOC_ARM_PCREL_JUMP:
4962c51a
MS
26244 case BFD_RELOC_ARM_ALU_PC_G0_NC:
26245 case BFD_RELOC_ARM_ALU_PC_G0:
26246 case BFD_RELOC_ARM_ALU_PC_G1_NC:
26247 case BFD_RELOC_ARM_ALU_PC_G1:
26248 case BFD_RELOC_ARM_ALU_PC_G2:
26249 case BFD_RELOC_ARM_LDR_PC_G0:
26250 case BFD_RELOC_ARM_LDR_PC_G1:
26251 case BFD_RELOC_ARM_LDR_PC_G2:
26252 case BFD_RELOC_ARM_LDRS_PC_G0:
26253 case BFD_RELOC_ARM_LDRS_PC_G1:
26254 case BFD_RELOC_ARM_LDRS_PC_G2:
26255 case BFD_RELOC_ARM_LDC_PC_G0:
26256 case BFD_RELOC_ARM_LDC_PC_G1:
26257 case BFD_RELOC_ARM_LDC_PC_G2:
26258 case BFD_RELOC_ARM_ALU_SB_G0_NC:
26259 case BFD_RELOC_ARM_ALU_SB_G0:
26260 case BFD_RELOC_ARM_ALU_SB_G1_NC:
26261 case BFD_RELOC_ARM_ALU_SB_G1:
26262 case BFD_RELOC_ARM_ALU_SB_G2:
26263 case BFD_RELOC_ARM_LDR_SB_G0:
26264 case BFD_RELOC_ARM_LDR_SB_G1:
26265 case BFD_RELOC_ARM_LDR_SB_G2:
26266 case BFD_RELOC_ARM_LDRS_SB_G0:
26267 case BFD_RELOC_ARM_LDRS_SB_G1:
26268 case BFD_RELOC_ARM_LDRS_SB_G2:
26269 case BFD_RELOC_ARM_LDC_SB_G0:
26270 case BFD_RELOC_ARM_LDC_SB_G1:
26271 case BFD_RELOC_ARM_LDC_SB_G2:
845b51d6 26272 case BFD_RELOC_ARM_V4BX:
72d98d16
MG
26273 case BFD_RELOC_ARM_THUMB_ALU_ABS_G0_NC:
26274 case BFD_RELOC_ARM_THUMB_ALU_ABS_G1_NC:
26275 case BFD_RELOC_ARM_THUMB_ALU_ABS_G2_NC:
26276 case BFD_RELOC_ARM_THUMB_ALU_ABS_G3_NC:
188fd7ae
CL
26277 case BFD_RELOC_ARM_GOTFUNCDESC:
26278 case BFD_RELOC_ARM_GOTOFFFUNCDESC:
26279 case BFD_RELOC_ARM_FUNCDESC:
e5d6e09e 26280 case BFD_RELOC_ARM_THUMB_BF17:
1caf72a5 26281 case BFD_RELOC_ARM_THUMB_BF19:
1889da70 26282 case BFD_RELOC_ARM_THUMB_BF13:
c19d1205
ZW
26283 code = fixp->fx_r_type;
26284 break;
a737bd4d 26285
0855e32b 26286 case BFD_RELOC_ARM_TLS_GOTDESC:
c19d1205 26287 case BFD_RELOC_ARM_TLS_GD32:
5c5a4843 26288 case BFD_RELOC_ARM_TLS_GD32_FDPIC:
75c11999 26289 case BFD_RELOC_ARM_TLS_LE32:
c19d1205 26290 case BFD_RELOC_ARM_TLS_IE32:
5c5a4843 26291 case BFD_RELOC_ARM_TLS_IE32_FDPIC:
c19d1205 26292 case BFD_RELOC_ARM_TLS_LDM32:
5c5a4843 26293 case BFD_RELOC_ARM_TLS_LDM32_FDPIC:
c19d1205
ZW
26294 /* BFD will include the symbol's address in the addend.
26295 But we don't want that, so subtract it out again here. */
26296 if (!S_IS_COMMON (fixp->fx_addsy))
26297 reloc->addend -= (*reloc->sym_ptr_ptr)->value;
26298 code = fixp->fx_r_type;
26299 break;
26300#endif
a737bd4d 26301
c19d1205
ZW
26302 case BFD_RELOC_ARM_IMMEDIATE:
26303 as_bad_where (fixp->fx_file, fixp->fx_line,
26304 _("internal relocation (type: IMMEDIATE) not fixed up"));
26305 return NULL;
a737bd4d 26306
c19d1205
ZW
26307 case BFD_RELOC_ARM_ADRL_IMMEDIATE:
26308 as_bad_where (fixp->fx_file, fixp->fx_line,
26309 _("ADRL used for a symbol not defined in the same file"));
26310 return NULL;
a737bd4d 26311
e12437dc 26312 case BFD_RELOC_THUMB_PCREL_BRANCH5:
f6b2b12d 26313 case BFD_RELOC_THUMB_PCREL_BFCSEL:
60f993ce 26314 case BFD_RELOC_ARM_THUMB_LOOP12:
e12437dc
AV
26315 as_bad_where (fixp->fx_file, fixp->fx_line,
26316 _("%s used for a symbol not defined in the same file"),
26317 bfd_get_reloc_code_name (fixp->fx_r_type));
26318 return NULL;
26319
c19d1205 26320 case BFD_RELOC_ARM_OFFSET_IMM:
00a97672
RS
26321 if (section->use_rela_p)
26322 {
26323 code = fixp->fx_r_type;
26324 break;
26325 }
26326
c19d1205
ZW
26327 if (fixp->fx_addsy != NULL
26328 && !S_IS_DEFINED (fixp->fx_addsy)
26329 && S_IS_LOCAL (fixp->fx_addsy))
a737bd4d 26330 {
c19d1205
ZW
26331 as_bad_where (fixp->fx_file, fixp->fx_line,
26332 _("undefined local label `%s'"),
26333 S_GET_NAME (fixp->fx_addsy));
26334 return NULL;
a737bd4d
NC
26335 }
26336
c19d1205
ZW
26337 as_bad_where (fixp->fx_file, fixp->fx_line,
26338 _("internal_relocation (type: OFFSET_IMM) not fixed up"));
26339 return NULL;
a737bd4d 26340
c19d1205
ZW
26341 default:
26342 {
e0471c16 26343 const char * type;
6c43fab6 26344
c19d1205
ZW
26345 switch (fixp->fx_r_type)
26346 {
26347 case BFD_RELOC_NONE: type = "NONE"; break;
26348 case BFD_RELOC_ARM_OFFSET_IMM8: type = "OFFSET_IMM8"; break;
26349 case BFD_RELOC_ARM_SHIFT_IMM: type = "SHIFT_IMM"; break;
3eb17e6b 26350 case BFD_RELOC_ARM_SMC: type = "SMC"; break;
c19d1205
ZW
26351 case BFD_RELOC_ARM_SWI: type = "SWI"; break;
26352 case BFD_RELOC_ARM_MULTI: type = "MULTI"; break;
26353 case BFD_RELOC_ARM_CP_OFF_IMM: type = "CP_OFF_IMM"; break;
db187cb9 26354 case BFD_RELOC_ARM_T32_OFFSET_IMM: type = "T32_OFFSET_IMM"; break;
8f06b2d8 26355 case BFD_RELOC_ARM_T32_CP_OFF_IMM: type = "T32_CP_OFF_IMM"; break;
c19d1205
ZW
26356 case BFD_RELOC_ARM_THUMB_ADD: type = "THUMB_ADD"; break;
26357 case BFD_RELOC_ARM_THUMB_SHIFT: type = "THUMB_SHIFT"; break;
26358 case BFD_RELOC_ARM_THUMB_IMM: type = "THUMB_IMM"; break;
26359 case BFD_RELOC_ARM_THUMB_OFFSET: type = "THUMB_OFFSET"; break;
26360 default: type = _("<unknown>"); break;
26361 }
26362 as_bad_where (fixp->fx_file, fixp->fx_line,
26363 _("cannot represent %s relocation in this object file format"),
26364 type);
26365 return NULL;
26366 }
a737bd4d 26367 }
6c43fab6 26368
c19d1205
ZW
26369#ifdef OBJ_ELF
26370 if ((code == BFD_RELOC_32_PCREL || code == BFD_RELOC_32)
26371 && GOT_symbol
26372 && fixp->fx_addsy == GOT_symbol)
26373 {
26374 code = BFD_RELOC_ARM_GOTPC;
26375 reloc->addend = fixp->fx_offset = reloc->address;
26376 }
26377#endif
6c43fab6 26378
c19d1205 26379 reloc->howto = bfd_reloc_type_lookup (stdoutput, code);
6c43fab6 26380
c19d1205
ZW
26381 if (reloc->howto == NULL)
26382 {
26383 as_bad_where (fixp->fx_file, fixp->fx_line,
26384 _("cannot represent %s relocation in this object file format"),
26385 bfd_get_reloc_code_name (code));
26386 return NULL;
26387 }
6c43fab6 26388
c19d1205
ZW
26389 /* HACK: Since arm ELF uses Rel instead of Rela, encode the
26390 vtable entry to be used in the relocation's section offset. */
26391 if (fixp->fx_r_type == BFD_RELOC_VTABLE_ENTRY)
26392 reloc->address = fixp->fx_offset;
6c43fab6 26393
c19d1205 26394 return reloc;
6c43fab6
RE
26395}
26396
c19d1205 26397/* This fix_new is called by cons via TC_CONS_FIX_NEW. */
6c43fab6 26398
c19d1205
ZW
26399void
26400cons_fix_new_arm (fragS * frag,
26401 int where,
26402 int size,
62ebcb5c
AM
26403 expressionS * exp,
26404 bfd_reloc_code_real_type reloc)
6c43fab6 26405{
c19d1205 26406 int pcrel = 0;
6c43fab6 26407
c19d1205
ZW
26408 /* Pick a reloc.
26409 FIXME: @@ Should look at CPU word size. */
26410 switch (size)
26411 {
26412 case 1:
62ebcb5c 26413 reloc = BFD_RELOC_8;
c19d1205
ZW
26414 break;
26415 case 2:
62ebcb5c 26416 reloc = BFD_RELOC_16;
c19d1205
ZW
26417 break;
26418 case 4:
26419 default:
62ebcb5c 26420 reloc = BFD_RELOC_32;
c19d1205
ZW
26421 break;
26422 case 8:
62ebcb5c 26423 reloc = BFD_RELOC_64;
c19d1205
ZW
26424 break;
26425 }
6c43fab6 26426
f0927246
NC
26427#ifdef TE_PE
26428 if (exp->X_op == O_secrel)
26429 {
26430 exp->X_op = O_symbol;
62ebcb5c 26431 reloc = BFD_RELOC_32_SECREL;
f0927246
NC
26432 }
26433#endif
26434
62ebcb5c 26435 fix_new_exp (frag, where, size, exp, pcrel, reloc);
c19d1205 26436}
6c43fab6 26437
4343666d 26438#if defined (OBJ_COFF)
c19d1205
ZW
26439void
26440arm_validate_fix (fixS * fixP)
6c43fab6 26441{
c19d1205
ZW
26442 /* If the destination of the branch is a defined symbol which does not have
26443 the THUMB_FUNC attribute, then we must be calling a function which has
26444 the (interfacearm) attribute. We look for the Thumb entry point to that
26445 function and change the branch to refer to that function instead. */
26446 if (fixP->fx_r_type == BFD_RELOC_THUMB_PCREL_BRANCH23
26447 && fixP->fx_addsy != NULL
26448 && S_IS_DEFINED (fixP->fx_addsy)
26449 && ! THUMB_IS_FUNC (fixP->fx_addsy))
6c43fab6 26450 {
c19d1205 26451 fixP->fx_addsy = find_real_start (fixP->fx_addsy);
6c43fab6 26452 }
c19d1205
ZW
26453}
26454#endif
6c43fab6 26455
267bf995 26456
c19d1205
ZW
26457int
26458arm_force_relocation (struct fix * fixp)
26459{
26460#if defined (OBJ_COFF) && defined (TE_PE)
26461 if (fixp->fx_r_type == BFD_RELOC_RVA)
26462 return 1;
26463#endif
6c43fab6 26464
267bf995
RR
26465 /* In case we have a call or a branch to a function in ARM ISA mode from
26466 a thumb function or vice-versa force the relocation. These relocations
26467 are cleared off for some cores that might have blx and simple transformations
26468 are possible. */
26469
26470#ifdef OBJ_ELF
26471 switch (fixp->fx_r_type)
26472 {
26473 case BFD_RELOC_ARM_PCREL_JUMP:
26474 case BFD_RELOC_ARM_PCREL_CALL:
26475 case BFD_RELOC_THUMB_PCREL_BLX:
26476 if (THUMB_IS_FUNC (fixp->fx_addsy))
26477 return 1;
26478 break;
26479
26480 case BFD_RELOC_ARM_PCREL_BLX:
26481 case BFD_RELOC_THUMB_PCREL_BRANCH25:
26482 case BFD_RELOC_THUMB_PCREL_BRANCH20:
26483 case BFD_RELOC_THUMB_PCREL_BRANCH23:
26484 if (ARM_IS_FUNC (fixp->fx_addsy))
26485 return 1;
26486 break;
26487
26488 default:
26489 break;
26490 }
26491#endif
26492
b5884301
PB
26493 /* Resolve these relocations even if the symbol is extern or weak.
26494 Technically this is probably wrong due to symbol preemption.
26495 In practice these relocations do not have enough range to be useful
26496 at dynamic link time, and some code (e.g. in the Linux kernel)
26497 expects these references to be resolved. */
c19d1205
ZW
26498 if (fixp->fx_r_type == BFD_RELOC_ARM_IMMEDIATE
26499 || fixp->fx_r_type == BFD_RELOC_ARM_OFFSET_IMM
b5884301 26500 || fixp->fx_r_type == BFD_RELOC_ARM_OFFSET_IMM8
0110f2b8 26501 || fixp->fx_r_type == BFD_RELOC_ARM_ADRL_IMMEDIATE
b5884301
PB
26502 || fixp->fx_r_type == BFD_RELOC_ARM_CP_OFF_IMM
26503 || fixp->fx_r_type == BFD_RELOC_ARM_CP_OFF_IMM_S2
26504 || fixp->fx_r_type == BFD_RELOC_ARM_THUMB_OFFSET
16805f35 26505 || fixp->fx_r_type == BFD_RELOC_ARM_T32_ADD_IMM
0110f2b8
PB
26506 || fixp->fx_r_type == BFD_RELOC_ARM_T32_IMMEDIATE
26507 || fixp->fx_r_type == BFD_RELOC_ARM_T32_IMM12
b5884301
PB
26508 || fixp->fx_r_type == BFD_RELOC_ARM_T32_OFFSET_IMM
26509 || fixp->fx_r_type == BFD_RELOC_ARM_T32_ADD_PC12
26510 || fixp->fx_r_type == BFD_RELOC_ARM_T32_CP_OFF_IMM
26511 || fixp->fx_r_type == BFD_RELOC_ARM_T32_CP_OFF_IMM_S2)
c19d1205 26512 return 0;
a737bd4d 26513
4962c51a
MS
26514 /* Always leave these relocations for the linker. */
26515 if ((fixp->fx_r_type >= BFD_RELOC_ARM_ALU_PC_G0_NC
26516 && fixp->fx_r_type <= BFD_RELOC_ARM_LDC_SB_G2)
26517 || fixp->fx_r_type == BFD_RELOC_ARM_LDR_PC_G0)
26518 return 1;
26519
f0291e4c
PB
26520 /* Always generate relocations against function symbols. */
26521 if (fixp->fx_r_type == BFD_RELOC_32
26522 && fixp->fx_addsy
26523 && (symbol_get_bfdsym (fixp->fx_addsy)->flags & BSF_FUNCTION))
26524 return 1;
26525
c19d1205 26526 return generic_force_reloc (fixp);
404ff6b5
AH
26527}
26528
0ffdc86c 26529#if defined (OBJ_ELF) || defined (OBJ_COFF)
e28387c3
PB
26530/* Relocations against function names must be left unadjusted,
26531 so that the linker can use this information to generate interworking
26532 stubs. The MIPS version of this function
c19d1205
ZW
26533 also prevents relocations that are mips-16 specific, but I do not
26534 know why it does this.
404ff6b5 26535
c19d1205
ZW
26536 FIXME:
26537 There is one other problem that ought to be addressed here, but
26538 which currently is not: Taking the address of a label (rather
26539 than a function) and then later jumping to that address. Such
26540 addresses also ought to have their bottom bit set (assuming that
26541 they reside in Thumb code), but at the moment they will not. */
404ff6b5 26542
c19d1205
ZW
26543bfd_boolean
26544arm_fix_adjustable (fixS * fixP)
404ff6b5 26545{
c19d1205
ZW
26546 if (fixP->fx_addsy == NULL)
26547 return 1;
404ff6b5 26548
e28387c3
PB
26549 /* Preserve relocations against symbols with function type. */
26550 if (symbol_get_bfdsym (fixP->fx_addsy)->flags & BSF_FUNCTION)
c921be7d 26551 return FALSE;
e28387c3 26552
c19d1205
ZW
26553 if (THUMB_IS_FUNC (fixP->fx_addsy)
26554 && fixP->fx_subsy == NULL)
c921be7d 26555 return FALSE;
a737bd4d 26556
c19d1205
ZW
26557 /* We need the symbol name for the VTABLE entries. */
26558 if ( fixP->fx_r_type == BFD_RELOC_VTABLE_INHERIT
26559 || fixP->fx_r_type == BFD_RELOC_VTABLE_ENTRY)
c921be7d 26560 return FALSE;
404ff6b5 26561
c19d1205
ZW
26562 /* Don't allow symbols to be discarded on GOT related relocs. */
26563 if (fixP->fx_r_type == BFD_RELOC_ARM_PLT32
26564 || fixP->fx_r_type == BFD_RELOC_ARM_GOT32
26565 || fixP->fx_r_type == BFD_RELOC_ARM_GOTOFF
26566 || fixP->fx_r_type == BFD_RELOC_ARM_TLS_GD32
5c5a4843 26567 || fixP->fx_r_type == BFD_RELOC_ARM_TLS_GD32_FDPIC
c19d1205
ZW
26568 || fixP->fx_r_type == BFD_RELOC_ARM_TLS_LE32
26569 || fixP->fx_r_type == BFD_RELOC_ARM_TLS_IE32
5c5a4843 26570 || fixP->fx_r_type == BFD_RELOC_ARM_TLS_IE32_FDPIC
c19d1205 26571 || fixP->fx_r_type == BFD_RELOC_ARM_TLS_LDM32
5c5a4843 26572 || fixP->fx_r_type == BFD_RELOC_ARM_TLS_LDM32_FDPIC
c19d1205 26573 || fixP->fx_r_type == BFD_RELOC_ARM_TLS_LDO32
0855e32b
NS
26574 || fixP->fx_r_type == BFD_RELOC_ARM_TLS_GOTDESC
26575 || fixP->fx_r_type == BFD_RELOC_ARM_TLS_CALL
26576 || fixP->fx_r_type == BFD_RELOC_ARM_THM_TLS_CALL
26577 || fixP->fx_r_type == BFD_RELOC_ARM_TLS_DESCSEQ
26578 || fixP->fx_r_type == BFD_RELOC_ARM_THM_TLS_DESCSEQ
c19d1205 26579 || fixP->fx_r_type == BFD_RELOC_ARM_TARGET2)
c921be7d 26580 return FALSE;
a737bd4d 26581
4962c51a
MS
26582 /* Similarly for group relocations. */
26583 if ((fixP->fx_r_type >= BFD_RELOC_ARM_ALU_PC_G0_NC
26584 && fixP->fx_r_type <= BFD_RELOC_ARM_LDC_SB_G2)
26585 || fixP->fx_r_type == BFD_RELOC_ARM_LDR_PC_G0)
c921be7d 26586 return FALSE;
4962c51a 26587
79947c54
CD
26588 /* MOVW/MOVT REL relocations have limited offsets, so keep the symbols. */
26589 if (fixP->fx_r_type == BFD_RELOC_ARM_MOVW
26590 || fixP->fx_r_type == BFD_RELOC_ARM_MOVT
26591 || fixP->fx_r_type == BFD_RELOC_ARM_MOVW_PCREL
26592 || fixP->fx_r_type == BFD_RELOC_ARM_MOVT_PCREL
26593 || fixP->fx_r_type == BFD_RELOC_ARM_THUMB_MOVW
26594 || fixP->fx_r_type == BFD_RELOC_ARM_THUMB_MOVT
26595 || fixP->fx_r_type == BFD_RELOC_ARM_THUMB_MOVW_PCREL
26596 || fixP->fx_r_type == BFD_RELOC_ARM_THUMB_MOVT_PCREL)
c921be7d 26597 return FALSE;
79947c54 26598
72d98d16
MG
26599 /* BFD_RELOC_ARM_THUMB_ALU_ABS_Gx_NC relocations have VERY limited
26600 offsets, so keep these symbols. */
26601 if (fixP->fx_r_type >= BFD_RELOC_ARM_THUMB_ALU_ABS_G0_NC
26602 && fixP->fx_r_type <= BFD_RELOC_ARM_THUMB_ALU_ABS_G3_NC)
26603 return FALSE;
26604
c921be7d 26605 return TRUE;
a737bd4d 26606}
0ffdc86c
NC
26607#endif /* defined (OBJ_ELF) || defined (OBJ_COFF) */
26608
26609#ifdef OBJ_ELF
c19d1205
ZW
26610const char *
26611elf32_arm_target_format (void)
404ff6b5 26612{
c19d1205
ZW
26613#ifdef TE_SYMBIAN
26614 return (target_big_endian
26615 ? "elf32-bigarm-symbian"
26616 : "elf32-littlearm-symbian");
26617#elif defined (TE_VXWORKS)
26618 return (target_big_endian
26619 ? "elf32-bigarm-vxworks"
26620 : "elf32-littlearm-vxworks");
b38cadfb
NC
26621#elif defined (TE_NACL)
26622 return (target_big_endian
26623 ? "elf32-bigarm-nacl"
26624 : "elf32-littlearm-nacl");
c19d1205 26625#else
18a20338
CL
26626 if (arm_fdpic)
26627 {
26628 if (target_big_endian)
26629 return "elf32-bigarm-fdpic";
26630 else
26631 return "elf32-littlearm-fdpic";
26632 }
c19d1205 26633 else
18a20338
CL
26634 {
26635 if (target_big_endian)
26636 return "elf32-bigarm";
26637 else
26638 return "elf32-littlearm";
26639 }
c19d1205 26640#endif
404ff6b5
AH
26641}
26642
c19d1205
ZW
26643void
26644armelf_frob_symbol (symbolS * symp,
26645 int * puntp)
404ff6b5 26646{
c19d1205
ZW
26647 elf_frob_symbol (symp, puntp);
26648}
26649#endif
404ff6b5 26650
c19d1205 26651/* MD interface: Finalization. */
a737bd4d 26652
c19d1205
ZW
26653void
26654arm_cleanup (void)
26655{
26656 literal_pool * pool;
a737bd4d 26657
5ee91343
AV
26658 /* Ensure that all the predication blocks are properly closed. */
26659 check_pred_blocks_finished ();
e07e6e58 26660
c19d1205
ZW
26661 for (pool = list_of_pools; pool; pool = pool->next)
26662 {
5f4273c7 26663 /* Put it at the end of the relevant section. */
c19d1205
ZW
26664 subseg_set (pool->section, pool->sub_section);
26665#ifdef OBJ_ELF
26666 arm_elf_change_section ();
26667#endif
26668 s_ltorg (0);
26669 }
404ff6b5
AH
26670}
26671
cd000bff
DJ
26672#ifdef OBJ_ELF
26673/* Remove any excess mapping symbols generated for alignment frags in
26674 SEC. We may have created a mapping symbol before a zero byte
26675 alignment; remove it if there's a mapping symbol after the
26676 alignment. */
26677static void
26678check_mapping_symbols (bfd *abfd ATTRIBUTE_UNUSED, asection *sec,
26679 void *dummy ATTRIBUTE_UNUSED)
26680{
26681 segment_info_type *seginfo = seg_info (sec);
26682 fragS *fragp;
26683
26684 if (seginfo == NULL || seginfo->frchainP == NULL)
26685 return;
26686
26687 for (fragp = seginfo->frchainP->frch_root;
26688 fragp != NULL;
26689 fragp = fragp->fr_next)
26690 {
26691 symbolS *sym = fragp->tc_frag_data.last_map;
26692 fragS *next = fragp->fr_next;
26693
26694 /* Variable-sized frags have been converted to fixed size by
26695 this point. But if this was variable-sized to start with,
26696 there will be a fixed-size frag after it. So don't handle
26697 next == NULL. */
26698 if (sym == NULL || next == NULL)
26699 continue;
26700
26701 if (S_GET_VALUE (sym) < next->fr_address)
26702 /* Not at the end of this frag. */
26703 continue;
26704 know (S_GET_VALUE (sym) == next->fr_address);
26705
26706 do
26707 {
26708 if (next->tc_frag_data.first_map != NULL)
26709 {
26710 /* Next frag starts with a mapping symbol. Discard this
26711 one. */
26712 symbol_remove (sym, &symbol_rootP, &symbol_lastP);
26713 break;
26714 }
26715
26716 if (next->fr_next == NULL)
26717 {
26718 /* This mapping symbol is at the end of the section. Discard
26719 it. */
26720 know (next->fr_fix == 0 && next->fr_var == 0);
26721 symbol_remove (sym, &symbol_rootP, &symbol_lastP);
26722 break;
26723 }
26724
26725 /* As long as we have empty frags without any mapping symbols,
26726 keep looking. */
26727 /* If the next frag is non-empty and does not start with a
26728 mapping symbol, then this mapping symbol is required. */
26729 if (next->fr_address != next->fr_next->fr_address)
26730 break;
26731
26732 next = next->fr_next;
26733 }
26734 while (next != NULL);
26735 }
26736}
26737#endif
26738
c19d1205
ZW
26739/* Adjust the symbol table. This marks Thumb symbols as distinct from
26740 ARM ones. */
404ff6b5 26741
c19d1205
ZW
26742void
26743arm_adjust_symtab (void)
404ff6b5 26744{
c19d1205
ZW
26745#ifdef OBJ_COFF
26746 symbolS * sym;
404ff6b5 26747
c19d1205
ZW
26748 for (sym = symbol_rootP; sym != NULL; sym = symbol_next (sym))
26749 {
26750 if (ARM_IS_THUMB (sym))
26751 {
26752 if (THUMB_IS_FUNC (sym))
26753 {
26754 /* Mark the symbol as a Thumb function. */
26755 if ( S_GET_STORAGE_CLASS (sym) == C_STAT
26756 || S_GET_STORAGE_CLASS (sym) == C_LABEL) /* This can happen! */
26757 S_SET_STORAGE_CLASS (sym, C_THUMBSTATFUNC);
404ff6b5 26758
c19d1205
ZW
26759 else if (S_GET_STORAGE_CLASS (sym) == C_EXT)
26760 S_SET_STORAGE_CLASS (sym, C_THUMBEXTFUNC);
26761 else
26762 as_bad (_("%s: unexpected function type: %d"),
26763 S_GET_NAME (sym), S_GET_STORAGE_CLASS (sym));
26764 }
26765 else switch (S_GET_STORAGE_CLASS (sym))
26766 {
26767 case C_EXT:
26768 S_SET_STORAGE_CLASS (sym, C_THUMBEXT);
26769 break;
26770 case C_STAT:
26771 S_SET_STORAGE_CLASS (sym, C_THUMBSTAT);
26772 break;
26773 case C_LABEL:
26774 S_SET_STORAGE_CLASS (sym, C_THUMBLABEL);
26775 break;
26776 default:
26777 /* Do nothing. */
26778 break;
26779 }
26780 }
a737bd4d 26781
c19d1205
ZW
26782 if (ARM_IS_INTERWORK (sym))
26783 coffsymbol (symbol_get_bfdsym (sym))->native->u.syment.n_flags = 0xFF;
404ff6b5 26784 }
c19d1205
ZW
26785#endif
26786#ifdef OBJ_ELF
26787 symbolS * sym;
26788 char bind;
404ff6b5 26789
c19d1205 26790 for (sym = symbol_rootP; sym != NULL; sym = symbol_next (sym))
404ff6b5 26791 {
c19d1205
ZW
26792 if (ARM_IS_THUMB (sym))
26793 {
26794 elf_symbol_type * elf_sym;
404ff6b5 26795
c19d1205
ZW
26796 elf_sym = elf_symbol (symbol_get_bfdsym (sym));
26797 bind = ELF_ST_BIND (elf_sym->internal_elf_sym.st_info);
404ff6b5 26798
b0796911
PB
26799 if (! bfd_is_arm_special_symbol_name (elf_sym->symbol.name,
26800 BFD_ARM_SPECIAL_SYM_TYPE_ANY))
c19d1205
ZW
26801 {
26802 /* If it's a .thumb_func, declare it as so,
26803 otherwise tag label as .code 16. */
26804 if (THUMB_IS_FUNC (sym))
39d911fc
TP
26805 ARM_SET_SYM_BRANCH_TYPE (elf_sym->internal_elf_sym.st_target_internal,
26806 ST_BRANCH_TO_THUMB);
3ba67470 26807 else if (EF_ARM_EABI_VERSION (meabi_flags) < EF_ARM_EABI_VER4)
c19d1205
ZW
26808 elf_sym->internal_elf_sym.st_info =
26809 ELF_ST_INFO (bind, STT_ARM_16BIT);
26810 }
26811 }
26812 }
cd000bff
DJ
26813
26814 /* Remove any overlapping mapping symbols generated by alignment frags. */
26815 bfd_map_over_sections (stdoutput, check_mapping_symbols, (char *) 0);
709001e9
MM
26816 /* Now do generic ELF adjustments. */
26817 elf_adjust_symtab ();
c19d1205 26818#endif
404ff6b5
AH
26819}
26820
c19d1205 26821/* MD interface: Initialization. */
404ff6b5 26822
a737bd4d 26823static void
c19d1205 26824set_constant_flonums (void)
a737bd4d 26825{
c19d1205 26826 int i;
404ff6b5 26827
c19d1205
ZW
26828 for (i = 0; i < NUM_FLOAT_VALS; i++)
26829 if (atof_ieee ((char *) fp_const[i], 'x', fp_values[i]) == NULL)
26830 abort ();
a737bd4d 26831}
404ff6b5 26832
3e9e4fcf
JB
26833/* Auto-select Thumb mode if it's the only available instruction set for the
26834 given architecture. */
26835
26836static void
26837autoselect_thumb_from_cpu_variant (void)
26838{
26839 if (!ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v1))
26840 opcode_select (16);
26841}
26842
c19d1205
ZW
26843void
26844md_begin (void)
a737bd4d 26845{
c19d1205
ZW
26846 unsigned mach;
26847 unsigned int i;
404ff6b5 26848
c19d1205
ZW
26849 if ( (arm_ops_hsh = hash_new ()) == NULL
26850 || (arm_cond_hsh = hash_new ()) == NULL
5ee91343 26851 || (arm_vcond_hsh = hash_new ()) == NULL
c19d1205
ZW
26852 || (arm_shift_hsh = hash_new ()) == NULL
26853 || (arm_psr_hsh = hash_new ()) == NULL
62b3e311 26854 || (arm_v7m_psr_hsh = hash_new ()) == NULL
c19d1205 26855 || (arm_reg_hsh = hash_new ()) == NULL
62b3e311
PB
26856 || (arm_reloc_hsh = hash_new ()) == NULL
26857 || (arm_barrier_opt_hsh = hash_new ()) == NULL)
c19d1205
ZW
26858 as_fatal (_("virtual memory exhausted"));
26859
26860 for (i = 0; i < sizeof (insns) / sizeof (struct asm_opcode); i++)
d3ce72d0 26861 hash_insert (arm_ops_hsh, insns[i].template_name, (void *) (insns + i));
c19d1205 26862 for (i = 0; i < sizeof (conds) / sizeof (struct asm_cond); i++)
d3ce72d0 26863 hash_insert (arm_cond_hsh, conds[i].template_name, (void *) (conds + i));
5ee91343
AV
26864 for (i = 0; i < sizeof (vconds) / sizeof (struct asm_cond); i++)
26865 hash_insert (arm_vcond_hsh, vconds[i].template_name, (void *) (vconds + i));
c19d1205 26866 for (i = 0; i < sizeof (shift_names) / sizeof (struct asm_shift_name); i++)
5a49b8ac 26867 hash_insert (arm_shift_hsh, shift_names[i].name, (void *) (shift_names + i));
c19d1205 26868 for (i = 0; i < sizeof (psrs) / sizeof (struct asm_psr); i++)
d3ce72d0 26869 hash_insert (arm_psr_hsh, psrs[i].template_name, (void *) (psrs + i));
62b3e311 26870 for (i = 0; i < sizeof (v7m_psrs) / sizeof (struct asm_psr); i++)
d3ce72d0 26871 hash_insert (arm_v7m_psr_hsh, v7m_psrs[i].template_name,
477330fc 26872 (void *) (v7m_psrs + i));
c19d1205 26873 for (i = 0; i < sizeof (reg_names) / sizeof (struct reg_entry); i++)
5a49b8ac 26874 hash_insert (arm_reg_hsh, reg_names[i].name, (void *) (reg_names + i));
62b3e311
PB
26875 for (i = 0;
26876 i < sizeof (barrier_opt_names) / sizeof (struct asm_barrier_opt);
26877 i++)
d3ce72d0 26878 hash_insert (arm_barrier_opt_hsh, barrier_opt_names[i].template_name,
5a49b8ac 26879 (void *) (barrier_opt_names + i));
c19d1205 26880#ifdef OBJ_ELF
3da1d841
NC
26881 for (i = 0; i < ARRAY_SIZE (reloc_names); i++)
26882 {
26883 struct reloc_entry * entry = reloc_names + i;
26884
26885 if (arm_is_eabi() && entry->reloc == BFD_RELOC_ARM_PLT32)
26886 /* This makes encode_branch() use the EABI versions of this relocation. */
26887 entry->reloc = BFD_RELOC_UNUSED;
26888
26889 hash_insert (arm_reloc_hsh, entry->name, (void *) entry);
26890 }
c19d1205
ZW
26891#endif
26892
26893 set_constant_flonums ();
404ff6b5 26894
c19d1205
ZW
26895 /* Set the cpu variant based on the command-line options. We prefer
26896 -mcpu= over -march= if both are set (as for GCC); and we prefer
26897 -mfpu= over any other way of setting the floating point unit.
26898 Use of legacy options with new options are faulted. */
e74cfd16 26899 if (legacy_cpu)
404ff6b5 26900 {
e74cfd16 26901 if (mcpu_cpu_opt || march_cpu_opt)
c19d1205
ZW
26902 as_bad (_("use of old and new-style options to set CPU type"));
26903
4d354d8b 26904 selected_arch = *legacy_cpu;
404ff6b5 26905 }
4d354d8b
TP
26906 else if (mcpu_cpu_opt)
26907 {
26908 selected_arch = *mcpu_cpu_opt;
26909 selected_ext = *mcpu_ext_opt;
26910 }
26911 else if (march_cpu_opt)
c168ce07 26912 {
4d354d8b
TP
26913 selected_arch = *march_cpu_opt;
26914 selected_ext = *march_ext_opt;
c168ce07 26915 }
4d354d8b 26916 ARM_MERGE_FEATURE_SETS (selected_cpu, selected_arch, selected_ext);
404ff6b5 26917
e74cfd16 26918 if (legacy_fpu)
c19d1205 26919 {
e74cfd16 26920 if (mfpu_opt)
c19d1205 26921 as_bad (_("use of old and new-style options to set FPU type"));
03b1477f 26922
4d354d8b 26923 selected_fpu = *legacy_fpu;
03b1477f 26924 }
4d354d8b
TP
26925 else if (mfpu_opt)
26926 selected_fpu = *mfpu_opt;
26927 else
03b1477f 26928 {
45eb4c1b
NS
26929#if !(defined (EABI_DEFAULT) || defined (TE_LINUX) \
26930 || defined (TE_NetBSD) || defined (TE_VXWORKS))
39c2da32
RE
26931 /* Some environments specify a default FPU. If they don't, infer it
26932 from the processor. */
e74cfd16 26933 if (mcpu_fpu_opt)
4d354d8b 26934 selected_fpu = *mcpu_fpu_opt;
e7da50fa 26935 else if (march_fpu_opt)
4d354d8b 26936 selected_fpu = *march_fpu_opt;
39c2da32 26937#else
4d354d8b 26938 selected_fpu = fpu_default;
39c2da32 26939#endif
03b1477f
RE
26940 }
26941
4d354d8b 26942 if (ARM_FEATURE_ZERO (selected_fpu))
03b1477f 26943 {
4d354d8b
TP
26944 if (!no_cpu_selected ())
26945 selected_fpu = fpu_default;
03b1477f 26946 else
4d354d8b 26947 selected_fpu = fpu_arch_fpa;
03b1477f
RE
26948 }
26949
ee065d83 26950#ifdef CPU_DEFAULT
4d354d8b 26951 if (ARM_FEATURE_ZERO (selected_arch))
ee065d83 26952 {
4d354d8b
TP
26953 selected_arch = cpu_default;
26954 selected_cpu = selected_arch;
ee065d83 26955 }
4d354d8b 26956 ARM_MERGE_FEATURE_SETS (cpu_variant, selected_cpu, selected_fpu);
e74cfd16 26957#else
4d354d8b
TP
26958 /* Autodection of feature mode: allow all features in cpu_variant but leave
26959 selected_cpu unset. It will be set in aeabi_set_public_attributes ()
26960 after all instruction have been processed and we can decide what CPU
26961 should be selected. */
26962 if (ARM_FEATURE_ZERO (selected_arch))
26963 ARM_MERGE_FEATURE_SETS (cpu_variant, arm_arch_any, selected_fpu);
ee065d83 26964 else
4d354d8b 26965 ARM_MERGE_FEATURE_SETS (cpu_variant, selected_cpu, selected_fpu);
ee065d83 26966#endif
03b1477f 26967
3e9e4fcf
JB
26968 autoselect_thumb_from_cpu_variant ();
26969
e74cfd16 26970 arm_arch_used = thumb_arch_used = arm_arch_none;
ee065d83 26971
f17c130b 26972#if defined OBJ_COFF || defined OBJ_ELF
b99bd4ef 26973 {
7cc69913
NC
26974 unsigned int flags = 0;
26975
26976#if defined OBJ_ELF
26977 flags = meabi_flags;
d507cf36
PB
26978
26979 switch (meabi_flags)
33a392fb 26980 {
d507cf36 26981 case EF_ARM_EABI_UNKNOWN:
7cc69913 26982#endif
d507cf36
PB
26983 /* Set the flags in the private structure. */
26984 if (uses_apcs_26) flags |= F_APCS26;
26985 if (support_interwork) flags |= F_INTERWORK;
26986 if (uses_apcs_float) flags |= F_APCS_FLOAT;
c19d1205 26987 if (pic_code) flags |= F_PIC;
e74cfd16 26988 if (!ARM_CPU_HAS_FEATURE (cpu_variant, fpu_any_hard))
7cc69913
NC
26989 flags |= F_SOFT_FLOAT;
26990
d507cf36
PB
26991 switch (mfloat_abi_opt)
26992 {
26993 case ARM_FLOAT_ABI_SOFT:
26994 case ARM_FLOAT_ABI_SOFTFP:
26995 flags |= F_SOFT_FLOAT;
26996 break;
33a392fb 26997
d507cf36
PB
26998 case ARM_FLOAT_ABI_HARD:
26999 if (flags & F_SOFT_FLOAT)
27000 as_bad (_("hard-float conflicts with specified fpu"));
27001 break;
27002 }
03b1477f 27003
e74cfd16
PB
27004 /* Using pure-endian doubles (even if soft-float). */
27005 if (ARM_CPU_HAS_FEATURE (cpu_variant, fpu_endian_pure))
7cc69913 27006 flags |= F_VFP_FLOAT;
f17c130b 27007
fde78edd 27008#if defined OBJ_ELF
e74cfd16 27009 if (ARM_CPU_HAS_FEATURE (cpu_variant, fpu_arch_maverick))
d507cf36 27010 flags |= EF_ARM_MAVERICK_FLOAT;
d507cf36
PB
27011 break;
27012
8cb51566 27013 case EF_ARM_EABI_VER4:
3a4a14e9 27014 case EF_ARM_EABI_VER5:
c19d1205 27015 /* No additional flags to set. */
d507cf36
PB
27016 break;
27017
27018 default:
27019 abort ();
27020 }
7cc69913 27021#endif
b99bd4ef
NC
27022 bfd_set_private_flags (stdoutput, flags);
27023
27024 /* We have run out flags in the COFF header to encode the
27025 status of ATPCS support, so instead we create a dummy,
c19d1205 27026 empty, debug section called .arm.atpcs. */
b99bd4ef
NC
27027 if (atpcs)
27028 {
27029 asection * sec;
27030
27031 sec = bfd_make_section (stdoutput, ".arm.atpcs");
27032
27033 if (sec != NULL)
27034 {
27035 bfd_set_section_flags
27036 (stdoutput, sec, SEC_READONLY | SEC_DEBUGGING /* | SEC_HAS_CONTENTS */);
27037 bfd_set_section_size (stdoutput, sec, 0);
27038 bfd_set_section_contents (stdoutput, sec, NULL, 0, 0);
27039 }
27040 }
7cc69913 27041 }
f17c130b 27042#endif
b99bd4ef
NC
27043
27044 /* Record the CPU type as well. */
2d447fca
JM
27045 if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_cext_iwmmxt2))
27046 mach = bfd_mach_arm_iWMMXt2;
27047 else if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_cext_iwmmxt))
e16bb312 27048 mach = bfd_mach_arm_iWMMXt;
e74cfd16 27049 else if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_cext_xscale))
b99bd4ef 27050 mach = bfd_mach_arm_XScale;
e74cfd16 27051 else if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_cext_maverick))
fde78edd 27052 mach = bfd_mach_arm_ep9312;
e74cfd16 27053 else if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v5e))
b99bd4ef 27054 mach = bfd_mach_arm_5TE;
e74cfd16 27055 else if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v5))
b99bd4ef 27056 {
e74cfd16 27057 if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v4t))
b99bd4ef
NC
27058 mach = bfd_mach_arm_5T;
27059 else
27060 mach = bfd_mach_arm_5;
27061 }
e74cfd16 27062 else if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v4))
b99bd4ef 27063 {
e74cfd16 27064 if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v4t))
b99bd4ef
NC
27065 mach = bfd_mach_arm_4T;
27066 else
27067 mach = bfd_mach_arm_4;
27068 }
e74cfd16 27069 else if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v3m))
b99bd4ef 27070 mach = bfd_mach_arm_3M;
e74cfd16
PB
27071 else if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v3))
27072 mach = bfd_mach_arm_3;
27073 else if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v2s))
27074 mach = bfd_mach_arm_2a;
27075 else if (ARM_CPU_HAS_FEATURE (cpu_variant, arm_ext_v2))
27076 mach = bfd_mach_arm_2;
27077 else
27078 mach = bfd_mach_arm_unknown;
b99bd4ef
NC
27079
27080 bfd_set_arch_mach (stdoutput, TARGET_ARCH, mach);
27081}
27082
c19d1205 27083/* Command line processing. */
b99bd4ef 27084
c19d1205
ZW
27085/* md_parse_option
27086 Invocation line includes a switch not recognized by the base assembler.
27087 See if it's a processor-specific option.
b99bd4ef 27088
c19d1205
ZW
27089 This routine is somewhat complicated by the need for backwards
27090 compatibility (since older releases of gcc can't be changed).
27091 The new options try to make the interface as compatible as
27092 possible with GCC.
b99bd4ef 27093
c19d1205 27094 New options (supported) are:
b99bd4ef 27095
c19d1205
ZW
27096 -mcpu=<cpu name> Assemble for selected processor
27097 -march=<architecture name> Assemble for selected architecture
27098 -mfpu=<fpu architecture> Assemble for selected FPU.
27099 -EB/-mbig-endian Big-endian
27100 -EL/-mlittle-endian Little-endian
27101 -k Generate PIC code
27102 -mthumb Start in Thumb mode
27103 -mthumb-interwork Code supports ARM/Thumb interworking
b99bd4ef 27104
278df34e 27105 -m[no-]warn-deprecated Warn about deprecated features
8b2d793c 27106 -m[no-]warn-syms Warn when symbols match instructions
267bf995 27107
c19d1205 27108 For now we will also provide support for:
b99bd4ef 27109
c19d1205
ZW
27110 -mapcs-32 32-bit Program counter
27111 -mapcs-26 26-bit Program counter
27112 -macps-float Floats passed in FP registers
27113 -mapcs-reentrant Reentrant code
27114 -matpcs
27115 (sometime these will probably be replaced with -mapcs=<list of options>
27116 and -matpcs=<list of options>)
b99bd4ef 27117
c19d1205
ZW
27118 The remaining options are only supported for back-wards compatibility.
27119 Cpu variants, the arm part is optional:
27120 -m[arm]1 Currently not supported.
27121 -m[arm]2, -m[arm]250 Arm 2 and Arm 250 processor
27122 -m[arm]3 Arm 3 processor
27123 -m[arm]6[xx], Arm 6 processors
27124 -m[arm]7[xx][t][[d]m] Arm 7 processors
27125 -m[arm]8[10] Arm 8 processors
27126 -m[arm]9[20][tdmi] Arm 9 processors
27127 -mstrongarm[110[0]] StrongARM processors
27128 -mxscale XScale processors
27129 -m[arm]v[2345[t[e]]] Arm architectures
27130 -mall All (except the ARM1)
27131 FP variants:
27132 -mfpa10, -mfpa11 FPA10 and 11 co-processor instructions
27133 -mfpe-old (No float load/store multiples)
27134 -mvfpxd VFP Single precision
27135 -mvfp All VFP
27136 -mno-fpu Disable all floating point instructions
b99bd4ef 27137
c19d1205
ZW
27138 The following CPU names are recognized:
27139 arm1, arm2, arm250, arm3, arm6, arm600, arm610, arm620,
27140 arm7, arm7m, arm7d, arm7dm, arm7di, arm7dmi, arm70, arm700,
27141 arm700i, arm710 arm710t, arm720, arm720t, arm740t, arm710c,
27142 arm7100, arm7500, arm7500fe, arm7tdmi, arm8, arm810, arm9,
27143 arm920, arm920t, arm940t, arm946, arm966, arm9tdmi, arm9e,
27144 arm10t arm10e, arm1020t, arm1020e, arm10200e,
27145 strongarm, strongarm110, strongarm1100, strongarm1110, xscale.
b99bd4ef 27146
c19d1205 27147 */
b99bd4ef 27148
c19d1205 27149const char * md_shortopts = "m:k";
b99bd4ef 27150
c19d1205
ZW
27151#ifdef ARM_BI_ENDIAN
27152#define OPTION_EB (OPTION_MD_BASE + 0)
27153#define OPTION_EL (OPTION_MD_BASE + 1)
b99bd4ef 27154#else
c19d1205
ZW
27155#if TARGET_BYTES_BIG_ENDIAN
27156#define OPTION_EB (OPTION_MD_BASE + 0)
b99bd4ef 27157#else
c19d1205
ZW
27158#define OPTION_EL (OPTION_MD_BASE + 1)
27159#endif
b99bd4ef 27160#endif
845b51d6 27161#define OPTION_FIX_V4BX (OPTION_MD_BASE + 2)
18a20338 27162#define OPTION_FDPIC (OPTION_MD_BASE + 3)
b99bd4ef 27163
c19d1205 27164struct option md_longopts[] =
b99bd4ef 27165{
c19d1205
ZW
27166#ifdef OPTION_EB
27167 {"EB", no_argument, NULL, OPTION_EB},
27168#endif
27169#ifdef OPTION_EL
27170 {"EL", no_argument, NULL, OPTION_EL},
b99bd4ef 27171#endif
845b51d6 27172 {"fix-v4bx", no_argument, NULL, OPTION_FIX_V4BX},
18a20338
CL
27173#ifdef OBJ_ELF
27174 {"fdpic", no_argument, NULL, OPTION_FDPIC},
27175#endif
c19d1205
ZW
27176 {NULL, no_argument, NULL, 0}
27177};
b99bd4ef 27178
c19d1205 27179size_t md_longopts_size = sizeof (md_longopts);
b99bd4ef 27180
c19d1205 27181struct arm_option_table
b99bd4ef 27182{
0198d5e6
TC
27183 const char * option; /* Option name to match. */
27184 const char * help; /* Help information. */
27185 int * var; /* Variable to change. */
27186 int value; /* What to change it to. */
27187 const char * deprecated; /* If non-null, print this message. */
c19d1205 27188};
b99bd4ef 27189
c19d1205
ZW
27190struct arm_option_table arm_opts[] =
27191{
27192 {"k", N_("generate PIC code"), &pic_code, 1, NULL},
27193 {"mthumb", N_("assemble Thumb code"), &thumb_mode, 1, NULL},
27194 {"mthumb-interwork", N_("support ARM/Thumb interworking"),
27195 &support_interwork, 1, NULL},
27196 {"mapcs-32", N_("code uses 32-bit program counter"), &uses_apcs_26, 0, NULL},
27197 {"mapcs-26", N_("code uses 26-bit program counter"), &uses_apcs_26, 1, NULL},
27198 {"mapcs-float", N_("floating point args are in fp regs"), &uses_apcs_float,
27199 1, NULL},
27200 {"mapcs-reentrant", N_("re-entrant code"), &pic_code, 1, NULL},
27201 {"matpcs", N_("code is ATPCS conformant"), &atpcs, 1, NULL},
27202 {"mbig-endian", N_("assemble for big-endian"), &target_big_endian, 1, NULL},
27203 {"mlittle-endian", N_("assemble for little-endian"), &target_big_endian, 0,
27204 NULL},
b99bd4ef 27205
c19d1205
ZW
27206 /* These are recognized by the assembler, but have no affect on code. */
27207 {"mapcs-frame", N_("use frame pointer"), NULL, 0, NULL},
27208 {"mapcs-stack-check", N_("use stack size checking"), NULL, 0, NULL},
278df34e
NS
27209
27210 {"mwarn-deprecated", NULL, &warn_on_deprecated, 1, NULL},
27211 {"mno-warn-deprecated", N_("do not warn on use of deprecated feature"),
27212 &warn_on_deprecated, 0, NULL},
8b2d793c
NC
27213 {"mwarn-syms", N_("warn about symbols that match instruction names [default]"), (int *) (& flag_warn_syms), TRUE, NULL},
27214 {"mno-warn-syms", N_("disable warnings about symobls that match instructions"), (int *) (& flag_warn_syms), FALSE, NULL},
e74cfd16
PB
27215 {NULL, NULL, NULL, 0, NULL}
27216};
27217
27218struct arm_legacy_option_table
27219{
0198d5e6
TC
27220 const char * option; /* Option name to match. */
27221 const arm_feature_set ** var; /* Variable to change. */
27222 const arm_feature_set value; /* What to change it to. */
27223 const char * deprecated; /* If non-null, print this message. */
e74cfd16 27224};
b99bd4ef 27225
e74cfd16
PB
27226const struct arm_legacy_option_table arm_legacy_opts[] =
27227{
c19d1205
ZW
27228 /* DON'T add any new processors to this list -- we want the whole list
27229 to go away... Add them to the processors table instead. */
e74cfd16
PB
27230 {"marm1", &legacy_cpu, ARM_ARCH_V1, N_("use -mcpu=arm1")},
27231 {"m1", &legacy_cpu, ARM_ARCH_V1, N_("use -mcpu=arm1")},
27232 {"marm2", &legacy_cpu, ARM_ARCH_V2, N_("use -mcpu=arm2")},
27233 {"m2", &legacy_cpu, ARM_ARCH_V2, N_("use -mcpu=arm2")},
27234 {"marm250", &legacy_cpu, ARM_ARCH_V2S, N_("use -mcpu=arm250")},
27235 {"m250", &legacy_cpu, ARM_ARCH_V2S, N_("use -mcpu=arm250")},
27236 {"marm3", &legacy_cpu, ARM_ARCH_V2S, N_("use -mcpu=arm3")},
27237 {"m3", &legacy_cpu, ARM_ARCH_V2S, N_("use -mcpu=arm3")},
27238 {"marm6", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm6")},
27239 {"m6", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm6")},
27240 {"marm600", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm600")},
27241 {"m600", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm600")},
27242 {"marm610", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm610")},
27243 {"m610", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm610")},
27244 {"marm620", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm620")},
27245 {"m620", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm620")},
27246 {"marm7", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7")},
27247 {"m7", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7")},
27248 {"marm70", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm70")},
27249 {"m70", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm70")},
27250 {"marm700", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm700")},
27251 {"m700", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm700")},
27252 {"marm700i", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm700i")},
27253 {"m700i", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm700i")},
27254 {"marm710", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm710")},
27255 {"m710", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm710")},
27256 {"marm710c", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm710c")},
27257 {"m710c", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm710c")},
27258 {"marm720", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm720")},
27259 {"m720", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm720")},
27260 {"marm7d", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7d")},
27261 {"m7d", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7d")},
27262 {"marm7di", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7di")},
27263 {"m7di", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7di")},
27264 {"marm7m", &legacy_cpu, ARM_ARCH_V3M, N_("use -mcpu=arm7m")},
27265 {"m7m", &legacy_cpu, ARM_ARCH_V3M, N_("use -mcpu=arm7m")},
27266 {"marm7dm", &legacy_cpu, ARM_ARCH_V3M, N_("use -mcpu=arm7dm")},
27267 {"m7dm", &legacy_cpu, ARM_ARCH_V3M, N_("use -mcpu=arm7dm")},
27268 {"marm7dmi", &legacy_cpu, ARM_ARCH_V3M, N_("use -mcpu=arm7dmi")},
27269 {"m7dmi", &legacy_cpu, ARM_ARCH_V3M, N_("use -mcpu=arm7dmi")},
27270 {"marm7100", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7100")},
27271 {"m7100", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7100")},
27272 {"marm7500", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7500")},
27273 {"m7500", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7500")},
27274 {"marm7500fe", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7500fe")},
27275 {"m7500fe", &legacy_cpu, ARM_ARCH_V3, N_("use -mcpu=arm7500fe")},
27276 {"marm7t", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm7tdmi")},
27277 {"m7t", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm7tdmi")},
27278 {"marm7tdmi", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm7tdmi")},
27279 {"m7tdmi", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm7tdmi")},
27280 {"marm710t", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm710t")},
27281 {"m710t", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm710t")},
27282 {"marm720t", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm720t")},
27283 {"m720t", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm720t")},
27284 {"marm740t", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm740t")},
27285 {"m740t", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm740t")},
27286 {"marm8", &legacy_cpu, ARM_ARCH_V4, N_("use -mcpu=arm8")},
27287 {"m8", &legacy_cpu, ARM_ARCH_V4, N_("use -mcpu=arm8")},
27288 {"marm810", &legacy_cpu, ARM_ARCH_V4, N_("use -mcpu=arm810")},
27289 {"m810", &legacy_cpu, ARM_ARCH_V4, N_("use -mcpu=arm810")},
27290 {"marm9", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm9")},
27291 {"m9", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm9")},
27292 {"marm9tdmi", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm9tdmi")},
27293 {"m9tdmi", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm9tdmi")},
27294 {"marm920", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm920")},
27295 {"m920", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm920")},
27296 {"marm940", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm940")},
27297 {"m940", &legacy_cpu, ARM_ARCH_V4T, N_("use -mcpu=arm940")},
27298 {"mstrongarm", &legacy_cpu, ARM_ARCH_V4, N_("use -mcpu=strongarm")},
27299 {"mstrongarm110", &legacy_cpu, ARM_ARCH_V4,
c19d1205 27300 N_("use -mcpu=strongarm110")},
e74cfd16 27301 {"mstrongarm1100", &legacy_cpu, ARM_ARCH_V4,
c19d1205 27302 N_("use -mcpu=strongarm1100")},
e74cfd16 27303 {"mstrongarm1110", &legacy_cpu, ARM_ARCH_V4,
c19d1205 27304 N_("use -mcpu=strongarm1110")},
e74cfd16
PB
27305 {"mxscale", &legacy_cpu, ARM_ARCH_XSCALE, N_("use -mcpu=xscale")},
27306 {"miwmmxt", &legacy_cpu, ARM_ARCH_IWMMXT, N_("use -mcpu=iwmmxt")},
27307 {"mall", &legacy_cpu, ARM_ANY, N_("use -mcpu=all")},
7ed4c4c5 27308
c19d1205 27309 /* Architecture variants -- don't add any more to this list either. */
e74cfd16
PB
27310 {"mv2", &legacy_cpu, ARM_ARCH_V2, N_("use -march=armv2")},
27311 {"marmv2", &legacy_cpu, ARM_ARCH_V2, N_("use -march=armv2")},
27312 {"mv2a", &legacy_cpu, ARM_ARCH_V2S, N_("use -march=armv2a")},
27313 {"marmv2a", &legacy_cpu, ARM_ARCH_V2S, N_("use -march=armv2a")},
27314 {"mv3", &legacy_cpu, ARM_ARCH_V3, N_("use -march=armv3")},
27315 {"marmv3", &legacy_cpu, ARM_ARCH_V3, N_("use -march=armv3")},
27316 {"mv3m", &legacy_cpu, ARM_ARCH_V3M, N_("use -march=armv3m")},
27317 {"marmv3m", &legacy_cpu, ARM_ARCH_V3M, N_("use -march=armv3m")},
27318 {"mv4", &legacy_cpu, ARM_ARCH_V4, N_("use -march=armv4")},
27319 {"marmv4", &legacy_cpu, ARM_ARCH_V4, N_("use -march=armv4")},
27320 {"mv4t", &legacy_cpu, ARM_ARCH_V4T, N_("use -march=armv4t")},
27321 {"marmv4t", &legacy_cpu, ARM_ARCH_V4T, N_("use -march=armv4t")},
27322 {"mv5", &legacy_cpu, ARM_ARCH_V5, N_("use -march=armv5")},
27323 {"marmv5", &legacy_cpu, ARM_ARCH_V5, N_("use -march=armv5")},
27324 {"mv5t", &legacy_cpu, ARM_ARCH_V5T, N_("use -march=armv5t")},
27325 {"marmv5t", &legacy_cpu, ARM_ARCH_V5T, N_("use -march=armv5t")},
27326 {"mv5e", &legacy_cpu, ARM_ARCH_V5TE, N_("use -march=armv5te")},
27327 {"marmv5e", &legacy_cpu, ARM_ARCH_V5TE, N_("use -march=armv5te")},
7ed4c4c5 27328
c19d1205 27329 /* Floating point variants -- don't add any more to this list either. */
0198d5e6
TC
27330 {"mfpe-old", &legacy_fpu, FPU_ARCH_FPE, N_("use -mfpu=fpe")},
27331 {"mfpa10", &legacy_fpu, FPU_ARCH_FPA, N_("use -mfpu=fpa10")},
27332 {"mfpa11", &legacy_fpu, FPU_ARCH_FPA, N_("use -mfpu=fpa11")},
27333 {"mno-fpu", &legacy_fpu, ARM_ARCH_NONE,
c19d1205 27334 N_("use either -mfpu=softfpa or -mfpu=softvfp")},
7ed4c4c5 27335
e74cfd16 27336 {NULL, NULL, ARM_ARCH_NONE, NULL}
c19d1205 27337};
7ed4c4c5 27338
c19d1205 27339struct arm_cpu_option_table
7ed4c4c5 27340{
0198d5e6
TC
27341 const char * name;
27342 size_t name_len;
27343 const arm_feature_set value;
27344 const arm_feature_set ext;
c19d1205
ZW
27345 /* For some CPUs we assume an FPU unless the user explicitly sets
27346 -mfpu=... */
0198d5e6 27347 const arm_feature_set default_fpu;
ee065d83
PB
27348 /* The canonical name of the CPU, or NULL to use NAME converted to upper
27349 case. */
0198d5e6 27350 const char * canonical_name;
c19d1205 27351};
7ed4c4c5 27352
c19d1205
ZW
27353/* This list should, at a minimum, contain all the cpu names
27354 recognized by GCC. */
996b5569 27355#define ARM_CPU_OPT(N, CN, V, E, DF) { N, sizeof (N) - 1, V, E, DF, CN }
0198d5e6 27356
e74cfd16 27357static const struct arm_cpu_option_table arm_cpus[] =
c19d1205 27358{
996b5569
TP
27359 ARM_CPU_OPT ("all", NULL, ARM_ANY,
27360 ARM_ARCH_NONE,
27361 FPU_ARCH_FPA),
27362 ARM_CPU_OPT ("arm1", NULL, ARM_ARCH_V1,
27363 ARM_ARCH_NONE,
27364 FPU_ARCH_FPA),
27365 ARM_CPU_OPT ("arm2", NULL, ARM_ARCH_V2,
27366 ARM_ARCH_NONE,
27367 FPU_ARCH_FPA),
27368 ARM_CPU_OPT ("arm250", NULL, ARM_ARCH_V2S,
27369 ARM_ARCH_NONE,
27370 FPU_ARCH_FPA),
27371 ARM_CPU_OPT ("arm3", NULL, ARM_ARCH_V2S,
27372 ARM_ARCH_NONE,
27373 FPU_ARCH_FPA),
27374 ARM_CPU_OPT ("arm6", NULL, ARM_ARCH_V3,
27375 ARM_ARCH_NONE,
27376 FPU_ARCH_FPA),
27377 ARM_CPU_OPT ("arm60", NULL, ARM_ARCH_V3,
27378 ARM_ARCH_NONE,
27379 FPU_ARCH_FPA),
27380 ARM_CPU_OPT ("arm600", NULL, ARM_ARCH_V3,
27381 ARM_ARCH_NONE,
27382 FPU_ARCH_FPA),
27383 ARM_CPU_OPT ("arm610", NULL, ARM_ARCH_V3,
27384 ARM_ARCH_NONE,
27385 FPU_ARCH_FPA),
27386 ARM_CPU_OPT ("arm620", NULL, ARM_ARCH_V3,
27387 ARM_ARCH_NONE,
27388 FPU_ARCH_FPA),
27389 ARM_CPU_OPT ("arm7", NULL, ARM_ARCH_V3,
27390 ARM_ARCH_NONE,
27391 FPU_ARCH_FPA),
27392 ARM_CPU_OPT ("arm7m", NULL, ARM_ARCH_V3M,
27393 ARM_ARCH_NONE,
27394 FPU_ARCH_FPA),
27395 ARM_CPU_OPT ("arm7d", NULL, ARM_ARCH_V3,
27396 ARM_ARCH_NONE,
27397 FPU_ARCH_FPA),
27398 ARM_CPU_OPT ("arm7dm", NULL, ARM_ARCH_V3M,
27399 ARM_ARCH_NONE,
27400 FPU_ARCH_FPA),
27401 ARM_CPU_OPT ("arm7di", NULL, ARM_ARCH_V3,
27402 ARM_ARCH_NONE,
27403 FPU_ARCH_FPA),
27404 ARM_CPU_OPT ("arm7dmi", NULL, ARM_ARCH_V3M,
27405 ARM_ARCH_NONE,
27406 FPU_ARCH_FPA),
27407 ARM_CPU_OPT ("arm70", NULL, ARM_ARCH_V3,
27408 ARM_ARCH_NONE,
27409 FPU_ARCH_FPA),
27410 ARM_CPU_OPT ("arm700", NULL, ARM_ARCH_V3,
27411 ARM_ARCH_NONE,
27412 FPU_ARCH_FPA),
27413 ARM_CPU_OPT ("arm700i", NULL, ARM_ARCH_V3,
27414 ARM_ARCH_NONE,
27415 FPU_ARCH_FPA),
27416 ARM_CPU_OPT ("arm710", NULL, ARM_ARCH_V3,
27417 ARM_ARCH_NONE,
27418 FPU_ARCH_FPA),
27419 ARM_CPU_OPT ("arm710t", NULL, ARM_ARCH_V4T,
27420 ARM_ARCH_NONE,
27421 FPU_ARCH_FPA),
27422 ARM_CPU_OPT ("arm720", NULL, ARM_ARCH_V3,
27423 ARM_ARCH_NONE,
27424 FPU_ARCH_FPA),
27425 ARM_CPU_OPT ("arm720t", NULL, ARM_ARCH_V4T,
27426 ARM_ARCH_NONE,
27427 FPU_ARCH_FPA),
27428 ARM_CPU_OPT ("arm740t", NULL, ARM_ARCH_V4T,
27429 ARM_ARCH_NONE,
27430 FPU_ARCH_FPA),
27431 ARM_CPU_OPT ("arm710c", NULL, ARM_ARCH_V3,
27432 ARM_ARCH_NONE,
27433 FPU_ARCH_FPA),
27434 ARM_CPU_OPT ("arm7100", NULL, ARM_ARCH_V3,
27435 ARM_ARCH_NONE,
27436 FPU_ARCH_FPA),
27437 ARM_CPU_OPT ("arm7500", NULL, ARM_ARCH_V3,
27438 ARM_ARCH_NONE,
27439 FPU_ARCH_FPA),
27440 ARM_CPU_OPT ("arm7500fe", NULL, ARM_ARCH_V3,
27441 ARM_ARCH_NONE,
27442 FPU_ARCH_FPA),
27443 ARM_CPU_OPT ("arm7t", NULL, ARM_ARCH_V4T,
27444 ARM_ARCH_NONE,
27445 FPU_ARCH_FPA),
27446 ARM_CPU_OPT ("arm7tdmi", NULL, ARM_ARCH_V4T,
27447 ARM_ARCH_NONE,
27448 FPU_ARCH_FPA),
27449 ARM_CPU_OPT ("arm7tdmi-s", NULL, ARM_ARCH_V4T,
27450 ARM_ARCH_NONE,
27451 FPU_ARCH_FPA),
27452 ARM_CPU_OPT ("arm8", NULL, ARM_ARCH_V4,
27453 ARM_ARCH_NONE,
27454 FPU_ARCH_FPA),
27455 ARM_CPU_OPT ("arm810", NULL, ARM_ARCH_V4,
27456 ARM_ARCH_NONE,
27457 FPU_ARCH_FPA),
27458 ARM_CPU_OPT ("strongarm", NULL, ARM_ARCH_V4,
27459 ARM_ARCH_NONE,
27460 FPU_ARCH_FPA),
27461 ARM_CPU_OPT ("strongarm1", NULL, ARM_ARCH_V4,
27462 ARM_ARCH_NONE,
27463 FPU_ARCH_FPA),
27464 ARM_CPU_OPT ("strongarm110", NULL, ARM_ARCH_V4,
27465 ARM_ARCH_NONE,
27466 FPU_ARCH_FPA),
27467 ARM_CPU_OPT ("strongarm1100", NULL, ARM_ARCH_V4,
27468 ARM_ARCH_NONE,
27469 FPU_ARCH_FPA),
27470 ARM_CPU_OPT ("strongarm1110", NULL, ARM_ARCH_V4,
27471 ARM_ARCH_NONE,
27472 FPU_ARCH_FPA),
27473 ARM_CPU_OPT ("arm9", NULL, ARM_ARCH_V4T,
27474 ARM_ARCH_NONE,
27475 FPU_ARCH_FPA),
27476 ARM_CPU_OPT ("arm920", "ARM920T", ARM_ARCH_V4T,
27477 ARM_ARCH_NONE,
27478 FPU_ARCH_FPA),
27479 ARM_CPU_OPT ("arm920t", NULL, ARM_ARCH_V4T,
27480 ARM_ARCH_NONE,
27481 FPU_ARCH_FPA),
27482 ARM_CPU_OPT ("arm922t", NULL, ARM_ARCH_V4T,
27483 ARM_ARCH_NONE,
27484 FPU_ARCH_FPA),
27485 ARM_CPU_OPT ("arm940t", NULL, ARM_ARCH_V4T,
27486 ARM_ARCH_NONE,
27487 FPU_ARCH_FPA),
27488 ARM_CPU_OPT ("arm9tdmi", NULL, ARM_ARCH_V4T,
27489 ARM_ARCH_NONE,
27490 FPU_ARCH_FPA),
27491 ARM_CPU_OPT ("fa526", NULL, ARM_ARCH_V4,
27492 ARM_ARCH_NONE,
27493 FPU_ARCH_FPA),
27494 ARM_CPU_OPT ("fa626", NULL, ARM_ARCH_V4,
27495 ARM_ARCH_NONE,
27496 FPU_ARCH_FPA),
27497
c19d1205
ZW
27498 /* For V5 or later processors we default to using VFP; but the user
27499 should really set the FPU type explicitly. */
996b5569
TP
27500 ARM_CPU_OPT ("arm9e-r0", NULL, ARM_ARCH_V5TExP,
27501 ARM_ARCH_NONE,
27502 FPU_ARCH_VFP_V2),
27503 ARM_CPU_OPT ("arm9e", NULL, ARM_ARCH_V5TE,
27504 ARM_ARCH_NONE,
27505 FPU_ARCH_VFP_V2),
27506 ARM_CPU_OPT ("arm926ej", "ARM926EJ-S", ARM_ARCH_V5TEJ,
27507 ARM_ARCH_NONE,
27508 FPU_ARCH_VFP_V2),
27509 ARM_CPU_OPT ("arm926ejs", "ARM926EJ-S", ARM_ARCH_V5TEJ,
27510 ARM_ARCH_NONE,
27511 FPU_ARCH_VFP_V2),
27512 ARM_CPU_OPT ("arm926ej-s", NULL, ARM_ARCH_V5TEJ,
27513 ARM_ARCH_NONE,
27514 FPU_ARCH_VFP_V2),
27515 ARM_CPU_OPT ("arm946e-r0", NULL, ARM_ARCH_V5TExP,
27516 ARM_ARCH_NONE,
27517 FPU_ARCH_VFP_V2),
27518 ARM_CPU_OPT ("arm946e", "ARM946E-S", ARM_ARCH_V5TE,
27519 ARM_ARCH_NONE,
27520 FPU_ARCH_VFP_V2),
27521 ARM_CPU_OPT ("arm946e-s", NULL, ARM_ARCH_V5TE,
27522 ARM_ARCH_NONE,
27523 FPU_ARCH_VFP_V2),
27524 ARM_CPU_OPT ("arm966e-r0", NULL, ARM_ARCH_V5TExP,
27525 ARM_ARCH_NONE,
27526 FPU_ARCH_VFP_V2),
27527 ARM_CPU_OPT ("arm966e", "ARM966E-S", ARM_ARCH_V5TE,
27528 ARM_ARCH_NONE,
27529 FPU_ARCH_VFP_V2),
27530 ARM_CPU_OPT ("arm966e-s", NULL, ARM_ARCH_V5TE,
27531 ARM_ARCH_NONE,
27532 FPU_ARCH_VFP_V2),
27533 ARM_CPU_OPT ("arm968e-s", NULL, ARM_ARCH_V5TE,
27534 ARM_ARCH_NONE,
27535 FPU_ARCH_VFP_V2),
27536 ARM_CPU_OPT ("arm10t", NULL, ARM_ARCH_V5T,
27537 ARM_ARCH_NONE,
27538 FPU_ARCH_VFP_V1),
27539 ARM_CPU_OPT ("arm10tdmi", NULL, ARM_ARCH_V5T,
27540 ARM_ARCH_NONE,
27541 FPU_ARCH_VFP_V1),
27542 ARM_CPU_OPT ("arm10e", NULL, ARM_ARCH_V5TE,
27543 ARM_ARCH_NONE,
27544 FPU_ARCH_VFP_V2),
27545 ARM_CPU_OPT ("arm1020", "ARM1020E", ARM_ARCH_V5TE,
27546 ARM_ARCH_NONE,
27547 FPU_ARCH_VFP_V2),
27548 ARM_CPU_OPT ("arm1020t", NULL, ARM_ARCH_V5T,
27549 ARM_ARCH_NONE,
27550 FPU_ARCH_VFP_V1),
27551 ARM_CPU_OPT ("arm1020e", NULL, ARM_ARCH_V5TE,
27552 ARM_ARCH_NONE,
27553 FPU_ARCH_VFP_V2),
27554 ARM_CPU_OPT ("arm1022e", NULL, ARM_ARCH_V5TE,
27555 ARM_ARCH_NONE,
27556 FPU_ARCH_VFP_V2),
27557 ARM_CPU_OPT ("arm1026ejs", "ARM1026EJ-S", ARM_ARCH_V5TEJ,
27558 ARM_ARCH_NONE,
27559 FPU_ARCH_VFP_V2),
27560 ARM_CPU_OPT ("arm1026ej-s", NULL, ARM_ARCH_V5TEJ,
27561 ARM_ARCH_NONE,
27562 FPU_ARCH_VFP_V2),
27563 ARM_CPU_OPT ("fa606te", NULL, ARM_ARCH_V5TE,
27564 ARM_ARCH_NONE,
27565 FPU_ARCH_VFP_V2),
27566 ARM_CPU_OPT ("fa616te", NULL, ARM_ARCH_V5TE,
27567 ARM_ARCH_NONE,
27568 FPU_ARCH_VFP_V2),
27569 ARM_CPU_OPT ("fa626te", NULL, ARM_ARCH_V5TE,
27570 ARM_ARCH_NONE,
27571 FPU_ARCH_VFP_V2),
27572 ARM_CPU_OPT ("fmp626", NULL, ARM_ARCH_V5TE,
27573 ARM_ARCH_NONE,
27574 FPU_ARCH_VFP_V2),
27575 ARM_CPU_OPT ("fa726te", NULL, ARM_ARCH_V5TE,
27576 ARM_ARCH_NONE,
27577 FPU_ARCH_VFP_V2),
27578 ARM_CPU_OPT ("arm1136js", "ARM1136J-S", ARM_ARCH_V6,
27579 ARM_ARCH_NONE,
27580 FPU_NONE),
27581 ARM_CPU_OPT ("arm1136j-s", NULL, ARM_ARCH_V6,
27582 ARM_ARCH_NONE,
27583 FPU_NONE),
27584 ARM_CPU_OPT ("arm1136jfs", "ARM1136JF-S", ARM_ARCH_V6,
27585 ARM_ARCH_NONE,
27586 FPU_ARCH_VFP_V2),
27587 ARM_CPU_OPT ("arm1136jf-s", NULL, ARM_ARCH_V6,
27588 ARM_ARCH_NONE,
27589 FPU_ARCH_VFP_V2),
27590 ARM_CPU_OPT ("mpcore", "MPCore", ARM_ARCH_V6K,
27591 ARM_ARCH_NONE,
27592 FPU_ARCH_VFP_V2),
27593 ARM_CPU_OPT ("mpcorenovfp", "MPCore", ARM_ARCH_V6K,
27594 ARM_ARCH_NONE,
27595 FPU_NONE),
27596 ARM_CPU_OPT ("arm1156t2-s", NULL, ARM_ARCH_V6T2,
27597 ARM_ARCH_NONE,
27598 FPU_NONE),
27599 ARM_CPU_OPT ("arm1156t2f-s", NULL, ARM_ARCH_V6T2,
27600 ARM_ARCH_NONE,
27601 FPU_ARCH_VFP_V2),
27602 ARM_CPU_OPT ("arm1176jz-s", NULL, ARM_ARCH_V6KZ,
27603 ARM_ARCH_NONE,
27604 FPU_NONE),
27605 ARM_CPU_OPT ("arm1176jzf-s", NULL, ARM_ARCH_V6KZ,
27606 ARM_ARCH_NONE,
27607 FPU_ARCH_VFP_V2),
27608 ARM_CPU_OPT ("cortex-a5", "Cortex-A5", ARM_ARCH_V7A,
27609 ARM_FEATURE_CORE_LOW (ARM_EXT_MP | ARM_EXT_SEC),
27610 FPU_NONE),
27611 ARM_CPU_OPT ("cortex-a7", "Cortex-A7", ARM_ARCH_V7VE,
27612 ARM_ARCH_NONE,
27613 FPU_ARCH_NEON_VFP_V4),
27614 ARM_CPU_OPT ("cortex-a8", "Cortex-A8", ARM_ARCH_V7A,
27615 ARM_FEATURE_CORE_LOW (ARM_EXT_SEC),
27616 ARM_FEATURE_COPROC (FPU_VFP_V3 | FPU_NEON_EXT_V1)),
27617 ARM_CPU_OPT ("cortex-a9", "Cortex-A9", ARM_ARCH_V7A,
27618 ARM_FEATURE_CORE_LOW (ARM_EXT_MP | ARM_EXT_SEC),
27619 ARM_FEATURE_COPROC (FPU_VFP_V3 | FPU_NEON_EXT_V1)),
27620 ARM_CPU_OPT ("cortex-a12", "Cortex-A12", ARM_ARCH_V7VE,
27621 ARM_ARCH_NONE,
27622 FPU_ARCH_NEON_VFP_V4),
27623 ARM_CPU_OPT ("cortex-a15", "Cortex-A15", ARM_ARCH_V7VE,
27624 ARM_ARCH_NONE,
27625 FPU_ARCH_NEON_VFP_V4),
27626 ARM_CPU_OPT ("cortex-a17", "Cortex-A17", ARM_ARCH_V7VE,
27627 ARM_ARCH_NONE,
27628 FPU_ARCH_NEON_VFP_V4),
27629 ARM_CPU_OPT ("cortex-a32", "Cortex-A32", ARM_ARCH_V8A,
27630 ARM_FEATURE_COPROC (CRC_EXT_ARMV8),
27631 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8),
27632 ARM_CPU_OPT ("cortex-a35", "Cortex-A35", ARM_ARCH_V8A,
27633 ARM_FEATURE_COPROC (CRC_EXT_ARMV8),
27634 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8),
27635 ARM_CPU_OPT ("cortex-a53", "Cortex-A53", ARM_ARCH_V8A,
27636 ARM_FEATURE_COPROC (CRC_EXT_ARMV8),
27637 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8),
15a7695f
JG
27638 ARM_CPU_OPT ("cortex-a55", "Cortex-A55", ARM_ARCH_V8_2A,
27639 ARM_FEATURE_CORE_HIGH (ARM_EXT2_FP16_INST),
0198d5e6 27640 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8_DOTPROD),
996b5569
TP
27641 ARM_CPU_OPT ("cortex-a57", "Cortex-A57", ARM_ARCH_V8A,
27642 ARM_FEATURE_COPROC (CRC_EXT_ARMV8),
27643 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8),
27644 ARM_CPU_OPT ("cortex-a72", "Cortex-A72", ARM_ARCH_V8A,
27645 ARM_FEATURE_COPROC (CRC_EXT_ARMV8),
27646 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8),
27647 ARM_CPU_OPT ("cortex-a73", "Cortex-A73", ARM_ARCH_V8A,
27648 ARM_FEATURE_COPROC (CRC_EXT_ARMV8),
27649 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8),
15a7695f
JG
27650 ARM_CPU_OPT ("cortex-a75", "Cortex-A75", ARM_ARCH_V8_2A,
27651 ARM_FEATURE_CORE_HIGH (ARM_EXT2_FP16_INST),
0198d5e6 27652 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8_DOTPROD),
7ebd1359 27653 ARM_CPU_OPT ("cortex-a76", "Cortex-A76", ARM_ARCH_V8_2A,
27654 ARM_FEATURE_CORE_HIGH (ARM_EXT2_FP16_INST),
27655 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8_DOTPROD),
ef8df4ca
KT
27656 ARM_CPU_OPT ("ares", "Ares", ARM_ARCH_V8_2A,
27657 ARM_FEATURE_CORE_HIGH (ARM_EXT2_FP16_INST),
27658 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8_DOTPROD),
996b5569
TP
27659 ARM_CPU_OPT ("cortex-r4", "Cortex-R4", ARM_ARCH_V7R,
27660 ARM_ARCH_NONE,
27661 FPU_NONE),
27662 ARM_CPU_OPT ("cortex-r4f", "Cortex-R4F", ARM_ARCH_V7R,
27663 ARM_ARCH_NONE,
27664 FPU_ARCH_VFP_V3D16),
27665 ARM_CPU_OPT ("cortex-r5", "Cortex-R5", ARM_ARCH_V7R,
27666 ARM_FEATURE_CORE_LOW (ARM_EXT_ADIV),
27667 FPU_NONE),
27668 ARM_CPU_OPT ("cortex-r7", "Cortex-R7", ARM_ARCH_V7R,
27669 ARM_FEATURE_CORE_LOW (ARM_EXT_ADIV),
27670 FPU_ARCH_VFP_V3D16),
27671 ARM_CPU_OPT ("cortex-r8", "Cortex-R8", ARM_ARCH_V7R,
27672 ARM_FEATURE_CORE_LOW (ARM_EXT_ADIV),
27673 FPU_ARCH_VFP_V3D16),
0cda1e19
TP
27674 ARM_CPU_OPT ("cortex-r52", "Cortex-R52", ARM_ARCH_V8R,
27675 ARM_FEATURE_COPROC (CRC_EXT_ARMV8),
27676 FPU_ARCH_NEON_VFP_ARMV8),
996b5569
TP
27677 ARM_CPU_OPT ("cortex-m33", "Cortex-M33", ARM_ARCH_V8M_MAIN,
27678 ARM_FEATURE_CORE_LOW (ARM_EXT_V5ExP | ARM_EXT_V6_DSP),
27679 FPU_NONE),
27680 ARM_CPU_OPT ("cortex-m23", "Cortex-M23", ARM_ARCH_V8M_BASE,
27681 ARM_ARCH_NONE,
27682 FPU_NONE),
27683 ARM_CPU_OPT ("cortex-m7", "Cortex-M7", ARM_ARCH_V7EM,
27684 ARM_ARCH_NONE,
27685 FPU_NONE),
27686 ARM_CPU_OPT ("cortex-m4", "Cortex-M4", ARM_ARCH_V7EM,
27687 ARM_ARCH_NONE,
27688 FPU_NONE),
27689 ARM_CPU_OPT ("cortex-m3", "Cortex-M3", ARM_ARCH_V7M,
27690 ARM_ARCH_NONE,
27691 FPU_NONE),
27692 ARM_CPU_OPT ("cortex-m1", "Cortex-M1", ARM_ARCH_V6SM,
27693 ARM_ARCH_NONE,
27694 FPU_NONE),
27695 ARM_CPU_OPT ("cortex-m0", "Cortex-M0", ARM_ARCH_V6SM,
27696 ARM_ARCH_NONE,
27697 FPU_NONE),
27698 ARM_CPU_OPT ("cortex-m0plus", "Cortex-M0+", ARM_ARCH_V6SM,
27699 ARM_ARCH_NONE,
27700 FPU_NONE),
27701 ARM_CPU_OPT ("exynos-m1", "Samsung Exynos M1", ARM_ARCH_V8A,
27702 ARM_FEATURE_COPROC (CRC_EXT_ARMV8),
27703 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8),
83f43c83
KT
27704 ARM_CPU_OPT ("neoverse-n1", "Neoverse N1", ARM_ARCH_V8_2A,
27705 ARM_FEATURE_CORE_HIGH (ARM_EXT2_FP16_INST),
27706 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8_DOTPROD),
c19d1205 27707 /* ??? XSCALE is really an architecture. */
996b5569
TP
27708 ARM_CPU_OPT ("xscale", NULL, ARM_ARCH_XSCALE,
27709 ARM_ARCH_NONE,
27710 FPU_ARCH_VFP_V2),
27711
c19d1205 27712 /* ??? iwmmxt is not a processor. */
996b5569
TP
27713 ARM_CPU_OPT ("iwmmxt", NULL, ARM_ARCH_IWMMXT,
27714 ARM_ARCH_NONE,
27715 FPU_ARCH_VFP_V2),
27716 ARM_CPU_OPT ("iwmmxt2", NULL, ARM_ARCH_IWMMXT2,
27717 ARM_ARCH_NONE,
27718 FPU_ARCH_VFP_V2),
27719 ARM_CPU_OPT ("i80200", NULL, ARM_ARCH_XSCALE,
27720 ARM_ARCH_NONE,
27721 FPU_ARCH_VFP_V2),
27722
0198d5e6 27723 /* Maverick. */
996b5569
TP
27724 ARM_CPU_OPT ("ep9312", "ARM920T",
27725 ARM_FEATURE_LOW (ARM_AEXT_V4T, ARM_CEXT_MAVERICK),
27726 ARM_ARCH_NONE, FPU_ARCH_MAVERICK),
27727
da4339ed 27728 /* Marvell processors. */
996b5569
TP
27729 ARM_CPU_OPT ("marvell-pj4", NULL, ARM_ARCH_V7A,
27730 ARM_FEATURE_CORE_LOW (ARM_EXT_MP | ARM_EXT_SEC),
27731 FPU_ARCH_VFP_V3D16),
27732 ARM_CPU_OPT ("marvell-whitney", NULL, ARM_ARCH_V7A,
27733 ARM_FEATURE_CORE_LOW (ARM_EXT_MP | ARM_EXT_SEC),
27734 FPU_ARCH_NEON_VFP_V4),
da4339ed 27735
996b5569
TP
27736 /* APM X-Gene family. */
27737 ARM_CPU_OPT ("xgene1", "APM X-Gene 1", ARM_ARCH_V8A,
27738 ARM_ARCH_NONE,
27739 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8),
27740 ARM_CPU_OPT ("xgene2", "APM X-Gene 2", ARM_ARCH_V8A,
27741 ARM_FEATURE_COPROC (CRC_EXT_ARMV8),
27742 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8),
27743
27744 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE, ARM_ARCH_NONE, NULL }
c19d1205 27745};
f3bad469 27746#undef ARM_CPU_OPT
7ed4c4c5 27747
34ef62f4
AV
27748struct arm_ext_table
27749{
27750 const char * name;
27751 size_t name_len;
27752 const arm_feature_set merge;
27753 const arm_feature_set clear;
27754};
27755
c19d1205 27756struct arm_arch_option_table
7ed4c4c5 27757{
34ef62f4
AV
27758 const char * name;
27759 size_t name_len;
27760 const arm_feature_set value;
27761 const arm_feature_set default_fpu;
27762 const struct arm_ext_table * ext_table;
27763};
27764
27765/* Used to add support for +E and +noE extension. */
27766#define ARM_EXT(E, M, C) { E, sizeof (E) - 1, M, C }
27767/* Used to add support for a +E extension. */
27768#define ARM_ADD(E, M) { E, sizeof(E) - 1, M, ARM_ARCH_NONE }
27769/* Used to add support for a +noE extension. */
27770#define ARM_REMOVE(E, C) { E, sizeof(E) -1, ARM_ARCH_NONE, C }
27771
27772#define ALL_FP ARM_FEATURE (0, ARM_EXT2_FP16_INST | ARM_EXT2_FP16_FML, \
27773 ~0 & ~FPU_ENDIAN_PURE)
27774
27775static const struct arm_ext_table armv5te_ext_table[] =
27776{
27777 ARM_EXT ("fp", FPU_ARCH_VFP_V2, ALL_FP),
27778 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27779};
27780
27781static const struct arm_ext_table armv7_ext_table[] =
27782{
27783 ARM_EXT ("fp", FPU_ARCH_VFP_V3D16, ALL_FP),
27784 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27785};
27786
27787static const struct arm_ext_table armv7ve_ext_table[] =
27788{
27789 ARM_EXT ("fp", FPU_ARCH_VFP_V4D16, ALL_FP),
27790 ARM_ADD ("vfpv3-d16", FPU_ARCH_VFP_V3D16),
27791 ARM_ADD ("vfpv3", FPU_ARCH_VFP_V3),
27792 ARM_ADD ("vfpv3-d16-fp16", FPU_ARCH_VFP_V3D16_FP16),
27793 ARM_ADD ("vfpv3-fp16", FPU_ARCH_VFP_V3_FP16),
27794 ARM_ADD ("vfpv4-d16", FPU_ARCH_VFP_V4D16), /* Alias for +fp. */
27795 ARM_ADD ("vfpv4", FPU_ARCH_VFP_V4),
27796
27797 ARM_EXT ("simd", FPU_ARCH_NEON_VFP_V4,
27798 ARM_FEATURE_COPROC (FPU_NEON_EXT_V1 | FPU_NEON_EXT_FMA)),
27799
27800 /* Aliases for +simd. */
27801 ARM_ADD ("neon-vfpv4", FPU_ARCH_NEON_VFP_V4),
27802
27803 ARM_ADD ("neon", FPU_ARCH_VFP_V3_PLUS_NEON_V1),
27804 ARM_ADD ("neon-vfpv3", FPU_ARCH_VFP_V3_PLUS_NEON_V1),
27805 ARM_ADD ("neon-fp16", FPU_ARCH_NEON_FP16),
27806
27807 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27808};
27809
27810static const struct arm_ext_table armv7a_ext_table[] =
27811{
27812 ARM_EXT ("fp", FPU_ARCH_VFP_V3D16, ALL_FP),
27813 ARM_ADD ("vfpv3-d16", FPU_ARCH_VFP_V3D16), /* Alias for +fp. */
27814 ARM_ADD ("vfpv3", FPU_ARCH_VFP_V3),
27815 ARM_ADD ("vfpv3-d16-fp16", FPU_ARCH_VFP_V3D16_FP16),
27816 ARM_ADD ("vfpv3-fp16", FPU_ARCH_VFP_V3_FP16),
27817 ARM_ADD ("vfpv4-d16", FPU_ARCH_VFP_V4D16),
27818 ARM_ADD ("vfpv4", FPU_ARCH_VFP_V4),
27819
27820 ARM_EXT ("simd", FPU_ARCH_VFP_V3_PLUS_NEON_V1,
27821 ARM_FEATURE_COPROC (FPU_NEON_EXT_V1 | FPU_NEON_EXT_FMA)),
27822
27823 /* Aliases for +simd. */
27824 ARM_ADD ("neon", FPU_ARCH_VFP_V3_PLUS_NEON_V1),
27825 ARM_ADD ("neon-vfpv3", FPU_ARCH_VFP_V3_PLUS_NEON_V1),
27826
27827 ARM_ADD ("neon-fp16", FPU_ARCH_NEON_FP16),
27828 ARM_ADD ("neon-vfpv4", FPU_ARCH_NEON_VFP_V4),
27829
27830 ARM_ADD ("mp", ARM_FEATURE_CORE_LOW (ARM_EXT_MP)),
27831 ARM_ADD ("sec", ARM_FEATURE_CORE_LOW (ARM_EXT_SEC)),
27832 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27833};
27834
27835static const struct arm_ext_table armv7r_ext_table[] =
27836{
27837 ARM_ADD ("fp.sp", FPU_ARCH_VFP_V3xD),
27838 ARM_ADD ("vfpv3xd", FPU_ARCH_VFP_V3xD), /* Alias for +fp.sp. */
27839 ARM_EXT ("fp", FPU_ARCH_VFP_V3D16, ALL_FP),
27840 ARM_ADD ("vfpv3-d16", FPU_ARCH_VFP_V3D16), /* Alias for +fp. */
27841 ARM_ADD ("vfpv3xd-fp16", FPU_ARCH_VFP_V3xD_FP16),
27842 ARM_ADD ("vfpv3-d16-fp16", FPU_ARCH_VFP_V3D16_FP16),
27843 ARM_EXT ("idiv", ARM_FEATURE_CORE_LOW (ARM_EXT_ADIV | ARM_EXT_DIV),
27844 ARM_FEATURE_CORE_LOW (ARM_EXT_ADIV | ARM_EXT_DIV)),
27845 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27846};
27847
27848static const struct arm_ext_table armv7em_ext_table[] =
27849{
27850 ARM_EXT ("fp", FPU_ARCH_VFP_V4_SP_D16, ALL_FP),
27851 /* Alias for +fp, used to be known as fpv4-sp-d16. */
27852 ARM_ADD ("vfpv4-sp-d16", FPU_ARCH_VFP_V4_SP_D16),
27853 ARM_ADD ("fpv5", FPU_ARCH_VFP_V5_SP_D16),
27854 ARM_ADD ("fp.dp", FPU_ARCH_VFP_V5D16),
27855 ARM_ADD ("fpv5-d16", FPU_ARCH_VFP_V5D16),
27856 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27857};
27858
27859static const struct arm_ext_table armv8a_ext_table[] =
27860{
27861 ARM_ADD ("crc", ARCH_CRC_ARMV8),
27862 ARM_ADD ("simd", FPU_ARCH_NEON_VFP_ARMV8),
27863 ARM_EXT ("crypto", FPU_ARCH_CRYPTO_NEON_VFP_ARMV8,
27864 ARM_FEATURE_COPROC (FPU_CRYPTO_ARMV8)),
27865
27866 /* Armv8-a does not allow an FP implementation without SIMD, so the user
27867 should use the +simd option to turn on FP. */
27868 ARM_REMOVE ("fp", ALL_FP),
27869 ARM_ADD ("sb", ARM_FEATURE_CORE_HIGH (ARM_EXT2_SB)),
27870 ARM_ADD ("predres", ARM_FEATURE_CORE_HIGH (ARM_EXT2_PREDRES)),
27871 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27872};
27873
27874
27875static const struct arm_ext_table armv81a_ext_table[] =
27876{
27877 ARM_ADD ("simd", FPU_ARCH_NEON_VFP_ARMV8_1),
27878 ARM_EXT ("crypto", FPU_ARCH_CRYPTO_NEON_VFP_ARMV8_1,
27879 ARM_FEATURE_COPROC (FPU_CRYPTO_ARMV8)),
27880
27881 /* Armv8-a does not allow an FP implementation without SIMD, so the user
27882 should use the +simd option to turn on FP. */
27883 ARM_REMOVE ("fp", ALL_FP),
27884 ARM_ADD ("sb", ARM_FEATURE_CORE_HIGH (ARM_EXT2_SB)),
27885 ARM_ADD ("predres", ARM_FEATURE_CORE_HIGH (ARM_EXT2_PREDRES)),
27886 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27887};
27888
27889static const struct arm_ext_table armv82a_ext_table[] =
27890{
27891 ARM_ADD ("simd", FPU_ARCH_NEON_VFP_ARMV8_1),
27892 ARM_ADD ("fp16", FPU_ARCH_NEON_VFP_ARMV8_2_FP16),
27893 ARM_ADD ("fp16fml", FPU_ARCH_NEON_VFP_ARMV8_2_FP16FML),
27894 ARM_EXT ("crypto", FPU_ARCH_CRYPTO_NEON_VFP_ARMV8_1,
27895 ARM_FEATURE_COPROC (FPU_CRYPTO_ARMV8)),
27896 ARM_ADD ("dotprod", FPU_ARCH_DOTPROD_NEON_VFP_ARMV8),
27897
27898 /* Armv8-a does not allow an FP implementation without SIMD, so the user
27899 should use the +simd option to turn on FP. */
27900 ARM_REMOVE ("fp", ALL_FP),
27901 ARM_ADD ("sb", ARM_FEATURE_CORE_HIGH (ARM_EXT2_SB)),
27902 ARM_ADD ("predres", ARM_FEATURE_CORE_HIGH (ARM_EXT2_PREDRES)),
27903 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27904};
27905
27906static const struct arm_ext_table armv84a_ext_table[] =
27907{
27908 ARM_ADD ("simd", FPU_ARCH_DOTPROD_NEON_VFP_ARMV8),
27909 ARM_ADD ("fp16", FPU_ARCH_NEON_VFP_ARMV8_4_FP16FML),
27910 ARM_EXT ("crypto", FPU_ARCH_CRYPTO_NEON_VFP_ARMV8_4,
27911 ARM_FEATURE_COPROC (FPU_CRYPTO_ARMV8)),
27912
27913 /* Armv8-a does not allow an FP implementation without SIMD, so the user
27914 should use the +simd option to turn on FP. */
27915 ARM_REMOVE ("fp", ALL_FP),
27916 ARM_ADD ("sb", ARM_FEATURE_CORE_HIGH (ARM_EXT2_SB)),
27917 ARM_ADD ("predres", ARM_FEATURE_CORE_HIGH (ARM_EXT2_PREDRES)),
27918 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27919};
27920
27921static const struct arm_ext_table armv85a_ext_table[] =
27922{
27923 ARM_ADD ("simd", FPU_ARCH_DOTPROD_NEON_VFP_ARMV8),
27924 ARM_ADD ("fp16", FPU_ARCH_NEON_VFP_ARMV8_4_FP16FML),
27925 ARM_EXT ("crypto", FPU_ARCH_CRYPTO_NEON_VFP_ARMV8_4,
27926 ARM_FEATURE_COPROC (FPU_CRYPTO_ARMV8)),
27927
27928 /* Armv8-a does not allow an FP implementation without SIMD, so the user
27929 should use the +simd option to turn on FP. */
27930 ARM_REMOVE ("fp", ALL_FP),
27931 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27932};
27933
27934static const struct arm_ext_table armv8m_main_ext_table[] =
27935{
27936 ARM_EXT ("dsp", ARM_FEATURE_CORE_LOW (ARM_EXT_V5ExP | ARM_EXT_V6_DSP),
27937 ARM_FEATURE_CORE_LOW (ARM_EXT_V5ExP | ARM_EXT_V6_DSP)),
27938 ARM_EXT ("fp", FPU_ARCH_VFP_V5_SP_D16, ALL_FP),
27939 ARM_ADD ("fp.dp", FPU_ARCH_VFP_V5D16),
27940 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27941};
27942
e0991585
AV
27943static const struct arm_ext_table armv8_1m_main_ext_table[] =
27944{
27945 ARM_EXT ("dsp", ARM_FEATURE_CORE_LOW (ARM_EXT_V5ExP | ARM_EXT_V6_DSP),
27946 ARM_FEATURE_CORE_LOW (ARM_EXT_V5ExP | ARM_EXT_V6_DSP)),
27947 ARM_EXT ("fp",
27948 ARM_FEATURE (0, ARM_EXT2_FP16_INST,
27949 FPU_VFP_V5_SP_D16 | FPU_VFP_EXT_FP16 | FPU_VFP_EXT_FMA),
27950 ALL_FP),
27951 ARM_ADD ("fp.dp",
27952 ARM_FEATURE (0, ARM_EXT2_FP16_INST,
27953 FPU_VFP_V5D16 | FPU_VFP_EXT_FP16 | FPU_VFP_EXT_FMA)),
a7ad558c
AV
27954 ARM_EXT ("mve", ARM_FEATURE_COPROC (FPU_MVE),
27955 ARM_FEATURE_COPROC (FPU_MVE | FPU_MVE_FP)),
27956 ARM_ADD ("mve.fp",
27957 ARM_FEATURE (0, ARM_EXT2_FP16_INST,
27958 FPU_MVE | FPU_MVE_FP | FPU_VFP_V5_SP_D16 |
27959 FPU_VFP_EXT_FP16 | FPU_VFP_EXT_FMA)),
e0991585
AV
27960 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
27961};
27962
34ef62f4
AV
27963static const struct arm_ext_table armv8r_ext_table[] =
27964{
27965 ARM_ADD ("crc", ARCH_CRC_ARMV8),
27966 ARM_ADD ("simd", FPU_ARCH_NEON_VFP_ARMV8),
27967 ARM_EXT ("crypto", FPU_ARCH_CRYPTO_NEON_VFP_ARMV8,
27968 ARM_FEATURE_COPROC (FPU_CRYPTO_ARMV8)),
27969 ARM_REMOVE ("fp", ALL_FP),
27970 ARM_ADD ("fp.sp", FPU_ARCH_VFP_V5_SP_D16),
27971 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE }
c19d1205 27972};
7ed4c4c5 27973
c19d1205
ZW
27974/* This list should, at a minimum, contain all the architecture names
27975 recognized by GCC. */
34ef62f4
AV
27976#define ARM_ARCH_OPT(N, V, DF) { N, sizeof (N) - 1, V, DF, NULL }
27977#define ARM_ARCH_OPT2(N, V, DF, ext) \
27978 { N, sizeof (N) - 1, V, DF, ext##_ext_table }
0198d5e6 27979
e74cfd16 27980static const struct arm_arch_option_table arm_archs[] =
c19d1205 27981{
497d849d
TP
27982 ARM_ARCH_OPT ("all", ARM_ANY, FPU_ARCH_FPA),
27983 ARM_ARCH_OPT ("armv1", ARM_ARCH_V1, FPU_ARCH_FPA),
27984 ARM_ARCH_OPT ("armv2", ARM_ARCH_V2, FPU_ARCH_FPA),
27985 ARM_ARCH_OPT ("armv2a", ARM_ARCH_V2S, FPU_ARCH_FPA),
27986 ARM_ARCH_OPT ("armv2s", ARM_ARCH_V2S, FPU_ARCH_FPA),
27987 ARM_ARCH_OPT ("armv3", ARM_ARCH_V3, FPU_ARCH_FPA),
27988 ARM_ARCH_OPT ("armv3m", ARM_ARCH_V3M, FPU_ARCH_FPA),
27989 ARM_ARCH_OPT ("armv4", ARM_ARCH_V4, FPU_ARCH_FPA),
27990 ARM_ARCH_OPT ("armv4xm", ARM_ARCH_V4xM, FPU_ARCH_FPA),
27991 ARM_ARCH_OPT ("armv4t", ARM_ARCH_V4T, FPU_ARCH_FPA),
27992 ARM_ARCH_OPT ("armv4txm", ARM_ARCH_V4TxM, FPU_ARCH_FPA),
27993 ARM_ARCH_OPT ("armv5", ARM_ARCH_V5, FPU_ARCH_VFP),
27994 ARM_ARCH_OPT ("armv5t", ARM_ARCH_V5T, FPU_ARCH_VFP),
27995 ARM_ARCH_OPT ("armv5txm", ARM_ARCH_V5TxM, FPU_ARCH_VFP),
34ef62f4
AV
27996 ARM_ARCH_OPT2 ("armv5te", ARM_ARCH_V5TE, FPU_ARCH_VFP, armv5te),
27997 ARM_ARCH_OPT2 ("armv5texp", ARM_ARCH_V5TExP, FPU_ARCH_VFP, armv5te),
27998 ARM_ARCH_OPT2 ("armv5tej", ARM_ARCH_V5TEJ, FPU_ARCH_VFP, armv5te),
27999 ARM_ARCH_OPT2 ("armv6", ARM_ARCH_V6, FPU_ARCH_VFP, armv5te),
28000 ARM_ARCH_OPT2 ("armv6j", ARM_ARCH_V6, FPU_ARCH_VFP, armv5te),
28001 ARM_ARCH_OPT2 ("armv6k", ARM_ARCH_V6K, FPU_ARCH_VFP, armv5te),
28002 ARM_ARCH_OPT2 ("armv6z", ARM_ARCH_V6Z, FPU_ARCH_VFP, armv5te),
f33026a9
MW
28003 /* The official spelling of this variant is ARMv6KZ, the name "armv6zk" is
28004 kept to preserve existing behaviour. */
34ef62f4
AV
28005 ARM_ARCH_OPT2 ("armv6kz", ARM_ARCH_V6KZ, FPU_ARCH_VFP, armv5te),
28006 ARM_ARCH_OPT2 ("armv6zk", ARM_ARCH_V6KZ, FPU_ARCH_VFP, armv5te),
28007 ARM_ARCH_OPT2 ("armv6t2", ARM_ARCH_V6T2, FPU_ARCH_VFP, armv5te),
28008 ARM_ARCH_OPT2 ("armv6kt2", ARM_ARCH_V6KT2, FPU_ARCH_VFP, armv5te),
28009 ARM_ARCH_OPT2 ("armv6zt2", ARM_ARCH_V6ZT2, FPU_ARCH_VFP, armv5te),
f33026a9
MW
28010 /* The official spelling of this variant is ARMv6KZ, the name "armv6zkt2" is
28011 kept to preserve existing behaviour. */
34ef62f4
AV
28012 ARM_ARCH_OPT2 ("armv6kzt2", ARM_ARCH_V6KZT2, FPU_ARCH_VFP, armv5te),
28013 ARM_ARCH_OPT2 ("armv6zkt2", ARM_ARCH_V6KZT2, FPU_ARCH_VFP, armv5te),
497d849d
TP
28014 ARM_ARCH_OPT ("armv6-m", ARM_ARCH_V6M, FPU_ARCH_VFP),
28015 ARM_ARCH_OPT ("armv6s-m", ARM_ARCH_V6SM, FPU_ARCH_VFP),
34ef62f4 28016 ARM_ARCH_OPT2 ("armv7", ARM_ARCH_V7, FPU_ARCH_VFP, armv7),
c450d570
PB
28017 /* The official spelling of the ARMv7 profile variants is the dashed form.
28018 Accept the non-dashed form for compatibility with old toolchains. */
34ef62f4
AV
28019 ARM_ARCH_OPT2 ("armv7a", ARM_ARCH_V7A, FPU_ARCH_VFP, armv7a),
28020 ARM_ARCH_OPT2 ("armv7ve", ARM_ARCH_V7VE, FPU_ARCH_VFP, armv7ve),
28021 ARM_ARCH_OPT2 ("armv7r", ARM_ARCH_V7R, FPU_ARCH_VFP, armv7r),
497d849d 28022 ARM_ARCH_OPT ("armv7m", ARM_ARCH_V7M, FPU_ARCH_VFP),
34ef62f4
AV
28023 ARM_ARCH_OPT2 ("armv7-a", ARM_ARCH_V7A, FPU_ARCH_VFP, armv7a),
28024 ARM_ARCH_OPT2 ("armv7-r", ARM_ARCH_V7R, FPU_ARCH_VFP, armv7r),
497d849d 28025 ARM_ARCH_OPT ("armv7-m", ARM_ARCH_V7M, FPU_ARCH_VFP),
34ef62f4 28026 ARM_ARCH_OPT2 ("armv7e-m", ARM_ARCH_V7EM, FPU_ARCH_VFP, armv7em),
497d849d 28027 ARM_ARCH_OPT ("armv8-m.base", ARM_ARCH_V8M_BASE, FPU_ARCH_VFP),
34ef62f4
AV
28028 ARM_ARCH_OPT2 ("armv8-m.main", ARM_ARCH_V8M_MAIN, FPU_ARCH_VFP,
28029 armv8m_main),
e0991585
AV
28030 ARM_ARCH_OPT2 ("armv8.1-m.main", ARM_ARCH_V8_1M_MAIN, FPU_ARCH_VFP,
28031 armv8_1m_main),
34ef62f4
AV
28032 ARM_ARCH_OPT2 ("armv8-a", ARM_ARCH_V8A, FPU_ARCH_VFP, armv8a),
28033 ARM_ARCH_OPT2 ("armv8.1-a", ARM_ARCH_V8_1A, FPU_ARCH_VFP, armv81a),
28034 ARM_ARCH_OPT2 ("armv8.2-a", ARM_ARCH_V8_2A, FPU_ARCH_VFP, armv82a),
28035 ARM_ARCH_OPT2 ("armv8.3-a", ARM_ARCH_V8_3A, FPU_ARCH_VFP, armv82a),
28036 ARM_ARCH_OPT2 ("armv8-r", ARM_ARCH_V8R, FPU_ARCH_VFP, armv8r),
28037 ARM_ARCH_OPT2 ("armv8.4-a", ARM_ARCH_V8_4A, FPU_ARCH_VFP, armv84a),
28038 ARM_ARCH_OPT2 ("armv8.5-a", ARM_ARCH_V8_5A, FPU_ARCH_VFP, armv85a),
497d849d
TP
28039 ARM_ARCH_OPT ("xscale", ARM_ARCH_XSCALE, FPU_ARCH_VFP),
28040 ARM_ARCH_OPT ("iwmmxt", ARM_ARCH_IWMMXT, FPU_ARCH_VFP),
28041 ARM_ARCH_OPT ("iwmmxt2", ARM_ARCH_IWMMXT2, FPU_ARCH_VFP),
34ef62f4 28042 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE, NULL }
c19d1205 28043};
f3bad469 28044#undef ARM_ARCH_OPT
7ed4c4c5 28045
69133863 28046/* ISA extensions in the co-processor and main instruction set space. */
0198d5e6 28047
69133863 28048struct arm_option_extension_value_table
c19d1205 28049{
0198d5e6
TC
28050 const char * name;
28051 size_t name_len;
28052 const arm_feature_set merge_value;
28053 const arm_feature_set clear_value;
d942732e
TP
28054 /* List of architectures for which an extension is available. ARM_ARCH_NONE
28055 indicates that an extension is available for all architectures while
28056 ARM_ANY marks an empty entry. */
0198d5e6 28057 const arm_feature_set allowed_archs[2];
c19d1205 28058};
7ed4c4c5 28059
0198d5e6
TC
28060/* The following table must be in alphabetical order with a NULL last entry. */
28061
d942732e
TP
28062#define ARM_EXT_OPT(N, M, C, AA) { N, sizeof (N) - 1, M, C, { AA, ARM_ANY } }
28063#define ARM_EXT_OPT2(N, M, C, AA1, AA2) { N, sizeof (N) - 1, M, C, {AA1, AA2} }
0198d5e6 28064
34ef62f4
AV
28065/* DEPRECATED: Refrain from using this table to add any new extensions, instead
28066 use the context sensitive approach using arm_ext_table's. */
69133863 28067static const struct arm_option_extension_value_table arm_extensions[] =
c19d1205 28068{
823d2571
TG
28069 ARM_EXT_OPT ("crc", ARCH_CRC_ARMV8, ARM_FEATURE_COPROC (CRC_EXT_ARMV8),
28070 ARM_FEATURE_CORE_LOW (ARM_EXT_V8)),
bca38921 28071 ARM_EXT_OPT ("crypto", FPU_ARCH_CRYPTO_NEON_VFP_ARMV8,
823d2571
TG
28072 ARM_FEATURE_COPROC (FPU_CRYPTO_ARMV8),
28073 ARM_FEATURE_CORE_LOW (ARM_EXT_V8)),
c604a79a
JW
28074 ARM_EXT_OPT ("dotprod", FPU_ARCH_DOTPROD_NEON_VFP_ARMV8,
28075 ARM_FEATURE_COPROC (FPU_NEON_EXT_DOTPROD),
28076 ARM_ARCH_V8_2A),
15afaa63
TP
28077 ARM_EXT_OPT ("dsp", ARM_FEATURE_CORE_LOW (ARM_EXT_V5ExP | ARM_EXT_V6_DSP),
28078 ARM_FEATURE_CORE_LOW (ARM_EXT_V5ExP | ARM_EXT_V6_DSP),
28079 ARM_FEATURE_CORE (ARM_EXT_V7M, ARM_EXT2_V8M)),
823d2571
TG
28080 ARM_EXT_OPT ("fp", FPU_ARCH_VFP_ARMV8, ARM_FEATURE_COPROC (FPU_VFP_ARMV8),
28081 ARM_FEATURE_CORE_LOW (ARM_EXT_V8)),
b8ec4e87
JW
28082 ARM_EXT_OPT ("fp16", ARM_FEATURE_CORE_HIGH (ARM_EXT2_FP16_INST),
28083 ARM_FEATURE_CORE_HIGH (ARM_EXT2_FP16_INST),
28084 ARM_ARCH_V8_2A),
01f48020
TC
28085 ARM_EXT_OPT ("fp16fml", ARM_FEATURE_CORE_HIGH (ARM_EXT2_FP16_INST
28086 | ARM_EXT2_FP16_FML),
28087 ARM_FEATURE_CORE_HIGH (ARM_EXT2_FP16_INST
28088 | ARM_EXT2_FP16_FML),
28089 ARM_ARCH_V8_2A),
d942732e 28090 ARM_EXT_OPT2 ("idiv", ARM_FEATURE_CORE_LOW (ARM_EXT_ADIV | ARM_EXT_DIV),
823d2571 28091 ARM_FEATURE_CORE_LOW (ARM_EXT_ADIV | ARM_EXT_DIV),
d942732e
TP
28092 ARM_FEATURE_CORE_LOW (ARM_EXT_V7A),
28093 ARM_FEATURE_CORE_LOW (ARM_EXT_V7R)),
3d030cdb
TP
28094 /* Duplicate entry for the purpose of allowing ARMv7 to match in presence of
28095 Thumb divide instruction. Due to this having the same name as the
28096 previous entry, this will be ignored when doing command-line parsing and
28097 only considered by build attribute selection code. */
28098 ARM_EXT_OPT ("idiv", ARM_FEATURE_CORE_LOW (ARM_EXT_DIV),
28099 ARM_FEATURE_CORE_LOW (ARM_EXT_DIV),
28100 ARM_FEATURE_CORE_LOW (ARM_EXT_V7)),
823d2571 28101 ARM_EXT_OPT ("iwmmxt",ARM_FEATURE_COPROC (ARM_CEXT_IWMMXT),
d942732e 28102 ARM_FEATURE_COPROC (ARM_CEXT_IWMMXT), ARM_ARCH_NONE),
823d2571 28103 ARM_EXT_OPT ("iwmmxt2", ARM_FEATURE_COPROC (ARM_CEXT_IWMMXT2),
d942732e 28104 ARM_FEATURE_COPROC (ARM_CEXT_IWMMXT2), ARM_ARCH_NONE),
823d2571 28105 ARM_EXT_OPT ("maverick", ARM_FEATURE_COPROC (ARM_CEXT_MAVERICK),
d942732e
TP
28106 ARM_FEATURE_COPROC (ARM_CEXT_MAVERICK), ARM_ARCH_NONE),
28107 ARM_EXT_OPT2 ("mp", ARM_FEATURE_CORE_LOW (ARM_EXT_MP),
823d2571 28108 ARM_FEATURE_CORE_LOW (ARM_EXT_MP),
d942732e
TP
28109 ARM_FEATURE_CORE_LOW (ARM_EXT_V7A),
28110 ARM_FEATURE_CORE_LOW (ARM_EXT_V7R)),
823d2571
TG
28111 ARM_EXT_OPT ("os", ARM_FEATURE_CORE_LOW (ARM_EXT_OS),
28112 ARM_FEATURE_CORE_LOW (ARM_EXT_OS),
28113 ARM_FEATURE_CORE_LOW (ARM_EXT_V6M)),
ddfded2f
MW
28114 ARM_EXT_OPT ("pan", ARM_FEATURE_CORE_HIGH (ARM_EXT2_PAN),
28115 ARM_FEATURE (ARM_EXT_V8, ARM_EXT2_PAN, 0),
ced40572 28116 ARM_FEATURE_CORE_HIGH (ARM_EXT2_V8A)),
dad0c3bf
SD
28117 ARM_EXT_OPT ("predres", ARM_FEATURE_CORE_HIGH (ARM_EXT2_PREDRES),
28118 ARM_FEATURE_CORE_HIGH (ARM_EXT2_PREDRES),
28119 ARM_ARCH_V8A),
4d1464f2
MW
28120 ARM_EXT_OPT ("ras", ARM_FEATURE_CORE_HIGH (ARM_EXT2_RAS),
28121 ARM_FEATURE (ARM_EXT_V8, ARM_EXT2_RAS, 0),
ced40572 28122 ARM_FEATURE_CORE_HIGH (ARM_EXT2_V8A)),
643afb90
MW
28123 ARM_EXT_OPT ("rdma", FPU_ARCH_NEON_VFP_ARMV8_1,
28124 ARM_FEATURE_COPROC (FPU_NEON_ARMV8 | FPU_NEON_EXT_RDMA),
ced40572 28125 ARM_FEATURE_CORE_HIGH (ARM_EXT2_V8A)),
7fadb25d
SD
28126 ARM_EXT_OPT ("sb", ARM_FEATURE_CORE_HIGH (ARM_EXT2_SB),
28127 ARM_FEATURE_CORE_HIGH (ARM_EXT2_SB),
28128 ARM_ARCH_V8A),
d942732e 28129 ARM_EXT_OPT2 ("sec", ARM_FEATURE_CORE_LOW (ARM_EXT_SEC),
823d2571 28130 ARM_FEATURE_CORE_LOW (ARM_EXT_SEC),
d942732e
TP
28131 ARM_FEATURE_CORE_LOW (ARM_EXT_V6K),
28132 ARM_FEATURE_CORE_LOW (ARM_EXT_V7A)),
643afb90
MW
28133 ARM_EXT_OPT ("simd", FPU_ARCH_NEON_VFP_ARMV8,
28134 ARM_FEATURE_COPROC (FPU_NEON_ARMV8),
28135 ARM_FEATURE_CORE_LOW (ARM_EXT_V8)),
823d2571
TG
28136 ARM_EXT_OPT ("virt", ARM_FEATURE_CORE_LOW (ARM_EXT_VIRT | ARM_EXT_ADIV
28137 | ARM_EXT_DIV),
28138 ARM_FEATURE_CORE_LOW (ARM_EXT_VIRT),
28139 ARM_FEATURE_CORE_LOW (ARM_EXT_V7A)),
28140 ARM_EXT_OPT ("xscale",ARM_FEATURE_COPROC (ARM_CEXT_XSCALE),
d942732e
TP
28141 ARM_FEATURE_COPROC (ARM_CEXT_XSCALE), ARM_ARCH_NONE),
28142 { NULL, 0, ARM_ARCH_NONE, ARM_ARCH_NONE, { ARM_ARCH_NONE, ARM_ARCH_NONE } }
69133863 28143};
f3bad469 28144#undef ARM_EXT_OPT
69133863
MGD
28145
28146/* ISA floating-point and Advanced SIMD extensions. */
28147struct arm_option_fpu_value_table
28148{
0198d5e6
TC
28149 const char * name;
28150 const arm_feature_set value;
c19d1205 28151};
7ed4c4c5 28152
c19d1205
ZW
28153/* This list should, at a minimum, contain all the fpu names
28154 recognized by GCC. */
69133863 28155static const struct arm_option_fpu_value_table arm_fpus[] =
c19d1205
ZW
28156{
28157 {"softfpa", FPU_NONE},
28158 {"fpe", FPU_ARCH_FPE},
28159 {"fpe2", FPU_ARCH_FPE},
28160 {"fpe3", FPU_ARCH_FPA}, /* Third release supports LFM/SFM. */
28161 {"fpa", FPU_ARCH_FPA},
28162 {"fpa10", FPU_ARCH_FPA},
28163 {"fpa11", FPU_ARCH_FPA},
28164 {"arm7500fe", FPU_ARCH_FPA},
28165 {"softvfp", FPU_ARCH_VFP},
28166 {"softvfp+vfp", FPU_ARCH_VFP_V2},
28167 {"vfp", FPU_ARCH_VFP_V2},
28168 {"vfp9", FPU_ARCH_VFP_V2},
d5e0ba9c 28169 {"vfp3", FPU_ARCH_VFP_V3}, /* Undocumented, use vfpv3. */
c19d1205
ZW
28170 {"vfp10", FPU_ARCH_VFP_V2},
28171 {"vfp10-r0", FPU_ARCH_VFP_V1},
28172 {"vfpxd", FPU_ARCH_VFP_V1xD},
b1cc4aeb
PB
28173 {"vfpv2", FPU_ARCH_VFP_V2},
28174 {"vfpv3", FPU_ARCH_VFP_V3},
62f3b8c8 28175 {"vfpv3-fp16", FPU_ARCH_VFP_V3_FP16},
b1cc4aeb 28176 {"vfpv3-d16", FPU_ARCH_VFP_V3D16},
62f3b8c8
PB
28177 {"vfpv3-d16-fp16", FPU_ARCH_VFP_V3D16_FP16},
28178 {"vfpv3xd", FPU_ARCH_VFP_V3xD},
28179 {"vfpv3xd-fp16", FPU_ARCH_VFP_V3xD_FP16},
c19d1205
ZW
28180 {"arm1020t", FPU_ARCH_VFP_V1},
28181 {"arm1020e", FPU_ARCH_VFP_V2},
d5e0ba9c 28182 {"arm1136jfs", FPU_ARCH_VFP_V2}, /* Undocumented, use arm1136jf-s. */
c19d1205
ZW
28183 {"arm1136jf-s", FPU_ARCH_VFP_V2},
28184 {"maverick", FPU_ARCH_MAVERICK},
d5e0ba9c 28185 {"neon", FPU_ARCH_VFP_V3_PLUS_NEON_V1},
d3375ddd 28186 {"neon-vfpv3", FPU_ARCH_VFP_V3_PLUS_NEON_V1},
8e79c3df 28187 {"neon-fp16", FPU_ARCH_NEON_FP16},
62f3b8c8
PB
28188 {"vfpv4", FPU_ARCH_VFP_V4},
28189 {"vfpv4-d16", FPU_ARCH_VFP_V4D16},
ada65aa3 28190 {"fpv4-sp-d16", FPU_ARCH_VFP_V4_SP_D16},
a715796b
TG
28191 {"fpv5-d16", FPU_ARCH_VFP_V5D16},
28192 {"fpv5-sp-d16", FPU_ARCH_VFP_V5_SP_D16},
62f3b8c8 28193 {"neon-vfpv4", FPU_ARCH_NEON_VFP_V4},
bca38921
MGD
28194 {"fp-armv8", FPU_ARCH_VFP_ARMV8},
28195 {"neon-fp-armv8", FPU_ARCH_NEON_VFP_ARMV8},
28196 {"crypto-neon-fp-armv8",
28197 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8},
d6b4b13e 28198 {"neon-fp-armv8.1", FPU_ARCH_NEON_VFP_ARMV8_1},
081e4c7d
MW
28199 {"crypto-neon-fp-armv8.1",
28200 FPU_ARCH_CRYPTO_NEON_VFP_ARMV8_1},
e74cfd16
PB
28201 {NULL, ARM_ARCH_NONE}
28202};
28203
28204struct arm_option_value_table
28205{
e0471c16 28206 const char *name;
e74cfd16 28207 long value;
c19d1205 28208};
7ed4c4c5 28209
e74cfd16 28210static const struct arm_option_value_table arm_float_abis[] =
c19d1205
ZW
28211{
28212 {"hard", ARM_FLOAT_ABI_HARD},
28213 {"softfp", ARM_FLOAT_ABI_SOFTFP},
28214 {"soft", ARM_FLOAT_ABI_SOFT},
e74cfd16 28215 {NULL, 0}
c19d1205 28216};
7ed4c4c5 28217
c19d1205 28218#ifdef OBJ_ELF
3a4a14e9 28219/* We only know how to output GNU and ver 4/5 (AAELF) formats. */
e74cfd16 28220static const struct arm_option_value_table arm_eabis[] =
c19d1205
ZW
28221{
28222 {"gnu", EF_ARM_EABI_UNKNOWN},
28223 {"4", EF_ARM_EABI_VER4},
3a4a14e9 28224 {"5", EF_ARM_EABI_VER5},
e74cfd16 28225 {NULL, 0}
c19d1205
ZW
28226};
28227#endif
7ed4c4c5 28228
c19d1205
ZW
28229struct arm_long_option_table
28230{
0198d5e6 28231 const char * option; /* Substring to match. */
e0471c16 28232 const char * help; /* Help information. */
17b9d67d 28233 int (* func) (const char * subopt); /* Function to decode sub-option. */
e0471c16 28234 const char * deprecated; /* If non-null, print this message. */
c19d1205 28235};
7ed4c4c5 28236
c921be7d 28237static bfd_boolean
c168ce07 28238arm_parse_extension (const char *str, const arm_feature_set *opt_set,
34ef62f4
AV
28239 arm_feature_set *ext_set,
28240 const struct arm_ext_table *ext_table)
7ed4c4c5 28241{
69133863 28242 /* We insist on extensions being specified in alphabetical order, and with
fa94de6b
RM
28243 extensions being added before being removed. We achieve this by having
28244 the global ARM_EXTENSIONS table in alphabetical order, and using the
69133863 28245 ADDING_VALUE variable to indicate whether we are adding an extension (1)
fa94de6b 28246 or removing it (0) and only allowing it to change in the order
69133863
MGD
28247 -1 -> 1 -> 0. */
28248 const struct arm_option_extension_value_table * opt = NULL;
d942732e 28249 const arm_feature_set arm_any = ARM_ANY;
69133863
MGD
28250 int adding_value = -1;
28251
c19d1205 28252 while (str != NULL && *str != 0)
7ed4c4c5 28253 {
82b8a785 28254 const char *ext;
f3bad469 28255 size_t len;
7ed4c4c5 28256
c19d1205
ZW
28257 if (*str != '+')
28258 {
28259 as_bad (_("invalid architectural extension"));
c921be7d 28260 return FALSE;
c19d1205 28261 }
7ed4c4c5 28262
c19d1205
ZW
28263 str++;
28264 ext = strchr (str, '+');
7ed4c4c5 28265
c19d1205 28266 if (ext != NULL)
f3bad469 28267 len = ext - str;
c19d1205 28268 else
f3bad469 28269 len = strlen (str);
7ed4c4c5 28270
f3bad469 28271 if (len >= 2 && strncmp (str, "no", 2) == 0)
69133863
MGD
28272 {
28273 if (adding_value != 0)
28274 {
28275 adding_value = 0;
28276 opt = arm_extensions;
28277 }
28278
f3bad469 28279 len -= 2;
69133863
MGD
28280 str += 2;
28281 }
f3bad469 28282 else if (len > 0)
69133863
MGD
28283 {
28284 if (adding_value == -1)
28285 {
28286 adding_value = 1;
28287 opt = arm_extensions;
28288 }
28289 else if (adding_value != 1)
28290 {
28291 as_bad (_("must specify extensions to add before specifying "
28292 "those to remove"));
28293 return FALSE;
28294 }
28295 }
28296
f3bad469 28297 if (len == 0)
c19d1205
ZW
28298 {
28299 as_bad (_("missing architectural extension"));
c921be7d 28300 return FALSE;
c19d1205 28301 }
7ed4c4c5 28302
69133863
MGD
28303 gas_assert (adding_value != -1);
28304 gas_assert (opt != NULL);
28305
34ef62f4
AV
28306 if (ext_table != NULL)
28307 {
28308 const struct arm_ext_table * ext_opt = ext_table;
28309 bfd_boolean found = FALSE;
28310 for (; ext_opt->name != NULL; ext_opt++)
28311 if (ext_opt->name_len == len
28312 && strncmp (ext_opt->name, str, len) == 0)
28313 {
28314 if (adding_value)
28315 {
28316 if (ARM_FEATURE_ZERO (ext_opt->merge))
28317 /* TODO: Option not supported. When we remove the
28318 legacy table this case should error out. */
28319 continue;
28320
28321 ARM_MERGE_FEATURE_SETS (*ext_set, *ext_set, ext_opt->merge);
28322 }
28323 else
28324 {
28325 if (ARM_FEATURE_ZERO (ext_opt->clear))
28326 /* TODO: Option not supported. When we remove the
28327 legacy table this case should error out. */
28328 continue;
28329 ARM_CLEAR_FEATURE (*ext_set, *ext_set, ext_opt->clear);
28330 }
28331 found = TRUE;
28332 break;
28333 }
28334 if (found)
28335 {
28336 str = ext;
28337 continue;
28338 }
28339 }
28340
69133863
MGD
28341 /* Scan over the options table trying to find an exact match. */
28342 for (; opt->name != NULL; opt++)
f3bad469 28343 if (opt->name_len == len && strncmp (opt->name, str, len) == 0)
c19d1205 28344 {
d942732e
TP
28345 int i, nb_allowed_archs =
28346 sizeof (opt->allowed_archs) / sizeof (opt->allowed_archs[0]);
69133863 28347 /* Check we can apply the extension to this architecture. */
d942732e
TP
28348 for (i = 0; i < nb_allowed_archs; i++)
28349 {
28350 /* Empty entry. */
28351 if (ARM_FEATURE_EQUAL (opt->allowed_archs[i], arm_any))
28352 continue;
c168ce07 28353 if (ARM_FSET_CPU_SUBSET (opt->allowed_archs[i], *opt_set))
d942732e
TP
28354 break;
28355 }
28356 if (i == nb_allowed_archs)
69133863
MGD
28357 {
28358 as_bad (_("extension does not apply to the base architecture"));
28359 return FALSE;
28360 }
28361
28362 /* Add or remove the extension. */
28363 if (adding_value)
4d354d8b 28364 ARM_MERGE_FEATURE_SETS (*ext_set, *ext_set, opt->merge_value);
69133863 28365 else
4d354d8b 28366 ARM_CLEAR_FEATURE (*ext_set, *ext_set, opt->clear_value);
69133863 28367
3d030cdb
TP
28368 /* Allowing Thumb division instructions for ARMv7 in autodetection
28369 rely on this break so that duplicate extensions (extensions
28370 with the same name as a previous extension in the list) are not
28371 considered for command-line parsing. */
c19d1205
ZW
28372 break;
28373 }
7ed4c4c5 28374
c19d1205
ZW
28375 if (opt->name == NULL)
28376 {
69133863
MGD
28377 /* Did we fail to find an extension because it wasn't specified in
28378 alphabetical order, or because it does not exist? */
28379
28380 for (opt = arm_extensions; opt->name != NULL; opt++)
f3bad469 28381 if (opt->name_len == len && strncmp (opt->name, str, len) == 0)
69133863
MGD
28382 break;
28383
28384 if (opt->name == NULL)
28385 as_bad (_("unknown architectural extension `%s'"), str);
28386 else
28387 as_bad (_("architectural extensions must be specified in "
28388 "alphabetical order"));
28389
c921be7d 28390 return FALSE;
c19d1205 28391 }
69133863
MGD
28392 else
28393 {
28394 /* We should skip the extension we've just matched the next time
28395 round. */
28396 opt++;
28397 }
7ed4c4c5 28398
c19d1205
ZW
28399 str = ext;
28400 };
7ed4c4c5 28401
c921be7d 28402 return TRUE;
c19d1205 28403}
7ed4c4c5 28404
c921be7d 28405static bfd_boolean
17b9d67d 28406arm_parse_cpu (const char *str)
7ed4c4c5 28407{
f3bad469 28408 const struct arm_cpu_option_table *opt;
82b8a785 28409 const char *ext = strchr (str, '+');
f3bad469 28410 size_t len;
7ed4c4c5 28411
c19d1205 28412 if (ext != NULL)
f3bad469 28413 len = ext - str;
7ed4c4c5 28414 else
f3bad469 28415 len = strlen (str);
7ed4c4c5 28416
f3bad469 28417 if (len == 0)
7ed4c4c5 28418 {
c19d1205 28419 as_bad (_("missing cpu name `%s'"), str);
c921be7d 28420 return FALSE;
7ed4c4c5
NC
28421 }
28422
c19d1205 28423 for (opt = arm_cpus; opt->name != NULL; opt++)
f3bad469 28424 if (opt->name_len == len && strncmp (opt->name, str, len) == 0)
c19d1205 28425 {
c168ce07 28426 mcpu_cpu_opt = &opt->value;
4d354d8b
TP
28427 if (mcpu_ext_opt == NULL)
28428 mcpu_ext_opt = XNEW (arm_feature_set);
28429 *mcpu_ext_opt = opt->ext;
e74cfd16 28430 mcpu_fpu_opt = &opt->default_fpu;
ee065d83 28431 if (opt->canonical_name)
ef8e6722
JW
28432 {
28433 gas_assert (sizeof selected_cpu_name > strlen (opt->canonical_name));
28434 strcpy (selected_cpu_name, opt->canonical_name);
28435 }
ee065d83
PB
28436 else
28437 {
f3bad469 28438 size_t i;
c921be7d 28439
ef8e6722
JW
28440 if (len >= sizeof selected_cpu_name)
28441 len = (sizeof selected_cpu_name) - 1;
28442
f3bad469 28443 for (i = 0; i < len; i++)
ee065d83
PB
28444 selected_cpu_name[i] = TOUPPER (opt->name[i]);
28445 selected_cpu_name[i] = 0;
28446 }
7ed4c4c5 28447
c19d1205 28448 if (ext != NULL)
34ef62f4 28449 return arm_parse_extension (ext, mcpu_cpu_opt, mcpu_ext_opt, NULL);
7ed4c4c5 28450
c921be7d 28451 return TRUE;
c19d1205 28452 }
7ed4c4c5 28453
c19d1205 28454 as_bad (_("unknown cpu `%s'"), str);
c921be7d 28455 return FALSE;
7ed4c4c5
NC
28456}
28457
c921be7d 28458static bfd_boolean
17b9d67d 28459arm_parse_arch (const char *str)
7ed4c4c5 28460{
e74cfd16 28461 const struct arm_arch_option_table *opt;
82b8a785 28462 const char *ext = strchr (str, '+');
f3bad469 28463 size_t len;
7ed4c4c5 28464
c19d1205 28465 if (ext != NULL)
f3bad469 28466 len = ext - str;
7ed4c4c5 28467 else
f3bad469 28468 len = strlen (str);
7ed4c4c5 28469
f3bad469 28470 if (len == 0)
7ed4c4c5 28471 {
c19d1205 28472 as_bad (_("missing architecture name `%s'"), str);
c921be7d 28473 return FALSE;
7ed4c4c5
NC
28474 }
28475
c19d1205 28476 for (opt = arm_archs; opt->name != NULL; opt++)
f3bad469 28477 if (opt->name_len == len && strncmp (opt->name, str, len) == 0)
c19d1205 28478 {
e74cfd16 28479 march_cpu_opt = &opt->value;
4d354d8b
TP
28480 if (march_ext_opt == NULL)
28481 march_ext_opt = XNEW (arm_feature_set);
28482 *march_ext_opt = arm_arch_none;
e74cfd16 28483 march_fpu_opt = &opt->default_fpu;
5f4273c7 28484 strcpy (selected_cpu_name, opt->name);
7ed4c4c5 28485
c19d1205 28486 if (ext != NULL)
34ef62f4
AV
28487 return arm_parse_extension (ext, march_cpu_opt, march_ext_opt,
28488 opt->ext_table);
7ed4c4c5 28489
c921be7d 28490 return TRUE;
c19d1205
ZW
28491 }
28492
28493 as_bad (_("unknown architecture `%s'\n"), str);
c921be7d 28494 return FALSE;
7ed4c4c5 28495}
eb043451 28496
c921be7d 28497static bfd_boolean
17b9d67d 28498arm_parse_fpu (const char * str)
c19d1205 28499{
69133863 28500 const struct arm_option_fpu_value_table * opt;
b99bd4ef 28501
c19d1205
ZW
28502 for (opt = arm_fpus; opt->name != NULL; opt++)
28503 if (streq (opt->name, str))
28504 {
e74cfd16 28505 mfpu_opt = &opt->value;
c921be7d 28506 return TRUE;
c19d1205 28507 }
b99bd4ef 28508
c19d1205 28509 as_bad (_("unknown floating point format `%s'\n"), str);
c921be7d 28510 return FALSE;
c19d1205
ZW
28511}
28512
c921be7d 28513static bfd_boolean
17b9d67d 28514arm_parse_float_abi (const char * str)
b99bd4ef 28515{
e74cfd16 28516 const struct arm_option_value_table * opt;
b99bd4ef 28517
c19d1205
ZW
28518 for (opt = arm_float_abis; opt->name != NULL; opt++)
28519 if (streq (opt->name, str))
28520 {
28521 mfloat_abi_opt = opt->value;
c921be7d 28522 return TRUE;
c19d1205 28523 }
cc8a6dd0 28524
c19d1205 28525 as_bad (_("unknown floating point abi `%s'\n"), str);
c921be7d 28526 return FALSE;
c19d1205 28527}
b99bd4ef 28528
c19d1205 28529#ifdef OBJ_ELF
c921be7d 28530static bfd_boolean
17b9d67d 28531arm_parse_eabi (const char * str)
c19d1205 28532{
e74cfd16 28533 const struct arm_option_value_table *opt;
cc8a6dd0 28534
c19d1205
ZW
28535 for (opt = arm_eabis; opt->name != NULL; opt++)
28536 if (streq (opt->name, str))
28537 {
28538 meabi_flags = opt->value;
c921be7d 28539 return TRUE;
c19d1205
ZW
28540 }
28541 as_bad (_("unknown EABI `%s'\n"), str);
c921be7d 28542 return FALSE;
c19d1205
ZW
28543}
28544#endif
cc8a6dd0 28545
c921be7d 28546static bfd_boolean
17b9d67d 28547arm_parse_it_mode (const char * str)
e07e6e58 28548{
c921be7d 28549 bfd_boolean ret = TRUE;
e07e6e58
NC
28550
28551 if (streq ("arm", str))
28552 implicit_it_mode = IMPLICIT_IT_MODE_ARM;
28553 else if (streq ("thumb", str))
28554 implicit_it_mode = IMPLICIT_IT_MODE_THUMB;
28555 else if (streq ("always", str))
28556 implicit_it_mode = IMPLICIT_IT_MODE_ALWAYS;
28557 else if (streq ("never", str))
28558 implicit_it_mode = IMPLICIT_IT_MODE_NEVER;
28559 else
28560 {
28561 as_bad (_("unknown implicit IT mode `%s', should be "\
477330fc 28562 "arm, thumb, always, or never."), str);
c921be7d 28563 ret = FALSE;
e07e6e58
NC
28564 }
28565
28566 return ret;
28567}
28568
2e6976a8 28569static bfd_boolean
17b9d67d 28570arm_ccs_mode (const char * unused ATTRIBUTE_UNUSED)
2e6976a8
DG
28571{
28572 codecomposer_syntax = TRUE;
28573 arm_comment_chars[0] = ';';
28574 arm_line_separator_chars[0] = 0;
28575 return TRUE;
28576}
28577
c19d1205
ZW
28578struct arm_long_option_table arm_long_opts[] =
28579{
28580 {"mcpu=", N_("<cpu name>\t assemble for CPU <cpu name>"),
28581 arm_parse_cpu, NULL},
28582 {"march=", N_("<arch name>\t assemble for architecture <arch name>"),
28583 arm_parse_arch, NULL},
28584 {"mfpu=", N_("<fpu name>\t assemble for FPU architecture <fpu name>"),
28585 arm_parse_fpu, NULL},
28586 {"mfloat-abi=", N_("<abi>\t assemble for floating point ABI <abi>"),
28587 arm_parse_float_abi, NULL},
28588#ifdef OBJ_ELF
7fac0536 28589 {"meabi=", N_("<ver>\t\t assemble for eabi version <ver>"),
c19d1205
ZW
28590 arm_parse_eabi, NULL},
28591#endif
e07e6e58
NC
28592 {"mimplicit-it=", N_("<mode>\t controls implicit insertion of IT instructions"),
28593 arm_parse_it_mode, NULL},
2e6976a8
DG
28594 {"mccs", N_("\t\t\t TI CodeComposer Studio syntax compatibility mode"),
28595 arm_ccs_mode, NULL},
c19d1205
ZW
28596 {NULL, NULL, 0, NULL}
28597};
cc8a6dd0 28598
c19d1205 28599int
17b9d67d 28600md_parse_option (int c, const char * arg)
c19d1205
ZW
28601{
28602 struct arm_option_table *opt;
e74cfd16 28603 const struct arm_legacy_option_table *fopt;
c19d1205 28604 struct arm_long_option_table *lopt;
b99bd4ef 28605
c19d1205 28606 switch (c)
b99bd4ef 28607 {
c19d1205
ZW
28608#ifdef OPTION_EB
28609 case OPTION_EB:
28610 target_big_endian = 1;
28611 break;
28612#endif
cc8a6dd0 28613
c19d1205
ZW
28614#ifdef OPTION_EL
28615 case OPTION_EL:
28616 target_big_endian = 0;
28617 break;
28618#endif
b99bd4ef 28619
845b51d6
PB
28620 case OPTION_FIX_V4BX:
28621 fix_v4bx = TRUE;
28622 break;
28623
18a20338
CL
28624#ifdef OBJ_ELF
28625 case OPTION_FDPIC:
28626 arm_fdpic = TRUE;
28627 break;
28628#endif /* OBJ_ELF */
28629
c19d1205
ZW
28630 case 'a':
28631 /* Listing option. Just ignore these, we don't support additional
28632 ones. */
28633 return 0;
b99bd4ef 28634
c19d1205
ZW
28635 default:
28636 for (opt = arm_opts; opt->option != NULL; opt++)
28637 {
28638 if (c == opt->option[0]
28639 && ((arg == NULL && opt->option[1] == 0)
28640 || streq (arg, opt->option + 1)))
28641 {
c19d1205 28642 /* If the option is deprecated, tell the user. */
278df34e 28643 if (warn_on_deprecated && opt->deprecated != NULL)
c19d1205
ZW
28644 as_tsktsk (_("option `-%c%s' is deprecated: %s"), c,
28645 arg ? arg : "", _(opt->deprecated));
b99bd4ef 28646
c19d1205
ZW
28647 if (opt->var != NULL)
28648 *opt->var = opt->value;
cc8a6dd0 28649
c19d1205
ZW
28650 return 1;
28651 }
28652 }
b99bd4ef 28653
e74cfd16
PB
28654 for (fopt = arm_legacy_opts; fopt->option != NULL; fopt++)
28655 {
28656 if (c == fopt->option[0]
28657 && ((arg == NULL && fopt->option[1] == 0)
28658 || streq (arg, fopt->option + 1)))
28659 {
e74cfd16 28660 /* If the option is deprecated, tell the user. */
278df34e 28661 if (warn_on_deprecated && fopt->deprecated != NULL)
e74cfd16
PB
28662 as_tsktsk (_("option `-%c%s' is deprecated: %s"), c,
28663 arg ? arg : "", _(fopt->deprecated));
e74cfd16
PB
28664
28665 if (fopt->var != NULL)
28666 *fopt->var = &fopt->value;
28667
28668 return 1;
28669 }
28670 }
28671
c19d1205
ZW
28672 for (lopt = arm_long_opts; lopt->option != NULL; lopt++)
28673 {
28674 /* These options are expected to have an argument. */
28675 if (c == lopt->option[0]
28676 && arg != NULL
28677 && strncmp (arg, lopt->option + 1,
28678 strlen (lopt->option + 1)) == 0)
28679 {
c19d1205 28680 /* If the option is deprecated, tell the user. */
278df34e 28681 if (warn_on_deprecated && lopt->deprecated != NULL)
c19d1205
ZW
28682 as_tsktsk (_("option `-%c%s' is deprecated: %s"), c, arg,
28683 _(lopt->deprecated));
b99bd4ef 28684
c19d1205
ZW
28685 /* Call the sup-option parser. */
28686 return lopt->func (arg + strlen (lopt->option) - 1);
28687 }
28688 }
a737bd4d 28689
c19d1205
ZW
28690 return 0;
28691 }
a394c00f 28692
c19d1205
ZW
28693 return 1;
28694}
a394c00f 28695
c19d1205
ZW
28696void
28697md_show_usage (FILE * fp)
a394c00f 28698{
c19d1205
ZW
28699 struct arm_option_table *opt;
28700 struct arm_long_option_table *lopt;
a394c00f 28701
c19d1205 28702 fprintf (fp, _(" ARM-specific assembler options:\n"));
a394c00f 28703
c19d1205
ZW
28704 for (opt = arm_opts; opt->option != NULL; opt++)
28705 if (opt->help != NULL)
28706 fprintf (fp, " -%-23s%s\n", opt->option, _(opt->help));
a394c00f 28707
c19d1205
ZW
28708 for (lopt = arm_long_opts; lopt->option != NULL; lopt++)
28709 if (lopt->help != NULL)
28710 fprintf (fp, " -%s%s\n", lopt->option, _(lopt->help));
a394c00f 28711
c19d1205
ZW
28712#ifdef OPTION_EB
28713 fprintf (fp, _("\
28714 -EB assemble code for a big-endian cpu\n"));
a394c00f
NC
28715#endif
28716
c19d1205
ZW
28717#ifdef OPTION_EL
28718 fprintf (fp, _("\
28719 -EL assemble code for a little-endian cpu\n"));
a737bd4d 28720#endif
845b51d6
PB
28721
28722 fprintf (fp, _("\
28723 --fix-v4bx Allow BX in ARMv4 code\n"));
18a20338
CL
28724
28725#ifdef OBJ_ELF
28726 fprintf (fp, _("\
28727 --fdpic generate an FDPIC object file\n"));
28728#endif /* OBJ_ELF */
c19d1205 28729}
ee065d83 28730
ee065d83 28731#ifdef OBJ_ELF
0198d5e6 28732
62b3e311
PB
28733typedef struct
28734{
28735 int val;
28736 arm_feature_set flags;
28737} cpu_arch_ver_table;
28738
2c6b98ea
TP
28739/* Mapping from CPU features to EABI CPU arch values. Table must be sorted
28740 chronologically for architectures, with an exception for ARMv6-M and
28741 ARMv6S-M due to legacy reasons. No new architecture should have a
28742 special case. This allows for build attribute selection results to be
28743 stable when new architectures are added. */
62b3e311
PB
28744static const cpu_arch_ver_table cpu_arch_ver[] =
28745{
031254f2
AV
28746 {TAG_CPU_ARCH_PRE_V4, ARM_ARCH_V1},
28747 {TAG_CPU_ARCH_PRE_V4, ARM_ARCH_V2},
28748 {TAG_CPU_ARCH_PRE_V4, ARM_ARCH_V2S},
28749 {TAG_CPU_ARCH_PRE_V4, ARM_ARCH_V3},
28750 {TAG_CPU_ARCH_PRE_V4, ARM_ARCH_V3M},
28751 {TAG_CPU_ARCH_V4, ARM_ARCH_V4xM},
28752 {TAG_CPU_ARCH_V4, ARM_ARCH_V4},
28753 {TAG_CPU_ARCH_V4T, ARM_ARCH_V4TxM},
28754 {TAG_CPU_ARCH_V4T, ARM_ARCH_V4T},
28755 {TAG_CPU_ARCH_V5T, ARM_ARCH_V5xM},
28756 {TAG_CPU_ARCH_V5T, ARM_ARCH_V5},
28757 {TAG_CPU_ARCH_V5T, ARM_ARCH_V5TxM},
28758 {TAG_CPU_ARCH_V5T, ARM_ARCH_V5T},
28759 {TAG_CPU_ARCH_V5TE, ARM_ARCH_V5TExP},
28760 {TAG_CPU_ARCH_V5TE, ARM_ARCH_V5TE},
28761 {TAG_CPU_ARCH_V5TEJ, ARM_ARCH_V5TEJ},
28762 {TAG_CPU_ARCH_V6, ARM_ARCH_V6},
28763 {TAG_CPU_ARCH_V6KZ, ARM_ARCH_V6Z},
28764 {TAG_CPU_ARCH_V6KZ, ARM_ARCH_V6KZ},
28765 {TAG_CPU_ARCH_V6K, ARM_ARCH_V6K},
28766 {TAG_CPU_ARCH_V6T2, ARM_ARCH_V6T2},
28767 {TAG_CPU_ARCH_V6T2, ARM_ARCH_V6KT2},
28768 {TAG_CPU_ARCH_V6T2, ARM_ARCH_V6ZT2},
28769 {TAG_CPU_ARCH_V6T2, ARM_ARCH_V6KZT2},
2c6b98ea
TP
28770
28771 /* When assembling a file with only ARMv6-M or ARMv6S-M instruction, GNU as
28772 always selected build attributes to match those of ARMv6-M
28773 (resp. ARMv6S-M). However, due to these architectures being a strict
28774 subset of ARMv7-M in terms of instructions available, ARMv7-M attributes
28775 would be selected when fully respecting chronology of architectures.
28776 It is thus necessary to make a special case of ARMv6-M and ARMv6S-M and
28777 move them before ARMv7 architectures. */
031254f2
AV
28778 {TAG_CPU_ARCH_V6_M, ARM_ARCH_V6M},
28779 {TAG_CPU_ARCH_V6S_M, ARM_ARCH_V6SM},
28780
28781 {TAG_CPU_ARCH_V7, ARM_ARCH_V7},
28782 {TAG_CPU_ARCH_V7, ARM_ARCH_V7A},
28783 {TAG_CPU_ARCH_V7, ARM_ARCH_V7R},
28784 {TAG_CPU_ARCH_V7, ARM_ARCH_V7M},
28785 {TAG_CPU_ARCH_V7, ARM_ARCH_V7VE},
28786 {TAG_CPU_ARCH_V7E_M, ARM_ARCH_V7EM},
28787 {TAG_CPU_ARCH_V8, ARM_ARCH_V8A},
28788 {TAG_CPU_ARCH_V8, ARM_ARCH_V8_1A},
28789 {TAG_CPU_ARCH_V8, ARM_ARCH_V8_2A},
28790 {TAG_CPU_ARCH_V8, ARM_ARCH_V8_3A},
28791 {TAG_CPU_ARCH_V8M_BASE, ARM_ARCH_V8M_BASE},
28792 {TAG_CPU_ARCH_V8M_MAIN, ARM_ARCH_V8M_MAIN},
28793 {TAG_CPU_ARCH_V8R, ARM_ARCH_V8R},
28794 {TAG_CPU_ARCH_V8, ARM_ARCH_V8_4A},
28795 {TAG_CPU_ARCH_V8, ARM_ARCH_V8_5A},
28796 {TAG_CPU_ARCH_V8_1M_MAIN, ARM_ARCH_V8_1M_MAIN},
28797 {-1, ARM_ARCH_NONE}
62b3e311
PB
28798};
28799
ee3c0378 28800/* Set an attribute if it has not already been set by the user. */
0198d5e6 28801
ee3c0378
AS
28802static void
28803aeabi_set_attribute_int (int tag, int value)
28804{
28805 if (tag < 1
28806 || tag >= NUM_KNOWN_OBJ_ATTRIBUTES
28807 || !attributes_set_explicitly[tag])
28808 bfd_elf_add_proc_attr_int (stdoutput, tag, value);
28809}
28810
28811static void
28812aeabi_set_attribute_string (int tag, const char *value)
28813{
28814 if (tag < 1
28815 || tag >= NUM_KNOWN_OBJ_ATTRIBUTES
28816 || !attributes_set_explicitly[tag])
28817 bfd_elf_add_proc_attr_string (stdoutput, tag, value);
28818}
28819
2c6b98ea
TP
28820/* Return whether features in the *NEEDED feature set are available via
28821 extensions for the architecture whose feature set is *ARCH_FSET. */
0198d5e6 28822
2c6b98ea
TP
28823static bfd_boolean
28824have_ext_for_needed_feat_p (const arm_feature_set *arch_fset,
28825 const arm_feature_set *needed)
28826{
28827 int i, nb_allowed_archs;
28828 arm_feature_set ext_fset;
28829 const struct arm_option_extension_value_table *opt;
28830
28831 ext_fset = arm_arch_none;
28832 for (opt = arm_extensions; opt->name != NULL; opt++)
28833 {
28834 /* Extension does not provide any feature we need. */
28835 if (!ARM_CPU_HAS_FEATURE (*needed, opt->merge_value))
28836 continue;
28837
28838 nb_allowed_archs =
28839 sizeof (opt->allowed_archs) / sizeof (opt->allowed_archs[0]);
28840 for (i = 0; i < nb_allowed_archs; i++)
28841 {
28842 /* Empty entry. */
28843 if (ARM_FEATURE_EQUAL (opt->allowed_archs[i], arm_arch_any))
28844 break;
28845
28846 /* Extension is available, add it. */
28847 if (ARM_FSET_CPU_SUBSET (opt->allowed_archs[i], *arch_fset))
28848 ARM_MERGE_FEATURE_SETS (ext_fset, ext_fset, opt->merge_value);
28849 }
28850 }
28851
28852 /* Can we enable all features in *needed? */
28853 return ARM_FSET_CPU_SUBSET (*needed, ext_fset);
28854}
28855
28856/* Select value for Tag_CPU_arch and Tag_CPU_arch_profile build attributes for
28857 a given architecture feature set *ARCH_EXT_FSET including extension feature
28858 set *EXT_FSET. Selection logic used depend on EXACT_MATCH:
28859 - if true, check for an exact match of the architecture modulo extensions;
28860 - otherwise, select build attribute value of the first superset
28861 architecture released so that results remains stable when new architectures
28862 are added.
28863 For -march/-mcpu=all the build attribute value of the most featureful
28864 architecture is returned. Tag_CPU_arch_profile result is returned in
28865 PROFILE. */
0198d5e6 28866
2c6b98ea
TP
28867static int
28868get_aeabi_cpu_arch_from_fset (const arm_feature_set *arch_ext_fset,
28869 const arm_feature_set *ext_fset,
28870 char *profile, int exact_match)
28871{
28872 arm_feature_set arch_fset;
28873 const cpu_arch_ver_table *p_ver, *p_ver_ret = NULL;
28874
28875 /* Select most featureful architecture with all its extensions if building
28876 for -march=all as the feature sets used to set build attributes. */
28877 if (ARM_FEATURE_EQUAL (*arch_ext_fset, arm_arch_any))
28878 {
28879 /* Force revisiting of decision for each new architecture. */
031254f2 28880 gas_assert (MAX_TAG_CPU_ARCH <= TAG_CPU_ARCH_V8_1M_MAIN);
2c6b98ea
TP
28881 *profile = 'A';
28882 return TAG_CPU_ARCH_V8;
28883 }
28884
28885 ARM_CLEAR_FEATURE (arch_fset, *arch_ext_fset, *ext_fset);
28886
28887 for (p_ver = cpu_arch_ver; p_ver->val != -1; p_ver++)
28888 {
28889 arm_feature_set known_arch_fset;
28890
28891 ARM_CLEAR_FEATURE (known_arch_fset, p_ver->flags, fpu_any);
28892 if (exact_match)
28893 {
28894 /* Base architecture match user-specified architecture and
28895 extensions, eg. ARMv6S-M matching -march=armv6-m+os. */
28896 if (ARM_FEATURE_EQUAL (*arch_ext_fset, known_arch_fset))
28897 {
28898 p_ver_ret = p_ver;
28899 goto found;
28900 }
28901 /* Base architecture match user-specified architecture only
28902 (eg. ARMv6-M in the same case as above). Record it in case we
28903 find a match with above condition. */
28904 else if (p_ver_ret == NULL
28905 && ARM_FEATURE_EQUAL (arch_fset, known_arch_fset))
28906 p_ver_ret = p_ver;
28907 }
28908 else
28909 {
28910
28911 /* Architecture has all features wanted. */
28912 if (ARM_FSET_CPU_SUBSET (arch_fset, known_arch_fset))
28913 {
28914 arm_feature_set added_fset;
28915
28916 /* Compute features added by this architecture over the one
28917 recorded in p_ver_ret. */
28918 if (p_ver_ret != NULL)
28919 ARM_CLEAR_FEATURE (added_fset, known_arch_fset,
28920 p_ver_ret->flags);
28921 /* First architecture that match incl. with extensions, or the
28922 only difference in features over the recorded match is
28923 features that were optional and are now mandatory. */
28924 if (p_ver_ret == NULL
28925 || ARM_FSET_CPU_SUBSET (added_fset, arch_fset))
28926 {
28927 p_ver_ret = p_ver;
28928 goto found;
28929 }
28930 }
28931 else if (p_ver_ret == NULL)
28932 {
28933 arm_feature_set needed_ext_fset;
28934
28935 ARM_CLEAR_FEATURE (needed_ext_fset, arch_fset, known_arch_fset);
28936
28937 /* Architecture has all features needed when using some
28938 extensions. Record it and continue searching in case there
28939 exist an architecture providing all needed features without
28940 the need for extensions (eg. ARMv6S-M Vs ARMv6-M with
28941 OS extension). */
28942 if (have_ext_for_needed_feat_p (&known_arch_fset,
28943 &needed_ext_fset))
28944 p_ver_ret = p_ver;
28945 }
28946 }
28947 }
28948
28949 if (p_ver_ret == NULL)
28950 return -1;
28951
28952found:
28953 /* Tag_CPU_arch_profile. */
28954 if (ARM_CPU_HAS_FEATURE (p_ver_ret->flags, arm_ext_v7a)
28955 || ARM_CPU_HAS_FEATURE (p_ver_ret->flags, arm_ext_v8)
28956 || (ARM_CPU_HAS_FEATURE (p_ver_ret->flags, arm_ext_atomics)
28957 && !ARM_CPU_HAS_FEATURE (p_ver_ret->flags, arm_ext_v8m_m_only)))
28958 *profile = 'A';
28959 else if (ARM_CPU_HAS_FEATURE (p_ver_ret->flags, arm_ext_v7r))
28960 *profile = 'R';
28961 else if (ARM_CPU_HAS_FEATURE (p_ver_ret->flags, arm_ext_m))
28962 *profile = 'M';
28963 else
28964 *profile = '\0';
28965 return p_ver_ret->val;
28966}
28967
ee065d83 28968/* Set the public EABI object attributes. */
0198d5e6 28969
c168ce07 28970static void
ee065d83
PB
28971aeabi_set_public_attributes (void)
28972{
b90d5ba0 28973 char profile = '\0';
2c6b98ea 28974 int arch = -1;
90ec0d68 28975 int virt_sec = 0;
bca38921 28976 int fp16_optional = 0;
2c6b98ea
TP
28977 int skip_exact_match = 0;
28978 arm_feature_set flags, flags_arch, flags_ext;
ee065d83 28979
54bab281
TP
28980 /* Autodetection mode, choose the architecture based the instructions
28981 actually used. */
28982 if (no_cpu_selected ())
28983 {
28984 ARM_MERGE_FEATURE_SETS (flags, arm_arch_used, thumb_arch_used);
ddd7f988 28985
54bab281
TP
28986 if (ARM_CPU_HAS_FEATURE (arm_arch_used, arm_arch_any))
28987 ARM_MERGE_FEATURE_SETS (flags, flags, arm_ext_v1);
ddd7f988 28988
54bab281
TP
28989 if (ARM_CPU_HAS_FEATURE (thumb_arch_used, arm_arch_any))
28990 ARM_MERGE_FEATURE_SETS (flags, flags, arm_ext_v4t);
ddd7f988 28991
54bab281 28992 /* Code run during relaxation relies on selected_cpu being set. */
4d354d8b
TP
28993 ARM_CLEAR_FEATURE (flags_arch, flags, fpu_any);
28994 flags_ext = arm_arch_none;
28995 ARM_CLEAR_FEATURE (selected_arch, flags_arch, flags_ext);
28996 selected_ext = flags_ext;
54bab281
TP
28997 selected_cpu = flags;
28998 }
28999 /* Otherwise, choose the architecture based on the capabilities of the
29000 requested cpu. */
29001 else
4d354d8b
TP
29002 {
29003 ARM_MERGE_FEATURE_SETS (flags_arch, selected_arch, selected_ext);
29004 ARM_CLEAR_FEATURE (flags_arch, flags_arch, fpu_any);
29005 flags_ext = selected_ext;
29006 flags = selected_cpu;
29007 }
29008 ARM_MERGE_FEATURE_SETS (flags, flags, selected_fpu);
7f78eb34 29009
ddd7f988 29010 /* Allow the user to override the reported architecture. */
4d354d8b 29011 if (!ARM_FEATURE_ZERO (selected_object_arch))
7a1d4c38 29012 {
4d354d8b 29013 ARM_CLEAR_FEATURE (flags_arch, selected_object_arch, fpu_any);
2c6b98ea 29014 flags_ext = arm_arch_none;
7a1d4c38 29015 }
2c6b98ea 29016 else
4d354d8b 29017 skip_exact_match = ARM_FEATURE_EQUAL (selected_cpu, arm_arch_any);
2c6b98ea
TP
29018
29019 /* When this function is run again after relaxation has happened there is no
29020 way to determine whether an architecture or CPU was specified by the user:
29021 - selected_cpu is set above for relaxation to work;
29022 - march_cpu_opt is not set if only -mcpu or .cpu is used;
29023 - mcpu_cpu_opt is set to arm_arch_any for autodetection.
29024 Therefore, if not in -march=all case we first try an exact match and fall
29025 back to autodetection. */
29026 if (!skip_exact_match)
29027 arch = get_aeabi_cpu_arch_from_fset (&flags_arch, &flags_ext, &profile, 1);
29028 if (arch == -1)
29029 arch = get_aeabi_cpu_arch_from_fset (&flags_arch, &flags_ext, &profile, 0);
29030 if (arch == -1)
29031 as_bad (_("no architecture contains all the instructions used\n"));
9e3c6df6 29032
ee065d83
PB
29033 /* Tag_CPU_name. */
29034 if (selected_cpu_name[0])
29035 {
91d6fa6a 29036 char *q;
ee065d83 29037
91d6fa6a
NC
29038 q = selected_cpu_name;
29039 if (strncmp (q, "armv", 4) == 0)
ee065d83
PB
29040 {
29041 int i;
5f4273c7 29042
91d6fa6a
NC
29043 q += 4;
29044 for (i = 0; q[i]; i++)
29045 q[i] = TOUPPER (q[i]);
ee065d83 29046 }
91d6fa6a 29047 aeabi_set_attribute_string (Tag_CPU_name, q);
ee065d83 29048 }
62f3b8c8 29049
ee065d83 29050 /* Tag_CPU_arch. */
ee3c0378 29051 aeabi_set_attribute_int (Tag_CPU_arch, arch);
62f3b8c8 29052
62b3e311 29053 /* Tag_CPU_arch_profile. */
69239280
MGD
29054 if (profile != '\0')
29055 aeabi_set_attribute_int (Tag_CPU_arch_profile, profile);
62f3b8c8 29056
15afaa63 29057 /* Tag_DSP_extension. */
4d354d8b 29058 if (ARM_CPU_HAS_FEATURE (selected_ext, arm_ext_dsp))
6c290d53 29059 aeabi_set_attribute_int (Tag_DSP_extension, 1);
15afaa63 29060
2c6b98ea 29061 ARM_CLEAR_FEATURE (flags_arch, flags, fpu_any);
ee065d83 29062 /* Tag_ARM_ISA_use. */
ee3c0378 29063 if (ARM_CPU_HAS_FEATURE (flags, arm_ext_v1)
2c6b98ea 29064 || ARM_FEATURE_ZERO (flags_arch))
ee3c0378 29065 aeabi_set_attribute_int (Tag_ARM_ISA_use, 1);
62f3b8c8 29066
ee065d83 29067 /* Tag_THUMB_ISA_use. */
ee3c0378 29068 if (ARM_CPU_HAS_FEATURE (flags, arm_ext_v4t)
2c6b98ea 29069 || ARM_FEATURE_ZERO (flags_arch))
4ed7ed8d
TP
29070 {
29071 int thumb_isa_use;
29072
29073 if (!ARM_CPU_HAS_FEATURE (flags, arm_ext_v8)
16a1fa25 29074 && ARM_CPU_HAS_FEATURE (flags, arm_ext_v8m_m_only))
4ed7ed8d
TP
29075 thumb_isa_use = 3;
29076 else if (ARM_CPU_HAS_FEATURE (flags, arm_arch_t2))
29077 thumb_isa_use = 2;
29078 else
29079 thumb_isa_use = 1;
29080 aeabi_set_attribute_int (Tag_THUMB_ISA_use, thumb_isa_use);
29081 }
62f3b8c8 29082
ee065d83 29083 /* Tag_VFP_arch. */
a715796b
TG
29084 if (ARM_CPU_HAS_FEATURE (flags, fpu_vfp_ext_armv8xd))
29085 aeabi_set_attribute_int (Tag_VFP_arch,
29086 ARM_CPU_HAS_FEATURE (flags, fpu_vfp_ext_d32)
29087 ? 7 : 8);
bca38921 29088 else if (ARM_CPU_HAS_FEATURE (flags, fpu_vfp_ext_fma))
62f3b8c8
PB
29089 aeabi_set_attribute_int (Tag_VFP_arch,
29090 ARM_CPU_HAS_FEATURE (flags, fpu_vfp_ext_d32)
29091 ? 5 : 6);
29092 else if (ARM_CPU_HAS_FEATURE (flags, fpu_vfp_ext_d32))
bca38921
MGD
29093 {
29094 fp16_optional = 1;
29095 aeabi_set_attribute_int (Tag_VFP_arch, 3);
29096 }
ada65aa3 29097 else if (ARM_CPU_HAS_FEATURE (flags, fpu_vfp_ext_v3xd))
bca38921
MGD
29098 {
29099 aeabi_set_attribute_int (Tag_VFP_arch, 4);
29100 fp16_optional = 1;
29101 }
ee3c0378
AS
29102 else if (ARM_CPU_HAS_FEATURE (flags, fpu_vfp_ext_v2))
29103 aeabi_set_attribute_int (Tag_VFP_arch, 2);
29104 else if (ARM_CPU_HAS_FEATURE (flags, fpu_vfp_ext_v1)
477330fc 29105 || ARM_CPU_HAS_FEATURE (flags, fpu_vfp_ext_v1xd))
ee3c0378 29106 aeabi_set_attribute_int (Tag_VFP_arch, 1);
62f3b8c8 29107
4547cb56
NC
29108 /* Tag_ABI_HardFP_use. */
29109 if (ARM_CPU_HAS_FEATURE (flags, fpu_vfp_ext_v1xd)
29110 && !ARM_CPU_HAS_FEATURE (flags, fpu_vfp_ext_v1))
29111 aeabi_set_attribute_int (Tag_ABI_HardFP_use, 1);
29112
ee065d83 29113 /* Tag_WMMX_arch. */
ee3c0378
AS
29114 if (ARM_CPU_HAS_FEATURE (flags, arm_cext_iwmmxt2))
29115 aeabi_set_attribute_int (Tag_WMMX_arch, 2);
29116 else if (ARM_CPU_HAS_FEATURE (flags, arm_cext_iwmmxt))
29117 aeabi_set_attribute_int (Tag_WMMX_arch, 1);
62f3b8c8 29118
ee3c0378 29119 /* Tag_Advanced_SIMD_arch (formerly Tag_NEON_arch). */
9411fd44
MW
29120 if (ARM_CPU_HAS_FEATURE (flags, fpu_neon_ext_v8_1))
29121 aeabi_set_attribute_int (Tag_Advanced_SIMD_arch, 4);
29122 else if (ARM_CPU_HAS_FEATURE (flags, fpu_neon_ext_armv8))
bca38921
MGD
29123 aeabi_set_attribute_int (Tag_Advanced_SIMD_arch, 3);
29124 else if (ARM_CPU_HAS_FEATURE (flags, fpu_neon_ext_v1))
29125 {
29126 if (ARM_CPU_HAS_FEATURE (flags, fpu_neon_ext_fma))
29127 {
29128 aeabi_set_attribute_int (Tag_Advanced_SIMD_arch, 2);
29129 }
29130 else
29131 {
29132 aeabi_set_attribute_int (Tag_Advanced_SIMD_arch, 1);
29133 fp16_optional = 1;
29134 }
29135 }
fa94de6b 29136
a7ad558c
AV
29137 if (ARM_CPU_HAS_FEATURE (flags, mve_fp_ext))
29138 aeabi_set_attribute_int (Tag_MVE_arch, 2);
29139 else if (ARM_CPU_HAS_FEATURE (flags, mve_ext))
29140 aeabi_set_attribute_int (Tag_MVE_arch, 1);
29141
ee3c0378 29142 /* Tag_VFP_HP_extension (formerly Tag_NEON_FP16_arch). */
bca38921 29143 if (ARM_CPU_HAS_FEATURE (flags, fpu_vfp_fp16) && fp16_optional)
ee3c0378 29144 aeabi_set_attribute_int (Tag_VFP_HP_extension, 1);
4547cb56 29145
69239280
MGD
29146 /* Tag_DIV_use.
29147
29148 We set Tag_DIV_use to two when integer divide instructions have been used
29149 in ARM state, or when Thumb integer divide instructions have been used,
29150 but we have no architecture profile set, nor have we any ARM instructions.
29151
4ed7ed8d
TP
29152 For ARMv8-A and ARMv8-M we set the tag to 0 as integer divide is implied
29153 by the base architecture.
bca38921 29154
69239280 29155 For new architectures we will have to check these tests. */
031254f2 29156 gas_assert (arch <= TAG_CPU_ARCH_V8_1M_MAIN);
4ed7ed8d
TP
29157 if (ARM_CPU_HAS_FEATURE (flags, arm_ext_v8)
29158 || ARM_CPU_HAS_FEATURE (flags, arm_ext_v8m))
bca38921
MGD
29159 aeabi_set_attribute_int (Tag_DIV_use, 0);
29160 else if (ARM_CPU_HAS_FEATURE (flags, arm_ext_adiv)
29161 || (profile == '\0'
29162 && ARM_CPU_HAS_FEATURE (flags, arm_ext_div)
29163 && !ARM_CPU_HAS_FEATURE (arm_arch_used, arm_arch_any)))
eea54501 29164 aeabi_set_attribute_int (Tag_DIV_use, 2);
60e5ef9f
MGD
29165
29166 /* Tag_MP_extension_use. */
29167 if (ARM_CPU_HAS_FEATURE (flags, arm_ext_mp))
29168 aeabi_set_attribute_int (Tag_MPextension_use, 1);
f4c65163
MGD
29169
29170 /* Tag Virtualization_use. */
29171 if (ARM_CPU_HAS_FEATURE (flags, arm_ext_sec))
90ec0d68
MGD
29172 virt_sec |= 1;
29173 if (ARM_CPU_HAS_FEATURE (flags, arm_ext_virt))
29174 virt_sec |= 2;
29175 if (virt_sec != 0)
29176 aeabi_set_attribute_int (Tag_Virtualization_use, virt_sec);
ee065d83
PB
29177}
29178
c168ce07
TP
29179/* Post relaxation hook. Recompute ARM attributes now that relaxation is
29180 finished and free extension feature bits which will not be used anymore. */
0198d5e6 29181
c168ce07
TP
29182void
29183arm_md_post_relax (void)
29184{
29185 aeabi_set_public_attributes ();
4d354d8b
TP
29186 XDELETE (mcpu_ext_opt);
29187 mcpu_ext_opt = NULL;
29188 XDELETE (march_ext_opt);
29189 march_ext_opt = NULL;
c168ce07
TP
29190}
29191
104d59d1 29192/* Add the default contents for the .ARM.attributes section. */
0198d5e6 29193
ee065d83
PB
29194void
29195arm_md_end (void)
29196{
ee065d83
PB
29197 if (EF_ARM_EABI_VERSION (meabi_flags) < EF_ARM_EABI_VER4)
29198 return;
29199
29200 aeabi_set_public_attributes ();
ee065d83 29201}
8463be01 29202#endif /* OBJ_ELF */
ee065d83 29203
ee065d83
PB
29204/* Parse a .cpu directive. */
29205
29206static void
29207s_arm_cpu (int ignored ATTRIBUTE_UNUSED)
29208{
e74cfd16 29209 const struct arm_cpu_option_table *opt;
ee065d83
PB
29210 char *name;
29211 char saved_char;
29212
29213 name = input_line_pointer;
5f4273c7 29214 while (*input_line_pointer && !ISSPACE (*input_line_pointer))
ee065d83
PB
29215 input_line_pointer++;
29216 saved_char = *input_line_pointer;
29217 *input_line_pointer = 0;
29218
29219 /* Skip the first "all" entry. */
29220 for (opt = arm_cpus + 1; opt->name != NULL; opt++)
29221 if (streq (opt->name, name))
29222 {
4d354d8b
TP
29223 selected_arch = opt->value;
29224 selected_ext = opt->ext;
29225 ARM_MERGE_FEATURE_SETS (selected_cpu, selected_arch, selected_ext);
ee065d83 29226 if (opt->canonical_name)
5f4273c7 29227 strcpy (selected_cpu_name, opt->canonical_name);
ee065d83
PB
29228 else
29229 {
29230 int i;
29231 for (i = 0; opt->name[i]; i++)
29232 selected_cpu_name[i] = TOUPPER (opt->name[i]);
f3bad469 29233
ee065d83
PB
29234 selected_cpu_name[i] = 0;
29235 }
4d354d8b
TP
29236 ARM_MERGE_FEATURE_SETS (cpu_variant, selected_cpu, selected_fpu);
29237
ee065d83
PB
29238 *input_line_pointer = saved_char;
29239 demand_empty_rest_of_line ();
29240 return;
29241 }
29242 as_bad (_("unknown cpu `%s'"), name);
29243 *input_line_pointer = saved_char;
29244 ignore_rest_of_line ();
29245}
29246
ee065d83
PB
29247/* Parse a .arch directive. */
29248
29249static void
29250s_arm_arch (int ignored ATTRIBUTE_UNUSED)
29251{
e74cfd16 29252 const struct arm_arch_option_table *opt;
ee065d83
PB
29253 char saved_char;
29254 char *name;
29255
29256 name = input_line_pointer;
5f4273c7 29257 while (*input_line_pointer && !ISSPACE (*input_line_pointer))
ee065d83
PB
29258 input_line_pointer++;
29259 saved_char = *input_line_pointer;
29260 *input_line_pointer = 0;
29261
29262 /* Skip the first "all" entry. */
29263 for (opt = arm_archs + 1; opt->name != NULL; opt++)
29264 if (streq (opt->name, name))
29265 {
4d354d8b
TP
29266 selected_arch = opt->value;
29267 selected_ext = arm_arch_none;
29268 selected_cpu = selected_arch;
5f4273c7 29269 strcpy (selected_cpu_name, opt->name);
4d354d8b 29270 ARM_MERGE_FEATURE_SETS (cpu_variant, selected_cpu, selected_fpu);
ee065d83
PB
29271 *input_line_pointer = saved_char;
29272 demand_empty_rest_of_line ();
29273 return;
29274 }
29275
29276 as_bad (_("unknown architecture `%s'\n"), name);
29277 *input_line_pointer = saved_char;
29278 ignore_rest_of_line ();
29279}
29280
7a1d4c38
PB
29281/* Parse a .object_arch directive. */
29282
29283static void
29284s_arm_object_arch (int ignored ATTRIBUTE_UNUSED)
29285{
29286 const struct arm_arch_option_table *opt;
29287 char saved_char;
29288 char *name;
29289
29290 name = input_line_pointer;
5f4273c7 29291 while (*input_line_pointer && !ISSPACE (*input_line_pointer))
7a1d4c38
PB
29292 input_line_pointer++;
29293 saved_char = *input_line_pointer;
29294 *input_line_pointer = 0;
29295
29296 /* Skip the first "all" entry. */
29297 for (opt = arm_archs + 1; opt->name != NULL; opt++)
29298 if (streq (opt->name, name))
29299 {
4d354d8b 29300 selected_object_arch = opt->value;
7a1d4c38
PB
29301 *input_line_pointer = saved_char;
29302 demand_empty_rest_of_line ();
29303 return;
29304 }
29305
29306 as_bad (_("unknown architecture `%s'\n"), name);
29307 *input_line_pointer = saved_char;
29308 ignore_rest_of_line ();
29309}
29310
69133863
MGD
29311/* Parse a .arch_extension directive. */
29312
29313static void
29314s_arm_arch_extension (int ignored ATTRIBUTE_UNUSED)
29315{
29316 const struct arm_option_extension_value_table *opt;
29317 char saved_char;
29318 char *name;
29319 int adding_value = 1;
29320
29321 name = input_line_pointer;
29322 while (*input_line_pointer && !ISSPACE (*input_line_pointer))
29323 input_line_pointer++;
29324 saved_char = *input_line_pointer;
29325 *input_line_pointer = 0;
29326
29327 if (strlen (name) >= 2
29328 && strncmp (name, "no", 2) == 0)
29329 {
29330 adding_value = 0;
29331 name += 2;
29332 }
29333
29334 for (opt = arm_extensions; opt->name != NULL; opt++)
29335 if (streq (opt->name, name))
29336 {
d942732e
TP
29337 int i, nb_allowed_archs =
29338 sizeof (opt->allowed_archs) / sizeof (opt->allowed_archs[i]);
29339 for (i = 0; i < nb_allowed_archs; i++)
29340 {
29341 /* Empty entry. */
4d354d8b 29342 if (ARM_CPU_IS_ANY (opt->allowed_archs[i]))
d942732e 29343 continue;
4d354d8b 29344 if (ARM_FSET_CPU_SUBSET (opt->allowed_archs[i], selected_arch))
d942732e
TP
29345 break;
29346 }
29347
29348 if (i == nb_allowed_archs)
69133863
MGD
29349 {
29350 as_bad (_("architectural extension `%s' is not allowed for the "
29351 "current base architecture"), name);
29352 break;
29353 }
29354
29355 if (adding_value)
4d354d8b 29356 ARM_MERGE_FEATURE_SETS (selected_ext, selected_ext,
5a70a223 29357 opt->merge_value);
69133863 29358 else
4d354d8b 29359 ARM_CLEAR_FEATURE (selected_ext, selected_ext, opt->clear_value);
69133863 29360
4d354d8b
TP
29361 ARM_MERGE_FEATURE_SETS (selected_cpu, selected_arch, selected_ext);
29362 ARM_MERGE_FEATURE_SETS (cpu_variant, selected_cpu, selected_fpu);
69133863
MGD
29363 *input_line_pointer = saved_char;
29364 demand_empty_rest_of_line ();
3d030cdb
TP
29365 /* Allowing Thumb division instructions for ARMv7 in autodetection rely
29366 on this return so that duplicate extensions (extensions with the
29367 same name as a previous extension in the list) are not considered
29368 for command-line parsing. */
69133863
MGD
29369 return;
29370 }
29371
29372 if (opt->name == NULL)
e673710a 29373 as_bad (_("unknown architecture extension `%s'\n"), name);
69133863
MGD
29374
29375 *input_line_pointer = saved_char;
29376 ignore_rest_of_line ();
29377}
29378
ee065d83
PB
29379/* Parse a .fpu directive. */
29380
29381static void
29382s_arm_fpu (int ignored ATTRIBUTE_UNUSED)
29383{
69133863 29384 const struct arm_option_fpu_value_table *opt;
ee065d83
PB
29385 char saved_char;
29386 char *name;
29387
29388 name = input_line_pointer;
5f4273c7 29389 while (*input_line_pointer && !ISSPACE (*input_line_pointer))
ee065d83
PB
29390 input_line_pointer++;
29391 saved_char = *input_line_pointer;
29392 *input_line_pointer = 0;
5f4273c7 29393
ee065d83
PB
29394 for (opt = arm_fpus; opt->name != NULL; opt++)
29395 if (streq (opt->name, name))
29396 {
4d354d8b
TP
29397 selected_fpu = opt->value;
29398#ifndef CPU_DEFAULT
29399 if (no_cpu_selected ())
29400 ARM_MERGE_FEATURE_SETS (cpu_variant, arm_arch_any, selected_fpu);
29401 else
29402#endif
29403 ARM_MERGE_FEATURE_SETS (cpu_variant, selected_cpu, selected_fpu);
ee065d83
PB
29404 *input_line_pointer = saved_char;
29405 demand_empty_rest_of_line ();
29406 return;
29407 }
29408
29409 as_bad (_("unknown floating point format `%s'\n"), name);
29410 *input_line_pointer = saved_char;
29411 ignore_rest_of_line ();
29412}
ee065d83 29413
794ba86a 29414/* Copy symbol information. */
f31fef98 29415
794ba86a
DJ
29416void
29417arm_copy_symbol_attributes (symbolS *dest, symbolS *src)
29418{
29419 ARM_GET_FLAG (dest) = ARM_GET_FLAG (src);
29420}
e04befd0 29421
f31fef98 29422#ifdef OBJ_ELF
e04befd0
AS
29423/* Given a symbolic attribute NAME, return the proper integer value.
29424 Returns -1 if the attribute is not known. */
f31fef98 29425
e04befd0
AS
29426int
29427arm_convert_symbolic_attribute (const char *name)
29428{
f31fef98
NC
29429 static const struct
29430 {
29431 const char * name;
29432 const int tag;
29433 }
29434 attribute_table[] =
29435 {
29436 /* When you modify this table you should
29437 also modify the list in doc/c-arm.texi. */
e04befd0 29438#define T(tag) {#tag, tag}
f31fef98
NC
29439 T (Tag_CPU_raw_name),
29440 T (Tag_CPU_name),
29441 T (Tag_CPU_arch),
29442 T (Tag_CPU_arch_profile),
29443 T (Tag_ARM_ISA_use),
29444 T (Tag_THUMB_ISA_use),
75375b3e 29445 T (Tag_FP_arch),
f31fef98
NC
29446 T (Tag_VFP_arch),
29447 T (Tag_WMMX_arch),
29448 T (Tag_Advanced_SIMD_arch),
29449 T (Tag_PCS_config),
29450 T (Tag_ABI_PCS_R9_use),
29451 T (Tag_ABI_PCS_RW_data),
29452 T (Tag_ABI_PCS_RO_data),
29453 T (Tag_ABI_PCS_GOT_use),
29454 T (Tag_ABI_PCS_wchar_t),
29455 T (Tag_ABI_FP_rounding),
29456 T (Tag_ABI_FP_denormal),
29457 T (Tag_ABI_FP_exceptions),
29458 T (Tag_ABI_FP_user_exceptions),
29459 T (Tag_ABI_FP_number_model),
75375b3e 29460 T (Tag_ABI_align_needed),
f31fef98 29461 T (Tag_ABI_align8_needed),
75375b3e 29462 T (Tag_ABI_align_preserved),
f31fef98
NC
29463 T (Tag_ABI_align8_preserved),
29464 T (Tag_ABI_enum_size),
29465 T (Tag_ABI_HardFP_use),
29466 T (Tag_ABI_VFP_args),
29467 T (Tag_ABI_WMMX_args),
29468 T (Tag_ABI_optimization_goals),
29469 T (Tag_ABI_FP_optimization_goals),
29470 T (Tag_compatibility),
29471 T (Tag_CPU_unaligned_access),
75375b3e 29472 T (Tag_FP_HP_extension),
f31fef98
NC
29473 T (Tag_VFP_HP_extension),
29474 T (Tag_ABI_FP_16bit_format),
cd21e546
MGD
29475 T (Tag_MPextension_use),
29476 T (Tag_DIV_use),
f31fef98
NC
29477 T (Tag_nodefaults),
29478 T (Tag_also_compatible_with),
29479 T (Tag_conformance),
29480 T (Tag_T2EE_use),
29481 T (Tag_Virtualization_use),
15afaa63 29482 T (Tag_DSP_extension),
a7ad558c 29483 T (Tag_MVE_arch),
cd21e546 29484 /* We deliberately do not include Tag_MPextension_use_legacy. */
e04befd0 29485#undef T
f31fef98 29486 };
e04befd0
AS
29487 unsigned int i;
29488
29489 if (name == NULL)
29490 return -1;
29491
f31fef98 29492 for (i = 0; i < ARRAY_SIZE (attribute_table); i++)
c921be7d 29493 if (streq (name, attribute_table[i].name))
e04befd0
AS
29494 return attribute_table[i].tag;
29495
29496 return -1;
29497}
267bf995 29498
93ef582d
NC
29499/* Apply sym value for relocations only in the case that they are for
29500 local symbols in the same segment as the fixup and you have the
29501 respective architectural feature for blx and simple switches. */
0198d5e6 29502
267bf995 29503int
93ef582d 29504arm_apply_sym_value (struct fix * fixP, segT this_seg)
267bf995
RR
29505{
29506 if (fixP->fx_addsy
29507 && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v5t)
93ef582d
NC
29508 /* PR 17444: If the local symbol is in a different section then a reloc
29509 will always be generated for it, so applying the symbol value now
29510 will result in a double offset being stored in the relocation. */
29511 && (S_GET_SEGMENT (fixP->fx_addsy) == this_seg)
34e77a92 29512 && !S_FORCE_RELOC (fixP->fx_addsy, TRUE))
267bf995
RR
29513 {
29514 switch (fixP->fx_r_type)
29515 {
29516 case BFD_RELOC_ARM_PCREL_BLX:
29517 case BFD_RELOC_THUMB_PCREL_BRANCH23:
29518 if (ARM_IS_FUNC (fixP->fx_addsy))
29519 return 1;
29520 break;
29521
29522 case BFD_RELOC_ARM_PCREL_CALL:
29523 case BFD_RELOC_THUMB_PCREL_BLX:
29524 if (THUMB_IS_FUNC (fixP->fx_addsy))
93ef582d 29525 return 1;
267bf995
RR
29526 break;
29527
29528 default:
29529 break;
29530 }
29531
29532 }
29533 return 0;
29534}
f31fef98 29535#endif /* OBJ_ELF */
This page took 5.773744 seconds and 4 git commands to generate.