Commit Graph

803 Commits

Author SHA1 Message Date
Johannes Schindelin
3bef5d89b0 ash: implement -d DELIM option for read
The POSIX standard only requires the read builtin to handle -r:
http://pubs.opengroup.org/onlinepubs/9699919799/utilities/read.html

However, Bash introduced the option -d <DELIM> to override IFS for
just one invocation, and it is quite useful.

It is also super easy to implement in BusyBox' ash, so let's do that.

The motivation: This option is used by Git's test suite.

function                                             old     new   delta
.rodata                                           163505  163587     +82
shell_builtin_read                                  1244    1289     +45
readcmd                                              233     259     +26
builtin_read                                         258     263      +5
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 4/0 up/down: 158/0)             Total: 158 bytes

Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-09 13:52:17 +02:00
Denys Vlasenko
80e8e3cc05 noexec: consolidate code
function                                             old     new   delta
run_noexec_applet_and_exit                             -      61     +61
find_applet_by_name                                  128     124      -4
run_applet_no_and_exit                               441     434      -7
tryexec                                              169     152     -17
pseudo_exec_argv                                     338     321     -17
------------------------------------------------------------------------------
(add/remove: 1/0 grow/shrink: 0/6 up/down: 61/-48)             Total: 13 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-07 19:24:57 +02:00
Denys Vlasenko
c9c1ccc4ed noexec: do GETOPT_RESET() before entering APPLET_main()
hush -c 'yes | head -1' was not happy.

function                                             old     new   delta
tryexec                                              159     169     +10
pseudo_exec_argv                                     328     338     +10

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-07 18:59:35 +02:00
Denys Vlasenko
f2cf1cc716 noexec: set comm field for noexecs
function                                             old     new   delta
set_task_comm                                          -      18     +18
tryexec                                              152     159      +7
pseudo_exec_argv                                     321     328      +7
main                                                 106      97      -9
------------------------------------------------------------------------------
(add/remove: 1/0 grow/shrink: 3/2 up/down: 34/-13)             Total: 23 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-07 18:45:33 +02:00
Denys Vlasenko
248a67fb75 free,stat: make NOEXEC
pkill/pgrep/pidof uncovered another quirk: what about noexec's _process names_?

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-07 18:18:09 +02:00
Denys Vlasenko
0f14f41e72 ash: do not set a signal to SIG_DFL if it already is
function                                             old     new   delta
setsignal                                            312     338     +26

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-06 20:06:19 +02:00
Denys Vlasenko
f8cdc7a2bc ash: BASH_XTRACEFD bashism
Based on patch by Johannes Schindelin <johannes.schindelin@gmx.de>

function                                             old     new   delta
evalcommand                                         1447    1500     +53

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-04 15:24:49 +02:00
Johannes Schindelin
7344755823 ash: remove no-longer-used variable
As of 035486c75 (ash: significant overhaul of redirect saving logic,
2017-07-31), the sv_pos variable is no longer used (just assigned to,
with no further effect).

Let's just remove it.

Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-04 14:52:08 +02:00
Denys Vlasenko
d329e34c96 ash: INT_OFF/INT_ON around run_nofork_applet()
function                                             old     new   delta
evalcommand                                         1441    1447      +6

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-04 14:50:03 +02:00
Denys Vlasenko
49e6bf2db9 sheel: improve comments on signal handling
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-04 14:28:16 +02:00
Denys Vlasenko
cfd392bea9 ash: add a fixme comment at run_nofork_applet
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-03 19:56:29 +02:00
Denys Vlasenko
84ea60ed65 line editing: make read_line_input() not take timeout param
It's almost always -1.

