Commit 898816a3 authored by Filip Roséen's avatar Filip Roséen Committed by Thomas Guillem

playlist/item: redirect request following deletion of node

:: Introduction

When we are dealing with a flat playlist, a request to add children to
an item results in that item being deleted, and its children being
inserted into the parent of said item. This is done in order to not
introduce any nested levels in the tree.

What this further means is that /if/ the item that is effectivelly removed is
scheduled for playback prior to the removal, the playlist might try to play an
entity which does not exist anymore; which is problematic for several reasons.

Note: The problem does not exist when --playlist-tree is enabled since
      the item on which children should be attached is then preserved.

:: Solution

The solution to the previously described problem is to "redirect" any
pending request that refers to the deleted entity, so that it instead
refers to its first child (if any).

closes #17183
Signed-off-by: Thomas Guillem's avatarThomas Guillem <>
parent 76233614
......@@ -54,6 +54,7 @@ static void input_item_add_subitem_tree ( const vlc_event_t * p_event,
input_item_t *p_input = p_event->p_obj;
playlist_t *p_playlist = (( playlist_item_t* ) user_data)->p_playlist;
playlist_private_t *p_sys = pl_priv( p_playlist );
input_item_node_t *p_new_root = p_event->u.input_item_subitem_tree_added.p_root;
......@@ -91,6 +92,8 @@ static void input_item_add_subitem_tree ( const vlc_event_t * p_event,
/* If we have to flatten out, then take the item's position in the parent as
insertion point and delete the item */
bool b_redirect_request = false;
if( b_flat )
playlist_item_t *p_parent = p_item->p_parent;
......@@ -109,6 +112,17 @@ static void input_item_add_subitem_tree ( const vlc_event_t * p_event,
playlist_DeleteItem( p_playlist, p_item, true );
/* If there is a pending request referring to the item we just deleted
* it needs to be updated so that we do not try to play an entity that
* is no longer part of the playlist. */
if( p_sys->request.b_request &&
( p_sys->request.p_item == p_item ||
p_sys->request.p_node == p_item ) )
b_redirect_request = true;
p_item = p_parent;
......@@ -125,6 +139,22 @@ static void input_item_add_subitem_tree ( const vlc_event_t * p_event,
b_flat );
if( b_redirect_request )
/* a redirect of the pending request is required, as such we update the
* request to refer to the item that would have been the next in line
* (if any). */
assert( b_flat );
playlist_item_t* p_redirect = NULL;
if( p_item->i_children > pos )
p_redirect = p_item->pp_children[pos];
p_sys->request.p_item = p_redirect;
p_sys->request.p_node = NULL;
if( !b_flat ) var_SetInteger( p_playlist, "leaf-to-parent", p_item->i_id );
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