Merge pull request #329 from YosysHQ/dave/net_aliases
json: Add support for net aliases
This commit is contained in:
commit
bc6b47efe0
@ -474,10 +474,10 @@ void BaseCtx::addClock(IdString net, float freq)
|
||||
cc->period = getCtx()->getDelayFromNS(1000 / freq);
|
||||
cc->high = getCtx()->getDelayFromNS(500 / freq);
|
||||
cc->low = getCtx()->getDelayFromNS(500 / freq);
|
||||
if (!nets.count(net)) {
|
||||
if (!net_aliases.count(net)) {
|
||||
log_warning("net '%s' does not exist in design, ignoring clock constraint\n", net.c_str(this));
|
||||
} else {
|
||||
nets.at(net)->clkconstr = std::move(cc);
|
||||
getNetByAlias(net)->clkconstr = std::move(cc);
|
||||
log_info("constraining clock net '%s' to %.02f MHz\n", net.c_str(this), freq);
|
||||
}
|
||||
}
|
||||
|
@ -609,6 +609,9 @@ struct BaseCtx
|
||||
std::unordered_map<IdString, std::unique_ptr<NetInfo>> nets;
|
||||
std::unordered_map<IdString, std::unique_ptr<CellInfo>> cells;
|
||||
|
||||
// Aliases for nets, which may have more than one name due to assignments and hierarchy
|
||||
std::unordered_map<IdString, IdString> net_aliases;
|
||||
|
||||
// Top-level ports
|
||||
std::unordered_map<IdString, PortInfo> ports;
|
||||
|
||||
@ -738,6 +741,8 @@ struct BaseCtx
|
||||
TimingConstrObjectId timingCellObject(CellInfo *cell);
|
||||
TimingConstrObjectId timingPortObject(CellInfo *cell, IdString port);
|
||||
|
||||
NetInfo *getNetByAlias(IdString alias) const { return nets.at(net_aliases.at(alias)).get(); }
|
||||
|
||||
void addConstraint(std::unique_ptr<TimingConstraint> constr);
|
||||
void removeConstraint(IdString constrName);
|
||||
|
||||
|
@ -125,12 +125,17 @@ void arch_wrap_python()
|
||||
|
||||
typedef std::unordered_map<IdString, std::unique_ptr<CellInfo>> CellMap;
|
||||
typedef std::unordered_map<IdString, std::unique_ptr<NetInfo>> NetMap;
|
||||
typedef std::unordered_map<IdString, IdString> AliasMap;
|
||||
|
||||
readonly_wrapper<Context, decltype(&Context::cells), &Context::cells, wrap_context<CellMap &>>::def_wrap(ctx_cls,
|
||||
"cells");
|
||||
readonly_wrapper<Context, decltype(&Context::nets), &Context::nets, wrap_context<NetMap &>>::def_wrap(ctx_cls,
|
||||
"nets");
|
||||
readonly_wrapper<Context, decltype(&Context::net_aliases), &Context::net_aliases,
|
||||
wrap_context<AliasMap &>>::def_wrap(ctx_cls, "net_aliases");
|
||||
|
||||
fn_wrapper_1a<Context, decltype(&Context::getNetByAlias), &Context::getNetByAlias, deref_and_wrap<NetInfo>,
|
||||
conv_from_str<IdString>>::def_wrap(ctx_cls, "getNetByAlias");
|
||||
fn_wrapper_2a_v<Context, decltype(&Context::addClock), &Context::addClock, conv_from_str<IdString>,
|
||||
pass_through<float>>::def_wrap(ctx_cls, "addClock");
|
||||
fn_wrapper_5a_v<Context, decltype(&Context::createRectangularRegion), &Context::createRectangularRegion,
|
||||
|
@ -136,12 +136,17 @@ void arch_wrap_python()
|
||||
|
||||
typedef std::unordered_map<IdString, std::unique_ptr<CellInfo>> CellMap;
|
||||
typedef std::unordered_map<IdString, std::unique_ptr<NetInfo>> NetMap;
|
||||
typedef std::unordered_map<IdString, IdString> AliasMap;
|
||||
|
||||
readonly_wrapper<Context, decltype(&Context::cells), &Context::cells, wrap_context<CellMap &>>::def_wrap(ctx_cls,
|
||||
"cells");
|
||||
readonly_wrapper<Context, decltype(&Context::nets), &Context::nets, wrap_context<NetMap &>>::def_wrap(ctx_cls,
|
||||
"nets");
|
||||
readonly_wrapper<Context, decltype(&Context::net_aliases), &Context::net_aliases,
|
||||
wrap_context<AliasMap &>>::def_wrap(ctx_cls, "net_aliases");
|
||||
|
||||
fn_wrapper_1a<Context, decltype(&Context::getNetByAlias), &Context::getNetByAlias, deref_and_wrap<NetInfo>,
|
||||
conv_from_str<IdString>>::def_wrap(ctx_cls, "getNetByAlias");
|
||||
fn_wrapper_2a_v<Context, decltype(&Context::addClock), &Context::addClock, conv_from_str<IdString>,
|
||||
pass_through<float>>::def_wrap(ctx_cls, "addClock");
|
||||
fn_wrapper_5a_v<Context, decltype(&Context::createRectangularRegion), &Context::createRectangularRegion,
|
||||
|
@ -805,7 +805,7 @@ void json_import(Context *ctx, string modname, JsonNode *node)
|
||||
};
|
||||
|
||||
// Import netnames
|
||||
std::vector<std::string> netlabels;
|
||||
std::vector<std::vector<std::string>> netlabels;
|
||||
if (node->data_dict.count("netnames")) {
|
||||
JsonNode *cell_parent = node->data_dict.at("netnames");
|
||||
for (int nnid = 0; nnid < GetSize(cell_parent->data_dict_keys); nnid++) {
|
||||
@ -838,15 +838,26 @@ void json_import(Context *ctx, string modname, JsonNode *node)
|
||||
ndx = start_offset + num_bits - i - 1;
|
||||
std::string name =
|
||||
basename + (num_bits == 1 ? "" : std::string("[") + std::to_string(ndx) + std::string("]"));
|
||||
if (prefer_netlabel(name, netlabels.at(netid)))
|
||||
netlabels.at(netid) = name;
|
||||
netlabels.at(netid).push_back(name);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
std::vector<IdString> netids;
|
||||
std::transform(netlabels.begin(), netlabels.end(), std::back_inserter(netids),
|
||||
[ctx](const std::string &s) { return ctx->id(s); });
|
||||
for (size_t i = 0; i < netlabels.size(); i++) {
|
||||
auto &labels = netlabels.at(i);
|
||||
if (labels.empty()) {
|
||||
// Backup for unnamed nets (not sure if these should actually happen)
|
||||
netids.push_back(ctx->id("$nextpnr$unknown_netname$" + std::to_string(i)));
|
||||
} else {
|
||||
// Pick a primary name for the net according to a simple heuristic
|
||||
std::string pref = labels.at(0);
|
||||
for (size_t j = 1; j < labels.size(); j++)
|
||||
if (prefer_netlabel(labels.at(j), pref))
|
||||
pref = labels.at(j);
|
||||
netids.push_back(ctx->id(pref));
|
||||
}
|
||||
}
|
||||
if (node->data_dict.count("cells")) {
|
||||
JsonNode *cell_parent = node->data_dict.at("cells");
|
||||
//
|
||||
@ -921,6 +932,17 @@ void json_import(Context *ctx, string modname, JsonNode *node)
|
||||
}
|
||||
}
|
||||
}
|
||||
// Import net aliases
|
||||
for (size_t i = 0; i < netids.size(); i++) {
|
||||
IdString netname = netids.at(i);
|
||||
if (!ctx->nets.count(netname))
|
||||
continue;
|
||||
for (auto &label : netlabels.at(i)) {
|
||||
IdString labelid = ctx->id(label);
|
||||
NPNR_ASSERT(!ctx->net_aliases.count(labelid));
|
||||
ctx->net_aliases[labelid] = netname;
|
||||
}
|
||||
}
|
||||
check_all_nets_driven(ctx);
|
||||
ctx->settings[ctx->id("synth")] = 1;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user