summary refs log tree commit diff
path: root/pkgs/shells/bash
diff options
context:
space:
mode:
authorRok Garbas <rok@garbas.si>2015-05-29 09:46:37 +0200
committerRok Garbas <rok@garbas.si>2015-05-29 10:18:06 +0200
commitbd59bf9a74797d03174ad7301405eff75b3cda9b (patch)
tree2cc38cfd1f522a97d310f8b1206bfcad9682881c /pkgs/shells/bash
parent035273f813cd11f10c08b5d83644ae4e45c37faa (diff)
downloadnixpkgs-bd59bf9a74797d03174ad7301405eff75b3cda9b.tar
nixpkgs-bd59bf9a74797d03174ad7301405eff75b3cda9b.tar.gz
nixpkgs-bd59bf9a74797d03174ad7301405eff75b3cda9b.tar.bz2
nixpkgs-bd59bf9a74797d03174ad7301405eff75b3cda9b.tar.lz
nixpkgs-bd59bf9a74797d03174ad7301405eff75b3cda9b.tar.xz
nixpkgs-bd59bf9a74797d03174ad7301405eff75b3cda9b.tar.zst
nixpkgs-bd59bf9a74797d03174ad7301405eff75b3cda9b.zip
cygwin: bash updated to 4.3 for cygwin platform
Diffstat (limited to 'pkgs/shells/bash')
-rw-r--r--pkgs/shells/bash/bash-4.1.17-9.src.patch987
-rw-r--r--pkgs/shells/bash/cygwin-bash-4.3.33-1.src.patch1393
-rw-r--r--pkgs/shells/bash/default.nix28
3 files changed, 1406 insertions, 1002 deletions
diff --git a/pkgs/shells/bash/bash-4.1.17-9.src.patch b/pkgs/shells/bash/bash-4.1.17-9.src.patch
deleted file mode 100644
index f236946483c..00000000000
--- a/pkgs/shells/bash/bash-4.1.17-9.src.patch
+++ /dev/null
@@ -1,987 +0,0 @@
---- Makefile.in	2009-12-30 10:05:40.000000000 -0800
-+++ Makefile.in	2014-10-08 13:50:27.419837900 -0700
-@@ -565,7 +565,7 @@ lint:
- 	${MAKE} ${MFLAGS} CFLAGS='${GCC_LINT_FLAGS}' .made
- 
- version.h:  $(SOURCES) config.h Makefile 
--	$(SHELL) $(SUPPORT_SRC)mkversion.sh -b -S ${topdir} -s $(RELSTATUS) -d $(Version) -o newversion.h \
-+	$(SHELL) $(SUPPORT_SRC)mkversion.sh -S ${topdir} -s $(RELSTATUS) -d $(Version) -o newversion.h \
- 		&& mv newversion.h version.h
- 
- bashversion$(EXEEXT):	patchlevel.h conftypes.h version.h buildversion.o $(SUPPORT_SRC)bashversion.c
---- bashline.c	2014-10-08 13:45:09.240173500 -0700
-+++ bashline.c	2014-10-08 13:50:27.419837900 -0700
-@@ -68,6 +68,12 @@
- #  include "pcomplete.h"
- #endif
- 
-+#ifdef __x86_64__
-+#define IMP(x) __imp_##x
-+#else
-+#define IMP(x) _imp__##x
-+#endif
-+
- /* These should agree with the defines for emacs_mode and vi_mode in
-    rldefs.h, even though that's not a public readline header file. */
- #ifndef EMACS_EDITING_MODE
-@@ -239,6 +245,11 @@ int no_empty_command_completion;
-    are the only possible matches, even if FIGNORE says to. */
- int force_fignore = 1;
- 
-+#if __CYGWIN__
-+/* If set, shorten "foo.exe" to "foo" when they are the same file.  */
-+int completion_strip_exe;
-+#endif /* __CYGWIN__ */
-+
- /* Perform spelling correction on directory names during word completion */
- int dircomplete_spelling = 0;
- 
-@@ -446,11 +457,12 @@ initialize_readline ()
-   kseq[0] = CTRL('J');
-   kseq[1] = '\0';
-   func = rl_function_of_keyseq (kseq, emacs_meta_keymap, (int *)NULL);
--  if (func == rl_vi_editing_mode)
-+  extern rl_command_func_t *IMP(rl_vi_editing_mode);
-+  if (func == rl_vi_editing_mode || func == IMP(rl_vi_editing_mode))
-     rl_unbind_key_in_map (CTRL('J'), emacs_meta_keymap);
-   kseq[0] = CTRL('M');
-   func = rl_function_of_keyseq (kseq, emacs_meta_keymap, (int *)NULL);
--  if (func == rl_vi_editing_mode)
-+  if (func == rl_vi_editing_mode || func == IMP(rl_vi_editing_mode))
-     rl_unbind_key_in_map (CTRL('M'), emacs_meta_keymap);
- #if defined (VI_MODE)
-   rl_unbind_key_in_map (CTRL('E'), vi_movement_keymap);
-@@ -469,7 +481,8 @@ initialize_readline ()
-   kseq[0] = '~';
-   kseq[1] = '\0';
-   func = rl_function_of_keyseq (kseq, emacs_meta_keymap, (int *)NULL);
--  if (func == 0 || func == rl_tilde_expand)
-+  extern rl_command_func_t *IMP(rl_tilde_expand);
-+  if (func == 0 || func == rl_tilde_expand || func == IMP(rl_tilde_expand))
-     rl_bind_keyseq_in_map (kseq, bash_complete_username, emacs_meta_keymap);
- 
-   rl_bind_key_if_unbound_in_map ('~', bash_possible_username_completions, emacs_ctlx_keymap);
-@@ -492,7 +505,8 @@ initialize_readline ()
-   kseq[0] = TAB;
-   kseq[1] = '\0';
-   func = rl_function_of_keyseq (kseq, emacs_meta_keymap, (int *)NULL);
--  if (func == 0 || func == rl_tab_insert)
-+  extern rl_command_func_t *IMP(rl_tab_insert);
-+  if (func == 0 || func == rl_tab_insert || func == IMP(rl_tab_insert))
-     rl_bind_key_in_map (TAB, dynamic_complete_history, emacs_meta_keymap);
- 
-   /* Tell the completer that we want a crack first. */
-@@ -1826,6 +1840,14 @@ globword:
-       /* If we have found a match, and it is an executable file or a
- 	 directory name, return it. */
-       if (match && executable_or_directory (val))
-+#elif __CYGWIN__
-+      /* executable_or_directory will do the right thing on //server,
-+	 but calling stat("//server") is an order of magnitude slower
-+	 than noting that readdir("//") only returns directories.  */
-+      if (match && (searching_path ? executable_file (val)
-+		    : ((val[0] == '/' && val[1] == '/'
-+			&& ! strchr (&val[2], '/'))
-+		       || executable_or_directory (val))))
- #else
-       /* If we have found a match, and it is an executable file, return it.
- 	 We don't return directory names when searching $PATH, since the
-@@ -1835,6 +1857,21 @@ globword:
-       if (match && (searching_path ? executable_file (val) : executable_or_directory (val)))
- #endif
- 	{
-+#if __CYGWIN__
-+          if (completion_strip_exe)
-+            {
-+              int val_len = strlen (val);
-+              char *candidate;
-+              if (val_len > 4 && !strcasecmp (&val[val_len - 4], ".exe")
-+                  && (candidate = strdup (val)))
-+                {
-+                  candidate[val_len - 4] = '\0';
-+                  if (same_file (val, candidate, NULL, NULL))
-+                    temp[strlen (temp) - 4] = '\0';
-+                  free (candidate);
-+                }
-+            }
-+#endif
- 	  free (val);
- 	  val = "";		/* So it won't be NULL. */
- 	  return (temp);
-@@ -2566,6 +2603,17 @@ test_for_directory (name)
-   int r;
- 
-   fn = bash_tilde_expand (name, 0);
-+#if __CYGWIN__
-+  /* stat("//server") can only be successful as a directory, but takes
-+     a several-second timeout to fail.  It is much faster to assume
-+     that //server is a valid name than it is to wait for the stat,
-+     even though it gives false positives on bad names.  */
-+  if (fn[0] == '/' && fn[1] == '/' && ! strchr (&fn[2], '/'))
-+    {
-+      free (fn);
-+      return 1;
-+    }
-+#endif /* __CYGWIN__ */
-   r = file_isdir (fn);
-   free (fn);
- 
---- builtins/evalfile.c	2009-10-19 14:38:21.000000000 -0700
-+++ builtins/evalfile.c	2014-10-08 13:50:27.419837900 -0700
-@@ -148,10 +148,6 @@ file_error_and_exit:
-       return ((flags & FEVAL_BUILTIN) ? EXECUTION_FAILURE : -1);
-     }      
- 
--#if defined (__CYGWIN__) && defined (O_TEXT)
--  setmode (fd, O_TEXT);
--#endif
--
-   if (S_ISREG (finfo.st_mode) && file_size <= SSIZE_MAX)
-     {
-       string = (char *)xmalloc (1 + file_size);
---- builtins/set.def	2009-01-04 11:32:23.000000000 -0800
-+++ builtins/set.def	2014-10-08 13:50:27.419837900 -0700
-@@ -56,6 +56,13 @@ extern int dont_save_function_defs;
- #if defined (READLINE)
- extern int no_line_editing;
- #endif /* READLINE */
-+#if __CYGWIN__
-+extern int igncr;
-+static int set_minus_o_option_maybe (int, const char *, int);
-+# define INTERACTIVE_ONLY ,1
-+#else /* ! __CYGWIN__ */
-+# define INTERACTIVE_ONLY
-+#endif
- 
- $BUILTIN set
- $FUNCTION set_builtin
-@@ -92,6 +99,9 @@ Options:
- #if defined (HISTORY)
-           history      enable command history
- #endif
-+#if __CYGWIN__
-+          igncr        on cygwin, ignore \r in line endings
-+#endif
-           ignoreeof    the shell will not exit upon reading EOF
-           interactive-comments
-                        allow comments to appear in interactive commands
-@@ -181,28 +191,40 @@ const struct {
-   int *variable;
-   setopt_set_func_t *set_func;
-   setopt_get_func_t *get_func;
-+#if __CYGWIN__
-+  /* Cygwin users have taken to exporting SHELLOPTS for the
-+     cygwin-specific igncr.  As a result, we need to make sure
-+     SHELLOPTS parsing does not turn on interactive options when
-+     exported from an interactive shell, but parsed in a
-+     non-interactive setting, since some interactive options violate
-+     POSIX /bin/sh rules.  */
-+  int interactive_only;
-+#endif /* __CYGWIN__ */
- } o_options[] = {
-   { "allexport",  'a', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL },
- #if defined (BRACE_EXPANSION)
-   { "braceexpand",'B', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
- #endif
- #if defined (READLINE)
--  { "emacs",     '\0', (int *)NULL, set_edit_mode, get_edit_mode },
-+  { "emacs",     '\0', (int *)NULL, set_edit_mode, get_edit_mode INTERACTIVE_ONLY},
- #endif
-   { "errexit",	  'e', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
-   { "errtrace",	  'E', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
-   { "functrace",  'T', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
-   { "hashall",    'h', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
- #if defined (BANG_HISTORY)
--  { "histexpand", 'H', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
-+  { "histexpand", 'H', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  INTERACTIVE_ONLY},
- #endif /* BANG_HISTORY */
- #if defined (HISTORY)
--  { "history",   '\0', &enable_history_list, bash_set_history, (setopt_get_func_t *)NULL },
-+  { "history",   '\0', &enable_history_list, bash_set_history, (setopt_get_func_t *)NULL INTERACTIVE_ONLY},
-+#endif
-+#if __CYGWIN__
-+  { "igncr", '\0', &igncr, NULL, (setopt_get_func_t *)NULL },
- #endif
-   { "ignoreeof", '\0', &ignoreeof, set_ignoreeof, (setopt_get_func_t *)NULL },
-   { "interactive-comments", '\0', &interactive_comments, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL },
-   { "keyword",    'k', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
--  { "monitor",	  'm', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
-+  { "monitor",	  'm', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  INTERACTIVE_ONLY},
-   { "noclobber",  'C', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
-   { "noexec",	  'n', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
-   { "noglob",	  'f', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
-@@ -220,7 +242,7 @@ const struct {
-   { "privileged", 'p', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
-   { "verbose",	  'v', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
- #if defined (READLINE)
--  { "vi",        '\0', (int *)NULL, set_edit_mode, get_edit_mode },
-+  { "vi",        '\0', (int *)NULL, set_edit_mode, get_edit_mode INTERACTIVE_ONLY},
- #endif
-   { "xtrace",	  'x', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
-   {(char *)NULL, 0 , (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL },
-@@ -407,6 +429,15 @@ int
- set_minus_o_option (on_or_off, option_name)
-      int on_or_off;
-      char *option_name;
-+#if __CYGWIN__
-+{
-+  /* See cygwin comments above.  */
-+  return set_minus_o_option_maybe (on_or_off, option_name, 0);
-+}
-+static int
-+set_minus_o_option_maybe (int on_or_off, const char *option_name,
-+			  int avoid_interactive)
-+#endif /* __CYGWIN__ */
- {
-   register int i;
- 
-@@ -414,6 +445,10 @@ set_minus_o_option (on_or_off, option_na
-     {
-       if (STREQ (option_name, o_options[i].name))
- 	{
-+#if __CYGWIN__
-+	  if (o_options[i].interactive_only && avoid_interactive)
-+	    return EXECUTION_SUCCESS;
-+#endif /* __CYGWIN__ */
- 	  if (o_options[i].letter == 0)
- 	    {
- 	      SET_BINARY_O_OPTION_VALUE (i, on_or_off, option_name);
-@@ -539,7 +574,11 @@ parse_shellopts (value)
-   vptr = 0;
-   while (vname = extract_colon_unit (value, &vptr))
-     {
-+#if __CYGWIN__
-+    set_minus_o_option_maybe (FLAG_ON, vname, !interactive_shell);
-+#else /* !__CYGWIN__ */
-       set_minus_o_option (FLAG_ON, vname);
-+#endif
-       free (vname);
-     }
- }
---- builtins/shopt.def	2009-12-22 13:25:32.000000000 -0800
-+++ builtins/shopt.def	2014-10-08 13:50:27.435414600 -0700
-@@ -85,6 +85,10 @@ extern int check_jobs_at_exit;
- extern int autocd;
- extern int glob_star;
- 
-+#if defined(__CYGWIN__) && defined(READLINE)
-+extern int completion_strip_exe;
-+#endif
-+
- #if defined (EXTENDED_GLOB)
- extern int extended_glob;
- #endif
-@@ -146,6 +150,9 @@ static struct {
-   { "compat31", &shopt_compat31, set_compatibility_level },
-   { "compat32", &shopt_compat32, set_compatibility_level },
-   { "compat40", &shopt_compat40, set_compatibility_level },
-+#if defined(__CYGWIN__) && defined(READLINE)
-+ { "completion_strip_exe", &completion_strip_exe, NULL },
-+#endif
- #if defined (READLINE)
-   { "dirspell", &dircomplete_spelling, (shopt_set_func_t *)NULL },
- #endif
---- config-top.h	2009-12-22 12:29:39.000000000 -0800
-+++ config-top.h	2014-10-08 13:50:27.435414600 -0700
-@@ -75,10 +75,10 @@
- #define KSH_COMPATIBLE_SELECT
- 
- /* System-wide .bashrc file for interactive shells. */
--/* #define SYS_BASHRC "/etc/bash.bashrc" */
-+//set by nix #define SYS_BASHRC "/etc/bash.bashrc"
- 
- /* System-wide .bash_logout for login shells. */
--/* #define SYS_BASH_LOGOUT "/etc/bash.bash_logout" */
-+//set by nix #define SYS_BASH_LOGOUT "/etc/bash.bash_logout"
- 
- /* Define this to make non-interactive shells begun with argv[0][0] == '-'
-    run the startup files when not in posix mode. */
-@@ -88,7 +88,7 @@
-    sshd and source the .bashrc if so (like the rshd behavior).  This checks
-    for the presence of SSH_CLIENT or SSH2_CLIENT in the initial environment,
-    which can be fooled under certain not-uncommon circumstances. */
--/* #define SSH_SOURCE_BASHRC */
-+//set by nix #define SSH_SOURCE_BASHRC
- 
- /* Define if you want the case-capitalizing operators (~[~]) and the
-    `capcase' variable attribute (declare -c). */
---- doc/Makefile.in	2009-03-10 08:44:30.000000000 -0700
-+++ doc/Makefile.in	2014-10-08 13:50:27.435414600 -0700
-@@ -170,7 +170,7 @@ bashref.html: $(BASHREF_FILES) $(HSUSER)
- 	$(TEXI2HTML) -menu -monolithic -I $(TEXINPUTDIR) $(srcdir)/bashref.texi
- 
- bash.info: bashref.info
--	${SHELL} ${INFOPOST} < $(srcdir)/bashref.info > $@ ; \
-+	${SHELL} ${INFOPOST} < bashref.info > $@ ; \
- 
- bash.txt: bash.1
- bash.ps: bash.1
-@@ -226,9 +226,9 @@ install: info installdirs bash.info
- 	-$(INSTALL_DATA) $(srcdir)/bash.1 $(DESTDIR)$(man1dir)/bash${man1ext}
- 	-$(INSTALL_DATA) $(srcdir)/bashbug.1 $(DESTDIR)$(man1dir)/bashbug${man1ext}
- # uncomment the next lines to install the builtins man page
--#	sed 's:bash\.1:man1/&:' $(srcdir)/builtins.1 > $${TMPDIR:-/var/tmp}/builtins.1
--#	-$(INSTALL_DATA) $${TMPDIR:-/var/tmp}/builtins.1 $(DESTDIR)$(man1dir)/bash_builtins${man1ext}
--#	-$(RM) $${TMPDIR:-/var/tmp}/builtins.1
-+	sed 's:bash\.1:man1/&:' $(srcdir)/builtins.1 > $${TMPDIR:-/var/tmp}/builtins.1
-+	-$(INSTALL_DATA) $${TMPDIR:-/var/tmp}/builtins.1 $(DESTDIR)$(man1dir)/bash_builtins${man1ext}
-+	-$(RM) $${TMPDIR:-/var/tmp}/builtins.1
- 	-if test -f bash.info; then d=.; else d=$(srcdir); fi; \
- 	  $(INSTALL_DATA) $$d/bash.info $(DESTDIR)$(infodir)/bash.info
- # run install-info if it is present to update the info directory
---- doc/bash.1	2009-12-30 10:01:31.000000000 -0800
-+++ doc/bash.1	2014-10-08 13:50:27.435414600 -0700
-@@ -1568,6 +1568,14 @@ subsequently reset.
- Expands to the effective user ID of the current user, initialized at
- shell startup.  This variable is readonly.
- .TP
-+.B EXECIGNORE
-+A colon-separated list of extended glob (see \fBPattern Matching\fP)
-+patterns. Files with full paths matching one of these patterns are
-+not considered executable for the purposes of completion and PATH
-+searching, but the \fB[\fP, \fB[[\fP, and \fBtest\fP builtins are not
-+affected. Use this variable to deal with systems that set the
-+executable bit on files that are not actually executable.
-+.TP
- .B FUNCNAME
- An array variable containing the names of all shell functions
- currently in the execution call stack.
-@@ -8772,6 +8780,10 @@ If set,
- attempts spelling correction on directory names during word completion
- if the directory name initially supplied does not exist.
- .TP 8
-+.B completion_strip_exe
-+If set, whenever bash sees `foo.exe' during completion, it checks if
-+`foo' is the same file and strips the suffix.
-+.TP 8
- .B dotglob
- If set, 
- .B bash
---- doc/bashref.texi	2009-12-29 12:59:18.000000000 -0800
-+++ doc/bashref.texi	2014-10-08 13:50:27.435414600 -0700
-@@ -4363,6 +4363,10 @@ If set, Bash
- changes its behavior to that of version 3.1 with respect to quoted
- arguments to the conditional command's =~ operator.
- 
-+@item completion_strip_exe
-+If set, whenever bash sees `foo.exe' during completion, it checks if
-+`foo' is the same file and strips the suffix.
-+
- @item dirspell
- If set, Bash
- attempts spelling correction on directory names during word completion 
-@@ -4892,6 +4896,14 @@ emacs shell buffer and disables line edi
- The numeric effective user id of the current user.  This variable
- is readonly.
- 
-+@item EXECIGNORE
-+A colon-separated list of extended glob ((@pxref{Pattern Matching})
-+patterns. Files with full paths matching one of these patterns are
-+not considered executable for the purposes of completion and PATH
-+searching, but the @code{[}, @code{[[}, and @code{test} builtins are
-+not affected. Use this variable to deal with systems that set the
-+executable bit on files that are not actually executable.
-+
- @item FCEDIT
- The editor used as a default by the @option{-e} option to the @code{fc}
- builtin command.
---- doc/builtins.1	2008-08-12 06:24:40.000000000 -0700
-+++ doc/builtins.1	2014-10-08 13:50:27.435414600 -0700
-@@ -12,6 +12,6 @@ shift, shopt, source, suspend, test, tim
- ulimit, umask, unalias, unset, wait \- bash built-in commands, see \fBbash\fR(1)
- .SH BASH BUILTIN COMMANDS
- .nr zZ 1
--.so bash.1
-+.so man1/bash.1
- .SH SEE ALSO
- bash(1), sh(1)
---- execute_cmd.c	2009-12-30 09:55:37.000000000 -0800
-+++ execute_cmd.c	2014-10-08 13:50:27.435414600 -0700
-@@ -4004,7 +4004,7 @@ execute_function (var, words, flags, fds
-   char *debug_trap, *error_trap, *return_trap;
- #if defined (ARRAY_VARS)
-   SHELL_VAR *funcname_v, *nfv, *bash_source_v, *bash_lineno_v;
--  ARRAY *funcname_a, *bash_source_a, *bash_lineno_a;
-+  ARRAY *funcname_a, *volatile bash_source_a, *volatile bash_lineno_a;
- #endif
-   FUNCTION_DEF *shell_fn;
-   char *sfile, *t;
-@@ -4571,6 +4571,12 @@ execute_disk_command (words, redirects,
- 	  hookf = find_function (NOTFOUND_HOOK);
- 	  if (hookf == 0)
- 	    {
-+#if __CYGWIN__
-+              /* Point out \r use to clueless users. The memory leak
-+                 is harmless - we're about to exit. */
-+              if (ansic_shouldquote (pathname))
-+                pathname = ansic_quote (pathname, 0, NULL);
-+#endif /* __CYGWIN__ */
- 	      internal_error (_("%s: command not found"), pathname);
- 	      exit (EX_NOTFOUND);	/* Posix.2 says the exit status is 127 */
- 	    }
-@@ -4990,6 +4996,10 @@ do_piping (pipe_in, pipe_out)
- 	dup_error (pipe_in, 0);
-       if (pipe_in > 0)
- 	close (pipe_in);
-+#if __CYGWIN__
-+      /* Let stdio know that fd may have changed from text to binary.  */
-+      freopen (NULL, "r", stdin);
-+#endif /* __CYGWIN__ */
-     }
-   if (pipe_out != NO_PIPE)
-     {
-@@ -5005,5 +5015,12 @@ do_piping (pipe_in, pipe_out)
- 	  if (dup2 (1, 2) < 0)
- 	    dup_error (1, 2);
- 	}
-+#if __CYGWIN__
-+      extern int sh_setlinebuf (FILE *);
-+      /* Let stdio know that fd may have changed from text to binary.  */
-+      freopen (NULL, "w", stdout);
-+      /* Bash builtins (foolishly) rely on line-buffering. */
-+      sh_setlinebuf (stdout);
-+#endif /* __CYGWIN__ */
-     }
- }
---- findcmd.c	2009-06-05 13:25:38.000000000 -0700
-+++ findcmd.c	2014-10-08 13:50:27.451015900 -0700
-@@ -43,6 +43,8 @@
- #include "hashcmd.h"
- #include "findcmd.h"	/* matching prototypes and declarations */
- 
-+#include <glob/strmatch.h>
-+
- extern int posixly_correct;
- 
- /* Static functions defined and used in this file. */
-@@ -71,6 +73,38 @@ int check_hashed_filenames;
-    containing the file of interest. */
- int dot_found_in_search = 0;
- 
-+static struct ignorevar execignore =
-+{
-+  "EXECIGNORE",
-+  (struct ign *)0,
-+  0,
-+  (char *)0,
-+  (sh_iv_item_func_t *)0,
-+};
-+
-+void
-+setup_exec_ignore (char *varname)
-+{
-+  setup_ignore_patterns (&execignore);
-+}
-+
-+/* Return whether we should never consider file executable
-+ * even if the system tells us it is. */
-+static int
-+is_on_exec_blacklist (char *name)
-+{
-+  struct ign *p;
-+  int flags = FNM_EXTMATCH | FNM_CASEFOLD;
-+
-+  for (p = execignore.ignores; p && p->val; p++)
-+    {
-+      if (strmatch (p->val, (char *)name, flags) != FNM_NOMATCH)
-+      return (1);
-+    }
-+
-+  return (0);
-+}
-+
- /* Return some flags based on information about this file.
-    The EXISTS bit is non-zero if the file is found.
-    The EXECABLE bit is non-zero the file is executble.
-@@ -98,7 +132,7 @@ file_status (name)
-      file access mechanisms into account.  eaccess uses the effective
-      user and group IDs, not the real ones.  We could use sh_eaccess,
-      but we don't want any special treatment for /dev/fd. */
--  if (eaccess (name, X_OK) == 0)
-+  if (!is_on_exec_blacklist (name) && eaccess (name, X_OK) == 0)
-     r |= FS_EXECABLE;
-   if (eaccess (name, R_OK) == 0)
-     r |= FS_READABLE;
---- findcmd.h	2009-01-04 11:32:29.000000000 -0800
-+++ findcmd.h	2014-10-08 13:50:27.451015900 -0700
-@@ -31,5 +31,6 @@ extern char *find_user_command __P((cons
- extern char *find_path_file __P((const char *));
- extern char *search_for_command __P((const char *));
- extern char *user_command_matches __P((const char *, int, int));
-+extern void setup_exec_ignore __P((char *));
- 
- #endif /* _FINDCMD_H_ */
---- general.c	2009-11-28 18:44:46.000000000 -0800
-+++ general.c	2014-10-08 13:50:27.451015900 -0700
-@@ -43,6 +43,10 @@
- 
- #include <tilde/tilde.h>
- 
-+#ifdef __CYGWIN__
-+#include <sys/cygwin.h>
-+#endif
-+
- #if !defined (errno)
- extern int errno;
- #endif /* !errno */
-@@ -601,7 +605,8 @@ make_absolute (string, dot_path)
-     {
-       char pathbuf[PATH_MAX + 1];
- 
--      cygwin_conv_to_full_posix_path (string, pathbuf);
-+      cygwin_conv_path (CCP_WIN_A_TO_POSIX | CCP_ABSOLUTE, string, pathbuf,
-+			PATH_MAX + 1);
-       result = savestring (pathbuf);
-     }
- #else
---- input.c	2009-01-04 11:32:29.000000000 -0800
-+++ input.c	2014-10-08 13:50:27.451015900 -0700
-@@ -43,6 +43,10 @@
- #include "externs.h"
- #include "quit.h"
- 
-+#if __CYGWIN__
-+int igncr;
-+#endif /* __CYGWIN__ */
-+
- #if !defined (errno)
- extern int errno;
- #endif /* !errno */
-@@ -193,6 +197,10 @@ make_buffered_stream (fd, buffer, bufsiz
-   bp->b_used = bp->b_inputp = bp->b_flag = 0;
-   if (bufsize == 1)
-     bp->b_flag |= B_UNBUFF;
-+#if __CYGWIN__
-+  if ((fcntl (fd, F_GETFL) & O_TEXT) != 0)
-+    bp->b_flag |= B_TEXT;
-+#endif /* __CYGWIN__ */
-   return (bp);
- }
- 
-@@ -361,11 +369,7 @@ duplicate_buffered_stream (fd1, fd2)
- }
- 
- /* Return 1 if a seek on FD will succeed. */
--#ifndef __CYGWIN__
- #  define fd_is_seekable(fd) (lseek ((fd), 0L, SEEK_CUR) >= 0)
--#else
--#  define fd_is_seekable(fd) 0
--#endif /* __CYGWIN__ */
- 
- /* Take FD, a file descriptor, and create and return a buffered stream
-    corresponding to it.  If something is wrong and the file descriptor
-@@ -474,6 +478,25 @@ b_fill_buffer (bp)
-   ssize_t nr;
- 
-   CHECK_TERMSIG;
-+#ifdef __CYGWIN__
-+  /* lseek'ing on text files is problematic; lseek reports the true
-+     file offset, but read collapses \r\n and returns a character
-+     count.  We cannot reliably seek backwards if nr is smaller than
-+     the seek offset encountered during the read, and must instead
-+     treat the stream as unbuffered.  */
-+  if ((bp->b_flag & (B_TEXT | B_UNBUFF)) == B_TEXT)
-+    {
-+      off_t offset = lseek (bp->b_fd, 0, SEEK_CUR);
-+      nr = zread (bp->b_fd, bp->b_buffer, bp->b_size);
-+      if (nr > 0 && nr < lseek (bp->b_fd, 0, SEEK_CUR) - offset)
-+	{
-+	  lseek (bp->b_fd, offset, SEEK_SET);
-+	  bp->b_flag |= B_UNBUFF;
-+	  nr = zread (bp->b_fd, bp->b_buffer, bp->b_size = 1);
-+	}
-+    }
-+  else
-+#endif /* __CYGWIN__ */
-   nr = zread (bp->b_fd, bp->b_buffer, bp->b_size);
-   if (nr <= 0)
-     {
-@@ -486,15 +509,6 @@ b_fill_buffer (bp)
-       return (EOF);
-     }
- 
--#if defined (__CYGWIN__)
--  /* If on cygwin, translate \r\n to \n. */
--  if (nr >= 2 && bp->b_buffer[nr - 2] == '\r' && bp->b_buffer[nr - 1] == '\n')
--    {
--      bp->b_buffer[nr - 2] = '\n';
--      nr--;
--    }
--#endif
--
-   bp->b_used = nr;
-   bp->b_inputp = 0;
-   return (bp->b_buffer[bp->b_inputp++] & 0xFF);
-@@ -543,6 +557,19 @@ buffered_getchar ()
- {
-   CHECK_TERMSIG;
- 
-+#if __CYGWIN__
-+  /* shopt igncr means to discard carriage returns from input stream.
-+     If cr is the only character in the buffer, then recurse to pick
-+     up the next character; otherwise flatten the buffer.  */
-+  if (igncr)
-+    {
-+      int ch;
-+      while ((ch = bufstream_getc (buffers[bash_input.location.buffered_fd]))
-+	     == '\r')
-+	;
-+      return ch;
-+    }
-+#endif /* __CYGWIN__ */
- #if !defined (DJGPP)
-   return (bufstream_getc (buffers[bash_input.location.buffered_fd]));
- #else
---- input.h	2009-01-04 11:32:29.000000000 -0800
-+++ input.h	2014-10-08 13:50:27.451015900 -0700
-@@ -48,6 +48,7 @@ enum stream_type {st_none, st_stdin, st_
- #define B_ERROR		0x02
- #define B_UNBUFF	0x04
- #define B_WASBASHINPUT	0x08
-+#define B_TEXT          0x10 /* Text stream, when O_BINARY is nonzero */
- 
- /* A buffered stream.  Like a FILE *, but with our own buffering and
-    synchronization.  Look in input.c for the implementation. */
---- lib/sh/pathcanon.c	2008-08-12 11:01:37.000000000 -0700
-+++ lib/sh/pathcanon.c	2014-10-08 13:50:27.451015900 -0700
-@@ -194,6 +194,8 @@ sh_canonpath (path, flags)
- 	    *q++ = DIRSEP;
- 	  while (*p && (ISDIRSEP(*p) == 0))
- 	    *q++ = *p++;
-+	}
-+    }
- 	  /* Check here for a valid directory with _path_isdir. */
- 	  if (flags & PATH_CHECKEXISTS)
- 	    {
-@@ -211,8 +213,7 @@ sh_canonpath (path, flags)
- 		}
- 	      *q = c;
- 	    }
--	}
--    }
-+
- 
-   /* Empty string is really ``.'' or `/', depending on what we started with. */
-   if (q == result)
---- lib/sh/pathphys.c	2008-08-12 11:01:23.000000000 -0700
-+++ lib/sh/pathphys.c	2014-10-08 13:50:27.451015900 -0700
-@@ -35,6 +35,7 @@
- #include <stdio.h>
- #include <chartypes.h>
- #include <errno.h>
-+#include <stdlib.h>
- 
- #include "shell.h"
- 
-@@ -76,6 +77,10 @@ sh_physpath (path, flags)
-      char *path;
-      int flags;
- {
-+#if __CYGWIN__
-+  /* realpath does this right without all the hassle */
-+  return realpath (path, NULL);
-+#else
-   char tbuf[PATH_MAX+1], linkbuf[PATH_MAX+1];
-   char *result, *p, *q, *qsave, *qbase, *workpath;
-   int double_slash_path, linklen, nlink;
-@@ -249,6 +254,7 @@ error:
-     }
- 
-   return (result);
-+#endif /* !__CYGWIN__ */
- }
- 
- char *
---- lib/sh/tmpfile.c	2008-08-12 10:50:12.000000000 -0700
-+++ lib/sh/tmpfile.c	2014-10-08 13:50:27.451015900 -0700
-@@ -40,7 +40,7 @@
- extern int errno;
- #endif
- 
--#define BASEOPENFLAGS	(O_CREAT | O_TRUNC | O_EXCL)
-+#define BASEOPENFLAGS	(O_CREAT | O_TRUNC | O_EXCL | O_BINARY)
- 
- #define DEFAULT_TMPDIR		"."	/* bogus default, should be changed */
- #define DEFAULT_NAMEROOT	"shtmp"
-@@ -94,7 +94,7 @@ get_tmpdir (flags)
-   if (tdir && (file_iswdir (tdir) == 0 || strlen (tdir) > PATH_MAX))
-     tdir = 0;
- 
--  if (tdir == 0)
-+  if (tdir == 0 || !file_iswdir (tdir))
-     tdir = get_sys_tmpdir ();
- 
- #if defined (HAVE_PATHCONF) && defined (_PC_NAME_MAX)
-@@ -116,14 +116,15 @@ sh_mktmpname (nameroot, flags)
-   struct stat sb;
-   int r, tdlen;
- 
--  filename = (char *)xmalloc (PATH_MAX + 1);
-+  filename = NULL;
-   tdir = get_tmpdir (flags);
-   tdlen = strlen (tdir);
- 
-   lroot = nameroot ? nameroot : DEFAULT_NAMEROOT;
- 
- #ifdef USE_MKTEMP
--  sprintf (filename, "%s/%s.XXXXXX", tdir, lroot);
-+  if (asprintf (&filename, "%s/%s.XXXXXX", tdir, lroot) < 0)
-+    return NULL;
-   if (mktemp (filename) == 0)
-     {
-       free (filename);
-@@ -136,7 +137,9 @@ sh_mktmpname (nameroot, flags)
- 		(unsigned long) time ((time_t *)0) ^
- 		(unsigned long) dollar_dollar_pid ^
- 		(unsigned long) ((flags & MT_USERANDOM) ? get_random_number () : ntmpfiles++);
--      sprintf (filename, "%s/%s-%lu", tdir, lroot, filenum);
-+      free (filename);
-+      if (asprintf (&filename, "%s/%s-%lu", tdir, lroot, filenum) < 0)
-+        return NULL;
-       if (tmpnamelen > 0 && tmpnamelen < 32)
- 	filename[tdlen + 1 + tmpnamelen] = '\0';
- #  ifdef HAVE_LSTAT
-@@ -161,14 +164,19 @@ sh_mktmpfd (nameroot, flags, namep)
-   char *filename, *tdir, *lroot;
-   int fd, tdlen;
- 
--  filename = (char *)xmalloc (PATH_MAX + 1);
-+  filename = NULL;
-   tdir = get_tmpdir (flags);
-   tdlen = strlen (tdir);
- 
-   lroot = nameroot ? nameroot : DEFAULT_NAMEROOT;
- 
- #ifdef USE_MKSTEMP
--  sprintf (filename, "%s/%s.XXXXXX", tdir, lroot);
-+  if (asprintf (&filename, "%s/%s.XXXXXX", tdir, lroot) < 0)
-+    {
-+      if (namep)
-+        *namep = NULL;
-+      return -1;
-+    }
-   fd = mkstemp (filename);
-   if (fd < 0 || namep == 0)
-     {
-@@ -185,7 +193,13 @@ sh_mktmpfd (nameroot, flags, namep)
- 		(unsigned long) time ((time_t *)0) ^
- 		(unsigned long) dollar_dollar_pid ^
- 		(unsigned long) ((flags & MT_USERANDOM) ? get_random_number () : ntmpfiles++);
--      sprintf (filename, "%s/%s-%lu", tdir, lroot, filenum);
-+      free (filename);
-+      if (asprintf (&filename, "%s/%s-%lu", tdir, lroot, filenum) < 0)
-+        {
-+          if (namep)
-+            *namep = NULL;
-+          return -1;
-+        }
-       if (tmpnamelen > 0 && tmpnamelen < 32)
- 	filename[tdlen + 1 + tmpnamelen] = '\0';
-       fd = open (filename, BASEOPENFLAGS | ((flags & MT_READWRITE) ? O_RDWR : O_WRONLY), 0600);
---- parse.y	2014-10-08 13:45:10.394563700 -0700
-+++ parse.y	2014-10-08 13:50:27.451015900 -0700
-@@ -1520,14 +1520,20 @@ yy_string_get ()
-   string = bash_input.location.string;
- 
-   /* If the string doesn't exist, or is empty, EOF found. */
--  if (string && *string)
-+  while (string && *string)
-     {
-       c = *string++;
-       bash_input.location.string = string;
-+#if __CYGWIN__
-+      {
-+        extern int igncr;
-+        if (igncr && c == '\r')
-+          continue;
-+      }
-+#endif /* __CYGWIN__ */
-       return (c);
-     }
--  else
--    return (EOF);
-+  return (EOF);
- }
- 
- static int
-@@ -5487,6 +5493,15 @@ report_syntax_error (message)
-      parser's complaining about by looking at current_token. */
-   if (current_token != 0 && EOF_Reached == 0 && (msg = error_token_from_token (current_token)))
-     {
-+#if __CYGWIN__
-+      /* Try to help clueless users. */
-+      char *p = msg;
-+      if (ansic_shouldquote (msg))
-+        {
-+          msg = ansic_quote (msg, 0, NULL);
-+          free (p);
-+        }
-+#endif /* __CYGWIN__ */
-       parser_error (line_number, _("syntax error near unexpected token `%s'"), msg);
-       free (msg);
- 
---- pathexp.h	2009-01-04 11:32:40.000000000 -0800
-+++ pathexp.h	2014-10-08 13:50:27.451015900 -0700
-@@ -86,7 +86,7 @@ struct ign {
- typedef int sh_iv_item_func_t __P((struct ign *));
- 
- struct ignorevar {
--  char *varname;	/* FIGNORE or GLOBIGNORE */
-+  char *varname;	/* FIGNORE or GLOBIGNORE or EXECIGNORE */
-   struct ign *ignores;	/* Store the ignore strings here */
-   int num_ignores;	/* How many are there? */
-   char *last_ignoreval;	/* Last value of variable - cached for speed */
---- redir.c	2009-09-17 07:04:18.000000000 -0700
-+++ redir.c	2014-10-08 13:50:27.451015900 -0700
-@@ -437,7 +437,7 @@ here_document_to_fd (redirectee, ri)
-   /* In an attempt to avoid races, we close the first fd only after opening
-      the second. */
-   /* Make the document really temporary.  Also make it the input. */
--  fd2 = open (filename, O_RDONLY, 0600);
-+  fd2 = open (filename, O_RDONLY | O_BINARY, 0600);
- 
-   if (fd2 < 0)
-     {
-@@ -453,14 +453,6 @@ here_document_to_fd (redirectee, ri)
-   if (unlink (filename) < 0)
-     {
-       r = errno;
--#if defined (__CYGWIN__)
--      /* Under CygWin 1.1.0, the unlink will fail if the file is
--	 open. This hack will allow the previous action of silently
--	 ignoring the error, but will still leave the file there. This
--	 needs some kind of magic. */
--      if (r == EACCES)
--	return (fd2);
--#endif /* __CYGWIN__ */
-       close (fd2);
-       free (filename);
-       errno = r;
---- shell.c	2009-11-19 07:05:54.000000000 -0800
-+++ shell.c	2014-10-08 13:50:27.466607600 -0700
-@@ -329,7 +329,10 @@ _cygwin32_check_tmp ()
-   struct stat sb;
- 
-   if (stat ("/tmp", &sb) < 0)
--    internal_warning (_("could not find /tmp, please create!"));
-+    {
-+      if (mkdir ("/tmp", S_IRWXU | S_IRWXG | S_IRWXO | S_ISVTX) != 0)
-+        internal_warning (_("could not find /tmp, please create!"));
-+    }
-   else
-     {
-       if (S_ISDIR (sb.st_mode) == 0)
-@@ -1471,10 +1474,6 @@ open_shell_script (script_name)
-      not match with ours. */
-   fd = move_to_high_fd (fd, 1, -1);
- 
--#if defined (__CYGWIN__) && defined (O_TEXT)
--  setmode (fd, O_TEXT);
--#endif
--
- #if defined (BUFFERED_INPUT)
-   default_buffered_input = fd;
-   SET_CLOSE_ON_EXEC (default_buffered_input);
---- subst.c	2009-12-30 05:24:28.000000000 -0800
-+++ subst.c	2014-10-08 13:50:27.466607600 -0700
-@@ -4921,10 +4921,6 @@ read_comsub (fd, quoted, rflag)
-   for (skip_ctlesc = skip_ctlnul = 0, s = ifs_value; s && *s; s++)
-     skip_ctlesc |= *s == CTLESC, skip_ctlnul |= *s == CTLNUL;
- 
--#ifdef __CYGWIN__
--  setmode (fd, O_TEXT);		/* we don't want CR/LF, we want Unix-style */
--#endif
--
-   /* Read the output of the command through the pipe.  This may need to be
-      changed to understand multibyte characters in the future. */
-   while (1)
-@@ -4947,6 +4943,13 @@ read_comsub (fd, quoted, rflag)
- #endif
- 	  continue;
- 	}
-+#if __CYGWIN__
-+      {
-+	extern int igncr;
-+	if (igncr && c == '\r')
-+	  continue;
-+      }
-+#endif /* __CYGWIN__ */
- 
-       /* Add the character to ISTRING, possibly after resizing it. */
-       RESIZE_MALLOCED_BUFFER (istring, istring_index, 2, istring_size, DEFAULT_ARRAY_SIZE);
-@@ -5063,6 +5066,27 @@ command_substitute (string, quoted)
-       sys_error (_("cannot make pipe for command substitution"));
-       goto error_exit;
-     }
-+#if __CYGWIN__
-+  /* Passing a pipe through std fds can cause hangs when talking to a
-+     non-cygwin child.  Move it.  */
-+  if (fildes[0] < 3)
-+    {
-+      int fd = fcntl (fildes[0], F_DUPFD, 3);
-+      close (fildes[0]);
-+      fildes[0] = fd;
-+    }
-+  if (fildes[1] < 3)
-+    {
-+      int fd = fcntl (fildes[1], F_DUPFD, 3);
-+      close (fildes[1]);
-+      fildes[1] = fd;
-+    }
-+  if (fildes[0] < 0 || fildes[1] < 0)
-+    {
-+      sys_error (_("cannot make pipe for command substitution"));
-+      goto error_exit;
-+    }
-+#endif /* __CYGWIN__ */
- 
-   old_pid = last_made_pid;
- #if defined (JOB_CONTROL)
-@@ -5130,6 +5154,12 @@ command_substitute (string, quoted)
- 	  (fildes[0] != fileno (stdout)) &&
- 	  (fildes[0] != fileno (stderr)))
- 	close (fildes[0]);
-+#if __CYGWIN__
-+      /* Inform stdio if any text/binary changes happened. */
-+      freopen (NULL, "w", stdout);
-+      /* Bash builtins (foolishly) rely on line-buffering. */
-+      sh_setlinebuf (stdout);
-+#endif /* __CYGWIN__ */
- 
-       /* The currently executing shell is not interactive. */
-       interactive = 0;
---- variables.c	2014-10-08 13:45:10.285364600 -0700
-+++ variables.c	2014-10-08 13:50:27.466607600 -0700
-@@ -4143,6 +4143,8 @@ static struct name_and_function special_
-   { "COMP_WORDBREAKS", sv_comp_wordbreaks },
- #endif
- 
-+  { "EXECIGNORE", sv_execignore },
-+
-   { "GLOBIGNORE", sv_globignore },
- 
- #if defined (HISTORY)
-@@ -4323,6 +4325,13 @@ sv_globignore (name)
-     setup_glob_ignore (name);
- }
- 
-+/* What to do when EXECIGNORE changes. */
-+void
-+sv_execignore (char *name)
-+{
-+  setup_exec_ignore (name);
-+}
-+
- #if defined (READLINE)
- void
- sv_comp_wordbreaks (name)
---- variables.h	2009-08-16 13:10:15.000000000 -0700
-+++ variables.h	2014-10-08 13:50:27.466607600 -0700
-@@ -351,6 +351,7 @@ extern void sv_ifs __P((char *));
- extern void sv_path __P((char *));
- extern void sv_mail __P((char *));
- extern void sv_globignore __P((char *));
-+extern void sv_execignore __P((char *));
- extern void sv_ignoreeof __P((char *));
- extern void sv_strict_posix __P((char *));
- extern void sv_optind __P((char *));
diff --git a/pkgs/shells/bash/cygwin-bash-4.3.33-1.src.patch b/pkgs/shells/bash/cygwin-bash-4.3.33-1.src.patch
new file mode 100644
index 00000000000..e0959d0446a
--- /dev/null
+++ b/pkgs/shells/bash/cygwin-bash-4.3.33-1.src.patch
@@ -0,0 +1,1393 @@
+--- bashline.c	2015-02-06 17:12:55.823275600 -0700
++++ bashline.c	2015-02-06 17:14:11.000103800 -0700
+@@ -71,6 +71,16 @@
+ #  include "pcomplete.h"
+ #endif
+ 
++#if __CYGWIN__
++#  ifdef __x86_64__
++#    define IMP(x) __imp_##x
++#  else
++#    define IMP(x) _imp__##x
++#  endif
++#else
++#  define IMP(x) x
++#endif
++
+ /* These should agree with the defines for emacs_mode and vi_mode in
+    rldefs.h, even though that's not a public readline header file. */
+ #ifndef EMACS_EDITING_MODE
+@@ -264,6 +274,11 @@ int no_empty_command_completion;
+    are the only possible matches, even if FIGNORE says to. */
+ int force_fignore = 1;
+ 
++#if __CYGWIN__
++/* If set, shorten "foo.exe" to "foo" when they are the same file.  */
++int completion_strip_exe;
++#endif /* __CYGWIN__ */
++
+ /* Perform spelling correction on directory names during word completion */
+ int dircomplete_spelling = 0;
+ 
+@@ -491,11 +506,12 @@ initialize_readline ()
+   kseq[0] = CTRL('J');
+   kseq[1] = '\0';
+   func = rl_function_of_keyseq (kseq, emacs_meta_keymap, (int *)NULL);
+-  if (func == rl_vi_editing_mode)
++  extern rl_command_func_t *IMP(rl_vi_editing_mode);
++  if (func == rl_vi_editing_mode || func == IMP(rl_vi_editing_mode))
+     rl_unbind_key_in_map (CTRL('J'), emacs_meta_keymap);
+   kseq[0] = CTRL('M');
+   func = rl_function_of_keyseq (kseq, emacs_meta_keymap, (int *)NULL);
+-  if (func == rl_vi_editing_mode)
++  if (func == rl_vi_editing_mode || func == IMP(rl_vi_editing_mode))
+     rl_unbind_key_in_map (CTRL('M'), emacs_meta_keymap);
+ #if defined (VI_MODE)
+   rl_unbind_key_in_map (CTRL('E'), vi_movement_keymap);
+@@ -514,7 +530,8 @@ initialize_readline ()
+   kseq[0] = '~';
+   kseq[1] = '\0';
+   func = rl_function_of_keyseq (kseq, emacs_meta_keymap, (int *)NULL);
+-  if (func == 0 || func == rl_tilde_expand)
++  extern rl_command_func_t *IMP(rl_tilde_expand);
++  if (func == 0 || func == rl_tilde_expand || func == IMP(rl_tilde_expand))
+     rl_bind_keyseq_in_map (kseq, bash_complete_username, emacs_meta_keymap);
+ 
+   rl_bind_key_if_unbound_in_map ('~', bash_possible_username_completions, emacs_ctlx_keymap);
+@@ -537,7 +554,8 @@ initialize_readline ()
+   kseq[0] = TAB;
+   kseq[1] = '\0';
+   func = rl_function_of_keyseq (kseq, emacs_meta_keymap, (int *)NULL);
+-  if (func == 0 || func == rl_tab_insert)
++  extern rl_command_func_t *IMP(rl_tab_insert);
++  if (func == 0 || func == rl_tab_insert || func == IMP(rl_tab_insert))
+     rl_bind_key_in_map (TAB, dynamic_complete_history, emacs_meta_keymap);
+ 
+   /* Tell the completer that we want a crack first. */
+@@ -2109,6 +2127,21 @@ globword:
+ 
+       if (match && executable_completion ((searching_path ? val : cval), searching_path))
+ 	{
++#if __CYGWIN__
++          if (completion_strip_exe)
++            {
++              size_t val_len = strlen (val);
++              char *candidate;
++              if (val_len > 4 && !strcasecmp (&val[val_len - 4], ".exe")
++                  && (candidate = strdup (val)))
++                {
++                  candidate[val_len - 4] = '\0';
++                  if (same_file (val, candidate, NULL, NULL))
++                    temp[strlen (temp) - 4] = '\0';
++                  free (candidate);
++                }
++            }
++#endif
+ 	  if (cval != val)
+ 	    free (cval);
+ 	  free (val);
+@@ -2844,6 +2877,17 @@ test_for_directory (name)
+   int r;
+ 
+   fn = bash_tilde_expand (name, 0);
++#if __CYGWIN__
++  /* stat("//server") can only be successful as a directory, but takes
++     a several-second timeout to fail.  It is much faster to assume
++     that //server is a valid name than it is to wait for the stat,
++     even though it gives false positives on bad names.  */
++  if (fn[0] == '/' && fn[1] == '/' && ! strchr (&fn[2], '/'))
++    {
++      free (fn);
++      return 1;
++    }
++#endif /* __CYGWIN__ */
+   r = file_isdir (fn);
+   free (fn);
+ 
+--- builtins/evalstring.c	2015-02-06 17:12:55.682776800 -0700
++++ builtins/evalstring.c	2015-02-06 17:14:11.015662800 -0700
+@@ -195,7 +195,7 @@ parse_and_execute (string, from_file, fl
+   int code, lreset;
+   volatile int should_jump_to_top_level, last_result;
+   COMMAND *volatile command;
+-  volatile sigset_t pe_sigmask;
++  sigset_t pe_sigmask;
+ 
+   parse_prologue (string, flags, PE_TAG);
+ 
+@@ -451,7 +451,7 @@ parse_string (string, from_file, flags,
+   volatile int should_jump_to_top_level;
+   COMMAND *volatile command, *oglobal;
+   char *ostring;
+-  volatile sigset_t ps_sigmask;
++  sigset_t ps_sigmask;
+ 
+   parse_prologue (string, flags, PS_TAG);
+ 
+--- builtins/set.def	2013-04-19 05:20:34.000000000 -0600
++++ builtins/set.def	2015-02-06 17:14:11.015662800 -0700
+@@ -56,6 +56,13 @@ extern int dont_save_function_defs;
+ #if defined (READLINE)
+ extern int no_line_editing;
+ #endif /* READLINE */
++#if __CYGWIN__
++extern int igncr;
++static int set_minus_o_option_maybe (int, const char *, int);
++#  define INTERACTIVE_ONLY ,1
++#else /* ! __CYGWIN__ */
++#  define INTERACTIVE_ONLY
++#endif
+ 
+ $BUILTIN set
+ $FUNCTION set_builtin
+@@ -92,6 +99,9 @@ Options:
+ #if defined (HISTORY)
+           history      enable command history
+ #endif
++#if __CYGWIN__
++          igncr        on cygwin, ignore \r in line endings
++#endif
+           ignoreeof    the shell will not exit upon reading EOF
+           interactive-comments
+                        allow comments to appear in interactive commands
+@@ -188,29 +198,41 @@ const struct {
+   int *variable;
+   setopt_set_func_t *set_func;
+   setopt_get_func_t *get_func;
++#if __CYGWIN__
++  /* Cygwin users have taken to exporting SHELLOPTS for the
++     cygwin-specific igncr.  As a result, we need to make sure
++     SHELLOPTS parsing does not turn on interactive options when
++     exported from an interactive shell, but parsed in a
++     non-interactive setting, since some interactive options violate
++     POSIX /bin/sh rules.  */
++  int interactive_only;
++#endif /* __CYGWIN__ */
+ } o_options[] = {
+   { "allexport",  'a', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL },
+ #if defined (BRACE_EXPANSION)
+   { "braceexpand",'B', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
+ #endif
+ #if defined (READLINE)
+-  { "emacs",     '\0', (int *)NULL, set_edit_mode, get_edit_mode },
++  { "emacs",     '\0', (int *)NULL, set_edit_mode, get_edit_mode INTERACTIVE_ONLY},
+ #endif
+   { "errexit",	  'e', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
+   { "errtrace",	  'E', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
+   { "functrace",  'T', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
+   { "hashall",    'h', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
+ #if defined (BANG_HISTORY)
+-  { "histexpand", 'H', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
++  { "histexpand", 'H', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL INTERACTIVE_ONLY},
+ #endif /* BANG_HISTORY */
+ #if defined (HISTORY)
+-  { "history",   '\0', &enable_history_list, bash_set_history, (setopt_get_func_t *)NULL },
++  { "history",   '\0', &enable_history_list, bash_set_history, (setopt_get_func_t *)NULL INTERACTIVE_ONLY},
++#endif
++#if __CYGWIN__
++  { "igncr", '\0', &igncr, NULL, (setopt_get_func_t *)NULL },
+ #endif
+   { "ignoreeof", '\0', &ignoreeof, set_ignoreeof, (setopt_get_func_t *)NULL },
+   { "interactive-comments", '\0', &interactive_comments, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL },
+   { "keyword",    'k', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
+ #if defined (JOB_CONTROL)
+-  { "monitor",	  'm', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
++  { "monitor",	  'm', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL INTERACTIVE_ONLY},
+ #endif
+   { "noclobber",  'C', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
+   { "noexec",	  'n', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
+@@ -229,7 +251,7 @@ const struct {
+   { "privileged", 'p', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
+   { "verbose",	  'v', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
+ #if defined (READLINE)
+-  { "vi",        '\0', (int *)NULL, set_edit_mode, get_edit_mode },
++  { "vi",        '\0', (int *)NULL, set_edit_mode, get_edit_mode INTERACTIVE_ONLY},
+ #endif
+   { "xtrace",	  'x', (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL  },
+   {(char *)NULL, 0 , (int *)NULL, (setopt_set_func_t *)NULL, (setopt_get_func_t *)NULL },
+@@ -416,6 +438,15 @@ int
+ set_minus_o_option (on_or_off, option_name)
+      int on_or_off;
+      char *option_name;
++#if __CYGWIN__
++{
++  /* See cygwin comments above.  */
++  return set_minus_o_option_maybe (on_or_off, option_name, 0);
++}
++static int
++set_minus_o_option_maybe (int on_or_off, const char *option_name,
++			  int avoid_interactive)
++#endif /* __CYGWIN__ */
+ {
+   register int i;
+ 
+@@ -423,6 +454,10 @@ set_minus_o_option (on_or_off, option_na
+     {
+       if (STREQ (option_name, o_options[i].name))
+ 	{
++#if __CYGWIN__
++	  if (o_options[i].interactive_only && avoid_interactive)
++	    return EXECUTION_SUCCESS;
++#endif /* __CYGWIN__ */
+ 	  if (o_options[i].letter == 0)
+ 	    {
+ 	      SET_BINARY_O_OPTION_VALUE (i, on_or_off, option_name);
+@@ -548,7 +583,11 @@ parse_shellopts (value)
+   vptr = 0;
+   while (vname = extract_colon_unit (value, &vptr))
+     {
++#if __CYGWIN__
++      set_minus_o_option_maybe (FLAG_ON, vname, !interactive_shell);
++#else /* !__CYGWIN__ */
+       set_minus_o_option (FLAG_ON, vname);
++#endif
+       free (vname);
+     }
+ }
+--- builtins/shopt.def	2013-02-27 07:43:20.000000000 -0700
++++ builtins/shopt.def	2015-02-06 17:14:11.015662800 -0700
+@@ -91,6 +91,11 @@ extern int glob_star;
+ extern int glob_asciirange;
+ extern int lastpipe_opt;
+ 
++#if __CYGWIN__
++extern int completion_strip_exe;
++#endif
++
++
+ #if defined (EXTENDED_GLOB)
+ extern int extended_glob;
+ #endif
+@@ -161,6 +166,9 @@ static struct {
+   { "compat40", &shopt_compat40, set_compatibility_level },
+   { "compat41", &shopt_compat41, set_compatibility_level },
+   { "compat42", &shopt_compat41, set_compatibility_level },
++#if __CYGWIN__
++  { "completion_strip_exe", &completion_strip_exe, NULL },
++#endif
+ #if defined (READLINE)
+   { "complete_fullquote", &complete_fullquote, (shopt_set_func_t *)NULL},
+   { "direxpand", &dircomplete_expand, shopt_set_complete_direxpand },
+--- config-top.h	2012-08-18 18:51:30.000000000 -0600
++++ config-top.h	2015-02-06 17:14:11.015662800 -0700
+@@ -80,10 +80,10 @@
+ #define KSH_COMPATIBLE_SELECT
+ 
+ /* System-wide .bashrc file for interactive shells. */
+-/* #define SYS_BASHRC "/etc/bash.bashrc" */
++#define SYS_BASHRC "/etc/bash.bashrc"
+ 
+ /* System-wide .bash_logout for login shells. */
+-/* #define SYS_BASH_LOGOUT "/etc/bash.bash_logout" */
++#define SYS_BASH_LOGOUT "/etc/bash.bash_logout"
+ 
+ /* Define this to make non-interactive shells begun with argv[0][0] == '-'
+    run the startup files when not in posix mode. */
+@@ -93,7 +93,7 @@
+    sshd and source the .bashrc if so (like the rshd behavior).  This checks
+    for the presence of SSH_CLIENT or SSH2_CLIENT in the initial environment,
+    which can be fooled under certain not-uncommon circumstances. */
+-/* #define SSH_SOURCE_BASHRC */
++#define SSH_SOURCE_BASHRC
+ 
+ /* Define if you want the case-capitalizing operators (~[~]) and the
+    `capcase' variable attribute (declare -c). */
+--- doc/Makefile.in	2013-10-30 14:18:12.000000000 -0600
++++ doc/Makefile.in	2015-02-06 17:14:11.015662800 -0700
+@@ -176,7 +176,7 @@ bashref.html: $(BASHREF_FILES) $(HSUSER)
+ 	$(TEXI2HTML) -menu -monolithic -I $(TEXINPUTDIR) $(srcdir)/bashref.texi
+ 
+ bash.info: bashref.info
+-	${SHELL} ${INFOPOST} < $(srcdir)/bashref.info > $@ ; \
++	${SHELL} ${INFOPOST} < bashref.info > $@ ; \
+ 
+ bash.txt: bash.1
+ bash.ps: bash.1
+@@ -237,9 +237,9 @@ install: info installdirs bash.info
+ 	-$(INSTALL_DATA) $(srcdir)/bashbug.1 $(DESTDIR)$(man1dir)/bashbug${man1ext}
+ 	-$(INSTALL_DATA) $(OTHER_DOCS) $(DESTDIR)$(docdir)
+ # uncomment the next lines to install the builtins man page
+-#	sed 's:bash\.1:man1/&:' $(srcdir)/builtins.1 > $${TMPDIR:-/var/tmp}/builtins.1
+-#	-$(INSTALL_DATA) $${TMPDIR:-/var/tmp}/builtins.1 $(DESTDIR)$(man1dir)/bash_builtins${man1ext}
+-#	-$(RM) $${TMPDIR:-/var/tmp}/builtins.1
++	sed 's:bash\.1:man1/&:' $(srcdir)/builtins.1 > $${TMPDIR:-/var/tmp}/builtins.1
++	-$(INSTALL_DATA) $${TMPDIR:-/var/tmp}/builtins.1 $(DESTDIR)$(man1dir)/bash_builtins${man1ext}
++	-$(RM) $${TMPDIR:-/var/tmp}/builtins.1
+ 	-if test -f bash.info; then d=.; else d=$(srcdir); fi; \
+ 	  $(INSTALL_DATA) $$d/bash.info $(DESTDIR)$(infodir)/bash.info
+ # run install-info if it is present to update the info directory
+--- doc/bash.1	2014-02-06 07:03:52.000000000 -0700
++++ doc/bash.1	2015-02-06 17:14:11.015662800 -0700
+@@ -1658,6 +1658,14 @@ subsequently reset.
+ Expands to the effective user ID of the current user, initialized at
+ shell startup.  This variable is readonly.
+ .TP
++.B EXECIGNORE
++A colon-separated list of extended glob (see \fBPattern Matching\fP)
++patterns. Files with full paths matching one of these patterns are
++not considered executable for the purposes of completion and PATH
++searching, but the \fB[\fP, \fB[[\fP, and \fBtest\fP builtins are not
++affected. Use this variable to deal with systems that set the
++executable bit on files that are not actually executable.
++.TP
+ .B FUNCNAME
+ An array variable containing the names of all shell functions
+ currently in the execution call stack.
+@@ -3308,6 +3316,10 @@ the character
+ .B ``.''
+ at the start of a name or immediately following a slash
+ must be matched explicitly, unless the shell option
++.B completion_strip_exe
++If set, whenever bash sees `foo.exe' during completion, it checks if
++`foo' is the same file and strips the suffix.
++.TP 8
+ .B dotglob
+ is set.
+ When matching a pathname, the slash character must always be
+--- doc/bashref.texi	2014-02-22 11:20:36.000000000 -0700
++++ doc/bashref.texi	2015-02-06 17:14:11.015662800 -0700
+@@ -4992,6 +4992,10 @@ filenames.
+ This variable is set by default, which is the default Bash behavior in
+ versions through 4.2.
+ 
++@item completion_strip_exe
++If set, whenever bash sees `foo.exe' during completion, it checks if
++`foo' is the same file and strips the suffix.
++
+ @item direxpand
+ If set, Bash
+ replaces directory names with the results of word expansion when performing
+@@ -5578,6 +5582,14 @@ Similar to @code{BASH_ENV}; used when th
+ The numeric effective user id of the current user.  This variable
+ is readonly.
+ 
++@item EXECIGNORE
++A colon-separated list of extended glob ((@pxref{Pattern Matching})
++patterns. Files with full paths matching one of these patterns are
++not considered executable for the purposes of completion and PATH
++searching, but the @code{[}, @code{[[}, and @code{test} builtins are
++not affected. Use this variable to deal with systems that set the
++executable bit on files that are not actually executable.
++
+ @item FCEDIT
+ The editor used as a default by the @option{-e} option to the @code{fc}
+ builtin command.
+--- doc/builtins.1	2012-02-21 12:32:05.000000000 -0700
++++ doc/builtins.1	2015-02-06 17:14:11.031260100 -0700
+@@ -19,6 +19,6 @@ shift, shopt, source, suspend, test, tim
+ ulimit, umask, unalias, unset, wait \- bash built-in commands, see \fBbash\fR(1)
+ .SH BASH BUILTIN COMMANDS
+ .nr zZ 1
+-.so bash.1
++.so man1/bash.1
+ .SH SEE ALSO
+ bash(1), sh(1)
+--- execute_cmd.c	2015-02-06 17:12:55.261573700 -0700
++++ execute_cmd.c	2015-02-06 17:14:11.031260100 -0700
+@@ -58,6 +58,7 @@ extern int errno;
+ #endif
+ 
+ #define NEED_FPURGE_DECL
++#define NEED_SH_SETLINEBUF_DECL		/* used in externs.h */
+ 
+ #include "bashansi.h"
+ #include "bashintl.h"
+--- expr.c	2014-01-03 06:55:00.000000000 -0700
++++ expr.c	2015-02-06 17:14:11.031260100 -0700
+@@ -83,6 +83,7 @@
+ 
+ #include "shell.h"
+ #include "typemax.h"		/* INTMAX_MAX, INTMAX_MIN */
++#define exp2 exp2_
+ 
+ /* Because of the $((...)) construct, expressions may include newlines.
+    Here is a macro which accepts newlines, tabs and spaces as whitespace. */
+--- findcmd.c	2012-10-15 05:45:04.000000000 -0600
++++ findcmd.c	2015-02-06 17:14:11.031260100 -0700
+@@ -48,6 +48,8 @@
+ extern int errno;
+ #endif
+ 
++#include <glob/strmatch.h>
++
+ extern int posixly_correct;
+ extern int last_command_exit_value;
+ 
+@@ -77,6 +79,38 @@ int check_hashed_filenames;
+    containing the file of interest. */
+ int dot_found_in_search = 0;
+ 
++static struct ignorevar execignore =
++{
++  "EXECIGNORE",
++  (struct ign *)0,
++  0,
++  (char *)0,
++  (sh_iv_item_func_t *)0,
++};
++
++void
++setup_exec_ignore (char *varname)
++{
++  setup_ignore_patterns (&execignore);
++}
++
++/* Return whether we should never consider file executable
++ * even if the system tells us it is. */
++static int
++is_on_exec_blacklist (char *name)
++{
++  struct ign *p;
++  int flags = FNM_EXTMATCH | FNM_CASEFOLD;
++
++  for (p = execignore.ignores; p && p->val; p++)
++    {
++      if (strmatch (p->val, (char *)name, flags) != FNM_NOMATCH)
++      return (1);
++    }
++
++  return (0);
++}
++
+ /* Return some flags based on information about this file.
+    The EXISTS bit is non-zero if the file is found.
+    The EXECABLE bit is non-zero the file is executble.
+@@ -104,7 +138,7 @@ file_status (name)
+      file access mechanisms into account.  eaccess uses the effective
+      user and group IDs, not the real ones.  We could use sh_eaccess,
+      but we don't want any special treatment for /dev/fd. */
+-  if (eaccess (name, X_OK) == 0)
++  if (!is_on_exec_blacklist (name) && eaccess (name, X_OK) == 0)
+     r |= FS_EXECABLE;
+   if (eaccess (name, R_OK) == 0)
+     r |= FS_READABLE;
+--- findcmd.h	2012-01-14 16:56:25.000000000 -0700
++++ findcmd.h	2015-02-06 17:14:11.031260100 -0700
+@@ -31,5 +31,6 @@ extern char *find_user_command __P((cons
+ extern char *find_path_file __P((const char *));
+ extern char *search_for_command __P((const char *, int));
+ extern char *user_command_matches __P((const char *, int, int));
++extern void setup_exec_ignore __P((char *));
+ 
+ #endif /* _FINDCMD_H_ */
+--- general.c	2014-01-30 14:46:15.000000000 -0700
++++ general.c	2015-02-06 17:14:11.031260100 -0700
+@@ -44,6 +44,10 @@
+ 
+ #include <tilde/tilde.h>
+ 
++#ifdef __CYGWIN__
++# include <sys/cygwin.h>
++#endif
++
+ #if !defined (errno)
+ extern int errno;
+ #endif /* !errno */
+@@ -632,7 +636,8 @@ make_absolute (string, dot_path)
+     {
+       char pathbuf[PATH_MAX + 1];
+ 
+-      cygwin_conv_to_full_posix_path (string, pathbuf);
++      cygwin_conv_path (CCP_WIN_A_TO_POSIX | CCP_ABSOLUTE, string, pathbuf,
++			sizeof pathbuf);
+       result = savestring (pathbuf);
+     }
+ #else
+--- include/chartypes.h	2011-04-11 12:30:52.000000000 -0600
++++ include/chartypes.h	2015-02-06 17:14:11.031260100 -0700
+@@ -40,6 +40,7 @@
+ #else
+ #  define IN_CTYPE_DOMAIN(c) isascii(c)
+ #endif
++#define to_uchar(c) ((unsigned char)(c))
+ 
+ #if !defined (isspace) && !defined (HAVE_ISSPACE)
+ #  define isspace(c) ((c) == ' ' || (c) == '\t' || (c) == '\n' || (c) == '\f')
+@@ -67,16 +68,16 @@
+ 
+ #undef ISPRINT
+ 
+-#define ISPRINT(c) (IN_CTYPE_DOMAIN (c) && isprint (c))
+-#define ISDIGIT(c) (IN_CTYPE_DOMAIN (c) && isdigit (c))
+-#define ISALNUM(c) (IN_CTYPE_DOMAIN (c) && isalnum (c))
+-#define ISALPHA(c) (IN_CTYPE_DOMAIN (c) && isalpha (c))
+-#define ISCNTRL(c) (IN_CTYPE_DOMAIN (c) && iscntrl (c))
+-#define ISLOWER(c) (IN_CTYPE_DOMAIN (c) && islower (c))
+-#define ISPUNCT(c) (IN_CTYPE_DOMAIN (c) && ispunct (c))
+-#define ISSPACE(c) (IN_CTYPE_DOMAIN (c) && isspace (c))
+-#define ISUPPER(c) (IN_CTYPE_DOMAIN (c) && isupper (c))
+-#define ISXDIGIT(c) (IN_CTYPE_DOMAIN (c) && isxdigit (c))
++#define ISPRINT(c) (IN_CTYPE_DOMAIN (c) && isprint (to_uchar (c)))
++#define ISDIGIT(c) (IN_CTYPE_DOMAIN (c) && isdigit (to_uchar (c)))
++#define ISALNUM(c) (IN_CTYPE_DOMAIN (c) && isalnum (to_uchar (c)))
++#define ISALPHA(c) (IN_CTYPE_DOMAIN (c) && isalpha (to_uchar (c)))
++#define ISCNTRL(c) (IN_CTYPE_DOMAIN (c) && iscntrl (to_uchar (c)))
++#define ISLOWER(c) (IN_CTYPE_DOMAIN (c) && islower (to_uchar (c)))
++#define ISPUNCT(c) (IN_CTYPE_DOMAIN (c) && ispunct (to_uchar (c)))
++#define ISSPACE(c) (IN_CTYPE_DOMAIN (c) && isspace (to_uchar (c)))
++#define ISUPPER(c) (IN_CTYPE_DOMAIN (c) && isupper (to_uchar (c)))
++#define ISXDIGIT(c) (IN_CTYPE_DOMAIN (c) && isxdigit (to_uchar (c)))
+ 
+ #define ISLETTER(c)	(ISALPHA(c))
+ 
+--- include/posixjmp.h	2012-12-23 20:20:50.000000000 -0700
++++ include/posixjmp.h	2015-02-06 17:14:11.031260100 -0700
+@@ -27,13 +27,13 @@
+ 
+ #if defined (HAVE_POSIX_SIGSETJMP)
+ #  define procenv_t	sigjmp_buf
+-#  if !defined (__OPENNT)
++#  if !defined (__OPENNT) && !defined __CYGWIN__
+ #    undef setjmp
+ #    define setjmp(x)	sigsetjmp((x), 1)
+-#    define setjmp_nosigs(x)	sigsetjmp((x), 0)
+ #    undef longjmp
+ #    define longjmp(x, n)	siglongjmp((x), (n))
+ #  endif /* !__OPENNT */
++#  define setjmp_nosigs(x)	sigsetjmp((x), 0)
+ #else
+ #  define procenv_t	jmp_buf
+ #  define setjmp_nosigs	setjmp
+--- input.c	2014-02-07 07:13:08.000000000 -0700
++++ input.c	2015-02-06 17:14:11.031260100 -0700
+@@ -44,6 +44,10 @@
+ #include "quit.h"
+ #include "trap.h"
+ 
++#if __CYGWIN__
++int igncr;
++#endif
++
+ #if !defined (errno)
+ extern int errno;
+ #endif /* !errno */
+@@ -561,6 +565,19 @@ buffered_getchar ()
+ {
+   CHECK_TERMSIG;
+ 
++#if __CYGWIN__
++  /* shopt igncr means to discard carriage returns from input stream.
++     If cr is the only character in the buffer, then recurse to pick
++     up the next character; otherwise flatten the buffer.  */
++  if (igncr)
++    {
++      int ch;
++      while ((ch = bufstream_getc (buffers[bash_input.location.buffered_fd]))
++	     == '\r')
++	;
++      return ch;
++    }
++#endif /* __CYGWIN__ */
+ #if !defined (DJGPP)
+   return (bufstream_getc (buffers[bash_input.location.buffered_fd]));
+ #else
+--- lib/readline/bind.c	2013-04-06 15:46:38.000000000 -0600
++++ lib/readline/bind.c	2015-02-06 17:14:11.031260100 -0700
+@@ -452,7 +452,7 @@ rl_translate_keyseq (seq, array, len)
+ {
+   register int i, c, l, temp;
+ 
+-  for (i = l = 0; c = seq[i]; i++)
++  for (i = l = 0; (c = seq[i]); i++)
+     {
+       if (c == '\\')
+ 	{
+@@ -1210,7 +1210,7 @@ _rl_skip_to_delim (string, start, delim)
+ {
+   int i, c, passc;
+ 
+-  for (i = start,passc = 0; c = string[i]; i++)
++  for (i = start,passc = 0; (c = string[i]); i++)
+     {
+       if (passc)
+ 	{
+@@ -1297,7 +1297,6 @@ rl_parse_and_bind (string)
+   if (_rl_stricmp (string, "set") == 0)
+     {
+       char *var, *value, *e;
+-      int s;
+ 
+       var = string + i;
+       /* Make VAR point to start of variable name. */
+@@ -2198,7 +2197,7 @@ rl_function_dumper (print_readably)
+ 
+   fprintf (rl_outstream, "\n");
+ 
+-  for (i = 0; name = names[i]; i++)
++  for (i = 0; (name = names[i]); i++)
+     {
+       rl_command_func_t *function;
+       char **invokers;
+--- lib/readline/chardefs.h	2011-07-25 19:47:56.000000000 -0600
++++ lib/readline/chardefs.h	2015-02-06 17:14:11.046889800 -0700
+@@ -71,6 +71,7 @@
+ #else
+ #  define IN_CTYPE_DOMAIN(c) isascii(c)
+ #endif
++#define to_uchar(c) ((unsigned char)(c))
+ 
+ #if !defined (isxdigit) && !defined (HAVE_ISXDIGIT) && !defined (__cplusplus)
+ #  define isxdigit(c)   (isdigit((c)) || ((c) >= 'a' && (c) <= 'f') || ((c) >= 'A' && (c) <= 'F'))
+@@ -87,13 +88,13 @@
+ 
+ /* Beware:  these only work with single-byte ASCII characters. */
+ 
+-#define ISALNUM(c)	(IN_CTYPE_DOMAIN (c) && isalnum (c))
+-#define ISALPHA(c)	(IN_CTYPE_DOMAIN (c) && isalpha (c))
+-#define ISDIGIT(c)	(IN_CTYPE_DOMAIN (c) && isdigit (c))
+-#define ISLOWER(c)	(IN_CTYPE_DOMAIN (c) && islower (c))
+-#define ISPRINT(c)	(IN_CTYPE_DOMAIN (c) && isprint (c))
+-#define ISUPPER(c)	(IN_CTYPE_DOMAIN (c) && isupper (c))
+-#define ISXDIGIT(c)	(IN_CTYPE_DOMAIN (c) && isxdigit (c))
++#define ISALNUM(c)	(IN_CTYPE_DOMAIN (c) && isalnum (to_uchar (c)))
++#define ISALPHA(c)	(IN_CTYPE_DOMAIN (c) && isalpha (to_uchar (c)))
++#define ISDIGIT(c)	(IN_CTYPE_DOMAIN (c) && isdigit (to_uchar (c)))
++#define ISLOWER(c)	(IN_CTYPE_DOMAIN (c) && islower (to_uchar (c)))
++#define ISPRINT(c)	(IN_CTYPE_DOMAIN (c) && isprint (to_uchar (c)))
++#define ISUPPER(c)	(IN_CTYPE_DOMAIN (c) && isupper (to_uchar (c)))
++#define ISXDIGIT(c)	(IN_CTYPE_DOMAIN (c) && isxdigit (to_uchar (c)))
+ 
+ #define _rl_lowercase_p(c)	(NON_NEGATIVE(c) && ISLOWER(c))
+ #define _rl_uppercase_p(c)	(NON_NEGATIVE(c) && ISUPPER(c))
+--- lib/readline/complete.c	2013-10-14 07:27:10.000000000 -0600
++++ lib/readline/complete.c	2015-02-06 17:14:11.046889800 -0700
+@@ -1082,7 +1082,7 @@ _rl_find_completion_word (fp, dp)
+       /* We didn't find an unclosed quoted substring upon which to do
+          completion, so use the word break characters to find the
+          substring on which to complete. */
+-      while (rl_point = MB_PREVCHAR (rl_line_buffer, rl_point, MB_FIND_ANY))
++      while ((rl_point = MB_PREVCHAR (rl_line_buffer, rl_point, MB_FIND_ANY)))
+ 	{
+ 	  scan = rl_line_buffer[rl_point];
+ 
+@@ -2116,7 +2116,7 @@ rl_completion_matches (text, entry_funct
+   match_list = (char **)xmalloc ((match_list_size + 1) * sizeof (char *));
+   match_list[1] = (char *)NULL;
+ 
+-  while (string = (*entry_function) (text, matches))
++  while ((string = (*entry_function) (text, matches)))
+     {
+       if (RL_SIG_RECEIVED ())
+ 	{
+@@ -2190,7 +2190,7 @@ rl_username_completion_function (text, s
+     }
+ 
+ #if defined (HAVE_GETPWENT)
+-  while (entry = getpwent ())
++  while ((entry = getpwent ()))
+     {
+       /* Null usernames should result in all users as possible completions. */
+       if (namelen == 0 || (STREQN (username, entry->pw_name, namelen)))
+@@ -2723,7 +2723,7 @@ rl_menu_complete (count, ignore)
+   static int full_completion = 0;	/* set to 1 if menu completion should reinitialize on next call */
+   static int orig_start, orig_end;
+   static char quote_char;
+-  static int delimiter, cstate;
++  static int delimiter;
+ 
+   /* The first time through, we generate the list of matches and set things
+      up to insert them. */
+--- lib/readline/display.c	2015-02-06 17:12:54.793574600 -0700
++++ lib/readline/display.c	2015-02-06 17:14:11.046889800 -0700
+@@ -66,7 +66,6 @@ extern char *strchr (), *strrchr ();
+ static void update_line PARAMS((char *, char *, int, int, int, int));
+ static void space_to_eol PARAMS((int));
+ static void delete_chars PARAMS((int));
+-static void insert_some_chars PARAMS((char *, int, int));
+ static void open_some_spaces PARAMS((int));
+ static void cr PARAMS((void));
+ 
+@@ -1314,7 +1313,7 @@ update_line (old, new, current_line, oma
+      int current_line, omax, nmax, inv_botlin;
+ {
+   register char *ofd, *ols, *oe, *nfd, *nls, *ne;
+-  int temp, lendiff, wsatend, od, nd, twidth, o_cpos;
++  int temp, lendiff, wsatend, od, nd, o_cpos;
+   int current_invis_chars;
+   int col_lendiff, col_temp;
+   int bytes_to_insert;
+@@ -2485,6 +2484,7 @@ _rl_clear_screen ()
+ #endif /* __DJGPP__ */
+ }
+ 
++#if 0
+ /* Insert COUNT characters from STRING to the output stream at column COL. */
+ static void
+ insert_some_chars (string, count, col)
+@@ -2494,6 +2494,7 @@ insert_some_chars (string, count, col)
+   open_some_spaces (col);
+   _rl_output_some_chars (string, count);
+ }
++#endif
+ 
+ /* Insert COL spaces, keeping the cursor at the same position.  We follow the
+    ncurses documentation and use either im/ei with explicit spaces, or IC/ic
+--- lib/readline/histexpand.c	2013-12-02 07:22:30.000000000 -0700
++++ lib/readline/histexpand.c	2015-02-06 17:14:11.046889800 -0700
+@@ -204,7 +204,7 @@ get_history_event (string, caller_index,
+     }
+ 
+   /* Only a closing `?' or a newline delimit a substring search string. */
+-  for (local_index = i; c = string[i]; i++)
++  for (local_index = i; (c = string[i]); i++)
+     {
+ #if defined (HANDLE_MULTIBYTE)
+       if (MB_CUR_MAX > 1 && rl_byte_oriented == 0)
+@@ -677,7 +677,7 @@ history_expand_internal (string, start,
+ 	case 's':
+ 	  {
+ 	    char *new_event;
+-	    int delimiter, failed, si, l_temp, ws, we;
++	    int delimiter, failed, si, l_temp, we;
+ 
+ 	    if (c == 's')
+ 	      {
+@@ -776,7 +776,6 @@ history_expand_internal (string, start,
+ 		  {
+ 		    for (; temp[si] && whitespace (temp[si]); si++)
+ 		      ;
+-		    ws = si;
+ 		    we = history_tokenize_word (temp, si);
+ 		  }
+ 
+--- lib/readline/histfile.c	2013-07-19 06:17:17.000000000 -0600
++++ lib/readline/histfile.c	2015-02-06 17:14:11.046889800 -0700
+@@ -104,7 +104,7 @@ int history_write_timestamps = 0;
+ 
+ /* Does S look like the beginning of a history timestamp entry?  Placeholder
+    for more extensive tests. */
+-#define HIST_TIMESTAMP_START(s)		(*(s) == history_comment_char && isdigit ((s)[1]) )
++#define HIST_TIMESTAMP_START(s)		(*(s) == history_comment_char && isdigit ((unsigned char) (s)[1]) )
+ 
+ /* Return the string that should be used in the place of this
+    filename.  This only matters when you don't specify the
+--- lib/readline/input.c	2015-02-06 17:12:55.027577800 -0700
++++ lib/readline/input.c	2015-02-06 17:14:11.046889800 -0700
+@@ -431,7 +431,7 @@ rl_read_key ()
+   else
+     {
+       /* If input is coming from a macro, then use that. */
+-      if (c = _rl_next_macro_key ())
++      if ((c = _rl_next_macro_key ()))
+ 	return (c);
+ 
+       /* If the user has an event function, then call it periodically. */
+--- lib/readline/isearch.c	2013-10-14 07:08:40.000000000 -0600
++++ lib/readline/isearch.c	2015-02-06 17:14:11.046889800 -0700
+@@ -740,7 +740,7 @@ rl_search_history (direction, invoking_k
+      int direction, invoking_key;
+ {
+   _rl_search_cxt *cxt;		/* local for now, but saved globally */
+-  int c, r;
++  int r;
+ 
+   RL_SETSTATE(RL_STATE_ISEARCH);
+   cxt = _rl_isearch_init (direction);
+@@ -755,7 +755,7 @@ rl_search_history (direction, invoking_k
+   r = -1;
+   for (;;)
+     {
+-      c = _rl_search_getchar (cxt);
++      _rl_search_getchar (cxt);
+       /* We might want to handle EOF here (c == 0) */
+       r = _rl_isearch_dispatch (cxt, cxt->lastc);
+       if (r <= 0)
+@@ -778,9 +778,9 @@ int
+ _rl_isearch_callback (cxt)
+      _rl_search_cxt *cxt;
+ {
+-  int c, r;
++  int r;
+ 
+-  c = _rl_search_getchar (cxt);
++  _rl_search_getchar (cxt);
+   /* We might want to handle EOF here */
+   r = _rl_isearch_dispatch (cxt, cxt->lastc);
+ 
+--- lib/readline/misc.c	2015-02-06 17:12:55.230384200 -0700
++++ lib/readline/misc.c	2015-02-06 17:14:11.046889800 -0700
+@@ -455,7 +455,7 @@ _rl_revert_all_lines ()
+   entry = (hpos == history_length) ? previous_history () : current_history ();
+   while (entry)
+     {
+-      if (ul = (UNDO_LIST *)entry->data)
++      if ((ul = (UNDO_LIST *)entry->data))
+ 	{
+ 	  if (ul == saved_undo_list)
+ 	    saved_undo_list = 0;
+@@ -502,7 +502,7 @@ rl_clear_history ()
+   for (i = 0; i < history_length; i++)
+     {
+       hent = hlist[i];
+-      if (ul = (UNDO_LIST *)hent->data)
++      if ((ul = (UNDO_LIST *)hent->data))
+ 	{
+ 	  if (ul == saved_undo_list)
+ 	    saved_undo_list = 0;
+--- lib/readline/nls.c	2013-03-09 12:51:10.000000000 -0700
++++ lib/readline/nls.c	2015-02-06 17:14:11.046889800 -0700
+@@ -80,7 +80,7 @@ static char *legal_lang_values[] =
+ static char *normalize_codeset PARAMS((char *));
+ #endif /* !HAVE_SETLOCALE */
+ 
+-static char *find_codeset PARAMS((char *, size_t *));
++static char *find_codeset PARAMS((char *, size_t *)) __attribute__ ((__unused__));
+ 
+ static char *_rl_get_locale_var PARAMS((const char *));
+ 
+@@ -104,12 +104,13 @@ utf8locale (lspec)
+      char *lspec;
+ {
+   char *cp;
+-  size_t len;
+ 
+ #if HAVE_LANGINFO_CODESET
+   cp = nl_langinfo (CODESET);
+   return (STREQ (cp, "UTF-8") || STREQ (cp, "utf8"));
+ #else
++  size_t len;
++
+   cp = find_codeset (lspec, &len);
+ 
+   if (cp == 0 || len < 4 || len > 5)
+--- lib/readline/parens.c	2009-04-19 11:12:06.000000000 -0600
++++ lib/readline/parens.c	2015-02-06 17:14:11.046889800 -0700
+@@ -106,7 +106,7 @@ rl_insert_close (count, invoking_key)
+   else
+     {
+ #if defined (HAVE_SELECT)
+-      int orig_point, match_point, ready;
++      int orig_point, match_point;
+       struct timeval timer;
+       fd_set readfds;
+ 
+@@ -126,7 +126,7 @@ rl_insert_close (count, invoking_key)
+       orig_point = rl_point;
+       rl_point = match_point;
+       (*rl_redisplay_function) ();
+-      ready = select (1, &readfds, (fd_set *)NULL, (fd_set *)NULL, &timer);
++      select (1, &readfds, (fd_set *)NULL, (fd_set *)NULL, &timer);
+       rl_point = orig_point;
+ #else /* !HAVE_SELECT */
+       _rl_insert_char (count, invoking_key);
+--- lib/readline/posixjmp.h	2012-12-23 20:20:50.000000000 -0700
++++ lib/readline/posixjmp.h	2015-02-06 17:14:11.046889800 -0700
+@@ -27,13 +27,13 @@
+ 
+ #if defined (HAVE_POSIX_SIGSETJMP)
+ #  define procenv_t	sigjmp_buf
+-#  if !defined (__OPENNT)
++#  if !defined (__OPENNT) && !defined __CYGWIN__
+ #    undef setjmp
+ #    define setjmp(x)	sigsetjmp((x), 1)
+-#    define setjmp_nosigs(x)	sigsetjmp((x), 0)
+ #    undef longjmp
+ #    define longjmp(x, n)	siglongjmp((x), (n))
+ #  endif /* !__OPENNT */
++#  define setjmp_nosigs(x)	sigsetjmp((x), 0)
+ #else
+ #  define procenv_t	jmp_buf
+ #  define setjmp_nosigs	setjmp
+--- lib/readline/readline.c	2015-02-06 17:12:54.310964200 -0700
++++ lib/readline/readline.c	2015-02-06 17:14:11.046889800 -0700
+@@ -95,7 +95,7 @@ static void bind_arrow_keys_internal PAR
+ static void bind_arrow_keys PARAMS((void));
+ 
+ static void readline_default_bindings PARAMS((void));
+-static void reset_default_bindings PARAMS((void));
++//static void reset_default_bindings PARAMS((void));
+ 
+ static int _rl_subseq_result PARAMS((int, Keymap, int, int));
+ static int _rl_subseq_getchar PARAMS((int));
+@@ -522,7 +522,7 @@ readline_internal_char ()
+ readline_internal_charloop ()
+ #endif
+ {
+-  static int lastc, eof_found;
++  static int lastc, eof_found __attribute__((unused));
+   int c, code, lk;
+ 
+   lastc = -1;
+@@ -1204,6 +1204,7 @@ readline_default_bindings ()
+     rl_tty_set_default_bindings (_rl_keymap);
+ }
+ 
++#if 0
+ /* Reset the default bindings for the terminal special characters we're
+    interested in back to rl_insert and read the new ones. */
+ static void
+@@ -1215,6 +1216,7 @@ reset_default_bindings ()
+       rl_tty_set_default_bindings (_rl_keymap);
+     }
+ }
++#endif
+ 
+ /* Bind some common arrow key sequences in MAP. */
+ static void
+--- lib/readline/rltty.c	2013-08-25 14:57:05.000000000 -0600
++++ lib/readline/rltty.c	2015-02-06 17:14:11.062454900 -0700
+@@ -30,6 +30,7 @@
+ #include <signal.h>
+ #include <errno.h>
+ #include <stdio.h>
++#include <sys/ioctl.h>
+ 
+ #if defined (HAVE_UNISTD_H)
+ #  include <unistd.h>
+--- lib/readline/shell.c	2013-03-13 08:17:00.000000000 -0600
++++ lib/readline/shell.c	2015-02-06 17:14:11.062454900 -0700
+@@ -123,8 +123,10 @@ sh_single_quote (string)
+ /* Set the environment variables LINES and COLUMNS to lines and cols,
+    respectively. */
+ static char setenv_buf[INT_STRLEN_BOUND (int) + 1];
++#  if !defined (HAVE_SETENV) && defined (HAVE_PUTENV)
+ static char putenv_buf1[INT_STRLEN_BOUND (int) + 6 + 1];	/* sizeof("LINES=") == 6 */
+ static char putenv_buf2[INT_STRLEN_BOUND (int) + 8 + 1];	/* sizeof("COLUMNS=") == 8 */
++#  endif
+ 
+ void
+ sh_set_lines_and_columns (lines, cols)
+--- lib/readline/signals.c	2014-01-10 13:06:48.000000000 -0700
++++ lib/readline/signals.c	2015-02-06 17:14:11.062454900 -0700
+@@ -576,7 +576,6 @@ rl_free_line_state ()
+ /* **************************************************************** */
+ 
+ #if defined (HAVE_POSIX_SIGNALS)
+-static sigset_t sigint_set, sigint_oset;
+ static sigset_t sigwinch_set, sigwinch_oset;
+ #else /* !HAVE_POSIX_SIGNALS */
+ #  if defined (HAVE_BSD_SIGNALS)
+--- lib/readline/terminal.c	2013-09-18 07:12:01.000000000 -0600
++++ lib/readline/terminal.c	2015-02-06 17:14:11.062454900 -0700
+@@ -31,6 +31,7 @@
+ #if defined (HAVE_SYS_FILE_H)
+ #  include <sys/file.h>
+ #endif /* HAVE_SYS_FILE_H */
++#include <sys/ioctl.h>
+ 
+ #if defined (HAVE_UNISTD_H)
+ #  include <unistd.h>
+--- lib/readline/text.c	2013-10-14 07:25:05.000000000 -0600
++++ lib/readline/text.c	2015-02-06 17:14:11.062454900 -0700
+@@ -859,11 +859,10 @@ _rl_overwrite_char (count, c)
+   int i;
+ #if defined (HANDLE_MULTIBYTE)
+   char mbkey[MB_LEN_MAX];
+-  int k;
+ 
+   /* Read an entire multibyte character sequence to insert COUNT times. */
+   if (count > 0 && MB_CUR_MAX > 1 && rl_byte_oriented == 0)
+-    k = _rl_read_mbstring (c, mbkey, MB_LEN_MAX);
++    _rl_read_mbstring (c, mbkey, MB_LEN_MAX);
+ #endif
+ 
+   rl_begin_undo_group ();
+--- lib/readline/tilde.c	2010-07-25 15:42:13.000000000 -0600
++++ lib/readline/tilde.c	2015-02-06 17:14:11.062454900 -0700
+@@ -196,7 +196,7 @@ tilde_expand (string)
+   int result_size, result_index;
+ 
+   result_index = result_size = 0;
+-  if (result = strchr (string, '~'))
++  if ((result = strchr (string, '~')))
+     result = (char *)xmalloc (result_size = (strlen (string) + 16));
+   else
+     result = (char *)xmalloc (result_size = (strlen (string) + 1));
+--- lib/readline/undo.c	2014-02-02 13:47:46.000000000 -0700
++++ lib/readline/undo.c	2015-02-06 17:14:11.062454900 -0700
+@@ -124,7 +124,7 @@ _rl_free_undo_list (ul)
+ void
+ rl_free_undo_list ()
+ {
+-  UNDO_LIST *release, *orig_list;
++  UNDO_LIST *orig_list;
+ 
+   orig_list = rl_undo_list;
+   _rl_free_undo_list (rl_undo_list);
+--- lib/readline/vi_mode.c	2012-09-01 16:55:30.000000000 -0600
++++ lib/readline/vi_mode.c	2015-02-06 17:14:11.062454900 -0700
+@@ -1089,7 +1089,7 @@ static int
+ rl_domove_motion_callback (m)
+      _rl_vimotion_cxt *m;
+ {
+-  int c, save, r;
++  int c, r;
+   int old_end;
+ 
+   _rl_vi_last_motion = c = m->motion;
+@@ -1257,7 +1257,6 @@ int
+ rl_vi_domove (x, ignore)
+      int x, *ignore;
+ {
+-  int r;
+   _rl_vimotion_cxt *m;
+ 
+   m = _rl_vimvcxt;
+--- lib/sh/pathphys.c	2013-05-28 13:33:58.000000000 -0600
++++ lib/sh/pathphys.c	2015-02-06 17:14:11.062454900 -0700
+@@ -35,6 +35,7 @@
+ #include <stdio.h>
+ #include <chartypes.h>
+ #include <errno.h>
++#include <stdlib.h>
+ 
+ #include "shell.h"
+ 
+@@ -76,6 +77,10 @@ sh_physpath (path, flags)
+      char *path;
+      int flags;
+ {
++#if __CYGWIN__
++  /* realpath does this correctly without all the hassle */
++  return realpath (path, NULL);
++#else
+   char tbuf[PATH_MAX+1], linkbuf[PATH_MAX+1];
+   char *result, *p, *q, *qsave, *qbase, *workpath;
+   int double_slash_path, linklen, nlink;
+@@ -214,11 +219,7 @@ error:
+ 	    {
+ 	      q = result;
+ 	      /* Duplicating some code here... */
+-#if defined (__CYGWIN__)
+-	      qbase = (ISALPHA((unsigned char)workpath[0]) && workpath[1] == ':') ? workpath + 3 : workpath + 1;
+-#else
+ 	      qbase = workpath + 1;
+-#endif
+ 	      double_slash_path = DOUBLE_SLASH (workpath);
+ 	      qbase += double_slash_path;
+     
+@@ -249,6 +250,7 @@ error:
+     }
+ 
+   return (result);
++#endif /* ! __CYGWIN__ */
+ }
+ 
+ char *
+--- lib/sh/tmpfile.c	2013-12-18 15:50:13.000000000 -0700
++++ lib/sh/tmpfile.c	2015-02-06 17:14:11.062454900 -0700
+@@ -96,7 +96,7 @@ get_tmpdir (flags)
+   if (tdir && (file_iswdir (tdir) == 0 || strlen (tdir) > PATH_MAX))
+     tdir = 0;
+ 
+-  if (tdir == 0)
++  if (tdir == 0 || !file_iswdir (tdir))
+     tdir = get_sys_tmpdir ();
+ 
+ #if defined (HAVE_PATHCONF) && defined (_PC_NAME_MAX)
+@@ -118,14 +118,15 @@ sh_mktmpname (nameroot, flags)
+   struct stat sb;
+   int r, tdlen;
+ 
+-  filename = (char *)xmalloc (PATH_MAX + 1);
++  filename = NULL;
+   tdir = get_tmpdir (flags);
+   tdlen = strlen (tdir);
+ 
+   lroot = nameroot ? nameroot : DEFAULT_NAMEROOT;
+ 
+ #ifdef USE_MKTEMP
+-  sprintf (filename, "%s/%s.XXXXXX", tdir, lroot);
++  if (asprintf (&filename, "%s/%s.XXXXXX", tdir, lroot) < 0)
++    return NULL;
+   if (mktemp (filename) == 0)
+     {
+       free (filename);
+@@ -138,7 +139,9 @@ sh_mktmpname (nameroot, flags)
+ 		(unsigned long) time ((time_t *)0) ^
+ 		(unsigned long) dollar_dollar_pid ^
+ 		(unsigned long) ((flags & MT_USERANDOM) ? random () : ntmpfiles++);
+-      sprintf (filename, "%s/%s-%lu", tdir, lroot, filenum);
++      free (filename);
++      if (asprintf (&filename, "%s/%s-%lu", tdir, lroot, filenum) < 0)
++	return NULL;
+       if (tmpnamelen > 0 && tmpnamelen < 32)
+ 	filename[tdlen + 1 + tmpnamelen] = '\0';
+ #  ifdef HAVE_LSTAT
+@@ -163,14 +166,19 @@ sh_mktmpfd (nameroot, flags, namep)
+   char *filename, *tdir, *lroot;
+   int fd, tdlen;
+ 
+-  filename = (char *)xmalloc (PATH_MAX + 1);
++  filename = NULL;
+   tdir = get_tmpdir (flags);
+   tdlen = strlen (tdir);
+ 
+   lroot = nameroot ? nameroot : DEFAULT_NAMEROOT;
+ 
+ #ifdef USE_MKSTEMP
+-  sprintf (filename, "%s/%s.XXXXXX", tdir, lroot);
++  if (asprintf (&filename, "%s/%s.XXXXXX", tdir, lroot) < 0)
++    {
++      if (namep)
++	*namep = NULL;
++      return -1;
++    }
+   fd = mkstemp (filename);
+   if (fd < 0 || namep == 0)
+     {
+@@ -187,7 +195,13 @@ sh_mktmpfd (nameroot, flags, namep)
+ 		(unsigned long) time ((time_t *)0) ^
+ 		(unsigned long) dollar_dollar_pid ^
+ 		(unsigned long) ((flags & MT_USERANDOM) ? random () : ntmpfiles++);
+-      sprintf (filename, "%s/%s-%lu", tdir, lroot, filenum);
++      free (filename);
++      if (asprintf (&filename, "%s/%s-%lu", tdir, lroot, filenum) < 0)
++	{
++	  if (namep)
++	    *namep = NULL;
++	  return -1;
++	}
+       if (tmpnamelen > 0 && tmpnamelen < 32)
+ 	filename[tdlen + 1 + tmpnamelen] = '\0';
+       fd = open (filename, BASEOPENFLAGS | ((flags & MT_READWRITE) ? O_RDWR : O_WRONLY), 0600);
+--- mksyntax.c	2012-07-29 17:48:38.000000000 -0600
++++ mksyntax.c	2015-02-06 17:14:11.062454900 -0700
+@@ -29,13 +29,13 @@
+ 
+ #ifdef HAVE_UNISTD_H
+ #  include <unistd.h>
++#else
++extern int optind;
++extern char *optarg;
+ #endif
+ 
+ #include "syntax.h"
+ 
+-extern int optind;
+-extern char *optarg;
+-
+ #ifndef errno
+ extern int errno;
+ #endif
+--- parse.y	2015-02-06 17:12:55.682776800 -0700
++++ parse.y	2015-02-06 17:14:11.062454900 -0700
+@@ -1531,14 +1531,20 @@ yy_string_get ()
+   string = bash_input.location.string;
+ 
+   /* If the string doesn't exist, or is empty, EOF found. */
+-  if (string && *string)
++  while (string && *string)
+     {
+       c = *string++;
+       bash_input.location.string = string;
++#if __CYGWIN__
++      {
++	extern int igncr;
++	if (igncr && c == '\r')
++	  continue;
++      }
++#endif
+       return (c);
+     }
+-  else
+-    return (EOF);
++  return (EOF);
+ }
+ 
+ static int
+@@ -2305,7 +2311,7 @@ shell_getc (remove_quoted_newline)
+ 	      if (n <= 2)	/* we have to save 1 for the newline added below */
+ 		{
+ 		  if (truncating == 0)
+-		    internal_warning("shell_getc: shell_input_line_size (%zu) exceeds SIZE_MAX (%llu): line truncated", shell_input_line_size, SIZE_MAX);
++		    internal_warning("shell_getc: shell_input_line_size (%zu) exceeds SIZE_MAX (%zu): line truncated", shell_input_line_size, SIZE_MAX);
+ 		  shell_input_line[i] = '\0';
+ 		  truncating = 1;
+ 		}
+@@ -3582,7 +3588,6 @@ parse_comsub (qc, open, close, lenp, fla
+ 
+   while (count)
+     {
+-comsub_readchar:
+       ch = shell_getc (qc != '\'' && (tflags & (LEX_INCOMMENT|LEX_PASSNEXT)) == 0);
+ 
+       if (ch == EOF)
+--- pathexp.h	2009-01-04 12:32:40.000000000 -0700
++++ pathexp.h	2015-02-06 17:14:11.062454900 -0700
+@@ -86,7 +86,7 @@ struct ign {
+ typedef int sh_iv_item_func_t __P((struct ign *));
+ 
+ struct ignorevar {
+-  char *varname;	/* FIGNORE or GLOBIGNORE */
++  char *varname;	/* FIGNORE or GLOBIGNORE or EXECIGNORE */
+   struct ign *ignores;	/* Store the ignore strings here */
+   int num_ignores;	/* How many are there? */
+   char *last_ignoreval;	/* Last value of variable - cached for speed */
+--- redir.c	2013-10-14 07:19:59.000000000 -0600
++++ redir.c	2015-02-06 17:14:11.078059300 -0700
+@@ -156,7 +156,6 @@ redirection_error (temp, error)
+ #endif
+   else if (expandable_redirection_filename (temp))
+     {
+-expandable_filename:
+       oflags = temp->redirectee.filename->flags;
+       if (posixly_correct && interactive_shell == 0)
+ 	temp->redirectee.filename->flags |= W_NOGLOB;
+--- subst.c	2015-02-06 17:12:55.370841100 -0700
++++ subst.c	2015-02-06 17:14:11.078059300 -0700
+@@ -41,6 +41,7 @@
+ #include "posixstat.h"
+ #include "bashintl.h"
+ 
++#define NEED_SH_SETLINEBUF_DECL		/* used in externs.h */
+ #include "shell.h"
+ #include "parser.h"
+ #include "flags.h"
+@@ -5268,6 +5269,13 @@ read_comsub (fd, quoted, rflag)
+ #endif
+ 	  continue;
+ 	}
++#if __CYGWIN__
++      {
++	extern int igncr;
++	if (igncr && c == '\r')
++	  continue;
++      }
++#endif /* __CYGWIN__ */
+ 
+       /* Add the character to ISTRING, possibly after resizing it. */
+       RESIZE_MALLOCED_BUFFER (istring, istring_index, 2, istring_size, DEFAULT_ARRAY_SIZE);
+@@ -5385,6 +5393,28 @@ command_substitute (string, quoted)
+       goto error_exit;
+     }
+ 
++#if __CYGWIN__
++  /* Passing a pipe through std fds can cause hangs when talking to a
++     non-cygwin child.  Move it.  */
++  if (fildes[0] < 3)
++    {
++      int fd = fcntl (fildes[0], F_DUPFD, 3);
++      close (fildes[0]);
++      fildes[0] = fd;
++    }
++  if (fildes[1] < 3)
++    {
++      int fd = fcntl (fildes[1], F_DUPFD, 3);
++      close (fildes[1]);
++      fildes[1] = fd;
++    }
++  if (fildes[0] < 0 || fildes[1] < 0)
++    {
++      sys_error (_("cannot make pipe for command substitution"));
++      goto error_exit;
++    }
++#endif /* __CYGWIN__ */
++
+   old_pid = last_made_pid;
+ #if defined (JOB_CONTROL)
+   old_pipeline_pgrp = pipeline_pgrp;
+--- support/bashversion.c	2008-09-09 07:31:53.000000000 -0600
++++ support/bashversion.c	2015-02-06 17:14:11.078059300 -0700
+@@ -26,6 +26,9 @@
+ 
+ #if defined (HAVE_UNISTD_H)
+ #  include <unistd.h>
++#else
++extern int optind;
++extern char *optarg;
+ #endif
+ 
+ #include "bashansi.h"
+@@ -41,9 +44,6 @@
+ #define LFLAG	0x0020
+ #define XFLAG	0x0040
+ 
+-extern int optind;
+-extern char *optarg;
+-
+ extern char *dist_version;
+ extern int patch_level;
+ 
+@@ -65,7 +65,7 @@ main (argc, argv)
+      char **argv;
+ {
+   int opt, oflags;
+-  char dv[128], *rv;
++  char dv[128], *rv = NULL;
+ 
+   if (progname = strrchr (argv[0], '/'))
+     progname++;
+--- support/mkversion.sh	2008-08-13 06:25:57.000000000 -0600
++++ support/mkversion.sh	2015-02-06 17:14:11.078059300 -0700
+@@ -29,7 +29,7 @@ source_dir="."
+ while [ $# -gt 0 ]; do
+ 	case "$1" in
+ 	-o)	shift; OUTFILE=$1; shift ;;
+-	-b)	shift; inc_build=yes ;;
++	-b)	shift; ;;# inc_build=yes ;; # hacked out for cygport
+ 	-s)	shift; rel_status=$1; shift ;;
+ 	-p)	shift; patch_level=$1; shift ;;
+ 	-d)	shift; dist_version=$1; shift ;;
+--- variables.c	2015-02-06 17:12:55.729569600 -0700
++++ variables.c	2015-02-06 17:14:11.078059300 -0700
+@@ -2526,9 +2526,9 @@ bind_variable_internal (name, value, tab
+ 
+   newname = 0;
+ #if defined (ARRAY_VARS)
+-  if ((aflags & ASS_FROMREF) && (hflags & HASH_NOSRCH) == 0 && valid_array_reference (name))
++  if ((aflags & ASS_FROMREF) && (hflags & HASH_NOSRCH) == 0 && valid_array_reference ((char *)name))
+     {
+-      newname = array_variable_name (name, &subp, &sublen);
++      newname = array_variable_name ((char*)name, &subp, &sublen);
+       if (newname == 0)
+ 	return (SHELL_VAR *)NULL;	/* XXX */
+       entry = hash_lookup (newname, table);
+@@ -2573,13 +2573,13 @@ bind_variable_internal (name, value, tab
+       entry = make_new_array_variable (newname);	/* indexed array by default */
+       if (entry == 0)
+ 	return entry;
+-      ind = array_expand_index (name, subp, sublen);
++      ind = array_expand_index (entry, subp, sublen);
+       bind_array_element (entry, ind, value, aflags);
+     }
+ #endif
+   else if (entry == 0)
+     {
+-      entry = make_new_variable (name, table);
++      entry = make_new_variable ((char*)name, table);
+       var_setvalue (entry, make_variable_value (entry, value, 0)); /* XXX */
+     }
+   else if (entry->assign_func)	/* array vars have assign functions now */
+@@ -4679,6 +4679,8 @@ static struct name_and_function special_
+   { "COMP_WORDBREAKS", sv_comp_wordbreaks },
+ #endif
+ 
++  { "EXECIGNORE", sv_execignore },
++
+   { "FUNCNEST", sv_funcnest },
+ 
+   { "GLOBIGNORE", sv_globignore },
+@@ -4877,6 +4879,13 @@ sv_globignore (name)
+     setup_glob_ignore (name);
+ }
+ 
++/* What to do when EXECIGNORE changes. */
++void
++sv_execignore (char *name)
++{
++  setup_exec_ignore (name);
++}
++
+ #if defined (READLINE)
+ void
+ sv_comp_wordbreaks (name)
+@@ -4950,7 +4959,7 @@ sv_winsize (name)
+ /* Update the value of HOME in the export environment so tilde expansion will
+    work on cygwin. */
+ #if defined (__CYGWIN__)
+-sv_home (name)
++void sv_home (name)
+      char *name;
+ {
+   array_needs_making = 1;
+--- variables.h	2014-01-08 13:33:29.000000000 -0700
++++ variables.h	2015-02-06 17:14:11.078059300 -0700
+@@ -372,6 +372,7 @@ extern void sv_ifs __P((char *));
+ extern void sv_path __P((char *));
+ extern void sv_mail __P((char *));
+ extern void sv_funcnest __P((char *));
++extern void sv_execignore __P((char *));
+ extern void sv_globignore __P((char *));
+ extern void sv_ignoreeof __P((char *));
+ extern void sv_strict_posix __P((char *));
diff --git a/pkgs/shells/bash/default.nix b/pkgs/shells/bash/default.nix
index 8774db33b5a..014a3ad4a2c 100644
--- a/pkgs/shells/bash/default.nix
+++ b/pkgs/shells/bash/default.nix
@@ -3,21 +3,11 @@
 assert interactive -> readline != null;
 
 let
-  version = if stdenv.isCygwin then "4.1" else "4.3";
+  version = "4.3";
   realName = "bash-${version}";
-  shortName = if stdenv.isCygwin then "bash41" else "bash43";
+  shortName = "bash43";
   baseConfigureFlags = if interactive then "--with-installed-readline" else "--disable-readline";
-  sha256 = if version == "4.1" then
-      "1np1ggp1lv8idwfx3mcxl9rhadqdf4h3x4isa3dk8v9wm0j72qiz"
-    else
-      "1m14s1f61mf6bijfibcjm9y6pkyvz6gibyl8p4hxq90fisi8gimg";
-
-  basePatchFun = if version == "4.1" then
-      ./bash-4.1-patches.nix
-    else
-      ./bash-4.3-patches.nix;
-
-  extraPatches = stdenv.lib.optional stdenv.isCygwin ./bash-4.1.17-9.src.patch;
+  sha256 = "1m14s1f61mf6bijfibcjm9y6pkyvz6gibyl8p4hxq90fisi8gimg";
 in
 
 stdenv.mkDerivation rec {
@@ -47,11 +37,19 @@ stdenv.mkDerivation rec {
           inherit sha256;
         };
     in
-      import basePatchFun patch) ++ extraPatches;
+      import ./bash-4.3-patches.nix patch) 
+      ++ stdenv.lib.optional stdenv.isCygwin ./cygwin-bash-4.3.33-1.src.patch;
 
   crossAttrs = {
     configureFlags = baseConfigureFlags +
-      " bash_cv_job_control_missing=nomissing bash_cv_sys_named_pipes=nomissing";
+      " bash_cv_job_control_missing=nomissing bash_cv_sys_named_pipes=nomissing" +
+      stdenv.lib.optionalString stdenv.isCygwin ''
+        --without-libintl-prefix --without-libiconv-prefix
+        --with-installed-readline
+        bash_cv_dev_stdin=present
+        bash_cv_dev_fd=standard
+        bash_cv_termcap_lib=libncurses 
+      '';
   };
 
   configureFlags = baseConfigureFlags;