/* * Move the cursor forward by the specified number of words. As you move * convert characters to lower case. Error if you try and move over the end of * the buffer. Bound to "M-L". */ int lowerword(int f, int n) { register int c; CELL ac; ac.a = 0; if (curbp->b_mode&MDVIEW) /* don't allow this command if */ return(rdonly()); /* we are in read only mode */ if (n < 0) return (FALSE); while (n--) { while (inword() == FALSE) { if (forwchar(FALSE, 1) == FALSE) return (FALSE); } while (inword() != FALSE) { c = lgetc(curwp->w_dotp, curwp->w_doto).c; if (c>='A' && c<='Z') { ac.c (c += 'a'-'A'); lputc(curwp->w_dotp, curwp->w_doto, ac); lchange(WFHARD); } if (forwchar(FALSE, 1) == FALSE) return (FALSE); } } return (TRUE); }
/* * set the highlight attribute accordingly on all characters in region */ int markregion(int attr) { register LINE *linep; register int loffs; register int s; REGION region; CELL ac; if ((s=getregion(®ion, curwp->w_markp, curwp->w_marko)) != TRUE) return (s); lchange(WFHARD); linep = region.r_linep; loffs = region.r_offset; while (region.r_size--) { if (loffs == llength(linep)) { linep = lforw(linep); loffs = 0; } else { ac = lgetc(linep, loffs); ac.a = attr; lputc(linep, loffs, ac); ++loffs; } } return (TRUE); }
/* * Upper case region. Zap all of the lower * case characters in the region to upper case. Use * the region code to set the limits. Scan the buffer, * doing the changes. Call "lchange" to ensure that * redisplay is done in all buffers. */ int upperregion (int f, int n, int k) { register LINE *linep; register int loffs; register int c; register int s; REGION region; if ((s = getregion (®ion)) != TRUE) return (s); if (checkreadonly () == FALSE) return FALSE; lchange (WFHARD); linep = region.r_pos.p; loffs = region.r_pos.o; while (region.r_size--) { if (loffs == llength (linep)) { linep = lforw (linep); loffs = 0; } else { c = lgetc (linep, loffs); if (ISLOWER (c) != FALSE) lputc (linep, loffs, TOUPPER (c)); ++loffs; } } return (TRUE); }
/* * Move the cursor forward by the specified number of words. As you move, * convert any characters to upper case. Error if you try and move beyond the * end of the buffer. Bound to "M-U" */ int upperword(int f, int n) { int c; if (n < 0) return (FALSE); while (n--) { while (inword() == FALSE) { if (forwchar(FALSE, 1) == FALSE) return (FALSE); } while (inword() != FALSE) { c = lgetc(curwp->w_dotp, curwp->w_doto); if (c >= 'a' && c <= 'z') { c -= 'a' - 'A'; lputc(curwp->w_dotp, curwp->w_doto, c); lchange(WFHARD); } if (forwchar(FALSE, 1) == FALSE) return (FALSE); } } return (TRUE); }
/* ARGSUSED */ int lowerregion(int f, int n) { struct line *linep; struct region region; int loffs, c, s; if ((s = checkdirty(curbp)) != TRUE) return (s); if (curbp->b_flag & BFREADONLY) { ewprintf("Buffer is read-only"); return (FALSE); } if ((s = getregion(®ion)) != TRUE) return (s); undo_add_change(region.r_linep, region.r_offset, region.r_size); lchange(WFFULL); linep = region.r_linep; loffs = region.r_offset; while (region.r_size--) { if (loffs == llength(linep)) { linep = lforw(linep); loffs = 0; } else { c = lgetc(linep, loffs); if (ISUPPER(c) != FALSE) lputc(linep, loffs, TOLOWER(c)); ++loffs; } } return (TRUE); }
/* ARGSUSED */ int capword(int f, int n) { int c, s; RSIZE size; if ((s = checkdirty(curbp)) != TRUE) return (s); if (curbp->b_flag & BFREADONLY) { dobeep(); ewprintf("Buffer is read-only"); return (FALSE); } if (n < 0) return (FALSE); while (n--) { while (inword() == FALSE) { if (forwchar(FFRAND, 1) == FALSE) return (TRUE); } size = countfword(); undo_add_change(curwp->w_dotp, curwp->w_doto, size); if (inword() != FALSE) { c = lgetc(curwp->w_dotp, curwp->w_doto); if (ISLOWER(c) != FALSE) { c = TOUPPER(c); lputc(curwp->w_dotp, curwp->w_doto, c); lchange(WFFULL); } if (forwchar(FFRAND, 1) == FALSE) return (TRUE); while (inword() != FALSE) { c = lgetc(curwp->w_dotp, curwp->w_doto); if (ISUPPER(c) != FALSE) { c = TOLOWER(c); lputc(curwp->w_dotp, curwp->w_doto, c); lchange(WFFULL); } if (forwchar(FFRAND, 1) == FALSE) return (TRUE); } } } return (TRUE); }
/* * Twiddle the two characters on either side of dot. If dot is at the end of * the line twiddle the two characters before it. Return with an error if dot * is at the beginning of line; it seems to be a bit pointless to make this * work. This fixes up a very common typo with a single stroke. Normally bound * to "C-T". This always works within a line, so "WFEDIT" is good enough */ int twiddle(int f, int n) { LINE *dotp; int doto, cl, cr; dotp = curwp->w_dotp; doto = curwp->w_doto; if (doto == llength(dotp) && --doto < 0) return (FALSE); cr = lgetc(dotp, doto); if (--doto < 0) return (FALSE); cl = lgetc(dotp, doto); lputc(dotp, doto + 0, cr); lputc(dotp, doto + 1, cl); lchange(WFEDIT); return (TRUE); }
/* * readbuf - reads in a buffer. */ void readbuf(char **buf) { register LINE *lp1; register LINE *lp2; register BUFFER *bp; register WINDOW *wp; register int i; register int s; char *sptr; /* pointer into buffer string */ int nbytes; char line[NLINE]; CELL ac; bp = curbp; bp->b_flag &= ~(BFTEMP|BFCHG); sptr = *buf; ac.a = 0; while((s=sgetline(&sptr,&nbytes,line,NLINE)) == FIOSUC || s == FIOLNG){ if ((lp1=lalloc(nbytes)) == NULL) { s = FIOERR; /* Keep message on the */ break; /* display. */ } lp2 = lback(curbp->b_linep); lp2->l_fp = lp1; lp1->l_fp = curbp->b_linep; lp1->l_bp = lp2; curbp->b_linep->l_bp = lp1; for (i=0; i<nbytes; ++i){ ac.c = line[i]; lputc(lp1, i, ac); } } for (wp=wheadp; wp!=NULL; wp=wp->w_wndp) { if (wp->w_bufp == curbp) { wheadp->w_linep = lforw(curbp->b_linep); wheadp->w_dotp = lback(curbp->b_linep); wheadp->w_doto = 0; wheadp->w_markp = NULL; wheadp->w_marko = 0; wheadp->w_flag |= WFHARD; } } strncpy(bp->b_bname, "main", sizeof(bp->b_bname)); bp->b_bname[sizeof(bp->b_bname)-1] = '\0'; strncpy(bp->b_fname, "", sizeof(bp->b_fname)); bp->b_fname[sizeof(bp->b_fname)-1] = '\0'; bp->b_dotp = bp->b_linep; bp->b_doto = 0; }
int lprintf(char *format,...) { Formatarg fa; int c; start_formatarg(fa,format); while((c = fa_getc(&fa)) != 0) lputc(c,lstdout); end_formatarg(fa); return(fa.count - 1); }
int lvfprintf(LFILE *f, char *fmt, va_list args) { Formatarg fa; char c; copy_va_list(args,fa.args); /* see compiler.h */ init_formatarg(&fa,fmt); while((c = fa_getc(&fa)) != 0) { if (lputc(c,f) < Success) break; } return(fa.count - 1); }
/* ARGSUSED */ int d_del(int f, int n) { if (n < 0) return (FALSE); while (n--) { if (llength(curwp->w_dotp) > 0) lputc(curwp->w_dotp, 0, 'D'); if (lforw(curwp->w_dotp) != curbp->b_headp) curwp->w_dotp = lforw(curwp->w_dotp); } curwp->w_flag |= WFEDIT | WFMOVE; curwp->w_doto = 0; return (TRUE); }
/* ARGSUSED */ int d_undelbak(int f, int n) { if (n < 0) return (d_undel(f, -n)); while (n--) { if (llength(curwp->w_dotp) > 0) lputc(curwp->w_dotp, 0, ' '); if (lback(curwp->w_dotp) != curbp->b_headp) curwp->w_dotp = lback(curwp->w_dotp); } curwp->w_doto = 0; curwp->w_flag |= WFEDIT | WFMOVE; return (TRUE); }
void Warning (const char *code, const char *fmt, ...) { va_list args; fflush(stdout_); fprintf(stdwarn_, "%c %s ", MSGCLASS_WARN, code); lprintf("%c %s ", MSGCLASS_WARN, code); va_start(args, fmt); vfprintf(stdwarn_, fmt, args); va_end(args); va_start(args, fmt); vlprintf(fmt, args); va_end(args); fputc('\n', stdwarn_); lputc('\n'); }
/* * nf_err - non fatal error message */ void nf_err (const char *code, const char *fmt, ...) { va_list args; fflush(stdout_); fprintf(stderr_, "%c %s ", MSGCLASS_ERR, code); lprintf("%c %s ", MSGCLASS_ERR, code); va_start(args, fmt); vfprintf(stderr_, fmt, args); va_end(args); va_start(args, fmt); vlprintf(fmt, args); va_end(args); fputc('\n', stderr_); lputc('\n'); fflush(stderr_); }
/* * The argument "text" points to a string. Append this line to the buffer list * buffer. Handcraft the EOL on the end. Return TRUE if it worked and FALSE if * you ran out of room. */ int addline (char *text) { LINE *lp; int ntext, i; ntext = strlen (text); if ((lp = lalloc (ntext)) == NULL) return (FALSE); for (i = 0; i < ntext; ++i) lputc (lp, i, text[i]); blistp->b_linep->l_bp->l_fp = lp; /* Hook onto the end */ lp->l_bp = blistp->b_linep->l_bp; blistp->b_linep->l_bp = lp; lp->l_fp = blistp->b_linep; if (blistp->b_dotp == blistp->b_linep) /* If "." is at the end */ blistp->b_dotp = lp; /* move it to new line */ return (TRUE); }
void Detail (const char *code, const char *fmt, ...) { if (Verbosity >= 3) { va_list args; fprintf (stdinfo_, "%c %s ", MSGCLASS_INFO, code); lprintf ("%c %s ", MSGCLASS_INFO, code); va_start(args, fmt); vfprintf(stdinfo_, fmt, args); va_end(args); va_start(args, fmt); vlprintf(fmt, args); va_end(args); fputc ('\n', stdinfo_); lputc ('\n'); } }
/* * clear all the attributes of all the characters in the buffer? * this is real dumb. Movement with mark set needs to be smarter! */ void unmarkbuffer(void) { register LINE *linep; register int n; CELL c; linep = curwp->w_linep; while(lforw(linep) != curwp->w_linep){ n = llength(linep); for(n=0; n < llength(linep); n++){ c = lgetc(linep, n); c.a = 0; lputc(linep, n, c); } linep = lforw(linep); } }
void ProgError (const char *code, const char *fmt, ...) { va_list args; fflush (stdout_); fprintf(stderr_, "E %s ", code); lprintf("E %s ", code); va_start(args, fmt); vfprintf(stderr_, fmt, args); va_end(args); va_start(args, fmt); vlprintf(fmt, args); va_end(args); fputc('\n', stderr_); lputc('\n'); (*Action)(); /* execute error handler*/ PrintExit(); exit(2); }
void LimitedWarn (int *left, const char *code, const char *fmt, ...) { if (left == NULL || (left != NULL && *left > 0)) { va_list args; fflush(stdout_); fprintf(stdwarn_, "%c %s ", MSGCLASS_WARN, code); lprintf("%c %s ", MSGCLASS_WARN, code); va_start(args, fmt); vfprintf(stdwarn_, fmt, args); va_end(args); va_start(args, fmt); vlprintf(fmt, args); va_end(args); fputc('\n', stdwarn_); lputc('\n'); } if (left != NULL) (*left)--; }
void Bug (const char *code, const char *fmt, ...) { va_list args; fflush(stdout_); fprintf(stdwarn_, "%c %s ", MSGCLASS_BUG, code); lprintf("%c %s ", MSGCLASS_BUG, code); va_start(args, fmt); vfprintf(stderr_, fmt, args); va_end(args); va_start(args, fmt); vlprintf(fmt, args); va_end(args); fputc('\n', stderr_); lputc('\n'); fputs("Please report that bug\n", stderr_); lputs("Please report that bug\n"); /* CloseWadFiles();*/ PrintExit(); exit(3); }
// Lower or upper case region. Change the case of all the characters in the region. Use the region code to set the // limits. Scan the buffer, doing the changes. Call "lchange" to ensure that redisplay is done in all buffers. int caseregion(int n,char *trantab) { Line *lnp; int offset; Region region; if(getregion(®ion,NULL) != SUCCESS) return rc.status; lchange(curbp,WFHARD); lnp = region.r_dot.lnp; offset = region.r_dot.off; while(region.r_size-- > 0) { if(offset == lused(lnp)) { lnp = lforw(lnp); offset = 0; } else { lputc(lnp,offset,trantab[(int) lgetc(lnp,offset)]); ++offset; } } return rc.status; }
/*ARGSUSED*/ upperregion(f, n) { register LINE *linep; register int loffs; register int c; register int s; REGION region; VOID lchange(); #ifdef READONLY /* 91.01.05 by S.Yoshida */ if (curbp->b_flag & BFRONLY) { /* If this buffer is read-only, */ warnreadonly(); /* do only displaying warning. */ return TRUE; } #endif /* READONLY */ if ((s=getregion(®ion)) != TRUE) return s; #ifdef UNDO undo_reset(curbp); /* this function cannot undo */ #endif lchange(WFHARD); linep = region.r_linep; loffs = region.r_offset; while (region.r_size--) { if (loffs == llength(linep)) { linep = lforw(linep); loffs = 0; } else { c = lgetc(linep, loffs); if (ISLOWER(c) != FALSE) lputc(linep, loffs, TOUPPER(c)); ++loffs; } } return TRUE; }
/* * Upper case region. Zap all of the lower * case characters in the region to upper case. Use * the region code to set the limits. Scan the buffer, * doing the changes. Call "lchange" to ensure that * redisplay is done in all buffers. Bound to * "C-X C-L". */ int upperregion(int f, int n) { register LINE *linep; register int loffs; register int c; register int s; REGION region; CELL ac; ac.a = 0; if (curbp->b_mode&MDVIEW) /* don't allow this command if */ return(rdonly()); /* we are in read only mode */ if ((s=getregion(®ion, curwp->w_markp, curwp->w_marko)) != TRUE) return (s); lchange(WFHARD); linep = region.r_linep; loffs = region.r_offset; while (region.r_size--) { if (loffs == llength(linep)) { linep = lforw(linep); loffs = 0; } else { c = lgetc(linep, loffs).c; if (c>='a' && c<='z'){ ac.c = c - 'a' + 'A'; lputc(linep, loffs, ac); } ++loffs; } } return (TRUE); }
/* ARGSUSED */ int upperword(int f, int n) { int c, s; RSIZE size; if ((s = checkdirty(curbp)) != TRUE) return (s); if (curbp->b_flag & BFREADONLY) { ewprintf("Buffer is read-only"); return (FALSE); } if (n < 0) return (FALSE); while (n--) { while (inword() == FALSE) { if (forwchar(FFRAND, 1) == FALSE) return (TRUE); } size = countfword(); undo_add_change(curwp->w_dotp, curwp->w_doto, size); while (inword() != FALSE) { c = lgetc(curwp->w_dotp, curwp->w_doto); #ifndef MRUBY if (ISLOWER(c) != FALSE) { c = TOUPPER(c); #else if (MG_ISLOWER(c) != FALSE) { c = MG_TOUPPER(c); #endif /* !MRUBY */ lputc(curwp->w_dotp, curwp->w_doto, c); lchange(WFFULL); } if (forwchar(FFRAND, 1) == FALSE) return (TRUE); } } return (TRUE); } /* * Move the cursor forward by the specified number of words. As you move * convert characters to lower case. */ /* ARGSUSED */ int lowerword(int f, int n) { int c, s; RSIZE size; if ((s = checkdirty(curbp)) != TRUE) return (s); if (curbp->b_flag & BFREADONLY) { ewprintf("Buffer is read-only"); return (FALSE); } if (n < 0) return (FALSE); while (n--) { while (inword() == FALSE) { if (forwchar(FFRAND, 1) == FALSE) return (TRUE); } size = countfword(); undo_add_change(curwp->w_dotp, curwp->w_doto, size); while (inword() != FALSE) { c = lgetc(curwp->w_dotp, curwp->w_doto); #ifndef MRUBY if (ISUPPER(c) != FALSE) { c = TOLOWER(c); #else if (MG_ISUPPER(c) != FALSE) { c = MG_TOLOWER(c); #endif /* !MRUBY */ lputc(curwp->w_dotp, curwp->w_doto, c); lchange(WFFULL); } if (forwchar(FFRAND, 1) == FALSE) return (TRUE); } } return (TRUE); } /* * Move the cursor forward by the specified number of words. As you move * convert the first character of the word to upper case, and subsequent * characters to lower case. Error if you try to move past the end of the * buffer. */ /* ARGSUSED */ int capword(int f, int n) { int c, s; RSIZE size; if ((s = checkdirty(curbp)) != TRUE) return (s); if (curbp->b_flag & BFREADONLY) { ewprintf("Buffer is read-only"); return (FALSE); } if (n < 0) return (FALSE); while (n--) { while (inword() == FALSE) { if (forwchar(FFRAND, 1) == FALSE) return (TRUE); } size = countfword(); undo_add_change(curwp->w_dotp, curwp->w_doto, size); if (inword() != FALSE) { c = lgetc(curwp->w_dotp, curwp->w_doto); #ifndef MRUBY if (ISLOWER(c) != FALSE) { c = TOUPPER(c); #else if (MG_ISLOWER(c) != FALSE) { c = MG_TOUPPER(c); #endif /* !MRUBY */ lputc(curwp->w_dotp, curwp->w_doto, c); lchange(WFFULL); } if (forwchar(FFRAND, 1) == FALSE) return (TRUE); while (inword() != FALSE) { c = lgetc(curwp->w_dotp, curwp->w_doto); #ifndef MRUBY if (ISUPPER(c) != FALSE) { c = TOLOWER(c); #else if (MG_ISUPPER(c) != FALSE) { c = MG_TOLOWER(c); #endif /* !MRUBY */ lputc(curwp->w_dotp, curwp->w_doto, c); lchange(WFFULL); } if (forwchar(FFRAND, 1) == FALSE) return (TRUE); } } } return (TRUE); } /* * Count characters in word, from current position */ RSIZE countfword() { RSIZE size; struct line *dotp; int doto; dotp = curwp->w_dotp; doto = curwp->w_doto; size = 0; while (inword() != FALSE) { if (forwchar(FFRAND, 1) == FALSE) /* hit the end of the buffer */ goto out; ++size; } out: curwp->w_dotp = dotp; curwp->w_doto = doto; return (size); } /* * Kill forward by "n" words. */ /* ARGSUSED */ int delfword(int f, int n) { RSIZE size; struct line *dotp; int doto; int s; if ((s = checkdirty(curbp)) != TRUE) return (s); if (curbp->b_flag & BFREADONLY) { ewprintf("Buffer is read-only"); return (FALSE); } if (n < 0) return (FALSE); /* purge kill buffer */ if ((lastflag & CFKILL) == 0) kdelete(); thisflag |= CFKILL; dotp = curwp->w_dotp; doto = curwp->w_doto; size = 0; while (n--) { while (inword() == FALSE) { if (forwchar(FFRAND, 1) == FALSE) /* hit the end of the buffer */ goto out; ++size; } while (inword() != FALSE) { if (forwchar(FFRAND, 1) == FALSE) /* hit the end of the buffer */ goto out; ++size; } } out: curwp->w_dotp = dotp; curwp->w_doto = doto; return (ldelete(size, KFORW)); } /* * Kill backwards by "n" words. The rules for success and failure are now * different, to prevent strange behavior at the start of the buffer. The * command only fails if something goes wrong with the actual delete of the * characters. It is successful even if no characters are deleted, or if you * say delete 5 words, and there are only 4 words left. I considered making * the first call to "backchar" special, but decided that that would just be * weird. Normally this is bound to "M-Rubout" and to "M-Backspace". */ /* ARGSUSED */ int delbword(int f, int n) { RSIZE size; int s; if ((s = checkdirty(curbp)) != TRUE) return (s); if (curbp->b_flag & BFREADONLY) { ewprintf("Buffer is read-only"); return (FALSE); } if (n < 0) return (FALSE); /* purge kill buffer */ if ((lastflag & CFKILL) == 0) kdelete(); thisflag |= CFKILL; if (backchar(FFRAND, 1) == FALSE) /* hit buffer start */ return (TRUE); /* one deleted */ size = 1; while (n--) { while (inword() == FALSE) { if (backchar(FFRAND, 1) == FALSE) /* hit buffer start */ goto out; ++size; } while (inword() != FALSE) { if (backchar(FFRAND, 1) == FALSE) /* hit buffer start */ goto out; ++size; } } if (forwchar(FFRAND, 1) == FALSE) return (FALSE); /* undo assumed delete */ --size; out: return (ldelete(size, KBACK)); }
/* * Read file "fname" into the current buffer, blowing away any text found * there. Called by both the read and find commands. Return the final status * of the read. Also called by the mainline, to read in a file specified on * the command line as an argument. */ int readin(char fname[]) { LINE *lp1, *lp2; WINDOW *wp; BUFFER *bp; char line[NLINE]; int nbytes, s, i; int nline = 0; /* initialize here to silence a gcc warning */ int lflag; /* any lines longer than allowed? */ bp = curbp; /* Cheap */ if ((s = bclear(bp)) != TRUE) /* Might be old */ return (s); bp->b_flag &= ~(BFTEMP | BFCHG); strncpy(bp->b_fname, fname, NFILEN); if ((s = ffropen(fname)) == FIOERR) /* Hard file open */ goto out; if (s == FIOFNF) { /* File not found */ mlwrite("[New file]"); goto out; } mlwrite("[Reading file]"); lflag = FALSE; while ((s = ffgetline(line, NLINE)) == FIOSUC || s == FIOLNG) { if (s == FIOLNG) lflag = TRUE; nbytes = strlen(line); if ((lp1 = lalloc(nbytes)) == NULL) { s = FIOERR; /* Keep message on the display */ break; } lp2 = lback(curbp->b_linep); lp2->l_fp = lp1; lp1->l_fp = curbp->b_linep; lp1->l_bp = lp2; curbp->b_linep->l_bp = lp1; for (i = 0; i < nbytes; ++i) lputc(lp1, i, line[i]); ++nline; } ffclose(); /* Ignore errors */ if (s == FIOEOF) { /* Don't zap message! */ if (nline != 1) mlwrite("[Read %d lines]", nline); else mlwrite("[Read 1 line]"); } if (lflag) { if (nline != 1) mlwrite("[Read %d lines: Long lines wrapped]", nline); else mlwrite("[Read 1 line: Long lines wrapped]"); } curwp->w_bufp->b_lines = nline; out: for (wp = wheadp; wp != NULL; wp = wp->w_wndp) { if (wp->w_bufp == curbp) { wp->w_linep = lforw(curbp->b_linep); wp->w_dotp = lforw(curbp->b_linep); wp->w_doto = 0; wp->w_markp = NULL; wp->w_marko = 0; wp->w_flag |= WFMODE | WFHARD; } } if (s == FIOERR || s == FIOFNF) /* False if error */ return (FALSE); return (TRUE); }
/* * Insert a character. While defining a macro, create a "LINE" containing * all inserted characters. */ int selfinsert(int f, int n) { struct line *lp; int c; int count; if (n < 0) return (FALSE); if (n == 0) return (TRUE); c = key.k_chars[key.k_count - 1]; if (macrodef && macrocount < MAXMACRO) { if (f & FFARG) macrocount -= 2; /* last command was insert -- tack on the end */ if (lastflag & CFINS) { macrocount--; /* Ensure the line can handle the new characters */ if (maclcur->l_size < maclcur->l_used + n) { if (lrealloc(maclcur, maclcur->l_used + n) == FALSE) return (FALSE); } maclcur->l_used += n; /* Copy in the new data */ for (count = maclcur->l_used - n; count < maclcur->l_used; count++) maclcur->l_text[count] = c; } else { macro[macrocount - 1].m_funct = insert; if ((lp = lalloc(n)) == NULL) return (FALSE); lp->l_bp = maclcur; lp->l_fp = maclcur->l_fp; maclcur->l_fp = lp; maclcur = lp; for (count = 0; count < n; count++) lp->l_text[count] = c; } thisflag |= CFINS; } if (c == '\n') { do { count = lnewline(); } while (--n && count == TRUE); return (count); } /* overwrite mode */ if (curbp->b_flag & BFOVERWRITE) { lchange(WFEDIT); while (curwp->w_doto < llength(curwp->w_dotp) && n--) lputc(curwp->w_dotp, curwp->w_doto++, c); if (n <= 0) return (TRUE); } return (linsert(n, c)); }
/* * dobuf: * execute the contents of the buffer pointed to * by the passed BP * * Directives start with a "!" and include: * * !endm End a macro * !if (cond) conditional execution * !else * !endif * !return Return (terminating current macro) * !goto <label> Jump to a label in the current macro * !force Force macro to continue...even if command fails * !while (cond) Execute a loop if the condition is true * !endwhile * * Line Labels begin with a "*" as the first nonblank char, like: * * *LBL01 * * struct buffer *bp; buffer to execute */ int dobuf(struct buffer *bp) { int status; /* status return */ struct line *lp; /* pointer to line to execute */ struct line *hlp; /* pointer to line header */ struct line *glp; /* line to goto */ struct line *mp; /* Macro line storage temp */ int dirnum; /* directive index */ int linlen; /* length of line to execute */ int i; /* index */ int c; /* temp character */ int force; /* force TRUE result? */ struct window *wp; /* ptr to windows to scan */ struct while_block *whlist; /* ptr to !WHILE list */ struct while_block *scanner; /* ptr during scan */ struct while_block *whtemp; /* temporary ptr to a struct while_block */ char *einit; /* initial value of eline */ char *eline; /* text of line to execute */ char *tkn; /* buffer to evaluate an expresion in */ #if DEBUGM char *sp; /* temp for building debug string */ char *ep; /* ptr to end of outline */ #endif tkn = alloca(NSTRING * sizeof(char)); /* clear IF level flags/while ptr */ execlevel = 0; whlist = NULL; scanner = NULL; /* scan the buffer to execute, building WHILE header blocks */ hlp = bp->b_linep; lp = hlp->l_fp; while (lp != hlp) { /* scan the current line */ eline = lp->l_text; i = lp->l_used; /* trim leading whitespace */ while (i-- > 0 && (*eline == ' ' || *eline == '\t')) ++eline; /* if theres nothing here, don't bother */ if (i <= 0) goto nxtscan; /* if is a while directive, make a block... */ if (eline[0] == '!' && eline[1] == 'w' && eline[2] == 'h') { whtemp = (struct while_block *)malloc(sizeof(struct while_block)); if (whtemp == NULL) { noram:mlwrite ("%%Out of memory during while scan"); failexit:freewhile (scanner); freewhile(whlist); return FALSE; } whtemp->w_begin = lp; whtemp->w_type = BTWHILE; whtemp->w_next = scanner; scanner = whtemp; } /* if is a BREAK directive, make a block... */ if (eline[0] == '!' && eline[1] == 'b' && eline[2] == 'r') { if (scanner == NULL) { mlwrite ("%%!BREAK outside of any !WHILE loop"); goto failexit; } whtemp = (struct while_block *)malloc(sizeof(struct while_block)); if (whtemp == NULL) goto noram; whtemp->w_begin = lp; whtemp->w_type = BTBREAK; whtemp->w_next = scanner; scanner = whtemp; } /* if it is an endwhile directive, record the spot... */ if (eline[0] == '!' && strncmp(&eline[1], "endw", 4) == 0) { if (scanner == NULL) { mlwrite ("%%!ENDWHILE with no preceding !WHILE in '%s'", bp->b_bname); goto failexit; } /* move top records from the scanner list to the whlist until we have moved all BREAK records and one WHILE record */ do { scanner->w_end = lp; whtemp = whlist; whlist = scanner; scanner = scanner->w_next; whlist->w_next = whtemp; } while (whlist->w_type == BTBREAK); } nxtscan: /* on to the next line */ lp = lp->l_fp; } /* while and endwhile should match! */ if (scanner != NULL) { mlwrite("%%!WHILE with no matching !ENDWHILE in '%s'", bp->b_bname); goto failexit; } /* let the first command inherit the flags from the last one.. */ thisflag = lastflag; /* starting at the beginning of the buffer */ hlp = bp->b_linep; lp = hlp->l_fp; while (lp != hlp) { /* allocate eline and copy macro line to it */ linlen = lp->l_used; if ((einit = eline = malloc(linlen + 1)) == NULL) { mlwrite("%%Out of Memory during macro execution"); freewhile(whlist); return FALSE; } strncpy(eline, lp->l_text, linlen); eline[linlen] = 0; /* make sure it ends */ /* trim leading whitespace */ while (*eline == ' ' || *eline == '\t') ++eline; /* dump comments and blank lines */ if (*eline == ';' || *eline == 0) goto onward; #if DEBUGM /* if $debug == TRUE, every line to execute gets echoed and a key needs to be pressed to continue ^G will abort the command */ if (macbug) { strcpy(outline, "<<<"); /* debug macro name */ strcat(outline, bp->b_bname); strcat(outline, ":"); /* debug if levels */ strcat(outline, itoa(execlevel)); strcat(outline, ":"); /* and lastly the line */ strcat(outline, eline); strcat(outline, ">>>"); /* change all '%' to ':' so mlwrite won't expect arguments */ sp = outline; while (*sp) if (*sp++ == '%') { /* advance to the end */ ep = --sp; while (*ep++); /* null terminate the string one out */ *(ep + 1) = 0; /* copy backwards */ while (ep-- > sp) *(ep + 1) = *ep; /* and advance sp past the new % */ sp += 2; } /* write out the debug line */ mlforce(outline); update(TRUE); /* and get the keystroke */ if ((c = get1key()) == abortc) { mlforce("(Macro aborted)"); freewhile(whlist); return FALSE; } if (c == metac) macbug = FALSE; } #endif /* Parse directives here.... */ dirnum = -1; if (*eline == '!') { /* Find out which directive this is */ ++eline; for (dirnum = 0; dirnum < NUMDIRS; dirnum++) if (strncmp(eline, dname[dirnum], strlen(dname[dirnum])) == 0) break; /* and bitch if it's illegal */ if (dirnum == NUMDIRS) { mlwrite("%%Unknown Directive"); freewhile(whlist); return FALSE; } /* service only the !ENDM macro here */ if (dirnum == DENDM) { mstore = FALSE; bstore = NULL; goto onward; } /* restore the original eline.... */ --eline; } /* if macro store is on, just salt this away */ if (mstore) { /* allocate the space for the line */ linlen = strlen(eline); if ((mp = lalloc(linlen)) == NULL) { mlwrite ("Out of memory while storing macro"); return FALSE; } /* copy the text into the new line */ for (i = 0; i < linlen; ++i) lputc(mp, i, eline[i]); /* attach the line to the end of the buffer */ bstore->b_linep->l_bp->l_fp = mp; mp->l_bp = bstore->b_linep->l_bp; bstore->b_linep->l_bp = mp; mp->l_fp = bstore->b_linep; goto onward; } force = FALSE; /* dump comments */ if (*eline == '*') goto onward; /* now, execute directives */ if (dirnum != -1) { /* skip past the directive */ while (*eline && *eline != ' ' && *eline != '\t') ++eline; execstr = eline; switch (dirnum) { case DIF: /* IF directive */ /* grab the value of the logical exp */ if (execlevel == 0) { if (macarg(tkn) != TRUE) goto eexec; if (stol(tkn) == FALSE) ++execlevel; } else ++execlevel; goto onward; case DWHILE: /* WHILE directive */ /* grab the value of the logical exp */ if (execlevel == 0) { if (macarg(tkn) != TRUE) goto eexec; if (stol(tkn) == TRUE) goto onward; } /* drop down and act just like !BREAK */ case DBREAK: /* BREAK directive */ if (dirnum == DBREAK && execlevel) goto onward; /* jump down to the endwhile */ /* find the right while loop */ whtemp = whlist; while (whtemp) { if (whtemp->w_begin == lp) break; whtemp = whtemp->w_next; } if (whtemp == NULL) { mlwrite ("%%Internal While loop error"); freewhile(whlist); return FALSE; } /* reset the line pointer back.. */ lp = whtemp->w_end; goto onward; case DELSE: /* ELSE directive */ if (execlevel == 1) --execlevel; else if (execlevel == 0) ++execlevel; goto onward; case DENDIF: /* ENDIF directive */ if (execlevel) --execlevel; goto onward; case DGOTO: /* GOTO directive */ /* .....only if we are currently executing */ if (execlevel == 0) { /* grab label to jump to */ eline = token(eline, golabel, NPAT); linlen = strlen(golabel); glp = hlp->l_fp; while (glp != hlp) { if (*glp->l_text == '*' && (strncmp (&glp->l_text[1], golabel, linlen) == 0)) { lp = glp; goto onward; } glp = glp->l_fp; } mlwrite("%%No such label"); freewhile(whlist); return FALSE; } goto onward; case DRETURN: /* RETURN directive */ if (execlevel == 0) goto eexec; goto onward; case DENDWHILE: /* ENDWHILE directive */ if (execlevel) { --execlevel; goto onward; } else { /* find the right while loop */ whtemp = whlist; while (whtemp) { if (whtemp->w_type == BTWHILE && whtemp->w_end == lp) break; whtemp = whtemp->w_next; } if (whtemp == NULL) { mlwrite ("%%Internal While loop error"); freewhile(whlist); return FALSE; } /* reset the line pointer back.. */ lp = whtemp->w_begin->l_bp; goto onward; } case DFORCE: /* FORCE directive */ force = TRUE; } } /* execute the statement */ status = docmd(eline); if (force) /* force the status */ status = TRUE; /* check for a command error */ if (status != TRUE) { /* look if buffer is showing */ wp = wheadp; while (wp != NULL) { if (wp->w_bufp == bp) { /* and point it */ wp->w_dotp = lp; wp->w_doto = 0; wp->w_flag |= WFHARD; } wp = wp->w_wndp; } /* in any case set the buffer . */ bp->b_dotp = lp; bp->b_doto = 0; free(einit); execlevel = 0; freewhile(whlist); return status; } onward: /* on to the next line */ free(einit); lp = lp->l_fp; } eexec: /* exit the current function */ execlevel = 0; freewhile(whlist); return TRUE; }
/* * Read file "fname" into the current buffer, blowing away any text * found there. Called by both the read and find commands. Return * the final status of the read. Also called by the mainline, to * read in a file specified on the command line as an argument. * The command bound to M-FNR is called after the buffer is set up * and before it is read. * * char fname[]; name of file to read * int lockfl; check for file locks? */ int readin(char *fname, int lockfl) { struct line *lp1; struct line *lp2; int i; struct window *wp; struct buffer *bp; int s; int nbytes; int nline; char mesg[NSTRING]; #if (FILOCK && BSD) || SVR4 if (lockfl && lockchk(fname) == ABORT) #if PKCODE { s = FIOFNF; bp = curbp; strcpy(bp->b_fname, ""); goto out; } #else return ABORT; #endif #endif #if CRYPT s = resetkey(); if (s != TRUE) return s; #endif bp = curbp; /* Cheap. */ if ((s = bclear(bp)) != TRUE) /* Might be old. */ return s; bp->b_flag &= ~(BFINVS | BFCHG); strcpy(bp->b_fname, fname); /* let a user macro get hold of things...if he wants */ execute(META | SPEC | 'R', FALSE, 1); if ((s = ffropen(fname)) == FIOERR) /* Hard file open. */ goto out; if (s == FIOFNF) { /* File not found. */ mlwrite("(New file)"); goto out; } /* read the file in */ mlwrite("(Reading file)"); nline = 0; while ((s = ffgetline()) == FIOSUC) { nbytes = strlen(fline); if ((lp1 = lalloc(nbytes)) == NULL) { s = FIOMEM; /* Keep message on the */ break; /* display. */ } #if PKCODE if (nline > MAXNLINE) { s = FIOMEM; break; } #endif lp2 = lback(curbp->b_linep); lp2->l_fp = lp1; lp1->l_fp = curbp->b_linep; lp1->l_bp = lp2; curbp->b_linep->l_bp = lp1; for (i = 0; i < nbytes; ++i) lputc(lp1, i, fline[i]); ++nline; } ffclose(); /* Ignore errors. */ strcpy(mesg, "("); if (s == FIOERR) { strcat(mesg, "I/O ERROR, "); curbp->b_flag |= BFTRUNC; } if (s == FIOMEM) { strcat(mesg, "OUT OF MEMORY, "); curbp->b_flag |= BFTRUNC; } sprintf(&mesg[strlen(mesg)], "Read %d line", nline); if (nline != 1) strcat(mesg, "s"); strcat(mesg, ")"); mlwrite(mesg); out: for (wp = wheadp; wp != NULL; wp = wp->w_wndp) { if (wp->w_bufp == curbp) { wp->w_linep = lforw(curbp->b_linep); wp->w_dotp = lforw(curbp->b_linep); wp->w_doto = 0; wp->w_markp = NULL; wp->w_marko = 0; wp->w_flag |= WFMODE | WFHARD; } } if (s == FIOERR || s == FIOFNF) /* False if error. */ return FALSE; return TRUE; }
/* * Insert file "fname" into the current buffer, Called by insert file command. * Return the final status of the read. */ int ifile(char fname[]) { LINE *lp0, *lp1, *lp2; BUFFER *bp; char line[NLINE]; int i, s, nbytes; int nline = 0; int lflag; /* any lines longer than allowed? */ bp = curbp; /* Cheap */ bp->b_flag |= BFCHG; /* we have changed */ bp->b_flag &= ~BFTEMP; /* and are not temporary */ if ((s = ffropen(fname)) == FIOERR) /* Hard file open */ goto out; if (s == FIOFNF) { /* File not found */ mlwrite("[No such file]"); return (FALSE); } mlwrite("[Inserting file]"); /* back up a line and save the mark here */ curwp->w_dotp = lback(curwp->w_dotp); curwp->w_doto = 0; curwp->w_markp = curwp->w_dotp; curwp->w_marko = 0; lflag = FALSE; while ((s = ffgetline(line, NLINE)) == FIOSUC || s == FIOLNG) { if (s == FIOLNG) lflag = TRUE; nbytes = strlen(line); if ((lp1 = lalloc(nbytes)) == NULL) { s = FIOERR; /* keep message on the */ break; /* display */ } lp0 = curwp->w_dotp; /* line previous to insert */ lp2 = lp0->l_fp; /* line after insert */ /* re-link new line between lp0 and lp2 */ lp2->l_bp = lp1; lp0->l_fp = lp1; lp1->l_bp = lp0; lp1->l_fp = lp2; /* and advance and write out the current line */ curwp->w_dotp = lp1; for (i = 0; i < nbytes; ++i) lputc(lp1, i, line[i]); ++nline; } ffclose(); /* Ignore errors */ curwp->w_markp = lforw(curwp->w_markp); if (s == FIOEOF) { /* Don't zap message! */ if (nline != 1) mlwrite("[Inserted %d lines]", nline); else mlwrite("[Inserted 1 line]"); } if (lflag) { if (nline != 1) mlwrite("[Inserted %d lines: Long lines wrapped]", nline); else mlwrite("[Inserted 1 line: Long lines wrapped]"); } out: /* advance to the next line and mark the window for changes */ curwp->w_dotp = lforw(curwp->w_dotp); curwp->w_flag |= WFHARD; /* copy window parameters back to the buffer structure */ curbp->b_dotp = curwp->w_dotp; curbp->b_doto = curwp->w_doto; curbp->b_markp = curwp->w_markp; curbp->b_marko = curwp->w_marko; /* we need to update number of lines in the buffer */ curwp->w_bufp->b_lines += nline; if (s == FIOERR) /* False if error */ return (FALSE); return (TRUE); }
/* * Insert file "fname" into the current * buffer, Called by insert file command. Return the final * status of the read. */ int ifile(char *fname) { struct line *lp0; struct line *lp1; struct line *lp2; int i; struct buffer *bp; int s; int nbytes; int nline; char mesg[NSTRING]; bp = curbp; /* Cheap. */ bp->b_flag |= BFCHG; /* we have changed */ bp->b_flag &= ~BFINVS; /* and are not temporary */ if ((s = ffropen(fname)) == FIOERR) /* Hard file open. */ goto out; if (s == FIOFNF) { /* File not found. */ mlwrite("(No such file)"); return FALSE; } mlwrite("(Inserting file)"); #if CRYPT s = resetkey(); if (s != TRUE) return s; #endif /* back up a line and save the mark here */ curwp->w_dotp = lback(curwp->w_dotp); curwp->w_doto = 0; curwp->w_markp = curwp->w_dotp; curwp->w_marko = 0; nline = 0; while ((s = ffgetline()) == FIOSUC) { nbytes = strlen(fline); if ((lp1 = lalloc(nbytes)) == NULL) { s = FIOMEM; /* Keep message on the */ break; /* display. */ } lp0 = curwp->w_dotp; /* line previous to insert */ lp2 = lp0->l_fp; /* line after insert */ /* re-link new line between lp0 and lp2 */ lp2->l_bp = lp1; lp0->l_fp = lp1; lp1->l_bp = lp0; lp1->l_fp = lp2; /* and advance and write out the current line */ curwp->w_dotp = lp1; for (i = 0; i < nbytes; ++i) lputc(lp1, i, fline[i]); ++nline; } ffclose(); /* Ignore errors. */ curwp->w_markp = lforw(curwp->w_markp); strcpy(mesg, "("); if (s == FIOERR) { strcat(mesg, "I/O ERROR, "); curbp->b_flag |= BFTRUNC; } if (s == FIOMEM) { strcat(mesg, "OUT OF MEMORY, "); curbp->b_flag |= BFTRUNC; } sprintf(&mesg[strlen(mesg)], "Inserted %d line", nline); if (nline > 1) strcat(mesg, "s"); strcat(mesg, ")"); mlwrite(mesg); out: /* advance to the next line and mark the window for changes */ curwp->w_dotp = lforw(curwp->w_dotp); curwp->w_flag |= WFHARD | WFMODE; /* copy window parameters back to the buffer structure */ curbp->b_dotp = curwp->w_dotp; curbp->b_doto = curwp->w_doto; curbp->b_markp = curwp->w_markp; curbp->b_marko = curwp->w_marko; if (s == FIOERR) /* False if error. */ return FALSE; return TRUE; }