From: Rémi Bernon rbernon@codeweavers.com
--- dlls/mf/tests/h264-concat-streams.bin | Bin 0 -> 4552 bytes dlls/mf/tests/mf_test.h | 1 + dlls/mf/tests/resource.rc | 15 +++ dlls/mf/tests/transform.c | 173 ++++++++++++++++++++++++-- 4 files changed, 176 insertions(+), 13 deletions(-) create mode 100644 dlls/mf/tests/h264-concat-streams.bin
diff --git a/dlls/mf/tests/h264-concat-streams.bin b/dlls/mf/tests/h264-concat-streams.bin new file mode 100644 index 0000000000000000000000000000000000000000..dc356da7c485365a70bd65171593f471bd12d9e7 GIT binary patch literal 4552 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
literal 0 HcmV?d00001
diff --git a/dlls/mf/tests/mf_test.h b/dlls/mf/tests/mf_test.h index 0f23e2aeb02..05aa34e3d28 100644 --- a/dlls/mf/tests/mf_test.h +++ b/dlls/mf/tests/mf_test.h @@ -94,6 +94,7 @@ struct sample_desc const struct buffer_desc *buffers; DWORD repeat_count; BOOL todo_length; + BOOL todo_duration; LONGLONG todo_time; };
diff --git a/dlls/mf/tests/resource.rc b/dlls/mf/tests/resource.rc index e3df92e375f..fb0d0841f9b 100644 --- a/dlls/mf/tests/resource.rc +++ b/dlls/mf/tests/resource.rc @@ -63,6 +63,21 @@ mp3decdata.bin RCDATA mp3decdata.bin /* @makedep: h264data.bin */ h264data.bin RCDATA h264data.bin
+/* Generated with: + gst-launch-1.0 videotestsrc num-buffers=60 pattern=smpte100 ! \ + video/x-raw,format=I420,width=84,height=82,framerate=30000/1001 ! \ + videoflip method=clockwise ! videoconvert ! \ + x264enc ! filesink location=dlls/mf/tests/h264-concat-streams-001.bin + gst-launch-1.0 videotestsrc num-buffers=60 pattern=smpte100 ! \ + video/x-raw,format=I420,width=100,height=98,framerate=30000/1001 ! \ + videoflip method=clockwise ! videoconvert ! \ + x264enc ! filesink location=dlls/mf/tests/h264-concat-streams-002.bin + cat dlls/mf/tests/h264-concat-streams-001.bin dlls/mf/tests/h264-concat-streams-002.bin \ + >dlls/mf/tests/h264-concat-streams.bin +*/ +/* @makedep: h264-concat-streams.bin */ +h264-concat-streams.bin RCDATA h264-concat-streams.bin + /* Generated from running the tests on Windows */ /* @makedep: nv12frame.bmp */ nv12frame.bmp RCDATA nv12frame.bmp diff --git a/dlls/mf/tests/transform.c b/dlls/mf/tests/transform.c index b1ac3ffbb14..a47f9d50b62 100644 --- a/dlls/mf/tests/transform.c +++ b/dlls/mf/tests/transform.c @@ -1140,13 +1140,16 @@ static DWORD check_mf_media_buffer_(const char *file, int line, IMFMediaBuffer * todo_wine_if(expect->todo_length) ok_(file, line)(length == expect_length, "got length %#lx\n", length);
- if (*expect_data_len < length) - todo_wine_if(expect->todo_length) - ok_(file, line)(0, "missing %#lx bytes\n", length - *expect_data_len); - else if (!expect->compare) - diff = compare_bytes(data, &length, NULL, *expect_data); - else - diff = expect->compare(data, &length, &expect->rect, *expect_data); + if (*expect_data) + { + if (*expect_data_len < length) + todo_wine_if(expect->todo_length) + ok_(file, line)(0, "missing %#lx bytes\n", length - *expect_data_len); + else if (!expect->compare) + diff = compare_bytes(data, &length, NULL, *expect_data); + else + diff = expect->compare(data, &length, &expect->rect, *expect_data); + }
hr = IMFMediaBuffer_Unlock(buffer); ok_(file, line)(hr == S_OK, "Unlock returned %#lx\n", hr); @@ -1209,7 +1212,7 @@ static DWORD check_mf_sample_(const char *file, int line, IMFSample *sample, con timestamp = 0xdeadbeef; hr = IMFSample_GetSampleDuration(sample, ×tamp); ok_(file, line)(hr == S_OK, "GetSampleDuration returned %#lx\n", hr); - todo_wine_if(expect->todo_length) + todo_wine_if(expect->todo_duration && expect->todo_duration == timestamp) ok_(file, line)(llabs(timestamp - expect->sample_duration) <= 1, "got sample duration %I64d\n", timestamp);
@@ -1221,7 +1224,7 @@ static DWORD check_mf_sample_(const char *file, int line, IMFSample *sample, con todo_wine_if(expect->todo_length) ok_(file, line)(total_length == ctx.total_length, "got total length %#lx\n", total_length); - ok_(file, line)(*expect_data_len >= ctx.total_length, + ok_(file, line)(!*expect_data || *expect_data_len >= ctx.total_length, "missing %#lx data\n", ctx.total_length - *expect_data_len);
*expect_data = ctx.data; @@ -1243,10 +1246,10 @@ DWORD check_mf_sample_collection_(const char *file, int line, IMFCollection *sam DWORD count; HRESULT hr;
- load_resource(expect_data_filename, &ctx.data, &ctx.data_len); + if (expect_data_filename) load_resource(expect_data_filename, &ctx.data, &ctx.data_len); enum_mf_samples(samples, expect_samples, check_mf_sample_collection_enum, &ctx);
- dump_mf_sample_collection(samples, expect_samples, expect_data_filename); + if (expect_data_filename) dump_mf_sample_collection(samples, expect_samples, expect_data_filename);
hr = IMFCollection_GetElementCount(samples, &count); ok_(file, line)(hr == S_OK, "GetElementCount returned %#lx\n", hr); @@ -3159,7 +3162,7 @@ static void test_wma_decoder(void) }, { .attributes = output_sample_attributes + 1, /* not MFT_OUTPUT_DATA_BUFFER_INCOMPLETE */ - .sample_time = 2786394, .sample_duration = 464399, + .sample_time = 2786394, .sample_duration = 464399, .todo_duration = 928798, .buffer_count = 1, .buffers = output_buffer_desc + 1, .todo_length = TRUE, }, }; @@ -4016,6 +4019,149 @@ failed: CoUninitialize(); }
+static void test_h264_decoder_concat_streams(void) +{ + const struct buffer_desc output_buffer_desc[] = + { + {.length = 0x3600}, + {.length = 0x3600, .todo_length = TRUE}, + {.length = 0x4980}, + }; + const struct attribute_desc output_sample_attributes[] = + { + ATTR_UINT32(MFSampleExtension_CleanPoint, 1), + {0}, + }; + const struct sample_desc output_sample_desc[] = + { + { + .attributes = output_sample_attributes + 0, + .sample_time = 0, .sample_duration = 333667, + .buffer_count = 1, .buffers = output_buffer_desc + 0, .repeat_count = 57, + }, + { + .attributes = output_sample_attributes + 0, + .sample_time = 19352666, .sample_duration = 333667, + .buffer_count = 1, .buffers = output_buffer_desc + 1, .repeat_count = 1, + .todo_length = TRUE, + }, + { + .attributes = output_sample_attributes + 0, + .sample_time = 60 * 333667, .sample_duration = 333667, + .buffer_count = 1, .buffers = output_buffer_desc + 2, .repeat_count = 59, + }, + }; + + const BYTE *h264_encoded_data; + IMFCollection *output_samples; + ULONG h264_encoded_data_len; + DWORD output_status, count; + IMFAttributes *attributes; + IMFMediaType *media_type; + IMFTransform *transform; + IMFSample *input_sample; + HRESULT hr; + LONG ret; + + hr = CoInitialize(NULL); + ok(hr == S_OK, "Failed to initialize, hr %#lx.\n", hr); + + if (FAILED(hr = CoCreateInstance(&CLSID_MSH264DecoderMFT, NULL, CLSCTX_INPROC_SERVER, + &IID_IMFTransform, (void **)&transform))) + goto failed; + ok(hr == S_OK, "hr %#lx\n", hr); + + hr = IMFTransform_GetAttributes(transform, &attributes); + ok(hr == S_OK, "GetAttributes returned %#lx\n", hr); + hr = IMFAttributes_SetUINT32(attributes, &MF_LOW_LATENCY, 1); + ok(hr == S_OK, "SetUINT32 returned %#lx\n", hr); + IMFAttributes_Release(attributes); + + hr = IMFTransform_GetInputAvailableType(transform, 0, 0, &media_type); + ok(hr == S_OK, "got %#lx\n", hr); + hr = IMFTransform_SetInputType(transform, 0, media_type, 0); + ok(hr == S_OK, "got %#lx\n", hr); + IMFMediaType_Release(media_type); + + hr = IMFTransform_GetOutputAvailableType(transform, 0, 0, &media_type); + ok(hr == S_OK, "got %#lx\n", hr); + hr = IMFTransform_SetOutputType(transform, 0, media_type, 0); + ok(hr == S_OK, "got %#lx\n", hr); + IMFMediaType_Release(media_type); + + load_resource(L"h264-concat-streams.bin", &h264_encoded_data, &h264_encoded_data_len); + + hr = MFCreateCollection(&output_samples); + ok(hr == S_OK, "MFCreateCollection returned %#lx\n", hr); + + input_sample = next_h264_sample(&h264_encoded_data, &h264_encoded_data_len); + while (input_sample) + { + MFT_OUTPUT_STREAM_INFO info = {0}; + + hr = IMFTransform_ProcessInput(transform, 0, input_sample, 0); + ok(hr == S_OK || hr == MF_E_NOTACCEPTING, "ProcessInput returned %#lx\n", hr); + + if (hr == S_OK) + { + IMFSample_Release(input_sample); + + if (h264_encoded_data_len > 4) + input_sample = next_h264_sample(&h264_encoded_data, &h264_encoded_data_len); + else + { + hr = IMFTransform_ProcessMessage(transform, MFT_MESSAGE_COMMAND_DRAIN, 0); + ok(hr == S_OK, "ProcessMessage returned %#lx\n", hr); + input_sample = NULL; + } + } + + hr = IMFTransform_GetOutputStreamInfo(transform, 0, &info); + ok(hr == S_OK, "GetOutputStreamInfo returned %#lx\n", hr); + + while (hr != MF_E_TRANSFORM_NEED_MORE_INPUT) + { + MFT_OUTPUT_DATA_BUFFER data = {.pSample = create_sample(NULL, info.cbSize)}; + + hr = IMFTransform_ProcessOutput(transform, 0, 1, &data, &output_status); + todo_wine_if(hr == 0xd0000001) + ok(hr == S_OK || hr == MF_E_TRANSFORM_NEED_MORE_INPUT || hr == MF_E_TRANSFORM_STREAM_CHANGE, + "ProcessOutput returned %#lx\n", hr); + + if (hr == S_OK) + { + hr = IMFCollection_AddElement(output_samples, (IUnknown *)data.pSample); + ok(hr == S_OK, "AddElement returned %#lx\n", hr); + } + if (hr == MF_E_TRANSFORM_STREAM_CHANGE) + { + hr = IMFTransform_GetOutputAvailableType(transform, 0, 0, &media_type); + ok(hr == S_OK, "GetOutputAvailableType returned %#lx\n", hr); + hr = IMFTransform_SetOutputType(transform, 0, media_type, 0); + ok(hr == S_OK, "SetOutputType returned %#lx\n", hr); + hr = IMFTransform_GetOutputStreamInfo(transform, 0, &info); + ok(hr == S_OK, "GetOutputStreamInfo returned %#lx\n", hr); + } + + IMFSample_Release(data.pSample); + } + } + + hr = IMFCollection_GetElementCount(output_samples, &count); + ok(hr == S_OK, "GetElementCount returned %#lx\n", hr); + todo_wine + ok(count >= 0x77, "GetElementCount returned %#lx\n", count); + + ret = check_mf_sample_collection(output_samples, output_sample_desc, NULL); + ok(ret == 0, "got %lu%% diff\n", ret); + + ret = IMFTransform_Release(transform); + ok(ret == 0, "Release returned %lu\n", ret); + +failed: + CoUninitialize(); +} + static void test_audio_convert(void) { const GUID *const class_id = &CLSID_CResamplerMediaObject; @@ -4180,7 +4326,7 @@ static void test_audio_convert(void) }, { .attributes = output_sample_attributes + 1, /* not MFT_OUTPUT_DATA_BUFFER_INCOMPLETE */ - .sample_time = 9287980, .sample_duration = 897506, + .sample_time = 9287980, .sample_duration = 897506, .todo_duration = 897280, .buffer_count = 1, .buffers = output_buffer_desc + 1, .todo_length = TRUE, }, { @@ -7691,4 +7837,5 @@ START_TEST(transform) test_iv50_decoder();
test_h264_with_dxgi_manager(); + test_h264_decoder_concat_streams(); }