SRC/route_export.h File Reference

This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Functions

boolean try_route (int width_fac, struct s_router_opts router_opts, struct s_det_routing_arch det_routing_arch, t_segment_inf *segment_inf, t_timing_inf timing_inf, float **net_slack, float **net_delay, t_chan_width_dist chan_width_dist, t_ivec **fb_opins_used_locally, t_mst_edge **mst, boolean *Fc_clipped)
boolean feasible_routing (void)
t_ivec ** alloc_route_structs (t_subblock_data subblock_data)
void free_route_structs (t_ivec **fb_opins_used_locally)
struct s_trace ** alloc_saved_routing (t_ivec **fb_opins_used_locally, t_ivec ***saved_clb_opins_used_locally_ptr)
void free_saved_routing (struct s_trace **best_routing, t_ivec **saved_clb_opins_used_locally)
void save_routing (struct s_trace **best_routing, t_ivec **fb_opins_used_locally, t_ivec **saved_clb_opins_used_locally)
void restore_routing (struct s_trace **best_routing, t_ivec **fb_opins_used_locally, t_ivec **saved_clb_opins_used_locally)
void get_serial_num (void)
void print_route (char *name)

Function Documentation

t_ivec** alloc_route_structs ( t_subblock_data  subblock_data  ) 

Definition at line 703 of file route_common.c.

00704 {
00705 
00706 /* Allocates the data structures needed for routing.    */
00707 
00708     t_ivec **fb_opins_used_locally;
00709 
00710     trace_head = (struct s_trace **)my_calloc(num_nets,
00711                                               sizeof(struct s_trace *));
00712     trace_tail = (struct s_trace **)my_malloc(num_nets *
00713                                               sizeof(struct s_trace *));
00714 
00715     heap_size = nx * ny;
00716     heap = (struct s_heap **)my_malloc(heap_size * sizeof(struct s_heap *));
00717     heap--;                     /* heap stores from [1..heap_size] */
00718     heap_tail = 1;
00719 
00720     route_bb = (struct s_bb *)my_malloc(num_nets * sizeof(struct s_bb));
00721 
00722     fb_opins_used_locally =
00723         alloc_and_load_clb_opins_used_locally(subblock_data);
00724 
00725     return (fb_opins_used_locally);
00726 }

Here is the call graph for this function:

Here is the caller graph for this function:

struct s_trace** alloc_saved_routing ( t_ivec **  fb_opins_used_locally,
t_ivec ***  saved_clb_opins_used_locally_ptr 
) [read]

Definition at line 730 of file route_common.c.

00732 {
00733 
00734 /* Allocates data structures into which the key routing data can be saved,   *
00735  * allowing the routing to be recovered later (e.g. after a another routing  *
00736  * is attempted).                                                            */
00737 
00738     struct s_trace **best_routing;
00739     t_ivec **saved_clb_opins_used_locally;
00740     int iblk, iclass, num_local_opins;
00741     t_type_ptr type;
00742 
00743     best_routing = (struct s_trace **)my_calloc(num_nets,
00744                                                 sizeof(struct s_trace *));
00745 
00746     saved_clb_opins_used_locally =
00747         (t_ivec **) my_malloc(num_blocks * sizeof(t_ivec *));
00748 
00749     for(iblk = 0; iblk < num_blocks; iblk++)
00750         {
00751             type = block[iblk].type;
00752             saved_clb_opins_used_locally[iblk] =
00753                 (t_ivec *) my_malloc(type->num_class * sizeof(t_ivec));
00754             for(iclass = 0; iclass < type->num_class; iclass++)
00755                 {
00756                     num_local_opins =
00757                         fb_opins_used_locally[iblk][iclass].nelem;
00758                     saved_clb_opins_used_locally[iblk][iclass].nelem =
00759                         num_local_opins;
00760 
00761                     if(num_local_opins == 0)
00762                         {
00763                             saved_clb_opins_used_locally[iblk][iclass].list =
00764                                 NULL;
00765                         }
00766                     else
00767                         {
00768                             saved_clb_opins_used_locally[iblk][iclass].list =
00769                                 (int *)my_malloc(num_local_opins *
00770                                                  sizeof(int));
00771                         }
00772                 }
00773         }
00774 
00775     *saved_clb_opins_used_locally_ptr = saved_clb_opins_used_locally;
00776     return (best_routing);
00777 }

