21using Repls = std::deque<std::unique_ptr<Repl>>;
22using Phases = std::deque<std::unique_ptr<Phase>>;
48 template<
class P,
class... Args>
49 static void run(Args&&... args) {
50 P p(std::forward<Args>(args)...);
104 void start()
override;
107 bool bootstrapping_ =
true;
129 void add(std::unique_ptr<Repl>&& repl) { repls_.emplace_back(std::move(repl)); }
130 const auto&
repls()
const {
return repls_; }
138#define MIM_CONCAT_INNER(a, b) a##b
139#define MIM_CONCAT(a, b) MIM_CONCAT_INNER(a, b)
141#define MIM_REPL(__stages, __annex, ...) MIM_REPL_IMPL(__stages, __annex, __LINE__, __VA_ARGS__)
144#define MIM_REPL_IMPL(__stages, __annex, __id, ...) \
145 struct MIM_CONCAT(Repl_, __id) : ::mim::Repl { \
146 MIM_CONCAT(Repl_, __id)(::mim::World & world, ::mim::flags_t annex) \
147 : Repl(world, annex) {} \
149 const ::mim::Def* replace(const ::mim::Def* def) final __VA_ARGS__ \
151 ::mim::Stage::hook<__annex, MIM_CONCAT(Repl_, __id)>(__stages)
197 void apply(
const App*)
final;
198 void apply(
Stage&)
final;
206 std::unique_ptr<PassMan> man_;
218 void apply(
bool,
Phases&&);
219 void apply(
const App*)
final;
220 void apply(
Stage&)
final;
227 const auto&
phases()
const {
return phases_; }
240template<class
M =
Def>
260 const bool elide_empty_;
265template<
class M = Def>
Cleanup(World &world, flags_t annex)
ClosedMutPhase(World &world, std::string name, bool elide_empty)
void start() override
Actual entry.
ClosedMutPhase(World &world, flags_t annex, bool elide_empty)
virtual void visit(M *)=0
NestPhase(World &world, flags_t annex, bool elide_empty)
virtual void visit(const Nest &)=0
const Nest & nest() const
NestPhase(World &world, std::string name, bool elide_empty)
Builds a nesting tree of all immutables‍/binders.
PassManPhase(World &world, flags_t annex)
PassManPhase(World &world, std::unique_ptr< PassMan > &&man)
void start() final
Actual entry.
const PassMan & man() const
An optimizer that combines several optimizations in an optimal way.
Organizes several Phases in a a pipeline.
PhaseMan(World &world, flags_t annex)
const auto & phases() const
As opposed to a Pass, a Phase does one thing at a time and does not mix with other Phases.
bool todo_
Set to true to indicate that you want to rerun all Phasees in current your fixed-point PhaseMan.
Phase(World &world, std::string name)
static void run(Args &&... args)
Runs a single Phase.
Phase(World &world, flags_t annex)
virtual void run()
Entry point and generates some debug output; invokes Phase::start.
virtual void start()=0
Actual entry.
World & new_world()
Create new Defs into this.
RWPhase(World &world, std::string name)
virtual void rewrite_annex(flags_t, const Def *)
bool is_bootstrapping() const
void start() override
Actual entry.
World & world()=delete
Hides both and forbids direct access.
RWPhase(World &world, flags_t annex)
virtual bool analyze()
You can do an optional fixed-point loop on the RWPhase::old_world before rewriting.
World & old_world()
Get old Defs from here.
virtual void rewrite_external(Def *)
const Def * rewrite(const Def *) final
ReplManPhase(World &world, flags_t annex)
const ReplMan & man() const
void start() final
Actual entry.
ReplManPhase(World &world, std::unique_ptr< ReplMan > &&man)
void apply(const App *) final
Invoked if your Stage has additional args.
void apply(Stage &stage) final
Dito, but invoked by Stage::recreate.
const auto & repls() const
const Def * replace(const Def *) final
ReplMan(World &world, flags_t annex)
void add(std::unique_ptr< Repl > &&repl)
Simple Stage that searches for a pattern and replaces it.
virtual const Def * replace(const Def *def)=0
Repl(World &world, flags_t annex)
Rewriter(std::unique_ptr< World > &&ptr)
Common base for Phase and Pass.
std::string_view name() const
Stage(World &world, std::string name)
The World represents the whole program and manages creation of MimIR nodes (Defs).
std::deque< std::unique_ptr< Repl > > Repls
std::deque< std::unique_ptr< Phase > > Phases