keep debugging rr_graph builder

This commit is contained in:
tangxifan 2020-02-04 15:21:45 -07:00
parent 15167c9bfb
commit 6881863506
5 changed files with 260 additions and 176 deletions

View File

@ -65,24 +65,10 @@ short RRGraph::node_ylow(const RRNodeId& node) const {
} }
short RRGraph::node_xhigh(const RRNodeId& node) const { short RRGraph::node_xhigh(const RRNodeId& node) const {
/* Special for SOURCE and SINK node, we always return the xlow
* This is due to the convention in creating RRGraph
* so that we can guarantee unique SOURCE/SINK nodes searching
if ( (SOURCE == node_type(node))
|| (SINK == node_type(node)) ) {
return node_bounding_box(node).xmin();
}
*/
return node_bounding_box(node).xmax(); return node_bounding_box(node).xmax();
} }
short RRGraph::node_yhigh(const RRNodeId& node) const { short RRGraph::node_yhigh(const RRNodeId& node) const {
/*
if ( (SOURCE == node_type(node))
|| (SINK == node_type(node)) ) {
return node_bounding_box(node).ymin();
}
*/
return node_bounding_box(node).ymax(); return node_bounding_box(node).ymax();
} }
@ -966,6 +952,12 @@ void RRGraph::remove_edge(const RREdgeId& edge) {
set_dirty(); set_dirty();
} }
void RRGraph::set_node_type(const RRNodeId& node, const t_rr_type& type) {
VTR_ASSERT(valid_node_id(node));
node_types_[node] = type;
}
void RRGraph::set_node_xlow(const RRNodeId& node, const short& xlow) { void RRGraph::set_node_xlow(const RRNodeId& node, const short& xlow) {
VTR_ASSERT(valid_node_id(node)); VTR_ASSERT(valid_node_id(node));
@ -1228,30 +1220,9 @@ void RRGraph::build_fast_node_lookup() const {
/* Special for SOURCE and SINK, we should annotate in the look-up /* Special for SOURCE and SINK, we should annotate in the look-up
* for all the (x,y) upto (xhigh, yhigh) * for all the (x,y) upto (xhigh, yhigh)
*/ */
std::vector<size_t> xlows; size_t x = node_xlow(node);
std::vector<size_t> ylows; size_t y = node_ylow(node);
/*
if ( (SOURCE == node_type(node))
|| (SINK == node_type(node))
|| (CHANX == node_type(node))
|| (CHANY == node_type(node)) ) {
xlows.resize(node_bounding_boxes_[node].xmax() - node_bounding_boxes_[node].xmin() + 1);
ylows.resize(node_bounding_boxes_[node].ymax() - node_bounding_boxes_[node].ymin() + 1);
std::iota(xlows.begin(), xlows.end(), node_xlow(node));
std::iota(ylows.begin(), ylows.end(), node_ylow(node));
VTR_ASSERT(size_t(node_bounding_boxes_[node].xmax()) == xlows.back());
VTR_ASSERT(size_t(node_bounding_boxes_[node].ymax()) == ylows.back());
} else {
*/
xlows.push_back(node_xlow(node));
ylows.push_back(node_ylow(node));
/*
}
*/
for (size_t x : xlows) {
for (size_t y : ylows) {
size_t itype = node_type(node); size_t itype = node_type(node);
size_t ptc = node_ptc_num(node); size_t ptc = node_ptc_num(node);
@ -1274,8 +1245,6 @@ void RRGraph::build_fast_node_lookup() const {
node_lookup_[x][y][itype][ptc][iside] = node; node_lookup_[x][y][itype][ptc][iside] = node;
} }
} }
}
}
void RRGraph::invalidate_fast_node_lookup() const { void RRGraph::invalidate_fast_node_lookup() const {
node_lookup_.clear(); node_lookup_.clear();

View File

@ -646,6 +646,8 @@ class RRGraph {
void remove_edge(const RREdgeId& edge); void remove_edge(const RREdgeId& edge);
/* Set node-level information */ /* Set node-level information */
void set_node_type(const RRNodeId& node, const t_rr_type& type);
void set_node_xlow(const RRNodeId& node, const short& xlow); void set_node_xlow(const RRNodeId& node, const short& xlow);
void set_node_ylow(const RRNodeId& node, const short& ylow); void set_node_ylow(const RRNodeId& node, const short& ylow);
void set_node_xhigh(const RRNodeId& node, const short& xhigh); void set_node_xhigh(const RRNodeId& node, const short& xhigh);

View File

@ -153,8 +153,7 @@ static int get_opin_direct_connections(int x,
const int num_directs, const int num_directs,
const t_clb_to_clb_directs* clb_to_clb_directs); const t_clb_to_clb_directs* clb_to_clb_directs);
static void alloc_and_load_rr_graph(const int num_nodes, static void alloc_and_load_rr_graph(RRGraph& rr_graph,
RRGraph& rr_graph,
const int num_seg_types, const int num_seg_types,
const t_chan_details& chan_details_x, const t_chan_details& chan_details_x,
const t_chan_details& chan_details_y, const t_chan_details& chan_details_y,
@ -599,11 +598,20 @@ static void build_rr_graph(const t_graph_type graph_type,
int num_rr_nodes = 0; int num_rr_nodes = 0;
/* Xifan Tang - /* Xifan Tang -
* We create all the nodes in the RRGraph object here * Reuse the legacy rr_node indice because it has many out-of-law exceptions during the graph building
* which is not allowed by RRGraph object
*/ */
device_ctx.rr_graph = alloc_and_load_rr_node_indices(max_chan_width, grid, t_rr_node_indices L_rr_node_indices = alloc_and_load_rr_node_indices(max_chan_width, grid,
&num_rr_nodes, chan_details_x, chan_details_y); &num_rr_nodes, chan_details_x, chan_details_y);
/* Allocate the nodes in RR Graph */
device_ctx.rr_graph.reserve_nodes(num_rr_nodes);
for (int i = 0; i < num_rr_nodes; ++i) {
/* Give a fake node type, will be corrected later in the builder */
device_ctx.rr_graph.create_node(SOURCE);
}
/* The number of segments are in general small, reserve segments may not bring /* The number of segments are in general small, reserve segments may not bring
* significant memory efficiency */ * significant memory efficiency */
device_ctx.rr_graph.reserve_segments(segment_inf.size()); device_ctx.rr_graph.reserve_segments(segment_inf.size());
@ -723,11 +731,11 @@ static void build_rr_graph(const t_graph_type graph_type,
device_ctx.rr_graph.create_switch(temp_rr_switch); device_ctx.rr_graph.create_switch(temp_rr_switch);
} }
alloc_and_load_rr_graph(device_ctx.rr_graph.nodes().size(), device_ctx.rr_graph, segment_inf.size(), alloc_and_load_rr_graph(device_ctx.rr_graph, segment_inf.size(),
chan_details_x, chan_details_y, chan_details_x, chan_details_y,
track_to_pin_lookup, opin_to_track_map, track_to_pin_lookup, opin_to_track_map,
switch_block_conn, sb_conn_map, grid, Fs, unidir_sb_pattern, switch_block_conn, sb_conn_map, grid, Fs, unidir_sb_pattern,
Fc_out, Fc_xofs, Fc_yofs, device_ctx.rr_node_indices, Fc_out, Fc_xofs, Fc_yofs, L_rr_node_indices,
max_chan_width, max_chan_width,
nodes_per_chan, nodes_per_chan,
wire_to_arch_ipin_switch, wire_to_arch_ipin_switch,
@ -820,6 +828,8 @@ static void build_rr_graph(const t_graph_type graph_type,
if (clb_to_clb_directs != nullptr) { if (clb_to_clb_directs != nullptr) {
free(clb_to_clb_directs); free(clb_to_clb_directs);
} }
L_rr_node_indices.clear();
} }
/* Allocates and loads the global rr_switch_inf array based on the global /* Allocates and loads the global rr_switch_inf array based on the global
@ -1292,8 +1302,7 @@ static void free_type_track_to_pin_map(t_track_to_pin_lookup& track_to_pin_map,
/* Does the actual work of allocating the rr_graph and filling all the * /* Does the actual work of allocating the rr_graph and filling all the *
* appropriate values. Everything up to this was just a prelude! */ * appropriate values. Everything up to this was just a prelude! */
static void alloc_and_load_rr_graph(const int num_nodes, static void alloc_and_load_rr_graph(RRGraph& rr_graph,
RRGraph& rr_graph,
const int num_seg_types, const int num_seg_types,
const t_chan_details& chan_details_x, const t_chan_details& chan_details_x,
const t_chan_details& chan_details_y, const t_chan_details& chan_details_y,
@ -1463,12 +1472,12 @@ static void build_bidir_rr_opins(const int i,
total_pin_Fc += Fc[pin_index][iseg]; total_pin_Fc += Fc[pin_index][iseg];
} }
RRNodeId node_index = rr_graph.find_node(i, j, OPIN, pin_index, side); RRNodeId node_index = RRNodeId(get_rr_node_index(L_rr_node_indices, i, j, OPIN, pin_index, side));
VTR_ASSERT(true == rr_graph.valid_node_id(node_index)); VTR_ASSERT(true == rr_graph.valid_node_id(node_index));
if (total_pin_Fc > 0) { if (total_pin_Fc > 0) {
get_bidir_opin_connections(i, j, pin_index, get_bidir_opin_connections(i, j, pin_index,
node_index, rr_edges_to_create, opin_to_track_map, rr_graph, node_index, rr_edges_to_create, opin_to_track_map, L_rr_node_indices,
chan_details_x, chan_details_x,
chan_details_y); chan_details_y);
} }
@ -1540,7 +1549,7 @@ static void build_rr_sinks_sources(const int i,
for (int iclass = 0; iclass < num_class; ++iclass) { for (int iclass = 0; iclass < num_class; ++iclass) {
RRNodeId inode = RRNodeId::INVALID(); RRNodeId inode = RRNodeId::INVALID();
if (class_inf[iclass].type == DRIVER) { /* SOURCE */ if (class_inf[iclass].type == DRIVER) { /* SOURCE */
inode = rr_graph.find_node(i, j, SOURCE, iclass); inode = RRNodeId(get_rr_node_index(L_rr_node_indices, i, j, SOURCE, iclass));
//Retrieve all the physical OPINs associated with this source, this includes //Retrieve all the physical OPINs associated with this source, this includes
//those at different grid tiles of this block //those at different grid tiles of this block
@ -1549,7 +1558,7 @@ static void build_rr_sinks_sources(const int i,
for (int height_offset = 0; height_offset < type->height; ++height_offset) { for (int height_offset = 0; height_offset < type->height; ++height_offset) {
for (int ipin = 0; ipin < class_inf[iclass].num_pins; ++ipin) { for (int ipin = 0; ipin < class_inf[iclass].num_pins; ++ipin) {
int pin_num = class_inf[iclass].pinlist[ipin]; int pin_num = class_inf[iclass].pinlist[ipin];
auto physical_pins = find_rr_graph_nodes(rr_graph, i + width_offset, j + height_offset, OPIN, pin_num); auto physical_pins = get_rr_graph_node_indices(L_rr_node_indices, i + width_offset, j + height_offset, OPIN, pin_num);
opin_nodes.insert(opin_nodes.end(), physical_pins.begin(), physical_pins.end()); opin_nodes.insert(opin_nodes.end(), physical_pins.begin(), physical_pins.end());
} }
} }
@ -1560,10 +1569,11 @@ static void build_rr_sinks_sources(const int i,
rr_edges_to_create.emplace_back(inode, opin_nodes[iedge], delayless_switch); rr_edges_to_create.emplace_back(inode, opin_nodes[iedge], delayless_switch);
} }
rr_graph.set_node_type(inode, SOURCE);
rr_graph.set_node_cost_index(inode, SOURCE_COST_INDEX); rr_graph.set_node_cost_index(inode, SOURCE_COST_INDEX);
} else { /* SINK */ } else { /* SINK */
VTR_ASSERT(class_inf[iclass].type == RECEIVER); VTR_ASSERT(class_inf[iclass].type == RECEIVER);
inode = rr_graph.find_node(i, j, SINK, iclass); inode = get_rr_graph_node_index(L_rr_node_indices, i, j, SINK, iclass);
/* NOTE: To allow route throughs through clbs, change the lines below to * /* NOTE: To allow route throughs through clbs, change the lines below to *
* make an edge from the input SINK to the output SOURCE. Do for just the * * make an edge from the input SINK to the output SOURCE. Do for just the *
@ -1572,7 +1582,8 @@ static void build_rr_sinks_sources(const int i,
* base cost of OPINs and/or SOURCES so they aren't used excessively. */ * base cost of OPINs and/or SOURCES so they aren't used excessively. */
/* Initialize to unconnected */ /* Initialize to unconnected */
rr_graph.set_node_cost_index(RRNodeId(inode), SINK_COST_INDEX); rr_graph.set_node_type(inode, SINK);
rr_graph.set_node_cost_index(inode, SINK_COST_INDEX);
} }
/* Things common to both SOURCEs and SINKs. */ /* Things common to both SOURCEs and SINKs. */
@ -1597,24 +1608,29 @@ static void build_rr_sinks_sources(const int i,
if (class_inf[iclass].type == RECEIVER) { if (class_inf[iclass].type == RECEIVER) {
//Connect the input pin to the sink //Connect the input pin to the sink
inode = rr_graph.find_node(i + width_offset, j + height_offset, IPIN, ipin, side); inode = RRNodeId(get_rr_node_index(L_rr_node_indices, i + width_offset, j + height_offset, IPIN, ipin, side));
RRNodeId to_node = rr_graph.find_node(i, j, SINK, iclass); RRNodeId to_node = RRNodeId(get_rr_node_index(L_rr_node_indices, i, j, SINK, iclass));
VTR_ASSERT(true == rr_graph.valid_node_id(inode));
VTR_ASSERT(true == rr_graph.valid_node_id(to_node));
//Add info about the edge to be created //Add info about the edge to be created
rr_edges_to_create.emplace_back(inode, to_node, delayless_switch); rr_edges_to_create.emplace_back(inode, to_node, delayless_switch);
VTR_ASSERT(true == rr_graph.valid_node_id(inode)); rr_graph.set_node_type(inode, IPIN);
rr_graph.set_node_cost_index(inode, IPIN_COST_INDEX); rr_graph.set_node_cost_index(inode, IPIN_COST_INDEX);
} else { } else {
VTR_ASSERT(class_inf[iclass].type == DRIVER); VTR_ASSERT(class_inf[iclass].type == DRIVER);
//Initialize the output pin //Initialize the output pin
// Note that we leave it's out-going edges unconnected (they will be hooked up to global routing later) // Note that we leave it's out-going edges unconnected (they will be hooked up to global routing later)
inode = rr_graph.find_node(i + width_offset, j + height_offset, OPIN, ipin, side); inode = RRNodeId(get_rr_node_index(L_rr_node_indices, i + width_offset, j + height_offset, OPIN, ipin, side));
VTR_ASSERT(true == rr_graph.valid_node_id(inode));
//Initially left unconnected //Initially left unconnected
rr_graph.set_node_type(inode, OPIN);
rr_graph.set_node_cost_index(inode, OPIN_COST_INDEX); rr_graph.set_node_cost_index(inode, OPIN_COST_INDEX);
} }
@ -1731,7 +1747,7 @@ static void build_rr_chan(const int x_coord,
from_seg_details = chan_details_x[start][y_coord].data(); from_seg_details = chan_details_x[start][y_coord].data();
} }
RRNodeId node = rr_graph.find_node(x_coord, y_coord, chan_type, track); RRNodeId node = get_rr_graph_node_index(L_rr_node_indices, x_coord, y_coord, chan_type, track);
if (node == RRNodeId::INVALID()) { if (node == RRNodeId::INVALID()) {
continue; continue;
@ -1740,7 +1756,7 @@ static void build_rr_chan(const int x_coord,
/* Add the edges from this track to all it's connected pins into the list */ /* Add the edges from this track to all it's connected pins into the list */
int num_edges = 0; int num_edges = 0;
num_edges += get_track_to_pins(start, chan_coord, track, tracks_per_chan, node, rr_edges_to_create, num_edges += get_track_to_pins(start, chan_coord, track, tracks_per_chan, node, rr_edges_to_create,
rr_graph, track_to_pin_lookup, seg_details, chan_type, seg_dimension, L_rr_node_indices, rr_graph, track_to_pin_lookup, seg_details, chan_type, seg_dimension,
wire_to_ipin_switch, directionality); wire_to_ipin_switch, directionality);
/* get edges going from the current track into channel segments which are perpendicular to it */ /* get edges going from the current track into channel segments which are perpendicular to it */
@ -1758,7 +1774,7 @@ static void build_rr_chan(const int x_coord,
Fs_per_side, sblock_pattern, node, rr_edges_to_create, Fs_per_side, sblock_pattern, node, rr_edges_to_create,
from_seg_details, to_seg_details, opposite_chan_details, from_seg_details, to_seg_details, opposite_chan_details,
directionality, directionality,
rr_graph, L_rr_node_indices, rr_graph,
switch_block_conn, sb_conn_map); switch_block_conn, sb_conn_map);
} }
} }
@ -1776,7 +1792,7 @@ static void build_rr_chan(const int x_coord,
Fs_per_side, sblock_pattern, node, rr_edges_to_create, Fs_per_side, sblock_pattern, node, rr_edges_to_create,
from_seg_details, to_seg_details, opposite_chan_details, from_seg_details, to_seg_details, opposite_chan_details,
directionality, directionality,
rr_graph, L_rr_node_indices, rr_graph,
switch_block_conn, sb_conn_map); switch_block_conn, sb_conn_map);
} }
} }
@ -1806,13 +1822,14 @@ static void build_rr_chan(const int x_coord,
Fs_per_side, sblock_pattern, node, rr_edges_to_create, Fs_per_side, sblock_pattern, node, rr_edges_to_create,
from_seg_details, to_seg_details, from_chan_details, from_seg_details, to_seg_details, from_chan_details,
directionality, directionality,
rr_graph, L_rr_node_indices, rr_graph,
switch_block_conn, sb_conn_map); switch_block_conn, sb_conn_map);
} }
} }
} }
/* Edge arrays have now been built up. Do everything else. */ /* Edge arrays have now been built up. Do everything else. */
rr_graph.set_node_type(node, chan_type); /* GLOBAL routing handled elsewhere */
rr_graph.set_node_cost_index(node, cost_index_offset + seg_details[track].index()); rr_graph.set_node_cost_index(node, cost_index_offset + seg_details[track].index());
rr_graph.set_node_capacity(node, 1); /* GLOBAL routing handled elsewhere */ rr_graph.set_node_capacity(node, 1); /* GLOBAL routing handled elsewhere */
@ -1869,7 +1886,7 @@ void alloc_and_load_edges(RRGraph& rr_graph,
//Note that we do this in bulk instead of via add_edge() to reduce //Note that we do this in bulk instead of via add_edge() to reduce
//memory fragmentation //memory fragmentation
rr_graph.reserve_edges(edge_count + rr_graph.edges().size()); //rr_graph.reserve_edges(edge_count + rr_graph.edges().size());
for (auto itr = edge_range.first; itr != edge_range.second; ++itr) { for (auto itr = edge_range.first; itr != edge_range.second; ++itr) {
VTR_ASSERT(itr->from_node == inode); VTR_ASSERT(itr->from_node == inode);
@ -2702,12 +2719,8 @@ static void build_unidir_rr_opins(const int i, const int j,
continue; continue;
} }
RRNodeId opin_node_index = rr_graph.find_node(i, j, OPIN, pin_index, side); RRNodeId opin_node_index = get_rr_graph_node_index(L_rr_node_indices, i, j, OPIN, pin_index, side);
//if (false == rr_graph.valid_node_id(opin_node_index)) continue; //No valid from node if (false == rr_graph.valid_node_id(opin_node_index)) continue; //No valid from node
if (1 == type->pinloc[width_offset][height_offset][side][pin_index]) {
VTR_ASSERT(true == rr_graph.valid_node_id(opin_node_index));
}
for (int iseg = 0; iseg < num_seg_types; iseg++) { for (int iseg = 0; iseg < num_seg_types; iseg++) {
/* get Fc for this segment type */ /* get Fc for this segment type */
@ -2760,7 +2773,7 @@ static void build_unidir_rr_opins(const int i, const int j,
opin_node_index, opin_node_index,
rr_edges_to_create, rr_edges_to_create,
Fc_ofs, max_len, max_chan_width, Fc_ofs, max_len, max_chan_width,
rr_graph, &clipped); L_rr_node_indices, &clipped);
if (clipped) { if (clipped) {
*Fc_clipped = true; *Fc_clipped = true;
} }
@ -3007,7 +3020,7 @@ static int get_opin_direct_connections(int x,
} }
} else { } else {
//No side specified, get all candidates //No side specified, get all candidates
inodes = find_rr_graph_nodes(rr_graph, x + directs[i].x_offset, y + directs[i].y_offset, inodes = get_rr_graph_node_indices(L_rr_node_indices, x + directs[i].x_offset, y + directs[i].y_offset,
IPIN, ipin); IPIN, ipin);
} }

