summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog10
-rw-r--r--Doc/Zsh/compwid.yo5
-rw-r--r--Doc/Zsh/params.yo43
-rw-r--r--NEWS4
-rw-r--r--Src/Zle/compresult.c8
-rw-r--r--Src/Zle/zle.h4
-rw-r--r--Src/Zle/zle_misc.c65
7 files changed, 120 insertions, 19 deletions
diff --git a/ChangeLog b/ChangeLog
index b2ca7ab76..39bbffbb1 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,11 @@
+2009-04-24 Peter Stephenson <pws@csr.com>
+
+ * 26876 (documentation slightly modified): NEWS, Doc/Zsh/compwid.yo,
+ Doc/Zsh/params.yo, Src/Zle/compresult.c, Src/Zle/zle.h,
+ Src/Zle/zle_misc.c: add ZLE_REMOVE_SUFFIX_CHARS and
+ ZLE_SPACE_SUFFIX_CHARS to make actions for suffix removals when
+ not controlled by completion system more configurable.
+
2009-04-23 Clint Adams <clint@zsh.org>
* 26877, 26879: Completion/Debian/Command/_apt: handle apt-get
@@ -11608,5 +11616,5 @@
*****************************************************
* This is used by the shell to define $ZSH_PATCHLEVEL
-* $Revision: 1.4665 $
+* $Revision: 1.4666 $
*****************************************************
diff --git a/Doc/Zsh/compwid.yo b/Doc/Zsh/compwid.yo
index 80427330d..b8786dd26 100644
--- a/Doc/Zsh/compwid.yo
+++ b/Doc/Zsh/compwid.yo
@@ -58,6 +58,11 @@ endmenu()
texinode(Completion Special Parameters)(Completion Builtin Commands)()(Completion Widgets)
sect(Completion Special Parameters)
+The parameters tt(ZLE_REMOVE_SUFFIX_CHARS) and tt(ZLE_SPACE_SUFFIX_CHARS)
+are used by the completion mechanism, but are not special.
+ifzman(See em(Parameters Used By The Shell) in zmanref(zshparam))\
+ifnzman(noderef(Parameters Used By The Shell)).
+
Inside completion widgets, and any functions called from them, some
parameters have special meaning; outside these functions they are not
special to the shell in any way. These parameters are used to pass
diff --git a/Doc/Zsh/params.yo b/Doc/Zsh/params.yo
index 7a8efdd94..e36becf53 100644
--- a/Doc/Zsh/params.yo
+++ b/Doc/Zsh/params.yo
@@ -1330,4 +1330,47 @@ item(tt(ZDOTDIR))(
The directory to search for shell startup files (.zshrc, etc),
if not tt($HOME).
)
+vindex(ZLE_REMOVE_SUFFIX_CHARS)
+vindex(ZLE_SPACE_SUFFIX_CHARS)
+xitem(tt(ZLE_REMOVE_SUFFIX_CHARS))
+item(tt(ZLE_SPACE_SUFFIX_CHARS))(
+These parameters are used by the line editor. In certain circumstances
+suffixes (typically space or slash) added by the completion system
+will be removed automatically, either because the next editing command
+was not an insertable character, or because the character was marked
+as requiring the suffix to be removed.
+
+These variables can contain the sets of characters that will cause the
+suffix to be removed. If tt(ZLE_REMOVE_SUFFIX_CHARS) is set, those
+characters will cause the suffix to be removed; if
+tt(ZLE_SPACE_SUFFIX_CHARS) is set, those characters will cause the
+suffix to be removed and replaced by a space.
+
+If tt(ZLE_REMOVE_SUFFIX_CHARS) is not set, the default behaviour is
+equivalent to:
+
+example(ZLE_REMOVE_SUFFIX_CHARS=$' \t\n;&|')
+
+If tt(ZLE_REMOVE_SUFFIX_CHARS) is set but is empty, no characters have this
+behaviour. tt(ZLE_SPACE_SUFFIX_CHARS) takes precedence, so that the
+following:
+
+example(ZLE_SPACE_SUFFIX_CHARS=$'&|')
+
+causes the characters `tt(&)' and `tt(|)' to remove the suffix but to
+replace it with a space.
+
+To illustrate the difference, suppose that the option tt(AUTO_REMOVE_SLASH)
+is in effect and the directory tt(DIR) has just been completed, with an
+appended tt(/), following which the user types `tt(&)'. The default result
+is `tt(DIR&)'. With tt(ZLE_REMOVE_SUFFIX_CHARS) set but without including
+`tt(&)' the result is `tt(DIR/&)'. With tt(ZLE_SPACE_SUFFIX_CHARS) set to
+include `tt(&)' the result is `tt(DIR &)'.
+
+Note that certain completions may provide their own suffix removal
+or replacement behaviour which overrides the values described here.
+See the completion system documentation in
+ifzman(zmanref(zshcompsys))\
+ifnzman(noderef(Completion System)).
+)
enditem()
diff --git a/NEWS b/NEWS
index e103840ee..b26617a60 100644
--- a/NEWS
+++ b/NEWS
@@ -20,6 +20,10 @@ shells.
The variable ZSH_PATCHLEVEL can be used to test for unreleased versions of
the shell; it is present but less useful in released versions.
+The variables ZLE_REMOVE_SUFFIX_CHARS and ZLE_SPACE_SUFFIX_CHARS allow more
+control over the way automatically removed suffixes are treated in
+completion.
+
Major changes between versions 4.3.6 and 4.3.9
----------------------------------------------
diff --git a/Src/Zle/compresult.c b/Src/Zle/compresult.c
index e595802dd..43733b0c6 100644
--- a/Src/Zle/compresult.c
+++ b/Src/Zle/compresult.c
@@ -1011,7 +1011,7 @@ do_single(Cmatch m)
stringaszleline(m->suf, 0, &len, NULL, NULL);
makesuffixstr(m->remf, m->rems, len);
if (len == 1)
- addsuffix(SUFTYP_POSSTR, wsuf, 1, 1);
+ addsuffix(SUFTYP_POSSTR, 0, wsuf, 1, 1);
free(wsuf);
}
}
@@ -1104,7 +1104,7 @@ do_single(Cmatch m)
makesuffixstr(m->remf, m->rems, 1);
else if (isset(AUTOREMOVESLASH)) {
makesuffix(1);
- addsuffix(SUFTYP_POSSTR, ZWS("/"), 1, 1);
+ addsuffix(SUFTYP_POSSTR, 0, ZWS("/"), 1, 1);
}
}
}
@@ -1119,7 +1119,7 @@ do_single(Cmatch m)
/* If a suffix was added, and is removable, let *
* `,' and `}' remove it. */
if (isset(AUTOPARAMKEYS))
- addsuffix(SUFTYP_POSSTR, ZWS(",}"), 2, suffixnoinslen);
+ addsuffix(SUFTYP_POSSTR, 0, ZWS(",}"), 2, suffixnoinslen);
} else if (!menucmp) {
/*{{*/
/* Otherwise, add a `,' suffix, and let `}' remove it. */
@@ -1129,7 +1129,7 @@ do_single(Cmatch m)
minfo.insc++;
makesuffix(1);
if ((!menucmp || minfo.we) && isset(AUTOPARAMKEYS))
- addsuffix(SUFTYP_POSSTR, ZWS(",}"), 2, 1);
+ addsuffix(SUFTYP_POSSTR, 0, ZWS(",}"), 2, 1);
}
} else if (!havesuff && (!(m->flags & CMF_FILE) || !sr)) {
/* If we didn't add a suffix, add a space, unless we are *
diff --git a/Src/Zle/zle.h b/Src/Zle/zle.h
index 1fd6d87a2..577a4442f 100644
--- a/Src/Zle/zle.h
+++ b/Src/Zle/zle.h
@@ -380,6 +380,10 @@ enum suffixtype {
SUFTYP_NEGRNG /* Range of characters not to match */
};
+/* Additional flags to suffixes */
+enum suffixflags {
+ SUFFLAGS_SPACE = 0x0001 /* Add a space when removing suffix */
+};
#ifdef MULTIBYTE_SUPPORT
/*
diff --git a/Src/Zle/zle_misc.c b/Src/Zle/zle_misc.c
index 961776f43..0beb43d6d 100644
--- a/Src/Zle/zle_misc.c
+++ b/Src/Zle/zle_misc.c
@@ -1232,6 +1232,7 @@ struct suffixset;
struct suffixset {
struct suffixset *next; /* Next in the list */
int tp; /* The SUFTYP_* from enum suffixtype */
+ int flags; /* Some of SUFFLAGS_* */
ZLE_STRING_T chars; /* Set of characters to match (or not) */
int lenstr; /* Length of chars */
int lensuf; /* Length of suffix */
@@ -1255,13 +1256,14 @@ suffixnoinslen;
/**/
mod_export void
-addsuffix(int tp, ZLE_STRING_T chars, int lenstr, int lensuf)
+addsuffix(int tp, int flags, ZLE_STRING_T chars, int lenstr, int lensuf)
{
struct suffixset *newsuf = zalloc(sizeof(struct suffixset));
newsuf->next = suffixlist;
suffixlist = newsuf;
newsuf->tp = tp;
+ newsuf->flags = flags;
if (lenstr) {
newsuf->chars = zalloc(lenstr*sizeof(ZLE_CHAR_T));
ZS_memcpy(newsuf->chars, chars, lenstr);
@@ -1271,6 +1273,24 @@ addsuffix(int tp, ZLE_STRING_T chars, int lenstr, int lensuf)
newsuf->lensuf = lensuf;
}
+
+/* Same as addsuffix, but from metafied string */
+
+/**/
+mod_export void
+addsuffixstring(int tp, int flags, char *chars, int lensuf)
+{
+ int slen, alloclen;
+ ZLE_STRING_T suffixstr;
+
+ /* string needs to be writable... I've been regretting this for years.. */
+ chars = ztrdup(chars);
+ suffixstr = stringaszleline(chars, 0, &slen, &alloclen, NULL);
+ addsuffix(tp, flags, suffixstr, slen, lensuf);
+ zfree(suffixstr, alloclen);
+ zsfree(chars);
+}
+
/* Set up suffix: the last n characters are a suffix that should be *
* removed in the usual word end conditions. */
@@ -1278,7 +1298,17 @@ addsuffix(int tp, ZLE_STRING_T chars, int lenstr, int lensuf)
mod_export void
makesuffix(int n)
{
- addsuffix(SUFTYP_POSSTR, ZWS(" \t\n;&|"), 6, n);
+ char *suffixchars;
+
+ if (!(suffixchars = getsparam("ZLE_REMOVE_SUFFIX_CHARS")))
+ suffixchars = " \t\n;&|";
+
+ addsuffixstring(SUFTYP_POSSTR, 0, suffixchars, n);
+
+ /* Do this second so it takes precedence */
+ if ((suffixchars = getsparam("ZLE_SPACE_SUFFIX_CHARS")) && *suffixchars)
+ addsuffixstring(SUFTYP_POSSTR, SUFFLAGS_SPACE, suffixchars, n);
+
suffixnoinslen = n;
}
@@ -1301,7 +1331,7 @@ makeparamsuffix(int br, int n)
lenstr += 6;
}
if (lenstr)
- addsuffix(SUFTYP_POSSTR, charstr, lenstr, n);
+ addsuffix(SUFTYP_POSSTR, 0, charstr, lenstr, n);
}
/* Set up suffix given a string containing the characters on which to *
@@ -1344,11 +1374,11 @@ makesuffixstr(char *f, char *s, int n)
ZLE_CHAR_T str[2];
if (wptr > lasts)
- addsuffix(inv ? SUFTYP_NEGSTR : SUFTYP_POSSTR,
+ addsuffix(inv ? SUFTYP_NEGSTR : SUFTYP_POSSTR, 0,
lasts, wptr - lasts, n);
str[0] = *wptr;
str[1] = wptr[2];
- addsuffix(inv ? SUFTYP_NEGRNG : SUFTYP_POSRNG,
+ addsuffix(inv ? SUFTYP_NEGRNG : SUFTYP_POSRNG, 0,
str, 2, n);
wptr += 3;
@@ -1360,7 +1390,7 @@ makesuffixstr(char *f, char *s, int n)
}
}
if (wptr > lasts)
- addsuffix(inv ? SUFTYP_NEGSTR : SUFTYP_POSSTR,
+ addsuffix(inv ? SUFTYP_NEGSTR : SUFTYP_POSSTR, 0,
lasts, wptr - lasts, n);
free(ws);
} else
@@ -1410,7 +1440,7 @@ iremovesuffix(ZLE_INT_T c, int keep)
zsfree(suffixfunc);
suffixfunc = NULL;
} else {
- int sl = 0;
+ int sl = 0, flags = 0;
struct suffixset *ss;
if (c == NO_INSERT_CHAR) {
@@ -1463,8 +1493,10 @@ iremovesuffix(ZLE_INT_T c, int keep)
}
break;
}
- if (found)
+ if (found) {
+ flags = ss->flags;
break;
+ }
}
if (!found)
@@ -1472,12 +1504,17 @@ iremovesuffix(ZLE_INT_T c, int keep)
}
if (sl) {
/* must be shifting wide character lengths */
- if (zlemetaline != NULL) {
- unmetafy_line();
- backdel(sl, CUT_RAW);
- metafy_line();
- } else
- backdel(sl, CUT_RAW);
+ backdel(sl, CUT_RAW);
+ if (flags & SUFFLAGS_SPACE)
+ {
+ /* Add a space and advance over it */
+ spaceinline(1);
+ if (zlemetaline) {
+ zlemetaline[zlemetacs++] = ' ';
+ } else {
+ zleline[zlecs++] = ZWC(' ');
+ }
+ }
if (!keep)
invalidatelist();
}