Implement vec4 basec %assign delay and event / vpiTimeVal for functions.
This commit is contained in:
parent
1a3adbe9cd
commit
2fc8ce8a16
|
|
@ -32,11 +32,25 @@ static void draw_binary_vec4_arith(ivl_expr_t expr, int stuff_ok_flag)
|
|||
ivl_expr_t le = ivl_expr_oper1(expr);
|
||||
ivl_expr_t re = ivl_expr_oper2(expr);
|
||||
|
||||
unsigned lwid = ivl_expr_width(le);
|
||||
unsigned rwid = ivl_expr_width(re);
|
||||
unsigned ewid = ivl_expr_width(expr);
|
||||
|
||||
int signed_flag = ivl_expr_signed(le) && ivl_expr_signed(re) ? 1 : 0;
|
||||
const char*signed_string = signed_flag? "/s" : "";
|
||||
|
||||
/* All the arithmetic operations handled here require that the
|
||||
operands (and the result) be the same width. We further
|
||||
assume that the core has not given us an operand wider then
|
||||
the expression width. So padd operands as needed. */
|
||||
draw_eval_vec4(le, stuff_ok_flag);
|
||||
if (lwid < ewid) {
|
||||
fprintf(vvp_out, " %%pad/%c %u;\n", ivl_expr_signed(le)? 's' : 'u', ewid);
|
||||
}
|
||||
draw_eval_vec4(re, stuff_ok_flag);
|
||||
if (rwid < ewid) {
|
||||
fprintf(vvp_out, " %%pad/%c %u;\n", ivl_expr_signed(re)? 's' : 'u', ewid);
|
||||
}
|
||||
|
||||
switch (ivl_expr_opcode(expr)) {
|
||||
case '+':
|
||||
|
|
|
|||
|
|
@ -202,7 +202,6 @@ extern bool of_SET_DAR(vthread_t thr, vvp_code_t code);
|
|||
extern bool of_SET_DAR_OBJ(vthread_t thr, vvp_code_t code);
|
||||
extern bool of_SET_DAR_OBJ_REAL(vthread_t thr, vvp_code_t code);
|
||||
extern bool of_SET_DAR_OBJ_STR(vthread_t thr, vvp_code_t code);
|
||||
extern bool of_SET_VEC(vthread_t thr, vvp_code_t code);
|
||||
extern bool of_SET_X0(vthread_t thr, vvp_code_t code);
|
||||
extern bool of_SET_X0_X(vthread_t thr, vvp_code_t code);
|
||||
extern bool of_SHIFTL(vthread_t thr, vvp_code_t code);
|
||||
|
|
|
|||
|
|
@ -250,7 +250,6 @@ static const struct opcode_table_s opcode_table[] = {
|
|||
{ "%set/dar/obj", of_SET_DAR_OBJ, 3,{OA_NUMBER,OA_BIT1,OA_BIT2} },
|
||||
{ "%set/dar/obj/real",of_SET_DAR_OBJ_REAL,1,{OA_NUMBER,OA_NONE,OA_NONE} },
|
||||
{ "%set/dar/obj/str", of_SET_DAR_OBJ_STR, 1,{OA_NUMBER,OA_NONE,OA_NONE} },
|
||||
{ "%set/v", of_SET_VEC,3, {OA_FUNC_PTR, OA_BIT1, OA_BIT2} },
|
||||
{ "%set/x0", of_SET_X0, 3, {OA_FUNC_PTR, OA_BIT1, OA_BIT2} },
|
||||
{ "%shiftl", of_SHIFTL, 1, {OA_NUMBER, OA_NONE, OA_NONE} },
|
||||
{ "%shiftr", of_SHIFTR, 1, {OA_NUMBER, OA_NONE, OA_NONE} },
|
||||
|
|
|
|||
|
|
@ -1118,7 +1118,7 @@ values.
|
|||
The "%set/dar/obj/str" opcode does the same but for string values and
|
||||
uses the string stack.
|
||||
|
||||
* %set/v <var-label>, <bit>, <wid>
|
||||
* %set/v <var-label>, <bit>, <wid> (XXXX Old definition)
|
||||
|
||||
This sets a vector to a variable, and is used to implement blocking
|
||||
assignments. The <var-label> identifies the variable to receive the
|
||||
|
|
|
|||
|
|
@ -477,6 +477,7 @@ class sysfunc_vec4 : public __vpiSysTaskCall {
|
|||
|
||||
private:
|
||||
vpiHandle put_value_int_(p_vpi_value vp);
|
||||
vpiHandle put_value_time_(p_vpi_value vp);
|
||||
|
||||
private:
|
||||
vvp_vector4_t return_value_;
|
||||
|
|
@ -494,6 +495,24 @@ vpiHandle sysfunc_vec4::put_value_int_(p_vpi_value vp)
|
|||
return 0;
|
||||
}
|
||||
|
||||
vpiHandle sysfunc_vec4::put_value_time_(p_vpi_value vp)
|
||||
{
|
||||
unsigned width = return_value_.size();
|
||||
long tmp = 0;
|
||||
for (unsigned idx = 0 ; idx < width ; idx += 1) {
|
||||
if (idx == 0)
|
||||
tmp = vp->value.time->low;
|
||||
else if (idx == 32)
|
||||
tmp = vp->value.time->high;
|
||||
else if (idx == 64)
|
||||
tmp = 0;
|
||||
|
||||
return_value_.set_bit(idx, (tmp&1)? BIT4_1 : BIT4_0);
|
||||
tmp >>= 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
vpiHandle sysfunc_vec4::vpi_put_value(p_vpi_value vp, int)
|
||||
{
|
||||
put_value = true;
|
||||
|
|
@ -501,8 +520,10 @@ vpiHandle sysfunc_vec4::vpi_put_value(p_vpi_value vp, int)
|
|||
switch (vp->format) {
|
||||
case vpiIntVal:
|
||||
return put_value_int_(vp);
|
||||
case vpiTimeVal:
|
||||
return put_value_time_(vp);
|
||||
default:
|
||||
fprintf(stderr, "Unsupported format %d.\n", (int)vp->format);
|
||||
fprintf(stderr, "Unsupported format %d seting sysfunc vec4 value.\n", (int)vp->format);
|
||||
assert(0);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -427,7 +427,7 @@ static vpiHandle vthr_vec_put_value(vpiHandle ref, s_vpi_value*vp, int)
|
|||
}
|
||||
|
||||
default:
|
||||
fprintf(stderr, "Unsupported format %d.\n", (int)vp->format);
|
||||
fprintf(stderr, "Unsupported format %d setting vec4 value.\n", (int)vp->format);
|
||||
assert(0);
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1204,6 +1204,7 @@ bool of_ASSIGN_AVE(vthread_t thr, vvp_code_t cp)
|
|||
}
|
||||
#else
|
||||
fprintf(stderr, "XXXX NOT IMPLEMENTED: %%assign/av/e ...\n");
|
||||
assert(0);
|
||||
#endif
|
||||
return true;
|
||||
}
|
||||
|
|
@ -1348,15 +1349,44 @@ bool of_ASSIGN_V0E(vthread_t thr, vvp_code_t cp)
|
|||
}
|
||||
#endif
|
||||
|
||||
/*
|
||||
* %assign/vec4/d <var-label> <delay>
|
||||
*/
|
||||
bool of_ASSIGN_VEC4D(vthread_t thr, vvp_code_t cp)
|
||||
{
|
||||
fprintf(stderr, "XXXX NOT IMPLEMENTED: %%assign/vec4/d\n");
|
||||
vvp_net_ptr_t ptr (cp->net, 0);
|
||||
unsigned del_index = cp->bit_idx[0];
|
||||
vvp_time64_t del = thr->words[del_index].w_int;
|
||||
|
||||
vvp_vector4_t value = thr->pop_vec4();
|
||||
|
||||
vvp_signal_value*sig = dynamic_cast<vvp_signal_value*> (cp->net->fil);
|
||||
assert(sig);
|
||||
|
||||
schedule_assign_vector(ptr, 0, sig->value_size(), value, del);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/*
|
||||
* %assign/vec4/e <var-label>
|
||||
*/
|
||||
bool of_ASSIGN_VEC4E(vthread_t thr, vvp_code_t cp)
|
||||
{
|
||||
fprintf(stderr, "XXXX NOT IMPLEMENTED: %%assign/vec4/e\n");
|
||||
vvp_net_ptr_t ptr (cp->net, 0);
|
||||
vvp_vector4_t value = thr->pop_vec4();
|
||||
|
||||
vvp_signal_value*sig = dynamic_cast<vvp_signal_value*> (cp->net->fil);
|
||||
assert(sig);
|
||||
|
||||
if (thr->ecount == 0) {
|
||||
schedule_assign_vector(ptr, 0, sig->value_size(), value, 0);
|
||||
} else {
|
||||
schedule_evctl(ptr, value, 0, sig->value_size(), thr->event, thr->ecount);
|
||||
}
|
||||
|
||||
thr->event = 0;
|
||||
thr->ecount = 0;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
@ -5493,36 +5523,6 @@ bool of_SET_DAR_OBJ_STR(vthread_t thr, vvp_code_t cp)
|
|||
return true;
|
||||
}
|
||||
|
||||
/*
|
||||
* This implements the "%set/v <label>, <bit>, <wid>" instruction.
|
||||
*
|
||||
* The <label> is a reference to a vvp_net_t object, and it is in
|
||||
* cp->net.
|
||||
*
|
||||
* The <bit> is the thread bit address, and is in cp->bin_idx[0].
|
||||
*
|
||||
* The <wid> is the width of the vector I'm to make, and is in
|
||||
* cp->bin_idx[1].
|
||||
*/
|
||||
bool of_SET_VEC(vthread_t thr, vvp_code_t cp)
|
||||
{
|
||||
#if 0
|
||||
assert(cp->bit_idx[1] > 0);
|
||||
unsigned bit = cp->bit_idx[0];
|
||||
unsigned wid = cp->bit_idx[1];
|
||||
|
||||
/* set the value into port 0 of the destination. */
|
||||
vvp_net_ptr_t ptr (cp->net, 0);
|
||||
|
||||
vvp_send_vec4(ptr, vthread_bits_to_vector(thr, bit, wid),
|
||||
thr->wt_context);
|
||||
#else
|
||||
fprintf(stderr, "XXXX NOT IMPLEMENTED: %%set/vec ...\n");
|
||||
#endif
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Implement the %set/x instruction:
|
||||
*
|
||||
|
|
@ -5582,6 +5582,7 @@ bool of_SET_X0(vthread_t thr, vvp_code_t cp)
|
|||
vvp_send_vec4_pv(ptr, bit_vec, index, wid, sig->value_size(), thr->wt_context);
|
||||
#else
|
||||
fprintf(stderr, "XXXX NOT IMPLEMENTED: %%set/x0 ...\n");
|
||||
assert(0);
|
||||
#endif
|
||||
return true;
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue