Process arguments to bitwise operator using singned/unsigned rules.

The arguments to bitwise operators are padded if *either* of the operands
is unsigned. This is according to the sign/unsigned expression rules
of Verilog, and also matches the behavior of the "Big-3."
This commit is contained in:
Stephen Williams 2008-10-01 22:38:53 -07:00
parent feba5d9470
commit 7b4fda8785
3 changed files with 14 additions and 0 deletions

View File

@ -355,6 +355,14 @@ NetExpr* PEBinary::elaborate_expr_base_bits_(Design*des,
NetExpr*lp, NetExpr*rp,
int expr_wid) const
{
// If either of the arguments is unsigned, then process both
// of them as unsigned. This only impacts the padding that is
// done to get the operands to the expr_wid.
if (! lp->has_sign())
rp->cast_signed(false);
if (! rp->has_sign())
lp->cast_signed(false);
if (expr_wid > 0) {
if (type_is_vectorable(lp->expr_type()))
lp = pad_to_width(lp, expr_wid);

View File

@ -127,6 +127,9 @@ ivl_variable_type_t NetEBAdd::expr_type() const
NetEBComp::NetEBComp(char op, NetExpr*l, NetExpr*r)
: NetEBinary(op, l, r)
{
// The output of compare is always unsigned.
cast_signed_base_(false);
if (NetEConst*tmp = dynamic_cast<NetEConst*>(r)) do {
if (tmp->has_width())

View File

@ -2073,6 +2073,9 @@ NetEBBits* NetEBBits::dup_expr() const
NetEBinary::NetEBinary(char op, NetExpr*l, NetExpr*r)
: op_(op), left_(l), right_(r)
{
// Binary expressions of all sorts are signed if both the
// arguments are signed.
cast_signed_base_( left_->has_sign() && right_->has_sign());
}
NetEBinary::~NetEBinary()