@@ -188,7 +188,6 @@ static std::function<void(t_chan_width*)> alloc_and_load_rr_graph(RRGraphBuilder
188
188
const t_track_to_pin_lookup& track_to_pin_lookup_y,
189
189
const t_pin_to_track_lookup& opin_to_track_map,
190
190
const vtr::NdMatrix<std::vector<int >, 3 >& switch_block_conn,
191
- vtr::NdMatrix<t_inter_die_switchblock_edge, 5 >& multi_layer_track_conn,
192
191
t_sb_connection_map* sb_conn_map,
193
192
const DeviceGrid& grid,
194
193
const int Fs,
@@ -469,8 +468,8 @@ static void build_rr_chan(RRGraphBuilder& rr_graph_builder,
469
468
const t_rr_type chan_type,
470
469
const t_track_to_pin_lookup& track_to_pin_lookup,
471
470
t_sb_connection_map* sb_conn_map,
472
- vtr::NdMatrix<t_inter_die_switchblock_edge, 5 >& multi_layer_track_conn,
473
471
const vtr::NdMatrix<std::vector<int >, 3 >& switch_block_conn,
472
+ vtr::NdMatrix<int , 2 >& num_of_3d_conns_custom_SB,
474
473
const int cost_index_offset,
475
474
const t_chan_width& nodes_per_chan,
476
475
const DeviceGrid& grid,
@@ -479,7 +478,8 @@ static void build_rr_chan(RRGraphBuilder& rr_graph_builder,
479
478
const int Fs_per_side,
480
479
const t_chan_details& chan_details_x,
481
480
const t_chan_details& chan_details_y,
482
- t_rr_edge_info_set& created_rr_edges,
481
+ t_rr_edge_info_set& rr_edges_to_create,
482
+ t_rr_edge_info_set& des_3d_rr_edges_to_create,
483
483
const int wire_to_ipin_switch,
484
484
const int wire_to_pin_between_dice_switch,
485
485
const int delayless_switch,
@@ -1265,24 +1265,13 @@ static void build_rr_graph(const t_graph_type graph_type,
1265
1265
}
1266
1266
/* END SB LOOKUP */
1267
1267
1268
- /* Add extra nodes to RR graph to support 3D custom switch blocks for multi-layer FPGAs
1269
- * For each connection in 3D custom switch blocks, multiple drivers can drive the same sink in another layer,
1270
- * this matrix keeps the drivers and the offset to extra length-0 node index in RR graph for each destination track
1271
- * based on its coordinate (layer, x, y), track ptc_num, channel type
1272
- * Access pattern: [0..grid.layer-1][0..grid.width-1][0..grid.height-1][0..max_chan_width-1][CHANX or CHANY]
1273
- */
1274
- vtr::NdMatrix<t_inter_die_switchblock_edge, 5 > multi_layer_track_conn;
1275
- auto & grid_ctx = device_ctx.grid ;
1276
-
1277
1268
/* check whether RR graph need to allocate new nodes for 3D custom switch blocks.
1278
1269
* To avoid wasting memory, the data structures are only allocated if a custom switch block
1279
1270
* is described in the architecture file and we have more than one die in device grid.
1280
1271
*/
1281
1272
if (grid.get_num_layers () > 1 && sb_type == CUSTOM) {
1282
- // initialize the multi_layer_track_conn
1283
- multi_layer_track_conn.resize (std::array<size_t , 5 >{(size_t )grid_ctx.get_num_layers (), grid.width (), grid.height (), (size_t )max_chan_width, 2 });
1284
- // keep how many nodes each switchblock requires
1285
- auto extra_nodes_per_switchblock = get_number_track_to_track_inter_die_conn (multi_layer_track_conn, sb_conn_map, device_ctx.rr_graph_builder );
1273
+ // keep how many nodes each switchblock requires for each x,y location
1274
+ auto extra_nodes_per_switchblock = get_number_track_to_track_inter_die_conn (sb_conn_map, device_ctx.rr_graph_builder );
1286
1275
// allocate new nodes in each switchblocks
1287
1276
alloc_and_load_inter_die_rr_node_indices (device_ctx.rr_graph_builder , &nodes_per_chan, grid, extra_nodes_per_switchblock, &num_rr_nodes);
1288
1277
device_ctx.rr_graph_builder .resize_nodes (num_rr_nodes);
@@ -1377,7 +1366,7 @@ static void build_rr_graph(const t_graph_type graph_type,
1377
1366
chan_details_x, chan_details_y,
1378
1367
track_to_pin_lookup_x, track_to_pin_lookup_y,
1379
1368
opin_to_track_map,
1380
- switch_block_conn, multi_layer_track_conn, sb_conn_map, grid, Fs, unidir_sb_pattern,
1369
+ switch_block_conn, sb_conn_map, grid, Fs, unidir_sb_pattern,
1381
1370
Fc_out, Fc_xofs, Fc_yofs,
1382
1371
nodes_per_chan,
1383
1372
wire_to_arch_ipin_switch,
@@ -1480,8 +1469,6 @@ static void build_rr_graph(const t_graph_type graph_type,
1480
1469
sb_conn_map = nullptr ;
1481
1470
}
1482
1471
1483
- multi_layer_track_conn.clear ();
1484
-
1485
1472
track_to_pin_lookup_x.clear ();
1486
1473
track_to_pin_lookup_y.clear ();
1487
1474
@@ -2037,7 +2024,6 @@ static std::function<void(t_chan_width*)> alloc_and_load_rr_graph(RRGraphBuilder
2037
2024
const t_track_to_pin_lookup& track_to_pin_lookup_y,
2038
2025
const t_pin_to_track_lookup& opin_to_track_map,
2039
2026
const vtr::NdMatrix<std::vector<int >, 3 >& switch_block_conn,
2040
- vtr::NdMatrix<t_inter_die_switchblock_edge, 5 >& multi_layer_track_conn,
2041
2027
t_sb_connection_map* sb_conn_map,
2042
2028
const DeviceGrid& grid,
2043
2029
const int Fs,
@@ -2163,31 +2149,41 @@ static std::function<void(t_chan_width*)> alloc_and_load_rr_graph(RRGraphBuilder
2163
2149
/* Build channels */
2164
2150
VTR_ASSERT (Fs % 3 == 0 );
2165
2151
2166
- for (int layer = 0 ; layer < grid.get_num_layers (); ++layer) {
2167
- auto & device_ctx = g_vpr_ctx.device ();
2168
- /* Skip the current die if architecture file specifies that it doesn't require inter-cluster programmable resource routing */
2169
- if (!device_ctx.inter_cluster_prog_routing_resources .at (layer)) {
2170
- continue ;
2171
- }
2172
- for (size_t i = 0 ; i < grid.width () - 1 ; ++i) {
2173
- for (size_t j = 0 ; j < grid.height () - 1 ; ++j) {
2152
+ /* In case of multi-die FPGA and a custom 3D SB, we keep track of how many 3D connections have been already made for each x,y location */
2153
+ vtr::NdMatrix<int , 2 > num_of_3d_conns_custom_SB;
2154
+
2155
+ t_rr_edge_info_set des_3d_rr_edges_to_create;
2156
+ if (grid.get_num_layers () > 1 && sb_conn_map != nullptr ){
2157
+ num_of_3d_conns_custom_SB.resize (std::array<size_t ,2 >{grid.width (), grid.height ()}, 0 );
2158
+ }
2159
+
2160
+ for (size_t i = 0 ; i < grid.width () - 1 ; ++i) {
2161
+ for (size_t j = 0 ; j < grid.height () - 1 ; ++j) {
2162
+ for (int layer = 0 ; layer < grid.get_num_layers (); ++layer) {
2163
+ auto &device_ctx = g_vpr_ctx.device ();
2164
+ /* Skip the current die if architecture file specifies that it doesn't require inter-cluster programmable resource routing */
2165
+ if (!device_ctx.inter_cluster_prog_routing_resources .at (layer)) {
2166
+ continue ;
2167
+ }
2174
2168
/* In multi-die FPGAs with track-to-track connections between layers, we need to load newly added length-0 CHANX nodes
2175
2169
* These extra nodes can be driven from many tracks in the source layer and can drive multiple tracks in the destination layer,
2176
2170
* since these die-crossing connections have more delays.
2177
2171
*/
2178
2172
if (grid.get_num_layers () > 1 && sb_conn_map != nullptr ) {
2179
2173
// custom switch block defined in the architecture
2180
2174
VTR_ASSERT (sblock_pattern.empty () && switch_block_conn.empty ());
2181
- build_inter_die_custom_sb_rr_chan (rr_graph_builder, layer, i, j, CHANX_COST_INDEX_START, chan_width, chan_details_x);
2175
+ build_inter_die_custom_sb_rr_chan (rr_graph_builder, layer, i, j, CHANX_COST_INDEX_START, chan_width,
2176
+ chan_details_x);
2182
2177
}
2183
2178
2184
2179
if (i > 0 ) {
2185
2180
int tracks_per_chan = ((is_global_graph) ? 1 : chan_width.x_list [j]);
2186
- build_rr_chan (rr_graph_builder, layer, i, j, CHANX, track_to_pin_lookup_x, sb_conn_map, multi_layer_track_conn, switch_block_conn,
2187
- CHANX_COST_INDEX_START,
2181
+ build_rr_chan (rr_graph_builder, layer, i, j, CHANX, track_to_pin_lookup_x, sb_conn_map,
2182
+ switch_block_conn,
2183
+ num_of_3d_conns_custom_SB, CHANX_COST_INDEX_START,
2188
2184
chan_width, grid, tracks_per_chan,
2189
2185
sblock_pattern, Fs / 3 , chan_details_x, chan_details_y,
2190
- rr_edges_to_create,
2186
+ rr_edges_to_create, des_3d_rr_edges_to_create,
2191
2187
wire_to_ipin_switch,
2192
2188
wire_to_pin_between_dice_switch,
2193
2189
delayless_switch,
@@ -2202,11 +2198,12 @@ static std::function<void(t_chan_width*)> alloc_and_load_rr_graph(RRGraphBuilder
2202
2198
}
2203
2199
if (j > 0 ) {
2204
2200
int tracks_per_chan = ((is_global_graph) ? 1 : chan_width.y_list [i]);
2205
- build_rr_chan (rr_graph_builder, layer, i, j, CHANY, track_to_pin_lookup_y, sb_conn_map, multi_layer_track_conn, switch_block_conn,
2206
- CHANX_COST_INDEX_START + num_seg_types_x,
2201
+ build_rr_chan (rr_graph_builder, layer, i, j, CHANY, track_to_pin_lookup_y, sb_conn_map,
2202
+ switch_block_conn,
2203
+ num_of_3d_conns_custom_SB, CHANX_COST_INDEX_START + num_seg_types_x,
2207
2204
chan_width, grid, tracks_per_chan,
2208
2205
sblock_pattern, Fs / 3 , chan_details_x, chan_details_y,
2209
- rr_edges_to_create,
2206
+ rr_edges_to_create, des_3d_rr_edges_to_create,
2210
2207
wire_to_ipin_switch,
2211
2208
wire_to_pin_between_dice_switch,
2212
2209
delayless_switch,
@@ -2223,6 +2220,14 @@ static std::function<void(t_chan_width*)> alloc_and_load_rr_graph(RRGraphBuilder
2223
2220
}
2224
2221
}
2225
2222
2223
+ if (grid.get_num_layers () > 1 && sb_conn_map != nullptr ){
2224
+ uniquify_edges (des_3d_rr_edges_to_create);
2225
+ alloc_and_load_edges (rr_graph_builder, des_3d_rr_edges_to_create);
2226
+ num_edges += des_3d_rr_edges_to_create.size ();
2227
+ des_3d_rr_edges_to_create.clear ();
2228
+ }
2229
+
2230
+
2226
2231
VTR_LOG (" CHAN->CHAN type edge count:%d\n " , num_edges);
2227
2232
num_edges = 0 ;
2228
2233
std::function<void (t_chan_width*)> update_chan_width = [](t_chan_width*) noexcept {};
@@ -3096,8 +3101,8 @@ static void build_rr_chan(RRGraphBuilder& rr_graph_builder,
3096
3101
const t_rr_type chan_type,
3097
3102
const t_track_to_pin_lookup& track_to_pin_lookup,
3098
3103
t_sb_connection_map* sb_conn_map,
3099
- vtr::NdMatrix<t_inter_die_switchblock_edge, 5 >& multi_layer_track_conn,
3100
3104
const vtr::NdMatrix<std::vector<int >, 3 >& switch_block_conn,
3105
+ vtr::NdMatrix<int , 2 >& num_of_3d_conns_custom_SB,
3101
3106
const int cost_index_offset,
3102
3107
const t_chan_width& nodes_per_chan,
3103
3108
const DeviceGrid& grid,
@@ -3107,6 +3112,7 @@ static void build_rr_chan(RRGraphBuilder& rr_graph_builder,
3107
3112
const t_chan_details& chan_details_x,
3108
3113
const t_chan_details& chan_details_y,
3109
3114
t_rr_edge_info_set& rr_edges_to_create,
3115
+ t_rr_edge_info_set& des_3d_rr_edges_to_create,
3110
3116
const int wire_to_ipin_switch,
3111
3117
const int wire_to_pin_between_dice_switch,
3112
3118
const int delayless_switch,
@@ -3189,9 +3195,9 @@ static void build_rr_chan(RRGraphBuilder& rr_graph_builder,
3189
3195
}
3190
3196
if (to_seg_details->length () > 0 ) {
3191
3197
get_track_to_tracks (rr_graph_builder, layer, chan_coord, start, track, chan_type, chan_coord,
3192
- opposite_chan_type, multi_layer_track_conn, seg_dimension, max_opposite_chan_width, grid,
3193
- Fs_per_side, sblock_pattern, node, rr_edges_to_create,
3194
- from_seg_details, to_seg_details, opposite_chan_details,
3198
+ opposite_chan_type, seg_dimension, max_opposite_chan_width, grid,
3199
+ Fs_per_side, sblock_pattern, num_of_3d_conns_custom_SB, node, rr_edges_to_create,
3200
+ des_3d_rr_edges_to_create, from_seg_details, to_seg_details, opposite_chan_details,
3195
3201
directionality,delayless_switch,
3196
3202
switch_block_conn, sb_conn_map);
3197
3203
}
@@ -3209,9 +3215,9 @@ static void build_rr_chan(RRGraphBuilder& rr_graph_builder,
3209
3215
}
3210
3216
if (to_seg_details->length () > 0 ) {
3211
3217
get_track_to_tracks (rr_graph_builder, layer, chan_coord, start, track, chan_type, chan_coord + 1 ,
3212
- opposite_chan_type, multi_layer_track_conn, seg_dimension, max_opposite_chan_width, grid,
3213
- Fs_per_side, sblock_pattern, node, rr_edges_to_create,
3214
- from_seg_details, to_seg_details, opposite_chan_details,
3218
+ opposite_chan_type, seg_dimension, max_opposite_chan_width, grid,
3219
+ Fs_per_side, sblock_pattern, num_of_3d_conns_custom_SB, node, rr_edges_to_create,
3220
+ des_3d_rr_edges_to_create, from_seg_details, to_seg_details, opposite_chan_details,
3215
3221
directionality, delayless_switch, switch_block_conn, sb_conn_map);
3216
3222
}
3217
3223
}
@@ -3241,9 +3247,9 @@ static void build_rr_chan(RRGraphBuilder& rr_graph_builder,
3241
3247
}
3242
3248
if (to_seg_details->length () > 0 ) {
3243
3249
get_track_to_tracks (rr_graph_builder, layer, chan_coord, start, track, chan_type, target_seg,
3244
- chan_type, multi_layer_track_conn, seg_dimension, max_chan_width, grid,
3245
- Fs_per_side, sblock_pattern, node, rr_edges_to_create,
3246
- from_seg_details, to_seg_details, from_chan_details,
3250
+ chan_type, seg_dimension, max_chan_width, grid,
3251
+ Fs_per_side, sblock_pattern, num_of_3d_conns_custom_SB, node, rr_edges_to_create,
3252
+ des_3d_rr_edges_to_create, from_seg_details, to_seg_details, from_chan_details,
3247
3253
directionality,delayless_switch,
3248
3254
switch_block_conn, sb_conn_map);
3249
3255
}
0 commit comments