Initial version of donated sources by Avertec, 3.4p5.
[tas-yagle.git] / distrib / sources / tas / mcc / mcc_fit.c
1 /****************************************************************************/
2 /* */
3 /* Chaine de CAO & VLSI Alliance */
4 /* */
5 /* Produit : MCC Version 1 */
6 /* Fichier : mcc_fit.c */
7 /* */
8 /* (c) copyright 1991-1998 Laboratoire LIP6 equipe ASIM */
9 /* Tous droits reserves */
10 /* Support : e-mail alliance-support@asim.lip6.fr */
11 /* */
12 /* Auteur(s) : Karim DIOURY */
13 /* */
14 /****************************************************************************/
15
16 #include "mcc_fit.h"
17 #include "mcc_debug.h"
18
19 long MCC_TASUD ;
20 long MCC_TASDU ;
21 long MCC_TASDD ;
22 long MCC_TASUU ;
23 long MCC_TASSUD ;
24 long MCC_TASSDU ;
25 long MCC_TASSDD ;
26 long MCC_TASSUU ;
27
28 int mcc_getdelay(char *filename,char *in,char *out,int mode,char sin,char sout,FILE *file)
29 {
30 ttvfig_list *ttvfig ;
31 chain_list *chain1 ;
32 chain_list *chain2 ;
33 ttvpath_list *path ;
34 ttvpath_list *headpath ;
35 ttvcritic_list *headcritic ;
36 ttvcritic_list *critic ;
37 ttvcritic_list *criticx ;
38 long nbud ;
39 long nbdu ;
40 long nb ;
41 char pin ;
42 char pout ;
43 char trans[2];
44
45 ttvfig = ttv_getttvfig(filename,(long)0) ;
46
47 if(ttvfig == NULL)
48 return(0) ;
49
50 chain1 = addchain(NULL,(void *)in) ;
51 chain2 = addchain(NULL,(void *)out) ;
52
53 headpath = ttv_getcriticpath(ttvfig,NULL,chain1,chain2,TTV_DELAY_MAX,TTV_DELAY_MIN,100,TTV_FIND_MAX|TTV_FIND_LINE) ;
54 path = headpath ;
55
56 if(path != NULL)
57 {
58 while(path != NULL)
59 {
60 if((path->NODE->TYPE & TTV_NODE_UP) == TTV_NODE_UP)
61 pin = 'U' ;
62 else
63 pin = 'D' ;
64
65 if((path->ROOT->TYPE & TTV_NODE_UP) == TTV_NODE_UP)
66 pout = 'U' ;
67 else
68 pout = 'D' ;
69
70 if(((sin == pin) || (sin == 'X')) && ((sout == pout) || (sout == 'X')))
71 {
72 headcritic = ttv_getcritic(ttvfig,NULL,path->ROOT,path->NODE,path->LATCH,path->CMDLATCH,(path->TYPE & ~(TTV_FIND_PATH)) | TTV_FIND_LINE) ;
73 break ;
74 }
75 path = path->NEXT ;
76 if(path == NULL)
77 return(0) ;
78 }
79 }
80 else
81 {
82 return(0) ;
83 }
84
85 ttv_freepathlist(headpath) ;
86
87 if(headcritic == NULL)
88 return(0) ;
89
90 MCC_TASUD = (long)0 ;
91 MCC_TASDU = (long)0 ;
92 MCC_TASDD = (long)0 ;
93 MCC_TASUU = (long)0 ;
94 MCC_TASSUD = (long)0 ;
95 MCC_TASSDU = (long)0 ;
96 MCC_TASSDD = (long)0 ;
97 MCC_TASSUU = (long)0 ;
98 nbud = (long)0 ;
99 nbdu = (long)0 ;
100 nb = (long)0 ;
101
102 if(mode == 0)
103 for(critic = headcritic->NEXT ; critic->NEXT != NULL ; critic = critic->NEXT)
104 {
105 criticx = critic->NEXT ;
106 if(nb == (long)0)
107 {
108 nb++ ;
109 continue ;
110 }
111 if(criticx->NEXT->NEXT == NULL)
112 break ;
113 if(critic->SNODE == TTV_UP)
114 {
115 MCC_TASUD += criticx->DELAY ;
116 MCC_TASSUD = criticx->SLOPE ;
117 nbud ++ ;
118 }
119 else
120 {
121 MCC_TASDU += criticx->DELAY ;
122 MCC_TASSDU = criticx->SLOPE ;
123 nbdu ++ ;
124 }
125 }
126 else // that case if for mcc debug
127 {
128 sprintf(trans,"%c%c",sin,sout);
129 for(critic = headcritic->NEXT ; critic->NEXT != NULL ; critic = critic->NEXT) ;
130 if(critic->SNODE == TTV_DOWN)
131 {
132 MCC_TASUD += critic->DELAY ;
133 MCC_TASSUD = critic->SLOPE ;
134 nbud ++ ;
135 }
136 else
137 {
138 MCC_TASDU += critic->DELAY ;
139 MCC_TASSDU = critic->SLOPE ;
140 nbdu ++ ;
141 }
142 }
143
144 ttv_freecriticlist(headcritic) ;
145
146 if(nbud != 0)
147 MCC_TASUD = (MCC_TASUD / nbud) ;
148 else
149 MCC_TASUD = 0 ;
150 if(nbdu != 0)
151 MCC_TASDU = (MCC_TASDU / nbdu) ;
152 else
153 MCC_TASDU = 0 ;
154
155 if ( mode )
156 {
157 if ( !strcmp(trans,"UU") )
158 {
159 if ( MCC_TASUD > MCC_TASDU )
160 {
161 MCC_TASUU = MCC_TASUD;
162 MCC_TASSUU = MCC_TASSUD;
163 MCC_TASUD = 0;
164 MCC_TASSUD = 0;
165 }
166 else
167 {
168 MCC_TASUU = MCC_TASDU;
169 MCC_TASSUU = MCC_TASSDU;
170 MCC_TASDU = 0;
171 MCC_TASSDU = 0;
172 }
173 }
174 else if ( !strcmp(trans,"DD") )
175 {
176 if ( MCC_TASUD > MCC_TASDU )
177 {
178 MCC_TASDD = MCC_TASUD;
179 MCC_TASSDD = MCC_TASSUD;
180 MCC_TASUD = 0;
181 MCC_TASSUD = 0;
182 }
183 }
184 fprintf(file==NULL?stdout:file,"\n%s tas delay : UD=%ld DU=%ld DD=%ld UU=%ld slope : UD=%ld DU=%ld DD=%ld UU=%ld\n",
185 filename,(long)(MCC_TASUD/TTV_UNIT),(long)(MCC_TASDU/TTV_UNIT),(long)(MCC_TASDD/TTV_UNIT),(long)(MCC_TASUU/TTV_UNIT),(long)(MCC_TASSUD/TTV_UNIT),(long)(MCC_TASSDU/TTV_UNIT),(long)(MCC_TASSDD/TTV_UNIT),(long)(MCC_TASSUU/TTV_UNIT)) ;
186 }
187 else
188 {
189 fprintf(file==NULL?stdout:file,"\n%s tas delay : UD=%ld DU=%ld slope : UD=%ld DU=%ld\n",
190 filename,(long)(MCC_TASUD/TTV_UNIT),(long)(MCC_TASDU/TTV_UNIT),(long)(MCC_TASSUD/TTV_UNIT),(long)(MCC_TASSDU/TTV_UNIT)) ;
191 }
192 ttv_freeallttvfig(ttvfig) ;
193
194 MCC_TASUD /= TTV_UNIT ;
195 MCC_TASDU /= TTV_UNIT ;
196 MCC_TASDD /= TTV_UNIT ;
197 MCC_TASUU /= TTV_UNIT ;
198 MCC_TASSUD /= TTV_UNIT ;
199 MCC_TASSDU /= TTV_UNIT ;
200 MCC_TASSDD /= TTV_UNIT ;
201 MCC_TASSUU /= TTV_UNIT ;
202
203 return(1) ;
204 }
205
206 void mcc_runtas(filename,slope,capa)
207 char *filename ;
208 int slope ;
209 int capa ;
210 {
211 pid_t pid ;
212 int status ;
213 char *argv[6] ;
214 char env[1024] ;
215 char slopes[48] ;
216 char capas[48] ;
217 char *name ;
218 int n = 0 ;
219
220 if(slope > 0)
221 sprintf(slopes,"-slope=%d",slope) ;
222
223 if(capa > 0)
224 sprintf(capas,"-cout=%.3f",(float)capa/1000.0) ;
225
226 pid = vfork() ;
227
228 if(pid == (pid_t)(-1))
229 {
230 fprintf(stderr,"\nmcc error: can't run %s\n",MCC_SPICENAME) ;
231 EXIT(1) ;
232 }
233 else if(pid == 0)
234 {
235 sprintf(env,"MBK_SPI_TN=%s",MCC_TNMODEL) ;
236 name = (char *)mbkalloc(strlen(env) + 1) ;
237 strcpy(name,env) ;
238 putenv(name) ;
239 sprintf(env,"MBK_SPI_TP=%s",MCC_TPMODEL) ;
240 name = (char *)mbkalloc(strlen(env) + 1) ;
241 strcpy(name,env) ;
242 putenv(name) ;
243 sprintf(env,"ELP_TECHNO_NAME=%s",MCC_ELPFILE) ;
244 name = (char *)mbkalloc(strlen(env) + 1) ;
245 strcpy(name,env) ;
246 putenv(name) ;
247 strcpy(env,"SIM_SLOPE_INTERNAL_THRESHOLDS=yes") ;
248 name = (char *)mbkalloc(strlen(env) + 1) ;
249 strcpy(name,env) ;
250 putenv(name) ;
251 argv[n++] = MCC_TASNAME ;
252 argv[n++] = "-t$" ;
253 argv[n++] = "-in=spi" ;
254 argv[n++] = "-s" ;
255 if(slope > 0)
256 argv[n++] = slopes ;
257 if(capa > 0)
258 argv[n++] = capas ;
259 name = filename ;
260 argv[n++] = name ;
261 argv[n++] = NULL ;
262 n = 0 ;
263 fprintf(stdout,"\nRUN: ") ;
264 while(argv[n] != NULL)
265 {
266 fprintf(stdout,"%s ",argv[n]) ;
267 n++ ;
268 fflush(stdout) ;
269 }
270 fprintf(stdout,"\n") ;
271 fflush(stdout) ;
272 status = execvp(argv[0],argv) ;
273
274 if(status != -1) {
275 EXIT(0) ;
276 }
277 else {
278 EXIT(1) ;
279 }
280 }
281 else
282 {
283 n = mbkwaitpid(pid,1,&status) ;
284 if((n == 0) || (WIFEXITED(status) == 0))
285 {
286 fprintf(stderr,"\nmcc error: can not execute tas\n") ;
287 }
288 else if(WEXITSTATUS(status) != 0)
289 {
290 fprintf(stderr,"\nmcc warning: tas exit with non zero value\n") ;
291 }
292 else
293 {
294 fprintf(stdout,"Execution Completed\n") ;
295 }
296 }
297 }
298
299 void mcc_fit(elp_lotrs_param *lotrsparam_n,elp_lotrs_param *lotrsparam_p,int componly)
300 {
301 double error ;
302 double errorx ;
303 double tref ;
304 long tasdelay ;
305 long spicedelay ;
306 int i ;
307 int maxloop ;
308 char *filename ;
309 char s1[8] ;
310 char s2[8] ;
311 char buf[1024], buf0[1024];
312 FILE *f;
313
314 strcpy(buf0,MCC_ELPFILE); // modifier a l'appel de tas
315
316 if (!componly) mcc_drvelp(MCC_PARAM,MCC_TRANS_B,lotrsparam_n,lotrsparam_p,MCC_DRV_ALL_MODEL) ;
317 // mcc_gencurv(MCC_PARAM,lotrsparam_n,lotrsparam_p) ;
318
319 f=fopen(mcc_debug_prefix("fit_output.log"),"w");
320 for(i = 0 ; i < MCC_TASNB ; i++)
321 {
322 if ( i == MCC_FIT_A && ( avt_gethashvar ("MCC_DONT_FITA" )) )
323 continue;
324 if ( (i == MCC_FIT_CG || i==MCC_FIT_CG_NOCAPA) && ( avt_gethashvar ("MCC_DONT_FITCG" )) )
325 continue;
326 if ( i == MCC_FIT_CDN && ( avt_gethashvar ("MCC_DONT_FITCDN" )) )
327 continue;
328 if ( i == MCC_FIT_CDP && ( avt_gethashvar ("MCC_DONT_FITCDP" )) )
329 continue;
330 maxloop = MCC_NBMAXLOOP ;
331 filename = mcc_getfilename(MCC_TASFILE[i]) ;
332 error = 100.0 ;
333 while(error > MCC_ERROR)
334 {
335 if (!componly) mcc_drvelp(i,MCC_TRANS_B,lotrsparam_n,lotrsparam_p,MCC_DRV_ALL_MODEL) ;
336 // mcc_runtas_tcl(mcc_debug_prefix(mcc_getfilename(MCC_TASFILE[i])),V_FLOAT_TAB[__FRONT_CON].VALUE,V_FLOAT_TAB[__TAS_CAPAOUT].VALUE,NULL) ;
337 strcpy(buf,mcc_debug_prefix(MCC_SPICEFILE[i]));
338 mcc_runtas_tcl(buf,V_FLOAT_TAB[__FRONT_CON].VALUE,0,NULL,mcc_debug_prefix(mcc_getfilename(MCC_TASFILE[i]))) ;
339 mbkfree(MCC_ELPFILE);
340 MCC_ELPFILE=mbkstrdup(buf0);
341 sprintf(s1,"s0") ;
342 sprintf(s2,"s%d",MCC_INSNUMB) ;
343 if(mcc_getdelay(mcc_debug_prefix(filename),s1,s2,0,'X','X',f) == 0)
344 {
345 fprintf(stderr,"\nmcc error : can't extract data from file %s\n",
346 MCC_TASFILE[i]) ;
347 EXIT(1) ;
348 }
349 switch(i)
350 {
351 case MCC_FIT_A : tasdelay = MCC_TASUD + MCC_TASDU ;
352 spicedelay = MCC_SPICEUD_FITA + MCC_SPICEDU_FITA ;
353 if (f!=NULL) fprintf(f,"%s spice delay : UD=%ld DU=%ld slope : UD=%ld DU=%ld\n",filename,MCC_SPICEUD_FITA,MCC_SPICEDU_FITA,MCC_SPICEFUD_FITA,MCC_SPICEFDU_FITA) ;
354 if(MCC_TASUD > MCC_SPICEUD_FITA)
355 error = (double)((MCC_TASUD - MCC_SPICEUD_FITA) /
356 (double)(MCC_TASUD)) ;
357 else
358 error = (double)((MCC_SPICEUD_FITA - MCC_TASUD) /
359 (double)(MCC_SPICEUD_FITA)) ;
360 if(MCC_TASDU > MCC_SPICEDU_FITA)
361 errorx = (double)((MCC_TASDU - MCC_SPICEDU_FITA) /
362 (double)(MCC_TASDU)) ;
363 else
364 errorx = (double)((MCC_SPICEDU_FITA - MCC_TASDU) /
365 (double)(MCC_SPICEDU_FITA)) ;
366 if(errorx > error)
367 error = errorx ;
368
369 if (componly) break;
370
371 tref = (double)((double)(MCC_TASUD) /
372 (double)(MCC_SPICEUD_FITA)) ;
373 MCC_AN = MCC_AN * tref ;
374 tref = (double)((double)(MCC_TASDU) /
375 (double)(MCC_SPICEDU_FITA)) ;
376 MCC_AP = MCC_AP * tref ;
377 break ;
378 case MCC_FIT_CG_NOCAPA:
379 tasdelay = MCC_TASUD + MCC_TASDU ;
380 spicedelay = MCC_SPICEUD_FITCGNOCAPA + MCC_SPICEDU_FITCGNOCAPA;
381 if (f!=NULL) fprintf(f,"%s spice delay : UD=%ld DU=%ld slope : UD=%ld DU=%ld\n",filename,MCC_SPICEUD_FITCGNOCAPA,MCC_SPICEDU_FITCGNOCAPA,MCC_SPICEFUD_FITCGNOCAPA,MCC_SPICEFDU_FITCGNOCAPA) ;
382 tref = (double)((double)(spicedelay) /
383 (double)(tasdelay)) ;
384 if(tasdelay > spicedelay)
385 error = (double)((tasdelay - spicedelay) /
386 (double)(tasdelay)) ;
387 else
388 error = (double)((spicedelay - tasdelay) /
389 (double)(spicedelay)) ;
390 if (componly) break;
391 MCC_CGSN = MCC_CGSN * tref ;
392 MCC_CGSP = MCC_CGSP * tref ;
393 MCC_CGDN = MCC_CGDN * tref ;
394 MCC_CGDCN = MCC_CGDCN * tref ;
395 MCC_CGDP = MCC_CGDP * tref ;
396 MCC_CGDCP = MCC_CGDCP * tref ;
397 MCC_CGSIN = MCC_CGSIN * tref ;
398 MCC_CGSICN = MCC_CGSICN * tref ;
399 MCC_CGSIP = MCC_CGSIP * tref ;
400 MCC_CGSICP = MCC_CGSICP * tref ;
401 MCC_CGPN = MCC_CGPN * tref ;
402 MCC_CGPP = MCC_CGPP * tref ;
403 break ;
404 case MCC_FIT_CG : tasdelay = MCC_TASUD + MCC_TASDU ;
405 spicedelay = MCC_SPICEUD_FITCG + MCC_SPICEDU_FITCG;
406 if (f!=NULL) fprintf(f,"%s spice delay : UD=%ld DU=%ld slope : UD=%ld DU=%ld\n",filename,MCC_SPICEUD_FITCG,MCC_SPICEDU_FITCG,MCC_SPICEFUD_FITCG,MCC_SPICEFDU_FITCG) ;
407 if(tasdelay > spicedelay)
408 error = (double)((tasdelay - spicedelay) /
409 (double)(tasdelay)) ;
410 else
411 error = (double)((spicedelay - tasdelay) /
412 (double)(spicedelay)) ;
413 if (componly) break;
414 tref = (double)((double)(spicedelay) /
415 (double)(tasdelay)) ;
416 MCC_CGSN = MCC_CGSN * tref ;
417 MCC_CGSP = MCC_CGSP * tref ;
418 MCC_CGDN = MCC_CGDN * tref ;
419 MCC_CGDCN = MCC_CGDCN * tref ;
420 MCC_CGDP = MCC_CGDP * tref ;
421 MCC_CGDCP = MCC_CGDCP * tref ;
422 MCC_CGSIN = MCC_CGSIN * tref ;
423 MCC_CGSICN = MCC_CGSICN * tref ;
424 MCC_CGSIP = MCC_CGSIP * tref ;
425 MCC_CGSICP = MCC_CGSICP * tref ;
426 MCC_CGPN = MCC_CGPN * tref ;
427 MCC_CGPP = MCC_CGPP * tref ;
428 break ;
429 case MCC_FIT_CDN : tasdelay = MCC_TASUD + MCC_TASDU ;
430 spicedelay = MCC_SPICEUD_FITDN + MCC_SPICEDU_FITDN;
431 if (f!=NULL) fprintf(f,"%s spice delay : UD=%ld DU=%ld slope : UD=%ld DU=%ld\n",filename,MCC_SPICEUD_FITDN,MCC_SPICEDU_FITDN,MCC_SPICEFUD_FITDN,MCC_SPICEFDU_FITDN) ;
432 if(tasdelay > spicedelay)
433 error = (double)((tasdelay - spicedelay) /
434 (double)(tasdelay)) ;
435 else
436 error = (double)((spicedelay - tasdelay) /
437 (double)(spicedelay)) ;
438 if (componly) break;
439 tref = (double)((double)(spicedelay) /
440 (double)(tasdelay)) ;
441 MCC_CDSN = MCC_CDSN * tref ;
442 MCC_CDS_U_N = MCC_CDS_U_N * tref ;
443 MCC_CDS_D_N = MCC_CDS_D_N * tref ;
444 MCC_CDPN = MCC_CDPN * tref ;
445 MCC_CDP_U_N = MCC_CDP_U_N * tref ;
446 MCC_CDP_D_N = MCC_CDP_D_N * tref ;
447 MCC_CDWN = MCC_CDWN * tref ;
448 MCC_CDW_U_N = MCC_CDW_U_N * tref ;
449 MCC_CDW_D_N = MCC_CDW_D_N * tref ;
450 MCC_CSSN = MCC_CDSN ;
451 MCC_CSS_U_N = MCC_CDS_U_N ;
452 MCC_CSS_D_N = MCC_CDS_D_N ;
453 MCC_CSPN = MCC_CDPN ;
454 MCC_CSP_U_N = MCC_CDP_U_N ;
455 MCC_CSP_D_N = MCC_CDP_D_N ;
456 MCC_CSWN = MCC_CDWN ;
457 MCC_CSW_U_N = MCC_CDW_U_N ;
458 MCC_CSW_U_N = MCC_CDW_D_N ;
459 break ;
460 case MCC_FIT_CDP : tasdelay = MCC_TASUD + MCC_TASDU ;
461 spicedelay = MCC_SPICEUD_FITDP + MCC_SPICEDU_FITDP;
462 if (f!=NULL) fprintf(f,"%s spice delay : UD=%ld DU=%ld slope : UD=%ld DU=%ld\n",filename,MCC_SPICEUD_FITDP,MCC_SPICEDU_FITDP,MCC_SPICEFUD_FITDP,MCC_SPICEFDU_FITDP) ;
463 if(tasdelay > spicedelay)
464 error = (double)((tasdelay - spicedelay) /
465 (double)(tasdelay)) ;
466 else
467 error = (double)((spicedelay - tasdelay) /
468 (double)(spicedelay)) ;
469 if (componly) break;
470 tref = (double)((double)(spicedelay) /
471 (double)(tasdelay)) ;
472 MCC_CDSP = MCC_CDSP * tref ;
473 MCC_CDS_U_P = MCC_CDS_U_P * tref ;
474 MCC_CDS_D_P = MCC_CDS_D_P * tref ;
475 MCC_CDPP = MCC_CDPP * tref ;
476 MCC_CDP_U_P = MCC_CDP_U_P * tref ;
477 MCC_CDP_D_P = MCC_CDP_D_P * tref ;
478 MCC_CDWP = MCC_CDWP * tref ;
479 MCC_CDW_U_P = MCC_CDW_U_P * tref ;
480 MCC_CDW_D_P = MCC_CDW_D_P * tref ;
481 MCC_CSSP = MCC_CDSP ;
482 MCC_CSS_U_P = MCC_CDS_U_P ;
483 MCC_CSS_D_P = MCC_CDS_D_P ;
484 MCC_CSPP = MCC_CDPP ;
485 MCC_CSP_U_P = MCC_CDP_U_P ;
486 MCC_CSP_D_P = MCC_CDP_D_P ;
487 MCC_CSWP = MCC_CDWP ;
488 MCC_CSW_U_P = MCC_CDW_U_P ;
489 MCC_CSW_D_P = MCC_CDW_D_P ;
490 break ;
491 }
492 maxloop-- ;
493 error = error * 100.0 ;
494 if (f!=NULL) fprintf(f,"tasdelay = %ld spicedelay = %ld ratio = %g\n",
495 tasdelay,spicedelay,error) ;
496 if(maxloop == 0 || componly)
497 break ;
498 }
499 mbkfree(filename) ;
500 if (!componly) mcc_drvelp(i,MCC_TRANS_B,lotrsparam_n,lotrsparam_p,MCC_DRV_ALL_MODEL) ;
501 }
502 if (f!=NULL) fclose(f);
503
504 mcc_gencurv(MCC_FIT,lotrsparam_n,lotrsparam_p) ;
505 }