/* * Go to the end of the current sentence. Like gotobosent(), if we skip into * an empty line, return at that point. */ int gotoeosent(int f, int n) { regexp *exp; int s; int empty = is_empty_line(DOT); exp = b_val_rexp(curbp, VAL_SENTENCES)->reg; /* if we're on the end of a sentence now, don't bother scanning further, or we'll miss the immediately following sentence */ if (!(lregexec(exp, DOT.l, DOT.o, llength(DOT.l)) && exp->startp[0] - lvalue(DOT.l) == DOT.o)) { if (findpat(f, n, exp, FORWARD) != TRUE) { DOT = curbp->b_line; } else if (empty || !is_at_end_of_line(DOT)) { s = forwchar(TRUE, RegexpLen(exp)); while (s && (is_at_end_of_line(DOT) || isSpace(CharAtDot()))) { LINE *lp = DOT.l; s = forwchar(TRUE, 1); if (lp != DOT.l) break; } } } else { s = forwchar(TRUE, RegexpLen(exp)); while (s && (is_at_end_of_line(DOT) || isSpace(CharAtDot()))) s = forwchar(TRUE, 1); } return TRUE; }
/* * Go to the end of the current section (or paragraph if no section marker * found). */ int gotoeosec(int f, int n) { #if OPT_STUTTER_SEC_CMD if (!getstutter()) return FALSE; #endif if (findpat(f, n, b_val_rexp(curbp, VAL_SECTIONS)->reg, FORWARD) != TRUE) { DOT = curbp->b_line; } return TRUE; }
/* * Go to the beginning of the current section (or paragraph if no section * marker found). */ int gotobosec(int f, int n) { #if OPT_STUTTER_SEC_CMD if (!getstutter()) return FALSE; #endif if (findpat(f, n, b_val_rexp(curbp, VAL_SECTIONS)->reg, REVERSE) != TRUE) { (void) gotobob(f, n); } return TRUE; }
/* * Go to the end of the current paragraph. */ int gotoeop(int f, int n) { MARK odot; int was_at_bol; int was_on_empty; int fc; n = need_a_count(f, n, 1); fc = firstchar(DOT.l); was_on_empty = is_empty_line(DOT); was_at_bol = ((fc >= 0 && DOT.o <= fc) || fc < 0); odot = DOT; while (n) { if (findpat(TRUE, 1, b_val_rexp(curbp, VAL_PARAGRAPHS)->reg, FORWARD) != TRUE) { DOT = curbp->b_line; } else if (is_empty_line(DOT)) { /* special case -- if we found an empty line. */ /* either as the very next line, or at the end of our search */ if ((was_on_empty && lback(DOT.l) == odot.l) || (n > 0 && llength(lback(DOT.l)) == 0)) { /* then we haven't really found what we wanted. keep going */ skipblanksf(); continue; } } n--; } if (doingopcmd) { /* if we're now at the beginning of a line and we can back up, do so to avoid eating the newline and leading whitespace */ fc = firstchar(DOT.l); if (((fc >= 0 && DOT.o <= fc) || fc < 0) && !is_first_line(DOT, curbp) && !sameline(DOT, odot)) { backchar(TRUE, DOT.o + 1); } /* if we started at the start of line, eat the whole line */ if (!sameline(DOT, odot) && was_at_bol) regionshape = rgn_FULLLINE; } return TRUE; }
/* * Go to the beginning of the current paragraph. */ int gotobop(int f, int n) { MARK odot; int was_on_empty; int fc; n = need_a_count(f, n, 1); was_on_empty = is_empty_line(DOT); odot = DOT; fc = firstchar(DOT.l); if (doingopcmd && ((fc >= 0 && DOT.o <= fc) || fc < 0) && !is_first_line(DOT, curbp)) { backchar(TRUE, DOT.o + 1); pre_op_dot = DOT; } while (n) { if (findpat(TRUE, 1, b_val_rexp(curbp, VAL_PARAGRAPHS)->reg, REVERSE) != TRUE) { (void) gotobob(f, n); } else if (is_empty_line(DOT)) { /* special case -- if we found an empty line, and it's adjacent to where we started, skip all adjacent empty lines, and try again */ if ((was_on_empty && lforw(DOT.l) == odot.l) || (n > 0 && llength(lforw(DOT.l)) == 0)) { /* then we haven't really found what we wanted. keep going */ skipblanksb(); continue; } } n--; } if (doingopcmd) { fc = firstchar(DOT.l); if (!sameline(DOT, odot) && (pre_op_dot.o > lastchar(pre_op_dot.l)) && ((fc >= 0 && DOT.o <= fc) || fc < 0)) { regionshape = rgn_FULLLINE; } } return TRUE; }
/* * Go to the beginning of the current sentence. If we skip into an empty line * (from a non-empty line), return at that point -- that's what vi does. */ int gotobosent(int f, int n) { MARK savepos; int looped = 0; int extra; int empty = is_empty_line(DOT); regexp *exp; int s = TRUE; savepos = DOT; exp = b_val_rexp(curbp, VAL_SENTENCES)->reg; while (s && (is_at_end_of_line(DOT) || isSpace(CharAtDot()))) { s = backchar(TRUE, 1); if (is_empty_line(DOT) && !empty) return TRUE; } top: extra = 0; if (findpat(f, n, exp, REVERSE) != TRUE) { return gotobob(f, n); } s = forwchar(TRUE, RegexpLen(exp)); while (s && (is_at_end_of_line(DOT) || isSpace(CharAtDot()))) { s = forwchar(TRUE, 1); extra++; } if (n == 1 && samepoint(savepos, DOT)) { /* try again */ if (looped > 10) return FALSE; s = backchar(TRUE, RegexpLen(exp) + extra + looped); while (s && is_at_end_of_line(DOT)) { if (!empty && is_empty_line(DOT)) return TRUE; s = backchar(TRUE, 1); } looped++; goto top; } return TRUE; }
int main(int argc, char *argv[]) { char pattern[MAXLINE]; int c; bool except = false; bool number = false; FILE *fp; // Evaluate optional switch arguments while (--argc > 0 && (*++argv)[0] == '-') while ((c = *++argv[0]) != '\0') switch (c) { case 'x': except = true; break; case 'n': number = true; break; default: fprintf(stderr, "minfind: illegal option %c\n", c); exit(EXIT_FAILURE); } // Check for valid usage (at least a pattern argument should still remain) if (argc < 1) { fprintf(stderr, "Usage: minfind [-x] [-n] pattern [file ...]\n"); exit(EXIT_FAILURE); } // Save search pattern strcpy(pattern, *argv); // If no more arguments remain, read from standard input if (argc == 1) { findpat(stdin, "", pattern, except, number); exit(EXIT_SUCCESS); } // Arguments do remain, so try to process them as if they are file names // searching each in turn for the pattern while (--argc > 0) { // Attempt to open the file if ((fp = fopen(*++argv, "r")) == NULL) { fprintf(stderr, "minfind: cannot open %s\n", *argv); exit(EXIT_FAILURE); } // Search the file findpat(fp, *argv, pattern, except, number); (void)fclose(fp); } exit(EXIT_SUCCESS); }