Diagnostic.h revision 0bc735ffcfb223c0186419547abaa5c84482663e
15f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer//===--- Diagnostic.h - C Language Family Diagnostic Handling ---*- C++ -*-===// 25f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer// 35f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer// The LLVM Compiler Infrastructure 45f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer// 50bc735ffcfb223c0186419547abaa5c84482663eChris Lattner// This file is distributed under the University of Illinois Open Source 60bc735ffcfb223c0186419547abaa5c84482663eChris Lattner// License. See LICENSE.TXT for details. 75f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer// 85f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer//===----------------------------------------------------------------------===// 95f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer// 105f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer// This file defines the Diagnostic-related interfaces. 115f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer// 125f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer//===----------------------------------------------------------------------===// 135f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 145f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer#ifndef LLVM_CLANG_DIAGNOSTIC_H 155f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer#define LLVM_CLANG_DIAGNOSTIC_H 165f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 172eefd8657c233bc7c9330acfe475fc270bbe7cabTed Kremenek#include "clang/Basic/SourceLocation.h" 185f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer#include <string> 19f86638365f4801ec2d2970f7c0663e94590618b8Chris Lattner#include <cassert> 205f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 215f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencernamespace clang { 225f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer class DiagnosticClient; 235f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer class SourceRange; 247a9d49fd2bfac00e905b361ba76d26ab5b6c3b09Ted Kremenek class SourceManager; 255f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 265f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer // Import the diagnostic enums themselves. 275f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer namespace diag { 28182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner class CustomDiagInfo; 29182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner 305f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// diag::kind - All of the diagnostics that can be emitted by the frontend. 315f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer enum kind { 325f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer#define DIAG(ENUM,FLAGS,DESC) ENUM, 335f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer#include "DiagnosticKinds.def" 340750618b0beacdc9b0a9e210a661e4746823ced7Chris Lattner NUM_BUILTIN_DIAGNOSTICS 355f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer }; 365f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 375f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// Enum values that allow the client to map NOTEs, WARNINGs, and EXTENSIONs 385f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// to either MAP_IGNORE (nothing), MAP_WARNING (emit a warning), MAP_ERROR 395f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// (emit as an error), or MAP_DEFAULT (handle the default way). 405f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer enum Mapping { 415f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer MAP_DEFAULT = 0, //< Do not map this diagnostic. 425f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer MAP_IGNORE = 1, //< Map this diagnostic to nothing, ignore it. 435f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer MAP_WARNING = 2, //< Map this diagnostic to a warning. 445f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer MAP_ERROR = 3 //< Map this diagnostic to an error. 455f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer }; 465f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer } 475f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 485f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer/// Diagnostic - This concrete class is used by the front-end to report 495f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer/// problems and issues. It massages the diagnostics (e.g. handling things like 505f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer/// "report warnings as errors" and passes them off to the DiagnosticClient for 515f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer/// reporting to the user. 525f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencerclass Diagnostic { 53182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattnerpublic: 54182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner /// Level - The level of the diagnostic, after it has been through mapping. 55182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner enum Level { 56182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner Ignored, Note, Warning, Error, Fatal 57182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner }; 58182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner 59182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattnerprivate: 605f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer bool WarningsAsErrors; // Treat warnings like errors: 615f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer bool WarnOnExtensions; // Enables warnings for gcc extensions: -pedantic. 625f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer bool ErrorOnExtensions; // Error on extensions: -pedantic-errors. 635f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer DiagnosticClient &Client; 645f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 655f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// DiagMappings - Mapping information for diagnostics. Mapping info is 665f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// packed into two bits per diagnostic. 670750618b0beacdc9b0a9e210a661e4746823ced7Chris Lattner unsigned char DiagMappings[(diag::NUM_BUILTIN_DIAGNOSTICS+3)/4]; 685f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 695f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// ErrorOccurred - This is set to true when an error is emitted, and is 705f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// sticky. 715f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer bool ErrorOccurred; 725f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 735f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer unsigned NumDiagnostics; // Number of diagnostics reported 745f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer unsigned NumErrors; // Number of diagnostics that are errors 75182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner 76182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner /// CustomDiagInfo - Information for uniquing and looking up custom diags. 77182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner diag::CustomDiagInfo *CustomDiagInfo; 785f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencerpublic: 795f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer explicit Diagnostic(DiagnosticClient &client); 80182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner ~Diagnostic(); 815f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 825f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer //===--------------------------------------------------------------------===// 835f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer // Diagnostic characterization methods, used by a client to customize how 845f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer // 855f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer const DiagnosticClient &getClient() const { return Client; }; 865f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 875f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// setWarningsAsErrors - When set to true, any warnings reported are issued 885f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// as errors. 895f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer void setWarningsAsErrors(bool Val) { WarningsAsErrors = Val; } 905f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer bool getWarningsAsErrors() const { return WarningsAsErrors; } 915f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 925f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// setWarnOnExtensions - When set to true, issue warnings on GCC extensions, 935f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// the equivalent of GCC's -pedantic. 945f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer void setWarnOnExtensions(bool Val) { WarnOnExtensions = Val; } 955f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer bool getWarnOnExtensions() const { return WarnOnExtensions; } 965f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 975f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// setErrorOnExtensions - When set to true issue errors for GCC extensions 985f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// instead of warnings. This is the equivalent to GCC's -pedantic-errors. 995f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer void setErrorOnExtensions(bool Val) { ErrorOnExtensions = Val; } 1005f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer bool getErrorOnExtensions() const { return ErrorOnExtensions; } 1015f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1025f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// setDiagnosticMapping - This allows the client to specify that certain 1035f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// warnings are ignored. Only NOTEs, WARNINGs, and EXTENSIONs can be mapped. 1045f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer void setDiagnosticMapping(diag::kind Diag, diag::Mapping Map) { 1050750618b0beacdc9b0a9e210a661e4746823ced7Chris Lattner assert(Diag < diag::NUM_BUILTIN_DIAGNOSTICS && 1060750618b0beacdc9b0a9e210a661e4746823ced7Chris Lattner "Can only map builtin diagnostics"); 1070750618b0beacdc9b0a9e210a661e4746823ced7Chris Lattner assert(isBuiltinNoteWarningOrExtension(Diag) && "Cannot map errors!"); 1085f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer unsigned char &Slot = DiagMappings[Diag/4]; 1095f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer unsigned Bits = (Diag & 3)*2; 1105f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer Slot &= ~(3 << Bits); 1115f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer Slot |= Map << Bits; 1125f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer } 1135f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1145f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// getDiagnosticMapping - Return the mapping currently set for the specified 1155f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// diagnostic. 1165f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer diag::Mapping getDiagnosticMapping(diag::kind Diag) const { 1175f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer return (diag::Mapping)((DiagMappings[Diag/4] >> (Diag & 3)*2) & 3); 1185f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer } 1195f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1205f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer bool hasErrorOccurred() const { return ErrorOccurred; } 1215f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1225f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer unsigned getNumErrors() const { return NumErrors; } 1235f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer unsigned getNumDiagnostics() const { return NumDiagnostics; } 1245f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 125182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner /// getCustomDiagID - Return an ID for a diagnostic with the specified message 126182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner /// and level. If this is the first request for this diagnosic, it is 127182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner /// registered and created, otherwise the existing ID is returned. 128182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner unsigned getCustomDiagID(Level L, const char *Message); 129182745ae7892bca0842d9c023370ade5f8d1c6e8Chris Lattner 1305f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer //===--------------------------------------------------------------------===// 1315f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer // Diagnostic classification and reporting interfaces. 1325f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer // 1335f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1345f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// getDescription - Given a diagnostic ID, return a description of the 1355f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// issue. 1360750618b0beacdc9b0a9e210a661e4746823ced7Chris Lattner const char *getDescription(unsigned DiagID); 1375f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1380750618b0beacdc9b0a9e210a661e4746823ced7Chris Lattner /// isBuiltinNoteWarningOrExtension - Return true if the unmapped diagnostic 1390750618b0beacdc9b0a9e210a661e4746823ced7Chris Lattner /// level of the specified diagnostic ID is a Note, Warning, or Extension. 1400750618b0beacdc9b0a9e210a661e4746823ced7Chris Lattner /// Note that this only works on builtin diagnostics, not custom ones. 1410750618b0beacdc9b0a9e210a661e4746823ced7Chris Lattner static bool isBuiltinNoteWarningOrExtension(unsigned DiagID); 1425f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1435f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// getDiagnosticLevel - Based on the way the client configured the Diagnostic 1445f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// object, classify the specified diagnostic ID into a Level, consumable by 1455f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// the DiagnosticClient. 1465f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer Level getDiagnosticLevel(unsigned DiagID) const; 1475f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1485f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// Report - Issue the message to the client. DiagID is a member of the 1495f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// diag::kind enum. 1509c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek void Report(FullSourceLoc Pos, unsigned DiagID, 1515f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer const std::string *Strs = 0, unsigned NumStrs = 0, 1529c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek const SourceRange *Ranges = 0, unsigned NumRanges = 0); 1532eefd8657c233bc7c9330acfe475fc270bbe7cabTed Kremenek 1542eefd8657c233bc7c9330acfe475fc270bbe7cabTed Kremenek /// Report - Issue the message to the client. DiagID is a member of the 1552eefd8657c233bc7c9330acfe475fc270bbe7cabTed Kremenek /// diag::kind enum. 1569c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek void Report(unsigned DiagID, 1579c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek const std::string *Strs = 0, unsigned NumStrs = 0, 1589c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek const SourceRange *Ranges = 0, unsigned NumRanges = 0) { 1599c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek Report(FullSourceLoc(),DiagID,Strs,NumStrs,Ranges,NumRanges); 1602eefd8657c233bc7c9330acfe475fc270bbe7cabTed Kremenek } 1615f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer}; 1625f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1635f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer/// DiagnosticClient - This is an abstract interface implemented by clients of 1645f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer/// the front-end, which formats and prints fully processed diagnostics. 1655f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencerclass DiagnosticClient { 1665f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencerpublic: 1675f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer virtual ~DiagnosticClient(); 1685f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1695f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// IgnoreDiagnostic - If the client wants to ignore this diagnostic, then 1705f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// return true. 1715f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer virtual bool IgnoreDiagnostic(Diagnostic::Level DiagLevel, 1729c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek FullSourceLoc Pos) = 0; 1735f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1745f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// HandleDiagnostic - Handle this diagnostic, reporting it to the user or 1755f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer /// capturing it to a log as needed. 1760750618b0beacdc9b0a9e210a661e4746823ced7Chris Lattner virtual void HandleDiagnostic(Diagnostic &Diags, 1779c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek Diagnostic::Level DiagLevel, 1789c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek FullSourceLoc Pos, 1799c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek diag::kind ID, 1807a9d49fd2bfac00e905b361ba76d26ab5b6c3b09Ted Kremenek const std::string *Strs, 1819c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek unsigned NumStrs, 1829c728dc4d8da89c73fcae74c9e72d7a83ffd7b6dTed Kremenek const SourceRange *Ranges, 1835f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer unsigned NumRanges) = 0; 1845f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer}; 1855f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1865f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer} // end namespace clang 1875f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer 1885f016e2cb5d11daeb237544de1c5d59f20fe1a6eReid Spencer#endif 189