[PATCH v3 0/7] MR10549: iyuv_32: Implement Decompression
This MR adds I420 "decompression" functionality to the `iyuv_32.dll`. -- v3: iyuv_32: Implement IYUV_Decompress. iyuv_32: Implement IYUV_DecompressBegin. iyuv_32: Implement IYUV_Open. iyuv_32: Implement IYUV_DecompressGetFormat. iyuv_32: Implement IYUV_DecompressQuery. iyuv_32: Implement IYUV_GetInfo. winegstreamer: Add winegstreamer_create_color_converter. https://gitlab.winehq.org/wine/wine/-/merge_requests/10549
From: Brendan McGrath <bmcgrath@codeweavers.com> This is a exported function that wraps the color_convert_create function. --- dlls/winegstreamer/color_convert.c | 16 ++++++++++++++++ dlls/winegstreamer/winegstreamer.spec | 1 + 2 files changed, 17 insertions(+) diff --git a/dlls/winegstreamer/color_convert.c b/dlls/winegstreamer/color_convert.c index 697cd6fcd4c..5d9e5f1c0a9 100644 --- a/dlls/winegstreamer/color_convert.c +++ b/dlls/winegstreamer/color_convert.c @@ -1038,3 +1038,19 @@ HRESULT color_convert_create(IUnknown *outer, IUnknown **out) TRACE("Created %p\n", *out); return S_OK; } + +HRESULT WINAPI winegstreamer_create_color_converter(IMFTransform **out) +{ + IUnknown *unknown; + HRESULT hr; + + TRACE("out %p.\n", out); + + if (!init_gstreamer()) + return E_FAIL; + + if (FAILED(hr = color_convert_create(NULL, &unknown))) + return hr; + + return IUnknown_QueryInterface(unknown, &IID_IMFTransform, (void**)out); +} diff --git a/dlls/winegstreamer/winegstreamer.spec b/dlls/winegstreamer/winegstreamer.spec index 095f75a0865..69eed004b78 100644 --- a/dlls/winegstreamer/winegstreamer.spec +++ b/dlls/winegstreamer/winegstreamer.spec @@ -4,3 +4,4 @@ @ stdcall -private DllUnregisterServer() @ stdcall winegstreamer_create_wm_sync_reader(ptr ptr) @ stdcall winegstreamer_create_video_decoder(ptr) +@ stdcall winegstreamer_create_color_converter(ptr) -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10549
From: Brendan McGrath <bmcgrath@codeweavers.com> --- dlls/iyuv_32/Makefile.in | 3 ++- dlls/iyuv_32/iyuv.c | 26 +++++++++++++++++++++++--- dlls/iyuv_32/iyuv_32.rc | 29 +++++++++++++++++++++++++++++ dlls/iyuv_32/iyuv_private.h | 27 +++++++++++++++++++++++++++ 4 files changed, 81 insertions(+), 4 deletions(-) create mode 100644 dlls/iyuv_32/iyuv_32.rc create mode 100644 dlls/iyuv_32/iyuv_private.h diff --git a/dlls/iyuv_32/Makefile.in b/dlls/iyuv_32/Makefile.in index 6b9b11569b1..c386ec9b924 100644 --- a/dlls/iyuv_32/Makefile.in +++ b/dlls/iyuv_32/Makefile.in @@ -2,4 +2,5 @@ MODULE = iyuv_32.dll IMPORTS = user32 mfplat ole32 SOURCES = \ - iyuv.c + iyuv.c \ + iyuv_32.rc diff --git a/dlls/iyuv_32/iyuv.c b/dlls/iyuv_32/iyuv.c index e114fde50e0..c4899c64652 100644 --- a/dlls/iyuv_32/iyuv.c +++ b/dlls/iyuv_32/iyuv.c @@ -31,19 +31,23 @@ #include "vfw.h" #include "wmcodecdsp.h" +#include "iyuv_private.h" #include "wine/debug.h" #define COBJMACROS #include "mfapi.h" #include "mferror.h" -#include "mfobjects.h" #include "mfidl.h" +#include "mfobjects.h" #include "mftransform.h" WINE_DEFAULT_DEBUG_CHANNEL(iyuv_32); static HINSTANCE IYUV_32_module; +#define FOURCC_IYUV mmioFOURCC('I', 'Y', 'U', 'V') +#define IYUV_MAGIC FOURCC_IYUV + static LRESULT IYUV_Open(const ICINFO *icinfo) { FIXME("DRV_OPEN %p\n", icinfo); @@ -81,9 +85,25 @@ static LRESULT IYUV_Decompress(IMFTransform *transform, const ICDECOMPRESS *para static LRESULT IYUV_GetInfo(ICINFO *icinfo, DWORD size) { - FIXME("ICM_GETINFO %p %lu\n", icinfo, size); + TRACE("ICM_GETINFO %p %lu\n", icinfo, size); - return ICERR_UNSUPPORTED; + if (!icinfo) + return sizeof(ICINFO); + if (size < sizeof(ICINFO)) + return 0; + + icinfo->dwSize = sizeof(ICINFO); + icinfo->fccType = ICTYPE_VIDEO; + icinfo->fccHandler = IYUV_MAGIC; + icinfo->dwFlags = 0; + icinfo->dwVersion = 0; + icinfo->dwVersionICM = ICVERSION; + + LoadStringW(IYUV_32_module, IDS_NAME, icinfo->szName, ARRAY_SIZE(icinfo->szName)); + LoadStringW(IYUV_32_module, IDS_DESCRIPTION, icinfo->szDescription, ARRAY_SIZE(icinfo->szDescription)); + /* msvfw32 will fill icinfo->szDriver for us */ + + return sizeof(ICINFO); } /*********************************************************************** diff --git a/dlls/iyuv_32/iyuv_32.rc b/dlls/iyuv_32/iyuv_32.rc new file mode 100644 index 00000000000..a9705a2bd76 --- /dev/null +++ b/dlls/iyuv_32/iyuv_32.rc @@ -0,0 +1,29 @@ +/* + * Copyright 2026 Brendan McGrath for CodeWeavers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +#include "iyuv_private.h" + +#pragma makedep po + +LANGUAGE LANG_ENGLISH, SUBLANG_DEFAULT + +STRINGTABLE +{ + IDS_NAME "IYUV codec" + IDS_DESCRIPTION "IYUV codec" +} diff --git a/dlls/iyuv_32/iyuv_private.h b/dlls/iyuv_32/iyuv_private.h new file mode 100644 index 00000000000..cf2d392dc44 --- /dev/null +++ b/dlls/iyuv_32/iyuv_private.h @@ -0,0 +1,27 @@ +/* + * Copyright 2026 Brendan McGrath for CodeWeavers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +#ifndef __IYUV_PRIVATE_H +#define __IYUV_PRIVATE_H + +#include "windef.h" + +#define IDS_NAME 100 +#define IDS_DESCRIPTION 101 + +#endif /* __IYUV_PRIVATE_H */ -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10549
From: Brendan McGrath <bmcgrath@codeweavers.com> --- dlls/iyuv_32/iyuv.c | 43 +++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 41 insertions(+), 2 deletions(-) diff --git a/dlls/iyuv_32/iyuv.c b/dlls/iyuv_32/iyuv.c index c4899c64652..3c2528fde52 100644 --- a/dlls/iyuv_32/iyuv.c +++ b/dlls/iyuv_32/iyuv.c @@ -45,9 +45,12 @@ WINE_DEFAULT_DEBUG_CHANNEL(iyuv_32); static HINSTANCE IYUV_32_module; +#define FOURCC_I420 mmioFOURCC('I', '4', '2', '0') #define FOURCC_IYUV mmioFOURCC('I', 'Y', 'U', 'V') #define IYUV_MAGIC FOURCC_IYUV +#define compare_fourcc(fcc1, fcc2) (((fcc1) ^ (fcc2)) & ~0x20202020) + static LRESULT IYUV_Open(const ICINFO *icinfo) { FIXME("DRV_OPEN %p\n", icinfo); @@ -57,9 +60,45 @@ static LRESULT IYUV_Open(const ICINFO *icinfo) static LRESULT IYUV_DecompressQuery(const BITMAPINFOHEADER *in, const BITMAPINFOHEADER *out) { - FIXME("ICM_DECOMPRESS_QUERY %p %p\n", in, out); + TRACE("in->planes = %d\n", in->biPlanes); + TRACE("in->bpp = %d\n", in->biBitCount); + TRACE("in->height = %ld\n", in->biHeight); + TRACE("in->width = %ld\n", in->biWidth); + TRACE("in->compr = %#lx\n", in->biCompression); - return ICERR_UNSUPPORTED; + if (compare_fourcc(in->biCompression, FOURCC_I420) && compare_fourcc(in->biCompression, FOURCC_IYUV)) + { + TRACE("can't do %#lx decompression\n", in->biCompression); + return ICERR_BADFORMAT; + } + + if (!in->biHeight || !in->biWidth) + return ICERR_BADFORMAT; + + /* output must be same dimensions as input */ + if (out) + { + TRACE("out->planes = %d\n", out->biPlanes); + TRACE("out->bpp = %d\n", out->biBitCount); + TRACE("out->height = %ld\n", out->biHeight); + TRACE("out->width = %ld\n", out->biWidth); + TRACE("out->compr = %#lx\n", out->biCompression); + + if (out->biCompression == BI_RGB) + { + if (out->biBitCount != 24 && out->biBitCount != 16 && out->biBitCount != 8) + return ICERR_BADFORMAT; + } + else + { + return ICERR_BADFORMAT; + } + + if (in->biWidth != out->biWidth || in->biHeight != out->biHeight) + return ICERR_BADFORMAT; + } + + return ICERR_OK; } static LRESULT IYUV_DecompressGetFormat(BITMAPINFOHEADER *in, BITMAPINFOHEADER *out) -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10549
From: Brendan McGrath <bmcgrath@codeweavers.com> --- dlls/iyuv_32/iyuv.c | 20 ++++++++++++++++++-- 1 file changed, 18 insertions(+), 2 deletions(-) diff --git a/dlls/iyuv_32/iyuv.c b/dlls/iyuv_32/iyuv.c index 3c2528fde52..ac169067666 100644 --- a/dlls/iyuv_32/iyuv.c +++ b/dlls/iyuv_32/iyuv.c @@ -103,9 +103,25 @@ static LRESULT IYUV_DecompressQuery(const BITMAPINFOHEADER *in, const BITMAPINFO static LRESULT IYUV_DecompressGetFormat(BITMAPINFOHEADER *in, BITMAPINFOHEADER *out) { - FIXME("ICM_DECOMPRESS_GETFORMAT %p %p\n", in, out); + TRACE("ICM_DECOMPRESS_GETFORMAT %p %p\n", in, out); - return ICERR_UNSUPPORTED; + if (compare_fourcc(in->biCompression, FOURCC_I420) && compare_fourcc(in->biCompression, FOURCC_IYUV)) + return ICERR_BADFORMAT; + + if (out) + { + memset(out, 0, sizeof(*out)); + out->biSize = sizeof(BITMAPINFOHEADER); + out->biWidth = in->biWidth; + out->biHeight = abs(in->biHeight); + out->biCompression = BI_RGB; + out->biPlanes = 1; + out->biBitCount = 24; + out->biSizeImage = out->biWidth * out->biHeight * 3; + return ICERR_OK; + } + + return sizeof(*out); } static LRESULT IYUV_DecompressBegin(IMFTransform *transform, const BITMAPINFOHEADER *in, const BITMAPINFOHEADER *out) -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10549
From: Brendan McGrath <bmcgrath@codeweavers.com> --- dlls/iyuv_32/Makefile.in | 2 +- dlls/iyuv_32/iyuv.c | 17 ++++++++++------- dlls/iyuv_32/iyuv_private.h | 6 ++++++ dlls/iyuv_32/tests/iyuv_32.c | 3 --- 4 files changed, 17 insertions(+), 11 deletions(-) diff --git a/dlls/iyuv_32/Makefile.in b/dlls/iyuv_32/Makefile.in index c386ec9b924..e5a261b973f 100644 --- a/dlls/iyuv_32/Makefile.in +++ b/dlls/iyuv_32/Makefile.in @@ -1,5 +1,5 @@ MODULE = iyuv_32.dll -IMPORTS = user32 mfplat ole32 +IMPORTS = user32 mfplat ole32 winegstreamer SOURCES = \ iyuv.c \ diff --git a/dlls/iyuv_32/iyuv.c b/dlls/iyuv_32/iyuv.c index ac169067666..87c52a5975c 100644 --- a/dlls/iyuv_32/iyuv.c +++ b/dlls/iyuv_32/iyuv.c @@ -34,12 +34,7 @@ #include "iyuv_private.h" #include "wine/debug.h" -#define COBJMACROS -#include "mfapi.h" #include "mferror.h" -#include "mfidl.h" -#include "mfobjects.h" -#include "mftransform.h" WINE_DEFAULT_DEBUG_CHANNEL(iyuv_32); @@ -53,9 +48,17 @@ static HINSTANCE IYUV_32_module; static LRESULT IYUV_Open(const ICINFO *icinfo) { - FIXME("DRV_OPEN %p\n", icinfo); + IMFTransform *transform; - return 0; + TRACE("DRV_OPEN %p\n", icinfo); + + if (icinfo && compare_fourcc(icinfo->fccType, ICTYPE_VIDEO)) + return 0; + + if (FAILED(winegstreamer_create_color_converter(&transform))) + transform = NULL; + + return (LRESULT)transform; } static LRESULT IYUV_DecompressQuery(const BITMAPINFOHEADER *in, const BITMAPINFOHEADER *out) diff --git a/dlls/iyuv_32/iyuv_private.h b/dlls/iyuv_32/iyuv_private.h index cf2d392dc44..694f89799d5 100644 --- a/dlls/iyuv_32/iyuv_private.h +++ b/dlls/iyuv_32/iyuv_private.h @@ -21,6 +21,12 @@ #include "windef.h" +#define COBJMACROS +#include "mfapi.h" +#include "mftransform.h" + +HRESULT WINAPI winegstreamer_create_color_converter(IMFTransform **out); + #define IDS_NAME 100 #define IDS_DESCRIPTION 101 diff --git a/dlls/iyuv_32/tests/iyuv_32.c b/dlls/iyuv_32/tests/iyuv_32.c index 97572411e6e..1de936ac7ed 100644 --- a/dlls/iyuv_32/tests/iyuv_32.c +++ b/dlls/iyuv_32/tests/iyuv_32.c @@ -456,10 +456,7 @@ START_TEST(iyuv_32) int i; hic = ICLocate(ICTYPE_VIDEO, FOURCC_I420, &in, NULL, ICMODE_DECOMPRESS); - todo_wine ok(!!hic, "Failed to locate iyuv codec\n"); - if (!hic) - return; ICClose(hic); for (i = 0; i < ARRAY_SIZE(handler); i++) -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10549
From: Brendan McGrath <bmcgrath@codeweavers.com> --- dlls/iyuv_32/iyuv.c | 61 ++++++++++++++++++++++++++++++++++-- dlls/iyuv_32/tests/iyuv_32.c | 6 ---- 2 files changed, 59 insertions(+), 8 deletions(-) diff --git a/dlls/iyuv_32/iyuv.c b/dlls/iyuv_32/iyuv.c index 87c52a5975c..bd7265bc447 100644 --- a/dlls/iyuv_32/iyuv.c +++ b/dlls/iyuv_32/iyuv.c @@ -46,6 +46,11 @@ static HINSTANCE IYUV_32_module; #define compare_fourcc(fcc1, fcc2) (((fcc1) ^ (fcc2)) & ~0x20202020) +static inline UINT64 make_uint64(UINT32 high, UINT32 low) +{ + return ((UINT64)high << 32) | low; +} + static LRESULT IYUV_Open(const ICINFO *icinfo) { IMFTransform *transform; @@ -129,9 +134,61 @@ static LRESULT IYUV_DecompressGetFormat(BITMAPINFOHEADER *in, BITMAPINFOHEADER * static LRESULT IYUV_DecompressBegin(IMFTransform *transform, const BITMAPINFOHEADER *in, const BITMAPINFOHEADER *out) { - FIXME("ICM_DECOMPRESS_BEGIN %p %p %p\n", transform, in, out); + IMFMediaType *input_type, *output_type; + LRESULT r = ICERR_INTERNAL; + const GUID *output_subtype; + LONG stride, depth; + + TRACE("transform %p, in %p, out %p.\n", transform, in, out); + + if (!transform) + return ICERR_BADPARAM; + + if (out->biBitCount == 24) + output_subtype = &MFVideoFormat_RGB24; + else if (out->biBitCount == 16) + output_subtype = &MFVideoFormat_RGB555; + else if (out->biBitCount == 8) + output_subtype = &MFVideoFormat_RGB8; + else + return ICERR_BADFORMAT; - return ICERR_UNSUPPORTED; + depth = out->biBitCount / 8; + stride = -((out->biWidth * depth + 3) & ~3); + + if (FAILED(MFCreateMediaType(&input_type))) + return ICERR_INTERNAL; + + if (FAILED(MFCreateMediaType(&output_type))) + { + IMFMediaType_Release(input_type); + return ICERR_INTERNAL; + } + + if (FAILED(IMFMediaType_SetGUID(input_type, &MF_MT_MAJOR_TYPE, &MFMediaType_Video)) || + FAILED(IMFMediaType_SetGUID(input_type, &MF_MT_SUBTYPE, &MFVideoFormat_I420))) + goto done; + if (FAILED(IMFMediaType_SetUINT64(input_type, &MF_MT_FRAME_SIZE, make_uint64(in->biWidth, in->biHeight)))) + goto done; + + if (FAILED(IMFMediaType_SetGUID(output_type, &MF_MT_MAJOR_TYPE, &MFMediaType_Video)) || + FAILED(IMFMediaType_SetGUID(output_type, &MF_MT_SUBTYPE, output_subtype))) + goto done; + if (FAILED(IMFMediaType_SetUINT64(output_type, &MF_MT_FRAME_SIZE, make_uint64(out->biWidth, out->biHeight)))) + goto done; + if (FAILED(IMFMediaType_SetUINT32(output_type, &MF_MT_DEFAULT_STRIDE, stride))) + goto done; + + if (FAILED(IMFTransform_SetInputType(transform, 0, input_type, 0)) || + FAILED(IMFTransform_SetOutputType(transform, 0, output_type, 0))) + goto done; + + r = ICERR_OK; + +done: + IMFMediaType_Release(input_type); + IMFMediaType_Release(output_type); + return r; } static LRESULT IYUV_Decompress(IMFTransform *transform, const ICDECOMPRESS *params) diff --git a/dlls/iyuv_32/tests/iyuv_32.c b/dlls/iyuv_32/tests/iyuv_32.c index 1de936ac7ed..cc8edca386b 100644 --- a/dlls/iyuv_32/tests/iyuv_32.c +++ b/dlls/iyuv_32/tests/iyuv_32.c @@ -269,7 +269,6 @@ static void test_formats(DWORD handler) out.biCompression = BI_RGB; out.biBitCount = 24; res = ICDecompressBegin(hic, &in, &out); - todo_wine ok(res == ICERR_OK, "Got %ld.\n", res); res = ICDecompressEnd(hic); @@ -329,12 +328,8 @@ static void test_decompress(DWORD handler) ok(!!hic, "Failed to open codec.\n"); res = ICDecompressBegin(hic, &i420_info, &rgb_info); - todo_wine ok(res == ICERR_OK, "Got %ld.\n", res); - if (res != ICERR_OK) - goto skip_decompression_tests; - res = ICDecompress(hic, 0, &i420_info, i420_data, &rgb_info, rgb_data); todo_wine ok(res == ICERR_OK, "Got %ld.\n", res); @@ -354,7 +349,6 @@ static void test_decompress(DWORD handler) todo_wine ok(diff == 0, "Got %lu%% difference.\n", diff); -skip_decompression_tests: res = ICClose(hic); ok(res == ICERR_OK, "Got %ld.\n", res); } -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10549
From: Brendan McGrath <bmcgrath@codeweavers.com> --- dlls/iyuv_32/iyuv.c | 81 +++++++++++++++++++++++++++++++++++- dlls/iyuv_32/tests/iyuv_32.c | 2 - 2 files changed, 79 insertions(+), 4 deletions(-) diff --git a/dlls/iyuv_32/iyuv.c b/dlls/iyuv_32/iyuv.c index bd7265bc447..ff9821b54a8 100644 --- a/dlls/iyuv_32/iyuv.c +++ b/dlls/iyuv_32/iyuv.c @@ -193,9 +193,86 @@ done: static LRESULT IYUV_Decompress(IMFTransform *transform, const ICDECOMPRESS *params) { - FIXME("ICM_DECOMPRESS %p %p\n", transform, params); + IMFSample *in_sample = NULL, *out_sample = NULL; + IMFMediaBuffer *in_buf = NULL, *out_buf = NULL; + MFT_OUTPUT_DATA_BUFFER mft_buf; + LRESULT r = ICERR_INTERNAL; + DWORD mft_status; + BYTE *data; + HRESULT hr; + + TRACE("transform %p, params %p.\n", transform, params); + + if (FAILED(MFCreateSample(&in_sample))) + return ICERR_INTERNAL; + + if (FAILED(MFCreateMemoryBuffer(params->lpbiInput->biSizeImage, &in_buf))) + goto done; + + if (FAILED(IMFSample_AddBuffer(in_sample, in_buf))) + goto done; + + if (FAILED(MFCreateSample(&out_sample))) + goto done; + + if (FAILED(MFCreateMemoryBuffer(params->lpbiOutput->biSizeImage, &out_buf))) + goto done; + + if (FAILED(IMFSample_AddBuffer(out_sample, out_buf))) + goto done; + + if (FAILED(IMFMediaBuffer_Lock(in_buf, &data, NULL, NULL))) + goto done; + + memcpy(data, params->lpInput, params->lpbiInput->biSizeImage); + + if (FAILED(IMFMediaBuffer_Unlock(in_buf))) + goto done; - return ICERR_UNSUPPORTED; + if (FAILED(IMFMediaBuffer_SetCurrentLength(in_buf, params->lpbiInput->biSizeImage))) + goto done; + + if (FAILED(IMFTransform_ProcessInput(transform, 0, in_sample, 0))) + goto done; + + memset(&mft_buf, 0, sizeof(mft_buf)); + mft_buf.pSample = out_sample; + + hr = IMFTransform_ProcessOutput(transform, 0, 1, &mft_buf, &mft_status); + if (hr == MF_E_TRANSFORM_STREAM_CHANGE) + hr = IMFTransform_ProcessOutput(transform, 0, 1, &mft_buf, &mft_status); + + if (SUCCEEDED(hr)) + { + LONG depth = params->lpbiOutput->biBitCount / 8; + LONG width = params->lpbiOutput->biWidth * depth; + LONG stride = (width + 3) & ~3; + + if (FAILED(IMFMediaBuffer_Lock(out_buf, &data, NULL, NULL))) + goto done; + + MFCopyImage(params->lpOutput, stride, data, stride, width, params->lpbiOutput->biHeight); + + IMFMediaBuffer_Unlock(out_buf); + r = ICERR_OK; + } + else if (hr == MF_E_TRANSFORM_NEED_MORE_INPUT) + { + TRACE("no output received.\n"); + r = ICERR_OK; + } + +done: + if (in_buf) + IMFMediaBuffer_Release(in_buf); + if (in_sample) + IMFSample_Release(in_sample); + if (out_buf) + IMFMediaBuffer_Release(out_buf); + if (out_sample) + IMFSample_Release(out_sample); + + return r; } static LRESULT IYUV_GetInfo(ICINFO *icinfo, DWORD size) diff --git a/dlls/iyuv_32/tests/iyuv_32.c b/dlls/iyuv_32/tests/iyuv_32.c index cc8edca386b..6bc565c4293 100644 --- a/dlls/iyuv_32/tests/iyuv_32.c +++ b/dlls/iyuv_32/tests/iyuv_32.c @@ -331,7 +331,6 @@ static void test_decompress(DWORD handler) ok(res == ICERR_OK, "Got %ld.\n", res); res = ICDecompress(hic, 0, &i420_info, i420_data, &rgb_info, rgb_data); - todo_wine ok(res == ICERR_OK, "Got %ld.\n", res); res = ICDecompressEnd(hic); ok(res == ICERR_OK, "Got %ld.\n", res); @@ -346,7 +345,6 @@ static void test_decompress(DWORD handler) for (unsigned int i = 0; i < rgb_info.biSizeImage; ++i) diff += abs((int)rgb_data[i] - (int)expect_rgb_data[i]); diff = diff * 100 / 256 / rgb_info.biSizeImage; - todo_wine ok(diff == 0, "Got %lu%% difference.\n", diff); res = ICClose(hic); -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10549
v3: - Add `TRACE` and call to `init_gstreamer` in `winegstreamer_create_color_converter` -- https://gitlab.winehq.org/wine/wine/-/merge_requests/10549#note_134902
The pipeline is still failing with the following test: ```xml <testcase classname="iyuv_32:iyuv_32" name="iyuv_32:iyuv_32 status -1073741819" file="dlls/iyuv_32/tests/iyuv_32.c" assertions="0" time="0.105000"> <system-out>Test exited with status -1073741819</system-out> <failure/> </testcase> ``` -1073741819 is 0xC0000005, which is `STATUS_ACCESS_VIOLATION`. But I can't recreate this locally, and the tests pass find on the testbot: https://testbot.winehq.org/JobDetails.pl?Key=162427 Is there a way to get additional detail about this failure? -- https://gitlab.winehq.org/wine/wine/-/merge_requests/10549#note_134903
Rémi Bernon (@rbernon) commented about dlls/iyuv_32/iyuv.c:
+ { + TRACE("out->planes = %d\n", out->biPlanes); + TRACE("out->bpp = %d\n", out->biBitCount); + TRACE("out->height = %ld\n", out->biHeight); + TRACE("out->width = %ld\n", out->biWidth); + TRACE("out->compr = %#lx\n", out->biCompression); + + if (out->biCompression == BI_RGB) + { + if (out->biBitCount != 24 && out->biBitCount != 16 && out->biBitCount != 8) + return ICERR_BADFORMAT; + } + else + { + return ICERR_BADFORMAT; + } What about this instead?
```suggestion:-8+0 if (out->biCompression != BI_RGB) return ICERR_BADFORMAT; if (out->biBitCount != 24 && out->biBitCount != 16 && out->biBitCount != 8) return ICERR_BADFORMAT; ``` -- https://gitlab.winehq.org/wine/wine/-/merge_requests/10549#note_134946
Rémi Bernon (@rbernon) commented about dlls/iyuv_32/iyuv.c:
+ + if (FAILED(IMFMediaBuffer_Unlock(in_buf))) + goto done; + + if (FAILED(IMFMediaBuffer_SetCurrentLength(in_buf, params->lpbiInput->biSizeImage))) + goto done; + + if (FAILED(IMFTransform_ProcessInput(transform, 0, in_sample, 0))) + goto done; + + memset(&mft_buf, 0, sizeof(mft_buf)); + mft_buf.pSample = out_sample; + + hr = IMFTransform_ProcessOutput(transform, 0, 1, &mft_buf, &mft_status); + if (hr == MF_E_TRANSFORM_STREAM_CHANGE) + hr = IMFTransform_ProcessOutput(transform, 0, 1, &mft_buf, &mft_status); I don't think that can happen with the color converter. It could be changed to an ERR maybe.
-- https://gitlab.winehq.org/wine/wine/-/merge_requests/10549#note_134947
Rémi Bernon (@rbernon) commented about dlls/iyuv_32/iyuv.c:
+ LONG width = params->lpbiOutput->biWidth * depth; + LONG stride = (width + 3) & ~3; + + if (FAILED(IMFMediaBuffer_Lock(out_buf, &data, NULL, NULL))) + goto done; + + MFCopyImage(params->lpOutput, stride, data, stride, width, params->lpbiOutput->biHeight); + + IMFMediaBuffer_Unlock(out_buf); + r = ICERR_OK; + } + else if (hr == MF_E_TRANSFORM_NEED_MORE_INPUT) + { + TRACE("no output received.\n"); + r = ICERR_OK; + } Same thing here, I don't think the color converter can ever return that if it has been provided an input sample.
-- https://gitlab.winehq.org/wine/wine/-/merge_requests/10549#note_134948
participants (3)
-
Brendan McGrath -
Brendan McGrath (@redmcg) -
Rémi Bernon (@rbernon)