Here is the call graph for this function:

Here is the caller graph for this function:

boolean feasible_routing ( void   ) 

Definition at line 337 of file route_common.c.

00338 {
00339 
00340 /* This routine checks to see if this is a resource-feasible routing.      *
00341  * That is, are all rr_node capacity limitations respected?  It assumes    *
00342  * that the occupancy arrays are up to date when it is called.             */
00343 
00344     int inode;
00345 
00346     for(inode = 0; inode < num_rr_nodes; inode++)
00347         if(rr_node[inode].occ > rr_node[inode].capacity)
00348             return (FALSE);
00349 
00350     return (TRUE);
00351 }

Here is the caller graph for this function:

void free_route_structs ( t_ivec **  fb_opins_used_locally  ) 

Definition at line 864 of file route_common.c.

00865 {
00866 
00867 /* Frees the temporary storage needed only during the routing.  The  *
00868  * final routing result is not freed.                                */
00869     int i;
00870 
00871     free(heap + 1);
00872     free(route_bb);
00873 
00874     heap = NULL;                /* Defensive coding:  crash hard if I use these. */
00875     route_bb = NULL;
00876 
00877     for(i = 0; i < num_blocks; i++)
00878         {
00879             free_ivec_vector(fb_opins_used_locally[i], 0,
00880                              block[i].type->num_class - 1);
00881         }
00882     free(fb_opins_used_locally);
00883 
00884 /* NB:  Should use my chunk_malloc for tptr, hptr, and mod_ptr structures. *
00885  * I could free everything except the tptrs at the end then.               */
00886 
00887 }

Here is the call graph for this function:

Here is the caller graph for this function:

void free_saved_routing ( struct s_trace **  best_routing,
t_ivec **  saved_clb_opins_used_locally 
)

Definition at line 891 of file route_common.c.

00893 {
00894 
00895 /* Frees the data structures needed to save a routing.                     */
00896     int i;
00897 
00898     free(best_routing);
00899     for(i = 0; i < num_blocks; i++)
00900         {
00901             free_ivec_vector(saved_clb_opins_used_locally[i], 0,
00902                              block[i].type->num_class - 1);
00903         }
00904     free(saved_clb_opins_used_locally);
00905 }

Here is the call graph for this function:

Here is the caller graph for this function:

void get_serial_num ( void   ) 

Definition at line 210 of file route_common.c.

00211 {
00212 
00213 /* This routine finds a "magic cookie" for the routing and prints it.    *
00214  * Use this number as a routing serial number to ensure that programming *
00215  * changes do not break the router.                                      */
00216 
00217     int inet, serial_num, inode;
00218     struct s_trace *tptr;
00219 
00220     serial_num = 0;
00221 
00222     for(inet = 0; inet < num_nets; inet++)
00223         {
00224 
00225 /* Global nets will have null trace_heads (never routed) so they *
00226  * are not included in the serial number calculation.            */
00227 
00228             tptr = trace_head[inet];
00229             while(tptr != NULL)
00230                 {
00231                     inode = tptr->index;
00232                     serial_num +=
00233                         (inet + 1) * (rr_node[inode].xlow * (nx + 1) -
00234                                       rr_node[inode].yhigh);
00235 
00236                     serial_num -= rr_node[inode].ptc_num * (inet + 1) * 10;
00237 
00238                     serial_num -= rr_node[inode].type * (inet + 1) * 100;
00239                     serial_num %= 2000000000;   /* Prevent overflow */
00240                     tptr = tptr->next;
00241                 }
00242         }
00243     printf("Serial number (magic cookie) for the routing is: %d\n",
00244            serial_num);
00245 }

Here is the caller graph for this function:

void print_route ( char *  name  ) 

Definition at line 1288 of file route_common.c.

