mirror of
https://github.com/YosysHQ/yosys
synced 2025-04-12 12:08:19 +00:00
quicklogic: add fracturable full-block dspv1 to keep vendor simulation model unchanged
This commit is contained in:
parent
9e79b03b73
commit
2e31dd3070
|
@ -39,6 +39,7 @@ $(eval $(call add_gen_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic
|
||||||
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/cells_sim.v))
|
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/cells_sim.v))
|
||||||
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/ffs_map.v))
|
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/ffs_map.v))
|
||||||
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/dspv1_sim.v))
|
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/dspv1_sim.v))
|
||||||
|
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/dspv1_sim_extra.v))
|
||||||
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/dspv1_map.v))
|
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/dspv1_map.v))
|
||||||
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/dspv1_final_map.v))
|
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/dspv1_final_map.v))
|
||||||
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/dspv2_sim.v))
|
$(eval $(call add_share_file,share/quicklogic/qlf_k6n10f,techlibs/quicklogic/qlf_k6n10f/dspv2_sim.v))
|
||||||
|
|
|
@ -61,7 +61,6 @@ static void create_ql_macc_dsp(ql_dsp_macc_pm &pm, int dsp_version)
|
||||||
cell_base_name = "dspv2";
|
cell_base_name = "dspv2";
|
||||||
|
|
||||||
std::function<void(Cell*)> set_fractured = nullptr;
|
std::function<void(Cell*)> set_fractured = nullptr;
|
||||||
auto set_fractured_dspv1 = [](Cell* cell) -> void {cell->setPort(ID(f_mode_i), State::S0);};
|
|
||||||
auto set_fractured_dspv2 = [](Cell* cell) -> void {cell->setParam(ID(FRAC_MODE), State::S0);};
|
auto set_fractured_dspv2 = [](Cell* cell) -> void {cell->setParam(ID(FRAC_MODE), State::S0);};
|
||||||
|
|
||||||
if (min_width <= 2 && max_width <= 2 && z_width <= 4) {
|
if (min_width <= 2 && max_width <= 2 && z_width <= 4) {
|
||||||
|
@ -81,7 +80,6 @@ static void create_ql_macc_dsp(ql_dsp_macc_pm &pm, int dsp_version)
|
||||||
tgt_a_width = 20;
|
tgt_a_width = 20;
|
||||||
tgt_b_width = 18;
|
tgt_b_width = 18;
|
||||||
tgt_z_width = 38;
|
tgt_z_width = 38;
|
||||||
set_fractured = set_fractured_dspv1;
|
|
||||||
} else {
|
} else {
|
||||||
reject = true;
|
reject = true;
|
||||||
}
|
}
|
||||||
|
|
|
@ -87,7 +87,7 @@ struct QlDspSimdPass : public Pass {
|
||||||
log_header(a_Design, "Executing QL_DSP_SIMD pass.\n");
|
log_header(a_Design, "Executing QL_DSP_SIMD pass.\n");
|
||||||
|
|
||||||
// The following lists have to match simulation model interfaces.
|
// The following lists have to match simulation model interfaces.
|
||||||
|
|
||||||
// DSP control and config ports that must be equal between
|
// DSP control and config ports that must be equal between
|
||||||
// merged half-blocks
|
// merged half-blocks
|
||||||
// In addition to functional differences,
|
// In addition to functional differences,
|
||||||
|
@ -156,13 +156,13 @@ struct QlDspSimdPass : public Pass {
|
||||||
ID(c_i),
|
ID(c_i),
|
||||||
ID(z_o),
|
ID(z_o),
|
||||||
};
|
};
|
||||||
|
|
||||||
// Source DSP cell type (half-block)
|
// Source DSP cell type (half-block)
|
||||||
static const IdString m_Dspv1SisdType = ID(dsp_t1_10x9x32_cfg_ports);
|
static const IdString m_Dspv1SisdType = ID(dsp_t1_10x9x32_cfg_ports);
|
||||||
static const IdString m_Dspv2SisdType = ID(dspv2_16x9x32_cfg_ports);
|
static const IdString m_Dspv2SisdType = ID(dspv2_16x9x32_cfg_ports);
|
||||||
|
|
||||||
// Target DSP cell types (full-block)
|
// Target DSP cell types (full-block)
|
||||||
static const IdString m_Dspv1SimdType = ID(dsp_t1_20x18x64_cfg_ports);
|
static const IdString m_Dspv1SimdType = ID(dsp_t1_20x18x64_cfg_ports_fracturable);
|
||||||
static const IdString m_Dspv2SimdType = ID(dspv2_32x18x64_cfg_ports);
|
static const IdString m_Dspv2SimdType = ID(dspv2_32x18x64_cfg_ports);
|
||||||
|
|
||||||
// Parse args
|
// Parse args
|
||||||
|
@ -241,7 +241,7 @@ struct QlDspSimdPass : public Pass {
|
||||||
// Check if the target cell is known (important to know
|
// Check if the target cell is known (important to know
|
||||||
// its port widths)
|
// its port widths)
|
||||||
if (!simd->known())
|
if (!simd->known())
|
||||||
log_error(" The target cell type '%s' is not known!", log_id(simd));
|
log_error(" The target cell type '%s' is not known!", log_id(simd->type));
|
||||||
// Connect common ports
|
// Connect common ports
|
||||||
|
|
||||||
for (auto port : cfg_ports) {
|
for (auto port : cfg_ports) {
|
||||||
|
|
|
@ -14,7 +14,7 @@
|
||||||
//
|
//
|
||||||
// SPDX-License-Identifier: Apache-2.0
|
// SPDX-License-Identifier: Apache-2.0
|
||||||
|
|
||||||
module dsp_t1_20x18x64_cfg_ports (
|
module dsp_t1_20x18x64_cfg_ports_fracturable (
|
||||||
input [19:0] a_i,
|
input [19:0] a_i,
|
||||||
input [17:0] b_i,
|
input [17:0] b_i,
|
||||||
input [ 5:0] acc_fir_i,
|
input [ 5:0] acc_fir_i,
|
||||||
|
@ -60,7 +60,7 @@ module dsp_t1_20x18x64_cfg_ports (
|
||||||
.unsigned_a (unsigned_a_i),
|
.unsigned_a (unsigned_a_i),
|
||||||
.unsigned_b (unsigned_b_i),
|
.unsigned_b (unsigned_b_i),
|
||||||
|
|
||||||
.f_mode (f_mode_i), // No fracturation
|
.f_mode (f_mode_i),
|
||||||
.output_select (output_select_i),
|
.output_select (output_select_i),
|
||||||
.saturate_enable (saturate_enable_i),
|
.saturate_enable (saturate_enable_i),
|
||||||
.shift_right (shift_right_i),
|
.shift_right (shift_right_i),
|
||||||
|
@ -71,6 +71,62 @@ module dsp_t1_20x18x64_cfg_ports (
|
||||||
|
|
||||||
endmodule
|
endmodule
|
||||||
|
|
||||||
|
module dsp_t1_20x18x64_cfg_ports (
|
||||||
|
input [19:0] a_i,
|
||||||
|
input [17:0] b_i,
|
||||||
|
input [ 5:0] acc_fir_i,
|
||||||
|
output [37:0] z_o,
|
||||||
|
output [17:0] dly_b_o,
|
||||||
|
|
||||||
|
input clock_i,
|
||||||
|
input reset_i,
|
||||||
|
|
||||||
|
input [2:0] feedback_i,
|
||||||
|
input load_acc_i,
|
||||||
|
input unsigned_a_i,
|
||||||
|
input unsigned_b_i,
|
||||||
|
|
||||||
|
input [2:0] output_select_i,
|
||||||
|
input saturate_enable_i,
|
||||||
|
input [5:0] shift_right_i,
|
||||||
|
input round_i,
|
||||||
|
input subtract_i,
|
||||||
|
input register_inputs_i
|
||||||
|
);
|
||||||
|
|
||||||
|
parameter [19:0] COEFF_0 = 20'd0;
|
||||||
|
parameter [19:0] COEFF_1 = 20'd0;
|
||||||
|
parameter [19:0] COEFF_2 = 20'd0;
|
||||||
|
parameter [19:0] COEFF_3 = 20'd0;
|
||||||
|
|
||||||
|
dsp_t1_20x18x64_cfg_ports_fracturable # (
|
||||||
|
.COEFF_0 (COEFF_0),
|
||||||
|
.COEFF_1 (COEFF_1),
|
||||||
|
.COEFF_2 (COEFF_2),
|
||||||
|
.COEFF_3 (COEFF_3)
|
||||||
|
) _TECHMAP_REPLACE_ (
|
||||||
|
.a_i (a_i),
|
||||||
|
.b_i (b_i),
|
||||||
|
.acc_fir_i (acc_fir_i),
|
||||||
|
.z_o (z_o),
|
||||||
|
.dly_b_o (dly_b_o),
|
||||||
|
.clock_i (clock_i),
|
||||||
|
.reset_i (reset_i),
|
||||||
|
.feedback_i (feedback_i),
|
||||||
|
.load_acc_i (load_acc_i),
|
||||||
|
.unsigned_a_i (unsigned_a_i),
|
||||||
|
.unsigned_b_i (unsigned_b_i),
|
||||||
|
.output_select_i (output_select_i),
|
||||||
|
.saturate_enable_i (saturate_enable_i),
|
||||||
|
.shift_right_i (shift_right_i),
|
||||||
|
.round_i (round_i),
|
||||||
|
.subtract_i (subtract_i),
|
||||||
|
.register_inputs_i (register_inputs_i),
|
||||||
|
.f_mode_i (1'b0)
|
||||||
|
);
|
||||||
|
|
||||||
|
endmodule
|
||||||
|
|
||||||
module dsp_t1_10x9x32_cfg_ports (
|
module dsp_t1_10x9x32_cfg_ports (
|
||||||
input [ 9:0] a_i,
|
input [ 9:0] a_i,
|
||||||
input [ 8:0] b_i,
|
input [ 8:0] b_i,
|
||||||
|
@ -123,7 +179,7 @@ module dsp_t1_10x9x32_cfg_ports (
|
||||||
.unsigned_a (unsigned_a_i),
|
.unsigned_a (unsigned_a_i),
|
||||||
.unsigned_b (unsigned_b_i),
|
.unsigned_b (unsigned_b_i),
|
||||||
|
|
||||||
.f_mode (1'b1), // Enable fractuation, Use the lower half
|
.f_mode (1'b0),
|
||||||
.output_select (output_select_i),
|
.output_select (output_select_i),
|
||||||
.saturate_enable (saturate_enable_i),
|
.saturate_enable (saturate_enable_i),
|
||||||
.shift_right (shift_right_i),
|
.shift_right (shift_right_i),
|
||||||
|
|
|
@ -4195,8 +4195,7 @@ module dsp_t1_20x18x64_cfg_ports (
|
||||||
input wire [ 5:0] shift_right_i,
|
input wire [ 5:0] shift_right_i,
|
||||||
input wire round_i,
|
input wire round_i,
|
||||||
input wire subtract_i,
|
input wire subtract_i,
|
||||||
input wire register_inputs_i,
|
input wire register_inputs_i
|
||||||
input wire f_mode_i
|
|
||||||
);
|
);
|
||||||
|
|
||||||
parameter [19:0] COEFF_0 = 20'd0;
|
parameter [19:0] COEFF_0 = 20'd0;
|
||||||
|
@ -4212,7 +4211,7 @@ module dsp_t1_20x18x64_cfg_ports (
|
||||||
.z(z_o),
|
.z(z_o),
|
||||||
.dly_b(dly_b_o),
|
.dly_b(dly_b_o),
|
||||||
|
|
||||||
.f_mode(f_mode_i), // 20x18x64 DSP
|
.f_mode(1'b0), // 20x18x64 DSP
|
||||||
|
|
||||||
.acc_fir(acc_fir_i),
|
.acc_fir(acc_fir_i),
|
||||||
.feedback(feedback_i),
|
.feedback(feedback_i),
|
||||||
|
|
80
techlibs/quicklogic/qlf_k6n10f/dspv1_sim_extra.v
Normal file
80
techlibs/quicklogic/qlf_k6n10f/dspv1_sim_extra.v
Normal file
|
@ -0,0 +1,80 @@
|
||||||
|
// Copyright 2020-2022 F4PGA Authors
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
//
|
||||||
|
// SPDX-License-Identifier: Apache-2.0
|
||||||
|
|
||||||
|
`timescale 1ps/1ps
|
||||||
|
|
||||||
|
`default_nettype none
|
||||||
|
|
||||||
|
// dsp_t1_20x18x64_cfg_ports but with input wire f_mode_i
|
||||||
|
// This is a yosys-specific extension beyond the vendor-provided model
|
||||||
|
module dsp_t1_20x18x64_cfg_ports_fracturable (
|
||||||
|
input wire [19:0] a_i,
|
||||||
|
input wire [17:0] b_i,
|
||||||
|
input wire [ 5:0] acc_fir_i,
|
||||||
|
output wire [37:0] z_o,
|
||||||
|
output wire [17:0] dly_b_o,
|
||||||
|
|
||||||
|
(* clkbuf_sink *)
|
||||||
|
input wire clock_i,
|
||||||
|
input wire reset_i,
|
||||||
|
|
||||||
|
input wire [ 2:0] feedback_i,
|
||||||
|
input wire load_acc_i,
|
||||||
|
input wire unsigned_a_i,
|
||||||
|
input wire unsigned_b_i,
|
||||||
|
|
||||||
|
input wire [ 2:0] output_select_i,
|
||||||
|
input wire saturate_enable_i,
|
||||||
|
input wire [ 5:0] shift_right_i,
|
||||||
|
input wire round_i,
|
||||||
|
input wire subtract_i,
|
||||||
|
input wire register_inputs_i,
|
||||||
|
input wire f_mode_i
|
||||||
|
);
|
||||||
|
|
||||||
|
parameter [19:0] COEFF_0 = 20'd0;
|
||||||
|
parameter [19:0] COEFF_1 = 20'd0;
|
||||||
|
parameter [19:0] COEFF_2 = 20'd0;
|
||||||
|
parameter [19:0] COEFF_3 = 20'd0;
|
||||||
|
|
||||||
|
QL_DSP2 #(
|
||||||
|
.MODE_BITS({COEFF_3, COEFF_2, COEFF_1, COEFF_0})
|
||||||
|
) dsp (
|
||||||
|
.a(a_i),
|
||||||
|
.b(b_i),
|
||||||
|
.z(z_o),
|
||||||
|
.dly_b(dly_b_o),
|
||||||
|
|
||||||
|
.f_mode(f_mode_i), // 20x18x64 DSP
|
||||||
|
|
||||||
|
.acc_fir(acc_fir_i),
|
||||||
|
.feedback(feedback_i),
|
||||||
|
.load_acc(load_acc_i),
|
||||||
|
|
||||||
|
.unsigned_a(unsigned_a_i),
|
||||||
|
.unsigned_b(unsigned_b_i),
|
||||||
|
|
||||||
|
.clk(clock_i),
|
||||||
|
.reset(reset_i),
|
||||||
|
|
||||||
|
.saturate_enable(saturate_enable_i),
|
||||||
|
.output_select(output_select_i),
|
||||||
|
.round(round_i),
|
||||||
|
.shift_right(shift_right_i),
|
||||||
|
.subtract(subtract_i),
|
||||||
|
.register_inputs(register_inputs_i)
|
||||||
|
);
|
||||||
|
endmodule
|
|
@ -208,9 +208,10 @@ struct SynthQuickLogicPass : public ScriptPass {
|
||||||
read_simlibs += stringf(" %sqlf_k6n10f/brams_sim.v", lib_path.c_str());
|
read_simlibs += stringf(" %sqlf_k6n10f/brams_sim.v", lib_path.c_str());
|
||||||
if (bramTypes)
|
if (bramTypes)
|
||||||
read_simlibs += stringf(" %sqlf_k6n10f/bram_types_sim.v", lib_path.c_str());
|
read_simlibs += stringf(" %sqlf_k6n10f/bram_types_sim.v", lib_path.c_str());
|
||||||
if (dsp == V1)
|
if (dsp == V1) {
|
||||||
read_simlibs += stringf(" %sqlf_k6n10f/dspv1_sim.v", lib_path.c_str());
|
read_simlibs += stringf(" %sqlf_k6n10f/dspv1_sim.v", lib_path.c_str());
|
||||||
else if (dsp == V2)
|
read_simlibs += stringf(" %sqlf_k6n10f/dspv1_sim_extra.v", lib_path.c_str());
|
||||||
|
} else if (dsp == V2)
|
||||||
read_simlibs += stringf(" %sqlf_k6n10f/dspv2_sim.v", lib_path.c_str());
|
read_simlibs += stringf(" %sqlf_k6n10f/dspv2_sim.v", lib_path.c_str());
|
||||||
}
|
}
|
||||||
run(read_simlibs);
|
run(read_simlibs);
|
||||||
|
|
|
@ -21,13 +21,14 @@ chtype -set $mul t:$__soft_mul
|
||||||
techmap -map +/mul2dsp.v -D DSP_A_MAXWIDTH=10 -D DSP_B_MAXWIDTH=9 -D DSP_A_MINWIDTH=4 -D DSP_B_MINWIDTH=4 -D DSP_NAME=$__QL_MUL10X9
|
techmap -map +/mul2dsp.v -D DSP_A_MAXWIDTH=10 -D DSP_B_MAXWIDTH=9 -D DSP_A_MINWIDTH=4 -D DSP_B_MINWIDTH=4 -D DSP_NAME=$__QL_MUL10X9
|
||||||
techmap -map +/quicklogic/qlf_k6n10f/dspv1_map.v -D USE_DSP_CFG_PARAMS=0
|
techmap -map +/quicklogic/qlf_k6n10f/dspv1_map.v -D USE_DSP_CFG_PARAMS=0
|
||||||
read_verilog -lib +/quicklogic/qlf_k6n10f/dspv1_sim.v
|
read_verilog -lib +/quicklogic/qlf_k6n10f/dspv1_sim.v
|
||||||
|
read_verilog -lib +/quicklogic/qlf_k6n10f/dspv1_sim_extra.v
|
||||||
|
|
||||||
select -assert-count 2 t:dsp_t1_10x9x32_cfg_ports
|
select -assert-count 2 t:dsp_t1_10x9x32_cfg_ports
|
||||||
select -assert-count 0 t:dsp_t1_20x18x64_cfg_ports
|
select -assert-count 0 t:dsp_t1_20x18x64_cfg_ports_fracturable
|
||||||
equiv_opt -assert -async2sync -map +/quicklogic/qlf_k6n10f/dspv1_sim.v ql_dsp_simd
|
equiv_opt -assert -async2sync -map +/quicklogic/qlf_k6n10f/dspv1_sim.v -map +/quicklogic/qlf_k6n10f/dspv1_sim_extra.v ql_dsp_simd
|
||||||
design -load postopt
|
design -load postopt
|
||||||
select -assert-count 0 t:dsp_t1_10x9x32_cfg_ports
|
select -assert-count 0 t:dsp_t1_10x9x32_cfg_ports
|
||||||
select -assert-count 1 t:dsp_t1_20x18x64_cfg_ports
|
select -assert-count 1 t:dsp_t1_20x18x64_cfg_ports_fracturable
|
||||||
|
|
||||||
design -reset
|
design -reset
|
||||||
|
|
||||||
|
@ -54,10 +55,11 @@ chtype -set $mul t:$__soft_mul
|
||||||
techmap -map +/mul2dsp.v -D DSP_A_MAXWIDTH=10 -D DSP_B_MAXWIDTH=9 -D DSP_A_MINWIDTH=4 -D DSP_B_MINWIDTH=4 -D DSP_NAME=$__QL_MUL10X9
|
techmap -map +/mul2dsp.v -D DSP_A_MAXWIDTH=10 -D DSP_B_MAXWIDTH=9 -D DSP_A_MINWIDTH=4 -D DSP_B_MINWIDTH=4 -D DSP_NAME=$__QL_MUL10X9
|
||||||
techmap -map +/quicklogic/qlf_k6n10f/dspv1_map.v -D USE_DSP_CFG_PARAMS=0
|
techmap -map +/quicklogic/qlf_k6n10f/dspv1_map.v -D USE_DSP_CFG_PARAMS=0
|
||||||
read_verilog -lib +/quicklogic/qlf_k6n10f/dspv1_sim.v
|
read_verilog -lib +/quicklogic/qlf_k6n10f/dspv1_sim.v
|
||||||
|
read_verilog -lib +/quicklogic/qlf_k6n10f/dspv1_sim_extra.v
|
||||||
|
|
||||||
select -assert-count 2 t:dsp_t1_10x9x32_cfg_ports
|
select -assert-count 2 t:dsp_t1_10x9x32_cfg_ports
|
||||||
select -assert-count 0 t:dsp_t1_20x18x64_cfg_ports
|
select -assert-count 0 t:dsp_t1_20x18x64_cfg_ports_fracturable
|
||||||
equiv_opt -assert -async2sync -map +/quicklogic/qlf_k6n10f/dspv1_sim.v ql_dsp_simd
|
equiv_opt -assert -async2sync -map +/quicklogic/qlf_k6n10f/dspv1_sim.v -map +/quicklogic/qlf_k6n10f/dspv1_sim_extra.v ql_dsp_simd
|
||||||
design -load postopt
|
design -load postopt
|
||||||
select -assert-count 0 t:dsp_t1_10x9x32_cfg_ports
|
select -assert-count 0 t:dsp_t1_10x9x32_cfg_ports
|
||||||
select -assert-count 1 t:dsp_t1_20x18x64_cfg_ports
|
select -assert-count 1 t:dsp_t1_20x18x64_cfg_ports_fracturable
|
||||||
|
|
Loading…
Reference in a new issue