From adb18d28b8f77538071340cac45d76a3a95de297 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 10:37:28 -0600 Subject: [PATCH 01/18] [Tool] Remove unused arguments --- openfpga/src/fpga_verilog/verilog_top_testbench.cpp | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/openfpga/src/fpga_verilog/verilog_top_testbench.cpp b/openfpga/src/fpga_verilog/verilog_top_testbench.cpp index c87073c67..13cfb52af 100644 --- a/openfpga/src/fpga_verilog/verilog_top_testbench.cpp +++ b/openfpga/src/fpga_verilog/verilog_top_testbench.cpp @@ -1953,7 +1953,6 @@ void print_verilog_full_testbench_configuration_chain_bitstream(std::fstream& fp const bool& bit_value_to_skip, const ModuleManager& module_manager, const ModuleId& top_module, - const BitstreamManager& bitstream_manager, const FabricBitstream& fabric_bitstream) { /* Validate the file stream */ valid_file_stream(fp); @@ -2078,7 +2077,7 @@ void print_verilog_full_testbench_bitstream(std::fstream& fp, fast_configuration, bit_value_to_skip, module_manager, top_module, - bitstream_manager, fabric_bitstream); + fabric_bitstream); break; case CONFIG_MEM_MEMORY_BANK: break; From 98308133c1f558bc35e973ee2f964861d064f19a Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 11:24:05 -0600 Subject: [PATCH 02/18] [Tool] Add configuration skip capability to top testbench which loads external bitstream file --- .../fpga_verilog/verilog_top_testbench.cpp | 65 ++++++++++++++++++- 1 file changed, 64 insertions(+), 1 deletion(-) diff --git a/openfpga/src/fpga_verilog/verilog_top_testbench.cpp b/openfpga/src/fpga_verilog/verilog_top_testbench.cpp index 13cfb52af..fb88e2bbf 100644 --- a/openfpga/src/fpga_verilog/verilog_top_testbench.cpp +++ b/openfpga/src/fpga_verilog/verilog_top_testbench.cpp @@ -63,6 +63,8 @@ constexpr char* TOP_TB_BITSTREAM_LENGTH_VARIABLE = "BITSTREAM_LENGTH"; constexpr char* TOP_TB_BITSTREAM_WIDTH_VARIABLE = "BITSTREAM_WIDTH"; constexpr char* TOP_TB_BITSTREAM_MEM_REG_NAME = "bit_mem"; constexpr char* TOP_TB_BITSTREAM_INDEX_REG_NAME = "bit_index"; +constexpr char* TOP_TB_BITSTREAM_ITERATOR_REG_NAME = "ibit"; +constexpr char* TOP_TB_BITSTREAM_SKIP_FLAG_REG_NAME = "skip_bits"; constexpr char* AUTOCHECK_TOP_TESTBENCH_VERILOG_MODULE_POSTFIX = "_autocheck_top_tb"; @@ -1983,7 +1985,12 @@ void print_verilog_full_testbench_configuration_chain_bitstream(std::fstream& fp fp << std::endl; fp << "reg [$clog2(`" << TOP_TB_BITSTREAM_LENGTH_VARIABLE << ") - 1:0] " << TOP_TB_BITSTREAM_INDEX_REG_NAME << ";" << std::endl; - + + BasicPort bit_skip_reg(TOP_TB_BITSTREAM_SKIP_FLAG_REG_NAME, 1); + print_verilog_comment(fp, "----- Registers used for fast configuration logic -----"); + fp << "reg [$clog2(`" << TOP_TB_BITSTREAM_LENGTH_VARIABLE << ") - 1:0] " << TOP_TB_BITSTREAM_ITERATOR_REG_NAME << ";" << std::endl; + fp << generate_verilog_port(VERILOG_PORT_REG, bit_skip_reg) << ";" << std::endl; + print_verilog_comment(fp, "----- Preload bitstream file to a virtual memory -----"); fp << "initial begin" << std::endl; fp << "\t"; @@ -2001,6 +2008,62 @@ void print_verilog_full_testbench_configuration_chain_bitstream(std::fstream& fp fp << ";"; fp << std::endl; + std::vector bit_skip_values(bit_skip_reg.get_width(), fast_configuration ? 1 : 0); + fp << "\t"; + fp << generate_verilog_port_constant_values(bit_skip_reg, bit_skip_values, true); + fp << ";"; + fp << std::endl; + + fp << "\t"; + fp << "for (" << TOP_TB_BITSTREAM_ITERATOR_REG_NAME << " = 0; "; + fp << TOP_TB_BITSTREAM_ITERATOR_REG_NAME << " < `" << TOP_TB_BITSTREAM_LENGTH_VARIABLE << " + 1; "; + fp << TOP_TB_BITSTREAM_ITERATOR_REG_NAME << " = " << TOP_TB_BITSTREAM_ITERATOR_REG_NAME << " + 1)"; + fp << " begin"; + fp << std::endl; + + fp << "\t\t"; + fp << "if ("; + fp << generate_verilog_constant_values(std::vector(fabric_bitstream.num_regions(), bit_value_to_skip)); + fp << " == "; + fp << TOP_TB_BITSTREAM_MEM_REG_NAME << "[" << TOP_TB_BITSTREAM_ITERATOR_REG_NAME << "]"; + fp << ")"; + fp << " begin"; + fp << std::endl; + + fp << "\t\t\t"; + fp << "if ("; + fp << generate_verilog_constant_values(std::vector(bit_skip_reg.get_width(), 1)); + fp << " == "; + fp << generate_verilog_port(VERILOG_PORT_CONKT, bit_skip_reg) << ")"; + fp << " begin"; + fp << std::endl; + + fp << "\t\t\t\t"; + fp << TOP_TB_BITSTREAM_INDEX_REG_NAME; + fp << " <= "; + fp << TOP_TB_BITSTREAM_INDEX_REG_NAME << " + 1"; + fp << ";" << std::endl; + + fp << "\t\t\t"; + fp << "end"; + fp << std::endl; + + fp << "\t\t"; + fp << "end else begin"; + fp << std::endl; + + fp << "\t\t\t"; + fp << generate_verilog_port_constant_values(bit_skip_reg, std::vector(bit_skip_reg.get_width(), 0), true); + fp << ";" << std::endl; + + fp << "\t\t"; + fp << "end"; + fp << std::endl; + + fp << "\t"; + fp << "end"; + fp << std::endl; + fp << "end"; fp << std::endl; From 81048d3698ec78d911239ddbefbc7f1e17c62d64 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 11:26:39 -0600 Subject: [PATCH 03/18] [Tool] Add option '--fast_configuration' to 'write_full_testbench' command --- openfpga/src/base/openfpga_verilog.cpp | 2 ++ openfpga/src/base/openfpga_verilog_command.cpp | 3 +++ 2 files changed, 5 insertions(+) diff --git a/openfpga/src/base/openfpga_verilog.cpp b/openfpga/src/base/openfpga_verilog.cpp index 6a3afdefd..6cfb9879a 100644 --- a/openfpga/src/base/openfpga_verilog.cpp +++ b/openfpga/src/base/openfpga_verilog.cpp @@ -130,6 +130,7 @@ int write_full_testbench(OpenfpgaContext& openfpga_ctx, CommandOptionId opt_fabric_netlist = cmd.option("fabric_netlist_file_path"); CommandOptionId opt_pcf = cmd.option("pin_constraints_file"); CommandOptionId opt_reference_benchmark = cmd.option("reference_benchmark_file_path"); + CommandOptionId opt_fast_configuration = cmd.option("fast_configuration"); CommandOptionId opt_explicit_port_mapping = cmd.option("explicit_port_mapping"); CommandOptionId opt_include_signal_init = cmd.option("include_signal_init"); CommandOptionId opt_verbose = cmd.option("verbose"); @@ -141,6 +142,7 @@ int write_full_testbench(OpenfpgaContext& openfpga_ctx, options.set_output_directory(cmd_context.option_value(cmd, opt_output_dir)); options.set_fabric_netlist_file_path(cmd_context.option_value(cmd, opt_fabric_netlist)); options.set_reference_benchmark_file_path(cmd_context.option_value(cmd, opt_reference_benchmark)); + options.set_fast_configuration(cmd_context.option_enable(cmd, opt_fast_configuration)); options.set_explicit_port_mapping(cmd_context.option_enable(cmd, opt_explicit_port_mapping)); options.set_verbose_output(cmd_context.option_enable(cmd, opt_verbose)); options.set_print_top_testbench(true); diff --git a/openfpga/src/base/openfpga_verilog_command.cpp b/openfpga/src/base/openfpga_verilog_command.cpp index 4518c0634..431eac47f 100644 --- a/openfpga/src/base/openfpga_verilog_command.cpp +++ b/openfpga/src/base/openfpga_verilog_command.cpp @@ -155,6 +155,9 @@ ShellCommandId add_openfpga_write_full_testbench_command(openfpga::Shell Date: Fri, 4 Jun 2021 11:28:10 -0600 Subject: [PATCH 04/18] [Script] Update openfpga shell script with fast configuration option --- .../write_full_testbench_example_script.openfpga | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga b/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga index 2a001ad30..8a87a0a08 100644 --- a/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga +++ b/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga @@ -55,7 +55,7 @@ write_fabric_verilog --file ./SRC --explicit_port_mapping --include_timing --pri # - Enable top-level testbench which is a full verification including programming circuit and core logic of FPGA # - Enable pre-configured top-level testbench which is a fast verification skipping programming phase # - Simulation ini file is optional and is needed only when you need to interface different HDL simulators using openfpga flow-run scripts -write_full_testbench --file ./SRC --reference_benchmark_file_path ${REFERENCE_VERILOG_TESTBENCH} --include_signal_init --explicit_port_mapping --bitstream fabric_bitstream.bit +write_full_testbench --file ./SRC --reference_benchmark_file_path ${REFERENCE_VERILOG_TESTBENCH} --include_signal_init --explicit_port_mapping --bitstream fabric_bitstream.bit ${OPENFPGA_FAST_CONFIGURATION} # Write the SDC files for PnR backend # - Turn on every options here From aa4e1f5f9a228f0c83769f171d3851aaea3cd6d2 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 11:29:43 -0600 Subject: [PATCH 05/18] [Test] Update test case which uses write_full_testbench openfpga shell script --- .../full_testbench/configuration_chain/config/task.conf | 1 + 1 file changed, 1 insertion(+) diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain/config/task.conf index f11b117cd..1f818415a 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain/config/task.conf @@ -20,6 +20,7 @@ openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scrip openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml openfpga_vpr_device_layout= +openfpga_fast_configuration= [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml From 2068291de03695a57f1e3d98b14c81024b3c6345 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 11:32:49 -0600 Subject: [PATCH 06/18] [Test] Now deploy the 'write_full_testbench' openfpga shell script to all the configuration chain test cases --- .../configuration_chain_config_enable_scff/config/task.conf | 4 +++- .../configuration_chain_use_reset/config/task.conf | 4 +++- .../configuration_chain_use_resetb/config/task.conf | 4 +++- .../configuration_chain_use_set/config/task.conf | 4 +++- .../configuration_chain_use_set_reset/config/task.conf | 4 +++- .../configuration_chain_use_setb/config/task.conf | 4 +++- 6 files changed, 18 insertions(+), 6 deletions(-) diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_config_enable_scff/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_config_enable_scff/config/task.conf index 8fd922fd9..a554331f3 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_config_enable_scff/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_config_enable_scff/config/task.conf @@ -16,9 +16,11 @@ timeout_each_job = 1*60 fpga_flow=yosys_vpr [OpenFPGA_SHELL] -openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/configuration_chain_example_script.openfpga +openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_cfgscff_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml +openfpga_vpr_device_layout= +openfpga_fast_configuration= [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_reset/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_reset/config/task.conf index 9d7ea2d8d..0707f4df2 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_reset/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_reset/config/task.conf @@ -16,9 +16,11 @@ timeout_each_job = 20*60 fpga_flow=yosys_vpr [OpenFPGA_SHELL] -openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/configuration_chain_example_script.openfpga +openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_use_reset_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml +openfpga_vpr_device_layout= +openfpga_fast_configuration= [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_resetb/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_resetb/config/task.conf index 4efa817a1..627e7a9ec 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_resetb/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_resetb/config/task.conf @@ -16,9 +16,11 @@ timeout_each_job = 20*60 fpga_flow=yosys_vpr [OpenFPGA_SHELL] -openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/configuration_chain_example_script.openfpga +openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_use_resetb_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml +openfpga_vpr_device_layout= +openfpga_fast_configuration= [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_set/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_set/config/task.conf index 37a1eb75b..e452a2371 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_set/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_set/config/task.conf @@ -16,9 +16,11 @@ timeout_each_job = 20*60 fpga_flow=yosys_vpr [OpenFPGA_SHELL] -openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/configuration_chain_example_script.openfpga +openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_use_set_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml +openfpga_vpr_device_layout= +openfpga_fast_configuration= [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_set_reset/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_set_reset/config/task.conf index 94acf3ed8..da327282e 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_set_reset/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_set_reset/config/task.conf @@ -16,9 +16,11 @@ timeout_each_job = 20*60 fpga_flow=yosys_vpr [OpenFPGA_SHELL] -openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/configuration_chain_example_script.openfpga +openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_use_both_set_reset_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml +openfpga_vpr_device_layout= +openfpga_fast_configuration= [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_setb/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_setb/config/task.conf index d3290d175..1706a4e4e 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_setb/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/configuration_chain_use_setb/config/task.conf @@ -16,9 +16,11 @@ timeout_each_job = 20*60 fpga_flow=yosys_vpr [OpenFPGA_SHELL] -openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/configuration_chain_example_script.openfpga +openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_use_setb_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml +openfpga_vpr_device_layout= +openfpga_fast_configuration= [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml From ec203d3a5cef7a5408952691ea481aea328b1a5c Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 11:35:23 -0600 Subject: [PATCH 07/18] [Test] Deploy 'write_full_testbench' openfpga shell script to all the fast configuration chain test cases --- .../full_testbench/fast_configuration_chain/config/task.conf | 4 +++- .../fast_configuration_chain_use_set/config/task.conf | 4 +++- .../smart_fast_configuration_chain/config/task.conf | 4 +++- 3 files changed, 9 insertions(+), 3 deletions(-) diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/fast_configuration_chain/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/fast_configuration_chain/config/task.conf index 1967bd2a4..71dbae458 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/fast_configuration_chain/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/fast_configuration_chain/config/task.conf @@ -16,9 +16,11 @@ timeout_each_job = 20*60 fpga_flow=yosys_vpr [OpenFPGA_SHELL] -openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/fast_configuration_example_script.openfpga +openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_use_reset_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml +openfpga_vpr_device_layout= +openfpga_fast_configuration=--fast_configuration [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/fast_configuration_chain_use_set/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/fast_configuration_chain_use_set/config/task.conf index 51f2344fe..10d5bfd62 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/fast_configuration_chain_use_set/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/fast_configuration_chain_use_set/config/task.conf @@ -16,9 +16,11 @@ timeout_each_job = 20*60 fpga_flow=yosys_vpr [OpenFPGA_SHELL] -openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/fast_configuration_example_script.openfpga +openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_use_set_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml +openfpga_vpr_device_layout= +openfpga_fast_configuration=--fast_configuration [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/smart_fast_configuration_chain/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/smart_fast_configuration_chain/config/task.conf index 4fac7ac49..56f90daef 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/smart_fast_configuration_chain/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/smart_fast_configuration_chain/config/task.conf @@ -16,9 +16,11 @@ timeout_each_job = 20*60 fpga_flow=yosys_vpr [OpenFPGA_SHELL] -openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/fast_configuration_example_script.openfpga +openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_cc_use_both_set_reset_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml +openfpga_vpr_device_layout= +openfpga_fast_configuration=--fast_configuration [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml From 5f96d440ec63a57bc2ab01dc2dbd332b302c94ae Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 11:48:05 -0600 Subject: [PATCH 08/18] [Test] Deploy 'write_full_testbench' openfpga shell script to multi-headed configuration chain with auto-tuned fast configuration --- .../config/task.conf | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/smart_fast_multi_region_configuration_chain/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/smart_fast_multi_region_configuration_chain/config/task.conf index ed7db9ae5..a5f85fc2b 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/smart_fast_multi_region_configuration_chain/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/smart_fast_multi_region_configuration_chain/config/task.conf @@ -16,9 +16,11 @@ timeout_each_job = 20*60 fpga_flow=yosys_vpr [OpenFPGA_SHELL] -openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/fast_configuration_example_script.openfpga +openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_multi_region_cc_use_both_set_reset_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml +openfpga_vpr_device_layout= +openfpga_fast_configuration=--fast_configuration [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml From 059e74b4efda3b04f207d7afcbc6fd0aa8030c99 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 15:17:00 -0600 Subject: [PATCH 09/18] [Doc] Add --fast configuration option to documentation for 'write_full_testbench' --- .../openfpga_commands/fpga_verilog_commands.rst | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/docs/source/manual/openfpga_shell/openfpga_commands/fpga_verilog_commands.rst b/docs/source/manual/openfpga_shell/openfpga_commands/fpga_verilog_commands.rst index c22d5aa73..8b559c698 100644 --- a/docs/source/manual/openfpga_shell/openfpga_commands/fpga_verilog_commands.rst +++ b/docs/source/manual/openfpga_shell/openfpga_commands/fpga_verilog_commands.rst @@ -114,6 +114,12 @@ write_full_testbench Specify the *Pin Constraints File* (PCF) if you want to custom stimulus in testbenches. For example, ``-pin_constraints_file pin_constraints.xml`` Strongly recommend for multi-clock simulations. See detailed file format about :ref:`file_format_pin_constraints_file`. + .. option:: --fast_configuration + + Enable fast configuration phase for the top-level testbench in order to reduce runtime of simulations. It is applicable to configuration chain, memory bank and frame-based configuration protocols. For configuration chain, when enabled, the zeros at the head of the bitstream will be skipped. For memory bank and frame-based, when enabled, all the zero configuration bits will be skipped. So ensure that your memory cells can be correctly reset to zero with a reset signal. + + .. note:: If both reset and set ports are defined in the circuit modeling for programming, OpenFPGA will pick the one that will bring largest benefit in speeding up configuration. + .. option:: --explicit_port_mapping Use explicit port mapping when writing the Verilog netlists From 061f83242966a56e98d0b63d198491b01faef403 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 16:23:40 -0600 Subject: [PATCH 10/18] [Tool] Enable fast configuration when writing fabric bitstream --- openfpga/src/base/openfpga_bitstream.cpp | 3 + .../src/base/openfpga_bitstream_command.cpp | 3 + .../src/fpga_bitstream/fast_configuration.cpp | 128 ++++++++++++++++++ .../src/fpga_bitstream/fast_configuration.h | 30 ++++ .../write_text_fabric_bitstream.cpp | 33 ++++- .../write_text_fabric_bitstream.h | 3 + 6 files changed, 199 insertions(+), 1 deletion(-) create mode 100644 openfpga/src/fpga_bitstream/fast_configuration.cpp create mode 100644 openfpga/src/fpga_bitstream/fast_configuration.h diff --git a/openfpga/src/base/openfpga_bitstream.cpp b/openfpga/src/base/openfpga_bitstream.cpp index f4ac33ab5..78e0cbddd 100644 --- a/openfpga/src/base/openfpga_bitstream.cpp +++ b/openfpga/src/base/openfpga_bitstream.cpp @@ -91,6 +91,7 @@ int write_fabric_bitstream(const OpenfpgaContext& openfpga_ctx, CommandOptionId opt_verbose = cmd.option("verbose"); CommandOptionId opt_file = cmd.option("file"); CommandOptionId opt_file_format = cmd.option("format"); + CommandOptionId opt_fast_config = cmd.option("fast_configuration"); /* Write fabric bitstream if required */ int status = CMD_EXEC_SUCCESS; @@ -119,7 +120,9 @@ int write_fabric_bitstream(const OpenfpgaContext& openfpga_ctx, status = write_fabric_bitstream_to_text_file(openfpga_ctx.bitstream_manager(), openfpga_ctx.fabric_bitstream(), openfpga_ctx.arch().config_protocol, + openfpga_ctx.fabric_global_port_info(), cmd_context.option_value(cmd, opt_file), + cmd_context.option_enable(cmd, opt_fast_config), cmd_context.option_enable(cmd, opt_verbose)); } diff --git a/openfpga/src/base/openfpga_bitstream_command.cpp b/openfpga/src/base/openfpga_bitstream_command.cpp index 39545d12f..a59d19adf 100644 --- a/openfpga/src/base/openfpga_bitstream_command.cpp +++ b/openfpga/src/base/openfpga_bitstream_command.cpp @@ -151,6 +151,9 @@ ShellCommandId add_openfpga_write_fabric_bitstream_command(openfpga::Shell + +/* Headers from vtrutil library */ +#include "vtr_log.h" +#include "vtr_assert.h" + +#include "fabric_global_port_info_utils.h" +#include "fast_configuration.h" + +/* begin namespace openfpga */ +namespace openfpga { + +/******************************************************************** + * Identify if fast configuration is applicable base on the availability + * of programming reset and programming set ports of the FPGA fabric + *******************************************************************/ +bool is_fast_configuration_applicable(const FabricGlobalPortInfo& global_ports) { + /* Preparation: find all the reset/set ports for programming usage */ + std::vector global_prog_reset_ports = find_fabric_global_programming_reset_ports(global_ports); + std::vector global_prog_set_ports = find_fabric_global_programming_set_ports(global_ports); + + /* Identify if we can apply fast configuration */ + if (global_prog_set_ports.empty() && global_prog_reset_ports.empty()) { + VTR_LOG_WARN("None of global reset and set ports are defined for programming purpose. Fast configuration is not applicable\n"); + return false; + } + + return true; +} + +/******************************************************************** + * Decide if we should use reset or set signal to acheive fast configuration + * - If only one type signal is specified, we use that type + * For example, only reset signal is defined, we will use reset + * - If both are defined, pick the one that will bring bigger reduction + * i.e., larger number of configuration bits can be skipped + *******************************************************************/ +bool find_bit_value_to_skip_for_fast_configuration(const e_config_protocol_type& config_protocol_type, + const FabricGlobalPortInfo& global_ports, + const BitstreamManager& bitstream_manager, + const FabricBitstream& fabric_bitstream) { + /* Preparation: find all the reset/set ports for programming usage */ + std::vector global_prog_reset_ports = find_fabric_global_programming_reset_ports(global_ports); + std::vector global_prog_set_ports = find_fabric_global_programming_set_ports(global_ports); + + /* Early exit conditions */ + if (!global_prog_reset_ports.empty() && global_prog_set_ports.empty()) { + return false; + } else if (!global_prog_set_ports.empty() && global_prog_reset_ports.empty()) { + return true; + } + + /* If both types of ports are not defined, the fast configuration is not applicable */ + VTR_ASSERT(!global_prog_set_ports.empty() && !global_prog_reset_ports.empty()); + bool bit_value_to_skip = false; + + VTR_LOG("Both reset and set ports are defined for programming controls, selecting the best-fit one...\n"); + + size_t num_ones_to_skip = 0; + size_t num_zeros_to_skip = 0; + + /* Branch on the type of configuration protocol */ + switch (config_protocol_type) { + case CONFIG_MEM_STANDALONE: + break; + case CONFIG_MEM_SCAN_CHAIN: { + /* We can only skip the ones/zeros at the beginning of the bitstream */ + /* Count how many logic '1' bits we can skip */ + for (const FabricBitId& bit_id : fabric_bitstream.bits()) { + if (false == bitstream_manager.bit_value(fabric_bitstream.config_bit(bit_id))) { + break; + } + VTR_ASSERT(true == bitstream_manager.bit_value(fabric_bitstream.config_bit(bit_id))); + num_ones_to_skip++; + } + /* Count how many logic '0' bits we can skip */ + for (const FabricBitId& bit_id : fabric_bitstream.bits()) { + if (true == bitstream_manager.bit_value(fabric_bitstream.config_bit(bit_id))) { + break; + } + VTR_ASSERT(false == bitstream_manager.bit_value(fabric_bitstream.config_bit(bit_id))); + num_zeros_to_skip++; + } + break; + } + case CONFIG_MEM_MEMORY_BANK: + case CONFIG_MEM_FRAME_BASED: { + /* Count how many logic '1' and logic '0' bits we can skip */ + for (const FabricBitId& bit_id : fabric_bitstream.bits()) { + if (false == bitstream_manager.bit_value(fabric_bitstream.config_bit(bit_id))) { + num_zeros_to_skip++; + } else { + VTR_ASSERT(true == bitstream_manager.bit_value(fabric_bitstream.config_bit(bit_id))); + num_ones_to_skip++; + } + } + break; + } + default: + VTR_LOGF_ERROR(__FILE__, __LINE__, + "Invalid configuration protocol type!\n"); + exit(1); + } + + VTR_LOG("Using reset will skip %g% (%lu/%lu) of configuration bitstream.\n", + 100. * (float) num_zeros_to_skip / (float) fabric_bitstream.num_bits(), + num_zeros_to_skip, fabric_bitstream.num_bits()); + + VTR_LOG("Using set will skip %g% (%lu/%lu) of configuration bitstream.\n", + 100. * (float) num_ones_to_skip / (float) fabric_bitstream.num_bits(), + num_ones_to_skip, fabric_bitstream.num_bits()); + + /* By default, we prefer to skip zeros (when the numbers are the same */ + if (num_ones_to_skip > num_zeros_to_skip) { + VTR_LOG("Will use set signal in fast configuration\n"); + bit_value_to_skip = true; + } else { + VTR_LOG("Will use reset signal in fast configuration\n"); + } + + return bit_value_to_skip; +} + +} /* end namespace openfpga */ diff --git a/openfpga/src/fpga_bitstream/fast_configuration.h b/openfpga/src/fpga_bitstream/fast_configuration.h new file mode 100644 index 000000000..eb161d1b2 --- /dev/null +++ b/openfpga/src/fpga_bitstream/fast_configuration.h @@ -0,0 +1,30 @@ +#ifndef FAST_CONFIGURATION_H +#define FAST_CONFIGURATION_H + +/******************************************************************** + * Include header files that are required by function declaration + *******************************************************************/ +#include +#include +#include "fabric_global_port_info.h" +#include "config_protocol.h" +#include "bitstream_manager.h" +#include "fabric_bitstream.h" + +/******************************************************************** + * Function declaration + *******************************************************************/ + +/* begin namespace openfpga */ +namespace openfpga { + +bool is_fast_configuration_applicable(const FabricGlobalPortInfo& global_ports); + +bool find_bit_value_to_skip_for_fast_configuration(const e_config_protocol_type& config_protocol_type, + const FabricGlobalPortInfo& global_ports, + const BitstreamManager& bitstream_manager, + const FabricBitstream& fabric_bitstream); + +} /* end namespace openfpga */ + +#endif diff --git a/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp b/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp index 3fa604de1..663e679d3 100644 --- a/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp +++ b/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp @@ -16,6 +16,7 @@ #include "openfpga_naming.h" +#include "fast_configuration.h" #include "bitstream_manager_utils.h" #include "fabric_bitstream_utils.h" #include "write_text_fabric_bitstream.h" @@ -118,6 +119,8 @@ int write_flatten_fabric_bitstream_to_text_file(std::fstream& fp, *******************************************************************/ static int write_config_chain_fabric_bitstream_to_text_file(std::fstream& fp, + const bool& fast_configuration, + const bool& bit_value_to_skip, const BitstreamManager& bitstream_manager, const FabricBitstream& fabric_bitstream) { int status = 0; @@ -125,7 +128,18 @@ int write_config_chain_fabric_bitstream_to_text_file(std::fstream& fp, size_t regional_bitstream_max_size = find_fabric_regional_bitstream_max_size(fabric_bitstream); ConfigChainFabricBitstream regional_bitstreams = build_config_chain_fabric_bitstream_by_region(bitstream_manager, fabric_bitstream); - for (size_t ibit = 0; ibit < regional_bitstream_max_size; ++ibit) { + /* For fast configuration, the bitstream size counts from the first bit '1' */ + size_t num_bits_to_skip = 0; + if (true == fast_configuration) { + num_bits_to_skip = find_configuration_chain_fabric_bitstream_size_to_be_skipped(fabric_bitstream, bitstream_manager, bit_value_to_skip); + } + VTR_ASSERT(num_bits_to_skip < regional_bitstream_max_size); + + VTR_LOG("Fast configuration will skip %g% (%lu/%lu) of configuration bitstream.\n", + 100. * (float) num_bits_to_skip / (float) regional_bitstream_max_size, + num_bits_to_skip, regional_bitstream_max_size); + + for (size_t ibit = num_bits_to_skip; ibit < regional_bitstream_max_size; ++ibit) { for (const auto& region_bitstream : regional_bitstreams) { fp << region_bitstream[ibit]; } @@ -214,7 +228,9 @@ int write_frame_based_fabric_bitstream_to_text_file(std::fstream& fp, int write_fabric_bitstream_to_text_file(const BitstreamManager& bitstream_manager, const FabricBitstream& fabric_bitstream, const ConfigProtocol& config_protocol, + const FabricGlobalPortInfo& global_ports, const std::string& fname, + const bool& fast_configuration, const bool& verbose) { /* Ensure that we have a valid file name */ if (true == fname.empty()) { @@ -230,6 +246,19 @@ int write_fabric_bitstream_to_text_file(const BitstreamManager& bitstream_manage check_file_stream(fname.c_str(), fp); + bool apply_fast_configuration = is_fast_configuration_applicable(global_ports); + if (fast_configuration && apply_fast_configuration != fast_configuration) { + VTR_LOG_WARN("Disable fast configuration even it is enabled by user\n"); + } + + bool bit_value_to_skip = false; + if (apply_fast_configuration) { + bit_value_to_skip = find_bit_value_to_skip_for_fast_configuration(config_protocol.type(), + global_ports, + bitstream_manager, + fabric_bitstream); + } + /* Output fabric bitstream to the file */ int status = 0; switch (config_protocol.type()) { @@ -241,6 +270,8 @@ int write_fabric_bitstream_to_text_file(const BitstreamManager& bitstream_manage break; case CONFIG_MEM_SCAN_CHAIN: status = write_config_chain_fabric_bitstream_to_text_file(fp, + apply_fast_configuration, + bit_value_to_skip, bitstream_manager, fabric_bitstream); break; diff --git a/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.h b/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.h index 9582a185c..17811f439 100644 --- a/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.h +++ b/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.h @@ -9,6 +9,7 @@ #include "bitstream_manager.h" #include "fabric_bitstream.h" #include "config_protocol.h" +#include "fabric_global_port_info.h" /******************************************************************** * Function declaration @@ -20,7 +21,9 @@ namespace openfpga { int write_fabric_bitstream_to_text_file(const BitstreamManager& bitstream_manager, const FabricBitstream& fabric_bitstream, const ConfigProtocol& config_protocol, + const FabricGlobalPortInfo& global_ports, const std::string& fname, + const bool& fast_configuration, const bool& verbose); } /* end namespace openfpga */ From e9fa44cc2520d89f7392f45d221f5f9ff29e6c71 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 16:24:56 -0600 Subject: [PATCH 11/18] [Tool] Add fast configuration to the write bitstream command in example shell script --- .../write_full_testbench_example_script.openfpga | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga b/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga index 8a87a0a08..612249a15 100644 --- a/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga +++ b/openfpga_flow/openfpga_shell_scripts/write_full_testbench_example_script.openfpga @@ -43,7 +43,7 @@ build_architecture_bitstream --verbose --write_file fabric_independent_bitstream build_fabric_bitstream --verbose # Write fabric-dependent bitstream -write_fabric_bitstream --file fabric_bitstream.bit --format plain_text +write_fabric_bitstream --file fabric_bitstream.bit --format plain_text ${OPENFPGA_FAST_CONFIGURATION} # Write the Verilog netlist for FPGA fabric # - Enable the use of explicit port mapping in Verilog netlist From 6e69c2d70a1f69aa960e293feec7f95a64327ab2 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 16:34:55 -0600 Subject: [PATCH 12/18] [Tool] Patch fast configuration in full Verilog testbench generator --- openfpga/src/fpga_verilog/verilog_top_testbench.cpp | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/openfpga/src/fpga_verilog/verilog_top_testbench.cpp b/openfpga/src/fpga_verilog/verilog_top_testbench.cpp index fb88e2bbf..cdc820e87 100644 --- a/openfpga/src/fpga_verilog/verilog_top_testbench.cpp +++ b/openfpga/src/fpga_verilog/verilog_top_testbench.cpp @@ -22,6 +22,7 @@ #include "simulation_utils.h" #include "openfpga_atom_netlist_utils.h" +#include "fast_configuration.h" #include "fabric_bitstream_utils.h" #include "fabric_global_port_info_utils.h" @@ -1955,6 +1956,7 @@ void print_verilog_full_testbench_configuration_chain_bitstream(std::fstream& fp const bool& bit_value_to_skip, const ModuleManager& module_manager, const ModuleId& top_module, + const BitstreamManager& bitstream_manager, const FabricBitstream& fabric_bitstream) { /* Validate the file stream */ valid_file_stream(fp); @@ -1964,8 +1966,15 @@ void print_verilog_full_testbench_configuration_chain_bitstream(std::fstream& fp /* Find the longest bitstream */ size_t regional_bitstream_max_size = find_fabric_regional_bitstream_max_size(fabric_bitstream); + /* For fast configuration, the bitstream size counts from the first bit '1' */ + size_t num_bits_to_skip = 0; + if (true == fast_configuration) { + num_bits_to_skip = find_configuration_chain_fabric_bitstream_size_to_be_skipped(fabric_bitstream, bitstream_manager, bit_value_to_skip); + } + VTR_ASSERT(num_bits_to_skip < regional_bitstream_max_size); + /* Define a constant for the bitstream length */ - print_verilog_define_flag(fp, std::string(TOP_TB_BITSTREAM_LENGTH_VARIABLE), regional_bitstream_max_size); + print_verilog_define_flag(fp, std::string(TOP_TB_BITSTREAM_LENGTH_VARIABLE), regional_bitstream_max_size - num_bits_to_skip); print_verilog_define_flag(fp, std::string(TOP_TB_BITSTREAM_WIDTH_VARIABLE), fabric_bitstream.num_regions()); /* Initial value should be the first configuration bits @@ -2140,6 +2149,7 @@ void print_verilog_full_testbench_bitstream(std::fstream& fp, fast_configuration, bit_value_to_skip, module_manager, top_module, + bitstream_manager, fabric_bitstream); break; case CONFIG_MEM_MEMORY_BANK: From d98be9f87b907956b135ab71649a96a26d68c6b5 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 16:45:00 -0600 Subject: [PATCH 13/18] [Tool] Remove icarus requirement on vcd writing in Verilog testbenches; Since vcd writing commands are standard Verilog --- .../verilog_formal_random_top_testbench.cpp | 1 - openfpga/src/fpga_verilog/verilog_testbench_utils.cpp | 11 ++--------- openfpga/src/fpga_verilog/verilog_testbench_utils.h | 1 - openfpga/src/fpga_verilog/verilog_top_testbench.cpp | 2 -- 4 files changed, 2 insertions(+), 13 deletions(-) diff --git a/openfpga/src/fpga_verilog/verilog_formal_random_top_testbench.cpp b/openfpga/src/fpga_verilog/verilog_formal_random_top_testbench.cpp index 848970a30..9ed4a8138 100644 --- a/openfpga/src/fpga_verilog/verilog_formal_random_top_testbench.cpp +++ b/openfpga/src/fpga_verilog/verilog_formal_random_top_testbench.cpp @@ -359,7 +359,6 @@ void print_verilog_random_top_testbench(const std::string& circuit_name, /* Add Icarus requirement */ print_verilog_timeout_and_vcd(fp, - std::string(ICARUS_SIMULATOR_FLAG), std::string(circuit_name + std::string(FORMAL_RANDOM_TOP_TESTBENCH_POSTFIX)), std::string(circuit_name + std::string("_formal.vcd")), std::string(FORMAL_TB_SIM_START_PORT_NAME), diff --git a/openfpga/src/fpga_verilog/verilog_testbench_utils.cpp b/openfpga/src/fpga_verilog/verilog_testbench_utils.cpp index 3329d33cf..994d6f280 100644 --- a/openfpga/src/fpga_verilog/verilog_testbench_utils.cpp +++ b/openfpga/src/fpga_verilog/verilog_testbench_utils.cpp @@ -300,7 +300,6 @@ void print_verilog_testbench_connect_fpga_ios(std::fstream& fp, * Note that: these codes are tuned for Icarus simulator!!! *******************************************************************/ void print_verilog_timeout_and_vcd(std::fstream& fp, - const std::string& icarus_preprocessing_flag, const std::string& module_name, const std::string& vcd_fname, const std::string& simulation_start_counter_name, @@ -309,20 +308,14 @@ void print_verilog_timeout_and_vcd(std::fstream& fp, /* Validate the file stream */ valid_file_stream(fp); - /* The following verilog codes are tuned for Icarus */ - print_verilog_preprocessing_flag(fp, icarus_preprocessing_flag); - - print_verilog_comment(fp, std::string("----- Begin Icarus requirement -------")); + print_verilog_comment(fp, std::string("----- Begin output waveform to VCD file-------")); fp << "\tinitial begin" << std::endl; fp << "\t\t$dumpfile(\"" << vcd_fname << "\");" << std::endl; fp << "\t\t$dumpvars(1, " << module_name << ");" << std::endl; fp << "\tend" << std::endl; - /* Condition ends for the Icarus requirement */ - print_verilog_endif(fp); - - print_verilog_comment(fp, std::string("----- END Icarus requirement -------")); + print_verilog_comment(fp, std::string("----- END output waveform to VCD file -------")); /* Add an empty line as splitter */ fp << std::endl; diff --git a/openfpga/src/fpga_verilog/verilog_testbench_utils.h b/openfpga/src/fpga_verilog/verilog_testbench_utils.h index 0eb77bda9..807d25ae5 100644 --- a/openfpga/src/fpga_verilog/verilog_testbench_utils.h +++ b/openfpga/src/fpga_verilog/verilog_testbench_utils.h @@ -55,7 +55,6 @@ void print_verilog_testbench_connect_fpga_ios(std::fstream& fp, const size_t& unused_io_value); void print_verilog_timeout_and_vcd(std::fstream& fp, - const std::string& icarus_preprocessing_flag, const std::string& module_name, const std::string& vcd_fname, const std::string& simulation_start_counter_name, diff --git a/openfpga/src/fpga_verilog/verilog_top_testbench.cpp b/openfpga/src/fpga_verilog/verilog_top_testbench.cpp index cdc820e87..a5359f585 100644 --- a/openfpga/src/fpga_verilog/verilog_top_testbench.cpp +++ b/openfpga/src/fpga_verilog/verilog_top_testbench.cpp @@ -2496,7 +2496,6 @@ void print_verilog_top_testbench(const ModuleManager& module_manager, * Always ceil the simulation time so that we test a sufficient length of period!!! */ print_verilog_timeout_and_vcd(fp, - std::string(ICARUS_SIMULATOR_FLAG), std::string(circuit_name + std::string(AUTOCHECK_TOP_TESTBENCH_VERILOG_MODULE_POSTFIX)), std::string(circuit_name + std::string("_formal.vcd")), std::string(TOP_TESTBENCH_SIM_START_PORT_NAME), @@ -2758,7 +2757,6 @@ int print_verilog_full_testbench(const ModuleManager& module_manager, * Always ceil the simulation time so that we test a sufficient length of period!!! */ print_verilog_timeout_and_vcd(fp, - std::string(ICARUS_SIMULATOR_FLAG), std::string(circuit_name + std::string(AUTOCHECK_TOP_TESTBENCH_VERILOG_MODULE_POSTFIX)), std::string(circuit_name + std::string("_formal.vcd")), std::string(TOP_TESTBENCH_SIM_START_PORT_NAME), From 70fb3a85dc08d0365719e3613f03b52cd55477c3 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 17:23:10 -0600 Subject: [PATCH 14/18] [Tool] Patch fast configuration in bitstream writing --- .../fpga_bitstream/write_text_fabric_bitstream.cpp | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp b/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp index 663e679d3..9a637bc72 100644 --- a/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp +++ b/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp @@ -132,12 +132,11 @@ int write_config_chain_fabric_bitstream_to_text_file(std::fstream& fp, size_t num_bits_to_skip = 0; if (true == fast_configuration) { num_bits_to_skip = find_configuration_chain_fabric_bitstream_size_to_be_skipped(fabric_bitstream, bitstream_manager, bit_value_to_skip); + VTR_ASSERT(num_bits_to_skip < regional_bitstream_max_size); + VTR_LOG("Fast configuration will skip %g% (%lu/%lu) of configuration bitstream.\n", + 100. * (float) num_bits_to_skip / (float) regional_bitstream_max_size, + num_bits_to_skip, regional_bitstream_max_size); } - VTR_ASSERT(num_bits_to_skip < regional_bitstream_max_size); - - VTR_LOG("Fast configuration will skip %g% (%lu/%lu) of configuration bitstream.\n", - 100. * (float) num_bits_to_skip / (float) regional_bitstream_max_size, - num_bits_to_skip, regional_bitstream_max_size); for (size_t ibit = num_bits_to_skip; ibit < regional_bitstream_max_size; ++ibit) { for (const auto& region_bitstream : regional_bitstreams) { @@ -246,7 +245,7 @@ int write_fabric_bitstream_to_text_file(const BitstreamManager& bitstream_manage check_file_stream(fname.c_str(), fp); - bool apply_fast_configuration = is_fast_configuration_applicable(global_ports); + bool apply_fast_configuration = is_fast_configuration_applicable(global_ports) && fast_configuration; if (fast_configuration && apply_fast_configuration != fast_configuration) { VTR_LOG_WARN("Disable fast configuration even it is enabled by user\n"); } From 27fa15603ace0281fef84083e384fa7fe498a455 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 18:17:47 -0600 Subject: [PATCH 15/18] [Tool] Patch test case due to changes in the template script --- .../multi_region_configuration_chain/config/task.conf | 1 + 1 file changed, 1 insertion(+) diff --git a/openfpga_flow/tasks/basic_tests/full_testbench/multi_region_configuration_chain/config/task.conf b/openfpga_flow/tasks/basic_tests/full_testbench/multi_region_configuration_chain/config/task.conf index ebc47d3b6..dd4bea019 100644 --- a/openfpga_flow/tasks/basic_tests/full_testbench/multi_region_configuration_chain/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/full_testbench/multi_region_configuration_chain/config/task.conf @@ -20,6 +20,7 @@ openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scrip openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_N4_40nm_multi_region_cc_openfpga.xml openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/auto_sim_openfpga.xml openfpga_vpr_device_layout=--device 2x2 +openfpga_fast_configuration= [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_N4_tileable_40nm.xml From cf7addb1a6847fc24603cdaf37bab8bfb6988806 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 19:48:48 -0600 Subject: [PATCH 16/18] [Tool] Add heads to bitstream plain text file --- .../write_text_fabric_bitstream.cpp | 24 +++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp b/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp index 9a637bc72..5be5d04cc 100644 --- a/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp +++ b/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp @@ -13,6 +13,7 @@ /* Headers from openfpgautil library */ #include "openfpga_digest.h" +#include "openfpga_version.h" #include "openfpga_naming.h" @@ -24,6 +25,21 @@ /* begin namespace openfpga */ namespace openfpga { +/******************************************************************** + * This function write header information to a bitstream file + *******************************************************************/ +static +void write_fabric_bitstream_text_file_head(std::fstream& fp) { + valid_file_stream(fp); + + auto end = std::chrono::system_clock::now(); + std::time_t end_time = std::chrono::system_clock::to_time_t(end); + + fp << "// Fabric bitstream" << std::endl; + fp << "// Version: " << openfpga::VERSION << std::endl; + fp << "// Date: " << std::ctime(&end_time) << std::endl; +} + /******************************************************************** * Write a configuration bit into a plain text file * The format depends on the type of configuration protocol @@ -138,6 +154,11 @@ int write_config_chain_fabric_bitstream_to_text_file(std::fstream& fp, num_bits_to_skip, regional_bitstream_max_size); } + /* Output bitstream size information */ + fp << "// Bitstream length: " << regional_bitstream_max_size - num_bits_to_skip << std::endl; + fp << "// Bitstream width (LSB -> MSB): " << fabric_bitstream.num_regions() << std::endl; + + /* Output bitstream data */ for (size_t ibit = num_bits_to_skip; ibit < regional_bitstream_max_size; ++ibit) { for (const auto& region_bitstream : regional_bitstreams) { fp << region_bitstream[ibit]; @@ -258,6 +279,9 @@ int write_fabric_bitstream_to_text_file(const BitstreamManager& bitstream_manage fabric_bitstream); } + /* Write file head */ + write_fabric_bitstream_text_file_head(fp); + /* Output fabric bitstream to the file */ int status = 0; switch (config_protocol.type()) { From c30be6e95ee9ca4cf495868e6c627dd0d3dc06be Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 20:00:28 -0600 Subject: [PATCH 17/18] [Doc] Update documentation about the fast configuration for write bitstream command --- .../openfpga_commands/fpga_bitstream_commands.rst | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/docs/source/manual/openfpga_shell/openfpga_commands/fpga_bitstream_commands.rst b/docs/source/manual/openfpga_shell/openfpga_commands/fpga_bitstream_commands.rst index a63717e15..12c4d8ff5 100644 --- a/docs/source/manual/openfpga_shell/openfpga_commands/fpga_bitstream_commands.rst +++ b/docs/source/manual/openfpga_shell/openfpga_commands/fpga_bitstream_commands.rst @@ -69,6 +69,15 @@ write_fabric_bitstream Specify the file format [``plain_text`` | ``xml``]. By default is ``plain_text``. See file formats in :ref:`file_formats_fabric_bitstream_xml` and :ref:`file_formats_fabric_bitstream_plain_text`. + .. option:: --fast_configuration + + Reduce the bitstream size when outputing by skipping dummy configuration bits. It is applicable to configuration chain, memory bank and frame-based configuration protocols. For configuration chain, when enabled, the zeros at the head of the bitstream will be skipped. For memory bank and frame-based, when enabled, all the zero configuration bits will be skipped. So ensure that your memory cells can be correctly reset to zero with a reset signal. + + .. warning:: Fast configuration is only applicable to plain text file format! + + .. note:: If both reset and set ports are defined in the circuit modeling for programming, OpenFPGA will pick the one that will bring largest benefit in speeding up configuration. + + .. option:: --verbose Show verbose log From 618b04568f09f21024551c9d27866b629a1bece7 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Fri, 4 Jun 2021 20:07:42 -0600 Subject: [PATCH 18/18] [Tool] Remove unnecessary new line in bitstream file --- openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp b/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp index 5be5d04cc..1fb86c574 100644 --- a/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp +++ b/openfpga/src/fpga_bitstream/write_text_fabric_bitstream.cpp @@ -37,7 +37,7 @@ void write_fabric_bitstream_text_file_head(std::fstream& fp) { fp << "// Fabric bitstream" << std::endl; fp << "// Version: " << openfpga::VERSION << std::endl; - fp << "// Date: " << std::ctime(&end_time) << std::endl; + fp << "// Date: " << std::ctime(&end_time); } /******************************************************************** @@ -163,7 +163,9 @@ int write_config_chain_fabric_bitstream_to_text_file(std::fstream& fp, for (const auto& region_bitstream : regional_bitstreams) { fp << region_bitstream[ibit]; } - fp << std::endl; + if (ibit < regional_bitstream_max_size - 1) { + fp << std::endl; + } } return status;