Internals: Refector to create single V3Number::emitC. Fix some double emit issues (#6528).
This commit is contained in:
parent
a03d327e96
commit
f09c30df35
|
|
@ -29,7 +29,6 @@
|
|||
class EmitCConstInit VL_NOT_FINAL : public EmitCBaseVisitorConst {
|
||||
// MEMBERS
|
||||
uint32_t m_unpackedWord = 0;
|
||||
bool m_inUnpacked = false;
|
||||
|
||||
// METHODS
|
||||
uint32_t tabModulus(const AstNodeDType* dtypep) {
|
||||
|
|
@ -44,9 +43,7 @@ class EmitCConstInit VL_NOT_FINAL : public EmitCBaseVisitorConst {
|
|||
protected:
|
||||
// VISITORS
|
||||
void visit(AstInitArray* nodep) override {
|
||||
VL_RESTORER(m_inUnpacked);
|
||||
VL_RESTORER(m_unpackedWord);
|
||||
m_inUnpacked = true;
|
||||
if (VN_IS(nodep->dtypep()->skipRefp(), AssocArrayDType)) {
|
||||
// Note the double {{ initializer. The first { starts the initializer of the
|
||||
// VlAssocArray, and the second starts the initializer of m_storage within the
|
||||
|
|
@ -98,55 +95,9 @@ protected:
|
|||
} // LCOV_EXCL_STOP
|
||||
|
||||
void visit(AstConst* nodep) override {
|
||||
// TODO merge with EmitCFunc::emitConstant
|
||||
const V3Number& num = nodep->num();
|
||||
UASSERT_OBJ(!num.isFourState(), nodep, "4-state value in constant pool");
|
||||
const AstNodeDType* const dtypep = nodep->dtypep();
|
||||
if (num.isNull()) {
|
||||
putns(nodep, "VlNull{}");
|
||||
} else if (num.isString()) {
|
||||
// Note: putsQuoted does not track indentation, so we use this instead
|
||||
putns(nodep, "\"");
|
||||
puts(num.toString());
|
||||
puts("\"");
|
||||
} else if (dtypep->isWide()) {
|
||||
const uint32_t size = dtypep->widthWords();
|
||||
// Note the double {{ initializer. The first { starts the initializer of the VlWide,
|
||||
// and the second starts the initializer of m_storage within the VlWide.
|
||||
putns(nodep, "{");
|
||||
ofp()->putsNoTracking("{");
|
||||
if (m_inUnpacked) puts(" // VlWide " + cvtToStr(m_unpackedWord));
|
||||
puts("\n");
|
||||
for (uint32_t n = 0; n < size; ++n) {
|
||||
if (n) puts((n % 4) ? ", " : ",\n");
|
||||
ofp()->printf("0x%08" PRIx32, num.edataWord(n));
|
||||
}
|
||||
puts("\n");
|
||||
puts("}");
|
||||
ofp()->putsNoTracking("}");
|
||||
} else if (dtypep->isDouble()) {
|
||||
const double dnum = num.toDouble();
|
||||
const char* const fmt
|
||||
= !m_inUnpacked && (static_cast<int>(dnum) == dnum && -1000 < dnum && dnum < 1000)
|
||||
? "%3.1f" // Force decimal point
|
||||
: "%.17e"; // %e always yields a float literal
|
||||
putns(nodep, "");
|
||||
ofp()->printf(fmt, dnum);
|
||||
} else if (dtypep->isQuad()) {
|
||||
const uint64_t qnum = static_cast<uint64_t>(num.toUQuad());
|
||||
const char* const fmt
|
||||
= !m_inUnpacked && (qnum < 10) ? ("%" PRIx64 "ULL") : ("0x%016" PRIx64 "ULL");
|
||||
putns(nodep, "");
|
||||
ofp()->printf(fmt, qnum);
|
||||
} else {
|
||||
const uint32_t unum = num.toUInt();
|
||||
const char* const fmt = !m_inUnpacked && (unum < 10) ? ("%" PRIu32 "U")
|
||||
: (dtypep->widthMin() > 16) ? ("0x%08" PRIx32 "U")
|
||||
: (dtypep->widthMin() > 8) ? ("0x%04" PRIx32 "U")
|
||||
: ("0x%02" PRIx32 "U");
|
||||
putns(nodep, "");
|
||||
ofp()->printf(fmt, unum);
|
||||
}
|
||||
putns(nodep, num.emitC());
|
||||
}
|
||||
|
||||
// Default
|
||||
|
|
|
|||
|
|
@ -488,111 +488,14 @@ void EmitCFunc::emitCvtWideArray(AstNode* nodep, AstNode* fromp) {
|
|||
puts(")");
|
||||
}
|
||||
|
||||
void EmitCFunc::emitConstant(AstConst* nodep, AstVarRef* assigntop, const string& assignString) {
|
||||
void EmitCFunc::emitConstant(AstConst* nodep) {
|
||||
// Put out constant set to the specified variable, or given variable in a string
|
||||
// TODO merge with V3EmitCConstInit::visit(AstConst)
|
||||
putns(nodep, "");
|
||||
if (nodep->num().isNull()) {
|
||||
putns(nodep, "VlNull{}");
|
||||
} else if (nodep->num().isFourState()) {
|
||||
const V3Number& num = nodep->num();
|
||||
if (num.isFourState()) {
|
||||
nodep->v3warn(E_UNSUPPORTED, "Unsupported: 4-state numbers in this context");
|
||||
} else if (nodep->num().isString()) {
|
||||
emitConstantString(nodep);
|
||||
} else if (nodep->isWide()) {
|
||||
int upWidth = nodep->num().widthToFit();
|
||||
int chunks = 0;
|
||||
if (upWidth > EMITC_NUM_CONSTW * VL_EDATASIZE) {
|
||||
// Output e.g. 8 words in groups of e.g. 8
|
||||
chunks = (upWidth - 1) / (EMITC_NUM_CONSTW * VL_EDATASIZE);
|
||||
upWidth %= (EMITC_NUM_CONSTW * VL_EDATASIZE);
|
||||
if (upWidth == 0) upWidth = (EMITC_NUM_CONSTW * VL_EDATASIZE);
|
||||
}
|
||||
{ // Upper e.g. 8 words
|
||||
if (chunks) {
|
||||
putnbs(nodep, "VL_CONSTHI_W_");
|
||||
puts(cvtToStr(VL_WORDS_I(upWidth)));
|
||||
puts("X(");
|
||||
puts(cvtToStr(nodep->widthMin()));
|
||||
puts(",");
|
||||
puts(cvtToStr(chunks * EMITC_NUM_CONSTW * VL_EDATASIZE));
|
||||
} else {
|
||||
putnbs(nodep, "VL_CONST_W_");
|
||||
puts(cvtToStr(VL_WORDS_I(upWidth)));
|
||||
puts("X(");
|
||||
puts(cvtToStr(nodep->widthMin()));
|
||||
}
|
||||
puts(",");
|
||||
if (!assigntop) {
|
||||
puts(assignString);
|
||||
} else {
|
||||
if (!assigntop->selfPointer().isEmpty()) {
|
||||
emitDereference(assigntop, assigntop->selfPointerProtect(m_useSelfForThis));
|
||||
}
|
||||
puts(assigntop->varp()->nameProtect());
|
||||
}
|
||||
for (int word = VL_WORDS_I(upWidth) - 1; word >= 0; word--) {
|
||||
// Only 32 bits - llx + long long here just to appease CPP format warning
|
||||
ofp()->printf(",0x%08" PRIx64, static_cast<uint64_t>(nodep->num().edataWord(
|
||||
word + chunks * EMITC_NUM_CONSTW)));
|
||||
}
|
||||
puts(")");
|
||||
}
|
||||
for (chunks--; chunks >= 0; chunks--) {
|
||||
puts(";\n");
|
||||
putbs("VL_CONSTLO_W_");
|
||||
puts(cvtToStr(EMITC_NUM_CONSTW));
|
||||
puts("X(");
|
||||
puts(cvtToStr(chunks * EMITC_NUM_CONSTW * VL_EDATASIZE));
|
||||
puts(",");
|
||||
if (!assigntop) {
|
||||
puts(assignString);
|
||||
} else {
|
||||
if (!assigntop->selfPointer().isEmpty()) {
|
||||
emitDereference(assigntop, assigntop->selfPointerProtect(m_useSelfForThis));
|
||||
}
|
||||
puts(assigntop->varp()->nameProtect());
|
||||
}
|
||||
for (int word = EMITC_NUM_CONSTW - 1; word >= 0; word--) {
|
||||
// Only 32 bits - llx + long long here just to appease CPP format warning
|
||||
ofp()->printf(",0x%08" PRIx64, static_cast<uint64_t>(nodep->num().edataWord(
|
||||
word + chunks * EMITC_NUM_CONSTW)));
|
||||
}
|
||||
puts(")");
|
||||
}
|
||||
} else if (nodep->isDouble()) {
|
||||
if (int(nodep->num().toDouble()) == nodep->num().toDouble()
|
||||
&& nodep->num().toDouble() < 1000 && nodep->num().toDouble() > -1000) {
|
||||
ofp()->printf("%3.1f", nodep->num().toDouble()); // Force decimal point
|
||||
} else if (std::isinf(nodep->num().toDouble())) {
|
||||
if (std::signbit(nodep->num().toDouble())) puts("-");
|
||||
ofp()->puts("std::numeric_limits<double>::infinity()");
|
||||
} else if (std::isnan(nodep->num().toDouble())) {
|
||||
if (std::signbit(nodep->num().toDouble())) puts("-");
|
||||
ofp()->puts("std::numeric_limits<double>::quiet_NaN()");
|
||||
} else {
|
||||
// Not %g as will not always put in decimal point, so not obvious to compiler
|
||||
// is a real number
|
||||
ofp()->printf("%.17e", nodep->num().toDouble());
|
||||
}
|
||||
} else if (nodep->isQuad()) {
|
||||
const uint64_t num = nodep->toUQuad();
|
||||
if (num < 10) {
|
||||
ofp()->printf("%" PRIu64 "ULL", num);
|
||||
} else {
|
||||
ofp()->printf("0x%" PRIx64 "ULL", num);
|
||||
}
|
||||
} else {
|
||||
const uint32_t num = nodep->toUInt();
|
||||
// Only 32 bits - llx + long long here just to appease CPP format warning
|
||||
if (num < 10) {
|
||||
puts(cvtToStr(num));
|
||||
} else {
|
||||
ofp()->printf("0x%" PRIx64, static_cast<uint64_t>(num));
|
||||
}
|
||||
// If signed, we'll do our own functions
|
||||
// But must be here, or <= comparisons etc may end up signed
|
||||
puts("U");
|
||||
return;
|
||||
}
|
||||
putns(nodep, num.emitC());
|
||||
}
|
||||
|
||||
void EmitCFunc::emitConstantString(const AstConst* nodep) {
|
||||
|
|
@ -604,11 +507,9 @@ void EmitCFunc::emitConstantString(const AstConst* nodep) {
|
|||
}
|
||||
|
||||
void EmitCFunc::emitSetVarConstant(const string& assignString, AstConst* constp) {
|
||||
if (!constp->isWide()) {
|
||||
puts(assignString);
|
||||
puts(" = ");
|
||||
}
|
||||
emitConstant(constp, nullptr, assignString);
|
||||
puts(assignString);
|
||||
puts(" = ");
|
||||
emitConstant(constp);
|
||||
puts(";\n");
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -120,7 +120,6 @@ class EmitCFunc VL_NOT_FINAL : public EmitCConstInit {
|
|||
AstVarRef* m_wideTempRefp = nullptr; // Variable that _WW macros should be setting
|
||||
std::unordered_map<AstJumpBlock*, size_t> m_labelNumbers; // Label numbers for AstJumpBlocks
|
||||
bool m_inUC = false; // Inside an AstUCStmt or AstUCExpr
|
||||
bool m_emitConstInit = false; // Emitting constant initializer
|
||||
bool m_createdScopeHash = false; // Already created a scope hash
|
||||
|
||||
// State associated with processing $display style string formatting
|
||||
|
|
@ -221,7 +220,7 @@ public:
|
|||
void emitDereference(AstNode* nodep, const string& pointer);
|
||||
void emitCvtPackStr(AstNode* nodep);
|
||||
void emitCvtWideArray(AstNode* nodep, AstNode* fromp);
|
||||
void emitConstant(AstConst* nodep, AstVarRef* assigntop, const string& assignString);
|
||||
void emitConstant(AstConst* nodep);
|
||||
void emitConstantString(const AstConst* nodep);
|
||||
void emitSetVarConstant(const string& assignString, AstConst* constp);
|
||||
void emitVarReset(AstVar* varp, bool constructing);
|
||||
|
|
@ -230,13 +229,7 @@ public:
|
|||
const string& suffix);
|
||||
void emitVarResetScopeHash();
|
||||
void emitChangeDet();
|
||||
void emitConstInit(AstNode* initp) {
|
||||
// We should refactor emit to produce output into a provided buffer, not go through members
|
||||
// variables. That way we could just invoke the appropriate emitter as needed.
|
||||
VL_RESTORER(m_emitConstInit);
|
||||
m_emitConstInit = true;
|
||||
iterateConst(initp);
|
||||
}
|
||||
void emitConstInit(AstNode* initp) { iterateConst(initp); }
|
||||
void putCommaIterateNext(AstNode* nodep, bool comma = false) {
|
||||
for (AstNode* subnodep = nodep; subnodep; subnodep = subnodep->nextp()) {
|
||||
if (comma) puts(", ");
|
||||
|
|
@ -263,6 +256,70 @@ public:
|
|||
if (const AstCNew* const cnewp = getSuperNewCallRecursep(nodep->nextp())) return cnewp;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void emitConstantW(AstConst* nodep, AstVarRef* assigntop) {
|
||||
// For tradition and compilation speed, assign each word directly into
|
||||
// output variable instead of using '='
|
||||
putns(nodep, "");
|
||||
if (nodep->num().isFourState()) {
|
||||
nodep->v3warn(E_UNSUPPORTED, "Unsupported: 4-state numbers in this context");
|
||||
return;
|
||||
}
|
||||
|
||||
int upWidth = nodep->num().widthToFit();
|
||||
int chunks = 0;
|
||||
if (upWidth > EMITC_NUM_CONSTW * VL_EDATASIZE) {
|
||||
// Output e.g. 8 words in groups of e.g. 8
|
||||
chunks = (upWidth - 1) / (EMITC_NUM_CONSTW * VL_EDATASIZE);
|
||||
upWidth %= (EMITC_NUM_CONSTW * VL_EDATASIZE);
|
||||
if (upWidth == 0) upWidth = (EMITC_NUM_CONSTW * VL_EDATASIZE);
|
||||
}
|
||||
{ // Upper e.g. 8 words
|
||||
if (chunks) {
|
||||
putnbs(nodep, "VL_CONSTHI_W_");
|
||||
puts(cvtToStr(VL_WORDS_I(upWidth)));
|
||||
puts("X(");
|
||||
puts(cvtToStr(nodep->widthMin()));
|
||||
puts(",");
|
||||
puts(cvtToStr(chunks * EMITC_NUM_CONSTW * VL_EDATASIZE));
|
||||
} else {
|
||||
putnbs(nodep, "VL_CONST_W_");
|
||||
puts(cvtToStr(VL_WORDS_I(upWidth)));
|
||||
puts("X(");
|
||||
puts(cvtToStr(nodep->widthMin()));
|
||||
}
|
||||
puts(",");
|
||||
if (!assigntop->selfPointer().isEmpty()) {
|
||||
emitDereference(assigntop, assigntop->selfPointerProtect(m_useSelfForThis));
|
||||
}
|
||||
puts(assigntop->varp()->nameProtect());
|
||||
for (int word = VL_WORDS_I(upWidth) - 1; word >= 0; word--) {
|
||||
// Only 32 bits - llx + long long here just to appease CPP format warning
|
||||
ofp()->printf(",0x%08" PRIx64, static_cast<uint64_t>(nodep->num().edataWord(
|
||||
word + chunks * EMITC_NUM_CONSTW)));
|
||||
}
|
||||
puts(")");
|
||||
}
|
||||
for (chunks--; chunks >= 0; chunks--) {
|
||||
puts(";\n");
|
||||
putbs("VL_CONSTLO_W_");
|
||||
puts(cvtToStr(EMITC_NUM_CONSTW));
|
||||
puts("X(");
|
||||
puts(cvtToStr(chunks * EMITC_NUM_CONSTW * VL_EDATASIZE));
|
||||
puts(",");
|
||||
if (!assigntop->selfPointer().isEmpty()) {
|
||||
emitDereference(assigntop, assigntop->selfPointerProtect(m_useSelfForThis));
|
||||
}
|
||||
puts(assigntop->varp()->nameProtect());
|
||||
for (int word = EMITC_NUM_CONSTW - 1; word >= 0; word--) {
|
||||
// Only 32 bits - llx + long long here just to appease CPP format warning
|
||||
ofp()->printf(",0x%08" PRIx64, static_cast<uint64_t>(nodep->num().edataWord(
|
||||
word + chunks * EMITC_NUM_CONSTW)));
|
||||
}
|
||||
puts(")");
|
||||
}
|
||||
}
|
||||
|
||||
void putConstructorSubinit(const AstClass* classp, AstCFunc* cfuncp) {
|
||||
// Virtual bases in depth-first left-to-right order
|
||||
std::vector<AstClass*> virtualBases;
|
||||
|
|
@ -549,6 +606,9 @@ public:
|
|||
} else if (nodep->isWide() && VN_IS(nodep->lhsp(), VarRef) //
|
||||
&& !VN_IS(nodep->rhsp(), CExpr) //
|
||||
&& !VN_IS(nodep->rhsp(), CMethodHard) //
|
||||
// Although not here currently, note putting !VN_IS(Const) works,
|
||||
// and means using '=' and bypasses using emitConstantW.
|
||||
// Whuch we don't want to do as slows compiler down.
|
||||
&& !VN_IS(nodep->rhsp(), VarRef) //
|
||||
&& !VN_IS(nodep->rhsp(), AssocSel) //
|
||||
&& !VN_IS(nodep->rhsp(), MemberSel) //
|
||||
|
|
@ -558,7 +618,8 @@ public:
|
|||
// Wide functions assign into the array directly, don't need separate assign statement
|
||||
m_wideTempRefp = VN_AS(nodep->lhsp(), VarRef);
|
||||
paren = false;
|
||||
} else if (nodep->isWide() && !VN_IS(nodep->dtypep()->skipRefp(), UnpackArrayDType)) {
|
||||
} else if (nodep->isWide() && !VN_IS(nodep->dtypep()->skipRefp(), UnpackArrayDType)
|
||||
&& !VN_IS(nodep->rhsp(), Const)) {
|
||||
putnbs(nodep, "VL_ASSIGN_W(");
|
||||
puts(cvtToStr(nodep->widthMin()) + ", ");
|
||||
iterateAndNextConstNull(nodep->lhsp());
|
||||
|
|
@ -1519,15 +1580,13 @@ public:
|
|||
putns(nodep, "&");
|
||||
puts(funcNameProtect(funcp));
|
||||
}
|
||||
void visit(AstConst* nodep) override {
|
||||
if (m_emitConstInit) {
|
||||
EmitCConstInit::visit(nodep);
|
||||
} else if (nodep->isWide()) {
|
||||
void visit(AstConst* nodep) override { //
|
||||
if (m_wideTempRefp && nodep->isWide()) {
|
||||
UASSERT_OBJ(m_wideTempRefp, nodep, "Wide Constant w/ no temp");
|
||||
emitConstant(nodep, m_wideTempRefp, "");
|
||||
emitConstantW(nodep, m_wideTempRefp);
|
||||
m_wideTempRefp = nullptr; // We used it, fail if set it a second time
|
||||
} else {
|
||||
emitConstant(nodep, nullptr, "");
|
||||
emitConstant(nodep);
|
||||
}
|
||||
}
|
||||
void visit(AstThisRef* nodep) override {
|
||||
|
|
|
|||
|
|
@ -18,6 +18,8 @@
|
|||
|
||||
#include "V3Number.h"
|
||||
|
||||
#include "V3File.h"
|
||||
|
||||
#include <algorithm>
|
||||
#include <cerrno>
|
||||
#include <cmath>
|
||||
|
|
@ -877,6 +879,65 @@ string V3Number::displayed(FileLine* fl, const string& vformat) const VL_MT_STAB
|
|||
}
|
||||
}
|
||||
|
||||
string V3Number::emitC() const VL_MT_STABLE {
|
||||
constexpr size_t bufsize = 1000;
|
||||
char sbuf[bufsize];
|
||||
string result;
|
||||
if (isNull()) {
|
||||
return "VlNull{}";
|
||||
} else if (isDouble()) {
|
||||
const double dnum = toDouble();
|
||||
if (std::isinf(dnum)) {
|
||||
if (std::signbit(dnum)) result += '-';
|
||||
result += "std::numeric_limits<double>::infinity()";
|
||||
} else if (std::isnan(dnum)) {
|
||||
if (std::signbit(dnum)) result += '-';
|
||||
result += "std::numeric_limits<double>::quiet_NaN()";
|
||||
} else {
|
||||
const char* const fmt = (static_cast<int>(dnum) == dnum && -1000 < dnum && dnum < 1000)
|
||||
? "%3.1f" // Force decimal point
|
||||
: "%.17e"; // %e always yields a float literal
|
||||
VL_SNPRINTF(sbuf, bufsize, fmt, dnum);
|
||||
return sbuf;
|
||||
}
|
||||
} else if (isString()) {
|
||||
const string strg = toString();
|
||||
const string quoted
|
||||
= V3OutFormatter::quoteNameControls(strg, V3OutFormatter::Language::LA_C);
|
||||
// Note: putsQuoted does not track indentation, so we use this instead
|
||||
return '"' + quoted + "\"s";
|
||||
} else if (words() > 2) {
|
||||
// Note the double {{ initializer. The first { starts the initializer of the VlWide,
|
||||
// and the second starts the initializer of m_storage within the VlWide.
|
||||
// Alternative is to have constructor with std::initializer_list
|
||||
result = "VlWide<" + std::to_string(words()) + ">{{";
|
||||
if (words() > 4) result += '\n';
|
||||
for (int n = 0; n < words(); ++n) {
|
||||
if (n) result += ((n % 4) ? ", " : ",\n");
|
||||
VL_SNPRINTF(sbuf, bufsize, "0x%08" PRIx32, edataWord(n));
|
||||
result += sbuf;
|
||||
}
|
||||
if (words() > 4) result += '\n';
|
||||
result += "}}";
|
||||
} else if (words() == 2) { // Quad
|
||||
const uint64_t qnum = static_cast<uint64_t>(toUQuad());
|
||||
const char* const fmt = (qnum < 10) ? ("%" PRIx64 "ULL") : ("0x%016" PRIx64 "ULL");
|
||||
VL_SNPRINTF(sbuf, bufsize, fmt, qnum);
|
||||
return sbuf;
|
||||
} else {
|
||||
// Always emit unsigned, if signed, will call correct signed functions
|
||||
// The 'U' must be here, to avoid <= comparisons etc ending up signed
|
||||
const uint32_t unum = toUInt();
|
||||
const char* const fmt = (unum < 10) ? ("%" PRIu32 "U")
|
||||
: (width() > 16) ? ("0x%08" PRIx32 "U")
|
||||
: (width() > 8) ? ("0x%04" PRIx32 "U")
|
||||
: ("0x%02" PRIx32 "U");
|
||||
VL_SNPRINTF(sbuf, bufsize, fmt, unum);
|
||||
return sbuf;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
string V3Number::toDecimalS() const VL_MT_STABLE {
|
||||
// Correct number of zero bits/width matters
|
||||
if (isNegative()) {
|
||||
|
|
|
|||
|
|
@ -595,6 +595,7 @@ public:
|
|||
string displayed(const AstNode* nodep, const string& vformat) const VL_MT_STABLE;
|
||||
string displayed(FileLine* fl, const string& vformat) const VL_MT_STABLE;
|
||||
static bool displayedFmtLegal(char format, bool isScan); // Is this a valid format letter?
|
||||
string emitC() const VL_MT_STABLE;
|
||||
int width() const VL_MT_SAFE { return m_data.width(); }
|
||||
int widthToFit() const; // Minimum width that can represent this number (~== log2(num)+1)
|
||||
bool sized() const VL_MT_SAFE { return m_data.m_sized; }
|
||||
|
|
|
|||
|
|
@ -898,7 +898,7 @@ int _mon_check_putget_str(p_cb_data cb_data) {
|
|||
// setup and install
|
||||
for (int i = 1; i <= 6; i++) {
|
||||
char buf[32];
|
||||
snprintf(buf, sizeof(buf), TestSimulator::rooted("arr[%d].arr"), i);
|
||||
VL_SNPRINTF(buf, sizeof(buf), TestSimulator::rooted("arr[%d].arr"), i);
|
||||
CHECK_RESULT_NZ(data[i].scope = vpi_handle_by_name((PLI_BYTE8*)buf, NULL));
|
||||
CHECK_RESULT_NZ(data[i].sig = vpi_handle_by_name((PLI_BYTE8*)"sig", data[i].scope));
|
||||
CHECK_RESULT_NZ(data[i].rfr = vpi_handle_by_name((PLI_BYTE8*)"rfr", data[i].scope));
|
||||
|
|
@ -910,7 +910,7 @@ int _mon_check_putget_str(p_cb_data cb_data) {
|
|||
|
||||
for (int i = 1; i <= 6; i++) {
|
||||
char buf[32];
|
||||
snprintf(buf, sizeof(buf), TestSimulator::rooted("subs[%d].subsub"), i);
|
||||
VL_SNPRINTF(buf, sizeof(buf), TestSimulator::rooted("subs[%d].subsub"), i);
|
||||
CHECK_RESULT_NZ(data[i].scope = vpi_handle_by_name((PLI_BYTE8*)buf, NULL));
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue