MimIR 0.1
MimIR is my Intermediate Representation
Loading...
Searching...
No Matches
stream.cpp
Go to the documentation of this file.
1#include <ostream>
2
3#include "mim/ast/ast.h"
4#include "mim/util/print.h"
5
6namespace mim::ast {
7
8using Tag = Tok::Tag;
9
10struct S {
11 S(Tab& tab, const Node* node)
12 : tab(tab)
13 , node(node) {}
14
16 const Node* node;
17
18 friend std::ostream& operator<<(std::ostream& os, const S& s) { return s.node->stream(s.tab, os); }
19};
20
21template<class T>
22struct R {
23 R(Tab& tab, const Ptrs<T>& range)
24 : tab(tab)
25 , range(range)
26 , f([&tab](std::ostream& os, const Ptr<T>& ptr) { ptr->stream(tab, os); }) {}
27
29 const Ptrs<T>& range;
30 std::function<void(std::ostream&, const Ptr<T>&)> f;
31};
32
33void Node::dump() const {
34 Tab tab;
35 stream(tab, std::cout) << std::endl;
36}
37
38/*
39 * Module
40 */
41
42std::ostream& Import::stream(Tab& tab, std::ostream& os) const { return tab.println(os, "{} '{}';", tag(), "TODO"); }
43
44std::ostream& Module::stream(Tab& tab, std::ostream& os) const {
45 for (const auto& import : imports())
46 import->stream(tab, os);
47 for (const auto& decl : decls())
48 tab.println(os, "{}", S(tab, decl.get()));
49 return os;
50}
51
52/*
53 * Ptrn
54 */
55
56std::ostream& ErrorPtrn::stream(Tab&, std::ostream& os) const { return os << "<error pattern>"; }
57std::ostream& AliasPtrn::stream(Tab& tab, std::ostream& os) const { return print(os, "{}: {}", S(tab, ptrn()), dbg()); }
58std::ostream& GrpPtrn::stream(Tab&, std::ostream& os) const { return os << dbg(); }
59
60std::ostream& IdPtrn::stream(Tab& tab, std::ostream& os) const {
61 // clang-format off
62 if ( dbg() && type()) return print(os, "{}: {}", dbg(), S(tab, type()));
63 if ( dbg() && !type()) return print(os, "{}", dbg());
64 if (!dbg() && type()) return print(os, "{}", S(tab, type()));
65 // clang-format on
66 return os << "<invalid identifier pattern>";
67}
68
69std::ostream& TuplePtrn::stream(Tab& tab, std::ostream& os) const {
70 return print(os, "{}{, }{}", delim_l(), R(tab, ptrns()), delim_r());
71}
72
73/*
74 * Expr
75 */
76
77std::ostream& IdExpr::stream(Tab&, std::ostream& os) const { return print(os, "{}", dbg()); }
78std::ostream& ErrorExpr::stream(Tab&, std::ostream& os) const { return os << "<error expression>"; }
79std::ostream& HoleExpr::stream(Tab&, std::ostream& os) const { return os << "?"; }
80std::ostream& PrimaryExpr::stream(Tab&, std::ostream& os) const { return print(os, "{}", tag()); }
81
82std::ostream& LitExpr::stream(Tab& tab, std::ostream& os) const {
83 switch (tag()) {
84 case Tag::L_i: return print(os, "{}", tok().lit_i());
85 case Tag::L_f: return os << std::bit_cast<double>(tok().lit_u());
86 case Tag::L_s:
87 case Tag::L_u:
88 os << tok().lit_u();
89 if (type()) print(os, ": {}", S(tab, type()));
90 break;
91 default: os << "TODO";
92 }
93 return os;
94}
95
96std::ostream& DeclExpr::stream(Tab& tab, std::ostream& os) const {
97 if (is_where()) {
98 tab.println(os, "{} where", S(tab, expr()));
99 ++tab;
100 for (const auto& decl : decls())
101 tab.println(os, "{}", S(tab, decl.get()));
102 --tab;
103 return os;
104 } else {
105 for (const auto& decl : decls())
106 tab.println(os, "{}", S(tab, decl.get()));
107 return print(os, "{}", S(tab, expr()));
108 }
109}
110
111std::ostream& TypeExpr::stream(Tab& tab, std::ostream& os) const { return print(os, "(Type {})", S(tab, level())); }
112
113std::ostream& ArrowExpr::stream(Tab& tab, std::ostream& os) const {
114 return print(os, "{} -> {}", S(tab, dom()), S(tab, codom()));
115}
116
117std::ostream& UnionExpr::stream(Tab& tab, std::ostream& os) const { return print(os, "({∪ })", R(tab, types())); }
118
119std::ostream& InjExpr::stream(Tab& tab, std::ostream& os) const {
120 return print(os, "{} inj {}", S(tab, value()), S(tab, type()));
121}
122
123std::ostream& MatchExpr::Arm::stream(Tab& tab, std::ostream& os) const {
124 return print(os, "{} => {}", S(tab, ptrn()), S(tab, body()));
125}
126
127std::ostream& MatchExpr::stream(Tab& tab, std::ostream& os) const {
128 tab.println(os, "match {} {{", S(tab, scrutinee()));
129 ++tab;
130 for (const auto& arm : arms())
131 tab.println(os, "{},", S(tab, arm.get()));
132 --tab;
133 return tab.println(os, "}}");
134}
135
136std::ostream& PiExpr::Dom::stream(Tab& tab, std::ostream& os) const {
137 print(os, "{}{}", is_implicit() ? "." : "", S(tab, ptrn()));
138 if (ret()) print(os, " -> {}", S(tab, ret()->type()));
139 return os;
140}
141
142std::ostream& PiExpr::stream(Tab& tab, std::ostream& os) const {
143 if (tag() != Tag::Nil) print(os, "{} ", tag());
144 print(os, "{}", S(tab, dom()));
145 if (codom()) print(os, " -> {}", S(tab, codom()));
146 return os;
147}
148
149std::ostream& LamExpr::stream(Tab& tab, std::ostream& os) const { return print(os, "{};", S(tab, lam())); }
150
151std::ostream& AppExpr::stream(Tab& tab, std::ostream& os) const {
152 return print(os, "{} {} {}", S(tab, callee()), is_explicit() ? "@" : "", S(tab, arg()));
153}
154
155std::ostream& RetExpr::stream(Tab& tab, std::ostream& os) const {
156 println(os, "ret {} = {} $ {};", S(tab, ptrn()), S(tab, callee()), S(tab, arg()));
157 return tab.print(os, "{}", S(tab, body()));
158}
159
160std::ostream& SigmaExpr::stream(Tab& tab, std::ostream& os) const { return ptrn()->stream(tab, os); }
161std::ostream& TupleExpr::stream(Tab& tab, std::ostream& os) const { return print(os, "({, })", R(tab, elems())); }
162
163std::ostream& SeqExpr::stream(Tab& tab, std::ostream& os) const {
164 return print(os, "{}{}; {}{}", is_arr() ? "«" : "‹", S(tab, arity()), S(tab, body()), is_arr() ? "»" : "›");
165}
166
167std::ostream& ExtractExpr::stream(Tab& tab, std::ostream& os) const {
168 if (auto expr = std::get_if<Ptr<Expr>>(&index())) return print(os, "{}#{}", S(tab, tuple()), S(tab, expr->get()));
169 return print(os, "{}#{}", S(tab, tuple()), std::get<Dbg>(index()));
170}
171
172std::ostream& InsertExpr::stream(Tab& tab, std::ostream& os) const {
173 return print(os, "ins({}, {}, {})", S(tab, tuple()), S(tab, index()), S(tab, value()));
174}
175
176std::ostream& UniqExpr::stream(Tab& tab, std::ostream& os) const { return print(os, "⦃{}⦄", S(tab, inhabitant())); }
177
178/*
179 * Decl
180 */
181
182std::ostream& AxmDecl::Alias::stream(Tab&, std::ostream& os) const { return os << dbg(); }
183
184std::ostream& AxmDecl::stream(Tab& tab, std::ostream& os) const {
185 print(os, "axm {}", dbg());
186 if (num_subs() != 0) {
187 os << '(';
188 for (auto sep = ""; const auto& aliases : subs()) {
189 print(os, "{}{ = }", sep, R(tab, aliases));
190 sep = ", ";
191 }
192 os << ')';
193 }
194 print(os, ": {}", S(tab, type()));
195 if (normalizer()) print(os, ", {}", normalizer());
196 if (curry()) print(os, ", {}", curry());
197 if (trip()) print(os, ", {}", trip());
198 return os << ";";
199}
200
201std::ostream& LetDecl::stream(Tab& tab, std::ostream& os) const {
202 return print(os, "let {} = {};", S(tab, ptrn()), S(tab, value()));
203}
204
205std::ostream& RecDecl::stream(Tab& tab, std::ostream& os) const {
206 print(os, ".rec {}", dbg());
207 if (!type()->isa<HoleExpr>()) print(os, ": {}", S(tab, type()));
208 return print(os, " = {};", S(tab, body()));
209}
210
211std::ostream& LamDecl::Dom::stream(Tab& tab, std::ostream& os) const {
212 print(os, "{}{}", is_implicit() ? "." : "", S(tab, ptrn()));
213 if (filter()) print(os, "@({})", S(tab, filter()));
214 if (ret()) print(os, ": {}", S(tab, ret()->type()));
215 return os;
216}
217
218std::ostream& LamDecl::stream(Tab& tab, std::ostream& os) const {
219 print(os, "{} {}", tag(), dbg());
220 if (!doms().front()->ptrn()->isa<TuplePtrn>()) os << ' ';
221 print(os, "{}", R(tab, doms()));
222 if (codom()) print(os, ": {}", S(tab, codom()));
223 if (body()) {
224 if (body()->isa<DeclExpr>()) {
225 os << " =" << std::endl;
226 (++tab).print(os, "{}", S(tab, body()));
227 --tab;
228 } else {
229 print(os, " = {}", S(tab, body()));
230 }
231 }
232 return os << ';';
233}
234
235std::ostream& CDecl::stream(Tab& tab, std::ostream& os) const {
236 print(os, "{} {} {}", dbg(), tag(), S(tab, dom()), S(tab, codom()));
237 if (tag() == Tag::K_cfun) print(os, ": {}", S(tab, codom()));
238 return os;
239}
240
241} // namespace mim::ast
Keeps track of indentation level.
Definition print.h:206
std::ostream & println(std::ostream &os, const char *s, Args &&... args)
Same as Tab::print but appends a std::endl to os.
Definition print.h:235
std::ostream & print(std::ostream &os, const char *s, Args &&... args)
Definition print.h:223
Dbg dbg() const
Definition ast.h:276
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:57
const Ptrn * ptrn() const
Definition ast.h:275
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:151
bool is_explicit() const
Definition ast.h:652
const Expr * arg() const
Definition ast.h:654
const Expr * callee() const
Definition ast.h:653
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:113
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:182
Dbg dbg() const
Definition ast.h:865
const auto & subs() const
Definition ast.h:887
const Expr * type() const
Definition ast.h:890
Tok trip() const
Definition ast.h:893
size_t num_subs() const
Definition ast.h:888
Tok curry() const
Definition ast.h:892
Dbg normalizer() const
Definition ast.h:891
Dbg dbg() const
Definition ast.h:886
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:184
Tok::Tag tag() const
Definition ast.h:1022
const Ptrn * dom() const
Definition ast.h:1023
const Expr * codom() const
Definition ast.h:1024
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:235
Dbg dbg() const
Definition ast.h:1021
const Expr * expr() const
Definition ast.h:420
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:96
const auto & decls() const
Definition ast.h:418
bool is_where() const
Definition ast.h:419
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:78
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:56
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:167
const auto & index() const
Definition ast.h:774
const Expr * tuple() const
Definition ast.h:773
Dbg dbg() const
Definition ast.h:254
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:58
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:79
Dbg dbg() const
Definition ast.h:354
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:77
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:60
Dbg dbg() const
Definition ast.h:224
const Expr * type() const
Definition ast.h:225
Tok::Tag tag() const
Definition ast.h:1050
std::ostream & stream(Tab &, std::ostream &) const
Definition stream.cpp:42
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:119
const Expr * type() const
Definition ast.h:482
const Expr * value() const
Definition ast.h:481
const Expr * index() const
Definition ast.h:798
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:172
const Expr * tuple() const
Definition ast.h:797
const Expr * value() const
Definition ast.h:799
const Expr * filter() const
Definition ast.h:960
bool is_implicit() const
Definition ast.h:959
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:211
Tok::Tag tag() const
Definition ast.h:989
const Ptrs< Dom > & doms() const
Definition ast.h:991
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:218
const Expr * codom() const
Definition ast.h:994
const LamDecl * lam() const
Definition ast.h:630
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:149
const Expr * value() const
Definition ast.h:843
const Ptrn * ptrn() const
Definition ast.h:842
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:201
Tok tok() const
Definition ast.h:395
const Expr * type() const
Definition ast.h:397
Tok::Tag tag() const
Definition ast.h:396
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:82
const Expr * body() const
Definition ast.h:507
const Ptrn * ptrn() const
Definition ast.h:506
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:123
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:127
const Expr * scrutinee() const
Definition ast.h:523
const Arm * arm(size_t i) const
Definition ast.h:525
const auto & arms() const
Definition ast.h:524
const auto & decls() const
Definition ast.h:1079
const auto & imports() const
Definition ast.h:1078
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:44
virtual std::ostream & stream(Tab &, std::ostream &) const =0
void dump() const
Definition stream.cpp:33
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:136
const IdPtrn * ret() const
Definition ast.h:579
bool is_implicit() const
Definition ast.h:577
const Ptrn * ptrn() const
Definition ast.h:578
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:142
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:80
Tok::Tag tag() const
Definition ast.h:376
Dbg dbg() const
Definition ast.h:920
const Expr * body() const
Definition ast.h:922
const Expr * type() const
Definition ast.h:921
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:205
const Ptrn * ptrn() const
Definition ast.h:677
const Expr * arg() const
Definition ast.h:679
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:155
const Expr * body() const
Definition ast.h:680
const Expr * callee() const
Definition ast.h:678
const Expr * body() const
Definition ast.h:748
const IdPtrn * arity() const
Definition ast.h:747
bool is_arr() const
Definition ast.h:746
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:163
const TuplePtrn * ptrn() const
Definition ast.h:702
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:160
uint64_t lit_u() const
Definition tok.h:166
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:161
const auto & elems() const
Definition ast.h:724
Tok::Tag delim_r() const
Definition ast.h:298
const auto & ptrns() const
Definition ast.h:303
Tok::Tag delim_l() const
Definition ast.h:297
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:69
const Expr * level() const
Definition ast.h:440
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:111
const auto & types() const
Definition ast.h:460
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:117
const Expr * inhabitant() const
Definition ast.h:819
std::ostream & stream(Tab &, std::ostream &) const override
Definition stream.cpp:176
Definition ast.h:14
fe::Arena::Ptr< const T > Ptr
Definition ast.h:22
std::deque< Ptr< T > > Ptrs
Definition ast.h:24
Tok::Tag Tag
Definition bind.cpp:7
std::ostream & print(std::ostream &os, const char *s)
Base case.
Definition print.cpp:5
std::ostream & println(std::ostream &os, const char *fmt, Args &&... args)
As above but end with std::endl.
Definition print.h:157
Definition span.h:122
const Ptrs< T > & range
Definition stream.cpp:29
std::function< void(std::ostream &, const Ptr< T > &)> f
Definition stream.cpp:30
R(Tab &tab, const Ptrs< T > &range)
Definition stream.cpp:23
Tab & tab
Definition stream.cpp:28
S(Tab &tab, const Node *node)
Definition stream.cpp:11
friend std::ostream & operator<<(std::ostream &os, const S &s)
Definition stream.cpp:18
const Node * node
Definition stream.cpp:16
Tab & tab
Definition stream.cpp:15