-
Notifications
You must be signed in to change notification settings - Fork 431
Adding Custom RR Graph Builder to OpenFPGA #3325
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Changes from all commits
d38f924
9164048
2af1e09
01eca68
d942d0e
14aa81b
6375030
08510ff
343a345
1bdb9b2
4986263
549c5b4
1fe6d46
ea02eed
8908e31
341ffed
bc4bc0b
bedddcd
099b81d
78c2581
852890a
d93536c
fc38a9f
84cc0b4
8215eee
008a4e2
8975125
3aaee29
327513e
ae4ceef
76789e7
91d1fc9
c67bae0
c895c31
9c9edfb
097ebdc
bdba300
d59ae52
67783be
7bbec6c
5c4aeca
0803118
8278af7
60cc0e0
2dc929e
6086a64
88afdce
21998d9
44990a9
fc88092
a393fbe
38ee748
dae8bc6
3c2350a
e3b345f
9f723a5
d064a15
f9c1c66
6883c93
6b4a95b
10b0888
7139c9e
7ef33f1
fdeb013
6ab4258
f14e6e0
2ba93e5
1933857
ef41a0b
7e2c039
d087834
d5a80f0
b62eed4
2d677ca
5d5133c
585ecaa
e3f0f28
61c3a21
ca34e03
c408a87
86698eb
5b17dd1
fe8225c
3952894
16e8ffe
f85d1c6
4b438b9
e6fc757
e07bbd1
12e17a7
1ce35ad
11d32fa
88caeb5
949e9a4
e2d0014
a6934c2
ca6fe30
219ab6e
3373b7d
dca5881
6324b79
e9d7a10
7aff688
fca44b1
b4d0a59
83a3aef
23f0dc8
c72e3c6
64ac05a
56796ca
f924fe4
ad08271
7f0b02e
29bfe3c
a1859aa
7d1e758
006f22b
848820d
e264986
2aa56e2
53490a8
91c8da5
e888c7d
3e839fb
cd4ee33
2701610
56d6981
19cf552
a135426
15d69c5
df4552d
eb86cfe
613989f
4a4f3c3
42b9dd4
e933685
9135061
7cb89f7
0608908
0415387
94b1a3b
a5fcbc8
a9f1a43
a758d0b
9b8f934
4aaeb0f
f35cde6
b2d8057
915de4a
6c7365f
ecec621
4c0f2dd
6a6eed7
06a76d9
702c6c6
52e73fa
4b90bd0
5eedb46
ac5e489
1fa6dc2
5f5a764
0fdc5f0
6dbd7cf
40f8216
3c8705f
d7f3183
ee938f3
345668d
7cfadf9
d129693
5bebbde
d6eeab3
8c84ee8
9ce59b9
d20a783
3402606
a226ec0
93c3a6a
38c4af4
b93665a
0e30395
1bae57a
2a7d23d
3542097
07da73e
a7f7aff
6aad676
5e47786
58265c6
b433a8a
23642d7
69ff7e9
f0731a1
fa818f2
7eafb67
33313b6
e3f8046
cf75217
2e768c7
e1f97f6
098e613
83a45d0
dcfcc93
16e8086
3c8afb7
cd2b546
65eece7
5520950
6610d9c
6be4658
b07a8bd
4ed0868
73edb0f
a7624e3
0f5bbb4
4aa07e7
092a7cb
1d674de
a522f36
1ea8a74
9bdaa71
a5106f4
a5ab5eb
99c842c
28b544d
b8fb937
9e12c99
455d78e
b523e17
881eafe
8ab14d3
88210fd
8c93669
f2977a6
69520dc
8d456d3
0cdc229
5991cfc
daba54e
8d099c7
893632e
fef08af
1bf90e6
331aea1
176f5c3
71feabe
36270c6
ae1b310
cb86ddc
f35efa7
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,3 +1,5 @@ | ||
| .. _vpr_command_line_usage: | ||
|
|
||
| Command-line Options | ||
| ==================== | ||
| .. program:: vpr | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,187 @@ | ||
| .. _custom_rr_graph_generator: | ||
|
|
||
| Custom RR Graph | ||
| =============== | ||
|
|
||
| For users who want more control over how connections are made in the routing resource graph, VPR provides a way to describe them through a Custom RR Graph (CRR) generator. | ||
|
|
||
| Currently, the CRR Generator is only based on the tileable RR Graph. Support for the default VPR RR Graph Generator is in progress. To generate a CRR, the following files are required: | ||
|
|
||
| * Switch block map file | ||
| * Switch block template files | ||
|
|
||
| Switch Block Map File | ||
| ~~~~~~~~~~~~~~~~~~~~~~ | ||
|
|
||
| This is a YAML file that specifies which switch block template should be used for each tile. The mapping format supports the following patterns: | ||
amin1377 marked this conversation as resolved.
Show resolved
Hide resolved
|
||
|
|
||
| * ``SB_1__1_: [sb_template.csv]`` - Tile at location (1, 1) uses switch block template ``sb_template.csv`` | ||
| * ``SB_1__*_: [sb_template.csv]`` - All tiles with x coordinate 1 use switch block template ``sb_template.csv`` | ||
| * ``SB_[7,20]__[2:32:3]_: [sb_template.csv]`` - Tiles with x equal to 7 or 20, and y coordinates from 2 to 32 (inclusive) with step 3 use switch block template ``sb_template.csv`` | ||
|
|
||
| Below is an example of a switch block map file where there is no switch block at the perimeter, and DSP blocks are placed from block 2 to 10 (inclusive) with a step of 2. For all other locations, the same switch block template is used. | ||
|
|
||
| .. code-block:: yaml | ||
|
|
||
| SB_MAPS: | ||
| SB_0__0_: null | ||
| SB_1__: sb_perimeter.csv | ||
| SB1: sb_perimeter.csv | ||
| SB[2:10:2]: sb_dsp.csv | ||
| SB*_: sb_main.csv | ||
|
|
||
| **Important:** The order in which patterns are defined matters, as the first matching pattern is used. | ||
|
|
||
| Switch Block Template Files | ||
| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | ||
|
|
||
| Terminology | ||
| ----------- | ||
|
|
||
| Before describing the template files, let's define some key terminology: | ||
|
|
||
| **Lane:** A lane is a group of routing wires that shuffle only within the boundaries of their own lane region as they propagate across tiles. | ||
|
|
||
| **Tap:** A switch block location where a wire passes through and can have fan-out connections. | ||
|
|
||
| See the figure below for an illustration: | ||
|
|
||
| .. figure:: lane_and_tap.png | ||
| :alt: Lane and Tap | ||
| :align: center | ||
|
|
||
| In the figure above, the taps for the red wire are shown, and the lanes are separated by dotted lines. Note that the figure is simplified for illustration purposes. | ||
|
|
||
| In the actual RR Graph, when a wire passes through a switch block, its track number changes. Below is a more realistic example: | ||
|
|
||
| .. figure:: lane_and_tap_realistic.png | ||
| :alt: Lane and Tap Realistic | ||
| :align: center | ||
|
|
||
| A more realistic example of a lane and a tap. Each box contains a lane. | ||
|
|
||
| Template File Format | ||
| -------------------- | ||
|
|
||
| There should be a directory containing the pattern files specified in the switch block maps file. Each template is a CSV file with the following format: | ||
|
|
||
| * **Rows** represent source nodes | ||
| * **Columns** represent sink nodes | ||
| * An **'x' mark** at an intersection indicates that the source and sink nodes are connected. The delay for that connections is retrieved from the sitch type specified in the architecture file. | ||
| * A **number** at an intersection indicates that the nodes are connected with the switch delay specified by that number | ||
|
|
||
| **Note:** The pattern currently only supports uni-directional segments. Therefore, wires can only be driven from their starting point. | ||
|
|
||
| Row Headers (Source Nodes) | ||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ | ||
|
|
||
| Each row has four header columns describing the source node: | ||
|
|
||
| 1. **Column 1 - Direction:** The side from which the source node is entering the switch block (e.g., 'left', 'right', 'top', 'bottom') | ||
| 2. **Column 2 - Segment Type:** The segment length to which the source node belongs | ||
| 3. **Column 3 - Lane Number:** The lane to which the source node belongs (see terminology above) | ||
| 4. **Column 4 - Tap Number:** Which tap of the source node is at this switch block | ||
|
|
||
| Column Headers (Sink Nodes) | ||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | ||
|
|
||
| Each column has header rows describing the sink node: | ||
|
|
||
| 1. **Row 1 - Direction:** The side from which the sink node is exiting the switch block | ||
| 2. **Row 2 - Segment Type:** The segment length to which the sink node belongs | ||
| 3. **Row 3 - Fan-in:** The number of fan-ins to the sink node (optional) | ||
| 4. **Row 4 - Lane Number:** The lane to which the sink node belongs | ||
|
|
||
| *Note:* Given that currently we only support unidirectional segments, the tap is not specified because a wire can only be driven from its starting point. | ||
|
|
||
| Example | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Can you create a simpler example where you can actually show the CSV file in this documentation? I feel like it would help a lot for understanding this. I was a little confused about the meaning of "row headers" and "column headers". The overall concept makes sense (its basically an adjacency matrix), but I did not understand the headers. |
||
| ^^^^^^^ | ||
|
|
||
| Consider an architecture with a channel width of ``160`` containing only wire | ||
| segments of length ``4`` (L4). | ||
|
|
||
| The number of **rows** in the template file is computed as: | ||
|
|
||
| - ``4`` (number of sides) × ``160/2`` (number of tracks in one direction) | ||
| = ``320`` rows. | ||
|
|
||
| On each side, we have: | ||
|
|
||
| - ``20`` lanes (``80 / 4``), and | ||
| - each lane requires ``4`` rows (Lane width is equal to the segment length). | ||
|
|
||
| The number of **columns** is: | ||
|
|
||
| - ``4`` (number of sides) × ``160/2`` (number of tracks in one direction) ÷ ``4`` (starting tracks per lane) | ||
| = ``80`` columns. | ||
|
|
||
| **Note:** The reason for dividing by 4 is that only the first track of each lane can be driven from each switch location. | ||
|
|
||
| ---- | ||
|
|
||
| To illustrate how a particular cell in the template file is interpreted, assume | ||
| the following row and column specifications: | ||
|
|
||
| **Row specification:** | ||
|
|
||
| - Direction: ``left`` | ||
| - Segment type: ``l4`` | ||
| - Lane number: ``2`` | ||
| - Tap number: ``3`` | ||
|
|
||
| **Column specification:** | ||
|
|
||
| - Direction: ``right`` | ||
| - Segment type: ``l4`` | ||
| - Lane number: ``2`` | ||
|
|
||
| Assuming ``l4`` is the only segment type, the row specification corresponds to a | ||
| source wire entering the switch block from the *left* side. The starting PTC | ||
| (track) number for lane 2 is: | ||
|
|
||
| .. code-block:: none | ||
|
|
||
| (2 - 1) * 4 * 2 = 8 | ||
|
|
||
| Thus, the PTC sequence for this L4 wire is (it increases by 2 since the odd PTC numbers are used for wires coming from the other side): | ||
|
|
||
| .. code-block:: none | ||
|
|
||
| 8, 10, 12, 14 | ||
|
|
||
| The row refers to the node associated with the **third tap**, meaning the | ||
| source node corresponds to the PTC value ``12``. With the starting and ending of the track, | ||
| and the PTC values, VPR can determine the source **Node ID**. | ||
|
|
||
| For the sink node, the column specification describes a wire exiting the switch | ||
| block on the *right* side, using the same PTC sequence: | ||
|
|
||
| .. code-block:: none | ||
|
|
||
| 8, 10, 12, 14 | ||
|
|
||
| Using this sequence, VPR determines the sink **Node ID**. | ||
|
|
||
| After computing both Node IDs, the tool inserts the switch defined in the | ||
| template file, with the associated delay value, into the RR Graph. | ||
|
|
||
| ---- | ||
|
|
||
| Each switch block template file must contain the number of rows and columns | ||
| calculated in the previous section. After creating a correctly sized template | ||
| file, populate it by placing switch delay values in the cells representing valid | ||
| connections between source and sink nodes, or if you want to use the switches defined | ||
| in the architecture file, you can mark the connection with an 'x'. | ||
|
|
||
| Once the switch block map file and template files are created, include the | ||
| following arguments in the VPR command line: | ||
|
|
||
| - ``--sb_maps <switch_block_map_file>`` | ||
| - ``--sb_templates <switch_block_template_directory>`` | ||
| - ``--sb_count_dir <switch_block_count_directory>`` (optional): | ||
| If provided, VPR generates a CSV file for each switch block template, | ||
| showing how many times each switch specified in the template is used in the | ||
| final routing results. | ||
|
|
||
| For additional arguments, refer to the command-line usage section in | ||
| :ref:`vpr_command_line_usage`. | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -12,6 +12,7 @@ | |
| * | ||
| */ | ||
|
|
||
| #include <string> | ||
| #include "rr_graph_storage.h" | ||
| #include "rr_spatial_lookup.h" | ||
| #include "metadata_storage.h" | ||
|
|
@@ -289,7 +290,10 @@ class RRGraphBuilder { | |
|
|
||
| /** @brief Add a new edge to the cache of edges to be built | ||
| * @note This will not add an edge to storage. You need to call build_edges() after all the edges are cached. */ | ||
| void create_edge_in_cache(RRNodeId src, RRNodeId dest, RRSwitchId edge_switch, bool remapped); | ||
| void create_edge_in_cache(RRNodeId src, | ||
| RRNodeId dest, | ||
| RRSwitchId edge_switch, | ||
| bool remapped); | ||
|
|
||
| /** @brief Add a new edge to the cache of edges to be built | ||
| * @note This will not add an edge to storage! You need to call build_edges() after all the edges are cached! */ | ||
|
|
@@ -332,7 +336,10 @@ class RRGraphBuilder { | |
| * remap the arch switch id to rr switch id, the edge switch id of this edge shouldn't be changed. For example, when the intra-cluster graph | ||
| * is built and the rr-graph related to global resources are read from a file, this parameter is true since the intra-cluster switches are | ||
| * also listed in rr-graph file. So, we use that list to use the rr switch id instead of passing arch switch id for intra-cluster edges.*/ | ||
| inline void emplace_back_edge(RRNodeId src, RRNodeId dest, short edge_switch, bool remapped) { | ||
| inline void emplace_back_edge(RRNodeId src, | ||
| RRNodeId dest, | ||
| short edge_switch, | ||
| bool remapped) { | ||
| node_storage_.emplace_back_edge(src, dest, edge_switch, remapped); | ||
| } | ||
| /** @brief Append 1 more RR node to the RR graph. */ | ||
|
|
@@ -401,6 +408,16 @@ class RRGraphBuilder { | |
| return node_storage_.count_rr_switches(arch_switch_inf, arch_switch_fanins); | ||
| } | ||
|
|
||
| /** | ||
| * @brief Unlock storage; required to modify an routing resource graph after edge is read | ||
| * @note This function is used by OpenFPGA and currently doesn't have any use in VPR code. | ||
| */ | ||
| inline void unlock_storage() { | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think you can merge this with RRGraphBuilder::reset_rr_graph_flags. As in, same name, same functionality, reset_rr_graph_flags calls this. |
||
| node_storage_.edges_read_ = false; | ||
| node_storage_.partitioned_ = false; | ||
| node_storage_.clear_node_first_edge(); | ||
| } | ||
|
|
||
| /** @brief Reserve the lists of nodes, edges, switches etc. to be memory efficient. | ||
| * This function is mainly used to reserve memory space inside RRGraph, | ||
| * when adding a large number of nodes/edge/switches/segments, | ||
|
|
@@ -420,7 +437,6 @@ class RRGraphBuilder { | |
| node_storage_.resize(size); | ||
| } | ||
|
|
||
|
|
||
| /** @brief This function resize rr_switch to accommodate size RR Switch. */ | ||
| inline void resize_switches(size_t size) { | ||
| rr_switch_inf_.resize(size); | ||
|
|
||
Uh oh!
There was an error while loading. Please reload this page.