Which I intend to use to support (and rewrite) instrument / wave downloads.
-- v2: dmusic: Implement IDirectMusicPortDownload_GetBuffer. dmusic: Implement IDirectMusicPortDownload_(Download|Unload). dmusic: Implement IDirectMusicPortDownload_AllocateBuffer. dmusic: Implement synth port IDirectMusicPortDownload_GetDLId. dmusic: Rename IDirectMusicDownloadImpl method prefix to download. dmusic: Move IDirectMusicDownloadImpl struct to where it is used. dmusic: Simplify and cleanup IDirectMusicDownload constructor. dmusic: Always return S_FALSE from DllCanUnloadNow. dmusic/tests: Test IDirectMusicPort_(Download|Unload)Instrument. dmusic/tests: Test IDirectMusic(Port)Download interfaces. include: Fix incorrect IDirectMusicPortDownload_Unload macro.
From: Rémi Bernon rbernon@codeweavers.com
--- include/dmusicc.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/include/dmusicc.h b/include/dmusicc.h index cdae16c75bd..94ff184dc9f 100644 --- a/include/dmusicc.h +++ b/include/dmusicc.h @@ -635,7 +635,7 @@ DECLARE_INTERFACE_(IDirectMusicPortDownload,IUnknown) #define IDirectMusicPortDownload_GetDLId(p,a,b) (p)->lpVtbl->GetDLId(p,a,b) #define IDirectMusicPortDownload_GetAppend(p,a) (p)->lpVtbl->GetAppend(p,a) #define IDirectMusicPortDownload_Download(p,a) (p)->lpVtbl->Download(p,a) -#define IDirectMusicPortDownload_Unload(p,a) (p)->lpVtbl->GetBuffer(p,a) +#define IDirectMusicPortDownload_Unload(p,a) (p)->lpVtbl->Unload(p,a) #endif
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmusic/tests/dmusic.c | 148 +++++++++++++++++++++++++++++++++++++ 1 file changed, 148 insertions(+)
diff --git a/dlls/dmusic/tests/dmusic.c b/dlls/dmusic/tests/dmusic.c index 37b517fe0ca..fd012111df0 100644 --- a/dlls/dmusic/tests/dmusic.c +++ b/dlls/dmusic/tests/dmusic.c @@ -947,6 +947,153 @@ static void test_synthport(void) IDirectMusic_Release(dmusic); }
+static void test_port_download(void) +{ + struct wave_download + { + DMUS_DOWNLOADINFO info; + ULONG offsets[2]; + DMUS_WAVE wave; + DMUS_WAVEDATA wave_data; + }; + + static void *invalid_ptr = (void *)0xdeadbeef; + IDirectMusicDownload *download, *tmp_download; + struct wave_download *wave_download; + IDirectMusicPortDownload *port; + IDirectMusicPort *tmp_port; + DWORD ids[4], append, size; + IDirectMusic *dmusic; + void *buffer; + HRESULT hr; + + tmp_port = create_synth_port(&dmusic); + hr = IDirectMusicPort_QueryInterface(tmp_port, &IID_IDirectMusicPortDownload, (void **)&port); + ok(hr == S_OK, "got %#lx\n", hr); + IDirectMusicPort_Release(tmp_port); + + /* GetBuffer only works with pre-allocated DLId */ + hr = IDirectMusicPortDownload_GetBuffer(port, 0, NULL); + ok(hr == E_POINTER, "got %#lx\n", hr); + hr = IDirectMusicPortDownload_GetBuffer(port, 0, &download); + todo_wine ok(hr == DMUS_E_INVALID_DOWNLOADID, "got %#lx\n", hr); + hr = IDirectMusicPortDownload_GetBuffer(port, 0xdeadbeef, &download); + todo_wine ok(hr == DMUS_E_INVALID_DOWNLOADID, "got %#lx\n", hr); + + /* AllocateBuffer use the exact requested size */ + hr = IDirectMusicPortDownload_AllocateBuffer(port, 0, NULL); + todo_wine ok(hr == E_POINTER, "got %#lx\n", hr); + hr = IDirectMusicPortDownload_AllocateBuffer(port, 0, &download); + todo_wine ok(hr == E_INVALIDARG, "got %#lx\n", hr); + + hr = IDirectMusicPortDownload_AllocateBuffer(port, 1, &download); + ok(hr == S_OK, "got %#lx\n", hr); + size = 0xdeadbeef; + buffer = invalid_ptr; + hr = IDirectMusicDownload_GetBuffer(download, (void **)&buffer, &size); + ok(hr == S_OK, "got %#lx\n", hr); + todo_wine ok(size == 1, "got %#lx\n", size); + todo_wine ok(buffer != invalid_ptr, "got %p\n", buffer); + IDirectMusicDownload_Release(download); + + /* GetDLId allocates the given number of slots and returns only the first */ + hr = IDirectMusicPortDownload_GetDLId(port, NULL, 0); + todo_wine ok(hr == E_POINTER, "got %#lx\n", hr); + hr = IDirectMusicPortDownload_GetDLId(port, ids, 0); + todo_wine ok(hr == E_INVALIDARG, "got %#lx\n", hr); + + memset(ids, 0xcc, sizeof(ids)); + hr = IDirectMusicPortDownload_GetDLId(port, ids, 4); + ok(hr == S_OK, "got %#lx\n", hr); + todo_wine ok(ids[0] == 0, "got %#lx\n", ids[0]); + ok(ids[1] == 0xcccccccc, "got %#lx\n", ids[1]); + + /* GetBuffer looks up allocated ids to find downloaded buffers */ + hr = IDirectMusicPortDownload_GetBuffer(port, 2, &download); + todo_wine ok(hr == DMUS_E_NOT_DOWNLOADED_TO_PORT, "got %#lx\n", hr); + + hr = IDirectMusicPortDownload_GetAppend(port, NULL); + todo_wine ok(hr == E_POINTER, "got %#lx\n", hr); + append = 0xdeadbeef; + hr = IDirectMusicPortDownload_GetAppend(port, &append); + ok(hr == S_OK, "got %#lx\n", hr); + todo_wine ok(append == 2, "got %#lx\n", append); + + /* test Download / Unload on invalid and valid buffers */ + + download = invalid_ptr; + hr = IDirectMusicPortDownload_AllocateBuffer(port, sizeof(struct wave_download), &download); + ok(hr == S_OK, "got %#lx\n", hr); + todo_wine ok(download != invalid_ptr, "got %p\n", download); + if (download == invalid_ptr) goto skip_tests; + size = 0xdeadbeef; + wave_download = invalid_ptr; + hr = IDirectMusicDownload_GetBuffer(download, (void **)&wave_download, &size); + ok(hr == S_OK, "got %#lx\n", hr); + todo_wine ok(size == sizeof(struct wave_download), "got %#lx\n", size); + todo_wine ok(wave_download != invalid_ptr, "got %p\n", wave_download); + wave_download->info.cbSize = sizeof(struct wave_download); + wave_download->info.dwDLId = 2; + wave_download->info.dwDLType = 0; + wave_download->info.dwNumOffsetTableEntries = 0; + hr = IDirectMusicPortDownload_GetBuffer(port, 2, &tmp_download); + todo_wine ok(hr == DMUS_E_NOT_DOWNLOADED_TO_PORT, "got %#lx\n", hr); + + hr = IDirectMusicPortDownload_Download(port, NULL); + todo_wine ok(hr == E_POINTER, "got %#lx\n", hr); + hr = IDirectMusicPortDownload_Download(port, download); + todo_wine ok(hr == DMUS_E_UNKNOWNDOWNLOAD, "got %#lx\n", hr); + + wave_download->info.dwDLType = DMUS_DOWNLOADINFO_WAVE; + wave_download->info.dwNumOffsetTableEntries = 2; + wave_download->offsets[0] = offsetof(struct wave_download, wave); + wave_download->offsets[1] = offsetof(struct wave_download, wave_data); + wave_download->wave.WaveformatEx.wFormatTag = WAVE_FORMAT_PCM; + wave_download->wave.WaveformatEx.nChannels = 1; + wave_download->wave.WaveformatEx.nSamplesPerSec = 44100; + wave_download->wave.WaveformatEx.nAvgBytesPerSec = 44100; + wave_download->wave.WaveformatEx.nBlockAlign = 1; + wave_download->wave.WaveformatEx.wBitsPerSample = 8; + wave_download->wave.WaveformatEx.cbSize = 0; + wave_download->wave.ulWaveDataIdx = 1; + wave_download->wave.ulCopyrightIdx = 0; + wave_download->wave.ulFirstExtCkIdx = 0; + wave_download->wave_data.cbSize = 1; + + hr = IDirectMusicPortDownload_Download(port, download); + ok(hr == S_OK, "got %#lx\n", hr); + hr = IDirectMusicPortDownload_Download(port, download); + todo_wine ok(hr == DMUS_E_ALREADY_DOWNLOADED, "got %#lx\n", hr); + + tmp_download = invalid_ptr; + hr = IDirectMusicPortDownload_GetBuffer(port, 2, &tmp_download); + ok(hr == S_OK, "got %#lx\n", hr); + todo_wine ok(tmp_download == download, "got %p\n", tmp_download); + if (tmp_download != invalid_ptr) IDirectMusicDownload_Release(tmp_download); + + hr = IDirectMusicPortDownload_Unload(port, NULL); + todo_wine ok(hr == E_POINTER, "got %#lx\n", hr); + hr = IDirectMusicPortDownload_Unload(port, download); + ok(hr == S_OK, "got %#lx\n", hr); + + hr = IDirectMusicPortDownload_GetBuffer(port, 2, &tmp_download); + todo_wine ok(hr == DMUS_E_NOT_DOWNLOADED_TO_PORT, "got %#lx\n", hr); + + hr = IDirectMusicPortDownload_Unload(port, download); + ok(hr == S_OK, "got %#lx\n", hr); + + /* DLIds are never released */ + hr = IDirectMusicPortDownload_GetDLId(port, ids, 1); + ok(hr == S_OK, "got %#lx\n", hr); + todo_wine ok(ids[0] == 4, "got %#lx\n", ids[0]); + + IDirectMusicDownload_Release(download); + +skip_tests: + IDirectMusicPortDownload_Release(port); + IDirectMusic_Release(dmusic); +} + START_TEST(dmusic) { CoInitializeEx(NULL, COINIT_MULTITHREADED); @@ -967,6 +1114,7 @@ START_TEST(dmusic) test_parsedescriptor(); test_master_clock(); test_synthport(); + test_port_download();
CoUninitialize(); }
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmusic/tests/dmusic.c | 240 ++++++++++++++++++++++++++++++++++++- 1 file changed, 234 insertions(+), 6 deletions(-)
diff --git a/dlls/dmusic/tests/dmusic.c b/dlls/dmusic/tests/dmusic.c index fd012111df0..6df37e3d63d 100644 --- a/dlls/dmusic/tests/dmusic.c +++ b/dlls/dmusic/tests/dmusic.c @@ -30,6 +30,95 @@ #include "dmusicf.h" #include "dmksctrl.h"
+static ULONG get_refcount(void *iface) +{ + IUnknown *unknown = iface; + IUnknown_AddRef(unknown); + return IUnknown_Release(unknown); +} + +#define check_interface(a, b, c) check_interface_(__LINE__, a, b, c) +static void check_interface_(unsigned int line, void *iface_ptr, REFIID iid, BOOL supported) +{ + ULONG expect_ref = get_refcount(iface_ptr); + IUnknown *iface = iface_ptr; + HRESULT hr, expected; + IUnknown *unk; + + expected = supported ? S_OK : E_NOINTERFACE; + hr = IUnknown_QueryInterface(iface, iid, (void **)&unk); + ok_(__FILE__, line)(hr == expected, "got hr %#lx, expected %#lx.\n", hr, expected); + if (SUCCEEDED(hr)) + { + LONG ref = get_refcount(unk); + ok_(__FILE__, line)(ref == expect_ref + 1, "got %ld\n", ref); + IUnknown_Release(unk); + ref = get_refcount(iface_ptr); + ok_(__FILE__, line)(ref == expect_ref, "got %ld\n", ref); + } +} + +static void stream_begin_chunk(IStream *stream, const char type[5], ULARGE_INTEGER *offset) +{ + static const LARGE_INTEGER zero = {0}; + HRESULT hr; + hr = IStream_Write(stream, type, 4, NULL); + ok(hr == S_OK, "got %#lx\n", hr); + hr = IStream_Seek(stream, zero, STREAM_SEEK_CUR, offset); + ok(hr == S_OK, "got %#lx\n", hr); + hr = IStream_Write(stream, "\0\0\0\0", 4, NULL); + ok(hr == S_OK, "got %#lx\n", hr); +} + +static void stream_end_chunk(IStream *stream, ULARGE_INTEGER *offset) +{ + static const LARGE_INTEGER zero = {0}; + ULARGE_INTEGER position; + HRESULT hr; + UINT size; + hr = IStream_Seek(stream, zero, STREAM_SEEK_CUR, &position); + ok(hr == S_OK, "got %#lx\n", hr); + hr = IStream_Seek(stream, *(LARGE_INTEGER *)offset, STREAM_SEEK_SET, NULL); + ok(hr == S_OK, "got %#lx\n", hr); + size = position.QuadPart - offset->QuadPart - 4; + hr = IStream_Write(stream, &size, 4, NULL); + ok(hr == S_OK, "got %#lx\n", hr); + hr = IStream_Seek(stream, *(LARGE_INTEGER *)&position, STREAM_SEEK_SET, NULL); + ok(hr == S_OK, "got %#lx\n", hr); +} + +#define CHUNK_BEGIN(stream, type) \ + do { \ + ULARGE_INTEGER __off; \ + stream_begin_chunk(stream, type, &__off); \ + do + +#define CHUNK_RIFF(stream, form) \ + do { \ + ULARGE_INTEGER __off; \ + stream_begin_chunk(stream, "RIFF", &__off); \ + IStream_Write(stream, form, 4, NULL); \ + do + +#define CHUNK_LIST(stream, form) \ + do { \ + ULARGE_INTEGER __off; \ + stream_begin_chunk(stream, "LIST", &__off); \ + IStream_Write(stream, form, 4, NULL); \ + do + +#define CHUNK_END \ + while (0); \ + stream_end_chunk(stream, &__off); \ + } while (0) + +#define CHUNK_DATA(stream, type, data) \ + CHUNK_BEGIN(stream, type) \ + { \ + IStream_Write((stream), &(data), sizeof(data), NULL); \ + } \ + CHUNK_END + static BOOL compare_time(REFERENCE_TIME x, REFERENCE_TIME y, unsigned int max_diff) { REFERENCE_TIME diff = x > y ? x - y : y - x; @@ -97,12 +186,6 @@ static void test_dmusic(void) IDirectMusic_Release(dmusic); }
-static ULONG get_refcount(IDirectSound *iface) -{ - IDirectSound_AddRef(iface); - return IDirectSound_Release(iface); -} - static void test_setdsound(void) { IDirectMusic *dmusic; @@ -1091,6 +1174,150 @@ static void test_port_download(void)
skip_tests: IDirectMusicPortDownload_Release(port); +} + +static void test_download_instrument(void) +{ + static const LARGE_INTEGER zero = {0}; + IDirectMusicDownloadedInstrument *downloaded; + IDirectMusicCollection *collection; + IDirectMusicInstrument *instrument; + IPersistStream *persist; + IDirectMusicPort *port; + IDirectMusic *dmusic; + WCHAR name[MAX_PATH]; + IStream *stream; + DWORD patch; + HRESULT hr; + + port = create_synth_port(&dmusic); + + hr = CoCreateInstance(&CLSID_DirectMusicCollection, NULL, CLSCTX_INPROC_SERVER, + &IID_IDirectMusicCollection, (void **)&collection); + ok(hr == S_OK, "got %#lx\n", hr); + + hr = IDirectMusicCollection_QueryInterface(collection, &IID_IPersistStream, (void **)&persist); + ok(hr == S_OK, "got %#lx\n", hr); + hr = CreateStreamOnHGlobal(0, TRUE, &stream); + ok(hr == S_OK, "got %#lx\n", hr); + + CHUNK_RIFF(stream, "DLS ") + { + DLSHEADER colh = {.cInstruments = 1}; + struct + { + POOLTABLE head; + POOLCUE cues[1]; + } ptbl = + { + .head = {.cbSize = sizeof(POOLTABLE), .cCues = ARRAY_SIZE(ptbl.cues)}, + .cues = {{.ulOffset = 0}}, /* offsets in wvpl */ + }; + + CHUNK_DATA(stream, "colh", colh); + CHUNK_LIST(stream, "lins") + { + CHUNK_LIST(stream, "ins ") + { + INSTHEADER insh = {.cRegions = 1, .Locale = {.ulBank = 0x12, .ulInstrument = 0x34}}; + + CHUNK_DATA(stream, "insh", insh); + CHUNK_LIST(stream, "lrgn") + { + CHUNK_LIST(stream, "rgn ") + { + RGNHEADER rgnh = + { + .RangeKey = {.usLow = 0, .usHigh = 127}, + .RangeVelocity = {.usLow = 1, .usHigh = 127}, + }; + WAVELINK wlnk = {.ulChannel = 1, .ulTableIndex = 0}; + WSMPL wsmp = {.cbSize = sizeof(WSMPL)}; + + CHUNK_DATA(stream, "rgnh", rgnh); + CHUNK_DATA(stream, "wsmp", wsmp); + CHUNK_DATA(stream, "wlnk", wlnk); + } + CHUNK_END; + } + CHUNK_END; + + CHUNK_LIST(stream, "lart") + { + CONNECTIONLIST connections = {.cbSize = sizeof(connections)}; + CHUNK_DATA(stream, "art1", connections); + } + CHUNK_END; + } + CHUNK_END; + } + CHUNK_END; + CHUNK_DATA(stream, "ptbl", ptbl); + CHUNK_LIST(stream, "wvpl") + { + CHUNK_LIST(stream, "wave") + { + WAVEFORMATEX fmt = + { + .wFormatTag = WAVE_FORMAT_PCM, + .nChannels = 1, + .wBitsPerSample = 8, + .nSamplesPerSec = 22050, + .nAvgBytesPerSec = 22050, + .nBlockAlign = 1, + }; + BYTE data[16] = {0}; + + /* native returns DMUS_E_INVALIDOFFSET from DownloadInstrument if data is last */ + CHUNK_DATA(stream, "data", data); + CHUNK_DATA(stream, "fmt ", fmt); + } + CHUNK_END; + } + CHUNK_END; + } + CHUNK_END; + + hr = IStream_Seek(stream, zero, 0, NULL); + ok(hr == S_OK, "got %#lx\n", hr); + hr = IPersistStream_Load(persist, stream); + ok(hr == S_OK, "got %#lx\n", hr); + IPersistStream_Release(persist); + IStream_Release(stream); + + patch = 0xdeadbeef; + wcscpy(name, L"DeadBeef"); + hr = IDirectMusicCollection_EnumInstrument(collection, 0, &patch, name, ARRAY_SIZE(name)); + ok(hr == S_OK, "got %#lx\n", hr); + ok(patch == 0x1234, "got %#lx\n", patch); + ok(*name == 0, "got %s\n", debugstr_w(name)); + hr = IDirectMusicCollection_EnumInstrument(collection, 1, &patch, name, ARRAY_SIZE(name)); + ok(hr == S_FALSE, "got %#lx\n", hr); + + hr = IDirectMusicCollection_GetInstrument(collection, 0x1234, &instrument); + ok(hr == S_OK, "got %#lx\n", hr); + + check_interface(instrument, &IID_IDirectMusicObject, FALSE); + check_interface(instrument, &IID_IDirectMusicDownload, FALSE); + check_interface(instrument, &IID_IDirectMusicDownloadedInstrument, FALSE); + + hr = IDirectMusicPort_DownloadInstrument(port, instrument, &downloaded, NULL, 0); + todo_wine ok(hr == S_OK, "got %#lx\n", hr); + if (hr != S_OK) goto skip_tests; + + check_interface(downloaded, &IID_IDirectMusicObject, FALSE); + check_interface(downloaded, &IID_IDirectMusicDownload, FALSE); + check_interface(downloaded, &IID_IDirectMusicInstrument, FALSE); + + hr = IDirectMusicPort_UnloadInstrument(port, downloaded); + ok(hr == S_OK, "got %#lx\n", hr); + IDirectMusicDownloadedInstrument_Release(downloaded); + + IDirectMusicInstrument_Release(instrument); + +skip_tests: + IDirectMusicCollection_Release(collection); + IDirectMusicPort_Release(port); IDirectMusic_Release(dmusic); }
@@ -1115,6 +1342,7 @@ START_TEST(dmusic) test_master_clock(); test_synthport(); test_port_download(); + test_download_instrument();
CoUninitialize(); }
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmusic/buffer.c | 2 -- dlls/dmusic/clock.c | 2 -- dlls/dmusic/collection.c | 2 -- dlls/dmusic/dmusic.c | 2 -- dlls/dmusic/dmusic_main.c | 21 --------------------- dlls/dmusic/dmusic_private.h | 8 -------- dlls/dmusic/download.c | 2 -- dlls/dmusic/instrument.c | 2 -- dlls/dmusic/port.c | 6 ------ 9 files changed, 47 deletions(-)
diff --git a/dlls/dmusic/buffer.c b/dlls/dmusic/buffer.c index 9aaa1a074b4..a2ad137fe4b 100644 --- a/dlls/dmusic/buffer.c +++ b/dlls/dmusic/buffer.c @@ -71,7 +71,6 @@ static ULONG WINAPI IDirectMusicBufferImpl_Release(LPDIRECTMUSICBUFFER iface) if (!ref) { free(This->data); free(This); - DMUSIC_UnlockModule(); }
return ref; @@ -319,7 +318,6 @@ HRESULT DMUSIC_CreateDirectMusicBufferImpl(LPDMUS_BUFFERDESC desc, LPVOID* ret_i return E_OUTOFMEMORY; }
- DMUSIC_LockModule(); *ret_iface = &dmbuffer->IDirectMusicBuffer_iface;
return S_OK; diff --git a/dlls/dmusic/clock.c b/dlls/dmusic/clock.c index 15a04c844e5..19441d3d56f 100644 --- a/dlls/dmusic/clock.c +++ b/dlls/dmusic/clock.c @@ -63,7 +63,6 @@ static ULONG WINAPI IReferenceClockImpl_Release(IReferenceClock *iface)
if (!ref) { free(This); - DMUSIC_UnlockModule(); }
return ref; @@ -137,7 +136,6 @@ HRESULT DMUSIC_CreateReferenceClockImpl(LPCGUID riid, LPVOID* ret_iface, LPUNKNO clock->rtTime = 0; clock->pClockInfo.dwSize = sizeof (DMUS_CLOCKINFO);
- DMUSIC_LockModule(); hr = IReferenceClockImpl_QueryInterface(&clock->IReferenceClock_iface, riid, ret_iface); IReferenceClock_Release(&clock->IReferenceClock_iface);
diff --git a/dlls/dmusic/collection.c b/dlls/dmusic/collection.c index 0febf9dfd08..3f1c70b01e3 100644 --- a/dlls/dmusic/collection.c +++ b/dlls/dmusic/collection.c @@ -99,7 +99,6 @@ static ULONG WINAPI IDirectMusicCollectionImpl_Release(IDirectMusicCollection *i
if (!ref) { free(This); - DMUSIC_UnlockModule(); }
return ref; @@ -544,7 +543,6 @@ HRESULT DMUSIC_CreateDirectMusicCollectionImpl(REFIID lpcGUID, void **ppobj, IUn
list_init (&obj->Instruments);
- DMUSIC_LockModule(); hr = IDirectMusicCollection_QueryInterface(&obj->IDirectMusicCollection_iface, lpcGUID, ppobj); IDirectMusicCollection_Release(&obj->IDirectMusicCollection_iface);
diff --git a/dlls/dmusic/dmusic.c b/dlls/dmusic/dmusic.c index 8fb35e65809..d284b32fdd7 100644 --- a/dlls/dmusic/dmusic.c +++ b/dlls/dmusic/dmusic.c @@ -201,7 +201,6 @@ static ULONG WINAPI IDirectMusic8Impl_Release(LPDIRECTMUSIC8 iface) free(This->system_ports); free(This->ports); free(This); - DMUSIC_UnlockModule(); }
return ref; @@ -606,7 +605,6 @@ HRESULT DMUSIC_CreateDirectMusicImpl(REFIID riid, void **ret_iface, IUnknown *un
create_system_ports_list(dmusic);
- DMUSIC_LockModule(); ret = IDirectMusic8Impl_QueryInterface(&dmusic->IDirectMusic8_iface, riid, ret_iface); IDirectMusic8_Release(&dmusic->IDirectMusic8_iface);
diff --git a/dlls/dmusic/dmusic_main.c b/dlls/dmusic/dmusic_main.c index 5d4939937a9..509e80f872b 100644 --- a/dlls/dmusic/dmusic_main.c +++ b/dlls/dmusic/dmusic_main.c @@ -39,8 +39,6 @@
WINE_DEFAULT_DEBUG_CHANNEL(dmusic);
-LONG DMUSIC_refCount = 0; - typedef struct { IClassFactory IClassFactory_iface; HRESULT (*fnCreateInstance)(REFIID riid, void **ppv, IUnknown *pUnkOuter); @@ -76,15 +74,11 @@ static HRESULT WINAPI ClassFactory_QueryInterface(IClassFactory *iface, REFIID r
static ULONG WINAPI ClassFactory_AddRef(IClassFactory *iface) { - DMUSIC_LockModule(); - return 2; /* non-heap based object */ }
static ULONG WINAPI ClassFactory_Release(IClassFactory *iface) { - DMUSIC_UnlockModule(); - return 1; /* non-heap based object */ }
@@ -101,12 +95,6 @@ static HRESULT WINAPI ClassFactory_CreateInstance(IClassFactory *iface, IUnknown static HRESULT WINAPI ClassFactory_LockServer(IClassFactory *iface, BOOL dolock) { TRACE("(%d)\n", dolock); - - if (dolock) - DMUSIC_LockModule(); - else - DMUSIC_UnlockModule(); - return S_OK; }
@@ -122,15 +110,6 @@ static IClassFactoryImpl DirectMusic_CF = {{&classfactory_vtbl}, DMUSIC_CreateDi static IClassFactoryImpl Collection_CF = {{&classfactory_vtbl}, DMUSIC_CreateDirectMusicCollectionImpl};
-/****************************************************************** - * DllCanUnloadNow (DMUSIC.@) - * - * - */ -HRESULT WINAPI DllCanUnloadNow(void) -{ - return DMUSIC_refCount != 0 ? S_FALSE : S_OK; -}
/****************************************************************** diff --git a/dlls/dmusic/dmusic_private.h b/dlls/dmusic/dmusic_private.h index d6abf1d1f81..b13780e1886 100644 --- a/dlls/dmusic/dmusic_private.h +++ b/dlls/dmusic/dmusic_private.h @@ -214,14 +214,6 @@ static inline IDirectMusicInstrumentImpl *impl_from_IDirectMusicInstrument(IDire /* custom :) */ extern HRESULT IDirectMusicInstrumentImpl_CustomLoad(IDirectMusicInstrument *iface, IStream *stream);
-/********************************************************************** - * Dll lifetime tracking declaration for dmusic.dll - */ -extern LONG DMUSIC_refCount; -static inline void DMUSIC_LockModule(void) { InterlockedIncrement( &DMUSIC_refCount ); } -static inline void DMUSIC_UnlockModule(void) { InterlockedDecrement( &DMUSIC_refCount ); } - - /***************************************************************************** * Misc. */ diff --git a/dlls/dmusic/download.c b/dlls/dmusic/download.c index 48f0efd5f69..095ea23235b 100644 --- a/dlls/dmusic/download.c +++ b/dlls/dmusic/download.c @@ -65,7 +65,6 @@ static ULONG WINAPI IDirectMusicDownloadImpl_Release(IDirectMusicDownload *iface
if (!ref) { free(This); - DMUSIC_UnlockModule(); }
return ref; @@ -102,6 +101,5 @@ HRESULT DMUSIC_CreateDirectMusicDownloadImpl(const GUID *guid, void **ret_iface, download->ref = 1; *ret_iface = download;
- DMUSIC_LockModule(); return S_OK; } diff --git a/dlls/dmusic/instrument.c b/dlls/dmusic/instrument.c index 7b7ee3def64..767c4419225 100644 --- a/dlls/dmusic/instrument.c +++ b/dlls/dmusic/instrument.c @@ -82,7 +82,6 @@ static ULONG WINAPI IDirectMusicInstrumentImpl_Release(LPDIRECTMUSICINSTRUMENT i free(This->articulations->connections); free(This->articulations); free(This); - DMUSIC_UnlockModule(); }
return ref; @@ -133,7 +132,6 @@ HRESULT DMUSIC_CreateDirectMusicInstrumentImpl (LPCGUID lpcGUID, LPVOID* ppobj, dminst->IDirectMusicInstrument_iface.lpVtbl = &DirectMusicInstrument_Vtbl; dminst->ref = 1;
- DMUSIC_LockModule(); hr = IDirectMusicInstrument_QueryInterface(&dminst->IDirectMusicInstrument_iface, lpcGUID, ppobj); IDirectMusicInstrument_Release(&dminst->IDirectMusicInstrument_iface); diff --git a/dlls/dmusic/port.c b/dlls/dmusic/port.c index 752e3e7bc4b..47137c7878c 100644 --- a/dlls/dmusic/port.c +++ b/dlls/dmusic/port.c @@ -105,7 +105,6 @@ static ULONG WINAPI IDirectMusicDownloadedInstrumentImpl_Release(LPDIRECTMUSICDO { free(This->data); free(This); - DMUSIC_UnlockModule(); }
return ref; @@ -141,7 +140,6 @@ static HRESULT DMUSIC_CreateDirectMusicDownloadedInstrumentImpl(IDirectMusicDown object->ref = 1;
*instrument = &object->IDirectMusicDownloadedInstrument_iface; - DMUSIC_LockModule();
return S_OK; } @@ -178,8 +176,6 @@ static ULONG WINAPI synth_port_AddRef(IDirectMusicPort *iface)
TRACE("(%p): new ref = %lu\n", This, ref);
- DMUSIC_LockModule(); - return ref; }
@@ -204,8 +200,6 @@ static ULONG WINAPI synth_port_Release(IDirectMusicPort *iface) free(This); }
- DMUSIC_UnlockModule(); - return ref; }
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmusic/dmusic_private.h | 3 ++- dlls/dmusic/download.c | 15 +++++---------- dlls/dmusic/port.c | 2 +- 3 files changed, 8 insertions(+), 12 deletions(-)
diff --git a/dlls/dmusic/dmusic_private.h b/dlls/dmusic/dmusic_private.h index b13780e1886..40cb0970173 100644 --- a/dlls/dmusic/dmusic_private.h +++ b/dlls/dmusic/dmusic_private.h @@ -97,10 +97,11 @@ extern HRESULT DMUSIC_CreateDirectMusicCollectionImpl(REFIID riid, void **ppobj,
/* Internal */ extern HRESULT DMUSIC_CreateDirectMusicBufferImpl(LPDMUS_BUFFERDESC desc, LPVOID* ret_iface); -extern HRESULT DMUSIC_CreateDirectMusicDownloadImpl (LPCGUID lpcGUID, LPVOID* ppobj, LPUNKNOWN pUnkOuter); extern HRESULT DMUSIC_CreateReferenceClockImpl (LPCGUID lpcGUID, LPVOID* ppobj, LPUNKNOWN pUnkOuter); extern HRESULT DMUSIC_CreateDirectMusicInstrumentImpl (LPCGUID lpcGUID, LPVOID* ppobj, LPUNKNOWN pUnkOuter);
+extern HRESULT download_create(IDirectMusicDownload **ret_iface); + /***************************************************************************** * IDirectMusic8Impl implementation structure */ diff --git a/dlls/dmusic/download.c b/dlls/dmusic/download.c index 095ea23235b..f7ac8d92ee6 100644 --- a/dlls/dmusic/download.c +++ b/dlls/dmusic/download.c @@ -85,21 +85,16 @@ static const IDirectMusicDownloadVtbl DirectMusicDownload_Vtbl = { IDirectMusicDownloadImpl_GetBuffer };
-/* for ClassFactory */ -HRESULT DMUSIC_CreateDirectMusicDownloadImpl(const GUID *guid, void **ret_iface, IUnknown *unk_outer) +HRESULT download_create(IDirectMusicDownload **ret_iface) { IDirectMusicDownloadImpl *download;
- download = malloc(sizeof(*download)); - if (!download) - { - *ret_iface = NULL; - return E_OUTOFMEMORY; - } - + *ret_iface = NULL; + if (!(download = calloc(1, sizeof(*download)))) return E_OUTOFMEMORY; download->IDirectMusicDownload_iface.lpVtbl = &DirectMusicDownload_Vtbl; download->ref = 1; - *ret_iface = download;
+ TRACE("Created DirectMusicDownload %p\n", download); + *ret_iface = &download->IDirectMusicDownload_iface; return S_OK; } diff --git a/dlls/dmusic/port.c b/dlls/dmusic/port.c index 47137c7878c..7f61e2d1ef7 100644 --- a/dlls/dmusic/port.c +++ b/dlls/dmusic/port.c @@ -582,7 +582,7 @@ static HRESULT WINAPI synth_port_download_GetBuffer(IDirectMusicPortDownload *if if (!IDMDownload) return E_POINTER;
- return DMUSIC_CreateDirectMusicDownloadImpl(&IID_IDirectMusicDownload, (LPVOID*)IDMDownload, NULL); + return download_create(IDMDownload); }
static HRESULT WINAPI synth_port_download_AllocateBuffer(IDirectMusicPortDownload *iface, DWORD size,
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmusic/dmusic_private.h | 12 ------------ dlls/dmusic/download.c | 8 ++++++++ 2 files changed, 8 insertions(+), 12 deletions(-)
diff --git a/dlls/dmusic/dmusic_private.h b/dlls/dmusic/dmusic_private.h index 40cb0970173..d2157288a02 100644 --- a/dlls/dmusic/dmusic_private.h +++ b/dlls/dmusic/dmusic_private.h @@ -47,7 +47,6 @@ typedef struct IDirectMusic8Impl IDirectMusic8Impl; typedef struct IDirectMusicBufferImpl IDirectMusicBufferImpl; typedef struct IDirectMusicDownloadedInstrumentImpl IDirectMusicDownloadedInstrumentImpl; -typedef struct IDirectMusicDownloadImpl IDirectMusicDownloadImpl; typedef struct IReferenceClockImpl IReferenceClockImpl;
typedef struct IDirectMusicInstrumentImpl IDirectMusicInstrumentImpl; @@ -145,17 +144,6 @@ struct IDirectMusicDownloadedInstrumentImpl { void *data; };
-/***************************************************************************** - * IDirectMusicDownloadImpl implementation structure - */ -struct IDirectMusicDownloadImpl { - /* IUnknown fields */ - IDirectMusicDownload IDirectMusicDownload_iface; - LONG ref; - - /* IDirectMusicDownloadImpl fields */ -}; - /** Internal factory */ extern HRESULT synth_port_create(IDirectMusic8Impl *parent, DMUS_PORTPARAMS *port_params, DMUS_PORTCAPS *port_caps, IDirectMusicPort **port); diff --git a/dlls/dmusic/download.c b/dlls/dmusic/download.c index f7ac8d92ee6..fc94cac6a68 100644 --- a/dlls/dmusic/download.c +++ b/dlls/dmusic/download.c @@ -23,6 +23,14 @@
WINE_DEFAULT_DEBUG_CHANNEL(dmusic);
+struct IDirectMusicDownloadImpl +{ + IDirectMusicDownload IDirectMusicDownload_iface; + LONG ref; +}; + +typedef struct IDirectMusicDownloadImpl IDirectMusicDownloadImpl; + static inline IDirectMusicDownloadImpl* impl_from_IDirectMusicDownload(IDirectMusicDownload *iface) { return CONTAINING_RECORD(iface, IDirectMusicDownloadImpl, IDirectMusicDownload_iface);
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmusic/download.c | 37 +++++++++++++++++-------------------- 1 file changed, 17 insertions(+), 20 deletions(-)
diff --git a/dlls/dmusic/download.c b/dlls/dmusic/download.c index fc94cac6a68..9c3f0d6b0cd 100644 --- a/dlls/dmusic/download.c +++ b/dlls/dmusic/download.c @@ -23,21 +23,18 @@
WINE_DEFAULT_DEBUG_CHANNEL(dmusic);
-struct IDirectMusicDownloadImpl +struct download { IDirectMusicDownload IDirectMusicDownload_iface; LONG ref; };
-typedef struct IDirectMusicDownloadImpl IDirectMusicDownloadImpl; - -static inline IDirectMusicDownloadImpl* impl_from_IDirectMusicDownload(IDirectMusicDownload *iface) +static inline struct download *impl_from_IDirectMusicDownload(IDirectMusicDownload *iface) { - return CONTAINING_RECORD(iface, IDirectMusicDownloadImpl, IDirectMusicDownload_iface); + return CONTAINING_RECORD(iface, struct download, IDirectMusicDownload_iface); }
-/* IDirectMusicDownloadImpl IUnknown part: */ -static HRESULT WINAPI IDirectMusicDownloadImpl_QueryInterface(IDirectMusicDownload *iface, REFIID riid, void **ret_iface) +static HRESULT WINAPI download_QueryInterface(IDirectMusicDownload *iface, REFIID riid, void **ret_iface) { TRACE("(%p, %s, %p)\n", iface, debugstr_dmguid(riid), ret_iface);
@@ -54,9 +51,9 @@ static HRESULT WINAPI IDirectMusicDownloadImpl_QueryInterface(IDirectMusicDownlo return E_NOINTERFACE; }
-static ULONG WINAPI IDirectMusicDownloadImpl_AddRef(IDirectMusicDownload *iface) +static ULONG WINAPI download_AddRef(IDirectMusicDownload *iface) { - IDirectMusicDownloadImpl *This = impl_from_IDirectMusicDownload(iface); + struct download *This = impl_from_IDirectMusicDownload(iface); ULONG ref = InterlockedIncrement(&This->ref);
TRACE("(%p): new ref = %lu\n", iface, ref); @@ -64,9 +61,9 @@ static ULONG WINAPI IDirectMusicDownloadImpl_AddRef(IDirectMusicDownload *iface) return ref; }
-static ULONG WINAPI IDirectMusicDownloadImpl_Release(IDirectMusicDownload *iface) +static ULONG WINAPI download_Release(IDirectMusicDownload *iface) { - IDirectMusicDownloadImpl *This = impl_from_IDirectMusicDownload(iface); + struct download *This = impl_from_IDirectMusicDownload(iface); ULONG ref = InterlockedDecrement(&This->ref);
TRACE("(%p): new ref = %lu\n", iface, ref); @@ -78,28 +75,28 @@ static ULONG WINAPI IDirectMusicDownloadImpl_Release(IDirectMusicDownload *iface return ref; }
-/* IDirectMusicDownloadImpl IDirectMusicDownload part: */ -static HRESULT WINAPI IDirectMusicDownloadImpl_GetBuffer(IDirectMusicDownload *iface, void **buffer, DWORD *size) +static HRESULT WINAPI download_GetBuffer(IDirectMusicDownload *iface, void **buffer, DWORD *size) { FIXME("(%p, %p, %p): stub\n", iface, buffer, size);
return S_OK; }
-static const IDirectMusicDownloadVtbl DirectMusicDownload_Vtbl = { - IDirectMusicDownloadImpl_QueryInterface, - IDirectMusicDownloadImpl_AddRef, - IDirectMusicDownloadImpl_Release, - IDirectMusicDownloadImpl_GetBuffer +static const IDirectMusicDownloadVtbl download_vtbl = +{ + download_QueryInterface, + download_AddRef, + download_Release, + download_GetBuffer, };
HRESULT download_create(IDirectMusicDownload **ret_iface) { - IDirectMusicDownloadImpl *download; + struct download *download;
*ret_iface = NULL; if (!(download = calloc(1, sizeof(*download)))) return E_OUTOFMEMORY; - download->IDirectMusicDownload_iface.lpVtbl = &DirectMusicDownload_Vtbl; + download->IDirectMusicDownload_iface.lpVtbl = &download_vtbl; download->ref = 1;
TRACE("Created DirectMusicDownload %p\n", download);
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmusic/port.c | 12 ++++++++++-- dlls/dmusic/tests/dmusic.c | 8 ++++---- 2 files changed, 14 insertions(+), 6 deletions(-)
diff --git a/dlls/dmusic/port.c b/dlls/dmusic/port.c index 7f61e2d1ef7..7cc30b525c1 100644 --- a/dlls/dmusic/port.c +++ b/dlls/dmusic/port.c @@ -40,6 +40,8 @@ struct synth_port { DMUS_PORTPARAMS params; int nrofgroups; DMUSIC_PRIVATE_CHANNEL_GROUP group[1]; + + DWORD next_dlid; };
static inline IDirectMusicDownloadedInstrumentImpl* impl_from_IDirectMusicDownloadedInstrument(IDirectMusicDownloadedInstrument *iface) @@ -595,11 +597,17 @@ static HRESULT WINAPI synth_port_download_AllocateBuffer(IDirectMusicPortDownloa return S_OK; }
-static HRESULT WINAPI synth_port_download_GetDLId(IDirectMusicPortDownload *iface, DWORD *start_DLId, DWORD count) +static HRESULT WINAPI synth_port_download_GetDLId(IDirectMusicPortDownload *iface, DWORD *first, DWORD count) { struct synth_port *This = synth_from_IDirectMusicPortDownload(iface);
- FIXME("(%p/%p, %p, %lu): stub\n", iface, This, start_DLId, count); + TRACE("(%p/%p, %p, %lu)\n", iface, This, first, count); + + if (!first) return E_POINTER; + if (!count) return E_INVALIDARG; + + *first = This->next_dlid; + This->next_dlid += count;
return S_OK; } diff --git a/dlls/dmusic/tests/dmusic.c b/dlls/dmusic/tests/dmusic.c index 6df37e3d63d..05568208fee 100644 --- a/dlls/dmusic/tests/dmusic.c +++ b/dlls/dmusic/tests/dmusic.c @@ -1081,14 +1081,14 @@ static void test_port_download(void)
/* GetDLId allocates the given number of slots and returns only the first */ hr = IDirectMusicPortDownload_GetDLId(port, NULL, 0); - todo_wine ok(hr == E_POINTER, "got %#lx\n", hr); + ok(hr == E_POINTER, "got %#lx\n", hr); hr = IDirectMusicPortDownload_GetDLId(port, ids, 0); - todo_wine ok(hr == E_INVALIDARG, "got %#lx\n", hr); + ok(hr == E_INVALIDARG, "got %#lx\n", hr);
memset(ids, 0xcc, sizeof(ids)); hr = IDirectMusicPortDownload_GetDLId(port, ids, 4); ok(hr == S_OK, "got %#lx\n", hr); - todo_wine ok(ids[0] == 0, "got %#lx\n", ids[0]); + ok(ids[0] == 0, "got %#lx\n", ids[0]); ok(ids[1] == 0xcccccccc, "got %#lx\n", ids[1]);
/* GetBuffer looks up allocated ids to find downloaded buffers */ @@ -1168,7 +1168,7 @@ static void test_port_download(void) /* DLIds are never released */ hr = IDirectMusicPortDownload_GetDLId(port, ids, 1); ok(hr == S_OK, "got %#lx\n", hr); - todo_wine ok(ids[0] == 4, "got %#lx\n", ids[0]); + ok(ids[0] == 4, "got %#lx\n", ids[0]);
IDirectMusicDownload_Release(download);
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmusic/dmusic_private.h | 2 +- dlls/dmusic/download.c | 15 +++++++++++++-- dlls/dmusic/port.c | 11 +++++++---- dlls/dmusic/tests/dmusic.c | 16 +++++++--------- 4 files changed, 28 insertions(+), 16 deletions(-)
diff --git a/dlls/dmusic/dmusic_private.h b/dlls/dmusic/dmusic_private.h index d2157288a02..03c1e6970ee 100644 --- a/dlls/dmusic/dmusic_private.h +++ b/dlls/dmusic/dmusic_private.h @@ -99,7 +99,7 @@ extern HRESULT DMUSIC_CreateDirectMusicBufferImpl(LPDMUS_BUFFERDESC desc, LPVOID extern HRESULT DMUSIC_CreateReferenceClockImpl (LPCGUID lpcGUID, LPVOID* ppobj, LPUNKNOWN pUnkOuter); extern HRESULT DMUSIC_CreateDirectMusicInstrumentImpl (LPCGUID lpcGUID, LPVOID* ppobj, LPUNKNOWN pUnkOuter);
-extern HRESULT download_create(IDirectMusicDownload **ret_iface); +extern HRESULT download_create(DWORD size, IDirectMusicDownload **ret_iface);
/***************************************************************************** * IDirectMusic8Impl implementation structure diff --git a/dlls/dmusic/download.c b/dlls/dmusic/download.c index 9c3f0d6b0cd..1417a7b3efc 100644 --- a/dlls/dmusic/download.c +++ b/dlls/dmusic/download.c @@ -27,8 +27,13 @@ struct download { IDirectMusicDownload IDirectMusicDownload_iface; LONG ref; + + DWORD size; + BYTE data[]; };
+C_ASSERT(sizeof(struct download) == offsetof(struct download, data[0])); + static inline struct download *impl_from_IDirectMusicDownload(IDirectMusicDownload *iface) { return CONTAINING_RECORD(iface, struct download, IDirectMusicDownload_iface); @@ -77,7 +82,12 @@ static ULONG WINAPI download_Release(IDirectMusicDownload *iface)
static HRESULT WINAPI download_GetBuffer(IDirectMusicDownload *iface, void **buffer, DWORD *size) { - FIXME("(%p, %p, %p): stub\n", iface, buffer, size); + struct download *This = impl_from_IDirectMusicDownload(iface); + + TRACE("(%p, %p, %p)\n", iface, buffer, size); + + *buffer = This->data; + *size = This->size;
return S_OK; } @@ -90,7 +100,7 @@ static const IDirectMusicDownloadVtbl download_vtbl = download_GetBuffer, };
-HRESULT download_create(IDirectMusicDownload **ret_iface) +HRESULT download_create(DWORD size, IDirectMusicDownload **ret_iface) { struct download *download;
@@ -98,6 +108,7 @@ HRESULT download_create(IDirectMusicDownload **ret_iface) if (!(download = calloc(1, sizeof(*download)))) return E_OUTOFMEMORY; download->IDirectMusicDownload_iface.lpVtbl = &download_vtbl; download->ref = 1; + download->size = size;
TRACE("Created DirectMusicDownload %p\n", download); *ret_iface = &download->IDirectMusicDownload_iface; diff --git a/dlls/dmusic/port.c b/dlls/dmusic/port.c index 7cc30b525c1..95144a6d905 100644 --- a/dlls/dmusic/port.c +++ b/dlls/dmusic/port.c @@ -584,17 +584,20 @@ static HRESULT WINAPI synth_port_download_GetBuffer(IDirectMusicPortDownload *if if (!IDMDownload) return E_POINTER;
- return download_create(IDMDownload); + return download_create(0, IDMDownload); }
static HRESULT WINAPI synth_port_download_AllocateBuffer(IDirectMusicPortDownload *iface, DWORD size, - IDirectMusicDownload **IDMDownload) + IDirectMusicDownload **download) { struct synth_port *This = synth_from_IDirectMusicPortDownload(iface);
- FIXME("(%p/%p, %lu, %p): stub\n", iface, This, size, IDMDownload); + TRACE("(%p/%p, %lu, %p)\n", iface, This, size, download);
- return S_OK; + if (!download) return E_POINTER; + if (!size) return E_INVALIDARG; + + return download_create(size, download); }
static HRESULT WINAPI synth_port_download_GetDLId(IDirectMusicPortDownload *iface, DWORD *first, DWORD count) diff --git a/dlls/dmusic/tests/dmusic.c b/dlls/dmusic/tests/dmusic.c index 05568208fee..8cfcc11ffd8 100644 --- a/dlls/dmusic/tests/dmusic.c +++ b/dlls/dmusic/tests/dmusic.c @@ -1065,9 +1065,9 @@ static void test_port_download(void)
/* AllocateBuffer use the exact requested size */ hr = IDirectMusicPortDownload_AllocateBuffer(port, 0, NULL); - todo_wine ok(hr == E_POINTER, "got %#lx\n", hr); + ok(hr == E_POINTER, "got %#lx\n", hr); hr = IDirectMusicPortDownload_AllocateBuffer(port, 0, &download); - todo_wine ok(hr == E_INVALIDARG, "got %#lx\n", hr); + ok(hr == E_INVALIDARG, "got %#lx\n", hr);
hr = IDirectMusicPortDownload_AllocateBuffer(port, 1, &download); ok(hr == S_OK, "got %#lx\n", hr); @@ -1075,8 +1075,8 @@ static void test_port_download(void) buffer = invalid_ptr; hr = IDirectMusicDownload_GetBuffer(download, (void **)&buffer, &size); ok(hr == S_OK, "got %#lx\n", hr); - todo_wine ok(size == 1, "got %#lx\n", size); - todo_wine ok(buffer != invalid_ptr, "got %p\n", buffer); + ok(size == 1, "got %#lx\n", size); + ok(buffer != invalid_ptr, "got %p\n", buffer); IDirectMusicDownload_Release(download);
/* GetDLId allocates the given number of slots and returns only the first */ @@ -1107,14 +1107,13 @@ static void test_port_download(void) download = invalid_ptr; hr = IDirectMusicPortDownload_AllocateBuffer(port, sizeof(struct wave_download), &download); ok(hr == S_OK, "got %#lx\n", hr); - todo_wine ok(download != invalid_ptr, "got %p\n", download); - if (download == invalid_ptr) goto skip_tests; + ok(download != invalid_ptr, "got %p\n", download); size = 0xdeadbeef; wave_download = invalid_ptr; hr = IDirectMusicDownload_GetBuffer(download, (void **)&wave_download, &size); ok(hr == S_OK, "got %#lx\n", hr); - todo_wine ok(size == sizeof(struct wave_download), "got %#lx\n", size); - todo_wine ok(wave_download != invalid_ptr, "got %p\n", wave_download); + ok(size == sizeof(struct wave_download), "got %#lx\n", size); + ok(wave_download != invalid_ptr, "got %p\n", wave_download); wave_download->info.cbSize = sizeof(struct wave_download); wave_download->info.dwDLId = 2; wave_download->info.dwDLType = 0; @@ -1172,7 +1171,6 @@ static void test_port_download(void)
IDirectMusicDownload_Release(download);
-skip_tests: IDirectMusicPortDownload_Release(port); }
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmusic/port.c | 70 ++++++++++++++++++++++++++++++++++---- dlls/dmusic/tests/dmusic.c | 6 ++-- 2 files changed, 67 insertions(+), 9 deletions(-)
diff --git a/dlls/dmusic/port.c b/dlls/dmusic/port.c index 95144a6d905..7dc0257c329 100644 --- a/dlls/dmusic/port.c +++ b/dlls/dmusic/port.c @@ -25,6 +25,14 @@
WINE_DEFAULT_DEBUG_CHANNEL(dmusic);
+struct download_entry +{ + struct list entry; + IDirectMusicDownload *download; + HANDLE handle; + DWORD id; +}; + struct synth_port { IDirectMusicPort IDirectMusicPort_iface; IDirectMusicPortDownload IDirectMusicPortDownload_iface; @@ -41,6 +49,7 @@ struct synth_port { int nrofgroups; DMUSIC_PRIVATE_CHANNEL_GROUP group[1];
+ struct list downloads; DWORD next_dlid; };
@@ -190,6 +199,15 @@ static ULONG WINAPI synth_port_Release(IDirectMusicPort *iface)
if (!ref) { + struct download_entry *entry, *next; + + LIST_FOR_EACH_ENTRY_SAFE(entry, next, &This->downloads, struct download_entry, entry) + { + list_remove(&entry->entry); + IDirectMusicDownload_Release(entry->download); + free(entry); + } + dmusic_remove_port(This->parent, iface); IDirectMusicSynthSink_Release(This->synth_sink); IDirectMusicSynth_Activate(This->synth, FALSE); @@ -624,22 +642,61 @@ static HRESULT WINAPI synth_port_download_GetAppend(IDirectMusicPortDownload *if return S_OK; }
-static HRESULT WINAPI synth_port_download_Download(IDirectMusicPortDownload *iface, IDirectMusicDownload *IDMDownload) +static HRESULT WINAPI synth_port_download_Download(IDirectMusicPortDownload *iface, IDirectMusicDownload *download) { struct synth_port *This = synth_from_IDirectMusicPortDownload(iface); + struct download_entry *entry; + DMUS_DOWNLOADINFO *info; + HANDLE handle; + BOOL can_free; + DWORD size; + HRESULT hr;
- FIXME("(%p/%p)->(%p): stub\n", iface, This, IDMDownload); + TRACE("(%p/%p)->(%p)\n", iface, This, download);
- return S_OK; + if (!download) return E_POINTER; + + LIST_FOR_EACH_ENTRY(entry, &This->downloads, struct download_entry, entry) + if (entry->download == download) return DMUS_E_ALREADY_DOWNLOADED; + + if (!(entry = malloc(sizeof(*entry)))) return E_OUTOFMEMORY; + if (SUCCEEDED(hr = IDirectMusicDownload_GetBuffer(download, (void **)&info, &size)) + && SUCCEEDED(hr = IDirectMusicSynth_Download(This->synth, &handle, info, &can_free))) + { + entry->download = download; + IDirectMusicDownload_AddRef(download); + entry->id = info->dwDLId; + entry->handle = handle; + list_add_tail(&This->downloads, &entry->entry); + } + + if (FAILED(hr)) free(entry); + return hr; }
-static HRESULT WINAPI synth_port_download_Unload(IDirectMusicPortDownload *iface, IDirectMusicDownload *IDMDownload) +static HRESULT WINAPI synth_port_download_Unload(IDirectMusicPortDownload *iface, IDirectMusicDownload *download) { struct synth_port *This = synth_from_IDirectMusicPortDownload(iface); + struct download_entry *entry; + HANDLE handle = 0;
- FIXME("(%p/%p)->(%p): stub\n", iface, This, IDMDownload); + TRACE("(%p/%p)->(%p)\n", iface, This, download);
- return S_OK; + if (!download) return E_POINTER; + + LIST_FOR_EACH_ENTRY(entry, &This->downloads, struct download_entry, entry) + { + if (entry->download == download) + { + list_remove(&entry->entry); + IDirectMusicDownload_Release(entry->download); + handle = entry->handle; + free(entry); + break; + } + } + + return IDirectMusicSynth_Unload(This->synth, handle, NULL, NULL); }
static const IDirectMusicPortDownloadVtbl synth_port_download_vtbl = { @@ -795,6 +852,7 @@ HRESULT synth_port_create(IDirectMusic8Impl *parent, DMUS_PORTPARAMS *port_param obj->parent = parent; obj->active = FALSE; obj->params = *port_params; + list_init(&obj->downloads);
hr = CoCreateInstance(&CLSID_DirectMusicSynth, NULL, CLSCTX_INPROC_SERVER, &IID_IDirectMusicSynth, (void **)&obj->synth); diff --git a/dlls/dmusic/tests/dmusic.c b/dlls/dmusic/tests/dmusic.c index 8cfcc11ffd8..13716c096e9 100644 --- a/dlls/dmusic/tests/dmusic.c +++ b/dlls/dmusic/tests/dmusic.c @@ -1122,7 +1122,7 @@ static void test_port_download(void) todo_wine ok(hr == DMUS_E_NOT_DOWNLOADED_TO_PORT, "got %#lx\n", hr);
hr = IDirectMusicPortDownload_Download(port, NULL); - todo_wine ok(hr == E_POINTER, "got %#lx\n", hr); + ok(hr == E_POINTER, "got %#lx\n", hr); hr = IDirectMusicPortDownload_Download(port, download); todo_wine ok(hr == DMUS_E_UNKNOWNDOWNLOAD, "got %#lx\n", hr);
@@ -1145,7 +1145,7 @@ static void test_port_download(void) hr = IDirectMusicPortDownload_Download(port, download); ok(hr == S_OK, "got %#lx\n", hr); hr = IDirectMusicPortDownload_Download(port, download); - todo_wine ok(hr == DMUS_E_ALREADY_DOWNLOADED, "got %#lx\n", hr); + ok(hr == DMUS_E_ALREADY_DOWNLOADED, "got %#lx\n", hr);
tmp_download = invalid_ptr; hr = IDirectMusicPortDownload_GetBuffer(port, 2, &tmp_download); @@ -1154,7 +1154,7 @@ static void test_port_download(void) if (tmp_download != invalid_ptr) IDirectMusicDownload_Release(tmp_download);
hr = IDirectMusicPortDownload_Unload(port, NULL); - todo_wine ok(hr == E_POINTER, "got %#lx\n", hr); + ok(hr == E_POINTER, "got %#lx\n", hr); hr = IDirectMusicPortDownload_Unload(port, download); ok(hr == S_OK, "got %#lx\n", hr);
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmusic/port.c | 23 +++++++++++++++++------ dlls/dmusic/tests/dmusic.c | 14 +++++++------- 2 files changed, 24 insertions(+), 13 deletions(-)
diff --git a/dlls/dmusic/port.c b/dlls/dmusic/port.c index 7dc0257c329..d221fcbc102 100644 --- a/dlls/dmusic/port.c +++ b/dlls/dmusic/port.c @@ -592,17 +592,28 @@ static ULONG WINAPI synth_port_download_Release(IDirectMusicPortDownload *iface) return IDirectMusicPort_Release(&This->IDirectMusicPort_iface); }
-static HRESULT WINAPI synth_port_download_GetBuffer(IDirectMusicPortDownload *iface, DWORD DLId, - IDirectMusicDownload **IDMDownload) +static HRESULT WINAPI synth_port_download_GetBuffer(IDirectMusicPortDownload *iface, DWORD id, + IDirectMusicDownload **download) { struct synth_port *This = synth_from_IDirectMusicPortDownload(iface); + struct download_entry *entry;
- FIXME("(%p/%p, %lu, %p): stub\n", iface, This, DLId, IDMDownload); + TRACE("(%p/%p, %lu, %p)\n", iface, This, id, download);
- if (!IDMDownload) - return E_POINTER; + if (!download) return E_POINTER; + if (id >= This->next_dlid) return DMUS_E_INVALID_DOWNLOADID; + + LIST_FOR_EACH_ENTRY(entry, &This->downloads, struct download_entry, entry) + { + if (entry->id == id) + { + *download = entry->download; + IDirectMusicDownload_AddRef(entry->download); + return S_OK; + } + }
- return download_create(0, IDMDownload); + return DMUS_E_NOT_DOWNLOADED_TO_PORT; }
static HRESULT WINAPI synth_port_download_AllocateBuffer(IDirectMusicPortDownload *iface, DWORD size, diff --git a/dlls/dmusic/tests/dmusic.c b/dlls/dmusic/tests/dmusic.c index 13716c096e9..a8152822613 100644 --- a/dlls/dmusic/tests/dmusic.c +++ b/dlls/dmusic/tests/dmusic.c @@ -1059,9 +1059,9 @@ static void test_port_download(void) hr = IDirectMusicPortDownload_GetBuffer(port, 0, NULL); ok(hr == E_POINTER, "got %#lx\n", hr); hr = IDirectMusicPortDownload_GetBuffer(port, 0, &download); - todo_wine ok(hr == DMUS_E_INVALID_DOWNLOADID, "got %#lx\n", hr); + ok(hr == DMUS_E_INVALID_DOWNLOADID, "got %#lx\n", hr); hr = IDirectMusicPortDownload_GetBuffer(port, 0xdeadbeef, &download); - todo_wine ok(hr == DMUS_E_INVALID_DOWNLOADID, "got %#lx\n", hr); + ok(hr == DMUS_E_INVALID_DOWNLOADID, "got %#lx\n", hr);
/* AllocateBuffer use the exact requested size */ hr = IDirectMusicPortDownload_AllocateBuffer(port, 0, NULL); @@ -1093,7 +1093,7 @@ static void test_port_download(void)
/* GetBuffer looks up allocated ids to find downloaded buffers */ hr = IDirectMusicPortDownload_GetBuffer(port, 2, &download); - todo_wine ok(hr == DMUS_E_NOT_DOWNLOADED_TO_PORT, "got %#lx\n", hr); + ok(hr == DMUS_E_NOT_DOWNLOADED_TO_PORT, "got %#lx\n", hr);
hr = IDirectMusicPortDownload_GetAppend(port, NULL); todo_wine ok(hr == E_POINTER, "got %#lx\n", hr); @@ -1119,7 +1119,7 @@ static void test_port_download(void) wave_download->info.dwDLType = 0; wave_download->info.dwNumOffsetTableEntries = 0; hr = IDirectMusicPortDownload_GetBuffer(port, 2, &tmp_download); - todo_wine ok(hr == DMUS_E_NOT_DOWNLOADED_TO_PORT, "got %#lx\n", hr); + ok(hr == DMUS_E_NOT_DOWNLOADED_TO_PORT, "got %#lx\n", hr);
hr = IDirectMusicPortDownload_Download(port, NULL); ok(hr == E_POINTER, "got %#lx\n", hr); @@ -1150,8 +1150,8 @@ static void test_port_download(void) tmp_download = invalid_ptr; hr = IDirectMusicPortDownload_GetBuffer(port, 2, &tmp_download); ok(hr == S_OK, "got %#lx\n", hr); - todo_wine ok(tmp_download == download, "got %p\n", tmp_download); - if (tmp_download != invalid_ptr) IDirectMusicDownload_Release(tmp_download); + ok(tmp_download == download, "got %p\n", tmp_download); + IDirectMusicDownload_Release(tmp_download);
hr = IDirectMusicPortDownload_Unload(port, NULL); ok(hr == E_POINTER, "got %#lx\n", hr); @@ -1159,7 +1159,7 @@ static void test_port_download(void) ok(hr == S_OK, "got %#lx\n", hr);
hr = IDirectMusicPortDownload_GetBuffer(port, 2, &tmp_download); - todo_wine ok(hr == DMUS_E_NOT_DOWNLOADED_TO_PORT, "got %#lx\n", hr); + ok(hr == DMUS_E_NOT_DOWNLOADED_TO_PORT, "got %#lx\n", hr);
hr = IDirectMusicPortDownload_Unload(port, download); ok(hr == S_OK, "got %#lx\n", hr);
Still getting tricked by the stub returning S_OK... gah.
v2: Initialize pointers to some invalid value to workaround test crashes until the functions get implemented.