Cleanup vpi_const to use vec4 values.
This commit is contained in:
parent
1b911ad87a
commit
5f5a6b5396
270
vvp/vpi_const.cc
270
vvp/vpi_const.cc
|
|
@ -17,7 +17,7 @@
|
|||
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||
*/
|
||||
#ifdef HAVE_CVS_IDENT
|
||||
#ident "$Id: vpi_const.cc,v 1.32 2004/10/04 01:10:59 steve Exp $"
|
||||
#ident "$Id: vpi_const.cc,v 1.33 2006/03/06 05:43:15 steve Exp $"
|
||||
#endif
|
||||
|
||||
# include "vpi_priv.h"
|
||||
|
|
@ -263,7 +263,7 @@ static int binary_get(int code, vpiHandle ref)
|
|||
return rfp->signed_flag? 1 : 0;
|
||||
|
||||
case vpiSize:
|
||||
return rfp->nbits;
|
||||
return rfp->bits.size();
|
||||
|
||||
default:
|
||||
fprintf(stderr, "vvp error: get %d not supported "
|
||||
|
|
@ -273,81 +273,6 @@ static int binary_get(int code, vpiHandle ref)
|
|||
}
|
||||
}
|
||||
|
||||
static void binary_vpiStringVal(struct __vpiBinaryConst*rfp, p_vpi_value vp)
|
||||
{
|
||||
unsigned nchar = rfp->nbits / 8;
|
||||
unsigned tail = rfp->nbits%8;
|
||||
|
||||
char*rbuf = need_result_buf(nchar + 1, RBUF_VAL);
|
||||
char*cp = rbuf;
|
||||
|
||||
if (tail > 0) {
|
||||
char char_val = 0;
|
||||
for (unsigned idx = rfp->nbits-tail; idx < rfp->nbits; idx += 1) {
|
||||
unsigned nibble = idx/4;
|
||||
unsigned shift = 2 * (idx%4);
|
||||
unsigned val = (rfp->bits[nibble] >> shift) & 3;
|
||||
if (val & 1)
|
||||
char_val |= 1 << idx;
|
||||
}
|
||||
|
||||
if (char_val != 0)
|
||||
*cp++ = char_val;
|
||||
}
|
||||
|
||||
for (unsigned idx = 0 ; idx < nchar ; idx += 1) {
|
||||
unsigned bit = (nchar - idx - 1) * 8;
|
||||
unsigned nibble = bit/4;
|
||||
unsigned vall = rfp->bits[nibble+0];
|
||||
unsigned valh = rfp->bits[nibble+1];
|
||||
|
||||
char char_val = 0;
|
||||
if (vall&0x01) char_val |= 0x01;
|
||||
if (vall&0x04) char_val |= 0x02;
|
||||
if (vall&0x10) char_val |= 0x04;
|
||||
if (vall&0x40) char_val |= 0x08;
|
||||
if (valh&0x01) char_val |= 0x10;
|
||||
if (valh&0x04) char_val |= 0x20;
|
||||
if (valh&0x10) char_val |= 0x40;
|
||||
if (valh&0x40) char_val |= 0x80;
|
||||
|
||||
if (char_val != 0)
|
||||
*cp++ = char_val;
|
||||
}
|
||||
|
||||
*cp = 0;
|
||||
vp->value.str = rbuf;
|
||||
}
|
||||
|
||||
static int bits2int(struct __vpiBinaryConst*rfp)
|
||||
{
|
||||
unsigned val = 0;
|
||||
unsigned bit_val = 0;
|
||||
unsigned bit_limit = rfp->nbits;
|
||||
if (bit_limit > 8*sizeof(val))
|
||||
bit_limit = 8*sizeof(val);
|
||||
|
||||
for (unsigned idx = 0 ; idx < bit_limit ; idx += 1) {
|
||||
unsigned nibble = idx/4;
|
||||
unsigned shift = 2 * (idx%4);
|
||||
bit_val = (rfp->bits[nibble] >> shift) & 3;
|
||||
if (bit_val > 1) {
|
||||
return 0;
|
||||
} else {
|
||||
val |= bit_val << idx;
|
||||
}
|
||||
}
|
||||
|
||||
/* sign extend */
|
||||
if (rfp->signed_flag && bit_val) {
|
||||
for (unsigned idx = rfp->nbits; idx <sizeof(val)*8; idx++)
|
||||
{
|
||||
val |= bit_val << idx;
|
||||
}
|
||||
}
|
||||
|
||||
return val;
|
||||
}
|
||||
|
||||
static void binary_value(vpiHandle ref, p_vpi_value vp)
|
||||
{
|
||||
|
|
@ -360,125 +285,16 @@ static void binary_value(vpiHandle ref, p_vpi_value vp)
|
|||
switch (vp->format) {
|
||||
|
||||
case vpiObjTypeVal:
|
||||
case vpiBinStrVal: {
|
||||
rbuf = need_result_buf(rfp->nbits + 1, RBUF_VAL);
|
||||
for (unsigned idx = 0 ; idx < rfp->nbits ; idx += 1) {
|
||||
unsigned nibble = idx/4;
|
||||
unsigned shift = 2 * (idx%4);
|
||||
unsigned val = (rfp->bits[nibble] >> shift) & 3;
|
||||
|
||||
rbuf[rfp->nbits-idx-1] = "01xz"[val];
|
||||
}
|
||||
rbuf[rfp->nbits] = 0;
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiDecStrVal: {
|
||||
unsigned wid = rfp->nbits;
|
||||
rbuf = need_result_buf(rfp->nbits + 1, RBUF_VAL);
|
||||
unsigned char*tmp = new unsigned char[wid];
|
||||
for (unsigned idx = 0 ; idx < wid ; idx += 1)
|
||||
tmp[idx] = (rfp->bits[idx/4] >> 2*(idx%4)) & 3;
|
||||
|
||||
vpip_bits_to_dec_str(tmp, wid, rbuf, wid + 1,
|
||||
rfp->signed_flag);
|
||||
|
||||
delete[]tmp;
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiHexStrVal: {
|
||||
unsigned nchar = (rfp->nbits+3)/4;
|
||||
rbuf = need_result_buf(nchar + 1, RBUF_VAL);
|
||||
for (unsigned idx = 0 ; idx < rfp->nbits ; idx += 4) {
|
||||
unsigned nibble = idx/4;
|
||||
unsigned vals = rfp->bits[nibble];
|
||||
|
||||
if (vals == 0xff) {
|
||||
rbuf[nchar-idx/4-1] = 'z';
|
||||
} else if (vals == 0xaa) {
|
||||
rbuf[nchar-idx/4-1] = 'x';
|
||||
} else if (vals & 0xaa) {
|
||||
rbuf[nchar-idx/4-1] = 'X';
|
||||
} else {
|
||||
unsigned val = vals&1;
|
||||
if (vals&0x04) val |= 2;
|
||||
if (vals&0x10) val |= 4;
|
||||
if (vals&0x40) val |= 8;
|
||||
rbuf[nchar-idx/4-1] = "0123456789abcdef"[val];
|
||||
}
|
||||
}
|
||||
|
||||
rbuf[nchar] = 0;
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiOctStrVal: {
|
||||
unsigned nchar = (rfp->nbits+2)/3;
|
||||
rbuf = need_result_buf(nchar + 1, RBUF_VAL);
|
||||
vpip_bits_to_oct_str(rfp->bits, rfp->nbits,
|
||||
rbuf, nchar+1, rfp->signed_flag);
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiIntVal: {
|
||||
vp->value.integer = bits2int(rfp);
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiVectorVal: {
|
||||
unsigned int obit = 0;
|
||||
unsigned hwid = (rfp->nbits - 1)/32 + 1;
|
||||
rbuf = need_result_buf(hwid*sizeof(s_vpi_vecval), RBUF_VAL);
|
||||
|
||||
s_vpi_vecval *op = (p_vpi_vecval)rbuf;
|
||||
vp->value.vector = op;
|
||||
|
||||
op->aval = op->bval = 0;
|
||||
for (unsigned idx = 0 ; idx < rfp->nbits ; idx += 1) {
|
||||
unsigned nibble = idx/4;
|
||||
unsigned shift = 2 * (idx%4);
|
||||
unsigned bit_val = (rfp->bits[nibble] >> shift) & 3;
|
||||
|
||||
switch (bit_val) {
|
||||
case 0:
|
||||
op->aval &= ~(1 << obit);
|
||||
op->bval &= ~(1 << obit);
|
||||
break;
|
||||
case 1:
|
||||
op->aval |= (1 << obit);
|
||||
op->bval &= ~(1 << obit);
|
||||
break;
|
||||
case 2:
|
||||
op->aval |= (1 << obit);
|
||||
op->bval |= (1 << obit);
|
||||
break;
|
||||
case 3:
|
||||
op->aval &= ~(1 << obit);
|
||||
op->bval |= (1 << obit);
|
||||
break;
|
||||
}
|
||||
obit++;
|
||||
if (!(obit % 32)) {
|
||||
op += 1;
|
||||
if ((op - vp->value.vector) < (long)hwid)
|
||||
op->aval = op->bval = 0;
|
||||
obit = 0;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiRealVal:
|
||||
vp->value.real = (double)bits2int(rfp);
|
||||
break;
|
||||
|
||||
case vpiBinStrVal:
|
||||
case vpiDecStrVal:
|
||||
case vpiOctStrVal:
|
||||
case vpiHexStrVal:
|
||||
case vpiIntVal:
|
||||
case vpiVectorVal:
|
||||
case vpiStringVal:
|
||||
binary_vpiStringVal(rfp, vp);
|
||||
case vpiRealVal:
|
||||
vpip_vec4_get_value(rfp->bits, rfp->bits.size(),
|
||||
rfp->signed_flag, vp);
|
||||
break;
|
||||
|
||||
default:
|
||||
|
|
@ -513,9 +329,7 @@ vpiHandle vpip_make_binary_const(unsigned wid, char*bits)
|
|||
obj->base.vpi_type = &vpip_binary_rt;
|
||||
|
||||
obj->signed_flag = 0;
|
||||
obj->nbits = wid;
|
||||
obj->bits = (unsigned char*)malloc((obj->nbits + 3) / 4);
|
||||
memset(obj->bits, 0, (obj->nbits + 3) / 4);
|
||||
obj->bits = vvp_vector4_t(wid);
|
||||
|
||||
const char*bp = bits;
|
||||
if (*bp == 's') {
|
||||
|
|
@ -523,25 +337,24 @@ vpiHandle vpip_make_binary_const(unsigned wid, char*bits)
|
|||
obj->signed_flag = 1;
|
||||
}
|
||||
|
||||
for (unsigned idx = 0 ; idx < obj->nbits ; idx += 1) {
|
||||
unsigned nibble = idx / 4;
|
||||
unsigned val = 0;
|
||||
for (unsigned idx = 0 ; idx < wid ; idx += 1) {
|
||||
vvp_bit4_t val = BIT4_0;
|
||||
switch (bp[wid-idx-1]) {
|
||||
case '0':
|
||||
val = 0;
|
||||
val = BIT4_0;
|
||||
break;
|
||||
case '1':
|
||||
val = 1;
|
||||
val = BIT4_1;
|
||||
break;
|
||||
case 'x':
|
||||
val = 2;
|
||||
val = BIT4_X;
|
||||
break;
|
||||
case 'z':
|
||||
val = 3;
|
||||
val = BIT4_Z;
|
||||
break;
|
||||
}
|
||||
|
||||
obj->bits[nibble] |= val << (2 * (idx%4));
|
||||
obj->bits.set_bit(idx, val);
|
||||
}
|
||||
|
||||
free(bits);
|
||||
|
|
@ -652,52 +465,13 @@ vpiHandle vpip_make_dec_const(int value)
|
|||
|
||||
/*
|
||||
* $Log: vpi_const.cc,v $
|
||||
* Revision 1.33 2006/03/06 05:43:15 steve
|
||||
* Cleanup vpi_const to use vec4 values.
|
||||
*
|
||||
* Revision 1.32 2004/10/04 01:10:59 steve
|
||||
* Clean up spurious trailing white space.
|
||||
*
|
||||
* Revision 1.31 2004/05/18 18:43:38 steve
|
||||
* Allow vpiParamter as a string type.
|
||||
*
|
||||
* Revision 1.30 2003/05/30 04:22:13 steve
|
||||
* Add tf_strgetp functions.
|
||||
*
|
||||
* Revision 1.29 2003/05/29 03:46:21 steve
|
||||
* Add tf_getp/putp support for integers
|
||||
* and real valued arguments.
|
||||
*
|
||||
* Add tf_mipname function.
|
||||
*
|
||||
* Revision 1.28 2003/03/17 23:47:25 steve
|
||||
* Make a safe copy of const string values.
|
||||
*
|
||||
* Revision 1.27 2003/03/15 05:44:50 steve
|
||||
* Remove excess assignment.
|
||||
*
|
||||
* Revision 1.26 2003/03/14 05:02:13 steve
|
||||
* Streamline parameter string value, get paramete scope.
|
||||
*
|
||||
* Revision 1.25 2003/03/13 04:59:21 steve
|
||||
* Use rbufs instead of static buffers.
|
||||
*
|
||||
* Revision 1.24 2003/03/10 23:37:07 steve
|
||||
* Direct support for string parameters.
|
||||
*
|
||||
* Revision 1.23 2003/03/10 19:14:27 steve
|
||||
* More carful about shifting beyond word size.
|
||||
*
|
||||
* Revision 1.22 2003/02/24 06:35:45 steve
|
||||
* Interactive task calls take string arguments.
|
||||
*
|
||||
* Revision 1.21 2002/11/03 20:33:43 steve
|
||||
* Compiler error wrt ptrdiff_t.
|
||||
*
|
||||
* Revision 1.20 2002/11/03 02:07:24 steve
|
||||
* Get VectorVals from constant values.
|
||||
*
|
||||
* Revision 1.19 2002/08/12 01:35:08 steve
|
||||
* conditional ident string using autoconfig.
|
||||
*
|
||||
* Revision 1.18 2002/06/23 18:23:09 steve
|
||||
* trivial performance boost.
|
||||
*/
|
||||
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@
|
|||
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||
*/
|
||||
#ifdef HAVE_CVS_IDENT
|
||||
#ident "$Id: vpi_memory.cc,v 1.32 2006/03/05 05:45:58 steve Exp $"
|
||||
#ident "$Id: vpi_memory.cc,v 1.33 2006/03/06 05:43:15 steve Exp $"
|
||||
#endif
|
||||
|
||||
# include "vpi_priv.h"
|
||||
|
|
@ -361,104 +361,6 @@ static char* memory_word_get_str(int code, vpiHandle ref)
|
|||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* This is a generic function to convert a vvp_vector4_t value into a
|
||||
* vpi_value structure. The format is selected by the format of the
|
||||
* value pointer. The width is the real width of the word, in case the
|
||||
* word_val width is not accurate.
|
||||
*/
|
||||
void vec4_get_value(const vvp_vector4_t word_val, unsigned width,
|
||||
s_vpi_value*vp)
|
||||
{
|
||||
char *rbuf = 0;
|
||||
|
||||
switch (vp->format) {
|
||||
default:
|
||||
cerr << "internal error: Format "
|
||||
<< vp->format
|
||||
<< " not implemented" << endl;
|
||||
assert(0 && "format not implemented");
|
||||
|
||||
case vpiBinStrVal:
|
||||
rbuf = need_result_buf(width+1, RBUF_VAL);
|
||||
for (unsigned idx = 0 ; idx < width ; idx += 1) {
|
||||
vvp_bit4_t bit = word_val.value(idx);
|
||||
rbuf[width-idx-1] = "01xz"[bit];
|
||||
}
|
||||
rbuf[width] = 0;
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
|
||||
case vpiOctStrVal: {
|
||||
unsigned hwid = (width+2) / 3;
|
||||
rbuf = need_result_buf(hwid+1, RBUF_VAL);
|
||||
vpip_vec4_to_oct_str(word_val, rbuf, hwid+1, false);
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiDecStrVal: {
|
||||
rbuf = need_result_buf(width+1, RBUF_VAL);
|
||||
vpip_vec4_to_dec_str(word_val, rbuf, width+1, false);
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiHexStrVal: {
|
||||
unsigned hwid = (width + 3) / 4;
|
||||
|
||||
rbuf = need_result_buf(hwid+1, RBUF_VAL);
|
||||
rbuf[hwid] = 0;
|
||||
|
||||
vpip_vec4_to_hex_str(word_val, rbuf, hwid+1, false);
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiIntVal: {
|
||||
unsigned long val;
|
||||
vector4_to_value(word_val, val);
|
||||
vp->value.integer = val;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiVectorVal: {
|
||||
unsigned hwid = (width - 1)/32 + 1;
|
||||
|
||||
rbuf = need_result_buf(hwid * sizeof(s_vpi_vecval), RBUF_VAL);
|
||||
s_vpi_vecval *op = (p_vpi_vecval)rbuf;
|
||||
vp->value.vector = op;
|
||||
|
||||
op->aval = op->bval = 0;
|
||||
for (unsigned idx = 0 ; idx < width ; idx += 1) {
|
||||
switch (word_val.value(idx)) {
|
||||
case BIT4_0:
|
||||
op->aval &= ~(1 << idx % 32);
|
||||
op->bval &= ~(1 << idx % 32);
|
||||
break;
|
||||
case BIT4_1:
|
||||
op->aval |= (1 << idx % 32);
|
||||
op->bval &= ~(1 << idx % 32);
|
||||
break;
|
||||
case BIT4_X:
|
||||
op->aval |= (1 << idx % 32);
|
||||
op->bval |= (1 << idx % 32);
|
||||
break;
|
||||
case BIT4_Z:
|
||||
op->aval &= ~(1 << idx % 32);
|
||||
op->bval |= (1 << idx % 32);
|
||||
break;
|
||||
}
|
||||
if (!((idx+1) % 32) && (idx+1 < width)) {
|
||||
op++;
|
||||
op->aval = op->bval = 0;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void memory_word_get_value(vpiHandle ref, s_vpi_value*vp)
|
||||
{
|
||||
struct __vpiMemoryWord*rfp = (struct __vpiMemoryWord*)ref;
|
||||
|
|
@ -469,7 +371,7 @@ static void memory_word_get_value(vpiHandle ref, s_vpi_value*vp)
|
|||
|
||||
vvp_vector4_t word_val = memory_get_word(rfp->mem->mem, word_address);
|
||||
|
||||
vec4_get_value(word_val, width, vp);
|
||||
vpip_vec4_get_value(word_val, width, false /* never signed */, vp);
|
||||
}
|
||||
|
||||
static const struct __vpirt vpip_memory_rt = {
|
||||
|
|
@ -532,7 +434,7 @@ void vpip_run_memory_value_change(vpiHandle ref, unsigned addr)
|
|||
continue;
|
||||
|
||||
if (cur->cb_data.value)
|
||||
vec4_get_value(word_val, width, cur->cb_data.value);
|
||||
vpip_vec4_get_value(word_val, width, false, cur->cb_data.value);
|
||||
|
||||
cur->cb_data.index = addr;
|
||||
vpi_mode_flag = VPI_MODE_RWSYNC;
|
||||
|
|
@ -576,6 +478,9 @@ vpiHandle vpip_make_memory(vvp_memory_t mem, const char*name)
|
|||
|
||||
/*
|
||||
* $Log: vpi_memory.cc,v $
|
||||
* Revision 1.33 2006/03/06 05:43:15 steve
|
||||
* Cleanup vpi_const to use vec4 values.
|
||||
*
|
||||
* Revision 1.32 2006/03/05 05:45:58 steve
|
||||
* Add support for memory value change callbacks.
|
||||
*
|
||||
|
|
|
|||
165
vvp/vpi_priv.cc
165
vvp/vpi_priv.cc
|
|
@ -17,7 +17,7 @@
|
|||
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||
*/
|
||||
#ifdef HAVE_CVS_IDENT
|
||||
#ident "$Id: vpi_priv.cc,v 1.49 2005/12/05 21:19:55 steve Exp $"
|
||||
#ident "$Id: vpi_priv.cc,v 1.50 2006/03/06 05:43:15 steve Exp $"
|
||||
#endif
|
||||
|
||||
# include "vpi_priv.h"
|
||||
|
|
@ -353,6 +353,166 @@ void vpi_set_vlog_info(int argc, char** argv)
|
|||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* This is a generic function to convert a vvp_vector4_t value into a
|
||||
* vpi_value structure. The format is selected by the format of the
|
||||
* value pointer. The width is the real width of the word, in case the
|
||||
* word_val width is not accurate.
|
||||
*/
|
||||
|
||||
static void vec4_get_value_string(const vvp_vector4_t&word_val, unsigned width,
|
||||
s_vpi_value*vp);
|
||||
|
||||
void vpip_vec4_get_value(const vvp_vector4_t&word_val, unsigned width,
|
||||
bool signed_flag, s_vpi_value*vp)
|
||||
{
|
||||
char *rbuf = 0;
|
||||
|
||||
switch (vp->format) {
|
||||
default:
|
||||
fprintf(stderr, "internal error: Format %d not implemented\n",
|
||||
vp->format);
|
||||
assert(0 && "format not implemented");
|
||||
|
||||
case vpiBinStrVal:
|
||||
rbuf = need_result_buf(width+1, RBUF_VAL);
|
||||
for (unsigned idx = 0 ; idx < width ; idx += 1) {
|
||||
vvp_bit4_t bit = word_val.value(idx);
|
||||
rbuf[width-idx-1] = "01xz"[bit];
|
||||
}
|
||||
rbuf[width] = 0;
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
|
||||
case vpiOctStrVal: {
|
||||
unsigned hwid = (width+2) / 3;
|
||||
rbuf = need_result_buf(hwid+1, RBUF_VAL);
|
||||
vpip_vec4_to_oct_str(word_val, rbuf, hwid+1, signed_flag);
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiDecStrVal: {
|
||||
rbuf = need_result_buf(width+1, RBUF_VAL);
|
||||
vpip_vec4_to_dec_str(word_val, rbuf, width+1, signed_flag);
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiHexStrVal: {
|
||||
unsigned hwid = (width + 3) / 4;
|
||||
|
||||
rbuf = need_result_buf(hwid+1, RBUF_VAL);
|
||||
rbuf[hwid] = 0;
|
||||
|
||||
vpip_vec4_to_hex_str(word_val, rbuf, hwid+1, signed_flag);
|
||||
vp->value.str = rbuf;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiIntVal: {
|
||||
long val = 0;
|
||||
vvp_bit4_t pad = BIT4_0;
|
||||
if (signed_flag && word_val.size() > 0)
|
||||
pad = word_val.value(word_val.size()-1);
|
||||
|
||||
for (long idx = 0 ; idx < 8*sizeof(val) ; idx += 1) {
|
||||
vvp_bit4_t val4 = pad;
|
||||
if (idx < word_val.size())
|
||||
val4 = word_val.value(idx);
|
||||
if (val4 == BIT4_1)
|
||||
val |= 1L << idx;
|
||||
}
|
||||
|
||||
vp->value.integer = val;
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiVectorVal: {
|
||||
unsigned hwid = (width - 1)/32 + 1;
|
||||
|
||||
rbuf = need_result_buf(hwid * sizeof(s_vpi_vecval), RBUF_VAL);
|
||||
s_vpi_vecval *op = (p_vpi_vecval)rbuf;
|
||||
vp->value.vector = op;
|
||||
|
||||
op->aval = op->bval = 0;
|
||||
for (unsigned idx = 0 ; idx < width ; idx += 1) {
|
||||
switch (word_val.value(idx)) {
|
||||
case BIT4_0:
|
||||
op->aval &= ~(1 << idx % 32);
|
||||
op->bval &= ~(1 << idx % 32);
|
||||
break;
|
||||
case BIT4_1:
|
||||
op->aval |= (1 << idx % 32);
|
||||
op->bval &= ~(1 << idx % 32);
|
||||
break;
|
||||
case BIT4_X:
|
||||
op->aval |= (1 << idx % 32);
|
||||
op->bval |= (1 << idx % 32);
|
||||
break;
|
||||
case BIT4_Z:
|
||||
op->aval &= ~(1 << idx % 32);
|
||||
op->bval |= (1 << idx % 32);
|
||||
break;
|
||||
}
|
||||
if (!((idx+1) % 32) && (idx+1 < width)) {
|
||||
op++;
|
||||
op->aval = op->bval = 0;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case vpiStringVal:
|
||||
vec4_get_value_string(word_val, width, vp);
|
||||
break;
|
||||
|
||||
case vpiRealVal: {
|
||||
unsigned long val;
|
||||
vector4_to_value(word_val, val);
|
||||
vp->value.real = val;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void vec4_get_value_string(const vvp_vector4_t&word_val, unsigned width,
|
||||
s_vpi_value*vp)
|
||||
{
|
||||
unsigned nchar = width / 8;
|
||||
unsigned tail = width % 8;
|
||||
|
||||
char*rbuf = need_result_buf(nchar + 1, RBUF_VAL);
|
||||
char*cp = rbuf;
|
||||
|
||||
if (tail > 0) {
|
||||
char char_val = 0;
|
||||
for (unsigned idx = width-tail; idx < width ; idx += 1) {
|
||||
vvp_bit4_t val = word_val.value(idx);
|
||||
if (val == BIT4_1)
|
||||
char_val |= 1 << idx;
|
||||
}
|
||||
|
||||
if (char_val != 0)
|
||||
*cp++ = char_val;
|
||||
}
|
||||
|
||||
for (unsigned idx = 0 ; idx < nchar ; idx += 1) {
|
||||
unsigned bit = (nchar - idx - 1) * 8;
|
||||
char char_val = 0;
|
||||
for (unsigned bdx = 0 ; bdx < 8 ; bdx += 1) {
|
||||
vvp_bit4_t val = word_val.value(bit+bdx);
|
||||
if (val == BIT4_1)
|
||||
char_val |= 1 << bdx;
|
||||
}
|
||||
if (char_val != 0)
|
||||
*cp++ = char_val;
|
||||
}
|
||||
|
||||
*cp = 0;
|
||||
vp->value.str = rbuf;
|
||||
}
|
||||
|
||||
void vpi_get_value(vpiHandle expr, s_vpi_value*vp)
|
||||
{
|
||||
assert(expr);
|
||||
|
|
@ -686,6 +846,9 @@ extern "C" void vpi_control(PLI_INT32 operation, ...)
|
|||
|
||||
/*
|
||||
* $Log: vpi_priv.cc,v $
|
||||
* Revision 1.50 2006/03/06 05:43:15 steve
|
||||
* Cleanup vpi_const to use vec4 values.
|
||||
*
|
||||
* Revision 1.49 2005/12/05 21:19:55 steve
|
||||
* Be more careful with double types.
|
||||
*
|
||||
|
|
|
|||
|
|
@ -19,7 +19,7 @@
|
|||
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||
*/
|
||||
#ifdef HAVE_CVS_IDENT
|
||||
#ident "$Id: vpi_priv.h,v 1.67 2006/03/05 05:45:58 steve Exp $"
|
||||
#ident "$Id: vpi_priv.h,v 1.68 2006/03/06 05:43:15 steve Exp $"
|
||||
#endif
|
||||
|
||||
# include "vpi_user.h"
|
||||
|
|
@ -290,8 +290,7 @@ vpiHandle vpip_make_string_param(char*name, char*value);
|
|||
|
||||
struct __vpiBinaryConst {
|
||||
struct __vpiHandle base;
|
||||
unsigned nbits;
|
||||
unsigned char*bits;
|
||||
vvp_vector4_t bits;
|
||||
unsigned signed_flag :1;
|
||||
};
|
||||
|
||||
|
|
@ -381,14 +380,7 @@ extern vvp_time64_t vpip_timestruct_to_time(const struct t_vpi_time*ts);
|
|||
extern const char* vpip_string(const char*str);
|
||||
extern const char* vpip_name_string(const char*str);
|
||||
|
||||
#if 0
|
||||
/*
|
||||
** Functions defined in vpi_scope.cc, to keep track of functor scope.
|
||||
*/
|
||||
|
||||
extern vpiHandle ipoint_get_scope(vvp_ipoint_t ipt);
|
||||
extern void functor_set_scope(vpiHandle scope);
|
||||
#endif
|
||||
/*
|
||||
* This function is used to make decimal string versions of various
|
||||
* vectors. The input format is an array of bit values (0, 1, 2, 3)
|
||||
|
|
@ -418,6 +410,8 @@ extern void vpip_oct_str_to_vec4(vvp_vector4_t&val, const char*str);
|
|||
extern void vpip_dec_str_to_vec4(vvp_vector4_t&val, const char*str, bool sign);
|
||||
extern void vpip_hex_str_to_vec4(vvp_vector4_t&val, const char*str);
|
||||
|
||||
extern void vpip_vec4_get_value(const vvp_vector4_t&word_val, unsigned width,
|
||||
bool signed_flag, s_vpi_value*vp);
|
||||
|
||||
/*
|
||||
* Function defined in vpi_signal.cc to manage vpi_get_* persistent
|
||||
|
|
@ -433,6 +427,9 @@ extern char *need_result_buf(unsigned cnt, vpi_rbuf_t type);
|
|||
|
||||
/*
|
||||
* $Log: vpi_priv.h,v $
|
||||
* Revision 1.68 2006/03/06 05:43:15 steve
|
||||
* Cleanup vpi_const to use vec4 values.
|
||||
*
|
||||
* Revision 1.67 2006/03/05 05:45:58 steve
|
||||
* Add support for memory value change callbacks.
|
||||
*
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@
|
|||
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||
*/
|
||||
#ifdef HAVE_CVS_IDENT
|
||||
#ident "$Id: vpi_scope.cc,v 1.34 2005/06/12 01:10:26 steve Exp $"
|
||||
#ident "$Id: vpi_scope.cc,v 1.35 2006/03/06 05:43:15 steve Exp $"
|
||||
#endif
|
||||
|
||||
# include "compile.h"
|
||||
|
|
@ -207,96 +207,6 @@ static vpiHandle module_iter(int code, vpiHandle obj)
|
|||
return module_iter_subset(code, ref);
|
||||
}
|
||||
|
||||
/*
|
||||
** Keeping track of functor scope. When the scope changes during
|
||||
** compilation, we record the current number of functors in a list.
|
||||
**
|
||||
** Why are we doing this? The SDF annotator needs this for
|
||||
** INTERCONNECT delays. The INTERCONNECT delay is specified between
|
||||
** a source modules output port and a target module input port, which
|
||||
** are connected with a wire. The vpiSignal for both ports point to
|
||||
** the same functor output, together with all other ports that may be
|
||||
** connected to the same wire. The SDF annotator need to find those
|
||||
** functors which are inside the scope of the target module, which
|
||||
** are driven by the source functor. And even this is only an
|
||||
** approximation, in case the wire is connected to multiple inputs of
|
||||
** the same module. But those should have the same delays anyway.
|
||||
**
|
||||
*/
|
||||
#if 0
|
||||
struct functor_scope_s {
|
||||
vpiHandle scope;
|
||||
unsigned start;
|
||||
};
|
||||
#endif
|
||||
#if 0
|
||||
static struct functor_scope_s * functor_scopes = 0;
|
||||
static unsigned n_functor_scopes = 0;
|
||||
static unsigned a_functor_scopes = 0;
|
||||
#endif
|
||||
#if 0
|
||||
void functor_set_scope(vpiHandle scope)
|
||||
{
|
||||
unsigned nfun = functor_limit();
|
||||
|
||||
if (n_functor_scopes) {
|
||||
functor_scope_s *last = &functor_scopes[n_functor_scopes - 1];
|
||||
|
||||
if (last->scope == scope) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (last->start == nfun) {
|
||||
last->scope = scope;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
n_functor_scopes += 1;
|
||||
if (n_functor_scopes >= a_functor_scopes) {
|
||||
a_functor_scopes += 512;
|
||||
functor_scopes = (struct functor_scope_s *)
|
||||
realloc(functor_scopes,
|
||||
a_functor_scopes*sizeof(struct functor_scope_s));
|
||||
assert(functor_scopes);
|
||||
}
|
||||
|
||||
functor_scope_s *last = &functor_scopes[n_functor_scopes - 1];
|
||||
last->start = nfun;
|
||||
last->scope = scope;
|
||||
}
|
||||
#endif
|
||||
#if 0
|
||||
/*
|
||||
** Look up the scope of a functor.
|
||||
**
|
||||
** Cannot use bsearch, since we are not looking for an exact match
|
||||
*/
|
||||
vpiHandle ipoint_get_scope(vvp_ipoint_t ipt)
|
||||
{
|
||||
if (n_functor_scopes == 0)
|
||||
return NULL;
|
||||
|
||||
unsigned fidx = ipt/4;
|
||||
|
||||
unsigned first = 0;
|
||||
unsigned last = n_functor_scopes;
|
||||
while (first < last) {
|
||||
unsigned next = (first+last)/2;
|
||||
functor_scope_s *cur = &functor_scopes[next];
|
||||
|
||||
if (cur->start > fidx)
|
||||
last = next;
|
||||
else if (next == first)
|
||||
break;
|
||||
else
|
||||
first = next;
|
||||
}
|
||||
|
||||
functor_scope_s *cur = &functor_scopes[first];
|
||||
return cur->scope;
|
||||
}
|
||||
#endif
|
||||
|
||||
static const struct __vpirt vpip_scope_module_rt = {
|
||||
vpiModule,
|
||||
|
|
@ -479,6 +389,9 @@ void vpip_attach_to_current_scope(vpiHandle obj)
|
|||
|
||||
/*
|
||||
* $Log: vpi_scope.cc,v $
|
||||
* Revision 1.35 2006/03/06 05:43:15 steve
|
||||
* Cleanup vpi_const to use vec4 values.
|
||||
*
|
||||
* Revision 1.34 2005/06/12 01:10:26 steve
|
||||
* Remove useless references to functor.h
|
||||
*
|
||||
|
|
|
|||
Loading…
Reference in New Issue