From: Thomas Bluemel Date: Fri, 13 Jan 2006 17:54:37 +0000 (+0000) Subject: revert my last change X-Git-Tag: backups/expat-rbuild@40467~333 X-Git-Url: https://git.reactos.org/?p=reactos.git;a=commitdiff_plain;h=55ae827634d27a63acc3b82f5c681eddb1de5657 revert my last change svn path=/trunk/; revision=20835 --- diff --git a/reactos/lib/crt/crt.xml b/reactos/lib/crt/crt.xml index 1a2f64f21f6..2db3f46fe95 100644 --- a/reactos/lib/crt/crt.xml +++ b/reactos/lib/crt/crt.xml @@ -385,6 +385,7 @@ cppexcept.c heap.c scanf.c + thread.c undname.c diff --git a/reactos/lib/crt/include/internal/tls.h b/reactos/lib/crt/include/internal/tls.h index 79ad295618e..4adcc83f236 100644 --- a/reactos/lib/crt/include/internal/tls.h +++ b/reactos/lib/crt/include/internal/tls.h @@ -17,10 +17,6 @@ typedef struct _ThreadData { - HANDLE hThread; /* handle to the current thread */ - void (__cdecl *start_address)(void*); /* the start address supplied by _beginthread() */ - void* arglist; /* the argument list supplied by _beginthread() */ - int terrno; /* *nix error code */ unsigned long tdoserrno; /* Win32 error code (for I/O only) */ unsigned __int64 tnext; /* used by rand/srand */ @@ -45,8 +41,7 @@ typedef struct _ThreadData int CreateThreadData(void); void DestroyThreadData(void); -int SetThreadData(PTHREADDATA ThreadData); -void FreeThreadData(PTHREADDATA ThreadData); +void FreeThreadData(PTHREADDATA ptd); PTHREADDATA GetThreadData(void); #endif /* __MSVCRT_INTERNAL_TLS_H */ diff --git a/reactos/lib/crt/misc/tls.c b/reactos/lib/crt/misc/tls.c index 41414f3c585..9fa6d036ac0 100644 --- a/reactos/lib/crt/misc/tls.c +++ b/reactos/lib/crt/misc/tls.c @@ -4,7 +4,7 @@ #include -static DWORD TlsIndex = TLS_OUT_OF_INDEXES; +static unsigned long TlsIndex = (unsigned long)-1; static void InitThreadData(PTHREADDATA ThreadData) @@ -19,38 +19,40 @@ static void InitThreadData(PTHREADDATA ThreadData) } -int SetThreadData(PTHREADDATA ThreadData) +int CreateThreadData(void) { - if(TlsIndex == TLS_OUT_OF_INDEXES || - !TlsSetValue(TlsIndex, ThreadData)) + PTHREADDATA ThreadData; + + TlsIndex = TlsAlloc(); + if (TlsIndex == (unsigned long)-1) return FALSE; - InitThreadData(ThreadData); + ThreadData = (PTHREADDATA)calloc(1, sizeof(THREADDATA)); + if (ThreadData == NULL) + return FALSE; - return TRUE; -} + if(!TlsSetValue(TlsIndex, (LPVOID)ThreadData)) + return FALSE; + InitThreadData(ThreadData); -int CreateThreadData(void) -{ - TlsIndex = TlsAlloc(); - return (TlsIndex != TLS_OUT_OF_INDEXES); + return TRUE; } void DestroyThreadData(void) { - if (TlsIndex != TLS_OUT_OF_INDEXES) + if (TlsIndex != (unsigned long)-1) { TlsFree(TlsIndex); - TlsIndex = TLS_OUT_OF_INDEXES; + TlsIndex = (unsigned long)-1; } } void FreeThreadData(PTHREADDATA ThreadData) { - if (TlsIndex != TLS_OUT_OF_INDEXES) + if (TlsIndex != (unsigned long)-1) { if (ThreadData == NULL) ThreadData = TlsGetValue(TlsIndex); @@ -82,8 +84,6 @@ PTHREADDATA GetThreadData(void) TlsSetValue(TlsIndex, (LPVOID)ThreadData); InitThreadData(ThreadData); - - ThreadData->hThread = GetCurrentThread(); } else { diff --git a/reactos/lib/crt/process/thread.c b/reactos/lib/crt/process/thread.c index 2b86729ae70..d058d7252e2 100644 --- a/reactos/lib/crt/process/thread.c +++ b/reactos/lib/crt/process/thread.c @@ -1,102 +1,23 @@ #include -void _endthread(void); - -static DWORD WINAPI -_beginthread_start(PVOID lpParameter) -{ - PTHREADDATA ThreadData = (PTHREADDATA)lpParameter; - - if (SetThreadData(ThreadData)) - { - /* FIXME - wrap start_address in SEH! */ - ThreadData->start_address(ThreadData->arglist); - - _endthread(); - } - else - { - /* couldn't set the thread data, free it before terminating */ - free(ThreadData); - } - - ExitThread(0); -} - - +#if 0 /* - * @implemented - * - * FIXME: the return type should be uintptr_t + * @unimplemented */ unsigned long _beginthread( void (__cdecl *start_address)(void*), unsigned stack_size, void* arglist) { - HANDLE hThread; - PTHREADDATA ThreadData; - - if (start_address == NULL) { - __set_errno(EINVAL); - return (unsigned long)-1; - } - - /* allocate the thread data structure already here instead of allocating the - thread data structure in the thread itself. this way we can pass an error - code to the caller in case we don't have sufficient resources */ - ThreadData = malloc(sizeof(THREADDATA)); - if (ThreadData == NULL) - { - __set_errno(EAGAIN); - return (unsigned long)-1; - } - - ThreadData->start_address = start_address; - ThreadData->arglist = arglist; - - hThread = CreateThread(NULL, - stack_size, - _beginthread_start, - ThreadData, - CREATE_SUSPENDED, - NULL); - if (hThread == NULL) - { - free(ThreadData); - __set_errno(EAGAIN); - return (unsigned long)-1; - } - - ThreadData->hThread = hThread; - - if (ResumeThread(hThread) == (DWORD)-1) - { - CloseHandle(hThread); - - /* freeing the ThreadData _could_ cause a crash, but only in case someone - else resumed the thread and it got to free the context before we actually - get here, but that's _very_ unlikely! */ - free(ThreadData); - __set_errno(EAGAIN); - return (unsigned long)-1; - } - - return (unsigned long)hThread; + __set_errno ( ENOSYS ); + return (unsigned long)-1; } - +#endif /* - * @implemented + * @unimplemented */ void _endthread(void) { - PTHREADDATA ThreadData = GetThreadData(); - - /* close the thread handle */ - CloseHandle(ThreadData->hThread); - - /* NOTE: the thread data will be freed in the thread detach routine that will - call FreeThreadData */ - - ExitThread(0); } + +/* EOF */ diff --git a/reactos/lib/crt/wine/thread.c b/reactos/lib/crt/wine/thread.c new file mode 100644 index 00000000000..d1574d69faa --- /dev/null +++ b/reactos/lib/crt/wine/thread.c @@ -0,0 +1,108 @@ +/* + * msvcrt.dll thread functions + * + * Copyright 2000 Jon Griffiths + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#include +#include + +#include +#include + +#include "wine/debug.h" + +WINE_DEFAULT_DEBUG_CHANNEL(msvcrt); + +void _amsg_exit (int errnum); +/* Index to TLS */ +DWORD MSVCRT_tls_index; + +typedef void (*_beginthread_start_routine_t)(void *); +typedef unsigned int (__stdcall *_beginthreadex_start_routine_t)(void *); + +/********************************************************************/ + +typedef struct { + _beginthread_start_routine_t start_address; + void *arglist; +} _beginthread_trampoline_t; + +/********************************************************************* + * msvcrt_get_thread_data + * + * Return the thread local storage structure. + */ +MSVCRT_thread_data *msvcrt_get_thread_data(void) +{ + MSVCRT_thread_data *ptr; + DWORD err = GetLastError(); /* need to preserve last error */ + + if (!(ptr = TlsGetValue( MSVCRT_tls_index ))) + { + if (!(ptr = HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*ptr) ))) + _amsg_exit( _RT_THREAD ); + if (!TlsSetValue( MSVCRT_tls_index, ptr )) + _amsg_exit( _RT_THREAD ); + if (!TlsSetValue( MSVCRT_tls_index, ptr )) + _amsg_exit( _RT_THREAD ); + } + SetLastError( err ); + return ptr; +} + +/********************************************************************* + * _beginthread_trampoline + */ +static DWORD CALLBACK _beginthread_trampoline(LPVOID arg) +{ + _beginthread_trampoline_t local_trampoline; + + /* Maybe it's just being paranoid, but freeing arg right + * away seems safer. + */ + memcpy(&local_trampoline,arg,sizeof(local_trampoline)); + free(arg); + + local_trampoline.start_address(local_trampoline.arglist); + return 0; +} + +/********************************************************************* + * _beginthread (MSVCRT.@) + */ +unsigned long _beginthread( + _beginthread_start_routine_t start_address, /* [in] Start address of routine that begins execution of new thread */ + unsigned int stack_size, /* [in] Stack size for new thread or 0 */ + void *arglist) /* [in] Argument list to be passed to new thread or NULL */ +{ + _beginthread_trampoline_t* trampoline; + + TRACE("(%p, %d, %p)\n", start_address, stack_size, arglist); + + /* Allocate the trampoline here so that it is still valid when the thread + * starts... typically after this function has returned. + * _beginthread_trampoline is responsible for freeing the trampoline + */ + trampoline=malloc(sizeof(*trampoline)); + trampoline->start_address = start_address; + trampoline->arglist = arglist; + + /* FIXME */ + return (unsigned long)CreateThread(NULL, stack_size, _beginthread_trampoline, + trampoline, 0, NULL); +}