1 //===-- X86AsmParser.cpp - Parse X86 assembly to MCInst instructions ------===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 #include "MCTargetDesc/X86BaseInfo.h"
11 #include "llvm/ADT/APFloat.h"
12 #include "llvm/ADT/STLExtras.h"
13 #include "llvm/ADT/SmallString.h"
14 #include "llvm/ADT/SmallVector.h"
15 #include "llvm/ADT/StringSwitch.h"
16 #include "llvm/ADT/Twine.h"
17 #include "llvm/MC/MCContext.h"
18 #include "llvm/MC/MCExpr.h"
19 #include "llvm/MC/MCInst.h"
20 #include "llvm/MC/MCParser/MCAsmLexer.h"
21 #include "llvm/MC/MCParser/MCAsmParser.h"
22 #include "llvm/MC/MCParser/MCParsedAsmOperand.h"
23 #include "llvm/MC/MCRegisterInfo.h"
24 #include "llvm/MC/MCStreamer.h"
25 #include "llvm/MC/MCSubtargetInfo.h"
26 #include "llvm/MC/MCSymbol.h"
27 #include "llvm/MC/MCTargetAsmParser.h"
28 #include "llvm/Support/SourceMgr.h"
29 #include "llvm/Support/TargetRegistry.h"
30 #include "llvm/Support/raw_ostream.h"
37 static const char OpPrecedence[] = {
50 class X86AsmParser : public MCTargetAsmParser {
53 ParseInstructionInfo *InstInfo;
55 SMLoc consumeToken() {
56 SMLoc Result = Parser.getTok().getLoc();
61 enum InfixCalculatorTok {
74 class InfixCalculator {
75 typedef std::pair< InfixCalculatorTok, int64_t > ICToken;
76 SmallVector<InfixCalculatorTok, 4> InfixOperatorStack;
77 SmallVector<ICToken, 4> PostfixStack;
80 int64_t popOperand() {
81 assert (!PostfixStack.empty() && "Poped an empty stack!");
82 ICToken Op = PostfixStack.pop_back_val();
83 assert ((Op.first == IC_IMM || Op.first == IC_REGISTER)
84 && "Expected and immediate or register!");
87 void pushOperand(InfixCalculatorTok Op, int64_t Val = 0) {
88 assert ((Op == IC_IMM || Op == IC_REGISTER) &&
89 "Unexpected operand!");
90 PostfixStack.push_back(std::make_pair(Op, Val));
93 void popOperator() { InfixOperatorStack.pop_back(); }
94 void pushOperator(InfixCalculatorTok Op) {
95 // Push the new operator if the stack is empty.
96 if (InfixOperatorStack.empty()) {
97 InfixOperatorStack.push_back(Op);
101 // Push the new operator if it has a higher precedence than the operator
102 // on the top of the stack or the operator on the top of the stack is a
104 unsigned Idx = InfixOperatorStack.size() - 1;
105 InfixCalculatorTok StackOp = InfixOperatorStack[Idx];
106 if (OpPrecedence[Op] > OpPrecedence[StackOp] || StackOp == IC_LPAREN) {
107 InfixOperatorStack.push_back(Op);
111 // The operator on the top of the stack has higher precedence than the
113 unsigned ParenCount = 0;
115 // Nothing to process.
116 if (InfixOperatorStack.empty())
119 Idx = InfixOperatorStack.size() - 1;
120 StackOp = InfixOperatorStack[Idx];
121 if (!(OpPrecedence[StackOp] >= OpPrecedence[Op] || ParenCount))
124 // If we have an even parentheses count and we see a left parentheses,
125 // then stop processing.
126 if (!ParenCount && StackOp == IC_LPAREN)
129 if (StackOp == IC_RPAREN) {
131 InfixOperatorStack.pop_back();
132 } else if (StackOp == IC_LPAREN) {
134 InfixOperatorStack.pop_back();
136 InfixOperatorStack.pop_back();
137 PostfixStack.push_back(std::make_pair(StackOp, 0));
140 // Push the new operator.
141 InfixOperatorStack.push_back(Op);
144 // Push any remaining operators onto the postfix stack.
145 while (!InfixOperatorStack.empty()) {
146 InfixCalculatorTok StackOp = InfixOperatorStack.pop_back_val();
147 if (StackOp != IC_LPAREN && StackOp != IC_RPAREN)
148 PostfixStack.push_back(std::make_pair(StackOp, 0));
151 if (PostfixStack.empty())
154 SmallVector<ICToken, 16> OperandStack;
155 for (unsigned i = 0, e = PostfixStack.size(); i != e; ++i) {
156 ICToken Op = PostfixStack[i];
157 if (Op.first == IC_IMM || Op.first == IC_REGISTER) {
158 OperandStack.push_back(Op);
160 assert (OperandStack.size() > 1 && "Too few operands.");
162 ICToken Op2 = OperandStack.pop_back_val();
163 ICToken Op1 = OperandStack.pop_back_val();
166 report_fatal_error("Unexpected operator!");
169 Val = Op1.second + Op2.second;
170 OperandStack.push_back(std::make_pair(IC_IMM, Val));
173 Val = Op1.second - Op2.second;
174 OperandStack.push_back(std::make_pair(IC_IMM, Val));
177 assert (Op1.first == IC_IMM && Op2.first == IC_IMM &&
178 "Multiply operation with an immediate and a register!");
179 Val = Op1.second * Op2.second;
180 OperandStack.push_back(std::make_pair(IC_IMM, Val));
183 assert (Op1.first == IC_IMM && Op2.first == IC_IMM &&
184 "Divide operation with an immediate and a register!");
185 assert (Op2.second != 0 && "Division by zero!");
186 Val = Op1.second / Op2.second;
187 OperandStack.push_back(std::make_pair(IC_IMM, Val));
190 assert (Op1.first == IC_IMM && Op2.first == IC_IMM &&
191 "Or operation with an immediate and a register!");
192 Val = Op1.second | Op2.second;
193 OperandStack.push_back(std::make_pair(IC_IMM, Val));
196 assert (Op1.first == IC_IMM && Op2.first == IC_IMM &&
197 "And operation with an immediate and a register!");
198 Val = Op1.second & Op2.second;
199 OperandStack.push_back(std::make_pair(IC_IMM, Val));
204 assert (OperandStack.size() == 1 && "Expected a single result.");
205 return OperandStack.pop_back_val().second;
209 enum IntelExprState {
226 class IntelExprStateMachine {
227 IntelExprState State, PrevState;
228 unsigned BaseReg, IndexReg, TmpReg, Scale;
232 bool StopOnLBrac, AddImmPrefix;
234 InlineAsmIdentifierInfo Info;
236 IntelExprStateMachine(int64_t imm, bool stoponlbrac, bool addimmprefix) :
237 State(IES_PLUS), PrevState(IES_ERROR), BaseReg(0), IndexReg(0), TmpReg(0),
238 Scale(1), Imm(imm), Sym(0), StopOnLBrac(stoponlbrac),
239 AddImmPrefix(addimmprefix) { Info.clear(); }
241 unsigned getBaseReg() { return BaseReg; }
242 unsigned getIndexReg() { return IndexReg; }
243 unsigned getScale() { return Scale; }
244 const MCExpr *getSym() { return Sym; }
245 StringRef getSymName() { return SymName; }
246 int64_t getImm() { return Imm + IC.execute(); }
247 bool isValidEndState() {
248 return State == IES_RBRAC || State == IES_INTEGER;
250 bool getStopOnLBrac() { return StopOnLBrac; }
251 bool getAddImmPrefix() { return AddImmPrefix; }
252 bool hadError() { return State == IES_ERROR; }
254 InlineAsmIdentifierInfo &getIdentifierInfo() {
259 IntelExprState CurrState = State;
268 IC.pushOperator(IC_OR);
271 PrevState = CurrState;
274 IntelExprState CurrState = State;
283 IC.pushOperator(IC_AND);
286 PrevState = CurrState;
289 IntelExprState CurrState = State;
298 IC.pushOperator(IC_PLUS);
299 if (CurrState == IES_REGISTER && PrevState != IES_MULTIPLY) {
300 // If we already have a BaseReg, then assume this is the IndexReg with
305 assert (!IndexReg && "BaseReg/IndexReg already set!");
312 PrevState = CurrState;
315 IntelExprState CurrState = State;
330 // Only push the minus operator if it is not a unary operator.
331 if (!(CurrState == IES_PLUS || CurrState == IES_MINUS ||
332 CurrState == IES_MULTIPLY || CurrState == IES_DIVIDE ||
333 CurrState == IES_LPAREN || CurrState == IES_LBRAC))
334 IC.pushOperator(IC_MINUS);
335 if (CurrState == IES_REGISTER && PrevState != IES_MULTIPLY) {
336 // If we already have a BaseReg, then assume this is the IndexReg with
341 assert (!IndexReg && "BaseReg/IndexReg already set!");
348 PrevState = CurrState;
350 void onRegister(unsigned Reg) {
351 IntelExprState CurrState = State;
358 State = IES_REGISTER;
360 IC.pushOperand(IC_REGISTER);
363 // Index Register - Scale * Register
364 if (PrevState == IES_INTEGER) {
365 assert (!IndexReg && "IndexReg already set!");
366 State = IES_REGISTER;
368 // Get the scale and replace the 'Scale * Register' with '0'.
369 Scale = IC.popOperand();
370 IC.pushOperand(IC_IMM);
377 PrevState = CurrState;
379 void onIdentifierExpr(const MCExpr *SymRef, StringRef SymRefName) {
389 SymName = SymRefName;
390 IC.pushOperand(IC_IMM);
394 void onInteger(int64_t TmpInt) {
395 IntelExprState CurrState = State;
408 if (PrevState == IES_REGISTER && CurrState == IES_MULTIPLY) {
409 // Index Register - Register * Scale
410 assert (!IndexReg && "IndexReg already set!");
413 // Get the scale and replace the 'Register * Scale' with '0'.
415 } else if ((PrevState == IES_PLUS || PrevState == IES_MINUS ||
416 PrevState == IES_OR || PrevState == IES_AND ||
417 PrevState == IES_MULTIPLY || PrevState == IES_DIVIDE ||
418 PrevState == IES_LPAREN || PrevState == IES_LBRAC) &&
419 CurrState == IES_MINUS) {
420 // Unary minus. No need to pop the minus operand because it was never
422 IC.pushOperand(IC_IMM, -TmpInt); // Push -Imm.
424 IC.pushOperand(IC_IMM, TmpInt);
428 PrevState = CurrState;
439 State = IES_MULTIPLY;
440 IC.pushOperator(IC_MULTIPLY);
453 IC.pushOperator(IC_DIVIDE);
465 IC.pushOperator(IC_PLUS);
470 IntelExprState CurrState = State;
479 if (CurrState == IES_REGISTER && PrevState != IES_MULTIPLY) {
480 // If we already have a BaseReg, then assume this is the IndexReg with
485 assert (!IndexReg && "BaseReg/IndexReg already set!");
492 PrevState = CurrState;
495 IntelExprState CurrState = State;
507 // FIXME: We don't handle this type of unary minus, yet.
508 if ((PrevState == IES_PLUS || PrevState == IES_MINUS ||
509 PrevState == IES_OR || PrevState == IES_AND ||
510 PrevState == IES_MULTIPLY || PrevState == IES_DIVIDE ||
511 PrevState == IES_LPAREN || PrevState == IES_LBRAC) &&
512 CurrState == IES_MINUS) {
517 IC.pushOperator(IC_LPAREN);
520 PrevState = CurrState;
532 IC.pushOperator(IC_RPAREN);
538 MCAsmParser &getParser() const { return Parser; }
540 MCAsmLexer &getLexer() const { return Parser.getLexer(); }
542 bool Error(SMLoc L, const Twine &Msg,
543 ArrayRef<SMRange> Ranges = None,
544 bool MatchingInlineAsm = false) {
545 if (MatchingInlineAsm) return true;
546 return Parser.Error(L, Msg, Ranges);
549 X86Operand *ErrorOperand(SMLoc Loc, StringRef Msg) {
554 X86Operand *DefaultMemSIOperand(SMLoc Loc);
555 X86Operand *DefaultMemDIOperand(SMLoc Loc);
556 X86Operand *ParseOperand();
557 X86Operand *ParseATTOperand();
558 X86Operand *ParseIntelOperand();
559 X86Operand *ParseIntelOffsetOfOperator();
560 bool ParseIntelDotOperator(const MCExpr *Disp, const MCExpr *&NewDisp);
561 X86Operand *ParseIntelOperator(unsigned OpKind);
562 X86Operand *ParseIntelSegmentOverride(unsigned SegReg, SMLoc Start, unsigned Size);
563 X86Operand *ParseIntelMemOperand(int64_t ImmDisp, SMLoc StartLoc,
565 bool ParseIntelExpression(IntelExprStateMachine &SM, SMLoc &End);
566 X86Operand *ParseIntelBracExpression(unsigned SegReg, SMLoc Start,
567 int64_t ImmDisp, unsigned Size);
568 bool ParseIntelIdentifier(const MCExpr *&Val, StringRef &Identifier,
569 InlineAsmIdentifierInfo &Info,
570 bool IsUnevaluatedOperand, SMLoc &End);
572 X86Operand *ParseMemOperand(unsigned SegReg, SMLoc StartLoc);
574 X86Operand *CreateMemForInlineAsm(unsigned SegReg, const MCExpr *Disp,
575 unsigned BaseReg, unsigned IndexReg,
576 unsigned Scale, SMLoc Start, SMLoc End,
577 unsigned Size, StringRef Identifier,
578 InlineAsmIdentifierInfo &Info);
580 bool ParseDirectiveWord(unsigned Size, SMLoc L);
581 bool ParseDirectiveCode(StringRef IDVal, SMLoc L);
583 bool processInstruction(MCInst &Inst,
584 const SmallVectorImpl<MCParsedAsmOperand*> &Ops);
586 bool MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
587 SmallVectorImpl<MCParsedAsmOperand*> &Operands,
588 MCStreamer &Out, unsigned &ErrorInfo,
589 bool MatchingInlineAsm);
591 /// doSrcDstMatch - Returns true if operands are matching in their
592 /// word size (%si and %di, %esi and %edi, etc.). Order depends on
593 /// the parsing mode (Intel vs. AT&T).
594 bool doSrcDstMatch(X86Operand &Op1, X86Operand &Op2);
596 bool is64BitMode() const {
597 // FIXME: Can tablegen auto-generate this?
598 return (STI.getFeatureBits() & X86::Mode64Bit) != 0;
600 bool is32BitMode() const {
601 // FIXME: Can tablegen auto-generate this?
602 return (STI.getFeatureBits() & X86::Mode32Bit) != 0;
604 bool is16BitMode() const {
605 // FIXME: Can tablegen auto-generate this?
606 return (STI.getFeatureBits() & X86::Mode16Bit) != 0;
608 void SwitchMode(uint64_t mode) {
609 uint64_t oldMode = STI.getFeatureBits() &
610 (X86::Mode64Bit | X86::Mode32Bit | X86::Mode16Bit);
611 unsigned FB = ComputeAvailableFeatures(STI.ToggleFeature(oldMode | mode));
612 setAvailableFeatures(FB);
613 assert(mode == (STI.getFeatureBits() &
614 (X86::Mode64Bit | X86::Mode32Bit | X86::Mode16Bit)));
617 bool isParsingIntelSyntax() {
618 return getParser().getAssemblerDialect();
621 /// @name Auto-generated Matcher Functions
624 #define GET_ASSEMBLER_HEADER
625 #include "X86GenAsmMatcher.inc"
630 X86AsmParser(MCSubtargetInfo &sti, MCAsmParser &parser,
631 const MCInstrInfo &MII)
632 : MCTargetAsmParser(), STI(sti), Parser(parser), InstInfo(0) {
634 // Initialize the set of available features.
635 setAvailableFeatures(ComputeAvailableFeatures(STI.getFeatureBits()));
637 virtual bool ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc);
639 virtual bool ParseInstruction(ParseInstructionInfo &Info, StringRef Name,
641 SmallVectorImpl<MCParsedAsmOperand*> &Operands);
643 virtual bool ParseDirective(AsmToken DirectiveID);
645 } // end anonymous namespace
647 /// @name Auto-generated Match Functions
650 static unsigned MatchRegisterName(StringRef Name);
654 static bool isImmSExti16i8Value(uint64_t Value) {
655 return (( Value <= 0x000000000000007FULL)||
656 (0x000000000000FF80ULL <= Value && Value <= 0x000000000000FFFFULL)||
657 (0xFFFFFFFFFFFFFF80ULL <= Value && Value <= 0xFFFFFFFFFFFFFFFFULL));
660 static bool isImmSExti32i8Value(uint64_t Value) {
661 return (( Value <= 0x000000000000007FULL)||
662 (0x00000000FFFFFF80ULL <= Value && Value <= 0x00000000FFFFFFFFULL)||
663 (0xFFFFFFFFFFFFFF80ULL <= Value && Value <= 0xFFFFFFFFFFFFFFFFULL));
666 static bool isImmZExtu32u8Value(uint64_t Value) {
667 return (Value <= 0x00000000000000FFULL);
670 static bool isImmSExti64i8Value(uint64_t Value) {
671 return (( Value <= 0x000000000000007FULL)||
672 (0xFFFFFFFFFFFFFF80ULL <= Value && Value <= 0xFFFFFFFFFFFFFFFFULL));
675 static bool isImmSExti64i32Value(uint64_t Value) {
676 return (( Value <= 0x000000007FFFFFFFULL)||
677 (0xFFFFFFFF80000000ULL <= Value && Value <= 0xFFFFFFFFFFFFFFFFULL));
681 /// X86Operand - Instances of this class represent a parsed X86 machine
683 struct X86Operand : public MCParsedAsmOperand {
691 SMLoc StartLoc, EndLoc;
726 X86Operand(KindTy K, SMLoc Start, SMLoc End)
727 : Kind(K), StartLoc(Start), EndLoc(End) {}
729 StringRef getSymName() { return SymName; }
730 void *getOpDecl() { return OpDecl; }
732 /// getStartLoc - Get the location of the first token of this operand.
733 SMLoc getStartLoc() const { return StartLoc; }
734 /// getEndLoc - Get the location of the last token of this operand.
735 SMLoc getEndLoc() const { return EndLoc; }
736 /// getLocRange - Get the range between the first and last token of this
738 SMRange getLocRange() const { return SMRange(StartLoc, EndLoc); }
739 /// getOffsetOfLoc - Get the location of the offset operator.
740 SMLoc getOffsetOfLoc() const { return OffsetOfLoc; }
742 virtual void print(raw_ostream &OS) const {}
744 StringRef getToken() const {
745 assert(Kind == Token && "Invalid access!");
746 return StringRef(Tok.Data, Tok.Length);
748 void setTokenValue(StringRef Value) {
749 assert(Kind == Token && "Invalid access!");
750 Tok.Data = Value.data();
751 Tok.Length = Value.size();
754 unsigned getReg() const {
755 assert(Kind == Register && "Invalid access!");
759 const MCExpr *getImm() const {
760 assert(Kind == Immediate && "Invalid access!");
764 const MCExpr *getMemDisp() const {
765 assert(Kind == Memory && "Invalid access!");
768 unsigned getMemSegReg() const {
769 assert(Kind == Memory && "Invalid access!");
772 unsigned getMemBaseReg() const {
773 assert(Kind == Memory && "Invalid access!");
776 unsigned getMemIndexReg() const {
777 assert(Kind == Memory && "Invalid access!");
780 unsigned getMemScale() const {
781 assert(Kind == Memory && "Invalid access!");
785 bool isToken() const {return Kind == Token; }
787 bool isImm() const { return Kind == Immediate; }
789 bool isImmSExti16i8() const {
793 // If this isn't a constant expr, just assume it fits and let relaxation
795 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
799 // Otherwise, check the value is in a range that makes sense for this
801 return isImmSExti16i8Value(CE->getValue());
803 bool isImmSExti32i8() const {
807 // If this isn't a constant expr, just assume it fits and let relaxation
809 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
813 // Otherwise, check the value is in a range that makes sense for this
815 return isImmSExti32i8Value(CE->getValue());
817 bool isImmZExtu32u8() const {
821 // If this isn't a constant expr, just assume it fits and let relaxation
823 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
827 // Otherwise, check the value is in a range that makes sense for this
829 return isImmZExtu32u8Value(CE->getValue());
831 bool isImmSExti64i8() const {
835 // If this isn't a constant expr, just assume it fits and let relaxation
837 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
841 // Otherwise, check the value is in a range that makes sense for this
843 return isImmSExti64i8Value(CE->getValue());
845 bool isImmSExti64i32() const {
849 // If this isn't a constant expr, just assume it fits and let relaxation
851 const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getImm());
855 // Otherwise, check the value is in a range that makes sense for this
857 return isImmSExti64i32Value(CE->getValue());
860 bool isOffsetOf() const {
861 return OffsetOfLoc.getPointer();
864 bool needAddressOf() const {
868 bool isMem() const { return Kind == Memory; }
869 bool isMem8() const {
870 return Kind == Memory && (!Mem.Size || Mem.Size == 8);
872 bool isMem16() const {
873 return Kind == Memory && (!Mem.Size || Mem.Size == 16);
875 bool isMem32() const {
876 return Kind == Memory && (!Mem.Size || Mem.Size == 32);
878 bool isMem64() const {
879 return Kind == Memory && (!Mem.Size || Mem.Size == 64);
881 bool isMem80() const {
882 return Kind == Memory && (!Mem.Size || Mem.Size == 80);
884 bool isMem128() const {
885 return Kind == Memory && (!Mem.Size || Mem.Size == 128);
887 bool isMem256() const {
888 return Kind == Memory && (!Mem.Size || Mem.Size == 256);
890 bool isMem512() const {
891 return Kind == Memory && (!Mem.Size || Mem.Size == 512);
894 bool isMemVX32() const {
895 return Kind == Memory && (!Mem.Size || Mem.Size == 32) &&
896 getMemIndexReg() >= X86::XMM0 && getMemIndexReg() <= X86::XMM15;
898 bool isMemVY32() const {
899 return Kind == Memory && (!Mem.Size || Mem.Size == 32) &&
900 getMemIndexReg() >= X86::YMM0 && getMemIndexReg() <= X86::YMM15;
902 bool isMemVX64() const {
903 return Kind == Memory && (!Mem.Size || Mem.Size == 64) &&
904 getMemIndexReg() >= X86::XMM0 && getMemIndexReg() <= X86::XMM15;
906 bool isMemVY64() const {
907 return Kind == Memory && (!Mem.Size || Mem.Size == 64) &&
908 getMemIndexReg() >= X86::YMM0 && getMemIndexReg() <= X86::YMM15;
910 bool isMemVZ32() const {
911 return Kind == Memory && (!Mem.Size || Mem.Size == 32) &&
912 getMemIndexReg() >= X86::ZMM0 && getMemIndexReg() <= X86::ZMM31;
914 bool isMemVZ64() const {
915 return Kind == Memory && (!Mem.Size || Mem.Size == 64) &&
916 getMemIndexReg() >= X86::ZMM0 && getMemIndexReg() <= X86::ZMM31;
919 bool isAbsMem() const {
920 return Kind == Memory && !getMemSegReg() && !getMemBaseReg() &&
921 !getMemIndexReg() && getMemScale() == 1;
924 bool isSrcIdx() const {
925 return !getMemIndexReg() && getMemScale() == 1 &&
926 (getMemBaseReg() == X86::RSI || getMemBaseReg() == X86::ESI ||
927 getMemBaseReg() == X86::SI) && isa<MCConstantExpr>(getMemDisp()) &&
928 cast<MCConstantExpr>(getMemDisp())->getValue() == 0;
930 bool isSrcIdx8() const {
931 return isMem8() && isSrcIdx();
933 bool isSrcIdx16() const {
934 return isMem16() && isSrcIdx();
936 bool isSrcIdx32() const {
937 return isMem32() && isSrcIdx();
939 bool isSrcIdx64() const {
940 return isMem64() && isSrcIdx();
943 bool isDstIdx() const {
944 return !getMemIndexReg() && getMemScale() == 1 &&
945 (getMemSegReg() == 0 || getMemSegReg() == X86::ES) &&
946 (getMemBaseReg() == X86::RDI || getMemBaseReg() == X86::EDI ||
947 getMemBaseReg() == X86::DI) && isa<MCConstantExpr>(getMemDisp()) &&
948 cast<MCConstantExpr>(getMemDisp())->getValue() == 0;
950 bool isDstIdx8() const {
951 return isMem8() && isDstIdx();
953 bool isDstIdx16() const {
954 return isMem16() && isDstIdx();
956 bool isDstIdx32() const {
957 return isMem32() && isDstIdx();
959 bool isDstIdx64() const {
960 return isMem64() && isDstIdx();
963 bool isMemOffs8() const {
964 return Kind == Memory && !getMemBaseReg() &&
965 !getMemIndexReg() && getMemScale() == 1 && (!Mem.Size || Mem.Size == 8);
967 bool isMemOffs16() const {
968 return Kind == Memory && !getMemBaseReg() &&
969 !getMemIndexReg() && getMemScale() == 1 && (!Mem.Size || Mem.Size == 16);
971 bool isMemOffs32() const {
972 return Kind == Memory && !getMemBaseReg() &&
973 !getMemIndexReg() && getMemScale() == 1 && (!Mem.Size || Mem.Size == 32);
975 bool isMemOffs64() const {
976 return Kind == Memory && !getMemBaseReg() &&
977 !getMemIndexReg() && getMemScale() == 1 && (!Mem.Size || Mem.Size == 64);
980 bool isReg() const { return Kind == Register; }
982 bool isGR32orGR64() const {
983 return Kind == Register &&
984 (X86MCRegisterClasses[X86::GR32RegClassID].contains(getReg()) ||
985 X86MCRegisterClasses[X86::GR64RegClassID].contains(getReg()));
988 void addExpr(MCInst &Inst, const MCExpr *Expr) const {
989 // Add as immediates when possible.
990 if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(Expr))
991 Inst.addOperand(MCOperand::CreateImm(CE->getValue()));
993 Inst.addOperand(MCOperand::CreateExpr(Expr));
996 void addRegOperands(MCInst &Inst, unsigned N) const {
997 assert(N == 1 && "Invalid number of operands!");
998 Inst.addOperand(MCOperand::CreateReg(getReg()));
1001 static unsigned getGR32FromGR64(unsigned RegNo) {
1003 default: llvm_unreachable("Unexpected register");
1004 case X86::RAX: return X86::EAX;
1005 case X86::RCX: return X86::ECX;
1006 case X86::RDX: return X86::EDX;
1007 case X86::RBX: return X86::EBX;
1008 case X86::RBP: return X86::EBP;
1009 case X86::RSP: return X86::ESP;
1010 case X86::RSI: return X86::ESI;
1011 case X86::RDI: return X86::EDI;
1012 case X86::R8: return X86::R8D;
1013 case X86::R9: return X86::R9D;
1014 case X86::R10: return X86::R10D;
1015 case X86::R11: return X86::R11D;
1016 case X86::R12: return X86::R12D;
1017 case X86::R13: return X86::R13D;
1018 case X86::R14: return X86::R14D;
1019 case X86::R15: return X86::R15D;
1020 case X86::RIP: return X86::EIP;
1024 void addGR32orGR64Operands(MCInst &Inst, unsigned N) const {
1025 assert(N == 1 && "Invalid number of operands!");
1026 unsigned RegNo = getReg();
1027 if (X86MCRegisterClasses[X86::GR64RegClassID].contains(RegNo))
1028 RegNo = getGR32FromGR64(RegNo);
1029 Inst.addOperand(MCOperand::CreateReg(RegNo));
1032 void addImmOperands(MCInst &Inst, unsigned N) const {
1033 assert(N == 1 && "Invalid number of operands!");
1034 addExpr(Inst, getImm());
1037 void addMemOperands(MCInst &Inst, unsigned N) const {
1038 assert((N == 5) && "Invalid number of operands!");
1039 Inst.addOperand(MCOperand::CreateReg(getMemBaseReg()));
1040 Inst.addOperand(MCOperand::CreateImm(getMemScale()));
1041 Inst.addOperand(MCOperand::CreateReg(getMemIndexReg()));
1042 addExpr(Inst, getMemDisp());
1043 Inst.addOperand(MCOperand::CreateReg(getMemSegReg()));
1046 void addAbsMemOperands(MCInst &Inst, unsigned N) const {
1047 assert((N == 1) && "Invalid number of operands!");
1048 // Add as immediates when possible.
1049 if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemDisp()))
1050 Inst.addOperand(MCOperand::CreateImm(CE->getValue()));
1052 Inst.addOperand(MCOperand::CreateExpr(getMemDisp()));
1055 void addSrcIdxOperands(MCInst &Inst, unsigned N) const {
1056 assert((N == 2) && "Invalid number of operands!");
1057 Inst.addOperand(MCOperand::CreateReg(getMemBaseReg()));
1058 Inst.addOperand(MCOperand::CreateReg(getMemSegReg()));
1060 void addDstIdxOperands(MCInst &Inst, unsigned N) const {
1061 assert((N == 1) && "Invalid number of operands!");
1062 Inst.addOperand(MCOperand::CreateReg(getMemBaseReg()));
1065 void addMemOffsOperands(MCInst &Inst, unsigned N) const {
1066 assert((N == 2) && "Invalid number of operands!");
1067 // Add as immediates when possible.
1068 if (const MCConstantExpr *CE = dyn_cast<MCConstantExpr>(getMemDisp()))
1069 Inst.addOperand(MCOperand::CreateImm(CE->getValue()));
1071 Inst.addOperand(MCOperand::CreateExpr(getMemDisp()));
1072 Inst.addOperand(MCOperand::CreateReg(getMemSegReg()));
1075 static X86Operand *CreateToken(StringRef Str, SMLoc Loc) {
1076 SMLoc EndLoc = SMLoc::getFromPointer(Loc.getPointer() + Str.size());
1077 X86Operand *Res = new X86Operand(Token, Loc, EndLoc);
1078 Res->Tok.Data = Str.data();
1079 Res->Tok.Length = Str.size();
1083 static X86Operand *CreateReg(unsigned RegNo, SMLoc StartLoc, SMLoc EndLoc,
1084 bool AddressOf = false,
1085 SMLoc OffsetOfLoc = SMLoc(),
1086 StringRef SymName = StringRef(),
1088 X86Operand *Res = new X86Operand(Register, StartLoc, EndLoc);
1089 Res->Reg.RegNo = RegNo;
1090 Res->AddressOf = AddressOf;
1091 Res->OffsetOfLoc = OffsetOfLoc;
1092 Res->SymName = SymName;
1093 Res->OpDecl = OpDecl;
1097 static X86Operand *CreateImm(const MCExpr *Val, SMLoc StartLoc, SMLoc EndLoc){
1098 X86Operand *Res = new X86Operand(Immediate, StartLoc, EndLoc);
1103 /// Create an absolute memory operand.
1104 static X86Operand *CreateMem(const MCExpr *Disp, SMLoc StartLoc, SMLoc EndLoc,
1105 unsigned Size = 0, StringRef SymName = StringRef(),
1107 X86Operand *Res = new X86Operand(Memory, StartLoc, EndLoc);
1108 Res->Mem.SegReg = 0;
1109 Res->Mem.Disp = Disp;
1110 Res->Mem.BaseReg = 0;
1111 Res->Mem.IndexReg = 0;
1113 Res->Mem.Size = Size;
1114 Res->SymName = SymName;
1115 Res->OpDecl = OpDecl;
1116 Res->AddressOf = false;
1120 /// Create a generalized memory operand.
1121 static X86Operand *CreateMem(unsigned SegReg, const MCExpr *Disp,
1122 unsigned BaseReg, unsigned IndexReg,
1123 unsigned Scale, SMLoc StartLoc, SMLoc EndLoc,
1125 StringRef SymName = StringRef(),
1127 // We should never just have a displacement, that should be parsed as an
1128 // absolute memory operand.
1129 assert((SegReg || BaseReg || IndexReg) && "Invalid memory operand!");
1131 // The scale should always be one of {1,2,4,8}.
1132 assert(((Scale == 1 || Scale == 2 || Scale == 4 || Scale == 8)) &&
1134 X86Operand *Res = new X86Operand(Memory, StartLoc, EndLoc);
1135 Res->Mem.SegReg = SegReg;
1136 Res->Mem.Disp = Disp;
1137 Res->Mem.BaseReg = BaseReg;
1138 Res->Mem.IndexReg = IndexReg;
1139 Res->Mem.Scale = Scale;
1140 Res->Mem.Size = Size;
1141 Res->SymName = SymName;
1142 Res->OpDecl = OpDecl;
1143 Res->AddressOf = false;
1148 } // end anonymous namespace.
1150 bool X86AsmParser::doSrcDstMatch(X86Operand &Op1, X86Operand &Op2)
1152 // Return true and let a normal complaint about bogus operands happen.
1153 if (!Op1.isMem() || !Op2.isMem())
1156 // Actually these might be the other way round if Intel syntax is
1157 // being used. It doesn't matter.
1158 unsigned diReg = Op1.Mem.BaseReg;
1159 unsigned siReg = Op2.Mem.BaseReg;
1161 if (X86MCRegisterClasses[X86::GR16RegClassID].contains(siReg))
1162 return X86MCRegisterClasses[X86::GR16RegClassID].contains(diReg);
1163 if (X86MCRegisterClasses[X86::GR32RegClassID].contains(siReg))
1164 return X86MCRegisterClasses[X86::GR32RegClassID].contains(diReg);
1165 if (X86MCRegisterClasses[X86::GR64RegClassID].contains(siReg))
1166 return X86MCRegisterClasses[X86::GR64RegClassID].contains(diReg);
1167 // Again, return true and let another error happen.
1171 bool X86AsmParser::ParseRegister(unsigned &RegNo,
1172 SMLoc &StartLoc, SMLoc &EndLoc) {
1174 const AsmToken &PercentTok = Parser.getTok();
1175 StartLoc = PercentTok.getLoc();
1177 // If we encounter a %, ignore it. This code handles registers with and
1178 // without the prefix, unprefixed registers can occur in cfi directives.
1179 if (!isParsingIntelSyntax() && PercentTok.is(AsmToken::Percent))
1180 Parser.Lex(); // Eat percent token.
1182 const AsmToken &Tok = Parser.getTok();
1183 EndLoc = Tok.getEndLoc();
1185 if (Tok.isNot(AsmToken::Identifier)) {
1186 if (isParsingIntelSyntax()) return true;
1187 return Error(StartLoc, "invalid register name",
1188 SMRange(StartLoc, EndLoc));
1191 RegNo = MatchRegisterName(Tok.getString());
1193 // If the match failed, try the register name as lowercase.
1195 RegNo = MatchRegisterName(Tok.getString().lower());
1197 if (!is64BitMode()) {
1198 // FIXME: This should be done using Requires<Not64BitMode> and
1199 // Requires<In64BitMode> so "eiz" usage in 64-bit instructions can be also
1201 // FIXME: Check AH, CH, DH, BH cannot be used in an instruction requiring a
1203 if (RegNo == X86::RIZ ||
1204 X86MCRegisterClasses[X86::GR64RegClassID].contains(RegNo) ||
1205 X86II::isX86_64NonExtLowByteReg(RegNo) ||
1206 X86II::isX86_64ExtendedReg(RegNo))
1207 return Error(StartLoc, "register %"
1208 + Tok.getString() + " is only available in 64-bit mode",
1209 SMRange(StartLoc, EndLoc));
1212 // Parse "%st" as "%st(0)" and "%st(1)", which is multiple tokens.
1213 if (RegNo == 0 && (Tok.getString() == "st" || Tok.getString() == "ST")) {
1215 Parser.Lex(); // Eat 'st'
1217 // Check to see if we have '(4)' after %st.
1218 if (getLexer().isNot(AsmToken::LParen))
1223 const AsmToken &IntTok = Parser.getTok();
1224 if (IntTok.isNot(AsmToken::Integer))
1225 return Error(IntTok.getLoc(), "expected stack index");
1226 switch (IntTok.getIntVal()) {
1227 case 0: RegNo = X86::ST0; break;
1228 case 1: RegNo = X86::ST1; break;
1229 case 2: RegNo = X86::ST2; break;
1230 case 3: RegNo = X86::ST3; break;
1231 case 4: RegNo = X86::ST4; break;
1232 case 5: RegNo = X86::ST5; break;
1233 case 6: RegNo = X86::ST6; break;
1234 case 7: RegNo = X86::ST7; break;
1235 default: return Error(IntTok.getLoc(), "invalid stack index");
1238 if (getParser().Lex().isNot(AsmToken::RParen))
1239 return Error(Parser.getTok().getLoc(), "expected ')'");
1241 EndLoc = Parser.getTok().getEndLoc();
1242 Parser.Lex(); // Eat ')'
1246 EndLoc = Parser.getTok().getEndLoc();
1248 // If this is "db[0-7]", match it as an alias
1250 if (RegNo == 0 && Tok.getString().size() == 3 &&
1251 Tok.getString().startswith("db")) {
1252 switch (Tok.getString()[2]) {
1253 case '0': RegNo = X86::DR0; break;
1254 case '1': RegNo = X86::DR1; break;
1255 case '2': RegNo = X86::DR2; break;
1256 case '3': RegNo = X86::DR3; break;
1257 case '4': RegNo = X86::DR4; break;
1258 case '5': RegNo = X86::DR5; break;
1259 case '6': RegNo = X86::DR6; break;
1260 case '7': RegNo = X86::DR7; break;
1264 EndLoc = Parser.getTok().getEndLoc();
1265 Parser.Lex(); // Eat it.
1271 if (isParsingIntelSyntax()) return true;
1272 return Error(StartLoc, "invalid register name",
1273 SMRange(StartLoc, EndLoc));
1276 Parser.Lex(); // Eat identifier token.
1280 X86Operand *X86AsmParser::DefaultMemSIOperand(SMLoc Loc) {
1282 is64BitMode() ? X86::RSI : (is32BitMode() ? X86::ESI : X86::SI);
1283 const MCExpr *Disp = MCConstantExpr::Create(0, getContext());
1284 return X86Operand::CreateMem(/*SegReg=*/0, Disp, /*BaseReg=*/basereg,
1285 /*IndexReg=*/0, /*Scale=*/1, Loc, Loc, 0);
1288 X86Operand *X86AsmParser::DefaultMemDIOperand(SMLoc Loc) {
1290 is64BitMode() ? X86::RDI : (is32BitMode() ? X86::EDI : X86::DI);
1291 const MCExpr *Disp = MCConstantExpr::Create(0, getContext());
1292 return X86Operand::CreateMem(/*SegReg=*/0, Disp, /*BaseReg=*/basereg,
1293 /*IndexReg=*/0, /*Scale=*/1, Loc, Loc, 0);
1296 X86Operand *X86AsmParser::ParseOperand() {
1297 if (isParsingIntelSyntax())
1298 return ParseIntelOperand();
1299 return ParseATTOperand();
1302 /// getIntelMemOperandSize - Return intel memory operand size.
1303 static unsigned getIntelMemOperandSize(StringRef OpStr) {
1304 unsigned Size = StringSwitch<unsigned>(OpStr)
1305 .Cases("BYTE", "byte", 8)
1306 .Cases("WORD", "word", 16)
1307 .Cases("DWORD", "dword", 32)
1308 .Cases("QWORD", "qword", 64)
1309 .Cases("XWORD", "xword", 80)
1310 .Cases("XMMWORD", "xmmword", 128)
1311 .Cases("YMMWORD", "ymmword", 256)
1312 .Cases("ZMMWORD", "zmmword", 512)
1313 .Cases("OPAQUE", "opaque", -1U) // needs to be non-zero, but doesn't matter
1319 X86AsmParser::CreateMemForInlineAsm(unsigned SegReg, const MCExpr *Disp,
1320 unsigned BaseReg, unsigned IndexReg,
1321 unsigned Scale, SMLoc Start, SMLoc End,
1322 unsigned Size, StringRef Identifier,
1323 InlineAsmIdentifierInfo &Info){
1324 if (isa<MCSymbolRefExpr>(Disp)) {
1325 // If this is not a VarDecl then assume it is a FuncDecl or some other label
1326 // reference. We need an 'r' constraint here, so we need to create register
1327 // operand to ensure proper matching. Just pick a GPR based on the size of
1329 if (!Info.IsVarDecl) {
1331 is64BitMode() ? X86::RBX : (is32BitMode() ? X86::EBX : X86::BX);
1332 return X86Operand::CreateReg(RegNo, Start, End, /*AddressOf=*/true,
1333 SMLoc(), Identifier, Info.OpDecl);
1336 Size = Info.Type * 8; // Size is in terms of bits in this context.
1338 InstInfo->AsmRewrites->push_back(AsmRewrite(AOK_SizeDirective, Start,
1343 // When parsing inline assembly we set the base register to a non-zero value
1344 // if we don't know the actual value at this time. This is necessary to
1345 // get the matching correct in some cases.
1346 BaseReg = BaseReg ? BaseReg : 1;
1347 return X86Operand::CreateMem(SegReg, Disp, BaseReg, IndexReg, Scale, Start,
1348 End, Size, Identifier, Info.OpDecl);
1352 RewriteIntelBracExpression(SmallVectorImpl<AsmRewrite> *AsmRewrites,
1353 StringRef SymName, int64_t ImmDisp,
1354 int64_t FinalImmDisp, SMLoc &BracLoc,
1355 SMLoc &StartInBrac, SMLoc &End) {
1356 // Remove the '[' and ']' from the IR string.
1357 AsmRewrites->push_back(AsmRewrite(AOK_Skip, BracLoc, 1));
1358 AsmRewrites->push_back(AsmRewrite(AOK_Skip, End, 1));
1360 // If ImmDisp is non-zero, then we parsed a displacement before the
1361 // bracketed expression (i.e., ImmDisp [ BaseReg + Scale*IndexReg + Disp])
1362 // If ImmDisp doesn't match the displacement computed by the state machine
1363 // then we have an additional displacement in the bracketed expression.
1364 if (ImmDisp != FinalImmDisp) {
1366 // We have an immediate displacement before the bracketed expression.
1367 // Adjust this to match the final immediate displacement.
1369 for (SmallVectorImpl<AsmRewrite>::iterator I = AsmRewrites->begin(),
1370 E = AsmRewrites->end(); I != E; ++I) {
1371 if ((*I).Loc.getPointer() > BracLoc.getPointer())
1373 if ((*I).Kind == AOK_ImmPrefix || (*I).Kind == AOK_Imm) {
1374 assert (!Found && "ImmDisp already rewritten.");
1375 (*I).Kind = AOK_Imm;
1376 (*I).Len = BracLoc.getPointer() - (*I).Loc.getPointer();
1377 (*I).Val = FinalImmDisp;
1382 assert (Found && "Unable to rewrite ImmDisp.");
1385 // We have a symbolic and an immediate displacement, but no displacement
1386 // before the bracketed expression. Put the immediate displacement
1387 // before the bracketed expression.
1388 AsmRewrites->push_back(AsmRewrite(AOK_Imm, BracLoc, 0, FinalImmDisp));
1391 // Remove all the ImmPrefix rewrites within the brackets.
1392 for (SmallVectorImpl<AsmRewrite>::iterator I = AsmRewrites->begin(),
1393 E = AsmRewrites->end(); I != E; ++I) {
1394 if ((*I).Loc.getPointer() < StartInBrac.getPointer())
1396 if ((*I).Kind == AOK_ImmPrefix)
1397 (*I).Kind = AOK_Delete;
1399 const char *SymLocPtr = SymName.data();
1400 // Skip everything before the symbol.
1401 if (unsigned Len = SymLocPtr - StartInBrac.getPointer()) {
1402 assert(Len > 0 && "Expected a non-negative length.");
1403 AsmRewrites->push_back(AsmRewrite(AOK_Skip, StartInBrac, Len));
1405 // Skip everything after the symbol.
1406 if (unsigned Len = End.getPointer() - (SymLocPtr + SymName.size())) {
1407 SMLoc Loc = SMLoc::getFromPointer(SymLocPtr + SymName.size());
1408 assert(Len > 0 && "Expected a non-negative length.");
1409 AsmRewrites->push_back(AsmRewrite(AOK_Skip, Loc, Len));
1413 bool X86AsmParser::ParseIntelExpression(IntelExprStateMachine &SM, SMLoc &End) {
1414 const AsmToken &Tok = Parser.getTok();
1418 bool UpdateLocLex = true;
1420 // The period in the dot operator (e.g., [ebx].foo.bar) is parsed as an
1421 // identifier. Don't try an parse it as a register.
1422 if (Tok.getString().startswith("."))
1425 // If we're parsing an immediate expression, we don't expect a '['.
1426 if (SM.getStopOnLBrac() && getLexer().getKind() == AsmToken::LBrac)
1429 switch (getLexer().getKind()) {
1431 if (SM.isValidEndState()) {
1435 return Error(Tok.getLoc(), "unknown token in expression");
1437 case AsmToken::EndOfStatement: {
1441 case AsmToken::Identifier: {
1442 // This could be a register or a symbolic displacement.
1445 SMLoc IdentLoc = Tok.getLoc();
1446 StringRef Identifier = Tok.getString();
1447 if(!ParseRegister(TmpReg, IdentLoc, End)) {
1448 SM.onRegister(TmpReg);
1449 UpdateLocLex = false;
1452 if (!isParsingInlineAsm()) {
1453 if (getParser().parsePrimaryExpr(Val, End))
1454 return Error(Tok.getLoc(), "Unexpected identifier!");
1456 InlineAsmIdentifierInfo &Info = SM.getIdentifierInfo();
1457 if (ParseIntelIdentifier(Val, Identifier, Info,
1458 /*Unevaluated=*/false, End))
1461 SM.onIdentifierExpr(Val, Identifier);
1462 UpdateLocLex = false;
1465 return Error(Tok.getLoc(), "Unexpected identifier!");
1467 case AsmToken::Integer: {
1468 if (isParsingInlineAsm() && SM.getAddImmPrefix())
1469 InstInfo->AsmRewrites->push_back(AsmRewrite(AOK_ImmPrefix,
1471 // Look for 'b' or 'f' following an Integer as a directional label
1472 SMLoc Loc = getTok().getLoc();
1473 int64_t IntVal = getTok().getIntVal();
1474 End = consumeToken();
1475 UpdateLocLex = false;
1476 if (getLexer().getKind() == AsmToken::Identifier) {
1477 StringRef IDVal = getTok().getString();
1478 if (IDVal == "f" || IDVal == "b") {
1480 getContext().GetDirectionalLocalSymbol(IntVal,
1481 IDVal == "f" ? 1 : 0);
1482 MCSymbolRefExpr::VariantKind Variant = MCSymbolRefExpr::VK_None;
1484 MCSymbolRefExpr::Create(Sym, Variant, getContext());
1485 if (IDVal == "b" && Sym->isUndefined())
1486 return Error(Loc, "invalid reference to undefined symbol");
1487 StringRef Identifier = Sym->getName();
1488 SM.onIdentifierExpr(Val, Identifier);
1489 End = consumeToken();
1491 SM.onInteger(IntVal);
1494 SM.onInteger(IntVal);
1498 case AsmToken::Plus: SM.onPlus(); break;
1499 case AsmToken::Minus: SM.onMinus(); break;
1500 case AsmToken::Star: SM.onStar(); break;
1501 case AsmToken::Slash: SM.onDivide(); break;
1502 case AsmToken::Pipe: SM.onOr(); break;
1503 case AsmToken::Amp: SM.onAnd(); break;
1504 case AsmToken::LBrac: SM.onLBrac(); break;
1505 case AsmToken::RBrac: SM.onRBrac(); break;
1506 case AsmToken::LParen: SM.onLParen(); break;
1507 case AsmToken::RParen: SM.onRParen(); break;
1510 return Error(Tok.getLoc(), "unknown token in expression");
1512 if (!Done && UpdateLocLex)
1513 End = consumeToken();
1518 X86Operand *X86AsmParser::ParseIntelBracExpression(unsigned SegReg, SMLoc Start,
1521 const AsmToken &Tok = Parser.getTok();
1522 SMLoc BracLoc = Tok.getLoc(), End = Tok.getEndLoc();
1523 if (getLexer().isNot(AsmToken::LBrac))
1524 return ErrorOperand(BracLoc, "Expected '[' token!");
1525 Parser.Lex(); // Eat '['
1527 SMLoc StartInBrac = Tok.getLoc();
1528 // Parse [ Symbol + ImmDisp ] and [ BaseReg + Scale*IndexReg + ImmDisp ]. We
1529 // may have already parsed an immediate displacement before the bracketed
1531 IntelExprStateMachine SM(ImmDisp, /*StopOnLBrac=*/false, /*AddImmPrefix=*/true);
1532 if (ParseIntelExpression(SM, End))
1536 if (const MCExpr *Sym = SM.getSym()) {
1537 // A symbolic displacement.
1539 if (isParsingInlineAsm())
1540 RewriteIntelBracExpression(InstInfo->AsmRewrites, SM.getSymName(),
1541 ImmDisp, SM.getImm(), BracLoc, StartInBrac,
1544 // An immediate displacement only.
1545 Disp = MCConstantExpr::Create(SM.getImm(), getContext());
1548 // Parse the dot operator (e.g., [ebx].foo.bar).
1549 if (Tok.getString().startswith(".")) {
1550 const MCExpr *NewDisp;
1551 if (ParseIntelDotOperator(Disp, NewDisp))
1554 End = Tok.getEndLoc();
1555 Parser.Lex(); // Eat the field.
1559 int BaseReg = SM.getBaseReg();
1560 int IndexReg = SM.getIndexReg();
1561 int Scale = SM.getScale();
1562 if (!isParsingInlineAsm()) {
1564 if (!BaseReg && !IndexReg) {
1566 return X86Operand::CreateMem(Disp, Start, End, Size);
1568 return X86Operand::CreateMem(SegReg, Disp, 0, 0, 1, Start, End, Size);
1570 return X86Operand::CreateMem(SegReg, Disp, BaseReg, IndexReg, Scale, Start,
1574 InlineAsmIdentifierInfo &Info = SM.getIdentifierInfo();
1575 return CreateMemForInlineAsm(SegReg, Disp, BaseReg, IndexReg, Scale, Start,
1576 End, Size, SM.getSymName(), Info);
1579 // Inline assembly may use variable names with namespace alias qualifiers.
1580 bool X86AsmParser::ParseIntelIdentifier(const MCExpr *&Val,
1581 StringRef &Identifier,
1582 InlineAsmIdentifierInfo &Info,
1583 bool IsUnevaluatedOperand, SMLoc &End) {
1584 assert (isParsingInlineAsm() && "Expected to be parsing inline assembly.");
1587 StringRef LineBuf(Identifier.data());
1588 SemaCallback->LookupInlineAsmIdentifier(LineBuf, Info, IsUnevaluatedOperand);
1590 const AsmToken &Tok = Parser.getTok();
1592 // Advance the token stream until the end of the current token is
1593 // after the end of what the frontend claimed.
1594 const char *EndPtr = Tok.getLoc().getPointer() + LineBuf.size();
1596 End = Tok.getEndLoc();
1599 assert(End.getPointer() <= EndPtr && "frontend claimed part of a token?");
1600 if (End.getPointer() == EndPtr) break;
1603 // Create the symbol reference.
1604 Identifier = LineBuf;
1605 MCSymbol *Sym = getContext().GetOrCreateSymbol(Identifier);
1606 MCSymbolRefExpr::VariantKind Variant = MCSymbolRefExpr::VK_None;
1607 Val = MCSymbolRefExpr::Create(Sym, Variant, getParser().getContext());
1611 /// \brief Parse intel style segment override.
1612 X86Operand *X86AsmParser::ParseIntelSegmentOverride(unsigned SegReg,
1615 assert(SegReg != 0 && "Tried to parse a segment override without a segment!");
1616 const AsmToken &Tok = Parser.getTok(); // Eat colon.
1617 if (Tok.isNot(AsmToken::Colon))
1618 return ErrorOperand(Tok.getLoc(), "Expected ':' token!");
1619 Parser.Lex(); // Eat ':'
1621 int64_t ImmDisp = 0;
1622 if (getLexer().is(AsmToken::Integer)) {
1623 ImmDisp = Tok.getIntVal();
1624 AsmToken ImmDispToken = Parser.Lex(); // Eat the integer.
1626 if (isParsingInlineAsm())
1627 InstInfo->AsmRewrites->push_back(
1628 AsmRewrite(AOK_ImmPrefix, ImmDispToken.getLoc()));
1630 if (getLexer().isNot(AsmToken::LBrac)) {
1631 // An immediate following a 'segment register', 'colon' token sequence can
1632 // be followed by a bracketed expression. If it isn't we know we have our
1633 // final segment override.
1634 const MCExpr *Disp = MCConstantExpr::Create(ImmDisp, getContext());
1635 return X86Operand::CreateMem(SegReg, Disp, /*BaseReg=*/0, /*IndexReg=*/0,
1636 /*Scale=*/1, Start, ImmDispToken.getEndLoc(),
1641 if (getLexer().is(AsmToken::LBrac))
1642 return ParseIntelBracExpression(SegReg, Start, ImmDisp, Size);
1646 if (!isParsingInlineAsm()) {
1647 if (getParser().parsePrimaryExpr(Val, End))
1648 return ErrorOperand(Tok.getLoc(), "unknown token in expression");
1650 return X86Operand::CreateMem(Val, Start, End, Size);
1653 InlineAsmIdentifierInfo Info;
1654 StringRef Identifier = Tok.getString();
1655 if (ParseIntelIdentifier(Val, Identifier, Info,
1656 /*Unevaluated=*/false, End))
1658 return CreateMemForInlineAsm(/*SegReg=*/0, Val, /*BaseReg=*/0,/*IndexReg=*/0,
1659 /*Scale=*/1, Start, End, Size, Identifier, Info);
1662 /// ParseIntelMemOperand - Parse intel style memory operand.
1663 X86Operand *X86AsmParser::ParseIntelMemOperand(int64_t ImmDisp, SMLoc Start,
1665 const AsmToken &Tok = Parser.getTok();
1668 // Parse ImmDisp [ BaseReg + Scale*IndexReg + Disp ].
1669 if (getLexer().is(AsmToken::LBrac))
1670 return ParseIntelBracExpression(/*SegReg=*/0, Start, ImmDisp, Size);
1673 if (!isParsingInlineAsm()) {
1674 if (getParser().parsePrimaryExpr(Val, End))
1675 return ErrorOperand(Tok.getLoc(), "unknown token in expression");
1677 return X86Operand::CreateMem(Val, Start, End, Size);
1680 InlineAsmIdentifierInfo Info;
1681 StringRef Identifier = Tok.getString();
1682 if (ParseIntelIdentifier(Val, Identifier, Info,
1683 /*Unevaluated=*/false, End))
1685 return CreateMemForInlineAsm(/*SegReg=*/0, Val, /*BaseReg=*/0, /*IndexReg=*/0,
1686 /*Scale=*/1, Start, End, Size, Identifier, Info);
1689 /// Parse the '.' operator.
1690 bool X86AsmParser::ParseIntelDotOperator(const MCExpr *Disp,
1691 const MCExpr *&NewDisp) {
1692 const AsmToken &Tok = Parser.getTok();
1693 int64_t OrigDispVal, DotDispVal;
1695 // FIXME: Handle non-constant expressions.
1696 if (const MCConstantExpr *OrigDisp = dyn_cast<MCConstantExpr>(Disp))
1697 OrigDispVal = OrigDisp->getValue();
1699 return Error(Tok.getLoc(), "Non-constant offsets are not supported!");
1702 StringRef DotDispStr = Tok.getString().drop_front(1);
1704 // .Imm gets lexed as a real.
1705 if (Tok.is(AsmToken::Real)) {
1707 DotDispStr.getAsInteger(10, DotDisp);
1708 DotDispVal = DotDisp.getZExtValue();
1709 } else if (isParsingInlineAsm() && Tok.is(AsmToken::Identifier)) {
1711 std::pair<StringRef, StringRef> BaseMember = DotDispStr.split('.');
1712 if (SemaCallback->LookupInlineAsmField(BaseMember.first, BaseMember.second,
1714 return Error(Tok.getLoc(), "Unable to lookup field reference!");
1715 DotDispVal = DotDisp;
1717 return Error(Tok.getLoc(), "Unexpected token type!");
1719 if (isParsingInlineAsm() && Tok.is(AsmToken::Identifier)) {
1720 SMLoc Loc = SMLoc::getFromPointer(DotDispStr.data());
1721 unsigned Len = DotDispStr.size();
1722 unsigned Val = OrigDispVal + DotDispVal;
1723 InstInfo->AsmRewrites->push_back(AsmRewrite(AOK_DotOperator, Loc, Len,
1727 NewDisp = MCConstantExpr::Create(OrigDispVal + DotDispVal, getContext());
1731 /// Parse the 'offset' operator. This operator is used to specify the
1732 /// location rather then the content of a variable.
1733 X86Operand *X86AsmParser::ParseIntelOffsetOfOperator() {
1734 const AsmToken &Tok = Parser.getTok();
1735 SMLoc OffsetOfLoc = Tok.getLoc();
1736 Parser.Lex(); // Eat offset.
1739 InlineAsmIdentifierInfo Info;
1740 SMLoc Start = Tok.getLoc(), End;
1741 StringRef Identifier = Tok.getString();
1742 if (ParseIntelIdentifier(Val, Identifier, Info,
1743 /*Unevaluated=*/false, End))
1746 // Don't emit the offset operator.
1747 InstInfo->AsmRewrites->push_back(AsmRewrite(AOK_Skip, OffsetOfLoc, 7));
1749 // The offset operator will have an 'r' constraint, thus we need to create
1750 // register operand to ensure proper matching. Just pick a GPR based on
1751 // the size of a pointer.
1753 is64BitMode() ? X86::RBX : (is32BitMode() ? X86::EBX : X86::BX);
1754 return X86Operand::CreateReg(RegNo, Start, End, /*GetAddress=*/true,
1755 OffsetOfLoc, Identifier, Info.OpDecl);
1758 enum IntelOperatorKind {
1764 /// Parse the 'LENGTH', 'TYPE' and 'SIZE' operators. The LENGTH operator
1765 /// returns the number of elements in an array. It returns the value 1 for
1766 /// non-array variables. The SIZE operator returns the size of a C or C++
1767 /// variable. A variable's size is the product of its LENGTH and TYPE. The
1768 /// TYPE operator returns the size of a C or C++ type or variable. If the
1769 /// variable is an array, TYPE returns the size of a single element.
1770 X86Operand *X86AsmParser::ParseIntelOperator(unsigned OpKind) {
1771 const AsmToken &Tok = Parser.getTok();
1772 SMLoc TypeLoc = Tok.getLoc();
1773 Parser.Lex(); // Eat operator.
1775 const MCExpr *Val = 0;
1776 InlineAsmIdentifierInfo Info;
1777 SMLoc Start = Tok.getLoc(), End;
1778 StringRef Identifier = Tok.getString();
1779 if (ParseIntelIdentifier(Val, Identifier, Info,
1780 /*Unevaluated=*/true, End))
1784 return ErrorOperand(Start, "unable to lookup expression");
1788 default: llvm_unreachable("Unexpected operand kind!");
1789 case IOK_LENGTH: CVal = Info.Length; break;
1790 case IOK_SIZE: CVal = Info.Size; break;
1791 case IOK_TYPE: CVal = Info.Type; break;
1794 // Rewrite the type operator and the C or C++ type or variable in terms of an
1795 // immediate. E.g. TYPE foo -> $$4
1796 unsigned Len = End.getPointer() - TypeLoc.getPointer();
1797 InstInfo->AsmRewrites->push_back(AsmRewrite(AOK_Imm, TypeLoc, Len, CVal));
1799 const MCExpr *Imm = MCConstantExpr::Create(CVal, getContext());
1800 return X86Operand::CreateImm(Imm, Start, End);
1803 X86Operand *X86AsmParser::ParseIntelOperand() {
1804 const AsmToken &Tok = Parser.getTok();
1807 // Offset, length, type and size operators.
1808 if (isParsingInlineAsm()) {
1809 StringRef AsmTokStr = Tok.getString();
1810 if (AsmTokStr == "offset" || AsmTokStr == "OFFSET")
1811 return ParseIntelOffsetOfOperator();
1812 if (AsmTokStr == "length" || AsmTokStr == "LENGTH")
1813 return ParseIntelOperator(IOK_LENGTH);
1814 if (AsmTokStr == "size" || AsmTokStr == "SIZE")
1815 return ParseIntelOperator(IOK_SIZE);
1816 if (AsmTokStr == "type" || AsmTokStr == "TYPE")
1817 return ParseIntelOperator(IOK_TYPE);
1820 unsigned Size = getIntelMemOperandSize(Tok.getString());
1822 Parser.Lex(); // Eat operand size (e.g., byte, word).
1823 if (Tok.getString() != "PTR" && Tok.getString() != "ptr")
1824 return ErrorOperand(Start, "Expected 'PTR' or 'ptr' token!");
1825 Parser.Lex(); // Eat ptr.
1827 Start = Tok.getLoc();
1830 if (getLexer().is(AsmToken::Integer) || getLexer().is(AsmToken::Minus) ||
1831 getLexer().is(AsmToken::LParen)) {
1832 AsmToken StartTok = Tok;
1833 IntelExprStateMachine SM(/*Imm=*/0, /*StopOnLBrac=*/true,
1834 /*AddImmPrefix=*/false);
1835 if (ParseIntelExpression(SM, End))
1838 int64_t Imm = SM.getImm();
1839 if (isParsingInlineAsm()) {
1840 unsigned Len = Tok.getLoc().getPointer() - Start.getPointer();
1841 if (StartTok.getString().size() == Len)
1842 // Just add a prefix if this wasn't a complex immediate expression.
1843 InstInfo->AsmRewrites->push_back(AsmRewrite(AOK_ImmPrefix, Start));
1845 // Otherwise, rewrite the complex expression as a single immediate.
1846 InstInfo->AsmRewrites->push_back(AsmRewrite(AOK_Imm, Start, Len, Imm));
1849 if (getLexer().isNot(AsmToken::LBrac)) {
1850 // If a directional label (ie. 1f or 2b) was parsed above from
1851 // ParseIntelExpression() then SM.getSym() was set to a pointer to
1852 // to the MCExpr with the directional local symbol and this is a
1853 // memory operand not an immediate operand.
1855 return X86Operand::CreateMem(SM.getSym(), Start, End, Size);
1857 const MCExpr *ImmExpr = MCConstantExpr::Create(Imm, getContext());
1858 return X86Operand::CreateImm(ImmExpr, Start, End);
1861 // Only positive immediates are valid.
1863 return ErrorOperand(Start, "expected a positive immediate displacement "
1864 "before bracketed expr.");
1866 // Parse ImmDisp [ BaseReg + Scale*IndexReg + Disp ].
1867 return ParseIntelMemOperand(Imm, Start, Size);
1872 if (!ParseRegister(RegNo, Start, End)) {
1873 // If this is a segment register followed by a ':', then this is the start
1874 // of a segment override, otherwise this is a normal register reference.
1875 if (getLexer().isNot(AsmToken::Colon))
1876 return X86Operand::CreateReg(RegNo, Start, End);
1878 return ParseIntelSegmentOverride(/*SegReg=*/RegNo, Start, Size);
1882 return ParseIntelMemOperand(/*Disp=*/0, Start, Size);
1885 X86Operand *X86AsmParser::ParseATTOperand() {
1886 switch (getLexer().getKind()) {
1888 // Parse a memory operand with no segment register.
1889 return ParseMemOperand(0, Parser.getTok().getLoc());
1890 case AsmToken::Percent: {
1891 // Read the register.
1894 if (ParseRegister(RegNo, Start, End)) return 0;
1895 if (RegNo == X86::EIZ || RegNo == X86::RIZ) {
1896 Error(Start, "%eiz and %riz can only be used as index registers",
1897 SMRange(Start, End));
1901 // If this is a segment register followed by a ':', then this is the start
1902 // of a memory reference, otherwise this is a normal register reference.
1903 if (getLexer().isNot(AsmToken::Colon))
1904 return X86Operand::CreateReg(RegNo, Start, End);
1906 getParser().Lex(); // Eat the colon.
1907 return ParseMemOperand(RegNo, Start);
1909 case AsmToken::Dollar: {
1910 // $42 -> immediate.
1911 SMLoc Start = Parser.getTok().getLoc(), End;
1914 if (getParser().parseExpression(Val, End))
1916 return X86Operand::CreateImm(Val, Start, End);
1921 /// ParseMemOperand: segment: disp(basereg, indexreg, scale). The '%ds:' prefix
1922 /// has already been parsed if present.
1923 X86Operand *X86AsmParser::ParseMemOperand(unsigned SegReg, SMLoc MemStart) {
1925 // We have to disambiguate a parenthesized expression "(4+5)" from the start
1926 // of a memory operand with a missing displacement "(%ebx)" or "(,%eax)". The
1927 // only way to do this without lookahead is to eat the '(' and see what is
1929 const MCExpr *Disp = MCConstantExpr::Create(0, getParser().getContext());
1930 if (getLexer().isNot(AsmToken::LParen)) {
1932 if (getParser().parseExpression(Disp, ExprEnd)) return 0;
1934 // After parsing the base expression we could either have a parenthesized
1935 // memory address or not. If not, return now. If so, eat the (.
1936 if (getLexer().isNot(AsmToken::LParen)) {
1937 // Unless we have a segment register, treat this as an immediate.
1939 return X86Operand::CreateMem(Disp, MemStart, ExprEnd);
1940 return X86Operand::CreateMem(SegReg, Disp, 0, 0, 1, MemStart, ExprEnd);
1946 // Okay, we have a '('. We don't know if this is an expression or not, but
1947 // so we have to eat the ( to see beyond it.
1948 SMLoc LParenLoc = Parser.getTok().getLoc();
1949 Parser.Lex(); // Eat the '('.
1951 if (getLexer().is(AsmToken::Percent) || getLexer().is(AsmToken::Comma)) {
1952 // Nothing to do here, fall into the code below with the '(' part of the
1953 // memory operand consumed.
1957 // It must be an parenthesized expression, parse it now.
1958 if (getParser().parseParenExpression(Disp, ExprEnd))
1961 // After parsing the base expression we could either have a parenthesized
1962 // memory address or not. If not, return now. If so, eat the (.
1963 if (getLexer().isNot(AsmToken::LParen)) {
1964 // Unless we have a segment register, treat this as an immediate.
1966 return X86Operand::CreateMem(Disp, LParenLoc, ExprEnd);
1967 return X86Operand::CreateMem(SegReg, Disp, 0, 0, 1, MemStart, ExprEnd);
1975 // If we reached here, then we just ate the ( of the memory operand. Process
1976 // the rest of the memory operand.
1977 unsigned BaseReg = 0, IndexReg = 0, Scale = 1;
1978 SMLoc IndexLoc, BaseLoc;
1980 if (getLexer().is(AsmToken::Percent)) {
1981 SMLoc StartLoc, EndLoc;
1982 BaseLoc = Parser.getTok().getLoc();
1983 if (ParseRegister(BaseReg, StartLoc, EndLoc)) return 0;
1984 if (BaseReg == X86::EIZ || BaseReg == X86::RIZ) {
1985 Error(StartLoc, "eiz and riz can only be used as index registers",
1986 SMRange(StartLoc, EndLoc));
1991 if (getLexer().is(AsmToken::Comma)) {
1992 Parser.Lex(); // Eat the comma.
1993 IndexLoc = Parser.getTok().getLoc();
1995 // Following the comma we should have either an index register, or a scale
1996 // value. We don't support the later form, but we want to parse it
1999 // Not that even though it would be completely consistent to support syntax
2000 // like "1(%eax,,1)", the assembler doesn't. Use "eiz" or "riz" for this.
2001 if (getLexer().is(AsmToken::Percent)) {
2003 if (ParseRegister(IndexReg, L, L)) return 0;
2005 if (getLexer().isNot(AsmToken::RParen)) {
2006 // Parse the scale amount:
2007 // ::= ',' [scale-expression]
2008 if (getLexer().isNot(AsmToken::Comma)) {
2009 Error(Parser.getTok().getLoc(),
2010 "expected comma in scale expression");
2013 Parser.Lex(); // Eat the comma.
2015 if (getLexer().isNot(AsmToken::RParen)) {
2016 SMLoc Loc = Parser.getTok().getLoc();
2019 if (getParser().parseAbsoluteExpression(ScaleVal)){
2020 Error(Loc, "expected scale expression");
2024 // Validate the scale amount.
2025 if (X86MCRegisterClasses[X86::GR16RegClassID].contains(BaseReg) &&
2027 Error(Loc, "scale factor in 16-bit address must be 1");
2030 if (ScaleVal != 1 && ScaleVal != 2 && ScaleVal != 4 && ScaleVal != 8){
2031 Error(Loc, "scale factor in address must be 1, 2, 4 or 8");
2034 Scale = (unsigned)ScaleVal;
2037 } else if (getLexer().isNot(AsmToken::RParen)) {
2038 // A scale amount without an index is ignored.
2040 SMLoc Loc = Parser.getTok().getLoc();
2043 if (getParser().parseAbsoluteExpression(Value))
2047 Warning(Loc, "scale factor without index register is ignored");
2052 // Ok, we've eaten the memory operand, verify we have a ')' and eat it too.
2053 if (getLexer().isNot(AsmToken::RParen)) {
2054 Error(Parser.getTok().getLoc(), "unexpected token in memory operand");
2057 SMLoc MemEnd = Parser.getTok().getEndLoc();
2058 Parser.Lex(); // Eat the ')'.
2060 // Check for use of invalid 16-bit registers. Only BX/BP/SI/DI are allowed,
2061 // and then only in non-64-bit modes. Except for DX, which is a special case
2062 // because an unofficial form of in/out instructions uses it.
2063 if (X86MCRegisterClasses[X86::GR16RegClassID].contains(BaseReg) &&
2064 (is64BitMode() || (BaseReg != X86::BX && BaseReg != X86::BP &&
2065 BaseReg != X86::SI && BaseReg != X86::DI)) &&
2066 BaseReg != X86::DX) {
2067 Error(BaseLoc, "invalid 16-bit base register");
2071 X86MCRegisterClasses[X86::GR16RegClassID].contains(IndexReg)) {
2072 Error(IndexLoc, "16-bit memory operand may not include only index register");
2075 // If we have both a base register and an index register make sure they are
2076 // both 64-bit or 32-bit registers.
2077 // To support VSIB, IndexReg can be 128-bit or 256-bit registers.
2078 if (BaseReg != 0 && IndexReg != 0) {
2079 if (X86MCRegisterClasses[X86::GR64RegClassID].contains(BaseReg) &&
2080 (X86MCRegisterClasses[X86::GR16RegClassID].contains(IndexReg) ||
2081 X86MCRegisterClasses[X86::GR32RegClassID].contains(IndexReg)) &&
2082 IndexReg != X86::RIZ) {
2083 Error(BaseLoc, "base register is 64-bit, but index register is not");
2086 if (X86MCRegisterClasses[X86::GR32RegClassID].contains(BaseReg) &&
2087 (X86MCRegisterClasses[X86::GR16RegClassID].contains(IndexReg) ||
2088 X86MCRegisterClasses[X86::GR64RegClassID].contains(IndexReg)) &&
2089 IndexReg != X86::EIZ){
2090 Error(BaseLoc, "base register is 32-bit, but index register is not");
2093 if (X86MCRegisterClasses[X86::GR16RegClassID].contains(BaseReg)) {
2094 if (X86MCRegisterClasses[X86::GR32RegClassID].contains(IndexReg) ||
2095 X86MCRegisterClasses[X86::GR64RegClassID].contains(IndexReg)) {
2096 Error(BaseLoc, "base register is 16-bit, but index register is not");
2099 if (((BaseReg == X86::BX || BaseReg == X86::BP) &&
2100 IndexReg != X86::SI && IndexReg != X86::DI) ||
2101 ((BaseReg == X86::SI || BaseReg == X86::DI) &&
2102 IndexReg != X86::BX && IndexReg != X86::BP)) {
2103 Error(BaseLoc, "invalid 16-bit base/index register combination");
2109 return X86Operand::CreateMem(SegReg, Disp, BaseReg, IndexReg, Scale,
2114 ParseInstruction(ParseInstructionInfo &Info, StringRef Name, SMLoc NameLoc,
2115 SmallVectorImpl<MCParsedAsmOperand*> &Operands) {
2117 StringRef PatchedName = Name;
2119 // FIXME: Hack to recognize setneb as setne.
2120 if (PatchedName.startswith("set") && PatchedName.endswith("b") &&
2121 PatchedName != "setb" && PatchedName != "setnb")
2122 PatchedName = PatchedName.substr(0, Name.size()-1);
2124 // FIXME: Hack to recognize cmp<comparison code>{ss,sd,ps,pd}.
2125 const MCExpr *ExtraImmOp = 0;
2126 if ((PatchedName.startswith("cmp") || PatchedName.startswith("vcmp")) &&
2127 (PatchedName.endswith("ss") || PatchedName.endswith("sd") ||
2128 PatchedName.endswith("ps") || PatchedName.endswith("pd"))) {
2129 bool IsVCMP = PatchedName[0] == 'v';
2130 unsigned SSECCIdx = IsVCMP ? 4 : 3;
2131 unsigned SSEComparisonCode = StringSwitch<unsigned>(
2132 PatchedName.slice(SSECCIdx, PatchedName.size() - 2))
2136 .Case("unord", 0x03)
2141 /* AVX only from here */
2142 .Case("eq_uq", 0x08)
2145 .Case("false", 0x0B)
2146 .Case("neq_oq", 0x0C)
2150 .Case("eq_os", 0x10)
2151 .Case("lt_oq", 0x11)
2152 .Case("le_oq", 0x12)
2153 .Case("unord_s", 0x13)
2154 .Case("neq_us", 0x14)
2155 .Case("nlt_uq", 0x15)
2156 .Case("nle_uq", 0x16)
2157 .Case("ord_s", 0x17)
2158 .Case("eq_us", 0x18)
2159 .Case("nge_uq", 0x19)
2160 .Case("ngt_uq", 0x1A)
2161 .Case("false_os", 0x1B)
2162 .Case("neq_os", 0x1C)
2163 .Case("ge_oq", 0x1D)
2164 .Case("gt_oq", 0x1E)
2165 .Case("true_us", 0x1F)
2167 if (SSEComparisonCode != ~0U && (IsVCMP || SSEComparisonCode < 8)) {
2168 ExtraImmOp = MCConstantExpr::Create(SSEComparisonCode,
2169 getParser().getContext());
2170 if (PatchedName.endswith("ss")) {
2171 PatchedName = IsVCMP ? "vcmpss" : "cmpss";
2172 } else if (PatchedName.endswith("sd")) {
2173 PatchedName = IsVCMP ? "vcmpsd" : "cmpsd";
2174 } else if (PatchedName.endswith("ps")) {
2175 PatchedName = IsVCMP ? "vcmpps" : "cmpps";
2177 assert(PatchedName.endswith("pd") && "Unexpected mnemonic!");
2178 PatchedName = IsVCMP ? "vcmppd" : "cmppd";
2183 Operands.push_back(X86Operand::CreateToken(PatchedName, NameLoc));
2185 if (ExtraImmOp && !isParsingIntelSyntax())
2186 Operands.push_back(X86Operand::CreateImm(ExtraImmOp, NameLoc, NameLoc));
2188 // Determine whether this is an instruction prefix.
2190 Name == "lock" || Name == "rep" ||
2191 Name == "repe" || Name == "repz" ||
2192 Name == "repne" || Name == "repnz" ||
2193 Name == "rex64" || Name == "data16";
2196 // This does the actual operand parsing. Don't parse any more if we have a
2197 // prefix juxtaposed with an operation like "lock incl 4(%rax)", because we
2198 // just want to parse the "lock" as the first instruction and the "incl" as
2200 if (getLexer().isNot(AsmToken::EndOfStatement) && !isPrefix) {
2202 // Parse '*' modifier.
2203 if (getLexer().is(AsmToken::Star))
2204 Operands.push_back(X86Operand::CreateToken("*", consumeToken()));
2206 // Read the first operand.
2207 if (X86Operand *Op = ParseOperand())
2208 Operands.push_back(Op);
2210 Parser.eatToEndOfStatement();
2214 while (getLexer().is(AsmToken::Comma)) {
2215 Parser.Lex(); // Eat the comma.
2217 // Parse and remember the operand.
2218 if (X86Operand *Op = ParseOperand())
2219 Operands.push_back(Op);
2221 Parser.eatToEndOfStatement();
2226 if (STI.getFeatureBits() & X86::FeatureAVX512) {
2227 // Parse mask register {%k1}
2228 if (getLexer().is(AsmToken::LCurly)) {
2229 Operands.push_back(X86Operand::CreateToken("{", consumeToken()));
2230 if (X86Operand *Op = ParseOperand()) {
2231 Operands.push_back(Op);
2232 if (!getLexer().is(AsmToken::RCurly)) {
2233 SMLoc Loc = getLexer().getLoc();
2234 Parser.eatToEndOfStatement();
2235 return Error(Loc, "Expected } at this point");
2237 Operands.push_back(X86Operand::CreateToken("}", consumeToken()));
2239 Parser.eatToEndOfStatement();
2243 // TODO: add parsing of broadcasts {1to8}, {1to16}
2244 // Parse "zeroing non-masked" semantic {z}
2245 if (getLexer().is(AsmToken::LCurly)) {
2246 Operands.push_back(X86Operand::CreateToken("{z}", consumeToken()));
2247 if (!getLexer().is(AsmToken::Identifier) || getLexer().getTok().getIdentifier() != "z") {
2248 SMLoc Loc = getLexer().getLoc();
2249 Parser.eatToEndOfStatement();
2250 return Error(Loc, "Expected z at this point");
2252 Parser.Lex(); // Eat the z
2253 if (!getLexer().is(AsmToken::RCurly)) {
2254 SMLoc Loc = getLexer().getLoc();
2255 Parser.eatToEndOfStatement();
2256 return Error(Loc, "Expected } at this point");
2258 Parser.Lex(); // Eat the }
2262 if (getLexer().isNot(AsmToken::EndOfStatement)) {
2263 SMLoc Loc = getLexer().getLoc();
2264 Parser.eatToEndOfStatement();
2265 return Error(Loc, "unexpected token in argument list");
2269 if (getLexer().is(AsmToken::EndOfStatement))
2270 Parser.Lex(); // Consume the EndOfStatement
2271 else if (isPrefix && getLexer().is(AsmToken::Slash))
2272 Parser.Lex(); // Consume the prefix separator Slash
2274 if (ExtraImmOp && isParsingIntelSyntax())
2275 Operands.push_back(X86Operand::CreateImm(ExtraImmOp, NameLoc, NameLoc));
2277 // This is a terrible hack to handle "out[bwl]? %al, (%dx)" ->
2278 // "outb %al, %dx". Out doesn't take a memory form, but this is a widely
2279 // documented form in various unofficial manuals, so a lot of code uses it.
2280 if ((Name == "outb" || Name == "outw" || Name == "outl" || Name == "out") &&
2281 Operands.size() == 3) {
2282 X86Operand &Op = *(X86Operand*)Operands.back();
2283 if (Op.isMem() && Op.Mem.SegReg == 0 &&
2284 isa<MCConstantExpr>(Op.Mem.Disp) &&
2285 cast<MCConstantExpr>(Op.Mem.Disp)->getValue() == 0 &&
2286 Op.Mem.BaseReg == MatchRegisterName("dx") && Op.Mem.IndexReg == 0) {
2287 SMLoc Loc = Op.getEndLoc();
2288 Operands.back() = X86Operand::CreateReg(Op.Mem.BaseReg, Loc, Loc);
2292 // Same hack for "in[bwl]? (%dx), %al" -> "inb %dx, %al".
2293 if ((Name == "inb" || Name == "inw" || Name == "inl" || Name == "in") &&
2294 Operands.size() == 3) {
2295 X86Operand &Op = *(X86Operand*)Operands.begin()[1];
2296 if (Op.isMem() && Op.Mem.SegReg == 0 &&
2297 isa<MCConstantExpr>(Op.Mem.Disp) &&
2298 cast<MCConstantExpr>(Op.Mem.Disp)->getValue() == 0 &&
2299 Op.Mem.BaseReg == MatchRegisterName("dx") && Op.Mem.IndexReg == 0) {
2300 SMLoc Loc = Op.getEndLoc();
2301 Operands.begin()[1] = X86Operand::CreateReg(Op.Mem.BaseReg, Loc, Loc);
2306 // Append default arguments to "ins[bwld]"
2307 if (Name.startswith("ins") && Operands.size() == 1 &&
2308 (Name == "insb" || Name == "insw" || Name == "insl" ||
2310 if (isParsingIntelSyntax()) {
2311 Operands.push_back(X86Operand::CreateReg(X86::DX, NameLoc, NameLoc));
2312 Operands.push_back(DefaultMemDIOperand(NameLoc));
2314 Operands.push_back(X86Operand::CreateReg(X86::DX, NameLoc, NameLoc));
2315 Operands.push_back(DefaultMemDIOperand(NameLoc));
2319 // Append default arguments to "outs[bwld]"
2320 if (Name.startswith("outs") && Operands.size() == 1 &&
2321 (Name == "outsb" || Name == "outsw" || Name == "outsl" ||
2322 Name == "outsd" )) {
2323 if (isParsingIntelSyntax()) {
2324 Operands.push_back(DefaultMemSIOperand(NameLoc));
2325 Operands.push_back(X86Operand::CreateReg(X86::DX, NameLoc, NameLoc));
2327 Operands.push_back(DefaultMemSIOperand(NameLoc));
2328 Operands.push_back(X86Operand::CreateReg(X86::DX, NameLoc, NameLoc));
2332 // Transform "lods[bwlq]" into "lods[bwlq] ($SIREG)" for appropriate
2333 // values of $SIREG according to the mode. It would be nice if this
2334 // could be achieved with InstAlias in the tables.
2335 if (Name.startswith("lods") && Operands.size() == 1 &&
2336 (Name == "lods" || Name == "lodsb" || Name == "lodsw" ||
2337 Name == "lodsl" || Name == "lodsd" || Name == "lodsq"))
2338 Operands.push_back(DefaultMemSIOperand(NameLoc));
2340 // Transform "stos[bwlq]" into "stos[bwlq] ($DIREG)" for appropriate
2341 // values of $DIREG according to the mode. It would be nice if this
2342 // could be achieved with InstAlias in the tables.
2343 if (Name.startswith("stos") && Operands.size() == 1 &&
2344 (Name == "stos" || Name == "stosb" || Name == "stosw" ||
2345 Name == "stosl" || Name == "stosd" || Name == "stosq"))
2346 Operands.push_back(DefaultMemDIOperand(NameLoc));
2348 // Transform "scas[bwlq]" into "scas[bwlq] ($DIREG)" for appropriate
2349 // values of $DIREG according to the mode. It would be nice if this
2350 // could be achieved with InstAlias in the tables.
2351 if (Name.startswith("scas") && Operands.size() == 1 &&
2352 (Name == "scas" || Name == "scasb" || Name == "scasw" ||
2353 Name == "scasl" || Name == "scasd" || Name == "scasq"))
2354 Operands.push_back(DefaultMemDIOperand(NameLoc));
2356 // Add default SI and DI operands to "cmps[bwlq]".
2357 if (Name.startswith("cmps") &&
2358 (Name == "cmps" || Name == "cmpsb" || Name == "cmpsw" ||
2359 Name == "cmpsl" || Name == "cmpsd" || Name == "cmpsq")) {
2360 if (Operands.size() == 1) {
2361 if (isParsingIntelSyntax()) {
2362 Operands.push_back(DefaultMemSIOperand(NameLoc));
2363 Operands.push_back(DefaultMemDIOperand(NameLoc));
2365 Operands.push_back(DefaultMemDIOperand(NameLoc));
2366 Operands.push_back(DefaultMemSIOperand(NameLoc));
2368 } else if (Operands.size() == 3) {
2369 X86Operand &Op = *(X86Operand*)Operands.begin()[1];
2370 X86Operand &Op2 = *(X86Operand*)Operands.begin()[2];
2371 if (!doSrcDstMatch(Op, Op2))
2372 return Error(Op.getStartLoc(),
2373 "mismatching source and destination index registers");
2377 // Add default SI and DI operands to "movs[bwlq]".
2378 if ((Name.startswith("movs") &&
2379 (Name == "movs" || Name == "movsb" || Name == "movsw" ||
2380 Name == "movsl" || Name == "movsd" || Name == "movsq")) ||
2381 (Name.startswith("smov") &&
2382 (Name == "smov" || Name == "smovb" || Name == "smovw" ||
2383 Name == "smovl" || Name == "smovd" || Name == "smovq"))) {
2384 if (Operands.size() == 1) {
2385 if (Name == "movsd")
2386 Operands.back() = X86Operand::CreateToken("movsl", NameLoc);
2387 if (isParsingIntelSyntax()) {
2388 Operands.push_back(DefaultMemDIOperand(NameLoc));
2389 Operands.push_back(DefaultMemSIOperand(NameLoc));
2391 Operands.push_back(DefaultMemSIOperand(NameLoc));
2392 Operands.push_back(DefaultMemDIOperand(NameLoc));
2394 } else if (Operands.size() == 3) {
2395 X86Operand &Op = *(X86Operand*)Operands.begin()[1];
2396 X86Operand &Op2 = *(X86Operand*)Operands.begin()[2];
2397 if (!doSrcDstMatch(Op, Op2))
2398 return Error(Op.getStartLoc(),
2399 "mismatching source and destination index registers");
2403 // FIXME: Hack to handle recognize s{hr,ar,hl} $1, <op>. Canonicalize to
2405 if ((Name.startswith("shr") || Name.startswith("sar") ||
2406 Name.startswith("shl") || Name.startswith("sal") ||
2407 Name.startswith("rcl") || Name.startswith("rcr") ||
2408 Name.startswith("rol") || Name.startswith("ror")) &&
2409 Operands.size() == 3) {
2410 if (isParsingIntelSyntax()) {
2412 X86Operand *Op1 = static_cast<X86Operand*>(Operands[2]);
2413 if (Op1->isImm() && isa<MCConstantExpr>(Op1->getImm()) &&
2414 cast<MCConstantExpr>(Op1->getImm())->getValue() == 1) {
2416 Operands.pop_back();
2419 X86Operand *Op1 = static_cast<X86Operand*>(Operands[1]);
2420 if (Op1->isImm() && isa<MCConstantExpr>(Op1->getImm()) &&
2421 cast<MCConstantExpr>(Op1->getImm())->getValue() == 1) {
2423 Operands.erase(Operands.begin() + 1);
2428 // Transforms "int $3" into "int3" as a size optimization. We can't write an
2429 // instalias with an immediate operand yet.
2430 if (Name == "int" && Operands.size() == 2) {
2431 X86Operand *Op1 = static_cast<X86Operand*>(Operands[1]);
2432 if (Op1->isImm() && isa<MCConstantExpr>(Op1->getImm()) &&
2433 cast<MCConstantExpr>(Op1->getImm())->getValue() == 3) {
2435 Operands.erase(Operands.begin() + 1);
2436 static_cast<X86Operand*>(Operands[0])->setTokenValue("int3");
2443 static bool convertToSExti8(MCInst &Inst, unsigned Opcode, unsigned Reg,
2446 TmpInst.setOpcode(Opcode);
2448 TmpInst.addOperand(MCOperand::CreateReg(Reg));
2449 TmpInst.addOperand(MCOperand::CreateReg(Reg));
2450 TmpInst.addOperand(Inst.getOperand(0));
2455 static bool convert16i16to16ri8(MCInst &Inst, unsigned Opcode,
2456 bool isCmp = false) {
2457 if (!Inst.getOperand(0).isImm() ||
2458 !isImmSExti16i8Value(Inst.getOperand(0).getImm()))
2461 return convertToSExti8(Inst, Opcode, X86::AX, isCmp);
2464 static bool convert32i32to32ri8(MCInst &Inst, unsigned Opcode,
2465 bool isCmp = false) {
2466 if (!Inst.getOperand(0).isImm() ||
2467 !isImmSExti32i8Value(Inst.getOperand(0).getImm()))
2470 return convertToSExti8(Inst, Opcode, X86::EAX, isCmp);
2473 static bool convert64i32to64ri8(MCInst &Inst, unsigned Opcode,
2474 bool isCmp = false) {
2475 if (!Inst.getOperand(0).isImm() ||
2476 !isImmSExti64i8Value(Inst.getOperand(0).getImm()))
2479 return convertToSExti8(Inst, Opcode, X86::RAX, isCmp);
2483 processInstruction(MCInst &Inst,
2484 const SmallVectorImpl<MCParsedAsmOperand*> &Ops) {
2485 switch (Inst.getOpcode()) {
2486 default: return false;
2487 case X86::AND16i16: return convert16i16to16ri8(Inst, X86::AND16ri8);
2488 case X86::AND32i32: return convert32i32to32ri8(Inst, X86::AND32ri8);
2489 case X86::AND64i32: return convert64i32to64ri8(Inst, X86::AND64ri8);
2490 case X86::XOR16i16: return convert16i16to16ri8(Inst, X86::XOR16ri8);
2491 case X86::XOR32i32: return convert32i32to32ri8(Inst, X86::XOR32ri8);
2492 case X86::XOR64i32: return convert64i32to64ri8(Inst, X86::XOR64ri8);
2493 case X86::OR16i16: return convert16i16to16ri8(Inst, X86::OR16ri8);
2494 case X86::OR32i32: return convert32i32to32ri8(Inst, X86::OR32ri8);
2495 case X86::OR64i32: return convert64i32to64ri8(Inst, X86::OR64ri8);
2496 case X86::CMP16i16: return convert16i16to16ri8(Inst, X86::CMP16ri8, true);
2497 case X86::CMP32i32: return convert32i32to32ri8(Inst, X86::CMP32ri8, true);
2498 case X86::CMP64i32: return convert64i32to64ri8(Inst, X86::CMP64ri8, true);
2499 case X86::ADD16i16: return convert16i16to16ri8(Inst, X86::ADD16ri8);
2500 case X86::ADD32i32: return convert32i32to32ri8(Inst, X86::ADD32ri8);
2501 case X86::ADD64i32: return convert64i32to64ri8(Inst, X86::ADD64ri8);
2502 case X86::SUB16i16: return convert16i16to16ri8(Inst, X86::SUB16ri8);
2503 case X86::SUB32i32: return convert32i32to32ri8(Inst, X86::SUB32ri8);
2504 case X86::SUB64i32: return convert64i32to64ri8(Inst, X86::SUB64ri8);
2505 case X86::ADC16i16: return convert16i16to16ri8(Inst, X86::ADC16ri8);
2506 case X86::ADC32i32: return convert32i32to32ri8(Inst, X86::ADC32ri8);
2507 case X86::ADC64i32: return convert64i32to64ri8(Inst, X86::ADC64ri8);
2508 case X86::SBB16i16: return convert16i16to16ri8(Inst, X86::SBB16ri8);
2509 case X86::SBB32i32: return convert32i32to32ri8(Inst, X86::SBB32ri8);
2510 case X86::SBB64i32: return convert64i32to64ri8(Inst, X86::SBB64ri8);
2511 case X86::VMOVAPDrr:
2512 case X86::VMOVAPDYrr:
2513 case X86::VMOVAPSrr:
2514 case X86::VMOVAPSYrr:
2515 case X86::VMOVDQArr:
2516 case X86::VMOVDQAYrr:
2517 case X86::VMOVDQUrr:
2518 case X86::VMOVDQUYrr:
2519 case X86::VMOVUPDrr:
2520 case X86::VMOVUPDYrr:
2521 case X86::VMOVUPSrr:
2522 case X86::VMOVUPSYrr: {
2523 if (X86II::isX86_64ExtendedReg(Inst.getOperand(0).getReg()) ||
2524 !X86II::isX86_64ExtendedReg(Inst.getOperand(1).getReg()))
2528 switch (Inst.getOpcode()) {
2529 default: llvm_unreachable("Invalid opcode");
2530 case X86::VMOVAPDrr: NewOpc = X86::VMOVAPDrr_REV; break;
2531 case X86::VMOVAPDYrr: NewOpc = X86::VMOVAPDYrr_REV; break;
2532 case X86::VMOVAPSrr: NewOpc = X86::VMOVAPSrr_REV; break;
2533 case X86::VMOVAPSYrr: NewOpc = X86::VMOVAPSYrr_REV; break;
2534 case X86::VMOVDQArr: NewOpc = X86::VMOVDQArr_REV; break;
2535 case X86::VMOVDQAYrr: NewOpc = X86::VMOVDQAYrr_REV; break;
2536 case X86::VMOVDQUrr: NewOpc = X86::VMOVDQUrr_REV; break;
2537 case X86::VMOVDQUYrr: NewOpc = X86::VMOVDQUYrr_REV; break;
2538 case X86::VMOVUPDrr: NewOpc = X86::VMOVUPDrr_REV; break;
2539 case X86::VMOVUPDYrr: NewOpc = X86::VMOVUPDYrr_REV; break;
2540 case X86::VMOVUPSrr: NewOpc = X86::VMOVUPSrr_REV; break;
2541 case X86::VMOVUPSYrr: NewOpc = X86::VMOVUPSYrr_REV; break;
2543 Inst.setOpcode(NewOpc);
2547 case X86::VMOVSSrr: {
2548 if (X86II::isX86_64ExtendedReg(Inst.getOperand(0).getReg()) ||
2549 !X86II::isX86_64ExtendedReg(Inst.getOperand(2).getReg()))
2552 switch (Inst.getOpcode()) {
2553 default: llvm_unreachable("Invalid opcode");
2554 case X86::VMOVSDrr: NewOpc = X86::VMOVSDrr_REV; break;
2555 case X86::VMOVSSrr: NewOpc = X86::VMOVSSrr_REV; break;
2557 Inst.setOpcode(NewOpc);
2563 static const char *getSubtargetFeatureName(unsigned Val);
2565 MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode,
2566 SmallVectorImpl<MCParsedAsmOperand*> &Operands,
2567 MCStreamer &Out, unsigned &ErrorInfo,
2568 bool MatchingInlineAsm) {
2569 assert(!Operands.empty() && "Unexpect empty operand list!");
2570 X86Operand *Op = static_cast<X86Operand*>(Operands[0]);
2571 assert(Op->isToken() && "Leading operand should always be a mnemonic!");
2572 ArrayRef<SMRange> EmptyRanges = None;
2574 // First, handle aliases that expand to multiple instructions.
2575 // FIXME: This should be replaced with a real .td file alias mechanism.
2576 // Also, MatchInstructionImpl should actually *do* the EmitInstruction
2578 if (Op->getToken() == "fstsw" || Op->getToken() == "fstcw" ||
2579 Op->getToken() == "fstsww" || Op->getToken() == "fstcww" ||
2580 Op->getToken() == "finit" || Op->getToken() == "fsave" ||
2581 Op->getToken() == "fstenv" || Op->getToken() == "fclex") {
2583 Inst.setOpcode(X86::WAIT);
2585 if (!MatchingInlineAsm)
2586 Out.EmitInstruction(Inst);
2589 StringSwitch<const char*>(Op->getToken())
2590 .Case("finit", "fninit")
2591 .Case("fsave", "fnsave")
2592 .Case("fstcw", "fnstcw")
2593 .Case("fstcww", "fnstcw")
2594 .Case("fstenv", "fnstenv")
2595 .Case("fstsw", "fnstsw")
2596 .Case("fstsww", "fnstsw")
2597 .Case("fclex", "fnclex")
2599 assert(Repl && "Unknown wait-prefixed instruction");
2601 Operands[0] = X86Operand::CreateToken(Repl, IDLoc);
2604 bool WasOriginallyInvalidOperand = false;
2607 // First, try a direct match.
2608 switch (MatchInstructionImpl(Operands, Inst,
2609 ErrorInfo, MatchingInlineAsm,
2610 isParsingIntelSyntax())) {
2613 // Some instructions need post-processing to, for example, tweak which
2614 // encoding is selected. Loop on it while changes happen so the
2615 // individual transformations can chain off each other.
2616 if (!MatchingInlineAsm)
2617 while (processInstruction(Inst, Operands))
2621 if (!MatchingInlineAsm)
2622 Out.EmitInstruction(Inst);
2623 Opcode = Inst.getOpcode();
2625 case Match_MissingFeature: {
2626 assert(ErrorInfo && "Unknown missing feature!");
2627 // Special case the error message for the very common case where only
2628 // a single subtarget feature is missing.
2629 std::string Msg = "instruction requires:";
2631 for (unsigned i = 0; i < (sizeof(ErrorInfo)*8-1); ++i) {
2632 if (ErrorInfo & Mask) {
2634 Msg += getSubtargetFeatureName(ErrorInfo & Mask);
2638 return Error(IDLoc, Msg, EmptyRanges, MatchingInlineAsm);
2640 case Match_InvalidOperand:
2641 WasOriginallyInvalidOperand = true;
2643 case Match_MnemonicFail:
2647 // FIXME: Ideally, we would only attempt suffix matches for things which are
2648 // valid prefixes, and we could just infer the right unambiguous
2649 // type. However, that requires substantially more matcher support than the
2652 // Change the operand to point to a temporary token.
2653 StringRef Base = Op->getToken();
2654 SmallString<16> Tmp;
2657 Op->setTokenValue(Tmp.str());
2659 // If this instruction starts with an 'f', then it is a floating point stack
2660 // instruction. These come in up to three forms for 32-bit, 64-bit, and
2661 // 80-bit floating point, which use the suffixes s,l,t respectively.
2663 // Otherwise, we assume that this may be an integer instruction, which comes
2664 // in 8/16/32/64-bit forms using the b,w,l,q suffixes respectively.
2665 const char *Suffixes = Base[0] != 'f' ? "bwlq" : "slt\0";
2667 // Check for the various suffix matches.
2668 Tmp[Base.size()] = Suffixes[0];
2669 unsigned ErrorInfoIgnore;
2670 unsigned ErrorInfoMissingFeature = 0; // Init suppresses compiler warnings.
2671 unsigned Match1, Match2, Match3, Match4;
2673 Match1 = MatchInstructionImpl(Operands, Inst, ErrorInfoIgnore,
2674 MatchingInlineAsm, isParsingIntelSyntax());
2675 // If this returned as a missing feature failure, remember that.
2676 if (Match1 == Match_MissingFeature)
2677 ErrorInfoMissingFeature = ErrorInfoIgnore;
2678 Tmp[Base.size()] = Suffixes[1];
2679 Match2 = MatchInstructionImpl(Operands, Inst, ErrorInfoIgnore,
2680 MatchingInlineAsm, isParsingIntelSyntax());
2681 // If this returned as a missing feature failure, remember that.
2682 if (Match2 == Match_MissingFeature)
2683 ErrorInfoMissingFeature = ErrorInfoIgnore;
2684 Tmp[Base.size()] = Suffixes[2];
2685 Match3 = MatchInstructionImpl(Operands, Inst, ErrorInfoIgnore,
2686 MatchingInlineAsm, isParsingIntelSyntax());
2687 // If this returned as a missing feature failure, remember that.
2688 if (Match3 == Match_MissingFeature)
2689 ErrorInfoMissingFeature = ErrorInfoIgnore;
2690 Tmp[Base.size()] = Suffixes[3];
2691 Match4 = MatchInstructionImpl(Operands, Inst, ErrorInfoIgnore,
2692 MatchingInlineAsm, isParsingIntelSyntax());
2693 // If this returned as a missing feature failure, remember that.
2694 if (Match4 == Match_MissingFeature)
2695 ErrorInfoMissingFeature = ErrorInfoIgnore;
2697 // Restore the old token.
2698 Op->setTokenValue(Base);
2700 // If exactly one matched, then we treat that as a successful match (and the
2701 // instruction will already have been filled in correctly, since the failing
2702 // matches won't have modified it).
2703 unsigned NumSuccessfulMatches =
2704 (Match1 == Match_Success) + (Match2 == Match_Success) +
2705 (Match3 == Match_Success) + (Match4 == Match_Success);
2706 if (NumSuccessfulMatches == 1) {
2708 if (!MatchingInlineAsm)
2709 Out.EmitInstruction(Inst);
2710 Opcode = Inst.getOpcode();
2714 // Otherwise, the match failed, try to produce a decent error message.
2716 // If we had multiple suffix matches, then identify this as an ambiguous
2718 if (NumSuccessfulMatches > 1) {
2720 unsigned NumMatches = 0;
2721 if (Match1 == Match_Success) MatchChars[NumMatches++] = Suffixes[0];
2722 if (Match2 == Match_Success) MatchChars[NumMatches++] = Suffixes[1];
2723 if (Match3 == Match_Success) MatchChars[NumMatches++] = Suffixes[2];
2724 if (Match4 == Match_Success) MatchChars[NumMatches++] = Suffixes[3];
2726 SmallString<126> Msg;
2727 raw_svector_ostream OS(Msg);
2728 OS << "ambiguous instructions require an explicit suffix (could be ";
2729 for (unsigned i = 0; i != NumMatches; ++i) {
2732 if (i + 1 == NumMatches)
2734 OS << "'" << Base << MatchChars[i] << "'";
2737 Error(IDLoc, OS.str(), EmptyRanges, MatchingInlineAsm);
2741 // Okay, we know that none of the variants matched successfully.
2743 // If all of the instructions reported an invalid mnemonic, then the original
2744 // mnemonic was invalid.
2745 if ((Match1 == Match_MnemonicFail) && (Match2 == Match_MnemonicFail) &&
2746 (Match3 == Match_MnemonicFail) && (Match4 == Match_MnemonicFail)) {
2747 if (!WasOriginallyInvalidOperand) {
2748 ArrayRef<SMRange> Ranges = MatchingInlineAsm ? EmptyRanges :
2750 return Error(IDLoc, "invalid instruction mnemonic '" + Base + "'",
2751 Ranges, MatchingInlineAsm);
2754 // Recover location info for the operand if we know which was the problem.
2755 if (ErrorInfo != ~0U) {
2756 if (ErrorInfo >= Operands.size())
2757 return Error(IDLoc, "too few operands for instruction",
2758 EmptyRanges, MatchingInlineAsm);
2760 X86Operand *Operand = (X86Operand*)Operands[ErrorInfo];
2761 if (Operand->getStartLoc().isValid()) {
2762 SMRange OperandRange = Operand->getLocRange();
2763 return Error(Operand->getStartLoc(), "invalid operand for instruction",
2764 OperandRange, MatchingInlineAsm);
2768 return Error(IDLoc, "invalid operand for instruction", EmptyRanges,
2772 // If one instruction matched with a missing feature, report this as a
2774 if ((Match1 == Match_MissingFeature) + (Match2 == Match_MissingFeature) +
2775 (Match3 == Match_MissingFeature) + (Match4 == Match_MissingFeature) == 1){
2776 std::string Msg = "instruction requires:";
2778 for (unsigned i = 0; i < (sizeof(ErrorInfoMissingFeature)*8-1); ++i) {
2779 if (ErrorInfoMissingFeature & Mask) {
2781 Msg += getSubtargetFeatureName(ErrorInfoMissingFeature & Mask);
2785 return Error(IDLoc, Msg, EmptyRanges, MatchingInlineAsm);
2788 // If one instruction matched with an invalid operand, report this as an
2790 if ((Match1 == Match_InvalidOperand) + (Match2 == Match_InvalidOperand) +
2791 (Match3 == Match_InvalidOperand) + (Match4 == Match_InvalidOperand) == 1){
2792 Error(IDLoc, "invalid operand for instruction", EmptyRanges,
2797 // If all of these were an outright failure, report it in a useless way.
2798 Error(IDLoc, "unknown use of instruction mnemonic without a size suffix",
2799 EmptyRanges, MatchingInlineAsm);
2804 bool X86AsmParser::ParseDirective(AsmToken DirectiveID) {
2805 StringRef IDVal = DirectiveID.getIdentifier();
2806 if (IDVal == ".word")
2807 return ParseDirectiveWord(2, DirectiveID.getLoc());
2808 else if (IDVal.startswith(".code"))
2809 return ParseDirectiveCode(IDVal, DirectiveID.getLoc());
2810 else if (IDVal.startswith(".att_syntax")) {
2811 getParser().setAssemblerDialect(0);
2813 } else if (IDVal.startswith(".intel_syntax")) {
2814 getParser().setAssemblerDialect(1);
2815 if (getLexer().isNot(AsmToken::EndOfStatement)) {
2816 // FIXME: Handle noprefix
2817 if (Parser.getTok().getString() == "noprefix")
2825 /// ParseDirectiveWord
2826 /// ::= .word [ expression (, expression)* ]
2827 bool X86AsmParser::ParseDirectiveWord(unsigned Size, SMLoc L) {
2828 if (getLexer().isNot(AsmToken::EndOfStatement)) {
2830 const MCExpr *Value;
2831 if (getParser().parseExpression(Value))
2834 getParser().getStreamer().EmitValue(Value, Size);
2836 if (getLexer().is(AsmToken::EndOfStatement))
2839 // FIXME: Improve diagnostic.
2840 if (getLexer().isNot(AsmToken::Comma)) {
2841 Error(L, "unexpected token in directive");
2852 /// ParseDirectiveCode
2853 /// ::= .code16 | .code32 | .code64
2854 bool X86AsmParser::ParseDirectiveCode(StringRef IDVal, SMLoc L) {
2855 if (IDVal == ".code16") {
2857 if (!is16BitMode()) {
2858 SwitchMode(X86::Mode16Bit);
2859 getParser().getStreamer().EmitAssemblerFlag(MCAF_Code16);
2861 } else if (IDVal == ".code32") {
2863 if (!is32BitMode()) {
2864 SwitchMode(X86::Mode32Bit);
2865 getParser().getStreamer().EmitAssemblerFlag(MCAF_Code32);
2867 } else if (IDVal == ".code64") {
2869 if (!is64BitMode()) {
2870 SwitchMode(X86::Mode64Bit);
2871 getParser().getStreamer().EmitAssemblerFlag(MCAF_Code64);
2874 Error(L, "unknown directive " + IDVal);
2881 // Force static initialization.
2882 extern "C" void LLVMInitializeX86AsmParser() {
2883 RegisterMCAsmParser<X86AsmParser> X(TheX86_32Target);
2884 RegisterMCAsmParser<X86AsmParser> Y(TheX86_64Target);
2887 #define GET_REGISTER_MATCHER
2888 #define GET_MATCHER_IMPLEMENTATION
2889 #define GET_SUBTARGET_FEATURE_NAME
2890 #include "X86GenAsmMatcher.inc"