PandA-2024.02
easy_module_binding.cpp
Go to the documentation of this file.
1 /*
2  *
3  * _/_/_/ _/_/ _/ _/ _/_/_/ _/_/
4  * _/ _/ _/ _/ _/_/ _/ _/ _/ _/ _/
5  * _/_/_/ _/_/_/_/ _/ _/_/ _/ _/ _/_/_/_/
6  * _/ _/ _/ _/ _/ _/ _/ _/ _/
7  * _/ _/ _/ _/ _/ _/_/_/ _/ _/
8  *
9  * ***********************************************
10  * PandA Project
11  * URL: http://panda.dei.polimi.it
12  * Politecnico di Milano - DEIB
13  * System Architectures Group
14  * ***********************************************
15  * Copyright (C) 2004-2024 Politecnico di Milano
16  *
17  * This file is part of the PandA framework.
18  *
19  * The PandA framework is free software; you can redistribute it and/or modify
20  * it under the terms of the GNU General Public License as published by
21  * the Free Software Foundation; either version 3 of the License, or
22  * (at your option) any later version.
23  *
24  * This program is distributed in the hope that it will be useful,
25  * but WITHOUT ANY WARRANTY; without even the implied warranty of
26  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
27  * GNU General Public License for more details.
28  *
29  * You should have received a copy of the GNU General Public License
30  * along with this program. If not, see <http://www.gnu.org/licenses/>.
31  *
32  */
43 #include "easy_module_binding.hpp"
44 #include "Parameter.hpp"
46 #include "behavioral_helper.hpp"
47 #include "cpu_time.hpp"
48 #include "custom_map.hpp"
49 #include "custom_set.hpp"
50 #include "dbgPrintHelper.hpp"
51 #include "fu_binding.hpp"
52 #include "function_behavior.hpp"
53 #include "graph.hpp"
54 #include "hls.hpp"
55 #include "hls_manager.hpp"
56 #include "op_graph.hpp"
58 #include "string_manipulation.hpp" // for GET_CLASS
59 #include "structural_manager.hpp"
60 #include "structural_objects.hpp"
61 #include "technology_node.hpp"
62 #include "tree_manager.hpp"
63 #include "tree_node.hpp"
64 #include <iosfwd>
65 #include <string>
66 #include <tuple>
67 
69  unsigned int _funId, const DesignFlowManagerConstRef _design_flow_manager)
70  : HLSFunctionStep(_Param, _HLSMgr, _funId, _design_flow_manager, HLSFlowStep_Type::EASY_MODULE_BINDING)
71 {
72  debug_level = _Param->get_class_debug_level(GET_CLASS(*this));
73 }
74 
76 
78 {
80  if(not HLS->Rfu)
81  {
82  if(parameters->getOption<int>(OPT_memory_banks_number) > 1 && !parameters->isOption(OPT_context_switch))
83  {
85  }
86  else
87  {
89  }
90  }
91 }
92 
95 {
97  switch(relationship_type)
98  {
100  {
103  if(HLSMgr->get_HLS(funId))
104  {
105  ret.insert(std::make_tuple(HLSMgr->get_HLS(funId)->chaining_algorithm, HLSFlowStepSpecializationConstRef(),
107  }
108  break;
109  }
111  {
112  break;
113  }
115  {
116  break;
117  }
118  default:
119  THROW_UNREACHABLE("");
120  }
121  return ret;
122 }
123 
125 {
126  long step_time = 0;
128  {
129  START_TIME(step_time);
130  }
131  const auto TM = HLSMgr->get_tree_manager();
132  // resource binding and allocation info
133  fu_binding& fu = *(HLS->Rfu);
134  const auto allocation_information = HLS->allocation_information;
135  // pointer to a Control, Data dependence and antidependence graph graph
136  const auto FB = HLSMgr->CGetFunctionBehavior(funId);
137  const auto sdg = FB->CGetOpGraph(FunctionBehavior::SDG);
138 
139  unsigned int fu_unit;
141  std::map<unsigned int, unsigned int> n_shared_fu;
142  for(const auto operation : sdg->CGetOperations())
143  {
144  const auto id = sdg->CGetOpNodeInfo(operation)->GetNodeId();
145  if(id == ENTRY_ID || id == EXIT_ID)
146  {
147  continue;
148  }
149  fu_unit = fu.get_assign(operation);
150  if(allocation_information->is_vertex_bounded(fu_unit))
151  {
152  continue;
153  }
154  if(n_shared_fu.find(fu_unit) == n_shared_fu.end())
155  {
156  n_shared_fu[fu_unit] = 1;
157  }
158  else
159  {
160  n_shared_fu[fu_unit] = 1 + n_shared_fu[fu_unit];
161  }
162  }
164  {
166  }
168  "-->Easy binding information for function " + FB->CGetBehavioralHelper()->get_function_name() + ":");
170  if(HLSMgr->GetFunctionBehavior(funId)->is_simple_pipeline())
171  {
172  std::set<vertex> bound_vertices;
173  std::map<unsigned int, unsigned int> fu_instances;
174  for(const auto op : sdg->CGetOperations())
175  {
176  if(fu.get_index(op) != INFINITE_UINT)
177  {
178  continue;
179  }
180  fu_unit = fu.get_assign(op);
181  if(fu_instances.find(fu_unit) == fu_instances.end())
182  {
183  fu_instances.insert(std::pair<unsigned int, unsigned int>(fu_unit, 0));
184  }
185  fu.bind(op, fu_unit, fu_instances[fu_unit]);
186  fu_instances[fu_unit]++;
187  bound_vertices.insert(op);
188  const auto node_id = sdg->CGetOpNodeInfo(op)->GetNodeId();
189  if(node_id)
190  {
192  "---" + GET_NAME(sdg, op) + "(" +
193  (node_id == ENTRY_ID ?
194  "ENTRY" :
195  (node_id == EXIT_ID ? "EXIT" : TM->get_tree_node_const(node_id)->ToString())) +
196  ") bound to " + allocation_information->get_fu_name(fu_unit).first + "(0)");
197  }
198  }
199  }
200  else
201  {
202  CustomOrderedSet<vertex> easy_bound_vertices;
203  for(const auto op : sdg->CGetOperations())
204  {
205  if(fu.get_index(op) != INFINITE_UINT)
206  {
207  continue;
208  }
209  fu_unit = fu.get_assign(op);
210  if(allocation_information->is_vertex_bounded(fu_unit) ||
211  (allocation_information->is_memory_unit(fu_unit) &&
212  (!allocation_information->is_readonly_memory_unit(fu_unit) ||
213  (!allocation_information->is_one_cycle_direct_access_memory_unit(fu_unit) &&
214  (!parameters->isOption(OPT_rom_duplication) || !parameters->getOption<bool>(OPT_rom_duplication)))) &&
215  allocation_information->get_number_channels(fu_unit) == 1) ||
216  n_shared_fu.find(fu_unit)->second == 1)
217  {
218  fu.bind(op, fu_unit, 0);
219  easy_bound_vertices.insert(op);
220  const auto node_id = sdg->CGetOpNodeInfo(op)->GetNodeId();
221  if(node_id)
222  {
224  "---" + GET_NAME(sdg, op) + "(" +
225  (node_id == ENTRY_ID ?
226  "ENTRY" :
227  (node_id == EXIT_ID ? "EXIT" : TM->get_tree_node_const(node_id)->ToString())) +
228  ") bound to " + allocation_information->get_fu_name(fu_unit).first + "(0)");
229  }
230  }
231  }
233  "---Bound operations:" + STR(easy_bound_vertices.size()) + "/" + STR(boost::num_vertices(*sdg)));
234  }
236  {
237  STOP_TIME(step_time);
239  "Time to perform easy binding: " + print_cpu_time(step_time) + " seconds");
240  }
243  {
245  }
247 }
void Initialize() override
Initialize the step (i.e., like a constructor, but executed just before exec.
void Initialize() override
Initialize the step (i.e., like a constructor, but executed just before exec.
const HLS_managerRef HLSMgr
information about all the HLS synthesis
Definition: hls_step.hpp:205
System dependence graph.
Data structure representing the entire HLS information.
File containing functions and utilities to support the printing of debug messagges.
refcount< fu_binding > fu_bindingRef
RefCount type definition of the fu_binding class structure.
Definition: fu_binding.hpp:402
#define GET_CLASS(obj)
Macro returning the actual type of an object.
const int output_level
The output level.
static fu_bindingRef create_fu_binding(const HLS_managerConstRef _HLSMgr, const unsigned int _function_id, const ParameterConstRef _parameters)
create_fu_binding: factory method for fu_binding
Definition: fu_binding.cpp:135
RelationshipType
The relationship type.
Source must be executed to satisfy target.
#define INDENT_OUT_MEX(outLevel, curOutLevel, mex)
unsigned int get_assign(const vertex &v) const
Returns the functional unit assigned to the vertex.
Definition: fu_binding.cpp:242
const unsigned int funId
identifier of the function to be processed (0 means that it is a global step)
#define GET_NAME(data, vertex_index)
Helper macro returning the name associated with a node.
Class specification of the graph structures.
AllocationInformationRef allocation_information
Store the technology information.
Definition: hls.hpp:115
DesignFlowStep_Status InternalExec() override
Execute the step.
#define OUTPUT_LEVEL_MINIMUM
minimum debugging print is performed.
redefinition of map to manage ordered/unordered structures
Include a set of utilities used to manage CPU time measures.
const CustomUnorderedSet< std::tuple< HLSFlowStep_Type, HLSFlowStepSpecializationConstRef, HLSFlowStep_Relationship > > ComputeHLSRelationships(const DesignFlowStep::RelationshipType relationship_type) const override
Compute the relationship of this step.
#define STR(s)
Macro which performs a lexical_cast to a string.
Auxiliary methods for manipulating string.
#define START_TIME(time_var)
Macro used to store the start time into time_var.
Definition: cpu_time.hpp:133
#define THROW_UNREACHABLE(str_expr)
helper function used to specify that some points should never be reached
Definition: exceptions.hpp:292
fu_bindingRef Rfu
Store the refcounted functional unit binding of the operations.
Definition: hls.hpp:121
#define EXIT_ID
constant used to represent tree node index of exit operation
Definition: op_graph.hpp:81
This class specifies the characteristic of a particular operation working on a given functional unit...
HLSFlowStep_Type
Definition: hls_step.hpp:95
Class specification of the data structures used to manage technology information. ...
void bind(const vertex &v, unsigned int unit, unsigned int index=std::numeric_limits< unsigned int >::max())
Binds an operation vertex to a functional unit.
Definition: fu_binding.cpp:173
redefinition of set to manage ordered/unordered structures
#define STOP_TIME(time_var)
Macro used to store the elapsed time into time_var.
Definition: cpu_time.hpp:136
easy_module_binding(const ParameterConstRef Param, const HLS_managerRef HLSMgr, unsigned int funId, const DesignFlowManagerConstRef design_flow_manager)
Constructor.
Data structure used to store the functional-unit binding of the vertices.
Classes specification of the tree_node data structures.
const ParameterConstRef parameters
Set of input parameters.
DesignFlowStep_Status
The status of a step.
This package is used by all HLS packages to manage resource constraints and characteristics.
std::string print_cpu_time(long int t)
massage a long which represents a time interval in milliseconds, into a string suitable for output ...
Definition: cpu_time.hpp:110
This class describes all classes used to represent a structural object.
#define OUTPUT_LEVEL_PEDANTIC
verbose debugging print is performed.
#define ENTRY_ID
constant used to represent tree node index of entry operation
Definition: op_graph.hpp:79
#define OUTPUT_LEVEL_VERY_PEDANTIC
verbose debugging print is performed.
Data structure used to store the functional-unit binding of the vertexes.
#define INFINITE_UINT
UNSIGNED INT representing infinite.
Definition: utility.hpp:70
hlsRef HLS
HLS data structure of the function to be analyzed.
Data structures used in operations graph.
Template borrowed from the ANTLR library by Terence Parr (http://www.jGuru.com - Software rights: htt...
Definition: refcount.hpp:94
this class is used to manage the command-line or XML options.
~easy_module_binding() override
Destructor.
Class implementation of the structural_manager.
Class managing the functional-unit binding.
Definition: fu_binding.hpp:90
int debug_level
The debug level.
refcount< const HLSFlowStepSpecialization > HLSFlowStepSpecializationConstRef
const refcount definition of the class
Definition: hls_step.hpp:93
Partial module binding based on simple conditions.
Data structure definition for high-level synthesis flow.
Superclass include.
unsigned int get_index(const vertex &v) const
Returns the index of functional unit assigned to the vertex.
Definition: fu_binding.cpp:261
Class specification of the manager of the tree structures extracted from the raw file.
A brief description of the C++ Header File.

Generated on Mon Feb 12 2024 13:02:53 for PandA-2024.02 by doxygen 1.8.13