Commit c97e1959 authored by Rémi Denis-Courmont's avatar Rémi Denis-Courmont

Win32: implement cancellation of detached threads

parent 4e647951
...@@ -516,7 +516,13 @@ void *vlc_threadvar_get (vlc_threadvar_t key) ...@@ -516,7 +516,13 @@ void *vlc_threadvar_get (vlc_threadvar_t key)
return TlsGetValue (key->id); return TlsGetValue (key->id);
} }
static void vlc_threadvar_cleanup (void) /*** Threads ***/
void vlc_threads_setup (libvlc_int_t *p_libvlc)
{
(void) p_libvlc;
}
static void vlc_thread_cleanup (vlc_thread_t *th)
{ {
vlc_threadvar_t key; vlc_threadvar_t key;
...@@ -535,13 +541,15 @@ retry: ...@@ -535,13 +541,15 @@ retry:
} }
} }
vlc_mutex_unlock (&super_mutex); vlc_mutex_unlock (&super_mutex);
}
if (th->detached)
/*** Threads ***/ {
void vlc_threads_setup (libvlc_int_t *p_libvlc) CloseHandle (th->id);
{ #ifdef UNDER_CE
(void) p_libvlc; CloseHandle (th->cancel_event);
#endif
free (th);
}
} }
static unsigned __stdcall vlc_entry (void *p) static unsigned __stdcall vlc_entry (void *p)
...@@ -551,9 +559,7 @@ static unsigned __stdcall vlc_entry (void *p) ...@@ -551,9 +559,7 @@ static unsigned __stdcall vlc_entry (void *p)
vlc_threadvar_set (thread_key, th); vlc_threadvar_set (thread_key, th);
th->killable = true; th->killable = true;
th->data = th->entry (th->data); th->data = th->entry (th->data);
vlc_threadvar_cleanup (); vlc_thread_exit (th);
if (th->detached)
free (th);
return 0; return 0;
} }
...@@ -586,7 +592,6 @@ int vlc_clone (vlc_thread_t *p_handle, void * (*entry) (void *), void *data, ...@@ -586,7 +592,6 @@ int vlc_clone (vlc_thread_t *p_handle, void * (*entry) (void *), void *data,
} }
#else #else
/* FIXME: cancel_event is useless and leaked in detached threads */
th->cancel_event = CreateEvent (NULL, FALSE, FALSE, NULL); th->cancel_event = CreateEvent (NULL, FALSE, FALSE, NULL);
if (th->cancel_event == NULL) if (th->cancel_event == NULL)
{ {
...@@ -606,17 +611,15 @@ int vlc_clone (vlc_thread_t *p_handle, void * (*entry) (void *), void *data, ...@@ -606,17 +611,15 @@ int vlc_clone (vlc_thread_t *p_handle, void * (*entry) (void *), void *data,
} }
#endif #endif
/* Thread is suspended, so we can safely set th->id */
th->id = hThread; th->id = hThread;
if (p_handle != NULL)
*p_handle = th;
ResumeThread (hThread); ResumeThread (hThread);
if (priority) if (priority)
SetThreadPriority (hThread, priority); SetThreadPriority (hThread, priority);
if (p_handle != NULL)
*p_handle = th;
else
CloseHandle (hThread);
return 0; return 0;
} }
...@@ -627,12 +630,12 @@ void vlc_join (vlc_thread_t th, void **result) ...@@ -627,12 +630,12 @@ void vlc_join (vlc_thread_t th, void **result)
while (WaitForSingleObjectEx (th->id, INFINITE, TRUE) while (WaitForSingleObjectEx (th->id, INFINITE, TRUE)
== WAIT_IO_COMPLETION); == WAIT_IO_COMPLETION);
if (result != NULL)
*result = th->data;
CloseHandle (th->id); CloseHandle (th->id);
#ifdef UNDER_CE #ifdef UNDER_CE
CloseHandle (th->cancel_event); CloseHandle (th->cancel_event);
#endif #endif
if (result != NULL)
*result = th->data;
free (th); free (th);
} }
...@@ -692,14 +695,11 @@ void vlc_testcancel (void) ...@@ -692,14 +695,11 @@ void vlc_testcancel (void)
if (th->killable && th->killed) if (th->killable && th->killed)
{ {
/* Detached threads cannot be cancelled */
assert (!th->detached);
th->data = NULL; /* TODO: special value? */
for (vlc_cleanup_t *p = th->cleaners; p != NULL; p = p->next) for (vlc_cleanup_t *p = th->cleaners; p != NULL; p = p->next)
p->proc (p->data); p->proc (p->data);
vlc_threadvar_cleanup ();
th->data = NULL; /* TODO: special value? */
vlc_thread_cleanup (th);
#ifndef UNDER_CE #ifndef UNDER_CE
_endthreadex(0); _endthreadex(0);
#else #else
......
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