diff options
| author | Marcin KoĆcielnicki <marcin@symbioticeda.com> | 2019-09-27 11:03:04 +0200 | 
|---|---|---|
| committer | Marcin KoĆcielnicki <koriakin@0x04.net> | 2019-09-27 18:34:12 +0200 | 
| commit | fd0e3a2c43d96ba31beede9865d5000230029994 (patch) | |
| tree | 4a208618b2d7fa0cfbac4f2b45fa5f20a681f5a5 | |
| parent | 4b15cf5f76e2226bbce1a73d1e0ff54fbf093fe8 (diff) | |
| download | yosys-fd0e3a2c43d96ba31beede9865d5000230029994.tar.gz yosys-fd0e3a2c43d96ba31beede9865d5000230029994.tar.bz2 yosys-fd0e3a2c43d96ba31beede9865d5000230029994.zip | |
Fix _TECHMAP_REMOVEINIT_ handling.
Previously, this wire was handled in the code that populated the "do or
do not" techmap cache, resulting in init value removal being performed
only for the first use of a given template.
Fixes the problem identified in #1396.
| -rw-r--r-- | passes/techmap/techmap.cc | 30 | ||||
| -rw-r--r-- | tests/techmap/wireinit.ys | 14 | 
2 files changed, 29 insertions, 15 deletions
| diff --git a/passes/techmap/techmap.cc b/passes/techmap/techmap.cc index 1d0362ad6..08a1af2d5 100644 --- a/passes/techmap/techmap.cc +++ b/passes/techmap/techmap.cc @@ -935,19 +935,6 @@ struct TechmapWorker  							for (auto &it2 : it.second)  								if (!it2.value.is_fully_const())  									log_error("Techmap yielded config wire %s with non-const value %s.\n", RTLIL::id2cstr(it2.wire->name), log_signal(it2.value)); -						if (it.first.substr(0, 20) == "_TECHMAP_REMOVEINIT_" && techmap_do_cache[tpl]) { -							for (auto &it2 : it.second) { -								auto val = it2.value.as_const(); -								auto wirename = RTLIL::escape_id(it.first.substr(20, it.first.size() - 20 - 1)); -								auto it = cell->connections().find(wirename); -								if (it != cell->connections().end()) { -									auto sig = sigmap(it->second); -									for (int i = 0; i < sig.size(); i++) -										if (val[i] == State::S1) -											remove_init_bits.insert(sig[i]); -								} -							} -						}  						techmap_wire_names.erase(it.first);  					} @@ -973,6 +960,23 @@ struct TechmapWorker  					mkdebug.off();  				} +				TechmapWires twd = techmap_find_special_wires(tpl); +				for (auto &it : twd) { +					if (it.first.substr(0, 20) == "_TECHMAP_REMOVEINIT_") { +						for (auto &it2 : it.second) { +							auto val = it2.value.as_const(); +							auto wirename = RTLIL::escape_id(it.first.substr(20, it.first.size() - 20 - 1)); +							auto it = cell->connections().find(wirename); +							if (it != cell->connections().end()) { +								auto sig = sigmap(it->second); +								for (int i = 0; i < sig.size(); i++) +									if (val[i] == State::S1) +										remove_init_bits.insert(sig[i]); +							} +						} +					} +				} +  				if (extern_mode && !in_recursion)  				{  					std::string m_name = stringf("$extern:%s", log_id(tpl)); diff --git a/tests/techmap/wireinit.ys b/tests/techmap/wireinit.ys index 1396839fe..89afaafb5 100644 --- a/tests/techmap/wireinit.ys +++ b/tests/techmap/wireinit.ys @@ -46,11 +46,13 @@ input clk;  input d;  output reg q0 = 0;  output reg q1 = 1; +output reg qq0 = 0;  output reg qx;  always @(posedge clk) begin  	q0 <= d;  	q1 <= d; +	qq0 <= q0;  	qx <= d;  end  endmodule @@ -64,16 +66,20 @@ simplemap  techmap -map %map  clean  # Make sure the parameter was used properly. -select -assert-count 2 top/t:ffbb +select -assert-count 3 top/t:ffbb  select -set ff0 top/w:q0 %ci t:ffbb %i +select -set ffq0 top/w:qq0 %ci t:ffbb %i  select -set ffx top/w:qx %ci t:ffbb %i  select -assert-count 1 @ff0 +select -assert-count 1 @ffq0  select -assert-count 1 @ffx  select -assert-count 1 @ff0 r:INIT=1'b0 %i +select -assert-count 1 @ffq0 r:INIT=1'b0 %i  select -assert-count 1 @ffx r:INIT=1'bx %i  select -assert-count 0 top/w:q1 %ci t:ffbb %i  # Make sure the init values are dropped from the wires iff mapping was performed.  select -assert-count 0 top/w:q0 a:init %i +select -assert-count 0 top/w:qq0 a:init %i  select -assert-count 1 top/w:q1 a:init=1'b1 %i  select -assert-count 0 top/w:qx a:init %i @@ -84,15 +90,19 @@ simplemap  techmap -map %map_noremove  clean  # Make sure the parameter was used properly. -select -assert-count 2 top/t:ffbb +select -assert-count 3 top/t:ffbb  select -set ff0 top/w:q0 %ci t:ffbb %i +select -set ffq0 top/w:qq0 %ci t:ffbb %i  select -set ffx top/w:qx %ci t:ffbb %i  select -assert-count 1 @ff0 +select -assert-count 1 @ffq0  select -assert-count 1 @ffx  select -assert-count 1 @ff0 r:INIT=1'b0 %i +select -assert-count 1 @ffq0 r:INIT=1'b0 %i  select -assert-count 1 @ffx r:INIT=1'bx %i  select -assert-count 0 top/w:q1 %ci t:ffbb %i  # Make sure the init values are not dropped from the wires.  select -assert-count 1 top/w:q0 a:init=1'b0 %i +select -assert-count 1 top/w:qq0 a:init=1'b0 %i  select -assert-count 1 top/w:q1 a:init=1'b1 %i  select -assert-count 0 top/w:qx a:init %i | 
