[CRT] Fix _onexit

Avoid calling malloc in CR initialisation code.
Have executables call msvcrt implementation, while the DLLs keep their own function tables

CORE-17362
This commit is contained in:
Jérôme Gardou 2020-12-28 12:06:34 +01:00 committed by Jérôme Gardou
parent 6c6d9bee68
commit 8a6d653044
4 changed files with 51 additions and 43 deletions

View file

@ -883,7 +883,7 @@
@ stub -version=0x600+ -arch=i386 _msize_debug
@ cdecl _nextafter(double double)
@ stub -arch=x86_64 _nextafterf
@ cdecl _onexit(ptr)
@ extern _onexit # Declaring it as extern let us use the symbol from msvcrtex while having the __imp_ symbol defined in the import lib
@ varargs _open(str long)
@ cdecl _open_osfhandle(long long)
@ extern _osplatform
@ -1293,7 +1293,7 @@
@ cdecl atan2(double double)
@ cdecl -arch=x86_64,arm atan2f(long)
@ cdecl -arch=x86_64,arm atanf(long)
@ extern atexit # <-- keep this as an extern, thank you
@ extern atexit # Declaring it as extern let us use the symbol from msvcrtex while having the __imp_ symbol defined in the import lib for those who really need it
@ cdecl atof(str)
@ cdecl atoi(str)
@ cdecl atol(str)

View file

@ -4,7 +4,6 @@
* No warranty is given; refer to the file DISCLAIMER.PD within this package.
*/
#undef CRTDLL
#ifndef _DLL
#define _DLL
#endif
@ -33,16 +32,19 @@ void __call_atexit(void)
/* Note: should only be called with the exit lock held */
_PVFV *first, *last;
first = (_PVFV *)_decode_pointer(__onexitbegin);
last = (_PVFV *)_decode_pointer(__onexitend);;
if (!__onexitbegin)
return;
if (!first) return;
first = (_PVFV *)_decode_pointer(__onexitbegin);
last = (_PVFV *)_decode_pointer(__onexitend);
while (--last >= first)
if (*last)
(**last)();
free(first);
__onexitbegin = __onexitend = NULL;
}
/* Choose a different name to prevent name conflicts. The CRT one works fine. */
@ -54,28 +56,39 @@ _onexit_t __cdecl _onexit(_onexit_t func)
_PVFV *onexitend;
_onexit_t retval;
onexitbegin = (_PVFV *) _decode_pointer (__onexitbegin);
if (onexitbegin == (_PVFV *) -1)
#ifdef __REACTOS__
{
onexitbegin = (_PVFV *)calloc(32, sizeof(_onexit_t));
if (onexitbegin == NULL)
return NULL;
__onexitbegin = _encode_pointer(onexitbegin);
__onexitend = _encode_pointer(onexitbegin + 32);
}
#else
#ifndef CRTDLL
if (__onexitbegin == (_PVFV *) -1)
return (* __MINGW_IMP_SYMBOL(_onexit)) (func);
#endif
_lock (_EXIT_LOCK1);
if (!__onexitbegin)
{
/* First time we are called. Initialize our array */
onexitbegin = calloc(1, sizeof(*onexitbegin));
if (!onexitbegin)
{
_unlock(_EXIT_LOCK1);
return NULL;
}
onexitend = onexitbegin;
}
else
{
onexitbegin = (_PVFV *) _decode_pointer (__onexitbegin);
onexitend = (_PVFV *) _decode_pointer (__onexitend);
}
retval = __dllonexit (func, &onexitbegin, &onexitend);
if (retval != NULL)
{
/* Update our globals in case of success */
__onexitbegin = (_PVFV *) _encode_pointer (onexitbegin);
__onexitend = (_PVFV *) _encode_pointer (onexitend);
}
_unlock (_EXIT_LOCK1);
return retval;
}

View file

@ -62,14 +62,8 @@ static int
__cdecl
pre_c_init (void)
{
_PVFV *onexitbegin;
__onexitend = __onexitbegin = NULL;
onexitbegin = (_PVFV *) malloc (32 * sizeof (_PVFV));
__onexitend = __onexitbegin = (_PVFV *) _encode_pointer (onexitbegin);
if (onexitbegin == NULL)
return 1;
*onexitbegin = (_PVFV) NULL;
return 0;
}
@ -136,14 +130,15 @@ WINBOOL WINAPI _CRT_INIT (HANDLE hDllHandle, DWORD dwReason, LPVOID lpreserved)
}
else
{
_PVFV * onexitbegin = (_PVFV *) _decode_pointer (__onexitbegin);
if (onexitbegin)
if (__onexitbegin)
{
_PVFV *onexitbegin = (_PVFV *) _decode_pointer (__onexitbegin);
_PVFV *onexitend = (_PVFV *) _decode_pointer (__onexitend);
while (--onexitend >= onexitbegin)
if (*onexitend != NULL)
(**onexitend) ();
free (onexitbegin);
if (!lpreserved)
free(onexitbegin);
__onexitbegin = __onexitend = (_PVFV *) NULL;
}
__native_startup_state = __uninitialized;

View file

@ -127,7 +127,7 @@ pre_c_init (void)
__set_app_type(_GUI_APP);
else
__set_app_type (_CONSOLE_APP);
__onexitbegin = __onexitend = (_PVFV *) _encode_pointer ((_PVFV *)(-1));
__onexitbegin = __onexitend = (_PVFV *)(-1);
* __MINGW_IMP_SYMBOL(_fmode) = _fmode;
* __MINGW_IMP_SYMBOL(_commode) = _commode;