71 std::set<RTLIL::SigBit> queue_bits;
72 std::set<RTLIL::Cell*> visited_cells;
79 queue_bits.insert(bits.begin(), bits.end());
84 while (!queue_bits.empty())
86 std::set<ModWalker::PortBit> portbits;
90 for (
auto &pbit : portbits) {
91 if (pbit.cell->type ==
"$mux" || pbit.cell->type ==
"$pmux") {
92 std::set<RTLIL::SigBit> bits =
modwalker.
sigmap(pbit.cell->getPort(
"\\S")).to_sigbit_set();
94 queue_bits.insert(bits.begin(), bits.end());
95 visited_cells.insert(pbit.cell);
97 if (
fwd_ct.
cell_known(pbit.cell->type) && visited_cells.count(pbit.cell) == 0) {
100 queue_bits.insert(bits.begin(), bits.end());
101 visited_cells.insert(pbit.cell);
122 for (
auto &p : m.
ports)
175 bool force_signed =
false, force_not_signed =
false;
181 force_not_signed =
true;
188 force_not_signed =
true;
191 if (force_signed && force_not_signed)
208 if (supercell_aux &&
GetSize(sig_a)) {
213 if (supercell_aux &&
GetSize(sig_b)) {
223 supermacc->ports.push_back(p);
229 if (p1.
in_a[i] == p2.
in_a[i] && score > 0)
233 if (p1.
in_b[i] == p2.
in_b[i] && score > 0)
242 Macc m1(c1), m2(c2), supermacc;
245 int width = std::max(w1, w2);
253 std::set<int> m1_unmapped, m2_unmapped;
255 for (
int i = 0; i <
GetSize(m1.ports); i++)
256 m1_unmapped.insert(i);
258 for (
int i = 0; i <
GetSize(m2.ports); i++)
259 m2_unmapped.insert(i);
263 int best_i = -1, best_j = -1, best_score = 0;
265 for (
int i : m1_unmapped)
266 for (
int j : m2_unmapped) {
268 if (score >= 0 && (best_i < 0 || best_score > score))
269 best_i = i, best_j = j, best_score = score;
273 m1_unmapped.erase(best_i);
274 m2_unmapped.erase(best_j);
275 share_macc_ports(m1.ports[best_i], m2.ports[best_j], w1, w2, act, &supermacc, supercell_aux);
280 for (
int i : m1_unmapped)
285 if (supercell_aux &&
GetSize(sig_a)) {
290 if (supercell_aux &&
GetSize(sig_b)) {
300 supermacc.
ports.push_back(p);
303 for (
int i : m2_unmapped)
308 if (supercell_aux &&
GetSize(sig_a)) {
313 if (supercell_aux &&
GetSize(sig_b)) {
323 supermacc.
ports.push_back(p);
333 supercell->setParam(
"\\Y_WIDTH", width);
334 supercell->setPort(
"\\Y", sig_y);
359 goto not_a_muxed_cell;
370 if (cell->type ==
"$memrd") {
371 if (!cell->parameters.at(
"\\CLK_ENABLE").as_bool())
376 if (cell->type ==
"$mul" || cell->type ==
"$div" || cell->type ==
"$mod") {
382 if (cell->type ==
"$shl" || cell->type ==
"$shr" || cell->type ==
"$sshl" || cell->type ==
"$sshr") {
401 if (c1->
type ==
"$memrd")
403 if (c1->
parameters.at(
"\\MEMID").decode_string() != c2->
parameters.at(
"\\MEMID").decode_string())
413 int a1_width = c1->
parameters.at(
"\\A_WIDTH").as_int();
414 int y1_width = c1->
parameters.at(
"\\Y_WIDTH").as_int();
416 int a2_width = c2->
parameters.at(
"\\A_WIDTH").as_int();
417 int y2_width = c2->
parameters.at(
"\\Y_WIDTH").as_int();
419 if (std::max(a1_width, a2_width) > 2 * std::min(a1_width, a2_width))
return false;
420 if (std::max(y1_width, y2_width) > 2 * std::min(y1_width, y2_width))
return false;
430 int a1_width = c1->
parameters.at(
"\\A_WIDTH").as_int();
431 int b1_width = c1->
parameters.at(
"\\B_WIDTH").as_int();
432 int y1_width = c1->
parameters.at(
"\\Y_WIDTH").as_int();
434 int a2_width = c2->
parameters.at(
"\\A_WIDTH").as_int();
435 int b2_width = c2->
parameters.at(
"\\B_WIDTH").as_int();
436 int y2_width = c2->
parameters.at(
"\\Y_WIDTH").as_int();
438 if (std::max(a1_width, a2_width) > 2 * std::min(a1_width, a2_width))
return false;
439 if (std::max(b1_width, b2_width) > 2 * std::min(b1_width, b2_width))
return false;
440 if (std::max(y1_width, y2_width) > 2 * std::min(y1_width, y2_width))
return false;
450 int a1_width = c1->
parameters.at(
"\\A_WIDTH").as_int();
451 int b1_width = c1->
parameters.at(
"\\B_WIDTH").as_int();
452 int y1_width = c1->
parameters.at(
"\\Y_WIDTH").as_int();
454 int a2_width = c2->
parameters.at(
"\\A_WIDTH").as_int();
455 int b2_width = c2->
parameters.at(
"\\B_WIDTH").as_int();
456 int y2_width = c2->
parameters.at(
"\\Y_WIDTH").as_int();
458 int min1_width = std::min(a1_width, b1_width);
459 int max1_width = std::max(a1_width, b1_width);
461 int min2_width = std::min(a2_width, b2_width);
462 int max2_width = std::max(a2_width, b2_width);
464 if (std::max(min1_width, min2_width) > 2 * std::min(min1_width, min2_width))
return false;
465 if (std::max(max1_width, max2_width) > 2 * std::min(max1_width, max2_width))
return false;
466 if (std::max(y1_width, y2_width) > 2 * std::min(y1_width, y2_width))
return false;
472 if (c1->
type ==
"$macc")
496 results.push_back(c);
514 unsigned_cell->
parameters.at(
"\\A_WIDTH") = unsigned_cell->
parameters.at(
"\\A_WIDTH").as_int() + 1;
517 unsigned_cell->
setPort(
"\\A", new_a);
519 unsigned_cell->
parameters.at(
"\\A_SIGNED") =
true;
520 unsigned_cell->
check();
523 bool a_signed = c1->
parameters.at(
"\\A_SIGNED").as_bool();
532 int a_width = std::max(a1.size(), a2.
size());
533 int y_width = std::max(y1.
size(), y2.
size());
544 supercell->
parameters[
"\\A_SIGNED"] = a_signed;
553 supercell_aux.insert(supercell);
559 bool modified_src_cells =
false;
563 int score_unflipped = std::max(c1->
parameters.at(
"\\A_WIDTH").as_int(), c2->
parameters.at(
"\\A_WIDTH").as_int()) +
566 int score_flipped = std::max(c1->
parameters.at(
"\\A_WIDTH").as_int(), c2->
parameters.at(
"\\B_WIDTH").as_int()) +
569 if (score_flipped < score_unflipped)
577 modified_src_cells =
true;
586 unsigned_cell->
parameters.at(
"\\A_WIDTH") = unsigned_cell->
parameters.at(
"\\A_WIDTH").as_int() + 1;
589 unsigned_cell->
setPort(
"\\A", new_a);
591 unsigned_cell->
parameters.at(
"\\A_SIGNED") =
true;
592 modified_src_cells =
true;
599 unsigned_cell->
parameters.at(
"\\B_WIDTH") = unsigned_cell->
parameters.at(
"\\B_WIDTH").as_int() + 1;
602 unsigned_cell->
setPort(
"\\B", new_b);
604 unsigned_cell->
parameters.at(
"\\B_SIGNED") =
true;
605 modified_src_cells =
true;
608 if (modified_src_cells) {
613 bool a_signed = c1->
parameters.at(
"\\A_SIGNED").as_bool();
614 bool b_signed = c1->
parameters.at(
"\\B_SIGNED").as_bool();
619 if (c1->
type ==
"$shl" || c1->
type ==
"$shr" || c1->
type ==
"$sshl" || c1->
type ==
"$sshr")
630 int a_width = std::max(a1.
size(), a2.
size());
631 int b_width = std::max(b1.
size(), b2.
size());
632 int y_width = std::max(y1.
size(), y2.
size());
634 if (c1->
type ==
"$shr" && a_signed)
636 a_width = std::max(y_width, a_width);
664 supercell->
parameters[
"\\A_SIGNED"] = a_signed;
665 supercell->
parameters[
"\\B_SIGNED"] = b_signed;
672 if (c1->
type ==
"$alu") {
676 supercell->
setPort(
"\\CI", ci);
677 supercell->
setPort(
"\\BI", bi);
678 supercell->
setPort(
"\\CO", co);
685 if (c1->
type ==
"$alu") {
692 supercell_aux.insert(supercell);
696 if (c1->
type ==
"$macc")
699 supercell_aux.insert(supercell);
700 share_macc(c1, c2, act, supercell, &supercell_aux);
705 if (c1->
type ==
"$memrd")
709 supercell_aux.insert(supercell);
726 static std::set<RTLIL::SigBit> empty_controls_set;
727 return empty_controls_set;
733 std::set<ModWalker::PortBit> pbits;
734 std::set<RTLIL::Cell*> consumer_cells;
738 for (
auto &bit : pbits) {
739 if ((bit.cell->type ==
"$mux" || bit.cell->type ==
"$pmux") && bit.port ==
"\\S")
741 consumer_cells.insert(bit.cell);
746 for (
auto c : consumer_cells)
767 std::map<RTLIL::SigBit, RTLIL::State> p_bits;
769 std::vector<RTLIL::SigBit> p_first_bits = p.first;
770 for (
int i = 0; i <
GetSize(p_first_bits); i++) {
773 if (p_bits.count(b) && p_bits.at(b) != v)
779 p.second.bits.clear();
781 for (
auto &it : p_bits) {
782 p.first.append_bit(it.first);
783 p.second.bits.push_back(it.second);
798 static std::set<std::pair<RTLIL::SigSpec, RTLIL::Const>> empty_patterns_set;
799 return empty_patterns_set;
806 std::set<RTLIL::Cell*> driven_cells, driven_data_muxes;
808 for (
auto &bit : cell_out_bits)
817 if ((pbit.cell->type ==
"$mux" || pbit.cell->type ==
"$pmux") && (pbit.port ==
"\\A" || pbit.port ==
"\\B"))
818 driven_data_muxes.insert(pbit.cell);
820 driven_cells.insert(pbit.cell);
826 for (
auto c : driven_data_muxes)
830 bool used_in_a =
false;
831 std::set<int> used_in_b_parts;
833 int width = c->parameters.at(
"\\WIDTH").as_int();
834 std::vector<RTLIL::SigBit> sig_a =
modwalker.
sigmap(c->getPort(
"\\A"));
835 std::vector<RTLIL::SigBit> sig_b =
modwalker.
sigmap(c->getPort(
"\\B"));
836 std::vector<RTLIL::SigBit> sig_s =
modwalker.
sigmap(c->getPort(
"\\S"));
838 for (
auto &bit : sig_a)
839 if (cell_out_bits.count(bit))
842 for (
int i = 0; i <
GetSize(sig_b); i++)
843 if (cell_out_bits.count(sig_b[i]))
844 used_in_b_parts.insert(i / width);
847 for (
auto p : c_patterns) {
848 for (
int i = 0; i <
GetSize(sig_s); i++)
854 for (
int idx : used_in_b_parts)
855 for (
auto p : c_patterns) {
862 for (
auto c : driven_cells) {
872 log(
"%sFound cell that is never activated: %s\n", indent,
log_id(cell));
883 std::set<RTLIL::SigBit> all_bits;
884 for (
auto &it : activation_patterns) {
885 std::vector<RTLIL::SigBit> bits = it.first;
886 all_bits.insert(bits.begin(), bits.end());
890 for (
auto &bit : all_bits)
897 const std::set<std::pair<RTLIL::SigSpec, RTLIL::Const>> &in,
const std::set<RTLIL::SigBit> &filter_bits)
901 std::vector<RTLIL::SigBit> p_first = p.first;
902 std::pair<RTLIL::SigSpec, RTLIL::Const> new_p;
904 for (
int i = 0; i <
GetSize(p_first); i++)
905 if (filter_bits.count(p_first[i]) == 0) {
906 new_p.first.append_bit(p_first[i]);
907 new_p.second.bits.push_back(p.second.bits.at(i));
918 for (
auto &p : activation_patterns) {
919 all_cases_wire->
width++;
923 if (all_cases_wire->
width == 1)
924 return all_cases_wire;
948 std::map<RTLIL::Cell*, std::set<RTLIL::SigBit>> cell_to_bits;
949 std::map<RTLIL::SigBit, std::set<RTLIL::Cell*>> bit_to_cells;
953 for (
auto &conn : cell->connections()) {
956 cell_to_bits[cell].insert(bit);
961 bit_to_cells[bit].insert(cell);
964 for (
auto &it : cell_to_bits)
968 for (
auto bit : it.second)
969 for (
auto c2 : bit_to_cells[bit])
970 toposort.
edge(c1, c2);
973 bool found_scc = !toposort.
sort();
977 for (
auto &loop : toposort.
loops) {
978 log(
"### loop ###\n");
991 if (stop.count(root))
1004 std::set<RTLIL::Cell*> stop;
1014 std::set<RTLIL::Cell*> queue, covered;
1017 while (!queue.empty())
1019 std::set<RTLIL::Cell*> new_queue;
1021 for (
auto c : queue) {
1024 for (
auto &conn : c->connections())
1026 for (
auto bit : conn.second)
1029 new_queue.insert(pi.cell);
1034 for (
auto c : new_queue) {
1039 if (!covered.count(c))
1053 config(config), design(design), module(module),
mi(module)
1082 log(
"Found %d cells in module %s that may be considered for resource sharing.\n",
1085 for (
auto cell : module->
cells())
1086 if (cell->type ==
"$pmux")
1087 for (
auto bit : cell->getPort(
"\\S"))
1088 for (
auto other_bit : cell->getPort(
"\\S"))
1089 if (bit < other_bit)
1090 exclusive_ctrls.push_back(std::pair<RTLIL::SigBit, RTLIL::SigBit>(bit, other_bit));
1097 log(
" Analyzing resource sharing options for %s:\n",
log_id(cell));
1102 if (cell_activation_patterns.empty()) {
1103 log(
" Cell is never active. Sharing is pointless, we simply remove it.\n");
1108 if (cell_activation_patterns.count(std::pair<RTLIL::SigSpec, RTLIL::Const>())) {
1109 log(
" Cell is always active. Therefore no sharing is possible.\n");
1113 log(
" Found %d activation_patterns using ctrl signal %s.\n",
GetSize(cell_activation_patterns),
log_signal(cell_activation_signals));
1115 std::vector<RTLIL::Cell*> candidates;
1118 if (candidates.empty()) {
1119 log(
" No candidates found.\n");
1123 log(
" Found %d candidates:",
GetSize(candidates));
1124 for (
auto c : candidates)
1128 for (
auto other_cell : candidates)
1130 log(
" Analyzing resource sharing with %s:\n",
log_id(other_cell));
1135 if (other_cell_activation_patterns.empty()) {
1136 log(
" Cell is never active. Sharing is pointless, we simply remove it.\n");
1142 if (other_cell_activation_patterns.count(std::pair<RTLIL::SigSpec, RTLIL::Const>())) {
1143 log(
" Cell is always active. Therefore no sharing is possible.\n");
1148 log(
" Found %d activation_patterns using ctrl signal %s.\n",
1149 GetSize(other_cell_activation_patterns),
log_signal(other_cell_activation_signals));
1154 std::set<RTLIL::SigBit> union_forbidden_controls;
1155 union_forbidden_controls.insert(cell_forbidden_controls.begin(), cell_forbidden_controls.end());
1156 union_forbidden_controls.insert(other_cell_forbidden_controls.begin(), other_cell_forbidden_controls.end());
1158 if (!union_forbidden_controls.empty())
1159 log(
" Forbidden control signals for this pair of cells: %s\n",
log_signal(union_forbidden_controls));
1161 std::set<std::pair<RTLIL::SigSpec, RTLIL::Const>> filtered_cell_activation_patterns;
1162 std::set<std::pair<RTLIL::SigSpec, RTLIL::Const>> filtered_other_cell_activation_patterns;
1165 filter_activation_patterns(filtered_other_cell_activation_patterns, other_cell_activation_patterns, union_forbidden_controls);
1173 std::set<RTLIL::Cell*> sat_cells;
1174 std::set<RTLIL::SigBit> bits_queue;
1176 std::vector<int> cell_active, other_cell_active;
1179 for (
auto &p : filtered_cell_activation_patterns) {
1182 all_ctrl_signals.
append(p.first);
1185 for (
auto &p : filtered_other_cell_activation_patterns) {
1188 all_ctrl_signals.
append(p.first);
1192 bits_queue.insert(bit);
1195 bits_queue.insert(bit);
1197 while (!bits_queue.empty())
1199 std::set<ModWalker::PortBit> portbits;
1203 for (
auto &pbit : portbits)
1210 sat_cells.insert(pbit.cell);
1213 if (config.
opt_fast && sat_cells.size() > 100)
1223 if (!ez.solve(ez.expression(ez.OpOr, cell_active))) {
1224 log(
" According to the SAT solver the cell %s is never active. Sharing is pointless, we simply remove it.\n",
log_id(cell));
1229 if (!ez.solve(ez.expression(ez.OpOr, other_cell_active))) {
1230 log(
" According to the SAT solver the cell %s is never active. Sharing is pointless, we simply remove it.\n",
log_id(other_cell));
1236 ez.non_incremental();
1239 std::vector<int> sat_model = satgen.
importSigSpec(all_ctrl_signals);
1240 std::vector<bool> sat_model_values;
1242 ez.assume(ez.AND(ez.expression(ez.OpOr, cell_active), ez.expression(ez.OpOr, other_cell_active)));
1244 log(
" Size of SAT problem: %d cells, %d variables, %d clauses\n",
1245 GetSize(sat_cells), ez.numCnfVariables(), ez.numCnfClauses());
1247 if (ez.solve(sat_model, sat_model_values)) {
1248 log(
" According to the SAT solver this pair of cells can not be shared.\n");
1249 log(
" Model from SAT solver: %s = %d'",
log_signal(all_ctrl_signals),
GetSize(sat_model_values));
1250 for (
int i =
GetSize(sat_model_values)-1; i >= 0; i--)
1251 log(
"%c", sat_model_values[i] ?
'1' :
'0');
1256 log(
" According to the SAT solver this pair of cells can be shared.\n");
1259 log(
" Sharing not possible: %s is in input cone of %s.\n",
log_id(other_cell),
log_id(cell));
1264 log(
" Sharing not possible: %s is in input cone of %s.\n",
log_id(cell),
log_id(other_cell));
1270 int cell_select_score = 0;
1271 int other_cell_select_score = 0;
1273 for (
auto &p : filtered_cell_activation_patterns)
1274 cell_select_score += p.first.size();
1276 for (
auto &p : filtered_other_cell_activation_patterns)
1277 other_cell_select_score += p.first.size();
1280 std::set<RTLIL::Cell*> supercell_aux;
1281 if (cell_select_score <= other_cell_select_score) {
1283 supercell =
make_supercell(cell, other_cell, act, supercell_aux);
1287 supercell =
make_supercell(other_cell, cell, act, supercell_aux);
1296 for (
auto c : supercell_aux)
1302 log(
" New topology contains loops! Rolling back..\n");
1306 for (
auto cc : supercell_aux)
1311 std::set<std::pair<RTLIL::SigSpec, RTLIL::Const>> supercell_activation_patterns;
1312 supercell_activation_patterns.insert(filtered_cell_activation_patterns.begin(), filtered_cell_activation_patterns.end());
1313 supercell_activation_patterns.insert(filtered_other_cell_activation_patterns.begin(), filtered_other_cell_activation_patterns.end());
1328 if (config.
limit > 0)
1356 log(
" share [options] [selection]\n");
1358 log(
"This pass merges shareable resources into a single resource. A SAT solver\n");
1359 log(
"is used to determine if two resources are share-able.\n");
1362 log(
" Per default the selection of cells that is considered for sharing is\n");
1363 log(
" narrowed using a list of cell types. With this option all selected\n");
1364 log(
" cells are considered for resource sharing.\n");
1366 log(
" IMPORTANT NOTE: If the -all option is used then no cells with internal\n");
1367 log(
" state must be selected!\n");
1369 log(
" -aggressive\n");
1370 log(
" Per default some heuristics are used to reduce the number of cells\n");
1371 log(
" considered for resource sharing to only large resources. This options\n");
1372 log(
" turns this heuristics off, resulting in much more cells being considered\n");
1373 log(
" for resource sharing.\n");
1376 log(
" Only consider the simple part of the control logic in SAT solving, resulting\n");
1377 log(
" in much easier SAT problems at the cost of maybe missing some oportunities\n");
1378 log(
" for resource sharing.\n");
1381 log(
" Only perform the first N merges, then stop. This is useful for debugging.\n");
1431 log_header(
"Executing SHARE pass (SAT-based resource sharing).\n");
1434 for (argidx = 1; argidx < args.size(); argidx++) {
1435 if (args[argidx] ==
"-force") {
1439 if (args[argidx] ==
"-aggressive") {
1443 if (args[argidx] ==
"-fast") {
1447 if (args[argidx] ==
"-limit" && argidx+1 < args.size()) {
1448 config.
limit = atoi(args[++argidx].c_str());
1455 for (
auto &mod_it : design->
modules_)
1456 if (design->
selected(mod_it.second))
void to_cell(RTLIL::Cell *cell) const
std::map< RTLIL::SigBit, std::set< PortBit > > signal_consumers
bool selected(T1 *module) const
bool find_in_input_cone(RTLIL::Cell *root, RTLIL::Cell *needle)
void find_terminal_bits()
bool is_shareable_pair(RTLIL::Cell *c1, RTLIL::Cell *c2)
std::map< RTLIL::Cell *, std::set< RTLIL::SigBit > > cell_outputs
void find_shareable_cells()
std::map< bitDef_t, shared_bit_data_t * > bits
std::set< RTLIL::SigBit > signal_outputs
void sort(T *array, int size, LessThan lt)
std::set< std::set< T, C > > loops
RTLIL::Cell * addCell(RTLIL::IdString name, RTLIL::IdString type)
void log_header(const char *format,...)
std::set< RTLIL::SigBit > terminal_bits
static int bits_macc(const Macc &m, int width)
std::map< RTLIL::Cell *, std::set< RTLIL::Cell *, cell_ptr_cmp >, cell_ptr_cmp > topo_cell_drivers
std::set< RTLIL::IdString > generic_other_ops
int importSigBit(RTLIL::SigBit bit, int timestep=-1)
bool is_part_of_scc(RTLIL::Cell *cell)
const char * log_signal(const RTLIL::SigSpec &sig, bool autoint)
static std::string idx(std::string str)
void setPort(RTLIL::IdString portname, RTLIL::SigSpec signal)
RTLIL::Cell * addEq(RTLIL::IdString name, RTLIL::SigSpec sig_a, RTLIL::SigSpec sig_b, RTLIL::SigSpec sig_y, bool is_signed=false)
std::vector< int > importSigSpec(RTLIL::SigSpec sig, int timestep=-1)
std::vector< port_t > ports
USING_YOSYS_NAMESPACE PRIVATE_NAMESPACE_BEGIN typedef RTLIL::IdString::compare_ptr_by_name< RTLIL::Cell > cell_ptr_cmp
std::map< RTLIL::IdString, RTLIL::Const > parameters
void extend_u0(int width, bool is_signed=false)
std::set< RTLIL::IdString > generic_uni_ops
std::set< RTLIL::Cell * > recursion_state
bool get_drivers(std::set< PortBit > &result, RTLIL::SigBit bit) const
RTLIL::Cell * addReduceOr(RTLIL::IdString name, RTLIL::SigSpec sig_a, RTLIL::SigSpec sig_y, bool is_signed=false)
static int bits_macc_port(const Macc::port_t &p, int width)
ShareWorker(ShareWorkerConfig config, RTLIL::Design *design, RTLIL::Module *module)
const std::set< std::pair< RTLIL::SigSpec, RTLIL::Const > > & find_cell_activation_patterns(RTLIL::Cell *cell, const char *indent)
void filter_activation_patterns(std::set< std::pair< RTLIL::SigSpec, RTLIL::Const >> &out, const std::set< std::pair< RTLIL::SigSpec, RTLIL::Const >> &in, const std::set< RTLIL::SigBit > &filter_bits)
YOSYS_NAMESPACE_BEGIN typedef ezMiniSAT ezDefaultSAT
bool get_consumers(std::set< PortBit > &result, RTLIL::SigBit bit) const
std::map< RTLIL::IdString, CellType > cell_types
void set(RTLIL::Module *module)
bool cell_known(RTLIL::IdString type)
void connect(const RTLIL::SigSig &conn)
void append_bit(const RTLIL::SigBit &bit)
bool importedSigBit(RTLIL::SigBit bit, int timestep=-1)
static bool cmp_macc_ports(const Macc::port_t &p1, const Macc::port_t &p2)
#define PRIVATE_NAMESPACE_BEGIN
bool cell_output(RTLIL::IdString type, RTLIL::IdString port)
const RTLIL::SigSpec & getPort(RTLIL::IdString portname) const
void edge(T left, T right)
std::map< RTLIL::SigBit, std::set< RTLIL::Cell *, cell_ptr_cmp > > topo_bit_drivers
int GetSize(RTLIL::Wire *wire)
#define log_assert(_assert_expr_)
RTLIL::Wire * addWire(RTLIL::IdString name, int width=1)
std::map< T, std::set< T, C >, C > database
std::map< RTLIL::Cell *, std::set< RTLIL::SigBit > > cell_inputs
#define PRIVATE_NAMESPACE_END
std::map< RTLIL::Cell *, std::set< std::pair< RTLIL::SigSpec, RTLIL::Const > > > activation_patterns_cache
static int bits_macc(RTLIL::Cell *c)
std::map< RTLIL::Cell *, std::set< RTLIL::SigBit > > forbidden_controls_cache
void optimize_activation_patterns(std::set< std::pair< RTLIL::SigSpec, RTLIL::Const >> &)
std::set< RTLIL::IdString > generic_cbin_ops
#define USING_YOSYS_NAMESPACE
RTLIL::ObjRange< RTLIL::Cell * > cells()
std::set< RTLIL::Cell *, RTLIL::sort_by_name_str< RTLIL::Cell > > shareable_cells
std::map< RTLIL::IdString, RTLIL::Module * > modules_
void setup(RTLIL::Design *design, RTLIL::Module *module, CellTypes *filter_ct=NULL)
std::map< RTLIL::IdString, RTLIL::Cell * > cells_
void remove(const std::set< RTLIL::Wire * > &wires)
std::set< RTLIL::Cell * > cells_to_remove
int share_macc(RTLIL::Cell *c1, RTLIL::Cell *c2, RTLIL::SigSpec act=RTLIL::SigSpec(), RTLIL::Cell *supercell=nullptr, std::set< RTLIL::Cell * > *supercell_aux=nullptr)
int share_macc_ports(Macc::port_t &p1, Macc::port_t &p2, int w1, int w2, RTLIL::SigSpec act=RTLIL::SigSpec(), Macc *supermacc=nullptr, std::set< RTLIL::Cell * > *supercell_aux=nullptr)
RTLIL::Cell * addMux(RTLIL::IdString name, RTLIL::SigSpec sig_a, RTLIL::SigSpec sig_b, RTLIL::SigSpec sig_s, RTLIL::SigSpec sig_y)
void log(const char *format,...)
RTLIL::SigSpec bits_from_activation_patterns(const std::set< std::pair< RTLIL::SigSpec, RTLIL::Const >> &activation_patterns)
bool importCell(RTLIL::Cell *cell, int timestep=-1)
RTLIL::SigSpec make_cell_activation_logic(const std::set< std::pair< RTLIL::SigSpec, RTLIL::Const >> &activation_patterns, std::set< RTLIL::Cell * > &supercell_aux)
void append(const RTLIL::SigSpec &signal)
RTLIL::Cell * make_supercell(RTLIL::Cell *c1, RTLIL::Cell *c2, RTLIL::SigSpec act, std::set< RTLIL::Cell * > &supercell_aux)
bool cell_input(RTLIL::IdString type, RTLIL::IdString port)
virtual void execute(std::vector< std::string > args, RTLIL::Design *design)
RTLIL::Cell * addPos(RTLIL::IdString name, RTLIL::SigSpec sig_a, RTLIL::SigSpec sig_y, bool is_signed=false)
void extra_args(std::vector< std::string > args, size_t argidx, RTLIL::Design *design, bool select=true)
void find_shareable_partners(std::vector< RTLIL::Cell * > &results, RTLIL::Cell *cell)
std::pair< SigSpec, SigSpec > SigSig
const char * log_id(RTLIL::IdString str)
std::vector< std::pair< RTLIL::SigBit, RTLIL::SigBit > > exclusive_ctrls
std::vector< RTLIL::SigBit > to_sigbit_vector() const
std::set< RTLIL::IdString > generic_ops
std::set< PortInfo > & query_ports(RTLIL::SigBit bit)
const std::set< RTLIL::SigBit > & find_forbidden_controls(RTLIL::Cell *cell)
bool sort_check_activation_pattern(std::pair< RTLIL::SigSpec, RTLIL::Const > &p)
std::set< RTLIL::IdString > generic_bin_ops
bool find_in_input_cone_worker(RTLIL::Cell *root, RTLIL::Cell *needle, std::set< RTLIL::Cell * > &stop)