[vlc-commits] [Git][videolan/vlc][master] 10 commits: es_out: remove always true argument

Thomas Guillem (@tguillem) gitlab at videolan.org
Fri Dec 5 12:23:17 UTC 2025



Thomas Guillem pushed to branch master at VideoLAN / VLC


Commits:
216810b4 by Thomas Guillem at 2025-12-05T11:32:35+00:00
es_out: remove always true argument

- - - - -
e4b1d76b by Thomas Guillem at 2025-12-05T11:32:35+00:00
aout: assert Play() is not called paused

- - - - -
a5b719e7 by Thomas Guillem at 2025-12-05T11:32:35+00:00
player: add on_paused event for timer_smpte

- - - - -
608a4cd8 by Thomas Guillem at 2025-12-05T11:32:35+00:00
decoder: add on_output_paused event

- - - - -
93067215 by Thomas Guillem at 2025-12-05T11:32:35+00:00
input: add INPUT_EVENT_OUTPUT_STATE event

To notify that an output is paused from the decoder.

- - - - -
b9158c84 by Thomas Guillem at 2025-12-05T11:32:35+00:00
es_out: implement on_output_paused

- - - - -
d4b3e9f7 by Thomas Guillem at 2025-12-05T11:32:35+00:00
player: handle pause events from outputs

And remove the hack that forced the es_source when paused.

Each timers will now receive the pause event from its es_source.

- - - - -
3eceb8cc by Thomas Guillem at 2025-12-05T11:32:35+00:00
test: player: timers: add wait helpers

Current timer tests are fetching reports when the player is stopped and
does not require any lock or wait mechanism. Add lock/cond and helpers
in order to allow fetching timer reports when the player is running.

- - - - -
d0036e76 by Thomas Guillem at 2025-12-05T11:32:35+00:00
test: player: timers: add smpte.on_paused

- - - - -
df5039d9 by Thomas Guillem at 2025-12-05T11:32:35+00:00
test: player: pause: ensure outputs are paused via timers

And that no frame is rendered once we receive the PAUSED event.

- - - - -


12 changed files:

- include/vlc_player.h
- src/audio_output/dec.c
- src/input/decoder.c
- src/input/decoder.h
- src/input/es_out.c
- src/input/event.h
- src/input/input_internal.h
- src/player/input.c
- src/player/timer.c
- test/src/player/pause.c
- test/src/player/timers.c
- test/src/player/timers.h


Changes:

=====================================
include/vlc_player.h
=====================================
@@ -3488,6 +3488,13 @@ struct vlc_player_timer_smpte_cbs
      */
     void (*on_update)(const struct vlc_player_timer_smpte_timecode *tc,
                       void *data);
+
+    /**
+     * The player timer is paused (can be NULL).
+     *
+     * @see vlc_player_timer_cbs.on_paused
+     */
+    void (*on_paused)(vlc_tick_t system_date, void *data);
 };
 
 /**


=====================================
src/audio_output/dec.c
=====================================
@@ -873,6 +873,7 @@ int vlc_aout_stream_Play(vlc_aout_stream *stream, block_t *block)
     audio_output_t *aout = aout_stream_aout(stream);
 
     assert (block->i_pts != VLC_TICK_INVALID);
+    assert (stream->timing.pause_date == VLC_TICK_INVALID);
 
     block->i_length = vlc_tick_from_samples( block->i_nb_samples,
                                    stream->input_format.i_rate );


=====================================
src/input/decoder.c
=====================================
@@ -1829,6 +1829,8 @@ static void *DecoderThread( void *p_data )
         if( p_owner->paused != p_owner->output_paused )
         {   /* Update playing/paused status of the output */
             Decoder_ChangeOutputPause( p_owner, p_owner->paused, p_owner->pause_date );
+            decoder_Notify(p_owner, on_output_paused, p_owner->paused,
+                           p_owner->pause_date);
             continue;
         }
 


