diff --git a/docs/source/manual/openfpga_shell/openfpga_commands/setup_commands.rst b/docs/source/manual/openfpga_shell/openfpga_commands/setup_commands.rst index ab27eeceb..d5fce4b8f 100644 --- a/docs/source/manual/openfpga_shell/openfpga_commands/setup_commands.rst +++ b/docs/source/manual/openfpga_shell/openfpga_commands/setup_commands.rst @@ -235,6 +235,10 @@ pb_pin_fixup .. warning:: This feature has been integrated into VPR to provide accurate timing analysis results at post-routing stage. However, this command provides a light fix-up (not as thorough as the one in VPR) but bring more flexibility in support some architecture without local routing. Suggest to enable it when your architecture does not have local routing for *Look-Up Tables* (LUTs) but you want to enable logic equivalent for input pins of LUTs .. warning:: This command may be deprecated in future + + .. option:: --map_global_net_to_msb + + If specified, any global net including clock, reset etc, will be mapped to a best-fit Most Significant Bit (MSB) of input ports of programmable blocks. If not specified, a best-fit Least Significant Bit (LSB) will be the default choice. For example, when ``--clock_modeling ideal`` is selected when running VPR, global nets will not be routed and their pin mapping on programmable blocks may be revoked by other nets due to optimization. Therefore, this command will restore the pin mapping for the global nets and pick a spare pin on programmable blocks. This option is to set a preference when mapping the global nets to spare pins. .. option:: --verbose diff --git a/openfpga/src/base/openfpga_pb_pin_fixup.cpp b/openfpga/src/base/openfpga_pb_pin_fixup.cpp index 3ae0cc8e2..79c73e327 100644 --- a/openfpga/src/base/openfpga_pb_pin_fixup.cpp +++ b/openfpga/src/base/openfpga_pb_pin_fixup.cpp @@ -32,8 +32,8 @@ namespace openfpga { static int update_cluster_pin_global_net_with_post_routing_results( const ClusteringContext& clustering_ctx, VprClusteringAnnotation& clustering_annotation, const ClusterBlockId& blk_id, - t_logical_block_type_ptr logical_block, size_t& num_fixup, - const bool& verbose) { + t_logical_block_type_ptr logical_block, const bool& map_gnet2msb, + size_t& num_fixup, const bool& verbose) { /* Reassign global nets to unused pins in the same port where they were mapped * NO optimization is done here!!! First find first fit */ @@ -77,10 +77,13 @@ static int update_cluster_pin_global_net_with_post_routing_results( "during routing optimization\n", clustering_ctx.clb_nlist.net_name(global_net_id).c_str()); size_t cand_pin_start = pb_type_pin - pb_graph_pin->pin_number; - size_t cand_pin_end = cand_pin_start + pb_graph_pin->port->num_pins; + std::vector cand_pins(pb_graph_pin->port->num_pins); + std::iota(cand_pins.begin(), cand_pins.end(), cand_pin_start); + if (map_gnet2msb) { + std::reverse(cand_pins.begin(), cand_pins.end()); + } bool found_cand = false; - for (size_t cand_pin = cand_pin_start; cand_pin < cand_pin_end; - ++cand_pin) { + for (size_t cand_pin : cand_pins) { ClusterNetId cand_pin_net_id = clustering_ctx.clb_nlist.block_net(blk_id, cand_pin); const t_pb_graph_pin* cand_pb_graph_pin = @@ -139,7 +142,7 @@ static int update_cluster_pin_with_post_routing_results( VprClusteringAnnotation& vpr_clustering_annotation, const size_t& layer, const vtr::Point& grid_coord, const ClusterBlockId& blk_id, const e_side& border_side, const size_t& z, const bool& perimeter_cb, - size_t& num_fixup, const bool& verbose) { + const bool& map_gnet2msb, size_t& num_fixup, const bool& verbose) { int status = CMD_EXEC_SUCCESS; /* Handle each pin */ auto logical_block = clustering_ctx.clb_nlist.block_type(blk_id); @@ -337,8 +340,8 @@ static int update_cluster_pin_with_post_routing_results( } /* 2nd round of fixup: focus on global nets */ status = update_cluster_pin_global_net_with_post_routing_results( - clustering_ctx, vpr_clustering_annotation, blk_id, logical_block, num_fixup, - verbose); + clustering_ctx, vpr_clustering_annotation, blk_id, logical_block, + map_gnet2msb, num_fixup, verbose); return status; } @@ -351,9 +354,12 @@ int update_pb_pin_with_post_routing_results( const PlacementContext& placement_ctx, const VprRoutingAnnotation& vpr_routing_annotation, VprClusteringAnnotation& vpr_clustering_annotation, const bool& perimeter_cb, - const bool& verbose) { + const bool& map_gnet2msb, const bool& verbose) { int status = CMD_EXEC_SUCCESS; size_t num_fixup = 0; + /* Confirm options */ + VTR_LOGV(verbose && map_gnet2msb, + "User choose to map global net to the best fit MSB of input port\n"); /* Ensure a clean start: remove all the remapping results from VTR's * post-routing clustering result sync-up */ vpr_clustering_annotation.clear_net_remapping(); @@ -384,7 +390,7 @@ int update_pb_pin_with_post_routing_results( device_ctx, clustering_ctx, vpr_routing_annotation, vpr_clustering_annotation, layer, grid_coord, cluster_blk_id, NUM_SIDES, placement_ctx.block_locs[cluster_blk_id].loc.sub_tile, - perimeter_cb, num_fixup, verbose); + perimeter_cb, map_gnet2msb, num_fixup, verbose); if (status != CMD_EXEC_SUCCESS) { return CMD_EXEC_FATAL_ERROR; } @@ -419,7 +425,7 @@ int update_pb_pin_with_post_routing_results( device_ctx, clustering_ctx, vpr_routing_annotation, vpr_clustering_annotation, layer, io_coord, cluster_blk_id, io_side, placement_ctx.block_locs[cluster_blk_id].loc.sub_tile, perimeter_cb, - num_fixup, verbose); + map_gnet2msb, num_fixup, verbose); if (status != CMD_EXEC_SUCCESS) { return CMD_EXEC_FATAL_ERROR; } diff --git a/openfpga/src/base/openfpga_pb_pin_fixup.h b/openfpga/src/base/openfpga_pb_pin_fixup.h index 11813b60c..1d7faa83b 100644 --- a/openfpga/src/base/openfpga_pb_pin_fixup.h +++ b/openfpga/src/base/openfpga_pb_pin_fixup.h @@ -19,7 +19,7 @@ int update_pb_pin_with_post_routing_results( const PlacementContext& placement_ctx, const VprRoutingAnnotation& vpr_routing_annotation, VprClusteringAnnotation& vpr_clustering_annotation, const bool& perimeter_cb, - const bool& verbose); + const bool& map_gnet2msb, const bool& verbose); } /* end namespace openfpga */ diff --git a/openfpga/src/base/openfpga_pb_pin_fixup_template.h b/openfpga/src/base/openfpga_pb_pin_fixup_template.h index 50c415727..beb402572 100644 --- a/openfpga/src/base/openfpga_pb_pin_fixup_template.h +++ b/openfpga/src/base/openfpga_pb_pin_fixup_template.h @@ -35,6 +35,7 @@ int pb_pin_fixup_template(T& openfpga_context, const Command& cmd, vtr::ScopedStartFinishTimer timer( "Fix up pb pin mapping results after routing optimization"); + CommandOptionId opt_map_gnet2msb = cmd.option("map_global_net_to_msb"); CommandOptionId opt_verbose = cmd.option("verbose"); /* Apply fix-up to each grid */ @@ -43,6 +44,7 @@ int pb_pin_fixup_template(T& openfpga_context, const Command& cmd, openfpga_context.vpr_routing_annotation(), openfpga_context.mutable_vpr_clustering_annotation(), g_vpr_ctx.device().arch->perimeter_cb, + cmd_context.option_enable(cmd, opt_map_gnet2msb), cmd_context.option_enable(cmd, opt_verbose)); } diff --git a/openfpga/src/base/openfpga_setup_command_template.h b/openfpga/src/base/openfpga_setup_command_template.h index 53e43f00f..1d74a61f0 100644 --- a/openfpga/src/base/openfpga_setup_command_template.h +++ b/openfpga/src/base/openfpga_setup_command_template.h @@ -324,6 +324,13 @@ ShellCommandId add_pb_pin_fixup_command_template( const std::vector& dependent_cmds, const bool& hidden) { Command shell_cmd("pb_pin_fixup"); + /* Add an option '--map_global_net_to_msb' */ + shell_cmd.add_option( + "map_global_net_to_msb", false, + "If specified, any global net including clock, reset etc, will be mapped " + "to a best-fit Most Significant Bit (MSB) of input ports of programmable " + "blocks. If not specified, a best-fit Least Significant Bit (LSB) will be " + "the default choice"); /* Add an option '--verbose' */ shell_cmd.add_option("verbose", false, "Show verbose outputs"); diff --git a/openfpga_flow/openfpga_shell_scripts/example_clkntwk_pb_pin_fixup_no_ace_script.openfpga b/openfpga_flow/openfpga_shell_scripts/example_clkntwk_pb_pin_fixup_no_ace_script.openfpga index f77fadd10..b5e326b27 100644 --- a/openfpga_flow/openfpga_shell_scripts/example_clkntwk_pb_pin_fixup_no_ace_script.openfpga +++ b/openfpga_flow/openfpga_shell_scripts/example_clkntwk_pb_pin_fixup_no_ace_script.openfpga @@ -22,7 +22,7 @@ append_clock_rr_graph # to debug use --verbose options link_openfpga_arch --sort_gsb_chan_node_in_edges -pb_pin_fixup --verbose +pb_pin_fixup ${OPENFPGA_PB_PIN_FIXUP_OPTIONS} # Route clock based on clock network definition route_clock_rr_graph ${OPENFPGA_ROUTE_CLOCK_OPTIONS} --pin_constraints_file ${OPENFPGA_PIN_CONSTRAINTS_FILE} diff --git a/openfpga_flow/regression_test_scripts/basic_reg_test.sh b/openfpga_flow/regression_test_scripts/basic_reg_test.sh index b968904fb..6b17c21c6 100755 --- a/openfpga_flow/regression_test_scripts/basic_reg_test.sh +++ b/openfpga_flow/regression_test_scripts/basic_reg_test.sh @@ -250,6 +250,7 @@ run-task basic_tests/clock_network/homo_1clock_1reset_3layer_2entry_disable_unus run-task basic_tests/clock_network/homo_1clock_1reset_2layer_y_entry $@ run-task basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut $@ run-task basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup $@ +run-task basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb $@ run-task basic_tests/clock_network/homo_1clock_1reset_2layer_syntax $@ run-task basic_tests/clock_network/homo_1clock_1reset_2layer_disable_unused_spines $@ run-task basic_tests/clock_network/homo_1clock_1reset_2layer_internal_driver $@ diff --git a/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup/config/task.conf b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup/config/task.conf index a03c48cb9..0dad873c1 100644 --- a/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup/config/task.conf +++ b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup/config/task.conf @@ -25,6 +25,7 @@ openfpga_vpr_route_chan_width=32 openfpga_clock_arch_file=${PATH:TASK_DIR}/config/clk_arch_1clk_1rst_2layer.xml openfpga_verilog_testbench_port_mapping=--explicit_port_mapping openfpga_route_clock_options= +openfpga_pb_pin_fixup_options=--verbose [ARCHITECTURES] arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_frac_N4_tileable_fracff_40nm.xml diff --git a/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/clk_arch_1clk_1rst_2layer.xml b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/clk_arch_1clk_1rst_2layer.xml new file mode 100644 index 000000000..b91512914 --- /dev/null +++ b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/clk_arch_1clk_1rst_2layer.xml @@ -0,0 +1,34 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/pin_constraints_clk.xml b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/pin_constraints_clk.xml new file mode 100644 index 000000000..f0b871511 --- /dev/null +++ b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/pin_constraints_clk.xml @@ -0,0 +1,8 @@ + + + + + + diff --git a/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/pin_constraints_rst.xml b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/pin_constraints_rst.xml new file mode 100644 index 000000000..15df5148e --- /dev/null +++ b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/pin_constraints_rst.xml @@ -0,0 +1,8 @@ + + + + + + diff --git a/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/pin_constraints_rst_and_clk.xml b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/pin_constraints_rst_and_clk.xml new file mode 100644 index 000000000..15df5148e --- /dev/null +++ b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/pin_constraints_rst_and_clk.xml @@ -0,0 +1,8 @@ + + + + + + diff --git a/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/repack_pin_constraints.xml b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/repack_pin_constraints.xml new file mode 100644 index 000000000..06a125111 --- /dev/null +++ b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/repack_pin_constraints.xml @@ -0,0 +1,4 @@ + + + + diff --git a/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/task.conf b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/task.conf new file mode 100644 index 000000000..2549ab7dc --- /dev/null +++ b/openfpga_flow/tasks/basic_tests/clock_network/homo_1clock_1reset_2layer_on_lut_pb_pin_fixup_msb/config/task.conf @@ -0,0 +1,57 @@ +# = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = +# Configuration file for running experiments +# = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = +# timeout_each_job : FPGA Task script splits fpga flow into multiple jobs +# Each job execute fpga_flow script on combination of architecture & benchmark +# timeout_each_job is timeout for each job +# = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = + +[GENERAL] +run_engine=openfpga_shell +power_tech_file = ${PATH:OPENFPGA_PATH}/openfpga_flow/tech/PTM_45nm/45nm.xml +power_analysis = false +spice_output=false +verilog_output=true +timeout_each_job = 3*60 +fpga_flow=yosys_vpr + +[OpenFPGA_SHELL] +openfpga_shell_template=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_shell_scripts/example_clkntwk_pb_pin_fixup_no_ace_script.openfpga +openfpga_arch_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_arch/k4_frac_N4_fracff_40nm_Ntwk1clk1rst2lvl_cc_openfpga.xml +openfpga_sim_setting_file=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_simulation_settings/fixed_sim_openfpga.xml +openfpga_repack_constraints_file=${PATH:TASK_DIR}/config/repack_pin_constraints.xml +openfpga_vpr_device_layout=2x2 +openfpga_vpr_route_chan_width=32 +openfpga_clock_arch_file=${PATH:TASK_DIR}/config/clk_arch_1clk_1rst_2layer.xml +openfpga_verilog_testbench_port_mapping=--explicit_port_mapping +openfpga_route_clock_options= +openfpga_pb_pin_fixup_options=--map_global_net_to_msb --verbose + +[ARCHITECTURES] +arch0=${PATH:OPENFPGA_PATH}/openfpga_flow/vpr_arch/k4_frac_N4_tileable_fracff_40nm.xml + +[BENCHMARKS] +bench0=${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/rst_on_lut/rst_on_lut.v +bench1=${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/clk_on_lut/clk_on_lut.v +bench2=${PATH:OPENFPGA_PATH}/openfpga_flow/benchmarks/micro_benchmark/rst_and_clk_on_lut/rst_and_clk_on_lut.v + +[SYNTHESIS_PARAM] +# Yosys script parameters +bench_yosys_cell_sim_verilog_common=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_yosys_techlib/openfpga_dff_sim.v +bench_yosys_dff_map_verilog_common=${PATH:OPENFPGA_PATH}/openfpga_flow/openfpga_yosys_techlib/openfpga_dff_map.v +bench_read_verilog_options_common = -nolatches +bench_yosys_common=${PATH:OPENFPGA_PATH}/openfpga_flow/misc/ys_tmpl_yosys_vpr_dff_flow.ys +bench_yosys_rewrite_common=${PATH:OPENFPGA_PATH}/openfpga_flow/misc/ys_tmpl_yosys_vpr_flow_with_rewrite.ys;${PATH:OPENFPGA_PATH}/openfpga_flow/misc/ys_tmpl_rewrite_flow.ys + +bench0_top = rst_on_lut +bench0_openfpga_pin_constraints_file = ${PATH:TASK_DIR}/config/pin_constraints_rst.xml + +bench1_top = clk_on_lut +bench1_openfpga_pin_constraints_file = ${PATH:TASK_DIR}/config/pin_constraints_clk.xml + +bench2_top = rst_and_clk_on_lut +bench2_openfpga_pin_constraints_file = ${PATH:TASK_DIR}/config/pin_constraints_rst_and_clk.xml + +[SCRIPT_PARAM_MIN_ROUTE_CHAN_WIDTH] +end_flow_with_test= +vpr_fpga_verilog_formal_verification_top_netlist=