From 0826ad72f318ecc0733f38ed7a15fae07afef569 Mon Sep 17 00:00:00 2001 From: Nathan Shreve Date: Mon, 12 Aug 2024 16:49:05 -0400 Subject: [PATCH] More comments --- vpr/src/base/vpr_context.h | 3 +- vpr/src/route/connection_router.cpp | 12 +- vpr/src/route/connection_router.h | 1 + vpr/src/route/lookahead_profiler.cpp | 2 +- vpr/src/route/lookahead_profiler.h | 2 +- vpr/src/route/route_common.cpp | 12 +- vpr/src/route/router_delay_profiling.cpp | 3 + vpr/src/route/router_delay_profiling.h | 7 +- vpr/src/route/router_lookahead.h | 29 ++++ .../route/router_lookahead_compressed_map.cpp | 5 +- vpr/src/route/router_lookahead_map.cpp | 144 +++++++++--------- vpr/src/route/router_lookahead_map.h | 2 +- 12 files changed, 136 insertions(+), 86 deletions(-) diff --git a/vpr/src/base/vpr_context.h b/vpr/src/base/vpr_context.h index 62d566f3837..f23330e52e0 100644 --- a/vpr/src/base/vpr_context.h +++ b/vpr/src/base/vpr_context.h @@ -37,9 +37,10 @@ #ifndef NO_SERVER #include "gateio.h" -# include "lookahead_profiler.h" #include "taskresolver.h" +# include "lookahead_profiler.h" + class SetupHoldTimingInfo; class PostClusterDelayCalculator; diff --git a/vpr/src/route/connection_router.cpp b/vpr/src/route/connection_router.cpp index 07e6539557e..cf401c9c4a8 100644 --- a/vpr/src/route/connection_router.cpp +++ b/vpr/src/route/connection_router.cpp @@ -924,9 +924,15 @@ void ConnectionRouter::add_route_tree_node_to_heap( tot_cost, describe_rr_node(device_ctx.rr_graph, device_ctx.grid, device_ctx.rr_indexed_data, inode, is_flat_).c_str()); - push_back_node(&heap_, rr_node_route_inf_, - inode, tot_cost, RREdgeId::INVALID(), - backward_path_cost, backward_path_delay, backward_path_congestion, R_upstream); + push_back_node(&heap_, + rr_node_route_inf_, + inode, + tot_cost, + RREdgeId::INVALID(), + backward_path_cost, + backward_path_delay, + backward_path_congestion, + R_upstream); } else { float expected_total_cost = compute_node_cost_using_rcv(cost_params, inode, target_node, rt_node.Tdel, 0, R_upstream); diff --git a/vpr/src/route/connection_router.h b/vpr/src/route/connection_router.h index 400def4cf6c..4bb8a80fb7d 100644 --- a/vpr/src/route/connection_router.h +++ b/vpr/src/route/connection_router.h @@ -127,6 +127,7 @@ class ConnectionRouter : public ConnectionRouterInterface { // Ensure route budgets have been calculated before enabling this void set_rcv_enabled(bool enable) final; + // Get a const reference to the router's lookahead const RouterLookahead& get_router_lookahead() const { return router_lookahead_; } diff --git a/vpr/src/route/lookahead_profiler.cpp b/vpr/src/route/lookahead_profiler.cpp index a5d1c873e6a..a3c47ba56be 100644 --- a/vpr/src/route/lookahead_profiler.cpp +++ b/vpr/src/route/lookahead_profiler.cpp @@ -18,7 +18,7 @@ void LookaheadProfiler::record(int iteration, const RouterLookahead& router_lookahead, const ParentNetId& net_id, const Netlist<>& net_list, - std::vector branch_inodes) { + const std::vector& branch_inodes) { auto& device_ctx = g_vpr_ctx.device(); const auto& rr_graph = device_ctx.rr_graph; auto& route_ctx = g_vpr_ctx.routing(); diff --git a/vpr/src/route/lookahead_profiler.h b/vpr/src/route/lookahead_profiler.h index 82467996db1..ce81b1d02a5 100644 --- a/vpr/src/route/lookahead_profiler.h +++ b/vpr/src/route/lookahead_profiler.h @@ -38,7 +38,7 @@ class LookaheadProfiler { const RouterLookahead& router_lookahead, const ParentNetId& net_id, const Netlist<>& net_list, - std::vector branch_inodes); + const std::vector& branch_inodes); private: ///@breif The output filestream. diff --git a/vpr/src/route/route_common.cpp b/vpr/src/route/route_common.cpp index 0dd2dfb89a9..8a3de79134a 100644 --- a/vpr/src/route/route_common.cpp +++ b/vpr/src/route/route_common.cpp @@ -839,9 +839,15 @@ void reserve_locally_used_opins(HeapInterface* heap, float pres_fac, float acc_f //Add the OPIN to the heap according to it's congestion cost cost = get_rr_cong_cost(to_node, pres_fac); - add_node_to_heap(heap, route_ctx.rr_node_route_inf, - to_node, cost, RREdgeId::INVALID(), - 0., 0., 0., 0.); + add_node_to_heap(heap, + route_ctx.rr_node_route_inf, + to_node, + cost, + RREdgeId::INVALID(), + 0., + 0., + 0., + 0.); } for (ipin = 0; ipin < num_local_opin; ipin++) { diff --git a/vpr/src/route/router_delay_profiling.cpp b/vpr/src/route/router_delay_profiling.cpp index 32d49256acf..02cad1e9cb0 100644 --- a/vpr/src/route/router_delay_profiling.cpp +++ b/vpr/src/route/router_delay_profiling.cpp @@ -149,6 +149,9 @@ bool RouterDelayProfiler::calculate_delay(RRNodeId source_node, float RouterDelayProfiler::get_min_delay(int physical_tile_type_idx, int from_layer, int to_layer, int dx, int dy) const { return min_delays_[physical_tile_type_idx][from_layer][to_layer][dx][dy]; } +const Netlist<>& RouterDelayProfiler::get_net_list() const { + return net_list_; +} //Returns the shortest path delay from src_node to all RR nodes in the RR graph, or NaN if no path exists vtr::vector calculate_all_path_delays_from_rr_node(RRNodeId src_rr_node, diff --git a/vpr/src/route/router_delay_profiling.h b/vpr/src/route/router_delay_profiling.h index e2b10d2fff5..5048f387c50 100644 --- a/vpr/src/route/router_delay_profiling.h +++ b/vpr/src/route/router_delay_profiling.h @@ -43,9 +43,10 @@ class RouterDelayProfiler { */ float get_min_delay(int physical_tile_type_idx, int from_layer, int to_layer, int dx, int dy) const; - const Netlist<>& get_net_list() { - return net_list_; - } + /** + * @brief Get a const reference to the netlist. + */ + const Netlist<>& get_net_list() const; private: const Netlist<>& net_list_; diff --git a/vpr/src/route/router_lookahead.h b/vpr/src/route/router_lookahead.h index 3deff54a312..70041d4caf5 100644 --- a/vpr/src/route/router_lookahead.h +++ b/vpr/src/route/router_lookahead.h @@ -15,15 +15,44 @@ class RouterLookahead { public: /** * @brief Get expected cost from node to target_node. + * * @attention Either compute or read methods must be invoked before invoking get_expected_cost. + * * @param node The source node from which the cost to the target node is obtained. * @param target_node The target node to which the cost is obtained. * @param params Contain the router parameter such as connection criticality, etc. Used to calculate the cost based on the delay and congestion costs. * @param R_upstream Upstream resistance to get to the "node". + * * @return */ virtual float get_expected_cost(RRNodeId node, RRNodeId target_node, const t_conn_cost_params& params, float R_upstream) const = 0; + + /** + * @brief Get expected (delay, congestion) from node to target_node. + * + * @attention Either compute or read methods must be invoked before invoking get_expected_delay_and_cong. + * + * @param node The source node from which the cost to the target node is obtained. + * @param target_node The target node to which the cost is obtained. + * @param params Contain the router parameter such as connection criticality, etc. + * @param R_upstream Upstream resistance to get to the "node". + * + * @return (delay, congestion) + * + * @warning (delay, congestion) are NOT multiplied by (params.criticality, 1. - params.criticality), respectively. + * scale_delay_and_cong_by_criticality should be called after this function before adding these to calculate the + * expected total cost. + */ virtual std::pair get_expected_delay_and_cong(RRNodeId node, RRNodeId target_node, const t_conn_cost_params& params, float R_upstream) const = 0; + + /** + * @brief Multiply delay by params.criticality and cong by (1. - params.criticality). Used in conjunction with + * get_expected_delay_and_cong to calculate the total expected cost. + * + * @param delay + * @param cong + * @param params + */ void scale_delay_and_cong_by_criticality(float& delay, float& cong, const t_conn_cost_params& params) const; /** diff --git a/vpr/src/route/router_lookahead_compressed_map.cpp b/vpr/src/route/router_lookahead_compressed_map.cpp index aed3319e8c9..9c313a7dd11 100644 --- a/vpr/src/route/router_lookahead_compressed_map.cpp +++ b/vpr/src/route/router_lookahead_compressed_map.cpp @@ -422,7 +422,10 @@ float CompressedMapLookahead::get_expected_cost(RRNodeId current_node, RRNodeId } } -std::pair CompressedMapLookahead::get_expected_delay_and_cong(RRNodeId from_node, RRNodeId to_node, const t_conn_cost_params& /*params*/, float) const { +std::pair CompressedMapLookahead::get_expected_delay_and_cong(RRNodeId from_node, + RRNodeId to_node, + const t_conn_cost_params& /*params*/, + float /*R_upstream*/) const { auto& device_ctx = g_vpr_ctx.device(); auto& rr_graph = device_ctx.rr_graph; diff --git a/vpr/src/route/router_lookahead_map.cpp b/vpr/src/route/router_lookahead_map.cpp index 7a71cb09ec9..549cd3a7b8f 100644 --- a/vpr/src/route/router_lookahead_map.cpp +++ b/vpr/src/route/router_lookahead_map.cpp @@ -1,25 +1,25 @@ /* -* The router lookahead provides an estimate of the cost from an intermediate node to the target node -* during directed (A*-like) routing. -* -* The VPR 7.0 lookahead (route/route_timing.c ==> get_timing_driven_expected_cost) lower-bounds the remaining delay and -* congestion by assuming that a minimum number of wires, of the same type as the current node being expanded, can be used -* to complete the route. While this method is efficient, it can run into trouble with architectures that use -* multiple interconnected wire types. -* -* The lookahead in this file performs undirected Dijkstra searches to evaluate many paths through the routing network, -* starting from all the different wire types in the routing architecture. This ensures the lookahead captures the -* effect of inter-wire connectivity. This information is then reduced into a delta_x delta_y based lookup table for -* reach source wire type (f_cost_map). This is used for estimates from CHANX/CHANY -> SINK nodes. See Section 3.2.4 -* in Oleg Petelin's MASc thesis (2016) for more discussion. -* -* To handle estimates starting from SOURCE/OPIN's the lookahead also creates a small side look-up table of the wire types -* which are reachable from each physical tile type's SOURCEs/OPINs (f_src_opin_delays). This is used for -* SRC/OPIN -> CHANX/CHANY estimates. -* -* In the case of SRC/OPIN -> SINK estimates the results from the two look-ups are added together (and the minimum taken -* if there are multiple possibilities). -*/ + * The router lookahead provides an estimate of the cost from an intermediate node to the target node + * during directed (A*-like) routing. + * + * The VPR 7.0 lookahead (route/route_timing.c ==> get_timing_driven_expected_cost) lower-bounds the remaining delay and + * congestion by assuming that a minimum number of wires, of the same type as the current node being expanded, can be used + * to complete the route. While this method is efficient, it can run into trouble with architectures that use + * multiple interconnected wire types. + * + * The lookahead in this file performs undirected Dijkstra searches to evaluate many paths through the routing network, + * starting from all the different wire types in the routing architecture. This ensures the lookahead captures the + * effect of inter-wire connectivity. This information is then reduced into a delta_x delta_y based lookup table for + * reach source wire type (f_cost_map). This is used for estimates from CHANX/CHANY -> SINK nodes. See Section 3.2.4 + * in Oleg Petelin's MASc thesis (2016) for more discussion. + * + * To handle estimates starting from SOURCE/OPIN's the lookahead also creates a small side look-up table of the wire types + * which are reachable from each physical tile type's SOURCEs/OPINs (f_src_opin_delays). This is used for + * SRC/OPIN -> CHANX/CHANY estimates. + * + * In the case of SRC/OPIN -> SINK estimates the results from the two look-ups are added together (and the minimum taken + * if there are multiple possibilities). + */ #include #include @@ -51,8 +51,8 @@ static constexpr int VALID_NEIGHBOR_NUMBER = 3; /* when a list of delay/congestion entries at a coordinate in Cost_Entry is boiled down to a single -* representative entry, this enum is passed-in to specify how that representative entry should be -* calculated */ + * representative entry, this enum is passed-in to specify how that representative entry should be + * calculated */ enum e_representative_entry_method { FIRST = 0, //the first cost that was recorded SMALLEST, //the smallest-delay cost recorded @@ -69,9 +69,9 @@ t_wire_cost_map f_wire_cost_map; /******** File-Scope Functions ********/ /*** -* @brief Fill f_wire_cost_map. It is a look-up table from CHANX/CHANY (to SINKs) for various distances -* @param segment_inf -*/ + * @brief Fill f_wire_cost_map. It is a look-up table from CHANX/CHANY (to SINKs) for various distances + * @param segment_inf + */ static util::Cost_Entry get_wire_cost_entry(e_rr_type rr_type, int seg_index, int from_layer_num, @@ -82,50 +82,50 @@ static util::Cost_Entry get_wire_cost_entry(e_rr_type rr_type, static void compute_router_wire_lookahead(const std::vector& segment_inf); /*** -* @brief Compute the cost from pin to sinks of tiles - Compute the minimum cost to get to each tile sink from pins on the cluster -* @param intra_tile_pin_primitive_pin_delay -* @param tile_min_cost -* @param det_routing_arch -* @param device_ctx -*/ + * @brief Compute the cost from pin to sinks of tiles - Compute the minimum cost to get to each tile sink from pins on the cluster + * @param intra_tile_pin_primitive_pin_delay + * @param tile_min_cost + * @param det_routing_arch + * @param device_ctx + */ static void compute_tiles_lookahead(std::unordered_map& intra_tile_pin_primitive_pin_delay, std::unordered_map>& tile_min_cost, const t_det_routing_arch& det_routing_arch, const DeviceContext& device_ctx); /*** -* @brief Compute the cose from tile pins to tile sinks -* @param intra_tile_pin_primitive_pin_delay [physical_tile_type_idx][from_pin_ptc_num][sink_ptc_num] -> cost -* @param physical_tile -* @param det_routing_arch -* @param delayless_switch -*/ + * @brief Compute the cose from tile pins to tile sinks + * @param intra_tile_pin_primitive_pin_delay [physical_tile_type_idx][from_pin_ptc_num][sink_ptc_num] -> cost + * @param physical_tile + * @param det_routing_arch + * @param delayless_switch + */ static void compute_tile_lookahead(std::unordered_map& intra_tile_pin_primitive_pin_delay, t_physical_tile_type_ptr physical_tile, const t_det_routing_arch& det_routing_arch, const int delayless_switch); /*** -* @brief Compute the minimum cost to get to the sinks from pins on the cluster -* @param tile_min_cost [physical_tile_idx][sink_ptc_num] -> min_cost -* @param physical_tile -* @param intra_tile_pin_primitive_pin_delay [physical_tile_type_idx][from_pin_ptc_num][sink_ptc_num] -> cost -*/ + * @brief Compute the minimum cost to get to the sinks from pins on the cluster + * @param tile_min_cost [physical_tile_idx][sink_ptc_num] -> min_cost + * @param physical_tile + * @param intra_tile_pin_primitive_pin_delay [physical_tile_type_idx][from_pin_ptc_num][sink_ptc_num] -> cost + */ static void store_min_cost_to_sinks(std::unordered_map>& tile_min_cost, t_physical_tile_type_ptr physical_tile, const std::unordered_map& intra_tile_pin_primitive_pin_delay); /** -* @brief Iterate over the first (channel type) and second (segment type) dimensions of f_wire_cost_map to get the minimum cost for each dx and dy_ -* @param internal_opin_global_cost_map This map is populated in this function. [dx][dy] -> cost -*/ + * @brief Iterate over the first (channel type) and second (segment type) dimensions of f_wire_cost_map to get the minimum cost for each dx and dy_ + * @param internal_opin_global_cost_map This map is populated in this function. [dx][dy] -> cost + */ static void min_chann_global_cost_map(vtr::NdMatrix& distance_min_cost); /** -* @brief // Given the src/opin map of each physical tile type, iterate over all OPINs/sources of a type and create -* the minimum cost map across all of them for each tile type. -* @param src_opin_delays -* @param distance_min_cost -*/ + * @brief // Given the src/opin map of each physical tile type, iterate over all OPINs/sources of a type and create + * the minimum cost map across all of them for each tile type. + * @param src_opin_delays + * @param distance_min_cost + */ static void min_opin_distance_cost_map(const util::t_src_opin_delays& src_opin_delays, vtr::NdMatrix& distance_min_cost); // Read the file and fill intra_tile_pin_primitive_pin_delay and tile_min_cost @@ -144,17 +144,17 @@ static void fill_in_missing_lookahead_entries(int segment_index, e_rr_type chan_ static util::Cost_Entry get_nearby_cost_entry(int from_layer_num, int x, int y, int to_layer_num, int segment_index, int chan_index); /** -* @brief Fill in the missing entry in router lookahead map -* If there is a missing entry in the router lookahead, search among its neighbors in a 3x3 window. If there are `VALID_NEIGHBOR_NUMBER` valid entries, -* take the average of them and fill in the missing entry. -* @param from_layer_num The layer num of the source node -* @param missing_dx Dx of the missing input -* @param missing_dy Dy of the missing input -* @param to_layer_num The layer num of the destination point -* @param segment_index The segment index of the source node -* @param chan_index The channel index of the source node -* @return The cost for the missing entry -*/ + * @brief Fill in the missing entry in router lookahead map + * If there is a missing entry in the router lookahead, search among its neighbors in a 3x3 window. If there are `VALID_NEIGHBOR_NUMBER` valid entries, + * take the average of them and fill in the missing entry. + * @param from_layer_num The layer num of the source node + * @param missing_dx Dx of the missing input + * @param missing_dy Dy of the missing input + * @param to_layer_num The layer num of the destination point + * @param segment_index The segment index of the source node + * @param chan_index The channel index of the source node + * @return The cost for the missing entry + */ static util::Cost_Entry get_nearby_cost_entry_average_neighbour(int from_layer_num, int missing_dx, int missing_dy, @@ -527,11 +527,11 @@ static void compute_router_wire_lookahead(const std::vector& segm } /* boil down the cost list in routing_cost_map at each coordinate to a representative cost entry and store it in the lookahead - * cost map */ + * cost map */ set_lookahead_map_costs(from_layer_num, segment_inf.seg_index, chan_type, routing_cost_map); /* fill in missing entries in the lookahead cost map by copying the closest cost entries (cost map was computed based on - * a reference coordinate > (0,0) so some entries that represent a cross-chip distance have not been computed) */ + * a reference coordinate > (0,0) so some entries that represent a cross-chip distance have not been computed) */ fill_in_missing_lookahead_entries(segment_inf.seg_index, chan_type); } } @@ -585,7 +585,7 @@ static void fill_in_missing_lookahead_entries(int segment_index, e_rr_type chan_ /* returns a cost entry in the f_wire_cost_map that is near the specified coordinates (and preferably towards (0,0)) */ static util::Cost_Entry get_nearby_cost_entry(int from_layer_num, int x, int y, int to_layer_num, int segment_index, int chan_index) { /* compute the slope from x,y to 0,0 and then move towards 0,0 by one unit to get the coordinates - * of the cost entry to be copied */ + * of the cost entry to be copied */ //VTR_ASSERT(x > 0 || y > 0); //Asertion fails in practise. TODO: debug @@ -796,12 +796,12 @@ static void min_chann_global_cost_map(vtr::NdMatrix& distan static void min_opin_distance_cost_map(const util::t_src_opin_delays& src_opin_delays, vtr::NdMatrix& distance_min_cost) { /** - * This function calculates and stores the minimum cost to reach a point on layer `n_sink`, which is `dx` and `dy` further from the current point - * on layer `n_source` and is located on physical tile type `t`. To compute this cost, the function iterates over all output pins of tile `t`, - * and for each pin, iterates over all segment types accessible by it. It then determines and stores the minimum cost to the destination point. - * "src_opin_delays" stores the routing segments accessible by each OPIN of each physical type on each layer. After getting the accessible segment types, - * "get_wire_cost_entry" is called to get the cost from that segment type to the destination point. - */ + * This function calculates and stores the minimum cost to reach a point on layer `n_sink`, which is `dx` and `dy` further from the current point + * on layer `n_source` and is located on physical tile type `t`. To compute this cost, the function iterates over all output pins of tile `t`, + * and for each pin, iterates over all segment types accessible by it. It then determines and stores the minimum cost to the destination point. + * "src_opin_delays" stores the routing segments accessible by each OPIN of each physical type on each layer. After getting the accessible segment types, + * "get_wire_cost_entry" is called to get the cost from that segment type to the destination point. + */ int num_tile_types = g_vpr_ctx.device().physical_tile_types.size(); int num_layers = g_vpr_ctx.device().grid.get_num_layers(); int width = (int)g_vpr_ctx.device().grid.width(); @@ -1090,4 +1090,4 @@ void write_router_lookahead(const std::string& file) { writeMessageToFile(file, &builder); } -#endif \ No newline at end of file +#endif diff --git a/vpr/src/route/router_lookahead_map.h b/vpr/src/route/router_lookahead_map.h index dc6c224853e..2ae9c5912e5 100644 --- a/vpr/src/route/router_lookahead_map.h +++ b/vpr/src/route/router_lookahead_map.h @@ -54,4 +54,4 @@ typedef vtr::NdMatrix t_wire_cost_map; //[0..num_layers][0. // is the layer number that the target node is on. void read_router_lookahead(const std::string& file); -void write_router_lookahead(const std::string& file); \ No newline at end of file +void write_router_lookahead(const std::string& file);