1 //===--- PreprocessingRecord.h - Record of Preprocessing --------*- 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 PreprocessingRecord class, which maintains a record 11 // of what occurred during preprocessing. 12 // 13 //===----------------------------------------------------------------------===// 14 #ifndef LLVM_CLANG_LEX_PREPROCESSINGRECORD_H 15 #define LLVM_CLANG_LEX_PREPROCESSINGRECORD_H 16 17 #include "clang/Basic/IdentifierTable.h" 18 #include "clang/Basic/SourceLocation.h" 19 #include "clang/Lex/PPCallbacks.h" 20 #include "llvm/ADT/DenseMap.h" 21 #include "llvm/ADT/Optional.h" 22 #include "llvm/ADT/SmallVector.h" 23 #include "llvm/ADT/iterator.h" 24 #include "llvm/Support/Allocator.h" 25 #include "llvm/Support/Compiler.h" 26 #include <vector> 27 28 namespace clang { 29 class IdentifierInfo; 30 class MacroInfo; 31 class PreprocessingRecord; 32 } 33 34 /// \brief Allocates memory within a Clang preprocessing record. 35 void* operator new(size_t bytes, clang::PreprocessingRecord& PR, 36 unsigned alignment = 8) throw(); 37 38 /// \brief Frees memory allocated in a Clang preprocessing record. 39 void operator delete(void* ptr, clang::PreprocessingRecord& PR, 40 unsigned) throw(); 41 42 namespace clang { 43 class MacroDefinition; 44 class FileEntry; 45 46 /// \brief Base class that describes a preprocessed entity, which may be a 47 /// preprocessor directive or macro expansion. 48 class PreprocessedEntity { 49 public: 50 /// \brief The kind of preprocessed entity an object describes. 51 enum EntityKind { 52 /// \brief Indicates a problem trying to load the preprocessed entity. 53 InvalidKind, 54 55 /// \brief A macro expansion. 56 MacroExpansionKind, 57 58 /// \defgroup Preprocessing directives 59 /// @{ 60 61 /// \brief A macro definition. 62 MacroDefinitionKind, 63 64 /// \brief An inclusion directive, such as \c \#include, \c 65 /// \#import, or \c \#include_next. 66 InclusionDirectiveKind, 67 68 /// @} 69 70 FirstPreprocessingDirective = MacroDefinitionKind, 71 LastPreprocessingDirective = InclusionDirectiveKind 72 }; 73 74 private: 75 /// \brief The kind of preprocessed entity that this object describes. 76 EntityKind Kind; 77 78 /// \brief The source range that covers this preprocessed entity. 79 SourceRange Range; 80 81 protected: 82 PreprocessedEntity(EntityKind Kind, SourceRange Range) 83 : Kind(Kind), Range(Range) { } 84 85 friend class PreprocessingRecord; 86 87 public: 88 /// \brief Retrieve the kind of preprocessed entity stored in this object. 89 EntityKind getKind() const { return Kind; } 90 91 /// \brief Retrieve the source range that covers this entire preprocessed 92 /// entity. 93 SourceRange getSourceRange() const LLVM_READONLY { return Range; } 94 95 /// \brief Returns true if there was a problem loading the preprocessed 96 /// entity. 97 bool isInvalid() const { return Kind == InvalidKind; } 98 99 // Only allow allocation of preprocessed entities using the allocator 100 // in PreprocessingRecord or by doing a placement new. 101 void* operator new(size_t bytes, PreprocessingRecord& PR, 102 unsigned alignment = 8) throw() { 103 return ::operator new(bytes, PR, alignment); 104 } 105 106 void* operator new(size_t bytes, void* mem) throw() { 107 return mem; 108 } 109 110 void operator delete(void* ptr, PreprocessingRecord& PR, 111 unsigned alignment) throw() { 112 return ::operator delete(ptr, PR, alignment); 113 } 114 115 void operator delete(void*, std::size_t) throw() { } 116 void operator delete(void*, void*) throw() { } 117 118 private: 119 // Make vanilla 'new' and 'delete' illegal for preprocessed entities. 120 void* operator new(size_t bytes) throw(); 121 void operator delete(void* data) throw(); 122 }; 123 124 /// \brief Records the presence of a preprocessor directive. 125 class PreprocessingDirective : public PreprocessedEntity { 126 public: 127 PreprocessingDirective(EntityKind Kind, SourceRange Range) 128 : PreprocessedEntity(Kind, Range) { } 129 130 // Implement isa/cast/dyncast/etc. 131 static bool classof(const PreprocessedEntity *PD) { 132 return PD->getKind() >= FirstPreprocessingDirective && 133 PD->getKind() <= LastPreprocessingDirective; 134 } 135 }; 136 137 /// \brief Record the location of a macro definition. 138 class MacroDefinition : public PreprocessingDirective { 139 /// \brief The name of the macro being defined. 140 const IdentifierInfo *Name; 141 142 public: 143 explicit MacroDefinition(const IdentifierInfo *Name, SourceRange Range) 144 : PreprocessingDirective(MacroDefinitionKind, Range), Name(Name) { } 145 146 /// \brief Retrieve the name of the macro being defined. 147 const IdentifierInfo *getName() const { return Name; } 148 149 /// \brief Retrieve the location of the macro name in the definition. 150 SourceLocation getLocation() const { return getSourceRange().getBegin(); } 151 152 // Implement isa/cast/dyncast/etc. 153 static bool classof(const PreprocessedEntity *PE) { 154 return PE->getKind() == MacroDefinitionKind; 155 } 156 }; 157 158 /// \brief Records the location of a macro expansion. 159 class MacroExpansion : public PreprocessedEntity { 160 /// \brief The definition of this macro or the name of the macro if it is 161 /// a builtin macro. 162 llvm::PointerUnion<IdentifierInfo *, MacroDefinition *> NameOrDef; 163 164 public: 165 MacroExpansion(IdentifierInfo *BuiltinName, SourceRange Range) 166 : PreprocessedEntity(MacroExpansionKind, Range), 167 NameOrDef(BuiltinName) { } 168 169 MacroExpansion(MacroDefinition *Definition, SourceRange Range) 170 : PreprocessedEntity(MacroExpansionKind, Range), 171 NameOrDef(Definition) { } 172 173 /// \brief True if it is a builtin macro. 174 bool isBuiltinMacro() const { return NameOrDef.is<IdentifierInfo *>(); } 175 176 /// \brief The name of the macro being expanded. 177 const IdentifierInfo *getName() const { 178 if (MacroDefinition *Def = getDefinition()) 179 return Def->getName(); 180 return NameOrDef.get<IdentifierInfo*>(); 181 } 182 183 /// \brief The definition of the macro being expanded. May return null if 184 /// this is a builtin macro. 185 MacroDefinition *getDefinition() const { 186 return NameOrDef.dyn_cast<MacroDefinition *>(); 187 } 188 189 // Implement isa/cast/dyncast/etc. 190 static bool classof(const PreprocessedEntity *PE) { 191 return PE->getKind() == MacroExpansionKind; 192 } 193 }; 194 195 /// \brief Record the location of an inclusion directive, such as an 196 /// \c \#include or \c \#import statement. 197 class InclusionDirective : public PreprocessingDirective { 198 public: 199 /// \brief The kind of inclusion directives known to the 200 /// preprocessor. 201 enum InclusionKind { 202 /// \brief An \c \#include directive. 203 Include, 204 /// \brief An Objective-C \c \#import directive. 205 Import, 206 /// \brief A GNU \c \#include_next directive. 207 IncludeNext, 208 /// \brief A Clang \c \#__include_macros directive. 209 IncludeMacros 210 }; 211 212 private: 213 /// \brief The name of the file that was included, as written in 214 /// the source. 215 StringRef FileName; 216 217 /// \brief Whether the file name was in quotation marks; otherwise, it was 218 /// in angle brackets. 219 unsigned InQuotes : 1; 220 221 /// \brief The kind of inclusion directive we have. 222 /// 223 /// This is a value of type InclusionKind. 224 unsigned Kind : 2; 225 226 /// \brief Whether the inclusion directive was automatically turned into 227 /// a module import. 228 unsigned ImportedModule : 1; 229 230 /// \brief The file that was included. 231 const FileEntry *File; 232 233 public: 234 InclusionDirective(PreprocessingRecord &PPRec, 235 InclusionKind Kind, StringRef FileName, 236 bool InQuotes, bool ImportedModule, 237 const FileEntry *File, SourceRange Range); 238 239 /// \brief Determine what kind of inclusion directive this is. 240 InclusionKind getKind() const { return static_cast<InclusionKind>(Kind); } 241 242 /// \brief Retrieve the included file name as it was written in the source. 243 StringRef getFileName() const { return FileName; } 244 245 /// \brief Determine whether the included file name was written in quotes; 246 /// otherwise, it was written in angle brackets. 247 bool wasInQuotes() const { return InQuotes; } 248 249 /// \brief Determine whether the inclusion directive was automatically 250 /// turned into a module import. 251 bool importedModule() const { return ImportedModule; } 252 253 /// \brief Retrieve the file entry for the actual file that was included 254 /// by this directive. 255 const FileEntry *getFile() const { return File; } 256 257 // Implement isa/cast/dyncast/etc. 258 static bool classof(const PreprocessedEntity *PE) { 259 return PE->getKind() == InclusionDirectiveKind; 260 } 261 }; 262 263 /// \brief An abstract class that should be subclassed by any external source 264 /// of preprocessing record entries. 265 class ExternalPreprocessingRecordSource { 266 public: 267 virtual ~ExternalPreprocessingRecordSource(); 268 269 /// \brief Read a preallocated preprocessed entity from the external source. 270 /// 271 /// \returns null if an error occurred that prevented the preprocessed 272 /// entity from being loaded. 273 virtual PreprocessedEntity *ReadPreprocessedEntity(unsigned Index) = 0; 274 275 /// \brief Returns a pair of [Begin, End) indices of preallocated 276 /// preprocessed entities that \p Range encompasses. 277 virtual std::pair<unsigned, unsigned> 278 findPreprocessedEntitiesInRange(SourceRange Range) = 0; 279 280 /// \brief Optionally returns true or false if the preallocated preprocessed 281 /// entity with index \p Index came from file \p FID. 282 virtual Optional<bool> isPreprocessedEntityInFileID(unsigned Index, 283 FileID FID) { 284 return None; 285 } 286 }; 287 288 /// \brief A record of the steps taken while preprocessing a source file, 289 /// including the various preprocessing directives processed, macros 290 /// expanded, etc. 291 class PreprocessingRecord : public PPCallbacks { 292 SourceManager &SourceMgr; 293 294 /// \brief Allocator used to store preprocessing objects. 295 llvm::BumpPtrAllocator BumpAlloc; 296 297 /// \brief The set of preprocessed entities in this record, in order they 298 /// were seen. 299 std::vector<PreprocessedEntity *> PreprocessedEntities; 300 301 /// \brief The set of preprocessed entities in this record that have been 302 /// loaded from external sources. 303 /// 304 /// The entries in this vector are loaded lazily from the external source, 305 /// and are referenced by the iterator using negative indices. 306 std::vector<PreprocessedEntity *> LoadedPreprocessedEntities; 307 308 /// \brief The set of ranges that were skipped by the preprocessor, 309 std::vector<SourceRange> SkippedRanges; 310 311 /// \brief Global (loaded or local) ID for a preprocessed entity. 312 /// Negative values are used to indicate preprocessed entities 313 /// loaded from the external source while non-negative values are used to 314 /// indicate preprocessed entities introduced by the current preprocessor. 315 /// Value -1 corresponds to element 0 in the loaded entities vector, 316 /// value -2 corresponds to element 1 in the loaded entities vector, etc. 317 /// Value 0 is an invalid value, the index to local entities is 1-based, 318 /// value 1 corresponds to element 0 in the local entities vector, 319 /// value 2 corresponds to element 1 in the local entities vector, etc. 320 class PPEntityID { 321 int ID; 322 explicit PPEntityID(int ID) : ID(ID) {} 323 friend class PreprocessingRecord; 324 public: 325 PPEntityID() : ID(0) {} 326 }; 327 328 static PPEntityID getPPEntityID(unsigned Index, bool isLoaded) { 329 return isLoaded ? PPEntityID(-int(Index)-1) : PPEntityID(Index+1); 330 } 331 332 /// \brief Mapping from MacroInfo structures to their definitions. 333 llvm::DenseMap<const MacroInfo *, MacroDefinition *> MacroDefinitions; 334 335 /// \brief External source of preprocessed entities. 336 ExternalPreprocessingRecordSource *ExternalSource; 337 338 /// \brief Retrieve the preprocessed entity at the given ID. 339 PreprocessedEntity *getPreprocessedEntity(PPEntityID PPID); 340 341 /// \brief Retrieve the loaded preprocessed entity at the given index. 342 PreprocessedEntity *getLoadedPreprocessedEntity(unsigned Index); 343 344 /// \brief Determine the number of preprocessed entities that were 345 /// loaded (or can be loaded) from an external source. 346 unsigned getNumLoadedPreprocessedEntities() const { 347 return LoadedPreprocessedEntities.size(); 348 } 349 350 /// \brief Returns a pair of [Begin, End) indices of local preprocessed 351 /// entities that \p Range encompasses. 352 std::pair<unsigned, unsigned> 353 findLocalPreprocessedEntitiesInRange(SourceRange Range) const; 354 unsigned findBeginLocalPreprocessedEntity(SourceLocation Loc) const; 355 unsigned findEndLocalPreprocessedEntity(SourceLocation Loc) const; 356 357 /// \brief Allocate space for a new set of loaded preprocessed entities. 358 /// 359 /// \returns The index into the set of loaded preprocessed entities, which 360 /// corresponds to the first newly-allocated entity. 361 unsigned allocateLoadedEntities(unsigned NumEntities); 362 363 /// \brief Register a new macro definition. 364 void RegisterMacroDefinition(MacroInfo *Macro, MacroDefinition *Def); 365 366 public: 367 /// \brief Construct a new preprocessing record. 368 explicit PreprocessingRecord(SourceManager &SM); 369 370 /// \brief Allocate memory in the preprocessing record. 371 void *Allocate(unsigned Size, unsigned Align = 8) { 372 return BumpAlloc.Allocate(Size, Align); 373 } 374 375 /// \brief Deallocate memory in the preprocessing record. 376 void Deallocate(void *Ptr) { } 377 378 size_t getTotalMemory() const; 379 380 SourceManager &getSourceManager() const { return SourceMgr; } 381 382 /// Iteration over the preprocessed entities. 383 /// 384 /// In a complete iteration, the iterator walks the range [-M, N), 385 /// where negative values are used to indicate preprocessed entities 386 /// loaded from the external source while non-negative values are used to 387 /// indicate preprocessed entities introduced by the current preprocessor. 388 /// However, to provide iteration in source order (for, e.g., chained 389 /// precompiled headers), dereferencing the iterator flips the negative 390 /// values (corresponding to loaded entities), so that position -M 391 /// corresponds to element 0 in the loaded entities vector, position -M+1 392 /// corresponds to element 1 in the loaded entities vector, etc. This 393 /// gives us a reasonably efficient, source-order walk. 394 /// 395 /// We define this as a wrapping iterator around an int. The 396 /// iterator_adaptor_base class forwards the iterator methods to basic 397 /// integer arithmetic. 398 class iterator : public llvm::iterator_adaptor_base< 399 iterator, int, std::random_access_iterator_tag, 400 PreprocessedEntity *, int, PreprocessedEntity *, 401 PreprocessedEntity *> { 402 PreprocessingRecord *Self; 403 404 iterator(PreprocessingRecord *Self, int Position) 405 : iterator::iterator_adaptor_base(Position), Self(Self) {} 406 friend class PreprocessingRecord; 407 408 public: 409 iterator() : iterator(nullptr, 0) {} 410 411 PreprocessedEntity *operator*() const { 412 bool isLoaded = this->I < 0; 413 unsigned Index = isLoaded ? 414 Self->LoadedPreprocessedEntities.size() + this->I : this->I; 415 PPEntityID ID = Self->getPPEntityID(Index, isLoaded); 416 return Self->getPreprocessedEntity(ID); 417 } 418 PreprocessedEntity *operator->() const { return **this; } 419 }; 420 421 /// \brief Begin iterator for all preprocessed entities. 422 iterator begin() { 423 return iterator(this, -(int)LoadedPreprocessedEntities.size()); 424 } 425 426 /// \brief End iterator for all preprocessed entities. 427 iterator end() { 428 return iterator(this, PreprocessedEntities.size()); 429 } 430 431 /// \brief Begin iterator for local, non-loaded, preprocessed entities. 432 iterator local_begin() { 433 return iterator(this, 0); 434 } 435 436 /// \brief End iterator for local, non-loaded, preprocessed entities. 437 iterator local_end() { 438 return iterator(this, PreprocessedEntities.size()); 439 } 440 441 /// \brief iterator range for the given range of loaded 442 /// preprocessed entities. 443 llvm::iterator_range<iterator> getIteratorsForLoadedRange(unsigned start, 444 unsigned count) { 445 unsigned end = start + count; 446 assert(end <= LoadedPreprocessedEntities.size()); 447 return llvm::make_range( 448 iterator(this, int(start) - LoadedPreprocessedEntities.size()), 449 iterator(this, int(end) - LoadedPreprocessedEntities.size())); 450 } 451 452 /// \brief Returns a range of preprocessed entities that source range \p R 453 /// encompasses. 454 /// 455 /// \param R the range to look for preprocessed entities. 456 /// 457 llvm::iterator_range<iterator> 458 getPreprocessedEntitiesInRange(SourceRange R); 459 460 /// \brief Returns true if the preprocessed entity that \p PPEI iterator 461 /// points to is coming from the file \p FID. 462 /// 463 /// Can be used to avoid implicit deserializations of preallocated 464 /// preprocessed entities if we only care about entities of a specific file 465 /// and not from files \#included in the range given at 466 /// \see getPreprocessedEntitiesInRange. 467 bool isEntityInFileID(iterator PPEI, FileID FID); 468 469 /// \brief Add a new preprocessed entity to this record. 470 PPEntityID addPreprocessedEntity(PreprocessedEntity *Entity); 471 472 /// \brief Set the external source for preprocessed entities. 473 void SetExternalSource(ExternalPreprocessingRecordSource &Source); 474 475 /// \brief Retrieve the external source for preprocessed entities. 476 ExternalPreprocessingRecordSource *getExternalSource() const { 477 return ExternalSource; 478 } 479 480 /// \brief Retrieve the macro definition that corresponds to the given 481 /// \c MacroInfo. 482 MacroDefinition *findMacroDefinition(const MacroInfo *MI); 483 484 /// \brief Retrieve all ranges that got skipped while preprocessing. 485 const std::vector<SourceRange> &getSkippedRanges() const { 486 return SkippedRanges; 487 } 488 489 private: 490 void MacroExpands(const Token &Id, const MacroDirective *MD, 491 SourceRange Range, const MacroArgs *Args) override; 492 void MacroDefined(const Token &Id, const MacroDirective *MD) override; 493 void MacroUndefined(const Token &Id, const MacroDirective *MD) override; 494 void InclusionDirective(SourceLocation HashLoc, const Token &IncludeTok, 495 StringRef FileName, bool IsAngled, 496 CharSourceRange FilenameRange, 497 const FileEntry *File, StringRef SearchPath, 498 StringRef RelativePath, 499 const Module *Imported) override; 500 void Ifdef(SourceLocation Loc, const Token &MacroNameTok, 501 const MacroDirective *MD) override; 502 void Ifndef(SourceLocation Loc, const Token &MacroNameTok, 503 const MacroDirective *MD) override; 504 /// \brief Hook called whenever the 'defined' operator is seen. 505 void Defined(const Token &MacroNameTok, const MacroDirective *MD, 506 SourceRange Range) override; 507 508 void SourceRangeSkipped(SourceRange Range) override; 509 510 void addMacroExpansion(const Token &Id, const MacroInfo *MI, 511 SourceRange Range); 512 513 /// \brief Cached result of the last \see getPreprocessedEntitiesInRange 514 /// query. 515 struct { 516 SourceRange Range; 517 std::pair<int, int> Result; 518 } CachedRangeQuery; 519 520 std::pair<int, int> getPreprocessedEntitiesInRangeSlow(SourceRange R); 521 522 friend class ASTReader; 523 friend class ASTWriter; 524 }; 525 } // end namespace clang 526 527 inline void* operator new(size_t bytes, clang::PreprocessingRecord& PR, 528 unsigned alignment) throw() { 529 return PR.Allocate(bytes, alignment); 530 } 531 532 inline void operator delete(void* ptr, clang::PreprocessingRecord& PR, 533 unsigned) throw() { 534 PR.Deallocate(ptr); 535 } 536 537 #endif // LLVM_CLANG_LEX_PREPROCESSINGRECORD_H 538