Commit 685788f5 authored by Pierre Ynard's avatar Pierre Ynard
Browse files

WinCE: switch back vlc_thread_t to an allocated struct

WinCE needs the cancellation event handle along with the thread handle,
so we have to switch back to a struct on WinCE. Which causes great
ugliness. Fix the build with the recent changes, and simplify some
related Win32 code.
parent 9ee09351
......@@ -112,7 +112,15 @@ typedef pthread_key_t vlc_threadvar_t;
typedef struct vlc_timer *vlc_timer_t;
#elif defined( WIN32 )
#if !defined( UNDER_CE )
typedef HANDLE vlc_thread_t;
#else
typedef struct
{
HANDLE handle;
HANDLE cancel_event;
} *vlc_thread_t;
#endif
typedef struct
{
......
......@@ -148,7 +148,11 @@ int __vlc_thread_set_priority( vlc_object_t *p_this, const char * psz_file,
#elif defined( WIN32 ) || defined( UNDER_CE )
VLC_UNUSED( psz_file); VLC_UNUSED( i_line );
#ifndef UNDER_CE
if( !SetThreadPriority(p_priv->thread_id, i_priority) )
#else
if( !SetThreadPriority(p_priv->thread_id->handle, i_priority) )
#endif
{
msg_Warn( p_this, "couldn't set a faster priority" );
return 1;
......
......@@ -411,6 +411,9 @@ struct vlc_entry_data
{
void * (*func) (void *);
void * data;
#ifdef UNDER_CE
HANDLE cancel_event;
#endif
};
static unsigned __stdcall vlc_entry (void *p)
......@@ -422,7 +425,7 @@ static unsigned __stdcall vlc_entry (void *p)
free (p);
#ifdef UNDER_CE
cancel_data.cancel_event = data.handle->cancel_event;
cancel_data.cancel_event = data.cancel_event;
#endif
vlc_threadvar_set (cancel_key, &cancel_data);
......@@ -433,10 +436,7 @@ static unsigned __stdcall vlc_entry (void *p)
int vlc_clone (vlc_thread_t *p_handle, void * (*entry) (void *), void *data,
int priority)
{
/* When using the MSVCRT C library you have to use the _beginthreadex
* function instead of CreateThread, otherwise you'll end up with
* memory leaks and the signal functions not working (see Microsoft
* Knowledge Base, article 104641) */
int err = ENOMEM;
HANDLE hThread;
struct vlc_entry_data *entry_data = malloc (sizeof (*entry_data));
......@@ -445,51 +445,73 @@ int vlc_clone (vlc_thread_t *p_handle, void * (*entry) (void *), void *data,
entry_data->func = entry;
entry_data->data = data;
#if defined( UNDER_CE )
th->cancel_event = CreateEvent (NULL, FALSE, FALSE, NULL);
if (th->cancel_event == NULL)
{
free (entry_data);
return errno;
}
hThread = CreateThread (NULL, 128*1024, vlc_entry, entry_data, CREATE_SUSPENDED, NULL);
#else
#ifndef UNDER_CE
/* When using the MSVCRT C library you have to use the _beginthreadex
* function instead of CreateThread, otherwise you'll end up with
* memory leaks and the signal functions not working (see Microsoft
* Knowledge Base, article 104641) */
hThread = (HANDLE)(uintptr_t)
_beginthreadex (NULL, 0, vlc_entry, entry_data, CREATE_SUSPENDED, NULL);
#endif
if (! hThread)
{
err = errno;
goto error;
}
if (hThread)
/* Thread closes the handle when exiting, duplicate it here
* to be on the safe side when joining. */
if (!DuplicateHandle (GetCurrentProcess (), hThread,
GetCurrentProcess (), p_handle, 0, FALSE,
DUPLICATE_SAME_ACCESS))
{
#ifndef UNDER_CE
/* Thread closes the handle when exiting, duplicate it here
* to be on the safe side when joining. */
if (!DuplicateHandle (GetCurrentProcess (), hThread,
GetCurrentProcess (), p_handle, 0, FALSE,
DUPLICATE_SAME_ACCESS))
{
CloseHandle (hThread);
free (entry_data);
return ENOMEM;
}
CloseHandle (hThread);
goto error;
}
#else
th->handle = hThread;
#endif
vlc_thread_t th = malloc (sizeof (*th));
if (th == NULL)
goto error;
th->cancel_event = CreateEvent (NULL, FALSE, FALSE, NULL);
if (th->cancel_event == NULL)
{
free (th);
goto error;
}
entry_data->cancel_event = th->cancel_event;
ResumeThread (hThread);
if (priority)
SetThreadPriority (hThread, priority);
return 0;
/* Not sure if CREATE_SUSPENDED + ResumeThread() is any useful on WinCE.
* Thread handles act up, too. */
th->handle = CreateThread (NULL, 128*1024, vlc_entry, entry_data,
CREATE_SUSPENDED, NULL);
if (th->handle == NULL)
{
CloseHandle (th->cancel_event);
free (th);
goto error;
}
#ifdef UNDER_CE
CloseHandle (th->cancel_event);
*p_handle = th;
hThread = th->handle;
#endif
ResumeThread (hThread);
if (priority)
SetThreadPriority (hThread, priority);
return 0;
error:
free (entry_data);
return errno;
return err;
}
void vlc_join (vlc_thread_t handle, void **result)
{
#ifdef UNDER_CE
# define handle handle->handle
#endif
do
vlc_testcancel ();
while (WaitForSingleObjectEx (handle, INFINITE, TRUE)
......@@ -498,13 +520,21 @@ void vlc_join (vlc_thread_t handle, void **result)
CloseHandle (handle);
assert (result == NULL); /* <- FIXME if ever needed */
#ifdef UNDER_CE
# undef handle
CloseHandle (handle->cancel_event);
free (handle);
#endif
}
void vlc_detach (vlc_thread_t handle)
{
#ifndef UNDER_CE
CloseHandle (handle);
#else
/* FIXME: handle->cancel_event leak */
CloseHandle (handle->handle);
free (handle);
#endif
}
/*** Thread cancellation ***/
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment