diff options
Diffstat (limited to 'editors/sed.c')
-rw-r--r-- | editors/sed.c | 110 |
1 files changed, 62 insertions, 48 deletions
diff --git a/editors/sed.c b/editors/sed.c index 4dd552a..a3e635d 100644 --- a/editors/sed.c +++ b/editors/sed.c @@ -33,12 +33,10 @@ static const char sed_usage[] = "sed [-n] [-e script] [file...]\n" -"Allowed scripts come in two forms:\n" -"'/regexp/[gp]'\n" -"\tattempt to match regexp against the pattern space\n" +"Allowed scripts come in the following form:\n\n" "'s/regexp/replacement/[gp]'\n" "\tattempt to match regexp against the pattern space\n" -"\tand if successful replaces the matched portion with replacement." +"\tand if successful replaces the matched portion with replacement.\n\n" "Options:\n" "-e\tadd the script to the commands to be executed\n" "-n\tsuppress automatic printing of pattern space\n\n" @@ -49,64 +47,86 @@ static const char sed_usage[] = #endif -static int replaceFlag = FALSE; -static int noprintFlag = FALSE; extern int sed_main (int argc, char **argv) { FILE *fp; - const char *needle; - const char *name; - const char *cp; - int tellName=TRUE; + char *needle=NULL, *newNeedle=NULL; + char *name; + char *cp; int ignoreCase=FALSE; - int tellLine=FALSE; - long line; - char haystack[BUF_SIZE]; - - ignoreCase = FALSE; - tellLine = FALSE; + int foundOne=FALSE; + int noprintFlag=FALSE; + int stopNow; + char *haystack; argc--; argv++; if (argc < 1) { - usage(grep_usage); + usage(sed_usage); } if (**argv == '-') { argc--; cp = *argv++; + stopNow=FALSE; - while (*++cp) + while (*++cp && stopNow==FALSE) switch (*cp) { case 'n': noprintFlag = TRUE; break; case 'e': - if (*(*argv)+1 != '\'' && **argv != '\"') { - if (--argc == 0) - usage( mkdir_usage); - ++argv; - if (*(*argv)+1 != '\'' && **argv != '\"') { - usage( mkdir_usage); + if (*(cp+1)==0 && --argc < 0) { + fprintf(stderr, "A\n"); + usage( sed_usage); } - /* Find the specified modes */ - mode = 0; - if ( parse_mode(*(++argv), &mode) == FALSE ) { - fprintf(stderr, "Unknown mode: %s\n", *argv); - exit( FALSE); + cp = *argv++; + while( *cp ) { + if (*cp == 's' && strlen(cp) > 3 && *(cp+1) == '/') { + char* pos=needle=cp+2; + for(;;) { + pos = strchr(pos, '/'); + if (pos==NULL) { + fprintf(stderr, "B\n"); + usage( sed_usage); + } + if (*(pos-1) == '\\') { + pos++; + continue; + } + break; + } + *pos=0; + newNeedle=++pos; + for(;;) { + pos = strchr(pos, '/'); + if (pos==NULL) { + fprintf(stderr, "C\n"); + usage( sed_usage); + } + if (*(pos-1) == '\\') { + pos++; + continue; + } + break; + } + *pos=0; + } + cp++; } + fprintf(stderr, "replace '%s' with '%s'\n", needle, newNeedle); + stopNow=TRUE; break; default: - usage(grep_usage); + fprintf(stderr, "D\n"); + usage(sed_usage); } } - needle = *argv++; - argc--; - + fprintf(stderr, "argc=%d\n", argc); while (argc-- > 0) { name = *argv++; @@ -115,25 +135,19 @@ extern int sed_main (int argc, char **argv) perror (name); continue; } + fprintf(stderr, "filename is '%s'\n", name); - line = 0; - + haystack = (char*)malloc( 80); while (fgets (haystack, sizeof (haystack), fp)) { - line++; - cp = &haystack[strlen (haystack) - 1]; - - if (*cp != '\n') - fprintf (stderr, "%s: Line too long\n", name); - - if (find_match(haystack, needle, ignoreCase) == TRUE) { - if (tellName==TRUE) - printf ("%s: ", name); - - if (tellLine==TRUE) - printf ("%ld: ", line); + foundOne = replace_match(haystack, needle, newNeedle, ignoreCase); + if (noprintFlag==TRUE && foundOne==TRUE) fputs (haystack, stdout); - } + else + fputs (haystack, stdout); + /* Avoid any mem leaks */ + free(haystack); + haystack = (char*)malloc( BUF_SIZE); } if (ferror (fp)) |