Fix scope map for multiple construction (#2710)

This commit is contained in:
Todd Strader
2020-12-17 12:21:40 -05:00
committed by GitHub
parent c18cbca813
commit a88965a124
5 changed files with 59 additions and 29 deletions
+41 -29
View File
@@ -116,6 +116,7 @@ class EmitCSyms final : EmitCBaseVisitor {
void checkSplit(bool usesVfinal);
void closeSplit();
void emitSymImpPreamble();
void emitScopeHier(bool destroy);
void emitSymImp();
void emitDpiHdr();
void emitDpiImp();
@@ -467,7 +468,7 @@ void EmitCSyms::emitSymHdr() {
puts("\n// CREATORS\n");
puts(symClassName() + "(" + topClassName() + "* topp, const char* namep);\n");
puts(string("~") + symClassName() + "() = default;\n");
puts(string("~") + symClassName() + "();\n");
for (const auto& i : m_usesVfinal) {
puts("void " + symClassName() + "_" + cvtToStr(i.first) + "(");
@@ -555,6 +556,40 @@ void EmitCSyms::emitSymImpPreamble() {
}
}
void EmitCSyms::emitScopeHier(bool destroy) {
if (v3Global.opt.vpi()) {
string verb = destroy ? "Tear down" : "Set up";
string method = destroy ? "remove" : "add";
puts("\n// " + verb + " scope hierarchy\n");
for (ScopeNames::const_iterator it = m_scopeNames.begin(); it != m_scopeNames.end();
++it) {
string name = it->second.m_prettyName;
if (it->first == "TOP") continue;
if ((name.find('.') == string::npos) && (it->second.m_type == "SCOPE_MODULE")) {
puts("__Vhier." + method + "(0, &" + protect("__Vscope_" + it->second.m_symName)
+ ");\n");
}
}
for (ScopeNameHierarchy::const_iterator it = m_vpiScopeHierarchy.begin();
it != m_vpiScopeHierarchy.end(); ++it) {
for (ScopeNameList::const_iterator lit = it->second.begin(); lit != it->second.end();
++lit) {
string fromname = scopeSymString(it->first);
string toname = scopeSymString(*lit);
const auto from = vlstd::as_const(m_scopeNames).find(fromname);
const auto to = vlstd::as_const(m_scopeNames).find(toname);
UASSERT(from != m_scopeNames.end(), fromname + " not in m_scopeNames");
UASSERT(to != m_scopeNames.end(), toname + " not in m_scopeNames");
puts("__Vhier." + method + "(");
puts("&" + protect("__Vscope_" + from->second.m_symName) + ", ");
puts("&" + protect("__Vscope_" + to->second.m_symName) + ");\n");
}
}
puts("\n");
}
}
void EmitCSyms::emitSymImp() {
UINFO(6, __FUNCTION__ << ": " << endl);
string filename = v3Global.opt.makeDir() + "/" + symClassName() + ".cpp";
@@ -604,6 +639,10 @@ void EmitCSyms::emitSymImp() {
puts("\n");
puts("\n// FUNCTIONS\n");
puts(symClassName() + "::~" + symClassName() + "()\n");
puts("{\n");
emitScopeHier(true);
puts("}\n\n");
puts(symClassName() + "::" + symClassName() + "(" + topClassName()
+ "* topp, const char* namep)\n");
puts(" // Setup locals\n");
@@ -685,34 +724,7 @@ void EmitCSyms::emitSymImp() {
}
}
if (v3Global.opt.vpi()) {
puts("\n// Setup scope hierarchy\n");
for (ScopeNames::const_iterator it = m_scopeNames.begin(); it != m_scopeNames.end();
++it) {
string name = it->second.m_prettyName;
if (it->first == "TOP") continue;
if ((name.find('.') == string::npos) && (it->second.m_type == "SCOPE_MODULE")) {
puts("__Vhier.add(0, &" + protect("__Vscope_" + it->second.m_symName) + ");\n");
}
}
for (ScopeNameHierarchy::const_iterator it = m_vpiScopeHierarchy.begin();
it != m_vpiScopeHierarchy.end(); ++it) {
for (ScopeNameList::const_iterator lit = it->second.begin(); lit != it->second.end();
++lit) {
string fromname = scopeSymString(it->first);
string toname = scopeSymString(*lit);
const auto from = vlstd::as_const(m_scopeNames).find(fromname);
const auto to = vlstd::as_const(m_scopeNames).find(toname);
UASSERT(from != m_scopeNames.end(), fromname + " not in m_scopeNames");
UASSERT(to != m_scopeNames.end(), toname + " not in m_scopeNames");
puts("__Vhier.add(");
puts("&" + protect("__Vscope_" + from->second.m_symName) + ", ");
puts("&" + protect("__Vscope_" + to->second.m_symName) + ");\n");
}
}
puts("\n");
}
emitScopeHier(false);
// Everything past here is in the __Vfinal loop, so start a new split file if needed
closeSplit();