diff options
author | tnn <tnn@pkgsrc.org> | 2008-05-31 16:47:36 +0000 |
---|---|---|
committer | tnn <tnn@pkgsrc.org> | 2008-05-31 16:47:36 +0000 |
commit | 07f2d7c8b3668b5b03e53d79519d48b22c7f6ce3 (patch) | |
tree | 148a3174dd13953fbaa9a00d98253dea52297fd9 /shells/pdksh/files/vi.c | |
parent | 69f6bb8dbc4daf959d342154179c9d338d1acac0 (diff) | |
download | pkgsrc-07f2d7c8b3668b5b03e53d79519d48b22c7f6ce3.tar.gz |
Merge assorted bugfixes to pdksh-5.2.14, taken as diff between
PDKSH-5_2_14 and NetBSD-current HEAD as of 2008-05-31.
- Fixes rare segfault seen on Solaris.
- add strlcpy and strlcat fallback implementations from libnbcompat
- regenerate configure (using autoconf-2.12, ugh)
Diffstat (limited to 'shells/pdksh/files/vi.c')
-rw-r--r-- | shells/pdksh/files/vi.c | 188 |
1 files changed, 109 insertions, 79 deletions
diff --git a/shells/pdksh/files/vi.c b/shells/pdksh/files/vi.c index b9408ceb490..dbde10b9e05 100644 --- a/shells/pdksh/files/vi.c +++ b/shells/pdksh/files/vi.c @@ -1,9 +1,17 @@ +/* $NetBSD: vi.c,v 1.2 2008/05/31 16:47:37 tnn Exp $ */ + /* * vi command editing * written by John Rochester (initially for nsh) * bludgeoned to fit pdksh by Larry Bouzane, Jeff Sparkes & Eric Gisin * */ +#include <sys/cdefs.h> + +#ifndef lint +__RCSID("$NetBSD: vi.c,v 1.2 2008/05/31 16:47:37 tnn Exp $"); +#endif + #include "config.h" #ifdef VI @@ -25,44 +33,45 @@ struct edstate { }; -static int vi_hook ARGS((int ch)); -static void vi_reset ARGS((char *buf, size_t len)); -static int nextstate ARGS((int ch)); -static int vi_insert ARGS((int ch)); -static int vi_cmd ARGS((int argcnt, const char *cmd)); -static int domove ARGS((int argcnt, const char *cmd, int sub)); -static int redo_insert ARGS((int count)); -static void yank_range ARGS((int a, int b)); -static int bracktype ARGS((int ch)); +static int vi_hook ARGS((int)); +static void vi_reset ARGS((char *, size_t)); +static int nextstate ARGS((int)); +static int vi_insert ARGS((int)); +static int vi_cmd ARGS((int, const char *)); +static int domove ARGS((int, const char *, int)); +static int redo_insert ARGS((int)); +static void yank_range ARGS((int, int)); +static int bracktype ARGS((int)); static void save_cbuf ARGS((void)); static void restore_cbuf ARGS((void)); -static void edit_reset ARGS((char *buf, size_t len)); -static int putbuf ARGS((const char *buf, int len, int repl)); -static void del_range ARGS((int a, int b)); -static int findch ARGS((int ch, int cnt, int forw, int incl)); -static int forwword ARGS((int argcnt)); -static int backword ARGS((int argcnt)); -static int endword ARGS((int argcnt)); -static int Forwword ARGS((int argcnt)); -static int Backword ARGS((int argcnt)); -static int Endword ARGS((int argcnt)); -static int grabhist ARGS((int save, int n)); -static int grabsearch ARGS((int save, int start, int fwd, char *pat)); -static void redraw_line ARGS((int newline)); -static void refresh ARGS((int leftside)); +static void edit_reset ARGS((char *, size_t)); +static int putbuf ARGS((const char *, int, int)); +static void del_range ARGS((int, int)); +static int findch ARGS((int, int, int, int)); +static int forwword ARGS((int)); +static int backword ARGS((int)); +static int endword ARGS((int)); +static int Forwword ARGS((int)); +static int Backword ARGS((int)); +static int Endword ARGS((int)); +static int grabhist ARGS((int, int)); +static int grabsearch ARGS((int, int, int, char *)); +static void redraw_line ARGS((int)); +static void refresh ARGS((int)); static int outofwin ARGS((void)); static void rewindow ARGS((void)); -static int newcol ARGS((int ch, int col)); -static void display ARGS((char *wb1, char *wb2, int leftside)); -static void ed_mov_opt ARGS((int col, char *wb)); -static int expand_word ARGS((int command)); -static int complete_word ARGS((int command, int count)); -static int print_expansions ARGS((struct edstate *e, int command)); -static int char_len ARGS((int c)); -static void x_vi_zotc ARGS((int c)); -static void vi_pprompt ARGS((int full)); +static int newcol ARGS((int, int)); +static void display ARGS((char *, char *, int)); +static void ed_mov_opt ARGS((int, char *)); +static int expand_word ARGS((int)); +static int complete_word ARGS((int, int)); +static int print_expansions ARGS((struct edstate *, int)); +static int char_len ARGS((int)); +static void x_vi_zotc ARGS((int)); +static void vi_pprompt ARGS((int)); static void vi_error ARGS((void)); static void vi_macro_reset ARGS((void)); +static int x_vi_putbuf ARGS((const char *, size_t)); #define C_ 0x1 /* a valid command that isn't a M_, E_, U_ */ #define M_ 0x2 /* movement command (h, l, etc.) */ @@ -235,7 +244,7 @@ x_vi(buf, len) x_putc('\r'); x_putc('\n'); x_flush(); - if (c == -1) + if (c == -1 || len <= es->linelen) return -1; if (es->cbuf != buf) @@ -419,7 +428,7 @@ vi_hook(ch) } } else { locpat[srchlen] = '\0'; - (void) strcpy(srchpat, locpat); + (void) strlcpy(srchpat, locpat, sizeof srchpat); } state = VCMD; } else if (ch == edchars.erase || ch == Ctrl('h')) { @@ -443,9 +452,9 @@ vi_hook(ch) int i; int n = srchlen; - while (n > 0 && isspace(locpat[n - 1])) + while (n > 0 && isspace((unsigned char)locpat[n - 1])) n--; - while (n > 0 && !isspace(locpat[n - 1])) + while (n > 0 && !isspace((unsigned char)locpat[n - 1])) n--; for (i = srchlen; --i >= n; ) es->linelen -= char_len((unsigned char) locpat[i]); @@ -459,15 +468,22 @@ vi_hook(ch) else { locpat[srchlen++] = ch; if ((ch & 0x80) && Flag(FVISHOW8)) { + if (es->linelen + 2 > es->cbufsize) + vi_error(); es->cbuf[es->linelen++] = 'M'; es->cbuf[es->linelen++] = '-'; ch &= 0x7f; } if (ch < ' ' || ch == 0x7f) { + if (es->linelen + 2 > es->cbufsize) + vi_error(); es->cbuf[es->linelen++] = '^'; es->cbuf[es->linelen++] = ch ^ '@'; - } else + } else { + if (es->linelen >= es->cbufsize) + vi_error(); es->cbuf[es->linelen++] = ch; + } es->cursor = es->linelen; refresh(0); } @@ -690,7 +706,7 @@ vi_insert(ch) /* End nonstandard vi commands } */ default: - if (es->linelen == es->cbufsize - 1) + if (es->linelen >= es->cbufsize - 1) return -1; ibuf[inslen++] = ch; if (insert == INSERT) { @@ -817,8 +833,8 @@ vi_cmd(argcnt, cmd) return -1; if (*cmd == 'c' && (cmd[1]=='w' || cmd[1]=='W') && - !isspace(es->cbuf[es->cursor])) { - while (isspace(es->cbuf[--ncursor])) + !isspace((unsigned char)es->cbuf[es->cursor])) { + while (isspace((unsigned char)es->cbuf[--ncursor])) ; ncursor++; } @@ -1050,7 +1066,7 @@ vi_cmd(argcnt, cmd) if (histnum(-1) < 0) return -1; p = *histpos(); -#define issp(c) (isspace((c)) || (c) == '\n') +#define issp(c) (isspace((unsigned char)(c)) || (c) == '\n') if (argcnt) { while (*p && issp(*p)) p++; @@ -1105,12 +1121,12 @@ vi_cmd(argcnt, cmd) return -1; for (i = 0; i < argcnt; i++) { p = &es->cbuf[es->cursor]; - if (islower(*p)) { + if (islower((unsigned char)*p)) { modified = 1; hnum = hlast; - *p = toupper(*p); - } else if (isupper(*p)) { + *p = toupper((unsigned char)*p); + } else if (isupper((unsigned char)*p)) { modified = 1; hnum = hlast; - *p = tolower(*p); + *p = tolower((unsigned char)*p); } if (es->cursor < es->linelen - 1) es->cursor++; @@ -1258,7 +1274,7 @@ domove(argcnt, cmd, sub) case '^': ncursor = 0; - while (ncursor < es->linelen - 1 && isspace(es->cbuf[ncursor])) + while (ncursor < es->linelen - 1 && isspace((unsigned char)es->cbuf[ncursor])) ncursor++; break; @@ -1402,8 +1418,8 @@ save_edstate(old) new = (struct edstate *)alloc(sizeof(struct edstate), APERM); new->cbuf = alloc(old->cbufsize, APERM); + memcpy(new->cbuf, old->cbuf, old->linelen); new->cbufsize = old->cbufsize; - strcpy(new->cbuf, old->cbuf); new->linelen = old->linelen; new->cursor = old->cursor; new->winleft = old->winleft; @@ -1414,7 +1430,7 @@ static void restore_edstate(new, old) struct edstate *old, *new; { - strncpy(new->cbuf, old->cbuf, old->linelen); + memcpy(new->cbuf, old->cbuf, old->linelen); new->linelen = old->linelen; new->cursor = old->cursor; new->winleft = old->winleft; @@ -1470,6 +1486,17 @@ edit_reset(buf, len) holdlen = 0; } +/* + * this is used for calling x_escape() in complete_word() + */ +static int +x_vi_putbuf(s, len) + const char *s; + size_t len; +{ + return putbuf(s, len, 0); +} + static int putbuf(buf, len, repl) const char *buf; @@ -1548,12 +1575,12 @@ forwword(argcnt) while (is_wordch(es->cbuf[ncursor]) && ncursor < es->linelen) ncursor++; - else if (!isspace(es->cbuf[ncursor])) + else if (!isspace((unsigned char)es->cbuf[ncursor])) while (!is_wordch(es->cbuf[ncursor]) && - !isspace(es->cbuf[ncursor]) && + !isspace((unsigned char)es->cbuf[ncursor]) && ncursor < es->linelen) ncursor++; - while (isspace(es->cbuf[ncursor]) && ncursor < es->linelen) + while (isspace((unsigned char)es->cbuf[ncursor]) && ncursor < es->linelen) ncursor++; } return ncursor; @@ -1567,7 +1594,7 @@ backword(argcnt) ncursor = es->cursor; while (ncursor > 0 && argcnt--) { - while (--ncursor > 0 && isspace(es->cbuf[ncursor])) + while (--ncursor > 0 && isspace((unsigned char)es->cbuf[ncursor])) ; if (ncursor > 0) { if (is_wordch(es->cbuf[ncursor])) @@ -1577,7 +1604,7 @@ backword(argcnt) else while (--ncursor >= 0 && !is_wordch(es->cbuf[ncursor]) && - !isspace(es->cbuf[ncursor])) + !isspace((unsigned char)es->cbuf[ncursor])) ; ncursor++; } @@ -1594,7 +1621,7 @@ endword(argcnt) ncursor = es->cursor; while (ncursor < es->linelen && argcnt--) { while (++ncursor < es->linelen - 1 && - isspace(es->cbuf[ncursor])) + isspace((unsigned char)es->cbuf[ncursor])) ; if (ncursor < es->linelen - 1) { if (is_wordch(es->cbuf[ncursor])) @@ -1604,7 +1631,7 @@ endword(argcnt) else while (++ncursor < es->linelen && !is_wordch(es->cbuf[ncursor]) && - !isspace(es->cbuf[ncursor])) + !isspace((unsigned char)es->cbuf[ncursor])) ; ncursor--; } @@ -1620,9 +1647,9 @@ Forwword(argcnt) ncursor = es->cursor; while (ncursor < es->linelen && argcnt--) { - while (!isspace(es->cbuf[ncursor]) && ncursor < es->linelen) + while (!isspace((unsigned char)es->cbuf[ncursor]) && ncursor < es->linelen) ncursor++; - while (isspace(es->cbuf[ncursor]) && ncursor < es->linelen) + while (isspace((unsigned char)es->cbuf[ncursor]) && ncursor < es->linelen) ncursor++; } return ncursor; @@ -1636,9 +1663,9 @@ Backword(argcnt) ncursor = es->cursor; while (ncursor > 0 && argcnt--) { - while (--ncursor >= 0 && isspace(es->cbuf[ncursor])) + while (--ncursor >= 0 && isspace((unsigned char)es->cbuf[ncursor])) ; - while (ncursor >= 0 && !isspace(es->cbuf[ncursor])) + while (ncursor >= 0 && !isspace((unsigned char)es->cbuf[ncursor])) ncursor--; ncursor++; } @@ -1654,11 +1681,11 @@ Endword(argcnt) ncursor = es->cursor; while (ncursor < es->linelen - 1 && argcnt--) { while (++ncursor < es->linelen - 1 && - isspace(es->cbuf[ncursor])) + isspace((unsigned char)es->cbuf[ncursor])) ; if (ncursor < es->linelen - 1) { while (++ncursor < es->linelen && - !isspace(es->cbuf[ncursor])) + !isspace((unsigned char)es->cbuf[ncursor])) ; ncursor--; } @@ -1732,8 +1759,8 @@ grabsearch(save, start, fwd, pat) } static void -redraw_line(newline) - int newline; +redraw_line(newlinex) + int newlinex; { (void) memset(wbuf[win], ' ', wbuf_len); if (newline) { @@ -1930,8 +1957,8 @@ ed_mov_opt(col, wb) /* replace word with all expansions (ie, expand word*) */ static int -expand_word(command) - int command; +expand_word(commandx) + int commandx; { static struct edstate *buf; int rval = 0; @@ -1941,7 +1968,7 @@ expand_word(command) int i; /* Undo previous expansion */ - if (command == 0 && expanded == EXPAND && buf) { + if (commandx == 0 && expanded == EXPAND && buf) { restore_edstate(es, buf); buf = 0; expanded = NONE; @@ -1965,7 +1992,7 @@ expand_word(command) del_range(start, end); es->cursor = start; for (i = 0; i < nwords; ) { - if (putbuf(words[i], (int) strlen(words[i]), 0) != 0) { + if (x_escape(words[i], strlen(words[i]), x_vi_putbuf) != 0) { rval = -1; break; } @@ -1985,8 +2012,8 @@ expand_word(command) } static int -complete_word(command, count) - int command; +complete_word(commandx, count) + int commandx; int count; { static struct edstate *buf; @@ -2000,12 +2027,12 @@ complete_word(command, count) int is_command; /* Undo previous completion */ - if (command == 0 && expanded == COMPLETE && buf) { + if (commandx == 0 && expanded == COMPLETE && buf) { print_expansions(buf, 0); expanded = PRINT; return 0; } - if (command == 0 && expanded == PRINT && buf) { + if (commandx == 0 && expanded == PRINT && buf) { restore_edstate(es, buf); buf = 0; expanded = NONE; @@ -2068,9 +2095,12 @@ complete_word(command, count) buf = save_edstate(es); del_range(start, end); es->cursor = start; - if (putbuf(match, match_len, 0) != 0) - rval = -1; - else if (is_unique) { + + /* escape all shell-sensitive characters and put the result into + * command buffer */ + rval = x_escape(match, match_len, x_vi_putbuf); + + if (rval == 0 && is_unique) { /* If exact match, don't undo. Allows directory completions * to be used (ie, complete the next portion of the path). */ @@ -2091,9 +2121,9 @@ complete_word(command, count) } static int -print_expansions(e, command) - struct edstate *e; - int command; +print_expansions(ex, commandx) + struct edstate *ex; + int commandx; { int nwords; int start, end; @@ -2101,7 +2131,7 @@ print_expansions(e, command) int is_command; nwords = x_cf_glob(XCF_COMMAND_FILE|XCF_FULLPATH, - e->cbuf, e->linelen, e->cursor, + ex->cbuf, ex->linelen, ex->cursor, &start, &end, &words, &is_command); if (nwords == 0) { vi_error(); @@ -2129,7 +2159,7 @@ char_len(c) return len; } -/* Similar to x_zotc(emacs.c), but no tab wierdness */ +/* Similar to x_zotc(emacs.c), but no tab weirdness */ static void x_vi_zotc(c) int c; |