1 //===-- X86AsmParser.cpp - Parse X86 assembly to MCInst instructions ------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #include "InstPrinter/X86IntelInstPrinter.h" 11 #include "MCTargetDesc/X86BaseInfo.h" 12 #include "MCTargetDesc/X86TargetStreamer.h" 13 #include "X86AsmInstrumentation.h" 14 #include "X86AsmParserCommon.h" 15 #include "X86Operand.h" 16 #include "llvm/ADT/STLExtras.h" 17 #include "llvm/ADT/SmallString.h" 18 #include "llvm/ADT/SmallVector.h" 19 #include "llvm/ADT/StringSwitch.h" 20 #include "llvm/ADT/Twine.h" 21 #include "llvm/MC/MCContext.h" 22 #include "llvm/MC/MCExpr.h" 23 #include "llvm/MC/MCInst.h" 24 #include "llvm/MC/MCInstrInfo.h" 25 #include "llvm/MC/MCParser/MCAsmLexer.h" 26 #include "llvm/MC/MCParser/MCAsmParser.h" 27 #include "llvm/MC/MCParser/MCParsedAsmOperand.h" 28 #include "llvm/MC/MCParser/MCTargetAsmParser.h" 29 #include "llvm/MC/MCRegisterInfo.h" 30 #include "llvm/MC/MCSection.h" 31 #include "llvm/MC/MCStreamer.h" 32 #include "llvm/MC/MCSubtargetInfo.h" 33 #include "llvm/MC/MCSymbol.h" 34 #include "llvm/Support/SourceMgr.h" 35 #include "llvm/Support/TargetRegistry.h" 36 #include "llvm/Support/raw_ostream.h" 37 #include <algorithm> 38 #include <memory> 39 40 using namespace llvm; 41 42 static bool checkScale(unsigned Scale, StringRef &ErrMsg) { 43 if (Scale != 1 && Scale != 2 && Scale != 4 && Scale != 8) { 44 ErrMsg = "scale factor in address must be 1, 2, 4 or 8"; 45 return true; 46 } 47 return false; 48 } 49 50 namespace { 51 52 static const char OpPrecedence[] = { 53 0, // IC_OR 54 1, // IC_XOR 55 2, // IC_AND 56 3, // IC_LSHIFT 57 3, // IC_RSHIFT 58 4, // IC_PLUS 59 4, // IC_MINUS 60 5, // IC_MULTIPLY 61 5, // IC_DIVIDE 62 5, // IC_MOD 63 6, // IC_NOT 64 7, // IC_NEG 65 8, // IC_RPAREN 66 9, // IC_LPAREN 67 0, // IC_IMM 68 0 // IC_REGISTER 69 }; 70 71 class X86AsmParser : public MCTargetAsmParser { 72 ParseInstructionInfo *InstInfo; 73 std::unique_ptr<X86AsmInstrumentation> Instrumentation; 74 bool Code16GCC; 75 76 private: 77 SMLoc consumeToken() { 78 MCAsmParser &Parser = getParser(); 79 SMLoc Result = Parser.getTok().getLoc(); 80 Parser.Lex(); 81 return Result; 82 } 83 84 X86TargetStreamer &getTargetStreamer() { 85 assert(getParser().getStreamer().getTargetStreamer() && 86 "do not have a target streamer"); 87 MCTargetStreamer &TS = *getParser().getStreamer().getTargetStreamer(); 88 return static_cast<X86TargetStreamer &>(TS); 89 } 90 91 unsigned MatchInstruction(const OperandVector &Operands, MCInst &Inst, 92 uint64_t &ErrorInfo, bool matchingInlineAsm, 93 unsigned VariantID = 0) { 94 // In Code16GCC mode, match as 32-bit. 95 if (Code16GCC) 96 SwitchMode(X86::Mode32Bit); 97 unsigned rv = MatchInstructionImpl(Operands, Inst, ErrorInfo, 98 matchingInlineAsm, VariantID); 99 if (Code16GCC) 100 SwitchMode(X86::Mode16Bit); 101 return rv; 102 } 103 104 enum InfixCalculatorTok { 105 IC_OR = 0, 106 IC_XOR, 107 IC_AND, 108 IC_LSHIFT, 109 IC_RSHIFT, 110 IC_PLUS, 111 IC_MINUS, 112 IC_MULTIPLY, 113 IC_DIVIDE, 114 IC_MOD, 115 IC_NOT, 116 IC_NEG, 117 IC_RPAREN, 118 IC_LPAREN, 119 IC_IMM, 120 IC_REGISTER 121 }; 122 123 enum IntelOperatorKind { 124 IOK_INVALID = 0, 125 IOK_LENGTH, 126 IOK_SIZE, 127 IOK_TYPE, 128 IOK_OFFSET 129 }; 130 131 class InfixCalculator { 132 typedef std::pair< InfixCalculatorTok, int64_t > ICToken; 133 SmallVector<InfixCalculatorTok, 4> InfixOperatorStack; 134 SmallVector<ICToken, 4> PostfixStack; 135 136 bool isUnaryOperator(const InfixCalculatorTok Op) { 137 return Op == IC_NEG || Op == IC_NOT; 138 } 139 140 public: 141 int64_t popOperand() { 142 assert (!PostfixStack.empty() && "Poped an empty stack!"); 143 ICToken Op = PostfixStack.pop_back_val(); 144 if (!(Op.first == IC_IMM || Op.first == IC_REGISTER)) 145 return -1; // The invalid Scale value will be caught later by checkScale 146 return Op.second; 147 } 148 void pushOperand(InfixCalculatorTok Op, int64_t Val = 0) { 149 assert ((Op == IC_IMM || Op == IC_REGISTER) && 150 "Unexpected operand!"); 151 PostfixStack.push_back(std::make_pair(Op, Val)); 152 } 153 154 void popOperator() { InfixOperatorStack.pop_back(); } 155 void pushOperator(InfixCalculatorTok Op) { 156 // Push the new operator if the stack is empty. 157 if (InfixOperatorStack.empty()) { 158 InfixOperatorStack.push_back(Op); 159 return; 160 } 161 162 // Push the new operator if it has a higher precedence than the operator 163 // on the top of the stack or the operator on the top of the stack is a 164 // left parentheses. 165 unsigned Idx = InfixOperatorStack.size() - 1; 166 InfixCalculatorTok StackOp = InfixOperatorStack[Idx]; 167 if (OpPrecedence[Op] > OpPrecedence[StackOp] || StackOp == IC_LPAREN) { 168 InfixOperatorStack.push_back(Op); 169 return; 170 } 171 172 // The operator on the top of the stack has higher precedence than the 173 // new operator. 174 unsigned ParenCount = 0; 175 while (1) { 176 // Nothing to process. 177 if (InfixOperatorStack.empty()) 178 break; 179 180 Idx = InfixOperatorStack.size() - 1; 181 StackOp = InfixOperatorStack[Idx]; 182 if (!(OpPrecedence[StackOp] >= OpPrecedence[Op] || ParenCount)) 183 break; 184 185 // If we have an even parentheses count and we see a left parentheses, 186 // then stop processing. 187 if (!ParenCount && StackOp == IC_LPAREN) 188 break; 189 190 if (StackOp == IC_RPAREN) { 191 ++ParenCount; 192 InfixOperatorStack.pop_back(); 193 } else if (StackOp == IC_LPAREN) { 194 --ParenCount; 195 InfixOperatorStack.pop_back(); 196 } else { 197 InfixOperatorStack.pop_back(); 198 PostfixStack.push_back(std::make_pair(StackOp, 0)); 199 } 200 } 201 // Push the new operator. 202 InfixOperatorStack.push_back(Op); 203 } 204 205 int64_t execute() { 206 // Push any remaining operators onto the postfix stack. 207 while (!InfixOperatorStack.empty()) { 208 InfixCalculatorTok StackOp = InfixOperatorStack.pop_back_val(); 209 if (StackOp != IC_LPAREN && StackOp != IC_RPAREN) 210 PostfixStack.push_back(std::make_pair(StackOp, 0)); 211 } 212 213 if (PostfixStack.empty()) 214 return 0; 215 216 SmallVector<ICToken, 16> OperandStack; 217 for (unsigned i = 0, e = PostfixStack.size(); i != e; ++i) { 218 ICToken Op = PostfixStack[i]; 219 if (Op.first == IC_IMM || Op.first == IC_REGISTER) { 220 OperandStack.push_back(Op); 221 } else if (isUnaryOperator(Op.first)) { 222 assert (OperandStack.size() > 0 && "Too few operands."); 223 ICToken Operand = OperandStack.pop_back_val(); 224 assert (Operand.first == IC_IMM && 225 "Unary operation with a register!"); 226 switch (Op.first) { 227 default: 228 report_fatal_error("Unexpected operator!"); 229 break; 230 case IC_NEG: 231 OperandStack.push_back(std::make_pair(IC_IMM, -Operand.second)); 232 break; 233 case IC_NOT: 234 OperandStack.push_back(std::make_pair(IC_IMM, ~Operand.second)); 235 break; 236 } 237 } else { 238 assert (OperandStack.size() > 1 && "Too few operands."); 239 int64_t Val; 240 ICToken Op2 = OperandStack.pop_back_val(); 241 ICToken Op1 = OperandStack.pop_back_val(); 242 switch (Op.first) { 243 default: 244 report_fatal_error("Unexpected operator!"); 245 break; 246 case IC_PLUS: 247 Val = Op1.second + Op2.second; 248 OperandStack.push_back(std::make_pair(IC_IMM, Val)); 249 break; 250 case IC_MINUS: 251 Val = Op1.second - Op2.second; 252 OperandStack.push_back(std::make_pair(IC_IMM, Val)); 253 break; 254 case IC_MULTIPLY: 255 assert (Op1.first == IC_IMM && Op2.first == IC_IMM && 256 "Multiply operation with an immediate and a register!"); 257 Val = Op1.second * Op2.second; 258 OperandStack.push_back(std::make_pair(IC_IMM, Val)); 259 break; 260 case IC_DIVIDE: 261 assert (Op1.first == IC_IMM && Op2.first == IC_IMM && 262 "Divide operation with an immediate and a register!"); 263 assert (Op2.second != 0 && "Division by zero!"); 264 Val = Op1.second / Op2.second; 265 OperandStack.push_back(std::make_pair(IC_IMM, Val)); 266 break; 267 case IC_MOD: 268 assert (Op1.first == IC_IMM && Op2.first == IC_IMM && 269 "Modulo operation with an immediate and a register!"); 270 Val = Op1.second % Op2.second; 271 OperandStack.push_back(std::make_pair(IC_IMM, Val)); 272 break; 273 case IC_OR: 274 assert (Op1.first == IC_IMM && Op2.first == IC_IMM && 275 "Or operation with an immediate and a register!"); 276 Val = Op1.second | Op2.second; 277 OperandStack.push_back(std::make_pair(IC_IMM, Val)); 278 break; 279 case IC_XOR: 280 assert(Op1.first == IC_IMM && Op2.first == IC_IMM && 281 "Xor operation with an immediate and a register!"); 282 Val = Op1.second ^ Op2.second; 283 OperandStack.push_back(std::make_pair(IC_IMM, Val)); 284 break; 285 case IC_AND: 286 assert (Op1.first == IC_IMM && Op2.first == IC_IMM && 287 "And operation with an immediate and a register!"); 288 Val = Op1.second & Op2.second; 289 OperandStack.push_back(std::make_pair(IC_IMM, Val)); 290 break; 291 case IC_LSHIFT: 292 assert (Op1.first == IC_IMM && Op2.first == IC_IMM && 293 "Left shift operation with an immediate and a register!"); 294 Val = Op1.second << Op2.second; 295 OperandStack.push_back(std::make_pair(IC_IMM, Val)); 296 break; 297 case IC_RSHIFT: 298 assert (Op1.first == IC_IMM && Op2.first == IC_IMM && 299 "Right shift operation with an immediate and a register!"); 300 Val = Op1.second >> Op2.second; 301 OperandStack.push_back(std::make_pair(IC_IMM, Val)); 302 break; 303 } 304 } 305 } 306 assert (OperandStack.size() == 1 && "Expected a single result."); 307 return OperandStack.pop_back_val().second; 308 } 309 }; 310 311 enum IntelExprState { 312 IES_INIT, 313 IES_OR, 314 IES_XOR, 315 IES_AND, 316 IES_LSHIFT, 317 IES_RSHIFT, 318 IES_PLUS, 319 IES_MINUS, 320 IES_NOT, 321 IES_MULTIPLY, 322 IES_DIVIDE, 323 IES_MOD, 324 IES_LBRAC, 325 IES_RBRAC, 326 IES_LPAREN, 327 IES_RPAREN, 328 IES_REGISTER, 329 IES_INTEGER, 330 IES_IDENTIFIER, 331 IES_ERROR 332 }; 333 334 class IntelExprStateMachine { 335 IntelExprState State, PrevState; 336 unsigned BaseReg, IndexReg, TmpReg, Scale; 337 int64_t Imm; 338 const MCExpr *Sym; 339 StringRef SymName; 340 InfixCalculator IC; 341 InlineAsmIdentifierInfo Info; 342 short BracCount; 343 bool MemExpr; 344 345 public: 346 IntelExprStateMachine() 347 : State(IES_INIT), PrevState(IES_ERROR), BaseReg(0), IndexReg(0), 348 TmpReg(0), Scale(1), Imm(0), Sym(nullptr), BracCount(0), 349 MemExpr(false) {} 350 351 void addImm(int64_t imm) { Imm += imm; } 352 short getBracCount() { return BracCount; } 353 bool isMemExpr() { return MemExpr; } 354 unsigned getBaseReg() { return BaseReg; } 355 unsigned getIndexReg() { return IndexReg; } 356 unsigned getScale() { return Scale; } 357 const MCExpr *getSym() { return Sym; } 358 StringRef getSymName() { return SymName; } 359 int64_t getImm() { return Imm + IC.execute(); } 360 bool isValidEndState() { 361 return State == IES_RBRAC || State == IES_INTEGER; 362 } 363 bool hadError() { return State == IES_ERROR; } 364 InlineAsmIdentifierInfo &getIdentifierInfo() { return Info; } 365 366 void onOr() { 367 IntelExprState CurrState = State; 368 switch (State) { 369 default: 370 State = IES_ERROR; 371 break; 372 case IES_INTEGER: 373 case IES_RPAREN: 374 case IES_REGISTER: 375 State = IES_OR; 376 IC.pushOperator(IC_OR); 377 break; 378 } 379 PrevState = CurrState; 380 } 381 void onXor() { 382 IntelExprState CurrState = State; 383 switch (State) { 384 default: 385 State = IES_ERROR; 386 break; 387 case IES_INTEGER: 388 case IES_RPAREN: 389 case IES_REGISTER: 390 State = IES_XOR; 391 IC.pushOperator(IC_XOR); 392 break; 393 } 394 PrevState = CurrState; 395 } 396 void onAnd() { 397 IntelExprState CurrState = State; 398 switch (State) { 399 default: 400 State = IES_ERROR; 401 break; 402 case IES_INTEGER: 403 case IES_RPAREN: 404 case IES_REGISTER: 405 State = IES_AND; 406 IC.pushOperator(IC_AND); 407 break; 408 } 409 PrevState = CurrState; 410 } 411 void onLShift() { 412 IntelExprState CurrState = State; 413 switch (State) { 414 default: 415 State = IES_ERROR; 416 break; 417 case IES_INTEGER: 418 case IES_RPAREN: 419 case IES_REGISTER: 420 State = IES_LSHIFT; 421 IC.pushOperator(IC_LSHIFT); 422 break; 423 } 424 PrevState = CurrState; 425 } 426 void onRShift() { 427 IntelExprState CurrState = State; 428 switch (State) { 429 default: 430 State = IES_ERROR; 431 break; 432 case IES_INTEGER: 433 case IES_RPAREN: 434 case IES_REGISTER: 435 State = IES_RSHIFT; 436 IC.pushOperator(IC_RSHIFT); 437 break; 438 } 439 PrevState = CurrState; 440 } 441 bool onPlus(StringRef &ErrMsg) { 442 IntelExprState CurrState = State; 443 switch (State) { 444 default: 445 State = IES_ERROR; 446 break; 447 case IES_INTEGER: 448 case IES_RPAREN: 449 case IES_REGISTER: 450 State = IES_PLUS; 451 IC.pushOperator(IC_PLUS); 452 if (CurrState == IES_REGISTER && PrevState != IES_MULTIPLY) { 453 // If we already have a BaseReg, then assume this is the IndexReg with 454 // a scale of 1. 455 if (!BaseReg) { 456 BaseReg = TmpReg; 457 } else { 458 if (IndexReg) { 459 ErrMsg = "BaseReg/IndexReg already set!"; 460 return true; 461 } 462 IndexReg = TmpReg; 463 Scale = 1; 464 } 465 } 466 break; 467 } 468 PrevState = CurrState; 469 return false; 470 } 471 bool onMinus(StringRef &ErrMsg) { 472 IntelExprState CurrState = State; 473 switch (State) { 474 default: 475 State = IES_ERROR; 476 break; 477 case IES_OR: 478 case IES_XOR: 479 case IES_AND: 480 case IES_LSHIFT: 481 case IES_RSHIFT: 482 case IES_PLUS: 483 case IES_NOT: 484 case IES_MULTIPLY: 485 case IES_DIVIDE: 486 case IES_MOD: 487 case IES_LPAREN: 488 case IES_RPAREN: 489 case IES_LBRAC: 490 case IES_RBRAC: 491 case IES_INTEGER: 492 case IES_REGISTER: 493 case IES_INIT: 494 State = IES_MINUS; 495 // push minus operator if it is not a negate operator 496 if (CurrState == IES_REGISTER || CurrState == IES_RPAREN || 497 CurrState == IES_INTEGER || CurrState == IES_RBRAC) 498 IC.pushOperator(IC_MINUS); 499 else if (PrevState == IES_REGISTER && CurrState == IES_MULTIPLY) { 500 // We have negate operator for Scale: it's illegal 501 ErrMsg = "Scale can't be negative"; 502 return true; 503 } else 504 IC.pushOperator(IC_NEG); 505 if (CurrState == IES_REGISTER && PrevState != IES_MULTIPLY) { 506 // If we already have a BaseReg, then assume this is the IndexReg with 507 // a scale of 1. 508 if (!BaseReg) { 509 BaseReg = TmpReg; 510 } else { 511 if (IndexReg) { 512 ErrMsg = "BaseReg/IndexReg already set!"; 513 return true; 514 } 515 IndexReg = TmpReg; 516 Scale = 1; 517 } 518 } 519 break; 520 } 521 PrevState = CurrState; 522 return false; 523 } 524 void onNot() { 525 IntelExprState CurrState = State; 526 switch (State) { 527 default: 528 State = IES_ERROR; 529 break; 530 case IES_OR: 531 case IES_XOR: 532 case IES_AND: 533 case IES_LSHIFT: 534 case IES_RSHIFT: 535 case IES_PLUS: 536 case IES_MINUS: 537 case IES_NOT: 538 case IES_MULTIPLY: 539 case IES_DIVIDE: 540 case IES_MOD: 541 case IES_LPAREN: 542 case IES_LBRAC: 543 case IES_INIT: 544 State = IES_NOT; 545 IC.pushOperator(IC_NOT); 546 break; 547 } 548 PrevState = CurrState; 549 } 550 551 bool onRegister(unsigned Reg, StringRef &ErrMsg) { 552 IntelExprState CurrState = State; 553 switch (State) { 554 default: 555 State = IES_ERROR; 556 break; 557 case IES_PLUS: 558 case IES_LPAREN: 559 case IES_LBRAC: 560 State = IES_REGISTER; 561 TmpReg = Reg; 562 IC.pushOperand(IC_REGISTER); 563 break; 564 case IES_MULTIPLY: 565 // Index Register - Scale * Register 566 if (PrevState == IES_INTEGER) { 567 if (IndexReg) { 568 ErrMsg = "BaseReg/IndexReg already set!"; 569 return true; 570 } 571 State = IES_REGISTER; 572 IndexReg = Reg; 573 // Get the scale and replace the 'Scale * Register' with '0'. 574 Scale = IC.popOperand(); 575 if (checkScale(Scale, ErrMsg)) 576 return true; 577 IC.pushOperand(IC_IMM); 578 IC.popOperator(); 579 } else { 580 State = IES_ERROR; 581 } 582 break; 583 } 584 PrevState = CurrState; 585 return false; 586 } 587 bool onIdentifierExpr(const MCExpr *SymRef, StringRef SymRefName, 588 const InlineAsmIdentifierInfo &IDInfo, 589 bool ParsingInlineAsm, StringRef &ErrMsg) { 590 // InlineAsm: Treat an enum value as an integer 591 if (ParsingInlineAsm) 592 if (IDInfo.isKind(InlineAsmIdentifierInfo::IK_EnumVal)) 593 return onInteger(IDInfo.Enum.EnumVal, ErrMsg); 594 // Treat a symbolic constant like an integer 595 if (auto *CE = dyn_cast<MCConstantExpr>(SymRef)) 596 return onInteger(CE->getValue(), ErrMsg); 597 PrevState = State; 598 bool HasSymbol = Sym != nullptr; 599 switch (State) { 600 default: 601 State = IES_ERROR; 602 break; 603 case IES_PLUS: 604 case IES_MINUS: 605 case IES_NOT: 606 case IES_INIT: 607 case IES_LBRAC: 608 MemExpr = true; 609 State = IES_INTEGER; 610 Sym = SymRef; 611 SymName = SymRefName; 612 IC.pushOperand(IC_IMM); 613 if (ParsingInlineAsm) 614 Info = IDInfo; 615 break; 616 } 617 if (HasSymbol) 618 ErrMsg = "cannot use more than one symbol in memory operand"; 619 return HasSymbol; 620 } 621 bool onInteger(int64_t TmpInt, StringRef &ErrMsg) { 622 IntelExprState CurrState = State; 623 switch (State) { 624 default: 625 State = IES_ERROR; 626 break; 627 case IES_PLUS: 628 case IES_MINUS: 629 case IES_NOT: 630 case IES_OR: 631 case IES_XOR: 632 case IES_AND: 633 case IES_LSHIFT: 634 case IES_RSHIFT: 635 case IES_DIVIDE: 636 case IES_MOD: 637 case IES_MULTIPLY: 638 case IES_LPAREN: 639 case IES_INIT: 640 case IES_LBRAC: 641 State = IES_INTEGER; 642 if (PrevState == IES_REGISTER && CurrState == IES_MULTIPLY) { 643 // Index Register - Register * Scale 644 if (IndexReg) { 645 ErrMsg = "BaseReg/IndexReg already set!"; 646 return true; 647 } 648 IndexReg = TmpReg; 649 Scale = TmpInt; 650 if (checkScale(Scale, ErrMsg)) 651 return true; 652 // Get the scale and replace the 'Register * Scale' with '0'. 653 IC.popOperator(); 654 } else { 655 IC.pushOperand(IC_IMM, TmpInt); 656 } 657 break; 658 } 659 PrevState = CurrState; 660 return false; 661 } 662 void onStar() { 663 PrevState = State; 664 switch (State) { 665 default: 666 State = IES_ERROR; 667 break; 668 case IES_INTEGER: 669 case IES_REGISTER: 670 case IES_RPAREN: 671 State = IES_MULTIPLY; 672 IC.pushOperator(IC_MULTIPLY); 673 break; 674 } 675 } 676 void onDivide() { 677 PrevState = State; 678 switch (State) { 679 default: 680 State = IES_ERROR; 681 break; 682 case IES_INTEGER: 683 case IES_RPAREN: 684 State = IES_DIVIDE; 685 IC.pushOperator(IC_DIVIDE); 686 break; 687 } 688 } 689 void onMod() { 690 PrevState = State; 691 switch (State) { 692 default: 693 State = IES_ERROR; 694 break; 695 case IES_INTEGER: 696 case IES_RPAREN: 697 State = IES_MOD; 698 IC.pushOperator(IC_MOD); 699 break; 700 } 701 } 702 bool onLBrac() { 703 if (BracCount) 704 return true; 705 PrevState = State; 706 switch (State) { 707 default: 708 State = IES_ERROR; 709 break; 710 case IES_RBRAC: 711 case IES_INTEGER: 712 case IES_RPAREN: 713 State = IES_PLUS; 714 IC.pushOperator(IC_PLUS); 715 break; 716 case IES_INIT: 717 assert(!BracCount && "BracCount should be zero on parsing's start"); 718 State = IES_LBRAC; 719 break; 720 } 721 MemExpr = true; 722 BracCount++; 723 return false; 724 } 725 bool onRBrac() { 726 IntelExprState CurrState = State; 727 switch (State) { 728 default: 729 State = IES_ERROR; 730 break; 731 case IES_INTEGER: 732 case IES_REGISTER: 733 case IES_RPAREN: 734 if (BracCount-- != 1) 735 return true; 736 State = IES_RBRAC; 737 if (CurrState == IES_REGISTER && PrevState != IES_MULTIPLY) { 738 // If we already have a BaseReg, then assume this is the IndexReg with 739 // a scale of 1. 740 if (!BaseReg) { 741 BaseReg = TmpReg; 742 } else { 743 assert (!IndexReg && "BaseReg/IndexReg already set!"); 744 IndexReg = TmpReg; 745 Scale = 1; 746 } 747 } 748 break; 749 } 750 PrevState = CurrState; 751 return false; 752 } 753 void onLParen() { 754 IntelExprState CurrState = State; 755 switch (State) { 756 default: 757 State = IES_ERROR; 758 break; 759 case IES_PLUS: 760 case IES_MINUS: 761 case IES_NOT: 762 case IES_OR: 763 case IES_XOR: 764 case IES_AND: 765 case IES_LSHIFT: 766 case IES_RSHIFT: 767 case IES_MULTIPLY: 768 case IES_DIVIDE: 769 case IES_MOD: 770 case IES_LPAREN: 771 case IES_INIT: 772 case IES_LBRAC: 773 State = IES_LPAREN; 774 IC.pushOperator(IC_LPAREN); 775 break; 776 } 777 PrevState = CurrState; 778 } 779 void onRParen() { 780 PrevState = State; 781 switch (State) { 782 default: 783 State = IES_ERROR; 784 break; 785 case IES_INTEGER: 786 case IES_REGISTER: 787 case IES_RPAREN: 788 State = IES_RPAREN; 789 IC.pushOperator(IC_RPAREN); 790 break; 791 } 792 } 793 }; 794 795 bool Error(SMLoc L, const Twine &Msg, SMRange Range = None, 796 bool MatchingInlineAsm = false) { 797 MCAsmParser &Parser = getParser(); 798 if (MatchingInlineAsm) { 799 if (!getLexer().isAtStartOfStatement()) 800 Parser.eatToEndOfStatement(); 801 return false; 802 } 803 return Parser.Error(L, Msg, Range); 804 } 805 806 std::nullptr_t ErrorOperand(SMLoc Loc, StringRef Msg) { 807 Error(Loc, Msg); 808 return nullptr; 809 } 810 811 std::unique_ptr<X86Operand> DefaultMemSIOperand(SMLoc Loc); 812 std::unique_ptr<X86Operand> DefaultMemDIOperand(SMLoc Loc); 813 bool IsSIReg(unsigned Reg); 814 unsigned GetSIDIForRegClass(unsigned RegClassID, unsigned Reg, bool IsSIReg); 815 void 816 AddDefaultSrcDestOperands(OperandVector &Operands, 817 std::unique_ptr<llvm::MCParsedAsmOperand> &&Src, 818 std::unique_ptr<llvm::MCParsedAsmOperand> &&Dst); 819 bool VerifyAndAdjustOperands(OperandVector &OrigOperands, 820 OperandVector &FinalOperands); 821 std::unique_ptr<X86Operand> ParseOperand(); 822 std::unique_ptr<X86Operand> ParseATTOperand(); 823 std::unique_ptr<X86Operand> ParseIntelOperand(); 824 std::unique_ptr<X86Operand> ParseIntelOffsetOfOperator(); 825 bool ParseIntelDotOperator(IntelExprStateMachine &SM, SMLoc &End); 826 unsigned IdentifyIntelInlineAsmOperator(StringRef Name); 827 unsigned ParseIntelInlineAsmOperator(unsigned OpKind); 828 std::unique_ptr<X86Operand> ParseRoundingModeOp(SMLoc Start, SMLoc End); 829 bool ParseIntelNamedOperator(StringRef Name, IntelExprStateMachine &SM); 830 void RewriteIntelExpression(IntelExprStateMachine &SM, SMLoc Start, 831 SMLoc End); 832 bool ParseIntelExpression(IntelExprStateMachine &SM, SMLoc &End); 833 bool ParseIntelInlineAsmIdentifier(const MCExpr *&Val, StringRef &Identifier, 834 InlineAsmIdentifierInfo &Info, 835 bool IsUnevaluatedOperand, SMLoc &End); 836 837 std::unique_ptr<X86Operand> ParseMemOperand(unsigned SegReg, SMLoc StartLoc); 838 839 bool ParseIntelMemoryOperandSize(unsigned &Size); 840 std::unique_ptr<X86Operand> 841 CreateMemForInlineAsm(unsigned SegReg, const MCExpr *Disp, unsigned BaseReg, 842 unsigned IndexReg, unsigned Scale, SMLoc Start, 843 SMLoc End, unsigned Size, StringRef Identifier, 844 const InlineAsmIdentifierInfo &Info); 845 846 bool parseDirectiveEven(SMLoc L); 847 bool ParseDirectiveWord(unsigned Size, SMLoc L); 848 bool ParseDirectiveCode(StringRef IDVal, SMLoc L); 849 850 /// CodeView FPO data directives. 851 bool parseDirectiveFPOProc(SMLoc L); 852 bool parseDirectiveFPOSetFrame(SMLoc L); 853 bool parseDirectiveFPOPushReg(SMLoc L); 854 bool parseDirectiveFPOStackAlloc(SMLoc L); 855 bool parseDirectiveFPOEndPrologue(SMLoc L); 856 bool parseDirectiveFPOEndProc(SMLoc L); 857 bool parseDirectiveFPOData(SMLoc L); 858 859 bool processInstruction(MCInst &Inst, const OperandVector &Ops); 860 861 /// Wrapper around MCStreamer::EmitInstruction(). Possibly adds 862 /// instrumentation around Inst. 863 void EmitInstruction(MCInst &Inst, OperandVector &Operands, MCStreamer &Out); 864 865 bool MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode, 866 OperandVector &Operands, MCStreamer &Out, 867 uint64_t &ErrorInfo, 868 bool MatchingInlineAsm) override; 869 870 void MatchFPUWaitAlias(SMLoc IDLoc, X86Operand &Op, OperandVector &Operands, 871 MCStreamer &Out, bool MatchingInlineAsm); 872 873 bool ErrorMissingFeature(SMLoc IDLoc, uint64_t ErrorInfo, 874 bool MatchingInlineAsm); 875 876 bool MatchAndEmitATTInstruction(SMLoc IDLoc, unsigned &Opcode, 877 OperandVector &Operands, MCStreamer &Out, 878 uint64_t &ErrorInfo, 879 bool MatchingInlineAsm); 880 881 bool MatchAndEmitIntelInstruction(SMLoc IDLoc, unsigned &Opcode, 882 OperandVector &Operands, MCStreamer &Out, 883 uint64_t &ErrorInfo, 884 bool MatchingInlineAsm); 885 886 bool OmitRegisterFromClobberLists(unsigned RegNo) override; 887 888 /// Parses AVX512 specific operand primitives: masked registers ({%k<NUM>}, {z}) 889 /// and memory broadcasting ({1to<NUM>}) primitives, updating Operands vector if required. 890 /// return false if no parsing errors occurred, true otherwise. 891 bool HandleAVX512Operand(OperandVector &Operands, 892 const MCParsedAsmOperand &Op); 893 894 bool ParseZ(std::unique_ptr<X86Operand> &Z, const SMLoc &StartLoc); 895 896 bool is64BitMode() const { 897 // FIXME: Can tablegen auto-generate this? 898 return getSTI().getFeatureBits()[X86::Mode64Bit]; 899 } 900 bool is32BitMode() const { 901 // FIXME: Can tablegen auto-generate this? 902 return getSTI().getFeatureBits()[X86::Mode32Bit]; 903 } 904 bool is16BitMode() const { 905 // FIXME: Can tablegen auto-generate this? 906 return getSTI().getFeatureBits()[X86::Mode16Bit]; 907 } 908 void SwitchMode(unsigned mode) { 909 MCSubtargetInfo &STI = copySTI(); 910 FeatureBitset AllModes({X86::Mode64Bit, X86::Mode32Bit, X86::Mode16Bit}); 911 FeatureBitset OldMode = STI.getFeatureBits() & AllModes; 912 unsigned FB = ComputeAvailableFeatures( 913 STI.ToggleFeature(OldMode.flip(mode))); 914 setAvailableFeatures(FB); 915 916 assert(FeatureBitset({mode}) == (STI.getFeatureBits() & AllModes)); 917 } 918 919 unsigned getPointerWidth() { 920 if (is16BitMode()) return 16; 921 if (is32BitMode()) return 32; 922 if (is64BitMode()) return 64; 923 llvm_unreachable("invalid mode"); 924 } 925 926 bool isParsingIntelSyntax() { 927 return getParser().getAssemblerDialect(); 928 } 929 930 /// @name Auto-generated Matcher Functions 931 /// { 932 933 #define GET_ASSEMBLER_HEADER 934 #include "X86GenAsmMatcher.inc" 935 936 /// } 937 938 public: 939 940 X86AsmParser(const MCSubtargetInfo &sti, MCAsmParser &Parser, 941 const MCInstrInfo &mii, const MCTargetOptions &Options) 942 : MCTargetAsmParser(Options, sti, mii), InstInfo(nullptr), 943 Code16GCC(false) { 944 945 // Initialize the set of available features. 946 setAvailableFeatures(ComputeAvailableFeatures(getSTI().getFeatureBits())); 947 Instrumentation.reset( 948 CreateX86AsmInstrumentation(Options, Parser.getContext(), STI)); 949 } 950 951 bool ParseRegister(unsigned &RegNo, SMLoc &StartLoc, SMLoc &EndLoc) override; 952 953 void SetFrameRegister(unsigned RegNo) override; 954 955 bool ParseInstruction(ParseInstructionInfo &Info, StringRef Name, 956 SMLoc NameLoc, OperandVector &Operands) override; 957 958 bool ParseDirective(AsmToken DirectiveID) override; 959 }; 960 } // end anonymous namespace 961 962 /// @name Auto-generated Match Functions 963 /// { 964 965 static unsigned MatchRegisterName(StringRef Name); 966 967 /// } 968 969 static bool CheckBaseRegAndIndexRegAndScale(unsigned BaseReg, unsigned IndexReg, 970 unsigned Scale, StringRef &ErrMsg) { 971 // If we have both a base register and an index register make sure they are 972 // both 64-bit or 32-bit registers. 973 // To support VSIB, IndexReg can be 128-bit or 256-bit registers. 974 975 if ((BaseReg == X86::RIP && IndexReg != 0) || (IndexReg == X86::RIP)) { 976 ErrMsg = "invalid base+index expression"; 977 return true; 978 } 979 if (BaseReg != 0 && IndexReg != 0) { 980 if (X86MCRegisterClasses[X86::GR64RegClassID].contains(BaseReg) && 981 (X86MCRegisterClasses[X86::GR16RegClassID].contains(IndexReg) || 982 X86MCRegisterClasses[X86::GR32RegClassID].contains(IndexReg)) && 983 IndexReg != X86::RIZ) { 984 ErrMsg = "base register is 64-bit, but index register is not"; 985 return true; 986 } 987 if (X86MCRegisterClasses[X86::GR32RegClassID].contains(BaseReg) && 988 (X86MCRegisterClasses[X86::GR16RegClassID].contains(IndexReg) || 989 X86MCRegisterClasses[X86::GR64RegClassID].contains(IndexReg)) && 990 IndexReg != X86::EIZ){ 991 ErrMsg = "base register is 32-bit, but index register is not"; 992 return true; 993 } 994 if (X86MCRegisterClasses[X86::GR16RegClassID].contains(BaseReg)) { 995 if (X86MCRegisterClasses[X86::GR32RegClassID].contains(IndexReg) || 996 X86MCRegisterClasses[X86::GR64RegClassID].contains(IndexReg)) { 997 ErrMsg = "base register is 16-bit, but index register is not"; 998 return true; 999 } 1000 if (((BaseReg == X86::BX || BaseReg == X86::BP) && 1001 IndexReg != X86::SI && IndexReg != X86::DI) || 1002 ((BaseReg == X86::SI || BaseReg == X86::DI) && 1003 IndexReg != X86::BX && IndexReg != X86::BP)) { 1004 ErrMsg = "invalid 16-bit base/index register combination"; 1005 return true; 1006 } 1007 } 1008 } 1009 return checkScale(Scale, ErrMsg); 1010 } 1011 1012 bool X86AsmParser::ParseRegister(unsigned &RegNo, 1013 SMLoc &StartLoc, SMLoc &EndLoc) { 1014 MCAsmParser &Parser = getParser(); 1015 RegNo = 0; 1016 const AsmToken &PercentTok = Parser.getTok(); 1017 StartLoc = PercentTok.getLoc(); 1018 1019 // If we encounter a %, ignore it. This code handles registers with and 1020 // without the prefix, unprefixed registers can occur in cfi directives. 1021 if (!isParsingIntelSyntax() && PercentTok.is(AsmToken::Percent)) 1022 Parser.Lex(); // Eat percent token. 1023 1024 const AsmToken &Tok = Parser.getTok(); 1025 EndLoc = Tok.getEndLoc(); 1026 1027 if (Tok.isNot(AsmToken::Identifier)) { 1028 if (isParsingIntelSyntax()) return true; 1029 return Error(StartLoc, "invalid register name", 1030 SMRange(StartLoc, EndLoc)); 1031 } 1032 1033 RegNo = MatchRegisterName(Tok.getString()); 1034 1035 // If the match failed, try the register name as lowercase. 1036 if (RegNo == 0) 1037 RegNo = MatchRegisterName(Tok.getString().lower()); 1038 1039 // The "flags" register cannot be referenced directly. 1040 // Treat it as an identifier instead. 1041 if (isParsingInlineAsm() && isParsingIntelSyntax() && RegNo == X86::EFLAGS) 1042 RegNo = 0; 1043 1044 if (!is64BitMode()) { 1045 // FIXME: This should be done using Requires<Not64BitMode> and 1046 // Requires<In64BitMode> so "eiz" usage in 64-bit instructions can be also 1047 // checked. 1048 // FIXME: Check AH, CH, DH, BH cannot be used in an instruction requiring a 1049 // REX prefix. 1050 if (RegNo == X86::RIZ || 1051 X86MCRegisterClasses[X86::GR64RegClassID].contains(RegNo) || 1052 X86II::isX86_64NonExtLowByteReg(RegNo) || 1053 X86II::isX86_64ExtendedReg(RegNo)) 1054 return Error(StartLoc, "register %" 1055 + Tok.getString() + " is only available in 64-bit mode", 1056 SMRange(StartLoc, EndLoc)); 1057 } else if (!getSTI().getFeatureBits()[X86::FeatureAVX512]) { 1058 if (X86II::is32ExtendedReg(RegNo)) 1059 return Error(StartLoc, "register %" 1060 + Tok.getString() + " is only available with AVX512", 1061 SMRange(StartLoc, EndLoc)); 1062 } 1063 1064 // Parse "%st" as "%st(0)" and "%st(1)", which is multiple tokens. 1065 if (RegNo == 0 && (Tok.getString() == "st" || Tok.getString() == "ST")) { 1066 RegNo = X86::ST0; 1067 Parser.Lex(); // Eat 'st' 1068 1069 // Check to see if we have '(4)' after %st. 1070 if (getLexer().isNot(AsmToken::LParen)) 1071 return false; 1072 // Lex the paren. 1073 getParser().Lex(); 1074 1075 const AsmToken &IntTok = Parser.getTok(); 1076 if (IntTok.isNot(AsmToken::Integer)) 1077 return Error(IntTok.getLoc(), "expected stack index"); 1078 switch (IntTok.getIntVal()) { 1079 case 0: RegNo = X86::ST0; break; 1080 case 1: RegNo = X86::ST1; break; 1081 case 2: RegNo = X86::ST2; break; 1082 case 3: RegNo = X86::ST3; break; 1083 case 4: RegNo = X86::ST4; break; 1084 case 5: RegNo = X86::ST5; break; 1085 case 6: RegNo = X86::ST6; break; 1086 case 7: RegNo = X86::ST7; break; 1087 default: return Error(IntTok.getLoc(), "invalid stack index"); 1088 } 1089 1090 if (getParser().Lex().isNot(AsmToken::RParen)) 1091 return Error(Parser.getTok().getLoc(), "expected ')'"); 1092 1093 EndLoc = Parser.getTok().getEndLoc(); 1094 Parser.Lex(); // Eat ')' 1095 return false; 1096 } 1097 1098 EndLoc = Parser.getTok().getEndLoc(); 1099 1100 // If this is "db[0-7]", match it as an alias 1101 // for dr[0-7]. 1102 if (RegNo == 0 && Tok.getString().size() == 3 && 1103 Tok.getString().startswith("db")) { 1104 switch (Tok.getString()[2]) { 1105 case '0': RegNo = X86::DR0; break; 1106 case '1': RegNo = X86::DR1; break; 1107 case '2': RegNo = X86::DR2; break; 1108 case '3': RegNo = X86::DR3; break; 1109 case '4': RegNo = X86::DR4; break; 1110 case '5': RegNo = X86::DR5; break; 1111 case '6': RegNo = X86::DR6; break; 1112 case '7': RegNo = X86::DR7; break; 1113 } 1114 1115 if (RegNo != 0) { 1116 EndLoc = Parser.getTok().getEndLoc(); 1117 Parser.Lex(); // Eat it. 1118 return false; 1119 } 1120 } 1121 1122 if (RegNo == 0) { 1123 if (isParsingIntelSyntax()) return true; 1124 return Error(StartLoc, "invalid register name", 1125 SMRange(StartLoc, EndLoc)); 1126 } 1127 1128 Parser.Lex(); // Eat identifier token. 1129 return false; 1130 } 1131 1132 void X86AsmParser::SetFrameRegister(unsigned RegNo) { 1133 Instrumentation->SetInitialFrameRegister(RegNo); 1134 } 1135 1136 std::unique_ptr<X86Operand> X86AsmParser::DefaultMemSIOperand(SMLoc Loc) { 1137 bool Parse32 = is32BitMode() || Code16GCC; 1138 unsigned Basereg = is64BitMode() ? X86::RSI : (Parse32 ? X86::ESI : X86::SI); 1139 const MCExpr *Disp = MCConstantExpr::create(0, getContext()); 1140 return X86Operand::CreateMem(getPointerWidth(), /*SegReg=*/0, Disp, 1141 /*BaseReg=*/Basereg, /*IndexReg=*/0, /*Scale=*/1, 1142 Loc, Loc, 0); 1143 } 1144 1145 std::unique_ptr<X86Operand> X86AsmParser::DefaultMemDIOperand(SMLoc Loc) { 1146 bool Parse32 = is32BitMode() || Code16GCC; 1147 unsigned Basereg = is64BitMode() ? X86::RDI : (Parse32 ? X86::EDI : X86::DI); 1148 const MCExpr *Disp = MCConstantExpr::create(0, getContext()); 1149 return X86Operand::CreateMem(getPointerWidth(), /*SegReg=*/0, Disp, 1150 /*BaseReg=*/Basereg, /*IndexReg=*/0, /*Scale=*/1, 1151 Loc, Loc, 0); 1152 } 1153 1154 bool X86AsmParser::IsSIReg(unsigned Reg) { 1155 switch (Reg) { 1156 default: llvm_unreachable("Only (R|E)SI and (R|E)DI are expected!"); 1157 case X86::RSI: 1158 case X86::ESI: 1159 case X86::SI: 1160 return true; 1161 case X86::RDI: 1162 case X86::EDI: 1163 case X86::DI: 1164 return false; 1165 } 1166 } 1167 1168 unsigned X86AsmParser::GetSIDIForRegClass(unsigned RegClassID, unsigned Reg, 1169 bool IsSIReg) { 1170 switch (RegClassID) { 1171 default: llvm_unreachable("Unexpected register class"); 1172 case X86::GR64RegClassID: 1173 return IsSIReg ? X86::RSI : X86::RDI; 1174 case X86::GR32RegClassID: 1175 return IsSIReg ? X86::ESI : X86::EDI; 1176 case X86::GR16RegClassID: 1177 return IsSIReg ? X86::SI : X86::DI; 1178 } 1179 } 1180 1181 void X86AsmParser::AddDefaultSrcDestOperands( 1182 OperandVector& Operands, std::unique_ptr<llvm::MCParsedAsmOperand> &&Src, 1183 std::unique_ptr<llvm::MCParsedAsmOperand> &&Dst) { 1184 if (isParsingIntelSyntax()) { 1185 Operands.push_back(std::move(Dst)); 1186 Operands.push_back(std::move(Src)); 1187 } 1188 else { 1189 Operands.push_back(std::move(Src)); 1190 Operands.push_back(std::move(Dst)); 1191 } 1192 } 1193 1194 bool X86AsmParser::VerifyAndAdjustOperands(OperandVector &OrigOperands, 1195 OperandVector &FinalOperands) { 1196 1197 if (OrigOperands.size() > 1) { 1198 // Check if sizes match, OrigOperands also contains the instruction name 1199 assert(OrigOperands.size() == FinalOperands.size() + 1 && 1200 "Operand size mismatch"); 1201 1202 SmallVector<std::pair<SMLoc, std::string>, 2> Warnings; 1203 // Verify types match 1204 int RegClassID = -1; 1205 for (unsigned int i = 0; i < FinalOperands.size(); ++i) { 1206 X86Operand &OrigOp = static_cast<X86Operand &>(*OrigOperands[i + 1]); 1207 X86Operand &FinalOp = static_cast<X86Operand &>(*FinalOperands[i]); 1208 1209 if (FinalOp.isReg() && 1210 (!OrigOp.isReg() || FinalOp.getReg() != OrigOp.getReg())) 1211 // Return false and let a normal complaint about bogus operands happen 1212 return false; 1213 1214 if (FinalOp.isMem()) { 1215 1216 if (!OrigOp.isMem()) 1217 // Return false and let a normal complaint about bogus operands happen 1218 return false; 1219 1220 unsigned OrigReg = OrigOp.Mem.BaseReg; 1221 unsigned FinalReg = FinalOp.Mem.BaseReg; 1222 1223 // If we've already encounterd a register class, make sure all register 1224 // bases are of the same register class 1225 if (RegClassID != -1 && 1226 !X86MCRegisterClasses[RegClassID].contains(OrigReg)) { 1227 return Error(OrigOp.getStartLoc(), 1228 "mismatching source and destination index registers"); 1229 } 1230 1231 if (X86MCRegisterClasses[X86::GR64RegClassID].contains(OrigReg)) 1232 RegClassID = X86::GR64RegClassID; 1233 else if (X86MCRegisterClasses[X86::GR32RegClassID].contains(OrigReg)) 1234 RegClassID = X86::GR32RegClassID; 1235 else if (X86MCRegisterClasses[X86::GR16RegClassID].contains(OrigReg)) 1236 RegClassID = X86::GR16RegClassID; 1237 else 1238 // Unexpected register class type 1239 // Return false and let a normal complaint about bogus operands happen 1240 return false; 1241 1242 bool IsSI = IsSIReg(FinalReg); 1243 FinalReg = GetSIDIForRegClass(RegClassID, FinalReg, IsSI); 1244 1245 if (FinalReg != OrigReg) { 1246 std::string RegName = IsSI ? "ES:(R|E)SI" : "ES:(R|E)DI"; 1247 Warnings.push_back(std::make_pair( 1248 OrigOp.getStartLoc(), 1249 "memory operand is only for determining the size, " + RegName + 1250 " will be used for the location")); 1251 } 1252 1253 FinalOp.Mem.Size = OrigOp.Mem.Size; 1254 FinalOp.Mem.SegReg = OrigOp.Mem.SegReg; 1255 FinalOp.Mem.BaseReg = FinalReg; 1256 } 1257 } 1258 1259 // Produce warnings only if all the operands passed the adjustment - prevent 1260 // legal cases like "movsd (%rax), %xmm0" mistakenly produce warnings 1261 for (auto &WarningMsg : Warnings) { 1262 Warning(WarningMsg.first, WarningMsg.second); 1263 } 1264 1265 // Remove old operands 1266 for (unsigned int i = 0; i < FinalOperands.size(); ++i) 1267 OrigOperands.pop_back(); 1268 } 1269 // OrigOperands.append(FinalOperands.begin(), FinalOperands.end()); 1270 for (unsigned int i = 0; i < FinalOperands.size(); ++i) 1271 OrigOperands.push_back(std::move(FinalOperands[i])); 1272 1273 return false; 1274 } 1275 1276 std::unique_ptr<X86Operand> X86AsmParser::ParseOperand() { 1277 if (isParsingIntelSyntax()) 1278 return ParseIntelOperand(); 1279 return ParseATTOperand(); 1280 } 1281 1282 std::unique_ptr<X86Operand> X86AsmParser::CreateMemForInlineAsm( 1283 unsigned SegReg, const MCExpr *Disp, unsigned BaseReg, unsigned IndexReg, 1284 unsigned Scale, SMLoc Start, SMLoc End, unsigned Size, StringRef Identifier, 1285 const InlineAsmIdentifierInfo &Info) { 1286 // If we found a decl other than a VarDecl, then assume it is a FuncDecl or 1287 // some other label reference. 1288 if (Info.isKind(InlineAsmIdentifierInfo::IK_Label)) { 1289 // Insert an explicit size if the user didn't have one. 1290 if (!Size) { 1291 Size = getPointerWidth(); 1292 InstInfo->AsmRewrites->emplace_back(AOK_SizeDirective, Start, 1293 /*Len=*/0, Size); 1294 } 1295 // Create an absolute memory reference in order to match against 1296 // instructions taking a PC relative operand. 1297 return X86Operand::CreateMem(getPointerWidth(), Disp, Start, End, Size, 1298 Identifier, Info.Label.Decl); 1299 } 1300 // We either have a direct symbol reference, or an offset from a symbol. The 1301 // parser always puts the symbol on the LHS, so look there for size 1302 // calculation purposes. 1303 unsigned FrontendSize = 0; 1304 void *Decl = nullptr; 1305 bool IsGlobalLV = false; 1306 if (Info.isKind(InlineAsmIdentifierInfo::IK_Var)) { 1307 // Size is in terms of bits in this context. 1308 FrontendSize = Info.Var.Type * 8; 1309 Decl = Info.Var.Decl; 1310 IsGlobalLV = Info.Var.IsGlobalLV; 1311 } 1312 // It is widely common for MS InlineAsm to use a global variable and one/two 1313 // registers in a mmory expression, and though unaccessible via rip/eip. 1314 if (IsGlobalLV && (BaseReg || IndexReg)) { 1315 return X86Operand::CreateMem(getPointerWidth(), Disp, Start, End); 1316 // Otherwise, we set the base register to a non-zero value 1317 // if we don't know the actual value at this time. This is necessary to 1318 // get the matching correct in some cases. 1319 } else { 1320 BaseReg = BaseReg ? BaseReg : 1; 1321 return X86Operand::CreateMem(getPointerWidth(), SegReg, Disp, BaseReg, 1322 IndexReg, Scale, Start, End, Size, Identifier, 1323 Decl, FrontendSize); 1324 } 1325 } 1326 1327 // Some binary bitwise operators have a named synonymous 1328 // Query a candidate string for being such a named operator 1329 // and if so - invoke the appropriate handler 1330 bool X86AsmParser::ParseIntelNamedOperator(StringRef Name, IntelExprStateMachine &SM) { 1331 // A named operator should be either lower or upper case, but not a mix 1332 if (Name.compare(Name.lower()) && Name.compare(Name.upper())) 1333 return false; 1334 if (Name.equals_lower("not")) 1335 SM.onNot(); 1336 else if (Name.equals_lower("or")) 1337 SM.onOr(); 1338 else if (Name.equals_lower("shl")) 1339 SM.onLShift(); 1340 else if (Name.equals_lower("shr")) 1341 SM.onRShift(); 1342 else if (Name.equals_lower("xor")) 1343 SM.onXor(); 1344 else if (Name.equals_lower("and")) 1345 SM.onAnd(); 1346 else if (Name.equals_lower("mod")) 1347 SM.onMod(); 1348 else 1349 return false; 1350 return true; 1351 } 1352 1353 bool X86AsmParser::ParseIntelExpression(IntelExprStateMachine &SM, SMLoc &End) { 1354 MCAsmParser &Parser = getParser(); 1355 const AsmToken &Tok = Parser.getTok(); 1356 StringRef ErrMsg; 1357 1358 AsmToken::TokenKind PrevTK = AsmToken::Error; 1359 bool Done = false; 1360 while (!Done) { 1361 bool UpdateLocLex = true; 1362 AsmToken::TokenKind TK = getLexer().getKind(); 1363 1364 switch (TK) { 1365 default: 1366 if ((Done = SM.isValidEndState())) 1367 break; 1368 return Error(Tok.getLoc(), "unknown token in expression"); 1369 case AsmToken::EndOfStatement: 1370 Done = true; 1371 break; 1372 case AsmToken::Real: 1373 // DotOperator: [ebx].0 1374 UpdateLocLex = false; 1375 if (ParseIntelDotOperator(SM, End)) 1376 return true; 1377 break; 1378 case AsmToken::String: 1379 case AsmToken::Identifier: { 1380 SMLoc IdentLoc = Tok.getLoc(); 1381 StringRef Identifier = Tok.getString(); 1382 UpdateLocLex = false; 1383 // Register 1384 unsigned Reg; 1385 if (Tok.isNot(AsmToken::String) && !ParseRegister(Reg, IdentLoc, End)) { 1386 if (SM.onRegister(Reg, ErrMsg)) 1387 return Error(Tok.getLoc(), ErrMsg); 1388 break; 1389 } 1390 // Operator synonymous ("not", "or" etc.) 1391 if ((UpdateLocLex = ParseIntelNamedOperator(Identifier, SM))) 1392 break; 1393 // Symbol reference, when parsing assembly content 1394 InlineAsmIdentifierInfo Info; 1395 const MCExpr *Val; 1396 if (!isParsingInlineAsm()) { 1397 if (getParser().parsePrimaryExpr(Val, End)) { 1398 return Error(Tok.getLoc(), "Unexpected identifier!"); 1399 } else if (SM.onIdentifierExpr(Val, Identifier, Info, false, ErrMsg)) { 1400 return Error(IdentLoc, ErrMsg); 1401 } else 1402 break; 1403 } 1404 // MS InlineAsm operators (TYPE/LENGTH/SIZE) 1405 if (unsigned OpKind = IdentifyIntelInlineAsmOperator(Identifier)) { 1406 if (OpKind == IOK_OFFSET) 1407 return Error(IdentLoc, "Dealing OFFSET operator as part of" 1408 "a compound immediate expression is yet to be supported"); 1409 if (int64_t Val = ParseIntelInlineAsmOperator(OpKind)) { 1410 if (SM.onInteger(Val, ErrMsg)) 1411 return Error(IdentLoc, ErrMsg); 1412 } else 1413 return true; 1414 break; 1415 } 1416 // MS Dot Operator expression 1417 if (Identifier.count('.') && PrevTK == AsmToken::RBrac) { 1418 if (ParseIntelDotOperator(SM, End)) 1419 return true; 1420 break; 1421 } 1422 // MS InlineAsm identifier 1423 if (ParseIntelInlineAsmIdentifier(Val, Identifier, Info, false, End)) 1424 return true; 1425 else if (SM.onIdentifierExpr(Val, Identifier, Info, true, ErrMsg)) 1426 return Error(IdentLoc, ErrMsg); 1427 break; 1428 } 1429 case AsmToken::Integer: { 1430 // Look for 'b' or 'f' following an Integer as a directional label 1431 SMLoc Loc = getTok().getLoc(); 1432 int64_t IntVal = getTok().getIntVal(); 1433 End = consumeToken(); 1434 UpdateLocLex = false; 1435 if (getLexer().getKind() == AsmToken::Identifier) { 1436 StringRef IDVal = getTok().getString(); 1437 if (IDVal == "f" || IDVal == "b") { 1438 MCSymbol *Sym = 1439 getContext().getDirectionalLocalSymbol(IntVal, IDVal == "b"); 1440 MCSymbolRefExpr::VariantKind Variant = MCSymbolRefExpr::VK_None; 1441 const MCExpr *Val = 1442 MCSymbolRefExpr::create(Sym, Variant, getContext()); 1443 if (IDVal == "b" && Sym->isUndefined()) 1444 return Error(Loc, "invalid reference to undefined symbol"); 1445 StringRef Identifier = Sym->getName(); 1446 InlineAsmIdentifierInfo Info; 1447 if (SM.onIdentifierExpr(Val, Identifier, Info, 1448 isParsingInlineAsm(), ErrMsg)) 1449 return Error(Loc, ErrMsg); 1450 End = consumeToken(); 1451 } else { 1452 if (SM.onInteger(IntVal, ErrMsg)) 1453 return Error(Loc, ErrMsg); 1454 } 1455 } else { 1456 if (SM.onInteger(IntVal, ErrMsg)) 1457 return Error(Loc, ErrMsg); 1458 } 1459 break; 1460 } 1461 case AsmToken::Plus: 1462 if (SM.onPlus(ErrMsg)) 1463 return Error(getTok().getLoc(), ErrMsg); 1464 break; 1465 case AsmToken::Minus: 1466 if (SM.onMinus(ErrMsg)) 1467 return Error(getTok().getLoc(), ErrMsg); 1468 break; 1469 case AsmToken::Tilde: SM.onNot(); break; 1470 case AsmToken::Star: SM.onStar(); break; 1471 case AsmToken::Slash: SM.onDivide(); break; 1472 case AsmToken::Pipe: SM.onOr(); break; 1473 case AsmToken::Caret: SM.onXor(); break; 1474 case AsmToken::Amp: SM.onAnd(); break; 1475 case AsmToken::LessLess: 1476 SM.onLShift(); break; 1477 case AsmToken::GreaterGreater: 1478 SM.onRShift(); break; 1479 case AsmToken::LBrac: 1480 if (SM.onLBrac()) 1481 return Error(Tok.getLoc(), "unexpected bracket encountered"); 1482 break; 1483 case AsmToken::RBrac: 1484 if (SM.onRBrac()) 1485 return Error(Tok.getLoc(), "unexpected bracket encountered"); 1486 break; 1487 case AsmToken::LParen: SM.onLParen(); break; 1488 case AsmToken::RParen: SM.onRParen(); break; 1489 } 1490 if (SM.hadError()) 1491 return Error(Tok.getLoc(), "unknown token in expression"); 1492 1493 if (!Done && UpdateLocLex) 1494 End = consumeToken(); 1495 1496 PrevTK = TK; 1497 } 1498 return false; 1499 } 1500 1501 void X86AsmParser::RewriteIntelExpression(IntelExprStateMachine &SM, 1502 SMLoc Start, SMLoc End) { 1503 SMLoc Loc = Start; 1504 unsigned ExprLen = End.getPointer() - Start.getPointer(); 1505 // Skip everything before a symbol displacement (if we have one) 1506 if (SM.getSym()) { 1507 StringRef SymName = SM.getSymName(); 1508 if (unsigned Len = SymName.data() - Start.getPointer()) 1509 InstInfo->AsmRewrites->emplace_back(AOK_Skip, Start, Len); 1510 Loc = SMLoc::getFromPointer(SymName.data() + SymName.size()); 1511 ExprLen = End.getPointer() - (SymName.data() + SymName.size()); 1512 // If we have only a symbol than there's no need for complex rewrite, 1513 // simply skip everything after it 1514 if (!(SM.getBaseReg() || SM.getIndexReg() || SM.getImm())) { 1515 if (ExprLen) 1516 InstInfo->AsmRewrites->emplace_back(AOK_Skip, Loc, ExprLen); 1517 return; 1518 } 1519 } 1520 // Build an Intel Expression rewrite 1521 StringRef BaseRegStr; 1522 StringRef IndexRegStr; 1523 if (SM.getBaseReg()) 1524 BaseRegStr = X86IntelInstPrinter::getRegisterName(SM.getBaseReg()); 1525 if (SM.getIndexReg()) 1526 IndexRegStr = X86IntelInstPrinter::getRegisterName(SM.getIndexReg()); 1527 // Emit it 1528 IntelExpr Expr(BaseRegStr, IndexRegStr, SM.getScale(), SM.getImm(), SM.isMemExpr()); 1529 InstInfo->AsmRewrites->emplace_back(Loc, ExprLen, Expr); 1530 } 1531 1532 // Inline assembly may use variable names with namespace alias qualifiers. 1533 bool X86AsmParser::ParseIntelInlineAsmIdentifier(const MCExpr *&Val, 1534 StringRef &Identifier, 1535 InlineAsmIdentifierInfo &Info, 1536 bool IsUnevaluatedOperand, 1537 SMLoc &End) { 1538 MCAsmParser &Parser = getParser(); 1539 assert(isParsingInlineAsm() && "Expected to be parsing inline assembly."); 1540 Val = nullptr; 1541 1542 StringRef LineBuf(Identifier.data()); 1543 SemaCallback->LookupInlineAsmIdentifier(LineBuf, Info, IsUnevaluatedOperand); 1544 1545 const AsmToken &Tok = Parser.getTok(); 1546 SMLoc Loc = Tok.getLoc(); 1547 1548 // Advance the token stream until the end of the current token is 1549 // after the end of what the frontend claimed. 1550 const char *EndPtr = Tok.getLoc().getPointer() + LineBuf.size(); 1551 do { 1552 End = Tok.getEndLoc(); 1553 getLexer().Lex(); 1554 } while (End.getPointer() < EndPtr); 1555 Identifier = LineBuf; 1556 1557 // The frontend should end parsing on an assembler token boundary, unless it 1558 // failed parsing. 1559 assert((End.getPointer() == EndPtr || 1560 Info.isKind(InlineAsmIdentifierInfo::IK_Invalid)) && 1561 "frontend claimed part of a token?"); 1562 1563 // If the identifier lookup was unsuccessful, assume that we are dealing with 1564 // a label. 1565 if (Info.isKind(InlineAsmIdentifierInfo::IK_Invalid)) { 1566 StringRef InternalName = 1567 SemaCallback->LookupInlineAsmLabel(Identifier, getSourceManager(), 1568 Loc, false); 1569 assert(InternalName.size() && "We should have an internal name here."); 1570 // Push a rewrite for replacing the identifier name with the internal name. 1571 InstInfo->AsmRewrites->emplace_back(AOK_Label, Loc, Identifier.size(), 1572 InternalName); 1573 } else if (Info.isKind(InlineAsmIdentifierInfo::IK_EnumVal)) 1574 return false; 1575 // Create the symbol reference. 1576 MCSymbol *Sym = getContext().getOrCreateSymbol(Identifier); 1577 MCSymbolRefExpr::VariantKind Variant = MCSymbolRefExpr::VK_None; 1578 Val = MCSymbolRefExpr::create(Sym, Variant, getParser().getContext()); 1579 return false; 1580 } 1581 1582 //ParseRoundingModeOp - Parse AVX-512 rounding mode operand 1583 std::unique_ptr<X86Operand> 1584 X86AsmParser::ParseRoundingModeOp(SMLoc Start, SMLoc End) { 1585 MCAsmParser &Parser = getParser(); 1586 const AsmToken &Tok = Parser.getTok(); 1587 // Eat "{" and mark the current place. 1588 const SMLoc consumedToken = consumeToken(); 1589 if (Tok.getIdentifier().startswith("r")){ 1590 int rndMode = StringSwitch<int>(Tok.getIdentifier()) 1591 .Case("rn", X86::STATIC_ROUNDING::TO_NEAREST_INT) 1592 .Case("rd", X86::STATIC_ROUNDING::TO_NEG_INF) 1593 .Case("ru", X86::STATIC_ROUNDING::TO_POS_INF) 1594 .Case("rz", X86::STATIC_ROUNDING::TO_ZERO) 1595 .Default(-1); 1596 if (-1 == rndMode) 1597 return ErrorOperand(Tok.getLoc(), "Invalid rounding mode."); 1598 Parser.Lex(); // Eat "r*" of r*-sae 1599 if (!getLexer().is(AsmToken::Minus)) 1600 return ErrorOperand(Tok.getLoc(), "Expected - at this point"); 1601 Parser.Lex(); // Eat "-" 1602 Parser.Lex(); // Eat the sae 1603 if (!getLexer().is(AsmToken::RCurly)) 1604 return ErrorOperand(Tok.getLoc(), "Expected } at this point"); 1605 Parser.Lex(); // Eat "}" 1606 const MCExpr *RndModeOp = 1607 MCConstantExpr::create(rndMode, Parser.getContext()); 1608 return X86Operand::CreateImm(RndModeOp, Start, End); 1609 } 1610 if(Tok.getIdentifier().equals("sae")){ 1611 Parser.Lex(); // Eat the sae 1612 if (!getLexer().is(AsmToken::RCurly)) 1613 return ErrorOperand(Tok.getLoc(), "Expected } at this point"); 1614 Parser.Lex(); // Eat "}" 1615 return X86Operand::CreateToken("{sae}", consumedToken); 1616 } 1617 return ErrorOperand(Tok.getLoc(), "unknown token in expression"); 1618 } 1619 1620 /// Parse the '.' operator. 1621 bool X86AsmParser::ParseIntelDotOperator(IntelExprStateMachine &SM, SMLoc &End) { 1622 const AsmToken &Tok = getTok(); 1623 unsigned Offset; 1624 1625 // Drop the optional '.'. 1626 StringRef DotDispStr = Tok.getString(); 1627 if (DotDispStr.startswith(".")) 1628 DotDispStr = DotDispStr.drop_front(1); 1629 1630 // .Imm gets lexed as a real. 1631 if (Tok.is(AsmToken::Real)) { 1632 APInt DotDisp; 1633 DotDispStr.getAsInteger(10, DotDisp); 1634 Offset = DotDisp.getZExtValue(); 1635 } else if (isParsingInlineAsm() && Tok.is(AsmToken::Identifier)) { 1636 std::pair<StringRef, StringRef> BaseMember = DotDispStr.split('.'); 1637 if (SemaCallback->LookupInlineAsmField(BaseMember.first, BaseMember.second, 1638 Offset)) 1639 return Error(Tok.getLoc(), "Unable to lookup field reference!"); 1640 } else 1641 return Error(Tok.getLoc(), "Unexpected token type!"); 1642 1643 // Eat the DotExpression and update End 1644 End = SMLoc::getFromPointer(DotDispStr.data()); 1645 const char *DotExprEndLoc = DotDispStr.data() + DotDispStr.size(); 1646 while (Tok.getLoc().getPointer() < DotExprEndLoc) 1647 Lex(); 1648 SM.addImm(Offset); 1649 return false; 1650 } 1651 1652 /// Parse the 'offset' operator. This operator is used to specify the 1653 /// location rather then the content of a variable. 1654 std::unique_ptr<X86Operand> X86AsmParser::ParseIntelOffsetOfOperator() { 1655 MCAsmParser &Parser = getParser(); 1656 const AsmToken &Tok = Parser.getTok(); 1657 SMLoc OffsetOfLoc = Tok.getLoc(); 1658 Parser.Lex(); // Eat offset. 1659 1660 const MCExpr *Val; 1661 InlineAsmIdentifierInfo Info; 1662 SMLoc Start = Tok.getLoc(), End; 1663 StringRef Identifier = Tok.getString(); 1664 if (ParseIntelInlineAsmIdentifier(Val, Identifier, Info, 1665 /*Unevaluated=*/false, End)) 1666 return nullptr; 1667 1668 void *Decl = nullptr; 1669 // FIXME: MS evaluates "offset <Constant>" to the underlying integral 1670 if (Info.isKind(InlineAsmIdentifierInfo::IK_EnumVal)) 1671 return ErrorOperand(Start, "offset operator cannot yet handle constants"); 1672 else if (Info.isKind(InlineAsmIdentifierInfo::IK_Var)) 1673 Decl = Info.Var.Decl; 1674 // Don't emit the offset operator. 1675 InstInfo->AsmRewrites->emplace_back(AOK_Skip, OffsetOfLoc, 7); 1676 1677 // The offset operator will have an 'r' constraint, thus we need to create 1678 // register operand to ensure proper matching. Just pick a GPR based on 1679 // the size of a pointer. 1680 bool Parse32 = is32BitMode() || Code16GCC; 1681 unsigned RegNo = is64BitMode() ? X86::RBX : (Parse32 ? X86::EBX : X86::BX); 1682 1683 return X86Operand::CreateReg(RegNo, Start, End, /*GetAddress=*/true, 1684 OffsetOfLoc, Identifier, Decl); 1685 } 1686 1687 // Query a candidate string for being an Intel assembly operator 1688 // Report back its kind, or IOK_INVALID if does not evaluated as a known one 1689 unsigned X86AsmParser::IdentifyIntelInlineAsmOperator(StringRef Name) { 1690 return StringSwitch<unsigned>(Name) 1691 .Cases("TYPE","type",IOK_TYPE) 1692 .Cases("SIZE","size",IOK_SIZE) 1693 .Cases("LENGTH","length",IOK_LENGTH) 1694 .Cases("OFFSET","offset",IOK_OFFSET) 1695 .Default(IOK_INVALID); 1696 } 1697 1698 /// Parse the 'LENGTH', 'TYPE' and 'SIZE' operators. The LENGTH operator 1699 /// returns the number of elements in an array. It returns the value 1 for 1700 /// non-array variables. The SIZE operator returns the size of a C or C++ 1701 /// variable. A variable's size is the product of its LENGTH and TYPE. The 1702 /// TYPE operator returns the size of a C or C++ type or variable. If the 1703 /// variable is an array, TYPE returns the size of a single element. 1704 unsigned X86AsmParser::ParseIntelInlineAsmOperator(unsigned OpKind) { 1705 MCAsmParser &Parser = getParser(); 1706 const AsmToken &Tok = Parser.getTok(); 1707 Parser.Lex(); // Eat operator. 1708 1709 const MCExpr *Val = nullptr; 1710 InlineAsmIdentifierInfo Info; 1711 SMLoc Start = Tok.getLoc(), End; 1712 StringRef Identifier = Tok.getString(); 1713 if (ParseIntelInlineAsmIdentifier(Val, Identifier, Info, 1714 /*Unevaluated=*/true, End)) 1715 return 0; 1716 1717 if (!Info.isKind(InlineAsmIdentifierInfo::IK_Var)) { 1718 Error(Start, "unable to lookup expression"); 1719 return 0; 1720 } 1721 1722 unsigned CVal = 0; 1723 switch(OpKind) { 1724 default: llvm_unreachable("Unexpected operand kind!"); 1725 case IOK_LENGTH: CVal = Info.Var.Length; break; 1726 case IOK_SIZE: CVal = Info.Var.Size; break; 1727 case IOK_TYPE: CVal = Info.Var.Type; break; 1728 } 1729 1730 return CVal; 1731 } 1732 1733 bool X86AsmParser::ParseIntelMemoryOperandSize(unsigned &Size) { 1734 Size = StringSwitch<unsigned>(getTok().getString()) 1735 .Cases("BYTE", "byte", 8) 1736 .Cases("WORD", "word", 16) 1737 .Cases("DWORD", "dword", 32) 1738 .Cases("FLOAT", "float", 32) 1739 .Cases("LONG", "long", 32) 1740 .Cases("FWORD", "fword", 48) 1741 .Cases("DOUBLE", "double", 64) 1742 .Cases("QWORD", "qword", 64) 1743 .Cases("MMWORD","mmword", 64) 1744 .Cases("XWORD", "xword", 80) 1745 .Cases("TBYTE", "tbyte", 80) 1746 .Cases("XMMWORD", "xmmword", 128) 1747 .Cases("YMMWORD", "ymmword", 256) 1748 .Cases("ZMMWORD", "zmmword", 512) 1749 .Cases("OPAQUE", "opaque", -1U) // needs to be non-zero, but doesn't matter 1750 .Default(0); 1751 if (Size) { 1752 const AsmToken &Tok = Lex(); // Eat operand size (e.g., byte, word). 1753 if (!(Tok.getString().equals("PTR") || Tok.getString().equals("ptr"))) 1754 return Error(Tok.getLoc(), "Expected 'PTR' or 'ptr' token!"); 1755 Lex(); // Eat ptr. 1756 } 1757 return false; 1758 } 1759 1760 std::unique_ptr<X86Operand> X86AsmParser::ParseIntelOperand() { 1761 MCAsmParser &Parser = getParser(); 1762 const AsmToken &Tok = Parser.getTok(); 1763 SMLoc Start, End; 1764 1765 // FIXME: Offset operator 1766 // Should be handled as part of immediate expression, as other operators 1767 // Currently, only supported as a stand-alone operand 1768 if (isParsingInlineAsm()) 1769 if (IdentifyIntelInlineAsmOperator(Tok.getString()) == IOK_OFFSET) 1770 return ParseIntelOffsetOfOperator(); 1771 1772 // Parse optional Size directive. 1773 unsigned Size; 1774 if (ParseIntelMemoryOperandSize(Size)) 1775 return nullptr; 1776 bool PtrInOperand = bool(Size); 1777 1778 Start = Tok.getLoc(); 1779 1780 // Rounding mode operand. 1781 if (getSTI().getFeatureBits()[X86::FeatureAVX512] && 1782 getLexer().is(AsmToken::LCurly)) 1783 return ParseRoundingModeOp(Start, End); 1784 1785 // Register operand. 1786 unsigned RegNo = 0; 1787 if (Tok.is(AsmToken::Identifier) && !ParseRegister(RegNo, Start, End)) { 1788 if (RegNo == X86::RIP) 1789 return ErrorOperand(Start, "rip can only be used as a base register"); 1790 // A Register followed by ':' is considered a segment override 1791 if (Tok.isNot(AsmToken::Colon)) 1792 return !PtrInOperand ? X86Operand::CreateReg(RegNo, Start, End) : 1793 ErrorOperand(Start, "expected memory operand after 'ptr', " 1794 "found register operand instead"); 1795 // An alleged segment override. check if we have a valid segment register 1796 if (!X86MCRegisterClasses[X86::SEGMENT_REGRegClassID].contains(RegNo)) 1797 return ErrorOperand(Start, "invalid segment register"); 1798 // Eat ':' and update Start location 1799 Start = Lex().getLoc(); 1800 } 1801 1802 // Immediates and Memory 1803 IntelExprStateMachine SM; 1804 if (ParseIntelExpression(SM, End)) 1805 return nullptr; 1806 1807 if (isParsingInlineAsm()) 1808 RewriteIntelExpression(SM, Start, Tok.getLoc()); 1809 1810 int64_t Imm = SM.getImm(); 1811 const MCExpr *Disp = SM.getSym(); 1812 const MCExpr *ImmDisp = MCConstantExpr::create(Imm, getContext()); 1813 if (Disp && Imm) 1814 Disp = MCBinaryExpr::createAdd(Disp, ImmDisp, getContext()); 1815 if (!Disp) 1816 Disp = ImmDisp; 1817 1818 // RegNo != 0 specifies a valid segment register, 1819 // and we are parsing a segment override 1820 if (!SM.isMemExpr() && !RegNo) 1821 return X86Operand::CreateImm(Disp, Start, End); 1822 1823 StringRef ErrMsg; 1824 unsigned BaseReg = SM.getBaseReg(); 1825 unsigned IndexReg = SM.getIndexReg(); 1826 unsigned Scale = SM.getScale(); 1827 1828 if ((BaseReg || IndexReg) && 1829 CheckBaseRegAndIndexRegAndScale(BaseReg, IndexReg, Scale, ErrMsg)) 1830 return ErrorOperand(Start, ErrMsg); 1831 if (isParsingInlineAsm()) 1832 return CreateMemForInlineAsm(RegNo, Disp, BaseReg, IndexReg, 1833 Scale, Start, End, Size, SM.getSymName(), 1834 SM.getIdentifierInfo()); 1835 if (!(BaseReg || IndexReg || RegNo)) 1836 return X86Operand::CreateMem(getPointerWidth(), Disp, Start, End, Size); 1837 return X86Operand::CreateMem(getPointerWidth(), RegNo, Disp, 1838 BaseReg, IndexReg, Scale, Start, End, Size); 1839 } 1840 1841 std::unique_ptr<X86Operand> X86AsmParser::ParseATTOperand() { 1842 MCAsmParser &Parser = getParser(); 1843 switch (getLexer().getKind()) { 1844 default: 1845 // Parse a memory operand with no segment register. 1846 return ParseMemOperand(0, Parser.getTok().getLoc()); 1847 case AsmToken::Percent: { 1848 // Read the register. 1849 unsigned RegNo; 1850 SMLoc Start, End; 1851 if (ParseRegister(RegNo, Start, End)) return nullptr; 1852 if (RegNo == X86::EIZ || RegNo == X86::RIZ) { 1853 Error(Start, "%eiz and %riz can only be used as index registers", 1854 SMRange(Start, End)); 1855 return nullptr; 1856 } 1857 if (RegNo == X86::RIP) { 1858 Error(Start, "%rip can only be used as a base register", 1859 SMRange(Start, End)); 1860 return nullptr; 1861 } 1862 1863 // If this is a segment register followed by a ':', then this is the start 1864 // of a memory reference, otherwise this is a normal register reference. 1865 if (getLexer().isNot(AsmToken::Colon)) 1866 return X86Operand::CreateReg(RegNo, Start, End); 1867 1868 if (!X86MCRegisterClasses[X86::SEGMENT_REGRegClassID].contains(RegNo)) 1869 return ErrorOperand(Start, "invalid segment register"); 1870 1871 getParser().Lex(); // Eat the colon. 1872 return ParseMemOperand(RegNo, Start); 1873 } 1874 case AsmToken::Dollar: { 1875 // $42 -> immediate. 1876 SMLoc Start = Parser.getTok().getLoc(), End; 1877 Parser.Lex(); 1878 const MCExpr *Val; 1879 if (getParser().parseExpression(Val, End)) 1880 return nullptr; 1881 return X86Operand::CreateImm(Val, Start, End); 1882 } 1883 case AsmToken::LCurly:{ 1884 SMLoc Start = Parser.getTok().getLoc(), End; 1885 if (getSTI().getFeatureBits()[X86::FeatureAVX512]) 1886 return ParseRoundingModeOp(Start, End); 1887 return ErrorOperand(Start, "Unexpected '{' in expression"); 1888 } 1889 } 1890 } 1891 1892 // true on failure, false otherwise 1893 // If no {z} mark was found - Parser doesn't advance 1894 bool X86AsmParser::ParseZ(std::unique_ptr<X86Operand> &Z, 1895 const SMLoc &StartLoc) { 1896 MCAsmParser &Parser = getParser(); 1897 // Assuming we are just pass the '{' mark, quering the next token 1898 // Searched for {z}, but none was found. Return false, as no parsing error was 1899 // encountered 1900 if (!(getLexer().is(AsmToken::Identifier) && 1901 (getLexer().getTok().getIdentifier() == "z"))) 1902 return false; 1903 Parser.Lex(); // Eat z 1904 // Query and eat the '}' mark 1905 if (!getLexer().is(AsmToken::RCurly)) 1906 return Error(getLexer().getLoc(), "Expected } at this point"); 1907 Parser.Lex(); // Eat '}' 1908 // Assign Z with the {z} mark opernad 1909 Z = X86Operand::CreateToken("{z}", StartLoc); 1910 return false; 1911 } 1912 1913 // true on failure, false otherwise 1914 bool X86AsmParser::HandleAVX512Operand(OperandVector &Operands, 1915 const MCParsedAsmOperand &Op) { 1916 MCAsmParser &Parser = getParser(); 1917 if(getSTI().getFeatureBits()[X86::FeatureAVX512]) { 1918 if (getLexer().is(AsmToken::LCurly)) { 1919 // Eat "{" and mark the current place. 1920 const SMLoc consumedToken = consumeToken(); 1921 // Distinguish {1to<NUM>} from {%k<NUM>}. 1922 if(getLexer().is(AsmToken::Integer)) { 1923 // Parse memory broadcasting ({1to<NUM>}). 1924 if (getLexer().getTok().getIntVal() != 1) 1925 return TokError("Expected 1to<NUM> at this point"); 1926 Parser.Lex(); // Eat "1" of 1to8 1927 if (!getLexer().is(AsmToken::Identifier) || 1928 !getLexer().getTok().getIdentifier().startswith("to")) 1929 return TokError("Expected 1to<NUM> at this point"); 1930 // Recognize only reasonable suffixes. 1931 const char *BroadcastPrimitive = 1932 StringSwitch<const char*>(getLexer().getTok().getIdentifier()) 1933 .Case("to2", "{1to2}") 1934 .Case("to4", "{1to4}") 1935 .Case("to8", "{1to8}") 1936 .Case("to16", "{1to16}") 1937 .Default(nullptr); 1938 if (!BroadcastPrimitive) 1939 return TokError("Invalid memory broadcast primitive."); 1940 Parser.Lex(); // Eat "toN" of 1toN 1941 if (!getLexer().is(AsmToken::RCurly)) 1942 return TokError("Expected } at this point"); 1943 Parser.Lex(); // Eat "}" 1944 Operands.push_back(X86Operand::CreateToken(BroadcastPrimitive, 1945 consumedToken)); 1946 // No AVX512 specific primitives can pass 1947 // after memory broadcasting, so return. 1948 return false; 1949 } else { 1950 // Parse either {k}{z}, {z}{k}, {k} or {z} 1951 // last one have no meaning, but GCC accepts it 1952 // Currently, we're just pass a '{' mark 1953 std::unique_ptr<X86Operand> Z; 1954 if (ParseZ(Z, consumedToken)) 1955 return true; 1956 // Reaching here means that parsing of the allegadly '{z}' mark yielded 1957 // no errors. 1958 // Query for the need of further parsing for a {%k<NUM>} mark 1959 if (!Z || getLexer().is(AsmToken::LCurly)) { 1960 SMLoc StartLoc = Z ? consumeToken() : consumedToken; 1961 // Parse an op-mask register mark ({%k<NUM>}), which is now to be 1962 // expected 1963 unsigned RegNo; 1964 SMLoc RegLoc; 1965 if (!ParseRegister(RegNo, RegLoc, StartLoc) && 1966 X86MCRegisterClasses[X86::VK1RegClassID].contains(RegNo)) { 1967 if (RegNo == X86::K0) 1968 return Error(RegLoc, "Register k0 can't be used as write mask"); 1969 if (!getLexer().is(AsmToken::RCurly)) 1970 return Error(getLexer().getLoc(), "Expected } at this point"); 1971 Operands.push_back(X86Operand::CreateToken("{", StartLoc)); 1972 Operands.push_back( 1973 X86Operand::CreateReg(RegNo, StartLoc, StartLoc)); 1974 Operands.push_back(X86Operand::CreateToken("}", consumeToken())); 1975 } else 1976 return Error(getLexer().getLoc(), 1977 "Expected an op-mask register at this point"); 1978 // {%k<NUM>} mark is found, inquire for {z} 1979 if (getLexer().is(AsmToken::LCurly) && !Z) { 1980 // Have we've found a parsing error, or found no (expected) {z} mark 1981 // - report an error 1982 if (ParseZ(Z, consumeToken()) || !Z) 1983 return Error(getLexer().getLoc(), 1984 "Expected a {z} mark at this point"); 1985 1986 } 1987 // '{z}' on its own is meaningless, hence should be ignored. 1988 // on the contrary - have it been accompanied by a K register, 1989 // allow it. 1990 if (Z) 1991 Operands.push_back(std::move(Z)); 1992 } 1993 } 1994 } 1995 } 1996 return false; 1997 } 1998 1999 /// ParseMemOperand: segment: disp(basereg, indexreg, scale). The '%ds:' prefix 2000 /// has already been parsed if present. 2001 std::unique_ptr<X86Operand> X86AsmParser::ParseMemOperand(unsigned SegReg, 2002 SMLoc MemStart) { 2003 2004 MCAsmParser &Parser = getParser(); 2005 // We have to disambiguate a parenthesized expression "(4+5)" from the start 2006 // of a memory operand with a missing displacement "(%ebx)" or "(,%eax)". The 2007 // only way to do this without lookahead is to eat the '(' and see what is 2008 // after it. 2009 const MCExpr *Disp = MCConstantExpr::create(0, getParser().getContext()); 2010 if (getLexer().isNot(AsmToken::LParen)) { 2011 SMLoc ExprEnd; 2012 if (getParser().parseExpression(Disp, ExprEnd)) return nullptr; 2013 2014 // After parsing the base expression we could either have a parenthesized 2015 // memory address or not. If not, return now. If so, eat the (. 2016 if (getLexer().isNot(AsmToken::LParen)) { 2017 // Unless we have a segment register, treat this as an immediate. 2018 if (SegReg == 0) 2019 return X86Operand::CreateMem(getPointerWidth(), Disp, MemStart, ExprEnd); 2020 return X86Operand::CreateMem(getPointerWidth(), SegReg, Disp, 0, 0, 1, 2021 MemStart, ExprEnd); 2022 } 2023 2024 // Eat the '('. 2025 Parser.Lex(); 2026 } else { 2027 // Okay, we have a '('. We don't know if this is an expression or not, but 2028 // so we have to eat the ( to see beyond it. 2029 SMLoc LParenLoc = Parser.getTok().getLoc(); 2030 Parser.Lex(); // Eat the '('. 2031 2032 if (getLexer().is(AsmToken::Percent) || getLexer().is(AsmToken::Comma)) { 2033 // Nothing to do here, fall into the code below with the '(' part of the 2034 // memory operand consumed. 2035 } else { 2036 SMLoc ExprEnd; 2037 getLexer().UnLex(AsmToken(AsmToken::LParen, "(")); 2038 2039 // It must be either an parenthesized expression, or an expression that 2040 // begins from a parenthesized expression, parse it now. Example: (1+2) or 2041 // (1+2)+3 2042 if (getParser().parseExpression(Disp, ExprEnd)) 2043 return nullptr; 2044 2045 // After parsing the base expression we could either have a parenthesized 2046 // memory address or not. If not, return now. If so, eat the (. 2047 if (getLexer().isNot(AsmToken::LParen)) { 2048 // Unless we have a segment register, treat this as an immediate. 2049 if (SegReg == 0) 2050 return X86Operand::CreateMem(getPointerWidth(), Disp, LParenLoc, 2051 ExprEnd); 2052 return X86Operand::CreateMem(getPointerWidth(), SegReg, Disp, 0, 0, 1, 2053 MemStart, ExprEnd); 2054 } 2055 2056 // Eat the '('. 2057 Parser.Lex(); 2058 } 2059 } 2060 2061 // If we reached here, then we just ate the ( of the memory operand. Process 2062 // the rest of the memory operand. 2063 unsigned BaseReg = 0, IndexReg = 0, Scale = 1; 2064 SMLoc IndexLoc, BaseLoc; 2065 2066 if (getLexer().is(AsmToken::Percent)) { 2067 SMLoc StartLoc, EndLoc; 2068 BaseLoc = Parser.getTok().getLoc(); 2069 if (ParseRegister(BaseReg, StartLoc, EndLoc)) return nullptr; 2070 if (BaseReg == X86::EIZ || BaseReg == X86::RIZ) { 2071 Error(StartLoc, "eiz and riz can only be used as index registers", 2072 SMRange(StartLoc, EndLoc)); 2073 return nullptr; 2074 } 2075 } 2076 2077 if (getLexer().is(AsmToken::Comma)) { 2078 Parser.Lex(); // Eat the comma. 2079 IndexLoc = Parser.getTok().getLoc(); 2080 2081 // Following the comma we should have either an index register, or a scale 2082 // value. We don't support the later form, but we want to parse it 2083 // correctly. 2084 // 2085 // Not that even though it would be completely consistent to support syntax 2086 // like "1(%eax,,1)", the assembler doesn't. Use "eiz" or "riz" for this. 2087 if (getLexer().is(AsmToken::Percent)) { 2088 SMLoc L; 2089 if (ParseRegister(IndexReg, L, L)) 2090 return nullptr; 2091 if (BaseReg == X86::RIP) { 2092 Error(IndexLoc, "%rip as base register can not have an index register"); 2093 return nullptr; 2094 } 2095 if (IndexReg == X86::RIP) { 2096 Error(IndexLoc, "%rip is not allowed as an index register"); 2097 return nullptr; 2098 } 2099 2100 if (getLexer().isNot(AsmToken::RParen)) { 2101 // Parse the scale amount: 2102 // ::= ',' [scale-expression] 2103 if (getLexer().isNot(AsmToken::Comma)) { 2104 Error(Parser.getTok().getLoc(), 2105 "expected comma in scale expression"); 2106 return nullptr; 2107 } 2108 Parser.Lex(); // Eat the comma. 2109 2110 if (getLexer().isNot(AsmToken::RParen)) { 2111 SMLoc Loc = Parser.getTok().getLoc(); 2112 2113 int64_t ScaleVal; 2114 if (getParser().parseAbsoluteExpression(ScaleVal)){ 2115 Error(Loc, "expected scale expression"); 2116 return nullptr; 2117 } 2118 2119 // Validate the scale amount. 2120 if (X86MCRegisterClasses[X86::GR16RegClassID].contains(BaseReg) && 2121 ScaleVal != 1) { 2122 Error(Loc, "scale factor in 16-bit address must be 1"); 2123 return nullptr; 2124 } 2125 if (ScaleVal != 1 && ScaleVal != 2 && ScaleVal != 4 && 2126 ScaleVal != 8) { 2127 Error(Loc, "scale factor in address must be 1, 2, 4 or 8"); 2128 return nullptr; 2129 } 2130 Scale = (unsigned)ScaleVal; 2131 } 2132 } 2133 } else if (getLexer().isNot(AsmToken::RParen)) { 2134 // A scale amount without an index is ignored. 2135 // index. 2136 SMLoc Loc = Parser.getTok().getLoc(); 2137 2138 int64_t Value; 2139 if (getParser().parseAbsoluteExpression(Value)) 2140 return nullptr; 2141 2142 if (Value != 1) 2143 Warning(Loc, "scale factor without index register is ignored"); 2144 Scale = 1; 2145 } 2146 } 2147 2148 // Ok, we've eaten the memory operand, verify we have a ')' and eat it too. 2149 if (getLexer().isNot(AsmToken::RParen)) { 2150 Error(Parser.getTok().getLoc(), "unexpected token in memory operand"); 2151 return nullptr; 2152 } 2153 SMLoc MemEnd = Parser.getTok().getEndLoc(); 2154 Parser.Lex(); // Eat the ')'. 2155 2156 // Check for use of invalid 16-bit registers. Only BX/BP/SI/DI are allowed, 2157 // and then only in non-64-bit modes. Except for DX, which is a special case 2158 // because an unofficial form of in/out instructions uses it. 2159 if (X86MCRegisterClasses[X86::GR16RegClassID].contains(BaseReg) && 2160 (is64BitMode() || (BaseReg != X86::BX && BaseReg != X86::BP && 2161 BaseReg != X86::SI && BaseReg != X86::DI)) && 2162 BaseReg != X86::DX) { 2163 Error(BaseLoc, "invalid 16-bit base register"); 2164 return nullptr; 2165 } 2166 if (BaseReg == 0 && 2167 X86MCRegisterClasses[X86::GR16RegClassID].contains(IndexReg)) { 2168 Error(IndexLoc, "16-bit memory operand may not include only index register"); 2169 return nullptr; 2170 } 2171 2172 StringRef ErrMsg; 2173 if (CheckBaseRegAndIndexRegAndScale(BaseReg, IndexReg, Scale, ErrMsg)) { 2174 Error(BaseLoc, ErrMsg); 2175 return nullptr; 2176 } 2177 2178 if (SegReg || BaseReg || IndexReg) 2179 return X86Operand::CreateMem(getPointerWidth(), SegReg, Disp, BaseReg, 2180 IndexReg, Scale, MemStart, MemEnd); 2181 return X86Operand::CreateMem(getPointerWidth(), Disp, MemStart, MemEnd); 2182 } 2183 2184 bool X86AsmParser::ParseInstruction(ParseInstructionInfo &Info, StringRef Name, 2185 SMLoc NameLoc, OperandVector &Operands) { 2186 MCAsmParser &Parser = getParser(); 2187 InstInfo = &Info; 2188 StringRef PatchedName = Name; 2189 2190 if ((Name.equals("jmp") || Name.equals("jc") || Name.equals("jz")) && 2191 isParsingIntelSyntax() && isParsingInlineAsm()) { 2192 StringRef NextTok = Parser.getTok().getString(); 2193 if (NextTok == "short") { 2194 SMLoc NameEndLoc = 2195 NameLoc.getFromPointer(NameLoc.getPointer() + Name.size()); 2196 // Eat the short keyword 2197 Parser.Lex(); 2198 // MS ignores the short keyword, it determines the jmp type based 2199 // on the distance of the label 2200 InstInfo->AsmRewrites->emplace_back(AOK_Skip, NameEndLoc, 2201 NextTok.size() + 1); 2202 } 2203 } 2204 2205 // FIXME: Hack to recognize setneb as setne. 2206 if (PatchedName.startswith("set") && PatchedName.endswith("b") && 2207 PatchedName != "setb" && PatchedName != "setnb") 2208 PatchedName = PatchedName.substr(0, Name.size()-1); 2209 2210 // FIXME: Hack to recognize cmp<comparison code>{ss,sd,ps,pd}. 2211 if ((PatchedName.startswith("cmp") || PatchedName.startswith("vcmp")) && 2212 (PatchedName.endswith("ss") || PatchedName.endswith("sd") || 2213 PatchedName.endswith("ps") || PatchedName.endswith("pd"))) { 2214 bool IsVCMP = PatchedName[0] == 'v'; 2215 unsigned CCIdx = IsVCMP ? 4 : 3; 2216 unsigned ComparisonCode = StringSwitch<unsigned>( 2217 PatchedName.slice(CCIdx, PatchedName.size() - 2)) 2218 .Case("eq", 0x00) 2219 .Case("eq_oq", 0x00) 2220 .Case("lt", 0x01) 2221 .Case("lt_os", 0x01) 2222 .Case("le", 0x02) 2223 .Case("le_os", 0x02) 2224 .Case("unord", 0x03) 2225 .Case("unord_q", 0x03) 2226 .Case("neq", 0x04) 2227 .Case("neq_uq", 0x04) 2228 .Case("nlt", 0x05) 2229 .Case("nlt_us", 0x05) 2230 .Case("nle", 0x06) 2231 .Case("nle_us", 0x06) 2232 .Case("ord", 0x07) 2233 .Case("ord_q", 0x07) 2234 /* AVX only from here */ 2235 .Case("eq_uq", 0x08) 2236 .Case("nge", 0x09) 2237 .Case("nge_us", 0x09) 2238 .Case("ngt", 0x0A) 2239 .Case("ngt_us", 0x0A) 2240 .Case("false", 0x0B) 2241 .Case("false_oq", 0x0B) 2242 .Case("neq_oq", 0x0C) 2243 .Case("ge", 0x0D) 2244 .Case("ge_os", 0x0D) 2245 .Case("gt", 0x0E) 2246 .Case("gt_os", 0x0E) 2247 .Case("true", 0x0F) 2248 .Case("true_uq", 0x0F) 2249 .Case("eq_os", 0x10) 2250 .Case("lt_oq", 0x11) 2251 .Case("le_oq", 0x12) 2252 .Case("unord_s", 0x13) 2253 .Case("neq_us", 0x14) 2254 .Case("nlt_uq", 0x15) 2255 .Case("nle_uq", 0x16) 2256 .Case("ord_s", 0x17) 2257 .Case("eq_us", 0x18) 2258 .Case("nge_uq", 0x19) 2259 .Case("ngt_uq", 0x1A) 2260 .Case("false_os", 0x1B) 2261 .Case("neq_os", 0x1C) 2262 .Case("ge_oq", 0x1D) 2263 .Case("gt_oq", 0x1E) 2264 .Case("true_us", 0x1F) 2265 .Default(~0U); 2266 if (ComparisonCode != ~0U && (IsVCMP || ComparisonCode < 8)) { 2267 2268 Operands.push_back(X86Operand::CreateToken(PatchedName.slice(0, CCIdx), 2269 NameLoc)); 2270 2271 const MCExpr *ImmOp = MCConstantExpr::create(ComparisonCode, 2272 getParser().getContext()); 2273 Operands.push_back(X86Operand::CreateImm(ImmOp, NameLoc, NameLoc)); 2274 2275 PatchedName = PatchedName.substr(PatchedName.size() - 2); 2276 } 2277 } 2278 2279 // FIXME: Hack to recognize vpcmp<comparison code>{ub,uw,ud,uq,b,w,d,q}. 2280 if (PatchedName.startswith("vpcmp") && 2281 (PatchedName.endswith("b") || PatchedName.endswith("w") || 2282 PatchedName.endswith("d") || PatchedName.endswith("q"))) { 2283 unsigned CCIdx = PatchedName.drop_back().back() == 'u' ? 2 : 1; 2284 unsigned ComparisonCode = StringSwitch<unsigned>( 2285 PatchedName.slice(5, PatchedName.size() - CCIdx)) 2286 .Case("eq", 0x0) // Only allowed on unsigned. Checked below. 2287 .Case("lt", 0x1) 2288 .Case("le", 0x2) 2289 //.Case("false", 0x3) // Not a documented alias. 2290 .Case("neq", 0x4) 2291 .Case("nlt", 0x5) 2292 .Case("nle", 0x6) 2293 //.Case("true", 0x7) // Not a documented alias. 2294 .Default(~0U); 2295 if (ComparisonCode != ~0U && (ComparisonCode != 0 || CCIdx == 2)) { 2296 Operands.push_back(X86Operand::CreateToken("vpcmp", NameLoc)); 2297 2298 const MCExpr *ImmOp = MCConstantExpr::create(ComparisonCode, 2299 getParser().getContext()); 2300 Operands.push_back(X86Operand::CreateImm(ImmOp, NameLoc, NameLoc)); 2301 2302 PatchedName = PatchedName.substr(PatchedName.size() - CCIdx); 2303 } 2304 } 2305 2306 // FIXME: Hack to recognize vpcom<comparison code>{ub,uw,ud,uq,b,w,d,q}. 2307 if (PatchedName.startswith("vpcom") && 2308 (PatchedName.endswith("b") || PatchedName.endswith("w") || 2309 PatchedName.endswith("d") || PatchedName.endswith("q"))) { 2310 unsigned CCIdx = PatchedName.drop_back().back() == 'u' ? 2 : 1; 2311 unsigned ComparisonCode = StringSwitch<unsigned>( 2312 PatchedName.slice(5, PatchedName.size() - CCIdx)) 2313 .Case("lt", 0x0) 2314 .Case("le", 0x1) 2315 .Case("gt", 0x2) 2316 .Case("ge", 0x3) 2317 .Case("eq", 0x4) 2318 .Case("neq", 0x5) 2319 .Case("false", 0x6) 2320 .Case("true", 0x7) 2321 .Default(~0U); 2322 if (ComparisonCode != ~0U) { 2323 Operands.push_back(X86Operand::CreateToken("vpcom", NameLoc)); 2324 2325 const MCExpr *ImmOp = MCConstantExpr::create(ComparisonCode, 2326 getParser().getContext()); 2327 Operands.push_back(X86Operand::CreateImm(ImmOp, NameLoc, NameLoc)); 2328 2329 PatchedName = PatchedName.substr(PatchedName.size() - CCIdx); 2330 } 2331 } 2332 2333 2334 // Determine whether this is an instruction prefix. 2335 // FIXME: 2336 // Enhance prefixes integrity robustness. for example, following forms 2337 // are currently tolerated: 2338 // repz repnz <insn> ; GAS errors for the use of two similar prefixes 2339 // lock addq %rax, %rbx ; Destination operand must be of memory type 2340 // xacquire <insn> ; xacquire must be accompanied by 'lock' 2341 bool isPrefix = StringSwitch<bool>(Name) 2342 .Cases("rex64", "data32", "data16", true) 2343 .Cases("xacquire", "xrelease", true) 2344 .Cases("acquire", "release", isParsingIntelSyntax()) 2345 .Default(false); 2346 2347 auto isLockRepeatPrefix = [](StringRef N) { 2348 return StringSwitch<bool>(N) 2349 .Cases("lock", "rep", "repe", "repz", "repne", "repnz", true) 2350 .Default(false); 2351 }; 2352 2353 bool CurlyAsEndOfStatement = false; 2354 2355 unsigned Flags = X86::IP_NO_PREFIX; 2356 while (isLockRepeatPrefix(Name.lower())) { 2357 unsigned Prefix = 2358 StringSwitch<unsigned>(Name) 2359 .Cases("lock", "lock", X86::IP_HAS_LOCK) 2360 .Cases("rep", "repe", "repz", X86::IP_HAS_REPEAT) 2361 .Cases("repne", "repnz", X86::IP_HAS_REPEAT_NE) 2362 .Default(X86::IP_NO_PREFIX); // Invalid prefix (impossible) 2363 Flags |= Prefix; 2364 Name = Parser.getTok().getString(); 2365 Parser.Lex(); // eat the prefix 2366 // Hack: we could have something like 2367 // "lock; cmpxchg16b $1" or "lock\0A\09incl" or "lock/incl" 2368 while (Name.startswith(";") || Name.startswith("\n") || 2369 Name.startswith("\t") || Name.startswith("/")) { 2370 Name = Parser.getTok().getString(); 2371 Parser.Lex(); // go to next prefix or instr 2372 } 2373 } 2374 2375 if (Flags) 2376 PatchedName = Name; 2377 Operands.push_back(X86Operand::CreateToken(PatchedName, NameLoc)); 2378 2379 // This does the actual operand parsing. Don't parse any more if we have a 2380 // prefix juxtaposed with an operation like "lock incl 4(%rax)", because we 2381 // just want to parse the "lock" as the first instruction and the "incl" as 2382 // the next one. 2383 if (getLexer().isNot(AsmToken::EndOfStatement) && !isPrefix) { 2384 // Parse '*' modifier. 2385 if (getLexer().is(AsmToken::Star)) 2386 Operands.push_back(X86Operand::CreateToken("*", consumeToken())); 2387 2388 // Read the operands. 2389 while(1) { 2390 if (std::unique_ptr<X86Operand> Op = ParseOperand()) { 2391 Operands.push_back(std::move(Op)); 2392 if (HandleAVX512Operand(Operands, *Operands.back())) 2393 return true; 2394 } else { 2395 return true; 2396 } 2397 // check for comma and eat it 2398 if (getLexer().is(AsmToken::Comma)) 2399 Parser.Lex(); 2400 else 2401 break; 2402 } 2403 2404 // In MS inline asm curly braces mark the beginning/end of a block, 2405 // therefore they should be interepreted as end of statement 2406 CurlyAsEndOfStatement = 2407 isParsingIntelSyntax() && isParsingInlineAsm() && 2408 (getLexer().is(AsmToken::LCurly) || getLexer().is(AsmToken::RCurly)); 2409 if (getLexer().isNot(AsmToken::EndOfStatement) && !CurlyAsEndOfStatement) 2410 return TokError("unexpected token in argument list"); 2411 } 2412 2413 // Consume the EndOfStatement or the prefix separator Slash 2414 if (getLexer().is(AsmToken::EndOfStatement) || 2415 (isPrefix && getLexer().is(AsmToken::Slash))) 2416 Parser.Lex(); 2417 else if (CurlyAsEndOfStatement) 2418 // Add an actual EndOfStatement before the curly brace 2419 Info.AsmRewrites->emplace_back(AOK_EndOfStatement, 2420 getLexer().getTok().getLoc(), 0); 2421 2422 // This is for gas compatibility and cannot be done in td. 2423 // Adding "p" for some floating point with no argument. 2424 // For example: fsub --> fsubp 2425 bool IsFp = 2426 Name == "fsub" || Name == "fdiv" || Name == "fsubr" || Name == "fdivr"; 2427 if (IsFp && Operands.size() == 1) { 2428 const char *Repl = StringSwitch<const char *>(Name) 2429 .Case("fsub", "fsubp") 2430 .Case("fdiv", "fdivp") 2431 .Case("fsubr", "fsubrp") 2432 .Case("fdivr", "fdivrp"); 2433 static_cast<X86Operand &>(*Operands[0]).setTokenValue(Repl); 2434 } 2435 2436 // Moving a 32 or 16 bit value into a segment register has the same 2437 // behavior. Modify such instructions to always take shorter form. 2438 if ((Name == "mov" || Name == "movw" || Name == "movl") && 2439 (Operands.size() == 3)) { 2440 X86Operand &Op1 = (X86Operand &)*Operands[1]; 2441 X86Operand &Op2 = (X86Operand &)*Operands[2]; 2442 SMLoc Loc = Op1.getEndLoc(); 2443 if (Op1.isReg() && Op2.isReg() && 2444 X86MCRegisterClasses[X86::SEGMENT_REGRegClassID].contains( 2445 Op2.getReg()) && 2446 (X86MCRegisterClasses[X86::GR16RegClassID].contains(Op1.getReg()) || 2447 X86MCRegisterClasses[X86::GR32RegClassID].contains(Op1.getReg()))) { 2448 // Change instruction name to match new instruction. 2449 if (Name != "mov" && Name[3] == (is16BitMode() ? 'l' : 'w')) { 2450 Name = is16BitMode() ? "movw" : "movl"; 2451 Operands[0] = X86Operand::CreateToken(Name, NameLoc); 2452 } 2453 // Select the correct equivalent 16-/32-bit source register. 2454 unsigned Reg = 2455 getX86SubSuperRegisterOrZero(Op1.getReg(), is16BitMode() ? 16 : 32); 2456 Operands[1] = X86Operand::CreateReg(Reg, Loc, Loc); 2457 } 2458 } 2459 2460 // This is a terrible hack to handle "out[s]?[bwl]? %al, (%dx)" -> 2461 // "outb %al, %dx". Out doesn't take a memory form, but this is a widely 2462 // documented form in various unofficial manuals, so a lot of code uses it. 2463 if ((Name == "outb" || Name == "outsb" || Name == "outw" || Name == "outsw" || 2464 Name == "outl" || Name == "outsl" || Name == "out" || Name == "outs") && 2465 Operands.size() == 3) { 2466 X86Operand &Op = (X86Operand &)*Operands.back(); 2467 if (Op.isMem() && Op.Mem.SegReg == 0 && 2468 isa<MCConstantExpr>(Op.Mem.Disp) && 2469 cast<MCConstantExpr>(Op.Mem.Disp)->getValue() == 0 && 2470 Op.Mem.BaseReg == MatchRegisterName("dx") && Op.Mem.IndexReg == 0) { 2471 SMLoc Loc = Op.getEndLoc(); 2472 Operands.back() = X86Operand::CreateReg(Op.Mem.BaseReg, Loc, Loc); 2473 } 2474 } 2475 // Same hack for "in[s]?[bwl]? (%dx), %al" -> "inb %dx, %al". 2476 if ((Name == "inb" || Name == "insb" || Name == "inw" || Name == "insw" || 2477 Name == "inl" || Name == "insl" || Name == "in" || Name == "ins") && 2478 Operands.size() == 3) { 2479 X86Operand &Op = (X86Operand &)*Operands[1]; 2480 if (Op.isMem() && Op.Mem.SegReg == 0 && 2481 isa<MCConstantExpr>(Op.Mem.Disp) && 2482 cast<MCConstantExpr>(Op.Mem.Disp)->getValue() == 0 && 2483 Op.Mem.BaseReg == MatchRegisterName("dx") && Op.Mem.IndexReg == 0) { 2484 SMLoc Loc = Op.getEndLoc(); 2485 Operands[1] = X86Operand::CreateReg(Op.Mem.BaseReg, Loc, Loc); 2486 } 2487 } 2488 2489 SmallVector<std::unique_ptr<MCParsedAsmOperand>, 2> TmpOperands; 2490 bool HadVerifyError = false; 2491 2492 // Append default arguments to "ins[bwld]" 2493 if (Name.startswith("ins") && 2494 (Operands.size() == 1 || Operands.size() == 3) && 2495 (Name == "insb" || Name == "insw" || Name == "insl" || Name == "insd" || 2496 Name == "ins")) { 2497 2498 AddDefaultSrcDestOperands(TmpOperands, 2499 X86Operand::CreateReg(X86::DX, NameLoc, NameLoc), 2500 DefaultMemDIOperand(NameLoc)); 2501 HadVerifyError = VerifyAndAdjustOperands(Operands, TmpOperands); 2502 } 2503 2504 // Append default arguments to "outs[bwld]" 2505 if (Name.startswith("outs") && 2506 (Operands.size() == 1 || Operands.size() == 3) && 2507 (Name == "outsb" || Name == "outsw" || Name == "outsl" || 2508 Name == "outsd" || Name == "outs")) { 2509 AddDefaultSrcDestOperands(TmpOperands, DefaultMemSIOperand(NameLoc), 2510 X86Operand::CreateReg(X86::DX, NameLoc, NameLoc)); 2511 HadVerifyError = VerifyAndAdjustOperands(Operands, TmpOperands); 2512 } 2513 2514 // Transform "lods[bwlq]" into "lods[bwlq] ($SIREG)" for appropriate 2515 // values of $SIREG according to the mode. It would be nice if this 2516 // could be achieved with InstAlias in the tables. 2517 if (Name.startswith("lods") && 2518 (Operands.size() == 1 || Operands.size() == 2) && 2519 (Name == "lods" || Name == "lodsb" || Name == "lodsw" || 2520 Name == "lodsl" || Name == "lodsd" || Name == "lodsq")) { 2521 TmpOperands.push_back(DefaultMemSIOperand(NameLoc)); 2522 HadVerifyError = VerifyAndAdjustOperands(Operands, TmpOperands); 2523 } 2524 2525 // Transform "stos[bwlq]" into "stos[bwlq] ($DIREG)" for appropriate 2526 // values of $DIREG according to the mode. It would be nice if this 2527 // could be achieved with InstAlias in the tables. 2528 if (Name.startswith("stos") && 2529 (Operands.size() == 1 || Operands.size() == 2) && 2530 (Name == "stos" || Name == "stosb" || Name == "stosw" || 2531 Name == "stosl" || Name == "stosd" || Name == "stosq")) { 2532 TmpOperands.push_back(DefaultMemDIOperand(NameLoc)); 2533 HadVerifyError = VerifyAndAdjustOperands(Operands, TmpOperands); 2534 } 2535 2536 // Transform "scas[bwlq]" into "scas[bwlq] ($DIREG)" for appropriate 2537 // values of $DIREG according to the mode. It would be nice if this 2538 // could be achieved with InstAlias in the tables. 2539 if (Name.startswith("scas") && 2540 (Operands.size() == 1 || Operands.size() == 2) && 2541 (Name == "scas" || Name == "scasb" || Name == "scasw" || 2542 Name == "scasl" || Name == "scasd" || Name == "scasq")) { 2543 TmpOperands.push_back(DefaultMemDIOperand(NameLoc)); 2544 HadVerifyError = VerifyAndAdjustOperands(Operands, TmpOperands); 2545 } 2546 2547 // Add default SI and DI operands to "cmps[bwlq]". 2548 if (Name.startswith("cmps") && 2549 (Operands.size() == 1 || Operands.size() == 3) && 2550 (Name == "cmps" || Name == "cmpsb" || Name == "cmpsw" || 2551 Name == "cmpsl" || Name == "cmpsd" || Name == "cmpsq")) { 2552 AddDefaultSrcDestOperands(TmpOperands, DefaultMemDIOperand(NameLoc), 2553 DefaultMemSIOperand(NameLoc)); 2554 HadVerifyError = VerifyAndAdjustOperands(Operands, TmpOperands); 2555 } 2556 2557 // Add default SI and DI operands to "movs[bwlq]". 2558 if (((Name.startswith("movs") && 2559 (Name == "movs" || Name == "movsb" || Name == "movsw" || 2560 Name == "movsl" || Name == "movsd" || Name == "movsq")) || 2561 (Name.startswith("smov") && 2562 (Name == "smov" || Name == "smovb" || Name == "smovw" || 2563 Name == "smovl" || Name == "smovd" || Name == "smovq"))) && 2564 (Operands.size() == 1 || Operands.size() == 3)) { 2565 if (Name == "movsd" && Operands.size() == 1 && !isParsingIntelSyntax()) 2566 Operands.back() = X86Operand::CreateToken("movsl", NameLoc); 2567 AddDefaultSrcDestOperands(TmpOperands, DefaultMemSIOperand(NameLoc), 2568 DefaultMemDIOperand(NameLoc)); 2569 HadVerifyError = VerifyAndAdjustOperands(Operands, TmpOperands); 2570 } 2571 2572 // Check if we encountered an error for one the string insturctions 2573 if (HadVerifyError) { 2574 return HadVerifyError; 2575 } 2576 2577 // FIXME: Hack to handle recognize s{hr,ar,hl} $1, <op>. Canonicalize to 2578 // "shift <op>". 2579 if ((Name.startswith("shr") || Name.startswith("sar") || 2580 Name.startswith("shl") || Name.startswith("sal") || 2581 Name.startswith("rcl") || Name.startswith("rcr") || 2582 Name.startswith("rol") || Name.startswith("ror")) && 2583 Operands.size() == 3) { 2584 if (isParsingIntelSyntax()) { 2585 // Intel syntax 2586 X86Operand &Op1 = static_cast<X86Operand &>(*Operands[2]); 2587 if (Op1.isImm() && isa<MCConstantExpr>(Op1.getImm()) && 2588 cast<MCConstantExpr>(Op1.getImm())->getValue() == 1) 2589 Operands.pop_back(); 2590 } else { 2591 X86Operand &Op1 = static_cast<X86Operand &>(*Operands[1]); 2592 if (Op1.isImm() && isa<MCConstantExpr>(Op1.getImm()) && 2593 cast<MCConstantExpr>(Op1.getImm())->getValue() == 1) 2594 Operands.erase(Operands.begin() + 1); 2595 } 2596 } 2597 2598 // Transforms "int $3" into "int3" as a size optimization. We can't write an 2599 // instalias with an immediate operand yet. 2600 if (Name == "int" && Operands.size() == 2) { 2601 X86Operand &Op1 = static_cast<X86Operand &>(*Operands[1]); 2602 if (Op1.isImm()) 2603 if (auto *CE = dyn_cast<MCConstantExpr>(Op1.getImm())) 2604 if (CE->getValue() == 3) { 2605 Operands.erase(Operands.begin() + 1); 2606 static_cast<X86Operand &>(*Operands[0]).setTokenValue("int3"); 2607 } 2608 } 2609 2610 // Transforms "xlat mem8" into "xlatb" 2611 if ((Name == "xlat" || Name == "xlatb") && Operands.size() == 2) { 2612 X86Operand &Op1 = static_cast<X86Operand &>(*Operands[1]); 2613 if (Op1.isMem8()) { 2614 Warning(Op1.getStartLoc(), "memory operand is only for determining the " 2615 "size, (R|E)BX will be used for the location"); 2616 Operands.pop_back(); 2617 static_cast<X86Operand &>(*Operands[0]).setTokenValue("xlatb"); 2618 } 2619 } 2620 2621 if (Flags) 2622 Operands.push_back(X86Operand::CreatePrefix(Flags, NameLoc, NameLoc)); 2623 return false; 2624 } 2625 2626 bool X86AsmParser::processInstruction(MCInst &Inst, const OperandVector &Ops) { 2627 return false; 2628 } 2629 2630 static const char *getSubtargetFeatureName(uint64_t Val); 2631 2632 void X86AsmParser::EmitInstruction(MCInst &Inst, OperandVector &Operands, 2633 MCStreamer &Out) { 2634 Instrumentation->InstrumentAndEmitInstruction(Inst, Operands, getContext(), 2635 MII, Out); 2636 } 2637 2638 bool X86AsmParser::MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode, 2639 OperandVector &Operands, 2640 MCStreamer &Out, uint64_t &ErrorInfo, 2641 bool MatchingInlineAsm) { 2642 if (isParsingIntelSyntax()) 2643 return MatchAndEmitIntelInstruction(IDLoc, Opcode, Operands, Out, ErrorInfo, 2644 MatchingInlineAsm); 2645 return MatchAndEmitATTInstruction(IDLoc, Opcode, Operands, Out, ErrorInfo, 2646 MatchingInlineAsm); 2647 } 2648 2649 void X86AsmParser::MatchFPUWaitAlias(SMLoc IDLoc, X86Operand &Op, 2650 OperandVector &Operands, MCStreamer &Out, 2651 bool MatchingInlineAsm) { 2652 // FIXME: This should be replaced with a real .td file alias mechanism. 2653 // Also, MatchInstructionImpl should actually *do* the EmitInstruction 2654 // call. 2655 const char *Repl = StringSwitch<const char *>(Op.getToken()) 2656 .Case("finit", "fninit") 2657 .Case("fsave", "fnsave") 2658 .Case("fstcw", "fnstcw") 2659 .Case("fstcww", "fnstcw") 2660 .Case("fstenv", "fnstenv") 2661 .Case("fstsw", "fnstsw") 2662 .Case("fstsww", "fnstsw") 2663 .Case("fclex", "fnclex") 2664 .Default(nullptr); 2665 if (Repl) { 2666 MCInst Inst; 2667 Inst.setOpcode(X86::WAIT); 2668 Inst.setLoc(IDLoc); 2669 if (!MatchingInlineAsm) 2670 EmitInstruction(Inst, Operands, Out); 2671 Operands[0] = X86Operand::CreateToken(Repl, IDLoc); 2672 } 2673 } 2674 2675 bool X86AsmParser::ErrorMissingFeature(SMLoc IDLoc, uint64_t ErrorInfo, 2676 bool MatchingInlineAsm) { 2677 assert(ErrorInfo && "Unknown missing feature!"); 2678 SmallString<126> Msg; 2679 raw_svector_ostream OS(Msg); 2680 OS << "instruction requires:"; 2681 uint64_t Mask = 1; 2682 for (unsigned i = 0; i < (sizeof(ErrorInfo)*8-1); ++i) { 2683 if (ErrorInfo & Mask) 2684 OS << ' ' << getSubtargetFeatureName(ErrorInfo & Mask); 2685 Mask <<= 1; 2686 } 2687 return Error(IDLoc, OS.str(), SMRange(), MatchingInlineAsm); 2688 } 2689 2690 static unsigned getPrefixes(OperandVector &Operands) { 2691 unsigned Result = 0; 2692 X86Operand &Prefix = static_cast<X86Operand &>(*Operands.back()); 2693 if (Prefix.isPrefix()) { 2694 Result = Prefix.getPrefix(); 2695 Operands.pop_back(); 2696 } 2697 return Result; 2698 } 2699 2700 bool X86AsmParser::MatchAndEmitATTInstruction(SMLoc IDLoc, unsigned &Opcode, 2701 OperandVector &Operands, 2702 MCStreamer &Out, 2703 uint64_t &ErrorInfo, 2704 bool MatchingInlineAsm) { 2705 assert(!Operands.empty() && "Unexpect empty operand list!"); 2706 X86Operand &Op = static_cast<X86Operand &>(*Operands[0]); 2707 assert(Op.isToken() && "Leading operand should always be a mnemonic!"); 2708 SMRange EmptyRange = None; 2709 2710 // First, handle aliases that expand to multiple instructions. 2711 MatchFPUWaitAlias(IDLoc, Op, Operands, Out, MatchingInlineAsm); 2712 2713 bool WasOriginallyInvalidOperand = false; 2714 unsigned Prefixes = getPrefixes(Operands); 2715 2716 MCInst Inst; 2717 2718 if (Prefixes) 2719 Inst.setFlags(Prefixes); 2720 2721 // First, try a direct match. 2722 switch (MatchInstruction(Operands, Inst, ErrorInfo, MatchingInlineAsm, 2723 isParsingIntelSyntax())) { 2724 default: llvm_unreachable("Unexpected match result!"); 2725 case Match_Success: 2726 // Some instructions need post-processing to, for example, tweak which 2727 // encoding is selected. Loop on it while changes happen so the 2728 // individual transformations can chain off each other. 2729 if (!MatchingInlineAsm) 2730 while (processInstruction(Inst, Operands)) 2731 ; 2732 2733 Inst.setLoc(IDLoc); 2734 if (!MatchingInlineAsm) 2735 EmitInstruction(Inst, Operands, Out); 2736 Opcode = Inst.getOpcode(); 2737 return false; 2738 case Match_MissingFeature: 2739 return ErrorMissingFeature(IDLoc, ErrorInfo, MatchingInlineAsm); 2740 case Match_InvalidOperand: 2741 WasOriginallyInvalidOperand = true; 2742 break; 2743 case Match_MnemonicFail: 2744 break; 2745 } 2746 2747 // FIXME: Ideally, we would only attempt suffix matches for things which are 2748 // valid prefixes, and we could just infer the right unambiguous 2749 // type. However, that requires substantially more matcher support than the 2750 // following hack. 2751 2752 // Change the operand to point to a temporary token. 2753 StringRef Base = Op.getToken(); 2754 SmallString<16> Tmp; 2755 Tmp += Base; 2756 Tmp += ' '; 2757 Op.setTokenValue(Tmp); 2758 2759 // If this instruction starts with an 'f', then it is a floating point stack 2760 // instruction. These come in up to three forms for 32-bit, 64-bit, and 2761 // 80-bit floating point, which use the suffixes s,l,t respectively. 2762 // 2763 // Otherwise, we assume that this may be an integer instruction, which comes 2764 // in 8/16/32/64-bit forms using the b,w,l,q suffixes respectively. 2765 const char *Suffixes = Base[0] != 'f' ? "bwlq" : "slt\0"; 2766 2767 // Check for the various suffix matches. 2768 uint64_t ErrorInfoIgnore; 2769 uint64_t ErrorInfoMissingFeature = 0; // Init suppresses compiler warnings. 2770 unsigned Match[4]; 2771 2772 for (unsigned I = 0, E = array_lengthof(Match); I != E; ++I) { 2773 Tmp.back() = Suffixes[I]; 2774 Match[I] = MatchInstruction(Operands, Inst, ErrorInfoIgnore, 2775 MatchingInlineAsm, isParsingIntelSyntax()); 2776 // If this returned as a missing feature failure, remember that. 2777 if (Match[I] == Match_MissingFeature) 2778 ErrorInfoMissingFeature = ErrorInfoIgnore; 2779 } 2780 2781 // Restore the old token. 2782 Op.setTokenValue(Base); 2783 2784 // If exactly one matched, then we treat that as a successful match (and the 2785 // instruction will already have been filled in correctly, since the failing 2786 // matches won't have modified it). 2787 unsigned NumSuccessfulMatches = 2788 std::count(std::begin(Match), std::end(Match), Match_Success); 2789 if (NumSuccessfulMatches == 1) { 2790 Inst.setLoc(IDLoc); 2791 if (!MatchingInlineAsm) 2792 EmitInstruction(Inst, Operands, Out); 2793 Opcode = Inst.getOpcode(); 2794 return false; 2795 } 2796 2797 // Otherwise, the match failed, try to produce a decent error message. 2798 2799 // If we had multiple suffix matches, then identify this as an ambiguous 2800 // match. 2801 if (NumSuccessfulMatches > 1) { 2802 char MatchChars[4]; 2803 unsigned NumMatches = 0; 2804 for (unsigned I = 0, E = array_lengthof(Match); I != E; ++I) 2805 if (Match[I] == Match_Success) 2806 MatchChars[NumMatches++] = Suffixes[I]; 2807 2808 SmallString<126> Msg; 2809 raw_svector_ostream OS(Msg); 2810 OS << "ambiguous instructions require an explicit suffix (could be "; 2811 for (unsigned i = 0; i != NumMatches; ++i) { 2812 if (i != 0) 2813 OS << ", "; 2814 if (i + 1 == NumMatches) 2815 OS << "or "; 2816 OS << "'" << Base << MatchChars[i] << "'"; 2817 } 2818 OS << ")"; 2819 Error(IDLoc, OS.str(), EmptyRange, MatchingInlineAsm); 2820 return true; 2821 } 2822 2823 // Okay, we know that none of the variants matched successfully. 2824 2825 // If all of the instructions reported an invalid mnemonic, then the original 2826 // mnemonic was invalid. 2827 if (std::count(std::begin(Match), std::end(Match), Match_MnemonicFail) == 4) { 2828 if (!WasOriginallyInvalidOperand) { 2829 return Error(IDLoc, "invalid instruction mnemonic '" + Base + "'", 2830 Op.getLocRange(), MatchingInlineAsm); 2831 } 2832 2833 // Recover location info for the operand if we know which was the problem. 2834 if (ErrorInfo != ~0ULL) { 2835 if (ErrorInfo >= Operands.size()) 2836 return Error(IDLoc, "too few operands for instruction", EmptyRange, 2837 MatchingInlineAsm); 2838 2839 X86Operand &Operand = (X86Operand &)*Operands[ErrorInfo]; 2840 if (Operand.getStartLoc().isValid()) { 2841 SMRange OperandRange = Operand.getLocRange(); 2842 return Error(Operand.getStartLoc(), "invalid operand for instruction", 2843 OperandRange, MatchingInlineAsm); 2844 } 2845 } 2846 2847 return Error(IDLoc, "invalid operand for instruction", EmptyRange, 2848 MatchingInlineAsm); 2849 } 2850 2851 // If one instruction matched with a missing feature, report this as a 2852 // missing feature. 2853 if (std::count(std::begin(Match), std::end(Match), 2854 Match_MissingFeature) == 1) { 2855 ErrorInfo = ErrorInfoMissingFeature; 2856 return ErrorMissingFeature(IDLoc, ErrorInfoMissingFeature, 2857 MatchingInlineAsm); 2858 } 2859 2860 // If one instruction matched with an invalid operand, report this as an 2861 // operand failure. 2862 if (std::count(std::begin(Match), std::end(Match), 2863 Match_InvalidOperand) == 1) { 2864 return Error(IDLoc, "invalid operand for instruction", EmptyRange, 2865 MatchingInlineAsm); 2866 } 2867 2868 // If all of these were an outright failure, report it in a useless way. 2869 Error(IDLoc, "unknown use of instruction mnemonic without a size suffix", 2870 EmptyRange, MatchingInlineAsm); 2871 return true; 2872 } 2873 2874 bool X86AsmParser::MatchAndEmitIntelInstruction(SMLoc IDLoc, unsigned &Opcode, 2875 OperandVector &Operands, 2876 MCStreamer &Out, 2877 uint64_t &ErrorInfo, 2878 bool MatchingInlineAsm) { 2879 assert(!Operands.empty() && "Unexpect empty operand list!"); 2880 X86Operand &Op = static_cast<X86Operand &>(*Operands[0]); 2881 assert(Op.isToken() && "Leading operand should always be a mnemonic!"); 2882 StringRef Mnemonic = Op.getToken(); 2883 SMRange EmptyRange = None; 2884 StringRef Base = Op.getToken(); 2885 unsigned Prefixes = getPrefixes(Operands); 2886 2887 // First, handle aliases that expand to multiple instructions. 2888 MatchFPUWaitAlias(IDLoc, Op, Operands, Out, MatchingInlineAsm); 2889 2890 MCInst Inst; 2891 2892 if (Prefixes) 2893 Inst.setFlags(Prefixes); 2894 2895 // Find one unsized memory operand, if present. 2896 X86Operand *UnsizedMemOp = nullptr; 2897 for (const auto &Op : Operands) { 2898 X86Operand *X86Op = static_cast<X86Operand *>(Op.get()); 2899 if (X86Op->isMemUnsized()) { 2900 UnsizedMemOp = X86Op; 2901 // Have we found an unqualified memory operand, 2902 // break. IA allows only one memory operand. 2903 break; 2904 } 2905 } 2906 2907 // Allow some instructions to have implicitly pointer-sized operands. This is 2908 // compatible with gas. 2909 if (UnsizedMemOp) { 2910 static const char *const PtrSizedInstrs[] = {"call", "jmp", "push"}; 2911 for (const char *Instr : PtrSizedInstrs) { 2912 if (Mnemonic == Instr) { 2913 UnsizedMemOp->Mem.Size = getPointerWidth(); 2914 break; 2915 } 2916 } 2917 } 2918 2919 SmallVector<unsigned, 8> Match; 2920 uint64_t ErrorInfoMissingFeature = 0; 2921 2922 // If unsized push has immediate operand we should default the default pointer 2923 // size for the size. 2924 if (Mnemonic == "push" && Operands.size() == 2) { 2925 auto *X86Op = static_cast<X86Operand *>(Operands[1].get()); 2926 if (X86Op->isImm()) { 2927 // If it's not a constant fall through and let remainder take care of it. 2928 const auto *CE = dyn_cast<MCConstantExpr>(X86Op->getImm()); 2929 unsigned Size = getPointerWidth(); 2930 if (CE && 2931 (isIntN(Size, CE->getValue()) || isUIntN(Size, CE->getValue()))) { 2932 SmallString<16> Tmp; 2933 Tmp += Base; 2934 Tmp += (is64BitMode()) 2935 ? "q" 2936 : (is32BitMode()) ? "l" : (is16BitMode()) ? "w" : " "; 2937 Op.setTokenValue(Tmp); 2938 // Do match in ATT mode to allow explicit suffix usage. 2939 Match.push_back(MatchInstruction(Operands, Inst, ErrorInfo, 2940 MatchingInlineAsm, 2941 false /*isParsingIntelSyntax()*/)); 2942 Op.setTokenValue(Base); 2943 } 2944 } 2945 } 2946 2947 // If an unsized memory operand is present, try to match with each memory 2948 // operand size. In Intel assembly, the size is not part of the instruction 2949 // mnemonic. 2950 if (UnsizedMemOp && UnsizedMemOp->isMemUnsized()) { 2951 static const unsigned MopSizes[] = {8, 16, 32, 64, 80, 128, 256, 512}; 2952 for (unsigned Size : MopSizes) { 2953 UnsizedMemOp->Mem.Size = Size; 2954 uint64_t ErrorInfoIgnore; 2955 unsigned LastOpcode = Inst.getOpcode(); 2956 unsigned M = MatchInstruction(Operands, Inst, ErrorInfoIgnore, 2957 MatchingInlineAsm, isParsingIntelSyntax()); 2958 if (Match.empty() || LastOpcode != Inst.getOpcode()) 2959 Match.push_back(M); 2960 2961 // If this returned as a missing feature failure, remember that. 2962 if (Match.back() == Match_MissingFeature) 2963 ErrorInfoMissingFeature = ErrorInfoIgnore; 2964 } 2965 2966 // Restore the size of the unsized memory operand if we modified it. 2967 UnsizedMemOp->Mem.Size = 0; 2968 } 2969 2970 // If we haven't matched anything yet, this is not a basic integer or FPU 2971 // operation. There shouldn't be any ambiguity in our mnemonic table, so try 2972 // matching with the unsized operand. 2973 if (Match.empty()) { 2974 Match.push_back(MatchInstruction( 2975 Operands, Inst, ErrorInfo, MatchingInlineAsm, isParsingIntelSyntax())); 2976 // If this returned as a missing feature failure, remember that. 2977 if (Match.back() == Match_MissingFeature) 2978 ErrorInfoMissingFeature = ErrorInfo; 2979 } 2980 2981 // Restore the size of the unsized memory operand if we modified it. 2982 if (UnsizedMemOp) 2983 UnsizedMemOp->Mem.Size = 0; 2984 2985 // If it's a bad mnemonic, all results will be the same. 2986 if (Match.back() == Match_MnemonicFail) { 2987 return Error(IDLoc, "invalid instruction mnemonic '" + Mnemonic + "'", 2988 Op.getLocRange(), MatchingInlineAsm); 2989 } 2990 2991 unsigned NumSuccessfulMatches = 2992 std::count(std::begin(Match), std::end(Match), Match_Success); 2993 2994 // If matching was ambiguous and we had size information from the frontend, 2995 // try again with that. This handles cases like "movxz eax, m8/m16". 2996 if (UnsizedMemOp && NumSuccessfulMatches > 1 && 2997 UnsizedMemOp->getMemFrontendSize()) { 2998 UnsizedMemOp->Mem.Size = UnsizedMemOp->getMemFrontendSize(); 2999 unsigned M = MatchInstruction( 3000 Operands, Inst, ErrorInfo, MatchingInlineAsm, isParsingIntelSyntax()); 3001 if (M == Match_Success) 3002 NumSuccessfulMatches = 1; 3003 3004 // Add a rewrite that encodes the size information we used from the 3005 // frontend. 3006 InstInfo->AsmRewrites->emplace_back( 3007 AOK_SizeDirective, UnsizedMemOp->getStartLoc(), 3008 /*Len=*/0, UnsizedMemOp->getMemFrontendSize()); 3009 } 3010 3011 // If exactly one matched, then we treat that as a successful match (and the 3012 // instruction will already have been filled in correctly, since the failing 3013 // matches won't have modified it). 3014 if (NumSuccessfulMatches == 1) { 3015 // Some instructions need post-processing to, for example, tweak which 3016 // encoding is selected. Loop on it while changes happen so the individual 3017 // transformations can chain off each other. 3018 if (!MatchingInlineAsm) 3019 while (processInstruction(Inst, Operands)) 3020 ; 3021 Inst.setLoc(IDLoc); 3022 if (!MatchingInlineAsm) 3023 EmitInstruction(Inst, Operands, Out); 3024 Opcode = Inst.getOpcode(); 3025 return false; 3026 } else if (NumSuccessfulMatches > 1) { 3027 assert(UnsizedMemOp && 3028 "multiple matches only possible with unsized memory operands"); 3029 return Error(UnsizedMemOp->getStartLoc(), 3030 "ambiguous operand size for instruction '" + Mnemonic + "\'", 3031 UnsizedMemOp->getLocRange()); 3032 } 3033 3034 // If one instruction matched with a missing feature, report this as a 3035 // missing feature. 3036 if (std::count(std::begin(Match), std::end(Match), 3037 Match_MissingFeature) == 1) { 3038 ErrorInfo = ErrorInfoMissingFeature; 3039 return ErrorMissingFeature(IDLoc, ErrorInfoMissingFeature, 3040 MatchingInlineAsm); 3041 } 3042 3043 // If one instruction matched with an invalid operand, report this as an 3044 // operand failure. 3045 if (std::count(std::begin(Match), std::end(Match), 3046 Match_InvalidOperand) == 1) { 3047 return Error(IDLoc, "invalid operand for instruction", EmptyRange, 3048 MatchingInlineAsm); 3049 } 3050 3051 // If all of these were an outright failure, report it in a useless way. 3052 return Error(IDLoc, "unknown instruction mnemonic", EmptyRange, 3053 MatchingInlineAsm); 3054 } 3055 3056 bool X86AsmParser::OmitRegisterFromClobberLists(unsigned RegNo) { 3057 return X86MCRegisterClasses[X86::SEGMENT_REGRegClassID].contains(RegNo); 3058 } 3059 3060 bool X86AsmParser::ParseDirective(AsmToken DirectiveID) { 3061 MCAsmParser &Parser = getParser(); 3062 StringRef IDVal = DirectiveID.getIdentifier(); 3063 if (IDVal == ".word") 3064 return ParseDirectiveWord(2, DirectiveID.getLoc()); 3065 else if (IDVal.startswith(".code")) 3066 return ParseDirectiveCode(IDVal, DirectiveID.getLoc()); 3067 else if (IDVal.startswith(".att_syntax")) { 3068 getParser().setParsingInlineAsm(false); 3069 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3070 if (Parser.getTok().getString() == "prefix") 3071 Parser.Lex(); 3072 else if (Parser.getTok().getString() == "noprefix") 3073 return Error(DirectiveID.getLoc(), "'.att_syntax noprefix' is not " 3074 "supported: registers must have a " 3075 "'%' prefix in .att_syntax"); 3076 } 3077 getParser().setAssemblerDialect(0); 3078 return false; 3079 } else if (IDVal.startswith(".intel_syntax")) { 3080 getParser().setAssemblerDialect(1); 3081 getParser().setParsingInlineAsm(true); 3082 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3083 if (Parser.getTok().getString() == "noprefix") 3084 Parser.Lex(); 3085 else if (Parser.getTok().getString() == "prefix") 3086 return Error(DirectiveID.getLoc(), "'.intel_syntax prefix' is not " 3087 "supported: registers must not have " 3088 "a '%' prefix in .intel_syntax"); 3089 } 3090 return false; 3091 } else if (IDVal == ".even") 3092 return parseDirectiveEven(DirectiveID.getLoc()); 3093 else if (IDVal == ".cv_fpo_proc") 3094 return parseDirectiveFPOProc(DirectiveID.getLoc()); 3095 else if (IDVal == ".cv_fpo_setframe") 3096 return parseDirectiveFPOSetFrame(DirectiveID.getLoc()); 3097 else if (IDVal == ".cv_fpo_pushreg") 3098 return parseDirectiveFPOPushReg(DirectiveID.getLoc()); 3099 else if (IDVal == ".cv_fpo_stackalloc") 3100 return parseDirectiveFPOStackAlloc(DirectiveID.getLoc()); 3101 else if (IDVal == ".cv_fpo_endprologue") 3102 return parseDirectiveFPOEndPrologue(DirectiveID.getLoc()); 3103 else if (IDVal == ".cv_fpo_endproc") 3104 return parseDirectiveFPOEndProc(DirectiveID.getLoc()); 3105 3106 return true; 3107 } 3108 3109 /// parseDirectiveEven 3110 /// ::= .even 3111 bool X86AsmParser::parseDirectiveEven(SMLoc L) { 3112 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3113 TokError("unexpected token in directive"); 3114 return false; 3115 } 3116 const MCSection *Section = getStreamer().getCurrentSectionOnly(); 3117 if (!Section) { 3118 getStreamer().InitSections(false); 3119 Section = getStreamer().getCurrentSectionOnly(); 3120 } 3121 if (Section->UseCodeAlign()) 3122 getStreamer().EmitCodeAlignment(2, 0); 3123 else 3124 getStreamer().EmitValueToAlignment(2, 0, 1, 0); 3125 return false; 3126 } 3127 /// ParseDirectiveWord 3128 /// ::= .word [ expression (, expression)* ] 3129 bool X86AsmParser::ParseDirectiveWord(unsigned Size, SMLoc L) { 3130 MCAsmParser &Parser = getParser(); 3131 if (getLexer().isNot(AsmToken::EndOfStatement)) { 3132 for (;;) { 3133 const MCExpr *Value; 3134 SMLoc ExprLoc = getLexer().getLoc(); 3135 if (getParser().parseExpression(Value)) 3136 return false; 3137 3138 if (const auto *MCE = dyn_cast<MCConstantExpr>(Value)) { 3139 assert(Size <= 8 && "Invalid size"); 3140 uint64_t IntValue = MCE->getValue(); 3141 if (!isUIntN(8 * Size, IntValue) && !isIntN(8 * Size, IntValue)) 3142 return Error(ExprLoc, "literal value out of range for directive"); 3143 getStreamer().EmitIntValue(IntValue, Size); 3144 } else { 3145 getStreamer().EmitValue(Value, Size, ExprLoc); 3146 } 3147 3148 if (getLexer().is(AsmToken::EndOfStatement)) 3149 break; 3150 3151 // FIXME: Improve diagnostic. 3152 if (getLexer().isNot(AsmToken::Comma)) { 3153 Error(L, "unexpected token in directive"); 3154 return false; 3155 } 3156 Parser.Lex(); 3157 } 3158 } 3159 3160 Parser.Lex(); 3161 return false; 3162 } 3163 3164 /// ParseDirectiveCode 3165 /// ::= .code16 | .code32 | .code64 3166 bool X86AsmParser::ParseDirectiveCode(StringRef IDVal, SMLoc L) { 3167 MCAsmParser &Parser = getParser(); 3168 Code16GCC = false; 3169 if (IDVal == ".code16") { 3170 Parser.Lex(); 3171 if (!is16BitMode()) { 3172 SwitchMode(X86::Mode16Bit); 3173 getParser().getStreamer().EmitAssemblerFlag(MCAF_Code16); 3174 } 3175 } else if (IDVal == ".code16gcc") { 3176 // .code16gcc parses as if in 32-bit mode, but emits code in 16-bit mode. 3177 Parser.Lex(); 3178 Code16GCC = true; 3179 if (!is16BitMode()) { 3180 SwitchMode(X86::Mode16Bit); 3181 getParser().getStreamer().EmitAssemblerFlag(MCAF_Code16); 3182 } 3183 } else if (IDVal == ".code32") { 3184 Parser.Lex(); 3185 if (!is32BitMode()) { 3186 SwitchMode(X86::Mode32Bit); 3187 getParser().getStreamer().EmitAssemblerFlag(MCAF_Code32); 3188 } 3189 } else if (IDVal == ".code64") { 3190 Parser.Lex(); 3191 if (!is64BitMode()) { 3192 SwitchMode(X86::Mode64Bit); 3193 getParser().getStreamer().EmitAssemblerFlag(MCAF_Code64); 3194 } 3195 } else { 3196 Error(L, "unknown directive " + IDVal); 3197 return false; 3198 } 3199 3200 return false; 3201 } 3202 3203 // .cv_fpo_proc foo 3204 bool X86AsmParser::parseDirectiveFPOProc(SMLoc L) { 3205 MCAsmParser &Parser = getParser(); 3206 StringRef ProcName; 3207 int64_t ParamsSize; 3208 if (Parser.parseIdentifier(ProcName)) 3209 return Parser.TokError("expected symbol name"); 3210 if (Parser.parseIntToken(ParamsSize, "expected parameter byte count")) 3211 return true; 3212 if (!isUIntN(32, ParamsSize)) 3213 return Parser.TokError("parameters size out of range"); 3214 if (Parser.parseEOL("unexpected tokens")) 3215 return addErrorSuffix(" in '.cv_fpo_proc' directive"); 3216 MCSymbol *ProcSym = getContext().getOrCreateSymbol(ProcName); 3217 return getTargetStreamer().emitFPOProc(ProcSym, ParamsSize, L); 3218 } 3219 3220 // .cv_fpo_setframe ebp 3221 bool X86AsmParser::parseDirectiveFPOSetFrame(SMLoc L) { 3222 MCAsmParser &Parser = getParser(); 3223 unsigned Reg; 3224 SMLoc DummyLoc; 3225 if (ParseRegister(Reg, DummyLoc, DummyLoc) || 3226 Parser.parseEOL("unexpected tokens")) 3227 return addErrorSuffix(" in '.cv_fpo_setframe' directive"); 3228 return getTargetStreamer().emitFPOSetFrame(Reg, L); 3229 } 3230 3231 // .cv_fpo_pushreg ebx 3232 bool X86AsmParser::parseDirectiveFPOPushReg(SMLoc L) { 3233 MCAsmParser &Parser = getParser(); 3234 unsigned Reg; 3235 SMLoc DummyLoc; 3236 if (ParseRegister(Reg, DummyLoc, DummyLoc) || 3237 Parser.parseEOL("unexpected tokens")) 3238 return addErrorSuffix(" in '.cv_fpo_pushreg' directive"); 3239 return getTargetStreamer().emitFPOPushReg(Reg, L); 3240 } 3241 3242 // .cv_fpo_stackalloc 20 3243 bool X86AsmParser::parseDirectiveFPOStackAlloc(SMLoc L) { 3244 MCAsmParser &Parser = getParser(); 3245 int64_t Offset; 3246 if (Parser.parseIntToken(Offset, "expected offset") || 3247 Parser.parseEOL("unexpected tokens")) 3248 return addErrorSuffix(" in '.cv_fpo_stackalloc' directive"); 3249 return getTargetStreamer().emitFPOStackAlloc(Offset, L); 3250 } 3251 3252 // .cv_fpo_endprologue 3253 bool X86AsmParser::parseDirectiveFPOEndPrologue(SMLoc L) { 3254 MCAsmParser &Parser = getParser(); 3255 if (Parser.parseEOL("unexpected tokens")) 3256 return addErrorSuffix(" in '.cv_fpo_endprologue' directive"); 3257 return getTargetStreamer().emitFPOEndPrologue(L); 3258 } 3259 3260 // .cv_fpo_endproc 3261 bool X86AsmParser::parseDirectiveFPOEndProc(SMLoc L) { 3262 MCAsmParser &Parser = getParser(); 3263 if (Parser.parseEOL("unexpected tokens")) 3264 return addErrorSuffix(" in '.cv_fpo_endproc' directive"); 3265 return getTargetStreamer().emitFPOEndProc(L); 3266 } 3267 3268 // Force static initialization. 3269 extern "C" void LLVMInitializeX86AsmParser() { 3270 RegisterMCAsmParser<X86AsmParser> X(getTheX86_32Target()); 3271 RegisterMCAsmParser<X86AsmParser> Y(getTheX86_64Target()); 3272 } 3273 3274 #define GET_REGISTER_MATCHER 3275 #define GET_MATCHER_IMPLEMENTATION 3276 #define GET_SUBTARGET_FEATURE_NAME 3277 #include "X86GenAsmMatcher.inc" 3278