01289 {
01290 
01291 /* Prints out the routing to file route_file.  */
01292 
01293     int inet, inode, ipin, bnum, ilow, jlow, node_block_pin, iclass;
01294     t_rr_type rr_type;
01295     struct s_trace *tptr;
01296     char *name_type[] =
01297         { "SOURCE", "SINK", "IPIN", "OPIN", "CHANX", "CHANY" };
01298     FILE *fp;
01299 
01300     fp = my_fopen(route_file, "w");
01301 
01302     fprintf(fp, "Array size: %d x %d logic blocks.\n", nx, ny);
01303     fprintf(fp, "\nRouting:");
01304     for(inet = 0; inet < num_nets; inet++)
01305         {
01306             if(net[inet].is_global == FALSE)
01307                 {
01308                     fprintf(fp, "\n\nNet %d (%s)\n\n", inet, net[inet].name);
01309                     tptr = trace_head[inet];
01310 
01311                     while(tptr != NULL)
01312                         {
01313                             inode = tptr->index;
01314                             rr_type = rr_node[inode].type;
01315                             ilow = rr_node[inode].xlow;
01316                             jlow = rr_node[inode].ylow;
01317 
01318                             fprintf(fp, "%6s (%d,%d) ", name_type[rr_type],
01319                                     ilow, jlow);
01320 
01321                             if((ilow != rr_node[inode].xhigh) || (jlow !=
01322                                                                   rr_node
01323                                                                   [inode].
01324                                                                   yhigh))
01325                                 fprintf(fp, "to (%d,%d) ",
01326                                         rr_node[inode].xhigh,
01327                                         rr_node[inode].yhigh);
01328 
01329                             switch (rr_type)
01330                                 {
01331 
01332                                 case IPIN:
01333                                 case OPIN:
01334                                     if(grid[ilow][jlow].type == IO_TYPE)
01335                                         {
01336                                             fprintf(fp, " Pad: ");
01337                                         }
01338                                     else
01339                                         {       /* IO Pad. */
01340                                             fprintf(fp, " Pin: ");
01341                                         }
01342                                     break;
01343 
01344                                 case CHANX:
01345                                 case CHANY:
01346                                     fprintf(fp, " Track: ");
01347                                     break;
01348 
01349                                 case SOURCE:
01350                                 case SINK:
01351                                     if(grid[ilow][jlow].type == IO_TYPE)
01352                                         {
01353                                             fprintf(fp, " Pad: ");
01354                                         }
01355                                     else
01356                                         {       /* IO Pad. */
01357                                             fprintf(fp, " Class: ");
01358                                         }
01359                                     break;
01360 
01361                                 default:
01362                                     printf
01363                                         ("Error in print_route:  Unexpected traceback element "
01364                                          "type: %d (%s).\n", rr_type,
01365                                          name_type[rr_type]);
01366                                     exit(1);
01367                                     break;
01368                                 }
01369 
01370                             fprintf(fp, "%d  ", rr_node[inode].ptc_num);
01371 
01372 /* Uncomment line below if you're debugging and want to see the switch types *
01373  * used in the routing.                                                      */
01374 /*          fprintf (fp, "Switch: %d", tptr->iswitch);    */
01375 
01376                             fprintf(fp, "\n");
01377 
01378                             tptr = tptr->next;
01379                         }
01380                 }
01381 
01382             else
01383                 {               /* Global net.  Never routed. */
01384                     fprintf(fp, "\n\nNet %d (%s): global net connecting:\n\n",
01385                             inet, net[inet].name);
01386 
01387                     for(ipin = 0; ipin <= net[inet].num_sinks; ipin++)
01388                         {
01389                             bnum = net[inet].node_block[ipin];
01390 
01391                             node_block_pin = net[inet].node_block_pin[ipin];
01392                             iclass =
01393                                 block[bnum].type->pin_class[node_block_pin];
01394 
01395                             fprintf(fp,
01396                                     "Block %s (#%d) at (%d, %d), Pin class %d.\n",
01397                                     block[bnum].name, bnum, block[bnum].x,
01398                                     block[bnum].y, iclass);
01399                         }
01400                 }
01401         }
01402 
01403     fclose(fp);
01404 
01405 #ifdef CREATE_ECHO_FILES
01406     fp = my_fopen("mem.echo", "w");
01407     fprintf(fp, "\nNum_heap_allocated: %d   Num_trace_allocated: %d\n",
01408             num_heap_allocated, num_trace_allocated);
01409     fprintf(fp, "Num_linked_f_pointer_allocated: %d\n",
01410             num_linked_f_pointer_allocated);
01411     fclose(fp);
01412 #endif /* CREATE_ECHO_FILES */
01413 
01414 }

