OSDN Git Service

Sort headers
[android-x86/external-llvm.git] / include / llvm / IR / DiagnosticInfo.h
1 //===- llvm/IR/DiagnosticInfo.h - Diagnostic Declaration --------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This file declares the different classes involved in low level diagnostics.
11 //
12 // Diagnostics reporting is still done as part of the LLVMContext.
13 //===----------------------------------------------------------------------===//
14
15 #ifndef LLVM_IR_DIAGNOSTICINFO_H
16 #define LLVM_IR_DIAGNOSTICINFO_H
17
18 #include "llvm-c/Types.h"
19 #include "llvm/ADT/Optional.h"
20 #include "llvm/ADT/StringRef.h"
21 #include "llvm/ADT/Twine.h"
22 #include "llvm/IR/DebugLoc.h"
23 #include "llvm/Support/CBindingWrapping.h"
24 #include <functional>
25 #include <string>
26
27 namespace llvm {
28
29 // Forward declarations.
30 class DiagnosticPrinter;
31 class Function;
32 class Instruction;
33 class LLVMContext;
34 class Module;
35 class SMDiagnostic;
36
37 /// \brief Defines the different supported severity of a diagnostic.
38 enum DiagnosticSeverity : char {
39   DS_Error,
40   DS_Warning,
41   DS_Remark,
42   // A note attaches additional information to one of the previous diagnostic
43   // types.
44   DS_Note
45 };
46
47 /// \brief Defines the different supported kind of a diagnostic.
48 /// This enum should be extended with a new ID for each added concrete subclass.
49 enum DiagnosticKind {
50   DK_Bitcode,
51   DK_InlineAsm,
52   DK_ResourceLimit,
53   DK_StackSize,
54   DK_Linker,
55   DK_DebugMetadataVersion,
56   DK_DebugMetadataInvalid,
57   DK_ISelFallback,
58   DK_SampleProfile,
59   DK_OptimizationRemark,
60   DK_OptimizationRemarkMissed,
61   DK_OptimizationRemarkAnalysis,
62   DK_OptimizationRemarkAnalysisFPCommute,
63   DK_OptimizationRemarkAnalysisAliasing,
64   DK_OptimizationFailure,
65   DK_FirstRemark = DK_OptimizationRemark,
66   DK_LastRemark = DK_OptimizationFailure,
67   DK_MIRParser,
68   DK_PGOProfile,
69   DK_Unsupported,
70   DK_FirstPluginKind
71 };
72
73 /// \brief Get the next available kind ID for a plugin diagnostic.
74 /// Each time this function is called, it returns a different number.
75 /// Therefore, a plugin that wants to "identify" its own classes
76 /// with a dynamic identifier, just have to use this method to get a new ID
77 /// and assign it to each of its classes.
78 /// The returned ID will be greater than or equal to DK_FirstPluginKind.
79 /// Thus, the plugin identifiers will not conflict with the
80 /// DiagnosticKind values.
81 int getNextAvailablePluginDiagnosticKind();
82
83 /// \brief This is the base abstract class for diagnostic reporting in
84 /// the backend.
85 /// The print method must be overloaded by the subclasses to print a
86 /// user-friendly message in the client of the backend (let us call it a
87 /// frontend).
88 class DiagnosticInfo {
89 private:
90   /// Kind defines the kind of report this is about.
91   const /* DiagnosticKind */ int Kind;
92   /// Severity gives the severity of the diagnostic.
93   const DiagnosticSeverity Severity;
94
95 public:
96   DiagnosticInfo(/* DiagnosticKind */ int Kind, DiagnosticSeverity Severity)
97       : Kind(Kind), Severity(Severity) {}
98
99   virtual ~DiagnosticInfo() {}
100
101   /* DiagnosticKind */ int getKind() const { return Kind; }
102   DiagnosticSeverity getSeverity() const { return Severity; }
103
104   /// Print using the given \p DP a user-friendly message.
105   /// This is the default message that will be printed to the user.
106   /// It is used when the frontend does not directly take advantage
107   /// of the information contained in fields of the subclasses.
108   /// The printed message must not end with '.' nor start with a severity
109   /// keyword.
110   virtual void print(DiagnosticPrinter &DP) const = 0;
111 };
112
113 typedef std::function<void(const DiagnosticInfo &)> DiagnosticHandlerFunction;
114
115 /// Diagnostic information for inline asm reporting.
116 /// This is basically a message and an optional location.
117 class DiagnosticInfoInlineAsm : public DiagnosticInfo {
118 private:
119   /// Optional line information. 0 if not set.
120   unsigned LocCookie;
121   /// Message to be reported.
122   const Twine &MsgStr;
123   /// Optional origin of the problem.
124   const Instruction *Instr;
125
126 public:
127   /// \p MsgStr is the message to be reported to the frontend.
128   /// This class does not copy \p MsgStr, therefore the reference must be valid
129   /// for the whole life time of the Diagnostic.
130   DiagnosticInfoInlineAsm(const Twine &MsgStr,
131                           DiagnosticSeverity Severity = DS_Error)
132       : DiagnosticInfo(DK_InlineAsm, Severity), LocCookie(0), MsgStr(MsgStr),
133         Instr(nullptr) {}
134
135   /// \p LocCookie if non-zero gives the line number for this report.
136   /// \p MsgStr gives the message.
137   /// This class does not copy \p MsgStr, therefore the reference must be valid
138   /// for the whole life time of the Diagnostic.
139   DiagnosticInfoInlineAsm(unsigned LocCookie, const Twine &MsgStr,
140                           DiagnosticSeverity Severity = DS_Error)
141       : DiagnosticInfo(DK_InlineAsm, Severity), LocCookie(LocCookie),
142         MsgStr(MsgStr), Instr(nullptr) {}
143
144   /// \p Instr gives the original instruction that triggered the diagnostic.
145   /// \p MsgStr gives the message.
146   /// This class does not copy \p MsgStr, therefore the reference must be valid
147   /// for the whole life time of the Diagnostic.
148   /// Same for \p I.
149   DiagnosticInfoInlineAsm(const Instruction &I, const Twine &MsgStr,
150                           DiagnosticSeverity Severity = DS_Error);
151
152   unsigned getLocCookie() const { return LocCookie; }
153   const Twine &getMsgStr() const { return MsgStr; }
154   const Instruction *getInstruction() const { return Instr; }
155
156   /// \see DiagnosticInfo::print.
157   void print(DiagnosticPrinter &DP) const override;
158
159   static bool classof(const DiagnosticInfo *DI) {
160     return DI->getKind() == DK_InlineAsm;
161   }
162 };
163
164 /// Diagnostic information for stack size etc. reporting.
165 /// This is basically a function and a size.
166 class DiagnosticInfoResourceLimit : public DiagnosticInfo {
167 private:
168   /// The function that is concerned by this resource limit diagnostic.
169   const Function &Fn;
170
171   /// Description of the resource type (e.g. stack size)
172   const char *ResourceName;
173
174   /// The computed size usage
175   uint64_t ResourceSize;
176
177   // Threshould passed
178   uint64_t ResourceLimit;
179
180 public:
181   /// \p The function that is concerned by this stack size diagnostic.
182   /// \p The computed stack size.
183   DiagnosticInfoResourceLimit(const Function &Fn,
184                               const char *ResourceName,
185                               uint64_t ResourceSize,
186                               DiagnosticSeverity Severity = DS_Warning,
187                               DiagnosticKind Kind = DK_ResourceLimit,
188                               uint64_t ResourceLimit = 0)
189       : DiagnosticInfo(Kind, Severity),
190         Fn(Fn),
191         ResourceName(ResourceName),
192         ResourceSize(ResourceSize),
193         ResourceLimit(ResourceLimit) {}
194
195   const Function &getFunction() const { return Fn; }
196   const char *getResourceName() const { return ResourceName; }
197   uint64_t getResourceSize() const { return ResourceSize; }
198   uint64_t getResourceLimit() const { return ResourceLimit; }
199
200   /// \see DiagnosticInfo::print.
201   void print(DiagnosticPrinter &DP) const override;
202
203   static bool classof(const DiagnosticInfo *DI) {
204     return DI->getKind() == DK_ResourceLimit ||
205            DI->getKind() == DK_StackSize;
206   }
207 };
208
209 class DiagnosticInfoStackSize : public DiagnosticInfoResourceLimit {
210 public:
211   DiagnosticInfoStackSize(const Function &Fn,
212                           uint64_t StackSize,
213                           DiagnosticSeverity Severity = DS_Warning,
214                           uint64_t StackLimit = 0)
215     : DiagnosticInfoResourceLimit(Fn, "stack size", StackSize,
216                                   Severity, DK_StackSize, StackLimit) {}
217
218   uint64_t getStackSize() const { return getResourceSize(); }
219   uint64_t getStackLimit() const { return getResourceLimit(); }
220
221   static bool classof(const DiagnosticInfo *DI) {
222     return DI->getKind() == DK_StackSize;
223   }
224 };
225
226 /// Diagnostic information for debug metadata version reporting.
227 /// This is basically a module and a version.
228 class DiagnosticInfoDebugMetadataVersion : public DiagnosticInfo {
229 private:
230   /// The module that is concerned by this debug metadata version diagnostic.
231   const Module &M;
232   /// The actual metadata version.
233   unsigned MetadataVersion;
234
235 public:
236   /// \p The module that is concerned by this debug metadata version diagnostic.
237   /// \p The actual metadata version.
238   DiagnosticInfoDebugMetadataVersion(const Module &M, unsigned MetadataVersion,
239                           DiagnosticSeverity Severity = DS_Warning)
240       : DiagnosticInfo(DK_DebugMetadataVersion, Severity), M(M),
241         MetadataVersion(MetadataVersion) {}
242
243   const Module &getModule() const { return M; }
244   unsigned getMetadataVersion() const { return MetadataVersion; }
245
246   /// \see DiagnosticInfo::print.
247   void print(DiagnosticPrinter &DP) const override;
248
249   static bool classof(const DiagnosticInfo *DI) {
250     return DI->getKind() == DK_DebugMetadataVersion;
251   }
252 };
253
254 /// Diagnostic information for stripping invalid debug metadata.
255 class DiagnosticInfoIgnoringInvalidDebugMetadata : public DiagnosticInfo {
256 private:
257   /// The module that is concerned by this debug metadata version diagnostic.
258   const Module &M;
259
260 public:
261   /// \p The module that is concerned by this debug metadata version diagnostic.
262   DiagnosticInfoIgnoringInvalidDebugMetadata(
263       const Module &M, DiagnosticSeverity Severity = DS_Warning)
264       : DiagnosticInfo(DK_DebugMetadataVersion, Severity), M(M) {}
265
266   const Module &getModule() const { return M; }
267
268   /// \see DiagnosticInfo::print.
269   void print(DiagnosticPrinter &DP) const override;
270
271   static bool classof(const DiagnosticInfo *DI) {
272     return DI->getKind() == DK_DebugMetadataInvalid;
273   }
274 };
275
276
277 /// Diagnostic information for the sample profiler.
278 class DiagnosticInfoSampleProfile : public DiagnosticInfo {
279 public:
280   DiagnosticInfoSampleProfile(StringRef FileName, unsigned LineNum,
281                               const Twine &Msg,
282                               DiagnosticSeverity Severity = DS_Error)
283       : DiagnosticInfo(DK_SampleProfile, Severity), FileName(FileName),
284         LineNum(LineNum), Msg(Msg) {}
285   DiagnosticInfoSampleProfile(StringRef FileName, const Twine &Msg,
286                               DiagnosticSeverity Severity = DS_Error)
287       : DiagnosticInfo(DK_SampleProfile, Severity), FileName(FileName),
288         LineNum(0), Msg(Msg) {}
289   DiagnosticInfoSampleProfile(const Twine &Msg,
290                               DiagnosticSeverity Severity = DS_Error)
291       : DiagnosticInfo(DK_SampleProfile, Severity), LineNum(0), Msg(Msg) {}
292
293   /// \see DiagnosticInfo::print.
294   void print(DiagnosticPrinter &DP) const override;
295
296   static bool classof(const DiagnosticInfo *DI) {
297     return DI->getKind() == DK_SampleProfile;
298   }
299
300   StringRef getFileName() const { return FileName; }
301   unsigned getLineNum() const { return LineNum; }
302   const Twine &getMsg() const { return Msg; }
303
304 private:
305   /// Name of the input file associated with this diagnostic.
306   StringRef FileName;
307
308   /// Line number where the diagnostic occurred. If 0, no line number will
309   /// be emitted in the message.
310   unsigned LineNum;
311
312   /// Message to report.
313   const Twine &Msg;
314 };
315
316 /// Diagnostic information for the PGO profiler.
317 class DiagnosticInfoPGOProfile : public DiagnosticInfo {
318 public:
319   DiagnosticInfoPGOProfile(const char *FileName, const Twine &Msg,
320                            DiagnosticSeverity Severity = DS_Error)
321       : DiagnosticInfo(DK_PGOProfile, Severity), FileName(FileName), Msg(Msg) {}
322
323   /// \see DiagnosticInfo::print.
324   void print(DiagnosticPrinter &DP) const override;
325
326   static bool classof(const DiagnosticInfo *DI) {
327     return DI->getKind() == DK_PGOProfile;
328   }
329
330   const char *getFileName() const { return FileName; }
331   const Twine &getMsg() const { return Msg; }
332
333 private:
334   /// Name of the input file associated with this diagnostic.
335   const char *FileName;
336
337   /// Message to report.
338   const Twine &Msg;
339 };
340
341 /// Common features for diagnostics with an associated DebugLoc
342 class DiagnosticInfoWithDebugLocBase : public DiagnosticInfo {
343 public:
344   /// \p Fn is the function where the diagnostic is being emitted. \p DLoc is
345   /// the location information to use in the diagnostic.
346   DiagnosticInfoWithDebugLocBase(enum DiagnosticKind Kind,
347                                  enum DiagnosticSeverity Severity,
348                                  const Function &Fn,
349                                  const DebugLoc &DLoc)
350       : DiagnosticInfo(Kind, Severity), Fn(Fn), DLoc(DLoc) {}
351
352   /// Return true if location information is available for this diagnostic.
353   bool isLocationAvailable() const;
354
355   /// Return a string with the location information for this diagnostic
356   /// in the format "file:line:col". If location information is not available,
357   /// it returns "<unknown>:0:0".
358   const std::string getLocationStr() const;
359
360   /// Return location information for this diagnostic in three parts:
361   /// the source file name, line number and column.
362   void getLocation(StringRef *Filename, unsigned *Line, unsigned *Column) const;
363
364   const Function &getFunction() const { return Fn; }
365   const DebugLoc &getDebugLoc() const { return DLoc; }
366
367 private:
368   /// Function where this diagnostic is triggered.
369   const Function &Fn;
370
371   /// Debug location where this diagnostic is triggered.
372   DebugLoc DLoc;
373 };
374
375 /// Common features for diagnostics dealing with optimization remarks.
376 class DiagnosticInfoOptimizationBase : public DiagnosticInfoWithDebugLocBase {
377 public:
378   /// \p PassName is the name of the pass emitting this diagnostic.
379   /// \p Fn is the function where the diagnostic is being emitted. \p DLoc is
380   /// the location information to use in the diagnostic. If line table
381   /// information is available, the diagnostic will include the source code
382   /// location. \p Msg is the message to show. Note that this class does not
383   /// copy this message, so this reference must be valid for the whole life time
384   /// of the diagnostic.
385   DiagnosticInfoOptimizationBase(enum DiagnosticKind Kind,
386                                  enum DiagnosticSeverity Severity,
387                                  const char *PassName, const Function &Fn,
388                                  const DebugLoc &DLoc, const Twine &Msg,
389                                  Optional<uint64_t> Hotness = None)
390       : DiagnosticInfoWithDebugLocBase(Kind, Severity, Fn, DLoc),
391         PassName(PassName), Msg(Msg), Hotness(Hotness) {}
392
393   /// \see DiagnosticInfo::print.
394   void print(DiagnosticPrinter &DP) const override;
395
396   /// Return true if this optimization remark is enabled by one of
397   /// of the LLVM command line flags (-pass-remarks, -pass-remarks-missed,
398   /// or -pass-remarks-analysis). Note that this only handles the LLVM
399   /// flags. We cannot access Clang flags from here (they are handled
400   /// in BackendConsumer::OptimizationRemarkHandler).
401   virtual bool isEnabled() const = 0;
402
403   const char *getPassName() const { return PassName; }
404   const Twine &getMsg() const { return Msg; }
405   Optional<uint64_t> getHotness() const { return Hotness; }
406
407   static bool classof(const DiagnosticInfo *DI) {
408     return DI->getKind() >= DK_FirstRemark &&
409            DI->getKind() <= DK_LastRemark;
410   }
411
412 private:
413   /// Name of the pass that triggers this report. If this matches the
414   /// regular expression given in -Rpass=regexp, then the remark will
415   /// be emitted.
416   const char *PassName;
417
418   /// Message to report.
419   const Twine &Msg;
420
421   /// If profile information is available, this is the number of times the
422   /// corresponding code was executed in a profile instrumentation run.
423   Optional<uint64_t> Hotness;
424 };
425
426 /// Diagnostic information for applied optimization remarks.
427 class DiagnosticInfoOptimizationRemark : public DiagnosticInfoOptimizationBase {
428 public:
429   /// \p PassName is the name of the pass emitting this diagnostic. If
430   /// this name matches the regular expression given in -Rpass=, then the
431   /// diagnostic will be emitted. \p Fn is the function where the diagnostic
432   /// is being emitted. \p DLoc is the location information to use in the
433   /// diagnostic. If line table information is available, the diagnostic
434   /// will include the source code location. \p Msg is the message to show.
435   /// Note that this class does not copy this message, so this reference
436   /// must be valid for the whole life time of the diagnostic.
437   DiagnosticInfoOptimizationRemark(const char *PassName, const Function &Fn,
438                                    const DebugLoc &DLoc, const Twine &Msg,
439                                    Optional<uint64_t> Hotness = None)
440       : DiagnosticInfoOptimizationBase(DK_OptimizationRemark, DS_Remark,
441                                        PassName, Fn, DLoc, Msg, Hotness) {}
442
443   static bool classof(const DiagnosticInfo *DI) {
444     return DI->getKind() == DK_OptimizationRemark;
445   }
446
447   /// \see DiagnosticInfoOptimizationBase::isEnabled.
448   bool isEnabled() const override;
449 };
450
451 /// Diagnostic information for missed-optimization remarks.
452 class DiagnosticInfoOptimizationRemarkMissed
453     : public DiagnosticInfoOptimizationBase {
454 public:
455   /// \p PassName is the name of the pass emitting this diagnostic. If
456   /// this name matches the regular expression given in -Rpass-missed=, then the
457   /// diagnostic will be emitted. \p Fn is the function where the diagnostic
458   /// is being emitted. \p DLoc is the location information to use in the
459   /// diagnostic. If line table information is available, the diagnostic
460   /// will include the source code location. \p Msg is the message to show.
461   /// Note that this class does not copy this message, so this reference
462   /// must be valid for the whole life time of the diagnostic.
463   DiagnosticInfoOptimizationRemarkMissed(const char *PassName,
464                                          const Function &Fn,
465                                          const DebugLoc &DLoc, const Twine &Msg,
466                                          Optional<uint64_t> Hotness = None)
467       : DiagnosticInfoOptimizationBase(DK_OptimizationRemarkMissed, DS_Remark,
468                                        PassName, Fn, DLoc, Msg, Hotness) {}
469
470   static bool classof(const DiagnosticInfo *DI) {
471     return DI->getKind() == DK_OptimizationRemarkMissed;
472   }
473
474   /// \see DiagnosticInfoOptimizationBase::isEnabled.
475   bool isEnabled() const override;
476 };
477
478 /// Diagnostic information for optimization analysis remarks.
479 class DiagnosticInfoOptimizationRemarkAnalysis
480     : public DiagnosticInfoOptimizationBase {
481 public:
482   /// \p PassName is the name of the pass emitting this diagnostic. If
483   /// this name matches the regular expression given in -Rpass-analysis=, then
484   /// the diagnostic will be emitted. \p Fn is the function where the diagnostic
485   /// is being emitted. \p DLoc is the location information to use in the
486   /// diagnostic. If line table information is available, the diagnostic will
487   /// include the source code location. \p Msg is the message to show. Note that
488   /// this class does not copy this message, so this reference must be valid for
489   /// the whole life time of the diagnostic.
490   DiagnosticInfoOptimizationRemarkAnalysis(const char *PassName,
491                                            const Function &Fn,
492                                            const DebugLoc &DLoc,
493                                            const Twine &Msg,
494                                            Optional<uint64_t> Hotness = None)
495       : DiagnosticInfoOptimizationBase(DK_OptimizationRemarkAnalysis, DS_Remark,
496                                        PassName, Fn, DLoc, Msg, Hotness) {}
497
498   static bool classof(const DiagnosticInfo *DI) {
499     return DI->getKind() == DK_OptimizationRemarkAnalysis;
500   }
501
502   /// \see DiagnosticInfoOptimizationBase::isEnabled.
503   bool isEnabled() const override;
504
505   static const char *AlwaysPrint;
506
507   bool shouldAlwaysPrint() const { return getPassName() == AlwaysPrint; }
508
509 protected:
510   DiagnosticInfoOptimizationRemarkAnalysis(
511       enum DiagnosticKind Kind, const char *PassName, const Function &Fn,
512       const DebugLoc &DLoc, const Twine &Msg, Optional<uint64_t> Hotness)
513       : DiagnosticInfoOptimizationBase(Kind, DS_Remark, PassName, Fn, DLoc, Msg,
514                                        Hotness) {}
515 };
516
517 /// Diagnostic information for optimization analysis remarks related to
518 /// floating-point non-commutativity.
519 class DiagnosticInfoOptimizationRemarkAnalysisFPCommute
520     : public DiagnosticInfoOptimizationRemarkAnalysis {
521 public:
522   /// \p PassName is the name of the pass emitting this diagnostic. If
523   /// this name matches the regular expression given in -Rpass-analysis=, then
524   /// the diagnostic will be emitted. \p Fn is the function where the diagnostic
525   /// is being emitted. \p DLoc is the location information to use in the
526   /// diagnostic. If line table information is available, the diagnostic will
527   /// include the source code location. \p Msg is the message to show. The
528   /// front-end will append its own message related to options that address
529   /// floating-point non-commutativity. Note that this class does not copy this
530   /// message, so this reference must be valid for the whole life time of the
531   /// diagnostic.
532   DiagnosticInfoOptimizationRemarkAnalysisFPCommute(
533       const char *PassName, const Function &Fn, const DebugLoc &DLoc,
534       const Twine &Msg, Optional<uint64_t> Hotness = None)
535       : DiagnosticInfoOptimizationRemarkAnalysis(
536             DK_OptimizationRemarkAnalysisFPCommute, PassName, Fn, DLoc, Msg,
537             Hotness) {}
538
539   static bool classof(const DiagnosticInfo *DI) {
540     return DI->getKind() == DK_OptimizationRemarkAnalysisFPCommute;
541   }
542 };
543
544 /// Diagnostic information for optimization analysis remarks related to
545 /// pointer aliasing.
546 class DiagnosticInfoOptimizationRemarkAnalysisAliasing
547     : public DiagnosticInfoOptimizationRemarkAnalysis {
548 public:
549   /// \p PassName is the name of the pass emitting this diagnostic. If
550   /// this name matches the regular expression given in -Rpass-analysis=, then
551   /// the diagnostic will be emitted. \p Fn is the function where the diagnostic
552   /// is being emitted. \p DLoc is the location information to use in the
553   /// diagnostic. If line table information is available, the diagnostic will
554   /// include the source code location. \p Msg is the message to show. The
555   /// front-end will append its own message related to options that address
556   /// pointer aliasing legality. Note that this class does not copy this
557   /// message, so this reference must be valid for the whole life time of the
558   /// diagnostic.
559   DiagnosticInfoOptimizationRemarkAnalysisAliasing(
560       const char *PassName, const Function &Fn, const DebugLoc &DLoc,
561       const Twine &Msg, Optional<uint64_t> Hotness = None)
562       : DiagnosticInfoOptimizationRemarkAnalysis(
563             DK_OptimizationRemarkAnalysisAliasing, PassName, Fn, DLoc, Msg,
564             Hotness) {}
565
566   static bool classof(const DiagnosticInfo *DI) {
567     return DI->getKind() == DK_OptimizationRemarkAnalysisAliasing;
568   }
569 };
570
571 /// Diagnostic information for machine IR parser.
572 class DiagnosticInfoMIRParser : public DiagnosticInfo {
573   const SMDiagnostic &Diagnostic;
574
575 public:
576   DiagnosticInfoMIRParser(DiagnosticSeverity Severity,
577                           const SMDiagnostic &Diagnostic)
578       : DiagnosticInfo(DK_MIRParser, Severity), Diagnostic(Diagnostic) {}
579
580   const SMDiagnostic &getDiagnostic() const { return Diagnostic; }
581
582   void print(DiagnosticPrinter &DP) const override;
583
584   static bool classof(const DiagnosticInfo *DI) {
585     return DI->getKind() == DK_MIRParser;
586   }
587 };
588
589 /// Diagnostic information for ISel fallback path.
590 class DiagnosticInfoISelFallback : public DiagnosticInfo {
591   /// The function that is concerned by this diagnostic.
592   const Function &Fn;
593
594 public:
595   DiagnosticInfoISelFallback(const Function &Fn,
596                              DiagnosticSeverity Severity = DS_Warning)
597       : DiagnosticInfo(DK_ISelFallback, Severity), Fn(Fn) {}
598
599   const Function &getFunction() const { return Fn; }
600
601   void print(DiagnosticPrinter &DP) const override;
602
603   static bool classof(const DiagnosticInfo *DI) {
604     return DI->getKind() == DK_ISelFallback;
605   }
606 };
607
608 // Create wrappers for C Binding types (see CBindingWrapping.h).
609 DEFINE_SIMPLE_CONVERSION_FUNCTIONS(DiagnosticInfo, LLVMDiagnosticInfoRef)
610
611 /// Emit an optimization-applied message. \p PassName is the name of the pass
612 /// emitting the message. If -Rpass= is given and \p PassName matches the
613 /// regular expression in -Rpass, then the remark will be emitted. \p Fn is
614 /// the function triggering the remark, \p DLoc is the debug location where
615 /// the diagnostic is generated. \p Msg is the message string to use.
616 void emitOptimizationRemark(LLVMContext &Ctx, const char *PassName,
617                             const Function &Fn, const DebugLoc &DLoc,
618                             const Twine &Msg);
619
620 /// Emit an optimization-missed message. \p PassName is the name of the
621 /// pass emitting the message. If -Rpass-missed= is given and \p PassName
622 /// matches the regular expression in -Rpass, then the remark will be
623 /// emitted. \p Fn is the function triggering the remark, \p DLoc is the
624 /// debug location where the diagnostic is generated. \p Msg is the
625 /// message string to use.
626 void emitOptimizationRemarkMissed(LLVMContext &Ctx, const char *PassName,
627                                   const Function &Fn, const DebugLoc &DLoc,
628                                   const Twine &Msg);
629
630 /// Emit an optimization analysis remark message. \p PassName is the name of
631 /// the pass emitting the message. If -Rpass-analysis= is given and \p
632 /// PassName matches the regular expression in -Rpass, then the remark will be
633 /// emitted. \p Fn is the function triggering the remark, \p DLoc is the debug
634 /// location where the diagnostic is generated. \p Msg is the message string
635 /// to use.
636 void emitOptimizationRemarkAnalysis(LLVMContext &Ctx, const char *PassName,
637                                     const Function &Fn, const DebugLoc &DLoc,
638                                     const Twine &Msg);
639
640 /// Emit an optimization analysis remark related to messages about
641 /// floating-point non-commutativity. \p PassName is the name of the pass
642 /// emitting the message. If -Rpass-analysis= is given and \p PassName matches
643 /// the regular expression in -Rpass, then the remark will be emitted. \p Fn is
644 /// the function triggering the remark, \p DLoc is the debug location where the
645 /// diagnostic is generated. \p Msg is the message string to use.
646 void emitOptimizationRemarkAnalysisFPCommute(LLVMContext &Ctx,
647                                              const char *PassName,
648                                              const Function &Fn,
649                                              const DebugLoc &DLoc,
650                                              const Twine &Msg);
651
652 /// Emit an optimization analysis remark related to messages about
653 /// pointer aliasing. \p PassName is the name of the pass emitting the message.
654 /// If -Rpass-analysis= is given and \p PassName matches the regular expression
655 /// in -Rpass, then the remark will be emitted. \p Fn is the function triggering
656 /// the remark, \p DLoc is the debug location where the diagnostic is generated.
657 /// \p Msg is the message string to use.
658 void emitOptimizationRemarkAnalysisAliasing(LLVMContext &Ctx,
659                                             const char *PassName,
660                                             const Function &Fn,
661                                             const DebugLoc &DLoc,
662                                             const Twine &Msg);
663
664 /// Diagnostic information for optimization failures.
665 class DiagnosticInfoOptimizationFailure
666     : public DiagnosticInfoOptimizationBase {
667 public:
668   /// \p Fn is the function where the diagnostic is being emitted. \p DLoc is
669   /// the location information to use in the diagnostic. If line table
670   /// information is available, the diagnostic will include the source code
671   /// location. \p Msg is the message to show. Note that this class does not
672   /// copy this message, so this reference must be valid for the whole life time
673   /// of the diagnostic.
674   DiagnosticInfoOptimizationFailure(const Function &Fn, const DebugLoc &DLoc,
675                                     const Twine &Msg)
676       : DiagnosticInfoOptimizationBase(DK_OptimizationFailure, DS_Warning,
677                                        nullptr, Fn, DLoc, Msg) {}
678
679   static bool classof(const DiagnosticInfo *DI) {
680     return DI->getKind() == DK_OptimizationFailure;
681   }
682
683   /// \see DiagnosticInfoOptimizationBase::isEnabled.
684   bool isEnabled() const override;
685 };
686
687 /// Diagnostic information for unsupported feature in backend.
688 class DiagnosticInfoUnsupported
689     : public DiagnosticInfoWithDebugLocBase {
690 private:
691   Twine Msg;
692
693 public:
694   /// \p Fn is the function where the diagnostic is being emitted. \p DLoc is
695   /// the location information to use in the diagnostic. If line table
696   /// information is available, the diagnostic will include the source code
697   /// location. \p Msg is the message to show. Note that this class does not
698   /// copy this message, so this reference must be valid for the whole life time
699   /// of the diagnostic.
700   DiagnosticInfoUnsupported(const Function &Fn, const Twine &Msg,
701                             DebugLoc DLoc = DebugLoc(),
702                             DiagnosticSeverity Severity = DS_Error)
703       : DiagnosticInfoWithDebugLocBase(DK_Unsupported, Severity, Fn, DLoc),
704         Msg(Msg) {}
705
706   static bool classof(const DiagnosticInfo *DI) {
707     return DI->getKind() == DK_Unsupported;
708   }
709
710   const Twine &getMessage() const { return Msg; }
711
712   void print(DiagnosticPrinter &DP) const override;
713 };
714
715 /// Emit a warning when loop vectorization is specified but fails. \p Fn is the
716 /// function triggering the warning, \p DLoc is the debug location where the
717 /// diagnostic is generated. \p Msg is the message string to use.
718 void emitLoopVectorizeWarning(LLVMContext &Ctx, const Function &Fn,
719                               const DebugLoc &DLoc, const Twine &Msg);
720
721 /// Emit a warning when loop interleaving is specified but fails. \p Fn is the
722 /// function triggering the warning, \p DLoc is the debug location where the
723 /// diagnostic is generated. \p Msg is the message string to use.
724 void emitLoopInterleaveWarning(LLVMContext &Ctx, const Function &Fn,
725                                const DebugLoc &DLoc, const Twine &Msg);
726
727 } // end namespace llvm
728
729 #endif // LLVM_IR_DIAGNOSTICINFO_H