]> CyberLeo.Net >> Repos - FreeBSD/stable/9.git/blob - contrib/llvm/tools/clang/include/clang/Lex/PPCallbacks.h
MFC r234353:
[FreeBSD/stable/9.git] / contrib / llvm / tools / clang / include / clang / Lex / PPCallbacks.h
1 //===--- PPCallbacks.h - Callbacks for Preprocessor actions -----*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 //  This file 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/Lex/DirectoryLookup.h"
18 #include "clang/Basic/SourceLocation.h"
19 #include "clang/Basic/DiagnosticIDs.h"
20 #include "llvm/ADT/StringRef.h"
21 #include <string>
22
23 namespace clang {
24   class SourceLocation;
25   class Token;
26   class IdentifierInfo;
27   class MacroInfo;
28
29 /// PPCallbacks - This interface provides a way to observe the actions of the
30 /// preprocessor as it does its thing.  Clients can define their hooks here to
31 /// implement preprocessor level tools.
32 class PPCallbacks {
33 public:
34   virtual ~PPCallbacks();
35
36   enum FileChangeReason {
37     EnterFile, ExitFile, SystemHeaderPragma, RenameFile
38   };
39
40   /// FileChanged - This callback is invoked whenever a source file is
41   /// entered or exited.  The SourceLocation indicates the new location, and
42   /// EnteringFile indicates whether this is because we are entering a new
43   /// #include'd file (when true) or whether we're exiting one because we ran
44   /// off the end (when false).
45   ///
46   /// \param PrevFID the file that was exited if \arg Reason is ExitFile. 
47   virtual void FileChanged(SourceLocation Loc, FileChangeReason Reason,
48                            SrcMgr::CharacteristicKind FileType,
49                            FileID PrevFID = FileID()) {
50   }
51
52   /// FileSkipped - This callback is invoked whenever a source file is
53   /// skipped as the result of header guard optimization.  ParentFile
54   /// is the file that #includes the skipped file.  FilenameTok is the
55   /// token in ParentFile that indicates the skipped file.
56   virtual void FileSkipped(const FileEntry &ParentFile,
57                            const Token &FilenameTok,
58                            SrcMgr::CharacteristicKind FileType) {
59   }
60
61   /// FileNotFound - This callback is invoked whenever an inclusion directive
62   /// results in a file-not-found error.
63   ///
64   /// \param FileName The name of the file being included, as written in the 
65   /// source code.
66   ///
67   /// \param RecoveryPath If this client indicates that it can recover from 
68   /// this missing file, the client should set this as an additional header
69   /// search patch.
70   ///
71   /// \returns true to indicate that the preprocessor should attempt to recover
72   /// by adding \p RecoveryPath as a header search path.
73   virtual bool FileNotFound(StringRef FileName,
74                             SmallVectorImpl<char> &RecoveryPath) {
75     return false;
76   }
77
78   /// \brief This callback is invoked whenever an inclusion directive of
79   /// any kind (\c #include, \c #import, etc.) has been processed, regardless
80   /// of whether the inclusion will actually result in an inclusion.
81   ///
82   /// \param HashLoc The location of the '#' that starts the inclusion 
83   /// directive.
84   ///
85   /// \param IncludeTok The token that indicates the kind of inclusion 
86   /// directive, e.g., 'include' or 'import'.
87   ///
88   /// \param FileName The name of the file being included, as written in the 
89   /// source code.
90   ///
91   /// \param IsAngled Whether the file name was enclosed in angle brackets;
92   /// otherwise, it was enclosed in quotes.
93   ///
94   /// \param File The actual file that may be included by this inclusion 
95   /// directive.
96   ///
97   /// \param EndLoc The location of the last token within the inclusion
98   /// directive.
99   ///
100   /// \param SearchPath Contains the search path which was used to find the file
101   /// in the file system. If the file was found via an absolute include path,
102   /// SearchPath will be empty. For framework includes, the SearchPath and
103   /// RelativePath will be split up. For example, if an include of "Some/Some.h"
104   /// is found via the framework path
105   /// "path/to/Frameworks/Some.framework/Headers/Some.h", SearchPath will be
106   /// "path/to/Frameworks/Some.framework/Headers" and RelativePath will be
107   /// "Some.h".
108   ///
109   /// \param RelativePath The path relative to SearchPath, at which the include
110   /// file was found. This is equal to FileName except for framework includes.
111   virtual void InclusionDirective(SourceLocation HashLoc,
112                                   const Token &IncludeTok,
113                                   StringRef FileName,
114                                   bool IsAngled,
115                                   const FileEntry *File,
116                                   SourceLocation EndLoc,
117                                   StringRef SearchPath,
118                                   StringRef RelativePath) {
119   }
120
121   /// EndOfMainFile - This callback is invoked when the end of the main file is
122   /// reach, no subsequent callbacks will be made.
123   virtual void EndOfMainFile() {
124   }
125
126   /// Ident - This callback is invoked when a #ident or #sccs directive is read.
127   /// \param Loc The location of the directive.
128   /// \param str The text of the directive.
129   ///
130   virtual void Ident(SourceLocation Loc, const std::string &str) {
131   }
132
133   /// PragmaComment - This callback is invoked when a #pragma comment directive
134   /// is read.
135   ///
136   virtual void PragmaComment(SourceLocation Loc, const IdentifierInfo *Kind,
137                              const std::string &Str) {
138   }
139
140   /// PragmaMessage - This callback is invoked when a #pragma message directive
141   /// is read.
142   /// \param Loc The location of the message directive.
143   /// \param str The text of the message directive.
144   ///
145   virtual void PragmaMessage(SourceLocation Loc, StringRef Str) {
146   }
147
148   /// PragmaDiagnosticPush - This callback is invoked when a
149   /// #pragma gcc dianostic push directive is read.
150   virtual void PragmaDiagnosticPush(SourceLocation Loc,
151                                     StringRef Namespace) {
152   }
153
154   /// PragmaDiagnosticPop - This callback is invoked when a
155   /// #pragma gcc dianostic pop directive is read.
156   virtual void PragmaDiagnosticPop(SourceLocation Loc,
157                                    StringRef Namespace) {
158   }
159
160   /// PragmaDiagnostic - This callback is invoked when a
161   /// #pragma gcc dianostic directive is read.
162   virtual void PragmaDiagnostic(SourceLocation Loc, StringRef Namespace,
163                                 diag::Mapping mapping, StringRef Str) {
164   }
165
166   /// MacroExpands - This is called by
167   /// Preprocessor::HandleMacroExpandedIdentifier when a macro invocation is
168   /// found.
169   virtual void MacroExpands(const Token &MacroNameTok, const MacroInfo* MI,
170                             SourceRange Range) {
171   }
172
173   /// MacroDefined - This hook is called whenever a macro definition is seen.
174   virtual void MacroDefined(const Token &MacroNameTok, const MacroInfo *MI) {
175   }
176
177   /// MacroUndefined - This hook is called whenever a macro #undef is seen.
178   /// MI is released immediately following this callback.
179   virtual void MacroUndefined(const Token &MacroNameTok, const MacroInfo *MI) {
180   }
181   
182   /// Defined - This hook is called whenever the 'defined' operator is seen.
183   virtual void Defined(const Token &MacroNameTok) {
184   }
185   
186   /// SourceRangeSkipped - This hook is called when a source range is skipped.
187   /// \param Range The SourceRange that was skipped. The range begins at the
188   /// #if/#else directive and ends after the #endif/#else directive.
189   virtual void SourceRangeSkipped(SourceRange Range) {
190   }
191
192   /// If -- This hook is called whenever an #if is seen.
193   /// \param Loc the source location of the directive.
194   /// \param ConditionRange The SourceRange of the expression being tested.
195   // FIXME: better to pass in a list (or tree!) of Tokens.
196   virtual void If(SourceLocation Loc, SourceRange ConditionRange) {
197   }
198
199   /// Elif -- This hook is called whenever an #elif is seen.
200   /// \param Loc the source location of the directive.
201   /// \param ConditionRange The SourceRange of the expression being tested.
202   /// \param IfLoc the source location of the #if/#ifdef/#ifndef directive.
203   // FIXME: better to pass in a list (or tree!) of Tokens.
204   virtual void Elif(SourceLocation Loc, SourceRange ConditionRange,
205                     SourceLocation IfLoc) {
206   }
207
208   /// Ifdef -- This hook is called whenever an #ifdef is seen.
209   /// \param Loc the source location of the directive.
210   /// \param II Information on the token being tested.
211   virtual void Ifdef(SourceLocation Loc, const Token &MacroNameTok) {
212   }
213
214   /// Ifndef -- This hook is called whenever an #ifndef is seen.
215   /// \param Loc the source location of the directive.
216   /// \param II Information on the token being tested.
217   virtual void Ifndef(SourceLocation Loc, const Token &MacroNameTok) {
218   }
219
220   /// Else -- This hook is called whenever an #else is seen.
221   /// \param Loc the source location of the directive.
222   /// \param IfLoc the source location of the #if/#ifdef/#ifndef directive.
223   virtual void Else(SourceLocation Loc, SourceLocation IfLoc) {
224   }
225
226   /// Endif -- This hook is called whenever an #endif is seen.
227   /// \param Loc the source location of the directive.
228   /// \param IfLoc the source location of the #if/#ifdef/#ifndef directive.
229   virtual void Endif(SourceLocation Loc, SourceLocation IfLoc) {
230   }
231 };
232
233 /// PPChainedCallbacks - Simple wrapper class for chaining callbacks.
234 class PPChainedCallbacks : public PPCallbacks {
235   virtual void anchor();
236   PPCallbacks *First, *Second;
237
238 public:
239   PPChainedCallbacks(PPCallbacks *_First, PPCallbacks *_Second)
240     : First(_First), Second(_Second) {}
241   ~PPChainedCallbacks() {
242     delete Second;
243     delete First;
244   }
245
246   virtual void FileChanged(SourceLocation Loc, FileChangeReason Reason,
247                            SrcMgr::CharacteristicKind FileType,
248                            FileID PrevFID) {
249     First->FileChanged(Loc, Reason, FileType, PrevFID);
250     Second->FileChanged(Loc, Reason, FileType, PrevFID);
251   }
252
253   virtual void FileSkipped(const FileEntry &ParentFile,
254                            const Token &FilenameTok,
255                            SrcMgr::CharacteristicKind FileType) {
256     First->FileSkipped(ParentFile, FilenameTok, FileType);
257     Second->FileSkipped(ParentFile, FilenameTok, FileType);
258   }
259
260   virtual bool FileNotFound(StringRef FileName,
261                             SmallVectorImpl<char> &RecoveryPath) {
262     return First->FileNotFound(FileName, RecoveryPath) ||
263            Second->FileNotFound(FileName, RecoveryPath);
264   }
265
266   virtual void InclusionDirective(SourceLocation HashLoc,
267                                   const Token &IncludeTok,
268                                   StringRef FileName,
269                                   bool IsAngled,
270                                   const FileEntry *File,
271                                   SourceLocation EndLoc,
272                                   StringRef SearchPath,
273                                   StringRef RelativePath) {
274     First->InclusionDirective(HashLoc, IncludeTok, FileName, IsAngled, File,
275                               EndLoc, SearchPath, RelativePath);
276     Second->InclusionDirective(HashLoc, IncludeTok, FileName, IsAngled, File,
277                                EndLoc, SearchPath, RelativePath);
278   }
279
280   virtual void EndOfMainFile() {
281     First->EndOfMainFile();
282     Second->EndOfMainFile();
283   }
284
285   virtual void Ident(SourceLocation Loc, const std::string &str) {
286     First->Ident(Loc, str);
287     Second->Ident(Loc, str);
288   }
289
290   virtual void PragmaComment(SourceLocation Loc, const IdentifierInfo *Kind,
291                              const std::string &Str) {
292     First->PragmaComment(Loc, Kind, Str);
293     Second->PragmaComment(Loc, Kind, Str);
294   }
295
296   virtual void PragmaMessage(SourceLocation Loc, StringRef Str) {
297     First->PragmaMessage(Loc, Str);
298     Second->PragmaMessage(Loc, Str);
299   }
300
301   virtual void PragmaDiagnosticPush(SourceLocation Loc,
302                                     StringRef Namespace) {
303     First->PragmaDiagnosticPush(Loc, Namespace);
304     Second->PragmaDiagnosticPush(Loc, Namespace);
305   }
306
307   virtual void PragmaDiagnosticPop(SourceLocation Loc,
308                                     StringRef Namespace) {
309     First->PragmaDiagnosticPop(Loc, Namespace);
310     Second->PragmaDiagnosticPop(Loc, Namespace);
311   }
312
313   virtual void PragmaDiagnostic(SourceLocation Loc, StringRef Namespace,
314                                 diag::Mapping mapping, StringRef Str) {
315     First->PragmaDiagnostic(Loc, Namespace, mapping, Str);
316     Second->PragmaDiagnostic(Loc, Namespace, mapping, Str);
317   }
318
319   virtual void MacroExpands(const Token &MacroNameTok, const MacroInfo* MI,
320                             SourceRange Range) {
321     First->MacroExpands(MacroNameTok, MI, Range);
322     Second->MacroExpands(MacroNameTok, MI, Range);
323   }
324
325   virtual void MacroDefined(const Token &MacroNameTok, const MacroInfo *MI) {
326     First->MacroDefined(MacroNameTok, MI);
327     Second->MacroDefined(MacroNameTok, MI);
328   }
329
330   virtual void MacroUndefined(const Token &MacroNameTok, const MacroInfo *MI) {
331     First->MacroUndefined(MacroNameTok, MI);
332     Second->MacroUndefined(MacroNameTok, MI);
333   }
334
335   virtual void Defined(const Token &MacroNameTok) {
336     First->Defined(MacroNameTok);
337     Second->Defined(MacroNameTok);
338   }
339
340   virtual void SourceRangeSkipped(SourceRange Range) {
341     First->SourceRangeSkipped(Range);
342     Second->SourceRangeSkipped(Range);
343   }
344
345   /// If -- This hook is called whenever an #if is seen.
346   virtual void If(SourceLocation Loc, SourceRange ConditionRange) {
347     First->If(Loc, ConditionRange);
348     Second->If(Loc, ConditionRange);
349   }
350
351   /// Elif -- This hook is called whenever an #if is seen.
352   virtual void Elif(SourceLocation Loc, SourceRange ConditionRange,
353                     SourceLocation IfLoc) {
354     First->Elif(Loc, ConditionRange, IfLoc);
355     Second->Elif(Loc, ConditionRange, IfLoc);
356   }
357
358   /// Ifdef -- This hook is called whenever an #ifdef is seen.
359   virtual void Ifdef(SourceLocation Loc, const Token &MacroNameTok) {
360     First->Ifdef(Loc, MacroNameTok);
361     Second->Ifdef(Loc, MacroNameTok);
362   }
363
364   /// Ifndef -- This hook is called whenever an #ifndef is seen.
365   virtual void Ifndef(SourceLocation Loc, const Token &MacroNameTok) {
366     First->Ifndef(Loc, MacroNameTok);
367     Second->Ifndef(Loc, MacroNameTok);
368   }
369
370   /// Else -- This hook is called whenever an #else is seen.
371   virtual void Else(SourceLocation Loc, SourceLocation IfLoc) {
372     First->Else(Loc, IfLoc);
373     Second->Else(Loc, IfLoc);
374   }
375
376   /// Endif -- This hook is called whenever an #endif is seen.
377   virtual void Endif(SourceLocation Loc, SourceLocation IfLoc) {
378     First->Endif(Loc, IfLoc);
379     Second->Endif(Loc, IfLoc);
380   }
381 };
382
383 }  // end namespace clang
384
385 #endif