mirror of
https://https.git.savannah.gnu.org/git/bash.git
synced 2026-06-29 08:29:54 +02:00
commit bash-20190308 snapshot
This commit is contained in:
@@ -5459,3 +5459,51 @@ subst.c
|
||||
string (after dequoting) is not null. For instance ${v= ''} should
|
||||
not have the SAWQUOTEDNULL flag set because it is " " after
|
||||
expansion and dequoting, even though we saw a quoted null there
|
||||
|
||||
3/6
|
||||
---
|
||||
lib/sh/eaccess.c
|
||||
- sh_eaccess: AIX needs the same kind of additional checks as FreeBSD
|
||||
and Solaris when running as root and checking whether or not a file
|
||||
is executable. Report and fix from REIX, Tony <tony.reix@atos.net>
|
||||
|
||||
3/7
|
||||
---
|
||||
lib/glob/glob.h
|
||||
- GX_RECURSE: new flag, indicates internal call to glob_filename
|
||||
|
||||
lib/glob/glob.c
|
||||
- glob_filename: add GX_RECURSE to recursive call to glob_filename
|
||||
- glob_filename: dequote a directory name (in the absence of a
|
||||
filename) only if this is not a recursive call to glob_filename
|
||||
((flags & GX_RECURSE) == 0). Fixes bug reported by Dr. Werner Fink
|
||||
<werner@suse.de>
|
||||
|
||||
3/8
|
||||
---
|
||||
parse.y
|
||||
- handle_eof_input_unit: before calling exit_builtin, set
|
||||
last_shell_builtin and this_shell_builtin appropriately, since the
|
||||
exit builtin uses them to determine whether or not to exit
|
||||
immediately. Fixes bug reported by Tom Levy <tomlevy93@gmail.com>
|
||||
|
||||
lib/sh/shquote.c
|
||||
- sh_double_quote,sh_mkdoublequoted,sh_backslash_quote_for_double_quotes:
|
||||
make sure to handle multibyte characters that may contain characters
|
||||
that need to be quoted in double quotes; adding a spurious double
|
||||
quote may turn them into different characters or uncover characters
|
||||
that are special in double quotes. Fixes bug reported by
|
||||
Stephane Chazelas <stephane.chazelas@gmail.com>
|
||||
- sh_backslash_quote: don't call COPY_CHAR_P if we're in a UTF-8
|
||||
locale and the current character doesn't have its eighth bit set;
|
||||
only check mb_cur_max and is_basic if we're not in a UTF-8 character
|
||||
set
|
||||
|
||||
3/9
|
||||
---
|
||||
subst.c
|
||||
- read_comsub: if it looks like we're starting a multibyte character,
|
||||
read a whole multibyte character from buf and add it all at once,
|
||||
so we don't quote each byte in a multibyte character sequence. Fixes
|
||||
bug uncovered by shquote changes from 3/8
|
||||
|
||||
|
||||
@@ -5360,6 +5360,9 @@ command under
|
||||
.SM
|
||||
.B "SHELL BUILTIN COMMANDS"
|
||||
below).
|
||||
This can have unwanted side effects if escaped portions of the string
|
||||
appear within command substitution or contain characters special to
|
||||
word expansion.
|
||||
.SH READLINE
|
||||
This is the library that handles reading input when using an interactive
|
||||
shell, unless the
|
||||
|
||||
@@ -7490,6 +7490,9 @@ After the string is decoded, it is expanded via
|
||||
parameter expansion, command substitution, arithmetic
|
||||
expansion, and quote removal, subject to the value of the
|
||||
@code{promptvars} shell option (@pxref{The Shopt Builtin}).
|
||||
This can have unwanted side effects if escaped portions of the string
|
||||
appear within command substitution or contain characters special to
|
||||
word expansion.
|
||||
|
||||
@node The Restricted Shell
|
||||
@section The Restricted Shell
|
||||
|
||||
+11
-2
@@ -1194,7 +1194,7 @@ glob_filename (pathname, flags)
|
||||
if (d[directory_len - 1] == '/')
|
||||
d[directory_len - 1] = '\0';
|
||||
|
||||
directories = glob_filename (d, dflags);
|
||||
directories = glob_filename (d, dflags|GX_RECURSE);
|
||||
|
||||
if (free_dirname)
|
||||
{
|
||||
@@ -1351,11 +1351,20 @@ only_filename:
|
||||
free (directory_name);
|
||||
return (NULL);
|
||||
}
|
||||
if (directory_len > 0 && hasglob == 2) /* need to dequote */
|
||||
/* If we have a directory name with quoted characters, and we are
|
||||
being called recursively to glob the directory portion of a pathname,
|
||||
we need to dequote the directory name before returning it so the
|
||||
caller can read the directory */
|
||||
if (directory_len > 0 && hasglob == 2 && (flags & GX_RECURSE) != 0)
|
||||
{
|
||||
dequote_pathname (directory_name);
|
||||
directory_len = strlen (directory_name);
|
||||
}
|
||||
|
||||
/* We could check whether or not the dequoted directory_name is a
|
||||
directory and return it here, returning the original directory_name
|
||||
if not, but we don't do that yet. I'm not sure it matters. */
|
||||
|
||||
/* Handle GX_MARKDIRS here. */
|
||||
result[0] = (char *) malloc (directory_len + 1);
|
||||
if (result[0] == NULL)
|
||||
|
||||
@@ -30,6 +30,7 @@
|
||||
#define GX_NULLDIR 0x100 /* internal -- no directory preceding pattern */
|
||||
#define GX_ADDCURDIR 0x200 /* internal -- add passed directory name */
|
||||
#define GX_GLOBSTAR 0x400 /* turn on special handling of ** */
|
||||
#define GX_RECURSE 0x800 /* internal -- glob_filename called recursively */
|
||||
|
||||
extern int glob_pattern_p __P((const char *));
|
||||
extern char **glob_vector __P((char *, char *, int));
|
||||
|
||||
+2
-2
@@ -213,10 +213,10 @@ sh_eaccess (path, mode)
|
||||
# else /* HAVE_EACCESS */ /* FreeBSD */
|
||||
ret = eaccess (path, mode); /* XXX -- not always correct for X_OK */
|
||||
# endif /* HAVE_EACCESS */
|
||||
# if defined (__FreeBSD__) || defined (SOLARIS)
|
||||
# if defined (__FreeBSD__) || defined (SOLARIS) || defined (_AIX)
|
||||
if (ret == 0 && current_user.euid == 0 && mode == X_OK)
|
||||
return (sh_stataccess (path, mode));
|
||||
# endif /* __FreeBSD__ || SOLARIS */
|
||||
# endif /* __FreeBSD__ || SOLARIS || _AIX */
|
||||
return ret;
|
||||
#elif defined (EFF_ONLY_OK) /* SVR4(?), SVR4.2 */
|
||||
return access (path, mode|EFF_ONLY_OK);
|
||||
|
||||
+59
-14
@@ -1,6 +1,6 @@
|
||||
/* shquote - functions to quote and dequote strings */
|
||||
|
||||
/* Copyright (C) 1999-2015 Free Software Foundation, Inc.
|
||||
/* Copyright (C) 1999-2019 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Bash, the Bourne Again SHell.
|
||||
|
||||
@@ -136,8 +136,15 @@ sh_double_quote (string)
|
||||
const char *string;
|
||||
{
|
||||
register unsigned char c;
|
||||
int mb_cur_max;
|
||||
char *result, *r;
|
||||
const char *s;
|
||||
size_t slen;
|
||||
const char *s, *send;
|
||||
DECLARE_MBSTATE;
|
||||
|
||||
slen = strlen (string);
|
||||
send = string + slen;
|
||||
mb_cur_max = MB_CUR_MAX;
|
||||
|
||||
result = (char *)xmalloc (3 + (2 * strlen (string)));
|
||||
r = result;
|
||||
@@ -148,12 +155,19 @@ sh_double_quote (string)
|
||||
/* Backslash-newline disappears within double quotes, so don't add one. */
|
||||
if ((sh_syntaxtab[c] & CBSDQUOTE) && c != '\n')
|
||||
*r++ = '\\';
|
||||
#if 0
|
||||
/* Assume that the string will not be further expanded. */
|
||||
else if (c == CTLESC || c == CTLNUL)
|
||||
*r++ = CTLESC; /* could be '\\'? */
|
||||
|
||||
#if defined (HANDLE_MULTIBYTE)
|
||||
if ((locale_utf8locale && (c & 0x80)) ||
|
||||
(locale_utf8locale == 0 && mb_cur_max > 1 && is_basic (c) == 0))
|
||||
{
|
||||
COPY_CHAR_P (r, s, send);
|
||||
s--; /* compensate for auto-increment in loop above */
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Assume that the string will not be further expanded, so no need to
|
||||
add CTLESC to protect CTLESC or CTLNUL. */
|
||||
*r++ = c;
|
||||
}
|
||||
|
||||
@@ -171,16 +185,29 @@ sh_mkdoublequoted (s, slen, flags)
|
||||
int slen, flags;
|
||||
{
|
||||
char *r, *ret;
|
||||
int rlen;
|
||||
const char *send;
|
||||
int rlen, mb_cur_max;
|
||||
DECLARE_MBSTATE;
|
||||
|
||||
send = s + slen;
|
||||
mb_cur_max = flags ? MB_CUR_MAX : 1;
|
||||
rlen = (flags == 0) ? slen + 3 : (2 * slen) + 1;
|
||||
ret = r = (char *)xmalloc (rlen);
|
||||
|
||||
|
||||
*r++ = '"';
|
||||
while (*s)
|
||||
{
|
||||
if (flags && *s == '"')
|
||||
*r++ = '\\';
|
||||
|
||||
#if defined (HANDLE_MULTIBYTE)
|
||||
if (flags && ((locale_utf8locale && (*s & 0x80)) ||
|
||||
(locale_utf8locale == 0 && mb_cur_max > 1 && is_basic (*s) == 0)))
|
||||
{
|
||||
COPY_CHAR_P (r, s, send);
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
*r++ = *s++;
|
||||
}
|
||||
*r++ = '"';
|
||||
@@ -259,7 +286,8 @@ sh_backslash_quote (string, table, flags)
|
||||
*r++ = c;
|
||||
continue;
|
||||
}
|
||||
if (mb_cur_max > 1 && is_basic (c) == 0)
|
||||
if ((locale_utf8locale && (c & 0x80)) ||
|
||||
(locale_utf8locale == 0 && mb_cur_max > 1 && is_basic (c) == 0))
|
||||
{
|
||||
COPY_CHAR_P (r, s, send);
|
||||
s--; /* compensate for auto-increment in loop above */
|
||||
@@ -291,18 +319,35 @@ sh_backslash_quote_for_double_quotes (string)
|
||||
char *string;
|
||||
{
|
||||
unsigned char c;
|
||||
char *result, *r, *s;
|
||||
|
||||
result = (char *)xmalloc (2 * strlen (string) + 1);
|
||||
char *result, *r, *s, *send;
|
||||
size_t slen;
|
||||
int mb_cur_max;
|
||||
DECLARE_MBSTATE;
|
||||
|
||||
slen = strlen (string);
|
||||
send = string + slen;
|
||||
mb_cur_max = MB_CUR_MAX;
|
||||
result = (char *)xmalloc (2 * slen + 1);
|
||||
|
||||
for (r = result, s = string; s && (c = *s); s++)
|
||||
{
|
||||
if (sh_syntaxtab[c] & CBSDQUOTE)
|
||||
/* Backslash-newline disappears within double quotes, so don't add one. */
|
||||
if ((sh_syntaxtab[c] & CBSDQUOTE) && c != '\n')
|
||||
*r++ = '\\';
|
||||
/* I should probably add flags for these to sh_syntaxtab[] */
|
||||
/* I should probably use the CSPECL flag for these in sh_syntaxtab[] */
|
||||
else if (c == CTLESC || c == CTLNUL)
|
||||
*r++ = CTLESC; /* could be '\\'? */
|
||||
|
||||
#if defined (HANDLE_MULTIBYTE)
|
||||
if ((locale_utf8locale && (c & 0x80)) ||
|
||||
(locale_utf8locale == 0 && mb_cur_max > 1 && is_basic (c) == 0))
|
||||
{
|
||||
COPY_CHAR_P (r, s, send);
|
||||
s--; /* compensate for auto-increment in loop above */
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
||||
*r++ = c;
|
||||
}
|
||||
|
||||
|
||||
@@ -6361,6 +6361,9 @@ handle_eof_input_unit ()
|
||||
|
||||
/* In this case EOF should exit the shell. Do it now. */
|
||||
reset_parser ();
|
||||
|
||||
last_shell_builtin = this_shell_builtin;
|
||||
this_shell_builtin = exit_builtin;
|
||||
exit_builtin ((WORD_LIST *)NULL);
|
||||
}
|
||||
else
|
||||
|
||||
@@ -6037,11 +6037,18 @@ read_comsub (fd, quoted, flags, rflag)
|
||||
int fd, quoted, flags;
|
||||
int *rflag;
|
||||
{
|
||||
char *istring, buf[128], *bufp;
|
||||
char *istring, buf[512], *bufp;
|
||||
int istring_index, c, tflag, skip_ctlesc, skip_ctlnul;
|
||||
int mb_cur_max;
|
||||
size_t istring_size;
|
||||
ssize_t bufn;
|
||||
int nullbyte;
|
||||
#if defined (HANDLE_MULTIBYTE)
|
||||
mbstate_t ps;
|
||||
wchar_t wc;
|
||||
size_t mblen;
|
||||
int i;
|
||||
#endif
|
||||
|
||||
istring = (char *)NULL;
|
||||
istring_index = istring_size = bufn = tflag = 0;
|
||||
@@ -6049,6 +6056,7 @@ read_comsub (fd, quoted, flags, rflag)
|
||||
skip_ctlesc = ifs_cmap[CTLESC];
|
||||
skip_ctlnul = ifs_cmap[CTLNUL];
|
||||
|
||||
mb_cur_max = MB_CUR_MAX;
|
||||
nullbyte = 0;
|
||||
|
||||
/* Read the output of the command through the pipe. This may need to be
|
||||
@@ -6079,7 +6087,7 @@ read_comsub (fd, quoted, flags, rflag)
|
||||
}
|
||||
|
||||
/* Add the character to ISTRING, possibly after resizing it. */
|
||||
RESIZE_MALLOCED_BUFFER (istring, istring_index, 2, istring_size, DEFAULT_ARRAY_SIZE);
|
||||
RESIZE_MALLOCED_BUFFER (istring, istring_index, mb_cur_max+1, istring_size, DEFAULT_ARRAY_SIZE);
|
||||
|
||||
/* This is essentially quote_string inline */
|
||||
if ((quoted & (Q_HERE_DOCUMENT|Q_DOUBLE_QUOTES)) /* || c == CTLESC || c == CTLNUL */)
|
||||
@@ -6094,6 +6102,27 @@ read_comsub (fd, quoted, flags, rflag)
|
||||
else if ((skip_ctlnul == 0 && c == CTLNUL) || (c == ' ' && (ifs_value && *ifs_value == 0)))
|
||||
istring[istring_index++] = CTLESC;
|
||||
|
||||
#if defined (HANDLE_MULTIBYTE)
|
||||
if ((locale_utf8locale && (c & 0x80)) ||
|
||||
(locale_utf8locale == 0 && mb_cur_max > 1 && (unsigned char)c > 127))
|
||||
{
|
||||
/* read a multibyte character from buf */
|
||||
/* punt on the hard case for now */
|
||||
memset (&ps, '\0', sizeof (mbstate_t));
|
||||
mblen = mbrtowc (&wc, bufp-1, bufn+1, &ps);
|
||||
if (MB_INVALIDCH (mblen) || mblen == 0 || mblen == 1)
|
||||
istring[istring_index++] = c;
|
||||
else
|
||||
{
|
||||
istring[istring_index++] = c;
|
||||
for (i = 0; i < mblen-1; i++)
|
||||
istring[istring_index++] = *bufp++;
|
||||
bufn -= mblen - 1;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
||||
istring[istring_index++] = c;
|
||||
|
||||
#if 0
|
||||
@@ -10250,9 +10279,7 @@ add_twochars:
|
||||
a special case; it's the only case where a quoted string
|
||||
can expand into more than one word. It's going to come back
|
||||
from the above call to expand_word_internal as a list with
|
||||
a single word, in which all characters are quoted and
|
||||
separated by blanks. What we want to do is to turn it back
|
||||
into a list for the next piece of code. */
|
||||
multiple words. */
|
||||
if (list)
|
||||
dequote_list (list);
|
||||
|
||||
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
BUILD_DIR=/usr/local/build/chet/bash/bash-current
|
||||
BUILD_DIR=/usr/local/build/bash/bash-current
|
||||
THIS_SH=$BUILD_DIR/bash
|
||||
PATH=$PATH:$BUILD_DIR
|
||||
|
||||
|
||||
+25
-6
@@ -63,12 +63,31 @@ a?
|
||||
aa
|
||||
<define\/\
|
||||
/>
|
||||
/tmp/a/b/c /tmp/a/b/c /tmp/a/b/c
|
||||
/tmp/a/b/c /tmp/a/b/c /tmp/a/b/c
|
||||
/tmp/a/b/c
|
||||
/tmp/a/b/c
|
||||
/tmp\/a/b/c
|
||||
/tm[p]\/a/b/c
|
||||
./tmp/a/b/c ./tmp/a/b/c ./tmp/a/b/c
|
||||
./tmp/a/b/c ./tmp/a/b/c ./tmp/a/b/c
|
||||
./tmp/a/b/c
|
||||
./tmp/a/b/c
|
||||
./tmp\/a/b/c
|
||||
./tm[p]\/a/b/c
|
||||
./tmp/a/b/c
|
||||
argv[1] = <./tmp/a/*>
|
||||
argv[1] = <./tmp/a/*>
|
||||
argv[1] = <./tmp/a/b/c>
|
||||
argv[1] = <./tmp/a/*>
|
||||
argv[1] = <./tmp/a/b/c>
|
||||
argv[1] = <./t\mp/a/*>
|
||||
argv[1] = <./tmp/a/b/c>
|
||||
argv[1] = <./tmp/a/>
|
||||
argv[1] = <./tmp/a/b/>
|
||||
argv[1] = <./t\mp/a/>
|
||||
argv[1] = <./t\mp/a/b/>
|
||||
argv[1] = <./tmp/a/*>
|
||||
argv[1] = <./tmp/a/b/c>
|
||||
argv[1] = <./tmp/a>
|
||||
argv[1] = <./tmp/a/b*>
|
||||
argv[1] = <./tmp/a>
|
||||
argv[1] = <./tmp/a/b*>
|
||||
argv[1] = <./tmp/>
|
||||
argv[1] = <a>
|
||||
argv[2] = <abc>
|
||||
argv[3] = <abd>
|
||||
|
||||
+49
-11
@@ -1,16 +1,54 @@
|
||||
mkdir -m700 /tmp/a /tmp/a/b
|
||||
touch /tmp/a/b/c
|
||||
ORIGD=$PWD
|
||||
: ${TMPDIR:=/var/tmp}
|
||||
|
||||
echo /tmp/a/b/* "/tmp/a/"b/* "/tmp/a/b"/*
|
||||
SD=$TMPDIR/scratch-$$
|
||||
[ -d $SD ] || mkdir $SD
|
||||
cd $SD
|
||||
mkdir tmp
|
||||
|
||||
chmod -r /tmp/a
|
||||
echo /tmp/a/b/* "/tmp/a/"b/* "/tmp/a/b"/*
|
||||
echo "/tmp/a/b"/*
|
||||
D=./tmp/a
|
||||
D1='./t\mp/a'
|
||||
|
||||
mkdir -m700 ./tmp/a ./tmp/a/b
|
||||
touch ./tmp/a/b/c
|
||||
|
||||
echo ./tmp/a/b/* "./tmp/a/"b/* "./tmp/a/b"/*
|
||||
|
||||
chmod -r ./tmp/a
|
||||
echo ./tmp/a/b/* "./tmp/a/"b/* "./tmp/a/b"/*
|
||||
echo "./tmp/a/b"/*
|
||||
|
||||
bs=\\
|
||||
echo /tmp${bs}/a/b/*
|
||||
echo /tmp${bs}/a/b/c
|
||||
echo /tm[p]${bs}/a/b/c
|
||||
echo ./tmp${bs}/a/b/*
|
||||
echo ./tmp${bs}/a/b/c
|
||||
echo ./tm[p]${bs}/a/b/c
|
||||
echo ./t${bs}mp/a/b/*
|
||||
|
||||
chmod +r /tmp/a
|
||||
rm -rf /tmp/a
|
||||
recho "./tmp/a"/*
|
||||
recho "$D"/*
|
||||
recho "$D"/b/*
|
||||
|
||||
recho $D/*
|
||||
recho $D/b/*
|
||||
recho $D1/*
|
||||
recho $D1/b/*
|
||||
recho $D/
|
||||
recho $D/b/
|
||||
recho $D1/
|
||||
recho $D1/b/
|
||||
|
||||
recho ./t\mp/a/*
|
||||
recho ./t\mp/a/b/*
|
||||
|
||||
recho ./tmp/a*
|
||||
recho ./tmp/a/b*
|
||||
recho ./t\mp/a*
|
||||
recho ./t\mp/a/b*
|
||||
|
||||
recho ./t\mp/
|
||||
|
||||
chmod +r ./tmp/a
|
||||
rm -rf ./tmp/a
|
||||
|
||||
cd $ORIGD
|
||||
rm -rf $SD
|
||||
|
||||
Reference in New Issue
Block a user