22
22
#include " vtr_assert.h"
23
23
#include " vtr_log.h"
24
24
25
+ namespace {
26
+
27
+ /* *
28
+ * @brief Enumeration for the state of the packer.
29
+ *
30
+ * If the packer fails to find a dense enough packing, depending on how the
31
+ * packer failed, the packer may iteratively retry packing with different
32
+ * settings to try and find a denser packing. These states represent a
33
+ * different type of iteration.
34
+ */
35
+ enum class e_packer_state {
36
+ // / @brief Default packer state.
37
+ DEFAULT,
38
+ // / @brief Succcess state for the packer. The packing looks feasible to
39
+ // / fit on the device (does not exceed number of blocks of each
40
+ // / type in the grid) and meets floorplanning constraints.
41
+ SUCCESS,
42
+ // / @brief Standard fallback where there are no region constraints. Turns
43
+ // / on unrelated clustering and balanced packing if it can.
44
+ UNRELATED_AND_BALANCED,
45
+ // / @brief Region constraints: Turns on attraction groups for overfilled regions.
46
+ ATTRACTION_GROUPS,
47
+ // / @brief Region constraints: Turns on more attraction groups for overfilled regions.
48
+ MORE_ATTRACTION_GROUPS,
49
+ // / @brief Region constraints: Turns on more attraction groups for all regions.
50
+ ATTRACTION_GROUPS_ALL_REGIONS,
51
+ // / @brief Region constraints: Turns on more attraction groups for all regions
52
+ // / and increases the target density of "clb" blocks.
53
+ // / TODO: This should increase the target density of all overused blocks.
54
+ ATTRACTION_GROUPS_ALL_REGIONS_AND_INCREASED_TARGET_DENSITY,
55
+ // / @brief The failure state.
56
+ FAILURE
57
+ };
58
+
59
+ } // namespace
60
+
25
61
static bool try_size_device_grid (const t_arch& arch,
26
62
const std::map<t_logical_block_type_ptr, size_t >& num_type_instances,
27
63
float target_device_utilization,
28
64
const std::string& device_layout_name);
29
65
66
+ /* *
67
+ * @brief The packer iteratively re-packes the netlist if it fails to find a
68
+ * valid clustering. Each iteration is a state the packer is in, where
69
+ * each state uses a different set of options. This method gets the next
70
+ * state of the packer given the current state of the packer.
71
+ *
72
+ * @param current_packer_state
73
+ * The current state of the packer (the state used to make the most recent
74
+ * clustering).
75
+ * @param fits_on_device
76
+ * Whether the current clustering fits on the device or not.
77
+ * @param floorplan_regions_overfull
78
+ * Whether the current clustering has overfilled regions.
79
+ * @param floorplan_not_fitting
80
+ * Whether the current clustering is fitting on the current floorplan.
81
+ */
82
+ static e_packer_state get_next_packer_state (e_packer_state current_packer_state,
83
+ bool fits_on_device,
84
+ bool floorplan_regions_overfull,
85
+ bool floorplan_not_fitting) {
86
+ // Next packer state logic
87
+ e_packer_state next_packer_state = e_packer_state::FAILURE;
88
+ if (fits_on_device && !floorplan_regions_overfull) {
89
+ // If everything fits on the device and the floorplan regions are
90
+ // not overfilled, the next state is success.
91
+ next_packer_state = e_packer_state::SUCCESS;
92
+ } else {
93
+ if (floorplan_not_fitting) {
94
+ // If there are overfilled region constraints.
95
+
96
+ // When running with tight floorplan constraints, some regions may become overfull with clusters (i.e.
97
+ // the number of blocks assigned to the region exceeds the number of blocks available). When this occurs, we
98
+ // cluster more densely to be able to adhere to the floorplan constraints. However, we do not want to cluster more
99
+ // densely unnecessarily, as this can negatively impact wirelength. So, we have iterative approach. We check at the end
100
+ // of every iteration if any floorplan regions are overfull. In the first iteration, we run
101
+ // with no attraction groups (not packing more densely). If regions are overfull at the end of the first iteration,
102
+ // we create attraction groups for partitions with overfull regions (pack those atoms more densely). We continue this way
103
+ // until the last iteration, when we create attraction groups for every partition, if needed.
104
+
105
+ switch (current_packer_state) {
106
+ case e_packer_state::DEFAULT:
107
+ next_packer_state = e_packer_state::ATTRACTION_GROUPS;
108
+ break ;
109
+ case e_packer_state::UNRELATED_AND_BALANCED:
110
+ case e_packer_state::ATTRACTION_GROUPS:
111
+ next_packer_state = e_packer_state::MORE_ATTRACTION_GROUPS;
112
+ break ;
113
+ case e_packer_state::MORE_ATTRACTION_GROUPS:
114
+ next_packer_state = e_packer_state::ATTRACTION_GROUPS_ALL_REGIONS;
115
+ break ;
116
+ case e_packer_state::ATTRACTION_GROUPS_ALL_REGIONS:
117
+ next_packer_state = e_packer_state::ATTRACTION_GROUPS_ALL_REGIONS_AND_INCREASED_TARGET_DENSITY;
118
+ break ;
119
+ case e_packer_state::ATTRACTION_GROUPS_ALL_REGIONS_AND_INCREASED_TARGET_DENSITY:
120
+ default :
121
+ next_packer_state = e_packer_state::FAILURE;
122
+ break ;
123
+ }
124
+ } else {
125
+ // If there are no overfilled region constraints, but some block
126
+ // types on the grid are overfilled.
127
+ switch (current_packer_state) {
128
+ case e_packer_state::DEFAULT:
129
+ next_packer_state = e_packer_state::UNRELATED_AND_BALANCED;
130
+ break ;
131
+ default :
132
+ next_packer_state = e_packer_state::FAILURE;
133
+ break ;
134
+ }
135
+ }
136
+ }
137
+
138
+ return next_packer_state;
139
+ }
140
+
30
141
bool try_pack (const t_packer_opts& packer_opts,
31
142
const t_analysis_opts& analysis_opts,
32
143
const t_ap_opts& ap_opts,
@@ -145,35 +256,6 @@ bool try_pack(const t_packer_opts& packer_opts,
145
256
146
257
g_vpr_ctx.mutable_atom ().mutable_lookup ().set_atom_pb_bimap_lock (true );
147
258
148
- /* *
149
- * @brief Enumeration for the state of the packer.
150
- *
151
- * If the packer fails to find a dense enough packing, depending on how the
152
- * packer failed, the packer may iteratively retry packing with different
153
- * setting to try and find a denser packing. These states represent a
154
- * different type of iteration.
155
- */
156
- enum class e_packer_state {
157
- // / @brief Default packer state.
158
- DEFAULT,
159
- // / @brief Succcess state for the packer.
160
- SUCCESS,
161
- // / @brief Standard fallback where there is not region constraints. Turns
162
- // / on unrelated clustering and balanced packing if it can.
163
- UNRELATED_AND_BALANCED,
164
- // / @brief Region constraints: Turns on attraction groups for overfilled regions.
165
- ATTRACTION_GROUPS,
166
- // / @brief Region constraints: Turns on more attraction groups for overfilled regions.
167
- MORE_ATTRACTION_GROUPS,
168
- // / @brief Region constraints: Turns on more attraction groups for all regions.
169
- ATTRACTION_GROUPS_ALL_REGIONS,
170
- // / @brief Region constraints: Turns on more attraction groups for all regions
171
- // / and increases the target density of clb blocks.
172
- ATTRACTION_GROUPS_ALL_REGIONS_AND_INCREASED_TARGET_DENSITY,
173
- // / @brief The failure state.
174
- FAILURE
175
- };
176
-
177
259
// The current state of the packer during iterative packing.
178
260
e_packer_state current_packer_state = e_packer_state::DEFAULT;
179
261
@@ -189,7 +271,7 @@ bool try_pack(const t_packer_opts& packer_opts,
189
271
attraction_groups,
190
272
mutable_device_ctx);
191
273
192
- // Try to size/find a device
274
+ // Try to size/find a device
193
275
bool fits_on_device = try_size_device_grid (arch, num_used_type_instances, packer_opts.target_device_utilization , packer_opts.device_layout );
194
276
195
277
/* We use this bool to determine the cause for the clustering not being dense enough. If the clustering
@@ -203,62 +285,20 @@ bool try_pack(const t_packer_opts& packer_opts,
203
285
bool floorplan_not_fitting = (floorplan_regions_overfull || g_vpr_ctx.floorplanning ().constraints .get_num_partitions () > 0 );
204
286
205
287
// Next packer state logic
206
- e_packer_state next_packer_state = e_packer_state::FAILURE;
207
- if (fits_on_device && !floorplan_regions_overfull) {
208
- // If everything fits on the device and the floorplan regions are
209
- // not overfilled, the next state is success.
210
- next_packer_state = e_packer_state::SUCCESS;
211
- } else {
212
- if (floorplan_not_fitting) {
213
- // If there are overfilled region constraints.
214
- /*
215
- * When running with tight floorplan constraints, some regions may become overfull with clusters (i.e.
216
- * the number of blocks assigned to the region exceeds the number of blocks available). When this occurs, we
217
- * cluster more densely to be able to adhere to the floorplan constraints. However, we do not want to cluster more
218
- * densely unnecessarily, as this can negatively impact wirelength. So, we have iterative approach. We check at the end
219
- * of every iteration if any floorplan regions are overfull. In the first iteration, we run
220
- * with no attraction groups (not packing more densely). If regions are overfull at the end of the first iteration,
221
- * we create attraction groups for partitions with overfull regions (pack those atoms more densely). We continue this way
222
- * until the last iteration, when we create attraction groups for every partition, if needed.
223
- */
224
- switch (current_packer_state) {
225
- case e_packer_state::DEFAULT:
226
- next_packer_state = e_packer_state::ATTRACTION_GROUPS;
227
- break ;
228
- case e_packer_state::UNRELATED_AND_BALANCED:
229
- case e_packer_state::ATTRACTION_GROUPS:
230
- next_packer_state = e_packer_state::MORE_ATTRACTION_GROUPS;
231
- break ;
232
- case e_packer_state::MORE_ATTRACTION_GROUPS:
233
- next_packer_state = e_packer_state::ATTRACTION_GROUPS_ALL_REGIONS;
234
- break ;
235
- case e_packer_state::ATTRACTION_GROUPS_ALL_REGIONS:
236
- next_packer_state = e_packer_state::ATTRACTION_GROUPS_ALL_REGIONS_AND_INCREASED_TARGET_DENSITY;
237
- break ;
238
- case e_packer_state::ATTRACTION_GROUPS_ALL_REGIONS_AND_INCREASED_TARGET_DENSITY:
239
- default :
240
- next_packer_state = e_packer_state::FAILURE;
241
- break ;
242
- }
243
- } else {
244
- // If there are no overfilled region constraints.
245
- switch (current_packer_state) {
246
- case e_packer_state::DEFAULT:
247
- next_packer_state = e_packer_state::UNRELATED_AND_BALANCED;
248
- break ;
249
- default :
250
- next_packer_state = e_packer_state::FAILURE;
251
- break ;
252
- }
253
- }
254
- }
255
-
256
- // Set up for the next packer state.
288
+ e_packer_state next_packer_state = get_next_packer_state (current_packer_state,
289
+ fits_on_device,
290
+ floorplan_regions_overfull,
291
+ floorplan_not_fitting);
292
+
293
+ // Set up for the options used for the next packer state.
294
+ // NOTE: This must be done here (and not at the start of the next packer
295
+ // iteration) since we need to know information about the current
296
+ // clustering to change the options for the next iteration.
257
297
switch (next_packer_state) {
258
298
case e_packer_state::UNRELATED_AND_BALANCED: {
259
- // 1st pack attempt was unsuccessful (i.e. not dense enough) and we have control of unrelated clustering
299
+ // 1st pack attempt was unsuccessful (i.e. not dense enough) and we have control of unrelated clustering
260
300
//
261
- // Turn it on to increase packing density
301
+ // Turn it on to increase packing density
262
302
// TODO: This will have no affect if unrelated clustering and
263
303
// balance block type utilization is not auto. Should update
264
304
// the next state logic.
@@ -348,7 +388,7 @@ bool try_pack(const t_packer_opts& packer_opts,
348
388
349
389
// If the packer was unsuccessful, reset the packed solution and try again.
350
390
if (next_packer_state != e_packer_state::SUCCESS) {
351
- // Reset floorplanning constraints for re-packing
391
+ // Reset floorplanning constraints for re-packing
352
392
g_vpr_ctx.mutable_floorplanning ().cluster_constraints .clear ();
353
393
354
394
// Reset the cluster legalizer for re-clustering.
0 commit comments