{ return __mingw_mkdtemp( __dirname_template ); }
#endif /* _POSIX_C_SOURCE >= 200809L (for mkdtemp()) */
+
+#if _POSIX_C_SOURCE >= 200112L
+/* setenv() and unsetenv() are also available, from POSIX.1-2001 onwards.
+ */
+__cdecl __MINGW_NOTHROW int setenv( const char *, const char *, int );
+__cdecl __MINGW_NOTHROW int unsetenv( const char * );
+
+__cdecl __MINGW_NOTHROW int __mingw_setenv( const char *, const char *, int );
+
+__CRT_ALIAS __JMPSTUB__(( FUNCTION = setenv ))
+__cdecl __MINGW_NOTHROW int setenv( const char *__n, const char *__v, int __f )
+{ return __mingw_setenv( __n, __v, __f ); }
+
+__CRT_ALIAS __LIBIMPL__(( FUNCTION = unsetenv ))
+__cdecl __MINGW_NOTHROW int unsetenv( const char *__name )
+{ return __mingw_setenv( __name, NULL, 1 ); }
+
+#endif /* _POSIX_C_SOURCE >= 200112L (for setenv()) */
#endif /* _STDLIB_H */
_END_C_DECLS
--- /dev/null
+/*
+ * setenv.c
+ *
+ * Implementation of POSIX standard IEEE 1003.1-2001 setenv() function;
+ * may also be invoked inline, as "retval = setenv( varname, NULL, 1 )",
+ * to implement the complementary unsetenv() function.
+ *
+ * $Id$
+ *
+ * Written by Keith Marshall <keithmarshall@users.sourceforge.net>
+ * Copyright (C) 2016, MinGW.org Project
+ *
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included
+ * in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+ * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ *
+ */
+#define _POSIX_C_SOURCE 200112L
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <errno.h>
+
+int __mingw_setenv( const char *var, const char *value, int overwrite )
+{
+ /* Core implementation for both setenv() and unsetenv() functions;
+ * at the outset, assume that the requested operation may fail.
+ */
+ int retval = -1;
+
+ /* The specified "var" name MUST be non-NULL, not a zero-length
+ * string, and must not include any '=' character.
+ */
+ if( var && *var && (strchr( var, '=' ) == NULL) )
+ {
+ /* A properly named variable may be added to, removed from,
+ * or modified within the environment, ONLY if "overwrite"
+ * mode is enabled, OR if the named variable does not yet
+ * exist...
+ */
+ if( overwrite || getenv( var ) == NULL )
+ {
+ /* ... in which cases, we convert the specified name and
+ * value into the appropriate form for use with putenv(),
+ * (noting that we accept a NULL "value" as equivalent to
+ * a zero-length string, which renders putenv() as the
+ * equivalent of unsetenv()).
+ */
+ const char *fmt = "%s=%s";
+ const char *val = value ? value : "";
+ char buf[1 + snprintf( NULL, 0, fmt, var, val )];
+ snprintf( buf, sizeof( buf ), fmt, var, val );
+
+ /* "buf" is now formatted as "var=value", in the form
+ * required by putenv(), but it exists only within our
+ * volatile stack-frame space. POSIX.1 suggests that we
+ * should copy it to more persistent storage, before it
+ * is passed to putenv(), to associate an environment
+ * pointer with it. However, we note that Microsoft's
+ * putenv() implementation appears to make such a copy
+ * in any case, so we do not do so; (in fact, if we did
+ * strdup() it (say), then we would leak memory).
+ */
+ if( (retval = putenv( buf )) != 0 )
+ /*
+ * If putenv() returns non-zero, indicating failure, the
+ * most probable explanation is that there wasn't enough
+ * free memory; ensure that errno is set accordingly.
+ */
+ errno = ENOMEM;
+ }
+ else
+ /* The named variable already exists, and overwrite mode
+ * was not enabled; there is nothing to be done.
+ */
+ retval = 0;
+ }
+ else
+ /* The specified environment variable name was invalid.
+ */
+ errno = EINVAL;
+
+ /* Succeed or fail, "retval" has now been set to indicate the
+ * appropriate status for return.
+ */
+ return retval;
+}
+
+/* $RCSfile$: end of file */