DiagnosticIDs.cpp revision ef8225444452a1486bd721f3285301fe84643b00
133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis//===--- DiagnosticIDs.cpp - Diagnostic IDs Handling ----------------------===// 233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// 333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// The LLVM Compiler Infrastructure 433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// 533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// This file is distributed under the University of Illinois Open Source 633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// License. See LICENSE.TXT for details. 733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// 833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis//===----------------------------------------------------------------------===// 933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// 1033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// This file implements the Diagnostic IDs-related interfaces. 1133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// 1233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis//===----------------------------------------------------------------------===// 1333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 1433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/DiagnosticIDs.h" 156c44886ed05d7804bfd7b80857b81fd3477079f6David Blaikie#include "clang/Basic/AllDiagnostics.h" 16923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall#include "clang/Basic/DiagnosticCategories.h" 1733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/SourceManager.h" 18cfaa5525b8eea6c5f7767010e04e323f76bed1abDavid Majnemer#include "llvm/ADT/STLExtras.h" 19651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines#include "llvm/ADT/SmallVector.h" 209fe8c74a93ac8e92512615c5f83e7a328b3b0544David Blaikie#include "llvm/Support/ErrorHandling.h" 2133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include <map> 2233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisusing namespace clang; 2333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 2433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis//===----------------------------------------------------------------------===// 2533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// Builtin Diagnostic information 2633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis//===----------------------------------------------------------------------===// 2733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 2833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisnamespace { 2933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 3033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// Diagnostic classes. 3133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisenum { 3233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis CLASS_NOTE = 0x01, 33651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines CLASS_REMARK = 0x02, 34651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines CLASS_WARNING = 0x03, 35651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines CLASS_EXTENSION = 0x04, 36651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines CLASS_ERROR = 0x05 3733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis}; 3833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 3933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisstruct StaticDiagInfoRec { 408bfffa51d773d2411cf7b8ac513ef1f50e1a4773Craig Topper uint16_t DiagID; 41ef8225444452a1486bd721f3285301fe84643b00Stephen Hines unsigned DefaultSeverity : 3; 4233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis unsigned Class : 3; 433347b497157d36cf280d1d9f52956faa6e702f34Richard Smith unsigned SFINAE : 2; 444213df3b5da21ce25a4541ca5c447eeb28b515a3Daniel Dunbar unsigned WarnNoWerror : 1; 454213df3b5da21ce25a4541ca5c447eeb28b515a3Daniel Dunbar unsigned WarnShowInSystemHeader : 1; 4633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis unsigned Category : 5; 4733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 48d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin Kramer uint16_t OptionGroupIndex; 49477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis 50477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis uint16_t DescriptionLen; 51477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis const char *DescriptionStr; 52477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis 53d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin Kramer unsigned getOptionGroupIndex() const { 54d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin Kramer return OptionGroupIndex; 55477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis } 56477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis 575f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner StringRef getDescription() const { 585f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner return StringRef(DescriptionStr, DescriptionLen); 59477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis } 607d2b8c1fcc2b707be78b09930a7767477822462fDouglas Gregor 6133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis bool operator<(const StaticDiagInfoRec &RHS) const { 6233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return DiagID < RHS.DiagID; 6333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 6433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis}; 6533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 66477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis} // namespace anonymous 67477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis 6833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisstatic const StaticDiagInfoRec StaticDiagInfo[] = { 69ef8225444452a1486bd721f3285301fe84643b00Stephen Hines#define DIAG(ENUM, CLASS, DEFAULT_SEVERITY, DESC, GROUP, SFINAE, NOWERROR, \ 70ef8225444452a1486bd721f3285301fe84643b00Stephen Hines SHOWINSYSHEADER, CATEGORY) \ 71ef8225444452a1486bd721f3285301fe84643b00Stephen Hines { \ 72ef8225444452a1486bd721f3285301fe84643b00Stephen Hines diag::ENUM, DEFAULT_SEVERITY, CLASS, DiagnosticIDs::SFINAE, NOWERROR, \ 73ef8225444452a1486bd721f3285301fe84643b00Stephen Hines SHOWINSYSHEADER, CATEGORY, GROUP, STR_SIZE(DESC, uint16_t), DESC \ 74ef8225444452a1486bd721f3285301fe84643b00Stephen Hines } \ 75ef8225444452a1486bd721f3285301fe84643b00Stephen Hines , 7633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/DiagnosticCommonKinds.inc" 7733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/DiagnosticDriverKinds.inc" 7833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/DiagnosticFrontendKinds.inc" 79a2398d7da920b896001f385587e7f7d3366e5b17Chandler Carruth#include "clang/Basic/DiagnosticSerializationKinds.inc" 8033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/DiagnosticLexKinds.inc" 8133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/DiagnosticParseKinds.inc" 8233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/DiagnosticASTKinds.inc" 83a5ef44ff5d93a3be6ca67782828157a71894cf0cDmitri Gribenko#include "clang/Basic/DiagnosticCommentKinds.inc" 8433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/DiagnosticSemaKinds.inc" 8533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/DiagnosticAnalysisKinds.inc" 8633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#undef DIAG 877d2b8c1fcc2b707be78b09930a7767477822462fDouglas Gregor}; 887d2b8c1fcc2b707be78b09930a7767477822462fDouglas Gregor 89cfaa5525b8eea6c5f7767010e04e323f76bed1abDavid Majnemerstatic const unsigned StaticDiagInfoSize = llvm::array_lengthof(StaticDiagInfo); 907d2b8c1fcc2b707be78b09930a7767477822462fDouglas Gregor 9133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// GetDiagInfo - Return the StaticDiagInfoRec entry for the specified DiagID, 9233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// or null if the ID is invalid. 9333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisstatic const StaticDiagInfoRec *GetDiagInfo(unsigned DiagID) { 9433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // If assertions are enabled, verify that the StaticDiagInfo array is sorted. 9533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#ifndef NDEBUG 96cbfb8d7ca40975acfa3382f5f62c40965fe316c4Craig Topper static bool IsFirst = true; // So the check is only performed on first call. 97cbfb8d7ca40975acfa3382f5f62c40965fe316c4Craig Topper if (IsFirst) { 98cbfb8d7ca40975acfa3382f5f62c40965fe316c4Craig Topper for (unsigned i = 1; i != StaticDiagInfoSize; ++i) { 99cbfb8d7ca40975acfa3382f5f62c40965fe316c4Craig Topper assert(StaticDiagInfo[i-1].DiagID != StaticDiagInfo[i].DiagID && 100cbfb8d7ca40975acfa3382f5f62c40965fe316c4Craig Topper "Diag ID conflict, the enums at the start of clang::diag (in " 101cbfb8d7ca40975acfa3382f5f62c40965fe316c4Craig Topper "DiagnosticIDs.h) probably need to be increased"); 102cbfb8d7ca40975acfa3382f5f62c40965fe316c4Craig Topper 103cbfb8d7ca40975acfa3382f5f62c40965fe316c4Craig Topper assert(StaticDiagInfo[i-1] < StaticDiagInfo[i] && 104cbfb8d7ca40975acfa3382f5f62c40965fe316c4Craig Topper "Improperly sorted diag info"); 105cbfb8d7ca40975acfa3382f5f62c40965fe316c4Craig Topper } 106cbfb8d7ca40975acfa3382f5f62c40965fe316c4Craig Topper IsFirst = false; 10733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 10833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#endif 10933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 110a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // Out of bounds diag. Can't be in the table. 111a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer using namespace diag; 112cfaa5525b8eea6c5f7767010e04e323f76bed1abDavid Majnemer if (DiagID >= DIAG_UPPER_LIMIT || DiagID <= DIAG_START_COMMON) 1136bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen Hines return nullptr; 11433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 115a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // Compute the index of the requested diagnostic in the static table. 116651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines // 1. Add the number of diagnostics in each category preceding the 117a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // diagnostic and of the category the diagnostic is in. This gives us 118a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // the offset of the category in the table. 119a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // 2. Subtract the number of IDs in each category from our ID. This gives us 120a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // the offset of the diagnostic in the category. 121a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // This is cheaper than a binary search on the table as it doesn't touch 122a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // memory at all. 123a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer unsigned Offset = 0; 124cfaa5525b8eea6c5f7767010e04e323f76bed1abDavid Majnemer unsigned ID = DiagID - DIAG_START_COMMON - 1; 125a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer#define CATEGORY(NAME, PREV) \ 126a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer if (DiagID > DIAG_START_##NAME) { \ 12735abfcd3285ad82fa269b8f2468dee01a4dceb52Argyrios Kyrtzidis Offset += NUM_BUILTIN_##PREV##_DIAGNOSTICS - DIAG_START_##PREV - 1; \ 12835abfcd3285ad82fa269b8f2468dee01a4dceb52Argyrios Kyrtzidis ID -= DIAG_START_##NAME - DIAG_START_##PREV; \ 129a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer } 130a07b59e5e9b55033239c80552094421a01b75c8aBenjamin KramerCATEGORY(DRIVER, COMMON) 131a07b59e5e9b55033239c80552094421a01b75c8aBenjamin KramerCATEGORY(FRONTEND, DRIVER) 132a07b59e5e9b55033239c80552094421a01b75c8aBenjamin KramerCATEGORY(SERIALIZATION, FRONTEND) 133a07b59e5e9b55033239c80552094421a01b75c8aBenjamin KramerCATEGORY(LEX, SERIALIZATION) 134a07b59e5e9b55033239c80552094421a01b75c8aBenjamin KramerCATEGORY(PARSE, LEX) 135a07b59e5e9b55033239c80552094421a01b75c8aBenjamin KramerCATEGORY(AST, PARSE) 136a07b59e5e9b55033239c80552094421a01b75c8aBenjamin KramerCATEGORY(COMMENT, AST) 137a07b59e5e9b55033239c80552094421a01b75c8aBenjamin KramerCATEGORY(SEMA, COMMENT) 138a07b59e5e9b55033239c80552094421a01b75c8aBenjamin KramerCATEGORY(ANALYSIS, SEMA) 139a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer#undef CATEGORY 140a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer 141a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // Avoid out of bounds reads. 142a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer if (ID + Offset >= StaticDiagInfoSize) 1436bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen Hines return nullptr; 144a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer 14535abfcd3285ad82fa269b8f2468dee01a4dceb52Argyrios Kyrtzidis assert(ID < StaticDiagInfoSize && Offset < StaticDiagInfoSize); 14635abfcd3285ad82fa269b8f2468dee01a4dceb52Argyrios Kyrtzidis 147a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer const StaticDiagInfoRec *Found = &StaticDiagInfo[ID + Offset]; 148a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // If the diag id doesn't match we found a different diag, abort. This can 149a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // happen when this function is called with an ID that points into a hole in 150a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer // the diagID space. 151a07b59e5e9b55033239c80552094421a01b75c8aBenjamin Kramer if (Found->DiagID != DiagID) 1526bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen Hines return nullptr; 15333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return Found; 15433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 15533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 156ef8225444452a1486bd721f3285301fe84643b00Stephen Hinesstatic DiagnosticMapping GetDefaultDiagMapping(unsigned DiagID) { 157ef8225444452a1486bd721f3285301fe84643b00Stephen Hines DiagnosticMapping Info = DiagnosticMapping::Make( 158ef8225444452a1486bd721f3285301fe84643b00Stephen Hines diag::Severity::Fatal, /*IsUser=*/false, /*IsPragma=*/false); 159a5e41333b06fdf036d58495490eb14d6a0a3fcf7Daniel Dunbar 160a5e41333b06fdf036d58495490eb14d6a0a3fcf7Daniel Dunbar if (const StaticDiagInfoRec *StaticInfo = GetDiagInfo(DiagID)) { 161ef8225444452a1486bd721f3285301fe84643b00Stephen Hines Info.setSeverity((diag::Severity)StaticInfo->DefaultSeverity); 1624213df3b5da21ce25a4541ca5c447eeb28b515a3Daniel Dunbar 163a5e41333b06fdf036d58495490eb14d6a0a3fcf7Daniel Dunbar if (StaticInfo->WarnNoWerror) { 164ef8225444452a1486bd721f3285301fe84643b00Stephen Hines assert(Info.getSeverity() == diag::Severity::Warning && 1654213df3b5da21ce25a4541ca5c447eeb28b515a3Daniel Dunbar "Unexpected mapping with no-Werror bit!"); 166a5e41333b06fdf036d58495490eb14d6a0a3fcf7Daniel Dunbar Info.setNoWarningAsError(true); 1674213df3b5da21ce25a4541ca5c447eeb28b515a3Daniel Dunbar } 1684213df3b5da21ce25a4541ca5c447eeb28b515a3Daniel Dunbar } 169a5e41333b06fdf036d58495490eb14d6a0a3fcf7Daniel Dunbar 170a5e41333b06fdf036d58495490eb14d6a0a3fcf7Daniel Dunbar return Info; 17133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 17233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 1737d2b8c1fcc2b707be78b09930a7767477822462fDouglas Gregor/// getCategoryNumberForDiag - Return the category number that a specified 17433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// DiagID belongs to, or 0 if no category. 17533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisunsigned DiagnosticIDs::getCategoryNumberForDiag(unsigned DiagID) { 17633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (const StaticDiagInfoRec *Info = GetDiagInfo(DiagID)) 17733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return Info->Category; 17833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return 0; 17933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 18033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 181dbda513550aaea9f4106455a3fc6b584bacc77f2Benjamin Kramernamespace { 182dbda513550aaea9f4106455a3fc6b584bacc77f2Benjamin Kramer // The diagnostic category names. 183dbda513550aaea9f4106455a3fc6b584bacc77f2Benjamin Kramer struct StaticDiagCategoryRec { 184dbda513550aaea9f4106455a3fc6b584bacc77f2Benjamin Kramer const char *NameStr; 185dbda513550aaea9f4106455a3fc6b584bacc77f2Benjamin Kramer uint8_t NameLen; 186477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis 1875f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner StringRef getName() const { 1885f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner return StringRef(NameStr, NameLen); 189dbda513550aaea9f4106455a3fc6b584bacc77f2Benjamin Kramer } 190dbda513550aaea9f4106455a3fc6b584bacc77f2Benjamin Kramer }; 191dbda513550aaea9f4106455a3fc6b584bacc77f2Benjamin Kramer} 192477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis 193ba494c64365d78b1cdb6baea4d1e79263389fda9Daniel Dunbar// Unfortunately, the split between DiagnosticIDs and Diagnostic is not 194ba494c64365d78b1cdb6baea4d1e79263389fda9Daniel Dunbar// particularly clean, but for now we just implement this method here so we can 195ba494c64365d78b1cdb6baea4d1e79263389fda9Daniel Dunbar// access GetDefaultDiagMapping. 196ef8225444452a1486bd721f3285301fe84643b00Stephen HinesDiagnosticMapping & 197ef8225444452a1486bd721f3285301fe84643b00Stephen HinesDiagnosticsEngine::DiagState::getOrAddMapping(diag::kind Diag) { 198ef8225444452a1486bd721f3285301fe84643b00Stephen Hines std::pair<iterator, bool> Result = 199ef8225444452a1486bd721f3285301fe84643b00Stephen Hines DiagMap.insert(std::make_pair(Diag, DiagnosticMapping())); 200ba494c64365d78b1cdb6baea4d1e79263389fda9Daniel Dunbar 201ba494c64365d78b1cdb6baea4d1e79263389fda9Daniel Dunbar // Initialize the entry if we added it. 202aeacae523a1c6e5bb99d12754415bbbc3ccb86c9Daniel Dunbar if (Result.second) 203ef8225444452a1486bd721f3285301fe84643b00Stephen Hines Result.first->second = GetDefaultDiagMapping(Diag); 204ba494c64365d78b1cdb6baea4d1e79263389fda9Daniel Dunbar 205ba494c64365d78b1cdb6baea4d1e79263389fda9Daniel Dunbar return Result.first->second; 206ba494c64365d78b1cdb6baea4d1e79263389fda9Daniel Dunbar} 207ba494c64365d78b1cdb6baea4d1e79263389fda9Daniel Dunbar 208dbda513550aaea9f4106455a3fc6b584bacc77f2Benjamin Kramerstatic const StaticDiagCategoryRec CategoryNameTable[] = { 20933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#define GET_CATEGORY_TABLE 210923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall#define CATEGORY(X, ENUM) { X, STR_SIZE(X, uint8_t) }, 21133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/DiagnosticGroups.inc" 21233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#undef GET_CATEGORY_TABLE 2136bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen Hines { nullptr, 0 } 214477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis}; 215477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis 216477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis/// getNumberOfCategories - Return the number of categories 217477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidisunsigned DiagnosticIDs::getNumberOfCategories() { 218b960232518a1cd79c5f64ab5ef54c88e34660191Craig Topper return llvm::array_lengthof(CategoryNameTable) - 1; 219477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis} 220477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis 221477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis/// getCategoryNameFromID - Given a category ID, return the name of the 222477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis/// category, an empty string if CategoryID is zero, or null if CategoryID is 223477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis/// invalid. 2245f9e272e632e951b1efe824cd16acb4d96077930Chris LattnerStringRef DiagnosticIDs::getCategoryNameFromID(unsigned CategoryID) { 225477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis if (CategoryID >= getNumberOfCategories()) 2265f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner return StringRef(); 227477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis return CategoryNameTable[CategoryID].getName(); 22833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 22933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 23033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 23133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 2323347b497157d36cf280d1d9f52956faa6e702f34Richard SmithDiagnosticIDs::SFINAEResponse 23333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios KyrtzidisDiagnosticIDs::getDiagnosticSFINAEResponse(unsigned DiagID) { 2343347b497157d36cf280d1d9f52956faa6e702f34Richard Smith if (const StaticDiagInfoRec *Info = GetDiagInfo(DiagID)) 2353347b497157d36cf280d1d9f52956faa6e702f34Richard Smith return static_cast<DiagnosticIDs::SFINAEResponse>(Info->SFINAE); 23633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return SFINAE_Report; 23733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 23833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 2397d2b8c1fcc2b707be78b09930a7767477822462fDouglas Gregor/// getBuiltinDiagClass - Return the class field of the diagnostic. 24033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// 24133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisstatic unsigned getBuiltinDiagClass(unsigned DiagID) { 24233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (const StaticDiagInfoRec *Info = GetDiagInfo(DiagID)) 24333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return Info->Class; 24433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return ~0U; 24533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 24633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 24733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis//===----------------------------------------------------------------------===// 24833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// Custom Diagnostic information 24933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis//===----------------------------------------------------------------------===// 25033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 25133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisnamespace clang { 25233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis namespace diag { 25333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis class CustomDiagInfo { 25433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis typedef std::pair<DiagnosticIDs::Level, std::string> DiagDesc; 25533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis std::vector<DiagDesc> DiagInfo; 25633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis std::map<DiagDesc, unsigned> DiagIDs; 25733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis public: 25833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 25933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis /// getDescription - Return the description of the specified custom 26033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis /// diagnostic. 2615f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner StringRef getDescription(unsigned DiagID) const { 26233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis assert(this && DiagID-DIAG_UPPER_LIMIT < DiagInfo.size() && 263fc09336a5965040736f9bc63a70416003972364eStefanus Du Toit "Invalid diagnostic ID"); 264477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis return DiagInfo[DiagID-DIAG_UPPER_LIMIT].second; 26533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 26633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 26733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis /// getLevel - Return the level of the specified custom diagnostic. 26833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis DiagnosticIDs::Level getLevel(unsigned DiagID) const { 26933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis assert(this && DiagID-DIAG_UPPER_LIMIT < DiagInfo.size() && 270fc09336a5965040736f9bc63a70416003972364eStefanus Du Toit "Invalid diagnostic ID"); 27133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return DiagInfo[DiagID-DIAG_UPPER_LIMIT].first; 27233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 27333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 2745f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner unsigned getOrCreateDiagID(DiagnosticIDs::Level L, StringRef Message, 27533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis DiagnosticIDs &Diags) { 27633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis DiagDesc D(L, Message); 27733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // Check to see if it already exists. 27833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis std::map<DiagDesc, unsigned>::iterator I = DiagIDs.lower_bound(D); 27933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (I != DiagIDs.end() && I->first == D) 28033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return I->second; 28133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 28233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // If not, assign a new ID. 28333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis unsigned ID = DiagInfo.size()+DIAG_UPPER_LIMIT; 28433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis DiagIDs.insert(std::make_pair(D, ID)); 28533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis DiagInfo.push_back(D); 28633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return ID; 28733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 28833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis }; 28933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 29033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } // end diag namespace 29133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} // end clang namespace 29233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 29333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 29433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis//===----------------------------------------------------------------------===// 29533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// Common Diagnostic implementation 29633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis//===----------------------------------------------------------------------===// 29733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 2986bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen HinesDiagnosticIDs::DiagnosticIDs() { CustomDiagInfo = nullptr; } 29933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 30033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios KyrtzidisDiagnosticIDs::~DiagnosticIDs() { 30133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis delete CustomDiagInfo; 30233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 30333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 30433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// getCustomDiagID - Return an ID for a diagnostic with the specified message 305fc09336a5965040736f9bc63a70416003972364eStefanus Du Toit/// and level. If this is the first request for this diagnostic, it is 30633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// registered and created, otherwise the existing ID is returned. 307651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines/// 308651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines/// \param FormatString A fixed diagnostic format string that will be hashed and 309651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines/// mapped to a unique DiagID. 310651f13cea278ec967336033dd032faef0e9fc2ecStephen Hinesunsigned DiagnosticIDs::getCustomDiagID(Level L, StringRef FormatString) { 3116bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen Hines if (!CustomDiagInfo) 31233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis CustomDiagInfo = new diag::CustomDiagInfo(); 313651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines return CustomDiagInfo->getOrCreateDiagID(L, FormatString, *this); 31433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 31533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 31633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 31733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// isBuiltinWarningOrExtension - Return true if the unmapped diagnostic 31833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// level of the specified diagnostic ID is a Warning or Extension. 31933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// This only works on builtin diagnostics, not custom ones, and is not legal to 32033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// call on NOTEs. 32133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisbool DiagnosticIDs::isBuiltinWarningOrExtension(unsigned DiagID) { 32233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return DiagID < diag::DIAG_UPPER_LIMIT && 32333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis getBuiltinDiagClass(DiagID) != CLASS_ERROR; 32433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 32533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 32633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// \brief Determine whether the given built-in diagnostic ID is a 32733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// Note. 32833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisbool DiagnosticIDs::isBuiltinNote(unsigned DiagID) { 32933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return DiagID < diag::DIAG_UPPER_LIMIT && 33033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis getBuiltinDiagClass(DiagID) == CLASS_NOTE; 33133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 33233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 33333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// isBuiltinExtensionDiag - Determine whether the given built-in diagnostic 33433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// ID is for an extension of some sort. This also returns EnabledByDefault, 33533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// which is set to indicate whether the diagnostic is ignored by default (in 33633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// which case -pedantic enables it) or treated as a warning/error by default. 33733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// 33833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisbool DiagnosticIDs::isBuiltinExtensionDiag(unsigned DiagID, 33933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis bool &EnabledByDefault) { 34033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (DiagID >= diag::DIAG_UPPER_LIMIT || 34133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis getBuiltinDiagClass(DiagID) != CLASS_EXTENSION) 34233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return false; 343ef8225444452a1486bd721f3285301fe84643b00Stephen Hines 344a5e41333b06fdf036d58495490eb14d6a0a3fcf7Daniel Dunbar EnabledByDefault = 345ef8225444452a1486bd721f3285301fe84643b00Stephen Hines GetDefaultDiagMapping(DiagID).getSeverity() != diag::Severity::Ignored; 34633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return true; 34733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 34833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 34976101cfe52d1b56974bf0e316247b3201f87c463Daniel Dunbarbool DiagnosticIDs::isDefaultMappingAsError(unsigned DiagID) { 35076101cfe52d1b56974bf0e316247b3201f87c463Daniel Dunbar if (DiagID >= diag::DIAG_UPPER_LIMIT) 35176101cfe52d1b56974bf0e316247b3201f87c463Daniel Dunbar return false; 35276101cfe52d1b56974bf0e316247b3201f87c463Daniel Dunbar 353ef8225444452a1486bd721f3285301fe84643b00Stephen Hines return GetDefaultDiagMapping(DiagID).getSeverity() == diag::Severity::Error; 3546bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen Hines} 3556bcf27bb9a4b5c3f79cb44c0e4654a6d7619ad89Stephen Hines 35633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// getDescription - Given a diagnostic ID, return a description of the 35733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// issue. 3585f9e272e632e951b1efe824cd16acb4d96077930Chris LattnerStringRef DiagnosticIDs::getDescription(unsigned DiagID) const { 35933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (const StaticDiagInfoRec *Info = GetDiagInfo(DiagID)) 360477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis return Info->getDescription(); 36133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return CustomDiagInfo->getDescription(DiagID); 36233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 36333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 364ef8225444452a1486bd721f3285301fe84643b00Stephen Hinesstatic DiagnosticIDs::Level toLevel(diag::Severity SV) { 365ef8225444452a1486bd721f3285301fe84643b00Stephen Hines switch (SV) { 366ef8225444452a1486bd721f3285301fe84643b00Stephen Hines case diag::Severity::Ignored: 367ef8225444452a1486bd721f3285301fe84643b00Stephen Hines return DiagnosticIDs::Ignored; 368ef8225444452a1486bd721f3285301fe84643b00Stephen Hines case diag::Severity::Remark: 369ef8225444452a1486bd721f3285301fe84643b00Stephen Hines return DiagnosticIDs::Remark; 370ef8225444452a1486bd721f3285301fe84643b00Stephen Hines case diag::Severity::Warning: 371ef8225444452a1486bd721f3285301fe84643b00Stephen Hines return DiagnosticIDs::Warning; 372ef8225444452a1486bd721f3285301fe84643b00Stephen Hines case diag::Severity::Error: 373ef8225444452a1486bd721f3285301fe84643b00Stephen Hines return DiagnosticIDs::Error; 374ef8225444452a1486bd721f3285301fe84643b00Stephen Hines case diag::Severity::Fatal: 375ef8225444452a1486bd721f3285301fe84643b00Stephen Hines return DiagnosticIDs::Fatal; 376ef8225444452a1486bd721f3285301fe84643b00Stephen Hines } 377ef8225444452a1486bd721f3285301fe84643b00Stephen Hines llvm_unreachable("unexpected severity"); 378ef8225444452a1486bd721f3285301fe84643b00Stephen Hines} 379ef8225444452a1486bd721f3285301fe84643b00Stephen Hines 380d6471f7c1921c7802804ce3ff6fe9768310f72b9David Blaikie/// getDiagnosticLevel - Based on the way the client configured the 381d6471f7c1921c7802804ce3ff6fe9768310f72b9David Blaikie/// DiagnosticsEngine object, classify the specified diagnostic ID into a Level, 382d6471f7c1921c7802804ce3ff6fe9768310f72b9David Blaikie/// by consumable the DiagnosticClient. 3830827408865e32789e0ec4b8113a302ccdc531423Argyrios KyrtzidisDiagnosticIDs::Level 3840827408865e32789e0ec4b8113a302ccdc531423Argyrios KyrtzidisDiagnosticIDs::getDiagnosticLevel(unsigned DiagID, SourceLocation Loc, 3851656aaec223949245fdbebf306b719cba0b687caDaniel Dunbar const DiagnosticsEngine &Diag) const { 38633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // Handle custom diagnostics, which cannot be mapped. 38733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (DiagID >= diag::DIAG_UPPER_LIMIT) 38833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return CustomDiagInfo->getLevel(DiagID); 38933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 39033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis unsigned DiagClass = getBuiltinDiagClass(DiagID); 391c6d64a26c28bbeee50e06c94c4f4c08e610327b7Jordan Rose if (DiagClass == CLASS_NOTE) return DiagnosticIDs::Note; 392ef8225444452a1486bd721f3285301fe84643b00Stephen Hines return toLevel(getDiagnosticSeverity(DiagID, Loc, Diag)); 39333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 39433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 3950827408865e32789e0ec4b8113a302ccdc531423Argyrios Kyrtzidis/// \brief Based on the way the client configured the Diagnostic 39633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// object, classify the specified diagnostic ID into a Level, consumable by 39733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// the DiagnosticClient. 3980827408865e32789e0ec4b8113a302ccdc531423Argyrios Kyrtzidis/// 3990827408865e32789e0ec4b8113a302ccdc531423Argyrios Kyrtzidis/// \param Loc The source location we are interested in finding out the 4000827408865e32789e0ec4b8113a302ccdc531423Argyrios Kyrtzidis/// diagnostic state. Can be null in order to query the latest state. 401ef8225444452a1486bd721f3285301fe84643b00Stephen Hinesdiag::Severity 402ef8225444452a1486bd721f3285301fe84643b00Stephen HinesDiagnosticIDs::getDiagnosticSeverity(unsigned DiagID, SourceLocation Loc, 403ef8225444452a1486bd721f3285301fe84643b00Stephen Hines const DiagnosticsEngine &Diag) const { 404ef8225444452a1486bd721f3285301fe84643b00Stephen Hines assert(getBuiltinDiagClass(DiagID) != CLASS_NOTE); 405ef8225444452a1486bd721f3285301fe84643b00Stephen Hines 40633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // Specific non-error diagnostics may be mapped to various levels from ignored 40733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // to error. Errors can only be mapped to fatal. 408ef8225444452a1486bd721f3285301fe84643b00Stephen Hines diag::Severity Result = diag::Severity::Fatal; 40933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 410d6471f7c1921c7802804ce3ff6fe9768310f72b9David Blaikie DiagnosticsEngine::DiagStatePointsTy::iterator 4110827408865e32789e0ec4b8113a302ccdc531423Argyrios Kyrtzidis Pos = Diag.GetDiagStatePointForLoc(Loc); 412d6471f7c1921c7802804ce3ff6fe9768310f72b9David Blaikie DiagnosticsEngine::DiagState *State = Pos->State; 4130827408865e32789e0ec4b8113a302ccdc531423Argyrios Kyrtzidis 414ba494c64365d78b1cdb6baea4d1e79263389fda9Daniel Dunbar // Get the mapping information, or compute it lazily. 415ef8225444452a1486bd721f3285301fe84643b00Stephen Hines DiagnosticMapping &Mapping = State->getOrAddMapping((diag::kind)DiagID); 416ef8225444452a1486bd721f3285301fe84643b00Stephen Hines 417ef8225444452a1486bd721f3285301fe84643b00Stephen Hines // TODO: Can a null severity really get here? 418ef8225444452a1486bd721f3285301fe84643b00Stephen Hines if (Mapping.getSeverity() != diag::Severity()) 419ef8225444452a1486bd721f3285301fe84643b00Stephen Hines Result = Mapping.getSeverity(); 42033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 421be1aa410274b28fc143c47c814f07c989f4534d6Daniel Dunbar // Upgrade ignored diagnostics if -Weverything is enabled. 422ef8225444452a1486bd721f3285301fe84643b00Stephen Hines if (Diag.EnableAllWarnings && Result == diag::Severity::Ignored && 423ef8225444452a1486bd721f3285301fe84643b00Stephen Hines !Mapping.isUser()) 424ef8225444452a1486bd721f3285301fe84643b00Stephen Hines Result = diag::Severity::Warning; 42533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 426651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines // Diagnostics of class REMARK are either printed as remarks or in case they 427651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines // have been added to -Werror they are printed as errors. 428ef8225444452a1486bd721f3285301fe84643b00Stephen Hines // FIXME: Disregarding user-requested remark mappings like this is bogus. 429ef8225444452a1486bd721f3285301fe84643b00Stephen Hines if (Result == diag::Severity::Warning && 430ef8225444452a1486bd721f3285301fe84643b00Stephen Hines getBuiltinDiagClass(DiagID) == CLASS_REMARK) 431ef8225444452a1486bd721f3285301fe84643b00Stephen Hines Result = diag::Severity::Remark; 432651f13cea278ec967336033dd032faef0e9fc2ecStephen Hines 43318c407fcb25ea88a52ad48fcc4397c3616dd185dBob Wilson // Ignore -pedantic diagnostics inside __extension__ blocks. 43418c407fcb25ea88a52ad48fcc4397c3616dd185dBob Wilson // (The diagnostics controlled by -pedantic are the extension diagnostics 43518c407fcb25ea88a52ad48fcc4397c3616dd185dBob Wilson // that are not enabled by default.) 436f3dee206ffa571b4541b8e777ee31dc8476d66daDaniel Dunbar bool EnabledByDefault = false; 43718c407fcb25ea88a52ad48fcc4397c3616dd185dBob Wilson bool IsExtensionDiag = isBuiltinExtensionDiag(DiagID, EnabledByDefault); 43818c407fcb25ea88a52ad48fcc4397c3616dd185dBob Wilson if (Diag.AllExtensionsSilenced && IsExtensionDiag && !EnabledByDefault) 439ef8225444452a1486bd721f3285301fe84643b00Stephen Hines return diag::Severity::Ignored; 44033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 441be1aa410274b28fc143c47c814f07c989f4534d6Daniel Dunbar // For extension diagnostics that haven't been explicitly mapped, check if we 442be1aa410274b28fc143c47c814f07c989f4534d6Daniel Dunbar // should upgrade the diagnostic. 443ef8225444452a1486bd721f3285301fe84643b00Stephen Hines if (IsExtensionDiag && !Mapping.isUser()) 444ef8225444452a1486bd721f3285301fe84643b00Stephen Hines Result = std::max(Result, Diag.ExtBehavior); 44533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 446be1aa410274b28fc143c47c814f07c989f4534d6Daniel Dunbar // At this point, ignored errors can no longer be upgraded. 447ef8225444452a1486bd721f3285301fe84643b00Stephen Hines if (Result == diag::Severity::Ignored) 448be1aa410274b28fc143c47c814f07c989f4534d6Daniel Dunbar return Result; 44933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 450be1aa410274b28fc143c47c814f07c989f4534d6Daniel Dunbar // Honor -w, which is lower in priority than pedantic-errors, but higher than 451be1aa410274b28fc143c47c814f07c989f4534d6Daniel Dunbar // -Werror. 452ef8225444452a1486bd721f3285301fe84643b00Stephen Hines if (Result == diag::Severity::Warning && Diag.IgnoreAllWarnings) 453ef8225444452a1486bd721f3285301fe84643b00Stephen Hines return diag::Severity::Ignored; 45433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 455be1aa410274b28fc143c47c814f07c989f4534d6Daniel Dunbar // If -Werror is enabled, map warnings to errors unless explicitly disabled. 456ef8225444452a1486bd721f3285301fe84643b00Stephen Hines if (Result == diag::Severity::Warning) { 457ef8225444452a1486bd721f3285301fe84643b00Stephen Hines if (Diag.WarningsAsErrors && !Mapping.hasNoWarningAsError()) 458ef8225444452a1486bd721f3285301fe84643b00Stephen Hines Result = diag::Severity::Error; 45933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 46033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 461be1aa410274b28fc143c47c814f07c989f4534d6Daniel Dunbar // If -Wfatal-errors is enabled, map errors to fatal unless explicity 462be1aa410274b28fc143c47c814f07c989f4534d6Daniel Dunbar // disabled. 463ef8225444452a1486bd721f3285301fe84643b00Stephen Hines if (Result == diag::Severity::Error) { 464ef8225444452a1486bd721f3285301fe84643b00Stephen Hines if (Diag.ErrorsAsFatal && !Mapping.hasNoErrorAsFatal()) 465ef8225444452a1486bd721f3285301fe84643b00Stephen Hines Result = diag::Severity::Fatal; 466be1aa410274b28fc143c47c814f07c989f4534d6Daniel Dunbar } 46733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 468ef8225444452a1486bd721f3285301fe84643b00Stephen Hines // Custom diagnostics always are emitted in system headers. 469ef8225444452a1486bd721f3285301fe84643b00Stephen Hines bool ShowInSystemHeader = 470ef8225444452a1486bd721f3285301fe84643b00Stephen Hines !GetDiagInfo(DiagID) || GetDiagInfo(DiagID)->WarnShowInSystemHeader; 471ef8225444452a1486bd721f3285301fe84643b00Stephen Hines 472aeacae523a1c6e5bb99d12754415bbbc3ccb86c9Daniel Dunbar // If we are in a system header, we ignore it. We look at the diagnostic class 473aeacae523a1c6e5bb99d12754415bbbc3ccb86c9Daniel Dunbar // because we also want to ignore extensions and warnings in -Werror and 474cfdadfe547015b916bd59aec892caa972ff76cf0Argyrios Kyrtzidis // -pedantic-errors modes, which *map* warnings/extensions to errors. 475ef8225444452a1486bd721f3285301fe84643b00Stephen Hines if (Diag.SuppressSystemWarnings && !ShowInSystemHeader && Loc.isValid() && 476cfdadfe547015b916bd59aec892caa972ff76cf0Argyrios Kyrtzidis Diag.getSourceManager().isInSystemHeader( 477402785357ab053dd53f4fdd858b9630a5e0f8badChandler Carruth Diag.getSourceManager().getExpansionLoc(Loc))) 478ef8225444452a1486bd721f3285301fe84643b00Stephen Hines return diag::Severity::Ignored; 479cfdadfe547015b916bd59aec892caa972ff76cf0Argyrios Kyrtzidis 48033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return Result; 48133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 48233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 483354f20a8720732aa1745d1ff9595382cee324ee2Craig Topper#define GET_DIAG_ARRAYS 484354f20a8720732aa1745d1ff9595382cee324ee2Craig Topper#include "clang/Basic/DiagnosticGroups.inc" 485354f20a8720732aa1745d1ff9595382cee324ee2Craig Topper#undef GET_DIAG_ARRAYS 486354f20a8720732aa1745d1ff9595382cee324ee2Craig Topper 48746c8fca7b32a7613f9b37b46c381dd064b773b30Craig Toppernamespace { 48846c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper struct WarningOption { 48946c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper uint16_t NameOffset; 49046c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper uint16_t Members; 49146c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper uint16_t SubGroups; 49246c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper 49346c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper // String is stored with a pascal-style length byte. 49446c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper StringRef getName() const { 49546c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper return StringRef(DiagGroupNames + NameOffset + 1, 49646c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper DiagGroupNames[NameOffset]); 49746c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper } 49846c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper }; 49946c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper} 50033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 50133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis// Second the table of options, sorted by name for fast binary lookup. 50233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidisstatic const WarningOption OptionTable[] = { 50333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#define GET_DIAG_TABLE 50433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#include "clang/Basic/DiagnosticGroups.inc" 50533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis#undef GET_DIAG_TABLE 50633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis}; 507b960232518a1cd79c5f64ab5ef54c88e34660191Craig Topperstatic const size_t OptionTableSize = llvm::array_lengthof(OptionTable); 50833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 509354f20a8720732aa1745d1ff9595382cee324ee2Craig Topperstatic bool WarningOptionCompare(const WarningOption &LHS, StringRef RHS) { 510354f20a8720732aa1745d1ff9595382cee324ee2Craig Topper return LHS.getName() < RHS; 51133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 51233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 513d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin Kramer/// getWarningOptionForDiag - Return the lowest-level warning option that 514d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin Kramer/// enables the specified diagnostic. If there is no -Wfoo flag that controls 515d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin Kramer/// the diagnostic, this returns null. 516d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin KramerStringRef DiagnosticIDs::getWarningOptionForDiag(unsigned DiagID) { 517d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin Kramer if (const StaticDiagInfoRec *Info = GetDiagInfo(DiagID)) 518d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin Kramer return OptionTable[Info->getOptionGroupIndex()].getName(); 519d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin Kramer return StringRef(); 520d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin Kramer} 521d49cb20288b2dbc222aaf5673c1a4738c151b7bfBenjamin Kramer 52246c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topperstatic void getDiagnosticsInGroup(const WarningOption *Group, 52346c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper SmallVectorImpl<diag::kind> &Diags) { 5243f8394669673451061f57ced81f0a2cae087f119Daniel Dunbar // Add the members of the option diagnostic set. 525b1aa16a18563ebb6824fbe7267420942c802a8caCraig Topper const int16_t *Member = DiagArrays + Group->Members; 526b1aa16a18563ebb6824fbe7267420942c802a8caCraig Topper for (; *Member != -1; ++Member) 527b1aa16a18563ebb6824fbe7267420942c802a8caCraig Topper Diags.push_back(*Member); 52833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 5293f8394669673451061f57ced81f0a2cae087f119Daniel Dunbar // Add the members of the subgroups. 530b1aa16a18563ebb6824fbe7267420942c802a8caCraig Topper const int16_t *SubGroups = DiagSubGroups + Group->SubGroups; 531b1aa16a18563ebb6824fbe7267420942c802a8caCraig Topper for (; *SubGroups != (int16_t)-1; ++SubGroups) 532b1aa16a18563ebb6824fbe7267420942c802a8caCraig Topper getDiagnosticsInGroup(&OptionTable[(short)*SubGroups], Diags); 53333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 53433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 5353f8394669673451061f57ced81f0a2cae087f119Daniel Dunbarbool DiagnosticIDs::getDiagnosticsInGroup( 536cfa88f893915ceb8ae4ce2f17c46c24a4d67502fDmitri Gribenko StringRef Group, 537cfa88f893915ceb8ae4ce2f17c46c24a4d67502fDmitri Gribenko SmallVectorImpl<diag::kind> &Diags) const { 53833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis const WarningOption *Found = 539354f20a8720732aa1745d1ff9595382cee324ee2Craig Topper std::lower_bound(OptionTable, OptionTable + OptionTableSize, Group, 54033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis WarningOptionCompare); 54133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (Found == OptionTable + OptionTableSize || 542477aab6782795e7472055a54108d2df270ce1a89Argyrios Kyrtzidis Found->getName() != Group) 5433f8394669673451061f57ced81f0a2cae087f119Daniel Dunbar return true; // Option not found. 54433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 54546c8fca7b32a7613f9b37b46c381dd064b773b30Craig Topper ::getDiagnosticsInGroup(Found, Diags); 54633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return false; 54733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 54833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 54911583c757bac6ce5c342f2eb572055dd2619a657Argyrios Kyrtzidisvoid DiagnosticIDs::getAllDiagnostics( 550cfa88f893915ceb8ae4ce2f17c46c24a4d67502fDmitri Gribenko SmallVectorImpl<diag::kind> &Diags) const { 55111583c757bac6ce5c342f2eb572055dd2619a657Argyrios Kyrtzidis for (unsigned i = 0; i != StaticDiagInfoSize; ++i) 55211583c757bac6ce5c342f2eb572055dd2619a657Argyrios Kyrtzidis Diags.push_back(StaticDiagInfo[i].DiagID); 55311583c757bac6ce5c342f2eb572055dd2619a657Argyrios Kyrtzidis} 55411583c757bac6ce5c342f2eb572055dd2619a657Argyrios Kyrtzidis 555a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin KramerStringRef DiagnosticIDs::getNearestWarningOption(StringRef Group) { 556a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer StringRef Best; 557dce6327160a6e333137b34cce77e2dfc2cd5aab6Benjamin Kramer unsigned BestDistance = Group.size() + 1; // Sanity threshold. 558a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer for (const WarningOption *i = OptionTable, *e = OptionTable + OptionTableSize; 559a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer i != e; ++i) { 560a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer // Don't suggest ignored warning flags. 561a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer if (!i->Members && !i->SubGroups) 562a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer continue; 563a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer 564a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer unsigned Distance = i->getName().edit_distance(Group, true, BestDistance); 565dce6327160a6e333137b34cce77e2dfc2cd5aab6Benjamin Kramer if (Distance == BestDistance) { 566dce6327160a6e333137b34cce77e2dfc2cd5aab6Benjamin Kramer // Two matches with the same distance, don't prefer one over the other. 567dce6327160a6e333137b34cce77e2dfc2cd5aab6Benjamin Kramer Best = ""; 568dce6327160a6e333137b34cce77e2dfc2cd5aab6Benjamin Kramer } else if (Distance < BestDistance) { 569dce6327160a6e333137b34cce77e2dfc2cd5aab6Benjamin Kramer // This is a better match. 570a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer Best = i->getName(); 571a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer BestDistance = Distance; 572a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer } 573a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer } 574a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer 575a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer return Best; 576a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer} 577a70cb9db9dd79ca9fc1febbb2f331004297664e0Benjamin Kramer 57833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// ProcessDiag - This is the method used to report a diagnostic that is 57933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis/// finally fully formed. 580d6471f7c1921c7802804ce3ff6fe9768310f72b9David Blaikiebool DiagnosticIDs::ProcessDiag(DiagnosticsEngine &Diag) const { 58140847cfb58acc3cac7d68727df9455ac45f2e118David Blaikie Diagnostic Info(&Diag); 58233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 58333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (Diag.SuppressAllDiagnostics) 58433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return false; 58533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 58633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis assert(Diag.getClient() && "DiagnosticClient not set!"); 58733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 58833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // Figure out the diagnostic level of this message. 58933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis unsigned DiagID = Info.getID(); 590c6d64a26c28bbeee50e06c94c4f4c08e610327b7Jordan Rose DiagnosticIDs::Level DiagLevel 591c6d64a26c28bbeee50e06c94c4f4c08e610327b7Jordan Rose = getDiagnosticLevel(DiagID, Info.getLocation(), Diag); 59233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 59333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (DiagLevel != DiagnosticIDs::Note) { 59433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // Record that a fatal error occurred only when we see a second 59533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // non-note diagnostic. This allows notes to be attached to the 59633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // fatal error, but suppresses any diagnostics that follow those 59733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // notes. 59833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (Diag.LastDiagLevel == DiagnosticIDs::Fatal) 59933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis Diag.FatalErrorOccurred = true; 60033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 60133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis Diag.LastDiagLevel = DiagLevel; 60233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 60333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 604c0a575f9b791a25c94b1c3c832dd73ec564646bbArgyrios Kyrtzidis // Update counts for DiagnosticErrorTrap even if a fatal error occurred. 605c0a575f9b791a25c94b1c3c832dd73ec564646bbArgyrios Kyrtzidis if (DiagLevel >= DiagnosticIDs::Error) { 606c0a575f9b791a25c94b1c3c832dd73ec564646bbArgyrios Kyrtzidis ++Diag.TrapNumErrorsOccurred; 607c0a575f9b791a25c94b1c3c832dd73ec564646bbArgyrios Kyrtzidis if (isUnrecoverable(DiagID)) 608c0a575f9b791a25c94b1c3c832dd73ec564646bbArgyrios Kyrtzidis ++Diag.TrapNumUnrecoverableErrorsOccurred; 609c0a575f9b791a25c94b1c3c832dd73ec564646bbArgyrios Kyrtzidis } 610c0a575f9b791a25c94b1c3c832dd73ec564646bbArgyrios Kyrtzidis 61133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // If a fatal error has already been emitted, silence all subsequent 61233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // diagnostics. 61333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (Diag.FatalErrorOccurred) { 61433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (DiagLevel >= DiagnosticIDs::Error && 61533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis Diag.Client->IncludeInDiagnosticCounts()) { 61633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis ++Diag.NumErrors; 61733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis ++Diag.NumErrorsSuppressed; 61833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 61933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 62033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return false; 62133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 62233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 62333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // If the client doesn't care about this message, don't issue it. If this is 62433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // a note and the last real diagnostic was ignored, ignore it too. 62533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (DiagLevel == DiagnosticIDs::Ignored || 62633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis (DiagLevel == DiagnosticIDs::Note && 62733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis Diag.LastDiagLevel == DiagnosticIDs::Ignored)) 62833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis return false; 62933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 63033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (DiagLevel >= DiagnosticIDs::Error) { 631c0a575f9b791a25c94b1c3c832dd73ec564646bbArgyrios Kyrtzidis if (isUnrecoverable(DiagID)) 63285bea9777d444ccbcc086d98f075fe666c2e865dDouglas Gregor Diag.UnrecoverableErrorOccurred = true; 6331c84c68b6d7a92416493ab6c36f630de48c65d08Daniel Jasper 63412f37e411462b8388eb1309357bd62257debacacDeLesley Hutchins // Warnings which have been upgraded to errors do not prevent compilation. 63512f37e411462b8388eb1309357bd62257debacacDeLesley Hutchins if (isDefaultMappingAsError(DiagID)) 63612f37e411462b8388eb1309357bd62257debacacDeLesley Hutchins Diag.UncompilableErrorOccurred = true; 63712f37e411462b8388eb1309357bd62257debacacDeLesley Hutchins 6381c84c68b6d7a92416493ab6c36f630de48c65d08Daniel Jasper Diag.ErrorOccurred = true; 63933e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (Diag.Client->IncludeInDiagnosticCounts()) { 64033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis ++Diag.NumErrors; 64133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 64233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 643f1d594864b4aefc1fe21535cb43e8a81038f3f15Douglas Gregor // If we've emitted a lot of errors, emit a fatal error instead of it to 644f1d594864b4aefc1fe21535cb43e8a81038f3f15Douglas Gregor // stop a flood of bogus errors. 645f1d594864b4aefc1fe21535cb43e8a81038f3f15Douglas Gregor if (Diag.ErrorLimit && Diag.NumErrors > Diag.ErrorLimit && 646f1d594864b4aefc1fe21535cb43e8a81038f3f15Douglas Gregor DiagLevel == DiagnosticIDs::Error) { 64733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis Diag.SetDelayedDiagnostic(diag::fatal_too_many_errors); 648f1d594864b4aefc1fe21535cb43e8a81038f3f15Douglas Gregor return false; 649f1d594864b4aefc1fe21535cb43e8a81038f3f15Douglas Gregor } 65033e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 65133e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 65233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis // Finally, report it. 653c6d64a26c28bbeee50e06c94c4f4c08e610327b7Jordan Rose EmitDiag(Diag, DiagLevel); 654c6d64a26c28bbeee50e06c94c4f4c08e610327b7Jordan Rose return true; 655c6d64a26c28bbeee50e06c94c4f4c08e610327b7Jordan Rose} 656c6d64a26c28bbeee50e06c94c4f4c08e610327b7Jordan Rose 657c6d64a26c28bbeee50e06c94c4f4c08e610327b7Jordan Rosevoid DiagnosticIDs::EmitDiag(DiagnosticsEngine &Diag, Level DiagLevel) const { 658c6d64a26c28bbeee50e06c94c4f4c08e610327b7Jordan Rose Diagnostic Info(&Diag); 659c6d64a26c28bbeee50e06c94c4f4c08e610327b7Jordan Rose assert(DiagLevel != DiagnosticIDs::Ignored && "Cannot emit ignored diagnostics!"); 660c6d64a26c28bbeee50e06c94c4f4c08e610327b7Jordan Rose 661d6471f7c1921c7802804ce3ff6fe9768310f72b9David Blaikie Diag.Client->HandleDiagnostic((DiagnosticsEngine::Level)DiagLevel, Info); 66233e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (Diag.Client->IncludeInDiagnosticCounts()) { 66333e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis if (DiagLevel == DiagnosticIDs::Warning) 66433e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis ++Diag.NumWarnings; 66533e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis } 66633e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis 66733e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis Diag.CurDiagID = ~0U; 66833e4e70c8c0a17e0ccb7465d96556b077a68ecb1Argyrios Kyrtzidis} 669923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall 670923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCallbool DiagnosticIDs::isUnrecoverable(unsigned DiagID) const { 671923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall if (DiagID >= diag::DIAG_UPPER_LIMIT) { 672923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall // Custom diagnostics. 673923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall return CustomDiagInfo->getLevel(DiagID) >= DiagnosticIDs::Error; 674923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall } 675923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall 676923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall // Only errors may be unrecoverable. 67785bea9777d444ccbcc086d98f075fe666c2e865dDouglas Gregor if (getBuiltinDiagClass(DiagID) < CLASS_ERROR) 678923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall return false; 679923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall 680923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall if (DiagID == diag::err_unavailable || 681923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall DiagID == diag::err_unavailable_message) 682923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall return false; 683923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall 684f85e193739c953358c865005855253af4f68a497John McCall // Currently we consider all ARC errors as recoverable. 685afdc21ad774eff6ed6c464e3f2dff9e26ed3d0b0Ted Kremenek if (isARCDiagnostic(DiagID)) 686f85e193739c953358c865005855253af4f68a497John McCall return false; 687f85e193739c953358c865005855253af4f68a497John McCall 688923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall return true; 689923cd5744a724d9302ea12baa5476ad1c37f474dJohn McCall} 690afdc21ad774eff6ed6c464e3f2dff9e26ed3d0b0Ted Kremenek 691afdc21ad774eff6ed6c464e3f2dff9e26ed3d0b0Ted Kremenekbool DiagnosticIDs::isARCDiagnostic(unsigned DiagID) { 692afdc21ad774eff6ed6c464e3f2dff9e26ed3d0b0Ted Kremenek unsigned cat = getCategoryNumberForDiag(DiagID); 693afdc21ad774eff6ed6c464e3f2dff9e26ed3d0b0Ted Kremenek return DiagnosticIDs::getCategoryNameFromID(cat).startswith("ARC "); 694afdc21ad774eff6ed6c464e3f2dff9e26ed3d0b0Ted Kremenek} 695