aboutsummaryrefslogtreecommitdiff
path: root/winsup/cygwin
diff options
context:
space:
mode:
authorKen Brown <kbrown@cornell.edu>2018-06-06 11:45:55 -0400
committerCorinna Vinschen <corinna@vinschen.de>2018-06-07 09:42:36 +0200
commit9234545e3d84a873e1c1a6faff28cfb55320a248 (patch)
treedec699754881be8dcbaadc9a4d8d527765b130b9 /winsup/cygwin
parent1ecbb8d7b796b980db120d81f625d206c6a728da (diff)
downloadnewlib-9234545e3d84a873e1c1a6faff28cfb55320a248.zip
newlib-9234545e3d84a873e1c1a6faff28cfb55320a248.tar.gz
newlib-9234545e3d84a873e1c1a6faff28cfb55320a248.tar.bz2
Cygwin: Allow the environment pointer to be NULL
Following glibc, interpret this as meaning the environment is empty.
Diffstat (limited to 'winsup/cygwin')
-rw-r--r--winsup/cygwin/environ.cc40
-rw-r--r--winsup/cygwin/pinfo.cc7
2 files changed, 30 insertions, 17 deletions
diff --git a/winsup/cygwin/environ.cc b/winsup/cygwin/environ.cc
index b452d21..06e1ced 100644
--- a/winsup/cygwin/environ.cc
+++ b/winsup/cygwin/environ.cc
@@ -30,6 +30,7 @@ details. */
#include "shared_info.h"
#include "ntdll.h"
+/* If this is not NULL, it points to memory allocated by us. */
static char **lastenviron;
/* Parse CYGWIN options */
@@ -483,6 +484,9 @@ my_findenv (const char *name, int *offset)
register char **p;
const char *c;
+ if (cur_environ () == NULL)
+ return NULL;
+
c = name;
len = 0;
while (*c && *c != '=')
@@ -545,14 +549,18 @@ _getenv_r (struct _reent *, const char *name)
return findenv_func (name, &offset);
}
-/* Return size of environment block, including terminating NULL. */
+/* Return number of environment entries, including terminating NULL. */
static int __stdcall
envsize (const char * const *in_envp)
{
const char * const *envp;
+
+ if (in_envp == NULL)
+ return 0;
+
for (envp = in_envp; *envp; envp++)
continue;
- return (1 + envp - in_envp) * sizeof (const char *);
+ return 1 + envp - in_envp;
}
/* Takes similar arguments to setenv except that overwrite is
@@ -584,23 +592,22 @@ _addenv (const char *name, const char *value, int overwrite)
{ /* Create new slot. */
int sz = envsize (cur_environ ());
- /* Allocate space for two new slots even though only one is needed.
- According to the commit message for commit ebd645e
- (2001-10-03), this is done to "work around problems with some
- buggy applications." */
- int allocsz = sz + (2 * sizeof (char *));
+ /* If sz == 0, we need two new slots, one for the terminating NULL.
+ But we add two slots in all cases, as has been done since
+ 2001-10-03 (commit ebd645e) to "work around problems with
+ some buggy applications." */
+ int allocsz = (sz + 2) * sizeof (char *);
- offset = (sz - 1) / sizeof (char *);
+ offset = sz == 0 ? 0 : sz - 1;
/* Allocate space for additional element. */
if (cur_environ () == lastenviron)
- lastenviron = __cygwin_environ = (char **) realloc (cur_environ (),
+ lastenviron = __cygwin_environ = (char **) realloc (lastenviron,
allocsz);
- else if ((lastenviron = (char **) malloc (allocsz)) != NULL)
- __cygwin_environ = (char **) memcpy ((char **) lastenviron,
- __cygwin_environ, sz);
-
- if (!__cygwin_environ)
+ else if ((lastenviron = (char **) realloc (lastenviron, allocsz)) != NULL)
+ __cygwin_environ = (char **) memcpy (lastenviron, __cygwin_environ,
+ sz * sizeof (char *));
+ if (!lastenviron)
{
#ifdef DEBUGGING
try_to_debug ();
@@ -1029,8 +1036,13 @@ build_env (const char * const *envp, PWCHAR &envblock, int &envc,
char **dstp;
bool saw_spenv[SPENVS_SIZE] = {0};
+ static char *const empty_env[] = { NULL };
+
debug_printf ("envp %p", envp);
+ if (!envp)
+ envp = empty_env;
+
/* How many elements? */
for (n = 0; envp[n]; n++)
continue;
diff --git a/winsup/cygwin/pinfo.cc b/winsup/cygwin/pinfo.cc
index e4eef8b..6b6986c 100644
--- a/winsup/cygwin/pinfo.cc
+++ b/winsup/cygwin/pinfo.cc
@@ -677,11 +677,12 @@ commune_process (void *arg)
sigproc_printf ("processing PICOM_ENVIRON");
unsigned n = 0;
char **env = cur_environ ();
- for (char **e = env; *e; e++)
- n += strlen (*e) + 1;
+ if (env)
+ for (char **e = env; *e; e++)
+ n += strlen (*e) + 1;
if (!WritePipeOverlapped (tothem, &n, sizeof n, &nr, 1000L))
sigproc_printf ("WritePipeOverlapped sizeof argv failed, %E");
- else
+ else if (env)
for (char **e = env; *e; e++)
if (!WritePipeOverlapped (tothem, *e, strlen (*e) + 1, &nr, 1000L))
{