diff options
Diffstat (limited to 'clang/lib')
-rw-r--r-- | clang/lib/Basic/Diagnostic.cpp | 90 | ||||
-rw-r--r-- | clang/lib/Lex/Pragma.cpp | 14 | ||||
-rw-r--r-- | clang/lib/Serialization/ASTReader.cpp | 3 | ||||
-rw-r--r-- | clang/lib/Serialization/ASTWriter.cpp | 7 |
4 files changed, 112 insertions, 2 deletions
diff --git a/clang/lib/Basic/Diagnostic.cpp b/clang/lib/Basic/Diagnostic.cpp index 5903d72ea5e..83e61dd9470 100644 --- a/clang/lib/Basic/Diagnostic.cpp +++ b/clang/lib/Basic/Diagnostic.cpp @@ -236,6 +236,96 @@ DiagnosticsEngine::DiagStateMap::getFile(SourceManager &SrcMgr, return &F; } +void DiagnosticsEngine::DiagStateMap::dump(SourceManager &SrcMgr, + StringRef DiagName) const { + llvm::errs() << "diagnostic state at "; + CurDiagStateLoc.dump(SrcMgr); + llvm::errs() << ": " << CurDiagState << "\n"; + + for (auto &F : Files) { + FileID ID = F.first; + File &File = F.second; + + bool PrintedOuterHeading = false; + auto PrintOuterHeading = [&] { + if (PrintedOuterHeading) return; + PrintedOuterHeading = true; + + llvm::errs() << "File " << &File << " <FileID " << ID.getHashValue() + << ">: " << SrcMgr.getBuffer(ID)->getBufferIdentifier(); + if (F.second.Parent) { + std::pair<FileID, unsigned> Decomp = + SrcMgr.getDecomposedIncludedLoc(ID); + assert(File.ParentOffset == Decomp.second); + llvm::errs() << " parent " << File.Parent << " <FileID " + << Decomp.first.getHashValue() << "> "; + SrcMgr.getLocForStartOfFile(Decomp.first) + .getLocWithOffset(Decomp.second) + .dump(SrcMgr); + } + if (File.HasLocalTransitions) + llvm::errs() << " has_local_transitions"; + llvm::errs() << "\n"; + }; + + if (DiagName.empty()) + PrintOuterHeading(); + + for (DiagStatePoint &Transition : File.StateTransitions) { + bool PrintedInnerHeading = false; + auto PrintInnerHeading = [&] { + if (PrintedInnerHeading) return; + PrintedInnerHeading = true; + + PrintOuterHeading(); + llvm::errs() << " "; + SrcMgr.getLocForStartOfFile(ID) + .getLocWithOffset(Transition.Offset) + .dump(SrcMgr); + llvm::errs() << ": state " << Transition.State << ":\n"; + }; + + if (DiagName.empty()) + PrintInnerHeading(); + + for (auto &Mapping : *Transition.State) { + StringRef Option = + DiagnosticIDs::getWarningOptionForDiag(Mapping.first); + if (!DiagName.empty() && DiagName != Option) + continue; + + PrintInnerHeading(); + llvm::errs() << " "; + if (Option.empty()) + llvm::errs() << "<unknown " << Mapping.first << ">"; + else + llvm::errs() << Option; + llvm::errs() << ": "; + + switch (Mapping.second.getSeverity()) { + case diag::Severity::Ignored: llvm::errs() << "ignored"; break; + case diag::Severity::Remark: llvm::errs() << "remark"; break; + case diag::Severity::Warning: llvm::errs() << "warning"; break; + case diag::Severity::Error: llvm::errs() << "error"; break; + case diag::Severity::Fatal: llvm::errs() << "fatal"; break; + } + + if (!Mapping.second.isUser()) + llvm::errs() << " default"; + if (Mapping.second.isPragma()) + llvm::errs() << " pragma"; + if (Mapping.second.hasNoWarningAsError()) + llvm::errs() << " no-error"; + if (Mapping.second.hasNoErrorAsFatal()) + llvm::errs() << " no-fatal"; + if (Mapping.second.wasUpgradedFromWarning()) + llvm::errs() << " overruled"; + llvm::errs() << "\n"; + } + } + } +} + void DiagnosticsEngine::PushDiagStatePoint(DiagState *State, SourceLocation Loc) { assert(Loc.isValid() && "Adding invalid loc point"); diff --git a/clang/lib/Lex/Pragma.cpp b/clang/lib/Lex/Pragma.cpp index b9be03f4f20..db32e452d07 100644 --- a/clang/lib/Lex/Pragma.cpp +++ b/clang/lib/Lex/Pragma.cpp @@ -1053,6 +1053,20 @@ struct PragmaDebugHandler : public PragmaHandler { PP.Diag(Identifier, diag::warn_pragma_debug_missing_argument) << II->getName(); } + } else if (II->isStr("diag_mapping")) { + Token DiagName; + PP.LexUnexpandedToken(DiagName); + if (DiagName.is(tok::eod)) + PP.getDiagnostics().dump(); + else if (DiagName.is(tok::string_literal) && !DiagName.hasUDSuffix()) { + StringLiteralParser Literal(DiagName, PP); + if (Literal.hadError) + return; + PP.getDiagnostics().dump(Literal.GetString()); + } else { + PP.Diag(DiagName, diag::warn_pragma_debug_missing_argument) + << II->getName(); + } } else if (II->isStr("llvm_fatal_error")) { llvm::report_fatal_error("#pragma clang __debug llvm_fatal_error"); } else if (II->isStr("llvm_unreachable")) { diff --git a/clang/lib/Serialization/ASTReader.cpp b/clang/lib/Serialization/ASTReader.cpp index b62c47c67f3..979ff0c2c62 100644 --- a/clang/lib/Serialization/ASTReader.cpp +++ b/clang/lib/Serialization/ASTReader.cpp @@ -5761,6 +5761,8 @@ void ASTReader::ReadPragmaDiagnosticMappings(DiagnosticsEngine &Diag) { Initial.ExtBehavior = (diag::Severity)Flags; FirstState = ReadDiagState(Initial, SourceLocation(), true); + assert(F.OriginalSourceFileID.isValid()); + // Set up the root buffer of the module to start with the initial // diagnostic state of the module itself, to cover files that contain no // explicit transitions (for which we did not serialize anything). @@ -5781,6 +5783,7 @@ void ASTReader::ReadPragmaDiagnosticMappings(DiagnosticsEngine &Diag) { "Invalid data, missing pragma diagnostic states"); SourceLocation Loc = ReadSourceLocation(F, Record[Idx++]); auto IDAndOffset = SourceMgr.getDecomposedLoc(Loc); + assert(IDAndOffset.first.isValid() && "invalid FileID for transition"); assert(IDAndOffset.second == 0 && "not a start location for a FileID"); unsigned Transitions = Record[Idx++]; diff --git a/clang/lib/Serialization/ASTWriter.cpp b/clang/lib/Serialization/ASTWriter.cpp index 50c60fe64c2..8c5863e28ae 100644 --- a/clang/lib/Serialization/ASTWriter.cpp +++ b/clang/lib/Serialization/ASTWriter.cpp @@ -3092,8 +3092,11 @@ void ASTWriter::WritePragmaDiagnosticMappings(const DiagnosticsEngine &Diag, !FileIDAndFile.second.HasLocalTransitions) continue; ++NumLocations; - AddSourceLocation(Diag.SourceMgr->getLocForStartOfFile(FileIDAndFile.first), - Record); + + SourceLocation Loc = Diag.SourceMgr->getComposedLoc(FileIDAndFile.first, 0); + assert(!Loc.isInvalid() && "start loc for valid FileID is invalid"); + AddSourceLocation(Loc, Record); + Record.push_back(FileIDAndFile.second.StateTransitions.size()); for (auto &StatePoint : FileIDAndFile.second.StateTransitions) { Record.push_back(StatePoint.Offset); |