35 #include "llvm/ADT/ArrayRef.h" 36 #include "llvm/ADT/ScopeExit.h" 37 #include "llvm/ADT/SmallString.h" 38 #include "llvm/ADT/SmallVector.h" 39 #include "llvm/ADT/STLExtras.h" 40 #include "llvm/ADT/StringSwitch.h" 41 #include "llvm/ADT/StringRef.h" 42 #include "llvm/Support/AlignOf.h" 43 #include "llvm/Support/ErrorHandling.h" 44 #include "llvm/Support/Path.h" 52 using namespace clang;
59 auto *MIChain =
new (BP) MacroInfoChain{L, MIChainHead};
60 MIChainHead = MIChain;
70 Preprocessor::AllocateUndefMacroDirective(
SourceLocation UndefLoc) {
88 while (Tmp.
isNot(tok::eod)) {
89 assert(Tmp.
isNot(
tok::eof) &&
"EOF seen while discarding directive tokens");
110 if (Text.size() >= 2 && Text[0] ==
'_' &&
116 if (Lang.CPlusPlus) {
117 if (Text.find(
"__") != StringRef::npos)
130 StringRef ModuleName) {
136 !CurrentModule.endswith(
"_Private") && TopLevelName.endswith(
"_Private"))
137 TopLevelName = TopLevelName.drop_back(8);
139 return TopLevelName == CurrentModule;
149 if (Lang.CPlusPlus11 && (Text.equals(
"override") || Text.equals(
"final")))
171 if (::llvm::sys::path::begin(Include)->equals_lower(
"boost"))
176 static const size_t MaxStdHeaderNameLen = 18u;
177 if (Include.size() > MaxStdHeaderNameLen)
182 for (
char &Ch : LowerInclude) {
184 if (static_cast<unsigned char>(Ch) > 0x7f)
187 if (Ch >=
'A' && Ch <=
'Z')
190 else if (::llvm::sys::path::is_separator(Ch))
195 return llvm::StringSwitch<bool>(LowerInclude)
197 .Cases(
"assert.h",
"complex.h",
"ctype.h",
"errno.h",
"fenv.h",
true)
198 .Cases(
"float.h",
"inttypes.h",
"iso646.h",
"limits.h",
"locale.h",
true)
199 .Cases(
"math.h",
"setjmp.h",
"signal.h",
"stdalign.h",
"stdarg.h",
true)
200 .Cases(
"stdatomic.h",
"stdbool.h",
"stddef.h",
"stdint.h",
"stdio.h",
true)
201 .Cases(
"stdlib.h",
"stdnoreturn.h",
"string.h",
"tgmath.h",
"threads.h",
true)
202 .Cases(
"time.h",
"uchar.h",
"wchar.h",
"wctype.h",
true)
205 .Cases(
"cassert",
"ccomplex",
"cctype",
"cerrno",
"cfenv",
true)
206 .Cases(
"cfloat",
"cinttypes",
"ciso646",
"climits",
"clocale",
true)
207 .Cases(
"cmath",
"csetjmp",
"csignal",
"cstdalign",
"cstdarg",
true)
208 .Cases(
"cstdbool",
"cstddef",
"cstdint",
"cstdio",
"cstdlib",
true)
209 .Cases(
"cstring",
"ctgmath",
"ctime",
"cuchar",
"cwchar",
true)
210 .Case(
"cwctype",
true)
213 .Cases(
"algorithm",
"fstream",
"list",
"regex",
"thread",
true)
214 .Cases(
"array",
"functional",
"locale",
"scoped_allocator",
"tuple",
true)
215 .Cases(
"atomic",
"future",
"map",
"set",
"type_traits",
true)
216 .Cases(
"bitset",
"initializer_list",
"memory",
"shared_mutex",
"typeindex",
true)
217 .Cases(
"chrono",
"iomanip",
"mutex",
"sstream",
"typeinfo",
true)
218 .Cases(
"codecvt",
"ios",
"new",
"stack",
"unordered_map",
true)
219 .Cases(
"complex",
"iosfwd",
"numeric",
"stdexcept",
"unordered_set",
true)
220 .Cases(
"condition_variable",
"iostream",
"ostream",
"streambuf",
"utility",
true)
221 .Cases(
"deque",
"istream",
"queue",
"string",
"valarray",
true)
222 .Cases(
"exception",
"iterator",
"random",
"strstream",
"vector",
true)
223 .Cases(
"forward_list",
"limits",
"ratio",
"system_error",
true)
226 .Cases(
"aio.h",
"arpa/inet.h",
"cpio.h",
"dirent.h",
"dlfcn.h",
true)
227 .Cases(
"fcntl.h",
"fmtmsg.h",
"fnmatch.h",
"ftw.h",
"glob.h",
true)
228 .Cases(
"grp.h",
"iconv.h",
"langinfo.h",
"libgen.h",
"monetary.h",
true)
229 .Cases(
"mqueue.h",
"ndbm.h",
"net/if.h",
"netdb.h",
"netinet/in.h",
true)
230 .Cases(
"netinet/tcp.h",
"nl_types.h",
"poll.h",
"pthread.h",
"pwd.h",
true)
231 .Cases(
"regex.h",
"sched.h",
"search.h",
"semaphore.h",
"spawn.h",
true)
232 .Cases(
"strings.h",
"stropts.h",
"sys/ipc.h",
"sys/mman.h",
"sys/msg.h",
true)
233 .Cases(
"sys/resource.h",
"sys/select.h",
"sys/sem.h",
"sys/shm.h",
"sys/socket.h",
true)
234 .Cases(
"sys/stat.h",
"sys/statvfs.h",
"sys/time.h",
"sys/times.h",
"sys/types.h",
true)
235 .Cases(
"sys/uio.h",
"sys/un.h",
"sys/utsname.h",
"sys/wait.h",
"syslog.h",
true)
236 .Cases(
"tar.h",
"termios.h",
"trace.h",
"ulimit.h",
true)
237 .Cases(
"unistd.h",
"utime.h",
"utmpx.h",
"wordexp.h",
true)
244 if (MacroNameTok.
is(tok::eod))
245 return Diag(MacroNameTok, diag::err_pp_missing_macro_name);
249 return Diag(MacroNameTok, diag::err_pp_macro_not_identifier);
255 ? diag::ext_pp_operator_used_as_macro_name
256 : diag::err_pp_operator_used_as_macro_name)
257 << II << MacroNameTok.
getKind();
264 return Diag(MacroNameTok, diag::err_defined_macro_name);
272 Diag(MacroNameTok, diag::ext_pp_undef_builtin_macro);
297 Diag(MacroNameTok, diag::warn_pp_macro_is_reserved_id);
313 void Preprocessor::ReadMacroName(
Token &MacroNameTok,
MacroUse isDefineUndef,
318 if (MacroNameTok.
is(tok::code_completion)) {
330 if (MacroNameTok.
isNot(tok::eod)) {
331 MacroNameTok.
setKind(tok::eod);
355 while (Tmp.
is(tok::comment))
358 if (Tmp.
is(tok::eod))
366 if ((LangOpts.GNUMode || LangOpts.C99 || LangOpts.CPlusPlus) &&
369 Diag(Tmp, diag::ext_pp_extra_tokens_at_eol) << DirType << Hint;
381 void Preprocessor::SkipExcludedConditionalBlock(
SourceLocation HashTokenLoc,
383 bool FoundNonSkipPortion,
387 assert(!CurTokenLexer && CurPPLexer &&
"Lexing a macro, not a file?");
389 if (PreambleConditionalStack.reachedEOFWhileSkipping())
390 PreambleConditionalStack.clearSkipInfo();
393 FoundNonSkipPortion, FoundElse);
402 if (Tok.
is(tok::code_completion)) {
414 if (PreambleConditionalStack.isRecording())
415 PreambleConditionalStack.SkipInfo.emplace(
416 HashTokenLoc, IfTokenLoc, FoundNonSkipPortion, FoundElse, ElseLoc);
428 if (CurLexer) CurLexer->SetKeepWhitespaceMode(
false);
436 if (Tok.
isNot(tok::raw_identifier)) {
439 if (CurLexer) CurLexer->resetExtendedTokenMode();
450 char FirstChar = RI[0];
451 if (FirstChar >=
'a' && FirstChar <=
'z' &&
452 FirstChar !=
'i' && FirstChar !=
'e') {
455 if (CurLexer) CurLexer->resetExtendedTokenMode();
462 char DirectiveBuf[20];
468 size_t IdLen = DirectiveStr.size();
472 if (CurLexer) CurLexer->resetExtendedTokenMode();
475 memcpy(DirectiveBuf, &DirectiveStr[0], IdLen);
476 Directive = StringRef(DirectiveBuf, IdLen);
479 if (Directive.startswith(
"if")) {
480 StringRef Sub = Directive.substr(2);
491 }
else if (Directive[0] ==
'e') {
492 StringRef Sub = Directive.substr(1);
498 assert(!InCond &&
"Can't be skipping if not in a conditional!");
513 }
else if (Sub ==
"lse") {
520 if (CondInfo.
FoundElse)
Diag(Tok, diag::pp_err_else_after_else);
540 }
else if (Sub ==
"lif") {
544 if (CondInfo.
FoundElse)
Diag(Tok, diag::pp_err_elif_after_else);
553 assert(CurPPLexer->
LexingRawMode &&
"We have to be skipping here!");
556 DirectiveEvalResult DER = EvaluateDirectiveExpression(IfNDefMacro);
557 const bool CondValue = DER.Conditional;
576 if (CurLexer) CurLexer->resetExtendedTokenMode();
587 Callbacks->SourceRangeSkipped(
616 assert(M &&
"no module to include");
627 !InGlobalModuleFragment)
644 if (InGlobalModuleFragment) {
651 bool InTextualHeader =
false;
653 if (!Header.getModule()->isSubModuleOf(TopM))
660 if (Header.isAccessibleFrom(IncM))
670 InTextualHeader =
true;
673 if (!InTextualHeader)
688 bool *IsFrameworkFound,
bool SkipCache) {
690 bool RequestingModuleIsModuleInterface = !SourceMgr.
isInMainFile(FilenameLoc);
696 bool BuildSystemModule =
false;
697 if (!FromDir && !FromFile) {
715 Includers.push_back(std::make_pair(
nullptr, MainFileDir));
717 }
else if ((FileEnt =
719 Includers.push_back(std::make_pair(FileEnt, FileMgr.
getDirectory(
".")));
721 Includers.push_back(std::make_pair(FileEnt, FileEnt->
getDir()));
727 if (LangOpts.MSVCCompat && !isAngled) {
728 for (IncludeStackInfo &ISEntry : llvm::reverse(IncludeMacroStack)) {
729 if (IsFileLexer(ISEntry))
730 if ((FileEnt = ISEntry.ThePPLexer->getFileEntry()))
731 Includers.push_back(std::make_pair(FileEnt, FileEnt->
getDir()));
736 CurDir = CurDirLookup;
744 Filename, FilenameLoc, isAngled, TmpFromDir, TmpCurDir,
745 Includers, SearchPath, RelativePath, RequestingModule,
746 SuggestedModule,
nullptr,
747 nullptr, SkipCache)) {
749 TmpFromDir = TmpCurDir;
751 if (FE == FromFile) {
753 FromDir = TmpFromDir;
762 Filename, FilenameLoc, isAngled, FromDir, CurDir, Includers, SearchPath,
763 RelativePath, RequestingModule, SuggestedModule, IsMapped,
764 IsFrameworkFound, SkipCache, BuildSystemModule);
766 if (SuggestedModule && !LangOpts.AsmPreprocessor)
768 RequestingModule, RequestingModuleIsModuleInterface, FilenameLoc,
780 SearchPath, RelativePath,
783 if (SuggestedModule && !LangOpts.AsmPreprocessor)
785 RequestingModule, RequestingModuleIsModuleInterface, FilenameLoc,
792 for (IncludeStackInfo &ISEntry : llvm::reverse(IncludeMacroStack)) {
793 if (IsFileLexer(ISEntry)) {
794 if ((CurFileEnt = ISEntry.ThePPLexer->getFileEntry())) {
796 Filename, CurFileEnt, SearchPath, RelativePath,
797 RequestingModule, SuggestedModule))) {
798 if (SuggestedModule && !LangOpts.AsmPreprocessor)
800 RequestingModule, RequestingModuleIsModuleInterface,
801 FilenameLoc, Filename, FE);
819 : PP(pp), save(pp->DisableMacroExpansion) {
820 if (pp->MacroExpansionInDirectivesOverride)
821 pp->DisableMacroExpansion =
false;
825 PP->DisableMacroExpansion = save;
843 return HandleDefineDirective(Result,
846 if (SkippingUntilPCHThroughHeader &&
848 return HandleIncludeDirective(HashLoc, Result);
850 if (SkippingUntilPragmaHdrStop && II->getPPKeywordID() == tok::pp_pragma) {
853 if (II && II->getName() ==
"hdrstop")
870 CurPPLexer->ParsingPreprocessorDirective =
true;
871 if (CurLexer) CurLexer->SetKeepWhitespaceMode(
false);
873 bool ImmediatelyAfterTopLevelIfndef =
874 CurPPLexer->MIOpt.getImmediatelyAfterTopLevelIfndef();
875 CurPPLexer->MIOpt.resetImmediatelyAfterTopLevelIfndef();
882 bool ReadAnyTokensBeforeDirective =CurPPLexer->MIOpt.getHasReadAnyTokensVal();
901 switch (II->getPPKeywordID()) {
907 Diag(Result, diag::err_embedded_directive) << II->getName();
908 Diag(*ArgMacro, diag::note_macro_expansion_here)
909 << ArgMacro->getIdentifierInfo();
916 Diag(Result, diag::ext_embedded_directive);
923 if (SkippingUntilPCHThroughHeader || SkippingUntilPragmaHdrStop)
929 case tok::code_completion:
931 CodeComplete->CodeCompleteDirective(
932 CurPPLexer->getConditionalStackDepth() > 0);
935 case tok::numeric_constant:
938 return HandleDigitDirective(Result);
948 return HandleIfDirective(Result, SavedHash, ReadAnyTokensBeforeDirective);
950 return HandleIfdefDirective(Result, SavedHash,
false,
953 return HandleIfdefDirective(Result, SavedHash,
true,
954 ReadAnyTokensBeforeDirective);
956 return HandleElifDirective(Result, SavedHash);
958 return HandleElseDirective(Result, SavedHash);
960 return HandleEndifDirective(Result);
972 return HandleDefineDirective(Result, ImmediatelyAfterTopLevelIfndef);
974 return HandleUndefDirective();
978 return HandleLineDirective();
982 return HandleUserDiagnosticDirective(Result,
false);
994 case tok::pp_warning:
995 Diag(Result, diag::ext_pp_warning_directive);
996 return HandleUserDiagnosticDirective(Result,
true);
998 return HandleIdentSCCSDirective(Result);
1000 return HandleIdentSCCSDirective(Result);
1001 case tok::pp_assert:
1004 case tok::pp_unassert:
1008 case tok::pp___public_macro:
1010 return HandleMacroPublicDirective(Result);
1013 case tok::pp___private_macro:
1015 return HandleMacroPrivateDirective();
1026 auto Toks = llvm::make_unique<Token[]>(2);
1028 Toks[0] = SavedHash;
1033 if (Result.
is(tok::hashhash))
1034 Toks[1].setKind(tok::unknown);
1039 EnterTokenStream(std::move(Toks), 2,
false,
false);
1044 Diag(Result, diag::err_pp_invalid_directive);
1056 bool IsGNULineDirective=
false) {
1057 if (DigitTok.
isNot(tok::numeric_constant)) {
1058 PP.
Diag(DigitTok, DiagID);
1060 if (DigitTok.
isNot(tok::eod))
1066 IntegerBuffer.resize(DigitTok.
getLength());
1067 const char *DigitTokBegin = &IntegerBuffer[0];
1068 bool Invalid =
false;
1069 unsigned ActualLength = PP.
getSpelling(DigitTok, DigitTokBegin, &Invalid);
1077 for (
unsigned i = 0;
i != ActualLength; ++
i) {
1080 if (DigitTokBegin[
i] ==
'\'')
1085 diag::err_pp_line_digit_sequence) << IsGNULineDirective;
1090 unsigned NextVal = Val*10+(DigitTokBegin[
i]-
'0');
1091 if (NextVal < Val) {
1092 PP.
Diag(DigitTok, DiagID);
1099 if (DigitTokBegin[0] ==
'0' && Val)
1101 << IsGNULineDirective;
1113 void Preprocessor::HandleLineDirective() {
1121 if (
GetLineValue(DigitTok, LineNo, diag::err_pp_line_requires_integer,*
this))
1125 Diag(DigitTok, diag::ext_pp_line_zero);
1129 unsigned LineLimit = 32768U;
1130 if (LangOpts.C99 || LangOpts.CPlusPlus11)
1131 LineLimit = 2147483648U;
1132 if (LineNo >= LineLimit)
1133 Diag(DigitTok, diag::ext_pp_line_too_big) << LineLimit;
1134 else if (LangOpts.CPlusPlus11 && LineNo >= 32768U)
1135 Diag(DigitTok, diag::warn_cxx98_compat_pp_line_too_big);
1137 int FilenameID = -1;
1143 if (StrTok.
is(tok::eod))
1145 else if (StrTok.
isNot(tok::string_literal)) {
1146 Diag(StrTok, diag::err_pp_line_invalid_filename);
1150 Diag(StrTok, diag::err_invalid_string_udl);
1156 assert(Literal.
isAscii() &&
"Didn't allow wide strings in");
1162 Diag(StrTok, diag::err_pp_linemarker_invalid_filename);
1166 FilenameID = SourceMgr.getLineTableFilenameID(Literal.
GetString());
1179 SourceMgr.getFileCharacteristic(DigitTok.
getLocation());
1181 SourceMgr.AddLineNote(DigitTok.
getLocation(), LineNo, FilenameID,
false,
1185 Callbacks->FileChanged(CurPPLexer->getSourceLocation(),
1197 if (FlagTok.
is(tok::eod))
return false;
1198 if (
GetLineValue(FlagTok, FlagVal, diag::err_pp_linemarker_invalid_flag, PP))
1205 if (FlagTok.
is(tok::eod))
return false;
1206 if (
GetLineValue(FlagTok, FlagVal, diag::err_pp_linemarker_invalid_flag,PP))
1208 }
else if (FlagVal == 2) {
1225 PP.
Diag(FlagTok, diag::err_pp_linemarker_invalid_pop);
1231 if (FlagTok.
is(tok::eod))
return false;
1232 if (
GetLineValue(FlagTok, FlagVal, diag::err_pp_linemarker_invalid_flag,PP))
1238 PP.
Diag(FlagTok, diag::err_pp_linemarker_invalid_flag);
1246 if (FlagTok.
is(tok::eod))
return false;
1247 if (
GetLineValue(FlagTok, FlagVal, diag::err_pp_linemarker_invalid_flag, PP))
1252 PP.
Diag(FlagTok, diag::err_pp_linemarker_invalid_flag);
1260 if (FlagTok.
is(tok::eod))
return false;
1263 PP.
Diag(FlagTok, diag::err_pp_linemarker_invalid_flag);
1275 void Preprocessor::HandleDigitDirective(
Token &DigitTok) {
1279 if (
GetLineValue(DigitTok, LineNo, diag::err_pp_linemarker_requires_integer,
1286 bool IsFileEntry =
false, IsFileExit =
false;
1287 int FilenameID = -1;
1292 if (StrTok.
is(tok::eod)) {
1294 FileKind = SourceMgr.getFileCharacteristic(DigitTok.
getLocation());
1295 }
else if (StrTok.
isNot(tok::string_literal)) {
1296 Diag(StrTok, diag::err_pp_linemarker_invalid_filename);
1300 Diag(StrTok, diag::err_invalid_string_udl);
1306 assert(Literal.
isAscii() &&
"Didn't allow wide strings in");
1312 Diag(StrTok, diag::err_pp_linemarker_invalid_filename);
1316 FilenameID = SourceMgr.getLineTableFilenameID(Literal.
GetString());
1324 SourceMgr.AddLineNote(DigitTok.
getLocation(), LineNo, FilenameID, IsFileEntry,
1325 IsFileExit, FileKind);
1334 else if (IsFileExit)
1337 Callbacks->FileChanged(CurPPLexer->getSourceLocation(), Reason, FileKind);
1343 void Preprocessor::HandleUserDiagnosticDirective(
Token &
Tok,
1351 CurLexer->ReadToEndOfLine(&Message);
1355 StringRef Msg = StringRef(Message).ltrim(
' ');
1358 Diag(Tok, diag::pp_hash_warning) << Msg;
1360 Diag(Tok, diag::err_pp_hash_error) << Msg;
1365 void Preprocessor::HandleIdentSCCSDirective(
Token &Tok) {
1367 Diag(Tok, diag::ext_pp_ident_directive);
1374 if (StrTok.
isNot(tok::string_literal) &&
1375 StrTok.
isNot(tok::wide_string_literal)) {
1376 Diag(StrTok, diag::err_pp_malformed_ident);
1377 if (StrTok.
isNot(tok::eod))
1383 Diag(StrTok, diag::err_invalid_string_udl);
1392 bool Invalid =
false;
1400 void Preprocessor::HandleMacroPublicDirective(
Token &Tok) {
1402 ReadMacroName(MacroNameTok,
MU_Undef);
1405 if (MacroNameTok.
is(tok::eod))
1417 Diag(MacroNameTok, diag::err_pp_visibility_non_macro) << II;
1427 void Preprocessor::HandleMacroPrivateDirective() {
1429 ReadMacroName(MacroNameTok,
MU_Undef);
1432 if (MacroNameTok.
is(tok::eod))
1444 Diag(MacroNameTok, diag::err_pp_visibility_non_macro) << II;
1464 StringRef &Buffer) {
1466 assert(!Buffer.empty() &&
"Can't have tokens with empty spellings!");
1478 if (Buffer[0] ==
'<') {
1479 if (Buffer.back() !=
'>') {
1480 Diag(Loc, diag::err_pp_expects_filename);
1481 Buffer = StringRef();
1485 }
else if (Buffer[0] ==
'"') {
1486 if (Buffer.back() !=
'"') {
1487 Diag(Loc, diag::err_pp_expects_filename);
1488 Buffer = StringRef();
1493 Diag(Loc, diag::err_pp_expects_filename);
1494 Buffer = StringRef();
1499 if (Buffer.size() <= 2) {
1500 Diag(Loc, diag::err_pp_empty_filename);
1501 Buffer = StringRef();
1506 Buffer = Buffer.substr(1, Buffer.size()-2);
1513 void *AnnotationVal) {
1516 auto Tok = llvm::make_unique<Token[]>(1);
1522 EnterTokenStream(std::move(Tok), 1,
true,
false);
1529 ArrayRef<std::pair<IdentifierInfo *, SourceLocation>> Path,
1531 StringRef ImportKeyword;
1533 ImportKeyword =
"@import";
1535 ImportKeyword =
"import";
1540 for (
size_t I = 0, N = Path.size(); I != N; ++I) {
1543 PathString += Path[I].first->getName();
1545 int IncludeKind = 0;
1565 llvm_unreachable(
"unknown include directive kind");
1570 PP.
Diag(HashLoc, diag::warn_auto_module_import)
1571 << IncludeKind << PathString
1573 ReplaceRange, (ImportKeyword +
" " + PathString +
";").str());
1580 StringRef RealPathName) {
1581 auto RealPathComponentIter = llvm::sys::path::rbegin(RealPathName);
1582 auto RealPathComponentEnd = llvm::sys::path::rend(RealPathName);
1584 bool SuggestReplacement =
false;
1587 for (
auto &Component : llvm::reverse(Components)) {
1588 if (
"." == Component) {
1589 }
else if (
".." == Component) {
1593 }
else if (RealPathComponentIter != RealPathComponentEnd) {
1594 if (Component != *RealPathComponentIter) {
1598 SuggestReplacement = RealPathComponentIter->equals_lower(Component);
1599 if (!SuggestReplacement)
1601 Component = *RealPathComponentIter;
1603 ++RealPathComponentIter;
1606 return SuggestReplacement;
1614 Module *ShadowingModule =
nullptr;
1615 if (M->
isAvailable(LangOpts, TargetInfo, Requirement, MissingHeader,
1622 }
else if (ShadowingModule) {
1625 diag::note_previous_definition);
1640 void Preprocessor::HandleIncludeDirective(
SourceLocation HashLoc,
1648 if (FilenameTok.
isNot(tok::header_name)) {
1650 if (FilenameTok.
isNot(tok::eod))
1662 auto Action = HandleHeaderIncludeOrImport(HashLoc, IncludeTok, FilenameTok,
1663 EndLoc, LookupFrom, LookupFromFile);
1664 switch (Action.Kind) {
1666 case ImportAction::SkippedModuleImport:
1668 case ImportAction::ModuleBegin:
1670 tok::annot_module_begin, Action.ModuleForHeader);
1672 case ImportAction::ModuleImport:
1674 tok::annot_module_include, Action.ModuleForHeader);
1691 Preprocessor::ImportAction Preprocessor::HandleHeaderIncludeOrImport(
1701 StringRef OriginalFilename =
Filename;
1707 if (Filename.empty())
1710 bool IsImportDecl = HashLoc.
isInvalid();
1714 if (PragmaARCCFCodeAuditedLoc.isValid()) {
1715 Diag(StartLoc, diag::err_pp_include_in_arc_cf_code_audited) << IsImportDecl;
1716 Diag(PragmaARCCFCodeAuditedLoc, diag::note_pragma_entered_here);
1723 if (PragmaAssumeNonNullLoc.isValid()) {
1724 Diag(StartLoc, diag::err_pp_include_in_assume_nonnull) << IsImportDecl;
1725 Diag(PragmaAssumeNonNullLoc, diag::note_pragma_entered_here);
1731 if (HeaderInfo.HasIncludeAliasMap()) {
1735 StringRef NewName = HeaderInfo.MapHeaderToIncludeAlias(OriginalFilename);
1736 if (!NewName.empty())
1741 bool IsMapped =
false;
1742 bool IsFrameworkFound =
false;
1751 if (LangOpts.MSVCCompat) {
1752 NormalizedPath = Filename.str();
1754 llvm::sys::path::native(NormalizedPath);
1758 FilenameLoc, LangOpts.MSVCCompat ? NormalizedPath.c_str() :
Filename,
1759 isAngled, LookupFrom, LookupFromFile, CurDir,
1760 Callbacks ? &SearchPath :
nullptr, Callbacks ? &RelativePath :
nullptr,
1761 &SuggestedModule, &IsMapped, &IsFrameworkFound);
1767 if (Callbacks->FileNotFound(Filename, RecoveryPath)) {
1768 if (
const DirectoryEntry *DE = FileMgr.getDirectory(RecoveryPath)) {
1771 HeaderInfo.AddSearchPath(DL, isAngled);
1776 LangOpts.MSVCCompat ? NormalizedPath.c_str() :
Filename, isAngled,
1777 LookupFrom, LookupFromFile, CurDir,
nullptr,
nullptr,
1778 &SuggestedModule, &IsMapped,
nullptr,
1784 if (!SuppressIncludeNotFoundError) {
1791 LangOpts.MSVCCompat ? NormalizedPath.c_str() :
Filename,
false,
1792 LookupFrom, LookupFromFile, CurDir,
1793 Callbacks ? &SearchPath :
nullptr,
1794 Callbacks ? &RelativePath :
nullptr, &SuggestedModule, &IsMapped,
1798 diag::err_pp_file_not_found_angled_include_not_fatal)
1799 << Filename << IsImportDecl
1801 "\"" + Filename.str() +
"\"");
1807 StringRef OriginalFilename =
Filename;
1808 if (LangOpts.SpellChecking && !File) {
1811 auto CorrectTypoFilename = [](llvm::StringRef
Filename) {
1814 Filename = Filename.drop_back();
1818 StringRef TypoCorrectionName = CorrectTypoFilename(Filename);
1820 if (LangOpts.MSVCCompat) {
1821 NormalizedTypoCorrectionPath = TypoCorrectionName.str();
1823 llvm::sys::path::native(NormalizedTypoCorrectionPath);
1828 LangOpts.MSVCCompat ? NormalizedTypoCorrectionPath.c_str()
1829 : TypoCorrectionName,
1830 isAngled, LookupFrom, LookupFromFile, CurDir,
1831 Callbacks ? &SearchPath :
nullptr,
1832 Callbacks ? &RelativePath :
nullptr, &SuggestedModule, &IsMapped,
1838 FilenameRange,
"<" + TypoCorrectionName.str() +
">")
1840 FilenameRange,
"\"" + TypoCorrectionName.str() +
"\"");
1841 Diag(FilenameTok, diag::err_pp_file_not_found_typo_not_fatal)
1842 << OriginalFilename << TypoCorrectionName << Hint;
1845 Filename = TypoCorrectionName;
1851 Diag(FilenameTok, diag::err_pp_file_not_found) << OriginalFilename
1853 if (IsFrameworkFound) {
1854 size_t SlashPos = OriginalFilename.find(
'/');
1855 assert(SlashPos != StringRef::npos &&
1856 "Include with framework name should have '/' in the filename");
1857 StringRef FrameworkName = OriginalFilename.substr(0, SlashPos);
1859 HeaderInfo.LookupFrameworkCache(FrameworkName);
1860 assert(CacheEntry.
Directory &&
"Found framework should be in cache");
1861 Diag(FilenameTok, diag::note_pp_framework_without_header)
1862 << OriginalFilename.substr(SlashPos + 1) << FrameworkName
1871 SkippingUntilPCHThroughHeader =
false;
1880 if (File && PreambleConditionalStack.isRecording() &&
1881 SourceMgr.translateFile(File) == SourceMgr.getMainFileID()) {
1883 diag::err_pp_including_mainfile_in_preamble);
1891 enum { Enter, Import, Skip, IncludeLimitReached } Action = Enter;
1893 if (PPOpts->SingleFileParseMode)
1894 Action = IncludeLimitReached;
1899 if (Action == Enter && HasReachedMaxIncludeDepth && File &&
1900 HeaderInfo.getFileInfo(File).NumIncludes)
1901 Action = IncludeLimitReached;
1906 if (Action == Enter && File && SuggestedModule &&
getLangOpts().Modules &&
1917 diag::note_implicit_top_level_module_import_here)
1929 std::reverse(Path.begin(), Path.end());
1942 assert((Imported ==
nullptr || Imported == SuggestedModule.
getModule()) &&
1943 "the imported module is different than the suggested one");
1961 assert(CurLexer &&
"#include but no current lexer set!");
1963 CurLexer->FormTokenWithChars(Result, CurLexer->BufferEnd,
tok::eof);
1964 CurLexer->cutOffLexing();
1974 SourceMgr.getFileCharacteristic(FilenameTok.
getLocation());
1976 FileCharacter =
std::max(HeaderInfo.getFileDirFlavor(File), FileCharacter);
1989 if (Action == Enter && File &&
1990 !HeaderInfo.ShouldEnterIncludeFile(*
this, File, EnterOnce,
2000 Action = (SuggestedModule && !
getLangOpts().CompilingPCH) ? Import : Skip;
2003 if (Callbacks && !IsImportDecl) {
2006 Callbacks->InclusionDirective(
2007 HashLoc, IncludeTok,
2008 LangOpts.MSVCCompat ? NormalizedPath.c_str() :
Filename, isAngled,
2009 FilenameRange, File, SearchPath, RelativePath,
2010 Action == Import ? SuggestedModule.
getModule() :
nullptr,
2013 Callbacks->FileSkipped(*File, FilenameTok, FileCharacter);
2021 if (IsImportDecl && !SuggestedModule) {
2022 Diag(FilenameTok, diag::err_header_import_not_header_unit)
2023 << OriginalFilename << File->
getName();
2029 const bool CheckIncludePathPortability =
2032 if (CheckIncludePathPortability) {
2033 StringRef Name = LangOpts.MSVCCompat ? NormalizedPath.str() :
Filename;
2036 llvm::sys::path::end(Name));
2040 Path.reserve(Name.size()+2);
2041 Path.push_back(isAngled ?
'<' :
'"');
2042 bool isLeadingSeparator = llvm::sys::path::is_absolute(Name);
2043 for (
auto Component : Components) {
2044 if (isLeadingSeparator)
2045 isLeadingSeparator =
false;
2047 Path.append(Component);
2050 Path.size() <= Filename.size() ? Filename[Path.size()-1] :
2051 (isAngled ?
'>' :
'"'));
2056 diag::pp_nonportable_path : diag::pp_nonportable_system_path;
2057 Diag(FilenameTok, DiagId) << Path <<
2066 return {ImportAction::SkippedModuleImport, M};
2069 case IncludeLimitReached:
2077 assert(M &&
"no module to import");
2085 return {ImportAction::ModuleImport, M};
2093 if (IncludeMacroStack.size() == MaxAllowedIncludeStackDepth-1) {
2094 Diag(FilenameTok, diag::err_pp_include_too_deep);
2095 HasReachedMaxIncludeDepth =
true;
2104 IncludePos = SourceMgr.getExpansionRange(IncludePos).getEnd();
2105 FileID FID = SourceMgr.createFileID(File, IncludePos, FileCharacter);
2106 assert(FID.
isValid() &&
"Expected valid file ID");
2113 if (
auto *M = SuggestedModule.
getModule()) {
2114 if (M->getTopLevelModule()->ShadowingModule) {
2117 Diag(M->DefinitionLoc, diag::err_module_build_shadowed_submodule)
2118 << M->getFullModuleName();
2119 Diag(M->getTopLevelModule()->ShadowingModule->DefinitionLoc,
2120 diag::note_previous_definition);
2136 assert(!CurLexerSubmodule &&
"should not have marked this as a module yet");
2137 CurLexerSubmodule = M;
2147 return {ImportAction::ModuleBegin, M};
2150 assert(!IsImportDecl &&
"failed to diagnose missing module for import decl");
2156 void Preprocessor::HandleIncludeNextDirective(
SourceLocation HashLoc,
2157 Token &IncludeNextTok) {
2158 Diag(IncludeNextTok, diag::ext_pp_include_next_directive);
2164 const FileEntry *LookupFromFile =
nullptr;
2171 Diag(IncludeNextTok, diag::pp_include_next_in_primary);
2172 }
else if (CurLexerSubmodule) {
2175 assert(CurPPLexer &&
"#include_next directive in macro?");
2176 LookupFromFile = CurPPLexer->getFileEntry();
2178 }
else if (!Lookup) {
2183 Diag(IncludeNextTok, diag::pp_include_next_absolute_path);
2189 return HandleIncludeDirective(HashLoc, IncludeNextTok, Lookup,
2194 void Preprocessor::HandleMicrosoftImportDirective(
Token &Tok) {
2200 Diag(Tok, diag::err_pp_import_directive_ms );
2211 if (!LangOpts.ObjC) {
2212 if (LangOpts.MSVCCompat)
2213 return HandleMicrosoftImportDirective(ImportTok);
2214 Diag(ImportTok, diag::ext_pp_import_directive);
2216 return HandleIncludeDirective(HashLoc, ImportTok);
2223 void Preprocessor::HandleIncludeMacrosDirective(
SourceLocation HashLoc,
2224 Token &IncludeMacrosTok) {
2228 if (SourceMgr.getBufferName(Loc) !=
"<built-in>") {
2230 diag::pp_include_macros_out_of_predefines);
2237 HandleIncludeDirective(HashLoc, IncludeMacrosTok);
2242 assert(TmpTok.
isNot(
tok::eof) &&
"Didn't find end of -imacros!");
2243 }
while (TmpTok.
isNot(tok::hashhash));
2254 bool Preprocessor::ReadMacroParameterList(
MacroInfo *MI,
Token &Tok) {
2262 if (Parameters.empty())
2265 Diag(Tok, diag::err_pp_expected_ident_in_arg_list);
2269 Diag(Tok, LangOpts.CPlusPlus11 ?
2270 diag::warn_cxx98_compat_variadic_macro :
2271 diag::ext_variadic_macro);
2274 if (LangOpts.OpenCL) {
2275 Diag(Tok, diag::ext_pp_opencl_variadic_macros);
2280 if (Tok.
isNot(tok::r_paren)) {
2281 Diag(Tok, diag::err_pp_missing_rparen_in_macro_def);
2285 Parameters.push_back(Ident__VA_ARGS__);
2290 Diag(Tok, diag::err_pp_missing_rparen_in_macro_def);
2298 Diag(Tok, diag::err_pp_invalid_tok_in_arg_list);
2304 if (llvm::find(Parameters, II) != Parameters.end()) {
2305 Diag(Tok, diag::err_pp_duplicate_name_in_arg_list) << II;
2310 Parameters.push_back(II);
2317 Diag(Tok, diag::err_pp_expected_comma_in_arg_list);
2326 Diag(Tok, diag::ext_named_variadic_macro);
2330 if (Tok.
isNot(tok::r_paren)) {
2331 Diag(Tok, diag::err_pp_missing_rparen_in_macro_def);
2359 if (!II->isKeyword(LOptions))
2361 StringRef ValueText = II->getName();
2362 StringRef TrimmedValue = ValueText;
2363 if (!ValueText.startswith(
"__")) {
2364 if (ValueText.startswith(
"_"))
2365 TrimmedValue = TrimmedValue.drop_front(1);
2369 TrimmedValue = TrimmedValue.drop_front(2);
2370 if (TrimmedValue.endswith(
"__"))
2371 TrimmedValue = TrimmedValue.drop_back(2);
2373 return TrimmedValue.equals(MacroText);
2380 return MacroName.
isOneOf(tok::kw_extern, tok::kw_inline, tok::kw_static,
2393 MacroInfo *Preprocessor::ReadOptionalMacroParameterListAndBody(
2394 const Token &MacroNameTok,
const bool ImmediatelyAfterHeaderGuard) {
2396 Token LastTok = MacroNameTok;
2404 auto _ = llvm::make_scope_exit([&]() {
2406 if (CurLexer->ParsingPreprocessorDirective)
2417 if (Tok.is(tok::eod)) {
2418 if (ImmediatelyAfterHeaderGuard) {
2424 }
else if (Tok.hasLeadingSpace()) {
2428 }
else if (Tok.is(tok::l_paren)) {
2431 if (ReadMacroParameterList(MI, LastTok))
2440 VariadicMacroScopeGuard.enterScope();
2445 }
else if (LangOpts.C99 || LangOpts.CPlusPlus11) {
2448 Diag(Tok, diag::ext_c99_whitespace_required_after_macro_name);
2457 if (Tok.is(tok::at))
2459 else if (Tok.is(tok::unknown)) {
2466 Diag(Tok, diag::ext_missing_whitespace_after_macro_name);
2468 Diag(Tok, diag::warn_missing_whitespace_after_macro_name);
2471 if (!Tok.is(tok::eod))
2477 while (Tok.isNot(tok::eod)) {
2490 while (Tok.isNot(tok::eod)) {
2493 if (!Tok.isOneOf(tok::hash, tok::hashat, tok::hashhash)) {
2499 Diag(Tok, diag::err_pp_vaopt_nested_use);
2504 if (Tok.isNot(tok::l_paren)) {
2505 Diag(Tok, diag::err_pp_missing_lparen_in_vaopt_use);
2511 if (Tok.is(tok::hashhash)) {
2512 Diag(Tok, diag::err_vaopt_paste_at_start);
2517 if (Tok.is(tok::r_paren)) {
2520 assert(NumTokens >= 3 &&
"Must have seen at least __VA_OPT__( " 2521 "and a subsequent tok::r_paren");
2523 Diag(Tok, diag::err_vaopt_paste_at_end);
2527 }
else if (Tok.is(tok::l_paren)) {
2540 Tok.setKind(tok::unknown);
2548 if (Tok.is(tok::hashhash)) {
2556 if (Tok.is(tok::eod)) {
2562 if (NumTokens && Tok.getIdentifierInfo() == Ident__VA_ARGS__ &&
2577 (Tok.getIdentifierInfo() ==
nullptr ||
2584 if (
getLangOpts().AsmPreprocessor && Tok.isNot(tok::eod)) {
2585 LastTok.
setKind(tok::unknown);
2589 Diag(Tok, diag::err_pp_stringize_not_parameter)
2590 << LastTok.
is(tok::hashat);
2610 assert(Tok.is(tok::eod) &&
"Must be at End Of preprocessing Directive");
2611 Diag(Tok, diag::err_pp_expected_after)
2612 << LastTok.
getKind() << tok::r_paren;
2622 void Preprocessor::HandleDefineDirective(
2623 Token &DefineTok,
const bool ImmediatelyAfterHeaderGuard) {
2627 bool MacroShadowsKeyword;
2628 ReadMacroName(MacroNameTok,
MU_Define, &MacroShadowsKeyword);
2631 if (MacroNameTok.
is(tok::eod))
2636 if (CurLexer) CurLexer->SetCommentRetentionState(KeepMacroComments);
2638 MacroInfo *
const MI = ReadOptionalMacroParameterListAndBody(
2639 MacroNameTok, ImmediatelyAfterHeaderGuard);
2643 if (MacroShadowsKeyword &&
2645 Diag(MacroNameTok, diag::warn_pp_macro_hides_keyword);
2650 if (NumTokens != 0) {
2662 if (SkippingUntilPCHThroughHeader) {
2665 LangOpts.MicrosoftExt))
2677 auto isObjCProtectedMacro = [](
const IdentifierInfo *II) ->
bool {
2678 return II->
isStr(
"__strong") ||
2679 II->isStr(
"__weak") ||
2680 II->isStr(
"__unsafe_unretained") ||
2681 II->isStr(
"__autoreleasing");
2684 SourceMgr.getFileID(OtherMI->getDefinitionLoc())
2689 !SourceMgr.isInSystemHeader(DefineTok.
getLocation())) &&
2691 LangOpts.MicrosoftExt)) {
2694 assert(!OtherMI->isWarnIfUnused());
2702 !SourceMgr.isInSystemHeader(DefineTok.
getLocation())) {
2703 if (!OtherMI->isUsed() && OtherMI->isWarnIfUnused())
2704 Diag(OtherMI->getDefinitionLoc(), diag::pp_macro_not_used);
2708 if (OtherMI->isBuiltinMacro())
2709 Diag(MacroNameTok, diag::ext_pp_redef_builtin_macro);
2712 else if (!OtherMI->isAllowRedefinitionsWithoutWarning() &&
2713 !MI->
isIdenticalTo(*OtherMI, *
this, LangOpts.MicrosoftExt)) {
2716 Diag(OtherMI->getDefinitionLoc(), diag::note_previous_definition);
2719 if (OtherMI->isWarnIfUnused())
2720 WarnUnusedMacroLocs.erase(OtherMI->getDefinitionLoc());
2737 Callbacks->MacroDefined(MacroNameTok, MD);
2742 void Preprocessor::HandleUndefDirective() {
2746 ReadMacroName(MacroNameTok,
MU_Undef);
2749 if (MacroNameTok.
is(tok::eod))
2761 if (
const MacroInfo *MI = MD.getMacroInfo()) {
2768 Undef = AllocateUndefMacroDirective(MacroNameTok.
getLocation());
2774 Callbacks->MacroUndefined(MacroNameTok, MD, Undef);
2789 void Preprocessor::HandleIfdefDirective(
Token &
Result,
2790 const Token &HashToken,
2792 bool ReadAnyTokensBeforeDirective) {
2797 ReadMacroName(MacroNameTok);
2800 if (MacroNameTok.
is(tok::eod)) {
2803 SkipExcludedConditionalBlock(HashToken.
getLocation(),
2816 if (CurPPLexer->getConditionalStackDepth() == 0) {
2821 if (!ReadAnyTokensBeforeDirective && !MI) {
2822 assert(isIfndef &&
"#ifdef shouldn't reach here");
2823 CurPPLexer->MIOpt.EnterTopLevelIfndef(MII, MacroNameTok.
getLocation());
2825 CurPPLexer->MIOpt.EnterTopLevelConditional();
2834 Callbacks->Ifndef(DirectiveTok.
getLocation(), MacroNameTok, MD);
2836 Callbacks->Ifdef(DirectiveTok.
getLocation(), MacroNameTok, MD);
2840 if (PPOpts->SingleFileParseMode && !MI) {
2843 CurPPLexer->pushConditionalLevel(DirectiveTok.
getLocation(),
2846 }
else if (!MI == isIfndef) {
2848 CurPPLexer->pushConditionalLevel(DirectiveTok.
getLocation(),
2853 SkipExcludedConditionalBlock(HashToken.
getLocation(),
2862 void Preprocessor::HandleIfDirective(
Token &IfToken,
2863 const Token &HashToken,
2864 bool ReadAnyTokensBeforeDirective) {
2869 const DirectiveEvalResult DER = EvaluateDirectiveExpression(IfNDefMacro);
2870 const bool ConditionalTrue = DER.Conditional;
2874 if (CurPPLexer->getConditionalStackDepth() == 0) {
2875 if (!ReadAnyTokensBeforeDirective && IfNDefMacro && ConditionalTrue)
2877 CurPPLexer->MIOpt.EnterTopLevelIfndef(IfNDefMacro, IfToken.
getLocation());
2879 CurPPLexer->MIOpt.EnterTopLevelConditional();
2888 if (PPOpts->SingleFileParseMode && DER.IncludedUndefinedIds) {
2891 CurPPLexer->pushConditionalLevel(IfToken.
getLocation(),
false,
2893 }
else if (ConditionalTrue) {
2895 CurPPLexer->pushConditionalLevel(IfToken.
getLocation(),
false,
2907 void Preprocessor::HandleEndifDirective(
Token &EndifToken) {
2914 if (CurPPLexer->popConditionalLevel(CondInfo)) {
2916 Diag(EndifToken, diag::err_pp_endif_without_if);
2921 if (CurPPLexer->getConditionalStackDepth() == 0)
2922 CurPPLexer->MIOpt.ExitTopLevelConditional();
2924 assert(!CondInfo.
WasSkipping && !CurPPLexer->LexingRawMode &&
2925 "This code should only be reachable in the non-skipping case!");
2933 void Preprocessor::HandleElseDirective(
Token &Result,
const Token &HashToken) {
2940 if (CurPPLexer->popConditionalLevel(CI)) {
2941 Diag(Result, diag::pp_err_else_without_if);
2946 if (CurPPLexer->getConditionalStackDepth() == 0)
2947 CurPPLexer->MIOpt.EnterTopLevelConditional();
2950 if (CI.
FoundElse)
Diag(Result, diag::pp_err_else_after_else);
2958 CurPPLexer->pushConditionalLevel(CI.
IfLoc,
false,
2971 void Preprocessor::HandleElifDirective(
Token &ElifToken,
2972 const Token &HashToken) {
2981 if (CurPPLexer->popConditionalLevel(CI)) {
2982 Diag(ElifToken, diag::pp_err_elif_without_if);
2987 if (CurPPLexer->getConditionalStackDepth() == 0)
2988 CurPPLexer->MIOpt.EnterTopLevelConditional();
2991 if (CI.
FoundElse)
Diag(ElifToken, diag::pp_err_elif_after_else);
2994 Callbacks->Elif(ElifToken.
getLocation(), ConditionRange,
3000 CurPPLexer->pushConditionalLevel(ElifToken.
getLocation(),
false,
3006 SkipExcludedConditionalBlock(
StringRef tryGetRealPathName() const
std::string Name
The name of this module.
Module * getModuleForLocation(SourceLocation Loc)
Find the module that owns the source or header file that Loc points to.
MacroInfo * AllocateMacroInfo(SourceLocation L)
Allocate a new MacroInfo object with the provided SourceLocation.
void AddTokenToBody(const Token &Tok)
Add the specified token to the replacement text for the macro.
void markMacroAsUsed(MacroInfo *MI)
A macro is used, update information about macros that need unused warnings.
void sawOpeningParen(SourceLocation LParenLoc)
Call this function each time an lparen is seen.
IdentifierInfo * getIdentifierInfo(StringRef Name) const
Return information about the specified preprocessor identifier token.
Defines the clang::FileManager interface and associated types.
static bool ReadLineMarkerFlags(bool &IsFileEntry, bool &IsFileExit, SrcMgr::CharacteristicKind &FileKind, Preprocessor &PP)
ReadLineMarkerFlags - Parse and validate any flags at the end of a GNU line marker directive...
This header is part of the module (for layering purposes) but should be textually included...
PPConditionalInfo & peekConditionalLevel()
Return the top of the conditional stack.
StringRef getBufferName(SourceLocation Loc, bool *Invalid=nullptr) const
Return the filename or buffer identifier of the buffer the location is in.
static bool isReservedId(StringRef Text, const LangOptions &Lang)
Checks if the specified identifier is reserved in the specified language.
bool is(tok::TokenKind K) const
is/isNot - Predicates to check if this token is a specific kind, as in "if (Tok.is(tok::l_brace)) {...
Module * getTopLevelModule()
Retrieve the top-level module for this (sub)module, which may be this module.
bool sawClosingParen()
Call this function each time an rparen is seen.
Defines the SourceManager interface.
Defines the clang::Module class, which describes a module in the source code.
Module * getCurrentModule()
Retrieves the module that we're currently building, if any.
void pushConditionalLevel(SourceLocation DirectiveStart, bool WasSkipping, bool FoundNonSkip, bool FoundElse)
pushConditionalLevel - When we enter a #if directive, this keeps track of what we are currently in fo...
unsigned IsFramework
Whether this is a framework module.
bool isInPrimaryFile() const
Return true if we're in the top-level file, not in a #include.
Defines the clang::MacroInfo and clang::MacroDirective classes.
DiagnosticBuilder Report(SourceLocation Loc, unsigned DiagID)
Issue the message to the client.
A directive for an undefined macro.
bool getSuppressSystemWarnings() const
void setCodeCompletionReached()
Note that we hit the code-completion point.
bool hadModuleLoaderFatalFailure() const
CharacteristicKind
Indicates whether a file or directory holds normal user code, system code, or system code which is im...
void setBegin(SourceLocation b)
void setIsWarnIfUnused(bool val)
Set the value of the IsWarnIfUnused flag.
tok::TokenKind getKind() const
static MacroDiag shouldWarnOnMacroDef(Preprocessor &PP, IdentifierInfo *II)
ModuleKind Kind
The kind of this module.
DefMacroDirective * appendDefMacroDirective(IdentifierInfo *II, MacroInfo *MI, SourceLocation Loc)
One of these records is kept for each identifier that is lexed.
A directive for a defined macro or a macro imported from a module.
bool ParsingPreprocessorDirective
True when parsing #XXX; turns '\n' into a tok::eod token.
bool isStr(const char(&Str)[StrLen]) const
Return true if this is the identifier for the specified string.
bool CheckMacroName(Token &MacroNameTok, MacroUse isDefineUndef, bool *ShadowFlag=nullptr)
void EnterSubmodule(Module *M, SourceLocation ImportLoc, bool ForPragma)
static void diagnoseAutoModuleImport(Preprocessor &PP, SourceLocation HashLoc, Token &IncludeTok, ArrayRef< std::pair< IdentifierInfo *, SourceLocation >> Path, SourceLocation PathEnd)
Produce a diagnostic informing the user that a #include or similar was implicitly treated as a module...
bool isCPlusPlusOperatorKeyword() const
const TargetInfo & getTargetInfo() const
Token - This structure provides full information about a lexed token.
static bool trySimplifyPath(SmallVectorImpl< StringRef > &Components, StringRef RealPathName)
void setKind(tok::TokenKind K)
__DEVICE__ int max(int __a, int __b)
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
const LangOptions & getLangOpts() const
Describes a module or submodule.
SourceRange DiscardUntilEndOfDirective()
Read and discard all tokens remaining on the current line until the tok::eod token is found...
bool popConditionalLevel(PPConditionalInfo &CI)
popConditionalLevel - Remove an entry off the top of the conditional stack, returning information abo...
A directive for setting the module visibility of a macro.
StringRef getTopLevelModuleName() const
Retrieve the name of the top-level module.
std::pair< FileID, unsigned > getDecomposedExpansionLoc(SourceLocation Loc) const
Decompose the specified location into a raw FileID + Offset pair.
SourceLocation AdvanceToTokenCharacter(SourceLocation TokStart, unsigned Char) const
Given a location that specifies the start of a token, return a new location that specifies a characte...
MacroUse
Context in which macro name is used.
std::string getFullModuleName(bool AllowStringLiterals=false) const
Retrieve the full name of this module, including the path from its top-level module.
StringRef getSpelling(SourceLocation loc, SmallVectorImpl< char > &buffer, bool *invalid=nullptr) const
Return the 'spelling' of the token at the given location; does not go up to the spelling location or ...
HeaderSearch & getHeaderSearchInfo() const
const Token & getReplacementToken(unsigned Tok) const
bool hasUDSuffix() const
Return true if this token is a string or character literal which has a ud-suffix. ...
SourceLocation getExpansionLoc(SourceLocation Loc) const
Given a SourceLocation object Loc, return the expansion location referenced by the ID...
void HandleDirective(Token &Result)
Callback invoked when the lexer sees a # token at the start of a line.
Concrete class used by the front-end to report problems and issues.
bool GetIncludeFilenameSpelling(SourceLocation Loc, StringRef &Buffer)
Turn the specified lexer token into a fully checked and spelled filename, e.g.
Module * Parent
The parent of this module.
bool isUsed() const
Return false if this macro is defined in the main file and has not yet been used. ...
bool FoundNonSkip
True if we have emitted tokens already, and now we're in an #else block or something.
LLVM_READONLY bool isUppercase(unsigned char c)
Return true if this character is an uppercase ASCII letter: [A-Z].
void appendMacroDirective(IdentifierInfo *II, MacroDirective *MD)
Add a directive to the macro directive history for this identifier.
void LexUnexpandedToken(Token &Result)
Just like Lex, but disables macro expansion of identifier tokens.
MacroDiag
Enumerates possible cases of #define/#undef a reserved identifier.
unsigned IsSystem
Whether this is a "system" module (which assumes that all headers in it are system headers)...
void HandleSkippedDirectiveWhileUsingPCH(Token &Result, SourceLocation HashLoc)
Process directives while skipping until the through header or #pragma hdrstop is found.
std::string CurrentModule
The name of the current module, of which the main source file is a part.
const DirectoryEntry * getDirectory(StringRef DirName, bool CacheFailure=true)
Lookup, cache, and verify the specified directory (real or virtual).
Describes the result of attempting to load a module.
Exposes information about the current target.
void setAnnotationValue(void *val)
void diagnoseHeaderInclusion(Module *RequestingModule, bool RequestingModuleIsModuleInterface, SourceLocation FilenameLoc, StringRef Filename, const FileEntry *File)
Reports errors if a module must not include a specific file.
Defines the clang::LangOptions interface.
bool LexingRawMode
True if in raw mode.
Represents a character-granular source range.
void setHasCommaPasting()
bool isInvalid() const
Return true if this object is invalid or uninitialized.
void makeModuleVisible(Module *M, SourceLocation Loc)
bool isInSystemHeader(SourceLocation Loc) const
Returns if a SourceLocation is in a system header.
const FileEntry * getFileEntryForID(FileID FID) const
Returns the FileEntry record for the provided FileID.
bool usingPCHWithThroughHeader()
True if using a PCH with a through header.
bool isPCHThroughHeader(const FileEntry *FE)
Returns true if the FileEntry is the PCH through header.
A class for tracking whether we're inside a VA_OPT during a traversal of the tokens of a variadic mac...
static bool warnByDefaultOnWrongCase(StringRef Include)
SourceLocation getLocation() const
Return a source location identifier for the specified offset in the current file. ...
Defines the clang::Preprocessor interface.
ResetMacroExpansionHelper(Preprocessor *pp)
LLVM_READONLY bool isAlphanumeric(unsigned char c)
Return true if this character is an ASCII letter or digit: [a-zA-Z0-9].
static bool checkModuleIsAvailable(const LangOptions &LangOpts, const TargetInfo &TargetInfo, DiagnosticsEngine &Diags, Module *M)
Check that the given module is available, producing a diagnostic if not.
const MacroInfo * getMacroInfo(const IdentifierInfo *II) const
Defines the clang::IdentifierInfo, clang::IdentifierTable, and clang::Selector interfaces.
SourceLocation getUnmatchedOpeningParenLoc() const
KnownHeader findModuleForHeader(const FileEntry *File, bool AllowTextual=false)
Retrieve the module that owns the given header file, if any.
Information about the conditional stack (#if directives) currently active.
Represents an unpacked "presumed" location which can be presented to the user.
SourceLocation getEnd() const
bool isAvailable() const
Determine whether this module is available for use within the current translation unit...
bool isObjectLike() const
The result type of a method or function.
StringRef GetString() const
DirectoryLookup - This class represents one entry in the search list that specifies the search order ...
bool isKeyword(const LangOptions &LangOpts) const
Return true if this token is a keyword in the specified language.
bool isRecordingPreamble() const
const DirectoryEntry * Directory
The directory entry which should be used for the cached framework.
static CharSourceRange getCharRange(SourceRange R)
SourceManager & getSourceManager() const
virtual SourceLocation getSourceLocation()=0
Return the source location for the next observable location.
MacroDirective * getLocalMacroDirective(const IdentifierInfo *II) const
Given an identifier, return its latest non-imported MacroDirective if it is #define'd and not #undef'...
const DirectoryEntry * getDir() const
Return the directory the file lives in.
bool isVAOptToken(const Token &T) const
void setIsFunctionLike()
Function/Object-likeness.
Encapsulates changes to the "macros namespace" (the location where the macro name became active...
bool WasSkipping
True if this was contained in a skipping directive, e.g., in a "\#if 0" block.
Encodes a location in the source.
StringRef getName() const
bool isConfigMismatch() const
Determines whether the module failed to load due to a configuration mismatch with an explicitly-named...
friend class VariadicMacroScopeGuard
MacroDefinition getMacroDefinition(const IdentifierInfo *II)
All of the names in this module are hidden.
IdentifierInfo * getIdentifierInfo() const
void setAnnotationEndLoc(SourceLocation L)
Cached information about one file (either on disk or in the virtual file system). ...
virtual void CodeCompleteInConditionalExclusion()
Callback invoked when performing code completion within a block of code that was excluded due to prep...
void setIsC99Varargs()
Varargs querying methods. This can only be set for function-like macros.
bool isInVAOpt() const
Returns true if we have seen the VA_OPT and '(' but before having seen the matching ')'...
void Lex(Token &Result)
Lex the next token for this preprocessor.
const char * getNameStart() const
Return the beginning of the actual null-terminated string for this identifier.
void setDefinitionEndLoc(SourceLocation EndLoc)
Set the location of the last token in the macro.
bool isAtStartOfLine() const
isAtStartOfLine - Return true if this token is at the start of a line.
This is a fragment of the global module within some C++ module.
TokenKind
Provides a simple uniform namespace for tokens from all C languages.
bool isInMainFile(SourceLocation Loc) const
Returns whether the PresumedLoc for a given SourceLocation is in the main file.
std::string ModuleName
The module currently being compiled as specified by -fmodule-name.
const FileEntry * LookupFile(SourceLocation FilenameLoc, StringRef Filename, bool isAngled, const DirectoryLookup *FromDir, const FileEntry *FromFile, const DirectoryLookup *&CurDir, SmallVectorImpl< char > *SearchPath, SmallVectorImpl< char > *RelativePath, ModuleMap::KnownHeader *SuggestedModule, bool *IsMapped, bool *IsFrameworkFound, bool SkipCache=false)
Given a "foo" or <foo> reference, look up the indicated file.
std::pair< std::string, bool > Requirement
An individual requirement: a feature name and a flag indicating the required state of that feature...
bool isC99Varargs() const
__DEVICE__ void * memcpy(void *__a, const void *__b, size_t __c)
void HandlePragmaHdrstop(Token &Tok)
StringRef getName() const
Return the actual identifier string.
SourceLocation IfLoc
Location where the conditional started.
An opaque identifier used by SourceManager which refers to a source file (MemoryBuffer) along with it...
bool isNot(tok::TokenKind K) const
static bool isInvalid(LocType Loc, bool *Invalid)
bool EnterSourceFile(FileID FID, const DirectoryLookup *Dir, SourceLocation Loc)
Add a source file to the top of the include stack and start lexing tokens from it instead of the curr...
Dataflow Directional Tag Classes.
bool isWarnIfUnused() const
Return true if we should emit a warning if the macro is unused.
bool isValid() const
Return true if this is a valid SourceLocation object.
The pragma was introduced via #pragma.
unsigned getNumTokens() const
Return the number of tokens that this macro expands to.
const FileEntry * getFileEntry() const
getFileEntry - Return the FileEntry corresponding to this FileID.
static bool isConfigurationPattern(Token &MacroName, MacroInfo *MI, const LangOptions &LOptions)
ArrayRef< KnownHeader > findAllModulesForHeader(const FileEntry *File) const
Retrieve all the modules that contain the given header file.
SourceLocation getIncludeLoc(FileID FID) const
Returns the include location if FID is a #include'd file otherwise it returns an invalid location...
FileID getMainFileID() const
Returns the FileID of the main source file.
bool isMissingExpected() const
Determines whether the module, which failed to load, was actually a submodule that we expected to see...
static bool isForModuleBuilding(Module *M, StringRef CurrentModule, StringRef ModuleName)
bool isOneOf(tok::TokenKind K1, tok::TokenKind K2) const
tok::PPKeywordKind getPPKeywordID() const
Return the preprocessor keyword ID for this identifier.
PresumedLoc getPresumedLoc(SourceLocation Loc, bool UseLineDirectives=true) const
Returns the "presumed" location of a SourceLocation specifies.
static MacroDiag shouldWarnOnMacroUndef(Preprocessor &PP, IdentifierInfo *II)
unsigned getLength() const
Encapsulates the data about a macro definition (e.g.
SourceLocation DefinitionLoc
The location of the module definition.
LLVM_READONLY bool isDigit(unsigned char c)
Return true if this character is an ASCII digit: [0-9].
FileID getFileID(SourceLocation SpellingLoc) const
Return the FileID for a SourceLocation.
int getParameterNum(const IdentifierInfo *Arg) const
Return the parameter number of the specified identifier, or -1 if the identifier is not a formal para...
static FixItHint CreateInsertion(SourceLocation InsertionLoc, StringRef Code, bool BeforePreviousInsertions=false)
Create a code modification hint that inserts the given code string at a specific location.
SourceLocation getDefinitionLoc() const
Return the location that the macro was defined at.
Cached information about one directory (either on disk or in the virtual file system).
Defines the PPCallbacks interface.
Defines the clang::TokenKind enum and support functions.
static bool GetLineValue(Token &DigitTok, unsigned &Val, unsigned DiagID, Preprocessor &PP, bool IsGNULineDirective=false)
GetLineValue - Convert a numeric token into an unsigned value, emitting Diagnostic DiagID if it is in...
virtual void CodeCompleteMacroName(bool IsDefinition)
Callback invoked when performing code completion in a context where the name of a macro is expected...
SourceLocation CheckEndOfDirective(const char *DirType, bool EnableMacros=false)
Ensure that the next token is a tok::eod token.
Defines the clang::SourceLocation class and associated facilities.
void setEnd(SourceLocation e)
FileID getPredefinesFileID() const
Returns the FileID for the preprocessor predefines.
DiagnosticsEngine & getDiagnostics() const
bool isIdenticalTo(const MacroInfo &Other, Preprocessor &PP, bool Syntactically) const
Return true if the specified macro definition is equal to this macro in spelling, arguments...
StringRef getRawIdentifier() const
getRawIdentifier - For a raw identifier token (i.e., an identifier lexed in raw mode), returns a reference to the text substring in the buffer if known.
bool isBuiltinMacro() const
Return true if this macro requires processing before expansion.
StringLiteralParser - This decodes string escape characters and performs wide string analysis and Tra...
static FixItHint CreateReplacement(CharSourceRange RemoveRange, StringRef Code)
Create a code modification hint that replaces the given source range with the given code string...
void sawVAOptFollowedByOpeningParens(const SourceLocation LParenLoc)
Call this function as soon as you see VA_OPT and '('.
const FileEntry * getModuleHeaderToIncludeForDiagnostics(SourceLocation IncLoc, Module *M, SourceLocation MLoc)
We want to produce a diagnostic at location IncLoc concerning a missing module import.
bool needsCleaning() const
Return true if this token has trigraphs or escaped newlines in it.
Annotates a diagnostic with some code that should be inserted, removed, or replaced to fix the proble...
void setLocation(SourceLocation L)
This structure is used to record entries in our framework cache.
A trivial tuple used to represent a source range.
bool LexHeaderName(Token &Result, bool AllowMacroExpansion=true)
Lex a token, forming a header-name token if possible.
void setParameterList(ArrayRef< IdentifierInfo *> List, llvm::BumpPtrAllocator &PPAllocator)
Set the specified list of identifiers as the parameter list for this macro.
PreprocessorLexer * getCurrentFileLexer() const
Return the current file lexer being lexed from.
void EnterAnnotationToken(SourceRange Range, tok::TokenKind Kind, void *AnnotationVal)
Enter an annotation token into the token stream.
SourceLocation getIncludeLoc() const
Return the presumed include location of this location.
bool FoundElse
True if we've seen a #else in this block.
SourceLocation getBegin() const
DiagnosticBuilder Diag(SourceLocation Loc, unsigned DiagID) const
Forwarding function for diagnostics.
VerifyDiagnosticConsumer::Directive Directive
This class handles loading and caching of source files into memory.
void startToken()
Reset all flags to cleared.
~ResetMacroExpansionHelper()
An RAII class that tracks when the Preprocessor starts and stops lexing the definition of a (ISO C/C+...
Engages in a tight little dance with the lexer to efficiently preprocess tokens.
StringRef getName() const
SourceLocation getEndLoc() const