Index: trunk/src/emx/include/InnoTekLIBC/logstrict.h
===================================================================
--- trunk/src/emx/include/InnoTekLIBC/logstrict.h	(revision 1314)
+++ trunk/src/emx/include/InnoTekLIBC/logstrict.h	(revision 1315)
@@ -176,4 +176,6 @@
 /** Signal APIs and events. */
 #define __LIBC_LOG_GRP_SIGNAL       14
+/** Environment APIs. */
+#define __LIBC_LOG_GRP_ENV          15
 
 /** Init/Term APIs and Events. */
Index: trunk/src/emx/include/InnoTekLIBC/thread.h
===================================================================
--- trunk/src/emx/include/InnoTekLIBC/thread.h	(revision 1314)
+++ trunk/src/emx/include/InnoTekLIBC/thread.h	(revision 1315)
@@ -59,5 +59,5 @@
  * Members most frequently used have been put together at the front.
  */
-typedef struct __libc_threadCurrentSlow
+typedef struct __libc_thread
 {
     /** errno value. (Comes first, see errnofun.s.) */
@@ -72,4 +72,6 @@
     void           *apvTLS[__LIBC_TLS_MAX];
 
+    /** The nesting depth of the default logger. */
+    unsigned        cDefLoggerDepth;
     /** Current rand() seed value. */
     unsigned int    iRand;
@@ -135,5 +137,5 @@
 #ifndef __LIBC_THREAD_DECLARED
 #define __LIBC_THREAD_DECLARED
-typedef struct __libc_threadCurrentSlow *__LIBC_PTHREAD, **__LIBC_PPTHREAD;
+typedef struct __libc_thread *__LIBC_PTHREAD, **__LIBC_PPTHREAD;
 #endif
 
Index: trunk/src/emx/src/lib/app/getenv.c
===================================================================
--- trunk/src/emx/src/lib/app/getenv.c	(revision 1314)
+++ trunk/src/emx/src/lib/app/getenv.c	(revision 1315)
@@ -4,16 +4,30 @@
 #include <stdlib.h>
 #include <string.h>
+#define __LIBC_LOG_GROUP  __LIBC_LOG_GRP_ENV
+#include <InnoTekLIBC/logstrict.h>
 
-char *_STD(getenv) (const char *name)
+char *_STD(getenv)(const char *name)
 {
-  int len;
-  char **p;
+    LIBCLOG_ENTER("name=%s\n", name);
+    int len;
+    char **p;
 
-  if (name == NULL || environ == NULL)
-    return NULL;
-  len = strlen (name);
-  for (p = environ; *p != NULL; ++p)
-    if (strncmp (*p, name, len) == 0 && (*p)[len] == '=')
-      return *p + len + 1;
-  return NULL;
+    if (name == NULL || environ == NULL)
+    {
+        LIBC_ASSERTM(name, "invalid parameter name(%p)\n", name);
+        LIBC_ASSERTM(environ, "environment is not configured!!!\n");
+        LIBCLOG_RETURN_P(NULL);
+    }
+    LIBC_ASSERTM(!strchr(name, '='), "name contains '='\n");
+    LIBC_ASSERTM(*name, "name is empty\n");
+
+    len = strlen(name);
+    for (p = environ; *p != NULL; ++p)
+        if (    strncmp(*p, name, len) == 0
+            &&  (*p)[len] == '=')
+        {
+            char *pszRet = *p + len + 1;
+            LIBCLOG_RETURN_MSG(pszRet, "ret %p(='%s')\n", pszRet, pszRet);
+        }
+    LIBCLOG_RETURN_P(NULL);
 }
Index: trunk/src/emx/src/lib/app/putenv.c
===================================================================
--- trunk/src/emx/src/lib/app/putenv.c	(revision 1314)
+++ trunk/src/emx/src/lib/app/putenv.c	(revision 1315)
@@ -7,52 +7,74 @@
 #include <emx/startup.h>
 #include <emx/time.h>           /* _tzset_flag */
+#define __LIBC_LOG_GROUP  __LIBC_LOG_GRP_ENV
+#include <InnoTekLIBC/logstrict.h>
 
-int _STD(putenv) (const char *string)
+int _STD(putenv)(const char *string)
 {
-  char *s, **p;
-  int len, env_size;
+    LIBCLOG_ENTER("string=%s\n", string);
+    char *s, **p;
+    int len, env_size;
 
-  if (string == NULL)
+    if (string == NULL)
     {
-      errno = EINVAL;
-      return -1;
+        LIBC_ASSERTM_FAILED("bad string(=%p)\n", string);
+        errno = EINVAL;
+        LIBCLOG_RETURN_INT(-1);
     }
-  _tzset_flag = 0;              /* Call tzset() */
-  s = strchr (string, '=');
-  if (s == NULL)
-    len = strlen (string);        /* Use complete string */
-  else
-    len = s - string;
-  p = environ;
-  env_size = 0;
-  if (p != NULL)
-    while (*p != NULL)
-      {
-        s = *p;
-        if (strncmp (s, string, len) == 0 && (s[len] == 0 || s[len] == '='))
-          break;
-        ++p; ++env_size;
-      }
-  if (p == NULL || *p == NULL)
+    _tzset_flag = 0;                    /* Call tzset() */
+    s = strchr(string, '=');
+    if (s == NULL)
+        len = strlen(string);           /* Use complete string */
+    else
+        len = s - string;
+    p = environ;
+    env_size = 0;
+    if (p != NULL)
     {
-      if (environ == _org_environ)
+        while (*p != NULL)
         {
-          p = malloc ((env_size+2) * sizeof (char *));
-          if (p == NULL) return -1;
-          environ = p;
-          if (env_size != 0)
-            memcpy (environ, _org_environ, env_size * sizeof (char *));
+            s = *p;
+            if (    strncmp(s, string, len) == 0
+                &&  (   s[len] == '\0'
+                     || s[len] == '='))
+                break;
+            ++p;
+            ++env_size;
         }
-      else
+    }
+    else
+        LIBC_ASSERTM_FAILED("environment not initiated!\n");
+
+    if (p == NULL || *p == NULL)
+    {
+        if (environ == _org_environ)
         {
-          p = realloc (environ, (env_size+2) * sizeof (char *));
-          if (p == NULL) return -1;
-          environ = p;
+            LIBCLOG_MSG("env_size=%d; new, first new\n", env_size);
+            p = malloc((env_size + 2) * sizeof (char *));
+            if (p == NULL)
+                LIBCLOG_RETURN_INT(-1);
+            environ = p;
+            if (env_size != 0)
+                memcpy(environ, _org_environ, env_size * sizeof (char *));
         }
-      environ[env_size+0] = (char *)string;
-      environ[env_size+1] = NULL;
+        else
+        {
+            LIBCLOG_MSG("env_size=%d; new, resize environ array\n", env_size);
+            p = realloc(environ, (env_size + 2) * sizeof (char *));
+            if (p == NULL)
+                LIBCLOG_RETURN_INT(-1);
+            environ = p;
+        }
+        environ[env_size + 0] = (char *)string;
+        environ[env_size + 1] = NULL;
     }
-  else
-    *p = (char *)string;
-  return 0;
+    else
+    {
+        LIBCLOG_MSG("replacing '%s' with '%s'\n", *p, string);
+        *p = (char *)string;
+        /** @todo this doesn't match the unset policy, we should remove the
+                  variable entirely from the environment when no value is
+                  specified! */
+    }
+    LIBCLOG_RETURN_INT(0);
 }
Index: trunk/src/emx/src/lib/app/setenv.c
===================================================================
--- trunk/src/emx/src/lib/app/setenv.c	(revision 1314)
+++ trunk/src/emx/src/lib/app/setenv.c	(revision 1315)
@@ -17,4 +17,6 @@
 #include <emx/startup.h>
 #include <emx/time.h>           /* _tzset_flag */
+#define __LIBC_LOG_GROUP  __LIBC_LOG_GRP_ENV
+#include <InnoTekLIBC/logstrict.h>
 
 
@@ -34,83 +36,96 @@
  * @author  knut st. osmundsen <bird-srcspam@anduin.net>
  * @remark  We skip the first equal in the environment value like BSD does.
+ * @remark  Make environment updating and such thread safe!
  */
-int _STD(setenv) (const char *envname, const char *envval, int overwrite)
+int _STD(setenv)(const char *envname, const char *envval, int overwrite)
 {
-  char **p;
-  int   lenname;
-  int   lenval;
-  int   env_size;
+    LIBCLOG_ENTER("envname=%s envval=%s overwrite=%d\n", envname, envval, overwrite);
+    char **p;
+    char *psz;
+    int   lenname;
+    int   lenval;
+    int   env_size;
 
-  /* validate */
-  if (envname == NULL || *envname == '\0' || strchr(envname, '=') != NULL)
+    /* validate */
+    if (envname == NULL || *envname == '\0' || strchr(envname, '=') != NULL)
     {
-      errno = EINVAL;
-      return -1;
+        LIBC_ASSERTM_FAILED("invalid argument envname(%p='%s')\n", envname, envname);
+        errno = EINVAL;
+        LIBCLOG_RETURN_INT(-1);
     }
-  _tzset_flag = 0;              /* Call tzset() */
+    _tzset_flag = 0;              /* Call tzset() */
 
-  /* BSD Compatability. */
-  if (*envval == '=')
-      envval++;
+    /* BSD Compatability. */
+    if (*envval == '=')
+        envval++;
 
-  /* search for existing variable iinstance  */
-  lenname = strlen (envname);
-  p = environ;
-  env_size = 0;
-  if (p != NULL)
-    while (*p != NULL)
-      {
-        char *s = *p;
-        if (strncmp (s, envname, lenname) == 0 && (s[lenname] == 0 || s[lenname] == '='))
-          break;
-        ++p; ++env_size;
-      }
+    /* search for existing variable iinstance  */
+    lenname = strlen(envname);
+    p = environ;
+    env_size = 0;
+    if (p != NULL)
+        while (*p != NULL)
+        {
+            char *s = *p;
+            if (    strncmp(s, envname, lenname) == 0
+                && (    s[lenname] == '\0'
+                    ||  s[lenname] == '='))
+                break;
+            ++p; ++env_size;
+        }
 
-  /* found it? */
-  lenval = strlen(envval);
-  if (p != NULL && *p != NULL)
+    /* found it? */
+    lenval = strlen(envval);
+    if (p != NULL && *p != NULL)
     {
-      if (!overwrite)
-        return 0;
-      /* if the older is larger then overwrite it */
-      if (strlen(*p + lenname + 1) >= lenval)
+        if (!overwrite)
         {
-           memcpy(*p + lenname + 1, envval, lenval + 1);
-           return 0;
+            LIBCLOG_MSG("exists, requested not to overwrite it\n");
+            LIBCLOG_RETURN_INT(0);
+        }
+        /* if the older is larger then overwrite it */
+        LIBCLOG_MSG("exists, overwrite\n");
+        if (strlen(*p + lenname + 1) >= lenval)
+        {
+            memcpy(*p + lenname + 1, envval, lenval + 1);
+            LIBCLOG_RETURN_INT(0);
         }
     }
-  else
+    else
     {
-      /* new variable: reallocate the environment pointer block */
-      if (environ == _org_environ)
+        /* new variable: reallocate the environment pointer block */
+        if (environ == _org_environ)
         {
-          p = malloc ((env_size+2) * sizeof (char *));
-          if (p == NULL)
-              return -1;
-          environ = p;
-          if (env_size != 0)
-            memcpy (environ, _org_environ, env_size * sizeof (char *));
+            LIBCLOG_MSG("env_size=%d; new, first new\n", env_size);
+            p = malloc((env_size + 2) * sizeof (char *));
+            if (p == NULL)
+                LIBCLOG_RETURN_INT(-1);
+            environ = p;
+            if (env_size != 0)
+                memcpy(environ, _org_environ, env_size * sizeof (char *));
         }
-      else
+        else
         {
-          p = realloc (environ, (env_size+2) * sizeof (char *));
-          if (p == NULL)
-              return -1;
-          environ = p;
+            LIBCLOG_MSG("env_size=%d; new, resize environ array\n", env_size);
+            p = realloc(environ, (env_size + 2) * sizeof (char *));
+            if (p == NULL)
+                LIBCLOG_RETURN_INT(-1);
+            environ = p;
         }
 
-      /* Add to end. */
-      p = &environ[env_size+0];
-      environ[env_size+1] = NULL;
+        /* Add to end. */
+        p = &environ[env_size + 0];
+        environ[env_size + 1] = NULL;
     }
 
-  /* Allocate space for new variable and assign it. */
-  *p = malloc(lenname + lenval + 2);
-  if (!*p)
-    return -1;
-  memcpy(*p, envname, lenname);
-  (*p)[lenname] = '=';
-  memcpy(*p + lenname + 1, envval, lenval + 1);
-  return 0;
+    /* Allocate space for new variable and assign it. */
+    psz = malloc(lenname + lenval + 2);
+    if (!psz)
+        LIBCLOG_RETURN_INT(-1);
+    memcpy(psz, envname, lenname);
+    psz[lenname] = '=';
+    memcpy(psz + lenname + 1, envval, lenval + 1);
+    *p = psz;
+    LIBCLOG_RETURN_INT(0);
 }
 
Index: trunk/src/emx/src/lib/app/stdio.c
===================================================================
--- trunk/src/emx/src/lib/app/stdio.c	(revision 1314)
+++ trunk/src/emx/src/lib/app/stdio.c	(revision 1315)
@@ -1,3 +1,4 @@
-/* stdio.c (emx+gcc) -- Copyright (c) 1990-1996 by Eberhard Mattes */
+/* stdio.c (emx+gcc) -- Copyright (c) 1990-1996 by Eberhard Mattes
+                     -- Copyright (c) 2003-2004 by knut st. osmundsen */
 
 #include "libc-alias.h"
@@ -9,4 +10,6 @@
 #include <emx/io.h>
 #include <emx/startup.h>
+#define __LIBC_LOG_GROUP  __LIBC_LOG_GRP_STREAM
+#include <InnoTekLIBC/logstrict.h>
 
 
@@ -53,4 +56,5 @@
 void _init_streams(void)
 {
+    LIBCLOG_ENTER("\n");
     struct _FILE       *pFile;
     struct _file2      *pFile2;
@@ -62,6 +66,7 @@
      */
     if (fInited)
-        return;
+        LIBCLOG_RETURN_VOID();
     fInited = 1;
+    LIBCLOG_MSG("_NFILES=%d\n", _NFILES);
 
     /*
@@ -101,5 +106,8 @@
             gaPreFiles[i]._flush     = _flushstream;
             if (_setmore(&gaPreFiles[i], 0))
+            {
+                LIBC_ASSERTM_FAILED("_setmore failed for i=%d\n", i);
                 abort();
+            }
 
             /*
@@ -114,4 +122,5 @@
                     gaPreFiles[0]._buffer    = gachStdIn;
                     gaPreFiles[0]._buf_size  = BUFSIZ;
+                    LIBCLOG_MSG("__stdinp=%p\n", __stdinp);
                     break;
 
@@ -120,4 +129,6 @@
                     gaPreFiles[1]._flags |= _IOWRT | _IOBUFNONE
                         | ((pFH->fFlags & F_TYPEMASK) == F_DEV ? _IONBF : _IOFBF);
+                    LIBCLOG_MSG("__stdoutp=%p flags=%#x (%s)\n", __stdoutp, gaPreFiles[1]._flags,
+                                (pFH->fFlags & F_TYPEMASK) == F_DEV ? "dev" : "none-dev");
                     break;
 
@@ -125,8 +136,12 @@
                     /* stderr is always unbuffered. */
                     gaPreFiles[2]._flags |= _IOWRT | _IOBUFNONE | _IONBF;
+                    LIBCLOG_MSG("__stderrp=%p\n", __stderrp);
                     break;
             }
         }