function                                             old     new   delta
read_line_input                                     3902    3912     +10
new_line_input_t                                      24      31      +7
pgetc                                                583     585      +2
save_command_ps_at_cur_history                        80      78      -2
read_line                                             76      74      -2
fgetc_interactive                                    246     244      -2
addLines                                              84      82      -2
doCommands                                          2226    2222      -4
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 3/5 up/down: 19/-12)              Total: 7 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-02 17:27:28 +02:00
Denys Vlasenko
95f7953f2c do not use `a' quoting style in comments
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-08-02 14:26:33 +02:00
Denys Vlasenko
ec05df13b0 ash: align --login code with dash
Upstream commit:

    Date: Sun, 13 Jul 2008 22:34:50 +0800
    [OPTIONS] Added support for -l

    This patch adds support for the -l option (login shell) as required
    by the LSB.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

It's a bit bigger, but gets rid of one global variable

function                                             old     new   delta
options                                              554     576     +22

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-31 19:43:47 +02:00
Denys Vlasenko
d0fff9155b ash: fix display of ">&-" redirect in job strings
function                                             old     new   delta
cmdtxt                                               558     569     +11

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-31 14:32:18 +02:00
Denys Vlasenko
32fdf2f9fc ash,hush: ">&10" redirects to script/tty fds should not work
The fact that shell has open fds to tty and/or scripts should be
unobservable, if possible. In particular, if redirect tries to dup
one of them via ">&script_fd", it's better to pretend that script_fd
is closed, and thus redirect fails with EBADF.

Fixes these two testcase failures:
ash-redir/redir_to_bad_fd.tests
hush-redir/redir_to_bad_fd3.tests

function                                             old     new   delta
redirect                                            1018    1129    +111
setup_redirects                                      250     359    +109
readtoken1                                          2651    2655      +4
cmdloop                                              185     187      +2
changepath                                           194     195      +1
save_fd_on_redirect                                  203     194      -9
evaltree                                             501     484     -17
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 5/2 up/down: 227/-26)           Total: 201 bytes
   text    data     bss     dec     hex filename
 914553     485    6848  921886   e111e busybox_old
 914754     485    6848  922087   e11e7 busybox_unstripped

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-31 04:35:18 +02:00
Denys Vlasenko
035486c750 ash: significant overhaul of redirect saving logic
New code is similar to what hush is doing.
Make CLOSED to -1: same as dash.
popredir() loses "restore" parameter: same as dash.
COPYFD_RESTORE bit is no longer necessary.

This change fixes this interactive bug:

	$ ls -l /proc/$$/fd 10>&-
	ash: can't set tty process group: Bad file descriptor
	ash: can't set tty process group: Bad file descriptor
	[1]+  Done(2)                    ls -l /proc/${\$}/fd 10>&4294967295

function                                             old     new   delta
unwindredir                                           29      27      -2
tryexec                                              154     152      -2
evaltree                                             503     501      -2
evalcommand                                         1369    1367      -2
cmdloop                                              187     185      -2
redirect                                            1029    1018     -11
popredir                                             153     123     -30
need_to_remember                                      36       -     -36
is_hidden_fd                                          68       -     -68
------------------------------------------------------------------------------
(add/remove: 0/2 grow/shrink: 0/7 up/down: 0/-155)           Total: -155 bytes
   text    data     bss     dec     hex filename
 914572     485    6848  921905   e1131 busybox_old
 914553     485    6848  921886   e111e busybox_unstripped

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-31 04:21:46 +02:00
Denys Vlasenko
d07a15bd1b ash: remove REDIR_SAVEFD2
function                                             old     new   delta
evalcommand                                         1364    1369      +5
redirect                                            1055    1014     -41
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 1/1 up/down: 5/-41)             Total: -36 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-31 04:05:51 +02:00
Denys Vlasenko
5f0a75f24b ash: if !ENABLE_ASH_EXPAND_PRMT, disable PSSYNTAX code
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-29 22:58:44 +02:00
Denys Vlasenko
1c79aeb6a8 ash: [REDIR] Fix popredir on abnormal exit from built-in
Upstream commit:

    Date: Thu, 27 May 2010 15:03:46 +0800
    [REDIR] Fix popredir on abnormal exit from built-in

    Just like the poplocalvar problem recently fixed, redirections
    can also be leaked in case of an abnormal exit.  This patch fixes
    it using the same method as poplocalvar, by storing the previous
    redirection state and restoring to that point.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-29 22:51:52 +02:00
Denys Vlasenko
469998015f ash: [PARSER] Add FAKEEOFMARK for expandstr
Upstream commit:

    Date: Thu, 27 Dec 2007 13:54:16 +1100
    [PARSER] Add FAKEEOFMARK for expandstr

    Previously expandstr used the string "" to indicate that it needs to be
    treated just like a here-doc except that there is no terminator.  However,
    the string "" is in fact a valid here-doc terminator so now that we deal
    with it correctly expandstr no longer works in the presence of new-lines
    in the prompt.

    This patch introduces the FAKEEOFMARK macro which does not equal any
    real EOF marker but is distinct from the NULL pointer which is used to
    indicate non-here-doc contexts.

    Thanks to Markus Triska for reporting this regression.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Unfortunately, I did not find the failing example for this old fix.

I also tweaked the code which was added by this commit:
"
Date: Mon Sep 24 18:30:02 2007 +0000
ash: fix prompt expansion (Natanael Copa <natanael.copa@gmail.com>)
"
since other parts of code do expect expandstr() to use DQSYNTAX, not PSSYNTAX.

function                                             old     new   delta
parse_stream                                        2609    2634     +25
setprompt_if                                         128     133      +5
read_profile                                          32      37      +5
evalcommand                                         1334    1339      +5
expandstr                                            122     120      -2
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 4/1 up/down: 40/-2)              Total: 38 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-29 21:12:29 +02:00
Denys Vlasenko
a732898fdd ash: [PARSER] Removed noexpand/length check on eofmark
Upstream comment:

	Date: Sun, 11 Nov 2007 14:21:23 +0800
	[PARSER] Removed noexpand/length check on eofmark

	On Tue, Oct 30, 2007 at 04:23:35AM +0000, Oleg Verych wrote:
	>
	> } 8<<""
	> ======================

	Actually this (the empty delim) only works with dash by accident.
	I've tried bash and pdksh and they both terminate on the first
	empty line which is what you would expect rather than EOF.  The
	real Korn shell does something completely different.

	I've fixed this in dash to conform to bash/pdksh.

	> In [0] it's stated, that delimiter isn't evaluated (expanded), only
	> quoiting must be checked. That if() seems to be completely bogus.

	OK I agree.  The reason it was there is because the parser would
	have already replaced the dollar sign by an internal representation.

	I've fixed it properly with this patch.

	Test case:

	        cat <<- $a
	                OK
	        $a

	        cat <<- ""
	                OK

	        echo OK

	Old result:

	        dash: Syntax error: Illegal eof marker for << redirection
	        OK

	        echo OK

	New result:

	        OK
	        OK
	        OK

function                                             old     new   delta
parsefname                                           227     152     -75
readtoken1                                          2819    2651    -168
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 0/2 up/down: 0/-243)           Total: -243 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-29 19:57:28 +02:00
Denys Vlasenko
170f93ef1b ash: "Undo all redirections" comment is wrong, delete it
No code changes.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-29 18:54:53 +02:00
Denys Vlasenko
00a1dbd230 ash: make tryexec(cmd) parameter const char
Fewer casts this way.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-29 01:20:53 +02:00
Ron Yorston
be366e5afa ash: support platforms that don't have '%m' printf specifier
The '%m' conversion specifier prints an error message based on the
current value of 'errno'.  It is available in the GNU C library,
Cygwin (since 2012), uClibc and musl.

It is not available in various BSDs, BSD-derived systems (MacOS,
Android) or Microsoft Windows.

Use a symbol defined in platform.h to control how error messages
can be formatted to display the 'errno' message.  On platforms that
support it use '%m'; on other platforms use '%s' and strerror().

On platforms that have '%m' there is essentially no change in the
size of the binary.  Otherwise:

function                                             old     new   delta
redirect                                            1287    1310     +23
xtcsetpgrp                                            27      44     +17
dup2_or_raise                                         34      51     +17
setinputfile                                         267     275      +8
.rodata                                           163379  163371      -8
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 4/1 up/down: 65/-8)              Total: 57 bytes

Signed-off-by: Ron Yorston <rmy@pobox.com>
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-28 15:39:26 +02:00
Denys Vlasenko
619d9b5e68 ash: less hackish implementation of evaltreenr()
Defining a function alias with __attribute__ ((alias("evaltree"),__noreturn__))
is not that usual, and clang had a bug which made it misunderstand
this construct.

Switch to:
ALWAYS_INLINE NORETURN evaltreenr() { evaltree(); unreachable(); }

Older gcc's do not know unreachable(), on them we pay the price of having
a few extra calls to abort():

function                                             old     new   delta
evalsubshell                                         151     156      +5
evalpipe                                             357     362      +5
argstr                                              1141    1144      +3

On newer gcc, code size does not change.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-28 15:28:33 +02:00
Denys Vlasenko
488e609203 ash: force inlining of a trivial function
function                                             old     new   delta
bltinlookup                                            5       -      -5

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-26 23:08:36 +02:00
Denys Vlasenko
b8c0bc18f0 ash: revert previous implementation of "A=1 A=2 B=$A cmd" code
Reverts this:

    commit 0e6f661e23
    Date:   Fri Feb 15 15:02:15 2008 +0000
    ash: handle "A=1 A=2 B=$A; echo $B". closes bug 947.

A different fix from upstream has been imported by previous six commits.

Last seven commits, cumulative:

function                                             old     new   delta
poplocalvars                                           -     314    +314
mklocal                                                -     288    +288
pushlocalvars                                          -      48     +48
evalcommand                                         1372    1408     +36
unwindlocalvars                                        -      22     +22
ash_main                                            1022    1029      +7
setvar                                               167     172      +5
localvar_stack                                         -       4      +4
setvareq                                             303     302      -1
evalcase                                             271     269      -2
subevalvar                                          1202    1198      -4
localvars                                              4       -      -4
cmdenviron                                             4       -      -4
expandarg                                            984     973     -11
evalvar                                              589     574     -15
argstr                                              1164    1141     -23
dotcmd                                               335     303     -32
bltinlookup                                           51       5     -46
varvalue                                             709     596    -113
evalfun                                              456     270    -186
localcmd                                             364      44    -320
------------------------------------------------------------------------------
(add/remove: 5/2 grow/shrink: 3/11 up/down: 724/-761)         Total: -37 bytes
   text	   data	    bss	    dec	    hex	filename
 915353	    485	   6888	 922726	  e1466	busybox_old
 915320	    485	   6880	 922685	  e143d	busybox_unstripped

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-26 23:03:21 +02:00
Denys Vlasenko
d04fc712e3 ash: [VAR] Fix loss of variables when hash collides
Upstream commit:

    Date: Tue, 6 Jul 2010 17:40:53 +0800
    [VAR] Fix loss of variables when hash collides

    Brian Koropoff reported that the new var patches broke the following
    script:

    #!/bin/dash
    GDM_LANG="bar"
    OPTION="foo"
    unset GDM_LANG
    # OPTION has mysteriously become unset
    echo "$OPTION"

    He correctly diagnosed this as a result of removing all variables
    in the hash chain preceding the one that should be removed in
    setvareq.

    He also provided a patch to fix this.

    This patch is based on his but without keeping the original vpp.
    As a result, we now store new variables at the end of the hash
    chain instead of the beginning.

    To make this work, setvareq/setvar now returns the vp pointer
    modified.  In case they're used to unset a variable the pointer
    returned is undefined.  This is because mklocal needs it and
    used to get it by assuming that the new variable always appear
    at the beginning of the chain.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-26 20:33:51 +02:00
Denys Vlasenko
85241c7b0b ash: [VAR] Do not poplocalvars prematurely on regular utilities
Upstream commit:

    Date: Thu, 27 May 2010 11:50:19 +0800
    [VAR] Do not poplocalvars prematurely on regular utilities

    The recent cmdenviron removal broke regular utilities by calling
    poplocalvars too early.  This patch fixes that by postponing the
    poplocalvars for regular utilities until they have completed.

    In order to ensure that local still works, it is now a special
    built-in.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-26 20:33:51 +02:00
Denys Vlasenko
484fc2056d ash: [VAR] Fix poplocalvar on abnormal exit from function
Upstream commit:

    Date: Thu, 27 May 2010 11:32:55 +0800
    [VAR] Fix poplocalvar on abnormal exit from function

    The new localvar code broke the abnormal exit from functions
    and built-ins by not restoring the original localvar state.

    This patch fixes this by storing the previous localvar state so
    that we always unwind correctly in case of an abnormal exit.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-26 20:33:51 +02:00
Denys Vlasenko
981a0568b3 ash: [VAR] Replace cmdenviron with localvars
Upstream commit:

    Date: Wed, 26 May 2010 18:54:19 +0800
    [VAR] Replace cmdenviron with localvars

    This patch replaces the cmdenviron mechanism for temporary command
    variables with the localvars mechanism used by functions.

    This reduces code size, and more importantly, makes the variable
    assignment take effect immediately as required by POSIX.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-26 20:33:51 +02:00
Denys Vlasenko
d5b500c81c ash: [VAR] Fix poplocalvar leak
Upstream commit:

    Date: Tue, 25 May 2010 18:14:32 +0800
    [VAR] Fix poplocalvar leak

    When a variable is marked as local, we set VSTRFIXED on its vp
    recored.  However, poplocalvar never clears this flag for variables
    that were unset to begin with.  Thus if you ever made an unset
    variable local, it would get the VSTRFIXED bit and stick around
    forever.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-26 20:33:51 +02:00
Denys Vlasenko
b8ab27bf53 ash: [VAR] Add localvars nesting
Upstream commit:

    Date: Mon, 24 May 2010 15:31:27 +0800
    [VAR] Add localvars nesting

    This patch adds localvars nesting infrastructure so we can reuse
    the localvars mechanism for command evaluation.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-26 20:33:51 +02:00
Denys Vlasenko
cf3a796dd1 ash: alloc slightly smaller buffer in cvtnum(); faster unsetvar()
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-26 14:38:19 +02:00
Denys Vlasenko
b31b61bb9b ash: fix redir_leak.tests if STANDALONE=y
If STANDALONE and we run a NOEXEC applet, saved copies of redirected fds
were visible for the child. They have CLOEXEC bit, yes, but we do not exec
in this case.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-26 13:42:53 +02:00
Denys Vlasenko
1e3e2ccd5d ash: [SHELL] Optimize dash -c "command" to avoid a fork
Upstream commit:

    Date: Thu, 7 Jul 2011 13:58:48 +0800
    [SHELL] Optimize dash -c "command" to avoid a fork

    On Sun, Apr 10, 2011 at 07:36:49AM +0000, Jonathan Nieder wrote:
    > From: Jilles Tjoelker <jilles@stack.nl>
    > Date: Sat, 13 Jun 2009 16:17:45 -0500
    >
    > This change only affects strings passed to -c, when the -s option is
    > not used.
    >
    > Use the EV_EXIT flag to inform the eval machinery that the string
    > being passed is the entirety of input.  This way, a fork may be
    > omitted in many special cases.
    >
    > If there are empty lines after the last command, the evalcmd will not
    > see the end early enough and forks will not be omitted. The same thing
    > seems to happen in bash.
    >
    > Example:
    >   sh -c 'ps lT'
    > No longer shows a shell process waiting for ps to finish.
    >
    > [jn: ported from FreeBSD SVN r194128.  Bugs are mine.]
    >
    > Signed-off-by: Jonathan Nieder <jrnieder@gmail.com>

    Instead of detecting EOF using the input layer, I'm going to
    use the parser instead.  In either case, we always have to read
    ahead in order to complete the parsing of the previous node.
    Therefore we always know whether there is more to come, except
    in the case where we see a newline/semicolon or similar.

    For the purposes of sh -c, this should be sufficient.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

function                                             old     new   delta
evalstring                                           190     224     +34
ash_main                                            1014    1022      +8
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 2/0 up/down: 42/0)               Total: 42 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-25 20:31:14 +02:00
Denys Vlasenko
86981e3ad2 ash: allow "trap NUM [SIG]..." syntax
While at it, make get_signum() return -1 for numeric strings >= NSIG.

function                                             old     new   delta
trapcmd                                              292     306     +14
get_signum                                           295     300      +5
builtin_trap                                         413     412      -1
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 2/1 up/down: 19/-1)              Total: 18 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-25 20:06:17 +02:00
Denys Vlasenko
f1a5cb0548 ash: [REDIR] Replace GPL noclobberopen code with the FreeBSD version
Upstream commit:

    Date: Thu, 10 Mar 2011 16:52:13 +0800
    [REDIR] Replace GPL noclobberopen code with the FreeBSD version

    Replace noclobberopen() from bash with the FreeBSD code for noclobber
    opens.

    This also reduces code size by eliminating an unnecessary check.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

function                                             old     new   delta
changepath                                           192     194      +2
localcmd                                             366     364      -2
expmeta                                              521     517      -4
redirect                                            1210    1135     -75
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 1/3 up/down: 2/-81)             Total: -79 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-25 17:47:48 +02:00
Denys Vlasenko
2990aa45d1 ash: sync up with dash with respect to redirection escaping
We fixed the problem differently than they. Let's not deviate.

Upstream commit:

    Date: Thu, 27 May 2010 20:07:29 +1000
    [EXPAND] Fix corruption of redirections with byte 0x81

    In other ash variants, a partial implementation of ksh-like cmd >file*
    adds and removes CTLESC bytes ('\x81') in redirection filenames,
    preserving 8-bit transparency. Long ago, dash removed the code to add
    the CTLESC bytes, but not the code to remove them, causing corruption of
    filenames containing CTLESC. This commit removes the code to remove the
    CTLESC bytes.

    The CTLESC byte occurs frequently in UTF-8 encoded non-Latin text.

    This bug has been reported various times to Ubuntu and Debian (e.g.
    Launchpad Ubuntu #422298). This patch is the same as the one submitted
    by Alexander Korolkov in Ubuntu #422298.

    Signed-off-by: Jilles Tjoelker <jilles@stack.nl>
    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

function                                             old     new   delta
changepath                                           194     192      -2
expandarg                                           1000     984     -16
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 0/2 up/down: 0/-18)             Total: -18 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-25 17:37:57 +02:00
Denys Vlasenko
b28d4c3462 ash: [VAR] Move unsetvar functionality into setvareq
Upstream commit:

    Date: Tue, 25 May 2010 20:55:05 +0800
    [VAR] Move unsetvar functionality into setvareq

    This patch moves the unsetvar code into setvareq so that we can
    no have a pathological case of an unset variable hanging around
    unless it has a bit pinning it like VEXPORT.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

function                                             old     new   delta
setvareq                                             227     303     +76
expmeta                                              517     521      +4
localcmd                                             364     366      +2
unsetcmd                                              96      76     -20
unsetvar                                             129       7    -122
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 3/2 up/down: 82/-142)           Total: -60 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-25 16:29:36 +02:00
Denys Vlasenko
5c123ac208 ash: fix comment, no code changes
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-24 20:03:24 +02:00
Denys Vlasenko
94af83eb8d ash: fix for last commit
"mempcpy(q, s, len) + len" is obviously no good :(

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-23 21:55:40 +02:00
Denys Vlasenko
5ace96a713 ash: use mempcpy() in more places
Most changes are taken from dash.

function                                             old     new   delta
single_quote                                         127     129      +2
stack_nputstr                                         28      29      +1
path_advance                                         209     202      -7
rmescapes                                            346     308     -38
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 2/2 up/down: 3/-45)             Total: -42 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-23 21:46:34 +02:00
Denys Vlasenko
da2244fe48 ash: use mempcpy() where appropriate
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-21 18:51:29 +02:00
Denys Vlasenko
42ba757d5e ash: improve set -x to quote strings as necessary
Basen on the patch from Martijn Dekker <martijn@inlv.org>

function                                             old     new   delta
evalcommand                                         1161    1302    +141
maybe_single_quote                                     -      60     +60
getoptscmd                                           527     546     +19
readtoken1                                          2819    2823      +4
localcmd                                             366     364      -2
evaltreenr                                           495     479     -16
evaltree                                             495     479     -16
------------------------------------------------------------------------------
(add/remove: 1/0 grow/shrink: 3/3 up/down: 224/-34)           Total: 190 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-21 13:20:14 +02:00
Denys Vlasenko
72089cf6b4 config: deindent all help texts
Those two spaces after tab have no effect, and always a nuisance when editing.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-21 09:50:55 +02:00
Denys Vlasenko
8ecd861406 ash: remove contradicting size info in config help
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-18 22:25:12 +02:00
Denys Vlasenko
4eed2c6c50 Update menuconfig items with approximate applet sizes
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-18 22:01:24 +02:00
Denys Vlasenko
826360ff23 ash: more general format ${var:EXPR:EXPR}
function                                             old     new   delta
subevalvar                                          1171    1202     +31
localcmd                                             364     366      +2

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-17 17:49:11 +02:00
Denys Vlasenko
4f8079de87 ash: "you disabled math" is wrong: user did not disable it, builder of ash did
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-17 17:11:48 +02:00
Denys Vlasenko
203fd7bc66 shells: expand TODO comments, no code changes
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-17 16:13:35 +02:00
Johannes Schindelin
9d4dc84a76 ash: protect WIFSTOPPED use with #if JOBS
This change fixes the build in setups where there are
no headers defining WIFSTOPPED and WSTOPSIG (where JOBS has to be
set to 0).

This partially reverts 4700fb5be (ash: make dowait() a bit more
readable. Logic is unchanged, 2015-10-09).

Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-15 11:38:00 +02:00
Denys Vlasenko
69a5ec9dcc main: fix the case where user has "halt" as login shell. Closes 9986
halt::0:0::/:/sbin/halt

function                                             old     new   delta
run_applet_and_exit                                  748     751      +3
run_applet_no_and_exit                               467     459      -8

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-07 19:08:56 +02:00
Denys Vlasenko
bd43c6784f hush: fix quoted_punct.tests failure
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-05 23:12:15 +02:00
Denys Vlasenko
4142f0187d ash: fix escaping of a few characters (broken by last commits)
Add a testcase which tests all ASCII punctuation escapes.
NB: hush is failing this test!

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-05 22:19:28 +02:00
Denys Vlasenko
ed79a63623 ash: tweak in comment
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-05 19:20:43 +02:00
Denys Vlasenko
92b8d9c9fa ash: note which versions of glibc exhibit "rho bug"
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-05 19:13:44 +02:00
Denys Vlasenko
fda9fafe27 ash: fix matching of unicode greek letter rho (cf 81) and similar cases
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-05 19:10:21 +02:00
Denys Vlasenko
48c803a206 ash: fix $HOME/.profile reading if !ASH_EXPAND_PRMT, take 2
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-01 23:26:12 +02:00
Denys Vlasenko
e9aba3e7ea ash: fix 'trap - 65'
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-07-01 21:09:27 +02:00
Denys Vlasenko
f56ddf2e4c ash: fix $HOME/.profile reading if !ASH_EXPAND_PRMT
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-06-27 17:51:07 +02:00
Youfu Zhang
6683d1cbb4 ash: fix incorrect path in describe_command
$ PATH=/extra/path:/usr/sbin:/usr/bin:/sbin:/bin \
> busybox sh -xc 'command -V ls; command -V ls; command -Vp ls; command -vp ls'
+ command -V ls
ls is /bin/ls
+ command -V ls
ls is a tracked alias for /bin/ls
+ command -Vp ls
ls is a tracked alias for (null)
+ command -vp ls
Segmentation fault

describe_command should respect `path' argument. Looking up in the hash table
may gives incorrect index in entry.u.index and finally causes incorrect output
or SIGSEGV.

function                                             old     new   delta
describe_command                                     386     313     -73

Signed-off-by: Youfu Zhang <zhangyoufu@gmail.com>
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-05-26 17:37:35 +02:00
Denys Vlasenko
f547041940 ash,hush: fix SIGCHLD interrupting read builtin
function                                             old     new   delta
readcmd                                              169     217     +48
shell_builtin_read                                  1087    1097     +10
localcmd                                             366     364      -2
builtin_read                                         197     193      -4
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 2/2 up/down: 58/-6)              Total: 52 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-05-22 19:34:45 +02:00
Denys Vlasenko
10ad622dc2 Spelling fixes in comments, documentation, tests and examples
By klemens <ka7@github.com>

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-04-17 16:13:32 +02:00
Denys Vlasenko
6c149f4d9a ash: implement "exec -a ARGV0 CMD ARGV1..."
function                                             old     new   delta
execcmd                                               71     112     +41
shellexec                                            221     224      +3
evalcommand                                         1158    1161      +3
localcmd                                             364     366      +2
unaliascmd                                           163     154      -9
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 4/1 up/down: 49/-9)              Total: 40 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-04-12 21:31:32 +02:00
Denys Vlasenko
e139ae307e ash: make shellexec capable of using separate argv[0] and filename to exec
function                                             old     new   delta
execcmd                                               71      78      +7
shellexec                                            221     224      +3
evalcommand                                         1158    1161      +3
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 3/0 up/down: 13/0)               Total: 13 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-04-12 21:02:33 +02:00
Denys Vlasenko
5f7c82b32f ash: add INT_OFF/ON around allocations
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-02-03 13:00:06 +01:00
Felix Fietkau
b5b21126ca ash: improve / fix glob expansion
When using musl libc glob() a very long string can cause glob() to fail,
which leads to an out of memory error being raised by ash.

This can happen easily if a very long quoted string contains *, even
though no glob expansion should ever be performed on it (since it's
quoted).

Fix this by properly parsing control characters and escaping and only
accept unquoted metacharacters. While we're at it, unify this check for
libc and built-in glob expansion

Signed-off-by: Felix Fietkau <nbd@nbd.name>
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-31 21:58:55 +01:00
Denys Vlasenko
205d48e948 *: add comment about APPLET_ODDNAME format
It confused me more than once

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-29 14:57:33 +01:00
Denys Vlasenko
098b713c7b ash: commented-out possible fix for 7694
bash has a feature: it restores termios after a successful wait for
a foreground job which had at least one stopped or sigkilled member.
The probable rationale is that SIGSTOP and SIGKILL can preclude task from
properly restoring tty state. Should we do this too?
A reproducer: ^Z an interactive python:

$ python
Python 2.7.12 (...)
>>> ^Z
    { python leaves tty in -icanon -echo state. We do survive that... }
 [1]+  Stopped                    python
    { ...however, next program (python no.2) does not survive it well: }
$ python
Python 2.7.12 (...)
>>> Traceback (most recent call last):
    { above, I typed "qwerty<CR>", but -echo state is still in effect }
  File "<stdin>", line 1, in <module>
NameError: name 'qwerty' is not defined

