summaryrefslogtreecommitdiff
path: root/tiger-compiler/src/inlining/inliner.cc
diff options
context:
space:
mode:
Diffstat (limited to 'tiger-compiler/src/inlining/inliner.cc')
-rw-r--r--tiger-compiler/src/inlining/inliner.cc64
1 files changed, 64 insertions, 0 deletions
diff --git a/tiger-compiler/src/inlining/inliner.cc b/tiger-compiler/src/inlining/inliner.cc
new file mode 100644
index 0000000..85bbc88
--- /dev/null
+++ b/tiger-compiler/src/inlining/inliner.cc
@@ -0,0 +1,64 @@
+/**
+ ** \file inlining/inliner.cc
+ ** \brief Implementation of inlining::Inliner.
+ */
+
+#include <boost/graph/transitive_closure.hpp>
+
+#include <ranges>
+#include <callgraph/libcallgraph.hh>
+#include <inlining/inliner.hh>
+#include <parse/libparse.hh>
+#include <parse/tweast.hh>
+
+namespace inlining
+{
+ using namespace ast;
+
+ Inliner::Inliner(const ast::Ast& tree)
+ : super_type()
+ , rec_funs_()
+ {
+ // Compute the transitive closure of the call graph to compute the
+ // set of recursive functions.
+ const callgraph::CallGraph* graph = callgraph::callgraph_compute(tree);
+ callgraph::CallGraph closure;
+ boost::transitive_closure(*graph, closure);
+
+ // Compute the parent graph to get nested functions.
+ const callgraph::ParentGraph* parentGraph =
+ callgraph::parentgraph_compute(const_cast<ast::Ast&>(tree));
+
+ // Re-attach properties to the vertices.
+ for (auto [i, i_end] = boost::vertices(closure); i != i_end; ++i)
+ closure[*i] = (*graph)[*i];
+ // Detect recursive functions.
+ for (auto [i, i_end] = boost::vertices(closure); i != i_end; ++i)
+ {
+ for (auto [j, j_end] = boost::adjacent_vertices(*i, closure);
+ j != j_end; ++j)
+ {
+ // Check all parent functions to detect cases like these :
+ // function a() =
+ // (
+ // let
+ // function b() = a()
+ // in
+ // end
+ // )
+ if (parentGraph->hfundec_deep_get(closure[*i], closure[*j]))
+ rec_funs_.insert(closure[*j]);
+ }
+ }
+ delete graph;
+ delete parentGraph;
+ }
+
+ const misc::set<const ast::FunctionDec*>& Inliner::rec_funs_get() const
+ {
+ return rec_funs_;
+ }
+
+ // FIXME: Some code was deleted here.
+
+} // namespace inlining