dsound: Properly implement DllCanUnloadNow

Robert Reif reif at earthlink.net
Mon Feb 7 19:00:16 CST 2005


James Hawkins wrote:

>On Mon, 07 Feb 2005 12:37:15 -0500, Robert Reif <reif at earthlink.net> wrote:
>  
>
>>James Hawkins wrote:
>>
>>    
>>
>>>Hi,
>>>
>>>Changelog
>>>* Properly implement DllCanUnloadNow ref counting.
>>>
>>>
>>>
>>>      
>>>
>>dsound.dll is a strange dll that doesn't really follow proper COM
>>reference counting rules for buffers.  This is intentional by Microsoft
>>(don't know why) and was made common by the example code from
>>"Inside Direct X" .
>>
>>You may want to add a test to the dsound.dll regression tests to
>>verify what Microsoft does.
>>
>>    
>>
>
>I've been reading a lot about COM and trying to catch up, but I don't
>know exactly what I need to test.  My guess for what you're looking
>for is to create some buffers and release them all the while keeping
>track of the ref count and when the dll can unload.  Is this close to
>what is needed?  Could you point me in the right direction concerning
>documentation (should I get "Inside Direct X") or examples for the
>tests.  Thanks a lot.
>
>  
>
Something like this is a start:

Only tested on wine but fails because of improper reference counting.  
The interesting
thing will be what happens when a direct sound object is released while 
buffers are still
active.  The reference count goes to zero but can the DLL be unloaded?  
This needs to
be tested on Windows to determine the correct behavior.


-------------- next part --------------
Index: dlls/dsound/tests/dsound8.c
===================================================================
RCS file: /home/wine/wine/dlls/dsound/tests/dsound8.c,v
retrieving revision 1.14
diff -u -r1.14 dsound8.c
--- dlls/dsound/tests/dsound8.c	10 Jan 2005 12:25:56 -0000	1.14
+++ dlls/dsound/tests/dsound8.c	8 Feb 2005 00:51:43 -0000
@@ -37,6 +37,7 @@
 #include "dsound_test.h"
 
 static HRESULT (WINAPI *pDirectSoundCreate8)(LPCGUID,LPDIRECTSOUND8*,LPUNKNOWN)=NULL;
+static HRESULT (WINAPI *pDllCanUnloadNow)(void)=NULL;
 
 static void IDirectSound8_test(LPDIRECTSOUND8 dso, BOOL initialized,
                                LPCGUID lpGuid)
@@ -265,9 +266,17 @@
     if (rc!=DS_OK)
         return rc;
 
+    /* Check if DLL can be unloaded now */
+    rc=pDllCanUnloadNow();
+    ok(rc==S_FALSE, "DllCanUnloadNow() returned %ld, should have returned %ld\n", rc, S_FALSE);
+
     /* Try the enumerated device */
     IDirectSound8_test(dso, TRUE, lpGuid);
 
+    /* Check if DLL can be unloaded now */
+    rc=pDllCanUnloadNow();
+    ok(rc==S_OK, "DllCanUnloadNow() returned %ld, should have returned %ld\n", rc, S_OK);
+
     /* Try the COM class factory method of creation with enumerated device */
     rc=CoCreateInstance(&CLSID_DirectSound8, NULL, CLSCTX_INPROC_SERVER,
                         &IID_IDirectSound8, (void**)&dso);
@@ -356,6 +365,10 @@
     } else
         return rc;
 
+    /* Check if DLL can be unloaded now */
+    rc=pDllCanUnloadNow();
+    ok(rc==S_OK, "DllCanUnloadNow() returned %ld, should have returned %ld\n", rc, S_OK);
+
     return DS_OK;
 }
 
@@ -769,6 +782,7 @@
 START_TEST(dsound8)
 {
     HMODULE hDsound;
+    HRESULT rc;
 
     CoInitialize(NULL);
 
@@ -778,6 +792,14 @@
         return;
     }
 
+    pDllCanUnloadNow = (void*)GetProcAddress(hDsound, "DllCanUnloadNow");
+    ok(pDllCanUnloadNow!=NULL, "GetProcAddress(DllCanUnloadNow) failed\n");
+    if (!pDllCanUnloadNow)
+        return;
+
+    rc=pDllCanUnloadNow();
+    ok(rc==S_OK, "DllCanUnloadNow() returned %ld, should have returned %ld\n", rc, S_OK);
+
     pDirectSoundCreate8 = (void*)GetProcAddress(hDsound, "DirectSoundCreate8");
     if (!pDirectSoundCreate8) {
         trace("dsound8 test skipped\n");
@@ -786,6 +808,9 @@
 
     IDirectSound8_tests();
     dsound8_tests();
+
+    rc=pDllCanUnloadNow();
+    ok(rc==S_OK, "DllCanUnloadNow() returned %ld, should have returned %ld\n", rc, S_OK);
 
     CoUninitialize();
 }


More information about the wine-devel mailing list