summaryrefslogtreecommitdiff
path: root/Src/Zle
diff options
context:
space:
mode:
Diffstat (limited to 'Src/Zle')
-rw-r--r--Src/Zle/compcore.c43
-rw-r--r--Src/Zle/compctl.c4
-rw-r--r--Src/Zle/complete.c6
-rw-r--r--Src/Zle/complist.c84
-rw-r--r--Src/Zle/compmatch.c14
-rw-r--r--Src/Zle/compresult.c22
-rw-r--r--Src/Zle/computil.c19
-rw-r--r--Src/Zle/textobjects.c6
-rw-r--r--Src/Zle/zle.h17
-rw-r--r--Src/Zle/zle_hist.c33
-rw-r--r--Src/Zle/zle_keymap.c85
-rw-r--r--Src/Zle/zle_main.c33
-rw-r--r--Src/Zle/zle_misc.c3
-rw-r--r--Src/Zle/zle_refresh.c500
-rw-r--r--Src/Zle/zle_thingy.c6
-rw-r--r--Src/Zle/zle_tricky.c71
-rw-r--r--Src/Zle/zle_utils.c55
-rw-r--r--Src/Zle/zle_vi.c9
18 files changed, 489 insertions, 521 deletions
diff --git a/Src/Zle/compcore.c b/Src/Zle/compcore.c
index 4ac5d089f..fb703f801 100644
--- a/Src/Zle/compcore.c
+++ b/Src/Zle/compcore.c
@@ -708,7 +708,7 @@ callcompfunc(char *s, char *fn)
sav = *ss;
*ss = '\0';
- tmp = (linwhat == IN_MATH ? dupstring(s) : multiquote(s, 0));
+ tmp = (linwhat == IN_MATH ? dupstring_wlen(s, offs) : multiquote(s, 0));
untokenize(tmp);
compprefix = ztrdup(tmp);
*ss = sav;
@@ -1230,14 +1230,14 @@ check_param(char *s, int set, int test)
else if (idigit(*e))
while (idigit(*e))
e++;
- else if ((ie = itype_end(e, IIDENT, 0)) != e) {
+ else if ((ie = itype_end(e, INAMESPC, 0)) != e) {
do {
e = ie;
if (comppatmatch && *comppatmatch &&
(*e == Star || *e == Quest))
ie = e + 1;
else
- ie = itype_end(e, IIDENT, 0);
+ ie = itype_end(e, INAMESPC, 0);
} while (ie != e);
}
@@ -1820,7 +1820,7 @@ set_comp_sep(void)
*/
sav = s[(i = swb - 1 - sqq + dq)];
s[i] = '\0';
- qp = (qttype == QT_SINGLE) ? dupstring(s) : rembslash(s);
+ qp = (qttype == QT_SINGLE) ? dupstring_wlen(s, i) : rembslash(s);
s[i] = sav;
if (swe < swb)
swe = swb;
@@ -2244,13 +2244,14 @@ addmatches(Cadata dat, char **argv)
if (dat->aflags & CAF_MATCH) {
lipre = dupstring(compiprefix);
lisuf = dupstring(compisuffix);
- lpre = dupstring(compprefix);
- lsuf = dupstring(compsuffix);
- llpl = strlen(lpre);
- llsl = strlen(lsuf);
-
- if (llpl + (int)strlen(compqiprefix) + (int)strlen(lipre) != origlpre
- || llsl + (int)strlen(compqisuffix) + (int)strlen(lisuf) != origlsuf)
+ llpl = strlen(compprefix);
+ llsl = strlen(compsuffix);
+ lpre = dupstring_wlen(compprefix, llpl);
+ lsuf = dupstring_wlen(compsuffix, llsl);
+
+ /* This used to reference compqiprefix and compqisuffix, why? */
+ if (llpl + (int)strlen(qipre) + (int)strlen(lipre) != origlpre
+ || llsl + (int)strlen(qisuf) + (int)strlen(lisuf) != origlsuf)
lenchanged = 1;
/* Test if there is an existing -P prefix. */
@@ -2299,12 +2300,8 @@ addmatches(Cadata dat, char **argv)
for (p = lpre + 2; *p && *p != ')'; p++);
if (*p == ')') {
- char sav = p[1];
-
- p[1] = '\0';
- globflag = dupstring(lpre);
gfl = p - lpre + 1;
- p[1] = sav;
+ globflag = dupstring_wlen(lpre, gfl);
lpre = p + 1;
llpl -= gfl;
@@ -2730,7 +2727,7 @@ add_match_data(int alt, char *str, char *orig, Cline line,
sl = tsl;
}
if (qisl) {
- Cline qsl = bld_parts(dupstring(qisuf), qisl, qisl, NULL, NULL);
+ Cline qsl = bld_parts(dupstring_wlen(qisuf, qisl), qisl, qisl, NULL, NULL);
qsl->flags |= CLF_SUF;
qsl->suffix = qsl->prefix;
@@ -2813,7 +2810,7 @@ add_match_data(int alt, char *str, char *orig, Cline line,
line = p;
}
if (qipl) {
- Cline lp, p = bld_parts(dupstring(qipre), qipl, qipl, &lp, NULL);
+ Cline lp, p = bld_parts(dupstring_wlen(qipre, qipl), qipl, qipl, &lp, NULL);
lp->next = line;
line = p;
@@ -2898,9 +2895,9 @@ add_match_data(int alt, char *str, char *orig, Cline line,
*t++ = '$';
*t++ = '\'';
*t++ = '\\';
- *t++ = '0' + ((STOUC(curchar) >> 6) & 7);
- *t++ = '0' + ((STOUC(curchar) >> 3) & 7);
- *t++ = '0' + (STOUC(curchar) & 7);
+ *t++ = '0' + (((unsigned char) curchar >> 6) & 7);
+ *t++ = '0' + (((unsigned char) curchar >> 3) & 7);
+ *t++ = '0' + ((unsigned char) curchar & 7);
*t++ = '\'';
} while (cnt == MB_INCOMPLETE && fs < fe);
/* Scanning restarts from the spot after the char we skipped. */
@@ -3252,7 +3249,7 @@ makearray(LinkList l, int type, int flags, int *np, int *nlp, int *llp)
/* Now sort the array (it contains matches). */
matchorder = flags;
qsort((void *) rp, n, sizeof(Cmatch),
- (int (*) _((const void *, const void *)))matchcmp);
+ (int (*) (const void *, const void *))matchcmp);
/* since the matches are sorted and the default is to remove
* all duplicates, -1 (remove only consecutive dupes) is a no-op,
@@ -3294,7 +3291,7 @@ makearray(LinkList l, int type, int flags, int *np, int *nlp, int *llp)
sp = (Cmatch *) zhalloc((n + 1) * sizeof(Cmatch));
memcpy(sp, rp, (n + 1) * sizeof(Cmatch));
qsort((void *) sp, n, sizeof(Cmatch),
- (int (*) _((const void *, const void *)))matchcmp);
+ (int (*) (const void *, const void *))matchcmp);
for (asp = sp + 1; *asp; asp++) {
Cmatch *ap = asp - 1, *bp = asp;
if (matcheq(*ap, *bp)) {
diff --git a/Src/Zle/compctl.c b/Src/Zle/compctl.c
index 08355d1b9..de3ccdfce 100644
--- a/Src/Zle/compctl.c
+++ b/Src/Zle/compctl.c
@@ -3201,8 +3201,8 @@ makecomplistflags(Compctl cc, char *s, int incmd, int compadd)
memcpy(lpre, s, lpl);
lpre[lpl] = '\0';
qlpre = quotename(lpre);
- lsuf = dupstring(s + offs);
- lsl = strlen(lsuf);
+ lsl = strlen(s + offs);
+ lsuf = dupstring_wlen(s + offs, lsl);
qlsuf = quotename(lsuf);
/* First check for ~.../... */
diff --git a/Src/Zle/complete.c b/Src/Zle/complete.c
index 67a60963e..342611f1f 100644
--- a/Src/Zle/complete.c
+++ b/Src/Zle/complete.c
@@ -518,7 +518,7 @@ parse_class(Cpattern p, char *iptr)
ch = range_type((char *)iptr, nptr-iptr);
iptr = nptr + 2;
if (ch != PP_UNKWN)
- *optr++ = STOUC(Meta) + ch;
+ *optr++ = (unsigned char) Meta + ch;
} else {
/* characters stay metafied */
char *ptr1 = iptr;
@@ -829,7 +829,9 @@ bin_compadd(char *name, char **argv, UNUSED(Options ops), UNUSED(int func))
ca_args:
- if (mstr && (match = parse_cmatcher(name, mstr)) == pcm_err) {
+ if (mstr && (dat.aflags & CAF_MATCH) &&
+ (match = parse_cmatcher(name, mstr)) == pcm_err)
+ {
zsfree(mstr);
zfree(dat.dpar, dparsize);
return 1;
diff --git a/Src/Zle/complist.c b/Src/Zle/complist.c
index 0dc64db6a..091ad03b1 100644
--- a/Src/Zle/complist.c
+++ b/Src/Zle/complist.c
@@ -291,12 +291,12 @@ getcolval(char *s, int multi)
case '?': *p = '\177'; break;
default:
if (*s >= '0' && *s <= '7') {
- int i = STOUC(*s);
+ int i = (unsigned char) *s;
if (*++s >= '0' && *s <= '7') {
- i = (i * 8) + STOUC(*s);
+ i = (i * 8) + (unsigned char) *s;
if (*++s >= '0' && *s <= '7')
- i = (i * 8) + STOUC(*s);
+ i = (i * 8) + (unsigned char) *s;
}
*p = (char) i;
} else
@@ -305,7 +305,7 @@ getcolval(char *s, int multi)
} else if (*s == '^') {
if ((s[1] >= '@' && s[1] <= '_') ||
(s[1] >= 'a' && s[1] <= 'z'))
- *p = (char) (STOUC(*s) & ~0x60);
+ *p = (char) ((unsigned char) *s & ~0x60);
else if (s[1] == '?')
*p = '\177';
else {
@@ -794,7 +794,7 @@ clnicezputs(int do_colors, char *s, int ml)
*/
for (t = sptr; *t; t++) {
/* Input is metafied... */
- int nc = (*t == Meta) ? STOUC(*++t ^ 32) : STOUC(*t);
+ int nc = (*t == Meta) ? (unsigned char) (*++t ^ 32) : (unsigned char) *t;
/* Is the screen full? */
if (ml == mlend - 1 && col == zterm_columns - 1) {
mlprinted = ml - oml;
@@ -852,7 +852,7 @@ clnicezputs(int do_colors, char *s, int ml)
cc = *s++ ^ 32;
for (t = nicechar(cc); *t; t++) {
- int nc = (*t == Meta) ? STOUC(*++t ^ 32) : STOUC(*t);
+ int nc = (*t == Meta) ? (unsigned char) (*++t ^ 32) : (unsigned char) *t;
if (ml == mlend - 1 && col == zterm_columns - 1) {
mlprinted = ml - oml;
return 0;
@@ -1072,7 +1072,7 @@ static int
compprintfmt(char *fmt, int n, int dopr, int doesc, int ml, int *stop)
{
char *p, nc[2*DIGBUFSIZE + 12], nbuf[2*DIGBUFSIZE + 12];
- int l = 0, cc = 0, b = 0, s = 0, u = 0, m, ask, beg, stat;
+ int l = 0, cc = 0, m, ask, beg, stat;
if ((stat = !fmt)) {
if (mlbeg >= 0) {
@@ -1118,48 +1118,46 @@ compprintfmt(char *fmt, int n, int dopr, int doesc, int ml, int *stop)
m = 0;
switch (cchar) {
case ZWC('%'):
- if (dopr == 1)
+ if (dopr == 1) {
+ applytextattributes(0);
putc('%', shout);
+ }
cc++;
break;
case ZWC('n'):
if (!stat) {
sprintf(nc, "%d", n);
- if (dopr == 1)
+ if (dopr == 1) {
+ applytextattributes(0);
fputs(nc, shout);
+ }
/* everything here is ASCII... */
cc += strlen(nc);
}
break;
case ZWC('B'):
- b = 1;
if (dopr)
- tcout(TCBOLDFACEBEG);
+ tsetattrs(TXTBOLDFACE);
break;
case ZWC('b'):
- b = 0; m = 1;
if (dopr)
- tcout(TCALLATTRSOFF);
+ tunsetattrs(TXTBOLDFACE);
break;
case ZWC('S'):
- s = 1;
if (dopr)
- tcout(TCSTANDOUTBEG);
+ tsetattrs(TXTSTANDOUT);
break;
case ZWC('s'):
- s = 0; m = 1;
if (dopr)
- tcout(TCSTANDOUTEND);
+ tunsetattrs(TXTSTANDOUT);
break;
case ZWC('U'):
- u = 1;
if (dopr)
- tcout(TCUNDERLINEBEG);
+ tsetattrs(TXTUNDERLINE);
break;
case ZWC('u'):
- u = 0; m = 1;
if (dopr)
- tcout(TCUNDERLINEEND);
+ tunsetattrs(TXTUNDERLINE);
break;
case ZWC('F'):
case ZWC('K'):
@@ -1173,20 +1171,28 @@ compprintfmt(char *fmt, int n, int dopr, int doesc, int ml, int *stop)
} else
atr = match_colour(NULL, is_fg, arg);
if (atr != TXT_ERROR && dopr)
- set_colour_attribute(atr, is_fg ? COL_SEQ_FG :
- COL_SEQ_BG, 0);
+ tsetattrs(atr);
break;
case ZWC('f'):
if (dopr)
- set_colour_attribute(TXTNOFGCOLOUR, COL_SEQ_FG, 0);
+ tunsetattrs(TXTFGCOLOUR);
break;
case ZWC('k'):
if (dopr)
- set_colour_attribute(TXTNOBGCOLOUR, COL_SEQ_BG, 0);
+ tunsetattrs(TXTBGCOLOUR);
+ break;
+ case ZWC('H'):
+ if (*p == '{') {
+ p = parsehighlight(p + 1, '}', &atr);
+ if (atr != TXT_ERROR && dopr)
+ treplaceattrs(atr);
+ }
break;
case ZWC('{'):
if (arg)
cc += arg;
+ if (dopr)
+ applytextattributes(0);
for (; *p && (*p != '%' || p[1] != '}'); p++)
if (dopr)
putc(*p == Meta ? *++p ^ 32 : *p, shout);
@@ -1197,7 +1203,7 @@ compprintfmt(char *fmt, int n, int dopr, int doesc, int ml, int *stop)
if (stat) {
sprintf(nc, "%d/%d", (n ? mlastm : mselect),
listdat.nlist);
- m = 2;
+ m = 1;
}
break;
case ZWC('M'):
@@ -1205,20 +1211,20 @@ compprintfmt(char *fmt, int n, int dopr, int doesc, int ml, int *stop)
sprintf(nbuf, "%d/%d", (n ? mlastm : mselect),
listdat.nlist);
sprintf(nc, "%-9s", nbuf);
- m = 2;
+ m = 1;
}
break;
case ZWC('l'):
if (stat) {
sprintf(nc, "%d/%d", ml + 1, listdat.nlines);
- m = 2;
+ m = 1;
}
break;
case ZWC('L'):
if (stat) {
sprintf(nbuf, "%d/%d", ml + 1, listdat.nlines);
sprintf(nc, "%-9s", nbuf);
- m = 2;
+ m = 1;
}
break;
case ZWC('p'):
@@ -1230,7 +1236,7 @@ compprintfmt(char *fmt, int n, int dopr, int doesc, int ml, int *stop)
((ml + 1) * 100) / listdat.nlines);
else
strcpy(nc, "Top");
- m = 2;
+ m = 1;
}
break;
case ZWC('P'):
@@ -1242,25 +1248,19 @@ compprintfmt(char *fmt, int n, int dopr, int doesc, int ml, int *stop)
((ml + 1) * 100) / listdat.nlines);
else
strcpy(nc, "Top ");
- m = 2;
+ m = 1;
}
break;
}
- if (m == 2 && dopr == 1) {
+ if (m && dopr) {
/* nc only contains ASCII text */
int l = strlen(nc);
if (l + cc > zterm_columns - 2)
nc[l -= l + cc - (zterm_columns - 2)] = '\0';
+ applytextattributes(0);
fputs(nc, shout);
cc += l;
- } else if (dopr && m == 1) {
- if (b)
- tcout(TCBOLDFACEBEG);
- if (s)
- tcout(TCSTANDOUTBEG);
- if (u)
- tcout(TCUNDERLINEBEG);
}
} else
break;
@@ -1276,6 +1276,7 @@ compprintfmt(char *fmt, int n, int dopr, int doesc, int ml, int *stop)
cc = 0;
}
if (dopr == 1) {
+ applytextattributes(0);
if (ml == mlend - 1 && (cc % zterm_columns) ==
zterm_columns - 1) {
dopr = 0;
@@ -1311,6 +1312,8 @@ compprintfmt(char *fmt, int n, int dopr, int doesc, int ml, int *stop)
}
}
if (dopr) {
+ treplaceattrs(0);
+ applytextattributes(0);
if (!(cc % zterm_columns))
fputs(" \010", shout);
cleareol();
@@ -2388,6 +2391,9 @@ domenuselect(Hookdef dummy, Chdata dat)
char *s;
char status[MAX_STATUS], *modeline = NULL;
+ if (! hasoldlist)
+ return 2;
+
msearchstack = NULL;
msearchstr = "";
msearchstate = MS_OK;
diff --git a/Src/Zle/compmatch.c b/Src/Zle/compmatch.c
index bb8359f1d..b58bd1f05 100644
--- a/Src/Zle/compmatch.c
+++ b/Src/Zle/compmatch.c
@@ -1161,8 +1161,8 @@ comp_match(char *pfx, char *sfx, char *w, Patprog cp, Cline *clp, int qu,
/* We still break it into parts here, trying to build a sensible
* cline list for these matches, too. */
- w = dupstring(w);
wl = strlen(w);
+ w = dupstring_wlen(w, wl);
*clp = bld_parts(w, wl, wl, NULL, NULL);
*exact = 0;
} else {
@@ -1319,7 +1319,7 @@ pattern_match_equivalence(Cpattern lp, convchar_t wind, int wmtp,
convchar_t lchr;
int lmtp;
- if (!PATMATCHINDEX(lp->u.str, wind, &lchr, &lmtp)) {
+ if (!PATMATCHINDEX(lp->u.str, wind-1, &lchr, &lmtp)) {
/*
* No equivalent. No possible match; give up.
*/
@@ -2045,12 +2045,12 @@ join_strs(int la, char *sa, int lb, char *sb)
zlelineasstring(line, mp->llen, 0, &convlen,
NULL, 0);
if (rr <= convlen) {
- char *or = rs;
+ ptrdiff_t diff = rp - rs;
int alloclen = (convlen > 20) ? convlen : 20;
rs = realloc(rs, (rl += alloclen));
rr += alloclen;
- rp += rs - or;
+ rp = rs + diff;
}
memcpy(rp, convstr, convlen);
rp += convlen;
@@ -2073,11 +2073,11 @@ join_strs(int la, char *sa, int lb, char *sb)
} else {
/* Same character, just take it. */
if (rr <= 1 /* HERE charlen */) {
- char *or = rs;
+ ptrdiff_t diff = rp - rs;
rs = realloc(rs, (rl += 20));
rr += 20;
- rp += rs - or;
+ rp = rs + diff;
}
/* HERE: multibyte char */
*rp++ = *sa;
@@ -2127,7 +2127,7 @@ cmp_anchors(Cline o, Cline n, int join)
(j = join_strs(o->wlen, o->word, n->wlen, n->word))) {
o->flags |= CLF_JOIN;
o->wlen = strlen(j);
- o->word = dupstring(j);
+ o->word = dupstring_wlen(j, o->wlen);
return 2;
}
diff --git a/Src/Zle/compresult.c b/Src/Zle/compresult.c
index 57789c0f3..7dbc5676a 100644
--- a/Src/Zle/compresult.c
+++ b/Src/Zle/compresult.c
@@ -489,7 +489,7 @@ static char *
build_pos_string(LinkList list)
{
LinkNode node;
- int l;
+ int l, buflen;
char buf[40], *s;
long p;
@@ -499,12 +499,12 @@ build_pos_string(LinkList list)
/* This could be used to put an extra colon before the end-of-word
* position if there is nothing missing. */
if (p < 0)
- sprintf(buf, ":%ld", -p);
+ buflen = sprintf(buf, ":%ld", -p);
else
#endif
- sprintf(buf, "%ld", p);
- setdata(node, dupstring(buf));
- l += 1 + strlen(buf);
+ buflen = sprintf(buf, "%ld", p);
+ setdata(node, dupstring_wlen(buf, buflen));
+ l += 1 + buflen;
}
s = (char *) zalloc(l * sizeof(char));
*s = 0;
@@ -897,7 +897,7 @@ void
do_allmatches(UNUSED(int end))
{
int first = 1, nm = nmatches - 1, omc = menucmp, oma = menuacc, e;
- Cmatch *mc;
+ Cmatch *mc = 0;
struct menuinfo mi;
char *p = (brbeg ? ztrdup(lastbrbeg->str) : NULL);
@@ -915,10 +915,10 @@ do_allmatches(UNUSED(int end))
#endif
}
+ if (minfo.group)
+ mc = (minfo.group)->matches;
- mc = (minfo.group)->matches;
-
- while (1) {
+ while (mc) {
if (!((*mc)->flags & CMF_ALL)) {
if (!first)
accept_last();
@@ -1731,8 +1731,6 @@ calclist(int showall)
width < zterm_columns && nth < g->dcount;
nth++, tcol++) {
- m = *p;
-
if (tcol == tcols) {
tcol = 0;
tlines++;
@@ -1994,7 +1992,6 @@ printlist(int over, CLPrintFunc printm, int showall)
(listdat.onlyexpl & ((*e)->always > 0 ? 2 : 1)))) {
if (pnl) {
putc('\n', shout);
- pnl = 0;
ml++;
if (cl >= 0 && --cl <= 1) {
cl = -1;
@@ -2087,7 +2084,6 @@ printlist(int over, CLPrintFunc printm, int showall)
(showall || !(m->flags & (CMF_HIDE|CMF_NOLIST)))) {
if (pnl) {
putc('\n', shout);
- pnl = 0;
ml++;
if (cl >= 0 && --cl <= 1) {
cl = -1;
diff --git a/Src/Zle/computil.c b/Src/Zle/computil.c
index 59abb4cc4..6ac458c91 100644
--- a/Src/Zle/computil.c
+++ b/Src/Zle/computil.c
@@ -911,7 +911,7 @@ struct cadef {
Caarg rest; /* the rest-argument */
char **defs; /* the original strings */
int ndefs; /* number of ... */
- int lastt; /* last time this was used */
+ time_t lastt; /* last time this was used */
Caopt *single; /* array of single-letter options */
char *match; /* -M spec to use */
int argsactive; /* if normal arguments are still allowed */
@@ -1296,8 +1296,7 @@ parse_cadef(char *nam, char **args)
int l = strlen(p) - 1;
if (*p == '(' && p[l] == ')') {
- axor = p = dupstring(p + 1);
- p[l - 1] = '\0';
+ axor = p = dupstring_wlen(p + 1, l - 1);
} else
axor = NULL;
if (!*p) {
@@ -1317,8 +1316,7 @@ parse_cadef(char *nam, char **args)
p = *++args;
l = strlen(p) - 1;
if (*p == '(' && p[l] == ')') {
- axor = p = dupstring(p + 1);
- p[l - 1] = '\0';
+ axor = p = dupstring_wlen(p + 1, l - 1);
} else
axor = NULL;
if (!*p) {
@@ -1339,7 +1337,7 @@ parse_cadef(char *nam, char **args)
LinkList list = newlinklist();
LinkNode node;
- char **xp, sav;
+ char **xp;
while (*p && *p != ')') {
for (p++; inblank(*p); p++);
@@ -1351,11 +1349,8 @@ parse_cadef(char *nam, char **args)
if (!*p)
break;
- sav = *p;
- *p = '\0';
- addlinknode(list, dupstring(q));
+ addlinknode(list, dupstring_wlen(q, p - q));
xnum++;
- *p = sav;
}
/* Oops, end-of-string. */
if (*p != ')') {
@@ -2935,7 +2930,7 @@ struct cvdef {
Cvval vals; /* value definitions */
char **defs; /* original strings */
int ndefs; /* number of ... */
- int lastt; /* last time used */
+ time_t lastt; /* last time used */
int words; /* if to look at other words */
};
@@ -4383,7 +4378,7 @@ cfp_matcher_range(Cmatcher *ms, char *add)
* word pattern.
*/
if ((ind = pattern_match_equivalence
- (m->word, ind, mt, addc)) != CHR_INVALID) {
+ (m->word, ind+1, mt, addc)) != CHR_INVALID) {
if (ret) {
if (imeta(ind)) {
*p++ = Meta;
diff --git a/Src/Zle/textobjects.c b/Src/Zle/textobjects.c
index c93777b65..a68c5296e 100644
--- a/Src/Zle/textobjects.c
+++ b/Src/Zle/textobjects.c
@@ -283,9 +283,9 @@ selectargument(UNUSED(char **args))
free(linein);
if (IS_THINGY(bindk, selectinshellword)) {
- ZLE_CHAR_T *match = ZWS("`\'\"");
- ZLE_CHAR_T *lmatch = ZWS("\'({"), *rmatch = ZWS("\')}");
- ZLE_CHAR_T *ematch = match, *found;
+ const ZLE_CHAR_T *match = ZWS("`\'\"");
+ const ZLE_CHAR_T *lmatch = ZWS("\'({"), *rmatch = ZWS("\')}");
+ const ZLE_CHAR_T *ematch = match, *found;
int start, end = zlecs;
/* for 'in' widget, don't include initial blanks ... */
while (mark < zlecs && ZC_iblank(zleline[mark]))
diff --git a/Src/Zle/zle.h b/Src/Zle/zle.h
index 391586c4a..5bb9e7a5e 100644
--- a/Src/Zle/zle.h
+++ b/Src/Zle/zle.h
@@ -186,7 +186,7 @@ typedef struct thingy *Thingy;
/* widgets (ZLE functions) */
-typedef int (*ZleIntFunc) _((char **));
+typedef int (*ZleIntFunc) (char **);
struct widget {
int flags; /* flags (see below) */
@@ -258,6 +258,9 @@ struct modifier {
#define MOD_NULL (1<<5) /* throw away text for the vi cut buffer */
#define MOD_CHAR (1<<6) /* force character-wise movement */
#define MOD_LINE (1<<7) /* force line-wise movement */
+#define MOD_PRI (1<<8) /* OS primary selection for the vi cut buffer */
+#define MOD_CLIP (1<<9) /* OS clipboard for the vi cut buffer */
+#define MOD_OSSEL (MOD_PRI | MOD_CLIP) /* either system selection */
/* current modifier status */
@@ -316,7 +319,7 @@ struct vichange {
typedef struct keymap *Keymap;
-typedef void (*KeyScanFunc) _((char *, Thingy, char *, void *));
+typedef void (*KeyScanFunc) (char *, Thingy, char *, void *);
#define invicmdmode() (!strcmp(curkeymapname, "vicmd"))
@@ -432,6 +435,8 @@ enum {
struct region_highlight {
/* Attributes turned on in the region */
zattr atr;
+ /* Priority for this region relative to others that overlap */
+ int layer;
/* Start of the region */
int start;
/* Start of the region in metafied ZLE line */
@@ -487,11 +492,7 @@ typedef struct {
*/
REFRESH_CHAR chr;
/*
- * Its attributes. 'On' attributes (TXT_ATTR_ON_MASK) are
- * applied before the character, 'off' attributes (TXT_ATTR_OFF_MASK)
- * after it. 'On' attributes are present for all characters that
- * need the effect; 'off' attributes are only present for the
- * last character in the sequence.
+ * Its attributes.
*/
zattr atr;
} REFRESH_ELEMENT;
@@ -523,7 +524,7 @@ typedef REFRESH_ELEMENT *REFRESH_STRING;
((int)((unsigned)(x) - ZSH_INVALID_WCHAR_BASE))
/* Turn a single byte character into a private wide character */
#define ZSH_CHAR_TO_INVALID_WCHAR(x) \
- ((wchar_t)(STOUC(x) + ZSH_INVALID_WCHAR_BASE))
+ ((wchar_t)((unsigned char) x + ZSH_INVALID_WCHAR_BASE))
#endif
diff --git a/Src/Zle/zle_hist.c b/Src/Zle/zle_hist.c
index cfaa70dae..53c722621 100644
--- a/Src/Zle/zle_hist.c
+++ b/Src/Zle/zle_hist.c
@@ -68,6 +68,13 @@ Keymap isearch_keymap;
*/
#define GETZLETEXT(ent) ((ent)->zle_text ? (ent)->zle_text : (ent)->node.nam)
+/*
+ * Flag that edits have been made to a zle line.
+ * If not set, nothing to forget.
+ */
+/**/
+int have_edits = 0;
+
/**/
void
remember_edits(void)
@@ -81,6 +88,7 @@ remember_edits(void)
if (ent->zle_text)
free(ent->zle_text);
ent->zle_text = zlemetaline ? ztrdup(line) : line;
+ have_edits = 1;
} else if (!zlemetaline)
free(line);
}
@@ -90,6 +98,10 @@ remember_edits(void)
void
forget_edits(void)
{
+ if (!have_edits) {
+ return;
+ }
+ have_edits = 0;
Histent he;
for (he = hist_ring; he; he = up_histent(he)) {
@@ -1746,7 +1758,8 @@ acceptandinfernexthistory(char **args)
{
Histent he;
- if (!(he = infernexthist(hist_ring, args)))
+ if (virangeflag || !(zlereadflags & ZLRF_HISTORY) ||
+ !(he = infernexthist(hist_ring, args)))
return 1;
zpushnode(bufstack, ztrdup(he->node.nam));
done = 1;
@@ -1758,8 +1771,11 @@ acceptandinfernexthistory(char **args)
int
infernexthistory(char **args)
{
- Histent he = quietgethist(histline);
+ Histent he;
+ if (virangeflag || !(zlereadflags & ZLRF_HISTORY))
+ return 1;
+ he = quietgethist(histline);
if (!he || !(he = infernexthist(he, args)))
return 1;
zle_setline(he);
@@ -1772,12 +1788,14 @@ vifetchhistory(UNUSED(char **args))
{
if (zmult < 0)
return 1;
- if (histline == curhist) {
+ if (histline == curhist || virangeflag || !(zlereadflags & ZLRF_HISTORY)) {
if (!(zmod.flags & MOD_MULT)) {
zlecs = zlell;
zlecs = findbol();
return 0;
}
+ if (virangeflag || !(zlereadflags & ZLRF_HISTORY))
+ return 1;
}
if (!zle_goto_hist((zmod.flags & MOD_MULT) ? zmult : curhist, 0, 0) &&
isset(HISTBEEP)) {
@@ -1921,6 +1939,9 @@ getvisrchstr(void)
int
vihistorysearchforward(char **args)
{
+ if (virangeflag || !(zlereadflags & ZLRF_HISTORY))
+ return 1;
+
if (*args) {
int ose = visrchsense, ret;
char *ost = visrchstr;
@@ -1942,6 +1963,9 @@ vihistorysearchforward(char **args)
int
vihistorysearchbackward(char **args)
{
+ if (virangeflag || !(zlereadflags & ZLRF_HISTORY))
+ return 1;
+
if (*args) {
int ose = visrchsense, ret;
char *ost = visrchstr;
@@ -1967,8 +1991,9 @@ virepeatsearch(UNUSED(char **args))
int n = zmult;
char *zt;
- if (!visrchstr)
+ if (!visrchstr || virangeflag || !(zlereadflags & ZLRF_HISTORY))
return 1;
+
if (zmult < 0) {
n = -n;
visrchsense = -visrchsense;
diff --git a/Src/Zle/zle_keymap.c b/Src/Zle/zle_keymap.c
index d90838f03..7f31f837c 100644
--- a/Src/Zle/zle_keymap.c
+++ b/Src/Zle/zle_keymap.c
@@ -404,7 +404,7 @@ static void
scankeys(HashNode hn, UNUSED(int flags))
{
Key k = (Key) hn;
- int f = k->nam[0] == Meta ? STOUC(k->nam[1])^32 : STOUC(k->nam[0]);
+ int f = k->nam[0] == Meta ? (unsigned char) k->nam[1]^32 : (unsigned char) k->nam[0];
char m[3];
while(skm_last < f) {
@@ -566,7 +566,7 @@ mod_export int
bindkey(Keymap km, const char *seq, Thingy bind, char *str)
{
Key k;
- int f = seq[0] == Meta ? STOUC(seq[1])^32 : STOUC(seq[0]);
+ int f = seq[0] == Meta ? (unsigned char) seq[1]^32 : (unsigned char) seq[0];
char *buf, *ptr;
if(km->flags & KM_IMMUTABLE)
@@ -661,7 +661,7 @@ keybind(Keymap km, char *seq, char **strp)
Key k;
if(ztrlen(seq) == 1) {
- int f = seq[0] == Meta ? STOUC(seq[1])^32 : STOUC(seq[0]);
+ int f = seq[0] == Meta ? (unsigned char) seq[1]^32 : (unsigned char) seq[0];
Thingy bind = km->first[f];
if(bind)
@@ -687,7 +687,7 @@ keyisprefix(Keymap km, char *seq)
if(!*seq)
return 1;
if(ztrlen(seq) == 1) {
- int f = seq[0] == Meta ? STOUC(seq[1])^32 : STOUC(seq[0]);
+ int f = seq[0] == Meta ? (unsigned char) seq[1]^32 : (unsigned char) seq[0];
if(km->first[f])
return 0;
@@ -745,7 +745,7 @@ bin_bindkey(char *name, char **argv, Options ops, UNUSED(int func))
static struct opn {
char o;
char selp;
- int (*func) _((char *, char *, Keymap, char **, Options, char));
+ int (*func) (char *, char *, Keymap, char **, Options, char);
int min, max;
} const opns[] = {
{ 'l', 0, bin_bindkey_lsmaps, 0, -1 },
@@ -764,10 +764,10 @@ bin_bindkey(char *name, char **argv, Options ops, UNUSED(int func))
int n;
/* select operation and ensure no clashing arguments */
- for(op = opns; op->o && !OPT_ISSET(ops,STOUC(op->o)); op++) ;
+ for(op = opns; op->o && !OPT_ISSET(ops,(unsigned char) op->o); op++) ;
if(op->o)
for(opp = op; (++opp)->o; )
- if(OPT_ISSET(ops,STOUC(opp->o))) {
+ if(OPT_ISSET(ops,(unsigned char) opp->o)) {
zwarnnam(name, "incompatible operation selection options");
return 1;
}
@@ -1049,7 +1049,7 @@ bin_bindkey_bind(char *name, char *kmname, Keymap km, char **argv, Options ops,
char m[3];
if(len < 2 || len > 2 + (bseq[1] == '-') ||
- (first = STOUC(bseq[0])) > (last = STOUC(bseq[len - 1]))) {
+ (first = (unsigned char) bseq[0]) > (last = (unsigned char) bseq[len - 1])) {
zwarnnam(name, "malformed key range `%s'", useq);
ret = 1;
} else {
@@ -1149,8 +1149,8 @@ scanbindlist(char *seq, Thingy bind, char *str, void *magic)
if(bind == bs->bind && (bind || !strcmp(str, bs->str)) &&
ztrlen(seq) == 1 && ztrlen(bs->lastseq) == 1) {
int l = bs->lastseq[1] ?
- STOUC(bs->lastseq[1]) ^ 32 : STOUC(bs->lastseq[0]);
- int t = seq[1] ? STOUC(seq[1]) ^ 32 : STOUC(seq[0]);
+ (unsigned char) bs->lastseq[1] ^ 32 : (unsigned char) bs->lastseq[0];
+ int t = seq[1] ? (unsigned char) seq[1] ^ 32 : (unsigned char) seq[0];
if(t == l + 1) {
zsfree(bs->lastseq);
@@ -1315,7 +1315,7 @@ default_bindings(void)
Keymap vismap = newkeymap(NULL, "visual");
Keymap smap = newkeymap(NULL, ".safe");
Keymap vimaps[2], vilmaps[2], kptr;
- char buf[3], *ed;
+ char buf[3];
int i;
/* vi insert mode and emacs mode: *
@@ -1445,17 +1445,14 @@ default_bindings(void)
}
/* Put the keymaps in the right namespace. The "main" keymap *
- * will be linked to the "emacs" keymap, except that if VISUAL *
- * or EDITOR contain the string "vi" then it will be linked to *
- * the "viins" keymap. */
+ * will be linked to the "emacs" keymap. */
linkkeymap(vmap, "viins", 0);
linkkeymap(emap, "emacs", 0);
linkkeymap(amap, "vicmd", 0);
linkkeymap(oppmap, "viopp", 0);
linkkeymap(vismap, "visual", 0);
linkkeymap(smap, ".safe", 1);
- if (((ed = zgetenv("VISUAL")) && strstr(ed, "vi")) ||
- ((ed = zgetenv("EDITOR")) && strstr(ed, "vi")))
+ if (isset(VIMODE))
linkkeymap(vmap, "main", 0);
else
linkkeymap(emap, "main", 0);
@@ -1526,10 +1523,10 @@ getrestchar_keybuf(void)
*/
while (1) {
if (bufind < buflen) {
- c = STOUC(keybuf[bufind++]);
+ c = (unsigned char) keybuf[bufind++];
if (c == Meta) {
DPUTS(bufind == buflen, "Meta at end of keybuf");
- c = STOUC(keybuf[bufind++]) ^ 32;
+ c = (unsigned char) keybuf[bufind++] ^ 32;
}
} else {
/*
@@ -1586,7 +1583,7 @@ getkeymapcmd(Keymap km, Thingy *funcp, char **strp)
Thingy func = t_undefinedkey;
char *str = NULL;
int lastlen = 0, lastc = lastchar;
- int timeout = 0;
+ int timeout = 0, csi = 0, oscdcs = 0;
keybuflen = 0;
keybuf[0] = 0;
@@ -1636,7 +1633,55 @@ getkeymapcmd(Keymap km, Thingy *funcp, char **strp)
}
#endif
}
- if (!ispfx)
+
+ /* CSI key sequences have a well defined structure so if we currently
+ * have an incomplete one, loop so the rest of it will be included in
+ * the key sequence if that arrives within the timeout. */
+ if (!csi && keybuflen >= 3 && keybuf[keybuflen - 3] == '\033' &&
+ keybuf[keybuflen - 2] == '[')
+ csi = keybuflen - 1;
+ if (csi) {
+ if (keybuf[keybuflen - 2] == Meta || keybuf[keybuflen - 1] < 0x20
+ || keybuf[keybuflen - 1] > 0x3f) {
+ /* If we reach the end of a valid CSI sequence and the matched key
+ * binding is for part of the CSI introduction, select instead the
+ * undefined-key widget and consume the full sequence from the
+ * input buffer. */
+ if (keybuf[keybuflen - 1] >= 0x40 &&
+ keybuf[keybuflen - 1] <= 0x7e && lastlen > csi - 2 &&
+ lastlen <= csi) {
+ if (keybuf[csi] == '?' && (keybuf[keybuflen - 1] == 'c' ||
+ keybuf[keybuflen - 1] == 'u'))
+ { /* is a terminal query response - discard */
+ keybuflen = csi - 2;
+ timeout = csi = 0;
+ continue;
+ }
+ func = t_undefinedkey;
+ lastlen = keybuflen;
+ }
+ csi = 0;
+ }
+ }
+ /* An OSC or DCS sequence is likely a late arriving terminal query
+ * response. Keep looping; if we reach an ST, discard the sequence
+ * - unless we first match a keybinding or a keytimeout elapses. */
+ if (oscdcs) {
+ if (keybuf[keybuflen - 1] == '\007' || /* BEL sometimes used */
+ (keybuf[keybuflen - 2] == '\033' &&
+ keybuf[keybuflen - 1] == '\\') ||
+ (keybuf[keybuflen - 2] == Meta && /* ST can be 0x9b */
+ (unsigned char) keybuf[keybuflen - 1] == (0x9b ^ 32)))
+ {
+ keybuflen = oscdcs - 2; /* discard */
+ timeout = oscdcs = 0;
+ continue;
+ }
+ } else if (keybuflen >= 2 && keybuf[keybuflen - 2] == '\033' &&
+ (keybuf[keybuflen - 1] == ']' || keybuf[keybuflen - 1] == 'P'))
+ oscdcs = keybuflen;
+
+ if (!ispfx && !csi && !oscdcs)
break;
}
if(!lastlen && keybuflen)
diff --git a/Src/Zle/zle_main.c b/Src/Zle/zle_main.c
index 9edf30e01..1afb1bf58 100644
--- a/Src/Zle/zle_main.c
+++ b/Src/Zle/zle_main.c
@@ -737,6 +737,7 @@ raw_getbyte(long do_keytmout, char *cptr, int full)
) {
/* Handle the fd. */
char *fdbuf;
+ Thingy save_lbindk = refthingy(lbindk);
{
char buf[BDIGBUFSIZE];
convbase(buf, lwatch_fd->fd, 10);
@@ -779,6 +780,8 @@ raw_getbyte(long do_keytmout, char *cptr, int full)
*/
errtry = 1;
}
+ unrefthingy(lbindk);
+ lbindk = save_lbindk;
}
}
/* Function may have invalidated the display. */
@@ -876,7 +879,7 @@ getbyte(long do_keytmout, int *timeout, int full)
#endif
if (kungetct)
- ret = STOUC(kungetbuf[--kungetct]);
+ ret = (unsigned char) kungetbuf[--kungetct];
else {
for (;;) {
int q = queue_signal_level();
@@ -940,7 +943,7 @@ getbyte(long do_keytmout, int *timeout, int full)
else if (cc == '\n')
cc = '\r';
- ret = STOUC(cc);
+ ret = (unsigned char) cc;
}
/*
* curvichg.buf is raw bytes, not wide characters, so is dealt
@@ -1230,9 +1233,9 @@ zleread(char **lp, char **rp, int flags, int context, char *init, char *finish)
char *pptbuf;
int pptlen;
- pptbuf = unmetafy(promptexpand(lp ? *lp : NULL, 0, NULL, NULL,
- &pmpt_attr),
+ pptbuf = unmetafy(promptexpand(lp ? *lp : NULL, 0, NULL, NULL),
&pptlen);
+ pmpt_attr = txtcurrentattrs;
write_loop(2, pptbuf, pptlen);
free(pptbuf);
return shingetline();
@@ -1267,10 +1270,13 @@ zleread(char **lp, char **rp, int flags, int context, char *init, char *finish)
fetchttyinfo = 0;
trashedzle = 0;
raw_lp = lp;
- lpromptbuf = promptexpand(lp ? *lp : NULL, 1, NULL, NULL, &pmpt_attr);
+ txtcurrentattrs = txtpendingattrs = txtunknownattrs = 0;
+ lpromptbuf = promptexpand(lp ? *lp : NULL, 1, NULL, NULL);
+ pmpt_attr = txtcurrentattrs;
raw_rp = rp;
- rpmpt_attr = pmpt_attr;
- rpromptbuf = promptexpand(rp ? *rp : NULL, 1, NULL, NULL, &rpmpt_attr);
+ rpromptbuf = promptexpand(rp ? *rp : NULL, 1, NULL, NULL);
+ rpmpt_attr = txtcurrentattrs;
+ prompt_attr = mixattrs(pmpt_attr, rpmpt_attr);
free_prepostdisplay();
zlereadflags = flags;
@@ -2009,17 +2015,18 @@ reexpandprompt(void)
char *new_lprompt, *new_rprompt;
looping = reexpanding;
- new_lprompt = promptexpand(raw_lp ? *raw_lp : NULL, 1, NULL, NULL,
- &pmpt_attr);
+ txtcurrentattrs = txtpendingattrs = txtunknownattrs = 0;
+ new_lprompt = promptexpand(raw_lp ? *raw_lp : NULL, 1, NULL, NULL);
+ pmpt_attr = txtcurrentattrs;
free(lpromptbuf);
lpromptbuf = new_lprompt;
if (looping != reexpanding)
continue;
- rpmpt_attr = pmpt_attr;
- new_rprompt = promptexpand(raw_rp ? *raw_rp : NULL, 1, NULL, NULL,
- &rpmpt_attr);
+ new_rprompt = promptexpand(raw_rp ? *raw_rp : NULL, 1, NULL, NULL);
+ rpmpt_attr = txtcurrentattrs;
+ prompt_attr = mixattrs(pmpt_attr, rpmpt_attr);
free(rpromptbuf);
rpromptbuf = new_rprompt;
} while (looping != reexpanding);
@@ -2065,6 +2072,8 @@ trashzle(void)
trashedzle = 1;
zrefresh();
showinglist = sl;
+ treplaceattrs(prompt_attr);
+ applytextattributes(0);
moveto(nlnct, 0);
if (clearflag && tccan(TCCLEAREOD)) {
tcout(TCCLEAREOD);
diff --git a/Src/Zle/zle_misc.c b/Src/Zle/zle_misc.c
index eba28d1ec..e17a08d53 100644
--- a/Src/Zle/zle_misc.c
+++ b/Src/Zle/zle_misc.c
@@ -841,9 +841,8 @@ whatcursorposition(UNUSED(char **args))
strcpy(s, mbstr);
s += len;
}
- sprintf(s, " (0%o, %u, 0x%x)", (unsigned int)c,
+ s += sprintf(s, " (0%o, %u, 0x%x)", (unsigned int)c,
(unsigned int)c, (unsigned int)c);
- s += strlen(s);
}
sprintf(s, " point %d of %d(%d%%) column %d", zlecs+1, zlell+1,
zlell ? 100 * zlecs / zlell : 0, zlecs - bol);
diff --git a/Src/Zle/zle_refresh.c b/Src/Zle/zle_refresh.c
index 30b5d4447..f076bdd61 100644
--- a/Src/Zle/zle_refresh.c
+++ b/Src/Zle/zle_refresh.c
@@ -36,8 +36,8 @@
* non-zero width followed by an arbitrary (but typically small)
* number of characters that have zero width (combining characters).
*
- * The allocated size for each array is given by ?mw_size; nmw_ind
- * is the next free element, i.e. nmwbuf[nmw_ind] will be the next
+ * The allocated size for each array is given by omw_size and nmw_size;
+ * nmw_ind is the next free element, i.e. nmwbuf[nmw_ind] will be the next
* element to be written (we never insert into omwbuf). We initialise
* nmw_ind to 1 to avoid the index stored in the character looking like a
* NULL. This wastees a word but it's safer than messing with pointers.
@@ -149,7 +149,7 @@ char *lpromptbuf, *rpromptbuf;
/* Text attributes after displaying prompts */
/**/
-zattr pmpt_attr, rpmpt_attr;
+zattr pmpt_attr, rpmpt_attr, prompt_attr;
/* number of lines displayed */
@@ -203,12 +203,18 @@ int predisplaylen, postdisplaylen;
/*
- * Attributes used by default on the command line, and
- * attributes for highlighting special (unprintable) characters
- * displayed on screen.
+ * Attributes used by default on the command line,
+ * for highlighting special (unprintable) characters displayed on screen,
+ * and for ellipsis continuation markers.
*/
-static zattr default_atr_on, special_atr_on;
+static zattr default_attr, special_attr, ellipsis_attr;
+
+/*
+ * Layer applied to highlighting for special characters
+ */
+
+static int special_layer;
/*
* Array of region highlights, no special termination.
@@ -245,20 +251,20 @@ char *tcout_func_name;
int cost;
# define SELECT_ADD_COST(X) (cost += X)
-# define zputc(a) (zwcputc(a, NULL), cost++)
+# define zputc(a) (zwcputc(a), cost++)
# define zwrite(a, b) (zwcwrite((a), (b)), \
cost += ((b) * ZLE_CHAR_SIZE))
#else
# define SELECT_ADD_COST(X)
-# define zputc(a) zwcputc(a, NULL)
+# define zputc(a) zwcputc(a)
# define zwrite(a, b) zwcwrite((a), (b))
#endif
-static const REFRESH_ELEMENT zr_cr = { ZWC('\r'), 0 };
+static const REFRESH_ELEMENT zr_cr = { ZWC('\r'), TXT_ERROR };
#ifdef MULTIBYTE_SUPPORT
-static const REFRESH_ELEMENT zr_dt = { ZWC('.'), 0 };
+static const REFRESH_ELEMENT zr_dt = { ZWC('.'), TXT_ERROR };
#endif
-static const REFRESH_ELEMENT zr_nl = { ZWC('\n'), 0 };
+static const REFRESH_ELEMENT zr_nl = { ZWC('\n'), TXT_ERROR };
static const REFRESH_ELEMENT zr_sp = { ZWC(' '), 0 };
static const REFRESH_ELEMENT zr_zr = { ZWC('\0'), 0 };
@@ -269,10 +275,10 @@ static const REFRESH_ELEMENT zr_zr = { ZWC('\0'), 0 };
static const REFRESH_ELEMENT zr_end_ellipsis[] = {
{ ZWC(' '), 0 },
{ ZWC('<'), 0 },
- { ZWC('.'), 0 },
- { ZWC('.'), 0 },
- { ZWC('.'), 0 },
- { ZWC('.'), 0 },
+ { ZWC('.'), TXT_ERROR },
+ { ZWC('.'), TXT_ERROR },
+ { ZWC('.'), TXT_ERROR },
+ { ZWC('.'), TXT_ERROR },
{ ZWC(' '), 0 },
};
#define ZR_END_ELLIPSIS_SIZE \
@@ -281,16 +287,16 @@ static const REFRESH_ELEMENT zr_end_ellipsis[] = {
static const REFRESH_ELEMENT zr_mid_ellipsis1[] = {
{ ZWC(' '), 0 },
{ ZWC('<'), 0 },
- { ZWC('.'), 0 },
- { ZWC('.'), 0 },
- { ZWC('.'), 0 },
- { ZWC('.'), 0 },
+ { ZWC('.'), TXT_ERROR },
+ { ZWC('.'), TXT_ERROR },
+ { ZWC('.'), TXT_ERROR },
+ { ZWC('.'), TXT_ERROR },
};
#define ZR_MID_ELLIPSIS1_SIZE \
((int)(sizeof(zr_mid_ellipsis1)/sizeof(zr_mid_ellipsis1[0])))
static const REFRESH_ELEMENT zr_mid_ellipsis2[] = {
- { ZWC('>'), 0 },
+ { ZWC('>'), TXT_ERROR },
{ ZWC(' '), 0 },
};
#define ZR_MID_ELLIPSIS2_SIZE \
@@ -298,10 +304,10 @@ static const REFRESH_ELEMENT zr_mid_ellipsis2[] = {
static const REFRESH_ELEMENT zr_start_ellipsis[] = {
{ ZWC('>'), 0 },
- { ZWC('.'), 0 },
- { ZWC('.'), 0 },
- { ZWC('.'), 0 },
- { ZWC('.'), 0 },
+ { ZWC('.'), TXT_ERROR },
+ { ZWC('.'), TXT_ERROR },
+ { ZWC('.'), TXT_ERROR },
+ { ZWC('.'), TXT_ERROR },
};
#define ZR_START_ELLIPSIS_SIZE \
((int)(sizeof(zr_start_ellipsis)/sizeof(zr_start_ellipsis[0])))
@@ -316,14 +322,15 @@ static void
zle_set_highlight(void)
{
char **atrs = getaparam("zle_highlight");
- int special_atr_on_set = 0;
- int region_atr_on_set = 0;
- int isearch_atr_on_set = 0;
- int suffix_atr_on_set = 0;
- int paste_atr_on_set = 0;
+ int special_attr_set = 0;
+ int region_attr_set = 0;
+ int isearch_attr_set = 0;
+ int suffix_attr_set = 0;
+ int paste_attr_set = 0;
+ int ellipsis_attr_set = 0;
struct region_highlight *rhp;
- special_atr_on = default_atr_on = 0;
+ special_attr = default_attr = 0;
if (!region_highlights) {
region_highlights = (struct region_highlight *)
zshcalloc(N_SPECIAL_HIGHLIGHTS*sizeof(struct region_highlight));
@@ -336,46 +343,63 @@ zle_set_highlight(void)
}
}
+ /* Default layers */
+ region_highlights[0].layer = 20; /* region */
+ region_highlights[1].layer = 20; /* isearch */
+ region_highlights[2].layer = 10; /* suffix */
+ region_highlights[3].layer = 15; /* paste */
+ special_layer = 30;
+
if (atrs) {
for (; *atrs; atrs++) {
if (!strcmp(*atrs, "none")) {
/* reset attributes for consistency... usually unnecessary */
- special_atr_on = default_atr_on = 0;
- special_atr_on_set = 1;
- paste_atr_on_set = region_atr_on_set =
- isearch_atr_on_set = suffix_atr_on_set = 1;
+ special_attr = default_attr = 0;
+ special_attr_set = 1;
+ paste_attr_set = region_attr_set =
+ isearch_attr_set = suffix_attr_set = 1;
} else if (strpfx("default:", *atrs)) {
- match_highlight(*atrs + 8, &default_atr_on);
+ match_highlight(*atrs + 8, &default_attr, NULL);
} else if (strpfx("special:", *atrs)) {
- match_highlight(*atrs + 8, &special_atr_on);
- special_atr_on_set = 1;
+ match_highlight(*atrs + 8, &special_attr, &special_layer);
+ special_attr_set = 1;
} else if (strpfx("region:", *atrs)) {
- match_highlight(*atrs + 7, &region_highlights[0].atr);
- region_atr_on_set = 1;
+ match_highlight(*atrs + 7, &(region_highlights[0].atr),
+ &(region_highlights[0].layer));
+ region_attr_set = 1;
} else if (strpfx("isearch:", *atrs)) {
- match_highlight(*atrs + 8, &(region_highlights[1].atr));
- isearch_atr_on_set = 1;
+ match_highlight(*atrs + 8, &(region_highlights[1].atr),
+ &(region_highlights[1].layer));
+ isearch_attr_set = 1;
} else if (strpfx("suffix:", *atrs)) {
- match_highlight(*atrs + 7, &(region_highlights[2].atr));
- suffix_atr_on_set = 1;
+ match_highlight(*atrs + 7, &(region_highlights[2].atr),
+ &(region_highlights[2].layer));
+ suffix_attr_set = 1;
} else if (strpfx("paste:", *atrs)) {
- match_highlight(*atrs + 6, &(region_highlights[3].atr));
- paste_atr_on_set = 1;
+ match_highlight(*atrs + 6, &(region_highlights[3].atr),
+ &(region_highlights[3].layer));
+ paste_attr_set = 1;
+ } else if (strpfx("ellipsis:", *atrs)) {
+ match_highlight(*atrs + 9, &ellipsis_attr, NULL);
+ ellipsis_attr_set = 1;
}
}
}
- /* Defaults */
- if (!special_atr_on_set)
- special_atr_on = TXTSTANDOUT;
- if (!region_atr_on_set)
+ /* Default attributes */
+ if (!special_attr_set)
+ special_attr = TXTSTANDOUT;
+ if (!region_attr_set)
region_highlights[0].atr = TXTSTANDOUT;
- if (!isearch_atr_on_set)
+ if (!isearch_attr_set)
region_highlights[1].atr = TXTUNDERLINE;
- if (!suffix_atr_on_set)
+ if (!suffix_attr_set)
region_highlights[2].atr = TXTBOLDFACE;
- if (!paste_atr_on_set)
+ if (!paste_attr_set)
region_highlights[3].atr = TXTSTANDOUT;
+ if (!ellipsis_attr_set)
+ ellipsis_attr = TXTBGCOLOUR | ((zattr) 3 << TXT_ATTR_BG_COL_SHIFT) |
+ TXTFGCOLOUR | ((zattr) 4 << TXT_ATTR_FG_COL_SHIFT);
allocate_colour_buffer();
}
@@ -400,14 +424,13 @@ zle_free_highlight(void)
char **
get_region_highlight(UNUSED(Param pm))
{
- int arrsize = n_region_highlights;
+ int arrsize = n_region_highlights - N_SPECIAL_HIGHLIGHTS;
char **retarr, **arrp;
struct region_highlight *rhp;
/* region_highlights may not have been set yet */
- if (!arrsize)
+ if (!n_region_highlights)
return hmkarray(NULL);
- arrsize -= N_SPECIAL_HIGHLIGHTS;
DPUTS(arrsize < 0, "arrsize is negative from n_region_highlights");
arrp = retarr = (char **)zhalloc((arrsize+1)*sizeof(char *));
@@ -415,20 +438,18 @@ get_region_highlight(UNUSED(Param pm))
for (rhp = region_highlights + N_SPECIAL_HIGHLIGHTS;
arrsize--;
rhp++, arrp++) {
- char digbuf1[DIGBUFSIZE], digbuf2[DIGBUFSIZE];
- int atrlen, alloclen;
- const char memo_equals[] = "memo=";
-
- sprintf(digbuf1, "%d", rhp->start);
- sprintf(digbuf2, "%d", rhp->end);
-
- atrlen = output_highlight(rhp->atr, NULL);
- alloclen = atrlen + strlen(digbuf1) + strlen(digbuf2) +
- 3; /* 2 spaces, 1 terminating NUL */
+ char digbuf[2 * DIGBUFSIZE], layerbuf[7 + DIGBUFSIZE];
+ int offset;
+ const char memo_equals[] = " memo=";
+ int alloclen = sprintf(digbuf, "%d %d", rhp->start, rhp->end) +
+ output_highlight(rhp->atr, NULL) +
+ 2; /* space and terminating NUL */
if (rhp->flags & ZRH_PREDISPLAY)
- alloclen += 2; /* "P " */
+ alloclen++; /* "P" */
+ if (rhp->layer != 10)
+ alloclen += sprintf(layerbuf, ",layer=%d", rhp->layer);
if (rhp->memo)
- alloclen += 1 /* space */ + strlen(memo_equals) + strlen(rhp->memo);
+ alloclen += sizeof(memo_equals) - 1 + strlen(rhp->memo);
*arrp = (char *)zhalloc(alloclen * sizeof(char));
/*
* On input we allow a space after the flags.
@@ -437,13 +458,14 @@ get_region_highlight(UNUSED(Param pm))
* into three words, and then check the first to
* see if there are flags. However, it's arguable.
*/
- sprintf(*arrp, "%s%s %s ",
+ offset = sprintf(*arrp, "%s%s ",
(rhp->flags & ZRH_PREDISPLAY) ? "P" : "",
- digbuf1, digbuf2);
- (void)output_highlight(rhp->atr, *arrp + strlen(*arrp));
+ digbuf);
+ (void)output_highlight(rhp->atr, *arrp + offset);
+ if (rhp->layer != 10)
+ strcat(*arrp, layerbuf);
if (rhp->memo) {
- strcat(*arrp, " ");
strcat(*arrp, memo_equals);
strcat(*arrp, rhp->memo);
}
@@ -452,12 +474,10 @@ get_region_highlight(UNUSED(Param pm))
return retarr;
}
-
/*
* The parameter system requires the pm argument, but this
* may be NULL if called directly.
*/
-
/**/
void
set_region_highlight(UNUSED(Param pm), char **aval)
@@ -516,7 +536,8 @@ set_region_highlight(UNUSED(Param pm), char **aval)
while (inblank(*strp))
strp++;
- strp = (char*) match_highlight(strp, &rhp->atr);
+ rhp->layer = 10; /* default */
+ strp = (char*) match_highlight(strp, &rhp->atr, &rhp->layer);
while (inblank(*strp))
strp++;
@@ -571,22 +592,6 @@ unset_region_highlight(Param pm, int exp)
}
-/* The last attributes that were on. */
-static zattr lastatr;
-
-/*
- * Clear the last attributes that we set: used when we're going
- * to be outputting stuff that shouldn't show up as text.
- */
-static void
-clearattributes(void)
-{
- if (lastatr) {
- settextattributes(TXT_ATTR_OFF_FROM_ON(lastatr));
- lastatr = 0;
- }
-}
-
/*
* Output a termcap capability, clearing any text attributes so
* as not to mess up the display.
@@ -595,7 +600,7 @@ clearattributes(void)
static void
tcoutclear(int cap)
{
- clearattributes();
+ cleartextattributes(0);
tcout(cap);
}
@@ -603,47 +608,20 @@ tcoutclear(int cap)
* Output the character. This must come from the new video
* buffer, nbuf, since we access the multiword buffer nmwbuf
* directly.
- *
- * curatrp may be NULL, otherwise points to an integer specifying
- * what attributes were turned on for a character output immediately
- * before, in order to optimise output of attribute changes.
*/
/**/
void
-zwcputc(const REFRESH_ELEMENT *c, zattr *curatrp)
+zwcputc(const REFRESH_ELEMENT *c)
{
- /*
- * Safety: turn attributes off if last heard of turned on.
- * This differs from *curatrp, which is an optimisation for
- * writing lots of stuff at once.
- */
#ifdef MULTIBYTE_SUPPORT
mbstate_t mbstate;
int i;
VARARR(char, mbtmp, MB_CUR_MAX + 1);
#endif
- if (lastatr & ~c->atr) {
- /* Stuff on we don't want, turn it off */
- settextattributes(TXT_ATTR_OFF_FROM_ON(lastatr & ~c->atr));
- lastatr = 0;
- }
-
- /*
- * Don't output "on" attributes in a string of characters with
- * the same attributes. Be careful in case a different colour
- * needs setting.
- */
- if ((c->atr & TXT_ATTR_ON_MASK) &&
- (!curatrp ||
- ((*curatrp & TXT_ATTR_ON_VALUES_MASK) !=
- (c->atr & TXT_ATTR_ON_VALUES_MASK)))) {
- /* Record just the control flags we might need to turn off... */
- lastatr = c->atr & TXT_ATTR_ON_MASK;
- /* ...but set including the values for colour attributes */
- settextattributes(c->atr & TXT_ATTR_ON_VALUES_MASK);
- }
+ treplaceattrs(c->atr);
+ applytextattributes(0);
#ifdef MULTIBYTE_SUPPORT
if (c->atr & TXT_MULTIWORD_MASK) {
@@ -664,35 +642,15 @@ zwcputc(const REFRESH_ELEMENT *c, zattr *curatrp)
#else
fputc(c->chr, shout);
#endif
-
- /*
- * Always output "off" attributes since we only turn off at
- * the end of a chunk of highlighted text.
- */
- if (c->atr & TXT_ATTR_OFF_MASK) {
- settextattributes(c->atr & TXT_ATTR_OFF_MASK);
- lastatr &= ~((c->atr & TXT_ATTR_OFF_MASK) >> TXT_ATTR_OFF_ON_SHIFT);
- }
- if (curatrp) {
- /*
- * Remember the current attributes: those that are turned
- * on, less those that are turned off again. Include
- * colour attributes here in case the colour changes to
- * another non-default one.
- */
- *curatrp = (c->atr & TXT_ATTR_ON_VALUES_MASK) &
- ~((c->atr & TXT_ATTR_OFF_MASK) >> TXT_ATTR_OFF_ON_SHIFT);
- }
}
static int
zwcwrite(const REFRESH_STRING s, size_t i)
{
size_t j;
- zattr curatr = 0;
for (j = 0; j < i; j++)
- zwcputc(s + j, &curatr);
+ zwcputc(s + j);
return i; /* TODO something better for error indication */
}
@@ -939,29 +897,6 @@ snextline(Rparams rpms)
rpms->sen = rpms->s + winw;
}
-
-/**/
-static void
-settextattributes(zattr atr)
-{
- if (txtchangeisset(atr, TXTNOBOLDFACE))
- tsetcap(TCALLATTRSOFF, 0);
- if (txtchangeisset(atr, TXTNOSTANDOUT))
- tsetcap(TCSTANDOUTEND, 0);
- if (txtchangeisset(atr, TXTNOUNDERLINE))
- tsetcap(TCUNDERLINEEND, 0);
- if (txtchangeisset(atr, TXTBOLDFACE))
- tsetcap(TCBOLDFACEBEG, 0);
- if (txtchangeisset(atr, TXTSTANDOUT))
- tsetcap(TCSTANDOUTBEG, 0);
- if (txtchangeisset(atr, TXTUNDERLINE))
- tsetcap(TCUNDERLINEBEG, 0);
- if (txtchangeisset(atr, TXTFGCOLOUR|TXTNOFGCOLOUR))
- set_colour_attribute(atr, COL_SEQ_FG, 0);
- if (txtchangeisset(atr, TXTBGCOLOUR|TXTNOBGCOLOUR))
- set_colour_attribute(atr, COL_SEQ_BG, 0);
-}
-
#ifdef MULTIBYTE_SUPPORT
/*
* Add a multiword glyph at the screen location base.
@@ -1043,7 +978,6 @@ zrefresh(void)
int tmppos; /* t - tmpline */
int tmpalloced; /* flag to free tmpline when finished */
int remetafy; /* flag that zle line is metafied */
- zattr txtchange; /* attributes set after prompts */
int rprompt_off = 1; /* Offset of rprompt from right of screen */
struct rparams rpms;
#ifdef MULTIBYTE_SUPPORT
@@ -1192,9 +1126,7 @@ zrefresh(void)
#endif
/* we probably should only have explicitly set attributes */
tsetcap(TCALLATTRSOFF, 0);
- tsetcap(TCSTANDOUTEND, 0);
- tsetcap(TCUNDERLINEEND, 0);
- txtattrmask = 0;
+ txtcurrentattrs = txtpendingattrs = txtunknownattrs = 0;
if (trashedzle && !clearflag)
reexpandprompt();
@@ -1218,9 +1150,8 @@ zrefresh(void)
zputs(lpromptbuf, shout);
if (lpromptwof == winw)
zputs("\n", shout); /* works with both hasam and !hasam */
- } else {
- txtchange = pmpt_attr;
- settextattributes(txtchange);
+ /* lpromptbuf includes literal escapes so we need to update for it */
+ txtcurrentattrs = txtpendingattrs = pmpt_attr;
}
if (clearflag) {
zputc(&zr_cr);
@@ -1263,45 +1194,40 @@ zrefresh(void)
rpms.s = nbuf[rpms.ln = 0] + lpromptw;
rpms.sen = *nbuf + winw;
for (t = tmpline, tmppos = 0; tmppos < tmpll; t++, tmppos++) {
- unsigned ireg;
- zattr base_atr_on = default_atr_on, base_atr_off = 0;
- zattr all_atr_on, all_atr_off;
+ zattr base_attr = mixattrs(default_attr, prompt_attr);
+ zattr all_attr;
struct region_highlight *rhp;
+ int layer, nextlayer = 0;
/*
* Calculate attribute based on region.
*/
- for (ireg = 0, rhp = region_highlights;
- ireg < n_region_highlights;
- ireg++, rhp++) {
- int offset;
- if (rhp->flags & ZRH_PREDISPLAY)
- offset = 0; /* include predisplay in start end */
- else
- offset = predisplaylen; /* increment over it */
- if (rhp->start + offset <= tmppos &&
- tmppos < rhp->end + offset) {
- if (rhp->atr & (TXTFGCOLOUR|TXTBGCOLOUR)) {
- /* override colour with later entry */
- base_atr_on = (base_atr_on & ~TXT_ATTR_ON_VALUES_MASK) |
- rhp->atr;
- } else {
- /* no colour set yet */
- base_atr_on |= rhp->atr;
+ do {
+ unsigned ireg;
+ layer = nextlayer;
+ nextlayer = special_layer;
+ for (ireg = 0, rhp = region_highlights;
+ ireg < n_region_highlights;
+ ireg++, rhp++) {
+ if (rhp->layer == layer) {
+ int offset;
+ if (rhp->flags & ZRH_PREDISPLAY)
+ offset = 0; /* include predisplay in start end */
+ else
+ offset = predisplaylen; /* increment over it */
+ if (rhp->start + offset <= tmppos &&
+ tmppos < rhp->end + offset) {
+ base_attr = mixattrs(rhp->atr, base_attr);
+ if (layer > special_layer)
+ all_attr = mixattrs(rhp->atr, all_attr);
+ }
+ } else if (rhp->layer > layer && rhp->layer < nextlayer) {
+ nextlayer = rhp->layer;
}
- if (tmppos == rhp->end + offset - 1 ||
- tmppos == tmpll - 1)
- base_atr_off |= TXT_ATTR_OFF_FROM_ON(rhp->atr);
}
- }
- if (special_atr_on & (TXTFGCOLOUR|TXTBGCOLOUR)) {
- /* keep colours from special attributes */
- all_atr_on = special_atr_on |
- (base_atr_on & ~TXT_ATTR_COLOUR_ON_MASK);
- } else {
- /* keep colours from standard attributes */
- all_atr_on = special_atr_on | base_atr_on;
- }
- all_atr_off = TXT_ATTR_OFF_FROM_ON(all_atr_on);
+ if (special_layer == layer) {
+ all_attr = mixattrs(special_attr, base_attr);
+ }
+ } while (nextlayer > layer);
if (t == scs) /* if cursor is here, remember it */
rpms.nvcs = rpms.s - nbuf[rpms.nvln = rpms.ln];
@@ -1319,10 +1245,9 @@ zrefresh(void)
} else {
do {
rpms.s->chr = ZWC(' ');
- rpms.s->atr = base_atr_on;
+ rpms.s->atr = base_attr;
rpms.s++;
} while ((++t0) & 7);
- rpms.s[-1].atr |= base_atr_off;
}
}
#ifdef MULTIBYTE_SUPPORT
@@ -1341,11 +1266,9 @@ zrefresh(void)
rpms.s->chr = ZWC(' ');
if (!started)
started = 1;
- rpms.s->atr = all_atr_on;
+ rpms.s->atr = all_attr;
rpms.s++;
} while (rpms.s < rpms.sen);
- if (started)
- rpms.s[-1].atr |= all_atr_off;
if (nextline(&rpms, 1))
break;
if (t == scs) {
@@ -1369,15 +1292,11 @@ zrefresh(void)
* occurrence.
*/
rpms.s->chr = ZWC('?');
- rpms.s->atr = all_atr_on | all_atr_off;
+ rpms.s->atr = all_attr;
rpms.s++;
} else {
/* We can fit it without reaching the end of the line. */
- /*
- * As we don't actually output the WEOF, we attach
- * any off attributes to the character itself.
- */
- rpms.s->atr = base_atr_on | base_atr_off;
+ rpms.s->atr = base_attr;
if (ichars > 1) {
/*
* Glyph includes combining characters.
@@ -1393,7 +1312,7 @@ zrefresh(void)
while (--width > 0) {
rpms.s->chr = WEOF;
/* Not used, but be consistent... */
- rpms.s->atr = base_atr_on | base_atr_off;
+ rpms.s->atr = base_attr;
rpms.s++;
}
}
@@ -1410,17 +1329,16 @@ zrefresh(void)
#endif
) { /* other control character */
rpms.s->chr = ZWC('^');
- rpms.s->atr = all_atr_on;
+ rpms.s->atr = all_attr;
rpms.s++;
if (rpms.s == rpms.sen) {
/* text wrapped */
- rpms.s[-1].atr |= all_atr_off;
if (nextline(&rpms, 1))
break;
}
rpms.s->chr = (((unsigned int)*t & ~0x80u) > 31) ?
ZWC('?') : (*t | ZWC('@'));
- rpms.s->atr = all_atr_on | all_atr_off;
+ rpms.s->atr = all_attr;
rpms.s++;
}
#ifdef MULTIBYTE_SUPPORT
@@ -1432,7 +1350,6 @@ zrefresh(void)
char dispchars[11];
char *dispptr = dispchars;
wchar_t wc;
- int started = 0;
#ifdef __STDC_ISO_10646__
if (ZSH_INVALID_WCHAR_TEST(*t)) {
@@ -1449,31 +1366,23 @@ zrefresh(void)
if (mbtowc(&wc, dispptr, 1) == 1 /* paranoia */)
{
rpms.s->chr = wc;
- if (!started)
- started = 1;
- rpms.s->atr = all_atr_on;
+ rpms.s->atr = all_attr;
rpms.s++;
if (rpms.s == rpms.sen) {
/* text wrapped */
- if (started) {
- rpms.s[-1].atr |= all_atr_off;
- started = 0;
- }
if (nextline(&rpms, 1))
break;
}
}
dispptr++;
}
- if (started)
- rpms.s[-1].atr |= all_atr_off;
if (*dispptr) /* nextline said stop processing */
break;
}
#else
else { /* normal character */
rpms.s->chr = *t;
- rpms.s->atr = base_atr_on | base_atr_off;
+ rpms.s->atr = base_attr;
rpms.s++;
}
#endif
@@ -1499,13 +1408,12 @@ zrefresh(void)
if (statusline) {
int outll, outsz;
- zattr all_atr_on, all_atr_off;
+ zattr all_attr;
char *statusdup = ztrdup(statusline);
ZLE_STRING_T outputline =
stringaszleline(statusdup, 0, &outll, &outsz, NULL);
- all_atr_on = special_atr_on;
- all_atr_off = TXT_ATTR_OFF_FROM_ON(all_atr_on);
+ all_attr = special_attr;
rpms.tosln = rpms.ln + 1;
nbuf[rpms.ln][winw + 1] = zr_zr; /* text not wrapped */
@@ -1525,7 +1433,7 @@ zrefresh(void)
}
if (width > rpms.sen - rpms.s) {
rpms.s->chr = ZWC('?');
- rpms.s->atr = all_atr_on | all_atr_off;
+ rpms.s->atr = all_attr;
rpms.s++;
} else {
rpms.s->chr = *u;
@@ -1542,7 +1450,7 @@ zrefresh(void)
#endif
if (ZC_icntrl(*u)) { /* simplified processing in the status line */
rpms.s->chr = ZWC('^');
- rpms.s->atr = all_atr_on;
+ rpms.s->atr = all_attr;
rpms.s++;
if (rpms.s == rpms.sen) {
nbuf[rpms.ln][winw + 1] = zr_nl;/* text wrapped */
@@ -1550,7 +1458,7 @@ zrefresh(void)
}
rpms.s->chr = (((unsigned int)*u & ~0x80u) > 31)
? ZWC('?') : (*u | ZWC('@'));
- rpms.s->atr = all_atr_on | all_atr_off;
+ rpms.s->atr = all_attr;
rpms.s++;
} else {
rpms.s->chr = *u;
@@ -1603,6 +1511,7 @@ zrefresh(void)
}
#endif
ZR_memcpy(rpms.sen, zr_end_ellipsis, ZR_END_ELLIPSIS_SIZE);
+ rpms.sen[1].atr = ellipsis_attr;
#ifdef MULTIBYTE_SUPPORT
/* Extend to the end if we backed off for a wide character */
if (extra_ellipsis) {
@@ -1638,6 +1547,7 @@ zrefresh(void)
}
#endif
ZR_memcpy(rpms.sen, zr_mid_ellipsis1, ZR_MID_ELLIPSIS1_SIZE);
+ rpms.sen[1].atr = ellipsis_attr;
rpms.sen += ZR_MID_ELLIPSIS1_SIZE;
#ifdef MULTIBYTE_SUPPORT
/* Extend if we backed off for a wide character */
@@ -1647,6 +1557,7 @@ zrefresh(void)
}
#endif
ZR_memcpy(rpms.sen, zr_mid_ellipsis2, ZR_MID_ELLIPSIS2_SIZE);
+ rpms.sen[1].atr = prompt_attr;
nbuf[rpms.tosln][winw] = nbuf[rpms.tosln][winw + 1] = zr_zr;
}
@@ -1679,7 +1590,9 @@ zrefresh(void)
t0 = winw - lpromptw;
t0 = t0 > ZR_START_ELLIPSIS_SIZE ? ZR_START_ELLIPSIS_SIZE : t0;
ZR_memcpy(nbuf[0] + lpromptw, zr_start_ellipsis, t0);
+ (*nbuf + lpromptw)->atr = ellipsis_attr;
ZR_memset(nbuf[0] + lpromptw + t0, zr_sp, winw - t0 - lpromptw);
+ (*nbuf + lpromptw + t0)->atr = prompt_attr;
nbuf[0][winw] = nbuf[0][winw + 1] = zr_zr;
}
@@ -1725,9 +1638,9 @@ zrefresh(void)
/* output the right-prompt if appropriate */
if (put_rpmpt && !iln && !oput_rpmpt) {
- zattr attrchange;
-
moveto(0, winw - rprompt_off - rpromptw);
+ treplaceattrs(pmpt_attr);
+ applytextattributes(0);
zputs(rpromptbuf, shout);
if (rprompt_off) {
vcs = winw - rprompt_off;
@@ -1735,39 +1648,7 @@ zrefresh(void)
zputc(&zr_cr);
vcs = 0;
}
- /* reset character attributes to that set by the main prompt */
- txtchange = pmpt_attr;
- /*
- * Keep attributes that have actually changed,
- * which are ones off in rpmpt_attr and on in
- * pmpt_attr, and vice versa.
- */
- attrchange = txtchange &
- (TXT_ATTR_OFF_FROM_ON(rpmpt_attr) |
- TXT_ATTR_ON_FROM_OFF(rpmpt_attr));
- /*
- * Careful in case the colour changed.
- */
- if (txtchangeisset(txtchange, TXTFGCOLOUR) &&
- (!txtchangeisset(rpmpt_attr, TXTFGCOLOUR) ||
- ((txtchange ^ rpmpt_attr) & TXT_ATTR_FG_COL_MASK)))
- {
- attrchange |=
- txtchange & (TXTFGCOLOUR | TXT_ATTR_FG_COL_MASK);
- }
- if (txtchangeisset(txtchange, TXTBGCOLOUR) &&
- (!txtchangeisset(rpmpt_attr, TXTBGCOLOUR) ||
- ((txtchange ^ rpmpt_attr) & TXT_ATTR_BG_COL_MASK)))
- {
- attrchange |=
- txtchange & (TXTBGCOLOUR | TXT_ATTR_BG_COL_MASK);
- }
- /*
- * Now feed these changes into the usual function,
- * if necessary.
- */
- if (attrchange)
- settextattributes(attrchange);
+ txtcurrentattrs = txtpendingattrs = rpmpt_attr;
}
}
@@ -1780,11 +1661,6 @@ individually */
refreshline(iln);
}
-/* reset character attributes */
- if (clearf && postedit) {
- if ((txtchange = pmpt_attr ? pmpt_attr : rpmpt_attr))
- settextattributes(txtchange);
- }
clearf = 0;
oput_rpmpt = put_rpmpt;
@@ -1984,8 +1860,6 @@ refreshline(int ln)
/* 3: main display loop - write out the buffer using whatever tricks we can */
for (;;) {
- zattr now_off;
-
#ifdef MULTIBYTE_SUPPORT
if ((!nl->chr || nl->chr != WEOF) && (!ol->chr || ol->chr != WEOF)) {
#endif
@@ -2087,7 +1961,7 @@ refreshline(int ln)
* deletions, so turn off text attributes.
*/
if (first) {
- clearattributes();
+ cleartextattributes(0);
first = 0;
}
tc_delchars(i);
@@ -2176,13 +2050,8 @@ refreshline(int ln)
break;
do {
#endif
- /*
- * If an attribute was on here but isn't any more,
- * output the sequence to turn it off.
- */
- now_off = ol->atr & ~nl->atr & TXT_ATTR_ON_MASK;
- if (now_off)
- settextattributes(TXT_ATTR_OFF_FROM_ON(now_off));
+ treplaceattrs(nl->atr);
+ applytextattributes(0);
/*
* This is deliberately called if nl->chr is WEOF
@@ -2560,8 +2429,8 @@ singlerefresh(ZLE_STRING_T tmpline, int tmpll, int tmpcs)
for (t0 = 0; t0 < tmpll; t0++) {
unsigned ireg;
- zattr base_atr_on = 0, base_atr_off = 0;
- zattr all_atr_on, all_atr_off;
+ zattr base_attr = 0;
+ zattr all_attr;
struct region_highlight *rhp;
/*
* Calculate attribute based on region.
@@ -2576,38 +2445,28 @@ singlerefresh(ZLE_STRING_T tmpline, int tmpll, int tmpcs)
offset = predisplaylen; /* increment over it */
if (rhp->start + offset <= t0 &&
t0 < rhp->end + offset) {
- if (base_atr_on & (TXTFGCOLOUR|TXTBGCOLOUR)) {
+ if (base_attr & (TXTFGCOLOUR|TXTBGCOLOUR)) {
/* keep colour already set */
- base_atr_on |= rhp->atr & ~TXT_ATTR_COLOUR_ON_MASK;
+ base_attr |= rhp->atr & ~TXT_ATTR_COLOUR_MASK;
} else {
/* no colour set yet */
- base_atr_on |= rhp->atr;
+ base_attr |= rhp->atr;
}
- if (t0 == rhp->end + offset - 1 ||
- t0 == tmpll - 1)
- base_atr_off |= TXT_ATTR_OFF_FROM_ON(rhp->atr);
}
}
- if (special_atr_on & (TXTFGCOLOUR|TXTBGCOLOUR)) {
- /* keep colours from special attributes */
- all_atr_on = special_atr_on |
- (base_atr_on & ~TXT_ATTR_COLOUR_ON_MASK);
- } else {
- /* keep colours from standard attributes */
- all_atr_on = special_atr_on | base_atr_on;
- }
- all_atr_off = TXT_ATTR_OFF_FROM_ON(all_atr_on);
+ all_attr = mixattrs(special_attr, base_attr);
+ if (t0 == tmpcs)
+ nvcs = vp - vbuf;
if (tmpline[t0] == ZWC('\t')) {
for (*vp++ = zr_sp; (vp - vbuf) & 7; )
*vp++ = zr_sp;
- vp[-1].atr |= base_atr_off;
} else if (tmpline[t0] == ZWC('\n')) {
vp->chr = ZWC('\\');
- vp->atr = all_atr_on;
+ vp->atr = all_attr;
vp++;
vp->chr = ZWC('n');
- vp->atr = all_atr_on | all_atr_off;
+ vp->atr = all_attr;
vp++;
#ifdef MULTIBYTE_SUPPORT
} else if (WC_ISPRINT(tmpline[t0]) &&
@@ -2623,7 +2482,7 @@ singlerefresh(ZLE_STRING_T tmpline, int tmpll, int tmpcs)
}
} else
ichars = 1;
- vp->atr = base_atr_on | base_atr_off;
+ vp->atr = base_attr;
if (ichars > 1)
addmultiword(vp, tmpline+t0, ichars);
else
@@ -2631,7 +2490,7 @@ singlerefresh(ZLE_STRING_T tmpline, int tmpll, int tmpcs)
vp++;
while (--width > 0) {
vp->chr = WEOF;
- vp->atr = base_atr_on | base_atr_off;
+ vp->atr = base_attr;
vp++;
}
t0 += ichars - 1;
@@ -2641,14 +2500,14 @@ singlerefresh(ZLE_STRING_T tmpline, int tmpll, int tmpcs)
&& (unsigned)tmpline[t0] <= 0xffU
#endif
) {
- ZLE_INT_T t = tmpline[++t0];
+ ZLE_INT_T t = tmpline[t0];
vp->chr = ZWC('^');
- vp->atr = all_atr_on;
+ vp->atr = all_attr;
vp++;
vp->chr = (((unsigned int)t & ~0x80u) > 31) ?
ZWC('?') : (t | ZWC('@'));
- vp->atr = all_atr_on | all_atr_off;
+ vp->atr = all_attr;
vp++;
}
#ifdef MULTIBYTE_SUPPORT
@@ -2656,7 +2515,6 @@ singlerefresh(ZLE_STRING_T tmpline, int tmpll, int tmpcs)
char dispchars[11];
char *dispptr = dispchars;
wchar_t wc;
- int started = 0;
if ((unsigned)tmpline[t0] > 0xffffU) {
sprintf(dispchars, "<%.08x>", (unsigned)tmpline[t0]);
@@ -2666,25 +2524,19 @@ singlerefresh(ZLE_STRING_T tmpline, int tmpll, int tmpcs)
while (*dispptr) {
if (mbtowc(&wc, dispptr, 1) == 1 /* paranoia */) {
vp->chr = wc;
- if (!started)
- started = 1;
- vp->atr = all_atr_on;
+ vp->atr = all_attr;
vp++;
}
dispptr++;
}
- if (started)
- vp[-1].atr |= all_atr_off;
}
#else
else {
vp->chr = tmpline[t0];
- vp->atr = base_atr_on | base_atr_off;
+ vp->atr = base_attr;
vp++;
}
#endif
- if (t0 == tmpcs)
- nvcs = vp - vbuf - 1;
}
if (t0 == tmpcs)
nvcs = vp - vbuf;
@@ -2699,11 +2551,11 @@ singlerefresh(ZLE_STRING_T tmpline, int tmpll, int tmpcs)
}
if (winpos) {
vbuf[winpos].chr = ZWC('<'); /* line continues to the left */
- vbuf[winpos].atr = 0;
+ vbuf[winpos].atr = ellipsis_attr;
}
if ((int)ZR_strlen(vbuf + winpos) > (winw - hasam)) {
vbuf[winpos + winw - hasam - 1].chr = ZWC('>'); /* line continues to right */
- vbuf[winpos + winw - hasam - 1].atr = 0;
+ vbuf[winpos + winw - hasam - 1].atr = ellipsis_attr;
vbuf[winpos + winw - hasam] = zr_zr;
}
ZR_strcpy(nbuf[0], vbuf + winpos);
diff --git a/Src/Zle/zle_thingy.c b/Src/Zle/zle_thingy.c
index cd3f2c356..f71435b01 100644
--- a/Src/Zle/zle_thingy.c
+++ b/Src/Zle/zle_thingy.c
@@ -344,7 +344,7 @@ bin_zle(char *name, char **args, Options ops, UNUSED(int func))
{
static struct opn {
char o;
- int (*func) _((char *, char **, Options, char));
+ int (*func) (char *, char **, Options, char);
int min, max;
} const opns[] = {
{ 'l', bin_zle_list, 0, -1 },
@@ -366,10 +366,10 @@ bin_zle(char *name, char **args, Options ops, UNUSED(int func))
int n;
/* select operation and ensure no clashing arguments */
- for(op = opns; op->o && !OPT_ISSET(ops,STOUC(op->o)); op++) ;
+ for(op = opns; op->o && !OPT_ISSET(ops, (unsigned char) op->o); op++) ;
if(op->o)
for(opp = op; (++opp)->o; )
- if(OPT_ISSET(ops,STOUC(opp->o))) {
+ if(OPT_ISSET(ops, (unsigned char) opp->o)) {
zwarnnam(name, "incompatible operation selection options");
return 1;
}
diff --git a/Src/Zle/zle_tricky.c b/Src/Zle/zle_tricky.c
index fdd168763..aa3c71bc2 100644
--- a/Src/Zle/zle_tricky.c
+++ b/Src/Zle/zle_tricky.c
@@ -576,7 +576,7 @@ parambeg(char *s)
while (idigit(*e))
e++;
else
- e = itype_end(e, IIDENT, 0);
+ e = itype_end(e, INAMESPC, 0);
/* Now make sure that the cursor is inside the name. */
if (offs <= e - s && offs >= b - s && n <= 0) {
@@ -765,7 +765,7 @@ docomplete(int lst)
else if (idigit(*q))
do q++; while (idigit(*q));
else
- q = itype_end(q, IIDENT, 0);
+ q = itype_end(q, INAMESPC, 0);
sav = *q;
*q = '\0';
if (zlemetacs - wb == q - s &&
@@ -1315,6 +1315,8 @@ get_comp_string(void)
ins = (tok == REPEAT ? 2 : (tok != STRING && tok != TYPESET));
zsfree(cmdstr);
cmdstr = ztrdup(tokstr);
+ untokenize(cmdstr);
+ remnulargs(cmdstr);
cmdtok = tok;
/*
* If everything before is a redirection, or anything
@@ -1497,7 +1499,8 @@ get_comp_string(void)
if (varq)
tt = clwords[clwpos];
- s = itype_end(tt, IIDENT, 0);
+ /* The only place we complete namespaces, see IIDENT below */
+ s = itype_end(tt, INAMESPC, 0);
sav = *s;
*s = '\0';
zsfree(varname);
@@ -1568,6 +1571,8 @@ get_comp_string(void)
i = 0;
MB_METACHARINIT();
+ /* All further uses of IIDENT in this file should change to *
+ * INAMESPC if this case is changed. Too ugly to risk now. */
if (itype_end(s, IIDENT, 1) == s)
nnb = s + MB_METACHARLEN(s);
else
@@ -1641,7 +1646,7 @@ get_comp_string(void)
} else {
/* In mathematical expression, we complete parameter names *
* (even if they don't have a `$' in front of them). So we *
- * have to find that name. */
+ * have to find that name. See above regarding INAMESPC */
char *cspos = zlemetaline + zlemetacs, *wptr, *cptr;
we = itype_end(cspos, IIDENT, 0) - zlemetaline;
@@ -2426,7 +2431,7 @@ mod_export int
printfmt(char *fmt, int n, int dopr, int doesc)
{
char *p = fmt, nc[DIGBUFSIZE];
- int l = 0, cc = 0, b = 0, s = 0, u = 0, m;
+ int l = 0, cc = 0;
MB_METACHARINIT();
for (; *p; ) {
@@ -2437,48 +2442,45 @@ printfmt(char *fmt, int n, int dopr, int doesc)
if (idigit(*++p))
arg = zstrtol(p, &p, 10);
if (*p) {
- m = 0;
switch (*p) {
case '%':
- if (dopr)
+ if (dopr) {
+ applytextattributes(0);
putc('%', shout);
+ }
cc++;
break;
case 'n':
sprintf(nc, "%d", n);
- if (dopr)
+ if (dopr) {
+ applytextattributes(0);
fputs(nc, shout);
+ }
cc += MB_METASTRWIDTH(nc);
break;
case 'B':
- b = 1;
if (dopr)
- tcout(TCBOLDFACEBEG);
+ tsetattrs(TXTBOLDFACE);
break;
case 'b':
- b = 0; m = 1;
if (dopr)
- tcout(TCALLATTRSOFF);
+ tunsetattrs(TXTBOLDFACE);
break;
case 'S':
- s = 1;
if (dopr)
- tcout(TCSTANDOUTBEG);
+ tsetattrs(TXTSTANDOUT);
break;
case 's':
- s = 0; m = 1;
if (dopr)
- tcout(TCSTANDOUTEND);
+ tunsetattrs(TXTSTANDOUT);
break;
case 'U':
- u = 1;
if (dopr)
- tcout(TCUNDERLINEBEG);
+ tsetattrs(TXTUNDERLINE);
break;
case 'u':
- u = 0; m = 1;
if (dopr)
- tcout(TCUNDERLINEEND);
+ tunsetattrs(TXTUNDERLINE);
break;
case 'F':
case 'K':
@@ -2491,18 +2493,27 @@ printfmt(char *fmt, int n, int dopr, int doesc)
} else
atr = match_colour(NULL, is_fg, arg);
if (atr != TXT_ERROR)
- set_colour_attribute(atr, is_fg ? COL_SEQ_FG :
- COL_SEQ_BG, 0);
+ tsetattrs(atr);
break;
case 'f':
- set_colour_attribute(TXTNOFGCOLOUR, COL_SEQ_FG, 0);
+ tunsetattrs(TXTFGCOLOUR);
break;
case 'k':
- set_colour_attribute(TXTNOBGCOLOUR, COL_SEQ_BG, 0);
+ tunsetattrs(TXTBGCOLOUR);
+ break;
+ case 'H':
+ if (p[1] == '{') {
+ p = parsehighlight(p + 2, '}', &atr);
+ --p;
+ if (atr != TXT_ERROR)
+ treplaceattrs(atr);
+ }
break;
case '{':
if (arg)
cc += arg;
+ if (dopr)
+ applytextattributes(0);
for (p++; *p && (*p != '%' || p[1] != '}'); p++) {
if (*p == Meta) {
p++;
@@ -2518,14 +2529,6 @@ printfmt(char *fmt, int n, int dopr, int doesc)
p--;
break;
}
- if (dopr && m) {
- if (b)
- tcout(TCBOLDFACEBEG);
- if (s)
- tcout(TCSTANDOUTBEG);
- if (u)
- tcout(TCUNDERLINEBEG);
- }
} else
break;
p++;
@@ -2533,6 +2536,7 @@ printfmt(char *fmt, int n, int dopr, int doesc)
if (*p == '\n') {
cc++;
if (dopr) {
+ applytextattributes(0);
if (tccan(TCCLEAREOL))
tcout(TCCLEAREOL);
else {
@@ -2551,6 +2555,7 @@ printfmt(char *fmt, int n, int dopr, int doesc)
convchar_t cchar;
int clen = MB_METACHARLENCONV(p, &cchar);
if (dopr) {
+ applytextattributes(0);
while (clen--) {
if (*p == Meta) {
p++;
@@ -2568,6 +2573,8 @@ printfmt(char *fmt, int n, int dopr, int doesc)
}
}
if (dopr) {
+ treplaceattrs(0);
+ applytextattributes(0);
if (!(cc % zterm_columns))
fputs(" \010", shout);
if (tccan(TCCLEAREOL))
diff --git a/Src/Zle/zle_utils.c b/Src/Zle/zle_utils.c
index 526216fa7..e2b86e863 100644
--- a/Src/Zle/zle_utils.c
+++ b/Src/Zle/zle_utils.c
@@ -512,12 +512,13 @@ stringaszleline(char *instr, int incs, int *outll, int *outsz, int *outcs)
*outcs = outptr - outstr;
*outll = outptr - outstr;
} else {
+ *outstr = ZWC('\0');
*outll = 0;
if (outcs)
*outcs = 0;
}
#else
- memcpy(outstr, instr, ll);
+ strcpy(outstr, instr);
*outll = ll;
if (outcs)
*outcs = incs;
@@ -580,7 +581,7 @@ struct zle_region;
struct zle_region {
struct zle_region *next;
/* Entries of region_highlight, as needed */
- int atr;
+ zattr atr;
int start;
int end;
int flags;
@@ -799,7 +800,7 @@ spaceinline(int ct)
if (rhp->start_meta - sub >= zlemetacs) {
rhp->start_meta += ct;
}
- if (rhp->end_meta - sub >= zlemetacs) {
+ if (rhp->end_meta - sub >= zlemetacs && (!predisplaylen || zlemetacs)) {
rhp->end_meta += ct;
}
}
@@ -827,7 +828,7 @@ spaceinline(int ct)
if (rhp->start - sub >= zlecs) {
rhp->start += ct;
}
- if (rhp->end - sub >= zlecs) {
+ if (rhp->end - sub >= zlecs && (!predisplaylen || zlecs)) {
rhp->end += ct;
}
}
@@ -866,13 +867,13 @@ shiftchars(int to, int cnt)
if (rhp->start_meta - sub > to + cnt)
rhp->start_meta -= cnt;
else
- rhp->start_meta = to;
+ rhp->start_meta = to + sub;
}
if (rhp->end_meta - sub > to) {
if (rhp->end_meta - sub > to + cnt)
rhp->end_meta -= cnt;
else
- rhp->end_meta = to;
+ rhp->end_meta = to + sub;
}
}
}
@@ -896,13 +897,13 @@ shiftchars(int to, int cnt)
if (rhp->start - sub > to + cnt)
rhp->start -= cnt;
else
- rhp->start = to;
+ rhp->start = to + sub;
}
if (rhp->end - sub > to) {
if (rhp->end - sub > to + cnt)
rhp->end -= cnt;
else
- rhp->end = to;
+ rhp->end = to + sub;
}
}
}
@@ -936,6 +937,28 @@ cut(int i, int ct, int flags)
cuttext(zleline + i, ct, flags);
}
+static char*
+base64_encode(const char *src, size_t len) {
+ static const char* base64_table =
+ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
+
+ const unsigned char *end = (unsigned char *)src + len;
+ const unsigned char *in = (unsigned char *)src;
+ char *ret = zhalloc(1 + 4 * ((len + 2) / 3)); /* 4 bytes out for 3 in */
+ char *cur = ret;
+
+ for (; end - in > 0; in += 3, cur += 4) {
+ unsigned int n = *in << 16;
+ cur[3] = end - in > 2 ? base64_table[(n |= in[2]) & 0x3f] : '=';
+ cur[2] = end - in > 1 ? base64_table[((n |= in[1]<<8) >> 6) & 0x3f] : '=';
+ cur[1] = base64_table[(n >> 12) & 0x3f];
+ cur[0] = base64_table[n >> 18];
+ }
+ *cur = '\0';
+
+ return ret;
+}
+
/*
* As cut, but explicitly supply the text together with its length.
*/
@@ -948,7 +971,15 @@ cuttext(ZLE_STRING_T line, int ct, int flags)
return;
UNMETACHECK();
- if (zmod.flags & MOD_VIBUF) {
+ if (zmod.flags & MOD_OSSEL) {
+ int cutll;
+ char *mbcut = zlelineasstring(line, ct, 0, &cutll, NULL, 1);
+ unmetafy(mbcut, &cutll);
+ mbcut = base64_encode(mbcut, cutll);
+
+ fprintf(shout, "\033]52;%c;%s\a", zmod.flags & MOD_CLIP ? 'c' : 'p',
+ mbcut);
+ } else if (zmod.flags & MOD_VIBUF) {
struct cutbuffer *b = &vibuf[zmod.vibuf];
if (!(zmod.flags & MOD_VIAPP) || !b->buf) {
@@ -1220,7 +1251,7 @@ getzlequery(void)
REFRESH_ELEMENT re;
re.chr = c;
re.atr = 0;
- zwcputc(&re, NULL);
+ zwcputc(&re);
}
return c == ZWC('y');
}
@@ -1235,7 +1266,7 @@ bindztrdup(char *str)
char *buf, *ptr, *ret;
for(ptr = str; *ptr; ptr++) {
- c = *ptr == Meta ? STOUC(*++ptr) ^ 32 : STOUC(*ptr);
+ c = *ptr == Meta ? (unsigned char) *++ptr ^ 32 : (unsigned char) *ptr;
if(c & 0x80) {
len += 3;
c &= 0x7f;
@@ -1249,7 +1280,7 @@ bindztrdup(char *str)
}
ptr = buf = zalloc(len);
for(; *str; str++) {
- c = *str == Meta ? STOUC(*++str) ^ 32 : STOUC(*str);
+ c = *str == Meta ? (unsigned char) *++str ^ 32 : (unsigned char) *str;
if(c & 0x80) {
*ptr++ = '\\';
*ptr++ = 'M';
diff --git a/Src/Zle/zle_vi.c b/Src/Zle/zle_vi.c
index 0f198d0e8..6692df830 100644
--- a/Src/Zle/zle_vi.c
+++ b/Src/Zle/zle_vi.c
@@ -1014,6 +1014,9 @@ int
visetbuffer(char **args)
{
ZLE_INT_T ch;
+ const ZLE_CHAR_T *match = ZWS("_*+");
+ int registermod[] = { MOD_NULL, MOD_PRI, MOD_CLIP };
+ ZLE_CHAR_T *found;
if (*args) {
ch = **args;
@@ -1022,12 +1025,12 @@ visetbuffer(char **args)
} else {
ch = getfullchar(0);
}
- if (ch == ZWC('_')) {
- zmod.flags |= MOD_NULL;
+ if ((found = ZS_strchr(match, ch))) {
+ zmod.flags |= registermod[found - match];
prefixflag = 1;
return 0;
} else
- zmod.flags &= ~MOD_NULL;
+ zmod.flags &= ~(MOD_NULL | MOD_OSSEL);
if ((ch < ZWC('0') || ch > ZWC('9')) &&
(ch < ZWC('a') || ch > ZWC('z')) &&
(ch < ZWC('A') || ch > ZWC('Z')))