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

interrupt: add replacement for vlc_object_alive()

There are still many cases where waking up the thread sleeping is only
half of the problem and waking it up half of the solution. For instance,
the net_* and stream_* I/O functions have no ways to return a non-fatal
error.
parent d6a7bc11
...@@ -142,5 +142,16 @@ VLC_API vlc_interrupt_t *vlc_interrupt_set(vlc_interrupt_t *); ...@@ -142,5 +142,16 @@ VLC_API vlc_interrupt_t *vlc_interrupt_set(vlc_interrupt_t *);
*/ */
VLC_API void vlc_interrupt_raise(vlc_interrupt_t *); VLC_API void vlc_interrupt_raise(vlc_interrupt_t *);
/**
* Marks the interruption context as "killed". This is not reversible.
*/
VLC_API void vlc_interrupt_kill(vlc_interrupt_t *);
/**
* Indicates whether the interruption context of the calling thread (if any)
* was killed with vlc_interrupt_kill().
*/
VLC_API bool vlc_killed(void) VLC_USED;
/** @} @} */ /** @} @} */
#endif #endif
...@@ -236,9 +236,7 @@ void input_Stop( input_thread_t *p_input ) ...@@ -236,9 +236,7 @@ void input_Stop( input_thread_t *p_input )
sys->is_stopped = true; sys->is_stopped = true;
vlc_cond_signal( &sys->wait_control ); vlc_cond_signal( &sys->wait_control );
vlc_mutex_unlock( &sys->lock_control ); vlc_mutex_unlock( &sys->lock_control );
/* Interrupt access/stream/demux/etc *after* the input is stopped. vlc_interrupt_kill( &sys->interrupt );
* Otherwise the interruption could be mistreated as a spurious wake-up. */
vlc_interrupt_raise( &sys->interrupt );
} }
/** /**
......
...@@ -554,6 +554,8 @@ vlc_interrupt_create ...@@ -554,6 +554,8 @@ vlc_interrupt_create
vlc_interrupt_destroy vlc_interrupt_destroy
vlc_interrupt_set vlc_interrupt_set
vlc_interrupt_raise vlc_interrupt_raise
vlc_interrupt_kill
vlc_killed
vlc_join vlc_join
vlc_list_children vlc_list_children
vlc_list_release vlc_list_release
......
...@@ -74,6 +74,7 @@ void vlc_interrupt_init(vlc_interrupt_t *ctx) ...@@ -74,6 +74,7 @@ void vlc_interrupt_init(vlc_interrupt_t *ctx)
vlc_mutex_init(&ctx->lock); vlc_mutex_init(&ctx->lock);
ctx->interrupted = false; ctx->interrupted = false;
atomic_init(&ctx->killed, false);
#ifndef NDEBUG #ifndef NDEBUG
ctx->attached = false; ctx->attached = false;
#endif #endif
...@@ -217,6 +218,21 @@ static void vlc_interrupt_cleanup(void *opaque) ...@@ -217,6 +218,21 @@ static void vlc_interrupt_cleanup(void *opaque)
vlc_interrupt_finish(opaque); vlc_interrupt_finish(opaque);
} }
void vlc_interrupt_kill(vlc_interrupt_t *ctx)
{
assert(ctx != NULL);
atomic_store(&ctx->killed, true);
vlc_interrupt_raise(ctx);
}
bool vlc_killed(void)
{
vlc_interrupt_t *ctx = vlc_threadvar_get(vlc_interrupt_var);
return (ctx != NULL) && atomic_load(&ctx->killed);
}
static void vlc_interrupt_sem(void *opaque) static void vlc_interrupt_sem(void *opaque)
{ {
vlc_sem_post(opaque); vlc_sem_post(opaque);
......
...@@ -23,6 +23,7 @@ ...@@ -23,6 +23,7 @@
# define LIBVLC_INPUT_SIGNAL_H 1 # define LIBVLC_INPUT_SIGNAL_H 1
# include <vlc_interrupt.h> # include <vlc_interrupt.h>
# include <vlc_atomic.h>
void vlc_interrupt_init(vlc_interrupt_t *); void vlc_interrupt_init(vlc_interrupt_t *);
void vlc_interrupt_deinit(vlc_interrupt_t *); void vlc_interrupt_deinit(vlc_interrupt_t *);
...@@ -34,6 +35,7 @@ struct vlc_interrupt ...@@ -34,6 +35,7 @@ struct vlc_interrupt
#ifndef NDEBUG #ifndef NDEBUG
bool attached; bool attached;
#endif #endif
atomic_bool killed;
void (*callback)(void *); void (*callback)(void *);
void *data; void *data;
}; };
......
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