/* int.c - Initialisation code for replace command (C) Richard K. Lloyd 2001-2004 */ #define Extern #include "replace.h" /* This next string gets output when you do a "what replace" in HP-UX */ static char ident[] = "@(#)replace " REPLACE_VERSION " (C) Richard K. Lloyd " REPLACE_YEAR; #ifdef __STDC__ void set_temp_file(char *tfile) #else void set_temp_file(tfile) char *tfile; #endif { /* The file passed to this routine should be unlinked in the tidy_up() routine. Passing "" as a file clears this and won't unlink during tidy_up(); */ (void)strcpy(tempfile_cleanup,tfile); } void tidy_up(P(void)) { /* I don't actually have to include this routine since UNIX does it for me when the program exits, but let's be careful anyway - you never know, it might be a library one day :-) */ size_t f; for (f=1;f<=numstrs;f++) { if (oldstr[f]!=(char *)NULL) free((MALLOCPTR)oldstr[f]); if (newstr[f]!=(char *)NULL) free((MALLOCPTR)newstr[f]); } for (f=1;f<=suffixes;f++) if (sufflist[f]!=(char *)NULL) free((MALLOCPTR)sufflist[f]); if (binchunkptr!=(char *)NULL) free((MALLOCPTR)binchunkptr); if (thestring!=(char *)NULL) free((MALLOCPTR)thestring); /* Remove any temp file that was being worked on at the time */ if (tempfile_cleanup[0]) (void)unlink(tempfile_cleanup); } #ifdef __STDC__ void tidy_up_handler(int signum) #else void tidy_up_handler(signum) int signum; #endif { /* Handle signal appropriately and then exit the program */ (void)signal(signum,SIG_DFL); /* Reset handler back to default */ tidy_up(); exit(EXIT_FAILURE); } void init_vars(P(void)) { /* Initialise global variables */ set_temp_file(""); /* No temporary file to clean up yet */ numstrs=0; /* No strings yet */ numfilereps=0; /* Number of files that had their strings replaced */ numfiles=0; /* Total number of files scanned */ numreps=0; /* Total number of replacements */ /* Default settings if no qualifiers supplied */ sensitive=0; /* Case-insensitive */ word=1; /* Match words only, not sub-strings */ force=0; /* Don't force it - keep .cln version */ padit=0; /* Don't pad new string with trailing spaces */ prepadit=0; /* Don't pad new string with leading spaces */ verbose=0; /* Not verbose */ startcol=1; /* Start replacing from column 1 */ startline=1; /* Start replacing from line 1 */ recursive=0; /* Don't recurse */ suffixes=0; /* No suffixes yet */ minsuff=BUFSIZ; /* Minimum length of a suffix */ prompt=0; /* Don't prompt yet */ fake=0; /* Don't "fake" the replacements */ binary=0; /* Not forcing binary replacements */ ascii=0; /* Not forcing text replacements */ hex=0; /* Not hex strings */ maxreplines=0; /* Replace in any number of lines */ maxtimes=0; /* Replace string any number of times in a single line */ zeroterm=0; /* Don't zero-terminate */ binchunkptr=(char *)NULL; binchunksize=0; /* No binary chunk yet */ thestring=(char *)NULL; thestringsize=0; /* No text string yet */ newline=(char *)NULL; newlinesize=0; /* No newstr output buffer yet */ retainstamp=0; /* Don't keep the timestamp of the original file */ followsoftlinks=0; /* Ignore soft-links if specified as filenames */ autodetect=1; /* Auto-detect if binary or text */ autobinsize=0; /* Didn't read any bytes for auto-detect yet */ /* Now set up signals to run the tidy_up_handler() routine */ (void)signal(SIGINT,tidy_up_handler); } #ifdef __STDC__ void leave(char *errmess) #else void leave(errmess) char *errmess; #endif { /* Something wrong, so leave, displaying an error message if non-null */ tidy_up(); if (errmess[0]) (void)fprintf(stderr,"%s: FATAL - %s\n",progname,errmess); exit(EXIT_FAILURE); } #ifdef __STDC__ static void add_suffix(char *sfx) #else static void add_suffix(sfx) char *sfx; #endif { /* New suffix to add to the list */ if (suffixesargc) usage(); oldtmp=strlen(argv[optind]); if (!oldtmp && binary) leave("Old string must be non-null"); if (hex) { int hptr=2; size_t hlp; int hval; if (oldtmp%2) hptr--; oldtmp=(oldtmp+1)/2; if ((oldstr[++numstrs]=(char *)malloc((MALLOCPAR)oldtmp))==(char *)NULL) leave("Can't allocate memory for old hex string"); for (hlp=0;hlp1)],"%x",&hval); oldstr[numstrs][hlp]=(char)hval; argv[optind][hptr]=oarg; hptr+=2; } } else { if ((oldstr[++numstrs]=(char *)malloc((MALLOCPAR)(oldtmp+1)))==(char *)NULL) leave("Can't allocate memory for old string"); (void)strcpy(oldstr[numstrs],argv[optind]); } oldstrlen[numstrs]=oldtmp; newtmp=strlen(argv[++optind]); if (!newtmp && binary) leave("New string must be non-null"); if ((prepadit || padit) && newtmp1)],"%x",&hval); newstr[numstrs][hlp]=(char)hval; argv[optind][hptr]=oarg; hptr+=2; } } else { if ((newstr[numstrs]=(char *)malloc((MALLOCPAR)(alloclen+1)))==(char *)NULL) leave("Can't allocate memory for new string"); (void)strcpy(newstr[numstrs],argv[optind]); if (padit) { while (newtmp=sdf;cp--) { newstr[numstrs][cp]=newstr[numstrs][cp-sdf]; } for (cp=0;cpoldtmp) leave("New binary string mustn't be larger than old binary string"); if (zeroterm && newtmp>=oldtmp) leave("New binary string must be smaller than old binary string if -z used"); if (hex) { if (newtmp==oldtmp && !memcmp((void *)oldstr[numstrs],(void *)newstr[numstrs],oldtmp)) leave("Old and new hex strings must be different"); } else if ((sensitive && !strcmp(oldstr[numstrs],newstr[numstrs])) || (!sensitive && !strcasecmp(oldstr[numstrs],newstr[numstrs]))) leave("Old and new strings must be different"); /* Yes, I could short-cut this, but some lints complain if I do */ looping=(++optind