mirror of
https://https.git.savannah.gnu.org/git/bash.git
synced 2026-06-21 12:57:58 +02:00
commit bash-20180817 snapshot
This commit is contained in:
+52
-1
@@ -3229,7 +3229,7 @@ doc/{bash.1,bashref.texi}
|
||||
2/1
|
||||
---
|
||||
config-top.h
|
||||
- DONT_REPORT_SIGPIPE: define, so non-interactive shells will no
|
||||
- DONT_REPORT_SIGTERM: define, so non-interactive shells will no
|
||||
longer print termination messages for child processes killed by
|
||||
SIGTERM
|
||||
|
||||
@@ -4186,3 +4186,54 @@ builtins/declare.def
|
||||
configure.ac
|
||||
- globasciiranges: RRI now on by default, must be turned off explicitly
|
||||
at configure time or runtime with `shopt -u globasciiranges'
|
||||
|
||||
8/14
|
||||
----
|
||||
variables.c
|
||||
- dispose_saved_dollar_vars: decrement stack pointer before looking
|
||||
for saved positional parameters to dispose; stack pointer always
|
||||
points to the first unused slot
|
||||
|
||||
8/15
|
||||
----
|
||||
variables.c
|
||||
- dollar_arg_stack: now a stack of struct saved_dollar_vars, which has
|
||||
an array for the first ten (dollar_vars) and a WORD_LIST * for the
|
||||
remaining (rest_of_args). Fixes performance issue with function calls
|
||||
and large numbers of positional parameters raised by
|
||||
Bize Ma <binaryzebra@gmail.com>
|
||||
- {save,restore,free,free_saved}_dollar_vars: new functions to manage
|
||||
dollar_vars and dollar_arg_stack members. Need to keep these in sync
|
||||
with whatever remember_args does
|
||||
- push_dollar_vars: use save_dollar_vars, which just copies pointers,
|
||||
and directly assign rest_of_args, without copying the words, to the
|
||||
dollar_arg_stack entry. Have to clear dollar_vars and rest_of_args
|
||||
with the assumption that callers will call remember_args(args, 1)
|
||||
immediately following
|
||||
- pop_dollar_vars: free current positional parameters and restore old
|
||||
ones from pointers saved in dollar_arg_stack, making sure to
|
||||
invalidate any cached value for "$@"
|
||||
- dispose_saved_dollar_vars: free saved pointers from current index
|
||||
into dollar_arg_stack
|
||||
|
||||
doc/{bash.1,bashref.texi}
|
||||
- POSIXLY_CORRECT: make sure to note that bash makes sure this variable
|
||||
is set when posix mode is enabled
|
||||
|
||||
8/17
|
||||
----
|
||||
{jobs,nojobs}.c
|
||||
- set_jobs_list_frozen: set jobs_list_frozen to a particular value.
|
||||
Intended to save and restore the value around code sections instead
|
||||
of unconditionally unfreezing it.
|
||||
|
||||
jobs.h
|
||||
- set_jobs_list_frozen: extern declaration
|
||||
|
||||
execute_cmd.c
|
||||
- execute_pipeline: if lastpipe is enabled, save and restore the
|
||||
value of jobs_list_frozen using freeze_jobs_list/set_jobs_list_frozen
|
||||
to avoid problems with race conditions and nested pipelines
|
||||
causing jobs to be removed from the jobs table. Fixes savannah issue
|
||||
https://savannah.gnu.org/support/index.php?109541 reported by
|
||||
Bj枚rn Kautler <vampire0>
|
||||
|
||||
@@ -1376,6 +1376,8 @@ tests/varenv11.sub f
|
||||
tests/varenv12.sub f
|
||||
tests/varenv13.sub f
|
||||
tests/varenv14.sub f
|
||||
tests/varenv15.sub f
|
||||
tests/varenv15.in f
|
||||
tests/version f
|
||||
tests/version.mini f
|
||||
tests/vredir.tests f
|
||||
|
||||
Vendored
+1
-1
@@ -1307,7 +1307,7 @@ AC_CACHE_VAL(bash_cv_must_reinstall_sighandlers,
|
||||
|
||||
typedef RETSIGTYPE sigfunc();
|
||||
|
||||
int nsigint;
|
||||
volatile int nsigint;
|
||||
|
||||
#ifdef HAVE_POSIX_SIGNALS
|
||||
sigfunc *
|
||||
|
||||
@@ -199,6 +199,8 @@ bind_array_var_internal (entry, ind, key, value, flags)
|
||||
FREE (newval);
|
||||
|
||||
VUNSETATTR (entry, att_invisible); /* no longer invisible */
|
||||
|
||||
/* check mark_modified_variables if we ever want to export array vars */
|
||||
return (entry);
|
||||
}
|
||||
|
||||
|
||||
@@ -15257,7 +15257,7 @@ else
|
||||
|
||||
typedef RETSIGTYPE sigfunc();
|
||||
|
||||
int nsigint;
|
||||
volatile int nsigint;
|
||||
|
||||
#ifdef HAVE_POSIX_SIGNALS
|
||||
sigfunc *
|
||||
|
||||
@@ -2414,6 +2414,8 @@ running, \fBbash\fP enables \fIposix mode\fP, as if the command
|
||||
.if t \f(CWset -o posix\fP
|
||||
.if n \fIset -o posix\fP
|
||||
had been executed.
|
||||
When the shell enters \fIposix mode\fP, it sets this variable if it was
|
||||
not already set.
|
||||
.TP
|
||||
.B PROMPT_COMMAND
|
||||
If set, the value is executed as a command prior to issuing each primary
|
||||
|
||||
+6
-1
@@ -6189,7 +6189,9 @@ as if the command
|
||||
@code{set -o posix}
|
||||
@end example
|
||||
@noindent
|
||||
had been executed.
|
||||
had been executed.
|
||||
When the shell enters @sc{posix} mode, it sets this variable if it was
|
||||
not already set.
|
||||
|
||||
@item PPID
|
||||
The process @sc{id} of the shell's parent process. This variable
|
||||
@@ -7528,6 +7530,9 @@ startup files.
|
||||
The following list is what's changed when `@sc{posix} mode' is in effect:
|
||||
|
||||
@enumerate
|
||||
@item
|
||||
Bash ensures that the @env{POSIXLY_CORRECT} variable is set.
|
||||
|
||||
@item
|
||||
When a command in the hash table no longer exists, Bash will re-search
|
||||
@env{$PATH} to find the new location. This is also available with
|
||||
|
||||
+4
-4
@@ -2448,7 +2448,7 @@ execute_pipeline (command, asynchronous, pipe_in, pipe_out, fds_to_close)
|
||||
struct fd_bitmap *fds_to_close;
|
||||
{
|
||||
int prev, fildes[2], new_bitmap_size, dummyfd, ignore_return, exec_result;
|
||||
int lstdin, lastpipe_flag, lastpipe_jid;
|
||||
int lstdin, lastpipe_flag, lastpipe_jid, old_frozen;
|
||||
COMMAND *cmd;
|
||||
struct fd_bitmap *fd_bitmap;
|
||||
pid_t lastpid;
|
||||
@@ -2563,7 +2563,7 @@ execute_pipeline (command, asynchronous, pipe_in, pipe_out, fds_to_close)
|
||||
prev = NO_PIPE;
|
||||
add_unwind_protect (restore_stdin, lstdin);
|
||||
lastpipe_flag = 1;
|
||||
freeze_jobs_list ();
|
||||
old_frozen = freeze_jobs_list ();
|
||||
lastpipe_jid = stop_pipeline (0, (COMMAND *)NULL); /* XXX */
|
||||
add_unwind_protect (lastpipe_cleanup, lastpipe_jid);
|
||||
}
|
||||
@@ -2611,9 +2611,9 @@ execute_pipeline (command, asynchronous, pipe_in, pipe_out, fds_to_close)
|
||||
else if (pipefail_opt)
|
||||
exec_result = exec_result | lstdin; /* XXX */
|
||||
/* otherwise we use exec_result */
|
||||
|
||||
#endif
|
||||
unfreeze_jobs_list ();
|
||||
|
||||
set_jobs_list_frozen (old_frozen);
|
||||
}
|
||||
|
||||
discard_unwind_frame ("lastpipe-exec");
|
||||
|
||||
@@ -4771,6 +4771,13 @@ unfreeze_jobs_list ()
|
||||
jobs_list_frozen = 0;
|
||||
}
|
||||
|
||||
void
|
||||
set_jobs_list_frozen (s)
|
||||
int s;
|
||||
{
|
||||
jobs_list_frozen = s;
|
||||
}
|
||||
|
||||
/* Allow or disallow job control to take place. Returns the old value
|
||||
of job_control. */
|
||||
int
|
||||
|
||||
@@ -259,7 +259,8 @@ extern int give_terminal_to __P((pid_t, int));
|
||||
extern void run_sigchld_trap __P((int));
|
||||
|
||||
extern int freeze_jobs_list __P((void));
|
||||
extern void unfreeze_jobs_list __P((void));
|
||||
extern void unfreeeze_jobs_list __P((void));
|
||||
extern void set_jobs_list_frozen __P((int));
|
||||
extern int set_job_control __P((int));
|
||||
extern void without_job_control __P((void));
|
||||
extern void end_job_control __P((void));
|
||||
|
||||
@@ -142,9 +142,11 @@ extern char *fmtullong __P((unsigned long long int, int, char *, size_t, int));
|
||||
302 / 1000 is log10 (2) rounded up;
|
||||
add one for integer division truncation;
|
||||
add one more for a minus sign if t is signed. */
|
||||
#ifndef INT_STRLEN_BOUND
|
||||
#define INT_STRLEN_BOUND(t) \
|
||||
((sizeof (t) * CHAR_BIT - TYPE_SIGNED (t)) * 302 / 1000 \
|
||||
+ 1 + TYPE_SIGNED (t))
|
||||
#endif
|
||||
|
||||
/* conversion flags */
|
||||
#define PF_ALTFORM 0x00001 /* # */
|
||||
|
||||
@@ -1037,6 +1037,12 @@ unfreeze_jobs_list ()
|
||||
{
|
||||
}
|
||||
|
||||
void
|
||||
set_jobs_list_frozen (s)
|
||||
int s;
|
||||
{
|
||||
}
|
||||
|
||||
int
|
||||
count_all_jobs ()
|
||||
{
|
||||
|
||||
@@ -177,6 +177,36 @@ declare -a a=([0]="X" [1]="Y")
|
||||
declare -a s=([0]="X" [1]="Y")
|
||||
declare -a a=([0]="XY")
|
||||
declare -a s=([0]="XY")
|
||||
f: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50
|
||||
f1: after: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
|
||||
done: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100
|
||||
f3:1
|
||||
f3:2
|
||||
f3:3
|
||||
f3:4
|
||||
f3:5
|
||||
f3:6
|
||||
f3:7
|
||||
f3:8
|
||||
f3:9
|
||||
f3:10
|
||||
f3:11
|
||||
f3:12
|
||||
f3:13
|
||||
f3:14
|
||||
f3:15
|
||||
f3:16
|
||||
f3:17
|
||||
f3:18
|
||||
f3:19
|
||||
f3:20
|
||||
before source: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
|
||||
varenv15.in: before set: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
|
||||
varenv15.in: after set: a b c d e f g h i j k l m n o p q r s t u v w x y z
|
||||
after source 1: a b c d e f g h i j k l m n o p q r s t u v w x y z
|
||||
varenv15.in: before set: one two three four five six seven eight nine ten
|
||||
varenv15.in: after set: a b c d e f g h i j k l m n o p q r s t u v w x y z
|
||||
after source 2: a b c d e f g h i j k l m n o p q r s t u v w x y z
|
||||
a=z
|
||||
a=b
|
||||
a=z
|
||||
|
||||
@@ -240,5 +240,7 @@ ${THIS_SH} ./varenv13.sub
|
||||
# localvar_inherit
|
||||
${THIS_SH} ./varenv14.sub
|
||||
|
||||
${THIS_SH} ./varenv15.sub
|
||||
|
||||
# make sure variable scoping is done right
|
||||
tt() { typeset a=b;echo a=$a; };a=z;echo a=$a;tt;echo a=$a
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
echo varenv15.in: before set: "$@"
|
||||
set -- a b c d e f g h i j k l m n o p q r s t u v w x y z
|
||||
echo varenv15.in: after set: "$@"
|
||||
@@ -0,0 +1,38 @@
|
||||
# check saving and restoring positional parameters around function calls
|
||||
|
||||
f()
|
||||
{
|
||||
echo $FUNCNAME: "$@"
|
||||
}
|
||||
|
||||
f1()
|
||||
{
|
||||
f {1..50}
|
||||
echo $FUNCNAME: after: $@
|
||||
}
|
||||
|
||||
set -- {1..100}
|
||||
|
||||
f1 {1..20}
|
||||
echo done: $@
|
||||
|
||||
f3()
|
||||
{
|
||||
echo $FUNCNAME:$1
|
||||
shift
|
||||
if [ $# -le 0 ]; then
|
||||
return
|
||||
fi
|
||||
f3 "$@"
|
||||
}
|
||||
|
||||
f3 {1..20}
|
||||
|
||||
# now let's try source with and without positional parameters
|
||||
|
||||
set -- {1..20}
|
||||
echo before source: "$@"
|
||||
. ./varenv15.in
|
||||
echo after source 1: "$@"
|
||||
. ./varenv15.in one two three four five six seven eight nine ten
|
||||
echo after source 2: "$@"
|
||||
+84
-12
@@ -5290,10 +5290,64 @@ pop_scope (is_special)
|
||||
/* */
|
||||
/* **************************************************************** */
|
||||
|
||||
static WORD_LIST **dollar_arg_stack = (WORD_LIST **)NULL;
|
||||
struct saved_dollar_vars {
|
||||
char **first_ten;
|
||||
WORD_LIST *rest;
|
||||
};
|
||||
|
||||
static struct saved_dollar_vars *dollar_arg_stack = (struct saved_dollar_vars *)NULL;
|
||||
static int dollar_arg_stack_slots;
|
||||
static int dollar_arg_stack_index;
|
||||
|
||||
/* Functions to manipulate dollar_vars array. Need to keep these in sync with
|
||||
whatever remember_args() does. */
|
||||
static char **
|
||||
save_dollar_vars ()
|
||||
{
|
||||
char **ret;
|
||||
int i;
|
||||
|
||||
ret = strvec_create (10);
|
||||
for (i = 1; i < 10; i++)
|
||||
{
|
||||
ret[i] = dollar_vars[i];
|
||||
dollar_vars[i] = (char *)NULL;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void
|
||||
restore_dollar_vars (args)
|
||||
char **args;
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 1; i < 10; i++)
|
||||
dollar_vars[i] = args[i];
|
||||
}
|
||||
|
||||
static void
|
||||
free_dollar_vars ()
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 1; i < 10; i++)
|
||||
{
|
||||
FREE (dollar_vars[i]);
|
||||
dollar_vars[i] = (char *)NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
free_saved_dollar_vars (args)
|
||||
char **args;
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 1; i < 10; i++)
|
||||
FREE (args[i]);
|
||||
}
|
||||
|
||||
/* XXX - should always be followed by remember_args () */
|
||||
void
|
||||
push_context (name, is_subshell, tempvars)
|
||||
@@ -5325,35 +5379,53 @@ push_dollar_vars ()
|
||||
{
|
||||
if (dollar_arg_stack_index + 2 > dollar_arg_stack_slots)
|
||||
{
|
||||
dollar_arg_stack = (WORD_LIST **)
|
||||
dollar_arg_stack = (struct saved_dollar_vars *)
|
||||
xrealloc (dollar_arg_stack, (dollar_arg_stack_slots += 10)
|
||||
* sizeof (WORD_LIST *));
|
||||
* sizeof (struct saved_dollar_vars));
|
||||
}
|
||||
dollar_arg_stack[dollar_arg_stack_index++] = list_rest_of_args ();
|
||||
dollar_arg_stack[dollar_arg_stack_index] = (WORD_LIST *)NULL;
|
||||
|
||||
dollar_arg_stack[dollar_arg_stack_index].first_ten = save_dollar_vars ();
|
||||
dollar_arg_stack[dollar_arg_stack_index++].rest = rest_of_args;
|
||||
rest_of_args = (WORD_LIST *)NULL;
|
||||
|
||||
dollar_arg_stack[dollar_arg_stack_index].first_ten = (char **)NULL;
|
||||
dollar_arg_stack[dollar_arg_stack_index].rest = (WORD_LIST *)NULL;
|
||||
}
|
||||
|
||||
/* Restore the positional parameters from our stack. */
|
||||
void
|
||||
pop_dollar_vars ()
|
||||
{
|
||||
if (!dollar_arg_stack || dollar_arg_stack_index == 0)
|
||||
if (dollar_arg_stack == 0 || dollar_arg_stack_index == 0)
|
||||
return;
|
||||
|
||||
remember_args (dollar_arg_stack[--dollar_arg_stack_index], 1);
|
||||
dispose_words (dollar_arg_stack[dollar_arg_stack_index]);
|
||||
dollar_arg_stack[dollar_arg_stack_index] = (WORD_LIST *)NULL;
|
||||
/* Do what remember_args (xxx, 1) would have done. */
|
||||
free_dollar_vars ();
|
||||
dispose_words (rest_of_args);
|
||||
|
||||
rest_of_args = dollar_arg_stack[--dollar_arg_stack_index].rest;
|
||||
restore_dollar_vars (dollar_arg_stack[dollar_arg_stack_index].first_ten);
|
||||
free (dollar_arg_stack[dollar_arg_stack_index].first_ten);
|
||||
|
||||
dollar_arg_stack[dollar_arg_stack_index].first_ten = (char **)NULL;
|
||||
dollar_arg_stack[dollar_arg_stack_index].rest = (WORD_LIST *)NULL;
|
||||
|
||||
set_dollar_vars_unchanged ();
|
||||
invalidate_cached_quoted_dollar_at ();
|
||||
}
|
||||
|
||||
void
|
||||
dispose_saved_dollar_vars ()
|
||||
{
|
||||
if (!dollar_arg_stack || dollar_arg_stack_index == 0)
|
||||
if (dollar_arg_stack == 0 || dollar_arg_stack_index == 0)
|
||||
return;
|
||||
|
||||
dispose_words (dollar_arg_stack[dollar_arg_stack_index]);
|
||||
dollar_arg_stack[dollar_arg_stack_index] = (WORD_LIST *)NULL;
|
||||
dispose_words (dollar_arg_stack[--dollar_arg_stack_index].rest);
|
||||
free_saved_dollar_vars (dollar_arg_stack[dollar_arg_stack_index].first_ten);
|
||||
free (dollar_arg_stack[dollar_arg_stack_index].first_ten);
|
||||
|
||||
dollar_arg_stack[dollar_arg_stack_index].first_ten = (char **)NULL;
|
||||
dollar_arg_stack[dollar_arg_stack_index].rest = (WORD_LIST *)NULL;
|
||||
}
|
||||
|
||||
/* Initialize BASH_ARGV and BASH_ARGC after turning on extdebug after the
|
||||
|
||||
Reference in New Issue
Block a user