Subversion Repositories QNX 8.QNX8 LLVM/Clang compiler suite

Rev

Blame | Last modification | View Log | Download | RSS feed

  1. //===- ScopDetectionDiagnostic.h - Diagnostic for ScopDetection -*- C++ -*-===//
  2. //
  3. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  4. // See https://llvm.org/LICENSE.txt for license information.
  5. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  6. //
  7. //===----------------------------------------------------------------------===//
  8. //
  9. // Small set of diagnostic helper classes to encapsulate any errors occurred
  10. // during the detection of Scops.
  11. //
  12. // The ScopDetection defines a set of error classes (via Statistic variables)
  13. // that groups a number of individual errors into a group, e.g. non-affinity
  14. // related errors.
  15. // On error we generate an object that carries enough additional information
  16. // to diagnose the error and generate a helpful error message.
  17. //
  18. //===----------------------------------------------------------------------===//
  19.  
  20. #ifndef POLLY_SCOPDETECTIONDIAGNOSTIC_H
  21. #define POLLY_SCOPDETECTIONDIAGNOSTIC_H
  22.  
  23. #include "llvm/Analysis/LoopInfo.h"
  24. #include "llvm/IR/DebugLoc.h"
  25. #include "llvm/IR/Instruction.h"
  26. #include <cstddef>
  27.  
  28. namespace llvm {
  29. class AliasSet;
  30. class BasicBlock;
  31. class OptimizationRemarkEmitter;
  32. class Region;
  33. class SCEV;
  34. } // namespace llvm
  35.  
  36. namespace polly {
  37. using llvm::AliasSet;
  38. using llvm::BasicBlock;
  39. using llvm::DebugLoc;
  40. using llvm::Instruction;
  41. using llvm::Loop;
  42. using llvm::OptimizationRemarkEmitter;
  43. using llvm::raw_ostream;
  44. using llvm::Region;
  45. using llvm::SCEV;
  46. using llvm::SmallVector;
  47. using llvm::Value;
  48.  
  49. /// Type to hold region delimiters (entry & exit block).
  50. using BBPair = std::pair<BasicBlock *, BasicBlock *>;
  51.  
  52. /// Return the region delimiters (entry & exit block) of @p R.
  53. BBPair getBBPairForRegion(const Region *R);
  54.  
  55. /// Set the begin and end source location for the region limited by @p P.
  56. void getDebugLocations(const BBPair &P, DebugLoc &Begin, DebugLoc &End);
  57.  
  58. class RejectLog;
  59.  
  60. /// Emit optimization remarks about the rejected regions to the user.
  61. ///
  62. /// This emits the content of the reject log as optimization remarks.
  63. /// Remember to at least track failures (-polly-detect-track-failures).
  64. /// @param P The region delimiters (entry & exit) we emit remarks for.
  65. /// @param Log The error log containing all messages being emitted as remark.
  66. void emitRejectionRemarks(const BBPair &P, const RejectLog &Log,
  67.                           OptimizationRemarkEmitter &ORE);
  68.  
  69. // Discriminator for LLVM-style RTTI (dyn_cast<> et al.)
  70. enum class RejectReasonKind {
  71.   // CFG Category
  72.   CFG,
  73.   InvalidTerminator,
  74.   IrreducibleRegion,
  75.   UnreachableInExit,
  76.   IndirectPredecessor,
  77.   LastCFG,
  78.  
  79.   // Non-Affinity
  80.   AffFunc,
  81.   UndefCond,
  82.   InvalidCond,
  83.   UndefOperand,
  84.   NonAffBranch,
  85.   NoBasePtr,
  86.   UndefBasePtr,
  87.   VariantBasePtr,
  88.   NonAffineAccess,
  89.   DifferentElementSize,
  90.   LastAffFunc,
  91.  
  92.   LoopBound,
  93.   LoopHasNoExit,
  94.   LoopHasMultipleExits,
  95.   LoopOnlySomeLatches,
  96.  
  97.   FuncCall,
  98.   NonSimpleMemoryAccess,
  99.  
  100.   Alias,
  101.  
  102.   // Other
  103.   Other,
  104.   IntToPtr,
  105.   Alloca,
  106.   UnknownInst,
  107.   Entry,
  108.   Unprofitable,
  109.   LastOther
  110. };
  111.  
  112. //===----------------------------------------------------------------------===//
  113. /// Base class of all reject reasons found during Scop detection.
  114. ///
  115. /// Subclasses of RejectReason should provide means to capture enough
  116. /// diagnostic information to help clients figure out what and where something
  117. /// went wrong in the Scop detection.
  118. class RejectReason {
  119. private:
  120.   const RejectReasonKind Kind;
  121.  
  122. protected:
  123.   static const DebugLoc Unknown;
  124.  
  125. public:
  126.   RejectReason(RejectReasonKind K);
  127.  
  128.   virtual ~RejectReason() = default;
  129.  
  130.   RejectReasonKind getKind() const { return Kind; }
  131.  
  132.   /// Generate the remark name to identify this remark.
  133.   ///
  134.   /// @return A short string that identifies the error.
  135.   virtual std::string getRemarkName() const = 0;
  136.  
  137.   /// Get the Basic Block containing this remark.
  138.   ///
  139.   /// @return The Basic Block containing this remark.
  140.   virtual const Value *getRemarkBB() const = 0;
  141.  
  142.   /// Generate a reasonable diagnostic message describing this error.
  143.   ///
  144.   /// @return A debug message representing this error.
  145.   virtual std::string getMessage() const = 0;
  146.  
  147.   /// Generate a message for the end-user describing this error.
  148.   ///
  149.   /// The message provided has to be suitable for the end-user. So it should
  150.   /// not reference any LLVM internal data structures or terminology.
  151.   /// Ideally, the message helps the end-user to increase the size of the
  152.   /// regions amenable to Polly.
  153.   ///
  154.   /// @return A short message representing this error.
  155.   virtual std::string getEndUserMessage() const { return "Unspecified error."; }
  156.  
  157.   /// Get the source location of this error.
  158.   ///
  159.   /// @return The debug location for this error.
  160.   virtual const DebugLoc &getDebugLoc() const;
  161. };
  162.  
  163. using RejectReasonPtr = std::shared_ptr<RejectReason>;
  164.  
  165. /// Stores all errors that occurred during the detection.
  166. class RejectLog final {
  167.   Region *R;
  168.   SmallVector<RejectReasonPtr, 1> ErrorReports;
  169.  
  170. public:
  171.   explicit RejectLog(Region *R) : R(R) {}
  172.  
  173.   using iterator = SmallVector<RejectReasonPtr, 1>::const_iterator;
  174.  
  175.   iterator begin() const { return ErrorReports.begin(); }
  176.   iterator end() const { return ErrorReports.end(); }
  177.   size_t size() const { return ErrorReports.size(); }
  178.  
  179.   /// Returns true, if we store at least one error.
  180.   ///
  181.   /// @return true, if we store at least one error.
  182.   bool hasErrors() const { return size() > 0; }
  183.  
  184.   void print(raw_ostream &OS, int level = 0) const;
  185.  
  186.   const Region *region() const { return R; }
  187.   void report(RejectReasonPtr Reject) { ErrorReports.push_back(Reject); }
  188. };
  189.  
  190. //===----------------------------------------------------------------------===//
  191. /// Base class for CFG related reject reasons.
  192. ///
  193. /// Scop candidates that violate structural restrictions can be grouped under
  194. /// this reject reason class.
  195. class ReportCFG : public RejectReason {
  196. public:
  197.   ReportCFG(const RejectReasonKind K);
  198.  
  199.   /// @name LLVM-RTTI interface
  200.   //@{
  201.   static bool classof(const RejectReason *RR);
  202.   //@}
  203. };
  204.  
  205. //===----------------------------------------------------------------------===//
  206. /// Captures bad terminator within a Scop candidate.
  207. class ReportInvalidTerminator final : public ReportCFG {
  208.   BasicBlock *BB;
  209.  
  210. public:
  211.   ReportInvalidTerminator(BasicBlock *BB)
  212.       : ReportCFG(RejectReasonKind::InvalidTerminator), BB(BB) {}
  213.  
  214.   /// @name LLVM-RTTI interface
  215.   //@{
  216.   static bool classof(const RejectReason *RR);
  217.   //@}
  218.  
  219.   /// @name RejectReason interface
  220.   //@{
  221.   std::string getRemarkName() const override;
  222.   const Value *getRemarkBB() const override;
  223.   std::string getMessage() const override;
  224.   const DebugLoc &getDebugLoc() const override;
  225.   //@}
  226. };
  227.  
  228. //===----------------------------------------------------------------------===//
  229. /// Captures irreducible regions in CFG.
  230. class ReportIrreducibleRegion final : public ReportCFG {
  231.   Region *R;
  232.   DebugLoc DbgLoc;
  233.  
  234. public:
  235.   ReportIrreducibleRegion(Region *R, DebugLoc DbgLoc)
  236.       : ReportCFG(RejectReasonKind::IrreducibleRegion), R(R), DbgLoc(DbgLoc) {}
  237.  
  238.   /// @name LLVM-RTTI interface
  239.   //@{
  240.   static bool classof(const RejectReason *RR);
  241.   //@}
  242.  
  243.   /// @name RejectReason interface
  244.   //@{
  245.   std::string getRemarkName() const override;
  246.   const Value *getRemarkBB() const override;
  247.   std::string getMessage() const override;
  248.   std::string getEndUserMessage() const override;
  249.   const DebugLoc &getDebugLoc() const override;
  250.   //@}
  251. };
  252.  
  253. //===----------------------------------------------------------------------===//
  254. /// Captures regions with an unreachable in the exit block.
  255. class ReportUnreachableInExit final : public ReportCFG {
  256.   BasicBlock *BB;
  257.   DebugLoc DbgLoc;
  258.  
  259. public:
  260.   ReportUnreachableInExit(BasicBlock *BB, DebugLoc DbgLoc)
  261.       : ReportCFG(RejectReasonKind::UnreachableInExit), BB(BB), DbgLoc(DbgLoc) {
  262.   }
  263.  
  264.   /// @name LLVM-RTTI interface
  265.   //@{
  266.   static bool classof(const RejectReason *RR);
  267.   //@}
  268.  
  269.   /// @name RejectReason interface
  270.   //@{
  271.   std::string getRemarkName() const override;
  272.   const Value *getRemarkBB() const override;
  273.   std::string getMessage() const override;
  274.   std::string getEndUserMessage() const override;
  275.   const DebugLoc &getDebugLoc() const override;
  276.   //@}
  277. };
  278.  
  279. //===----------------------------------------------------------------------===//
  280. /// Captures regions with an IndirectBr predecessor.
  281. class ReportIndirectPredecessor final : public ReportCFG {
  282.   Instruction *Inst;
  283.   DebugLoc DbgLoc;
  284.  
  285. public:
  286.   ReportIndirectPredecessor(Instruction *Inst, DebugLoc DbgLoc)
  287.       : ReportCFG(RejectReasonKind::IndirectPredecessor), Inst(Inst),
  288.         DbgLoc(DbgLoc) {}
  289.  
  290.   /// @name LLVM-RTTI interface
  291.   //@{
  292.   static bool classof(const RejectReason *RR);
  293.   //@}
  294.  
  295.   /// @name RejectReason interface
  296.   //@{
  297.   std::string getRemarkName() const override;
  298.   const Value *getRemarkBB() const override;
  299.   std::string getMessage() const override;
  300.   std::string getEndUserMessage() const override;
  301.   const DebugLoc &getDebugLoc() const override;
  302.   //@}
  303. };
  304.  
  305. //===----------------------------------------------------------------------===//
  306. /// Base class for non-affine reject reasons.
  307. ///
  308. /// Scop candidates that violate restrictions to affinity are reported under
  309. /// this class.
  310. class ReportAffFunc : public RejectReason {
  311. protected:
  312.   // The instruction that caused non-affinity to occur.
  313.   const Instruction *Inst;
  314.  
  315. public:
  316.   ReportAffFunc(const RejectReasonKind K, const Instruction *Inst);
  317.  
  318.   /// @name LLVM-RTTI interface
  319.   //@{
  320.   static bool classof(const RejectReason *RR);
  321.   //@}
  322.  
  323.   /// @name RejectReason interface
  324.   //@{
  325.   const DebugLoc &getDebugLoc() const override { return Inst->getDebugLoc(); }
  326.   //@}
  327. };
  328.  
  329. //===----------------------------------------------------------------------===//
  330. /// Captures a condition that is based on an 'undef' value.
  331. class ReportUndefCond final : public ReportAffFunc {
  332.   // The BasicBlock we found the broken condition in.
  333.   BasicBlock *BB;
  334.  
  335. public:
  336.   ReportUndefCond(const Instruction *Inst, BasicBlock *BB)
  337.       : ReportAffFunc(RejectReasonKind::UndefCond, Inst), BB(BB) {}
  338.  
  339.   /// @name LLVM-RTTI interface
  340.   //@{
  341.   static bool classof(const RejectReason *RR);
  342.   //@}
  343.  
  344.   /// @name RejectReason interface
  345.   //@{
  346.   std::string getRemarkName() const override;
  347.   const Value *getRemarkBB() const override;
  348.   std::string getMessage() const override;
  349.   //@}
  350. };
  351.  
  352. //===----------------------------------------------------------------------===//
  353. /// Captures an invalid condition
  354. ///
  355. /// Conditions have to be either constants or icmp instructions.
  356. class ReportInvalidCond final : public ReportAffFunc {
  357.   // The BasicBlock we found the broken condition in.
  358.   BasicBlock *BB;
  359.  
  360. public:
  361.   ReportInvalidCond(const Instruction *Inst, BasicBlock *BB)
  362.       : ReportAffFunc(RejectReasonKind::InvalidCond, Inst), BB(BB) {}
  363.  
  364.   /// @name LLVM-RTTI interface
  365.   //@{
  366.   static bool classof(const RejectReason *RR);
  367.   //@}
  368.  
  369.   /// @name RejectReason interface
  370.   //@{
  371.   std::string getRemarkName() const override;
  372.   const Value *getRemarkBB() const override;
  373.   std::string getMessage() const override;
  374.   //@}
  375. };
  376.  
  377. //===----------------------------------------------------------------------===//
  378. /// Captures an undefined operand.
  379. class ReportUndefOperand final : public ReportAffFunc {
  380.   // The BasicBlock we found the undefined operand in.
  381.   BasicBlock *BB;
  382.  
  383. public:
  384.   ReportUndefOperand(BasicBlock *BB, const Instruction *Inst)
  385.       : ReportAffFunc(RejectReasonKind::UndefOperand, Inst), BB(BB) {}
  386.  
  387.   /// @name LLVM-RTTI interface
  388.   //@{
  389.   static bool classof(const RejectReason *RR);
  390.   //@}
  391.  
  392.   /// @name RejectReason interface
  393.   //@{
  394.   std::string getRemarkName() const override;
  395.   const Value *getRemarkBB() const override;
  396.   std::string getMessage() const override;
  397.   //@}
  398. };
  399.  
  400. //===----------------------------------------------------------------------===//
  401. /// Captures a non-affine branch.
  402. class ReportNonAffBranch final : public ReportAffFunc {
  403.   // The BasicBlock we found the non-affine branch in.
  404.   BasicBlock *BB;
  405.  
  406.   /// LHS & RHS of the failed condition.
  407.   //@{
  408.   const SCEV *LHS;
  409.   const SCEV *RHS;
  410.   //@}
  411.  
  412. public:
  413.   ReportNonAffBranch(BasicBlock *BB, const SCEV *LHS, const SCEV *RHS,
  414.                      const Instruction *Inst)
  415.       : ReportAffFunc(RejectReasonKind::NonAffBranch, Inst), BB(BB), LHS(LHS),
  416.         RHS(RHS) {}
  417.  
  418.   const SCEV *lhs() { return LHS; }
  419.   const SCEV *rhs() { return RHS; }
  420.  
  421.   /// @name LLVM-RTTI interface
  422.   //@{
  423.   static bool classof(const RejectReason *RR);
  424.   //@}
  425.  
  426.   /// @name RejectReason interface
  427.   //@{
  428.   std::string getRemarkName() const override;
  429.   const Value *getRemarkBB() const override;
  430.   std::string getMessage() const override;
  431.   //@}
  432. };
  433.  
  434. //===----------------------------------------------------------------------===//
  435. /// Captures a missing base pointer.
  436. class ReportNoBasePtr final : public ReportAffFunc {
  437. public:
  438.   ReportNoBasePtr(const Instruction *Inst)
  439.       : ReportAffFunc(RejectReasonKind::NoBasePtr, Inst) {}
  440.  
  441.   /// @name LLVM-RTTI interface
  442.   //@{
  443.   static bool classof(const RejectReason *RR);
  444.   //@}
  445.  
  446.   /// @name RejectReason interface
  447.   //@{
  448.   std::string getRemarkName() const override;
  449.   const Value *getRemarkBB() const override;
  450.   std::string getMessage() const override;
  451.   //@}
  452. };
  453.  
  454. //===----------------------------------------------------------------------===//
  455. /// Captures an undefined base pointer.
  456. class ReportUndefBasePtr final : public ReportAffFunc {
  457. public:
  458.   ReportUndefBasePtr(const Instruction *Inst)
  459.       : ReportAffFunc(RejectReasonKind::UndefBasePtr, Inst) {}
  460.  
  461.   /// @name LLVM-RTTI interface
  462.   //@{
  463.   static bool classof(const RejectReason *RR);
  464.   //@}
  465.  
  466.   /// @name RejectReason interface
  467.   //@{
  468.   std::string getRemarkName() const override;
  469.   const Value *getRemarkBB() const override;
  470.   std::string getMessage() const override;
  471.   //@}
  472. };
  473.  
  474. //===----------------------------------------------------------------------===//
  475. /// Captures a base pointer that is not invariant in the region.
  476. class ReportVariantBasePtr final : public ReportAffFunc {
  477.   // The variant base pointer.
  478.   Value *BaseValue;
  479.  
  480. public:
  481.   ReportVariantBasePtr(Value *BaseValue, const Instruction *Inst)
  482.       : ReportAffFunc(RejectReasonKind::VariantBasePtr, Inst),
  483.         BaseValue(BaseValue) {}
  484.  
  485.   /// @name LLVM-RTTI interface
  486.   //@{
  487.   static bool classof(const RejectReason *RR);
  488.   //@}
  489.  
  490.   /// @name RejectReason interface
  491.   //@{
  492.   std::string getRemarkName() const override;
  493.   const Value *getRemarkBB() const override;
  494.   std::string getMessage() const override;
  495.   std::string getEndUserMessage() const override;
  496.   //@}
  497. };
  498.  
  499. //===----------------------------------------------------------------------===//
  500. /// Captures a non-affine access function.
  501. class ReportNonAffineAccess final : public ReportAffFunc {
  502.   // The non-affine access function.
  503.   const SCEV *AccessFunction;
  504.  
  505.   // The base pointer of the memory access.
  506.   const Value *BaseValue;
  507.  
  508. public:
  509.   ReportNonAffineAccess(const SCEV *AccessFunction, const Instruction *Inst,
  510.                         const Value *V)
  511.       : ReportAffFunc(RejectReasonKind::NonAffineAccess, Inst),
  512.         AccessFunction(AccessFunction), BaseValue(V) {}
  513.  
  514.   const SCEV *get() { return AccessFunction; }
  515.  
  516.   /// @name LLVM-RTTI interface
  517.   //@{
  518.   static bool classof(const RejectReason *RR);
  519.   //@}
  520.  
  521.   /// @name RejectReason interface
  522.   //@{
  523.   std::string getRemarkName() const override;
  524.   const Value *getRemarkBB() const override;
  525.   std::string getMessage() const override;
  526.   std::string getEndUserMessage() const override;
  527.   //@}
  528. };
  529.  
  530. //===----------------------------------------------------------------------===//
  531. /// Report array accesses with differing element size.
  532. class ReportDifferentArrayElementSize final : public ReportAffFunc {
  533.   // The base pointer of the memory access.
  534.   const Value *BaseValue;
  535.  
  536. public:
  537.   ReportDifferentArrayElementSize(const Instruction *Inst, const Value *V)
  538.       : ReportAffFunc(RejectReasonKind::DifferentElementSize, Inst),
  539.         BaseValue(V) {}
  540.  
  541.   /// @name LLVM-RTTI interface
  542.   //@{
  543.   static bool classof(const RejectReason *RR);
  544.   //@}
  545.  
  546.   /// @name RejectReason interface
  547.   //@{
  548.   std::string getRemarkName() const override;
  549.   const Value *getRemarkBB() const override;
  550.   std::string getMessage() const override;
  551.   std::string getEndUserMessage() const override;
  552.   //@}
  553. };
  554.  
  555. //===----------------------------------------------------------------------===//
  556. /// Captures errors with non affine loop bounds.
  557. class ReportLoopBound final : public RejectReason {
  558.   // The offending loop.
  559.   Loop *L;
  560.  
  561.   // The non-affine loop bound.
  562.   const SCEV *LoopCount;
  563.  
  564.   // A copy of the offending loop's debug location.
  565.   const DebugLoc Loc;
  566.  
  567. public:
  568.   ReportLoopBound(Loop *L, const SCEV *LoopCount);
  569.  
  570.   const SCEV *loopCount() { return LoopCount; }
  571.  
  572.   /// @name LLVM-RTTI interface
  573.   //@{
  574.   static bool classof(const RejectReason *RR);
  575.   //@}
  576.  
  577.   /// @name RejectReason interface
  578.   //@{
  579.   std::string getRemarkName() const override;
  580.   const Value *getRemarkBB() const override;
  581.   std::string getMessage() const override;
  582.   const DebugLoc &getDebugLoc() const override;
  583.   std::string getEndUserMessage() const override;
  584.   //@}
  585. };
  586.  
  587. //===----------------------------------------------------------------------===//
  588. /// Captures errors when loop has no exit.
  589. class ReportLoopHasNoExit final : public RejectReason {
  590.   /// The loop that has no exit.
  591.   Loop *L;
  592.  
  593.   const DebugLoc Loc;
  594.  
  595. public:
  596.   ReportLoopHasNoExit(Loop *L)
  597.       : RejectReason(RejectReasonKind::LoopHasNoExit), L(L),
  598.         Loc(L->getStartLoc()) {}
  599.  
  600.   /// @name LLVM-RTTI interface
  601.   //@{
  602.   static bool classof(const RejectReason *RR);
  603.   //@}
  604.  
  605.   /// @name RejectReason interface
  606.   //@{
  607.   std::string getRemarkName() const override;
  608.   const Value *getRemarkBB() const override;
  609.   std::string getMessage() const override;
  610.   const DebugLoc &getDebugLoc() const override;
  611.   std::string getEndUserMessage() const override;
  612.   //@}
  613. };
  614.  
  615. //===----------------------------------------------------------------------===//
  616. /// Captures errors when a loop has multiple exists.
  617. class ReportLoopHasMultipleExits final : public RejectReason {
  618.   /// The loop that has multiple exits.
  619.   Loop *L;
  620.  
  621.   const DebugLoc Loc;
  622.  
  623. public:
  624.   ReportLoopHasMultipleExits(Loop *L)
  625.       : RejectReason(RejectReasonKind::LoopHasMultipleExits), L(L),
  626.         Loc(L->getStartLoc()) {}
  627.  
  628.   /// @name LLVM-RTTI interface
  629.   //@{
  630.   static bool classof(const RejectReason *RR);
  631.   //@}
  632.  
  633.   /// @name RejectReason interface
  634.   //@{
  635.   std::string getRemarkName() const override;
  636.   const Value *getRemarkBB() const override;
  637.   std::string getMessage() const override;
  638.   const DebugLoc &getDebugLoc() const override;
  639.   std::string getEndUserMessage() const override;
  640.   //@}
  641. };
  642.  
  643. //===----------------------------------------------------------------------===//
  644. /// Captures errors when not all loop latches are part of the scop.
  645. class ReportLoopOnlySomeLatches final : public RejectReason {
  646.   /// The loop for which not all loop latches are part of the scop.
  647.   Loop *L;
  648.  
  649.   const DebugLoc Loc;
  650.  
  651. public:
  652.   ReportLoopOnlySomeLatches(Loop *L)
  653.       : RejectReason(RejectReasonKind::LoopOnlySomeLatches), L(L),
  654.         Loc(L->getStartLoc()) {}
  655.  
  656.   /// @name LLVM-RTTI interface
  657.   //@{
  658.   static bool classof(const RejectReason *RR);
  659.   //@}
  660.  
  661.   /// @name RejectReason interface
  662.   //@{
  663.   std::string getRemarkName() const override;
  664.   const Value *getRemarkBB() const override;
  665.   std::string getMessage() const override;
  666.   const DebugLoc &getDebugLoc() const override;
  667.   std::string getEndUserMessage() const override;
  668.   //@}
  669. };
  670.  
  671. //===----------------------------------------------------------------------===//
  672. /// Captures errors with non-side-effect-known function calls.
  673. class ReportFuncCall final : public RejectReason {
  674.   // The offending call instruction.
  675.   Instruction *Inst;
  676.  
  677. public:
  678.   ReportFuncCall(Instruction *Inst);
  679.  
  680.   /// @name LLVM-RTTI interface
  681.   //@{
  682.   static bool classof(const RejectReason *RR);
  683.   //@}
  684.  
  685.   /// @name RejectReason interface
  686.   //@{
  687.   std::string getRemarkName() const override;
  688.   const Value *getRemarkBB() const override;
  689.   std::string getMessage() const override;
  690.   const DebugLoc &getDebugLoc() const override;
  691.   std::string getEndUserMessage() const override;
  692.   //@}
  693. };
  694.  
  695. //===----------------------------------------------------------------------===//
  696. /// Captures errors with aliasing.
  697. class ReportAlias final : public RejectReason {
  698. public:
  699.   using PointerSnapshotTy = std::vector<const Value *>;
  700.  
  701. private:
  702.   /// Format an invalid alias set.
  703.   ///
  704.   //  @param Prefix A prefix string to put before the list of aliasing pointers.
  705.   //  @param Suffix A suffix string to put after the list of aliasing pointers.
  706.   std::string formatInvalidAlias(std::string Prefix = "",
  707.                                  std::string Suffix = "") const;
  708.  
  709.   Instruction *Inst;
  710.  
  711.   // A snapshot of the llvm values that took part in the aliasing error.
  712.   mutable PointerSnapshotTy Pointers;
  713.  
  714. public:
  715.   ReportAlias(Instruction *Inst, AliasSet &AS);
  716.  
  717.   const PointerSnapshotTy &getPointers() const { return Pointers; }
  718.  
  719.   /// @name LLVM-RTTI interface
  720.   //@{
  721.   static bool classof(const RejectReason *RR);
  722.   //@}
  723.  
  724.   /// @name RejectReason interface
  725.   //@{
  726.   std::string getRemarkName() const override;
  727.   const Value *getRemarkBB() const override;
  728.   std::string getMessage() const override;
  729.   const DebugLoc &getDebugLoc() const override;
  730.   std::string getEndUserMessage() const override;
  731.   //@}
  732. };
  733.  
  734. //===----------------------------------------------------------------------===//
  735. /// Base class for otherwise ungrouped reject reasons.
  736. class ReportOther : public RejectReason {
  737. public:
  738.   ReportOther(const RejectReasonKind K);
  739.  
  740.   /// @name LLVM-RTTI interface
  741.   //@{
  742.   static bool classof(const RejectReason *RR);
  743.   //@}
  744.  
  745.   /// @name RejectReason interface
  746.   //@{
  747.   std::string getRemarkName() const override;
  748.   std::string getMessage() const override;
  749.   //@}
  750. };
  751.  
  752. //===----------------------------------------------------------------------===//
  753. /// Captures errors with bad IntToPtr instructions.
  754. class ReportIntToPtr final : public ReportOther {
  755.   // The offending base value.
  756.   Instruction *BaseValue;
  757.  
  758. public:
  759.   ReportIntToPtr(Instruction *BaseValue);
  760.  
  761.   /// @name LLVM-RTTI interface
  762.   //@{
  763.   static bool classof(const RejectReason *RR);
  764.   //@}
  765.  
  766.   /// @name RejectReason interface
  767.   //@{
  768.   std::string getRemarkName() const override;
  769.   const Value *getRemarkBB() const override;
  770.   std::string getMessage() const override;
  771.   const DebugLoc &getDebugLoc() const override;
  772.   //@}
  773. };
  774.  
  775. //===----------------------------------------------------------------------===//
  776. /// Captures errors with alloca instructions.
  777. class ReportAlloca final : public ReportOther {
  778.   Instruction *Inst;
  779.  
  780. public:
  781.   ReportAlloca(Instruction *Inst);
  782.  
  783.   /// @name LLVM-RTTI interface
  784.   //@{
  785.   static bool classof(const RejectReason *RR);
  786.   //@}
  787.  
  788.   /// @name RejectReason interface
  789.   //@{
  790.   std::string getRemarkName() const override;
  791.   const Value *getRemarkBB() const override;
  792.   std::string getMessage() const override;
  793.   const DebugLoc &getDebugLoc() const override;
  794.   //@}
  795. };
  796.  
  797. //===----------------------------------------------------------------------===//
  798. /// Captures errors with unknown instructions.
  799. class ReportUnknownInst final : public ReportOther {
  800.   Instruction *Inst;
  801.  
  802. public:
  803.   ReportUnknownInst(Instruction *Inst);
  804.  
  805.   /// @name LLVM-RTTI interface
  806.   //@{
  807.   static bool classof(const RejectReason *RR);
  808.   //@}
  809.  
  810.   /// @name RejectReason interface
  811.   //@{
  812.   std::string getRemarkName() const override;
  813.   const Value *getRemarkBB() const override;
  814.   std::string getMessage() const override;
  815.   const DebugLoc &getDebugLoc() const override;
  816.   //@}
  817. };
  818.  
  819. //===----------------------------------------------------------------------===//
  820. /// Captures errors with regions containing the function entry block.
  821. class ReportEntry final : public ReportOther {
  822.   BasicBlock *BB;
  823.  
  824. public:
  825.   ReportEntry(BasicBlock *BB);
  826.  
  827.   /// @name LLVM-RTTI interface
  828.   //@{
  829.   static bool classof(const RejectReason *RR);
  830.   //@}
  831.  
  832.   /// @name RejectReason interface
  833.   //@{
  834.   std::string getRemarkName() const override;
  835.   const Value *getRemarkBB() const override;
  836.   std::string getMessage() const override;
  837.   std::string getEndUserMessage() const override;
  838.   const DebugLoc &getDebugLoc() const override;
  839.   //@}
  840. };
  841.  
  842. //===----------------------------------------------------------------------===//
  843. /// Report regions that seem not profitable to be optimized.
  844. class ReportUnprofitable final : public ReportOther {
  845.   Region *R;
  846.  
  847. public:
  848.   ReportUnprofitable(Region *R);
  849.  
  850.   /// @name LLVM-RTTI interface
  851.   //@{
  852.   static bool classof(const RejectReason *RR);
  853.   //@}
  854.  
  855.   /// @name RejectReason interface
  856.   //@{
  857.   std::string getRemarkName() const override;
  858.   const Value *getRemarkBB() const override;
  859.   std::string getMessage() const override;
  860.   std::string getEndUserMessage() const override;
  861.   const DebugLoc &getDebugLoc() const override;
  862.   //@}
  863. };
  864.  
  865. //===----------------------------------------------------------------------===//
  866. /// Captures errors with non-simple memory accesses.
  867. class ReportNonSimpleMemoryAccess final : public ReportOther {
  868.   // The offending call instruction.
  869.   Instruction *Inst;
  870.  
  871. public:
  872.   ReportNonSimpleMemoryAccess(Instruction *Inst);
  873.  
  874.   /// @name LLVM-RTTI interface
  875.   //@{
  876.   static bool classof(const RejectReason *RR);
  877.   //@}
  878.  
  879.   /// @name RejectReason interface
  880.   //@{
  881.   std::string getRemarkName() const override;
  882.   const Value *getRemarkBB() const override;
  883.   std::string getMessage() const override;
  884.   const DebugLoc &getDebugLoc() const override;
  885.   std::string getEndUserMessage() const override;
  886.   //@}
  887. };
  888. } // namespace polly
  889.  
  890. #endif // POLLY_SCOPDETECTIONDIAGNOSTIC_H
  891.