View File

@ -31,14 +31,15 @@ static void load_chan_rr_indices(const int max_chan_width,
const int num_chans, const int num_chans,
const t_rr_type type, const t_rr_type type,
const t_chan_details& chan_details, const t_chan_details& chan_details,
RRGraph& rr_graph, t_rr_node_indices& indices,
int* index); int* index);
static void load_block_rr_indices(const DeviceGrid& grid, static void load_block_rr_indices(const DeviceGrid& grid,
RRGraph& rr_graph, t_rr_node_indices& indices,
int* index); int* index);
static int get_bidir_track_to_chan_seg(const std::vector<int> conn_tracks, static int get_bidir_track_to_chan_seg(const std::vector<int> conn_tracks,
const t_rr_node_indices& L_rr_node_indices,
const RRGraph& rr_graph, const RRGraph& rr_graph,
const int to_chan, const int to_chan,
const int to_seg, const int to_seg,
@ -64,6 +65,7 @@ static int get_unidir_track_to_chan_seg(const int from_track,
const int Fs_per_side, const int Fs_per_side,
t_sblock_pattern& sblock_pattern, t_sblock_pattern& sblock_pattern,
const int switch_override, const int switch_override,
const t_rr_node_indices& L_rr_node_indices,
const RRGraph& rr_graph, const RRGraph& rr_graph,
const t_chan_seg_details* seg_details, const t_chan_seg_details* seg_details,
bool* Fs_clipped, bool* Fs_clipped,
@ -77,6 +79,7 @@ static int get_track_to_chan_seg(const int from_track,
const e_side from_side, const e_side from_side,
const e_side to_side, const e_side to_side,
const int swtich_override, const int swtich_override,
const t_rr_node_indices& L_rr_node_indices,
const RRGraph& rr_graph, const RRGraph& rr_graph,
t_sb_connection_map* sb_conn_map, t_sb_connection_map* sb_conn_map,
const RRNodeId& from_rr_node, const RRNodeId& from_rr_node,
@ -667,7 +670,7 @@ int get_bidir_opin_connections(const int i,
const RRNodeId& from_rr_node, const RRNodeId& from_rr_node,
t_rr_edge_info_set& rr_edges_to_create, t_rr_edge_info_set& rr_edges_to_create,
const t_pin_to_track_lookup& opin_to_track_map, const t_pin_to_track_lookup& opin_to_track_map,
const RRGraph& rr_graph, const t_rr_node_indices& L_rr_node_indices,
const t_chan_details& chan_details_x, const t_chan_details& chan_details_x,
const t_chan_details& chan_details_y) { const t_chan_details& chan_details_y) {
int num_conn, tr_i, tr_j, chan, seg; int num_conn, tr_i, tr_j, chan, seg;
@ -731,7 +734,7 @@ int get_bidir_opin_connections(const int i,
/* Only connect to wire if there is a CB */ /* Only connect to wire if there is a CB */
if (is_cblock(chan, seg, to_track, seg_details)) { if (is_cblock(chan, seg, to_track, seg_details)) {
to_switch = seg_details[to_track].arch_wire_switch(); to_switch = seg_details[to_track].arch_wire_switch();
to_node = rr_graph.find_node(tr_i, tr_j, to_type, to_track); to_node = RRNodeId(get_rr_node_index(L_rr_node_indices, tr_i, tr_j, to_type, to_track));
if (to_node == RRNodeId::INVALID()) { if (to_node == RRNodeId::INVALID()) {
continue; continue;
@ -757,7 +760,7 @@ int get_unidir_opin_connections(const int chan,
vtr::NdMatrix<int, 3>& Fc_ofs, vtr::NdMatrix<int, 3>& Fc_ofs,
const int max_len, const int max_len,
const int max_chan_width, const int max_chan_width,
const RRGraph& rr_graph, const t_rr_node_indices& L_rr_node_indices,
bool* Fc_clipped) { bool* Fc_clipped) {
/* Gets a linked list of Fc nodes of specified seg_type_index to connect /* Gets a linked list of Fc nodes of specified seg_type_index to connect
* to in given chan seg. Fc_ofs is used for the opin staggering pattern. */ * to in given chan seg. Fc_ofs is used for the opin staggering pattern. */
@ -809,8 +812,8 @@ int get_unidir_opin_connections(const int chan,
dec_track = dec_muxes[dec_mux]; dec_track = dec_muxes[dec_mux];
/* Figure the inodes of those muxes */ /* Figure the inodes of those muxes */
inc_inode_index = rr_graph.find_node(x, y, chan_type, inc_track); inc_inode_index = get_rr_graph_node_index(L_rr_node_indices, x, y, chan_type, inc_track);
dec_inode_index = rr_graph.find_node(x, y, chan_type, dec_track); dec_inode_index = get_rr_graph_node_index(L_rr_node_indices, x, y, chan_type, dec_track);
if (inc_inode_index == RRNodeId::INVALID() || dec_inode_index == RRNodeId::INVALID()) { if (inc_inode_index == RRNodeId::INVALID() || dec_inode_index == RRNodeId::INVALID()) {
continue; continue;
@ -1059,8 +1062,20 @@ static void load_chan_rr_indices(const int max_chan_width,
const int num_chans, const int num_chans,
const t_rr_type type, const t_rr_type type,
const t_chan_details& chan_details, const t_chan_details& chan_details,
RRGraph& rr_graph, t_rr_node_indices& indices,
int* index) { int* index) {
VTR_ASSERT(indices[type].size() == size_t(num_chans));
for (int chan = 0; chan < num_chans - 1; ++chan) {
VTR_ASSERT(indices[type][chan].size() == size_t(chan_len));
for (int seg = 1; seg < chan_len - 1; ++seg) {
VTR_ASSERT(indices[type][chan][seg].size() == NUM_SIDES);
/* Alloc the track inode lookup list */
//Since channels have no side, we just use the first side
indices[type][chan][seg][0].resize(max_chan_width, OPEN);
}
}
for (int chan = 0; chan < num_chans - 1; ++chan) { for (int chan = 0; chan < num_chans - 1; ++chan) {
for (int seg = 1; seg < chan_len - 1; ++seg) { for (int seg = 1; seg < chan_len - 1; ++seg) {
@ -1069,34 +1084,32 @@ static void load_chan_rr_indices(const int max_chan_width,
int y = (type == CHANX ? chan : seg); int y = (type == CHANX ? chan : seg);
const t_chan_seg_details* seg_details = chan_details[x][y].data(); const t_chan_seg_details* seg_details = chan_details[x][y].data();
for (int track = 0; track < num_chans - 1; ++track) { for (unsigned track = 0; track < indices[type][chan][seg][0].size(); ++track) {
if (seg_details[track].length() <= 0) if (seg_details[track].length() <= 0)
continue; continue;
int start = get_seg_start(seg_details, track, chan, seg); int start = get_seg_start(seg_details, track, chan, seg);
/* We give a fake coordinator here, to ease the downstream builder */ /* If the start of the wire doesn't have a inode,
short xlow = chan; * assign one to it. */
short ylow = start; int inode = indices[type][chan][start][0][track];
if (CHANX == type) { if (OPEN == inode) {
std::swap(xlow, ylow); inode = *index;
} ++(*index);
RRNodeId node = rr_graph.find_node(xlow, ylow, type, track);
if (false == rr_graph.valid_node_id(node)) {
RRNodeId new_node = rr_graph.create_node(type); indices[type][chan][start][0][track] = inode;
rr_graph.set_node_bounding_box(new_node, vtr::Rect<short>(xlow, ylow, xlow, ylow));
rr_graph.set_node_track_num(new_node, track);
(*index)++;
} }
/* Assign inode of start of wire to current position */
indices[type][chan][seg][0][track] = inode;
} }
} }
} }
} }
static void load_block_rr_indices(const DeviceGrid& grid, static void load_block_rr_indices(const DeviceGrid& grid,
RRGraph& rr_graph, t_rr_node_indices& indices,
int* index) { int* index) {
//Walk through the grid assigning indices to SOURCE/SINK IPIN/OPIN //Walk through the grid assigning indices to SOURCE/SINK IPIN/OPIN
for (size_t x = 0; x < grid.width(); x++) { for (size_t x = 0; x < grid.width(); x++) {
@ -1110,14 +1123,12 @@ static void load_block_rr_indices(const DeviceGrid& grid,
for (int iclass = 0; iclass < type->num_class; ++iclass) { for (int iclass = 0; iclass < type->num_class; ++iclass) {
auto class_type = type->class_inf[iclass].type; auto class_type = type->class_inf[iclass].type;
if (class_type == DRIVER) { if (class_type == DRIVER) {
RRNodeId node = rr_graph.create_node(SOURCE); indices[SOURCE][x][y][0].push_back(*index);
rr_graph.set_node_bounding_box(node, vtr::Rect<short>(x, y, x, y)); indices[SINK][x][y][0].push_back(OPEN);
rr_graph.set_node_class_num(node, iclass);
} else { } else {
VTR_ASSERT(class_type == RECEIVER); VTR_ASSERT(class_type == RECEIVER);
RRNodeId node = rr_graph.create_node(SINK); indices[SINK][x][y][0].push_back(*index);
rr_graph.set_node_bounding_box(node, vtr::Rect<short>(x, y, x, y)); indices[SOURCE][x][y][0].push_back(OPEN);
rr_graph.set_node_class_num(node, iclass);
} }
++(*index); ++(*index);
} }
@ -1134,23 +1145,34 @@ static void load_block_rr_indices(const DeviceGrid& grid,
auto class_type = type->class_inf[iclass].type; auto class_type = type->class_inf[iclass].type;
if (class_type == DRIVER) { if (class_type == DRIVER) {
RRNodeId node = rr_graph.create_node(OPIN); indices[OPIN][x_tile][y_tile][side].push_back(*index);
rr_graph.set_node_bounding_box(node, vtr::Rect<short>(x_tile, y_tile, x_tile, y_tile)); indices[IPIN][x_tile][y_tile][side].push_back(OPEN);
rr_graph.set_node_pin_num(node, ipin);
rr_graph.set_node_side(node, side);
} else { } else {
VTR_ASSERT(class_type == RECEIVER); VTR_ASSERT(class_type == RECEIVER);
RRNodeId node = rr_graph.create_node(IPIN); indices[IPIN][x_tile][y_tile][side].push_back(*index);
rr_graph.set_node_bounding_box(node, vtr::Rect<short>(x_tile, y_tile, x_tile, y_tile)); indices[OPIN][x_tile][y_tile][side].push_back(OPEN);
rr_graph.set_node_pin_num(node, ipin);
rr_graph.set_node_side(node, side);
} }
++(*index); ++(*index);
} else {
indices[IPIN][x_tile][y_tile][side].push_back(OPEN);
indices[OPIN][x_tile][y_tile][side].push_back(OPEN);
} }
} }
} }
} }
} }
//Sanity check
for (int width_offset = 0; width_offset < type->width; ++width_offset) {
int x_tile = x + width_offset;
for (int height_offset = 0; height_offset < type->height; ++height_offset) {
int y_tile = y + height_offset;
for (e_side side : SIDES) {
VTR_ASSERT(indices[IPIN][x_tile][y_tile][side].size() == size_t(type->num_pins));
VTR_ASSERT(indices[OPIN][x_tile][y_tile][side].size() == size_t(type->num_pins));
}
}
}
} }
} }
} }
@ -1169,46 +1191,56 @@ static void load_block_rr_indices(const DeviceGrid& grid,
int root_x = x - width_offset; int root_x = x - width_offset;
int root_y = y - height_offset; int root_y = y - height_offset;
//Process each block from it's root location indices[SOURCE][x][y] = indices[SOURCE][root_x][root_y];
auto type = grid[x][y].type; indices[SINK][x][y] = indices[SINK][root_x][root_y];
//Assign indicies for SINKs and SOURCEs
// Note that SINKS/SOURCES have no side, so we always use side 0
for (int iclass = 0; iclass < type->num_class; ++iclass) {
auto class_type = type->class_inf[iclass].type;
if (class_type == DRIVER) {
RRNodeId node = rr_graph.find_node(root_x, root_y, SOURCE, iclass);
/* Update the internal look-up so that we can find the SOURCE/SINK node using their offset coordinates */
rr_graph.set_node_bounding_box(node, vtr::Rect<short>(root_x, root_y, x, y));
} else {
VTR_ASSERT(class_type == RECEIVER);
RRNodeId node = rr_graph.find_node(root_x, root_y, SINK, iclass);
/* Update the internal look-up so that we can find the SOURCE/SINK node using their offset coordinates */
rr_graph.set_node_bounding_box(node, vtr::Rect<short>(root_x, root_y, x, y));
}
}
} }
} }
} }
} }
RRGraph alloc_and_load_rr_node_indices(const int max_chan_width, t_rr_node_indices alloc_and_load_rr_node_indices(const int max_chan_width,
const DeviceGrid& grid, const DeviceGrid& grid,
int* index, int* index,
const t_chan_details& chan_details_x, const t_chan_details& chan_details_x,
const t_chan_details& chan_details_y) { const t_chan_details& chan_details_y) {
/* Allocates and loads all the nodes in a RRGraph object */ /* Allocates and loads all the structures needed for fast lookups of the *
RRGraph rr_graph; * index of an rr_node. rr_node_indices is a matrix containing the index *
* of the *first* rr_node at a given (i,j) location. */
t_rr_node_indices indices;
/* Alloc the lookup table */
indices.resize(NUM_RR_TYPES);
for (t_rr_type rr_type : RR_TYPES) {
if (rr_type == CHANX) {
indices[rr_type].resize(grid.height());
for (size_t y = 0; y < grid.height(); ++y) {
indices[rr_type][y].resize(grid.width());
for (size_t x = 0; x < grid.width(); ++x) {
indices[rr_type][y][x].resize(NUM_SIDES);
}
}
} else {
indices[rr_type].resize(grid.width());
for (size_t x = 0; x < grid.width(); ++x) {
indices[rr_type][x].resize(grid.height());
for (size_t y = 0; y < grid.height(); ++y) {
indices[rr_type][x][y].resize(NUM_SIDES);
}
}
}
}
/* Assign indices for block nodes */ /* Assign indices for block nodes */
load_block_rr_indices(grid, rr_graph, index); load_block_rr_indices(grid, indices, index);
/* Load the data for x and y channels */ /* Load the data for x and y channels */
load_chan_rr_indices(max_chan_width, grid.width(), grid.height(), load_chan_rr_indices(max_chan_width, grid.width(), grid.height(),
CHANX, chan_details_x, rr_graph, index); CHANX, chan_details_x, indices, index);
load_chan_rr_indices(max_chan_width, grid.height(), grid.width(), load_chan_rr_indices(max_chan_width, grid.height(), grid.width(),
CHANY, chan_details_y, rr_graph, index); CHANY, chan_details_y, indices, index);
return rr_graph; return indices;
} }
std::vector<int> get_rr_node_chan_wires_at_location(const t_rr_node_indices& L_rr_node_indices, std::vector<int> get_rr_node_chan_wires_at_location(const t_rr_node_indices& L_rr_node_indices,
@ -1225,6 +1257,44 @@ std::vector<int> get_rr_node_chan_wires_at_location(const t_rr_node_indices& L_r
return L_rr_node_indices[rr_type][x][y][SIDES[0]]; return L_rr_node_indices[rr_type][x][y][SIDES[0]];
} }
/********************************************************************
* A wrapper for the old function to return a vector of RRNodeId
*******************************************************************/
std::vector<RRNodeId> get_rr_graph_node_indices(const t_rr_node_indices& L_rr_node_indices,
int x,
int y,
t_rr_type rr_type,
int ptc) {
/*
* Like get_rr_node_index() but returns all matching nodes,
* rather than just the first. This is particularly useful for getting all instances
* of a specific IPIN/OPIN at a specific gird tile (x,y) location.
*/
std::vector<RRNodeId> indices;
if (rr_type == IPIN || rr_type == OPIN) {
//For pins we need to look at all the sides of the current grid tile
for (e_side side : SIDES) {
int rr_node_index = get_rr_node_index(L_rr_node_indices, x, y, rr_type, ptc, side);
if (rr_node_index >= 0) {
indices.push_back(RRNodeId(rr_node_index));
}
}
} else {
//Sides do not effect non-pins so there should only be one per ptc
int rr_node_index = get_rr_node_index(L_rr_node_indices, x, y, rr_type, ptc);
if (rr_node_index != OPEN) {
indices.push_back(RRNodeId(rr_node_index));
}
}
return indices;
}
std::vector<int> get_rr_node_indices(const t_rr_node_indices& L_rr_node_indices, std::vector<int> get_rr_node_indices(const t_rr_node_indices& L_rr_node_indices,
int x, int x,
int y, int y,
@ -1259,6 +1329,15 @@ std::vector<int> get_rr_node_indices(const t_rr_node_indices& L_rr_node_indices,
return indices; return indices;
} }
RRNodeId get_rr_graph_node_index(const t_rr_node_indices& L_rr_node_indices,
int x,
int y,
t_rr_type rr_type,
int ptc,
e_side side) {
return RRNodeId(get_rr_node_index(L_rr_node_indices, x, y, rr_type, ptc, side));
}
int get_rr_node_index(const t_rr_node_indices& L_rr_node_indices, int get_rr_node_index(const t_rr_node_indices& L_rr_node_indices,
int x, int x,
int y, int y,
@ -1398,6 +1477,7 @@ int get_track_to_pins(int seg,
int tracks_per_chan, int tracks_per_chan,
const RRNodeId& from_rr_node, const RRNodeId& from_rr_node,
t_rr_edge_info_set& rr_edges_to_create, t_rr_edge_info_set& rr_edges_to_create,
const t_rr_node_indices& L_rr_node_indices,
const RRGraph& rr_graph, const RRGraph& rr_graph,
const t_track_to_pin_lookup& track_to_pin_lookup, const t_track_to_pin_lookup& track_to_pin_lookup,
const t_chan_seg_details* seg_details, const t_chan_seg_details* seg_details,
@ -1456,7 +1536,7 @@ int get_track_to_pins(int seg,
/* Check there is a connection and Fc map isn't wrong */ /* Check there is a connection and Fc map isn't wrong */
/*int to_node = get_rr_node_index(L_rr_node_indices, x + width_offset, y + height_offset, IPIN, ipin, side);*/ /*int to_node = get_rr_node_index(L_rr_node_indices, x + width_offset, y + height_offset, IPIN, ipin, side);*/
RRNodeId to_node = rr_graph.find_node(x, y, IPIN, ipin, side); RRNodeId to_node = RRNodeId(get_rr_node_index(L_rr_node_indices, x, y, IPIN, ipin, side));
if (rr_graph.valid_node_id(to_node)) { if (rr_graph.valid_node_id(to_node)) {
rr_edges_to_create.emplace_back(from_rr_node, to_node, wire_to_ipin_switch); rr_edges_to_create.emplace_back(from_rr_node, to_node, wire_to_ipin_switch);
++num_conn; ++num_conn;
@ -1503,6 +1583,7 @@ int get_track_to_tracks(const int from_chan,
const t_chan_seg_details* to_seg_details, const t_chan_seg_details* to_seg_details,
const t_chan_details& to_chan_details, const t_chan_details& to_chan_details,
const enum e_directionality directionality, const enum e_directionality directionality,
const t_rr_node_indices& L_rr_node_indices,
const RRGraph& rr_graph, const RRGraph& rr_graph,
const vtr::NdMatrix<std::vector<int>, 3>& switch_block_conn, const vtr::NdMatrix<std::vector<int>, 3>& switch_block_conn,
t_sb_connection_map* sb_conn_map) { t_sb_connection_map* sb_conn_map) {
@ -1636,7 +1717,7 @@ int get_track_to_tracks(const int from_chan,
num_conn += get_track_to_chan_seg(from_track, to_chan, to_seg, num_conn += get_track_to_chan_seg(from_track, to_chan, to_seg,
to_type, from_side_a, to_side, to_type, from_side_a, to_side,
switch_override, switch_override,
rr_graph, L_rr_node_indices, rr_graph,
sb_conn_map, from_rr_node, rr_edges_to_create); sb_conn_map, from_rr_node, rr_edges_to_create);
} }
} else { } else {
@ -1645,7 +1726,7 @@ int get_track_to_tracks(const int from_chan,
* switchbox, so we follow through regardless of whether the current segment has an SB */ * switchbox, so we follow through regardless of whether the current segment has an SB */
conn_tracks = switch_block_conn[from_side_a][to_side][from_track]; conn_tracks = switch_block_conn[from_side_a][to_side][from_track];
num_conn += get_bidir_track_to_chan_seg(conn_tracks, num_conn += get_bidir_track_to_chan_seg(conn_tracks,
rr_graph, to_chan, to_seg, to_sb, to_type, L_rr_node_indices, rr_graph, to_chan, to_seg, to_sb, to_type,
to_seg_details, from_is_sblock, from_switch, to_seg_details, from_is_sblock, from_switch,
switch_override, switch_override,
directionality, from_rr_node, rr_edges_to_create); directionality, from_rr_node, rr_edges_to_create);
@ -1660,7 +1741,7 @@ int get_track_to_tracks(const int from_chan,
from_side_a, to_side, Fs_per_side, from_side_a, to_side, Fs_per_side,
sblock_pattern, sblock_pattern,
switch_override, switch_override,
rr_graph, to_seg_details, L_rr_node_indices, rr_graph, to_seg_details,
&Fs_clipped, from_rr_node, rr_edges_to_create); &Fs_clipped, from_rr_node, rr_edges_to_create);
} }
} }
@ -1675,7 +1756,7 @@ int get_track_to_tracks(const int from_chan,
num_conn += get_track_to_chan_seg(from_track, to_chan, to_seg, num_conn += get_track_to_chan_seg(from_track, to_chan, to_seg,
to_type, from_side_b, to_side, to_type, from_side_b, to_side,
switch_override, switch_override,
rr_graph, L_rr_node_indices, rr_graph,
sb_conn_map, from_rr_node, rr_edges_to_create); sb_conn_map, from_rr_node, rr_edges_to_create);
} }
} else { } else {
@ -1684,7 +1765,7 @@ int get_track_to_tracks(const int from_chan,
* switchbox, so we follow through regardless of whether the current segment has an SB */ * switchbox, so we follow through regardless of whether the current segment has an SB */
conn_tracks = switch_block_conn[from_side_b][to_side][from_track]; conn_tracks = switch_block_conn[from_side_b][to_side][from_track];
num_conn += get_bidir_track_to_chan_seg(conn_tracks, num_conn += get_bidir_track_to_chan_seg(conn_tracks,
rr_graph, to_chan, to_seg, to_sb, to_type, L_rr_node_indices, rr_graph, to_chan, to_seg, to_sb, to_type,
to_seg_details, from_is_sblock, from_switch, to_seg_details, from_is_sblock, from_switch,
switch_override, switch_override,
directionality, from_rr_node, rr_edges_to_create); directionality, from_rr_node, rr_edges_to_create);
@ -1700,7 +1781,7 @@ int get_track_to_tracks(const int from_chan,
from_side_b, to_side, Fs_per_side, from_side_b, to_side, Fs_per_side,
sblock_pattern, sblock_pattern,
switch_override, switch_override,
rr_graph, to_seg_details, L_rr_node_indices, rr_graph, to_seg_details,
&Fs_clipped, from_rr_node, rr_edges_to_create); &Fs_clipped, from_rr_node, rr_edges_to_create);
} }
} }
@ -1712,6 +1793,7 @@ int get_track_to_tracks(const int from_chan,
} }
static int get_bidir_track_to_chan_seg(const std::vector<int> conn_tracks, static int get_bidir_track_to_chan_seg(const std::vector<int> conn_tracks,
const t_rr_node_indices& L_rr_node_indices,
const RRGraph& rr_graph, const RRGraph& rr_graph,
const int to_chan, const int to_chan,
const int to_seg, const int to_seg,
@ -1744,9 +1826,9 @@ static int get_bidir_track_to_chan_seg(const std::vector<int> conn_tracks,
num_conn = 0; num_conn = 0;
for (iconn = 0; iconn < conn_tracks.size(); ++iconn) { for (iconn = 0; iconn < conn_tracks.size(); ++iconn) {
to_track = conn_tracks[iconn]; to_track = conn_tracks[iconn];
to_node = rr_graph.find_node(to_x, to_y, to_type, to_track); to_node = get_rr_graph_node_index(L_rr_node_indices, to_x, to_y, to_type, to_track);
if (to_node == RRNodeId::INVALID()) { if (false == rr_graph.valid_node_id(to_node)) {
continue; continue;
} }
@ -1787,6 +1869,7 @@ static int get_track_to_chan_seg(const int from_wire,
const e_side from_side, const e_side from_side,
const e_side to_side, const e_side to_side,
const int switch_override, const int switch_override,
const t_rr_node_indices& L_rr_node_indices,
const RRGraph& rr_graph, const RRGraph& rr_graph,
t_sb_connection_map* sb_conn_map, t_sb_connection_map* sb_conn_map,
const RRNodeId& from_rr_node, const RRNodeId& from_rr_node,
@ -1823,9 +1906,9 @@ static int get_track_to_chan_seg(const int from_wire,
if (conn_vector.at(iconn).from_wire != from_wire) continue; if (conn_vector.at(iconn).from_wire != from_wire) continue;
int to_wire = conn_vector.at(iconn).to_wire; int to_wire = conn_vector.at(iconn).to_wire;
RRNodeId to_node = rr_graph.find_node(to_x, to_y, to_chan_type, to_wire); RRNodeId to_node = RRNodeId(get_rr_node_index(L_rr_node_indices, to_x, to_y, to_chan_type, to_wire));
if (to_node == RRNodeId::INVALID()) { if (false == rr_graph.valid_node_id(to_node)) {
continue; continue;
} }
@ -1866,6 +1949,7 @@ static int get_unidir_track_to_chan_seg(const int from_track,
const int Fs_per_side, const int Fs_per_side,
t_sblock_pattern& sblock_pattern, t_sblock_pattern& sblock_pattern,
const int switch_override, const int switch_override,
const t_rr_node_indices& L_rr_node_indices,
const RRGraph& rr_graph, const RRGraph& rr_graph,
const t_chan_seg_details* seg_details, const t_chan_seg_details* seg_details,
bool* Fs_clipped, bool* Fs_clipped,
@ -1923,9 +2007,9 @@ static int get_unidir_track_to_chan_seg(const int from_track,
sblock_pattern[sb_x][sb_y][from_side][to_side][from_track][j + 1] = to_track; sblock_pattern[sb_x][sb_y][from_side][to_side][from_track][j + 1] = to_track;
} }
RRNodeId to_node = rr_graph.find_node(to_x, to_y, to_type, to_track); RRNodeId to_node = get_rr_graph_node_index(L_rr_node_indices, to_x, to_y, to_type, to_track);
if (to_node == RRNodeId::INVALID()) { if (false == rr_graph.valid_node_id(to_node)) {
continue; continue;
} }

View File

@ -47,7 +47,7 @@ typedef vtr::NdMatrix<short, 6> t_sblock_pattern;
/******************* Subroutines exported by rr_graph2.c *********************/ /******************* Subroutines exported by rr_graph2.c *********************/
RRGraph alloc_and_load_rr_node_indices(const int max_chan_width, t_rr_node_indices alloc_and_load_rr_node_indices(const int max_chan_width,
const DeviceGrid& grid, const DeviceGrid& grid,
int* index, int* index,
const t_chan_details& chan_details_x, const t_chan_details& chan_details_x,
@ -59,7 +59,14 @@ int get_rr_node_index(int x,
int ptc, int ptc,
const t_rr_node_indices& L_rr_node_indices); const t_rr_node_indices& L_rr_node_indices);
//Returns all the rr nodes associated with the specified coordinate (i.e. accross sides) //Returns all the rr nodes associated with the specified coordinate (i.e. accross sides)
std::vector<RRNodeId> get_rr_graph_node_indices(const t_rr_node_indices& L_rr_node_indices,
int x,
int y,
t_rr_type rr_type,
int ptc);
std::vector<int> get_rr_node_indices(const t_rr_node_indices& L_rr_node_indices, std::vector<int> get_rr_node_indices(const t_rr_node_indices& L_rr_node_indices,
int x, int x,
int y, int y,
@ -74,6 +81,13 @@ std::vector<int> get_rr_node_chan_wires_at_location(const t_rr_node_indices& L_r
//Return the first rr node of the specified type and coordinates //Return the first rr node of the specified type and coordinates
// For non-IPIN/OPIN types 'side' is ignored // For non-IPIN/OPIN types 'side' is ignored
RRNodeId get_rr_graph_node_index(const t_rr_node_indices& L_rr_node_indices,
int x,
int y,
t_rr_type rr_type,
int ptc,
e_side side = NUM_SIDES);
int get_rr_node_index(const t_rr_node_indices& L_rr_node_indices, int get_rr_node_index(const t_rr_node_indices& L_rr_node_indices,
int x, int x,
int y, int y,
@ -156,7 +170,7 @@ int get_bidir_opin_connections(const int i,
const RRNodeId& from_rr_node, const RRNodeId& from_rr_node,
t_rr_edge_info_set& rr_edges_to_create, t_rr_edge_info_set& rr_edges_to_create,
const t_pin_to_track_lookup& opin_to_track_map, const t_pin_to_track_lookup& opin_to_track_map,
const RRGraph& rr_graph, const t_rr_node_indices& L_rr_node_indices,
const t_chan_details& chan_details_x, const t_chan_details& chan_details_x,
const t_chan_details& chan_details_y); const t_chan_details& chan_details_y);
@ -171,7 +185,7 @@ int get_unidir_opin_connections(const int chan,
vtr::NdMatrix<int, 3>& Fc_ofs, vtr::NdMatrix<int, 3>& Fc_ofs,
const int max_len, const int max_len,
const int max_chan_width, const int max_chan_width,
const RRGraph& rr_graph, const t_rr_node_indices& L_rr_node_indices,
bool* Fc_clipped); bool* Fc_clipped);
int get_track_to_pins(int seg, int get_track_to_pins(int seg,
@ -180,6 +194,7 @@ int get_track_to_pins(int seg,
int tracks_per_chan, int tracks_per_chan,
const RRNodeId& from_rr_node, const RRNodeId& from_rr_node,
t_rr_edge_info_set& rr_edges_to_create, t_rr_edge_info_set& rr_edges_to_create,
const t_rr_node_indices& L_rr_node_indices,
const RRGraph& rr_graph, const RRGraph& rr_graph,
const t_track_to_pin_lookup& track_to_pin_lookup, const t_track_to_pin_lookup& track_to_pin_lookup,
const t_chan_seg_details* seg_details, const t_chan_seg_details* seg_details,
@ -205,6 +220,7 @@ int get_track_to_tracks(const int from_chan,
const t_chan_seg_details* to_seg_details, const t_chan_seg_details* to_seg_details,
const t_chan_details& to_chan_details, const t_chan_details& to_chan_details,
const enum e_directionality directionality, const enum e_directionality directionality,
const t_rr_node_indices& L_rr_node_indices,
const RRGraph& rr_graph, const RRGraph& rr_graph,
const vtr::NdMatrix<std::vector<int>, 3>& switch_block_conn, const vtr::NdMatrix<std::vector<int>, 3>& switch_block_conn,
t_sb_connection_map* sb_conn_map); t_sb_connection_map* sb_conn_map);