mirror of
https://https.git.savannah.gnu.org/git/bash.git
synced 2026-06-29 08:29:54 +02:00
commit bash-20060621 snapshot
This commit is contained in:
@@ -13456,3 +13456,59 @@ execute_cmd.c
|
||||
Gillmor <dkg-debian.org@fifthhorseman.net>
|
||||
|
||||
[bash-3.2-alpha frozen]
|
||||
|
||||
6/22
|
||||
----
|
||||
syntax.h
|
||||
- add new CBLANK (for [:blank:] class) flag value for syntax table and
|
||||
shellblank(c) character test macro
|
||||
|
||||
mksyntax.c
|
||||
- add support for setting CBLANK flag in the syntax table depending on
|
||||
whether or not isblank(x) returns true for character x
|
||||
|
||||
locale.c
|
||||
- change locale_setblanks to set or unset CBLANK flag for each
|
||||
character when locale changes
|
||||
|
||||
parse.y
|
||||
- change call to whitespace(c) in lexical analyzer (read_token()) to
|
||||
call shellblank(c) instead, so locale-specific blank characters are
|
||||
treated as white space. Fixes bug reported by Serge van deb Boom
|
||||
<svdb+bug-bash@stack.nl>
|
||||
|
||||
print_cmd.c
|
||||
- when printing redirections, add a space between <, >, and <> and the
|
||||
following word, to avoid conflicts with process substitution. Bug
|
||||
reported by Ittay Dror <ittyad@qlusters.com>
|
||||
|
||||
6/26
|
||||
----
|
||||
configure.in
|
||||
- set CROSS_COMPILE to the empty string by default, so we don't inherit
|
||||
a random value from the environment
|
||||
|
||||
6/29
|
||||
----
|
||||
lib/glob/xmbsrtowcs.c
|
||||
- make sure destp is non-null before assigning a 0 to *destp in
|
||||
xdupmbstowcs. Fix from Louiwa Salem <loulwas@us.ibm.com>
|
||||
|
||||
execute_cmd.c
|
||||
- fix execute_in_subshell to make sure asynchronous isn't set to 0
|
||||
before subshell_environment is set appropriately and
|
||||
setup_async_signals is run. Based on report by Louiwa Salem
|
||||
<loulwas@us.ibm.com>
|
||||
|
||||
lib/readline/bind.c
|
||||
- in rl_generic_bind(), make sure that the keys array is freed before
|
||||
an error return. Fix from Louiwa Salem <loulwas@us.ibm.com>
|
||||
|
||||
7/1
|
||||
---
|
||||
builtins/read.def
|
||||
- make sure all editing code is protected with #ifdef READLINE, esp.
|
||||
unwind-protect that restores the default completion function
|
||||
|
||||
lib/readline/display.c
|
||||
- make sure to set local_prompt_len in rl_message()
|
||||
|
||||
@@ -13454,3 +13454,57 @@ execute_cmd.c
|
||||
strings from overwriting the command strings associated with jobs
|
||||
and printed in job control messages. Bug reported by Daniel Kahn
|
||||
Gillmor <dkg-debian.org@fifthhorseman.net>
|
||||
|
||||
[bash-3.2-alpha frozen]
|
||||
|
||||
6/22
|
||||
----
|
||||
syntax.h
|
||||
- add new CBLANK (for [:blank:] class) flag value for syntax table and
|
||||
shellblank(c) character test macro
|
||||
|
||||
mksyntax.c
|
||||
- add support for setting CBLANK flag in the syntax table depending on
|
||||
whether or not isblank(x) returns true for character x
|
||||
|
||||
locale.c
|
||||
- change locale_setblanks to set or unset CBLANK flag for each
|
||||
character when locale changes
|
||||
|
||||
parse.y
|
||||
- change call to whitespace(c) in lexical analyzer (read_token()) to
|
||||
call shellblank(c) instead, so locale-specific blank characters are
|
||||
treated as white space. Fixes bug reported by Serge van deb Boom
|
||||
<svdb+bug-bash@stack.nl>
|
||||
|
||||
print_cmd.c
|
||||
- when printing redirections, add a space between <, >, and <> and the
|
||||
following word, to avoid conflicts with process substitution. Bug
|
||||
reported by Ittay Dror <ittyad@qlusters.com>
|
||||
|
||||
6/26
|
||||
----
|
||||
configure.in
|
||||
- set CROSS_COMPILE to the empty string by default, so we don't inherit
|
||||
a random value from the environment
|
||||
|
||||
6/29
|
||||
----
|
||||
lib/glob/xmbsrtowcs.c
|
||||
- make sure destp is non-null before assigning a 0 to *destp in
|
||||
xdupmbstowcs. Fix from Louiwa Salem <loulwas@us.ibm.com>
|
||||
|
||||
execute_cmd.c
|
||||
- fix execute_in_subshell to make sure asynchronous isn't set to 0
|
||||
before subshell_environment is set appropriately and
|
||||
setup_async_signals is run. Based on report by Louiwa Salem
|
||||
<loulwas@us.ibm.com>
|
||||
|
||||
lib/readline/bind.c
|
||||
- in rl_generic_bind(), make sure that the keys array is freed before
|
||||
an error return. Fix from Louiwa Salem <loulwas@us.ibm.com>
|
||||
|
||||
7/1
|
||||
---
|
||||
lib/readline/display.c
|
||||
- make sure to set local_prompt_len in rl_message()
|
||||
|
||||
+28596
File diff suppressed because it is too large
Load Diff
+121
-12
@@ -17,19 +17,19 @@
|
||||
{
|
||||
'm4_pattern_forbid' => 1,
|
||||
'AC_CONFIG_LIBOBJ_DIR' => 1,
|
||||
'AC_TYPE_OFF_T' => 1,
|
||||
'AC_C_VOLATILE' => 1,
|
||||
'AC_TYPE_OFF_T' => 1,
|
||||
'AC_FUNC_CLOSEDIR_VOID' => 1,
|
||||
'AC_REPLACE_FNMATCH' => 1,
|
||||
'AC_PROG_LIBTOOL' => 1,
|
||||
'AC_FUNC_STAT' => 1,
|
||||
'AC_FUNC_WAIT3' => 1,
|
||||
'AC_HEADER_TIME' => 1,
|
||||
'AM_AUTOMAKE_VERSION' => 1,
|
||||
'AC_STRUCT_TM' => 1,
|
||||
'AC_FUNC_WAIT3' => 1,
|
||||
'AC_FUNC_LSTAT' => 1,
|
||||
'AC_FUNC_GETMNTENT' => 1,
|
||||
'AC_STRUCT_TM' => 1,
|
||||
'AM_AUTOMAKE_VERSION' => 1,
|
||||
'AC_TYPE_MODE_T' => 1,
|
||||
'AC_FUNC_GETMNTENT' => 1,
|
||||
'AC_FUNC_STRTOD' => 1,
|
||||
'AC_CHECK_HEADERS' => 1,
|
||||
'AC_FUNC_STRNLEN' => 1,
|
||||
@@ -48,17 +48,17 @@
|
||||
'AC_STRUCT_ST_BLOCKS' => 1,
|
||||
'AC_TYPE_SIGNAL' => 1,
|
||||
'AC_TYPE_UID_T' => 1,
|
||||
'AC_PROG_MAKE_SET' => 1,
|
||||
'AC_CONFIG_AUX_DIR' => 1,
|
||||
'm4_pattern_allow' => 1,
|
||||
'AC_PROG_MAKE_SET' => 1,
|
||||
'sinclude' => 1,
|
||||
'm4_pattern_allow' => 1,
|
||||
'AC_DEFINE_TRACE_LITERAL' => 1,
|
||||
'AC_FUNC_STRERROR_R' => 1,
|
||||
'AC_PROG_CC' => 1,
|
||||
'AC_DECL_SYS_SIGLIST' => 1,
|
||||
'AC_FUNC_FORK' => 1,
|
||||
'AC_FUNC_STRCOLL' => 1,
|
||||
'AC_DECL_SYS_SIGLIST' => 1,
|
||||
'AC_FUNC_VPRINTF' => 1,
|
||||
'AC_FUNC_STRCOLL' => 1,
|
||||
'AC_PROG_YACC' => 1,
|
||||
'AC_INIT' => 1,
|
||||
'AC_STRUCT_TIMEZONE' => 1,
|
||||
@@ -80,13 +80,122 @@
|
||||
'AM_MAINTAINER_MODE' => 1,
|
||||
'AC_FUNC_UTIME_NULL' => 1,
|
||||
'AC_FUNC_SELECT_ARGTYPES' => 1,
|
||||
'AC_HEADER_STAT' => 1,
|
||||
'AC_FUNC_STRFTIME' => 1,
|
||||
'AC_HEADER_STAT' => 1,
|
||||
'AC_PROG_CPP' => 1,
|
||||
'AC_C_INLINE' => 1,
|
||||
'AC_TYPE_PID_T' => 1,
|
||||
'AC_PROG_LEX' => 1,
|
||||
'AC_C_CONST' => 1,
|
||||
'AC_CONFIG_FILES' => 1,
|
||||
'include' => 1,
|
||||
'AC_FUNC_SETVBUF_REVERSED' => 1,
|
||||
'AC_PROG_INSTALL' => 1,
|
||||
'AM_GNU_GETTEXT' => 1,
|
||||
'AC_CHECK_LIB' => 1,
|
||||
'AC_FUNC_OBSTACK' => 1,
|
||||
'AC_FUNC_MALLOC' => 1,
|
||||
'AC_FUNC_GETGROUPS' => 1,
|
||||
'AC_FUNC_GETLOADAVG' => 1,
|
||||
'AH_OUTPUT' => 1,
|
||||
'AC_FUNC_FSEEKO' => 1,
|
||||
'AM_PROG_CC_C_O' => 1,
|
||||
'AC_FUNC_MKTIME' => 1,
|
||||
'AC_CANONICAL_SYSTEM' => 1,
|
||||
'AM_CONDITIONAL' => 1,
|
||||
'AC_CONFIG_HEADERS' => 1,
|
||||
'AC_HEADER_SYS_WAIT' => 1,
|
||||
'AC_FUNC_MEMCMP' => 1,
|
||||
'AC_PROG_LN_S' => 1,
|
||||
'm4_include' => 1,
|
||||
'AC_HEADER_DIRENT' => 1,
|
||||
'AC_CHECK_FUNCS' => 1
|
||||
}
|
||||
], 'Autom4te::Request' ),
|
||||
bless( [
|
||||
'1',
|
||||
1,
|
||||
[
|
||||
'/usr/share/autoconf'
|
||||
],
|
||||
[
|
||||
'/usr/share/autoconf/autoconf/autoconf.m4f',
|
||||
'aclocal.m4',
|
||||
'configure.in'
|
||||
],
|
||||
{
|
||||
'm4_pattern_forbid' => 1,
|
||||
'AC_CONFIG_LIBOBJ_DIR' => 1,
|
||||
'AC_TYPE_OFF_T' => 1,
|
||||
'AC_C_VOLATILE' => 1,
|
||||
'AC_FUNC_CLOSEDIR_VOID' => 1,
|
||||
'AC_REPLACE_FNMATCH' => 1,
|
||||
'AC_PROG_LIBTOOL' => 1,
|
||||
'AC_FUNC_STAT' => 1,
|
||||
'AC_HEADER_TIME' => 1,
|
||||
'AC_FUNC_WAIT3' => 1,
|
||||
'AM_AUTOMAKE_VERSION' => 1,
|
||||
'AC_STRUCT_TM' => 1,
|
||||
'AC_FUNC_LSTAT' => 1,
|
||||
'AC_TYPE_MODE_T' => 1,
|
||||
'AC_FUNC_GETMNTENT' => 1,
|
||||
'AC_FUNC_STRTOD' => 1,
|
||||
'AC_CHECK_HEADERS' => 1,
|
||||
'AC_FUNC_STRNLEN' => 1,
|
||||
'm4_sinclude' => 1,
|
||||
'AC_PROG_CXX' => 1,
|
||||
'AC_PATH_X' => 1,
|
||||
'AC_FUNC_LSTAT_FOLLOWS_SLASHED_SYMLINK' => 1,
|
||||
'AC_PROG_AWK' => 1,
|
||||
'_m4_warn' => 1,
|
||||
'AC_HEADER_STDC' => 1,
|
||||
'AC_HEADER_MAJOR' => 1,
|
||||
'AC_FUNC_ERROR_AT_LINE' => 1,
|
||||
'AC_PROG_GCC_TRADITIONAL' => 1,
|
||||
'AC_LIBSOURCE' => 1,
|
||||
'AC_FUNC_MBRTOWC' => 1,
|
||||
'AC_STRUCT_ST_BLOCKS' => 1,
|
||||
'AC_TYPE_SIGNAL' => 1,
|
||||
'AC_TYPE_UID_T' => 1,
|
||||
'AC_CONFIG_AUX_DIR' => 1,
|
||||
'AC_PROG_MAKE_SET' => 1,
|
||||
'sinclude' => 1,
|
||||
'm4_pattern_allow' => 1,
|
||||
'AC_DEFINE_TRACE_LITERAL' => 1,
|
||||
'AC_FUNC_STRERROR_R' => 1,
|
||||
'AC_PROG_CC' => 1,
|
||||
'AC_FUNC_FORK' => 1,
|
||||
'AC_DECL_SYS_SIGLIST' => 1,
|
||||
'AC_FUNC_VPRINTF' => 1,
|
||||
'AC_FUNC_STRCOLL' => 1,
|
||||
'AC_PROG_YACC' => 1,
|
||||
'AC_INIT' => 1,
|
||||
'AC_STRUCT_TIMEZONE' => 1,
|
||||
'AC_FUNC_CHOWN' => 1,
|
||||
'AC_SUBST' => 1,
|
||||
'AC_FUNC_ALLOCA' => 1,
|
||||
'AC_CANONICAL_HOST' => 1,
|
||||
'AC_FUNC_GETPGRP' => 1,
|
||||
'AC_PROG_RANLIB' => 1,
|
||||
'AM_INIT_AUTOMAKE' => 1,
|
||||
'AC_FUNC_SETPGRP' => 1,
|
||||
'AC_CONFIG_SUBDIRS' => 1,
|
||||
'AC_FUNC_MMAP' => 1,
|
||||
'AC_FUNC_REALLOC' => 1,
|
||||
'AC_TYPE_SIZE_T' => 1,
|
||||
'AC_CONFIG_LINKS' => 1,
|
||||
'AC_CHECK_TYPES' => 1,
|
||||
'AC_CHECK_MEMBERS' => 1,
|
||||
'AM_MAINTAINER_MODE' => 1,
|
||||
'AC_FUNC_UTIME_NULL' => 1,
|
||||
'AC_FUNC_SELECT_ARGTYPES' => 1,
|
||||
'AC_FUNC_STRFTIME' => 1,
|
||||
'AC_HEADER_STAT' => 1,
|
||||
'AC_C_INLINE' => 1,
|
||||
'AC_PROG_CPP' => 1,
|
||||
'AC_TYPE_PID_T' => 1,
|
||||
'AC_C_CONST' => 1,
|
||||
'AC_PROG_LEX' => 1,
|
||||
'AC_TYPE_PID_T' => 1,
|
||||
'AC_CONFIG_FILES' => 1,
|
||||
'include' => 1,
|
||||
'AC_FUNC_SETVBUF_REVERSED' => 1,
|
||||
@@ -105,8 +214,8 @@
|
||||
'AC_FUNC_MKTIME' => 1,
|
||||
'AC_CONFIG_HEADERS' => 1,
|
||||
'AC_HEADER_SYS_WAIT' => 1,
|
||||
'AC_PROG_LN_S' => 1,
|
||||
'AC_FUNC_MEMCMP' => 1,
|
||||
'AC_PROG_LN_S' => 1,
|
||||
'm4_include' => 1,
|
||||
'AC_HEADER_DIRENT' => 1,
|
||||
'AC_CHECK_FUNCS' => 1
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -329,8 +329,10 @@ read_builtin (list)
|
||||
}
|
||||
old_alrm = set_signal_handler (SIGALRM, sigalrm);
|
||||
add_unwind_protect (reset_alarm, (char *)NULL);
|
||||
#if defined (READLINE)
|
||||
if (edit)
|
||||
add_unwind_protect (reset_attempted_completion_function, (char *)NULL);
|
||||
#endif
|
||||
alarm (tmout);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
#! /bin/sh
|
||||
# From configure.in for Bash 3.2, version 3.188.
|
||||
# From configure.in for Bash 3.2, version 3.190.
|
||||
# Guess values for system-dependent variables and create Makefiles.
|
||||
# Generated by GNU Autoconf 2.59 for bash 3.2-alpha.
|
||||
# Generated by GNU Autoconf 2.59 for bash 3.2-beta.
|
||||
#
|
||||
# Report bugs to <bug-bash@gnu.org>.
|
||||
#
|
||||
@@ -270,8 +270,8 @@ SHELL=${CONFIG_SHELL-/bin/sh}
|
||||
# Identity of this package.
|
||||
PACKAGE_NAME='bash'
|
||||
PACKAGE_TARNAME='bash'
|
||||
PACKAGE_VERSION='3.2-alpha'
|
||||
PACKAGE_STRING='bash 3.2-alpha'
|
||||
PACKAGE_VERSION='3.2-beta'
|
||||
PACKAGE_STRING='bash 3.2-beta'
|
||||
PACKAGE_BUGREPORT='bug-bash@gnu.org'
|
||||
|
||||
ac_unique_file="shell.h"
|
||||
@@ -785,7 +785,7 @@ if test "$ac_init_help" = "long"; then
|
||||
# Omit some internal or obsolete options to make the list less imposing.
|
||||
# This message is too long to be a string in the A/UX 3.1 sh.
|
||||
cat <<_ACEOF
|
||||
\`configure' configures bash 3.2-alpha to adapt to many kinds of systems.
|
||||
\`configure' configures bash 3.2-beta to adapt to many kinds of systems.
|
||||
|
||||
Usage: $0 [OPTION]... [VAR=VALUE]...
|
||||
|
||||
@@ -846,7 +846,7 @@ fi
|
||||
|
||||
if test -n "$ac_init_help"; then
|
||||
case $ac_init_help in
|
||||
short | recursive ) echo "Configuration of bash 3.2-alpha:";;
|
||||
short | recursive ) echo "Configuration of bash 3.2-beta:";;
|
||||
esac
|
||||
cat <<\_ACEOF
|
||||
|
||||
@@ -1039,7 +1039,7 @@ fi
|
||||
test -n "$ac_init_help" && exit 0
|
||||
if $ac_init_version; then
|
||||
cat <<\_ACEOF
|
||||
bash configure 3.2-alpha
|
||||
bash configure 3.2-beta
|
||||
generated by GNU Autoconf 2.59
|
||||
|
||||
Copyright (C) 2003 Free Software Foundation, Inc.
|
||||
@@ -1053,7 +1053,7 @@ cat >&5 <<_ACEOF
|
||||
This file contains any messages produced by compilers while
|
||||
running configure, to aid debugging if configure makes a mistake.
|
||||
|
||||
It was created by bash $as_me 3.2-alpha, which was
|
||||
It was created by bash $as_me 3.2-beta, which was
|
||||
generated by GNU Autoconf 2.59. Invocation command line was
|
||||
|
||||
$ $0 $@
|
||||
@@ -1422,7 +1422,7 @@ ac_configure="$SHELL $ac_aux_dir/configure" # This should be Cygnus configure.
|
||||
|
||||
|
||||
BASHVERS=3.2
|
||||
RELSTATUS=alpha
|
||||
RELSTATUS=beta
|
||||
|
||||
case "$RELSTATUS" in
|
||||
alp*|bet*|dev*|rc*) DEBUG='-DDEBUG' MALLOC_DEBUG='-DMALLOC_DEBUG' ;;
|
||||
@@ -4118,6 +4118,7 @@ SIGNAMES_H=lsignames.h
|
||||
|
||||
|
||||
|
||||
CROSS_COMPILE=
|
||||
if test "x$cross_compiling" = "xyes"; then
|
||||
case "${host}" in
|
||||
*-cygwin*)
|
||||
@@ -27484,7 +27485,7 @@ _ASBOX
|
||||
} >&5
|
||||
cat >&5 <<_CSEOF
|
||||
|
||||
This file was extended by bash $as_me 3.2-alpha, which was
|
||||
This file was extended by bash $as_me 3.2-beta, which was
|
||||
generated by GNU Autoconf 2.59. Invocation command line was
|
||||
|
||||
CONFIG_FILES = $CONFIG_FILES
|
||||
@@ -27547,7 +27548,7 @@ _ACEOF
|
||||
|
||||
cat >>$CONFIG_STATUS <<_ACEOF
|
||||
ac_cs_version="\\
|
||||
bash config.status 3.2-alpha
|
||||
bash config.status 3.2-beta
|
||||
configured by $0, generated by GNU Autoconf 2.59,
|
||||
with options \\"`echo "$ac_configure_args" | sed 's/[\\""\`\$]/\\\\&/g'`\\"
|
||||
|
||||
|
||||
+3
-2
@@ -22,10 +22,10 @@ dnl Process this file with autoconf to produce a configure script.
|
||||
# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
|
||||
# 02111-1307, USA.
|
||||
|
||||
AC_REVISION([for Bash 3.2, version 3.188])dnl
|
||||
AC_REVISION([for Bash 3.2, version 3.190])dnl
|
||||
|
||||
define(bashvers, 3.2)
|
||||
define(relstatus, devel)
|
||||
define(relstatus, beta)
|
||||
|
||||
AC_INIT([bash], bashvers-relstatus, [bug-bash@gnu.org])
|
||||
|
||||
@@ -383,6 +383,7 @@ dnl Note that host and target machine are the same, and different than the
|
||||
dnl build machine.
|
||||
dnl Set SIGNAMES_H based on whether or not we're cross-compiling.
|
||||
|
||||
CROSS_COMPILE=
|
||||
if test "x$cross_compiling" = "xyes"; then
|
||||
case "${host}" in
|
||||
*-cygwin*)
|
||||
|
||||
+13
-2
@@ -1209,6 +1209,10 @@ execute_in_subshell (command, asynchronous, pipe_in, pipe_out, fds_to_close)
|
||||
the special case of an asynchronous GROUP command where the
|
||||
the subshell bit is turned on down in case cm_group: below),
|
||||
turn off `asynchronous', so that two subshells aren't spawned.
|
||||
XXX - asynchronous used to be set to 0 in this block, but that
|
||||
means that setup_async_signals was never run. Now it's set to
|
||||
0 after subshell_environment is set appropriately and setup_async_signals
|
||||
is run.
|
||||
|
||||
This seems semantically correct to me. For example,
|
||||
( foo ) & seems to say ``do the command `foo' in a subshell
|
||||
@@ -1236,7 +1240,6 @@ execute_in_subshell (command, asynchronous, pipe_in, pipe_out, fds_to_close)
|
||||
aliases. */
|
||||
if (ois != interactive_shell)
|
||||
expand_aliases = 0;
|
||||
asynchronous = 0;
|
||||
}
|
||||
|
||||
/* Subshells are neither login nor interactive. */
|
||||
@@ -1256,8 +1259,16 @@ execute_in_subshell (command, asynchronous, pipe_in, pipe_out, fds_to_close)
|
||||
reset_terminating_signals (); /* in sig.c */
|
||||
/* Cancel traps, in trap.c. */
|
||||
restore_original_signals ();
|
||||
|
||||
/* Make sure restore_original_signals doesn't undo the work done by
|
||||
make_child to ensure that asynchronous children are immune to SIGINT
|
||||
and SIGQUIT. Turn off asynchronous to make sure more subshells are
|
||||
not spawned. */
|
||||
if (asynchronous)
|
||||
setup_async_signals ();
|
||||
{
|
||||
setup_async_signals ();
|
||||
asynchronous = 0;
|
||||
}
|
||||
|
||||
#if defined (JOB_CONTROL)
|
||||
set_sigchld_handler ();
|
||||
|
||||
+8
-6
@@ -1209,6 +1209,10 @@ execute_in_subshell (command, asynchronous, pipe_in, pipe_out, fds_to_close)
|
||||
the special case of an asynchronous GROUP command where the
|
||||
the subshell bit is turned on down in case cm_group: below),
|
||||
turn off `asynchronous', so that two subshells aren't spawned.
|
||||
XXX - asynchronous used to be set to 0 in this block, but that
|
||||
means that setup_async_signals was never run. Now it's set to
|
||||
0 after subshell_environment is set appropriately and setup_async_signals
|
||||
is run.
|
||||
|
||||
This seems semantically correct to me. For example,
|
||||
( foo ) & seems to say ``do the command `foo' in a subshell
|
||||
@@ -1236,7 +1240,6 @@ execute_in_subshell (command, asynchronous, pipe_in, pipe_out, fds_to_close)
|
||||
aliases. */
|
||||
if (ois != interactive_shell)
|
||||
expand_aliases = 0;
|
||||
asynchronous = 0;
|
||||
}
|
||||
|
||||
/* Subshells are neither login nor interactive. */
|
||||
@@ -1257,7 +1260,10 @@ execute_in_subshell (command, asynchronous, pipe_in, pipe_out, fds_to_close)
|
||||
/* Cancel traps, in trap.c. */
|
||||
restore_original_signals ();
|
||||
if (asynchronous)
|
||||
setup_async_signals ();
|
||||
{
|
||||
setup_async_signals ();
|
||||
asynchronous = 0;
|
||||
}
|
||||
|
||||
#if defined (JOB_CONTROL)
|
||||
set_sigchld_handler ();
|
||||
@@ -3021,11 +3027,7 @@ execute_simple_command (simple_command, pipe_in, pipe_out, async, fds_to_close)
|
||||
}
|
||||
|
||||
if (command_line == 0)
|
||||
#if 0
|
||||
command_line = savestring (the_printed_command);
|
||||
#else
|
||||
command_line = savestring (the_printed_command_except_trap);
|
||||
#endif
|
||||
|
||||
execute_disk_command (words, simple_command->redirects, command_line,
|
||||
pipe_in, pipe_out, async, fds_to_close,
|
||||
|
||||
@@ -145,7 +145,8 @@ xdupmbstowcs (destp, indicesp, src)
|
||||
/* In case SRC or DESP is NULL, conversion doesn't take place. */
|
||||
if (src == NULL || destp == NULL)
|
||||
{
|
||||
*destp = NULL;
|
||||
if (destp)
|
||||
*destp = NULL;
|
||||
return (size_t)-1;
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,250 @@
|
||||
/* xmbsrtowcs.c -- replacement function for mbsrtowcs */
|
||||
|
||||
/* Copyright (C) 2002-2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Bash, the Bourne Again SHell.
|
||||
|
||||
Bash is free software; you can redistribute it and/or modify it under
|
||||
the terms of the GNU General Public License as published by the Free
|
||||
Software Foundation; either version 2, or (at your option) any later
|
||||
version.
|
||||
|
||||
Bash is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||
WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along
|
||||
with Bash; see the file COPYING. If not, write to the Free Software
|
||||
Foundation, 59 Temple Place, Suite 330, Boston, MA 02111 USA. */
|
||||
#include <config.h>
|
||||
|
||||
#include <bashansi.h>
|
||||
|
||||
/* <wchar.h>, <wctype.h> and <stdlib.h> are included in "shmbutil.h".
|
||||
If <wchar.h>, <wctype.h>, mbsrtowcs(), exist, HANDLE_MULTIBYTE
|
||||
is defined as 1. */
|
||||
#include <shmbutil.h>
|
||||
|
||||
#if HANDLE_MULTIBYTE
|
||||
/* On some locales (ex. ja_JP.sjis), mbsrtowc doesn't convert 0x5c to U<0x5c>.
|
||||
So, this function is made for converting 0x5c to U<0x5c>. */
|
||||
|
||||
static mbstate_t local_state;
|
||||
static int local_state_use = 0;
|
||||
|
||||
size_t
|
||||
xmbsrtowcs (dest, src, len, pstate)
|
||||
wchar_t *dest;
|
||||
const char **src;
|
||||
size_t len;
|
||||
mbstate_t *pstate;
|
||||
{
|
||||
mbstate_t *ps;
|
||||
size_t mblength, wclength, n;
|
||||
|
||||
ps = pstate;
|
||||
if (pstate == NULL)
|
||||
{
|
||||
if (!local_state_use)
|
||||
{
|
||||
memset (&local_state, '\0', sizeof(mbstate_t));
|
||||
local_state_use = 1;
|
||||
}
|
||||
ps = &local_state;
|
||||
}
|
||||
|
||||
n = strlen (*src);
|
||||
|
||||
if (dest == NULL)
|
||||
{
|
||||
wchar_t *wsbuf;
|
||||
const char *mbs;
|
||||
mbstate_t psbuf;
|
||||
|
||||
/* It doesn't matter if malloc fails here, since mbsrtowcs should do
|
||||
the right thing with a NULL first argument. */
|
||||
wsbuf = (wchar_t *) malloc ((n + 1) * sizeof(wchar_t));
|
||||
mbs = *src;
|
||||
psbuf = *ps;
|
||||
|
||||
wclength = mbsrtowcs (wsbuf, &mbs, n, &psbuf);
|
||||
|
||||
if (wsbuf)
|
||||
free (wsbuf);
|
||||
return wclength;
|
||||
}
|
||||
|
||||
for (wclength = 0; wclength < len; wclength++, dest++)
|
||||
{
|
||||
if (mbsinit(ps))
|
||||
{
|
||||
if (**src == '\0')
|
||||
{
|
||||
*dest = L'\0';
|
||||
*src = NULL;
|
||||
return (wclength);
|
||||
}
|
||||
else if (**src == '\\')
|
||||
{
|
||||
*dest = L'\\';
|
||||
mblength = 1;
|
||||
}
|
||||
else
|
||||
mblength = mbrtowc(dest, *src, n, ps);
|
||||
}
|
||||
else
|
||||
mblength = mbrtowc(dest, *src, n, ps);
|
||||
|
||||
/* Cannot convert multibyte character to wide character. */
|
||||
if (mblength == (size_t)-1 || mblength == (size_t)-2)
|
||||
return (size_t)-1;
|
||||
|
||||
*src += mblength;
|
||||
n -= mblength;
|
||||
|
||||
/* The multibyte string has been completely converted,
|
||||
including the terminating '\0'. */
|
||||
if (*dest == L'\0')
|
||||
{
|
||||
*src = NULL;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return (wclength);
|
||||
}
|
||||
|
||||
/* Convert a multibyte string to a wide character string. Memory for the
|
||||
new wide character string is obtained with malloc.
|
||||
|
||||
The return value is the length of the wide character string. Returns a
|
||||
pointer to the wide character string in DESTP. If INDICESP is not NULL,
|
||||
INDICESP stores the pointer to the pointer array. Each pointer is to
|
||||
the first byte of each multibyte character. Memory for the pointer array
|
||||
is obtained with malloc, too.
|
||||
If conversion is failed, the return value is (size_t)-1 and the values
|
||||
of DESTP and INDICESP are NULL. */
|
||||
|
||||
#define WSBUF_INC 32
|
||||
|
||||
size_t
|
||||
xdupmbstowcs (destp, indicesp, src)
|
||||
wchar_t **destp; /* Store the pointer to the wide character string */
|
||||
char ***indicesp; /* Store the pointer to the pointer array. */
|
||||
const char *src; /* Multibyte character string */
|
||||
{
|
||||
const char *p; /* Conversion start position of src */
|
||||
wchar_t wc; /* Created wide character by conversion */
|
||||
wchar_t *wsbuf; /* Buffer for wide characters. */
|
||||
char **indices; /* Buffer for indices. */
|
||||
size_t wsbuf_size; /* Size of WSBUF */
|
||||
size_t wcnum; /* Number of wide characters in WSBUF */
|
||||
mbstate_t state; /* Conversion State */
|
||||
|
||||
/* In case SRC or DESP is NULL, conversion doesn't take place. */
|
||||
if (src == NULL || destp == NULL)
|
||||
{
|
||||
*destp = NULL;
|
||||
return (size_t)-1;
|
||||
}
|
||||
|
||||
memset (&state, '\0', sizeof(mbstate_t));
|
||||
wsbuf_size = WSBUF_INC;
|
||||
|
||||
wsbuf = (wchar_t *) malloc (wsbuf_size * sizeof(wchar_t));
|
||||
if (wsbuf == NULL)
|
||||
{
|
||||
*destp = NULL;
|
||||
return (size_t)-1;
|
||||
}
|
||||
|
||||
indices = (char **) malloc (wsbuf_size * sizeof(char *));
|
||||
if (indices == NULL)
|
||||
{
|
||||
free (wsbuf);
|
||||
*destp = NULL;
|
||||
return (size_t)-1;
|
||||
}
|
||||
|
||||
p = src;
|
||||
wcnum = 0;
|
||||
do
|
||||
{
|
||||
size_t mblength; /* Byte length of one multibyte character. */
|
||||
|
||||
if (mbsinit (&state))
|
||||
{
|
||||
if (*p == '\0')
|
||||
{
|
||||
wc = L'\0';
|
||||
mblength = 1;
|
||||
}
|
||||
else if (*p == '\\')
|
||||
{
|
||||
wc = L'\\';
|
||||
mblength = 1;
|
||||
}
|
||||
else
|
||||
mblength = mbrtowc(&wc, p, MB_LEN_MAX, &state);
|
||||
}
|
||||
else
|
||||
mblength = mbrtowc(&wc, p, MB_LEN_MAX, &state);
|
||||
|
||||
/* Conversion failed. */
|
||||
if (MB_INVALIDCH (mblength))
|
||||
{
|
||||
free (wsbuf);
|
||||
free (indices);
|
||||
*destp = NULL;
|
||||
return (size_t)-1;
|
||||
}
|
||||
|
||||
++wcnum;
|
||||
|
||||
/* Resize buffers when they are not large enough. */
|
||||
if (wsbuf_size < wcnum)
|
||||
{
|
||||
wchar_t *wstmp;
|
||||
char **idxtmp;
|
||||
|
||||
wsbuf_size += WSBUF_INC;
|
||||
|
||||
wstmp = (wchar_t *) realloc (wsbuf, wsbuf_size * sizeof (wchar_t));
|
||||
if (wstmp == NULL)
|
||||
{
|
||||
free (wsbuf);
|
||||
free (indices);
|
||||
*destp = NULL;
|
||||
return (size_t)-1;
|
||||
}
|
||||
wsbuf = wstmp;
|
||||
|
||||
idxtmp = (char **) realloc (indices, wsbuf_size * sizeof (char **));
|
||||
if (idxtmp == NULL)
|
||||
{
|
||||
free (wsbuf);
|
||||
free (indices);
|
||||
*destp = NULL;
|
||||
return (size_t)-1;
|
||||
}
|
||||
indices = idxtmp;
|
||||
}
|
||||
|
||||
wsbuf[wcnum - 1] = wc;
|
||||
indices[wcnum - 1] = (char *)p;
|
||||
p += mblength;
|
||||
}
|
||||
while (MB_NULLWCH (wc) == 0);
|
||||
|
||||
/* Return the length of the wide character string, not including `\0'. */
|
||||
*destp = wsbuf;
|
||||
if (indicesp != NULL)
|
||||
*indicesp = indices;
|
||||
else
|
||||
free (indices);
|
||||
|
||||
return (wcnum - 1);
|
||||
}
|
||||
|
||||
#endif /* HANDLE_MULTIBYTE */
|
||||
+4
-1
@@ -370,7 +370,10 @@ rl_generic_bind (type, keyseq, data, map)
|
||||
|
||||
ic = uc;
|
||||
if (ic < 0 || ic >= KEYMAP_SIZE)
|
||||
return -1;
|
||||
{
|
||||
free (keys);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (META_CHAR (ic) && _rl_convert_meta_chars_to_ascii)
|
||||
{
|
||||
|
||||
@@ -691,7 +691,7 @@ rl_function_of_keyseq (keyseq, map, type)
|
||||
{
|
||||
register int i;
|
||||
|
||||
if (!map)
|
||||
if (map == 0)
|
||||
map = _rl_keymap;
|
||||
|
||||
for (i = 0; keyseq && keyseq[i]; i++)
|
||||
@@ -705,9 +705,9 @@ rl_function_of_keyseq (keyseq, map, type)
|
||||
map = FUNCTION_TO_KEYMAP (map, ESC);
|
||||
ic = UNMETA (ic);
|
||||
}
|
||||
else if (map[ESC].type != ISKMAP && keyseq[i+1])
|
||||
return ((rl_command_func_t *)NULL);
|
||||
else /* map[ESC].type != ISKMAP && keyseq[i+1] == 0 */
|
||||
/* XXX - should we just return NULL here, since this obviously
|
||||
doesn't match? */
|
||||
else
|
||||
{
|
||||
if (type)
|
||||
*type = map[ESC].type;
|
||||
|
||||
@@ -1930,6 +1930,7 @@ rl_message (va_alist)
|
||||
&prompt_invis_chars_first_line,
|
||||
&prompt_physical_chars);
|
||||
local_prompt_prefix = (char *)NULL;
|
||||
local_prompt_len = local_prompt ? strlen (local_prompt) : 0;
|
||||
(*rl_redisplay_function) ();
|
||||
|
||||
return 0;
|
||||
|
||||
@@ -582,6 +582,7 @@ rl_yank_nth_arg_internal (count, ignore, history_skip)
|
||||
if (!arg || !*arg)
|
||||
{
|
||||
rl_ding ();
|
||||
FREE (arg);
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,693 @@
|
||||
/* kill.c -- kill ring management. */
|
||||
|
||||
/* Copyright (C) 1994 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of the GNU Readline Library, a library for
|
||||
reading lines of text with interactive input and history editing.
|
||||
|
||||
The GNU Readline Library is free software; you can redistribute it
|
||||
and/or modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2, or
|
||||
(at your option) any later version.
|
||||
|
||||
The GNU Readline Library is distributed in the hope that it will be
|
||||
useful, but WITHOUT ANY WARRANTY; without even the implied warranty
|
||||
of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
The GNU General Public License is often shipped with GNU software, and
|
||||
is generally kept in a file called COPYING or LICENSE. If you do not
|
||||
have a copy of the license, write to the Free Software Foundation,
|
||||
59 Temple Place, Suite 330, Boston, MA 02111 USA. */
|
||||
#define READLINE_LIBRARY
|
||||
|
||||
#if defined (HAVE_CONFIG_H)
|
||||
# include <config.h>
|
||||
#endif
|
||||
|
||||
#include <sys/types.h>
|
||||
|
||||
#if defined (HAVE_UNISTD_H)
|
||||
# include <unistd.h> /* for _POSIX_VERSION */
|
||||
#endif /* HAVE_UNISTD_H */
|
||||
|
||||
#if defined (HAVE_STDLIB_H)
|
||||
# include <stdlib.h>
|
||||
#else
|
||||
# include "ansi_stdlib.h"
|
||||
#endif /* HAVE_STDLIB_H */
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
/* System-specific feature definitions and include files. */
|
||||
#include "rldefs.h"
|
||||
|
||||
/* Some standard library routines. */
|
||||
#include "readline.h"
|
||||
#include "history.h"
|
||||
|
||||
#include "rlprivate.h"
|
||||
#include "xmalloc.h"
|
||||
|
||||
/* **************************************************************** */
|
||||
/* */
|
||||
/* Killing Mechanism */
|
||||
/* */
|
||||
/* **************************************************************** */
|
||||
|
||||
/* What we assume for a max number of kills. */
|
||||
#define DEFAULT_MAX_KILLS 10
|
||||
|
||||
/* The real variable to look at to find out when to flush kills. */
|
||||
static int rl_max_kills = DEFAULT_MAX_KILLS;
|
||||
|
||||
/* Where to store killed text. */
|
||||
static char **rl_kill_ring = (char **)NULL;
|
||||
|
||||
/* Where we are in the kill ring. */
|
||||
static int rl_kill_index;
|
||||
|
||||
/* How many slots we have in the kill ring. */
|
||||
static int rl_kill_ring_length;
|
||||
|
||||
static int _rl_copy_to_kill_ring PARAMS((char *, int));
|
||||
static int region_kill_internal PARAMS((int));
|
||||
static int _rl_copy_word_as_kill PARAMS((int, int));
|
||||
static int rl_yank_nth_arg_internal PARAMS((int, int, int));
|
||||
|
||||
/* How to say that you only want to save a certain amount
|
||||
of kill material. */
|
||||
int
|
||||
rl_set_retained_kills (num)
|
||||
int num;
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Add TEXT to the kill ring, allocating a new kill ring slot as necessary.
|
||||
This uses TEXT directly, so the caller must not free it. If APPEND is
|
||||
non-zero, and the last command was a kill, the text is appended to the
|
||||
current kill ring slot, otherwise prepended. */
|
||||
static int
|
||||
_rl_copy_to_kill_ring (text, append)
|
||||
char *text;
|
||||
int append;
|
||||
{
|
||||
char *old, *new;
|
||||
int slot;
|
||||
|
||||
/* First, find the slot to work with. */
|
||||
if (_rl_last_command_was_kill == 0)
|
||||
{
|
||||
/* Get a new slot. */
|
||||
if (rl_kill_ring == 0)
|
||||
{
|
||||
/* If we don't have any defined, then make one. */
|
||||
rl_kill_ring = (char **)
|
||||
xmalloc (((rl_kill_ring_length = 1) + 1) * sizeof (char *));
|
||||
rl_kill_ring[slot = 0] = (char *)NULL;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* We have to add a new slot on the end, unless we have
|
||||
exceeded the max limit for remembering kills. */
|
||||
slot = rl_kill_ring_length;
|
||||
if (slot == rl_max_kills)
|
||||
{
|
||||
register int i;
|
||||
free (rl_kill_ring[0]);
|
||||
for (i = 0; i < slot; i++)
|
||||
rl_kill_ring[i] = rl_kill_ring[i + 1];
|
||||
}
|
||||
else
|
||||
{
|
||||
slot = rl_kill_ring_length += 1;
|
||||
rl_kill_ring = (char **)xrealloc (rl_kill_ring, slot * sizeof (char *));
|
||||
}
|
||||
rl_kill_ring[--slot] = (char *)NULL;
|
||||
}
|
||||
}
|
||||
else
|
||||
slot = rl_kill_ring_length - 1;
|
||||
|
||||
/* If the last command was a kill, prepend or append. */
|
||||
if (_rl_last_command_was_kill && rl_editing_mode != vi_mode)
|
||||
{
|
||||
old = rl_kill_ring[slot];
|
||||
new = (char *)xmalloc (1 + strlen (old) + strlen (text));
|
||||
|
||||
if (append)
|
||||
{
|
||||
strcpy (new, old);
|
||||
strcat (new, text);
|
||||
}
|
||||
else
|
||||
{
|
||||
strcpy (new, text);
|
||||
strcat (new, old);
|
||||
}
|
||||
free (old);
|
||||
free (text);
|
||||
rl_kill_ring[slot] = new;
|
||||
}
|
||||
else
|
||||
rl_kill_ring[slot] = text;
|
||||
|
||||
rl_kill_index = slot;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* The way to kill something. This appends or prepends to the last
|
||||
kill, if the last command was a kill command. if FROM is less
|
||||
than TO, then the text is appended, otherwise prepended. If the
|
||||
last command was not a kill command, then a new slot is made for
|
||||
this kill. */
|
||||
int
|
||||
rl_kill_text (from, to)
|
||||
int from, to;
|
||||
{
|
||||
char *text;
|
||||
|
||||
/* Is there anything to kill? */
|
||||
if (from == to)
|
||||
{
|
||||
_rl_last_command_was_kill++;
|
||||
return 0;
|
||||
}
|
||||
|
||||
text = rl_copy_text (from, to);
|
||||
|
||||
/* Delete the copied text from the line. */
|
||||
rl_delete_text (from, to);
|
||||
|
||||
_rl_copy_to_kill_ring (text, from < to);
|
||||
|
||||
_rl_last_command_was_kill++;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Now REMEMBER! In order to do prepending or appending correctly, kill
|
||||
commands always make rl_point's original position be the FROM argument,
|
||||
and rl_point's extent be the TO argument. */
|
||||
|
||||
/* **************************************************************** */
|
||||
/* */
|
||||
/* Killing Commands */
|
||||
/* */
|
||||
/* **************************************************************** */
|
||||
|
||||
/* Delete the word at point, saving the text in the kill ring. */
|
||||
int
|
||||
rl_kill_word (count, key)
|
||||
int count, key;
|
||||
{
|
||||
int orig_point;
|
||||
|
||||
if (count < 0)
|
||||
return (rl_backward_kill_word (-count, key));
|
||||
else
|
||||
{
|
||||
orig_point = rl_point;
|
||||
rl_forward_word (count, key);
|
||||
|
||||
if (rl_point != orig_point)
|
||||
rl_kill_text (orig_point, rl_point);
|
||||
|
||||
rl_point = orig_point;
|
||||
if (rl_editing_mode == emacs_mode)
|
||||
rl_mark = rl_point;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Rubout the word before point, placing it on the kill ring. */
|
||||
int
|
||||
rl_backward_kill_word (count, ignore)
|
||||
int count, ignore;
|
||||
{
|
||||
int orig_point;
|
||||
|
||||
if (count < 0)
|
||||
return (rl_kill_word (-count, ignore));
|
||||
else
|
||||
{
|
||||
orig_point = rl_point;
|
||||
rl_backward_word (count, ignore);
|
||||
|
||||
if (rl_point != orig_point)
|
||||
rl_kill_text (orig_point, rl_point);
|
||||
|
||||
if (rl_editing_mode == emacs_mode)
|
||||
rl_mark = rl_point;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Kill from here to the end of the line. If DIRECTION is negative, kill
|
||||
back to the line start instead. */
|
||||
int
|
||||
rl_kill_line (direction, ignore)
|
||||
int direction, ignore;
|
||||
{
|
||||
int orig_point;
|
||||
|
||||
if (direction < 0)
|
||||
return (rl_backward_kill_line (1, ignore));
|
||||
else
|
||||
{
|
||||
orig_point = rl_point;
|
||||
rl_end_of_line (1, ignore);
|
||||
if (orig_point != rl_point)
|
||||
rl_kill_text (orig_point, rl_point);
|
||||
rl_point = orig_point;
|
||||
if (rl_editing_mode == emacs_mode)
|
||||
rl_mark = rl_point;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Kill backwards to the start of the line. If DIRECTION is negative, kill
|
||||
forwards to the line end instead. */
|
||||
int
|
||||
rl_backward_kill_line (direction, ignore)
|
||||
int direction, ignore;
|
||||
{
|
||||
int orig_point;
|
||||
|
||||
if (direction < 0)
|
||||
return (rl_kill_line (1, ignore));
|
||||
else
|
||||
{
|
||||
if (!rl_point)
|
||||
rl_ding ();
|
||||
else
|
||||
{
|
||||
orig_point = rl_point;
|
||||
rl_beg_of_line (1, ignore);
|
||||
if (rl_point != orig_point)
|
||||
rl_kill_text (orig_point, rl_point);
|
||||
if (rl_editing_mode == emacs_mode)
|
||||
rl_mark = rl_point;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Kill the whole line, no matter where point is. */
|
||||
int
|
||||
rl_kill_full_line (count, ignore)
|
||||
int count, ignore;
|
||||
{
|
||||
rl_begin_undo_group ();
|
||||
rl_point = 0;
|
||||
rl_kill_text (rl_point, rl_end);
|
||||
rl_mark = 0;
|
||||
rl_end_undo_group ();
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* The next two functions mimic unix line editing behaviour, except they
|
||||
save the deleted text on the kill ring. This is safer than not saving
|
||||
it, and since we have a ring, nobody should get screwed. */
|
||||
|
||||
/* This does what C-w does in Unix. We can't prevent people from
|
||||
using behaviour that they expect. */
|
||||
int
|
||||
rl_unix_word_rubout (count, key)
|
||||
int count, key;
|
||||
{
|
||||
int orig_point;
|
||||
|
||||
if (rl_point == 0)
|
||||
rl_ding ();
|
||||
else
|
||||
{
|
||||
orig_point = rl_point;
|
||||
if (count <= 0)
|
||||
count = 1;
|
||||
|
||||
while (count--)
|
||||
{
|
||||
while (rl_point && whitespace (rl_line_buffer[rl_point - 1]))
|
||||
rl_point--;
|
||||
|
||||
while (rl_point && (whitespace (rl_line_buffer[rl_point - 1]) == 0))
|
||||
rl_point--;
|
||||
}
|
||||
|
||||
rl_kill_text (orig_point, rl_point);
|
||||
if (rl_editing_mode == emacs_mode)
|
||||
rl_mark = rl_point;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* This deletes one filename component in a Unix pathname. That is, it
|
||||
deletes backward to directory separator (`/') or whitespace. */
|
||||
int
|
||||
rl_unix_filename_rubout (count, key)
|
||||
int count, key;
|
||||
{
|
||||
int orig_point, c;
|
||||
|
||||
if (rl_point == 0)
|
||||
rl_ding ();
|
||||
else
|
||||
{
|
||||
orig_point = rl_point;
|
||||
if (count <= 0)
|
||||
count = 1;
|
||||
|
||||
while (count--)
|
||||
{
|
||||
c = rl_line_buffer[rl_point - 1];
|
||||
while (rl_point && (whitespace (c) || c == '/'))
|
||||
{
|
||||
rl_point--;
|
||||
c = rl_line_buffer[rl_point - 1];
|
||||
}
|
||||
|
||||
while (rl_point && (whitespace (c) == 0) && c != '/')
|
||||
{
|
||||
rl_point--;
|
||||
c = rl_line_buffer[rl_point - 1];
|
||||
}
|
||||
}
|
||||
|
||||
rl_kill_text (orig_point, rl_point);
|
||||
if (rl_editing_mode == emacs_mode)
|
||||
rl_mark = rl_point;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Here is C-u doing what Unix does. You don't *have* to use these
|
||||
key-bindings. We have a choice of killing the entire line, or
|
||||
killing from where we are to the start of the line. We choose the
|
||||
latter, because if you are a Unix weenie, then you haven't backspaced
|
||||
into the line at all, and if you aren't, then you know what you are
|
||||
doing. */
|
||||
int
|
||||
rl_unix_line_discard (count, key)
|
||||
int count, key;
|
||||
{
|
||||
if (rl_point == 0)
|
||||
rl_ding ();
|
||||
else
|
||||
{
|
||||
rl_kill_text (rl_point, 0);
|
||||
rl_point = 0;
|
||||
if (rl_editing_mode == emacs_mode)
|
||||
rl_mark = rl_point;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Copy the text in the `region' to the kill ring. If DELETE is non-zero,
|
||||
delete the text from the line as well. */
|
||||
static int
|
||||
region_kill_internal (delete)
|
||||
int delete;
|
||||
{
|
||||
char *text;
|
||||
|
||||
if (rl_mark != rl_point)
|
||||
{
|
||||
text = rl_copy_text (rl_point, rl_mark);
|
||||
if (delete)
|
||||
rl_delete_text (rl_point, rl_mark);
|
||||
_rl_copy_to_kill_ring (text, rl_point < rl_mark);
|
||||
}
|
||||
|
||||
_rl_last_command_was_kill++;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Copy the text in the region to the kill ring. */
|
||||
int
|
||||
rl_copy_region_to_kill (count, ignore)
|
||||
int count, ignore;
|
||||
{
|
||||
return (region_kill_internal (0));
|
||||
}
|
||||
|
||||
/* Kill the text between the point and mark. */
|
||||
int
|
||||
rl_kill_region (count, ignore)
|
||||
int count, ignore;
|
||||
{
|
||||
int r, npoint;
|
||||
|
||||
npoint = (rl_point < rl_mark) ? rl_point : rl_mark;
|
||||
r = region_kill_internal (1);
|
||||
_rl_fix_point (1);
|
||||
rl_point = npoint;
|
||||
return r;
|
||||
}
|
||||
|
||||
/* Copy COUNT words to the kill ring. DIR says which direction we look
|
||||
to find the words. */
|
||||
static int
|
||||
_rl_copy_word_as_kill (count, dir)
|
||||
int count, dir;
|
||||
{
|
||||
int om, op, r;
|
||||
|
||||
om = rl_mark;
|
||||
op = rl_point;
|
||||
|
||||
if (dir > 0)
|
||||
rl_forward_word (count, 0);
|
||||
else
|
||||
rl_backward_word (count, 0);
|
||||
|
||||
rl_mark = rl_point;
|
||||
|
||||
if (dir > 0)
|
||||
rl_backward_word (count, 0);
|
||||
else
|
||||
rl_forward_word (count, 0);
|
||||
|
||||
r = region_kill_internal (0);
|
||||
|
||||
rl_mark = om;
|
||||
rl_point = op;
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
int
|
||||
rl_copy_forward_word (count, key)
|
||||
int count, key;
|
||||
{
|
||||
if (count < 0)
|
||||
return (rl_copy_backward_word (-count, key));
|
||||
|
||||
return (_rl_copy_word_as_kill (count, 1));
|
||||
}
|
||||
|
||||
int
|
||||
rl_copy_backward_word (count, key)
|
||||
int count, key;
|
||||
{
|
||||
if (count < 0)
|
||||
return (rl_copy_forward_word (-count, key));
|
||||
|
||||
return (_rl_copy_word_as_kill (count, -1));
|
||||
}
|
||||
|
||||
/* Yank back the last killed text. This ignores arguments. */
|
||||
int
|
||||
rl_yank (count, ignore)
|
||||
int count, ignore;
|
||||
{
|
||||
if (rl_kill_ring == 0)
|
||||
{
|
||||
_rl_abort_internal ();
|
||||
return -1;
|
||||
}
|
||||
|
||||
_rl_set_mark_at_pos (rl_point);
|
||||
rl_insert_text (rl_kill_ring[rl_kill_index]);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* If the last command was yank, or yank_pop, and the text just
|
||||
before point is identical to the current kill item, then
|
||||
delete that text from the line, rotate the index down, and
|
||||
yank back some other text. */
|
||||
int
|
||||
rl_yank_pop (count, key)
|
||||
int count, key;
|
||||
{
|
||||
int l, n;
|
||||
|
||||
if (((rl_last_func != rl_yank_pop) && (rl_last_func != rl_yank)) ||
|
||||
!rl_kill_ring)
|
||||
{
|
||||
_rl_abort_internal ();
|
||||
return -1;
|
||||
}
|
||||
|
||||
l = strlen (rl_kill_ring[rl_kill_index]);
|
||||
n = rl_point - l;
|
||||
if (n >= 0 && STREQN (rl_line_buffer + n, rl_kill_ring[rl_kill_index], l))
|
||||
{
|
||||
rl_delete_text (n, rl_point);
|
||||
rl_point = n;
|
||||
rl_kill_index--;
|
||||
if (rl_kill_index < 0)
|
||||
rl_kill_index = rl_kill_ring_length - 1;
|
||||
rl_yank (1, 0);
|
||||
return 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
_rl_abort_internal ();
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
/* Yank the COUNTh argument from the previous history line, skipping
|
||||
HISTORY_SKIP lines before looking for the `previous line'. */
|
||||
static int
|
||||
rl_yank_nth_arg_internal (count, ignore, history_skip)
|
||||
int count, ignore, history_skip;
|
||||
{
|
||||
register HIST_ENTRY *entry;
|
||||
char *arg;
|
||||
int i, pos;
|
||||
|
||||
pos = where_history ();
|
||||
|
||||
if (history_skip)
|
||||
{
|
||||
for (i = 0; i < history_skip; i++)
|
||||
entry = previous_history ();
|
||||
}
|
||||
|
||||
entry = previous_history ();
|
||||
|
||||
history_set_pos (pos);
|
||||
|
||||
if (entry == 0)
|
||||
{
|
||||
rl_ding ();
|
||||
return -1;
|
||||
}
|
||||
|
||||
arg = history_arg_extract (count, count, entry->line);
|
||||
if (!arg || !*arg)
|
||||
{
|
||||
rl_ding ();
|
||||
return -1;
|
||||
}
|
||||
|
||||
rl_begin_undo_group ();
|
||||
|
||||
_rl_set_mark_at_pos (rl_point);
|
||||
|
||||
#if defined (VI_MODE)
|
||||
/* Vi mode always inserts a space before yanking the argument, and it
|
||||
inserts it right *after* rl_point. */
|
||||
if (rl_editing_mode == vi_mode)
|
||||
{
|
||||
rl_vi_append_mode (1, ignore);
|
||||
rl_insert_text (" ");
|
||||
}
|
||||
#endif /* VI_MODE */
|
||||
|
||||
rl_insert_text (arg);
|
||||
free (arg);
|
||||
|
||||
rl_end_undo_group ();
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Yank the COUNTth argument from the previous history line. */
|
||||
int
|
||||
rl_yank_nth_arg (count, ignore)
|
||||
int count, ignore;
|
||||
{
|
||||
return (rl_yank_nth_arg_internal (count, ignore, 0));
|
||||
}
|
||||
|
||||
/* Yank the last argument from the previous history line. This `knows'
|
||||
how rl_yank_nth_arg treats a count of `$'. With an argument, this
|
||||
behaves the same as rl_yank_nth_arg. */
|
||||
int
|
||||
rl_yank_last_arg (count, key)
|
||||
int count, key;
|
||||
{
|
||||
static int history_skip = 0;
|
||||
static int explicit_arg_p = 0;
|
||||
static int count_passed = 1;
|
||||
static int direction = 1;
|
||||
static int undo_needed = 0;
|
||||
int retval;
|
||||
|
||||
if (rl_last_func != rl_yank_last_arg)
|
||||
{
|
||||
history_skip = 0;
|
||||
explicit_arg_p = rl_explicit_arg;
|
||||
count_passed = count;
|
||||
direction = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (undo_needed)
|
||||
rl_do_undo ();
|
||||
if (count < 1)
|
||||
direction = -direction;
|
||||
history_skip += direction;
|
||||
if (history_skip < 0)
|
||||
history_skip = 0;
|
||||
}
|
||||
|
||||
if (explicit_arg_p)
|
||||
retval = rl_yank_nth_arg_internal (count_passed, key, history_skip);
|
||||
else
|
||||
retval = rl_yank_nth_arg_internal ('$', key, history_skip);
|
||||
|
||||
undo_needed = retval == 0;
|
||||
return retval;
|
||||
}
|
||||
|
||||
/* A special paste command for users of Cygnus's cygwin32. */
|
||||
#if defined (__CYGWIN__)
|
||||
#include <windows.h>
|
||||
|
||||
int
|
||||
rl_paste_from_clipboard (count, key)
|
||||
int count, key;
|
||||
{
|
||||
char *data, *ptr;
|
||||
int len;
|
||||
|
||||
if (OpenClipboard (NULL) == 0)
|
||||
return (0);
|
||||
|
||||
data = (char *)GetClipboardData (CF_TEXT);
|
||||
if (data)
|
||||
{
|
||||
ptr = strchr (data, '\r');
|
||||
if (ptr)
|
||||
{
|
||||
len = ptr - data;
|
||||
ptr = (char *)xmalloc (len + 1);
|
||||
ptr[len] = '\0';
|
||||
strncpy (ptr, data, len);
|
||||
}
|
||||
else
|
||||
ptr = data;
|
||||
_rl_set_mark_at_pos (rl_point);
|
||||
rl_insert_text (ptr);
|
||||
if (ptr != data)
|
||||
free (ptr);
|
||||
CloseClipboard ();
|
||||
}
|
||||
return (0);
|
||||
}
|
||||
#endif /* __CYGWIN__ */
|
||||
@@ -40,9 +40,9 @@ extern "C" {
|
||||
#endif
|
||||
|
||||
/* Hex-encoded Readline version number. */
|
||||
#define RL_READLINE_VERSION 0x0501 /* Readline 5.1 */
|
||||
#define RL_READLINE_VERSION 0x0502 /* Readline 5.2 */
|
||||
#define RL_VERSION_MAJOR 5
|
||||
#define RL_VERSION_MINOR 1
|
||||
#define RL_VERSION_MINOR 2
|
||||
|
||||
/* Readline data structures. */
|
||||
|
||||
|
||||
@@ -498,10 +498,13 @@ locale_setblanks ()
|
||||
for (x = 0; x < sh_syntabsiz; x++)
|
||||
{
|
||||
if (isblank (x))
|
||||
sh_syntaxtab[x] |= CSHBRK;
|
||||
sh_syntaxtab[x] |= CSHBRK|CBLANK;
|
||||
else if (member (x, shell_break_chars))
|
||||
sh_syntaxtab[x] |= CSHBRK;
|
||||
{
|
||||
sh_syntaxtab[x] |= CSHBRK;
|
||||
sh_syntaxtab[x] &= ~CBLANK;
|
||||
}
|
||||
else
|
||||
sh_syntaxtab[x] &= ~CSHBRK;
|
||||
sh_syntaxtab[x] &= ~(CSHBRK|CBLANK);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -66,7 +66,6 @@ set_default_locale ()
|
||||
default_locale = setlocale (LC_ALL, "");
|
||||
if (default_locale)
|
||||
default_locale = savestring (default_locale);
|
||||
itrace("default locale = %s", default_locale ? default_locale : "NULL");
|
||||
#endif /* HAVE_SETLOCALE */
|
||||
bindtextdomain (PACKAGE, LOCALEDIR);
|
||||
textdomain (PACKAGE);
|
||||
@@ -294,17 +293,11 @@ static int
|
||||
reset_locale_vars ()
|
||||
{
|
||||
#if defined (HAVE_SETLOCALE)
|
||||
char *locale;
|
||||
|
||||
if (lang == 0 || *lang == '\0')
|
||||
maybe_make_export_env (); /* trust that this will change environment for setlocale */
|
||||
if (setlocale (LC_ALL, lang ? lang : "") == 0)
|
||||
return 0;
|
||||
|
||||
itrace("setlocale(LC_ALL, \"%s\")", lang ? lang : "");
|
||||
locale = setlocale(LC_ALL, (char *)NULL);
|
||||
itrace("current locale = %s", locale ? locale : "NULL");
|
||||
|
||||
# if defined (LC_CTYPE)
|
||||
setlocale (LC_CTYPE, get_locale_var ("LC_CTYPE"));
|
||||
# endif
|
||||
@@ -505,10 +498,10 @@ locale_setblanks ()
|
||||
for (x = 0; x < sh_syntabsiz; x++)
|
||||
{
|
||||
if (isblank (x))
|
||||
sh_syntaxtab[x] |= CSHBRK;
|
||||
sh_syntaxtab[x] |= CSHBRK|CBLANK;
|
||||
else if (member (x, shell_break_chars))
|
||||
sh_syntaxtab[x] |= CSHBRK;
|
||||
else
|
||||
sh_syntaxtab[x] &= ~CSHBRK;
|
||||
sh_syntaxtab[x] &= ~(CSHBRK|CBLANK);
|
||||
}
|
||||
}
|
||||
|
||||
+19
@@ -62,6 +62,7 @@ struct wordflag {
|
||||
{ CXQUOTE, "CXQUOTE" },
|
||||
{ CSPECVAR, "CSPECVAR" },
|
||||
{ CSUBSTOP, "CSUBSTOP" },
|
||||
{ CBLANK, "CBLANK" },
|
||||
};
|
||||
|
||||
#define N_WFLAGS (sizeof (wordflags) / sizeof (wordflags[0]))
|
||||
@@ -196,6 +197,22 @@ addcchar (c, flag)
|
||||
lsyntax[c] |= flag;
|
||||
}
|
||||
|
||||
static void
|
||||
addblanks ()
|
||||
{
|
||||
register int i;
|
||||
unsigned char uc;
|
||||
|
||||
for (i = 0; i < SYNSIZE; i++)
|
||||
{
|
||||
uc = i;
|
||||
/* Since we don't call setlocale(), this defaults to the "C" locale, and
|
||||
the default blank characters will be space and tab. */
|
||||
if (isblank (uc))
|
||||
lsyntax[uc] |= CBLANK;
|
||||
}
|
||||
}
|
||||
|
||||
/* load up the correct flag values in lsyntax */
|
||||
static void
|
||||
load_lsyntax ()
|
||||
@@ -230,6 +247,8 @@ load_lsyntax ()
|
||||
addcstr ("@*#?-$!", CSPECVAR); /* omits $0...$9 and $_ */
|
||||
|
||||
addcstr ("-=?+", CSUBSTOP); /* OP in ${paramOPword} */
|
||||
|
||||
addblanks ();
|
||||
}
|
||||
|
||||
static void
|
||||
|
||||
+413
@@ -0,0 +1,413 @@
|
||||
/*
|
||||
* mksyntax.c - construct shell syntax table for fast char attribute lookup.
|
||||
*/
|
||||
|
||||
/* Copyright (C) 2000-2002 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Bash, the Bourne Again SHell.
|
||||
|
||||
Bash is free software; you can redistribute it and/or modify it under
|
||||
the terms of the GNU General Public License as published by the Free
|
||||
Software Foundation; either version 2, or (at your option) any later
|
||||
version.
|
||||
|
||||
Bash is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||
WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along
|
||||
with Bash; see the file COPYING. If not, write to the Free Software
|
||||
Foundation, 59 Temple Place, Suite 330, Boston, MA 02111 USA. */
|
||||
|
||||
#include "config.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include "bashansi.h"
|
||||
#include "chartypes.h"
|
||||
#include <errno.h>
|
||||
|
||||
#ifdef HAVE_UNISTD_H
|
||||
# include <unistd.h>
|
||||
#endif
|
||||
|
||||
#include "syntax.h"
|
||||
|
||||
extern int optind;
|
||||
extern char *optarg;
|
||||
|
||||
#ifndef errno
|
||||
extern int errno;
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_STRERROR
|
||||
extern char *strerror();
|
||||
#endif
|
||||
|
||||
struct wordflag {
|
||||
int flag;
|
||||
char *fstr;
|
||||
} wordflags[] = {
|
||||
{ CWORD, "CWORD" },
|
||||
{ CSHMETA, "CSHMETA" },
|
||||
{ CSHBRK, "CSHBRK" },
|
||||
{ CBACKQ, "CBACKQ" },
|
||||
{ CQUOTE, "CQUOTE" },
|
||||
{ CSPECL, "CSPECL" },
|
||||
{ CEXP, "CEXP" },
|
||||
{ CBSDQUOTE, "CBSDQUOTE" },
|
||||
{ CBSHDOC, "CBSHDOC" },
|
||||
{ CGLOB, "CGLOB" },
|
||||
{ CXGLOB, "CXGLOB" },
|
||||
{ CXQUOTE, "CXQUOTE" },
|
||||
{ CSPECVAR, "CSPECVAR" },
|
||||
{ CSUBSTOP, "CSUBSTOP" },
|
||||
{ CBLANK, "CBLANK" },
|
||||
};
|
||||
|
||||
#define N_WFLAGS (sizeof (wordflags) / sizeof (wordflags[0]))
|
||||
#define SYNSIZE 256
|
||||
|
||||
int lsyntax[SYNSIZE];
|
||||
int debug;
|
||||
char *progname;
|
||||
|
||||
char preamble[] = "\
|
||||
/*\n\
|
||||
* This file was generated by mksyntax. DO NOT EDIT.\n\
|
||||
*/\n\
|
||||
\n";
|
||||
|
||||
char includes[] = "\
|
||||
#include \"config.h\"\n\
|
||||
#include \"stdc.h\"\n\
|
||||
#include \"syntax.h\"\n\n";
|
||||
|
||||
static void
|
||||
usage()
|
||||
{
|
||||
fprintf (stderr, "%s: usage: %s [-d] [-o filename]\n", progname, progname);
|
||||
exit (2);
|
||||
}
|
||||
|
||||
#ifdef INCLUDE_UNUSED
|
||||
static int
|
||||
getcflag (s)
|
||||
char *s;
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < N_WFLAGS; i++)
|
||||
if (strcmp (s, wordflags[i].fstr) == 0)
|
||||
return wordflags[i].flag;
|
||||
return -1;
|
||||
}
|
||||
#endif
|
||||
|
||||
static char *
|
||||
cdesc (i)
|
||||
int i;
|
||||
{
|
||||
static char xbuf[16];
|
||||
|
||||
if (i == ' ')
|
||||
return "SPC";
|
||||
else if (ISPRINT (i))
|
||||
{
|
||||
xbuf[0] = i;
|
||||
xbuf[1] = '\0';
|
||||
return (xbuf);
|
||||
}
|
||||
else if (i == CTLESC)
|
||||
return "CTLESC";
|
||||
else if (i == CTLNUL)
|
||||
return "CTLNUL";
|
||||
else if (i == '\033') /* ASCII */
|
||||
return "ESC";
|
||||
|
||||
xbuf[0] = '\\';
|
||||
xbuf[2] = '\0';
|
||||
|
||||
switch (i)
|
||||
{
|
||||
#ifdef __STDC__
|
||||
case '\a': xbuf[1] = 'a'; break;
|
||||
case '\v': xbuf[1] = 'v'; break;
|
||||
#else
|
||||
case '\007': xbuf[1] = 'a'; break;
|
||||
case 0x0B: xbuf[1] = 'v'; break;
|
||||
#endif
|
||||
case '\b': xbuf[1] = 'b'; break;
|
||||
case '\f': xbuf[1] = 'f'; break;
|
||||
case '\n': xbuf[1] = 'n'; break;
|
||||
case '\r': xbuf[1] = 'r'; break;
|
||||
case '\t': xbuf[1] = 't'; break;
|
||||
default: sprintf (xbuf, "%d", i); break;
|
||||
}
|
||||
|
||||
return xbuf;
|
||||
}
|
||||
|
||||
static char *
|
||||
getcstr (f)
|
||||
int f;
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < N_WFLAGS; i++)
|
||||
if (f == wordflags[i].flag)
|
||||
return (wordflags[i].fstr);
|
||||
return ((char *)NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
addcstr (str, flag)
|
||||
char *str;
|
||||
int flag;
|
||||
{
|
||||
char *s, *fstr;
|
||||
unsigned char uc;
|
||||
|
||||
for (s = str; s && *s; s++)
|
||||
{
|
||||
uc = *s;
|
||||
|
||||
if (debug)
|
||||
{
|
||||
fstr = getcstr (flag);
|
||||
fprintf(stderr, "added %s for character %s\n", fstr, cdesc(uc));
|
||||
}
|
||||
|
||||
lsyntax[uc] |= flag;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
addcchar (c, flag)
|
||||
unsigned char c;
|
||||
int flag;
|
||||
{
|
||||
char *fstr;
|
||||
|
||||
if (debug)
|
||||
{
|
||||
fstr = getcstr (flag);
|
||||
fprintf (stderr, "added %s for character %s\n", fstr, cdesc(c));
|
||||
}
|
||||
lsyntax[c] |= flag;
|
||||
}
|
||||
|
||||
static void
|
||||
addblanks ()
|
||||
{
|
||||
register int i;
|
||||
unsigned char uc;
|
||||
|
||||
for (i = 0; i < SYNSIZE; i++)
|
||||
{
|
||||
uc = i;
|
||||
if (isblank (uc))
|
||||
lsyntax[uc] |= CBLANK;
|
||||
}
|
||||
}
|
||||
|
||||
/* load up the correct flag values in lsyntax */
|
||||
static void
|
||||
load_lsyntax ()
|
||||
{
|
||||
/* shell metacharacters */
|
||||
addcstr (shell_meta_chars, CSHMETA);
|
||||
|
||||
/* shell word break characters */
|
||||
addcstr (shell_break_chars, CSHBRK);
|
||||
|
||||
addcchar ('`', CBACKQ);
|
||||
|
||||
addcstr (shell_quote_chars, CQUOTE);
|
||||
|
||||
addcchar (CTLESC, CSPECL);
|
||||
addcchar (CTLNUL, CSPECL);
|
||||
|
||||
addcstr (shell_exp_chars, CEXP);
|
||||
|
||||
addcstr (slashify_in_quotes, CBSDQUOTE);
|
||||
addcstr (slashify_in_here_document, CBSHDOC);
|
||||
|
||||
addcstr (shell_glob_chars, CGLOB);
|
||||
|
||||
#if defined (EXTENDED_GLOB)
|
||||
addcstr (ext_glob_chars, CXGLOB);
|
||||
#endif
|
||||
|
||||
addcstr (shell_quote_chars, CXQUOTE);
|
||||
addcchar ('\\', CXQUOTE);
|
||||
|
||||
addcstr ("@*#?-$!", CSPECVAR); /* omits $0...$9 and $_ */
|
||||
|
||||
addcstr ("-=?+", CSUBSTOP); /* OP in ${paramOPword} */
|
||||
|
||||
addblanks ();
|
||||
}
|
||||
|
||||
static void
|
||||
dump_lflags (fp, ind)
|
||||
FILE *fp;
|
||||
int ind;
|
||||
{
|
||||
int xflags, first, i;
|
||||
|
||||
xflags = lsyntax[ind];
|
||||
first = 1;
|
||||
|
||||
if (xflags == 0)
|
||||
fputs (wordflags[0].fstr, fp);
|
||||
else
|
||||
{
|
||||
for (i = 1; i < N_WFLAGS; i++)
|
||||
if (xflags & wordflags[i].flag)
|
||||
{
|
||||
if (first)
|
||||
first = 0;
|
||||
else
|
||||
putc ('|', fp);
|
||||
fputs (wordflags[i].fstr, fp);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
wcomment (fp, i)
|
||||
FILE *fp;
|
||||
int i;
|
||||
{
|
||||
fputs ("\t\t/* ", fp);
|
||||
|
||||
fprintf (fp, "%s", cdesc(i));
|
||||
|
||||
fputs (" */", fp);
|
||||
}
|
||||
|
||||
static void
|
||||
dump_lsyntax (fp)
|
||||
FILE *fp;
|
||||
{
|
||||
int i;
|
||||
|
||||
fprintf (fp, "int sh_syntabsiz = %d;\n", SYNSIZE);
|
||||
fprintf (fp, "int sh_syntaxtab[%d] = {\n", SYNSIZE);
|
||||
|
||||
for (i = 0; i < SYNSIZE; i++)
|
||||
{
|
||||
putc ('\t', fp);
|
||||
dump_lflags (fp, i);
|
||||
putc (',', fp);
|
||||
wcomment (fp, i);
|
||||
putc ('\n', fp);
|
||||
}
|
||||
|
||||
fprintf (fp, "};\n");
|
||||
}
|
||||
|
||||
int
|
||||
main(argc, argv)
|
||||
int argc;
|
||||
char **argv;
|
||||
{
|
||||
int opt, i;
|
||||
char *filename;
|
||||
FILE *fp;
|
||||
|
||||
if ((progname = strrchr (argv[0], '/')) == 0)
|
||||
progname = argv[0];
|
||||
else
|
||||
progname++;
|
||||
|
||||
filename = (char *)NULL;
|
||||
debug = 0;
|
||||
|
||||
while ((opt = getopt (argc, argv, "do:")) != EOF)
|
||||
{
|
||||
switch (opt)
|
||||
{
|
||||
case 'd':
|
||||
debug = 1;
|
||||
break;
|
||||
case 'o':
|
||||
filename = optarg;
|
||||
break;
|
||||
default:
|
||||
usage();
|
||||
}
|
||||
}
|
||||
|
||||
argc -= optind;
|
||||
argv += optind;
|
||||
|
||||
if (filename)
|
||||
{
|
||||
fp = fopen (filename, "w");
|
||||
if (fp == 0)
|
||||
{
|
||||
fprintf (stderr, "%s: %s: cannot open: %s\n", progname, filename, strerror(errno));
|
||||
exit (1);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
filename = "stdout";
|
||||
fp = stdout;
|
||||
}
|
||||
|
||||
|
||||
for (i = 0; i < SYNSIZE; i++)
|
||||
lsyntax[i] = CWORD;
|
||||
|
||||
load_lsyntax ();
|
||||
|
||||
fprintf (fp, "%s\n", preamble);
|
||||
fprintf (fp, "%s\n", includes);
|
||||
|
||||
dump_lsyntax (fp);
|
||||
|
||||
if (fp != stdout)
|
||||
fclose (fp);
|
||||
exit (0);
|
||||
}
|
||||
|
||||
|
||||
#if !defined (HAVE_STRERROR)
|
||||
|
||||
#include <bashtypes.h>
|
||||
#ifndef _MINIX
|
||||
# include <sys/param.h>
|
||||
#endif
|
||||
|
||||
#if defined (HAVE_UNISTD_H)
|
||||
# include <unistd.h>
|
||||
#endif
|
||||
|
||||
/* Return a string corresponding to the error number E. From
|
||||
the ANSI C spec. */
|
||||
#if defined (strerror)
|
||||
# undef strerror
|
||||
#endif
|
||||
|
||||
char *
|
||||
strerror (e)
|
||||
int e;
|
||||
{
|
||||
static char emsg[40];
|
||||
#if defined (HAVE_SYS_ERRLIST)
|
||||
extern int sys_nerr;
|
||||
extern char *sys_errlist[];
|
||||
|
||||
if (e > 0 && e < sys_nerr)
|
||||
return (sys_errlist[e]);
|
||||
else
|
||||
#endif /* HAVE_SYS_ERRLIST */
|
||||
{
|
||||
sprintf (emsg, "Unknown system error %d", e);
|
||||
return (&emsg[0]);
|
||||
}
|
||||
}
|
||||
#endif /* HAVE_STRERROR */
|
||||
@@ -2563,7 +2563,7 @@ read_token (command)
|
||||
#endif /* ALIAS */
|
||||
|
||||
/* Read a single word from input. Start by skipping blanks. */
|
||||
while ((character = shell_getc (1)) != EOF && whitespace (character))
|
||||
while ((character = shell_getc (1)) != EOF && shellblank (character))
|
||||
;
|
||||
|
||||
if (character == EOF)
|
||||
|
||||
@@ -3998,7 +3998,7 @@ decode_prompt_string (string)
|
||||
int last_exit_value;
|
||||
#if defined (PROMPT_STRING_DECODE)
|
||||
int result_size, result_index;
|
||||
int c, n;
|
||||
int c, n, i;
|
||||
char *temp, octal_string[4];
|
||||
struct tm *tm;
|
||||
time_t the_time;
|
||||
@@ -4270,9 +4270,12 @@ decode_prompt_string (string)
|
||||
break;
|
||||
}
|
||||
temp = (char *)xmalloc (3);
|
||||
temp[0] = CTLESC;
|
||||
temp[1] = (c == '[') ? RL_PROMPT_START_IGNORE : RL_PROMPT_END_IGNORE;
|
||||
temp[2] = '\0';
|
||||
n = (c == '[') ? RL_PROMPT_START_IGNORE : RL_PROMPT_END_IGNORE;
|
||||
i = 0;
|
||||
if (n == CTLESC || n == CTLNUL)
|
||||
temp[i++] = CTLESC;
|
||||
temp[i++] = n;
|
||||
temp[i] = '\0';
|
||||
goto add_string;
|
||||
#endif /* READLINE */
|
||||
|
||||
|
||||
+4
-4
@@ -879,13 +879,13 @@ print_redirection (redirect)
|
||||
case r_output_direction:
|
||||
if (redirector != 1)
|
||||
cprintf ("%d", redirector);
|
||||
cprintf (">%s", redirectee->word);
|
||||
cprintf ("> %s", redirectee->word);
|
||||
break;
|
||||
|
||||
case r_input_direction:
|
||||
if (redirector != 0)
|
||||
cprintf ("%d", redirector);
|
||||
cprintf ("<%s", redirectee->word);
|
||||
cprintf ("< %s", redirectee->word);
|
||||
break;
|
||||
|
||||
case r_inputa_direction: /* Redirection created by the shell. */
|
||||
@@ -895,7 +895,7 @@ print_redirection (redirect)
|
||||
case r_appending_to:
|
||||
if (redirector != 1)
|
||||
cprintf ("%d", redirector);
|
||||
cprintf (">>%s", redirectee->word);
|
||||
cprintf (">> %s", redirectee->word);
|
||||
break;
|
||||
|
||||
case r_deblank_reading_until:
|
||||
@@ -975,7 +975,7 @@ print_redirection (redirect)
|
||||
case r_input_output:
|
||||
if (redirector != 1)
|
||||
cprintf ("%d", redirector);
|
||||
cprintf ("<>%s", redirectee->word);
|
||||
cprintf ("<> %s", redirectee->word);
|
||||
break;
|
||||
|
||||
case r_output_force:
|
||||
|
||||
+1307
File diff suppressed because it is too large
Load Diff
@@ -62,6 +62,7 @@
|
||||
#define CXQUOTE 0x0400 /* cquote + backslash */
|
||||
#define CSPECVAR 0x0800 /* single-character shell variable name */
|
||||
#define CSUBSTOP 0x1000 /* values of OP for ${word[:]OPstuff} */
|
||||
#define CBLANK 0x2000 /* whitespace (blank) character */
|
||||
|
||||
/* Defines for use by the rest of the shell. */
|
||||
extern int sh_syntaxtab[];
|
||||
@@ -70,9 +71,10 @@ extern int sh_syntabsiz;
|
||||
#define shellmeta(c) (sh_syntaxtab[(unsigned char)(c)] & CSHMETA)
|
||||
#define shellbreak(c) (sh_syntaxtab[(unsigned char)(c)] & CSHBRK)
|
||||
#define shellquote(c) (sh_syntaxtab[(unsigned char)(c)] & CQUOTE)
|
||||
|
||||
#define shellxquote(c) (sh_syntaxtab[(unsigned char)(c)] & CXQUOTE)
|
||||
|
||||
#define shellblank(c) (sh_syntaxtab[(unsigned char)(c)] & CBLANK)
|
||||
|
||||
#define issyntype(c, t) ((sh_syntaxtab[(unsigned char)(c)] & (t)) != 0)
|
||||
#define notsyntype(c,t) ((sh_syntaxtab[(unsigned char)(c)] & (t)) == 0)
|
||||
|
||||
|
||||
@@ -0,0 +1,102 @@
|
||||
/* syntax.h -- Syntax definitions for the shell */
|
||||
|
||||
/* Copyright (C) 2000 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Bash, the Bourne Again SHell.
|
||||
|
||||
Bash is free software; you can redistribute it and/or modify it under
|
||||
the terms of the GNU General Public License as published by the Free
|
||||
Software Foundation; either version 2, or (at your option) any later
|
||||
version.
|
||||
|
||||
Bash is distributed in the hope that it will be useful, but WITHOUT ANY
|
||||
WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License along
|
||||
with Bash; see the file COPYING. If not, write to the Free Software
|
||||
Foundation, 59 Temple Place, Suite 330, Boston, MA 02111 USA. */
|
||||
|
||||
#ifndef _SYNTAX_H_
|
||||
#define _SYNTAX_H_
|
||||
|
||||
/* Defines for use by mksyntax.c */
|
||||
|
||||
#define slashify_in_quotes "\\`$\"\n"
|
||||
#define slashify_in_here_document "\\`$"
|
||||
|
||||
#define shell_meta_chars "()<>;&|"
|
||||
#define shell_break_chars "()<>;&| \t\n"
|
||||
|
||||
#define shell_quote_chars "\"`'"
|
||||
|
||||
#if defined (PROCESS_SUBSTITUTION)
|
||||
# define shell_exp_chars "$<>"
|
||||
#else
|
||||
# define shell_exp_chars "$"
|
||||
#endif
|
||||
|
||||
#if defined (EXTENDED_GLOB)
|
||||
# define ext_glob_chars "@*+?!"
|
||||
#else
|
||||
# define ext_glob_chars ""
|
||||
#endif
|
||||
#define shell_glob_chars "*?[]^"
|
||||
|
||||
/* Defines shared by mksyntax.c and the rest of the shell code. */
|
||||
|
||||
/* Values for character flags in syntax tables */
|
||||
|
||||
#define CWORD 0x0000 /* nothing special; an ordinary character */
|
||||
#define CSHMETA 0x0001 /* shell meta character */
|
||||
#define CSHBRK 0x0002 /* shell break character */
|
||||
#define CBACKQ 0x0004 /* back quote */
|
||||
#define CQUOTE 0x0008 /* shell quote character */
|
||||
#define CSPECL 0x0010 /* special character that needs quoting */
|
||||
#define CEXP 0x0020 /* shell expansion character */
|
||||
#define CBSDQUOTE 0x0040 /* characters escaped by backslash in double quotes */
|
||||
#define CBSHDOC 0x0080 /* characters escaped by backslash in here doc */
|
||||
#define CGLOB 0x0100 /* globbing characters */
|
||||
#define CXGLOB 0x0200 /* extended globbing characters */
|
||||
#define CXQUOTE 0x0400 /* cquote + backslash */
|
||||
#define CSPECVAR 0x0800 /* single-character shell variable name */
|
||||
#define CSUBSTOP 0x1000 /* values of OP for ${word[:]OPstuff} */
|
||||
|
||||
/* Defines for use by the rest of the shell. */
|
||||
extern int sh_syntaxtab[];
|
||||
extern int sh_syntabsiz;
|
||||
|
||||
#define shellmeta(c) (sh_syntaxtab[(unsigned char)(c)] & CSHMETA)
|
||||
#define shellbreak(c) (sh_syntaxtab[(unsigned char)(c)] & CSHBRK)
|
||||
#define shellquote(c) (sh_syntaxtab[(unsigned char)(c)] & CQUOTE)
|
||||
|
||||
#define shellxquote(c) (sh_syntaxtab[(unsigned char)(c)] & CXQUOTE)
|
||||
|
||||
#define issyntype(c, t) ((sh_syntaxtab[(unsigned char)(c)] & (t)) != 0)
|
||||
#define notsyntype(c,t) ((sh_syntaxtab[(unsigned char)(c)] & (t)) == 0)
|
||||
|
||||
#if defined (PROCESS_SUBSTITUTION)
|
||||
# define shellexp(c) ((c) == '$' || (c) == '<' || (c) == '>')
|
||||
#else
|
||||
# define shellexp(c) ((c) == '$')
|
||||
#endif
|
||||
|
||||
#if defined (EXTENDED_GLOB)
|
||||
# define PATTERN_CHAR(c) \
|
||||
((c) == '@' || (c) == '*' || (c) == '+' || (c) == '?' || (c) == '!')
|
||||
#else
|
||||
# define PATTERN_CHAR(c) 0
|
||||
#endif
|
||||
|
||||
#define GLOB_CHAR(c) \
|
||||
((c) == '*' || (c) == '?' || (c) == '[' || (c) == ']' || (c) == '^')
|
||||
|
||||
#define CTLESC '\001'
|
||||
#define CTLNUL '\177'
|
||||
|
||||
#if !defined (HAVE_ISBLANK) && !defined (isblank)
|
||||
# define isblank(x) ((x) == ' ' || (x) == '\t')
|
||||
#endif
|
||||
|
||||
#endif /* _SYNTAX_H_ */
|
||||
+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
|
||||
|
||||
|
||||
+10
-10
@@ -1,14 +1,14 @@
|
||||
tf is a function
|
||||
tf ()
|
||||
{
|
||||
echo this is ${0##*/} >/dev/null;
|
||||
echo a | cat - >/dev/null;
|
||||
echo this is ${0##*/} > /dev/null;
|
||||
echo a | cat - > /dev/null;
|
||||
test -f ${0##*/} && echo ${0##*/} is a regular file;
|
||||
test -d ${0##*/} || echo ${0##*/} is not a directory;
|
||||
echo a;
|
||||
echo b;
|
||||
echo c;
|
||||
echo background >/dev/null & ( exit 1 );
|
||||
echo background > /dev/null & ( exit 1 );
|
||||
echo $?;
|
||||
{
|
||||
echo a
|
||||
@@ -18,20 +18,20 @@ tf ()
|
||||
test -r /dev/fd/$i;
|
||||
i=$(( i + 1 ));
|
||||
done;
|
||||
[[ -r /dev/fd/0 && -w /dev/fd/1 ]] || echo oops >/dev/null;
|
||||
[[ -r /dev/fd/0 && -w /dev/fd/1 ]] || echo oops > /dev/null;
|
||||
for name in $( echo 1 2 3 );
|
||||
do
|
||||
test -r /dev/fd/$name;
|
||||
done;
|
||||
if [[ -r /dev/fd/0 && -w /dev/fd/1 ]]; then
|
||||
echo ok >/dev/null;
|
||||
echo ok > /dev/null;
|
||||
else
|
||||
if (( 7 > 40 )); then
|
||||
echo oops;
|
||||
else
|
||||
echo done;
|
||||
fi;
|
||||
fi >/dev/null;
|
||||
fi > /dev/null;
|
||||
case $PATH in
|
||||
*$PWD*)
|
||||
echo \$PWD in \$PATH
|
||||
@@ -39,13 +39,13 @@ tf ()
|
||||
*)
|
||||
echo \$PWD not in \$PATH
|
||||
;;
|
||||
esac >/dev/null;
|
||||
esac > /dev/null;
|
||||
while false; do
|
||||
echo z;
|
||||
done >/dev/null;
|
||||
done > /dev/null;
|
||||
until true; do
|
||||
echo z;
|
||||
done >/dev/null;
|
||||
done > /dev/null;
|
||||
echo \&\|'()' \{ echo abcde \; \};
|
||||
eval fu\%nc'()' \{ echo abcde \; \};
|
||||
type fu\%nc
|
||||
@@ -54,7 +54,7 @@ tf2 is a function
|
||||
tf2 ()
|
||||
{
|
||||
( {
|
||||
time -p echo a | cat - >/dev/null
|
||||
time -p echo a | cat - > /dev/null
|
||||
} ) 2>&1
|
||||
}
|
||||
cprint.tests is a regular file
|
||||
|
||||
+2
-2
@@ -20,7 +20,7 @@ jkl mno
|
||||
fff is a function
|
||||
fff ()
|
||||
{
|
||||
ed /tmp/foo >/dev/null <<ENDOFINPUT
|
||||
ed /tmp/foo > /dev/null <<ENDOFINPUT
|
||||
/^name/d
|
||||
w
|
||||
q
|
||||
@@ -31,7 +31,7 @@ ENDOFINPUT
|
||||
fff is a function
|
||||
fff ()
|
||||
{
|
||||
ed /tmp/foo >/dev/null <<ENDOFINPUT
|
||||
ed /tmp/foo > /dev/null <<ENDOFINPUT
|
||||
/^name/d
|
||||
w
|
||||
q
|
||||
|
||||
+1
-1
@@ -78,7 +78,7 @@ read line
|
||||
echo $line
|
||||
f ()
|
||||
{
|
||||
exec 5<$0;
|
||||
exec 5< $0;
|
||||
exec 0<&5-;
|
||||
while read line; do
|
||||
echo "$line";
|
||||
|
||||
Reference in New Issue
Block a user