=====================================
src/input/decoder.h
=====================================
@@ -40,6 +40,10 @@ struct vlc_input_decoder_callbacks {
                             void *userdata);
     void (*on_vout_stopped)(vlc_input_decoder_t *decoder, vout_thread_t *vout,
                             void *userdata);
+    void (*on_output_paused)(vlc_input_decoder_t *decoder, bool paused,
+                             vlc_tick_t pause_date,
+                             void *userdata);
+
     void (*on_thumbnail_ready)(vlc_input_decoder_t *decoder, picture_t *pic,
                                void *userdata);
 


=====================================
src/input/es_out.c
=====================================
@@ -259,7 +259,7 @@ static void EsOutDeleteInfoEs(es_out_sys_t *, es_out_id_t *es);
 static void EsOutUnselectEs(es_out_sys_t *out, es_out_id_t *es, bool b_update);
 static void EsOutDecoderChangeDelay(es_out_sys_t *out, es_out_id_t *p_es);
 static void EsOutDecodersChangePause(es_out_sys_t *out, bool b_paused, vlc_tick_t i_date);
-static void EsOutChangePosition(es_out_sys_t *out, bool b_flush, es_out_id_t *p_next_frame_es);
+static void EsOutChangePosition(es_out_sys_t *out, es_out_id_t *p_next_frame_es);
 static void EsOutProgramChangePause(es_out_sys_t *out, bool b_paused, vlc_tick_t i_date);
 static void EsOutProgramsChangeRate(es_out_sys_t *out);
 static void EsOutDecodersStopBuffering(es_out_sys_t *out, bool b_forced);
@@ -411,6 +411,25 @@ decoder_on_vout_stopped(vlc_input_decoder_t *decoder, vout_thread_t *vout, void
     input_SendEventVout(p_sys->p_input, &event);
 }
 
