Support <number>'() sized casts, bug628.
This commit is contained in:
parent
7bd96c2876
commit
a767da4f3f
2
Changes
2
Changes
|
|
@ -20,6 +20,8 @@ indicates the contributor was also the author of the fix; Thanks!
|
||||||
|
|
||||||
**** Support bind in $unit, bug602. [Ed Lander]
|
**** Support bind in $unit, bug602. [Ed Lander]
|
||||||
|
|
||||||
|
**** Support <number>'() sized casts, bug628. [Ed Lander]
|
||||||
|
|
||||||
**** Fix DETECTARRAY on packed structures, bug610. [Jeremy Bennett]
|
**** Fix DETECTARRAY on packed structures, bug610. [Jeremy Bennett]
|
||||||
|
|
||||||
**** Fix LITENDIAN on unpacked structures, bug614. [Wai Sum Mong]
|
**** Fix LITENDIAN on unpacked structures, bug614. [Wai Sum Mong]
|
||||||
|
|
|
||||||
|
|
@ -3184,6 +3184,20 @@ struct AstCast : public AstNode {
|
||||||
AstNodeDType* childDTypep() const { return op2p()->castNodeDType(); }
|
AstNodeDType* childDTypep() const { return op2p()->castNodeDType(); }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct AstCastSize : public AstNode {
|
||||||
|
// Cast to specific size; signed/twostate inherited from lower element per IEEE
|
||||||
|
AstCastSize(FileLine* fl, AstNode* lhsp, AstConst* rhsp) : AstNode(fl) {
|
||||||
|
setOp1p(lhsp); setOp2p(rhsp);
|
||||||
|
}
|
||||||
|
ASTNODE_NODE_FUNCS(CastSize, CASTSIZE)
|
||||||
|
virtual string emitVerilog() { return "((%r)'(%l))"; }
|
||||||
|
virtual string emitC() { V3ERROR_NA; return ""; }
|
||||||
|
virtual bool cleanOut() { V3ERROR_NA; return true;} virtual bool cleanLhs() {return true;}
|
||||||
|
virtual bool sizeMattersLhs() {return false;}
|
||||||
|
AstNode* lhsp() const { return op1p(); }
|
||||||
|
AstNode* rhsp() const { return op2p(); }
|
||||||
|
};
|
||||||
|
|
||||||
struct AstCCast : public AstNodeUniop {
|
struct AstCCast : public AstNodeUniop {
|
||||||
// Cast to C-based data type
|
// Cast to C-based data type
|
||||||
private:
|
private:
|
||||||
|
|
|
||||||
|
|
@ -805,6 +805,28 @@ private:
|
||||||
pushDeletep(nodep); nodep=NULL;
|
pushDeletep(nodep); nodep=NULL;
|
||||||
//if (debug()) newp->dumpTree(cout," CastOut: ");
|
//if (debug()) newp->dumpTree(cout," CastOut: ");
|
||||||
}
|
}
|
||||||
|
virtual void visit(AstCastSize* nodep, AstNUser* vup) {
|
||||||
|
if (!nodep->rhsp()->castConst()) nodep->v3fatalSrc("Unsupported: Non-const cast of size");
|
||||||
|
//if (debug()) nodep->dumpTree(cout," CastPre: ");
|
||||||
|
int width = nodep->rhsp()->castConst()->toSInt();
|
||||||
|
if (width < 1) { nodep->v3error("Size-changing cast to zero or negative size"); width=1; }
|
||||||
|
nodep->lhsp()->iterateAndNext(*this,WidthVP(ANYSIZE,0,BOTH).p());
|
||||||
|
AstBasicDType* underDtp = nodep->lhsp()->dtypep()->castBasicDType();
|
||||||
|
if (!underDtp) {
|
||||||
|
nodep->v3error("Unsupported: Size-changing cast on non-basic data type");
|
||||||
|
underDtp = nodep->findLogicBoolDType()->castBasicDType();
|
||||||
|
}
|
||||||
|
AstNodeDType* newDtp = (underDtp->keyword().isFourstate()
|
||||||
|
? nodep->findLogicDType(width, width, underDtp->numeric())
|
||||||
|
: nodep->findBitDType(width, width, underDtp->numeric()));
|
||||||
|
nodep->dtypep(newDtp);
|
||||||
|
AstNode* underp = nodep->lhsp()->unlinkFrBack();
|
||||||
|
nodep->replaceWith(underp);
|
||||||
|
if (underp->width()!=width) {
|
||||||
|
fixWidthExtend(underp, newDtp);
|
||||||
|
}
|
||||||
|
pushDeletep(nodep); nodep=NULL;
|
||||||
|
}
|
||||||
virtual void visit(AstVar* nodep, AstNUser* vup) {
|
virtual void visit(AstVar* nodep, AstNUser* vup) {
|
||||||
//if (debug()) nodep->dumpTree(cout," InitPre: ");
|
//if (debug()) nodep->dumpTree(cout," InitPre: ");
|
||||||
// Must have deterministic constant width
|
// Must have deterministic constant width
|
||||||
|
|
|
||||||
|
|
@ -2825,6 +2825,7 @@ expr<nodep>: // IEEE: part of expression/constant_expression/primary
|
||||||
// // Spec only allows primary with addition of a type reference
|
// // Spec only allows primary with addition of a type reference
|
||||||
// // We'll be more general, and later assert LHS was a type.
|
// // We'll be more general, and later assert LHS was a type.
|
||||||
//UNSUP ~l~expr yP_TICK '(' expr ')' { UNSUP }
|
//UNSUP ~l~expr yP_TICK '(' expr ')' { UNSUP }
|
||||||
|
| yaINTNUM yP_TICK '(' expr ')' { $$ = new AstCastSize($2,$4,new AstConst($1->fileline(),*$1)); }
|
||||||
//
|
//
|
||||||
// // IEEE: assignment_pattern_expression
|
// // IEEE: assignment_pattern_expression
|
||||||
// // IEEE: streaming_concatenation
|
// // IEEE: streaming_concatenation
|
||||||
|
|
|
||||||
|
|
@ -10,11 +10,14 @@ module t;
|
||||||
|
|
||||||
mc_t o;
|
mc_t o;
|
||||||
|
|
||||||
|
logic [15:0] allones = 16'hffff;
|
||||||
|
|
||||||
initial begin
|
initial begin
|
||||||
if (4'shf > 4'sh0) $stop;
|
if (4'shf > 4'sh0) $stop;
|
||||||
if (signed'(4'hf) > 4'sh0) $stop;
|
if (signed'(4'hf) > 4'sh0) $stop;
|
||||||
if (4'hf < 4'h0) $stop;
|
if (4'hf < 4'h0) $stop;
|
||||||
if (unsigned'(4'shf) < 4'h0) $stop;
|
if (unsigned'(4'shf) < 4'h0) $stop;
|
||||||
|
if (4'(allones) !== 4'hf) $stop;
|
||||||
|
|
||||||
o = tocast_t'(4'b1);
|
o = tocast_t'(4'b1);
|
||||||
if (o != 4'b1) $stop;
|
if (o != 4'b1) $stop;
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue