Skip to content

Commit 425411d

Browse files
committed
Add requested documentation
1 parent 0a58008 commit 425411d

File tree

6 files changed

+49
-11
lines changed

6 files changed

+49
-11
lines changed

vpr/src/base/read_options.cpp

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -164,8 +164,8 @@ struct ParseRouterAlgorithm {
164164
};
165165

166166
struct ParseNodeReorderAlgorithm {
167-
ConvertedValue<e_node_reorder_algorithm> from_str(std::string str) {
168-
ConvertedValue<e_node_reorder_algorithm> conv_value;
167+
ConvertedValue<e_rr_node_reorder_algorithm> from_str(std::string str) {
168+
ConvertedValue<e_rr_node_reorder_algorithm> conv_value;
169169
if (str == "none")
170170
conv_value.set_value(DONT_REORDER);
171171
else if (str == "degree_bfs")
@@ -174,13 +174,13 @@ struct ParseNodeReorderAlgorithm {
174174
conv_value.set_value(RANDOM_SHUFFLE);
175175
else {
176176
std::stringstream msg;
177-
msg << "Invalid conversion from '" << str << "' to e_node_reorder_algorithm (expected one of: " << argparse::join(default_choices(), ", ") << ")";
177+
msg << "Invalid conversion from '" << str << "' to e_rr_node_reorder_algorithm (expected one of: " << argparse::join(default_choices(), ", ") << ")";
178178
conv_value.set_error(msg.str());
179179
}
180180
return conv_value;
181181
}
182182

183-
ConvertedValue<std::string> to_str(e_node_reorder_algorithm val) {
183+
ConvertedValue<std::string> to_str(e_rr_node_reorder_algorithm val) {
184184
ConvertedValue<std::string> conv_value;
185185
if (val == DONT_REORDER)
186186
conv_value.set_value("none");
@@ -1932,7 +1932,7 @@ argparse::ArgumentParser create_arg_parser(std::string prog_name, t_options& arg
19321932
.default_value("off")
19331933
.show_in(argparse::ShowIn::HELP_ONLY);
19341934

1935-
route_grp.add_argument<e_node_reorder_algorithm, ParseNodeReorderAlgorithm>(args.reorder_rr_graph_nodes_algorithm, "--reorder_rr_graph_nodes_algorithm")
1935+
route_grp.add_argument<e_rr_node_reorder_algorithm, ParseNodeReorderAlgorithm>(args.reorder_rr_graph_nodes_algorithm, "--reorder_rr_graph_nodes_algorithm")
19361936
.help(
19371937
"Specifies the node reordering algorithm to use.\n"
19381938
" * none: don't reorder nodes\n"

vpr/src/base/read_options.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -150,7 +150,7 @@ struct t_options {
150150
argparse::ArgValue<e_check_route_option> check_route;
151151
argparse::ArgValue<size_t> max_logged_overused_rr_nodes;
152152
argparse::ArgValue<bool> generate_rr_node_overuse_report;
153-
argparse::ArgValue<e_node_reorder_algorithm> reorder_rr_graph_nodes_algorithm;
153+
argparse::ArgValue<e_rr_node_reorder_algorithm> reorder_rr_graph_nodes_algorithm;
154154
argparse::ArgValue<int> reorder_rr_graph_nodes_threshold;
155155
argparse::ArgValue<int> reorder_rr_graph_nodes_seed;
156156

vpr/src/base/vpr_types.h

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -977,7 +977,8 @@ enum e_router_algorithm {
977977
TIMING_DRIVEN,
978978
};
979979

980-
enum e_node_reorder_algorithm {
980+
// Node reordering algorithms for rr_nodes
981+
enum e_rr_node_reorder_algorithm {
981982
DONT_REORDER,
982983
DEGREE_BFS,
983984
RANDOM_SHUFFLE,
@@ -1035,9 +1036,6 @@ enum class e_incr_reroute_delay_ripup {
10351036
constexpr int NO_FIXED_CHANNEL_WIDTH = -1;
10361037

10371038
struct t_router_opts {
1038-
e_node_reorder_algorithm reorder_rr_graph_nodes_algorithm = DONT_REORDER;
1039-
int reorder_rr_graph_nodes_threshold = 0;
1040-
int reorder_rr_graph_nodes_seed = 1;
10411039
bool read_rr_edge_metadata = false;
10421040
bool do_check_rr_graph = true;
10431041
float first_iter_pres_fac;
@@ -1097,6 +1095,11 @@ struct t_router_opts {
10971095

10981096
size_t max_logged_overused_rr_nodes;
10991097
bool generate_rr_node_overuse_report;
1098+
1099+
// Options related to rr_node reordering, for testing and possible cache optimization
1100+
e_rr_node_reorder_algorithm reorder_rr_graph_nodes_algorithm = DONT_REORDER;
1101+
int reorder_rr_graph_nodes_threshold = 0;
1102+
int reorder_rr_graph_nodes_seed = 1;
11001103
};
11011104

11021105
struct t_analysis_opts {

vpr/src/route/rr_graph_storage.cpp

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -740,9 +740,24 @@ t_rr_graph_view t_rr_graph_storage::view() const {
740740
vtr::make_const_array_view_id(edge_switch_));
741741
}
742742

743+
// Given `order`, a vector mapping each RRNodeId to a new one (old -> new),
744+
// and `inverse_order`, its inverse (new -> old), update the t_rr_graph_storage
745+
// data structure to an isomorphic graph using the new RRNodeId's.
746+
//
747+
// Because the RRNodeId's affect the memory layout, this can be used to
748+
// optimize cache locality.
749+
//
750+
// Preconditions:
751+
// order[inverse_order[x]] == x
752+
// inverse_order[order[x]] == x
753+
// x != y <===> order[x] != order[y]
754+
//
755+
// NOTE: Re-ordering will invalidate any external references, so this
756+
// should generally be called before creating such references.
743757
void t_rr_graph_storage::reorder(const vtr::vector<RRNodeId, RRNodeId>& order,
744758
const vtr::vector<RRNodeId, RRNodeId>& inverse_order) {
745759
VTR_ASSERT_SAFE(validate());
760+
VTR_ASSERT(order.size() == inverse_order.size());
746761
{
747762
auto old_node_storage = node_storage_;
748763

vpr/src/route/rr_graph_storage.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -435,6 +435,12 @@ class t_rr_graph_storage {
435435
node_storage_.emplace_back();
436436
node_ptc_.emplace_back();
437437
}
438+
439+
// Given `order`, a vector mapping each RRNodeId to a new one (old -> new),
440+
// and `inverse_order`, its inverse (new -> old), update the t_rr_graph_storage
441+
// data structure to an isomorphic graph using the new RRNodeId's.
442+
// NOTE: Re-ordering will invalidate any external references, so this
443+
// should generally be called before creating such references.
438444
void reorder(const vtr::vector<RRNodeId, RRNodeId>& order,
439445
const vtr::vector<RRNodeId, RRNodeId>& inverse_order);
440446

vpr/src/route/rr_graph_util.cpp

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -81,6 +81,15 @@ int seg_index_of_sblock(int from_node, int to_node) {
8181
}
8282
}
8383

84+
// Reorder RRNodeId's using one of these algorithms:
85+
// - DONT_REORDER: The identity reordering (does nothing.)
86+
// - DEGREE_BFS: Order by degree primarily, and BFS traversal order secondarily.
87+
// - RANDOM_SHUFFLE: Shuffle using the specified seed. Great for testing.
88+
// The DEGREE_BFS algorithm was selected because it had the best performance of seven
89+
// existing algorithms here: https://github.com/SymbiFlow/vtr-rrgraph-reordering-tool
90+
// It might be worth further research, as the DEGREE_BFS algorithm is simple and
91+
// makes some arbitrary choices, such as the starting node.
92+
// Nonetheless, it does improve performance ~7% for the SymbiFlow Xilinx Artix 7 graph.
8493
void reorder_rr_graph_nodes(const t_router_opts& router_opts) {
8594
auto& device_ctx = g_vpr_ctx.mutable_device();
8695
auto& graph = device_ctx.rr_nodes;
@@ -97,11 +106,15 @@ void reorder_rr_graph_nodes(const t_router_opts& router_opts) {
97106
n = RRNodeId(cur_idx++);
98107
}
99108

109+
// This method works well. The intution is that highly connected nodes are enumerated first (together),
110+
// and since there will be a lot of nodes with the same degree, they are then ordered based on some
111+
// distance from the starting node.
100112
if (router_opts.reorder_rr_graph_nodes_algorithm == DEGREE_BFS) {
101113
vtr::vector<RRNodeId, size_t> bfs_idx(v_num);
102114
vtr::vector<RRNodeId, size_t> degree(v_num);
103115
std::queue<RRNodeId> que;
104116

117+
// Compute both degree (in + out) and an index based on the BFS traversal
105118
cur_idx = 0;
106119
for (size_t i = 0; i < v_num; ++i) {
107120
if (bfs_idx[RRNodeId(i)]) continue;
@@ -121,6 +134,7 @@ void reorder_rr_graph_nodes(const t_router_opts& router_opts) {
121134
}
122135
}
123136

137+
// Sort by degree primarily, and BFS order secondarily
124138
sort(src_order.begin(), src_order.end(),
125139
[&](auto a, auto b) -> bool {
126140
auto deg_a = degree[a];
@@ -138,7 +152,7 @@ void reorder_rr_graph_nodes(const t_router_opts& router_opts) {
138152

139153
graph.reorder(dest_order, src_order);
140154

141-
// update rr_node_indices
155+
// update rr_node_indices, a map to optimize rr_index lookups
142156
for (auto& grid : device_ctx.rr_node_indices) {
143157
for (size_t x = 0; x < grid.dim_size(0); x++) {
144158
for (size_t y = 0; y < grid.dim_size(1); y++) {

0 commit comments

Comments
 (0)