diff options
author | Richard Smith <richard-llvm@metafoo.co.uk> | 2018-02-09 01:15:13 +0000 |
---|---|---|
committer | Richard Smith <richard-llvm@metafoo.co.uk> | 2018-02-09 01:15:13 +0000 |
commit | 945b03408215598c12dbddaa1e826cc796acf3f7 (patch) | |
tree | 899ce9241b3043deefdf2d4e9a7203f33e989090 /include | |
parent | 37031df06d0b18c853128a87d7648c625ca3a6e9 (diff) |
[modules] Fix incorrect diagnostic mapping computation when a module changes
diagnostic settings using _Pragma within a macro.
The AST writer had previously been assuming that all diagnostic state
transitions would occur within a FileID corresponding to a file. When a
diagnostic state change occured within a macro, it was unable to form a
location for that state change and would instead corrupt the diagnostic state
of the "root" node (and thus that of the main compilation).
Also introduce a "#pragma clang __debug diag_mapping" debugging utility
that I added to track this issue down.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@324695 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'include')
-rw-r--r-- | include/clang/Basic/Diagnostic.h | 9 | ||||
-rw-r--r-- | include/clang/Basic/SourceManager.h | 12 |
2 files changed, 21 insertions, 0 deletions
diff --git a/include/clang/Basic/Diagnostic.h b/include/clang/Basic/Diagnostic.h index d87d25f254..a40a78d841 100644 --- a/include/clang/Basic/Diagnostic.h +++ b/include/clang/Basic/Diagnostic.h @@ -262,6 +262,10 @@ private: CurDiagStateLoc = SourceLocation(); } + /// Produce a debugging dump of the diagnostic state. + LLVM_DUMP_METHOD void dump(SourceManager &SrcMgr, + StringRef DiagName = StringRef()) const; + /// Grab the most-recently-added state point. DiagState *getCurDiagState() const { return CurDiagState; } /// Get the location at which a diagnostic state was last added. @@ -409,6 +413,11 @@ public: DiagnosticsEngine &operator=(const DiagnosticsEngine &) = delete; ~DiagnosticsEngine(); + LLVM_DUMP_METHOD void dump() const { DiagStatesByLoc.dump(*SourceMgr); } + LLVM_DUMP_METHOD void dump(StringRef DiagName) const { + DiagStatesByLoc.dump(*SourceMgr, DiagName); + } + const IntrusiveRefCntPtr<DiagnosticIDs> &getDiagnosticIDs() const { return Diags; } diff --git a/include/clang/Basic/SourceManager.h b/include/clang/Basic/SourceManager.h index 397ad2e77f..fe5aedaf20 100644 --- a/include/clang/Basic/SourceManager.h +++ b/include/clang/Basic/SourceManager.h @@ -1137,6 +1137,18 @@ public: /// be used by clients. SourceLocation getImmediateSpellingLoc(SourceLocation Loc) const; + /// \brief Form a SourceLocation from a FileID and Offset pair. + SourceLocation getComposedLoc(FileID FID, unsigned Offset) const { + bool Invalid = false; + const SrcMgr::SLocEntry &Entry = getSLocEntry(FID, &Invalid); + if (Invalid) + return SourceLocation(); + + unsigned GlobalOffset = Entry.getOffset() + Offset; + return Entry.isFile() ? SourceLocation::getFileLoc(GlobalOffset) + : SourceLocation::getMacroLoc(GlobalOffset); + } + /// \brief Decompose the specified location into a raw FileID + Offset pair. /// /// The first element is the FileID, the second is the offset from the |