- Don't change the environment block if the number of variables has not changed (in BlockEnvToEnviron).

- Use a copy of the environment strings (in BlockEnvToEnviron).

svn path=/trunk/; revision=9506
This commit is contained in:
Hartmut Birr 2004-05-27 11:49:48 +00:00
parent 94c04c2051
commit 6e3bbc606d
2 changed files with 78 additions and 80 deletions

View file

@ -1,4 +1,4 @@
/* $Id: dllmain.c,v 1.21 2004/05/11 20:44:30 gvg Exp $
/* $Id: dllmain.c,v 1.22 2004/05/27 11:49:48 hbirr Exp $
*
* dllmain.c
*
@ -14,9 +14,9 @@
* DISCLAMED. This includes but is not limited to warrenties of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
*
* $Revision: 1.21 $
* $Author: gvg $
* $Date: 2004/05/11 20:44:30 $
* $Revision: 1.22 $
* $Author: hbirr $
* $Date: 2004/05/27 11:49:48 $
*
*/
@ -48,8 +48,6 @@ extern char** __initenv; /* pointer to initial environment block */
/* LIBRARY GLOBAL VARIABLES ***************************************************/
static int nAttachCount = 0;
HANDLE hHeap = NULL; /* handle for heap */
@ -69,22 +67,11 @@ DllMain(PVOID hinstDll, ULONG dwReason, PVOID reserved)
_winminor = _osver & 0xFF;
_winver = (_winmajor << 8) + _winminor;
_osver = (_osver >> 16) & 0xFFFF;
if (hHeap == NULL || hHeap == INVALID_HANDLE_VALUE)
{
hHeap = HeapCreate(0, 100000, 0);
if (hHeap == NULL || hHeap == INVALID_HANDLE_VALUE)
{
return FALSE;
}
}
if (nAttachCount==0)
{
if (!__fileno_init()) {
HeapDestroy(hHeap);
hHeap = NULL;
return FALSE;
}
}
hHeap = HeapCreate(0, 100000, 0);
if (hHeap == NULL)
return FALSE;
if (!__fileno_init())
return FALSE;
/* create tls stuff */
if (!CreateThreadData())
@ -102,7 +89,6 @@ DllMain(PVOID hinstDll, ULONG dwReason, PVOID reserved)
msvcrt_init_mt_locks();
msvcrt_init_args();
nAttachCount++;
DPRINT("Attach done\n");
break;
@ -115,42 +101,26 @@ DllMain(PVOID hinstDll, ULONG dwReason, PVOID reserved)
case DLL_PROCESS_DETACH://0
DPRINT("Detach %d\n", nAttachCount);
if (nAttachCount > 0)
{
nAttachCount--;
/* FIXME: more cleanup... */
_fcloseall();
/* Deinitialization of the WINE code */
msvcrt_free_args();
msvcrt_free_mt_locks();
/* destroy tls stuff */
DestroyThreadData();
/* FIXME: more cleanup... */
_fcloseall();
if (__initenv && __initenv != _environ)
{
free(__initenv[0]);
free(__initenv);
}
if (_environ)
{
free(_environ[0]);
free(_environ);
}
/* destroy heap */
HeapDestroy(hHeap);
/* destroy tls stuff */
DestroyThreadData();
/* destroy heap */
if (nAttachCount == 0)
{
if (__initenv && __initenv != _environ)
{
FreeEnvironmentStringsA(__initenv[0]);
free(__initenv);
__initenv = NULL;
}
if (_environ)
{
FreeEnvironmentStringsA(_environ[0]);
free(_environ);
_environ = NULL;
}
#if 1
HeapDestroy(hHeap);
hHeap = NULL;
#endif
}
DPRINT("Detach done\n");
}
break;
}

View file

@ -1,4 +1,4 @@
/* $Id: environ.c,v 1.7 2004/02/21 08:02:49 tamlin Exp $
/* $Id: environ.c,v 1.8 2004/05/27 11:49:48 hbirr Exp $
*
* dllmain.c
*
@ -20,6 +20,7 @@ unsigned int _winmajor = 0;
unsigned int _winver = 0;
char *_acmdln = NULL; /* pointer to ascii command line */
unsigned _envvar_count; /* number of environment vars within current environment */
#undef _environ
char **_environ = NULL; /* pointer to environment block */
char ***_environ_dll = &_environ;/* pointer to environment block */
@ -43,46 +44,73 @@ int *__p__commode(void) // not exported by NTDLL
int BlockEnvToEnviron(void)
{
char * ptr, * ptr2;
int i, count;
int i, count, len, size;
DPRINT("BlockEnvToEnviron()\n");
if (_environ && _environ != __initenv) {
FreeEnvironmentStringsA(_environ[0]);
free(_environ);
}
_environ = NULL;
ptr2 = ptr = (char*)GetEnvironmentStringsA();
if (ptr == NULL) {
DPRINT("GetEnvironmentStringsA() returnd NULL\n");
return -1;
return -1;
}
size = 0;
count = 0;
while (*ptr2) {
/* skip current directory of the form "=C:=C:\directory\" */
if (*ptr2 != '=') {
count++;
}
ptr2 += strlen(ptr2) + 1;
len = strlen(ptr2);
if (*ptr2 != '=') {
count++;
size += len + 1;
}
ptr2 += len + 1;
}
_environ = malloc((count + 1) * sizeof(char*));
if (_environ == NULL) {
FreeEnvironmentStringsA(ptr);
return -1;
if (count != _envvar_count) {
if (_environ && _environ != __initenv) {
free(_environ[0]);
_environ = realloc(_environ, (count + 1) * sizeof(char*));
} else {
_environ = malloc((count + 1) * sizeof(char*));
}
if (_environ == NULL) {
FreeEnvironmentStringsA(ptr);
_envvar_count = 0;
return -1;
}
_environ[0] = NULL;
}
if (_environ[0] != NULL) {
free(_environ[0]);
}
_environ[0] = malloc(size);
if (_environ[0] == NULL) {
FreeEnvironmentStringsA(ptr);
free(_environ);
_envvar_count = 0;
return -1;
}
ptr2 = ptr;
i = 0;
while (i < count && *ptr) {
if (*ptr != '=') {
_environ[i] = ptr;
++i;
}
ptr += strlen(ptr) + 1;
while (*ptr2 && i < count) {
len = strlen(ptr2);
/* skip current directory of the form "=C:=C:\directory\" */
if (*ptr2 != '=') {
memcpy(_environ[i], ptr2, len + 1);
i++;
if (i < count) {
_environ[i] = _environ[i - 1] + len + 1;
}
}
ptr2 += len + 1;
}
_environ[i] = NULL;
if (__initenv == NULL)
_envvar_count = count;
if (__initenv == NULL)
{
__initenv = _environ;
}
FreeEnvironmentStringsA(ptr);
return 0;
}