Details | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
14 | pmbaty | 1 | //===--- PPCallbacks.h - Callbacks for Preprocessor actions -----*- C++ -*-===// |
2 | // |
||
3 | // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. |
||
4 | // See https://llvm.org/LICENSE.txt for license information. |
||
5 | // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception |
||
6 | // |
||
7 | //===----------------------------------------------------------------------===// |
||
8 | /// |
||
9 | /// \file |
||
10 | /// Defines the PPCallbacks interface. |
||
11 | /// |
||
12 | //===----------------------------------------------------------------------===// |
||
13 | |||
14 | #ifndef LLVM_CLANG_LEX_PPCALLBACKS_H |
||
15 | #define LLVM_CLANG_LEX_PPCALLBACKS_H |
||
16 | |||
17 | #include "clang/Basic/DiagnosticIDs.h" |
||
18 | #include "clang/Basic/SourceLocation.h" |
||
19 | #include "clang/Basic/SourceManager.h" |
||
20 | #include "clang/Lex/ModuleLoader.h" |
||
21 | #include "clang/Lex/Pragma.h" |
||
22 | #include "llvm/ADT/StringRef.h" |
||
23 | |||
24 | namespace clang { |
||
25 | class Token; |
||
26 | class IdentifierInfo; |
||
27 | class MacroDefinition; |
||
28 | class MacroDirective; |
||
29 | class MacroArgs; |
||
30 | |||
31 | /// This interface provides a way to observe the actions of the |
||
32 | /// preprocessor as it does its thing. |
||
33 | /// |
||
34 | /// Clients can define their hooks here to implement preprocessor level tools. |
||
35 | class PPCallbacks { |
||
36 | public: |
||
37 | virtual ~PPCallbacks(); |
||
38 | |||
39 | enum FileChangeReason { |
||
40 | EnterFile, ExitFile, SystemHeaderPragma, RenameFile |
||
41 | }; |
||
42 | |||
43 | /// Callback invoked whenever a source file is entered or exited. |
||
44 | /// |
||
45 | /// \param Loc Indicates the new location. |
||
46 | /// \param PrevFID the file that was exited if \p Reason is ExitFile or the |
||
47 | /// the file before the new one entered for \p Reason EnterFile. |
||
48 | virtual void FileChanged(SourceLocation Loc, FileChangeReason Reason, |
||
49 | SrcMgr::CharacteristicKind FileType, |
||
50 | FileID PrevFID = FileID()) { |
||
51 | } |
||
52 | |||
53 | enum class LexedFileChangeReason { EnterFile, ExitFile }; |
||
54 | |||
55 | /// Callback invoked whenever the \p Lexer moves to a different file for |
||
56 | /// lexing. Unlike \p FileChanged line number directives and other related |
||
57 | /// pragmas do not trigger callbacks to \p LexedFileChanged. |
||
58 | /// |
||
59 | /// \param FID The \p FileID that the \p Lexer moved to. |
||
60 | /// |
||
61 | /// \param Reason Whether the \p Lexer entered a new file or exited one. |
||
62 | /// |
||
63 | /// \param FileType The \p CharacteristicKind of the file the \p Lexer moved |
||
64 | /// to. |
||
65 | /// |
||
66 | /// \param PrevFID The \p FileID the \p Lexer was using before the change. |
||
67 | /// |
||
68 | /// \param Loc The location where the \p Lexer entered a new file from or the |
||
69 | /// location that the \p Lexer moved into after exiting a file. |
||
70 | virtual void LexedFileChanged(FileID FID, LexedFileChangeReason Reason, |
||
71 | SrcMgr::CharacteristicKind FileType, |
||
72 | FileID PrevFID, SourceLocation Loc) {} |
||
73 | |||
74 | /// Callback invoked whenever a source file is skipped as the result |
||
75 | /// of header guard optimization. |
||
76 | /// |
||
77 | /// \param SkippedFile The file that is skipped instead of entering \#include |
||
78 | /// |
||
79 | /// \param FilenameTok The file name token in \#include "FileName" directive |
||
80 | /// or macro expanded file name token from \#include MACRO(PARAMS) directive. |
||
81 | /// Note that FilenameTok contains corresponding quotes/angles symbols. |
||
82 | virtual void FileSkipped(const FileEntryRef &SkippedFile, |
||
83 | const Token &FilenameTok, |
||
84 | SrcMgr::CharacteristicKind FileType) {} |
||
85 | |||
86 | /// Callback invoked whenever the preprocessor cannot find a file for an |
||
87 | /// inclusion directive. |
||
88 | /// |
||
89 | /// \param FileName The name of the file being included, as written in the |
||
90 | /// source code. |
||
91 | /// |
||
92 | /// \returns true to indicate that the preprocessor should skip this file |
||
93 | /// and not issue any diagnostic. |
||
94 | virtual bool FileNotFound(StringRef FileName) { return false; } |
||
95 | |||
96 | /// Callback invoked whenever an inclusion directive of |
||
97 | /// any kind (\c \#include, \c \#import, etc.) has been processed, regardless |
||
98 | /// of whether the inclusion will actually result in an inclusion. |
||
99 | /// |
||
100 | /// \param HashLoc The location of the '#' that starts the inclusion |
||
101 | /// directive. |
||
102 | /// |
||
103 | /// \param IncludeTok The token that indicates the kind of inclusion |
||
104 | /// directive, e.g., 'include' or 'import'. |
||
105 | /// |
||
106 | /// \param FileName The name of the file being included, as written in the |
||
107 | /// source code. |
||
108 | /// |
||
109 | /// \param IsAngled Whether the file name was enclosed in angle brackets; |
||
110 | /// otherwise, it was enclosed in quotes. |
||
111 | /// |
||
112 | /// \param FilenameRange The character range of the quotes or angle brackets |
||
113 | /// for the written file name. |
||
114 | /// |
||
115 | /// \param File The actual file that may be included by this inclusion |
||
116 | /// directive. |
||
117 | /// |
||
118 | /// \param SearchPath Contains the search path which was used to find the file |
||
119 | /// in the file system. If the file was found via an absolute include path, |
||
120 | /// SearchPath will be empty. For framework includes, the SearchPath and |
||
121 | /// RelativePath will be split up. For example, if an include of "Some/Some.h" |
||
122 | /// is found via the framework path |
||
123 | /// "path/to/Frameworks/Some.framework/Headers/Some.h", SearchPath will be |
||
124 | /// "path/to/Frameworks/Some.framework/Headers" and RelativePath will be |
||
125 | /// "Some.h". |
||
126 | /// |
||
127 | /// \param RelativePath The path relative to SearchPath, at which the include |
||
128 | /// file was found. This is equal to FileName except for framework includes. |
||
129 | /// |
||
130 | /// \param Imported The module, whenever an inclusion directive was |
||
131 | /// automatically turned into a module import or null otherwise. |
||
132 | /// |
||
133 | /// \param FileType The characteristic kind, indicates whether a file or |
||
134 | /// directory holds normal user code, system code, or system code which is |
||
135 | /// implicitly 'extern "C"' in C++ mode. |
||
136 | /// |
||
137 | virtual void InclusionDirective(SourceLocation HashLoc, |
||
138 | const Token &IncludeTok, StringRef FileName, |
||
139 | bool IsAngled, CharSourceRange FilenameRange, |
||
140 | OptionalFileEntryRef File, |
||
141 | StringRef SearchPath, StringRef RelativePath, |
||
142 | const Module *Imported, |
||
143 | SrcMgr::CharacteristicKind FileType) {} |
||
144 | |||
145 | /// Callback invoked whenever a submodule was entered. |
||
146 | /// |
||
147 | /// \param M The submodule we have entered. |
||
148 | /// |
||
149 | /// \param ImportLoc The location of import directive token. |
||
150 | /// |
||
151 | /// \param ForPragma If entering from pragma directive. |
||
152 | /// |
||
153 | virtual void EnteredSubmodule(Module *M, SourceLocation ImportLoc, |
||
154 | bool ForPragma) { } |
||
155 | |||
156 | /// Callback invoked whenever a submodule was left. |
||
157 | /// |
||
158 | /// \param M The submodule we have left. |
||
159 | /// |
||
160 | /// \param ImportLoc The location of import directive token. |
||
161 | /// |
||
162 | /// \param ForPragma If entering from pragma directive. |
||
163 | /// |
||
164 | virtual void LeftSubmodule(Module *M, SourceLocation ImportLoc, |
||
165 | bool ForPragma) { } |
||
166 | |||
167 | /// Callback invoked whenever there was an explicit module-import |
||
168 | /// syntax. |
||
169 | /// |
||
170 | /// \param ImportLoc The location of import directive token. |
||
171 | /// |
||
172 | /// \param Path The identifiers (and their locations) of the module |
||
173 | /// "path", e.g., "std.vector" would be split into "std" and "vector". |
||
174 | /// |
||
175 | /// \param Imported The imported module; can be null if importing failed. |
||
176 | /// |
||
177 | virtual void moduleImport(SourceLocation ImportLoc, |
||
178 | ModuleIdPath Path, |
||
179 | const Module *Imported) { |
||
180 | } |
||
181 | |||
182 | /// Callback invoked when the end of the main file is reached. |
||
183 | /// |
||
184 | /// No subsequent callbacks will be made. |
||
185 | virtual void EndOfMainFile() { |
||
186 | } |
||
187 | |||
188 | /// Callback invoked when a \#ident or \#sccs directive is read. |
||
189 | /// \param Loc The location of the directive. |
||
190 | /// \param str The text of the directive. |
||
191 | /// |
||
192 | virtual void Ident(SourceLocation Loc, StringRef str) { |
||
193 | } |
||
194 | |||
195 | /// Callback invoked when start reading any pragma directive. |
||
196 | virtual void PragmaDirective(SourceLocation Loc, |
||
197 | PragmaIntroducerKind Introducer) { |
||
198 | } |
||
199 | |||
200 | /// Callback invoked when a \#pragma comment directive is read. |
||
201 | virtual void PragmaComment(SourceLocation Loc, const IdentifierInfo *Kind, |
||
202 | StringRef Str) { |
||
203 | } |
||
204 | |||
205 | /// Callback invoked when a \#pragma mark comment is read. |
||
206 | virtual void PragmaMark(SourceLocation Loc, StringRef Trivia) { |
||
207 | } |
||
208 | |||
209 | /// Callback invoked when a \#pragma detect_mismatch directive is |
||
210 | /// read. |
||
211 | virtual void PragmaDetectMismatch(SourceLocation Loc, StringRef Name, |
||
212 | StringRef Value) { |
||
213 | } |
||
214 | |||
215 | /// Callback invoked when a \#pragma clang __debug directive is read. |
||
216 | /// \param Loc The location of the debug directive. |
||
217 | /// \param DebugType The identifier following __debug. |
||
218 | virtual void PragmaDebug(SourceLocation Loc, StringRef DebugType) { |
||
219 | } |
||
220 | |||
221 | /// Determines the kind of \#pragma invoking a call to PragmaMessage. |
||
222 | enum PragmaMessageKind { |
||
223 | /// \#pragma message has been invoked. |
||
224 | PMK_Message, |
||
225 | |||
226 | /// \#pragma GCC warning has been invoked. |
||
227 | PMK_Warning, |
||
228 | |||
229 | /// \#pragma GCC error has been invoked. |
||
230 | PMK_Error |
||
231 | }; |
||
232 | |||
233 | /// Callback invoked when a \#pragma message directive is read. |
||
234 | /// \param Loc The location of the message directive. |
||
235 | /// \param Namespace The namespace of the message directive. |
||
236 | /// \param Kind The type of the message directive. |
||
237 | /// \param Str The text of the message directive. |
||
238 | virtual void PragmaMessage(SourceLocation Loc, StringRef Namespace, |
||
239 | PragmaMessageKind Kind, StringRef Str) { |
||
240 | } |
||
241 | |||
242 | /// Callback invoked when a \#pragma gcc diagnostic push directive |
||
243 | /// is read. |
||
244 | virtual void PragmaDiagnosticPush(SourceLocation Loc, |
||
245 | StringRef Namespace) { |
||
246 | } |
||
247 | |||
248 | /// Callback invoked when a \#pragma gcc diagnostic pop directive |
||
249 | /// is read. |
||
250 | virtual void PragmaDiagnosticPop(SourceLocation Loc, |
||
251 | StringRef Namespace) { |
||
252 | } |
||
253 | |||
254 | /// Callback invoked when a \#pragma gcc diagnostic directive is read. |
||
255 | virtual void PragmaDiagnostic(SourceLocation Loc, StringRef Namespace, |
||
256 | diag::Severity mapping, StringRef Str) {} |
||
257 | |||
258 | /// Called when an OpenCL extension is either disabled or |
||
259 | /// enabled with a pragma. |
||
260 | virtual void PragmaOpenCLExtension(SourceLocation NameLoc, |
||
261 | const IdentifierInfo *Name, |
||
262 | SourceLocation StateLoc, unsigned State) { |
||
263 | } |
||
264 | |||
265 | /// Callback invoked when a \#pragma warning directive is read. |
||
266 | enum PragmaWarningSpecifier { |
||
267 | PWS_Default, |
||
268 | PWS_Disable, |
||
269 | PWS_Error, |
||
270 | PWS_Once, |
||
271 | PWS_Suppress, |
||
272 | PWS_Level1, |
||
273 | PWS_Level2, |
||
274 | PWS_Level3, |
||
275 | PWS_Level4, |
||
276 | }; |
||
277 | virtual void PragmaWarning(SourceLocation Loc, |
||
278 | PragmaWarningSpecifier WarningSpec, |
||
279 | ArrayRef<int> Ids) {} |
||
280 | |||
281 | /// Callback invoked when a \#pragma warning(push) directive is read. |
||
282 | virtual void PragmaWarningPush(SourceLocation Loc, int Level) { |
||
283 | } |
||
284 | |||
285 | /// Callback invoked when a \#pragma warning(pop) directive is read. |
||
286 | virtual void PragmaWarningPop(SourceLocation Loc) { |
||
287 | } |
||
288 | |||
289 | /// Callback invoked when a \#pragma execution_character_set(push) directive |
||
290 | /// is read. |
||
291 | virtual void PragmaExecCharsetPush(SourceLocation Loc, StringRef Str) {} |
||
292 | |||
293 | /// Callback invoked when a \#pragma execution_character_set(pop) directive |
||
294 | /// is read. |
||
295 | virtual void PragmaExecCharsetPop(SourceLocation Loc) {} |
||
296 | |||
297 | /// Callback invoked when a \#pragma clang assume_nonnull begin directive |
||
298 | /// is read. |
||
299 | virtual void PragmaAssumeNonNullBegin(SourceLocation Loc) {} |
||
300 | |||
301 | /// Callback invoked when a \#pragma clang assume_nonnull end directive |
||
302 | /// is read. |
||
303 | virtual void PragmaAssumeNonNullEnd(SourceLocation Loc) {} |
||
304 | |||
305 | /// Called by Preprocessor::HandleMacroExpandedIdentifier when a |
||
306 | /// macro invocation is found. |
||
307 | virtual void MacroExpands(const Token &MacroNameTok, |
||
308 | const MacroDefinition &MD, SourceRange Range, |
||
309 | const MacroArgs *Args) {} |
||
310 | |||
311 | /// Hook called whenever a macro definition is seen. |
||
312 | virtual void MacroDefined(const Token &MacroNameTok, |
||
313 | const MacroDirective *MD) { |
||
314 | } |
||
315 | |||
316 | /// Hook called whenever a macro \#undef is seen. |
||
317 | /// \param MacroNameTok The active Token |
||
318 | /// \param MD A MacroDefinition for the named macro. |
||
319 | /// \param Undef New MacroDirective if the macro was defined, null otherwise. |
||
320 | /// |
||
321 | /// MD is released immediately following this callback. |
||
322 | virtual void MacroUndefined(const Token &MacroNameTok, |
||
323 | const MacroDefinition &MD, |
||
324 | const MacroDirective *Undef) { |
||
325 | } |
||
326 | |||
327 | /// Hook called whenever the 'defined' operator is seen. |
||
328 | /// \param MD The MacroDirective if the name was a macro, null otherwise. |
||
329 | virtual void Defined(const Token &MacroNameTok, const MacroDefinition &MD, |
||
330 | SourceRange Range) { |
||
331 | } |
||
332 | |||
333 | /// Hook called when a '__has_include' or '__has_include_next' directive is |
||
334 | /// read. |
||
335 | virtual void HasInclude(SourceLocation Loc, StringRef FileName, bool IsAngled, |
||
336 | OptionalFileEntryRef File, |
||
337 | SrcMgr::CharacteristicKind FileType); |
||
338 | |||
339 | /// Hook called when a source range is skipped. |
||
340 | /// \param Range The SourceRange that was skipped. The range begins at the |
||
341 | /// \#if/\#else directive and ends after the \#endif/\#else directive. |
||
342 | /// \param EndifLoc The end location of the 'endif' token, which may precede |
||
343 | /// the range skipped by the directive (e.g excluding comments after an |
||
344 | /// 'endif'). |
||
345 | virtual void SourceRangeSkipped(SourceRange Range, SourceLocation EndifLoc) { |
||
346 | } |
||
347 | |||
348 | enum ConditionValueKind { |
||
349 | CVK_NotEvaluated, CVK_False, CVK_True |
||
350 | }; |
||
351 | |||
352 | /// Hook called whenever an \#if is seen. |
||
353 | /// \param Loc the source location of the directive. |
||
354 | /// \param ConditionRange The SourceRange of the expression being tested. |
||
355 | /// \param ConditionValue The evaluated value of the condition. |
||
356 | /// |
||
357 | // FIXME: better to pass in a list (or tree!) of Tokens. |
||
358 | virtual void If(SourceLocation Loc, SourceRange ConditionRange, |
||
359 | ConditionValueKind ConditionValue) { |
||
360 | } |
||
361 | |||
362 | /// Hook called whenever an \#elif is seen. |
||
363 | /// \param Loc the source location of the directive. |
||
364 | /// \param ConditionRange The SourceRange of the expression being tested. |
||
365 | /// \param ConditionValue The evaluated value of the condition. |
||
366 | /// \param IfLoc the source location of the \#if/\#ifdef/\#ifndef directive. |
||
367 | // FIXME: better to pass in a list (or tree!) of Tokens. |
||
368 | virtual void Elif(SourceLocation Loc, SourceRange ConditionRange, |
||
369 | ConditionValueKind ConditionValue, SourceLocation IfLoc) { |
||
370 | } |
||
371 | |||
372 | /// Hook called whenever an \#ifdef is seen. |
||
373 | /// \param Loc the source location of the directive. |
||
374 | /// \param MacroNameTok Information on the token being tested. |
||
375 | /// \param MD The MacroDefinition if the name was a macro, null otherwise. |
||
376 | virtual void Ifdef(SourceLocation Loc, const Token &MacroNameTok, |
||
377 | const MacroDefinition &MD) { |
||
378 | } |
||
379 | |||
380 | /// Hook called whenever an \#elifdef branch is taken. |
||
381 | /// \param Loc the source location of the directive. |
||
382 | /// \param MacroNameTok Information on the token being tested. |
||
383 | /// \param MD The MacroDefinition if the name was a macro, null otherwise. |
||
384 | virtual void Elifdef(SourceLocation Loc, const Token &MacroNameTok, |
||
385 | const MacroDefinition &MD) { |
||
386 | } |
||
387 | /// Hook called whenever an \#elifdef is skipped. |
||
388 | /// \param Loc the source location of the directive. |
||
389 | /// \param ConditionRange The SourceRange of the expression being tested. |
||
390 | /// \param IfLoc the source location of the \#if/\#ifdef/\#ifndef directive. |
||
391 | // FIXME: better to pass in a list (or tree!) of Tokens. |
||
392 | virtual void Elifdef(SourceLocation Loc, SourceRange ConditionRange, |
||
393 | SourceLocation IfLoc) { |
||
394 | } |
||
395 | |||
396 | /// Hook called whenever an \#ifndef is seen. |
||
397 | /// \param Loc the source location of the directive. |
||
398 | /// \param MacroNameTok Information on the token being tested. |
||
399 | /// \param MD The MacroDefiniton if the name was a macro, null otherwise. |
||
400 | virtual void Ifndef(SourceLocation Loc, const Token &MacroNameTok, |
||
401 | const MacroDefinition &MD) { |
||
402 | } |
||
403 | |||
404 | /// Hook called whenever an \#elifndef branch is taken. |
||
405 | /// \param Loc the source location of the directive. |
||
406 | /// \param MacroNameTok Information on the token being tested. |
||
407 | /// \param MD The MacroDefinition if the name was a macro, null otherwise. |
||
408 | virtual void Elifndef(SourceLocation Loc, const Token &MacroNameTok, |
||
409 | const MacroDefinition &MD) { |
||
410 | } |
||
411 | /// Hook called whenever an \#elifndef is skipped. |
||
412 | /// \param Loc the source location of the directive. |
||
413 | /// \param ConditionRange The SourceRange of the expression being tested. |
||
414 | /// \param IfLoc the source location of the \#if/\#ifdef/\#ifndef directive. |
||
415 | // FIXME: better to pass in a list (or tree!) of Tokens. |
||
416 | virtual void Elifndef(SourceLocation Loc, SourceRange ConditionRange, |
||
417 | SourceLocation IfLoc) { |
||
418 | } |
||
419 | |||
420 | /// Hook called whenever an \#else is seen. |
||
421 | /// \param Loc the source location of the directive. |
||
422 | /// \param IfLoc the source location of the \#if/\#ifdef/\#ifndef directive. |
||
423 | virtual void Else(SourceLocation Loc, SourceLocation IfLoc) { |
||
424 | } |
||
425 | |||
426 | /// Hook called whenever an \#endif is seen. |
||
427 | /// \param Loc the source location of the directive. |
||
428 | /// \param IfLoc the source location of the \#if/\#ifdef/\#ifndef directive. |
||
429 | virtual void Endif(SourceLocation Loc, SourceLocation IfLoc) { |
||
430 | } |
||
431 | }; |
||
432 | |||
433 | /// Simple wrapper class for chaining callbacks. |
||
434 | class PPChainedCallbacks : public PPCallbacks { |
||
435 | std::unique_ptr<PPCallbacks> First, Second; |
||
436 | |||
437 | public: |
||
438 | PPChainedCallbacks(std::unique_ptr<PPCallbacks> _First, |
||
439 | std::unique_ptr<PPCallbacks> _Second) |
||
440 | : First(std::move(_First)), Second(std::move(_Second)) {} |
||
441 | |||
442 | ~PPChainedCallbacks() override; |
||
443 | |||
444 | void FileChanged(SourceLocation Loc, FileChangeReason Reason, |
||
445 | SrcMgr::CharacteristicKind FileType, |
||
446 | FileID PrevFID) override { |
||
447 | First->FileChanged(Loc, Reason, FileType, PrevFID); |
||
448 | Second->FileChanged(Loc, Reason, FileType, PrevFID); |
||
449 | } |
||
450 | |||
451 | void LexedFileChanged(FileID FID, LexedFileChangeReason Reason, |
||
452 | SrcMgr::CharacteristicKind FileType, FileID PrevFID, |
||
453 | SourceLocation Loc) override { |
||
454 | First->LexedFileChanged(FID, Reason, FileType, PrevFID, Loc); |
||
455 | Second->LexedFileChanged(FID, Reason, FileType, PrevFID, Loc); |
||
456 | } |
||
457 | |||
458 | void FileSkipped(const FileEntryRef &SkippedFile, const Token &FilenameTok, |
||
459 | SrcMgr::CharacteristicKind FileType) override { |
||
460 | First->FileSkipped(SkippedFile, FilenameTok, FileType); |
||
461 | Second->FileSkipped(SkippedFile, FilenameTok, FileType); |
||
462 | } |
||
463 | |||
464 | bool FileNotFound(StringRef FileName) override { |
||
465 | bool Skip = First->FileNotFound(FileName); |
||
466 | // Make sure to invoke the second callback, no matter if the first already |
||
467 | // returned true to skip the file. |
||
468 | Skip |= Second->FileNotFound(FileName); |
||
469 | return Skip; |
||
470 | } |
||
471 | |||
472 | void InclusionDirective(SourceLocation HashLoc, const Token &IncludeTok, |
||
473 | StringRef FileName, bool IsAngled, |
||
474 | CharSourceRange FilenameRange, |
||
475 | OptionalFileEntryRef File, StringRef SearchPath, |
||
476 | StringRef RelativePath, const Module *Imported, |
||
477 | SrcMgr::CharacteristicKind FileType) override { |
||
478 | First->InclusionDirective(HashLoc, IncludeTok, FileName, IsAngled, |
||
479 | FilenameRange, File, SearchPath, RelativePath, |
||
480 | Imported, FileType); |
||
481 | Second->InclusionDirective(HashLoc, IncludeTok, FileName, IsAngled, |
||
482 | FilenameRange, File, SearchPath, RelativePath, |
||
483 | Imported, FileType); |
||
484 | } |
||
485 | |||
486 | void EnteredSubmodule(Module *M, SourceLocation ImportLoc, |
||
487 | bool ForPragma) override { |
||
488 | First->EnteredSubmodule(M, ImportLoc, ForPragma); |
||
489 | Second->EnteredSubmodule(M, ImportLoc, ForPragma); |
||
490 | } |
||
491 | |||
492 | void LeftSubmodule(Module *M, SourceLocation ImportLoc, |
||
493 | bool ForPragma) override { |
||
494 | First->LeftSubmodule(M, ImportLoc, ForPragma); |
||
495 | Second->LeftSubmodule(M, ImportLoc, ForPragma); |
||
496 | } |
||
497 | |||
498 | void moduleImport(SourceLocation ImportLoc, ModuleIdPath Path, |
||
499 | const Module *Imported) override { |
||
500 | First->moduleImport(ImportLoc, Path, Imported); |
||
501 | Second->moduleImport(ImportLoc, Path, Imported); |
||
502 | } |
||
503 | |||
504 | void EndOfMainFile() override { |
||
505 | First->EndOfMainFile(); |
||
506 | Second->EndOfMainFile(); |
||
507 | } |
||
508 | |||
509 | void Ident(SourceLocation Loc, StringRef str) override { |
||
510 | First->Ident(Loc, str); |
||
511 | Second->Ident(Loc, str); |
||
512 | } |
||
513 | |||
514 | void PragmaDirective(SourceLocation Loc, |
||
515 | PragmaIntroducerKind Introducer) override { |
||
516 | First->PragmaDirective(Loc, Introducer); |
||
517 | Second->PragmaDirective(Loc, Introducer); |
||
518 | } |
||
519 | |||
520 | void PragmaComment(SourceLocation Loc, const IdentifierInfo *Kind, |
||
521 | StringRef Str) override { |
||
522 | First->PragmaComment(Loc, Kind, Str); |
||
523 | Second->PragmaComment(Loc, Kind, Str); |
||
524 | } |
||
525 | |||
526 | void PragmaMark(SourceLocation Loc, StringRef Trivia) override { |
||
527 | First->PragmaMark(Loc, Trivia); |
||
528 | Second->PragmaMark(Loc, Trivia); |
||
529 | } |
||
530 | |||
531 | void PragmaDetectMismatch(SourceLocation Loc, StringRef Name, |
||
532 | StringRef Value) override { |
||
533 | First->PragmaDetectMismatch(Loc, Name, Value); |
||
534 | Second->PragmaDetectMismatch(Loc, Name, Value); |
||
535 | } |
||
536 | |||
537 | void PragmaDebug(SourceLocation Loc, StringRef DebugType) override { |
||
538 | First->PragmaDebug(Loc, DebugType); |
||
539 | Second->PragmaDebug(Loc, DebugType); |
||
540 | } |
||
541 | |||
542 | void PragmaMessage(SourceLocation Loc, StringRef Namespace, |
||
543 | PragmaMessageKind Kind, StringRef Str) override { |
||
544 | First->PragmaMessage(Loc, Namespace, Kind, Str); |
||
545 | Second->PragmaMessage(Loc, Namespace, Kind, Str); |
||
546 | } |
||
547 | |||
548 | void PragmaDiagnosticPush(SourceLocation Loc, StringRef Namespace) override { |
||
549 | First->PragmaDiagnosticPush(Loc, Namespace); |
||
550 | Second->PragmaDiagnosticPush(Loc, Namespace); |
||
551 | } |
||
552 | |||
553 | void PragmaDiagnosticPop(SourceLocation Loc, StringRef Namespace) override { |
||
554 | First->PragmaDiagnosticPop(Loc, Namespace); |
||
555 | Second->PragmaDiagnosticPop(Loc, Namespace); |
||
556 | } |
||
557 | |||
558 | void PragmaDiagnostic(SourceLocation Loc, StringRef Namespace, |
||
559 | diag::Severity mapping, StringRef Str) override { |
||
560 | First->PragmaDiagnostic(Loc, Namespace, mapping, Str); |
||
561 | Second->PragmaDiagnostic(Loc, Namespace, mapping, Str); |
||
562 | } |
||
563 | |||
564 | void HasInclude(SourceLocation Loc, StringRef FileName, bool IsAngled, |
||
565 | OptionalFileEntryRef File, |
||
566 | SrcMgr::CharacteristicKind FileType) override; |
||
567 | |||
568 | void PragmaOpenCLExtension(SourceLocation NameLoc, const IdentifierInfo *Name, |
||
569 | SourceLocation StateLoc, unsigned State) override { |
||
570 | First->PragmaOpenCLExtension(NameLoc, Name, StateLoc, State); |
||
571 | Second->PragmaOpenCLExtension(NameLoc, Name, StateLoc, State); |
||
572 | } |
||
573 | |||
574 | void PragmaWarning(SourceLocation Loc, PragmaWarningSpecifier WarningSpec, |
||
575 | ArrayRef<int> Ids) override { |
||
576 | First->PragmaWarning(Loc, WarningSpec, Ids); |
||
577 | Second->PragmaWarning(Loc, WarningSpec, Ids); |
||
578 | } |
||
579 | |||
580 | void PragmaWarningPush(SourceLocation Loc, int Level) override { |
||
581 | First->PragmaWarningPush(Loc, Level); |
||
582 | Second->PragmaWarningPush(Loc, Level); |
||
583 | } |
||
584 | |||
585 | void PragmaWarningPop(SourceLocation Loc) override { |
||
586 | First->PragmaWarningPop(Loc); |
||
587 | Second->PragmaWarningPop(Loc); |
||
588 | } |
||
589 | |||
590 | void PragmaExecCharsetPush(SourceLocation Loc, StringRef Str) override { |
||
591 | First->PragmaExecCharsetPush(Loc, Str); |
||
592 | Second->PragmaExecCharsetPush(Loc, Str); |
||
593 | } |
||
594 | |||
595 | void PragmaExecCharsetPop(SourceLocation Loc) override { |
||
596 | First->PragmaExecCharsetPop(Loc); |
||
597 | Second->PragmaExecCharsetPop(Loc); |
||
598 | } |
||
599 | |||
600 | void PragmaAssumeNonNullBegin(SourceLocation Loc) override { |
||
601 | First->PragmaAssumeNonNullBegin(Loc); |
||
602 | Second->PragmaAssumeNonNullBegin(Loc); |
||
603 | } |
||
604 | |||
605 | void PragmaAssumeNonNullEnd(SourceLocation Loc) override { |
||
606 | First->PragmaAssumeNonNullEnd(Loc); |
||
607 | Second->PragmaAssumeNonNullEnd(Loc); |
||
608 | } |
||
609 | |||
610 | void MacroExpands(const Token &MacroNameTok, const MacroDefinition &MD, |
||
611 | SourceRange Range, const MacroArgs *Args) override { |
||
612 | First->MacroExpands(MacroNameTok, MD, Range, Args); |
||
613 | Second->MacroExpands(MacroNameTok, MD, Range, Args); |
||
614 | } |
||
615 | |||
616 | void MacroDefined(const Token &MacroNameTok, |
||
617 | const MacroDirective *MD) override { |
||
618 | First->MacroDefined(MacroNameTok, MD); |
||
619 | Second->MacroDefined(MacroNameTok, MD); |
||
620 | } |
||
621 | |||
622 | void MacroUndefined(const Token &MacroNameTok, |
||
623 | const MacroDefinition &MD, |
||
624 | const MacroDirective *Undef) override { |
||
625 | First->MacroUndefined(MacroNameTok, MD, Undef); |
||
626 | Second->MacroUndefined(MacroNameTok, MD, Undef); |
||
627 | } |
||
628 | |||
629 | void Defined(const Token &MacroNameTok, const MacroDefinition &MD, |
||
630 | SourceRange Range) override { |
||
631 | First->Defined(MacroNameTok, MD, Range); |
||
632 | Second->Defined(MacroNameTok, MD, Range); |
||
633 | } |
||
634 | |||
635 | void SourceRangeSkipped(SourceRange Range, SourceLocation EndifLoc) override { |
||
636 | First->SourceRangeSkipped(Range, EndifLoc); |
||
637 | Second->SourceRangeSkipped(Range, EndifLoc); |
||
638 | } |
||
639 | |||
640 | /// Hook called whenever an \#if is seen. |
||
641 | void If(SourceLocation Loc, SourceRange ConditionRange, |
||
642 | ConditionValueKind ConditionValue) override { |
||
643 | First->If(Loc, ConditionRange, ConditionValue); |
||
644 | Second->If(Loc, ConditionRange, ConditionValue); |
||
645 | } |
||
646 | |||
647 | /// Hook called whenever an \#elif is seen. |
||
648 | void Elif(SourceLocation Loc, SourceRange ConditionRange, |
||
649 | ConditionValueKind ConditionValue, SourceLocation IfLoc) override { |
||
650 | First->Elif(Loc, ConditionRange, ConditionValue, IfLoc); |
||
651 | Second->Elif(Loc, ConditionRange, ConditionValue, IfLoc); |
||
652 | } |
||
653 | |||
654 | /// Hook called whenever an \#ifdef is seen. |
||
655 | void Ifdef(SourceLocation Loc, const Token &MacroNameTok, |
||
656 | const MacroDefinition &MD) override { |
||
657 | First->Ifdef(Loc, MacroNameTok, MD); |
||
658 | Second->Ifdef(Loc, MacroNameTok, MD); |
||
659 | } |
||
660 | |||
661 | /// Hook called whenever an \#elifdef is taken. |
||
662 | void Elifdef(SourceLocation Loc, const Token &MacroNameTok, |
||
663 | const MacroDefinition &MD) override { |
||
664 | First->Elifdef(Loc, MacroNameTok, MD); |
||
665 | Second->Elifdef(Loc, MacroNameTok, MD); |
||
666 | } |
||
667 | /// Hook called whenever an \#elifdef is skipped. |
||
668 | void Elifdef(SourceLocation Loc, SourceRange ConditionRange, |
||
669 | SourceLocation IfLoc) override { |
||
670 | First->Elifdef(Loc, ConditionRange, IfLoc); |
||
671 | Second->Elifdef(Loc, ConditionRange, IfLoc); |
||
672 | } |
||
673 | |||
674 | /// Hook called whenever an \#ifndef is seen. |
||
675 | void Ifndef(SourceLocation Loc, const Token &MacroNameTok, |
||
676 | const MacroDefinition &MD) override { |
||
677 | First->Ifndef(Loc, MacroNameTok, MD); |
||
678 | Second->Ifndef(Loc, MacroNameTok, MD); |
||
679 | } |
||
680 | |||
681 | /// Hook called whenever an \#elifndef is taken. |
||
682 | void Elifndef(SourceLocation Loc, const Token &MacroNameTok, |
||
683 | const MacroDefinition &MD) override { |
||
684 | First->Elifndef(Loc, MacroNameTok, MD); |
||
685 | Second->Elifndef(Loc, MacroNameTok, MD); |
||
686 | } |
||
687 | /// Hook called whenever an \#elifndef is skipped. |
||
688 | void Elifndef(SourceLocation Loc, SourceRange ConditionRange, |
||
689 | SourceLocation IfLoc) override { |
||
690 | First->Elifndef(Loc, ConditionRange, IfLoc); |
||
691 | Second->Elifndef(Loc, ConditionRange, IfLoc); |
||
692 | } |
||
693 | |||
694 | /// Hook called whenever an \#else is seen. |
||
695 | void Else(SourceLocation Loc, SourceLocation IfLoc) override { |
||
696 | First->Else(Loc, IfLoc); |
||
697 | Second->Else(Loc, IfLoc); |
||
698 | } |
||
699 | |||
700 | /// Hook called whenever an \#endif is seen. |
||
701 | void Endif(SourceLocation Loc, SourceLocation IfLoc) override { |
||
702 | First->Endif(Loc, IfLoc); |
||
703 | Second->Endif(Loc, IfLoc); |
||
704 | } |
||
705 | }; |
||
706 | |||
707 | } // end namespace clang |
||
708 | |||
709 | #endif |