2727 * Date: May 16, 2012
2828 */
2929
30+ #include < unordered_map>
31+ #include < unordered_set>
3032#include < vector>
3133#include " physical_types.h"
3234#include " vtr_assert.h"
3335#include " vtr_log.h"
3436#include " vpr_types.h"
3537
36- #include " hash.h"
3738#include " cluster_feasibility_filter.h"
3839
3940/* header functions that identify pin classes */
@@ -42,18 +43,21 @@ static int get_max_depth_of_pb_graph_node(const t_pb_graph_node* pb_graph_node);
4243static void load_pin_class_by_depth (t_pb_graph_node* pb_graph_node,
4344 const int depth,
4445 int * input_count,
45- int * output_count);
46+ int * output_count,
47+ std::unordered_map<t_pb_graph_pin*, int >& pin_marker);
4648static void load_list_of_connectable_input_pin_ptrs (t_pb_graph_node* pb_graph_node);
4749static void expand_pb_graph_node_and_load_output_to_input_connections (t_pb_graph_pin* current_pb_graph_pin,
4850 t_pb_graph_pin* reference_pin,
49- const int depth);
50- static void unmark_fanout_intermediate_nodes (t_pb_graph_pin* current_pb_graph_pin);
51- static void reset_pin_class_scratch_pad_rec (t_pb_graph_node* pb_graph_node);
51+ const int depth,
52+ std::unordered_set<t_pb_graph_pin*>& seen_pins);
53+ static void unmark_fanout_intermediate_nodes (t_pb_graph_pin* current_pb_graph_pin,
54+ std::unordered_set<t_pb_graph_pin*>& seen_pins);
5255static void expand_pb_graph_node_and_load_pin_class_by_depth (t_pb_graph_pin* current_pb_graph_pin,
5356 const t_pb_graph_pin* reference_pb_graph_pin,
5457 const int depth,
5558 int * input_count,
56- int * output_count);
59+ int * output_count,
60+ std::unordered_map<t_pb_graph_pin*, int >& pin_marker);
5761static void sum_pin_class (t_pb_graph_node* pb_graph_node);
5862
5963static void discover_all_forced_connections (t_pb_graph_node* pb_graph_node);
@@ -72,12 +76,13 @@ void load_pin_classes_in_pb_graph_head(t_pb_graph_node* pb_graph_node) {
7276 depth = get_max_depth_of_pb_graph_node (pb_graph_node);
7377 for (i = 0 ; i < depth; i++) {
7478 input_count = output_count = 0 ;
75- reset_pin_class_scratch_pad_rec (pb_graph_node);
76- load_pin_class_by_depth (pb_graph_node, i, &input_count, &output_count);
79+ // The following function marks pins based on the pin count. This is
80+ // used when traversing the pb heirarchy.
81+ std::unordered_map<t_pb_graph_pin*, int > pin_marker;
82+ load_pin_class_by_depth (pb_graph_node, i, &input_count, &output_count, pin_marker);
7783 }
7884
7985 /* Load internal output-to-input connections within each cluster */
80- reset_pin_class_scratch_pad_rec (pb_graph_node);
8186 load_list_of_connectable_input_pin_ptrs (pb_graph_node);
8287 discover_all_forced_connections (pb_graph_node);
8388}
@@ -156,39 +161,12 @@ static int get_max_depth_of_pb_graph_node(const t_pb_graph_node* pb_graph_node)
156161 return max_depth;
157162}
158163
159- static void reset_pin_class_scratch_pad_rec (t_pb_graph_node* pb_graph_node) {
160- int i, j, k;
161-
162- for (i = 0 ; i < pb_graph_node->num_input_ports ; i++) {
163- for (j = 0 ; j < pb_graph_node->num_input_pins [i]; j++) {
164- pb_graph_node->input_pins [i][j].scratch_pad = UNDEFINED;
165- }
166- }
167- for (i = 0 ; i < pb_graph_node->num_output_ports ; i++) {
168- for (j = 0 ; j < pb_graph_node->num_output_pins [i]; j++) {
169- pb_graph_node->output_pins [i][j].scratch_pad = UNDEFINED;
170- }
171- }
172- for (i = 0 ; i < pb_graph_node->num_clock_ports ; i++) {
173- for (j = 0 ; j < pb_graph_node->num_clock_pins [i]; j++) {
174- pb_graph_node->clock_pins [i][j].scratch_pad = UNDEFINED;
175- }
176- }
177-
178- for (i = 0 ; i < pb_graph_node->pb_type ->num_modes ; i++) {
179- for (j = 0 ; j < pb_graph_node->pb_type ->modes [i].num_pb_type_children ; j++) {
180- for (k = 0 ; k < pb_graph_node->pb_type ->modes [i].pb_type_children [j].num_pb ; k++) {
181- reset_pin_class_scratch_pad_rec (&pb_graph_node->child_pb_graph_nodes [i][j][k]);
182- }
183- }
184- }
185- }
186-
187164/* load pin class based on limited depth */
188165static void load_pin_class_by_depth (t_pb_graph_node* pb_graph_node,
189166 const int depth,
190167 int * input_count,
191- int * output_count) {
168+ int * output_count,
169+ std::unordered_map<t_pb_graph_pin*, int >& pin_marker) {
192170 int i, j, k;
193171
194172 if (pb_graph_node->is_primitive ()) {
@@ -199,7 +177,8 @@ static void load_pin_class_by_depth(t_pb_graph_node* pb_graph_node,
199177 if (pb_graph_node->input_pins [i][j].parent_pin_class [depth] == UNDEFINED) {
200178 expand_pb_graph_node_and_load_pin_class_by_depth (&pb_graph_node->input_pins [i][j],
201179 &pb_graph_node->input_pins [i][j], depth,
202- input_count, output_count);
180+ input_count, output_count,
181+ pin_marker);
203182 (*input_count)++;
204183 }
205184 }
@@ -209,7 +188,8 @@ static void load_pin_class_by_depth(t_pb_graph_node* pb_graph_node,
209188 if (pb_graph_node->output_pins [i][j].parent_pin_class [depth] == UNDEFINED) {
210189 expand_pb_graph_node_and_load_pin_class_by_depth (&pb_graph_node->output_pins [i][j],
211190 &pb_graph_node->output_pins [i][j], depth,
212- input_count, output_count);
191+ input_count, output_count,
192+ pin_marker);
213193 (*output_count)++;
214194 }
215195 }
@@ -219,7 +199,8 @@ static void load_pin_class_by_depth(t_pb_graph_node* pb_graph_node,
219199 if (pb_graph_node->clock_pins [i][j].parent_pin_class [depth] == UNDEFINED) {
220200 expand_pb_graph_node_and_load_pin_class_by_depth (&pb_graph_node->clock_pins [i][j],
221201 &pb_graph_node->clock_pins [i][j], depth,
222- input_count, output_count);
202+ input_count, output_count,
203+ pin_marker);
223204 (*input_count)++;
224205 }
225206 }
@@ -253,7 +234,7 @@ static void load_pin_class_by_depth(t_pb_graph_node* pb_graph_node,
253234 for (j = 0 ; j < pb_graph_node->pb_type ->modes [i].num_pb_type_children ; j++) {
254235 for (k = 0 ; k < pb_graph_node->pb_type ->modes [i].pb_type_children [j].num_pb ; k++) {
255236 load_pin_class_by_depth (&pb_graph_node->child_pb_graph_nodes [i][j][k], depth,
256- input_count, output_count);
237+ input_count, output_count, pin_marker );
257238 }
258239 }
259240 }
@@ -278,14 +259,20 @@ static void load_pin_class_by_depth(t_pb_graph_node* pb_graph_node,
278259static void load_list_of_connectable_input_pin_ptrs (t_pb_graph_node* pb_graph_node) {
279260 int i, j, k;
280261
262+ // We keep track of the pins we have already seen when expanding the pb
263+ // graph.
264+ std::unordered_set<t_pb_graph_pin*> seen_pins;
265+
281266 if (pb_graph_node->is_primitive ()) {
282267 /* If this is a primitive, discover what input pins the output pins can connect to */
283268 for (i = 0 ; i < pb_graph_node->num_output_ports ; i++) {
284269 for (j = 0 ; j < pb_graph_node->num_output_pins [i]; j++) {
285270 for (k = 0 ; k < pb_graph_node->pb_type ->depth ; k++) {
286271 expand_pb_graph_node_and_load_output_to_input_connections (&pb_graph_node->output_pins [i][j],
287- &pb_graph_node->output_pins [i][j], k);
288- unmark_fanout_intermediate_nodes (&pb_graph_node->output_pins [i][j]);
272+ &pb_graph_node->output_pins [i][j], k,
273+ seen_pins);
274+ unmark_fanout_intermediate_nodes (&pb_graph_node->output_pins [i][j],
275+ seen_pins);
289276 }
290277 }
291278 }
@@ -305,16 +292,18 @@ static void load_list_of_connectable_input_pin_ptrs(t_pb_graph_node* pb_graph_no
305292 */
306293static void expand_pb_graph_node_and_load_output_to_input_connections (t_pb_graph_pin* current_pb_graph_pin,
307294 t_pb_graph_pin* reference_pin,
308- const int depth) {
295+ const int depth,
296+ std::unordered_set<t_pb_graph_pin*>& seen_pins) {
309297 int i;
310298
311- if (current_pb_graph_pin-> scratch_pad == UNDEFINED
299+ if (seen_pins. count ( current_pb_graph_pin) == 0
312300 && current_pb_graph_pin->parent_node ->pb_type ->depth > depth) {
313- current_pb_graph_pin-> scratch_pad = 1 ;
301+ seen_pins. insert ( current_pb_graph_pin) ;
314302 for (i = 0 ; i < current_pb_graph_pin->num_output_edges ; i++) {
315303 VTR_ASSERT (current_pb_graph_pin->output_edges [i]->num_output_pins == 1 );
316304 expand_pb_graph_node_and_load_output_to_input_connections (current_pb_graph_pin->output_edges [i]->output_pins [0 ],
317- reference_pin, depth);
305+ reference_pin, depth,
306+ seen_pins);
318307 }
319308 if (current_pb_graph_pin->is_primitive_pin ()
320309 && current_pb_graph_pin->port ->type == IN_PORT) {
@@ -343,15 +332,17 @@ static void expand_pb_graph_node_and_load_output_to_input_connections(t_pb_graph
343332}
344333
345334/* *
346- * Clear scratch_pad for all fanout of pin
335+ * Mark all fanout of pin as un-seen.
347336 */
348- static void unmark_fanout_intermediate_nodes (t_pb_graph_pin* current_pb_graph_pin) {
337+ static void unmark_fanout_intermediate_nodes (t_pb_graph_pin* current_pb_graph_pin,
338+ std::unordered_set<t_pb_graph_pin*>& seen_pins) {
349339 int i;
350- if (current_pb_graph_pin-> scratch_pad != UNDEFINED ) {
351- current_pb_graph_pin-> scratch_pad = UNDEFINED ;
340+ if (seen_pins. count ( current_pb_graph_pin) != 0 ) {
341+ seen_pins. erase ( current_pb_graph_pin) ;
352342 for (i = 0 ; i < current_pb_graph_pin->num_output_edges ; i++) {
353343 VTR_ASSERT (current_pb_graph_pin->output_edges [i]->num_output_pins == 1 );
354- unmark_fanout_intermediate_nodes (current_pb_graph_pin->output_edges [i]->output_pins [0 ]);
344+ unmark_fanout_intermediate_nodes (current_pb_graph_pin->output_edges [i]->output_pins [0 ],
345+ seen_pins);
355346 }
356347 }
357348}
@@ -363,7 +354,8 @@ static void expand_pb_graph_node_and_load_pin_class_by_depth(t_pb_graph_pin* cur
363354 const t_pb_graph_pin* reference_pb_graph_pin,
364355 const int depth,
365356 int * input_count,
366- int * output_count) {
357+ int * output_count,
358+ std::unordered_map<t_pb_graph_pin*, int >& pin_marker) {
367359 int i;
368360 int marker;
369361 int active_pin_class;
@@ -378,9 +370,9 @@ static void expand_pb_graph_node_and_load_pin_class_by_depth(t_pb_graph_pin* cur
378370 VTR_ASSERT (reference_pb_graph_pin->is_primitive_pin ());
379371 VTR_ASSERT (current_pb_graph_pin->parent_node ->pb_type ->depth >= depth);
380372 VTR_ASSERT (current_pb_graph_pin->port ->type != INOUT_PORT);
381- if (current_pb_graph_pin-> scratch_pad != marker) {
373+ if (pin_marker. count ( current_pb_graph_pin) == 0 || pin_marker[current_pb_graph_pin] != marker) {
382374 if (current_pb_graph_pin->is_primitive_pin ()) {
383- current_pb_graph_pin-> scratch_pad = marker;
375+ pin_marker[ current_pb_graph_pin] = marker;
384376 /* This is a primitive, determine what pins cans share the same pin class as the reference pin */
385377 if (current_pb_graph_pin->parent_pin_class [depth] == UNDEFINED
386378 && reference_pb_graph_pin->port ->is_clock == current_pb_graph_pin->port ->is_clock
@@ -391,16 +383,16 @@ static void expand_pb_graph_node_and_load_pin_class_by_depth(t_pb_graph_pin* cur
391383 VTR_ASSERT (current_pb_graph_pin->input_edges [i]->num_input_pins == 1 );
392384 expand_pb_graph_node_and_load_pin_class_by_depth (current_pb_graph_pin->input_edges [i]->input_pins [0 ],
393385 reference_pb_graph_pin, depth, input_count,
394- output_count);
386+ output_count, pin_marker );
395387 }
396388 for (i = 0 ; i < current_pb_graph_pin->num_output_edges ; i++) {
397389 VTR_ASSERT (current_pb_graph_pin->output_edges [i]->num_output_pins == 1 );
398390 expand_pb_graph_node_and_load_pin_class_by_depth (current_pb_graph_pin->output_edges [i]->output_pins [0 ],
399391 reference_pb_graph_pin, depth, input_count,
400- output_count);
392+ output_count, pin_marker );
401393 }
402394 } else if (current_pb_graph_pin->parent_node ->pb_type ->depth == depth) {
403- current_pb_graph_pin-> scratch_pad = marker;
395+ pin_marker[ current_pb_graph_pin] = marker;
404396 if (current_pb_graph_pin->port ->type == OUT_PORT) {
405397 if (reference_pb_graph_pin->port ->type == OUT_PORT) {
406398 /* This cluster's output pin can be driven by primitive outputs belonging to this pin class */
@@ -410,7 +402,7 @@ static void expand_pb_graph_node_and_load_pin_class_by_depth(t_pb_graph_pin* cur
410402 VTR_ASSERT (current_pb_graph_pin->input_edges [i]->num_input_pins == 1 );
411403 expand_pb_graph_node_and_load_pin_class_by_depth (current_pb_graph_pin->input_edges [i]->input_pins [0 ],
412404 reference_pb_graph_pin, depth, input_count,
413- output_count);
405+ output_count, pin_marker );
414406 }
415407 }
416408 if (current_pb_graph_pin->port ->type == IN_PORT) {
@@ -422,23 +414,23 @@ static void expand_pb_graph_node_and_load_pin_class_by_depth(t_pb_graph_pin* cur
422414 VTR_ASSERT (current_pb_graph_pin->output_edges [i]->num_output_pins == 1 );
423415 expand_pb_graph_node_and_load_pin_class_by_depth (current_pb_graph_pin->output_edges [i]->output_pins [0 ],
424416 reference_pb_graph_pin, depth, input_count,
425- output_count);
417+ output_count, pin_marker );
426418 }
427419 }
428420 } else if (current_pb_graph_pin->parent_node ->pb_type ->depth > depth) {
429421 /* Inside an intermediate cluster, traverse to either a primitive or to the cluster we're interested in populating */
430- current_pb_graph_pin-> scratch_pad = marker;
422+ pin_marker[ current_pb_graph_pin] = marker;
431423 for (i = 0 ; i < current_pb_graph_pin->num_input_edges ; i++) {
432424 VTR_ASSERT (current_pb_graph_pin->input_edges [i]->num_input_pins == 1 );
433425 expand_pb_graph_node_and_load_pin_class_by_depth (current_pb_graph_pin->input_edges [i]->input_pins [0 ],
434426 reference_pb_graph_pin, depth, input_count,
435- output_count);
427+ output_count, pin_marker );
436428 }
437429 for (i = 0 ; i < current_pb_graph_pin->num_output_edges ; i++) {
438430 VTR_ASSERT (current_pb_graph_pin->output_edges [i]->num_output_pins == 1 );
439431 expand_pb_graph_node_and_load_pin_class_by_depth (current_pb_graph_pin->output_edges [i]->output_pins [0 ],
440432 reference_pb_graph_pin, depth, input_count,
441- output_count);
433+ output_count, pin_marker );
442434 }
443435 }
444436 }
0 commit comments