[AArch64][SVE 20/32] Add support for tied operands
[deliverable/binutils-gdb.git] / opcodes / aarch64-opc.c
CommitLineData
a06ea964 1/* aarch64-opc.c -- AArch64 opcode support.
6f2750fe 2 Copyright (C) 2009-2016 Free Software Foundation, Inc.
a06ea964
NC
3 Contributed by ARM Ltd.
4
5 This file is part of the GNU opcodes library.
6
7 This library is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3, or (at your option)
10 any later version.
11
12 It is distributed in the hope that it will be useful, but WITHOUT
13 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
14 or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
15 License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; see the file COPYING3. If not,
19 see <http://www.gnu.org/licenses/>. */
20
21#include "sysdep.h"
22#include <assert.h>
23#include <stdlib.h>
24#include <stdio.h>
25#include <stdint.h>
26#include <stdarg.h>
27#include <inttypes.h>
28
29#include "opintl.h"
30
31#include "aarch64-opc.h"
32
33#ifdef DEBUG_AARCH64
34int debug_dump = FALSE;
35#endif /* DEBUG_AARCH64 */
36
37/* Helper functions to determine which operand to be used to encode/decode
38 the size:Q fields for AdvSIMD instructions. */
39
40static inline bfd_boolean
41vector_qualifier_p (enum aarch64_opnd_qualifier qualifier)
42{
43 return ((qualifier >= AARCH64_OPND_QLF_V_8B
44 && qualifier <= AARCH64_OPND_QLF_V_1Q) ? TRUE
45 : FALSE);
46}
47
48static inline bfd_boolean
49fp_qualifier_p (enum aarch64_opnd_qualifier qualifier)
50{
51 return ((qualifier >= AARCH64_OPND_QLF_S_B
52 && qualifier <= AARCH64_OPND_QLF_S_Q) ? TRUE
53 : FALSE);
54}
55
56enum data_pattern
57{
58 DP_UNKNOWN,
59 DP_VECTOR_3SAME,
60 DP_VECTOR_LONG,
61 DP_VECTOR_WIDE,
62 DP_VECTOR_ACROSS_LANES,
63};
64
65static const char significant_operand_index [] =
66{
67 0, /* DP_UNKNOWN, by default using operand 0. */
68 0, /* DP_VECTOR_3SAME */
69 1, /* DP_VECTOR_LONG */
70 2, /* DP_VECTOR_WIDE */
71 1, /* DP_VECTOR_ACROSS_LANES */
72};
73
74/* Given a sequence of qualifiers in QUALIFIERS, determine and return
75 the data pattern.
76 N.B. QUALIFIERS is a possible sequence of qualifiers each of which
77 corresponds to one of a sequence of operands. */
78
79static enum data_pattern
80get_data_pattern (const aarch64_opnd_qualifier_seq_t qualifiers)
81{
82 if (vector_qualifier_p (qualifiers[0]) == TRUE)
83 {
84 /* e.g. v.4s, v.4s, v.4s
85 or v.4h, v.4h, v.h[3]. */
86 if (qualifiers[0] == qualifiers[1]
87 && vector_qualifier_p (qualifiers[2]) == TRUE
88 && (aarch64_get_qualifier_esize (qualifiers[0])
89 == aarch64_get_qualifier_esize (qualifiers[1]))
90 && (aarch64_get_qualifier_esize (qualifiers[0])
91 == aarch64_get_qualifier_esize (qualifiers[2])))
92 return DP_VECTOR_3SAME;
93 /* e.g. v.8h, v.8b, v.8b.
94 or v.4s, v.4h, v.h[2].
95 or v.8h, v.16b. */
96 if (vector_qualifier_p (qualifiers[1]) == TRUE
97 && aarch64_get_qualifier_esize (qualifiers[0]) != 0
98 && (aarch64_get_qualifier_esize (qualifiers[0])
99 == aarch64_get_qualifier_esize (qualifiers[1]) << 1))
100 return DP_VECTOR_LONG;
101 /* e.g. v.8h, v.8h, v.8b. */
102 if (qualifiers[0] == qualifiers[1]
103 && vector_qualifier_p (qualifiers[2]) == TRUE
104 && aarch64_get_qualifier_esize (qualifiers[0]) != 0
105 && (aarch64_get_qualifier_esize (qualifiers[0])
106 == aarch64_get_qualifier_esize (qualifiers[2]) << 1)
107 && (aarch64_get_qualifier_esize (qualifiers[0])
108 == aarch64_get_qualifier_esize (qualifiers[1])))
109 return DP_VECTOR_WIDE;
110 }
111 else if (fp_qualifier_p (qualifiers[0]) == TRUE)
112 {
113 /* e.g. SADDLV <V><d>, <Vn>.<T>. */
114 if (vector_qualifier_p (qualifiers[1]) == TRUE
115 && qualifiers[2] == AARCH64_OPND_QLF_NIL)
116 return DP_VECTOR_ACROSS_LANES;
117 }
118
119 return DP_UNKNOWN;
120}
121
122/* Select the operand to do the encoding/decoding of the 'size:Q' fields in
123 the AdvSIMD instructions. */
124/* N.B. it is possible to do some optimization that doesn't call
125 get_data_pattern each time when we need to select an operand. We can
126 either buffer the caculated the result or statically generate the data,
127 however, it is not obvious that the optimization will bring significant
128 benefit. */
129
130int
131aarch64_select_operand_for_sizeq_field_coding (const aarch64_opcode *opcode)
132{
133 return
134 significant_operand_index [get_data_pattern (opcode->qualifiers_list[0])];
135}
136\f
137const aarch64_field fields[] =
138{
139 { 0, 0 }, /* NIL. */
140 { 0, 4 }, /* cond2: condition in truly conditional-executed inst. */
141 { 0, 4 }, /* nzcv: flag bit specifier, encoded in the "nzcv" field. */
142 { 5, 5 }, /* defgh: d:e:f:g:h bits in AdvSIMD modified immediate. */
143 { 16, 3 }, /* abc: a:b:c bits in AdvSIMD modified immediate. */
144 { 5, 19 }, /* imm19: e.g. in CBZ. */
145 { 5, 19 }, /* immhi: e.g. in ADRP. */
146 { 29, 2 }, /* immlo: e.g. in ADRP. */
147 { 22, 2 }, /* size: in most AdvSIMD and floating-point instructions. */
148 { 10, 2 }, /* vldst_size: size field in the AdvSIMD load/store inst. */
149 { 29, 1 }, /* op: in AdvSIMD modified immediate instructions. */
150 { 30, 1 }, /* Q: in most AdvSIMD instructions. */
151 { 0, 5 }, /* Rt: in load/store instructions. */
152 { 0, 5 }, /* Rd: in many integer instructions. */
153 { 5, 5 }, /* Rn: in many integer instructions. */
154 { 10, 5 }, /* Rt2: in load/store pair instructions. */
155 { 10, 5 }, /* Ra: in fp instructions. */
156 { 5, 3 }, /* op2: in the system instructions. */
157 { 8, 4 }, /* CRm: in the system instructions. */
158 { 12, 4 }, /* CRn: in the system instructions. */
159 { 16, 3 }, /* op1: in the system instructions. */
160 { 19, 2 }, /* op0: in the system instructions. */
161 { 10, 3 }, /* imm3: in add/sub extended reg instructions. */
162 { 12, 4 }, /* cond: condition flags as a source operand. */
163 { 12, 4 }, /* opcode: in advsimd load/store instructions. */
164 { 12, 4 }, /* cmode: in advsimd modified immediate instructions. */
165 { 13, 3 }, /* asisdlso_opcode: opcode in advsimd ld/st single element. */
166 { 13, 2 }, /* len: in advsimd tbl/tbx instructions. */
167 { 16, 5 }, /* Rm: in ld/st reg offset and some integer inst. */
168 { 16, 5 }, /* Rs: in load/store exclusive instructions. */
169 { 13, 3 }, /* option: in ld/st reg offset + add/sub extended reg inst. */
170 { 12, 1 }, /* S: in load/store reg offset instructions. */
171 { 21, 2 }, /* hw: in move wide constant instructions. */
172 { 22, 2 }, /* opc: in load/store reg offset instructions. */
173 { 23, 1 }, /* opc1: in load/store reg offset instructions. */
174 { 22, 2 }, /* shift: in add/sub reg/imm shifted instructions. */
175 { 22, 2 }, /* type: floating point type field in fp data inst. */
176 { 30, 2 }, /* ldst_size: size field in ld/st reg offset inst. */
177 { 10, 6 }, /* imm6: in add/sub reg shifted instructions. */
178 { 11, 4 }, /* imm4: in advsimd ext and advsimd ins instructions. */
179 { 16, 5 }, /* imm5: in conditional compare (immediate) instructions. */
180 { 15, 7 }, /* imm7: in load/store pair pre/post index instructions. */
181 { 13, 8 }, /* imm8: in floating-point scalar move immediate inst. */
182 { 12, 9 }, /* imm9: in load/store pre/post index instructions. */
183 { 10, 12 }, /* imm12: in ld/st unsigned imm or add/sub shifted inst. */
184 { 5, 14 }, /* imm14: in test bit and branch instructions. */
185 { 5, 16 }, /* imm16: in exception instructions. */
186 { 0, 26 }, /* imm26: in unconditional branch instructions. */
187 { 10, 6 }, /* imms: in bitfield and logical immediate instructions. */
188 { 16, 6 }, /* immr: in bitfield and logical immediate instructions. */
189 { 16, 3 }, /* immb: in advsimd shift by immediate instructions. */
190 { 19, 4 }, /* immh: in advsimd shift by immediate instructions. */
191 { 22, 1 }, /* N: in logical (immediate) instructions. */
192 { 11, 1 }, /* index: in ld/st inst deciding the pre/post-index. */
193 { 24, 1 }, /* index2: in ld/st pair inst deciding the pre/post-index. */
194 { 31, 1 }, /* sf: in integer data processing instructions. */
ee804238 195 { 30, 1 }, /* lse_size: in LSE extension atomic instructions. */
a06ea964
NC
196 { 11, 1 }, /* H: in advsimd scalar x indexed element instructions. */
197 { 21, 1 }, /* L: in advsimd scalar x indexed element instructions. */
198 { 20, 1 }, /* M: in advsimd scalar x indexed element instructions. */
199 { 31, 1 }, /* b5: in the test bit and branch instructions. */
200 { 19, 5 }, /* b40: in the test bit and branch instructions. */
201 { 10, 6 }, /* scale: in the fixed-point scalar to fp converting inst. */
202};
203
204enum aarch64_operand_class
205aarch64_get_operand_class (enum aarch64_opnd type)
206{
207 return aarch64_operands[type].op_class;
208}
209
210const char *
211aarch64_get_operand_name (enum aarch64_opnd type)
212{
213 return aarch64_operands[type].name;
214}
215
216/* Get operand description string.
217 This is usually for the diagnosis purpose. */
218const char *
219aarch64_get_operand_desc (enum aarch64_opnd type)
220{
221 return aarch64_operands[type].desc;
222}
223
224/* Table of all conditional affixes. */
225const aarch64_cond aarch64_conds[16] =
226{
227 {{"eq"}, 0x0},
228 {{"ne"}, 0x1},
229 {{"cs", "hs"}, 0x2},
230 {{"cc", "lo", "ul"}, 0x3},
231 {{"mi"}, 0x4},
232 {{"pl"}, 0x5},
233 {{"vs"}, 0x6},
234 {{"vc"}, 0x7},
235 {{"hi"}, 0x8},
236 {{"ls"}, 0x9},
237 {{"ge"}, 0xa},
238 {{"lt"}, 0xb},
239 {{"gt"}, 0xc},
240 {{"le"}, 0xd},
241 {{"al"}, 0xe},
242 {{"nv"}, 0xf},
243};
244
245const aarch64_cond *
246get_cond_from_value (aarch64_insn value)
247{
248 assert (value < 16);
249 return &aarch64_conds[(unsigned int) value];
250}
251
252const aarch64_cond *
253get_inverted_cond (const aarch64_cond *cond)
254{
255 return &aarch64_conds[cond->value ^ 0x1];
256}
257
258/* Table describing the operand extension/shifting operators; indexed by
259 enum aarch64_modifier_kind.
260
261 The value column provides the most common values for encoding modifiers,
262 which enables table-driven encoding/decoding for the modifiers. */
263const struct aarch64_name_value_pair aarch64_operand_modifiers [] =
264{
265 {"none", 0x0},
266 {"msl", 0x0},
267 {"ror", 0x3},
268 {"asr", 0x2},
269 {"lsr", 0x1},
270 {"lsl", 0x0},
271 {"uxtb", 0x0},
272 {"uxth", 0x1},
273 {"uxtw", 0x2},
274 {"uxtx", 0x3},
275 {"sxtb", 0x4},
276 {"sxth", 0x5},
277 {"sxtw", 0x6},
278 {"sxtx", 0x7},
279 {NULL, 0},
280};
281
282enum aarch64_modifier_kind
283aarch64_get_operand_modifier (const struct aarch64_name_value_pair *desc)
284{
285 return desc - aarch64_operand_modifiers;
286}
287
288aarch64_insn
289aarch64_get_operand_modifier_value (enum aarch64_modifier_kind kind)
290{
291 return aarch64_operand_modifiers[kind].value;
292}
293
294enum aarch64_modifier_kind
295aarch64_get_operand_modifier_from_value (aarch64_insn value,
296 bfd_boolean extend_p)
297{
298 if (extend_p == TRUE)
299 return AARCH64_MOD_UXTB + value;
300 else
301 return AARCH64_MOD_LSL - value;
302}
303
304bfd_boolean
305aarch64_extend_operator_p (enum aarch64_modifier_kind kind)
306{
307 return (kind > AARCH64_MOD_LSL && kind <= AARCH64_MOD_SXTX)
308 ? TRUE : FALSE;
309}
310
311static inline bfd_boolean
312aarch64_shift_operator_p (enum aarch64_modifier_kind kind)
313{
314 return (kind >= AARCH64_MOD_ROR && kind <= AARCH64_MOD_LSL)
315 ? TRUE : FALSE;
316}
317
318const struct aarch64_name_value_pair aarch64_barrier_options[16] =
319{
320 { "#0x00", 0x0 },
321 { "oshld", 0x1 },
322 { "oshst", 0x2 },
323 { "osh", 0x3 },
324 { "#0x04", 0x4 },
325 { "nshld", 0x5 },
326 { "nshst", 0x6 },
327 { "nsh", 0x7 },
328 { "#0x08", 0x8 },
329 { "ishld", 0x9 },
330 { "ishst", 0xa },
331 { "ish", 0xb },
332 { "#0x0c", 0xc },
333 { "ld", 0xd },
334 { "st", 0xe },
335 { "sy", 0xf },
336};
337
9ed608f9
MW
338/* Table describing the operands supported by the aliases of the HINT
339 instruction.
340
341 The name column is the operand that is accepted for the alias. The value
342 column is the hint number of the alias. The list of operands is terminated
343 by NULL in the name column. */
344
345const struct aarch64_name_value_pair aarch64_hint_options[] =
346{
1e6f4800 347 { "csync", 0x11 }, /* PSB CSYNC. */
9ed608f9
MW
348 { NULL, 0x0 },
349};
350
a32c3ff8 351/* op -> op: load = 0 instruction = 1 store = 2
a06ea964
NC
352 l -> level: 1-3
353 t -> temporal: temporal (retained) = 0 non-temporal (streaming) = 1 */
a32c3ff8 354#define B(op,l,t) (((op) << 3) | (((l) - 1) << 1) | (t))
a06ea964
NC
355const struct aarch64_name_value_pair aarch64_prfops[32] =
356{
357 { "pldl1keep", B(0, 1, 0) },
358 { "pldl1strm", B(0, 1, 1) },
359 { "pldl2keep", B(0, 2, 0) },
360 { "pldl2strm", B(0, 2, 1) },
361 { "pldl3keep", B(0, 3, 0) },
362 { "pldl3strm", B(0, 3, 1) },
a1ccaec9
YZ
363 { NULL, 0x06 },
364 { NULL, 0x07 },
a32c3ff8
NC
365 { "plil1keep", B(1, 1, 0) },
366 { "plil1strm", B(1, 1, 1) },
367 { "plil2keep", B(1, 2, 0) },
368 { "plil2strm", B(1, 2, 1) },
369 { "plil3keep", B(1, 3, 0) },
370 { "plil3strm", B(1, 3, 1) },
a1ccaec9
YZ
371 { NULL, 0x0e },
372 { NULL, 0x0f },
a32c3ff8
NC
373 { "pstl1keep", B(2, 1, 0) },
374 { "pstl1strm", B(2, 1, 1) },
375 { "pstl2keep", B(2, 2, 0) },
376 { "pstl2strm", B(2, 2, 1) },
377 { "pstl3keep", B(2, 3, 0) },
378 { "pstl3strm", B(2, 3, 1) },
a1ccaec9
YZ
379 { NULL, 0x16 },
380 { NULL, 0x17 },
381 { NULL, 0x18 },
382 { NULL, 0x19 },
383 { NULL, 0x1a },
384 { NULL, 0x1b },
385 { NULL, 0x1c },
386 { NULL, 0x1d },
387 { NULL, 0x1e },
388 { NULL, 0x1f },
a06ea964
NC
389};
390#undef B
391\f
392/* Utilities on value constraint. */
393
394static inline int
395value_in_range_p (int64_t value, int low, int high)
396{
397 return (value >= low && value <= high) ? 1 : 0;
398}
399
400static inline int
401value_aligned_p (int64_t value, int align)
402{
403 return ((value & (align - 1)) == 0) ? 1 : 0;
404}
405
406/* A signed value fits in a field. */
407static inline int
408value_fit_signed_field_p (int64_t value, unsigned width)
409{
410 assert (width < 32);
411 if (width < sizeof (value) * 8)
412 {
413 int64_t lim = (int64_t)1 << (width - 1);
414 if (value >= -lim && value < lim)
415 return 1;
416 }
417 return 0;
418}
419
420/* An unsigned value fits in a field. */
421static inline int
422value_fit_unsigned_field_p (int64_t value, unsigned width)
423{
424 assert (width < 32);
425 if (width < sizeof (value) * 8)
426 {
427 int64_t lim = (int64_t)1 << width;
428 if (value >= 0 && value < lim)
429 return 1;
430 }
431 return 0;
432}
433
434/* Return 1 if OPERAND is SP or WSP. */
435int
436aarch64_stack_pointer_p (const aarch64_opnd_info *operand)
437{
438 return ((aarch64_get_operand_class (operand->type)
439 == AARCH64_OPND_CLASS_INT_REG)
440 && operand_maybe_stack_pointer (aarch64_operands + operand->type)
441 && operand->reg.regno == 31);
442}
443
444/* Return 1 if OPERAND is XZR or WZP. */
445int
446aarch64_zero_register_p (const aarch64_opnd_info *operand)
447{
448 return ((aarch64_get_operand_class (operand->type)
449 == AARCH64_OPND_CLASS_INT_REG)
450 && !operand_maybe_stack_pointer (aarch64_operands + operand->type)
451 && operand->reg.regno == 31);
452}
453
454/* Return true if the operand *OPERAND that has the operand code
455 OPERAND->TYPE and been qualified by OPERAND->QUALIFIER can be also
456 qualified by the qualifier TARGET. */
457
458static inline int
459operand_also_qualified_p (const struct aarch64_opnd_info *operand,
460 aarch64_opnd_qualifier_t target)
461{
462 switch (operand->qualifier)
463 {
464 case AARCH64_OPND_QLF_W:
465 if (target == AARCH64_OPND_QLF_WSP && aarch64_stack_pointer_p (operand))
466 return 1;
467 break;
468 case AARCH64_OPND_QLF_X:
469 if (target == AARCH64_OPND_QLF_SP && aarch64_stack_pointer_p (operand))
470 return 1;
471 break;
472 case AARCH64_OPND_QLF_WSP:
473 if (target == AARCH64_OPND_QLF_W
474 && operand_maybe_stack_pointer (aarch64_operands + operand->type))
475 return 1;
476 break;
477 case AARCH64_OPND_QLF_SP:
478 if (target == AARCH64_OPND_QLF_X
479 && operand_maybe_stack_pointer (aarch64_operands + operand->type))
480 return 1;
481 break;
482 default:
483 break;
484 }
485
486 return 0;
487}
488
489/* Given qualifier sequence list QSEQ_LIST and the known qualifier KNOWN_QLF
490 for operand KNOWN_IDX, return the expected qualifier for operand IDX.
491
492 Return NIL if more than one expected qualifiers are found. */
493
494aarch64_opnd_qualifier_t
495aarch64_get_expected_qualifier (const aarch64_opnd_qualifier_seq_t *qseq_list,
496 int idx,
497 const aarch64_opnd_qualifier_t known_qlf,
498 int known_idx)
499{
500 int i, saved_i;
501
502 /* Special case.
503
504 When the known qualifier is NIL, we have to assume that there is only
505 one qualifier sequence in the *QSEQ_LIST and return the corresponding
506 qualifier directly. One scenario is that for instruction
507 PRFM <prfop>, [<Xn|SP>, #:lo12:<symbol>]
508 which has only one possible valid qualifier sequence
509 NIL, S_D
510 the caller may pass NIL in KNOWN_QLF to obtain S_D so that it can
511 determine the correct relocation type (i.e. LDST64_LO12) for PRFM.
512
513 Because the qualifier NIL has dual roles in the qualifier sequence:
514 it can mean no qualifier for the operand, or the qualifer sequence is
515 not in use (when all qualifiers in the sequence are NILs), we have to
516 handle this special case here. */
517 if (known_qlf == AARCH64_OPND_NIL)
518 {
519 assert (qseq_list[0][known_idx] == AARCH64_OPND_NIL);
520 return qseq_list[0][idx];
521 }
522
523 for (i = 0, saved_i = -1; i < AARCH64_MAX_QLF_SEQ_NUM; ++i)
524 {
525 if (qseq_list[i][known_idx] == known_qlf)
526 {
527 if (saved_i != -1)
528 /* More than one sequences are found to have KNOWN_QLF at
529 KNOWN_IDX. */
530 return AARCH64_OPND_NIL;
531 saved_i = i;
532 }
533 }
534
535 return qseq_list[saved_i][idx];
536}
537
538enum operand_qualifier_kind
539{
540 OQK_NIL,
541 OQK_OPD_VARIANT,
542 OQK_VALUE_IN_RANGE,
543 OQK_MISC,
544};
545
546/* Operand qualifier description. */
547struct operand_qualifier_data
548{
549 /* The usage of the three data fields depends on the qualifier kind. */
550 int data0;
551 int data1;
552 int data2;
553 /* Description. */
554 const char *desc;
555 /* Kind. */
556 enum operand_qualifier_kind kind;
557};
558
559/* Indexed by the operand qualifier enumerators. */
560struct operand_qualifier_data aarch64_opnd_qualifiers[] =
561{
562 {0, 0, 0, "NIL", OQK_NIL},
563
564 /* Operand variant qualifiers.
565 First 3 fields:
566 element size, number of elements and common value for encoding. */
567
568 {4, 1, 0x0, "w", OQK_OPD_VARIANT},
569 {8, 1, 0x1, "x", OQK_OPD_VARIANT},
570 {4, 1, 0x0, "wsp", OQK_OPD_VARIANT},
571 {8, 1, 0x1, "sp", OQK_OPD_VARIANT},
572
573 {1, 1, 0x0, "b", OQK_OPD_VARIANT},
574 {2, 1, 0x1, "h", OQK_OPD_VARIANT},
575 {4, 1, 0x2, "s", OQK_OPD_VARIANT},
576 {8, 1, 0x3, "d", OQK_OPD_VARIANT},
577 {16, 1, 0x4, "q", OQK_OPD_VARIANT},
578
579 {1, 8, 0x0, "8b", OQK_OPD_VARIANT},
580 {1, 16, 0x1, "16b", OQK_OPD_VARIANT},
3067d3b9 581 {2, 2, 0x0, "2h", OQK_OPD_VARIANT},
a06ea964
NC
582 {2, 4, 0x2, "4h", OQK_OPD_VARIANT},
583 {2, 8, 0x3, "8h", OQK_OPD_VARIANT},
584 {4, 2, 0x4, "2s", OQK_OPD_VARIANT},
585 {4, 4, 0x5, "4s", OQK_OPD_VARIANT},
586 {8, 1, 0x6, "1d", OQK_OPD_VARIANT},
587 {8, 2, 0x7, "2d", OQK_OPD_VARIANT},
588 {16, 1, 0x8, "1q", OQK_OPD_VARIANT},
589
590 /* Qualifiers constraining the value range.
591 First 3 fields:
592 Lower bound, higher bound, unused. */
593
594 {0, 7, 0, "imm_0_7" , OQK_VALUE_IN_RANGE},
595 {0, 15, 0, "imm_0_15", OQK_VALUE_IN_RANGE},
596 {0, 31, 0, "imm_0_31", OQK_VALUE_IN_RANGE},
597 {0, 63, 0, "imm_0_63", OQK_VALUE_IN_RANGE},
598 {1, 32, 0, "imm_1_32", OQK_VALUE_IN_RANGE},
599 {1, 64, 0, "imm_1_64", OQK_VALUE_IN_RANGE},
600
601 /* Qualifiers for miscellaneous purpose.
602 First 3 fields:
603 unused, unused and unused. */
604
605 {0, 0, 0, "lsl", 0},
606 {0, 0, 0, "msl", 0},
607
608 {0, 0, 0, "retrieving", 0},
609};
610
611static inline bfd_boolean
612operand_variant_qualifier_p (aarch64_opnd_qualifier_t qualifier)
613{
614 return (aarch64_opnd_qualifiers[qualifier].kind == OQK_OPD_VARIANT)
615 ? TRUE : FALSE;
616}
617
618static inline bfd_boolean
619qualifier_value_in_range_constraint_p (aarch64_opnd_qualifier_t qualifier)
620{
621 return (aarch64_opnd_qualifiers[qualifier].kind == OQK_VALUE_IN_RANGE)
622 ? TRUE : FALSE;
623}
624
625const char*
626aarch64_get_qualifier_name (aarch64_opnd_qualifier_t qualifier)
627{
628 return aarch64_opnd_qualifiers[qualifier].desc;
629}
630
631/* Given an operand qualifier, return the expected data element size
632 of a qualified operand. */
633unsigned char
634aarch64_get_qualifier_esize (aarch64_opnd_qualifier_t qualifier)
635{
636 assert (operand_variant_qualifier_p (qualifier) == TRUE);
637 return aarch64_opnd_qualifiers[qualifier].data0;
638}
639
640unsigned char
641aarch64_get_qualifier_nelem (aarch64_opnd_qualifier_t qualifier)
642{
643 assert (operand_variant_qualifier_p (qualifier) == TRUE);
644 return aarch64_opnd_qualifiers[qualifier].data1;
645}
646
647aarch64_insn
648aarch64_get_qualifier_standard_value (aarch64_opnd_qualifier_t qualifier)
649{
650 assert (operand_variant_qualifier_p (qualifier) == TRUE);
651 return aarch64_opnd_qualifiers[qualifier].data2;
652}
653
654static int
655get_lower_bound (aarch64_opnd_qualifier_t qualifier)
656{
657 assert (qualifier_value_in_range_constraint_p (qualifier) == TRUE);
658 return aarch64_opnd_qualifiers[qualifier].data0;
659}
660
661static int
662get_upper_bound (aarch64_opnd_qualifier_t qualifier)
663{
664 assert (qualifier_value_in_range_constraint_p (qualifier) == TRUE);
665 return aarch64_opnd_qualifiers[qualifier].data1;
666}
667
668#ifdef DEBUG_AARCH64
669void
670aarch64_verbose (const char *str, ...)
671{
672 va_list ap;
673 va_start (ap, str);
674 printf ("#### ");
675 vprintf (str, ap);
676 printf ("\n");
677 va_end (ap);
678}
679
680static inline void
681dump_qualifier_sequence (const aarch64_opnd_qualifier_t *qualifier)
682{
683 int i;
684 printf ("#### \t");
685 for (i = 0; i < AARCH64_MAX_OPND_NUM; ++i, ++qualifier)
686 printf ("%s,", aarch64_get_qualifier_name (*qualifier));
687 printf ("\n");
688}
689
690static void
691dump_match_qualifiers (const struct aarch64_opnd_info *opnd,
692 const aarch64_opnd_qualifier_t *qualifier)
693{
694 int i;
695 aarch64_opnd_qualifier_t curr[AARCH64_MAX_OPND_NUM];
696
697 aarch64_verbose ("dump_match_qualifiers:");
698 for (i = 0; i < AARCH64_MAX_OPND_NUM; ++i)
699 curr[i] = opnd[i].qualifier;
700 dump_qualifier_sequence (curr);
701 aarch64_verbose ("against");
702 dump_qualifier_sequence (qualifier);
703}
704#endif /* DEBUG_AARCH64 */
705
706/* TODO improve this, we can have an extra field at the runtime to
707 store the number of operands rather than calculating it every time. */
708
709int
710aarch64_num_of_operands (const aarch64_opcode *opcode)
711{
712 int i = 0;
713 const enum aarch64_opnd *opnds = opcode->operands;
714 while (opnds[i++] != AARCH64_OPND_NIL)
715 ;
716 --i;
717 assert (i >= 0 && i <= AARCH64_MAX_OPND_NUM);
718 return i;
719}
720
721/* Find the best matched qualifier sequence in *QUALIFIERS_LIST for INST.
722 If succeeds, fill the found sequence in *RET, return 1; otherwise return 0.
723
724 N.B. on the entry, it is very likely that only some operands in *INST
725 have had their qualifiers been established.
726
727 If STOP_AT is not -1, the function will only try to match
728 the qualifier sequence for operands before and including the operand
729 of index STOP_AT; and on success *RET will only be filled with the first
730 (STOP_AT+1) qualifiers.
731
732 A couple examples of the matching algorithm:
733
734 X,W,NIL should match
735 X,W,NIL
736
737 NIL,NIL should match
738 X ,NIL
739
740 Apart from serving the main encoding routine, this can also be called
741 during or after the operand decoding. */
742
743int
744aarch64_find_best_match (const aarch64_inst *inst,
745 const aarch64_opnd_qualifier_seq_t *qualifiers_list,
746 int stop_at, aarch64_opnd_qualifier_t *ret)
747{
748 int found = 0;
749 int i, num_opnds;
750 const aarch64_opnd_qualifier_t *qualifiers;
751
752 num_opnds = aarch64_num_of_operands (inst->opcode);
753 if (num_opnds == 0)
754 {
755 DEBUG_TRACE ("SUCCEED: no operand");
756 return 1;
757 }
758
759 if (stop_at < 0 || stop_at >= num_opnds)
760 stop_at = num_opnds - 1;
761
762 /* For each pattern. */
763 for (i = 0; i < AARCH64_MAX_QLF_SEQ_NUM; ++i, ++qualifiers_list)
764 {
765 int j;
766 qualifiers = *qualifiers_list;
767
768 /* Start as positive. */
769 found = 1;
770
771 DEBUG_TRACE ("%d", i);
772#ifdef DEBUG_AARCH64
773 if (debug_dump)
774 dump_match_qualifiers (inst->operands, qualifiers);
775#endif
776
777 /* Most opcodes has much fewer patterns in the list.
778 First NIL qualifier indicates the end in the list. */
779 if (empty_qualifier_sequence_p (qualifiers) == TRUE)
780 {
781 DEBUG_TRACE_IF (i == 0, "SUCCEED: empty qualifier list");
782 if (i)
783 found = 0;
784 break;
785 }
786
787 for (j = 0; j < num_opnds && j <= stop_at; ++j, ++qualifiers)
788 {
789 if (inst->operands[j].qualifier == AARCH64_OPND_QLF_NIL)
790 {
791 /* Either the operand does not have qualifier, or the qualifier
792 for the operand needs to be deduced from the qualifier
793 sequence.
794 In the latter case, any constraint checking related with
795 the obtained qualifier should be done later in
796 operand_general_constraint_met_p. */
797 continue;
798 }
799 else if (*qualifiers != inst->operands[j].qualifier)
800 {
801 /* Unless the target qualifier can also qualify the operand
802 (which has already had a non-nil qualifier), non-equal
803 qualifiers are generally un-matched. */
804 if (operand_also_qualified_p (inst->operands + j, *qualifiers))
805 continue;
806 else
807 {
808 found = 0;
809 break;
810 }
811 }
812 else
813 continue; /* Equal qualifiers are certainly matched. */
814 }
815
816 /* Qualifiers established. */
817 if (found == 1)
818 break;
819 }
820
821 if (found == 1)
822 {
823 /* Fill the result in *RET. */
824 int j;
825 qualifiers = *qualifiers_list;
826
827 DEBUG_TRACE ("complete qualifiers using list %d", i);
828#ifdef DEBUG_AARCH64
829 if (debug_dump)
830 dump_qualifier_sequence (qualifiers);
831#endif
832
833 for (j = 0; j <= stop_at; ++j, ++qualifiers)
834 ret[j] = *qualifiers;
835 for (; j < AARCH64_MAX_OPND_NUM; ++j)
836 ret[j] = AARCH64_OPND_QLF_NIL;
837
838 DEBUG_TRACE ("SUCCESS");
839 return 1;
840 }
841
842 DEBUG_TRACE ("FAIL");
843 return 0;
844}
845
846/* Operand qualifier matching and resolving.
847
848 Return 1 if the operand qualifier(s) in *INST match one of the qualifier
849 sequences in INST->OPCODE->qualifiers_list; otherwise return 0.
850
851 if UPDATE_P == TRUE, update the qualifier(s) in *INST after the matching
852 succeeds. */
853
854static int
855match_operands_qualifier (aarch64_inst *inst, bfd_boolean update_p)
856{
4989adac 857 int i, nops;
a06ea964
NC
858 aarch64_opnd_qualifier_seq_t qualifiers;
859
860 if (!aarch64_find_best_match (inst, inst->opcode->qualifiers_list, -1,
861 qualifiers))
862 {
863 DEBUG_TRACE ("matching FAIL");
864 return 0;
865 }
866
4989adac
RS
867 if (inst->opcode->flags & F_STRICT)
868 {
869 /* Require an exact qualifier match, even for NIL qualifiers. */
870 nops = aarch64_num_of_operands (inst->opcode);
871 for (i = 0; i < nops; ++i)
872 if (inst->operands[i].qualifier != qualifiers[i])
873 return FALSE;
874 }
875
a06ea964
NC
876 /* Update the qualifiers. */
877 if (update_p == TRUE)
878 for (i = 0; i < AARCH64_MAX_OPND_NUM; ++i)
879 {
880 if (inst->opcode->operands[i] == AARCH64_OPND_NIL)
881 break;
882 DEBUG_TRACE_IF (inst->operands[i].qualifier != qualifiers[i],
883 "update %s with %s for operand %d",
884 aarch64_get_qualifier_name (inst->operands[i].qualifier),
885 aarch64_get_qualifier_name (qualifiers[i]), i);
886 inst->operands[i].qualifier = qualifiers[i];
887 }
888
889 DEBUG_TRACE ("matching SUCCESS");
890 return 1;
891}
892
893/* Return TRUE if VALUE is a wide constant that can be moved into a general
894 register by MOVZ.
895
896 IS32 indicates whether value is a 32-bit immediate or not.
897 If SHIFT_AMOUNT is not NULL, on the return of TRUE, the logical left shift
898 amount will be returned in *SHIFT_AMOUNT. */
899
900bfd_boolean
901aarch64_wide_constant_p (int64_t value, int is32, unsigned int *shift_amount)
902{
903 int amount;
904
905 DEBUG_TRACE ("enter with 0x%" PRIx64 "(%" PRIi64 ")", value, value);
906
907 if (is32)
908 {
909 /* Allow all zeros or all ones in top 32-bits, so that
910 32-bit constant expressions like ~0x80000000 are
911 permitted. */
912 uint64_t ext = value;
913 if (ext >> 32 != 0 && ext >> 32 != (uint64_t) 0xffffffff)
914 /* Immediate out of range. */
915 return FALSE;
916 value &= (int64_t) 0xffffffff;
917 }
918
919 /* first, try movz then movn */
920 amount = -1;
921 if ((value & ((int64_t) 0xffff << 0)) == value)
922 amount = 0;
923 else if ((value & ((int64_t) 0xffff << 16)) == value)
924 amount = 16;
925 else if (!is32 && (value & ((int64_t) 0xffff << 32)) == value)
926 amount = 32;
927 else if (!is32 && (value & ((int64_t) 0xffff << 48)) == value)
928 amount = 48;
929
930 if (amount == -1)
931 {
932 DEBUG_TRACE ("exit FALSE with 0x%" PRIx64 "(%" PRIi64 ")", value, value);
933 return FALSE;
934 }
935
936 if (shift_amount != NULL)
937 *shift_amount = amount;
938
939 DEBUG_TRACE ("exit TRUE with amount %d", amount);
940
941 return TRUE;
942}
943
944/* Build the accepted values for immediate logical SIMD instructions.
945
946 The standard encodings of the immediate value are:
947 N imms immr SIMD size R S
948 1 ssssss rrrrrr 64 UInt(rrrrrr) UInt(ssssss)
949 0 0sssss 0rrrrr 32 UInt(rrrrr) UInt(sssss)
950 0 10ssss 00rrrr 16 UInt(rrrr) UInt(ssss)
951 0 110sss 000rrr 8 UInt(rrr) UInt(sss)
952 0 1110ss 0000rr 4 UInt(rr) UInt(ss)
953 0 11110s 00000r 2 UInt(r) UInt(s)
954 where all-ones value of S is reserved.
955
956 Let's call E the SIMD size.
957
958 The immediate value is: S+1 bits '1' rotated to the right by R.
959
960 The total of valid encodings is 64*63 + 32*31 + ... + 2*1 = 5334
961 (remember S != E - 1). */
962
963#define TOTAL_IMM_NB 5334
964
965typedef struct
966{
967 uint64_t imm;
968 aarch64_insn encoding;
969} simd_imm_encoding;
970
971static simd_imm_encoding simd_immediates[TOTAL_IMM_NB];
972
973static int
974simd_imm_encoding_cmp(const void *i1, const void *i2)
975{
976 const simd_imm_encoding *imm1 = (const simd_imm_encoding *)i1;
977 const simd_imm_encoding *imm2 = (const simd_imm_encoding *)i2;
978
979 if (imm1->imm < imm2->imm)
980 return -1;
981 if (imm1->imm > imm2->imm)
982 return +1;
983 return 0;
984}
985
986/* immediate bitfield standard encoding
987 imm13<12> imm13<5:0> imm13<11:6> SIMD size R S
988 1 ssssss rrrrrr 64 rrrrrr ssssss
989 0 0sssss 0rrrrr 32 rrrrr sssss
990 0 10ssss 00rrrr 16 rrrr ssss
991 0 110sss 000rrr 8 rrr sss
992 0 1110ss 0000rr 4 rr ss
993 0 11110s 00000r 2 r s */
994static inline int
995encode_immediate_bitfield (int is64, uint32_t s, uint32_t r)
996{
997 return (is64 << 12) | (r << 6) | s;
998}
999
1000static void
1001build_immediate_table (void)
1002{
1003 uint32_t log_e, e, s, r, s_mask;
1004 uint64_t mask, imm;
1005 int nb_imms;
1006 int is64;
1007
1008 nb_imms = 0;
1009 for (log_e = 1; log_e <= 6; log_e++)
1010 {
1011 /* Get element size. */
1012 e = 1u << log_e;
1013 if (log_e == 6)
1014 {
1015 is64 = 1;
1016 mask = 0xffffffffffffffffull;
1017 s_mask = 0;
1018 }
1019 else
1020 {
1021 is64 = 0;
1022 mask = (1ull << e) - 1;
1023 /* log_e s_mask
1024 1 ((1 << 4) - 1) << 2 = 111100
1025 2 ((1 << 3) - 1) << 3 = 111000
1026 3 ((1 << 2) - 1) << 4 = 110000
1027 4 ((1 << 1) - 1) << 5 = 100000
1028 5 ((1 << 0) - 1) << 6 = 000000 */
1029 s_mask = ((1u << (5 - log_e)) - 1) << (log_e + 1);
1030 }
1031 for (s = 0; s < e - 1; s++)
1032 for (r = 0; r < e; r++)
1033 {
1034 /* s+1 consecutive bits to 1 (s < 63) */
1035 imm = (1ull << (s + 1)) - 1;
1036 /* rotate right by r */
1037 if (r != 0)
1038 imm = (imm >> r) | ((imm << (e - r)) & mask);
1039 /* replicate the constant depending on SIMD size */
1040 switch (log_e)
1041 {
1042 case 1: imm = (imm << 2) | imm;
1043 case 2: imm = (imm << 4) | imm;
1044 case 3: imm = (imm << 8) | imm;
1045 case 4: imm = (imm << 16) | imm;
1046 case 5: imm = (imm << 32) | imm;
1047 case 6: break;
1048 default: abort ();
1049 }
1050 simd_immediates[nb_imms].imm = imm;
1051 simd_immediates[nb_imms].encoding =
1052 encode_immediate_bitfield(is64, s | s_mask, r);
1053 nb_imms++;
1054 }
1055 }
1056 assert (nb_imms == TOTAL_IMM_NB);
1057 qsort(simd_immediates, nb_imms,
1058 sizeof(simd_immediates[0]), simd_imm_encoding_cmp);
1059}
1060
1061/* Return TRUE if VALUE is a valid logical immediate, i.e. bitmask, that can
1062 be accepted by logical (immediate) instructions
1063 e.g. ORR <Xd|SP>, <Xn>, #<imm>.
1064
42408347 1065 ESIZE is the number of bytes in the decoded immediate value.
a06ea964
NC
1066 If ENCODING is not NULL, on the return of TRUE, the standard encoding for
1067 VALUE will be returned in *ENCODING. */
1068
1069bfd_boolean
42408347 1070aarch64_logical_immediate_p (uint64_t value, int esize, aarch64_insn *encoding)
a06ea964
NC
1071{
1072 simd_imm_encoding imm_enc;
1073 const simd_imm_encoding *imm_encoding;
1074 static bfd_boolean initialized = FALSE;
42408347
RS
1075 uint64_t upper;
1076 int i;
a06ea964
NC
1077
1078 DEBUG_TRACE ("enter with 0x%" PRIx64 "(%" PRIi64 "), is32: %d", value,
1079 value, is32);
1080
1081 if (initialized == FALSE)
1082 {
1083 build_immediate_table ();
1084 initialized = TRUE;
1085 }
1086
42408347
RS
1087 /* Allow all zeros or all ones in top bits, so that
1088 constant expressions like ~1 are permitted. */
1089 upper = (uint64_t) -1 << (esize * 4) << (esize * 4);
1090 if ((value & ~upper) != value && (value | upper) != value)
1091 return FALSE;
7e105031 1092
42408347
RS
1093 /* Replicate to a full 64-bit value. */
1094 value &= ~upper;
1095 for (i = esize * 8; i < 64; i *= 2)
1096 value |= (value << i);
a06ea964
NC
1097
1098 imm_enc.imm = value;
1099 imm_encoding = (const simd_imm_encoding *)
1100 bsearch(&imm_enc, simd_immediates, TOTAL_IMM_NB,
1101 sizeof(simd_immediates[0]), simd_imm_encoding_cmp);
1102 if (imm_encoding == NULL)
1103 {
1104 DEBUG_TRACE ("exit with FALSE");
1105 return FALSE;
1106 }
1107 if (encoding != NULL)
1108 *encoding = imm_encoding->encoding;
1109 DEBUG_TRACE ("exit with TRUE");
1110 return TRUE;
1111}
1112
1113/* If 64-bit immediate IMM is in the format of
1114 "aaaaaaaabbbbbbbbccccccccddddddddeeeeeeeeffffffffgggggggghhhhhhhh",
1115 where a, b, c, d, e, f, g and h are independently 0 or 1, return an integer
1116 of value "abcdefgh". Otherwise return -1. */
1117int
1118aarch64_shrink_expanded_imm8 (uint64_t imm)
1119{
1120 int i, ret;
1121 uint32_t byte;
1122
1123 ret = 0;
1124 for (i = 0; i < 8; i++)
1125 {
1126 byte = (imm >> (8 * i)) & 0xff;
1127 if (byte == 0xff)
1128 ret |= 1 << i;
1129 else if (byte != 0x00)
1130 return -1;
1131 }
1132 return ret;
1133}
1134
1135/* Utility inline functions for operand_general_constraint_met_p. */
1136
1137static inline void
1138set_error (aarch64_operand_error *mismatch_detail,
1139 enum aarch64_operand_error_kind kind, int idx,
1140 const char* error)
1141{
1142 if (mismatch_detail == NULL)
1143 return;
1144 mismatch_detail->kind = kind;
1145 mismatch_detail->index = idx;
1146 mismatch_detail->error = error;
1147}
1148
4e50d5f8
YZ
1149static inline void
1150set_syntax_error (aarch64_operand_error *mismatch_detail, int idx,
1151 const char* error)
1152{
1153 if (mismatch_detail == NULL)
1154 return;
1155 set_error (mismatch_detail, AARCH64_OPDE_SYNTAX_ERROR, idx, error);
1156}
1157
a06ea964
NC
1158static inline void
1159set_out_of_range_error (aarch64_operand_error *mismatch_detail,
1160 int idx, int lower_bound, int upper_bound,
1161 const char* error)
1162{
1163 if (mismatch_detail == NULL)
1164 return;
1165 set_error (mismatch_detail, AARCH64_OPDE_OUT_OF_RANGE, idx, error);
1166 mismatch_detail->data[0] = lower_bound;
1167 mismatch_detail->data[1] = upper_bound;
1168}
1169
1170static inline void
1171set_imm_out_of_range_error (aarch64_operand_error *mismatch_detail,
1172 int idx, int lower_bound, int upper_bound)
1173{
1174 if (mismatch_detail == NULL)
1175 return;
1176 set_out_of_range_error (mismatch_detail, idx, lower_bound, upper_bound,
1177 _("immediate value"));
1178}
1179
1180static inline void
1181set_offset_out_of_range_error (aarch64_operand_error *mismatch_detail,
1182 int idx, int lower_bound, int upper_bound)
1183{
1184 if (mismatch_detail == NULL)
1185 return;
1186 set_out_of_range_error (mismatch_detail, idx, lower_bound, upper_bound,
1187 _("immediate offset"));
1188}
1189
1190static inline void
1191set_regno_out_of_range_error (aarch64_operand_error *mismatch_detail,
1192 int idx, int lower_bound, int upper_bound)
1193{
1194 if (mismatch_detail == NULL)
1195 return;
1196 set_out_of_range_error (mismatch_detail, idx, lower_bound, upper_bound,
1197 _("register number"));
1198}
1199
1200static inline void
1201set_elem_idx_out_of_range_error (aarch64_operand_error *mismatch_detail,
1202 int idx, int lower_bound, int upper_bound)
1203{
1204 if (mismatch_detail == NULL)
1205 return;
1206 set_out_of_range_error (mismatch_detail, idx, lower_bound, upper_bound,
1207 _("register element index"));
1208}
1209
1210static inline void
1211set_sft_amount_out_of_range_error (aarch64_operand_error *mismatch_detail,
1212 int idx, int lower_bound, int upper_bound)
1213{
1214 if (mismatch_detail == NULL)
1215 return;
1216 set_out_of_range_error (mismatch_detail, idx, lower_bound, upper_bound,
1217 _("shift amount"));
1218}
1219
1220static inline void
1221set_unaligned_error (aarch64_operand_error *mismatch_detail, int idx,
1222 int alignment)
1223{
1224 if (mismatch_detail == NULL)
1225 return;
1226 set_error (mismatch_detail, AARCH64_OPDE_UNALIGNED, idx, NULL);
1227 mismatch_detail->data[0] = alignment;
1228}
1229
1230static inline void
1231set_reg_list_error (aarch64_operand_error *mismatch_detail, int idx,
1232 int expected_num)
1233{
1234 if (mismatch_detail == NULL)
1235 return;
1236 set_error (mismatch_detail, AARCH64_OPDE_REG_LIST, idx, NULL);
1237 mismatch_detail->data[0] = expected_num;
1238}
1239
1240static inline void
1241set_other_error (aarch64_operand_error *mismatch_detail, int idx,
1242 const char* error)
1243{
1244 if (mismatch_detail == NULL)
1245 return;
1246 set_error (mismatch_detail, AARCH64_OPDE_OTHER_ERROR, idx, error);
1247}
1248
1249/* General constraint checking based on operand code.
1250
1251 Return 1 if OPNDS[IDX] meets the general constraint of operand code TYPE
1252 as the IDXth operand of opcode OPCODE. Otherwise return 0.
1253
1254 This function has to be called after the qualifiers for all operands
1255 have been resolved.
1256
1257 Mismatching error message is returned in *MISMATCH_DETAIL upon request,
1258 i.e. when MISMATCH_DETAIL is non-NULL. This avoids the generation
1259 of error message during the disassembling where error message is not
1260 wanted. We avoid the dynamic construction of strings of error messages
1261 here (i.e. in libopcodes), as it is costly and complicated; instead, we
1262 use a combination of error code, static string and some integer data to
1263 represent an error. */
1264
1265static int
1266operand_general_constraint_met_p (const aarch64_opnd_info *opnds, int idx,
1267 enum aarch64_opnd type,
1268 const aarch64_opcode *opcode,
1269 aarch64_operand_error *mismatch_detail)
1270{
1271 unsigned num;
1272 unsigned char size;
1273 int64_t imm;
1274 const aarch64_opnd_info *opnd = opnds + idx;
1275 aarch64_opnd_qualifier_t qualifier = opnd->qualifier;
1276
1277 assert (opcode->operands[idx] == opnd->type && opnd->type == type);
1278
1279 switch (aarch64_operands[type].op_class)
1280 {
1281 case AARCH64_OPND_CLASS_INT_REG:
ee804238
JW
1282 /* Check pair reg constraints for cas* instructions. */
1283 if (type == AARCH64_OPND_PAIRREG)
1284 {
1285 assert (idx == 1 || idx == 3);
1286 if (opnds[idx - 1].reg.regno % 2 != 0)
1287 {
1288 set_syntax_error (mismatch_detail, idx - 1,
1289 _("reg pair must start from even reg"));
1290 return 0;
1291 }
1292 if (opnds[idx].reg.regno != opnds[idx - 1].reg.regno + 1)
1293 {
1294 set_syntax_error (mismatch_detail, idx,
1295 _("reg pair must be contiguous"));
1296 return 0;
1297 }
1298 break;
1299 }
1300
a06ea964
NC
1301 /* <Xt> may be optional in some IC and TLBI instructions. */
1302 if (type == AARCH64_OPND_Rt_SYS)
1303 {
1304 assert (idx == 1 && (aarch64_get_operand_class (opnds[0].type)
1305 == AARCH64_OPND_CLASS_SYSTEM));
ea2deeec
MW
1306 if (opnds[1].present
1307 && !aarch64_sys_ins_reg_has_xt (opnds[0].sysins_op))
a06ea964
NC
1308 {
1309 set_other_error (mismatch_detail, idx, _("extraneous register"));
1310 return 0;
1311 }
ea2deeec
MW
1312 if (!opnds[1].present
1313 && aarch64_sys_ins_reg_has_xt (opnds[0].sysins_op))
a06ea964
NC
1314 {
1315 set_other_error (mismatch_detail, idx, _("missing register"));
1316 return 0;
1317 }
1318 }
1319 switch (qualifier)
1320 {
1321 case AARCH64_OPND_QLF_WSP:
1322 case AARCH64_OPND_QLF_SP:
1323 if (!aarch64_stack_pointer_p (opnd))
1324 {
1325 set_other_error (mismatch_detail, idx,
1326 _("stack pointer register expected"));
1327 return 0;
1328 }
1329 break;
1330 default:
1331 break;
1332 }
1333 break;
1334
68a64283
YZ
1335 case AARCH64_OPND_CLASS_COND:
1336 if (type == AARCH64_OPND_COND1
1337 && (opnds[idx].cond->value & 0xe) == 0xe)
1338 {
1339 /* Not allow AL or NV. */
1340 set_syntax_error (mismatch_detail, idx, NULL);
1341 }
1342 break;
1343
a06ea964
NC
1344 case AARCH64_OPND_CLASS_ADDRESS:
1345 /* Check writeback. */
1346 switch (opcode->iclass)
1347 {
1348 case ldst_pos:
1349 case ldst_unscaled:
1350 case ldstnapair_offs:
1351 case ldstpair_off:
1352 case ldst_unpriv:
1353 if (opnd->addr.writeback == 1)
1354 {
4e50d5f8
YZ
1355 set_syntax_error (mismatch_detail, idx,
1356 _("unexpected address writeback"));
a06ea964
NC
1357 return 0;
1358 }
1359 break;
1360 case ldst_imm9:
1361 case ldstpair_indexed:
1362 case asisdlsep:
1363 case asisdlsop:
1364 if (opnd->addr.writeback == 0)
1365 {
4e50d5f8
YZ
1366 set_syntax_error (mismatch_detail, idx,
1367 _("address writeback expected"));
a06ea964
NC
1368 return 0;
1369 }
1370 break;
1371 default:
1372 assert (opnd->addr.writeback == 0);
1373 break;
1374 }
1375 switch (type)
1376 {
1377 case AARCH64_OPND_ADDR_SIMM7:
1378 /* Scaled signed 7 bits immediate offset. */
1379 /* Get the size of the data element that is accessed, which may be
1380 different from that of the source register size,
1381 e.g. in strb/ldrb. */
1382 size = aarch64_get_qualifier_esize (opnd->qualifier);
1383 if (!value_in_range_p (opnd->addr.offset.imm, -64 * size, 63 * size))
1384 {
1385 set_offset_out_of_range_error (mismatch_detail, idx,
1386 -64 * size, 63 * size);
1387 return 0;
1388 }
1389 if (!value_aligned_p (opnd->addr.offset.imm, size))
1390 {
1391 set_unaligned_error (mismatch_detail, idx, size);
1392 return 0;
1393 }
1394 break;
1395 case AARCH64_OPND_ADDR_SIMM9:
1396 /* Unscaled signed 9 bits immediate offset. */
1397 if (!value_in_range_p (opnd->addr.offset.imm, -256, 255))
1398 {
1399 set_offset_out_of_range_error (mismatch_detail, idx, -256, 255);
1400 return 0;
1401 }
1402 break;
1403
1404 case AARCH64_OPND_ADDR_SIMM9_2:
1405 /* Unscaled signed 9 bits immediate offset, which has to be negative
1406 or unaligned. */
1407 size = aarch64_get_qualifier_esize (qualifier);
1408 if ((value_in_range_p (opnd->addr.offset.imm, 0, 255)
1409 && !value_aligned_p (opnd->addr.offset.imm, size))
1410 || value_in_range_p (opnd->addr.offset.imm, -256, -1))
1411 return 1;
1412 set_other_error (mismatch_detail, idx,
1413 _("negative or unaligned offset expected"));
1414 return 0;
1415
1416 case AARCH64_OPND_SIMD_ADDR_POST:
1417 /* AdvSIMD load/store multiple structures, post-index. */
1418 assert (idx == 1);
1419 if (opnd->addr.offset.is_reg)
1420 {
1421 if (value_in_range_p (opnd->addr.offset.regno, 0, 30))
1422 return 1;
1423 else
1424 {
1425 set_other_error (mismatch_detail, idx,
1426 _("invalid register offset"));
1427 return 0;
1428 }
1429 }
1430 else
1431 {
1432 const aarch64_opnd_info *prev = &opnds[idx-1];
1433 unsigned num_bytes; /* total number of bytes transferred. */
1434 /* The opcode dependent area stores the number of elements in
1435 each structure to be loaded/stored. */
1436 int is_ld1r = get_opcode_dependent_value (opcode) == 1;
1437 if (opcode->operands[0] == AARCH64_OPND_LVt_AL)
1438 /* Special handling of loading single structure to all lane. */
1439 num_bytes = (is_ld1r ? 1 : prev->reglist.num_regs)
1440 * aarch64_get_qualifier_esize (prev->qualifier);
1441 else
1442 num_bytes = prev->reglist.num_regs
1443 * aarch64_get_qualifier_esize (prev->qualifier)
1444 * aarch64_get_qualifier_nelem (prev->qualifier);
1445 if ((int) num_bytes != opnd->addr.offset.imm)
1446 {
1447 set_other_error (mismatch_detail, idx,
1448 _("invalid post-increment amount"));
1449 return 0;
1450 }
1451 }
1452 break;
1453
1454 case AARCH64_OPND_ADDR_REGOFF:
1455 /* Get the size of the data element that is accessed, which may be
1456 different from that of the source register size,
1457 e.g. in strb/ldrb. */
1458 size = aarch64_get_qualifier_esize (opnd->qualifier);
1459 /* It is either no shift or shift by the binary logarithm of SIZE. */
1460 if (opnd->shifter.amount != 0
1461 && opnd->shifter.amount != (int)get_logsz (size))
1462 {
1463 set_other_error (mismatch_detail, idx,
1464 _("invalid shift amount"));
1465 return 0;
1466 }
1467 /* Only UXTW, LSL, SXTW and SXTX are the accepted extending
1468 operators. */
1469 switch (opnd->shifter.kind)
1470 {
1471 case AARCH64_MOD_UXTW:
1472 case AARCH64_MOD_LSL:
1473 case AARCH64_MOD_SXTW:
1474 case AARCH64_MOD_SXTX: break;
1475 default:
1476 set_other_error (mismatch_detail, idx,
1477 _("invalid extend/shift operator"));
1478 return 0;
1479 }
1480 break;
1481
1482 case AARCH64_OPND_ADDR_UIMM12:
1483 imm = opnd->addr.offset.imm;
1484 /* Get the size of the data element that is accessed, which may be
1485 different from that of the source register size,
1486 e.g. in strb/ldrb. */
1487 size = aarch64_get_qualifier_esize (qualifier);
1488 if (!value_in_range_p (opnd->addr.offset.imm, 0, 4095 * size))
1489 {
1490 set_offset_out_of_range_error (mismatch_detail, idx,
1491 0, 4095 * size);
1492 return 0;
1493 }
9de794e1 1494 if (!value_aligned_p (opnd->addr.offset.imm, size))
a06ea964
NC
1495 {
1496 set_unaligned_error (mismatch_detail, idx, size);
1497 return 0;
1498 }
1499 break;
1500
1501 case AARCH64_OPND_ADDR_PCREL14:
1502 case AARCH64_OPND_ADDR_PCREL19:
1503 case AARCH64_OPND_ADDR_PCREL21:
1504 case AARCH64_OPND_ADDR_PCREL26:
1505 imm = opnd->imm.value;
1506 if (operand_need_shift_by_two (get_operand_from_code (type)))
1507 {
1508 /* The offset value in a PC-relative branch instruction is alway
1509 4-byte aligned and is encoded without the lowest 2 bits. */
1510 if (!value_aligned_p (imm, 4))
1511 {
1512 set_unaligned_error (mismatch_detail, idx, 4);
1513 return 0;
1514 }
1515 /* Right shift by 2 so that we can carry out the following check
1516 canonically. */
1517 imm >>= 2;
1518 }
1519 size = get_operand_fields_width (get_operand_from_code (type));
1520 if (!value_fit_signed_field_p (imm, size))
1521 {
1522 set_other_error (mismatch_detail, idx,
1523 _("immediate out of range"));
1524 return 0;
1525 }
1526 break;
1527
1528 default:
1529 break;
1530 }
1531 break;
1532
1533 case AARCH64_OPND_CLASS_SIMD_REGLIST:
dab26bf4
RS
1534 if (type == AARCH64_OPND_LEt)
1535 {
1536 /* Get the upper bound for the element index. */
1537 num = 16 / aarch64_get_qualifier_esize (qualifier) - 1;
1538 if (!value_in_range_p (opnd->reglist.index, 0, num))
1539 {
1540 set_elem_idx_out_of_range_error (mismatch_detail, idx, 0, num);
1541 return 0;
1542 }
1543 }
a06ea964
NC
1544 /* The opcode dependent area stores the number of elements in
1545 each structure to be loaded/stored. */
1546 num = get_opcode_dependent_value (opcode);
1547 switch (type)
1548 {
1549 case AARCH64_OPND_LVt:
1550 assert (num >= 1 && num <= 4);
1551 /* Unless LD1/ST1, the number of registers should be equal to that
1552 of the structure elements. */
1553 if (num != 1 && opnd->reglist.num_regs != num)
1554 {
1555 set_reg_list_error (mismatch_detail, idx, num);
1556 return 0;
1557 }
1558 break;
1559 case AARCH64_OPND_LVt_AL:
1560 case AARCH64_OPND_LEt:
1561 assert (num >= 1 && num <= 4);
1562 /* The number of registers should be equal to that of the structure
1563 elements. */
1564 if (opnd->reglist.num_regs != num)
1565 {
1566 set_reg_list_error (mismatch_detail, idx, num);
1567 return 0;
1568 }
1569 break;
1570 default:
1571 break;
1572 }
1573 break;
1574
1575 case AARCH64_OPND_CLASS_IMMEDIATE:
1576 /* Constraint check on immediate operand. */
1577 imm = opnd->imm.value;
1578 /* E.g. imm_0_31 constrains value to be 0..31. */
1579 if (qualifier_value_in_range_constraint_p (qualifier)
1580 && !value_in_range_p (imm, get_lower_bound (qualifier),
1581 get_upper_bound (qualifier)))
1582 {
1583 set_imm_out_of_range_error (mismatch_detail, idx,
1584 get_lower_bound (qualifier),
1585 get_upper_bound (qualifier));
1586 return 0;
1587 }
1588
1589 switch (type)
1590 {
1591 case AARCH64_OPND_AIMM:
1592 if (opnd->shifter.kind != AARCH64_MOD_LSL)
1593 {
1594 set_other_error (mismatch_detail, idx,
1595 _("invalid shift operator"));
1596 return 0;
1597 }
1598 if (opnd->shifter.amount != 0 && opnd->shifter.amount != 12)
1599 {
1600 set_other_error (mismatch_detail, idx,
1601 _("shift amount expected to be 0 or 12"));
1602 return 0;
1603 }
1604 if (!value_fit_unsigned_field_p (opnd->imm.value, 12))
1605 {
1606 set_other_error (mismatch_detail, idx,
1607 _("immediate out of range"));
1608 return 0;
1609 }
1610 break;
1611
1612 case AARCH64_OPND_HALF:
1613 assert (idx == 1 && opnds[0].type == AARCH64_OPND_Rd);
1614 if (opnd->shifter.kind != AARCH64_MOD_LSL)
1615 {
1616 set_other_error (mismatch_detail, idx,
1617 _("invalid shift operator"));
1618 return 0;
1619 }
1620 size = aarch64_get_qualifier_esize (opnds[0].qualifier);
1621 if (!value_aligned_p (opnd->shifter.amount, 16))
1622 {
1623 set_other_error (mismatch_detail, idx,
1624 _("shift amount should be a multiple of 16"));
1625 return 0;
1626 }
1627 if (!value_in_range_p (opnd->shifter.amount, 0, size * 8 - 16))
1628 {
1629 set_sft_amount_out_of_range_error (mismatch_detail, idx,
1630 0, size * 8 - 16);
1631 return 0;
1632 }
1633 if (opnd->imm.value < 0)
1634 {
1635 set_other_error (mismatch_detail, idx,
1636 _("negative immediate value not allowed"));
1637 return 0;
1638 }
1639 if (!value_fit_unsigned_field_p (opnd->imm.value, 16))
1640 {
1641 set_other_error (mismatch_detail, idx,
1642 _("immediate out of range"));
1643 return 0;
1644 }
1645 break;
1646
1647 case AARCH64_OPND_IMM_MOV:
1648 {
42408347 1649 int esize = aarch64_get_qualifier_esize (opnds[0].qualifier);
a06ea964
NC
1650 imm = opnd->imm.value;
1651 assert (idx == 1);
1652 switch (opcode->op)
1653 {
1654 case OP_MOV_IMM_WIDEN:
1655 imm = ~imm;
1656 /* Fall through... */
1657 case OP_MOV_IMM_WIDE:
42408347 1658 if (!aarch64_wide_constant_p (imm, esize == 4, NULL))
a06ea964
NC
1659 {
1660 set_other_error (mismatch_detail, idx,
1661 _("immediate out of range"));
1662 return 0;
1663 }
1664 break;
1665 case OP_MOV_IMM_LOG:
42408347 1666 if (!aarch64_logical_immediate_p (imm, esize, NULL))
a06ea964
NC
1667 {
1668 set_other_error (mismatch_detail, idx,
1669 _("immediate out of range"));
1670 return 0;
1671 }
1672 break;
1673 default:
1674 assert (0);
1675 return 0;
1676 }
1677 }
1678 break;
1679
1680 case AARCH64_OPND_NZCV:
1681 case AARCH64_OPND_CCMP_IMM:
1682 case AARCH64_OPND_EXCEPTION:
1683 case AARCH64_OPND_UIMM4:
1684 case AARCH64_OPND_UIMM7:
1685 case AARCH64_OPND_UIMM3_OP1:
1686 case AARCH64_OPND_UIMM3_OP2:
1687 size = get_operand_fields_width (get_operand_from_code (type));
1688 assert (size < 32);
1689 if (!value_fit_unsigned_field_p (opnd->imm.value, size))
1690 {
1691 set_imm_out_of_range_error (mismatch_detail, idx, 0,
1692 (1 << size) - 1);
1693 return 0;
1694 }
1695 break;
1696
1697 case AARCH64_OPND_WIDTH:
d685192a 1698 assert (idx > 1 && opnds[idx-1].type == AARCH64_OPND_IMM
a06ea964
NC
1699 && opnds[0].type == AARCH64_OPND_Rd);
1700 size = get_upper_bound (qualifier);
1701 if (opnd->imm.value + opnds[idx-1].imm.value > size)
1702 /* lsb+width <= reg.size */
1703 {
1704 set_imm_out_of_range_error (mismatch_detail, idx, 1,
1705 size - opnds[idx-1].imm.value);
1706 return 0;
1707 }
1708 break;
1709
1710 case AARCH64_OPND_LIMM:
42408347
RS
1711 {
1712 int esize = aarch64_get_qualifier_esize (opnds[0].qualifier);
1713 uint64_t uimm = opnd->imm.value;
1714 if (opcode->op == OP_BIC)
1715 uimm = ~uimm;
1716 if (aarch64_logical_immediate_p (uimm, esize, NULL) == FALSE)
1717 {
1718 set_other_error (mismatch_detail, idx,
1719 _("immediate out of range"));
1720 return 0;
1721 }
1722 }
a06ea964
NC
1723 break;
1724
1725 case AARCH64_OPND_IMM0:
1726 case AARCH64_OPND_FPIMM0:
1727 if (opnd->imm.value != 0)
1728 {
1729 set_other_error (mismatch_detail, idx,
1730 _("immediate zero expected"));
1731 return 0;
1732 }
1733 break;
1734
1735 case AARCH64_OPND_SHLL_IMM:
1736 assert (idx == 2);
1737 size = 8 * aarch64_get_qualifier_esize (opnds[idx - 1].qualifier);
1738 if (opnd->imm.value != size)
1739 {
1740 set_other_error (mismatch_detail, idx,
1741 _("invalid shift amount"));
1742 return 0;
1743 }
1744 break;
1745
1746 case AARCH64_OPND_IMM_VLSL:
1747 size = aarch64_get_qualifier_esize (qualifier);
1748 if (!value_in_range_p (opnd->imm.value, 0, size * 8 - 1))
1749 {
1750 set_imm_out_of_range_error (mismatch_detail, idx, 0,
1751 size * 8 - 1);
1752 return 0;
1753 }
1754 break;
1755
1756 case AARCH64_OPND_IMM_VLSR:
1757 size = aarch64_get_qualifier_esize (qualifier);
1758 if (!value_in_range_p (opnd->imm.value, 1, size * 8))
1759 {
1760 set_imm_out_of_range_error (mismatch_detail, idx, 1, size * 8);
1761 return 0;
1762 }
1763 break;
1764
1765 case AARCH64_OPND_SIMD_IMM:
1766 case AARCH64_OPND_SIMD_IMM_SFT:
1767 /* Qualifier check. */
1768 switch (qualifier)
1769 {
1770 case AARCH64_OPND_QLF_LSL:
1771 if (opnd->shifter.kind != AARCH64_MOD_LSL)
1772 {
1773 set_other_error (mismatch_detail, idx,
1774 _("invalid shift operator"));
1775 return 0;
1776 }
1777 break;
1778 case AARCH64_OPND_QLF_MSL:
1779 if (opnd->shifter.kind != AARCH64_MOD_MSL)
1780 {
1781 set_other_error (mismatch_detail, idx,
1782 _("invalid shift operator"));
1783 return 0;
1784 }
1785 break;
1786 case AARCH64_OPND_QLF_NIL:
1787 if (opnd->shifter.kind != AARCH64_MOD_NONE)
1788 {
1789 set_other_error (mismatch_detail, idx,
1790 _("shift is not permitted"));
1791 return 0;
1792 }
1793 break;
1794 default:
1795 assert (0);
1796 return 0;
1797 }
1798 /* Is the immediate valid? */
1799 assert (idx == 1);
1800 if (aarch64_get_qualifier_esize (opnds[0].qualifier) != 8)
1801 {
d2865ed3
YZ
1802 /* uimm8 or simm8 */
1803 if (!value_in_range_p (opnd->imm.value, -128, 255))
a06ea964 1804 {
d2865ed3 1805 set_imm_out_of_range_error (mismatch_detail, idx, -128, 255);
a06ea964
NC
1806 return 0;
1807 }
1808 }
1809 else if (aarch64_shrink_expanded_imm8 (opnd->imm.value) < 0)
1810 {
1811 /* uimm64 is not
1812 'aaaaaaaabbbbbbbbccccccccddddddddeeeeeeee
1813 ffffffffgggggggghhhhhhhh'. */
1814 set_other_error (mismatch_detail, idx,
1815 _("invalid value for immediate"));
1816 return 0;
1817 }
1818 /* Is the shift amount valid? */
1819 switch (opnd->shifter.kind)
1820 {
1821 case AARCH64_MOD_LSL:
1822 size = aarch64_get_qualifier_esize (opnds[0].qualifier);
f5555712 1823 if (!value_in_range_p (opnd->shifter.amount, 0, (size - 1) * 8))
a06ea964 1824 {
f5555712
YZ
1825 set_sft_amount_out_of_range_error (mismatch_detail, idx, 0,
1826 (size - 1) * 8);
a06ea964
NC
1827 return 0;
1828 }
f5555712 1829 if (!value_aligned_p (opnd->shifter.amount, 8))
a06ea964 1830 {
f5555712 1831 set_unaligned_error (mismatch_detail, idx, 8);
a06ea964
NC
1832 return 0;
1833 }
1834 break;
1835 case AARCH64_MOD_MSL:
1836 /* Only 8 and 16 are valid shift amount. */
1837 if (opnd->shifter.amount != 8 && opnd->shifter.amount != 16)
1838 {
1839 set_other_error (mismatch_detail, idx,
1840 _("shift amount expected to be 0 or 16"));
1841 return 0;
1842 }
1843 break;
1844 default:
1845 if (opnd->shifter.kind != AARCH64_MOD_NONE)
1846 {
1847 set_other_error (mismatch_detail, idx,
1848 _("invalid shift operator"));
1849 return 0;
1850 }
1851 break;
1852 }
1853 break;
1854
1855 case AARCH64_OPND_FPIMM:
1856 case AARCH64_OPND_SIMD_FPIMM:
1857 if (opnd->imm.is_fp == 0)
1858 {
1859 set_other_error (mismatch_detail, idx,
1860 _("floating-point immediate expected"));
1861 return 0;
1862 }
1863 /* The value is expected to be an 8-bit floating-point constant with
1864 sign, 3-bit exponent and normalized 4 bits of precision, encoded
1865 in "a:b:c:d:e:f:g:h" or FLD_imm8 (depending on the type of the
1866 instruction). */
1867 if (!value_in_range_p (opnd->imm.value, 0, 255))
1868 {
1869 set_other_error (mismatch_detail, idx,
1870 _("immediate out of range"));
1871 return 0;
1872 }
1873 if (opnd->shifter.kind != AARCH64_MOD_NONE)
1874 {
1875 set_other_error (mismatch_detail, idx,
1876 _("invalid shift operator"));
1877 return 0;
1878 }
1879 break;
1880
1881 default:
1882 break;
1883 }
1884 break;
1885
1886 case AARCH64_OPND_CLASS_CP_REG:
1887 /* Cn or Cm: 4-bit opcode field named for historical reasons.
1888 valid range: C0 - C15. */
1889 if (opnd->reg.regno > 15)
1890 {
1891 set_regno_out_of_range_error (mismatch_detail, idx, 0, 15);
1892 return 0;
1893 }
1894 break;
1895
1896 case AARCH64_OPND_CLASS_SYSTEM:
1897 switch (type)
1898 {
1899 case AARCH64_OPND_PSTATEFIELD:
1900 assert (idx == 0 && opnds[1].type == AARCH64_OPND_UIMM4);
0bff6e2d
MW
1901 /* MSR UAO, #uimm4
1902 MSR PAN, #uimm4
c2825638 1903 The immediate must be #0 or #1. */
0bff6e2d
MW
1904 if ((opnd->pstatefield == 0x03 /* UAO. */
1905 || opnd->pstatefield == 0x04) /* PAN. */
c2825638
MW
1906 && opnds[1].imm.value > 1)
1907 {
1908 set_imm_out_of_range_error (mismatch_detail, idx, 0, 1);
1909 return 0;
1910 }
a06ea964
NC
1911 /* MSR SPSel, #uimm4
1912 Uses uimm4 as a control value to select the stack pointer: if
1913 bit 0 is set it selects the current exception level's stack
1914 pointer, if bit 0 is clear it selects shared EL0 stack pointer.
1915 Bits 1 to 3 of uimm4 are reserved and should be zero. */
1916 if (opnd->pstatefield == 0x05 /* spsel */ && opnds[1].imm.value > 1)
1917 {
1918 set_imm_out_of_range_error (mismatch_detail, idx, 0, 1);
1919 return 0;
1920 }
1921 break;
1922 default:
1923 break;
1924 }
1925 break;
1926
1927 case AARCH64_OPND_CLASS_SIMD_ELEMENT:
1928 /* Get the upper bound for the element index. */
1929 num = 16 / aarch64_get_qualifier_esize (qualifier) - 1;
1930 /* Index out-of-range. */
1931 if (!value_in_range_p (opnd->reglane.index, 0, num))
1932 {
1933 set_elem_idx_out_of_range_error (mismatch_detail, idx, 0, num);
1934 return 0;
1935 }
1936 /* SMLAL<Q> <Vd>.<Ta>, <Vn>.<Tb>, <Vm>.<Ts>[<index>].
1937 <Vm> Is the vector register (V0-V31) or (V0-V15), whose
1938 number is encoded in "size:M:Rm":
1939 size <Vm>
1940 00 RESERVED
1941 01 0:Rm
1942 10 M:Rm
1943 11 RESERVED */
1944 if (type == AARCH64_OPND_Em && qualifier == AARCH64_OPND_QLF_S_H
1945 && !value_in_range_p (opnd->reglane.regno, 0, 15))
1946 {
1947 set_regno_out_of_range_error (mismatch_detail, idx, 0, 15);
1948 return 0;
1949 }
1950 break;
1951
1952 case AARCH64_OPND_CLASS_MODIFIED_REG:
1953 assert (idx == 1 || idx == 2);
1954 switch (type)
1955 {
1956 case AARCH64_OPND_Rm_EXT:
1957 if (aarch64_extend_operator_p (opnd->shifter.kind) == FALSE
1958 && opnd->shifter.kind != AARCH64_MOD_LSL)
1959 {
1960 set_other_error (mismatch_detail, idx,
1961 _("extend operator expected"));
1962 return 0;
1963 }
1964 /* It is not optional unless at least one of "Rd" or "Rn" is '11111'
1965 (i.e. SP), in which case it defaults to LSL. The LSL alias is
1966 only valid when "Rd" or "Rn" is '11111', and is preferred in that
1967 case. */
1968 if (!aarch64_stack_pointer_p (opnds + 0)
1969 && (idx != 2 || !aarch64_stack_pointer_p (opnds + 1)))
1970 {
1971 if (!opnd->shifter.operator_present)
1972 {
1973 set_other_error (mismatch_detail, idx,
1974 _("missing extend operator"));
1975 return 0;
1976 }
1977 else if (opnd->shifter.kind == AARCH64_MOD_LSL)
1978 {
1979 set_other_error (mismatch_detail, idx,
1980 _("'LSL' operator not allowed"));
1981 return 0;
1982 }
1983 }
1984 assert (opnd->shifter.operator_present /* Default to LSL. */
1985 || opnd->shifter.kind == AARCH64_MOD_LSL);
1986 if (!value_in_range_p (opnd->shifter.amount, 0, 4))
1987 {
1988 set_sft_amount_out_of_range_error (mismatch_detail, idx, 0, 4);
1989 return 0;
1990 }
1991 /* In the 64-bit form, the final register operand is written as Wm
1992 for all but the (possibly omitted) UXTX/LSL and SXTX
1993 operators.
1994 N.B. GAS allows X register to be used with any operator as a
1995 programming convenience. */
1996 if (qualifier == AARCH64_OPND_QLF_X
1997 && opnd->shifter.kind != AARCH64_MOD_LSL
1998 && opnd->shifter.kind != AARCH64_MOD_UXTX
1999 && opnd->shifter.kind != AARCH64_MOD_SXTX)
2000 {
2001 set_other_error (mismatch_detail, idx, _("W register expected"));
2002 return 0;
2003 }
2004 break;
2005
2006 case AARCH64_OPND_Rm_SFT:
2007 /* ROR is not available to the shifted register operand in
2008 arithmetic instructions. */
2009 if (aarch64_shift_operator_p (opnd->shifter.kind) == FALSE)
2010 {
2011 set_other_error (mismatch_detail, idx,
2012 _("shift operator expected"));
2013 return 0;
2014 }
2015 if (opnd->shifter.kind == AARCH64_MOD_ROR
2016 && opcode->iclass != log_shift)
2017 {
2018 set_other_error (mismatch_detail, idx,
2019 _("'ROR' operator not allowed"));
2020 return 0;
2021 }
2022 num = qualifier == AARCH64_OPND_QLF_W ? 31 : 63;
2023 if (!value_in_range_p (opnd->shifter.amount, 0, num))
2024 {
2025 set_sft_amount_out_of_range_error (mismatch_detail, idx, 0, num);
2026 return 0;
2027 }
2028 break;
2029
2030 default:
2031 break;
2032 }
2033 break;
2034
2035 default:
2036 break;
2037 }
2038
2039 return 1;
2040}
2041
2042/* Main entrypoint for the operand constraint checking.
2043
2044 Return 1 if operands of *INST meet the constraint applied by the operand
2045 codes and operand qualifiers; otherwise return 0 and if MISMATCH_DETAIL is
2046 not NULL, return the detail of the error in *MISMATCH_DETAIL. N.B. when
2047 adding more constraint checking, make sure MISMATCH_DETAIL->KIND is set
2048 with a proper error kind rather than AARCH64_OPDE_NIL (GAS asserts non-NIL
2049 error kind when it is notified that an instruction does not pass the check).
2050
2051 Un-determined operand qualifiers may get established during the process. */
2052
2053int
2054aarch64_match_operands_constraint (aarch64_inst *inst,
2055 aarch64_operand_error *mismatch_detail)
2056{
2057 int i;
2058
2059 DEBUG_TRACE ("enter");
2060
0c608d6b
RS
2061 /* Check for cases where a source register needs to be the same as the
2062 destination register. Do this before matching qualifiers since if
2063 an instruction has both invalid tying and invalid qualifiers,
2064 the error about qualifiers would suggest several alternative
2065 instructions that also have invalid tying. */
2066 i = inst->opcode->tied_operand;
2067 if (i > 0 && (inst->operands[0].reg.regno != inst->operands[i].reg.regno))
2068 {
2069 if (mismatch_detail)
2070 {
2071 mismatch_detail->kind = AARCH64_OPDE_UNTIED_OPERAND;
2072 mismatch_detail->index = i;
2073 mismatch_detail->error = NULL;
2074 }
2075 return 0;
2076 }
2077
a06ea964
NC
2078 /* Match operands' qualifier.
2079 *INST has already had qualifier establish for some, if not all, of
2080 its operands; we need to find out whether these established
2081 qualifiers match one of the qualifier sequence in
2082 INST->OPCODE->QUALIFIERS_LIST. If yes, we will assign each operand
2083 with the corresponding qualifier in such a sequence.
2084 Only basic operand constraint checking is done here; the more thorough
2085 constraint checking will carried out by operand_general_constraint_met_p,
2086 which has be to called after this in order to get all of the operands'
2087 qualifiers established. */
2088 if (match_operands_qualifier (inst, TRUE /* update_p */) == 0)
2089 {
2090 DEBUG_TRACE ("FAIL on operand qualifier matching");
2091 if (mismatch_detail)
2092 {
2093 /* Return an error type to indicate that it is the qualifier
2094 matching failure; we don't care about which operand as there
2095 are enough information in the opcode table to reproduce it. */
2096 mismatch_detail->kind = AARCH64_OPDE_INVALID_VARIANT;
2097 mismatch_detail->index = -1;
2098 mismatch_detail->error = NULL;
2099 }
2100 return 0;
2101 }
2102
2103 /* Match operands' constraint. */
2104 for (i = 0; i < AARCH64_MAX_OPND_NUM; ++i)
2105 {
2106 enum aarch64_opnd type = inst->opcode->operands[i];
2107 if (type == AARCH64_OPND_NIL)
2108 break;
2109 if (inst->operands[i].skip)
2110 {
2111 DEBUG_TRACE ("skip the incomplete operand %d", i);
2112 continue;
2113 }
2114 if (operand_general_constraint_met_p (inst->operands, i, type,
2115 inst->opcode, mismatch_detail) == 0)
2116 {
2117 DEBUG_TRACE ("FAIL on operand %d", i);
2118 return 0;
2119 }
2120 }
2121
2122 DEBUG_TRACE ("PASS");
2123
2124 return 1;
2125}
2126
2127/* Replace INST->OPCODE with OPCODE and return the replaced OPCODE.
2128 Also updates the TYPE of each INST->OPERANDS with the corresponding
2129 value of OPCODE->OPERANDS.
2130
2131 Note that some operand qualifiers may need to be manually cleared by
2132 the caller before it further calls the aarch64_opcode_encode; by
2133 doing this, it helps the qualifier matching facilities work
2134 properly. */
2135
2136const aarch64_opcode*
2137aarch64_replace_opcode (aarch64_inst *inst, const aarch64_opcode *opcode)
2138{
2139 int i;
2140 const aarch64_opcode *old = inst->opcode;
2141
2142 inst->opcode = opcode;
2143
2144 /* Update the operand types. */
2145 for (i = 0; i < AARCH64_MAX_OPND_NUM; ++i)
2146 {
2147 inst->operands[i].type = opcode->operands[i];
2148 if (opcode->operands[i] == AARCH64_OPND_NIL)
2149 break;
2150 }
2151
2152 DEBUG_TRACE ("replace %s with %s", old->name, opcode->name);
2153
2154 return old;
2155}
2156
2157int
2158aarch64_operand_index (const enum aarch64_opnd *operands, enum aarch64_opnd operand)
2159{
2160 int i;
2161 for (i = 0; i < AARCH64_MAX_OPND_NUM; ++i)
2162 if (operands[i] == operand)
2163 return i;
2164 else if (operands[i] == AARCH64_OPND_NIL)
2165 break;
2166 return -1;
2167}
2168\f
72e9f319
RS
2169/* R0...R30, followed by FOR31. */
2170#define BANK(R, FOR31) \
2171 { R (0), R (1), R (2), R (3), R (4), R (5), R (6), R (7), \
2172 R (8), R (9), R (10), R (11), R (12), R (13), R (14), R (15), \
2173 R (16), R (17), R (18), R (19), R (20), R (21), R (22), R (23), \
2174 R (24), R (25), R (26), R (27), R (28), R (29), R (30), FOR31 }
a06ea964
NC
2175/* [0][0] 32-bit integer regs with sp Wn
2176 [0][1] 64-bit integer regs with sp Xn sf=1
2177 [1][0] 32-bit integer regs with #0 Wn
2178 [1][1] 64-bit integer regs with #0 Xn sf=1 */
2179static const char *int_reg[2][2][32] = {
72e9f319
RS
2180#define R32(X) "w" #X
2181#define R64(X) "x" #X
2182 { BANK (R32, "wsp"), BANK (R64, "sp") },
2183 { BANK (R32, "wzr"), BANK (R64, "xzr") }
a06ea964
NC
2184#undef R64
2185#undef R32
2186};
72e9f319 2187#undef BANK
a06ea964
NC
2188
2189/* Return the integer register name.
2190 if SP_REG_P is not 0, R31 is an SP reg, other R31 is the zero reg. */
2191
2192static inline const char *
2193get_int_reg_name (int regno, aarch64_opnd_qualifier_t qualifier, int sp_reg_p)
2194{
2195 const int has_zr = sp_reg_p ? 0 : 1;
2196 const int is_64 = aarch64_get_qualifier_esize (qualifier) == 4 ? 0 : 1;
2197 return int_reg[has_zr][is_64][regno];
2198}
2199
2200/* Like get_int_reg_name, but IS_64 is always 1. */
2201
2202static inline const char *
2203get_64bit_int_reg_name (int regno, int sp_reg_p)
2204{
2205 const int has_zr = sp_reg_p ? 0 : 1;
2206 return int_reg[has_zr][1][regno];
2207}
2208
01dbfe4c
RS
2209/* Get the name of the integer offset register in OPND, using the shift type
2210 to decide whether it's a word or doubleword. */
2211
2212static inline const char *
2213get_offset_int_reg_name (const aarch64_opnd_info *opnd)
2214{
2215 switch (opnd->shifter.kind)
2216 {
2217 case AARCH64_MOD_UXTW:
2218 case AARCH64_MOD_SXTW:
2219 return get_int_reg_name (opnd->addr.offset.regno, AARCH64_OPND_QLF_W, 0);
2220
2221 case AARCH64_MOD_LSL:
2222 case AARCH64_MOD_SXTX:
2223 return get_int_reg_name (opnd->addr.offset.regno, AARCH64_OPND_QLF_X, 0);
2224
2225 default:
2226 abort ();
2227 }
2228}
2229
a06ea964
NC
2230/* Types for expanding an encoded 8-bit value to a floating-point value. */
2231
2232typedef union
2233{
2234 uint64_t i;
2235 double d;
2236} double_conv_t;
2237
2238typedef union
2239{
2240 uint32_t i;
2241 float f;
2242} single_conv_t;
2243
cf86120b
MW
2244typedef union
2245{
2246 uint32_t i;
2247 float f;
2248} half_conv_t;
2249
a06ea964
NC
2250/* IMM8 is an 8-bit floating-point constant with sign, 3-bit exponent and
2251 normalized 4 bits of precision, encoded in "a:b:c:d:e:f:g:h" or FLD_imm8
2252 (depending on the type of the instruction). IMM8 will be expanded to a
cf86120b
MW
2253 single-precision floating-point value (SIZE == 4) or a double-precision
2254 floating-point value (SIZE == 8). A half-precision floating-point value
2255 (SIZE == 2) is expanded to a single-precision floating-point value. The
2256 expanded value is returned. */
a06ea964
NC
2257
2258static uint64_t
cf86120b 2259expand_fp_imm (int size, uint32_t imm8)
a06ea964
NC
2260{
2261 uint64_t imm;
2262 uint32_t imm8_7, imm8_6_0, imm8_6, imm8_6_repl4;
2263
2264 imm8_7 = (imm8 >> 7) & 0x01; /* imm8<7> */
2265 imm8_6_0 = imm8 & 0x7f; /* imm8<6:0> */
2266 imm8_6 = imm8_6_0 >> 6; /* imm8<6> */
2267 imm8_6_repl4 = (imm8_6 << 3) | (imm8_6 << 2)
2268 | (imm8_6 << 1) | imm8_6; /* Replicate(imm8<6>,4) */
cf86120b 2269 if (size == 8)
a06ea964
NC
2270 {
2271 imm = (imm8_7 << (63-32)) /* imm8<7> */
2272 | ((imm8_6 ^ 1) << (62-32)) /* NOT(imm8<6) */
2273 | (imm8_6_repl4 << (58-32)) | (imm8_6 << (57-32))
2274 | (imm8_6 << (56-32)) | (imm8_6 << (55-32)) /* Replicate(imm8<6>,7) */
2275 | (imm8_6_0 << (48-32)); /* imm8<6>:imm8<5:0> */
2276 imm <<= 32;
2277 }
cf86120b 2278 else if (size == 4 || size == 2)
a06ea964
NC
2279 {
2280 imm = (imm8_7 << 31) /* imm8<7> */
2281 | ((imm8_6 ^ 1) << 30) /* NOT(imm8<6>) */
2282 | (imm8_6_repl4 << 26) /* Replicate(imm8<6>,4) */
2283 | (imm8_6_0 << 19); /* imm8<6>:imm8<5:0> */
2284 }
cf86120b
MW
2285 else
2286 {
2287 /* An unsupported size. */
2288 assert (0);
2289 }
a06ea964
NC
2290
2291 return imm;
2292}
2293
2294/* Produce the string representation of the register list operand *OPND
8a7f0c1b
RS
2295 in the buffer pointed by BUF of size SIZE. PREFIX is the part of
2296 the register name that comes before the register number, such as "v". */
a06ea964 2297static void
8a7f0c1b
RS
2298print_register_list (char *buf, size_t size, const aarch64_opnd_info *opnd,
2299 const char *prefix)
a06ea964
NC
2300{
2301 const int num_regs = opnd->reglist.num_regs;
2302 const int first_reg = opnd->reglist.first_regno;
2303 const int last_reg = (first_reg + num_regs - 1) & 0x1f;
2304 const char *qlf_name = aarch64_get_qualifier_name (opnd->qualifier);
2305 char tb[8]; /* Temporary buffer. */
2306
2307 assert (opnd->type != AARCH64_OPND_LEt || opnd->reglist.has_index);
2308 assert (num_regs >= 1 && num_regs <= 4);
2309
2310 /* Prepare the index if any. */
2311 if (opnd->reglist.has_index)
dab26bf4 2312 snprintf (tb, 8, "[%" PRIi64 "]", opnd->reglist.index);
a06ea964
NC
2313 else
2314 tb[0] = '\0';
2315
2316 /* The hyphenated form is preferred for disassembly if there are
2317 more than two registers in the list, and the register numbers
2318 are monotonically increasing in increments of one. */
2319 if (num_regs > 2 && last_reg > first_reg)
8a7f0c1b
RS
2320 snprintf (buf, size, "{%s%d.%s-%s%d.%s}%s", prefix, first_reg, qlf_name,
2321 prefix, last_reg, qlf_name, tb);
a06ea964
NC
2322 else
2323 {
2324 const int reg0 = first_reg;
2325 const int reg1 = (first_reg + 1) & 0x1f;
2326 const int reg2 = (first_reg + 2) & 0x1f;
2327 const int reg3 = (first_reg + 3) & 0x1f;
2328
2329 switch (num_regs)
2330 {
2331 case 1:
8a7f0c1b 2332 snprintf (buf, size, "{%s%d.%s}%s", prefix, reg0, qlf_name, tb);
a06ea964
NC
2333 break;
2334 case 2:
8a7f0c1b
RS
2335 snprintf (buf, size, "{%s%d.%s, %s%d.%s}%s", prefix, reg0, qlf_name,
2336 prefix, reg1, qlf_name, tb);
a06ea964
NC
2337 break;
2338 case 3:
8a7f0c1b
RS
2339 snprintf (buf, size, "{%s%d.%s, %s%d.%s, %s%d.%s}%s",
2340 prefix, reg0, qlf_name, prefix, reg1, qlf_name,
2341 prefix, reg2, qlf_name, tb);
a06ea964
NC
2342 break;
2343 case 4:
8a7f0c1b
RS
2344 snprintf (buf, size, "{%s%d.%s, %s%d.%s, %s%d.%s, %s%d.%s}%s",
2345 prefix, reg0, qlf_name, prefix, reg1, qlf_name,
2346 prefix, reg2, qlf_name, prefix, reg3, qlf_name, tb);
a06ea964
NC
2347 break;
2348 }
2349 }
2350}
2351
01dbfe4c
RS
2352/* Print the register+immediate address in OPND to BUF, which has SIZE
2353 characters. BASE is the name of the base register. */
2354
2355static void
2356print_immediate_offset_address (char *buf, size_t size,
2357 const aarch64_opnd_info *opnd,
2358 const char *base)
2359{
2360 if (opnd->addr.writeback)
2361 {
2362 if (opnd->addr.preind)
2363 snprintf (buf, size, "[%s,#%d]!", base, opnd->addr.offset.imm);
2364 else
2365 snprintf (buf, size, "[%s],#%d", base, opnd->addr.offset.imm);
2366 }
2367 else
2368 {
2369 if (opnd->addr.offset.imm)
2370 snprintf (buf, size, "[%s,#%d]", base, opnd->addr.offset.imm);
2371 else
2372 snprintf (buf, size, "[%s]", base);
2373 }
2374}
2375
a06ea964 2376/* Produce the string representation of the register offset address operand
01dbfe4c
RS
2377 *OPND in the buffer pointed by BUF of size SIZE. BASE and OFFSET are
2378 the names of the base and offset registers. */
a06ea964
NC
2379static void
2380print_register_offset_address (char *buf, size_t size,
01dbfe4c
RS
2381 const aarch64_opnd_info *opnd,
2382 const char *base, const char *offset)
a06ea964 2383{
0d2f91fe 2384 char tb[16]; /* Temporary buffer. */
a06ea964
NC
2385 bfd_boolean print_extend_p = TRUE;
2386 bfd_boolean print_amount_p = TRUE;
2387 const char *shift_name = aarch64_operand_modifiers[opnd->shifter.kind].name;
2388
a06ea964
NC
2389 if (!opnd->shifter.amount && (opnd->qualifier != AARCH64_OPND_QLF_S_B
2390 || !opnd->shifter.amount_present))
2391 {
2392 /* Not print the shift/extend amount when the amount is zero and
2393 when it is not the special case of 8-bit load/store instruction. */
2394 print_amount_p = FALSE;
2395 /* Likewise, no need to print the shift operator LSL in such a
2396 situation. */
01dbfe4c 2397 if (opnd->shifter.kind == AARCH64_MOD_LSL)
a06ea964
NC
2398 print_extend_p = FALSE;
2399 }
2400
2401 /* Prepare for the extend/shift. */
2402 if (print_extend_p)
2403 {
2404 if (print_amount_p)
0d2f91fe 2405 snprintf (tb, sizeof (tb), ",%s #%d", shift_name, opnd->shifter.amount);
a06ea964 2406 else
0d2f91fe 2407 snprintf (tb, sizeof (tb), ",%s", shift_name);
a06ea964
NC
2408 }
2409 else
2410 tb[0] = '\0';
2411
01dbfe4c 2412 snprintf (buf, size, "[%s,%s%s]", base, offset, tb);
a06ea964
NC
2413}
2414
2415/* Generate the string representation of the operand OPNDS[IDX] for OPCODE
2416 in *BUF. The caller should pass in the maximum size of *BUF in SIZE.
2417 PC, PCREL_P and ADDRESS are used to pass in and return information about
2418 the PC-relative address calculation, where the PC value is passed in
2419 PC. If the operand is pc-relative related, *PCREL_P (if PCREL_P non-NULL)
2420 will return 1 and *ADDRESS (if ADDRESS non-NULL) will return the
2421 calculated address; otherwise, *PCREL_P (if PCREL_P non-NULL) returns 0.
2422
2423 The function serves both the disassembler and the assembler diagnostics
2424 issuer, which is the reason why it lives in this file. */
2425
2426void
2427aarch64_print_operand (char *buf, size_t size, bfd_vma pc,
2428 const aarch64_opcode *opcode,
2429 const aarch64_opnd_info *opnds, int idx, int *pcrel_p,
2430 bfd_vma *address)
2431{
2432 int i;
2433 const char *name = NULL;
2434 const aarch64_opnd_info *opnd = opnds + idx;
2435 enum aarch64_modifier_kind kind;
2436 uint64_t addr;
2437
2438 buf[0] = '\0';
2439 if (pcrel_p)
2440 *pcrel_p = 0;
2441
2442 switch (opnd->type)
2443 {
2444 case AARCH64_OPND_Rd:
2445 case AARCH64_OPND_Rn:
2446 case AARCH64_OPND_Rm:
2447 case AARCH64_OPND_Rt:
2448 case AARCH64_OPND_Rt2:
2449 case AARCH64_OPND_Rs:
2450 case AARCH64_OPND_Ra:
2451 case AARCH64_OPND_Rt_SYS:
ee804238 2452 case AARCH64_OPND_PAIRREG:
a06ea964
NC
2453 /* The optional-ness of <Xt> in e.g. IC <ic_op>{, <Xt>} is determined by
2454 the <ic_op>, therefore we we use opnd->present to override the
2455 generic optional-ness information. */
2456 if (opnd->type == AARCH64_OPND_Rt_SYS && !opnd->present)
2457 break;
2458 /* Omit the operand, e.g. RET. */
2459 if (optional_operand_p (opcode, idx)
2460 && opnd->reg.regno == get_optional_operand_default_value (opcode))
2461 break;
2462 assert (opnd->qualifier == AARCH64_OPND_QLF_W
2463 || opnd->qualifier == AARCH64_OPND_QLF_X);
2464 snprintf (buf, size, "%s",
2465 get_int_reg_name (opnd->reg.regno, opnd->qualifier, 0));
2466 break;
2467
2468 case AARCH64_OPND_Rd_SP:
2469 case AARCH64_OPND_Rn_SP:
2470 assert (opnd->qualifier == AARCH64_OPND_QLF_W
2471 || opnd->qualifier == AARCH64_OPND_QLF_WSP
2472 || opnd->qualifier == AARCH64_OPND_QLF_X
2473 || opnd->qualifier == AARCH64_OPND_QLF_SP);
2474 snprintf (buf, size, "%s",
2475 get_int_reg_name (opnd->reg.regno, opnd->qualifier, 1));
2476 break;
2477
2478 case AARCH64_OPND_Rm_EXT:
2479 kind = opnd->shifter.kind;
2480 assert (idx == 1 || idx == 2);
2481 if ((aarch64_stack_pointer_p (opnds)
2482 || (idx == 2 && aarch64_stack_pointer_p (opnds + 1)))
2483 && ((opnd->qualifier == AARCH64_OPND_QLF_W
2484 && opnds[0].qualifier == AARCH64_OPND_QLF_W
2485 && kind == AARCH64_MOD_UXTW)
2486 || (opnd->qualifier == AARCH64_OPND_QLF_X
2487 && kind == AARCH64_MOD_UXTX)))
2488 {
2489 /* 'LSL' is the preferred form in this case. */
2490 kind = AARCH64_MOD_LSL;
2491 if (opnd->shifter.amount == 0)
2492 {
2493 /* Shifter omitted. */
2494 snprintf (buf, size, "%s",
2495 get_int_reg_name (opnd->reg.regno, opnd->qualifier, 0));
2496 break;
2497 }
2498 }
2499 if (opnd->shifter.amount)
2500 snprintf (buf, size, "%s, %s #%d",
2501 get_int_reg_name (opnd->reg.regno, opnd->qualifier, 0),
2502 aarch64_operand_modifiers[kind].name,
2503 opnd->shifter.amount);
2504 else
2505 snprintf (buf, size, "%s, %s",
2506 get_int_reg_name (opnd->reg.regno, opnd->qualifier, 0),
2507 aarch64_operand_modifiers[kind].name);
2508 break;
2509
2510 case AARCH64_OPND_Rm_SFT:
2511 assert (opnd->qualifier == AARCH64_OPND_QLF_W
2512 || opnd->qualifier == AARCH64_OPND_QLF_X);
2513 if (opnd->shifter.amount == 0 && opnd->shifter.kind == AARCH64_MOD_LSL)
2514 snprintf (buf, size, "%s",
2515 get_int_reg_name (opnd->reg.regno, opnd->qualifier, 0));
2516 else
2517 snprintf (buf, size, "%s, %s #%d",
2518 get_int_reg_name (opnd->reg.regno, opnd->qualifier, 0),
2519 aarch64_operand_modifiers[opnd->shifter.kind].name,
2520 opnd->shifter.amount);
2521 break;
2522
2523 case AARCH64_OPND_Fd:
2524 case AARCH64_OPND_Fn:
2525 case AARCH64_OPND_Fm:
2526 case AARCH64_OPND_Fa:
2527 case AARCH64_OPND_Ft:
2528 case AARCH64_OPND_Ft2:
2529 case AARCH64_OPND_Sd:
2530 case AARCH64_OPND_Sn:
2531 case AARCH64_OPND_Sm:
2532 snprintf (buf, size, "%s%d", aarch64_get_qualifier_name (opnd->qualifier),
2533 opnd->reg.regno);
2534 break;
2535
2536 case AARCH64_OPND_Vd:
2537 case AARCH64_OPND_Vn:
2538 case AARCH64_OPND_Vm:
2539 snprintf (buf, size, "v%d.%s", opnd->reg.regno,
2540 aarch64_get_qualifier_name (opnd->qualifier));
2541 break;
2542
2543 case AARCH64_OPND_Ed:
2544 case AARCH64_OPND_En:
2545 case AARCH64_OPND_Em:
dab26bf4 2546 snprintf (buf, size, "v%d.%s[%" PRIi64 "]", opnd->reglane.regno,
a06ea964
NC
2547 aarch64_get_qualifier_name (opnd->qualifier),
2548 opnd->reglane.index);
2549 break;
2550
2551 case AARCH64_OPND_VdD1:
2552 case AARCH64_OPND_VnD1:
2553 snprintf (buf, size, "v%d.d[1]", opnd->reg.regno);
2554 break;
2555
2556 case AARCH64_OPND_LVn:
2557 case AARCH64_OPND_LVt:
2558 case AARCH64_OPND_LVt_AL:
2559 case AARCH64_OPND_LEt:
8a7f0c1b 2560 print_register_list (buf, size, opnd, "v");
a06ea964
NC
2561 break;
2562
2563 case AARCH64_OPND_Cn:
2564 case AARCH64_OPND_Cm:
2565 snprintf (buf, size, "C%d", opnd->reg.regno);
2566 break;
2567
2568 case AARCH64_OPND_IDX:
2569 case AARCH64_OPND_IMM:
2570 case AARCH64_OPND_WIDTH:
2571 case AARCH64_OPND_UIMM3_OP1:
2572 case AARCH64_OPND_UIMM3_OP2:
2573 case AARCH64_OPND_BIT_NUM:
2574 case AARCH64_OPND_IMM_VLSL:
2575 case AARCH64_OPND_IMM_VLSR:
2576 case AARCH64_OPND_SHLL_IMM:
2577 case AARCH64_OPND_IMM0:
2578 case AARCH64_OPND_IMMR:
2579 case AARCH64_OPND_IMMS:
2580 case AARCH64_OPND_FBITS:
a06ea964
NC
2581 snprintf (buf, size, "#%" PRIi64, opnd->imm.value);
2582 break;
2583
fb098a1e
YZ
2584 case AARCH64_OPND_IMM_MOV:
2585 switch (aarch64_get_qualifier_esize (opnds[0].qualifier))
2586 {
2587 case 4: /* e.g. MOV Wd, #<imm32>. */
2588 {
2589 int imm32 = opnd->imm.value;
2590 snprintf (buf, size, "#0x%-20x\t// #%d", imm32, imm32);
2591 }
2592 break;
2593 case 8: /* e.g. MOV Xd, #<imm64>. */
2594 snprintf (buf, size, "#0x%-20" PRIx64 "\t// #%" PRIi64,
2595 opnd->imm.value, opnd->imm.value);
2596 break;
2597 default: assert (0);
2598 }
2599 break;
2600
a06ea964
NC
2601 case AARCH64_OPND_FPIMM0:
2602 snprintf (buf, size, "#0.0");
2603 break;
2604
2605 case AARCH64_OPND_LIMM:
2606 case AARCH64_OPND_AIMM:
2607 case AARCH64_OPND_HALF:
2608 if (opnd->shifter.amount)
2609 snprintf (buf, size, "#0x%" PRIx64 ", lsl #%d", opnd->imm.value,
2610 opnd->shifter.amount);
2611 else
2612 snprintf (buf, size, "#0x%" PRIx64, opnd->imm.value);
2613 break;
2614
2615 case AARCH64_OPND_SIMD_IMM:
2616 case AARCH64_OPND_SIMD_IMM_SFT:
2617 if ((! opnd->shifter.amount && opnd->shifter.kind == AARCH64_MOD_LSL)
2618 || opnd->shifter.kind == AARCH64_MOD_NONE)
2619 snprintf (buf, size, "#0x%" PRIx64, opnd->imm.value);
2620 else
2621 snprintf (buf, size, "#0x%" PRIx64 ", %s #%d", opnd->imm.value,
2622 aarch64_operand_modifiers[opnd->shifter.kind].name,
2623 opnd->shifter.amount);
2624 break;
2625
2626 case AARCH64_OPND_FPIMM:
2627 case AARCH64_OPND_SIMD_FPIMM:
2628 switch (aarch64_get_qualifier_esize (opnds[0].qualifier))
2629 {
cf86120b
MW
2630 case 2: /* e.g. FMOV <Hd>, #<imm>. */
2631 {
2632 half_conv_t c;
2633 c.i = expand_fp_imm (2, opnd->imm.value);
2634 snprintf (buf, size, "#%.18e", c.f);
2635 }
2636 break;
a06ea964
NC
2637 case 4: /* e.g. FMOV <Vd>.4S, #<imm>. */
2638 {
2639 single_conv_t c;
cf86120b 2640 c.i = expand_fp_imm (4, opnd->imm.value);
a06ea964
NC
2641 snprintf (buf, size, "#%.18e", c.f);
2642 }
2643 break;
2644 case 8: /* e.g. FMOV <Sd>, #<imm>. */
2645 {
2646 double_conv_t c;
cf86120b 2647 c.i = expand_fp_imm (8, opnd->imm.value);
a06ea964
NC
2648 snprintf (buf, size, "#%.18e", c.d);
2649 }
2650 break;
2651 default: assert (0);
2652 }
2653 break;
2654
2655 case AARCH64_OPND_CCMP_IMM:
2656 case AARCH64_OPND_NZCV:
2657 case AARCH64_OPND_EXCEPTION:
2658 case AARCH64_OPND_UIMM4:
2659 case AARCH64_OPND_UIMM7:
2660 if (optional_operand_p (opcode, idx) == TRUE
2661 && (opnd->imm.value ==
2662 (int64_t) get_optional_operand_default_value (opcode)))
2663 /* Omit the operand, e.g. DCPS1. */
2664 break;
2665 snprintf (buf, size, "#0x%x", (unsigned int)opnd->imm.value);
2666 break;
2667
2668 case AARCH64_OPND_COND:
68a64283 2669 case AARCH64_OPND_COND1:
a06ea964
NC
2670 snprintf (buf, size, "%s", opnd->cond->names[0]);
2671 break;
2672
2673 case AARCH64_OPND_ADDR_ADRP:
2674 addr = ((pc + AARCH64_PCREL_OFFSET) & ~(uint64_t)0xfff)
2675 + opnd->imm.value;
2676 if (pcrel_p)
2677 *pcrel_p = 1;
2678 if (address)
2679 *address = addr;
2680 /* This is not necessary during the disassembling, as print_address_func
2681 in the disassemble_info will take care of the printing. But some
2682 other callers may be still interested in getting the string in *STR,
2683 so here we do snprintf regardless. */
2684 snprintf (buf, size, "#0x%" PRIx64, addr);
2685 break;
2686
2687 case AARCH64_OPND_ADDR_PCREL14:
2688 case AARCH64_OPND_ADDR_PCREL19:
2689 case AARCH64_OPND_ADDR_PCREL21:
2690 case AARCH64_OPND_ADDR_PCREL26:
2691 addr = pc + AARCH64_PCREL_OFFSET + opnd->imm.value;
2692 if (pcrel_p)
2693 *pcrel_p = 1;
2694 if (address)
2695 *address = addr;
2696 /* This is not necessary during the disassembling, as print_address_func
2697 in the disassemble_info will take care of the printing. But some
2698 other callers may be still interested in getting the string in *STR,
2699 so here we do snprintf regardless. */
2700 snprintf (buf, size, "#0x%" PRIx64, addr);
2701 break;
2702
2703 case AARCH64_OPND_ADDR_SIMPLE:
2704 case AARCH64_OPND_SIMD_ADDR_SIMPLE:
2705 case AARCH64_OPND_SIMD_ADDR_POST:
2706 name = get_64bit_int_reg_name (opnd->addr.base_regno, 1);
2707 if (opnd->type == AARCH64_OPND_SIMD_ADDR_POST)
2708 {
2709 if (opnd->addr.offset.is_reg)
2710 snprintf (buf, size, "[%s], x%d", name, opnd->addr.offset.regno);
2711 else
2712 snprintf (buf, size, "[%s], #%d", name, opnd->addr.offset.imm);
2713 }
2714 else
2715 snprintf (buf, size, "[%s]", name);
2716 break;
2717
2718 case AARCH64_OPND_ADDR_REGOFF:
01dbfe4c
RS
2719 print_register_offset_address
2720 (buf, size, opnd, get_64bit_int_reg_name (opnd->addr.base_regno, 1),
2721 get_offset_int_reg_name (opnd));
a06ea964
NC
2722 break;
2723
2724 case AARCH64_OPND_ADDR_SIMM7:
2725 case AARCH64_OPND_ADDR_SIMM9:
2726 case AARCH64_OPND_ADDR_SIMM9_2:
01dbfe4c
RS
2727 print_immediate_offset_address
2728 (buf, size, opnd, get_64bit_int_reg_name (opnd->addr.base_regno, 1));
a06ea964
NC
2729 break;
2730
2731 case AARCH64_OPND_ADDR_UIMM12:
2732 name = get_64bit_int_reg_name (opnd->addr.base_regno, 1);
2733 if (opnd->addr.offset.imm)
2734 snprintf (buf, size, "[%s,#%d]", name, opnd->addr.offset.imm);
2735 else
2736 snprintf (buf, size, "[%s]", name);
2737 break;
2738
2739 case AARCH64_OPND_SYSREG:
2740 for (i = 0; aarch64_sys_regs[i].name; ++i)
49eec193
YZ
2741 if (aarch64_sys_regs[i].value == opnd->sysreg
2742 && ! aarch64_sys_reg_deprecated_p (&aarch64_sys_regs[i]))
a06ea964
NC
2743 break;
2744 if (aarch64_sys_regs[i].name)
2745 snprintf (buf, size, "%s", aarch64_sys_regs[i].name);
2746 else
2747 {
2748 /* Implementation defined system register. */
2749 unsigned int value = opnd->sysreg;
2750 snprintf (buf, size, "s%u_%u_c%u_c%u_%u", (value >> 14) & 0x3,
2751 (value >> 11) & 0x7, (value >> 7) & 0xf, (value >> 3) & 0xf,
2752 value & 0x7);
2753 }
2754 break;
2755
2756 case AARCH64_OPND_PSTATEFIELD:
2757 for (i = 0; aarch64_pstatefields[i].name; ++i)
2758 if (aarch64_pstatefields[i].value == opnd->pstatefield)
2759 break;
2760 assert (aarch64_pstatefields[i].name);
2761 snprintf (buf, size, "%s", aarch64_pstatefields[i].name);
2762 break;
2763
2764 case AARCH64_OPND_SYSREG_AT:
2765 case AARCH64_OPND_SYSREG_DC:
2766 case AARCH64_OPND_SYSREG_IC:
2767 case AARCH64_OPND_SYSREG_TLBI:
875880c6 2768 snprintf (buf, size, "%s", opnd->sysins_op->name);
a06ea964
NC
2769 break;
2770
2771 case AARCH64_OPND_BARRIER:
2772 snprintf (buf, size, "%s", opnd->barrier->name);
2773 break;
2774
2775 case AARCH64_OPND_BARRIER_ISB:
2776 /* Operand can be omitted, e.g. in DCPS1. */
2777 if (! optional_operand_p (opcode, idx)
2778 || (opnd->barrier->value
2779 != get_optional_operand_default_value (opcode)))
2780 snprintf (buf, size, "#0x%x", opnd->barrier->value);
2781 break;
2782
2783 case AARCH64_OPND_PRFOP:
a1ccaec9
YZ
2784 if (opnd->prfop->name != NULL)
2785 snprintf (buf, size, "%s", opnd->prfop->name);
2786 else
2787 snprintf (buf, size, "#0x%02x", opnd->prfop->value);
a06ea964
NC
2788 break;
2789
1e6f4800
MW
2790 case AARCH64_OPND_BARRIER_PSB:
2791 snprintf (buf, size, "%s", opnd->hint_option->name);
2792 break;
2793
a06ea964
NC
2794 default:
2795 assert (0);
2796 }
2797}
2798\f
2799#define CPENC(op0,op1,crn,crm,op2) \
2800 ((((op0) << 19) | ((op1) << 16) | ((crn) << 12) | ((crm) << 8) | ((op2) << 5)) >> 5)
2801 /* for 3.9.3 Instructions for Accessing Special Purpose Registers */
2802#define CPEN_(op1,crm,op2) CPENC(3,(op1),4,(crm),(op2))
2803 /* for 3.9.10 System Instructions */
2804#define CPENS(op1,crn,crm,op2) CPENC(1,(op1),(crn),(crm),(op2))
2805
2806#define C0 0
2807#define C1 1
2808#define C2 2
2809#define C3 3
2810#define C4 4
2811#define C5 5
2812#define C6 6
2813#define C7 7
2814#define C8 8
2815#define C9 9
2816#define C10 10
2817#define C11 11
2818#define C12 12
2819#define C13 13
2820#define C14 14
2821#define C15 15
2822
49eec193
YZ
2823#ifdef F_DEPRECATED
2824#undef F_DEPRECATED
2825#endif
2826#define F_DEPRECATED 0x1 /* Deprecated system register. */
2827
f21cce2c
MW
2828#ifdef F_ARCHEXT
2829#undef F_ARCHEXT
2830#endif
2831#define F_ARCHEXT 0x2 /* Architecture dependent system register. */
2832
ea2deeec
MW
2833#ifdef F_HASXT
2834#undef F_HASXT
2835#endif
2836#define F_HASXT 0x4 /* System instruction register <Xt>
2837 operand. */
2838
f21cce2c 2839
a06ea964
NC
2840/* TODO there are two more issues need to be resolved
2841 1. handle read-only and write-only system registers
2842 2. handle cpu-implementation-defined system registers. */
49eec193
YZ
2843const aarch64_sys_reg aarch64_sys_regs [] =
2844{
2845 { "spsr_el1", CPEN_(0,C0,0), 0 }, /* = spsr_svc */
250aafa4 2846 { "spsr_el12", CPEN_ (5, C0, 0), F_ARCHEXT },
49eec193 2847 { "elr_el1", CPEN_(0,C0,1), 0 },
250aafa4 2848 { "elr_el12", CPEN_ (5, C0, 1), F_ARCHEXT },
49eec193
YZ
2849 { "sp_el0", CPEN_(0,C1,0), 0 },
2850 { "spsel", CPEN_(0,C2,0), 0 },
2851 { "daif", CPEN_(3,C2,1), 0 },
2852 { "currentel", CPEN_(0,C2,2), 0 }, /* RO */
f21cce2c 2853 { "pan", CPEN_(0,C2,3), F_ARCHEXT },
6479e48e 2854 { "uao", CPEN_ (0, C2, 4), F_ARCHEXT },
49eec193
YZ
2855 { "nzcv", CPEN_(3,C2,0), 0 },
2856 { "fpcr", CPEN_(3,C4,0), 0 },
2857 { "fpsr", CPEN_(3,C4,1), 0 },
2858 { "dspsr_el0", CPEN_(3,C5,0), 0 },
2859 { "dlr_el0", CPEN_(3,C5,1), 0 },
2860 { "spsr_el2", CPEN_(4,C0,0), 0 }, /* = spsr_hyp */
2861 { "elr_el2", CPEN_(4,C0,1), 0 },
2862 { "sp_el1", CPEN_(4,C1,0), 0 },
2863 { "spsr_irq", CPEN_(4,C3,0), 0 },
2864 { "spsr_abt", CPEN_(4,C3,1), 0 },
2865 { "spsr_und", CPEN_(4,C3,2), 0 },
2866 { "spsr_fiq", CPEN_(4,C3,3), 0 },
2867 { "spsr_el3", CPEN_(6,C0,0), 0 },
2868 { "elr_el3", CPEN_(6,C0,1), 0 },
2869 { "sp_el2", CPEN_(6,C1,0), 0 },
2870 { "spsr_svc", CPEN_(0,C0,0), F_DEPRECATED }, /* = spsr_el1 */
2871 { "spsr_hyp", CPEN_(4,C0,0), F_DEPRECATED }, /* = spsr_el2 */
2872 { "midr_el1", CPENC(3,0,C0,C0,0), 0 }, /* RO */
2873 { "ctr_el0", CPENC(3,3,C0,C0,1), 0 }, /* RO */
2874 { "mpidr_el1", CPENC(3,0,C0,C0,5), 0 }, /* RO */
2875 { "revidr_el1", CPENC(3,0,C0,C0,6), 0 }, /* RO */
2876 { "aidr_el1", CPENC(3,1,C0,C0,7), 0 }, /* RO */
2877 { "dczid_el0", CPENC(3,3,C0,C0,7), 0 }, /* RO */
2878 { "id_dfr0_el1", CPENC(3,0,C0,C1,2), 0 }, /* RO */
2879 { "id_pfr0_el1", CPENC(3,0,C0,C1,0), 0 }, /* RO */
2880 { "id_pfr1_el1", CPENC(3,0,C0,C1,1), 0 }, /* RO */
2881 { "id_afr0_el1", CPENC(3,0,C0,C1,3), 0 }, /* RO */
2882 { "id_mmfr0_el1", CPENC(3,0,C0,C1,4), 0 }, /* RO */
2883 { "id_mmfr1_el1", CPENC(3,0,C0,C1,5), 0 }, /* RO */
2884 { "id_mmfr2_el1", CPENC(3,0,C0,C1,6), 0 }, /* RO */
2885 { "id_mmfr3_el1", CPENC(3,0,C0,C1,7), 0 }, /* RO */
bdfa8b95 2886 { "id_mmfr4_el1", CPENC(3,0,C0,C2,6), 0 }, /* RO */
49eec193
YZ
2887 { "id_isar0_el1", CPENC(3,0,C0,C2,0), 0 }, /* RO */
2888 { "id_isar1_el1", CPENC(3,0,C0,C2,1), 0 }, /* RO */
2889 { "id_isar2_el1", CPENC(3,0,C0,C2,2), 0 }, /* RO */
2890 { "id_isar3_el1", CPENC(3,0,C0,C2,3), 0 }, /* RO */
2891 { "id_isar4_el1", CPENC(3,0,C0,C2,4), 0 }, /* RO */
2892 { "id_isar5_el1", CPENC(3,0,C0,C2,5), 0 }, /* RO */
2893 { "mvfr0_el1", CPENC(3,0,C0,C3,0), 0 }, /* RO */
2894 { "mvfr1_el1", CPENC(3,0,C0,C3,1), 0 }, /* RO */
2895 { "mvfr2_el1", CPENC(3,0,C0,C3,2), 0 }, /* RO */
2896 { "ccsidr_el1", CPENC(3,1,C0,C0,0), 0 }, /* RO */
2897 { "id_aa64pfr0_el1", CPENC(3,0,C0,C4,0), 0 }, /* RO */
2898 { "id_aa64pfr1_el1", CPENC(3,0,C0,C4,1), 0 }, /* RO */
2899 { "id_aa64dfr0_el1", CPENC(3,0,C0,C5,0), 0 }, /* RO */
2900 { "id_aa64dfr1_el1", CPENC(3,0,C0,C5,1), 0 }, /* RO */
2901 { "id_aa64isar0_el1", CPENC(3,0,C0,C6,0), 0 }, /* RO */
2902 { "id_aa64isar1_el1", CPENC(3,0,C0,C6,1), 0 }, /* RO */
2903 { "id_aa64mmfr0_el1", CPENC(3,0,C0,C7,0), 0 }, /* RO */
2904 { "id_aa64mmfr1_el1", CPENC(3,0,C0,C7,1), 0 }, /* RO */
1a04d1a7 2905 { "id_aa64mmfr2_el1", CPENC (3, 0, C0, C7, 2), F_ARCHEXT }, /* RO */
49eec193
YZ
2906 { "id_aa64afr0_el1", CPENC(3,0,C0,C5,4), 0 }, /* RO */
2907 { "id_aa64afr1_el1", CPENC(3,0,C0,C5,5), 0 }, /* RO */
2908 { "clidr_el1", CPENC(3,1,C0,C0,1), 0 }, /* RO */
2909 { "csselr_el1", CPENC(3,2,C0,C0,0), 0 }, /* RO */
2910 { "vpidr_el2", CPENC(3,4,C0,C0,0), 0 },
2911 { "vmpidr_el2", CPENC(3,4,C0,C0,5), 0 },
2912 { "sctlr_el1", CPENC(3,0,C1,C0,0), 0 },
2913 { "sctlr_el2", CPENC(3,4,C1,C0,0), 0 },
2914 { "sctlr_el3", CPENC(3,6,C1,C0,0), 0 },
250aafa4 2915 { "sctlr_el12", CPENC (3, 5, C1, C0, 0), F_ARCHEXT },
49eec193
YZ
2916 { "actlr_el1", CPENC(3,0,C1,C0,1), 0 },
2917 { "actlr_el2", CPENC(3,4,C1,C0,1), 0 },
2918 { "actlr_el3", CPENC(3,6,C1,C0,1), 0 },
2919 { "cpacr_el1", CPENC(3,0,C1,C0,2), 0 },
250aafa4 2920 { "cpacr_el12", CPENC (3, 5, C1, C0, 2), F_ARCHEXT },
49eec193
YZ
2921 { "cptr_el2", CPENC(3,4,C1,C1,2), 0 },
2922 { "cptr_el3", CPENC(3,6,C1,C1,2), 0 },
2923 { "scr_el3", CPENC(3,6,C1,C1,0), 0 },
2924 { "hcr_el2", CPENC(3,4,C1,C1,0), 0 },
2925 { "mdcr_el2", CPENC(3,4,C1,C1,1), 0 },
2926 { "mdcr_el3", CPENC(3,6,C1,C3,1), 0 },
2927 { "hstr_el2", CPENC(3,4,C1,C1,3), 0 },
2928 { "hacr_el2", CPENC(3,4,C1,C1,7), 0 },
2929 { "ttbr0_el1", CPENC(3,0,C2,C0,0), 0 },
2930 { "ttbr1_el1", CPENC(3,0,C2,C0,1), 0 },
2931 { "ttbr0_el2", CPENC(3,4,C2,C0,0), 0 },
250aafa4 2932 { "ttbr1_el2", CPENC (3, 4, C2, C0, 1), F_ARCHEXT },
49eec193 2933 { "ttbr0_el3", CPENC(3,6,C2,C0,0), 0 },
250aafa4
MW
2934 { "ttbr0_el12", CPENC (3, 5, C2, C0, 0), F_ARCHEXT },
2935 { "ttbr1_el12", CPENC (3, 5, C2, C0, 1), F_ARCHEXT },
49eec193
YZ
2936 { "vttbr_el2", CPENC(3,4,C2,C1,0), 0 },
2937 { "tcr_el1", CPENC(3,0,C2,C0,2), 0 },
2938 { "tcr_el2", CPENC(3,4,C2,C0,2), 0 },
2939 { "tcr_el3", CPENC(3,6,C2,C0,2), 0 },
250aafa4 2940 { "tcr_el12", CPENC (3, 5, C2, C0, 2), F_ARCHEXT },
49eec193
YZ
2941 { "vtcr_el2", CPENC(3,4,C2,C1,2), 0 },
2942 { "afsr0_el1", CPENC(3,0,C5,C1,0), 0 },
2943 { "afsr1_el1", CPENC(3,0,C5,C1,1), 0 },
2944 { "afsr0_el2", CPENC(3,4,C5,C1,0), 0 },
2945 { "afsr1_el2", CPENC(3,4,C5,C1,1), 0 },
2946 { "afsr0_el3", CPENC(3,6,C5,C1,0), 0 },
250aafa4 2947 { "afsr0_el12", CPENC (3, 5, C5, C1, 0), F_ARCHEXT },
49eec193 2948 { "afsr1_el3", CPENC(3,6,C5,C1,1), 0 },
250aafa4 2949 { "afsr1_el12", CPENC (3, 5, C5, C1, 1), F_ARCHEXT },
49eec193
YZ
2950 { "esr_el1", CPENC(3,0,C5,C2,0), 0 },
2951 { "esr_el2", CPENC(3,4,C5,C2,0), 0 },
2952 { "esr_el3", CPENC(3,6,C5,C2,0), 0 },
250aafa4 2953 { "esr_el12", CPENC (3, 5, C5, C2, 0), F_ARCHEXT },
47f81142 2954 { "vsesr_el2", CPENC (3, 4, C5, C2, 3), F_ARCHEXT }, /* RO */
49eec193 2955 { "fpexc32_el2", CPENC(3,4,C5,C3,0), 0 },
47f81142
MW
2956 { "erridr_el1", CPENC (3, 0, C5, C3, 0), F_ARCHEXT }, /* RO */
2957 { "errselr_el1", CPENC (3, 0, C5, C3, 1), F_ARCHEXT },
2958 { "erxfr_el1", CPENC (3, 0, C5, C4, 0), F_ARCHEXT }, /* RO */
2959 { "erxctlr_el1", CPENC (3, 0, C5, C4, 1), F_ARCHEXT },
2960 { "erxstatus_el1", CPENC (3, 0, C5, C4, 2), F_ARCHEXT },
2961 { "erxaddr_el1", CPENC (3, 0, C5, C4, 3), F_ARCHEXT },
2962 { "erxmisc0_el1", CPENC (3, 0, C5, C5, 0), F_ARCHEXT },
2963 { "erxmisc1_el1", CPENC (3, 0, C5, C5, 1), F_ARCHEXT },
49eec193
YZ
2964 { "far_el1", CPENC(3,0,C6,C0,0), 0 },
2965 { "far_el2", CPENC(3,4,C6,C0,0), 0 },
2966 { "far_el3", CPENC(3,6,C6,C0,0), 0 },
250aafa4 2967 { "far_el12", CPENC (3, 5, C6, C0, 0), F_ARCHEXT },
49eec193
YZ
2968 { "hpfar_el2", CPENC(3,4,C6,C0,4), 0 },
2969 { "par_el1", CPENC(3,0,C7,C4,0), 0 },
2970 { "mair_el1", CPENC(3,0,C10,C2,0), 0 },
2971 { "mair_el2", CPENC(3,4,C10,C2,0), 0 },
2972 { "mair_el3", CPENC(3,6,C10,C2,0), 0 },
250aafa4 2973 { "mair_el12", CPENC (3, 5, C10, C2, 0), F_ARCHEXT },
49eec193
YZ
2974 { "amair_el1", CPENC(3,0,C10,C3,0), 0 },
2975 { "amair_el2", CPENC(3,4,C10,C3,0), 0 },
2976 { "amair_el3", CPENC(3,6,C10,C3,0), 0 },
250aafa4 2977 { "amair_el12", CPENC (3, 5, C10, C3, 0), F_ARCHEXT },
49eec193
YZ
2978 { "vbar_el1", CPENC(3,0,C12,C0,0), 0 },
2979 { "vbar_el2", CPENC(3,4,C12,C0,0), 0 },
2980 { "vbar_el3", CPENC(3,6,C12,C0,0), 0 },
250aafa4 2981 { "vbar_el12", CPENC (3, 5, C12, C0, 0), F_ARCHEXT },
49eec193
YZ
2982 { "rvbar_el1", CPENC(3,0,C12,C0,1), 0 }, /* RO */
2983 { "rvbar_el2", CPENC(3,4,C12,C0,1), 0 }, /* RO */
2984 { "rvbar_el3", CPENC(3,6,C12,C0,1), 0 }, /* RO */
2985 { "rmr_el1", CPENC(3,0,C12,C0,2), 0 },
2986 { "rmr_el2", CPENC(3,4,C12,C0,2), 0 },
2987 { "rmr_el3", CPENC(3,6,C12,C0,2), 0 },
2988 { "isr_el1", CPENC(3,0,C12,C1,0), 0 }, /* RO */
47f81142
MW
2989 { "disr_el1", CPENC (3, 0, C12, C1, 1), F_ARCHEXT },
2990 { "vdisr_el2", CPENC (3, 4, C12, C1, 1), F_ARCHEXT },
49eec193 2991 { "contextidr_el1", CPENC(3,0,C13,C0,1), 0 },
250aafa4
MW
2992 { "contextidr_el2", CPENC (3, 4, C13, C0, 1), F_ARCHEXT },
2993 { "contextidr_el12", CPENC (3, 5, C13, C0, 1), F_ARCHEXT },
49eec193
YZ
2994 { "tpidr_el0", CPENC(3,3,C13,C0,2), 0 },
2995 { "tpidrro_el0", CPENC(3,3,C13,C0,3), 0 }, /* RO */
2996 { "tpidr_el1", CPENC(3,0,C13,C0,4), 0 },
2997 { "tpidr_el2", CPENC(3,4,C13,C0,2), 0 },
2998 { "tpidr_el3", CPENC(3,6,C13,C0,2), 0 },
2999 { "teecr32_el1", CPENC(2,2,C0, C0,0), 0 }, /* See section 3.9.7.1 */
3000 { "cntfrq_el0", CPENC(3,3,C14,C0,0), 0 }, /* RO */
3001 { "cntpct_el0", CPENC(3,3,C14,C0,1), 0 }, /* RO */
3002 { "cntvct_el0", CPENC(3,3,C14,C0,2), 0 }, /* RO */
3003 { "cntvoff_el2", CPENC(3,4,C14,C0,3), 0 },
3004 { "cntkctl_el1", CPENC(3,0,C14,C1,0), 0 },
250aafa4 3005 { "cntkctl_el12", CPENC (3, 5, C14, C1, 0), F_ARCHEXT },
49eec193
YZ
3006 { "cnthctl_el2", CPENC(3,4,C14,C1,0), 0 },
3007 { "cntp_tval_el0", CPENC(3,3,C14,C2,0), 0 },
250aafa4 3008 { "cntp_tval_el02", CPENC (3, 5, C14, C2, 0), F_ARCHEXT },
49eec193 3009 { "cntp_ctl_el0", CPENC(3,3,C14,C2,1), 0 },
250aafa4 3010 { "cntp_ctl_el02", CPENC (3, 5, C14, C2, 1), F_ARCHEXT },
49eec193 3011 { "cntp_cval_el0", CPENC(3,3,C14,C2,2), 0 },
250aafa4 3012 { "cntp_cval_el02", CPENC (3, 5, C14, C2, 2), F_ARCHEXT },
49eec193 3013 { "cntv_tval_el0", CPENC(3,3,C14,C3,0), 0 },
250aafa4 3014 { "cntv_tval_el02", CPENC (3, 5, C14, C3, 0), F_ARCHEXT },
49eec193 3015 { "cntv_ctl_el0", CPENC(3,3,C14,C3,1), 0 },
250aafa4 3016 { "cntv_ctl_el02", CPENC (3, 5, C14, C3, 1), F_ARCHEXT },
49eec193 3017 { "cntv_cval_el0", CPENC(3,3,C14,C3,2), 0 },
250aafa4 3018 { "cntv_cval_el02", CPENC (3, 5, C14, C3, 2), F_ARCHEXT },
49eec193
YZ
3019 { "cnthp_tval_el2", CPENC(3,4,C14,C2,0), 0 },
3020 { "cnthp_ctl_el2", CPENC(3,4,C14,C2,1), 0 },
3021 { "cnthp_cval_el2", CPENC(3,4,C14,C2,2), 0 },
3022 { "cntps_tval_el1", CPENC(3,7,C14,C2,0), 0 },
3023 { "cntps_ctl_el1", CPENC(3,7,C14,C2,1), 0 },
3024 { "cntps_cval_el1", CPENC(3,7,C14,C2,2), 0 },
250aafa4
MW
3025 { "cnthv_tval_el2", CPENC (3, 4, C14, C3, 0), F_ARCHEXT },
3026 { "cnthv_ctl_el2", CPENC (3, 4, C14, C3, 1), F_ARCHEXT },
3027 { "cnthv_cval_el2", CPENC (3, 4, C14, C3, 2), F_ARCHEXT },
49eec193
YZ
3028 { "dacr32_el2", CPENC(3,4,C3,C0,0), 0 },
3029 { "ifsr32_el2", CPENC(3,4,C5,C0,1), 0 },
3030 { "teehbr32_el1", CPENC(2,2,C1,C0,0), 0 },
3031 { "sder32_el3", CPENC(3,6,C1,C1,1), 0 },
3032 { "mdscr_el1", CPENC(2,0,C0, C2, 2), 0 },
3033 { "mdccsr_el0", CPENC(2,3,C0, C1, 0), 0 }, /* r */
3034 { "mdccint_el1", CPENC(2,0,C0, C2, 0), 0 },
3035 { "dbgdtr_el0", CPENC(2,3,C0, C4, 0), 0 },
3036 { "dbgdtrrx_el0", CPENC(2,3,C0, C5, 0), 0 }, /* r */
3037 { "dbgdtrtx_el0", CPENC(2,3,C0, C5, 0), 0 }, /* w */
3038 { "osdtrrx_el1", CPENC(2,0,C0, C0, 2), 0 }, /* r */
3039 { "osdtrtx_el1", CPENC(2,0,C0, C3, 2), 0 }, /* w */
3040 { "oseccr_el1", CPENC(2,0,C0, C6, 2), 0 },
3041 { "dbgvcr32_el2", CPENC(2,4,C0, C7, 0), 0 },
3042 { "dbgbvr0_el1", CPENC(2,0,C0, C0, 4), 0 },
3043 { "dbgbvr1_el1", CPENC(2,0,C0, C1, 4), 0 },
3044 { "dbgbvr2_el1", CPENC(2,0,C0, C2, 4), 0 },
3045 { "dbgbvr3_el1", CPENC(2,0,C0, C3, 4), 0 },
3046 { "dbgbvr4_el1", CPENC(2,0,C0, C4, 4), 0 },
3047 { "dbgbvr5_el1", CPENC(2,0,C0, C5, 4), 0 },
3048 { "dbgbvr6_el1", CPENC(2,0,C0, C6, 4), 0 },
3049 { "dbgbvr7_el1", CPENC(2,0,C0, C7, 4), 0 },
3050 { "dbgbvr8_el1", CPENC(2,0,C0, C8, 4), 0 },
3051 { "dbgbvr9_el1", CPENC(2,0,C0, C9, 4), 0 },
3052 { "dbgbvr10_el1", CPENC(2,0,C0, C10,4), 0 },
3053 { "dbgbvr11_el1", CPENC(2,0,C0, C11,4), 0 },
3054 { "dbgbvr12_el1", CPENC(2,0,C0, C12,4), 0 },
3055 { "dbgbvr13_el1", CPENC(2,0,C0, C13,4), 0 },
3056 { "dbgbvr14_el1", CPENC(2,0,C0, C14,4), 0 },
3057 { "dbgbvr15_el1", CPENC(2,0,C0, C15,4), 0 },
3058 { "dbgbcr0_el1", CPENC(2,0,C0, C0, 5), 0 },
3059 { "dbgbcr1_el1", CPENC(2,0,C0, C1, 5), 0 },
3060 { "dbgbcr2_el1", CPENC(2,0,C0, C2, 5), 0 },
3061 { "dbgbcr3_el1", CPENC(2,0,C0, C3, 5), 0 },
3062 { "dbgbcr4_el1", CPENC(2,0,C0, C4, 5), 0 },
3063 { "dbgbcr5_el1", CPENC(2,0,C0, C5, 5), 0 },
3064 { "dbgbcr6_el1", CPENC(2,0,C0, C6, 5), 0 },
3065 { "dbgbcr7_el1", CPENC(2,0,C0, C7, 5), 0 },
3066 { "dbgbcr8_el1", CPENC(2,0,C0, C8, 5), 0 },
3067 { "dbgbcr9_el1", CPENC(2,0,C0, C9, 5), 0 },
3068 { "dbgbcr10_el1", CPENC(2,0,C0, C10,5), 0 },
3069 { "dbgbcr11_el1", CPENC(2,0,C0, C11,5), 0 },
3070 { "dbgbcr12_el1", CPENC(2,0,C0, C12,5), 0 },
3071 { "dbgbcr13_el1", CPENC(2,0,C0, C13,5), 0 },
3072 { "dbgbcr14_el1", CPENC(2,0,C0, C14,5), 0 },
3073 { "dbgbcr15_el1", CPENC(2,0,C0, C15,5), 0 },
3074 { "dbgwvr0_el1", CPENC(2,0,C0, C0, 6), 0 },
3075 { "dbgwvr1_el1", CPENC(2,0,C0, C1, 6), 0 },
3076 { "dbgwvr2_el1", CPENC(2,0,C0, C2, 6), 0 },
3077 { "dbgwvr3_el1", CPENC(2,0,C0, C3, 6), 0 },
3078 { "dbgwvr4_el1", CPENC(2,0,C0, C4, 6), 0 },
3079 { "dbgwvr5_el1", CPENC(2,0,C0, C5, 6), 0 },
3080 { "dbgwvr6_el1", CPENC(2,0,C0, C6, 6), 0 },
3081 { "dbgwvr7_el1", CPENC(2,0,C0, C7, 6), 0 },
3082 { "dbgwvr8_el1", CPENC(2,0,C0, C8, 6), 0 },
3083 { "dbgwvr9_el1", CPENC(2,0,C0, C9, 6), 0 },
3084 { "dbgwvr10_el1", CPENC(2,0,C0, C10,6), 0 },
3085 { "dbgwvr11_el1", CPENC(2,0,C0, C11,6), 0 },
3086 { "dbgwvr12_el1", CPENC(2,0,C0, C12,6), 0 },
3087 { "dbgwvr13_el1", CPENC(2,0,C0, C13,6), 0 },
3088 { "dbgwvr14_el1", CPENC(2,0,C0, C14,6), 0 },
3089 { "dbgwvr15_el1", CPENC(2,0,C0, C15,6), 0 },
3090 { "dbgwcr0_el1", CPENC(2,0,C0, C0, 7), 0 },
3091 { "dbgwcr1_el1", CPENC(2,0,C0, C1, 7), 0 },
3092 { "dbgwcr2_el1", CPENC(2,0,C0, C2, 7), 0 },
3093 { "dbgwcr3_el1", CPENC(2,0,C0, C3, 7), 0 },
3094 { "dbgwcr4_el1", CPENC(2,0,C0, C4, 7), 0 },
3095 { "dbgwcr5_el1", CPENC(2,0,C0, C5, 7), 0 },
3096 { "dbgwcr6_el1", CPENC(2,0,C0, C6, 7), 0 },
3097 { "dbgwcr7_el1", CPENC(2,0,C0, C7, 7), 0 },
3098 { "dbgwcr8_el1", CPENC(2,0,C0, C8, 7), 0 },
3099 { "dbgwcr9_el1", CPENC(2,0,C0, C9, 7), 0 },
3100 { "dbgwcr10_el1", CPENC(2,0,C0, C10,7), 0 },
3101 { "dbgwcr11_el1", CPENC(2,0,C0, C11,7), 0 },
3102 { "dbgwcr12_el1", CPENC(2,0,C0, C12,7), 0 },
3103 { "dbgwcr13_el1", CPENC(2,0,C0, C13,7), 0 },
3104 { "dbgwcr14_el1", CPENC(2,0,C0, C14,7), 0 },
3105 { "dbgwcr15_el1", CPENC(2,0,C0, C15,7), 0 },
3106 { "mdrar_el1", CPENC(2,0,C1, C0, 0), 0 }, /* r */
3107 { "oslar_el1", CPENC(2,0,C1, C0, 4), 0 }, /* w */
3108 { "oslsr_el1", CPENC(2,0,C1, C1, 4), 0 }, /* r */
3109 { "osdlr_el1", CPENC(2,0,C1, C3, 4), 0 },
3110 { "dbgprcr_el1", CPENC(2,0,C1, C4, 4), 0 },
3111 { "dbgclaimset_el1", CPENC(2,0,C7, C8, 6), 0 },
3112 { "dbgclaimclr_el1", CPENC(2,0,C7, C9, 6), 0 },
3113 { "dbgauthstatus_el1", CPENC(2,0,C7, C14,6), 0 }, /* r */
55c144e6
MW
3114 { "pmblimitr_el1", CPENC (3, 0, C9, C10, 0), F_ARCHEXT }, /* rw */
3115 { "pmbptr_el1", CPENC (3, 0, C9, C10, 1), F_ARCHEXT }, /* rw */
3116 { "pmbsr_el1", CPENC (3, 0, C9, C10, 3), F_ARCHEXT }, /* rw */
3117 { "pmbidr_el1", CPENC (3, 0, C9, C10, 7), F_ARCHEXT }, /* ro */
3118 { "pmscr_el1", CPENC (3, 0, C9, C9, 0), F_ARCHEXT }, /* rw */
3119 { "pmsicr_el1", CPENC (3, 0, C9, C9, 2), F_ARCHEXT }, /* rw */
3120 { "pmsirr_el1", CPENC (3, 0, C9, C9, 3), F_ARCHEXT }, /* rw */
3121 { "pmsfcr_el1", CPENC (3, 0, C9, C9, 4), F_ARCHEXT }, /* rw */
3122 { "pmsevfr_el1", CPENC (3, 0, C9, C9, 5), F_ARCHEXT }, /* rw */
3123 { "pmslatfr_el1", CPENC (3, 0, C9, C9, 6), F_ARCHEXT }, /* rw */
3124 { "pmsidr_el1", CPENC (3, 0, C9, C9, 7), F_ARCHEXT }, /* ro */
3125 { "pmscr_el2", CPENC (3, 4, C9, C9, 0), F_ARCHEXT }, /* rw */
3126 { "pmscr_el12", CPENC (3, 5, C9, C9, 0), F_ARCHEXT }, /* rw */
49eec193
YZ
3127 { "pmcr_el0", CPENC(3,3,C9,C12, 0), 0 },
3128 { "pmcntenset_el0", CPENC(3,3,C9,C12, 1), 0 },
3129 { "pmcntenclr_el0", CPENC(3,3,C9,C12, 2), 0 },
3130 { "pmovsclr_el0", CPENC(3,3,C9,C12, 3), 0 },
3131 { "pmswinc_el0", CPENC(3,3,C9,C12, 4), 0 }, /* w */
3132 { "pmselr_el0", CPENC(3,3,C9,C12, 5), 0 },
3133 { "pmceid0_el0", CPENC(3,3,C9,C12, 6), 0 }, /* r */
3134 { "pmceid1_el0", CPENC(3,3,C9,C12, 7), 0 }, /* r */
3135 { "pmccntr_el0", CPENC(3,3,C9,C13, 0), 0 },
3136 { "pmxevtyper_el0", CPENC(3,3,C9,C13, 1), 0 },
3137 { "pmxevcntr_el0", CPENC(3,3,C9,C13, 2), 0 },
3138 { "pmuserenr_el0", CPENC(3,3,C9,C14, 0), 0 },
3139 { "pmintenset_el1", CPENC(3,0,C9,C14, 1), 0 },
3140 { "pmintenclr_el1", CPENC(3,0,C9,C14, 2), 0 },
3141 { "pmovsset_el0", CPENC(3,3,C9,C14, 3), 0 },
3142 { "pmevcntr0_el0", CPENC(3,3,C14,C8, 0), 0 },
3143 { "pmevcntr1_el0", CPENC(3,3,C14,C8, 1), 0 },
3144 { "pmevcntr2_el0", CPENC(3,3,C14,C8, 2), 0 },
3145 { "pmevcntr3_el0", CPENC(3,3,C14,C8, 3), 0 },
3146 { "pmevcntr4_el0", CPENC(3,3,C14,C8, 4), 0 },
3147 { "pmevcntr5_el0", CPENC(3,3,C14,C8, 5), 0 },
3148 { "pmevcntr6_el0", CPENC(3,3,C14,C8, 6), 0 },
3149 { "pmevcntr7_el0", CPENC(3,3,C14,C8, 7), 0 },
3150 { "pmevcntr8_el0", CPENC(3,3,C14,C9, 0), 0 },
3151 { "pmevcntr9_el0", CPENC(3,3,C14,C9, 1), 0 },
3152 { "pmevcntr10_el0", CPENC(3,3,C14,C9, 2), 0 },
3153 { "pmevcntr11_el0", CPENC(3,3,C14,C9, 3), 0 },
3154 { "pmevcntr12_el0", CPENC(3,3,C14,C9, 4), 0 },
3155 { "pmevcntr13_el0", CPENC(3,3,C14,C9, 5), 0 },
3156 { "pmevcntr14_el0", CPENC(3,3,C14,C9, 6), 0 },
3157 { "pmevcntr15_el0", CPENC(3,3,C14,C9, 7), 0 },
3158 { "pmevcntr16_el0", CPENC(3,3,C14,C10,0), 0 },
3159 { "pmevcntr17_el0", CPENC(3,3,C14,C10,1), 0 },
3160 { "pmevcntr18_el0", CPENC(3,3,C14,C10,2), 0 },
3161 { "pmevcntr19_el0", CPENC(3,3,C14,C10,3), 0 },
3162 { "pmevcntr20_el0", CPENC(3,3,C14,C10,4), 0 },
3163 { "pmevcntr21_el0", CPENC(3,3,C14,C10,5), 0 },
3164 { "pmevcntr22_el0", CPENC(3,3,C14,C10,6), 0 },
3165 { "pmevcntr23_el0", CPENC(3,3,C14,C10,7), 0 },
3166 { "pmevcntr24_el0", CPENC(3,3,C14,C11,0), 0 },
3167 { "pmevcntr25_el0", CPENC(3,3,C14,C11,1), 0 },
3168 { "pmevcntr26_el0", CPENC(3,3,C14,C11,2), 0 },
3169 { "pmevcntr27_el0", CPENC(3,3,C14,C11,3), 0 },
3170 { "pmevcntr28_el0", CPENC(3,3,C14,C11,4), 0 },
3171 { "pmevcntr29_el0", CPENC(3,3,C14,C11,5), 0 },
3172 { "pmevcntr30_el0", CPENC(3,3,C14,C11,6), 0 },
3173 { "pmevtyper0_el0", CPENC(3,3,C14,C12,0), 0 },
3174 { "pmevtyper1_el0", CPENC(3,3,C14,C12,1), 0 },
3175 { "pmevtyper2_el0", CPENC(3,3,C14,C12,2), 0 },
3176 { "pmevtyper3_el0", CPENC(3,3,C14,C12,3), 0 },
3177 { "pmevtyper4_el0", CPENC(3,3,C14,C12,4), 0 },
3178 { "pmevtyper5_el0", CPENC(3,3,C14,C12,5), 0 },
3179 { "pmevtyper6_el0", CPENC(3,3,C14,C12,6), 0 },
3180 { "pmevtyper7_el0", CPENC(3,3,C14,C12,7), 0 },
3181 { "pmevtyper8_el0", CPENC(3,3,C14,C13,0), 0 },
3182 { "pmevtyper9_el0", CPENC(3,3,C14,C13,1), 0 },
3183 { "pmevtyper10_el0", CPENC(3,3,C14,C13,2), 0 },
3184 { "pmevtyper11_el0", CPENC(3,3,C14,C13,3), 0 },
3185 { "pmevtyper12_el0", CPENC(3,3,C14,C13,4), 0 },
3186 { "pmevtyper13_el0", CPENC(3,3,C14,C13,5), 0 },
3187 { "pmevtyper14_el0", CPENC(3,3,C14,C13,6), 0 },
3188 { "pmevtyper15_el0", CPENC(3,3,C14,C13,7), 0 },
3189 { "pmevtyper16_el0", CPENC(3,3,C14,C14,0), 0 },
3190 { "pmevtyper17_el0", CPENC(3,3,C14,C14,1), 0 },
3191 { "pmevtyper18_el0", CPENC(3,3,C14,C14,2), 0 },
3192 { "pmevtyper19_el0", CPENC(3,3,C14,C14,3), 0 },
3193 { "pmevtyper20_el0", CPENC(3,3,C14,C14,4), 0 },
3194 { "pmevtyper21_el0", CPENC(3,3,C14,C14,5), 0 },
3195 { "pmevtyper22_el0", CPENC(3,3,C14,C14,6), 0 },
3196 { "pmevtyper23_el0", CPENC(3,3,C14,C14,7), 0 },
3197 { "pmevtyper24_el0", CPENC(3,3,C14,C15,0), 0 },
3198 { "pmevtyper25_el0", CPENC(3,3,C14,C15,1), 0 },
3199 { "pmevtyper26_el0", CPENC(3,3,C14,C15,2), 0 },
3200 { "pmevtyper27_el0", CPENC(3,3,C14,C15,3), 0 },
3201 { "pmevtyper28_el0", CPENC(3,3,C14,C15,4), 0 },
3202 { "pmevtyper29_el0", CPENC(3,3,C14,C15,5), 0 },
3203 { "pmevtyper30_el0", CPENC(3,3,C14,C15,6), 0 },
3204 { "pmccfiltr_el0", CPENC(3,3,C14,C15,7), 0 },
3205 { 0, CPENC(0,0,0,0,0), 0 },
a06ea964
NC
3206};
3207
49eec193
YZ
3208bfd_boolean
3209aarch64_sys_reg_deprecated_p (const aarch64_sys_reg *reg)
3210{
3211 return (reg->flags & F_DEPRECATED) != 0;
3212}
3213
f21cce2c
MW
3214bfd_boolean
3215aarch64_sys_reg_supported_p (const aarch64_feature_set features,
3216 const aarch64_sys_reg *reg)
3217{
3218 if (!(reg->flags & F_ARCHEXT))
3219 return TRUE;
3220
3221 /* PAN. Values are from aarch64_sys_regs. */
3222 if (reg->value == CPEN_(0,C2,3)
3223 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_PAN))
3224 return FALSE;
3225
250aafa4
MW
3226 /* Virtualization host extensions: system registers. */
3227 if ((reg->value == CPENC (3, 4, C2, C0, 1)
3228 || reg->value == CPENC (3, 4, C13, C0, 1)
3229 || reg->value == CPENC (3, 4, C14, C3, 0)
3230 || reg->value == CPENC (3, 4, C14, C3, 1)
3231 || reg->value == CPENC (3, 4, C14, C3, 2))
3232 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_V8_1))
3233 return FALSE;
3234
3235 /* Virtualization host extensions: *_el12 names of *_el1 registers. */
3236 if ((reg->value == CPEN_ (5, C0, 0)
3237 || reg->value == CPEN_ (5, C0, 1)
3238 || reg->value == CPENC (3, 5, C1, C0, 0)
3239 || reg->value == CPENC (3, 5, C1, C0, 2)
3240 || reg->value == CPENC (3, 5, C2, C0, 0)
3241 || reg->value == CPENC (3, 5, C2, C0, 1)
3242 || reg->value == CPENC (3, 5, C2, C0, 2)
3243 || reg->value == CPENC (3, 5, C5, C1, 0)
3244 || reg->value == CPENC (3, 5, C5, C1, 1)
3245 || reg->value == CPENC (3, 5, C5, C2, 0)
3246 || reg->value == CPENC (3, 5, C6, C0, 0)
3247 || reg->value == CPENC (3, 5, C10, C2, 0)
3248 || reg->value == CPENC (3, 5, C10, C3, 0)
3249 || reg->value == CPENC (3, 5, C12, C0, 0)
3250 || reg->value == CPENC (3, 5, C13, C0, 1)
3251 || reg->value == CPENC (3, 5, C14, C1, 0))
3252 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_V8_1))
3253 return FALSE;
3254
3255 /* Virtualization host extensions: *_el02 names of *_el0 registers. */
3256 if ((reg->value == CPENC (3, 5, C14, C2, 0)
3257 || reg->value == CPENC (3, 5, C14, C2, 1)
3258 || reg->value == CPENC (3, 5, C14, C2, 2)
3259 || reg->value == CPENC (3, 5, C14, C3, 0)
3260 || reg->value == CPENC (3, 5, C14, C3, 1)
3261 || reg->value == CPENC (3, 5, C14, C3, 2))
3262 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_V8_1))
63511907 3263 return FALSE;
1a04d1a7
MW
3264
3265 /* ARMv8.2 features. */
6479e48e
MW
3266
3267 /* ID_AA64MMFR2_EL1. */
1a04d1a7
MW
3268 if (reg->value == CPENC (3, 0, C0, C7, 2)
3269 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_V8_2))
250aafa4
MW
3270 return FALSE;
3271
6479e48e
MW
3272 /* PSTATE.UAO. */
3273 if (reg->value == CPEN_ (0, C2, 4)
3274 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_V8_2))
3275 return FALSE;
3276
47f81142
MW
3277 /* RAS extension. */
3278
651657fa
MW
3279 /* ERRIDR_EL1, ERRSELR_EL1, ERXFR_EL1, ERXCTLR_EL1, ERXSTATUS_EL, ERXADDR_EL1,
3280 ERXMISC0_EL1 AND ERXMISC1_EL1. */
47f81142 3281 if ((reg->value == CPENC (3, 0, C5, C3, 0)
651657fa 3282 || reg->value == CPENC (3, 0, C5, C3, 1)
47f81142
MW
3283 || reg->value == CPENC (3, 0, C5, C3, 2)
3284 || reg->value == CPENC (3, 0, C5, C3, 3)
651657fa
MW
3285 || reg->value == CPENC (3, 0, C5, C4, 0)
3286 || reg->value == CPENC (3, 0, C5, C4, 1)
3287 || reg->value == CPENC (3, 0, C5, C4, 2)
3288 || reg->value == CPENC (3, 0, C5, C4, 3)
47f81142
MW
3289 || reg->value == CPENC (3, 0, C5, C5, 0)
3290 || reg->value == CPENC (3, 0, C5, C5, 1))
3291 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_RAS))
3292 return FALSE;
3293
3294 /* VSESR_EL2, DISR_EL1 and VDISR_EL2. */
3295 if ((reg->value == CPENC (3, 4, C5, C2, 3)
3296 || reg->value == CPENC (3, 0, C12, C1, 1)
3297 || reg->value == CPENC (3, 4, C12, C1, 1))
3298 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_RAS))
3299 return FALSE;
3300
55c144e6
MW
3301 /* Statistical Profiling extension. */
3302 if ((reg->value == CPENC (3, 0, C9, C10, 0)
3303 || reg->value == CPENC (3, 0, C9, C10, 1)
3304 || reg->value == CPENC (3, 0, C9, C10, 3)
3305 || reg->value == CPENC (3, 0, C9, C10, 7)
3306 || reg->value == CPENC (3, 0, C9, C9, 0)
3307 || reg->value == CPENC (3, 0, C9, C9, 2)
3308 || reg->value == CPENC (3, 0, C9, C9, 3)
3309 || reg->value == CPENC (3, 0, C9, C9, 4)
3310 || reg->value == CPENC (3, 0, C9, C9, 5)
3311 || reg->value == CPENC (3, 0, C9, C9, 6)
3312 || reg->value == CPENC (3, 0, C9, C9, 7)
3313 || reg->value == CPENC (3, 4, C9, C9, 0)
3314 || reg->value == CPENC (3, 5, C9, C9, 0))
3315 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_PROFILE))
3316 return FALSE;
3317
f21cce2c
MW
3318 return TRUE;
3319}
3320
87b8eed7 3321const aarch64_sys_reg aarch64_pstatefields [] =
a06ea964 3322{
87b8eed7
YZ
3323 { "spsel", 0x05, 0 },
3324 { "daifset", 0x1e, 0 },
3325 { "daifclr", 0x1f, 0 },
f21cce2c 3326 { "pan", 0x04, F_ARCHEXT },
6479e48e 3327 { "uao", 0x03, F_ARCHEXT },
87b8eed7 3328 { 0, CPENC(0,0,0,0,0), 0 },
a06ea964
NC
3329};
3330
f21cce2c
MW
3331bfd_boolean
3332aarch64_pstatefield_supported_p (const aarch64_feature_set features,
3333 const aarch64_sys_reg *reg)
3334{
3335 if (!(reg->flags & F_ARCHEXT))
3336 return TRUE;
3337
3338 /* PAN. Values are from aarch64_pstatefields. */
3339 if (reg->value == 0x04
3340 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_PAN))
3341 return FALSE;
3342
6479e48e
MW
3343 /* UAO. Values are from aarch64_pstatefields. */
3344 if (reg->value == 0x03
3345 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_V8_2))
3346 return FALSE;
3347
f21cce2c
MW
3348 return TRUE;
3349}
3350
a06ea964
NC
3351const aarch64_sys_ins_reg aarch64_sys_regs_ic[] =
3352{
3353 { "ialluis", CPENS(0,C7,C1,0), 0 },
3354 { "iallu", CPENS(0,C7,C5,0), 0 },
ea2deeec 3355 { "ivau", CPENS (3, C7, C5, 1), F_HASXT },
a06ea964
NC
3356 { 0, CPENS(0,0,0,0), 0 }
3357};
3358
3359const aarch64_sys_ins_reg aarch64_sys_regs_dc[] =
3360{
ea2deeec
MW
3361 { "zva", CPENS (3, C7, C4, 1), F_HASXT },
3362 { "ivac", CPENS (0, C7, C6, 1), F_HASXT },
3363 { "isw", CPENS (0, C7, C6, 2), F_HASXT },
3364 { "cvac", CPENS (3, C7, C10, 1), F_HASXT },
3365 { "csw", CPENS (0, C7, C10, 2), F_HASXT },
3366 { "cvau", CPENS (3, C7, C11, 1), F_HASXT },
d6bf7ce6 3367 { "cvap", CPENS (3, C7, C12, 1), F_HASXT | F_ARCHEXT },
ea2deeec
MW
3368 { "civac", CPENS (3, C7, C14, 1), F_HASXT },
3369 { "cisw", CPENS (0, C7, C14, 2), F_HASXT },
a06ea964
NC
3370 { 0, CPENS(0,0,0,0), 0 }
3371};
3372
3373const aarch64_sys_ins_reg aarch64_sys_regs_at[] =
3374{
ea2deeec
MW
3375 { "s1e1r", CPENS (0, C7, C8, 0), F_HASXT },
3376 { "s1e1w", CPENS (0, C7, C8, 1), F_HASXT },
3377 { "s1e0r", CPENS (0, C7, C8, 2), F_HASXT },
3378 { "s1e0w", CPENS (0, C7, C8, 3), F_HASXT },
3379 { "s12e1r", CPENS (4, C7, C8, 4), F_HASXT },
3380 { "s12e1w", CPENS (4, C7, C8, 5), F_HASXT },
3381 { "s12e0r", CPENS (4, C7, C8, 6), F_HASXT },
3382 { "s12e0w", CPENS (4, C7, C8, 7), F_HASXT },
3383 { "s1e2r", CPENS (4, C7, C8, 0), F_HASXT },
3384 { "s1e2w", CPENS (4, C7, C8, 1), F_HASXT },
3385 { "s1e3r", CPENS (6, C7, C8, 0), F_HASXT },
3386 { "s1e3w", CPENS (6, C7, C8, 1), F_HASXT },
22a5455c
MW
3387 { "s1e1rp", CPENS (0, C7, C9, 0), F_HASXT | F_ARCHEXT },
3388 { "s1e1wp", CPENS (0, C7, C9, 1), F_HASXT | F_ARCHEXT },
a06ea964
NC
3389 { 0, CPENS(0,0,0,0), 0 }
3390};
3391
3392const aarch64_sys_ins_reg aarch64_sys_regs_tlbi[] =
3393{
3394 { "vmalle1", CPENS(0,C8,C7,0), 0 },
ea2deeec
MW
3395 { "vae1", CPENS (0, C8, C7, 1), F_HASXT },
3396 { "aside1", CPENS (0, C8, C7, 2), F_HASXT },
3397 { "vaae1", CPENS (0, C8, C7, 3), F_HASXT },
a06ea964 3398 { "vmalle1is", CPENS(0,C8,C3,0), 0 },
ea2deeec
MW
3399 { "vae1is", CPENS (0, C8, C3, 1), F_HASXT },
3400 { "aside1is", CPENS (0, C8, C3, 2), F_HASXT },
3401 { "vaae1is", CPENS (0, C8, C3, 3), F_HASXT },
3402 { "ipas2e1is", CPENS (4, C8, C0, 1), F_HASXT },
3403 { "ipas2le1is",CPENS (4, C8, C0, 5), F_HASXT },
3404 { "ipas2e1", CPENS (4, C8, C4, 1), F_HASXT },
3405 { "ipas2le1", CPENS (4, C8, C4, 5), F_HASXT },
3406 { "vae2", CPENS (4, C8, C7, 1), F_HASXT },
3407 { "vae2is", CPENS (4, C8, C3, 1), F_HASXT },
a06ea964
NC
3408 { "vmalls12e1",CPENS(4,C8,C7,6), 0 },
3409 { "vmalls12e1is",CPENS(4,C8,C3,6), 0 },
ea2deeec
MW
3410 { "vae3", CPENS (6, C8, C7, 1), F_HASXT },
3411 { "vae3is", CPENS (6, C8, C3, 1), F_HASXT },
a06ea964
NC
3412 { "alle2", CPENS(4,C8,C7,0), 0 },
3413 { "alle2is", CPENS(4,C8,C3,0), 0 },
3414 { "alle1", CPENS(4,C8,C7,4), 0 },
3415 { "alle1is", CPENS(4,C8,C3,4), 0 },
3416 { "alle3", CPENS(6,C8,C7,0), 0 },
3417 { "alle3is", CPENS(6,C8,C3,0), 0 },
ea2deeec
MW
3418 { "vale1is", CPENS (0, C8, C3, 5), F_HASXT },
3419 { "vale2is", CPENS (4, C8, C3, 5), F_HASXT },
3420 { "vale3is", CPENS (6, C8, C3, 5), F_HASXT },
3421 { "vaale1is", CPENS (0, C8, C3, 7), F_HASXT },
3422 { "vale1", CPENS (0, C8, C7, 5), F_HASXT },
3423 { "vale2", CPENS (4, C8, C7, 5), F_HASXT },
3424 { "vale3", CPENS (6, C8, C7, 5), F_HASXT },
3425 { "vaale1", CPENS (0, C8, C7, 7), F_HASXT },
a06ea964
NC
3426 { 0, CPENS(0,0,0,0), 0 }
3427};
3428
ea2deeec
MW
3429bfd_boolean
3430aarch64_sys_ins_reg_has_xt (const aarch64_sys_ins_reg *sys_ins_reg)
3431{
3432 return (sys_ins_reg->flags & F_HASXT) != 0;
3433}
3434
d6bf7ce6
MW
3435extern bfd_boolean
3436aarch64_sys_ins_reg_supported_p (const aarch64_feature_set features,
3437 const aarch64_sys_ins_reg *reg)
3438{
3439 if (!(reg->flags & F_ARCHEXT))
3440 return TRUE;
3441
3442 /* DC CVAP. Values are from aarch64_sys_regs_dc. */
3443 if (reg->value == CPENS (3, C7, C12, 1)
3444 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_V8_2))
3445 return FALSE;
3446
63511907
MW
3447 /* AT S1E1RP, AT S1E1WP. Values are from aarch64_sys_regs_at. */
3448 if ((reg->value == CPENS (0, C7, C9, 0)
3449 || reg->value == CPENS (0, C7, C9, 1))
3450 && !AARCH64_CPU_HAS_FEATURE (features, AARCH64_FEATURE_V8_2))
3451 return FALSE;
3452
d6bf7ce6
MW
3453 return TRUE;
3454}
3455
a06ea964
NC
3456#undef C0
3457#undef C1
3458#undef C2
3459#undef C3
3460#undef C4
3461#undef C5
3462#undef C6
3463#undef C7
3464#undef C8
3465#undef C9
3466#undef C10
3467#undef C11
3468#undef C12
3469#undef C13
3470#undef C14
3471#undef C15
3472
4bd13cde
NC
3473#define BIT(INSN,BT) (((INSN) >> (BT)) & 1)
3474#define BITS(INSN,HI,LO) (((INSN) >> (LO)) & ((1 << (((HI) - (LO)) + 1)) - 1))
3475
20f55f38 3476static bfd_boolean
4bd13cde
NC
3477verify_ldpsw (const struct aarch64_opcode * opcode ATTRIBUTE_UNUSED,
3478 const aarch64_insn insn)
3479{
3480 int t = BITS (insn, 4, 0);
3481 int n = BITS (insn, 9, 5);
3482 int t2 = BITS (insn, 14, 10);
3483
3484 if (BIT (insn, 23))
3485 {
3486 /* Write back enabled. */
3487 if ((t == n || t2 == n) && n != 31)
3488 return FALSE;
3489 }
3490
3491 if (BIT (insn, 22))
3492 {
3493 /* Load */
3494 if (t == t2)
3495 return FALSE;
3496 }
3497
3498 return TRUE;
3499}
3500
a06ea964
NC
3501/* Include the opcode description table as well as the operand description
3502 table. */
20f55f38 3503#define VERIFIER(x) verify_##x
a06ea964 3504#include "aarch64-tbl.h"
This page took 0.87893 seconds and 4 git commands to generate.