1 /****************************************************************************/
3 /* Chaine de CAO & VLSI AVERTEC */
5 /* Produit : AVERTEC global tools */
6 /* Fichier : mbk_fileextract.c */
8 /* © copyright 2000 AVERTEC */
9 /* Tous droits reserves */
11 /* Auteur(s) : Antony PINTO */
13 /****************************************************************************/
16 #include "mbk_fileextract.h"
18 static int mfe_error();
20 static void newlabel(label_table
**table
);
21 static void freelabel(label_table
*label
, int nbmc
);
22 static void newrule(extract_rules
**ruleslist
);
23 static void freerule(extract_rules
*rule
);
24 static void allocref(label_ref
**ref
);
25 static int affectlabel(label_ref
*ref
, char *label
, double value
, int match
, int nbmc
);
26 static void duplabel(label_ref
**new, label_table
*tbl
);
27 static void freeref(label_ref
**ref
);
28 static int decodeline(char *buf
, extract_rules
*rules
, label_ref
*ref
, int usemc
);
30 static int __getline(FILE *fd
, char *buf
);
31 static int istoken(char *buf
, char *token
, int *offset
);
32 static int isvalue(char *buf
, double *value
, int *offset
);
33 static int istext(char *buf
, char text
[], int *offset
);
34 static int matchline(char *head
, extract_rules
*rule
, label_ref
*ref
, int usemc
);
35 static int matchtoken(char *head
, char *token
, int *offset
, char *label
, double *value
, char *isval
);
36 static int matchtableline(char *head
, extract_rules
*rule
);
38 static int domatchvarval(label_ref
*ref
, extract_rules
*rule
);
40 static int MFE_DEBUG_MODE
= 0;
42 #define GO2ERR(x) do { ret = (x); goto endfunc; } while(0)
46 /*{{{ Memory tracing */
47 /****************************************************************************/
49 static void *alloc
[2048][2];
55 memset(alloc
,0,2048 * 2 * sizeof(void *));
63 printf("There is %d blocs allocated\n",nballoc
);
64 for (i
= 0; i
< 2048; i
++)
66 res
+= (long) alloc
[i
][1];
67 printf("It makes %ld bytes\n",res
);
74 printf("All memory allocated hasn't been freed\n");
80 void *alloue(int size
)
91 for (i
= 0; i
< 2048; i
++)
95 alloc
[i
][1] = (void *)size
;
103 void desalloue(void *ptr
)
107 for (i
= 0; i
< 2048; i
++)
108 if (alloc
[i
][0] == ptr
)
110 mbkfree(alloc
[i
][0]);
118 char *copystr(char *str
)
128 res
= mbkstrdup(str
);
129 for (i
= 0; i
< 2048; i
++)
133 alloc
[i
][1] = (void *)strlen(str
);
141 /*}}}************************************************************************/
142 /*}}}************************************************************************/
144 static void print_error(FILE *fd
, int code
);
145 static void print_rule(extract_rules
*rule
);
146 static void ruletostr(char *buf
, extract_rules
*rule
);
148 /*{{{ tests functions */
149 /*{{{ print_error() */
152 /****************************************************************************/
153 static void print_error(FILE *fd
, int code
)
155 fprintf(fd
,"[RUL_ERR] ");
159 fprintf(fd
,"unknow type\n");
162 fprintf(fd
,"unable to decode begin and end\n");
165 fprintf(fd
,"too much token (superior to 1024)\n");
168 fprintf(fd
,"rule problem\n");
173 /*}}}************************************************************************/
174 /*{{{ print_rule() */
177 /****************************************************************************/
178 static void print_rule(extract_rules
*rule
)
182 if (rule
->TYPE
== RULE_TYPE_LINE
)
183 printf("type : line\n");
184 else if (rule
->TYPE
== RULE_TYPE_TABLE
)
185 printf("type : table\n");
186 // printf("begin : %s\n",(rule->BEGIN) ? rule->BEGIN : "NULL");
187 // printf("end : %s\n",(rule->END) ? rule->END : "NULL");
188 printf("begin : %s\n",rule
->BEGIN
);
189 printf("end : %s\n",rule
->END
);
190 printf("nbtoken : %d\n",rule
->NBTOKEN
);
191 for (i
= 0; i
< rule
->NBTOKEN
; i
++)
192 printf("token %3d : %s\n",i
,rule
->TOKEN
[i
]);
193 printf("next : %p\n",rule
->NEXT
);
196 /*}}}************************************************************************/
200 /****************************************************************************/
201 static int testrule(int trace
)
203 extract_rules
*rules_list
= NULL
, *rx
, *tmp
;
207 "line:/begin/end0/:# %r %t %y %u %f",
208 "line://end1/:& %r %t %y %u %f" ,
209 "line:/beginend2/:* %r %t %y %u %f" ,
210 "line:begin/end3/:^%r %t %y %u %f" ,
211 "line:/begin/end4:u %r %t %y %u %f" ,
212 "table:/begin/end5/: okri %v kflk %t" ,
213 "array:/begin/end6/:%r %t %y %u %f"
217 0 , RULE_TYPE_LINE
, 1, 1 , 6,
218 0 , RULE_TYPE_LINE
, 1, 1 , 6,
219 RULE_BEGE_ERR
, 0 , 0, 0 , 0,
220 RULE_BEGE_ERR
, 0 , 0, 0 , 0,
221 RULE_BEGE_ERR
, 0 , 0, 0 , 0,
222 0 , RULE_TYPE_TABLE
, 1, 1 , 3,
223 RULE_TYPE_ERR
, 0 , 0, 0 , 0,
229 if (trace
) printf("-**** %s readrules ****-\n",__func__
);
230 for (i
= 0; i
< (int)(sizeof(ruletab
) / sizeof(char *)); i
++)
232 if (trace
) printf("-**************-\n");
233 if (trace
) printf(" %d, %s\n",i
,ruletab
[i
]);
234 if (trace
) printf("-**************-\n");
235 if ((res
= mfe_addrule(&rules_list
,ruletab
[i
])))
237 if (trace
) print_error(stderr
,res
);
241 if (trace
) print_rule(rules_list
);
245 if (res
!= restab
[i
*5]) nberr
++;
248 if (rules_list
->TYPE
!= restab
[i
*5 + 1]) nberr
++;
249 if (rules_list
->BEGIN
&& !restab
[i
*5 + 2]) nberr
++;
250 if (!rules_list
->BEGIN
&& restab
[i
*5 + 2]) nberr
++;
251 if (rules_list
->END
&& !restab
[i
*5 + 3]) nberr
++;
252 if (!rules_list
->END
&& restab
[i
*5 + 3]) nberr
++;
253 if (rules_list
->NBTOKEN
!= restab
[i
*5 + 4]) nberr
++;
256 mfe_delrule(&rules_list
,tmp
);
257 if (trace
) printf("-**** %s del ****-\n",__func__
);
258 for (rx
= rules_list
; rx
; rx
= rx
->NEXT
)
260 if (trace
) print_rule(rx
);
262 mfe_freerules(&rules_list
);
264 if (trace
) printf("-**** %s free ****-\n",__func__
);
265 if (closememory()) nberr
++;
267 if (nberr
) printf("%s %d errors\n",__func__
,nberr
);
272 /*}}}************************************************************************/
276 /****************************************************************************/
277 static int testlabels(int trace
)
296 /*}}}************************************************************************/
300 /****************************************************************************/
301 static int testisvalue(int trace
)
318 int nberr
= 0, offset
, set
;
320 if (trace
) printf("-**** %s 1 ****-\n",__func__
);
321 for (i
= 0; i
< sizeof(res1
)/sizeof(double); i
++)
324 if (isvalue(test1
[i
],&value
,&offset
))
326 if (trace
) printf(" tested : %s\n",test1
[i
]);
327 if (trace
) printf(" error code\n");
330 if (value
!= res1
[i
])
332 if (trace
) printf(" tested : %s\n",test1
[i
]);
333 if (trace
) printf(" obtained : %g\n",value
);
336 if (offset
!= (int)(5+i
))
338 if (trace
) printf(" tested : %s\n",test1
[i
]);
339 if (trace
) printf(" offset : %d\n",offset
);
344 if (trace
) printf("-**** %s 2 ****-\n",__func__
);
346 for (i
= 0; i
< sizeof(res1
)/sizeof(double); i
++)
348 strcat(buf
,test1
[i
]);
354 for (i
= 0; i
< sizeof(res1
)/sizeof(double); i
++)
357 if (isvalue(buf
,&value
,&offset
))
359 if (trace
) printf(" tested : %s\n",test1
[i
]);
360 if (trace
) printf(" error code\n");
363 if (value
!= res1
[i
])
365 if (trace
) printf(" tested : %s\n",test1
[i
]);
366 if (trace
) printf(" obtained : %g\n",value
);
371 if (trace
) printf(" tested : %s\n",test1
[i
]);
372 if (trace
) printf(" offset : %d\n",offset
);
378 if (nberr
) printf("%s %d errors\n",__func__
,nberr
);
383 /*}}}************************************************************************/
387 /****************************************************************************/
388 static int testistoken(int trace
)
390 int nberr
= 0, offset
;
392 if (trace
) printf("-**** %s ****-\n",__func__
);
394 if (istoken("test du token","test",&offset
)) nberr
++;
395 if (istoken("test du token","du",&offset
)) nberr
++;
396 if (istoken("test du token","token",&offset
)) nberr
++;
398 if (nberr
) printf("%s %d errors\n",__func__
,nberr
);
403 /*}}}************************************************************************/
407 /****************************************************************************/
408 static int testistext(int trace
)
414 }, buf
[2048], test2
[2048];
421 int nberr
= 0, offset
, set
;
423 if (trace
) printf("-**** %s 1 ****-\n",__func__
);
424 for (i
= 0; i
< sizeof(res
)/sizeof(double); i
++)
427 if (istext(test1
[i
],buf
,&offset
) && res
[i
])
429 if (trace
) printf(" tested : %s\n",test1
[i
]);
430 if (trace
) printf(" error code\n");
433 if (strcmp(test1
[i
],buf
))
435 if (trace
) printf(" tested : %s\n",test1
[i
]);
436 if (trace
) printf(" obtained : %s\n",buf
);
439 if (offset
!= (int)(6+i
))
441 if (trace
) printf(" tested : %s\n",test1
[i
]);
442 if (trace
) printf(" offset : %d\n",offset
);
447 if (trace
) printf("-**** %s 2 ****-\n",__func__
);
449 for (i
= 0; i
< sizeof(res
)/sizeof(double); i
++)
451 strcat(test2
,test1
[i
]);
457 for (i
= 0; i
< sizeof(res
)/sizeof(double); i
++)
460 if (istext(test2
,buf
,&offset
) && res
[i
])
462 if (trace
) printf(" tested : %s\n",test1
[i
]);
463 if (trace
) printf(" error code\n");
466 if (strcmp(buf
,test1
[i
]))
468 if (trace
) printf(" tested : %s\n",test1
[i
]);
469 if (trace
) printf(" obtained : %s\n",buf
);
474 if (trace
) printf(" tested : %s\n",test1
[i
]);
475 if (trace
) printf(" offset : %d\n",offset
);
481 if (nberr
) printf("%s %d errors\n",__func__
,nberr
);
486 /*}}}************************************************************************/
490 /****************************************************************************/
491 static void filetitan(FILE * fd
)
494 "Measure results from Transient analysis:\n"
495 " ==============================================================================\n"
497 " --- Nominal Run, Temperature = -30.000 (Deg C)\n"
499 " Measure Statement | Result | Trigger Point | Target Point\n"
500 " ------------------------------------------------------------------------------\n"
501 " D_RISE | 2.24824269E-09 | 9.50000000E-10 | 3.19824269E-09\n"
502 " D_FALL | 2.37524146E-09 | 1.95000000E-09 | 4.32524146E-09\n");
505 /*}}}************************************************************************/
509 /****************************************************************************/
510 static void filehsp(FILE * fd
)
513 "$DATA1 SOURCE='HSPICE' VERSION='2002.2' \n"
515 " d_rise d_fall temper alter# \n"
516 " 5.369e-09 5.669e-09 110.0000 1.0000\n"
520 /*}}}************************************************************************/
524 /****************************************************************************/
525 static void filehsp2(FILE * fd
)
528 "$DATA1 SOURCE='HSPICE' VERSION='U-2003.03'\n"
530 "sim_slope_sig129 sim_delay_sig131___sig129 sim_slope_sig131\n"
531 "sim_delay_sig218___sig131 sim_slope_sig218 sim_delay_sig147___sig218\n"
532 "sim_slope_sig147 sim_delay_sig216___sig147 sim_slope_sig216\n"
533 "sim_delay_sig151___sig216 sim_slope_sig151 sim_delay_sig214___sig151 \n"
534 "sim_slope_sig214 sim_delay_sig159___sig214 sim_slope_sig159 \n"
535 "sim_delay_tran18_grid___sig159 sim_slope_tran7_drain \n"
536 "sim_delay_tran7_drain___tran18_grid sim_slope_tran18_grid \n"
537 "sim_delay_tran7_grid___tran7_drain sim_slope_tran15_source \n"
538 "sim_delay_tran15_source___tran7_grid sim_slope_tran7_grid \n"
539 "sim_delay_sig196___tran15_source sim_slope_sig196 sim_delay_sig202___sig196\n"
540 "sim_slope_sig202 sim_delay_sig203___sig202 sim_delay_sig203___sig131 temper\n"
542 "5.208e-09 -1.923e-10 1.311e-08 1.070e-08 5.642e-10 3.349e-10 2.148e-09\n"
543 "1.496e-09 5.225e-10 3.084e-10 2.141e-09 1.716e-09 5.709e-10 3.261e-10\n"
544 "2.201e-09 1.793e-09 1.306e-09 6.667e-13 1.306e-09 5.070e-10 4.767e-09\n"
545 "1.853e-12 4.768e-09 3.402e-09 9.945e-10 5.941e-10 3.596e-10 3.751e-10\n"
546 "2.156e-08 125.0000 1.0000\n"
550 /*}}}************************************************************************/
554 /****************************************************************************/
555 static int testfile(int trace
)
560 "line:/EXTRACT INFORMATION/1****/:* %l = %v targ= %0 trig= %0",
561 "line:///:%l | %v | %0 | %0",
562 "table:/.TITLE ' '//:%l %v"
566 "sim_save_titan.tr.measure",
573 { 5.3665e-09 , 5.6704e-09 },
574 { 2.24824269E-09 , 2.37524146E-09 },
575 { 5.369e-9 , 5.669e-09 }
577 int nblabel
= (int)(sizeof(label
)/sizeof(char*));
578 int nbtest
= (int)(sizeof(rule
)/sizeof(char*));
579 extract_rules
*rules
= NULL
;
580 label_ref
*labels
= NULL
;
585 for (i
= 0; i
< nbtest
; i
++)
587 if (trace
) printf("-**** %s %s ****-\n",__func__
,filename
[i
]);
589 mfe_addrule(&rules
,rule
[i
]);
591 for (j
= 0; j
< nblabel
; j
++)
592 mfe_addlabel(&labels
,label
[j
],0);
594 mfe_fileextractlabel(filename
[i
],rules
,labels
,0);
596 for (j
= 0; j
< nblabel
; j
++)
597 if (!mfe_labelvalue(labels
,label
[j
],&value
,-1))
599 if (trace
) printf(" %s = %g\n",label
[j
],value
);
600 if (value
- res
[i
][j
] > 1e-12 || value
- res
[i
][j
] < -1e-12) nberr
++;
606 mfe_freelabels(&labels
);
607 mfe_freerules(&rules
);
610 if (closememory()) nberr
++;
612 if (nberr
) printf("%s %d errors\n",__func__
,nberr
);
617 /*}}}************************************************************************/
621 /****************************************************************************/
622 static int testfile2(int trace
)
626 char *rule
= "table:/.TITLE '*e'//:%l %v";
627 char *filename
= "main.hsp.mt01";
629 "sim_slope_sig129", "sim_delay_sig131___sig129", "sim_slope_sig131",
630 "sim_delay_sig218___sig131", "sim_slope_sig218", "sim_delay_sig147___sig218",
631 "sim_slope_sig147", "sim_delay_sig216___sig147", "sim_slope_sig216",
632 "sim_delay_sig151___sig216", "sim_slope_sig151", "sim_delay_sig214___sig151",
633 "sim_slope_sig214", "sim_delay_sig159___sig214", "sim_slope_sig159",
634 "sim_delay_tran18_grid___sig159", "sim_slope_tran7_drain",
635 "sim_delay_tran7_drain___tran18_grid", "sim_slope_tran18_grid",
636 "sim_delay_tran7_grid___tran7_drain", "sim_slope_tran15_source",
637 "sim_delay_tran15_source___tran7_grid", "sim_slope_tran7_grid",
638 "sim_delay_sig196___tran15_source", "sim_slope_sig196", "sim_delay_sig202___sig196",
639 "sim_slope_sig202", "sim_delay_sig203___sig202", "sim_delay_sig203___sig131"
642 5.208e-09 , -1.923e-10 , 1.311e-08 , 1.070e-08 , 5.642e-10 , 3.349e-10 , 2.148e-09 ,
643 1.496e-09 , 5.225e-10 , 3.084e-10 , 2.141e-09 , 1.716e-09 , 5.709e-10 , 3.261e-10 ,
644 2.201e-09 , 1.793e-09 , 1.306e-09 , 6.667e-13 , 1.306e-09 , 5.070e-10 , 4.767e-09 ,
645 1.853e-12 , 4.768e-09 , 3.402e-09 , 9.945e-10 , 5.941e-10 , 3.596e-10 , 3.751e-10 ,
648 int nblabel
= (int)(sizeof(label
)/sizeof(char*));
649 extract_rules
*rules
= NULL
;
650 label_ref
*labels
= NULL
;
653 tmpfile
= fopen(filename
,"w");
660 if (trace
) printf("-**** %s %s ****-\n",__func__
,filename
);
662 mfe_addrule(&rules
,rule
);
664 for (j
= 0; j
< nblabel
; j
++)
666 //if (trace) printf("-**** adding label %s in database\n",label[j]);
667 mfe_addlabel(&labels
,label
[j
],0);
670 mfe_fileextractlabel(filename
,rules
,labels
,0);
672 for (j
= 0; j
< nblabel
; j
++)
673 if (!mfe_labelvalue(labels
,label
[j
],&value
,-1))
675 if (trace
) printf(" %s = %g\n",label
[j
],value
);
676 if (value
- res
[j
] > 1e-12 || value
- res
[j
] < -1e-12) nberr
++;
682 mfe_freelabels(&labels
);
683 mfe_freerules(&rules
);
685 if (closememory()) nberr
++;
687 if (nberr
) printf("%s %d errors\n",__func__
,nberr
);
692 /*}}}************************************************************************/
696 /****************************************************************************/
697 static int testglobal(int trace
)
703 extract_rules
*rules
= NULL
;
707 void (*func
[])(FILE*) = {
711 "line:///:%l | %v | %0 | %0",
712 "table:/.TITLE ' '//:%l %v" };
713 label_ref
*labels
= NULL
;
719 { 2.24824269E-09 , 2.37524146E-09 },
720 { 5.369e-9 , 5.669e-09}
726 if (trace
) printf("-**** %s ****-\n",__func__
);
730 for (i
= 0; i
< (int)(sizeof(buf
)/(26*sizeof(char))); i
++)
732 sprintf(buf
[i
],"%stestfileXXXXXX",type
[i
]);
734 if (trace
) printf("-**** %s generating testfile %s ****-\n",__func__
,buf
[i
]);
735 tmpfile
= fopen(buf
[i
],"w");
740 for (i
= 0; i
< 2; i
++)
742 if (trace
) printf("-**** %s starting test %s ****-\n",__func__
,buf
[i
]);
743 mfe_addrule(&rules
,rule
[i
]);
744 for (j
= 0; j
< 2; j
++)
745 mfe_addlabel(&labels
,label
[j
],0);
747 mfe_fileextractlabel(buf
[i
],rules
,labels
,0);
749 for (j
= 0; j
< 2; j
++)
750 if (!mfe_labelvalue(labels
,label
[j
],&value
,-1))
752 if (trace
) printf(" %s = %g\n",label
[j
],value
);
753 if (value
- res
[i
][j
] > 1e-19 || value
- res
[i
][j
] < -1e-19) nberr
++;
759 mfe_freelabels(&labels
);
760 mfe_freerules(&rules
);
764 if (closememory()) nberr
++;
766 if (nberr
) printf("%s %d errors\n",__func__
,nberr
);
771 /*}}}************************************************************************/
775 /****************************************************************************/
776 static int testduplication(int trace
)
778 extract_rules
*rules
= NULL
, *duprules
, *rx
;
779 label_ref
*ref
= NULL
, *dupref
;
781 "line:/EXTRACT INFORMATION/1****/:* %l = %v targ= %0 trig= %0",
782 "line:///:%l | %v | %0 | %0",
783 "table:/.TITLE ' '//:%l %v"
785 "d_rise" , "d_fall", "test_2"
787 int nblabel
= (int)(sizeof(label
)/sizeof(char*));
788 int nbrule
= (int)(sizeof(rule
)/sizeof(char*));
794 if (trace
) printf("-**** %s ****-\n",__func__
);
798 for (i
= 0; i
< nbrule
; i
++)
799 mfe_addrule(&rules
,rule
[i
]);
800 for (i
= 0; i
< nblabel
; i
++)
801 mfe_addlabel(&ref
,label
[i
],0);
803 if (trace
) printf("-**** %s affect ref ****-\n",__func__
);
804 for (i
= 0; i
< nblabel
; i
++)
806 if (affectlabel(ref
,min_namealloc(label
[i
]),(double)i
,LABL_FOUND
,0)) nberr
++;
807 if (mfe_labelvalue(ref
,min_namealloc(label
[i
]),&value
,-1)) nberr
++;
808 if (trace
) printf(" %s = %g\n",label
[i
],value
);
811 if (trace
) printf("-**** %s affiche rules ****-\n",__func__
);
812 for (i
= nbrule
, rx
= rules
; i
> 0; i
--, rx
= rx
->NEXT
)
815 if (trace
) printf(" %s\n",buf
);
816 if (trace
) printf(" %s\n",rule
[i
-1]);
817 if (strcmp(rule
[i
-1],buf
)) nberr
++;
820 if (trace
) printf("-**** %s duplication ****-\n",__func__
);
821 mfe_duprules(&duprules
,rules
);
822 mfe_duplabels(&dupref
,ref
);
824 if (trace
) printf("-**** %s free ****-\n",__func__
);
825 mfe_freerules(&rules
);
826 mfe_freelabels(&ref
);
828 if (trace
) printf("-**** %s affiche duprules ****-\n",__func__
);
829 for (i
= nbrule
, rx
= duprules
; i
> 0; i
--, rx
= rx
->NEXT
)
832 if (trace
) printf(" %s\n",buf
);
833 if (trace
) printf(" %s\n",rule
[i
-1]);
834 if (strcmp(rule
[i
-1],buf
)) nberr
++;
837 for (i
= 0; i
< nblabel
; i
++)
839 if (mfe_labelvalue(dupref
,label
[i
],&value
,-1) != LABL_NOTFOUND
)
841 if (trace
) printf(" %s = %g\n",label
[i
],value
);
844 mfe_freerules(&duprules
);
845 mfe_freelabels(&dupref
);
847 if (closememory()) nberr
++;
848 if (nberr
) printf("%s %d errors\n",__func__
,nberr
);
852 /*}}}************************************************************************/
855 /* test function for mbk_fileextract */
857 /* />gcc -o main -L$AVT_DISTRIB_DIR/lib -Xlinker -z -Xlinker allextract \
858 -lMut325 -lstdc++ -lnsl -ldl -lm -Xlinker -z -Xlinker defaultextract */
861 /****************************************************************************/
862 int main(int argc
, char *argv
[])
871 nberr
+= testrule(trace
);
872 nberr
+= testisvalue(trace
);
873 nberr
+= testistoken(trace
);
874 nberr
+= testistext(trace
);
875 nberr
+= testglobal(trace
);
876 nberr
+= testfile(trace
);
877 nberr
+= testfile2(trace
);
878 nberr
+= testduplication(trace
);
880 if (nberr
) printf("total : %d errors\n",nberr
);
881 else printf("ok : %d error\n",nberr
);
886 /*}}}************************************************************************/
890 /****************************************************************************/
891 static void ruletostr(char *buf
, extract_rules
*rule
)
897 if (rule
->TYPE
== RULE_TYPE_LINE
)
898 strcat(buf
,"line:/");
899 else if (rule
->TYPE
== RULE_TYPE_TABLE
)
900 strcat(buf
,"table:/");
902 strcat(buf
,rule
->BEGIN
);
904 strcat(buf
,rule
->END
);
906 for (i
= 0; i
< rule
->NBTOKEN
; i
++)
910 strcat(buf
,rule
->TOKEN
[i
]);
914 /*}}}************************************************************************/
915 /*}}}************************************************************************/
916 /*}}}************************************************************************/
919 #define alloue(size) mbkalloc(size)
920 #define desalloue(ptr) mbkfree(ptr)
921 #define copystr(str) mbkstrdup(str)
923 #define closememory() 0
924 /*}}}************************************************************************/
926 /****************************************************************************/
927 /*{{{ Static functions */
928 /****************************************************************************/
932 /****************************************************************************/
933 static int mfe_error()
935 fprintf(stderr
,"[MFE_ERR]\n");
940 /*}}}************************************************************************/
944 /****************************************************************************/
945 static void newrule(extract_rules
**ruleslist
)
949 neo
= alloue(sizeof(extract_rules
));
950 memset(neo
,0,sizeof(extract_rules
));
951 neo
->NEXT
= *ruleslist
;
955 /*}}}************************************************************************/
959 /****************************************************************************/
960 static void freerule(extract_rules
*rule
)
967 desalloue(rule
->BEGIN
);
969 desalloue(rule
->END
);
970 for (i
= 0; i
< rule
->NBTOKEN
; i
++)
971 desalloue(rule
->TOKEN
[i
]);
973 desalloue(rule
->TOKEN
);
978 /*}}}************************************************************************/
982 /****************************************************************************/
983 static void newlabel(label_table
**table
)
987 neo
= alloue(sizeof(label_table
));
988 memset(neo
,0,sizeof(label_table
));
993 /*}}}************************************************************************/
997 /****************************************************************************/
998 static void freelabel(label_table
*label
, int cleanmc
)
1002 mbkfree( label
->VALUE
.MC
.TABLE
);
1007 /*}}}************************************************************************/
1011 /****************************************************************************/
1012 static void allocref(label_ref
**ref
)
1014 *ref
= alloue(sizeof(label_ref
));
1015 memset(*ref
,0,sizeof(label_ref
));
1016 (*ref
)->REFTBL
= addht(50);
1019 /*}}}************************************************************************/
1023 /****************************************************************************/
1024 static void freeref(label_ref
**ref
)
1026 delht((*ref
)->REFTBL
);
1031 /*}}}************************************************************************/
1032 /*{{{ affectlabel() */
1035 /****************************************************************************/
1036 static int affectlabel(label_ref
*ref
, char *label
, double value
, int match
, int usemc
)
1041 if ((lbl
= (label_table
*)gethtitem(ref
->REFTBL
,label
)) == (void*)EMPTYHT
)
1042 return LABL_ULBL_ERR
;
1046 printf("[MFE_MES] storing %g for %s\n",value
,label
);
1048 n
= lbl
->VALUE
.MC
.NBMC
;
1049 if( n
< lbl
->VALUE
.MC
.MAXMC
) {
1050 lbl
->VALUE
.MC
.TABLE
[n
] = value
;
1051 lbl
->VALUE
.MC
.NBMC
++ ;
1055 lbl
->VALUE
.NUMBER
= value
;
1062 /*}}}************************************************************************/
1066 /****************************************************************************/
1067 static void duplabel(label_ref
**new, label_table
*tbl
)
1071 duplabel(new, tbl
->NEXT
);
1072 mfe_addlabel(new,tbl
->LABEL
,0);
1076 /*}}}************************************************************************/
1077 /*{{{ __getline() */
1080 /****************************************************************************/
1081 static int __getline(FILE *fd
, char *buf
)
1085 if (fgets(buf
,MFE_CHAR_IN_LINE
,fd
))
1086 if ((len
= strlen(buf
)) != MFE_CHAR_IN_LINE
- 1)
1092 if (buf
[len
]<' ') buf
[len
]=' ';
1098 return MFE_LONGLINE_ERR
;
1103 /*}}}************************************************************************/
1107 /****************************************************************************/
1108 static int istext(char *buf
, char text
[], int *offset
)
1112 while (buf
[*offset
] == ' ')
1113 if (buf
[*offset
] == '\0')
1114 return RULE_MATC_ERR
;
1118 if (isalpha((int)buf
[*offset
]))
1120 while (buf
[*offset
] != ' ' && buf
[*offset
] != '=' && buf
[*offset
] != '\0')
1123 text
[i
++] = buf
[(*offset
)++];
1131 return RULE_MATC_ERR
;
1135 /*}}}************************************************************************/
1139 /****************************************************************************/
1140 static int istoken(char *buf
, char *token
, int *offset
)
1144 while (buf
[*offset
] == ' ')
1145 if (buf
[*offset
] == '\0')
1146 return RULE_MATC_ERR
;
1150 while (buf
[*offset
] != ' ' && buf
[*offset
] != '\0')
1151 if (token
[i
]=='\0') break;
1153 if (token
[i
++] != buf
[(*offset
)++])
1154 return RULE_MATC_ERR
;
1159 /*}}}************************************************************************/
1163 /****************************************************************************/
1164 static int isvalue(char *buf
, double *value
, int *offset
)
1169 valtmp
= strtod(buf
+ (*offset
)*sizeof(char), &endptr
);
1170 if (*offset
== endptr
- buf
)
1173 return RULE_MATC_ERR
;
1175 *offset
= endptr
- buf
;
1180 return RULE_MATC_ERR
;
1185 /*}}}************************************************************************/
1186 /*{{{ matchtoken() */
1189 /****************************************************************************/
1190 static int matchtoken(char *head
, char *token
, int *offset
,
1191 char *label
, double *value
, char *isval
)
1196 if (token
[0] == '%')
1200 res
= istext(head
,label
,offset
);
1202 isval
[0] = label
[0];
1203 len
= strlen(token
);
1206 tail
= label
+ strlen(label
) - (len
-2);
1207 if (!strcmp(tail
, token
+2))
1210 res
= RULE_UTOK_ERR
;
1213 printf("[MFE_MES] %s match token %s\n",label
,token
);
1216 res
= istext(head
,NULL
,offset
);
1219 res
= isvalue(head
,value
,offset
);
1221 printf("[MFE_MES] %g match token %s\n",*value
,token
);
1226 res
= isvalue(head
,NULL
,offset
);
1229 res
= RULE_UTOK_ERR
;
1233 res
= istoken(head
,token
,offset
);
1238 /*}}}************************************************************************/
1239 /*{{{ matchline() */
1242 /****************************************************************************/
1243 static int matchline(char *head
, extract_rules
*rule
, label_ref
*ref
, int usemc
)
1246 char label
[1024], *name
;
1252 for (i
= 0, offset
= 0; i
< rule
->NBTOKEN
; i
++)
1253 if (matchtoken(head
,rule
->TOKEN
[i
],&offset
,label
,&value
,0))
1256 if (label
[0] != '\0' && i
== rule
->NBTOKEN
&& (name
= min_namefind(label
)))
1258 affectlabel(ref
,name
,value
,LABL_FOUND
,usemc
);
1262 return RULE_FTOK_ERR
;
1265 /*}}}************************************************************************/
1266 /*{{{ matchtableline() */
1268 /* simple revision */
1269 /****************************************************************************/
1270 static int matchtableline(char *head
, extract_rules
*rule
)
1272 char *token
, label
[1024], is
/*what is*/;
1276 token
= rule
->TOKEN
[rule
->LINE
];
1279 rule
->LBLLIST
= alloue(500 * sizeof(label_list
));
1282 for (i
= 0; head
[offset
] != '\0'; i
++)
1285 if ((res
= matchtoken(head
,token
,&offset
,label
,&value
,&is
)))
1288 rule
->NBELT1ST
= rule
->NBELT
;
1292 if (rule
->LINE
> rule
->NBTOKEN
-1)
1296 rule
->NBELT1ST
= 0;
1298 // printf("[MFE_WAR] Be carefull, maybe the file hasn't been generated by unix systems\n");
1303 return matchtableline(head
,rule
);
1310 rule
->LBLLIST
[rule
->NBELT
].VALUE
= value
;
1314 rule
->LBLLIST
[rule
->NBELT
].LABEL
= min_namefind(label
);
1319 while (head
[offset
] == ' ')
1326 /*}}}************************************************************************/
1327 /*{{{ domatchvarval() */
1330 /****************************************************************************/
1331 static int domatchvarval(label_ref
*ref
, extract_rules
*rule
)
1335 for (i
= 0; i
< rule
->NBELT
; i
++)
1336 if (rule
->LBLLIST
[i
].LABEL
)
1337 affectlabel(ref
,rule
->LBLLIST
[i
].LABEL
,
1338 rule
->LBLLIST
[i
].VALUE
,LABL_FOUND
,-1);
1343 /*}}}************************************************************************/
1344 /*{{{ decodeline() */
1347 /****************************************************************************/
1348 static int decodeline(char *buf
, extract_rules
*rules
, label_ref
*ref
, int usemc
)
1352 for (rx
= rules
; rx
; rx
= rx
->NEXT
)
1354 if (rx
->ACTIVATED
!= RULE_UNACTIVATED
)
1355 if (rx
->END
[0] && strstr(buf
,rx
->END
))
1356 rx
->ACTIVATED
= RULE_UNACTIVATED
;
1357 else switch (rx
->TYPE
)
1359 case RULE_TYPE_LINE
:
1360 matchline(buf
,rx
,ref
,usemc
);
1362 case RULE_TYPE_TABLE
:
1363 if (matchtableline(buf
,rx
))
1367 else if (rx
->LINE
== rx
->NBTOKEN
-1 && rx
->NBELT
== rx
->NBELT1ST
)
1369 domatchvarval(ref
,rx
);
1374 return RULE_TYPE_ERR
;
1377 if (strstr(buf
,rx
->BEGIN
))
1378 rx
->ACTIVATED
= RULE_ACTIVATED
;
1383 /*}}}************************************************************************/
1384 /*}}}************************************************************************/
1385 /*{{{ Extern Functions */
1386 /****************************************************************************/
1387 /*{{{ mfe_addrule() */
1390 /****************************************************************************/
1391 int mfe_addrule(extract_rules
**ruleslist
, char *rule
)
1393 int i
, nbtoken
, ret
= 0;
1394 char *token
[1024], *next
, *begend
[2], line
[2048];
1397 // momentatly disable NEXT field
1402 sprintf(line
,"%s",rule
);
1406 if (next
[0] == 't' && next
[1] == 'a' && next
[2] == 'b' && next
[3] == 'l' &&
1407 next
[4] == 'e' && next
[5] == ':')
1409 next
= next
+ 6 * sizeof(char);
1410 res
->TYPE
= RULE_TYPE_TABLE
;
1412 else if (next
[0] == 'l' && next
[1] == 'i' && next
[2] == 'n' &&
1413 next
[3] == 'e' && next
[4] == ':')
1415 next
= next
+ 5 * sizeof(char);
1416 res
->TYPE
= RULE_TYPE_LINE
;
1419 GO2ERR(RULE_TYPE_ERR
);
1423 /* find begin and end */
1424 for (i
= 0; i
< 3; i
++)
1427 GO2ERR(RULE_BEGE_ERR
);
1429 next
= next
+ sizeof(char);
1433 if (!(next
= strchr(next
,'/')))
1434 GO2ERR(RULE_BEGE_ERR
);
1436 res
->BEGIN
= copystr(begend
[0]);
1437 res
->END
= copystr(begend
[1]);
1439 next
= next
+ sizeof(char);
1441 GO2ERR(RULE_BEGE_ERR
);
1445 if (res
->TYPE
== RULE_TYPE_LINE
)
1446 for (i
= 0, nbtoken
= 0; next
[i
] != '\0'; i
++)
1450 while (next
[j
] == ' ')
1452 if (j
!= i
|| i
== 0)
1455 token
[nbtoken
++] = next
+ i
* sizeof(char);
1457 GO2ERR(RULE_TOOT_ERR
);
1460 else if (res
->TYPE
== RULE_TYPE_TABLE
)
1461 for (i
= 0, nbtoken
= 0; next
[i
] != '\0'; i
++)
1465 while (next
[j
] == ' ')
1467 if (next
[j
] == '%' || i
== 0)
1472 token
[nbtoken
++] = next
+ i
* sizeof(char);
1474 GO2ERR(RULE_TOOT_ERR
);
1478 res
->TOKEN
= alloue(nbtoken
* sizeof(char *));
1479 res
->NBTOKEN
= nbtoken
;
1480 for (i
= 0; i
< nbtoken
; i
++)
1481 res
->TOKEN
[i
] = copystr(token
[i
]);
1485 mfe_delrule(ruleslist
,*ruleslist
);
1489 /*}}}************************************************************************/
1490 /*{{{ mfe_delrule() */
1493 /****************************************************************************/
1494 int mfe_delrule(extract_rules
**ruleslist
, extract_rules
*rule
)
1496 extract_rules
*rx
, head
;
1498 head
.NEXT
= *ruleslist
;
1499 for (rx
= &head
; rx
->NEXT
; rx
= rx
->NEXT
)
1500 if (rx
->NEXT
== rule
)
1502 rx
->NEXT
= rx
->NEXT
->NEXT
;
1504 *ruleslist
= head
.NEXT
;
1512 /*}}}************************************************************************/
1513 /*{{{ mfe_freerules() */
1516 /****************************************************************************/
1517 void mfe_freerules(extract_rules
**ruleslist
)
1521 mfe_freerules(&((*ruleslist
)->NEXT
));
1522 freerule(*ruleslist
);
1527 /*}}}************************************************************************/
1528 /*{{{ mfe_duprules() */
1531 /****************************************************************************/
1532 void mfe_duprules(extract_rules
**newrules
, extract_rules
*rules
)
1538 mfe_duprules(newrules
,rules
->NEXT
);
1540 (*newrules
)->TYPE
= rules
->TYPE
;
1541 (*newrules
)->ACTIVATED
= rules
->ACTIVATED
;
1542 (*newrules
)->NBTOKEN
= rules
->NBTOKEN
;
1543 (*newrules
)->TOKEN
= alloue(rules
->NBTOKEN
* sizeof(char *));
1544 for (i
= 0; i
< rules
->NBTOKEN
; i
++)
1545 (*newrules
)->TOKEN
[i
] = copystr(rules
->TOKEN
[i
]);
1546 (*newrules
)->BEGIN
= copystr(rules
->BEGIN
);
1547 (*newrules
)->END
= copystr(rules
->END
);
1553 /*}}}************************************************************************/
1554 /*{{{ mfe_addlabel() */
1557 /****************************************************************************/
1558 int mfe_addlabel(label_ref
**ref
, char *label
, int nbmc
)
1562 label
= min_namealloc(label
);
1565 res
= gethtitem((*ref
)->REFTBL
,label
);
1567 return LABL_LEXI_WAR
;
1572 tbl
= &((*ref
)->LABTBL
);
1574 (*tbl
)->LABEL
= label
;
1575 (*tbl
)->FLAG
= LABL_NOTFOUND
;
1577 (*tbl
)->VALUE
.MC
.TABLE
= (double*)mbkalloc( sizeof(double)*nbmc
);
1578 (*tbl
)->VALUE
.MC
.NBMC
= 0 ;
1579 (*tbl
)->VALUE
.MC
.MAXMC
= nbmc
;
1581 addhtitem((*ref
)->REFTBL
,label
,(long)*tbl
);
1587 /*}}}************************************************************************/
1588 /*{{{ mfe_dellabel() */
1591 /****************************************************************************/
1592 int mfe_dellabel(label_ref
**ref
, char *label
)
1594 label_table
*tbl
, *tx
, head
;
1596 tbl
= (label_table
*)gethtitem((*ref
)->REFTBL
,label
);
1597 if (tbl
== (label_table
*)EMPTYHT
)
1598 return LABL_ULBL_ERR
;
1601 head
.NEXT
= (*ref
)->LABTBL
;
1602 for (tx
= &head
; tx
->NEXT
; tx
= tx
->NEXT
)
1603 if (tx
->NEXT
== tbl
)
1605 delhtitem((*ref
)->REFTBL
,label
);
1610 (*ref
)->LABTBL
= head
.NEXT
;
1615 return LABL_PLBL_ERR
;
1619 /*}}}************************************************************************/
1620 /*{{{ mfe_freelabels() */
1623 /****************************************************************************/
1624 void mfe_freelabels(label_ref
**ref
, int cleanmc
)
1628 label_table
*tx
, *txx
;
1630 for (tx
= (*ref
)->LABTBL
; tx
; )
1633 freelabel(tx
, cleanmc
);
1640 /*}}}************************************************************************/
1641 /*{{{ mfe_duplabels() */
1644 /****************************************************************************/
1645 void mfe_duplabels(label_ref
**table
, label_ref
*ref
)
1648 duplabel(table
,ref
->LABTBL
);
1651 /*}}}************************************************************************/
1652 /*{{{ mfe_fileextractlabel() */
1655 /****************************************************************************/
1656 int mfe_fileextractlabel(char *filename
, extract_rules
*rules
, label_ref
*ref
, int nbmc
)
1673 for (rx
= rules
; rx
; rx
= rx
->NEXT
)
1676 if ((fd
= mbkfopen(filename
,NULL
,"r")))
1678 if (getenv("MFE_DEBUG"))
1680 buf
= alloue(MFE_LINE_SIZE
);
1682 while (!feof(fd
) && __getline(fd
,buf
)!=1)
1683 if (decodeline(buf
,rules
,ref
,usemc
))
1686 /* free rules buffer if needed */
1687 for (rx
= rules
; rx
; rx
= rx
->NEXT
)
1690 desalloue(rx
->LBLLIST
);
1704 /*}}}************************************************************************/
1705 /*{{{ mfe_labelvalue() */
1708 /****************************************************************************/
1709 int mfe_labelvalue(label_ref
*ref
, char *label
, double *value
, int idmc
)
1713 label
= min_namealloc(label
);
1714 if (ref
&& ref
->REFTBL
)
1715 if ((res
= gethtitem(ref
->REFTBL
,label
)) == EMPTYHT
)
1718 printf("[MFE_MES] %s doesn't match anything\n",label
);
1720 return LABL_ULBL_ERR
;
1724 label_table
*table
= (void *)res
;
1726 if (table
->FLAG
== LABL_NOTFOUND
)
1727 return LABL_NOTFOUND
;
1732 *value
= table
->VALUE
.MC
.TABLE
[ idmc
];
1734 *value
= table
->VALUE
.NUMBER
;
1737 printf("[MFE_MES] %s match, result is: %g\n",label
,*value
);
1739 return LABL_FOUND
; /* 0 */
1743 return LABL_UTBL_ERR
;
1746 /*}}}************************************************************************/
1747 /*{{{ mfe_cleanLabel() */
1750 /****************************************************************************/
1751 void mfe_cleanLabel(label_ref
*ref
)
1756 for (tx
= ref
->LABTBL
; tx
; tx
= tx
->NEXT
)
1758 tx
->FLAG
= LABL_NOTFOUND
;
1762 /*}}}************************************************************************/
1763 /*}}}************************************************************************/
1765 int mfe_readmeasure(char *filename
, void *mferules
, char *rule
, char *label
, double *value
)
1768 extract_rules
*crules
= (extract_rules
*)mferules
;
1769 label_ref
*labels
= NULL
;
1771 if (rule
!=NULL
) mfe_addrule(&crules
,rule
);
1773 mfe_addlabel(&labels
,label
, 0);
1775 mfe_fileextractlabel(filename
,crules
,labels
,0);
1777 err
=mfe_labelvalue(labels
,label
,value
,-1);
1779 mfe_freelabels(&labels
,0);
1780 if (rule
!=NULL
) mfe_freerules(&crules
);
1785 static int cutword(char *buf
, char **tab
, int max
)
1791 res
=strtok_r(buf
, " ", &r
);
1792 while (res
!=NULL
&& i
<max
)
1795 res
=strtok_r(NULL
, " ", &r
);
1800 void mfe_read_montecarlo_ltspice(char *filename
, label_ref
*ref
)
1808 if ((f
=fopen(filename
,"r"))!=NULL
)
1810 buf
= alloue(MFE_LINE_SIZE
);
1811 while (!feof(f
) && __getline(f
, buf
)!=1)
1813 i
=cutword(buf
, tab
, 5);
1814 if (i
==2 && strcasecmp(tab
[0],"Measurement:")==0)
1816 label
=min_namefind(tab
[1]);
1818 } else if (i
==0 || (i
==4 && label
!=NULL
&& strcasecmp(tab
[1],label
)==0 && strcasecmp(tab
[2],"from")==0 && strcasecmp(tab
[3],"to")==0))
1826 for (i
=lastidx
+1; i
<il
; i
++)
1827 affectlabel(ref
,label
,-1,LABL_FOUND
,1);
1828 affectlabel(ref
,label
,atof(tab
[1]),LABL_FOUND
,1);