1 //==- AArch64AsmParser.cpp - Parse AArch64 assembly to MCInst instructions -==//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "MCTargetDesc/AArch64AddressingModes.h"
10 #include "MCTargetDesc/AArch64MCExpr.h"
11 #include "MCTargetDesc/AArch64MCTargetDesc.h"
12 #include "MCTargetDesc/AArch64TargetStreamer.h"
13 #include "TargetInfo/AArch64TargetInfo.h"
14 #include "AArch64InstrInfo.h"
15 #include "Utils/AArch64BaseInfo.h"
16 #include "llvm/ADT/APFloat.h"
17 #include "llvm/ADT/APInt.h"
18 #include "llvm/ADT/ArrayRef.h"
19 #include "llvm/ADT/STLExtras.h"
20 #include "llvm/ADT/SmallVector.h"
21 #include "llvm/ADT/StringExtras.h"
22 #include "llvm/ADT/StringMap.h"
23 #include "llvm/ADT/StringRef.h"
24 #include "llvm/ADT/StringSwitch.h"
25 #include "llvm/ADT/Twine.h"
26 #include "llvm/MC/MCContext.h"
27 #include "llvm/MC/MCExpr.h"
28 #include "llvm/MC/MCInst.h"
29 #include "llvm/MC/MCLinkerOptimizationHint.h"
30 #include "llvm/MC/MCObjectFileInfo.h"
31 #include "llvm/MC/MCParser/MCAsmLexer.h"
32 #include "llvm/MC/MCParser/MCAsmParser.h"
33 #include "llvm/MC/MCParser/MCAsmParserExtension.h"
34 #include "llvm/MC/MCParser/MCParsedAsmOperand.h"
35 #include "llvm/MC/MCParser/MCTargetAsmParser.h"
36 #include "llvm/MC/MCRegisterInfo.h"
37 #include "llvm/MC/MCStreamer.h"
38 #include "llvm/MC/MCSubtargetInfo.h"
39 #include "llvm/MC/MCSymbol.h"
40 #include "llvm/MC/MCTargetOptions.h"
41 #include "llvm/MC/SubtargetFeature.h"
42 #include "llvm/MC/MCValue.h"
43 #include "llvm/Support/Casting.h"
44 #include "llvm/Support/Compiler.h"
45 #include "llvm/Support/ErrorHandling.h"
46 #include "llvm/Support/MathExtras.h"
47 #include "llvm/Support/SMLoc.h"
48 #include "llvm/Support/TargetParser.h"
49 #include "llvm/Support/TargetRegistry.h"
50 #include "llvm/Support/raw_ostream.h"
51 #include <cassert>
52 #include <cctype>
53 #include <cstdint>
54 #include <cstdio>
55 #include <string>
56 #include <tuple>
57 #include <utility>
58 #include <vector>
59 
60 using namespace llvm;
61 
62 namespace {
63 
64 enum class RegKind {
65   Scalar,
66   NeonVector,
67   SVEDataVector,
68   SVEPredicateVector
69 };
70 
71 enum RegConstraintEqualityTy {
72   EqualsReg,
73   EqualsSuperReg,
74   EqualsSubReg
75 };
76 
77 class AArch64AsmParser : public MCTargetAsmParser {
78 private:
79   StringRef Mnemonic; ///< Instruction mnemonic.
80 
81   // Map of register aliases registers via the .req directive.
82   StringMap<std::pair<RegKind, unsigned>> RegisterReqs;
83 
84   class PrefixInfo {
85   public:
86     static PrefixInfo CreateFromInst(const MCInst &Inst, uint64_t TSFlags) {
87       PrefixInfo Prefix;
88       switch (Inst.getOpcode()) {
89       case AArch64::MOVPRFX_ZZ:
90         Prefix.Active = true;
91         Prefix.Dst = Inst.getOperand(0).getReg();
92         break;
93       case AArch64::MOVPRFX_ZPmZ_B:
94       case AArch64::MOVPRFX_ZPmZ_H:
95       case AArch64::MOVPRFX_ZPmZ_S:
96       case AArch64::MOVPRFX_ZPmZ_D:
97         Prefix.Active = true;
98         Prefix.Predicated = true;
99         Prefix.ElementSize = TSFlags & AArch64::ElementSizeMask;
100         assert(Prefix.ElementSize != AArch64::ElementSizeNone &&
101                "No destructive element size set for movprfx");
102         Prefix.Dst = Inst.getOperand(0).getReg();
103         Prefix.Pg = Inst.getOperand(2).getReg();
104         break;
105       case AArch64::MOVPRFX_ZPzZ_B:
106       case AArch64::MOVPRFX_ZPzZ_H:
107       case AArch64::MOVPRFX_ZPzZ_S:
108       case AArch64::MOVPRFX_ZPzZ_D:
109         Prefix.Active = true;
110         Prefix.Predicated = true;
111         Prefix.ElementSize = TSFlags & AArch64::ElementSizeMask;
112         assert(Prefix.ElementSize != AArch64::ElementSizeNone &&
113                "No destructive element size set for movprfx");
114         Prefix.Dst = Inst.getOperand(0).getReg();
115         Prefix.Pg = Inst.getOperand(1).getReg();
116         break;
117       default:
118         break;
119       }
120 
121       return Prefix;
122     }
123 
124     PrefixInfo() : Active(false), Predicated(false) {}
125     bool isActive() const { return Active; }
126     bool isPredicated() const { return Predicated; }
127     unsigned getElementSize() const {
128       assert(Predicated);
129       return ElementSize;
130     }
131     unsigned getDstReg() const { return Dst; }
132     unsigned getPgReg() const {
133       assert(Predicated);
134       return Pg;
135     }
136 
137   private:
138     bool Active;
139     bool Predicated;
140     unsigned ElementSize;
141     unsigned Dst;
142     unsigned Pg;
143   } NextPrefix;
144 
145   AArch64TargetStreamer &getTargetStreamer() {
146     MCTargetStreamer &TS = *getParser().getStreamer().getTargetStreamer();
147     return static_cast<AArch64TargetStreamer &>(TS);
148   }
149 
150   SMLoc getLoc() const { return getParser().getTok().getLoc(); }
151 
152   bool parseSysAlias(StringRef Name, SMLoc NameLoc, OperandVector &Operands);
153   void createSysAlias(uint16_t Encoding, OperandVector &Operands, SMLoc S);
154   AArch64CC::CondCode parseCondCodeString(StringRef Cond);
155   bool parseCondCode(OperandVector &Operands, bool invertCondCode);
156   unsigned matchRegisterNameAlias(StringRef Name, RegKind Kind);
157   bool parseRegister(OperandVector &Operands);
158   bool parseSymbolicImmVal(const MCExpr *&ImmVal);
159   bool parseNeonVectorList(OperandVector &Operands);
160   bool parseOptionalMulOperand(OperandVector &Operands);
161   bool parseOperand(OperandVector &Operands, bool isCondCode,
162                     bool invertCondCode);
163 
164   bool showMatchError(SMLoc Loc, unsigned ErrCode, uint64_t ErrorInfo,
165                       OperandVector &Operands);
166 
167   bool parseDirectiveArch(SMLoc L);
168   bool parseDirectiveArchExtension(SMLoc L);
169   bool parseDirectiveCPU(SMLoc L);
170   bool parseDirectiveInst(SMLoc L);
171 
172   bool parseDirectiveTLSDescCall(SMLoc L);
173 
174   bool parseDirectiveLOH(StringRef LOH, SMLoc L);
175   bool parseDirectiveLtorg(SMLoc L);
176 
177   bool parseDirectiveReq(StringRef Name, SMLoc L);
178   bool parseDirectiveUnreq(SMLoc L);
179   bool parseDirectiveCFINegateRAState();
180   bool parseDirectiveCFIBKeyFrame();
181 
182   bool validateInstruction(MCInst &Inst, SMLoc &IDLoc,
183                            SmallVectorImpl<SMLoc> &Loc);
184   bool MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
185                                OperandVector &Operands, MCStreamer &Out,
186                                uint64_t &ErrorInfo,
187                                bool MatchingInlineAsm) override;
188 /// @name Auto-generated Match Functions
189 /// {
190 
191 #define GET_ASSEMBLER_HEADER
192 #include "AArch64GenAsmMatcher.inc"
193 
194   /// }
195 
196   OperandMatchResultTy tryParseScalarRegister(unsigned &Reg);
197   OperandMatchResultTy tryParseVectorRegister(unsigned &Reg, StringRef &Kind,
198                                               RegKind MatchKind);
199   OperandMatchResultTy tryParseOptionalShiftExtend(OperandVector &Operands);
200   OperandMatchResultTy tryParseBarrierOperand(OperandVector &Operands);
201   OperandMatchResultTy tryParseMRSSystemRegister(OperandVector &Operands);
202   OperandMatchResultTy tryParseSysReg(OperandVector &Operands);
203   OperandMatchResultTy tryParseSysCROperand(OperandVector &Operands);
204   template <bool IsSVEPrefetch = false>
205   OperandMatchResultTy tryParsePrefetch(OperandVector &Operands);
206   OperandMatchResultTy tryParsePSBHint(OperandVector &Operands);
207   OperandMatchResultTy tryParseBTIHint(OperandVector &Operands);
208   OperandMatchResultTy tryParseAdrpLabel(OperandVector &Operands);
209   OperandMatchResultTy tryParseAdrLabel(OperandVector &Operands);
210   template<bool AddFPZeroAsLiteral>
211   OperandMatchResultTy tryParseFPImm(OperandVector &Operands);
212   OperandMatchResultTy tryParseImmWithOptionalShift(OperandVector &Operands);
213   OperandMatchResultTy tryParseGPR64sp0Operand(OperandVector &Operands);
214   bool tryParseNeonVectorRegister(OperandVector &Operands);
215   OperandMatchResultTy tryParseVectorIndex(OperandVector &Operands);
216   OperandMatchResultTy tryParseGPRSeqPair(OperandVector &Operands);
217   template <bool ParseShiftExtend,
218             RegConstraintEqualityTy EqTy = RegConstraintEqualityTy::EqualsReg>
219   OperandMatchResultTy tryParseGPROperand(OperandVector &Operands);
220   template <bool ParseShiftExtend, bool ParseSuffix>
221   OperandMatchResultTy tryParseSVEDataVector(OperandVector &Operands);
222   OperandMatchResultTy tryParseSVEPredicateVector(OperandVector &Operands);
223   template <RegKind VectorKind>
224   OperandMatchResultTy tryParseVectorList(OperandVector &Operands,
225                                           bool ExpectMatch = false);
226   OperandMatchResultTy tryParseSVEPattern(OperandVector &Operands);
227 
228 public:
229   enum AArch64MatchResultTy {
230     Match_InvalidSuffix = FIRST_TARGET_MATCH_RESULT_TY,
231 #define GET_OPERAND_DIAGNOSTIC_TYPES
232 #include "AArch64GenAsmMatcher.inc"
233   };
234   bool IsILP32;
235 
236   AArch64AsmParser(const MCSubtargetInfo &STI, MCAsmParser &Parser,
237                    const MCInstrInfo &MII, const MCTargetOptions &Options)
238     : MCTargetAsmParser(Options, STI, MII) {
239     IsILP32 = Options.getABIName() == "ilp32";
240     MCAsmParserExtension::Initialize(Parser);
241     MCStreamer &S = getParser().getStreamer();
242     if (S.getTargetStreamer() == nullptr)
243       new AArch64TargetStreamer(S);
244 
245     // Alias .hword/.word/.[dx]word to the target-independent
246     // .2byte/.4byte/.8byte directives as they have the same form and
247     // semantics:
248     ///  ::= (.hword | .word | .dword | .xword ) [ expression (, expression)* ]
249     Parser.addAliasForDirective(".hword", ".2byte");
250     Parser.addAliasForDirective(".word", ".4byte");
251     Parser.addAliasForDirective(".dword", ".8byte");
252     Parser.addAliasForDirective(".xword", ".8byte");
253 
254     // Initialize the set of available features.
255     setAvailableFeatures(ComputeAvailableFeatures(getSTI().getFeatureBits()));
256   }
257 
258   bool regsEqual(const MCParsedAsmOperand &Op1,
259                  const MCParsedAsmOperand &Op2) const override;
260   bool ParseInstruction(ParseInstructionInfo &Info, StringRef Name,
261                         SMLoc NameLoc, OperandVector &Operands) override;
262   bool ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc) override;
263   OperandMatchResultTy tryParseRegister(unsigned &RegNo, SMLoc &StartLoc,
264                                         SMLoc &EndLoc) override;
265   bool ParseDirective(AsmToken DirectiveID) override;
266   unsigned validateTargetOperandClass(MCParsedAsmOperand &Op,
267                                       unsigned Kind) override;
268 
269   static bool classifySymbolRef(const MCExpr *Expr,
270                                 AArch64MCExpr::VariantKind &ELFRefKind,
271                                 MCSymbolRefExpr::VariantKind &DarwinRefKind,
272                                 int64_t &Addend);
273 };
274 
275 /// AArch64Operand - Instances of this class represent a parsed AArch64 machine
276 /// instruction.
277 class AArch64Operand : public MCParsedAsmOperand {
278 private:
279   enum KindTy {
280     k_Immediate,
281     k_ShiftedImm,
282     k_CondCode,
283     k_Register,
284     k_VectorList,
285     k_VectorIndex,
286     k_Token,
287     k_SysReg,
288     k_SysCR,
289     k_Prefetch,
290     k_ShiftExtend,
291     k_FPImm,
292     k_Barrier,
293     k_PSBHint,
294     k_BTIHint,
295   } Kind;
296 
297   SMLoc StartLoc, EndLoc;
298 
299   struct TokOp {
300     const char *Data;
301     unsigned Length;
302     bool IsSuffix; // Is the operand actually a suffix on the mnemonic.
303   };
304 
305   // Separate shift/extend operand.
306   struct ShiftExtendOp {
307     AArch64_AM::ShiftExtendType Type;
308     unsigned Amount;
309     bool HasExplicitAmount;
310   };
311 
312   struct RegOp {
313     unsigned RegNum;
314     RegKind Kind;
315     int ElementWidth;
316 
317     // The register may be allowed as a different register class,
318     // e.g. for GPR64as32 or GPR32as64.
319     RegConstraintEqualityTy EqualityTy;
320 
321     // In some cases the shift/extend needs to be explicitly parsed together
322     // with the register, rather than as a separate operand. This is needed
323     // for addressing modes where the instruction as a whole dictates the
324     // scaling/extend, rather than specific bits in the instruction.
325     // By parsing them as a single operand, we avoid the need to pass an
326     // extra operand in all CodeGen patterns (because all operands need to
327     // have an associated value), and we avoid the need to update TableGen to
328     // accept operands that have no associated bits in the instruction.
329     //
330     // An added benefit of parsing them together is that the assembler
331     // can give a sensible diagnostic if the scaling is not correct.
332     //
333     // The default is 'lsl #0' (HasExplicitAmount = false) if no
334     // ShiftExtend is specified.
335     ShiftExtendOp ShiftExtend;
336   };
337 
338   struct VectorListOp {
339     unsigned RegNum;
340     unsigned Count;
341     unsigned NumElements;
342     unsigned ElementWidth;
343     RegKind  RegisterKind;
344   };
345 
346   struct VectorIndexOp {
347     unsigned Val;
348   };
349 
350   struct ImmOp {
351     const MCExpr *Val;
352   };
353 
354   struct ShiftedImmOp {
355     const MCExpr *Val;
356     unsigned ShiftAmount;
357   };
358 
359   struct CondCodeOp {
360     AArch64CC::CondCode Code;
361   };
362 
363   struct FPImmOp {
364     uint64_t Val; // APFloat value bitcasted to uint64_t.
365     bool IsExact; // describes whether parsed value was exact.
366   };
367 
368   struct BarrierOp {
369     const char *Data;
370     unsigned Length;
371     unsigned Val; // Not the enum since not all values have names.
372   };
373 
374   struct SysRegOp {
375     const char *Data;
376     unsigned Length;
377     uint32_t MRSReg;
378     uint32_t MSRReg;
379     uint32_t PStateField;
380   };
381 
382   struct SysCRImmOp {
383     unsigned Val;
384   };
385 
386   struct PrefetchOp {
387     const char *Data;
388     unsigned Length;
389     unsigned Val;
390   };
391 
392   struct PSBHintOp {
393     const char *Data;
394     unsigned Length;
395     unsigned Val;
396   };
397 
398   struct BTIHintOp {
399     const char *Data;
400     unsigned Length;
401     unsigned Val;
402   };
403 
404   struct ExtendOp {
405     unsigned Val;
406   };
407 
408   union {
409     struct TokOp Tok;
410     struct RegOp Reg;
411     struct VectorListOp VectorList;
412     struct VectorIndexOp VectorIndex;
413     struct ImmOp Imm;
414     struct ShiftedImmOp ShiftedImm;
415     struct CondCodeOp CondCode;
416     struct FPImmOp FPImm;
417     struct BarrierOp Barrier;
418     struct SysRegOp SysReg;
419     struct SysCRImmOp SysCRImm;
420     struct PrefetchOp Prefetch;
421     struct PSBHintOp PSBHint;
422     struct BTIHintOp BTIHint;
423     struct ShiftExtendOp ShiftExtend;
424   };
425 
426   // Keep the MCContext around as the MCExprs may need manipulated during
427   // the add<>Operands() calls.
428   MCContext &Ctx;
429 
430 public:
431   AArch64Operand(KindTy K, MCContext &Ctx) : Kind(K), Ctx(Ctx) {}
432 
433   AArch64Operand(const AArch64Operand &o) : MCParsedAsmOperand(), Ctx(o.Ctx) {
434     Kind = o.Kind;
435     StartLoc = o.StartLoc;
436     EndLoc = o.EndLoc;
437     switch (Kind) {
438     case k_Token:
439       Tok = o.Tok;
440       break;
441     case k_Immediate:
442       Imm = o.Imm;
443       break;
444     case k_ShiftedImm:
445       ShiftedImm = o.ShiftedImm;
446       break;
447     case k_CondCode:
448       CondCode = o.CondCode;
449       break;
450     case k_FPImm:
451       FPImm = o.FPImm;
452       break;
453     case k_Barrier:
454       Barrier = o.Barrier;
455       break;
456     case k_Register:
457       Reg = o.Reg;
458       break;
459     case k_VectorList:
460       VectorList = o.VectorList;
461       break;
462     case k_VectorIndex:
463       VectorIndex = o.VectorIndex;
464       break;
465     case k_SysReg:
466       SysReg = o.SysReg;
467       break;
468     case k_SysCR:
469       SysCRImm = o.SysCRImm;
470       break;
471     case k_Prefetch:
472       Prefetch = o.Prefetch;
473       break;
474     case k_PSBHint:
475       PSBHint = o.PSBHint;
476       break;
477     case k_BTIHint:
478       BTIHint = o.BTIHint;
479       break;
480     case k_ShiftExtend:
481       ShiftExtend = o.ShiftExtend;
482       break;
483     }
484   }
485 
486   /// getStartLoc - Get the location of the first token of this operand.
487   SMLoc getStartLoc() const override { return StartLoc; }
488   /// getEndLoc - Get the location of the last token of this operand.
489   SMLoc getEndLoc() const override { return EndLoc; }
490 
491   StringRef getToken() const {
492     assert(Kind == k_Token && "Invalid access!");
493     return StringRef(Tok.Data, Tok.Length);
494   }
495 
496   bool isTokenSuffix() const {
497     assert(Kind == k_Token && "Invalid access!");
498     return Tok.IsSuffix;
499   }
500 
501   const MCExpr *getImm() const {
502     assert(Kind == k_Immediate && "Invalid access!");
503     return Imm.Val;
504   }
505 
506   const MCExpr *getShiftedImmVal() const {
507     assert(Kind == k_ShiftedImm && "Invalid access!");
508     return ShiftedImm.Val;
509   }
510 
511   unsigned getShiftedImmShift() const {
512     assert(Kind == k_ShiftedImm && "Invalid access!");
513     return ShiftedImm.ShiftAmount;
514   }
515 
516   AArch64CC::CondCode getCondCode() const {
517     assert(Kind == k_CondCode && "Invalid access!");
518     return CondCode.Code;
519   }
520 
521   APFloat getFPImm() const {
522     assert (Kind == k_FPImm && "Invalid access!");
523     return APFloat(APFloat::IEEEdouble(), APInt(64, FPImm.Val, true));
524   }
525 
526   bool getFPImmIsExact() const {
527     assert (Kind == k_FPImm && "Invalid access!");
528     return FPImm.IsExact;
529   }
530 
531   unsigned getBarrier() const {
532     assert(Kind == k_Barrier && "Invalid access!");
533     return Barrier.Val;
534   }
535 
536   StringRef getBarrierName() const {
537     assert(Kind == k_Barrier && "Invalid access!");
538     return StringRef(Barrier.Data, Barrier.Length);
539   }
540 
541   unsigned getReg() const override {
542     assert(Kind == k_Register && "Invalid access!");
543     return Reg.RegNum;
544   }
545 
546   RegConstraintEqualityTy getRegEqualityTy() const {
547     assert(Kind == k_Register && "Invalid access!");
548     return Reg.EqualityTy;
549   }
550 
551   unsigned getVectorListStart() const {
552     assert(Kind == k_VectorList && "Invalid access!");
553     return VectorList.RegNum;
554   }
555 
556   unsigned getVectorListCount() const {
557     assert(Kind == k_VectorList && "Invalid access!");
558     return VectorList.Count;
559   }
560 
561   unsigned getVectorIndex() const {
562     assert(Kind == k_VectorIndex && "Invalid access!");
563     return VectorIndex.Val;
564   }
565 
566   StringRef getSysReg() const {
567     assert(Kind == k_SysReg && "Invalid access!");
568     return StringRef(SysReg.Data, SysReg.Length);
569   }
570 
571   unsigned getSysCR() const {
572     assert(Kind == k_SysCR && "Invalid access!");
573     return SysCRImm.Val;
574   }
575 
576   unsigned getPrefetch() const {
577     assert(Kind == k_Prefetch && "Invalid access!");
578     return Prefetch.Val;
579   }
580 
581   unsigned getPSBHint() const {
582     assert(Kind == k_PSBHint && "Invalid access!");
583     return PSBHint.Val;
584   }
585 
586   StringRef getPSBHintName() const {
587     assert(Kind == k_PSBHint && "Invalid access!");
588     return StringRef(PSBHint.Data, PSBHint.Length);
589   }
590 
591   unsigned getBTIHint() const {
592     assert(Kind == k_BTIHint && "Invalid access!");
593     return BTIHint.Val;
594   }
595 
596   StringRef getBTIHintName() const {
597     assert(Kind == k_BTIHint && "Invalid access!");
598     return StringRef(BTIHint.Data, BTIHint.Length);
599   }
600 
601   StringRef getPrefetchName() const {
602     assert(Kind == k_Prefetch && "Invalid access!");
603     return StringRef(Prefetch.Data, Prefetch.Length);
604   }
605 
606   AArch64_AM::ShiftExtendType getShiftExtendType() const {
607     if (Kind == k_ShiftExtend)
608       return ShiftExtend.Type;
609     if (Kind == k_Register)
610       return Reg.ShiftExtend.Type;
611     llvm_unreachable("Invalid access!");
612   }
613 
614   unsigned getShiftExtendAmount() const {
615     if (Kind == k_ShiftExtend)
616       return ShiftExtend.Amount;
617     if (Kind == k_Register)
618       return Reg.ShiftExtend.Amount;
619     llvm_unreachable("Invalid access!");
620   }
621 
622   bool hasShiftExtendAmount() const {
623     if (Kind == k_ShiftExtend)
624       return ShiftExtend.HasExplicitAmount;
625     if (Kind == k_Register)
626       return Reg.ShiftExtend.HasExplicitAmount;
627     llvm_unreachable("Invalid access!");
628   }
629 
630   bool isImm() const override { return Kind == k_Immediate; }
631   bool isMem() const override { return false; }
632 
633   bool isUImm6() const {
634     if (!isImm())
635       return false;
636     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
637     if (!MCE)
638       return false;
639     int64_t Val = MCE->getValue();
640     return (Val >= 0 && Val < 64);
641   }
642 
643   template <int Width> bool isSImm() const { return isSImmScaled<Width, 1>(); }
644 
645   template <int Bits, int Scale> DiagnosticPredicate isSImmScaled() const {
646     return isImmScaled<Bits, Scale>(true);
647   }
648 
649   template <int Bits, int Scale> DiagnosticPredicate isUImmScaled() const {
650     return isImmScaled<Bits, Scale>(false);
651   }
652 
653   template <int Bits, int Scale>
654   DiagnosticPredicate isImmScaled(bool Signed) const {
655     if (!isImm())
656       return DiagnosticPredicateTy::NoMatch;
657 
658     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
659     if (!MCE)
660       return DiagnosticPredicateTy::NoMatch;
661 
662     int64_t MinVal, MaxVal;
663     if (Signed) {
664       int64_t Shift = Bits - 1;
665       MinVal = (int64_t(1) << Shift) * -Scale;
666       MaxVal = ((int64_t(1) << Shift) - 1) * Scale;
667     } else {
668       MinVal = 0;
669       MaxVal = ((int64_t(1) << Bits) - 1) * Scale;
670     }
671 
672     int64_t Val = MCE->getValue();
673     if (Val >= MinVal && Val <= MaxVal && (Val % Scale) == 0)
674       return DiagnosticPredicateTy::Match;
675 
676     return DiagnosticPredicateTy::NearMatch;
677   }
678 
679   DiagnosticPredicate isSVEPattern() const {
680     if (!isImm())
681       return DiagnosticPredicateTy::NoMatch;
682     auto *MCE = dyn_cast<MCConstantExpr>(getImm());
683     if (!MCE)
684       return DiagnosticPredicateTy::NoMatch;
685     int64_t Val = MCE->getValue();
686     if (Val >= 0 && Val < 32)
687       return DiagnosticPredicateTy::Match;
688     return DiagnosticPredicateTy::NearMatch;
689   }
690 
691   bool isSymbolicUImm12Offset(const MCExpr *Expr) const {
692     AArch64MCExpr::VariantKind ELFRefKind;
693     MCSymbolRefExpr::VariantKind DarwinRefKind;
694     int64_t Addend;
695     if (!AArch64AsmParser::classifySymbolRef(Expr, ELFRefKind, DarwinRefKind,
696                                            Addend)) {
697       // If we don't understand the expression, assume the best and
698       // let the fixup and relocation code deal with it.
699       return true;
700     }
701 
702     if (DarwinRefKind == MCSymbolRefExpr::VK_PAGEOFF ||
703         ELFRefKind == AArch64MCExpr::VK_LO12 ||
704         ELFRefKind == AArch64MCExpr::VK_GOT_LO12 ||
705         ELFRefKind == AArch64MCExpr::VK_DTPREL_LO12 ||
706         ELFRefKind == AArch64MCExpr::VK_DTPREL_LO12_NC ||
707         ELFRefKind == AArch64MCExpr::VK_TPREL_LO12 ||
708         ELFRefKind == AArch64MCExpr::VK_TPREL_LO12_NC ||
709         ELFRefKind == AArch64MCExpr::VK_GOTTPREL_LO12_NC ||
710         ELFRefKind == AArch64MCExpr::VK_TLSDESC_LO12 ||
711         ELFRefKind == AArch64MCExpr::VK_SECREL_LO12 ||
712         ELFRefKind == AArch64MCExpr::VK_SECREL_HI12) {
713       // Note that we don't range-check the addend. It's adjusted modulo page
714       // size when converted, so there is no "out of range" condition when using
715       // @pageoff.
716       return true;
717     } else if (DarwinRefKind == MCSymbolRefExpr::VK_GOTPAGEOFF ||
718                DarwinRefKind == MCSymbolRefExpr::VK_TLVPPAGEOFF) {
719       // @gotpageoff/@tlvppageoff can only be used directly, not with an addend.
720       return Addend == 0;
721     }
722 
723     return false;
724   }
725 
726   template <int Scale> bool isUImm12Offset() const {
727     if (!isImm())
728       return false;
729 
730     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
731     if (!MCE)
732       return isSymbolicUImm12Offset(getImm());
733 
734     int64_t Val = MCE->getValue();
735     return (Val % Scale) == 0 && Val >= 0 && (Val / Scale) < 0x1000;
736   }
737 
738   template <int N, int M>
739   bool isImmInRange() const {
740     if (!isImm())
741       return false;
742     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
743     if (!MCE)
744       return false;
745     int64_t Val = MCE->getValue();
746     return (Val >= N && Val <= M);
747   }
748 
749   // NOTE: Also used for isLogicalImmNot as anything that can be represented as
750   // a logical immediate can always be represented when inverted.
751   template <typename T>
752   bool isLogicalImm() const {
753     if (!isImm())
754       return false;
755     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
756     if (!MCE)
757       return false;
758 
759     int64_t Val = MCE->getValue();
760     // Avoid left shift by 64 directly.
761     uint64_t Upper = UINT64_C(-1) << (sizeof(T) * 4) << (sizeof(T) * 4);
762     // Allow all-0 or all-1 in top bits to permit bitwise NOT.
763     if ((Val & Upper) && (Val & Upper) != Upper)
764       return false;
765 
766     return AArch64_AM::isLogicalImmediate(Val & ~Upper, sizeof(T) * 8);
767   }
768 
769   bool isShiftedImm() const { return Kind == k_ShiftedImm; }
770 
771   /// Returns the immediate value as a pair of (imm, shift) if the immediate is
772   /// a shifted immediate by value 'Shift' or '0', or if it is an unshifted
773   /// immediate that can be shifted by 'Shift'.
774   template <unsigned Width>
775   Optional<std::pair<int64_t, unsigned> > getShiftedVal() const {
776     if (isShiftedImm() && Width == getShiftedImmShift())
777       if (auto *CE = dyn_cast<MCConstantExpr>(getShiftedImmVal()))
778         return std::make_pair(CE->getValue(), Width);
779 
780     if (isImm())
781       if (auto *CE = dyn_cast<MCConstantExpr>(getImm())) {
782         int64_t Val = CE->getValue();
783         if ((Val != 0) && (uint64_t(Val >> Width) << Width) == uint64_t(Val))
784           return std::make_pair(Val >> Width, Width);
785         else
786           return std::make_pair(Val, 0u);
787       }
788 
789     return {};
790   }
791 
792   bool isAddSubImm() const {
793     if (!isShiftedImm() && !isImm())
794       return false;
795 
796     const MCExpr *Expr;
797 
798     // An ADD/SUB shifter is either 'lsl #0' or 'lsl #12'.
799     if (isShiftedImm()) {
800       unsigned Shift = ShiftedImm.ShiftAmount;
801       Expr = ShiftedImm.Val;
802       if (Shift != 0 && Shift != 12)
803         return false;
804     } else {
805       Expr = getImm();
806     }
807 
808     AArch64MCExpr::VariantKind ELFRefKind;
809     MCSymbolRefExpr::VariantKind DarwinRefKind;
810     int64_t Addend;
811     if (AArch64AsmParser::classifySymbolRef(Expr, ELFRefKind,
812                                           DarwinRefKind, Addend)) {
813       return DarwinRefKind == MCSymbolRefExpr::VK_PAGEOFF
814           || DarwinRefKind == MCSymbolRefExpr::VK_TLVPPAGEOFF
815           || (DarwinRefKind == MCSymbolRefExpr::VK_GOTPAGEOFF && Addend == 0)
816           || ELFRefKind == AArch64MCExpr::VK_LO12
817           || ELFRefKind == AArch64MCExpr::VK_DTPREL_HI12
818           || ELFRefKind == AArch64MCExpr::VK_DTPREL_LO12
819           || ELFRefKind == AArch64MCExpr::VK_DTPREL_LO12_NC
820           || ELFRefKind == AArch64MCExpr::VK_TPREL_HI12
821           || ELFRefKind == AArch64MCExpr::VK_TPREL_LO12
822           || ELFRefKind == AArch64MCExpr::VK_TPREL_LO12_NC
823           || ELFRefKind == AArch64MCExpr::VK_TLSDESC_LO12
824           || ELFRefKind == AArch64MCExpr::VK_SECREL_HI12
825           || ELFRefKind == AArch64MCExpr::VK_SECREL_LO12;
826     }
827 
828     // If it's a constant, it should be a real immediate in range.
829     if (auto ShiftedVal = getShiftedVal<12>())
830       return ShiftedVal->first >= 0 && ShiftedVal->first <= 0xfff;
831 
832     // If it's an expression, we hope for the best and let the fixup/relocation
833     // code deal with it.
834     return true;
835   }
836 
837   bool isAddSubImmNeg() const {
838     if (!isShiftedImm() && !isImm())
839       return false;
840 
841     // Otherwise it should be a real negative immediate in range.
842     if (auto ShiftedVal = getShiftedVal<12>())
843       return ShiftedVal->first < 0 && -ShiftedVal->first <= 0xfff;
844 
845     return false;
846   }
847 
848   // Signed value in the range -128 to +127. For element widths of
849   // 16 bits or higher it may also be a signed multiple of 256 in the
850   // range -32768 to +32512.
851   // For element-width of 8 bits a range of -128 to 255 is accepted,
852   // since a copy of a byte can be either signed/unsigned.
853   template <typename T>
854   DiagnosticPredicate isSVECpyImm() const {
855     if (!isShiftedImm() && (!isImm() || !isa<MCConstantExpr>(getImm())))
856       return DiagnosticPredicateTy::NoMatch;
857 
858     bool IsByte = std::is_same<int8_t, std::make_signed_t<T>>::value;
859     if (auto ShiftedImm = getShiftedVal<8>())
860       if (!(IsByte && ShiftedImm->second) &&
861           AArch64_AM::isSVECpyImm<T>(uint64_t(ShiftedImm->first)
862                                      << ShiftedImm->second))
863         return DiagnosticPredicateTy::Match;
864 
865     return DiagnosticPredicateTy::NearMatch;
866   }
867 
868   // Unsigned value in the range 0 to 255. For element widths of
869   // 16 bits or higher it may also be a signed multiple of 256 in the
870   // range 0 to 65280.
871   template <typename T> DiagnosticPredicate isSVEAddSubImm() const {
872     if (!isShiftedImm() && (!isImm() || !isa<MCConstantExpr>(getImm())))
873       return DiagnosticPredicateTy::NoMatch;
874 
875     bool IsByte = std::is_same<int8_t, std::make_signed_t<T>>::value;
876     if (auto ShiftedImm = getShiftedVal<8>())
877       if (!(IsByte && ShiftedImm->second) &&
878           AArch64_AM::isSVEAddSubImm<T>(ShiftedImm->first
879                                         << ShiftedImm->second))
880         return DiagnosticPredicateTy::Match;
881 
882     return DiagnosticPredicateTy::NearMatch;
883   }
884 
885   template <typename T> DiagnosticPredicate isSVEPreferredLogicalImm() const {
886     if (isLogicalImm<T>() && !isSVECpyImm<T>())
887       return DiagnosticPredicateTy::Match;
888     return DiagnosticPredicateTy::NoMatch;
889   }
890 
891   bool isCondCode() const { return Kind == k_CondCode; }
892 
893   bool isSIMDImmType10() const {
894     if (!isImm())
895       return false;
896     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
897     if (!MCE)
898       return false;
899     return AArch64_AM::isAdvSIMDModImmType10(MCE->getValue());
900   }
901 
902   template<int N>
903   bool isBranchTarget() const {
904     if (!isImm())
905       return false;
906     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
907     if (!MCE)
908       return true;
909     int64_t Val = MCE->getValue();
910     if (Val & 0x3)
911       return false;
912     assert(N > 0 && "Branch target immediate cannot be 0 bits!");
913     return (Val >= -((1<<(N-1)) << 2) && Val <= (((1<<(N-1))-1) << 2));
914   }
915 
916   bool
917   isMovWSymbol(ArrayRef<AArch64MCExpr::VariantKind> AllowedModifiers) const {
918     if (!isImm())
919       return false;
920 
921     AArch64MCExpr::VariantKind ELFRefKind;
922     MCSymbolRefExpr::VariantKind DarwinRefKind;
923     int64_t Addend;
924     if (!AArch64AsmParser::classifySymbolRef(getImm(), ELFRefKind,
925                                              DarwinRefKind, Addend)) {
926       return false;
927     }
928     if (DarwinRefKind != MCSymbolRefExpr::VK_None)
929       return false;
930 
931     for (unsigned i = 0; i != AllowedModifiers.size(); ++i) {
932       if (ELFRefKind == AllowedModifiers[i])
933         return true;
934     }
935 
936     return false;
937   }
938 
939   bool isMovWSymbolG3() const {
940     return isMovWSymbol({AArch64MCExpr::VK_ABS_G3, AArch64MCExpr::VK_PREL_G3});
941   }
942 
943   bool isMovWSymbolG2() const {
944     return isMovWSymbol(
945         {AArch64MCExpr::VK_ABS_G2, AArch64MCExpr::VK_ABS_G2_S,
946          AArch64MCExpr::VK_ABS_G2_NC, AArch64MCExpr::VK_PREL_G2,
947          AArch64MCExpr::VK_PREL_G2_NC, AArch64MCExpr::VK_TPREL_G2,
948          AArch64MCExpr::VK_DTPREL_G2});
949   }
950 
951   bool isMovWSymbolG1() const {
952     return isMovWSymbol(
953         {AArch64MCExpr::VK_ABS_G1, AArch64MCExpr::VK_ABS_G1_S,
954          AArch64MCExpr::VK_ABS_G1_NC, AArch64MCExpr::VK_PREL_G1,
955          AArch64MCExpr::VK_PREL_G1_NC, AArch64MCExpr::VK_GOTTPREL_G1,
956          AArch64MCExpr::VK_TPREL_G1, AArch64MCExpr::VK_TPREL_G1_NC,
957          AArch64MCExpr::VK_DTPREL_G1, AArch64MCExpr::VK_DTPREL_G1_NC});
958   }
959 
960   bool isMovWSymbolG0() const {
961     return isMovWSymbol(
962         {AArch64MCExpr::VK_ABS_G0, AArch64MCExpr::VK_ABS_G0_S,
963          AArch64MCExpr::VK_ABS_G0_NC, AArch64MCExpr::VK_PREL_G0,
964          AArch64MCExpr::VK_PREL_G0_NC, AArch64MCExpr::VK_GOTTPREL_G0_NC,
965          AArch64MCExpr::VK_TPREL_G0, AArch64MCExpr::VK_TPREL_G0_NC,
966          AArch64MCExpr::VK_DTPREL_G0, AArch64MCExpr::VK_DTPREL_G0_NC});
967   }
968 
969   template<int RegWidth, int Shift>
970   bool isMOVZMovAlias() const {
971     if (!isImm()) return false;
972 
973     const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
974     if (!CE) return false;
975     uint64_t Value = CE->getValue();
976 
977     return AArch64_AM::isMOVZMovAlias(Value, Shift, RegWidth);
978   }
979 
980   template<int RegWidth, int Shift>
981   bool isMOVNMovAlias() const {
982     if (!isImm()) return false;
983 
984     const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
985     if (!CE) return false;
986     uint64_t Value = CE->getValue();
987 
988     return AArch64_AM::isMOVNMovAlias(Value, Shift, RegWidth);
989   }
990 
991   bool isFPImm() const {
992     return Kind == k_FPImm &&
993            AArch64_AM::getFP64Imm(getFPImm().bitcastToAPInt()) != -1;
994   }
995 
996   bool isBarrier() const { return Kind == k_Barrier; }
997   bool isSysReg() const { return Kind == k_SysReg; }
998 
999   bool isMRSSystemRegister() const {
1000     if (!isSysReg()) return false;
1001 
1002     return SysReg.MRSReg != -1U;
1003   }
1004 
1005   bool isMSRSystemRegister() const {
1006     if (!isSysReg()) return false;
1007     return SysReg.MSRReg != -1U;
1008   }
1009 
1010   bool isSystemPStateFieldWithImm0_1() const {
1011     if (!isSysReg()) return false;
1012     return (SysReg.PStateField == AArch64PState::PAN ||
1013             SysReg.PStateField == AArch64PState::DIT ||
1014             SysReg.PStateField == AArch64PState::UAO ||
1015             SysReg.PStateField == AArch64PState::SSBS);
1016   }
1017 
1018   bool isSystemPStateFieldWithImm0_15() const {
1019     if (!isSysReg() || isSystemPStateFieldWithImm0_1()) return false;
1020     return SysReg.PStateField != -1U;
1021   }
1022 
1023   bool isReg() const override {
1024     return Kind == k_Register;
1025   }
1026 
1027   bool isScalarReg() const {
1028     return Kind == k_Register && Reg.Kind == RegKind::Scalar;
1029   }
1030 
1031   bool isNeonVectorReg() const {
1032     return Kind == k_Register && Reg.Kind == RegKind::NeonVector;
1033   }
1034 
1035   bool isNeonVectorRegLo() const {
1036     return Kind == k_Register && Reg.Kind == RegKind::NeonVector &&
1037            (AArch64MCRegisterClasses[AArch64::FPR128_loRegClassID].contains(
1038                 Reg.RegNum) ||
1039             AArch64MCRegisterClasses[AArch64::FPR64_loRegClassID].contains(
1040                 Reg.RegNum));
1041   }
1042 
1043   template <unsigned Class> bool isSVEVectorReg() const {
1044     RegKind RK;
1045     switch (Class) {
1046     case AArch64::ZPRRegClassID:
1047     case AArch64::ZPR_3bRegClassID:
1048     case AArch64::ZPR_4bRegClassID:
1049       RK = RegKind::SVEDataVector;
1050       break;
1051     case AArch64::PPRRegClassID:
1052     case AArch64::PPR_3bRegClassID:
1053       RK = RegKind::SVEPredicateVector;
1054       break;
1055     default:
1056       llvm_unreachable("Unsupport register class");
1057     }
1058 
1059     return (Kind == k_Register && Reg.Kind == RK) &&
1060            AArch64MCRegisterClasses[Class].contains(getReg());
1061   }
1062 
1063   template <unsigned Class> bool isFPRasZPR() const {
1064     return Kind == k_Register && Reg.Kind == RegKind::Scalar &&
1065            AArch64MCRegisterClasses[Class].contains(getReg());
1066   }
1067 
1068   template <int ElementWidth, unsigned Class>
1069   DiagnosticPredicate isSVEPredicateVectorRegOfWidth() const {
1070     if (Kind != k_Register || Reg.Kind != RegKind::SVEPredicateVector)
1071       return DiagnosticPredicateTy::NoMatch;
1072 
1073     if (isSVEVectorReg<Class>() && (Reg.ElementWidth == ElementWidth))
1074       return DiagnosticPredicateTy::Match;
1075 
1076     return DiagnosticPredicateTy::NearMatch;
1077   }
1078 
1079   template <int ElementWidth, unsigned Class>
1080   DiagnosticPredicate isSVEDataVectorRegOfWidth() const {
1081     if (Kind != k_Register || Reg.Kind != RegKind::SVEDataVector)
1082       return DiagnosticPredicateTy::NoMatch;
1083 
1084     if (isSVEVectorReg<Class>() && Reg.ElementWidth == ElementWidth)
1085       return DiagnosticPredicateTy::Match;
1086 
1087     return DiagnosticPredicateTy::NearMatch;
1088   }
1089 
1090   template <int ElementWidth, unsigned Class,
1091             AArch64_AM::ShiftExtendType ShiftExtendTy, int ShiftWidth,
1092             bool ShiftWidthAlwaysSame>
1093   DiagnosticPredicate isSVEDataVectorRegWithShiftExtend() const {
1094     auto VectorMatch = isSVEDataVectorRegOfWidth<ElementWidth, Class>();
1095     if (!VectorMatch.isMatch())
1096       return DiagnosticPredicateTy::NoMatch;
1097 
1098     // Give a more specific diagnostic when the user has explicitly typed in
1099     // a shift-amount that does not match what is expected, but for which
1100     // there is also an unscaled addressing mode (e.g. sxtw/uxtw).
1101     bool MatchShift = getShiftExtendAmount() == Log2_32(ShiftWidth / 8);
1102     if (!MatchShift && (ShiftExtendTy == AArch64_AM::UXTW ||
1103                         ShiftExtendTy == AArch64_AM::SXTW) &&
1104         !ShiftWidthAlwaysSame && hasShiftExtendAmount() && ShiftWidth == 8)
1105       return DiagnosticPredicateTy::NoMatch;
1106 
1107     if (MatchShift && ShiftExtendTy == getShiftExtendType())
1108       return DiagnosticPredicateTy::Match;
1109 
1110     return DiagnosticPredicateTy::NearMatch;
1111   }
1112 
1113   bool isGPR32as64() const {
1114     return Kind == k_Register && Reg.Kind == RegKind::Scalar &&
1115       AArch64MCRegisterClasses[AArch64::GPR64RegClassID].contains(Reg.RegNum);
1116   }
1117 
1118   bool isGPR64as32() const {
1119     return Kind == k_Register && Reg.Kind == RegKind::Scalar &&
1120       AArch64MCRegisterClasses[AArch64::GPR32RegClassID].contains(Reg.RegNum);
1121   }
1122 
1123   bool isWSeqPair() const {
1124     return Kind == k_Register && Reg.Kind == RegKind::Scalar &&
1125            AArch64MCRegisterClasses[AArch64::WSeqPairsClassRegClassID].contains(
1126                Reg.RegNum);
1127   }
1128 
1129   bool isXSeqPair() const {
1130     return Kind == k_Register && Reg.Kind == RegKind::Scalar &&
1131            AArch64MCRegisterClasses[AArch64::XSeqPairsClassRegClassID].contains(
1132                Reg.RegNum);
1133   }
1134 
1135   template<int64_t Angle, int64_t Remainder>
1136   DiagnosticPredicate isComplexRotation() const {
1137     if (!isImm()) return DiagnosticPredicateTy::NoMatch;
1138 
1139     const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
1140     if (!CE) return DiagnosticPredicateTy::NoMatch;
1141     uint64_t Value = CE->getValue();
1142 
1143     if (Value % Angle == Remainder && Value <= 270)
1144       return DiagnosticPredicateTy::Match;
1145     return DiagnosticPredicateTy::NearMatch;
1146   }
1147 
1148   template <unsigned RegClassID> bool isGPR64() const {
1149     return Kind == k_Register && Reg.Kind == RegKind::Scalar &&
1150            AArch64MCRegisterClasses[RegClassID].contains(getReg());
1151   }
1152 
1153   template <unsigned RegClassID, int ExtWidth>
1154   DiagnosticPredicate isGPR64WithShiftExtend() const {
1155     if (Kind != k_Register || Reg.Kind != RegKind::Scalar)
1156       return DiagnosticPredicateTy::NoMatch;
1157 
1158     if (isGPR64<RegClassID>() && getShiftExtendType() == AArch64_AM::LSL &&
1159         getShiftExtendAmount() == Log2_32(ExtWidth / 8))
1160       return DiagnosticPredicateTy::Match;
1161     return DiagnosticPredicateTy::NearMatch;
1162   }
1163 
1164   /// Is this a vector list with the type implicit (presumably attached to the
1165   /// instruction itself)?
1166   template <RegKind VectorKind, unsigned NumRegs>
1167   bool isImplicitlyTypedVectorList() const {
1168     return Kind == k_VectorList && VectorList.Count == NumRegs &&
1169            VectorList.NumElements == 0 &&
1170            VectorList.RegisterKind == VectorKind;
1171   }
1172 
1173   template <RegKind VectorKind, unsigned NumRegs, unsigned NumElements,
1174             unsigned ElementWidth>
1175   bool isTypedVectorList() const {
1176     if (Kind != k_VectorList)
1177       return false;
1178     if (VectorList.Count != NumRegs)
1179       return false;
1180     if (VectorList.RegisterKind != VectorKind)
1181       return false;
1182     if (VectorList.ElementWidth != ElementWidth)
1183       return false;
1184     return VectorList.NumElements == NumElements;
1185   }
1186 
1187   template <int Min, int Max>
1188   DiagnosticPredicate isVectorIndex() const {
1189     if (Kind != k_VectorIndex)
1190       return DiagnosticPredicateTy::NoMatch;
1191     if (VectorIndex.Val >= Min && VectorIndex.Val <= Max)
1192       return DiagnosticPredicateTy::Match;
1193     return DiagnosticPredicateTy::NearMatch;
1194   }
1195 
1196   bool isToken() const override { return Kind == k_Token; }
1197 
1198   bool isTokenEqual(StringRef Str) const {
1199     return Kind == k_Token && getToken() == Str;
1200   }
1201   bool isSysCR() const { return Kind == k_SysCR; }
1202   bool isPrefetch() const { return Kind == k_Prefetch; }
1203   bool isPSBHint() const { return Kind == k_PSBHint; }
1204   bool isBTIHint() const { return Kind == k_BTIHint; }
1205   bool isShiftExtend() const { return Kind == k_ShiftExtend; }
1206   bool isShifter() const {
1207     if (!isShiftExtend())
1208       return false;
1209 
1210     AArch64_AM::ShiftExtendType ST = getShiftExtendType();
1211     return (ST == AArch64_AM::LSL || ST == AArch64_AM::LSR ||
1212             ST == AArch64_AM::ASR || ST == AArch64_AM::ROR ||
1213             ST == AArch64_AM::MSL);
1214   }
1215 
1216   template <unsigned ImmEnum> DiagnosticPredicate isExactFPImm() const {
1217     if (Kind != k_FPImm)
1218       return DiagnosticPredicateTy::NoMatch;
1219 
1220     if (getFPImmIsExact()) {
1221       // Lookup the immediate from table of supported immediates.
1222       auto *Desc = AArch64ExactFPImm::lookupExactFPImmByEnum(ImmEnum);
1223       assert(Desc && "Unknown enum value");
1224 
1225       // Calculate its FP value.
1226       APFloat RealVal(APFloat::IEEEdouble());
1227       auto StatusOrErr =
1228           RealVal.convertFromString(Desc->Repr, APFloat::rmTowardZero);
1229       if (errorToBool(StatusOrErr.takeError()) || *StatusOrErr != APFloat::opOK)
1230         llvm_unreachable("FP immediate is not exact");
1231 
1232       if (getFPImm().bitwiseIsEqual(RealVal))
1233         return DiagnosticPredicateTy::Match;
1234     }
1235 
1236     return DiagnosticPredicateTy::NearMatch;
1237   }
1238 
1239   template <unsigned ImmA, unsigned ImmB>
1240   DiagnosticPredicate isExactFPImm() const {
1241     DiagnosticPredicate Res = DiagnosticPredicateTy::NoMatch;
1242     if ((Res = isExactFPImm<ImmA>()))
1243       return DiagnosticPredicateTy::Match;
1244     if ((Res = isExactFPImm<ImmB>()))
1245       return DiagnosticPredicateTy::Match;
1246     return Res;
1247   }
1248 
1249   bool isExtend() const {
1250     if (!isShiftExtend())
1251       return false;
1252 
1253     AArch64_AM::ShiftExtendType ET = getShiftExtendType();
1254     return (ET == AArch64_AM::UXTB || ET == AArch64_AM::SXTB ||
1255             ET == AArch64_AM::UXTH || ET == AArch64_AM::SXTH ||
1256             ET == AArch64_AM::UXTW || ET == AArch64_AM::SXTW ||
1257             ET == AArch64_AM::UXTX || ET == AArch64_AM::SXTX ||
1258             ET == AArch64_AM::LSL) &&
1259            getShiftExtendAmount() <= 4;
1260   }
1261 
1262   bool isExtend64() const {
1263     if (!isExtend())
1264       return false;
1265     // Make sure the extend expects a 32-bit source register.
1266     AArch64_AM::ShiftExtendType ET = getShiftExtendType();
1267     return ET == AArch64_AM::UXTB || ET == AArch64_AM::SXTB ||
1268            ET == AArch64_AM::UXTH || ET == AArch64_AM::SXTH ||
1269            ET == AArch64_AM::UXTW || ET == AArch64_AM::SXTW;
1270   }
1271 
1272   bool isExtendLSL64() const {
1273     if (!isExtend())
1274       return false;
1275     AArch64_AM::ShiftExtendType ET = getShiftExtendType();
1276     return (ET == AArch64_AM::UXTX || ET == AArch64_AM::SXTX ||
1277             ET == AArch64_AM::LSL) &&
1278            getShiftExtendAmount() <= 4;
1279   }
1280 
1281   template<int Width> bool isMemXExtend() const {
1282     if (!isExtend())
1283       return false;
1284     AArch64_AM::ShiftExtendType ET = getShiftExtendType();
1285     return (ET == AArch64_AM::LSL || ET == AArch64_AM::SXTX) &&
1286            (getShiftExtendAmount() == Log2_32(Width / 8) ||
1287             getShiftExtendAmount() == 0);
1288   }
1289 
1290   template<int Width> bool isMemWExtend() const {
1291     if (!isExtend())
1292       return false;
1293     AArch64_AM::ShiftExtendType ET = getShiftExtendType();
1294     return (ET == AArch64_AM::UXTW || ET == AArch64_AM::SXTW) &&
1295            (getShiftExtendAmount() == Log2_32(Width / 8) ||
1296             getShiftExtendAmount() == 0);
1297   }
1298 
1299   template <unsigned width>
1300   bool isArithmeticShifter() const {
1301     if (!isShifter())
1302       return false;
1303 
1304     // An arithmetic shifter is LSL, LSR, or ASR.
1305     AArch64_AM::ShiftExtendType ST = getShiftExtendType();
1306     return (ST == AArch64_AM::LSL || ST == AArch64_AM::LSR ||
1307             ST == AArch64_AM::ASR) && getShiftExtendAmount() < width;
1308   }
1309 
1310   template <unsigned width>
1311   bool isLogicalShifter() const {
1312     if (!isShifter())
1313       return false;
1314 
1315     // A logical shifter is LSL, LSR, ASR or ROR.
1316     AArch64_AM::ShiftExtendType ST = getShiftExtendType();
1317     return (ST == AArch64_AM::LSL || ST == AArch64_AM::LSR ||
1318             ST == AArch64_AM::ASR || ST == AArch64_AM::ROR) &&
1319            getShiftExtendAmount() < width;
1320   }
1321 
1322   bool isMovImm32Shifter() const {
1323     if (!isShifter())
1324       return false;
1325 
1326     // A MOVi shifter is LSL of 0, 16, 32, or 48.
1327     AArch64_AM::ShiftExtendType ST = getShiftExtendType();
1328     if (ST != AArch64_AM::LSL)
1329       return false;
1330     uint64_t Val = getShiftExtendAmount();
1331     return (Val == 0 || Val == 16);
1332   }
1333 
1334   bool isMovImm64Shifter() const {
1335     if (!isShifter())
1336       return false;
1337 
1338     // A MOVi shifter is LSL of 0 or 16.
1339     AArch64_AM::ShiftExtendType ST = getShiftExtendType();
1340     if (ST != AArch64_AM::LSL)
1341       return false;
1342     uint64_t Val = getShiftExtendAmount();
1343     return (Val == 0 || Val == 16 || Val == 32 || Val == 48);
1344   }
1345 
1346   bool isLogicalVecShifter() const {
1347     if (!isShifter())
1348       return false;
1349 
1350     // A logical vector shifter is a left shift by 0, 8, 16, or 24.
1351     unsigned Shift = getShiftExtendAmount();
1352     return getShiftExtendType() == AArch64_AM::LSL &&
1353            (Shift == 0 || Shift == 8 || Shift == 16 || Shift == 24);
1354   }
1355 
1356   bool isLogicalVecHalfWordShifter() const {
1357     if (!isLogicalVecShifter())
1358       return false;
1359 
1360     // A logical vector shifter is a left shift by 0 or 8.
1361     unsigned Shift = getShiftExtendAmount();
1362     return getShiftExtendType() == AArch64_AM::LSL &&
1363            (Shift == 0 || Shift == 8);
1364   }
1365 
1366   bool isMoveVecShifter() const {
1367     if (!isShiftExtend())
1368       return false;
1369 
1370     // A logical vector shifter is a left shift by 8 or 16.
1371     unsigned Shift = getShiftExtendAmount();
1372     return getShiftExtendType() == AArch64_AM::MSL &&
1373            (Shift == 8 || Shift == 16);
1374   }
1375 
1376   // Fallback unscaled operands are for aliases of LDR/STR that fall back
1377   // to LDUR/STUR when the offset is not legal for the former but is for
1378   // the latter. As such, in addition to checking for being a legal unscaled
1379   // address, also check that it is not a legal scaled address. This avoids
1380   // ambiguity in the matcher.
1381   template<int Width>
1382   bool isSImm9OffsetFB() const {
1383     return isSImm<9>() && !isUImm12Offset<Width / 8>();
1384   }
1385 
1386   bool isAdrpLabel() const {
1387     // Validation was handled during parsing, so we just sanity check that
1388     // something didn't go haywire.
1389     if (!isImm())
1390         return false;
1391 
1392     if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Imm.Val)) {
1393       int64_t Val = CE->getValue();
1394       int64_t Min = - (4096 * (1LL << (21 - 1)));
1395       int64_t Max = 4096 * ((1LL << (21 - 1)) - 1);
1396       return (Val % 4096) == 0 && Val >= Min && Val <= Max;
1397     }
1398 
1399     return true;
1400   }
1401 
1402   bool isAdrLabel() const {
1403     // Validation was handled during parsing, so we just sanity check that
1404     // something didn't go haywire.
1405     if (!isImm())
1406         return false;
1407 
1408     if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Imm.Val)) {
1409       int64_t Val = CE->getValue();
1410       int64_t Min = - (1LL << (21 - 1));
1411       int64_t Max = ((1LL << (21 - 1)) - 1);
1412       return Val >= Min && Val <= Max;
1413     }
1414 
1415     return true;
1416   }
1417 
1418   void addExpr(MCInst &Inst, const MCExpr *Expr) const {
1419     // Add as immediates when possible.  Null MCExpr = 0.
1420     if (!Expr)
1421       Inst.addOperand(MCOperand::createImm(0));
1422     else if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Expr))
1423       Inst.addOperand(MCOperand::createImm(CE->getValue()));
1424     else
1425       Inst.addOperand(MCOperand::createExpr(Expr));
1426   }
1427 
1428   void addRegOperands(MCInst &Inst, unsigned N) const {
1429     assert(N == 1 && "Invalid number of operands!");
1430     Inst.addOperand(MCOperand::createReg(getReg()));
1431   }
1432 
1433   void addGPR32as64Operands(MCInst &Inst, unsigned N) const {
1434     assert(N == 1 && "Invalid number of operands!");
1435     assert(
1436         AArch64MCRegisterClasses[AArch64::GPR64RegClassID].contains(getReg()));
1437 
1438     const MCRegisterInfo *RI = Ctx.getRegisterInfo();
1439     uint32_t Reg = RI->getRegClass(AArch64::GPR32RegClassID).getRegister(
1440         RI->getEncodingValue(getReg()));
1441 
1442     Inst.addOperand(MCOperand::createReg(Reg));
1443   }
1444 
1445   void addGPR64as32Operands(MCInst &Inst, unsigned N) const {
1446     assert(N == 1 && "Invalid number of operands!");
1447     assert(
1448         AArch64MCRegisterClasses[AArch64::GPR32RegClassID].contains(getReg()));
1449 
1450     const MCRegisterInfo *RI = Ctx.getRegisterInfo();
1451     uint32_t Reg = RI->getRegClass(AArch64::GPR64RegClassID).getRegister(
1452         RI->getEncodingValue(getReg()));
1453 
1454     Inst.addOperand(MCOperand::createReg(Reg));
1455   }
1456 
1457   template <int Width>
1458   void addFPRasZPRRegOperands(MCInst &Inst, unsigned N) const {
1459     unsigned Base;
1460     switch (Width) {
1461     case 8:   Base = AArch64::B0; break;
1462     case 16:  Base = AArch64::H0; break;
1463     case 32:  Base = AArch64::S0; break;
1464     case 64:  Base = AArch64::D0; break;
1465     case 128: Base = AArch64::Q0; break;
1466     default:
1467       llvm_unreachable("Unsupported width");
1468     }
1469     Inst.addOperand(MCOperand::createReg(AArch64::Z0 + getReg() - Base));
1470   }
1471 
1472   void addVectorReg64Operands(MCInst &Inst, unsigned N) const {
1473     assert(N == 1 && "Invalid number of operands!");
1474     assert(
1475         AArch64MCRegisterClasses[AArch64::FPR128RegClassID].contains(getReg()));
1476     Inst.addOperand(MCOperand::createReg(AArch64::D0 + getReg() - AArch64::Q0));
1477   }
1478 
1479   void addVectorReg128Operands(MCInst &Inst, unsigned N) const {
1480     assert(N == 1 && "Invalid number of operands!");
1481     assert(
1482         AArch64MCRegisterClasses[AArch64::FPR128RegClassID].contains(getReg()));
1483     Inst.addOperand(MCOperand::createReg(getReg()));
1484   }
1485 
1486   void addVectorRegLoOperands(MCInst &Inst, unsigned N) const {
1487     assert(N == 1 && "Invalid number of operands!");
1488     Inst.addOperand(MCOperand::createReg(getReg()));
1489   }
1490 
1491   enum VecListIndexType {
1492     VecListIdx_DReg = 0,
1493     VecListIdx_QReg = 1,
1494     VecListIdx_ZReg = 2,
1495   };
1496 
1497   template <VecListIndexType RegTy, unsigned NumRegs>
1498   void addVectorListOperands(MCInst &Inst, unsigned N) const {
1499     assert(N == 1 && "Invalid number of operands!");
1500     static const unsigned FirstRegs[][5] = {
1501       /* DReg */ { AArch64::Q0,
1502                    AArch64::D0,       AArch64::D0_D1,
1503                    AArch64::D0_D1_D2, AArch64::D0_D1_D2_D3 },
1504       /* QReg */ { AArch64::Q0,
1505                    AArch64::Q0,       AArch64::Q0_Q1,
1506                    AArch64::Q0_Q1_Q2, AArch64::Q0_Q1_Q2_Q3 },
1507       /* ZReg */ { AArch64::Z0,
1508                    AArch64::Z0,       AArch64::Z0_Z1,
1509                    AArch64::Z0_Z1_Z2, AArch64::Z0_Z1_Z2_Z3 }
1510     };
1511 
1512     assert((RegTy != VecListIdx_ZReg || NumRegs <= 4) &&
1513            " NumRegs must be <= 4 for ZRegs");
1514 
1515     unsigned FirstReg = FirstRegs[(unsigned)RegTy][NumRegs];
1516     Inst.addOperand(MCOperand::createReg(FirstReg + getVectorListStart() -
1517                                          FirstRegs[(unsigned)RegTy][0]));
1518   }
1519 
1520   void addVectorIndexOperands(MCInst &Inst, unsigned N) const {
1521     assert(N == 1 && "Invalid number of operands!");
1522     Inst.addOperand(MCOperand::createImm(getVectorIndex()));
1523   }
1524 
1525   template <unsigned ImmIs0, unsigned ImmIs1>
1526   void addExactFPImmOperands(MCInst &Inst, unsigned N) const {
1527     assert(N == 1 && "Invalid number of operands!");
1528     assert(bool(isExactFPImm<ImmIs0, ImmIs1>()) && "Invalid operand");
1529     Inst.addOperand(MCOperand::createImm(bool(isExactFPImm<ImmIs1>())));
1530   }
1531 
1532   void addImmOperands(MCInst &Inst, unsigned N) const {
1533     assert(N == 1 && "Invalid number of operands!");
1534     // If this is a pageoff symrefexpr with an addend, adjust the addend
1535     // to be only the page-offset portion. Otherwise, just add the expr
1536     // as-is.
1537     addExpr(Inst, getImm());
1538   }
1539 
1540   template <int Shift>
1541   void addImmWithOptionalShiftOperands(MCInst &Inst, unsigned N) const {
1542     assert(N == 2 && "Invalid number of operands!");
1543     if (auto ShiftedVal = getShiftedVal<Shift>()) {
1544       Inst.addOperand(MCOperand::createImm(ShiftedVal->first));
1545       Inst.addOperand(MCOperand::createImm(ShiftedVal->second));
1546     } else if (isShiftedImm()) {
1547       addExpr(Inst, getShiftedImmVal());
1548       Inst.addOperand(MCOperand::createImm(getShiftedImmShift()));
1549     } else {
1550       addExpr(Inst, getImm());
1551       Inst.addOperand(MCOperand::createImm(0));
1552     }
1553   }
1554 
1555   template <int Shift>
1556   void addImmNegWithOptionalShiftOperands(MCInst &Inst, unsigned N) const {
1557     assert(N == 2 && "Invalid number of operands!");
1558     if (auto ShiftedVal = getShiftedVal<Shift>()) {
1559       Inst.addOperand(MCOperand::createImm(-ShiftedVal->first));
1560       Inst.addOperand(MCOperand::createImm(ShiftedVal->second));
1561     } else
1562       llvm_unreachable("Not a shifted negative immediate");
1563   }
1564 
1565   void addCondCodeOperands(MCInst &Inst, unsigned N) const {
1566     assert(N == 1 && "Invalid number of operands!");
1567     Inst.addOperand(MCOperand::createImm(getCondCode()));
1568   }
1569 
1570   void addAdrpLabelOperands(MCInst &Inst, unsigned N) const {
1571     assert(N == 1 && "Invalid number of operands!");
1572     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
1573     if (!MCE)
1574       addExpr(Inst, getImm());
1575     else
1576       Inst.addOperand(MCOperand::createImm(MCE->getValue() >> 12));
1577   }
1578 
1579   void addAdrLabelOperands(MCInst &Inst, unsigned N) const {
1580     addImmOperands(Inst, N);
1581   }
1582 
1583   template<int Scale>
1584   void addUImm12OffsetOperands(MCInst &Inst, unsigned N) const {
1585     assert(N == 1 && "Invalid number of operands!");
1586     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
1587 
1588     if (!MCE) {
1589       Inst.addOperand(MCOperand::createExpr(getImm()));
1590       return;
1591     }
1592     Inst.addOperand(MCOperand::createImm(MCE->getValue() / Scale));
1593   }
1594 
1595   void addUImm6Operands(MCInst &Inst, unsigned N) const {
1596     assert(N == 1 && "Invalid number of operands!");
1597     const MCConstantExpr *MCE = cast<MCConstantExpr>(getImm());
1598     Inst.addOperand(MCOperand::createImm(MCE->getValue()));
1599   }
1600 
1601   template <int Scale>
1602   void addImmScaledOperands(MCInst &Inst, unsigned N) const {
1603     assert(N == 1 && "Invalid number of operands!");
1604     const MCConstantExpr *MCE = cast<MCConstantExpr>(getImm());
1605     Inst.addOperand(MCOperand::createImm(MCE->getValue() / Scale));
1606   }
1607 
1608   template <typename T>
1609   void addLogicalImmOperands(MCInst &Inst, unsigned N) const {
1610     assert(N == 1 && "Invalid number of operands!");
1611     const MCConstantExpr *MCE = cast<MCConstantExpr>(getImm());
1612     std::make_unsigned_t<T> Val = MCE->getValue();
1613     uint64_t encoding = AArch64_AM::encodeLogicalImmediate(Val, sizeof(T) * 8);
1614     Inst.addOperand(MCOperand::createImm(encoding));
1615   }
1616 
1617   template <typename T>
1618   void addLogicalImmNotOperands(MCInst &Inst, unsigned N) const {
1619     assert(N == 1 && "Invalid number of operands!");
1620     const MCConstantExpr *MCE = cast<MCConstantExpr>(getImm());
1621     std::make_unsigned_t<T> Val = ~MCE->getValue();
1622     uint64_t encoding = AArch64_AM::encodeLogicalImmediate(Val, sizeof(T) * 8);
1623     Inst.addOperand(MCOperand::createImm(encoding));
1624   }
1625 
1626   void addSIMDImmType10Operands(MCInst &Inst, unsigned N) const {
1627     assert(N == 1 && "Invalid number of operands!");
1628     const MCConstantExpr *MCE = cast<MCConstantExpr>(getImm());
1629     uint64_t encoding = AArch64_AM::encodeAdvSIMDModImmType10(MCE->getValue());
1630     Inst.addOperand(MCOperand::createImm(encoding));
1631   }
1632 
1633   void addBranchTarget26Operands(MCInst &Inst, unsigned N) const {
1634     // Branch operands don't encode the low bits, so shift them off
1635     // here. If it's a label, however, just put it on directly as there's
1636     // not enough information now to do anything.
1637     assert(N == 1 && "Invalid number of operands!");
1638     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
1639     if (!MCE) {
1640       addExpr(Inst, getImm());
1641       return;
1642     }
1643     assert(MCE && "Invalid constant immediate operand!");
1644     Inst.addOperand(MCOperand::createImm(MCE->getValue() >> 2));
1645   }
1646 
1647   void addPCRelLabel19Operands(MCInst &Inst, unsigned N) const {
1648     // Branch operands don't encode the low bits, so shift them off
1649     // here. If it's a label, however, just put it on directly as there's
1650     // not enough information now to do anything.
1651     assert(N == 1 && "Invalid number of operands!");
1652     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
1653     if (!MCE) {
1654       addExpr(Inst, getImm());
1655       return;
1656     }
1657     assert(MCE && "Invalid constant immediate operand!");
1658     Inst.addOperand(MCOperand::createImm(MCE->getValue() >> 2));
1659   }
1660 
1661   void addBranchTarget14Operands(MCInst &Inst, unsigned N) const {
1662     // Branch operands don't encode the low bits, so shift them off
1663     // here. If it's a label, however, just put it on directly as there's
1664     // not enough information now to do anything.
1665     assert(N == 1 && "Invalid number of operands!");
1666     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(getImm());
1667     if (!MCE) {
1668       addExpr(Inst, getImm());
1669       return;
1670     }
1671     assert(MCE && "Invalid constant immediate operand!");
1672     Inst.addOperand(MCOperand::createImm(MCE->getValue() >> 2));
1673   }
1674 
1675   void addFPImmOperands(MCInst &Inst, unsigned N) const {
1676     assert(N == 1 && "Invalid number of operands!");
1677     Inst.addOperand(MCOperand::createImm(
1678         AArch64_AM::getFP64Imm(getFPImm().bitcastToAPInt())));
1679   }
1680 
1681   void addBarrierOperands(MCInst &Inst, unsigned N) const {
1682     assert(N == 1 && "Invalid number of operands!");
1683     Inst.addOperand(MCOperand::createImm(getBarrier()));
1684   }
1685 
1686   void addMRSSystemRegisterOperands(MCInst &Inst, unsigned N) const {
1687     assert(N == 1 && "Invalid number of operands!");
1688 
1689     Inst.addOperand(MCOperand::createImm(SysReg.MRSReg));
1690   }
1691 
1692   void addMSRSystemRegisterOperands(MCInst &Inst, unsigned N) const {
1693     assert(N == 1 && "Invalid number of operands!");
1694 
1695     Inst.addOperand(MCOperand::createImm(SysReg.MSRReg));
1696   }
1697 
1698   void addSystemPStateFieldWithImm0_1Operands(MCInst &Inst, unsigned N) const {
1699     assert(N == 1 && "Invalid number of operands!");
1700 
1701     Inst.addOperand(MCOperand::createImm(SysReg.PStateField));
1702   }
1703 
1704   void addSystemPStateFieldWithImm0_15Operands(MCInst &Inst, unsigned N) const {
1705     assert(N == 1 && "Invalid number of operands!");
1706 
1707     Inst.addOperand(MCOperand::createImm(SysReg.PStateField));
1708   }
1709 
1710   void addSysCROperands(MCInst &Inst, unsigned N) const {
1711     assert(N == 1 && "Invalid number of operands!");
1712     Inst.addOperand(MCOperand::createImm(getSysCR()));
1713   }
1714 
1715   void addPrefetchOperands(MCInst &Inst, unsigned N) const {
1716     assert(N == 1 && "Invalid number of operands!");
1717     Inst.addOperand(MCOperand::createImm(getPrefetch()));
1718   }
1719 
1720   void addPSBHintOperands(MCInst &Inst, unsigned N) const {
1721     assert(N == 1 && "Invalid number of operands!");
1722     Inst.addOperand(MCOperand::createImm(getPSBHint()));
1723   }
1724 
1725   void addBTIHintOperands(MCInst &Inst, unsigned N) const {
1726     assert(N == 1 && "Invalid number of operands!");
1727     Inst.addOperand(MCOperand::createImm(getBTIHint()));
1728   }
1729 
1730   void addShifterOperands(MCInst &Inst, unsigned N) const {
1731     assert(N == 1 && "Invalid number of operands!");
1732     unsigned Imm =
1733         AArch64_AM::getShifterImm(getShiftExtendType(), getShiftExtendAmount());
1734     Inst.addOperand(MCOperand::createImm(Imm));
1735   }
1736 
1737   void addExtendOperands(MCInst &Inst, unsigned N) const {
1738     assert(N == 1 && "Invalid number of operands!");
1739     AArch64_AM::ShiftExtendType ET = getShiftExtendType();
1740     if (ET == AArch64_AM::LSL) ET = AArch64_AM::UXTW;
1741     unsigned Imm = AArch64_AM::getArithExtendImm(ET, getShiftExtendAmount());
1742     Inst.addOperand(MCOperand::createImm(Imm));
1743   }
1744 
1745   void addExtend64Operands(MCInst &Inst, unsigned N) const {
1746     assert(N == 1 && "Invalid number of operands!");
1747     AArch64_AM::ShiftExtendType ET = getShiftExtendType();
1748     if (ET == AArch64_AM::LSL) ET = AArch64_AM::UXTX;
1749     unsigned Imm = AArch64_AM::getArithExtendImm(ET, getShiftExtendAmount());
1750     Inst.addOperand(MCOperand::createImm(Imm));
1751   }
1752 
1753   void addMemExtendOperands(MCInst &Inst, unsigned N) const {
1754     assert(N == 2 && "Invalid number of operands!");
1755     AArch64_AM::ShiftExtendType ET = getShiftExtendType();
1756     bool IsSigned = ET == AArch64_AM::SXTW || ET == AArch64_AM::SXTX;
1757     Inst.addOperand(MCOperand::createImm(IsSigned));
1758     Inst.addOperand(MCOperand::createImm(getShiftExtendAmount() != 0));
1759   }
1760 
1761   // For 8-bit load/store instructions with a register offset, both the
1762   // "DoShift" and "NoShift" variants have a shift of 0. Because of this,
1763   // they're disambiguated by whether the shift was explicit or implicit rather
1764   // than its size.
1765   void addMemExtend8Operands(MCInst &Inst, unsigned N) const {
1766     assert(N == 2 && "Invalid number of operands!");
1767     AArch64_AM::ShiftExtendType ET = getShiftExtendType();
1768     bool IsSigned = ET == AArch64_AM::SXTW || ET == AArch64_AM::SXTX;
1769     Inst.addOperand(MCOperand::createImm(IsSigned));
1770     Inst.addOperand(MCOperand::createImm(hasShiftExtendAmount()));
1771   }
1772 
1773   template<int Shift>
1774   void addMOVZMovAliasOperands(MCInst &Inst, unsigned N) const {
1775     assert(N == 1 && "Invalid number of operands!");
1776 
1777     const MCConstantExpr *CE = cast<MCConstantExpr>(getImm());
1778     uint64_t Value = CE->getValue();
1779     Inst.addOperand(MCOperand::createImm((Value >> Shift) & 0xffff));
1780   }
1781 
1782   template<int Shift>
1783   void addMOVNMovAliasOperands(MCInst &Inst, unsigned N) const {
1784     assert(N == 1 && "Invalid number of operands!");
1785 
1786     const MCConstantExpr *CE = cast<MCConstantExpr>(getImm());
1787     uint64_t Value = CE->getValue();
1788     Inst.addOperand(MCOperand::createImm((~Value >> Shift) & 0xffff));
1789   }
1790 
1791   void addComplexRotationEvenOperands(MCInst &Inst, unsigned N) const {
1792     assert(N == 1 && "Invalid number of operands!");
1793     const MCConstantExpr *MCE = cast<MCConstantExpr>(getImm());
1794     Inst.addOperand(MCOperand::createImm(MCE->getValue() / 90));
1795   }
1796 
1797   void addComplexRotationOddOperands(MCInst &Inst, unsigned N) const {
1798     assert(N == 1 && "Invalid number of operands!");
1799     const MCConstantExpr *MCE = cast<MCConstantExpr>(getImm());
1800     Inst.addOperand(MCOperand::createImm((MCE->getValue() - 90) / 180));
1801   }
1802 
1803   void print(raw_ostream &OS) const override;
1804 
1805   static std::unique_ptr<AArch64Operand>
1806   CreateToken(StringRef Str, bool IsSuffix, SMLoc S, MCContext &Ctx) {
1807     auto Op = std::make_unique<AArch64Operand>(k_Token, Ctx);
1808     Op->Tok.Data = Str.data();
1809     Op->Tok.Length = Str.size();
1810     Op->Tok.IsSuffix = IsSuffix;
1811     Op->StartLoc = S;
1812     Op->EndLoc = S;
1813     return Op;
1814   }
1815 
1816   static std::unique_ptr<AArch64Operand>
1817   CreateReg(unsigned RegNum, RegKind Kind, SMLoc S, SMLoc E, MCContext &Ctx,
1818             RegConstraintEqualityTy EqTy = RegConstraintEqualityTy::EqualsReg,
1819             AArch64_AM::ShiftExtendType ExtTy = AArch64_AM::LSL,
1820             unsigned ShiftAmount = 0,
1821             unsigned HasExplicitAmount = false) {
1822     auto Op = std::make_unique<AArch64Operand>(k_Register, Ctx);
1823     Op->Reg.RegNum = RegNum;
1824     Op->Reg.Kind = Kind;
1825     Op->Reg.ElementWidth = 0;
1826     Op->Reg.EqualityTy = EqTy;
1827     Op->Reg.ShiftExtend.Type = ExtTy;
1828     Op->Reg.ShiftExtend.Amount = ShiftAmount;
1829     Op->Reg.ShiftExtend.HasExplicitAmount = HasExplicitAmount;
1830     Op->StartLoc = S;
1831     Op->EndLoc = E;
1832     return Op;
1833   }
1834 
1835   static std::unique_ptr<AArch64Operand>
1836   CreateVectorReg(unsigned RegNum, RegKind Kind, unsigned ElementWidth,
1837                   SMLoc S, SMLoc E, MCContext &Ctx,
1838                   AArch64_AM::ShiftExtendType ExtTy = AArch64_AM::LSL,
1839                   unsigned ShiftAmount = 0,
1840                   unsigned HasExplicitAmount = false) {
1841     assert((Kind == RegKind::NeonVector || Kind == RegKind::SVEDataVector ||
1842             Kind == RegKind::SVEPredicateVector) &&
1843            "Invalid vector kind");
1844     auto Op = CreateReg(RegNum, Kind, S, E, Ctx, EqualsReg, ExtTy, ShiftAmount,
1845                         HasExplicitAmount);
1846     Op->Reg.ElementWidth = ElementWidth;
1847     return Op;
1848   }
1849 
1850   static std::unique_ptr<AArch64Operand>
1851   CreateVectorList(unsigned RegNum, unsigned Count, unsigned NumElements,
1852                    unsigned ElementWidth, RegKind RegisterKind, SMLoc S, SMLoc E,
1853                    MCContext &Ctx) {
1854     auto Op = std::make_unique<AArch64Operand>(k_VectorList, Ctx);
1855     Op->VectorList.RegNum = RegNum;
1856     Op->VectorList.Count = Count;
1857     Op->VectorList.NumElements = NumElements;
1858     Op->VectorList.ElementWidth = ElementWidth;
1859     Op->VectorList.RegisterKind = RegisterKind;
1860     Op->StartLoc = S;
1861     Op->EndLoc = E;
1862     return Op;
1863   }
1864 
1865   static std::unique_ptr<AArch64Operand>
1866   CreateVectorIndex(unsigned Idx, SMLoc S, SMLoc E, MCContext &Ctx) {
1867     auto Op = std::make_unique<AArch64Operand>(k_VectorIndex, Ctx);
1868     Op->VectorIndex.Val = Idx;
1869     Op->StartLoc = S;
1870     Op->EndLoc = E;
1871     return Op;
1872   }
1873 
1874   static std::unique_ptr<AArch64Operand> CreateImm(const MCExpr *Val, SMLoc S,
1875                                                    SMLoc E, MCContext &Ctx) {
1876     auto Op = std::make_unique<AArch64Operand>(k_Immediate, Ctx);
1877     Op->Imm.Val = Val;
1878     Op->StartLoc = S;
1879     Op->EndLoc = E;
1880     return Op;
1881   }
1882 
1883   static std::unique_ptr<AArch64Operand> CreateShiftedImm(const MCExpr *Val,
1884                                                           unsigned ShiftAmount,
1885                                                           SMLoc S, SMLoc E,
1886                                                           MCContext &Ctx) {
1887     auto Op = std::make_unique<AArch64Operand>(k_ShiftedImm, Ctx);
1888     Op->ShiftedImm .Val = Val;
1889     Op->ShiftedImm.ShiftAmount = ShiftAmount;
1890     Op->StartLoc = S;
1891     Op->EndLoc = E;
1892     return Op;
1893   }
1894 
1895   static std::unique_ptr<AArch64Operand>
1896   CreateCondCode(AArch64CC::CondCode Code, SMLoc S, SMLoc E, MCContext &Ctx) {
1897     auto Op = std::make_unique<AArch64Operand>(k_CondCode, Ctx);
1898     Op->CondCode.Code = Code;
1899     Op->StartLoc = S;
1900     Op->EndLoc = E;
1901     return Op;
1902   }
1903 
1904   static std::unique_ptr<AArch64Operand>
1905   CreateFPImm(APFloat Val, bool IsExact, SMLoc S, MCContext &Ctx) {
1906     auto Op = std::make_unique<AArch64Operand>(k_FPImm, Ctx);
1907     Op->FPImm.Val = Val.bitcastToAPInt().getSExtValue();
1908     Op->FPImm.IsExact = IsExact;
1909     Op->StartLoc = S;
1910     Op->EndLoc = S;
1911     return Op;
1912   }
1913 
1914   static std::unique_ptr<AArch64Operand> CreateBarrier(unsigned Val,
1915                                                        StringRef Str,
1916                                                        SMLoc S,
1917                                                        MCContext &Ctx) {
1918     auto Op = std::make_unique<AArch64Operand>(k_Barrier, Ctx);
1919     Op->Barrier.Val = Val;
1920     Op->Barrier.Data = Str.data();
1921     Op->Barrier.Length = Str.size();
1922     Op->StartLoc = S;
1923     Op->EndLoc = S;
1924     return Op;
1925   }
1926 
1927   static std::unique_ptr<AArch64Operand> CreateSysReg(StringRef Str, SMLoc S,
1928                                                       uint32_t MRSReg,
1929                                                       uint32_t MSRReg,
1930                                                       uint32_t PStateField,
1931                                                       MCContext &Ctx) {
1932     auto Op = std::make_unique<AArch64Operand>(k_SysReg, Ctx);
1933     Op->SysReg.Data = Str.data();
1934     Op->SysReg.Length = Str.size();
1935     Op->SysReg.MRSReg = MRSReg;
1936     Op->SysReg.MSRReg = MSRReg;
1937     Op->SysReg.PStateField = PStateField;
1938     Op->StartLoc = S;
1939     Op->EndLoc = S;
1940     return Op;
1941   }
1942 
1943   static std::unique_ptr<AArch64Operand> CreateSysCR(unsigned Val, SMLoc S,
1944                                                      SMLoc E, MCContext &Ctx) {
1945     auto Op = std::make_unique<AArch64Operand>(k_SysCR, Ctx);
1946     Op->SysCRImm.Val = Val;
1947     Op->StartLoc = S;
1948     Op->EndLoc = E;
1949     return Op;
1950   }
1951 
1952   static std::unique_ptr<AArch64Operand> CreatePrefetch(unsigned Val,
1953                                                         StringRef Str,
1954                                                         SMLoc S,
1955                                                         MCContext &Ctx) {
1956     auto Op = std::make_unique<AArch64Operand>(k_Prefetch, Ctx);
1957     Op->Prefetch.Val = Val;
1958     Op->Barrier.Data = Str.data();
1959     Op->Barrier.Length = Str.size();
1960     Op->StartLoc = S;
1961     Op->EndLoc = S;
1962     return Op;
1963   }
1964 
1965   static std::unique_ptr<AArch64Operand> CreatePSBHint(unsigned Val,
1966                                                        StringRef Str,
1967                                                        SMLoc S,
1968                                                        MCContext &Ctx) {
1969     auto Op = std::make_unique<AArch64Operand>(k_PSBHint, Ctx);
1970     Op->PSBHint.Val = Val;
1971     Op->PSBHint.Data = Str.data();
1972     Op->PSBHint.Length = Str.size();
1973     Op->StartLoc = S;
1974     Op->EndLoc = S;
1975     return Op;
1976   }
1977 
1978   static std::unique_ptr<AArch64Operand> CreateBTIHint(unsigned Val,
1979                                                        StringRef Str,
1980                                                        SMLoc S,
1981                                                        MCContext &Ctx) {
1982     auto Op = std::make_unique<AArch64Operand>(k_BTIHint, Ctx);
1983     Op->BTIHint.Val = Val << 1 | 32;
1984     Op->BTIHint.Data = Str.data();
1985     Op->BTIHint.Length = Str.size();
1986     Op->StartLoc = S;
1987     Op->EndLoc = S;
1988     return Op;
1989   }
1990 
1991   static std::unique_ptr<AArch64Operand>
1992   CreateShiftExtend(AArch64_AM::ShiftExtendType ShOp, unsigned Val,
1993                     bool HasExplicitAmount, SMLoc S, SMLoc E, MCContext &Ctx) {
1994     auto Op = std::make_unique<AArch64Operand>(k_ShiftExtend, Ctx);
1995     Op->ShiftExtend.Type = ShOp;
1996     Op->ShiftExtend.Amount = Val;
1997     Op->ShiftExtend.HasExplicitAmount = HasExplicitAmount;
1998     Op->StartLoc = S;
1999     Op->EndLoc = E;
2000     return Op;
2001   }
2002 };
2003 
2004 } // end anonymous namespace.
2005 
2006 void AArch64Operand::print(raw_ostream &OS) const {
2007   switch (Kind) {
2008   case k_FPImm:
2009     OS << "<fpimm " << getFPImm().bitcastToAPInt().getZExtValue();
2010     if (!getFPImmIsExact())
2011       OS << " (inexact)";
2012     OS << ">";
2013     break;
2014   case k_Barrier: {
2015     StringRef Name = getBarrierName();
2016     if (!Name.empty())
2017       OS << "<barrier " << Name << ">";
2018     else
2019       OS << "<barrier invalid #" << getBarrier() << ">";
2020     break;
2021   }
2022   case k_Immediate:
2023     OS << *getImm();
2024     break;
2025   case k_ShiftedImm: {
2026     unsigned Shift = getShiftedImmShift();
2027     OS << "<shiftedimm ";
2028     OS << *getShiftedImmVal();
2029     OS << ", lsl #" << AArch64_AM::getShiftValue(Shift) << ">";
2030     break;
2031   }
2032   case k_CondCode:
2033     OS << "<condcode " << getCondCode() << ">";
2034     break;
2035   case k_VectorList: {
2036     OS << "<vectorlist ";
2037     unsigned Reg = getVectorListStart();
2038     for (unsigned i = 0, e = getVectorListCount(); i != e; ++i)
2039       OS << Reg + i << " ";
2040     OS << ">";
2041     break;
2042   }
2043   case k_VectorIndex:
2044     OS << "<vectorindex " << getVectorIndex() << ">";
2045     break;
2046   case k_SysReg:
2047     OS << "<sysreg: " << getSysReg() << '>';
2048     break;
2049   case k_Token:
2050     OS << "'" << getToken() << "'";
2051     break;
2052   case k_SysCR:
2053     OS << "c" << getSysCR();
2054     break;
2055   case k_Prefetch: {
2056     StringRef Name = getPrefetchName();
2057     if (!Name.empty())
2058       OS << "<prfop " << Name << ">";
2059     else
2060       OS << "<prfop invalid #" << getPrefetch() << ">";
2061     break;
2062   }
2063   case k_PSBHint:
2064     OS << getPSBHintName();
2065     break;
2066   case k_Register:
2067     OS << "<register " << getReg() << ">";
2068     if (!getShiftExtendAmount() && !hasShiftExtendAmount())
2069       break;
2070     LLVM_FALLTHROUGH;
2071   case k_BTIHint:
2072     OS << getBTIHintName();
2073     break;
2074   case k_ShiftExtend:
2075     OS << "<" << AArch64_AM::getShiftExtendName(getShiftExtendType()) << " #"
2076        << getShiftExtendAmount();
2077     if (!hasShiftExtendAmount())
2078       OS << "<imp>";
2079     OS << '>';
2080     break;
2081   }
2082 }
2083 
2084 /// @name Auto-generated Match Functions
2085 /// {
2086 
2087 static unsigned MatchRegisterName(StringRef Name);
2088 
2089 /// }
2090 
2091 static unsigned MatchNeonVectorRegName(StringRef Name) {
2092   return StringSwitch<unsigned>(Name.lower())
2093       .Case("v0", AArch64::Q0)
2094       .Case("v1", AArch64::Q1)
2095       .Case("v2", AArch64::Q2)
2096       .Case("v3", AArch64::Q3)
2097       .Case("v4", AArch64::Q4)
2098       .Case("v5", AArch64::Q5)
2099       .Case("v6", AArch64::Q6)
2100       .Case("v7", AArch64::Q7)
2101       .Case("v8", AArch64::Q8)
2102       .Case("v9", AArch64::Q9)
2103       .Case("v10", AArch64::Q10)
2104       .Case("v11", AArch64::Q11)
2105       .Case("v12", AArch64::Q12)
2106       .Case("v13", AArch64::Q13)
2107       .Case("v14", AArch64::Q14)
2108       .Case("v15", AArch64::Q15)
2109       .Case("v16", AArch64::Q16)
2110       .Case("v17", AArch64::Q17)
2111       .Case("v18", AArch64::Q18)
2112       .Case("v19", AArch64::Q19)
2113       .Case("v20", AArch64::Q20)
2114       .Case("v21", AArch64::Q21)
2115       .Case("v22", AArch64::Q22)
2116       .Case("v23", AArch64::Q23)
2117       .Case("v24", AArch64::Q24)
2118       .Case("v25", AArch64::Q25)
2119       .Case("v26", AArch64::Q26)
2120       .Case("v27", AArch64::Q27)
2121       .Case("v28", AArch64::Q28)
2122       .Case("v29", AArch64::Q29)
2123       .Case("v30", AArch64::Q30)
2124       .Case("v31", AArch64::Q31)
2125       .Default(0);
2126 }
2127 
2128 /// Returns an optional pair of (#elements, element-width) if Suffix
2129 /// is a valid vector kind. Where the number of elements in a vector
2130 /// or the vector width is implicit or explicitly unknown (but still a
2131 /// valid suffix kind), 0 is used.
2132 static Optional<std::pair<int, int>> parseVectorKind(StringRef Suffix,
2133                                                      RegKind VectorKind) {
2134   std::pair<int, int> Res = {-1, -1};
2135 
2136   switch (VectorKind) {
2137   case RegKind::NeonVector:
2138     Res =
2139         StringSwitch<std::pair<int, int>>(Suffix.lower())
2140             .Case("", {0, 0})
2141             .Case(".1d", {1, 64})
2142             .Case(".1q", {1, 128})
2143             // '.2h' needed for fp16 scalar pairwise reductions
2144             .Case(".2h", {2, 16})
2145             .Case(".2s", {2, 32})
2146             .Case(".2d", {2, 64})
2147             // '.4b' is another special case for the ARMv8.2a dot product
2148             // operand
2149             .Case(".4b", {4, 8})
2150             .Case(".4h", {4, 16})
2151             .Case(".4s", {4, 32})
2152             .Case(".8b", {8, 8})
2153             .Case(".8h", {8, 16})
2154             .Case(".16b", {16, 8})
2155             // Accept the width neutral ones, too, for verbose syntax. If those
2156             // aren't used in the right places, the token operand won't match so
2157             // all will work out.
2158             .Case(".b", {0, 8})
2159             .Case(".h", {0, 16})
2160             .Case(".s", {0, 32})
2161             .Case(".d", {0, 64})
2162             .Default({-1, -1});
2163     break;
2164   case RegKind::SVEPredicateVector:
2165   case RegKind::SVEDataVector:
2166     Res = StringSwitch<std::pair<int, int>>(Suffix.lower())
2167               .Case("", {0, 0})
2168               .Case(".b", {0, 8})
2169               .Case(".h", {0, 16})
2170               .Case(".s", {0, 32})
2171               .Case(".d", {0, 64})
2172               .Case(".q", {0, 128})
2173               .Default({-1, -1});
2174     break;
2175   default:
2176     llvm_unreachable("Unsupported RegKind");
2177   }
2178 
2179   if (Res == std::make_pair(-1, -1))
2180     return Optional<std::pair<int, int>>();
2181 
2182   return Optional<std::pair<int, int>>(Res);
2183 }
2184 
2185 static bool isValidVectorKind(StringRef Suffix, RegKind VectorKind) {
2186   return parseVectorKind(Suffix, VectorKind).hasValue();
2187 }
2188 
2189 static unsigned matchSVEDataVectorRegName(StringRef Name) {
2190   return StringSwitch<unsigned>(Name.lower())
2191       .Case("z0", AArch64::Z0)
2192       .Case("z1", AArch64::Z1)
2193       .Case("z2", AArch64::Z2)
2194       .Case("z3", AArch64::Z3)
2195       .Case("z4", AArch64::Z4)
2196       .Case("z5", AArch64::Z5)
2197       .Case("z6", AArch64::Z6)
2198       .Case("z7", AArch64::Z7)
2199       .Case("z8", AArch64::Z8)
2200       .Case("z9", AArch64::Z9)
2201       .Case("z10", AArch64::Z10)
2202       .Case("z11", AArch64::Z11)
2203       .Case("z12", AArch64::Z12)
2204       .Case("z13", AArch64::Z13)
2205       .Case("z14", AArch64::Z14)
2206       .Case("z15", AArch64::Z15)
2207       .Case("z16", AArch64::Z16)
2208       .Case("z17", AArch64::Z17)
2209       .Case("z18", AArch64::Z18)
2210       .Case("z19", AArch64::Z19)
2211       .Case("z20", AArch64::Z20)
2212       .Case("z21", AArch64::Z21)
2213       .Case("z22", AArch64::Z22)
2214       .Case("z23", AArch64::Z23)
2215       .Case("z24", AArch64::Z24)
2216       .Case("z25", AArch64::Z25)
2217       .Case("z26", AArch64::Z26)
2218       .Case("z27", AArch64::Z27)
2219       .Case("z28", AArch64::Z28)
2220       .Case("z29", AArch64::Z29)
2221       .Case("z30", AArch64::Z30)
2222       .Case("z31", AArch64::Z31)
2223       .Default(0);
2224 }
2225 
2226 static unsigned matchSVEPredicateVectorRegName(StringRef Name) {
2227   return StringSwitch<unsigned>(Name.lower())
2228       .Case("p0", AArch64::P0)
2229       .Case("p1", AArch64::P1)
2230       .Case("p2", AArch64::P2)
2231       .Case("p3", AArch64::P3)
2232       .Case("p4", AArch64::P4)
2233       .Case("p5", AArch64::P5)
2234       .Case("p6", AArch64::P6)
2235       .Case("p7", AArch64::P7)
2236       .Case("p8", AArch64::P8)
2237       .Case("p9", AArch64::P9)
2238       .Case("p10", AArch64::P10)
2239       .Case("p11", AArch64::P11)
2240       .Case("p12", AArch64::P12)
2241       .Case("p13", AArch64::P13)
2242       .Case("p14", AArch64::P14)
2243       .Case("p15", AArch64::P15)
2244       .Default(0);
2245 }
2246 
2247 bool AArch64AsmParser::ParseRegister(unsigned &RegNo, SMLoc &StartLoc,
2248                                      SMLoc &EndLoc) {
2249   return tryParseRegister(RegNo, StartLoc, EndLoc) != MatchOperand_Success;
2250 }
2251 
2252 OperandMatchResultTy AArch64AsmParser::tryParseRegister(unsigned &RegNo,
2253                                                         SMLoc &StartLoc,
2254                                                         SMLoc &EndLoc) {
2255   StartLoc = getLoc();
2256   auto Res = tryParseScalarRegister(RegNo);
2257   EndLoc = SMLoc::getFromPointer(getLoc().getPointer() - 1);
2258   return Res;
2259 }
2260 
2261 // Matches a register name or register alias previously defined by '.req'
2262 unsigned AArch64AsmParser::matchRegisterNameAlias(StringRef Name,
2263                                                   RegKind Kind) {
2264   unsigned RegNum = 0;
2265   if ((RegNum = matchSVEDataVectorRegName(Name)))
2266     return Kind == RegKind::SVEDataVector ? RegNum : 0;
2267 
2268   if ((RegNum = matchSVEPredicateVectorRegName(Name)))
2269     return Kind == RegKind::SVEPredicateVector ? RegNum : 0;
2270 
2271   if ((RegNum = MatchNeonVectorRegName(Name)))
2272     return Kind == RegKind::NeonVector ? RegNum : 0;
2273 
2274   // The parsed register must be of RegKind Scalar
2275   if ((RegNum = MatchRegisterName(Name)))
2276     return Kind == RegKind::Scalar ? RegNum : 0;
2277 
2278   if (!RegNum) {
2279     // Handle a few common aliases of registers.
2280     if (auto RegNum = StringSwitch<unsigned>(Name.lower())
2281                     .Case("fp", AArch64::FP)
2282                     .Case("lr",  AArch64::LR)
2283                     .Case("x31", AArch64::XZR)
2284                     .Case("w31", AArch64::WZR)
2285                     .Default(0))
2286       return Kind == RegKind::Scalar ? RegNum : 0;
2287 
2288     // Check for aliases registered via .req. Canonicalize to lower case.
2289     // That's more consistent since register names are case insensitive, and
2290     // it's how the original entry was passed in from MC/MCParser/AsmParser.
2291     auto Entry = RegisterReqs.find(Name.lower());
2292     if (Entry == RegisterReqs.end())
2293       return 0;
2294 
2295     // set RegNum if the match is the right kind of register
2296     if (Kind == Entry->getValue().first)
2297       RegNum = Entry->getValue().second;
2298   }
2299   return RegNum;
2300 }
2301 
2302 /// tryParseScalarRegister - Try to parse a register name. The token must be an
2303 /// Identifier when called, and if it is a register name the token is eaten and
2304 /// the register is added to the operand list.
2305 OperandMatchResultTy
2306 AArch64AsmParser::tryParseScalarRegister(unsigned &RegNum) {
2307   MCAsmParser &Parser = getParser();
2308   const AsmToken &Tok = Parser.getTok();
2309   if (Tok.isNot(AsmToken::Identifier))
2310     return MatchOperand_NoMatch;
2311 
2312   std::string lowerCase = Tok.getString().lower();
2313   unsigned Reg = matchRegisterNameAlias(lowerCase, RegKind::Scalar);
2314   if (Reg == 0)
2315     return MatchOperand_NoMatch;
2316 
2317   RegNum = Reg;
2318   Parser.Lex(); // Eat identifier token.
2319   return MatchOperand_Success;
2320 }
2321 
2322 /// tryParseSysCROperand - Try to parse a system instruction CR operand name.
2323 OperandMatchResultTy
2324 AArch64AsmParser::tryParseSysCROperand(OperandVector &Operands) {
2325   MCAsmParser &Parser = getParser();
2326   SMLoc S = getLoc();
2327 
2328   if (Parser.getTok().isNot(AsmToken::Identifier)) {
2329     Error(S, "Expected cN operand where 0 <= N <= 15");
2330     return MatchOperand_ParseFail;
2331   }
2332 
2333   StringRef Tok = Parser.getTok().getIdentifier();
2334   if (Tok[0] != 'c' && Tok[0] != 'C') {
2335     Error(S, "Expected cN operand where 0 <= N <= 15");
2336     return MatchOperand_ParseFail;
2337   }
2338 
2339   uint32_t CRNum;
2340   bool BadNum = Tok.drop_front().getAsInteger(10, CRNum);
2341   if (BadNum || CRNum > 15) {
2342     Error(S, "Expected cN operand where 0 <= N <= 15");
2343     return MatchOperand_ParseFail;
2344   }
2345 
2346   Parser.Lex(); // Eat identifier token.
2347   Operands.push_back(
2348       AArch64Operand::CreateSysCR(CRNum, S, getLoc(), getContext()));
2349   return MatchOperand_Success;
2350 }
2351 
2352 /// tryParsePrefetch - Try to parse a prefetch operand.
2353 template <bool IsSVEPrefetch>
2354 OperandMatchResultTy
2355 AArch64AsmParser::tryParsePrefetch(OperandVector &Operands) {
2356   MCAsmParser &Parser = getParser();
2357   SMLoc S = getLoc();
2358   const AsmToken &Tok = Parser.getTok();
2359 
2360   auto LookupByName = [](StringRef N) {
2361     if (IsSVEPrefetch) {
2362       if (auto Res = AArch64SVEPRFM::lookupSVEPRFMByName(N))
2363         return Optional<unsigned>(Res->Encoding);
2364     } else if (auto Res = AArch64PRFM::lookupPRFMByName(N))
2365       return Optional<unsigned>(Res->Encoding);
2366     return Optional<unsigned>();
2367   };
2368 
2369   auto LookupByEncoding = [](unsigned E) {
2370     if (IsSVEPrefetch) {
2371       if (auto Res = AArch64SVEPRFM::lookupSVEPRFMByEncoding(E))
2372         return Optional<StringRef>(Res->Name);
2373     } else if (auto Res = AArch64PRFM::lookupPRFMByEncoding(E))
2374       return Optional<StringRef>(Res->Name);
2375     return Optional<StringRef>();
2376   };
2377   unsigned MaxVal = IsSVEPrefetch ? 15 : 31;
2378 
2379   // Either an identifier for named values or a 5-bit immediate.
2380   // Eat optional hash.
2381   if (parseOptionalToken(AsmToken::Hash) ||
2382       Tok.is(AsmToken::Integer)) {
2383     const MCExpr *ImmVal;
2384     if (getParser().parseExpression(ImmVal))
2385       return MatchOperand_ParseFail;
2386 
2387     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(ImmVal);
2388     if (!MCE) {
2389       TokError("immediate value expected for prefetch operand");
2390       return MatchOperand_ParseFail;
2391     }
2392     unsigned prfop = MCE->getValue();
2393     if (prfop > MaxVal) {
2394       TokError("prefetch operand out of range, [0," + utostr(MaxVal) +
2395                "] expected");
2396       return MatchOperand_ParseFail;
2397     }
2398 
2399     auto PRFM = LookupByEncoding(MCE->getValue());
2400     Operands.push_back(AArch64Operand::CreatePrefetch(
2401         prfop, PRFM.getValueOr(""), S, getContext()));
2402     return MatchOperand_Success;
2403   }
2404 
2405   if (Tok.isNot(AsmToken::Identifier)) {
2406     TokError("prefetch hint expected");
2407     return MatchOperand_ParseFail;
2408   }
2409 
2410   auto PRFM = LookupByName(Tok.getString());
2411   if (!PRFM) {
2412     TokError("prefetch hint expected");
2413     return MatchOperand_ParseFail;
2414   }
2415 
2416   Parser.Lex(); // Eat identifier token.
2417   Operands.push_back(AArch64Operand::CreatePrefetch(
2418       *PRFM, Tok.getString(), S, getContext()));
2419   return MatchOperand_Success;
2420 }
2421 
2422 /// tryParsePSBHint - Try to parse a PSB operand, mapped to Hint command
2423 OperandMatchResultTy
2424 AArch64AsmParser::tryParsePSBHint(OperandVector &Operands) {
2425   MCAsmParser &Parser = getParser();
2426   SMLoc S = getLoc();
2427   const AsmToken &Tok = Parser.getTok();
2428   if (Tok.isNot(AsmToken::Identifier)) {
2429     TokError("invalid operand for instruction");
2430     return MatchOperand_ParseFail;
2431   }
2432 
2433   auto PSB = AArch64PSBHint::lookupPSBByName(Tok.getString());
2434   if (!PSB) {
2435     TokError("invalid operand for instruction");
2436     return MatchOperand_ParseFail;
2437   }
2438 
2439   Parser.Lex(); // Eat identifier token.
2440   Operands.push_back(AArch64Operand::CreatePSBHint(
2441       PSB->Encoding, Tok.getString(), S, getContext()));
2442   return MatchOperand_Success;
2443 }
2444 
2445 /// tryParseBTIHint - Try to parse a BTI operand, mapped to Hint command
2446 OperandMatchResultTy
2447 AArch64AsmParser::tryParseBTIHint(OperandVector &Operands) {
2448   MCAsmParser &Parser = getParser();
2449   SMLoc S = getLoc();
2450   const AsmToken &Tok = Parser.getTok();
2451   if (Tok.isNot(AsmToken::Identifier)) {
2452     TokError("invalid operand for instruction");
2453     return MatchOperand_ParseFail;
2454   }
2455 
2456   auto BTI = AArch64BTIHint::lookupBTIByName(Tok.getString());
2457   if (!BTI) {
2458     TokError("invalid operand for instruction");
2459     return MatchOperand_ParseFail;
2460   }
2461 
2462   Parser.Lex(); // Eat identifier token.
2463   Operands.push_back(AArch64Operand::CreateBTIHint(
2464       BTI->Encoding, Tok.getString(), S, getContext()));
2465   return MatchOperand_Success;
2466 }
2467 
2468 /// tryParseAdrpLabel - Parse and validate a source label for the ADRP
2469 /// instruction.
2470 OperandMatchResultTy
2471 AArch64AsmParser::tryParseAdrpLabel(OperandVector &Operands) {
2472   MCAsmParser &Parser = getParser();
2473   SMLoc S = getLoc();
2474   const MCExpr *Expr = nullptr;
2475 
2476   if (Parser.getTok().is(AsmToken::Hash)) {
2477     Parser.Lex(); // Eat hash token.
2478   }
2479 
2480   if (parseSymbolicImmVal(Expr))
2481     return MatchOperand_ParseFail;
2482 
2483   AArch64MCExpr::VariantKind ELFRefKind;
2484   MCSymbolRefExpr::VariantKind DarwinRefKind;
2485   int64_t Addend;
2486   if (classifySymbolRef(Expr, ELFRefKind, DarwinRefKind, Addend)) {
2487     if (DarwinRefKind == MCSymbolRefExpr::VK_None &&
2488         ELFRefKind == AArch64MCExpr::VK_INVALID) {
2489       // No modifier was specified at all; this is the syntax for an ELF basic
2490       // ADRP relocation (unfortunately).
2491       Expr =
2492           AArch64MCExpr::create(Expr, AArch64MCExpr::VK_ABS_PAGE, getContext());
2493     } else if ((DarwinRefKind == MCSymbolRefExpr::VK_GOTPAGE ||
2494                 DarwinRefKind == MCSymbolRefExpr::VK_TLVPPAGE) &&
2495                Addend != 0) {
2496       Error(S, "gotpage label reference not allowed an addend");
2497       return MatchOperand_ParseFail;
2498     } else if (DarwinRefKind != MCSymbolRefExpr::VK_PAGE &&
2499                DarwinRefKind != MCSymbolRefExpr::VK_GOTPAGE &&
2500                DarwinRefKind != MCSymbolRefExpr::VK_TLVPPAGE &&
2501                ELFRefKind != AArch64MCExpr::VK_ABS_PAGE_NC &&
2502                ELFRefKind != AArch64MCExpr::VK_GOT_PAGE &&
2503                ELFRefKind != AArch64MCExpr::VK_GOTTPREL_PAGE &&
2504                ELFRefKind != AArch64MCExpr::VK_TLSDESC_PAGE) {
2505       // The operand must be an @page or @gotpage qualified symbolref.
2506       Error(S, "page or gotpage label reference expected");
2507       return MatchOperand_ParseFail;
2508     }
2509   }
2510 
2511   // We have either a label reference possibly with addend or an immediate. The
2512   // addend is a raw value here. The linker will adjust it to only reference the
2513   // page.
2514   SMLoc E = SMLoc::getFromPointer(getLoc().getPointer() - 1);
2515   Operands.push_back(AArch64Operand::CreateImm(Expr, S, E, getContext()));
2516 
2517   return MatchOperand_Success;
2518 }
2519 
2520 /// tryParseAdrLabel - Parse and validate a source label for the ADR
2521 /// instruction.
2522 OperandMatchResultTy
2523 AArch64AsmParser::tryParseAdrLabel(OperandVector &Operands) {
2524   SMLoc S = getLoc();
2525   const MCExpr *Expr = nullptr;
2526 
2527   // Leave anything with a bracket to the default for SVE
2528   if (getParser().getTok().is(AsmToken::LBrac))
2529     return MatchOperand_NoMatch;
2530 
2531   if (getParser().getTok().is(AsmToken::Hash))
2532     getParser().Lex(); // Eat hash token.
2533 
2534   if (parseSymbolicImmVal(Expr))
2535     return MatchOperand_ParseFail;
2536 
2537   AArch64MCExpr::VariantKind ELFRefKind;
2538   MCSymbolRefExpr::VariantKind DarwinRefKind;
2539   int64_t Addend;
2540   if (classifySymbolRef(Expr, ELFRefKind, DarwinRefKind, Addend)) {
2541     if (DarwinRefKind == MCSymbolRefExpr::VK_None &&
2542         ELFRefKind == AArch64MCExpr::VK_INVALID) {
2543       // No modifier was specified at all; this is the syntax for an ELF basic
2544       // ADR relocation (unfortunately).
2545       Expr = AArch64MCExpr::create(Expr, AArch64MCExpr::VK_ABS, getContext());
2546     } else {
2547       Error(S, "unexpected adr label");
2548       return MatchOperand_ParseFail;
2549     }
2550   }
2551 
2552   SMLoc E = SMLoc::getFromPointer(getLoc().getPointer() - 1);
2553   Operands.push_back(AArch64Operand::CreateImm(Expr, S, E, getContext()));
2554   return MatchOperand_Success;
2555 }
2556 
2557 /// tryParseFPImm - A floating point immediate expression operand.
2558 template<bool AddFPZeroAsLiteral>
2559 OperandMatchResultTy
2560 AArch64AsmParser::tryParseFPImm(OperandVector &Operands) {
2561   MCAsmParser &Parser = getParser();
2562   SMLoc S = getLoc();
2563 
2564   bool Hash = parseOptionalToken(AsmToken::Hash);
2565 
2566   // Handle negation, as that still comes through as a separate token.
2567   bool isNegative = parseOptionalToken(AsmToken::Minus);
2568 
2569   const AsmToken &Tok = Parser.getTok();
2570   if (!Tok.is(AsmToken::Real) && !Tok.is(AsmToken::Integer)) {
2571     if (!Hash)
2572       return MatchOperand_NoMatch;
2573     TokError("invalid floating point immediate");
2574     return MatchOperand_ParseFail;
2575   }
2576 
2577   // Parse hexadecimal representation.
2578   if (Tok.is(AsmToken::Integer) && Tok.getString().startswith("0x")) {
2579     if (Tok.getIntVal() > 255 || isNegative) {
2580       TokError("encoded floating point value out of range");
2581       return MatchOperand_ParseFail;
2582     }
2583 
2584     APFloat F((double)AArch64_AM::getFPImmFloat(Tok.getIntVal()));
2585     Operands.push_back(
2586         AArch64Operand::CreateFPImm(F, true, S, getContext()));
2587   } else {
2588     // Parse FP representation.
2589     APFloat RealVal(APFloat::IEEEdouble());
2590     auto StatusOrErr =
2591         RealVal.convertFromString(Tok.getString(), APFloat::rmTowardZero);
2592     if (errorToBool(StatusOrErr.takeError())) {
2593       TokError("invalid floating point representation");
2594       return MatchOperand_ParseFail;
2595     }
2596 
2597     if (isNegative)
2598       RealVal.changeSign();
2599 
2600     if (AddFPZeroAsLiteral && RealVal.isPosZero()) {
2601       Operands.push_back(
2602           AArch64Operand::CreateToken("#0", false, S, getContext()));
2603       Operands.push_back(
2604           AArch64Operand::CreateToken(".0", false, S, getContext()));
2605     } else
2606       Operands.push_back(AArch64Operand::CreateFPImm(
2607           RealVal, *StatusOrErr == APFloat::opOK, S, getContext()));
2608   }
2609 
2610   Parser.Lex(); // Eat the token.
2611 
2612   return MatchOperand_Success;
2613 }
2614 
2615 /// tryParseImmWithOptionalShift - Parse immediate operand, optionally with
2616 /// a shift suffix, for example '#1, lsl #12'.
2617 OperandMatchResultTy
2618 AArch64AsmParser::tryParseImmWithOptionalShift(OperandVector &Operands) {
2619   MCAsmParser &Parser = getParser();
2620   SMLoc S = getLoc();
2621 
2622   if (Parser.getTok().is(AsmToken::Hash))
2623     Parser.Lex(); // Eat '#'
2624   else if (Parser.getTok().isNot(AsmToken::Integer))
2625     // Operand should start from # or should be integer, emit error otherwise.
2626     return MatchOperand_NoMatch;
2627 
2628   const MCExpr *Imm = nullptr;
2629   if (parseSymbolicImmVal(Imm))
2630     return MatchOperand_ParseFail;
2631   else if (Parser.getTok().isNot(AsmToken::Comma)) {
2632     SMLoc E = Parser.getTok().getLoc();
2633     Operands.push_back(
2634         AArch64Operand::CreateImm(Imm, S, E, getContext()));
2635     return MatchOperand_Success;
2636   }
2637 
2638   // Eat ','
2639   Parser.Lex();
2640 
2641   // The optional operand must be "lsl #N" where N is non-negative.
2642   if (!Parser.getTok().is(AsmToken::Identifier) ||
2643       !Parser.getTok().getIdentifier().equals_lower("lsl")) {
2644     Error(Parser.getTok().getLoc(), "only 'lsl #+N' valid after immediate");
2645     return MatchOperand_ParseFail;
2646   }
2647 
2648   // Eat 'lsl'
2649   Parser.Lex();
2650 
2651   parseOptionalToken(AsmToken::Hash);
2652 
2653   if (Parser.getTok().isNot(AsmToken::Integer)) {
2654     Error(Parser.getTok().getLoc(), "only 'lsl #+N' valid after immediate");
2655     return MatchOperand_ParseFail;
2656   }
2657 
2658   int64_t ShiftAmount = Parser.getTok().getIntVal();
2659 
2660   if (ShiftAmount < 0) {
2661     Error(Parser.getTok().getLoc(), "positive shift amount required");
2662     return MatchOperand_ParseFail;
2663   }
2664   Parser.Lex(); // Eat the number
2665 
2666   // Just in case the optional lsl #0 is used for immediates other than zero.
2667   if (ShiftAmount == 0 && Imm != nullptr) {
2668     SMLoc E = Parser.getTok().getLoc();
2669     Operands.push_back(AArch64Operand::CreateImm(Imm, S, E, getContext()));
2670     return MatchOperand_Success;
2671   }
2672 
2673   SMLoc E = Parser.getTok().getLoc();
2674   Operands.push_back(AArch64Operand::CreateShiftedImm(Imm, ShiftAmount,
2675                                                       S, E, getContext()));
2676   return MatchOperand_Success;
2677 }
2678 
2679 /// parseCondCodeString - Parse a Condition Code string.
2680 AArch64CC::CondCode AArch64AsmParser::parseCondCodeString(StringRef Cond) {
2681   AArch64CC::CondCode CC = StringSwitch<AArch64CC::CondCode>(Cond.lower())
2682                     .Case("eq", AArch64CC::EQ)
2683                     .Case("ne", AArch64CC::NE)
2684                     .Case("cs", AArch64CC::HS)
2685                     .Case("hs", AArch64CC::HS)
2686                     .Case("cc", AArch64CC::LO)
2687                     .Case("lo", AArch64CC::LO)
2688                     .Case("mi", AArch64CC::MI)
2689                     .Case("pl", AArch64CC::PL)
2690                     .Case("vs", AArch64CC::VS)
2691                     .Case("vc", AArch64CC::VC)
2692                     .Case("hi", AArch64CC::HI)
2693                     .Case("ls", AArch64CC::LS)
2694                     .Case("ge", AArch64CC::GE)
2695                     .Case("lt", AArch64CC::LT)
2696                     .Case("gt", AArch64CC::GT)
2697                     .Case("le", AArch64CC::LE)
2698                     .Case("al", AArch64CC::AL)
2699                     .Case("nv", AArch64CC::NV)
2700                     .Default(AArch64CC::Invalid);
2701 
2702   if (CC == AArch64CC::Invalid &&
2703       getSTI().getFeatureBits()[AArch64::FeatureSVE])
2704     CC = StringSwitch<AArch64CC::CondCode>(Cond.lower())
2705                     .Case("none",  AArch64CC::EQ)
2706                     .Case("any",   AArch64CC::NE)
2707                     .Case("nlast", AArch64CC::HS)
2708                     .Case("last",  AArch64CC::LO)
2709                     .Case("first", AArch64CC::MI)
2710                     .Case("nfrst", AArch64CC::PL)
2711                     .Case("pmore", AArch64CC::HI)
2712                     .Case("plast", AArch64CC::LS)
2713                     .Case("tcont", AArch64CC::GE)
2714                     .Case("tstop", AArch64CC::LT)
2715                     .Default(AArch64CC::Invalid);
2716 
2717   return CC;
2718 }
2719 
2720 /// parseCondCode - Parse a Condition Code operand.
2721 bool AArch64AsmParser::parseCondCode(OperandVector &Operands,
2722                                      bool invertCondCode) {
2723   MCAsmParser &Parser = getParser();
2724   SMLoc S = getLoc();
2725   const AsmToken &Tok = Parser.getTok();
2726   assert(Tok.is(AsmToken::Identifier) && "Token is not an Identifier");
2727 
2728   StringRef Cond = Tok.getString();
2729   AArch64CC::CondCode CC = parseCondCodeString(Cond);
2730   if (CC == AArch64CC::Invalid)
2731     return TokError("invalid condition code");
2732   Parser.Lex(); // Eat identifier token.
2733 
2734   if (invertCondCode) {
2735     if (CC == AArch64CC::AL || CC == AArch64CC::NV)
2736       return TokError("condition codes AL and NV are invalid for this instruction");
2737     CC = AArch64CC::getInvertedCondCode(AArch64CC::CondCode(CC));
2738   }
2739 
2740   Operands.push_back(
2741       AArch64Operand::CreateCondCode(CC, S, getLoc(), getContext()));
2742   return false;
2743 }
2744 
2745 /// tryParseOptionalShift - Some operands take an optional shift argument. Parse
2746 /// them if present.
2747 OperandMatchResultTy
2748 AArch64AsmParser::tryParseOptionalShiftExtend(OperandVector &Operands) {
2749   MCAsmParser &Parser = getParser();
2750   const AsmToken &Tok = Parser.getTok();
2751   std::string LowerID = Tok.getString().lower();
2752   AArch64_AM::ShiftExtendType ShOp =
2753       StringSwitch<AArch64_AM::ShiftExtendType>(LowerID)
2754           .Case("lsl", AArch64_AM::LSL)
2755           .Case("lsr", AArch64_AM::LSR)
2756           .Case("asr", AArch64_AM::ASR)
2757           .Case("ror", AArch64_AM::ROR)
2758           .Case("msl", AArch64_AM::MSL)
2759           .Case("uxtb", AArch64_AM::UXTB)
2760           .Case("uxth", AArch64_AM::UXTH)
2761           .Case("uxtw", AArch64_AM::UXTW)
2762           .Case("uxtx", AArch64_AM::UXTX)
2763           .Case("sxtb", AArch64_AM::SXTB)
2764           .Case("sxth", AArch64_AM::SXTH)
2765           .Case("sxtw", AArch64_AM::SXTW)
2766           .Case("sxtx", AArch64_AM::SXTX)
2767           .Default(AArch64_AM::InvalidShiftExtend);
2768 
2769   if (ShOp == AArch64_AM::InvalidShiftExtend)
2770     return MatchOperand_NoMatch;
2771 
2772   SMLoc S = Tok.getLoc();
2773   Parser.Lex();
2774 
2775   bool Hash = parseOptionalToken(AsmToken::Hash);
2776 
2777   if (!Hash && getLexer().isNot(AsmToken::Integer)) {
2778     if (ShOp == AArch64_AM::LSL || ShOp == AArch64_AM::LSR ||
2779         ShOp == AArch64_AM::ASR || ShOp == AArch64_AM::ROR ||
2780         ShOp == AArch64_AM::MSL) {
2781       // We expect a number here.
2782       TokError("expected #imm after shift specifier");
2783       return MatchOperand_ParseFail;
2784     }
2785 
2786     // "extend" type operations don't need an immediate, #0 is implicit.
2787     SMLoc E = SMLoc::getFromPointer(getLoc().getPointer() - 1);
2788     Operands.push_back(
2789         AArch64Operand::CreateShiftExtend(ShOp, 0, false, S, E, getContext()));
2790     return MatchOperand_Success;
2791   }
2792 
2793   // Make sure we do actually have a number, identifier or a parenthesized
2794   // expression.
2795   SMLoc E = Parser.getTok().getLoc();
2796   if (!Parser.getTok().is(AsmToken::Integer) &&
2797       !Parser.getTok().is(AsmToken::LParen) &&
2798       !Parser.getTok().is(AsmToken::Identifier)) {
2799     Error(E, "expected integer shift amount");
2800     return MatchOperand_ParseFail;
2801   }
2802 
2803   const MCExpr *ImmVal;
2804   if (getParser().parseExpression(ImmVal))
2805     return MatchOperand_ParseFail;
2806 
2807   const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(ImmVal);
2808   if (!MCE) {
2809     Error(E, "expected constant '#imm' after shift specifier");
2810     return MatchOperand_ParseFail;
2811   }
2812 
2813   E = SMLoc::getFromPointer(getLoc().getPointer() - 1);
2814   Operands.push_back(AArch64Operand::CreateShiftExtend(
2815       ShOp, MCE->getValue(), true, S, E, getContext()));
2816   return MatchOperand_Success;
2817 }
2818 
2819 static const struct Extension {
2820   const char *Name;
2821   const FeatureBitset Features;
2822 } ExtensionMap[] = {
2823     {"crc", {AArch64::FeatureCRC}},
2824     {"sm4", {AArch64::FeatureSM4}},
2825     {"sha3", {AArch64::FeatureSHA3}},
2826     {"sha2", {AArch64::FeatureSHA2}},
2827     {"aes", {AArch64::FeatureAES}},
2828     {"crypto", {AArch64::FeatureCrypto}},
2829     {"fp", {AArch64::FeatureFPARMv8}},
2830     {"simd", {AArch64::FeatureNEON}},
2831     {"ras", {AArch64::FeatureRAS}},
2832     {"lse", {AArch64::FeatureLSE}},
2833     {"predres", {AArch64::FeaturePredRes}},
2834     {"ccdp", {AArch64::FeatureCacheDeepPersist}},
2835     {"mte", {AArch64::FeatureMTE}},
2836     {"tlb-rmi", {AArch64::FeatureTLB_RMI}},
2837     {"pan-rwv", {AArch64::FeaturePAN_RWV}},
2838     {"ccpp", {AArch64::FeatureCCPP}},
2839     {"sve", {AArch64::FeatureSVE}},
2840     {"sve2", {AArch64::FeatureSVE2}},
2841     {"sve2-aes", {AArch64::FeatureSVE2AES}},
2842     {"sve2-sm4", {AArch64::FeatureSVE2SM4}},
2843     {"sve2-sha3", {AArch64::FeatureSVE2SHA3}},
2844     {"sve2-bitperm", {AArch64::FeatureSVE2BitPerm}},
2845     // FIXME: Unsupported extensions
2846     {"pan", {}},
2847     {"lor", {}},
2848     {"rdma", {}},
2849     {"profile", {}},
2850 };
2851 
2852 static void setRequiredFeatureString(FeatureBitset FBS, std::string &Str) {
2853   if (FBS[AArch64::HasV8_1aOps])
2854     Str += "ARMv8.1a";
2855   else if (FBS[AArch64::HasV8_2aOps])
2856     Str += "ARMv8.2a";
2857   else if (FBS[AArch64::HasV8_3aOps])
2858     Str += "ARMv8.3a";
2859   else if (FBS[AArch64::HasV8_4aOps])
2860     Str += "ARMv8.4a";
2861   else if (FBS[AArch64::HasV8_5aOps])
2862     Str += "ARMv8.5a";
2863   else if (FBS[AArch64::HasV8_6aOps])
2864     Str += "ARMv8.6a";
2865   else {
2866     auto ext = std::find_if(std::begin(ExtensionMap),
2867       std::end(ExtensionMap),
2868       [&](const Extension& e)
2869       // Use & in case multiple features are enabled
2870       { return (FBS & e.Features) != FeatureBitset(); }
2871     );
2872 
2873     Str += ext != std::end(ExtensionMap) ? ext->Name : "(unknown)";
2874   }
2875 }
2876 
2877 void AArch64AsmParser::createSysAlias(uint16_t Encoding, OperandVector &Operands,
2878                                       SMLoc S) {
2879   const uint16_t Op2 = Encoding & 7;
2880   const uint16_t Cm = (Encoding & 0x78) >> 3;
2881   const uint16_t Cn = (Encoding & 0x780) >> 7;
2882   const uint16_t Op1 = (Encoding & 0x3800) >> 11;
2883 
2884   const MCExpr *Expr = MCConstantExpr::create(Op1, getContext());
2885 
2886   Operands.push_back(
2887       AArch64Operand::CreateImm(Expr, S, getLoc(), getContext()));
2888   Operands.push_back(
2889       AArch64Operand::CreateSysCR(Cn, S, getLoc(), getContext()));
2890   Operands.push_back(
2891       AArch64Operand::CreateSysCR(Cm, S, getLoc(), getContext()));
2892   Expr = MCConstantExpr::create(Op2, getContext());
2893   Operands.push_back(
2894       AArch64Operand::CreateImm(Expr, S, getLoc(), getContext()));
2895 }
2896 
2897 /// parseSysAlias - The IC, DC, AT, and TLBI instructions are simple aliases for
2898 /// the SYS instruction. Parse them specially so that we create a SYS MCInst.
2899 bool AArch64AsmParser::parseSysAlias(StringRef Name, SMLoc NameLoc,
2900                                    OperandVector &Operands) {
2901   if (Name.find('.') != StringRef::npos)
2902     return TokError("invalid operand");
2903 
2904   Mnemonic = Name;
2905   Operands.push_back(
2906       AArch64Operand::CreateToken("sys", false, NameLoc, getContext()));
2907 
2908   MCAsmParser &Parser = getParser();
2909   const AsmToken &Tok = Parser.getTok();
2910   StringRef Op = Tok.getString();
2911   SMLoc S = Tok.getLoc();
2912 
2913   if (Mnemonic == "ic") {
2914     const AArch64IC::IC *IC = AArch64IC::lookupICByName(Op);
2915     if (!IC)
2916       return TokError("invalid operand for IC instruction");
2917     else if (!IC->haveFeatures(getSTI().getFeatureBits())) {
2918       std::string Str("IC " + std::string(IC->Name) + " requires ");
2919       setRequiredFeatureString(IC->getRequiredFeatures(), Str);
2920       return TokError(Str.c_str());
2921     }
2922     createSysAlias(IC->Encoding, Operands, S);
2923   } else if (Mnemonic == "dc") {
2924     const AArch64DC::DC *DC = AArch64DC::lookupDCByName(Op);
2925     if (!DC)
2926       return TokError("invalid operand for DC instruction");
2927     else if (!DC->haveFeatures(getSTI().getFeatureBits())) {
2928       std::string Str("DC " + std::string(DC->Name) + " requires ");
2929       setRequiredFeatureString(DC->getRequiredFeatures(), Str);
2930       return TokError(Str.c_str());
2931     }
2932     createSysAlias(DC->Encoding, Operands, S);
2933   } else if (Mnemonic == "at") {
2934     const AArch64AT::AT *AT = AArch64AT::lookupATByName(Op);
2935     if (!AT)
2936       return TokError("invalid operand for AT instruction");
2937     else if (!AT->haveFeatures(getSTI().getFeatureBits())) {
2938       std::string Str("AT " + std::string(AT->Name) + " requires ");
2939       setRequiredFeatureString(AT->getRequiredFeatures(), Str);
2940       return TokError(Str.c_str());
2941     }
2942     createSysAlias(AT->Encoding, Operands, S);
2943   } else if (Mnemonic == "tlbi") {
2944     const AArch64TLBI::TLBI *TLBI = AArch64TLBI::lookupTLBIByName(Op);
2945     if (!TLBI)
2946       return TokError("invalid operand for TLBI instruction");
2947     else if (!TLBI->haveFeatures(getSTI().getFeatureBits())) {
2948       std::string Str("TLBI " + std::string(TLBI->Name) + " requires ");
2949       setRequiredFeatureString(TLBI->getRequiredFeatures(), Str);
2950       return TokError(Str.c_str());
2951     }
2952     createSysAlias(TLBI->Encoding, Operands, S);
2953   } else if (Mnemonic == "cfp" || Mnemonic == "dvp" || Mnemonic == "cpp") {
2954     const AArch64PRCTX::PRCTX *PRCTX = AArch64PRCTX::lookupPRCTXByName(Op);
2955     if (!PRCTX)
2956       return TokError("invalid operand for prediction restriction instruction");
2957     else if (!PRCTX->haveFeatures(getSTI().getFeatureBits())) {
2958       std::string Str(
2959           Mnemonic.upper() + std::string(PRCTX->Name) + " requires ");
2960       setRequiredFeatureString(PRCTX->getRequiredFeatures(), Str);
2961       return TokError(Str.c_str());
2962     }
2963     uint16_t PRCTX_Op2 =
2964       Mnemonic == "cfp" ? 4 :
2965       Mnemonic == "dvp" ? 5 :
2966       Mnemonic == "cpp" ? 7 :
2967       0;
2968     assert(PRCTX_Op2 && "Invalid mnemonic for prediction restriction instruction");
2969     createSysAlias(PRCTX->Encoding << 3 | PRCTX_Op2 , Operands, S);
2970   }
2971 
2972   Parser.Lex(); // Eat operand.
2973 
2974   bool ExpectRegister = (Op.lower().find("all") == StringRef::npos);
2975   bool HasRegister = false;
2976 
2977   // Check for the optional register operand.
2978   if (parseOptionalToken(AsmToken::Comma)) {
2979     if (Tok.isNot(AsmToken::Identifier) || parseRegister(Operands))
2980       return TokError("expected register operand");
2981     HasRegister = true;
2982   }
2983 
2984   if (ExpectRegister && !HasRegister)
2985     return TokError("specified " + Mnemonic + " op requires a register");
2986   else if (!ExpectRegister && HasRegister)
2987     return TokError("specified " + Mnemonic + " op does not use a register");
2988 
2989   if (parseToken(AsmToken::EndOfStatement, "unexpected token in argument list"))
2990     return true;
2991 
2992   return false;
2993 }
2994 
2995 OperandMatchResultTy
2996 AArch64AsmParser::tryParseBarrierOperand(OperandVector &Operands) {
2997   MCAsmParser &Parser = getParser();
2998   const AsmToken &Tok = Parser.getTok();
2999 
3000   if (Mnemonic == "tsb" && Tok.isNot(AsmToken::Identifier)) {
3001     TokError("'csync' operand expected");
3002     return MatchOperand_ParseFail;
3003   // Can be either a #imm style literal or an option name
3004   } else if (parseOptionalToken(AsmToken::Hash) || Tok.is(AsmToken::Integer)) {
3005     // Immediate operand.
3006     const MCExpr *ImmVal;
3007     SMLoc ExprLoc = getLoc();
3008     if (getParser().parseExpression(ImmVal))
3009       return MatchOperand_ParseFail;
3010     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(ImmVal);
3011     if (!MCE) {
3012       Error(ExprLoc, "immediate value expected for barrier operand");
3013       return MatchOperand_ParseFail;
3014     }
3015     if (MCE->getValue() < 0 || MCE->getValue() > 15) {
3016       Error(ExprLoc, "barrier operand out of range");
3017       return MatchOperand_ParseFail;
3018     }
3019     auto DB = AArch64DB::lookupDBByEncoding(MCE->getValue());
3020     Operands.push_back(AArch64Operand::CreateBarrier(
3021         MCE->getValue(), DB ? DB->Name : "", ExprLoc, getContext()));
3022     return MatchOperand_Success;
3023   }
3024 
3025   if (Tok.isNot(AsmToken::Identifier)) {
3026     TokError("invalid operand for instruction");
3027     return MatchOperand_ParseFail;
3028   }
3029 
3030   auto TSB = AArch64TSB::lookupTSBByName(Tok.getString());
3031   // The only valid named option for ISB is 'sy'
3032   auto DB = AArch64DB::lookupDBByName(Tok.getString());
3033   if (Mnemonic == "isb" && (!DB || DB->Encoding != AArch64DB::sy)) {
3034     TokError("'sy' or #imm operand expected");
3035     return MatchOperand_ParseFail;
3036   // The only valid named option for TSB is 'csync'
3037   } else if (Mnemonic == "tsb" && (!TSB || TSB->Encoding != AArch64TSB::csync)) {
3038     TokError("'csync' operand expected");
3039     return MatchOperand_ParseFail;
3040   } else if (!DB && !TSB) {
3041     TokError("invalid barrier option name");
3042     return MatchOperand_ParseFail;
3043   }
3044 
3045   Operands.push_back(AArch64Operand::CreateBarrier(
3046       DB ? DB->Encoding : TSB->Encoding, Tok.getString(), getLoc(), getContext()));
3047   Parser.Lex(); // Consume the option
3048 
3049   return MatchOperand_Success;
3050 }
3051 
3052 OperandMatchResultTy
3053 AArch64AsmParser::tryParseSysReg(OperandVector &Operands) {
3054   MCAsmParser &Parser = getParser();
3055   const AsmToken &Tok = Parser.getTok();
3056 
3057   if (Tok.isNot(AsmToken::Identifier))
3058     return MatchOperand_NoMatch;
3059 
3060   int MRSReg, MSRReg;
3061   auto SysReg = AArch64SysReg::lookupSysRegByName(Tok.getString());
3062   if (SysReg && SysReg->haveFeatures(getSTI().getFeatureBits())) {
3063     MRSReg = SysReg->Readable ? SysReg->Encoding : -1;
3064     MSRReg = SysReg->Writeable ? SysReg->Encoding : -1;
3065   } else
3066     MRSReg = MSRReg = AArch64SysReg::parseGenericRegister(Tok.getString());
3067 
3068   auto PState = AArch64PState::lookupPStateByName(Tok.getString());
3069   unsigned PStateImm = -1;
3070   if (PState && PState->haveFeatures(getSTI().getFeatureBits()))
3071     PStateImm = PState->Encoding;
3072 
3073   Operands.push_back(
3074       AArch64Operand::CreateSysReg(Tok.getString(), getLoc(), MRSReg, MSRReg,
3075                                    PStateImm, getContext()));
3076   Parser.Lex(); // Eat identifier
3077 
3078   return MatchOperand_Success;
3079 }
3080 
3081 /// tryParseNeonVectorRegister - Parse a vector register operand.
3082 bool AArch64AsmParser::tryParseNeonVectorRegister(OperandVector &Operands) {
3083   MCAsmParser &Parser = getParser();
3084   if (Parser.getTok().isNot(AsmToken::Identifier))
3085     return true;
3086 
3087   SMLoc S = getLoc();
3088   // Check for a vector register specifier first.
3089   StringRef Kind;
3090   unsigned Reg;
3091   OperandMatchResultTy Res =
3092       tryParseVectorRegister(Reg, Kind, RegKind::NeonVector);
3093   if (Res != MatchOperand_Success)
3094     return true;
3095 
3096   const auto &KindRes = parseVectorKind(Kind, RegKind::NeonVector);
3097   if (!KindRes)
3098     return true;
3099 
3100   unsigned ElementWidth = KindRes->second;
3101   Operands.push_back(
3102       AArch64Operand::CreateVectorReg(Reg, RegKind::NeonVector, ElementWidth,
3103                                       S, getLoc(), getContext()));
3104 
3105   // If there was an explicit qualifier, that goes on as a literal text
3106   // operand.
3107   if (!Kind.empty())
3108     Operands.push_back(
3109         AArch64Operand::CreateToken(Kind, false, S, getContext()));
3110 
3111   return tryParseVectorIndex(Operands) == MatchOperand_ParseFail;
3112 }
3113 
3114 OperandMatchResultTy
3115 AArch64AsmParser::tryParseVectorIndex(OperandVector &Operands) {
3116   SMLoc SIdx = getLoc();
3117   if (parseOptionalToken(AsmToken::LBrac)) {
3118     const MCExpr *ImmVal;
3119     if (getParser().parseExpression(ImmVal))
3120       return MatchOperand_NoMatch;
3121     const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(ImmVal);
3122     if (!MCE) {
3123       TokError("immediate value expected for vector index");
3124       return MatchOperand_ParseFail;;
3125     }
3126 
3127     SMLoc E = getLoc();
3128 
3129     if (parseToken(AsmToken::RBrac, "']' expected"))
3130       return MatchOperand_ParseFail;;
3131 
3132     Operands.push_back(AArch64Operand::CreateVectorIndex(MCE->getValue(), SIdx,
3133                                                          E, getContext()));
3134     return MatchOperand_Success;
3135   }
3136 
3137   return MatchOperand_NoMatch;
3138 }
3139 
3140 // tryParseVectorRegister - Try to parse a vector register name with
3141 // optional kind specifier. If it is a register specifier, eat the token
3142 // and return it.
3143 OperandMatchResultTy
3144 AArch64AsmParser::tryParseVectorRegister(unsigned &Reg, StringRef &Kind,
3145                                          RegKind MatchKind) {
3146   MCAsmParser &Parser = getParser();
3147   const AsmToken &Tok = Parser.getTok();
3148 
3149   if (Tok.isNot(AsmToken::Identifier))
3150     return MatchOperand_NoMatch;
3151 
3152   StringRef Name = Tok.getString();
3153   // If there is a kind specifier, it's separated from the register name by
3154   // a '.'.
3155   size_t Start = 0, Next = Name.find('.');
3156   StringRef Head = Name.slice(Start, Next);
3157   unsigned RegNum = matchRegisterNameAlias(Head, MatchKind);
3158 
3159   if (RegNum) {
3160     if (Next != StringRef::npos) {
3161       Kind = Name.slice(Next, StringRef::npos);
3162       if (!isValidVectorKind(Kind, MatchKind)) {
3163         TokError("invalid vector kind qualifier");
3164         return MatchOperand_ParseFail;
3165       }
3166     }
3167     Parser.Lex(); // Eat the register token.
3168 
3169     Reg = RegNum;
3170     return MatchOperand_Success;
3171   }
3172 
3173   return MatchOperand_NoMatch;
3174 }
3175 
3176 /// tryParseSVEPredicateVector - Parse a SVE predicate register operand.
3177 OperandMatchResultTy
3178 AArch64AsmParser::tryParseSVEPredicateVector(OperandVector &Operands) {
3179   // Check for a SVE predicate register specifier first.
3180   const SMLoc S = getLoc();
3181   StringRef Kind;
3182   unsigned RegNum;
3183   auto Res = tryParseVectorRegister(RegNum, Kind, RegKind::SVEPredicateVector);
3184   if (Res != MatchOperand_Success)
3185     return Res;
3186 
3187   const auto &KindRes = parseVectorKind(Kind, RegKind::SVEPredicateVector);
3188   if (!KindRes)
3189     return MatchOperand_NoMatch;
3190 
3191   unsigned ElementWidth = KindRes->second;
3192   Operands.push_back(AArch64Operand::CreateVectorReg(
3193       RegNum, RegKind::SVEPredicateVector, ElementWidth, S,
3194       getLoc(), getContext()));
3195 
3196   // Not all predicates are followed by a '/m' or '/z'.
3197   MCAsmParser &Parser = getParser();
3198   if (Parser.getTok().isNot(AsmToken::Slash))
3199     return MatchOperand_Success;
3200 
3201   // But when they do they shouldn't have an element type suffix.
3202   if (!Kind.empty()) {
3203     Error(S, "not expecting size suffix");
3204     return MatchOperand_ParseFail;
3205   }
3206 
3207   // Add a literal slash as operand
3208   Operands.push_back(
3209       AArch64Operand::CreateToken("/" , false, getLoc(), getContext()));
3210 
3211   Parser.Lex(); // Eat the slash.
3212 
3213   // Zeroing or merging?
3214   auto Pred = Parser.getTok().getString().lower();
3215   if (Pred != "z" && Pred != "m") {
3216     Error(getLoc(), "expecting 'm' or 'z' predication");
3217     return MatchOperand_ParseFail;
3218   }
3219 
3220   // Add zero/merge token.
3221   const char *ZM = Pred == "z" ? "z" : "m";
3222   Operands.push_back(
3223     AArch64Operand::CreateToken(ZM, false, getLoc(), getContext()));
3224 
3225   Parser.Lex(); // Eat zero/merge token.
3226   return MatchOperand_Success;
3227 }
3228 
3229 /// parseRegister - Parse a register operand.
3230 bool AArch64AsmParser::parseRegister(OperandVector &Operands) {
3231   // Try for a Neon vector register.
3232   if (!tryParseNeonVectorRegister(Operands))
3233     return false;
3234 
3235   // Otherwise try for a scalar register.
3236   if (tryParseGPROperand<false>(Operands) == MatchOperand_Success)
3237     return false;
3238 
3239   return true;
3240 }
3241 
3242 bool AArch64AsmParser::parseSymbolicImmVal(const MCExpr *&ImmVal) {
3243   MCAsmParser &Parser = getParser();
3244   bool HasELFModifier = false;
3245   AArch64MCExpr::VariantKind RefKind;
3246 
3247   if (parseOptionalToken(AsmToken::Colon)) {
3248     HasELFModifier = true;
3249 
3250     if (Parser.getTok().isNot(AsmToken::Identifier))
3251       return TokError("expect relocation specifier in operand after ':'");
3252 
3253     std::string LowerCase = Parser.getTok().getIdentifier().lower();
3254     RefKind = StringSwitch<AArch64MCExpr::VariantKind>(LowerCase)
3255                   .Case("lo12", AArch64MCExpr::VK_LO12)
3256                   .Case("abs_g3", AArch64MCExpr::VK_ABS_G3)
3257                   .Case("abs_g2", AArch64MCExpr::VK_ABS_G2)
3258                   .Case("abs_g2_s", AArch64MCExpr::VK_ABS_G2_S)
3259                   .Case("abs_g2_nc", AArch64MCExpr::VK_ABS_G2_NC)
3260                   .Case("abs_g1", AArch64MCExpr::VK_ABS_G1)
3261                   .Case("abs_g1_s", AArch64MCExpr::VK_ABS_G1_S)
3262                   .Case("abs_g1_nc", AArch64MCExpr::VK_ABS_G1_NC)
3263                   .Case("abs_g0", AArch64MCExpr::VK_ABS_G0)
3264                   .Case("abs_g0_s", AArch64MCExpr::VK_ABS_G0_S)
3265                   .Case("abs_g0_nc", AArch64MCExpr::VK_ABS_G0_NC)
3266                   .Case("prel_g3", AArch64MCExpr::VK_PREL_G3)
3267                   .Case("prel_g2", AArch64MCExpr::VK_PREL_G2)
3268                   .Case("prel_g2_nc", AArch64MCExpr::VK_PREL_G2_NC)
3269                   .Case("prel_g1", AArch64MCExpr::VK_PREL_G1)
3270                   .Case("prel_g1_nc", AArch64MCExpr::VK_PREL_G1_NC)
3271                   .Case("prel_g0", AArch64MCExpr::VK_PREL_G0)
3272                   .Case("prel_g0_nc", AArch64MCExpr::VK_PREL_G0_NC)
3273                   .Case("dtprel_g2", AArch64MCExpr::VK_DTPREL_G2)
3274                   .Case("dtprel_g1", AArch64MCExpr::VK_DTPREL_G1)
3275                   .Case("dtprel_g1_nc", AArch64MCExpr::VK_DTPREL_G1_NC)
3276                   .Case("dtprel_g0", AArch64MCExpr::VK_DTPREL_G0)
3277                   .Case("dtprel_g0_nc", AArch64MCExpr::VK_DTPREL_G0_NC)
3278                   .Case("dtprel_hi12", AArch64MCExpr::VK_DTPREL_HI12)
3279                   .Case("dtprel_lo12", AArch64MCExpr::VK_DTPREL_LO12)
3280                   .Case("dtprel_lo12_nc", AArch64MCExpr::VK_DTPREL_LO12_NC)
3281                   .Case("pg_hi21_nc", AArch64MCExpr::VK_ABS_PAGE_NC)
3282                   .Case("tprel_g2", AArch64MCExpr::VK_TPREL_G2)
3283                   .Case("tprel_g1", AArch64MCExpr::VK_TPREL_G1)
3284                   .Case("tprel_g1_nc", AArch64MCExpr::VK_TPREL_G1_NC)
3285                   .Case("tprel_g0", AArch64MCExpr::VK_TPREL_G0)
3286                   .Case("tprel_g0_nc", AArch64MCExpr::VK_TPREL_G0_NC)
3287                   .Case("tprel_hi12", AArch64MCExpr::VK_TPREL_HI12)
3288                   .Case("tprel_lo12", AArch64MCExpr::VK_TPREL_LO12)
3289                   .Case("tprel_lo12_nc", AArch64MCExpr::VK_TPREL_LO12_NC)
3290                   .Case("tlsdesc_lo12", AArch64MCExpr::VK_TLSDESC_LO12)
3291                   .Case("got", AArch64MCExpr::VK_GOT_PAGE)
3292                   .Case("got_lo12", AArch64MCExpr::VK_GOT_LO12)
3293                   .Case("gottprel", AArch64MCExpr::VK_GOTTPREL_PAGE)
3294                   .Case("gottprel_lo12", AArch64MCExpr::VK_GOTTPREL_LO12_NC)
3295                   .Case("gottprel_g1", AArch64MCExpr::VK_GOTTPREL_G1)
3296                   .Case("gottprel_g0_nc", AArch64MCExpr::VK_GOTTPREL_G0_NC)
3297                   .Case("tlsdesc", AArch64MCExpr::VK_TLSDESC_PAGE)
3298                   .Case("secrel_lo12", AArch64MCExpr::VK_SECREL_LO12)
3299                   .Case("secrel_hi12", AArch64MCExpr::VK_SECREL_HI12)
3300                   .Default(AArch64MCExpr::VK_INVALID);
3301 
3302     if (RefKind == AArch64MCExpr::VK_INVALID)
3303       return TokError("expect relocation specifier in operand after ':'");
3304 
3305     Parser.Lex(); // Eat identifier
3306 
3307     if (parseToken(AsmToken::Colon, "expect ':' after relocation specifier"))
3308       return true;
3309   }
3310 
3311   if (getParser().parseExpression(ImmVal))
3312     return true;
3313 
3314   if (HasELFModifier)
3315     ImmVal = AArch64MCExpr::create(ImmVal, RefKind, getContext());
3316 
3317   return false;
3318 }
3319 
3320 template <RegKind VectorKind>
3321 OperandMatchResultTy
3322 AArch64AsmParser::tryParseVectorList(OperandVector &Operands,
3323                                      bool ExpectMatch) {
3324   MCAsmParser &Parser = getParser();
3325   if (!Parser.getTok().is(AsmToken::LCurly))
3326     return MatchOperand_NoMatch;
3327 
3328   // Wrapper around parse function
3329   auto ParseVector = [this, &Parser](unsigned &Reg, StringRef &Kind, SMLoc Loc,
3330                                      bool NoMatchIsError) {
3331     auto RegTok = Parser.getTok();
3332     auto ParseRes = tryParseVectorRegister(Reg, Kind, VectorKind);
3333     if (ParseRes == MatchOperand_Success) {
3334       if (parseVectorKind(Kind, VectorKind))
3335         return ParseRes;
3336       llvm_unreachable("Expected a valid vector kind");
3337     }
3338 
3339     if (RegTok.isNot(AsmToken::Identifier) ||
3340         ParseRes == MatchOperand_ParseFail ||
3341         (ParseRes == MatchOperand_NoMatch && NoMatchIsError)) {
3342       Error(Loc, "vector register expected");
3343       return MatchOperand_ParseFail;
3344     }
3345 
3346     return MatchOperand_NoMatch;
3347   };
3348 
3349   SMLoc S = getLoc();
3350   auto LCurly = Parser.getTok();
3351   Parser.Lex(); // Eat left bracket token.
3352 
3353   StringRef Kind;
3354   unsigned FirstReg;
3355   auto ParseRes = ParseVector(FirstReg, Kind, getLoc(), ExpectMatch);
3356 
3357   // Put back the original left bracket if there was no match, so that
3358   // different types of list-operands can be matched (e.g. SVE, Neon).
3359   if (ParseRes == MatchOperand_NoMatch)
3360     Parser.getLexer().UnLex(LCurly);
3361 
3362   if (ParseRes != MatchOperand_Success)
3363     return ParseRes;
3364 
3365   int64_t PrevReg = FirstReg;
3366   unsigned Count = 1;
3367 
3368   if (parseOptionalToken(AsmToken::Minus)) {
3369     SMLoc Loc = getLoc();
3370     StringRef NextKind;
3371 
3372     unsigned Reg;
3373     ParseRes = ParseVector(Reg, NextKind, getLoc(), true);
3374     if (ParseRes != MatchOperand_Success)
3375       return ParseRes;
3376 
3377     // Any Kind suffices must match on all regs in the list.
3378     if (Kind != NextKind) {
3379       Error(Loc, "mismatched register size suffix");
3380       return MatchOperand_ParseFail;
3381     }
3382 
3383     unsigned Space = (PrevReg < Reg) ? (Reg - PrevReg) : (Reg + 32 - PrevReg);
3384 
3385     if (Space == 0 || Space > 3) {
3386       Error(Loc, "invalid number of vectors");
3387       return MatchOperand_ParseFail;
3388     }
3389 
3390     Count += Space;
3391   }
3392   else {
3393     while (parseOptionalToken(AsmToken::Comma)) {
3394       SMLoc Loc = getLoc();
3395       StringRef NextKind;
3396       unsigned Reg;
3397       ParseRes = ParseVector(Reg, NextKind, getLoc(), true);
3398       if (ParseRes != MatchOperand_Success)
3399         return ParseRes;
3400 
3401       // Any Kind suffices must match on all regs in the list.
3402       if (Kind != NextKind) {
3403         Error(Loc, "mismatched register size suffix");
3404         return MatchOperand_ParseFail;
3405       }
3406 
3407       // Registers must be incremental (with wraparound at 31)
3408       if (getContext().getRegisterInfo()->getEncodingValue(Reg) !=
3409           (getContext().getRegisterInfo()->getEncodingValue(PrevReg) + 1) % 32) {
3410         Error(Loc, "registers must be sequential");
3411         return MatchOperand_ParseFail;
3412       }
3413 
3414       PrevReg = Reg;
3415       ++Count;
3416     }
3417   }
3418 
3419   if (parseToken(AsmToken::RCurly, "'}' expected"))
3420     return MatchOperand_ParseFail;
3421 
3422   if (Count > 4) {
3423     Error(S, "invalid number of vectors");
3424     return MatchOperand_ParseFail;
3425   }
3426 
3427   unsigned NumElements = 0;
3428   unsigned ElementWidth = 0;
3429   if (!Kind.empty()) {
3430     if (const auto &VK = parseVectorKind(Kind, VectorKind))
3431       std::tie(NumElements, ElementWidth) = *VK;
3432   }
3433 
3434   Operands.push_back(AArch64Operand::CreateVectorList(
3435       FirstReg, Count, NumElements, ElementWidth, VectorKind, S, getLoc(),
3436       getContext()));
3437 
3438   return MatchOperand_Success;
3439 }
3440 
3441 /// parseNeonVectorList - Parse a vector list operand for AdvSIMD instructions.
3442 bool AArch64AsmParser::parseNeonVectorList(OperandVector &Operands) {
3443   auto ParseRes = tryParseVectorList<RegKind::NeonVector>(Operands, true);
3444   if (ParseRes != MatchOperand_Success)
3445     return true;
3446 
3447   return tryParseVectorIndex(Operands) == MatchOperand_ParseFail;
3448 }
3449 
3450 OperandMatchResultTy
3451 AArch64AsmParser::tryParseGPR64sp0Operand(OperandVector &Operands) {
3452   SMLoc StartLoc = getLoc();
3453 
3454   unsigned RegNum;
3455   OperandMatchResultTy Res = tryParseScalarRegister(RegNum);
3456   if (Res != MatchOperand_Success)
3457     return Res;
3458 
3459   if (!parseOptionalToken(AsmToken::Comma)) {
3460     Operands.push_back(AArch64Operand::CreateReg(
3461         RegNum, RegKind::Scalar, StartLoc, getLoc(), getContext()));
3462     return MatchOperand_Success;
3463   }
3464 
3465   parseOptionalToken(AsmToken::Hash);
3466 
3467   if (getParser().getTok().isNot(AsmToken::Integer)) {
3468     Error(getLoc(), "index must be absent or #0");
3469     return MatchOperand_ParseFail;
3470   }
3471 
3472   const MCExpr *ImmVal;
3473   if (getParser().parseExpression(ImmVal) || !isa<MCConstantExpr>(ImmVal) ||
3474       cast<MCConstantExpr>(ImmVal)->getValue() != 0) {
3475     Error(getLoc(), "index must be absent or #0");
3476     return MatchOperand_ParseFail;
3477   }
3478 
3479   Operands.push_back(AArch64Operand::CreateReg(
3480       RegNum, RegKind::Scalar, StartLoc, getLoc(), getContext()));
3481   return MatchOperand_Success;
3482 }
3483 
3484 template <bool ParseShiftExtend, RegConstraintEqualityTy EqTy>
3485 OperandMatchResultTy
3486 AArch64AsmParser::tryParseGPROperand(OperandVector &Operands) {
3487   SMLoc StartLoc = getLoc();
3488 
3489   unsigned RegNum;
3490   OperandMatchResultTy Res = tryParseScalarRegister(RegNum);
3491   if (Res != MatchOperand_Success)
3492     return Res;
3493 
3494   // No shift/extend is the default.
3495   if (!ParseShiftExtend || getParser().getTok().isNot(AsmToken::Comma)) {
3496     Operands.push_back(AArch64Operand::CreateReg(
3497         RegNum, RegKind::Scalar, StartLoc, getLoc(), getContext(), EqTy));
3498     return MatchOperand_Success;
3499   }
3500 
3501   // Eat the comma
3502   getParser().Lex();
3503 
3504   // Match the shift
3505   SmallVector<std::unique_ptr<MCParsedAsmOperand>, 1> ExtOpnd;
3506   Res = tryParseOptionalShiftExtend(ExtOpnd);
3507   if (Res != MatchOperand_Success)
3508     return Res;
3509 
3510   auto Ext = static_cast<AArch64Operand*>(ExtOpnd.back().get());
3511   Operands.push_back(AArch64Operand::CreateReg(
3512       RegNum, RegKind::Scalar, StartLoc, Ext->getEndLoc(), getContext(), EqTy,
3513       Ext->getShiftExtendType(), Ext->getShiftExtendAmount(),
3514       Ext->hasShiftExtendAmount()));
3515 
3516   return MatchOperand_Success;
3517 }
3518 
3519 bool AArch64AsmParser::parseOptionalMulOperand(OperandVector &Operands) {
3520   MCAsmParser &Parser = getParser();
3521 
3522   // Some SVE instructions have a decoration after the immediate, i.e.
3523   // "mul vl". We parse them here and add tokens, which must be present in the
3524   // asm string in the tablegen instruction.
3525   bool NextIsVL = Parser.getLexer().peekTok().getString().equals_lower("vl");
3526   bool NextIsHash = Parser.getLexer().peekTok().is(AsmToken::Hash);
3527   if (!Parser.getTok().getString().equals_lower("mul") ||
3528       !(NextIsVL || NextIsHash))
3529     return true;
3530 
3531   Operands.push_back(
3532     AArch64Operand::CreateToken("mul", false, getLoc(), getContext()));
3533   Parser.Lex(); // Eat the "mul"
3534 
3535   if (NextIsVL) {
3536     Operands.push_back(
3537         AArch64Operand::CreateToken("vl", false, getLoc(), getContext()));
3538     Parser.Lex(); // Eat the "vl"
3539     return false;
3540   }
3541 
3542   if (NextIsHash) {
3543     Parser.Lex(); // Eat the #
3544     SMLoc S = getLoc();
3545 
3546     // Parse immediate operand.
3547     const MCExpr *ImmVal;
3548     if (!Parser.parseExpression(ImmVal))
3549       if (const MCConstantExpr *MCE = dyn_cast<MCConstantExpr>(ImmVal)) {
3550         Operands.push_back(AArch64Operand::CreateImm(
3551             MCConstantExpr::create(MCE->getValue(), getContext()), S, getLoc(),
3552             getContext()));
3553         return MatchOperand_Success;
3554       }
3555   }
3556 
3557   return Error(getLoc(), "expected 'vl' or '#<imm>'");
3558 }
3559 
3560 /// parseOperand - Parse a arm instruction operand.  For now this parses the
3561 /// operand regardless of the mnemonic.
3562 bool AArch64AsmParser::parseOperand(OperandVector &Operands, bool isCondCode,
3563                                   bool invertCondCode) {
3564   MCAsmParser &Parser = getParser();
3565 
3566   OperandMatchResultTy ResTy =
3567       MatchOperandParserImpl(Operands, Mnemonic, /*ParseForAllFeatures=*/ true);
3568 
3569   // Check if the current operand has a custom associated parser, if so, try to
3570   // custom parse the operand, or fallback to the general approach.
3571   if (ResTy == MatchOperand_Success)
3572     return false;
3573   // If there wasn't a custom match, try the generic matcher below. Otherwise,
3574   // there was a match, but an error occurred, in which case, just return that
3575   // the operand parsing failed.
3576   if (ResTy == MatchOperand_ParseFail)
3577     return true;
3578 
3579   // Nothing custom, so do general case parsing.
3580   SMLoc S, E;
3581   switch (getLexer().getKind()) {
3582   default: {
3583     SMLoc S = getLoc();
3584     const MCExpr *Expr;
3585     if (parseSymbolicImmVal(Expr))
3586       return Error(S, "invalid operand");
3587 
3588     SMLoc E = SMLoc::getFromPointer(getLoc().getPointer() - 1);
3589     Operands.push_back(AArch64Operand::CreateImm(Expr, S, E, getContext()));
3590     return false;
3591   }
3592   case AsmToken::LBrac: {
3593     SMLoc Loc = Parser.getTok().getLoc();
3594     Operands.push_back(AArch64Operand::CreateToken("[", false, Loc,
3595                                                    getContext()));
3596     Parser.Lex(); // Eat '['
3597 
3598     // There's no comma after a '[', so we can parse the next operand
3599     // immediately.
3600     return parseOperand(Operands, false, false);
3601   }
3602   case AsmToken::LCurly:
3603     return parseNeonVectorList(Operands);
3604   case AsmToken::Identifier: {
3605     // If we're expecting a Condition Code operand, then just parse that.
3606     if (isCondCode)
3607       return parseCondCode(Operands, invertCondCode);
3608 
3609     // If it's a register name, parse it.
3610     if (!parseRegister(Operands))
3611       return false;
3612 
3613     // See if this is a "mul vl" decoration or "mul #<int>" operand used
3614     // by SVE instructions.
3615     if (!parseOptionalMulOperand(Operands))
3616       return false;
3617 
3618     // This could be an optional "shift" or "extend" operand.
3619     OperandMatchResultTy GotShift = tryParseOptionalShiftExtend(Operands);
3620     // We can only continue if no tokens were eaten.
3621     if (GotShift != MatchOperand_NoMatch)
3622       return GotShift;
3623 
3624     // This was not a register so parse other operands that start with an
3625     // identifier (like labels) as expressions and create them as immediates.
3626     const MCExpr *IdVal;
3627     S = getLoc();
3628     if (getParser().parseExpression(IdVal))
3629       return true;
3630     E = SMLoc::getFromPointer(getLoc().getPointer() - 1);
3631     Operands.push_back(AArch64Operand::CreateImm(IdVal, S, E, getContext()));
3632     return false;
3633   }
3634   case AsmToken::Integer:
3635   case AsmToken::Real:
3636   case AsmToken::Hash: {
3637     // #42 -> immediate.
3638     S = getLoc();
3639 
3640     parseOptionalToken(AsmToken::Hash);
3641 
3642     // Parse a negative sign
3643     bool isNegative = false;
3644     if (Parser.getTok().is(AsmToken::Minus)) {
3645       isNegative = true;
3646       // We need to consume this token only when we have a Real, otherwise
3647       // we let parseSymbolicImmVal take care of it
3648       if (Parser.getLexer().peekTok().is(AsmToken::Real))
3649         Parser.Lex();
3650     }
3651 
3652     // The only Real that should come through here is a literal #0.0 for
3653     // the fcmp[e] r, #0.0 instructions. They expect raw token operands,
3654     // so convert the value.
3655     const AsmToken &Tok = Parser.getTok();
3656     if (Tok.is(AsmToken::Real)) {
3657       APFloat RealVal(APFloat::IEEEdouble(), Tok.getString());
3658       uint64_t IntVal = RealVal.bitcastToAPInt().getZExtValue();
3659       if (Mnemonic != "fcmp" && Mnemonic != "fcmpe" && Mnemonic != "fcmeq" &&
3660           Mnemonic != "fcmge" && Mnemonic != "fcmgt" && Mnemonic != "fcmle" &&
3661           Mnemonic != "fcmlt" && Mnemonic != "fcmne")
3662         return TokError("unexpected floating point literal");
3663       else if (IntVal != 0 || isNegative)
3664         return TokError("expected floating-point constant #0.0");
3665       Parser.Lex(); // Eat the token.
3666 
3667       Operands.push_back(
3668           AArch64Operand::CreateToken("#0", false, S, getContext()));
3669       Operands.push_back(
3670           AArch64Operand::CreateToken(".0", false, S, getContext()));
3671       return false;
3672     }
3673 
3674     const MCExpr *ImmVal;
3675     if (parseSymbolicImmVal(ImmVal))
3676       return true;
3677 
3678     E = SMLoc::getFromPointer(getLoc().getPointer() - 1);
3679     Operands.push_back(AArch64Operand::CreateImm(ImmVal, S, E, getContext()));
3680     return false;
3681   }
3682   case AsmToken::Equal: {
3683     SMLoc Loc = getLoc();
3684     if (Mnemonic != "ldr") // only parse for ldr pseudo (e.g. ldr r0, =val)
3685       return TokError("unexpected token in operand");
3686     Parser.Lex(); // Eat '='
3687     const MCExpr *SubExprVal;
3688     if (getParser().parseExpression(SubExprVal))
3689       return true;
3690 
3691     if (Operands.size() < 2 ||
3692         !static_cast<AArch64Operand &>(*Operands[1]).isScalarReg())
3693       return Error(Loc, "Only valid when first operand is register");
3694 
3695     bool IsXReg =
3696         AArch64MCRegisterClasses[AArch64::GPR64allRegClassID].contains(
3697             Operands[1]->getReg());
3698 
3699     MCContext& Ctx = getContext();
3700     E = SMLoc::getFromPointer(Loc.getPointer() - 1);
3701     // If the op is an imm and can be fit into a mov, then replace ldr with mov.
3702     if (isa<MCConstantExpr>(SubExprVal)) {
3703       uint64_t Imm = (cast<MCConstantExpr>(SubExprVal))->getValue();
3704       uint32_t ShiftAmt = 0, MaxShiftAmt = IsXReg ? 48 : 16;
3705       while(Imm > 0xFFFF && countTrailingZeros(Imm) >= 16) {
3706         ShiftAmt += 16;
3707         Imm >>= 16;
3708       }
3709       if (ShiftAmt <= MaxShiftAmt && Imm <= 0xFFFF) {
3710           Operands[0] = AArch64Operand::CreateToken("movz", false, Loc, Ctx);
3711           Operands.push_back(AArch64Operand::CreateImm(
3712                      MCConstantExpr::create(Imm, Ctx), S, E, Ctx));
3713         if (ShiftAmt)
3714           Operands.push_back(AArch64Operand::CreateShiftExtend(AArch64_AM::LSL,
3715                      ShiftAmt, true, S, E, Ctx));
3716         return false;
3717       }
3718       APInt Simm = APInt(64, Imm << ShiftAmt);
3719       // check if the immediate is an unsigned or signed 32-bit int for W regs
3720       if (!IsXReg && !(Simm.isIntN(32) || Simm.isSignedIntN(32)))
3721         return Error(Loc, "Immediate too large for register");
3722     }
3723     // If it is a label or an imm that cannot fit in a movz, put it into CP.
3724     const MCExpr *CPLoc =
3725         getTargetStreamer().addConstantPoolEntry(SubExprVal, IsXReg ? 8 : 4, Loc);
3726     Operands.push_back(AArch64Operand::CreateImm(CPLoc, S, E, Ctx));
3727     return false;
3728   }
3729   }
3730 }
3731 
3732 bool AArch64AsmParser::regsEqual(const MCParsedAsmOperand &Op1,
3733                                  const MCParsedAsmOperand &Op2) const {
3734   auto &AOp1 = static_cast<const AArch64Operand&>(Op1);
3735   auto &AOp2 = static_cast<const AArch64Operand&>(Op2);
3736   if (AOp1.getRegEqualityTy() == RegConstraintEqualityTy::EqualsReg &&
3737       AOp2.getRegEqualityTy() == RegConstraintEqualityTy::EqualsReg)
3738     return MCTargetAsmParser::regsEqual(Op1, Op2);
3739 
3740   assert(AOp1.isScalarReg() && AOp2.isScalarReg() &&
3741          "Testing equality of non-scalar registers not supported");
3742 
3743   // Check if a registers match their sub/super register classes.
3744   if (AOp1.getRegEqualityTy() == EqualsSuperReg)
3745     return getXRegFromWReg(Op1.getReg()) == Op2.getReg();
3746   if (AOp1.getRegEqualityTy() == EqualsSubReg)
3747     return getWRegFromXReg(Op1.getReg()) == Op2.getReg();
3748   if (AOp2.getRegEqualityTy() == EqualsSuperReg)
3749     return getXRegFromWReg(Op2.getReg()) == Op1.getReg();
3750   if (AOp2.getRegEqualityTy() == EqualsSubReg)
3751     return getWRegFromXReg(Op2.getReg()) == Op1.getReg();
3752 
3753   return false;
3754 }
3755 
3756 /// ParseInstruction - Parse an AArch64 instruction mnemonic followed by its
3757 /// operands.
3758 bool AArch64AsmParser::ParseInstruction(ParseInstructionInfo &Info,
3759                                         StringRef Name, SMLoc NameLoc,
3760                                         OperandVector &Operands) {
3761   MCAsmParser &Parser = getParser();
3762   Name = StringSwitch<StringRef>(Name.lower())
3763              .Case("beq", "b.eq")
3764              .Case("bne", "b.ne")
3765              .Case("bhs", "b.hs")
3766              .Case("bcs", "b.cs")
3767              .Case("blo", "b.lo")
3768              .Case("bcc", "b.cc")
3769              .Case("bmi", "b.mi")
3770              .Case("bpl", "b.pl")
3771              .Case("bvs", "b.vs")
3772              .Case("bvc", "b.vc")
3773              .Case("bhi", "b.hi")
3774              .Case("bls", "b.ls")
3775              .Case("bge", "b.ge")
3776              .Case("blt", "b.lt")
3777              .Case("bgt", "b.gt")
3778              .Case("ble", "b.le")
3779              .Case("bal", "b.al")
3780              .Case("bnv", "b.nv")
3781              .Default(Name);
3782 
3783   // First check for the AArch64-specific .req directive.
3784   if (Parser.getTok().is(AsmToken::Identifier) &&
3785       Parser.getTok().getIdentifier().lower() == ".req") {
3786     parseDirectiveReq(Name, NameLoc);
3787     // We always return 'error' for this, as we're done with this
3788     // statement and don't need to match the 'instruction."
3789     return true;
3790   }
3791 
3792   // Create the leading tokens for the mnemonic, split by '.' characters.
3793   size_t Start = 0, Next = Name.find('.');
3794   StringRef Head = Name.slice(Start, Next);
3795 
3796   // IC, DC, AT, TLBI and Prediction invalidation instructions are aliases for
3797   // the SYS instruction.
3798   if (Head == "ic" || Head == "dc" || Head == "at" || Head == "tlbi" ||
3799       Head == "cfp" || Head == "dvp" || Head == "cpp")
3800     return parseSysAlias(Head, NameLoc, Operands);
3801 
3802   Operands.push_back(
3803       AArch64Operand::CreateToken(Head, false, NameLoc, getContext()));
3804   Mnemonic = Head;
3805 
3806   // Handle condition codes for a branch mnemonic
3807   if (Head == "b" && Next != StringRef::npos) {
3808     Start = Next;
3809     Next = Name.find('.', Start + 1);
3810     Head = Name.slice(Start + 1, Next);
3811 
3812     SMLoc SuffixLoc = SMLoc::getFromPointer(NameLoc.getPointer() +
3813                                             (Head.data() - Name.data()));
3814     AArch64CC::CondCode CC = parseCondCodeString(Head);
3815     if (CC == AArch64CC::Invalid)
3816       return Error(SuffixLoc, "invalid condition code");
3817     Operands.push_back(
3818         AArch64Operand::CreateToken(".", true, SuffixLoc, getContext()));
3819     Operands.push_back(
3820         AArch64Operand::CreateCondCode(CC, NameLoc, NameLoc, getContext()));
3821   }
3822 
3823   // Add the remaining tokens in the mnemonic.
3824   while (Next != StringRef::npos) {
3825     Start = Next;
3826     Next = Name.find('.', Start + 1);
3827     Head = Name.slice(Start, Next);
3828     SMLoc SuffixLoc = SMLoc::getFromPointer(NameLoc.getPointer() +
3829                                             (Head.data() - Name.data()) + 1);
3830     Operands.push_back(
3831         AArch64Operand::CreateToken(Head, true, SuffixLoc, getContext()));
3832   }
3833 
3834   // Conditional compare instructions have a Condition Code operand, which needs
3835   // to be parsed and an immediate operand created.
3836   bool condCodeFourthOperand =
3837       (Head == "ccmp" || Head == "ccmn" || Head == "fccmp" ||
3838        Head == "fccmpe" || Head == "fcsel" || Head == "csel" ||
3839        Head == "csinc" || Head == "csinv" || Head == "csneg");
3840 
3841   // These instructions are aliases to some of the conditional select
3842   // instructions. However, the condition code is inverted in the aliased
3843   // instruction.
3844   //
3845   // FIXME: Is this the correct way to handle these? Or should the parser
3846   //        generate the aliased instructions directly?
3847   bool condCodeSecondOperand = (Head == "cset" || Head == "csetm");
3848   bool condCodeThirdOperand =
3849       (Head == "cinc" || Head == "cinv" || Head == "cneg");
3850 
3851   // Read the remaining operands.
3852   if (getLexer().isNot(AsmToken::EndOfStatement)) {
3853 
3854     unsigned N = 1;
3855     do {
3856       // Parse and remember the operand.
3857       if (parseOperand(Operands, (N == 4 && condCodeFourthOperand) ||
3858                                      (N == 3 && condCodeThirdOperand) ||
3859                                      (N == 2 && condCodeSecondOperand),
3860                        condCodeSecondOperand || condCodeThirdOperand)) {
3861         return true;
3862       }
3863 
3864       // After successfully parsing some operands there are two special cases to
3865       // consider (i.e. notional operands not separated by commas). Both are due
3866       // to memory specifiers:
3867       //  + An RBrac will end an address for load/store/prefetch
3868       //  + An '!' will indicate a pre-indexed operation.
3869       //
3870       // It's someone else's responsibility to make sure these tokens are sane
3871       // in the given context!
3872 
3873       SMLoc RLoc = Parser.getTok().getLoc();
3874       if (parseOptionalToken(AsmToken::RBrac))
3875         Operands.push_back(
3876             AArch64Operand::CreateToken("]", false, RLoc, getContext()));
3877       SMLoc ELoc = Parser.getTok().getLoc();
3878       if (parseOptionalToken(AsmToken::Exclaim))
3879         Operands.push_back(
3880             AArch64Operand::CreateToken("!", false, ELoc, getContext()));
3881 
3882       ++N;
3883     } while (parseOptionalToken(AsmToken::Comma));
3884   }
3885 
3886   if (parseToken(AsmToken::EndOfStatement, "unexpected token in argument list"))
3887     return true;
3888 
3889   return false;
3890 }
3891 
3892 static inline bool isMatchingOrAlias(unsigned ZReg, unsigned Reg) {
3893   assert((ZReg >= AArch64::Z0) && (ZReg <= AArch64::Z31));
3894   return (ZReg == ((Reg - AArch64::B0) + AArch64::Z0)) ||
3895          (ZReg == ((Reg - AArch64::H0) + AArch64::Z0)) ||
3896          (ZReg == ((Reg - AArch64::S0) + AArch64::Z0)) ||
3897          (ZReg == ((Reg - AArch64::D0) + AArch64::Z0)) ||
3898          (ZReg == ((Reg - AArch64::Q0) + AArch64::Z0)) ||
3899          (ZReg == ((Reg - AArch64::Z0) + AArch64::Z0));
3900 }
3901 
3902 // FIXME: This entire function is a giant hack to provide us with decent
3903 // operand range validation/diagnostics until TableGen/MC can be extended
3904 // to support autogeneration of this kind of validation.
3905 bool AArch64AsmParser::validateInstruction(MCInst &Inst, SMLoc &IDLoc,
3906                                            SmallVectorImpl<SMLoc> &Loc) {
3907   const MCRegisterInfo *RI = getContext().getRegisterInfo();
3908   const MCInstrDesc &MCID = MII.get(Inst.getOpcode());
3909 
3910   // A prefix only applies to the instruction following it.  Here we extract
3911   // prefix information for the next instruction before validating the current
3912   // one so that in the case of failure we don't erronously continue using the
3913   // current prefix.
3914   PrefixInfo Prefix = NextPrefix;
3915   NextPrefix = PrefixInfo::CreateFromInst(Inst, MCID.TSFlags);
3916 
3917   // Before validating the instruction in isolation we run through the rules
3918   // applicable when it follows a prefix instruction.
3919   // NOTE: brk & hlt can be prefixed but require no additional validation.
3920   if (Prefix.isActive() &&
3921       (Inst.getOpcode() != AArch64::BRK) &&
3922       (Inst.getOpcode() != AArch64::HLT)) {
3923 
3924     // Prefixed intructions must have a destructive operand.
3925     if ((MCID.TSFlags & AArch64::DestructiveInstTypeMask) ==
3926         AArch64::NotDestructive)
3927       return Error(IDLoc, "instruction is unpredictable when following a"
3928                    " movprfx, suggest replacing movprfx with mov");
3929 
3930     // Destination operands must match.
3931     if (Inst.getOperand(0).getReg() != Prefix.getDstReg())
3932       return Error(Loc[0], "instruction is unpredictable when following a"
3933                    " movprfx writing to a different destination");
3934 
3935     // Destination operand must not be used in any other location.
3936     for (unsigned i = 1; i < Inst.getNumOperands(); ++i) {
3937       if (Inst.getOperand(i).isReg() &&
3938           (MCID.getOperandConstraint(i, MCOI::TIED_TO) == -1) &&
3939           isMatchingOrAlias(Prefix.getDstReg(), Inst.getOperand(i).getReg()))
3940         return Error(Loc[0], "instruction is unpredictable when following a"
3941                      " movprfx and destination also used as non-destructive"
3942                      " source");
3943     }
3944 
3945     auto PPRRegClass = AArch64MCRegisterClasses[AArch64::PPRRegClassID];
3946     if (Prefix.isPredicated()) {
3947       int PgIdx = -1;
3948 
3949       // Find the instructions general predicate.
3950       for (unsigned i = 1; i < Inst.getNumOperands(); ++i)
3951         if (Inst.getOperand(i).isReg() &&
3952             PPRRegClass.contains(Inst.getOperand(i).getReg())) {
3953           PgIdx = i;
3954           break;
3955         }
3956 
3957       // Instruction must be predicated if the movprfx is predicated.
3958       if (PgIdx == -1 ||
3959           (MCID.TSFlags & AArch64::ElementSizeMask) == AArch64::ElementSizeNone)
3960         return Error(IDLoc, "instruction is unpredictable when following a"
3961                      " predicated movprfx, suggest using unpredicated movprfx");
3962 
3963       // Instruction must use same general predicate as the movprfx.
3964       if (Inst.getOperand(PgIdx).getReg() != Prefix.getPgReg())
3965         return Error(IDLoc, "instruction is unpredictable when following a"
3966                      " predicated movprfx using a different general predicate");
3967 
3968       // Instruction element type must match the movprfx.
3969       if ((MCID.TSFlags & AArch64::ElementSizeMask) != Prefix.getElementSize())
3970         return Error(IDLoc, "instruction is unpredictable when following a"
3971                      " predicated movprfx with a different element size");
3972     }
3973   }
3974 
3975   // Check for indexed addressing modes w/ the base register being the
3976   // same as a destination/source register or pair load where
3977   // the Rt == Rt2. All of those are undefined behaviour.
3978   switch (Inst.getOpcode()) {
3979   case AArch64::LDPSWpre:
3980   case AArch64::LDPWpost:
3981   case AArch64::LDPWpre:
3982   case AArch64::LDPXpost:
3983   case AArch64::LDPXpre: {
3984     unsigned Rt = Inst.getOperand(1).getReg();
3985     unsigned Rt2 = Inst.getOperand(2).getReg();
3986     unsigned Rn = Inst.getOperand(3).getReg();
3987     if (RI->isSubRegisterEq(Rn, Rt))
3988       return Error(Loc[0], "unpredictable LDP instruction, writeback base "
3989                            "is also a destination");
3990     if (RI->isSubRegisterEq(Rn, Rt2))
3991       return Error(Loc[1], "unpredictable LDP instruction, writeback base "
3992                            "is also a destination");
3993     LLVM_FALLTHROUGH;
3994   }
3995   case AArch64::LDPDi:
3996   case AArch64::LDPQi:
3997   case AArch64::LDPSi:
3998   case AArch64::LDPSWi:
3999   case AArch64::LDPWi:
4000   case AArch64::LDPXi: {
4001     unsigned Rt = Inst.getOperand(0).getReg();
4002     unsigned Rt2 = Inst.getOperand(1).getReg();
4003     if (Rt == Rt2)
4004       return Error(Loc[1], "unpredictable LDP instruction, Rt2==Rt");
4005     break;
4006   }
4007   case AArch64::LDPDpost:
4008   case AArch64::LDPDpre:
4009   case AArch64::LDPQpost:
4010   case AArch64::LDPQpre:
4011   case AArch64::LDPSpost:
4012   case AArch64::LDPSpre:
4013   case AArch64::LDPSWpost: {
4014     unsigned Rt = Inst.getOperand(1).getReg();
4015     unsigned Rt2 = Inst.getOperand(2).getReg();
4016     if (Rt == Rt2)
4017       return Error(Loc[1], "unpredictable LDP instruction, Rt2==Rt");
4018     break;
4019   }
4020   case AArch64::STPDpost:
4021   case AArch64::STPDpre:
4022   case AArch64::STPQpost:
4023   case AArch64::STPQpre:
4024   case AArch64::STPSpost:
4025   case AArch64::STPSpre:
4026   case AArch64::STPWpost:
4027   case AArch64::STPWpre:
4028   case AArch64::STPXpost:
4029   case AArch64::STPXpre: {
4030     unsigned Rt = Inst.getOperand(1).getReg();
4031     unsigned Rt2 = Inst.getOperand(2).getReg();
4032     unsigned Rn = Inst.getOperand(3).getReg();
4033     if (RI->isSubRegisterEq(Rn, Rt))
4034       return Error(Loc[0], "unpredictable STP instruction, writeback base "
4035                            "is also a source");
4036     if (RI->isSubRegisterEq(Rn, Rt2))
4037       return Error(Loc[1], "unpredictable STP instruction, writeback base "
4038                            "is also a source");
4039     break;
4040   }
4041   case AArch64::LDRBBpre:
4042   case AArch64::LDRBpre:
4043   case AArch64::LDRHHpre:
4044   case AArch64::LDRHpre:
4045   case AArch64::LDRSBWpre:
4046   case AArch64::LDRSBXpre:
4047   case AArch64::LDRSHWpre:
4048   case AArch64::LDRSHXpre:
4049   case AArch64::LDRSWpre:
4050   case AArch64::LDRWpre:
4051   case AArch64::LDRXpre:
4052   case AArch64::LDRBBpost:
4053   case AArch64::LDRBpost:
4054   case AArch64::LDRHHpost:
4055   case AArch64::LDRHpost:
4056   case AArch64::LDRSBWpost:
4057   case AArch64::LDRSBXpost:
4058   case AArch64::LDRSHWpost:
4059   case AArch64::LDRSHXpost:
4060   case AArch64::LDRSWpost:
4061   case AArch64::LDRWpost:
4062   case AArch64::LDRXpost: {
4063     unsigned Rt = Inst.getOperand(1).getReg();
4064     unsigned Rn = Inst.getOperand(2).getReg();
4065     if (RI->isSubRegisterEq(Rn, Rt))
4066       return Error(Loc[0], "unpredictable LDR instruction, writeback base "
4067                            "is also a source");
4068     break;
4069   }
4070   case AArch64::STRBBpost:
4071   case AArch64::STRBpost:
4072   case AArch64::STRHHpost:
4073   case AArch64::STRHpost:
4074   case AArch64::STRWpost:
4075   case AArch64::STRXpost:
4076   case AArch64::STRBBpre:
4077   case AArch64::STRBpre:
4078   case AArch64::STRHHpre:
4079   case AArch64::STRHpre:
4080   case AArch64::STRWpre:
4081   case AArch64::STRXpre: {
4082     unsigned Rt = Inst.getOperand(1).getReg();
4083     unsigned Rn = Inst.getOperand(2).getReg();
4084     if (RI->isSubRegisterEq(Rn, Rt))
4085       return Error(Loc[0], "unpredictable STR instruction, writeback base "
4086                            "is also a source");
4087     break;
4088   }
4089   case AArch64::STXRB:
4090   case AArch64::STXRH:
4091   case AArch64::STXRW:
4092   case AArch64::STXRX:
4093   case AArch64::STLXRB:
4094   case AArch64::STLXRH:
4095   case AArch64::STLXRW:
4096   case AArch64::STLXRX: {
4097     unsigned Rs = Inst.getOperand(0).getReg();
4098     unsigned Rt = Inst.getOperand(1).getReg();
4099     unsigned Rn = Inst.getOperand(2).getReg();
4100     if (RI->isSubRegisterEq(Rt, Rs) ||
4101         (RI->isSubRegisterEq(Rn, Rs) && Rn != AArch64::SP))
4102       return Error(Loc[0],
4103                    "unpredictable STXR instruction, status is also a source");
4104     break;
4105   }
4106   case AArch64::STXPW:
4107   case AArch64::STXPX:
4108   case AArch64::STLXPW:
4109   case AArch64::STLXPX: {
4110     unsigned Rs = Inst.getOperand(0).getReg();
4111     unsigned Rt1 = Inst.getOperand(1).getReg();
4112     unsigned Rt2 = Inst.getOperand(2).getReg();
4113     unsigned Rn = Inst.getOperand(3).getReg();
4114     if (RI->isSubRegisterEq(Rt1, Rs) || RI->isSubRegisterEq(Rt2, Rs) ||
4115         (RI->isSubRegisterEq(Rn, Rs) && Rn != AArch64::SP))
4116       return Error(Loc[0],
4117                    "unpredictable STXP instruction, status is also a source");
4118     break;
4119   }
4120   case AArch64::LDRABwriteback:
4121   case AArch64::LDRAAwriteback: {
4122     unsigned Xt = Inst.getOperand(0).getReg();
4123     unsigned Xn = Inst.getOperand(1).getReg();
4124     if (Xt == Xn)
4125       return Error(Loc[0],
4126           "unpredictable LDRA instruction, writeback base"
4127           " is also a destination");
4128     break;
4129   }
4130   }
4131 
4132 
4133   // Now check immediate ranges. Separate from the above as there is overlap
4134   // in the instructions being checked and this keeps the nested conditionals
4135   // to a minimum.
4136   switch (Inst.getOpcode()) {
4137   case AArch64::ADDSWri:
4138   case AArch64::ADDSXri:
4139   case AArch64::ADDWri:
4140   case AArch64::ADDXri:
4141   case AArch64::SUBSWri:
4142   case AArch64::SUBSXri:
4143   case AArch64::SUBWri:
4144   case AArch64::SUBXri: {
4145     // Annoyingly we can't do this in the isAddSubImm predicate, so there is
4146     // some slight duplication here.
4147     if (Inst.getOperand(2).isExpr()) {
4148       const MCExpr *Expr = Inst.getOperand(2).getExpr();
4149       AArch64MCExpr::VariantKind ELFRefKind;
4150       MCSymbolRefExpr::VariantKind DarwinRefKind;
4151       int64_t Addend;
4152       if (classifySymbolRef(Expr, ELFRefKind, DarwinRefKind, Addend)) {
4153 
4154         // Only allow these with ADDXri.
4155         if ((DarwinRefKind == MCSymbolRefExpr::VK_PAGEOFF ||
4156              DarwinRefKind == MCSymbolRefExpr::VK_TLVPPAGEOFF) &&
4157             Inst.getOpcode() == AArch64::ADDXri)
4158           return false;
4159 
4160         // Only allow these with ADDXri/ADDWri
4161         if ((ELFRefKind == AArch64MCExpr::VK_LO12 ||
4162              ELFRefKind == AArch64MCExpr::VK_DTPREL_HI12 ||
4163              ELFRefKind == AArch64MCExpr::VK_DTPREL_LO12 ||
4164              ELFRefKind == AArch64MCExpr::VK_DTPREL_LO12_NC ||
4165              ELFRefKind == AArch64MCExpr::VK_TPREL_HI12 ||
4166              ELFRefKind == AArch64MCExpr::VK_TPREL_LO12 ||
4167              ELFRefKind == AArch64MCExpr::VK_TPREL_LO12_NC ||
4168              ELFRefKind == AArch64MCExpr::VK_TLSDESC_LO12 ||
4169              ELFRefKind == AArch64MCExpr::VK_SECREL_LO12 ||
4170              ELFRefKind == AArch64MCExpr::VK_SECREL_HI12) &&
4171             (Inst.getOpcode() == AArch64::ADDXri ||
4172              Inst.getOpcode() == AArch64::ADDWri))
4173           return false;
4174 
4175         // Don't allow symbol refs in the immediate field otherwise
4176         // Note: Loc.back() may be Loc[1] or Loc[2] depending on the number of
4177         // operands of the original instruction (i.e. 'add w0, w1, borked' vs
4178         // 'cmp w0, 'borked')
4179         return Error(Loc.back(), "invalid immediate expression");
4180       }
4181       // We don't validate more complex expressions here
4182     }
4183     return false;
4184   }
4185   default:
4186     return false;
4187   }
4188 }
4189 
4190 static std::string AArch64MnemonicSpellCheck(StringRef S,
4191                                              const FeatureBitset &FBS,
4192                                              unsigned VariantID = 0);
4193 
4194 bool AArch64AsmParser::showMatchError(SMLoc Loc, unsigned ErrCode,
4195                                       uint64_t ErrorInfo,
4196                                       OperandVector &Operands) {
4197   switch (ErrCode) {
4198   case Match_InvalidTiedOperand: {
4199     RegConstraintEqualityTy EqTy =
4200         static_cast<const AArch64Operand &>(*Operands[ErrorInfo])
4201             .getRegEqualityTy();
4202     switch (EqTy) {
4203     case RegConstraintEqualityTy::EqualsSubReg:
4204       return Error(Loc, "operand must be 64-bit form of destination register");
4205     case RegConstraintEqualityTy::EqualsSuperReg:
4206       return Error(Loc, "operand must be 32-bit form of destination register");
4207     case RegConstraintEqualityTy::EqualsReg:
4208       return Error(Loc, "operand must match destination register");
4209     }
4210     llvm_unreachable("Unknown RegConstraintEqualityTy");
4211   }
4212   case Match_MissingFeature:
4213     return Error(Loc,
4214                  "instruction requires a CPU feature not currently enabled");
4215   case Match_InvalidOperand:
4216     return Error(Loc, "invalid operand for instruction");
4217   case Match_InvalidSuffix:
4218     return Error(Loc, "invalid type suffix for instruction");
4219   case Match_InvalidCondCode:
4220     return Error(Loc, "expected AArch64 condition code");
4221   case Match_AddSubRegExtendSmall:
4222     return Error(Loc,
4223       "expected '[su]xt[bhw]' with optional integer in range [0, 4]");
4224   case Match_AddSubRegExtendLarge:
4225     return Error(Loc,
4226       "expected 'sxtx' 'uxtx' or 'lsl' with optional integer in range [0, 4]");
4227   case Match_AddSubSecondSource:
4228     return Error(Loc,
4229       "expected compatible register, symbol or integer in range [0, 4095]");
4230   case Match_LogicalSecondSource:
4231     return Error(Loc, "expected compatible register or logical immediate");
4232   case Match_InvalidMovImm32Shift:
4233     return Error(Loc, "expected 'lsl' with optional integer 0 or 16");
4234   case Match_InvalidMovImm64Shift:
4235     return Error(Loc, "expected 'lsl' with optional integer 0, 16, 32 or 48");
4236   case Match_AddSubRegShift32:
4237     return Error(Loc,
4238        "expected 'lsl', 'lsr' or 'asr' with optional integer in range [0, 31]");
4239   case Match_AddSubRegShift64:
4240     return Error(Loc,
4241        "expected 'lsl', 'lsr' or 'asr' with optional integer in range [0, 63]");
4242   case Match_InvalidFPImm:
4243     return Error(Loc,
4244                  "expected compatible register or floating-point constant");
4245   case Match_InvalidMemoryIndexedSImm6:
4246     return Error(Loc, "index must be an integer in range [-32, 31].");
4247   case Match_InvalidMemoryIndexedSImm5:
4248     return Error(Loc, "index must be an integer in range [-16, 15].");
4249   case Match_InvalidMemoryIndexed1SImm4:
4250     return Error(Loc, "index must be an integer in range [-8, 7].");
4251   case Match_InvalidMemoryIndexed2SImm4:
4252     return Error(Loc, "index must be a multiple of 2 in range [-16, 14].");
4253   case Match_InvalidMemoryIndexed3SImm4:
4254     return Error(Loc, "index must be a multiple of 3 in range [-24, 21].");
4255   case Match_InvalidMemoryIndexed4SImm4:
4256     return Error(Loc, "index must be a multiple of 4 in range [-32, 28].");
4257   case Match_InvalidMemoryIndexed16SImm4:
4258     return Error(Loc, "index must be a multiple of 16 in range [-128, 112].");
4259   case Match_InvalidMemoryIndexed1SImm6:
4260     return Error(Loc, "index must be an integer in range [-32, 31].");
4261   case Match_InvalidMemoryIndexedSImm8:
4262     return Error(Loc, "index must be an integer in range [-128, 127].");
4263   case Match_InvalidMemoryIndexedSImm9:
4264     return Error(Loc, "index must be an integer in range [-256, 255].");
4265   case Match_InvalidMemoryIndexed16SImm9:
4266     return Error(Loc, "index must be a multiple of 16 in range [-4096, 4080].");
4267   case Match_InvalidMemoryIndexed8SImm10:
4268     return Error(Loc, "index must be a multiple of 8 in range [-4096, 4088].");
4269   case Match_InvalidMemoryIndexed4SImm7:
4270     return Error(Loc, "index must be a multiple of 4 in range [-256, 252].");
4271   case Match_InvalidMemoryIndexed8SImm7:
4272     return Error(Loc, "index must be a multiple of 8 in range [-512, 504].");
4273   case Match_InvalidMemoryIndexed16SImm7:
4274     return Error(Loc, "index must be a multiple of 16 in range [-1024, 1008].");
4275   case Match_InvalidMemoryIndexed8UImm5:
4276     return Error(Loc, "index must be a multiple of 8 in range [0, 248].");
4277   case Match_InvalidMemoryIndexed4UImm5:
4278     return Error(Loc, "index must be a multiple of 4 in range [0, 124].");
4279   case Match_InvalidMemoryIndexed2UImm5:
4280     return Error(Loc, "index must be a multiple of 2 in range [0, 62].");
4281   case Match_InvalidMemoryIndexed8UImm6:
4282     return Error(Loc, "index must be a multiple of 8 in range [0, 504].");
4283   case Match_InvalidMemoryIndexed16UImm6:
4284     return Error(Loc, "index must be a multiple of 16 in range [0, 1008].");
4285   case Match_InvalidMemoryIndexed4UImm6:
4286     return Error(Loc, "index must be a multiple of 4 in range [0, 252].");
4287   case Match_InvalidMemoryIndexed2UImm6:
4288     return Error(Loc, "index must be a multiple of 2 in range [0, 126].");
4289   case Match_InvalidMemoryIndexed1UImm6:
4290     return Error(Loc, "index must be in range [0, 63].");
4291   case Match_InvalidMemoryWExtend8:
4292     return Error(Loc,
4293                  "expected 'uxtw' or 'sxtw' with optional shift of #0");
4294   case Match_InvalidMemoryWExtend16:
4295     return Error(Loc,
4296                  "expected 'uxtw' or 'sxtw' with optional shift of #0 or #1");
4297   case Match_InvalidMemoryWExtend32:
4298     return Error(Loc,
4299                  "expected 'uxtw' or 'sxtw' with optional shift of #0 or #2");
4300   case Match_InvalidMemoryWExtend64:
4301     return Error(Loc,
4302                  "expected 'uxtw' or 'sxtw' with optional shift of #0 or #3");
4303   case Match_InvalidMemoryWExtend128:
4304     return Error(Loc,
4305                  "expected 'uxtw' or 'sxtw' with optional shift of #0 or #4");
4306   case Match_InvalidMemoryXExtend8:
4307     return Error(Loc,
4308                  "expected 'lsl' or 'sxtx' with optional shift of #0");
4309   case Match_InvalidMemoryXExtend16:
4310     return Error(Loc,
4311                  "expected 'lsl' or 'sxtx' with optional shift of #0 or #1");
4312   case Match_InvalidMemoryXExtend32:
4313     return Error(Loc,
4314                  "expected 'lsl' or 'sxtx' with optional shift of #0 or #2");
4315   case Match_InvalidMemoryXExtend64:
4316     return Error(Loc,
4317                  "expected 'lsl' or 'sxtx' with optional shift of #0 or #3");
4318   case Match_InvalidMemoryXExtend128:
4319     return Error(Loc,
4320                  "expected 'lsl' or 'sxtx' with optional shift of #0 or #4");
4321   case Match_InvalidMemoryIndexed1:
4322     return Error(Loc, "index must be an integer in range [0, 4095].");
4323   case Match_InvalidMemoryIndexed2:
4324     return Error(Loc, "index must be a multiple of 2 in range [0, 8190].");
4325   case Match_InvalidMemoryIndexed4:
4326     return Error(Loc, "index must be a multiple of 4 in range [0, 16380].");
4327   case Match_InvalidMemoryIndexed8:
4328     return Error(Loc, "index must be a multiple of 8 in range [0, 32760].");
4329   case Match_InvalidMemoryIndexed16:
4330     return Error(Loc, "index must be a multiple of 16 in range [0, 65520].");
4331   case Match_InvalidImm0_1:
4332     return Error(Loc, "immediate must be an integer in range [0, 1].");
4333   case Match_InvalidImm0_7:
4334     return Error(Loc, "immediate must be an integer in range [0, 7].");
4335   case Match_InvalidImm0_15:
4336     return Error(Loc, "immediate must be an integer in range [0, 15].");
4337   case Match_InvalidImm0_31:
4338     return Error(Loc, "immediate must be an integer in range [0, 31].");
4339   case Match_InvalidImm0_63:
4340     return Error(Loc, "immediate must be an integer in range [0, 63].");
4341   case Match_InvalidImm0_127:
4342     return Error(Loc, "immediate must be an integer in range [0, 127].");
4343   case Match_InvalidImm0_255:
4344     return Error(Loc, "immediate must be an integer in range [0, 255].");
4345   case Match_InvalidImm0_65535:
4346     return Error(Loc, "immediate must be an integer in range [0, 65535].");
4347   case Match_InvalidImm1_8:
4348     return Error(Loc, "immediate must be an integer in range [1, 8].");
4349   case Match_InvalidImm1_16:
4350     return Error(Loc, "immediate must be an integer in range [1, 16].");
4351   case Match_InvalidImm1_32:
4352     return Error(Loc, "immediate must be an integer in range [1, 32].");
4353   case Match_InvalidImm1_64:
4354     return Error(Loc, "immediate must be an integer in range [1, 64].");
4355   case Match_InvalidSVEAddSubImm8:
4356     return Error(Loc, "immediate must be an integer in range [0, 255]"
4357                       " with a shift amount of 0");
4358   case Match_InvalidSVEAddSubImm16:
4359   case Match_InvalidSVEAddSubImm32:
4360   case Match_InvalidSVEAddSubImm64:
4361     return Error(Loc, "immediate must be an integer in range [0, 255] or a "
4362                       "multiple of 256 in range [256, 65280]");
4363   case Match_InvalidSVECpyImm8:
4364     return Error(Loc, "immediate must be an integer in range [-128, 255]"
4365                       " with a shift amount of 0");
4366   case Match_InvalidSVECpyImm16:
4367     return Error(Loc, "immediate must be an integer in range [-128, 127] or a "
4368                       "multiple of 256 in range [-32768, 65280]");
4369   case Match_InvalidSVECpyImm32:
4370   case Match_InvalidSVECpyImm64:
4371     return Error(Loc, "immediate must be an integer in range [-128, 127] or a "
4372                       "multiple of 256 in range [-32768, 32512]");
4373   case Match_InvalidIndexRange1_1:
4374     return Error(Loc, "expected lane specifier '[1]'");
4375   case Match_InvalidIndexRange0_15:
4376     return Error(Loc, "vector lane must be an integer in range [0, 15].");
4377   case Match_InvalidIndexRange0_7:
4378     return Error(Loc, "vector lane must be an integer in range [0, 7].");
4379   case Match_InvalidIndexRange0_3:
4380     return Error(Loc, "vector lane must be an integer in range [0, 3].");
4381   case Match_InvalidIndexRange0_1:
4382     return Error(Loc, "vector lane must be an integer in range [0, 1].");
4383   case Match_InvalidSVEIndexRange0_63:
4384     return Error(Loc, "vector lane must be an integer in range [0, 63].");
4385   case Match_InvalidSVEIndexRange0_31:
4386     return Error(Loc, "vector lane must be an integer in range [0, 31].");
4387   case Match_InvalidSVEIndexRange0_15:
4388     return Error(Loc, "vector lane must be an integer in range [0, 15].");
4389   case Match_InvalidSVEIndexRange0_7:
4390     return Error(Loc, "vector lane must be an integer in range [0, 7].");
4391   case Match_InvalidSVEIndexRange0_3:
4392     return Error(Loc, "vector lane must be an integer in range [0, 3].");
4393   case Match_InvalidLabel:
4394     return Error(Loc, "expected label or encodable integer pc offset");
4395   case Match_MRS:
4396     return Error(Loc, "expected readable system register");
4397   case Match_MSR:
4398     return Error(Loc, "expected writable system register or pstate");
4399   case Match_InvalidComplexRotationEven:
4400     return Error(Loc, "complex rotation must be 0, 90, 180 or 270.");
4401   case Match_InvalidComplexRotationOdd:
4402     return Error(Loc, "complex rotation must be 90 or 270.");
4403   case Match_MnemonicFail: {
4404     std::string Suggestion = AArch64MnemonicSpellCheck(
4405         ((AArch64Operand &)*Operands[0]).getToken(),
4406         ComputeAvailableFeatures(STI->getFeatureBits()));
4407     return Error(Loc, "unrecognized instruction mnemonic" + Suggestion);
4408   }
4409   case Match_InvalidGPR64shifted8:
4410     return Error(Loc, "register must be x0..x30 or xzr, without shift");
4411   case Match_InvalidGPR64shifted16:
4412     return Error(Loc, "register must be x0..x30 or xzr, with required shift 'lsl #1'");
4413   case Match_InvalidGPR64shifted32:
4414     return Error(Loc, "register must be x0..x30 or xzr, with required shift 'lsl #2'");
4415   case Match_InvalidGPR64shifted64:
4416     return Error(Loc, "register must be x0..x30 or xzr, with required shift 'lsl #3'");
4417   case Match_InvalidGPR64NoXZRshifted8:
4418     return Error(Loc, "register must be x0..x30 without shift");
4419   case Match_InvalidGPR64NoXZRshifted16:
4420     return Error(Loc, "register must be x0..x30 with required shift 'lsl #1'");
4421   case Match_InvalidGPR64NoXZRshifted32:
4422     return Error(Loc, "register must be x0..x30 with required shift 'lsl #2'");
4423   case Match_InvalidGPR64NoXZRshifted64:
4424     return Error(Loc, "register must be x0..x30 with required shift 'lsl #3'");
4425   case Match_InvalidZPR32UXTW8:
4426   case Match_InvalidZPR32SXTW8:
4427     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].s, (uxtw|sxtw)'");
4428   case Match_InvalidZPR32UXTW16:
4429   case Match_InvalidZPR32SXTW16:
4430     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].s, (uxtw|sxtw) #1'");
4431   case Match_InvalidZPR32UXTW32:
4432   case Match_InvalidZPR32SXTW32:
4433     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].s, (uxtw|sxtw) #2'");
4434   case Match_InvalidZPR32UXTW64:
4435   case Match_InvalidZPR32SXTW64:
4436     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].s, (uxtw|sxtw) #3'");
4437   case Match_InvalidZPR64UXTW8:
4438   case Match_InvalidZPR64SXTW8:
4439     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].d, (uxtw|sxtw)'");
4440   case Match_InvalidZPR64UXTW16:
4441   case Match_InvalidZPR64SXTW16:
4442     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].d, (lsl|uxtw|sxtw) #1'");
4443   case Match_InvalidZPR64UXTW32:
4444   case Match_InvalidZPR64SXTW32:
4445     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].d, (lsl|uxtw|sxtw) #2'");
4446   case Match_InvalidZPR64UXTW64:
4447   case Match_InvalidZPR64SXTW64:
4448     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].d, (lsl|uxtw|sxtw) #3'");
4449   case Match_InvalidZPR32LSL8:
4450     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].s'");
4451   case Match_InvalidZPR32LSL16:
4452     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].s, lsl #1'");
4453   case Match_InvalidZPR32LSL32:
4454     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].s, lsl #2'");
4455   case Match_InvalidZPR32LSL64:
4456     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].s, lsl #3'");
4457   case Match_InvalidZPR64LSL8:
4458     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].d'");
4459   case Match_InvalidZPR64LSL16:
4460     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].d, lsl #1'");
4461   case Match_InvalidZPR64LSL32:
4462     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].d, lsl #2'");
4463   case Match_InvalidZPR64LSL64:
4464     return Error(Loc, "invalid shift/extend specified, expected 'z[0..31].d, lsl #3'");
4465   case Match_InvalidZPR0:
4466     return Error(Loc, "expected register without element width suffix");
4467   case Match_InvalidZPR8:
4468   case Match_InvalidZPR16:
4469   case Match_InvalidZPR32:
4470   case Match_InvalidZPR64:
4471   case Match_InvalidZPR128:
4472     return Error(Loc, "invalid element width");
4473   case Match_InvalidZPR_3b8:
4474     return Error(Loc, "Invalid restricted vector register, expected z0.b..z7.b");
4475   case Match_InvalidZPR_3b16:
4476     return Error(Loc, "Invalid restricted vector register, expected z0.h..z7.h");
4477   case Match_InvalidZPR_3b32:
4478     return Error(Loc, "Invalid restricted vector register, expected z0.s..z7.s");
4479   case Match_InvalidZPR_4b16:
4480     return Error(Loc, "Invalid restricted vector register, expected z0.h..z15.h");
4481   case Match_InvalidZPR_4b32:
4482     return Error(Loc, "Invalid restricted vector register, expected z0.s..z15.s");
4483   case Match_InvalidZPR_4b64:
4484     return Error(Loc, "Invalid restricted vector register, expected z0.d..z15.d");
4485   case Match_InvalidSVEPattern:
4486     return Error(Loc, "invalid predicate pattern");
4487   case Match_InvalidSVEPredicateAnyReg:
4488   case Match_InvalidSVEPredicateBReg:
4489   case Match_InvalidSVEPredicateHReg:
4490   case Match_InvalidSVEPredicateSReg:
4491   case Match_InvalidSVEPredicateDReg:
4492     return Error(Loc, "invalid predicate register.");
4493   case Match_InvalidSVEPredicate3bAnyReg:
4494     return Error(Loc, "invalid restricted predicate register, expected p0..p7 (without element suffix)");
4495   case Match_InvalidSVEPredicate3bBReg:
4496     return Error(Loc, "invalid restricted predicate register, expected p0.b..p7.b");
4497   case Match_InvalidSVEPredicate3bHReg:
4498     return Error(Loc, "invalid restricted predicate register, expected p0.h..p7.h");
4499   case Match_InvalidSVEPredicate3bSReg:
4500     return Error(Loc, "invalid restricted predicate register, expected p0.s..p7.s");
4501   case Match_InvalidSVEPredicate3bDReg:
4502     return Error(Loc, "invalid restricted predicate register, expected p0.d..p7.d");
4503   case Match_InvalidSVEExactFPImmOperandHalfOne:
4504     return Error(Loc, "Invalid floating point constant, expected 0.5 or 1.0.");
4505   case Match_InvalidSVEExactFPImmOperandHalfTwo:
4506     return Error(Loc, "Invalid floating point constant, expected 0.5 or 2.0.");
4507   case Match_InvalidSVEExactFPImmOperandZeroOne:
4508     return Error(Loc, "Invalid floating point constant, expected 0.0 or 1.0.");
4509   default:
4510     llvm_unreachable("unexpected error code!");
4511   }
4512 }
4513 
4514 static const char *getSubtargetFeatureName(uint64_t Val);
4515 
4516 bool AArch64AsmParser::MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
4517                                                OperandVector &Operands,
4518                                                MCStreamer &Out,
4519                                                uint64_t &ErrorInfo,
4520                                                bool MatchingInlineAsm) {
4521   assert(!Operands.empty() && "Unexpect empty operand list!");
4522   AArch64Operand &Op = static_cast<AArch64Operand &>(*Operands[0]);
4523   assert(Op.isToken() && "Leading operand should always be a mnemonic!");
4524 
4525   StringRef Tok = Op.getToken();
4526   unsigned NumOperands = Operands.size();
4527 
4528   if (NumOperands == 4 && Tok == "lsl") {
4529     AArch64Operand &Op2 = static_cast<AArch64Operand &>(*Operands[2]);
4530     AArch64Operand &Op3 = static_cast<AArch64Operand &>(*Operands[3]);
4531     if (Op2.isScalarReg() && Op3.isImm()) {
4532       const MCConstantExpr *Op3CE = dyn_cast<MCConstantExpr>(Op3.getImm());
4533       if (Op3CE) {
4534         uint64_t Op3Val = Op3CE->getValue();
4535         uint64_t NewOp3Val = 0;
4536         uint64_t NewOp4Val = 0;
4537         if (AArch64MCRegisterClasses[AArch64::GPR32allRegClassID].contains(
4538                 Op2.getReg())) {
4539           NewOp3Val = (32 - Op3Val) & 0x1f;
4540           NewOp4Val = 31 - Op3Val;
4541         } else {
4542           NewOp3Val = (64 - Op3Val) & 0x3f;
4543           NewOp4Val = 63 - Op3Val;
4544         }
4545 
4546         const MCExpr *NewOp3 = MCConstantExpr::create(NewOp3Val, getContext());
4547         const MCExpr *NewOp4 = MCConstantExpr::create(NewOp4Val, getContext());
4548 
4549         Operands[0] = AArch64Operand::CreateToken(
4550             "ubfm", false, Op.getStartLoc(), getContext());
4551         Operands.push_back(AArch64Operand::CreateImm(
4552             NewOp4, Op3.getStartLoc(), Op3.getEndLoc(), getContext()));
4553         Operands[3] = AArch64Operand::CreateImm(NewOp3, Op3.getStartLoc(),
4554                                                 Op3.getEndLoc(), getContext());
4555       }
4556     }
4557   } else if (NumOperands == 4 && Tok == "bfc") {
4558     // FIXME: Horrible hack to handle BFC->BFM alias.
4559     AArch64Operand &Op1 = static_cast<AArch64Operand &>(*Operands[1]);
4560     AArch64Operand LSBOp = static_cast<AArch64Operand &>(*Operands[2]);
4561     AArch64Operand WidthOp = static_cast<AArch64Operand &>(*Operands[3]);
4562 
4563     if (Op1.isScalarReg() && LSBOp.isImm() && WidthOp.isImm()) {
4564       const MCConstantExpr *LSBCE = dyn_cast<MCConstantExpr>(LSBOp.getImm());
4565       const MCConstantExpr *WidthCE = dyn_cast<MCConstantExpr>(WidthOp.getImm());
4566 
4567       if (LSBCE && WidthCE) {
4568         uint64_t LSB = LSBCE->getValue();
4569         uint64_t Width = WidthCE->getValue();
4570 
4571         uint64_t RegWidth = 0;
4572         if (AArch64MCRegisterClasses[AArch64::GPR64allRegClassID].contains(
4573                 Op1.getReg()))
4574           RegWidth = 64;
4575         else
4576           RegWidth = 32;
4577 
4578         if (LSB >= RegWidth)
4579           return Error(LSBOp.getStartLoc(),
4580                        "expected integer in range [0, 31]");
4581         if (Width < 1 || Width > RegWidth)
4582           return Error(WidthOp.getStartLoc(),
4583                        "expected integer in range [1, 32]");
4584 
4585         uint64_t ImmR = 0;
4586         if (RegWidth == 32)
4587           ImmR = (32 - LSB) & 0x1f;
4588         else
4589           ImmR = (64 - LSB) & 0x3f;
4590 
4591         uint64_t ImmS = Width - 1;
4592 
4593         if (ImmR != 0 && ImmS >= ImmR)
4594           return Error(WidthOp.getStartLoc(),
4595                        "requested insert overflows register");
4596 
4597         const MCExpr *ImmRExpr = MCConstantExpr::create(ImmR, getContext());
4598         const MCExpr *ImmSExpr = MCConstantExpr::create(ImmS, getContext());
4599         Operands[0] = AArch64Operand::CreateToken(
4600               "bfm", false, Op.getStartLoc(), getContext());
4601         Operands[2] = AArch64Operand::CreateReg(
4602             RegWidth == 32 ? AArch64::WZR : AArch64::XZR, RegKind::Scalar,
4603             SMLoc(), SMLoc(), getContext());
4604         Operands[3] = AArch64Operand::CreateImm(
4605             ImmRExpr, LSBOp.getStartLoc(), LSBOp.getEndLoc(), getContext());
4606         Operands.emplace_back(
4607             AArch64Operand::CreateImm(ImmSExpr, WidthOp.getStartLoc(),
4608                                       WidthOp.getEndLoc(), getContext()));
4609       }
4610     }
4611   } else if (NumOperands == 5) {
4612     // FIXME: Horrible hack to handle the BFI -> BFM, SBFIZ->SBFM, and
4613     // UBFIZ -> UBFM aliases.
4614     if (Tok == "bfi" || Tok == "sbfiz" || Tok == "ubfiz") {
4615       AArch64Operand &Op1 = static_cast<AArch64Operand &>(*Operands[1]);
4616       AArch64Operand &Op3 = static_cast<AArch64Operand &>(*Operands[3]);
4617       AArch64Operand &Op4 = static_cast<AArch64Operand &>(*Operands[4]);
4618 
4619       if (Op1.isScalarReg() && Op3.isImm() && Op4.isImm()) {
4620         const MCConstantExpr *Op3CE = dyn_cast<MCConstantExpr>(Op3.getImm());
4621         const MCConstantExpr *Op4CE = dyn_cast<MCConstantExpr>(Op4.getImm());
4622 
4623         if (Op3CE && Op4CE) {
4624           uint64_t Op3Val = Op3CE->getValue();
4625           uint64_t Op4Val = Op4CE->getValue();
4626 
4627           uint64_t RegWidth = 0;
4628           if (AArch64MCRegisterClasses[AArch64::GPR64allRegClassID].contains(
4629                   Op1.getReg()))
4630             RegWidth = 64;
4631           else
4632             RegWidth = 32;
4633 
4634           if (Op3Val >= RegWidth)
4635             return Error(Op3.getStartLoc(),
4636                          "expected integer in range [0, 31]");
4637           if (Op4Val < 1 || Op4Val > RegWidth)
4638             return Error(Op4.getStartLoc(),
4639                          "expected integer in range [1, 32]");
4640 
4641           uint64_t NewOp3Val = 0;
4642           if (RegWidth == 32)
4643             NewOp3Val = (32 - Op3Val) & 0x1f;
4644           else
4645             NewOp3Val = (64 - Op3Val) & 0x3f;
4646 
4647           uint64_t NewOp4Val = Op4Val - 1;
4648 
4649           if (NewOp3Val != 0 && NewOp4Val >= NewOp3Val)
4650             return Error(Op4.getStartLoc(),
4651                          "requested insert overflows register");
4652 
4653           const MCExpr *NewOp3 =
4654               MCConstantExpr::create(NewOp3Val, getContext());
4655           const MCExpr *NewOp4 =
4656               MCConstantExpr::create(NewOp4Val, getContext());
4657           Operands[3] = AArch64Operand::CreateImm(
4658               NewOp3, Op3.getStartLoc(), Op3.getEndLoc(), getContext());
4659           Operands[4] = AArch64Operand::CreateImm(
4660               NewOp4, Op4.getStartLoc(), Op4.getEndLoc(), getContext());
4661           if (Tok == "bfi")
4662             Operands[0] = AArch64Operand::CreateToken(
4663                 "bfm", false, Op.getStartLoc(), getContext());
4664           else if (Tok == "sbfiz")
4665             Operands[0] = AArch64Operand::CreateToken(
4666                 "sbfm", false, Op.getStartLoc(), getContext());
4667           else if (Tok == "ubfiz")
4668             Operands[0] = AArch64Operand::CreateToken(
4669                 "ubfm", false, Op.getStartLoc(), getContext());
4670           else
4671             llvm_unreachable("No valid mnemonic for alias?");
4672         }
4673       }
4674 
4675       // FIXME: Horrible hack to handle the BFXIL->BFM, SBFX->SBFM, and
4676       // UBFX -> UBFM aliases.
4677     } else if (NumOperands == 5 &&
4678                (Tok == "bfxil" || Tok == "sbfx" || Tok == "ubfx")) {
4679       AArch64Operand &Op1 = static_cast<AArch64Operand &>(*Operands[1]);
4680       AArch64Operand &Op3 = static_cast<AArch64Operand &>(*Operands[3]);
4681       AArch64Operand &Op4 = static_cast<AArch64Operand &>(*Operands[4]);
4682 
4683       if (Op1.isScalarReg() && Op3.isImm() && Op4.isImm()) {
4684         const MCConstantExpr *Op3CE = dyn_cast<MCConstantExpr>(Op3.getImm());
4685         const MCConstantExpr *Op4CE = dyn_cast<MCConstantExpr>(Op4.getImm());
4686 
4687         if (Op3CE && Op4CE) {
4688           uint64_t Op3Val = Op3CE->getValue();
4689           uint64_t Op4Val = Op4CE->getValue();
4690 
4691           uint64_t RegWidth = 0;
4692           if (AArch64MCRegisterClasses[AArch64::GPR64allRegClassID].contains(
4693                   Op1.getReg()))
4694             RegWidth = 64;
4695           else
4696             RegWidth = 32;
4697 
4698           if (Op3Val >= RegWidth)
4699             return Error(Op3.getStartLoc(),
4700                          "expected integer in range [0, 31]");
4701           if (Op4Val < 1 || Op4Val > RegWidth)
4702             return Error(Op4.getStartLoc(),
4703                          "expected integer in range [1, 32]");
4704 
4705           uint64_t NewOp4Val = Op3Val + Op4Val - 1;
4706 
4707           if (NewOp4Val >= RegWidth || NewOp4Val < Op3Val)
4708             return Error(Op4.getStartLoc(),
4709                          "requested extract overflows register");
4710 
4711           const MCExpr *NewOp4 =
4712               MCConstantExpr::create(NewOp4Val, getContext());
4713           Operands[4] = AArch64Operand::CreateImm(
4714               NewOp4, Op4.getStartLoc(), Op4.getEndLoc(), getContext());
4715           if (Tok == "bfxil")
4716             Operands[0] = AArch64Operand::CreateToken(
4717                 "bfm", false, Op.getStartLoc(), getContext());
4718           else if (Tok == "sbfx")
4719             Operands[0] = AArch64Operand::CreateToken(
4720                 "sbfm", false, Op.getStartLoc(), getContext());
4721           else if (Tok == "ubfx")
4722             Operands[0] = AArch64Operand::CreateToken(
4723                 "ubfm", false, Op.getStartLoc(), getContext());
4724           else
4725             llvm_unreachable("No valid mnemonic for alias?");
4726         }
4727       }
4728     }
4729   }
4730 
4731   // The Cyclone CPU and early successors didn't execute the zero-cycle zeroing
4732   // instruction for FP registers correctly in some rare circumstances. Convert
4733   // it to a safe instruction and warn (because silently changing someone's
4734   // assembly is rude).
4735   if (getSTI().getFeatureBits()[AArch64::FeatureZCZeroingFPWorkaround] &&
4736       NumOperands == 4 && Tok == "movi") {
4737     AArch64Operand &Op1 = static_cast<AArch64Operand &>(*Operands[1]);
4738     AArch64Operand &Op2 = static_cast<AArch64Operand &>(*Operands[2]);
4739     AArch64Operand &Op3 = static_cast<AArch64Operand &>(*Operands[3]);
4740     if ((Op1.isToken() && Op2.isNeonVectorReg() && Op3.isImm()) ||
4741         (Op1.isNeonVectorReg() && Op2.isToken() && Op3.isImm())) {
4742       StringRef Suffix = Op1.isToken() ? Op1.getToken() : Op2.getToken();
4743       if (Suffix.lower() == ".2d" &&
4744           cast<MCConstantExpr>(Op3.getImm())->getValue() == 0) {
4745         Warning(IDLoc, "instruction movi.2d with immediate #0 may not function"
4746                 " correctly on this CPU, converting to equivalent movi.16b");
4747         // Switch the suffix to .16b.
4748         unsigned Idx = Op1.isToken() ? 1 : 2;
4749         Operands[Idx] = AArch64Operand::CreateToken(".16b", false, IDLoc,
4750                                                   getContext());
4751       }
4752     }
4753   }
4754 
4755   // FIXME: Horrible hack for sxtw and uxtw with Wn src and Xd dst operands.
4756   //        InstAlias can't quite handle this since the reg classes aren't
4757   //        subclasses.
4758   if (NumOperands == 3 && (Tok == "sxtw" || Tok == "uxtw")) {
4759     // The source register can be Wn here, but the matcher expects a
4760     // GPR64. Twiddle it here if necessary.
4761     AArch64Operand &Op = static_cast<AArch64Operand &>(*Operands[2]);
4762     if (Op.isScalarReg()) {
4763       unsigned Reg = getXRegFromWReg(Op.getReg());
4764       Operands[2] = AArch64Operand::CreateReg(Reg, RegKind::Scalar,
4765                                               Op.getStartLoc(), Op.getEndLoc(),
4766                                               getContext());
4767     }
4768   }
4769   // FIXME: Likewise for sxt[bh] with a Xd dst operand
4770   else if (NumOperands == 3 && (Tok == "sxtb" || Tok == "sxth")) {
4771     AArch64Operand &Op = static_cast<AArch64Operand &>(*Operands[1]);
4772     if (Op.isScalarReg() &&
4773         AArch64MCRegisterClasses[AArch64::GPR64allRegClassID].contains(
4774             Op.getReg())) {
4775       // The source register can be Wn here, but the matcher expects a
4776       // GPR64. Twiddle it here if necessary.
4777       AArch64Operand &Op = static_cast<AArch64Operand &>(*Operands[2]);
4778       if (Op.isScalarReg()) {
4779         unsigned Reg = getXRegFromWReg(Op.getReg());
4780         Operands[2] = AArch64Operand::CreateReg(Reg, RegKind::Scalar,
4781                                                 Op.getStartLoc(),
4782                                                 Op.getEndLoc(), getContext());
4783       }
4784     }
4785   }
4786   // FIXME: Likewise for uxt[bh] with a Xd dst operand
4787   else if (NumOperands == 3 && (Tok == "uxtb" || Tok == "uxth")) {
4788     AArch64Operand &Op = static_cast<AArch64Operand &>(*Operands[1]);
4789     if (Op.isScalarReg() &&
4790         AArch64MCRegisterClasses[AArch64::GPR64allRegClassID].contains(
4791             Op.getReg())) {
4792       // The source register can be Wn here, but the matcher expects a
4793       // GPR32. Twiddle it here if necessary.
4794       AArch64Operand &Op = static_cast<AArch64Operand &>(*Operands[1]);
4795       if (Op.isScalarReg()) {
4796         unsigned Reg = getWRegFromXReg(Op.getReg());
4797         Operands[1] = AArch64Operand::CreateReg(Reg, RegKind::Scalar,
4798                                                 Op.getStartLoc(),
4799                                                 Op.getEndLoc(), getContext());
4800       }
4801     }
4802   }
4803 
4804   MCInst Inst;
4805   FeatureBitset MissingFeatures;
4806   // First try to match against the secondary set of tables containing the
4807   // short-form NEON instructions (e.g. "fadd.2s v0, v1, v2").
4808   unsigned MatchResult =
4809       MatchInstructionImpl(Operands, Inst, ErrorInfo, MissingFeatures,
4810                            MatchingInlineAsm, 1);
4811 
4812   // If that fails, try against the alternate table containing long-form NEON:
4813   // "fadd v0.2s, v1.2s, v2.2s"
4814   if (MatchResult != Match_Success) {
4815     // But first, save the short-form match result: we can use it in case the
4816     // long-form match also fails.
4817     auto ShortFormNEONErrorInfo = ErrorInfo;
4818     auto ShortFormNEONMatchResult = MatchResult;
4819     auto ShortFormNEONMissingFeatures = MissingFeatures;
4820 
4821     MatchResult =
4822         MatchInstructionImpl(Operands, Inst, ErrorInfo, MissingFeatures,
4823                              MatchingInlineAsm, 0);
4824 
4825     // Now, both matches failed, and the long-form match failed on the mnemonic
4826     // suffix token operand.  The short-form match failure is probably more
4827     // relevant: use it instead.
4828     if (MatchResult == Match_InvalidOperand && ErrorInfo == 1 &&
4829         Operands.size() > 1 && ((AArch64Operand &)*Operands[1]).isToken() &&
4830         ((AArch64Operand &)*Operands[1]).isTokenSuffix()) {
4831       MatchResult = ShortFormNEONMatchResult;
4832       ErrorInfo = ShortFormNEONErrorInfo;
4833       MissingFeatures = ShortFormNEONMissingFeatures;
4834     }
4835   }
4836 
4837   switch (MatchResult) {
4838   case Match_Success: {
4839     // Perform range checking and other semantic validations
4840     SmallVector<SMLoc, 8> OperandLocs;
4841     NumOperands = Operands.size();
4842     for (unsigned i = 1; i < NumOperands; ++i)
4843       OperandLocs.push_back(Operands[i]->getStartLoc());
4844     if (validateInstruction(Inst, IDLoc, OperandLocs))
4845       return true;
4846 
4847     Inst.setLoc(IDLoc);
4848     Out.emitInstruction(Inst, getSTI());
4849     return false;
4850   }
4851   case Match_MissingFeature: {
4852     assert(MissingFeatures.any() && "Unknown missing feature!");
4853     // Special case the error message for the very common case where only
4854     // a single subtarget feature is missing (neon, e.g.).
4855     std::string Msg = "instruction requires:";
4856     for (unsigned i = 0, e = MissingFeatures.size(); i != e; ++i) {
4857       if (MissingFeatures[i]) {
4858         Msg += " ";
4859         Msg += getSubtargetFeatureName(i);
4860       }
4861     }
4862     return Error(IDLoc, Msg);
4863   }
4864   case Match_MnemonicFail:
4865     return showMatchError(IDLoc, MatchResult, ErrorInfo, Operands);
4866   case Match_InvalidOperand: {
4867     SMLoc ErrorLoc = IDLoc;
4868 
4869     if (ErrorInfo != ~0ULL) {
4870       if (ErrorInfo >= Operands.size())
4871         return Error(IDLoc, "too few operands for instruction",
4872                      SMRange(IDLoc, getTok().getLoc()));
4873 
4874       ErrorLoc = ((AArch64Operand &)*Operands[ErrorInfo]).getStartLoc();
4875       if (ErrorLoc == SMLoc())
4876         ErrorLoc = IDLoc;
4877     }
4878     // If the match failed on a suffix token operand, tweak the diagnostic
4879     // accordingly.
4880     if (((AArch64Operand &)*Operands[ErrorInfo]).isToken() &&
4881         ((AArch64Operand &)*Operands[ErrorInfo]).isTokenSuffix())
4882       MatchResult = Match_InvalidSuffix;
4883 
4884     return showMatchError(ErrorLoc, MatchResult, ErrorInfo, Operands);
4885   }
4886   case Match_InvalidTiedOperand:
4887   case Match_InvalidMemoryIndexed1:
4888   case Match_InvalidMemoryIndexed2:
4889   case Match_InvalidMemoryIndexed4:
4890   case Match_InvalidMemoryIndexed8:
4891   case Match_InvalidMemoryIndexed16:
4892   case Match_InvalidCondCode:
4893   case Match_AddSubRegExtendSmall:
4894   case Match_AddSubRegExtendLarge:
4895   case Match_AddSubSecondSource:
4896   case Match_LogicalSecondSource:
4897   case Match_AddSubRegShift32:
4898   case Match_AddSubRegShift64:
4899   case Match_InvalidMovImm32Shift:
4900   case Match_InvalidMovImm64Shift:
4901   case Match_InvalidFPImm:
4902   case Match_InvalidMemoryWExtend8:
4903   case Match_InvalidMemoryWExtend16:
4904   case Match_InvalidMemoryWExtend32:
4905   case Match_InvalidMemoryWExtend64:
4906   case Match_InvalidMemoryWExtend128:
4907   case Match_InvalidMemoryXExtend8:
4908   case Match_InvalidMemoryXExtend16:
4909   case Match_InvalidMemoryXExtend32:
4910   case Match_InvalidMemoryXExtend64:
4911   case Match_InvalidMemoryXExtend128:
4912   case Match_InvalidMemoryIndexed1SImm4:
4913   case Match_InvalidMemoryIndexed2SImm4:
4914   case Match_InvalidMemoryIndexed3SImm4:
4915   case Match_InvalidMemoryIndexed4SImm4:
4916   case Match_InvalidMemoryIndexed1SImm6:
4917   case Match_InvalidMemoryIndexed16SImm4:
4918   case Match_InvalidMemoryIndexed4SImm7:
4919   case Match_InvalidMemoryIndexed8SImm7:
4920   case Match_InvalidMemoryIndexed16SImm7:
4921   case Match_InvalidMemoryIndexed8UImm5:
4922   case Match_InvalidMemoryIndexed4UImm5:
4923   case Match_InvalidMemoryIndexed2UImm5:
4924   case Match_InvalidMemoryIndexed1UImm6:
4925   case Match_InvalidMemoryIndexed2UImm6:
4926   case Match_InvalidMemoryIndexed4UImm6:
4927   case Match_InvalidMemoryIndexed8UImm6:
4928   case Match_InvalidMemoryIndexed16UImm6:
4929   case Match_InvalidMemoryIndexedSImm6:
4930   case Match_InvalidMemoryIndexedSImm5:
4931   case Match_InvalidMemoryIndexedSImm8:
4932   case Match_InvalidMemoryIndexedSImm9:
4933   case Match_InvalidMemoryIndexed16SImm9:
4934   case Match_InvalidMemoryIndexed8SImm10:
4935   case Match_InvalidImm0_1:
4936   case Match_InvalidImm0_7:
4937   case Match_InvalidImm0_15:
4938   case Match_InvalidImm0_31:
4939   case Match_InvalidImm0_63:
4940   case Match_InvalidImm0_127:
4941   case Match_InvalidImm0_255:
4942   case Match_InvalidImm0_65535:
4943   case Match_InvalidImm1_8:
4944   case Match_InvalidImm1_16:
4945   case Match_InvalidImm1_32:
4946   case Match_InvalidImm1_64:
4947   case Match_InvalidSVEAddSubImm8:
4948   case Match_InvalidSVEAddSubImm16:
4949   case Match_InvalidSVEAddSubImm32:
4950   case Match_InvalidSVEAddSubImm64:
4951   case Match_InvalidSVECpyImm8:
4952   case Match_InvalidSVECpyImm16:
4953   case Match_InvalidSVECpyImm32:
4954   case Match_InvalidSVECpyImm64:
4955   case Match_InvalidIndexRange1_1:
4956   case Match_InvalidIndexRange0_15:
4957   case Match_InvalidIndexRange0_7:
4958   case Match_InvalidIndexRange0_3:
4959   case Match_InvalidIndexRange0_1:
4960   case Match_InvalidSVEIndexRange0_63:
4961   case Match_InvalidSVEIndexRange0_31:
4962   case Match_InvalidSVEIndexRange0_15:
4963   case Match_InvalidSVEIndexRange0_7:
4964   case Match_InvalidSVEIndexRange0_3:
4965   case Match_InvalidLabel:
4966   case Match_InvalidComplexRotationEven:
4967   case Match_InvalidComplexRotationOdd:
4968   case Match_InvalidGPR64shifted8:
4969   case Match_InvalidGPR64shifted16:
4970   case Match_InvalidGPR64shifted32:
4971   case Match_InvalidGPR64shifted64:
4972   case Match_InvalidGPR64NoXZRshifted8:
4973   case Match_InvalidGPR64NoXZRshifted16:
4974   case Match_InvalidGPR64NoXZRshifted32:
4975   case Match_InvalidGPR64NoXZRshifted64:
4976   case Match_InvalidZPR32UXTW8:
4977   case Match_InvalidZPR32UXTW16:
4978   case Match_InvalidZPR32UXTW32:
4979   case Match_InvalidZPR32UXTW64:
4980   case Match_InvalidZPR32SXTW8:
4981   case Match_InvalidZPR32SXTW16:
4982   case Match_InvalidZPR32SXTW32:
4983   case Match_InvalidZPR32SXTW64:
4984   case Match_InvalidZPR64UXTW8:
4985   case Match_InvalidZPR64SXTW8:
4986   case Match_InvalidZPR64UXTW16:
4987   case Match_InvalidZPR64SXTW16:
4988   case Match_InvalidZPR64UXTW32:
4989   case Match_InvalidZPR64SXTW32:
4990   case Match_InvalidZPR64UXTW64:
4991   case Match_InvalidZPR64SXTW64:
4992   case Match_InvalidZPR32LSL8:
4993   case Match_InvalidZPR32LSL16:
4994   case Match_InvalidZPR32LSL32:
4995   case Match_InvalidZPR32LSL64:
4996   case Match_InvalidZPR64LSL8:
4997   case Match_InvalidZPR64LSL16:
4998   case Match_InvalidZPR64LSL32:
4999   case Match_InvalidZPR64LSL64:
5000   case Match_InvalidZPR0:
5001   case Match_InvalidZPR8:
5002   case Match_InvalidZPR16:
5003   case Match_InvalidZPR32:
5004   case Match_InvalidZPR64:
5005   case Match_InvalidZPR128:
5006   case Match_InvalidZPR_3b8:
5007   case Match_InvalidZPR_3b16:
5008   case Match_InvalidZPR_3b32:
5009   case Match_InvalidZPR_4b16:
5010   case Match_InvalidZPR_4b32:
5011   case Match_InvalidZPR_4b64:
5012   case Match_InvalidSVEPredicateAnyReg:
5013   case Match_InvalidSVEPattern:
5014   case Match_InvalidSVEPredicateBReg:
5015   case Match_InvalidSVEPredicateHReg:
5016   case Match_InvalidSVEPredicateSReg:
5017   case Match_InvalidSVEPredicateDReg:
5018   case Match_InvalidSVEPredicate3bAnyReg:
5019   case Match_InvalidSVEPredicate3bBReg:
5020   case Match_InvalidSVEPredicate3bHReg:
5021   case Match_InvalidSVEPredicate3bSReg:
5022   case Match_InvalidSVEPredicate3bDReg:
5023   case Match_InvalidSVEExactFPImmOperandHalfOne:
5024   case Match_InvalidSVEExactFPImmOperandHalfTwo:
5025   case Match_InvalidSVEExactFPImmOperandZeroOne:
5026   case Match_MSR:
5027   case Match_MRS: {
5028     if (ErrorInfo >= Operands.size())
5029       return Error(IDLoc, "too few operands for instruction", SMRange(IDLoc, (*Operands.back()).getEndLoc()));
5030     // Any time we get here, there's nothing fancy to do. Just get the
5031     // operand SMLoc and display the diagnostic.
5032     SMLoc ErrorLoc = ((AArch64Operand &)*Operands[ErrorInfo]).getStartLoc();
5033     if (ErrorLoc == SMLoc())
5034       ErrorLoc = IDLoc;
5035     return showMatchError(ErrorLoc, MatchResult, ErrorInfo, Operands);
5036   }
5037   }
5038 
5039   llvm_unreachable("Implement any new match types added!");
5040 }
5041 
5042 /// ParseDirective parses the arm specific directives
5043 bool AArch64AsmParser::ParseDirective(AsmToken DirectiveID) {
5044   const MCObjectFileInfo::Environment Format =
5045     getContext().getObjectFileInfo()->getObjectFileType();
5046   bool IsMachO = Format == MCObjectFileInfo::IsMachO;
5047 
5048   auto IDVal = DirectiveID.getIdentifier().lower();
5049   SMLoc Loc = DirectiveID.getLoc();
5050   if (IDVal == ".arch")
5051     parseDirectiveArch(Loc);
5052   else if (IDVal == ".cpu")
5053     parseDirectiveCPU(Loc);
5054   else if (IDVal == ".tlsdesccall")
5055     parseDirectiveTLSDescCall(Loc);
5056   else if (IDVal == ".ltorg" || IDVal == ".pool")
5057     parseDirectiveLtorg(Loc);
5058   else if (IDVal == ".unreq")
5059     parseDirectiveUnreq(Loc);
5060   else if (IDVal == ".inst")
5061     parseDirectiveInst(Loc);
5062   else if (IDVal == ".cfi_negate_ra_state")
5063     parseDirectiveCFINegateRAState();
5064   else if (IDVal == ".cfi_b_key_frame")
5065     parseDirectiveCFIBKeyFrame();
5066   else if (IDVal == ".arch_extension")
5067     parseDirectiveArchExtension(Loc);
5068   else if (IsMachO) {
5069     if (IDVal == MCLOHDirectiveName())
5070       parseDirectiveLOH(IDVal, Loc);
5071     else
5072       return true;
5073   } else
5074     return true;
5075   return false;
5076 }
5077 
5078 static void ExpandCryptoAEK(AArch64::ArchKind ArchKind,
5079                             SmallVector<StringRef, 4> &RequestedExtensions) {
5080   const bool NoCrypto =
5081       (std::find(RequestedExtensions.begin(), RequestedExtensions.end(),
5082                  "nocrypto") != std::end(RequestedExtensions));
5083   const bool Crypto =
5084       (std::find(RequestedExtensions.begin(), RequestedExtensions.end(),
5085                  "crypto") != std::end(RequestedExtensions));
5086 
5087   if (!NoCrypto && Crypto) {
5088     switch (ArchKind) {
5089     default:
5090       // Map 'generic' (and others) to sha2 and aes, because
5091       // that was the traditional meaning of crypto.
5092     case AArch64::ArchKind::ARMV8_1A:
5093     case AArch64::ArchKind::ARMV8_2A:
5094     case AArch64::ArchKind::ARMV8_3A:
5095       RequestedExtensions.push_back("sha2");
5096       RequestedExtensions.push_back("aes");
5097       break;
5098     case AArch64::ArchKind::ARMV8_4A:
5099     case AArch64::ArchKind::ARMV8_5A:
5100     case AArch64::ArchKind::ARMV8_6A:
5101       RequestedExtensions.push_back("sm4");
5102       RequestedExtensions.push_back("sha3");
5103       RequestedExtensions.push_back("sha2");
5104       RequestedExtensions.push_back("aes");
5105       break;
5106     }
5107   } else if (NoCrypto) {
5108     switch (ArchKind) {
5109     default:
5110       // Map 'generic' (and others) to sha2 and aes, because
5111       // that was the traditional meaning of crypto.
5112     case AArch64::ArchKind::ARMV8_1A:
5113     case AArch64::ArchKind::ARMV8_2A:
5114     case AArch64::ArchKind::ARMV8_3A:
5115       RequestedExtensions.push_back("nosha2");
5116       RequestedExtensions.push_back("noaes");
5117       break;
5118     case AArch64::ArchKind::ARMV8_4A:
5119     case AArch64::ArchKind::ARMV8_5A:
5120     case AArch64::ArchKind::ARMV8_6A:
5121       RequestedExtensions.push_back("nosm4");
5122       RequestedExtensions.push_back("nosha3");
5123       RequestedExtensions.push_back("nosha2");
5124       RequestedExtensions.push_back("noaes");
5125       break;
5126     }
5127   }
5128 }
5129 
5130 /// parseDirectiveArch
5131 ///   ::= .arch token
5132 bool AArch64AsmParser::parseDirectiveArch(SMLoc L) {
5133   SMLoc ArchLoc = getLoc();
5134 
5135   StringRef Arch, ExtensionString;
5136   std::tie(Arch, ExtensionString) =
5137       getParser().parseStringToEndOfStatement().trim().split('+');
5138 
5139   AArch64::ArchKind ID = AArch64::parseArch(Arch);
5140   if (ID == AArch64::ArchKind::INVALID)
5141     return Error(ArchLoc, "unknown arch name");
5142 
5143   if (parseToken(AsmToken::EndOfStatement))
5144     return true;
5145 
5146   // Get the architecture and extension features.
5147   std::vector<StringRef> AArch64Features;
5148   AArch64::getArchFeatures(ID, AArch64Features);
5149   AArch64::getExtensionFeatures(AArch64::getDefaultExtensions("generic", ID),
5150                                 AArch64Features);
5151 
5152   MCSubtargetInfo &STI = copySTI();
5153   std::vector<std::string> ArchFeatures(AArch64Features.begin(), AArch64Features.end());
5154   STI.setDefaultFeatures("generic", join(ArchFeatures.begin(), ArchFeatures.end(), ","));
5155 
5156   SmallVector<StringRef, 4> RequestedExtensions;
5157   if (!ExtensionString.empty())
5158     ExtensionString.split(RequestedExtensions, '+');
5159 
5160   ExpandCryptoAEK(ID, RequestedExtensions);
5161 
5162   FeatureBitset Features = STI.getFeatureBits();
5163   for (auto Name : RequestedExtensions) {
5164     bool EnableFeature = true;
5165 
5166     if (Name.startswith_lower("no")) {
5167       EnableFeature = false;
5168       Name = Name.substr(2);
5169     }
5170 
5171     for (const auto &Extension : ExtensionMap) {
5172       if (Extension.Name != Name)
5173         continue;
5174 
5175       if (Extension.Features.none())
5176         report_fatal_error("unsupported architectural extension: " + Name);
5177 
5178       FeatureBitset ToggleFeatures = EnableFeature
5179                                          ? (~Features & Extension.Features)
5180                                          : ( Features & Extension.Features);
5181       FeatureBitset Features =
5182           ComputeAvailableFeatures(STI.ToggleFeature(ToggleFeatures));
5183       setAvailableFeatures(Features);
5184       break;
5185     }
5186   }
5187   return false;
5188 }
5189 
5190 /// parseDirectiveArchExtension
5191 ///   ::= .arch_extension [no]feature
5192 bool AArch64AsmParser::parseDirectiveArchExtension(SMLoc L) {
5193   SMLoc ExtLoc = getLoc();
5194 
5195   StringRef Name = getParser().parseStringToEndOfStatement().trim();
5196 
5197   if (parseToken(AsmToken::EndOfStatement,
5198                  "unexpected token in '.arch_extension' directive"))
5199     return true;
5200 
5201   bool EnableFeature = true;
5202   if (Name.startswith_lower("no")) {
5203     EnableFeature = false;
5204     Name = Name.substr(2);
5205   }
5206 
5207   MCSubtargetInfo &STI = copySTI();
5208   FeatureBitset Features = STI.getFeatureBits();
5209   for (const auto &Extension : ExtensionMap) {
5210     if (Extension.Name != Name)
5211       continue;
5212 
5213     if (Extension.Features.none())
5214       return Error(ExtLoc, "unsupported architectural extension: " + Name);
5215 
5216     FeatureBitset ToggleFeatures = EnableFeature
5217                                        ? (~Features & Extension.Features)
5218                                        : (Features & Extension.Features);
5219     FeatureBitset Features =
5220         ComputeAvailableFeatures(STI.ToggleFeature(ToggleFeatures));
5221     setAvailableFeatures(Features);
5222     return false;
5223   }
5224 
5225   return Error(ExtLoc, "unknown architectural extension: " + Name);
5226 }
5227 
5228 static SMLoc incrementLoc(SMLoc L, int Offset) {
5229   return SMLoc::getFromPointer(L.getPointer() + Offset);
5230 }
5231 
5232 /// parseDirectiveCPU
5233 ///   ::= .cpu id
5234 bool AArch64AsmParser::parseDirectiveCPU(SMLoc L) {
5235   SMLoc CurLoc = getLoc();
5236 
5237   StringRef CPU, ExtensionString;
5238   std::tie(CPU, ExtensionString) =
5239       getParser().parseStringToEndOfStatement().trim().split('+');
5240 
5241   if (parseToken(AsmToken::EndOfStatement))
5242     return true;
5243 
5244   SmallVector<StringRef, 4> RequestedExtensions;
5245   if (!ExtensionString.empty())
5246     ExtensionString.split(RequestedExtensions, '+');
5247 
5248   // FIXME This is using tablegen data, but should be moved to ARMTargetParser
5249   // once that is tablegen'ed
5250   if (!getSTI().isCPUStringValid(CPU)) {
5251     Error(CurLoc, "unknown CPU name");
5252     return false;
5253   }
5254 
5255   MCSubtargetInfo &STI = copySTI();
5256   STI.setDefaultFeatures(CPU, "");
5257   CurLoc = incrementLoc(CurLoc, CPU.size());
5258 
5259   ExpandCryptoAEK(llvm::AArch64::getCPUArchKind(CPU), RequestedExtensions);
5260 
5261   FeatureBitset Features = STI.getFeatureBits();
5262   for (auto Name : RequestedExtensions) {
5263     // Advance source location past '+'.
5264     CurLoc = incrementLoc(CurLoc, 1);
5265 
5266     bool EnableFeature = true;
5267 
5268     if (Name.startswith_lower("no")) {
5269       EnableFeature = false;
5270       Name = Name.substr(2);
5271     }
5272 
5273     bool FoundExtension = false;
5274     for (const auto &Extension : ExtensionMap) {
5275       if (Extension.Name != Name)
5276         continue;
5277 
5278       if (Extension.Features.none())
5279         report_fatal_error("unsupported architectural extension: " + Name);
5280 
5281       FeatureBitset ToggleFeatures = EnableFeature
5282                                          ? (~Features & Extension.Features)
5283                                          : ( Features & Extension.Features);
5284       FeatureBitset Features =
5285           ComputeAvailableFeatures(STI.ToggleFeature(ToggleFeatures));
5286       setAvailableFeatures(Features);
5287       FoundExtension = true;
5288 
5289       break;
5290     }
5291 
5292     if (!FoundExtension)
5293       Error(CurLoc, "unsupported architectural extension");
5294 
5295     CurLoc = incrementLoc(CurLoc, Name.size());
5296   }
5297   return false;
5298 }
5299 
5300 /// parseDirectiveInst
5301 ///  ::= .inst opcode [, ...]
5302 bool AArch64AsmParser::parseDirectiveInst(SMLoc Loc) {
5303   if (getLexer().is(AsmToken::EndOfStatement))
5304     return Error(Loc, "expected expression following '.inst' directive");
5305 
5306   auto parseOp = [&]() -> bool {
5307     SMLoc L = getLoc();
5308     const MCExpr *Expr = nullptr;
5309     if (check(getParser().parseExpression(Expr), L, "expected expression"))
5310       return true;
5311     const MCConstantExpr *Value = dyn_cast_or_null<MCConstantExpr>(Expr);
5312     if (check(!Value, L, "expected constant expression"))
5313       return true;
5314     getTargetStreamer().emitInst(Value->getValue());
5315     return false;
5316   };
5317 
5318   if (parseMany(parseOp))
5319     return addErrorSuffix(" in '.inst' directive");
5320   return false;
5321 }
5322 
5323 // parseDirectiveTLSDescCall:
5324 //   ::= .tlsdesccall symbol
5325 bool AArch64AsmParser::parseDirectiveTLSDescCall(SMLoc L) {
5326   StringRef Name;
5327   if (check(getParser().parseIdentifier(Name), L,
5328             "expected symbol after directive") ||
5329       parseToken(AsmToken::EndOfStatement))
5330     return true;
5331 
5332   MCSymbol *Sym = getContext().getOrCreateSymbol(Name);
5333   const MCExpr *Expr = MCSymbolRefExpr::create(Sym, getContext());
5334   Expr = AArch64MCExpr::create(Expr, AArch64MCExpr::VK_TLSDESC, getContext());
5335 
5336   MCInst Inst;
5337   Inst.setOpcode(AArch64::TLSDESCCALL);
5338   Inst.addOperand(MCOperand::createExpr(Expr));
5339 
5340   getParser().getStreamer().emitInstruction(Inst, getSTI());
5341   return false;
5342 }
5343 
5344 /// ::= .loh <lohName | lohId> label1, ..., labelN
5345 /// The number of arguments depends on the loh identifier.
5346 bool AArch64AsmParser::parseDirectiveLOH(StringRef IDVal, SMLoc Loc) {
5347   MCLOHType Kind;
5348   if (getParser().getTok().isNot(AsmToken::Identifier)) {
5349     if (getParser().getTok().isNot(AsmToken::Integer))
5350       return TokError("expected an identifier or a number in directive");
5351     // We successfully get a numeric value for the identifier.
5352     // Check if it is valid.
5353     int64_t Id = getParser().getTok().getIntVal();
5354     if (Id <= -1U && !isValidMCLOHType(Id))
5355       return TokError("invalid numeric identifier in directive");
5356     Kind = (MCLOHType)Id;
5357   } else {
5358     StringRef Name = getTok().getIdentifier();
5359     // We successfully parse an identifier.
5360     // Check if it is a recognized one.
5361     int Id = MCLOHNameToId(Name);
5362 
5363     if (Id == -1)
5364       return TokError("invalid identifier in directive");
5365     Kind = (MCLOHType)Id;
5366   }
5367   // Consume the identifier.
5368   Lex();
5369   // Get the number of arguments of this LOH.
5370   int NbArgs = MCLOHIdToNbArgs(Kind);
5371 
5372   assert(NbArgs != -1 && "Invalid number of arguments");
5373 
5374   SmallVector<MCSymbol *, 3> Args;
5375   for (int Idx = 0; Idx < NbArgs; ++Idx) {
5376     StringRef Name;
5377     if (getParser().parseIdentifier(Name))
5378       return TokError("expected identifier in directive");
5379     Args.push_back(getContext().getOrCreateSymbol(Name));
5380 
5381     if (Idx + 1 == NbArgs)
5382       break;
5383     if (parseToken(AsmToken::Comma,
5384                    "unexpected token in '" + Twine(IDVal) + "' directive"))
5385       return true;
5386   }
5387   if (parseToken(AsmToken::EndOfStatement,
5388                  "unexpected token in '" + Twine(IDVal) + "' directive"))
5389     return true;
5390 
5391   getStreamer().emitLOHDirective((MCLOHType)Kind, Args);
5392   return false;
5393 }
5394 
5395 /// parseDirectiveLtorg
5396 ///  ::= .ltorg | .pool
5397 bool AArch64AsmParser::parseDirectiveLtorg(SMLoc L) {
5398   if (parseToken(AsmToken::EndOfStatement, "unexpected token in directive"))
5399     return true;
5400   getTargetStreamer().emitCurrentConstantPool();
5401   return false;
5402 }
5403 
5404 /// parseDirectiveReq
5405 ///  ::= name .req registername
5406 bool AArch64AsmParser::parseDirectiveReq(StringRef Name, SMLoc L) {
5407   MCAsmParser &Parser = getParser();
5408   Parser.Lex(); // Eat the '.req' token.
5409   SMLoc SRegLoc = getLoc();
5410   RegKind RegisterKind = RegKind::Scalar;
5411   unsigned RegNum;
5412   OperandMatchResultTy ParseRes = tryParseScalarRegister(RegNum);
5413 
5414   if (ParseRes != MatchOperand_Success) {
5415     StringRef Kind;
5416     RegisterKind = RegKind::NeonVector;
5417     ParseRes = tryParseVectorRegister(RegNum, Kind, RegKind::NeonVector);
5418 
5419     if (ParseRes == MatchOperand_ParseFail)
5420       return true;
5421 
5422     if (ParseRes == MatchOperand_Success && !Kind.empty())
5423       return Error(SRegLoc, "vector register without type specifier expected");
5424   }
5425 
5426   if (ParseRes != MatchOperand_Success) {
5427     StringRef Kind;
5428     RegisterKind = RegKind::SVEDataVector;
5429     ParseRes =
5430         tryParseVectorRegister(RegNum, Kind, RegKind::SVEDataVector);
5431 
5432     if (ParseRes == MatchOperand_ParseFail)
5433       return true;
5434 
5435     if (ParseRes == MatchOperand_Success && !Kind.empty())
5436       return Error(SRegLoc,
5437                    "sve vector register without type specifier expected");
5438   }
5439 
5440   if (ParseRes != MatchOperand_Success) {
5441     StringRef Kind;
5442     RegisterKind = RegKind::SVEPredicateVector;
5443     ParseRes = tryParseVectorRegister(RegNum, Kind, RegKind::SVEPredicateVector);
5444 
5445     if (ParseRes == MatchOperand_ParseFail)
5446       return true;
5447 
5448     if (ParseRes == MatchOperand_Success && !Kind.empty())
5449       return Error(SRegLoc,
5450                    "sve predicate register without type specifier expected");
5451   }
5452 
5453   if (ParseRes != MatchOperand_Success)
5454     return Error(SRegLoc, "register name or alias expected");
5455 
5456   // Shouldn't be anything else.
5457   if (parseToken(AsmToken::EndOfStatement,
5458                  "unexpected input in .req directive"))
5459     return true;
5460 
5461   auto pair = std::make_pair(RegisterKind, (unsigned) RegNum);
5462   if (RegisterReqs.insert(std::make_pair(Name, pair)).first->second != pair)
5463     Warning(L, "ignoring redefinition of register alias '" + Name + "'");
5464 
5465   return false;
5466 }
5467 
5468 /// parseDirectiveUneq
5469 ///  ::= .unreq registername
5470 bool AArch64AsmParser::parseDirectiveUnreq(SMLoc L) {
5471   MCAsmParser &Parser = getParser();
5472   if (getTok().isNot(AsmToken::Identifier))
5473     return TokError("unexpected input in .unreq directive.");
5474   RegisterReqs.erase(Parser.getTok().getIdentifier().lower());
5475   Parser.Lex(); // Eat the identifier.
5476   if (parseToken(AsmToken::EndOfStatement))
5477     return addErrorSuffix("in '.unreq' directive");
5478   return false;
5479 }
5480 
5481 bool AArch64AsmParser::parseDirectiveCFINegateRAState() {
5482   if (parseToken(AsmToken::EndOfStatement, "unexpected token in directive"))
5483     return true;
5484   getStreamer().emitCFINegateRAState();
5485   return false;
5486 }
5487 
5488 /// parseDirectiveCFIBKeyFrame
5489 /// ::= .cfi_b_key
5490 bool AArch64AsmParser::parseDirectiveCFIBKeyFrame() {
5491   if (parseToken(AsmToken::EndOfStatement,
5492                  "unexpected token in '.cfi_b_key_frame'"))
5493     return true;
5494   getStreamer().emitCFIBKeyFrame();
5495   return false;
5496 }
5497 
5498 bool
5499 AArch64AsmParser::classifySymbolRef(const MCExpr *Expr,
5500                                     AArch64MCExpr::VariantKind &ELFRefKind,
5501                                     MCSymbolRefExpr::VariantKind &DarwinRefKind,
5502                                     int64_t &Addend) {
5503   ELFRefKind = AArch64MCExpr::VK_INVALID;
5504   DarwinRefKind = MCSymbolRefExpr::VK_None;
5505   Addend = 0;
5506 
5507   if (const AArch64MCExpr *AE = dyn_cast<AArch64MCExpr>(Expr)) {
5508     ELFRefKind = AE->getKind();
5509     Expr = AE->getSubExpr();
5510   }
5511 
5512   const MCSymbolRefExpr *SE = dyn_cast<MCSymbolRefExpr>(Expr);
5513   if (SE) {
5514     // It's a simple symbol reference with no addend.
5515     DarwinRefKind = SE->getKind();
5516     return true;
5517   }
5518 
5519   // Check that it looks like a symbol + an addend
5520   MCValue Res;
5521   bool Relocatable = Expr->evaluateAsRelocatable(Res, nullptr, nullptr);
5522   if (!Relocatable || Res.getSymB())
5523     return false;
5524 
5525   // Treat expressions with an ELFRefKind (like ":abs_g1:3", or
5526   // ":abs_g1:x" where x is constant) as symbolic even if there is no symbol.
5527   if (!Res.getSymA() && ELFRefKind == AArch64MCExpr::VK_INVALID)
5528     return false;
5529 
5530   if (Res.getSymA())
5531     DarwinRefKind = Res.getSymA()->getKind();
5532   Addend = Res.getConstant();
5533 
5534   // It's some symbol reference + a constant addend, but really
5535   // shouldn't use both Darwin and ELF syntax.
5536   return ELFRefKind == AArch64MCExpr::VK_INVALID ||
5537          DarwinRefKind == MCSymbolRefExpr::VK_None;
5538 }
5539 
5540 /// Force static initialization.
5541 extern "C" LLVM_EXTERNAL_VISIBILITY void LLVMInitializeAArch64AsmParser() {
5542   RegisterMCAsmParser<AArch64AsmParser> X(getTheAArch64leTarget());
5543   RegisterMCAsmParser<AArch64AsmParser> Y(getTheAArch64beTarget());
5544   RegisterMCAsmParser<AArch64AsmParser> Z(getTheARM64Target());
5545   RegisterMCAsmParser<AArch64AsmParser> W(getTheARM64_32Target());
5546   RegisterMCAsmParser<AArch64AsmParser> V(getTheAArch64_32Target());
5547 }
5548 
5549 #define GET_REGISTER_MATCHER
5550 #define GET_SUBTARGET_FEATURE_NAME
5551 #define GET_MATCHER_IMPLEMENTATION
5552 #define GET_MNEMONIC_SPELL_CHECKER
5553 #include "AArch64GenAsmMatcher.inc"
5554 
5555 // Define this matcher function after the auto-generated include so we
5556 // have the match class enum definitions.
5557 unsigned AArch64AsmParser::validateTargetOperandClass(MCParsedAsmOperand &AsmOp,
5558                                                       unsigned Kind) {
5559   AArch64Operand &Op = static_cast<AArch64Operand &>(AsmOp);
5560   // If the kind is a token for a literal immediate, check if our asm
5561   // operand matches. This is for InstAliases which have a fixed-value
5562   // immediate in the syntax.
5563   int64_t ExpectedVal;
5564   switch (Kind) {
5565   default:
5566     return Match_InvalidOperand;
5567   case MCK__HASH_0:
5568     ExpectedVal = 0;
5569     break;
5570   case MCK__HASH_1:
5571     ExpectedVal = 1;
5572     break;
5573   case MCK__HASH_12:
5574     ExpectedVal = 12;
5575     break;
5576   case MCK__HASH_16:
5577     ExpectedVal = 16;
5578     break;
5579   case MCK__HASH_2:
5580     ExpectedVal = 2;
5581     break;
5582   case MCK__HASH_24:
5583     ExpectedVal = 24;
5584     break;
5585   case MCK__HASH_3:
5586     ExpectedVal = 3;
5587     break;
5588   case MCK__HASH_32:
5589     ExpectedVal = 32;
5590     break;
5591   case MCK__HASH_4:
5592     ExpectedVal = 4;
5593     break;
5594   case MCK__HASH_48:
5595     ExpectedVal = 48;
5596     break;
5597   case MCK__HASH_6:
5598     ExpectedVal = 6;
5599     break;
5600   case MCK__HASH_64:
5601     ExpectedVal = 64;
5602     break;
5603   case MCK__HASH_8:
5604     ExpectedVal = 8;
5605     break;
5606   }
5607   if (!Op.isImm())
5608     return Match_InvalidOperand;
5609   const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Op.getImm());
5610   if (!CE)
5611     return Match_InvalidOperand;
5612   if (CE->getValue() == ExpectedVal)
5613     return Match_Success;
5614   return Match_InvalidOperand;
5615 }
5616 
5617 OperandMatchResultTy
5618 AArch64AsmParser::tryParseGPRSeqPair(OperandVector &Operands) {
5619 
5620   SMLoc S = getLoc();
5621 
5622   if (getParser().getTok().isNot(AsmToken::Identifier)) {
5623     Error(S, "expected register");
5624     return MatchOperand_ParseFail;
5625   }
5626 
5627   unsigned FirstReg;
5628   OperandMatchResultTy Res = tryParseScalarRegister(FirstReg);
5629   if (Res != MatchOperand_Success)
5630     return MatchOperand_ParseFail;
5631 
5632   const MCRegisterClass &WRegClass =
5633       AArch64MCRegisterClasses[AArch64::GPR32RegClassID];
5634   const MCRegisterClass &XRegClass =
5635       AArch64MCRegisterClasses[AArch64::GPR64RegClassID];
5636 
5637   bool isXReg = XRegClass.contains(FirstReg),
5638        isWReg = WRegClass.contains(FirstReg);
5639   if (!isXReg && !isWReg) {
5640     Error(S, "expected first even register of a "
5641              "consecutive same-size even/odd register pair");
5642     return MatchOperand_ParseFail;
5643   }
5644 
5645   const MCRegisterInfo *RI = getContext().getRegisterInfo();
5646   unsigned FirstEncoding = RI->getEncodingValue(FirstReg);
5647 
5648   if (FirstEncoding & 0x1) {
5649     Error(S, "expected first even register of a "
5650              "consecutive same-size even/odd register pair");
5651     return MatchOperand_ParseFail;
5652   }
5653 
5654   if (getParser().getTok().isNot(AsmToken::Comma)) {
5655     Error(getLoc(), "expected comma");
5656     return MatchOperand_ParseFail;
5657   }
5658   // Eat the comma
5659   getParser().Lex();
5660 
5661   SMLoc E = getLoc();
5662   unsigned SecondReg;
5663   Res = tryParseScalarRegister(SecondReg);
5664   if (Res != MatchOperand_Success)
5665     return MatchOperand_ParseFail;
5666 
5667   if (RI->getEncodingValue(SecondReg) != FirstEncoding + 1 ||
5668       (isXReg && !XRegClass.contains(SecondReg)) ||
5669       (isWReg && !WRegClass.contains(SecondReg))) {
5670     Error(E,"expected second odd register of a "
5671              "consecutive same-size even/odd register pair");
5672     return MatchOperand_ParseFail;
5673   }
5674 
5675   unsigned Pair = 0;
5676   if (isXReg) {
5677     Pair = RI->getMatchingSuperReg(FirstReg, AArch64::sube64,
5678            &AArch64MCRegisterClasses[AArch64::XSeqPairsClassRegClassID]);
5679   } else {
5680     Pair = RI->getMatchingSuperReg(FirstReg, AArch64::sube32,
5681            &AArch64MCRegisterClasses[AArch64::WSeqPairsClassRegClassID]);
5682   }
5683 
5684   Operands.push_back(AArch64Operand::CreateReg(Pair, RegKind::Scalar, S,
5685       getLoc(), getContext()));
5686 
5687   return MatchOperand_Success;
5688 }
5689 
5690 template <bool ParseShiftExtend, bool ParseSuffix>
5691 OperandMatchResultTy
5692 AArch64AsmParser::tryParseSVEDataVector(OperandVector &Operands) {
5693   const SMLoc S = getLoc();
5694   // Check for a SVE vector register specifier first.
5695   unsigned RegNum;
5696   StringRef Kind;
5697 
5698   OperandMatchResultTy Res =
5699       tryParseVectorRegister(RegNum, Kind, RegKind::SVEDataVector);
5700 
5701   if (Res != MatchOperand_Success)
5702     return Res;
5703 
5704   if (ParseSuffix && Kind.empty())
5705     return MatchOperand_NoMatch;
5706 
5707   const auto &KindRes = parseVectorKind(Kind, RegKind::SVEDataVector);
5708   if (!KindRes)
5709     return MatchOperand_NoMatch;
5710 
5711   unsigned ElementWidth = KindRes->second;
5712 
5713   // No shift/extend is the default.
5714   if (!ParseShiftExtend || getParser().getTok().isNot(AsmToken::Comma)) {
5715     Operands.push_back(AArch64Operand::CreateVectorReg(
5716         RegNum, RegKind::SVEDataVector, ElementWidth, S, S, getContext()));
5717 
5718     OperandMatchResultTy Res = tryParseVectorIndex(Operands);
5719     if (Res == MatchOperand_ParseFail)
5720       return MatchOperand_ParseFail;
5721     return MatchOperand_Success;
5722   }
5723 
5724   // Eat the comma
5725   getParser().Lex();
5726 
5727   // Match the shift
5728   SmallVector<std::unique_ptr<MCParsedAsmOperand>, 1> ExtOpnd;
5729   Res = tryParseOptionalShiftExtend(ExtOpnd);
5730   if (Res != MatchOperand_Success)
5731     return Res;
5732 
5733   auto Ext = static_cast<AArch64Operand *>(ExtOpnd.back().get());
5734   Operands.push_back(AArch64Operand::CreateVectorReg(
5735       RegNum, RegKind::SVEDataVector, ElementWidth, S, Ext->getEndLoc(),
5736       getContext(), Ext->getShiftExtendType(), Ext->getShiftExtendAmount(),
5737       Ext->hasShiftExtendAmount()));
5738 
5739   return MatchOperand_Success;
5740 }
5741 
5742 OperandMatchResultTy
5743 AArch64AsmParser::tryParseSVEPattern(OperandVector &Operands) {
5744   MCAsmParser &Parser = getParser();
5745 
5746   SMLoc SS = getLoc();
5747   const AsmToken &TokE = Parser.getTok();
5748   bool IsHash = TokE.is(AsmToken::Hash);
5749 
5750   if (!IsHash && TokE.isNot(AsmToken::Identifier))
5751     return MatchOperand_NoMatch;
5752 
5753   int64_t Pattern;
5754   if (IsHash) {
5755     Parser.Lex(); // Eat hash
5756 
5757     // Parse the immediate operand.
5758     const MCExpr *ImmVal;
5759     SS = getLoc();
5760     if (Parser.parseExpression(ImmVal))
5761       return MatchOperand_ParseFail;
5762 
5763     auto *MCE = dyn_cast<MCConstantExpr>(ImmVal);
5764     if (!MCE)
5765       return MatchOperand_ParseFail;
5766 
5767     Pattern = MCE->getValue();
5768   } else {
5769     // Parse the pattern
5770     auto Pat = AArch64SVEPredPattern::lookupSVEPREDPATByName(TokE.getString());
5771     if (!Pat)
5772       return MatchOperand_NoMatch;
5773 
5774     Parser.Lex();
5775     Pattern = Pat->Encoding;
5776     assert(Pattern >= 0 && Pattern < 32);
5777   }
5778 
5779   Operands.push_back(
5780       AArch64Operand::CreateImm(MCConstantExpr::create(Pattern, getContext()),
5781                                 SS, getLoc(), getContext()));
5782 
5783   return MatchOperand_Success;
5784 }
5785