ivl: Casting vectors to dynamic arrays.
This commit is contained in:
parent
a52242745a
commit
8b3667f76e
3
PExpr.h
3
PExpr.h
|
|
@ -999,6 +999,9 @@ class PECastType : public PExpr {
|
||||||
|
|
||||||
void dump(ostream &out) const;
|
void dump(ostream &out) const;
|
||||||
|
|
||||||
|
virtual NetExpr*elaborate_expr(Design*des, NetScope*scope,
|
||||||
|
ivl_type_t type, unsigned flags) const;
|
||||||
|
|
||||||
virtual NetExpr*elaborate_expr(Design*des, NetScope*scope,
|
virtual NetExpr*elaborate_expr(Design*des, NetScope*scope,
|
||||||
unsigned expr_wid, unsigned flags) const;
|
unsigned expr_wid, unsigned flags) const;
|
||||||
|
|
||||||
|
|
|
||||||
33
elab_expr.cc
33
elab_expr.cc
|
|
@ -2541,6 +2541,39 @@ unsigned PECastType::test_width(Design*des, NetScope*scope, width_mode_t&wid)
|
||||||
return expr_width_;
|
return expr_width_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
NetExpr* PECastType::elaborate_expr(Design*des, NetScope*scope,
|
||||||
|
ivl_type_t type, unsigned) const
|
||||||
|
{
|
||||||
|
const netdarray_t*darray = NULL;
|
||||||
|
const netvector_t*vector = NULL;
|
||||||
|
|
||||||
|
// Casting array of vectors to dynamic array type
|
||||||
|
if((darray = dynamic_cast<const netdarray_t*>(type)) &&
|
||||||
|
(vector = dynamic_cast<const netvector_t*>(darray->element_type()))) {
|
||||||
|
PExpr::width_mode_t mode = PExpr::SIZED;
|
||||||
|
unsigned use_wid = base_->test_width(des, scope, mode);
|
||||||
|
NetExpr*base = base_->elaborate_expr(des, scope, use_wid, NO_FLAGS);
|
||||||
|
|
||||||
|
assert(vector->packed_width() > 0);
|
||||||
|
assert(base->expr_width() > 0);
|
||||||
|
|
||||||
|
// Find rounded up length that can fit the whole casted array of vectors
|
||||||
|
int len = base->expr_width() + vector->packed_width() - 1;
|
||||||
|
if(base->expr_width() > vector->packed_width()) {
|
||||||
|
len /= vector->packed_width();
|
||||||
|
} else {
|
||||||
|
len /= base->expr_width();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Number of words in the created dynamic array
|
||||||
|
NetEConst*len_expr = new NetEConst(verinum(len));
|
||||||
|
return new NetENew(type, len_expr, base);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fallback
|
||||||
|
return elaborate_expr(des, scope, (unsigned) 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
NetExpr* PECastType::elaborate_expr(Design*des, NetScope*scope,
|
NetExpr* PECastType::elaborate_expr(Design*des, NetScope*scope,
|
||||||
unsigned, unsigned) const
|
unsigned, unsigned) const
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -129,12 +129,15 @@ static int eval_darray_new(ivl_expr_t ex)
|
||||||
unsigned wid;
|
unsigned wid;
|
||||||
switch (ivl_type_base(element_type)) {
|
switch (ivl_type_base(element_type)) {
|
||||||
case IVL_VT_BOOL:
|
case IVL_VT_BOOL:
|
||||||
|
case IVL_VT_LOGIC:
|
||||||
wid = width_of_packed_type(element_type);
|
wid = width_of_packed_type(element_type);
|
||||||
draw_eval_vec4(init_expr);
|
|
||||||
resize_vec4_wid(init_expr, wid);
|
|
||||||
for (idx = 0 ; idx < cnt ; idx += 1) {
|
for (idx = 0 ; idx < cnt ; idx += 1) {
|
||||||
fprintf(vvp_out, " %%ix/load 3, %ld, 0;\n", idx);
|
draw_eval_vec4(init_expr);
|
||||||
|
fprintf(vvp_out, " %%parti/%c %d, %ld, 6;\n",
|
||||||
|
ivl_expr_signed(init_expr) ? 's' : 'u', wid, idx * wid);
|
||||||
|
fprintf(vvp_out, " %%ix/load 3, %ld, 0;\n", cnt - idx - 1);
|
||||||
fprintf(vvp_out, " %%set/dar/obj/vec4 3;\n");
|
fprintf(vvp_out, " %%set/dar/obj/vec4 3;\n");
|
||||||
|
fprintf(vvp_out, " %%pop/vec4 1;\n");
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case IVL_VT_REAL:
|
case IVL_VT_REAL:
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue