@@ -8,7 +8,9 @@ PRIVATE_NAMESPACE_BEGIN
88
99// ============================================================================
1010
11- void create_ql_macc_dsp (ql_dsp_macc_pm &pm)
11+ bool use_dsp_cfg_params;
12+
13+ static void create_ql_macc_dsp (ql_dsp_macc_pm &pm)
1214{
1315 auto &st = pm.st_ql_dsp_macc ;
1416
@@ -78,16 +80,21 @@ void create_ql_macc_dsp(ql_dsp_macc_pm &pm)
7880 size_t tgt_b_width;
7981 size_t tgt_z_width;
8082
83+ string cell_base_name = " dsp_t1" ;
84+ string cell_size_name = " " ;
85+ string cell_cfg_name = " " ;
86+ string cell_full_name = " " ;
87+
8188 if (min_width <= 2 && max_width <= 2 && z_width <= 4 ) {
8289 // Too narrow
8390 return ;
8491 } else if (min_width <= 9 && max_width <= 10 && z_width <= 19 ) {
85- type = RTLIL::escape_id ( " dsp_t1_10x9x32 " ) ;
92+ cell_size_name = " _10x9x32 " ;
8693 tgt_a_width = 10 ;
8794 tgt_b_width = 9 ;
8895 tgt_z_width = 19 ;
8996 } else if (min_width <= 18 && max_width <= 20 && z_width <= 38 ) {
90- type = RTLIL::escape_id ( " dsp_t1_20x18x64 " ) ;
97+ cell_size_name = " _20x18x64 " ;
9198 tgt_a_width = 20 ;
9299 tgt_b_width = 18 ;
93100 tgt_z_width = 38 ;
@@ -96,6 +103,14 @@ void create_ql_macc_dsp(ql_dsp_macc_pm &pm)
96103 return ;
97104 }
98105
106+ if (use_dsp_cfg_params)
107+ cell_cfg_name = " _cfg_params" ;
108+ else
109+ cell_cfg_name = " _cfg_ports" ;
110+
111+ cell_full_name = cell_base_name + cell_size_name + cell_cfg_name;
112+
113+ type = RTLIL::escape_id (cell_full_name);
99114 log (" Inferring MACC %zux%zu->%zu as %s from:\n " , a_width, b_width, z_width, RTLIL::unescape_id (type).c_str ());
100115
101116 for (auto cell : {st.mul , st.add , st.mux , st.ff }) {
@@ -199,19 +214,26 @@ void create_ql_macc_dsp(ql_dsp_macc_pm &pm)
199214 cell->setPort (RTLIL::escape_id (" unsigned_a_i" ), RTLIL::SigSpec (a_signed ? RTLIL::S0 : RTLIL::S1));
200215 cell->setPort (RTLIL::escape_id (" unsigned_b_i" ), RTLIL::SigSpec (b_signed ? RTLIL::S0 : RTLIL::S1));
201216
202- // Connect config ports
203- cell->setPort (RTLIL::escape_id (" saturate_enable_i" ), RTLIL::SigSpec (RTLIL::S0));
204- cell->setPort (RTLIL::escape_id (" shift_right_i" ), RTLIL::SigSpec (RTLIL::S0, 6 ));
205- cell->setPort (RTLIL::escape_id (" round_i" ), RTLIL::SigSpec (RTLIL::S0));
206- cell->setPort (RTLIL::escape_id (" register_inputs_i" ), RTLIL::SigSpec (RTLIL::S0));
217+ // Connect config bits
218+ if (use_dsp_cfg_params) {
219+ cell->setParam (RTLIL::escape_id (" SATURATE_ENABLE" ), RTLIL::Const (RTLIL::S0));
220+ cell->setParam (RTLIL::escape_id (" SHIFT_RIGHT" ), RTLIL::Const (RTLIL::S0, 6 ));
221+ cell->setParam (RTLIL::escape_id (" ROUND" ), RTLIL::Const (RTLIL::S0));
222+ cell->setParam (RTLIL::escape_id (" REGISTER_INPUTS" ), RTLIL::Const (RTLIL::S0));
223+ // 3 - output post acc; 1 - output pre acc
224+ cell->setParam (RTLIL::escape_id (" OUTPUT_SELECT" ), out_ff ? RTLIL::Const (1 , 3 ) : RTLIL::Const (3 , 3 ));
225+ } else {
226+ cell->setPort (RTLIL::escape_id (" saturate_enable_i" ), RTLIL::SigSpec (RTLIL::S0));
227+ cell->setPort (RTLIL::escape_id (" shift_right_i" ), RTLIL::SigSpec (RTLIL::S0, 6 ));
228+ cell->setPort (RTLIL::escape_id (" round_i" ), RTLIL::SigSpec (RTLIL::S0));
229+ cell->setPort (RTLIL::escape_id (" register_inputs_i" ), RTLIL::SigSpec (RTLIL::S0));
230+ // 3 - output post acc; 1 - output pre acc
231+ cell->setPort (RTLIL::escape_id (" output_select_i" ), out_ff ? RTLIL::Const (1 , 3 ) : RTLIL::Const (3 , 3 ));
232+ }
207233
208234 bool subtract = (st.add ->type == RTLIL::escape_id (" $sub" ));
209235 cell->setPort (RTLIL::escape_id (" subtract_i" ), RTLIL::SigSpec (subtract ? RTLIL::S1 : RTLIL::S0));
210236
211- // 3 - output post acc
212- // 1 - output pre acc
213- cell->setPort (RTLIL::escape_id (" output_select_i" ), out_ff ? RTLIL::Const (1 , 3 ) : RTLIL::Const (3 , 3 ));
214-
215237 // Mark the cells for removal
216238 pm.autoremove (st.mul );
217239 pm.autoremove (st.add );
@@ -230,14 +252,25 @@ struct QlDspMacc : public Pass {
230252 log (" \n " );
231253 log (" ql_dsp_macc [options] [selection]\n " );
232254 log (" \n " );
255+ log (" -use_dsp_cfg_params\n " );
256+ log (" By default use DSP blocks with configuration bits available at module ports.\n " );
257+ log (" Specifying this forces usage of DSP block with configuration bits available as module parameters\n " );
258+ log (" \n " );
233259 }
234260
261+ void clear_flags () override { use_dsp_cfg_params = false ; }
262+
235263 void execute (std::vector<std::string> a_Args, RTLIL::Design *a_Design) override
236264 {
237265 log_header (a_Design, " Executing QL_DSP_MACC pass.\n " );
238266
239267 size_t argidx;
240268 for (argidx = 1 ; argidx < a_Args.size (); argidx++) {
269+ if (a_Args[argidx] == " -use_dsp_cfg_params" ) {
270+ use_dsp_cfg_params = true ;
271+ continue ;
272+ }
273+
241274 break ;
242275 }
243276 extra_args (a_Args, argidx, a_Design);
@@ -246,6 +279,7 @@ struct QlDspMacc : public Pass {
246279 ql_dsp_macc_pm (module , module ->selected_cells ()).run_ql_dsp_macc (create_ql_macc_dsp);
247280 }
248281 }
282+
249283} QlDspMacc;
250284
251285PRIVATE_NAMESPACE_END
0 commit comments