diff --git a/NEWS.md b/NEWS.md index 1216e6b22..282e21930 100644 --- a/NEWS.md +++ b/NEWS.md @@ -31,6 +31,8 @@ attached files. Fixes #2001. * mkvmerge: MP4 reader: MPEG-1/2 video read from MP4 files was written with an invalid codec ID (e.g. `V_MPEG7`) in certain cases. Fixes #1995. +* mkvmerge: MPEG PS reader: made the file type detection less strict so that + garbage at the start of the file doesn't prevent detection. Fixes #2008. # Version 12.0.0 "Trust / Lust" 2017-05-20 diff --git a/src/input/r_mpeg_ps.cpp b/src/input/r_mpeg_ps.cpp index 0ea2032b7..81de28ca4 100644 --- a/src/input/r_mpeg_ps.cpp +++ b/src/input/r_mpeg_ps.cpp @@ -47,10 +47,36 @@ mpeg_ps_reader_c::probe_file(mm_io_c *in, if (in->read(buf, 4) != 4) return 0; - if (get_uint32_be(buf) != MPEGVIDEO_PACKET_START_CODE) + if (get_uint32_be(buf) == MPEGVIDEO_PACKET_START_CODE) + return 1; + + in->setFilePointer(0, seek_beginning); + + auto mem = memory_c::alloc(32 * 1024); + auto num_read = in->read(mem, mem->get_size()); + + if (num_read < 4) return 0; - return 1; + auto base = mem->get_buffer(); + auto code = get_uint32_be(base); + auto offset = 2u; + auto system_header_start_code_found = false; + auto packet_start_code_found = false; + + while( ((offset + 4) < num_read) + && (!system_header_start_code_found || !packet_start_code_found)) { + ++offset; + code = (code << 8) | base[offset]; + + if (code == MPEGVIDEO_SYSTEM_HEADER_START_CODE) + system_header_start_code_found = true; + + else if (code == MPEGVIDEO_PACKET_START_CODE) + packet_start_code_found = true; + } + + return system_header_start_code_found && packet_start_code_found; } catch (...) { return 0; diff --git a/tests/results.txt b/tests/results.txt index 8cc8c88e9..79aa3a6e3 100644 --- a/tests/results.txt +++ b/tests/results.txt @@ -447,3 +447,4 @@ T_598aac_track_not_listed_in_pmt:444929dd4db38e68b59a3ebf833e5128-AAC:passed:201 T_599mp4_nclx_colour_type_in_colr_atom:3639a6fdf7a0e46d158188fdd932bd2b:passed:20170514-203828:0.018287634 T_600mpeg_ts_multiple_programs:890b456227714da673b137a941bf45b2-2a728cb7e28e2b05e8784aa8fd6f6827-d78702c82db3e49891717626ad0fb9fb-a210b7b90d61e14c7d5a5d97253f1bc2:passed:20170522-193901:1.342170107 T_601mp4_mpeg2_via_esds:5cadaf9b8dd86a51052182ed341a4bc0:passed:20170618-150319:0.386032567 +T_602vob_with_garbage_at_start:9ea25678a9a2746f9cb9bae8e73c766d:passed:20170619-185256:0.236132323 diff --git a/tests/test-602vob_with_garbage_at_start.rb b/tests/test-602vob_with_garbage_at_start.rb new file mode 100755 index 000000000..ebb80b1d7 --- /dev/null +++ b/tests/test-602vob_with_garbage_at_start.rb @@ -0,0 +1,5 @@ +#!/usr/bin/ruby -w + +# T_602vob_with_garbage_at_start +describe "mkvmerge / VOB with garbage at the beginning" +test_identify "data/vob/starts_with_garbage.vob"