xref: /llvm-project/flang/include/flang/Lower/DumpEvaluateExpr.h (revision 77d8cfb3c50e3341d65af1f9e442004bbd77af9b)
1 //===-- Lower/DumpEvaluateExpr.h --------------------------------*- 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 #ifndef FORTRAN_LOWER_DUMPEVALUATEEXPR_H
10 #define FORTRAN_LOWER_DUMPEVALUATEEXPR_H
11 
12 #include "flang/Evaluate/tools.h"
13 #include "flang/Lower/Support/Utils.h"
14 #include "llvm/ADT/StringRef.h"
15 #include "llvm/ADT/Twine.h"
16 
17 namespace Fortran::lower {
18 
19 /// Class to dump Fortran::evaluate::Expr trees out in a user readable way.
20 ///
21 /// FIXME: This can be improved to dump more information in some cases.
22 class DumpEvaluateExpr {
23 public:
DumpEvaluateExpr()24   DumpEvaluateExpr() : outs(llvm::errs()) {}
DumpEvaluateExpr(llvm::raw_ostream & str)25   DumpEvaluateExpr(llvm::raw_ostream &str) : outs(str) {}
26 
27   template <typename A>
dump(const A & x)28   static void dump(const A &x) {
29     DumpEvaluateExpr{}.show(x);
30   }
31   template <typename A>
dump(llvm::raw_ostream & stream,const A & x)32   static void dump(llvm::raw_ostream &stream, const A &x) {
33     DumpEvaluateExpr{stream}.show(x);
34   }
35 
36 private:
37   template <typename A, bool C>
show(const Fortran::common::Indirection<A,C> & x)38   void show(const Fortran::common::Indirection<A, C> &x) {
39     show(x.value());
40   }
41   template <typename A>
show(const Fortran::semantics::SymbolRef x)42   void show(const Fortran::semantics::SymbolRef x) {
43     show(*x);
44   }
45   template <typename A>
show(const std::unique_ptr<A> & x)46   void show(const std::unique_ptr<A> &x) {
47     show(x.get());
48   }
49   template <typename A>
show(const std::shared_ptr<A> & x)50   void show(const std::shared_ptr<A> &x) {
51     show(x.get());
52   }
53   template <typename A>
show(const A * x)54   void show(const A *x) {
55     if (x) {
56       show(*x);
57       return;
58     }
59     print("nullptr");
60   }
61   template <typename A>
show(const std::optional<A> & x)62   void show(const std::optional<A> &x) {
63     if (x) {
64       show(*x);
65       return;
66     }
67     print("None");
68   }
69   template <typename... A>
show(const std::variant<A...> & u)70   void show(const std::variant<A...> &u) {
71     Fortran::common::visit([&](const auto &v) { show(v); }, u);
72   }
73   template <typename A>
show(const std::vector<A> & x)74   void show(const std::vector<A> &x) {
75     indent("vector");
76     for (const auto &v : x)
77       show(v);
78     outdent();
79   }
80   void show(const Fortran::evaluate::BOZLiteralConstant &);
81   void show(const Fortran::evaluate::NullPointer &);
82   template <typename T>
show(const Fortran::evaluate::Constant<T> & x)83   void show(const Fortran::evaluate::Constant<T> &x) {
84     if constexpr (T::category == Fortran::common::TypeCategory::Derived) {
85       indent("derived constant");
86       for (const auto &map : x.values())
87         for (const auto &pair : map)
88           show(pair.second.value());
89       outdent();
90     } else {
91       print("constant");
92     }
93   }
94   void show(const Fortran::semantics::Symbol &symbol);
95   void show(const Fortran::evaluate::StaticDataObject &);
96   void show(const Fortran::evaluate::ImpliedDoIndex &);
97   void show(const Fortran::evaluate::BaseObject &x);
98   void show(const Fortran::evaluate::Component &x);
99   void show(const Fortran::evaluate::NamedEntity &x);
100   void show(const Fortran::evaluate::TypeParamInquiry &x);
101   void show(const Fortran::evaluate::Triplet &x);
102   void show(const Fortran::evaluate::Subscript &x);
103   void show(const Fortran::evaluate::ArrayRef &x);
104   void show(const Fortran::evaluate::CoarrayRef &x);
105   void show(const Fortran::evaluate::DataRef &x);
106   void show(const Fortran::evaluate::Substring &x);
107   void show(const Fortran::evaluate::ComplexPart &x);
108   template <typename T>
show(const Fortran::evaluate::Designator<T> & x)109   void show(const Fortran::evaluate::Designator<T> &x) {
110     indent("designator");
111     show(x.u);
112     outdent();
113   }
114   template <typename T>
show(const Fortran::evaluate::Variable<T> & x)115   void show(const Fortran::evaluate::Variable<T> &x) {
116     indent("variable");
117     show(x.u);
118     outdent();
119   }
120   void show(const Fortran::evaluate::DescriptorInquiry &x);
121   void show(const Fortran::evaluate::SpecificIntrinsic &);
122   void show(const Fortran::evaluate::ProcedureDesignator &x);
123   void show(const Fortran::evaluate::ActualArgument &x);
show(const Fortran::evaluate::ProcedureRef & x)124   void show(const Fortran::evaluate::ProcedureRef &x) {
125     indent("procedure ref");
126     show(x.proc());
127     show(x.arguments());
128     outdent();
129   }
130   template <typename T>
show(const Fortran::evaluate::FunctionRef<T> & x)131   void show(const Fortran::evaluate::FunctionRef<T> &x) {
132     indent("function ref");
133     show(x.proc());
134     show(x.arguments());
135     outdent();
136   }
137   template <typename T>
show(const Fortran::evaluate::ArrayConstructorValue<T> & x)138   void show(const Fortran::evaluate::ArrayConstructorValue<T> &x) {
139     show(x.u);
140   }
141   template <typename T>
show(const Fortran::evaluate::ArrayConstructorValues<T> & x)142   void show(const Fortran::evaluate::ArrayConstructorValues<T> &x) {
143     indent("array constructor value");
144     for (auto &v : x)
145       show(v);
146     outdent();
147   }
148   template <typename T>
show(const Fortran::evaluate::ImpliedDo<T> & x)149   void show(const Fortran::evaluate::ImpliedDo<T> &x) {
150     indent("implied do");
151     show(x.lower());
152     show(x.upper());
153     show(x.stride());
154     show(x.values());
155     outdent();
156   }
157   void show(const Fortran::semantics::ParamValue &x);
158   void
159   show(const Fortran::semantics::DerivedTypeSpec::ParameterMapType::value_type
160            &x);
161   void show(const Fortran::semantics::DerivedTypeSpec &x);
162   void show(const Fortran::evaluate::StructureConstructorValues::value_type &x);
163   void show(const Fortran::evaluate::StructureConstructor &x);
164   template <typename D, typename R, typename O>
show(const Fortran::evaluate::Operation<D,R,O> & op)165   void show(const Fortran::evaluate::Operation<D, R, O> &op) {
166     indent("unary op");
167     show(op.left());
168     outdent();
169   }
170   template <typename D, typename R, typename LO, typename RO>
show(const Fortran::evaluate::Operation<D,R,LO,RO> & op)171   void show(const Fortran::evaluate::Operation<D, R, LO, RO> &op) {
172     indent("binary op");
173     show(op.left());
174     show(op.right());
175     outdent();
176   }
177   void
178   show(const Fortran::evaluate::Relational<Fortran::evaluate::SomeType> &x);
179   template <typename T>
show(const Fortran::evaluate::Expr<T> & x)180   void show(const Fortran::evaluate::Expr<T> &x) {
181     indent("expr T");
182     show(x.u);
183     outdent();
184   }
185 
186   const char *getIndentString() const;
187   void print(llvm::Twine s);
188   void indent(llvm::StringRef s);
189   void outdent();
190 
191   llvm::raw_ostream &outs;
192   unsigned level = 0;
193 };
194 
195 LLVM_DUMP_METHOD void
196 dumpEvExpr(const Fortran::evaluate::Expr<Fortran::evaluate::SomeType> &x);
197 LLVM_DUMP_METHOD void dumpEvExpr(
198     const Fortran::evaluate::Expr<
199         Fortran::evaluate::Type<Fortran::common::TypeCategory::Integer, 4>> &x);
200 LLVM_DUMP_METHOD void dumpEvExpr(
201     const Fortran::evaluate::Expr<
202         Fortran::evaluate::Type<Fortran::common::TypeCategory::Integer, 8>> &x);
203 LLVM_DUMP_METHOD void dumpEvExpr(const Fortran::evaluate::ArrayRef &x);
204 LLVM_DUMP_METHOD void dumpEvExpr(const Fortran::evaluate::DataRef &x);
205 LLVM_DUMP_METHOD void dumpEvExpr(const Fortran::evaluate::Substring &x);
206 LLVM_DUMP_METHOD void dumpEvExpr(
207     const Fortran::evaluate::Designator<
208         Fortran::evaluate::Type<Fortran::common::TypeCategory::Integer, 4>> &x);
209 
210 } // namespace Fortran::lower
211 
212 #endif // FORTRAN_LOWER_DUMPEVALUATEEXPR_H
213