Jlm
base-hls.cpp
Go to the documentation of this file.
1 /*
2  * Copyright 2021 David Metz <david.c.metz@ntnu.no>
3  * See COPYING for terms of redistribution.
4  */
5 
7 
8 #include <algorithm>
9 #include <cmath>
10 #include <regex>
11 
12 namespace jlm::hls
13 {
14 
15 bool
17 {
18  if (('A' <= c && c <= 'Z') || ('a' <= c && c <= 'z') || ('0' <= c && c <= '9') || '_' == c)
19  {
20  return false;
21  }
22  return true;
23 }
24 
25 BaseHLS::~BaseHLS() = default;
26 
27 std::string
29 {
30  auto found = node_map.find(node);
31  if (found != node_map.end())
32  {
33  return found->second;
34  }
35  std::string append = "";
36  auto inPorts = node->ninputs();
37  auto outPorts = node->noutputs();
38  if (inPorts)
39  {
40  append.append("_IN");
41  append.append(std::to_string(inPorts));
42  append.append("_W");
43  append.append(std::to_string(JlmSize(node->input(inPorts - 1)->Type().get())));
44  }
45  if (outPorts)
46  {
47  append.append("_OUT");
48  append.append(std::to_string(outPorts));
49  append.append("_W");
50  append.append(std::to_string(JlmSize(node->output(outPorts - 1)->Type().get())));
51  }
52  auto name = util::strfmt("op_", node->DebugString(), append, "_", node_map.size());
53  // remove chars that are not valid in firrtl module names
54  std::replace_if(name.begin(), name.end(), isForbiddenChar, '_');
55  // verilator seems to throw a fit if there are too many underscores in some scenarios
56  name = std::regex_replace(name, std::regex("_+"), "_");
57  node_map[node] = name;
58  return name;
59 }
60 
61 std::string
63 {
64  std::string result;
65  if (jlm::rvsdg::TryGetOwnerNode<jlm::rvsdg::Node>(*port))
66  {
67  result += "i";
68  }
69  else if (jlm::rvsdg::TryGetOwnerRegion(*port))
70  {
71  result += "r";
72  }
73  else
74  {
75  throw std::logic_error(port->debug_string() + " not implemented!");
76  }
77  result += util::strfmt(port->index());
78  return result;
79 }
80 
81 std::string
83 {
84  if (port == nullptr)
85  {
86  throw std::logic_error("nullptr!");
87  }
88  std::string result;
89  if (dynamic_cast<const jlm::rvsdg::RegionArgument *>(port))
90  {
91  result += "a";
92  }
93  else if (dynamic_cast<const rvsdg::NodeOutput *>(port))
94  {
95  result += "o";
96  }
97  else if (dynamic_cast<const rvsdg::StructuralOutput *>(port))
98  {
99  result += "so";
100  }
101  else
102  {
103  throw std::logic_error(port->debug_string() + " not implemented!");
104  }
105  result += util::strfmt(port->index());
106  return result;
107 }
108 
109 int
111 {
112  return jlm::hls::JlmSize(type);
113 }
114 
115 void
117 {
118  for (auto & node : r->Nodes())
119  {
120  if (dynamic_cast<jlm::rvsdg::SimpleNode *>(&node))
121  {
122  get_node_name(&node);
123  }
124  else if (auto oln = dynamic_cast<LoopNode *>(&node))
125  {
126  create_node_names(oln->subregion());
127  }
128  else
129  {
130  throw util::Error("Unimplemented op (unexpected structural node) : " + node.DebugString());
131  }
132  }
133 }
134 
137 {
138  auto region = &rm.Rvsdg().GetRootRegion();
139  auto ln = dynamic_cast<const rvsdg::LambdaNode *>(region->Nodes().begin().ptr());
140  if (region->numNodes() == 1 && ln)
141  {
142  return ln;
143  }
144  else
145  {
146  throw util::Error("Root should have only one lambda node now");
147  }
148 }
149 
150 std::string
152 {
153  auto source_file_name = rm.SourceFileName().name();
154  auto base_file_name = source_file_name.substr(0, source_file_name.find_last_of('.'));
155  return base_file_name;
156 }
157 
158 }
std::unordered_map< const rvsdg::Node *, std::string > node_map
Definition: base-hls.hpp:44
static std::string get_port_name(jlm::rvsdg::Input *port)
Definition: base-hls.cpp:62
void create_node_names(rvsdg::Region *r)
Definition: base-hls.cpp:116
virtual ~BaseHLS()
static int JlmSize(const jlm::rvsdg::Type *type)
Definition: base-hls.cpp:110
const rvsdg::LambdaNode * get_hls_lambda(llvm::LlvmRvsdgModule &rm)
Definition: base-hls.cpp:136
std::string get_node_name(const rvsdg::Node *node)
Definition: base-hls.cpp:28
static std::string get_base_file_name(const llvm::LlvmRvsdgModule &rm)
Definition: base-hls.cpp:151
const util::FilePath & SourceFileName() const noexcept
Region & GetRootRegion() const noexcept
Definition: graph.hpp:99
size_t index() const noexcept
Definition: node.hpp:52
virtual std::string debug_string() const
Definition: node.cpp:58
const std::shared_ptr< const rvsdg::Type > & Type() const noexcept
Definition: node.hpp:67
Lambda node.
Definition: lambda.hpp:83
virtual std::string DebugString() const =0
NodeInput * input(size_t index) const noexcept
Definition: node.hpp:615
NodeOutput * output(size_t index) const noexcept
Definition: node.hpp:650
size_t ninputs() const noexcept
Definition: node.hpp:609
size_t noutputs() const noexcept
Definition: node.hpp:644
const std::shared_ptr< const rvsdg::Type > & Type() const noexcept
Definition: node.hpp:366
virtual std::string debug_string() const
Definition: node.cpp:168
size_t index() const noexcept
Definition: node.hpp:274
Represents the argument of a region.
Definition: region.hpp:41
Represent acyclic RVSDG subgraphs.
Definition: region.hpp:213
NodeRange Nodes() noexcept
Definition: region.hpp:328
Graph & Rvsdg() noexcept
Definition: RvsdgModule.hpp:57
std::string name() const noexcept
Returns the name of the file, excluding the path.
Definition: file.hpp:81
int JlmSize(const jlm::rvsdg::Type *type)
Definition: hls.cpp:344
bool isForbiddenChar(char c)
Definition: base-hls.cpp:16
static std::string type(const Node *n)
Definition: view.cpp:255
Region * TryGetOwnerRegion(const rvsdg::Input &input) noexcept
Definition: node.hpp:1021
static std::string strfmt(Args... args)
Definition: strfmt.hpp:35