Indentation fix, cleanup.
[AROS.git] / tools / cxref / xref.c
blob24fa308d137582a3b58909e842f3252b5b0b94f1
1 /***************************************
2 $Header$
4 C Cross Referencing & Documentation tool. Version 1.5e.
6 Cross referencing of functions.
7 ******************/ /******************
8 Written by Andrew M. Bishop
10 This file Copyright 1995,96,97,98,99,2000,01,02 Andrew M. Bishop
11 It may be distributed under the GNU Public License, version 2, or
12 any higher version. See section COPYING of the GNU Public license
13 for conditions under which this file may be redistributed.
14 ***************************************/
16 /*+ The names of the function cross reference files. +*/
17 #define XREF_FUNC_FILE ".function"
18 #define XREF_FUNC_BACKUP ".function~"
20 /*+ The names of the variable cross reference files. +*/
21 #define XREF_VAR_FILE ".variable"
22 #define XREF_VAR_BACKUP ".variable~"
24 /*+ The names of the include cross reference files. +*/
25 #define XREF_INC_FILE ".include"
26 #define XREF_INC_BACKUP ".include~"
28 /*+ The names of the type cross reference files. +*/
29 #define XREF_TYPE_FILE ".typedef"
30 #define XREF_TYPE_BACKUP ".typedef~"
32 #include <stdlib.h>
33 #include <stdio.h>
34 #include <string.h>
35 #include <unistd.h>
36 #include <limits.h>
38 #define TYPE_MAX_LEN 256 /*+ The maximum type definition length +*/
39 #define FUNC_MAX_LEN 64 /*+ The maximum function name length. +*/
40 #if defined(PATH_MAX) && defined(NAME_MAX)
41 #define FILE_MAX_LEN (PATH_MAX+NAME_MAX) /*+ The maximum filename length. +*/
42 #elif defined(PATH_MAX)
43 #define FILE_MAX_LEN (PATH_MAX+256) /*+ The maximum filename length. +*/
44 #else
45 #define FILE_MAX_LEN 512 /*+ The maximum filename length. +*/
46 #endif
48 #include "memory.h"
49 #include "datatype.h"
50 #include "cxref.h"
52 /*+ The name of the directory for the output. +*/
53 extern char* option_odir;
55 /*+ The base name of the file for the output. +*/
56 extern char* option_name;
58 /*+ The option for cross referencing. +*/
59 extern int option_xref;
61 /*+ The option for indexing. +*/
62 extern int option_index;
64 static void check_for_called(File file,char* called,char* caller,char* filename);
65 static void check_for_caller(File file,char* called,char* filename);
66 static void check_for_var(File file,char* variable,char* filename,int scope,char* funcname);
67 static int check_for_var_func(File file,Variable var,Function func);
68 static void fixup_extern_var(Variable var,StringList2 refs);
70 /*++++++++++++++++++++++++++++++++++++++
71 Cross reference the functions, variables and includes that are used in this file
72 with the global functions, variables and includes. The types that are defined are also listed here.
74 File file The file structure containing the information.
76 int outputs Set to true if any cross referencing to produce outputs is required.
77 ++++++++++++++++++++++++++++++++++++++*/
79 void CrossReference(File file,int outputs)
81 FILE *in,*out;
82 char *ifile,*ofile;
84 /* Format: filename [[%]include1] [[%]include2] ... : Files include1, include2, ... are included in filename;
85 those with a % are local. */
87 if(option_xref&XREF_FILE) /* First do the files */
89 Include inc;
91 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_INC_FILE);
92 ofile=ConcatStrings(4,option_odir,"/",option_name,XREF_INC_BACKUP);
94 in =fopen(ifile,"r");
95 out=fopen(ofile,"w");
97 if(!out)
98 {fprintf(stderr,"cxref: Failed to open the include cross reference file '%s'\n",ofile);exit(1);}
100 fprintf(out,"%s",file->name);
101 for(inc=file->includes;inc;inc=inc->next)
102 fprintf(out," %s%s",inc->scope==LOCAL?"%":"",inc->name);
103 fprintf(out,"\n");
105 if(in)
107 char include[FILE_MAX_LEN+1],filename[FILE_MAX_LEN+1],ch;
109 while(fscanf(in,"%s%c",filename,&ch)==2)
111 int diff_file=strcmp(filename,file->name);
113 if(diff_file)
114 fprintf(out,"%s",filename);
116 while(ch==' ')
118 fscanf(in,"%s%c",include,&ch);
120 if(diff_file)
121 fprintf(out," %s",include);
123 if(outputs)
124 if(include[0]=='%' && !strcmp(&include[1],file->name))
125 AddToStringList(file->inc_in,filename,1,1);
128 if(diff_file)
129 fprintf(out,"\n");
132 fclose(in);
133 unlink(ifile);
136 fclose(out);
137 rename(ofile,ifile);
140 /* Format: filename funcname scope [[%][&]funcname1] [[%][&]funcname2] ... : The function funcname in file filename
141 calls or references functions funcname1, funcname2 ... ; those with a % are local, with a & are references. */
142 /* Format: filename $ 0 [[%]&funcname1] [[%]&funcname2] ... : The file references functions funcname1, funcname2 ... ;
143 those with a % are local. */
145 if(option_xref&XREF_FUNC) /* Now do the functions */
147 Function func;
148 int i;
150 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_FUNC_FILE);
151 ofile=ConcatStrings(4,option_odir,"/",option_name,XREF_FUNC_BACKUP);
153 in =fopen(ifile,"r");
154 out=fopen(ofile,"w");
156 if(!out)
157 {fprintf(stderr,"cxref: Failed to open the functional cross reference file '%s'\n",ofile);exit(1);}
159 for(i=0;i<file->f_refs->n;i++)
160 check_for_called(file,ConcatStrings(2,"&",file->f_refs->s1[i]),NULL,file->name);
162 for(func=file->functions;func;func=func->next)
164 for(i=0;i<func->calls->n;i++)
165 check_for_called(file,func->calls->s1[i],func->name,file->name);
166 for(i=0;i<func->f_refs->n;i++)
167 check_for_called(file,ConcatStrings(2,"&",func->f_refs->s1[i]),func->name,file->name);
170 for(func=file->functions;func;func=func->next)
171 check_for_caller(file,func->name,file->name);
173 if(file->f_refs->n)
175 fprintf(out,"%s $ 0",file->name);
176 for(i=0;i<file->f_refs->n;i++)
178 if(file->f_refs->s2[i])
179 fprintf(out," %%&%s",file->f_refs->s1[i]);
180 else
181 fprintf(out," &%s",file->f_refs->s1[i]);
183 fprintf(out,"\n");
186 for(func=file->functions;func;func=func->next)
188 fprintf(out,"%s %s %d",file->name,func->name,func->scope);
189 for(i=0;i<func->calls->n;i++)
191 if(func->calls->s2[i])
192 fprintf(out," %%%s",func->calls->s1[i]);
193 else
194 fprintf(out," %s",func->calls->s1[i]);
196 for(i=0;i<func->f_refs->n;i++)
198 if(func->f_refs->s2[i])
199 fprintf(out," %%&%s",func->f_refs->s1[i]);
200 else
201 fprintf(out," &%s",func->f_refs->s1[i]);
203 fprintf(out,"\n");
206 if(in)
208 char ch,funcname[FUNC_MAX_LEN+1],filename[FILE_MAX_LEN+1],called[FUNC_MAX_LEN+1];
209 int scope;
211 while(fscanf(in,"%s %s %d%c",filename,funcname,&scope,&ch)==4)
213 int diff_file=strcmp(filename,file->name);
215 if(diff_file)
217 if(outputs)
218 if(funcname[0]!='$' || funcname[1]!=0)
219 check_for_caller(file,funcname,filename);
220 fprintf(out,"%s %s %d",filename,funcname,scope);
223 while(ch==' ')
225 fscanf(in,"%s%c",called,&ch);
227 if(diff_file)
229 if(outputs)
231 if(called[0]!='%')
233 if(funcname[0]!='$' || funcname[1]!=0)
234 check_for_called(file,called,funcname,filename);
235 else
236 check_for_called(file,called,NULL,filename);
239 fprintf(out," %s",called);
243 if(diff_file)
244 fprintf(out,"\n");
247 fclose(in);
248 unlink(ifile);
251 fclose(out);
252 rename(ofile,ifile);
255 /* Format: filename varname scope [$] [[%]funcname1] [[%]funcname2] ... : variable varname is used in
256 the file filename if $, and functions funcname1, funcname2 ... Those with a % are local. */
258 if(option_xref&XREF_VAR) /* Now do the variables */
260 Variable var;
261 Function func;
263 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_VAR_FILE);
264 ofile=ConcatStrings(4,option_odir,"/",option_name,XREF_VAR_BACKUP);
266 in =fopen(ifile,"r");
267 out=fopen(ofile,"w");
269 if(!out)
270 {fprintf(stderr,"cxref: Failed to open the variable cross reference file '%s'\n",ofile);exit(1);}
272 for(var=file->variables;var;var=var->next)
274 check_for_var(file,var->name,file->name,var->scope,NULL);
275 fprintf(out,"%s %s %d",file->name,var->name,var->scope);
276 if(check_for_var_func(file,var,NULL))
277 fprintf(out," $");
278 for(func=file->functions;func;func=func->next)
279 if(check_for_var_func(file,var,func))
280 fprintf(out," %s%s",func->scope==LOCAL?"%":"",func->name);
281 fprintf(out,"\n");
284 if(in)
286 char varname[FUNC_MAX_LEN+1],filename[FILE_MAX_LEN+1],funcname[FUNC_MAX_LEN+1],ch;
287 int scope;
289 while(fscanf(in,"%s %s %d%c",filename,varname,&scope,&ch)==4)
291 int diff_file=strcmp(filename,file->name);
293 if(diff_file)
295 if(outputs)
296 if(!(scope&LOCAL))
297 check_for_var(file,varname,filename,scope,NULL);
298 fprintf(out,"%s %s %d",filename,varname,scope);
301 while(ch==' ')
303 fscanf(in,"%s%c",funcname,&ch);
305 if(diff_file)
307 if(outputs)
309 if(!(scope&LOCAL))
311 if(funcname[0]=='%')
312 check_for_var(file,varname,filename,scope,&funcname[1]);
313 else
314 check_for_var(file,varname,filename,scope,funcname);
317 fprintf(out," %s",funcname);
321 if(diff_file)
322 fprintf(out,"\n");
325 fclose(in);
326 unlink(ifile);
329 /* We must fix the location of the extern variables now since it was not known earlier. */
331 if(outputs)
333 fixup_extern_var(file->variables,file->v_refs);
334 for(func=file->functions;func;func=func->next)
335 fixup_extern_var(file->variables,func->v_refs);
338 fclose(out);
339 rename(ofile,ifile);
342 /* Format: filename typename type... : For a typedef type. */
343 /* Format: filename # type... : For a non typedef type. */
345 if(option_xref&XREF_TYPE) /* Now do the types */
347 Typedef type;
349 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_TYPE_FILE);
350 ofile=ConcatStrings(4,option_odir,"/",option_name,XREF_TYPE_BACKUP);
352 in =fopen(ifile,"r");
353 out=fopen(ofile,"w");
355 if(!out)
356 {fprintf(stderr,"cxref: Failed to open the typedef reference file '%s'\n",ofile);exit(1);}
358 for(type=file->typedefs;type;type=type->next)
359 if(type->type)
360 fprintf(out,"%s %s %s\n",file->name,type->name,type->type);
361 else
362 fprintf(out,"%s # %s\n",file->name,type->name);
364 if(in)
366 char typename[TYPE_MAX_LEN+1],filename[FILE_MAX_LEN+1];
368 while(fscanf(in,"%s %s",filename,typename)==2)
370 int diff_file=strcmp(filename,file->name);
372 if(diff_file)
373 fprintf(out,"%s %s",filename,typename);
375 fgets(typename,TYPE_MAX_LEN,in);
377 if(diff_file)
378 fputs(typename,out);
381 fclose(in);
382 unlink(ifile);
385 fclose(out);
386 rename(ofile,ifile);
391 /*++++++++++++++++++++++++++++++++++++++
392 Check through all of the functions in this file to see if any of them are called or referenced.
394 File file The file structure.
396 char* called The function that is called.
398 char* caller The function that the called function is called from.
400 char* filename The file that the function is called from.
401 ++++++++++++++++++++++++++++++++++++++*/
403 static void check_for_called(File file,char* called,char* caller,char* filename)
405 Function func;
407 /* Check for function calls */
409 if(called[0]!='&')
410 for(func=file->functions;func;func=func->next)
412 if(!strcmp(called,func->name))
413 AddToStringList2(func->called,caller,filename,1,1);
416 /* Check for function references */
418 else
419 for(func=file->functions;func;func=func->next)
421 if(!strcmp(&called[1],func->name))
423 if(caller)
424 AddToStringList2(func->used,caller,filename,1,1);
425 else
426 AddToStringList2(func->used,"$",filename,1,0);
432 /*++++++++++++++++++++++++++++++++++++++
433 Check through all of the functions in this file to see if any of them are callers or referencers.
435 File file The file structure.
437 char* called The function that is called.
439 char* filename The file that the called function is in.
440 ++++++++++++++++++++++++++++++++++++++*/
442 static void check_for_caller(File file,char* called,char* filename)
444 int i;
445 Function func;
447 /* Check the functions that are called. */
449 for(func=file->functions;func;func=func->next)
450 for(i=0;i<func->calls->n;i++)
451 if(!strcmp(called,func->calls->s1[i]))
452 if(!func->calls->s2[i])
453 func->calls->s2[i]=MallocString(filename);
455 /* Check the functions that are referenced. */
457 for(i=0;i<file->f_refs->n;i++)
458 if(!strcmp(called,file->f_refs->s1[i]))
459 if(!file->f_refs->s2[i])
460 file->f_refs->s2[i]=MallocString(filename);
462 for(func=file->functions;func;func=func->next)
463 for(i=0;i<func->f_refs->n;i++)
464 if(!strcmp(called,func->f_refs->s1[i]))
465 if(!func->f_refs->s2[i])
466 func->f_refs->s2[i]=MallocString(filename);
470 /*++++++++++++++++++++++++++++++++++++++
471 Check through all of the variables in this file to see if any of them are extern usage of others.
473 File file The file structure.
475 char* variable The global variable name.
477 char* filename The file that the variable is used in.
479 int scope The scope of the variable in the foreign file.
481 char* funcname The name of a function that uses the variable.
482 ++++++++++++++++++++++++++++++++++++++*/
484 static void check_for_var(File file,char* variable,char* filename,int scope,char* funcname)
486 Variable var;
488 if(!funcname)
490 if(!(scope&(GLOBAL|EXTERNAL|EXTERN_H)))
491 return;
493 for(var=file->variables;var;var=var->next)
494 if((scope&GLOBAL && var->scope&(EXTERNAL|EXTERN_H|EXTERN_F)) ||
495 (scope&(GLOBAL|EXTERNAL|EXTERN_H) && var->scope&GLOBAL))
496 if(!strcmp(variable,var->name))
498 if(scope&GLOBAL && var->scope&(EXTERNAL|EXTERN_H|EXTERN_F))
499 var->defined=MallocString(filename);
501 if(scope&(GLOBAL|EXTERNAL|EXTERN_H) && var->scope&GLOBAL)
502 AddToStringList2(var->visible,"$",filename,1,0);
505 else
507 for(var=file->variables;var;var=var->next)
508 if(!strcmp(variable,var->name))
510 if(funcname[0]=='$' && !funcname[1])
511 AddToStringList2(var->used,"$",filename,1,0);
512 else
514 AddToStringList2(var->used,funcname,filename,1,1);
516 if(scope&EXTERN_F && var->scope&GLOBAL)
517 AddToStringList2(var->visible,funcname,filename,1,1);
524 /*++++++++++++++++++++++++++++++++++++++
525 Check through the function to see if it uses the variable, if func is NULL then check the file.
527 int check_for_var_func Returns 1 if the variable is referenced from the function or file.
529 File file The file that the function belongs to.
531 Variable var The variable that may be referenced.
533 Function func The function that is to be checked.
534 ++++++++++++++++++++++++++++++++++++++*/
536 static int check_for_var_func(File file,Variable var,Function func)
538 int i;
540 if(func)
542 for(i=0;i<func->v_refs->n;i++)
543 if(!strcmp(var->name,func->v_refs->s1[i]))
545 AddToStringList2(var->used,func->name,file->name,1,1);
546 if(var->scope&(GLOBAL|LOCAL))
547 func->v_refs->s2[i]=MallocString(file->name);
548 else
550 if(func->v_refs->s2[i]) Free(func->v_refs->s2[i]);
551 func->v_refs->s2[i]=MallocString("$");
553 return(1);
556 else
558 for(i=0;i<file->v_refs->n;i++)
559 if(!strcmp(var->name,file->v_refs->s1[i]))
561 AddToStringList2(var->used,"$",file->name,1,0);
562 if(var->scope&(GLOBAL|LOCAL))
563 file->v_refs->s2[i]=MallocString(file->name);
564 else
566 if(file->v_refs->s2[i]) Free(file->v_refs->s2[i]);
567 file->v_refs->s2[i]=MallocString("$");
569 return(1);
573 return(0);
577 /*++++++++++++++++++++++++++++++++++++++
578 We can only now put in the location of the external variables that we found were used.
579 Previously we did not know the location of their global definition.
581 Variable var The list of variables for this file.
583 StringList2 refs A list of variable references from a file or a function.
584 ++++++++++++++++++++++++++++++++++++++*/
586 static void fixup_extern_var(Variable var,StringList2 refs)
588 int i;
589 Variable v;
591 for(i=0;i<refs->n;i++)
593 if(refs->s2[i][0]=='$' && !refs->s2[i][1])
594 for(v=var;v;v=v->next)
595 if(v->scope&(EXTERNAL|EXTERN_H|EXTERN_F) && !strcmp(refs->s1[i],v->name))
597 if(v->defined)
599 Free(refs->s2[i]);
600 refs->s2[i]=MallocString(v->defined);
602 else
604 Free(refs->s1[i]);
605 refs->s1[i]=MallocString(v->name);
606 Free(refs->s2[i]);
607 refs->s2[i]=NULL;
610 break;
616 /*++++++++++++++++++++++++++++++++++++++
617 Create the appendix of files, global functions, global variables and types.
619 StringList files The list of files to create.
621 StringList2 funcs The list of functions to create.
623 StringList2 vars The list of variables to create.
625 StringList2 types The list of types to create.
626 ++++++++++++++++++++++++++++++++++++++*/
628 void CreateAppendix(StringList files,StringList2 funcs,StringList2 vars,StringList2 types)
630 FILE *in;
631 char *ifile;
633 if(option_index&INDEX_FILE) /* First do the files */
635 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_INC_FILE);
637 in =fopen(ifile,"r");
639 if(in)
641 char include[FILE_MAX_LEN+1],filename[FILE_MAX_LEN+1],ch;
643 while(fscanf(in,"%s%c",filename,&ch)==2)
645 AddToStringList(files,filename,1,1);
646 while(ch==' ')
647 fscanf(in,"%s%c",include,&ch);
650 fclose(in);
654 if(option_index&INDEX_FUNC) /* Now do the functions */
656 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_FUNC_FILE);
658 in =fopen(ifile,"r");
660 if(in)
662 char ch,caller[FUNC_MAX_LEN+1],filename[FILE_MAX_LEN+1],called[FUNC_MAX_LEN+1];
663 int scope;
665 while(fscanf(in,"%s %s %d%c",filename,caller,&scope,&ch)==4)
667 if(scope&GLOBAL)
668 AddToStringList2(funcs,caller,filename,1,1);
669 while(ch==' ')
670 fscanf(in,"%s%c",called,&ch);
673 fclose(in);
677 if(option_index&INDEX_VAR) /* Now do the variables */
679 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_VAR_FILE);
681 in =fopen(ifile,"r");
683 if(in)
685 char variable[FUNC_MAX_LEN+1],filename[FILE_MAX_LEN+1],funcname[FUNC_MAX_LEN+1],ch;
686 int scope;
688 while(fscanf(in,"%s %s %d%c",filename,variable,&scope,&ch)==4)
690 if(scope&GLOBAL)
691 AddToStringList2(vars,variable,filename,1,1);
692 while(ch==' ')
693 fscanf(in,"%s%c",funcname,&ch);
696 fclose(in);
700 if(option_index&INDEX_TYPE) /* Now do the types */
702 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_TYPE_FILE);
704 in =fopen(ifile,"r");
706 if(in)
708 char typename[TYPE_MAX_LEN],filename[FILE_MAX_LEN+1];
710 while(fscanf(in,"%s %s",filename,typename)==2)
712 if(typename[0]=='#')
714 fgets(typename,TYPE_MAX_LEN,in);
715 typename[strlen(typename)-1]=0;
716 AddToStringList2(types,&typename[1],filename,1,1);
718 else
720 AddToStringList2(types,typename,filename,1,1);
721 fgets(typename,TYPE_MAX_LEN,in);
725 fclose(in);
731 /*++++++++++++++++++++++++++++++++++++++
732 Delete the named file from the cross reference database.
734 char *name The name of the file that is to be deleted.
735 ++++++++++++++++++++++++++++++++++++++*/
737 void CrossReferenceDelete(char *name)
739 FILE *in,*out;
740 char *ifile,*ofile;
742 /* First do the files */
744 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_INC_FILE);
745 ofile=ConcatStrings(4,option_odir,"/",option_name,XREF_INC_BACKUP);
747 in =fopen(ifile,"r");
748 out=fopen(ofile,"w");
750 if(in && !out)
751 {fprintf(stderr,"cxref: Failed to open the include cross reference file '%s'\n",ofile);fclose(in);}
752 else if(in)
754 char include[FILE_MAX_LEN+1],filename[FILE_MAX_LEN+1],ch;
756 while(fscanf(in,"%s%c",filename,&ch)==2)
758 int diff_file=strcmp(filename,name);
760 if(diff_file)
761 fprintf(out,"%s",filename);
763 while(ch==' ')
765 fscanf(in,"%s%c",include,&ch);
767 if(diff_file)
768 fprintf(out," %s",include);
771 if(diff_file)
772 fprintf(out,"\n");
775 fclose(in);
776 unlink(ifile);
778 fclose(out);
779 rename(ofile,ifile);
781 else if(out)
783 fclose(out);
784 unlink(ofile);
787 /* Now do the functions */
789 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_FUNC_FILE);
790 ofile=ConcatStrings(4,option_odir,"/",option_name,XREF_FUNC_BACKUP);
792 in =fopen(ifile,"r");
793 out=fopen(ofile,"w");
795 if(in && !out)
796 {fprintf(stderr,"cxref: Failed to open the functional cross reference file '%s'\n",ofile);fclose(in);}
797 else if(in)
799 char ch,funcname[FUNC_MAX_LEN+1],filename[FILE_MAX_LEN+1],called[FUNC_MAX_LEN+1];
800 int scope;
802 while(fscanf(in,"%s %s %d%c",filename,funcname,&scope,&ch)==4)
804 int diff_file=strcmp(filename,name);
806 if(diff_file)
807 fprintf(out,"%s %s %d",filename,funcname,scope);
809 while(ch==' ')
811 fscanf(in,"%s%c",called,&ch);
812 if(diff_file)
813 fprintf(out," %s",called);
816 if(diff_file)
817 fprintf(out,"\n");
820 fclose(in);
821 unlink(ifile);
823 fclose(out);
824 rename(ofile,ifile);
826 else if(out)
828 fclose(out);
829 unlink(ofile);
832 /* Now do the variables */
834 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_VAR_FILE);
835 ofile=ConcatStrings(4,option_odir,"/",option_name,XREF_VAR_BACKUP);
837 in =fopen(ifile,"r");
838 out=fopen(ofile,"w");
840 if(in && !out)
841 {fprintf(stderr,"cxref: Failed to open the variable cross reference file '%s'\n",ofile);fclose(in);}
842 else if(in)
844 char varname[FUNC_MAX_LEN+1],filename[FILE_MAX_LEN+1],funcname[FUNC_MAX_LEN+1],ch;
845 int scope;
847 while(fscanf(in,"%s %s %d%c",filename,varname,&scope,&ch)==4)
849 int diff_file=strcmp(filename,name);
851 if(diff_file)
852 fprintf(out,"%s %s %d",filename,varname,scope);
854 while(ch==' ')
856 fscanf(in,"%s%c",funcname,&ch);
858 if(diff_file)
859 fprintf(out," %s",funcname);
862 if(diff_file)
863 fprintf(out,"\n");
866 fclose(in);
867 unlink(ifile);
869 fclose(out);
870 rename(ofile,ifile);
872 else if(out)
874 fclose(out);
875 unlink(ofile);
878 /* Now do the types */
880 ifile=ConcatStrings(4,option_odir,"/",option_name,XREF_TYPE_FILE);
881 ofile=ConcatStrings(4,option_odir,"/",option_name,XREF_TYPE_BACKUP);
883 in =fopen(ifile,"r");
884 out=fopen(ofile,"w");
886 if(in && !out)
887 {fprintf(stderr,"cxref: Failed to open the typedef reference file '%s'\n",ofile);fclose(in);}
888 else if(in)
890 char typename[TYPE_MAX_LEN+1],filename[FILE_MAX_LEN+1];
892 while(fscanf(in,"%s %s",filename,typename)==2)
894 int diff_file=strcmp(filename,name);
896 if(diff_file)
897 fprintf(out,"%s %s",filename,typename);
899 fgets(typename,TYPE_MAX_LEN,in);
901 if(diff_file)
902 fputs(typename,out);
905 fclose(in);
906 unlink(ifile);
908 fclose(out);
909 rename(ofile,ifile);
911 else if(out)
913 fclose(out);
914 unlink(ofile);