Merge pull request #1062 from larsclausen/replicate-for-concat-repeat
Use NetReplicate to implement replication for concat
This commit is contained in:
commit
c53b1c0101
|
|
@ -776,23 +776,24 @@ NetNet* NetEConcat::synthesize(Design*des, NetScope*scope, NetExpr*root)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Make a NetNet object to carry the output vector. */
|
NetNet *osig = nullptr;
|
||||||
perm_string path = scope->local_symbol();
|
|
||||||
netvector_t*osig_vec = new netvector_t(data_type, expr_width()-1, 0);
|
|
||||||
NetNet*osig = new NetNet(scope, path, NetNet::IMPLICIT, osig_vec);
|
|
||||||
osig->set_line(*this);
|
|
||||||
osig->local_flag(true);
|
|
||||||
|
|
||||||
NetConcat*cncat = new NetConcat(scope, scope->local_symbol(),
|
if (num_parms != 1) {
|
||||||
osig->vector_width(),
|
/* Make a NetNet object to carry the output vector. */
|
||||||
num_parms * repeat());
|
auto osig_vec = new netvector_t(data_type, expr_width() / repeat() - 1, 0);
|
||||||
cncat->set_line(*this);
|
osig = new NetNet(scope, scope->local_symbol(), NetNet::IMPLICIT,
|
||||||
des->add_node(cncat);
|
osig_vec);
|
||||||
connect(cncat->pin(0), osig->pin(0));
|
osig->set_line(*this);
|
||||||
|
osig->local_flag(true);
|
||||||
|
|
||||||
unsigned count_input_width = 0;
|
auto cncat = new NetConcat(scope, scope->local_symbol(),
|
||||||
unsigned cur_pin = 1;
|
osig->vector_width(), num_parms);
|
||||||
for (unsigned rpt = 0; rpt < repeat(); rpt += 1) {
|
cncat->set_line(*this);
|
||||||
|
des->add_node(cncat);
|
||||||
|
connect(cncat->pin(0), osig->pin(0));
|
||||||
|
|
||||||
|
unsigned count_input_width = 0;
|
||||||
|
unsigned cur_pin = 1;
|
||||||
for (unsigned idx = 0 ; idx < parms_.size() ; idx += 1) {
|
for (unsigned idx = 0 ; idx < parms_.size() ; idx += 1) {
|
||||||
unsigned concat_item = parms_.size()-idx-1;
|
unsigned concat_item = parms_.size()-idx-1;
|
||||||
if (tmp[concat_item] == 0) continue;
|
if (tmp[concat_item] == 0) continue;
|
||||||
|
|
@ -800,14 +801,38 @@ NetNet* NetEConcat::synthesize(Design*des, NetScope*scope, NetExpr*root)
|
||||||
cur_pin += 1;
|
cur_pin += 1;
|
||||||
count_input_width += tmp[concat_item]->vector_width();
|
count_input_width += tmp[concat_item]->vector_width();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (count_input_width != osig->vector_width()) {
|
||||||
|
cerr << get_fileline() << ": internal error: "
|
||||||
|
<< "NetEConcat input width = " << count_input_width
|
||||||
|
<< ", expecting " << osig->vector_width()
|
||||||
|
<< endl;
|
||||||
|
des->errors += 1;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
/* There is exactly one input signal */
|
||||||
|
for (unsigned idx = 0; idx < parms_.size(); idx++) {
|
||||||
|
if (tmp[idx]) {
|
||||||
|
osig = tmp[idx];
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ivl_assert(*this, osig);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (count_input_width != osig->vector_width()) {
|
if (repeat() != 1) {
|
||||||
cerr << get_fileline() << ": internal error: "
|
auto rep = new NetReplicate(scope, scope->local_symbol(),
|
||||||
<< "NetEConcat input width = " << count_input_width
|
expr_width(), repeat());
|
||||||
<< ", expecting " << osig->vector_width()
|
rep->set_line(*this);
|
||||||
<< " (repeat=" << repeat() << ")" << endl;
|
des->add_node(rep);
|
||||||
des->errors += 1;
|
connect(rep->pin(1), osig->pin(0));
|
||||||
|
|
||||||
|
auto osig_vec = new netvector_t(data_type, expr_width() - 1, 0);
|
||||||
|
osig = new NetNet(scope, scope->local_symbol(), NetNet::IMPLICIT,
|
||||||
|
osig_vec);
|
||||||
|
osig->set_line(*this);
|
||||||
|
osig->local_flag(true);
|
||||||
|
connect(rep->pin(0), osig->pin(0));
|
||||||
}
|
}
|
||||||
|
|
||||||
delete[]tmp;
|
delete[]tmp;
|
||||||
|
|
|
||||||
|
|
@ -234,6 +234,13 @@ void vvp_fun_repeat::recv_vec4(vvp_net_ptr_t port, const vvp_vector4_t&bit,
|
||||||
port.ptr()->send_vec4(val, 0);
|
port.ptr()->send_vec4(val, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void vvp_fun_repeat::recv_vec4_pv(vvp_net_ptr_t port, const vvp_vector4_t &bit,
|
||||||
|
unsigned base, unsigned vwid,
|
||||||
|
vvp_context_t context)
|
||||||
|
{
|
||||||
|
recv_vec4_pv_(port, bit, base, vwid, context);
|
||||||
|
}
|
||||||
|
|
||||||
void compile_repeat(char*label, long width, long repeat, struct symb_s arg)
|
void compile_repeat(char*label, long width, long repeat, struct symb_s arg)
|
||||||
{
|
{
|
||||||
vvp_fun_repeat*fun = new vvp_fun_repeat(width, repeat);
|
vvp_fun_repeat*fun = new vvp_fun_repeat(width, repeat);
|
||||||
|
|
|
||||||
|
|
@ -1450,6 +1450,9 @@ class vvp_fun_repeat : public vvp_net_fun_t {
|
||||||
|
|
||||||
void recv_vec4(vvp_net_ptr_t port, const vvp_vector4_t&bit,
|
void recv_vec4(vvp_net_ptr_t port, const vvp_vector4_t&bit,
|
||||||
vvp_context_t context);
|
vvp_context_t context);
|
||||||
|
void recv_vec4_pv(vvp_net_ptr_t port, const vvp_vector4_t&bit,
|
||||||
|
unsigned int base, unsigned int vwid,
|
||||||
|
vvp_context_t context) final;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
unsigned wid_;
|
unsigned wid_;
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue