From 1ad4a62336c2b6f02bc1968c91b877b6d4951c58 Mon Sep 17 00:00:00 2001 From: wm4 Date: Tue, 24 Mar 2015 21:29:09 +0100 Subject: demux: fix rar support for files containing DTS audio tracks With a recent cleanup, rar support was stuffed into demux_playlist.c (because "opening" rar files pretty much just lists archive contents and adds them to a playlist using a special rar:// protocol, which will actually access the rar file contents). Since demux_playlist.c is probed _after_ demux_lavf.c (and should/must be), libavformat was given the chance to detect DTS streams embedded within the rar file. This is not really what we want, and a regression what happened before rar listing was moved to demux_playlist.c. Fix it by moving the rar listing into its own pseudo-demuxer, and let ir probe before demux_lavf.c. (Yes, this feature still has users.) --- demux/demux.c | 2 ++ demux/demux_playlist.c | 26 --------------------- demux/demux_rar.c | 62 ++++++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 64 insertions(+), 26 deletions(-) create mode 100644 demux/demux_rar.c (limited to 'demux') diff --git a/demux/demux.c b/demux/demux.c index e9edac78f8..6790ba52c3 100644 --- a/demux/demux.c +++ b/demux/demux.c @@ -54,6 +54,7 @@ extern const demuxer_desc_t demuxer_desc_libass; extern const demuxer_desc_t demuxer_desc_subreader; extern const demuxer_desc_t demuxer_desc_playlist; extern const demuxer_desc_t demuxer_desc_disc; +extern const demuxer_desc_t demuxer_desc_rar; /* Please do not add any new demuxers here. If you want to implement a new * demuxer, add it to libavformat, except for wrappers around external @@ -72,6 +73,7 @@ const demuxer_desc_t *const demuxer_list[] = { &demuxer_desc_libass, #endif &demuxer_desc_matroska, + &demuxer_desc_rar, &demuxer_desc_lavf, &demuxer_desc_mf, &demuxer_desc_playlist, diff --git a/demux/demux_playlist.c b/demux/demux_playlist.c index 13f1fe6ac3..381b50f269 100644 --- a/demux/demux_playlist.c +++ b/demux/demux_playlist.c @@ -23,7 +23,6 @@ #include "common/playlist.h" #include "options/path.h" #include "stream/stream.h" -#include "stream/rar.h" #include "demux.h" #define PROBE_SIZE (8 * 1024) @@ -189,30 +188,6 @@ static int parse_pls(struct pl_parser *p) return 0; } -static int parse_rar(struct pl_parser *p) -{ - if (RarProbe(p->s)) - return -1; - if (p->probing) - return 0; - - int count; - rar_file_t **files; - if (RarParse(p->s, &count, &files)) - return -1; - - p->pl->disable_safety = true; // make it load rar:// - char *prefix = mp_url_escape(p, p->real_stream->url, "~|"); - for (int n = 0; n < count; n++) { - // stream_rar.c does the real work - playlist_add_file(p->pl, - talloc_asprintf(p, "rar://%s|%s", prefix, files[n]->name)); - RarFileDelete(files[n]); - } - talloc_free(files); - return 0; -} - static int parse_txt(struct pl_parser *p) { if (!p->force) @@ -245,7 +220,6 @@ static const struct pl_format formats[] = { {"mov", parse_mov_rtsptext}, {"pls", parse_pls, MIME_TYPES("audio/x-scpls")}, - {"rar", parse_rar}, {"txt", parse_txt}, }; diff --git a/demux/demux_rar.c b/demux/demux_rar.c new file mode 100644 index 0000000000..46311bce65 --- /dev/null +++ b/demux/demux_rar.c @@ -0,0 +1,62 @@ +/* + * This file is part of mpv. + * + * mpv is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * mpv is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with mpv. If not, see . + */ + +#include "common/common.h" +#include "common/playlist.h" +#include "stream/stream.h" +#include "stream/rar.h" +#include "demux.h" + +static int open_file(struct demuxer *demuxer, enum demux_check check) +{ + if (RarProbe(demuxer->stream)) + return -1; + + int count; + rar_file_t **files; + if (RarParse(demuxer->stream, &count, &files)) + return -1; + + void *tmp = talloc_new(NULL); + talloc_steal(tmp, files); + + struct playlist *pl = talloc_zero(demuxer, struct playlist); + demuxer->playlist = pl; + + // make it load rar:// + pl->disable_safety = true; + + char *prefix = mp_url_escape(tmp, demuxer->stream->url, "~|"); + for (int n = 0; n < count; n++) { + // stream_rar.c does the real work + playlist_add_file(pl, + talloc_asprintf(tmp, "rar://%s|%s", prefix, files[n]->name)); + RarFileDelete(files[n]); + } + + demuxer->filetype = "rar"; + demuxer->fully_read = true; + + talloc_free(tmp); + return 0; +} + +const struct demuxer_desc demuxer_desc_rar = { + .name = "rar", + .desc = "Rar archive file", + .open = open_file, +}; -- cgit v1.2.3