1 /*
2 * Copyright (C) 1989-1991 Yale University
3 * Copyright (C) 2015 Staf Verhaegen <staf@stafverhaegen.be>
4 *
5 * This work is distributed in the hope that it will be useful; you can
6 * redistribute it and/or modify it under the terms of the
7 * GNU General Public License as published by the Free Software Foundation;
8 * either version 2 of the License,
9 * or any later version, on the following conditions:
10 *
11 * (a) YALE MAKES NO, AND EXPRESSLY DISCLAIMS
12 * ALL, REPRESENTATIONS OR WARRANTIES THAT THE MANUFACTURE, USE, PRACTICE,
13 * SALE OR
14 * OTHER DISPOSAL OF THE SOFTWARE DOES NOT OR WILL NOT INFRINGE UPON ANY
15 * PATENT OR
16 * OTHER RIGHTS NOT VESTED IN YALE.
17 *
18 * (b) YALE MAKES NO, AND EXPRESSLY DISCLAIMS ALL, REPRESENTATIONS AND
19 * WARRANTIES
20 * WHATSOEVER WITH RESPECT TO THE SOFTWARE, EITHER EXPRESS OR IMPLIED,
21 * INCLUDING,
22 * BUT NOT LIMITED TO, WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A
23 * PARTICULAR
24 * PURPOSE.
25 *
26 * (c) LICENSEE SHALL MAKE NO STATEMENTS, REPRESENTATION OR WARRANTIES
27 * WHATSOEVER TO
28 * ANY THIRD PARTIES THAT ARE INCONSISTENT WITH THE DISCLAIMERS BY YALE IN
29 * ARTICLE
30 * (a) AND (b) above.
31 *
32 * (d) IN NO EVENT SHALL YALE, OR ITS TRUSTEES, DIRECTORS, OFFICERS,
33 * EMPLOYEES AND
34 * AFFILIATES BE LIABLE FOR DAMAGES OF ANY KIND, INCLUDING ECONOMIC DAMAGE OR
35 * INJURY TO PROPERTY AND LOST PROFITS, REGARDLESS OF WHETHER YALE SHALL BE
36 * ADVISED, SHALL HAVE OTHER REASON TO KNOW, OR IN FACT SHALL KNOW OF THE
37 * POSSIBILITY OF THE FOREGOING.
38 *
39 */
40
41 /* -----------------------------------------------------------------
42 FILE: feedest.c
43 DESCRIPTION:feedthru estimation.
44 CONTENTS: feedest()
45 re_estimate_feed_penalty( )
46 estimate_pass_thru_penalty( row1 , row2 )
47 INT row1 , row2 ;
48 update_feedest( net )
49 INT net ;
50 free_up_feedest_malloc()
51 update_segment_data( segptr )
52 SEGBOXPTR segptr ;
53 PINBOXPTR makeSTpt( net , ptr1 , ptr2 )
54 INT net ;
55 PINBOXPTR ptr1 , ptr2 ;
56 SEGBOXPTR makeseg( lowptr , highptr )
57 PINBOXPTR lowptr , highptr ;
58 dbg_cost()
59 DATE: Mar 27, 1989
60 REVISIONS: Sat Dec 15 22:08:21 EST 1990 - modified pinloc values
61 so that it will always be positive.
62 Tue Mar 12 17:08:44 CST 1991 - added back missing
63 computation.
64 ----------------------------------------------------------------- */
65
66 #define FEEDS_VARS
67
68 #include <string.h>
69 #include "standard.h"
70 #include "groute.h"
71 #include "feeds.h"
72 #include "main.h"
73
74 /* global definitions */
75 INT *rowfeed_penaltyG ;
76
77 extern BOOL absolute_minimum_feedsG ;
78
79 /* static definitions */
80 static DOUBLE *fd_estimateS ;
81 static INT *min_feedS ;
82 static INT *row_flagS ;
83 static INT chip_width_penaltyS ;
84 static INT *est_min_ratioS ;
85
86 void estimate_pass_thru_penalty(INT row1 , INT row2 );
87
feedest()88 void feedest()
89 {
90
91 DOUBLE ratio ;
92 INT net , row , toprow , botrow, maxdesire ;
93 DBOXPTR dimptr ;
94 PINBOXPTR ptr ;
95
96 fd_estimateS = (DOUBLE *)Ysafe_calloc( numChansG + 1, sizeof(DOUBLE) ) ;
97 min_feedS = (INT *)Ysafe_calloc( numChansG + 1, sizeof(INT) ) ;
98 row_flagS = (INT *)Ysafe_calloc( numChansG + 1, sizeof(INT) ) ;
99 rowfeed_penaltyG = (INT *)Ysafe_malloc( ( numChansG + 1 ) * sizeof(INT) ) ;
100 memset(rowfeed_penaltyG, 0, ( numChansG + 1 ) * sizeof(INT) ); // FIXME: If not clearing, result is non-determinsitic. Figure out why
101 est_min_ratioS = (INT *)Ysafe_malloc( numChansG * sizeof(INT) ) ;
102
103 maxdesire = barrayG[1]->desire ;
104 for( row = 2 ; row <= numRowsG ; row++ ) {
105 if( maxdesire < barrayG[row]->desire ) {
106 maxdesire = barrayG[row]->desire ;
107 }
108 }
109
110 ratio = (DOUBLE)(maxdesire) / (DOUBLE)( barrayG[numRowsG]->bycenter -
111 barrayG[1]->bycenter + rowHeightG ) ;
112 ratio = 1.0 / ratio ; /* to fix Kai-Win's bug */
113
114 if( absolute_minimum_feedsG ) {
115 if( ratio >= 1.0 ) {
116 chip_width_penaltyS = barrayG[numRowsG]->bycenter -
117 barrayG[1]->bycenter + rowHeightG ;
118 } else {
119 chip_width_penaltyS = maxdesire ;
120 }
121 } else {
122 /* chip_width_penaltyS = 2.0 * (DOUBLE) rowHeightG ; */
123 chip_width_penaltyS = 6.9 * (DOUBLE) rowHeightG ;
124 }
125
126
127
128 if( !absolute_minimum_feedsG ) {
129 add_Lcorner_feedG = TRUE ;
130 /* Carl */
131 for( row = 1 ; row <= numRowsG ; row++ ) {
132 if( FeedInRowG[row] == 0 ) {
133 add_Lcorner_feedG = FALSE ;
134 break ;
135 }
136 }
137 /* Carl */
138 } else {
139 add_Lcorner_feedG = FALSE ;
140 }
141 for( net = 1 ; net <= numnetsG ; net++ ) {
142 dimptr = netarrayG[net] ;
143 if( !(dimptr->pins) ) {
144 continue ;
145 }
146 switch( dimptr->numpins ) {
147 case 0 :
148 case 1 :
149 break ;
150 case 2 :
151 ptr = dimptr->pins ;
152 toprow = ptr->row ;
153 botrow = ptr->next->row ;
154 if( toprow > botrow ) {
155 for( row = botrow + 1 ; row < toprow ; row++ ) {
156 fd_estimateS[row]++ ;
157 min_feedS[row]++ ;
158 }
159 if( ABS( ptr->xpos - ptr->next->xpos ) >=
160 average_feed_sepG ) {
161 fd_estimateS[botrow] += 0.5 ;
162 fd_estimateS[toprow] += 0.5 ;
163 }
164 } else if( toprow < botrow ) {
165 for( row = toprow + 1 ; row < botrow ; row++ ) {
166 fd_estimateS[row]++ ;
167 min_feedS[row]++ ;
168 }
169 if( ABS( ptr->xpos - ptr->next->xpos ) >=
170 average_feed_sepG ) {
171 fd_estimateS[botrow] += 0.5 ;
172 fd_estimateS[toprow] += 0.5 ;
173 }
174 }
175 row_flagS[botrow] = 0 ;
176 row_flagS[toprow] = 0 ;
177 break ;
178 case 3 :
179 case 4 :
180 case 5 :
181 ptr = dimptr->pins ;
182 toprow = botrow = ptr->row ;
183 row_flagS[toprow] = 1 ;
184 for( ptr = ptr->next ; ptr ; ptr = ptr->next ) {
185 row = ptr->row ;
186 if( row < botrow ) {
187 botrow = row ;
188 }
189 if( row > toprow ) {
190 toprow = row ;
191 }
192 row_flagS[row] = 1 ;
193 }
194 for( row = botrow + 1 ; row < toprow ; row++ ) {
195 if( row_flagS[row] ) {
196 fd_estimateS[row]++ ;
197 row_flagS[row] = 0 ;
198 } else {
199 fd_estimateS[row] += 1.5 ;
200 min_feedS[row]++ ;
201 }
202 }
203 if( toprow > botrow ) {
204 fd_estimateS[botrow] += 0.5 ;
205 fd_estimateS[toprow] += 0.5 ;
206 }
207 row_flagS[botrow] = 0 ;
208 row_flagS[toprow] = 0 ;
209 break ;
210 default :
211 ptr = dimptr->pins ;
212 toprow = botrow = ptr->row ;
213 row_flagS[toprow] = 1 ;
214 for( ptr = ptr->next ; ptr ; ptr = ptr->next ) {
215 row = ptr->row ;
216 if( row < botrow ) {
217 botrow = row ;
218 }
219 if( row > toprow ) {
220 toprow = row ;
221 }
222 row_flagS[row] = 1 ;
223 }
224 for( row = botrow + 1 ; row < toprow ; row++ ) {
225 if( row_flagS[row] ) {
226 fd_estimateS[row]++ ;
227 row_flagS[row] = 0 ;
228 } else {
229 fd_estimateS[row] += 1.5 ;
230 min_feedS[row]++ ;
231 }
232 }
233 if( toprow > botrow ) {
234 fd_estimateS[botrow]++ ;
235 fd_estimateS[toprow]++ ;
236 }
237 row_flagS[botrow] = 0 ;
238 row_flagS[toprow] = 0 ;
239 break ;
240 }
241 }
242
243 estimate_pass_thru_penalty( 1 , numRowsG ) ;
244
245 }
246
re_estimate_feed_penalty()247 void re_estimate_feed_penalty()
248 {
249
250 INT i , n , row , row_rite , excess_fd , *old_penalty ;
251 DOUBLE ratio , factor ;
252 FEED_DATA *feedptr ;
253 CBOXPTR cellptr ;
254
255 old_penalty = (INT *)Ysafe_malloc( numChansG * sizeof(INT) ) ;
256 for( row = 1 ; row <= numRowsG ; row++ ) {
257 old_penalty[row] = rowfeed_penaltyG[row] ;
258 feedptr = feedpptrG[row] ;
259 n = 0 ;
260 for( i = 1 ; i <= chan_node_noG ; i++ ) {
261 n += feedptr[i]->needed ;
262 }
263 fd_estimateS[row] = n ;
264 }
265 estimate_pass_thru_penalty( 1 , numRowsG ) ;
266
267 if( !enough_built_in_feedG ) {
268 goto out ;
269 }
270 for( row = 1 ; row <= numRowsG ; row++ ) {
271 rowfeed_penaltyG[row] =
272 ( 2 * old_penalty[row] + 3 * rowfeed_penaltyG[row] ) / 5 ;
273 cellptr = carrayG[ pairArrayG[row][ pairArrayG[row][0] ] ] ;
274 row_rite = cellptr->cxcenter + cellptr->tileptr->right ;
275 if( fdWidthG > 0 ) {
276 excess_fd = fdcel_addedG[row] + 1 -
277 ( right_most_in_classG[ row_rite_classG[row] ] - row_rite ) /
278 fdWidthG;
279 } else {
280 excess_fd = fdcel_addedG[row] + 1 -
281 ( right_most_in_classG[ row_rite_classG[row] ] - row_rite ) ;
282 }
283 if( excess_fd <= 0 ) {
284 continue ;
285 }
286 ratio = (DOUBLE)(fdcel_addedG[row]) / (DOUBLE)(FeedInRowG[row]) ;
287 if( ratio <= 0.01 ) {
288 factor = 4 ;
289 } else if( ratio <= 0.03 ) {
290 factor = 8 ;
291 } else if( ratio <= 0.05 ) {
292 factor = 15 ;
293 } else if( ratio <= 0.08 ) {
294 factor = 25 ;
295 } else if( ratio <= 0.10 ) {
296 factor = 30 ;
297 } else if( ratio <= 0.20 ) {
298 factor = 40 ;
299 } else {
300 factor = 50 ;
301 }
302 rowfeed_penaltyG[row] += factor * ratio * (DOUBLE)(rowHeightG) ;
303 }
304 /*
305 fp = TWOPEN("vcost.dat", "a", ABORT ) ;
306 fprintf(fp, " row newcost oldcost\n" ) ;
307 for( row = 1 ; row <= numRowsG ; row++ ) {
308 fprintf(fp," %3d %7d %7d\n", row,
309 rowfeed_penaltyG[row], old_penalty[row] ) ;
310 }
311 TWCLOSE(fp) ;
312 */
313 out:
314 Ysafe_free( old_penalty );
315 }
316
317 #ifdef Carl
estimate_pass_thru_penalty(INT row1,INT row2)318 void estimate_pass_thru_penalty(INT row1 , INT row2 )
319 {
320
321 INT row ;
322 DOUBLE ratio ;
323 if( row1 < 1 ) {
324 row1 = 1 ;
325 }
326 if( row2 > numRowsG ) {
327 row2 = numRowsG ;
328 }
329 ratio = (DOUBLE) implicit_feed_count / (DOUBLE) TotRegPins ;
330 if( ratio > 0.0 ) {
331 ratio += 0.1 ;
332 }
333 if( ratio > 1.0 ) {
334 ratio = 1.0 ;
335 }
336 for( row = row1 ; row <= row2 ; row++ ) {
337 if( !absolute_minimum_feeds ) {
338 rowfeed_penaltyG[row] = (2.0 - ratio * 1.2) * rowHeightG ;
339 } else {
340 rowfeed_penaltyG[row] = chip_width_penaltyS ;
341 }
342 }
343 }
344 #else
345
estimate_pass_thru_penalty(INT row1,INT row2)346 void estimate_pass_thru_penalty(INT row1 , INT row2 )
347 {
348
349 INT row ;
350 DOUBLE actual , estimate , act_est_ratio ;
351 if( row1 < 1 ) {
352 row1 = 1 ;
353 }
354 if( row2 > numRowsG ) {
355 row2 = numRowsG ;
356 }
357
358 for( row = row1 ; row <= row2 ; row++ ) {
359 actual = FeedInRowG[row] ;
360 estimate = fd_estimateS[row] ;
361 if( actual > min_feedS[row] && !absolute_minimum_feedsG ) {
362 if( estimate > 0.0 ) {
363 act_est_ratio = actual / estimate ;
364 } else {
365 act_est_ratio = INT_MAX ;
366 /* fix by Carl 1/25/89 */
367 }
368 if( act_est_ratio >= 4 ) {
369 rowfeed_penaltyG[row] = rowHeightG * 0.3 ;
370 } else if( act_est_ratio >= 1.0 ) {
371 rowfeed_penaltyG[row] =
372 ( 0.9 - 0.2 * ( act_est_ratio - 1.0 ) ) * rowHeightG ;
373 } else if( act_est_ratio <= 0.5 ) {
374 rowfeed_penaltyG[row] = 6.9 * rowHeightG ;
375 } else {
376 rowfeed_penaltyG[row] =
377 ( 0.9 + 12.0 * ( 1.0 - act_est_ratio ) ) * rowHeightG ;
378 }
379 } else {
380 rowfeed_penaltyG[row] = chip_width_penaltyS ;
381 }
382 }
383 }
384 #endif
385
386
update_feedest(net)387 void update_feedest( net )
388 INT net ;
389 {
390
391 DBOXPTR dimptr ;
392 SEGBOXPTR seg ;
393 PINBOXPTR ptr ;
394 INT row , toprow , botrow , row1 , row2 ;
395
396
397 dimptr = netarrayG[net] ;
398 if( !(dimptr->pins) ) {
399 return ;
400 }
401 switch( dimptr->numpins ) {
402 case 0 :
403 case 1 :
404 case 2 :
405 return ;
406 case 3 :
407 case 4 :
408 case 5 :
409 ptr = dimptr->pins ;
410 toprow = botrow = ptr->row ;
411 row_flagS[toprow] = 1 ;
412 for( ptr = ptr->next ; ptr ; ptr = ptr->next ) {
413 row = ptr->row ;
414 if( row < botrow ) {
415 botrow = row ;
416 }
417 if( row > toprow ) {
418 toprow = row ;
419 }
420 row_flagS[row] = 1 ;
421 }
422 for( row = botrow + 1 ; row < toprow ; row++ ) {
423 if( row_flagS[row] ) {
424 fd_estimateS[row]-- ;
425 row_flagS[row] = 0 ;
426 } else {
427 fd_estimateS[row] -= 1.5 ;
428 }
429 }
430 if( toprow > botrow ) {
431 fd_estimateS[botrow] -= 0.5 ;
432 fd_estimateS[toprow] -= 0.5 ;
433 }
434 row_flagS[botrow] = 0 ;
435 row_flagS[toprow] = 0 ;
436 break ;
437 default :
438 ptr = dimptr->pins ;
439 toprow = botrow = ptr->row ;
440 row_flagS[toprow] = 1 ;
441 for( ptr = ptr->next ; ptr ; ptr = ptr->next ) {
442 row = ptr->row ;
443 if( row < botrow ) {
444 botrow = row ;
445 }
446 if( row > toprow ) {
447 toprow = row ;
448 }
449 row_flagS[row] = 1 ;
450 }
451 for( row = botrow + 1 ; row < toprow ; row++ ) {
452 if( row_flagS[row] ) {
453 fd_estimateS[row]-- ;
454 row_flagS[row] = 0 ;
455 } else {
456 fd_estimateS[row] -= 1.5 ;
457 }
458 }
459 if( toprow > botrow ) {
460 fd_estimateS[botrow]-- ;
461 fd_estimateS[toprow]-- ;
462 }
463 row_flagS[botrow] = 0 ;
464 row_flagS[toprow] = 0 ;
465 break ;
466 }
467 for( seg = netsegHeadG[net]->next ; seg ; seg = seg->next ) {
468 row1 = seg->pin1ptr->row ;
469 row2 = seg->pin2ptr->row ;
470 if( row1 == row2 ) {
471 if( ABS( seg->pin1ptr->pinloc - seg->pin2ptr->pinloc ) <= 1 ) {
472 continue ;
473 } else {
474 fd_estimateS[row1]++ ;
475 }
476 } else {
477 for( row = row1 + 1 ; row < row2 ; row++ ) {
478 fd_estimateS[row]++ ;
479 }
480 if( seg->pin1ptr->pinloc < NEITHER ) {
481 fd_estimateS[row1]++ ;
482 }
483 if( seg->pin2ptr->pinloc > NEITHER ) {
484 fd_estimateS[row2]++ ;
485 }
486 if( add_Lcorner_feedG && seg->switchvalue != nswLINE ) {
487 fd_estimateS[row1] += 0.5 ;
488 fd_estimateS[row2] += 0.5 ;
489 }
490 }
491 }
492 for( ptr = steinerHeadG[net]->next; ptr ; ptr = ptr->next ) {
493 fd_estimateS[ ptr->row ]++ ;
494 }
495
496 estimate_pass_thru_penalty( botrow , toprow ) ;
497
498 }
499
500
free_up_feedest_malloc()501 void free_up_feedest_malloc()
502 {
503
504 Ysafe_free( fd_estimateS ) ;
505 Ysafe_free( min_feedS ) ;
506 Ysafe_free( row_flagS ) ;
507 Ysafe_free( rowfeed_penaltyG ) ;
508 Ysafe_free( est_min_ratioS ) ;
509 }
510
511
update_segment_data(segptr)512 void update_segment_data( segptr )
513 SEGBOXPTR segptr ;
514 {
515 PINBOXPTR ptr1 , ptr2 ;
516
517 ptr1 = segptr->pin1ptr ;
518 ptr2 = segptr->pin2ptr ;
519 segptr->flag = NEW ;
520 if( ptr1->row < ptr2->row ) {
521 segptr->pin1ptr = ptr1 ;
522 segptr->pin2ptr = ptr2 ;
523 if( ABS( ptr1->xpos - ptr2->xpos ) >= average_feed_sepG ) {
524 segptr->switchvalue = swL_up ;
525 } else {
526 segptr->switchvalue = nswLINE ;
527 }
528 } else if( ptr1->row > ptr2->row ) {
529 segptr->pin2ptr = ptr1 ;
530 segptr->pin1ptr = ptr2 ;
531 if( ABS( ptr1->xpos - ptr2->xpos ) >= average_feed_sepG ) {
532 segptr->switchvalue = swL_up ;
533 } else {
534 segptr->switchvalue = nswLINE ;
535 }
536 } else if( (INT) ptr1->pinloc == BOTCELL && (INT) ptr2->pinloc == TOPCELL ) {
537 segptr->pin1ptr = ptr1 ;
538 segptr->pin2ptr = ptr2 ;
539 segptr->switchvalue = nswLINE ;
540 } else if( (INT) ptr1->pinloc == TOPCELL && (INT) ptr2->pinloc == BOTCELL ) {
541 segptr->pin1ptr = ptr2 ;
542 segptr->pin2ptr = ptr1 ;
543 segptr->switchvalue = nswLINE ;
544 } else if( ptr1->xpos <= ptr2->xpos ) {
545 segptr->pin1ptr = ptr1 ;
546 segptr->pin2ptr = ptr2 ;
547 segptr->switchvalue = nswLINE ;
548 } else {
549 segptr->pin1ptr = ptr2 ;
550 segptr->pin2ptr = ptr1 ;
551 segptr->switchvalue = nswLINE ;
552 }
553 }
554
555
makeSTpt(net,ptr1,ptr2)556 PINBOXPTR makeSTpt( net , ptr1 , ptr2 )
557 INT net ;
558 PINBOXPTR ptr1 , ptr2 ;
559 {
560
561 PINBOXPTR ptr ;
562
563 ptr = (PINBOXPTR)Ysafe_malloc( sizeof(PINBOX) ) ;
564 ptr->xpos = ptr1->xpos ;
565 ptr->ypos = ptr2->ypos ;
566 ptr->terminal = 0 ;
567 if( ptr1->terminal == 0 ) {
568 ptr->newx = ptr1->newx ;
569 } else {
570 ptr->newx = ptr1->terminal ;
571 }
572 /* the 'newx' field is temporary used for storing the
573 y-direction terminal that steiner points refered to */
574 ptr->row = ptr2->row ;
575 ptr->pinloc = NEITHER ;
576 ptr->newy = 3 * ptr->row ;
577 ptr->net = net ;
578 ptr->adjptr = (ADJASEGPTR)Ysafe_calloc( 1, sizeof(ADJASEG) ) ;
579 ptr->next = steinerHeadG[net]->next ;
580 steinerHeadG[net]->next = ptr ;
581 return( ptr ) ;
582 }
583
584
makeseg(lowptr,highptr)585 SEGBOXPTR makeseg( lowptr , highptr )
586 PINBOXPTR lowptr , highptr ;
587 {
588 ADJASEG *adj1, *adj2 ;
589 SEGBOXPTR segptr ;
590
591 segptr = ( SEGBOXPTR )Ysafe_malloc( sizeof(SEGBOX) ) ;
592 if( lowptr->row < highptr->row ) {
593 segptr->pin1ptr = lowptr ;
594 segptr->pin2ptr = highptr ;
595 segptr->switchvalue = swL_up ;
596 } else if( lowptr->row > highptr->row ) {
597 segptr->pin2ptr = lowptr ;
598 segptr->pin1ptr = highptr ;
599 segptr->switchvalue = swL_up ;
600 } else if( (INT) lowptr->pinloc == BOTCELL && (INT) highptr->pinloc == TOPCELL ) {
601 segptr->pin1ptr = lowptr ;
602 segptr->pin2ptr = highptr ;
603 segptr->switchvalue = swL_up ;
604 } else if( (INT) lowptr->pinloc == TOPCELL && (INT) highptr->pinloc == BOTCELL ) {
605 segptr->pin1ptr = highptr ;
606 segptr->pin2ptr = lowptr ;
607 segptr->switchvalue = swL_up ;
608 } else if( lowptr->xpos < highptr->xpos ) {
609 segptr->pin1ptr = lowptr ;
610 segptr->pin2ptr = highptr ;
611 segptr->switchvalue = nswLINE ;
612 } else {
613 segptr->pin2ptr = lowptr ;
614 segptr->pin1ptr = highptr ;
615 segptr->switchvalue = nswLINE ;
616 }
617 adj1 = (ADJASEGPTR)Ysafe_calloc( 1, sizeof(ADJASEG) ) ;
618 adj2 = (ADJASEGPTR)Ysafe_calloc( 1, sizeof(ADJASEG) ) ;
619 adj1->segptr = segptr ;
620 adj2->segptr = segptr ;
621 adj1->next = lowptr->adjptr->next ;
622 adj2->next = highptr->adjptr->next ;
623 lowptr->adjptr->next = adj1 ;
624 highptr->adjptr->next = adj2 ;
625 segptr->next = netsegHeadG[lowptr->net]->next ;
626 netsegHeadG[lowptr->net]->next = segptr ;
627 return( segptr ) ;
628 }
629
630
dbg_cost()631 void dbg_cost()
632 {
633 FILE *fp ;
634 INT row ;
635 DOUBLE cost, ratio ;
636
637 fp = TWOPEN("vcost.dat", "w", ABORT ) ;
638 fprintf(fp, " rowHeightG = %d\n", rowHeightG ) ;
639 fprintf(fp, " row cost actual estimate ratio\n" ) ;
640 for( row = 1 ; row <= numRowsG ; row++ ) {
641 cost = (DOUBLE)(rowfeed_penaltyG[row]) / (DOUBLE)(rowHeightG) ;
642 ratio = (DOUBLE)(FeedInRowG[row]) / fd_estimateS[row] ;
643 fprintf(fp, " %3d %5.2f %6d %8.2f %8.2f\n", row, cost,
644 FeedInRowG[row], fd_estimateS[row], ratio ) ;
645 }
646 TWCLOSE(fp) ;
647 }
648
649
dbx_fdpen()650 void dbx_fdpen()
651 {
652
653 FILE *fp ;
654 FEED_DATA *feedptr ;
655 INT row , i , s ;
656
657 fp = TWOPEN("pen.dat" , "w", ABORT ) ;
658 fprintf(fp," row min_feedSS fd_estimateS act_feed needed\n" ) ;
659 for( row = 1 ; row <= numRowsG ; row++ ) {
660 feedptr = feedpptrG[row] ;
661 s = 0 ;
662 for( i = 1 ; i <= chan_node_noG ; i++ ) {
663 s += feedptr[i]->needed ;
664 }
665 fprintf(fp," %3d %8d %8d %8d %6d\n", row, min_feedS[row],
666 (INT)fd_estimateS[row] , FeedInRowG[row] , s ) ;
667 }
668 TWCLOSE(fp) ;
669 }
670