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))