+        else
+            LIBCLOG_MSG("No open file for %d\n", i);
     } /* for standard handles. */
+    LIBCLOG_RETURN_VOID();
 }
 
Index: trunk/src/emx/src/lib/app/unsetenv.c
===================================================================
--- trunk/src/emx/src/lib/app/unsetenv.c	(revision 1314)
+++ trunk/src/emx/src/lib/app/unsetenv.c	(revision 1315)
@@ -2,5 +2,5 @@
 /** @file
  *
- * unsetenv()
+ * LIBC APP - unsetenv()
  *
  * Copyright (c) 2003 InnoTek Systemberatung GmbH
@@ -17,4 +17,6 @@
 #include <errno.h>
 #include <emx/startup.h>
+#define __LIBC_LOG_GROUP  __LIBC_LOG_GRP_ENV
+#include <InnoTekLIBC/logstrict.h>
 
 
@@ -26,20 +28,22 @@
  * @returns -1 and errno=EINVAL if name is invalid in any way.
  * @param   name    Name of environment variable to unset.
- *                  Shall not be NULL, empty string of contain '='.
- * @remark  May be leaking memory, but that's what BSD does.
+ *                  Shall not be NULL, empty string or contain '='.
+ * @remark  Leaks memory, but that's what BSD does too.
  * @author  knut st. osmundsen <bird-srcspam@anduin.net>
  */
 int _STD(unsetenv)(const char *name)
 {
+    LIBCLOG_ENTER("name=%s\n", name);
     int     lenname;
     char ** p;
 
+
     /* validate input */
     if (name == NULL || *name == '\0' || strchr(name, '=') != NULL)
-      {
+    {
         errno = EINVAL;
-        return -1;
-      }
-
+        LIBC_ASSERTM_FAILED("name(%p='%s') is invalid\n", name, name);
+        LIBCLOG_RETURN_INT(-1);
+    }
 
     /* search (thru all the environment in case of multiple defintions). */
@@ -47,19 +51,23 @@
     p = environ;
     while (*p != NULL)
-      {
+    {
         char *s = *p;
-        if (strncmp (s, name, lenname) == 0 && (s[lenname] == 0 || s[lenname] == '='))
-          { /* shift down the remaining entries. */
+        if (    strncmp(s, name, lenname) == 0
+            && (    s[lenname] == '\0'
+                ||  s[lenname] == '='))
+        { /* shift down the remaining entries. */
             char **p2 = p;
             for (;;p2++)
                 if ((p2[0] = p2[1]) == NULL)
                     break;
-          }
+            LIBCLOG_MSG("deleted '%s'\n", s);
+        }
         else
-          {
+        {
             /* next */
             p++;
-          }
-      }
-    return 0;
+        }
+    }
+
+    LIBCLOG_RETURN_INT(0);
 }
