Internals: Style cleanup. No functional change.
This commit is contained in:
parent
1acff950d0
commit
5ae09daf5b
|
|
@ -44,18 +44,18 @@ private:
|
|||
// NODE STATE
|
||||
// Cleared entire netlist
|
||||
// AstCFunc::user() // bool. Indicates processing completed
|
||||
AstUser1InUse m_inuser1;
|
||||
AstUser1InUse m_inuser1;
|
||||
|
||||
// TYPES
|
||||
typedef std::multimap<string,AstCFunc*> FuncMmap;
|
||||
typedef std::multimap<string, AstCFunc*> FuncMmap;
|
||||
|
||||
// STATE
|
||||
AstNodeModule* m_modp; // Current module
|
||||
AstScope* m_scopep; // Current scope
|
||||
bool m_modSingleton; // m_modp is only instanced once
|
||||
bool m_allowThis; // Allow function non-static
|
||||
bool m_needThis; // Make function non-static
|
||||
FuncMmap m_modFuncs; // Name of public functions added
|
||||
AstNodeModule* m_modp; // Current module
|
||||
AstScope* m_scopep; // Current scope
|
||||
bool m_modSingleton; // m_modp is only instanced once
|
||||
bool m_allowThis; // Allow function non-static
|
||||
bool m_needThis; // Make function non-static
|
||||
FuncMmap m_modFuncs; // Name of public functions added
|
||||
|
||||
// METHODS
|
||||
VL_DEBUG_FUNC; // Declare debug()
|
||||
|
|
@ -63,7 +63,7 @@ private:
|
|||
static bool modIsSingleton(AstNodeModule* modp) {
|
||||
// True iff there's exactly one instance of this module in the design.
|
||||
int instances = 0;
|
||||
for (AstNode* stmtp = modp->stmtsp(); stmtp; stmtp=stmtp->nextp()) {
|
||||
for (AstNode* stmtp = modp->stmtsp(); stmtp; stmtp = stmtp->nextp()) {
|
||||
if (VN_IS(stmtp, Scope)) {
|
||||
if (++instances > 1) { return false; }
|
||||
}
|
||||
|
|
@ -81,8 +81,7 @@ private:
|
|||
// Sets 'hierThisr' true if the object is local to this scope
|
||||
// (and could be made into a function-local later in V3Localize),
|
||||
// false if the object is in another scope.
|
||||
string descopedName(const AstScope* scopep, bool& hierThisr,
|
||||
const AstVar* varp=NULL) {
|
||||
string descopedName(const AstScope* scopep, bool& hierThisr, const AstVar* varp = NULL) {
|
||||
UASSERT(scopep, "Var/Func not scoped");
|
||||
hierThisr = (scopep == m_scopep);
|
||||
|
||||
|
|
@ -97,7 +96,6 @@ private:
|
|||
//
|
||||
// Static functions can't use this
|
||||
if (!m_allowThis) relativeRefOk = false;
|
||||
|
||||
//
|
||||
// Use absolute refs in top-scoped routines, keep them static.
|
||||
// The DPI callback registration depends on representing top-level
|
||||
|
|
@ -106,18 +104,14 @@ private:
|
|||
//
|
||||
// V3Combine wouldn't likely be able to combine top-level
|
||||
// routines anyway, so there's no harm in keeping these static.
|
||||
if (m_modp->isTop()) {
|
||||
relativeRefOk = false;
|
||||
}
|
||||
if (m_modp->isTop()) relativeRefOk = false;
|
||||
//
|
||||
// Use absolute refs if this scope is the only instance of the module.
|
||||
// Saves a bit of overhead on passing the 'this' pointer, and there's no
|
||||
// need to be nice to V3Combine when we have only a single instance.
|
||||
// The risk that this prevents combining identical logic from differently-
|
||||
// named but identical modules seems low.
|
||||
if (m_modSingleton) {
|
||||
relativeRefOk = false;
|
||||
}
|
||||
if (m_modSingleton) relativeRefOk = false;
|
||||
|
||||
if (varp && varp->isFuncLocal()) {
|
||||
hierThisr = true;
|
||||
|
|
@ -130,23 +124,21 @@ private:
|
|||
// Reference to scope of cell directly under this module, can just "cell->"
|
||||
string name = scopep->name();
|
||||
string::size_type pos;
|
||||
if ((pos = name.rfind('.')) != string::npos) {
|
||||
name.erase(0, pos+1);
|
||||
}
|
||||
if ((pos = name.rfind('.')) != string::npos) name.erase(0, pos + 1);
|
||||
m_needThis = true;
|
||||
return name+"->";
|
||||
return name + "->";
|
||||
} else {
|
||||
// Reference to something elsewhere, or relative references
|
||||
// are disabled. Use global variable
|
||||
UINFO(8," Descope "<<scopep<<endl);
|
||||
UINFO(8," to "<<scopep->name()<<endl);
|
||||
UINFO(8," under "<<m_scopep->name()<<endl);
|
||||
UINFO(8, " Descope " << scopep << endl);
|
||||
UINFO(8, " to " << scopep->name() << endl);
|
||||
UINFO(8, " under " << m_scopep->name() << endl);
|
||||
if (!scopep->aboveScopep()) { // Top
|
||||
// We could also return "vlSymsp->TOPp->" here, but GCC would
|
||||
// suspect aliases.
|
||||
return "vlTOPp->";
|
||||
} else {
|
||||
return scopep->nameVlSym()+".";
|
||||
return scopep->nameVlSym() + ".";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -155,64 +147,64 @@ private:
|
|||
// We recorded all public functions in m_modFuncs.
|
||||
// If for any given name only one function exists, we can use that function directly.
|
||||
// If multiple functions exist, we need to select the appropriate scope.
|
||||
for (FuncMmap::iterator it = m_modFuncs.begin(); it!=m_modFuncs.end(); ++it) {
|
||||
for (FuncMmap::iterator it = m_modFuncs.begin(); it != m_modFuncs.end(); ++it) {
|
||||
string name = it->first;
|
||||
AstCFunc* topFuncp = it->second;
|
||||
FuncMmap::iterator nextIt1 = it; ++nextIt1;
|
||||
bool moreOfSame1 = (nextIt1!=m_modFuncs.end() && nextIt1->first == name);
|
||||
FuncMmap::iterator nextIt1 = it;
|
||||
++nextIt1;
|
||||
bool moreOfSame1 = (nextIt1 != m_modFuncs.end() && nextIt1->first == name);
|
||||
if (moreOfSame1) {
|
||||
// Multiple functions under this name, need a wrapper function
|
||||
UINFO(6," Wrapping "<<name<<" multifuncs\n");
|
||||
UINFO(6, " Wrapping " << name << " multifuncs\n");
|
||||
AstCFunc* newfuncp = topFuncp->cloneTree(false);
|
||||
if (newfuncp->initsp()) newfuncp->initsp()->unlinkFrBackWithNext()->deleteTree();
|
||||
if (newfuncp->stmtsp()) newfuncp->stmtsp()->unlinkFrBackWithNext()->deleteTree();
|
||||
if (newfuncp->initsp()) newfuncp->initsp()->unlinkFrBackWithNext()->deleteTree();
|
||||
if (newfuncp->stmtsp()) newfuncp->stmtsp()->unlinkFrBackWithNext()->deleteTree();
|
||||
if (newfuncp->finalsp()) newfuncp->finalsp()->unlinkFrBackWithNext()->deleteTree();
|
||||
newfuncp->name(name);
|
||||
newfuncp->isStatic(false);
|
||||
newfuncp->addInitsp(
|
||||
new AstCStmt(newfuncp->fileline(),
|
||||
EmitCBaseVisitor::symClassVar()+" = this->__VlSymsp;\n"));
|
||||
newfuncp->addInitsp(new AstCStmt(newfuncp->fileline(),
|
||||
EmitCBaseVisitor::symTopAssign()+"\n"));
|
||||
EmitCBaseVisitor::symClassVar() + " = this->__VlSymsp;\n"));
|
||||
newfuncp->addInitsp(
|
||||
new AstCStmt(newfuncp->fileline(), EmitCBaseVisitor::symTopAssign() + "\n"));
|
||||
topFuncp->addNextHere(newfuncp);
|
||||
// In the body, call each function if it matches the given scope
|
||||
for (FuncMmap::iterator eachIt = it;
|
||||
eachIt != m_modFuncs.end() && eachIt->first==name; ++eachIt) {
|
||||
eachIt != m_modFuncs.end() && eachIt->first == name; ++eachIt) {
|
||||
it = eachIt;
|
||||
AstCFunc* funcp = eachIt->second;
|
||||
FuncMmap::iterator nextIt2 = eachIt; ++nextIt2;
|
||||
bool moreOfSame = (nextIt2!=m_modFuncs.end() && nextIt2->first == name);
|
||||
FuncMmap::iterator nextIt2 = eachIt;
|
||||
++nextIt2;
|
||||
bool moreOfSame = (nextIt2 != m_modFuncs.end() && nextIt2->first == name);
|
||||
UASSERT_OBJ(funcp->scopep(), funcp, "Not scoped");
|
||||
|
||||
UINFO(6," Wrapping "<<name<<" "<<funcp<<endl);
|
||||
UINFO(6," at "<<newfuncp->argTypes()<<" und "<<funcp->argTypes()<<endl);
|
||||
UINFO(6, " Wrapping " << name << " " << funcp << endl);
|
||||
UINFO(6, " at " << newfuncp->argTypes()
|
||||
<< " und " << funcp->argTypes() << endl);
|
||||
funcp->declPrivate(true);
|
||||
AstNode* argsp = NULL;
|
||||
for (AstNode* stmtp = newfuncp->argsp(); stmtp; stmtp=stmtp->nextp()) {
|
||||
for (AstNode* stmtp = newfuncp->argsp(); stmtp; stmtp = stmtp->nextp()) {
|
||||
if (AstVar* portp = VN_CAST(stmtp, Var)) {
|
||||
if (portp->isIO() && !portp->isFuncReturn()) {
|
||||
AstNode* newp = new AstVarRef(portp->fileline(),
|
||||
portp, portp->isWritable());
|
||||
if (argsp) argsp = argsp->addNextNull(newp);
|
||||
else argsp = newp;
|
||||
AstNode* newp
|
||||
= new AstVarRef(portp->fileline(), portp, portp->isWritable());
|
||||
argsp = argsp ? argsp->addNextNull(newp) : newp;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
AstNode* returnp = new AstCReturn(funcp->fileline(),
|
||||
new AstCCall(funcp->fileline(),
|
||||
funcp, argsp));
|
||||
AstNode* returnp = new AstCReturn(
|
||||
funcp->fileline(), new AstCCall(funcp->fileline(), funcp, argsp));
|
||||
|
||||
if (moreOfSame) {
|
||||
AstIf* ifp = new AstIf(funcp->fileline(),
|
||||
new AstEq(funcp->fileline(),
|
||||
new AstCMath(funcp->fileline(),
|
||||
"this", 64),
|
||||
new AstCMath(funcp->fileline(),
|
||||
string("&(")
|
||||
+funcp->scopep()->nameVlSym()
|
||||
+")", 64)),
|
||||
returnp, NULL);
|
||||
AstIf* ifp = new AstIf(
|
||||
funcp->fileline(),
|
||||
new AstEq(
|
||||
funcp->fileline(), new AstCMath(funcp->fileline(), "this", 64),
|
||||
new AstCMath(funcp->fileline(),
|
||||
string("&(") + funcp->scopep()->nameVlSym() + ")",
|
||||
64)),
|
||||
returnp, NULL);
|
||||
newfuncp->addStmtsp(ifp);
|
||||
} else {
|
||||
newfuncp->addStmtsp(returnp);
|
||||
|
|
@ -220,14 +212,15 @@ private:
|
|||
}
|
||||
// Not really any way the user could do this, and we'd need
|
||||
// to come up with some return value
|
||||
//newfuncp->addStmtsp(new AstDisplay(newfuncp->fileline(),
|
||||
// newfuncp->addStmtsp(new AstDisplay(newfuncp->fileline(),
|
||||
// AstDisplayType::DT_WARNING,
|
||||
// string("%%Error: ")+name+"() called with bad scope", NULL));
|
||||
//newfuncp->addStmtsp(new AstStop(newfuncp->fileline()));
|
||||
if (debug()>=9) newfuncp->dumpTree(cout, " newfunc: ");
|
||||
// string("%%Error: ")+name+"() called with bad
|
||||
// scope", NULL));
|
||||
// newfuncp->addStmtsp(new AstStop(newfuncp->fileline()));
|
||||
if (debug() >= 9) newfuncp->dumpTree(cout, " newfunc: ");
|
||||
} else {
|
||||
// Only a single function under this name, we can simply rename it
|
||||
UINFO(6," Wrapping "<<name<<" just one "<<topFuncp<<endl);
|
||||
UINFO(6, " Wrapping " << name << " just one " << topFuncp << endl);
|
||||
topFuncp->name(name);
|
||||
}
|
||||
}
|
||||
|
|
@ -257,19 +250,19 @@ private:
|
|||
// Convert the hierch name
|
||||
UASSERT_OBJ(m_scopep, nodep, "Node not under scope");
|
||||
bool hierThis;
|
||||
nodep->hiername(descopedName(nodep->varScopep()->scopep(), hierThis/*ref*/,
|
||||
nodep->hiername(descopedName(nodep->varScopep()->scopep(), hierThis /*ref*/,
|
||||
nodep->varScopep()->varp()));
|
||||
nodep->hierThis(hierThis);
|
||||
nodep->varScopep(NULL);
|
||||
}
|
||||
virtual void visit(AstCCall* nodep) {
|
||||
//UINFO(9," "<<nodep<<endl);
|
||||
// UINFO(9," "<<nodep<<endl);
|
||||
iterateChildren(nodep);
|
||||
// Convert the hierch name
|
||||
UASSERT_OBJ(m_scopep, nodep, "Node not under scope");
|
||||
UASSERT_OBJ(nodep->funcp()->scopep(), nodep, "CFunc not under scope");
|
||||
bool hierThis;
|
||||
nodep->hiername(descopedName(nodep->funcp()->scopep(), hierThis/*ref*/));
|
||||
nodep->hiername(descopedName(nodep->funcp()->scopep(), hierThis /*ref*/));
|
||||
// Can't do this, as we may have more calls later
|
||||
// nodep->funcp()->scopep(NULL);
|
||||
}
|
||||
|
|
@ -279,9 +272,7 @@ private:
|
|||
m_allowThis = nodep->isStatic().falseU(); // Non-static or unknown if static
|
||||
iterateChildren(nodep);
|
||||
nodep->user1(true);
|
||||
if (m_needThis) {
|
||||
nodep->isStatic(false);
|
||||
}
|
||||
if (m_needThis) nodep->isStatic(false);
|
||||
// If it's under a scope, move it up to the top
|
||||
if (m_scopep) {
|
||||
nodep->unlinkFrBack();
|
||||
|
|
@ -291,23 +282,22 @@ private:
|
|||
// There may be multiple public functions by the same name;
|
||||
// record for later correction or making of shells
|
||||
m_modFuncs.insert(make_pair(nodep->name(), nodep));
|
||||
nodep->name(m_scopep->nameDotless() +"__" + nodep->name());
|
||||
nodep->name(m_scopep->nameDotless() + "__" + nodep->name());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
virtual void visit(AstVar*) {}
|
||||
virtual void visit(AstNode* nodep) {
|
||||
iterateChildren(nodep);
|
||||
}
|
||||
virtual void visit(AstNode* nodep) { iterateChildren(nodep); }
|
||||
|
||||
public:
|
||||
// CONSTRUCTORS
|
||||
explicit DescopeVisitor(AstNetlist* nodep)
|
||||
: m_modp(NULL),
|
||||
m_scopep(NULL),
|
||||
m_modSingleton(false),
|
||||
m_allowThis(false),
|
||||
m_needThis(false) {
|
||||
: m_modp(NULL)
|
||||
, m_scopep(NULL)
|
||||
, m_modSingleton(false)
|
||||
, m_allowThis(false)
|
||||
, m_needThis(false) {
|
||||
iterate(nodep);
|
||||
}
|
||||
virtual ~DescopeVisitor() {}
|
||||
|
|
|
|||
Loading…
Reference in New Issue