Andrew Eikum : mmdevapi: Attempt to determine default devices from the registry.

Alexandre Julliard julliard at winehq.org
Wed Oct 5 18:03:58 CDT 2011


Module: wine
Branch: master
Commit: 66724f617ef8871c91619dbbf8ce12a0e90a6258
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=66724f617ef8871c91619dbbf8ce12a0e90a6258

Author: Andrew Eikum <aeikum at codeweavers.com>
Date:   Wed Oct  5 13:39:53 2011 -0500

mmdevapi: Attempt to determine default devices from the registry.

This uses a new, Wine-specific registry key
<HKCU\Software\Wine\Drivers\wine<driver>.drv> to determine the correct
device to use for the various defaults. The drivers still supply their
own defaults which will be chosen if no registry entry is defined. For
portability we use a driver-specific key in order to support default
devices for each of the driver backends.

---

 dlls/mmdevapi/devenum.c  |   70 ++++++++++++++++++++++++++++++++++++++++++----
 dlls/mmdevapi/main.c     |    7 ++--
 dlls/mmdevapi/mmdevapi.h |    2 +
 3 files changed, 70 insertions(+), 9 deletions(-)

diff --git a/dlls/mmdevapi/devenum.c b/dlls/mmdevapi/devenum.c
index 6b6cfb6..06a1adf 100644
--- a/dlls/mmdevapi/devenum.c
+++ b/dlls/mmdevapi/devenum.c
@@ -909,21 +909,79 @@ static HRESULT WINAPI MMDevEnum_EnumAudioEndpoints(IMMDeviceEnumerator *iface, E
 static HRESULT WINAPI MMDevEnum_GetDefaultAudioEndpoint(IMMDeviceEnumerator *iface, EDataFlow flow, ERole role, IMMDevice **device)
 {
     MMDevEnumImpl *This = impl_from_IMMDeviceEnumerator(iface);
+    WCHAR reg_key[256];
+    HKEY key;
+    HRESULT hr;
+
+    static const WCHAR slashW[] = {'\\',0};
+    static const WCHAR reg_out_nameW[] = {'D','e','f','a','u','l','t','O','u','t','p','u','t',0};
+    static const WCHAR reg_vout_nameW[] = {'D','e','f','a','u','l','t','V','o','i','c','e','O','u','t','p','u','t',0};
+    static const WCHAR reg_in_nameW[] = {'D','e','f','a','u','l','t','I','n','p','u','t',0};
+    static const WCHAR reg_vin_nameW[] = {'D','e','f','a','u','l','t','V','o','i','c','e','I','n','p','u','t',0};
+
     TRACE("(%p)->(%u,%u,%p)\n", This, flow, role, device);
 
     if (!device)
         return E_POINTER;
+
+    if((flow != eRender && flow != eCapture) ||
+            (role != eConsole && role != eMultimedia && role != eCommunications)){
+        WARN("Unknown flow (%u) or role (%u)\n", flow, role);
+        return E_INVALIDARG;
+    }
+
     *device = NULL;
 
+    if(!drvs.module_name[0])
+        return E_NOTFOUND;
+
+    lstrcpyW(reg_key, drv_keyW);
+    lstrcatW(reg_key, slashW);
+    lstrcatW(reg_key, drvs.module_name);
+
+    if(RegOpenKeyW(HKEY_CURRENT_USER, reg_key, &key) == ERROR_SUCCESS){
+        const WCHAR *reg_x_name, *reg_vx_name;
+        WCHAR def_id[256];
+        DWORD size = sizeof(def_id);
+
+        if(flow == eRender){
+            reg_x_name = reg_out_nameW;
+            reg_vx_name = reg_vout_nameW;
+        }else{
+            reg_x_name = reg_in_nameW;
+            reg_vx_name = reg_vin_nameW;
+        }
+
+        if(role == eCommunications &&
+                RegQueryValueExW(key, reg_vx_name, 0, NULL,
+                    (BYTE*)def_id, &size) == ERROR_SUCCESS){
+            hr = IMMDeviceEnumerator_GetDevice(iface, def_id, device);
+            if(SUCCEEDED(hr)){
+                RegCloseKey(key);
+                return S_OK;
+            }
+
+            TRACE("Unable to find voice device %s\n", wine_dbgstr_w(def_id));
+        }
+
+        if(RegQueryValueExW(key, reg_x_name, 0, NULL,
+                    (BYTE*)def_id, &size) == ERROR_SUCCESS){
+            hr = IMMDeviceEnumerator_GetDevice(iface, def_id, device);
+            if(SUCCEEDED(hr)){
+                RegCloseKey(key);
+                return S_OK;
+            }
+
+            TRACE("Unable to find device %s\n", wine_dbgstr_w(def_id));
+        }
+
+        RegCloseKey(key);
+    }
+
     if (flow == eRender)
         *device = &MMDevice_def_play->IMMDevice_iface;
-    else if (flow == eCapture)
-        *device = &MMDevice_def_rec->IMMDevice_iface;
     else
-    {
-        WARN("Unknown flow %u\n", flow);
-        return E_INVALIDARG;
-    }
+        *device = &MMDevice_def_rec->IMMDevice_iface;
 
     if (!*device)
         return E_NOTFOUND;
diff --git a/dlls/mmdevapi/main.c b/dlls/mmdevapi/main.c
index c2c3562..c0e2ff6 100644
--- a/dlls/mmdevapi/main.c
+++ b/dlls/mmdevapi/main.c
@@ -53,6 +53,9 @@ static HINSTANCE instance;
 
 DriverFuncs drvs;
 
+const WCHAR drv_keyW[] = {'S','o','f','t','w','a','r','e','\\',
+    'W','i','n','e','\\','D','r','i','v','e','r','s',0};
+
 static const char *get_priority_string(int prio)
 {
     switch(prio){
@@ -106,8 +109,6 @@ static BOOL load_driver(const WCHAR *name, DriverFuncs *driver)
 
 static BOOL init_driver(void)
 {
-    static const WCHAR drv_key[] = {'S','o','f','t','w','a','r','e','\\',
-        'W','i','n','e','\\','D','r','i','v','e','r','s',0};
     static const WCHAR drv_value[] = {'A','u','d','i','o',0};
 
     static WCHAR default_list[] = {'a','l','s','a',',','o','s','s',',',
@@ -120,7 +121,7 @@ static BOOL init_driver(void)
     if(drvs.module)
         return TRUE;
 
-    if(RegOpenKeyW(HKEY_CURRENT_USER, drv_key, &key) == ERROR_SUCCESS){
+    if(RegOpenKeyW(HKEY_CURRENT_USER, drv_keyW, &key) == ERROR_SUCCESS){
         DWORD size = sizeof(reg_list);
 
         if(RegQueryValueExW(key, drv_value, 0, NULL, (BYTE*)reg_list,
diff --git a/dlls/mmdevapi/mmdevapi.h b/dlls/mmdevapi/mmdevapi.h
index 6ad1ab3..98e0825 100644
--- a/dlls/mmdevapi/mmdevapi.h
+++ b/dlls/mmdevapi/mmdevapi.h
@@ -75,3 +75,5 @@ typedef struct MMDevice {
 
 extern HRESULT AudioClient_Create(MMDevice *parent, IAudioClient **ppv) DECLSPEC_HIDDEN;
 extern HRESULT AudioEndpointVolume_Create(MMDevice *parent, IAudioEndpointVolume **ppv) DECLSPEC_HIDDEN;
+
+extern const WCHAR drv_keyW[] DECLSPEC_HIDDEN;




More information about the wine-cvs mailing list