mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2025-05-04 07:24:46 +00:00
task: add separate methods to add enter/leave callback
Remove the structure of callbacks and replace with separate methods to register each callback. This is much more binding friendly. Fixes https://bugzilla.gnome.org/show_bug.cgi?id=677898
This commit is contained in:
parent
76e8b2ecda
commit
b2aa56f4e3
4 changed files with 94 additions and 69 deletions
|
@ -54,6 +54,10 @@ gst_atomic_queue_peek
|
|||
gst_atomic_queue_pop
|
||||
|
||||
gst_atomic_queue_length
|
||||
|
||||
<SUBSECTION Standard>
|
||||
GST_TYPE_ATOMIC_QUEUE
|
||||
gst_atomic_queue_get_type
|
||||
</SECTION>
|
||||
|
||||
<SECTION>
|
||||
|
@ -582,6 +586,7 @@ gst_element_factory_get_klass
|
|||
gst_element_factory_get_longname
|
||||
gst_pad_get_caps_reffed
|
||||
gst_pad_peer_get_caps_reffed
|
||||
gst_pad_set_caps
|
||||
gst_buffer_new_and_alloc
|
||||
GST_BUFFER_TIMESTAMP
|
||||
GST_BUFFER_TIMESTAMP_IS_VALID
|
||||
|
@ -2672,8 +2677,9 @@ gst_task_set_lock
|
|||
gst_task_set_pool
|
||||
gst_task_get_pool
|
||||
|
||||
GstTaskThreadCallbacks
|
||||
gst_task_set_thread_callbacks
|
||||
GstTaskThreadFunc
|
||||
gst_task_set_enter_callback
|
||||
gst_task_set_leave_callback
|
||||
|
||||
gst_task_get_state
|
||||
gst_task_set_state
|
||||
|
|
|
@ -5070,11 +5070,6 @@ pad_leave_thread (GstTask * task, GThread * thread, gpointer user_data)
|
|||
thread, task);
|
||||
}
|
||||
|
||||
static GstTaskThreadCallbacks thr_callbacks = {
|
||||
pad_enter_thread,
|
||||
pad_leave_thread,
|
||||
};
|
||||
|
||||
/**
|
||||
* gst_pad_start_task:
|
||||
* @pad: the #GstPad to start the task of
|
||||
|
@ -5106,7 +5101,8 @@ gst_pad_start_task (GstPad * pad, GstTaskFunction func, gpointer user_data,
|
|||
if (task == NULL) {
|
||||
task = gst_task_new (func, user_data, notify);
|
||||
gst_task_set_lock (task, GST_PAD_GET_STREAM_LOCK (pad));
|
||||
gst_task_set_thread_callbacks (task, &thr_callbacks, pad, NULL);
|
||||
gst_task_set_enter_callback (task, pad_enter_thread, pad, NULL);
|
||||
gst_task_set_leave_callback (task, pad_leave_thread, pad, NULL);
|
||||
GST_INFO_OBJECT (pad, "created task %p", task);
|
||||
GST_PAD_TASK (pad) = task;
|
||||
gst_object_ref (task);
|
||||
|
|
114
gst/gsttask.c
114
gst/gsttask.c
|
@ -92,9 +92,13 @@ GST_DEBUG_CATEGORY_STATIC (task_debug);
|
|||
struct _GstTaskPrivate
|
||||
{
|
||||
/* callbacks for managing the thread of this task */
|
||||
GstTaskThreadCallbacks thr_callbacks;
|
||||
gpointer thr_user_data;
|
||||
GDestroyNotify thr_notify;
|
||||
GstTaskThreadFunc enter_func;
|
||||
gpointer enter_user_data;
|
||||
GDestroyNotify enter_notify;
|
||||
|
||||
GstTaskThreadFunc leave_func;
|
||||
gpointer leave_user_data;
|
||||
GDestroyNotify leave_notify;
|
||||
|
||||
/* configured pool */
|
||||
GstTaskPool *pool;
|
||||
|
@ -203,10 +207,11 @@ gst_task_finalize (GObject * object)
|
|||
|
||||
GST_DEBUG ("task %p finalize", task);
|
||||
|
||||
if (priv->thr_notify)
|
||||
priv->thr_notify (priv->thr_user_data);
|
||||
priv->thr_notify = NULL;
|
||||
priv->thr_user_data = NULL;
|
||||
if (priv->enter_notify)
|
||||
priv->enter_notify (priv->enter_user_data);
|
||||
|
||||
if (priv->leave_notify)
|
||||
priv->leave_notify (priv->leave_user_data);
|
||||
|
||||
if (task->notify)
|
||||
task->notify (task->user_data);
|
||||
|
@ -276,9 +281,9 @@ gst_task_func (GstTask * task)
|
|||
task->thread = tself;
|
||||
GST_OBJECT_UNLOCK (task);
|
||||
|
||||
/* fire the enter_thread callback when we need to */
|
||||
if (priv->thr_callbacks.enter_thread)
|
||||
priv->thr_callbacks.enter_thread (task, tself, priv->thr_user_data);
|
||||
/* fire the enter_func callback when we need to */
|
||||
if (priv->enter_func)
|
||||
priv->enter_func (task, tself, priv->enter_user_data);
|
||||
|
||||
/* locking order is TASK_LOCK, LOCK */
|
||||
g_rec_mutex_lock (lock);
|
||||
|
@ -317,11 +322,11 @@ done:
|
|||
task->thread = NULL;
|
||||
|
||||
exit:
|
||||
if (priv->thr_callbacks.leave_thread) {
|
||||
/* fire the leave_thread callback when we need to. We need to do this before
|
||||
if (priv->leave_func) {
|
||||
/* fire the leave_func callback when we need to. We need to do this before
|
||||
* we signal the task and with the task lock released. */
|
||||
GST_OBJECT_UNLOCK (task);
|
||||
priv->thr_callbacks.leave_thread (task, tself, priv->thr_user_data);
|
||||
priv->leave_func (task, tself, priv->leave_user_data);
|
||||
GST_OBJECT_LOCK (task);
|
||||
}
|
||||
/* now we allow messing with the lock again by setting the running flag to
|
||||
|
@ -503,56 +508,79 @@ gst_task_set_pool (GstTask * task, GstTaskPool * pool)
|
|||
gst_object_unref (old);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* gst_task_set_thread_callbacks:
|
||||
* gst_task_set_enter_callback:
|
||||
* @task: The #GstTask to use
|
||||
* @callbacks: (in): a #GstTaskThreadCallbacks pointer
|
||||
* @user_data: (closure): user data passed to the callbacks
|
||||
* @enter_func: (in): a #GstTaskThreadFunc
|
||||
* @user_data: user data passed to @enter_func
|
||||
* @notify: called when @user_data is no longer referenced
|
||||
*
|
||||
* Set callbacks which will be executed when a new thread is needed, the thread
|
||||
* function is entered and left and when the thread is joined.
|
||||
*
|
||||
* By default a thread for @task will be created from a default thread pool.
|
||||
*
|
||||
* Objects can use custom GThreads or can perform additional configuration of
|
||||
* the threads (such as changing the thread priority) by installing callbacks.
|
||||
*
|
||||
* MT safe.
|
||||
*
|
||||
* Since: 0.10.24
|
||||
* Call @enter_func when the task function of @task is entered. @user_data will
|
||||
* be passed to @enter_func and @notify will be called when @user_data is no
|
||||
* longer referenced.
|
||||
*/
|
||||
void
|
||||
gst_task_set_thread_callbacks (GstTask * task,
|
||||
GstTaskThreadCallbacks * callbacks, gpointer user_data,
|
||||
GDestroyNotify notify)
|
||||
gst_task_set_enter_callback (GstTask * task, GstTaskThreadFunc enter_func,
|
||||
gpointer user_data, GDestroyNotify notify)
|
||||
{
|
||||
GDestroyNotify old_notify;
|
||||
|
||||
g_return_if_fail (task != NULL);
|
||||
g_return_if_fail (GST_IS_TASK (task));
|
||||
g_return_if_fail (callbacks != NULL);
|
||||
|
||||
GST_OBJECT_LOCK (task);
|
||||
old_notify = task->priv->thr_notify;
|
||||
if ((old_notify = task->priv->enter_notify)) {
|
||||
gpointer old_data = task->priv->enter_user_data;
|
||||
|
||||
if (old_notify) {
|
||||
gpointer old_data;
|
||||
|
||||
old_data = task->priv->thr_user_data;
|
||||
|
||||
task->priv->thr_user_data = NULL;
|
||||
task->priv->thr_notify = NULL;
|
||||
task->priv->enter_user_data = NULL;
|
||||
task->priv->enter_notify = NULL;
|
||||
GST_OBJECT_UNLOCK (task);
|
||||
|
||||
old_notify (old_data);
|
||||
|
||||
GST_OBJECT_LOCK (task);
|
||||
}
|
||||
task->priv->thr_callbacks = *callbacks;
|
||||
task->priv->thr_user_data = user_data;
|
||||
task->priv->thr_notify = notify;
|
||||
task->priv->enter_func = enter_func;
|
||||
task->priv->enter_user_data = user_data;
|
||||
task->priv->enter_notify = notify;
|
||||
GST_OBJECT_UNLOCK (task);
|
||||
}
|
||||
|
||||
/**
|
||||
* gst_task_set_leave_callback:
|
||||
* @task: The #GstTask to use
|
||||
* @leave_func: (in): a #GstTaskThreadFunc
|
||||
* @user_data: user data passed to @leave_func
|
||||
* @notify: called when @user_data is no longer referenced
|
||||
*
|
||||
* Call @leave_func when the task function of @task is left. @user_data will
|
||||
* be passed to @leave_func and @notify will be called when @user_data is no
|
||||
* longer referenced.
|
||||
*/
|
||||
void
|
||||
gst_task_set_leave_callback (GstTask * task, GstTaskThreadFunc leave_func,
|
||||
gpointer user_data, GDestroyNotify notify)
|
||||
{
|
||||
GDestroyNotify old_notify;
|
||||
|
||||
g_return_if_fail (task != NULL);
|
||||
g_return_if_fail (GST_IS_TASK (task));
|
||||
|
||||
GST_OBJECT_LOCK (task);
|
||||
if ((old_notify = task->priv->leave_notify)) {
|
||||
gpointer old_data = task->priv->leave_user_data;
|
||||
|
||||
task->priv->leave_user_data = NULL;
|
||||
task->priv->leave_notify = NULL;
|
||||
GST_OBJECT_UNLOCK (task);
|
||||
|
||||
old_notify (old_data);
|
||||
|
||||
GST_OBJECT_LOCK (task);
|
||||
}
|
||||
task->priv->leave_func = leave_func;
|
||||
task->priv->leave_user_data = user_data;
|
||||
task->priv->leave_notify = notify;
|
||||
GST_OBJECT_UNLOCK (task);
|
||||
}
|
||||
|
||||
|
|
|
@ -110,23 +110,14 @@ typedef enum {
|
|||
#define GST_TASK_GET_LOCK(task) (GST_TASK_CAST(task)->lock)
|
||||
|
||||
/**
|
||||
* GstTaskThreadCallbacks:
|
||||
* @enter_thread: a thread is entered, this callback is called when the new
|
||||
* thread enters its function.
|
||||
* @leave_thread: a thread is exiting, this is called when the thread is about
|
||||
* to leave its function
|
||||
* GstTaskThreadFunc:
|
||||
* @task: The #GstTask
|
||||
* @thread: The #GThread
|
||||
* @user_data: user data
|
||||
*
|
||||
* Custom GstTask thread callback functions that can be installed.
|
||||
*
|
||||
* Since: 0.10.24
|
||||
*/
|
||||
typedef struct {
|
||||
/* manage the lifetime of the thread */
|
||||
void (*enter_thread) (GstTask *task, GThread *thread, gpointer user_data);
|
||||
void (*leave_thread) (GstTask *task, GThread *thread, gpointer user_data);
|
||||
/*< private >*/
|
||||
gpointer _gst_reserved[GST_PADDING];
|
||||
} GstTaskThreadCallbacks;
|
||||
typedef void (*GstTaskThreadFunc) (GstTask *task, GThread *thread, gpointer user_data);
|
||||
|
||||
/**
|
||||
* GstTask:
|
||||
|
@ -185,10 +176,14 @@ void gst_task_set_lock (GstTask *task, GRecMutex *mutex);
|
|||
GstTaskPool * gst_task_get_pool (GstTask *task);
|
||||
void gst_task_set_pool (GstTask *task, GstTaskPool *pool);
|
||||
|
||||
void gst_task_set_thread_callbacks (GstTask *task,
|
||||
GstTaskThreadCallbacks *callbacks,
|
||||
gpointer user_data,
|
||||
GDestroyNotify notify);
|
||||
void gst_task_set_enter_callback (GstTask *task,
|
||||
GstTaskThreadFunc enter_func,
|
||||
gpointer user_data,
|
||||
GDestroyNotify notify);
|
||||
void gst_task_set_leave_callback (GstTask *task,
|
||||
GstTaskThreadFunc leave_func,
|
||||
gpointer user_data,
|
||||
GDestroyNotify notify);
|
||||
|
||||
GstTaskState gst_task_get_state (GstTask *task);
|
||||
gboolean gst_task_set_state (GstTask *task, GstTaskState state);
|
||||
|
|
Loading…
Reference in a new issue