From d191de856486174faec188ad142ef3ff1b347bd4 Mon Sep 17 00:00:00 2001 From: wm4 Date: Thu, 25 Sep 2014 23:38:23 +0200 Subject: stream_dvd: better .ifo probing stream_dvd.c includes a pseudo-protocol that recognizes .IFO files, and plays them using libdvdread. This was relatively lazy, and could perhaps easily trigger with files that just had the .ifo extension. Make the checks stricter, and even probe the file header. Apparently the first bytes in an .ifo file are always "DVDVIDEO-VTS", so check for this. Refuse to load the main "video_ts.ifo". The plan is to use stream_dvdnav for it. This also removes at least 1 memory leak. --- stream/stream_dvd.c | 42 ++++++++++++++++++++++-------------------- 1 file changed, 22 insertions(+), 20 deletions(-) (limited to 'stream/stream_dvd.c') diff --git a/stream/stream_dvd.c b/stream/stream_dvd.c index 857d144a65..eb055abc13 100644 --- a/stream/stream_dvd.c +++ b/stream/stream_dvd.c @@ -33,6 +33,8 @@ #include #include +#include "osdep/io.h" + #include "config.h" #include "talloc.h" #include "common/common.h" @@ -46,6 +48,7 @@ #include "stream.h" #include "options/m_option.h" #include "options/options.h" +#include "options/path.h" #include "stream_dvd_common.h" @@ -913,38 +916,37 @@ fail: return STREAM_UNSUPPORTED; } -static int ifo_stream_open (stream_t *stream) +static int ifo_stream_open(stream_t *stream) { - char* filename; dvd_priv_t *priv = talloc_ptrtype(stream, priv); stream->priv = priv; *priv = stream_priv_dflts; - // "file://" prefix -> decode URL-style escapes - if (strlen(stream->url) > strlen(stream->path)) - mp_url_unescape_inplace(stream->path); + char *path = mp_file_get_path(priv, bstr0(stream->url)); + if (!path) + goto unsupported; - int len = strlen(stream->path); - if (len < 4 || strcasecmp (stream->path + len - 4, ".ifo")) - return STREAM_UNSUPPORTED; + if (!dvd_probe(path, ".ifo", "DVDVIDEO-VTS")) + goto unsupported; - MP_INFO(stream, ".IFO detected. Redirecting to dvd://\n"); + char *base = mp_basename(path); - filename = strdup(basename(stream->path)); + // Only accept individual titles - use dvdnav for video_ts.ifo + if (strncasecmp(base, "vts_", 4)) + goto unsupported; - talloc_free(priv->cfg_device); - priv->cfg_device = talloc_strdup(NULL, dirname(stream->path)); - if(!strncasecmp(filename,"vts_",4)) - { - if(sscanf(filename+3, "_%02d_", &priv->cfg_title)!=0) - priv->cfg_title = 0; - }else - priv->cfg_title = 0; + if (sscanf(base + 3, "_%02d_", &priv->cfg_title) != 1) + goto unsupported; - free(filename); - stream->url=talloc_strdup(stream, "dvdread://"); + priv->cfg_device = bstrto0(priv, mp_dirname(path)); + MP_INFO(stream, ".IFO detected. Redirecting to dvdread://\n"); return open_s(stream); + +unsupported: + talloc_free(priv); + stream->priv = NULL; + return STREAM_UNSUPPORTED; } const stream_info_t stream_info_dvd = { -- cgit v1.2.3