The implementation is modeled on bash code and seems to work.
However, I'm not sure we should do this. For one: what if I'd fg
the stopped python instead? It'll be confused by "restored" tty state.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-11 19:59:03 +01:00
Denys Vlasenko
4c179373e0 ash: 16-bit ->nprocs field is a pain for many CPUs
function                                             old     new   delta
getoptscmd                                           527     540     +13
getjob                                               280     286      +6
makejob                                              278     282      +4
forkchild                                            602     600      -2
waitcmd                                              208     205      -3
showjob                                              382     379      -3
getstatus                                             83      80      -3
dowait                                               408     405      -3
freejob                                               93      89      -4
fg_bgcmd                                             290     286      -4
forkshell                                            260     255      -5
killcmd                                              224     218      -6
jobno                                                 17      11      -6
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 3/10 up/down: 23/-39)           Total: -16 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-11 18:44:15 +01:00
Denys Vlasenko
7d4aec0c3e ash: split bash compatible extensions into separate defines. No code changes
Splitting these options makes it self-documenting about what
bash-compatible features we have.

Signed-off-by: Kang-Che Sung <explorer09@gmail.com>
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-11 14:00:38 +01:00
Denys Vlasenko
2b4c258e74 ash: revert "make dot command search current directory first"
Reverts this:
    commit 8ad78e1ec7
    Author: Denis Vlasenko <vda.linux@googlemail.com>
    Date:   Sun Feb 15 12:40:30 2009 +0000
    ash: make dot command search current directory first, as bash does.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-10 15:18:38 +01:00
