[vlc-devel] [PATCH] libvlc: add libvlc_media_discoverer_services_get
Thomas Guillem
thomas at gllm.fr
Tue Feb 9 13:41:41 CET 2016
This function return the list of services discovery handled by libVLC.
---
include/vlc/libvlc_media_discoverer.h | 57 +++++++++++++++++++
lib/media_discoverer.c | 101 ++++++++++++++++++++++++++++++++++
2 files changed, 158 insertions(+)
diff --git a/include/vlc/libvlc_media_discoverer.h b/include/vlc/libvlc_media_discoverer.h
index 8866607..f11b2c6 100644
--- a/include/vlc/libvlc_media_discoverer.h
+++ b/include/vlc/libvlc_media_discoverer.h
@@ -30,6 +30,31 @@
extern "C" {
# endif
+/**
+ * Category of a media discoverer service
+ * \see libvlc_media_discoverer_services_get()
+ */
+typedef enum {
+ /** devices, like portable music player */
+ libvlc_media_discoverer_devices,
+ /** LAN/WAN services, like Upnp, SMB, or SAP */
+ libvlc_media_discoverer_lan,
+ /** Internet of Website channels services */
+ libvlc_media_discoverer_internet,
+ /** Computer services, like Discs or Apps */
+ libvlc_media_discoverer_mycomputer,
+} libvlc_media_discoverer_category;
+
+/**
+ * Media discoverer service
+ * \see libvlc_media_discoverer_services_get()
+ */
+typedef struct {
+ char *psz_name;
+ char *psz_longname;
+ libvlc_media_discoverer_category i_cat;
+} libvlc_media_discoverer_service;
+
/** \defgroup libvlc_media_discoverer LibVLC media discovery
* \ingroup libvlc
* LibVLC media discovery finds available media via various means.
@@ -145,6 +170,38 @@ LIBVLC_API libvlc_event_manager_t *
LIBVLC_API int
libvlc_media_discoverer_is_running( libvlc_media_discoverer_t * p_mdis );
+/**
+ * Get media discoverer services by category
+ *
+ * \version LibVLC 3.0.0 and later.
+ *
+ * \param p_inst libvlc instance
+ * \param i_cat category of the service to fetch
+ * \param ppp_services address to store an allocated array of media discoverer
+ * services (must be freed with libvlc_media_discoverer_services_release() by
+ * the caller) [OUT]
+ *
+ * \return the number of media discoverer services (zero on error)
+ */
+LIBVLC_API unsigned int
+libvlc_media_discoverer_services_get( libvlc_instance_t *p_inst,
+ libvlc_media_discoverer_category i_cat,
+ libvlc_media_discoverer_service ***ppp_services );
+
+/**
+ * Release an array of media discoverer services
+ *
+ * \version LibVLC 3.0.0 and later.
+ *
+ * \see libvlc_media_discoverer_services_get()
+ *
+ * \param pp_services array to release
+ * \param i_count number of elements in the array
+ */
+LIBVLC_API void
+libvlc_media_discoverer_services_release( libvlc_media_discoverer_service **pp_services,
+ unsigned int i_count );
+
/**@} */
# ifdef __cplusplus
diff --git a/lib/media_discoverer.c b/lib/media_discoverer.c
index ed9390b..3e76780 100644
--- a/lib/media_discoverer.c
+++ b/lib/media_discoverer.c
@@ -385,3 +385,104 @@ libvlc_media_discoverer_is_running( libvlc_media_discoverer_t * p_mdis )
{
return p_mdis->running;
}
+
+void
+libvlc_media_discoverer_services_release( libvlc_media_discoverer_service **pp_services,
+ unsigned int i_count )
+{
+ for( unsigned int i = 0; i < i_count; ++i )
+ {
+ free( pp_services[i]->psz_name );
+ free( pp_services[i]->psz_longname );
+ free( pp_services[i] );
+ }
+ free( pp_services );
+}
+
+unsigned int
+libvlc_media_discoverer_services_get( libvlc_instance_t *p_inst,
+ libvlc_media_discoverer_category i_cat,
+ libvlc_media_discoverer_service ***ppp_services )
+{
+ int i_core_cat;
+ switch( i_cat )
+ {
+ case libvlc_media_discoverer_devices:
+ i_core_cat = SD_CAT_DEVICES;
+ break;
+ case libvlc_media_discoverer_lan:
+ i_core_cat = SD_CAT_LAN;
+ break;
+ case libvlc_media_discoverer_internet:
+ i_core_cat = SD_CAT_INTERNET;
+ break;
+ case libvlc_media_discoverer_mycomputer:
+ i_core_cat = SD_CAT_MYCOMPUTER;
+ break;
+ default:
+ vlc_assert_unreachable();
+ return 0;
+ }
+
+ /* Fetch all sd names, longnames and categories */
+ char **ppsz_names, **ppsz_longnames;
+ int *p_categories;
+ ppsz_names = vlc_sd_GetNames( p_inst->p_libvlc_int, &ppsz_longnames,
+ &p_categories );
+
+ if( ppsz_names == NULL )
+ return 0;
+
+ /* Count the number of sd matching our category (i_cat/i_core_cat) */
+ unsigned int i_nb_services = 0;
+ char **ppsz_name = ppsz_names;
+ int *p_category = p_categories;
+ for( ; *ppsz_name != NULL; ppsz_name++, p_category++ )
+ {
+ if( *p_category == i_core_cat )
+ i_nb_services++;
+ }
+
+ libvlc_media_discoverer_service **pp_services = i_nb_services > 0 ?
+ malloc( i_nb_services * sizeof(libvlc_media_discoverer_service *) ) : NULL;
+
+ /* Fill output pp_services or free unused name, longnames */
+ char **ppsz_longname = ppsz_longnames;
+ ppsz_name = ppsz_names;
+ p_category = p_categories;
+ unsigned int i_service_idx = 0;
+ for( ; *ppsz_name != NULL; ppsz_name++, ppsz_longname++, p_category++ )
+ {
+ if( pp_services != NULL && *p_category == i_core_cat )
+ {
+ libvlc_media_discoverer_service *p_service =
+ malloc( sizeof(libvlc_media_discoverer_service) );
+ if( p_service == NULL )
+ {
+ libvlc_media_discoverer_services_release( pp_services,
+ i_service_idx );
+ pp_services = NULL;
+ i_nb_services = 0;
+ }
+ else
+ {
+ p_service->psz_name = *ppsz_name;
+ p_service->psz_longname = *ppsz_longname;
+ p_service->i_cat = i_cat;
+ pp_services[i_service_idx++] = p_service;
+ }
+ }
+ else
+ {
+ free( *ppsz_name );
+ free( *ppsz_longname );
+ }
+ }
+ free( ppsz_names );
+ free( ppsz_longnames );
+ free( p_categories );
+
+ if( i_nb_services > 0 )
+ *ppp_services = pp_services;
+ return i_nb_services;
+}
--
2.7.0.rc3
More information about the vlc-devel
mailing list