From 64d431d98b022d186aa088a295d723b2ec727b84 Mon Sep 17 00:00:00 2001 From: Peter Stephenson Date: Fri, 11 Jun 2010 20:08:01 +0000 Subject: 28025: (D) parameter flag --- ChangeLog | 7 ++++++- Doc/Zsh/expn.yo | 28 +++++++++++++++++++--------- Src/subst.c | 34 +++++++++++++++++++++++----------- Src/utils.c | 17 +++++++++++++++++ 4 files changed, 65 insertions(+), 21 deletions(-) diff --git a/ChangeLog b/ChangeLog index 080d5ca6d..03a69a846 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,8 @@ +2010-06-11 Peter Stephenson + + * 28025: Doc/Zsh/expn.yo, Src/subst.c, Src/utils.c: (D) + parameter flag to abbreviate directories. + 2010-06-09 Peter Stephenson * Haakon Riiser: 28009: Completion/Unix/Command/_ffmpeg: new. @@ -13267,5 +13272,5 @@ ***************************************************** * This is used by the shell to define $ZSH_PATCHLEVEL -* $Revision: 1.4997 $ +* $Revision: 1.4998 $ ***************************************************** diff --git a/Doc/Zsh/expn.yo b/Doc/Zsh/expn.yo index 2641fd61f..83a195def 100644 --- a/Doc/Zsh/expn.yo +++ b/Doc/Zsh/expn.yo @@ -771,6 +771,13 @@ Capitalize the resulting words. `Words' in this case refers to sequences of alphanumeric characters separated by non-alphanumerics, em(not) to words that result from field splitting. ) +item(tt(D))( +Assume the string or array elements contain directories and attempt +to substitute the leading part of these by names. This is the reverse +of `tt(~)' substitution: see +ifnzman(noderef(Filename Expansion))\ +ifzman(the section FILENAME EXPANSION below). +) item(tt(e))( Perform em(parameter expansion), em(command substitution) and em(arithmetic expansion) on the result. Such expansions can be @@ -1199,40 +1206,43 @@ item(tt(13.) em(Quote application))( Any quoting or unquoting using tt((q)) and tt((Q)) and related flags is applied. ) -item(tt(14.) em(Visibility enhancment))( +item(tt(14.) em(Directory naming))( +Any directory name substitution using tt((D)) flag is applied. +) +item(tt(15.) em(Visibility enhancment))( Any modifications to make characters visible using the tt((V)) flag are applied. ) -item(tt(15.) em(Forced Splitting))( +item(tt(16.) em(Forced Splitting))( If one of the `tt((s))', `tt((f))' or `tt((z))' flags are present, or the `tt(=)' specifier was present (e.g. tt(${=)var(var)tt(})), the word is split on occurrences of the specified string, or (for tt(=) with neither of the two flags present) any of the characters in tt($IFS). ) -item(tt(16.) em(Shell Word Splitting))( +item(tt(17.) em(Shell Word Splitting))( If no `tt((s))', `tt((f))' or `tt(=)' was given, but the word is not quoted and the option tt(SH_WORD_SPLIT) is set, the word is split on occurrences of any of the characters in tt($IFS). Note this step, too, takes place at all levels of a nested substitution. ) -item(tt(17.) em(Uniqueness))( +item(tt(18.) em(Uniqueness))( If the result is an array and the `tt((u))' flag was present, duplicate elements are removed from the array. ) -item(tt(18.) em(Ordering))( +item(tt(19.) em(Ordering))( If the result is still an array and one of the `tt((o))' or `tt((O))' flags was present, the array is reordered. ) -item(tt(19.) em(Re-Evaluation))( +item(tt(20.) em(Re-Evaluation))( Any `tt((e))' flag is applied to the value, forcing it to be re-examined for new parameter substitutions, but also for command and arithmetic substitutions. ) -item(tt(20.) em(Padding))( +item(tt(21.) em(Padding))( Any padding of the value by the `tt(LPAR()l.)var(fill)tt(.RPAR())' or `tt(LPAR()r.)var(fill)tt(.RPAR())' flags is applied. ) -item(tt(21.) em(Semantic Joining))( +item(tt(22.) em(Semantic Joining))( In contexts where expansion semantics requires a single word to result, all words are rejoined with the first character of tt(IFS) between. So in `tt(${LPAR()P)tt(RPAR()${LPAR()f)tt(RPAR()lines}})' @@ -1241,7 +1251,7 @@ joined again before the tt(P) flag can be applied. If a single word is not required, this rule is skipped. ) -item(tt(22.) em(Empty argument removal))( +item(tt(23.) em(Empty argument removal))( If the substitution does not appear in double quotes, any resulting zero-length argument, whether from a scalar or an element of an array, is elided from the list of arguments inserted into the command line. diff --git a/Src/subst.c b/Src/subst.c index 304add6f9..2543c7cce 100644 --- a/Src/subst.c +++ b/Src/subst.c @@ -1459,14 +1459,16 @@ paramsubst(LinkList l, LinkNode n, char **str, int qt, int ssub) */ int quotemod = 0, quotetype = QT_NONE, quoteerr = 0; /* - * (V) flag: fairly straightforward, except that as with so - * many flags it's not easy to decide where to put it in the order. + * Various fairly straightforward modifications, except that as with so + * many flags it's not easy to decide where to put them in the order. + * bit 0: (D) flag. + * bit 1: (V) flag. */ - int visiblemod = 0; + int mods = 0; /* * The (z) flag, nothing to do with SH_WORD_SPLIT which is tied * spbreak, see above; fairly straighforward in use but c.f. - * the comment for visiblemod. + * the comment for mods. */ int shsplit = 0; /* @@ -1514,7 +1516,7 @@ paramsubst(LinkList l, LinkNode n, char **str, int qt, int ssub) */ int aspar = 0; /* - * The (%) flag, c.f. visiblemod again. + * The (%) flag, c.f. mods again. */ int presc = 0; /* @@ -1678,8 +1680,11 @@ paramsubst(LinkList l, LinkNode n, char **str, int qt, int ssub) indord = 1; break; + case 'D': + mods |= 1; + break; case 'V': - visiblemod++; + mods |= 2; break; case 'q': @@ -2954,19 +2959,26 @@ paramsubst(LinkList l, LinkNode n, char **str, int qt, int ssub) } /* * Transform special characters in the string to make them - * printable. + * printable, or to show directories, or possibly even both. */ - if (visiblemod) { + if (mods) { if (isarr) { char **ap; if (!copied) aval = arrdup(aval), copied = 1; - for (ap = aval; *ap; ap++) - *ap = nicedupstring(*ap); + for (ap = aval; *ap; ap++) { + if (mods & 1) + *ap = substnamedir(*ap); + if (mods & 2) + *ap = nicedupstring(*ap); + } } else { if (!copied) val = dupstring(val), copied = 1; - val = nicedupstring(val); + if (mods & 1) + val = substnamedir(val); + if (mods & 2) + val = nicedupstring(val); } } /* diff --git a/Src/utils.c b/Src/utils.c index 184b2f354..379f9f738 100644 --- a/Src/utils.c +++ b/Src/utils.c @@ -766,6 +766,23 @@ fprintdir(char *s, FILE *f) } } +/* + * Substitute a directory using a name. + * If there is none, return the original argument. + */ + +/**/ +char * +substnamedir(char *s) +{ + Nameddir d = finddir(s); + + if (!d) + return s; + return zhtricat("~", d->node.nam, s + strlen(d->dir)); +} + + /* Returns the current username. It caches the username * * and uid to try to avoid requerying the password files * * or NIS/NIS+ database. */ -- cgit 1.4.1