diff options
51 files changed, 472 insertions, 302 deletions
@@ -123,7 +123,7 @@ LDFLAGS += -rdynamic LDLIBS += -lrt endif -YOSYS_VER := 0.9+3568 +YOSYS_VER := 0.9+3599 GIT_REV := $(shell cd $(YOSYS_SRC) && git rev-parse --short HEAD 2> /dev/null || echo UNKNOWN) OBJS = kernel/version_$(GIT_REV).o @@ -171,8 +171,7 @@ else PYTHON_CONFIG := $(PYTHON_EXECUTABLE)-config endif -PYTHON_PREFIX := $(shell $(PYTHON_CONFIG) --prefix) -PYTHON_DESTDIR := $(PYTHON_PREFIX)/lib/python$(PYTHON_VERSION)/site-packages +PYTHON_DESTDIR := $(shell $(PYTHON_EXECUTABLE) -c "import site; print(site.getsitepackages()[-1]);") # Reload Makefile.conf to override python specific variables if defined ifneq ($(wildcard Makefile.conf),) @@ -686,7 +685,7 @@ endif %.pyh: %.h $(Q) mkdir -p $(dir $@) - $(P) cat $< | grep -E -v "#[ ]*(include|error)" | $(LD) -x c++ -o $@ -E -P - + $(P) cat $< | grep -E -v "#[ ]*(include|error)" | $(LD) $(CXXFLAGS) -x c++ -o $@ -E -P - ifeq ($(ENABLE_PYOSYS),1) $(PY_WRAPPER_FILE).cc: misc/$(PY_GEN_SCRIPT).py $(PY_WRAP_INCLUDES) @@ -846,9 +845,9 @@ ifeq ($(ENABLE_LIBYOSYS),1) $(INSTALL_SUDO) cp libyosys.so $(DESTDIR)$(LIBDIR)/ $(INSTALL_SUDO) $(STRIP) -S $(DESTDIR)$(LIBDIR)/libyosys.so ifeq ($(ENABLE_PYOSYS),1) - $(INSTALL_SUDO) mkdir -p $(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys - $(INSTALL_SUDO) cp libyosys.so $(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys/libyosys.so - $(INSTALL_SUDO) cp misc/__init__.py $(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys/ + $(INSTALL_SUDO) mkdir -p $(DESTDIR)$(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys + $(INSTALL_SUDO) cp libyosys.so $(DESTDIR)$(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys/libyosys.so + $(INSTALL_SUDO) cp misc/__init__.py $(DESTDIR)$(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys/ endif endif @@ -858,9 +857,9 @@ uninstall: ifeq ($(ENABLE_LIBYOSYS),1) $(INSTALL_SUDO) rm -vf $(DESTDIR)$(LIBDIR)/libyosys.so ifeq ($(ENABLE_PYOSYS),1) - $(INSTALL_SUDO) rm -vf $(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys/libyosys.so - $(INSTALL_SUDO) rm -vf $(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys/__init__.py - $(INSTALL_SUDO) rmdir $(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys + $(INSTALL_SUDO) rm -vf $(DESTDIR)$(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys/libyosys.so + $(INSTALL_SUDO) rm -vf $(DESTDIR)$(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys/__init__.py + $(INSTALL_SUDO) rmdir $(DESTDIR)$(PYTHON_DESTDIR)/$(subst -,_,$(PROGRAM_PREFIX))pyosys endif endif diff --git a/backends/aiger/aiger.cc b/backends/aiger/aiger.cc index 81a3f483b..476b30488 100644 --- a/backends/aiger/aiger.cc +++ b/backends/aiger/aiger.cc @@ -111,7 +111,7 @@ struct AigerWriter // promote public wires for (auto wire : module->wires()) - if (wire->name[0] == '\\') + if (wire->name.isPublic()) sigmap.add(wire); // promote input wires diff --git a/backends/aiger/xaiger.cc b/backends/aiger/xaiger.cc index ef0103c17..27499b64a 100644 --- a/backends/aiger/xaiger.cc +++ b/backends/aiger/xaiger.cc @@ -146,7 +146,7 @@ struct XAigerWriter // promote public wires for (auto wire : module->wires()) - if (wire->name[0] == '\\') + if (wire->name.isPublic()) sigmap.add(wire); // promote input wires diff --git a/backends/edif/edif.cc b/backends/edif/edif.cc index 5e6becfd0..e0013238c 100644 --- a/backends/edif/edif.cc +++ b/backends/edif/edif.cc @@ -330,7 +330,7 @@ struct EdifBackend : public Backend { } *f << stringf("\n (property %s (string \"%d'h%s\"))", EDIF_DEF(name), GetSize(val.bits), hex_string.c_str()); } - }; + }; for (auto module : sorted_modules) { if (module->get_blackbox_attribute()) @@ -373,8 +373,8 @@ struct EdifBackend : public Backend { } { - int c1 = w1->name[0] == '\\'; - int c2 = w2->name[0] == '\\'; + int c1 = w1->name.isPublic(); + int c2 = w2->name.isPublic(); if (c1 > c2) goto promote; if (c1 < c2) goto nopromote; @@ -524,7 +524,7 @@ struct EdifBackend : public Backend { *f << stringf(" (portRef %c (instanceRef GND))\n", gndvccy ? 'Y' : 'G'); if (sig == RTLIL::State::S1) *f << stringf(" (portRef %c (instanceRef VCC))\n", gndvccy ? 'Y' : 'P'); - } + } *f << stringf(" )"); if (attr_properties && sig.wire != NULL) for (auto &p : sig.wire->attributes) diff --git a/backends/smt2/smt2.cc b/backends/smt2/smt2.cc index 4a53ce6d5..0b4e20ac6 100644 --- a/backends/smt2/smt2.cc +++ b/backends/smt2/smt2.cc @@ -822,7 +822,7 @@ struct Smt2Worker for (auto bit : SigSpec(wire)) if (reg_bits.count(bit)) is_register = true; - if (wire->port_id || is_register || wire->get_bool_attribute(ID::keep) || (wiresmode && wire->name[0] == '\\')) { + if (wire->port_id || is_register || wire->get_bool_attribute(ID::keep) || (wiresmode && wire->name.isPublic())) { RTLIL::SigSpec sig = sigmap(wire); std::vector<std::string> comments; if (wire->port_input) @@ -831,7 +831,7 @@ struct Smt2Worker comments.push_back(stringf("; yosys-smt2-output %s %d\n", get_id(wire), wire->width)); if (is_register) comments.push_back(stringf("; yosys-smt2-register %s %d\n", get_id(wire), wire->width)); - if (wire->get_bool_attribute(ID::keep) || (wiresmode && wire->name[0] == '\\')) + if (wire->get_bool_attribute(ID::keep) || (wiresmode && wire->name.isPublic())) comments.push_back(stringf("; yosys-smt2-wire %s %d\n", get_id(wire), wire->width)); if (GetSize(wire) == 1 && (clock_posedge.count(sig) || clock_negedge.count(sig))) comments.push_back(stringf("; yosys-smt2-clock %s%s%s\n", get_id(wire), diff --git a/backends/verilog/verilog_backend.cc b/backends/verilog/verilog_backend.cc index 372f68ea5..bf980129d 100644 --- a/backends/verilog/verilog_backend.cc +++ b/backends/verilog/verilog_backend.cc @@ -926,7 +926,7 @@ bool dump_cell_expr(std::ostream &f, std::string indent, RTLIL::Cell *cell) { SigSpec sig_d; Const val_arst, val_srst; - std::string reg_bit_name; + std::string reg_bit_name, sig_set_name, sig_clr_name, sig_arst_name; if (chunky) { reg_bit_name = stringf("%s[%d]", reg_name.c_str(), i); if (ff.has_d) @@ -941,6 +941,32 @@ bool dump_cell_expr(std::ostream &f, std::string indent, RTLIL::Cell *cell) if (ff.has_srst) val_srst = chunky ? ff.val_srst[i] : ff.val_srst; + // If there are constants in the sensitivity list, replace them with an intermediate wire + if (ff.has_sr) { + if (ff.sig_set[i].wire == NULL) + { + sig_set_name = next_auto_id(); + f << stringf("%s" "wire %s = ", indent.c_str(), sig_set_name.c_str()); + dump_const(f, ff.sig_set[i].data); + f << stringf(";\n"); + } + if (ff.sig_clr[i].wire == NULL) + { + sig_clr_name = next_auto_id(); + f << stringf("%s" "wire %s = ", indent.c_str(), sig_clr_name.c_str()); + dump_const(f, ff.sig_clr[i].data); + f << stringf(";\n"); + } + } else if (ff.has_arst) { + if (ff.sig_arst[i].wire == NULL) + { + sig_arst_name = next_auto_id(); + f << stringf("%s" "wire %s = ", indent.c_str(), sig_arst_name.c_str()); + dump_const(f, ff.sig_arst[i].data); + f << stringf(";\n"); + } + } + dump_attributes(f, indent, cell->attributes); if (ff.has_clk) { @@ -949,27 +975,47 @@ bool dump_cell_expr(std::ostream &f, std::string indent, RTLIL::Cell *cell) dump_sigspec(f, ff.sig_clk); if (ff.has_sr) { f << stringf(", %sedge ", ff.pol_set ? "pos" : "neg"); - dump_sigspec(f, ff.sig_set[i]); + if (ff.sig_set[i].wire == NULL) + f << stringf("%s", sig_set_name.c_str()); + else + dump_sigspec(f, ff.sig_set[i]); + f << stringf(", %sedge ", ff.pol_clr ? "pos" : "neg"); - dump_sigspec(f, ff.sig_clr[i]); + if (ff.sig_clr[i].wire == NULL) + f << stringf("%s", sig_clr_name.c_str()); + else + dump_sigspec(f, ff.sig_clr[i]); + } else if (ff.has_arst) { f << stringf(", %sedge ", ff.pol_arst ? "pos" : "neg"); - dump_sigspec(f, ff.sig_arst); + if (ff.sig_arst[i].wire == NULL) + f << stringf("%s", sig_arst_name.c_str()); + else + dump_sigspec(f, ff.sig_arst); } f << stringf(")\n"); f << stringf("%s" " ", indent.c_str()); if (ff.has_sr) { f << stringf("if (%s", ff.pol_clr ? "" : "!"); - dump_sigspec(f, ff.sig_clr[i]); + if (ff.sig_clr[i].wire == NULL) + f << stringf("%s", sig_clr_name.c_str()); + else + dump_sigspec(f, ff.sig_clr[i]); f << stringf(") %s <= 1'b0;\n", reg_bit_name.c_str()); f << stringf("%s" " else if (%s", indent.c_str(), ff.pol_set ? "" : "!"); - dump_sigspec(f, ff.sig_set[i]); + if (ff.sig_set[i].wire == NULL) + f << stringf("%s", sig_set_name.c_str()); + else + dump_sigspec(f, ff.sig_set[i]); f << stringf(") %s <= 1'b1;\n", reg_bit_name.c_str()); f << stringf("%s" " else ", indent.c_str()); } else if (ff.has_arst) { f << stringf("if (%s", ff.pol_arst ? "" : "!"); - dump_sigspec(f, ff.sig_arst); + if (ff.sig_arst[i].wire == NULL) + f << stringf("%s", sig_arst_name.c_str()); + else + dump_sigspec(f, ff.sig_arst); f << stringf(") %s <= ", reg_bit_name.c_str()); dump_sigspec(f, val_arst); f << stringf(";\n"); diff --git a/frontends/ast/simplify.cc b/frontends/ast/simplify.cc index 95f2d1810..fb6623f02 100644 --- a/frontends/ast/simplify.cc +++ b/frontends/ast/simplify.cc @@ -1526,7 +1526,7 @@ bool AstNode::simplify(bool const_fold, bool at_zero, bool in_lvalue, int stage, integer = children[0]->children.size(); // save original number of dimensions for $size() etc. for (int i = 0; 2*i < GetSize(id2ast->multirange_dimensions); i++) { - if (GetSize(children[0]->children) < i) + if (GetSize(children[0]->children) <= i) log_file_error(filename, location.first_line, "Insufficient number of array indices for %s.\n", log_id(str)); AstNode *new_index_expr = children[0]->children[i]->children.at(0)->clone(); diff --git a/frontends/verific/verific.cc b/frontends/verific/verific.cc index 7bbda9d49..acb854a4d 100644 --- a/frontends/verific/verific.cc +++ b/frontends/verific/verific.cc @@ -21,6 +21,7 @@ #include "kernel/sigtools.h" #include "kernel/celltypes.h" #include "kernel/log.h" +#include "libs/sha1/sha1.h" #include <stdlib.h> #include <stdio.h> #include <string.h> @@ -864,6 +865,21 @@ void VerificImporter::merge_past_ffs(pool<RTLIL::Cell*> &candidates) merge_past_ffs_clock(it.second, it.first.first, it.first.second); } +static std::string sha1_if_contain_spaces(std::string str) +{ + if(str.find_first_of(' ') != std::string::npos) { + std::size_t open = str.find_first_of('('); + std::size_t closed = str.find_last_of(')'); + if (open != std::string::npos && closed != std::string::npos) { + std::string content = str.substr(open + 1, closed - open - 1); + return str.substr(0, open + 1) + sha1(content) + str.substr(closed); + } else { + return sha1(str); + } + } + return str; +} + void VerificImporter::import_netlist(RTLIL::Design *design, Netlist *nl, std::set<Netlist*> &nl_todo, bool norename) { std::string netlist_name = nl->GetAtt(" \\top") ? nl->CellBaseName() : nl->Owner()->Name(); @@ -877,7 +893,7 @@ void VerificImporter::import_netlist(RTLIL::Design *design, Netlist *nl, std::se module_name += nl->Name(); module_name += ")"; } - module_name = "\\" + module_name; + module_name = "\\" + sha1_if_contain_spaces(module_name); } netlist = nl; @@ -1512,7 +1528,7 @@ void VerificImporter::import_netlist(RTLIL::Design *design, Netlist *nl, std::se inst_type += inst->View()->Name(); inst_type += ")"; } - inst_type = "\\" + inst_type; + inst_type = "\\" + sha1_if_contain_spaces(inst_type); } RTLIL::Cell *cell = module->addCell(inst_name, inst_type); diff --git a/frontends/verific/verificsva.cc b/frontends/verific/verificsva.cc index 49c0c40ac..632043b6f 100644 --- a/frontends/verific/verificsva.cc +++ b/frontends/verific/verificsva.cc @@ -1040,8 +1040,14 @@ struct VerificSvaImporter [[noreturn]] void parser_error(Instance *inst) { - parser_error(stringf("Verific SVA primitive %s (%s) is currently unsupported in this context", - inst->View()->Owner()->Name(), inst->Name()), inst->Linefile()); + std::string msg; + if (inst->Type() == PRIM_SVA_MATCH_ITEM_TRIGGER || inst->Type() == PRIM_SVA_MATCH_ITEM_ASSIGN) + { + msg = "SVA sequences with local variable assignments are currently not supported.\n"; + } + + parser_error(stringf("%sVerific SVA primitive %s (%s) is currently unsupported in this context", + msg.c_str(), inst->View()->Owner()->Name(), inst->Name()), inst->Linefile()); } dict<Net*, bool, hash_ptr_ops> check_expression_cache; diff --git a/frontends/verilog/verilog_parser.y b/frontends/verilog/verilog_parser.y index 63f0341d9..8e5236639 100644 --- a/frontends/verilog/verilog_parser.y +++ b/frontends/verilog/verilog_parser.y @@ -210,14 +210,23 @@ static AstNode *checkRange(AstNode *type_node, AstNode *range_node) return range_node; } -static void rewriteAsMemoryNode(AstNode *node, AstNode *rangeNode) +static void rewriteRange(AstNode *rangeNode) { - node->type = AST_MEMORY; if (rangeNode->type == AST_RANGE && rangeNode->children.size() == 1) { // SV array size [n], rewrite as [n-1:0] rangeNode->children[0] = new AstNode(AST_SUB, rangeNode->children[0], AstNode::mkconst_int(1, true)); rangeNode->children.push_back(AstNode::mkconst_int(0, false)); } +} + +static void rewriteAsMemoryNode(AstNode *node, AstNode *rangeNode) +{ + node->type = AST_MEMORY; + if (rangeNode->type == AST_MULTIRANGE) { + for (auto *itr : rangeNode->children) + rewriteRange(itr); + } else + rewriteRange(rangeNode); node->children.push_back(rangeNode); } diff --git a/kernel/rtlil.h b/kernel/rtlil.h index 6c561cb85..a03e8933c 100644 --- a/kernel/rtlil.h +++ b/kernel/rtlil.h @@ -375,6 +375,8 @@ namespace RTLIL bool in(const char *rhs) const { return *this == rhs; } bool in(const std::string &rhs) const { return *this == rhs; } bool in(const pool<IdString> &rhs) const { return rhs.count(*this) != 0; } + + bool isPublic() { return begins_with("\\"); } }; namespace ID { diff --git a/passes/cmds/rename.cc b/passes/cmds/rename.cc index 6326b4b15..f8fe715c8 100644 --- a/passes/cmds/rename.cc +++ b/passes/cmds/rename.cc @@ -290,11 +290,11 @@ struct RenamePass : public Pass { dict<RTLIL::Cell *, IdString> new_cell_names; for (auto wire : module->selected_wires()) - if (wire->name[0] == '\\' && wire->port_id == 0) + if (wire->name.isPublic() && wire->port_id == 0) new_wire_names[wire] = NEW_ID; for (auto cell : module->selected_cells()) - if (cell->name[0] == '\\') + if (cell->name.isPublic()) new_cell_names[cell] = NEW_ID; for (auto &it : new_wire_names) diff --git a/passes/cmds/show.cc b/passes/cmds/show.cc index a4ad861f6..0c96f8c5d 100644 --- a/passes/cmds/show.cc +++ b/passes/cmds/show.cc @@ -368,7 +368,7 @@ struct ShowWorker const char *shape = "diamond"; if (wire->port_input || wire->port_output) shape = "octagon"; - if (wire->name[0] == '\\') { + if (wire->name.isPublic()) { fprintf(f, "n%d [ shape=%s, label=\"%s\", %s, fontcolor=\"black\" ];\n", id2num(wire->name), shape, findLabel(wire->name.str()), nextColor(RTLIL::SigSpec(wire), "color=\"black\"").c_str()); diff --git a/passes/cmds/splice.cc b/passes/cmds/splice.cc index 20627d601..0f63b91c5 100644 --- a/passes/cmds/splice.cc +++ b/passes/cmds/splice.cc @@ -211,7 +211,7 @@ struct SpliceWorker std::vector<Wire*> mod_wires = module->wires(); for (auto wire : mod_wires) - if ((!no_outputs && wire->port_output) || (do_wires && wire->name[0] == '\\')) { + if ((!no_outputs && wire->port_output) || (do_wires && wire->name.isPublic())) { if (!design->selected(module, wire)) continue; RTLIL::SigSpec sig = sigmap(wire); diff --git a/passes/cmds/stat.cc b/passes/cmds/stat.cc index ed51fdc24..0d84c73db 100644 --- a/passes/cmds/stat.cc +++ b/passes/cmds/stat.cc @@ -81,7 +81,7 @@ struct statdata_t for (auto wire : mod->selected_wires()) { - if (wire->name[0] == '\\') { + if (wire->name.isPublic()) { num_pub_wires++; num_pub_wire_bits += wire->width; } diff --git a/passes/equiv/equiv_make.cc b/passes/equiv/equiv_make.cc index 51b4ad0f1..6923ae3d0 100644 --- a/passes/equiv/equiv_make.cc +++ b/passes/equiv/equiv_make.cc @@ -114,25 +114,25 @@ struct EquivMakeWorker Module *gate_clone = gate_mod->clone(); for (auto it : gold_clone->wires().to_vector()) { - if ((it->name[0] == '\\' || inames) && blacklist_names.count(it->name) == 0) + if ((it->name.isPublic() || inames) && blacklist_names.count(it->name) == 0) wire_names.insert(it->name); gold_clone->rename(it, it->name.str() + "_gold"); } for (auto it : gold_clone->cells().to_vector()) { - if ((it->name[0] == '\\' || inames) && blacklist_names.count(it->name) == 0) + if ((it->name.isPublic() || inames) && blacklist_names.count(it->name) == 0) cell_names.insert(it->name); gold_clone->rename(it, it->name.str() + "_gold"); } for (auto it : gate_clone->wires().to_vector()) { - if ((it->name[0] == '\\' || inames) && blacklist_names.count(it->name) == 0) + if ((it->name.isPublic() || inames) && blacklist_names.count(it->name) == 0) wire_names.insert(it->name); gate_clone->rename(it, it->name.str() + "_gate"); } for (auto it : gate_clone->cells().to_vector()) { - if ((it->name[0] == '\\' || inames) && blacklist_names.count(it->name) == 0) + if ((it->name.isPublic() || inames) && blacklist_names.count(it->name) == 0) cell_names.insert(it->name); gate_clone->rename(it, it->name.str() + "_gate"); } diff --git a/passes/equiv/equiv_purge.cc b/passes/equiv/equiv_purge.cc index d15c8d183..a43ecec5a 100644 --- a/passes/equiv/equiv_purge.cc +++ b/passes/equiv/equiv_purge.cc @@ -35,7 +35,7 @@ struct EquivPurgeWorker { if (sig.is_wire()) { Wire *wire = sig.as_wire(); - if (wire->name[0] == '\\') { + if (wire->name.isPublic()) { if (!wire->port_output) { log(" Module output: %s (%s)\n", log_signal(wire), log_id(cellname)); wire->port_output = true; @@ -62,7 +62,7 @@ struct EquivPurgeWorker { if (sig.is_wire()) { Wire *wire = sig.as_wire(); - if (wire->name[0] == '\\') { + if (wire->name.isPublic()) { if (!wire->port_output) { log(" Module input: %s\n", log_signal(wire)); wire->port_input = true; diff --git a/passes/hierarchy/hierarchy.cc b/passes/hierarchy/hierarchy.cc index 90b25949d..225e1feae 100644 --- a/passes/hierarchy/hierarchy.cc +++ b/passes/hierarchy/hierarchy.cc @@ -765,11 +765,13 @@ struct HierarchyPass : public Pass { top_mod = design->module(top_name); dict<RTLIL::IdString, RTLIL::Const> top_parameters; - for (auto ¶ : parameters) { - SigSpec sig_value; - if (!RTLIL::SigSpec::parse(sig_value, NULL, para.second)) - log_cmd_error("Can't decode value '%s'!\n", para.second.c_str()); - top_parameters[RTLIL::escape_id(para.first)] = sig_value.as_const(); + if ((top_mod == nullptr && design->module(abstract_id)) || top_mod != nullptr) { + for (auto ¶ : parameters) { + SigSpec sig_value; + if (!RTLIL::SigSpec::parse(sig_value, NULL, para.second)) + log_cmd_error("Can't decode value '%s'!\n", para.second.c_str()); + top_parameters[RTLIL::escape_id(para.first)] = sig_value.as_const(); + } } if (top_mod == nullptr && design->module(abstract_id)) diff --git a/passes/opt/opt_clean.cc b/passes/opt/opt_clean.cc index 5370881d3..bd9856e81 100644 --- a/passes/opt/opt_clean.cc +++ b/passes/opt/opt_clean.cc @@ -207,7 +207,7 @@ bool compare_signals(RTLIL::SigBit &s1, RTLIL::SigBit &s2, SigPool ®s, SigPoo if ((w1->port_input && w1->port_output) != (w2->port_input && w2->port_output)) return !(w2->port_input && w2->port_output); - if (w1->name[0] == '\\' && w2->name[0] == '\\') { + if (w1->name.isPublic() && w2->name.isPublic()) { if (regs.check(s1) != regs.check(s2)) return regs.check(s2); if (direct_wires.count(w1) != direct_wires.count(w2)) @@ -220,7 +220,7 @@ bool compare_signals(RTLIL::SigBit &s1, RTLIL::SigBit &s2, SigPool ®s, SigPoo return w2->port_output; if (w1->name[0] != w2->name[0]) - return w2->name[0] == '\\'; + return w2->name.isPublic(); int attrs1 = count_nontrivial_wire_attrs(w1); int attrs2 = count_nontrivial_wire_attrs(w2); diff --git a/passes/sat/mutate.cc b/passes/sat/mutate.cc index 15abee73e..95e0e0944 100644 --- a/passes/sat/mutate.cc +++ b/passes/sat/mutate.cc @@ -439,7 +439,7 @@ void mutate_list(Design *design, const mutate_opts_t &opts, const string &filena dict<SigBit, int> bit_user_cnt; for (auto wire : module->wires()) { - if (wire->name[0] == '\\' && wire->attributes.count(ID::src)) + if (wire->name.isPublic() && wire->attributes.count(ID::src)) sigmap.add(wire); } @@ -468,7 +468,7 @@ void mutate_list(Design *design, const mutate_opts_t &opts, const string &filena } if (!bit.wire->name[0] != !sigbit.wire->name[0]) { - if (bit.wire->name[0] == '\\') + if (bit.wire->name.isPublic()) sigmap.add(bit); continue; } @@ -493,7 +493,7 @@ void mutate_list(Design *design, const mutate_opts_t &opts, const string &filena entry.src.insert(s); SigBit bit = sigmap(conn.second[i]); - if (bit.wire && bit.wire->name[0] == '\\' && (cell->output(conn.first) || bit_user_cnt[bit] == 1)) { + if (bit.wire && bit.wire->name.isPublic() && (cell->output(conn.first) || bit_user_cnt[bit] == 1)) { for (auto &s : bit.wire->get_strpool_attribute(ID::src)) entry.src.insert(s); entry.wire = bit.wire->name; diff --git a/passes/sat/sat.cc b/passes/sat/sat.cc index d7bf125d1..9fdac6147 100644 --- a/passes/sat/sat.cc +++ b/passes/sat/sat.cc @@ -1365,7 +1365,7 @@ struct SatPass : public Pass { if (show_public) { for (auto wire : module->wires()) - if (wire->name[0] == '\\') + if (wire->name.isPublic()) shows.push_back(wire->name.str()); } diff --git a/techlibs/xilinx/cells_sim.v b/techlibs/xilinx/cells_sim.v index a04587e87..40804c367 100644 --- a/techlibs/xilinx/cells_sim.v +++ b/techlibs/xilinx/cells_sim.v @@ -3014,8 +3014,12 @@ endmodule // Virtex 6, Series 7. `ifdef YOSYS -(* abc9_box=!(PREG || AREG || ADREG || BREG || CREG || DREG || MREG), - lib_whitebox=!(PREG || AREG || ADREG || BREG || CREG || DREG || MREG) *) +(* abc9_box=!(PREG || AREG || ADREG || BREG || CREG || DREG || MREG) +`ifdef ALLOW_WHITEBOX_DSP48E1 + // Do not make DSP48E1 a whitebox for ABC9 even if fully combinatorial, since it is a big complex block + , lib_whitebox=!(PREG || AREG || ADREG || BREG || CREG || DREG || MREG || INMODEREG || OPMODEREG || ALUMODEREG || CARRYINREG || CARRYINSELREG) +`endif +*) `endif module DSP48E1 ( output [29:0] ACOUT, @@ -3503,11 +3507,15 @@ module DSP48E1 ( if (OPMODEr[3:2] != 2'b01) $fatal(1, "OPMODEr[3:2] must be 2'b01 when OPMODEr[1:0] is 2'b01"); `endif end - 2'b10: begin X = P; + 2'b10: + if (PREG == 1) + X = P; + else begin + X = 48'bx; `ifndef YOSYS - if (PREG != 1) $fatal(1, "PREG must be 1 when OPMODEr[1:0] is 2'b10"); + $fatal(1, "PREG must be 1 when OPMODEr[1:0] is 2'b10"); `endif - end + end 2'b11: X = $signed({Ar2, Br2}); default: X = 48'bx; endcase @@ -3529,20 +3537,36 @@ module DSP48E1 ( case (OPMODEr[6:4]) 3'b000: Z = 48'b0; 3'b001: Z = PCIN; - 3'b010: begin Z = P; + 3'b010: + if (PREG == 1) + Z = P; + else begin + Z = 48'bx; `ifndef YOSYS - if (PREG != 1) $fatal(1, "PREG must be 1 when OPMODEr[6:4] i0s 3'b010"); + $fatal(1, "PREG must be 1 when OPMODEr[6:4] is 3'b010"); `endif - end + end 3'b011: Z = Cr; - 3'b100: begin Z = P; + 3'b100: + if (PREG == 1 && OPMODEr[3:0] === 4'b1000) + Z = P; + else begin + Z = 48'bx; `ifndef YOSYS - if (PREG != 1) $fatal(1, "PREG must be 1 when OPMODEr[6:4] is 3'b100"); - if (OPMODEr[3:0] != 4'b1000) $fatal(1, "OPMODEr[3:0] must be 4'b1000 when OPMODEr[6:4] i0s 3'b100"); + if (PREG != 1) $fatal(1, "PREG must be 1 when OPMODEr[6:4] is 3'b100"); + if (OPMODEr[3:0] != 4'b1000) $fatal(1, "OPMODEr[3:0] must be 4'b1000 when OPMODEr[6:4] i0s 3'b100"); `endif - end + end 3'b101: Z = $signed(PCIN[47:17]); - 3'b110: Z = $signed(P[47:17]); + 3'b110: + if (PREG == 1) + Z = $signed(P[47:17]); + else begin + Z = 48'bx; +`ifndef YOSYS + $fatal(1, "PREG must be 1 when OPMODEr[6:4] is 3'b110"); +`endif + end default: Z = 48'bx; endcase end @@ -3568,10 +3592,34 @@ module DSP48E1 ( 3'b001: cin_muxed = ~PCIN[47]; 3'b010: cin_muxed = CARRYCASCIN; 3'b011: cin_muxed = PCIN[47]; - 3'b100: cin_muxed = CARRYCASCOUT; - 3'b101: cin_muxed = ~P[47]; + 3'b100: + if (PREG == 1) + cin_muxed = CARRYCASCOUT; + else begin + cin_muxed = 1'bx; +`ifndef YOSYS + $fatal(1, "PREG must be 1 when CARRYINSEL is 3'b100"); +`endif + end + 3'b101: + if (PREG == 1) + cin_muxed = ~P[47]; + else begin + cin_muxed = 1'bx; +`ifndef YOSYS + $fatal(1, "PREG must be 1 when CARRYINSEL is 3'b101"); +`endif + end 3'b110: cin_muxed = A24_xnor_B17; - 3'b111: cin_muxed = P[47]; + 3'b111: + if (PREG == 1) + cin_muxed = P[47]; + else begin + cin_muxed = 1'bx; +`ifndef YOSYS + $fatal(1, "PREG must be 1 when CARRYINSEL is 3'b111"); +`endif + end default: cin_muxed = 1'bx; endcase end @@ -4163,4 +4211,3 @@ module RAMB36E1 ( if (|DOB_REG) (posedge CLKBWRCLK => (DOPBDOP : 4'bx)) = 882; endspecify endmodule - diff --git a/techlibs/xilinx/xc7_dsp_map.v b/techlibs/xilinx/xc7_dsp_map.v index a4256eb92..58df977ec 100644 --- a/techlibs/xilinx/xc7_dsp_map.v +++ b/techlibs/xilinx/xc7_dsp_map.v @@ -33,6 +33,7 @@ module \$__MUL25X18 (input [24:0] A, input [17:0] B, output [42:0] Y); .B(B), .C(48'b0), .D(25'b0), + .CARRYIN(1'b0), .P(P_48), .INMODE(5'b00000), diff --git a/tests/aiger/run-test.sh b/tests/aiger/run-test.sh index de7bc68cf..bcf2b964a 100755 --- a/tests/aiger/run-test.sh +++ b/tests/aiger/run-test.sh @@ -55,5 +55,5 @@ done for y in *.ys; do echo "Running $y." - ../../yosys $y -ql ${y%.*}.log + ../../yosys -ql ${y%.*}.log $y done diff --git a/tests/arch/anlogic/run-test.sh b/tests/arch/anlogic/run-test.sh index bf19b887d..4be4b70ae 100755 --- a/tests/arch/anlogic/run-test.sh +++ b/tests/arch/anlogic/run-test.sh @@ -1,20 +1,4 @@ #!/usr/bin/env bash -set -e -{ -echo "all::" -for x in *.ys; do - echo "all:: run-$x" - echo "run-$x:" - echo " @echo 'Running $x..'" - echo " @../../../yosys -ql ${x%.ys}.log -w 'Yosys has only limited support for tri-state logic at the moment.' $x" -done -for s in *.sh; do - if [ "$s" != "run-test.sh" ]; then - echo "all:: run-$s" - echo "run-$s:" - echo " @echo 'Running $s..'" - echo " @bash $s" - fi -done -} > run-test.mk -exec ${MAKE:-make} -f run-test.mk +set -eu +source ../../gen-tests-makefile.sh +run_tests --yosys-scripts --bash --yosys-args "-w 'Yosys has only limited support for tri-state logic at the moment.'" diff --git a/tests/arch/ecp5/run-test.sh b/tests/arch/ecp5/run-test.sh index bf19b887d..4be4b70ae 100755 --- a/tests/arch/ecp5/run-test.sh +++ b/tests/arch/ecp5/run-test.sh @@ -1,20 +1,4 @@ #!/usr/bin/env bash -set -e -{ -echo "all::" -for x in *.ys; do - echo "all:: run-$x" - echo "run-$x:" - echo " @echo 'Running $x..'" - echo " @../../../yosys -ql ${x%.ys}.log -w 'Yosys has only limited support for tri-state logic at the moment.' $x" -done -for s in *.sh; do - if [ "$s" != "run-test.sh" ]; then - echo "all:: run-$s" - echo "run-$s:" - echo " @echo 'Running $s..'" - echo " @bash $s" - fi -done -} > run-test.mk -exec ${MAKE:-make} -f run-test.mk +set -eu +source ../../gen-tests-makefile.sh +run_tests --yosys-scripts --bash --yosys-args "-w 'Yosys has only limited support for tri-state logic at the moment.'" diff --git a/tests/arch/efinix/run-test.sh b/tests/arch/efinix/run-test.sh index bf19b887d..4be4b70ae 100755 --- a/tests/arch/efinix/run-test.sh +++ b/tests/arch/efinix/run-test.sh @@ -1,20 +1,4 @@ #!/usr/bin/env bash -set -e -{ -echo "all::" -for x in *.ys; do - echo "all:: run-$x" - echo "run-$x:" - echo " @echo 'Running $x..'" - echo " @../../../yosys -ql ${x%.ys}.log -w 'Yosys has only limited support for tri-state logic at the moment.' $x" -done -for s in *.sh; do - if [ "$s" != "run-test.sh" ]; then - echo "all:: run-$s" - echo "run-$s:" - echo " @echo 'Running $s..'" - echo " @bash $s" - fi -done -} > run-test.mk -exec ${MAKE:-make} -f run-test.mk +set -eu +source ../../gen-tests-makefile.sh +run_tests --yosys-scripts --bash --yosys-args "-w 'Yosys has only limited support for tri-state logic at the moment.'" diff --git a/tests/arch/gowin/run-test.sh b/tests/arch/gowin/run-test.sh index bf19b887d..4be4b70ae 100755 --- a/tests/arch/gowin/run-test.sh +++ b/tests/arch/gowin/run-test.sh @@ -1,20 +1,4 @@ #!/usr/bin/env bash -set -e -{ -echo "all::" -for x in *.ys; do - echo "all:: run-$x" - echo "run-$x:" - echo " @echo 'Running $x..'" - echo " @../../../yosys -ql ${x%.ys}.log -w 'Yosys has only limited support for tri-state logic at the moment.' $x" -done -for s in *.sh; do - if [ "$s" != "run-test.sh" ]; then - echo "all:: run-$s" - echo "run-$s:" - echo " @echo 'Running $s..'" - echo " @bash $s" - fi -done -} > run-test.mk -exec ${MAKE:-make} -f run-test.mk +set -eu +source ../../gen-tests-makefile.sh +run_tests --yosys-scripts --bash --yosys-args "-w 'Yosys has only limited support for tri-state logic at the moment.'" diff --git a/tests/arch/ice40/run-test.sh b/tests/arch/ice40/run-test.sh index bf19b887d..4be4b70ae 100755 --- a/tests/arch/ice40/run-test.sh +++ b/tests/arch/ice40/run-test.sh @@ -1,20 +1,4 @@ #!/usr/bin/env bash -set -e -{ -echo "all::" -for x in *.ys; do - echo "all:: run-$x" - echo "run-$x:" - echo " @echo 'Running $x..'" - echo " @../../../yosys -ql ${x%.ys}.log -w 'Yosys has only limited support for tri-state logic at the moment.' $x" -done -for s in *.sh; do - if [ "$s" != "run-test.sh" ]; then - echo "all:: run-$s" - echo "run-$s:" - echo " @echo 'Running $s..'" - echo " @bash $s" - fi -done -} > run-test.mk -exec ${MAKE:-make} -f run-test.mk +set -eu +source ../../gen-tests-makefile.sh +run_tests --yosys-scripts --bash --yosys-args "-w 'Yosys has only limited support for tri-state logic at the moment.'" diff --git a/tests/arch/intel_alm/run-test.sh b/tests/arch/intel_alm/run-test.sh index bf19b887d..4be4b70ae 100755 --- a/tests/arch/intel_alm/run-test.sh +++ b/tests/arch/intel_alm/run-test.sh @@ -1,20 +1,4 @@ #!/usr/bin/env bash -set -e -{ -echo "all::" -for x in *.ys; do - echo "all:: run-$x" - echo "run-$x:" - echo " @echo 'Running $x..'" - echo " @../../../yosys -ql ${x%.ys}.log -w 'Yosys has only limited support for tri-state logic at the moment.' $x" -done -for s in *.sh; do - if [ "$s" != "run-test.sh" ]; then - echo "all:: run-$s" - echo "run-$s:" - echo " @echo 'Running $s..'" - echo " @bash $s" - fi -done -} > run-test.mk -exec ${MAKE:-make} -f run-test.mk +set -eu +source ../../gen-tests-makefile.sh +run_tests --yosys-scripts --bash --yosys-args "-w 'Yosys has only limited support for tri-state logic at the moment.'" diff --git a/tests/arch/xilinx/dsp_abc9.ys b/tests/arch/xilinx/dsp_abc9.ys new file mode 100644 index 000000000..909e54149 --- /dev/null +++ b/tests/arch/xilinx/dsp_abc9.ys @@ -0,0 +1,37 @@ +read_verilog <<EOT +module top(input [24:0] A, input [17:0] B, output [47:0] P); +DSP48E1 #(.PREG(0)) dsp(.A(A), .B(B), .P(P)); +endmodule +EOT +techmap -autoproc -wb -map +/xilinx/cells_sim.v +opt +scc -expect 0 + + +design -reset +read_verilog <<EOT +module top(input signed [24:0] A, input signed [17:0] B, output [47:0] P); +assign P = A * B; +endmodule +EOT +synth_xilinx -abc9 +techmap -autoproc -wb -map +/xilinx/cells_sim.v +opt -full -fine +select -assert-count 1 t:$mul +select -assert-count 0 t:* t:$mul %D + + +design -reset +read_verilog -icells -formal <<EOT +module top(output [42:0] P); +\$__MUL25X18 mul (.A(42), .B(42), .Y(P)); +assert property (P == 42*42); +endmodule +EOT +techmap -map +/xilinx/xc7_dsp_map.v +verilog_defaults -add -D ALLOW_WHITEBOX_DSP48E1 +synth_xilinx -abc9 +techmap -autoproc -wb -map +/xilinx/cells_sim.v +opt -full -fine +select -assert-count 0 t:* t:$assert %d +sat -verify -prove-asserts diff --git a/tests/arch/xilinx/run-test.sh b/tests/arch/xilinx/run-test.sh index bf19b887d..4be4b70ae 100755 --- a/tests/arch/xilinx/run-test.sh +++ b/tests/arch/xilinx/run-test.sh @@ -1,20 +1,4 @@ #!/usr/bin/env bash -set -e -{ -echo "all::" -for x in *.ys; do - echo "all:: run-$x" - echo "run-$x:" - echo " @echo 'Running $x..'" - echo " @../../../yosys -ql ${x%.ys}.log -w 'Yosys has only limited support for tri-state logic at the moment.' $x" -done -for s in *.sh; do - if [ "$s" != "run-test.sh" ]; then - echo "all:: run-$s" - echo "run-$s:" - echo " @echo 'Running $s..'" - echo " @bash $s" - fi -done -} > run-test.mk -exec ${MAKE:-make} -f run-test.mk +set -eu +source ../../gen-tests-makefile.sh +run_tests --yosys-scripts --bash --yosys-args "-w 'Yosys has only limited support for tri-state logic at the moment.'" diff --git a/tests/gen-tests-makefile.sh b/tests/gen-tests-makefile.sh new file mode 100755 index 000000000..ab8fb7013 --- /dev/null +++ b/tests/gen-tests-makefile.sh @@ -0,0 +1,94 @@ +set -eu + +YOSYS_BASEDIR="$(cd "$(dirname "${BASH_SOURCE[0]}")"/../ >/dev/null 2>&1 && pwd)" + +# $ generate_target target_name test_command +generate_target() { + target_name=$1 + test_command=$2 + echo "all: $target_name" + echo ".PHONY: $target_name" + echo "$target_name:" + printf "\t@%s\n" "$test_command" + printf "\t@echo 'Passed %s'\n" "$target_name" +} + +# $ generate_ys_test ys_file [yosys_args] +generate_ys_test() { + ys_file=$1 + yosys_args=${2:-} + generate_target "$ys_file" "$YOSYS_BASEDIR/yosys -ql ${ys_file%.*}.log $yosys_args $ys_file" +} + +# $ generate_bash_test bash_file +generate_bash_test() { + bash_file=$1 + generate_target "$bash_file" "bash -v $bash_file >${bash_file%.*}.log 2>&1" +} + +# $ generate_tests [-y|--yosys-scripts] [-s|--prove-sv] [-b|--bash] [-a|--yosys-args yosys_args] +generate_tests() { + do_ys=false + do_sv=false + do_sh=false + yosys_args="" + + while [[ $# -gt 0 ]]; do + arg="$1" + case "$arg" in + -y|--yosys-scripts) + do_ys=true + shift + ;; + -s|--prove-sv) + do_sv=true + shift + ;; + -b|--bash) + do_sh=true + shift + ;; + -a|--yosys-args) + yosys_args+="$2" + shift + shift + ;; + *) + echo >&2 "Unknown argument: $1" + exit 1 + esac + done + + if [[ ! ( $do_ys = true || $do_sv = true || $do_sh = true ) ]]; then + echo >&2 "Error: No file types selected" + exit 1 + fi + + echo ".PHONY: all" + echo "all:" + + if [[ $do_ys = true ]]; then + for x in *.ys; do + generate_ys_test "$x" "$yosys_args" + done + fi; + if [[ $do_sv = true ]]; then + for x in *.sv; do + if [ ! -f "${x%.sv}.ys" ]; then + generate_ys_test "$x" "-p \"prep -top top; sat -verify -prove-asserts\" $yosys_args" + fi; + done + fi; + if [[ $do_sh == true ]]; then + for s in *.sh; do + if [ "$s" != "run-test.sh" ]; then + generate_bash_test "$s" + fi + done + fi +} + +run_tests() { + generate_tests "$@" > run-test.mk + exec ${MAKE:-make} -f run-test.mk +} diff --git a/tests/memories/run-test.sh b/tests/memories/run-test.sh index 8d1a8b413..376f5bf79 100755 --- a/tests/memories/run-test.sh +++ b/tests/memories/run-test.sh @@ -9,12 +9,12 @@ while getopts "A:S:" opt do case "$opt" in A) abcopt="-A $OPTARG" ;; - S) seed="-S $OPTARG" ;; + S) seed="$OPTARG" ;; esac done shift "$((OPTIND-1))" -bash ../tools/autotest.sh $abcopt $seed -G *.v +${MAKE:-make} -f ../tools/autotest.mk SEED="$seed" EXTRA_FLAGS="$abcopt" *.v for f in `egrep -l 'expect-(wr-ports|rd-ports|rd-clk)' *.v`; do echo -n "Testing expectations for $f .." diff --git a/tests/opt/.gitignore b/tests/opt/.gitignore index 397b4a762..8355de9dc 100644 --- a/tests/opt/.gitignore +++ b/tests/opt/.gitignore @@ -1 +1,2 @@ *.log +run-test.mk diff --git a/tests/opt/run-test.sh b/tests/opt/run-test.sh index 44ce7e674..2007cd6e4 100755 --- a/tests/opt/run-test.sh +++ b/tests/opt/run-test.sh @@ -1,6 +1,4 @@ #!/bin/bash -set -e -for x in *.ys; do - echo "Running $x.." - ../../yosys -ql ${x%.ys}.log $x -done +set -eu +source ../gen-tests-makefile.sh +run_tests --yosys-scripts diff --git a/tests/opt_share/run-test.sh b/tests/opt_share/run-test.sh index e01552646..e0008a259 100755 --- a/tests/opt_share/run-test.sh +++ b/tests/opt_share/run-test.sh @@ -22,12 +22,23 @@ mkdir -p temp echo "generating tests.." python3 generate.py -c $count $seed +{ + echo ".PHONY: all" + echo "all:" + + for i in $( ls temp/*.ys | sed 's,[^0-9],,g; s,^0*\(.\),\1,g;' ); do + idx=$( printf "%05d" $i ) + echo ".PHONY: test-$idx" + echo "all: test-$idx" + echo "test-$idx:" + printf "\t@%s\n" \ + "echo -n [$i]" \ + "../../yosys -ql temp/uut_${idx}.log temp/uut_${idx}.ys" + done +} > temp/makefile + echo "running tests.." -for i in $( ls temp/*.ys | sed 's,[^0-9],,g; s,^0*\(.\),\1,g;' ); do - echo -n "[$i]" - idx=$( printf "%05d" $i ) - ../../yosys -ql temp/uut_${idx}.log temp/uut_${idx}.ys -done +${MAKE:-make} -f temp/makefile echo failed_share=$( echo $( gawk '/^#job#/ { j=$2; db[j]=0; } /^Removing [246] cells/ { delete db[j]; } END { for (j in db) print(j); }' temp/all_share_log.txt ) ) diff --git a/tests/sat/.gitignore b/tests/sat/.gitignore index 397b4a762..8355de9dc 100644 --- a/tests/sat/.gitignore +++ b/tests/sat/.gitignore @@ -1 +1,2 @@ *.log +run-test.mk diff --git a/tests/sat/run-test.sh b/tests/sat/run-test.sh index 67e1beb23..74589dfeb 100755 --- a/tests/sat/run-test.sh +++ b/tests/sat/run-test.sh @@ -1,6 +1,4 @@ -#!/bin/bash -set -e -for x in *.ys; do - echo "Running $x.." - ../../yosys -ql ${x%.ys}.log $x -done +#!/usr/bin/env bash +set -eu +source ../gen-tests-makefile.sh +run_tests --yosys-scripts diff --git a/tests/simple/run-test.sh b/tests/simple/run-test.sh index f20fd0d30..47bcfd6da 100755 --- a/tests/simple/run-test.sh +++ b/tests/simple/run-test.sh @@ -17,5 +17,4 @@ if ! command -v iverilog > /dev/null ; then exit 1 fi -shopt -s nullglob exec ${MAKE:-make} -f ../tools/autotest.mk $seed *.{sv,v} diff --git a/tests/svtypes/multirange_array.sv b/tests/svtypes/multirange_array.sv new file mode 100644 index 000000000..be0d3dfc2 --- /dev/null +++ b/tests/svtypes/multirange_array.sv @@ -0,0 +1,16 @@ +// test for multirange arrays + +`define STRINGIFY(x) `"x`" +`define STATIC_ASSERT(x) if(!(x)) $error({"assert failed: ", `STRINGIFY(x)}) + +module top; + + logic a [3]; + logic b [3][5]; + logic c [3][5][7]; + + `STATIC_ASSERT($bits(a) == 3); + `STATIC_ASSERT($bits(b) == 15); + `STATIC_ASSERT($bits(c) == 105); + +endmodule diff --git a/tests/svtypes/multirange_subarray_access.ys b/tests/svtypes/multirange_subarray_access.ys new file mode 100644 index 000000000..de57d1423 --- /dev/null +++ b/tests/svtypes/multirange_subarray_access.ys @@ -0,0 +1,12 @@ +logger -expect error "Insufficient number of array indices for a." 1 +read_verilog -sv <<EOT +module foo; +logic a [6:0][4:0][1:0]; +logic b [1:0]; + +assign a[0][0][0] = 1'b0; +assign a[0][0][1] = 1'b1; +assign b = a[0][0]; + +endmodule +EOT diff --git a/tests/svtypes/run-test.sh b/tests/svtypes/run-test.sh index 09a30eed1..91ceae227 100755 --- a/tests/svtypes/run-test.sh +++ b/tests/svtypes/run-test.sh @@ -1,20 +1,4 @@ #!/usr/bin/env bash -set -e -{ -echo "all::" -for x in *.ys; do - echo "all:: run-$x" - echo "run-$x:" - echo " @echo 'Running $x..'" - echo " @../../yosys -ql ${x%.ys}.log $x" -done -for x in *.sv; do - if [ ! -f "${x%.sv}.ys" ]; then - echo "all:: check-$x" - echo "check-$x:" - echo " @echo 'Checking $x..'" - echo " @../../yosys -ql ${x%.sv}.log -p \"prep -top top; sat -verify -prove-asserts\" $x" - fi -done -} > run-test.mk -exec ${MAKE:-make} -f run-test.mk +set -eu +source ../gen-tests-makefile.sh +run_tests --yosys-scripts --prove-sv diff --git a/tests/techmap/mem_simple_4x1_runtest.sh b/tests/techmap/mem_simple_4x1_runtest.sh index e2c6303da..9c41fa56a 100644 --- a/tests/techmap/mem_simple_4x1_runtest.sh +++ b/tests/techmap/mem_simple_4x1_runtest.sh @@ -1,6 +1,6 @@ #!/bin/bash -set -ev +set -e ../../yosys -b 'verilog -noattr' -o mem_simple_4x1_synth.v -p 'proc; opt; memory -nomap; techmap -map mem_simple_4x1_map.v;; techmap; opt; abc;; stat' mem_simple_4x1_uut.v diff --git a/tests/techmap/recursive_runtest.sh b/tests/techmap/recursive_runtest.sh index 30c79bf03..0725ccf40 100644 --- a/tests/techmap/recursive_runtest.sh +++ b/tests/techmap/recursive_runtest.sh @@ -1,3 +1,3 @@ -set -ev +set -e ../../yosys -p 'hierarchy -top top; techmap -map recursive_map.v -max_iter 1; select -assert-count 2 t:sub; select -assert-count 2 t:bar' recursive.v diff --git a/tests/techmap/run-test.sh b/tests/techmap/run-test.sh index c16f204d9..581847ab0 100755 --- a/tests/techmap/run-test.sh +++ b/tests/techmap/run-test.sh @@ -1,20 +1,4 @@ #!/usr/bin/env bash -set -e -{ -echo "all::" -for x in *.ys; do - echo "all:: run-$x" - echo "run-$x:" - echo " @echo 'Running $x..'" - echo " @../../yosys -ql ${x%.ys}.log -e 'select out of bounds' $x" -done -for s in *.sh; do - if [ "$s" != "run-test.sh" ]; then - echo "all:: run-$s" - echo "run-$s:" - echo " @echo 'Running $s..'" - echo " @bash $s > ${s%.sh}.log 2>&1" - fi -done -} > run-test.mk -exec ${MAKE:-make} -f run-test.mk +set -eu +source ../gen-tests-makefile.sh +run_tests --yosys-scripts --bash --yosys-args "-e 'select out of bounds'" diff --git a/tests/various/run-test.sh b/tests/various/run-test.sh index ea56b70f0..2f91cf0fd 100755 --- a/tests/various/run-test.sh +++ b/tests/various/run-test.sh @@ -1,20 +1,4 @@ #!/usr/bin/env bash -set -e -{ -echo "all::" -for x in *.ys; do - echo "all:: run-$x" - echo "run-$x:" - echo " @echo 'Running $x..'" - echo " @../../yosys -ql ${x%.ys}.log $x" -done -for s in *.sh; do - if [ "$s" != "run-test.sh" ]; then - echo "all:: run-$s" - echo "run-$s:" - echo " @echo 'Running $s..'" - echo " @bash $s" - fi -done -} > run-test.mk -exec ${MAKE:-make} -f run-test.mk +set -eu +source ../gen-tests-makefile.sh +run_tests --yosys-scripts --bash diff --git a/tests/verilog/.gitignore b/tests/verilog/.gitignore index b48f808a1..34da23437 100644 --- a/tests/verilog/.gitignore +++ b/tests/verilog/.gitignore @@ -1,3 +1,5 @@ /*.log /*.out /run-test.mk +/const_arst.v +/const_sr.v diff --git a/tests/verilog/const_arst.ys b/tests/verilog/const_arst.ys new file mode 100644 index 000000000..df720575c --- /dev/null +++ b/tests/verilog/const_arst.ys @@ -0,0 +1,24 @@ +read_verilog <<EOT +module test ( + input clk, d, + output reg q +); +wire nop = 1'h0; +always @(posedge clk, posedge nop) begin + if (nop) q <= 1'b0; + else q <= d; +end +endmodule +EOT +prep -top test +write_verilog const_arst.v +design -stash gold +read_verilog const_arst.v +prep -top test +design -stash gate +design -copy-from gold -as gold A:top +design -copy-from gate -as gate A:top +miter -equiv -flatten -make_assert gold gate miter +prep -top miter +clk2fflogic +sat -set-init-zero -tempinduct -prove-asserts -verify diff --git a/tests/verilog/const_sr.ys b/tests/verilog/const_sr.ys new file mode 100644 index 000000000..c1406b0a0 --- /dev/null +++ b/tests/verilog/const_sr.ys @@ -0,0 +1,25 @@ +read_verilog <<EOT +module test ( + input clk, rst, d, + output reg q +); +wire nop = 1'h0; +always @(posedge clk, posedge nop, posedge rst) begin + if (rst) q <= 1'b0; + else if (nop) q <= 1'b1; + else q <= d; +end +endmodule +EOT +prep -top test +write_verilog const_sr.v +design -stash gold +read_verilog const_sr.v +prep -top test +design -stash gate +design -copy-from gold -as gold A:top +design -copy-from gate -as gate A:top +miter -equiv -flatten -make_assert gold gate miter +prep -top miter +clk2fflogic +sat -set-init-zero -tempinduct -prove-asserts -verify diff --git a/tests/verilog/run-test.sh b/tests/verilog/run-test.sh index ea56b70f0..2f91cf0fd 100755 --- a/tests/verilog/run-test.sh +++ b/tests/verilog/run-test.sh @@ -1,20 +1,4 @@ #!/usr/bin/env bash -set -e -{ -echo "all::" -for x in *.ys; do - echo "all:: run-$x" - echo "run-$x:" - echo " @echo 'Running $x..'" - echo " @../../yosys -ql ${x%.ys}.log $x" -done -for s in *.sh; do - if [ "$s" != "run-test.sh" ]; then - echo "all:: run-$s" - echo "run-$s:" - echo " @echo 'Running $s..'" - echo " @bash $s" - fi -done -} > run-test.mk -exec ${MAKE:-make} -f run-test.mk +set -eu +source ../gen-tests-makefile.sh +run_tests --yosys-scripts --bash |