3
0
Fork 0
mirror of https://github.com/YosysHQ/yosys synced 2025-04-05 09:04:08 +00:00

Merge pull request #4904 from YosysHQ/emil/share-limit-effort

share: add -pattern-limit to limit analysis effort
This commit is contained in:
Emil J 2025-03-15 18:00:42 +01:00 committed by GitHub
commit 05cd1e2942
No known key found for this signature in database
GPG key ID: B5690EEEBB952194

View file

@ -23,6 +23,7 @@
#include "kernel/modtools.h"
#include "kernel/utils.h"
#include "kernel/macc.h"
#include <iterator>
USING_YOSYS_NAMESPACE
PRIVATE_NAMESPACE_BEGIN
@ -33,6 +34,7 @@ typedef std::pair<RTLIL::SigSpec, RTLIL::Const> ssc_pair_t;
struct ShareWorkerConfig
{
int limit;
size_t pattern_limit;
bool opt_force;
bool opt_aggressive;
bool opt_fast;
@ -853,6 +855,23 @@ struct ShareWorker
optimize_activation_patterns(patterns);
}
template<typename Iterator>
bool insert_capped(pool<ssc_pair_t>& cache, Iterator begin_pattern, Iterator end_pattern)
{
if (cache.size() + std::distance(begin_pattern, end_pattern) > config.pattern_limit) {
cache.clear();
cache.insert(ssc_pair_t());
return false;
} else {
cache.insert(begin_pattern, end_pattern);
}
return true;
}
bool insert_capped(pool<ssc_pair_t>& cache, ssc_pair_t pattern)
{
return insert_capped(cache, &pattern, &pattern + 1);
}
const pool<ssc_pair_t> &find_cell_activation_patterns(RTLIL::Cell *cell, const char *indent)
{
if (recursion_state.count(cell)) {
@ -909,20 +928,29 @@ struct ShareWorker
for (int i = 0; i < GetSize(sig_s); i++)
p.first.append(sig_s[i]), p.second.bits().push_back(RTLIL::State::S0);
if (sort_check_activation_pattern(p))
activation_patterns_cache[cell].insert(p);
if (!insert_capped(activation_patterns_cache[cell], p)) {
recursion_state.erase(cell);
return activation_patterns_cache[cell];
}
}
for (int idx : used_in_b_parts)
for (auto p : c_patterns) {
p.first.append(sig_s[idx]), p.second.bits().push_back(RTLIL::State::S1);
if (sort_check_activation_pattern(p))
activation_patterns_cache[cell].insert(p);
if (!insert_capped(activation_patterns_cache[cell], p)) {
recursion_state.erase(cell);
return activation_patterns_cache[cell];
}
}
}
for (auto c : driven_cells) {
const pool<ssc_pair_t> &c_patterns = find_cell_activation_patterns(c, indent);
activation_patterns_cache[cell].insert(c_patterns.begin(), c_patterns.end());
if (!insert_capped(activation_patterns_cache[cell], c_patterns.begin(), c_patterns.end())) {
recursion_state.erase(cell);
return activation_patterns_cache[cell];
}
}
log_assert(recursion_state.count(cell) != 0);
@ -1438,12 +1466,18 @@ struct SharePass : public Pass {
log(" -limit N\n");
log(" Only perform the first N merges, then stop. This is useful for debugging.\n");
log("\n");
log(" -pattern-limit N\n");
log(" Only analyze up to N activation patterns per cell, otherwise assume active.\n");
log(" N is 1000 by default. Higher values may merge more resources at the cost of\n");
log(" more runtime and memory consumption.\n");
log("\n");
}
void execute(std::vector<std::string> args, RTLIL::Design *design) override
{
ShareWorkerConfig config;
config.limit = -1;
config.pattern_limit = design->scratchpad_get_int("share.pattern_limit", 1000);
config.opt_force = false;
config.opt_aggressive = false;
config.opt_fast = false;
@ -1508,6 +1542,10 @@ struct SharePass : public Pass {
config.limit = atoi(args[++argidx].c_str());
continue;
}
if (args[argidx] == "-pattern-limit" && argidx+1 < args.size()) {
config.pattern_limit = atoi(args[++argidx].c_str());
continue;
}
break;
}
extra_args(args, argidx, design);