3
0
Fork 0
mirror of https://github.com/YosysHQ/yosys synced 2026-02-06 09:16:19 +00:00
This commit is contained in:
Emil J 2026-01-16 23:56:45 +01:00 committed by GitHub
commit 7e3e156f70
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
10 changed files with 392 additions and 8 deletions

View file

@ -658,6 +658,30 @@ RTLIL::Const RTLIL::const_bmux(const RTLIL::Const &arg1, const RTLIL::Const &arg
return t;
}
RTLIL::Const RTLIL::const_priority(const RTLIL::Const &arg, int p_width, const RTLIL::Const &polarity)
{
std::vector<State> t;
for (int offset = 0; offset < GetSize(arg); offset += p_width)
{
std::optional<State> first_non_zero = std::nullopt;
for (int i = offset; i < offset + p_width; i++)
{
RTLIL::State s = arg.at(i);
if (first_non_zero && s != State::Sx) {
auto inactive = polarity[i] == State::S0 ? State::S1 : State::S0;
auto val = *first_non_zero == State::Sx ? State::Sx : inactive;
t.push_back(val);
} else {
t.push_back(s);
}
if ((!first_non_zero && s == polarity[i]) || s == State::Sx) {
first_non_zero = s;
}
}
}
return t;
}
RTLIL::Const RTLIL::const_demux(const RTLIL::Const &arg1, const RTLIL::Const &arg2)
{
int width = GetSize(arg1);

View file

@ -118,7 +118,7 @@ struct CellTypes
void setup_internals_eval()
{
std::vector<RTLIL::IdString> unary_ops = {
ID($not), ID($pos), ID($buf), ID($neg),
ID($not), ID($pos), ID($buf), ID($neg), ID($priority),
ID($reduce_and), ID($reduce_or), ID($reduce_xor), ID($reduce_xnor), ID($reduce_bool),
ID($logic_not), ID($slice), ID($lut), ID($sop)
};
@ -509,6 +509,11 @@ struct CellTypes
return default_ret;
}
if (cell->type == ID($priority))
{
return const_priority(arg1, cell->getParam(ID::P_WIDTH).as_int(), cell->getParam(ID::POLARITY));
}
bool signed_a = cell->parameters.count(ID::A_SIGNED) > 0 && cell->parameters[ID::A_SIGNED].as_bool();
bool signed_b = cell->parameters.count(ID::B_SIGNED) > 0 && cell->parameters[ID::B_SIGNED].as_bool();
int result_len = cell->parameters.count(ID::Y_WIDTH) > 0 ? cell->parameters[ID::Y_WIDTH].as_int() : -1;

View file

@ -259,6 +259,7 @@ X($pmux)
X($pos)
X($pow)
X($print)
X($priority)
X($recrem)
X($reduce_and)
X($reduce_bool)
@ -614,6 +615,7 @@ X(PATTERN)
X(PCIN)
X(PIPELINE_16x16_MULT_REG1)
X(PIPELINE_16x16_MULT_REG2)
X(POLARITY)
X(PORTID)
X(PORT_A1_ADDR)
X(PORT_A1_CLK)
@ -678,6 +680,7 @@ X(PRODUCT_NEGATED)
X(P_BYPASS)
X(P_EN)
X(P_SRST_N)
X(P_WIDTH)
X(Q)
X(QL_DSP2)
X(R)

View file

@ -2654,6 +2654,15 @@ namespace {
check_expected();
return;
}
if (cell->type.in(ID($priority))) {
param(ID::WIDTH);
param(ID::P_WIDTH);
param(ID::POLARITY);
port(ID::A, param(ID::P_WIDTH)*param(ID::WIDTH));
port(ID::Y, param(ID::P_WIDTH)*param(ID::WIDTH));
check_expected();
return;
}
/*
* Checklist for adding internal cell types
* ========================================
@ -3969,6 +3978,14 @@ RTLIL::Cell* RTLIL::Module::addDlatchsr(RTLIL::IdString name, const RTLIL::SigSp
cell->set_src_attribute(src);
return cell;
}
RTLIL::Cell* RTLIL::Module::addPriority(RTLIL::IdString name, const RTLIL::SigSpec &sig_a, const RTLIL::SigSpec &sig_y, const std::string &src)
{
RTLIL::Cell *cell = addCell(name, ID($priority));
cell->setPort(ID::A, sig_a);
cell->setPort(ID::Y, sig_y);
cell->set_src_attribute(src);
return cell;
}
RTLIL::Cell* RTLIL::Module::addSrGate(RTLIL::IdString name, const RTLIL::SigSpec &sig_set, const RTLIL::SigSpec &sig_clr,
const RTLIL::SigSpec &sig_q, bool set_polarity, bool clr_polarity, const std::string &src)
@ -4528,7 +4545,8 @@ void RTLIL::Cell::check()
void RTLIL::Cell::fixup_parameters(bool set_a_signed, bool set_b_signed)
{
if (!type.begins_with("$") || type.begins_with("$_") || type.begins_with("$paramod") || type.begins_with("$fmcombine") ||
type.begins_with("$verific$") || type.begins_with("$array:") || type.begins_with("$extern:"))
type.begins_with("$verific$") || type.begins_with("$array:") || type.begins_with("$extern:")||
type.begins_with("$priority"))
return;
if (type == ID($buf) || type == ID($mux) || type == ID($pmux) || type == ID($bmux) || type == ID($bwmux) || type == ID($bweqx)) {

View file

@ -848,6 +848,7 @@ namespace RTLIL {
RTLIL::Const const_pmux (const RTLIL::Const &arg1, const RTLIL::Const &arg2, const RTLIL::Const &arg3);
RTLIL::Const const_bmux (const RTLIL::Const &arg1, const RTLIL::Const &arg2);
RTLIL::Const const_demux (const RTLIL::Const &arg1, const RTLIL::Const &arg2);
RTLIL::Const const_priority (const RTLIL::Const &arg, int p_width, const RTLIL::Const &polarity);
RTLIL::Const const_bweqx (const RTLIL::Const &arg1, const RTLIL::Const &arg2);
RTLIL::Const const_bwmux (const RTLIL::Const &arg1, const RTLIL::Const &arg2, const RTLIL::Const &arg3);
@ -2262,6 +2263,8 @@ public:
RTLIL::Cell* addAdlatch (RTLIL::IdString name, const RTLIL::SigSpec &sig_en, const RTLIL::SigSpec &sig_arst, const RTLIL::SigSpec &sig_d, const RTLIL::SigSpec &sig_q, RTLIL::Const arst_value, bool en_polarity = true, bool arst_polarity = true, const std::string &src = "");
RTLIL::Cell* addDlatchsr (RTLIL::IdString name, const RTLIL::SigSpec &sig_en, const RTLIL::SigSpec &sig_set, const RTLIL::SigSpec &sig_clr, RTLIL::SigSpec sig_d, const RTLIL::SigSpec &sig_q, bool en_polarity = true, bool set_polarity = true, bool clr_polarity = true, const std::string &src = "");
RTLIL::Cell* addPriority (RTLIL::IdString name, const RTLIL::SigSpec &sig_a, const RTLIL::SigSpec &sig_y, const std::string &src = "");
RTLIL::Cell* addBufGate (RTLIL::IdString name, const RTLIL::SigBit &sig_a, const RTLIL::SigBit &sig_y, const std::string &src = "");
RTLIL::Cell* addNotGate (RTLIL::IdString name, const RTLIL::SigBit &sig_a, const RTLIL::SigBit &sig_y, const std::string &src = "");
RTLIL::Cell* addAndGate (RTLIL::IdString name, const RTLIL::SigBit &sig_a, const RTLIL::SigBit &sig_b, const RTLIL::SigBit &sig_y, const std::string &src = "");

View file

@ -430,6 +430,47 @@ bool SatGen::importCell(RTLIL::Cell *cell, int timestep)
return true;
}
if (cell->type == ID($priority))
{
std::vector<int> a = importDefSigSpec(cell->getPort(ID::A), timestep);
std::vector<int> y = importDefSigSpec(cell->getPort(ID::Y), timestep);
std::vector<int> yy = model_undef ? ez->vec_var(y.size()) : y;
const Const& polarity = cell->getParam(ID::POLARITY);
int p_width = cell->getParam(ID::P_WIDTH).as_int();
for (size_t offset = 0; offset < a.size(); offset += p_width) {
int any_previous_active;
if (p_width) {
any_previous_active = polarity[offset] ? a[offset] : ez->NOT(a[offset]);
ez->assume(ez->IFF(yy[offset], a[offset]));
}
for (size_t i = offset + 1; i < offset + p_width; i++) {
int inactive_val = !polarity[i] ? ez->CONST_TRUE : ez->CONST_FALSE;
int active_val = polarity[i] ? ez->CONST_TRUE : ez->CONST_FALSE;
ez->assume(ez->IFF(yy[i], ez->ITE(any_previous_active, inactive_val, a[i])));
any_previous_active = ez->OR(any_previous_active, ez->IFF(a[i], active_val));
}
if (model_undef) {
std::vector<int> undef_a = importUndefSigSpec(cell->getPort(ID::A), timestep);
std::vector<int> undef_y = importUndefSigSpec(cell->getPort(ID::Y), timestep);
int any_previous_undef;
if (p_width) {
any_previous_undef = undef_a[offset];
ez->assume(ez->IFF(undef_y[offset], undef_a[offset]));
}
for (size_t i = offset + 1; i < offset + p_width; i++) {
any_previous_undef = ez->OR(any_previous_undef, undef_a[i]);
ez->assume(ez->IFF(undef_y[i], any_previous_undef));
}
undefGating(y, yy, undef_y);
}
}
return true;
}
if (cell->type.in(ID($pos), ID($buf), ID($neg)))
{
std::vector<int> a = importDefSigSpec(cell->getPort(ID::A), timestep);