+static void
+decoder_on_output_paused(vlc_input_decoder_t *decoder, bool paused,
+                         vlc_tick_t paused_date, void *userdata)
+{
+    (void) decoder;
+    es_out_id_t *id = userdata;
+    struct vlc_input_es_out *out = id->out;
+    es_out_sys_t *p_sys = PRIV(&out->out);
+
+    struct vlc_input_event_output_state event = {
+        .action = paused ? VLC_INPUT_EVENT_OUTPUT_STATE_PAUSED
+                         : VLC_INPUT_EVENT_OUTPUT_STATE_RESUMED,
+        .paused_date = paused_date,
+        .id = &id->id,
+    };
+
+    input_SendEventOutputState(p_sys->p_input, &event);
+}
+
 static void
 decoder_on_thumbnail_ready(vlc_input_decoder_t *decoder, picture_t *pic, void *userdata)
 {
@@ -503,6 +522,7 @@ decoder_get_attachments(vlc_input_decoder_t *decoder,
 static const struct vlc_input_decoder_callbacks decoder_cbs = {
     .on_vout_started = decoder_on_vout_started,
     .on_vout_stopped = decoder_on_vout_stopped,
+    .on_output_paused = decoder_on_output_paused,
     .on_thumbnail_ready = decoder_on_thumbnail_ready,
     .on_new_video_stats = decoder_on_new_video_stats,
     .on_new_audio_stats = decoder_on_new_audio_stats,
@@ -883,7 +903,7 @@ static void EsOutStopNextFrame(es_out_sys_t *p_sys)
 {
     assert( p_sys->p_next_frame_es != NULL );
     /* Flush every ES except the video one */
-    EsOutChangePosition(p_sys, true, p_sys->p_next_frame_es );
+    EsOutChangePosition(p_sys, p_sys->p_next_frame_es );
     p_sys->p_next_frame_es = NULL;
 }
 
@@ -941,7 +961,7 @@ static void EsOutChangeRate(es_out_sys_t *p_sys, float rate)
             vlc_input_decoder_ChangeRate( es->p_dec, rate );
 }
 
-static void EsOutChangePosition(es_out_sys_t *p_sys, bool b_flush,
+static void EsOutChangePosition(es_out_sys_t *p_sys,
                                 es_out_id_t *p_next_frame_es)
 {
     es_out_id_t *p_es;
@@ -952,7 +972,7 @@ static void EsOutChangePosition(es_out_sys_t *p_sys, bool b_flush,
     {
         if( p_es->p_dec != NULL )
         {
-            if( b_flush && p_es != p_next_frame_es )
+            if( p_es != p_next_frame_es )
                 vlc_input_decoder_Flush( p_es->p_dec );
             if( !p_sys->b_buffering )
             {
@@ -1021,7 +1041,7 @@ static void EsOutDecodersStopBuffering(es_out_sys_t *p_sys, bool b_forced)
      * increase the buffering duration. */
     if (i_stream_duration < 0)
     {
-        EsOutChangePosition(p_sys, true, NULL);
+        EsOutChangePosition(p_sys, NULL);
         return;
     }
 
@@ -3520,7 +3540,7 @@ static int EsOutVaControlLocked(es_out_sys_t *p_sys, input_source_t *source,
 
     case ES_OUT_RESET_PCR:
         msg_Dbg( p_sys->p_input, "ES_OUT_RESET_PCR called" );
-        EsOutChangePosition(p_sys, true, NULL);
+        EsOutChangePosition(p_sys, NULL);
         return VLC_SUCCESS;
 
     case ES_OUT_SET_GROUP:


=====================================
src/input/event.h
=====================================
@@ -293,6 +293,15 @@ static inline void input_SendEventVout(input_thread_t *p_input,
     });
 }
 
+static inline void input_SendEventOutputState(input_thread_t *p_input,
+                                              const struct vlc_input_event_output_state *state)
+{
+    input_SendEvent(p_input, &(struct vlc_input_event) {
+        .type = INPUT_EVENT_OUTPUT_STATE,
+        .output_state = *state,
+    });
+}
+
 /*****************************************************************************
  * Event for control.c/input.c
  *****************************************************************************/


=====================================
src/input/input_internal.h
=====================================
@@ -134,6 +134,9 @@ typedef enum input_event_type_e
     /* A vout_thread_t object has been created/deleted by *the input* */
     INPUT_EVENT_VOUT,
 
+    /* The output state changed (paused or resumed) */
+    INPUT_EVENT_OUTPUT_STATE,
+
     /* (pre-)parsing events */
     INPUT_EVENT_SUBITEMS,
 
@@ -273,6 +276,16 @@ struct vlc_input_event_vout
     vlc_es_id_t *id;
 };
 
+struct vlc_input_event_output_state
+{
+    enum {
+        VLC_INPUT_EVENT_OUTPUT_STATE_RESUMED,
+        VLC_INPUT_EVENT_OUTPUT_STATE_PAUSED,
+    } action;
+    vlc_tick_t paused_date;
+    vlc_es_id_t *id;
+};
+
 struct vlc_input_event_attachments
 {
     input_attachment_t *const* array;
@@ -318,6 +331,8 @@ struct vlc_input_event
         float cache;
         /* INPUT_EVENT_VOUT */
         struct vlc_input_event_vout vout;
+        /* INPUT_EVENT_OUTPUT_STATE */
+        struct vlc_input_event_output_state output_state;
         /* INPUT_EVENT_SUBITEMS */
         input_item_node_t *subitems;
         /* INPUT_EVENT_VBI_PAGE */


=====================================
src/player/input.c
=====================================
@@ -1049,6 +1049,12 @@ input_thread_Events(input_thread_t *input_thread,
         case INPUT_EVENT_VOUT:
             vlc_player_input_HandleVoutEvent(input, &event->vout);
             break;
+        case INPUT_EVENT_OUTPUT_STATE:
+            if (event->output_state.action == VLC_INPUT_EVENT_OUTPUT_STATE_PAUSED)
+                vlc_player_UpdateTimerEvent(player, event->output_state.id,
+                                            VLC_PLAYER_TIMER_EVENT_PAUSED,
+                                            event->output_state.paused_date);
+            break;
         case INPUT_EVENT_ITEM_META:
         case INPUT_EVENT_ITEM_INFO:
             vlc_player_SendEvent(player, on_media_meta_changed,


=====================================
src/player/timer.c
=====================================
@@ -62,6 +62,30 @@ vlc_player_SendTimerSeek(vlc_player_t *player,
     }
 }
 
+static void
+vlc_player_SendTimerPause(vlc_player_t *player,
+                          struct vlc_player_timer_source *source,
+                          vlc_tick_t system_date, bool is_smpte)
+{
+    (void) player;
+
+    vlc_player_timer_id *timer;
+    vlc_list_foreach(timer, &source->listeners, node)
+    {
+        if (is_smpte)
+        {
+            if (timer->smpte_cbs->on_paused != NULL)
+                timer->smpte_cbs->on_paused(system_date, timer->data);
+        }
+        else
+        {
+            timer->last_update_date = VLC_TICK_INVALID;
+            if (timer->cbs->on_paused != NULL)
+                timer->cbs->on_paused(system_date, timer->data);
+        }
+    }
+}
+
 static void
 vlc_player_SendTimerSourceUpdates(vlc_player_t *player,
                                   struct vlc_player_timer_source *source,
@@ -202,7 +226,6 @@ vlc_player_UpdateTimerEvent(vlc_player_t *player, vlc_es_id_t *es_source,
     /* Discontinuity is signalled by all output clocks and the input.
      * discard the event if it was already signalled or not on the good
      * es_source. */
-    bool notify = false;
     struct vlc_player_timer_source *bestsource = &player->timer.best_source;
 
     switch (event)
@@ -232,9 +255,18 @@ vlc_player_UpdateTimerEvent(vlc_player_t *player, vlc_es_id_t *es_source,
             break;
 
         case VLC_PLAYER_TIMER_EVENT_PAUSED:
-            notify = true;
             assert(system_date != VLC_TICK_INVALID);
             player->timer.paused = true;
+
+            for (size_t i = 0; i < VLC_PLAYER_TIMER_TYPE_COUNT; ++i)
+            {
+                struct vlc_player_timer_source *source = &player->timer.sources[i];
+                if (source->es != es_source)
+                    continue;
+                vlc_player_SendTimerPause(player, source, system_date,
+                                          i == VLC_PLAYER_TIMER_TYPE_SMPTE);
+            }
+
             break;
 
         case VLC_PLAYER_TIMER_EVENT_PLAYING:
@@ -244,26 +276,19 @@ vlc_player_UpdateTimerEvent(vlc_player_t *player, vlc_es_id_t *es_source,
 
         case VLC_PLAYER_TIMER_EVENT_STOPPING:
             player->timer.stopping = true;
-            notify = true;
+            for (size_t i = 0; i < VLC_PLAYER_TIMER_TYPE_COUNT; ++i)
+            {
+                struct vlc_player_timer_source *source = &player->timer.sources[i];
+                vlc_player_SendTimerPause(player, source, system_date,
+                                          i == VLC_PLAYER_TIMER_TYPE_SMPTE);
+            }
             break;
 
         default:
             vlc_assert_unreachable();
     }
 
-    if (!notify)
-    {
-        vlc_mutex_unlock(&player->timer.lock);
-        return;
-    }
 
-    vlc_player_timer_id *timer;
-    vlc_list_foreach(timer, &bestsource->listeners, node)
-    {
-        timer->last_update_date = VLC_TICK_INVALID;
-        if (timer->cbs->on_paused != NULL)
-            timer->cbs->on_paused(system_date, timer->data);
-    }
 
     vlc_mutex_unlock(&player->timer.lock);
 }
@@ -346,16 +371,12 @@ vlc_player_UpdateTimerBestSource(vlc_player_t *player, vlc_es_id_t *es_source,
                                  bool force_update)
 {
     /* Best source priority:
-     * 1/ es_source != NULL when paused (any ES tracks when paused. Indeed,
-     * there is likely no audio update (master) when paused but only video
-     * ones, via vlc_player_NextVideoFrame() for example)
-     * 2/ es_source != NULL + master (from the master ES track)
-     * 3/ es_source != NULL (from the first ES track updated)
-     * 4/ es_source == NULL (from the input)
+     * 1/ es_source != NULL + master (from the master ES track)
+     * 2/ es_source != NULL (from the first ES track updated)
+     * 3/ es_source == NULL (from the input)
      */
     struct vlc_player_timer_source *source = &player->timer.best_source;
-    if (!source->es || es_source_is_master
-     || (es_source && player->timer.paused))
+    if (!source->es || es_source_is_master)
         source->es = es_source;
 
     /* Notify the best source */


=====================================
test/src/player/pause.c
=====================================
@@ -6,6 +6,36 @@
  *****************************************************************************/
 
 #include "common.h"
+#include "timers.h"
+
+static struct report_timer *
+wait_timer_report(vlc_player_t *player, struct timer_state *timer,
+                  unsigned type)
+{
+    struct report_timer *r_found = NULL;
+    player_lock_timer(player, timer);
+    for (;;)
+    {
+        struct report_timer *r = timer_state_wait_next_report(timer);
+        if (r->type == type)
+        {
+            r_found = r;
+            break;
+        }
+    }
+    assert(r_found != NULL);
+    player_unlock_timer(player, timer);
+    return r_found;
+}
+
+static struct report_timer *
+get_timer_report(vlc_player_t *player, struct timer_state *timer)
+{
+    player_lock_timer(player, timer);
+    struct report_timer *r = &timer->vec.data[timer->vec.size -1];
+    player_unlock_timer(player, timer);
+    return r;
+}
 
 static void
 test_pause(struct ctx *ctx)
@@ -15,6 +45,9 @@ test_pause(struct ctx *ctx)
 
     struct media_params params = DEFAULT_MEDIA_PARAMS(VLC_TICK_FROM_SEC(10));
     player_set_next_mock_media(ctx, "media1", &params);
+    struct timer_state video_timer, timer;
+    player_add_timer(player, &video_timer, true, VLC_TICK_INVALID);
+    player_add_timer(player, &timer, false, VLC_TICK_INVALID);
 
     /* Start paused */
     vlc_player_SetStartPaused(player, true);
@@ -34,6 +67,10 @@ test_pause(struct ctx *ctx)
         assert(vec->size == 0);
     }
 
+    /* Ensure all timers are paused */
+    wait_timer_report(player, &video_timer, REPORT_TIMER_PAUSED);
+    wait_timer_report(player, &timer, REPORT_TIMER_PAUSED);
+
     /* Resume */
     vlc_player_Resume(player);
 
@@ -50,6 +87,10 @@ test_pause(struct ctx *ctx)
             vlc_player_CondWait(player, &ctx->wait);
     }
 
+    /* Ensure we got a video/audio point updated */
+    wait_timer_report(player, &video_timer, REPORT_TIMER_TC);
+    wait_timer_report(player, &timer, REPORT_TIMER_POINT);
+
     /* Pause again (while playing) */
     vlc_player_Pause(player);
 
@@ -60,7 +101,22 @@ test_pause(struct ctx *ctx)
         assert(vec->size == 5);
     }
 
+    /* Ensure all timers are paused */
+    struct report_timer *r_video_paused, *r_paused;
+    r_video_paused = wait_timer_report(player, &video_timer, REPORT_TIMER_PAUSED);
+    r_paused = wait_timer_report(player, &timer, REPORT_TIMER_PAUSED);
+
+    /* Ensure we stay paused */
+    vlc_tick_sleep(VLC_TICK_FROM_MS(100));
+
+    /* Ensure the last video timer report is the paused one (and that no ouput
+     * are updated after) */
+    assert(get_timer_report(player, &video_timer) == r_video_paused);
+    assert(get_timer_report(player, &timer) == r_paused);
+
     test_end(ctx);
+    player_remove_timer(player, &video_timer);
+    player_remove_timer(player, &timer);
 }
 
 int


=====================================
test/src/player/timers.c
=====================================
@@ -20,10 +20,13 @@ test_timers_assert_smpte(struct timer_state *timer,
 
     /* Check that we didn't miss any update points */
     assert(vec->data[0].tc.frames == 0);
+    struct report_timer *prev_report = NULL;
+
     for (size_t i = 0; i < vec->size; ++i)
     {
-        struct report_timer *prev_report = i > 0 ? &vec->data[i - 1] : NULL;
         struct report_timer *report = &vec->data[i];
+        if (report->type != REPORT_TIMER_TC)
+            continue;
 
         assert(report->tc.seconds == (i / fps));
         if (prev_report)
@@ -37,11 +40,11 @@ test_timers_assert_smpte(struct timer_state *timer,
                 assert(report->tc.frames == prev_report->tc.frames + 1);
         }
 
-        assert(report->type == REPORT_TIMER_TC);
         assert(report->tc.drop_frame == drop_frame);
         assert(report->tc.frame_resolution == frame_resolution);
+        prev_report = report;
     }
-    assert(VEC_LAST(vec).tc.frames + 1 == fps * duration / VLC_TICK_FROM_SEC(1));
+    assert(prev_report->tc.frames + 1 == fps * duration / VLC_TICK_FROM_SEC(1));
 }
 
 static void
@@ -54,10 +57,17 @@ test_timers_assert_smpte_dropframe(struct timer_state *timer, unsigned minute,
     vec_report_timer *vec = &timer->vec;
 
     bool last_second_seen = false, minute_seen = false;
-    for (size_t i = 1; i < vec->size; ++i)
+    struct report_timer *prev_report = NULL;
+    for (size_t i = 0; i < vec->size; ++i)
     {
-        struct report_timer *prev_report = &vec->data[i - 1];
         struct report_timer *report = &vec->data[i];
+        if (report->type != REPORT_TIMER_TC)
+            continue;
+        if (prev_report == NULL)
+        {
+            prev_report = report;
+            continue;
+        }
 
         assert(report->tc.drop_frame == true);
         assert(report->tc.frame_resolution == 2);
@@ -96,6 +106,7 @@ test_timers_assert_smpte_dropframe(struct timer_state *timer, unsigned minute,
         else if (prev_report->tc.minutes != 0 && prev_report->tc.seconds != 0
               && prev_report->tc.frames != 0)
             assert(report->tc.frames == prev_report->tc.frames + 1);
+        prev_report = report;
     }
 
     /* Assert that we've seen the full last second and the new minute */
@@ -232,7 +243,8 @@ test_timers_playback(struct ctx *ctx, struct timer_state timers[],
     {
         struct timer_state *timer = &timers[SMPTE_TIMER_IDX];
         vec_report_timer *vec = &timer->vec;
-        assert(vec->size == 0);
+        assert(vec->size == 1);
+        assert(timer->vec.data[0].type == REPORT_TIMER_PAUSED);
     }
     test_end(ctx);
 


=====================================
test/src/player/timers.h
=====================================
@@ -35,6 +35,9 @@ struct timer_state
     vlc_player_timer_id *id;
     vlc_tick_t delay;
     vec_report_timer vec;
+    size_t last_report_idx;
+    vlc_mutex_t lock;
+    vlc_cond_t wait;
 };
 
 static inline void
@@ -46,7 +49,10 @@ timers_on_update(const struct vlc_player_timer_point *point, void *data)
         .type = REPORT_TIMER_POINT,
         .point = *point,
     };
+    vlc_mutex_lock(&timer->lock);
     bool success = vlc_vector_push(&timer->vec, report);
+    vlc_cond_signal(&timer->wait);
+    vlc_mutex_unlock(&timer->lock);
     assert(success);
 }
 
@@ -59,7 +65,10 @@ timers_on_paused(vlc_tick_t system_date, void *data)
         .type = REPORT_TIMER_PAUSED,
         .paused_date = system_date,
     };
+    vlc_mutex_lock(&timer->lock);
     bool success = vlc_vector_push(&timer->vec, report);
+    vlc_cond_signal(&timer->wait);
+    vlc_mutex_unlock(&timer->lock);
     assert(success);
 }
 
@@ -74,7 +83,10 @@ timers_on_seek(const struct vlc_player_timer_point *point, void *data)
     report.seek.finished = point == NULL;
     if (!report.seek.finished)
         report.seek.point = *point;
+    vlc_mutex_lock(&timer->lock);
     bool success = vlc_vector_push(&timer->vec, report);
+    vlc_cond_signal(&timer->wait);
+    vlc_mutex_unlock(&timer->lock);
     assert(success);
 }
 
@@ -88,7 +100,10 @@ timers_smpte_on_update(const struct vlc_player_timer_smpte_timecode *tc,
         .type = REPORT_TIMER_TC,
         .tc = *tc,
     };
+    vlc_mutex_lock(&timer->lock);
     bool success = vlc_vector_push(&timer->vec, report);
+    vlc_cond_signal(&timer->wait);
+    vlc_mutex_unlock(&timer->lock);
     assert(success);
 }
 
@@ -106,9 +121,13 @@ player_add_timer(vlc_player_t *player, struct timer_state *timer, bool smpte,
     static const struct vlc_player_timer_smpte_cbs smpte_cbs =
     {
         .on_update = timers_smpte_on_update,
+        .on_paused = timers_on_paused,
     };
 
     vlc_vector_init(&timer->vec);
+    vlc_mutex_init(&timer->lock);
+    vlc_cond_init(&timer->wait);
+    timer->last_report_idx = 0;
     timer->delay = delay;
     if (smpte)
         timer->id = vlc_player_AddSmpteTimer(player, &smpte_cbs, timer);
@@ -122,4 +141,28 @@ player_remove_timer(vlc_player_t *player, struct timer_state *timer)
 {
     vlc_vector_clear(&timer->vec);
     vlc_player_RemoveTimer(player, timer->id);
+}
+
+static inline void
+player_lock_timer(vlc_player_t *player, struct timer_state *timer)
+{
+    vlc_player_Unlock(player);
+    vlc_mutex_lock(&timer->lock);
+}
+
+static inline void
+player_unlock_timer(vlc_player_t *player, struct timer_state *timer)
+{
+    vlc_mutex_unlock(&timer->lock);
+    vlc_player_Lock(player);
+}
+
+static inline struct report_timer *
+timer_state_wait_next_report(struct timer_state *timer)
+{
+    while (timer->vec.size < timer->last_report_idx + 1)
+        vlc_cond_wait(&timer->wait, &timer->lock);
+    struct report_timer *r = &timer->vec.data[timer->last_report_idx];
+    timer->last_report_idx++;
+    return r;
 }
\ No newline at end of file



View it on GitLab: https://code.videolan.org/videolan/vlc/-/compare/6b95cfb4a6aef7176ca0e8312b45998e17c040d0...df5039d94d252e8d4a0703e5eb45c9e9db53b2f3

-- 
View it on GitLab: https://code.videolan.org/videolan/vlc/-/compare/6b95cfb4a6aef7176ca0e8312b45998e17c040d0...df5039d94d252e8d4a0703e5eb45c9e9db53b2f3
You're receiving this email because of your account on code.videolan.org.


VideoLAN code repository instance


More information about the vlc-commits mailing list