Denys Vlasenko
265062d59d shells: make hush test optional, rename ASH_BUILTIN_foo -> ASH_foo
This makes hash and ash more symmetrical wrt config menu and config
options.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-10 15:13:30 +01:00
Denys Vlasenko
f560422fa0 Big cleanup in config help and description
Redundant help texts (one which only repeats the description)
are deleted.

Descriptions and help texts are trimmed.

Some config options are moved, even across menus.

No config option _names_ are changed.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-10 14:58:54 +01:00
Denys Vlasenko
fb87d93d1e ash: fix a bug in argv restoration after sourcing a file
if sourced file "shift"ed argvs so that $1 is NULL, restore wasn't done.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-09 08:22:06 +01:00
Denys Vlasenko
86584e134e ash: fix open fds leaking in redirects. Closes 9561
commit e19923f665 deleted clearredir()
call in shellexec():

	ash: [REDIR] Remove redundant CLOEXEC calls
	Upstream commit:

	Now that we're marking file descriptors as CLOEXEC in savefd, we no longer
	need to close them on exec or in setinputfd.

but it missed one place where we don't set CLOEXEC. Fixing this.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-07 10:16:56 +01:00
Kang-Che Sung
6cd0294725 ash: explicltly group ash options
This would makes all ash options indented inside "ash" in menuconfig.
It appears that menuconfig has a limit at tracking multiple dependency
lines like this (it looks like a "diamond problem" but I'm not sure if
it is):

               ---ASH <----------
              /                  \       ASH_OPTIMIZE_FOR_SIZE
    !NOMMU <-*----SH_IS_ASH <----[OR] <--ASH_INTERNAL_GLOB
              \                  /       ASH_RANDOM_SUPPORT
               ---BASH_IS_ASH <--        [...]

