aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--backends/verilog/verilog_backend.cc4
-rw-r--r--frontends/ast/simplify.cc45
-rw-r--r--kernel/log.cc4
-rw-r--r--kernel/register.cc2
-rw-r--r--kernel/rtlil.cc2
-rw-r--r--kernel/rtlil.h64
-rw-r--r--kernel/yosys.cc8
-rw-r--r--techlibs/ice40/cells_sim.v19
8 files changed, 102 insertions, 46 deletions
diff --git a/backends/verilog/verilog_backend.cc b/backends/verilog/verilog_backend.cc
index 6818edb7a..83d83f488 100644
--- a/backends/verilog/verilog_backend.cc
+++ b/backends/verilog/verilog_backend.cc
@@ -1673,6 +1673,8 @@ struct VerilogBackend : public Backend {
bool blackboxes = false;
bool selected = false;
+ auto_name_map.clear();
+ reg_wires.clear();
reg_ct.clear();
reg_ct.insert("$dff");
@@ -1779,6 +1781,8 @@ struct VerilogBackend : public Backend {
dump_module(*f, "", it->second);
}
+ auto_name_map.clear();
+ reg_wires.clear();
reg_ct.clear();
}
} VerilogBackend;
diff --git a/frontends/ast/simplify.cc b/frontends/ast/simplify.cc
index ae7dec88d..1c9932ee0 100644
--- a/frontends/ast/simplify.cc
+++ b/frontends/ast/simplify.cc
@@ -50,7 +50,6 @@ using namespace AST_INTERNAL;
bool AstNode::simplify(bool const_fold, bool at_zero, bool in_lvalue, int stage, int width_hint, bool sign_hint, bool in_param)
{
static int recursion_counter = 0;
- static pair<string, int> last_blocking_assignment_warn;
static bool deep_recursion_warning = false;
if (recursion_counter++ == 1000 && deep_recursion_warning) {
@@ -72,7 +71,6 @@ bool AstNode::simplify(bool const_fold, bool at_zero, bool in_lvalue, int stage,
if (stage == 0)
{
log_assert(type == AST_MODULE || type == AST_INTERFACE);
- last_blocking_assignment_warn = pair<string, int>();
deep_recursion_warning = true;
while (simplify(const_fold, at_zero, in_lvalue, 1, width_hint, sign_hint, in_param)) { }
@@ -1592,14 +1590,6 @@ skip_dynamic_range_lvalue_expansion:;
sstr << "$memwr$" << children[0]->str << "$" << filename << ":" << linenum << "$" << (autoidx++);
std::string id_addr = sstr.str() + "_ADDR", id_data = sstr.str() + "_DATA", id_en = sstr.str() + "_EN";
- if (type == AST_ASSIGN_EQ) {
- pair<string, int> this_blocking_assignment_warn(filename, linenum);
- if (this_blocking_assignment_warn != last_blocking_assignment_warn)
- log_warning("Blocking assignment to memory in line %s:%d is handled like a non-blocking assignment.\n",
- filename.c_str(), linenum);
- last_blocking_assignment_warn = this_blocking_assignment_warn;
- }
-
int mem_width, mem_size, addr_bits;
bool mem_signed = children[0]->id2ast->is_signed;
children[0]->id2ast->meminfo(mem_width, mem_size, addr_bits);
@@ -2928,7 +2918,7 @@ void AstNode::mem2reg_as_needed_pass1(dict<AstNode*, pool<std::string>> &mem2reg
dict<AstNode*, uint32_t> &mem2reg_candidates, dict<AstNode*, uint32_t> &proc_flags, uint32_t &flags)
{
uint32_t children_flags = 0;
- int ignore_children_counter = 0;
+ int lhs_children_counter = 0;
if (type == AST_ASSIGN || type == AST_ASSIGN_LE || type == AST_ASSIGN_EQ)
{
@@ -2954,12 +2944,14 @@ void AstNode::mem2reg_as_needed_pass1(dict<AstNode*, pool<std::string>> &mem2reg
proc_flags[mem] |= AstNode::MEM2REG_FL_EQ1;
}
- // remember if this is a constant index or not
- if (children[0]->children.size() && children[0]->children[0]->type == AST_RANGE && children[0]->children[0]->children.size()) {
- if (children[0]->children[0]->children[0]->type == AST_CONSTANT)
- mem2reg_candidates[mem] |= AstNode::MEM2REG_FL_CONST_LHS;
- else
- mem2reg_candidates[mem] |= AstNode::MEM2REG_FL_VAR_LHS;
+ // for proper (non-init) writes: remember if this is a constant index or not
+ if ((flags & MEM2REG_FL_INIT) == 0) {
+ if (children[0]->children.size() && children[0]->children[0]->type == AST_RANGE && children[0]->children[0]->children.size()) {
+ if (children[0]->children[0]->children[0]->type == AST_CONSTANT)
+ mem2reg_candidates[mem] |= AstNode::MEM2REG_FL_CONST_LHS;
+ else
+ mem2reg_candidates[mem] |= AstNode::MEM2REG_FL_VAR_LHS;
+ }
}
// remember where this is
@@ -2974,7 +2966,7 @@ void AstNode::mem2reg_as_needed_pass1(dict<AstNode*, pool<std::string>> &mem2reg
}
}
- ignore_children_counter = 1;
+ lhs_children_counter = 1;
}
if (type == AST_IDENTIFIER && id2ast && id2ast->type == AST_MEMORY)
@@ -3017,12 +3009,23 @@ void AstNode::mem2reg_as_needed_pass1(dict<AstNode*, pool<std::string>> &mem2reg
log_assert((flags & ~0x000000ff) == 0);
for (auto child : children)
- if (ignore_children_counter > 0)
- ignore_children_counter--;
- else if (proc_flags_p)
+ {
+ if (lhs_children_counter > 0) {
+ lhs_children_counter--;
+ if (child->children.size() && child->children[0]->type == AST_RANGE && child->children[0]->children.size()) {
+ for (auto c : child->children[0]->children) {
+ if (proc_flags_p)
+ c->mem2reg_as_needed_pass1(mem2reg_places, mem2reg_candidates, *proc_flags_p, flags);
+ else
+ c->mem2reg_as_needed_pass1(mem2reg_places, mem2reg_candidates, proc_flags, flags);
+ }
+ }
+ } else
+ if (proc_flags_p)
child->mem2reg_as_needed_pass1(mem2reg_places, mem2reg_candidates, *proc_flags_p, flags);
else
child->mem2reg_as_needed_pass1(mem2reg_places, mem2reg_candidates, proc_flags, flags);
+ }
flags &= ~children_flags | backup_flags;
diff --git a/kernel/log.cc b/kernel/log.cc
index 0ee2170a0..400a549dd 100644
--- a/kernel/log.cc
+++ b/kernel/log.cc
@@ -196,7 +196,11 @@ void logv_header(RTLIL::Design *design, const char *format, va_list ap)
if (log_hdump.count(header_id) && design != nullptr)
for (auto &filename : log_hdump.at(header_id)) {
log("Dumping current design to '%s'.\n", filename.c_str());
+ if (yosys_xtrace)
+ IdString::xtrace_db_dump();
Pass::call(design, {"dump", "-o", filename});
+ if (yosys_xtrace)
+ log("#X# -- end of dump --\n");
}
if (pop_errfile)
diff --git a/kernel/register.cc b/kernel/register.cc
index 402a5b3ea..64956401f 100644
--- a/kernel/register.cc
+++ b/kernel/register.cc
@@ -86,6 +86,8 @@ Pass::pre_post_exec_state_t Pass::pre_execute()
void Pass::post_execute(Pass::pre_post_exec_state_t state)
{
+ IdString::checkpoint();
+
int64_t time_ns = PerformanceTimer::query() - state.begin_ns;
runtime_ns += time_ns;
current_pass = state.parent_pass;
diff --git a/kernel/rtlil.cc b/kernel/rtlil.cc
index d4aebcda9..7f1816190 100644
--- a/kernel/rtlil.cc
+++ b/kernel/rtlil.cc
@@ -33,6 +33,8 @@ std::vector<int> RTLIL::IdString::global_refcount_storage_;
std::vector<char*> RTLIL::IdString::global_id_storage_;
dict<char*, int, hash_cstr_ops> RTLIL::IdString::global_id_index_;
std::vector<int> RTLIL::IdString::global_free_idx_list_;
+int RTLIL::IdString::last_created_idx_[8];
+int RTLIL::IdString::last_created_idx_ptr_;
RTLIL::Const::Const()
{
diff --git a/kernel/rtlil.h b/kernel/rtlil.h
index f877622aa..01323d112 100644
--- a/kernel/rtlil.h
+++ b/kernel/rtlil.h
@@ -76,6 +76,9 @@ namespace RTLIL
struct IdString
{
+ #undef YOSYS_XTRACE_GET_PUT
+ #undef YOSYS_SORT_ID_FREE_LIST
+
// the global id string cache
static struct destruct_guard_t {
@@ -89,9 +92,43 @@ namespace RTLIL
static dict<char*, int, hash_cstr_ops> global_id_index_;
static std::vector<int> global_free_idx_list_;
+ static int last_created_idx_ptr_;
+ static int last_created_idx_[8];
+
+ static inline void xtrace_db_dump()
+ {
+ #ifdef YOSYS_XTRACE_GET_PUT
+ for (int idx = 0; idx < GetSize(global_id_storage_); idx++)
+ {
+ if (global_id_storage_.at(idx) == nullptr)
+ log("#X# DB-DUMP index %d: FREE\n", idx);
+ else
+ log("#X# DB-DUMP index %d: '%s' (ref %d)\n", idx, global_id_storage_.at(idx), global_refcount_storage_.at(idx));
+ }
+ #endif
+ }
+
+ static inline void checkpoint()
+ {
+ last_created_idx_ptr_ = 0;
+ for (int i = 0; i < 8; i++) {
+ if (last_created_idx_[i])
+ put_reference(last_created_idx_[i]);
+ last_created_idx_[i] = 0;
+ }
+ #ifdef YOSYS_SORT_ID_FREE_LIST
+ std::sort(global_free_idx_list_.begin(), global_free_idx_list_.end(), std::greater<int>());
+ #endif
+ }
+
static inline int get_reference(int idx)
{
global_refcount_storage_.at(idx)++;
+ #ifdef YOSYS_XTRACE_GET_PUT
+ if (yosys_xtrace) {
+ log("#X# GET-BY-INDEX '%s' (index %d, refcount %d)\n", global_id_storage_.at(idx), idx, global_refcount_storage_.at(idx));
+ }
+ #endif
return idx;
}
@@ -107,6 +144,11 @@ namespace RTLIL
auto it = global_id_index_.find((char*)p);
if (it != global_id_index_.end()) {
global_refcount_storage_.at(it->second)++;
+ #ifdef YOSYS_XTRACE_GET_PUT
+ if (yosys_xtrace) {
+ log("#X# GET-BY-NAME '%s' (index %d, refcount %d)\n", global_id_storage_.at(it->second), it->second, global_refcount_storage_.at(it->second));
+ }
+ #endif
return it->second;
}
@@ -124,16 +166,22 @@ namespace RTLIL
global_refcount_storage_.at(idx)++;
// Avoid Create->Delete->Create pattern
- static IdString last_created_id;
- put_reference(last_created_id.index_);
- last_created_id.index_ = idx;
- get_reference(last_created_id.index_);
+ if (last_created_idx_[last_created_idx_ptr_])
+ put_reference(last_created_idx_[last_created_idx_ptr_]);
+ last_created_idx_[last_created_idx_ptr_] = idx;
+ get_reference(last_created_idx_[last_created_idx_ptr_]);
+ last_created_idx_ptr_ = (last_created_idx_ptr_ + 1) & 7;
if (yosys_xtrace) {
log("#X# New IdString '%s' with index %d.\n", p, idx);
log_backtrace("-X- ", yosys_xtrace-1);
}
+ #ifdef YOSYS_XTRACE_GET_PUT
+ if (yosys_xtrace) {
+ log("#X# GET-BY-NAME '%s' (index %d, refcount %d)\n", global_id_storage_.at(idx), idx, global_refcount_storage_.at(idx));
+ }
+ #endif
return idx;
}
@@ -144,6 +192,12 @@ namespace RTLIL
if (!destruct_guard.ok)
return;
+ #ifdef YOSYS_XTRACE_GET_PUT
+ if (yosys_xtrace) {
+ log("#X# PUT '%s' (index %d, refcount %d)\n", global_id_storage_.at(idx), idx, global_refcount_storage_.at(idx));
+ }
+ #endif
+
log_assert(global_refcount_storage_.at(idx) > 0);
if (--global_refcount_storage_.at(idx) != 0)
@@ -1282,7 +1336,7 @@ inline bool RTLIL::SigBit::operator<(const RTLIL::SigBit &other) const {
return wire ? (offset < other.offset) : (data < other.data);
if (wire != nullptr && other.wire != nullptr)
return wire->name < other.wire->name;
- return wire < other.wire;
+ return (wire != nullptr) < (other.wire != nullptr);
}
inline bool RTLIL::SigBit::operator==(const RTLIL::SigBit &other) const {
diff --git a/kernel/yosys.cc b/kernel/yosys.cc
index 6fd53f85e..450e4e4cf 100644
--- a/kernel/yosys.cc
+++ b/kernel/yosys.cc
@@ -218,12 +218,18 @@ std::string next_token(std::string &text, const char *sep, bool long_strings)
if (long_strings && pos_begin != text.size() && text[pos_begin] == '"') {
string sep_string = sep;
- for (size_t i = pos_begin+1; i < text.size(); i++)
+ for (size_t i = pos_begin+1; i < text.size(); i++) {
if (text[i] == '"' && (i+1 == text.size() || sep_string.find(text[i+1]) != std::string::npos)) {
std::string token = text.substr(pos_begin, i-pos_begin+1);
text = text.substr(i+1);
return token;
}
+ if (i+1 < text.size() && text[i] == '"' && text[i+1] == ';' && (i+2 == text.size() || sep_string.find(text[i+2]) != std::string::npos)) {
+ std::string token = text.substr(pos_begin, i-pos_begin+1);
+ text = text.substr(i+2);
+ return token + ";";
+ }
+ }
}
size_t pos_end = text.find_first_of(sep, pos_begin);
diff --git a/techlibs/ice40/cells_sim.v b/techlibs/ice40/cells_sim.v
index bc36cdd14..62a28364b 100644
--- a/techlibs/ice40/cells_sim.v
+++ b/techlibs/ice40/cells_sim.v
@@ -414,24 +414,6 @@ module SB_RAM40_4K (
$readmemh(INIT_FILE, memory);
else
for (i=0; i<16; i=i+1) begin
-`ifdef YOSYS
- memory[ 0*16 + i] <= INIT_0[16*i +: 16];
- memory[ 1*16 + i] <= INIT_1[16*i +: 16];
- memory[ 2*16 + i] <= INIT_2[16*i +: 16];
- memory[ 3*16 + i] <= INIT_3[16*i +: 16];
- memory[ 4*16 + i] <= INIT_4[16*i +: 16];
- memory[ 5*16 + i] <= INIT_5[16*i +: 16];
- memory[ 6*16 + i] <= INIT_6[16*i +: 16];
- memory[ 7*16 + i] <= INIT_7[16*i +: 16];
- memory[ 8*16 + i] <= INIT_8[16*i +: 16];
- memory[ 9*16 + i] <= INIT_9[16*i +: 16];
- memory[10*16 + i] <= INIT_A[16*i +: 16];
- memory[11*16 + i] <= INIT_B[16*i +: 16];
- memory[12*16 + i] <= INIT_C[16*i +: 16];
- memory[13*16 + i] <= INIT_D[16*i +: 16];
- memory[14*16 + i] <= INIT_E[16*i +: 16];
- memory[15*16 + i] <= INIT_F[16*i +: 16];
-`else
memory[ 0*16 + i] = INIT_0[16*i +: 16];
memory[ 1*16 + i] = INIT_1[16*i +: 16];
memory[ 2*16 + i] = INIT_2[16*i +: 16];
@@ -448,7 +430,6 @@ module SB_RAM40_4K (
memory[13*16 + i] = INIT_D[16*i +: 16];
memory[14*16 + i] = INIT_E[16*i +: 16];
memory[15*16 + i] = INIT_F[16*i +: 16];
-`endif
end
end