OLD | NEW |
1 //===---- ParseStmtAsm.cpp - Assembly Statement Parser --------------------===// | 1 //===---- ParseStmtAsm.cpp - Assembly Statement Parser --------------------===// |
2 // | 2 // |
3 // The LLVM Compiler Infrastructure | 3 // The LLVM Compiler Infrastructure |
4 // | 4 // |
5 // This file is distributed under the University of Illinois Open Source | 5 // This file is distributed under the University of Illinois Open Source |
6 // License. See LICENSE.TXT for details. | 6 // License. See LICENSE.TXT for details. |
7 // | 7 // |
8 //===----------------------------------------------------------------------===// | 8 //===----------------------------------------------------------------------===// |
9 // | 9 // |
10 // This file implements parsing for GCC and Microsoft inline assembly. | 10 // This file implements parsing for GCC and Microsoft inline assembly. |
(...skipping 598 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
609 StmtResult Parser::ParseAsmStatement(bool &msAsm) { | 609 StmtResult Parser::ParseAsmStatement(bool &msAsm) { |
610 assert(Tok.is(tok::kw_asm) && "Not an asm stmt"); | 610 assert(Tok.is(tok::kw_asm) && "Not an asm stmt"); |
611 SourceLocation AsmLoc = ConsumeToken(); | 611 SourceLocation AsmLoc = ConsumeToken(); |
612 | 612 |
613 if (getLangOpts().AsmBlocks && Tok.isNot(tok::l_paren) && | 613 if (getLangOpts().AsmBlocks && Tok.isNot(tok::l_paren) && |
614 !isTypeQualifier()) { | 614 !isTypeQualifier()) { |
615 msAsm = true; | 615 msAsm = true; |
616 return ParseMicrosoftAsmStatement(AsmLoc); | 616 return ParseMicrosoftAsmStatement(AsmLoc); |
617 } | 617 } |
618 | 618 |
619 // Check if GNU-style inline Asm is disabled. | |
620 if (!getLangOpts().GNUAsm) | |
621 Diag(AsmLoc, diag::err_gnu_inline_asm_disabled); | |
622 | |
623 DeclSpec DS(AttrFactory); | 619 DeclSpec DS(AttrFactory); |
624 SourceLocation Loc = Tok.getLocation(); | 620 SourceLocation Loc = Tok.getLocation(); |
625 ParseTypeQualifierListOpt(DS, AR_VendorAttributesParsed); | 621 ParseTypeQualifierListOpt(DS, AR_VendorAttributesParsed); |
626 | 622 |
627 // GNU asms accept, but warn, about type-qualifiers other than volatile. | 623 // GNU asms accept, but warn, about type-qualifiers other than volatile. |
628 if (DS.getTypeQualifiers() & DeclSpec::TQ_const) | 624 if (DS.getTypeQualifiers() & DeclSpec::TQ_const) |
629 Diag(Loc, diag::w_asm_qualifier_ignored) << "const"; | 625 Diag(Loc, diag::w_asm_qualifier_ignored) << "const"; |
630 if (DS.getTypeQualifiers() & DeclSpec::TQ_restrict) | 626 if (DS.getTypeQualifiers() & DeclSpec::TQ_restrict) |
631 Diag(Loc, diag::w_asm_qualifier_ignored) << "restrict"; | 627 Diag(Loc, diag::w_asm_qualifier_ignored) << "restrict"; |
632 // FIXME: Once GCC supports _Atomic, check whether it permits it here. | 628 // FIXME: Once GCC supports _Atomic, check whether it permits it here. |
633 if (DS.getTypeQualifiers() & DeclSpec::TQ_atomic) | 629 if (DS.getTypeQualifiers() & DeclSpec::TQ_atomic) |
634 Diag(Loc, diag::w_asm_qualifier_ignored) << "_Atomic"; | 630 Diag(Loc, diag::w_asm_qualifier_ignored) << "_Atomic"; |
635 | 631 |
636 // Remember if this was a volatile asm. | 632 // Remember if this was a volatile asm. |
637 bool isVolatile = DS.getTypeQualifiers() & DeclSpec::TQ_volatile; | 633 bool isVolatile = DS.getTypeQualifiers() & DeclSpec::TQ_volatile; |
638 if (Tok.isNot(tok::l_paren)) { | 634 if (Tok.isNot(tok::l_paren)) { |
639 Diag(Tok, diag::err_expected_lparen_after) << "asm"; | 635 Diag(Tok, diag::err_expected_lparen_after) << "asm"; |
640 SkipUntil(tok::r_paren, StopAtSemi); | 636 SkipUntil(tok::r_paren, StopAtSemi); |
641 return StmtError(); | 637 return StmtError(); |
642 } | 638 } |
643 BalancedDelimiterTracker T(*this, tok::l_paren); | 639 BalancedDelimiterTracker T(*this, tok::l_paren); |
644 T.consumeOpen(); | 640 T.consumeOpen(); |
645 | 641 |
646 ExprResult AsmString(ParseAsmStringLiteral()); | 642 ExprResult AsmString(ParseAsmStringLiteral()); |
| 643 |
| 644 // Check if GNU-style InlineAsm is disabled. |
| 645 // Error on anything other than empty string. |
| 646 if (!(getLangOpts().GNUAsm || AsmString.isInvalid())) { |
| 647 const auto *SL = cast<StringLiteral>(AsmString.get()); |
| 648 if (!SL->getString().trim().empty()) |
| 649 Diag(Loc, diag::err_gnu_inline_asm_disabled); |
| 650 } |
| 651 |
647 if (AsmString.isInvalid()) { | 652 if (AsmString.isInvalid()) { |
648 // Consume up to and including the closing paren. | 653 // Consume up to and including the closing paren. |
649 T.skipToEnd(); | 654 T.skipToEnd(); |
650 return StmtError(); | 655 return StmtError(); |
651 } | 656 } |
652 | 657 |
653 SmallVector<IdentifierInfo *, 4> Names; | 658 SmallVector<IdentifierInfo *, 4> Names; |
654 ExprVector Constraints; | 659 ExprVector Constraints; |
655 ExprVector Exprs; | 660 ExprVector Exprs; |
656 ExprVector Clobbers; | 661 ExprVector Clobbers; |
(...skipping 127 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
784 if (Res.isInvalid()) { | 789 if (Res.isInvalid()) { |
785 SkipUntil(tok::r_paren, StopAtSemi); | 790 SkipUntil(tok::r_paren, StopAtSemi); |
786 return true; | 791 return true; |
787 } | 792 } |
788 Exprs.push_back(Res.get()); | 793 Exprs.push_back(Res.get()); |
789 // Eat the comma and continue parsing if it exists. | 794 // Eat the comma and continue parsing if it exists. |
790 if (!TryConsumeToken(tok::comma)) | 795 if (!TryConsumeToken(tok::comma)) |
791 return false; | 796 return false; |
792 } | 797 } |
793 } | 798 } |
OLD | NEW |