/************************************************************************
*
* environ.cpp - definitions of testsuite helpers
*
* $Id: environ.cpp 290013 2005-09-18 23:47:55Z sebor $
*
************************************************************************
*
* Copyright (c) 1994-2005 Quovadx, Inc., acting through its Rogue Wave
* Software division. Licensed under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance with the
* License. You may obtain a copy of the License at
* http://www.apache.org/licenses/LICENSE-2.0. Unless required by
* applicable law or agreed to in writing, software distributed under
* the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
* CONDITIONS OF ANY KIND, either express or implied. See the License
* for the specific language governing permissions and limitations under
* the License.
*
**************************************************************************/
// expand _TEST_EXPORT macros
#define _RWSTD_TEST_SRC
#include <environ.h>
#include <assert.h> // for assert
#include <stdlib.h> // for getenv, malloc, putenv
#include <string.h> // for strchr, strlen, ...
extern "C" {
#ifndef _RWSTD_NO_PUTENV_CONST_CHAR
IMPORT_C int putenv (const char*) _LIBC_THROWS ();
#else // if defined (_RWSTD_NO_PUTENV_CONST_CHAR)
_RWSTD_DLLIMPORT int putenv (char*) _LIBC_THROWS ();
#endif // _RWSTD_NO_PUTENV_CONST_CHAR
} // extern "C"
// sets one or more sep-separated environment variables
_TEST_EXPORT int
rw_putenv (const char* str, int sep /* = -1 */)
{
int nset = 0;
int ret = 0;
if (!str) {
str = getenv ("RW_PUTENV");
if (str)
sep = *str++;
else
return 0;
}
for (const char *pvar = str; pvar && *pvar; ++nset) {
const char *pend = strchr (pvar, sep);
if (!pend)
pend = pvar + strlen (pvar);
const size_t varlen = pend - pvar;
char* const envvar = (char*)malloc (pend - pvar + 1);
memcpy (envvar, pvar, varlen);
envvar [varlen] = '\0';
// Note: calling Solaris 7 putenv() during program startup
// (i.e., from ctors of namespace-scope objects) prevents
// getenv() from finding that variable at program runtime
ret = putenv (envvar);
// determine wheteher putenv() made copy of the variable
// or if it simply used the pointer passed to it; if the
// former, deallocate the buffer dynamically allocated
// above
char namebuf [256];
char* const equals = strchr (envvar, '=');
if (equals) {
assert (size_t (equals - envvar) < sizeof namebuf);
memcpy (namebuf, envvar, equals - envvar);
namebuf [equals - envvar] = '\0';
const char* const var = getenv (namebuf);
if (equals + 1 != var)
free (envvar);
}
else
free (envvar);
pvar = pend + !!*pend;
}
if (1 == nset)
return ret;
return nset;
}