Here is the call graph for this function:

Here is the caller graph for this function:

void restore_routing ( struct s_trace **  best_routing,
t_ivec **  fb_opins_used_locally,
t_ivec **  saved_clb_opins_used_locally 
)

Definition at line 162 of file route_common.c.

00165 {
00166 
00167 /* Deallocates any current routing in trace_head, and replaces it with    *
00168  * the routing in best_routing.  Best_routing is set to NULL to show that *
00169  * it no longer points to a valid routing.  NOTE:  trace_tail is not      *
00170  * restored -- it is set to all NULLs since it is only used in            *
00171  * update_traceback.  If you need trace_tail restored, modify this        *
00172  * routine.  Also restores the locally used opin data.                    */
00173 
00174     int inet, iblk, ipin, iclass, num_local_opins;
00175     t_type_ptr type;
00176 
00177     for(inet = 0; inet < num_nets; inet++)
00178         {
00179 
00180             /* Free any current routing. */
00181             free_traceback(inet);
00182 
00183             /* Set the current routing to the saved one. */
00184             trace_head[inet] = best_routing[inet];
00185             best_routing[inet] = NULL;  /* No stored routing. */
00186         }
00187 
00188 /* Save which OPINs are locally used.                           */
00189 
00190     for(iblk = 0; iblk < num_blocks; iblk++)
00191         {
00192             type = block[iblk].type;
00193             for(iclass = 0; iclass < type->num_class; iclass++)
00194                 {
00195                     num_local_opins =
00196                         fb_opins_used_locally[iblk][iclass].nelem;
00197                     for(ipin = 0; ipin < num_local_opins; ipin++)
00198                         {
00199                             fb_opins_used_locally[iblk][iclass].list[ipin] =
00200                                 saved_clb_opins_used_locally[iblk][iclass].
00201                                 list[ipin];
00202                         }
00203                 }
00204 
00205         }
00206 }

Here is the call graph for this function:

Here is the caller graph for this function:

void save_routing ( struct s_trace **  best_routing,
t_ivec **  fb_opins_used_locally,
t_ivec **  saved_clb_opins_used_locally 
)

Definition at line 101 of file route_common.c.

00104 {
00105 
00106 /* This routing frees any routing currently held in best routing,       *
00107  * then copies over the current routing (held in trace_head), and       *
00108  * finally sets trace_head and trace_tail to all NULLs so that the      *
00109  * connection to the saved routing is broken.  This is necessary so     *
00110  * that the next iteration of the router does not free the saved        *
00111  * routing elements.  Also saves any data about locally used clb_opins, *
00112  * since this is also part of the routing.                              */
00113 
00114     int inet, iblk, iclass, ipin, num_local_opins;
00115     struct s_trace *tptr, *tempptr;
00116     t_type_ptr type;
00117 
00118     for(inet = 0; inet < num_nets; inet++)
00119         {
00120 
00121 /* Free any previously saved routing.  It is no longer best. */
00122             tptr = best_routing[inet];
00123             while(tptr != NULL)
00124                 {
00125                     tempptr = tptr->next;
00126                     free_trace_data(tptr);
00127                     tptr = tempptr;
00128                 }
00129 
00130 /* Save a pointer to the current routing in best_routing. */
00131             best_routing[inet] = trace_head[inet];
00132 
00133 /* Set the current (working) routing to NULL so the current trace       *
00134  * elements won't be reused by the memory allocator.                    */
00135 
00136             trace_head[inet] = NULL;
00137             trace_tail[inet] = NULL;
00138         }
00139 
00140 /* Save which OPINs are locally used.                           */
00141 
00142     for(iblk = 0; iblk < num_blocks; iblk++)
00143         {
00144             type = block[iblk].type;
00145             for(iclass = 0; iclass < type->num_class; iclass++)
00146                 {
00147                     num_local_opins =
00148                         fb_opins_used_locally[iblk][iclass].nelem;
00149                     for(ipin = 0; ipin < num_local_opins; ipin++)
00150                         {
00151                             saved_clb_opins_used_locally[iblk][iclass].
00152                                 list[ipin] =
00153                                 fb_opins_used_locally[iblk][iclass].
00154                                 list[ipin];
00155                         }
00156                 }
00157         }
00158 }

