summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTreehugger Robot <treehugger-gerrit@google.com>2020-05-21 22:16:10 +0000
committerAutomerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>2020-05-21 22:16:10 +0000
commit76e4243dd626fab81d9b7ad7f3db4ae251a64845 (patch)
tree0d0b36ad2f9412cf1969f0c0399d2845756c5156
parent13fd1d1f9cf2fe029e2258c7528d2e985c6fd314 (diff)
parentfcdb2d69582f60efa411b3caa5109bf3ce0d275c (diff)
downloadmksh-76e4243dd626fab81d9b7ad7f3db4ae251a64845.tar.gz
Merge "Upgrade to mksh R59b." am: 4adbc81376 am: efb93a535d am: d04311005c am: fcdb2d6958
Change-Id: I9882cfd38faf9b21d11c3f89c102bfb3cf72a4d8
-rw-r--r--Android.bp2
-rw-r--r--Android.patch.txt21
-rw-r--r--src/Build.sh4
-rw-r--r--src/check.t212
-rw-r--r--src/edit.c18
-rw-r--r--src/eval.c3
-rw-r--r--src/funcs.c4
-rw-r--r--src/main.c73
-rw-r--r--src/misc.c89
-rw-r--r--src/mksh.169
-rw-r--r--src/mksh.faq4
-rw-r--r--src/sh.h27
-rw-r--r--src/sh_flags.gen3
-rw-r--r--src/sh_flags.opt6
14 files changed, 360 insertions, 175 deletions
diff --git a/Android.bp b/Android.bp
index e3e374b..15afd71 100644
--- a/Android.bp
+++ b/Android.bp
@@ -107,7 +107,7 @@ cc_defaults {
"-DHAVE_SYS_ERRLIST_DECL=0",
"-DHAVE_SYS_SIGLIST_DECL=1",
"-DHAVE_PERSISTENT_HISTORY=0",
- "-DMKSH_BUILD_R=591",
+ "-DMKSH_BUILD_R=592",
// Additional flags
"-DMKSH_DEFAULT_PROFILEDIR=\"/system/etc\"",
diff --git a/Android.patch.txt b/Android.patch.txt
index d2cd1fa..eefcd5c 100644
--- a/Android.patch.txt
+++ b/Android.patch.txt
@@ -1,6 +1,7 @@
-diff -u mksh-R59/funcs.c src/funcs.c
---- mksh-R59/funcs.c 2020-04-13 12:51:34.000000000 -0700
-+++ src/funcs.c 2020-05-15 16:10:35.035013192 -0700
+Only in src: FAQ.htm
+diff -u mksh-R59b/funcs.c src/funcs.c
+--- mksh-R59b/funcs.c 2020-05-16 15:38:48.000000000 -0700
++++ src/funcs.c 2020-05-20 17:14:19.588510856 -0700
@@ -104,7 +104,9 @@
{Tsgbreak, c_brkcont},
{T__builtin, c_builtin},
@@ -32,11 +33,10 @@ diff -u mksh-R59/funcs.c src/funcs.c
#ifdef __MirBSD__
/* alias to "true" for historical reasons */
{"domainname", c_true},
-Only in src: funcs.c.orig
-diff -u mksh-R59/main.c src/main.c
---- mksh-R59/main.c 2020-04-13 10:04:41.000000000 -0700
-+++ src/main.c 2020-05-15 16:10:35.035013192 -0700
-@@ -402,6 +402,12 @@
+diff -u mksh-R59b/main.c src/main.c
+--- mksh-R59b/main.c 2020-05-16 15:51:51.000000000 -0700
++++ src/main.c 2020-05-20 17:14:19.588510856 -0700
+@@ -414,6 +414,12 @@
/* import environment */
init_environ();
@@ -50,3 +50,8 @@ diff -u mksh-R59/main.c src/main.c
typeset(TinitIFS, 0, 0, 0, 0);
Only in src: main.c.orig
+Only in src: Rebuild.sh
+Only in src: rlimits.gen
+Only in src: sh_flags.gen
+Only in src: signames.inc
+Only in src: test.sh
diff --git a/src/Build.sh b/src/Build.sh
index 1a95e66..1d30045 100644
--- a/src/Build.sh
+++ b/src/Build.sh
@@ -1,5 +1,5 @@
#!/bin/sh
-srcversion='$MirOS: src/bin/mksh/Build.sh,v 1.755 2020/04/07 23:15:11 tg Exp $'
+srcversion='$MirOS: src/bin/mksh/Build.sh,v 1.756 2020/05/16 22:53:03 tg Exp $'
#-
# Copyright (c) 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010,
# 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2019,
@@ -2461,7 +2461,7 @@ addsrcs '!' HAVE_STRLCPY strlcpy.c
addsrcs USE_PRINTF_BUILTIN printf.c
test 1 = "$USE_PRINTF_BUILTIN" && add_cppflags -DMKSH_PRINTF_BUILTIN
test 1 = "$HAVE_CAN_VERB" && CFLAGS="$CFLAGS -verbose"
-add_cppflags -DMKSH_BUILD_R=591
+add_cppflags -DMKSH_BUILD_R=592
$e $bi$me: Finished configuration testing, now producing output.$ao
diff --git a/src/check.t b/src/check.t
index a750c50..8818822 100644
--- a/src/check.t
+++ b/src/check.t
@@ -1,4 +1,4 @@
-# $MirOS: src/bin/mksh/check.t,v 1.838 2020/04/13 19:51:08 tg Exp $
+# $MirOS: src/bin/mksh/check.t,v 1.845 2020/05/16 22:19:15 tg Exp $
# -*- mode: sh -*-
#-
# Copyright © 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010,
@@ -31,7 +31,7 @@
# (2013/12/02 20:39:44) http://cvsweb.openbsd.org/cgi-bin/cvsweb/src/regress/bin/ksh/?sortby=date
expected-stdout:
- KSH R59 2020/04/14
+ KSH R59 2020/05/16
description:
Check base version of full shell
stdin:
@@ -8082,45 +8082,50 @@ name: test-str-pattern
description:
Check that [[ x = $y ]] can take extglobs, like ksh93
stdin:
+ [[ -n $BASH_VERSION ]] && shopt -s extglob
+ function one {
+ n=$1 x=$2 y=$3 z=${4:-$3}
+ [[ $x = $y ]]; a=$?
+ [[ $x = "$y" ]]; b=$?
+ eval '[[ $x = '"$z"' ]]; c=$?'
+ eval '[[ $x = "'"$z"'" ]]; d=$?'
+ echo $n $a $b $c $d .
+ }
x='a\'
- [[ $x = a\ ]]; echo 1 $? .
- [[ $x = a\\ ]]; echo 2 $? .
- y='a\'
- [[ $x = $y ]]; echo 3 $? .
- [[ $x = "$y" ]]; echo 4 $? .
- x='a\b'
- y='a\b'
- [[ $x = $y ]]; echo 5 $? .
- [[ $x = "$y" ]]; echo 6 $? .
- y='a\\b'
- [[ $x = $y ]]; echo 7 $? .
- [[ $x = "$y" ]]; echo 8 $? .
- x='foo'
- y='f+(o)'
- [[ $x = $y ]]; echo 9 $? .
- [[ $x = "$y" ]]; echo 10 $? .
- x=$y
- [[ $x = $y ]]; echo 11 $? .
- [[ $x = "$y" ]]; echo 12 $? .
+ [[ $x = a\ ]]; echo 01 $? .
+ [[ $x = a\\ ]]; echo 02 $? .
+ one 03 'a\' 'a\' 'a\\'
+ one 04 'a\b' 'a\b'
+ one 05 'a\b' 'a\\b'
+ one 06 'foo' 'f+(o)'
+ one 07 'f+(o)' 'f+(o)'
+ one 08 'f+(o' 'f+(o' 'f+\(o'
+ one 09 foo 'f+(o' 'f+\(o'
+ one 10 abcde 'a\*e'
+ one 11 'a*e' 'a\*e'
+ one 12 'a\*e' 'a\*e'
+ echo extras:
x='f+(o'
- y=$x
- [[ $x = $y ]]; echo 13 $? .
- [[ $x = "$y" ]]; echo 14 $? .
-expected-stdout:
- 1 1 .
- 2 0 .
- 3 0 .
- 4 0 .
- 5 1 .
- 6 0 .
- 7 0 .
- 8 1 .
- 9 0 .
- 10 1 .
- 11 1 .
- 12 0 .
- 13 0 .
- 14 0 .
+ z='f+(o'
+ eval '[[ $x = "'"$z"'" ]]; echo 14 $? "(08:4)" .'
+ x=foo
+ eval '[[ $x = "'"$z"'" ]]; echo 15 $? "(09:4)" .'
+expected-stdout:
+ 01 1 .
+ 02 0 .
+ 03 0 0 0 0 .
+ 04 1 0 1 0 .
+ 05 0 1 0 0 .
+ 06 0 1 0 1 .
+ 07 1 0 1 0 .
+ 08 0 0 0 1 .
+ 09 1 1 1 1 .
+ 10 1 1 1 1 .
+ 11 0 1 0 1 .
+ 12 1 0 1 0 .
+ extras:
+ 14 0 (08:4) .
+ 15 1 (09:4) .
---
name: test-precedence-1
description:
@@ -8448,8 +8453,10 @@ description:
stdin:
set -o braceexpand
set +o sh
- [[ $(set +o) == *@(-o sh)@(| *) ]] && echo sh || echo nosh
- [[ $(set +o) == *@(-o braceexpand)@(| *) ]] && echo brex || echo nobrex
+ [[ -o sh ]] && echo sh
+ [[ -o !sh ]] && echo nosh
+ [[ -o braceexpand ]] && echo brex
+ [[ -o !braceexpand ]] && echo nobrex
echo {a,b,c}
set +o braceexpand
echo {a,b,c}
@@ -8457,12 +8464,17 @@ stdin:
echo {a,b,c}
set -o sh
echo {a,b,c}
- [[ $(set +o) == *@(-o sh)@(| *) ]] && echo sh || echo nosh
- [[ $(set +o) == *@(-o braceexpand)@(| *) ]] && echo brex || echo nobrex
+ [[ -o sh ]] && echo sh
+ [[ -o !sh ]] && echo nosh
+ [[ -o braceexpand ]] && echo brex
+ [[ -o !braceexpand ]] && echo nobrex
set -o braceexpand
echo {a,b,c}
- [[ $(set +o) == *@(-o sh)@(| *) ]] && echo sh || echo nosh
- [[ $(set +o) == *@(-o braceexpand)@(| *) ]] && echo brex || echo nobrex
+ [[ -o sh ]] && echo sh
+ [[ -o !sh ]] && echo nosh
+ [[ -o braceexpand ]] && echo brex
+ [[ -o !braceexpand ]] && echo nobrex
+ [[ $(exec -a -set "$__progname" -o) = *login+(' ')on* ]]; echo $?
expected-stdout:
nosh
brex
@@ -8475,44 +8487,110 @@ expected-stdout:
a b c
sh
brex
+ 0
---
name: sh-mode-2a
description:
Check that posix or sh mode is *not* automatically turned on
category: !binsh
stdin:
- ln -s "$__progname" ksh || cp "$__progname" ksh
- ln -s "$__progname" sh || cp "$__progname" sh
- ln -s "$__progname" ./-ksh || cp "$__progname" ./-ksh
- ln -s "$__progname" ./-sh || cp "$__progname" ./-sh
- for shell in {,-}{,k}sh; do
- print -- $shell $(./$shell +l -c \
- '[[ $(set +o) == *"-o "@(sh|posix)@(| *) ]] && echo sh || echo nosh')
+ for shell in {,-}{,r}{,k,mk}sh {,-}{,R}{,K,MK}SH.EXE; do
+ ln -s "$__progname" ./$shell || cp "$__progname" ./$shell
+ print -- $shell $(./$shell +l -c '
+ [[ -o sh || -o posix ]] && echo sh
+ [[ -o !sh && -o !posix ]] && echo nosh
+ [[ -o restricted ]] && echo lim || echo ok
+ ')
done
expected-stdout:
- sh nosh
- ksh nosh
- -sh nosh
- -ksh nosh
+ sh nosh ok
+ ksh nosh ok
+ mksh nosh ok
+ rsh nosh lim
+ rksh nosh lim
+ rmksh nosh lim
+ -sh nosh ok
+ -ksh nosh ok
+ -mksh nosh ok
+ -rsh nosh lim
+ -rksh nosh lim
+ -rmksh nosh lim
+ SH.EXE nosh ok
+ KSH.EXE nosh ok
+ MKSH.EXE nosh ok
+ RSH.EXE nosh lim
+ RKSH.EXE nosh lim
+ RMKSH.EXE nosh lim
+ -SH.EXE nosh ok
+ -KSH.EXE nosh ok
+ -MKSH.EXE nosh ok
+ -RSH.EXE nosh lim
+ -RKSH.EXE nosh lim
+ -RMKSH.EXE nosh lim
---
name: sh-mode-2b
description:
Check that posix or sh mode *is* automatically turned on
category: binsh
stdin:
- ln -s "$__progname" ksh || cp "$__progname" ksh
- ln -s "$__progname" sh || cp "$__progname" sh
- ln -s "$__progname" ./-ksh || cp "$__progname" ./-ksh
- ln -s "$__progname" ./-sh || cp "$__progname" ./-sh
- for shell in {,-}{,k}sh; do
- print -- $shell $(./$shell +l -c \
- '[[ $(set +o) == *"-o "@(sh|posix)@(| *) ]] && echo sh || echo nosh')
+ for shell in {,-}{,r}{,k,mk}sh {,-}{,R}{,K,MK}SH.EXE; do
+ ln -s "$__progname" ./$shell || cp "$__progname" ./$shell
+ print -- $shell $(./$shell +l -c '
+ [[ -o sh || -o posix ]] && echo sh
+ [[ -o !sh && -o !posix ]] && echo nosh
+ [[ -o restricted ]] && echo lim || echo ok
+ ')
done
expected-stdout:
- sh sh
- ksh nosh
- -sh sh
- -ksh nosh
+ sh sh ok
+ ksh nosh ok
+ mksh nosh ok
+ rsh sh lim
+ rksh nosh lim
+ rmksh nosh lim
+ -sh sh ok
+ -ksh nosh ok
+ -mksh nosh ok
+ -rsh sh lim
+ -rksh nosh lim
+ -rmksh nosh lim
+ SH.EXE sh ok
+ KSH.EXE nosh ok
+ MKSH.EXE nosh ok
+ RSH.EXE sh lim
+ RKSH.EXE nosh lim
+ RMKSH.EXE nosh lim
+ -SH.EXE sh ok
+ -KSH.EXE nosh ok
+ -MKSH.EXE nosh ok
+ -RSH.EXE sh lim
+ -RKSH.EXE nosh lim
+ -RMKSH.EXE nosh lim
+---
+name: sh-options
+description:
+ Check that "set +o" DTRT per POSIX
+stdin:
+ t() {
+ [[ -o vi ]]; a=$?
+ [[ -o pipefail ]]; b=$?
+ echo $((++i)) $a $b .
+ }
+ set -e
+ set -o vi
+ set +o pipefail
+ set +e
+ t
+ x=$(set +o)
+ set +o vi
+ set -o pipefail
+ t
+ eval "$x"
+ t
+expected-stdout:
+ 1 0 1 .
+ 2 1 0 .
+ 3 0 1 .
---
name: pipeline-1
description:
diff --git a/src/edit.c b/src/edit.c
index f38092e..8c1c2c8 100644
--- a/src/edit.c
+++ b/src/edit.c
@@ -29,7 +29,7 @@
#ifndef MKSH_NO_CMDLINE_EDITING
-__RCSID("$MirOS: src/bin/mksh/edit.c,v 1.350 2020/04/13 20:46:37 tg Exp $");
+__RCSID("$MirOS: src/bin/mksh/edit.c,v 1.351 2020/04/15 20:16:19 tg Exp $");
/*
* in later versions we might use libtermcap for this, but since external
@@ -5603,9 +5603,19 @@ x_initterm(const char *termtype)
{
/* default must be 0 (bss) */
x_term_mode = 0;
- /* this is what tmux uses, don't ask me about it */
- if (!strcmp(termtype, "screen") || !strncmp(termtype, "screen-", 7))
- x_term_mode = 1;
+ /* catch any of the TERM types tmux uses, don’t ask m̲e̲ about it… */
+ switch (*termtype) {
+ case 's':
+ if (!strncmp(termtype, "screen", 6) &&
+ (termtype[6] == '\0' || termtype[6] == '-'))
+ x_term_mode = 1;
+ break;
+ case 't':
+ if (!strncmp(termtype, "tmux", 4) &&
+ (termtype[4] == '\0' || termtype[4] == '-'))
+ x_term_mode = 1;
+ break;
+ }
}
#ifndef MKSH_SMALL
diff --git a/src/eval.c b/src/eval.c
index 6e7b505..33a8ea1 100644
--- a/src/eval.c
+++ b/src/eval.c
@@ -24,7 +24,7 @@
#include "sh.h"
-__RCSID("$MirOS: src/bin/mksh/eval.c,v 1.230 2020/04/07 23:14:41 tg Exp $");
+__RCSID("$MirOS: src/bin/mksh/eval.c,v 1.231 2020/05/05 21:34:27 tg Exp $");
/*
* string expansion
@@ -882,6 +882,7 @@ expand(
c = ORD('\\');
else
++x.str;
+ quote |= 2;
break;
/* ctype(c, C_PATMO) */
case ORD('!'):
diff --git a/src/funcs.c b/src/funcs.c
index a5cfc69..d3427d0 100644
--- a/src/funcs.c
+++ b/src/funcs.c
@@ -39,7 +39,7 @@
#endif
#endif
-__RCSID("$MirOS: src/bin/mksh/funcs.c,v 1.372 2020/04/13 19:51:07 tg Exp $");
+__RCSID("$MirOS: src/bin/mksh/funcs.c,v 1.373 2020/05/16 22:38:21 tg Exp $");
#if HAVE_KILLPG
/*
@@ -330,7 +330,7 @@ c_print(const char **wp)
#ifndef MKSH_MIDNIGHTBSD01ASH_COMPAT
Flag(FSH) ||
#endif
- Flag(FAS_BUILTIN)) {
+ as_builtin) {
/* BSD "echo" cmd, Debian Policy 10.4 compliant */
++wp;
bsd_echo:
diff --git a/src/main.c b/src/main.c
index 3d440dd..1328045 100644
--- a/src/main.c
+++ b/src/main.c
@@ -35,7 +35,7 @@
#include <locale.h>
#endif
-__RCSID("$MirOS: src/bin/mksh/main.c,v 1.364 2020/04/13 17:04:14 tg Exp $");
+__RCSID("$MirOS: src/bin/mksh/main.c,v 1.372 2020/05/16 22:51:24 tg Exp $");
#ifndef MKSHRC_PATH
#define MKSHRC_PATH "~/.mkshrc"
@@ -242,6 +242,9 @@ main_init(int argc, const char *argv[], Source **sp, struct block **lp)
#ifdef __OS2__
os2_init(&argc, &argv);
+#define builtin_name_cmp stricmp
+#else
+#define builtin_name_cmp strcmp
#endif
/* do things like getpgrp() et al. */
@@ -276,10 +279,11 @@ main_init(int argc, const char *argv[], Source **sp, struct block **lp)
ccp += argi;
begin_parsing_kshname:
argi = 0;
- if (*ccp == '-')
- ++ccp;
}
}
+ Flag(FLOGIN) = (ord(*ccp) == ORD('-')) || (ord(*kshname) == ORD('-'));
+ if (ord(*ccp) == ORD('-'))
+ ++ccp;
if (!*ccp)
ccp = empty_argv[0];
@@ -304,24 +308,32 @@ main_init(int argc, const char *argv[], Source **sp, struct block **lp)
ktinit(APERM, &builtins,
/* currently up to 52 builtins: 75% of 128 = 2^7 */
7);
- for (i = 0; mkshbuiltins[i].name != NULL; i++)
- if (!strcmp(ccp, builtin(mkshbuiltins[i].name,
- mkshbuiltins[i].func)))
- Flag(FAS_BUILTIN) = 1;
+ for (i = 0; mkshbuiltins[i].name != NULL; ++i) {
+ const char *builtin_name;
+
+ builtin_name = builtin(mkshbuiltins[i].name,
+ mkshbuiltins[i].func);
+ if (!builtin_name_cmp(ccp, builtin_name)) {
+ /* canonicalise argv[0] */
+ ccp = builtin_name;
+ as_builtin = true;
+ }
+ }
- if (!Flag(FAS_BUILTIN)) {
+ if (!as_builtin) {
/* check for -T option early */
argi = parse_args(argv, OF_FIRSTTIME, NULL);
if (argi < 0)
return (1);
- /* called as rsh, rmksh, -rsh, -rmksh, etc.? */
- if (ord(*ccp) == ORD('r')) {
+ /* called as rsh, rmksh, -rsh, RKSH.EXE, etc.? */
+ if (ksh_eq(*ccp, 'R', 'r')) {
++ccp;
++restricted_shell;
}
#if defined(MKSH_BINSHPOSIX) || defined(MKSH_BINSHREDUCED)
- /* are we called as -sh or /bin/sh or so? */
- if (!strcmp(ccp, "sh" MKSH_EXE_EXT)) {
+ /* are we called as -rsh or /bin/sh or SH.EXE or so? */
+ if (ksh_eq(ccp[0], 'S', 's') &&
+ ksh_eq(ccp[1], 'H', 'h')) {
/* either also turns off braceexpand */
#ifdef MKSH_BINSHPOSIX
/* enable better POSIX conformance */
@@ -474,7 +486,7 @@ main_init(int argc, const char *argv[], Source **sp, struct block **lp)
/* this to note if utf-8 mode is set on command line (see below) */
UTFMODE = 2;
- if (!Flag(FAS_BUILTIN)) {
+ if (!as_builtin) {
argi = parse_args(argv, OF_CMDLINE, NULL);
if (argi < 0)
return (1);
@@ -484,7 +496,7 @@ main_init(int argc, const char *argv[], Source **sp, struct block **lp)
utf_flag = UTFMODE;
UTFMODE = 0;
- if (Flag(FAS_BUILTIN)) {
+ if (as_builtin) {
/* auto-detect from environment variables, always */
utf_flag = 3;
} else if (Flag(FCOMMAND)) {
@@ -549,8 +561,8 @@ main_init(int argc, const char *argv[], Source **sp, struct block **lp)
}
/* this bizarreness is mandated by POSIX */
- if (fstat(0, &s_stdin) >= 0 && S_ISCHR(s_stdin.st_mode) &&
- Flag(FTALKING))
+ if (Flag(FTALKING) && fstat(0, &s_stdin) >= 0 &&
+ S_ISCHR(s_stdin.st_mode))
reset_nonblock(0);
/* initialise job control */
@@ -582,7 +594,7 @@ main_init(int argc, const char *argv[], Source **sp, struct block **lp)
#endif
l = e->loc;
- if (Flag(FAS_BUILTIN)) {
+ if (as_builtin) {
l->argc = argc;
l->argv = argv;
l->argv[0] = ccp;
@@ -650,6 +662,21 @@ main_init(int argc, const char *argv[], Source **sp, struct block **lp)
errexit = Flag(FERREXIT);
Flag(FERREXIT) = 0;
+ /* save flags for "set +o" handling */
+ memcpy(baseline_flags, shell_flags, sizeof(shell_flags));
+ /* disable these because they have special handling */
+ baseline_flags[(int)FPOSIX] = 0;
+ baseline_flags[(int)FSH] = 0;
+ /* ensure these always show up setting, for FPOSIX/FSH */
+ baseline_flags[(int)FBRACEEXPAND] = 0;
+ baseline_flags[(int)FUNNYCODE] = 0;
+#if !defined(MKSH_SMALL) || defined(DEBUG)
+ /* mark as initialised */
+ baseline_flags[(int)FNFLAGS] = 1;
+#endif
+ if (as_builtin)
+ goto skip_startup_files;
+
/*
* Do this before profile/$ENV so that if it causes problems in them,
* user will know why things broke.
@@ -668,6 +695,8 @@ main_init(int argc, const char *argv[], Source **sp, struct block **lp)
else
/* turn off -p if not set explicitly */
change_flag(FPRIVILEGED, OF_INTERNAL, false);
+ /* track shell-imposed changes */
+ baseline_flags[(int)FPRIVILEGED] = Flag(FPRIVILEGED);
} else {
if (Flag(FLOGIN))
include(substitute("$HOME/.profile", 0), 0, NULL, true);
@@ -681,14 +710,20 @@ main_init(int argc, const char *argv[], Source **sp, struct block **lp)
c_builtin(restr_com);
/* After typeset command... */
Flag(FRESTRICTED) = 1;
+ /* track shell-imposed changes */
+ baseline_flags[(int)FRESTRICTED] = 1;
}
Flag(FERREXIT) = errexit;
if (Flag(FTALKING) && s)
hist_init(s);
- else
+ else {
/* set after ENV */
+ skip_startup_files:
Flag(FTRACKALL) = 1;
+ /* track shell-imposed change (might lower surprise) */
+ baseline_flags[(int)FTRACKALL] = 1;
+ }
alarm_init();
@@ -707,7 +742,7 @@ main(int argc, const char *argv[])
struct block *l;
if ((rv = main_init(argc, argv, &s, &l)) == 0) {
- if (Flag(FAS_BUILTIN)) {
+ if (as_builtin) {
rv = c_builtin(l->argv);
} else {
shell(s, 0);
diff --git a/src/misc.c b/src/misc.c
index 9e5b572..b19a253 100644
--- a/src/misc.c
+++ b/src/misc.c
@@ -3,7 +3,8 @@
/*-
* Copyright (c) 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010,
- * 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2019
+ * 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2019,
+ * 2020
* mirabilos <m@mirbsd.org>
* Copyright (c) 2015
* Daniel Richard G. <skunk@iSKUNK.ORG>
@@ -32,7 +33,7 @@
#include <grp.h>
#endif
-__RCSID("$MirOS: src/bin/mksh/misc.c,v 1.297 2020/04/07 11:56:46 tg Exp $");
+__RCSID("$MirOS: src/bin/mksh/misc.c,v 1.299 2020/05/16 22:19:58 tg Exp $");
#define KSH_CHVT_FLAG
#ifdef MKSH_SMALL
@@ -141,7 +142,8 @@ struct options_info {
};
static void options_fmt_entry(char *, size_t, unsigned int, const void *);
-static void printoptions(bool);
+static int printoptions(bool);
+static int printoption(size_t);
/* format a single select menu item */
static void
@@ -154,10 +156,32 @@ options_fmt_entry(char *buf, size_t buflen, unsigned int i, const void *arg)
Flag(oi->opts[i]) ? "on" : "off");
}
-static void
+static int
+printoption(size_t i)
+{
+ if (Flag(i) == baseline_flags[i])
+ return (0);
+ if (!OFN(i)[0]) {
+#if !defined(MKSH_SMALL) || defined(DEBUG)
+ bi_errorf(Tf_sd, "change in unnamed option", (int)i);
+#endif
+ return (1);
+ }
+ if (Flag(i) != 0 && Flag(i) != 1) {
+#if !defined(MKSH_SMALL) || defined(DEBUG)
+ bi_errorf(Tf_s_sD_s, Tdo, OFN(i), "not 0 or 1");
+#endif
+ return (1);
+ }
+ shprintf(Tf__s_s, Flag(i) ? Tdo : Tpo, OFN(i));
+ return (0);
+}
+
+static int
printoptions(bool verbose)
{
size_t i = 0;
+ int rv = 0;
if (verbose) {
size_t n = 0, len, octs = 0;
@@ -187,13 +211,17 @@ printoptions(bool verbose)
} else {
/* short version like AT&T ksh93 */
shf_puts(Tset, shl_stdout);
- while (i < NELEM(options)) {
- if (Flag(i) && OFN(i)[0])
- shprintf(" -o %s", OFN(i));
+ shf_puts(To_o_reset, shl_stdout);
+ printoption(FSH);
+ printoption(FPOSIX);
+ while (i < FNFLAGS) {
+ if (i != FSH && i != FPOSIX)
+ rv |= printoption(i);
++i;
}
shf_putc('\n', shl_stdout);
}
+ return (rv);
}
char *
@@ -362,7 +390,8 @@ parse_args(const char **argv,
#undef SHFLAGS_NOT_CMD
;
bool set;
- const char *opts;
+ const char *opts = what == OF_CMDLINE || what == OF_FIRSTTIME ?
+ cmd_opts : set_opts;
const char *array = NULL;
Getopt go;
size_t i;
@@ -370,22 +399,6 @@ parse_args(const char **argv,
bool sortargs = false;
bool fcompatseen = false;
- if (what == OF_CMDLINE) {
- const char *p = argv[0], *q;
- /*
- * Set FLOGIN before parsing options so user can clear
- * flag using +l.
- */
- if (*p != '-')
- for (q = p; *q; )
- if (mksh_cdirsep(*q++))
- p = q;
- Flag(FLOGIN) = (*p == '-');
- opts = cmd_opts;
- } else if (what == OF_FIRSTTIME) {
- opts = cmd_opts;
- } else
- opts = set_opts;
ksh_getopt_reset(&go, GF_ERROR|GF_PLUSOPT);
while ((optc = ksh_getopt(argv, &go, opts)) != -1) {
set = tobool(!(go.info & GI_PLUS));
@@ -408,7 +421,15 @@ parse_args(const char **argv,
* an option (ie, can't get here if what is
* OF_CMDLINE).
*/
- printoptions(set);
+#if !defined(MKSH_SMALL) || defined(DEBUG)
+ if (!set && !baseline_flags[(int)FNFLAGS]) {
+ bi_errorf(Tf_s_s, "too early",
+ Tset_po);
+ return (-1);
+ }
+#endif
+ if (printoptions(set))
+ return (-1);
break;
}
i = option(go.optarg);
@@ -433,7 +454,23 @@ parse_args(const char **argv,
;
else if ((i != (size_t)-1) && (OFF(i) & what))
change_flag((enum sh_flag)i, what, set);
- else {
+ else if (!strcmp(go.optarg, To_reset)) {
+#if !defined(MKSH_SMALL) || defined(DEBUG)
+ if (!baseline_flags[(int)FNFLAGS]) {
+ bi_errorf(Tf_ss, "too early",
+ To_o_reset);
+ return (-1);
+ }
+#endif
+ /*
+ * ordering, with respect to side effects,
+ * was ensured above by printoptions
+ */
+ for (i = 0; i < FNFLAGS; ++i)
+ if (Flag(i) != baseline_flags[i])
+ change_flag((enum sh_flag)i,
+ what, baseline_flags[i]);
+ } else {
bi_errorf(Tf_sD_s, go.optarg,
Tunknown_option);
return (-1);
diff --git a/src/mksh.1 b/src/mksh.1
index 672e6b6..1f1a121 100644
--- a/src/mksh.1
+++ b/src/mksh.1
@@ -1,4 +1,4 @@
-.\" $MirOS: src/bin/mksh/mksh.1,v 1.489 2020/04/14 22:45:21 tg Exp $
+.\" $MirOS: src/bin/mksh/mksh.1,v 1.491 2020/05/16 22:12:36 tg Exp $
.\" $OpenBSD: ksh.1,v 1.160 2015/07/04 13:27:04 feinerer Exp $
.\"-
.\" Copyright © 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009,
@@ -84,7 +84,7 @@
.\" with -mandoc, it might implement .Mx itself, but we want to
.\" use our own definition. And .Dd must come *first*, always.
.\"
-.Dd $Mdocdate: April 14 2020 $
+.Dd $Mdocdate: May 16 2020 $
.\"
.\" Check which macro package we use, and do other -mdoc setup.
.\"
@@ -270,7 +270,7 @@ option is on by default (see the
command below).
.It Fl l
Login shell.
-If the basename the shell is called with (i.e. argv[0])
+If the name or basename the shell is called with (i.e. argv[0])
starts with
.Ql \-
or if this option is used,
@@ -297,7 +297,9 @@ option is cleared automatically after processing the startup files.
Restricted shell.
A shell is
.Dq restricted
-if the basename the shell is called with (i.e. argv[0]) starts with
+if the basename the shell is called with, after
+.Ql \-
+processing, starts with
.Ql r
or if this option is used.
The following restrictions come into effect after the shell processes any
@@ -382,7 +384,7 @@ is determined as follows: if the
.Fl c
option is used and there is a non-option argument, it is used as the name;
if commands are being read from a file, the file is used as the name;
-otherwise, the basename the shell was called with (i.e. argv[0]) is used.
+otherwise, the name the shell was called with (i.e. argv[0]) is used.
.Pp
The exit status of the shell is 127 if the command file specified on the
command line could not be opened, or non-zero if a fatal syntax error
@@ -1801,12 +1803,11 @@ if it was invoked with the
.Fl c
option and arguments were given; otherwise the
.Ar file
-argument, if it was supplied;
-or else the basename the shell was invoked with (i.e.\&
-.Li argv[0] ) .
+argument, if it was supplied; or else the name the shell was invoked with
+.Pq i.e.\& Li argv[0] .
.Ev $0
-is also set to the name of the current script or
-the name of the current function, if it was defined with the
+is also set to the name of the current script,
+or to the name of the current function if it was defined with the
.Ic function
keyword (i.e. a Korn shell style function).
.It Ev 1 No .. Ev 9
@@ -2024,7 +2025,7 @@ and
.Xc
See the end of the Emacs editing mode documentation for an example.
.It Ev KSH_VERSION
-The name and version of the shell (read-only).
+The name (self-identification) and version of the shell (read-only).
See also the version commands in
.Sx Emacs editing mode
and
@@ -4562,34 +4563,42 @@ Behave closer to the standards
(see
.Sx POSIX mode
for details).
-Automatically enabled if the basename of the shell invocation begins with
+Automatically enabled if the shell invocation basename, after
+.Sq \-
+and
+.Sq r
+processing, begins with
.Dq sh
-and this autodetection feature is compiled in (not in MirBSD; commonly used for
-.Nm lksh
-only).
+and
+.Pq often used for the Nm lksh No binary
+this autodetection feature is compiled in.
As a side effect, setting this flag turns off the
.Ic braceexpand
and
.Ic utf8\-mode
flags, which can be turned back on manually, and
-.Pq unless both are enabled at the same time
+.Pq unless both are set in the same command
.Ic sh
mode.
.It Fl o Ic sh
-Enable
+Enable kludge
.Pa /bin/sh
-.Pq kludge
-mode (see
-.Sx SH mode ) .
-Automatically enabled if the basename of the shell invocation begins with
+compatibility mode (see
+.Sx SH mode
+below for details).
+Automatically enabled if the basename of the shell invocation, after
+.Sq \-
+and
+.Sq r
+processing, begins with
.Dq sh
and this autodetection feature is compiled in
.Pq rather uncommon .
-As a side effect, setting this flag turns off
+As a side effect, setting this flag turns off the
.Ic braceexpand
-mode, which can be turned back on manually, and
+flag, which can be turned back on manually, and
.Ic posix
-mode (unless both are enabled at the same time).
+mode (unless both are set in the same command).
.It Fl o Ic vi
Enable
.Xr vi 1 Ns -like
@@ -4623,12 +4632,10 @@ options (with single letter names) can be found in the parameter
.Ic set Fl o
with no option name will list all the options and whether each is on or off;
.Ic set +o
-will print the long names of all options that are currently on.
-In a future version,
-.Ic set +o
-will behave
-.Tn POSIX
-compliant and print commands to restore the current options instead.
+prints a command to restore the current option set, using the internal
+.Ic set Fl o Ic .reset
+construct, which is an implementation detail; these commands are transient
+.Pq only valid within the current shell session .
.Pp
Remaining arguments, if any, are positional parameters and are assigned, in
order, to the positional parameters (i.e. $1, $2, etc.).
@@ -7065,7 +7072,7 @@ for the in-memory portion of the history is slow, should use
.Xr memmove 3 .
.Pp
This document attempts to describe
-.Nm mksh\ R59
+.Nm mksh\ R59b
and up,
.\" with vendor patches from insert-your-name-here,
compiled without any options impacting functionality, such as
diff --git a/src/mksh.faq b/src/mksh.faq
index 1fc3b7d..83e0191 100644
--- a/src/mksh.faq
+++ b/src/mksh.faq
@@ -1,4 +1,4 @@
-RCSID: $MirOS: src/bin/mksh/mksh.faq,v 1.6 2020/04/13 20:46:39 tg Exp $
+RCSID: $MirOS: src/bin/mksh/mksh.faq,v 1.7 2020/04/25 12:09:55 tg Exp $
ToC: spelling
Title: How do you spell <tt>mksh</tt>? How do you pronounce it?
@@ -357,7 +357,7 @@ Title: What about programmable tab completion?
The shell itself provides static deterministic tab completion.
However, you can use hooks like reprogramming the Tab key to a
command line editor macro, and using the <tt>evaluate-region</tt>
-editor command (modulo a bugfix) together with <tt>quote-region<tt> and shell functions to
+editor command (modulo a bugfix) together with <tt>quote-region</tt> and shell functions to
implement a programmable completion engine. Multiple people have
been considering doing so in our IRC channel; we’ll hyperlink to
these engines when they are available.
diff --git a/src/sh.h b/src/sh.h
index c5e4dc5..8394c89 100644
--- a/src/sh.h
+++ b/src/sh.h
@@ -191,9 +191,9 @@
#endif
#ifdef EXTERN
-__RCSID("$MirOS: src/bin/mksh/sh.h,v 1.892 2020/04/14 22:45:22 tg Exp $");
+__RCSID("$MirOS: src/bin/mksh/sh.h,v 1.898 2020/05/16 22:38:23 tg Exp $");
#endif
-#define MKSH_VERSION "R59 2020/04/14"
+#define MKSH_VERSION "R59 2020/05/16"
/* arithmetic types: C implementation */
#if !HAVE_CAN_INTTYPES
@@ -513,9 +513,8 @@ extern int __cdecl setegid(gid_t);
#define O_BINARY 0
#endif
-#ifndef O_MAYEXEC
+#undef O_MAYEXEC /* https://lwn.net/Articles/820658/ */
#define O_MAYEXEC 0
-#endif
#ifdef MKSH__NO_SYMLINK
#undef S_ISLNK
@@ -669,7 +668,7 @@ char *ucstrstr(char *, const char *);
#endif
#endif
-#if (!defined(MKSH_BUILDMAKEFILE4BSD) && !defined(MKSH_BUILDSH)) || (MKSH_BUILD_R != 591)
+#if (!defined(MKSH_BUILDMAKEFILE4BSD) && !defined(MKSH_BUILDSH)) || (MKSH_BUILD_R != 592)
#error Must run Build.sh to compile this.
extern void thiswillneverbedefinedIhope(void);
int
@@ -917,6 +916,12 @@ EXTERN struct tbl *vp_pipest; /* global PIPESTATUS array */
EXTERN short trap_exstat; /* exit status before running a trap */
EXTERN uint8_t trap_nested; /* running nested traps */
EXTERN uint8_t shell_flags[FNFLAGS];
+EXTERN uint8_t baseline_flags[FNFLAGS
+#if !defined(MKSH_SMALL) || defined(DEBUG)
+ + 1
+#endif
+ ];
+EXTERN bool as_builtin; /* direct builtin call */
EXTERN const char *kshname; /* $0 */
EXTERN struct {
uid_t kshuid_v; /* real UID of shell at startup */
@@ -1038,7 +1043,10 @@ EXTERN const char Tnot_found_s[] E_INIT("%s not found");
#define Tnot_started (Tjob_not_started + 4)
#define TOLDPWD (Tno_OLDPWD + 3)
#define Topen (Tcant_open + 6)
+EXTERN const char To_o_reset[] E_INIT(" -o .reset");
+#define To_reset (To_o_reset + 4)
#define TPATH (TFPATH + 1)
+#define Tpo (Tset_po + 4)
#define Tpv (TpVv + 1)
EXTERN const char TpVv[] E_INIT("Vpv");
#define TPWD (Tno_OLDPWD + 6)
@@ -1053,6 +1061,7 @@ EXTERN const char TREPLY[] E_INIT("REPLY");
EXTERN const char Treq_arg[] E_INIT("requires an argument");
EXTERN const char Tselect[] E_INIT("select");
#define Tset (Tf_parm + 18)
+EXTERN const char Tset_po[] E_INIT("set +o");
EXTERN const char Tsghset[] E_INIT("*=#set");
#define Tsh (Tmksh + 2)
#define TSHELL (TEXECSHELL + 4)
@@ -1083,6 +1092,7 @@ EXTERN const char Tuser_sp2[] E_INIT(" user ");
#define Twrite (Tshf_write + 4)
EXTERN const char Tf__S[] E_INIT(" %S");
#define Tf__d (Tunexpected_type + 22)
+#define Tf_ss (Tf__ss + 1)
EXTERN const char Tf__ss[] E_INIT(" %s%s");
#define Tf__sN (Tf_s_s_sN + 5)
#define Tf_T (Tf_s_T + 3)
@@ -1091,6 +1101,7 @@ EXTERN const char Tf_s_[] E_INIT("%s ");
EXTERN const char Tf_s_T[] E_INIT("%s %T");
EXTERN const char Tf_s_s_sN[] E_INIT("%s %s %s\n");
#define Tf_s_s (Tf_sD_s_s + 4)
+#define Tf__s_s (Tf_sD_s_s + 3)
#define Tf_s_sD_s (Tf_cant_ss_s + 6)
EXTERN const char Tf_optfoo[] E_INIT("%s%s-%c: %s");
EXTERN const char Tf_sD_[] E_INIT("%s: ");
@@ -1198,7 +1209,10 @@ EXTERN const char T_devtty[] E_INIT("/dev/tty");
#define Tnot_started "not started"
#define TOLDPWD "OLDPWD"
#define Topen "open"
+#define To_o_reset " -o .reset"
+#define To_reset ".reset"
#define TPATH "PATH"
+#define Tpo "+o"
#define Tpv "pv"
#define TpVv "Vpv"
#define TPWD "PWD"
@@ -1213,6 +1227,7 @@ EXTERN const char T_devtty[] E_INIT("/dev/tty");
#define Treq_arg "requires an argument"
#define Tselect "select"
#define Tset "set"
+#define Tset_po "set +o"
#define Tsghset "*=#set"
#define Tsh "sh"
#define TSHELL "SHELL"
@@ -1243,6 +1258,7 @@ EXTERN const char T_devtty[] E_INIT("/dev/tty");
#define Twrite "write"
#define Tf__S " %S"
#define Tf__d " %d"
+#define Tf_ss "%s%s"
#define Tf__ss " %s%s"
#define Tf__sN " %s\n"
#define Tf_T "%T"
@@ -1251,6 +1267,7 @@ EXTERN const char T_devtty[] E_INIT("/dev/tty");
#define Tf_s_T "%s %T"
#define Tf_s_s_sN "%s %s %s\n"
#define Tf_s_s "%s %s"
+#define Tf__s_s " %s %s"
#define Tf_s_sD_s "%s %s: %s"
#define Tf_optfoo "%s%s-%c: %s"
#define Tf_sD_ "%s: "
diff --git a/src/sh_flags.gen b/src/sh_flags.gen
index a0a0f6a..538baf1 100644
--- a/src/sh_flags.gen
+++ b/src/sh_flags.gen
@@ -21,7 +21,7 @@
#ifndef SHFLAGS_OPTCS
#if defined(SHFLAGS_DEFNS)
-__RCSID("$MirOS: src/bin/mksh/sh_flags.opt,v 1.8 2019/12/30 03:58:58 tg Exp $");
+__RCSID("$MirOS: src/bin/mksh/sh_flags.opt,v 1.9 2020/05/16 22:38:25 tg Exp $");
#elif defined(SHFLAGS_ENUMS)
#define FN(sname,cname,flags,ochar) cname,
#define F0(sname,cname,flags,ochar) cname = 0,
@@ -95,7 +95,6 @@ FN("xtrace", FXTRACE, OF_ANY, 'x')
#ifndef SHFLAGS_NOT_CMD
FN("", FCOMMAND, OF_CMDLINE, 'c')
#endif
-FN("", FAS_BUILTIN, OF_INTERNAL, 0)
FN("", FTALKING_I, OF_INTERNAL, 0)
#undef F0
#undef FN
diff --git a/src/sh_flags.opt b/src/sh_flags.opt
index d81d9d9..d84d1f1 100644
--- a/src/sh_flags.opt
+++ b/src/sh_flags.opt
@@ -19,7 +19,7 @@
*/
@SHFLAGS_DEFNS
-__RCSID("$MirOS: src/bin/mksh/sh_flags.opt,v 1.8 2019/12/30 03:58:58 tg Exp $");
+__RCSID("$MirOS: src/bin/mksh/sh_flags.opt,v 1.9 2020/05/16 22:38:25 tg Exp $");
@SHFLAGS_ENUMS
#define FN(sname,cname,flags,ochar) cname,
#define F0(sname,cname,flags,ochar) cname = 0,
@@ -187,10 +187,6 @@ FN("", FCOMMAND, OF_CMDLINE
* anonymous flags: used internally by shell only (not visible to user)
*/
-/* ./. direct builtin call (divined from argv[0] multi-call binary) */
->|
-FN("", FAS_BUILTIN, OF_INTERNAL
-
/* ./. (internal) initial shell was interactive */
>|
FN("", FTALKING_I, OF_INTERNAL