Reduce .rodata footprint of trace initialization (#3250)
Trace initialization (tracep->decl* functions) used to explicitly pass the complete hierarchical names of signals as string constants. This contains a lot of redundancy (path prefixes), does not scale well with large designs and resulted in .rodata sections (the string constants) in ELF executables being extremely large. This patch changes the API of trace initialization that allows pushing and popping name prefixes as we walk the hierarchy tree, which are prepended to declared signal names at run-time during trace initialization. This in turn allows us to emit repeat path/name components only once, effectively removing all duplicate path prefixes. On SweRV EH1 this reduces the .rodata section in a --trace build by 94%. Additionally, trace declarations are now emitted in lexical order by hierarchical signal names, and the top level trace initialization function respects --output-split-ctrace.
This commit is contained in:
parent
30ccccdb67
commit
ff425369ac
1
Changes
1
Changes
|
|
@ -21,6 +21,7 @@ Verilator 4.217 devel
|
||||||
|
|
||||||
* Support lower dimension looping in foreach loops (#3172). [Ehab Ibrahim]
|
* Support lower dimension looping in foreach loops (#3172). [Ehab Ibrahim]
|
||||||
* Support up to 64 bit enums for .next/.prev/.name (#3244). [Alexander Grobman]
|
* Support up to 64 bit enums for .next/.prev/.name (#3244). [Alexander Grobman]
|
||||||
|
* Reduce .rodata footpring of trace initializatoin (#3250). [Geza Lore, Shunyao CAD]
|
||||||
* Fix MSWIN compile error (#2681). [Unai Martinez-Corral]
|
* Fix MSWIN compile error (#2681). [Unai Martinez-Corral]
|
||||||
* Fix break under foreach loop (#3230).
|
* Fix break under foreach loop (#3230).
|
||||||
* Fix VL_STREAML_FAST_QQI with 64 bit left-hand-side (#3232) (#3235)
|
* Fix VL_STREAML_FAST_QQI with 64 bit left-hand-side (#3232) (#3235)
|
||||||
|
|
|
||||||
|
|
@ -2625,14 +2625,11 @@ void Verilated::debug(int level) VL_MT_SAFE {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const char* Verilated::catName(const char* n1, const char* n2, int scopet,
|
const char* Verilated::catName(const char* n1, const char* n2, const char* delimiter) VL_MT_SAFE {
|
||||||
const char* delimiter) VL_MT_SAFE {
|
|
||||||
// Returns new'ed data
|
|
||||||
// Used by symbol table creation to make module names
|
// Used by symbol table creation to make module names
|
||||||
static VL_THREAD_LOCAL char* t_strp = nullptr;
|
static VL_THREAD_LOCAL char* t_strp = nullptr;
|
||||||
static VL_THREAD_LOCAL size_t t_len = 0;
|
static VL_THREAD_LOCAL size_t t_len = 0;
|
||||||
const size_t newlen
|
const size_t newlen = std::strlen(n1) + std::strlen(n2) + std::strlen(delimiter) + 1;
|
||||||
= std::strlen(n1) + std::strlen(n2) + std::strlen(delimiter) + (scopet > 0 ? 2 : 1);
|
|
||||||
if (VL_UNLIKELY(!t_strp || newlen > t_len)) {
|
if (VL_UNLIKELY(!t_strp || newlen > t_len)) {
|
||||||
if (t_strp) delete[] t_strp;
|
if (t_strp) delete[] t_strp;
|
||||||
t_strp = new char[newlen];
|
t_strp = new char[newlen];
|
||||||
|
|
@ -2640,8 +2637,6 @@ const char* Verilated::catName(const char* n1, const char* n2, int scopet,
|
||||||
}
|
}
|
||||||
char* dp = t_strp;
|
char* dp = t_strp;
|
||||||
for (const char* sp = n1; *sp;) *dp++ = *sp++;
|
for (const char* sp = n1; *sp;) *dp++ = *sp++;
|
||||||
// Add scope type
|
|
||||||
if (scopet) *dp++ = (char)(0x80 + scopet);
|
|
||||||
for (const char* sp = delimiter; *sp;) *dp++ = *sp++;
|
for (const char* sp = delimiter; *sp;) *dp++ = *sp++;
|
||||||
for (const char* sp = n2; *sp;) *dp++ = *sp++;
|
for (const char* sp = n2; *sp;) *dp++ = *sp++;
|
||||||
*dp++ = '\0';
|
*dp++ = '\0';
|
||||||
|
|
|
||||||
|
|
@ -823,8 +823,8 @@ public:
|
||||||
public:
|
public:
|
||||||
// METHODS - INTERNAL USE ONLY (but public due to what uses it)
|
// METHODS - INTERNAL USE ONLY (but public due to what uses it)
|
||||||
// Internal: Create a new module name by concatenating two strings
|
// Internal: Create a new module name by concatenating two strings
|
||||||
static const char* catName(const char* n1, const char* n2, int scopet = 0,
|
// Returns pointer to thread-local static data (overwritten on next call)
|
||||||
const char* delimiter = "."); // Returns static data
|
static const char* catName(const char* n1, const char* n2, const char* delimiter = ".");
|
||||||
|
|
||||||
// Internal: Throw signal assertion
|
// Internal: Throw signal assertion
|
||||||
static void nullPointerError(const char* filename, int linenum) VL_ATTR_NORETURN VL_MT_SAFE;
|
static void nullPointerError(const char* filename, int linenum) VL_ATTR_NORETURN VL_MT_SAFE;
|
||||||
|
|
|
||||||
|
|
@ -163,13 +163,13 @@ void VerilatedFst::declare(vluint32_t code, const char* name, int dtypenum, fstV
|
||||||
|
|
||||||
VerilatedTrace<VerilatedFst>::declCode(code, bits, false);
|
VerilatedTrace<VerilatedFst>::declCode(code, bits, false);
|
||||||
|
|
||||||
std::istringstream nameiss{name};
|
std::string nameasstr = namePrefix() + name;
|
||||||
|
std::istringstream nameiss{nameasstr};
|
||||||
std::istream_iterator<std::string> beg(nameiss);
|
std::istream_iterator<std::string> beg(nameiss);
|
||||||
std::istream_iterator<std::string> end;
|
std::istream_iterator<std::string> end;
|
||||||
std::list<std::string> tokens(beg, end); // Split name
|
std::list<std::string> tokens(beg, end); // Split name
|
||||||
std::string symbol_name{tokens.back()};
|
std::string symbol_name{tokens.back()};
|
||||||
tokens.pop_back(); // Remove symbol name from hierarchy
|
tokens.pop_back(); // Remove symbol name from hierarchy
|
||||||
tokens.insert(tokens.begin(), moduleName()); // Add current module to the hierarchy
|
|
||||||
std::string tmpModName;
|
std::string tmpModName;
|
||||||
|
|
||||||
// Find point where current and new scope diverge
|
// Find point where current and new scope diverge
|
||||||
|
|
|
||||||
|
|
@ -150,7 +150,7 @@ private:
|
||||||
vluint32_t m_nextCode; // Next code number to assign
|
vluint32_t m_nextCode; // Next code number to assign
|
||||||
vluint32_t m_numSignals; // Number of distinct signals
|
vluint32_t m_numSignals; // Number of distinct signals
|
||||||
vluint32_t m_maxBits; // Number of bits in the widest signal
|
vluint32_t m_maxBits; // Number of bits in the widest signal
|
||||||
std::string m_moduleName; // Name of module being trace initialized now
|
std::vector<std::string> m_namePrefixStack{""}; // Path prefixes to add to signal names
|
||||||
char m_scopeEscape;
|
char m_scopeEscape;
|
||||||
double m_timeRes; // Time resolution (ns/ms etc)
|
double m_timeRes; // Time resolution (ns/ms etc)
|
||||||
double m_timeUnit; // Time units (ns/ms etc)
|
double m_timeUnit; // Time units (ns/ms etc)
|
||||||
|
|
@ -213,7 +213,6 @@ protected:
|
||||||
vluint32_t nextCode() const { return m_nextCode; }
|
vluint32_t nextCode() const { return m_nextCode; }
|
||||||
vluint32_t numSignals() const { return m_numSignals; }
|
vluint32_t numSignals() const { return m_numSignals; }
|
||||||
vluint32_t maxBits() const { return m_maxBits; }
|
vluint32_t maxBits() const { return m_maxBits; }
|
||||||
const std::string& moduleName() const { return m_moduleName; }
|
|
||||||
void fullDump(bool value) { m_fullDump = value; }
|
void fullDump(bool value) { m_fullDump = value; }
|
||||||
vluint64_t timeLastDump() { return m_timeLastDump; }
|
vluint64_t timeLastDump() { return m_timeLastDump; }
|
||||||
|
|
||||||
|
|
@ -229,6 +228,8 @@ protected:
|
||||||
bool isScopeEscape(char c) { return std::isspace(c) || c == m_scopeEscape; }
|
bool isScopeEscape(char c) { return std::isspace(c) || c == m_scopeEscape; }
|
||||||
// Character that splits scopes. Note whitespace are ALWAYS escapes.
|
// Character that splits scopes. Note whitespace are ALWAYS escapes.
|
||||||
char scopeEscape() { return m_scopeEscape; }
|
char scopeEscape() { return m_scopeEscape; }
|
||||||
|
// Prefix to assume in signal declarations
|
||||||
|
const std::string& namePrefix() const { return m_namePrefixStack.back(); }
|
||||||
|
|
||||||
void closeBase();
|
void closeBase();
|
||||||
void flushBase();
|
void flushBase();
|
||||||
|
|
@ -269,9 +270,11 @@ public:
|
||||||
void addChgCb(dumpCb_t cb, void* userp) VL_MT_SAFE;
|
void addChgCb(dumpCb_t cb, void* userp) VL_MT_SAFE;
|
||||||
void addCleanupCb(dumpCb_t cb, void* userp) VL_MT_SAFE;
|
void addCleanupCb(dumpCb_t cb, void* userp) VL_MT_SAFE;
|
||||||
|
|
||||||
void module(const std::string& name) VL_MT_UNSAFE;
|
|
||||||
void scopeEscape(char flag) { m_scopeEscape = flag; }
|
void scopeEscape(char flag) { m_scopeEscape = flag; }
|
||||||
|
|
||||||
|
void pushNamePrefix(const std::string&);
|
||||||
|
void popNamePrefix(unsigned count = 1);
|
||||||
|
|
||||||
//=========================================================================
|
//=========================================================================
|
||||||
// Hot path internal interface to Verilator generated code
|
// Hot path internal interface to Verilator generated code
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -504,9 +504,14 @@ template <> void VerilatedTrace<VL_DERIVED_T>::addCleanupCb(dumpCb_t cb, void* u
|
||||||
CallbackRecord cbr{cb, userp};
|
CallbackRecord cbr{cb, userp};
|
||||||
addCallbackRecord(m_cleanupCbs, cbr);
|
addCallbackRecord(m_cleanupCbs, cbr);
|
||||||
}
|
}
|
||||||
template <> void VerilatedTrace<VL_DERIVED_T>::module(const std::string& name) VL_MT_UNSAFE {
|
|
||||||
// Called via callbacks way above in call stack, which already hold m_mutex
|
template <> void VerilatedTrace<VL_DERIVED_T>::pushNamePrefix(const std::string& prefix) {
|
||||||
m_moduleName = name;
|
m_namePrefixStack.push_back(m_namePrefixStack.back() + prefix);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <> void VerilatedTrace<VL_DERIVED_T>::popNamePrefix(unsigned count) {
|
||||||
|
while (count--) m_namePrefixStack.pop_back();
|
||||||
|
assert(!m_namePrefixStack.empty());
|
||||||
}
|
}
|
||||||
|
|
||||||
//=========================================================================
|
//=========================================================================
|
||||||
|
|
|
||||||
|
|
@ -477,10 +477,7 @@ void VerilatedVcd::declare(vluint32_t code, const char* name, const char* wirep,
|
||||||
// Tab separates final scope from signal name
|
// Tab separates final scope from signal name
|
||||||
// Tab sorts before spaces, so signals nicely will print before scopes
|
// Tab sorts before spaces, so signals nicely will print before scopes
|
||||||
// Note the hiername may be nothing, if so we'll add "\t{name}"
|
// Note the hiername may be nothing, if so we'll add "\t{name}"
|
||||||
std::string nameasstr = name;
|
std::string nameasstr = namePrefix() + name;
|
||||||
if (!moduleName().empty()) {
|
|
||||||
nameasstr = moduleName() + scopeEscape() + nameasstr; // Optional ->module prefix
|
|
||||||
}
|
|
||||||
std::string hiername;
|
std::string hiername;
|
||||||
std::string basename;
|
std::string basename;
|
||||||
for (const char* cp = nameasstr.c_str(); *cp; cp++) {
|
for (const char* cp = nameasstr.c_str(); *cp; cp++) {
|
||||||
|
|
@ -830,16 +827,19 @@ float flo = 0.0f;
|
||||||
|
|
||||||
void vcdInit(void*, VerilatedVcd* vcdp, vluint32_t) {
|
void vcdInit(void*, VerilatedVcd* vcdp, vluint32_t) {
|
||||||
vcdp->scopeEscape('.');
|
vcdp->scopeEscape('.');
|
||||||
vcdp->module("top");
|
vcdp->pushNamePrefix("top.");
|
||||||
/**/ vcdp->declBus(0x2, "v1", -1, 0, 5, 1);
|
/**/ vcdp->declBus(0x2, "v1", -1, 0, 5, 1);
|
||||||
/**/ vcdp->declBus(0x3, "v2", -1, 0, 6, 1);
|
/**/ vcdp->declBus(0x3, "v2", -1, 0, 6, 1);
|
||||||
/**/ vcdp->module("top.sub1");
|
/**/ vcdp->pushNamePrefix("sub1.");
|
||||||
/***/ vcdp->declBit(0x4, "s1", -1, 0);
|
/***/ vcdp->declBit(0x4, "s1", -1, 0);
|
||||||
/***/ vcdp->declBit(0x5, "ch", -1, 0);
|
/***/ vcdp->declBit(0x5, "ch", -1, 0);
|
||||||
/**/ vcdp->module("top.sub2");
|
/**/ vcdp->popNamePrefix();
|
||||||
|
/**/ vcdp->pushNamePrefix("sub2.");
|
||||||
/***/ vcdp->declArray(0x6, "s2", -1, 0, 40, 3);
|
/***/ vcdp->declArray(0x6, "s2", -1, 0, 40, 3);
|
||||||
|
/**/ vcdp->popNamePrefix();
|
||||||
|
vcdp->popNamePrefix();
|
||||||
// Note need to add 3 for next code.
|
// Note need to add 3 for next code.
|
||||||
vcdp->module("top2");
|
vcdp->pushNamePrefix("top2.");
|
||||||
/**/ vcdp->declBus(0x2, "t2v1", -1, 0, 4, 1);
|
/**/ vcdp->declBus(0x2, "t2v1", -1, 0, 4, 1);
|
||||||
/**/ vcdp->declTriBit(0x10, "io1", -1, 0);
|
/**/ vcdp->declTriBit(0x10, "io1", -1, 0);
|
||||||
/**/ vcdp->declTriBus(0x12, "io5", -1, 0, 4, 0);
|
/**/ vcdp->declTriBus(0x12, "io5", -1, 0, 4, 0);
|
||||||
|
|
@ -851,6 +851,7 @@ void vcdInit(void*, VerilatedVcd* vcdp, vluint32_t) {
|
||||||
/**/ // Note need to add 4 for next code.
|
/**/ // Note need to add 4 for next code.
|
||||||
/**/ vcdp->declTriQuad(0x24, "tq", -1, 0, 63, 0);
|
/**/ vcdp->declTriQuad(0x24, "tq", -1, 0, 63, 0);
|
||||||
/**/ // Note need to add 4 for next code.
|
/**/ // Note need to add 4 for next code.
|
||||||
|
vcdp->popNamePrefix();
|
||||||
}
|
}
|
||||||
|
|
||||||
void vcdFull(void*, VerilatedVcd* vcdp) {
|
void vcdFull(void*, VerilatedVcd* vcdp) {
|
||||||
|
|
|
||||||
|
|
@ -5257,6 +5257,28 @@ public:
|
||||||
AstNode* widthp() const { return op4p(); }
|
AstNode* widthp() const { return op4p(); }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class AstTracePushNamePrefix final : public AstNodeStmt {
|
||||||
|
const string m_prefix; // Prefix to add to signal names
|
||||||
|
public:
|
||||||
|
AstTracePushNamePrefix(FileLine* fl, const string& prefix)
|
||||||
|
: ASTGEN_SUPER_TracePushNamePrefix(fl)
|
||||||
|
, m_prefix{prefix} {}
|
||||||
|
ASTNODE_NODE_FUNCS(TracePushNamePrefix)
|
||||||
|
virtual bool same(const AstNode* samep) const override { return false; }
|
||||||
|
string prefix() const { return m_prefix; }
|
||||||
|
};
|
||||||
|
|
||||||
|
class AstTracePopNamePrefix final : public AstNodeStmt {
|
||||||
|
const unsigned m_count; // How many levels to pop
|
||||||
|
public:
|
||||||
|
AstTracePopNamePrefix(FileLine* fl, unsigned count)
|
||||||
|
: ASTGEN_SUPER_TracePopNamePrefix(fl)
|
||||||
|
, m_count{count} {}
|
||||||
|
ASTNODE_NODE_FUNCS(TracePopNamePrefix)
|
||||||
|
virtual bool same(const AstNode* samep) const override { return false; }
|
||||||
|
unsigned count() const { return m_count; }
|
||||||
|
};
|
||||||
|
|
||||||
class AstTraceDecl final : public AstNodeStmt {
|
class AstTraceDecl final : public AstNodeStmt {
|
||||||
// Trace point declaration
|
// Trace point declaration
|
||||||
// Separate from AstTraceInc; as a declaration can't be deleted
|
// Separate from AstTraceInc; as a declaration can't be deleted
|
||||||
|
|
@ -5271,12 +5293,10 @@ private:
|
||||||
const AstVarType m_varType; // Type of variable (for localparam vs. param)
|
const AstVarType m_varType; // Type of variable (for localparam vs. param)
|
||||||
const AstBasicDTypeKwd m_declKwd; // Keyword at declaration time
|
const AstBasicDTypeKwd m_declKwd; // Keyword at declaration time
|
||||||
const VDirection m_declDirection; // Declared direction input/output etc
|
const VDirection m_declDirection; // Declared direction input/output etc
|
||||||
const bool m_isScoped; // Uses run-time scope (for interfaces)
|
|
||||||
public:
|
public:
|
||||||
AstTraceDecl(FileLine* fl, const string& showname,
|
AstTraceDecl(FileLine* fl, const string& showname,
|
||||||
AstVar* varp, // For input/output state etc
|
AstVar* varp, // For input/output state etc
|
||||||
AstNode* valuep, const VNumRange& bitRange, const VNumRange& arrayRange,
|
AstNode* valuep, const VNumRange& bitRange, const VNumRange& arrayRange)
|
||||||
bool isScoped)
|
|
||||||
: ASTGEN_SUPER_TraceDecl(fl)
|
: ASTGEN_SUPER_TraceDecl(fl)
|
||||||
, m_showname{showname}
|
, m_showname{showname}
|
||||||
, m_bitRange{bitRange}
|
, m_bitRange{bitRange}
|
||||||
|
|
@ -5286,8 +5306,7 @@ public:
|
||||||
* (VL_EDATASIZE / 32))) // A code is always 32-bits
|
* (VL_EDATASIZE / 32))) // A code is always 32-bits
|
||||||
, m_varType{varp->varType()}
|
, m_varType{varp->varType()}
|
||||||
, m_declKwd{varp->declKwd()}
|
, m_declKwd{varp->declKwd()}
|
||||||
, m_declDirection{varp->declDirection()}
|
, m_declDirection{varp->declDirection()} {
|
||||||
, m_isScoped{isScoped} {
|
|
||||||
dtypeFrom(valuep);
|
dtypeFrom(valuep);
|
||||||
addNOp1p(valuep);
|
addNOp1p(valuep);
|
||||||
}
|
}
|
||||||
|
|
@ -5307,7 +5326,6 @@ public:
|
||||||
AstVarType varType() const { return m_varType; }
|
AstVarType varType() const { return m_varType; }
|
||||||
AstBasicDTypeKwd declKwd() const { return m_declKwd; }
|
AstBasicDTypeKwd declKwd() const { return m_declKwd; }
|
||||||
VDirection declDirection() const { return m_declDirection; }
|
VDirection declDirection() const { return m_declDirection; }
|
||||||
bool isScoped() const { return m_isScoped; }
|
|
||||||
AstNode* valuep() const { return op1p(); }
|
AstNode* valuep() const { return op1p(); }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -441,9 +441,6 @@ public:
|
||||||
iterateAndNextNull(nodep->exprp());
|
iterateAndNextNull(nodep->exprp());
|
||||||
puts("; }\n");
|
puts("; }\n");
|
||||||
}
|
}
|
||||||
virtual void visit(AstIntfRef* nodep) override {
|
|
||||||
putsQuoted(VIdProtect::protectWordsIf(AstNode::vcdName(nodep->name()), nodep->protect()));
|
|
||||||
}
|
|
||||||
virtual void visit(AstNodeCase* nodep) override { // LCOV_EXCL_LINE
|
virtual void visit(AstNodeCase* nodep) override { // LCOV_EXCL_LINE
|
||||||
// In V3Case...
|
// In V3Case...
|
||||||
nodep->v3fatalSrc("Case statements should have been reduced out");
|
nodep->v3fatalSrc("Case statements should have been reduced out");
|
||||||
|
|
|
||||||
|
|
@ -631,9 +631,7 @@ class EmitCTrace final : EmitCFunc {
|
||||||
puts("(c+" + cvtToStr(nodep->code()));
|
puts("(c+" + cvtToStr(nodep->code()));
|
||||||
if (nodep->arrayRange().ranged()) puts("+i*" + cvtToStr(nodep->widthWords()));
|
if (nodep->arrayRange().ranged()) puts("+i*" + cvtToStr(nodep->widthWords()));
|
||||||
puts(",");
|
puts(",");
|
||||||
if (nodep->isScoped()) puts("Verilated::catName(scopep,");
|
|
||||||
putsQuoted(VIdProtect::protectWordsIf(nodep->showname(), nodep->protect()));
|
putsQuoted(VIdProtect::protectWordsIf(nodep->showname(), nodep->protect()));
|
||||||
if (nodep->isScoped()) puts(",(int)scopet,\" \")");
|
|
||||||
// Direction
|
// Direction
|
||||||
if (v3Global.opt.traceFormat().fst()) {
|
if (v3Global.opt.traceFormat().fst()) {
|
||||||
puts("," + cvtToStr(enumNum));
|
puts("," + cvtToStr(enumNum));
|
||||||
|
|
@ -836,12 +834,22 @@ class EmitCTrace final : EmitCFunc {
|
||||||
|
|
||||||
EmitCFunc::visit(nodep);
|
EmitCFunc::visit(nodep);
|
||||||
}
|
}
|
||||||
|
virtual void visit(AstTracePushNamePrefix* nodep) override {
|
||||||
|
puts("tracep->pushNamePrefix(");
|
||||||
|
putsQuoted(VIdProtect::protectWordsIf(nodep->prefix(), nodep->protect()));
|
||||||
|
puts(");\n");
|
||||||
|
}
|
||||||
|
virtual void visit(AstTracePopNamePrefix* nodep) override { //
|
||||||
|
puts("tracep->popNamePrefix(");
|
||||||
|
puts(cvtToStr(nodep->count()));
|
||||||
|
puts(");\n");
|
||||||
|
}
|
||||||
virtual void visit(AstTraceDecl* nodep) override {
|
virtual void visit(AstTraceDecl* nodep) override {
|
||||||
const int enumNum = emitTraceDeclDType(nodep->dtypep());
|
const int enumNum = emitTraceDeclDType(nodep->dtypep());
|
||||||
if (nodep->arrayRange().ranged()) {
|
if (nodep->arrayRange().ranged()) {
|
||||||
puts("{int i; for (i=0; i<" + cvtToStr(nodep->arrayRange().elements()) + "; i++) {\n");
|
puts("for (int i = 0; i < " + cvtToStr(nodep->arrayRange().elements()) + "; ++i) {\n");
|
||||||
emitTraceInitOne(nodep, enumNum);
|
emitTraceInitOne(nodep, enumNum);
|
||||||
puts("}}\n");
|
puts("\n}\n");
|
||||||
} else {
|
} else {
|
||||||
emitTraceInitOne(nodep, enumNum);
|
emitTraceInitOne(nodep, enumNum);
|
||||||
puts("\n");
|
puts("\n");
|
||||||
|
|
|
||||||
|
|
@ -563,9 +563,10 @@ class EmitCModel final : public EmitCFunc {
|
||||||
"0.\");\n");
|
"0.\");\n");
|
||||||
puts("}\n");
|
puts("}\n");
|
||||||
puts("vlSymsp->__Vm_baseCode = code;\n");
|
puts("vlSymsp->__Vm_baseCode = code;\n");
|
||||||
puts("tracep->module(vlSymsp->name());\n");
|
|
||||||
puts("tracep->scopeEscape(' ');\n");
|
puts("tracep->scopeEscape(' ');\n");
|
||||||
|
puts("tracep->pushNamePrefix(std::string{vlSymsp->name()} + ' ');\n");
|
||||||
puts(topModNameProtected + "__" + protect("trace_init_top") + "(vlSelf, tracep);\n");
|
puts(topModNameProtected + "__" + protect("trace_init_top") + "(vlSelf, tracep);\n");
|
||||||
|
puts("tracep->popNamePrefix();\n");
|
||||||
puts("tracep->scopeEscape('.');\n"); // Restore so later traced files won't break
|
puts("tracep->scopeEscape('.');\n"); // Restore so later traced files won't break
|
||||||
puts("}\n");
|
puts("}\n");
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -29,6 +29,62 @@
|
||||||
#include "V3EmitCBase.h"
|
#include "V3EmitCBase.h"
|
||||||
#include "V3Stats.h"
|
#include "V3Stats.h"
|
||||||
|
|
||||||
|
#include <algorithm>
|
||||||
|
#include <functional>
|
||||||
|
#include <limits>
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
|
//######################################################################
|
||||||
|
// Utility class to emit path adjustments
|
||||||
|
|
||||||
|
class PathAdjustor final {
|
||||||
|
FileLine* const m_flp; // FileLine used for created nodes
|
||||||
|
std::function<void(AstNodeStmt*)> m_emit; // Function called with adjustment statements
|
||||||
|
std::vector<std::string> m_stack{""}; // Stack of current paths
|
||||||
|
|
||||||
|
static constexpr char SEPARATOR = ' ';
|
||||||
|
|
||||||
|
public:
|
||||||
|
explicit PathAdjustor(FileLine* flp, std::function<void(AstNodeStmt*)> emit)
|
||||||
|
: m_flp{flp}
|
||||||
|
, m_emit{emit} {}
|
||||||
|
|
||||||
|
// Emit Prefix adjustments until the current path is 'newPath'
|
||||||
|
void adjust(const string& newPath) {
|
||||||
|
// Move up to enclosing path
|
||||||
|
unsigned toPop = 0;
|
||||||
|
while (!VString::startsWith(newPath, m_stack.back())) {
|
||||||
|
++toPop;
|
||||||
|
m_stack.pop_back();
|
||||||
|
}
|
||||||
|
if (toPop) m_emit(new AstTracePopNamePrefix{m_flp, toPop});
|
||||||
|
// Move down, one path element at a time
|
||||||
|
if (newPath != m_stack.back()) {
|
||||||
|
const string& extraPrefix = newPath.substr(m_stack.back().size());
|
||||||
|
size_t begin = 0;
|
||||||
|
while (true) {
|
||||||
|
const size_t end = extraPrefix.find(SEPARATOR, begin);
|
||||||
|
if (end == string::npos) break;
|
||||||
|
const string& extra = extraPrefix.substr(begin, end + 1 - begin);
|
||||||
|
m_emit(new AstTracePushNamePrefix{m_flp, extra});
|
||||||
|
m_stack.push_back(m_stack.back() + extra);
|
||||||
|
begin = end + 1;
|
||||||
|
}
|
||||||
|
const string& extra = extraPrefix.substr(begin);
|
||||||
|
if (!extra.empty()) {
|
||||||
|
m_emit(new AstTracePushNamePrefix{m_flp, extra + SEPARATOR});
|
||||||
|
m_stack.push_back(m_stack.back() + extra);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Emit Prefix adjustments to unwind the path back to its original state
|
||||||
|
void unwind() {
|
||||||
|
const unsigned toPop = m_stack.size() - 1;
|
||||||
|
if (toPop) m_emit(new AstTracePopNamePrefix{m_flp, toPop});
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
//######################################################################
|
//######################################################################
|
||||||
// TraceDecl state, as a visitor of each AstNode
|
// TraceDecl state, as a visitor of each AstNode
|
||||||
|
|
||||||
|
|
@ -37,15 +93,38 @@ private:
|
||||||
// NODE STATE
|
// NODE STATE
|
||||||
|
|
||||||
// STATE
|
// STATE
|
||||||
AstScope* const m_topScopep = v3Global.rootp()->topScopep()->scopep(); // The top AstScope
|
AstTopScope* const m_topScopep; // The singleton AstTopScope
|
||||||
AstCFunc* m_initFuncp = nullptr; // Trace function being built
|
const AstScope* m_currScopep = nullptr; // Current scope being visited
|
||||||
AstCFunc* m_initSubFuncp = nullptr; // Trace function being built (under m_init)
|
|
||||||
int m_initSubStmts = 0; // Number of statements in function
|
std::vector<AstCFunc*> m_topFuncps; // Top level trace initialization functions
|
||||||
int m_funcNum = 0; // Function number being built
|
std::vector<AstCFunc*> m_subFuncps; // Trace sub functions for this scope
|
||||||
const AstVarScope* m_traVscp = nullptr; // Signal being trace constructed
|
int m_topFuncSize = 0; // Size of the top function currently being built
|
||||||
AstNode* m_traValuep = nullptr; // Signal being traced's value to trace in it
|
int m_subFuncSize = 0; // Size of the sub function currently being built
|
||||||
string m_traShowname; // Signal being traced's component name
|
const int m_funcSizeLimit // Maximum size of a function
|
||||||
bool m_interface = false; // Currently tracing an interface
|
= v3Global.opt.outputSplitCTrace() ? v3Global.opt.outputSplitCTrace()
|
||||||
|
: std::numeric_limits<int>::max();
|
||||||
|
// Trace init sub functions to invoke for path names in the hierarchy. Note path names and
|
||||||
|
// AstScope instances are not one to one due to the presence of AstIntfRef.
|
||||||
|
std::map<std::string, std::vector<AstCFunc*>> m_scopeSubFuncps;
|
||||||
|
|
||||||
|
struct Signal final {
|
||||||
|
AstVarScope* m_vscp; // AstVarScope being traced (non const to allow copy during sorting)
|
||||||
|
std::string m_path; // Path to enclosing module in hierarchy
|
||||||
|
std::string m_name; // Name of signal
|
||||||
|
Signal(AstVarScope* vscp)
|
||||||
|
: m_vscp{vscp} {
|
||||||
|
// Compute path in hierarchy and signal name
|
||||||
|
const string& vcdName = AstNode::vcdName(vscp->varp()->name());
|
||||||
|
const size_t pos = vcdName.rfind(' ');
|
||||||
|
const size_t pathLen = pos == string::npos ? 0 : pos + 1;
|
||||||
|
m_path = vcdName.substr(0, pathLen);
|
||||||
|
m_name = vcdName.substr(pathLen);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
std::vector<Signal> m_signals; // Signals under current scope
|
||||||
|
AstVarScope* m_traVscp = nullptr; // Current AstVarScope we are constructing AstTraceDecls for
|
||||||
|
AstNode* m_traValuep = nullptr; // Value expression for current signal
|
||||||
|
string m_traName; // Name component for current signal
|
||||||
|
|
||||||
VDouble0 m_statSigs; // Statistic tracking
|
VDouble0 m_statSigs; // Statistic tracking
|
||||||
VDouble0 m_statIgnSigs; // Statistic tracking
|
VDouble0 m_statIgnSigs; // Statistic tracking
|
||||||
|
|
@ -69,38 +148,44 @@ private:
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
AstCFunc* newCFunc(const string& name) {
|
AstCFunc* newCFunc(FileLine* flp, const string& name) {
|
||||||
FileLine* const flp = m_topScopep->fileline();
|
AstScope* const topScopep = m_topScopep->scopep();
|
||||||
AstCFunc* const funcp = new AstCFunc(flp, name, m_topScopep);
|
AstCFunc* const funcp = new AstCFunc{flp, name, topScopep};
|
||||||
string argTypes = v3Global.opt.traceClassBase() + "* tracep";
|
funcp->argTypes(v3Global.opt.traceClassBase() + "* tracep");
|
||||||
if (m_interface) argTypes += ", int scopet, const char* scopep";
|
|
||||||
funcp->argTypes(argTypes);
|
|
||||||
funcp->isTrace(true);
|
funcp->isTrace(true);
|
||||||
funcp->isStatic(false);
|
funcp->isStatic(false);
|
||||||
funcp->isLoose(true);
|
funcp->isLoose(true);
|
||||||
funcp->slow(true);
|
funcp->slow(true);
|
||||||
m_topScopep->addActivep(funcp);
|
topScopep->addActivep(funcp);
|
||||||
UINFO(5, " Newfunc " << funcp << endl);
|
|
||||||
return funcp;
|
return funcp;
|
||||||
}
|
}
|
||||||
void callCFuncSub(AstCFunc* basep, AstCFunc* funcp, AstIntfRef* irp) {
|
|
||||||
AstCCall* const callp = new AstCCall(funcp->fileline(), funcp);
|
void addToTopFunc(AstNodeStmt* stmtp) {
|
||||||
if (irp) {
|
if (m_topFuncSize > m_funcSizeLimit || m_topFuncps.empty()) {
|
||||||
callp->argTypes("tracep, VLT_TRACE_SCOPE_INTERFACE");
|
m_topFuncSize = 0;
|
||||||
callp->addArgsp(irp->unlinkFrBack());
|
//
|
||||||
} else {
|
const string n = cvtToStr(m_topFuncps.size());
|
||||||
callp->argTypes("tracep");
|
const string name{"trace_init_top__" + n};
|
||||||
|
AstCFunc* const funcp = newCFunc(m_topScopep->fileline(), name);
|
||||||
|
m_topFuncps.push_back(funcp);
|
||||||
}
|
}
|
||||||
basep->addStmtsp(callp);
|
m_topFuncps.back()->addStmtsp(stmtp);
|
||||||
|
m_topFuncSize += EmitCBaseCounterVisitor{stmtp}.count();
|
||||||
}
|
}
|
||||||
AstCFunc* newCFuncSub(AstCFunc* basep) {
|
|
||||||
FileLine* const fl = basep->fileline();
|
void addToSubFunc(AstNodeStmt* stmtp) {
|
||||||
const string name = "trace_init_sub_" + cvtToStr(m_funcNum++);
|
if (m_subFuncSize > m_funcSizeLimit || m_subFuncps.empty()) {
|
||||||
AstCFunc* const funcp = newCFunc(name);
|
m_subFuncSize = 0;
|
||||||
funcp->addInitsp(new AstCStmt(fl, "const int c = vlSymsp->__Vm_baseCode;\n"));
|
//
|
||||||
funcp->addInitsp(new AstCStmt(fl, "if (false && tracep && c) {} // Prevent unused\n"));
|
FileLine* const flp = m_currScopep->fileline();
|
||||||
if (!m_interface) callCFuncSub(basep, funcp, nullptr);
|
const string n = cvtToStr(m_subFuncps.size());
|
||||||
return funcp;
|
const string name{"trace_init_sub__" + m_currScopep->nameDotless() + "__" + n};
|
||||||
|
AstCFunc* const funcp = newCFunc(flp, name);
|
||||||
|
funcp->addInitsp(new AstCStmt{flp, "const int c = vlSymsp->__Vm_baseCode;\n"});
|
||||||
|
m_subFuncps.push_back(funcp);
|
||||||
|
}
|
||||||
|
m_subFuncps.back()->addStmtsp(stmtp);
|
||||||
|
m_subFuncSize += EmitCBaseCounterVisitor{stmtp}.count();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string getScopeChar(VltTraceScope sct) { return std::string(1, (char)(0x80 + sct)); }
|
std::string getScopeChar(VltTraceScope sct) { return std::string(1, (char)(0x80 + sct)); }
|
||||||
|
|
@ -114,114 +199,124 @@ private:
|
||||||
} else if (const AstBasicDType* const bdtypep = m_traValuep->dtypep()->basicp()) {
|
} else if (const AstBasicDType* const bdtypep = m_traValuep->dtypep()->basicp()) {
|
||||||
bitRange = bdtypep->nrange();
|
bitRange = bdtypep->nrange();
|
||||||
}
|
}
|
||||||
AstTraceDecl* const declp
|
addToSubFunc(new AstTraceDecl{m_traVscp->fileline(), m_traName, m_traVscp->varp(),
|
||||||
= new AstTraceDecl(m_traVscp->fileline(), m_traShowname, m_traVscp->varp(),
|
m_traValuep->cloneTree(false), bitRange, arrayRange});
|
||||||
m_traValuep->cloneTree(true), bitRange, arrayRange, m_interface);
|
|
||||||
UINFO(9, "Decl " << declp << endl);
|
|
||||||
|
|
||||||
if (!m_interface && v3Global.opt.outputSplitCTrace()
|
|
||||||
&& m_initSubStmts > v3Global.opt.outputSplitCTrace()) {
|
|
||||||
m_initSubFuncp = newCFuncSub(m_initFuncp);
|
|
||||||
m_initSubStmts = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
m_initSubFuncp->addStmtsp(declp);
|
|
||||||
m_initSubStmts += EmitCBaseCounterVisitor(declp).count();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void addIgnore(const char* why) {
|
void addIgnore(const char* why) {
|
||||||
++m_statIgnSigs;
|
++m_statIgnSigs;
|
||||||
m_initSubFuncp->addStmtsp(new AstComment(
|
addToSubFunc(new AstComment{m_traVscp->fileline(),
|
||||||
m_traVscp->fileline(), "Tracing: " + m_traShowname + " // Ignored: " + why, true));
|
"Tracing: " + m_traName + " // Ignored: " + why, true});
|
||||||
}
|
}
|
||||||
|
|
||||||
// VISITORS
|
// VISITORS
|
||||||
virtual void visit(AstTopScope* nodep) override {
|
|
||||||
// Create the trace init function
|
|
||||||
m_initFuncp = newCFunc("trace_init_top");
|
|
||||||
// Create initial sub function
|
|
||||||
m_initSubFuncp = newCFuncSub(m_initFuncp);
|
|
||||||
// And find variables
|
|
||||||
iterateChildren(nodep);
|
|
||||||
}
|
|
||||||
virtual void visit(AstScope* nodep) override {
|
virtual void visit(AstScope* nodep) override {
|
||||||
const AstCell* const cellp = nodep->aboveCellp();
|
UASSERT_OBJ(!m_currScopep, nodep, "Should not nest");
|
||||||
if (cellp && VN_IS(cellp->modp(), Iface)) {
|
UASSERT_OBJ(m_subFuncps.empty(), nodep, "Should not nest");
|
||||||
AstCFunc* const origSubFunc = m_initSubFuncp;
|
UASSERT_OBJ(m_signals.empty(), nodep, "Should not nest");
|
||||||
int origSubStmts = m_initSubStmts;
|
UASSERT_OBJ(!m_traVscp, nodep, "Should not nest");
|
||||||
{
|
UASSERT_OBJ(m_traName.empty(), nodep, "Should not nest");
|
||||||
m_interface = true;
|
|
||||||
m_initSubFuncp = newCFuncSub(origSubFunc);
|
|
||||||
string scopeName = nodep->prettyName();
|
|
||||||
const size_t lastDot = scopeName.find_last_of('.');
|
|
||||||
UASSERT_OBJ(lastDot != string::npos, nodep,
|
|
||||||
"Expected an interface scope name to have at least one dot");
|
|
||||||
scopeName = scopeName.substr(0, lastDot + 1);
|
|
||||||
const size_t scopeLen = scopeName.length();
|
|
||||||
|
|
||||||
AstIntfRef* nextIrp = cellp->intfRefp();
|
FileLine* const flp = nodep->fileline();
|
||||||
// While instead of for loop because interface references will
|
m_currScopep = nodep;
|
||||||
// be unlinked as we go
|
|
||||||
while (nextIrp) {
|
|
||||||
AstIntfRef* const irp = nextIrp;
|
|
||||||
nextIrp = VN_AS(irp->nextp(), IntfRef);
|
|
||||||
|
|
||||||
const string irpName = irp->prettyName();
|
// Gather all signals under this AstScope
|
||||||
if (scopeLen > irpName.length()) continue;
|
iterateChildrenConst(nodep);
|
||||||
const string intfScopeName = irpName.substr(0, scopeLen);
|
|
||||||
if (scopeName != intfScopeName) continue;
|
// If nothing to trace in this scope, then job done
|
||||||
callCFuncSub(origSubFunc, m_initSubFuncp, irp);
|
if (m_signals.empty()) {
|
||||||
++origSubStmts;
|
m_currScopep = nullptr;
|
||||||
}
|
return;
|
||||||
iterateChildren(nodep);
|
|
||||||
}
|
|
||||||
m_initSubFuncp = origSubFunc;
|
|
||||||
m_initSubStmts = origSubStmts;
|
|
||||||
m_interface = false;
|
|
||||||
} else {
|
|
||||||
iterateChildren(nodep);
|
|
||||||
}
|
}
|
||||||
}
|
|
||||||
virtual void visit(AstVarScope* nodep) override {
|
|
||||||
iterateChildren(nodep);
|
|
||||||
// Prefilter - things that get through this if will either get
|
|
||||||
// traced or get a comment as to why not traced.
|
|
||||||
// Generally this equation doesn't need updating, instead use
|
|
||||||
// varp->isTrace() and/or vscIgnoreTrace.
|
|
||||||
if ((!nodep->varp()->isTemp() || nodep->varp()->isTrace())
|
|
||||||
&& !nodep->varp()->isClassMember() && !nodep->varp()->isFuncLocal()) {
|
|
||||||
UINFO(5, " vsc " << nodep << endl);
|
|
||||||
const AstVar* const varp = nodep->varp();
|
|
||||||
const AstScope* const scopep = nodep->scopep();
|
|
||||||
// Compute show name
|
|
||||||
// This code assumes SPTRACEVCDC_VERSION >= 1330;
|
|
||||||
// it uses spaces to separate hierarchy components.
|
|
||||||
if (m_interface) {
|
|
||||||
m_traShowname = AstNode::vcdName(varp->name());
|
|
||||||
} else {
|
|
||||||
m_traShowname = AstNode::vcdName(scopep->name() + " " + varp->name());
|
|
||||||
if (m_traShowname.substr(0, 4) == "TOP ") m_traShowname.erase(0, 4);
|
|
||||||
}
|
|
||||||
UASSERT_OBJ(m_initSubFuncp, nodep, "nullptr");
|
|
||||||
|
|
||||||
m_traVscp = nodep;
|
// Sort signals, first by enclosing instance, then by source location, then by name
|
||||||
if (const char* const ignoreReasonp = vscIgnoreTrace(nodep)) {
|
std::stable_sort(m_signals.begin(), m_signals.end(), [](const Signal& a, const Signal& b) {
|
||||||
|
if (const int cmp = a.m_path.compare(b.m_path)) return cmp < 0;
|
||||||
|
const FileLine* const aflp = a.m_vscp->fileline();
|
||||||
|
const FileLine* const bflp = b.m_vscp->fileline();
|
||||||
|
if (const int cmp = aflp->operatorCompare(*bflp)) return cmp < 0;
|
||||||
|
return a.m_name < b.m_name;
|
||||||
|
});
|
||||||
|
|
||||||
|
// Build trace initialization functions for this AstScope
|
||||||
|
PathAdjustor pathAdjustor{flp, [&](AstNodeStmt* stmtp) { addToSubFunc(stmtp); }};
|
||||||
|
for (const Signal& signal : m_signals) {
|
||||||
|
// Adjust name prefix based on path in hierarchy
|
||||||
|
pathAdjustor.adjust(signal.m_path);
|
||||||
|
|
||||||
|
// Build AstTraceDecl for this signal
|
||||||
|
m_traVscp = signal.m_vscp;
|
||||||
|
m_traName = signal.m_name;
|
||||||
|
if (const char* const ignoreReasonp = vscIgnoreTrace(m_traVscp)) {
|
||||||
addIgnore(ignoreReasonp);
|
addIgnore(ignoreReasonp);
|
||||||
} else {
|
} else {
|
||||||
++m_statSigs;
|
++m_statSigs;
|
||||||
if (nodep->valuep()) {
|
if (AstNode* const valuep = m_traVscp->valuep()) {
|
||||||
m_traValuep = nodep->valuep()->cloneTree(true);
|
m_traValuep = valuep->cloneTree(false);
|
||||||
} else {
|
} else {
|
||||||
m_traValuep = new AstVarRef(nodep->fileline(), nodep, VAccess::READ);
|
m_traValuep = new AstVarRef{m_traVscp->fileline(), m_traVscp, VAccess::READ};
|
||||||
}
|
}
|
||||||
// Recurse into data type of the signal; the visitors will call addTraceDecl()
|
// Recurse into data type of the signal. The visit methods will add AstTraceDecls.
|
||||||
iterate(varp->dtypep()->skipRefToEnump());
|
iterate(m_traVscp->varp()->dtypep()->skipRefToEnump());
|
||||||
// Cleanup
|
// Cleanup
|
||||||
if (m_traValuep) VL_DO_CLEAR(m_traValuep->deleteTree(), m_traValuep = nullptr);
|
if (m_traValuep) VL_DO_DANGLING(m_traValuep->deleteTree(), m_traValuep);
|
||||||
}
|
}
|
||||||
m_traVscp = nullptr;
|
|
||||||
m_traShowname = "";
|
|
||||||
}
|
}
|
||||||
|
pathAdjustor.unwind();
|
||||||
|
m_traVscp = nullptr;
|
||||||
|
m_traName.clear();
|
||||||
|
UASSERT_OBJ(!m_traValuep, nodep, "Should have been deleted");
|
||||||
|
m_signals.clear();
|
||||||
|
|
||||||
|
// Add sub functions to m_scopeSubFuncps
|
||||||
|
const AstCell* const cellp = nodep->aboveCellp();
|
||||||
|
if (cellp && VN_IS(cellp->modp(), Iface)) {
|
||||||
|
string scopeName = nodep->prettyName();
|
||||||
|
const size_t lastDot = scopeName.find_last_of('.');
|
||||||
|
UASSERT_OBJ(lastDot != string::npos, nodep,
|
||||||
|
"Expected an interface scope name to have at least one dot");
|
||||||
|
scopeName = scopeName.substr(0, lastDot + 1);
|
||||||
|
const size_t scopeLen = scopeName.length();
|
||||||
|
|
||||||
|
for (AstIntfRef *irp = cellp->intfRefp(), *nextIrp; irp; irp = nextIrp) {
|
||||||
|
nextIrp = VN_AS(irp->nextp(), IntfRef);
|
||||||
|
|
||||||
|
const string irpName = irp->prettyName();
|
||||||
|
if (scopeLen > irpName.length()) continue;
|
||||||
|
const string intfScopeName = irpName.substr(0, scopeLen);
|
||||||
|
if (scopeName != intfScopeName) continue;
|
||||||
|
|
||||||
|
string scopeName = AstNode::vcdName(irp->name());
|
||||||
|
if (scopeName.substr(0, 4) == "TOP ") scopeName.erase(0, 4);
|
||||||
|
scopeName += getScopeChar(VLT_TRACE_SCOPE_INTERFACE) + ' ';
|
||||||
|
m_scopeSubFuncps.emplace(scopeName, m_subFuncps);
|
||||||
|
|
||||||
|
VL_DO_DANGLING(irp->unlinkFrBack(), irp);
|
||||||
|
}
|
||||||
|
|
||||||
|
m_subFuncps.clear();
|
||||||
|
} else {
|
||||||
|
string scopeName = AstNode::vcdName(nodep->name()) + ' ';
|
||||||
|
if (VString::startsWith(scopeName, "TOP ")) scopeName.erase(0, 4);
|
||||||
|
m_scopeSubFuncps.emplace(scopeName, std::move(m_subFuncps));
|
||||||
|
}
|
||||||
|
|
||||||
|
m_currScopep = nullptr;
|
||||||
}
|
}
|
||||||
|
virtual void visit(AstVarScope* nodep) override {
|
||||||
|
UASSERT_OBJ(m_currScopep, nodep, "AstVarScope not under AstScope");
|
||||||
|
|
||||||
|
// Prefilter - things that get added to m_vscps will either get traced or get a comment as
|
||||||
|
// to why they are not traced. Generally these conditions doesn't need updating, instead
|
||||||
|
// use varp->isTrace() and/or vscIgnoreTrace.
|
||||||
|
if (nodep->varp()->isTemp() && !nodep->varp()->isTrace()) return;
|
||||||
|
if (nodep->varp()->isClassMember()) return;
|
||||||
|
if (nodep->varp()->isFuncLocal()) return;
|
||||||
|
|
||||||
|
// Add to traced signal list
|
||||||
|
m_signals.emplace_back(nodep);
|
||||||
|
}
|
||||||
|
|
||||||
// VISITORS - Data types when tracing
|
// VISITORS - Data types when tracing
|
||||||
virtual void visit(AstConstDType* nodep) override {
|
virtual void visit(AstConstDType* nodep) override {
|
||||||
if (m_traVscp) iterate(nodep->subDTypep()->skipRefToEnump());
|
if (m_traVscp) iterate(nodep->subDTypep()->skipRefToEnump());
|
||||||
|
|
@ -247,20 +342,20 @@ private:
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// Unroll now, as have no other method to get right signal names
|
// Unroll now, as have no other method to get right signal names
|
||||||
|
FileLine* const flp = nodep->fileline();
|
||||||
AstNodeDType* const subtypep = nodep->subDTypep()->skipRefToEnump();
|
AstNodeDType* const subtypep = nodep->subDTypep()->skipRefToEnump();
|
||||||
|
VL_RESTORER(m_traName);
|
||||||
|
addToSubFunc(new AstTracePushNamePrefix{flp, m_traName});
|
||||||
for (int i = nodep->lo(); i <= nodep->hi(); ++i) {
|
for (int i = nodep->lo(); i <= nodep->hi(); ++i) {
|
||||||
VL_RESTORER(m_traShowname);
|
|
||||||
VL_RESTORER(m_traValuep);
|
VL_RESTORER(m_traValuep);
|
||||||
{
|
m_traName = string{"["} + cvtToStr(i) + string{"]"};
|
||||||
m_traShowname += string("[") + cvtToStr(i) + string("]");
|
m_traValuep = m_traValuep->cloneTree(false);
|
||||||
m_traValuep = new AstArraySel(
|
m_traValuep = new AstArraySel{flp, m_traValuep, i - nodep->lo()};
|
||||||
nodep->fileline(), m_traValuep->cloneTree(true), i - nodep->lo());
|
m_traValuep->dtypep(subtypep);
|
||||||
|
iterate(subtypep);
|
||||||
m_traValuep->dtypep(subtypep);
|
VL_DO_CLEAR(m_traValuep->deleteTree(), m_traValuep = nullptr);
|
||||||
iterate(subtypep);
|
|
||||||
VL_DO_CLEAR(m_traValuep->deleteTree(), m_traValuep = nullptr);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
addToSubFunc(new AstTracePopNamePrefix{flp, 1});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -272,20 +367,21 @@ private:
|
||||||
// a much faster way to trace
|
// a much faster way to trace
|
||||||
addTraceDecl(VNumRange(), nodep->width());
|
addTraceDecl(VNumRange(), nodep->width());
|
||||||
} else {
|
} else {
|
||||||
|
FileLine* const flp = nodep->fileline();
|
||||||
AstNodeDType* const subtypep = nodep->subDTypep()->skipRefToEnump();
|
AstNodeDType* const subtypep = nodep->subDTypep()->skipRefToEnump();
|
||||||
|
VL_RESTORER(m_traName);
|
||||||
|
addToSubFunc(new AstTracePushNamePrefix{flp, m_traName});
|
||||||
for (int i = nodep->lo(); i <= nodep->hi(); ++i) {
|
for (int i = nodep->lo(); i <= nodep->hi(); ++i) {
|
||||||
VL_RESTORER(m_traShowname);
|
|
||||||
VL_RESTORER(m_traValuep);
|
VL_RESTORER(m_traValuep);
|
||||||
{
|
m_traName = string{"["} + cvtToStr(i) + string{"]"};
|
||||||
m_traShowname += string("[") + cvtToStr(i) + string("]");
|
const int lsb = (i - nodep->lo()) * subtypep->width();
|
||||||
m_traValuep
|
m_traValuep = m_traValuep->cloneTree(false);
|
||||||
= new AstSel(nodep->fileline(), m_traValuep->cloneTree(true),
|
m_traValuep = new AstSel{flp, m_traValuep, lsb, subtypep->width()};
|
||||||
(i - nodep->lo()) * subtypep->width(), subtypep->width());
|
m_traValuep->dtypep(subtypep);
|
||||||
m_traValuep->dtypep(subtypep);
|
iterate(subtypep);
|
||||||
iterate(subtypep);
|
VL_DO_CLEAR(m_traValuep->deleteTree(), m_traValuep = nullptr);
|
||||||
VL_DO_CLEAR(m_traValuep->deleteTree(), m_traValuep = nullptr);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
addToSubFunc(new AstTracePopNamePrefix{flp, 1});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -299,31 +395,30 @@ private:
|
||||||
} else if (!nodep->packed()) {
|
} else if (!nodep->packed()) {
|
||||||
addIgnore("Unsupported: Unpacked struct/union");
|
addIgnore("Unsupported: Unpacked struct/union");
|
||||||
} else {
|
} else {
|
||||||
|
FileLine* const flp = nodep->fileline();
|
||||||
|
const bool isStruct = VN_IS(nodep, StructDType); // Otherwise union
|
||||||
|
VL_RESTORER(m_traName);
|
||||||
|
string prefix{m_traName};
|
||||||
|
prefix += isStruct ? getScopeChar(VLT_TRACE_SCOPE_STRUCT) // Mark scope type
|
||||||
|
: getScopeChar(VLT_TRACE_SCOPE_UNION);
|
||||||
|
addToSubFunc(new AstTracePushNamePrefix{flp, prefix + ' '});
|
||||||
for (const AstMemberDType* itemp = nodep->membersp(); itemp;
|
for (const AstMemberDType* itemp = nodep->membersp(); itemp;
|
||||||
itemp = VN_AS(itemp->nextp(), MemberDType)) {
|
itemp = VN_AS(itemp->nextp(), MemberDType)) {
|
||||||
AstNodeDType* const subtypep = itemp->subDTypep()->skipRefToEnump();
|
AstNodeDType* const subtypep = itemp->subDTypep()->skipRefToEnump();
|
||||||
VL_RESTORER(m_traShowname);
|
m_traName = itemp->prettyName();
|
||||||
VL_RESTORER(m_traValuep);
|
if (isStruct) {
|
||||||
{
|
VL_RESTORER(m_traValuep);
|
||||||
if (VN_IS(nodep, StructDType)) {
|
m_traValuep = m_traValuep->cloneTree(false);
|
||||||
// Mark scope as a struct by setting the last char to 0x80 + the
|
m_traValuep
|
||||||
// fstScopeType
|
= new AstSel{flp, m_traValuep, itemp->lsb(), subtypep->width()};
|
||||||
m_traShowname += getScopeChar(VLT_TRACE_SCOPE_STRUCT) + " "
|
m_traValuep->dtypep(subtypep);
|
||||||
+ itemp->prettyName();
|
iterate(subtypep);
|
||||||
|
VL_DO_CLEAR(m_traValuep->deleteTree(), m_traValuep = nullptr);
|
||||||
m_traValuep
|
} else { // Else union, replicate fields
|
||||||
= new AstSel(nodep->fileline(), m_traValuep->cloneTree(true),
|
iterate(subtypep);
|
||||||
itemp->lsb(), subtypep->width());
|
|
||||||
m_traValuep->dtypep(subtypep);
|
|
||||||
iterate(subtypep);
|
|
||||||
VL_DO_CLEAR(m_traValuep->deleteTree(), m_traValuep = nullptr);
|
|
||||||
} else { // Else union, replicate fields
|
|
||||||
m_traShowname
|
|
||||||
+= getScopeChar(VLT_TRACE_SCOPE_UNION) + " " + itemp->prettyName();
|
|
||||||
iterate(subtypep);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
addToSubFunc(new AstTracePopNamePrefix{flp, 1});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -348,7 +443,48 @@ private:
|
||||||
|
|
||||||
public:
|
public:
|
||||||
// CONSTRUCTORS
|
// CONSTRUCTORS
|
||||||
explicit TraceDeclVisitor(AstNetlist* nodep) { iterate(nodep); }
|
explicit TraceDeclVisitor(AstNetlist* nodep)
|
||||||
|
: m_topScopep{nodep->topScopep()} {
|
||||||
|
FileLine* const flp = nodep->fileline();
|
||||||
|
|
||||||
|
// Iterate modules to build per scope initialization sub functions
|
||||||
|
iterateAndNextConstNull(nodep->modulesp());
|
||||||
|
UASSERT_OBJ(m_subFuncps.empty(), nodep, "Should have been emptied");
|
||||||
|
|
||||||
|
// Build top level trace initialization functions
|
||||||
|
PathAdjustor pathAdjustor{flp, [&](AstNodeStmt* stmtp) { addToTopFunc(stmtp); }};
|
||||||
|
for (const auto& item : m_scopeSubFuncps) {
|
||||||
|
// Adjust name prefix based on path in hierarchy
|
||||||
|
pathAdjustor.adjust(item.first);
|
||||||
|
|
||||||
|
// Call all sub functions for this path
|
||||||
|
for (AstCFunc* const subFuncp : item.second) {
|
||||||
|
AstCCall* const callp = new AstCCall{flp, subFuncp};
|
||||||
|
callp->argTypes("tracep");
|
||||||
|
addToTopFunc(callp);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
pathAdjustor.unwind();
|
||||||
|
|
||||||
|
// Ensure a top function exists, in case there was nothing to trace at all
|
||||||
|
if (m_topFuncps.empty()) addToTopFunc(new AstComment{flp, "Empty"});
|
||||||
|
|
||||||
|
// Create single top level function, if more than one exists
|
||||||
|
if (m_topFuncps.size() > 1) {
|
||||||
|
AstCFunc* const topFuncp = newCFunc(flp, "");
|
||||||
|
for (AstCFunc* funcp : m_topFuncps) {
|
||||||
|
AstCCall* const callp = new AstCCall{flp, funcp};
|
||||||
|
callp->argTypes("tracep");
|
||||||
|
topFuncp->addStmtsp(callp);
|
||||||
|
}
|
||||||
|
m_topFuncps.clear();
|
||||||
|
m_topFuncps.push_back(topFuncp);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set name of top level function
|
||||||
|
AstCFunc* const topFuncp = m_topFuncps.front();
|
||||||
|
topFuncp->name("trace_init_top");
|
||||||
|
}
|
||||||
virtual ~TraceDeclVisitor() override {
|
virtual ~TraceDeclVisitor() override {
|
||||||
V3Stats::addStat("Tracing, Traced signals", m_statSigs);
|
V3Stats::addStat("Tracing, Traced signals", m_statSigs);
|
||||||
V3Stats::addStat("Tracing, Ignored signals", m_statIgnSigs);
|
V3Stats::addStat("Tracing, Ignored signals", m_statIgnSigs);
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,6 @@
|
||||||
$version Generated by VerilatedVcd $end
|
$version Generated by VerilatedVcd $end
|
||||||
$date Sun May 31 15:48:42 2020
|
$date Sat Dec 18 13:32:31 2021 $end
|
||||||
$end
|
$timescale 1ps $end
|
||||||
$timescale 1ps $end
|
|
||||||
|
|
||||||
$scope module top $end
|
$scope module top $end
|
||||||
$var wire 1 W clk $end
|
$var wire 1 W clk $end
|
||||||
|
|
@ -11,31 +10,31 @@ $timescale 1ps $end
|
||||||
$var wire 8 ' cyc_copy [7:0] $end
|
$var wire 8 ' cyc_copy [7:0] $end
|
||||||
$var wire 1 % toggle $end
|
$var wire 1 % toggle $end
|
||||||
$var wire 32 ; vlCoverageLineTrace_t_cover_line__102_elsif [31:0] $end
|
$var wire 32 ; vlCoverageLineTrace_t_cover_line__102_elsif [31:0] $end
|
||||||
$var wire 32 : vlCoverageLineTrace_t_cover_line__105_elsif [31:0] $end
|
$var wire 32 < vlCoverageLineTrace_t_cover_line__105_elsif [31:0] $end
|
||||||
$var wire 32 9 vlCoverageLineTrace_t_cover_line__112_else [31:0] $end
|
$var wire 32 = vlCoverageLineTrace_t_cover_line__112_else [31:0] $end
|
||||||
$var wire 32 8 vlCoverageLineTrace_t_cover_line__112_if [31:0] $end
|
$var wire 32 > vlCoverageLineTrace_t_cover_line__112_if [31:0] $end
|
||||||
$var wire 32 X vlCoverageLineTrace_t_cover_line__119_block [31:0] $end
|
$var wire 32 X vlCoverageLineTrace_t_cover_line__119_block [31:0] $end
|
||||||
$var wire 32 # vlCoverageLineTrace_t_cover_line__15_block [31:0] $end
|
$var wire 32 # vlCoverageLineTrace_t_cover_line__15_block [31:0] $end
|
||||||
$var wire 32 $ vlCoverageLineTrace_t_cover_line__18_block [31:0] $end
|
$var wire 32 $ vlCoverageLineTrace_t_cover_line__18_block [31:0] $end
|
||||||
$var wire 32 > vlCoverageLineTrace_t_cover_line__47_block [31:0] $end
|
$var wire 32 ( vlCoverageLineTrace_t_cover_line__47_block [31:0] $end
|
||||||
$var wire 32 = vlCoverageLineTrace_t_cover_line__48_else [31:0] $end
|
$var wire 32 ) vlCoverageLineTrace_t_cover_line__48_else [31:0] $end
|
||||||
$var wire 32 < vlCoverageLineTrace_t_cover_line__48_if [31:0] $end
|
$var wire 32 * vlCoverageLineTrace_t_cover_line__48_if [31:0] $end
|
||||||
$var wire 32 ) vlCoverageLineTrace_t_cover_line__52_else [31:0] $end
|
$var wire 32 + vlCoverageLineTrace_t_cover_line__52_else [31:0] $end
|
||||||
$var wire 32 ( vlCoverageLineTrace_t_cover_line__52_if [31:0] $end
|
$var wire 32 , vlCoverageLineTrace_t_cover_line__52_if [31:0] $end
|
||||||
$var wire 32 + vlCoverageLineTrace_t_cover_line__53_else [31:0] $end
|
$var wire 32 - vlCoverageLineTrace_t_cover_line__53_else [31:0] $end
|
||||||
$var wire 32 * vlCoverageLineTrace_t_cover_line__53_if [31:0] $end
|
$var wire 32 . vlCoverageLineTrace_t_cover_line__53_if [31:0] $end
|
||||||
$var wire 32 - vlCoverageLineTrace_t_cover_line__58_else [31:0] $end
|
$var wire 32 / vlCoverageLineTrace_t_cover_line__58_else [31:0] $end
|
||||||
$var wire 32 , vlCoverageLineTrace_t_cover_line__58_if [31:0] $end
|
$var wire 32 0 vlCoverageLineTrace_t_cover_line__58_if [31:0] $end
|
||||||
$var wire 32 / vlCoverageLineTrace_t_cover_line__59_else [31:0] $end
|
$var wire 32 1 vlCoverageLineTrace_t_cover_line__59_else [31:0] $end
|
||||||
$var wire 32 . vlCoverageLineTrace_t_cover_line__59_if [31:0] $end
|
$var wire 32 2 vlCoverageLineTrace_t_cover_line__59_if [31:0] $end
|
||||||
$var wire 32 1 vlCoverageLineTrace_t_cover_line__65_else [31:0] $end
|
$var wire 32 3 vlCoverageLineTrace_t_cover_line__65_else [31:0] $end
|
||||||
$var wire 32 0 vlCoverageLineTrace_t_cover_line__65_if [31:0] $end
|
$var wire 32 4 vlCoverageLineTrace_t_cover_line__65_if [31:0] $end
|
||||||
$var wire 32 3 vlCoverageLineTrace_t_cover_line__66_else [31:0] $end
|
$var wire 32 5 vlCoverageLineTrace_t_cover_line__66_else [31:0] $end
|
||||||
$var wire 32 2 vlCoverageLineTrace_t_cover_line__66_if [31:0] $end
|
$var wire 32 6 vlCoverageLineTrace_t_cover_line__66_if [31:0] $end
|
||||||
$var wire 32 7 vlCoverageLineTrace_t_cover_line__75_elsif [31:0] $end
|
$var wire 32 7 vlCoverageLineTrace_t_cover_line__75_elsif [31:0] $end
|
||||||
$var wire 32 6 vlCoverageLineTrace_t_cover_line__79_elsif [31:0] $end
|
$var wire 32 8 vlCoverageLineTrace_t_cover_line__79_elsif [31:0] $end
|
||||||
$var wire 32 5 vlCoverageLineTrace_t_cover_line__83_else [31:0] $end
|
$var wire 32 9 vlCoverageLineTrace_t_cover_line__83_else [31:0] $end
|
||||||
$var wire 32 4 vlCoverageLineTrace_t_cover_line__83_if [31:0] $end
|
$var wire 32 : vlCoverageLineTrace_t_cover_line__83_if [31:0] $end
|
||||||
$var wire 32 ] vlCoverageLineTrace_t_cover_line__92_block [31:0] $end
|
$var wire 32 ] vlCoverageLineTrace_t_cover_line__92_block [31:0] $end
|
||||||
$var wire 32 ^ vlCoverageLineTrace_t_cover_line__93_block [31:0] $end
|
$var wire 32 ^ vlCoverageLineTrace_t_cover_line__93_block [31:0] $end
|
||||||
$var wire 32 _ vlCoverageLineTrace_t_cover_line__96_block [31:0] $end
|
$var wire 32 _ vlCoverageLineTrace_t_cover_line__96_block [31:0] $end
|
||||||
|
|
@ -43,57 +42,57 @@ $timescale 1ps $end
|
||||||
$scope module a1 $end
|
$scope module a1 $end
|
||||||
$var wire 1 W clk $end
|
$var wire 1 W clk $end
|
||||||
$var wire 1 % toggle $end
|
$var wire 1 % toggle $end
|
||||||
$var wire 32 B vlCoverageLineTrace_t_cover_line__132_block [31:0] $end
|
$var wire 32 ? vlCoverageLineTrace_t_cover_line__132_block [31:0] $end
|
||||||
$var wire 32 @ vlCoverageLineTrace_t_cover_line__133_else [31:0] $end
|
$var wire 32 @ vlCoverageLineTrace_t_cover_line__133_else [31:0] $end
|
||||||
$var wire 32 ? vlCoverageLineTrace_t_cover_line__133_if [31:0] $end
|
$var wire 32 A vlCoverageLineTrace_t_cover_line__133_if [31:0] $end
|
||||||
$var wire 32 A vlCoverageLineTrace_t_cover_line__137_else [31:0] $end
|
$var wire 32 B vlCoverageLineTrace_t_cover_line__137_else [31:0] $end
|
||||||
$upscope $end
|
$upscope $end
|
||||||
$scope module a2 $end
|
$scope module a2 $end
|
||||||
$var wire 1 W clk $end
|
$var wire 1 W clk $end
|
||||||
$var wire 1 % toggle $end
|
$var wire 1 % toggle $end
|
||||||
$var wire 32 F vlCoverageLineTrace_t_cover_line__132_block [31:0] $end
|
$var wire 32 C vlCoverageLineTrace_t_cover_line__132_block [31:0] $end
|
||||||
$var wire 32 D vlCoverageLineTrace_t_cover_line__133_else [31:0] $end
|
$var wire 32 D vlCoverageLineTrace_t_cover_line__133_else [31:0] $end
|
||||||
$var wire 32 C vlCoverageLineTrace_t_cover_line__133_if [31:0] $end
|
$var wire 32 E vlCoverageLineTrace_t_cover_line__133_if [31:0] $end
|
||||||
$var wire 32 E vlCoverageLineTrace_t_cover_line__137_else [31:0] $end
|
$var wire 32 F vlCoverageLineTrace_t_cover_line__137_else [31:0] $end
|
||||||
$upscope $end
|
$upscope $end
|
||||||
$scope module b1 $end
|
$scope module b1 $end
|
||||||
$var wire 1 W clk $end
|
$var wire 1 W clk $end
|
||||||
$var wire 1 % toggle $end
|
$var wire 1 % toggle $end
|
||||||
$var wire 32 O vlCoverageLineTrace_t_cover_line__156_block [31:0] $end
|
$var wire 32 K vlCoverageLineTrace_t_cover_line__156_block [31:0] $end
|
||||||
$var wire 32 K vlCoverageLineTrace_t_cover_line__158_else [31:0] $end
|
$var wire 32 L vlCoverageLineTrace_t_cover_line__158_else [31:0] $end
|
||||||
$var wire 32 b vlCoverageLineTrace_t_cover_line__158_if [31:0] $end
|
$var wire 32 b vlCoverageLineTrace_t_cover_line__158_if [31:0] $end
|
||||||
$var wire 32 M vlCoverageLineTrace_t_cover_line__162_else [31:0] $end
|
$var wire 32 M vlCoverageLineTrace_t_cover_line__162_else [31:0] $end
|
||||||
$var wire 32 L vlCoverageLineTrace_t_cover_line__162_if [31:0] $end
|
$var wire 32 N vlCoverageLineTrace_t_cover_line__162_if [31:0] $end
|
||||||
$var wire 32 N vlCoverageLineTrace_t_cover_line__166_else [31:0] $end
|
$var wire 32 O vlCoverageLineTrace_t_cover_line__166_else [31:0] $end
|
||||||
$upscope $end
|
$upscope $end
|
||||||
$scope module b2 $end
|
$scope module b2 $end
|
||||||
$var wire 1 W clk $end
|
$var wire 1 W clk $end
|
||||||
$var wire 1 % toggle $end
|
$var wire 1 % toggle $end
|
||||||
$var wire 32 T vlCoverageLineTrace_t_cover_line__156_block [31:0] $end
|
$var wire 32 P vlCoverageLineTrace_t_cover_line__156_block [31:0] $end
|
||||||
$var wire 32 P vlCoverageLineTrace_t_cover_line__158_else [31:0] $end
|
$var wire 32 Q vlCoverageLineTrace_t_cover_line__158_else [31:0] $end
|
||||||
$var wire 32 c vlCoverageLineTrace_t_cover_line__158_if [31:0] $end
|
$var wire 32 c vlCoverageLineTrace_t_cover_line__158_if [31:0] $end
|
||||||
$var wire 32 R vlCoverageLineTrace_t_cover_line__162_else [31:0] $end
|
$var wire 32 R vlCoverageLineTrace_t_cover_line__162_else [31:0] $end
|
||||||
$var wire 32 Q vlCoverageLineTrace_t_cover_line__162_if [31:0] $end
|
$var wire 32 S vlCoverageLineTrace_t_cover_line__162_if [31:0] $end
|
||||||
$var wire 32 S vlCoverageLineTrace_t_cover_line__166_else [31:0] $end
|
$var wire 32 T vlCoverageLineTrace_t_cover_line__166_else [31:0] $end
|
||||||
$upscope $end
|
$upscope $end
|
||||||
$scope module o1 $end
|
$scope module o1 $end
|
||||||
$var wire 1 W clk $end
|
$var wire 1 W clk $end
|
||||||
$var wire 1 % toggle $end
|
$var wire 1 % toggle $end
|
||||||
$var wire 32 J vlCoverageLineTrace_t_cover_line__220_block [31:0] $end
|
$var wire 32 G vlCoverageLineTrace_t_cover_line__220_block [31:0] $end
|
||||||
$var wire 32 I vlCoverageLineTrace_t_cover_line__221_else [31:0] $end
|
$var wire 32 H vlCoverageLineTrace_t_cover_line__221_else [31:0] $end
|
||||||
$var wire 32 H vlCoverageLineTrace_t_cover_line__221_if [31:0] $end
|
$var wire 32 I vlCoverageLineTrace_t_cover_line__221_if [31:0] $end
|
||||||
$var wire 32 G vlCoverageLineTrace_t_cover_line__224_else [31:0] $end
|
$var wire 32 J vlCoverageLineTrace_t_cover_line__224_else [31:0] $end
|
||||||
$var wire 32 a vlCoverageLineTrace_t_cover_line__224_if [31:0] $end
|
$var wire 32 a vlCoverageLineTrace_t_cover_line__224_if [31:0] $end
|
||||||
$upscope $end
|
$upscope $end
|
||||||
$scope module t1 $end
|
$scope module t1 $end
|
||||||
$var wire 1 W clk $end
|
$var wire 1 W clk $end
|
||||||
$var wire 1 % toggle $end
|
$var wire 1 % toggle $end
|
||||||
$var wire 32 U vlCoverageLineTrace_t_cover_line__187_block [31:0] $end
|
$var wire 32 U vlCoverageLineTrace_t_cover_line__187_block [31:0] $end
|
||||||
$var wire 32 \ vlCoverageLineTrace_t_cover_line__191_block [31:0] $end
|
$var wire 32 Y vlCoverageLineTrace_t_cover_line__191_block [31:0] $end
|
||||||
$var wire 32 Z vlCoverageLineTrace_t_cover_line__194_else [31:0] $end
|
$var wire 32 Z vlCoverageLineTrace_t_cover_line__194_else [31:0] $end
|
||||||
$var wire 32 Y vlCoverageLineTrace_t_cover_line__194_if [31:0] $end
|
$var wire 32 [ vlCoverageLineTrace_t_cover_line__194_if [31:0] $end
|
||||||
$var wire 32 V vlCoverageLineTrace_t_cover_line__197_else [31:0] $end
|
$var wire 32 V vlCoverageLineTrace_t_cover_line__197_else [31:0] $end
|
||||||
$var wire 32 [ vlCoverageLineTrace_t_cover_line__197_if [31:0] $end
|
$var wire 32 \ vlCoverageLineTrace_t_cover_line__197_if [31:0] $end
|
||||||
$upscope $end
|
$upscope $end
|
||||||
$upscope $end
|
$upscope $end
|
||||||
$upscope $end
|
$upscope $end
|
||||||
|
|
@ -169,7 +168,8 @@ b00000000000000000000000000000000 c
|
||||||
#10
|
#10
|
||||||
b00000000000000000000000000000010 &
|
b00000000000000000000000000000010 &
|
||||||
b00000010 '
|
b00000010 '
|
||||||
b00000000000000000000000000000001 )
|
b00000000000000000000000000000001 (
|
||||||
|
b00000000000000000000000000000001 *
|
||||||
b00000000000000000000000000000001 +
|
b00000000000000000000000000000001 +
|
||||||
b00000000000000000000000000000001 -
|
b00000000000000000000000000000001 -
|
||||||
b00000000000000000000000000000001 /
|
b00000000000000000000000000000001 /
|
||||||
|
|
@ -177,35 +177,35 @@ b00000000000000000000000000000001 1
|
||||||
b00000000000000000000000000000001 3
|
b00000000000000000000000000000001 3
|
||||||
b00000000000000000000000000000001 5
|
b00000000000000000000000000000001 5
|
||||||
b00000000000000000000000000000001 9
|
b00000000000000000000000000000001 9
|
||||||
b00000000000000000000000000000001 <
|
b00000000000000000000000000000001 =
|
||||||
b00000000000000000000000000000001 >
|
b00000000000000000000000000000001 ?
|
||||||
b00000000000000000000000000000001 @
|
b00000000000000000000000000000001 @
|
||||||
b00000000000000000000000000000001 A
|
|
||||||
b00000000000000000000000000000001 B
|
b00000000000000000000000000000001 B
|
||||||
|
b00000000000000000000000000000001 C
|
||||||
b00000000000000000000000000000001 D
|
b00000000000000000000000000000001 D
|
||||||
b00000000000000000000000000000001 E
|
|
||||||
b00000000000000000000000000000001 F
|
b00000000000000000000000000000001 F
|
||||||
b00000000000000000000000000000001 I
|
b00000000000000000000000000000001 G
|
||||||
b00000000000000000000000000000001 J
|
b00000000000000000000000000000001 H
|
||||||
b00000000000000000000000000000001 K
|
b00000000000000000000000000000001 K
|
||||||
|
b00000000000000000000000000000001 L
|
||||||
b00000000000000000000000000000001 M
|
b00000000000000000000000000000001 M
|
||||||
b00000000000000000000000000000001 N
|
|
||||||
b00000000000000000000000000000001 O
|
b00000000000000000000000000000001 O
|
||||||
b00000000000000000000000000000001 P
|
b00000000000000000000000000000001 P
|
||||||
|
b00000000000000000000000000000001 Q
|
||||||
b00000000000000000000000000000001 R
|
b00000000000000000000000000000001 R
|
||||||
b00000000000000000000000000000001 S
|
|
||||||
b00000000000000000000000000000001 T
|
b00000000000000000000000000000001 T
|
||||||
b00000000000000000000000000000001 U
|
b00000000000000000000000000000001 U
|
||||||
b00000000000000000000000000000001 V
|
b00000000000000000000000000000001 V
|
||||||
1W
|
1W
|
||||||
|
b00000000000000000000000000000001 Y
|
||||||
b00000000000000000000000000000001 Z
|
b00000000000000000000000000000001 Z
|
||||||
b00000000000000000000000000000001 \
|
|
||||||
#15
|
#15
|
||||||
0W
|
0W
|
||||||
#20
|
#20
|
||||||
b00000000000000000000000000000011 &
|
b00000000000000000000000000000011 &
|
||||||
b00000011 '
|
b00000011 '
|
||||||
b00000000000000000000000000000010 )
|
b00000000000000000000000000000010 (
|
||||||
|
b00000000000000000000000000000010 *
|
||||||
b00000000000000000000000000000010 +
|
b00000000000000000000000000000010 +
|
||||||
b00000000000000000000000000000010 -
|
b00000000000000000000000000000010 -
|
||||||
b00000000000000000000000000000010 /
|
b00000000000000000000000000000010 /
|
||||||
|
|
@ -213,315 +213,314 @@ b00000000000000000000000000000010 1
|
||||||
b00000000000000000000000000000010 3
|
b00000000000000000000000000000010 3
|
||||||
b00000000000000000000000000000010 5
|
b00000000000000000000000000000010 5
|
||||||
b00000000000000000000000000000010 9
|
b00000000000000000000000000000010 9
|
||||||
b00000000000000000000000000000010 <
|
b00000000000000000000000000000010 =
|
||||||
b00000000000000000000000000000010 >
|
b00000000000000000000000000000010 ?
|
||||||
b00000000000000000000000000000010 @
|
b00000000000000000000000000000010 @
|
||||||
b00000000000000000000000000000010 A
|
|
||||||
b00000000000000000000000000000010 B
|
b00000000000000000000000000000010 B
|
||||||
|
b00000000000000000000000000000010 C
|
||||||
b00000000000000000000000000000010 D
|
b00000000000000000000000000000010 D
|
||||||
b00000000000000000000000000000010 E
|
|
||||||
b00000000000000000000000000000010 F
|
b00000000000000000000000000000010 F
|
||||||
b00000000000000000000000000000010 I
|
b00000000000000000000000000000010 G
|
||||||
b00000000000000000000000000000010 J
|
b00000000000000000000000000000010 H
|
||||||
b00000000000000000000000000000010 K
|
b00000000000000000000000000000010 K
|
||||||
|
b00000000000000000000000000000010 L
|
||||||
b00000000000000000000000000000010 M
|
b00000000000000000000000000000010 M
|
||||||
b00000000000000000000000000000010 N
|
|
||||||
b00000000000000000000000000000010 O
|
b00000000000000000000000000000010 O
|
||||||
b00000000000000000000000000000010 P
|
b00000000000000000000000000000010 P
|
||||||
|
b00000000000000000000000000000010 Q
|
||||||
b00000000000000000000000000000010 R
|
b00000000000000000000000000000010 R
|
||||||
b00000000000000000000000000000010 S
|
|
||||||
b00000000000000000000000000000010 T
|
b00000000000000000000000000000010 T
|
||||||
b00000000000000000000000000000010 U
|
b00000000000000000000000000000010 U
|
||||||
b00000000000000000000000000000010 V
|
b00000000000000000000000000000010 V
|
||||||
1W
|
1W
|
||||||
|
b00000000000000000000000000000010 Y
|
||||||
b00000000000000000000000000000010 Z
|
b00000000000000000000000000000010 Z
|
||||||
b00000000000000000000000000000010 \
|
|
||||||
#25
|
#25
|
||||||
0W
|
0W
|
||||||
#30
|
#30
|
||||||
1%
|
1%
|
||||||
b00000000000000000000000000000100 &
|
b00000000000000000000000000000100 &
|
||||||
b00000100 '
|
b00000100 '
|
||||||
b00000000000000000000000000000001 (
|
b00000000000000000000000000000011 (
|
||||||
b00000000000000000000000000000001 *
|
b00000000000000000000000000000011 *
|
||||||
b00000000000000000000000000000001 ,
|
b00000000000000000000000000000001 ,
|
||||||
b00000000000000000000000000000001 .
|
b00000000000000000000000000000001 .
|
||||||
b00000000000000000000000000000001 0
|
b00000000000000000000000000000001 0
|
||||||
b00000000000000000000000000000001 2
|
b00000000000000000000000000000001 2
|
||||||
|
b00000000000000000000000000000001 4
|
||||||
|
b00000000000000000000000000000001 6
|
||||||
b00000000000000000000000000000001 7
|
b00000000000000000000000000000001 7
|
||||||
b00000000000000000000000000000001 ;
|
b00000000000000000000000000000001 ;
|
||||||
b00000000000000000000000000000011 <
|
b00000000000000000000000000000011 ?
|
||||||
b00000000000000000000000000000011 >
|
|
||||||
b00000000000000000000000000000011 @
|
b00000000000000000000000000000011 @
|
||||||
b00000000000000000000000000000011 A
|
|
||||||
b00000000000000000000000000000011 B
|
b00000000000000000000000000000011 B
|
||||||
|
b00000000000000000000000000000011 C
|
||||||
b00000000000000000000000000000011 D
|
b00000000000000000000000000000011 D
|
||||||
b00000000000000000000000000000011 E
|
|
||||||
b00000000000000000000000000000011 F
|
b00000000000000000000000000000011 F
|
||||||
b00000000000000000000000000000011 I
|
b00000000000000000000000000000011 G
|
||||||
b00000000000000000000000000000011 J
|
b00000000000000000000000000000011 H
|
||||||
b00000000000000000000000000000011 K
|
b00000000000000000000000000000011 K
|
||||||
|
b00000000000000000000000000000011 L
|
||||||
b00000000000000000000000000000011 M
|
b00000000000000000000000000000011 M
|
||||||
b00000000000000000000000000000011 N
|
|
||||||
b00000000000000000000000000000011 O
|
b00000000000000000000000000000011 O
|
||||||
b00000000000000000000000000000011 P
|
b00000000000000000000000000000011 P
|
||||||
|
b00000000000000000000000000000011 Q
|
||||||
b00000000000000000000000000000011 R
|
b00000000000000000000000000000011 R
|
||||||
b00000000000000000000000000000011 S
|
|
||||||
b00000000000000000000000000000011 T
|
b00000000000000000000000000000011 T
|
||||||
b00000000000000000000000000000011 U
|
b00000000000000000000000000000011 U
|
||||||
b00000000000000000000000000000011 V
|
b00000000000000000000000000000011 V
|
||||||
1W
|
1W
|
||||||
|
b00000000000000000000000000000011 Y
|
||||||
b00000000000000000000000000000011 Z
|
b00000000000000000000000000000011 Z
|
||||||
b00000000000000000000000000000011 \
|
|
||||||
#35
|
#35
|
||||||
0W
|
0W
|
||||||
#40
|
#40
|
||||||
0%
|
0%
|
||||||
b00000000000000000000000000000101 &
|
b00000000000000000000000000000101 &
|
||||||
b00000101 '
|
b00000101 '
|
||||||
b00000000000000000000000000000011 )
|
b00000000000000000000000000000100 (
|
||||||
|
b00000000000000000000000000000100 *
|
||||||
b00000000000000000000000000000011 +
|
b00000000000000000000000000000011 +
|
||||||
b00000000000000000000000000000011 -
|
b00000000000000000000000000000011 -
|
||||||
b00000000000000000000000000000011 /
|
b00000000000000000000000000000011 /
|
||||||
b00000000000000000000000000000011 1
|
b00000000000000000000000000000011 1
|
||||||
b00000000000000000000000000000011 3
|
b00000000000000000000000000000011 3
|
||||||
b00000000000000000000000000000001 6
|
b00000000000000000000000000000011 5
|
||||||
b00000000000000000000000000000011 9
|
b00000000000000000000000000000001 8
|
||||||
b00000000000000000000000000000100 <
|
b00000000000000000000000000000011 =
|
||||||
b00000000000000000000000000000100 >
|
b00000000000000000000000000000100 ?
|
||||||
b00000000000000000000000000000001 ?
|
b00000000000000000000000000000001 A
|
||||||
b00000000000000000000000000000100 B
|
b00000000000000000000000000000100 C
|
||||||
b00000000000000000000000000000001 C
|
b00000000000000000000000000000001 E
|
||||||
b00000000000000000000000000000100 F
|
b00000000000000000000000000000100 G
|
||||||
b00000000000000000000000000000001 G
|
b00000000000000000000000000000001 I
|
||||||
b00000000000000000000000000000001 H
|
b00000000000000000000000000000001 J
|
||||||
b00000000000000000000000000000100 J
|
|
||||||
b00000000000000000000000000000100 K
|
b00000000000000000000000000000100 K
|
||||||
b00000000000000000000000000000001 L
|
b00000000000000000000000000000100 L
|
||||||
b00000000000000000000000000000100 O
|
b00000000000000000000000000000001 N
|
||||||
b00000000000000000000000000000100 P
|
b00000000000000000000000000000100 P
|
||||||
b00000000000000000000000000000001 Q
|
b00000000000000000000000000000100 Q
|
||||||
b00000000000000000000000000000100 T
|
b00000000000000000000000000000001 S
|
||||||
b00000000000000000000000000000100 U
|
b00000000000000000000000000000100 U
|
||||||
b00000000000000000000000000000100 V
|
b00000000000000000000000000000100 V
|
||||||
1W
|
1W
|
||||||
b00000000000000000000000000000001 Y
|
b00000000000000000000000000000100 Y
|
||||||
b00000000000000000000000000000100 \
|
b00000000000000000000000000000001 [
|
||||||
#45
|
#45
|
||||||
0W
|
0W
|
||||||
#50
|
#50
|
||||||
b00000000000000000000000000000110 &
|
b00000000000000000000000000000110 &
|
||||||
b00000110 '
|
b00000110 '
|
||||||
b00000000000000000000000000000100 )
|
b00000000000000000000000000000101 (
|
||||||
|
b00000000000000000000000000000101 *
|
||||||
b00000000000000000000000000000100 +
|
b00000000000000000000000000000100 +
|
||||||
b00000000000000000000000000000100 -
|
b00000000000000000000000000000100 -
|
||||||
b00000000000000000000000000000100 /
|
b00000000000000000000000000000100 /
|
||||||
b00000000000000000000000000000100 1
|
b00000000000000000000000000000100 1
|
||||||
b00000000000000000000000000000100 3
|
b00000000000000000000000000000100 3
|
||||||
b00000000000000000000000000000001 4
|
b00000000000000000000000000000100 5
|
||||||
b00000000000000000000000000000001 :
|
b00000000000000000000000000000001 :
|
||||||
b00000000000000000000000000000101 <
|
b00000000000000000000000000000001 <
|
||||||
b00000000000000000000000000000101 >
|
b00000000000000000000000000000101 ?
|
||||||
b00000000000000000000000000000100 @
|
b00000000000000000000000000000100 @
|
||||||
b00000000000000000000000000000100 A
|
b00000000000000000000000000000100 B
|
||||||
b00000000000000000000000000000101 B
|
b00000000000000000000000000000101 C
|
||||||
b00000000000000000000000000000100 D
|
b00000000000000000000000000000100 D
|
||||||
b00000000000000000000000000000100 E
|
b00000000000000000000000000000100 F
|
||||||
b00000000000000000000000000000101 F
|
b00000000000000000000000000000101 G
|
||||||
b00000000000000000000000000000100 I
|
b00000000000000000000000000000100 H
|
||||||
b00000000000000000000000000000101 J
|
|
||||||
b00000000000000000000000000000101 K
|
b00000000000000000000000000000101 K
|
||||||
|
b00000000000000000000000000000101 L
|
||||||
b00000000000000000000000000000100 M
|
b00000000000000000000000000000100 M
|
||||||
b00000000000000000000000000000100 N
|
b00000000000000000000000000000100 O
|
||||||
b00000000000000000000000000000101 O
|
|
||||||
b00000000000000000000000000000101 P
|
b00000000000000000000000000000101 P
|
||||||
|
b00000000000000000000000000000101 Q
|
||||||
b00000000000000000000000000000100 R
|
b00000000000000000000000000000100 R
|
||||||
b00000000000000000000000000000100 S
|
b00000000000000000000000000000100 T
|
||||||
b00000000000000000000000000000101 T
|
|
||||||
b00000000000000000000000000000101 U
|
b00000000000000000000000000000101 U
|
||||||
b00000000000000000000000000000101 V
|
b00000000000000000000000000000101 V
|
||||||
1W
|
1W
|
||||||
b00000000000000000000000000000001 X
|
b00000000000000000000000000000001 X
|
||||||
|
b00000000000000000000000000000110 Y
|
||||||
b00000000000000000000000000000101 Z
|
b00000000000000000000000000000101 Z
|
||||||
b00000000000000000000000000000001 [
|
b00000000000000000000000000000001 \
|
||||||
b00000000000000000000000000000110 \
|
|
||||||
#55
|
#55
|
||||||
0W
|
0W
|
||||||
#60
|
#60
|
||||||
b00000000000000000000000000000111 &
|
b00000000000000000000000000000111 &
|
||||||
b00000111 '
|
b00000111 '
|
||||||
b00000000000000000000000000000101 )
|
b00000000000000000000000000000110 (
|
||||||
|
b00000000000000000000000000000110 *
|
||||||
b00000000000000000000000000000101 +
|
b00000000000000000000000000000101 +
|
||||||
b00000000000000000000000000000101 -
|
b00000000000000000000000000000101 -
|
||||||
b00000000000000000000000000000101 /
|
b00000000000000000000000000000101 /
|
||||||
b00000000000000000000000000000101 1
|
b00000000000000000000000000000101 1
|
||||||
b00000000000000000000000000000101 3
|
b00000000000000000000000000000101 3
|
||||||
b00000000000000000000000000000011 5
|
b00000000000000000000000000000101 5
|
||||||
b00000000000000000000000000000100 9
|
b00000000000000000000000000000011 9
|
||||||
b00000000000000000000000000000110 <
|
b00000000000000000000000000000100 =
|
||||||
b00000000000000000000000000000110 >
|
b00000000000000000000000000000110 ?
|
||||||
b00000000000000000000000000000101 @
|
b00000000000000000000000000000101 @
|
||||||
b00000000000000000000000000000101 A
|
b00000000000000000000000000000101 B
|
||||||
b00000000000000000000000000000110 B
|
b00000000000000000000000000000110 C
|
||||||
b00000000000000000000000000000101 D
|
b00000000000000000000000000000101 D
|
||||||
b00000000000000000000000000000101 E
|
b00000000000000000000000000000101 F
|
||||||
b00000000000000000000000000000110 F
|
b00000000000000000000000000000110 G
|
||||||
b00000000000000000000000000000101 I
|
b00000000000000000000000000000101 H
|
||||||
b00000000000000000000000000000110 J
|
|
||||||
b00000000000000000000000000000110 K
|
b00000000000000000000000000000110 K
|
||||||
|
b00000000000000000000000000000110 L
|
||||||
b00000000000000000000000000000101 M
|
b00000000000000000000000000000101 M
|
||||||
b00000000000000000000000000000101 N
|
b00000000000000000000000000000101 O
|
||||||
b00000000000000000000000000000110 O
|
|
||||||
b00000000000000000000000000000110 P
|
b00000000000000000000000000000110 P
|
||||||
|
b00000000000000000000000000000110 Q
|
||||||
b00000000000000000000000000000101 R
|
b00000000000000000000000000000101 R
|
||||||
b00000000000000000000000000000101 S
|
b00000000000000000000000000000101 T
|
||||||
b00000000000000000000000000000110 T
|
|
||||||
b00000000000000000000000000000110 U
|
b00000000000000000000000000000110 U
|
||||||
b00000000000000000000000000000110 V
|
b00000000000000000000000000000110 V
|
||||||
1W
|
1W
|
||||||
|
b00000000000000000000000000000111 Y
|
||||||
b00000000000000000000000000000110 Z
|
b00000000000000000000000000000110 Z
|
||||||
b00000000000000000000000000000111 \
|
|
||||||
#65
|
#65
|
||||||
0W
|
0W
|
||||||
#70
|
#70
|
||||||
b00000000000000000000000000001000 &
|
b00000000000000000000000000001000 &
|
||||||
b00001000 '
|
b00001000 '
|
||||||
b00000000000000000000000000000110 )
|
b00000000000000000000000000000111 (
|
||||||
|
b00000000000000000000000000000111 *
|
||||||
b00000000000000000000000000000110 +
|
b00000000000000000000000000000110 +
|
||||||
b00000000000000000000000000000110 -
|
b00000000000000000000000000000110 -
|
||||||
b00000000000000000000000000000110 /
|
b00000000000000000000000000000110 /
|
||||||
b00000000000000000000000000000110 1
|
b00000000000000000000000000000110 1
|
||||||
b00000000000000000000000000000110 3
|
b00000000000000000000000000000110 3
|
||||||
b00000000000000000000000000000100 5
|
b00000000000000000000000000000110 5
|
||||||
b00000000000000000000000000000101 9
|
b00000000000000000000000000000100 9
|
||||||
b00000000000000000000000000000111 <
|
b00000000000000000000000000000101 =
|
||||||
b00000000000000000000000000000111 >
|
b00000000000000000000000000000111 ?
|
||||||
b00000000000000000000000000000110 @
|
b00000000000000000000000000000110 @
|
||||||
b00000000000000000000000000000110 A
|
b00000000000000000000000000000110 B
|
||||||
b00000000000000000000000000000111 B
|
b00000000000000000000000000000111 C
|
||||||
b00000000000000000000000000000110 D
|
b00000000000000000000000000000110 D
|
||||||
b00000000000000000000000000000110 E
|
b00000000000000000000000000000110 F
|
||||||
b00000000000000000000000000000111 F
|
b00000000000000000000000000000111 G
|
||||||
b00000000000000000000000000000110 I
|
b00000000000000000000000000000110 H
|
||||||
b00000000000000000000000000000111 J
|
|
||||||
b00000000000000000000000000000111 K
|
b00000000000000000000000000000111 K
|
||||||
|
b00000000000000000000000000000111 L
|
||||||
b00000000000000000000000000000110 M
|
b00000000000000000000000000000110 M
|
||||||
b00000000000000000000000000000110 N
|
b00000000000000000000000000000110 O
|
||||||
b00000000000000000000000000000111 O
|
|
||||||
b00000000000000000000000000000111 P
|
b00000000000000000000000000000111 P
|
||||||
|
b00000000000000000000000000000111 Q
|
||||||
b00000000000000000000000000000110 R
|
b00000000000000000000000000000110 R
|
||||||
b00000000000000000000000000000110 S
|
b00000000000000000000000000000110 T
|
||||||
b00000000000000000000000000000111 T
|
|
||||||
b00000000000000000000000000000111 U
|
b00000000000000000000000000000111 U
|
||||||
b00000000000000000000000000000111 V
|
b00000000000000000000000000000111 V
|
||||||
1W
|
1W
|
||||||
|
b00000000000000000000000000001000 Y
|
||||||
b00000000000000000000000000000111 Z
|
b00000000000000000000000000000111 Z
|
||||||
b00000000000000000000000000001000 \
|
|
||||||
#75
|
#75
|
||||||
0W
|
0W
|
||||||
#80
|
#80
|
||||||
b00000000000000000000000000001001 &
|
b00000000000000000000000000001001 &
|
||||||
b00001001 '
|
b00001001 '
|
||||||
b00000000000000000000000000000111 )
|
b00000000000000000000000000001000 (
|
||||||
|
b00000000000000000000000000001000 *
|
||||||
b00000000000000000000000000000111 +
|
b00000000000000000000000000000111 +
|
||||||
b00000000000000000000000000000111 -
|
b00000000000000000000000000000111 -
|
||||||
b00000000000000000000000000000111 /
|
b00000000000000000000000000000111 /
|
||||||
b00000000000000000000000000000111 1
|
b00000000000000000000000000000111 1
|
||||||
b00000000000000000000000000000111 3
|
b00000000000000000000000000000111 3
|
||||||
b00000000000000000000000000000101 5
|
b00000000000000000000000000000111 5
|
||||||
b00000000000000000000000000000110 9
|
b00000000000000000000000000000101 9
|
||||||
b00000000000000000000000000001000 <
|
b00000000000000000000000000000110 =
|
||||||
b00000000000000000000000000001000 >
|
b00000000000000000000000000001000 ?
|
||||||
b00000000000000000000000000000111 @
|
b00000000000000000000000000000111 @
|
||||||
b00000000000000000000000000000111 A
|
b00000000000000000000000000000111 B
|
||||||
b00000000000000000000000000001000 B
|
b00000000000000000000000000001000 C
|
||||||
b00000000000000000000000000000111 D
|
b00000000000000000000000000000111 D
|
||||||
b00000000000000000000000000000111 E
|
b00000000000000000000000000000111 F
|
||||||
b00000000000000000000000000001000 F
|
b00000000000000000000000000001000 G
|
||||||
b00000000000000000000000000000111 I
|
b00000000000000000000000000000111 H
|
||||||
b00000000000000000000000000001000 J
|
|
||||||
b00000000000000000000000000001000 K
|
b00000000000000000000000000001000 K
|
||||||
|
b00000000000000000000000000001000 L
|
||||||
b00000000000000000000000000000111 M
|
b00000000000000000000000000000111 M
|
||||||
b00000000000000000000000000000111 N
|
b00000000000000000000000000000111 O
|
||||||
b00000000000000000000000000001000 O
|
|
||||||
b00000000000000000000000000001000 P
|
b00000000000000000000000000001000 P
|
||||||
|
b00000000000000000000000000001000 Q
|
||||||
b00000000000000000000000000000111 R
|
b00000000000000000000000000000111 R
|
||||||
b00000000000000000000000000000111 S
|
b00000000000000000000000000000111 T
|
||||||
b00000000000000000000000000001000 T
|
|
||||||
b00000000000000000000000000001000 U
|
b00000000000000000000000000001000 U
|
||||||
b00000000000000000000000000001000 V
|
b00000000000000000000000000001000 V
|
||||||
1W
|
1W
|
||||||
|
b00000000000000000000000000001001 Y
|
||||||
b00000000000000000000000000001000 Z
|
b00000000000000000000000000001000 Z
|
||||||
b00000000000000000000000000001001 \
|
|
||||||
#85
|
#85
|
||||||
0W
|
0W
|
||||||
#90
|
#90
|
||||||
b00000000000000000000000000001010 &
|
b00000000000000000000000000001010 &
|
||||||
b00001010 '
|
b00001010 '
|
||||||
b00000000000000000000000000001000 )
|
b00000000000000000000000000001001 (
|
||||||
|
b00000000000000000000000000001001 *
|
||||||
b00000000000000000000000000001000 +
|
b00000000000000000000000000001000 +
|
||||||
b00000000000000000000000000001000 -
|
b00000000000000000000000000001000 -
|
||||||
b00000000000000000000000000001000 /
|
b00000000000000000000000000001000 /
|
||||||
b00000000000000000000000000001000 1
|
b00000000000000000000000000001000 1
|
||||||
b00000000000000000000000000001000 3
|
b00000000000000000000000000001000 3
|
||||||
b00000000000000000000000000000110 5
|
b00000000000000000000000000001000 5
|
||||||
b00000000000000000000000000000111 9
|
b00000000000000000000000000000110 9
|
||||||
b00000000000000000000000000001001 <
|
b00000000000000000000000000000111 =
|
||||||
b00000000000000000000000000001001 >
|
b00000000000000000000000000001001 ?
|
||||||
b00000000000000000000000000001000 @
|
b00000000000000000000000000001000 @
|
||||||
b00000000000000000000000000001000 A
|
b00000000000000000000000000001000 B
|
||||||
b00000000000000000000000000001001 B
|
b00000000000000000000000000001001 C
|
||||||
b00000000000000000000000000001000 D
|
b00000000000000000000000000001000 D
|
||||||
b00000000000000000000000000001000 E
|
b00000000000000000000000000001000 F
|
||||||
b00000000000000000000000000001001 F
|
b00000000000000000000000000001001 G
|
||||||
b00000000000000000000000000001000 I
|
b00000000000000000000000000001000 H
|
||||||
b00000000000000000000000000001001 J
|
|
||||||
b00000000000000000000000000001001 K
|
b00000000000000000000000000001001 K
|
||||||
|
b00000000000000000000000000001001 L
|
||||||
b00000000000000000000000000001000 M
|
b00000000000000000000000000001000 M
|
||||||
b00000000000000000000000000001000 N
|
b00000000000000000000000000001000 O
|
||||||
b00000000000000000000000000001001 O
|
|
||||||
b00000000000000000000000000001001 P
|
b00000000000000000000000000001001 P
|
||||||
|
b00000000000000000000000000001001 Q
|
||||||
b00000000000000000000000000001000 R
|
b00000000000000000000000000001000 R
|
||||||
b00000000000000000000000000001000 S
|
b00000000000000000000000000001000 T
|
||||||
b00000000000000000000000000001001 T
|
|
||||||
b00000000000000000000000000001001 U
|
b00000000000000000000000000001001 U
|
||||||
b00000000000000000000000000001001 V
|
b00000000000000000000000000001001 V
|
||||||
1W
|
1W
|
||||||
|
b00000000000000000000000000001010 Y
|
||||||
b00000000000000000000000000001001 Z
|
b00000000000000000000000000001001 Z
|
||||||
b00000000000000000000000000001010 \
|
|
||||||
#95
|
#95
|
||||||
0W
|
0W
|
||||||
#100
|
#100
|
||||||
b00000000000000000000000000001011 &
|
b00000000000000000000000000001011 &
|
||||||
b00001011 '
|
b00001011 '
|
||||||
b00000000000000000000000000001001 )
|
b00000000000000000000000000001010 (
|
||||||
|
b00000000000000000000000000001010 *
|
||||||
b00000000000000000000000000001001 +
|
b00000000000000000000000000001001 +
|
||||||
b00000000000000000000000000001001 -
|
b00000000000000000000000000001001 -
|
||||||
b00000000000000000000000000001001 /
|
b00000000000000000000000000001001 /
|
||||||
b00000000000000000000000000001001 1
|
b00000000000000000000000000001001 1
|
||||||
b00000000000000000000000000001001 3
|
b00000000000000000000000000001001 3
|
||||||
b00000000000000000000000000000111 5
|
b00000000000000000000000000001001 5
|
||||||
b00000000000000000000000000000001 8
|
b00000000000000000000000000000111 9
|
||||||
b00000000000000000000000000001010 <
|
b00000000000000000000000000000001 >
|
||||||
b00000000000000000000000000001010 >
|
b00000000000000000000000000001010 ?
|
||||||
b00000000000000000000000000001001 @
|
b00000000000000000000000000001001 @
|
||||||
b00000000000000000000000000001001 A
|
b00000000000000000000000000001001 B
|
||||||
b00000000000000000000000000001010 B
|
b00000000000000000000000000001010 C
|
||||||
b00000000000000000000000000001001 D
|
b00000000000000000000000000001001 D
|
||||||
b00000000000000000000000000001001 E
|
b00000000000000000000000000001001 F
|
||||||
b00000000000000000000000000001010 F
|
b00000000000000000000000000001010 G
|
||||||
b00000000000000000000000000001001 I
|
b00000000000000000000000000001001 H
|
||||||
b00000000000000000000000000001010 J
|
|
||||||
b00000000000000000000000000001010 K
|
b00000000000000000000000000001010 K
|
||||||
|
b00000000000000000000000000001010 L
|
||||||
b00000000000000000000000000001001 M
|
b00000000000000000000000000001001 M
|
||||||
b00000000000000000000000000001001 N
|
b00000000000000000000000000001001 O
|
||||||
b00000000000000000000000000001010 O
|
|
||||||
b00000000000000000000000000001010 P
|
b00000000000000000000000000001010 P
|
||||||
|
b00000000000000000000000000001010 Q
|
||||||
b00000000000000000000000000001001 R
|
b00000000000000000000000000001001 R
|
||||||
b00000000000000000000000000001001 S
|
b00000000000000000000000000001001 T
|
||||||
b00000000000000000000000000001010 T
|
|
||||||
b00000000000000000000000000001010 U
|
b00000000000000000000000000001010 U
|
||||||
b00000000000000000000000000001010 V
|
b00000000000000000000000000001010 V
|
||||||
1W
|
1W
|
||||||
|
b00000000000000000000000000001011 Y
|
||||||
b00000000000000000000000000001010 Z
|
b00000000000000000000000000001010 Z
|
||||||
b00000000000000000000000000001011 \
|
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,26 @@
|
||||||
|
#!/usr/bin/env perl
|
||||||
|
if (!$::Driver) { use FindBin; exec("$FindBin::Bin/bootstrap.pl", @ARGV, $0); die; }
|
||||||
|
# DESCRIPTION: Verilator: Verilog Test driver/expect definition
|
||||||
|
#
|
||||||
|
# Copyright 2021 by Wilson Snyder. This program is free software; you
|
||||||
|
# can redistribute it and/or modify it under the terms of either the GNU
|
||||||
|
# Lesser General Public License Version 3 or the Perl Artistic License
|
||||||
|
# Version 2.0.
|
||||||
|
# SPDX-License-Identifier: LGPL-3.0-only OR Artistic-2.0
|
||||||
|
|
||||||
|
scenarios(simulator => 1);
|
||||||
|
|
||||||
|
compile(
|
||||||
|
verilator_flags2 => ['--trace'],
|
||||||
|
);
|
||||||
|
|
||||||
|
execute(
|
||||||
|
check_finished => 1,
|
||||||
|
);
|
||||||
|
|
||||||
|
file_grep_not("$Self->{obj_dir}/simx.vcd", qr/scope/);
|
||||||
|
file_grep_not("$Self->{obj_dir}/simx.vcd", qr/upscope/);
|
||||||
|
file_grep_not("$Self->{obj_dir}/simx.vcd", qr/var/);
|
||||||
|
|
||||||
|
ok(1);
|
||||||
|
1;
|
||||||
|
|
@ -0,0 +1,26 @@
|
||||||
|
// DESCRIPTION: Verilator: Verilog Test module
|
||||||
|
//
|
||||||
|
// This file ONLY is placed under the Creative Commons Public Domain, for
|
||||||
|
// any use, without warranty, 2021 by Geza Lore.
|
||||||
|
// SPDX-License-Identifier: CC0-1.0
|
||||||
|
|
||||||
|
module t(/*AUTOARG*/
|
||||||
|
// Inputs
|
||||||
|
clk
|
||||||
|
);
|
||||||
|
|
||||||
|
/* verilator tracing_off */
|
||||||
|
|
||||||
|
input clk;
|
||||||
|
|
||||||
|
reg [7:0] cyc = 8'd0;
|
||||||
|
|
||||||
|
always @(posedge clk) begin
|
||||||
|
cyc <= cyc + 1;
|
||||||
|
if (cyc == 20) begin
|
||||||
|
$write("*-* All Finished *-*\n");
|
||||||
|
$finish;
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
endmodule
|
||||||
Loading…
Reference in New Issue