diff options
author | Mark Ryan <mark.d.ryan@intel.com> | 2013-04-10 11:49:11 +0200 |
---|---|---|
committer | Christophe Guiraud <christophe.guiraud@intel.com> | 2013-04-11 11:24:35 +0200 |
commit | 1e5e0bde3250af0278f3839057564ce24aa905e3 (patch) | |
tree | b15fe6ecc67ac03a35d6fe76fad4001b34f3099b | |
parent | 329a2855eefeaeefe168de4ba80c896ea1421d6b (diff) | |
download | dleyna-server-1e5e0bde3250af0278f3839057564ce24aa905e3.tar.gz |
dLeyna-server now handles invalid types.
Previously, invalid types were not handled correctly which could lead
to crashes when processing invalid meta data or when an invalid type
is passed from applications, in the create container function for
example.
See https://github.com/01org/dleyna-renderer/issues/30 for more details
Signed-off-by: Mark Ryan <mark.d.ryan@intel.com>
-rw-r--r-- | libdleyna/server/device.c | 29 | ||||
-rw-r--r-- | libdleyna/server/props.c | 10 | ||||
-rw-r--r-- | libdleyna/server/task.c | 3 | ||||
-rw-r--r-- | libdleyna/server/upnp.c | 3 |
4 files changed, 40 insertions, 5 deletions
diff --git a/libdleyna/server/device.c b/libdleyna/server/device.c index 34818a8..a83c3da 100644 --- a/libdleyna/server/device.c +++ b/libdleyna/server/device.c @@ -2797,11 +2797,16 @@ static gchar *prv_create_new_container_didl(const gchar *parent_id, GUPnPDIDLLiteWriter *writer; GUPnPDIDLLiteObject *item; GUPnPDIDLLiteContainer *container; - gchar *retval; GVariantIter iter; GVariant *child_type; const gchar *actual_type; GUPnPOCMFlags flags; + gchar *retval = NULL; + + actual_type = dls_props_media_spec_to_upnp_class( + task->ut.create_container.type); + if (!actual_type) + goto on_error; writer = gupnp_didl_lite_writer_new(NULL); item = GUPNP_DIDL_LITE_OBJECT( @@ -2813,8 +2818,6 @@ static gchar *prv_create_new_container_didl(const gchar *parent_id, item, task->ut.create_container.display_name); gupnp_didl_lite_object_set_parent_id(item, parent_id); - actual_type = dls_props_media_spec_to_upnp_class( - task->ut.create_container.type); gupnp_didl_lite_object_set_upnp_class(item, actual_type); gupnp_didl_lite_object_set_restricted(item, FALSE); flags = GUPNP_OCM_FLAGS_UPLOAD | @@ -2839,6 +2842,8 @@ static gchar *prv_create_new_container_didl(const gchar *parent_id, g_object_unref(item); g_object_unref(writer); +on_error: + return retval; } @@ -3639,6 +3644,14 @@ void dls_device_create_container(dls_client_t *client, context = dls_device_get_context(task->target.device, client); didl = prv_create_new_container_didl(parent_id, task); + if (!didl) { + DLEYNA_LOG_WARNING("Unable to create didl"); + + cb_data->error = g_error_new(DLEYNA_SERVER_ERROR, + DLEYNA_ERROR_OPERATION_FAILED, + "Unable to create didl"); + goto on_error; + } DLEYNA_LOG_DEBUG("DIDL: %s", didl); @@ -3661,7 +3674,11 @@ void dls_device_create_container(dls_client_t *client, g_free(didl); +on_error: + DLEYNA_LOG_DEBUG("Exit"); + + return; } static void prv_update_object_update_cb(GUPnPServiceProxy *proxy, @@ -3749,11 +3766,13 @@ static gchar *prv_get_new_xml_fragment(GUPnPDIDLLiteObject *object, } else if (mask & DLS_UPNP_MASK_PROP_TYPE) { upnp_class = dls_props_media_spec_to_upnp_class( g_variant_get_string(value, NULL)); + if (!upnp_class) + goto on_error; gupnp_didl_lite_object_set_upnp_class(object, upnp_class); retval = gupnp_didl_lite_object_get_upnp_class_xml_string( - object); + object); } else if (mask & DLS_UPNP_MASK_PROP_TRACK_NUMBER) { gupnp_didl_lite_object_set_track_number( object, @@ -3776,6 +3795,8 @@ static gchar *prv_get_new_xml_fragment(GUPnPDIDLLiteObject *object, retval = gupnp_didl_lite_object_get_artists_xml_string(object); } +on_error: + return retval; } diff --git a/libdleyna/server/props.c b/libdleyna/server/props.c index 983002e..aada049 100644 --- a/libdleyna/server/props.c +++ b/libdleyna/server/props.c @@ -1047,6 +1047,9 @@ const gchar *dls_props_media_spec_to_upnp_class(const gchar *m2spec_class) { const gchar *retval = NULL; + if (!m2spec_class) + goto on_error; + if (!strcmp(m2spec_class, gMediaSpec2AlbumPhoto)) retval = gUPnPPhotoAlbum; else if (!strcmp(m2spec_class, gMediaSpec2AlbumMusic)) @@ -1090,6 +1093,8 @@ const gchar *dls_props_media_spec_to_upnp_class(const gchar *m2spec_class) else if (!strcmp(m2spec_class, gMediaSpec2Item)) retval = gUPnPItem; +on_error: + return retval; } @@ -1098,6 +1103,9 @@ const gchar *dls_props_upnp_class_to_media_spec(const gchar *upnp_class) const gchar *retval = NULL; const gchar *ptr; + if (!upnp_class) + goto on_error; + if (!strncmp(upnp_class, gUPnPAlbum, gUPnPAlbumLen)) { ptr = upnp_class + gUPnPAlbumLen; if (!strcmp(ptr, ".photoAlbum")) @@ -1159,6 +1167,8 @@ const gchar *dls_props_upnp_class_to_media_spec(const gchar *upnp_class) retval = gMediaSpec2Item; } +on_error: + return retval; } diff --git a/libdleyna/server/task.c b/libdleyna/server/task.c index 3d74c56..bed8003 100644 --- a/libdleyna/server/task.c +++ b/libdleyna/server/task.c @@ -91,7 +91,8 @@ static void prv_delete(dls_task_t *task) case DLS_TASK_CREATE_CONTAINER_IN_ANY: g_free(task->ut.create_container.display_name); g_free(task->ut.create_container.type); - g_variant_unref(task->ut.create_container.child_types); + if (task->ut.create_container.child_types) + g_variant_unref(task->ut.create_container.child_types); break; case DLS_TASK_UPDATE_OBJECT: if (task->ut.update.to_add_update) diff --git a/libdleyna/server/upnp.c b/libdleyna/server/upnp.c index 073e9a2..b66be43 100644 --- a/libdleyna/server/upnp.c +++ b/libdleyna/server/upnp.c @@ -916,6 +916,9 @@ void dls_upnp_create_container(dls_upnp_t *upnp, dls_client_t *client, dls_device_create_container(client, task, task->target.id); + if (!cb_data->action) + (void) g_idle_add(dls_async_task_complete, cb_data); + DLEYNA_LOG_DEBUG("Exit"); } |