[vlc-commits] service_discovery: lock playlist_ServicesDiscoveryKillAll()
Thomas Guillem
git at videolan.org
Mon Jan 22 11:14:55 CET 2018
vlc | branch: master | Thomas Guillem <thomas at gllm.fr> | Mon Jan 22 11:06:48 2018 +0100| [d9661b8bdcd40331c71963a565c6e1788f474be7] | committer: Thomas Guillem
service_discovery: lock playlist_ServicesDiscoveryKillAll()
This fixes a race condition between playlist_ServicesDiscoveryRemove() and
playlist_ServicesDiscoveryKillAll().
SDs can be removed from any threads by lua plugins.
CD dd542657-7b65-4f66-9741-22f15e0d563e
> http://git.videolan.org/gitweb.cgi/vlc.git/?a=commit;h=d9661b8bdcd40331c71963a565c6e1788f474be7
---
src/playlist/services_discovery.c | 30 ++++++++++++++++++++----------
1 file changed, 20 insertions(+), 10 deletions(-)
diff --git a/src/playlist/services_discovery.c b/src/playlist/services_discovery.c
index 39a43badd6..6c2d9072c0 100644
--- a/src/playlist/services_discovery.c
+++ b/src/playlist/services_discovery.c
@@ -147,23 +147,24 @@ int playlist_ServicesDiscoveryAdd(playlist_t *playlist, const char *chain)
return VLC_SUCCESS;
}
-static void playlist_ServicesDiscoveryInternalRemove(playlist_t *playlist,
- vlc_sd_internal_t *sds)
+static void playlist_ServicesDiscoveryInternalRemoveLocked(playlist_t *playlist,
+ vlc_sd_internal_t *sds)
{
assert(sds->sd != NULL);
- vlc_sd_Destroy(sds->sd);
+ playlist_Unlock(playlist);
+
+ vlc_sd_Destroy(sds->sd);
/* Remove the sd playlist node if it exists */
playlist_Lock(playlist);
+
if (sds->node != NULL)
playlist_NodeDeleteExplicit(playlist, sds->node,
PLAYLIST_DELETE_FORCE | PLAYLIST_DELETE_STOP_IF_CURRENT );
- playlist_Unlock(playlist);
free(sds);
}
-
int playlist_ServicesDiscoveryRemove(playlist_t *playlist, const char *name)
{
playlist_private_t *priv = pl_priv(playlist);
@@ -181,15 +182,18 @@ int playlist_ServicesDiscoveryRemove(playlist_t *playlist, const char *name)
break;
}
}
- playlist_Unlock(playlist);
if (sds == NULL)
{
msg_Warn(playlist, "discovery %s is not loaded", name);
+ playlist_Unlock(playlist);
return VLC_EGENERIC;
}
- playlist_ServicesDiscoveryInternalRemove(playlist, sds);
+ playlist_ServicesDiscoveryInternalRemoveLocked(playlist, sds);
+
+ playlist_Unlock(playlist);
+
return VLC_SUCCESS;
}
@@ -244,8 +248,14 @@ void playlist_ServicesDiscoveryKillAll(playlist_t *playlist)
{
playlist_private_t *priv = pl_priv(playlist);
- for (int i = 0; i < priv->i_sds; i++)
- playlist_ServicesDiscoveryInternalRemove(playlist, priv->pp_sds[i]);
+ playlist_Lock(playlist);
+ while (priv->i_sds > 0)
+ {
+ vlc_sd_internal_t *sds = priv->pp_sds[priv->i_sds - 1];
+ TAB_ERASE(priv->i_sds, priv->pp_sds, priv->i_sds - 1);
+
+ playlist_ServicesDiscoveryInternalRemoveLocked(playlist, sds);
+ }
- TAB_CLEAN(priv->i_sds, priv->pp_sds);
+ playlist_Unlock(playlist);
}
More information about the vlc-commits
mailing list