From b79b4677f910d101f8f392fb1ec2618ddb4c38da Mon Sep 17 00:00:00 2001 From: Toni Gundogdu Date: Thu, 24 Oct 2013 21:26:04 +0300 Subject: [PATCH] API: Return URLs in escaped (percent-encoded) form - Extend `l_chk_s' and `l_chk_assign_s' functions to allow the caller set the `escape_url' arg to TRUE to tell the library to store the string value in URI escaped form - All URLs returned by the library (e.g. media stream or thumbnail) are now stored in their escaped form, and passed as such to the applications querying them - "Reserved chars" remain unescaped - https://tools.ietf.org/html/rfc3986#section-2.2 Affected API functions - quvi_subtitle_lang_get (QUVI_SUBTITLE_LANG_PROPERTY_URL) - quvi_playlist_get (QUVI_PLAYLIST_*_URL) - quvi_media_get (QUVI_MEDIA_*_URL) Rationale - Address the potential problem of chars getting mangled when the URLs containing UTF8 chars are passed to the application trying to access the URL Signed-off-by: Toni Gundogdu --- src/api/media_get.c | 12 +++++++----- src/api/playlist_get.c | 1 + src/api/subtitle_lang_get.c | 1 + src/lua/chk.c | 18 +++++++++++++----- src/lua/chk.h | 7 ++++--- src/lua/exec_media_script_parse.c | 18 +++++++++--------- src/lua/exec_playlist_script_parse.c | 10 +++++----- src/lua/exec_subtitle_export_script_export.c | 2 +- src/lua/exec_subtitle_export_script_ident.c | 2 +- src/lua/exec_subtitle_script_parse.c | 10 +++++----- 10 files changed, 47 insertions(+), 34 deletions(-) diff --git a/src/api/media_get.c b/src/api/media_get.c index d93de31..f1913e3 100644 --- a/src/api/media_get.c +++ b/src/api/media_get.c @@ -160,11 +160,13 @@ static QuviError _media_get(_quvi_media_t qm, const QuviMediaProperty n, ...) /** @brief Return a media property @sa @ref parse_media @ingroup mediaprop -@note Accessing any of the QUVI_MEDIA_STREAM_PROPERTY_* values using -this function will cause the library to advance to the first stream -in the list, this will conflict with @ref quvi_media_stream_next, -causing @ref quvi_media_stream_next to advance from the second stream, -not the first stream +@note + - Accessing any of the QUVI_MEDIA_STREAM_PROPERTY_* values using this + function will cause the library to advance to the first stream in + the list, this will conflict with @ref quvi_media_stream_next, + causing @ref quvi_media_stream_next to advance from the second + stream, not the first stream + - URLs will be returned in the escaped form */ void quvi_media_get(quvi_media_t handle, QuviMediaProperty property, ...) { diff --git a/src/api/playlist_get.c b/src/api/playlist_get.c index f70e611..6ba65c0 100644 --- a/src/api/playlist_get.c +++ b/src/api/playlist_get.c @@ -146,6 +146,7 @@ static QuviError _playlist_get(_quvi_playlist_t qp, /** @brief Return a playlist property @sa @ref parse_playlist @ingroup playlistprop +@note URLs will be returned in the escaped form */ void quvi_playlist_get(quvi_playlist_t handle, QuviPlaylistProperty property, ...) diff --git a/src/api/subtitle_lang_get.c b/src/api/subtitle_lang_get.c index 4e25e06..147e1a5 100644 --- a/src/api/subtitle_lang_get.c +++ b/src/api/subtitle_lang_get.c @@ -113,6 +113,7 @@ static QuviError _get(_quvi_subtitle_lang_t qsl, /** @brief Return a subtitle property @sa @ref parse_subtitle @ingroup subprop +@note URLs will be returned in the escaped form */ void quvi_subtitle_lang_get(quvi_subtitle_lang_t handle, QuviSubtitleLangProperty n, ...) diff --git a/src/lua/chk.c b/src/lua/chk.c index ab2214f..7cc27d4 100644 --- a/src/lua/chk.c +++ b/src/lua/chk.c @@ -1,5 +1,5 @@ /* libquvi - * Copyright (C) 2012 Toni Gundogdu + * Copyright (C) 2012,2013 Toni Gundogdu * * This file is part of libquvi . * @@ -30,6 +30,7 @@ /* -- */ #include "lua/chk.h" #include "lua/def.h" +#include "misc/url.h" #include "misc/re.h" /* @@ -51,7 +52,7 @@ gboolean l_chk_can_parse_url(lua_State *l, _quvi_script_t qs, lua_pushnil(l); while (lua_next(l, LI_KEY)) { - l_chk_assign_s(l, k_domains, qs->domains, TRUE); + l_chk_assign_s(l, k_domains, qs->domains, TRUE, FALSE); l_chk_assign_b(l, k_can_parse_url, &r); lua_pop(l, 1); } @@ -70,7 +71,8 @@ gboolean l_chk_can_parse_url(lua_State *l, _quvi_script_t qs, * * NOTE: g_free the returned value when done using it. */ -gboolean l_chk_s(lua_State *l, const gchar *w, gchar **v, gboolean trim_flag) +gboolean l_chk_s(lua_State *l, const gchar *w, gchar **v, + gboolean trim_flag, gboolean escape_url) { if (lua_isstring(l, LI_KEY) && lua_isstring(l, LI_VALUE)) { @@ -80,6 +82,12 @@ gboolean l_chk_s(lua_State *l, const gchar *w, gchar **v, gboolean trim_flag) *v = (trim_flag == TRUE) ? m_trim_ws(s) : g_strdup(s); + if (escape_url == TRUE) + { + gchar *e = m_url_escaped_form(*v); + g_free(*v); + *v = e; + } return (TRUE); } } @@ -87,10 +95,10 @@ gboolean l_chk_s(lua_State *l, const gchar *w, gchar **v, gboolean trim_flag) } gboolean l_chk_assign_s(lua_State *l, const gchar *k, GString *v, - gboolean trim_flag) + gboolean trim_flag, gboolean escape_url) { gchar *s = NULL; - if (l_chk_s(l, k, &s, trim_flag) == TRUE) + if (l_chk_s(l, k, &s, trim_flag, escape_url) == TRUE) { g_string_assign(v, s); g_free(s); diff --git a/src/lua/chk.h b/src/lua/chk.h index d22bcf7..730937a 100644 --- a/src/lua/chk.h +++ b/src/lua/chk.h @@ -1,5 +1,5 @@ /* libquvi - * Copyright (C) 2012 Toni Gundogdu + * Copyright (C) 2012,2013 Toni Gundogdu * * This file is part of libquvi . * @@ -24,8 +24,9 @@ gboolean l_chk_can_parse_url(lua_State*, _quvi_script_t, const gchar*, const gchar*, const gchar*); -gboolean l_chk_assign_s(lua_State*, const gchar*, GString*, gboolean); -gboolean l_chk_s(lua_State*, const gchar*, gchar**, gboolean); +gboolean l_chk_assign_s(lua_State*, const gchar*, GString*, gboolean, + gboolean); +gboolean l_chk_s(lua_State*, const gchar*, gchar**, gboolean, gboolean); gboolean l_chk_assign_n(lua_State*, const gchar*, gdouble*); gboolean l_chk_n(lua_State*, const gchar*, gdouble*); diff --git a/src/lua/exec_media_script_parse.c b/src/lua/exec_media_script_parse.c index 370bc56..9bb5313 100644 --- a/src/lua/exec_media_script_parse.c +++ b/src/lua/exec_media_script_parse.c @@ -52,7 +52,7 @@ static void _foreach_video_property(lua_State *l, _quvi_media_t qm, while (lua_next(l, LI_KEY)) { l_chk_assign_n(l, MSS_VIDEO_BITRATE_KBIT_S, &qms->video.bitrate_kbit_s); - l_chk_assign_s(l, MSS_VIDEO_ENCODING, qms->video.encoding, TRUE); + l_chk_assign_s(l, MSS_VIDEO_ENCODING, qms->video.encoding, TRUE, FALSE); l_chk_assign_n(l, MSS_VIDEO_HEIGHT, &qms->video.height); l_chk_assign_n(l, MSS_VIDEO_WIDTH, &qms->video.width); lua_pop(l, 1); @@ -66,7 +66,7 @@ static void _foreach_audio_property(lua_State *l, _quvi_media_t qm, while (lua_next(l, LI_KEY)) { l_chk_assign_n(l, MSS_AUDIO_BITRATE_KBIT_S, &qms->audio.bitrate_kbit_s); - l_chk_assign_s(l, MSS_AUDIO_ENCODING, qms->audio.encoding, TRUE); + l_chk_assign_s(l, MSS_AUDIO_ENCODING, qms->audio.encoding, TRUE, FALSE); lua_pop(l, 1); } } @@ -130,9 +130,9 @@ static _quvi_media_stream_t _new_stream(lua_State *l, _quvi_media_t qm, _chk_stream_sublevel(MSS_VIDEO, l, qm, qms, _foreach_video_property); _chk_stream_sublevel(MSS_AUDIO, l, qm, qms, _foreach_audio_property); _chk_stream_sublevel(MSS_FLAGS, l, qm, qms, _foreach_flag_property); - l_chk_assign_s(l, MSS_CONTAINER, qms->container, TRUE); - l_chk_assign_s(l, MSS_URL, qms->url, TRUE); - l_chk_assign_s(l, MSS_ID, qms->id, TRUE); + l_chk_assign_s(l, MSS_CONTAINER, qms->container, TRUE, FALSE); + l_chk_assign_s(l, MSS_URL, qms->url, TRUE, TRUE); + l_chk_assign_s(l, MSS_ID, qms->id, TRUE, FALSE); lua_pop(l, 1); } _has_stream_url(l, qms, script_path, i); @@ -219,9 +219,9 @@ static void _chk_optional(lua_State *l, _quvi_media_t qm) { l_chk_assign_n(l, MS_START_TIME_MS, &qm->start_time_ms); l_chk_assign_n(l, MS_DURATION_MS, &qm->duration_ms); - l_chk_assign_s(l, MS_THUMB_URL, qm->url.thumbnail, TRUE); - l_chk_assign_s(l, MS_TITLE, qm->title, TRUE); - l_chk_assign_s(l, MS_ID, qm->id, TRUE); + l_chk_assign_s(l, MS_THUMB_URL, qm->url.thumbnail, TRUE, TRUE); + l_chk_assign_s(l, MS_TITLE, qm->title, TRUE, FALSE); + l_chk_assign_s(l, MS_ID, qm->id, TRUE, FALSE); lua_pop(l, 1); } } @@ -232,7 +232,7 @@ static gboolean _chk_goto_instr(lua_State *l, _quvi_media_t qm) lua_pushnil(l); while (lua_next(l, LI_KEY)) { - l_chk_assign_s(l, MS_GOTO_URL, qm->url.redirect_to, TRUE); + l_chk_assign_s(l, MS_GOTO_URL, qm->url.redirect_to, TRUE, TRUE); lua_pop(l, 1); } return ((qm->url.redirect_to->len >0) ? TRUE:FALSE); diff --git a/src/lua/exec_playlist_script_parse.c b/src/lua/exec_playlist_script_parse.c index 6b85061..eb4c4c8 100644 --- a/src/lua/exec_playlist_script_parse.c +++ b/src/lua/exec_playlist_script_parse.c @@ -63,8 +63,8 @@ static gboolean _new_media(lua_State *l, _quvi_playlist_t qp, while (lua_next(l, LI_KEY)) /* For each qargs.media */ { l_chk_assign_n(l, PSM_DURATION_MS, &(*qpm)->duration_ms); - l_chk_assign_s(l, PSM_TITLE, (*qpm)->title, TRUE); - l_chk_assign_s(l, PSM_URL, (*qpm)->url, TRUE); + l_chk_assign_s(l, PSM_TITLE, (*qpm)->title, TRUE, FALSE); + l_chk_assign_s(l, PSM_URL, (*qpm)->url, TRUE, TRUE); lua_pop(l, 1); } @@ -122,9 +122,9 @@ static void _chk_optional(lua_State *l, _quvi_playlist_t qp) lua_pushnil(l); while (lua_next(l, LI_KEY)) { - l_chk_assign_s(l, PS_THUMB_URL, qp->url.thumbnail, TRUE); - l_chk_assign_s(l, PS_ID, qp->id.playlist, TRUE); - l_chk_assign_s(l, PS_TITLE, qp->title, TRUE); + l_chk_assign_s(l, PS_THUMB_URL, qp->url.thumbnail, TRUE, TRUE); + l_chk_assign_s(l, PS_ID, qp->id.playlist, TRUE, FALSE); + l_chk_assign_s(l, PS_TITLE, qp->title, TRUE, FALSE); lua_pop(l, 1); } } diff --git a/src/lua/exec_subtitle_export_script_export.c b/src/lua/exec_subtitle_export_script_export.c index cc35d1d..072609f 100644 --- a/src/lua/exec_subtitle_export_script_export.c +++ b/src/lua/exec_subtitle_export_script_export.c @@ -52,7 +52,7 @@ static QuviError _chk_result(lua_State *l, _quvi_subtitle_export_t qse, lua_pushnil(l); while (lua_next(l, LI_KEY)) { - l_chk_assign_s(l, SUES_DATA, qse->data, FALSE); + l_chk_assign_s(l, SUES_DATA, qse->data, FALSE, FALSE); lua_pop(l, 1); } diff --git a/src/lua/exec_subtitle_export_script_ident.c b/src/lua/exec_subtitle_export_script_ident.c index fc7d39c..2020efe 100644 --- a/src/lua/exec_subtitle_export_script_ident.c +++ b/src/lua/exec_subtitle_export_script_ident.c @@ -51,7 +51,7 @@ static QuviError _chk_results(lua_State *l, _quvi_script_t qs) lua_pushnil(l); while (lua_next(l, LI_KEY)) { - l_chk_assign_s(l, SUES_EXPORT_FORMAT, qs->export.format, TRUE); + l_chk_assign_s(l, SUES_EXPORT_FORMAT, qs->export.format, TRUE, FALSE); l_chk_assign_b(l, SUES_CAN_EXPORT_DATA, &r); lua_pop(l, 1); } diff --git a/src/lua/exec_subtitle_script_parse.c b/src/lua/exec_subtitle_script_parse.c index a3d7811..43d4d1f 100644 --- a/src/lua/exec_subtitle_script_parse.c +++ b/src/lua/exec_subtitle_script_parse.c @@ -130,11 +130,11 @@ static _quvi_subtitle_lang_t _new_lang(lua_State *l, const gchar *script_path, lua_pushnil(l); while (lua_next(l, LI_KEY)) { - l_chk_assign_s(l, SUSSL_TRANSLATED, qsl->translated, TRUE); - l_chk_assign_s(l, SUSSL_ORIGINAL, qsl->original, TRUE); - l_chk_assign_s(l, SUSSL_CODE, qsl->code, TRUE); - l_chk_assign_s(l, SUSSL_URL, qsl->url, TRUE); - l_chk_assign_s(l, SUSSL_ID, qsl->id, TRUE); + l_chk_assign_s(l, SUSSL_TRANSLATED, qsl->translated, TRUE, FALSE); + l_chk_assign_s(l, SUSSL_ORIGINAL, qsl->original, TRUE, FALSE); + l_chk_assign_s(l, SUSSL_CODE, qsl->code, TRUE, FALSE); + l_chk_assign_s(l, SUSSL_URL, qsl->url, TRUE, TRUE); + l_chk_assign_s(l, SUSSL_ID, qsl->id, TRUE, FALSE); lua_pop(l, 1); } return (_chk_url(l, script_path, qsl, i)); -- 2.11.4.GIT