mirror of
https://github.com/verilator/verilator.git
synced 2025-01-01 04:07:34 +00:00
Internals: Refactor into V3Width enumSelect function
This commit is contained in:
parent
13c7b6e827
commit
b873c23cf2
@ -3326,27 +3326,9 @@ class WidthVisitor final : public VNVisitor {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// Need a runtime lookup table. Yuk.
|
AstNodeExpr* const newp
|
||||||
const uint64_t msbdim = enumMaxValue(nodep, adtypep);
|
= enumSelect(nodep->fromp()->unlinkFrBack(), adtypep, attrType);
|
||||||
const bool assoc = msbdim > ENUM_LOOKUP_BITS;
|
nodep->replaceWith(newp);
|
||||||
if (assoc) {
|
|
||||||
AstVar* const varp = enumVarp(adtypep, attrType, true, 0);
|
|
||||||
AstNode* const newp = new AstAssocSel{nodep->fileline(), newVarRefDollarUnit(varp),
|
|
||||||
nodep->fromp()->unlinkFrBack()};
|
|
||||||
newp->dtypeFrom(adtypep); // To prevent a later ENUMVALUE
|
|
||||||
nodep->replaceWith(newp);
|
|
||||||
} else {
|
|
||||||
const int selwidth = V3Number::log2b(msbdim) + 1; // Width to address a bit
|
|
||||||
AstVar* const varp = enumVarp(adtypep, attrType, false, (1ULL << selwidth) - 1);
|
|
||||||
AstNode* const newp = new AstArraySel{
|
|
||||||
nodep->fileline(), newVarRefDollarUnit(varp),
|
|
||||||
// Select in case widths are off due to msblen!=width
|
|
||||||
// We return "random" values if outside the range, which is fine
|
|
||||||
// as next/previous on illegal values just need something good out
|
|
||||||
new AstSel{nodep->fileline(), nodep->fromp()->unlinkFrBack(), 0, selwidth}};
|
|
||||||
newp->dtypeFrom(adtypep); // To prevent a later ENUMVALUE
|
|
||||||
nodep->replaceWith(newp);
|
|
||||||
}
|
|
||||||
VL_DO_DANGLING(nodep->deleteTree(), nodep);
|
VL_DO_DANGLING(nodep->deleteTree(), nodep);
|
||||||
} else {
|
} else {
|
||||||
nodep->v3error("Unknown built-in enum method " << nodep->prettyNameQ());
|
nodep->v3error("Unknown built-in enum method " << nodep->prettyNameQ());
|
||||||
@ -7764,6 +7746,30 @@ class WidthVisitor final : public VNVisitor {
|
|||||||
}
|
}
|
||||||
return pair.first->second;
|
return pair.first->second;
|
||||||
}
|
}
|
||||||
|
AstNodeExpr* enumSelect(AstNodeExpr* nodep, AstEnumDType* adtypep, VAttrType attrType) {
|
||||||
|
// Return expression to get given attrType information from a enum's value (nodep)
|
||||||
|
// Need a runtime lookup table. Yuk.
|
||||||
|
const uint64_t msbdim = enumMaxValue(nodep, adtypep);
|
||||||
|
const bool assoc = msbdim > ENUM_LOOKUP_BITS;
|
||||||
|
if (assoc) {
|
||||||
|
AstVar* const varp = enumVarp(adtypep, attrType, true, 0);
|
||||||
|
AstNodeExpr* const newp
|
||||||
|
= new AstAssocSel{nodep->fileline(), newVarRefDollarUnit(varp), nodep};
|
||||||
|
newp->dtypeFrom(adtypep); // To prevent a later ENUMVALUE
|
||||||
|
return newp;
|
||||||
|
} else {
|
||||||
|
const int selwidth = V3Number::log2b(msbdim) + 1; // Width to address a bit
|
||||||
|
AstVar* const varp = enumVarp(adtypep, attrType, false, (1ULL << selwidth) - 1);
|
||||||
|
AstNodeExpr* const newp = new AstArraySel{
|
||||||
|
nodep->fileline(), newVarRefDollarUnit(varp),
|
||||||
|
// Select in case widths are off due to msblen!=width
|
||||||
|
// We return "random" values if outside the range, which is fine
|
||||||
|
// as next/previous on illegal values just need something good out
|
||||||
|
new AstSel{nodep->fileline(), nodep, 0, selwidth}};
|
||||||
|
newp->dtypeFrom(adtypep); // To prevent a later ENUMVALUE
|
||||||
|
return newp;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
PatVecMap patVectorMap(AstPattern* nodep, const VNumRange& range) {
|
PatVecMap patVectorMap(AstPattern* nodep, const VNumRange& range) {
|
||||||
PatVecMap patmap;
|
PatVecMap patmap;
|
||||||
|
@ -1,9 +1,8 @@
|
|||||||
%Error: t/t_enum_huge_methods_bad.v:15:18: Value too wide for 64-bits expected in this context 160'h12344567abcd12344567abcd
|
%Error: t/t_enum_huge_methods_bad.v:15:18: Value too wide for 64-bits expected in this context 160'h12344567abcd12344567abcd
|
||||||
15 | ELARGE = 160'h1234_4567_abcd_1234_4567_abcd
|
15 | ELARGE = 160'h1234_4567_abcd_1234_4567_abcd
|
||||||
| ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
| ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||||
%Error-UNSUPPORTED: t/t_enum_huge_methods_bad.v:30:21: Unsupported: enum next/prev/name method on enum with > 64 bits
|
%Error-UNSUPPORTED: t/t_enum_huge_methods_bad.v:30:19: Unsupported: enum next/prev/name method on enum with > 64 bits
|
||||||
: ... note: In instance 't'
|
|
||||||
30 | $display(e.name);
|
30 | $display(e.name);
|
||||||
| ^~~~
|
| ^
|
||||||
... For error description see https://verilator.org/warn/UNSUPPORTED?v=latest
|
... For error description see https://verilator.org/warn/UNSUPPORTED?v=latest
|
||||||
%Error: Exiting due to
|
%Error: Exiting due to
|
||||||
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue
Block a user