Optimize/inline vvp_bit4_r AND, OR and vector set bit.

The AND and OR operators for vvp_bit4_t are slightly tweaked to be
lighter and inlinable.

The vvp_vector4_t::set_bit is optimized to do less silly mask fiddling.
This commit is contained in:
Stephen Williams 2008-05-26 11:09:33 -07:00
parent 9af459f95b
commit 8190307dd3
2 changed files with 51 additions and 54 deletions

View File

@ -61,28 +61,6 @@ vvp_bit4_t add_with_carry(vvp_bit4_t a, vvp_bit4_t b, vvp_bit4_t&c)
}
}
vvp_bit4_t operator & (vvp_bit4_t a, vvp_bit4_t b)
{
if (a == BIT4_0)
return BIT4_0;
if (b == BIT4_0)
return BIT4_0;
if (bit4_is_xz(a))
return BIT4_X;
if (bit4_is_xz(b))
return BIT4_X;
return BIT4_1;
}
vvp_bit4_t operator | (vvp_bit4_t a, vvp_bit4_t b)
{
if (a == BIT4_1)
return BIT4_1;
if (b == BIT4_1)
return BIT4_1;
return bit4_z2x( (vvp_bit4_t) ((int)a | (int)b) );
}
vvp_bit4_t operator ^ (vvp_bit4_t a, vvp_bit4_t b)
{
if (bit4_is_xz(a))

View File

@ -87,8 +87,21 @@ inline vvp_bit4_t bit4_z2x(vvp_bit4_t a)
inline vvp_bit4_t operator ~ (vvp_bit4_t a)
{ return bit4_z2x((vvp_bit4_t) (((int)a) ^ 1)); }
extern vvp_bit4_t operator | (vvp_bit4_t a, vvp_bit4_t b);
extern vvp_bit4_t operator & (vvp_bit4_t a, vvp_bit4_t b);
inline vvp_bit4_t operator | (vvp_bit4_t a, vvp_bit4_t b)
{
if (a==BIT4_1 || b==BIT4_1)
return BIT4_1;
return bit4_z2x( (vvp_bit4_t) ((int)a | (int)b) );
}
inline vvp_bit4_t operator & (vvp_bit4_t a, vvp_bit4_t b)
{
if (a==BIT4_0 || b==BIT4_0)
return BIT4_0;
return bit4_z2x( (vvp_bit4_t) ((int)a | (int)b) );
}
extern vvp_bit4_t operator ^ (vvp_bit4_t a, vvp_bit4_t b);
extern ostream& operator<< (ostream&o, vvp_bit4_t a);
@ -294,41 +307,47 @@ inline void vvp_vector4_t::set_bit(unsigned idx, vvp_bit4_t val)
assert(idx < size_);
unsigned long off = idx % BITS_PER_WORD;
unsigned long amask = 0, bmask = 0;
switch (val) {
case BIT4_0:
amask = 0;
bmask = 0;
break;
case BIT4_1:
amask = 1;
bmask = 0;
break;
case BIT4_X:
amask = 1;
bmask = 1;
break;
case BIT4_Z:
amask = 0;
bmask = 1;
break;
}
unsigned long mask = 1UL << off;
amask <<= off;
bmask <<= off;
if (size_ > BITS_PER_WORD) {
unsigned wdx = idx / BITS_PER_WORD;
abits_ptr_[wdx] &= ~mask;
abits_ptr_[wdx] |= amask;
bbits_ptr_[wdx] &= ~mask;
bbits_ptr_[wdx] |= bmask;
switch (val) {
case BIT4_0:
abits_ptr_[wdx] &= ~mask;
bbits_ptr_[wdx] &= ~mask;
break;
case BIT4_1:
abits_ptr_[wdx] |= mask;
bbits_ptr_[wdx] &= ~mask;
break;
case BIT4_X:
abits_ptr_[wdx] |= mask;
bbits_ptr_[wdx] |= mask;
break;
case BIT4_Z:
abits_ptr_[wdx] &= ~mask;
bbits_ptr_[wdx] |= mask;
break;
}
} else {
abits_val_ &= ~mask;
abits_val_ |= amask;
bbits_val_ &= ~mask;
bbits_val_ |= bmask;
switch (val) {
case BIT4_0:
abits_val_ &= ~mask;
bbits_val_ &= ~mask;
break;
case BIT4_1:
abits_val_ |= mask;
bbits_val_ &= ~mask;
break;
case BIT4_X:
abits_val_ |= mask;
bbits_val_ |= mask;
break;
case BIT4_Z:
abits_val_ &= ~mask;
bbits_val_ |= mask;
break;
}
}
}