Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/bin/sh Add the "specialvar" built-in command. Discussed (w...



details:   https://anonhg.NetBSD.org/src/rev/d1f431ade870
branches:  trunk
changeset: 448934:d1f431ade870
user:      kre <kre%NetBSD.org@localhost>
date:      Thu Feb 14 11:15:24 2019 +0000

description:
Add the "specialvar" built-in command.   Discussed (well, mentioned
anway) on tech-userlevel with no adverse response.

This allows the magic of vars like HOSTNAME SECONDS, ToD (etc) to be
restored should it be lost - perhaps by having a var of the same name
imported from the environment (which needs to remove the magic in case
a set of scripts are using the env to pass data, and the var name chosen
happens to be one of our magic ones).

No change to SMALL shells (or smaller) - none of the magic vars (except
LINENO, which is exempt from all of this) exist in those, hence such a
shell has no need for this command either.

diffstat:

 bin/sh/builtins.def |   5 ++++-
 bin/sh/sh.1         |  49 +++++++++++++++++++++++++++++++++++++++++++++++--
 bin/sh/var.c        |  47 +++++++++++++++++++++++++++++++++++++++++++++--
 3 files changed, 96 insertions(+), 5 deletions(-)

diffs (191 lines):

diff -r 68a11fb95baa -r d1f431ade870 bin/sh/builtins.def
--- a/bin/sh/builtins.def       Thu Feb 14 10:36:33 2019 +0000
+++ b/bin/sh/builtins.def       Thu Feb 14 11:15:24 2019 +0000
@@ -1,5 +1,5 @@
 #!/bin/sh -
-#      $NetBSD: builtins.def,v 1.25 2017/05/15 20:00:36 kre Exp $
+#      $NetBSD: builtins.def,v 1.26 2019/02/14 11:15:24 kre Exp $
 #
 # Copyright (c) 1991, 1993
 #      The Regents of the University of California.  All rights reserved.
@@ -76,6 +76,9 @@
 fdflagscmd     fdflags
 setvarcmd      setvar
 shiftcmd       -s shift
+#ifndef SMALL
+specialvarcmd  specialvar
+#endif
 timescmd       -s times
 trapcmd                -s trap
 truecmd                -s : -u true
diff -r 68a11fb95baa -r d1f431ade870 bin/sh/sh.1
--- a/bin/sh/sh.1       Thu Feb 14 10:36:33 2019 +0000
+++ b/bin/sh/sh.1       Thu Feb 14 11:15:24 2019 +0000
@@ -1,4 +1,4 @@
-.\"    $NetBSD: sh.1,v 1.219 2019/02/04 12:18:36 wiz Exp $
+.\"    $NetBSD: sh.1,v 1.220 2019/02/14 11:15:24 kre Exp $
 .\" Copyright (c) 1991, 1993
 .\"    The Regents of the University of California.  All rights reserved.
 .\"
@@ -31,7 +31,7 @@
 .\"
 .\"    @(#)sh.1        8.6 (Berkeley) 5/4/95
 .\"
-.Dd February 4, 2019
+.Dd February 14, 2019
 .Dt SH 1
 .\" everything except c o and s (keep them ordered)
 .ds flags abCEeFfhIiLmnpquVvXx
@@ -3351,6 +3351,39 @@
 .Dq Li $# )
 before the shift.
 .\"
+.It Ic specialvar Ar variable ...
+For each
+.Ar variable
+name given,
+if the variable named is one which,
+in this
+.Nm ,
+could be treated as a special variable,
+then cause that
+.Ar variable
+to be made special, undoing any effects of an earlier
+.Ic unset
+or assignment to the variable.
+If all
+.Ar variable Ns s
+given are recognized special variables in this
+.Nm
+the
+.Ic specialvar
+command will exit with status 0, otherwise 1.
+Invalid usage will result in an exit status of 2.
+.Pp
+Note that all variables capable of being special are created
+that way, this command is not required to cause that to happen.
+However should such a variable be imported from the environment,
+that will cause (for those special variables so designated)
+the special effects for that variable to be lost.
+Consequently, as the contents of the environment cannot be controlled,
+any script which desires to make use of the properties
+of most of the special variables should use this command,
+naming the variables required,
+to ensure that their special properties are available.
+.\"
 .It Ic times
 Prints two lines to standard output.
 Each line contains two accumulated time values, expressed
@@ -4093,6 +4126,9 @@
 cause updates without further action.
 If unset, it returns nothing.
 If set it loses its special properties, and is simply a variable.
+See the
+.Ic specialvar
+built-in command for remedial action.
 .It Ev HISTSIZE
 The number of lines in the history buffer for the shell.
 .It Ev HOME
@@ -4112,6 +4148,9 @@
 without further action.
 If unset, it returns nothing.
 If set it loses its special properties, and is simply a variable.
+See the
+.Ic specialvar
+built-in command for remedial action.
 .It Ev IFS
 Input Field Separators.
 This is normally set to
@@ -4284,6 +4323,9 @@
 Returns the number of seconds since the current shell was started.
 If unset, it remains unset, and returns nothing, unless set again.
 If set, it loses its special properties, and becomes a normal variable.
+See the
+.Ic specialvar
+built-in command for remedial action.
 .It Ev START_TIME
 Initialized by the shell to the number of seconds since the Epoch
 (see
@@ -4318,6 +4360,9 @@
 .Ev ToD
 returns nothing.
 If set, it loses its special properties, and becomes a normal variable.
+See the
+.Ic specialvar
+built-in command for remedial action.
 .It Ev ToD_FORMAT
 Can be set to the
 .Xr strftime 3
diff -r 68a11fb95baa -r d1f431ade870 bin/sh/var.c
--- a/bin/sh/var.c      Thu Feb 14 10:36:33 2019 +0000
+++ b/bin/sh/var.c      Thu Feb 14 11:15:24 2019 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: var.c,v 1.77 2019/02/09 09:38:11 kre Exp $     */
+/*     $NetBSD: var.c,v 1.78 2019/02/14 11:15:24 kre Exp $     */
 
 /*-
  * Copyright (c) 1991, 1993
@@ -37,7 +37,7 @@
 #if 0
 static char sccsid[] = "@(#)var.c      8.3 (Berkeley) 5/4/95";
 #else
-__RCSID("$NetBSD: var.c,v 1.77 2019/02/09 09:38:11 kre Exp $");
+__RCSID("$NetBSD: var.c,v 1.78 2019/02/14 11:15:24 kre Exp $");
 #endif
 #endif /* not lint */
 
@@ -194,6 +194,7 @@
 STATIC struct var *find_var(const char *, struct var ***, int *);
 STATIC void showvar(struct var *, const char *, const char *, int);
 static void export_usage(const char *) __dead;
+STATIC int makespecial(const char *);
 
 /*
  * Initialize the varable symbol tables and import the environment
@@ -1616,4 +1617,46 @@
 #undef srandom
 }
 
+STATIC int
+makespecial(const char *name)
+{
+       const struct varinit *ip;
+       struct var *vp;
+
+       CTRACE(DBG_VARS, ("makespecial('%s') -> ", name));
+       for (ip = varinit ; (vp = ip->var) != NULL ; ip++) {
+               if (strequal(ip->text, name)) {
+                       if (!(ip->flags & VFUNCREF)) {
+                               CTRACE(DBG_VARS, ("+1\n"));
+                               return 1;
+                       }
+                       INTOFF;
+                       vp->flags &= ~VUNSET;
+                       vp->v_u = ip->v_u;
+                       INTON;
+                       CTRACE(DBG_VARS, ("0\n"));
+                       return 0;
+               }
+       }
+       CTRACE(DBG_VARS, ("1\n"));
+       return 1;
+}
+
+int
+specialvarcmd(int argc, char **argv)
+{
+       int res = 0;
+       char **ap;
+
+       (void) nextopt("");
+
+       if (!*argptr)
+               error("Usage: specialvar var...");
+
+       for (ap = argptr; *ap ; ap++)
+               res |= makespecial(*ap);
+
+       return res;
+}
+
 #endif /* SMALL */



Home | Main Index | Thread Index | Old Index