diff options
author | Regis Merlino <regis.merlino@intel.com> | 2013-02-26 17:25:50 +0100 |
---|---|---|
committer | Ludovic Ferrandis <ludovic.ferrandis@intel.com> | 2013-02-26 18:20:25 +0100 |
commit | 38e71f8a0dbdd2183b57c8f62e945021e2cd0ae4 (patch) | |
tree | ff65e9decc79cfa1c66c11a6e7f2f75adf6e1316 | |
parent | a6ba856815a40ee38a558791222976e952bf1c17 (diff) | |
download | dleyna-server-38e71f8a0dbdd2183b57c8f62e945021e2cd0ae4.tar.gz |
[Device] Handle unsubscribe when exiting
Signed-off-by: Regis Merlino <regis.merlino@intel.com>
-rw-r--r-- | lib/device.c | 69 | ||||
-rw-r--r-- | lib/device.h | 2 | ||||
-rw-r--r-- | lib/server.c | 14 | ||||
-rw-r--r-- | lib/upnp.c | 17 | ||||
-rw-r--r-- | lib/upnp.h | 2 |
5 files changed, 77 insertions, 27 deletions
diff --git a/lib/device.c b/lib/device.c index e48c939..3972d5a 100644 --- a/lib/device.c +++ b/lib/device.c @@ -145,34 +145,43 @@ static void prv_count_data_new(dls_async_task_t *cb_data, *count_data = cd; } +static void prv_context_unsubscribe(dls_device_context_t *ctx) +{ + if (ctx->timeout_id) { + (void) g_source_remove(ctx->timeout_id); + ctx->timeout_id = 0; + } + + if (ctx->subscribed) { + gupnp_service_proxy_remove_notify( + ctx->service_proxy, + DLS_SYSTEM_UPDATE_VAR, + prv_system_update_cb, + ctx->device); + gupnp_service_proxy_remove_notify( + ctx->service_proxy, + DLS_CONTAINER_UPDATE_VAR, + prv_container_update_cb, + ctx->device); + gupnp_service_proxy_remove_notify( + ctx->service_proxy, + DLS_LAST_CHANGE_VAR, + prv_last_change_cb, + ctx->device); + + gupnp_service_proxy_set_subscribed(ctx->service_proxy, + FALSE); + + ctx->subscribed = FALSE; + } +} + static void prv_context_delete(gpointer context) { dls_device_context_t *ctx = context; if (ctx) { - if (ctx->timeout_id) - (void) g_source_remove(ctx->timeout_id); - - if (ctx->subscribed) { - gupnp_service_proxy_remove_notify( - ctx->service_proxy, - DLS_SYSTEM_UPDATE_VAR, - prv_system_update_cb, - ctx->device); - gupnp_service_proxy_remove_notify( - ctx->service_proxy, - DLS_CONTAINER_UPDATE_VAR, - prv_container_update_cb, - ctx->device); - gupnp_service_proxy_remove_notify( - ctx->service_proxy, - DLS_LAST_CHANGE_VAR, - prv_last_change_cb, - ctx->device); - - gupnp_service_proxy_set_subscribed(ctx->service_proxy, - FALSE); - } + prv_context_unsubscribe(ctx); if (ctx->device_proxy) g_object_unref(ctx->device_proxy); @@ -233,6 +242,20 @@ void dls_device_delete(void *device) } } +void dls_device_unsubscribe(void *device) +{ + unsigned int i; + dls_device_t *dev = device; + dls_device_context_t *context; + + if (dev) { + for (i = 0; i < dev->contexts->len; ++i) { + context = g_ptr_array_index(dev->contexts, i); + prv_context_unsubscribe(context); + } + } +} + static void prv_last_change_decode(GUPnPCDSLastChangeEntry *entry, GVariantBuilder *array, const char *root_path) diff --git a/lib/device.h b/lib/device.h index 5b5705a..ef3e3df 100644 --- a/lib/device.h +++ b/lib/device.h @@ -63,6 +63,8 @@ dls_device_context_t *dls_device_append_new_context(dls_device_t *device, GUPnPDeviceProxy *proxy); void dls_device_delete(void *device); +void dls_device_unsubscribe(void *device); + dls_device_t *dls_device_new( dleyna_connector_id_t connection, GUPnPDeviceProxy *proxy, diff --git a/lib/server.c b/lib/server.c index 7837e23..f09e238 100644 --- a/lib/server.c +++ b/lib/server.c @@ -1148,12 +1148,11 @@ static void prv_control_point_initialize(const dleyna_connector_t *connector, g_set_prgname(DLS_PRG_NAME); } -static void prv_control_point_free(void) +static void prv_control_point_finalize(void) { - dls_upnp_delete(g_context.upnp); + dls_upnp_unsubscribe(g_context.upnp); - if (g_context.watchers) - g_hash_table_unref(g_context.watchers); + dls_upnp_delete(g_context.upnp); if (g_context.connection) { if (g_context.dls_id) @@ -1163,6 +1162,12 @@ static void prv_control_point_free(void) } } +static void prv_control_point_free(void) +{ + if (g_context.watchers) + g_hash_table_unref(g_context.watchers); +} + static const gchar *prv_control_point_server_name(void) { return DLEYNA_SERVER_NAME; @@ -1180,6 +1185,7 @@ static const gchar *prv_control_point_root_introspection(void) static const dleyna_control_point_t g_control_point = { prv_control_point_initialize, + prv_control_point_finalize, prv_control_point_free, prv_control_point_server_name, prv_control_point_server_introspection, @@ -1046,6 +1046,23 @@ on_error: DLEYNA_LOG_DEBUG("Exit failure"); } +void dls_upnp_unsubscribe(dls_upnp_t *upnp) +{ + GHashTableIter iter; + gpointer value; + dls_device_t *device; + + DLEYNA_LOG_DEBUG("Enter"); + + g_hash_table_iter_init(&iter, upnp->server_udn_map); + while (g_hash_table_iter_next(&iter, NULL, &value)) { + device = value; + dls_device_unsubscribe(device); + } + + DLEYNA_LOG_DEBUG("Exit"); +} + static gboolean prv_device_uc_find(gpointer key, gpointer value, gpointer user_data) { @@ -101,6 +101,8 @@ void dls_upnp_create_playlist_in_any(dls_upnp_t *upnp, dls_client_t *client, dls_task_t *task, dls_upnp_task_complete_t cb); +void dls_upnp_unsubscribe(dls_upnp_t *upnp); + gboolean dls_upnp_device_context_exist(dls_device_t *device, dls_device_context_t *context); |