The kconfig-language document [1] states that:

> If a menu entry somehow depends on the previous entry, it can be
> made a submenu of it. First, the previous (parent) symbol must be
> part of the dependency list and then one of these two conditions
> must be true:
> - the child entry must become invisible, if the parent is set to 'n'

    [BusyBox ash used to satisfy this, but no longer does]

> - the child entry must only be visible, if the parent is visible

    [BusyBox ash configs actually satisfy this, but because of
     "diamond" above this might not be easily detected]

So I found out a direct workaround: by making ash options explicitly
depend on !NOMMU, we can tell menuconfig that rule 2 above is satisfied
without any more tracking.

               ---------------------
              /                     \
    !NOMMU <-*-----ASH <--------     \
              \                 \     \        ASH_OPTIMIZE_FOR_SIZE
               *---SH_IS_ASH <---[OR]-[AND] <--ASH_INTERNAL_GLOB
                \                /             ASH_RANDOM_SUPPORT
                 --BASH_IS_ASH <-              [...]

So all ash options would now be indented under "ash".

[1] "Documentation/kbuild/kconfig-language.txt" in Linux kernel source

Signed-off-by: Kang-Che Sung <explorer09@gmail.com>
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-06 17:03:18 +01:00
Ron Yorston
ea7d2f6ec0 ash: fix error code regression
The commit 'ash,hush: set exit code 127 in "sh /does/not/exist" case'
only partly implemented the dash commit '[ERROR] Allow the originator
of EXERROR to set the exit status'.  This resulted in incorrect error
codes for a syntax error:

   $ )
   $ echo $?
   0

or a redirection error for a special builtin:

   $ rm -f xxx
   $ eval cat <xxx
   $ echo $?
   0