Here is the call graph for this function:

Here is the caller graph for this function:

boolean try_route ( int  width_fac,
struct s_router_opts  router_opts,
struct s_det_routing_arch  det_routing_arch,
t_segment_inf segment_inf,
t_timing_inf  timing_inf,
float **  net_slack,
float **  net_delay,
t_chan_width_dist  chan_width_dist,
t_ivec **  fb_opins_used_locally,
t_mst_edge **  mst,
boolean Fc_clipped 
)

Definition at line 249 of file route_common.c.

00260 {
00261 
00262 /* Attempts a routing via an iterated maze router algorithm.  Width_fac *
00263  * specifies the relative width of the channels, while the members of   *
00264  * router_opts determine the value of the costs assigned to routing     *
00265  * resource node, etc.  det_routing_arch describes the detailed routing *
00266  * architecture (connection and switch boxes) of the FPGA; it is used   *
00267  * only if a DETAILED routing has been selected.                        */
00268 
00269     int tmp;
00270     boolean success;
00271         t_graph_type graph_type;
00272 
00273         if(router_opts.route_type == GLOBAL) {
00274                 graph_type = GRAPH_GLOBAL;
00275         } else {
00276                 graph_type = (det_routing_arch.directionality ==
00277                     BI_DIRECTIONAL ? GRAPH_BIDIR : GRAPH_UNIDIR);
00278         }
00279 
00280 /* Set the channel widths */
00281 
00282     init_chan(width_fac, chan_width_dist);
00283 
00284 /* Free any old routing graph, if one exists. */
00285 
00286     free_rr_graph();
00287 
00288 /* Set up the routing resource graph defined by this FPGA architecture. */
00289 
00290     build_rr_graph(graph_type,
00291                    num_types, type_descriptors, nx, ny, grid,
00292                    chan_width_x[0], NULL,
00293                    det_routing_arch.switch_block_type, det_routing_arch.Fs,
00294                    det_routing_arch.num_segment, det_routing_arch.num_switch, segment_inf,
00295                    det_routing_arch.global_route_switch,
00296                    det_routing_arch.delayless_switch, timing_inf,
00297                    det_routing_arch.wire_to_ipin_switch,
00298                    router_opts.base_cost_type, &tmp);
00299 
00300 /* Allocate and load some additional rr_graph information needed only by *
00301  * the router.                                                           */
00302 
00303     alloc_and_load_rr_node_route_structs();
00304 
00305     init_route_structs(router_opts.bb_factor);
00306 
00307     if(router_opts.router_algorithm == BREADTH_FIRST)
00308         {
00309             printf("Confirming Router Algorithm: BREADTH_FIRST.\n");
00310             success =
00311                 try_breadth_first_route(router_opts, fb_opins_used_locally,
00312                                         width_fac);
00313         }
00314     else if(router_opts.router_algorithm == TIMING_DRIVEN)
00315         {                       /* TIMING_DRIVEN route */
00316             printf("Confirming Router Algorithm: TIMING_DRIVEN.\n");
00317             assert(router_opts.route_type != GLOBAL);
00318             success =
00319                 try_timing_driven_route(router_opts, net_slack, net_delay,
00320                                         fb_opins_used_locally);
00321         }
00322     else
00323         {                       /* Directed Search Routability Driven */
00324             printf("Confirming Router Algorithm: DIRECTED_SEARCH.\n");
00325             success =
00326                 try_directed_search_route(router_opts, fb_opins_used_locally,
00327                                           width_fac, mst);
00328         }
00329 
00330     free_rr_node_route_structs();
00331 
00332     return (success);
00333 }

Here is the call graph for this function:

Here is the caller graph for this function:


Generated on Tue Jan 5 15:26:14 2010 for VPR5.0 by  doxygen 1.6.1