-- v2: dmime: Pass the DMUS_PMSG through the performance graph. dmime: Rename DMUS_PMSGToItem to impl_from_DMUS_PMSG. dmime: Remove unnecessary struct message members. dmime: Use a struct list to keep performance messages. dmime: Get rid of the DMUS_PMSGItem typedef. dmime: Convert DMUS_PMSG music and reference times in SendPMsg. dmime/tests: Test that SendPMsg also converts reference time.
From: Rémi Bernon rbernon@codeweavers.com
And avoid checking a possibly freed message. --- dlls/dmime/tests/dmime.c | 109 +++++++++++++++++++++++++++------------ 1 file changed, 77 insertions(+), 32 deletions(-)
diff --git a/dlls/dmime/tests/dmime.c b/dlls/dmime/tests/dmime.c index 26efdd4c72f..00cbd045bd8 100644 --- a/dlls/dmime/tests/dmime.c +++ b/dlls/dmime/tests/dmime.c @@ -1730,9 +1730,10 @@ static void test_performance_pmsg(void) static const DWORD delivery_flags[] = {DMUS_PMSGF_TOOL_IMMEDIATE, DMUS_PMSGF_TOOL_QUEUE, DMUS_PMSGF_TOOL_ATTIME}; static const DWORD message_types[] = {DMUS_PMSGT_MIDI, DMUS_PMSGT_USER}; IDirectMusicPerformance *performance; - IDirectMusicGraph *graph; + IDirectMusicGraph *graph, *performance_graph; IDirectMusicTool *tool; DMUS_PMSG *msg, *clone; + MUSIC_TIME music_time; REFERENCE_TIME time; HRESULT hr; DWORD ret; @@ -1744,6 +1745,8 @@ static void test_performance_pmsg(void) hr = CoCreateInstance(&CLSID_DirectMusicPerformance, NULL, CLSCTX_INPROC_SERVER, &IID_IDirectMusicPerformance, (void **)&performance); ok(hr == S_OK, "got %#lx\n", hr); + hr = IDirectMusicPerformance_QueryInterface(performance, &IID_IDirectMusicGraph, (void **)&performance_graph); + ok(hr == S_OK, "got %#lx\n", hr);
hr = IDirectMusicPerformance_AllocPMsg(performance, 0, NULL); @@ -1826,6 +1829,40 @@ static void test_performance_pmsg(void) ok(hr == S_OK, "got %#lx\n", hr);
+ /* SendPMsg skips all the tools unless messages are stamped beforehand */ + + hr = IDirectMusicPerformance_AllocPMsg(performance, sizeof(DMUS_PMSG), &msg); + ok(hr == S_OK, "got %#lx\n", hr); + ok(msg->dwSize == sizeof(DMUS_PMSG), "got %ld\n", msg->dwSize); + msg->mtTime = 0; + msg->dwFlags = DMUS_PMSGF_MUSICTIME; + msg->dwType = DMUS_PMSGT_USER; + hr = IDirectMusicPerformance_SendPMsg(performance, msg); + ok(hr == S_OK, "got %#lx\n", hr); + + ret = test_tool_wait_message(tool, 10, &msg); + ok(ret == WAIT_TIMEOUT, "got %#lx\n", ret); + ok(!msg, "got %p\n", msg); + + + /* SendPMsg converts music time to reference time if it is missing */ + + hr = IDirectMusicPerformance_AllocPMsg(performance, sizeof(DMUS_PMSG), &msg); + ok(hr == S_OK, "got %#lx\n", hr); + ok(msg->dwSize == sizeof(DMUS_PMSG), "got %ld\n", msg->dwSize); + msg->mtTime = 500; + msg->dwFlags = DMUS_PMSGF_MUSICTIME; + msg->dwType = DMUS_PMSGT_USER; + hr = IDirectMusicGraph_StampPMsg(performance_graph, msg); + ok(hr == S_OK, "got %#lx\n", hr); + hr = IDirectMusicPerformance_SendPMsg(performance, msg); + ok(hr == S_OK, "got %#lx\n", hr); + + ret = test_tool_wait_message(tool, 50, &msg); + todo_wine ok(!ret, "got %#lx\n", ret); + todo_wine ok(msg != NULL, "got %p\n", msg); + if (!msg) goto skip_rtime; + time = 0xdeadbeef; hr = IDirectMusicPerformance_MusicToReferenceTime(performance, msg->mtTime, &time); ok(hr == S_OK, "got %#lx\n", hr); @@ -1833,32 +1870,26 @@ static void test_performance_pmsg(void) todo_wine ok(msg->rtTime == time, "got %I64d\n", msg->rtTime); ok(msg->mtTime == 500, "got %ld\n", msg->mtTime); todo_wine ok(msg->dwFlags & DMUS_PMSGF_REFTIME, "got %#lx\n", msg->dwFlags); + todo_wine ok(msg->dwFlags & DMUS_PMSGF_MUSICTIME, "got %#lx\n", msg->dwFlags); todo_wine ok(msg->dwFlags & (DMUS_PMSGF_TOOL_QUEUE | DMUS_PMSGF_TOOL_IMMEDIATE), "got %#lx\n", msg->dwFlags); ok(!msg->dwPChannel, "got %ld\n", msg->dwPChannel); ok(!msg->dwVirtualTrackID, "got %ld\n", msg->dwVirtualTrackID); - ok(!msg->pTool, "got %p\n", msg->pTool); - ok(!msg->pGraph, "got %p\n", msg->pGraph); - ok(!msg->dwType, "got %#lx\n", msg->dwType); + ok(msg->pTool == tool, "got %p\n", msg->pTool); + ok(msg->pGraph == performance_graph, "got %p\n", msg->pGraph); + ok(msg->dwType == DMUS_PMSGT_USER, "got %#lx\n", msg->dwType); ok(!msg->dwVoiceID, "got %ld\n", msg->dwVoiceID); ok(!msg->dwGroupID, "got %ld\n", msg->dwGroupID); ok(!msg->punkUser, "got %p\n", msg->punkUser);
- - /* SendPMsg skips all the tools unless messages are stamped beforehand */ - - hr = IDirectMusicPerformance_AllocPMsg(performance, sizeof(DMUS_PMSG), &msg); - ok(hr == S_OK, "got %#lx\n", hr); - ok(msg->dwSize == sizeof(DMUS_PMSG), "got %ld\n", msg->dwSize); - msg->rtTime = time; - msg->dwFlags = DMUS_PMSGF_REFTIME; - msg->dwType = DMUS_PMSGT_USER; - hr = IDirectMusicPerformance_SendPMsg(performance, msg); + hr = IDirectMusicPerformance_FreePMsg(performance, msg); ok(hr == S_OK, "got %#lx\n", hr);
- ret = test_tool_wait_message(tool, 10, &msg); - ok(ret == WAIT_TIMEOUT, "got %#lx\n", ret); - ok(!msg, "got %p\n", msg);
+skip_rtime: + /* SendPMsg converts reference time to music time if it is missing */ + + hr = IDirectMusicPerformance_GetTime(performance, &time, &music_time); + ok(hr == S_OK, "got %#lx\n", hr);
hr = IDirectMusicPerformance_AllocPMsg(performance, sizeof(DMUS_PMSG), &msg); ok(hr == S_OK, "got %#lx\n", hr); @@ -1866,24 +1897,39 @@ static void test_performance_pmsg(void) msg->rtTime = time; msg->dwFlags = DMUS_PMSGF_REFTIME; msg->dwType = DMUS_PMSGT_USER; - - hr = IDirectMusicPerformance_QueryInterface(performance, &IID_IDirectMusicGraph, (void **)&graph); + hr = IDirectMusicGraph_StampPMsg(performance_graph, msg); ok(hr == S_OK, "got %#lx\n", hr); - hr = IDirectMusicGraph_StampPMsg(graph, msg); - ok(hr == S_OK, "got %#lx\n", hr); - IDirectMusicGraph_Release(graph); - hr = IDirectMusicPerformance_SendPMsg(performance, msg); ok(hr == S_OK, "got %#lx\n", hr);
ret = test_tool_wait_message(tool, 50, &msg); todo_wine ok(!ret, "got %#lx\n", ret); todo_wine ok(msg != NULL, "got %p\n", msg); - if (!msg) hr = S_OK; - else hr = IDirectMusicPerformance_FreePMsg(performance, msg); + if (!msg) goto skip_mtime; + + music_time = 0xdeadbeef; + hr = IDirectMusicPerformance_ReferenceToMusicTime(performance, msg->rtTime, &music_time); + ok(hr == S_OK, "got %#lx\n", hr); + ok(msg->dwSize == sizeof(DMUS_PMSG), "got %ld\n", msg->dwSize); + todo_wine ok(msg->rtTime == time, "got %I64d\n", msg->rtTime); + todo_wine ok(msg->mtTime == music_time, "got %ld\n", msg->mtTime); + todo_wine ok(msg->dwFlags & DMUS_PMSGF_REFTIME, "got %#lx\n", msg->dwFlags); + todo_wine ok(msg->dwFlags & DMUS_PMSGF_MUSICTIME, "got %#lx\n", msg->dwFlags); + todo_wine ok(msg->dwFlags & (DMUS_PMSGF_TOOL_QUEUE | DMUS_PMSGF_TOOL_IMMEDIATE), "got %#lx\n", msg->dwFlags); + ok(!msg->dwPChannel, "got %ld\n", msg->dwPChannel); + ok(!msg->dwVirtualTrackID, "got %ld\n", msg->dwVirtualTrackID); + ok(msg->pTool == tool, "got %p\n", msg->pTool); + ok(msg->pGraph == performance_graph, "got %p\n", msg->pGraph); + ok(msg->dwType == DMUS_PMSGT_USER, "got %#lx\n", msg->dwType); + ok(!msg->dwVoiceID, "got %ld\n", msg->dwVoiceID); + ok(!msg->dwGroupID, "got %ld\n", msg->dwGroupID); + ok(!msg->punkUser, "got %p\n", msg->punkUser); + + hr = IDirectMusicPerformance_FreePMsg(performance, msg); ok(hr == S_OK, "got %#lx\n", hr);
+skip_mtime: for (i = 0; i < ARRAY_SIZE(delivery_flags); i++) { DWORD duration = 0; @@ -1896,12 +1942,8 @@ static void test_performance_pmsg(void) msg->rtTime = time + 150 * 10000; msg->dwFlags = DMUS_PMSGF_REFTIME; msg->dwType = DMUS_PMSGT_USER; - - hr = IDirectMusicPerformance_QueryInterface(performance, &IID_IDirectMusicGraph, (void **)&graph); - ok(hr == S_OK, "got %#lx\n", hr); - hr = IDirectMusicGraph_StampPMsg(graph, msg); + hr = IDirectMusicGraph_StampPMsg(performance_graph, msg); ok(hr == S_OK, "got %#lx\n", hr); - IDirectMusicGraph_Release(graph);
msg->dwFlags &= ~(DMUS_PMSGF_TOOL_IMMEDIATE | DMUS_PMSGF_TOOL_QUEUE | DMUS_PMSGF_TOOL_ATTIME); msg->dwFlags |= delivery_flags[i]; @@ -1921,8 +1963,8 @@ static void test_performance_pmsg(void) switch (delivery_flags[i]) { case DMUS_PMSGF_TOOL_IMMEDIATE: todo_wine ok(duration <= 50, "got %lu\n", duration); break; - case DMUS_PMSGF_TOOL_QUEUE: todo_wine ok(duration >= 50 && duration <= 100, "got %lu\n", duration); break; - case DMUS_PMSGF_TOOL_ATTIME: todo_wine ok(duration >= 150 && duration <= 500, "got %lu\n", duration); break; + case DMUS_PMSGF_TOOL_QUEUE: todo_wine ok(duration >= 50 && duration <= 125, "got %lu\n", duration); break; + case DMUS_PMSGF_TOOL_ATTIME: todo_wine ok(duration >= 125 && duration <= 500, "got %lu\n", duration); break; } }
@@ -1931,7 +1973,10 @@ static void test_performance_pmsg(void) ok(hr == S_OK, "got %#lx\n", hr);
+ IDirectMusicGraph_Release(performance_graph); + IDirectMusicPerformance_Release(performance); + IDirectMusicTool_Release(tool); }
START_TEST(dmime)
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmime/performance.c | 25 ++++++++++++++++++------- 1 file changed, 18 insertions(+), 7 deletions(-)
diff --git a/dlls/dmime/performance.c b/dlls/dmime/performance.c index b3fd4851d45..c2681c4b150 100644 --- a/dlls/dmime/performance.c +++ b/dlls/dmime/performance.c @@ -74,7 +74,6 @@ struct DMUS_PMSGItem { DMUS_PMSGItem* next; DMUS_PMSGItem* prev;
- REFERENCE_TIME rtItemTime; BOOL bInUse; DWORD cb; DMUS_PMSG pMsg; @@ -141,14 +140,14 @@ static DWORD WINAPI ProcessMsgThread(LPVOID lpParam) { it = it_next; }
- for (it = This->head; NULL != it && it->rtItemTime < rtCurTime + dwDec; ) { + for (it = This->head; NULL != it && it->pMsg.rtTime < rtCurTime + dwDec; ) { it_next = it->next; cur = ProceedMsg(This, it); free(cur); it = it_next; } if (NULL != it) { - timeOut = ( it->rtItemTime - rtCurTime ) + This->rtLatencyTime; + timeOut = ( it->pMsg.rtTime - rtCurTime ) + This->rtLatencyTime; }
outrefresh: @@ -425,11 +424,22 @@ static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS hr = DMUS_E_ALREADY_SENT; else { - /* TODO: Valid Flags */ - /* TODO: DMUS_PMSGF_MUSICTIME */ - message->rtItemTime = msg->rtTime; + if (!(msg->dwFlags & DMUS_PMSGF_MUSICTIME)) + { + if (FAILED(hr = IDirectMusicPerformance8_ReferenceToMusicTime(iface, + msg->rtTime, &msg->mtTime))) + goto done; + msg->dwFlags |= DMUS_PMSGF_MUSICTIME; + } + if (!(msg->dwFlags & DMUS_PMSGF_REFTIME)) + { + if (FAILED(hr = IDirectMusicPerformance8_MusicToReferenceTime(iface, + msg->mtTime, &msg->rtTime))) + goto done; + msg->dwFlags |= DMUS_PMSGF_REFTIME; + }
- for (it = *queue; NULL != it && it->rtItemTime < message->rtItemTime; it = it->next) + for (it = *queue; NULL != it && it->pMsg.rtTime < message->pMsg.rtTime; it = it->next) prev_it = it;
if (!prev_it) @@ -452,6 +462,7 @@ static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS hr = S_OK; }
+done: LeaveCriticalSection(&This->safe);
return hr;
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmime/performance.c | 43 ++++++++++++++++++++-------------------- 1 file changed, 22 insertions(+), 21 deletions(-)
diff --git a/dlls/dmime/performance.c b/dlls/dmime/performance.c index c2681c4b150..786ad817cd4 100644 --- a/dlls/dmime/performance.c +++ b/dlls/dmime/performance.c @@ -62,24 +62,24 @@ struct performance DWORD procThreadId; BOOL procThreadTicStarted; CRITICAL_SECTION safe; - struct DMUS_PMSGItem *head; - struct DMUS_PMSGItem *imm_head; + struct message *head; + struct message *imm_head;
IReferenceClock *master_clock; REFERENCE_TIME init_time; };
-typedef struct DMUS_PMSGItem DMUS_PMSGItem; -struct DMUS_PMSGItem { - DMUS_PMSGItem* next; - DMUS_PMSGItem* prev; +struct message +{ + struct message *next; + struct message *prev;
- BOOL bInUse; - DWORD cb; - DMUS_PMSG pMsg; + BOOL bInUse; + DWORD cb; + DMUS_PMSG pMsg; };
-#define DMUS_PMSGToItem(pMSG) ((DMUS_PMSGItem *)(((unsigned char *)pMSG) - offsetof(DMUS_PMSGItem, pMsg))) +#define DMUS_PMSGToItem(pMSG) ((struct message *)(((unsigned char *)pMSG) - offsetof(struct message, pMsg))) #define DMUS_ItemRemoveFromQueue(This,pItem) \ {\ if (pItem->prev) pItem->prev->next = pItem->next;\ @@ -95,7 +95,8 @@ struct DMUS_PMSGItem { #define PROCESSMSG_ADD (WM_APP + 4)
-static DMUS_PMSGItem* ProceedMsg(struct performance *This, DMUS_PMSGItem* cur) { +static struct message *ProceedMsg(struct performance *This, struct message *cur) +{ if (cur->pMsg.dwType == DMUS_PMSGT_NOTIFICATION) { SetEvent(This->hNotification); } @@ -117,9 +118,9 @@ static DWORD WINAPI ProcessMsgThread(LPVOID lpParam) { MSG msg; HRESULT hr; REFERENCE_TIME rtCurTime; - DMUS_PMSGItem* it = NULL; - DMUS_PMSGItem* cur = NULL; - DMUS_PMSGItem* it_next = NULL; + struct message *it = NULL; + struct message *cur = NULL; + struct message *it_next = NULL;
while (TRUE) { DWORD dwDec = This->rtLatencyTime + This->dwBumperLength; @@ -401,10 +402,10 @@ static HRESULT WINAPI performance_GetBumperLength(IDirectMusicPerformance8 *ifac static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS_PMSG *msg) { struct performance *This = impl_from_IDirectMusicPerformance8(iface); - DMUS_PMSGItem *message; - DMUS_PMSGItem *it = NULL; - DMUS_PMSGItem *prev_it = NULL; - DMUS_PMSGItem **queue; + struct message *message; + struct message *it = NULL; + struct message *prev_it = NULL; + struct message **queue; HRESULT hr;
FIXME("(%p, %p): semi-stub\n", This, msg); @@ -535,14 +536,14 @@ static HRESULT WINAPI performance_GetTime(IDirectMusicPerformance8 *iface, REFER static HRESULT WINAPI performance_AllocPMsg(IDirectMusicPerformance8 *iface, ULONG size, DMUS_PMSG **msg) { struct performance *This = impl_from_IDirectMusicPerformance8(iface); - DMUS_PMSGItem *message; + struct message *message;
TRACE("(%p, %ld, %p)\n", This, size, msg);
if (!msg) return E_POINTER; if (size < sizeof(DMUS_PMSG)) return E_INVALIDARG;
- if (!(message = calloc(1, size - sizeof(DMUS_PMSG) + sizeof(DMUS_PMSGItem)))) return E_OUTOFMEMORY; + if (!(message = calloc(1, size - sizeof(DMUS_PMSG) + sizeof(struct message)))) return E_OUTOFMEMORY; message->pMsg.dwSize = size; *msg = &message->pMsg;
@@ -552,7 +553,7 @@ static HRESULT WINAPI performance_AllocPMsg(IDirectMusicPerformance8 *iface, ULO static HRESULT WINAPI performance_FreePMsg(IDirectMusicPerformance8 *iface, DMUS_PMSG *msg) { struct performance *This = impl_from_IDirectMusicPerformance8(iface); - DMUS_PMSGItem *message; + struct message *message; HRESULT hr;
TRACE("(%p, %p)\n", This, msg);
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmime/performance.c | 79 +++++++++++++--------------------------- 1 file changed, 26 insertions(+), 53 deletions(-)
diff --git a/dlls/dmime/performance.c b/dlls/dmime/performance.c index 786ad817cd4..b3d821d90bc 100644 --- a/dlls/dmime/performance.c +++ b/dlls/dmime/performance.c @@ -62,8 +62,8 @@ struct performance DWORD procThreadId; BOOL procThreadTicStarted; CRITICAL_SECTION safe; - struct message *head; - struct message *imm_head; + struct list immediate_messages; + struct list queued_messages;
IReferenceClock *master_clock; REFERENCE_TIME init_time; @@ -71,23 +71,13 @@ struct performance
struct message { - struct message *next; - struct message *prev; - + struct list entry; BOOL bInUse; DWORD cb; DMUS_PMSG pMsg; };
#define DMUS_PMSGToItem(pMSG) ((struct message *)(((unsigned char *)pMSG) - offsetof(struct message, pMsg))) -#define DMUS_ItemRemoveFromQueue(This,pItem) \ -{\ - if (pItem->prev) pItem->prev->next = pItem->next;\ - if (pItem->next) pItem->next->prev = pItem->prev;\ - if (This->head == pItem) This->head = pItem->next;\ - if (This->imm_head == pItem) This->imm_head = pItem->next;\ - pItem->bInUse = FALSE;\ -}
#define PROCESSMSG_START (WM_APP + 0) #define PROCESSMSG_EXIT (WM_APP + 1) @@ -100,7 +90,8 @@ static struct message *ProceedMsg(struct performance *This, struct message *cur) if (cur->pMsg.dwType == DMUS_PMSGT_NOTIFICATION) { SetEvent(This->hNotification); } - DMUS_ItemRemoveFromQueue(This, cur); + list_remove(&cur->entry); + cur->bInUse = FALSE; switch (cur->pMsg.dwType) { case DMUS_PMSGT_WAVE: case DMUS_PMSGT_TEMPO: @@ -118,9 +109,8 @@ static DWORD WINAPI ProcessMsgThread(LPVOID lpParam) { MSG msg; HRESULT hr; REFERENCE_TIME rtCurTime; - struct message *it = NULL; + struct message *message, *next; struct message *cur = NULL; - struct message *it_next = NULL;
while (TRUE) { DWORD dwDec = This->rtLatencyTime + This->dwBumperLength; @@ -134,21 +124,18 @@ static DWORD WINAPI ProcessMsgThread(LPVOID lpParam) { goto outrefresh; }
- for (it = This->imm_head; NULL != it; ) { - it_next = it->next; - cur = ProceedMsg(This, it); - free(cur); - it = it_next; + LIST_FOR_EACH_ENTRY_SAFE(message, next, &This->immediate_messages, struct message, entry) + { + cur = ProceedMsg(This, message); + free(cur); }
- for (it = This->head; NULL != it && it->pMsg.rtTime < rtCurTime + dwDec; ) { - it_next = it->next; - cur = ProceedMsg(This, it); - free(cur); - it = it_next; - } - if (NULL != it) { - timeOut = ( it->pMsg.rtTime - rtCurTime ) + This->rtLatencyTime; + LIST_FOR_EACH_ENTRY_SAFE(message, next, &This->queued_messages, struct message, entry) + { + timeOut = (message->pMsg.rtTime - rtCurTime) + This->rtLatencyTime; + if (message->pMsg.rtTime >= rtCurTime + dwDec) break; + cur = ProceedMsg(This, message); + free(cur); }
outrefresh: @@ -402,10 +389,8 @@ static HRESULT WINAPI performance_GetBumperLength(IDirectMusicPerformance8 *ifac static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS_PMSG *msg) { struct performance *This = impl_from_IDirectMusicPerformance8(iface); - struct message *message; - struct message *it = NULL; - struct message *prev_it = NULL; - struct message **queue; + struct message *message, *next; + struct list *queue; HRESULT hr;
FIXME("(%p, %p): semi-stub\n", This, msg); @@ -414,8 +399,8 @@ static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS if (!This->dmusic) return DMUS_E_NO_MASTER_CLOCK; if (!(msg->dwFlags & (DMUS_PMSGF_MUSICTIME | DMUS_PMSGF_REFTIME))) return E_INVALIDARG;
- if (msg->dwFlags & DMUS_PMSGF_TOOL_IMMEDIATE) queue = &This->imm_head; - else queue = &This->head; + if (msg->dwFlags & DMUS_PMSGF_TOOL_IMMEDIATE) queue = &This->immediate_messages; + else queue = &This->queued_messages;
message = DMUS_PMSGToItem(msg);
@@ -440,24 +425,9 @@ static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS msg->dwFlags |= DMUS_PMSGF_REFTIME; }
- for (it = *queue; NULL != it && it->pMsg.rtTime < message->pMsg.rtTime; it = it->next) - prev_it = it; - - if (!prev_it) - { - message->prev = NULL; - if (*queue) message->next = (*queue)->next; - /*assert( NULL == message->next->prev );*/ - if (message->next) message->next->prev = message; - *queue = message; - } - else - { - message->prev = prev_it; - message->next = prev_it->next; - prev_it->next = message; - if (message->next) message->next->prev = message; - } + LIST_FOR_EACH_ENTRY(next, queue, struct message, entry) + if (next->pMsg.rtTime >= message->pMsg.rtTime) break; + list_add_before(&next->entry, &message->entry);
message->bInUse = TRUE; hr = S_OK; @@ -1517,6 +1487,9 @@ HRESULT create_dmperformance(REFIID iid, void **ret_iface) obj->safe.DebugInfo->Spare[0] = (DWORD_PTR)(__FILE__ ": performance->safe"); wine_rb_init(&obj->pchannels, pchannel_block_compare);
+ list_init(&obj->immediate_messages); + list_init(&obj->queued_messages); + obj->rtLatencyTime = 100; /* 100 ms TO FIX */ obj->dwBumperLength = 50; /* 50 ms default */ obj->dwPrepareTime = 1000; /* 1000 ms default */
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmime/performance.c | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-)
diff --git a/dlls/dmime/performance.c b/dlls/dmime/performance.c index b3d821d90bc..77089d51709 100644 --- a/dlls/dmime/performance.c +++ b/dlls/dmime/performance.c @@ -72,8 +72,6 @@ struct performance struct message { struct list entry; - BOOL bInUse; - DWORD cb; DMUS_PMSG pMsg; };
@@ -91,7 +89,7 @@ static struct message *ProceedMsg(struct performance *This, struct message *cur) SetEvent(This->hNotification); } list_remove(&cur->entry); - cur->bInUse = FALSE; + list_init(&cur->entry); switch (cur->pMsg.dwType) { case DMUS_PMSGT_WAVE: case DMUS_PMSGT_TEMPO: @@ -406,7 +404,7 @@ static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS
EnterCriticalSection(&This->safe);
- if (message->bInUse) + if (!list_empty(&message->entry)) hr = DMUS_E_ALREADY_SENT; else { @@ -429,7 +427,6 @@ static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS if (next->pMsg.rtTime >= message->pMsg.rtTime) break; list_add_before(&next->entry, &message->entry);
- message->bInUse = TRUE; hr = S_OK; }
@@ -515,6 +512,7 @@ static HRESULT WINAPI performance_AllocPMsg(IDirectMusicPerformance8 *iface, ULO
if (!(message = calloc(1, size - sizeof(DMUS_PMSG) + sizeof(struct message)))) return E_OUTOFMEMORY; message->pMsg.dwSize = size; + list_init(&message->entry); *msg = &message->pMsg;
return S_OK; @@ -532,7 +530,7 @@ static HRESULT WINAPI performance_FreePMsg(IDirectMusicPerformance8 *iface, DMUS message = DMUS_PMSGToItem(msg);
EnterCriticalSection(&This->safe); - hr = message->bInUse ? DMUS_E_CANNOT_FREE : S_OK; + hr = !list_empty(&message->entry) ? DMUS_E_CANNOT_FREE : S_OK; LeaveCriticalSection(&This->safe);
if (SUCCEEDED(hr))
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmime/performance.c | 30 +++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-)
diff --git a/dlls/dmime/performance.c b/dlls/dmime/performance.c index 77089d51709..48c52b15f5c 100644 --- a/dlls/dmime/performance.c +++ b/dlls/dmime/performance.c @@ -72,10 +72,13 @@ struct performance struct message { struct list entry; - DMUS_PMSG pMsg; + DMUS_PMSG msg; };
-#define DMUS_PMSGToItem(pMSG) ((struct message *)(((unsigned char *)pMSG) - offsetof(struct message, pMsg))) +static inline struct message *impl_from_DMUS_PMSG(DMUS_PMSG *msg) +{ + return msg ? CONTAINING_RECORD(msg, struct message, msg) : NULL; +}
#define PROCESSMSG_START (WM_APP + 0) #define PROCESSMSG_EXIT (WM_APP + 1) @@ -85,17 +88,17 @@ struct message
static struct message *ProceedMsg(struct performance *This, struct message *cur) { - if (cur->pMsg.dwType == DMUS_PMSGT_NOTIFICATION) { + if (cur->msg.dwType == DMUS_PMSGT_NOTIFICATION) { SetEvent(This->hNotification); } list_remove(&cur->entry); list_init(&cur->entry); - switch (cur->pMsg.dwType) { + switch (cur->msg.dwType) { case DMUS_PMSGT_WAVE: case DMUS_PMSGT_TEMPO: case DMUS_PMSGT_STOP: default: - FIXME("Unhandled PMsg Type: %#lx\n", cur->pMsg.dwType); + FIXME("Unhandled PMsg Type: %#lx\n", cur->msg.dwType); break; } return cur; @@ -130,8 +133,8 @@ static DWORD WINAPI ProcessMsgThread(LPVOID lpParam) {
LIST_FOR_EACH_ENTRY_SAFE(message, next, &This->queued_messages, struct message, entry) { - timeOut = (message->pMsg.rtTime - rtCurTime) + This->rtLatencyTime; - if (message->pMsg.rtTime >= rtCurTime + dwDec) break; + timeOut = (message->msg.rtTime - rtCurTime) + This->rtLatencyTime; + if (message->msg.rtTime >= rtCurTime + dwDec) break; cur = ProceedMsg(This, message); free(cur); } @@ -393,15 +396,13 @@ static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS
FIXME("(%p, %p): semi-stub\n", This, msg);
- if (!msg) return E_POINTER; + if (!(message = impl_from_DMUS_PMSG(msg))) return E_POINTER; if (!This->dmusic) return DMUS_E_NO_MASTER_CLOCK; if (!(msg->dwFlags & (DMUS_PMSGF_MUSICTIME | DMUS_PMSGF_REFTIME))) return E_INVALIDARG;
if (msg->dwFlags & DMUS_PMSGF_TOOL_IMMEDIATE) queue = &This->immediate_messages; else queue = &This->queued_messages;
- message = DMUS_PMSGToItem(msg); - EnterCriticalSection(&This->safe);
if (!list_empty(&message->entry)) @@ -424,7 +425,7 @@ static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS }
LIST_FOR_EACH_ENTRY(next, queue, struct message, entry) - if (next->pMsg.rtTime >= message->pMsg.rtTime) break; + if (next->msg.rtTime >= message->msg.rtTime) break; list_add_before(&next->entry, &message->entry);
hr = S_OK; @@ -511,9 +512,9 @@ static HRESULT WINAPI performance_AllocPMsg(IDirectMusicPerformance8 *iface, ULO if (size < sizeof(DMUS_PMSG)) return E_INVALIDARG;
if (!(message = calloc(1, size - sizeof(DMUS_PMSG) + sizeof(struct message)))) return E_OUTOFMEMORY; - message->pMsg.dwSize = size; + message->msg.dwSize = size; list_init(&message->entry); - *msg = &message->pMsg; + *msg = &message->msg;
return S_OK; } @@ -526,8 +527,7 @@ static HRESULT WINAPI performance_FreePMsg(IDirectMusicPerformance8 *iface, DMUS
TRACE("(%p, %p)\n", This, msg);
- if (!msg) return E_POINTER; - message = DMUS_PMSGToItem(msg); + if (!(message = impl_from_DMUS_PMSG(msg))) return E_POINTER;
EnterCriticalSection(&This->safe); hr = !list_empty(&message->entry) ? DMUS_E_CANNOT_FREE : S_OK;
From: Rémi Bernon rbernon@codeweavers.com
--- dlls/dmime/performance.c | 203 ++++++++++++++++++++++----------------- dlls/dmime/tests/dmime.c | 42 ++++---- 2 files changed, 133 insertions(+), 112 deletions(-)
diff --git a/dlls/dmime/performance.c b/dlls/dmime/performance.c index 48c52b15f5c..6035d427207 100644 --- a/dlls/dmime/performance.c +++ b/dlls/dmime/performance.c @@ -62,11 +62,10 @@ struct performance DWORD procThreadId; BOOL procThreadTicStarted; CRITICAL_SECTION safe; - struct list immediate_messages; - struct list queued_messages;
IReferenceClock *master_clock; REFERENCE_TIME init_time; + struct list messages; };
struct message @@ -80,99 +79,109 @@ static inline struct message *impl_from_DMUS_PMSG(DMUS_PMSG *msg) return msg ? CONTAINING_RECORD(msg, struct message, msg) : NULL; }
+static HRESULT performance_process_message(struct performance *This, DMUS_PMSG *msg, DWORD *timeout) +{ + static const DWORD delivery_flags = DMUS_PMSGF_TOOL_IMMEDIATE | DMUS_PMSGF_TOOL_QUEUE | DMUS_PMSGF_TOOL_ATTIME; + IDirectMusicPerformance *performance = (IDirectMusicPerformance *)&This->IDirectMusicPerformance8_iface; + HRESULT hr; + + do + { + REFERENCE_TIME current, offset = 0; + IDirectMusicTool *tool; + + if (FAILED(hr = IDirectMusicPerformance_GetTime(performance, ¤t, NULL))) return hr; + if (!(tool = msg->pTool)) tool = &This->IDirectMusicTool_iface; + + switch (msg->dwFlags & delivery_flags) + { + default: + WARN("No delivery flag found for message %p\n", msg); + /* fallthrough */ + case DMUS_PMSGF_TOOL_IMMEDIATE: + hr = IDirectMusicTool_ProcessPMsg(tool, performance, msg); + break; + case DMUS_PMSGF_TOOL_QUEUE: + offset = This->dwBumperLength * 10000; + /* fallthrough */ + case DMUS_PMSGF_TOOL_ATTIME: + if (msg->rtTime >= offset && msg->rtTime - offset >= current) + { + if (timeout) *timeout = (msg->rtTime - offset - current) / 10000; + return DMUS_S_REQUEUE; + } + + hr = IDirectMusicTool_ProcessPMsg(tool, performance, msg); + break; + } + } while (hr == DMUS_S_REQUEUE); + + if (hr == DMUS_S_FREE) hr = IDirectMusicPerformance_FreePMsg(performance, msg); + if (FAILED(hr)) WARN("Failed to process message, hr %#lx\n", hr); + return hr; +} + #define PROCESSMSG_START (WM_APP + 0) #define PROCESSMSG_EXIT (WM_APP + 1) #define PROCESSMSG_REMOVE (WM_APP + 2) #define PROCESSMSG_ADD (WM_APP + 4)
+static DWORD WINAPI ProcessMsgThread(LPVOID lpParam) +{ + struct performance *This = lpParam; + DWORD timeout = INFINITE; + MSG msg; + HRESULT hr; + struct message *message, *next;
-static struct message *ProceedMsg(struct performance *This, struct message *cur) -{ - if (cur->msg.dwType == DMUS_PMSGT_NOTIFICATION) { - SetEvent(This->hNotification); - } - list_remove(&cur->entry); - list_init(&cur->entry); - switch (cur->msg.dwType) { - case DMUS_PMSGT_WAVE: - case DMUS_PMSGT_TEMPO: - case DMUS_PMSGT_STOP: - default: - FIXME("Unhandled PMsg Type: %#lx\n", cur->msg.dwType); - break; - } - return cur; -} + while (TRUE) + { + if (timeout > 0) MsgWaitForMultipleObjects(0, NULL, FALSE, timeout, QS_POSTMESSAGE | QS_SENDMESSAGE | QS_TIMER); + timeout = INFINITE;
-static DWORD WINAPI ProcessMsgThread(LPVOID lpParam) { - struct performance *This = lpParam; - DWORD timeOut = INFINITE; - MSG msg; - HRESULT hr; - REFERENCE_TIME rtCurTime; - struct message *message, *next; - struct message *cur = NULL; + EnterCriticalSection(&This->safe);
- while (TRUE) { - DWORD dwDec = This->rtLatencyTime + This->dwBumperLength; + LIST_FOR_EACH_ENTRY_SAFE(message, next, &This->messages, struct message, entry) + { + list_remove(&message->entry); + list_init(&message->entry);
- if (timeOut > 0) MsgWaitForMultipleObjects(0, NULL, FALSE, timeOut, QS_POSTMESSAGE|QS_SENDMESSAGE|QS_TIMER); - timeOut = INFINITE; + hr = performance_process_message(This, &message->msg, &timeout); + if (hr == DMUS_S_REQUEUE) list_add_before(&next->entry, &message->entry); + if (hr != S_OK) break; + }
- EnterCriticalSection(&This->safe); - hr = IDirectMusicPerformance8_GetTime(&This->IDirectMusicPerformance8_iface, &rtCurTime, NULL); - if (FAILED(hr)) { - goto outrefresh; - } - - LIST_FOR_EACH_ENTRY_SAFE(message, next, &This->immediate_messages, struct message, entry) - { - cur = ProceedMsg(This, message); - free(cur); - } + LeaveCriticalSection(&This->safe);
- LIST_FOR_EACH_ENTRY_SAFE(message, next, &This->queued_messages, struct message, entry) - { - timeOut = (message->msg.rtTime - rtCurTime) + This->rtLatencyTime; - if (message->msg.rtTime >= rtCurTime + dwDec) break; - cur = ProceedMsg(This, message); - free(cur); - } + while (PeekMessageA(&msg, NULL, 0, 0, PM_REMOVE)) + { + /** if hwnd we suppose that is a windows event ... */ + if (NULL != msg.hwnd) + { + TranslateMessage(&msg); + DispatchMessageA(&msg); + } + else + { + switch (msg.message) + { + case WM_QUIT: + case PROCESSMSG_EXIT: goto outofthread; + case PROCESSMSG_START: break; + case PROCESSMSG_ADD: break; + case PROCESSMSG_REMOVE: break; + default: ERR("Unhandled message %u. Critical Path\n", msg.message); break; + } + } + }
-outrefresh: - LeaveCriticalSection(&This->safe); - - while (PeekMessageA(&msg, NULL, 0, 0, PM_REMOVE)) { - /** if hwnd we suppose that is a windows event ... */ - if (NULL != msg.hwnd) { - TranslateMessage(&msg); - DispatchMessageA(&msg); - } else { - switch (msg.message) { - case WM_QUIT: - case PROCESSMSG_EXIT: - goto outofthread; - case PROCESSMSG_START: - break; - case PROCESSMSG_ADD: - break; - case PROCESSMSG_REMOVE: - break; - default: - ERR("Unhandled message %u. Critical Path\n", msg.message); - break; - } - } + /** here we should run a little of current AudioPath */ }
- /** here we should run a little of current AudioPath */ - - } - outofthread: - TRACE("(%p): Exiting\n", This); - - return 0; + TRACE("(%p): Exiting\n", This); + + return 0; }
static BOOL PostMessageToProcessMsgThread(struct performance *This, UINT iMsg) { @@ -389,9 +398,9 @@ static HRESULT WINAPI performance_GetBumperLength(IDirectMusicPerformance8 *ifac
static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS_PMSG *msg) { + const DWORD delivery_flags = DMUS_PMSGF_TOOL_IMMEDIATE | DMUS_PMSGF_TOOL_QUEUE | DMUS_PMSGF_TOOL_ATTIME; struct performance *This = impl_from_IDirectMusicPerformance8(iface); struct message *message, *next; - struct list *queue; HRESULT hr;
FIXME("(%p, %p): semi-stub\n", This, msg); @@ -400,15 +409,13 @@ static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS if (!This->dmusic) return DMUS_E_NO_MASTER_CLOCK; if (!(msg->dwFlags & (DMUS_PMSGF_MUSICTIME | DMUS_PMSGF_REFTIME))) return E_INVALIDARG;
- if (msg->dwFlags & DMUS_PMSGF_TOOL_IMMEDIATE) queue = &This->immediate_messages; - else queue = &This->queued_messages; - EnterCriticalSection(&This->safe);
if (!list_empty(&message->entry)) hr = DMUS_E_ALREADY_SENT; else { + if (!(msg->dwFlags & delivery_flags)) msg->dwFlags |= DMUS_PMSGF_TOOL_IMMEDIATE; if (!(msg->dwFlags & DMUS_PMSGF_MUSICTIME)) { if (FAILED(hr = IDirectMusicPerformance8_ReferenceToMusicTime(iface, @@ -424,9 +431,16 @@ static HRESULT WINAPI performance_SendPMsg(IDirectMusicPerformance8 *iface, DMUS msg->dwFlags |= DMUS_PMSGF_REFTIME; }
- LIST_FOR_EACH_ENTRY(next, queue, struct message, entry) + if (msg->dwFlags & DMUS_PMSGF_TOOL_IMMEDIATE) + { + hr = performance_process_message(This, &message->msg, NULL); + if (hr != DMUS_S_REQUEUE) goto done; + } + + LIST_FOR_EACH_ENTRY(next, &This->messages, struct message, entry) if (next->msg.rtTime >= message->msg.rtTime) break; list_add_before(&next->entry, &message->entry); + PostThreadMessageW(This->procThreadId, PROCESSMSG_ADD, 0, 0);
hr = S_OK; } @@ -1440,8 +1454,20 @@ static HRESULT WINAPI performance_tool_ProcessPMsg(IDirectMusicTool *iface, IDirectMusicPerformance *performance, DMUS_PMSG *msg) { struct performance *This = impl_from_IDirectMusicTool(iface); - FIXME("(%p, %p, %p): stub\n", This, performance, msg); - return E_NOTIMPL; + + FIXME("(%p, %p, %p): semi-stub\n", This, performance, msg); + + switch (msg->dwType) + { + case DMUS_PMSGT_NOTIFICATION: + SetEvent(This->hNotification); + /* fallthrough */ + default: + FIXME("Unhandled message type %#lx\n", msg->dwType); + break; + } + + return DMUS_S_FREE; }
static HRESULT WINAPI performance_tool_Flush(IDirectMusicTool *iface, @@ -1485,8 +1511,7 @@ HRESULT create_dmperformance(REFIID iid, void **ret_iface) obj->safe.DebugInfo->Spare[0] = (DWORD_PTR)(__FILE__ ": performance->safe"); wine_rb_init(&obj->pchannels, pchannel_block_compare);
- list_init(&obj->immediate_messages); - list_init(&obj->queued_messages); + list_init(&obj->messages);
obj->rtLatencyTime = 100; /* 100 ms TO FIX */ obj->dwBumperLength = 50; /* 50 ms default */ diff --git a/dlls/dmime/tests/dmime.c b/dlls/dmime/tests/dmime.c index 00cbd045bd8..89be2c32019 100644 --- a/dlls/dmime/tests/dmime.c +++ b/dlls/dmime/tests/dmime.c @@ -1506,7 +1506,7 @@ static void test_performance_tool(void) hr = IDirectMusicTool_GetMediaTypes(tool, (DWORD **)&types, 64); ok(hr == E_NOTIMPL, "got %#lx\n", hr); hr = IDirectMusicTool_ProcessPMsg(tool, performance, &msg); - todo_wine ok(hr == DMUS_S_FREE, "got %#lx\n", hr); + ok(hr == DMUS_S_FREE, "got %#lx\n", hr); hr = IDirectMusicTool_Flush(tool, performance, &msg, 0); todo_wine ok(hr == S_OK, "got %#lx\n", hr);
@@ -1859,19 +1859,18 @@ static void test_performance_pmsg(void) ok(hr == S_OK, "got %#lx\n", hr);
ret = test_tool_wait_message(tool, 50, &msg); - todo_wine ok(!ret, "got %#lx\n", ret); - todo_wine ok(msg != NULL, "got %p\n", msg); - if (!msg) goto skip_rtime; + ok(!ret, "got %#lx\n", ret); + ok(msg != NULL, "got %p\n", msg);
time = 0xdeadbeef; hr = IDirectMusicPerformance_MusicToReferenceTime(performance, msg->mtTime, &time); ok(hr == S_OK, "got %#lx\n", hr); ok(msg->dwSize == sizeof(DMUS_PMSG), "got %ld\n", msg->dwSize); - todo_wine ok(msg->rtTime == time, "got %I64d\n", msg->rtTime); + ok(msg->rtTime == time, "got %I64d\n", msg->rtTime); ok(msg->mtTime == 500, "got %ld\n", msg->mtTime); - todo_wine ok(msg->dwFlags & DMUS_PMSGF_REFTIME, "got %#lx\n", msg->dwFlags); - todo_wine ok(msg->dwFlags & DMUS_PMSGF_MUSICTIME, "got %#lx\n", msg->dwFlags); - todo_wine ok(msg->dwFlags & (DMUS_PMSGF_TOOL_QUEUE | DMUS_PMSGF_TOOL_IMMEDIATE), "got %#lx\n", msg->dwFlags); + ok(msg->dwFlags & DMUS_PMSGF_REFTIME, "got %#lx\n", msg->dwFlags); + ok(msg->dwFlags & DMUS_PMSGF_MUSICTIME, "got %#lx\n", msg->dwFlags); + ok(msg->dwFlags & (DMUS_PMSGF_TOOL_QUEUE | DMUS_PMSGF_TOOL_IMMEDIATE), "got %#lx\n", msg->dwFlags); ok(!msg->dwPChannel, "got %ld\n", msg->dwPChannel); ok(!msg->dwVirtualTrackID, "got %ld\n", msg->dwVirtualTrackID); ok(msg->pTool == tool, "got %p\n", msg->pTool); @@ -1885,7 +1884,6 @@ static void test_performance_pmsg(void) ok(hr == S_OK, "got %#lx\n", hr);
-skip_rtime: /* SendPMsg converts reference time to music time if it is missing */
hr = IDirectMusicPerformance_GetTime(performance, &time, &music_time); @@ -1903,19 +1901,18 @@ skip_rtime: ok(hr == S_OK, "got %#lx\n", hr);
ret = test_tool_wait_message(tool, 50, &msg); - todo_wine ok(!ret, "got %#lx\n", ret); - todo_wine ok(msg != NULL, "got %p\n", msg); - if (!msg) goto skip_mtime; + ok(!ret, "got %#lx\n", ret); + ok(msg != NULL, "got %p\n", msg);
music_time = 0xdeadbeef; hr = IDirectMusicPerformance_ReferenceToMusicTime(performance, msg->rtTime, &music_time); ok(hr == S_OK, "got %#lx\n", hr); ok(msg->dwSize == sizeof(DMUS_PMSG), "got %ld\n", msg->dwSize); - todo_wine ok(msg->rtTime == time, "got %I64d\n", msg->rtTime); - todo_wine ok(msg->mtTime == music_time, "got %ld\n", msg->mtTime); - todo_wine ok(msg->dwFlags & DMUS_PMSGF_REFTIME, "got %#lx\n", msg->dwFlags); - todo_wine ok(msg->dwFlags & DMUS_PMSGF_MUSICTIME, "got %#lx\n", msg->dwFlags); - todo_wine ok(msg->dwFlags & (DMUS_PMSGF_TOOL_QUEUE | DMUS_PMSGF_TOOL_IMMEDIATE), "got %#lx\n", msg->dwFlags); + ok(msg->rtTime == time, "got %I64d\n", msg->rtTime); + ok(msg->mtTime == music_time, "got %ld\n", msg->mtTime); + ok(msg->dwFlags & DMUS_PMSGF_REFTIME, "got %#lx\n", msg->dwFlags); + ok(msg->dwFlags & DMUS_PMSGF_MUSICTIME, "got %#lx\n", msg->dwFlags); + ok(msg->dwFlags & (DMUS_PMSGF_TOOL_QUEUE | DMUS_PMSGF_TOOL_IMMEDIATE), "got %#lx\n", msg->dwFlags); ok(!msg->dwPChannel, "got %ld\n", msg->dwPChannel); ok(!msg->dwVirtualTrackID, "got %ld\n", msg->dwVirtualTrackID); ok(msg->pTool == tool, "got %p\n", msg->pTool); @@ -1929,7 +1926,6 @@ skip_rtime: ok(hr == S_OK, "got %#lx\n", hr);
-skip_mtime: for (i = 0; i < ARRAY_SIZE(delivery_flags); i++) { DWORD duration = 0; @@ -1953,8 +1949,8 @@ skip_mtime: ok(hr == S_OK, "got %#lx\n", hr); msg = NULL; ret = test_tool_wait_message(tool, 1000, &msg); - todo_wine ok(!ret, "got %#lx\n", ret); - todo_wine ok(msg != NULL, "got %p\n", msg); + ok(!ret, "got %#lx\n", ret); + ok(msg != NULL, "got %p\n", msg); duration += GetTickCount();
if (msg) hr = IDirectMusicPerformance_FreePMsg(performance, msg); @@ -1962,9 +1958,9 @@ skip_mtime:
switch (delivery_flags[i]) { - case DMUS_PMSGF_TOOL_IMMEDIATE: todo_wine ok(duration <= 50, "got %lu\n", duration); break; - case DMUS_PMSGF_TOOL_QUEUE: todo_wine ok(duration >= 50 && duration <= 125, "got %lu\n", duration); break; - case DMUS_PMSGF_TOOL_ATTIME: todo_wine ok(duration >= 125 && duration <= 500, "got %lu\n", duration); break; + case DMUS_PMSGF_TOOL_IMMEDIATE: ok(duration <= 50, "got %lu\n", duration); break; + case DMUS_PMSGF_TOOL_QUEUE: ok(duration >= 50 && duration <= 125, "got %lu\n", duration); break; + case DMUS_PMSGF_TOOL_ATTIME: ok(duration >= 125 && duration <= 500, "got %lu\n", duration); break; } }
v2: Relax a bit the PMSG delays to avoid some spurious failures.
Can you please rename impl_from_DMUS_PMSG? message_from_DMUS_PMSG or msg_from_DMUS_PMSG; or something else, I don't really mind.
"impl" comes from the "Impl" in IFooImpl COM object names / types so would imply we get from a DMUS_PMSG to a COM object.
The rest looks good, though I'm concerned about the test failure: ```dmime.c:1962: Test failed: got 265``` The MR update should rerun the test and we'll see if it was some transient or the test if "flaky" in the pipeline.\ I've rerun the tests 60+ times but could never get it to fail. As that is a timing test I wonder if the CI box was overloaded at that time.
Yeah the CI and testbot often have very high noise. I could probably remove the tests if they prove very flaky, I was interested in checking how the different delivery modes worked but now it's pretty clear. Or maybe see how we can increase the QUEUE vs AT_TIME offset and use larger time differences (though at the cost of run time).