2 * Unit tests for MultiMedia Stream functions
4 * Copyright (C) 2009, 2012 Christian Costa
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
22 #define NONAMELESSUNION
24 #include "wine/test.h"
32 #include "wmcodecdsp.h"
33 #include "wine/strmbase.h"
35 static const WAVEFORMATEX audio_format
=
37 .wFormatTag
= WAVE_FORMAT_PCM
,
39 .nSamplesPerSec
= 11025,
42 .nAvgBytesPerSec
= 2 * 11025,
45 static const AM_MEDIA_TYPE audio_mt
=
47 /* MEDIATYPE_Audio, MEDIASUBTYPE_PCM, FORMAT_WaveFormatEx */
48 .majortype
= {0x73647561, 0x0000, 0x0010, {0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71}},
49 .subtype
= {0x00000001, 0x0000, 0x0010, {0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71}},
50 .formattype
= {0x05589f81, 0xc356, 0x11ce, {0xbf, 0x01, 0x00, 0xaa, 0x00, 0x55, 0x59, 0x5a}},
51 .cbFormat
= sizeof(WAVEFORMATEX
),
52 .pbFormat
= (BYTE
*)&audio_format
,
55 static const VIDEOINFO rgb8_video_info
=
57 .bmiHeader
.biSize
= sizeof(BITMAPINFOHEADER
),
58 .bmiHeader
.biWidth
= 333,
59 .bmiHeader
.biHeight
= -444,
60 .bmiHeader
.biPlanes
= 1,
61 .bmiHeader
.biBitCount
= 8,
62 .bmiHeader
.biCompression
= BI_RGB
,
65 static const VIDEOINFO rgb555_video_info
=
67 .bmiHeader
.biSize
= sizeof(BITMAPINFOHEADER
),
68 .bmiHeader
.biWidth
= 333,
69 .bmiHeader
.biHeight
= -444,
70 .bmiHeader
.biPlanes
= 1,
71 .bmiHeader
.biBitCount
= 16,
72 .bmiHeader
.biCompression
= BI_RGB
,
75 static const VIDEOINFO rgb565_video_info
=
77 .bmiHeader
.biSize
= sizeof(BITMAPINFOHEADER
),
78 .bmiHeader
.biWidth
= 333,
79 .bmiHeader
.biHeight
= -444,
80 .bmiHeader
.biPlanes
= 1,
81 .bmiHeader
.biBitCount
= 16,
82 .bmiHeader
.biCompression
= BI_BITFIELDS
,
83 .u
.dwBitMasks
= {0xf800, 0x07e0, 0x001f},
86 static const VIDEOINFO rgb24_video_info
=
88 .bmiHeader
.biSize
= sizeof(BITMAPINFOHEADER
),
89 .bmiHeader
.biWidth
= 333,
90 .bmiHeader
.biHeight
= -444,
91 .bmiHeader
.biPlanes
= 1,
92 .bmiHeader
.biBitCount
= 24,
93 .bmiHeader
.biCompression
= BI_RGB
,
96 static const VIDEOINFO rgb32_video_info
=
98 .bmiHeader
.biSize
= sizeof(BITMAPINFOHEADER
),
99 .bmiHeader
.biWidth
= 333,
100 .bmiHeader
.biHeight
= -444,
101 .bmiHeader
.biPlanes
= 1,
102 .bmiHeader
.biBitCount
= 32,
103 .bmiHeader
.biCompression
= BI_RGB
,
106 static const AM_MEDIA_TYPE rgb8_mt
=
108 /* MEDIATYPE_Video, MEDIASUBTYPE_RGB8, FORMAT_VideoInfo */
109 .majortype
= {0x73646976, 0x0000, 0x0010, {0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71}},
110 .subtype
= {0xe436eb7a, 0x524f, 0x11ce, {0x9f, 0x53, 0x00, 0x20, 0xaf, 0x0b, 0xa7, 0x70}},
111 .formattype
= {0x05589f80, 0xc356, 0x11ce, {0xbf, 0x01, 0x00, 0xaa, 0x00, 0x55, 0x59, 0x5a}},
112 .cbFormat
= sizeof(VIDEOINFO
),
113 .pbFormat
= (BYTE
*)&rgb8_video_info
,
116 static const AM_MEDIA_TYPE rgb555_mt
=
118 /* MEDIATYPE_Video, MEDIASUBTYPE_RGB555, FORMAT_VideoInfo */
119 .majortype
= {0x73646976, 0x0000, 0x0010, {0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71}},
120 .subtype
= {0xe436eb7c, 0x524f, 0x11ce, {0x9f, 0x53, 0x00, 0x20, 0xaf, 0x0b, 0xa7, 0x70}},
121 .formattype
= {0x05589f80, 0xc356, 0x11ce, {0xbf, 0x01, 0x00, 0xaa, 0x00, 0x55, 0x59, 0x5a}},
122 .cbFormat
= sizeof(VIDEOINFO
),
123 .pbFormat
= (BYTE
*)&rgb555_video_info
,
126 static const AM_MEDIA_TYPE rgb565_mt
=
128 /* MEDIATYPE_Video, MEDIASUBTYPE_RGB565, FORMAT_VideoInfo */
129 .majortype
= {0x73646976, 0x0000, 0x0010, {0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71}},
130 .subtype
= {0xe436eb7b, 0x524f, 0x11ce, {0x9f, 0x53, 0x00, 0x20, 0xaf, 0x0b, 0xa7, 0x70}},
131 .formattype
= {0x05589f80, 0xc356, 0x11ce, {0xbf, 0x01, 0x00, 0xaa, 0x00, 0x55, 0x59, 0x5a}},
132 .cbFormat
= sizeof(VIDEOINFO
),
133 .pbFormat
= (BYTE
*)&rgb565_video_info
,
136 static const AM_MEDIA_TYPE rgb24_mt
=
138 /* MEDIATYPE_Video, MEDIASUBTYPE_RGB24, FORMAT_VideoInfo */
139 .majortype
= {0x73646976, 0x0000, 0x0010, {0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71}},
140 .subtype
= {0xe436eb7d, 0x524f, 0x11ce, {0x9f, 0x53, 0x00, 0x20, 0xaf, 0x0b, 0xa7, 0x70}},
141 .formattype
= {0x05589f80, 0xc356, 0x11ce, {0xbf, 0x01, 0x00, 0xaa, 0x00, 0x55, 0x59, 0x5a}},
142 .cbFormat
= sizeof(VIDEOINFO
),
143 .pbFormat
= (BYTE
*)&rgb24_video_info
,
146 static const AM_MEDIA_TYPE rgb32_mt
=
148 /* MEDIATYPE_Video, MEDIASUBTYPE_RGB32, FORMAT_VideoInfo */
149 .majortype
= {0x73646976, 0x0000, 0x0010, {0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71}},
150 .subtype
= {0xe436eb7e, 0x524f, 0x11ce, {0x9f, 0x53, 0x00, 0x20, 0xaf, 0x0b, 0xa7, 0x70}},
151 .formattype
= {0x05589f80, 0xc356, 0x11ce, {0xbf, 0x01, 0x00, 0xaa, 0x00, 0x55, 0x59, 0x5a}},
152 .cbFormat
= sizeof(VIDEOINFO
),
153 .pbFormat
= (BYTE
*)&rgb32_video_info
,
156 static const DDSURFACEDESC rgb8_format
=
158 .dwSize
= sizeof(DDSURFACEDESC
),
159 .dwFlags
= DDSD_PIXELFORMAT
,
160 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
161 .ddpfPixelFormat
.dwFlags
= DDPF_RGB
| DDPF_PALETTEINDEXED8
,
162 .ddpfPixelFormat
.u1
.dwRGBBitCount
= 8,
165 static const DDSURFACEDESC rgb555_format
=
167 .dwSize
= sizeof(DDSURFACEDESC
),
168 .dwFlags
= DDSD_PIXELFORMAT
,
169 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
170 .ddpfPixelFormat
.dwFlags
= DDPF_RGB
,
171 .ddpfPixelFormat
.u1
.dwRGBBitCount
= 16,
172 .ddpfPixelFormat
.u2
.dwRBitMask
= 0x7c00,
173 .ddpfPixelFormat
.u3
.dwGBitMask
= 0x03e0,
174 .ddpfPixelFormat
.u4
.dwBBitMask
= 0x001f,
177 static const DDSURFACEDESC rgb565_format
=
179 .dwSize
= sizeof(DDSURFACEDESC
),
180 .dwFlags
= DDSD_PIXELFORMAT
,
181 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
182 .ddpfPixelFormat
.dwFlags
= DDPF_RGB
,
183 .ddpfPixelFormat
.u1
.dwRGBBitCount
= 16,
184 .ddpfPixelFormat
.u2
.dwRBitMask
= 0xf800,
185 .ddpfPixelFormat
.u3
.dwGBitMask
= 0x07e0,
186 .ddpfPixelFormat
.u4
.dwBBitMask
= 0x001f,
189 static const DDSURFACEDESC rgb24_format
=
191 .dwSize
= sizeof(DDSURFACEDESC
),
192 .dwFlags
= DDSD_PIXELFORMAT
,
193 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
194 .ddpfPixelFormat
.dwFlags
= DDPF_RGB
,
195 .ddpfPixelFormat
.u1
.dwRGBBitCount
= 24,
196 .ddpfPixelFormat
.u2
.dwRBitMask
= 0xff0000,
197 .ddpfPixelFormat
.u3
.dwGBitMask
= 0x00ff00,
198 .ddpfPixelFormat
.u4
.dwBBitMask
= 0x0000ff,
201 static const DDSURFACEDESC rgb32_format
=
203 .dwSize
= sizeof(DDSURFACEDESC
),
204 .dwFlags
= DDSD_PIXELFORMAT
,
205 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
206 .ddpfPixelFormat
.dwFlags
= DDPF_RGB
,
207 .ddpfPixelFormat
.u1
.dwRGBBitCount
= 32,
208 .ddpfPixelFormat
.u2
.dwRBitMask
= 0xff0000,
209 .ddpfPixelFormat
.u3
.dwGBitMask
= 0x00ff00,
210 .ddpfPixelFormat
.u4
.dwBBitMask
= 0x0000ff,
213 static const DDSURFACEDESC argb32_format
=
215 .dwSize
= sizeof(DDSURFACEDESC
),
216 .dwFlags
= DDSD_PIXELFORMAT
,
217 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
218 .ddpfPixelFormat
.dwFlags
= DDPF_RGB
| DDPF_ALPHAPIXELS
,
219 .ddpfPixelFormat
.u1
.dwRGBBitCount
= 32,
220 .ddpfPixelFormat
.u2
.dwRBitMask
= 0xff0000,
221 .ddpfPixelFormat
.u3
.dwGBitMask
= 0x00ff00,
222 .ddpfPixelFormat
.u4
.dwBBitMask
= 0x0000ff,
223 .ddpfPixelFormat
.u5
.dwRGBAlphaBitMask
= 0xff000000,
226 static const DDSURFACEDESC yuy2_format
=
228 .dwSize
= sizeof(DDSURFACEDESC
),
229 .dwFlags
= DDSD_PIXELFORMAT
,
230 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
231 .ddpfPixelFormat
.dwFlags
= DDPF_FOURCC
,
232 .ddpfPixelFormat
.dwFourCC
= MAKEFOURCC('Y', 'U', 'Y', '2'),
233 .ddpfPixelFormat
.u1
.dwYUVBitCount
= 16,
236 static const DDSURFACEDESC yv12_format
=
238 .dwSize
= sizeof(DDSURFACEDESC
),
239 .dwFlags
= DDSD_PIXELFORMAT
,
240 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
241 .ddpfPixelFormat
.dwFlags
= DDPF_FOURCC
,
242 .ddpfPixelFormat
.dwFourCC
= MAKEFOURCC('Y', 'V', '1', '2'),
243 .ddpfPixelFormat
.u1
.dwYUVBitCount
= 12,
246 static const WCHAR primary_video_sink_id
[] = L
"I{A35FF56A-9FDA-11D0-8FDF-00C04FD9189D}";
247 static const WCHAR primary_audio_sink_id
[] = L
"I{A35FF56B-9FDA-11D0-8FDF-00C04FD9189D}";
249 static const WCHAR
*load_resource(const WCHAR
*name
)
251 HMODULE module
= GetModuleHandleA(NULL
);
259 path
= calloc(MAX_PATH
+ 1, sizeof(WCHAR
));
260 ok(!!path
, "Failed to allocate temp path string.\n");
261 GetTempPathW(MAX_PATH
+ 1, path
);
264 file
= CreateFileW(path
, GENERIC_READ
| GENERIC_WRITE
, 0, NULL
, CREATE_ALWAYS
, 0, 0);
265 ok(file
!= INVALID_HANDLE_VALUE
, "Failed to create file %s, error %u.\n", wine_dbgstr_w(path
), GetLastError());
267 resource
= FindResourceW(module
, name
, (const WCHAR
*)RT_RCDATA
);
268 ok(!!resource
, "Failed to find resource %s, error %u.\n", wine_dbgstr_w(name
), GetLastError());
270 size
= SizeofResource(module
, resource
);
271 ptr
= LockResource(LoadResource(module
, resource
));
273 WriteFile(file
, ptr
, size
, &written
, NULL
);
274 ok(written
== size
, "Failed to write file %s.\n", wine_dbgstr_w(path
));
281 static void unload_resource(const WCHAR
*path
)
283 BOOL ret
= DeleteFileW(path
);
284 ok(ret
, "Failed to delete file %s.\n", wine_dbgstr_w(path
));
288 #define EXPECT_REF(obj,ref) _expect_ref((IUnknown*)obj, ref, __LINE__)
289 static void _expect_ref(IUnknown
* obj
, ULONG ref
, int line
)
292 IUnknown_AddRef(obj
);
293 rc
= IUnknown_Release(obj
);
294 ok_(__FILE__
,line
)(rc
== ref
, "expected refcount %d, got %d\n", ref
, rc
);
297 static IAMMultiMediaStream
*create_ammultimediastream(void)
299 IAMMultiMediaStream
*stream
= NULL
;
300 HRESULT hr
= CoCreateInstance(&CLSID_AMMultiMediaStream
, NULL
, CLSCTX_INPROC_SERVER
,
301 &IID_IAMMultiMediaStream
, (void **)&stream
);
302 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
306 static ULONG
get_refcount(void *iface
)
308 IUnknown
*unknown
= iface
;
309 IUnknown_AddRef(unknown
);
310 return IUnknown_Release(unknown
);
313 #define check_interface(a, b, c) check_interface_(__LINE__, a, b, c)
314 static void check_interface_(unsigned int line
, void *iface_ptr
, REFIID iid
, BOOL supported
)
316 IUnknown
*iface
= iface_ptr
;
317 HRESULT hr
, expected_hr
;
320 expected_hr
= supported
? S_OK
: E_NOINTERFACE
;
322 hr
= IUnknown_QueryInterface(iface
, iid
, (void **)&unk
);
323 ok_(__FILE__
, line
)(hr
== expected_hr
, "Got hr %#x, expected %#x.\n", hr
, expected_hr
);
325 IUnknown_Release(unk
);
328 static void test_interfaces(void)
330 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
331 IMediaStreamFilter
*filter
;
332 IMediaStream
*stream
;
336 check_interface(mmstream
, &IID_IAMMultiMediaStream
, TRUE
);
337 check_interface(mmstream
, &IID_IMultiMediaStream
, TRUE
);
338 check_interface(mmstream
, &IID_IUnknown
, TRUE
);
340 check_interface(mmstream
, &IID_IAMMediaStream
, FALSE
);
341 check_interface(mmstream
, &IID_IAMMediaTypeStream
, FALSE
);
342 check_interface(mmstream
, &IID_IAudioMediaStream
, FALSE
);
343 check_interface(mmstream
, &IID_IBaseFilter
, FALSE
);
344 check_interface(mmstream
, &IID_IDirectDrawMediaStream
, FALSE
);
345 check_interface(mmstream
, &IID_IMediaFilter
, FALSE
);
346 check_interface(mmstream
, &IID_IMediaStream
, FALSE
);
347 check_interface(mmstream
, &IID_IMediaStreamFilter
, FALSE
);
348 check_interface(mmstream
, &IID_IPin
, FALSE
);
350 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
351 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
353 check_interface(filter
, &IID_IBaseFilter
, TRUE
);
354 check_interface(filter
, &IID_IMediaFilter
, TRUE
);
355 check_interface(filter
, &IID_IMediaStreamFilter
, TRUE
);
356 check_interface(filter
, &IID_IPersist
, TRUE
);
357 check_interface(filter
, &IID_IUnknown
, TRUE
);
359 check_interface(filter
, &IID_IAMMediaStream
, FALSE
);
360 check_interface(filter
, &IID_IAMMediaTypeStream
, FALSE
);
361 check_interface(filter
, &IID_IAMMultiMediaStream
, FALSE
);
362 check_interface(filter
, &IID_IAudioMediaStream
, FALSE
);
363 check_interface(filter
, &IID_IDirectDrawMediaStream
, FALSE
);
364 check_interface(filter
, &IID_IMediaStream
, FALSE
);
365 check_interface(filter
, &IID_IMultiMediaStream
, FALSE
);
366 check_interface(filter
, &IID_IPin
, FALSE
);
368 IMediaStreamFilter_Release(filter
);
370 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
371 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
373 check_interface(stream
, &IID_IAMMediaStream
, TRUE
);
374 check_interface(stream
, &IID_IAudioMediaStream
, TRUE
);
375 check_interface(stream
, &IID_IMediaStream
, TRUE
);
376 check_interface(stream
, &IID_IMemInputPin
, TRUE
);
377 check_interface(stream
, &IID_IPin
, TRUE
);
378 check_interface(stream
, &IID_IUnknown
, TRUE
);
380 check_interface(stream
, &IID_IAMMediaTypeStream
, FALSE
);
381 check_interface(stream
, &IID_IAMMultiMediaStream
, FALSE
);
382 check_interface(stream
, &IID_IBaseFilter
, FALSE
);
383 check_interface(stream
, &IID_IDirectDrawMediaStream
, FALSE
);
384 check_interface(stream
, &IID_IMediaFilter
, FALSE
);
385 check_interface(stream
, &IID_IMediaStreamFilter
, FALSE
);
386 check_interface(stream
, &IID_IMultiMediaStream
, FALSE
);
387 check_interface(stream
, &IID_IPersist
, FALSE
);
389 IMediaStream_Release(stream
);
391 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
392 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
394 check_interface(stream
, &IID_IAMMediaStream
, TRUE
);
395 check_interface(stream
, &IID_IDirectDrawMediaStream
, TRUE
);
396 check_interface(stream
, &IID_IMediaStream
, TRUE
);
397 check_interface(stream
, &IID_IMemInputPin
, TRUE
);
398 check_interface(stream
, &IID_IPin
, TRUE
);
399 check_interface(stream
, &IID_IUnknown
, TRUE
);
401 check_interface(stream
, &IID_IAMMediaTypeStream
, FALSE
);
402 check_interface(stream
, &IID_IAMMultiMediaStream
, FALSE
);
403 check_interface(stream
, &IID_IAudioMediaStream
, FALSE
);
404 check_interface(stream
, &IID_IBaseFilter
, FALSE
);
405 check_interface(stream
, &IID_IDirectDraw
, FALSE
);
406 check_interface(stream
, &IID_IMediaFilter
, FALSE
);
407 check_interface(stream
, &IID_IMediaStreamFilter
, FALSE
);
408 check_interface(stream
, &IID_IMultiMediaStream
, FALSE
);
409 check_interface(stream
, &IID_IPersist
, FALSE
);
411 IMediaStream_Release(stream
);
413 ref
= IAMMultiMediaStream_Release(mmstream
);
414 ok(!ref
, "Got outstanding refcount %u.\n", ref
);
417 static void test_openfile(const WCHAR
*test_avi_path
)
419 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
420 IMediaControl
*media_control
;
421 IMediaStreamFilter
*filter
;
422 IMediaFilter
*media_filter
;
423 IReferenceClock
*clock
;
424 IGraphBuilder
*graph
;
429 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
430 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
431 ok(!graph
, "Expected NULL graph.\n");
433 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
434 ok(!!filter
, "Expected non-NULL filter.\n");
435 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
437 check_interface(filter
, &IID_IMediaSeeking
, FALSE
);
439 hr
= IAMMultiMediaStream_OpenFile(mmstream
, test_avi_path
, AMMSF_NORENDER
);
440 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
442 check_interface(filter
, &IID_IMediaSeeking
, FALSE
);
444 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
445 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
446 ok(!!graph
, "Expected non-NULL graph.\n");
447 IGraphBuilder_Release(graph
);
448 IMediaStreamFilter_Release(filter
);
450 ref
= IAMMultiMediaStream_Release(mmstream
);
451 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
453 mmstream
= create_ammultimediastream();
454 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
455 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
456 ok(!graph
, "Expected NULL graph.\n");
458 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
459 ok(!!filter
, "Expected non-NULL filter.\n");
460 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
462 check_interface(filter
, &IID_IMediaSeeking
, FALSE
);
464 hr
= IAMMultiMediaStream_OpenFile(mmstream
, test_avi_path
, 0);
465 ok(hr
== VFW_E_CANNOT_CONNECT
, "Got hr %#x.\n", hr
);
467 check_interface(filter
, &IID_IMediaSeeking
, FALSE
);
469 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
470 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
471 ok(!!graph
, "Expected non-NULL graph.\n");
472 IGraphBuilder_Release(graph
);
473 IMediaStreamFilter_Release(filter
);
475 ref
= IAMMultiMediaStream_Release(mmstream
);
476 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
478 mmstream
= create_ammultimediastream();
479 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, NULL
);
480 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
481 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
482 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
483 ok(!!graph
, "Expected non-NULL graph.\n");
484 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaFilter
, (void **)&media_filter
);
485 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
486 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
487 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
489 check_interface(filter
, &IID_IMediaSeeking
, FALSE
);
491 hr
= IAMMultiMediaStream_OpenFile(mmstream
, test_avi_path
, 0);
492 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
494 check_interface(filter
, &IID_IMediaSeeking
, TRUE
);
496 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
497 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
500 IMediaFilter_GetSyncSource(media_filter
, &clock
);
501 ok(!!clock
, "Expected non-NULL clock.\n");
503 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
504 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
506 ref
= IAMMultiMediaStream_Release(mmstream
);
507 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
508 IMediaFilter_Release(media_filter
);
509 ref
= IGraphBuilder_Release(graph
);
510 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
511 ref
= IMediaStreamFilter_Release(filter
);
512 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
513 ref
= IReferenceClock_Release(clock
);
514 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
516 mmstream
= create_ammultimediastream();
517 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, NULL
);
518 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
519 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
520 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
521 ok(!!graph
, "Expected non-NULL graph.\n");
522 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaControl
, (void **)&media_control
);
523 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
525 hr
= IAMMultiMediaStream_OpenFile(mmstream
, test_avi_path
, AMMSF_RUN
);
526 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
529 hr
= IMediaControl_GetState(media_control
, INFINITE
, &state
);
530 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
531 ok(state
== State_Running
, "Got state %#x.\n", state
);
533 ref
= IAMMultiMediaStream_Release(mmstream
);
534 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
535 IMediaControl_Release(media_control
);
536 ref
= IGraphBuilder_Release(graph
);
537 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
539 mmstream
= create_ammultimediastream();
540 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, NULL
);
541 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
542 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
543 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
544 ok(!!graph
, "Expected non-NULL graph.\n");
545 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaFilter
, (void **)&media_filter
);
546 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
548 hr
= IAMMultiMediaStream_OpenFile(mmstream
, test_avi_path
, AMMSF_NOCLOCK
);
549 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
551 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
552 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
554 clock
= (IReferenceClock
*)0xdeadbeef;
555 IMediaFilter_GetSyncSource(media_filter
, &clock
);
556 ok(!clock
, "Got clock %p.\n", clock
);
558 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
559 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
561 ref
= IAMMultiMediaStream_Release(mmstream
);
562 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
563 IMediaFilter_Release(media_filter
);
564 ref
= IGraphBuilder_Release(graph
);
565 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
568 static void test_mmstream_get_duration(const WCHAR
*test_avi_path
)
570 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
571 HRESULT hr
, audio_hr
;
575 duration
= 0xdeadbeefdeadbeefULL
;
576 hr
= IAMMultiMediaStream_GetDuration(mmstream
, &duration
);
577 ok(hr
== E_NOINTERFACE
, "Got hr %#x.\n", hr
);
578 ok(duration
== 0xdeadbeefdeadbeefULL
, "Got duration %s.\n", wine_dbgstr_longlong(duration
));
580 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, NULL
);
581 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
583 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, AMMSF_ADDDEFAULTRENDERER
, NULL
);
584 ok(hr
== S_OK
|| hr
== VFW_E_NO_AUDIO_HARDWARE
, "Got hr %#x.\n", hr
);
587 hr
= IAMMultiMediaStream_OpenFile(mmstream
, test_avi_path
, 0);
588 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
590 duration
= 0xdeadbeefdeadbeefULL
;
591 hr
= IAMMultiMediaStream_GetDuration(mmstream
, &duration
);
592 if (audio_hr
== S_OK
)
594 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
595 ok(duration
== 1000000LL, "Got duration %s.\n", wine_dbgstr_longlong(duration
));
599 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
600 ok(!duration
, "Got duration %s.\n", wine_dbgstr_longlong(duration
));
603 ref
= IAMMultiMediaStream_Release(mmstream
);
604 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
606 mmstream
= create_ammultimediastream();
607 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, NULL
);
608 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
610 duration
= 0xdeadbeefdeadbeefULL
;
611 hr
= IAMMultiMediaStream_GetDuration(mmstream
, &duration
);
612 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
613 ok(duration
== 0, "Got duration %s.\n", wine_dbgstr_longlong(duration
));
615 ref
= IAMMultiMediaStream_Release(mmstream
);
616 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
618 mmstream
= create_ammultimediastream();
620 hr
= IAMMultiMediaStream_OpenFile(mmstream
, test_avi_path
, 0);
621 ok(hr
== VFW_E_CANNOT_CONNECT
, "Got hr %#x.\n", hr
);
623 duration
= 0xdeadbeefdeadbeefULL
;
624 hr
= IAMMultiMediaStream_GetDuration(mmstream
, &duration
);
625 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
626 ok(duration
== 0, "Got duration %s.\n", wine_dbgstr_longlong(duration
));
628 ref
= IAMMultiMediaStream_Release(mmstream
);
629 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
631 mmstream
= create_ammultimediastream();
632 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, NULL
);
633 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
635 hr
= IAMMultiMediaStream_OpenFile(mmstream
, test_avi_path
, AMMSF_NORENDER
);
636 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
638 duration
= 0xdeadbeefdeadbeefULL
;
639 hr
= IAMMultiMediaStream_GetDuration(mmstream
, &duration
);
640 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
641 ok(duration
== 0, "Got duration %s.\n", wine_dbgstr_longlong(duration
));
643 ref
= IAMMultiMediaStream_Release(mmstream
);
644 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
647 static const GUID test_mspid
= {0x88888888};
651 IAMMediaStream IAMMediaStream_iface
;
655 IAMMultiMediaStream
*mmstream
;
656 IMediaStreamFilter
*filter
;
659 HRESULT set_state_result
;
662 static struct teststream
*impl_from_IAMMediaStream(IAMMediaStream
*iface
)
664 return CONTAINING_RECORD(iface
, struct teststream
, IAMMediaStream_iface
);
667 static struct teststream
*impl_from_IPin(IPin
*iface
)
669 return CONTAINING_RECORD(iface
, struct teststream
, IPin_iface
);
672 static HRESULT WINAPI
pin_QueryInterface(IPin
*iface
, REFIID iid
, void **out
)
674 struct teststream
*stream
= impl_from_IPin(iface
);
675 return IAMMediaStream_QueryInterface(&stream
->IAMMediaStream_iface
, iid
, out
);
678 static ULONG WINAPI
pin_AddRef(IPin
*iface
)
680 struct teststream
*stream
= impl_from_IPin(iface
);
681 return IAMMediaStream_AddRef(&stream
->IAMMediaStream_iface
);
684 static ULONG WINAPI
pin_Release(IPin
*iface
)
686 struct teststream
*stream
= impl_from_IPin(iface
);
687 return IAMMediaStream_Release(&stream
->IAMMediaStream_iface
);
690 static HRESULT WINAPI
pin_Connect(IPin
*iface
, IPin
*peer
, const AM_MEDIA_TYPE
*mt
)
692 ok(0, "Unexpected call.\n");
696 static HRESULT WINAPI
pin_ReceiveConnection(IPin
*iface
, IPin
*peer
, const AM_MEDIA_TYPE
*mt
)
698 ok(0, "Unexpected call.\n");
702 static HRESULT WINAPI
pin_Disconnect(IPin
*iface
)
704 if (winetest_debug
> 1) trace("Disconnect\n");
708 static HRESULT WINAPI
pin_ConnectedTo(IPin
*iface
, IPin
**peer
)
710 if (winetest_debug
> 1) trace("ConnectedTo\n");
714 static HRESULT WINAPI
pin_ConnectionMediaType(IPin
*iface
, AM_MEDIA_TYPE
*mt
)
716 ok(0, "Unexpected call.\n");
720 static HRESULT WINAPI
pin_QueryPinInfo(IPin
*iface
, PIN_INFO
*info
)
722 ok(0, "Unexpected call.\n");
726 static HRESULT WINAPI
pin_QueryDirection(IPin
*iface
, PIN_DIRECTION
*dir
)
728 if (winetest_debug
> 1) trace("QueryDirection\n");
733 static HRESULT WINAPI
pin_QueryId(IPin
*iface
, WCHAR
**id
)
735 ok(0, "Unexpected call.\n");
739 static HRESULT WINAPI
pin_QueryAccept(IPin
*iface
, const AM_MEDIA_TYPE
*mt
)
741 ok(0, "Unexpected call.\n");
745 static HRESULT WINAPI
pin_EnumMediaTypes(IPin
*iface
, IEnumMediaTypes
**out
)
747 ok(0, "Unexpected call.\n");
751 static HRESULT WINAPI
pin_QueryInternalConnections(IPin
*iface
, IPin
**pins
, ULONG
*count
)
753 ok(0, "Unexpected call.\n");
757 static HRESULT WINAPI
pin_EndOfStream(IPin
*iface
)
759 ok(0, "Unexpected call.\n");
763 static HRESULT WINAPI
pin_BeginFlush(IPin
*iface
)
765 ok(0, "Unexpected call.\n");
769 static HRESULT WINAPI
pin_EndFlush(IPin
*iface
)
771 ok(0, "Unexpected call.\n");
775 static HRESULT WINAPI
pin_NewSegment(IPin
*iface
, REFERENCE_TIME start
, REFERENCE_TIME stop
, double rate
)
777 ok(0, "Unexpected call.\n");
781 static const IPinVtbl pin_vtbl
=
787 pin_ReceiveConnection
,
790 pin_ConnectionMediaType
,
796 pin_QueryInternalConnections
,
803 static HRESULT WINAPI
stream_QueryInterface(IAMMediaStream
*iface
, REFIID iid
, void **out
)
805 struct teststream
*stream
= impl_from_IAMMediaStream(iface
);
807 if (winetest_debug
> 1) trace("QueryInterface(%s)\n", wine_dbgstr_guid(iid
));
809 if (IsEqualGUID(iid
, &IID_IUnknown
) || IsEqualGUID(iid
, &IID_IMediaStream
) || IsEqualGUID(iid
, &IID_IAMMediaStream
))
811 IAMMediaStream_AddRef(iface
);
815 else if (IsEqualGUID(iid
, &IID_IPin
))
817 IAMMediaStream_AddRef(iface
);
818 *out
= &stream
->IPin_iface
;
822 ok(0, "Unexpected interface %s.\n", wine_dbgstr_guid(iid
));
823 return E_NOINTERFACE
;
826 static ULONG WINAPI
stream_AddRef(IAMMediaStream
*iface
)
828 struct teststream
*stream
= impl_from_IAMMediaStream(iface
);
829 return InterlockedIncrement(&stream
->refcount
);
832 static ULONG WINAPI
stream_Release(IAMMediaStream
*iface
)
834 struct teststream
*stream
= impl_from_IAMMediaStream(iface
);
835 return InterlockedDecrement(&stream
->refcount
);
838 static HRESULT WINAPI
stream_GetMultiMediaStream(IAMMediaStream
*iface
, IMultiMediaStream
**mmstream
)
840 ok(0, "Unexpected call.\n");
844 static HRESULT WINAPI
stream_GetInformation(IAMMediaStream
*iface
, MSPID
*id
, STREAM_TYPE
*type
)
846 struct teststream
*stream
= impl_from_IAMMediaStream(iface
);
847 if (winetest_debug
> 1) trace("GetInformation(%p, %p)\n", id
, type
);
851 *type
= STREAMTYPE_READ
;
855 static HRESULT WINAPI
stream_SetSameFormat(IAMMediaStream
*iface
, IMediaStream
*ref
, DWORD flags
)
857 ok(0, "Unexpected call.\n");
861 static HRESULT WINAPI
stream_AllocateSample(IAMMediaStream
*iface
, DWORD flags
, IStreamSample
**sample
)
863 ok(0, "Unexpected call.\n");
867 static HRESULT WINAPI
stream_CreateSharedSample(IAMMediaStream
*iface
,
868 IStreamSample
*existing
, DWORD flags
, IStreamSample
**out
)
870 ok(0, "Unexpected call.\n");
874 static HRESULT WINAPI
stream_SendEndOfStream(IAMMediaStream
*iface
, DWORD flags
)
876 ok(0, "Unexpected call.\n");
880 static HRESULT WINAPI
stream_Initialize(IAMMediaStream
*iface
, IUnknown
*source
,
881 DWORD flags
, REFMSPID id
, const STREAM_TYPE type
)
883 ok(0, "Unexpected call.\n");
887 static HRESULT WINAPI
stream_SetState(IAMMediaStream
*iface
, FILTER_STATE state
)
889 struct teststream
*stream
= impl_from_IAMMediaStream(iface
);
890 if (winetest_debug
> 1) trace("SetState(%#x)\n", state
);
891 if (SUCCEEDED(stream
->set_state_result
))
892 stream
->state
= state
;
893 return stream
->set_state_result
;
896 static HRESULT WINAPI
stream_JoinAMMultiMediaStream(IAMMediaStream
*iface
, IAMMultiMediaStream
*mmstream
)
898 struct teststream
*stream
= impl_from_IAMMediaStream(iface
);
899 if (winetest_debug
> 1) trace("JoinAMMultiMediaStream(%p)\n", mmstream
);
900 stream
->mmstream
= mmstream
;
904 static HRESULT WINAPI
stream_JoinFilter(IAMMediaStream
*iface
, IMediaStreamFilter
*filter
)
906 struct teststream
*stream
= impl_from_IAMMediaStream(iface
);
907 if (winetest_debug
> 1) trace("JoinFilter(%p)\n", filter
);
908 stream
->filter
= filter
;
912 static HRESULT WINAPI
stream_JoinFilterGraph(IAMMediaStream
*iface
, IFilterGraph
*graph
)
914 struct teststream
*stream
= impl_from_IAMMediaStream(iface
);
915 if (winetest_debug
> 1) trace("JoinFilterGraph(%p)\n", graph
);
916 stream
->graph
= graph
;
920 static const IAMMediaStreamVtbl stream_vtbl
=
922 stream_QueryInterface
,
925 stream_GetMultiMediaStream
,
926 stream_GetInformation
,
927 stream_SetSameFormat
,
928 stream_AllocateSample
,
929 stream_CreateSharedSample
,
930 stream_SendEndOfStream
,
933 stream_JoinAMMultiMediaStream
,
935 stream_JoinFilterGraph
,
938 static void teststream_init(struct teststream
*stream
)
940 memset(stream
, 0, sizeof(*stream
));
941 stream
->IAMMediaStream_iface
.lpVtbl
= &stream_vtbl
;
942 stream
->IPin_iface
.lpVtbl
= &pin_vtbl
;
943 stream
->refcount
= 1;
944 stream
->mspid
= test_mspid
;
945 stream
->set_state_result
= S_OK
;
948 #define check_enum_stream(a,b,c,d) check_enum_stream_(__LINE__,a,b,c,d)
949 static void check_enum_stream_(int line
, IAMMultiMediaStream
*mmstream
,
950 IMediaStreamFilter
*filter
, LONG index
, IMediaStream
*expect
)
952 IMediaStream
*stream
= NULL
, *stream2
= NULL
;
955 hr
= IAMMultiMediaStream_EnumMediaStreams(mmstream
, index
, &stream
);
956 ok_(__FILE__
, line
)(hr
== (expect
? S_OK
: S_FALSE
),
957 "IAMMultiMediaStream::EnumMediaStreams() returned %#x.\n", hr
);
958 hr
= IMediaStreamFilter_EnumMediaStreams(filter
, index
, &stream2
);
959 ok_(__FILE__
, line
)(hr
== (expect
? S_OK
: S_FALSE
),
960 "IMediaStreamFilter::EnumMediaStreams() returned %#x.\n", hr
);
963 ok_(__FILE__
, line
)(stream
== expect
, "Expected stream %p, got %p.\n", expect
, stream
);
964 ok_(__FILE__
, line
)(stream2
== expect
, "Expected stream %p, got %p.\n", expect
, stream2
);
965 IMediaStream_Release(stream
);
966 IMediaStream_Release(stream2
);
972 struct strmbase_filter filter
;
973 struct strmbase_source source
;
974 IMediaSeeking IMediaSeeking_iface
;
975 LONGLONG current_position
;
976 LONGLONG stop_position
;
977 const AM_MEDIA_TYPE
*preferred_mt
;
978 HANDLE wait_state_event
;
979 HRESULT get_duration_hr
;
980 HRESULT get_stop_position_hr
;
981 HRESULT set_positions_hr
;
982 HRESULT init_stream_hr
;
983 HRESULT cleanup_stream_hr
;
984 HRESULT wait_state_hr
;
985 HRESULT is_format_supported_hr
;
988 static inline struct testfilter
*impl_from_BaseFilter(struct strmbase_filter
*iface
)
990 return CONTAINING_RECORD(iface
, struct testfilter
, filter
);
993 static struct strmbase_pin
*testfilter_get_pin(struct strmbase_filter
*iface
, unsigned int index
)
995 struct testfilter
*filter
= impl_from_BaseFilter(iface
);
997 return &filter
->source
.pin
;
1001 static void testfilter_destroy(struct strmbase_filter
*iface
)
1003 struct testfilter
*filter
= impl_from_BaseFilter(iface
);
1004 CloseHandle(filter
->wait_state_event
);
1005 strmbase_source_cleanup(&filter
->source
);
1006 strmbase_filter_cleanup(&filter
->filter
);
1009 static HRESULT
testfilter_init_stream(struct strmbase_filter
*iface
)
1011 struct testfilter
*filter
= impl_from_BaseFilter(iface
);
1014 if (SUCCEEDED(filter
->init_stream_hr
) && filter
->source
.pin
.peer
)
1016 hr
= IMemAllocator_Commit(filter
->source
.pAllocator
);
1017 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1020 return filter
->init_stream_hr
;
1023 static HRESULT
testfilter_cleanup_stream(struct strmbase_filter
*iface
)
1025 struct testfilter
*filter
= impl_from_BaseFilter(iface
);
1028 if (SUCCEEDED(filter
->cleanup_stream_hr
) && filter
->source
.pin
.peer
)
1030 hr
= IMemAllocator_Decommit(filter
->source
.pAllocator
);
1031 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1034 return filter
->cleanup_stream_hr
;
1037 static HRESULT
testfilter_wait_state(struct strmbase_filter
*iface
, DWORD timeout
)
1039 struct testfilter
*filter
= impl_from_BaseFilter(iface
);
1042 LeaveCriticalSection(&filter
->filter
.filter_cs
);
1043 WaitForSingleObject(filter
->wait_state_event
, timeout
);
1044 EnterCriticalSection(&filter
->filter
.filter_cs
);
1046 hr
= filter
->wait_state_hr
;
1051 static const struct strmbase_filter_ops testfilter_ops
=
1053 .filter_get_pin
= testfilter_get_pin
,
1054 .filter_destroy
= testfilter_destroy
,
1055 .filter_init_stream
= testfilter_init_stream
,
1056 .filter_cleanup_stream
= testfilter_cleanup_stream
,
1057 .filter_wait_state
= testfilter_wait_state
,
1060 static inline struct testfilter
*impl_from_base_pin(struct strmbase_pin
*iface
)
1062 return CONTAINING_RECORD(iface
, struct testfilter
, source
.pin
);
1065 static HRESULT
testsource_get_media_type(struct strmbase_pin
*iface
, unsigned int index
, AM_MEDIA_TYPE
*mt
)
1067 struct testfilter
*filter
= impl_from_base_pin(iface
);
1069 if (index
< 1 && filter
->preferred_mt
)
1070 return CopyMediaType(mt
, filter
->preferred_mt
);
1072 return VFW_S_NO_MORE_ITEMS
;
1075 static HRESULT
testsource_query_interface(struct strmbase_pin
*iface
, REFIID iid
, void **out
)
1077 struct testfilter
*filter
= impl_from_base_pin(iface
);
1079 if (IsEqualGUID(iid
, &IID_IMediaSeeking
) && filter
->IMediaSeeking_iface
.lpVtbl
)
1080 *out
= &filter
->IMediaSeeking_iface
;
1082 return E_NOINTERFACE
;
1084 IUnknown_AddRef((IUnknown
*)*out
);
1089 static HRESULT WINAPI
testsource_DecideAllocator(struct strmbase_source
*iface
, IMemInputPin
*pin
, IMemAllocator
**alloc
)
1091 ALLOCATOR_PROPERTIES props
= {0};
1094 /* AMDirectDrawStream tries to use it's custom allocator and
1095 * when it is able to do so it's behavior changes slightly
1096 * (e.g. it uses dynamic format change instead of reconnecting in SetFormat).
1097 * We don't yet implement the custom allocator so force the standard one for now. */
1098 hr
= BaseOutputPinImpl_InitAllocator(iface
, alloc
);
1099 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1101 IMemInputPin_GetAllocatorRequirements(pin
, &props
);
1102 hr
= iface
->pFuncsTable
->pfnDecideBufferSize(iface
, *alloc
, &props
);
1103 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1105 return IMemInputPin_NotifyAllocator(pin
, *alloc
, FALSE
);
1108 static HRESULT WINAPI
testsource_DecideBufferSize(struct strmbase_source
*iface
,
1109 IMemAllocator
*alloc
, ALLOCATOR_PROPERTIES
*requested
)
1111 ALLOCATOR_PROPERTIES actual
;
1113 if (!requested
->cbAlign
)
1114 requested
->cbAlign
= 1;
1116 if (requested
->cbBuffer
< 4096)
1117 requested
->cbBuffer
= 4096;
1119 if (!requested
->cBuffers
)
1120 requested
->cBuffers
= 2;
1122 return IMemAllocator_SetProperties(alloc
, requested
, &actual
);
1125 static const struct strmbase_source_ops testsource_ops
=
1127 .base
.pin_get_media_type
= testsource_get_media_type
,
1128 .base
.pin_query_interface
= testsource_query_interface
,
1129 .pfnAttemptConnection
= BaseOutputPinImpl_AttemptConnection
,
1130 .pfnDecideBufferSize
= testsource_DecideBufferSize
,
1131 .pfnDecideAllocator
= testsource_DecideAllocator
,
1134 static void testfilter_init(struct testfilter
*filter
)
1136 static const GUID clsid
= {0xabacab};
1137 memset(filter
, 0, sizeof(*filter
));
1138 strmbase_filter_init(&filter
->filter
, NULL
, &clsid
, &testfilter_ops
);
1139 strmbase_source_init(&filter
->source
, &filter
->filter
, L
"", &testsource_ops
);
1140 filter
->stop_position
= 0x8000000000000000ULL
;
1141 filter
->wait_state_event
= CreateEventW(NULL
, TRUE
, TRUE
, NULL
);
1144 static inline struct testfilter
*impl_from_IMediaSeeking(IMediaSeeking
*iface
)
1146 return CONTAINING_RECORD(iface
, struct testfilter
, IMediaSeeking_iface
);
1149 static HRESULT WINAPI
testsource_seeking_QueryInterface(IMediaSeeking
*iface
, REFIID iid
, void **out
)
1151 struct testfilter
*filter
= impl_from_IMediaSeeking(iface
);
1152 return IBaseFilter_QueryInterface(&filter
->filter
.IBaseFilter_iface
, iid
, out
);
1155 static ULONG WINAPI
testsource_seeking_AddRef(IMediaSeeking
*iface
)
1157 struct testfilter
*filter
= impl_from_IMediaSeeking(iface
);
1158 return IBaseFilter_AddRef(&filter
->filter
.IBaseFilter_iface
);
1161 static ULONG WINAPI
testsource_seeking_Release(IMediaSeeking
*iface
)
1163 struct testfilter
*filter
= impl_from_IMediaSeeking(iface
);
1164 return IBaseFilter_Release(&filter
->filter
.IBaseFilter_iface
);
1167 static HRESULT WINAPI
testsource_seeking_GetCapabilities(IMediaSeeking
*iface
, DWORD
*capabilities
)
1169 ok(0, "Unexpected call.\n");
1173 static HRESULT WINAPI
testsource_seeking_CheckCapabilities(IMediaSeeking
*iface
, DWORD
*capabilities
)
1175 ok(0, "Unexpected call.\n");
1179 static HRESULT WINAPI
testsource_seeking_IsFormatSupported(IMediaSeeking
*iface
, const GUID
*format
)
1181 struct testfilter
*filter
= impl_from_IMediaSeeking(iface
);
1183 ok(IsEqualGUID(format
, &TIME_FORMAT_MEDIA_TIME
),
1184 "Got format %s.\n", wine_dbgstr_guid(format
));
1186 return filter
->is_format_supported_hr
;
1189 static HRESULT WINAPI
testsource_seeking_QueryPreferredFormat(IMediaSeeking
*iface
, GUID
*format
)
1191 ok(0, "Unexpected call.\n");
1195 static HRESULT WINAPI
testsource_seeking_GetTimeFormat(IMediaSeeking
*iface
, GUID
*format
)
1197 ok(0, "Unexpected call.\n");
1201 static HRESULT WINAPI
testsource_seeking_IsUsingTimeFormat(IMediaSeeking
*iface
, const GUID
*format
)
1203 ok(0, "Unexpected call.\n");
1207 static HRESULT WINAPI
testsource_seeking_SetTimeFormat(IMediaSeeking
*iface
, const GUID
*format
)
1209 ok(0, "Unexpected call.\n");
1213 static HRESULT WINAPI
testsource_seeking_GetDuration(IMediaSeeking
*iface
, LONGLONG
*duration
)
1215 struct testfilter
*filter
= impl_from_IMediaSeeking(iface
);
1217 if (SUCCEEDED(filter
->get_duration_hr
))
1218 *duration
= 0x8000000000000000ULL
;
1220 return filter
->get_duration_hr
;
1223 static HRESULT WINAPI
testsource_seeking_GetStopPosition(IMediaSeeking
*iface
, LONGLONG
*stop
)
1225 struct testfilter
*filter
= impl_from_IMediaSeeking(iface
);
1227 if (SUCCEEDED(filter
->get_stop_position_hr
))
1228 *stop
= 0x8000000000000000ULL
;
1230 return filter
->get_stop_position_hr
;
1233 static HRESULT WINAPI
testsource_seeking_GetCurrentPosition(IMediaSeeking
*iface
, LONGLONG
*current
)
1235 ok(0, "Unexpected call.\n");
1239 static HRESULT WINAPI
testsource_seeking_ConvertTimeFormat(IMediaSeeking
*iface
, LONGLONG
*target
,
1240 const GUID
*target_format
, LONGLONG source
, const GUID
*source_format
)
1242 ok(0, "Unexpected call.\n");
1246 static HRESULT WINAPI
testsource_seeking_SetPositions(IMediaSeeking
*iface
, LONGLONG
*current_ptr
, DWORD current_flags
,
1247 LONGLONG
*stop_ptr
, DWORD stop_flags
)
1249 struct testfilter
*filter
= impl_from_IMediaSeeking(iface
);
1251 if (SUCCEEDED(filter
->set_positions_hr
))
1254 filter
->current_position
= *current_ptr
;
1257 filter
->stop_position
= *stop_ptr
;
1260 return filter
->set_positions_hr
;
1263 static HRESULT WINAPI
testsource_seeking_GetPositions(IMediaSeeking
*iface
, LONGLONG
*current
, LONGLONG
*stop
)
1265 ok(0, "Unexpected call.\n");
1269 static HRESULT WINAPI
testsource_seeking_GetAvailable(IMediaSeeking
*iface
, LONGLONG
*earliest
, LONGLONG
*latest
)
1271 ok(0, "Unexpected call.\n");
1275 static HRESULT WINAPI
testsource_seeking_SetRate(IMediaSeeking
*iface
, double rate
)
1277 ok(0, "Unexpected call.\n");
1281 static HRESULT WINAPI
testsource_seeking_GetRate(IMediaSeeking
*iface
, double *rate
)
1283 ok(0, "Unexpected call.\n");
1287 static HRESULT WINAPI
testsource_seeking_GetPreroll(IMediaSeeking
*iface
, LONGLONG
*preroll
)
1289 ok(0, "Unexpected call.\n");
1293 static const IMediaSeekingVtbl testsource_seeking_vtbl
=
1295 testsource_seeking_QueryInterface
,
1296 testsource_seeking_AddRef
,
1297 testsource_seeking_Release
,
1298 testsource_seeking_GetCapabilities
,
1299 testsource_seeking_CheckCapabilities
,
1300 testsource_seeking_IsFormatSupported
,
1301 testsource_seeking_QueryPreferredFormat
,
1302 testsource_seeking_GetTimeFormat
,
1303 testsource_seeking_IsUsingTimeFormat
,
1304 testsource_seeking_SetTimeFormat
,
1305 testsource_seeking_GetDuration
,
1306 testsource_seeking_GetStopPosition
,
1307 testsource_seeking_GetCurrentPosition
,
1308 testsource_seeking_ConvertTimeFormat
,
1309 testsource_seeking_SetPositions
,
1310 testsource_seeking_GetPositions
,
1311 testsource_seeking_GetAvailable
,
1312 testsource_seeking_SetRate
,
1313 testsource_seeking_GetRate
,
1314 testsource_seeking_GetPreroll
,
1317 #define check_get_stream(a,b,c,d) check_get_stream_(__LINE__,a,b,c,d)
1318 static void check_get_stream_(int line
, IAMMultiMediaStream
*mmstream
,
1319 IMediaStreamFilter
*filter
, const GUID
*mspid
, IMediaStream
*expect
)
1321 IMediaStream
*stream
= NULL
, *stream2
= NULL
;
1324 hr
= IAMMultiMediaStream_GetMediaStream(mmstream
, mspid
, &stream
);
1325 ok_(__FILE__
, line
)(hr
== (expect
? S_OK
: MS_E_NOSTREAM
),
1326 "IAMMultiMediaStream::GetMediaStream() returned %#x.\n", hr
);
1327 hr
= IMediaStreamFilter_GetMediaStream(filter
, mspid
, &stream2
);
1328 ok_(__FILE__
, line
)(hr
== (expect
? S_OK
: MS_E_NOSTREAM
),
1329 "IMediaStreamFilter::GetMediaStream() returned %#x.\n", hr
);
1332 ok_(__FILE__
, line
)(stream
== expect
, "Expected stream %p, got %p.\n", expect
, stream
);
1333 ok_(__FILE__
, line
)(stream2
== expect
, "Expected stream %p, got %p.\n", expect
, stream2
);
1336 if (stream
) IMediaStream_Release(stream
);
1337 if (stream2
) IMediaStream_Release(stream2
);
1340 static void test_add_stream(void)
1342 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
1343 IMediaStream
*video_stream
, *audio_stream
, *stream
;
1344 IDirectDrawMediaStream
*ddraw_stream
;
1345 IMediaStreamFilter
*stream_filter
;
1346 struct teststream teststream
;
1347 IDirectDraw
*ddraw
, *ddraw2
;
1348 IEnumFilters
*enum_filters
;
1349 IBaseFilter
*filters
[3];
1350 IGraphBuilder
*graph
;
1356 teststream_init(&teststream
);
1358 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &stream_filter
);
1359 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1361 hr
= IAMMultiMediaStream_EnumMediaStreams(mmstream
, 0, NULL
);
1362 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1363 hr
= IMediaStreamFilter_EnumMediaStreams(stream_filter
, 0, NULL
);
1364 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1366 hr
= IAMMultiMediaStream_GetMediaStream(mmstream
, &MSPID_PrimaryAudio
, NULL
);
1367 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
1368 hr
= IMediaStreamFilter_GetMediaStream(stream_filter
, &MSPID_PrimaryAudio
, NULL
);
1369 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
1370 hr
= IAMMultiMediaStream_GetMediaStream(mmstream
, &MSPID_PrimaryVideo
, NULL
);
1371 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
1372 hr
= IMediaStreamFilter_GetMediaStream(stream_filter
, &MSPID_PrimaryVideo
, NULL
);
1373 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
1375 check_enum_stream(mmstream
, stream_filter
, 0, NULL
);
1377 check_get_stream(mmstream
, stream_filter
, NULL
, NULL
);
1378 check_get_stream(mmstream
, stream_filter
, &MSPID_PrimaryAudio
, NULL
);
1379 check_get_stream(mmstream
, stream_filter
, &MSPID_PrimaryVideo
, NULL
);
1380 check_get_stream(mmstream
, stream_filter
, &test_mspid
, NULL
);
1382 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &test_mspid
, 0, &stream
);
1383 ok(hr
== MS_E_PURPOSEID
, "Got hr %#x.\n", hr
);
1385 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &video_stream
);
1386 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1388 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
1389 ok(hr
== MS_E_PURPOSEID
, "Got hr %#x.\n", hr
);
1391 hr
= IAMMultiMediaStream_EnumMediaStreams(mmstream
, 0, NULL
);
1392 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
1393 hr
= IMediaStreamFilter_EnumMediaStreams(stream_filter
, 0, NULL
);
1394 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
1395 hr
= IAMMultiMediaStream_EnumMediaStreams(mmstream
, 1, NULL
);
1396 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1397 hr
= IMediaStreamFilter_EnumMediaStreams(stream_filter
, 1, NULL
);
1398 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1400 check_enum_stream(mmstream
, stream_filter
, 0, video_stream
);
1401 check_enum_stream(mmstream
, stream_filter
, 1, NULL
);
1403 check_get_stream(mmstream
, stream_filter
, &MSPID_PrimaryVideo
, video_stream
);
1404 check_get_stream(mmstream
, stream_filter
, &MSPID_PrimaryAudio
, NULL
);
1405 check_get_stream(mmstream
, stream_filter
, &test_mspid
, NULL
);
1407 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &audio_stream
);
1408 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1410 check_enum_stream(mmstream
, stream_filter
, 0, video_stream
);
1411 check_enum_stream(mmstream
, stream_filter
, 1, audio_stream
);
1412 check_enum_stream(mmstream
, stream_filter
, 2, NULL
);
1414 check_get_stream(mmstream
, stream_filter
, &MSPID_PrimaryVideo
, video_stream
);
1415 check_get_stream(mmstream
, stream_filter
, &MSPID_PrimaryAudio
, audio_stream
);
1416 check_get_stream(mmstream
, stream_filter
, &test_mspid
, NULL
);
1418 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)&teststream
, &IID_IUnknown
, 0, &stream
);
1419 ok(hr
== MS_E_PURPOSEID
, "Got hr %#x.\n", hr
);
1421 hr
= IMediaStreamFilter_QueryFilterInfo(stream_filter
, &info
);
1422 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1424 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)&teststream
, &test_mspid
, 0, &stream
);
1425 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1426 ok(stream
== (IMediaStream
*)&teststream
, "Streams didn't match.\n");
1427 IMediaStream_Release(stream
);
1428 ok(teststream
.mmstream
== mmstream
, "IAMMultiMediaStream objects didn't match.\n");
1429 ok(teststream
.filter
== stream_filter
, "IMediaStreamFilter objects didn't match.\n");
1430 ok(teststream
.graph
== info
.pGraph
, "IFilterGraph objects didn't match.\n");
1432 IFilterGraph_Release(info
.pGraph
);
1434 check_enum_stream(mmstream
, stream_filter
, 0, video_stream
);
1435 check_enum_stream(mmstream
, stream_filter
, 1, audio_stream
);
1436 check_enum_stream(mmstream
, stream_filter
, 2, (IMediaStream
*)&teststream
);
1437 check_enum_stream(mmstream
, stream_filter
, 3, NULL
);
1439 check_get_stream(mmstream
, stream_filter
, &MSPID_PrimaryVideo
, video_stream
);
1440 check_get_stream(mmstream
, stream_filter
, &MSPID_PrimaryAudio
, audio_stream
);
1441 check_get_stream(mmstream
, stream_filter
, &test_mspid
, (IMediaStream
*)&teststream
);
1443 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
1444 ok(hr
== MS_E_PURPOSEID
, "Got hr %#x.\n", hr
);
1446 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
1447 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1448 ok(!!graph
, "Expected a non-NULL graph.\n");
1450 hr
= IGraphBuilder_EnumFilters(graph
, &enum_filters
);
1451 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1452 hr
= IEnumFilters_Next(enum_filters
, 3, filters
, &count
);
1453 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1454 ok(count
== 1, "Got count %u.\n", count
);
1455 ok(filters
[0] == (IBaseFilter
*)stream_filter
,
1456 "Expected filter %p, got %p.\n", stream_filter
, filters
[0]);
1457 IBaseFilter_Release(filters
[0]);
1458 IEnumFilters_Release(enum_filters
);
1459 IGraphBuilder_Release(graph
);
1461 IMediaStreamFilter_Release(stream_filter
);
1462 ref
= IAMMultiMediaStream_Release(mmstream
);
1463 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1464 ref
= IMediaStream_Release(video_stream
);
1465 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1466 ref
= IMediaStream_Release(audio_stream
);
1467 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1468 ok(teststream
.refcount
== 1, "Got outstanding refcount %d.\n", teststream
.refcount
);
1470 /* The return parameter is optional. */
1472 mmstream
= create_ammultimediastream();
1474 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, NULL
);
1475 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1477 hr
= IAMMultiMediaStream_GetMediaStream(mmstream
, &MSPID_PrimaryVideo
, &stream
);
1478 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1479 IMediaStream_Release(stream
);
1481 ref
= IAMMultiMediaStream_Release(mmstream
);
1482 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1484 /* Test supplying a DirectDraw object with the primary video stream. */
1486 hr
= DirectDrawCreate(NULL
, &ddraw
, NULL
);
1487 ok(hr
== DD_OK
, "Got hr %#x.\n", hr
);
1488 mmstream
= create_ammultimediastream();
1490 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)ddraw
, &MSPID_PrimaryVideo
, 0, &video_stream
);
1491 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1493 hr
= IMediaStream_QueryInterface(video_stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
1494 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1495 hr
= IDirectDrawMediaStream_GetDirectDraw(ddraw_stream
, &ddraw2
);
1496 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1497 ok(ddraw2
== ddraw
, "Expected IDirectDraw %p, got %p.\n", ddraw
, ddraw2
);
1498 IDirectDraw_Release(ddraw2
);
1499 IDirectDrawMediaStream_Release(ddraw_stream
);
1501 ref
= IAMMultiMediaStream_Release(mmstream
);
1502 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1503 ref
= IMediaStream_Release(video_stream
);
1504 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1505 ref
= IDirectDraw_Release(ddraw
);
1506 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1508 mmstream
= create_ammultimediastream();
1510 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &video_stream
);
1511 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1513 hr
= IMediaStream_QueryInterface(video_stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
1514 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1515 hr
= IDirectDrawMediaStream_GetDirectDraw(ddraw_stream
, &ddraw
);
1516 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1517 ok(!!ddraw
, "Expected a non-NULL IDirectDraw.\n");
1518 IDirectDraw_Release(ddraw
);
1519 IDirectDrawMediaStream_Release(ddraw_stream
);
1521 ref
= IAMMultiMediaStream_Release(mmstream
);
1522 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1523 ref
= IMediaStream_Release(video_stream
);
1524 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1526 /* Test the AMMSF_ADDDEFAULTRENDERER flag. No stream is added; however, a
1527 * new filter will be added to the graph. */
1529 mmstream
= create_ammultimediastream();
1530 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &stream_filter
);
1531 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1533 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
,
1534 AMMSF_ADDDEFAULTRENDERER
, &video_stream
);
1535 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
1537 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
,
1538 AMMSF_ADDDEFAULTRENDERER
, NULL
);
1539 ok(hr
== MS_E_PURPOSEID
, "Got hr %#x.\n", hr
);
1541 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
,
1542 AMMSF_ADDDEFAULTRENDERER
, &audio_stream
);
1543 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
1545 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
,
1546 AMMSF_ADDDEFAULTRENDERER
, NULL
);
1547 ok(hr
== S_OK
|| hr
== VFW_E_NO_AUDIO_HARDWARE
, "Got hr %#x.\n", hr
);
1549 check_enum_stream(mmstream
, stream_filter
, 0, NULL
);
1551 check_get_stream(mmstream
, stream_filter
, &MSPID_PrimaryAudio
, NULL
);
1552 check_get_stream(mmstream
, stream_filter
, &MSPID_PrimaryVideo
, NULL
);
1556 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
1557 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1558 ok(!!graph
, "Got graph %p.\n", graph
);
1559 hr
= IGraphBuilder_EnumFilters(graph
, &enum_filters
);
1560 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1561 hr
= IEnumFilters_Next(enum_filters
, 3, filters
, &count
);
1562 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1563 ok(count
== 2, "Got count %u.\n", count
);
1564 ok(filters
[1] == (IBaseFilter
*)stream_filter
,
1565 "Expected filter %p, got %p.\n", stream_filter
, filters
[1]);
1566 hr
= IBaseFilter_GetClassID(filters
[0], &clsid
);
1567 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1568 ok(IsEqualGUID(&clsid
, &CLSID_DSoundRender
), "Got unexpected filter %s.\n", wine_dbgstr_guid(&clsid
));
1569 IBaseFilter_Release(filters
[0]);
1570 IBaseFilter_Release(filters
[1]);
1571 IEnumFilters_Release(enum_filters
);
1572 IGraphBuilder_Release(graph
);
1575 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &test_mspid
,
1576 AMMSF_ADDDEFAULTRENDERER
, NULL
);
1577 ok(hr
== MS_E_PURPOSEID
, "Got hr %#x.\n", hr
);
1578 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &test_mspid
,
1579 AMMSF_ADDDEFAULTRENDERER
, &audio_stream
);
1580 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
1582 ref
= IAMMultiMediaStream_Release(mmstream
);
1583 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1584 ref
= IMediaStreamFilter_Release(stream_filter
);
1585 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1588 static void test_media_streams(void)
1590 IAMMultiMediaStream
*pams
;
1592 IMediaStream
*video_stream
= NULL
;
1593 IMediaStream
*audio_stream
= NULL
;
1594 IMediaStreamFilter
* media_stream_filter
= NULL
;
1596 if (!(pams
= create_ammultimediastream()))
1599 hr
= IAMMultiMediaStream_Initialize(pams
, STREAMTYPE_READ
, 0, NULL
);
1600 ok(hr
== S_OK
, "IAMMultiMediaStream_Initialize returned: %x\n", hr
);
1602 /* Retrieve media stream filter */
1603 hr
= IAMMultiMediaStream_GetFilter(pams
, NULL
);
1604 ok(hr
== E_POINTER
, "IAMMultiMediaStream_GetFilter returned: %x\n", hr
);
1605 hr
= IAMMultiMediaStream_GetFilter(pams
, &media_stream_filter
);
1606 ok(hr
== S_OK
, "IAMMultiMediaStream_GetFilter returned: %x\n", hr
);
1608 hr
= IAMMultiMediaStream_AddMediaStream(pams
, NULL
, &MSPID_PrimaryVideo
, 0, NULL
);
1609 ok(hr
== S_OK
, "IAMMultiMediaStream_AddMediaStream returned: %x\n", hr
);
1610 hr
= IAMMultiMediaStream_GetMediaStream(pams
, &MSPID_PrimaryVideo
, &video_stream
);
1611 ok(hr
== S_OK
, "IAMMultiMediaStream_GetMediaStream returned: %x\n", hr
);
1613 /* Check interfaces and samples for video */
1616 IAMMediaStream
* am_media_stream
;
1617 IMultiMediaStream
*multi_media_stream
;
1619 IAudioMediaStream
* audio_media_stream
;
1620 IDirectDrawMediaStream
*ddraw_stream
= NULL
;
1621 IDirectDrawStreamSample
*ddraw_sample
= NULL
;
1623 hr
= IMediaStream_QueryInterface(video_stream
, &IID_IAMMediaStream
, (LPVOID
*)&am_media_stream
);
1624 ok(hr
== S_OK
, "IMediaStream_QueryInterface returned: %x\n", hr
);
1625 ok((void*)am_media_stream
== (void*)video_stream
, "Not same interface, got %p expected %p\n", am_media_stream
, video_stream
);
1627 hr
= IAMMediaStream_GetMultiMediaStream(am_media_stream
, NULL
);
1628 ok(hr
== E_POINTER
, "Expected E_POINTER, got %x\n", hr
);
1630 multi_media_stream
= (void *)0xdeadbeef;
1631 hr
= IAMMediaStream_GetMultiMediaStream(am_media_stream
, &multi_media_stream
);
1632 ok(hr
== S_OK
, "IAMMediaStream_GetMultiMediaStream returned: %x\n", hr
);
1633 ok((void *)multi_media_stream
== (void *)pams
, "Expected %p, got %p\n", pams
, multi_media_stream
);
1634 IMultiMediaStream_Release(multi_media_stream
);
1636 IAMMediaStream_Release(am_media_stream
);
1638 hr
= IMediaStream_QueryInterface(video_stream
, &IID_IPin
, (void **)&pin
);
1639 ok(hr
== S_OK
, "IMediaStream_QueryInterface returned: %x\n", hr
);
1643 hr
= IMediaStream_QueryInterface(video_stream
, &IID_IAudioMediaStream
, (LPVOID
*)&audio_media_stream
);
1644 ok(hr
== E_NOINTERFACE
, "IMediaStream_QueryInterface returned: %x\n", hr
);
1646 hr
= IMediaStream_QueryInterface(video_stream
, &IID_IDirectDrawMediaStream
, (LPVOID
*)&ddraw_stream
);
1647 ok(hr
== S_OK
, "IMediaStream_QueryInterface returned: %x\n", hr
);
1651 DDSURFACEDESC current_format
, desired_format
;
1652 IDirectDrawPalette
*palette
;
1655 hr
= IDirectDrawMediaStream_GetFormat(ddraw_stream
, ¤t_format
, &palette
, &desired_format
, &flags
);
1656 ok(hr
== MS_E_NOSTREAM
, "IDirectDrawoMediaStream_GetFormat returned: %x\n", hr
);
1658 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, &ddraw_sample
);
1659 ok(hr
== S_OK
, "IDirectDrawMediaStream_CreateSample returned: %x\n", hr
);
1661 hr
= IDirectDrawMediaStream_GetMultiMediaStream(ddraw_stream
, NULL
);
1662 ok(hr
== E_POINTER
, "Expected E_POINTER, got %x\n", hr
);
1664 multi_media_stream
= (void *)0xdeadbeef;
1665 hr
= IDirectDrawMediaStream_GetMultiMediaStream(ddraw_stream
, &multi_media_stream
);
1666 ok(hr
== S_OK
, "IDirectDrawMediaStream_GetMultiMediaStream returned: %x\n", hr
);
1667 ok((void *)multi_media_stream
== (void *)pams
, "Expected %p, got %p\n", pams
, multi_media_stream
);
1668 IMultiMediaStream_Release(multi_media_stream
);
1672 IDirectDrawStreamSample_Release(ddraw_sample
);
1674 IDirectDrawMediaStream_Release(ddraw_stream
);
1677 hr
= IAMMultiMediaStream_AddMediaStream(pams
, NULL
, &MSPID_PrimaryAudio
, 0, NULL
);
1678 ok(hr
== S_OK
, "IAMMultiMediaStream_AddMediaStream returned: %x\n", hr
);
1679 hr
= IAMMultiMediaStream_GetMediaStream(pams
, &MSPID_PrimaryAudio
, &audio_stream
);
1680 ok(hr
== S_OK
, "IAMMultiMediaStream_GetMediaStream returned: %x\n", hr
);
1682 /* Check interfaces and samples for audio */
1685 IAMMediaStream
* am_media_stream
;
1686 IMultiMediaStream
*multi_media_stream
;
1688 IDirectDrawMediaStream
* ddraw_stream
= NULL
;
1689 IAudioMediaStream
* audio_media_stream
= NULL
;
1690 IAudioStreamSample
*audio_sample
= NULL
;
1692 hr
= IMediaStream_QueryInterface(audio_stream
, &IID_IAMMediaStream
, (LPVOID
*)&am_media_stream
);
1693 ok(hr
== S_OK
, "IMediaStream_QueryInterface returned: %x\n", hr
);
1694 ok((void*)am_media_stream
== (void*)audio_stream
, "Not same interface, got %p expected %p\n", am_media_stream
, audio_stream
);
1696 hr
= IAMMediaStream_GetMultiMediaStream(am_media_stream
, NULL
);
1697 ok(hr
== E_POINTER
, "Expected E_POINTER, got %x\n", hr
);
1699 multi_media_stream
= (void *)0xdeadbeef;
1700 hr
= IAMMediaStream_GetMultiMediaStream(am_media_stream
, &multi_media_stream
);
1701 ok(hr
== S_OK
, "IAMMediaStream_GetMultiMediaStream returned: %x\n", hr
);
1702 ok((void *)multi_media_stream
== (void *)pams
, "Expected %p, got %p\n", pams
, multi_media_stream
);
1703 IMultiMediaStream_Release(multi_media_stream
);
1705 IAMMediaStream_Release(am_media_stream
);
1707 hr
= IMediaStream_QueryInterface(audio_stream
, &IID_IPin
, (void **)&pin
);
1708 ok(hr
== S_OK
, "IMediaStream_QueryInterface returned: %x\n", hr
);
1712 hr
= IMediaStream_QueryInterface(audio_stream
, &IID_IDirectDrawMediaStream
, (LPVOID
*)&ddraw_stream
);
1713 ok(hr
== E_NOINTERFACE
, "IMediaStream_QueryInterface returned: %x\n", hr
);
1715 hr
= IMediaStream_QueryInterface(audio_stream
, &IID_IAudioMediaStream
, (LPVOID
*)&audio_media_stream
);
1716 ok(hr
== S_OK
, "IMediaStream_QueryInterface returned: %x\n", hr
);
1720 IAudioData
* audio_data
= NULL
;
1722 hr
= CoCreateInstance(&CLSID_AMAudioData
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAudioData
, (void **)&audio_data
);
1723 ok(hr
== S_OK
, "CoCreateInstance returned: %x\n", hr
);
1725 hr
= IAudioMediaStream_CreateSample(audio_media_stream
, NULL
, 0, &audio_sample
);
1726 ok(hr
== E_POINTER
, "IAudioMediaStream_CreateSample returned: %x\n", hr
);
1728 EXPECT_REF(audio_stream
, 3);
1729 EXPECT_REF(audio_data
, 1);
1730 hr
= IAudioMediaStream_CreateSample(audio_media_stream
, audio_data
, 0, &audio_sample
);
1731 ok(hr
== S_OK
, "IAudioMediaStream_CreateSample returned: %x\n", hr
);
1732 EXPECT_REF(audio_stream
, 4);
1733 EXPECT_REF(audio_data
, 2);
1735 hr
= IAudioMediaStream_GetMultiMediaStream(audio_media_stream
, NULL
);
1736 ok(hr
== E_POINTER
, "Expected E_POINTER, got %x\n", hr
);
1738 multi_media_stream
= (void *)0xdeadbeef;
1739 hr
= IAudioMediaStream_GetMultiMediaStream(audio_media_stream
, &multi_media_stream
);
1740 ok(hr
== S_OK
, "IAudioMediaStream_GetMultiMediaStream returned: %x\n", hr
);
1741 ok((void *)multi_media_stream
== (void *)pams
, "Expected %p, got %p\n", pams
, multi_media_stream
);
1742 IMultiMediaStream_Release(multi_media_stream
);
1745 IAudioData_Release(audio_data
);
1747 IAudioStreamSample_Release(audio_sample
);
1748 if (audio_media_stream
)
1749 IAudioMediaStream_Release(audio_media_stream
);
1753 if (media_stream_filter
)
1755 IEnumPins
*enum_pins
;
1757 hr
= IMediaStreamFilter_EnumPins(media_stream_filter
, &enum_pins
);
1758 ok(hr
== S_OK
, "IBaseFilter_EnumPins returned: %x\n", hr
);
1761 IPin
* pins
[3] = { NULL
, NULL
, NULL
};
1763 ULONG expected_nb_pins
= audio_stream
? 2 : 1;
1766 hr
= IEnumPins_Next(enum_pins
, 3, pins
, &nb_pins
);
1767 ok(SUCCEEDED(hr
), "IEnumPins_Next returned: %x\n", hr
);
1768 ok(nb_pins
== expected_nb_pins
, "Number of pins is %u instead of %u\n", nb_pins
, expected_nb_pins
);
1769 for (i
= 0; i
< min(nb_pins
, expected_nb_pins
); i
++)
1773 hr
= IPin_ConnectedTo(pins
[i
], &pin
);
1774 ok(hr
== VFW_E_NOT_CONNECTED
, "IPin_ConnectedTo returned: %x\n", hr
);
1775 IPin_Release(pins
[i
]);
1777 IEnumPins_Release(enum_pins
);
1781 /* Test open file with no filename */
1782 hr
= IAMMultiMediaStream_OpenFile(pams
, NULL
, 0);
1783 ok(hr
== E_POINTER
, "IAMMultiMediaStream_OpenFile returned %x instead of %x\n", hr
, E_POINTER
);
1786 IMediaStream_Release(video_stream
);
1788 IMediaStream_Release(audio_stream
);
1789 if (media_stream_filter
)
1790 IMediaStreamFilter_Release(media_stream_filter
);
1792 IAMMultiMediaStream_Release(pams
);
1795 static void test_enum_pins(void)
1797 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
1798 IMediaStreamFilter
*filter
;
1799 IEnumPins
*enum1
, *enum2
;
1800 IMediaStream
*stream
;
1801 IPin
*pins
[3], *pin
;
1805 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
1806 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1808 ref
= get_refcount(filter
);
1809 ok(ref
== 3, "Got unexpected refcount %d.\n", ref
);
1811 hr
= IMediaStreamFilter_EnumPins(filter
, NULL
);
1812 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
1814 hr
= IMediaStreamFilter_EnumPins(filter
, &enum1
);
1815 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1816 ref
= get_refcount(filter
);
1817 ok(ref
== 3, "Got unexpected refcount %d.\n", ref
);
1818 ref
= get_refcount(enum1
);
1819 ok(ref
== 1, "Got unexpected refcount %d.\n", ref
);
1821 hr
= IEnumPins_Next(enum1
, 1, NULL
, NULL
);
1822 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
1824 hr
= IEnumPins_Next(enum1
, 1, pins
, NULL
);
1825 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1827 hr
= IEnumPins_Reset(enum1
);
1828 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1830 hr
= IEnumPins_Skip(enum1
, 0);
1831 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1833 hr
= IEnumPins_Skip(enum1
, 1);
1834 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1836 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
1837 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1838 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
1839 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1841 /* Reset() isn't enough; we have to call EnumPins() again to see the updated
1843 hr
= IEnumPins_Reset(enum1
);
1844 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1846 hr
= IEnumPins_Next(enum1
, 1, pins
, NULL
);
1847 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1849 IEnumPins_Release(enum1
);
1851 hr
= IMediaStreamFilter_EnumPins(filter
, &enum1
);
1852 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1854 ref
= get_refcount(filter
);
1855 ok(ref
== 4, "Got unexpected refcount %d.\n", ref
);
1856 ref
= get_refcount(enum1
);
1857 ok(ref
== 1, "Got unexpected refcount %d.\n", ref
);
1858 ref
= get_refcount(pin
);
1859 ok(ref
== 4, "Got unexpected refcount %d.\n", ref
);
1861 hr
= IEnumPins_Next(enum1
, 1, pins
, NULL
);
1862 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1863 ok(pins
[0] == pin
, "Expected pin %p, got %p.\n", pin
, pins
[0]);
1864 ref
= get_refcount(filter
);
1865 ok(ref
== 4, "Got unexpected refcount %d.\n", ref
);
1866 ref
= get_refcount(enum1
);
1867 ok(ref
== 1, "Got unexpected refcount %d.\n", ref
);
1868 ref
= get_refcount(pin
);
1869 ok(ref
== 5, "Got unexpected refcount %d.\n", ref
);
1870 IPin_Release(pins
[0]);
1872 hr
= IEnumPins_Next(enum1
, 1, pins
, NULL
);
1873 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1875 hr
= IEnumPins_Reset(enum1
);
1876 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1878 hr
= IEnumPins_Next(enum1
, 1, pins
, &count
);
1879 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1880 ok(count
== 1, "Got count %u.\n", count
);
1881 ok(pins
[0] == pin
, "Expected pin %p, got %p.\n", pin
, pins
[0]);
1882 IPin_Release(pins
[0]);
1884 hr
= IEnumPins_Reset(enum1
);
1885 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1887 hr
= IEnumPins_Next(enum1
, 2, pins
, NULL
);
1888 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
1890 hr
= IEnumPins_Next(enum1
, 2, pins
, &count
);
1891 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1892 ok(count
== 1, "Got count %u.\n", count
);
1893 ok(pins
[0] == pin
, "Expected pin %p, got %p.\n", pin
, pins
[0]);
1894 IPin_Release(pins
[0]);
1896 hr
= IEnumPins_Reset(enum1
);
1897 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1899 hr
= IEnumPins_Clone(enum1
, &enum2
);
1900 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1902 hr
= IEnumPins_Skip(enum1
, 0);
1903 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1905 hr
= IEnumPins_Skip(enum1
, 1);
1906 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1908 hr
= IEnumPins_Next(enum1
, 1, pins
, NULL
);
1909 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
1911 hr
= IEnumPins_Next(enum2
, 1, pins
, NULL
);
1912 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1913 ok(pins
[0] == pin
, "Expected pin %p, got %p.\n", pin
, pins
[0]);
1914 IPin_Release(pins
[0]);
1916 IEnumPins_Release(enum2
);
1917 IEnumPins_Release(enum1
);
1919 IMediaStreamFilter_Release(filter
);
1920 ref
= IAMMultiMediaStream_Release(mmstream
);
1921 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1922 IMediaStream_Release(stream
);
1923 ref
= IPin_Release(pin
);
1924 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1927 static void test_find_pin(void)
1929 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
1930 IMediaStreamFilter
*filter
;
1931 IMediaStream
*stream
;
1936 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
1937 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1939 hr
= IMediaStreamFilter_FindPin(filter
, primary_video_sink_id
, &pin2
);
1940 ok(hr
== VFW_E_NOT_FOUND
, "Got hr %#x.\n", hr
);
1942 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
1943 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1944 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
1945 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1947 hr
= IMediaStreamFilter_FindPin(filter
, primary_video_sink_id
, &pin2
);
1948 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1949 ok(pin2
== pin
, "Expected pin %p, got %p.\n", pin
, pin2
);
1953 IMediaStream_Release(stream
);
1954 IMediaStreamFilter_Release(filter
);
1955 ref
= IAMMultiMediaStream_Release(mmstream
);
1956 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
1959 static void test_pin_info(void)
1961 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
1962 IMediaStreamFilter
*filter
;
1963 IMediaStream
*stream
;
1971 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
1972 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1974 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
1975 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1976 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
1977 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1979 hr
= IPin_QueryPinInfo(pin
, &info
);
1980 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1981 ok(info
.pFilter
== (IBaseFilter
*)filter
, "Expected filter %p, got %p.\n", filter
, info
.pFilter
);
1982 ok(info
.dir
== PINDIR_INPUT
, "Got direction %d.\n", info
.dir
);
1983 ok(!wcscmp(info
.achName
, primary_video_sink_id
), "Got name %s.\n", wine_dbgstr_w(info
.achName
));
1984 IBaseFilter_Release(info
.pFilter
);
1986 hr
= IPin_QueryDirection(pin
, &dir
);
1987 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1988 ok(dir
== PINDIR_INPUT
, "Got direction %d.\n", dir
);
1990 hr
= IPin_QueryId(pin
, &id
);
1991 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
1992 ok(!wcscmp(id
, primary_video_sink_id
), "Got id %s.\n", wine_dbgstr_w(id
));
1995 hr
= IPin_QueryInternalConnections(pin
, NULL
, &count
);
1996 ok(hr
== E_NOTIMPL
, "Got hr %#x.\n", hr
);
1999 IMediaStream_Release(stream
);
2001 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
2002 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2003 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
2004 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2006 hr
= IPin_QueryPinInfo(pin
, &info
);
2007 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2008 ok(info
.pFilter
== (IBaseFilter
*)filter
, "Expected filter %p, got %p.\n", filter
, info
.pFilter
);
2009 ok(info
.dir
== PINDIR_INPUT
, "Got direction %d.\n", info
.dir
);
2010 ok(!wcscmp(info
.achName
, primary_audio_sink_id
), "Got name %s.\n", wine_dbgstr_w(info
.achName
));
2011 IBaseFilter_Release(info
.pFilter
);
2013 hr
= IPin_QueryDirection(pin
, &dir
);
2014 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2015 ok(dir
== PINDIR_INPUT
, "Got direction %d.\n", dir
);
2017 hr
= IPin_QueryId(pin
, &id
);
2018 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2019 ok(!wcscmp(id
, primary_audio_sink_id
), "Got id %s.\n", wine_dbgstr_w(id
));
2022 hr
= IPin_QueryInternalConnections(pin
, NULL
, &count
);
2023 ok(hr
== E_NOTIMPL
, "Got hr %#x.\n", hr
);
2026 IMediaStream_Release(stream
);
2028 IMediaStreamFilter_Release(filter
);
2029 ref
= IAMMultiMediaStream_Release(mmstream
);
2030 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
2033 static IUnknown
*graph_inner_unk
;
2034 static IFilterGraph2
*graph_inner
;
2035 static LONG graph_refcount
= 1;
2036 static unsigned int got_add_filter
;
2037 static IBaseFilter
*graph_filter
;
2038 static WCHAR graph_filter_name
[128];
2040 static HRESULT WINAPI
graph_QueryInterface(IFilterGraph2
*iface
, REFIID iid
, void **out
)
2042 if (winetest_debug
> 1) trace("QueryInterface(%s)\n", wine_dbgstr_guid(iid
));
2043 if (IsEqualGUID(iid
, &IID_IFilterGraph2
)
2044 || IsEqualGUID(iid
, &IID_IGraphBuilder
)
2045 || IsEqualGUID(iid
, &IID_IFilterGraph
)
2046 || IsEqualGUID(iid
, &IID_IUnknown
))
2049 IFilterGraph2_AddRef(iface
);
2052 else if (IsEqualGUID(iid
, &IID_IMediaSeeking
)
2053 || IsEqualGUID(iid
, &IID_IMediaControl
)
2054 || IsEqualGUID(iid
, &IID_IMediaEventEx
))
2056 return IUnknown_QueryInterface(graph_inner_unk
, iid
, out
);
2058 return E_NOINTERFACE
;
2061 static ULONG WINAPI
graph_AddRef(IFilterGraph2
*iface
)
2063 return InterlockedIncrement(&graph_refcount
);
2066 static ULONG WINAPI
graph_Release(IFilterGraph2
*iface
)
2068 return InterlockedDecrement(&graph_refcount
);
2071 static HRESULT WINAPI
graph_AddFilter(IFilterGraph2
*iface
, IBaseFilter
*filter
, const WCHAR
*name
)
2073 if (winetest_debug
> 1) trace("AddFilter(%p, %s)\n", filter
, wine_dbgstr_w(name
));
2075 graph_filter
= filter
;
2077 wcscpy(graph_filter_name
, name
);
2079 graph_filter_name
[0] = 0;
2080 return IFilterGraph2_AddFilter(graph_inner
, filter
, name
);
2083 static HRESULT WINAPI
graph_RemoveFilter(IFilterGraph2
*iface
, IBaseFilter
*filter
)
2085 ok(0, "Unexpected call.\n");
2089 static HRESULT WINAPI
graph_EnumFilters(IFilterGraph2
*iface
, IEnumFilters
**enumfilters
)
2091 if (winetest_debug
> 1) trace("EnumFilters()\n");
2092 return IFilterGraph2_EnumFilters(graph_inner
, enumfilters
);
2095 static HRESULT WINAPI
graph_FindFilterByName(IFilterGraph2
*iface
, const WCHAR
*name
, IBaseFilter
**filter
)
2097 ok(0, "Unexpected call.\n");
2101 static HRESULT WINAPI
graph_ConnectDirect(IFilterGraph2
*iface
, IPin
*source
, IPin
*sink
, const AM_MEDIA_TYPE
*mt
)
2103 ok(0, "Unexpected call.\n");
2107 static HRESULT WINAPI
graph_Reconnect(IFilterGraph2
*iface
, IPin
*pin
)
2109 ok(0, "Unexpected call.\n");
2113 static HRESULT WINAPI
graph_Disconnect(IFilterGraph2
*iface
, IPin
*pin
)
2115 ok(0, "Unexpected call.\n");
2119 static HRESULT WINAPI
graph_SetDefaultSyncSource(IFilterGraph2
*iface
)
2121 ok(0, "Unexpected call.\n");
2125 static HRESULT WINAPI
graph_Connect(IFilterGraph2
*iface
, IPin
*source
, IPin
*sink
)
2127 ok(0, "Unexpected call.\n");
2131 static HRESULT WINAPI
graph_Render(IFilterGraph2
*iface
, IPin
*source
)
2133 ok(0, "Unexpected call.\n");
2137 static HRESULT WINAPI
graph_RenderFile(IFilterGraph2
*iface
, const WCHAR
*filename
, const WCHAR
*playlist
)
2139 ok(0, "Unexpected call.\n");
2143 static HRESULT WINAPI
graph_AddSourceFilter(IFilterGraph2
*iface
,
2144 const WCHAR
*filename
, const WCHAR
*filter_name
, IBaseFilter
**filter
)
2146 ok(0, "Unexpected call.\n");
2150 static HRESULT WINAPI
graph_SetLogFile(IFilterGraph2
*iface
, DWORD_PTR file
)
2152 ok(0, "Unexpected call.\n");
2156 static HRESULT WINAPI
graph_Abort(IFilterGraph2
*iface
)
2158 ok(0, "Unexpected call.\n");
2162 static HRESULT WINAPI
graph_ShouldOperationContinue(IFilterGraph2
*iface
)
2164 ok(0, "Unexpected call.\n");
2168 static HRESULT WINAPI
graph_AddSourceFilterForMoniker(IFilterGraph2
*iface
,
2169 IMoniker
*moniker
, IBindCtx
*bind_ctx
, const WCHAR
*filter_name
, IBaseFilter
**filter
)
2171 ok(0, "Unexpected call.\n");
2175 static HRESULT WINAPI
graph_ReconnectEx(IFilterGraph2
*iface
, IPin
*pin
, const AM_MEDIA_TYPE
*mt
)
2177 ok(0, "Unexpected call.\n");
2181 static HRESULT WINAPI
graph_RenderEx(IFilterGraph2
*iface
, IPin
*pin
, DWORD flags
, DWORD
*context
)
2183 ok(0, "Unexpected call.\n");
2187 static const IFilterGraph2Vtbl graph_vtbl
=
2189 graph_QueryInterface
,
2195 graph_FindFilterByName
,
2196 graph_ConnectDirect
,
2199 graph_SetDefaultSyncSource
,
2203 graph_AddSourceFilter
,
2206 graph_ShouldOperationContinue
,
2207 graph_AddSourceFilterForMoniker
,
2212 static void test_initialize(void)
2214 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
2215 IFilterGraph2 graph
= {&graph_vtbl
};
2216 IMediaStreamFilter
*filter
;
2217 IGraphBuilder
*ret_graph
;
2218 IMediaStream
*stream
;
2223 ret_graph
= (IGraphBuilder
*)0xdeadbeef;
2224 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &ret_graph
);
2225 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2226 ok(!ret_graph
, "Got unexpected graph %p.\n", ret_graph
);
2228 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
2229 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2230 ok(!!filter
, "Expected a non-NULL filter.");
2231 IMediaStreamFilter_Release(filter
);
2233 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
2234 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2236 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
2237 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2238 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_WRITE
, 0, NULL
);
2239 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
2240 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_TRANSFORM
, 0, NULL
);
2241 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
2243 ret_graph
= (IGraphBuilder
*)0xdeadbeef;
2244 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &ret_graph
);
2245 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2246 ok(!ret_graph
, "Got unexpected graph %p.\n", ret_graph
);
2248 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
2249 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2251 hr
= IMediaStream_GetInformation(stream
, NULL
, &type
);
2252 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2253 ok(type
== STREAMTYPE_READ
, "Got type %u.\n", type
);
2254 IMediaStream_Release(stream
);
2257 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &ret_graph
);
2258 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2259 ok(!!ret_graph
, "Got unexpected graph %p.\n", ret_graph
);
2260 IGraphBuilder_Release(ret_graph
);
2262 ref
= IAMMultiMediaStream_Release(mmstream
);
2263 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
2265 mmstream
= create_ammultimediastream();
2267 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_WRITE
, 0, NULL
);
2268 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2270 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_WRITE
, 0, NULL
);
2271 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2272 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
2273 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
2274 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_TRANSFORM
, 0, NULL
);
2275 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
2277 ret_graph
= (IGraphBuilder
*)0xdeadbeef;
2278 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &ret_graph
);
2279 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2280 ok(!ret_graph
, "Got unexpected graph %p.\n", ret_graph
);
2282 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
2283 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2285 hr
= IMediaStream_GetInformation(stream
, NULL
, &type
);
2286 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2287 ok(type
== STREAMTYPE_WRITE
, "Got type %u.\n", type
);
2288 IMediaStream_Release(stream
);
2290 ref
= IAMMultiMediaStream_Release(mmstream
);
2291 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
2293 mmstream
= create_ammultimediastream();
2295 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_TRANSFORM
, 0, NULL
);
2296 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2298 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_TRANSFORM
, 0, NULL
);
2299 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2300 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
2301 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
2302 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_WRITE
, 0, NULL
);
2303 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
2305 ret_graph
= (IGraphBuilder
*)0xdeadbeef;
2306 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &ret_graph
);
2307 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2308 ok(!ret_graph
, "Got unexpected graph %p.\n", ret_graph
);
2310 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
2311 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2313 hr
= IMediaStream_GetInformation(stream
, NULL
, &type
);
2314 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2315 ok(type
== STREAMTYPE_TRANSFORM
, "Got type %u.\n", type
);
2316 IMediaStream_Release(stream
);
2318 ref
= IAMMultiMediaStream_Release(mmstream
);
2319 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
2321 mmstream
= create_ammultimediastream();
2323 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
2324 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2327 hr
= IMediaStream_GetInformation(stream
, NULL
, &type
);
2328 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2329 ok(type
== STREAMTYPE_READ
, "Got type %u.\n", type
);
2332 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &ret_graph
);
2333 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2334 ok(!!ret_graph
, "Got unexpected graph %p.\n", ret_graph
);
2335 IGraphBuilder_Release(ret_graph
);
2337 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_TRANSFORM
, 0, NULL
);
2338 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2341 hr
= IMediaStream_GetInformation(stream
, NULL
, &type
);
2342 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2343 ok(type
== STREAMTYPE_READ
, "Got type %u.\n", type
);
2345 IMediaStream_Release(stream
);
2346 ref
= IAMMultiMediaStream_Release(mmstream
);
2347 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
2349 /* Test with a custom filter graph. */
2351 mmstream
= create_ammultimediastream();
2353 CoCreateInstance(&CLSID_FilterGraph
, (IUnknown
*)&graph
, CLSCTX_INPROC_SERVER
,
2354 &IID_IUnknown
, (void **)&graph_inner_unk
);
2355 IUnknown_QueryInterface(graph_inner_unk
, &IID_IFilterGraph2
, (void **)&graph_inner
);
2357 ret_graph
= (IGraphBuilder
*)0xdeadbeef;
2358 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &ret_graph
);
2359 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2360 ok(!ret_graph
, "Got unexpected graph %p.\n", ret_graph
);
2362 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
2363 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2364 ok(!!filter
, "Expected a non-NULL filter.");
2367 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, (IGraphBuilder
*)&graph
);
2368 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2369 ok(got_add_filter
== 1, "Got %d calls to IGraphBuilder::AddFilter().\n", got_add_filter
);
2370 ok(graph_filter
== (IBaseFilter
*)filter
, "Got filter %p.\n", filter
);
2371 ok(!wcscmp(graph_filter_name
, L
"MediaStreamFilter"), "Got unexpected name %s.\n", wine_dbgstr_w(graph_filter_name
));
2373 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &ret_graph
);
2374 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2375 ok(ret_graph
== (IGraphBuilder
*)&graph
, "Got unexpected graph %p.\n", ret_graph
);
2376 IGraphBuilder_Release(ret_graph
);
2379 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, NULL
);
2380 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2381 ok(!got_add_filter
, "Got %d calls to IGraphBuilder::AddFilter().\n", got_add_filter
);
2384 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, NULL
);
2385 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2386 ok(!got_add_filter
, "Got %d calls to IGraphBuilder::AddFilter().\n", got_add_filter
);
2388 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, (IGraphBuilder
*)&graph
);
2389 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
2390 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
2391 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2392 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_WRITE
, 0, NULL
);
2393 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
2394 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_TRANSFORM
, 0, NULL
);
2395 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
2397 IMediaStreamFilter_Release(filter
);
2398 ref
= IAMMultiMediaStream_Release(mmstream
);
2399 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
2400 IFilterGraph2_Release(graph_inner
);
2401 ok(graph_refcount
== 1, "Got outstanding refcount %d.\n", graph_refcount
);
2402 IUnknown_Release(graph_inner_unk
);
2405 static IAMMultiMediaStream
*mmstream_mmstream
;
2406 static STREAM_STATE mmstream_state
;
2408 static DWORD CALLBACK
mmstream_set_state(void *param
)
2412 hr
= IAMMultiMediaStream_SetState(mmstream_mmstream
, mmstream_state
);
2413 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2418 static void test_set_state(void)
2420 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
2421 IMediaControl
*media_control
;
2422 struct testfilter source
;
2423 IGraphBuilder
*graph
;
2429 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
2430 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2431 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, NULL
);
2432 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2433 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
2434 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2435 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
2436 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaControl
, (void **)&media_control
);
2437 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2438 testfilter_init(&source
);
2440 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
2441 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2443 source
.init_stream_hr
= E_FAIL
;
2444 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
2445 ok(hr
== E_FAIL
, "Got hr %#x.\n", hr
);
2446 source
.init_stream_hr
= S_OK
;
2447 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
2448 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2450 source
.init_stream_hr
= S_FALSE
;
2451 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
2452 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2453 source
.init_stream_hr
= S_OK
;
2454 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
2455 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2457 source
.wait_state_hr
= E_FAIL
;
2458 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
2459 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2460 source
.wait_state_hr
= S_OK
;
2461 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
2462 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2464 source
.wait_state_hr
= VFW_S_STATE_INTERMEDIATE
;
2465 ResetEvent(source
.wait_state_event
);
2467 mmstream_mmstream
= mmstream
;
2468 mmstream_state
= STREAMSTATE_RUN
;
2469 thread
= CreateThread(NULL
, 0, mmstream_set_state
, NULL
, 0, NULL
);
2471 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "SetState returned prematurely.\n");
2473 EnterCriticalSection(&source
.filter
.filter_cs
);
2474 source
.wait_state_hr
= S_OK
;
2475 SetEvent(source
.wait_state_event
);
2476 LeaveCriticalSection(&source
.filter
.filter_cs
);
2478 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
2479 CloseHandle(thread
);
2481 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
2482 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2484 source
.init_stream_hr
= E_FAIL
;
2485 source
.wait_state_hr
= VFW_S_STATE_INTERMEDIATE
;
2486 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
2487 ok(hr
== E_FAIL
, "Got hr %#x.\n", hr
);
2488 source
.init_stream_hr
= S_OK
;
2489 source
.wait_state_hr
= S_OK
;
2490 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
2491 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2493 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
2494 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2495 source
.cleanup_stream_hr
= E_FAIL
;
2496 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
2497 ok(hr
== E_FAIL
, "Got hr %#x.\n", hr
);
2498 source
.cleanup_stream_hr
= S_OK
;
2499 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
2500 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2502 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
2503 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2504 source
.cleanup_stream_hr
= S_FALSE
;
2505 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
2506 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
2507 source
.cleanup_stream_hr
= S_OK
;
2509 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
2510 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2511 source
.wait_state_hr
= VFW_S_STATE_INTERMEDIATE
;
2512 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
2513 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2514 source
.wait_state_hr
= S_OK
;
2516 /* Crashes on native. */
2519 hr
= IAMMultiMediaStream_GetState(mmstream
, NULL
);
2520 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
2524 hr
= IAMMultiMediaStream_GetState(mmstream
, &state
);
2525 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2526 ok(state
== STREAMSTATE_STOP
, "Got state %#x.\n", state
);
2528 hr
= IMediaControl_Run(media_control
);
2529 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2532 hr
= IAMMultiMediaStream_GetState(mmstream
, &state
);
2533 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2534 ok(state
== STREAMSTATE_STOP
, "Got state %#x.\n", state
);
2536 hr
= IMediaControl_Stop(media_control
);
2537 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2539 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
2540 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2543 hr
= IAMMultiMediaStream_GetState(mmstream
, &state
);
2544 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2545 ok(state
== STREAMSTATE_RUN
, "Got state %#x.\n", state
);
2547 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
2548 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2551 hr
= IAMMultiMediaStream_GetState(mmstream
, &state
);
2552 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2553 ok(state
== STREAMSTATE_STOP
, "Got state %#x.\n", state
);
2555 source
.init_stream_hr
= E_FAIL
;
2556 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
2557 ok(hr
== E_FAIL
, "Got hr %#x.\n", hr
);
2560 hr
= IAMMultiMediaStream_GetState(mmstream
, &state
);
2561 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2562 ok(state
== STREAMSTATE_STOP
, "Got state %#x.\n", state
);
2564 ref
= IAMMultiMediaStream_Release(mmstream
);
2565 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
2566 IMediaControl_Release(media_control
);
2567 ref
= IGraphBuilder_Release(graph
);
2568 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
2571 static void test_enum_media_types(void)
2573 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
2574 IEnumMediaTypes
*enum1
, *enum2
;
2575 AM_MEDIA_TYPE
*mts
[2];
2576 IMediaStream
*stream
;
2581 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
2582 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2583 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
2584 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2586 hr
= IPin_EnumMediaTypes(pin
, &enum1
);
2587 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2589 hr
= IEnumMediaTypes_Next(enum1
, 1, mts
, NULL
);
2590 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
2592 hr
= IEnumMediaTypes_Next(enum1
, 0, mts
, &count
);
2593 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2594 ok(!count
, "Got count %u.\n", count
);
2596 hr
= IEnumMediaTypes_Next(enum1
, 1, mts
, &count
);
2597 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2598 ok(count
== 1, "Got count %u.\n", count
);
2599 CoTaskMemFree(mts
[0]);
2601 hr
= IEnumMediaTypes_Next(enum1
, 1, mts
, &count
);
2602 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
2603 ok(!count
, "Got count %u.\n", count
);
2605 hr
= IEnumMediaTypes_Reset(enum1
);
2606 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2608 hr
= IEnumMediaTypes_Next(enum1
, 2, mts
, &count
);
2609 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
2610 ok(count
== 1, "Got count %u.\n", count
);
2611 CoTaskMemFree(mts
[0]);
2613 hr
= IEnumMediaTypes_Reset(enum1
);
2614 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2616 hr
= IEnumMediaTypes_Clone(enum1
, &enum2
);
2617 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2619 hr
= IEnumMediaTypes_Skip(enum1
, 2);
2620 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2622 hr
= IEnumMediaTypes_Next(enum1
, 1, mts
, &count
);
2623 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
2624 ok(!count
, "Got count %u.\n", count
);
2626 hr
= IEnumMediaTypes_Next(enum2
, 1, mts
, &count
);
2627 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2628 ok(count
== 1, "Got count %u.\n", count
);
2629 CoTaskMemFree(mts
[0]);
2631 IEnumMediaTypes_Release(enum2
);
2632 IEnumMediaTypes_Release(enum1
);
2634 IMediaStream_Release(stream
);
2636 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
2637 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2638 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
2639 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2641 hr
= IPin_EnumMediaTypes(pin
, &enum1
);
2642 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2644 hr
= IEnumMediaTypes_Next(enum1
, 1, mts
, NULL
);
2645 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
2647 hr
= IEnumMediaTypes_Next(enum1
, 0, mts
, &count
);
2648 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2649 ok(!count
, "Got count %u.\n", count
);
2651 hr
= IEnumMediaTypes_Next(enum1
, 1, mts
, &count
);
2652 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2653 ok(count
== 1, "Got count %u.\n", count
);
2654 CoTaskMemFree(mts
[0]->pbFormat
);
2655 CoTaskMemFree(mts
[0]);
2657 hr
= IEnumMediaTypes_Next(enum1
, 1, mts
, &count
);
2658 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
2659 ok(!count
, "Got count %u.\n", count
);
2661 hr
= IEnumMediaTypes_Reset(enum1
);
2662 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2664 hr
= IEnumMediaTypes_Next(enum1
, 2, mts
, &count
);
2665 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
2666 ok(count
== 1, "Got count %u.\n", count
);
2667 CoTaskMemFree(mts
[0]->pbFormat
);
2668 CoTaskMemFree(mts
[0]);
2670 hr
= IEnumMediaTypes_Reset(enum1
);
2671 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2673 hr
= IEnumMediaTypes_Clone(enum1
, &enum2
);
2674 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2676 hr
= IEnumMediaTypes_Skip(enum1
, 2);
2677 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2679 hr
= IEnumMediaTypes_Next(enum1
, 1, mts
, &count
);
2680 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
2681 ok(!count
, "Got count %u.\n", count
);
2683 hr
= IEnumMediaTypes_Next(enum2
, 1, mts
, &count
);
2684 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2685 ok(count
== 1, "Got count %u.\n", count
);
2686 CoTaskMemFree(mts
[0]->pbFormat
);
2687 CoTaskMemFree(mts
[0]);
2689 IEnumMediaTypes_Release(enum2
);
2690 IEnumMediaTypes_Release(enum1
);
2692 IMediaStream_Release(stream
);
2694 ref
= IAMMultiMediaStream_Release(mmstream
);
2695 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
2698 static void test_media_types(void)
2700 static const VIDEOINFOHEADER2 req_vih2
;
2701 static const VIDEOINFOHEADER req_vih
;
2702 static const MPEG2VIDEOINFO req_m2vi
;
2703 static const MPEG1VIDEOINFO req_m1vi
;
2704 static const WAVEFORMATEX req_wfx
;
2705 static const WAVEFORMATEX expect_wfx
=
2707 .wFormatTag
= WAVE_FORMAT_PCM
,
2709 .nSamplesPerSec
= 11025,
2710 .nAvgBytesPerSec
= 11025 * 2,
2712 .wBitsPerSample
= 16,
2715 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
2716 IEnumMediaTypes
*enummt
;
2717 IMediaStream
*stream
;
2732 {&GUID_NULL
, NULL
, 0 },
2733 {&FORMAT_None
, NULL
, 0 },
2734 {&FORMAT_WaveFormatEx
, (BYTE
*)&req_wfx
, sizeof(WAVEFORMATEX
)},
2735 {&FORMAT_MPEG2Video
, (BYTE
*)&req_m2vi
, sizeof(MPEG2VIDEOINFO
)},
2736 {&FORMAT_MPEGVideo
, (BYTE
*)&req_m1vi
, sizeof(MPEG2VIDEOINFO
)},
2737 {&FORMAT_VideoInfo2
, (BYTE
*)&req_vih2
, sizeof(VIDEOINFOHEADER2
)},
2738 {&FORMAT_VideoInfo
, (BYTE
*)&req_vih
, sizeof(VIDEOINFOHEADER
)},
2741 static const GUID
*rejected_subtypes
[] =
2745 &MEDIASUBTYPE_RGB565
,
2746 &MEDIASUBTYPE_RGB555
,
2747 &MEDIASUBTYPE_RGB24
,
2748 &MEDIASUBTYPE_RGB32
,
2749 &MEDIASUBTYPE_ARGB32
,
2750 &MEDIASUBTYPE_ARGB1555
,
2751 &MEDIASUBTYPE_ARGB4444
,
2763 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
2764 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2765 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
2766 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2768 hr
= IPin_EnumMediaTypes(pin
, &enummt
);
2769 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2771 hr
= IEnumMediaTypes_Next(enummt
, 1, &pmt
, NULL
);
2772 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
2774 hr
= IEnumMediaTypes_Next(enummt
, 1, &pmt
, &count
);
2775 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2776 ok(count
== 1, "Got count %u.\n", count
);
2777 ok(IsEqualGUID(&pmt
->majortype
, &MEDIATYPE_Video
), "Got major type %s\n",
2778 wine_dbgstr_guid(&pmt
->majortype
));
2779 ok(IsEqualGUID(&pmt
->subtype
, &MEDIASUBTYPE_RGB8
), "Got subtype %s\n",
2780 wine_dbgstr_guid(&pmt
->subtype
));
2781 ok(pmt
->bFixedSizeSamples
== TRUE
, "Got fixed size %d.\n", pmt
->bFixedSizeSamples
);
2782 ok(!pmt
->bTemporalCompression
, "Got temporal compression %d.\n", pmt
->bTemporalCompression
);
2783 ok(pmt
->lSampleSize
== 10000, "Got sample size %u.\n", pmt
->lSampleSize
);
2784 ok(IsEqualGUID(&pmt
->formattype
, &GUID_NULL
), "Got format type %s.\n",
2785 wine_dbgstr_guid(&pmt
->formattype
));
2786 ok(!pmt
->pUnk
, "Got pUnk %p.\n", pmt
->pUnk
);
2788 for (i
= 0; i
< ARRAY_SIZE(tests
); ++i
)
2790 pmt
->formattype
= *tests
[i
].type
;
2791 pmt
->cbFormat
= tests
[i
].size
;
2792 pmt
->pbFormat
= tests
[i
].format
;
2793 hr
= IPin_QueryAccept(pin
, pmt
);
2794 ok(hr
== (i
== 6 ? S_OK
: VFW_E_TYPE_NOT_ACCEPTED
), "Got hr %#x.\n", hr
);
2797 pmt
->bFixedSizeSamples
= FALSE
;
2798 pmt
->bTemporalCompression
= TRUE
;
2799 pmt
->lSampleSize
= 123;
2800 hr
= IPin_QueryAccept(pin
, pmt
);
2801 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2803 pmt
->majortype
= MEDIATYPE_NULL
;
2804 hr
= IPin_QueryAccept(pin
, pmt
);
2805 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
2806 pmt
->majortype
= MEDIATYPE_Audio
;
2807 hr
= IPin_QueryAccept(pin
, pmt
);
2808 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
2809 pmt
->majortype
= MEDIATYPE_Stream
;
2810 hr
= IPin_QueryAccept(pin
, pmt
);
2811 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
2812 pmt
->majortype
= MEDIATYPE_Video
;
2814 for (i
= 0; i
< ARRAY_SIZE(rejected_subtypes
); ++i
)
2816 pmt
->subtype
= *rejected_subtypes
[i
];
2817 hr
= IPin_QueryAccept(pin
, pmt
);
2818 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x for subtype %s.\n",
2819 hr
, wine_dbgstr_guid(rejected_subtypes
[i
]));
2824 hr
= IEnumMediaTypes_Next(enummt
, 1, &pmt
, &count
);
2825 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
2827 IEnumMediaTypes_Release(enummt
);
2829 IMediaStream_Release(stream
);
2831 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
2832 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2833 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
2834 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2836 hr
= IPin_EnumMediaTypes(pin
, &enummt
);
2837 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2839 hr
= IEnumMediaTypes_Next(enummt
, 1, &pmt
, NULL
);
2840 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
2842 hr
= IEnumMediaTypes_Next(enummt
, 1, &pmt
, &count
);
2843 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
2844 ok(count
== 1, "Got count %u.\n", count
);
2845 ok(IsEqualGUID(&pmt
->majortype
, &MEDIATYPE_Audio
), "Got major type %s\n",
2846 wine_dbgstr_guid(&pmt
->majortype
));
2847 ok(IsEqualGUID(&pmt
->subtype
, &GUID_NULL
), "Got subtype %s\n",
2848 wine_dbgstr_guid(&pmt
->subtype
));
2849 ok(pmt
->bFixedSizeSamples
== TRUE
, "Got fixed size %d.\n", pmt
->bFixedSizeSamples
);
2850 ok(!pmt
->bTemporalCompression
, "Got temporal compression %d.\n", pmt
->bTemporalCompression
);
2851 ok(pmt
->lSampleSize
== 2, "Got sample size %u.\n", pmt
->lSampleSize
);
2852 ok(IsEqualGUID(&pmt
->formattype
, &FORMAT_WaveFormatEx
), "Got format type %s.\n",
2853 wine_dbgstr_guid(&pmt
->formattype
));
2854 ok(!pmt
->pUnk
, "Got pUnk %p.\n", pmt
->pUnk
);
2855 ok(pmt
->cbFormat
== sizeof(WAVEFORMATEX
), "Got format size %u.\n", pmt
->cbFormat
);
2856 ok(!memcmp(pmt
->pbFormat
, &expect_wfx
, pmt
->cbFormat
), "Format blocks didn't match.\n");
2858 hr
= IPin_QueryAccept(pin
, pmt
);
2859 ok(hr
== E_NOTIMPL
, "Got hr %#x.\n", hr
);
2861 CoTaskMemFree(pmt
->pbFormat
);
2864 hr
= IEnumMediaTypes_Next(enummt
, 1, &pmt
, &count
);
2865 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
2867 IEnumMediaTypes_Release(enummt
);
2869 IMediaStream_Release(stream
);
2871 ref
= IAMMultiMediaStream_Release(mmstream
);
2872 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
2875 static IUnknown
*create_audio_data(void)
2877 IUnknown
*audio_data
= NULL
;
2878 HRESULT result
= CoCreateInstance(&CLSID_AMAudioData
, NULL
, CLSCTX_INPROC_SERVER
,
2879 &IID_IUnknown
, (void **)&audio_data
);
2880 ok(S_OK
== result
, "got 0x%08x\n", result
);
2884 static void test_audiodata_query_interface(void)
2886 IUnknown
*unknown
= create_audio_data();
2887 IMemoryData
*memory_data
= NULL
;
2888 IAudioData
*audio_data
= NULL
;
2892 result
= IUnknown_QueryInterface(unknown
, &IID_IMemoryData
, (void **)&memory_data
);
2893 ok(E_NOINTERFACE
== result
, "got 0x%08x\n", result
);
2895 result
= IUnknown_QueryInterface(unknown
, &IID_IAudioData
, (void **)&audio_data
);
2896 ok(S_OK
== result
, "got 0x%08x\n", result
);
2899 result
= IAudioData_QueryInterface(audio_data
, &IID_IMemoryData
, (void **)&memory_data
);
2900 ok(E_NOINTERFACE
== result
, "got 0x%08x\n", result
);
2902 IAudioData_Release(audio_data
);
2905 IUnknown_Release(unknown
);
2908 static void test_audiodata_get_info(void)
2910 IUnknown
*unknown
= create_audio_data();
2911 IAudioData
*audio_data
= NULL
;
2915 result
= IUnknown_QueryInterface(unknown
, &IID_IAudioData
, (void **)&audio_data
);
2918 /* test_audiodata_query_interface handles this case */
2919 skip("No IAudioData\n");
2923 result
= IAudioData_GetInfo(audio_data
, NULL
, NULL
, NULL
);
2924 ok(MS_E_NOTINIT
== result
, "got 0x%08x\n", result
);
2926 IAudioData_Release(audio_data
);
2929 IUnknown_Release(unknown
);
2932 static void test_audiodata_set_buffer(void)
2934 IUnknown
*unknown
= create_audio_data();
2935 IAudioData
*audio_data
= NULL
;
2936 BYTE buffer
[100] = {0};
2942 result
= IUnknown_QueryInterface(unknown
, &IID_IAudioData
, (void **)&audio_data
);
2945 /* test_audiodata_query_interface handles this case */
2946 skip("No IAudioData\n");
2950 result
= IAudioData_SetBuffer(audio_data
, 100, NULL
, 0);
2951 ok(S_OK
== result
, "got 0x%08x\n", result
);
2953 data
= (BYTE
*)0xdeadbeef;
2954 length
= 0xdeadbeef;
2955 result
= IAudioData_GetInfo(audio_data
, &length
, &data
, NULL
);
2956 ok(S_OK
== result
, "got 0x%08x\n", result
);
2957 ok(100 == length
, "got %u\n", length
);
2958 ok(NULL
!= data
, "got %p\n", data
);
2960 result
= IAudioData_SetBuffer(audio_data
, 0, buffer
, 0);
2961 ok(E_INVALIDARG
== result
, "got 0x%08x\n", result
);
2963 result
= IAudioData_SetBuffer(audio_data
, sizeof(buffer
), buffer
, 0);
2964 ok(S_OK
== result
, "got 0x%08x\n", result
);
2966 data
= (BYTE
*)0xdeadbeef;
2967 length
= 0xdeadbeef;
2968 result
= IAudioData_GetInfo(audio_data
, &length
, &data
, NULL
);
2969 ok(S_OK
== result
, "got 0x%08x\n", result
);
2970 ok(sizeof(buffer
) == length
, "got %u\n", length
);
2971 ok(buffer
== data
, "got %p\n", data
);
2973 IAudioData_Release(audio_data
);
2976 IUnknown_Release(unknown
);
2979 static void test_audiodata_set_actual(void)
2981 IUnknown
*unknown
= create_audio_data();
2982 IAudioData
*audio_data
= NULL
;
2983 BYTE buffer
[100] = {0};
2984 DWORD actual_data
= 0;
2988 result
= IUnknown_QueryInterface(unknown
, &IID_IAudioData
, (void **)&audio_data
);
2991 /* test_audiodata_query_interface handles this case */
2992 skip("No IAudioData\n");
2996 result
= IAudioData_SetActual(audio_data
, 0);
2997 ok(S_OK
== result
, "got 0x%08x\n", result
);
2999 result
= IAudioData_SetBuffer(audio_data
, sizeof(buffer
), buffer
, 0);
3000 ok(S_OK
== result
, "got 0x%08x\n", result
);
3002 result
= IAudioData_SetActual(audio_data
, sizeof(buffer
) + 1);
3003 ok(E_INVALIDARG
== result
, "got 0x%08x\n", result
);
3005 result
= IAudioData_SetActual(audio_data
, sizeof(buffer
));
3006 ok(S_OK
== result
, "got 0x%08x\n", result
);
3008 actual_data
= 0xdeadbeef;
3009 result
= IAudioData_GetInfo(audio_data
, NULL
, NULL
, &actual_data
);
3010 ok(S_OK
== result
, "got 0x%08x\n", result
);
3011 ok(sizeof(buffer
) == actual_data
, "got %u\n", actual_data
);
3013 result
= IAudioData_SetActual(audio_data
, 0);
3014 ok(S_OK
== result
, "got 0x%08x\n", result
);
3016 actual_data
= 0xdeadbeef;
3017 result
= IAudioData_GetInfo(audio_data
, NULL
, NULL
, &actual_data
);
3018 ok(S_OK
== result
, "got 0x%08x\n", result
);
3019 ok(0 == actual_data
, "got %u\n", actual_data
);
3021 IAudioData_Release(audio_data
);
3024 IUnknown_Release(unknown
);
3027 static void test_audiodata_get_format(void)
3029 IUnknown
*unknown
= create_audio_data();
3030 IAudioData
*audio_data
= NULL
;
3031 WAVEFORMATEX wave_format
= {0};
3035 result
= IUnknown_QueryInterface(unknown
, &IID_IAudioData
, (void **)&audio_data
);
3038 /* test_audiodata_query_interface handles this case */
3039 skip("No IAudioData\n");
3043 result
= IAudioData_GetFormat(audio_data
, NULL
);
3044 ok(E_POINTER
== result
, "got 0x%08x\n", result
);
3046 wave_format
.wFormatTag
= 0xdead;
3047 wave_format
.nChannels
= 0xdead;
3048 wave_format
.nSamplesPerSec
= 0xdeadbeef;
3049 wave_format
.nAvgBytesPerSec
= 0xdeadbeef;
3050 wave_format
.nBlockAlign
= 0xdead;
3051 wave_format
.wBitsPerSample
= 0xdead;
3052 wave_format
.cbSize
= 0xdead;
3053 result
= IAudioData_GetFormat(audio_data
, &wave_format
);
3054 ok(S_OK
== result
, "got 0x%08x\n", result
);
3055 ok(WAVE_FORMAT_PCM
== wave_format
.wFormatTag
, "got %u\n", wave_format
.wFormatTag
);
3056 ok(1 == wave_format
.nChannels
, "got %u\n", wave_format
.nChannels
);
3057 ok(11025 == wave_format
.nSamplesPerSec
, "got %u\n", wave_format
.nSamplesPerSec
);
3058 ok(22050 == wave_format
.nAvgBytesPerSec
, "got %u\n", wave_format
.nAvgBytesPerSec
);
3059 ok(2 == wave_format
.nBlockAlign
, "got %u\n", wave_format
.nBlockAlign
);
3060 ok(16 == wave_format
.wBitsPerSample
, "got %u\n", wave_format
.wBitsPerSample
);
3061 ok(0 == wave_format
.cbSize
, "got %u\n", wave_format
.cbSize
);
3063 IAudioData_Release(audio_data
);
3066 IUnknown_Release(unknown
);
3069 static void test_audiodata_set_format(void)
3071 IUnknown
*unknown
= create_audio_data();
3072 IAudioData
*audio_data
= NULL
;
3073 WAVEFORMATPCMEX wave_format
= {{0}};
3077 result
= IUnknown_QueryInterface(unknown
, &IID_IAudioData
, (void **)&audio_data
);
3080 /* test_audiodata_query_interface handles this case */
3081 skip("No IAudioData\n");
3085 result
= IAudioData_SetFormat(audio_data
, NULL
);
3086 ok(E_POINTER
== result
, "got 0x%08x\n", result
);
3088 wave_format
.Format
.wFormatTag
= WAVE_FORMAT_EXTENSIBLE
;
3089 wave_format
.Format
.nChannels
= 2;
3090 wave_format
.Format
.nSamplesPerSec
= 44100;
3091 wave_format
.Format
.nAvgBytesPerSec
= 176400;
3092 wave_format
.Format
.nBlockAlign
= 4;
3093 wave_format
.Format
.wBitsPerSample
= 16;
3094 wave_format
.Format
.cbSize
= 22;
3095 wave_format
.Samples
.wValidBitsPerSample
= 16;
3096 wave_format
.dwChannelMask
= KSAUDIO_SPEAKER_STEREO
;
3097 wave_format
.SubFormat
= KSDATAFORMAT_SUBTYPE_PCM
;
3098 result
= IAudioData_SetFormat(audio_data
, &wave_format
.Format
);
3099 ok(E_INVALIDARG
== result
, "got 0x%08x\n", result
);
3101 wave_format
.Format
.wFormatTag
= WAVE_FORMAT_PCM
;
3102 wave_format
.Format
.nChannels
= 2;
3103 wave_format
.Format
.nSamplesPerSec
= 44100;
3104 wave_format
.Format
.nAvgBytesPerSec
= 176400;
3105 wave_format
.Format
.nBlockAlign
= 4;
3106 wave_format
.Format
.wBitsPerSample
= 16;
3107 wave_format
.Format
.cbSize
= 0;
3108 result
= IAudioData_SetFormat(audio_data
, &wave_format
.Format
);
3109 ok(S_OK
== result
, "got 0x%08x\n", result
);
3111 wave_format
.Format
.wFormatTag
= 0xdead;
3112 wave_format
.Format
.nChannels
= 0xdead;
3113 wave_format
.Format
.nSamplesPerSec
= 0xdeadbeef;
3114 wave_format
.Format
.nAvgBytesPerSec
= 0xdeadbeef;
3115 wave_format
.Format
.nBlockAlign
= 0xdead;
3116 wave_format
.Format
.wBitsPerSample
= 0xdead;
3117 wave_format
.Format
.cbSize
= 0xdead;
3118 result
= IAudioData_GetFormat(audio_data
, &wave_format
.Format
);
3119 ok(S_OK
== result
, "got 0x%08x\n", result
);
3120 ok(WAVE_FORMAT_PCM
== wave_format
.Format
.wFormatTag
, "got %u\n", wave_format
.Format
.wFormatTag
);
3121 ok(2 == wave_format
.Format
.nChannels
, "got %u\n", wave_format
.Format
.nChannels
);
3122 ok(44100 == wave_format
.Format
.nSamplesPerSec
, "got %u\n", wave_format
.Format
.nSamplesPerSec
);
3123 ok(176400 == wave_format
.Format
.nAvgBytesPerSec
, "got %u\n", wave_format
.Format
.nAvgBytesPerSec
);
3124 ok(4 == wave_format
.Format
.nBlockAlign
, "got %u\n", wave_format
.Format
.nBlockAlign
);
3125 ok(16 == wave_format
.Format
.wBitsPerSample
, "got %u\n", wave_format
.Format
.wBitsPerSample
);
3126 ok(0 == wave_format
.Format
.cbSize
, "got %u\n", wave_format
.Format
.cbSize
);
3128 IAudioData_Release(audio_data
);
3131 IUnknown_Release(unknown
);
3134 struct advise_time_cookie
3139 HANDLE advise_time_called_event
;
3140 BOOL unadvise_called
;
3145 IReferenceClock IReferenceClock_iface
;
3148 struct advise_time_cookie
*advise_time_cookie
;
3149 HRESULT get_time_hr
;
3152 static inline struct testclock
*impl_from_IReferenceClock(IReferenceClock
*iface
)
3154 return CONTAINING_RECORD(iface
, struct testclock
, IReferenceClock_iface
);
3157 static HRESULT WINAPI
testclock_QueryInterface(IReferenceClock
*iface
, REFIID iid
, void **out
)
3159 if (winetest_debug
> 1) trace("QueryInterface(%s)\n", wine_dbgstr_guid(iid
));
3160 if (IsEqualGUID(iid
, &IID_IReferenceClock
)
3161 || IsEqualGUID(iid
, &IID_IUnknown
))
3164 IReferenceClock_AddRef(iface
);
3167 return E_NOINTERFACE
;
3170 static ULONG WINAPI
testclock_AddRef(IReferenceClock
*iface
)
3172 struct testclock
*clock
= impl_from_IReferenceClock(iface
);
3173 return InterlockedIncrement(&clock
->refcount
);
3176 static ULONG WINAPI
testclock_Release(IReferenceClock
*iface
)
3178 struct testclock
*clock
= impl_from_IReferenceClock(iface
);
3179 return InterlockedDecrement(&clock
->refcount
);
3182 static HRESULT WINAPI
testclock_GetTime(IReferenceClock
*iface
, REFERENCE_TIME
*time
)
3184 struct testclock
*clock
= impl_from_IReferenceClock(iface
);
3185 if (SUCCEEDED(clock
->get_time_hr
))
3186 *time
= clock
->time
;
3187 return clock
->get_time_hr
;
3190 static HRESULT WINAPI
testclock_AdviseTime(IReferenceClock
*iface
, REFERENCE_TIME base
, REFERENCE_TIME offset
, HEVENT event
, DWORD_PTR
*cookie
)
3192 struct testclock
*clock
= impl_from_IReferenceClock(iface
);
3193 if (clock
->advise_time_cookie
)
3195 clock
->advise_time_cookie
->base
= base
;
3196 clock
->advise_time_cookie
->offset
= offset
;
3197 clock
->advise_time_cookie
->event
= (HANDLE
)event
;
3198 SetEvent(clock
->advise_time_cookie
->advise_time_called_event
);
3202 SetEvent((HANDLE
)event
);
3204 *cookie
= (DWORD_PTR
)clock
->advise_time_cookie
;
3208 static HRESULT WINAPI
testclock_AdvisePeriodic(IReferenceClock
*iface
, REFERENCE_TIME start
, REFERENCE_TIME period
, HSEMAPHORE semaphore
, DWORD_PTR
*cookie
)
3210 ok(0, "Unexpected call.\n");
3214 static HRESULT WINAPI
testclock_Unadvise(IReferenceClock
*iface
, DWORD_PTR cookie
)
3217 ((struct advise_time_cookie
*)cookie
)->unadvise_called
= TRUE
;
3221 static IReferenceClockVtbl testclock_vtbl
=
3223 testclock_QueryInterface
,
3227 testclock_AdviseTime
,
3228 testclock_AdvisePeriodic
,
3232 static void testclock_init(struct testclock
*clock
)
3234 memset(clock
, 0, sizeof(*clock
));
3235 clock
->IReferenceClock_iface
.lpVtbl
= &testclock_vtbl
;
3238 static void test_audiostream_get_format(void)
3240 static const WAVEFORMATEX pin_format
=
3242 .wFormatTag
= WAVE_FORMAT_PCM
,
3244 .nSamplesPerSec
= 44100,
3245 .wBitsPerSample
= 16,
3247 .nAvgBytesPerSec
= 4 * 44100,
3251 .majortype
= MEDIATYPE_Audio
,
3252 .subtype
= MEDIASUBTYPE_PCM
,
3253 .formattype
= FORMAT_WaveFormatEx
,
3254 .cbFormat
= sizeof(WAVEFORMATEX
),
3255 .pbFormat
= (BYTE
*)&pin_format
,
3257 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
3258 IAudioMediaStream
*audio_stream
;
3259 struct testfilter source
;
3260 IGraphBuilder
*graph
;
3261 IMediaStream
*stream
;
3262 WAVEFORMATEX format
;
3267 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
3268 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3269 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
3270 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3271 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
3272 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3274 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
3275 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3276 ok(!!graph
, "Expected non-NULL graph.\n");
3278 testfilter_init(&source
);
3280 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, L
"source");
3281 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3283 hr
= IAudioMediaStream_GetFormat(audio_stream
, NULL
);
3284 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
3286 hr
= IAudioMediaStream_GetFormat(audio_stream
, &format
);
3287 ok(hr
== MS_E_NOSTREAM
, "Got hr %#x.\n", hr
);
3289 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
3290 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3292 memset(&format
, 0xcc, sizeof(format
));
3293 hr
= IAudioMediaStream_GetFormat(audio_stream
, &format
);
3294 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3295 ok(format
.wFormatTag
== WAVE_FORMAT_PCM
, "Got tag %#x.\n", format
.wFormatTag
);
3296 ok(format
.nChannels
== 2, "Got %u channels.\n", format
.nChannels
);
3297 ok(format
.nSamplesPerSec
== 44100, "Got sample rate %u.\n", format
.nSamplesPerSec
);
3298 ok(format
.nAvgBytesPerSec
== 176400, "Got %u bytes/sec.\n", format
.nAvgBytesPerSec
);
3299 ok(format
.nBlockAlign
== 4, "Got alignment %u.\n", format
.nBlockAlign
);
3300 ok(format
.wBitsPerSample
== 16, "Got %u bits/sample.\n", format
.wBitsPerSample
);
3301 ok(!format
.cbSize
, "Got extra size %u.\n", format
.cbSize
);
3303 hr
= IGraphBuilder_Disconnect(graph
, pin
);
3304 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3305 hr
= IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
3306 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3308 hr
= IAudioMediaStream_GetFormat(audio_stream
, &format
);
3309 ok(hr
== MS_E_NOSTREAM
, "Got hr %#x.\n", hr
);
3311 ref
= IAMMultiMediaStream_Release(mmstream
);
3312 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3313 ref
= IGraphBuilder_Release(graph
);
3314 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3316 IAudioMediaStream_Release(audio_stream
);
3317 ref
= IMediaStream_Release(stream
);
3318 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3319 ref
= IBaseFilter_Release(&source
.filter
.IBaseFilter_iface
);
3320 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3323 static HRESULT
set_audiostream_format(const WAVEFORMATEX
*format
)
3325 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
3326 IAudioMediaStream
*audio_stream
;
3327 IMediaStream
*stream
;
3331 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
3332 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3333 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
3334 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3336 hr
= IAudioMediaStream_SetFormat(audio_stream
, format
);
3338 ref
= IAMMultiMediaStream_Release(mmstream
);
3339 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3340 IAudioMediaStream_Release(audio_stream
);
3341 ref
= IMediaStream_Release(stream
);
3342 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3347 static void test_audiostream_set_format(void)
3349 static const WAVEFORMATEX valid_format
=
3351 .wFormatTag
= WAVE_FORMAT_PCM
,
3353 .nSamplesPerSec
= 44100,
3354 .wBitsPerSample
= 16,
3356 .nAvgBytesPerSec
= 4 * 44100,
3359 const AM_MEDIA_TYPE mt
=
3361 .majortype
= MEDIATYPE_Audio
,
3362 .subtype
= MEDIASUBTYPE_PCM
,
3363 .formattype
= FORMAT_WaveFormatEx
,
3364 .cbFormat
= sizeof(WAVEFORMATEX
),
3365 .pbFormat
= (BYTE
*)&valid_format
,
3368 WAVEFORMATEXTENSIBLE extensible_format
;
3369 IAudioMediaStream
*audio_stream
;
3370 IAMMultiMediaStream
*mmstream
;
3371 struct testfilter source
;
3372 IGraphBuilder
*graph
;
3373 IMediaStream
*stream
;
3374 WAVEFORMATEX format
;
3379 hr
= set_audiostream_format(&valid_format
);
3380 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3381 hr
= set_audiostream_format(NULL
);
3382 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
3384 extensible_format
.Format
= valid_format
;
3385 extensible_format
.Format
.wFormatTag
= WAVE_FORMAT_EXTENSIBLE
;
3386 extensible_format
.Format
.cbSize
= sizeof(WAVEFORMATEXTENSIBLE
) - sizeof(WAVEFORMATEX
);
3387 extensible_format
.Samples
.wValidBitsPerSample
= valid_format
.wBitsPerSample
;
3388 extensible_format
.dwChannelMask
= KSAUDIO_SPEAKER_STEREO
;
3389 extensible_format
.SubFormat
= KSDATAFORMAT_SUBTYPE_PCM
;
3390 hr
= set_audiostream_format(&extensible_format
.Format
);
3391 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
3393 format
= valid_format
;
3394 format
.nBlockAlign
= 1;
3395 hr
= set_audiostream_format(&format
);
3396 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3398 format
= valid_format
;
3399 format
.nAvgBytesPerSec
= 1234;
3400 hr
= set_audiostream_format(&format
);
3401 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3403 mmstream
= create_ammultimediastream();
3405 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
3406 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3407 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
3408 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3410 hr
= IAudioMediaStream_SetFormat(audio_stream
, &valid_format
);
3411 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3413 hr
= IAudioMediaStream_GetFormat(audio_stream
, &format
);
3414 ok(hr
== MS_E_NOSTREAM
, "Got hr %#x.\n", hr
);
3416 format
= valid_format
;
3417 format
.nChannels
= 1;
3418 hr
= IAudioMediaStream_SetFormat(audio_stream
, &format
);
3419 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
3421 format
= valid_format
;
3422 format
.nSamplesPerSec
= 11025;
3423 hr
= IAudioMediaStream_SetFormat(audio_stream
, &format
);
3424 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
3426 format
= valid_format
;
3427 format
.nAvgBytesPerSec
= 1234;
3428 hr
= IAudioMediaStream_SetFormat(audio_stream
, &format
);
3429 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
3431 format
= valid_format
;
3432 format
.nBlockAlign
= 1;
3433 hr
= IAudioMediaStream_SetFormat(audio_stream
, &format
);
3434 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
3436 format
= valid_format
;
3437 format
.wBitsPerSample
= 8;
3438 hr
= IAudioMediaStream_SetFormat(audio_stream
, &format
);
3439 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
3441 format
= valid_format
;
3443 hr
= IAudioMediaStream_SetFormat(audio_stream
, &format
);
3444 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
3446 hr
= IAudioMediaStream_SetFormat(audio_stream
, &valid_format
);
3447 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3449 ref
= IAMMultiMediaStream_Release(mmstream
);
3450 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3451 IAudioMediaStream_Release(audio_stream
);
3452 ref
= IMediaStream_Release(stream
);
3453 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3455 mmstream
= create_ammultimediastream();
3457 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
3458 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3459 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
3460 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3461 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
3462 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3464 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
3465 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3466 ok(!!graph
, "Expected non-NULL graph.\n");
3468 testfilter_init(&source
);
3470 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
3471 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3473 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
3474 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3476 format
= valid_format
;
3477 format
.nChannels
= 1;
3478 hr
= IAudioMediaStream_SetFormat(audio_stream
, &format
);
3479 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
3481 hr
= IGraphBuilder_Disconnect(graph
, pin
);
3482 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3483 hr
= IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
3484 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3486 format
= valid_format
;
3487 format
.nChannels
= 1;
3488 hr
= IAudioMediaStream_SetFormat(audio_stream
, &format
);
3489 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3491 ref
= IAMMultiMediaStream_Release(mmstream
);
3492 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3493 ref
= IGraphBuilder_Release(graph
);
3494 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3496 IAudioMediaStream_Release(audio_stream
);
3497 ref
= IMediaStream_Release(stream
);
3498 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3499 ref
= IBaseFilter_Release(&source
.filter
.IBaseFilter_iface
);
3500 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3503 static void test_audiostream_receive_connection(void)
3505 WAVEFORMATEXTENSIBLE extensible_format
;
3506 IAudioMediaStream
*audio_stream
;
3507 IAMMultiMediaStream
*mmstream
;
3508 struct testfilter source
;
3509 IGraphBuilder
*graph
;
3510 IMediaStream
*stream
;
3511 WAVEFORMATEX format
;
3517 mmstream
= create_ammultimediastream();
3518 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
3519 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3520 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
3521 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3522 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
3523 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3524 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
3525 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3526 ok(graph
!= NULL
, "Expected non-null graph\n");
3527 testfilter_init(&source
);
3528 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
3529 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3531 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &audio_mt
);
3532 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3533 IGraphBuilder_Disconnect(graph
, pin
);
3534 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
3537 mt
.majortype
= GUID_NULL
;
3538 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &mt
);
3539 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3542 mt
.subtype
= MEDIASUBTYPE_RGB24
;
3543 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
3544 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3545 IGraphBuilder_Disconnect(graph
, pin
);
3546 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
3549 mt
.formattype
= GUID_NULL
;
3550 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &mt
);
3551 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3554 mt
.cbFormat
= sizeof(WAVEFORMATEX
) - 1;
3555 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
3556 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3558 extensible_format
.Format
= audio_format
;
3559 extensible_format
.Format
.wFormatTag
= WAVE_FORMAT_EXTENSIBLE
;
3560 extensible_format
.Format
.cbSize
= sizeof(WAVEFORMATEXTENSIBLE
) - sizeof(WAVEFORMATEX
);
3561 extensible_format
.Samples
.wValidBitsPerSample
= audio_format
.wBitsPerSample
;
3562 extensible_format
.dwChannelMask
= KSAUDIO_SPEAKER_STEREO
;
3563 extensible_format
.SubFormat
= KSDATAFORMAT_SUBTYPE_PCM
;
3565 mt
.cbFormat
= sizeof(extensible_format
);
3566 mt
.pbFormat
= (BYTE
*)&extensible_format
;
3567 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
3568 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
3570 hr
= IAudioMediaStream_SetFormat(audio_stream
, &audio_format
);
3571 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3573 format
= audio_format
;
3574 format
.nChannels
= 2;
3576 mt
.pbFormat
= (BYTE
*)&format
;
3577 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
3578 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
3580 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &audio_mt
);
3581 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3582 IGraphBuilder_Disconnect(graph
, pin
);
3583 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
3585 ref
= IAMMultiMediaStream_Release(mmstream
);
3586 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3587 ref
= IGraphBuilder_Release(graph
);
3588 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3590 IAudioMediaStream_Release(audio_stream
);
3591 ref
= IMediaStream_Release(stream
);
3592 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3593 ref
= IBaseFilter_Release(&source
.filter
.IBaseFilter_iface
);
3594 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3597 static void test_ddrawstream_receive_connection(void)
3599 static const VIDEOINFOHEADER req_vih
;
3600 IDirectDrawMediaStream
*ddraw_stream
;
3601 IAMMultiMediaStream
*mmstream
;
3602 struct testfilter source
;
3603 DDSURFACEDESC format
;
3604 IMediaStream
*stream
;
3605 VIDEOINFO video_info
;
3612 static const VIDEOINFO yuy2_video_info
=
3614 .bmiHeader
.biSize
= sizeof(BITMAPINFOHEADER
),
3615 .bmiHeader
.biWidth
= 333,
3616 .bmiHeader
.biHeight
= -444,
3617 .bmiHeader
.biPlanes
= 1,
3618 .bmiHeader
.biBitCount
= 16,
3619 .bmiHeader
.biCompression
= MAKEFOURCC('Y', 'U', 'Y', '2'),
3622 const AM_MEDIA_TYPE yuy2_mt
=
3624 .majortype
= MEDIATYPE_Video
,
3625 .subtype
= MEDIASUBTYPE_YUY2
,
3626 .formattype
= FORMAT_VideoInfo
,
3627 .cbFormat
= sizeof(VIDEOINFOHEADER
),
3628 .pbFormat
= (BYTE
*)&yuy2_video_info
,
3631 const AM_MEDIA_TYPE video_mt
=
3633 .majortype
= MEDIATYPE_Video
,
3634 .subtype
= MEDIASUBTYPE_RGB8
,
3635 .formattype
= FORMAT_VideoInfo
,
3636 .cbFormat
= sizeof(VIDEOINFOHEADER
),
3637 .pbFormat
= (BYTE
*)&req_vih
,
3640 static const GUID
*subtypes
[] =
3642 &MEDIASUBTYPE_RGB24
,
3643 &MEDIASUBTYPE_RGB32
,
3644 &MEDIASUBTYPE_RGB555
,
3645 &MEDIASUBTYPE_RGB565
,
3648 &MEDIASUBTYPE_ARGB32
,
3649 &MEDIASUBTYPE_ARGB1555
,
3650 &MEDIASUBTYPE_ARGB4444
,
3662 mmstream
= create_ammultimediastream();
3663 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
3664 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3665 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
3666 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3667 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
3668 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3670 testfilter_init(&source
);
3673 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &mt
);
3674 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3675 hr
= IPin_Disconnect(pin
);
3676 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3678 for (i
= 0; i
< ARRAY_SIZE(subtypes
); ++i
)
3681 mt
.subtype
= *subtypes
[i
];
3682 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &mt
);
3683 ok(hr
== (i
< 4 ? S_OK
: VFW_E_TYPE_NOT_ACCEPTED
), "Got hr %#x.\n", hr
);
3686 hr
= IPin_Disconnect(pin
);
3687 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3691 format
= rgb8_format
;
3692 format
.dwFlags
= DDSD_WIDTH
;
3693 format
.dwWidth
= 222;
3694 format
.dwHeight
= 555;
3695 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &format
, NULL
);
3696 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3698 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb32_mt
);
3699 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3700 hr
= IPin_Disconnect(pin
);
3701 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3703 format
= rgb8_format
;
3704 format
.dwFlags
= DDSD_HEIGHT
;
3705 format
.dwWidth
= 333;
3706 format
.dwHeight
= 444;
3707 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &format
, NULL
);
3708 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3710 video_info
= rgb555_video_info
;
3711 video_info
.bmiHeader
.biWidth
= 333;
3712 video_info
.bmiHeader
.biHeight
= 444;
3714 mt
.pbFormat
= (BYTE
*)&video_info
;
3715 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &mt
);
3716 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3717 hr
= IPin_Disconnect(pin
);
3718 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3720 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb32_mt
);
3721 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3722 hr
= IPin_Disconnect(pin
);
3723 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3725 video_info
= rgb32_video_info
;
3726 video_info
.bmiHeader
.biWidth
= 332;
3727 video_info
.bmiHeader
.biHeight
= 444;
3729 mt
.pbFormat
= (BYTE
*)&video_info
;
3730 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &mt
);
3731 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3733 video_info
= rgb32_video_info
;
3734 video_info
.bmiHeader
.biWidth
= 333;
3735 video_info
.bmiHeader
.biHeight
= 443;
3737 mt
.pbFormat
= (BYTE
*)&video_info
;
3738 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &mt
);
3739 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3741 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &rgb8_format
, NULL
);
3742 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3744 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb555_mt
);
3745 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3747 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb8_mt
);
3748 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3749 hr
= IPin_Disconnect(pin
);
3750 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3752 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &rgb555_format
, NULL
);
3753 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3755 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb565_mt
);
3756 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3758 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb555_mt
);
3759 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3760 hr
= IPin_Disconnect(pin
);
3761 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3763 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &rgb565_format
, NULL
);
3764 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3766 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb24_mt
);
3767 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3769 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb565_mt
);
3770 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3771 hr
= IPin_Disconnect(pin
);
3772 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3774 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &rgb24_format
, NULL
);
3775 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3777 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb32_mt
);
3778 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3780 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb24_mt
);
3781 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3782 hr
= IPin_Disconnect(pin
);
3783 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3785 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &rgb32_format
, NULL
);
3786 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3788 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb8_mt
);
3789 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3791 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb32_mt
);
3792 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3793 hr
= IPin_Disconnect(pin
);
3794 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3796 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &yuy2_format
, NULL
);
3797 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3799 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &yuy2_mt
);
3800 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3802 format
= yuy2_format
;
3803 format
.ddpfPixelFormat
.u2
.dwRBitMask
= 0xf800;
3804 format
.ddpfPixelFormat
.u3
.dwGBitMask
= 0x07e0;
3805 format
.ddpfPixelFormat
.u4
.dwBBitMask
= 0x001f;
3806 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &format
, NULL
);
3807 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3809 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb565_mt
);
3810 ok(hr
== VFW_E_TYPE_NOT_ACCEPTED
, "Got hr %#x.\n", hr
);
3812 format
= rgb8_format
;
3814 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &format
, NULL
);
3815 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3817 hr
= IPin_ReceiveConnection(pin
, &source
.source
.pin
.IPin_iface
, &rgb565_mt
);
3818 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3819 hr
= IPin_Disconnect(pin
);
3820 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3822 ref
= IAMMultiMediaStream_Release(mmstream
);
3823 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3825 IDirectDrawMediaStream_Release(ddraw_stream
);
3826 ref
= IMediaStream_Release(stream
);
3827 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3828 ref
= IBaseFilter_Release(&source
.filter
.IBaseFilter_iface
);
3829 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3832 static void test_audiostream_receive(void)
3834 ALLOCATOR_PROPERTIES properties
=
3841 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
3842 ALLOCATOR_PROPERTIES actual
;
3843 struct testfilter source
;
3844 IMemAllocator
*allocator
;
3845 IGraphBuilder
*graph
;
3846 IMediaStream
*stream
;
3847 IMediaSample
*sample1
;
3848 IMediaSample
*sample2
;
3849 IMediaSample
*sample3
;
3854 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
3855 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3856 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
3857 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3858 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
3859 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3860 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
3861 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3862 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
3863 testfilter_init(&source
);
3864 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
3865 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3866 hr
= CoCreateInstance(&CLSID_MemoryAllocator
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IMemAllocator
, (void **)&allocator
);
3867 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3868 hr
= IMemAllocator_SetProperties(allocator
, &properties
, &actual
);
3869 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3870 hr
= IMemAllocator_Commit(allocator
);
3871 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3873 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &audio_mt
);
3874 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3876 hr
= IMemAllocator_GetBuffer(allocator
, &sample1
, NULL
, NULL
, 0);
3877 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3878 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, sample1
);
3879 ok(hr
== VFW_E_WRONG_STATE
, "Got hr %#x.\n", hr
);
3880 ref
= IMediaSample_Release(sample1
);
3881 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3883 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
3884 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3886 hr
= IMemAllocator_GetBuffer(allocator
, &sample1
, NULL
, NULL
, 0);
3887 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3888 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, sample1
);
3889 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3890 ref
= get_refcount(sample1
);
3891 ok(ref
== 2, "Got unexpected refcount %d.\n", ref
);
3893 hr
= IMemAllocator_GetBuffer(allocator
, &sample2
, NULL
, NULL
, 0);
3894 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3895 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, sample2
);
3896 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3897 ref
= get_refcount(sample2
);
3898 ok(ref
== 2, "Got unexpected refcount %d.\n", ref
);
3900 hr
= IPin_EndOfStream(pin
);
3901 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3903 hr
= IMemAllocator_GetBuffer(allocator
, &sample3
, NULL
, NULL
, 0);
3904 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3905 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, sample3
);
3906 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3907 ref
= get_refcount(sample3
);
3908 ok(ref
== 2, "Got unexpected refcount %d.\n", ref
);
3910 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
3911 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3913 ref
= IMediaSample_Release(sample1
);
3914 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3915 ref
= IMediaSample_Release(sample2
);
3916 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3917 ref
= IMediaSample_Release(sample3
);
3918 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3920 hr
= IMemAllocator_GetBuffer(allocator
, &sample1
, NULL
, NULL
, 0);
3921 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3922 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, sample1
);
3923 ok(hr
== VFW_E_WRONG_STATE
, "Got hr %#x.\n", hr
);
3924 ref
= IMediaSample_Release(sample1
);
3925 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3927 IGraphBuilder_Disconnect(graph
, pin
);
3928 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
3930 hr
= IMemAllocator_Decommit(allocator
);
3931 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3933 ref
= IAMMultiMediaStream_Release(mmstream
);
3934 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3935 ref
= IGraphBuilder_Release(graph
);
3936 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3938 ref
= IMediaStream_Release(stream
);
3939 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3940 ref
= IMemAllocator_Release(allocator
);
3941 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3944 static void test_audiostream_initialize(void)
3946 IAMMediaStream
*stream
;
3952 hr
= CoCreateInstance(&CLSID_AMAudioStream
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAMMediaStream
, (void **)&stream
);
3953 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3955 /* Crashes on native. */
3958 hr
= IAMMediaStream_Initialize(stream
, NULL
, 0, NULL
, STREAMTYPE_WRITE
);
3959 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
3962 hr
= IAMMediaStream_Initialize(stream
, NULL
, 0, &test_mspid
, STREAMTYPE_WRITE
);
3963 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3965 hr
= IAMMediaStream_GetInformation(stream
, &mspid
, &type
);
3966 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3967 ok(IsEqualGUID(&mspid
, &test_mspid
), "Got mspid %s.\n", wine_dbgstr_guid(&mspid
));
3968 ok(type
== STREAMTYPE_WRITE
, "Got type %u.\n", type
);
3970 hr
= IAMMediaStream_Initialize(stream
, NULL
, 0, &MSPID_PrimaryAudio
, STREAMTYPE_READ
);
3971 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3973 hr
= IAMMediaStream_GetInformation(stream
, &mspid
, &type
);
3974 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3975 ok(IsEqualGUID(&mspid
, &MSPID_PrimaryAudio
), "Got mspid %s.\n", wine_dbgstr_guid(&mspid
));
3976 ok(type
== STREAMTYPE_READ
, "Got type %u.\n", type
);
3978 ref
= IAMMediaStream_Release(stream
);
3979 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
3982 static void test_audiostream_begin_flush_end_flush(void)
3984 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
3985 IAudioStreamSample
*stream_sample
;
3986 IAudioMediaStream
*audio_stream
;
3987 IMediaSample
*media_sample
;
3988 struct testfilter source
;
3989 IAudioData
*audio_data
;
3990 IGraphBuilder
*graph
;
3991 IMediaStream
*stream
;
3996 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
3997 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
3998 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
3999 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4000 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
4001 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4002 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
4003 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4004 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
4005 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4006 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
4007 testfilter_init(&source
);
4008 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
4009 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4010 hr
= CoCreateInstance(&CLSID_AMAudioData
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAudioData
, (void **)&audio_data
);
4011 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4012 hr
= IAudioData_SetBuffer(audio_data
, 16, NULL
, 0);
4013 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4014 hr
= IAudioMediaStream_CreateSample(audio_stream
, audio_data
, 0, &stream_sample
);
4015 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4017 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &audio_mt
);
4018 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4020 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
4021 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4023 hr
= BaseOutputPinImpl_GetDeliveryBuffer(&source
.source
, &media_sample
, NULL
, NULL
, 0);
4024 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4025 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
4026 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4027 ref
= get_refcount(media_sample
);
4028 ok(ref
== 2, "Got unexpected refcount %d.\n", ref
);
4030 hr
= IPin_EndOfStream(pin
);
4031 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4033 hr
= IPin_BeginFlush(pin
);
4034 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4036 ref
= IMediaSample_Release(media_sample
);
4037 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4039 hr
= BaseOutputPinImpl_GetDeliveryBuffer(&source
.source
, &media_sample
, NULL
, NULL
, 0);
4040 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4041 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
4042 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
4044 ref
= IMediaSample_Release(media_sample
);
4045 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4047 hr
= IAudioStreamSample_Update(stream_sample
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
4048 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
4050 hr
= IPin_EndOfStream(pin
);
4051 ok(hr
== E_FAIL
, "Got hr %#x.\n", hr
);
4053 hr
= IPin_EndFlush(pin
);
4054 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4056 hr
= BaseOutputPinImpl_GetDeliveryBuffer(&source
.source
, &media_sample
, NULL
, NULL
, 0);
4057 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4058 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
4059 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4060 ref
= IMediaSample_Release(media_sample
);
4061 ok(ref
== 1, "Got outstanding refcount %d.\n", ref
);
4063 hr
= IPin_EndOfStream(pin
);
4064 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4066 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
4067 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4069 IGraphBuilder_Disconnect(graph
, pin
);
4070 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
4072 ref
= IAudioStreamSample_Release(stream_sample
);
4073 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4074 ref
= IAudioData_Release(audio_data
);
4075 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4076 ref
= IAMMultiMediaStream_Release(mmstream
);
4077 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4078 ref
= IGraphBuilder_Release(graph
);
4079 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4081 IAudioMediaStream_Release(audio_stream
);
4082 ref
= IMediaStream_Release(stream
);
4083 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4086 static IMediaSample
*ammediastream_allocate_sample(struct testfilter
*source
, const BYTE
*input_data
, DWORD input_length
)
4088 IMediaSample
*sample
;
4092 hr
= BaseOutputPinImpl_GetDeliveryBuffer(&source
->source
, &sample
, NULL
, NULL
, 0);
4093 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4095 hr
= IMediaSample_GetPointer(sample
, &sample_data
);
4096 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4098 hr
= IMediaSample_SetActualDataLength(sample
, input_length
);
4099 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4101 memcpy(sample_data
, input_data
, input_length
);
4106 static void test_audiostream_new_segment(void)
4108 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
4109 static const BYTE test_data
[8] = { 0 };
4110 IAudioStreamSample
*stream_sample
;
4111 IAudioMediaStream
*audio_stream
;
4112 IMemInputPin
*mem_input_pin
;
4113 IMediaSample
*media_sample
;
4114 struct testfilter source
;
4115 IAudioData
*audio_data
;
4116 STREAM_TIME start_time
;
4117 STREAM_TIME end_time
;
4118 IGraphBuilder
*graph
;
4119 IMediaStream
*stream
;
4124 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
4125 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4126 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
4127 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4128 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
4129 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4130 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
4131 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4132 hr
= IMediaStream_QueryInterface(stream
, &IID_IMemInputPin
, (void **)&mem_input_pin
);
4133 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4134 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
4135 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4136 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
4137 testfilter_init(&source
);
4138 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
4139 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4140 hr
= CoCreateInstance(&CLSID_AMAudioData
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAudioData
, (void **)&audio_data
);
4141 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4142 hr
= IAudioMediaStream_CreateSample(audio_stream
, audio_data
, 0, &stream_sample
);
4143 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4144 hr
= IAudioData_SetBuffer(audio_data
, 5, NULL
, 0);
4145 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4147 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &audio_mt
);
4148 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4149 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
4150 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4152 hr
= IPin_NewSegment(pin
, 11111111, 22222222, 1.0);
4153 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4155 media_sample
= ammediastream_allocate_sample(&source
, test_data
, 5);
4156 start_time
= 12345678;
4157 end_time
= 23456789;
4158 hr
= IMediaSample_SetTime(media_sample
, &start_time
, &end_time
);
4159 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4160 hr
= IMemInputPin_Receive(mem_input_pin
, media_sample
);
4161 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4162 IMediaSample_Release(media_sample
);
4164 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4165 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4167 start_time
= 0xdeadbeefdeadbeef;
4168 end_time
= 0xdeadbeefdeadbeef;
4169 hr
= IAudioStreamSample_GetSampleTimes(stream_sample
, &start_time
, &end_time
, NULL
);
4170 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4171 ok(start_time
== 23456789, "Got start time %s.\n", wine_dbgstr_longlong(start_time
));
4172 ok(end_time
== 23459057, "Got end time %s.\n", wine_dbgstr_longlong(end_time
));
4174 hr
= IPin_NewSegment(pin
, 11111111, 22222222, 2.0);
4175 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4177 media_sample
= ammediastream_allocate_sample(&source
, test_data
, 5);
4178 start_time
= 12345678;
4179 end_time
= 23456789;
4180 hr
= IMediaSample_SetTime(media_sample
, &start_time
, &end_time
);
4181 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4182 hr
= IMemInputPin_Receive(mem_input_pin
, media_sample
);
4183 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4184 IMediaSample_Release(media_sample
);
4186 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4187 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4189 start_time
= 0xdeadbeefdeadbeef;
4190 end_time
= 0xdeadbeefdeadbeef;
4191 hr
= IAudioStreamSample_GetSampleTimes(stream_sample
, &start_time
, &end_time
, NULL
);
4192 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4193 ok(start_time
== 23456789, "Got start time %s.\n", wine_dbgstr_longlong(start_time
));
4194 ok(end_time
== 23459057, "Got end time %s.\n", wine_dbgstr_longlong(end_time
));
4196 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
4197 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4198 IGraphBuilder_Disconnect(graph
, pin
);
4199 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
4201 ref
= IAudioStreamSample_Release(stream_sample
);
4202 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4203 ref
= IAudioData_Release(audio_data
);
4204 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4205 ref
= IAMMultiMediaStream_Release(mmstream
);
4206 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4207 ref
= IGraphBuilder_Release(graph
);
4208 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4210 IMemInputPin_Release(mem_input_pin
);
4211 IAudioMediaStream_Release(audio_stream
);
4212 ref
= IMediaStream_Release(stream
);
4213 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4216 static void CALLBACK
apc_func(ULONG_PTR param
)
4220 static IPin
*ammediastream_pin
;
4221 static IMemInputPin
*ammediastream_mem_input_pin
;
4222 static IMediaSample
*ammediastream_media_sample
;
4223 static DWORD ammediastream_sleep_time
;
4224 static HRESULT ammediastream_expected_hr
;
4226 static DWORD CALLBACK
ammediastream_end_of_stream(void *param
)
4230 Sleep(ammediastream_sleep_time
);
4231 hr
= IPin_EndOfStream(ammediastream_pin
);
4232 ok(hr
== ammediastream_expected_hr
, "Got hr %#x.\n", hr
);
4237 static DWORD CALLBACK
ammediastream_receive(void *param
)
4241 Sleep(ammediastream_sleep_time
);
4242 hr
= IMemInputPin_Receive(ammediastream_mem_input_pin
, ammediastream_media_sample
);
4243 ok(hr
== ammediastream_expected_hr
, "Got hr %#x.\n", hr
);
4248 struct ammediastream_receive_release_param
4250 IMemInputPin
*mem_input_pin
;
4251 IMediaSample
*media_sample
;
4254 static DWORD CALLBACK
ammediastream_receive_release(void *p
)
4256 struct ammediastream_receive_release_param
*param
= (struct ammediastream_receive_release_param
*)p
;
4260 hr
= IMemInputPin_Receive(param
->mem_input_pin
, param
->media_sample
);
4261 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4263 ref
= IMediaSample_Release(param
->media_sample
);
4264 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4271 static HANDLE
ammediastream_async_receive_time(struct testfilter
*source
,
4272 REFERENCE_TIME start_time
, REFERENCE_TIME end_time
, const BYTE
*input_data
, DWORD input_length
)
4274 struct ammediastream_receive_release_param
*param
;
4275 IMediaSample
*sample
;
4278 sample
= ammediastream_allocate_sample(source
, input_data
, input_length
);
4279 hr
= IMediaSample_SetTime(sample
, &start_time
, &end_time
);
4280 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4282 param
= calloc(1, sizeof(*param
));
4283 param
->mem_input_pin
= source
->source
.pMemInputPin
;
4284 param
->media_sample
= sample
;
4285 return CreateThread(NULL
, 0, ammediastream_receive_release
, param
, 0, NULL
);
4288 static IStreamSample
*streamsample_sample
;
4289 static DWORD streamsample_flags
;
4290 static DWORD streamsample_timeout
;
4291 static HRESULT streamsample_expected_hr
;
4293 static DWORD CALLBACK
streamsample_completion_status(void *param
)
4297 hr
= IStreamSample_CompletionStatus(streamsample_sample
, streamsample_flags
, streamsample_timeout
);
4298 ok(hr
== streamsample_expected_hr
, "Got hr %#x.\n", hr
);
4303 static void test_audiostreamsample_update(void)
4305 static const BYTE test_data
[] = { 0, 1, 2, 3, 4, 5, 6, 7 };
4306 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
4307 IAudioStreamSample
*stream_sample
;
4308 IAudioMediaStream
*audio_stream
;
4309 IMediaControl
*media_control
;
4310 IMemInputPin
*mem_input_pin
;
4311 IMediaSample
*media_sample1
;
4312 IMediaSample
*media_sample2
;
4313 struct testfilter source
;
4314 IAudioData
*audio_data
;
4315 IGraphBuilder
*graph
;
4316 IMediaStream
*stream
;
4317 DWORD actual_length
;
4325 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
4326 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4327 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
4328 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4329 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
4330 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4331 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
4332 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4333 hr
= IMediaStream_QueryInterface(stream
, &IID_IMemInputPin
, (void **)&mem_input_pin
);
4334 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4335 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
4336 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4337 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
4338 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaControl
, (void **)&media_control
);
4339 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4340 testfilter_init(&source
);
4341 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
4342 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4343 hr
= CoCreateInstance(&CLSID_AMAudioData
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAudioData
, (void **)&audio_data
);
4344 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4345 hr
= IAudioMediaStream_CreateSample(audio_stream
, audio_data
, 0, &stream_sample
);
4346 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4347 event
= CreateEventW(NULL
, FALSE
, FALSE
, NULL
);
4348 ok(event
!= NULL
, "Expected non-NULL event.");
4350 hr
= IAudioStreamSample_Update(stream_sample
, 0, event
, apc_func
, 0);
4351 ok(hr
== MS_E_NOTINIT
, "Got hr %#x.\n", hr
);
4353 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4354 ok(hr
== MS_E_NOTINIT
, "Got hr %#x.\n", hr
);
4356 hr
= IAudioData_SetBuffer(audio_data
, sizeof(buffer
), buffer
, 0);
4357 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4359 hr
= IAudioStreamSample_Update(stream_sample
, 0, event
, apc_func
, 0);
4360 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
4362 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4363 ok(hr
== MS_E_NOTRUNNING
, "Got hr %#x.\n", hr
);
4365 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
4366 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4368 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4369 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
4371 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
4372 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4373 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &audio_mt
);
4374 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4375 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
4376 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4378 media_sample1
= ammediastream_allocate_sample(&source
, test_data
, 8);
4379 hr
= IMemInputPin_Receive(mem_input_pin
, media_sample1
);
4380 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4381 ref
= get_refcount(media_sample1
);
4382 ok(ref
== 2, "Got unexpected refcount %d.\n", ref
);
4384 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4385 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4387 hr
= IAudioData_GetInfo(audio_data
, NULL
, NULL
, &actual_length
);
4388 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4389 ok(actual_length
== 6, "Got actual length %u.\n", actual_length
);
4391 ok(memcmp(buffer
, test_data
, 6) == 0, "Sample data didn't match.\n");
4393 ref
= get_refcount(media_sample1
);
4394 ok(ref
== 2, "Got unexpected refcount %d.\n", ref
);
4396 media_sample2
= ammediastream_allocate_sample(&source
, test_data
, 8);
4397 hr
= IMemInputPin_Receive(mem_input_pin
, media_sample2
);
4398 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4399 ref
= get_refcount(media_sample2
);
4400 ok(ref
== 2, "Got unexpected refcount %d.\n", ref
);
4402 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4403 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4405 hr
= IAudioData_GetInfo(audio_data
, NULL
, NULL
, &actual_length
);
4406 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4407 ok(actual_length
== 6, "Got actual length %u.\n", actual_length
);
4409 ok(memcmp(buffer
, &test_data
[6], 2) == 0, "Sample data didn't match.\n");
4410 ok(memcmp(&buffer
[2], test_data
, 4) == 0, "Sample data didn't match.\n");
4412 ref
= IMediaSample_Release(media_sample1
);
4413 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4415 hr
= IPin_EndOfStream(pin
);
4416 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4418 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4419 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4421 hr
= IAudioData_GetInfo(audio_data
, NULL
, NULL
, &actual_length
);
4422 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4423 ok(actual_length
== 4, "Got actual length %u.\n", actual_length
);
4425 ok(memcmp(buffer
, &test_data
[4], 4) == 0, "Sample data didn't match.\n");
4427 ref
= IMediaSample_Release(media_sample2
);
4428 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4430 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4431 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
4433 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
4434 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4435 hr
= IMediaControl_Pause(media_control
);
4436 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4438 media_sample1
= ammediastream_allocate_sample(&source
, test_data
, 6);
4439 hr
= IMemInputPin_Receive(mem_input_pin
, media_sample1
);
4440 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4441 ref
= IMediaSample_Release(media_sample1
);
4442 ok(ref
== 1, "Got outstanding refcount %d.\n", ref
);
4444 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4445 ok(hr
== MS_E_NOTRUNNING
, "Got hr %#x.\n", hr
);
4447 hr
= IMediaControl_Stop(media_control
);
4448 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4449 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
4450 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4452 media_sample1
= ammediastream_allocate_sample(&source
, test_data
, 6);
4454 ammediastream_mem_input_pin
= mem_input_pin
;
4455 ammediastream_media_sample
= media_sample1
;
4456 ammediastream_sleep_time
= 100;
4457 ammediastream_expected_hr
= S_OK
;
4458 thread
= CreateThread(NULL
, 0, ammediastream_receive
, NULL
, 0, NULL
);
4460 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4461 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4463 hr
= IAudioData_GetInfo(audio_data
, NULL
, NULL
, &actual_length
);
4464 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4465 ok(actual_length
== 6, "Got actual length %u.\n", actual_length
);
4467 ok(memcmp(buffer
, test_data
, 6) == 0, "Sample data didn't match.\n");
4469 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
4470 CloseHandle(thread
);
4472 ref
= IMediaSample_Release(media_sample1
);
4473 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4475 ammediastream_pin
= pin
;
4476 ammediastream_sleep_time
= 100;
4477 ammediastream_expected_hr
= S_OK
;
4478 thread
= CreateThread(NULL
, 0, ammediastream_end_of_stream
, NULL
, 0, NULL
);
4480 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4481 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
4483 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
4484 CloseHandle(thread
);
4486 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
4487 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4488 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
4489 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4491 hr
= IAudioStreamSample_Update(stream_sample
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
4492 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
4494 IAudioStreamSample_AddRef(stream_sample
);
4495 ref
= IAudioStreamSample_Release(stream_sample
);
4496 ok(ref
== 1, "Got outstanding refcount %d.\n", ref
);
4498 hr
= IAudioStreamSample_Update(stream_sample
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
4499 ok(hr
== MS_E_BUSY
, "Got hr %#x.\n", hr
);
4501 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
4502 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4503 IGraphBuilder_Disconnect(graph
, pin
);
4504 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
4505 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
4506 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4508 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4509 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
4511 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
4514 ref
= IAudioStreamSample_Release(stream_sample
);
4515 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4516 ref
= IAudioData_Release(audio_data
);
4517 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4518 ref
= IAMMultiMediaStream_Release(mmstream
);
4519 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4520 IMediaControl_Release(media_control
);
4521 ref
= IGraphBuilder_Release(graph
);
4522 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4524 IMemInputPin_Release(mem_input_pin
);
4525 IAudioMediaStream_Release(audio_stream
);
4526 ref
= IMediaStream_Release(stream
);
4527 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4530 void test_audiostreamsample_completion_status(void)
4532 static const BYTE test_data
[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11 };
4533 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
4534 IAudioStreamSample
*stream_sample1
;
4535 IAudioStreamSample
*stream_sample2
;
4536 IAudioMediaStream
*audio_stream
;
4537 IMediaSample
*media_sample
;
4538 struct testfilter source
;
4539 IAudioData
*audio_data1
;
4540 IAudioData
*audio_data2
;
4541 IGraphBuilder
*graph
;
4542 IMediaStream
*stream
;
4548 event
= CreateEventW(NULL
, FALSE
, FALSE
, NULL
);
4549 ok(event
!= NULL
, "Expected non-NULL event.");
4551 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
4552 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4553 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
4554 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4555 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
4556 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4557 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
4558 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4559 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
4560 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4561 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
4562 testfilter_init(&source
);
4563 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
4564 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4565 hr
= CoCreateInstance(&CLSID_AMAudioData
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAudioData
, (void **)&audio_data1
);
4566 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4567 hr
= CoCreateInstance(&CLSID_AMAudioData
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAudioData
, (void **)&audio_data2
);
4568 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4569 hr
= IAudioData_SetBuffer(audio_data1
, 6, NULL
, 0);
4570 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4571 hr
= IAudioData_SetBuffer(audio_data2
, 6, NULL
, 0);
4572 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4573 hr
= IAudioMediaStream_CreateSample(audio_stream
, audio_data1
, 0, &stream_sample1
);
4574 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4575 hr
= IAudioMediaStream_CreateSample(audio_stream
, audio_data2
, 0, &stream_sample2
);
4576 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4578 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &audio_mt
);
4579 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4580 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
4581 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4583 hr
= IAudioStreamSample_CompletionStatus(stream_sample1
, 0, 0);
4584 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4586 hr
= IAudioStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
4587 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
4589 hr
= IAudioStreamSample_CompletionStatus(stream_sample1
, 0, 0);
4590 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
4592 media_sample
= ammediastream_allocate_sample(&source
, test_data
, 6);
4593 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
4594 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4595 ref
= IMediaSample_Release(media_sample
);
4596 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4598 hr
= IAudioStreamSample_CompletionStatus(stream_sample1
, 0, 0);
4599 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4601 hr
= IAudioStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
4602 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
4604 hr
= IAudioStreamSample_Update(stream_sample2
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
4605 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
4607 media_sample
= ammediastream_allocate_sample(&source
, test_data
, 12);
4608 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
4609 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4610 ref
= IMediaSample_Release(media_sample
);
4611 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4613 hr
= IAudioStreamSample_CompletionStatus(stream_sample1
, 0, 0);
4614 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4616 hr
= IAudioStreamSample_CompletionStatus(stream_sample2
, 0, 0);
4617 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4619 hr
= IAudioStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
4620 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
4622 hr
= IPin_EndOfStream(pin
);
4623 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4625 hr
= IAudioStreamSample_CompletionStatus(stream_sample1
, 0, 0);
4626 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
4628 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
4629 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4630 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
4631 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4633 hr
= IAudioStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
4634 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
4636 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
4637 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4639 hr
= IAudioStreamSample_CompletionStatus(stream_sample1
, 0, 0);
4640 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
4642 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
4643 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4645 media_sample
= ammediastream_allocate_sample(&source
, test_data
, 6);
4646 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
4647 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4648 ref
= IMediaSample_Release(media_sample
);
4649 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4651 hr
= IAudioStreamSample_CompletionStatus(stream_sample1
, 0, 0);
4652 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4654 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
4655 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4657 IGraphBuilder_Disconnect(graph
, pin
);
4658 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
4660 ref
= IAudioStreamSample_Release(stream_sample1
);
4661 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4662 ref
= IAudioStreamSample_Release(stream_sample2
);
4663 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4664 ref
= IAudioData_Release(audio_data1
);
4665 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4666 ref
= IAudioData_Release(audio_data2
);
4667 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4668 ref
= IAMMultiMediaStream_Release(mmstream
);
4669 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4670 ref
= IGraphBuilder_Release(graph
);
4671 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4673 IAudioMediaStream_Release(audio_stream
);
4674 ref
= IMediaStream_Release(stream
);
4675 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4680 static void test_audiostreamsample_get_sample_times(void)
4682 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
4683 static const BYTE test_data
[8] = { 0 };
4684 IAudioStreamSample
*stream_sample
;
4685 IMediaFilter
*graph_media_filter
;
4686 IAudioMediaStream
*audio_stream
;
4687 STREAM_TIME filter_start_time
;
4688 IMemInputPin
*mem_input_pin
;
4689 IMediaStreamFilter
*filter
;
4690 IMediaSample
*media_sample
;
4691 struct testfilter source
;
4692 STREAM_TIME current_time
;
4693 struct testclock clock
;
4694 IAudioData
*audio_data
;
4695 STREAM_TIME start_time
;
4696 STREAM_TIME end_time
;
4697 IGraphBuilder
*graph
;
4698 IMediaStream
*stream
;
4703 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
4704 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4705 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
4706 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4707 ok(!!filter
, "Expected non-null filter.\n");
4708 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
4709 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4710 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
4711 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4712 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
4713 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4714 hr
= IMediaStream_QueryInterface(stream
, &IID_IMemInputPin
, (void **)&mem_input_pin
);
4715 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4716 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
4717 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4718 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
4719 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaFilter
, (void **)&graph_media_filter
);
4720 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4721 testfilter_init(&source
);
4722 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
4723 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4724 hr
= CoCreateInstance(&CLSID_AMAudioData
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAudioData
, (void **)&audio_data
);
4725 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4726 hr
= IAudioMediaStream_CreateSample(audio_stream
, audio_data
, 0, &stream_sample
);
4727 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4728 hr
= IAudioData_SetBuffer(audio_data
, 5, NULL
, 0);
4729 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4730 testclock_init(&clock
);
4732 clock
.time
= 12345678;
4734 current_time
= 0xdeadbeefdeadbeef;
4735 hr
= IAudioStreamSample_GetSampleTimes(stream_sample
, NULL
, NULL
, ¤t_time
);
4736 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4737 ok(current_time
== 0, "Got current time %s.\n", wine_dbgstr_longlong(current_time
));
4739 IMediaFilter_SetSyncSource(graph_media_filter
, &clock
.IReferenceClock_iface
);
4740 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4742 current_time
= 0xdeadbeefdeadbeef;
4743 hr
= IAudioStreamSample_GetSampleTimes(stream_sample
, NULL
, NULL
, ¤t_time
);
4744 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4745 ok(current_time
== 0, "Got current time %s.\n", wine_dbgstr_longlong(current_time
));
4747 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &audio_mt
);
4748 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4749 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
4750 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4752 hr
= IMediaStreamFilter_GetCurrentStreamTime(filter
, &filter_start_time
);
4753 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4755 clock
.get_time_hr
= E_FAIL
;
4757 current_time
= 0xdeadbeefdeadbeef;
4758 hr
= IAudioStreamSample_GetSampleTimes(stream_sample
, NULL
, NULL
, ¤t_time
);
4759 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4760 ok(current_time
== 0xdeadbeefddf15da1 + filter_start_time
, "Expected current time %s, got %s.\n",
4761 wine_dbgstr_longlong(0xdeadbeefddf15da1 + filter_start_time
), wine_dbgstr_longlong(current_time
));
4763 clock
.get_time_hr
= S_OK
;
4765 current_time
= 0xdeadbeefdeadbeef;
4766 hr
= IAudioStreamSample_GetSampleTimes(stream_sample
, NULL
, NULL
, ¤t_time
);
4767 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4768 ok(current_time
== filter_start_time
, "Expected current time %s, got %s.\n",
4769 wine_dbgstr_longlong(filter_start_time
), wine_dbgstr_longlong(current_time
));
4771 clock
.time
= 23456789;
4773 current_time
= 0xdeadbeefdeadbeef;
4774 hr
= IAudioStreamSample_GetSampleTimes(stream_sample
, NULL
, NULL
, ¤t_time
);
4775 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4776 ok(current_time
== filter_start_time
+ 11111111, "Expected current time %s, got %s.\n",
4777 wine_dbgstr_longlong(filter_start_time
+ 11111111), wine_dbgstr_longlong(current_time
));
4779 start_time
= 0xdeadbeefdeadbeef;
4780 end_time
= 0xdeadbeefdeadbeef;
4781 hr
= IAudioStreamSample_GetSampleTimes(stream_sample
, &start_time
, &end_time
, NULL
);
4782 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4783 ok(start_time
== 0, "Got start time %s.\n", wine_dbgstr_longlong(start_time
));
4784 ok(end_time
== 0, "Got end time %s.\n", wine_dbgstr_longlong(end_time
));
4786 media_sample
= ammediastream_allocate_sample(&source
, test_data
, 8);
4787 start_time
= 12345678;
4788 end_time
= 23456789;
4789 hr
= IMediaSample_SetTime(media_sample
, &start_time
, &end_time
);
4790 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4791 hr
= IMemInputPin_Receive(mem_input_pin
, media_sample
);
4792 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4793 IMediaSample_Release(media_sample
);
4795 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4796 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4798 start_time
= 0xdeadbeefdeadbeef;
4799 end_time
= 0xdeadbeefdeadbeef;
4800 hr
= IAudioStreamSample_GetSampleTimes(stream_sample
, &start_time
, &end_time
, NULL
);
4801 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4802 ok(start_time
== 12345678, "Got start time %s.\n", wine_dbgstr_longlong(start_time
));
4803 ok(end_time
== 12347946, "Got end time %s.\n", wine_dbgstr_longlong(end_time
));
4805 media_sample
= ammediastream_allocate_sample(&source
, test_data
, 6);
4806 start_time
= 12345678;
4807 end_time
= 23456789;
4808 hr
= IMediaSample_SetTime(media_sample
, &start_time
, &end_time
);
4809 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4810 hr
= IMemInputPin_Receive(mem_input_pin
, media_sample
);
4811 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4812 IMediaSample_Release(media_sample
);
4814 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4815 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4817 start_time
= 0xdeadbeefdeadbeef;
4818 end_time
= 0xdeadbeefdeadbeef;
4819 hr
= IAudioStreamSample_GetSampleTimes(stream_sample
, &start_time
, &end_time
, NULL
);
4820 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4821 ok(start_time
== 12347946, "Got start time %s.\n", wine_dbgstr_longlong(start_time
));
4822 ok(end_time
== 12346585, "Got end time %s.\n", wine_dbgstr_longlong(end_time
));
4824 hr
= IPin_EndOfStream(pin
);
4825 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4827 hr
= IAudioStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
4828 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4830 start_time
= 0xdeadbeefdeadbeef;
4831 end_time
= 0xdeadbeefdeadbeef;
4832 hr
= IAudioStreamSample_GetSampleTimes(stream_sample
, &start_time
, &end_time
, NULL
);
4833 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4834 ok(start_time
== 12346585, "Got start time %s.\n", wine_dbgstr_longlong(start_time
));
4835 ok(end_time
== 12348399, "Got end time %s.\n", wine_dbgstr_longlong(end_time
));
4837 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
4838 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4839 IGraphBuilder_Disconnect(graph
, pin
);
4840 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
4842 ref
= IAudioStreamSample_Release(stream_sample
);
4843 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4844 ref
= IAudioData_Release(audio_data
);
4845 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4846 ref
= IAMMultiMediaStream_Release(mmstream
);
4847 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4848 IMediaFilter_Release(graph_media_filter
);
4849 ref
= IGraphBuilder_Release(graph
);
4850 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4851 ref
= IMediaStreamFilter_Release(filter
);
4852 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4854 IMemInputPin_Release(mem_input_pin
);
4855 IAudioMediaStream_Release(audio_stream
);
4856 ref
= IMediaStream_Release(stream
);
4857 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4860 static void test_ddrawstream_initialize(void)
4862 IDirectDrawMediaStream
*ddraw_stream
;
4863 IAMMediaStream
*stream
;
4864 IDirectDraw
*ddraw2
;
4871 hr
= DirectDrawCreate(NULL
, &ddraw
, NULL
);
4872 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4874 hr
= CoCreateInstance(&CLSID_AMDirectDrawStream
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAMMediaStream
, (void **)&stream
);
4875 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4877 hr
= IAMMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
4878 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4880 /* Crashes on native. */
4883 hr
= IAMMediaStream_Initialize(stream
, NULL
, 0, NULL
, STREAMTYPE_WRITE
);
4884 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
4887 hr
= IAMMediaStream_Initialize(stream
, NULL
, 0, &test_mspid
, STREAMTYPE_WRITE
);
4888 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4890 hr
= IAMMediaStream_GetInformation(stream
, &mspid
, &type
);
4891 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4892 ok(IsEqualGUID(&mspid
, &test_mspid
), "Got mspid %s.\n", wine_dbgstr_guid(&mspid
));
4893 ok(type
== STREAMTYPE_WRITE
, "Got type %u.\n", type
);
4895 hr
= IAMMediaStream_Initialize(stream
, (IUnknown
*)ddraw
, 0, &MSPID_PrimaryAudio
, STREAMTYPE_READ
);
4896 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4898 hr
= IAMMediaStream_GetInformation(stream
, &mspid
, &type
);
4899 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4900 ok(IsEqualGUID(&mspid
, &MSPID_PrimaryAudio
), "Got mspid %s.\n", wine_dbgstr_guid(&mspid
));
4901 ok(type
== STREAMTYPE_READ
, "Got type %u.\n", type
);
4903 hr
= IDirectDrawMediaStream_GetDirectDraw(ddraw_stream
, &ddraw2
);
4904 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4905 ok(ddraw2
== ddraw
, "Expected ddraw %p, got %p.\n", ddraw
, ddraw2
);
4907 IDirectDrawMediaStream_Release(ddraw_stream
);
4908 ref
= IAMMediaStream_Release(stream
);
4909 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4910 IDirectDraw_Release(ddraw2
);
4911 ref
= IDirectDraw_Release(ddraw
);
4912 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
4915 #define check_ddrawstream_get_format(a,b,c) check_ddrawstream_get_format_(__LINE__,a,b,c)
4916 static void check_ddrawstream_get_format_(int line
, IDirectDrawMediaStream
*stream
,
4917 const AM_MEDIA_TYPE
*mt
, const DDSURFACEDESC
*expected_format
)
4919 DDSURFACEDESC current_format
;
4920 DDSURFACEDESC desired_format
;
4921 struct testfilter source
;
4922 FILTER_INFO filter_info
;
4923 DDSURFACEDESC format
;
4929 hr
= IDirectDrawMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
4930 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
4931 hr
= IPin_QueryPinInfo(pin
, &pin_info
);
4932 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
4933 hr
= IBaseFilter_QueryFilterInfo(pin_info
.pFilter
, &filter_info
);
4934 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
4936 testfilter_init(&source
);
4938 hr
= IFilterGraph_AddFilter(filter_info
.pGraph
, &source
.filter
.IBaseFilter_iface
, L
"source");
4939 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
4941 hr
= IFilterGraph_ConnectDirect(filter_info
.pGraph
, &source
.source
.pin
.IPin_iface
, pin
, mt
);
4942 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
4944 hr
= IDirectDrawMediaStream_GetFormat(stream
, NULL
, NULL
, NULL
, NULL
);
4945 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
4947 memset(¤t_format
, 0xcc, sizeof(current_format
));
4948 current_format
.dwSize
= sizeof(current_format
);
4949 memset(&desired_format
, 0xcc, sizeof(desired_format
));
4950 desired_format
.dwSize
= sizeof(desired_format
);
4952 hr
= IDirectDrawMediaStream_GetFormat(stream
, ¤t_format
, NULL
, &desired_format
, &flags
);
4953 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
4954 memset(&format
, 0xcc, sizeof(format
));
4955 format
.dwSize
= sizeof(format
);
4956 format
.ddpfPixelFormat
= expected_format
->ddpfPixelFormat
;
4957 format
.dwFlags
= DDSD_WIDTH
| DDSD_HEIGHT
| DDSD_CAPS
;
4958 format
.dwWidth
= 333;
4959 format
.dwHeight
= 444;
4960 format
.ddsCaps
.dwCaps
= DDSCAPS_OFFSCREENPLAIN
| DDSCAPS_SYSTEMMEMORY
;
4961 ok_(__FILE__
, line
)(memcmp(¤t_format
, &format
, sizeof(DDSURFACEDESC
)) == 0, "Current format didn't match.\n");
4962 format
.dwFlags
= DDSD_WIDTH
| DDSD_HEIGHT
;
4963 ok_(__FILE__
, line
)(memcmp(&desired_format
, &format
, sizeof(DDSURFACEDESC
)) == 0, "Desired format didn't match.\n");
4965 hr
= IFilterGraph_Disconnect(filter_info
.pGraph
, &source
.source
.pin
.IPin_iface
);
4966 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
4967 hr
= IFilterGraph_Disconnect(filter_info
.pGraph
, pin
);
4968 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
4970 hr
= IFilterGraph_RemoveFilter(filter_info
.pGraph
, &source
.filter
.IBaseFilter_iface
);
4971 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
4973 IFilterGraph_Release(filter_info
.pGraph
);
4974 IBaseFilter_Release(pin_info
.pFilter
);
4978 static void test_ddrawstream_get_format(void)
4980 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
4981 IDirectDrawMediaStream
*ddraw_stream
;
4982 DDSURFACEDESC current_format
;
4983 DDSURFACEDESC desired_format
;
4984 IDirectDrawPalette
*palette
;
4985 IMediaStream
*stream
;
4986 VIDEOINFO video_info
;
4992 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
4993 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4994 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
4995 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
4997 current_format
.dwSize
= sizeof(current_format
);
4998 desired_format
.dwSize
= sizeof(desired_format
);
4999 hr
= IDirectDrawMediaStream_GetFormat(ddraw_stream
, ¤t_format
, &palette
, &desired_format
, &flags
);
5000 ok(hr
== MS_E_NOSTREAM
, "Got hr %#x.\n", hr
);
5002 video_info
= rgb32_video_info
;
5003 video_info
.rcSource
.right
= 222;
5004 video_info
.rcSource
.bottom
= 333;
5005 video_info
.rcTarget
.right
= 444;
5006 video_info
.rcTarget
.bottom
= 666;
5008 mt
.pbFormat
= (BYTE
*)&video_info
;
5009 check_ddrawstream_get_format(ddraw_stream
, &mt
, &rgb32_format
);
5011 video_info
= rgb32_video_info
;
5012 video_info
.bmiHeader
.biHeight
= 444;
5014 mt
.pbFormat
= (BYTE
*)&video_info
;
5015 check_ddrawstream_get_format(ddraw_stream
, &mt
, &rgb32_format
);
5017 check_ddrawstream_get_format(ddraw_stream
, &rgb8_mt
, &rgb8_format
);
5018 check_ddrawstream_get_format(ddraw_stream
, &rgb555_mt
, &rgb555_format
);
5019 check_ddrawstream_get_format(ddraw_stream
, &rgb565_mt
, &rgb565_format
);
5020 check_ddrawstream_get_format(ddraw_stream
, &rgb24_mt
, &rgb24_format
);
5021 check_ddrawstream_get_format(ddraw_stream
, &rgb32_mt
, &rgb32_format
);
5023 current_format
.dwSize
= sizeof(current_format
);
5024 desired_format
.dwSize
= sizeof(desired_format
);
5025 hr
= IDirectDrawMediaStream_GetFormat(ddraw_stream
, ¤t_format
, &palette
, &desired_format
, &flags
);
5026 ok(hr
== MS_E_NOSTREAM
, "Got hr %#x.\n", hr
);
5028 ref
= IAMMultiMediaStream_Release(mmstream
);
5029 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5030 IDirectDrawMediaStream_Release(ddraw_stream
);
5031 ref
= IMediaStream_Release(stream
);
5032 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5035 #define check_ddrawstream_set_format(a,b,c,d) check_ddrawstream_set_format_(__LINE__,a,b,c,d)
5036 static void check_ddrawstream_set_format_(int line
, IDirectDrawMediaStream
*stream
,
5037 const DDSURFACEDESC
*format
, const AM_MEDIA_TYPE
*mt
, HRESULT expected_hr
)
5039 struct testfilter source
;
5040 FILTER_INFO filter_info
;
5045 hr
= IDirectDrawMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
5046 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
5047 hr
= IPin_QueryPinInfo(pin
, &pin_info
);
5048 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
5049 hr
= IBaseFilter_QueryFilterInfo(pin_info
.pFilter
, &filter_info
);
5050 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
5052 testfilter_init(&source
);
5054 hr
= IFilterGraph_AddFilter(filter_info
.pGraph
, &source
.filter
.IBaseFilter_iface
, L
"source");
5055 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
5057 hr
= IDirectDrawMediaStream_SetFormat(stream
, format
, NULL
);
5058 ok_(__FILE__
, line
)(hr
== expected_hr
, "Got hr %#x.\n", hr
);
5062 DDSURFACEDESC current_format
;
5063 DDSURFACEDESC desired_format
;
5066 hr
= IFilterGraph_ConnectDirect(filter_info
.pGraph
, &source
.source
.pin
.IPin_iface
, pin
, mt
);
5067 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
5069 memset(¤t_format
, 0xcc, sizeof(current_format
));
5070 memset(&desired_format
, 0xcc, sizeof(desired_format
));
5072 current_format
.dwSize
= sizeof(current_format
);
5073 desired_format
.dwSize
= sizeof(desired_format
);
5074 hr
= IDirectDrawMediaStream_GetFormat(stream
, ¤t_format
, NULL
, &desired_format
, &flags
);
5075 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
5076 if (format
->dwFlags
& DDSD_PIXELFORMAT
)
5078 ok_(__FILE__
, line
)(current_format
.dwFlags
== (DDSD_WIDTH
| DDSD_HEIGHT
| DDSD_CAPS
| DDSD_PIXELFORMAT
),
5079 "Got current format flags %#x.\n", current_format
.dwFlags
);
5080 ok_(__FILE__
, line
)(memcmp(¤t_format
.ddpfPixelFormat
, &format
->ddpfPixelFormat
, sizeof(DDPIXELFORMAT
)) == 0,
5081 "Current pixel format didn't match.\n");
5082 ok_(__FILE__
, line
)(memcmp(&desired_format
.ddpfPixelFormat
, &format
->ddpfPixelFormat
, sizeof(DDPIXELFORMAT
)) == 0,
5083 "Desired pixel format didn't match.\n");
5087 ok_(__FILE__
, line
)(current_format
.dwFlags
== (DDSD_WIDTH
| DDSD_HEIGHT
| DDSD_CAPS
),
5088 "Got flags %#x.\n", current_format
.dwFlags
);
5090 ok_(__FILE__
, line
)(desired_format
.dwFlags
== (DDSD_WIDTH
| DDSD_HEIGHT
),
5091 "Got desired format flags %#x.\n", desired_format
.dwFlags
);
5092 ok_(__FILE__
, line
)(current_format
.ddsCaps
.dwCaps
== (DDSCAPS_OFFSCREENPLAIN
| DDSCAPS_SYSTEMMEMORY
),
5093 "Got current format caps %#x.\n", current_format
.ddsCaps
.dwCaps
);
5094 ok_(__FILE__
, line
)(desired_format
.ddsCaps
.dwCaps
== (DDSCAPS_OFFSCREENPLAIN
| DDSCAPS_SYSTEMMEMORY
),
5095 "Got desired format caps %#x.\n", desired_format
.ddsCaps
.dwCaps
);
5096 ok_(__FILE__
, line
)(flags
== 0, "Got flags %#x.\n", flags
);
5098 hr
= IFilterGraph_Disconnect(filter_info
.pGraph
, &source
.source
.pin
.IPin_iface
);
5099 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
5100 hr
= IFilterGraph_Disconnect(filter_info
.pGraph
, pin
);
5101 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
5104 hr
= IFilterGraph_RemoveFilter(filter_info
.pGraph
, &source
.filter
.IBaseFilter_iface
);
5105 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
5107 IFilterGraph_Release(filter_info
.pGraph
);
5108 IBaseFilter_Release(pin_info
.pFilter
);
5112 static void test_ddrawstream_set_format(void)
5114 static const DDSURFACEDESC rgb1_format
=
5116 .dwSize
= sizeof(DDSURFACEDESC
),
5117 .dwFlags
= DDSD_PIXELFORMAT
,
5118 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
5119 .ddpfPixelFormat
.dwFlags
= DDPF_RGB
| DDPF_PALETTEINDEXED1
,
5120 .ddpfPixelFormat
.u1
.dwRGBBitCount
= 1,
5122 static const DDSURFACEDESC rgb2_format
=
5124 .dwSize
= sizeof(DDSURFACEDESC
),
5125 .dwFlags
= DDSD_PIXELFORMAT
,
5126 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
5127 .ddpfPixelFormat
.dwFlags
= DDPF_RGB
| DDPF_PALETTEINDEXED2
,
5128 .ddpfPixelFormat
.u1
.dwRGBBitCount
= 2,
5130 static const DDSURFACEDESC rgb4_format
=
5132 .dwSize
= sizeof(DDSURFACEDESC
),
5133 .dwFlags
= DDSD_PIXELFORMAT
,
5134 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
5135 .ddpfPixelFormat
.dwFlags
= DDPF_RGB
| DDPF_PALETTEINDEXED4
,
5136 .ddpfPixelFormat
.u1
.dwRGBBitCount
= 4,
5138 static const DDSURFACEDESC rgb4to8_format
=
5140 .dwSize
= sizeof(DDSURFACEDESC
),
5141 .dwFlags
= DDSD_PIXELFORMAT
,
5142 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
5143 .ddpfPixelFormat
.dwFlags
= DDPF_RGB
| DDPF_PALETTEINDEXEDTO8
,
5144 .ddpfPixelFormat
.u1
.dwRGBBitCount
= 4,
5146 static const DDSURFACEDESC rgb332_format
=
5148 .dwSize
= sizeof(DDSURFACEDESC
),
5149 .dwFlags
= DDSD_PIXELFORMAT
,
5150 .ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
),
5151 .ddpfPixelFormat
.dwFlags
= DDPF_RGB
,
5152 .ddpfPixelFormat
.u1
.dwRGBBitCount
= 8,
5153 .ddpfPixelFormat
.u2
.dwRBitMask
= 0xe0,
5154 .ddpfPixelFormat
.u3
.dwGBitMask
= 0x1c,
5155 .ddpfPixelFormat
.u4
.dwBBitMask
= 0x03,
5158 IDirectDrawMediaStream
*ddraw_stream
;
5159 IAMMultiMediaStream
*mmstream
;
5160 DDSURFACEDESC current_format
;
5161 DDSURFACEDESC desired_format
;
5162 struct testfilter source
;
5163 IGraphBuilder
*graph
;
5164 DDSURFACEDESC format
;
5165 IMediaStream
*stream
;
5166 VIDEOINFO video_info
;
5172 mmstream
= create_ammultimediastream();
5174 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
5175 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5176 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
5177 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5179 check_ddrawstream_set_format(ddraw_stream
, &rgb8_format
, &rgb8_mt
, S_OK
);
5180 check_ddrawstream_set_format(ddraw_stream
, &rgb555_format
, &rgb555_mt
, S_OK
);
5181 check_ddrawstream_set_format(ddraw_stream
, &rgb565_format
, &rgb565_mt
, S_OK
);
5182 check_ddrawstream_set_format(ddraw_stream
, &rgb24_format
, &rgb24_mt
, S_OK
);
5183 check_ddrawstream_set_format(ddraw_stream
, &rgb32_format
, &rgb32_mt
, S_OK
);
5184 check_ddrawstream_set_format(ddraw_stream
, &argb32_format
, &rgb32_mt
, S_OK
);
5185 check_ddrawstream_set_format(ddraw_stream
, &yuy2_format
, NULL
, S_OK
);
5186 check_ddrawstream_set_format(ddraw_stream
, &yv12_format
, NULL
, S_OK
);
5188 format
= rgb32_format
;
5189 format
.ddpfPixelFormat
.dwFlags
|= DDPF_ALPHAPIXELS
| DDPF_ALPHA
5190 | DDPF_COMPRESSED
| DDPF_RGBTOYUV
| DDPF_ZBUFFER
| DDPF_ZPIXELS
| DDPF_STENCILBUFFER
5191 | DDPF_ALPHAPREMULT
| DDPF_LUMINANCE
| DDPF_BUMPLUMINANCE
| DDPF_BUMPDUDV
;
5192 check_ddrawstream_set_format(ddraw_stream
, &format
, &rgb32_mt
, S_OK
);
5194 format
= yuy2_format
;
5195 format
.ddpfPixelFormat
.dwFlags
|= DDPF_ALPHAPIXELS
| DDPF_ALPHA
5196 | DDPF_PALETTEINDEXED4
| DDPF_PALETTEINDEXEDTO8
| DDPF_PALETTEINDEXED8
5197 | DDPF_RGB
| DDPF_COMPRESSED
| DDPF_RGBTOYUV
| DDPF_YUV
| DDPF_ZBUFFER
5198 | DDPF_PALETTEINDEXED1
| DDPF_PALETTEINDEXED2
| DDPF_ZPIXELS
5199 | DDPF_STENCILBUFFER
| DDPF_ALPHAPREMULT
| DDPF_LUMINANCE
5200 | DDPF_BUMPLUMINANCE
| DDPF_BUMPDUDV
;
5201 check_ddrawstream_set_format(ddraw_stream
, &format
, NULL
, S_OK
);
5203 format
= rgb32_format
;
5204 format
.dwFlags
|= DDSD_CAPS
;
5205 format
.ddsCaps
.dwCaps
= DDSCAPS_OFFSCREENPLAIN
| DDSCAPS_VIDEOMEMORY
;
5206 check_ddrawstream_set_format(ddraw_stream
, &format
, &rgb32_mt
, S_OK
);
5208 format
= rgb8_format
;
5210 check_ddrawstream_set_format(ddraw_stream
, &format
, &rgb32_mt
, S_OK
);
5212 check_ddrawstream_set_format(ddraw_stream
, &rgb1_format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5213 check_ddrawstream_set_format(ddraw_stream
, &rgb2_format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5214 check_ddrawstream_set_format(ddraw_stream
, &rgb4_format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5215 check_ddrawstream_set_format(ddraw_stream
, &rgb4to8_format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5216 check_ddrawstream_set_format(ddraw_stream
, &rgb332_format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5218 format
= rgb8_format
;
5219 format
.ddpfPixelFormat
.dwFlags
&= ~DDPF_RGB
;
5220 check_ddrawstream_set_format(ddraw_stream
, &format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5222 format
= rgb8_format
;
5223 format
.ddpfPixelFormat
.dwFlags
|= DDPF_PALETTEINDEXED1
;
5224 check_ddrawstream_set_format(ddraw_stream
, &format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5226 format
= rgb32_format
;
5227 format
.ddpfPixelFormat
.dwFlags
|= DDPF_PALETTEINDEXED8
;
5228 check_ddrawstream_set_format(ddraw_stream
, &format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5230 format
= rgb32_format
;
5231 format
.ddpfPixelFormat
.dwFlags
|= DDPF_YUV
;
5232 check_ddrawstream_set_format(ddraw_stream
, &format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5234 format
= rgb565_format
;
5235 format
.ddpfPixelFormat
.u2
.dwRBitMask
= 0x001f;
5236 format
.ddpfPixelFormat
.u3
.dwGBitMask
= 0x07e0;
5237 format
.ddpfPixelFormat
.u4
.dwBBitMask
= 0xf800;
5238 check_ddrawstream_set_format(ddraw_stream
, &format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5240 format
= rgb32_format
;
5241 format
.ddpfPixelFormat
.u2
.dwRBitMask
= 0x00ff00;
5242 format
.ddpfPixelFormat
.u3
.dwGBitMask
= 0x0000ff;
5243 format
.ddpfPixelFormat
.u4
.dwBBitMask
= 0xff0000;
5244 check_ddrawstream_set_format(ddraw_stream
, &format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5246 format
= yuy2_format
;
5247 format
.ddpfPixelFormat
.u1
.dwYUVBitCount
= 0;
5248 check_ddrawstream_set_format(ddraw_stream
, &format
, NULL
, E_INVALIDARG
);
5250 format
= rgb32_format
;
5251 format
.dwSize
= sizeof(DDSURFACEDESC
) + 1;
5252 check_ddrawstream_set_format(ddraw_stream
, &format
, NULL
, E_INVALIDARG
);
5254 format
= rgb32_format
;
5255 format
.ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
) + 1;
5256 check_ddrawstream_set_format(ddraw_stream
, &format
, NULL
, DDERR_INVALIDSURFACETYPE
);
5258 ref
= IAMMultiMediaStream_Release(mmstream
);
5259 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5260 IDirectDrawMediaStream_Release(ddraw_stream
);
5261 ref
= IMediaStream_Release(stream
);
5262 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5264 mmstream
= create_ammultimediastream();
5266 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
5267 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5268 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
5269 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5270 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
5271 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5273 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
5274 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5275 ok(!!graph
, "Expected non-NULL graph.\n");
5277 testfilter_init(&source
);
5279 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, L
"source");
5280 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5282 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &rgb8_mt
);
5283 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5285 source
.preferred_mt
= NULL
;
5287 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &rgb555_format
, NULL
);
5288 ok(hr
== DDERR_INVALIDSURFACETYPE
, "Got hr %#x.\n", hr
);
5289 ok(IsEqualGUID(&source
.source
.pin
.mt
.subtype
, &MEDIASUBTYPE_RGB8
),
5290 "Got subtype %s.\n", wine_dbgstr_guid(&source
.source
.pin
.mt
.subtype
));
5291 hr
= IDirectDrawMediaStream_GetFormat(ddraw_stream
, ¤t_format
, NULL
, &desired_format
, NULL
);
5292 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5293 ok(current_format
.ddpfPixelFormat
.u1
.dwRGBBitCount
== 8,
5294 "Got rgb bit count %u.\n", current_format
.ddpfPixelFormat
.u1
.dwRGBBitCount
);
5295 ok(desired_format
.ddpfPixelFormat
.u1
.dwRGBBitCount
== 8,
5296 "Got rgb bit count %u.\n", desired_format
.ddpfPixelFormat
.u1
.dwRGBBitCount
);
5298 format
= rgb555_format
;
5300 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &format
, NULL
);
5301 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5302 ok(IsEqualGUID(&source
.source
.pin
.mt
.subtype
, &MEDIASUBTYPE_RGB8
),
5303 "Got subtype %s.\n", wine_dbgstr_guid(&source
.source
.pin
.mt
.subtype
));
5305 source
.preferred_mt
= &rgb555_mt
;
5307 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &rgb8_format
, NULL
);
5308 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5310 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &rgb555_format
, NULL
);
5311 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5312 ok(IsEqualGUID(&source
.source
.pin
.mt
.subtype
, &MEDIASUBTYPE_RGB555
),
5313 "Got subtype %s.\n", wine_dbgstr_guid(&source
.source
.pin
.mt
.subtype
));
5314 hr
= IDirectDrawMediaStream_GetFormat(ddraw_stream
, ¤t_format
, NULL
, &desired_format
, NULL
);
5315 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5316 ok(current_format
.ddpfPixelFormat
.u1
.dwRGBBitCount
== 16,
5317 "Got rgb bit count %u.\n", current_format
.ddpfPixelFormat
.u1
.dwRGBBitCount
);
5318 ok(desired_format
.ddpfPixelFormat
.u1
.dwRGBBitCount
== 16,
5319 "Got rgb bit count %u.\n", desired_format
.ddpfPixelFormat
.u1
.dwRGBBitCount
);
5321 video_info
= rgb555_video_info
;
5322 video_info
.bmiHeader
.biWidth
= 222;
5323 video_info
.bmiHeader
.biHeight
= -555;
5325 mt
.pbFormat
= (BYTE
*)&video_info
;
5326 source
.preferred_mt
= &mt
;
5328 format
= rgb555_format
;
5329 format
.dwFlags
|= DDSD_WIDTH
| DDSD_HEIGHT
;
5330 format
.dwWidth
= 222;
5331 format
.dwHeight
= 555;
5332 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, &format
, NULL
);
5333 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5334 ok(IsEqualGUID(&source
.source
.pin
.mt
.subtype
, &MEDIASUBTYPE_RGB555
),
5335 "Got subtype %s.\n", wine_dbgstr_guid(&source
.source
.pin
.mt
.subtype
));
5336 ok(((VIDEOINFO
*)source
.source
.pin
.mt
.pbFormat
)->bmiHeader
.biWidth
== 222,
5337 "Got width %d.\n", ((VIDEOINFO
*)source
.source
.pin
.mt
.pbFormat
)->bmiHeader
.biWidth
);
5338 ok(((VIDEOINFO
*)source
.source
.pin
.mt
.pbFormat
)->bmiHeader
.biHeight
== -555,
5339 "Got height %d.\n", ((VIDEOINFO
*)source
.source
.pin
.mt
.pbFormat
)->bmiHeader
.biHeight
);
5341 hr
= IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
5342 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5343 hr
= IGraphBuilder_Disconnect(graph
, pin
);
5344 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5346 ref
= IAMMultiMediaStream_Release(mmstream
);
5347 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5348 ref
= IGraphBuilder_Release(graph
);
5349 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5351 IDirectDrawMediaStream_Release(ddraw_stream
);
5352 ref
= IMediaStream_Release(stream
);
5353 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5356 static void test_ddrawstream_receive(void)
5358 ALLOCATOR_PROPERTIES properties
=
5365 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
5366 ALLOCATOR_PROPERTIES actual
;
5367 IMediaStreamFilter
*filter
;
5368 struct testfilter source
;
5369 IMemAllocator
*allocator
;
5370 IGraphBuilder
*graph
;
5371 IMediaStream
*stream
;
5372 IMediaSample
*sample
;
5378 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
5379 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5380 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
5381 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5382 ok(!!filter
, "Expected non-null filter.\n");
5383 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
5384 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5385 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
5386 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5387 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
5388 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5389 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
5390 testfilter_init(&source
);
5391 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
5392 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5393 hr
= CoCreateInstance(&CLSID_MemoryAllocator
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IMemAllocator
, (void **)&allocator
);
5394 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5395 hr
= IMemAllocator_SetProperties(allocator
, &properties
, &actual
);
5396 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5397 hr
= IMemAllocator_Commit(allocator
);
5398 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5400 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &rgb32_mt
);
5401 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5403 hr
= IMemAllocator_GetBuffer(allocator
, &sample
, NULL
, NULL
, 0);
5404 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5405 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, sample
);
5406 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5407 ref
= IMediaSample_Release(sample
);
5408 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5410 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
5411 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5413 hr
= IMemAllocator_GetBuffer(allocator
, &sample
, NULL
, NULL
, 0);
5414 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5416 ammediastream_mem_input_pin
= source
.source
.pMemInputPin
;
5417 ammediastream_media_sample
= sample
;
5418 ammediastream_sleep_time
= 0;
5419 ammediastream_expected_hr
= S_OK
;
5420 thread
= CreateThread(NULL
, 0, ammediastream_receive
, NULL
, 0, NULL
);
5422 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
5424 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
5425 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5427 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
5428 CloseHandle(thread
);
5430 ref
= IMediaSample_Release(sample
);
5431 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5433 hr
= IMemAllocator_GetBuffer(allocator
, &sample
, NULL
, NULL
, 0);
5434 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5435 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, sample
);
5436 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5437 ref
= IMediaSample_Release(sample
);
5438 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5440 IGraphBuilder_Disconnect(graph
, pin
);
5441 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
5443 hr
= IMemAllocator_Decommit(allocator
);
5444 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5446 ref
= IAMMultiMediaStream_Release(mmstream
);
5447 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5448 ref
= IGraphBuilder_Release(graph
);
5449 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5450 ref
= IMediaStreamFilter_Release(filter
);
5451 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5453 ref
= IMediaStream_Release(stream
);
5454 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5455 ref
= IMemAllocator_Release(allocator
);
5456 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5459 static void test_ddrawstream_begin_flush_end_flush(void)
5461 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
5462 IDirectDrawStreamSample
*stream_sample
;
5463 IDirectDrawMediaStream
*ddraw_stream
;
5464 IMediaSample
*media_sample
;
5465 IMediaFilter
*media_filter
;
5466 struct testfilter source
;
5467 IGraphBuilder
*graph
;
5468 IMediaStream
*stream
;
5469 VIDEOINFO video_info
;
5476 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
5477 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5478 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
5479 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5480 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
5481 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5482 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
5483 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5484 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
5485 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5486 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
5487 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaFilter
, (void **)&media_filter
);
5488 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5489 testfilter_init(&source
);
5490 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
5491 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5493 hr
= IMediaFilter_SetSyncSource(media_filter
, NULL
);
5494 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5496 video_info
= rgb32_video_info
;
5497 video_info
.bmiHeader
.biWidth
= 3;
5498 video_info
.bmiHeader
.biHeight
= 1;
5500 mt
.pbFormat
= (BYTE
*)&video_info
;
5501 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
5502 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5504 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, &stream_sample
);
5505 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5507 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
5508 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5510 hr
= BaseOutputPinImpl_GetDeliveryBuffer(&source
.source
, &media_sample
, NULL
, NULL
, 0);
5511 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5513 ammediastream_mem_input_pin
= source
.source
.pMemInputPin
;
5514 ammediastream_media_sample
= media_sample
;
5515 ammediastream_sleep_time
= 0;
5516 ammediastream_expected_hr
= S_FALSE
;
5517 thread
= CreateThread(NULL
, 0, ammediastream_receive
, NULL
, 0, NULL
);
5519 hr
= IPin_BeginFlush(pin
);
5520 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5522 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
5523 CloseHandle(thread
);
5525 ref
= IMediaSample_Release(media_sample
);
5526 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5528 hr
= BaseOutputPinImpl_GetDeliveryBuffer(&source
.source
, &media_sample
, NULL
, NULL
, 0);
5529 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5530 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
5531 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
5533 ref
= IMediaSample_Release(media_sample
);
5534 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5536 hr
= IDirectDrawStreamSample_Update(stream_sample
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
5537 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
5539 hr
= IPin_EndOfStream(pin
);
5540 ok(hr
== E_FAIL
, "Got hr %#x.\n", hr
);
5542 hr
= IPin_EndFlush(pin
);
5543 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5545 hr
= BaseOutputPinImpl_GetDeliveryBuffer(&source
.source
, &media_sample
, NULL
, NULL
, 0);
5546 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5547 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
5548 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5549 ref
= IMediaSample_Release(media_sample
);
5550 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5552 hr
= IPin_EndOfStream(pin
);
5553 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5555 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
5556 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5558 IGraphBuilder_Disconnect(graph
, pin
);
5559 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
5561 ref
= IDirectDrawStreamSample_Release(stream_sample
);
5562 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5563 ref
= IAMMultiMediaStream_Release(mmstream
);
5564 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5565 IMediaFilter_Release(media_filter
);
5566 ref
= IGraphBuilder_Release(graph
);
5567 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5569 IDirectDrawMediaStream_Release(ddraw_stream
);
5570 ref
= IMediaStream_Release(stream
);
5571 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5574 static void test_ddrawstream_new_segment(void)
5576 static const BYTE test_data
[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11 };
5577 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
5578 IDirectDrawStreamSample
*stream_sample
;
5579 IDirectDrawMediaStream
*ddraw_stream
;
5580 IMemInputPin
*mem_input_pin
;
5581 IMediaSample
*media_sample
;
5582 IMediaFilter
*media_filter
;
5583 struct testfilter source
;
5584 STREAM_TIME start_time
;
5585 STREAM_TIME end_time
;
5586 IGraphBuilder
*graph
;
5587 IMediaStream
*stream
;
5588 VIDEOINFO video_info
;
5594 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
5595 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5596 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
5597 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5598 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
5599 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5600 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
5601 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5602 hr
= IMediaStream_QueryInterface(stream
, &IID_IMemInputPin
, (void **)&mem_input_pin
);
5603 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5604 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
5605 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5606 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
5607 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaFilter
, (void **)&media_filter
);
5608 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5609 testfilter_init(&source
);
5610 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
5611 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5613 hr
= IMediaFilter_SetSyncSource(media_filter
, NULL
);
5614 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5616 video_info
= rgb32_video_info
;
5617 video_info
.bmiHeader
.biWidth
= 3;
5618 video_info
.bmiHeader
.biHeight
= 1;
5620 mt
.pbFormat
= (BYTE
*)&video_info
;
5621 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
5622 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5624 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, &stream_sample
);
5625 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5627 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
5628 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5630 hr
= IPin_NewSegment(pin
, 11111111, 22222222, 1.0);
5631 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5633 hr
= IDirectDrawStreamSample_Update(stream_sample
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
5634 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
5636 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
5637 start_time
= 12345678;
5638 end_time
= 23456789;
5639 hr
= IMediaSample_SetTime(media_sample
, &start_time
, &end_time
);
5640 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5641 hr
= IMemInputPin_Receive(mem_input_pin
, media_sample
);
5642 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5643 IMediaSample_Release(media_sample
);
5645 start_time
= 0xdeadbeefdeadbeef;
5646 end_time
= 0xdeadbeefdeadbeef;
5647 hr
= IDirectDrawStreamSample_GetSampleTimes(stream_sample
, &start_time
, &end_time
, NULL
);
5648 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5649 ok(start_time
== 23456789, "Got start time %s.\n", wine_dbgstr_longlong(start_time
));
5650 ok(end_time
== 34567900, "Got end time %s.\n", wine_dbgstr_longlong(end_time
));
5652 hr
= IPin_NewSegment(pin
, 11111111, 22222222, 2.0);
5653 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5655 hr
= IDirectDrawStreamSample_Update(stream_sample
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
5656 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
5658 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
5659 start_time
= 12345678;
5660 end_time
= 23456789;
5661 hr
= IMediaSample_SetTime(media_sample
, &start_time
, &end_time
);
5662 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5663 hr
= IMemInputPin_Receive(mem_input_pin
, media_sample
);
5664 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5665 IMediaSample_Release(media_sample
);
5667 start_time
= 0xdeadbeefdeadbeef;
5668 end_time
= 0xdeadbeefdeadbeef;
5669 hr
= IDirectDrawStreamSample_GetSampleTimes(stream_sample
, &start_time
, &end_time
, NULL
);
5670 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5671 ok(start_time
== 23456789, "Got start time %s.\n", wine_dbgstr_longlong(start_time
));
5672 ok(end_time
== 34567900, "Got end time %s.\n", wine_dbgstr_longlong(end_time
));
5674 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
5675 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5676 IGraphBuilder_Disconnect(graph
, pin
);
5677 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
5679 ref
= IDirectDrawStreamSample_Release(stream_sample
);
5680 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5681 ref
= IAMMultiMediaStream_Release(mmstream
);
5682 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5683 IMediaFilter_Release(media_filter
);
5684 ref
= IGraphBuilder_Release(graph
);
5685 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5687 IMemInputPin_Release(mem_input_pin
);
5688 IDirectDrawMediaStream_Release(ddraw_stream
);
5689 ref
= IMediaStream_Release(stream
);
5690 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5693 static void test_ddrawstream_get_time_per_frame(void)
5695 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
5696 IDirectDrawMediaStream
*ddraw_stream
;
5697 struct testfilter source
;
5698 STREAM_TIME frame_time
;
5699 IGraphBuilder
*graph
;
5700 IMediaStream
*stream
;
5701 VIDEOINFO video_info
;
5707 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
5708 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5709 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
5710 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5711 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
5712 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5713 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
5714 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5715 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
5716 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5717 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
5718 testfilter_init(&source
);
5719 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
5720 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5722 hr
= IDirectDrawMediaStream_GetTimePerFrame(ddraw_stream
, NULL
);
5723 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
5725 hr
= IDirectDrawMediaStream_GetTimePerFrame(ddraw_stream
, &frame_time
);
5726 ok(hr
== MS_E_NOSTREAM
, "Got hr %#x.\n", hr
);
5728 video_info
= rgb32_video_info
;
5729 video_info
.AvgTimePerFrame
= 12345678;
5731 mt
.pbFormat
= (BYTE
*)&video_info
;
5732 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
5733 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5735 frame_time
= 0xdeadbeefdeadbeef;
5736 hr
= IDirectDrawMediaStream_GetTimePerFrame(ddraw_stream
, &frame_time
);
5737 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5738 ok(frame_time
== 12345678, "Got frame time %s.\n", wine_dbgstr_longlong(frame_time
));
5740 ref
= IAMMultiMediaStream_Release(mmstream
);
5741 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5742 ref
= IGraphBuilder_Release(graph
);
5743 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5745 IDirectDrawMediaStream_Release(ddraw_stream
);
5746 ref
= IMediaStream_Release(stream
);
5747 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5750 static void check_ammediastream_join_am_multi_media_stream(const CLSID
*clsid
)
5752 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
5753 IMultiMediaStream
*mmstream2
;
5754 IAMMediaStream
*stream
;
5759 hr
= CoCreateInstance(clsid
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAMMediaStream
, (void **)&stream
);
5760 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5762 mmstream_ref
= get_refcount(mmstream
);
5764 hr
= IAMMediaStream_JoinAMMultiMediaStream(stream
, mmstream
);
5765 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5767 ref
= get_refcount(mmstream
);
5768 ok(ref
== mmstream_ref
, "Expected outstanding refcount %d, got %d.\n", mmstream_ref
, ref
);
5770 hr
= IAMMediaStream_GetMultiMediaStream(stream
, &mmstream2
);
5771 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5772 ok(mmstream2
== (IMultiMediaStream
*)mmstream
, "Expected mmstream %p, got %p.\n", mmstream
, mmstream2
);
5774 IMultiMediaStream_Release(mmstream2
);
5776 hr
= IAMMediaStream_JoinAMMultiMediaStream(stream
, NULL
);
5777 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5779 hr
= IAMMediaStream_GetMultiMediaStream(stream
, &mmstream2
);
5780 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5781 ok(mmstream2
== NULL
, "Got mmstream %p.\n", mmstream2
);
5783 ref
= IAMMediaStream_Release(stream
);
5784 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5785 ref
= IAMMultiMediaStream_Release(mmstream
);
5786 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5789 static void test_ammediastream_join_am_multi_media_stream(void)
5791 check_ammediastream_join_am_multi_media_stream(&CLSID_AMAudioStream
);
5792 check_ammediastream_join_am_multi_media_stream(&CLSID_AMDirectDrawStream
);
5795 static void check_ammediastream_join_filter(const CLSID
*clsid
)
5797 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
5798 IMediaStreamFilter
*filter
, *filter2
, *filter3
;
5799 IAMMediaStream
*stream
;
5803 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
5804 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5805 ok(!!filter
, "Expected non-null filter.\n");
5806 EXPECT_REF(filter
, 3);
5808 hr
= CoCreateInstance(clsid
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAMMediaStream
, (void **)&stream
);
5809 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5810 EXPECT_REF(filter
, 3);
5812 hr
= CoCreateInstance(&CLSID_MediaStreamFilter
, NULL
, CLSCTX_INPROC_SERVER
,
5813 &IID_IMediaStreamFilter
, (void **)&filter2
);
5814 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5815 EXPECT_REF(filter
, 3);
5816 EXPECT_REF(filter2
, 1);
5818 hr
= IAMMediaStream_JoinFilter(stream
, filter2
);
5819 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5820 EXPECT_REF(filter
, 3);
5821 EXPECT_REF(filter2
, 1);
5823 /* Crashes on native. */
5826 hr
= IAMMediaStream_JoinFilter(stream
, NULL
);
5827 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5830 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter3
);
5831 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5832 ok(filter3
== filter
, "Expected filter %p, got %p.\n", filter
, filter3
);
5833 EXPECT_REF(filter
, 4);
5835 IMediaStreamFilter_Release(filter3
);
5836 EXPECT_REF(filter
, 3);
5838 ref
= IMediaStreamFilter_Release(filter2
);
5839 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5840 ref
= IAMMediaStream_Release(stream
);
5841 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5842 EXPECT_REF(filter
, 3);
5843 ref
= IAMMultiMediaStream_Release(mmstream
);
5844 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5845 EXPECT_REF(filter
, 1);
5846 ref
= IMediaStreamFilter_Release(filter
);
5847 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5850 static void test_ammediastream_join_filter(void)
5852 check_ammediastream_join_filter(&CLSID_AMAudioStream
);
5853 check_ammediastream_join_filter(&CLSID_AMDirectDrawStream
);
5856 static void check_ammediastream_join_filter_graph(const MSPID
*id
)
5858 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
5859 IGraphBuilder
*builder
, *builder2
;
5860 IMediaStreamFilter
*filter
;
5861 IAMMediaStream
*stream
;
5862 IFilterGraph
*graph
;
5867 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
5868 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5869 ok(!!filter
, "Expected non-null filter.\n");
5871 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, id
, 0, (IMediaStream
**)&stream
);
5872 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5874 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &builder
);
5875 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5876 ok(!!builder
, "Expected non-null graph.\n");
5877 EXPECT_REF(builder
, 4);
5879 hr
= IMediaStreamFilter_QueryFilterInfo(filter
, &info
);
5880 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5881 ok(info
.pGraph
== (IFilterGraph
*)builder
, "Expected graph %p, got %p.\n", (IFilterGraph
*)builder
, info
.pGraph
);
5882 EXPECT_REF(builder
, 5);
5883 IFilterGraph_Release(info
.pGraph
);
5884 EXPECT_REF(builder
, 4);
5886 hr
= CoCreateInstance(&CLSID_FilterGraph
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IFilterGraph
, (void **)&graph
);
5887 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5888 EXPECT_REF(builder
, 4);
5889 EXPECT_REF(graph
, 1);
5891 /* Crashes on native. */
5894 hr
= IAMMediaStream_JoinFilterGraph(stream
, NULL
);
5895 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
5898 hr
= IAMMediaStream_JoinFilterGraph(stream
, graph
);
5899 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5900 EXPECT_REF(builder
, 4);
5901 EXPECT_REF(graph
, 1);
5903 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &builder2
);
5904 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5905 ok(builder2
== builder
, "Expected graph %p, got %p.\n", builder
, builder2
);
5906 EXPECT_REF(builder
, 5);
5907 EXPECT_REF(graph
, 1);
5908 IGraphBuilder_Release(builder2
);
5909 EXPECT_REF(builder
, 4);
5910 EXPECT_REF(graph
, 1);
5912 hr
= IMediaStreamFilter_QueryFilterInfo(filter
, &info
);
5913 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5914 ok(info
.pGraph
== (IFilterGraph
*)builder
, "Expected graph %p, got %p.\n", (IFilterGraph
*)builder
, info
.pGraph
);
5915 EXPECT_REF(builder
, 5);
5916 EXPECT_REF(graph
, 1);
5917 IFilterGraph_Release(info
.pGraph
);
5918 EXPECT_REF(builder
, 4);
5919 EXPECT_REF(graph
, 1);
5921 ref
= IFilterGraph_Release(graph
);
5922 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5923 ref
= IAMMultiMediaStream_Release(mmstream
);
5924 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5925 ref
= IGraphBuilder_Release(builder
);
5926 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5927 ref
= IMediaStreamFilter_Release(filter
);
5928 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5929 ref
= IAMMediaStream_Release(stream
);
5930 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5933 static void test_ammediastream_join_filter_graph(void)
5935 check_ammediastream_join_filter_graph(&MSPID_PrimaryAudio
);
5936 check_ammediastream_join_filter_graph(&MSPID_PrimaryVideo
);
5939 static void check_ammediastream_set_state(const MSPID
*id
)
5941 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
5942 IAMMediaStream
*am_stream
;
5943 IMediaStream
*stream
;
5947 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
5948 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5949 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, id
, 0, &stream
);
5950 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5951 hr
= IMediaStream_QueryInterface(stream
, &IID_IAMMediaStream
, (void **)&am_stream
);
5952 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5954 hr
= IAMMediaStream_SetState(am_stream
, 4);
5955 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5957 hr
= IAMMediaStream_SetState(am_stream
, State_Running
);
5958 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5960 hr
= IAMMediaStream_SetState(am_stream
, State_Paused
);
5961 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5963 hr
= IAMMediaStream_SetState(am_stream
, State_Stopped
);
5964 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5966 ref
= IAMMultiMediaStream_Release(mmstream
);
5967 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5968 IAMMediaStream_Release(am_stream
);
5969 ref
= IMediaStream_Release(stream
);
5970 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
5973 static void test_ammediastream_set_state(void)
5975 check_ammediastream_set_state(&MSPID_PrimaryAudio
);
5976 check_ammediastream_set_state(&MSPID_PrimaryVideo
);
5979 static void check_ammediastream_end_of_stream(const MSPID
*id
, const AM_MEDIA_TYPE
*mt
)
5981 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
5982 struct testfilter source
;
5983 IGraphBuilder
*graph
;
5984 IMediaStream
*stream
;
5989 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
5990 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5991 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, id
, 0, &stream
);
5992 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5993 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
5994 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5995 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
5996 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
5997 ok(!!graph
, "Expected non-NULL graph.\n");
5998 testfilter_init(&source
);
5999 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
6000 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6002 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, mt
);
6003 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6005 hr
= IPin_EndOfStream(pin
);
6006 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6008 hr
= IPin_EndOfStream(pin
);
6009 ok(hr
== E_FAIL
, "Got hr %#x.\n", hr
);
6011 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
6012 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6014 hr
= IPin_EndOfStream(pin
);
6015 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6017 hr
= IPin_EndOfStream(pin
);
6018 ok(hr
== E_FAIL
, "Got hr %#x.\n", hr
);
6020 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
6021 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6023 hr
= IPin_EndOfStream(pin
);
6024 ok(hr
== E_FAIL
, "Got hr %#x.\n", hr
);
6026 IGraphBuilder_Disconnect(graph
, pin
);
6027 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
6029 ref
= IAMMultiMediaStream_Release(mmstream
);
6030 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6031 ref
= IGraphBuilder_Release(graph
);
6032 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6034 ref
= IMediaStream_Release(stream
);
6035 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6038 static void test_ammediastream_end_of_stream(void)
6040 check_ammediastream_end_of_stream(&MSPID_PrimaryAudio
, &audio_mt
);
6041 check_ammediastream_end_of_stream(&MSPID_PrimaryVideo
, &rgb32_mt
);
6044 void test_mediastreamfilter_get_state(void)
6046 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
6047 IMediaStreamFilter
*filter
;
6052 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
6053 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6054 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
6055 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6056 ok(!!filter
, "Expected non-null filter.\n");
6058 /* Crashes on native. */
6061 hr
= IMediaStreamFilter_GetState(filter
, 0, NULL
);
6062 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
6066 hr
= IMediaStreamFilter_GetState(filter
, 0, &state
);
6067 ok(state
== State_Stopped
, "Got state %#x.\n", state
);
6069 ref
= IAMMultiMediaStream_Release(mmstream
);
6070 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6071 ref
= IMediaStreamFilter_Release(filter
);
6072 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6075 void check_mediastreamfilter_state(FILTER_STATE expected_state
, HRESULT (*set_state
)(IMediaStreamFilter
*),
6076 HRESULT (*reset_state
)(IMediaStreamFilter
*))
6078 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
6079 struct teststream teststream
, teststream2
;
6080 IMediaStreamFilter
*filter
;
6085 teststream_init(&teststream
);
6086 teststream_init(&teststream2
);
6088 teststream2
.mspid
.Data2
= 1;
6090 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
6091 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6092 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)&teststream
, &teststream
.mspid
, 0, NULL
);
6093 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6094 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)&teststream2
, &teststream2
.mspid
, 0, NULL
);
6095 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6096 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
6097 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6098 ok(filter
!= NULL
, "Expected non-null filter\n");
6100 hr
= reset_state(filter
);
6101 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6103 teststream
.state
= 0xcc;
6104 teststream2
.state
= 0xcc;
6105 hr
= set_state(filter
);
6106 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6107 ok(teststream
.state
== expected_state
, "Got state %#x.\n", teststream
.state
);
6108 ok(teststream2
.state
== expected_state
, "Got state %#x.\n", teststream2
.state
);
6109 hr
= IMediaStreamFilter_GetState(filter
, 0, &state
);
6110 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6111 ok(state
== expected_state
, "Got state %#x.\n", state
);
6113 teststream
.state
= 0xcc;
6114 teststream2
.state
= 0xcc;
6115 hr
= set_state(filter
);
6116 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6117 ok(teststream
.state
== 0xcc, "Got state %#x.\n", teststream
.state
);
6118 ok(teststream2
.state
== 0xcc, "Got state %#x.\n", teststream2
.state
);
6120 hr
= reset_state(filter
);
6121 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6123 teststream
.set_state_result
= E_FAIL
;
6124 teststream
.state
= 0xcc;
6125 teststream2
.state
= 0xcc;
6126 hr
= set_state(filter
);
6127 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6128 ok(teststream
.state
== 0xcc, "Got state %#x.\n", teststream
.state
);
6129 ok(teststream2
.state
== expected_state
, "Got state %#x.\n", teststream2
.state
);
6130 hr
= IMediaStreamFilter_GetState(filter
, 0, &state
);
6131 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6132 ok(state
== expected_state
, "Got state %#x.\n", state
);
6134 hr
= reset_state(filter
);
6135 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6137 teststream
.set_state_result
= E_FAIL
;
6138 teststream2
.set_state_result
= E_FAIL
;
6139 teststream
.state
= 0xcc;
6140 teststream2
.state
= 0xcc;
6141 hr
= set_state(filter
);
6142 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6143 ok(teststream
.state
== 0xcc, "Got state %#x.\n", teststream
.state
);
6144 ok(teststream2
.state
== 0xcc, "Got state %#x.\n", teststream2
.state
);
6145 hr
= IMediaStreamFilter_GetState(filter
, 0, &state
);
6146 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6147 ok(state
== expected_state
, "Got state %#x.\n", state
);
6149 ref
= IAMMultiMediaStream_Release(mmstream
);
6150 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6151 ref
= IMediaStreamFilter_Release(filter
);
6152 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6153 ok(teststream
.refcount
== 1, "Got outstanding refcount %d.\n", teststream
.refcount
);
6154 ok(teststream2
.refcount
== 1, "Got outstanding refcount %d.\n", teststream2
.refcount
);
6157 static HRESULT
mediastreamfilter_stop(IMediaStreamFilter
*filter
)
6159 return IMediaStreamFilter_Stop(filter
);
6162 static HRESULT
mediastreamfilter_pause(IMediaStreamFilter
*filter
)
6164 return IMediaStreamFilter_Pause(filter
);
6167 static HRESULT
mediastreamfilter_run(IMediaStreamFilter
*filter
)
6169 return IMediaStreamFilter_Run(filter
, 0);
6172 void test_mediastreamfilter_stop_pause_run(void)
6174 check_mediastreamfilter_state(State_Stopped
, mediastreamfilter_stop
, mediastreamfilter_run
);
6175 check_mediastreamfilter_state(State_Paused
, mediastreamfilter_pause
, mediastreamfilter_stop
);
6176 check_mediastreamfilter_state(State_Running
, mediastreamfilter_run
, mediastreamfilter_stop
);
6179 static void test_mediastreamfilter_support_seeking(void)
6181 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
6182 static const MSPID mspid1
= {0x88888888, 1};
6183 static const MSPID mspid2
= {0x88888888, 2};
6184 static const MSPID mspid3
= {0x88888888, 3};
6185 struct testfilter source1
, source2
, source3
;
6186 IAMMediaStream
*stream1
, *stream2
, *stream3
;
6187 IMediaStreamFilter
*filter
;
6188 IPin
*pin1
, *pin2
, *pin3
;
6189 ULONG ref
, seeking_ref
;
6190 IGraphBuilder
*graph
;
6193 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
6194 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6195 hr
= CoCreateInstance(&CLSID_AMAudioStream
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAMMediaStream
, (void **)&stream1
);
6196 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6197 hr
= CoCreateInstance(&CLSID_AMAudioStream
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAMMediaStream
, (void **)&stream2
);
6198 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6199 hr
= CoCreateInstance(&CLSID_AMAudioStream
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAMMediaStream
, (void **)&stream3
);
6200 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6201 hr
= IAMMediaStream_Initialize(stream1
, NULL
, 0, &mspid1
, STREAMTYPE_READ
);
6202 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6203 hr
= IAMMediaStream_Initialize(stream2
, NULL
, 0, &mspid2
, STREAMTYPE_READ
);
6204 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6205 hr
= IAMMediaStream_Initialize(stream3
, NULL
, 0, &mspid3
, STREAMTYPE_READ
);
6206 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6207 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)stream1
, &mspid1
, 0, NULL
);
6208 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6209 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)stream2
, &mspid2
, 0, NULL
);
6210 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6211 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)stream3
, &mspid3
, 0, NULL
);
6212 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6213 hr
= IAMMediaStream_QueryInterface(stream1
, &IID_IPin
, (void **)&pin1
);
6214 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6215 hr
= IAMMediaStream_QueryInterface(stream2
, &IID_IPin
, (void **)&pin2
);
6216 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6217 hr
= IAMMediaStream_QueryInterface(stream3
, &IID_IPin
, (void **)&pin3
);
6218 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6219 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
6220 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6221 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
6222 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6223 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
6224 testfilter_init(&source1
);
6225 testfilter_init(&source2
);
6226 testfilter_init(&source3
);
6227 source2
.IMediaSeeking_iface
.lpVtbl
= &testsource_seeking_vtbl
;
6228 source3
.IMediaSeeking_iface
.lpVtbl
= &testsource_seeking_vtbl
;
6229 hr
= IGraphBuilder_AddFilter(graph
, &source1
.filter
.IBaseFilter_iface
, NULL
);
6230 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6231 hr
= IGraphBuilder_AddFilter(graph
, &source2
.filter
.IBaseFilter_iface
, NULL
);
6232 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6233 hr
= IGraphBuilder_AddFilter(graph
, &source3
.filter
.IBaseFilter_iface
, NULL
);
6234 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6236 hr
= IMediaStreamFilter_SupportSeeking(filter
, TRUE
);
6237 ok(hr
== E_NOINTERFACE
, "Got hr %#x.\n", hr
);
6239 hr
= IGraphBuilder_ConnectDirect(graph
, &source1
.source
.pin
.IPin_iface
, pin1
, &audio_mt
);
6240 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6242 source2
.get_duration_hr
= E_FAIL
;
6244 hr
= IMediaStreamFilter_SupportSeeking(filter
, TRUE
);
6245 ok(hr
== E_NOINTERFACE
, "Got hr %#x.\n", hr
);
6247 hr
= IGraphBuilder_ConnectDirect(graph
, &source2
.source
.pin
.IPin_iface
, pin2
, &audio_mt
);
6248 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6250 hr
= IMediaStreamFilter_SupportSeeking(filter
, TRUE
);
6251 ok(hr
== E_NOINTERFACE
, "Got hr %#x.\n", hr
);
6253 hr
= IGraphBuilder_ConnectDirect(graph
, &source3
.source
.pin
.IPin_iface
, pin3
, &audio_mt
);
6254 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6256 check_interface(filter
, &IID_IMediaSeeking
, FALSE
);
6258 seeking_ref
= get_refcount(&source3
.IMediaSeeking_iface
);
6260 hr
= IMediaStreamFilter_SupportSeeking(filter
, TRUE
);
6261 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6263 check_interface(filter
, &IID_IMediaSeeking
, TRUE
);
6265 ref
= get_refcount(&source3
.IMediaSeeking_iface
);
6266 ok(ref
== seeking_ref
, "Expected outstanding refcount %d, got %d.\n", seeking_ref
, ref
);
6268 hr
= IMediaStreamFilter_SupportSeeking(filter
, TRUE
);
6269 ok(hr
== HRESULT_FROM_WIN32(ERROR_ALREADY_INITIALIZED
), "Got hr %#x.\n", hr
);
6271 IGraphBuilder_Disconnect(graph
, pin1
);
6272 IGraphBuilder_Disconnect(graph
, &source1
.source
.pin
.IPin_iface
);
6274 IGraphBuilder_Disconnect(graph
, pin2
);
6275 IGraphBuilder_Disconnect(graph
, &source2
.source
.pin
.IPin_iface
);
6277 IGraphBuilder_Disconnect(graph
, pin3
);
6278 IGraphBuilder_Disconnect(graph
, &source3
.source
.pin
.IPin_iface
);
6280 ref
= IAMMultiMediaStream_Release(mmstream
);
6281 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6282 ref
= IGraphBuilder_Release(graph
);
6283 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6284 ref
= IMediaStreamFilter_Release(filter
);
6285 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6287 ref
= IAMMediaStream_Release(stream1
);
6288 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6290 ref
= IAMMediaStream_Release(stream2
);
6291 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6293 ref
= IAMMediaStream_Release(stream3
);
6294 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6297 static void check_mediastreamfilter_seeking(void (*check
)(IMediaSeeking
*seeking
, struct testfilter
*source1
,
6298 struct testfilter
*source2
, struct testfilter
*source3
, HRESULT source2_hr
, HRESULT expected_hr
))
6300 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
6301 static const MSPID mspid1
= {0x88888888, 1};
6302 static const MSPID mspid2
= {0x88888888, 2};
6303 static const MSPID mspid3
= {0x88888888, 3};
6304 IMediaStreamFilter
*filter
;
6305 struct testfilter source1
;
6306 struct testfilter source2
;
6307 struct testfilter source3
;
6308 IAMMediaStream
*stream1
;
6309 IAMMediaStream
*stream2
;
6310 IAMMediaStream
*stream3
;
6311 IMediaSeeking
*seeking
;
6312 IGraphBuilder
*graph
;
6319 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
6320 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6321 hr
= CoCreateInstance(&CLSID_AMAudioStream
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAMMediaStream
, (void **)&stream1
);
6322 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6323 hr
= CoCreateInstance(&CLSID_AMAudioStream
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAMMediaStream
, (void **)&stream2
);
6324 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6325 hr
= CoCreateInstance(&CLSID_AMAudioStream
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAMMediaStream
, (void **)&stream3
);
6326 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6327 hr
= IAMMediaStream_Initialize(stream1
, NULL
, 0, &mspid1
, STREAMTYPE_READ
);
6328 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6329 hr
= IAMMediaStream_Initialize(stream2
, NULL
, 0, &mspid2
, STREAMTYPE_READ
);
6330 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6331 hr
= IAMMediaStream_Initialize(stream3
, NULL
, 0, &mspid3
, STREAMTYPE_READ
);
6332 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6333 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)stream1
, &mspid1
, 0, NULL
);
6334 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6335 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)stream2
, &mspid2
, 0, NULL
);
6336 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6337 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)stream3
, &mspid3
, 0, NULL
);
6338 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6339 hr
= IAMMediaStream_QueryInterface(stream1
, &IID_IPin
, (void **)&pin1
);
6340 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6341 hr
= IAMMediaStream_QueryInterface(stream2
, &IID_IPin
, (void **)&pin2
);
6342 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6343 hr
= IAMMediaStream_QueryInterface(stream3
, &IID_IPin
, (void **)&pin3
);
6344 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6345 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
6346 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6347 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
6348 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6349 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
6350 testfilter_init(&source1
);
6351 testfilter_init(&source2
);
6352 testfilter_init(&source3
);
6353 source1
.IMediaSeeking_iface
.lpVtbl
= &testsource_seeking_vtbl
;
6354 source2
.IMediaSeeking_iface
.lpVtbl
= &testsource_seeking_vtbl
;
6355 source3
.IMediaSeeking_iface
.lpVtbl
= &testsource_seeking_vtbl
;
6356 hr
= IGraphBuilder_AddFilter(graph
, &source1
.filter
.IBaseFilter_iface
, NULL
);
6357 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6358 hr
= IGraphBuilder_AddFilter(graph
, &source2
.filter
.IBaseFilter_iface
, NULL
);
6359 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6360 hr
= IGraphBuilder_AddFilter(graph
, &source3
.filter
.IBaseFilter_iface
, NULL
);
6361 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6363 hr
= IGraphBuilder_ConnectDirect(graph
, &source2
.source
.pin
.IPin_iface
, pin2
, &audio_mt
);
6364 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6365 hr
= IGraphBuilder_ConnectDirect(graph
, &source3
.source
.pin
.IPin_iface
, pin3
, &audio_mt
);
6366 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6368 hr
= IMediaStreamFilter_SupportSeeking(filter
, TRUE
);
6369 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6371 hr
= IGraphBuilder_ConnectDirect(graph
, &source1
.source
.pin
.IPin_iface
, pin1
, &audio_mt
);
6372 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6374 hr
= IMediaStreamFilter_QueryInterface(filter
, &IID_IMediaSeeking
, (void **)&seeking
);
6375 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6377 check(seeking
, &source1
, &source2
, &source3
, S_OK
, S_OK
);
6378 check(seeking
, &source1
, &source2
, &source3
, E_FAIL
, E_FAIL
);
6379 check(seeking
, &source1
, &source2
, &source3
, E_NOTIMPL
, E_NOTIMPL
);
6381 source2
.IMediaSeeking_iface
.lpVtbl
= NULL
;
6383 check(seeking
, &source1
, &source2
, &source3
, S_OK
, E_NOTIMPL
);
6385 source2
.IMediaSeeking_iface
.lpVtbl
= &testsource_seeking_vtbl
;
6387 IGraphBuilder_Disconnect(graph
, pin2
);
6388 IGraphBuilder_Disconnect(graph
, &source2
.source
.pin
.IPin_iface
);
6390 check(seeking
, &source1
, &source2
, &source3
, S_OK
, E_NOTIMPL
);
6392 IGraphBuilder_Disconnect(graph
, pin2
);
6393 IGraphBuilder_Disconnect(graph
, &source2
.source
.pin
.IPin_iface
);
6394 IGraphBuilder_Disconnect(graph
, pin3
);
6395 IGraphBuilder_Disconnect(graph
, &source3
.source
.pin
.IPin_iface
);
6397 ref
= IAMMultiMediaStream_Release(mmstream
);
6398 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6399 ref
= IGraphBuilder_Release(graph
);
6400 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6401 IMediaSeeking_Release(seeking
);
6402 ref
= IMediaStreamFilter_Release(filter
);
6403 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6405 ref
= IAMMediaStream_Release(stream1
);
6406 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6408 ref
= IAMMediaStream_Release(stream2
);
6409 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6411 ref
= IAMMediaStream_Release(stream3
);
6412 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6415 static void check_mediastreamfilter_set_positions(IMediaSeeking
*seeking
, struct testfilter
*source1
,
6416 struct testfilter
*source2
, struct testfilter
*source3
, HRESULT source2_hr
, HRESULT expected_hr
)
6418 LONGLONG current_position
= 12345678;
6419 LONGLONG stop_position
= 87654321;
6422 source2
->set_positions_hr
= source2_hr
;
6423 source1
->current_position
= 0xdeadbeefdeadbeefULL
;
6424 source1
->stop_position
= 0xdeadbeefdeadbeefULL
;
6425 source2
->current_position
= 0xdeadbeefdeadbeefULL
;
6426 source2
->stop_position
= 0xdeadbeefdeadbeefULL
;
6427 source3
->current_position
= 0xdeadbeefdeadbeefULL
;
6428 source3
->stop_position
= 0xdeadbeefdeadbeefULL
;
6429 hr
= IMediaSeeking_SetPositions(seeking
, ¤t_position
, AM_SEEKING_AbsolutePositioning
,
6430 &stop_position
, AM_SEEKING_AbsolutePositioning
);
6431 ok(hr
== expected_hr
, "Got hr %#x.\n", hr
);
6432 ok(source1
->current_position
== 0xdeadbeefdeadbeefULL
, "Got current position %s.\n",
6433 wine_dbgstr_longlong(source1
->current_position
));
6434 ok(source1
->stop_position
== 0xdeadbeefdeadbeefULL
, "Got stop position %s.\n",
6435 wine_dbgstr_longlong(source1
->stop_position
));
6436 if (SUCCEEDED(expected_hr
))
6438 ok(source2
->current_position
== 12345678, "Got current position %s.\n",
6439 wine_dbgstr_longlong(source2
->current_position
));
6440 ok(source2
->stop_position
== 87654321, "Got stop position %s.\n",
6441 wine_dbgstr_longlong(source2
->stop_position
));
6443 ok(source3
->current_position
== 0xdeadbeefdeadbeefULL
, "Got current position %s.\n",
6444 wine_dbgstr_longlong(source3
->current_position
));
6445 ok(source3
->stop_position
== 0xdeadbeefdeadbeefULL
, "Got stop position %s.\n",
6446 wine_dbgstr_longlong(source3
->stop_position
));
6449 static void check_mediastreamfilter_get_duration(IMediaSeeking
*seeking
, struct testfilter
*source1
,
6450 struct testfilter
*source2
, struct testfilter
*source3
, HRESULT source2_hr
, HRESULT expected_hr
)
6452 LONGLONG duration
= 0xdeadbeefdeadbeefULL
;
6455 source2
->get_duration_hr
= source2_hr
;
6456 hr
= IMediaSeeking_GetDuration(seeking
, &duration
);
6457 ok(hr
== expected_hr
, "Got hr %#x.\n", hr
);
6458 if (SUCCEEDED(expected_hr
))
6459 ok(duration
== 0x8000000000000000ULL
, "Got duration %s.\n", wine_dbgstr_longlong(duration
));
6461 ok(duration
== 0xdeadbeefdeadbeefULL
, "Got duration %s.\n", wine_dbgstr_longlong(duration
));
6464 static void check_mediastreamfilter_get_stop_position(IMediaSeeking
*seeking
, struct testfilter
*source1
,
6465 struct testfilter
*source2
, struct testfilter
*source3
, HRESULT source2_hr
, HRESULT expected_hr
)
6467 LONGLONG stop
= 0xdeadbeefdeadbeefULL
;
6470 source2
->get_stop_position_hr
= source2_hr
;
6471 hr
= IMediaSeeking_GetStopPosition(seeking
, &stop
);
6472 ok(hr
== expected_hr
, "Got hr %#x.\n", hr
);
6473 if (SUCCEEDED(expected_hr
))
6474 ok(stop
== 0x8000000000000000ULL
, "Got stop position %s.\n", wine_dbgstr_longlong(stop
));
6476 ok(stop
== 0xdeadbeefdeadbeefULL
, "Got stop position %s.\n", wine_dbgstr_longlong(stop
));
6479 static void check_mediastreamfilter_is_format_supported(IMediaSeeking
*seeking
, struct testfilter
*source1
,
6480 struct testfilter
*source2
, struct testfilter
*source3
, HRESULT source2_hr
, HRESULT expected_hr
)
6484 source2
->is_format_supported_hr
= source2_hr
;
6485 hr
= IMediaSeeking_IsFormatSupported(seeking
, &TIME_FORMAT_MEDIA_TIME
);
6486 ok(hr
== expected_hr
, "Got hr %#x.\n", hr
);
6489 static void test_mediastreamfilter_seeking(void)
6491 check_mediastreamfilter_seeking(check_mediastreamfilter_set_positions
);
6492 check_mediastreamfilter_seeking(check_mediastreamfilter_get_duration
);
6493 check_mediastreamfilter_seeking(check_mediastreamfilter_get_stop_position
);
6494 check_mediastreamfilter_seeking(check_mediastreamfilter_is_format_supported
);
6497 static void test_mediastreamfilter_get_current_stream_time(void)
6499 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
6500 STREAM_TIME filter_start_time
;
6501 IMediaStreamFilter
*filter
;
6502 IMediaFilter
*media_filter
;
6503 struct testclock clock
;
6504 IGraphBuilder
*graph
;
6509 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
6510 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6511 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
6512 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6513 ok(!!filter
, "Expected non-null filter.\n");
6514 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, NULL
);
6515 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6516 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
6517 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6518 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
6519 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaFilter
, (void **)&media_filter
);
6520 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6521 testclock_init(&clock
);
6523 /* Crashes on native. */
6526 hr
= IMediaStreamFilter_GetCurrentStreamTime(filter
, NULL
);
6527 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
6528 hr
= IAMMultiMediaStream_GetTime(mmstream
, NULL
);
6529 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
6532 time
= 0xdeadbeefdeadbeef;
6533 hr
= IMediaStreamFilter_GetCurrentStreamTime(filter
, &time
);
6534 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
6535 ok(time
== 0, "Got time %s.\n", wine_dbgstr_longlong(time
));
6536 time
= 0xdeadbeefdeadbeef;
6537 hr
= IAMMultiMediaStream_GetTime(mmstream
, &time
);
6538 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
6539 ok(time
== 0, "Got time %s.\n", wine_dbgstr_longlong(time
));
6541 hr
= IMediaFilter_SetSyncSource(media_filter
, &clock
.IReferenceClock_iface
);
6542 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6544 clock
.get_time_hr
= E_FAIL
;
6546 time
= 0xdeadbeefdeadbeef;
6547 hr
= IMediaStreamFilter_GetCurrentStreamTime(filter
, &time
);
6548 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
6549 ok(time
== 0, "Got time %s.\n", wine_dbgstr_longlong(time
));
6550 time
= 0xdeadbeefdeadbeef;
6551 hr
= IAMMultiMediaStream_GetTime(mmstream
, &time
);
6552 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
6553 ok(time
== 0, "Got time %s.\n", wine_dbgstr_longlong(time
));
6555 clock
.time
= 23456789;
6556 clock
.get_time_hr
= S_OK
;
6558 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
6559 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6561 hr
= IMediaStreamFilter_GetCurrentStreamTime(filter
, &filter_start_time
);
6562 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6564 clock
.time
= 34567890;
6566 time
= 0xdeadbeefdeadbeef;
6567 hr
= IMediaStreamFilter_GetCurrentStreamTime(filter
, &time
);
6568 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6569 ok(time
== 11111101 + filter_start_time
, "Got time %s.\n", wine_dbgstr_longlong(time
));
6570 time
= 0xdeadbeefdeadbeef;
6571 hr
= IAMMultiMediaStream_GetTime(mmstream
, &time
);
6572 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6573 ok(time
== 11111101 + filter_start_time
, "Got time %s.\n", wine_dbgstr_longlong(time
));
6575 ref
= IAMMultiMediaStream_Release(mmstream
);
6576 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6577 IMediaFilter_Release(media_filter
);
6578 ref
= IGraphBuilder_Release(graph
);
6579 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6580 ref
= IMediaStreamFilter_Release(filter
);
6581 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6584 static void test_mediastreamfilter_reference_time_to_stream_time(void)
6586 IMediaStreamFilter
*filter
;
6587 struct testclock clock
;
6588 REFERENCE_TIME time
;
6592 hr
= CoCreateInstance(&CLSID_MediaStreamFilter
, NULL
, CLSCTX_INPROC_SERVER
,
6593 &IID_IMediaStreamFilter
, (void **)&filter
);
6594 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6595 testclock_init(&clock
);
6597 hr
= IMediaStreamFilter_ReferenceTimeToStreamTime(filter
, NULL
);
6598 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
6600 time
= 0xdeadbeefdeadbeef;
6601 hr
= IMediaStreamFilter_ReferenceTimeToStreamTime(filter
, &time
);
6602 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
6603 ok(time
== 0xdeadbeefdeadbeef, "Got time %s.\n", wine_dbgstr_longlong(time
));
6605 hr
= IMediaStreamFilter_SetSyncSource(filter
, &clock
.IReferenceClock_iface
);
6606 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6608 clock
.get_time_hr
= E_FAIL
;
6610 /* Crashes on native. */
6613 hr
= IMediaStreamFilter_ReferenceTimeToStreamTime(filter
, NULL
);
6614 ok(hr
== S_FALSE
, "Got hr %#x.\n", hr
);
6617 time
= 0xdeadbeefdeadbeef;
6618 hr
= IMediaStreamFilter_ReferenceTimeToStreamTime(filter
, &time
);
6619 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6620 ok(time
== 0xdeadbeefdeadbeef, "Got time %s.\n", wine_dbgstr_longlong(time
));
6622 hr
= IMediaStreamFilter_Run(filter
, 23456789);
6623 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6625 time
= 0xdeadbeefdeadbeef;
6626 hr
= IMediaStreamFilter_ReferenceTimeToStreamTime(filter
, &time
);
6627 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6628 ok(time
== 0xdeadbeefdd47d2da, "Got time %s.\n", wine_dbgstr_longlong(time
));
6630 clock
.time
= 34567890;
6631 clock
.get_time_hr
= S_OK
;
6633 time
= 0xdeadbeefdeadbeef;
6634 hr
= IMediaStreamFilter_ReferenceTimeToStreamTime(filter
, &time
);
6635 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6636 ok(time
== 0xdeadbeefdd47d2da, "Got time %s.\n", wine_dbgstr_longlong(time
));
6638 ref
= IMediaStreamFilter_Release(filter
);
6639 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6642 struct mediastreamfilter_wait_until_params
6644 IMediaStreamFilter
*filter
;
6645 REFERENCE_TIME time
;
6646 HRESULT expected_hr
;
6649 static DWORD CALLBACK
mediastreamfilter_wait_until(void *p
)
6651 struct mediastreamfilter_wait_until_params
*params
= (struct mediastreamfilter_wait_until_params
*)p
;
6654 hr
= IMediaStreamFilter_WaitUntil(params
->filter
, params
->time
);
6655 ok(hr
== params
->expected_hr
, "Got hr %#x.\n", hr
);
6660 static void test_mediastreamfilter_wait_until(void)
6662 struct mediastreamfilter_wait_until_params params1
;
6663 struct mediastreamfilter_wait_until_params params2
;
6664 struct advise_time_cookie cookie1
= { 0 };
6665 struct advise_time_cookie cookie2
= { 0 };
6666 IMediaStreamFilter
*filter
;
6667 struct testclock clock
;
6673 hr
= CoCreateInstance(&CLSID_MediaStreamFilter
, NULL
, CLSCTX_INPROC_SERVER
,
6674 &IID_IMediaStreamFilter
, (void **)&filter
);
6675 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6676 testclock_init(&clock
);
6677 cookie1
.advise_time_called_event
= CreateEventW(NULL
, FALSE
, FALSE
, NULL
);
6678 cookie2
.advise_time_called_event
= CreateEventW(NULL
, FALSE
, FALSE
, NULL
);
6680 hr
= IMediaStreamFilter_Run(filter
, 12345678);
6681 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6683 hr
= IMediaStreamFilter_WaitUntil(filter
, 23456789);
6684 ok(hr
== E_FAIL
, "Got hr %#x.\n", hr
);
6686 hr
= IMediaStreamFilter_Stop(filter
);
6687 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6689 hr
= IMediaStreamFilter_SetSyncSource(filter
, &clock
.IReferenceClock_iface
);
6690 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6692 clock
.advise_time_cookie
= &cookie1
;
6694 params1
.filter
= filter
;
6695 params1
.time
= 23456789;
6696 params1
.expected_hr
= S_OK
;
6697 thread1
= CreateThread(NULL
, 0, mediastreamfilter_wait_until
, ¶ms1
, 0, NULL
);
6698 ok(!WaitForSingleObject(cookie1
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
6699 ok(WaitForSingleObject(thread1
, 100) == WAIT_TIMEOUT
, "WaitUntil returned prematurely.\n");
6701 ok(cookie1
.base
== 23456789, "Got base %s.\n", wine_dbgstr_longlong(cookie1
.base
));
6702 ok(cookie1
.offset
== 12345678, "Got offset %s.\n", wine_dbgstr_longlong(cookie1
.offset
));
6703 ok(!!cookie1
.event
, "Expected non-NULL event.\n");
6705 SetEvent(cookie1
.event
);
6707 ok(!WaitForSingleObject(thread1
, 2000), "Wait timed out.\n");
6708 CloseHandle(thread1
);
6710 ok(!cookie1
.unadvise_called
, "Unexpected Unadvise call.\n");
6712 hr
= IMediaStreamFilter_Run(filter
, 12345678);
6713 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6715 clock
.time
= 30000000;
6717 clock
.advise_time_cookie
= &cookie1
;
6719 params1
.filter
= filter
;
6720 params1
.time
= 23456789;
6721 params1
.expected_hr
= S_OK
;
6722 thread1
= CreateThread(NULL
, 0, mediastreamfilter_wait_until
, ¶ms1
, 0, NULL
);
6723 ok(!WaitForSingleObject(cookie1
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
6724 ok(WaitForSingleObject(thread1
, 100) == WAIT_TIMEOUT
, "WaitUntil returned prematurely.\n");
6726 ok(cookie1
.base
== 23456789, "Got base %s.\n", wine_dbgstr_longlong(cookie1
.base
));
6727 ok(cookie1
.offset
== 12345678, "Got offset %s.\n", wine_dbgstr_longlong(cookie1
.offset
));
6728 ok(!!cookie1
.event
, "Expected non-NULL event.\n");
6730 clock
.advise_time_cookie
= &cookie2
;
6732 params2
.filter
= filter
;
6733 params2
.time
= 11111111;
6734 params2
.expected_hr
= S_OK
;
6735 thread2
= CreateThread(NULL
, 0, mediastreamfilter_wait_until
, ¶ms2
, 0, NULL
);
6736 ok(!WaitForSingleObject(cookie2
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
6737 ok(WaitForSingleObject(thread2
, 100) == WAIT_TIMEOUT
, "WaitUntil returned prematurely.\n");
6739 ok(cookie2
.base
== 11111111, "Got base %s.\n", wine_dbgstr_longlong(cookie2
.base
));
6740 ok(cookie2
.offset
== 12345678, "Got offset %s.\n", wine_dbgstr_longlong(cookie2
.offset
));
6741 ok(!!cookie2
.event
, "Expected non-NULL event.\n");
6743 SetEvent(cookie1
.event
);
6745 ok(!WaitForSingleObject(thread1
, 2000), "Wait timed out.\n");
6746 CloseHandle(thread1
);
6748 ok(WaitForSingleObject(thread2
, 100) == WAIT_TIMEOUT
, "WaitUntil returned prematurely.\n");
6750 SetEvent(cookie2
.event
);
6752 ok(!WaitForSingleObject(thread2
, 2000), "Wait timed out.\n");
6753 CloseHandle(thread2
);
6755 clock
.advise_time_cookie
= &cookie1
;
6757 params1
.filter
= filter
;
6758 params1
.time
= 23456789;
6759 params1
.expected_hr
= S_FALSE
;
6760 thread1
= CreateThread(NULL
, 0, mediastreamfilter_wait_until
, ¶ms1
, 0, NULL
);
6761 ok(!WaitForSingleObject(cookie1
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
6762 ok(WaitForSingleObject(thread1
, 100) == WAIT_TIMEOUT
, "WaitUntil returned prematurely.\n");
6764 clock
.advise_time_cookie
= &cookie2
;
6766 params2
.filter
= filter
;
6767 params2
.time
= 23456789;
6768 params2
.expected_hr
= S_FALSE
;
6769 thread2
= CreateThread(NULL
, 0, mediastreamfilter_wait_until
, ¶ms2
, 0, NULL
);
6770 ok(!WaitForSingleObject(cookie2
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
6771 ok(WaitForSingleObject(thread2
, 100) == WAIT_TIMEOUT
, "WaitUntil returned prematurely.\n");
6773 hr
= IMediaStreamFilter_Flush(filter
, FALSE
);
6774 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6776 ok(cookie1
.unadvise_called
, "Expected Unadvise to be called.\n");
6777 ok(cookie2
.unadvise_called
, "Expected Unadvise to be called.\n");
6779 ok(!WaitForSingleObject(thread1
, 2000), "Wait timed out.\n");
6780 CloseHandle(thread1
);
6781 ok(!WaitForSingleObject(thread2
, 2000), "Wait timed out.\n");
6782 CloseHandle(thread2
);
6784 clock
.advise_time_cookie
= &cookie1
;
6786 params1
.filter
= filter
;
6787 params1
.time
= 23456789;
6788 params1
.expected_hr
= S_FALSE
;
6789 thread1
= CreateThread(NULL
, 0, mediastreamfilter_wait_until
, ¶ms1
, 0, NULL
);
6790 ok(!WaitForSingleObject(cookie1
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
6791 ok(WaitForSingleObject(thread1
, 100) == WAIT_TIMEOUT
, "WaitUntil returned prematurely.\n");
6793 clock
.advise_time_cookie
= &cookie2
;
6795 params2
.filter
= filter
;
6796 params2
.time
= 23456789;
6797 params2
.expected_hr
= S_FALSE
;
6798 thread2
= CreateThread(NULL
, 0, mediastreamfilter_wait_until
, ¶ms2
, 0, NULL
);
6799 ok(!WaitForSingleObject(cookie2
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
6800 ok(WaitForSingleObject(thread2
, 100) == WAIT_TIMEOUT
, "WaitUntil returned prematurely.\n");
6802 hr
= IMediaStreamFilter_Stop(filter
);
6803 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6805 ok(cookie1
.unadvise_called
, "Expected Unadvise to be called.\n");
6806 ok(cookie2
.unadvise_called
, "Expected Unadvise to be called.\n");
6808 ok(!WaitForSingleObject(thread1
, 2000), "Wait timed out.\n");
6809 CloseHandle(thread1
);
6810 ok(!WaitForSingleObject(thread2
, 2000), "Wait timed out.\n");
6811 CloseHandle(thread2
);
6813 CloseHandle(cookie1
.advise_time_called_event
);
6814 CloseHandle(cookie2
.advise_time_called_event
);
6816 ref
= IMediaStreamFilter_Release(filter
);
6817 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6820 static void test_ddrawstream_getsetdirectdraw(void)
6822 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
6823 IDirectDraw
*ddraw
, *ddraw2
, *ddraw3
, *ddraw4
;
6824 IDirectDrawMediaStream
*ddraw_stream
;
6825 IDirectDrawStreamSample
*sample
;
6826 IDirectDraw7
*ddraw7
;
6827 IMediaStream
*stream
;
6831 hr
= DirectDrawCreate(NULL
, &ddraw
, NULL
);
6832 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6833 hr
= IDirectDraw_QueryInterface(ddraw
, &IID_IDirectDraw7
, (void **)&ddraw7
);
6834 ok(hr
== DD_OK
, "Got hr %#x.\n", hr
);
6835 hr
= IDirectDraw7_SetCooperativeLevel(ddraw7
, GetDesktopWindow(), DDSCL_NORMAL
);
6836 ok(hr
== DD_OK
, "Got hr %#x.\n", hr
);
6837 EXPECT_REF(ddraw
, 1);
6838 EXPECT_REF(ddraw7
, 1);
6840 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
6841 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6843 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)ddraw7
, &MSPID_PrimaryVideo
, 0, &stream
);
6844 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6845 EXPECT_REF(ddraw
, 2);
6847 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
6848 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6850 hr
= IDirectDrawMediaStream_GetDirectDraw(ddraw_stream
, NULL
);
6851 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
6853 hr
= IDirectDrawMediaStream_GetDirectDraw(ddraw_stream
, &ddraw2
);
6854 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6855 ok(ddraw2
== ddraw
, "Expected ddraw %p, got %p.\n", ddraw
, ddraw2
);
6856 EXPECT_REF(ddraw
, 3);
6858 hr
= IDirectDrawMediaStream_GetDirectDraw(ddraw_stream
, &ddraw3
);
6859 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6860 ok(ddraw3
== ddraw2
, "Expected ddraw %p, got %p.\n", ddraw2
, ddraw3
);
6861 EXPECT_REF(ddraw
, 4);
6862 IDirectDraw_Release(ddraw3
);
6863 EXPECT_REF(ddraw
, 3);
6865 /* The current ddraw is released when SetDirectDraw() is called. */
6866 hr
= IDirectDrawMediaStream_SetDirectDraw(ddraw_stream
, NULL
);
6867 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6868 EXPECT_REF(ddraw
, 2);
6870 hr
= IDirectDrawMediaStream_GetDirectDraw(ddraw_stream
, &ddraw3
);
6871 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6872 ok(ddraw3
== NULL
, "Expected NULL, got %p.\n", ddraw3
);
6874 hr
= IDirectDrawMediaStream_SetDirectDraw(ddraw_stream
, ddraw2
);
6875 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6876 EXPECT_REF(ddraw
, 3);
6878 hr
= IDirectDrawMediaStream_GetDirectDraw(ddraw_stream
, &ddraw3
);
6879 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6880 ok(ddraw3
== ddraw2
, "Expected ddraw %p, got %p.\n", ddraw2
, ddraw3
);
6881 EXPECT_REF(ddraw
, 4);
6882 IDirectDraw_Release(ddraw3
);
6883 EXPECT_REF(ddraw
, 3);
6885 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, &sample
);
6886 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6888 /* SetDirectDraw() doesn't take an extra reference to the ddraw object
6889 * if there are samples extant. */
6890 hr
= IDirectDrawMediaStream_SetDirectDraw(ddraw_stream
, ddraw2
);
6891 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6892 EXPECT_REF(ddraw
, 3);
6894 hr
= DirectDrawCreate(NULL
, &ddraw3
, NULL
);
6895 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6896 hr
= IDirectDraw_SetCooperativeLevel(ddraw3
, GetDesktopWindow(), DDSCL_NORMAL
);
6897 ok(hr
== DD_OK
, "Got hr %#x.\n", hr
);
6898 EXPECT_REF(ddraw3
, 1);
6900 hr
= IDirectDrawMediaStream_SetDirectDraw(ddraw_stream
, ddraw3
);
6901 ok(hr
== MS_E_SAMPLEALLOC
, "Got hr %#x.\n", hr
);
6903 hr
= IDirectDrawMediaStream_GetDirectDraw(ddraw_stream
, &ddraw4
);
6904 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6905 ok(ddraw4
== ddraw2
, "Expected ddraw %p, got %p.\n", ddraw2
, ddraw4
);
6906 EXPECT_REF(ddraw
, 4);
6907 IDirectDraw_Release(ddraw4
);
6908 EXPECT_REF(ddraw
, 3);
6910 ref
= IDirectDrawStreamSample_Release(sample
);
6911 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6913 hr
= IDirectDrawMediaStream_SetDirectDraw(ddraw_stream
, ddraw3
);
6914 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6915 EXPECT_REF(ddraw
, 2);
6916 EXPECT_REF(ddraw3
, 2);
6918 hr
= IDirectDrawMediaStream_GetDirectDraw(ddraw_stream
, &ddraw4
);
6919 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6920 ok(ddraw4
== ddraw3
, "Expected ddraw %p, got %p.\n", ddraw3
, ddraw4
);
6921 EXPECT_REF(ddraw3
, 3);
6922 IDirectDraw_Release(ddraw4
);
6923 EXPECT_REF(ddraw3
, 2);
6925 hr
= IDirectDrawMediaStream_SetDirectDraw(ddraw_stream
, NULL
);
6926 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6927 EXPECT_REF(ddraw3
, 1);
6929 ref
= IDirectDraw_Release(ddraw3
);
6930 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6932 EXPECT_REF(stream
, 3);
6933 IDirectDrawMediaStream_Release(ddraw_stream
);
6934 EXPECT_REF(stream
, 2);
6935 ref
= IAMMultiMediaStream_Release(mmstream
);
6936 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6937 EXPECT_REF(stream
, 1);
6938 ref
= IMediaStream_Release(stream
);
6939 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6940 ref
= IDirectDraw7_Release(ddraw7
);
6941 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6942 IDirectDraw_Release(ddraw2
);
6943 EXPECT_REF(ddraw
, 1);
6944 ref
= IDirectDraw_Release(ddraw
);
6945 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6948 static void test_audiostreamsample_get_media_stream(void)
6950 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
6951 IAudioStreamSample
*audio_sample
;
6952 IAudioMediaStream
*audio_stream
;
6953 IMediaStream
*stream
, *stream2
;
6954 IAudioData
*audio_data
;
6958 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
6959 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6961 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
6962 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6964 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
6965 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6967 hr
= CoCreateInstance(&CLSID_AMAudioData
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAudioData
, (void **)&audio_data
);
6968 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6970 hr
= IAudioMediaStream_CreateSample(audio_stream
, audio_data
, 0, &audio_sample
);
6971 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6973 /* Crashes on native. */
6976 hr
= IAudioStreamSample_GetMediaStream(audio_sample
, NULL
);
6977 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
6980 EXPECT_REF(stream
, 4);
6981 hr
= IAudioStreamSample_GetMediaStream(audio_sample
, &stream2
);
6982 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
6983 ok(stream2
== stream
, "Expected stream %p, got %p.\n", stream
, stream2
);
6984 EXPECT_REF(stream
, 5);
6986 IMediaStream_Release(stream2
);
6988 IAudioMediaStream_Release(audio_stream
);
6989 ref
= IAudioStreamSample_Release(audio_sample
);
6990 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6991 ref
= IAudioData_Release(audio_data
);
6992 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6993 ref
= IAMMultiMediaStream_Release(mmstream
);
6994 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6995 ref
= IMediaStream_Release(stream
);
6996 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
6999 static void test_audiostreamsample_get_audio_data(void)
7001 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
7002 IAudioData
*audio_data
, *audio_data2
;
7003 IAudioStreamSample
*audio_sample
;
7004 IAudioMediaStream
*audio_stream
;
7005 IMediaStream
*stream
;
7009 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
7010 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7012 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryAudio
, 0, &stream
);
7013 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7015 hr
= IMediaStream_QueryInterface(stream
, &IID_IAudioMediaStream
, (void **)&audio_stream
);
7016 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7018 hr
= CoCreateInstance(&CLSID_AMAudioData
, NULL
, CLSCTX_INPROC_SERVER
, &IID_IAudioData
, (void **)&audio_data
);
7019 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7021 hr
= IAudioMediaStream_CreateSample(audio_stream
, audio_data
, 0, &audio_sample
);
7022 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7024 hr
= IAudioStreamSample_GetAudioData(audio_sample
, NULL
);
7025 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
7027 EXPECT_REF(audio_data
, 2);
7028 hr
= IAudioStreamSample_GetAudioData(audio_sample
, &audio_data2
);
7029 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7030 ok(audio_data2
== audio_data
, "Expected audio data %p, got %p.\n", audio_data
, audio_data2
);
7031 EXPECT_REF(audio_data
, 3);
7033 IAudioData_Release(audio_data2
);
7035 IAudioMediaStream_Release(audio_stream
);
7036 ref
= IAudioStreamSample_Release(audio_sample
);
7037 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7038 ref
= IAudioData_Release(audio_data
);
7039 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7040 ref
= IAMMultiMediaStream_Release(mmstream
);
7041 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7042 ref
= IMediaStream_Release(stream
);
7043 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7046 #define get_ddrawstream_create_sample_desc(a,b,c,d) get_ddrawstream_create_sample_desc_(__LINE__,a,b,c,d)
7047 static void get_ddrawstream_create_sample_desc_(int line
, const DDSURFACEDESC
*format1
,
7048 const DDSURFACEDESC
*format2
, const AM_MEDIA_TYPE
*mt
, DDSURFACEDESC
*desc
)
7050 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
7051 IDirectDrawMediaStream
*ddraw_stream
;
7052 IDirectDrawStreamSample
*sample
;
7053 IDirectDrawSurface
*surface
;
7054 struct testfilter source
;
7055 IGraphBuilder
*graph
;
7056 IMediaStream
*stream
;
7061 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
7062 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7063 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
7064 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7065 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
7066 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7067 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
7068 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7069 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
7070 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7072 testfilter_init(&source
);
7074 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
7075 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7079 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, format1
, NULL
);
7080 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7084 hr
= IDirectDrawMediaStream_SetFormat(ddraw_stream
, format2
, NULL
);
7085 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7089 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, mt
);
7090 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7092 hr
= IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
7093 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7094 hr
= IGraphBuilder_Disconnect(graph
, pin
);
7095 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7098 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, &sample
);
7099 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7101 hr
= IDirectDrawStreamSample_GetSurface(sample
, &surface
, NULL
);
7102 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7103 ok_(__FILE__
, line
)(!!surface
, "Expected non-NULL sufrace.\n");
7105 desc
->dwSize
= sizeof(*desc
);
7106 hr
= IDirectDrawSurface_GetSurfaceDesc(surface
, desc
);
7107 ok_(__FILE__
, line
)(hr
== S_OK
, "Got hr %#x.\n", hr
);
7109 ref
= IDirectDrawStreamSample_Release(sample
);
7110 ok_(__FILE__
, line
)(!ref
, "Got outstanding refcount %d.\n", ref
);
7111 ref
= IDirectDrawSurface_Release(surface
);
7112 ok_(__FILE__
, line
)(!ref
, "Got outstanding refcount %d.\n", ref
);
7113 ref
= IAMMultiMediaStream_Release(mmstream
);
7114 ok_(__FILE__
, line
)(!ref
, "Got outstanding refcount %d.\n", ref
);
7115 ref
= IGraphBuilder_Release(graph
);
7116 ok_(__FILE__
, line
)(!ref
, "Got outstanding refcount %d.\n", ref
);
7118 IDirectDrawMediaStream_Release(ddraw_stream
);
7119 ref
= IMediaStream_Release(stream
);
7120 ok_(__FILE__
, line
)(!ref
, "Got outstanding refcount %d.\n", ref
);
7123 static void test_ddrawstream_create_sample(void)
7125 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
7126 DDSURFACEDESC desc2
= { sizeof(desc2
) };
7127 IDirectDrawSurface
*surface
, *surface2
;
7128 DDSURFACEDESC desc
= { sizeof(desc
) };
7129 IDirectDrawMediaStream
*ddraw_stream
;
7130 IDirectDrawStreamSample
*sample
;
7131 DDSURFACEDESC format1
;
7132 DDSURFACEDESC format2
;
7133 IMediaStream
*stream
;
7139 hr
= DirectDrawCreate(NULL
, &ddraw
, NULL
);
7140 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7142 hr
= IDirectDraw_SetCooperativeLevel(ddraw
, NULL
, DDSCL_NORMAL
);
7143 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7145 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
7146 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7148 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)ddraw
, &MSPID_PrimaryVideo
, 0, &stream
);
7149 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7151 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
7152 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7154 /* Crashes on native. */
7157 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, NULL
);
7158 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
7161 SetRectEmpty(&rect
);
7162 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, &rect
, 0, &sample
);
7163 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
7165 EXPECT_REF(mmstream
, 1);
7166 EXPECT_REF(stream
, 3);
7167 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, &sample
);
7168 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7169 EXPECT_REF(mmstream
, 2);
7170 EXPECT_REF(stream
, 4);
7172 hr
= IDirectDrawStreamSample_GetSurface(sample
, NULL
, NULL
);
7173 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7175 hr
= IDirectDrawStreamSample_GetSurface(sample
, NULL
, &rect
);
7176 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7178 hr
= IDirectDrawStreamSample_GetSurface(sample
, &surface
, NULL
);
7179 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7180 ok(surface
!= NULL
, "Expected non-NULL surface.\n");
7181 IDirectDrawSurface_Release(surface
);
7184 hr
= IDirectDrawStreamSample_GetSurface(sample
, &surface
, &rect
);
7185 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7186 ok(surface
!= NULL
, "Expected non-NULL surface.\n");
7188 hr
= IDirectDrawSurface_GetSurfaceDesc(surface
, &desc
);
7189 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7190 ok(desc
.dwWidth
== 100, "Expected width 100, got %d.\n", desc
.dwWidth
);
7191 ok(desc
.dwHeight
== 100, "Expected height 100, got %d.\n", desc
.dwHeight
);
7192 ok(desc
.ddpfPixelFormat
.dwFlags
== DDPF_RGB
, "Expected format flags DDPF_RGB, got %#x.\n", desc
.ddpfPixelFormat
.dwFlags
);
7193 ok(desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
, "Expected non-zero RGB bit count.\n");
7194 IDirectDrawSurface_Release(surface
);
7195 IDirectDrawStreamSample_Release(sample
);
7196 EXPECT_REF(stream
, 3);
7198 memset(&desc
, 0, sizeof(desc
));
7199 desc
.dwSize
= sizeof(desc
);
7200 desc
.dwFlags
= DDSD_CAPS
;
7201 desc
.ddsCaps
.dwCaps
= DDSCAPS_PRIMARYSURFACE
;
7202 hr
= IDirectDraw_CreateSurface(ddraw
, &desc
, &surface
, NULL
);
7203 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7205 EXPECT_REF(surface
, 1);
7206 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, surface
, NULL
, 0, &sample
);
7207 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7208 EXPECT_REF(surface
, 2);
7211 SetRectEmpty(&rect
);
7212 hr
= IDirectDrawStreamSample_GetSurface(sample
, &surface2
, &rect
);
7213 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7214 ok(surface2
== surface
, "Expected surface %p, got %p.\n", surface
, surface2
);
7215 ok(rect
.right
> 0 && rect
.bottom
> 0, "Got rect %d, %d.\n", rect
.right
, rect
.bottom
);
7216 EXPECT_REF(surface
, 3);
7217 IDirectDrawSurface_Release(surface2
);
7218 EXPECT_REF(surface
, 2);
7219 IDirectDrawStreamSample_Release(sample
);
7220 EXPECT_REF(surface
, 1);
7222 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, surface
, &rect
, 0, &sample
);
7223 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7225 ref
= IDirectDrawStreamSample_Release(sample
);
7226 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7227 ref
= IDirectDrawSurface_Release(surface
);
7228 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7230 memset(&desc
, 0, sizeof(desc
));
7231 desc
.dwSize
= sizeof(desc
);
7232 desc
.dwFlags
= DDSD_WIDTH
| DDSD_HEIGHT
| DDSD_PIXELFORMAT
| DDSD_CAPS
;
7234 desc
.dwHeight
= 400;
7235 desc
.ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
);
7236 desc
.ddpfPixelFormat
.dwFlags
= DDPF_RGB
| DDPF_ALPHAPIXELS
;
7237 desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
= 32;
7238 desc
.ddpfPixelFormat
.u2
.dwRBitMask
= 0xff0000;
7239 desc
.ddpfPixelFormat
.u3
.dwGBitMask
= 0x00ff00;
7240 desc
.ddpfPixelFormat
.u4
.dwBBitMask
= 0x0000ff;
7241 desc
.ddpfPixelFormat
.u5
.dwRGBAlphaBitMask
= 0xff000000;
7242 desc
.ddsCaps
.dwCaps
= DDSCAPS_SYSTEMMEMORY
| DDSCAPS_OFFSCREENPLAIN
;
7243 hr
= IDirectDraw_CreateSurface(ddraw
, &desc
, &surface
, NULL
);
7244 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7246 SetRect(&rect
, 111, 100, 333, 300);
7248 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, surface
, &rect
, 0, &sample
);
7249 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7250 ref
= IDirectDrawStreamSample_Release(sample
);
7251 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7253 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, &sample
);
7254 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7256 hr
= IDirectDrawStreamSample_GetSurface(sample
, &surface2
, &rect
);
7257 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7259 hr
= IDirectDrawSurface_GetSurfaceDesc(surface
, &desc
);
7260 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7261 hr
= IDirectDrawSurface_GetSurfaceDesc(surface2
, &desc2
);
7262 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7263 ok(desc2
.dwWidth
== 222, "Got width %u.\n", desc2
.dwWidth
);
7264 ok(desc2
.dwHeight
== 200, "Got height %u.\n", desc2
.dwHeight
);
7265 ok(memcmp(&desc2
.ddpfPixelFormat
, &desc
.ddpfPixelFormat
, sizeof(DDPIXELFORMAT
)) == 0,
7266 "Pixel format didn't match.\n");
7268 ref
= IDirectDrawStreamSample_Release(sample
);
7269 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7270 ref
= IDirectDrawSurface_Release(surface
);
7271 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7272 ref
= IDirectDrawSurface_Release(surface2
);
7273 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7275 memset(&desc
, 0, sizeof(desc
));
7276 desc
.dwSize
= sizeof(desc
);
7277 desc
.dwFlags
= DDSD_WIDTH
| DDSD_HEIGHT
| DDSD_PIXELFORMAT
| DDSD_CAPS
;
7279 desc
.dwHeight
= 400;
7280 desc
.ddpfPixelFormat
.dwSize
= sizeof(DDPIXELFORMAT
);
7281 desc
.ddpfPixelFormat
.dwFlags
= DDPF_RGB
| DDPF_PALETTEINDEXED4
;
7282 desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
= 4;
7283 desc
.ddsCaps
.dwCaps
= DDSCAPS_SYSTEMMEMORY
| DDSCAPS_OFFSCREENPLAIN
;
7284 hr
= IDirectDraw_CreateSurface(ddraw
, &desc
, &surface
, NULL
);
7285 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7287 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, surface
, NULL
, 0, &sample
);
7288 ok(hr
== DDERR_INVALIDSURFACETYPE
, "Got hr %#x.\n", hr
);
7290 IDirectDrawMediaStream_Release(ddraw_stream
);
7291 ref
= IDirectDrawSurface_Release(surface
);
7292 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7293 ref
= IAMMultiMediaStream_Release(mmstream
);
7294 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7295 ref
= IMediaStream_Release(stream
);
7296 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7297 ref
= IDirectDraw_Release(ddraw
);
7298 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7300 format1
= rgb8_format
;
7301 format1
.dwFlags
= 0;
7302 format1
.dwWidth
= 333;
7303 format1
.dwHeight
= 444;
7304 get_ddrawstream_create_sample_desc(&format1
, NULL
, NULL
, &desc
);
7305 ok(desc
.dwWidth
== 100, "Got width %u.\n", desc
.dwWidth
);
7306 ok(desc
.dwHeight
== 100, "Got height %u.\n", desc
.dwHeight
);
7307 ok(desc
.ddpfPixelFormat
.dwFlags
== DDPF_RGB
, "Got flags %#x.\n", desc
.ddpfPixelFormat
.dwFlags
);
7308 ok(desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
== 32, "Got rgb bit count %u.\n", desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
);
7309 ok(desc
.ddpfPixelFormat
.u2
.dwRBitMask
== 0xff0000, "Got r bit mask %#x.\n", desc
.ddpfPixelFormat
.u2
.dwRBitMask
);
7310 ok(desc
.ddpfPixelFormat
.u3
.dwGBitMask
== 0x00ff00, "Got g bit mask %#x.\n", desc
.ddpfPixelFormat
.u3
.dwGBitMask
);
7311 ok(desc
.ddpfPixelFormat
.u4
.dwBBitMask
== 0x0000ff, "Got b bit mask %#x.\n", desc
.ddpfPixelFormat
.u4
.dwBBitMask
);
7313 format1
= rgb8_format
;
7314 format1
.dwFlags
|= DDSD_WIDTH
;
7315 format1
.dwWidth
= 333;
7316 format1
.dwHeight
= 444;
7317 format2
= rgb8_format
;
7318 format2
.dwFlags
= 0;
7319 get_ddrawstream_create_sample_desc(&format1
, &format2
, NULL
, &desc
);
7320 ok(desc
.dwWidth
== 333, "Got width %u.\n", desc
.dwWidth
);
7321 ok(desc
.dwHeight
== 444, "Got height %u.\n", desc
.dwHeight
);
7323 format1
= rgb8_format
;
7324 format1
.dwFlags
|= DDSD_HEIGHT
;
7325 format1
.dwWidth
= 333;
7326 format1
.dwHeight
= 444;
7327 format2
= rgb8_format
;
7328 format2
.dwFlags
= 0;
7329 get_ddrawstream_create_sample_desc(&format1
, &format2
, NULL
, &desc
);
7330 ok(desc
.dwWidth
== 333, "Got width %u.\n", desc
.dwWidth
);
7331 ok(desc
.dwHeight
== 444, "Got height %u.\n", desc
.dwHeight
);
7333 get_ddrawstream_create_sample_desc(NULL
, NULL
, &rgb8_mt
, &desc
);
7334 ok(desc
.dwWidth
== 333, "Got width %u.\n", desc
.dwWidth
);
7335 ok(desc
.dwHeight
== 444, "Got height %u.\n", desc
.dwHeight
);
7336 ok(desc
.ddpfPixelFormat
.dwFlags
== DDPF_RGB
, "Got flags %#x.\n", desc
.ddpfPixelFormat
.dwFlags
);
7337 ok(desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
== 32, "Got rgb bit count %u.\n", desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
);
7338 ok(desc
.ddpfPixelFormat
.u2
.dwRBitMask
== 0xff0000, "Got r bit mask %#x.\n", desc
.ddpfPixelFormat
.u2
.dwRBitMask
);
7339 ok(desc
.ddpfPixelFormat
.u3
.dwGBitMask
== 0x00ff00, "Got g bit mask %#x.\n", desc
.ddpfPixelFormat
.u3
.dwGBitMask
);
7340 ok(desc
.ddpfPixelFormat
.u4
.dwBBitMask
== 0x0000ff, "Got b bit mask %#x.\n", desc
.ddpfPixelFormat
.u4
.dwBBitMask
);
7342 get_ddrawstream_create_sample_desc(&rgb565_format
, NULL
, NULL
, &desc
);
7343 ok(desc
.dwWidth
== 100, "Got width %u.\n", desc
.dwWidth
);
7344 ok(desc
.dwHeight
== 100, "Got height %u.\n", desc
.dwHeight
);
7345 ok(desc
.ddpfPixelFormat
.dwFlags
== DDPF_RGB
, "Got flags %#x.\n", desc
.ddpfPixelFormat
.dwFlags
);
7346 ok(desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
== 16, "Got rgb bit count %u.\n", desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
);
7347 ok(desc
.ddpfPixelFormat
.u2
.dwRBitMask
== 0xf800, "Got r bit mask %#x.\n", desc
.ddpfPixelFormat
.u2
.dwRBitMask
);
7348 ok(desc
.ddpfPixelFormat
.u3
.dwGBitMask
== 0x07e0, "Got g bit mask %#x.\n", desc
.ddpfPixelFormat
.u3
.dwGBitMask
);
7349 ok(desc
.ddpfPixelFormat
.u4
.dwBBitMask
== 0x001f, "Got b bit mask %#x.\n", desc
.ddpfPixelFormat
.u4
.dwBBitMask
);
7351 get_ddrawstream_create_sample_desc(&argb32_format
, NULL
, NULL
, &desc
);
7352 ok(desc
.dwWidth
== 100, "Got width %u.\n", desc
.dwWidth
);
7353 ok(desc
.dwHeight
== 100, "Got height %u.\n", desc
.dwHeight
);
7354 ok(desc
.ddpfPixelFormat
.dwFlags
== (DDPF_RGB
| DDPF_ALPHAPIXELS
), "Got flags %#x.\n", desc
.ddpfPixelFormat
.dwFlags
);
7355 ok(desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
== 32, "Got rgb bit count %u.\n", desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
);
7356 ok(desc
.ddpfPixelFormat
.u2
.dwRBitMask
== 0xff0000, "Got r bit mask %#x.\n", desc
.ddpfPixelFormat
.u2
.dwRBitMask
);
7357 ok(desc
.ddpfPixelFormat
.u3
.dwGBitMask
== 0x00ff00, "Got g bit mask %#x.\n", desc
.ddpfPixelFormat
.u3
.dwGBitMask
);
7358 ok(desc
.ddpfPixelFormat
.u4
.dwBBitMask
== 0x0000ff, "Got b bit mask %#x.\n", desc
.ddpfPixelFormat
.u4
.dwBBitMask
);
7359 ok(desc
.ddpfPixelFormat
.u5
.dwRGBAlphaBitMask
== 0xff000000,
7360 "Got alpha bit mask %#x.\n", desc
.ddpfPixelFormat
.u4
.dwBBitMask
);
7362 format1
= rgb32_format
;
7363 format1
.dwFlags
|= DDSD_CAPS
;
7364 format1
.ddsCaps
.dwCaps
= DDSCAPS_OFFSCREENPLAIN
| DDSCAPS_VIDEOMEMORY
;
7365 get_ddrawstream_create_sample_desc(&format1
, NULL
, NULL
, &desc
);
7366 ok(desc
.ddsCaps
.dwCaps
& DDSCAPS_OFFSCREENPLAIN
, "Expected set DDSCAPS_OFFSCREENPLAIN.\n");
7367 ok(desc
.ddsCaps
.dwCaps
& DDSCAPS_SYSTEMMEMORY
, "Expected set DDSCAPS_SYSTEMMEMORY.\n");
7368 ok(!(desc
.ddsCaps
.dwCaps
& DDSCAPS_VIDEOMEMORY
), "Expected unset DDSCAPS_VIDEOMEMORY.\n");
7369 ok(desc
.dwWidth
== 100, "Got width %u.\n", desc
.dwWidth
);
7370 ok(desc
.dwHeight
== 100, "Got height %u.\n", desc
.dwHeight
);
7371 ok(desc
.ddpfPixelFormat
.dwFlags
== DDPF_RGB
, "Got flags %#x.\n", desc
.ddpfPixelFormat
.dwFlags
);
7372 ok(desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
== 32, "Got rgb bit count %u.\n", desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
);
7373 ok(desc
.ddpfPixelFormat
.u2
.dwRBitMask
== 0xff0000, "Got r bit mask %#x.\n", desc
.ddpfPixelFormat
.u2
.dwRBitMask
);
7374 ok(desc
.ddpfPixelFormat
.u3
.dwGBitMask
== 0x00ff00, "Got g bit mask %#x.\n", desc
.ddpfPixelFormat
.u3
.dwGBitMask
);
7375 ok(desc
.ddpfPixelFormat
.u4
.dwBBitMask
== 0x0000ff, "Got b bit mask %#x.\n", desc
.ddpfPixelFormat
.u4
.dwBBitMask
);
7377 format1
= rgb32_format
;
7378 format1
.dwFlags
|= DDSD_CKSRCBLT
;
7379 format1
.ddckCKSrcBlt
.dwColorSpaceLowValue
= 0xff00ff;
7380 format1
.ddckCKSrcBlt
.dwColorSpaceHighValue
= 0xff00ff;
7381 get_ddrawstream_create_sample_desc(&format1
, NULL
, NULL
, &desc
);
7382 ok(!(desc
.dwFlags
& DDSD_CKSRCBLT
), "Expected unset DDSD_CKSRCBLT.\n");
7383 ok(desc
.dwWidth
== 100, "Got width %u.\n", desc
.dwWidth
);
7384 ok(desc
.dwHeight
== 100, "Got height %u.\n", desc
.dwHeight
);
7385 ok(desc
.ddpfPixelFormat
.dwFlags
== DDPF_RGB
, "Got flags %#x.\n", desc
.ddpfPixelFormat
.dwFlags
);
7386 ok(desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
== 32, "Got rgb bit count %u.\n", desc
.ddpfPixelFormat
.u1
.dwRGBBitCount
);
7387 ok(desc
.ddpfPixelFormat
.u2
.dwRBitMask
== 0xff0000, "Got r bit mask %#x.\n", desc
.ddpfPixelFormat
.u2
.dwRBitMask
);
7388 ok(desc
.ddpfPixelFormat
.u3
.dwGBitMask
== 0x00ff00, "Got g bit mask %#x.\n", desc
.ddpfPixelFormat
.u3
.dwGBitMask
);
7389 ok(desc
.ddpfPixelFormat
.u4
.dwBBitMask
== 0x0000ff, "Got b bit mask %#x.\n", desc
.ddpfPixelFormat
.u4
.dwBBitMask
);
7390 ok(desc
.ddckCKSrcBlt
.dwColorSpaceLowValue
== 0, "Got color key low value %#x.\n",
7391 desc
.ddckCKSrcBlt
.dwColorSpaceLowValue
);
7392 ok(desc
.ddckCKSrcBlt
.dwColorSpaceHighValue
== 0, "Got color key high value %#x.\n",
7393 desc
.ddckCKSrcBlt
.dwColorSpaceHighValue
);
7396 static void test_ddrawstreamsample_get_media_stream(void)
7398 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
7399 IDirectDrawMediaStream
*ddraw_stream
;
7400 IDirectDrawStreamSample
*sample
;
7401 IMediaStream
*stream
, *stream2
;
7406 hr
= DirectDrawCreate(NULL
, &ddraw
, NULL
);
7407 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7409 hr
= IDirectDraw_SetCooperativeLevel(ddraw
, NULL
, DDSCL_NORMAL
);
7410 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7412 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
7413 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7415 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, (IUnknown
*)ddraw
, &MSPID_PrimaryVideo
, 0, &stream
);
7416 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7418 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
7419 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7421 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, &sample
);
7422 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7424 /* Crashes on native. */
7427 hr
= IDirectDrawStreamSample_GetMediaStream(sample
, NULL
);
7428 ok(hr
== E_POINTER
, "Got hr %#x.\n", hr
);
7431 EXPECT_REF(stream
, 4);
7432 hr
= IDirectDrawStreamSample_GetMediaStream(sample
, &stream2
);
7433 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7434 ok(stream2
== stream
, "Expected stream %p, got %p.\n", stream
, stream2
);
7435 EXPECT_REF(stream
, 5);
7436 IMediaStream_Release(stream2
);
7437 EXPECT_REF(stream
, 4);
7439 IDirectDrawMediaStream_Release(ddraw_stream
);
7440 ref
= IDirectDrawStreamSample_Release(sample
);
7441 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7442 ref
= IAMMultiMediaStream_Release(mmstream
);
7443 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7444 ref
= IMediaStream_Release(stream
);
7445 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7446 ref
= IDirectDraw_Release(ddraw
);
7447 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7450 static void test_ddrawstreamsample_update(void)
7452 static const BYTE initial_data
[] =
7454 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef,
7456 static const BYTE test_data
[] =
7458 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11,
7459 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23,
7461 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
7462 IDirectDrawStreamSample
*stream_sample
;
7463 struct advise_time_cookie cookie
= {0};
7464 IDirectDrawMediaStream
*ddraw_stream
;
7465 IMediaControl
*media_control
;
7466 IDirectDrawSurface
*surface
;
7467 IMemInputPin
*mem_input_pin
;
7468 IMediaSample
*media_sample
;
7469 IMediaFilter
*media_filter
;
7470 REFERENCE_TIME start_time
;
7471 REFERENCE_TIME end_time
;
7472 struct testfilter source
;
7473 struct testclock clock
;
7474 IGraphBuilder
*graph
;
7475 IMediaStream
*stream
;
7476 VIDEOINFO video_info
;
7488 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
7489 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7490 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
7491 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7492 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
7493 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7494 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
7495 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7496 hr
= IMediaStream_QueryInterface(stream
, &IID_IMemInputPin
, (void **)&mem_input_pin
);
7497 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7498 hr
= IDirectDrawMediaStream_GetDirectDraw(ddraw_stream
, &ddraw
);
7499 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7500 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
7501 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7502 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
7503 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaControl
, (void **)&media_control
);
7504 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7505 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaFilter
, (void **)&media_filter
);
7506 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7507 testfilter_init(&source
);
7508 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
7509 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7510 testclock_init(&clock
);
7511 event
= CreateEventW(NULL
, FALSE
, FALSE
, NULL
);
7512 ok(event
!= NULL
, "Expected non-NULL event.");
7513 cookie
.advise_time_called_event
= CreateEventW(NULL
, FALSE
, FALSE
, NULL
);
7514 ok(cookie
.advise_time_called_event
!= NULL
, "Expected non-NULL event.");
7516 hr
= IMediaFilter_SetSyncSource(media_filter
, NULL
);
7517 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7519 desc
= rgb24_format
;
7520 desc
.dwFlags
|= DDSD_WIDTH
| DDSD_HEIGHT
| DDSD_CAPS
;
7523 desc
.ddsCaps
.dwCaps
= DDSCAPS_SYSTEMMEMORY
| DDSCAPS_OFFSCREENPLAIN
;
7524 hr
= IDirectDraw_CreateSurface(ddraw
, &desc
, &surface
, NULL
);
7525 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7526 /* Make the rect width equal to the surface width, as the native
7527 * implementation incorrectly handles rects that are not full-width
7528 * when the ddraw stream's custom allocator is not used. */
7529 SetRect(&rect
, 0, 1, 4, 3);
7530 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, surface
, &rect
, 0, &stream_sample
);
7531 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7533 hr
= IDirectDrawStreamSample_Update(stream_sample
, 0, event
, apc_func
, 0);
7534 ok(hr
== E_INVALIDARG
, "Got hr %#x.\n", hr
);
7536 hr
= IDirectDrawStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
7537 ok(hr
== MS_E_NOTRUNNING
, "Got hr %#x.\n", hr
);
7539 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
7540 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7542 hr
= IDirectDrawStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
7543 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
7545 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
7546 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7547 video_info
= rgb24_video_info
;
7548 video_info
.bmiHeader
.biWidth
= 4;
7549 video_info
.bmiHeader
.biHeight
= -2;
7551 mt
.pbFormat
= (BYTE
*)&video_info
;
7552 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
7553 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7555 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
7556 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7558 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7559 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7560 for (i
= 0; i
< 5; ++i
)
7561 memcpy((BYTE
*)desc
.lpSurface
+ i
* desc
.u1
.lPitch
, initial_data
, 12);
7562 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7563 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7565 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
7567 ammediastream_mem_input_pin
= mem_input_pin
;
7568 ammediastream_media_sample
= media_sample
;
7569 ammediastream_sleep_time
= 0;
7570 ammediastream_expected_hr
= S_OK
;
7571 thread
= CreateThread(NULL
, 0, ammediastream_receive
, NULL
, 0, NULL
);
7574 hr
= IDirectDrawStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
7575 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7576 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7577 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7578 ok(memcmp((BYTE
*)desc
.lpSurface
+ 0 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7579 ok(memcmp((BYTE
*)desc
.lpSurface
+ 1 * desc
.u1
.lPitch
, &test_data
[0], 12) == 0, "Sample data didn't match.\n");
7580 ok(memcmp((BYTE
*)desc
.lpSurface
+ 2 * desc
.u1
.lPitch
, &test_data
[12], 12) == 0, "Sample data didn't match.\n");
7581 ok(memcmp((BYTE
*)desc
.lpSurface
+ 3 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7582 ok(memcmp((BYTE
*)desc
.lpSurface
+ 4 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7583 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7584 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7586 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
7587 CloseHandle(thread
);
7589 ref
= IMediaSample_Release(media_sample
);
7590 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7592 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
7593 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7594 IGraphBuilder_Disconnect(graph
, pin
);
7595 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
7596 video_info
= rgb24_video_info
;
7597 video_info
.bmiHeader
.biWidth
= 4;
7598 video_info
.bmiHeader
.biHeight
= 2;
7600 mt
.pbFormat
= (BYTE
*)&video_info
;
7601 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
7602 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7603 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
7604 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7606 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7607 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7608 for (i
= 0; i
< 5; ++i
)
7609 memcpy((BYTE
*)desc
.lpSurface
+ i
* desc
.u1
.lPitch
, initial_data
, 12);
7610 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7611 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7613 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
7615 ammediastream_mem_input_pin
= mem_input_pin
;
7616 ammediastream_media_sample
= media_sample
;
7617 ammediastream_sleep_time
= 0;
7618 ammediastream_expected_hr
= S_OK
;
7619 thread
= CreateThread(NULL
, 0, ammediastream_receive
, NULL
, 0, NULL
);
7622 hr
= IDirectDrawStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
7623 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7624 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7625 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7626 ok(memcmp((BYTE
*)desc
.lpSurface
+ 0 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7627 ok(memcmp((BYTE
*)desc
.lpSurface
+ 1 * desc
.u1
.lPitch
, &test_data
[12], 12) == 0, "Sample data didn't match.\n");
7628 ok(memcmp((BYTE
*)desc
.lpSurface
+ 2 * desc
.u1
.lPitch
, &test_data
[0], 12) == 0, "Sample data didn't match.\n");
7629 ok(memcmp((BYTE
*)desc
.lpSurface
+ 3 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7630 ok(memcmp((BYTE
*)desc
.lpSurface
+ 4 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7631 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7632 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7634 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
7635 CloseHandle(thread
);
7637 ref
= IMediaSample_Release(media_sample
);
7638 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7640 hr
= IPin_EndOfStream(pin
);
7641 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7643 hr
= IDirectDrawStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
7644 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
7646 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
7647 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7648 hr
= IMediaControl_Pause(media_control
);
7649 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7651 hr
= IDirectDrawStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
7652 ok(hr
== MS_E_NOTRUNNING
, "Got hr %#x.\n", hr
);
7654 hr
= IMediaControl_Stop(media_control
);
7655 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7656 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
7657 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7659 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7660 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7661 for (i
= 0; i
< 5; ++i
)
7662 memcpy((BYTE
*)desc
.lpSurface
+ i
* desc
.u1
.lPitch
, initial_data
, 12);
7663 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7664 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7666 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
7668 ammediastream_mem_input_pin
= mem_input_pin
;
7669 ammediastream_media_sample
= media_sample
;
7670 ammediastream_sleep_time
= 100;
7671 ammediastream_expected_hr
= S_OK
;
7672 thread
= CreateThread(NULL
, 0, ammediastream_receive
, NULL
, 0, NULL
);
7674 hr
= IDirectDrawStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
7675 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7676 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7677 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7678 ok(memcmp((BYTE
*)desc
.lpSurface
+ 0 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7679 ok(memcmp((BYTE
*)desc
.lpSurface
+ 1 * desc
.u1
.lPitch
, &test_data
[12], 12) == 0, "Sample data didn't match.\n");
7680 ok(memcmp((BYTE
*)desc
.lpSurface
+ 2 * desc
.u1
.lPitch
, &test_data
[0], 12) == 0, "Sample data didn't match.\n");
7681 ok(memcmp((BYTE
*)desc
.lpSurface
+ 3 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7682 ok(memcmp((BYTE
*)desc
.lpSurface
+ 4 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7683 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7684 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7686 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
7687 CloseHandle(thread
);
7689 ref
= IMediaSample_Release(media_sample
);
7690 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7692 ammediastream_pin
= pin
;
7693 ammediastream_sleep_time
= 100;
7694 ammediastream_expected_hr
= S_OK
;
7695 thread
= CreateThread(NULL
, 0, ammediastream_end_of_stream
, NULL
, 0, NULL
);
7697 hr
= IDirectDrawStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
7698 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
7700 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
7701 CloseHandle(thread
);
7703 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
7704 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7705 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
7706 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7708 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7709 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7710 for (i
= 0; i
< 5; ++i
)
7711 memcpy((BYTE
*)desc
.lpSurface
+ i
* desc
.u1
.lPitch
, initial_data
, 12);
7712 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7713 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7715 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
7717 ammediastream_mem_input_pin
= mem_input_pin
;
7718 ammediastream_media_sample
= media_sample
;
7719 ammediastream_sleep_time
= 100;
7720 ammediastream_expected_hr
= S_OK
;
7721 thread
= CreateThread(NULL
, 0, ammediastream_receive
, NULL
, 0, NULL
);
7723 hr
= IDirectDrawStreamSample_Update(stream_sample
, SSUPDATE_CONTINUOUS
, NULL
, NULL
, 0);
7724 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7725 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7726 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7727 ok(memcmp((BYTE
*)desc
.lpSurface
+ 0 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7728 ok(memcmp((BYTE
*)desc
.lpSurface
+ 1 * desc
.u1
.lPitch
, &test_data
[12], 12) == 0, "Sample data didn't match.\n");
7729 ok(memcmp((BYTE
*)desc
.lpSurface
+ 2 * desc
.u1
.lPitch
, &test_data
[0], 12) == 0, "Sample data didn't match.\n");
7730 ok(memcmp((BYTE
*)desc
.lpSurface
+ 3 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7731 ok(memcmp((BYTE
*)desc
.lpSurface
+ 4 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7732 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7733 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7735 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
7736 CloseHandle(thread
);
7738 ref
= IMediaSample_Release(media_sample
);
7739 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7741 hr
= IDirectDrawStreamSample_Update(stream_sample
, SSUPDATE_ASYNC
| SSUPDATE_CONTINUOUS
, NULL
, NULL
, 0);
7742 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
7744 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7745 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7746 for (i
= 0; i
< 5; ++i
)
7747 memcpy((BYTE
*)desc
.lpSurface
+ i
* desc
.u1
.lPitch
, initial_data
, 12);
7748 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7749 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7751 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
7752 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
7753 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7754 ref
= IMediaSample_Release(media_sample
);
7755 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7757 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7758 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7759 ok(memcmp((BYTE
*)desc
.lpSurface
+ 0 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7760 ok(memcmp((BYTE
*)desc
.lpSurface
+ 1 * desc
.u1
.lPitch
, &test_data
[12], 12) == 0, "Sample data didn't match.\n");
7761 ok(memcmp((BYTE
*)desc
.lpSurface
+ 2 * desc
.u1
.lPitch
, &test_data
[0], 12) == 0, "Sample data didn't match.\n");
7762 ok(memcmp((BYTE
*)desc
.lpSurface
+ 3 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7763 ok(memcmp((BYTE
*)desc
.lpSurface
+ 4 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7764 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7765 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7767 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7768 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7769 for (i
= 0; i
< 5; ++i
)
7770 memcpy((BYTE
*)desc
.lpSurface
+ i
* desc
.u1
.lPitch
, initial_data
, 12);
7771 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7772 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7774 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
7775 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
7776 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7777 ref
= IMediaSample_Release(media_sample
);
7778 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7780 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7781 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7782 ok(memcmp((BYTE
*)desc
.lpSurface
+ 0 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7783 ok(memcmp((BYTE
*)desc
.lpSurface
+ 1 * desc
.u1
.lPitch
, &test_data
[12], 12) == 0, "Sample data didn't match.\n");
7784 ok(memcmp((BYTE
*)desc
.lpSurface
+ 2 * desc
.u1
.lPitch
, &test_data
[0], 12) == 0, "Sample data didn't match.\n");
7785 ok(memcmp((BYTE
*)desc
.lpSurface
+ 3 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7786 ok(memcmp((BYTE
*)desc
.lpSurface
+ 4 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7787 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7788 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7790 hr
= IPin_EndOfStream(pin
);
7791 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7793 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
7794 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7795 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
7796 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7798 hr
= IDirectDrawStreamSample_Update(stream_sample
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
7799 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
7800 EXPECT_REF(stream_sample
, 1);
7802 hr
= IDirectDrawStreamSample_Update(stream_sample
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
7803 ok(hr
== MS_E_BUSY
, "Got hr %#x.\n", hr
);
7805 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
7806 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7807 hr
= IMediaFilter_SetSyncSource(media_filter
, &clock
.IReferenceClock_iface
);
7808 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7809 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
7810 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7812 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7813 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7814 for (i
= 0; i
< 5; ++i
)
7815 memcpy((BYTE
*)desc
.lpSurface
+ i
* desc
.u1
.lPitch
, initial_data
, 12);
7816 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7817 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7819 hr
= IDirectDrawStreamSample_Update(stream_sample
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
7820 ok(hr
== MS_E_BUSY
, "Got hr %#x.\n", hr
);
7822 clock
.advise_time_cookie
= &cookie
;
7824 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
7825 start_time
= 11111111;
7826 end_time
= 11111111;
7827 hr
= IMediaSample_SetTime(media_sample
, &start_time
, &end_time
);
7828 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7830 ammediastream_mem_input_pin
= mem_input_pin
;
7831 ammediastream_media_sample
= media_sample
;
7832 ammediastream_sleep_time
= 0;
7833 ammediastream_expected_hr
= S_OK
;
7834 thread
= CreateThread(NULL
, 0, ammediastream_receive
, NULL
, 0, NULL
);
7835 ok(!WaitForSingleObject(cookie
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
7836 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
7838 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7839 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7840 for (i
= 0; i
< 5; ++i
)
7841 ok(memcmp((BYTE
*)desc
.lpSurface
+ i
* desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7842 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7843 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7845 SetEvent(cookie
.event
);
7847 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
7848 CloseHandle(thread
);
7850 hr
= IDirectDrawSurface_Lock(surface
, NULL
, &desc
, 0, NULL
);
7851 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7852 ok(memcmp((BYTE
*)desc
.lpSurface
+ 0 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7853 ok(memcmp((BYTE
*)desc
.lpSurface
+ 1 * desc
.u1
.lPitch
, &test_data
[12], 12) == 0, "Sample data didn't match.\n");
7854 ok(memcmp((BYTE
*)desc
.lpSurface
+ 2 * desc
.u1
.lPitch
, &test_data
[0], 12) == 0, "Sample data didn't match.\n");
7855 ok(memcmp((BYTE
*)desc
.lpSurface
+ 3 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7856 ok(memcmp((BYTE
*)desc
.lpSurface
+ 4 * desc
.u1
.lPitch
, initial_data
, 12) == 0, "Sample data didn't match.\n");
7857 hr
= IDirectDrawSurface_Unlock(surface
, desc
.lpSurface
);
7858 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7860 ref
= IMediaSample_Release(media_sample
);
7861 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7863 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
7864 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7865 IGraphBuilder_Disconnect(graph
, pin
);
7866 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
7867 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
7868 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7870 hr
= IDirectDrawStreamSample_Update(stream_sample
, 0, NULL
, NULL
, 0);
7871 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
7873 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
7874 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7876 CloseHandle(cookie
.advise_time_called_event
);
7878 ref
= IDirectDrawStreamSample_Release(stream_sample
);
7879 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7880 ref
= IDirectDrawSurface_Release(surface
);
7881 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7882 ref
= IAMMultiMediaStream_Release(mmstream
);
7883 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7884 IMediaControl_Release(media_control
);
7885 IMediaFilter_Release(media_filter
);
7886 ref
= IGraphBuilder_Release(graph
);
7887 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7889 IMemInputPin_Release(mem_input_pin
);
7890 IDirectDrawMediaStream_Release(ddraw_stream
);
7891 ref
= IMediaStream_Release(stream
);
7892 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7893 ref
= IDirectDraw_Release(ddraw
);
7894 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7897 static void test_ddrawstreamsample_completion_status(void)
7899 static const BYTE test_data
[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11 };
7900 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
7901 struct advise_time_cookie cookie
= { 0 };
7902 IDirectDrawStreamSample
*stream_sample1
;
7903 IDirectDrawStreamSample
*stream_sample2
;
7904 IDirectDrawMediaStream
*ddraw_stream
;
7905 STREAM_TIME filter_start_time
;
7906 IMediaStreamFilter
*filter
;
7907 IMediaSample
*media_sample
;
7908 IMediaFilter
*media_filter
;
7909 struct testfilter source
;
7910 struct testclock clock
;
7911 VIDEOINFO video_info
;
7912 IGraphBuilder
*graph
;
7913 IMediaStream
*stream
;
7920 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
7921 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7922 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
7923 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7924 ok(!!filter
, "Expected non-null filter.\n");
7925 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
7926 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7927 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
7928 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7929 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
7930 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7931 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
7932 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7933 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
7934 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaFilter
, (void **)&media_filter
);
7935 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7936 testfilter_init(&source
);
7937 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
7938 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7939 testclock_init(&clock
);
7940 cookie
.advise_time_called_event
= CreateEventW(NULL
, FALSE
, FALSE
, NULL
);
7942 hr
= IMediaFilter_SetSyncSource(media_filter
, NULL
);
7943 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7945 video_info
= rgb32_video_info
;
7946 video_info
.bmiHeader
.biWidth
= 3;
7947 video_info
.bmiHeader
.biHeight
= 1;
7949 mt
.pbFormat
= (BYTE
*)&video_info
;
7950 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
7951 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7952 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
7953 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7955 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, &stream_sample1
);
7956 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7957 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, &stream_sample2
);
7958 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7960 /* Initial status is S_OK. */
7961 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
7962 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7964 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_WAIT
, INFINITE
);
7965 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7967 /* Update changes the status to MS_S_PENDING. */
7968 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
7969 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
7971 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
7972 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
7974 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_WAIT
, 100);
7975 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
7977 /* Each Receive call changes the status of one queued sample to S_OK in the same order Update was called. */
7978 hr
= IDirectDrawStreamSample_Update(stream_sample2
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
7979 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
7981 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample2
, 0, 0);
7982 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
7984 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
7985 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
7986 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7987 ref
= IMediaSample_Release(media_sample
);
7988 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
7990 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
7991 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7993 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_WAIT
, INFINITE
);
7994 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
7996 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample2
, 0, 0);
7997 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
7999 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
8000 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
8001 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8002 ref
= IMediaSample_Release(media_sample
);
8003 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8005 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample2
, 0, 0);
8006 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8008 /* COMPSTAT_NOUPDATEOK removes the sample from the queue and changes the status to MS_S_NOUPDATE. */
8009 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8010 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8012 hr
= IDirectDrawStreamSample_Update(stream_sample2
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8013 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8015 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_NOUPDATEOK
, 0);
8016 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8018 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_WAIT
, INFINITE
);
8019 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8021 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
8022 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
8023 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8024 ref
= IMediaSample_Release(media_sample
);
8025 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8027 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8028 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8030 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample2
, 0, 0);
8031 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8033 /* COMPSTAT_ABORT removes the sample from the queue and changes the status to MS_S_NOUPDATE. */
8034 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8035 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8037 hr
= IDirectDrawStreamSample_Update(stream_sample2
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8038 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8040 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_ABORT
, 0);
8041 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8043 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_WAIT
, INFINITE
);
8044 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8046 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
8047 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
8048 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8049 ref
= IMediaSample_Release(media_sample
);
8050 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8052 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8053 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8055 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample2
, 0, 0);
8056 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8058 /* COMPSTAT_WAIT has no effect when combined with COMPSTAT_NOUPDATEOK. */
8059 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8060 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8062 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_NOUPDATEOK
| COMPSTAT_WAIT
, INFINITE
);
8063 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8065 /* COMPSTAT_WAIT has no effect when combined with COMPSTAT_ABORT. */
8066 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8067 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8069 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_ABORT
| COMPSTAT_WAIT
, INFINITE
);
8070 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8072 /* EndOfStream changes the status of the queued samples to MS_S_ENDOFSTREAM. */
8073 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8074 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8076 hr
= IPin_EndOfStream(pin
);
8077 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8079 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8080 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
8082 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_WAIT
, INFINITE
);
8083 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
8085 /* Update after EndOfStream changes the status to MS_S_ENDOFSTREAM. */
8086 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8087 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
8089 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8090 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
8092 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_WAIT
, INFINITE
);
8093 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
8095 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
8096 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8097 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
8098 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8100 /* Continuous update can be canceled by COMPSTAT_NOUPDATEOK. */
8101 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
| SSUPDATE_CONTINUOUS
, NULL
, NULL
, 0);
8102 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8104 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_NOUPDATEOK
, 0);
8105 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8107 /* Continuous update can be canceled by COMPSTAT_ABORT. */
8108 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
| SSUPDATE_CONTINUOUS
, NULL
, NULL
, 0);
8109 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8111 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_ABORT
, 0);
8112 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8114 /* If a sample is in countinuous update mode, when Receive is called it's status remains MS_S_PENDING
8115 * and the sample is moved to the end of the queue. */
8116 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
| SSUPDATE_CONTINUOUS
, NULL
, NULL
, 0);
8117 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8119 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
| SSUPDATE_CONTINUOUS
, NULL
, NULL
, 0);
8120 ok(hr
== MS_E_BUSY
, "Got hr %#x.\n", hr
);
8122 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8123 ok(hr
== MS_E_BUSY
, "Got hr %#x.\n", hr
);
8125 hr
= IDirectDrawStreamSample_Update(stream_sample2
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8126 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8128 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8129 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8131 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
8132 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
8133 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8134 ref
= IMediaSample_Release(media_sample
);
8135 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8137 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8138 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8140 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample2
, 0, 0);
8141 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8143 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
8144 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
8145 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8146 ref
= IMediaSample_Release(media_sample
);
8147 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8149 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8150 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8152 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample2
, 0, 0);
8153 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8155 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_NOUPDATEOK
, 0);
8156 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8158 /* In continuous update mode, flushing does not affect the status. */
8159 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
| SSUPDATE_CONTINUOUS
, NULL
, NULL
, 0);
8160 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8162 hr
= IPin_BeginFlush(pin
);
8163 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8165 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8166 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8168 hr
= IPin_EndFlush(pin
);
8169 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8171 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8172 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8174 /* In continuous update mode, stopping and running the stream does not affect the status. */
8175 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
8176 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8178 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8179 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8181 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
8182 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8184 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8185 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8187 /* In continuous update mode, EndOfStream changes the status to MS_S_ENDOFSTREAM. */
8188 hr
= IPin_EndOfStream(pin
);
8189 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8191 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8192 ok(hr
== MS_S_ENDOFSTREAM
, "Got hr %#x.\n", hr
);
8194 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
8195 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8196 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
8197 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8199 /* COMPSTAT_WAIT resets the sample to the non-continuous update mode. */
8200 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
| SSUPDATE_CONTINUOUS
, NULL
, NULL
, 0);
8201 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8203 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_WAIT
, 0);
8204 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8206 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
8207 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
8208 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8209 ref
= IMediaSample_Release(media_sample
);
8210 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8212 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8213 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8215 /* In continuous update mode, CompletionStatus with COMPSTAT_WAIT returns when Receive is called. */
8216 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
| SSUPDATE_CONTINUOUS
, NULL
, NULL
, 0);
8217 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8219 streamsample_sample
= (IStreamSample
*)stream_sample1
;
8220 streamsample_flags
= COMPSTAT_WAIT
;
8221 streamsample_timeout
= INFINITE
;
8222 streamsample_expected_hr
= S_OK
;
8223 thread
= CreateThread(NULL
, 0, streamsample_completion_status
, NULL
, 0, NULL
);
8224 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "CompletionStatus returned prematurely.\n");
8226 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
8227 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
8228 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8229 ref
= IMediaSample_Release(media_sample
);
8230 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8232 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
8233 CloseHandle(thread
);
8235 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8236 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8238 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
8239 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8240 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
8241 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8243 /* CompletionStatus with COMPSTAT_WAIT returns when Receive is called. */
8244 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8245 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8247 streamsample_sample
= (IStreamSample
*)stream_sample1
;
8248 streamsample_flags
= COMPSTAT_WAIT
;
8249 streamsample_timeout
= INFINITE
;
8250 streamsample_expected_hr
= S_OK
;
8251 thread
= CreateThread(NULL
, 0, streamsample_completion_status
, NULL
, 0, NULL
);
8252 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "CompletionStatus returned prematurely.\n");
8254 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
8255 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
8256 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8257 ref
= IMediaSample_Release(media_sample
);
8258 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8260 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
8261 CloseHandle(thread
);
8263 /* CompletionStatus with COMPSTAT_WAIT returns when EndOfStream is called. */
8264 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8265 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8267 streamsample_sample
= (IStreamSample
*)stream_sample1
;
8268 streamsample_flags
= COMPSTAT_WAIT
;
8269 streamsample_timeout
= INFINITE
;
8270 streamsample_expected_hr
= MS_S_ENDOFSTREAM
;
8271 thread
= CreateThread(NULL
, 0, streamsample_completion_status
, NULL
, 0, NULL
);
8272 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "CompletionStatus returned prematurely.\n");
8274 hr
= IPin_EndOfStream(pin
);
8275 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8277 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
8278 CloseHandle(thread
);
8280 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
8281 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8282 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
8283 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8285 /* Stopping and running the stream does not affect the status and does not remove the sample from the queue. */
8286 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8287 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8289 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
8290 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8292 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8293 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8295 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
8296 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8298 media_sample
= ammediastream_allocate_sample(&source
, test_data
, 6);
8299 hr
= IMemInputPin_Receive(source
.source
.pMemInputPin
, media_sample
);
8300 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8301 ref
= IMediaSample_Release(media_sample
);
8302 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8304 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8305 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8307 /* When the stream is stopped Update does not change the status. */
8308 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
8309 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8311 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8312 ok(hr
== MS_E_NOTRUNNING
, "Got hr %#x.\n", hr
);
8314 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8315 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8317 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_WAIT
, INFINITE
);
8318 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8320 /* When the wait time is less than 1ms the sample is updated immediately. */
8321 hr
= IMediaFilter_SetSyncSource(media_filter
, &clock
.IReferenceClock_iface
);
8322 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8324 clock
.time
= 12345678;
8326 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
8327 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8329 hr
= IMediaStreamFilter_GetCurrentStreamTime(filter
, &filter_start_time
);
8330 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8332 clock
.time
= 12345678 - filter_start_time
+ 11111111;
8334 clock
.advise_time_cookie
= &cookie
;
8336 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8337 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8339 thread
= ammediastream_async_receive_time(&source
,
8340 11111111 + 9999, 11111111 + 9999, test_data
, sizeof(test_data
));
8341 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
8342 CloseHandle(thread
);
8344 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, INFINITE
);
8345 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8347 /* When the wait time is 1ms or greater AdviseTime is called
8348 * with base equal to the sample start time and offset equal to the filter start time. */
8349 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8350 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8352 thread
= ammediastream_async_receive_time(&source
,
8353 11111111 + 10000, 11111111 + 10000, test_data
, sizeof(test_data
));
8354 ok(!WaitForSingleObject(cookie
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
8355 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
8357 ok(cookie
.base
== 11111111 + 10000, "Got base %s.\n", wine_dbgstr_longlong(cookie
.base
));
8358 ok(cookie
.offset
== 12345678 - filter_start_time
, "Got offset %s.\n", wine_dbgstr_longlong(cookie
.offset
));
8360 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8361 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8363 clock
.time
= 12345678 - filter_start_time
+ 11111111 + 10000;
8364 SetEvent(cookie
.event
);
8366 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
8367 CloseHandle(thread
);
8369 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8370 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8372 /* NewSegment does not affect the values passed to AdviseTime. */
8373 hr
= IPin_NewSegment(pin
, 22222222, 33333333, 1.0);
8374 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8376 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8377 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8379 thread
= ammediastream_async_receive_time(&source
,
8380 11111111 + 20000, 11111111 + 20000, test_data
, sizeof(test_data
));
8381 ok(!WaitForSingleObject(cookie
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
8382 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
8384 ok(cookie
.base
== 11111111 + 20000, "Got base %s.\n", wine_dbgstr_longlong(cookie
.base
));
8385 ok(cookie
.offset
== 12345678 - filter_start_time
, "Got offset %s.\n", wine_dbgstr_longlong(cookie
.offset
));
8387 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_NOUPDATEOK
, 0);
8388 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8390 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
8392 clock
.time
= 12345678 - filter_start_time
+ 11111111 + 20000;
8393 SetEvent(cookie
.event
);
8395 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
8397 /* COMPSTAT_NOUPDATEOK does not cause Receive to return.
8398 * Receive waits for the next sample to be queued and updates it. */
8399 hr
= IDirectDrawStreamSample_Update(stream_sample1
, 0, NULL
, NULL
, 0);
8400 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8402 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
8403 CloseHandle(thread
);
8405 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8406 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8408 thread
= ammediastream_async_receive_time(&source
,
8409 11111111 + 30000, 11111111 + 30000, test_data
, sizeof(test_data
));
8410 ok(!WaitForSingleObject(cookie
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
8411 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
8413 ok(cookie
.base
== 11111111 + 30000, "Got base %s.\n", wine_dbgstr_longlong(cookie
.base
));
8414 ok(cookie
.offset
== 12345678 - filter_start_time
, "Got offset %s.\n", wine_dbgstr_longlong(cookie
.offset
));
8416 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_NOUPDATEOK
| COMPSTAT_WAIT
, INFINITE
);
8417 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8419 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
8421 clock
.time
= 12345678 - filter_start_time
+ 11111111 + 30000;
8422 SetEvent(cookie
.event
);
8424 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
8426 hr
= IDirectDrawStreamSample_Update(stream_sample1
, 0, NULL
, NULL
, 0);
8427 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8429 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
8430 CloseHandle(thread
);
8432 /* COMPSTAT_ABORT does not cause Receive to return.
8433 * Receive waits for the next sample to be queued and updates it. */
8434 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8435 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8437 thread
= ammediastream_async_receive_time(&source
,
8438 11111111 + 40000, 11111111 + 40000, test_data
, sizeof(test_data
));
8439 ok(!WaitForSingleObject(cookie
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
8440 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
8442 ok(cookie
.base
== 11111111 + 40000, "Got base %s.\n", wine_dbgstr_longlong(cookie
.base
));
8443 ok(cookie
.offset
== 12345678 - filter_start_time
, "Got offset %s.\n", wine_dbgstr_longlong(cookie
.offset
));
8445 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, COMPSTAT_ABORT
, 0);
8446 ok(hr
== MS_S_NOUPDATE
, "Got hr %#x.\n", hr
);
8448 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
8450 clock
.time
= 12345678 - filter_start_time
+ 11111111 + 40000;
8451 SetEvent(cookie
.event
);
8453 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
8455 hr
= IDirectDrawStreamSample_Update(stream_sample1
, 0, NULL
, NULL
, 0);
8456 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8458 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
8459 CloseHandle(thread
);
8461 /* Stopping the stream causes Receive to return and leaves the sample with MS_S_PENDING status. */
8462 hr
= IDirectDrawStreamSample_Update(stream_sample1
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8463 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8465 thread
= ammediastream_async_receive_time(&source
,
8466 11111111 + 50000, 11111111 + 50000, test_data
, sizeof(test_data
));
8467 ok(!WaitForSingleObject(cookie
.advise_time_called_event
, 2000), "Expected AdviseTime to be called.\n");
8468 ok(WaitForSingleObject(thread
, 100) == WAIT_TIMEOUT
, "Receive returned prematurely.\n");
8470 ok(cookie
.base
== 11111111 + 50000, "Got base %s.\n", wine_dbgstr_longlong(cookie
.base
));
8471 ok(cookie
.offset
== 12345678 - filter_start_time
, "Got offset %s.\n", wine_dbgstr_longlong(cookie
.offset
));
8473 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
8474 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8476 ok(!WaitForSingleObject(thread
, 2000), "Wait timed out.\n");
8477 CloseHandle(thread
);
8479 hr
= IDirectDrawStreamSample_CompletionStatus(stream_sample1
, 0, 0);
8480 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8482 IGraphBuilder_Disconnect(graph
, pin
);
8483 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
8485 CloseHandle(cookie
.advise_time_called_event
);
8486 ref
= IDirectDrawStreamSample_Release(stream_sample1
);
8487 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8488 ref
= IDirectDrawStreamSample_Release(stream_sample2
);
8489 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8490 ref
= IAMMultiMediaStream_Release(mmstream
);
8491 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8492 IMediaFilter_Release(media_filter
);
8493 ref
= IGraphBuilder_Release(graph
);
8494 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8495 ref
= IMediaStreamFilter_Release(filter
);
8496 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8498 IDirectDrawMediaStream_Release(ddraw_stream
);
8499 ref
= IMediaStream_Release(stream
);
8500 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8503 static void test_ddrawstreamsample_get_sample_times(void)
8505 static const BYTE test_data
[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11 };
8506 IAMMultiMediaStream
*mmstream
= create_ammultimediastream();
8507 IDirectDrawStreamSample
*stream_sample
;
8508 IMediaFilter
*graph_media_filter
;
8509 IDirectDrawMediaStream
*ddraw_stream
;
8510 STREAM_TIME filter_start_time
;
8511 IMemInputPin
*mem_input_pin
;
8512 IMediaStreamFilter
*filter
;
8513 IMediaSample
*media_sample
;
8514 struct testfilter source
;
8515 STREAM_TIME current_time
;
8516 struct testclock clock
;
8517 STREAM_TIME start_time
;
8518 STREAM_TIME end_time
;
8519 IGraphBuilder
*graph
;
8520 IMediaStream
*stream
;
8521 VIDEOINFO video_info
;
8527 hr
= IAMMultiMediaStream_Initialize(mmstream
, STREAMTYPE_READ
, 0, NULL
);
8528 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8529 hr
= IAMMultiMediaStream_GetFilter(mmstream
, &filter
);
8530 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8531 ok(!!filter
, "Expected non-null filter.\n");
8532 hr
= IAMMultiMediaStream_AddMediaStream(mmstream
, NULL
, &MSPID_PrimaryVideo
, 0, &stream
);
8533 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8534 hr
= IMediaStream_QueryInterface(stream
, &IID_IDirectDrawMediaStream
, (void **)&ddraw_stream
);
8535 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8536 hr
= IMediaStream_QueryInterface(stream
, &IID_IPin
, (void **)&pin
);
8537 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8538 hr
= IMediaStream_QueryInterface(stream
, &IID_IMemInputPin
, (void **)&mem_input_pin
);
8539 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8540 hr
= IAMMultiMediaStream_GetFilterGraph(mmstream
, &graph
);
8541 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8542 ok(graph
!= NULL
, "Expected non-NULL graph.\n");
8543 hr
= IGraphBuilder_QueryInterface(graph
, &IID_IMediaFilter
, (void **)&graph_media_filter
);
8544 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8545 testfilter_init(&source
);
8546 hr
= IGraphBuilder_AddFilter(graph
, &source
.filter
.IBaseFilter_iface
, NULL
);
8547 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8548 testclock_init(&clock
);
8550 video_info
= rgb32_video_info
;
8551 video_info
.bmiHeader
.biWidth
= 3;
8552 video_info
.bmiHeader
.biHeight
= 1;
8554 mt
.pbFormat
= (BYTE
*)&video_info
;
8555 hr
= IGraphBuilder_ConnectDirect(graph
, &source
.source
.pin
.IPin_iface
, pin
, &mt
);
8556 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8558 hr
= IDirectDrawMediaStream_CreateSample(ddraw_stream
, NULL
, NULL
, 0, &stream_sample
);
8559 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8561 clock
.time
= 12345678;
8563 current_time
= 0xdeadbeefdeadbeef;
8564 hr
= IDirectDrawStreamSample_GetSampleTimes(stream_sample
, NULL
, NULL
, ¤t_time
);
8565 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8566 ok(current_time
== 0, "Got current time %s.\n", wine_dbgstr_longlong(current_time
));
8568 IMediaFilter_SetSyncSource(graph_media_filter
, &clock
.IReferenceClock_iface
);
8569 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8571 current_time
= 0xdeadbeefdeadbeef;
8572 hr
= IDirectDrawStreamSample_GetSampleTimes(stream_sample
, NULL
, NULL
, ¤t_time
);
8573 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8574 ok(current_time
== 0, "Got current time %s.\n", wine_dbgstr_longlong(current_time
));
8576 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_RUN
);
8577 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8579 hr
= IMediaStreamFilter_GetCurrentStreamTime(filter
, &filter_start_time
);
8580 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8582 clock
.get_time_hr
= E_FAIL
;
8584 current_time
= 0xdeadbeefdeadbeef;
8585 hr
= IDirectDrawStreamSample_GetSampleTimes(stream_sample
, NULL
, NULL
, ¤t_time
);
8586 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8587 ok(current_time
== 0xdeadbeefddf15da1 + filter_start_time
, "Expected current time %s, got %s.\n",
8588 wine_dbgstr_longlong(0xdeadbeefddf15da1 + filter_start_time
), wine_dbgstr_longlong(current_time
));
8590 clock
.get_time_hr
= S_OK
;
8592 current_time
= 0xdeadbeefdeadbeef;
8593 hr
= IDirectDrawStreamSample_GetSampleTimes(stream_sample
, NULL
, NULL
, ¤t_time
);
8594 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8595 ok(current_time
== filter_start_time
, "Expected current time %s, got %s.\n",
8596 wine_dbgstr_longlong(filter_start_time
), wine_dbgstr_longlong(current_time
));
8598 clock
.time
= 23456789;
8600 current_time
= 0xdeadbeefdeadbeef;
8601 hr
= IDirectDrawStreamSample_GetSampleTimes(stream_sample
, NULL
, NULL
, ¤t_time
);
8602 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8603 ok(current_time
== filter_start_time
+ 11111111, "Expected current time %s, got %s.\n",
8604 wine_dbgstr_longlong(filter_start_time
+ 11111111), wine_dbgstr_longlong(current_time
));
8606 start_time
= 0xdeadbeefdeadbeef;
8607 end_time
= 0xdeadbeefdeadbeef;
8608 hr
= IDirectDrawStreamSample_GetSampleTimes(stream_sample
, &start_time
, &end_time
, NULL
);
8609 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8610 ok(start_time
== 0, "Got start time %s.\n", wine_dbgstr_longlong(start_time
));
8611 ok(end_time
== 0, "Got end time %s.\n", wine_dbgstr_longlong(end_time
));
8613 hr
= IDirectDrawStreamSample_Update(stream_sample
, SSUPDATE_ASYNC
, NULL
, NULL
, 0);
8614 ok(hr
== MS_S_PENDING
, "Got hr %#x.\n", hr
);
8616 media_sample
= ammediastream_allocate_sample(&source
, test_data
, sizeof(test_data
));
8617 start_time
= 12345678;
8618 end_time
= 23456789;
8619 hr
= IMediaSample_SetTime(media_sample
, &start_time
, &end_time
);
8620 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8621 hr
= IMemInputPin_Receive(mem_input_pin
, media_sample
);
8622 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8623 IMediaSample_Release(media_sample
);
8625 start_time
= 0xdeadbeefdeadbeef;
8626 end_time
= 0xdeadbeefdeadbeef;
8627 hr
= IDirectDrawStreamSample_GetSampleTimes(stream_sample
, &start_time
, &end_time
, NULL
);
8628 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8629 ok(start_time
== 12345678, "Got start time %s.\n", wine_dbgstr_longlong(start_time
));
8630 ok(end_time
== 23456789, "Got end time %s.\n", wine_dbgstr_longlong(end_time
));
8632 hr
= IAMMultiMediaStream_SetState(mmstream
, STREAMSTATE_STOP
);
8633 ok(hr
== S_OK
, "Got hr %#x.\n", hr
);
8634 IGraphBuilder_Disconnect(graph
, pin
);
8635 IGraphBuilder_Disconnect(graph
, &source
.source
.pin
.IPin_iface
);
8637 ref
= IDirectDrawStreamSample_Release(stream_sample
);
8638 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8639 ref
= IAMMultiMediaStream_Release(mmstream
);
8640 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8641 IMediaFilter_Release(graph_media_filter
);
8642 ref
= IGraphBuilder_Release(graph
);
8643 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8644 ref
= IMediaStreamFilter_Release(filter
);
8645 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8647 IMemInputPin_Release(mem_input_pin
);
8648 IDirectDrawMediaStream_Release(ddraw_stream
);
8649 ref
= IMediaStream_Release(stream
);
8650 ok(!ref
, "Got outstanding refcount %d.\n", ref
);
8653 START_TEST(amstream
)
8655 const WCHAR
*test_avi_path
;
8657 CoInitializeEx(NULL
, COINIT_MULTITHREADED
);
8661 test_media_streams();
8667 test_enum_media_types();
8670 test_avi_path
= load_resource(L
"test.avi");
8672 test_openfile(test_avi_path
);
8673 test_mmstream_get_duration(test_avi_path
);
8675 unload_resource(test_avi_path
);
8677 test_audiodata_query_interface();
8678 test_audiodata_get_info();
8679 test_audiodata_set_buffer();
8680 test_audiodata_set_actual();
8681 test_audiodata_get_format();
8682 test_audiodata_set_format();
8684 test_audiostream_get_format();
8685 test_audiostream_set_format();
8686 test_audiostream_receive_connection();
8687 test_audiostream_receive();
8688 test_audiostream_initialize();
8689 test_audiostream_begin_flush_end_flush();
8690 test_audiostream_new_segment();
8692 test_audiostreamsample_update();
8693 test_audiostreamsample_completion_status();
8694 test_audiostreamsample_get_sample_times();
8695 test_audiostreamsample_get_media_stream();
8696 test_audiostreamsample_get_audio_data();
8698 test_ddrawstream_initialize();
8699 test_ddrawstream_getsetdirectdraw();
8700 test_ddrawstream_receive_connection();
8701 test_ddrawstream_create_sample();
8702 test_ddrawstream_get_format();
8703 test_ddrawstream_set_format();
8704 test_ddrawstream_receive();
8705 test_ddrawstream_begin_flush_end_flush();
8706 test_ddrawstream_new_segment();
8707 test_ddrawstream_get_time_per_frame();
8709 test_ddrawstreamsample_get_media_stream();
8710 test_ddrawstreamsample_update();
8711 test_ddrawstreamsample_completion_status();
8712 test_ddrawstreamsample_get_sample_times();
8714 test_ammediastream_join_am_multi_media_stream();
8715 test_ammediastream_join_filter();
8716 test_ammediastream_join_filter_graph();
8717 test_ammediastream_set_state();
8718 test_ammediastream_end_of_stream();
8720 test_mediastreamfilter_get_state();
8721 test_mediastreamfilter_stop_pause_run();
8722 test_mediastreamfilter_support_seeking();
8723 test_mediastreamfilter_seeking();
8724 test_mediastreamfilter_get_current_stream_time();
8725 test_mediastreamfilter_reference_time_to_stream_time();
8726 test_mediastreamfilter_wait_until();