diff --git a/vpr/src/pack/sync_netlists_to_routing_flat.cpp b/vpr/src/pack/sync_netlists_to_routing_flat.cpp index 6670212ea49..ef1e29b8160 100644 --- a/vpr/src/pack/sync_netlists_to_routing_flat.cpp +++ b/vpr/src/pack/sync_netlists_to_routing_flat.cpp @@ -3,6 +3,7 @@ * after routing optimization *******************************************************************/ /* Headers from vtrutil library */ +#include "clustered_netlist_fwd.h" #include "clustered_netlist_utils.h" #include "logic_types.h" #include "netlist_fwd.h" @@ -25,6 +26,31 @@ static void sync_pb_routes_to_routing(void); static void sync_clustered_netlist_to_routing(void); static void fixup_atom_pb_graph_pin_mapping(void); +inline ClusterBlockId get_cluster_block_from_rr_node(RRNodeId inode){ + auto& device_ctx = g_vpr_ctx.device(); + auto& place_ctx = g_vpr_ctx.placement(); + auto& rr_graph = device_ctx.rr_graph; + + auto physical_tile = device_ctx.grid.get_physical_type({ + rr_graph.node_xlow(inode), + rr_graph.node_ylow(inode), + rr_graph.node_layer(inode) + }); + + int source_pin = rr_graph.node_pin_num(inode); + + auto [_, subtile] = get_sub_tile_from_pin_physical_num(physical_tile, source_pin); + + ClusterBlockId clb = place_ctx.grid_blocks.block_at_location({ + rr_graph.node_xlow(inode), + rr_graph.node_ylow(inode), + subtile, + rr_graph.node_layer(inode) + }); + + return clb; +} + /* Output all intra-cluster connections for a RouteTreeNode */ static void get_intra_cluster_connections(const RouteTree& tree, std::vector>& out_connections){ auto& rr_graph = g_vpr_ctx.device().rr_graph; @@ -34,22 +60,24 @@ static void get_intra_cluster_connections(const RouteTree& tree, std::vectorinode); - /* Both nodes are IPIN/OPIN: this has to be an intrablock connection */ - if((type == OPIN || type == IPIN) && (parent_type == OPIN || parent_type == IPIN)){ - out_connections.push_back({parent->inode, node.inode}); + if((type == IPIN || type == OPIN) && (parent_type == IPIN || parent_type == OPIN)){ + auto clb = get_cluster_block_from_rr_node(node.inode); + auto parent_clb = get_cluster_block_from_rr_node(parent->inode); + if(clb == parent_clb) + out_connections.push_back({parent->inode, node.inode}); } } } /** Rudimentary intra-cluster router between two pb_graph pins. * Easier to use than the packer's router, but it assumes that there is only one path between the provided pins. - * Expect this to fail/produce invalid results if that's not the case with your architecture. + * (which should be the case due to the flat router's RR graph compression) * Outputs the path to the given pb. */ static void route_intra_cluster_conn(const t_pb_graph_pin* source_pin, const t_pb_graph_pin* sink_pin, AtomNetId net_id, t_pb* out_pb){ - std::unordered_set visited; std::deque queue; std::unordered_map prev; @@ -61,7 +89,6 @@ static void route_intra_cluster_conn(const t_pb_graph_pin* source_pin, const t_p while(!queue.empty()){ const t_pb_graph_pin* cur_pin = queue.front(); - //std::cout << "expanding: " << cur_pin->to_string() << "\n"; queue.pop_front(); if(visited.count(cur_pin)) continue; @@ -75,20 +102,20 @@ static void route_intra_cluster_conn(const t_pb_graph_pin* source_pin, const t_p for(auto& edge: cur_pin->output_edges){ VTR_ASSERT(edge->num_output_pins == 1); queue.push_back(edge->output_pins[0]); - //std::cout << "pushing back " << edge->output_pins[0]->to_string() << "\n"; prev[edge->output_pins[0]] = cur_pin; } } - + VTR_ASSERT_MSG(visited.count(sink_pin), "Couldn't find sink pin"); /* Collect path: we need to build pb_routes from source to sink */ std::vector path; const t_pb_graph_pin* cur_pin = sink_pin; - while(cur_pin){ + while(cur_pin != source_pin){ path.push_back(cur_pin); cur_pin = prev[cur_pin]; } + path.push_back(source_pin); /* Output the path into out_pb_routes (start from source) */ int prev_pin_id = -1;