d3drm: Implement texture SetAppData and GetAppData.
[wine/multimedia.git] / dlls / dmusic / port.c
blobb6489a73855e153419f2fd6c844d4a45fafd84c9
1 /*
2 * IDirectMusicPort Implementation
4 * Copyright (C) 2003-2004 Rok Mandeljc
5 * Copyright (C) 2012 Christian Costa
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
22 #include "dmusic_private.h"
24 WINE_DEFAULT_DEBUG_CHANNEL(dmusic);
26 static inline SynthPortImpl *impl_from_SynthPortImpl_IDirectMusicPort(IDirectMusicPort *iface)
28 return CONTAINING_RECORD(iface, SynthPortImpl, IDirectMusicPort_iface);
31 static inline SynthPortImpl *impl_from_SynthPortImpl_IDirectMusicPortDownload(IDirectMusicPortDownload *iface)
33 return CONTAINING_RECORD(iface, SynthPortImpl, IDirectMusicPortDownload_iface);
36 static inline SynthPortImpl *impl_from_SynthPortImpl_IDirectMusicThru(IDirectMusicThru *iface)
38 return CONTAINING_RECORD(iface, SynthPortImpl, IDirectMusicThru_iface);
41 /* SynthPortImpl IDirectMusicPort IUnknown part follows: */
42 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_QueryInterface(LPDIRECTMUSICPORT iface, REFIID riid, LPVOID *ret_iface)
44 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
46 TRACE("(%p/%p)->(%s, %p)\n", iface, This, debugstr_dmguid(riid), ret_iface);
48 if (IsEqualIID (riid, &IID_IUnknown) ||
49 IsEqualGUID(riid, &IID_IDirectMusicPort) ||
50 IsEqualGUID(riid, &IID_IDirectMusicPort8)) {
51 *ret_iface = &This->IDirectMusicPort_iface;
52 IDirectMusicPort_AddRef((LPDIRECTMUSICPORT)*ret_iface);
53 return S_OK;
54 } else if (IsEqualGUID(riid, &IID_IDirectMusicPortDownload) ||
55 IsEqualGUID(riid, &IID_IDirectMusicPortDownload8)) {
56 *ret_iface = &This->IDirectMusicPortDownload_iface;
57 IDirectMusicPortDownload_AddRef((LPDIRECTMUSICPORTDOWNLOAD)*ret_iface);
58 return S_OK;
59 } else if (IsEqualGUID(riid, &IID_IDirectMusicThru) ||
60 IsEqualGUID(riid, &IID_IDirectMusicThru8)) {
61 *ret_iface = &This->IDirectMusicThru_iface;
62 IDirectMusicThru_AddRef((LPDIRECTMUSICTHRU)*ret_iface);
63 return S_OK;
66 WARN("(%p, %s, %p): not found\n", This, debugstr_dmguid(riid), ret_iface);
68 return E_NOINTERFACE;
71 static ULONG WINAPI SynthPortImpl_IDirectMusicPort_AddRef(LPDIRECTMUSICPORT iface)
73 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
74 ULONG ref = InterlockedIncrement(&This->ref);
76 TRACE("(%p)->(): new ref = %u\n", This, ref);
78 DMUSIC_LockModule();
80 return ref;
83 static ULONG WINAPI SynthPortImpl_IDirectMusicPort_Release(LPDIRECTMUSICPORT iface)
85 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
86 ULONG ref = InterlockedDecrement(&This->ref);
88 TRACE("(%p)->(): new ref = %u\n", This, ref);
90 if (!ref)
92 IDirectMusicSynth_Activate(This->synth, FALSE);
93 IDirectMusicSynth_Close(This->synth);
94 IDirectMusicSynth_Release(This->synth);
95 IDirectMusicSynthSink_Release(This->synth_sink);
96 IReferenceClock_Release(This->pLatencyClock);
97 HeapFree(GetProcessHeap(), 0, This);
100 DMUSIC_UnlockModule();
102 return ref;
105 /* SynthPortImpl IDirectMusicPort interface follows: */
106 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_PlayBuffer(LPDIRECTMUSICPORT iface, LPDIRECTMUSICBUFFER buffer)
108 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
109 HRESULT hr;
110 REFERENCE_TIME time;
111 LPBYTE data;
112 DWORD size;
114 TRACE("(%p/%p)->(%p)\n", iface, This, buffer);
116 if (!buffer)
117 return E_POINTER;
119 hr = IDirectMusicBuffer_GetStartTime(buffer, &time);
121 if (SUCCEEDED(hr))
122 hr = IDirectMusicBuffer_GetRawBufferPtr(buffer, &data);
124 if (SUCCEEDED(hr))
125 hr = IDirectMusicBuffer_GetUsedBytes(buffer, &size);
127 if (SUCCEEDED(hr))
128 hr = IDirectMusicSynth_PlayBuffer(This->synth, time, data, size);
130 return hr;
133 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_SetReadNotificationHandle(LPDIRECTMUSICPORT iface, HANDLE event)
135 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
137 FIXME("(%p/%p)->(%p): stub\n", iface, This, event);
139 return S_OK;
142 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_Read(LPDIRECTMUSICPORT iface, LPDIRECTMUSICBUFFER buffer)
144 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
146 FIXME("(%p/%p)->(%p): stub\n", iface, This, buffer);
148 return S_OK;
151 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_DownloadInstrument(LPDIRECTMUSICPORT iface, IDirectMusicInstrument* instrument, IDirectMusicDownloadedInstrument** downloaded_instrument, DMUS_NOTERANGE* note_ranges, DWORD num_note_ranges)
153 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
155 FIXME("(%p/%p)->(%p, %p, %p, %d): stub\n", iface, This, instrument, downloaded_instrument, note_ranges, num_note_ranges);
157 if (!instrument || !downloaded_instrument || (num_note_ranges && !note_ranges))
158 return E_POINTER;
160 return DMUSIC_CreateDirectMusicDownloadedInstrumentImpl(&IID_IDirectMusicDownloadedInstrument, (LPVOID*)downloaded_instrument, NULL);
163 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_UnloadInstrument(LPDIRECTMUSICPORT iface, IDirectMusicDownloadedInstrument *downloaded_instrument)
165 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
167 FIXME("(%p/%p)->(%p): stub\n", iface, This, downloaded_instrument);
169 return S_OK;
172 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_GetLatencyClock(LPDIRECTMUSICPORT iface, IReferenceClock** clock)
174 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
176 TRACE("(%p/%p)->(%p)\n", iface, This, clock);
178 *clock = This->pLatencyClock;
179 IReferenceClock_AddRef(*clock);
181 return S_OK;
184 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_GetRunningStats(LPDIRECTMUSICPORT iface, LPDMUS_SYNTHSTATS stats)
186 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
188 FIXME("(%p/%p)->(%p): stub\n", iface, This, stats);
190 return S_OK;
193 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_Compact(LPDIRECTMUSICPORT iface)
195 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
197 FIXME("(%p/%p)->(): stub\n", iface, This);
199 return S_OK;
202 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_GetCaps(LPDIRECTMUSICPORT iface, LPDMUS_PORTCAPS port_caps)
204 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
206 TRACE("(%p/%p)->(%p)\n", iface, This, port_caps);
208 *port_caps = This->caps;
210 return S_OK;
213 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_DeviceIoControl(LPDIRECTMUSICPORT iface, DWORD io_control_code, LPVOID in_buffer, DWORD in_buffer_size,
214 LPVOID out_buffer, DWORD out_buffer_size, LPDWORD bytes_returned, LPOVERLAPPED overlapped)
216 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
218 FIXME("(%p/%p)->(%d, %p, %d, %p, %d, %p, %p): stub\n", iface, This, io_control_code, in_buffer, in_buffer_size, out_buffer, out_buffer_size, bytes_returned, overlapped);
220 return S_OK;
223 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_SetNumChannelGroups(LPDIRECTMUSICPORT iface, DWORD channel_groups)
225 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
227 FIXME("(%p/%p)->(%d): semi-stub\n", iface, This, channel_groups);
229 This->nrofgroups = channel_groups;
231 return S_OK;
234 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_GetNumChannelGroups(LPDIRECTMUSICPORT iface, LPDWORD channel_groups)
236 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
238 TRACE("(%p/%p)->(%p)\n", iface, This, channel_groups);
240 *channel_groups = This->nrofgroups;
242 return S_OK;
245 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_Activate(LPDIRECTMUSICPORT iface, BOOL active)
247 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
249 TRACE("(%p/%p)->(%d)\n", iface, This, active);
251 This->fActive = active;
253 return S_OK;
256 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_SetChannelPriority(LPDIRECTMUSICPORT iface, DWORD channel_group, DWORD channel, DWORD priority)
258 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
260 FIXME("(%p/%p)->(%d, %d, %d): semi-stub\n", iface, This, channel_group, channel, priority);
262 if (channel > 16)
264 WARN("isn't there supposed to be 16 channels (no. %d requested)?! (faking as it is ok)\n", channel);
265 /*return E_INVALIDARG;*/
268 return S_OK;
271 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_GetChannelPriority(LPDIRECTMUSICPORT iface, DWORD channel_group, DWORD channel, LPDWORD priority)
273 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
275 TRACE("(%p/%p)->(%u, %u, %p)\n", iface, This, channel_group, channel, priority);
277 *priority = This->group[channel_group - 1].channel[channel].priority;
279 return S_OK;
282 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_SetDirectSound(LPDIRECTMUSICPORT iface, LPDIRECTSOUND direct_sound, LPDIRECTSOUNDBUFFER direct_sound_buffer)
284 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
286 FIXME("(%p/%p)->(%p, %p): stub\n", iface, This, direct_sound, direct_sound_buffer);
288 return S_OK;
291 static HRESULT WINAPI SynthPortImpl_IDirectMusicPort_GetFormat(LPDIRECTMUSICPORT iface, LPWAVEFORMATEX pWaveFormatEx, LPDWORD pdwWaveFormatExSize, LPDWORD pdwBufferSize)
293 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPort(iface);
294 WAVEFORMATEX format;
295 FIXME("(%p, %p, %p, %p): stub\n", This, pWaveFormatEx, pdwWaveFormatExSize, pdwBufferSize);
297 if (pWaveFormatEx == NULL)
299 if (pdwWaveFormatExSize)
300 *pdwWaveFormatExSize = sizeof(format);
301 else
302 return E_POINTER;
304 else
306 if (pdwWaveFormatExSize == NULL)
307 return E_POINTER;
309 /* Just fill this in with something that will not crash Direct Sound for now. */
310 /* It won't be used anyway until Performances are completed */
311 format.wFormatTag = WAVE_FORMAT_PCM;
312 format.nChannels = 2; /* This->params.dwAudioChannels; */
313 format.nSamplesPerSec = 44100; /* This->params.dwSampleRate; */
314 format.wBitsPerSample = 16; /* FIXME: check this */
315 format.nBlockAlign = (format.wBitsPerSample * format.nChannels) / 8;
316 format.nAvgBytesPerSec = format.nSamplesPerSec * format.nBlockAlign;
317 format.cbSize = 0;
319 if (*pdwWaveFormatExSize >= sizeof(format))
321 CopyMemory(pWaveFormatEx, &format, min(sizeof(format), *pdwWaveFormatExSize));
322 *pdwWaveFormatExSize = sizeof(format); /* FIXME check if this is set */
324 else
325 return E_POINTER; /* FIXME find right error */
328 if (pdwBufferSize)
329 *pdwBufferSize = 44100 * 2 * 2;
330 else
331 return E_POINTER;
333 return S_OK;
336 static const IDirectMusicPortVtbl SynthPortImpl_DirectMusicPort_Vtbl = {
337 /**** IDirectMusicPort IUnknown part methods ***/
338 SynthPortImpl_IDirectMusicPort_QueryInterface,
339 SynthPortImpl_IDirectMusicPort_AddRef,
340 SynthPortImpl_IDirectMusicPort_Release,
341 /**** IDirectMusicPort methods ***/
342 SynthPortImpl_IDirectMusicPort_PlayBuffer,
343 SynthPortImpl_IDirectMusicPort_SetReadNotificationHandle,
344 SynthPortImpl_IDirectMusicPort_Read,
345 SynthPortImpl_IDirectMusicPort_DownloadInstrument,
346 SynthPortImpl_IDirectMusicPort_UnloadInstrument,
347 SynthPortImpl_IDirectMusicPort_GetLatencyClock,
348 SynthPortImpl_IDirectMusicPort_GetRunningStats,
349 SynthPortImpl_IDirectMusicPort_Compact,
350 SynthPortImpl_IDirectMusicPort_GetCaps,
351 SynthPortImpl_IDirectMusicPort_DeviceIoControl,
352 SynthPortImpl_IDirectMusicPort_SetNumChannelGroups,
353 SynthPortImpl_IDirectMusicPort_GetNumChannelGroups,
354 SynthPortImpl_IDirectMusicPort_Activate,
355 SynthPortImpl_IDirectMusicPort_SetChannelPriority,
356 SynthPortImpl_IDirectMusicPort_GetChannelPriority,
357 SynthPortImpl_IDirectMusicPort_SetDirectSound,
358 SynthPortImpl_IDirectMusicPort_GetFormat
361 /* SynthPortImpl IDirectMusicPortDownload IUnknown part follows: */
362 static HRESULT WINAPI SynthPortImpl_IDirectMusicPortDownload_QueryInterface(LPDIRECTMUSICPORTDOWNLOAD iface, REFIID riid, LPVOID *ret_iface)
364 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPortDownload(iface);
366 TRACE("(%p/%p)->(%s, %p)\n", iface, This, debugstr_dmguid(riid), ret_iface);
368 return IDirectMusicPort_QueryInterface(&This->IDirectMusicPort_iface, riid, ret_iface);
371 static ULONG WINAPI SynthPortImpl_IDirectMusicPortDownload_AddRef (LPDIRECTMUSICPORTDOWNLOAD iface)
373 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPortDownload(iface);
375 TRACE("(%p/%p)->()\n", iface, This);
377 return IDirectMusicPort_AddRef(&This->IDirectMusicPort_iface);
380 static ULONG WINAPI SynthPortImpl_IDirectMusicPortDownload_Release(LPDIRECTMUSICPORTDOWNLOAD iface)
382 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPortDownload(iface);
384 TRACE("(%p/%p)->()\n", iface, This);
386 return IDirectMusicPort_Release(&This->IDirectMusicPort_iface);
389 /* SynthPortImpl IDirectMusicPortDownload Interface follows: */
390 static HRESULT WINAPI SynthPortImpl_IDirectMusicPortDownload_GetBuffer(LPDIRECTMUSICPORTDOWNLOAD iface, DWORD DLId, IDirectMusicDownload** IDMDownload)
392 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPortDownload(iface);
394 FIXME("(%p/%p)->(%u, %p): stub\n", iface, This, DLId, IDMDownload);
396 if (!IDMDownload)
397 return E_POINTER;
399 return DMUSIC_CreateDirectMusicDownloadImpl(&IID_IDirectMusicDownload, (LPVOID*)IDMDownload, NULL);
402 static HRESULT WINAPI SynthPortImpl_IDirectMusicPortDownload_AllocateBuffer(LPDIRECTMUSICPORTDOWNLOAD iface, DWORD size, IDirectMusicDownload** IDMDownload)
404 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPortDownload(iface);
406 FIXME("(%p/%p)->(%u, %p): stub\n", iface, This, size, IDMDownload);
408 return S_OK;
411 static HRESULT WINAPI SynthPortImpl_IDirectMusicPortDownload_GetDLId(LPDIRECTMUSICPORTDOWNLOAD iface, DWORD* start_DLId, DWORD count)
413 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPortDownload(iface);
415 FIXME("(%p/%p)->(%p, %u): stub\n", iface, This, start_DLId, count);
417 return S_OK;
420 static HRESULT WINAPI SynthPortImpl_IDirectMusicPortDownload_GetAppend (LPDIRECTMUSICPORTDOWNLOAD iface, DWORD* append)
422 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPortDownload(iface);
424 FIXME("(%p/%p)->(%p): stub\n", iface, This, append);
426 return S_OK;
429 static HRESULT WINAPI SynthPortImpl_IDirectMusicPortDownload_Download(LPDIRECTMUSICPORTDOWNLOAD iface, IDirectMusicDownload* IDMDownload)
431 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPortDownload(iface);
433 FIXME("(%p/%p)->(%p): stub\n", iface, This, IDMDownload);
435 return S_OK;
438 static HRESULT WINAPI SynthPortImpl_IDirectMusicPortDownload_Unload(LPDIRECTMUSICPORTDOWNLOAD iface, IDirectMusicDownload* IDMDownload)
440 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicPortDownload(iface);
442 FIXME("(%p/%p)->(%p): stub\n", iface, This, IDMDownload);
444 return S_OK;
447 static const IDirectMusicPortDownloadVtbl SynthPortImpl_DirectMusicPortDownload_Vtbl = {
448 /*** IDirectMusicPortDownload IUnknown part methods ***/
449 SynthPortImpl_IDirectMusicPortDownload_QueryInterface,
450 SynthPortImpl_IDirectMusicPortDownload_AddRef,
451 SynthPortImpl_IDirectMusicPortDownload_Release,
452 /*** IDirectMusicPortDownload methods ***/
453 SynthPortImpl_IDirectMusicPortDownload_GetBuffer,
454 SynthPortImpl_IDirectMusicPortDownload_AllocateBuffer,
455 SynthPortImpl_IDirectMusicPortDownload_GetDLId,
456 SynthPortImpl_IDirectMusicPortDownload_GetAppend,
457 SynthPortImpl_IDirectMusicPortDownload_Download,
458 SynthPortImpl_IDirectMusicPortDownload_Unload
461 /* SynthPortImpl IDirectMusicThru IUnknown part follows: */
462 static HRESULT WINAPI SynthPortImpl_IDirectMusicThru_QueryInterface(LPDIRECTMUSICTHRU iface, REFIID riid, LPVOID *ret_iface)
464 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicThru(iface);
466 TRACE("(%p/%p)->(%s, %p)\n", iface, This, debugstr_dmguid(riid), ret_iface);
468 return IDirectMusicPort_QueryInterface(&This->IDirectMusicPort_iface, riid, ret_iface);
471 static ULONG WINAPI SynthPortImpl_IDirectMusicThru_AddRef(LPDIRECTMUSICTHRU iface)
473 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicThru(iface);
475 TRACE("(%p/%p)->()\n", iface, This);
477 return IDirectMusicPort_AddRef(&This->IDirectMusicPort_iface);
480 static ULONG WINAPI SynthPortImpl_IDirectMusicThru_Release(LPDIRECTMUSICTHRU iface)
482 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicThru(iface);
484 TRACE("(%p/%p)->()\n", iface, This);
486 return IDirectMusicPort_Release(&This->IDirectMusicPort_iface);
489 /* SynthPortImpl IDirectMusicThru Interface follows: */
490 static HRESULT WINAPI SynthPortImpl_IDirectMusicThru_ThruChannel(LPDIRECTMUSICTHRU iface, DWORD source_channel_group, DWORD source_channel, DWORD destination_channel_group,
491 DWORD destination_channel, LPDIRECTMUSICPORT destination_port)
493 SynthPortImpl *This = impl_from_SynthPortImpl_IDirectMusicThru(iface);
495 FIXME("(%p/%p)->(%d, %d, %d, %d, %p): stub\n", iface, This, source_channel_group, source_channel, destination_channel_group, destination_channel, destination_port);
497 return S_OK;
500 static const IDirectMusicThruVtbl SynthPortImpl_DirectMusicThru_Vtbl = {
501 /*** IDirectMusicThru IUnknown part methods */
502 SynthPortImpl_IDirectMusicThru_QueryInterface,
503 SynthPortImpl_IDirectMusicThru_AddRef,
504 SynthPortImpl_IDirectMusicThru_Release,
505 /*** IDirectMusicThru methods ***/
506 SynthPortImpl_IDirectMusicThru_ThruChannel
509 HRESULT DMUSIC_CreateSynthPortImpl(LPCGUID guid, LPVOID *object, LPUNKNOWN unkouter, LPDMUS_PORTPARAMS port_params, LPDMUS_PORTCAPS port_caps, DWORD device)
511 SynthPortImpl *obj;
512 HRESULT hr = E_FAIL;
513 UINT i;
515 TRACE("(%p,%p,%p,%p,%p%d)\n", guid, object, unkouter, port_params, port_caps, device);
517 *object = NULL;
519 obj = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(SynthPortImpl));
520 if (!obj)
521 return E_OUTOFMEMORY;
523 obj->IDirectMusicPort_iface.lpVtbl = &SynthPortImpl_DirectMusicPort_Vtbl;
524 obj->IDirectMusicPortDownload_iface.lpVtbl = &SynthPortImpl_DirectMusicPortDownload_Vtbl;
525 obj->IDirectMusicThru_iface.lpVtbl = &SynthPortImpl_DirectMusicThru_Vtbl;
526 obj->ref = 0; /* Will be inited by QueryInterface */
527 obj->fActive = FALSE;
528 obj->params = *port_params;
529 obj->caps = *port_caps;
531 hr = DMUSIC_CreateReferenceClockImpl(&IID_IReferenceClock, (LPVOID*)&obj->pLatencyClock, NULL);
532 if (hr != S_OK)
534 HeapFree(GetProcessHeap(), 0, obj);
535 return hr;
538 if (SUCCEEDED(hr))
539 hr = CoCreateInstance(&CLSID_DirectMusicSynth, NULL, CLSCTX_INPROC_SERVER, &IID_IDirectMusicSynth, (void**)&obj->synth);
541 if (SUCCEEDED(hr))
542 hr = CoCreateInstance(&CLSID_DirectMusicSynthSink, NULL, CLSCTX_INPROC_SERVER, &IID_IDirectMusicSynthSink, (void**)&obj->synth_sink);
544 if (SUCCEEDED(hr))
545 hr = IDirectMusicSynth_SetMasterClock(obj->synth, obj->pLatencyClock);
547 if (SUCCEEDED(hr))
548 hr = IDirectMusicSynthSink_SetMasterClock(obj->synth_sink, obj->pLatencyClock);
550 if (SUCCEEDED(hr))
551 hr = IDirectMusicSynth_SetSynthSink(obj->synth, obj->synth_sink);
553 if (SUCCEEDED(hr))
554 hr = IDirectMusicSynth_Open(obj->synth, port_params);
556 if (0)
558 if (port_params->dwValidParams & DMUS_PORTPARAMS_CHANNELGROUPS) {
559 obj->nrofgroups = port_params->dwChannelGroups;
560 /* Setting default priorities */
561 for (i = 0; i < obj->nrofgroups; i++) {
562 TRACE ("Setting default channel priorities on channel group %i\n", i + 1);
563 obj->group[i].channel[0].priority = DAUD_CHAN1_DEF_VOICE_PRIORITY;
564 obj->group[i].channel[1].priority = DAUD_CHAN2_DEF_VOICE_PRIORITY;
565 obj->group[i].channel[2].priority = DAUD_CHAN3_DEF_VOICE_PRIORITY;
566 obj->group[i].channel[3].priority = DAUD_CHAN4_DEF_VOICE_PRIORITY;
567 obj->group[i].channel[4].priority = DAUD_CHAN5_DEF_VOICE_PRIORITY;
568 obj->group[i].channel[5].priority = DAUD_CHAN6_DEF_VOICE_PRIORITY;
569 obj->group[i].channel[6].priority = DAUD_CHAN7_DEF_VOICE_PRIORITY;
570 obj->group[i].channel[7].priority = DAUD_CHAN8_DEF_VOICE_PRIORITY;
571 obj->group[i].channel[8].priority = DAUD_CHAN9_DEF_VOICE_PRIORITY;
572 obj->group[i].channel[9].priority = DAUD_CHAN10_DEF_VOICE_PRIORITY;
573 obj->group[i].channel[10].priority = DAUD_CHAN11_DEF_VOICE_PRIORITY;
574 obj->group[i].channel[11].priority = DAUD_CHAN12_DEF_VOICE_PRIORITY;
575 obj->group[i].channel[12].priority = DAUD_CHAN13_DEF_VOICE_PRIORITY;
576 obj->group[i].channel[13].priority = DAUD_CHAN14_DEF_VOICE_PRIORITY;
577 obj->group[i].channel[14].priority = DAUD_CHAN15_DEF_VOICE_PRIORITY;
578 obj->group[i].channel[15].priority = DAUD_CHAN16_DEF_VOICE_PRIORITY;
583 if (SUCCEEDED(hr))
584 return IDirectMusicPort_QueryInterface((LPDIRECTMUSICPORT)obj, guid, object);
586 if (obj->synth)
587 IDirectMusicSynth_Release(obj->synth);
588 if (obj->synth_sink)
589 IDirectMusicSynthSink_Release(obj->synth_sink);
590 if (obj->pLatencyClock)
591 IReferenceClock_Release(obj->pLatencyClock);
592 HeapFree(GetProcessHeap(), 0, obj);
594 return hr;
597 HRESULT DMUSIC_CreateMidiOutPortImpl(LPCGUID guid, LPVOID *object, LPUNKNOWN unkouter, LPDMUS_PORTPARAMS port_params, LPDMUS_PORTCAPS port_caps, DWORD device)
599 TRACE("(%p,%p,%p,%p,%p,%d): stub\n", guid, object, unkouter, port_params, port_caps, device);
601 return E_NOTIMPL;
604 HRESULT DMUSIC_CreateMidiInPortImpl(LPCGUID guid, LPVOID *object, LPUNKNOWN unkouter, LPDMUS_PORTPARAMS port_params, LPDMUS_PORTCAPS port_caps, DWORD device)
606 TRACE("(%p,%p,%p,%p,%p,%d): stub\n", guid, object, unkouter, port_params, port_caps, device);
608 return E_NOTIMPL;