diff --git a/README.developers.md b/README.developers.md index ab18e7967eb..09922fa6c7b 100644 --- a/README.developers.md +++ b/README.developers.md @@ -92,7 +92,7 @@ The overall approach is similar, but we call out the differences below. ## Commit Messages -Commit messages are an important part of understanding the code base and it's history. +Commit messages are an important part of understanding the code base and its history. It is therefore *extremely* important to provide the following information in the commit message: * What is being changed? diff --git a/README.md b/README.md index f28823264df..2256ff5bd39 100644 --- a/README.md +++ b/README.md @@ -3,7 +3,7 @@ [![Build Status](https://github.com/verilog-to-routing/vtr-verilog-to-routing/workflows/Test/badge.svg)](https://github.com/verilog-to-routing/vtr-verilog-to-routing/actions?query=workflow%3ATest) [![Documentation Status](https://readthedocs.org/projects/vtr/badge/?version=latest)](http://docs.verilogtorouting.org/en/latest/) ## Introduction -The Verilog-to-Routing (VTR) project is a world-wide collaborative effort to provide a open-source framework for conducting FPGA architecture and CAD research and development. +The Verilog-to-Routing (VTR) project is a world-wide collaborative effort to provide an open-source framework for conducting FPGA architecture and CAD research and development. The VTR design flow takes as input a Verilog description of a digital circuit, and a description of the target FPGA architecture. It then performs: * Elaboration & Synthesis (ODIN II) diff --git a/utils/fasm/test/test_fasm.cpp b/utils/fasm/test/test_fasm.cpp index 91bf57d99cf..19eceae3059 100644 --- a/utils/fasm/test/test_fasm.cpp +++ b/utils/fasm/test/test_fasm.cpp @@ -256,8 +256,8 @@ TEST_CASE("fasm_integration_test", "[fasm]") { const auto& rr_graph = device_ctx.rr_graph; for(size_t inode = 0; inode < device_ctx.rr_nodes.size(); ++inode) { for(t_edge_size iedge = 0; iedge < rr_graph.num_edges(RRNodeId(inode)); ++iedge) { - auto sink_inode = device_ctx.rr_nodes[inode].edge_sink_node(iedge); - auto switch_id = device_ctx.rr_nodes[inode].edge_switch(iedge); + auto sink_inode = size_t(rr_graph.edge_sink_node(RRNodeId(inode), iedge)); + auto switch_id = rr_graph.edge_switch(RRNodeId(inode), iedge); auto value = vtr::string_fmt("%d_%d_%zu", inode, sink_inode, switch_id); diff --git a/vpr/src/device/rr_graph_view.h b/vpr/src/device/rr_graph_view.h index 7bd32ddd560..a22df813e96 100644 --- a/vpr/src/device/rr_graph_view.h +++ b/vpr/src/device/rr_graph_view.h @@ -258,6 +258,18 @@ class RRGraphView { inline const char* node_side_string(RRNodeId node) const { return node_storage_.node_side_string(node); } + /** @brief Get the switch id that represents the iedge'th outgoing edge from a specific node + * TODO: We may need to revisit this API and think about higher level APIs, like ``switch_delay()`` + **/ + inline short edge_switch(RRNodeId id, t_edge_size iedge) const { + return node_storage_.edge_switch(id, iedge); + } + /** @brief Get the destination node for the iedge'th edge from specified RRNodeId. + * This method should generally not be used, and instead first_edge and + * last_edge should be used.*/ + inline RRNodeId edge_sink_node(RRNodeId id, t_edge_size iedge) const { + return node_storage_.edge_sink_node(id, iedge); + } /** @brief Get the number of configurable edges. This function is inlined for runtime optimization. */ inline t_edge_size num_configurable_edges(RRNodeId node) const { @@ -298,13 +310,6 @@ class RRGraphView { * This API is very powerful and developers should not use it unless it is necessary, * e.g the node type is unknown. If the node type is known, the more specific routines, `node_pin_num()`, * `node_track_num()`and `node_class_num()`, for different types of nodes should be used.*/ - /** @brief Return detailed routing segment information with a given id* @note The routing segments here may not be exactly same as those defined in architecture file. They have been - * adapted to fit the context of routing resource graphs. - */ - - inline const t_segment_inf& rr_segments(RRSegmentId seg_id) const { - return rr_segments_[seg_id]; - } inline short node_ptc_num(RRNodeId node) const { return node_storage_.node_ptc_num(node); } @@ -331,6 +336,13 @@ class RRGraphView { RRIndexedDataId node_cost_index(RRNodeId node) const { return node_storage_.node_cost_index(node); } + /** @brief Return detailed routing segment information with a given id* @note The routing segments here may not be exactly same as those defined in architecture file. They have been + * adapted to fit the context of routing resource graphs. + */ + + inline const t_segment_inf& rr_segments(RRSegmentId seg_id) const { + return rr_segments_[seg_id]; + } /** @brief Return the fast look-up data structure for queries from client functions */ const RRSpatialLookup& node_lookup() const { diff --git a/vpr/src/draw/draw.cpp b/vpr/src/draw/draw.cpp index 896e6b66698..7be758f22c2 100644 --- a/vpr/src/draw/draw.cpp +++ b/vpr/src/draw/draw.cpp @@ -1686,10 +1686,10 @@ static void draw_rr_edges(int inode, ezgl::renderer* g) { return; /* Nothing to draw. */ } - from_ptc_num = rr_graph.node_ptc_num(RRNodeId(inode)); + from_ptc_num = rr_graph.node_ptc_num(rr_node); for (t_edge_size iedge = 0, l = rr_graph.num_edges(RRNodeId(inode)); iedge < l; iedge++) { - to_node = device_ctx.rr_nodes[inode].edge_sink_node(iedge); + to_node = size_t(rr_graph.edge_sink_node(rr_node, iedge)); to_type = rr_graph.node_type(RRNodeId(to_node)); to_ptc_num = rr_graph.node_ptc_num(RRNodeId(to_node)); bool edge_configurable = device_ctx.rr_nodes[inode].edge_is_configurable(iedge); @@ -1772,8 +1772,8 @@ static void draw_rr_edges(int inode, ezgl::renderer* g) { } else { g->set_color(blk_DARKGREEN); } - switch_type = device_ctx.rr_nodes[inode].edge_switch(iedge); - draw_chanx_to_chanx_edge(RRNodeId(inode), RRNodeId(to_node), + switch_type = rr_graph.edge_switch(rr_node, iedge); + draw_chanx_to_chanx_edge(rr_node, RRNodeId(to_node), to_ptc_num, switch_type, g); break; @@ -1789,7 +1789,7 @@ static void draw_rr_edges(int inode, ezgl::renderer* g) { } else { g->set_color(blk_DARKGREEN); } - switch_type = device_ctx.rr_nodes[inode].edge_switch(iedge); + switch_type = rr_graph.edge_switch(rr_node, iedge); draw_chanx_to_chany_edge(inode, from_ptc_num, to_node, to_ptc_num, FROM_X_TO_Y, switch_type, g); break; @@ -1842,7 +1842,7 @@ static void draw_rr_edges(int inode, ezgl::renderer* g) { } else { g->set_color(blk_DARKGREEN); } - switch_type = device_ctx.rr_nodes[inode].edge_switch(iedge); + switch_type = rr_graph.edge_switch(rr_node, iedge); draw_chanx_to_chany_edge(to_node, to_ptc_num, inode, from_ptc_num, FROM_Y_TO_X, switch_type, g); break; @@ -1860,8 +1860,8 @@ static void draw_rr_edges(int inode, ezgl::renderer* g) { } else { g->set_color(blk_DARKGREEN); } - switch_type = device_ctx.rr_nodes[inode].edge_switch(iedge); - draw_chany_to_chany_edge(RRNodeId(inode), RRNodeId(to_node), + switch_type = rr_graph.edge_switch(rr_node, iedge); + draw_chany_to_chany_edge(rr_node, RRNodeId(to_node), to_ptc_num, switch_type, g); break; @@ -2519,7 +2519,7 @@ void draw_partial_route(const std::vector& rr_nodes_to_draw, ezgl::renderer auto prev_type = rr_graph.node_type(RRNodeId(prev_node)); auto iedge = find_edge(prev_node, inode); - auto switch_type = device_ctx.rr_nodes[prev_node].edge_switch(iedge); + auto switch_type = rr_graph.edge_switch(RRNodeId(prev_node), iedge); switch (rr_type) { case OPIN: { @@ -2698,12 +2698,11 @@ void draw_highlight_fan_in_fan_out(const std::set& nodes) { t_draw_state* draw_state = get_draw_state_vars(); auto& device_ctx = g_vpr_ctx.device(); const auto& rr_graph = device_ctx.rr_graph; - for (auto node : nodes) { /* Highlight the fanout nodes in red. */ for (t_edge_size iedge = 0, l = rr_graph.num_edges(RRNodeId(node)); iedge < l; iedge++) { - int fanout_node = device_ctx.rr_nodes[node].edge_sink_node(iedge); + int fanout_node = size_t(rr_graph.edge_sink_node(RRNodeId(node), iedge)); if (draw_state->draw_rr_node[node].color == ezgl::MAGENTA && draw_state->draw_rr_node[fanout_node].color @@ -2722,8 +2721,7 @@ void draw_highlight_fan_in_fan_out(const std::set& nodes) { for (size_t inode = 0; inode < device_ctx.rr_nodes.size(); inode++) { for (t_edge_size iedge = 0, l = rr_graph.num_edges(RRNodeId(inode)); iedge < l; iedge++) { - int fanout_node = device_ctx.rr_nodes[inode].edge_sink_node( - iedge); + int fanout_node = size_t(rr_graph.edge_sink_node(RRNodeId(node), iedge)); if (fanout_node == node) { if (draw_state->draw_rr_node[node].color == ezgl::MAGENTA && draw_state->draw_rr_node[inode].color @@ -2825,13 +2823,12 @@ void draw_expand_non_configurable_rr_nodes_recurr(int from_node, std::set& expanded_nodes) { auto& device_ctx = g_vpr_ctx.device(); const auto& rr_graph = device_ctx.rr_graph; - expanded_nodes.insert(from_node); for (t_edge_size iedge = 0; iedge < rr_graph.num_edges(RRNodeId(from_node)); ++iedge) { bool edge_configurable = device_ctx.rr_nodes[from_node].edge_is_configurable(iedge); - int to_node = device_ctx.rr_nodes[from_node].edge_sink_node(iedge); + int to_node = size_t(rr_graph.edge_sink_node(RRNodeId(from_node), iedge)); if (!edge_configurable && !expanded_nodes.count(to_node)) { draw_expand_non_configurable_rr_nodes_recurr(to_node, @@ -3788,7 +3785,7 @@ static t_edge_size find_edge(int prev_inode, int inode) { const auto& rr_graph = device_ctx.rr_graph; for (t_edge_size iedge = 0; iedge < rr_graph.num_edges(RRNodeId(prev_inode)); ++iedge) { - if (device_ctx.rr_nodes[prev_inode].edge_sink_node(iedge) == inode) { + if (size_t(rr_graph.edge_sink_node(RRNodeId(prev_inode), iedge)) == size_t(inode)) { return iedge; } } diff --git a/vpr/src/place/timing_place_lookup.cpp b/vpr/src/place/timing_place_lookup.cpp index 28b818b3d3d..967d151fad3 100644 --- a/vpr/src/place/timing_place_lookup.cpp +++ b/vpr/src/place/timing_place_lookup.cpp @@ -1161,22 +1161,21 @@ bool directconnect_exists(int src_rr_node, int sink_rr_node) { //which starts at src_rr_node and ends at sink_rr_node auto& device_ctx = g_vpr_ctx.device(); const auto& rr_graph = device_ctx.rr_graph; - auto& rr_nodes = device_ctx.rr_nodes; VTR_ASSERT(rr_graph.node_type(RRNodeId(src_rr_node)) == SOURCE && rr_graph.node_type(RRNodeId(sink_rr_node)) == SINK); //TODO: This is a constant depth search, but still may be too slow for (t_edge_size i_src_edge = 0; i_src_edge < rr_graph.num_edges(RRNodeId(src_rr_node)); ++i_src_edge) { - int opin_rr_node = rr_nodes[src_rr_node].edge_sink_node(i_src_edge); + int opin_rr_node = size_t(rr_graph.edge_sink_node(RRNodeId(src_rr_node), i_src_edge)); if (rr_graph.node_type(RRNodeId(opin_rr_node)) != OPIN) continue; for (t_edge_size i_opin_edge = 0; i_opin_edge < rr_graph.num_edges(RRNodeId(opin_rr_node)); ++i_opin_edge) { - int ipin_rr_node = rr_nodes[opin_rr_node].edge_sink_node(i_opin_edge); + int ipin_rr_node = size_t(rr_graph.edge_sink_node(RRNodeId(opin_rr_node), i_opin_edge)); if (rr_graph.node_type(RRNodeId(ipin_rr_node)) != IPIN) continue; for (t_edge_size i_ipin_edge = 0; i_ipin_edge < rr_graph.num_edges(RRNodeId(ipin_rr_node)); ++i_ipin_edge) { - if (sink_rr_node == rr_nodes[ipin_rr_node].edge_sink_node(i_ipin_edge)) { + if (size_t(sink_rr_node) == size_t(rr_graph.edge_sink_node(RRNodeId(ipin_rr_node), i_ipin_edge))) { return true; } } diff --git a/vpr/src/power/power.cpp b/vpr/src/power/power.cpp index d88666e22a5..bab019a5734 100644 --- a/vpr/src/power/power.cpp +++ b/vpr/src/power/power.cpp @@ -814,7 +814,6 @@ static void power_usage_routing(t_power_usage* power_usage, t_trace* trace; for (trace = route_ctx.trace[net_id].head; trace != nullptr; trace = trace->next) { - auto node = device_ctx.rr_nodes[trace->index]; t_rr_node_power* node_power = &rr_node_power[trace->index]; if (node_power->visited) { @@ -822,8 +821,8 @@ static void power_usage_routing(t_power_usage* power_usage, } for (t_edge_size edge_idx = 0; edge_idx < rr_graph.num_edges(RRNodeId(trace->index)); edge_idx++) { - const auto& next_node_id = node.edge_sink_node(edge_idx); - if (next_node_id != OPEN) { + const auto& next_node_id = size_t(rr_graph.edge_sink_node(RRNodeId(trace->index), edge_idx)); + if (next_node_id != size_t(OPEN)) { t_rr_node_power* next_node_power = &rr_node_power[next_node_id]; switch (rr_graph.node_type(RRNodeId(next_node_id))) { @@ -857,7 +856,6 @@ static void power_usage_routing(t_power_usage* power_usage, /* Calculate power of all routing entities */ for (size_t rr_node_idx = 0; rr_node_idx < device_ctx.rr_nodes.size(); rr_node_idx++) { t_power_usage sub_power_usage; - auto node = device_ctx.rr_nodes[rr_node_idx]; RRNodeId rr_node = RRNodeId(rr_node_idx); t_rr_node_power* node_power = &rr_node_power[rr_node_idx]; float C_wire; @@ -982,9 +980,9 @@ static void power_usage_routing(t_power_usage* power_usage, connectionbox_fanout = 0; switchbox_fanout = 0; for (t_edge_size iedge = 0; iedge < rr_graph.num_edges(rr_node); iedge++) { - if (node.edge_switch(iedge) == routing_arch->wire_to_rr_ipin_switch) { + if (rr_graph.edge_switch(rr_node, iedge) == routing_arch->wire_to_rr_ipin_switch) { connectionbox_fanout++; - } else if (node.edge_switch(iedge) == routing_arch->delayless_switch) { + } else if (rr_graph.edge_switch(rr_node, iedge) == routing_arch->delayless_switch) { /* Do nothing */ } else { switchbox_fanout++; @@ -1209,7 +1207,6 @@ void power_routing_init(const t_det_routing_arch* routing_arch) { for (size_t rr_node_idx = 0; rr_node_idx < device_ctx.rr_nodes.size(); rr_node_idx++) { t_edge_size fanout_to_IPIN = 0; t_edge_size fanout_to_seg = 0; - auto node = device_ctx.rr_nodes[rr_node_idx]; t_rr_node_power* node_power = &rr_node_power[rr_node_idx]; const t_edge_size node_fan_in = rr_graph.node_fan_in(RRNodeId(rr_node_idx)); @@ -1226,9 +1223,9 @@ void power_routing_init(const t_det_routing_arch* routing_arch) { case CHANX: case CHANY: for (t_edge_size iedge = 0; iedge < rr_graph.num_edges(RRNodeId(rr_node_idx)); iedge++) { - if (node.edge_switch(iedge) == routing_arch->wire_to_rr_ipin_switch) { + if (rr_graph.edge_switch(RRNodeId(rr_node_idx), iedge) == routing_arch->wire_to_rr_ipin_switch) { fanout_to_IPIN++; - } else if (node.edge_switch(iedge) != routing_arch->delayless_switch) { + } else if (rr_graph.edge_switch(RRNodeId(rr_node_idx), iedge) != routing_arch->delayless_switch) { fanout_to_seg++; } } @@ -1258,14 +1255,12 @@ void power_routing_init(const t_det_routing_arch* routing_arch) { /* Populate driver switch type */ for (size_t rr_node_idx = 0; rr_node_idx < device_ctx.rr_nodes.size(); rr_node_idx++) { - auto node = device_ctx.rr_nodes[rr_node_idx]; - for (t_edge_size edge_idx = 0; edge_idx < rr_graph.num_edges(RRNodeId(rr_node_idx)); edge_idx++) { - if (node.edge_sink_node(edge_idx) != OPEN) { - if (rr_node_power[node.edge_sink_node(edge_idx)].driver_switch_type == OPEN) { - rr_node_power[node.edge_sink_node(edge_idx)].driver_switch_type = node.edge_switch(edge_idx); + if (size_t(rr_graph.edge_sink_node(RRNodeId(rr_node_idx), edge_idx))) { + if (rr_node_power[size_t(rr_graph.edge_sink_node(RRNodeId(rr_node_idx), edge_idx))].driver_switch_type == OPEN) { + rr_node_power[size_t(rr_graph.edge_sink_node(RRNodeId(rr_node_idx), edge_idx))].driver_switch_type = rr_graph.edge_switch(RRNodeId(rr_node_idx), edge_idx); } else { - VTR_ASSERT(rr_node_power[node.edge_sink_node(edge_idx)].driver_switch_type == node.edge_switch(edge_idx)); + VTR_ASSERT(rr_node_power[size_t(rr_graph.edge_sink_node(RRNodeId(rr_node_idx), edge_idx))].driver_switch_type == rr_graph.edge_switch(RRNodeId(rr_node_idx), edge_idx)); } } } diff --git a/vpr/src/route/check_route.cpp b/vpr/src/route/check_route.cpp index e352a1fcdf0..c1b6407f1f4 100644 --- a/vpr/src/route/check_route.cpp +++ b/vpr/src/route/check_route.cpp @@ -310,7 +310,7 @@ static bool check_adjacent(int from_node, int to_node) { reached = false; for (t_edge_size iconn = 0; iconn < rr_graph.num_edges(RRNodeId(from_node)); iconn++) { - if (device_ctx.rr_nodes[from_node].edge_sink_node(iconn) == to_node) { + if (size_t(rr_graph.edge_sink_node(RRNodeId(from_node), iconn)) == size_t(to_node)) { reached = true; break; } diff --git a/vpr/src/route/check_rr_graph.cpp b/vpr/src/route/check_rr_graph.cpp index c778741f22d..984891e1c78 100644 --- a/vpr/src/route/check_rr_graph.cpp +++ b/vpr/src/route/check_rr_graph.cpp @@ -80,7 +80,7 @@ void check_rr_graph(const t_graph_type graph_type, edges.reserve(num_edges); for (int iedge = 0; iedge < num_edges; iedge++) { - int to_node = device_ctx.rr_nodes[inode].edge_sink_node(iedge); + int to_node = size_t(rr_graph.edge_sink_node(rr_node, iedge)); if (to_node < 0 || to_node >= (int)device_ctx.rr_nodes.size()) { VPR_FATAL_ERROR(VPR_ERROR_ROUTE, @@ -94,7 +94,7 @@ void check_rr_graph(const t_graph_type graph_type, edges.emplace_back(to_node, iedge); total_edges_to_node[to_node]++; - auto switch_type = device_ctx.rr_nodes[inode].edge_switch(iedge); + auto switch_type = rr_graph.edge_switch(rr_node, iedge); if (switch_type < 0 || switch_type >= num_rr_switches) { VPR_FATAL_ERROR(VPR_ERROR_ROUTE, @@ -110,7 +110,7 @@ void check_rr_graph(const t_graph_type graph_type, //Check that multiple edges between the same from/to nodes make sense for (int iedge = 0; iedge < num_edges; iedge++) { - int to_node = device_ctx.rr_nodes[inode].edge_sink_node(iedge); + int to_node = size_t(rr_graph.edge_sink_node(rr_node, iedge)); auto range = std::equal_range(edges.begin(), edges.end(), to_node, node_edge_sorter()); @@ -158,7 +158,7 @@ void check_rr_graph(const t_graph_type graph_type, std::map switch_counts; for (const auto& to_edge : vtr::Range(range.first, range.second)) { auto edge = to_edge.second; - auto edge_switch = device_ctx.rr_nodes[inode].edge_switch(edge); + auto edge_switch = rr_graph.edge_switch(rr_node, edge); switch_counts[edge_switch]++; } @@ -547,13 +547,13 @@ static void check_unbuffered_edges(int from_node) { from_num_edges = rr_graph.num_edges(RRNodeId(from_node)); for (from_edge = 0; from_edge < from_num_edges; from_edge++) { - to_node = device_ctx.rr_nodes[from_node].edge_sink_node(from_edge); + to_node = size_t(rr_graph.edge_sink_node(RRNodeId(from_node), from_edge)); to_rr_type = rr_graph.node_type(RRNodeId(to_node)); if (to_rr_type != CHANX && to_rr_type != CHANY) continue; - from_switch_type = device_ctx.rr_nodes[from_node].edge_switch(from_edge); + from_switch_type = rr_graph.edge_switch(RRNodeId(from_node), from_edge); if (device_ctx.rr_switch_inf[from_switch_type].buffered()) continue; @@ -566,8 +566,8 @@ static void check_unbuffered_edges(int from_node) { trans_matched = false; for (to_edge = 0; to_edge < to_num_edges; to_edge++) { - if (device_ctx.rr_nodes[to_node].edge_sink_node(to_edge) == from_node - && device_ctx.rr_nodes[to_node].edge_switch(to_edge) == from_switch_type) { + if (size_t(rr_graph.edge_sink_node(RRNodeId(to_node), to_edge)) == size_t(from_node) + && rr_graph.edge_switch(RRNodeId(to_node), to_edge) == from_switch_type) { trans_matched = true; break; } @@ -606,7 +606,7 @@ static void check_rr_edge(int from_node, int iedge, int to_node) { const auto& rr_graph = device_ctx.rr_graph; //Check that to to_node's fan-in is correct, given the switch type - int iswitch = device_ctx.rr_nodes[from_node].edge_switch(iedge); + int iswitch = rr_graph.edge_switch(RRNodeId(from_node), iedge); auto switch_type = device_ctx.rr_switch_inf[iswitch].type(); int to_fanin = rr_graph.node_fan_in(RRNodeId(to_node)); diff --git a/vpr/src/route/route_common.cpp b/vpr/src/route/route_common.cpp index e8f9622a6c3..21e8c69c4db 100644 --- a/vpr/src/route/route_common.cpp +++ b/vpr/src/route/route_common.cpp @@ -631,7 +631,7 @@ static std::pair add_trace_non_configurable_recurr(int node, for (auto iedge : rr_graph.non_configurable_edges(RRNodeId(node))) { VTR_ASSERT_SAFE(!device_ctx.rr_nodes[node].edge_is_configurable(iedge)); - int to_node = device_ctx.rr_nodes[node].edge_sink_node(iedge); + int to_node = size_t(rr_graph.edge_sink_node(RRNodeId(node), iedge)); if (!trace_nodes.count(to_node)) { unvisited_non_configurable_edges.push_back(iedge); @@ -654,8 +654,8 @@ static std::pair add_trace_non_configurable_recurr(int node, } else { //Recursive case: intermediate node with non-configurable edges for (auto iedge : unvisited_non_configurable_edges) { - int to_node = device_ctx.rr_nodes[node].edge_sink_node(iedge); - int iswitch = device_ctx.rr_nodes[node].edge_switch(iedge); + int to_node = size_t(rr_graph.edge_sink_node(RRNodeId(node), iedge)); + int iswitch = rr_graph.edge_switch(RRNodeId(node), iedge); VTR_ASSERT(!trace_nodes.count(to_node)); trace_nodes.insert(node); @@ -1427,7 +1427,7 @@ void reserve_locally_used_opins(HeapInterface* heap, float pres_fac, float acc_f from_node = route_ctx.rr_blk_source[blk_id][iclass]; num_edges = rr_graph.num_edges(RRNodeId(from_node)); for (iconn = 0; iconn < num_edges; iconn++) { - to_node = device_ctx.rr_nodes[from_node].edge_sink_node(iconn); + to_node = size_t(rr_graph.edge_sink_node(RRNodeId(from_node), iconn)); VTR_ASSERT(rr_graph.node_type(RRNodeId(to_node)) == OPIN); @@ -1563,16 +1563,15 @@ bool validate_traceback_recurr(t_trace* trace, std::set& seen_rr_nodes) { auto& device_ctx = g_vpr_ctx.device(); const auto& rr_graph = device_ctx.rr_graph; - bool found = false; for (t_edge_size iedge = 0; iedge < rr_graph.num_edges(RRNodeId(trace->index)); ++iedge) { - int to_node = device_ctx.rr_nodes[trace->index].edge_sink_node(iedge); + int to_node = size_t(rr_graph.edge_sink_node(RRNodeId(trace->index), iedge)); if (to_node == next->index) { found = true; //Verify that the switch matches - int rr_iswitch = device_ctx.rr_nodes[trace->index].edge_switch(iedge); + int rr_iswitch = rr_graph.edge_switch(RRNodeId(trace->index), iedge); if (trace->iswitch != rr_iswitch) { VPR_FATAL_ERROR(VPR_ERROR_ROUTE, "Traceback mismatched switch type: traceback %d rr_graph %d (RR nodes %d -> %d)\n", trace->iswitch, rr_iswitch, diff --git a/vpr/src/route/route_tree_timing.cpp b/vpr/src/route/route_tree_timing.cpp index fb510f7de8c..214b8d2b329 100644 --- a/vpr/src/route/route_tree_timing.cpp +++ b/vpr/src/route/route_tree_timing.cpp @@ -421,14 +421,13 @@ static t_rt_node* add_non_configurable_to_route_tree(const int rr_node, const bo for (int iedge : rr_graph.non_configurable_edges(RRNodeId(rr_node))) { //Recursive case: expand children VTR_ASSERT(!device_ctx.rr_nodes[rr_node].edge_is_configurable(iedge)); - - int to_rr_node = device_ctx.rr_nodes[rr_node].edge_sink_node(iedge); + int to_rr_node = size_t(rr_graph.edge_sink_node(RRNodeId(rr_node), iedge)); //Recurse t_rt_node* child_rt_node = add_non_configurable_to_route_tree(to_rr_node, true, visited); if (!child_rt_node) continue; - int iswitch = device_ctx.rr_nodes[rr_node].edge_switch(iedge); + int iswitch = rr_graph.edge_switch(RRNodeId(rr_node), iedge); //Create the edge t_linked_rt_edge* linked_rt_edge = alloc_linked_rt_edge(); diff --git a/vpr/src/route/router_lookahead_extended_map.cpp b/vpr/src/route/router_lookahead_extended_map.cpp index f220f87bc82..258de89050b 100644 --- a/vpr/src/route/router_lookahead_extended_map.cpp +++ b/vpr/src/route/router_lookahead_extended_map.cpp @@ -311,8 +311,7 @@ bool ExtendedMapLookahead::add_paths(RRNodeId start_node, delta}; if (size_t(this_node) != size_t(start_node)) { - auto& parent_node = device_ctx.rr_nodes[size_t(parent)]; - start_to_here = Entry(this_node, parent_node.edge_switch(paths[*it].edge), &start_to_here); + start_to_here = Entry(this_node, rr_graph.edge_switch(RRNodeId(parent), paths[*it].edge), &start_to_here); parent = this_node; } @@ -400,8 +399,7 @@ std::pair ExtendedMapLookahead::run_dijkstra(RRNodeId start_node, path_count++; this->add_paths(start_node, current, *paths, routing_costs); } else { - util::expand_dijkstra_neighbours(device_ctx.rr_nodes, - current, paths, node_expanded, &pq); + util::expand_dijkstra_neighbours(rr_graph, current, paths, node_expanded, &pq); (*node_expanded)[size_t(node)] = true; } } diff --git a/vpr/src/route/router_lookahead_map_utils.cpp b/vpr/src/route/router_lookahead_map_utils.cpp index ceeeeb67829..0101aece49a 100644 --- a/vpr/src/route/router_lookahead_map_utils.cpp +++ b/vpr/src/route/router_lookahead_map_utils.cpp @@ -252,22 +252,18 @@ util::Cost_Entry util::Expansion_Cost_Entry::get_median_entry() const { } template -void expand_dijkstra_neighbours(const t_rr_graph_storage& rr_nodes, +void expand_dijkstra_neighbours(const RRGraphView& rr_graph, const Entry& parent_entry, std::vector* paths, std::vector* node_expanded, std::priority_queue, std::greater>* pq) { - auto& device_ctx = g_vpr_ctx.device(); - const auto& rr_graph = device_ctx.rr_graph; RRNodeId parent = parent_entry.rr_node; - auto& parent_node = rr_nodes[size_t(parent)]; - - for (int iedge = 0; iedge < rr_graph.num_edges(RRNodeId(parent)); iedge++) { - int child_node_ind = parent_node.edge_sink_node(iedge); - int switch_ind = parent_node.edge_switch(iedge); + for (int iedge = 0; iedge < rr_graph.num_edges(parent); iedge++) { + int child_node_ind = size_t(rr_graph.edge_sink_node(RRNodeId(parent), iedge)); + int switch_ind = rr_graph.edge_switch(parent, iedge); /* skip this child if it has already been expanded from */ if ((*node_expanded)[child_node_ind]) { @@ -288,14 +284,14 @@ void expand_dijkstra_neighbours(const t_rr_graph_storage& rr_nodes, } } -template void expand_dijkstra_neighbours(const t_rr_graph_storage& rr_nodes, +template void expand_dijkstra_neighbours(const RRGraphView& rr_graph, const PQ_Entry_Delay& parent_entry, std::vector* paths, std::vector* node_expanded, std::priority_queue, std::greater>* pq); -template void expand_dijkstra_neighbours(const t_rr_graph_storage& rr_nodes, +template void expand_dijkstra_neighbours(const RRGraphView& rr_graph, const PQ_Entry_Base_Cost& parent_entry, std::vector* paths, std::vector* node_expanded, diff --git a/vpr/src/route/router_lookahead_map_utils.h b/vpr/src/route/router_lookahead_map_utils.h index 5a3fe3b3bd5..8380a16c854 100644 --- a/vpr/src/route/router_lookahead_map_utils.h +++ b/vpr/src/route/router_lookahead_map_utils.h @@ -23,6 +23,7 @@ #include "vpr_types.h" #include "vtr_geometry.h" #include "rr_node.h" +#include "rr_graph_view.h" namespace util { @@ -238,7 +239,7 @@ struct Search_Path { /* iterates over the children of the specified node and selectively pushes them onto the priority queue */ template -void expand_dijkstra_neighbours(const t_rr_graph_storage& rr_nodes, +void expand_dijkstra_neighbours(const RRGraphView& rr_graph, const Entry& parent_entry, std::vector* paths, std::vector* node_expanded, diff --git a/vpr/src/route/rr_graph_area.cpp b/vpr/src/route/rr_graph_area.cpp index 4afbb05eafc..66ec0d0cbaa 100644 --- a/vpr/src/route/rr_graph_area.cpp +++ b/vpr/src/route/rr_graph_area.cpp @@ -167,7 +167,7 @@ void count_bidir_routing_transistors(int num_switch, int wire_to_ipin_switch, fl num_edges = rr_graph.num_edges(RRNodeId(from_node)); for (iedge = 0; iedge < num_edges; iedge++) { - RRNodeId to_node = RRNodeId(device_ctx.rr_nodes[from_node].edge_sink_node(iedge)); + RRNodeId to_node = rr_graph.edge_sink_node(RRNodeId(from_node), iedge); to_rr_type = rr_graph.node_type(to_node); /* Ignore any uninitialized rr_graph nodes */ @@ -178,7 +178,7 @@ void count_bidir_routing_transistors(int num_switch, int wire_to_ipin_switch, fl switch (to_rr_type) { case CHANX: case CHANY: - iswitch = device_ctx.rr_nodes[from_node].edge_switch(iedge); + iswitch = rr_graph.edge_switch(RRNodeId(from_node), iedge); if (device_ctx.rr_switch_inf[iswitch].buffered()) { iseg = seg_index_of_sblock(from_node, size_t(to_node)); @@ -253,7 +253,7 @@ void count_bidir_routing_transistors(int num_switch, int wire_to_ipin_switch, fl shared_opin_buffer_trans = 0.; for (iedge = 0; iedge < num_edges; iedge++) { - iswitch = device_ctx.rr_nodes[from_node].edge_switch(iedge); + iswitch = rr_graph.edge_switch(RRNodeId(from_node), iedge); ntrans_no_sharing += unsharable_switch_trans[iswitch] + sharable_switch_trans[iswitch]; ntrans_sharing += unsharable_switch_trans[iswitch]; @@ -365,7 +365,7 @@ void count_unidir_routing_transistors(std::vector& /*segment_inf* /* Increment number of inputs per cblock if IPIN */ for (iedge = 0; iedge < num_edges; iedge++) { - RRNodeId to_node = RRNodeId(device_ctx.rr_nodes[from_node].edge_sink_node(iedge)); + RRNodeId to_node = rr_graph.edge_sink_node(RRNodeId(from_node), iedge); to_rr_type = rr_graph.node_type(to_node); /* Ignore any uninitialized rr_graph nodes */ @@ -377,7 +377,7 @@ void count_unidir_routing_transistors(std::vector& /*segment_inf* case CHANX: case CHANY: if (!chan_node_switch_done[size_t(to_node)]) { - int switch_index = device_ctx.rr_nodes[from_node].edge_switch(iedge); + int switch_index = rr_graph.edge_switch(RRNodeId(from_node), iedge); auto switch_type = device_ctx.rr_switch_inf[switch_index].type(); int fan_in = rr_graph.node_fan_in(to_node); diff --git a/vpr/src/route/rr_graph_timing_params.cpp b/vpr/src/route/rr_graph_timing_params.cpp index 15bf7cdf997..d51c77de6c1 100644 --- a/vpr/src/route/rr_graph_timing_params.cpp +++ b/vpr/src/route/rr_graph_timing_params.cpp @@ -55,11 +55,11 @@ void add_rr_graph_C_from_switches(float C_ipin_cblock) { if (from_rr_type == CHANX || from_rr_type == CHANY) { for (t_edge_size iedge = 0; iedge < rr_graph.num_edges(RRNodeId(inode)); iedge++) { - to_node = device_ctx.rr_nodes[inode].edge_sink_node(iedge); + to_node = size_t(rr_graph.edge_sink_node(RRNodeId(inode), iedge)); to_rr_type = rr_graph.node_type(RRNodeId(to_node)); if (to_rr_type == CHANX || to_rr_type == CHANY) { - switch_index = device_ctx.rr_nodes[inode].edge_switch(iedge); + switch_index = rr_graph.edge_switch(RRNodeId(inode), iedge); Cin = device_ctx.rr_switch_inf[switch_index].Cin; Cout = device_ctx.rr_switch_inf[switch_index].Cout; buffered = device_ctx.rr_switch_inf[switch_index].buffered(); @@ -150,8 +150,8 @@ void add_rr_graph_C_from_switches(float C_ipin_cblock) { /* End node is CHANX or CHANY */ else if (from_rr_type == OPIN) { for (t_edge_size iedge = 0; iedge < rr_graph.num_edges(RRNodeId(inode)); iedge++) { - switch_index = device_ctx.rr_nodes[inode].edge_switch(iedge); - to_node = device_ctx.rr_nodes[inode].edge_sink_node(iedge); + switch_index = rr_graph.edge_switch(RRNodeId(inode), iedge); + to_node = size_t(rr_graph.edge_sink_node(RRNodeId(inode), iedge)); to_rr_type = rr_graph.node_type(RRNodeId(to_node)); if (to_rr_type != CHANX && to_rr_type != CHANY) @@ -159,7 +159,7 @@ void add_rr_graph_C_from_switches(float C_ipin_cblock) { if (rr_graph.node_direction(RRNodeId(to_node)) == Direction::BIDIR) { Cout = device_ctx.rr_switch_inf[switch_index].Cout; - to_node = device_ctx.rr_nodes[inode].edge_sink_node(iedge); /* Will be CHANX or CHANY */ + to_node = size_t(rr_graph.edge_sink_node(RRNodeId(inode), iedge)); /* Will be CHANX or CHANY */ rr_node_C[to_node] += Cout; } } @@ -174,8 +174,8 @@ void add_rr_graph_C_from_switches(float C_ipin_cblock) { Couts_to_add = (float*)vtr::calloc(device_ctx.rr_nodes.size(), sizeof(float)); for (size_t inode = 0; inode < device_ctx.rr_nodes.size(); inode++) { for (t_edge_size iedge = 0; iedge < rr_graph.num_edges(RRNodeId(inode)); iedge++) { - switch_index = device_ctx.rr_nodes[inode].edge_switch(iedge); - to_node = device_ctx.rr_nodes[inode].edge_sink_node(iedge); + switch_index = rr_graph.edge_switch(RRNodeId(inode), iedge); + to_node = size_t(rr_graph.edge_sink_node(RRNodeId(inode), iedge)); to_rr_type = rr_graph.node_type(RRNodeId(to_node)); if (to_rr_type == CHANX || to_rr_type == CHANY) { if (rr_graph.node_direction(RRNodeId(to_node)) != Direction::BIDIR) { diff --git a/vpr/src/route/rr_graph_uxsdcxx_serializer.h b/vpr/src/route/rr_graph_uxsdcxx_serializer.h index 5efb80efa16..159399e48cc 100644 --- a/vpr/src/route/rr_graph_uxsdcxx_serializer.h +++ b/vpr/src/route/rr_graph_uxsdcxx_serializer.h @@ -167,11 +167,11 @@ class EdgeWalker { } int current_sink_node() const { VTR_ASSERT(current_src_inode_ < nodes_->size()); - return (*nodes_)[current_src_inode_].edge_sink_node(current_edge_); + return size_t(rr_graph_->edge_sink_node(RRNodeId(current_src_inode_), current_edge_)); } int current_switch_id_node() const { VTR_ASSERT(current_src_inode_ < nodes_->size()); - return (*nodes_)[current_src_inode_].edge_switch(current_edge_); + return rr_graph_->edge_switch(RRNodeId(current_src_inode_), current_edge_); } size_t advance(int n) { diff --git a/vpr/src/route/rr_node.cpp b/vpr/src/route/rr_node.cpp index 33154dc6d00..cdb96ac2250 100644 --- a/vpr/src/route/rr_node.cpp +++ b/vpr/src/route/rr_node.cpp @@ -10,12 +10,11 @@ short t_rr_node::length() const { storage_->node_yhigh(id_) - storage_->node_ylow(id_), storage_->node_xhigh(id_) - storage_->node_xlow(id_)); } - +/* TODO: This API should be reworked once rr_switch APIs are in RRGraphView. */ bool t_rr_node::edge_is_configurable(t_edge_size iedge) const { - auto iswitch = edge_switch(iedge); - auto& device_ctx = g_vpr_ctx.device(); - + const auto& rr_graph = device_ctx.rr_graph; + auto iswitch = rr_graph.edge_switch(id_, iedge); return device_ctx.rr_switch_inf[iswitch].configurable(); } diff --git a/vpr/src/route/rr_node_impl.h b/vpr/src/route/rr_node_impl.h index 85482f878c8..3f4ab4ed616 100644 --- a/vpr/src/route/rr_node_impl.h +++ b/vpr/src/route/rr_node_impl.h @@ -83,12 +83,4 @@ inline t_edge_size t_rr_node::num_configurable_edges() const { return storage_->num_configurable_edges(id_); } -inline int t_rr_node::edge_sink_node(t_edge_size iedge) const { - size_t inode = (size_t)storage_->edge_sink_node(id_, iedge); - return inode; -} -inline short t_rr_node::edge_switch(t_edge_size iedge) const { - return storage_->edge_switch(id_, iedge); -} - #endif /* _RR_NODE_IMPL_H_ */ diff --git a/vpr/src/util/vpr_utils.cpp b/vpr/src/util/vpr_utils.cpp index e82ac44561e..482b09bf9ca 100644 --- a/vpr/src/util/vpr_utils.cpp +++ b/vpr/src/util/vpr_utils.cpp @@ -1789,7 +1789,6 @@ static int convert_switch_index(int* switch_index, int* fanin) { void print_switch_usage() { auto& device_ctx = g_vpr_ctx.device(); const auto& rr_graph = device_ctx.rr_graph; - if (device_ctx.switch_fanin_remap.empty()) { VTR_LOG_WARN("Cannot print switch usage stats: device_ctx.switch_fanin_remap is empty\n"); return; @@ -1802,11 +1801,10 @@ void print_switch_usage() { // map key: switch index; map value: count (fanin) std::map* inward_switch_inf = new std::map[device_ctx.rr_nodes.size()]; for (size_t inode = 0; inode < device_ctx.rr_nodes.size(); inode++) { - const t_rr_node& from_node = device_ctx.rr_nodes[inode]; int num_edges = rr_graph.num_edges(RRNodeId(inode)); for (int iedge = 0; iedge < num_edges; iedge++) { - int switch_index = from_node.edge_switch(iedge); - int to_node_index = from_node.edge_sink_node(iedge); + int switch_index = rr_graph.edge_switch(RRNodeId(inode), iedge); + int to_node_index = size_t(rr_graph.edge_sink_node(RRNodeId(inode), iedge)); // Assumption: suppose for a L4 wire (bi-directional): ----+----+----+----, it can be driven from any point (0, 1, 2, 3). // physically, the switch driving from point 1 & 3 should be the same. But we will assign then different switch // index; or there is no way to differentiate them after abstracting a 2D wire into a 1D node diff --git a/vpr/test/test_connection_router.cpp b/vpr/test/test_connection_router.cpp index c9fed28a480..001ceba4324 100644 --- a/vpr/test/test_connection_router.cpp +++ b/vpr/test/test_connection_router.cpp @@ -16,7 +16,6 @@ namespace { // Route from source_node to sink_node, returning either the delay, or infinity if unroutable. static float do_one_route(int source_node, int sink_node, const t_router_opts& router_opts, const std::vector& segment_inf) { auto& device_ctx = g_vpr_ctx.device(); - auto& route_ctx = g_vpr_ctx.routing(); t_rt_node* rt_root = init_route_tree_to_source_no_net(source_node); diff --git a/vpr/test/test_vpr.cpp b/vpr/test/test_vpr.cpp index 5e13977ce85..cbe7f26f8a3 100644 --- a/vpr/test/test_vpr.cpp +++ b/vpr/test/test_vpr.cpp @@ -143,8 +143,8 @@ TEST_CASE("read_rr_graph_metadata", "[vpr]") { } REQUIRE(src_inode >= 0); - sink_inode = device_ctx.rr_nodes[src_inode].edge_sink_node(0); - switch_id = device_ctx.rr_nodes[src_inode].edge_switch(0); + sink_inode = size_t(rr_graph.edge_sink_node(RRNodeId(src_inode), 0)); + switch_id = rr_graph.edge_switch(RRNodeId(src_inode), 0); vpr::add_rr_node_metadata(src_inode, vtr::string_view("node"), vtr::string_view("test node")); vpr::add_rr_edge_metadata(src_inode, sink_inode, switch_id, vtr::string_view("edge"), vtr::string_view("test edge"));