Signed-off-by: Ron Yorston <rmy@pobox.com>
Reported-by: Martijn Dekker <martijn@inlv.org>
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2017-01-03 11:18:23 +01:00
Denys Vlasenko
0b8835861b Make it possible to select "sh" and "bash" aliases without selecting ash or hush
The same can be done for msh, but we are probably better off just deleting it
in a next versio or two.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-12-23 16:56:43 +01:00
Denys Vlasenko
6704746c69 shell: move "config" blocks above their use in coditional includes
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-12-22 15:21:58 +01:00
Denys Vlasenko
326edc3e37 Tweak some config defaults; fix MODPROBE_SMALL ordering in "make config"
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-12-22 14:36:49 +01:00
Denys Vlasenko
2166952ec3 ash: clarify uclibc glob() bug in comment
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-12-21 21:04:16 +01:00
Denys Vlasenko
3a4cdf45f9 ash: error out if ASH_INTERNAL_GLOB is not selected on uClibc
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-12-21 04:13:23 +01:00
Denys Vlasenko
2fe66b1d2d ash: fix signed char expansion bug
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-12-12 17:39:12 +01:00
Denys Vlasenko
b6afcc7819 shell: suppress "unused var/func" warnings on some configs
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-12-12 16:30:20 +01:00
Denys Vlasenko
4b89d512b1 ash,hush: make ^C in interactive mode visually much closer to bash behavior
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-11-25 03:41:03 +01:00
Denys Vlasenko
8660aeb312 ash,hush: ^C from command line should set $? to 128+SIGINT
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-11-24 17:44:02 +01:00
Denys Vlasenko
15fb91cefb test: make [ and [[ forms individually selectable
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-11-23 18:31:48 +01:00
Denys Vlasenko
06b114900f ash: fix "duplicate local" code (forgot to re-enable interrupts)
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-11-04 16:43:18 +01:00
Denys Vlasenko
1ab7c2fc6d ash: while (!got_sig) pause() is not reliable, use sigsuspend()
dash was doing it for a reason. Unfortunately, it had no comment why...
now I know.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-11-03 20:22:54 +01:00
Denys Vlasenko
d4f3db9427 ash: if using libc glob(), skip it if no metachars are in word
This saves making tons of pointless stat() calls

function                                             old     new   delta
expandarg                                            888     921     +33

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-10-30 18:41:01 +01:00
Denys Vlasenko
474ed06c39 ash: fix bit-rotten debug infrastructure
DEBUG = 2 output was a bit messed up

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-10-30 18:30:29 +01:00
Denys Vlasenko
493b9cae80 ash: make popfile() anfter popallfiles() safe
In this example:

	ash -c 'readonly x; echo $(command eval x=2)'

evalstring() is called after forkchild(), which calls popallfiles().
On exception, evalstring() will popfile().

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-10-30 18:27:14 +01:00
Denys Vlasenko
8f7b0248ad ash: use pause(), not sigsuspend(), in wait builtin
Same effect, smaller code

function                                             old     new   delta
dowait                                               463     374     -89

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-10-28 17:16:11 +02:00
Denys Vlasenko
d81e9f5093 ash: fix interactive "command eval STRING" exiting on errors.
This bug is also present in current dash

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-10-28 15:43:50 +02:00
Denys Vlasenko
458c1f218b ash: [JOBS] Fix dowait signal race
Upstream commit:

    Date: Sun, 22 Feb 2009 18:10:01 +0800
    [JOBS] Fix dowait signal race

    This test program by Alexey Gladkov can cause dash to enter an
    infinite loop in waitcmd.

    #!/bin/dash
    trap "echo TRAP" USR1
    stub() {
        echo ">>> STUB $1" >&2
        sleep $1
        echo "<<< STUB $1" >&2
        kill -USR1 $$
    }
    stub 3 &
    stub 2 &
    until { echo "###"; wait; } do
    echo "*** $?"
    done

    The problem is that if we get a signal after the wait3 system
    call has returned but before we get to INTON in dowait, then
    we can jump back up to the top and lose the exit status.  So
    if we then wait for the job that has just exited, then it'll
    stay there forever.

    I made the original change that caused this bug to fix pretty
    much the same bug but in the opposite direction.  That is, if
    we get a signal after we enter wait3 but before we hit the kernel
    then it too can cause the wait to go on forever (assuming the
    child doesn't exit).

    In fact this is pretty much exactly the scenario that you'll
    find in glibc's documentation on pause().  The solution is given
    there too, in the form of sigsuspend, which is the only way to
    do the check and wait atomically.

    So this patch fixes Alexey's race without reintroducing the old
    bug by converting the blocking wait3 to a sigsuspend.

    In order to do this we need to set a signal handler for SIGCHLD,
    so the code has been modified to always do that.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

I failed to reproduce the bug (it requires precise timing), but it seems real.

function                                             old     new   delta
dowait                                               284     463    +179
setsignal                                            301     326     +25
signal_handler                                        59      76     +17
ash_main                                            1481    1487      +6
localcmd                                             350     348      -2
------------------------------------------------------------------------------
(add/remove: 0/0 grow/shrink: 4/1 up/down: 227/-2)            Total: 225 bytes

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-10-27 23:51:19 +02:00
Denys Vlasenko
c0663c7cd2 ash: [SIGNAL] Remove EXSIG
Upstream commit 1:

    Date: Sun, 22 Feb 2009 18:16:13 +0800
    [SIGNAL] Remove EXSIG

    Now that waitcmd no longer uses EXSIG we can remove it.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Upstream commit 2:

    Date: Thu, 2 Oct 2014 21:07:55 +0800
    [ERROR] Set exitstatus in onint

    Currently the exit status when we receive SIGINT is set in evalcommand
    which means that it doesn't always get set.  For example, if you press
    CTRL-C at the prompt of an interactive dash, the exit status is not
    set to 130 as it is in many other Bourne shells.

    This patch fixes this by moving the setting of the exit status into
    onint which also simplifies evalcommand.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Upstream commit 3:

    Date: Fri, 3 Oct 2014 14:07:07 +0800
    [EVAL] Do not clobber exitstatus in evalcommand

    All originators of EXERROR have been setting the exitstatus for
    a while now.  So it is no longer appropriate to set it explicitly
    in evalcommand.

    In fact doing so may cause the original exitstatus to be lost.

    Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Last three coomits:
function                                             old     new   delta
waitcmd                                              186     224     +38
dowait                                               276     284      +8
waitforjob                                           104     107      +3
localcmd                                             348     350      +2
showjobs                                              64      61      -3
forkshell                                            263     260      -3
raise_interrupt                                       93      67     -26
blocking_wait_with_raise_on_sig                       40       -     -40
evalcommand                                         1264    1208     -56
evaltree                                             809     498    -311

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-10-27 21:13:49 +02:00
Denys Vlasenko
6918811014 ash: open-code blocking_dowait_with_raise_on_sig()
There is in fact only one callsite.

Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
2016-10-27 21:13:24 +02:00