1193326Sed//===--- PPCallbacks.h - Callbacks for Preprocessor actions -----*- C++ -*-===// 2193326Sed// 3193326Sed// The LLVM Compiler Infrastructure 4193326Sed// 5193326Sed// This file is distributed under the University of Illinois Open Source 6193326Sed// License. See LICENSE.TXT for details. 7193326Sed// 8193326Sed//===----------------------------------------------------------------------===// 9245431Sdim/// 10245431Sdim/// \file 11245431Sdim/// \brief Defines the PPCallbacks interface. 12245431Sdim/// 13193326Sed//===----------------------------------------------------------------------===// 14193326Sed 15193326Sed#ifndef LLVM_CLANG_LEX_PPCALLBACKS_H 16193326Sed#define LLVM_CLANG_LEX_PPCALLBACKS_H 17193326Sed 18252723Sdim#include "clang/Basic/DiagnosticIDs.h" 19252723Sdim#include "clang/Basic/SourceLocation.h" 20193326Sed#include "clang/Lex/DirectoryLookup.h" 21245431Sdim#include "clang/Lex/ModuleLoader.h" 22263509Sdim#include "clang/Lex/Pragma.h" 23210299Sed#include "llvm/ADT/StringRef.h" 24193326Sed#include <string> 25193326Sed 26193326Sednamespace clang { 27193326Sed class SourceLocation; 28193326Sed class Token; 29193326Sed class IdentifierInfo; 30252723Sdim class MacroDirective; 31252723Sdim class MacroArgs; 32198092Srdivacky 33245431Sdim/// \brief This interface provides a way to observe the actions of the 34245431Sdim/// preprocessor as it does its thing. 35245431Sdim/// 36245431Sdim/// Clients can define their hooks here to implement preprocessor level tools. 37193326Sedclass PPCallbacks { 38193326Sedpublic: 39193326Sed virtual ~PPCallbacks(); 40198092Srdivacky 41193326Sed enum FileChangeReason { 42193326Sed EnterFile, ExitFile, SystemHeaderPragma, RenameFile 43193326Sed }; 44198092Srdivacky 45245431Sdim /// \brief Callback invoked whenever a source file is entered or exited. 46226890Sdim /// 47245431Sdim /// \param Loc Indicates the new location. 48245431Sdim /// \param PrevFID the file that was exited if \p Reason is ExitFile. 49193326Sed virtual void FileChanged(SourceLocation Loc, FileChangeReason Reason, 50226890Sdim SrcMgr::CharacteristicKind FileType, 51226890Sdim FileID PrevFID = FileID()) { 52193326Sed } 53198092Srdivacky 54245431Sdim /// \brief Callback invoked whenever a source file is skipped as the result 55245431Sdim /// of header guard optimization. 56245431Sdim /// 57245431Sdim /// \param ParentFile The file that \#included the skipped file. 58245431Sdim /// 59245431Sdim /// \param FilenameTok The token in ParentFile that indicates the 60245431Sdim /// skipped file. 61207619Srdivacky virtual void FileSkipped(const FileEntry &ParentFile, 62207619Srdivacky const Token &FilenameTok, 63207619Srdivacky SrcMgr::CharacteristicKind FileType) { 64207619Srdivacky } 65206084Srdivacky 66245431Sdim /// \brief Callback invoked whenever an inclusion directive results in a 67245431Sdim /// file-not-found error. 68235633Sdim /// 69235633Sdim /// \param FileName The name of the file being included, as written in the 70235633Sdim /// source code. 71235633Sdim /// 72235633Sdim /// \param RecoveryPath If this client indicates that it can recover from 73235633Sdim /// this missing file, the client should set this as an additional header 74235633Sdim /// search patch. 75235633Sdim /// 76235633Sdim /// \returns true to indicate that the preprocessor should attempt to recover 77235633Sdim /// by adding \p RecoveryPath as a header search path. 78235633Sdim virtual bool FileNotFound(StringRef FileName, 79235633Sdim SmallVectorImpl<char> &RecoveryPath) { 80235633Sdim return false; 81235633Sdim } 82235633Sdim 83245431Sdim /// \brief Callback invoked whenever an inclusion directive of 84245431Sdim /// any kind (\c \#include, \c \#import, etc.) has been processed, regardless 85218893Sdim /// of whether the inclusion will actually result in an inclusion. 86218893Sdim /// 87218893Sdim /// \param HashLoc The location of the '#' that starts the inclusion 88218893Sdim /// directive. 89218893Sdim /// 90218893Sdim /// \param IncludeTok The token that indicates the kind of inclusion 91218893Sdim /// directive, e.g., 'include' or 'import'. 92218893Sdim /// 93218893Sdim /// \param FileName The name of the file being included, as written in the 94218893Sdim /// source code. 95218893Sdim /// 96218893Sdim /// \param IsAngled Whether the file name was enclosed in angle brackets; 97218893Sdim /// otherwise, it was enclosed in quotes. 98218893Sdim /// 99245431Sdim /// \param FilenameRange The character range of the quotes or angle brackets 100245431Sdim /// for the written file name. 101245431Sdim /// 102218893Sdim /// \param File The actual file that may be included by this inclusion 103218893Sdim /// directive. 104218893Sdim /// 105221345Sdim /// \param SearchPath Contains the search path which was used to find the file 106221345Sdim /// in the file system. If the file was found via an absolute include path, 107221345Sdim /// SearchPath will be empty. For framework includes, the SearchPath and 108221345Sdim /// RelativePath will be split up. For example, if an include of "Some/Some.h" 109221345Sdim /// is found via the framework path 110221345Sdim /// "path/to/Frameworks/Some.framework/Headers/Some.h", SearchPath will be 111221345Sdim /// "path/to/Frameworks/Some.framework/Headers" and RelativePath will be 112221345Sdim /// "Some.h". 113221345Sdim /// 114221345Sdim /// \param RelativePath The path relative to SearchPath, at which the include 115221345Sdim /// file was found. This is equal to FileName except for framework includes. 116245431Sdim /// 117245431Sdim /// \param Imported The module, whenever an inclusion directive was 118245431Sdim /// automatically turned into a module import or null otherwise. 119245431Sdim /// 120218893Sdim virtual void InclusionDirective(SourceLocation HashLoc, 121218893Sdim const Token &IncludeTok, 122226890Sdim StringRef FileName, 123218893Sdim bool IsAngled, 124245431Sdim CharSourceRange FilenameRange, 125218893Sdim const FileEntry *File, 126226890Sdim StringRef SearchPath, 127245431Sdim StringRef RelativePath, 128245431Sdim const Module *Imported) { 129218893Sdim } 130218893Sdim 131245431Sdim /// \brief Callback invoked whenever there was an explicit module-import 132245431Sdim /// syntax. 133245431Sdim /// 134245431Sdim /// \param ImportLoc The location of import directive token. 135245431Sdim /// 136245431Sdim /// \param Path The identifiers (and their locations) of the module 137245431Sdim /// "path", e.g., "std.vector" would be split into "std" and "vector". 138245431Sdim /// 139245431Sdim /// \param Imported The imported module; can be null if importing failed. 140245431Sdim /// 141245431Sdim virtual void moduleImport(SourceLocation ImportLoc, 142245431Sdim ModuleIdPath Path, 143245431Sdim const Module *Imported) { 144245431Sdim } 145245431Sdim 146245431Sdim /// \brief Callback invoked when the end of the main file is reached. 147245431Sdim /// 148245431Sdim /// No subsequent callbacks will be made. 149206084Srdivacky virtual void EndOfMainFile() { 150206084Srdivacky } 151206084Srdivacky 152245431Sdim /// \brief Callback invoked when a \#ident or \#sccs directive is read. 153218893Sdim /// \param Loc The location of the directive. 154218893Sdim /// \param str The text of the directive. 155193326Sed /// 156193326Sed virtual void Ident(SourceLocation Loc, const std::string &str) { 157193326Sed } 158198092Srdivacky 159263509Sdim /// \brief Callback invoked when start reading any pragma directive. 160263509Sdim virtual void PragmaDirective(SourceLocation Loc, 161263509Sdim PragmaIntroducerKind Introducer) { 162263509Sdim } 163263509Sdim 164245431Sdim /// \brief Callback invoked when a \#pragma comment directive is read. 165198092Srdivacky virtual void PragmaComment(SourceLocation Loc, const IdentifierInfo *Kind, 166193326Sed const std::string &Str) { 167193326Sed } 168198092Srdivacky 169263509Sdim /// \brief Callback invoked when a \#pragma detect_mismatch directive is 170263509Sdim /// read. 171263509Sdim virtual void PragmaDetectMismatch(SourceLocation Loc, 172263509Sdim const std::string &Name, 173263509Sdim const std::string &Value) { 174263509Sdim } 175263509Sdim 176252723Sdim /// \brief Callback invoked when a \#pragma clang __debug directive is read. 177252723Sdim /// \param Loc The location of the debug directive. 178252723Sdim /// \param DebugType The identifier following __debug. 179252723Sdim virtual void PragmaDebug(SourceLocation Loc, StringRef DebugType) { 180252723Sdim } 181252723Sdim 182252723Sdim /// \brief Determines the kind of \#pragma invoking a call to PragmaMessage. 183252723Sdim enum PragmaMessageKind { 184252723Sdim /// \brief \#pragma message has been invoked. 185252723Sdim PMK_Message, 186252723Sdim 187252723Sdim /// \brief \#pragma GCC warning has been invoked. 188252723Sdim PMK_Warning, 189252723Sdim 190252723Sdim /// \brief \#pragma GCC error has been invoked. 191252723Sdim PMK_Error 192252723Sdim }; 193252723Sdim 194245431Sdim /// \brief Callback invoked when a \#pragma message directive is read. 195218893Sdim /// \param Loc The location of the message directive. 196252723Sdim /// \param Namespace The namespace of the message directive. 197252723Sdim /// \param Kind The type of the message directive. 198245431Sdim /// \param Str The text of the message directive. 199252723Sdim virtual void PragmaMessage(SourceLocation Loc, StringRef Namespace, 200252723Sdim PragmaMessageKind Kind, StringRef Str) { 201210299Sed } 202210299Sed 203245431Sdim /// \brief Callback invoked when a \#pragma gcc dianostic push directive 204245431Sdim /// is read. 205224145Sdim virtual void PragmaDiagnosticPush(SourceLocation Loc, 206226890Sdim StringRef Namespace) { 207224145Sdim } 208224145Sdim 209245431Sdim /// \brief Callback invoked when a \#pragma gcc dianostic pop directive 210245431Sdim /// is read. 211224145Sdim virtual void PragmaDiagnosticPop(SourceLocation Loc, 212226890Sdim StringRef Namespace) { 213224145Sdim } 214224145Sdim 215245431Sdim /// \brief Callback invoked when a \#pragma gcc dianostic directive is read. 216226890Sdim virtual void PragmaDiagnostic(SourceLocation Loc, StringRef Namespace, 217226890Sdim diag::Mapping mapping, StringRef Str) { 218224145Sdim } 219224145Sdim 220263509Sdim /// \brief Called when an OpenCL extension is either disabled or 221263509Sdim /// enabled with a pragma. 222263509Sdim virtual void PragmaOpenCLExtension(SourceLocation NameLoc, 223263509Sdim const IdentifierInfo *Name, 224263509Sdim SourceLocation StateLoc, unsigned State) { 225263509Sdim } 226263509Sdim 227263509Sdim /// \brief Callback invoked when a \#pragma warning directive is read. 228263509Sdim virtual void PragmaWarning(SourceLocation Loc, StringRef WarningSpec, 229263509Sdim ArrayRef<int> Ids) { 230263509Sdim } 231263509Sdim 232263509Sdim /// \brief Callback invoked when a \#pragma warning(push) directive is read. 233263509Sdim virtual void PragmaWarningPush(SourceLocation Loc, int Level) { 234263509Sdim } 235263509Sdim 236263509Sdim /// \brief Callback invoked when a \#pragma warning(pop) directive is read. 237263509Sdim virtual void PragmaWarningPop(SourceLocation Loc) { 238263509Sdim } 239263509Sdim 240245431Sdim /// \brief Called by Preprocessor::HandleMacroExpandedIdentifier when a 241245431Sdim /// macro invocation is found. 242252723Sdim virtual void MacroExpands(const Token &MacroNameTok, const MacroDirective *MD, 243252723Sdim SourceRange Range, const MacroArgs *Args) { 244193326Sed } 245198092Srdivacky 246245431Sdim /// \brief Hook called whenever a macro definition is seen. 247252723Sdim virtual void MacroDefined(const Token &MacroNameTok, 248252723Sdim const MacroDirective *MD) { 249193326Sed } 250193326Sed 251245431Sdim /// \brief Hook called whenever a macro \#undef is seen. 252245431Sdim /// 253252723Sdim /// MD is released immediately following this callback. 254252723Sdim virtual void MacroUndefined(const Token &MacroNameTok, 255252723Sdim const MacroDirective *MD) { 256193326Sed } 257226890Sdim 258245431Sdim /// \brief Hook called whenever the 'defined' operator is seen. 259252723Sdim /// \param MD The MacroDirective if the name was a macro, null otherwise. 260263509Sdim virtual void Defined(const Token &MacroNameTok, const MacroDirective *MD, 261263509Sdim SourceRange Range) { 262226890Sdim } 263226890Sdim 264245431Sdim /// \brief Hook called when a source range is skipped. 265226890Sdim /// \param Range The SourceRange that was skipped. The range begins at the 266245431Sdim /// \#if/\#else directive and ends after the \#endif/\#else directive. 267226890Sdim virtual void SourceRangeSkipped(SourceRange Range) { 268226890Sdim } 269218893Sdim 270245431Sdim /// \brief Hook called whenever an \#if is seen. 271235633Sdim /// \param Loc the source location of the directive. 272235633Sdim /// \param ConditionRange The SourceRange of the expression being tested. 273263509Sdim /// \param ConditionValue The evaluated value of the condition. 274245431Sdim /// 275218893Sdim // FIXME: better to pass in a list (or tree!) of Tokens. 276263509Sdim virtual void If(SourceLocation Loc, SourceRange ConditionRange, 277263509Sdim bool ConditionValue) { 278218893Sdim } 279218893Sdim 280245431Sdim /// \brief Hook called whenever an \#elif is seen. 281235633Sdim /// \param Loc the source location of the directive. 282235633Sdim /// \param ConditionRange The SourceRange of the expression being tested. 283263509Sdim /// \param ConditionValue The evaluated value of the condition. 284245431Sdim /// \param IfLoc the source location of the \#if/\#ifdef/\#ifndef directive. 285218893Sdim // FIXME: better to pass in a list (or tree!) of Tokens. 286235633Sdim virtual void Elif(SourceLocation Loc, SourceRange ConditionRange, 287263509Sdim bool ConditionValue, SourceLocation IfLoc) { 288218893Sdim } 289218893Sdim 290245431Sdim /// \brief Hook called whenever an \#ifdef is seen. 291235633Sdim /// \param Loc the source location of the directive. 292245431Sdim /// \param MacroNameTok Information on the token being tested. 293252723Sdim /// \param MD The MacroDirective if the name was a macro, null otherwise. 294252723Sdim virtual void Ifdef(SourceLocation Loc, const Token &MacroNameTok, 295252723Sdim const MacroDirective *MD) { 296218893Sdim } 297218893Sdim 298245431Sdim /// \brief Hook called whenever an \#ifndef is seen. 299235633Sdim /// \param Loc the source location of the directive. 300245431Sdim /// \param MacroNameTok Information on the token being tested. 301252723Sdim /// \param MD The MacroDirective if the name was a macro, null otherwise. 302252723Sdim virtual void Ifndef(SourceLocation Loc, const Token &MacroNameTok, 303252723Sdim const MacroDirective *MD) { 304218893Sdim } 305218893Sdim 306245431Sdim /// \brief Hook called whenever an \#else is seen. 307235633Sdim /// \param Loc the source location of the directive. 308245431Sdim /// \param IfLoc the source location of the \#if/\#ifdef/\#ifndef directive. 309235633Sdim virtual void Else(SourceLocation Loc, SourceLocation IfLoc) { 310218893Sdim } 311218893Sdim 312245431Sdim /// \brief Hook called whenever an \#endif is seen. 313235633Sdim /// \param Loc the source location of the directive. 314245431Sdim /// \param IfLoc the source location of the \#if/\#ifdef/\#ifndef directive. 315235633Sdim virtual void Endif(SourceLocation Loc, SourceLocation IfLoc) { 316218893Sdim } 317193326Sed}; 318193326Sed 319245431Sdim/// \brief Simple wrapper class for chaining callbacks. 320193326Sedclass PPChainedCallbacks : public PPCallbacks { 321235633Sdim virtual void anchor(); 322193326Sed PPCallbacks *First, *Second; 323193326Sed 324198092Srdivackypublic: 325193326Sed PPChainedCallbacks(PPCallbacks *_First, PPCallbacks *_Second) 326193326Sed : First(_First), Second(_Second) {} 327193326Sed ~PPChainedCallbacks() { 328193326Sed delete Second; 329193326Sed delete First; 330193326Sed } 331193326Sed 332193326Sed virtual void FileChanged(SourceLocation Loc, FileChangeReason Reason, 333226890Sdim SrcMgr::CharacteristicKind FileType, 334226890Sdim FileID PrevFID) { 335226890Sdim First->FileChanged(Loc, Reason, FileType, PrevFID); 336226890Sdim Second->FileChanged(Loc, Reason, FileType, PrevFID); 337193326Sed } 338198092Srdivacky 339207619Srdivacky virtual void FileSkipped(const FileEntry &ParentFile, 340207619Srdivacky const Token &FilenameTok, 341207619Srdivacky SrcMgr::CharacteristicKind FileType) { 342207619Srdivacky First->FileSkipped(ParentFile, FilenameTok, FileType); 343207619Srdivacky Second->FileSkipped(ParentFile, FilenameTok, FileType); 344207619Srdivacky } 345207619Srdivacky 346235633Sdim virtual bool FileNotFound(StringRef FileName, 347235633Sdim SmallVectorImpl<char> &RecoveryPath) { 348235633Sdim return First->FileNotFound(FileName, RecoveryPath) || 349235633Sdim Second->FileNotFound(FileName, RecoveryPath); 350235633Sdim } 351235633Sdim 352218893Sdim virtual void InclusionDirective(SourceLocation HashLoc, 353218893Sdim const Token &IncludeTok, 354226890Sdim StringRef FileName, 355218893Sdim bool IsAngled, 356245431Sdim CharSourceRange FilenameRange, 357218893Sdim const FileEntry *File, 358226890Sdim StringRef SearchPath, 359245431Sdim StringRef RelativePath, 360245431Sdim const Module *Imported) { 361245431Sdim First->InclusionDirective(HashLoc, IncludeTok, FileName, IsAngled, 362245431Sdim FilenameRange, File, SearchPath, RelativePath, 363245431Sdim Imported); 364245431Sdim Second->InclusionDirective(HashLoc, IncludeTok, FileName, IsAngled, 365245431Sdim FilenameRange, File, SearchPath, RelativePath, 366245431Sdim Imported); 367218893Sdim } 368218893Sdim 369245431Sdim virtual void moduleImport(SourceLocation ImportLoc, 370245431Sdim ModuleIdPath Path, 371245431Sdim const Module *Imported) { 372245431Sdim First->moduleImport(ImportLoc, Path, Imported); 373245431Sdim Second->moduleImport(ImportLoc, Path, Imported); 374245431Sdim } 375245431Sdim 376206084Srdivacky virtual void EndOfMainFile() { 377206084Srdivacky First->EndOfMainFile(); 378206084Srdivacky Second->EndOfMainFile(); 379206084Srdivacky } 380206084Srdivacky 381193326Sed virtual void Ident(SourceLocation Loc, const std::string &str) { 382193326Sed First->Ident(Loc, str); 383193326Sed Second->Ident(Loc, str); 384193326Sed } 385198092Srdivacky 386198092Srdivacky virtual void PragmaComment(SourceLocation Loc, const IdentifierInfo *Kind, 387193326Sed const std::string &Str) { 388193326Sed First->PragmaComment(Loc, Kind, Str); 389193326Sed Second->PragmaComment(Loc, Kind, Str); 390193326Sed } 391198092Srdivacky 392263509Sdim virtual void PragmaDetectMismatch(SourceLocation Loc, 393263509Sdim const std::string &Name, 394263509Sdim const std::string &Value) { 395263509Sdim First->PragmaDetectMismatch(Loc, Name, Value); 396263509Sdim Second->PragmaDetectMismatch(Loc, Name, Value); 397263509Sdim } 398263509Sdim 399252723Sdim virtual void PragmaMessage(SourceLocation Loc, StringRef Namespace, 400252723Sdim PragmaMessageKind Kind, StringRef Str) { 401252723Sdim First->PragmaMessage(Loc, Namespace, Kind, Str); 402252723Sdim Second->PragmaMessage(Loc, Namespace, Kind, Str); 403210299Sed } 404210299Sed 405224145Sdim virtual void PragmaDiagnosticPush(SourceLocation Loc, 406226890Sdim StringRef Namespace) { 407224145Sdim First->PragmaDiagnosticPush(Loc, Namespace); 408224145Sdim Second->PragmaDiagnosticPush(Loc, Namespace); 409224145Sdim } 410224145Sdim 411224145Sdim virtual void PragmaDiagnosticPop(SourceLocation Loc, 412226890Sdim StringRef Namespace) { 413224145Sdim First->PragmaDiagnosticPop(Loc, Namespace); 414224145Sdim Second->PragmaDiagnosticPop(Loc, Namespace); 415224145Sdim } 416224145Sdim 417226890Sdim virtual void PragmaDiagnostic(SourceLocation Loc, StringRef Namespace, 418226890Sdim diag::Mapping mapping, StringRef Str) { 419224145Sdim First->PragmaDiagnostic(Loc, Namespace, mapping, Str); 420224145Sdim Second->PragmaDiagnostic(Loc, Namespace, mapping, Str); 421224145Sdim } 422224145Sdim 423263509Sdim virtual void PragmaOpenCLExtension(SourceLocation NameLoc, 424263509Sdim const IdentifierInfo *Name, 425263509Sdim SourceLocation StateLoc, unsigned State) { 426263509Sdim First->PragmaOpenCLExtension(NameLoc, Name, StateLoc, State); 427263509Sdim Second->PragmaOpenCLExtension(NameLoc, Name, StateLoc, State); 428263509Sdim } 429263509Sdim 430263509Sdim virtual void PragmaWarning(SourceLocation Loc, StringRef WarningSpec, 431263509Sdim ArrayRef<int> Ids) { 432263509Sdim First->PragmaWarning(Loc, WarningSpec, Ids); 433263509Sdim Second->PragmaWarning(Loc, WarningSpec, Ids); 434263509Sdim } 435263509Sdim 436263509Sdim virtual void PragmaWarningPush(SourceLocation Loc, int Level) { 437263509Sdim First->PragmaWarningPush(Loc, Level); 438263509Sdim Second->PragmaWarningPush(Loc, Level); 439263509Sdim } 440263509Sdim 441263509Sdim virtual void PragmaWarningPop(SourceLocation Loc) { 442263509Sdim First->PragmaWarningPop(Loc); 443263509Sdim Second->PragmaWarningPop(Loc); 444263509Sdim } 445263509Sdim 446252723Sdim virtual void MacroExpands(const Token &MacroNameTok, const MacroDirective *MD, 447252723Sdim SourceRange Range, const MacroArgs *Args) { 448252723Sdim First->MacroExpands(MacroNameTok, MD, Range, Args); 449252723Sdim Second->MacroExpands(MacroNameTok, MD, Range, Args); 450193326Sed } 451198092Srdivacky 452252723Sdim virtual void MacroDefined(const Token &MacroNameTok, const MacroDirective *MD) { 453252723Sdim First->MacroDefined(MacroNameTok, MD); 454252723Sdim Second->MacroDefined(MacroNameTok, MD); 455193326Sed } 456193326Sed 457252723Sdim virtual void MacroUndefined(const Token &MacroNameTok, 458252723Sdim const MacroDirective *MD) { 459252723Sdim First->MacroUndefined(MacroNameTok, MD); 460252723Sdim Second->MacroUndefined(MacroNameTok, MD); 461193326Sed } 462218893Sdim 463263509Sdim virtual void Defined(const Token &MacroNameTok, const MacroDirective *MD, 464263509Sdim SourceRange Range) { 465263509Sdim First->Defined(MacroNameTok, MD, Range); 466263509Sdim Second->Defined(MacroNameTok, MD, Range); 467226890Sdim } 468226890Sdim 469226890Sdim virtual void SourceRangeSkipped(SourceRange Range) { 470226890Sdim First->SourceRangeSkipped(Range); 471226890Sdim Second->SourceRangeSkipped(Range); 472226890Sdim } 473226890Sdim 474245431Sdim /// \brief Hook called whenever an \#if is seen. 475263509Sdim virtual void If(SourceLocation Loc, SourceRange ConditionRange, 476263509Sdim bool ConditionValue) { 477263509Sdim First->If(Loc, ConditionRange, ConditionValue); 478263509Sdim Second->If(Loc, ConditionRange, ConditionValue); 479218893Sdim } 480218893Sdim 481263509Sdim /// \brief Hook called whenever an \#elif is seen. 482235633Sdim virtual void Elif(SourceLocation Loc, SourceRange ConditionRange, 483263509Sdim bool ConditionValue, SourceLocation IfLoc) { 484263509Sdim First->Elif(Loc, ConditionRange, ConditionValue, IfLoc); 485263509Sdim Second->Elif(Loc, ConditionRange, ConditionValue, IfLoc); 486218893Sdim } 487218893Sdim 488245431Sdim /// \brief Hook called whenever an \#ifdef is seen. 489252723Sdim virtual void Ifdef(SourceLocation Loc, const Token &MacroNameTok, 490252723Sdim const MacroDirective *MD) { 491252723Sdim First->Ifdef(Loc, MacroNameTok, MD); 492252723Sdim Second->Ifdef(Loc, MacroNameTok, MD); 493218893Sdim } 494218893Sdim 495245431Sdim /// \brief Hook called whenever an \#ifndef is seen. 496252723Sdim virtual void Ifndef(SourceLocation Loc, const Token &MacroNameTok, 497252723Sdim const MacroDirective *MD) { 498252723Sdim First->Ifndef(Loc, MacroNameTok, MD); 499252723Sdim Second->Ifndef(Loc, MacroNameTok, MD); 500218893Sdim } 501218893Sdim 502245431Sdim /// \brief Hook called whenever an \#else is seen. 503235633Sdim virtual void Else(SourceLocation Loc, SourceLocation IfLoc) { 504235633Sdim First->Else(Loc, IfLoc); 505235633Sdim Second->Else(Loc, IfLoc); 506218893Sdim } 507218893Sdim 508245431Sdim /// \brief Hook called whenever an \#endif is seen. 509235633Sdim virtual void Endif(SourceLocation Loc, SourceLocation IfLoc) { 510235633Sdim First->Endif(Loc, IfLoc); 511235633Sdim Second->Endif(Loc, IfLoc); 512218893Sdim } 513193326Sed}; 514193326Sed 515193326Sed} // end namespace clang 516193326Sed 517193326Sed#endif 518