vlc | branch: master | Francois Cartegnie <[email protected]> | Tue Apr 23 14:34:37 2019 +0200| [dfe4aca1f22265115e07c501a77c870cfea4cd52] | committer: Francois Cartegnie
demux: hls: probe content Solves issues when the server does not sends proper MIME and the file does not match known extension. > http://git.videolan.org/gitweb.cgi/vlc.git/?a=commit;h=dfe4aca1f22265115e07c501a77c870cfea4cd52 --- modules/demux/adaptive/StreamFormat.cpp | 22 +++++++++++++++++++++- modules/demux/adaptive/StreamFormat.hpp | 2 ++ modules/demux/adaptive/plumbing/Demuxer.cpp | 15 +++++++++++++-- 3 files changed, 36 insertions(+), 3 deletions(-) diff --git a/modules/demux/adaptive/StreamFormat.cpp b/modules/demux/adaptive/StreamFormat.cpp index c5f027df59..9a695c3c34 100644 --- a/modules/demux/adaptive/StreamFormat.cpp +++ b/modules/demux/adaptive/StreamFormat.cpp @@ -23,6 +23,8 @@ #endif #include "StreamFormat.hpp" + +#include <vlc_common.h> #include <algorithm> using namespace adaptive; @@ -66,7 +68,7 @@ StreamFormat::StreamFormat( const std::string &mimetype ) std::string mime = mimetype; std::transform(mime.begin(), mime.end(), mime.begin(), ::tolower); std::string::size_type pos = mime.find("/"); - formatid = UNSUPPORTED; + formatid = UNKNOWN; if(pos != std::string::npos) { std::string tail = mime.substr(pos + 1); @@ -83,6 +85,24 @@ StreamFormat::StreamFormat( const std::string &mimetype ) } } +StreamFormat::StreamFormat(const void *data_, size_t sz) +{ + const uint8_t *data = reinterpret_cast<const uint8_t *>(data_); + formatid = UNKNOWN; + const char moov[] = "ftypmoovmoof"; + if(sz > 188 && data[0] == 0x47 && data[188] == 0x47) + formatid = StreamFormat::MPEG2TS; + else if(sz > 4 && (!memcmp(&moov, data, 4) || + !memcmp(&moov[4], data, 4) || + !memcmp(&moov[8], data, 4))) + formatid = StreamFormat::MP4; + else if(sz > 7 && !memcmp("WEBVTT", data, 6) && + std::isspace(static_cast<unsigned char>(data[7]))) + formatid = StreamFormat::WEBVTT; + else if(sz > 4 && !memcmp(".Eߣ", data, 4)) + formatid = StreamFormat::WEBM; +} + StreamFormat::~StreamFormat() { diff --git a/modules/demux/adaptive/StreamFormat.hpp b/modules/demux/adaptive/StreamFormat.hpp index 62b4865a38..db70a53753 100644 --- a/modules/demux/adaptive/StreamFormat.hpp +++ b/modules/demux/adaptive/StreamFormat.hpp @@ -36,9 +36,11 @@ namespace adaptive static const unsigned PACKEDAAC = 5; static const unsigned WEBM = 6; static const unsigned UNKNOWN = 0xFF; /* will probe */ + static const unsigned PEEK_SIZE = 189; StreamFormat( unsigned = UNSUPPORTED ); explicit StreamFormat( const std::string &mime ); + StreamFormat( const void *, size_t ); ~StreamFormat(); operator unsigned() const; std::string str() const; diff --git a/modules/demux/adaptive/plumbing/Demuxer.cpp b/modules/demux/adaptive/plumbing/Demuxer.cpp index 3b6772e233..346d79f79a 100644 --- a/modules/demux/adaptive/plumbing/Demuxer.cpp +++ b/modules/demux/adaptive/plumbing/Demuxer.cpp @@ -100,13 +100,24 @@ bool MimeDemuxer::create() if(!p_newstream) return false; + StreamFormat format; char *type = stream_ContentType(p_newstream); if(type) { - demuxer = factory->newDemux( p_realdemux, StreamFormat(std::string(type)), - p_es_out, sourcestream ); + format = StreamFormat(std::string(type)); free(type); } + /* Try to probe */ + if(format == StreamFormat(StreamFormat::UNKNOWN)) + { + const uint8_t *p_peek; + size_t i_peek = sourcestream->Peek(&p_peek, StreamFormat::PEEK_SIZE); + format = StreamFormat(reinterpret_cast<const void *>(p_peek), i_peek); + } + + if(format != StreamFormat(StreamFormat::UNKNOWN)) + demuxer = factory->newDemux(p_realdemux, format, p_es_out, sourcestream); + vlc_stream_Delete(p_newstream); if(!demuxer || !demuxer->create()) _______________________________________________ vlc-commits mailing list [email protected] https://mailman.videolan.org/listinfo/vlc-commits
