From 2e9d484382fe45ff1dcd325be0992b1857f9498d Mon Sep 17 00:00:00 2001 From: Christopher Faylor Date: Thu, 13 Apr 2006 01:37:00 +0000 Subject: [PATCH] * spawn.cc (spawn_guts): Revert patch which treated derived cygwin programs differently from those which are mounted with -X. Pass extra argument to linebuf::fromargv. * winf.h (MAXCYGWINCMDLEN): New define. (linebuf::finish): Add a new argument denoting when command line overflow is ok. (linebuf::fromargv): Ditto. * winf.cc (linebuf::finish): Implement above change. (linebuf::fromargv): Ditto. --- winsup/cygwin/ChangeLog | 13 +++++++++++++ winsup/cygwin/spawn.cc | 7 ++++--- winsup/cygwin/winf.cc | 12 ++++++++---- winsup/cygwin/winf.h | 12 ++++++++++-- 4 files changed, 35 insertions(+), 9 deletions(-) diff --git a/winsup/cygwin/ChangeLog b/winsup/cygwin/ChangeLog index 0352479fb..5e4f22c79 100644 --- a/winsup/cygwin/ChangeLog +++ b/winsup/cygwin/ChangeLog @@ -1,3 +1,16 @@ +2006-04-12 Corinna Vinschen + Christopher Faylor + + * spawn.cc (spawn_guts): Revert patch which treated derived cygwin + programs differently from those which are mounted with -X. Pass extra + argument to linebuf::fromargv. + * winf.h (MAXCYGWINCMDLEN): New define. + (linebuf::finish): Add a new argument denoting when command line + overflow is ok. + (linebuf::fromargv): Ditto. + * winf.cc (linebuf::finish): Implement above change. + (linebuf::fromargv): Ditto. + 2006-04-11 Christopher Faylor * Makefile.in (DLL_OFILES): Add winf.o. diff --git a/winsup/cygwin/spawn.cc b/winsup/cygwin/spawn.cc index 9d358da0c..a39145ed8 100644 --- a/winsup/cygwin/spawn.cc +++ b/winsup/cygwin/spawn.cc @@ -347,6 +347,7 @@ spawn_guts (const char * prog_arg, const char *const *argv, goto out; } + bool wascygexec = real_path.iscygexec (); res = newargv.fixup (prog_arg, real_path, ext); if (res) @@ -371,9 +372,9 @@ spawn_guts (const char * prog_arg, const char *const *argv, } else { - if (real_path.iscygexec ()) + if (wascygexec) newargv.dup_all (); - else if (!one_line.fromargv (newargv, real_path)) + else if (!one_line.fromargv (newargv, real_path, real_path.iscygexec ())) { res = -1; goto out; @@ -461,6 +462,7 @@ spawn_guts (const char * prog_arg, const char *const *argv, cygheap->fdtab.set_file_pointers_for_exec (); + ch.set (chtype, real_path.iscygexec ()); moreinfo->envp = build_env (envp, envblock, moreinfo->envc, real_path.iscygexec ()); if (!moreinfo->envp || !envblock) { @@ -468,7 +470,6 @@ spawn_guts (const char * prog_arg, const char *const *argv, res = -1; goto out; } - ch.set (chtype, real_path.iscygexec ()); ch.moreinfo = moreinfo; si.lpReserved2 = (LPBYTE) &ch; diff --git a/winsup/cygwin/winf.cc b/winsup/cygwin/winf.cc index 01c5cfb65..81c58db4f 100644 --- a/winsup/cygwin/winf.cc +++ b/winsup/cygwin/winf.cc @@ -19,12 +19,16 @@ details. */ #include "sys/cygwin.h" void -linebuf::finish () +linebuf::finish (bool cmdlenoverflow_ok) { if (!ix) add ("", 1); else - buf[--ix] = '\0'; + { + if (ix-- > MAXCYGWINCMDLEN && cmdlenoverflow_ok) + ix = MAXCYGWINCMDLEN - 1; + buf[ix] = '\0'; + } } void @@ -61,7 +65,7 @@ linebuf::prepend (const char *what, int len) } bool -linebuf::fromargv (av& newargv, char *real_path) +linebuf::fromargv (av& newargv, char *real_path, bool cmdlenoverflow_ok) { bool success = true; for (int i = 0; i < newargv.argc; i++) @@ -110,7 +114,7 @@ linebuf::fromargv (av& newargv, char *real_path) add (" ", 1); } - finish (); + finish (cmdlenoverflow_ok); if (ix >= MAXWINCMDLEN) { diff --git a/winsup/cygwin/winf.h b/winsup/cygwin/winf.h index 3b7fec23b..209091468 100644 --- a/winsup/cygwin/winf.h +++ b/winsup/cygwin/winf.h @@ -9,6 +9,14 @@ details. */ #ifndef _WINF_H #define _WINF_H +/* Hack for Cygwin processes. If the Windows command line length gets slightly + bigger than this value, the stack position is suddenly moved up by 64K for + no apparent reason, which results in subsequent forks failing. Since Cygwin + processes get the full command line as argv array anyway, this only affects + the maximum command line length of Cygwin applications which non-sensically + have a WinMain instead of a main entry point. */ +#define MAXCYGWINCMDLEN 31767 + #define MAXWINCMDLEN 32767 #define LINE_BUF_CHUNK (CYG_MAX_PATH * 2) @@ -74,8 +82,8 @@ class linebuf void add (const char *what, int len) __attribute__ ((regparm (3))); void add (const char *what) {add (what, strlen (what));} void prepend (const char *what, int len); - void finish () __attribute__ ((regparm (1))); - bool fromargv(av&, char *); + void finish (bool) __attribute__ ((regparm (2))); + bool fromargv(av&, char *, bool) __attribute__ ((regparm (3)));; operator char *() {return buf;} };