aboutsummaryrefslogtreecommitdiff
path: root/clang/lib/CodeGen/CodeGenAction.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'clang/lib/CodeGen/CodeGenAction.cpp')
-rw-r--r--clang/lib/CodeGen/CodeGenAction.cpp76
1 files changed, 65 insertions, 11 deletions
diff --git a/clang/lib/CodeGen/CodeGenAction.cpp b/clang/lib/CodeGen/CodeGenAction.cpp
index f8ae031..b8352781 100644
--- a/clang/lib/CodeGen/CodeGenAction.cpp
+++ b/clang/lib/CodeGen/CodeGenAction.cpp
@@ -23,6 +23,7 @@
#include "clang/Lex/Preprocessor.h"
#include "llvm/ADT/SmallString.h"
#include "llvm/Bitcode/ReaderWriter.h"
+#include "llvm/CodeGen/DiagnosticInfoCodeGen.h"
#include "llvm/IR/DebugInfo.h"
#include "llvm/IR/DiagnosticInfo.h"
#include "llvm/IR/DiagnosticPrinter.h"
@@ -242,6 +243,13 @@ namespace clang {
((BackendConsumer *)Context)->DiagnosticHandlerImpl(DI);
}
+ /// Get the best possible source location to represent a diagnostic that
+ /// may have associated debug info.
+ const FullSourceLoc
+ getBestLocationFromDebugLoc(const llvm::DiagnosticInfoWithDebugLocBase &D,
+ bool &BadDebugInfo, StringRef &Filename,
+ unsigned &Line, unsigned &Column) const;
+
void InlineAsmDiagHandler2(const llvm::SMDiagnostic &,
SourceLocation LocCookie);
@@ -254,6 +262,8 @@ namespace clang {
/// \return True if the diagnostic has been successfully reported, false
/// otherwise.
bool StackSizeDiagHandler(const llvm::DiagnosticInfoStackSize &D);
+ /// \brief Specialized handler for unsupported backend feature diagnostic.
+ void UnsupportedDiagHandler(const llvm::DiagnosticInfoUnsupported &D);
/// \brief Specialized handlers for optimization remarks.
/// Note that these handlers only accept remarks and they always handle
/// them.
@@ -439,16 +449,11 @@ BackendConsumer::StackSizeDiagHandler(const llvm::DiagnosticInfoStackSize &D) {
return false;
}
-void BackendConsumer::EmitOptimizationMessage(
- const llvm::DiagnosticInfoOptimizationBase &D, unsigned DiagID) {
- // We only support warnings and remarks.
- assert(D.getSeverity() == llvm::DS_Remark ||
- D.getSeverity() == llvm::DS_Warning);
-
+const FullSourceLoc BackendConsumer::getBestLocationFromDebugLoc(
+ const llvm::DiagnosticInfoWithDebugLocBase &D, bool &BadDebugInfo, StringRef &Filename,
+ unsigned &Line, unsigned &Column) const {
SourceManager &SourceMgr = Context->getSourceManager();
FileManager &FileMgr = SourceMgr.getFileManager();
- StringRef Filename;
- unsigned Line, Column;
SourceLocation DILoc;
if (D.isLocationAvailable()) {
@@ -459,6 +464,7 @@ void BackendConsumer::EmitOptimizationMessage(
// source manager, so pass 1 if Column is not set.
DILoc = SourceMgr.translateFileLineCol(FE, Line, Column ? Column : 1);
}
+ BadDebugInfo = DILoc.isInvalid();
}
// If a location isn't available, try to approximate it using the associated
@@ -467,18 +473,63 @@ void BackendConsumer::EmitOptimizationMessage(
FullSourceLoc Loc(DILoc, SourceMgr);
if (Loc.isInvalid())
if (const Decl *FD = Gen->GetDeclForMangledName(D.getFunction().getName()))
- Loc = FD->getASTContext().getFullLoc(FD->getBodyRBrace());
+ Loc = FD->getASTContext().getFullLoc(FD->getLocation());
+
+ if (DILoc.isInvalid() && D.isLocationAvailable())
+ // If we were not able to translate the file:line:col information
+ // back to a SourceLocation, at least emit a note stating that
+ // we could not translate this location. This can happen in the
+ // case of #line directives.
+ Diags.Report(Loc, diag::note_fe_backend_invalid_loc)
+ << Filename << Line;
+
+ return Loc;
+}
+
+void BackendConsumer::UnsupportedDiagHandler(
+ const llvm::DiagnosticInfoUnsupported &D) {
+ // We only support errors.
+ assert(D.getSeverity() == llvm::DS_Error);
+
+ StringRef Filename;
+ unsigned Line, Column;
+ bool BadDebugInfo;
+ FullSourceLoc Loc = getBestLocationFromDebugLoc(D, BadDebugInfo, Filename,
+ Line, Column);
+
+ Diags.Report(Loc, diag::err_fe_backend_unsupported) << D.getMessage().str();
+
+ if (BadDebugInfo)
+ // If we were not able to translate the file:line:col information
+ // back to a SourceLocation, at least emit a note stating that
+ // we could not translate this location. This can happen in the
+ // case of #line directives.
+ Diags.Report(Loc, diag::note_fe_backend_invalid_loc)
+ << Filename << Line << Column;
+}
+
+void BackendConsumer::EmitOptimizationMessage(
+ const llvm::DiagnosticInfoOptimizationBase &D, unsigned DiagID) {
+ // We only support warnings and remarks.
+ assert(D.getSeverity() == llvm::DS_Remark ||
+ D.getSeverity() == llvm::DS_Warning);
+
+ StringRef Filename;
+ unsigned Line, Column;
+ bool BadDebugInfo = false;
+ FullSourceLoc Loc = getBestLocationFromDebugLoc(D, BadDebugInfo, Filename,
+ Line, Column);
Diags.Report(Loc, DiagID)
<< AddFlagValue(D.getPassName() ? D.getPassName() : "")
<< D.getMsg().str();
- if (DILoc.isInvalid() && D.isLocationAvailable())
+ if (BadDebugInfo)
// If we were not able to translate the file:line:col information
// back to a SourceLocation, at least emit a note stating that
// we could not translate this location. This can happen in the
// case of #line directives.
- Diags.Report(Loc, diag::note_fe_backend_optimization_remark_invalid_loc)
+ Diags.Report(Loc, diag::note_fe_backend_invalid_loc)
<< Filename << Line << Column;
}
@@ -603,6 +654,9 @@ void BackendConsumer::DiagnosticHandlerImpl(const DiagnosticInfo &DI) {
// handler.
OptimizationFailureHandler(cast<DiagnosticInfoOptimizationFailure>(DI));
return;
+ case llvm::DK_Unsupported:
+ UnsupportedDiagHandler(cast<DiagnosticInfoUnsupported>(DI));
+ return;
default:
// Plugin IDs are not bound to any value as they are set dynamically.
ComputeDiagRemarkID(Severity, backend_plugin, DiagID);