Mercurial > hg > CbC > CbC_llvm
comparison clang/lib/Parse/ParsePragma.cpp @ 207:2e18cbf3894f
LLVM12
author | Shinji KONO <kono@ie.u-ryukyu.ac.jp> |
---|---|
date | Tue, 08 Jun 2021 06:07:14 +0900 |
parents | 0572611fdcc8 |
children | c4bab56944e8 |
comparison
equal
deleted
inserted
replaced
173:0572611fdcc8 | 207:2e18cbf3894f |
---|---|
12 | 12 |
13 #include "clang/AST/ASTContext.h" | 13 #include "clang/AST/ASTContext.h" |
14 #include "clang/Basic/PragmaKinds.h" | 14 #include "clang/Basic/PragmaKinds.h" |
15 #include "clang/Basic/TargetInfo.h" | 15 #include "clang/Basic/TargetInfo.h" |
16 #include "clang/Lex/Preprocessor.h" | 16 #include "clang/Lex/Preprocessor.h" |
17 #include "clang/Lex/Token.h" | |
17 #include "clang/Parse/LoopHint.h" | 18 #include "clang/Parse/LoopHint.h" |
18 #include "clang/Parse/ParseDiagnostic.h" | 19 #include "clang/Parse/ParseDiagnostic.h" |
19 #include "clang/Parse/Parser.h" | 20 #include "clang/Parse/Parser.h" |
20 #include "clang/Parse/RAIIObjectsForParser.h" | 21 #include "clang/Parse/RAIIObjectsForParser.h" |
21 #include "clang/Sema/Scope.h" | 22 #include "clang/Sema/Scope.h" |
23 #include "llvm/ADT/ArrayRef.h" | |
22 #include "llvm/ADT/StringSwitch.h" | 24 #include "llvm/ADT/StringSwitch.h" |
23 using namespace clang; | 25 using namespace clang; |
24 | 26 |
25 namespace { | 27 namespace { |
26 | 28 |
101 struct PragmaSTDC_FENV_ACCESSHandler : public PragmaHandler { | 103 struct PragmaSTDC_FENV_ACCESSHandler : public PragmaHandler { |
102 PragmaSTDC_FENV_ACCESSHandler() : PragmaHandler("FENV_ACCESS") {} | 104 PragmaSTDC_FENV_ACCESSHandler() : PragmaHandler("FENV_ACCESS") {} |
103 | 105 |
104 void HandlePragma(Preprocessor &PP, PragmaIntroducer Introducer, | 106 void HandlePragma(Preprocessor &PP, PragmaIntroducer Introducer, |
105 Token &Tok) override { | 107 Token &Tok) override { |
108 Token PragmaName = Tok; | |
109 if (!PP.getTargetInfo().hasStrictFP() && !PP.getLangOpts().ExpStrictFP) { | |
110 PP.Diag(Tok.getLocation(), diag::warn_pragma_fp_ignored) | |
111 << PragmaName.getIdentifierInfo()->getName(); | |
112 return; | |
113 } | |
106 tok::OnOffSwitch OOS; | 114 tok::OnOffSwitch OOS; |
107 if (PP.LexOnOffSwitch(OOS)) | 115 if (PP.LexOnOffSwitch(OOS)) |
108 return; | 116 return; |
109 if (OOS == tok::OOS_ON) { | |
110 PP.Diag(Tok, diag::warn_stdc_fenv_access_not_supported); | |
111 return; | |
112 } | |
113 | 117 |
114 MutableArrayRef<Token> Toks(PP.getPreprocessorAllocator().Allocate<Token>(1), | 118 MutableArrayRef<Token> Toks(PP.getPreprocessorAllocator().Allocate<Token>(1), |
115 1); | 119 1); |
116 Toks[0].startToken(); | 120 Toks[0].startToken(); |
117 Toks[0].setKind(tok::annot_pragma_fenv_access); | 121 Toks[0].setKind(tok::annot_pragma_fenv_access); |
133 tok::OnOffSwitch OOS; | 137 tok::OnOffSwitch OOS; |
134 PP.LexOnOffSwitch(OOS); | 138 PP.LexOnOffSwitch(OOS); |
135 } | 139 } |
136 }; | 140 }; |
137 | 141 |
142 /// Handler for "\#pragma STDC FENV_ROUND ...". | |
143 struct PragmaSTDC_FENV_ROUNDHandler : public PragmaHandler { | |
144 PragmaSTDC_FENV_ROUNDHandler() : PragmaHandler("FENV_ROUND") {} | |
145 | |
146 void HandlePragma(Preprocessor &PP, PragmaIntroducer Introducer, | |
147 Token &Tok) override; | |
148 }; | |
149 | |
138 /// PragmaSTDC_UnknownHandler - "\#pragma STDC ...". | 150 /// PragmaSTDC_UnknownHandler - "\#pragma STDC ...". |
139 struct PragmaSTDC_UnknownHandler : public PragmaHandler { | 151 struct PragmaSTDC_UnknownHandler : public PragmaHandler { |
140 PragmaSTDC_UnknownHandler() = default; | 152 PragmaSTDC_UnknownHandler() = default; |
141 | 153 |
142 void HandlePragma(Preprocessor &PP, PragmaIntroducer Introducer, | 154 void HandlePragma(Preprocessor &PP, PragmaIntroducer Introducer, |
280 PragmaMaxTokensTotalHandler() : PragmaHandler("max_tokens_total") {} | 292 PragmaMaxTokensTotalHandler() : PragmaHandler("max_tokens_total") {} |
281 void HandlePragma(Preprocessor &PP, PragmaIntroducer Introducer, | 293 void HandlePragma(Preprocessor &PP, PragmaIntroducer Introducer, |
282 Token &FirstToken) override; | 294 Token &FirstToken) override; |
283 }; | 295 }; |
284 | 296 |
297 void markAsReinjectedForRelexing(llvm::MutableArrayRef<clang::Token> Toks) { | |
298 for (auto &T : Toks) | |
299 T.setFlag(clang::Token::IsReinjected); | |
300 } | |
285 } // end namespace | 301 } // end namespace |
286 | 302 |
287 void Parser::initializePragmaHandlers() { | 303 void Parser::initializePragmaHandlers() { |
288 AlignHandler = std::make_unique<PragmaAlignHandler>(); | 304 AlignHandler = std::make_unique<PragmaAlignHandler>(); |
289 PP.AddPragmaHandler(AlignHandler.get()); | 305 PP.AddPragmaHandler(AlignHandler.get()); |
310 PP.AddPragmaHandler(RedefineExtnameHandler.get()); | 326 PP.AddPragmaHandler(RedefineExtnameHandler.get()); |
311 | 327 |
312 FPContractHandler = std::make_unique<PragmaFPContractHandler>(); | 328 FPContractHandler = std::make_unique<PragmaFPContractHandler>(); |
313 PP.AddPragmaHandler("STDC", FPContractHandler.get()); | 329 PP.AddPragmaHandler("STDC", FPContractHandler.get()); |
314 | 330 |
315 STDCFENVHandler = std::make_unique<PragmaSTDC_FENV_ACCESSHandler>(); | 331 STDCFenvAccessHandler = std::make_unique<PragmaSTDC_FENV_ACCESSHandler>(); |
316 PP.AddPragmaHandler("STDC", STDCFENVHandler.get()); | 332 PP.AddPragmaHandler("STDC", STDCFenvAccessHandler.get()); |
333 | |
334 STDCFenvRoundHandler = std::make_unique<PragmaSTDC_FENV_ROUNDHandler>(); | |
335 PP.AddPragmaHandler("STDC", STDCFenvRoundHandler.get()); | |
317 | 336 |
318 STDCCXLIMITHandler = std::make_unique<PragmaSTDC_CX_LIMITED_RANGEHandler>(); | 337 STDCCXLIMITHandler = std::make_unique<PragmaSTDC_CX_LIMITED_RANGEHandler>(); |
319 PP.AddPragmaHandler("STDC", STDCCXLIMITHandler.get()); | 338 PP.AddPragmaHandler("STDC", STDCCXLIMITHandler.get()); |
320 | 339 |
321 STDCUnknownHandler = std::make_unique<PragmaSTDC_UnknownHandler>(); | 340 STDCUnknownHandler = std::make_unique<PragmaSTDC_UnknownHandler>(); |
384 LoopHintHandler = std::make_unique<PragmaLoopHintHandler>(); | 403 LoopHintHandler = std::make_unique<PragmaLoopHintHandler>(); |
385 PP.AddPragmaHandler("clang", LoopHintHandler.get()); | 404 PP.AddPragmaHandler("clang", LoopHintHandler.get()); |
386 | 405 |
387 UnrollHintHandler = std::make_unique<PragmaUnrollHintHandler>("unroll"); | 406 UnrollHintHandler = std::make_unique<PragmaUnrollHintHandler>("unroll"); |
388 PP.AddPragmaHandler(UnrollHintHandler.get()); | 407 PP.AddPragmaHandler(UnrollHintHandler.get()); |
408 PP.AddPragmaHandler("GCC", UnrollHintHandler.get()); | |
389 | 409 |
390 NoUnrollHintHandler = std::make_unique<PragmaUnrollHintHandler>("nounroll"); | 410 NoUnrollHintHandler = std::make_unique<PragmaUnrollHintHandler>("nounroll"); |
391 PP.AddPragmaHandler(NoUnrollHintHandler.get()); | 411 PP.AddPragmaHandler(NoUnrollHintHandler.get()); |
412 PP.AddPragmaHandler("GCC", NoUnrollHintHandler.get()); | |
392 | 413 |
393 UnrollAndJamHintHandler = | 414 UnrollAndJamHintHandler = |
394 std::make_unique<PragmaUnrollHintHandler>("unroll_and_jam"); | 415 std::make_unique<PragmaUnrollHintHandler>("unroll_and_jam"); |
395 PP.AddPragmaHandler(UnrollAndJamHintHandler.get()); | 416 PP.AddPragmaHandler(UnrollAndJamHintHandler.get()); |
396 | 417 |
483 } | 504 } |
484 | 505 |
485 PP.RemovePragmaHandler("STDC", FPContractHandler.get()); | 506 PP.RemovePragmaHandler("STDC", FPContractHandler.get()); |
486 FPContractHandler.reset(); | 507 FPContractHandler.reset(); |
487 | 508 |
488 PP.RemovePragmaHandler("STDC", STDCFENVHandler.get()); | 509 PP.RemovePragmaHandler("STDC", STDCFenvAccessHandler.get()); |
489 STDCFENVHandler.reset(); | 510 STDCFenvAccessHandler.reset(); |
511 | |
512 PP.RemovePragmaHandler("STDC", STDCFenvRoundHandler.get()); | |
513 STDCFenvRoundHandler.reset(); | |
490 | 514 |
491 PP.RemovePragmaHandler("STDC", STDCCXLIMITHandler.get()); | 515 PP.RemovePragmaHandler("STDC", STDCCXLIMITHandler.get()); |
492 STDCCXLIMITHandler.reset(); | 516 STDCCXLIMITHandler.reset(); |
493 | 517 |
494 PP.RemovePragmaHandler("STDC", STDCUnknownHandler.get()); | 518 PP.RemovePragmaHandler("STDC", STDCUnknownHandler.get()); |
499 | 523 |
500 PP.RemovePragmaHandler("clang", LoopHintHandler.get()); | 524 PP.RemovePragmaHandler("clang", LoopHintHandler.get()); |
501 LoopHintHandler.reset(); | 525 LoopHintHandler.reset(); |
502 | 526 |
503 PP.RemovePragmaHandler(UnrollHintHandler.get()); | 527 PP.RemovePragmaHandler(UnrollHintHandler.get()); |
528 PP.RemovePragmaHandler("GCC", UnrollHintHandler.get()); | |
504 UnrollHintHandler.reset(); | 529 UnrollHintHandler.reset(); |
505 | 530 |
506 PP.RemovePragmaHandler(NoUnrollHintHandler.get()); | 531 PP.RemovePragmaHandler(NoUnrollHintHandler.get()); |
532 PP.RemovePragmaHandler("GCC", NoUnrollHintHandler.get()); | |
507 NoUnrollHintHandler.reset(); | 533 NoUnrollHintHandler.reset(); |
508 | 534 |
509 PP.RemovePragmaHandler(UnrollAndJamHintHandler.get()); | 535 PP.RemovePragmaHandler(UnrollAndJamHintHandler.get()); |
510 UnrollAndJamHintHandler.reset(); | 536 UnrollAndJamHintHandler.reset(); |
511 | 537 |
652 case tok::OOS_DEFAULT: | 678 case tok::OOS_DEFAULT: |
653 FPC = getLangOpts().getDefaultFPContractMode(); | 679 FPC = getLangOpts().getDefaultFPContractMode(); |
654 break; | 680 break; |
655 } | 681 } |
656 | 682 |
657 Actions.ActOnPragmaFPContract(FPC); | 683 SourceLocation PragmaLoc = ConsumeAnnotationToken(); |
658 ConsumeAnnotationToken(); | 684 Actions.ActOnPragmaFPContract(PragmaLoc, FPC); |
659 } | 685 } |
660 | 686 |
661 void Parser::HandlePragmaFloatControl() { | 687 void Parser::HandlePragmaFloatControl() { |
662 assert(Tok.is(tok::annot_pragma_float_control)); | 688 assert(Tok.is(tok::annot_pragma_float_control)); |
663 | 689 |
695 | 721 |
696 SourceLocation PragmaLoc = ConsumeAnnotationToken(); | 722 SourceLocation PragmaLoc = ConsumeAnnotationToken(); |
697 Actions.ActOnPragmaFEnvAccess(PragmaLoc, IsEnabled); | 723 Actions.ActOnPragmaFEnvAccess(PragmaLoc, IsEnabled); |
698 } | 724 } |
699 | 725 |
726 void Parser::HandlePragmaFEnvRound() { | |
727 assert(Tok.is(tok::annot_pragma_fenv_round)); | |
728 auto RM = static_cast<llvm::RoundingMode>( | |
729 reinterpret_cast<uintptr_t>(Tok.getAnnotationValue())); | |
730 | |
731 SourceLocation PragmaLoc = ConsumeAnnotationToken(); | |
732 Actions.setRoundingMode(PragmaLoc, RM); | |
733 } | |
700 | 734 |
701 StmtResult Parser::HandlePragmaCaptured() | 735 StmtResult Parser::HandlePragmaCaptured() |
702 { | 736 { |
703 assert(Tok.is(tok::annot_pragma_captured)); | 737 assert(Tok.is(tok::annot_pragma_captured)); |
704 ConsumeAnnotationToken(); | 738 ConsumeAnnotationToken(); |
745 auto Name = Ident->getName(); | 779 auto Name = Ident->getName(); |
746 // OpenCL 1.1 9.1: "The all variant sets the behavior for all extensions, | 780 // OpenCL 1.1 9.1: "The all variant sets the behavior for all extensions, |
747 // overriding all previously issued extension directives, but only if the | 781 // overriding all previously issued extension directives, but only if the |
748 // behavior is set to disable." | 782 // behavior is set to disable." |
749 if (Name == "all") { | 783 if (Name == "all") { |
750 if (State == Disable) { | 784 if (State == Disable) |
751 Opt.disableAll(); | 785 Opt.disableAll(); |
752 Opt.enableSupportedCore(getLangOpts()); | 786 else |
753 } else { | |
754 PP.Diag(NameLoc, diag::warn_pragma_expected_predicate) << 1; | 787 PP.Diag(NameLoc, diag::warn_pragma_expected_predicate) << 1; |
755 } | |
756 } else if (State == Begin) { | 788 } else if (State == Begin) { |
757 if (!Opt.isKnown(Name) || !Opt.isSupported(Name, getLangOpts())) { | 789 if (!Opt.isKnown(Name) || !Opt.isSupported(Name, getLangOpts())) { |
758 Opt.support(Name); | 790 Opt.support(Name); |
759 } | 791 // FIXME: Default behavior of the extension pragma is not defined. |
760 Actions.setCurrentOpenCLExtension(Name); | 792 // Therefore, it should never be added by default. |
793 Opt.acceptsPragma(Name); | |
794 } | |
761 } else if (State == End) { | 795 } else if (State == End) { |
762 if (Name != Actions.getCurrentOpenCLExtension()) | 796 // There is no behavior for this directive. We only accept this for |
763 PP.Diag(NameLoc, diag::warn_pragma_begin_end_mismatch); | 797 // backward compatibility. |
764 Actions.setCurrentOpenCLExtension(""); | 798 } else if (!Opt.isKnown(Name) || !Opt.isWithPragma(Name)) |
765 } else if (!Opt.isKnown(Name)) | |
766 PP.Diag(NameLoc, diag::warn_pragma_unknown_extension) << Ident; | 799 PP.Diag(NameLoc, diag::warn_pragma_unknown_extension) << Ident; |
767 else if (Opt.isSupportedExtension(Name, getLangOpts())) | 800 else if (Opt.isSupportedExtension(Name, getLangOpts())) |
768 Opt.enable(Name, State == Enable); | 801 Opt.enable(Name, State == Enable); |
769 else if (Opt.isSupportedCore(Name, getLangOpts())) | 802 else if (Opt.isSupportedCoreOrOptionalCore(Name, getLangOpts())) |
770 PP.Diag(NameLoc, diag::warn_pragma_extension_is_core) << Ident; | 803 PP.Diag(NameLoc, diag::warn_pragma_extension_is_core) << Ident; |
771 else | 804 else |
772 PP.Diag(NameLoc, diag::warn_pragma_unsupported_extension) << Ident; | 805 PP.Diag(NameLoc, diag::warn_pragma_unsupported_extension) << Ident; |
773 } | 806 } |
774 | 807 |
1161 } | 1194 } |
1162 if (Toks.size() > 2) | 1195 if (Toks.size() > 2) |
1163 Diag(Tok.getLocation(), diag::warn_pragma_extra_tokens_at_eol) | 1196 Diag(Tok.getLocation(), diag::warn_pragma_extra_tokens_at_eol) |
1164 << PragmaLoopHintString(Info->PragmaName, Info->Option); | 1197 << PragmaLoopHintString(Info->PragmaName, Info->Option); |
1165 Hint.StateLoc = IdentifierLoc::create(Actions.Context, StateLoc, StateInfo); | 1198 Hint.StateLoc = IdentifierLoc::create(Actions.Context, StateLoc, StateInfo); |
1199 } else if (OptionInfo && OptionInfo->getName() == "vectorize_width") { | |
1200 PP.EnterTokenStream(Toks, /*DisableMacroExpansion=*/false, | |
1201 /*IsReinject=*/false); | |
1202 ConsumeAnnotationToken(); | |
1203 | |
1204 SourceLocation StateLoc = Toks[0].getLocation(); | |
1205 IdentifierInfo *StateInfo = Toks[0].getIdentifierInfo(); | |
1206 StringRef IsScalableStr = StateInfo ? StateInfo->getName() : ""; | |
1207 | |
1208 // Look for vectorize_width(fixed|scalable) | |
1209 if (IsScalableStr == "scalable" || IsScalableStr == "fixed") { | |
1210 PP.Lex(Tok); // Identifier | |
1211 | |
1212 if (Toks.size() > 2) { | |
1213 Diag(Tok.getLocation(), diag::warn_pragma_extra_tokens_at_eol) | |
1214 << PragmaLoopHintString(Info->PragmaName, Info->Option); | |
1215 while (Tok.isNot(tok::eof)) | |
1216 ConsumeAnyToken(); | |
1217 } | |
1218 | |
1219 Hint.StateLoc = | |
1220 IdentifierLoc::create(Actions.Context, StateLoc, StateInfo); | |
1221 | |
1222 ConsumeToken(); // Consume the constant expression eof terminator. | |
1223 } else { | |
1224 // Enter constant expression including eof terminator into token stream. | |
1225 ExprResult R = ParseConstantExpression(); | |
1226 | |
1227 if (R.isInvalid() && !Tok.is(tok::comma)) | |
1228 Diag(Toks[0].getLocation(), | |
1229 diag::note_pragma_loop_invalid_vectorize_option); | |
1230 | |
1231 bool Arg2Error = false; | |
1232 if (Tok.is(tok::comma)) { | |
1233 PP.Lex(Tok); // , | |
1234 | |
1235 StateInfo = Tok.getIdentifierInfo(); | |
1236 IsScalableStr = StateInfo->getName(); | |
1237 | |
1238 if (IsScalableStr != "scalable" && IsScalableStr != "fixed") { | |
1239 Diag(Tok.getLocation(), | |
1240 diag::err_pragma_loop_invalid_vectorize_option); | |
1241 Arg2Error = true; | |
1242 } else | |
1243 Hint.StateLoc = | |
1244 IdentifierLoc::create(Actions.Context, StateLoc, StateInfo); | |
1245 | |
1246 PP.Lex(Tok); // Identifier | |
1247 } | |
1248 | |
1249 // Tokens following an error in an ill-formed constant expression will | |
1250 // remain in the token stream and must be removed. | |
1251 if (Tok.isNot(tok::eof)) { | |
1252 Diag(Tok.getLocation(), diag::warn_pragma_extra_tokens_at_eol) | |
1253 << PragmaLoopHintString(Info->PragmaName, Info->Option); | |
1254 while (Tok.isNot(tok::eof)) | |
1255 ConsumeAnyToken(); | |
1256 } | |
1257 | |
1258 ConsumeToken(); // Consume the constant expression eof terminator. | |
1259 | |
1260 if (Arg2Error || R.isInvalid() || | |
1261 Actions.CheckLoopHintExpr(R.get(), Toks[0].getLocation())) | |
1262 return false; | |
1263 | |
1264 // Argument is a constant expression with an integer type. | |
1265 Hint.ValueExpr = R.get(); | |
1266 } | |
1166 } else { | 1267 } else { |
1167 // Enter constant expression including eof terminator into token stream. | 1268 // Enter constant expression including eof terminator into token stream. |
1168 PP.EnterTokenStream(Toks, /*DisableMacroExpansion=*/false, | 1269 PP.EnterTokenStream(Toks, /*DisableMacroExpansion=*/false, |
1169 /*IsReinject=*/false); | 1270 /*IsReinject=*/false); |
1170 ConsumeAnnotationToken(); | 1271 ConsumeAnnotationToken(); |
1171 | |
1172 ExprResult R = ParseConstantExpression(); | 1272 ExprResult R = ParseConstantExpression(); |
1173 | 1273 |
1174 // Tokens following an error in an ill-formed constant expression will | 1274 // Tokens following an error in an ill-formed constant expression will |
1175 // remain in the token stream and must be removed. | 1275 // remain in the token stream and must be removed. |
1176 if (Tok.isNot(tok::eof)) { | 1276 if (Tok.isNot(tok::eof)) { |
1710 | 1810 |
1711 PP.Lex(Tok); | 1811 PP.Lex(Tok); |
1712 | 1812 |
1713 // In MSVC/gcc, #pragma pack(4) sets the alignment without affecting | 1813 // In MSVC/gcc, #pragma pack(4) sets the alignment without affecting |
1714 // the push/pop stack. | 1814 // the push/pop stack. |
1715 // In Apple gcc, #pragma pack(4) is equivalent to #pragma pack(push, 4) | 1815 // In Apple gcc/XL, #pragma pack(4) is equivalent to #pragma pack(push, 4) |
1716 Action = | 1816 Action = (PP.getLangOpts().ApplePragmaPack || PP.getLangOpts().XLPragmaPack) |
1717 PP.getLangOpts().ApplePragmaPack ? Sema::PSK_Push_Set : Sema::PSK_Set; | 1817 ? Sema::PSK_Push_Set |
1818 : Sema::PSK_Set; | |
1718 } else if (Tok.is(tok::identifier)) { | 1819 } else if (Tok.is(tok::identifier)) { |
1719 const IdentifierInfo *II = Tok.getIdentifierInfo(); | 1820 const IdentifierInfo *II = Tok.getIdentifierInfo(); |
1720 if (II->isStr("show")) { | 1821 if (II->isStr("show")) { |
1721 Action = Sema::PSK_Show; | 1822 Action = Sema::PSK_Show; |
1722 PP.Lex(Tok); | 1823 PP.Lex(Tok); |
1760 PP.Diag(Tok.getLocation(), diag::warn_pragma_pack_malformed); | 1861 PP.Diag(Tok.getLocation(), diag::warn_pragma_pack_malformed); |
1761 return; | 1862 return; |
1762 } | 1863 } |
1763 } | 1864 } |
1764 } | 1865 } |
1765 } else if (PP.getLangOpts().ApplePragmaPack) { | 1866 } else if (PP.getLangOpts().ApplePragmaPack || |
1867 PP.getLangOpts().XLPragmaPack) { | |
1766 // In MSVC/gcc, #pragma pack() resets the alignment without affecting | 1868 // In MSVC/gcc, #pragma pack() resets the alignment without affecting |
1767 // the push/pop stack. | 1869 // the push/pop stack. |
1768 // In Apple gcc #pragma pack() is equivalent to #pragma pack(pop). | 1870 // In Apple gcc and IBM XL, #pragma pack() is equivalent to #pragma |
1871 // pack(pop). | |
1769 Action = Sema::PSK_Pop; | 1872 Action = Sema::PSK_Pop; |
1770 } | 1873 } |
1771 | 1874 |
1772 if (Tok.isNot(tok::r_paren)) { | 1875 if (Tok.isNot(tok::r_paren)) { |
1773 PP.Diag(Tok.getLocation(), diag::warn_pragma_expected_rparen) << "pack"; | 1876 PP.Diag(Tok.getLocation(), diag::warn_pragma_expected_rparen) << "pack"; |
1892 } | 1995 } |
1893 } | 1996 } |
1894 | 1997 |
1895 // #pragma 'align' '=' {'native','natural','mac68k','power','reset'} | 1998 // #pragma 'align' '=' {'native','natural','mac68k','power','reset'} |
1896 // #pragma 'options 'align' '=' {'native','natural','mac68k','power','reset'} | 1999 // #pragma 'options 'align' '=' {'native','natural','mac68k','power','reset'} |
2000 // #pragma 'align' '(' {'native','natural','mac68k','power','reset'} ')' | |
1897 static void ParseAlignPragma(Preprocessor &PP, Token &FirstTok, | 2001 static void ParseAlignPragma(Preprocessor &PP, Token &FirstTok, |
1898 bool IsOptions) { | 2002 bool IsOptions) { |
1899 Token Tok; | 2003 Token Tok; |
1900 | 2004 |
1901 if (IsOptions) { | 2005 if (IsOptions) { |
1906 return; | 2010 return; |
1907 } | 2011 } |
1908 } | 2012 } |
1909 | 2013 |
1910 PP.Lex(Tok); | 2014 PP.Lex(Tok); |
1911 if (Tok.isNot(tok::equal)) { | 2015 if (PP.getLangOpts().XLPragmaPack) { |
2016 if (Tok.isNot(tok::l_paren)) { | |
2017 PP.Diag(Tok.getLocation(), diag::warn_pragma_expected_lparen) << "align"; | |
2018 return; | |
2019 } | |
2020 } else if (Tok.isNot(tok::equal)) { | |
1912 PP.Diag(Tok.getLocation(), diag::warn_pragma_align_expected_equal) | 2021 PP.Diag(Tok.getLocation(), diag::warn_pragma_align_expected_equal) |
1913 << IsOptions; | 2022 << IsOptions; |
1914 return; | 2023 return; |
1915 } | 2024 } |
1916 | 2025 |
1937 Kind = Sema::POAK_Reset; | 2046 Kind = Sema::POAK_Reset; |
1938 else { | 2047 else { |
1939 PP.Diag(Tok.getLocation(), diag::warn_pragma_align_invalid_option) | 2048 PP.Diag(Tok.getLocation(), diag::warn_pragma_align_invalid_option) |
1940 << IsOptions; | 2049 << IsOptions; |
1941 return; | 2050 return; |
2051 } | |
2052 | |
2053 if (PP.getLangOpts().XLPragmaPack) { | |
2054 PP.Lex(Tok); | |
2055 if (Tok.isNot(tok::r_paren)) { | |
2056 PP.Diag(Tok.getLocation(), diag::warn_pragma_expected_rparen) << "align"; | |
2057 return; | |
2058 } | |
1942 } | 2059 } |
1943 | 2060 |
1944 SourceLocation EndLoc = Tok.getLocation(); | 2061 SourceLocation EndLoc = Tok.getLocation(); |
1945 PP.Lex(Tok); | 2062 PP.Lex(Tok); |
1946 if (Tok.isNot(tok::eod)) { | 2063 if (Tok.isNot(tok::eod)) { |
2508 } | 2625 } |
2509 // Add a sentinel EoF token to the end of the list. | 2626 // Add a sentinel EoF token to the end of the list. |
2510 TokenVector.push_back(EoF); | 2627 TokenVector.push_back(EoF); |
2511 // We must allocate this array with new because EnterTokenStream is going to | 2628 // We must allocate this array with new because EnterTokenStream is going to |
2512 // delete it later. | 2629 // delete it later. |
2630 markAsReinjectedForRelexing(TokenVector); | |
2513 auto TokenArray = std::make_unique<Token[]>(TokenVector.size()); | 2631 auto TokenArray = std::make_unique<Token[]>(TokenVector.size()); |
2514 std::copy(TokenVector.begin(), TokenVector.end(), TokenArray.get()); | 2632 std::copy(TokenVector.begin(), TokenVector.end(), TokenArray.get()); |
2515 auto Value = new (PP.getPreprocessorAllocator()) | 2633 auto Value = new (PP.getPreprocessorAllocator()) |
2516 std::pair<std::unique_ptr<Token[]>, size_t>(std::move(TokenArray), | 2634 std::pair<std::unique_ptr<Token[]>, size_t>(std::move(TokenArray), |
2517 TokenVector.size()); | 2635 TokenVector.size()); |
2533 void PragmaFloatControlHandler::HandlePragma(Preprocessor &PP, | 2651 void PragmaFloatControlHandler::HandlePragma(Preprocessor &PP, |
2534 PragmaIntroducer Introducer, | 2652 PragmaIntroducer Introducer, |
2535 Token &Tok) { | 2653 Token &Tok) { |
2536 Sema::PragmaMsStackAction Action = Sema::PSK_Set; | 2654 Sema::PragmaMsStackAction Action = Sema::PSK_Set; |
2537 SourceLocation FloatControlLoc = Tok.getLocation(); | 2655 SourceLocation FloatControlLoc = Tok.getLocation(); |
2656 Token PragmaName = Tok; | |
2657 if (!PP.getTargetInfo().hasStrictFP() && !PP.getLangOpts().ExpStrictFP) { | |
2658 PP.Diag(Tok.getLocation(), diag::warn_pragma_fp_ignored) | |
2659 << PragmaName.getIdentifierInfo()->getName(); | |
2660 return; | |
2661 } | |
2538 PP.Lex(Tok); | 2662 PP.Lex(Tok); |
2539 if (Tok.isNot(tok::l_paren)) { | 2663 if (Tok.isNot(tok::l_paren)) { |
2540 PP.Diag(FloatControlLoc, diag::err_expected) << tok::l_paren; | 2664 PP.Diag(FloatControlLoc, diag::err_expected) << tok::l_paren; |
2541 return; | 2665 return; |
2542 } | 2666 } |
2723 if (Tok.isNot(tok::identifier)) { | 2847 if (Tok.isNot(tok::identifier)) { |
2724 PP.Diag(CommentLoc, diag::err_pragma_comment_malformed); | 2848 PP.Diag(CommentLoc, diag::err_pragma_comment_malformed); |
2725 return; | 2849 return; |
2726 } | 2850 } |
2727 | 2851 |
2728 // Verify that this is one of the 5 whitelisted options. | 2852 // Verify that this is one of the 5 explicitly listed options. |
2729 IdentifierInfo *II = Tok.getIdentifierInfo(); | 2853 IdentifierInfo *II = Tok.getIdentifierInfo(); |
2730 PragmaMSCommentKind Kind = | 2854 PragmaMSCommentKind Kind = |
2731 llvm::StringSwitch<PragmaMSCommentKind>(II->getName()) | 2855 llvm::StringSwitch<PragmaMSCommentKind>(II->getName()) |
2732 .Case("linker", PCK_Linker) | 2856 .Case("linker", PCK_Linker) |
2733 .Case("lib", PCK_Lib) | 2857 .Case("lib", PCK_Lib) |
2764 | 2888 |
2765 // FIXME: warn that 'exestr' is deprecated. | 2889 // FIXME: warn that 'exestr' is deprecated. |
2766 // FIXME: If the kind is "compiler" warn if the string is present (it is | 2890 // FIXME: If the kind is "compiler" warn if the string is present (it is |
2767 // ignored). | 2891 // ignored). |
2768 // The MSDN docs say that "lib" and "linker" require a string and have a short | 2892 // The MSDN docs say that "lib" and "linker" require a string and have a short |
2769 // whitelist of linker options they support, but in practice MSVC doesn't | 2893 // list of linker options they support, but in practice MSVC doesn't |
2770 // issue a diagnostic. Therefore neither does clang. | 2894 // issue a diagnostic. Therefore neither does clang. |
2771 | 2895 |
2772 if (Tok.isNot(tok::r_paren)) { | 2896 if (Tok.isNot(tok::r_paren)) { |
2773 PP.Diag(Tok.getLocation(), diag::err_pragma_comment_malformed); | 2897 PP.Diag(Tok.getLocation(), diag::err_pragma_comment_malformed); |
2774 return; | 2898 return; |
2826 } | 2950 } |
2827 | 2951 |
2828 namespace { | 2952 namespace { |
2829 /// Used as the annotation value for tok::annot_pragma_fp. | 2953 /// Used as the annotation value for tok::annot_pragma_fp. |
2830 struct TokFPAnnotValue { | 2954 struct TokFPAnnotValue { |
2831 enum FlagKinds { Contract, Reassociate }; | 2955 enum FlagKinds { Contract, Reassociate, Exceptions }; |
2832 enum FlagValues { On, Off, Fast }; | 2956 enum FlagValues { On, Off, Fast }; |
2833 | 2957 |
2834 FlagKinds FlagKind; | 2958 llvm::Optional<LangOptions::FPModeKind> ContractValue; |
2835 FlagValues FlagValue; | 2959 llvm::Optional<LangOptions::FPModeKind> ReassociateValue; |
2960 llvm::Optional<LangOptions::FPExceptionModeKind> ExceptionsValue; | |
2836 }; | 2961 }; |
2837 } // end anonymous namespace | 2962 } // end anonymous namespace |
2838 | 2963 |
2839 void PragmaFPHandler::HandlePragma(Preprocessor &PP, | 2964 void PragmaFPHandler::HandlePragma(Preprocessor &PP, |
2840 PragmaIntroducer Introducer, Token &Tok) { | 2965 PragmaIntroducer Introducer, Token &Tok) { |
2847 PP.Diag(Tok.getLocation(), diag::err_pragma_fp_invalid_option) | 2972 PP.Diag(Tok.getLocation(), diag::err_pragma_fp_invalid_option) |
2848 << /*MissingOption=*/true << ""; | 2973 << /*MissingOption=*/true << ""; |
2849 return; | 2974 return; |
2850 } | 2975 } |
2851 | 2976 |
2977 auto *AnnotValue = new (PP.getPreprocessorAllocator()) TokFPAnnotValue; | |
2852 while (Tok.is(tok::identifier)) { | 2978 while (Tok.is(tok::identifier)) { |
2853 IdentifierInfo *OptionInfo = Tok.getIdentifierInfo(); | 2979 IdentifierInfo *OptionInfo = Tok.getIdentifierInfo(); |
2854 | 2980 |
2855 auto FlagKind = | 2981 auto FlagKind = |
2856 llvm::StringSwitch<llvm::Optional<TokFPAnnotValue::FlagKinds>>( | 2982 llvm::StringSwitch<llvm::Optional<TokFPAnnotValue::FlagKinds>>( |
2857 OptionInfo->getName()) | 2983 OptionInfo->getName()) |
2858 .Case("contract", TokFPAnnotValue::Contract) | 2984 .Case("contract", TokFPAnnotValue::Contract) |
2859 .Case("reassociate", TokFPAnnotValue::Reassociate) | 2985 .Case("reassociate", TokFPAnnotValue::Reassociate) |
2986 .Case("exceptions", TokFPAnnotValue::Exceptions) | |
2860 .Default(None); | 2987 .Default(None); |
2861 if (!FlagKind) { | 2988 if (!FlagKind) { |
2862 PP.Diag(Tok.getLocation(), diag::err_pragma_fp_invalid_option) | 2989 PP.Diag(Tok.getLocation(), diag::err_pragma_fp_invalid_option) |
2863 << /*MissingOption=*/false << OptionInfo; | 2990 << /*MissingOption=*/false << OptionInfo; |
2864 return; | 2991 return; |
2873 PP.Lex(Tok); | 3000 PP.Lex(Tok); |
2874 | 3001 |
2875 if (Tok.isNot(tok::identifier)) { | 3002 if (Tok.isNot(tok::identifier)) { |
2876 PP.Diag(Tok.getLocation(), diag::err_pragma_fp_invalid_argument) | 3003 PP.Diag(Tok.getLocation(), diag::err_pragma_fp_invalid_argument) |
2877 << PP.getSpelling(Tok) << OptionInfo->getName() | 3004 << PP.getSpelling(Tok) << OptionInfo->getName() |
2878 << (FlagKind == TokFPAnnotValue::Reassociate); | 3005 << static_cast<int>(*FlagKind); |
2879 return; | 3006 return; |
2880 } | 3007 } |
2881 const IdentifierInfo *II = Tok.getIdentifierInfo(); | 3008 const IdentifierInfo *II = Tok.getIdentifierInfo(); |
2882 | 3009 |
2883 auto FlagValue = | 3010 if (FlagKind == TokFPAnnotValue::Contract) { |
2884 llvm::StringSwitch<llvm::Optional<TokFPAnnotValue::FlagValues>>( | 3011 AnnotValue->ContractValue = |
2885 II->getName()) | 3012 llvm::StringSwitch<llvm::Optional<LangOptions::FPModeKind>>( |
2886 .Case("on", TokFPAnnotValue::On) | 3013 II->getName()) |
2887 .Case("off", TokFPAnnotValue::Off) | 3014 .Case("on", LangOptions::FPModeKind::FPM_On) |
2888 .Case("fast", TokFPAnnotValue::Fast) | 3015 .Case("off", LangOptions::FPModeKind::FPM_Off) |
2889 .Default(llvm::None); | 3016 .Case("fast", LangOptions::FPModeKind::FPM_Fast) |
2890 | 3017 .Default(llvm::None); |
2891 if (!FlagValue || (FlagKind == TokFPAnnotValue::Reassociate && | 3018 if (!AnnotValue->ContractValue) { |
2892 FlagValue == TokFPAnnotValue::Fast)) { | 3019 PP.Diag(Tok.getLocation(), diag::err_pragma_fp_invalid_argument) |
2893 PP.Diag(Tok.getLocation(), diag::err_pragma_fp_invalid_argument) | 3020 << PP.getSpelling(Tok) << OptionInfo->getName() << *FlagKind; |
2894 << PP.getSpelling(Tok) << OptionInfo->getName() | 3021 return; |
2895 << (FlagKind == TokFPAnnotValue::Reassociate); | 3022 } |
2896 return; | 3023 } else if (FlagKind == TokFPAnnotValue::Reassociate) { |
3024 AnnotValue->ReassociateValue = | |
3025 llvm::StringSwitch<llvm::Optional<LangOptions::FPModeKind>>( | |
3026 II->getName()) | |
3027 .Case("on", LangOptions::FPModeKind::FPM_On) | |
3028 .Case("off", LangOptions::FPModeKind::FPM_Off) | |
3029 .Default(llvm::None); | |
3030 if (!AnnotValue->ReassociateValue) { | |
3031 PP.Diag(Tok.getLocation(), diag::err_pragma_fp_invalid_argument) | |
3032 << PP.getSpelling(Tok) << OptionInfo->getName() << *FlagKind; | |
3033 return; | |
3034 } | |
3035 } else if (FlagKind == TokFPAnnotValue::Exceptions) { | |
3036 AnnotValue->ExceptionsValue = | |
3037 llvm::StringSwitch<llvm::Optional<LangOptions::FPExceptionModeKind>>( | |
3038 II->getName()) | |
3039 .Case("ignore", LangOptions::FPE_Ignore) | |
3040 .Case("maytrap", LangOptions::FPE_MayTrap) | |
3041 .Case("strict", LangOptions::FPE_Strict) | |
3042 .Default(llvm::None); | |
3043 if (!AnnotValue->ExceptionsValue) { | |
3044 PP.Diag(Tok.getLocation(), diag::err_pragma_fp_invalid_argument) | |
3045 << PP.getSpelling(Tok) << OptionInfo->getName() << *FlagKind; | |
3046 return; | |
3047 } | |
2897 } | 3048 } |
2898 PP.Lex(Tok); | 3049 PP.Lex(Tok); |
2899 | 3050 |
2900 // Read ')' | 3051 // Read ')' |
2901 if (Tok.isNot(tok::r_paren)) { | 3052 if (Tok.isNot(tok::r_paren)) { |
2902 PP.Diag(Tok.getLocation(), diag::err_expected) << tok::r_paren; | 3053 PP.Diag(Tok.getLocation(), diag::err_expected) << tok::r_paren; |
2903 return; | 3054 return; |
2904 } | 3055 } |
2905 PP.Lex(Tok); | 3056 PP.Lex(Tok); |
2906 | |
2907 auto *AnnotValue = new (PP.getPreprocessorAllocator()) | |
2908 TokFPAnnotValue{*FlagKind, *FlagValue}; | |
2909 // Generate the fp annotation token. | |
2910 Token FPTok; | |
2911 FPTok.startToken(); | |
2912 FPTok.setKind(tok::annot_pragma_fp); | |
2913 FPTok.setLocation(PragmaName.getLocation()); | |
2914 FPTok.setAnnotationEndLoc(PragmaName.getLocation()); | |
2915 FPTok.setAnnotationValue(reinterpret_cast<void *>(AnnotValue)); | |
2916 TokenList.push_back(FPTok); | |
2917 } | 3057 } |
2918 | 3058 |
2919 if (Tok.isNot(tok::eod)) { | 3059 if (Tok.isNot(tok::eod)) { |
2920 PP.Diag(Tok.getLocation(), diag::warn_pragma_extra_tokens_at_eol) | 3060 PP.Diag(Tok.getLocation(), diag::warn_pragma_extra_tokens_at_eol) |
2921 << "clang fp"; | 3061 << "clang fp"; |
2922 return; | 3062 return; |
2923 } | 3063 } |
2924 | 3064 |
3065 Token FPTok; | |
3066 FPTok.startToken(); | |
3067 FPTok.setKind(tok::annot_pragma_fp); | |
3068 FPTok.setLocation(PragmaName.getLocation()); | |
3069 FPTok.setAnnotationEndLoc(PragmaName.getLocation()); | |
3070 FPTok.setAnnotationValue(reinterpret_cast<void *>(AnnotValue)); | |
3071 TokenList.push_back(FPTok); | |
3072 | |
2925 auto TokenArray = std::make_unique<Token[]>(TokenList.size()); | 3073 auto TokenArray = std::make_unique<Token[]>(TokenList.size()); |
2926 std::copy(TokenList.begin(), TokenList.end(), TokenArray.get()); | 3074 std::copy(TokenList.begin(), TokenList.end(), TokenArray.get()); |
2927 | 3075 |
2928 PP.EnterTokenStream(std::move(TokenArray), TokenList.size(), | 3076 PP.EnterTokenStream(std::move(TokenArray), TokenList.size(), |
2929 /*DisableMacroExpansion=*/false, /*IsReinject=*/false); | 3077 /*DisableMacroExpansion=*/false, /*IsReinject=*/false); |
3078 } | |
3079 | |
3080 void PragmaSTDC_FENV_ROUNDHandler::HandlePragma(Preprocessor &PP, | |
3081 PragmaIntroducer Introducer, | |
3082 Token &Tok) { | |
3083 Token PragmaName = Tok; | |
3084 SmallVector<Token, 1> TokenList; | |
3085 if (!PP.getTargetInfo().hasStrictFP() && !PP.getLangOpts().ExpStrictFP) { | |
3086 PP.Diag(Tok.getLocation(), diag::warn_pragma_fp_ignored) | |
3087 << PragmaName.getIdentifierInfo()->getName(); | |
3088 return; | |
3089 } | |
3090 | |
3091 PP.Lex(Tok); | |
3092 if (Tok.isNot(tok::identifier)) { | |
3093 PP.Diag(Tok.getLocation(), diag::warn_pragma_expected_identifier) | |
3094 << PragmaName.getIdentifierInfo()->getName(); | |
3095 return; | |
3096 } | |
3097 IdentifierInfo *II = Tok.getIdentifierInfo(); | |
3098 | |
3099 auto RM = | |
3100 llvm::StringSwitch<llvm::RoundingMode>(II->getName()) | |
3101 .Case("FE_TOWARDZERO", llvm::RoundingMode::TowardZero) | |
3102 .Case("FE_TONEAREST", llvm::RoundingMode::NearestTiesToEven) | |
3103 .Case("FE_UPWARD", llvm::RoundingMode::TowardPositive) | |
3104 .Case("FE_DOWNWARD", llvm::RoundingMode::TowardNegative) | |
3105 .Case("FE_TONEARESTFROMZERO", llvm::RoundingMode::NearestTiesToAway) | |
3106 .Case("FE_DYNAMIC", llvm::RoundingMode::Dynamic) | |
3107 .Default(llvm::RoundingMode::Invalid); | |
3108 if (RM == llvm::RoundingMode::Invalid) { | |
3109 PP.Diag(Tok.getLocation(), diag::warn_stdc_unknown_rounding_mode); | |
3110 return; | |
3111 } | |
3112 PP.Lex(Tok); | |
3113 | |
3114 if (Tok.isNot(tok::eod)) { | |
3115 PP.Diag(Tok.getLocation(), diag::warn_pragma_extra_tokens_at_eol) | |
3116 << "STDC FENV_ROUND"; | |
3117 return; | |
3118 } | |
3119 | |
3120 // Until the pragma is fully implemented, issue a warning. | |
3121 PP.Diag(Tok.getLocation(), diag::warn_stdc_fenv_round_not_supported); | |
3122 | |
3123 MutableArrayRef<Token> Toks(PP.getPreprocessorAllocator().Allocate<Token>(1), | |
3124 1); | |
3125 Toks[0].startToken(); | |
3126 Toks[0].setKind(tok::annot_pragma_fenv_round); | |
3127 Toks[0].setLocation(Tok.getLocation()); | |
3128 Toks[0].setAnnotationEndLoc(Tok.getLocation()); | |
3129 Toks[0].setAnnotationValue( | |
3130 reinterpret_cast<void *>(static_cast<uintptr_t>(RM))); | |
3131 PP.EnterTokenStream(Toks, /*DisableMacroExpansion=*/true, | |
3132 /*IsReinject=*/false); | |
2930 } | 3133 } |
2931 | 3134 |
2932 void Parser::HandlePragmaFP() { | 3135 void Parser::HandlePragmaFP() { |
2933 assert(Tok.is(tok::annot_pragma_fp)); | 3136 assert(Tok.is(tok::annot_pragma_fp)); |
2934 auto *AnnotValue = | 3137 auto *AnnotValue = |
2935 reinterpret_cast<TokFPAnnotValue *>(Tok.getAnnotationValue()); | 3138 reinterpret_cast<TokFPAnnotValue *>(Tok.getAnnotationValue()); |
2936 | 3139 |
2937 if (AnnotValue->FlagKind == TokFPAnnotValue::Reassociate) | 3140 if (AnnotValue->ReassociateValue) |
2938 Actions.ActOnPragmaFPReassociate(AnnotValue->FlagValue == | 3141 Actions.ActOnPragmaFPReassociate(Tok.getLocation(), |
2939 TokFPAnnotValue::On); | 3142 *AnnotValue->ReassociateValue == |
2940 else { | 3143 LangOptions::FPModeKind::FPM_On); |
2941 LangOptions::FPModeKind FPC; | 3144 if (AnnotValue->ContractValue) |
2942 switch (AnnotValue->FlagValue) { | 3145 Actions.ActOnPragmaFPContract(Tok.getLocation(), |
2943 case TokFPAnnotValue::Off: | 3146 *AnnotValue->ContractValue); |
2944 FPC = LangOptions::FPM_Off; | 3147 if (AnnotValue->ExceptionsValue) |
2945 break; | 3148 Actions.ActOnPragmaFPExceptions(Tok.getLocation(), |
2946 case TokFPAnnotValue::On: | 3149 *AnnotValue->ExceptionsValue); |
2947 FPC = LangOptions::FPM_On; | |
2948 break; | |
2949 case TokFPAnnotValue::Fast: | |
2950 FPC = LangOptions::FPM_Fast; | |
2951 break; | |
2952 } | |
2953 Actions.ActOnPragmaFPContract(FPC); | |
2954 } | |
2955 ConsumeAnnotationToken(); | 3150 ConsumeAnnotationToken(); |
2956 } | 3151 } |
2957 | 3152 |
2958 /// Parses loop or unroll pragma hint value and fills in Info. | 3153 /// Parses loop or unroll pragma hint value and fills in Info. |
2959 static bool ParseLoopHintValue(Preprocessor &PP, Token &Tok, Token PragmaName, | 3154 static bool ParseLoopHintValue(Preprocessor &PP, Token &Tok, Token PragmaName, |
2988 EOFTok.startToken(); | 3183 EOFTok.startToken(); |
2989 EOFTok.setKind(tok::eof); | 3184 EOFTok.setKind(tok::eof); |
2990 EOFTok.setLocation(Tok.getLocation()); | 3185 EOFTok.setLocation(Tok.getLocation()); |
2991 ValueList.push_back(EOFTok); // Terminates expression for parsing. | 3186 ValueList.push_back(EOFTok); // Terminates expression for parsing. |
2992 | 3187 |
3188 markAsReinjectedForRelexing(ValueList); | |
2993 Info.Toks = llvm::makeArrayRef(ValueList).copy(PP.getPreprocessorAllocator()); | 3189 Info.Toks = llvm::makeArrayRef(ValueList).copy(PP.getPreprocessorAllocator()); |
2994 | 3190 |
2995 Info.PragmaName = PragmaName; | 3191 Info.PragmaName = PragmaName; |
2996 Info.Option = Option; | 3192 Info.Option = Option; |
2997 return false; | 3193 return false; |
3097 | 3293 |
3098 // Generate the loop hint token. | 3294 // Generate the loop hint token. |
3099 Token LoopHintTok; | 3295 Token LoopHintTok; |
3100 LoopHintTok.startToken(); | 3296 LoopHintTok.startToken(); |
3101 LoopHintTok.setKind(tok::annot_pragma_loop_hint); | 3297 LoopHintTok.setKind(tok::annot_pragma_loop_hint); |
3102 LoopHintTok.setLocation(PragmaName.getLocation()); | 3298 LoopHintTok.setLocation(Introducer.Loc); |
3103 LoopHintTok.setAnnotationEndLoc(PragmaName.getLocation()); | 3299 LoopHintTok.setAnnotationEndLoc(PragmaName.getLocation()); |
3104 LoopHintTok.setAnnotationValue(static_cast<void *>(Info)); | 3300 LoopHintTok.setAnnotationValue(static_cast<void *>(Info)); |
3105 TokenList.push_back(LoopHintTok); | 3301 TokenList.push_back(LoopHintTok); |
3106 } | 3302 } |
3107 | 3303 |
3184 | 3380 |
3185 // Generate the hint token. | 3381 // Generate the hint token. |
3186 auto TokenArray = std::make_unique<Token[]>(1); | 3382 auto TokenArray = std::make_unique<Token[]>(1); |
3187 TokenArray[0].startToken(); | 3383 TokenArray[0].startToken(); |
3188 TokenArray[0].setKind(tok::annot_pragma_loop_hint); | 3384 TokenArray[0].setKind(tok::annot_pragma_loop_hint); |
3189 TokenArray[0].setLocation(PragmaName.getLocation()); | 3385 TokenArray[0].setLocation(Introducer.Loc); |
3190 TokenArray[0].setAnnotationEndLoc(PragmaName.getLocation()); | 3386 TokenArray[0].setAnnotationEndLoc(PragmaName.getLocation()); |
3191 TokenArray[0].setAnnotationValue(static_cast<void *>(Info)); | 3387 TokenArray[0].setAnnotationValue(static_cast<void *>(Info)); |
3192 PP.EnterTokenStream(std::move(TokenArray), 1, | 3388 PP.EnterTokenStream(std::move(TokenArray), 1, |
3193 /*DisableMacroExpansion=*/false, /*IsReinject=*/false); | 3389 /*DisableMacroExpansion=*/false, /*IsReinject=*/false); |
3194 } | 3390 } |
3444 EOFTok.startToken(); | 3640 EOFTok.startToken(); |
3445 EOFTok.setKind(tok::eof); | 3641 EOFTok.setKind(tok::eof); |
3446 EOFTok.setLocation(EndLoc); | 3642 EOFTok.setLocation(EndLoc); |
3447 AttributeTokens.push_back(EOFTok); | 3643 AttributeTokens.push_back(EOFTok); |
3448 | 3644 |
3645 markAsReinjectedForRelexing(AttributeTokens); | |
3449 Info->Tokens = | 3646 Info->Tokens = |
3450 llvm::makeArrayRef(AttributeTokens).copy(PP.getPreprocessorAllocator()); | 3647 llvm::makeArrayRef(AttributeTokens).copy(PP.getPreprocessorAllocator()); |
3451 } | 3648 } |
3452 | 3649 |
3453 if (Tok.isNot(tok::eod)) | 3650 if (Tok.isNot(tok::eod)) |