xref: /reactos/base/applications/dxdiag/sound.c (revision 5100859e)
1 /*
2  * PROJECT:     ReactX Diagnosis Application
3  * LICENSE:     LGPL - See COPYING in the top level directory
4  * FILE:        base/applications/dxdiag/sound.c
5  * PURPOSE:     ReactX diagnosis sound page
6  * COPYRIGHT:   Copyright 2008 Johannes Anderwald
7  *
8  */
9 
10 #include "precomp.h"
11 
12 #include <mmsystem.h>
13 #include <mmreg.h>
14 #include <dsound.h>
15 
16 #if 0
17 BOOL
18 GetCatFileFromDriverPath(LPWSTR szFileName, LPWSTR szCatFileName)
19 {
20     GUID VerifyGuid = DRIVER_ACTION_VERIFY;
21     HANDLE hFile;
22     DWORD dwHash;
23     BYTE bHash[100];
24     HCATINFO hCatInfo;
25     HCATADMIN hActAdmin;
26     BOOL bRet = FALSE;
27     CATALOG_INFO CatInfo;
28 
29     /* attempt to open file */
30     hFile = CreateFileW(szFileName, GENERIC_READ,  FILE_SHARE_READ, NULL,  OPEN_EXISTING,  FILE_ATTRIBUTE_NORMAL, NULL);
31     if (hFile == INVALID_HANDLE_VALUE)
32         return FALSE;
33 
34      /* calculate hash from file handle */
35      dwHash = sizeof(bHash);
36      if (!CryptCATAdminCalcHashFromFileHandle(hFile, &dwHash, bHash, 0))
37      {
38         CloseHandle(hFile);
39         return FALSE;
40      }
41 
42     /* try open the CAT admin */
43     if (!CryptCATAdminAcquireContext(&hActAdmin, &VerifyGuid, 0))
44     {
45         CloseHandle(hFile);
46         return FALSE;
47     }
48 
49     /* search catalog to find for catalog containing this hash */
50     hCatInfo = CryptCATAdminEnumCatalogFromHash(hActAdmin, bHash, dwHash, 0, NULL);
51     if (hCatInfo != NULL)
52     {
53         /* theres a catalog get the filename */
54         bRet = CryptCATCatalogInfoFromContext(hCatInfo, &CatInfo, 0);
55         if (bRet)
56            wcscpy(szCatFileName, CatInfo.wszCatalogFile);
57         CryptCATAdminReleaseCatalogContext(hActAdmin, hCatInfo, 0);
58     }
59 
60     /* perform cleanup */
61     CloseHandle(hFile);
62     CryptCATAdminReleaseContext(hActAdmin, 0);
63     return bRet;
64 }
65 
66 BOOL
67 IsDriverWHQL(LPWSTR szFileName)
68 {
69     WCHAR szCatFile[MAX_PATH];
70     HANDLE hCat;
71     BOOL bRet = FALSE;
72 
73     /* get the driver's cat file */
74     if (!GetCatFileFromDriverPath(szFileName, szCatFile))
75     {
76         /* driver has no cat so it's definitely not WHQL signed */
77         return FALSE;
78     }
79 
80     /* open the CAT file */
81     hCat = CryptCATOpen(szCatFile, CRYPTCAT_OPEN_EXISTING, 0, 0, 0);
82     if (hCat == INVALID_HANDLE_VALUE)
83     {
84         /* couldnt open cat */
85         return FALSE;
86     }
87 
88     /* FIXME
89      * build certificate chain with CertGetCertificateChain
90      * verify certificate chain (WinVerifyTrust)
91      * retrieve signer (WTHelperGetProvSignerFromChain)
92      */
93 
94 
95     /* close CAT file */
96     CryptCATClose(hCat);
97     return bRet;
98 }
99 #endif
100 
101 static
102 void
103 SetDeviceDetails(HWND hwndDlg, LPCGUID classGUID, LPCWSTR lpcstrDescription)
104 {
105     HDEVINFO hInfo;
106     DWORD dwIndex = 0;
107     SP_DEVINFO_DATA InfoData;
108     WCHAR szText[30];
109     HWND hDlgCtrls[3];
110     WAVEOUTCAPSW waveOut;
111     UINT numDev;
112     MMRESULT errCode;
113 
114 
115     /*  enumerate waveout devices */
116     numDev = waveOutGetNumDevs();
117     if (numDev)
118     {
119         do
120         {
121                 ZeroMemory(&waveOut, sizeof(waveOut));
122                 errCode = waveOutGetDevCapsW(dwIndex++, &waveOut, sizeof(waveOut));
123                 if (!wcsncmp(lpcstrDescription, waveOut.szPname, min(MAXPNAMELEN, wcslen(waveOut.szPname))))
124                 {
125                     /* set the product id */
126                     SetDlgItemInt(hwndDlg, IDC_STATIC_DSOUND_PRODUCTID, waveOut.wPid, FALSE);
127                     /* set the vendor id */
128                     SetDlgItemInt(hwndDlg, IDC_STATIC_DSOUND_VENDORID, waveOut.wMid, FALSE);
129                     /* check if it's a WDM audio driver */
130                     if (waveOut.wPid == MM_MSFT_WDMAUDIO_WAVEOUT)
131                         SendDlgItemMessageW(hwndDlg, IDC_STATIC_DSOUND_TYPE, WM_SETTEXT, 0, (LPARAM)L"WDM");
132 
133                     /* check if device is default device */
134                     szText[0] = L'\0';
135                     if (dwIndex - 1 == 0) /* FIXME assume default playback device is device 0 */
136                         LoadStringW(hInst, IDS_OPTION_YES, szText, sizeof(szText)/sizeof(WCHAR));
137                     else
138                         LoadStringW(hInst, IDS_OPTION_NO, szText, sizeof(szText)/sizeof(WCHAR));
139 
140                     szText[(sizeof(szText)/sizeof(WCHAR))-1] = L'\0';
141                     /* set default device info */
142                     SendDlgItemMessageW(hwndDlg, IDC_STATIC_DSOUND_STANDARD, WM_SETTEXT, 0, (LPARAM)szText);
143                     break;
144                 }
145                 }while(errCode == MMSYSERR_NOERROR && dwIndex < numDev);
146     }
147 
148     dwIndex = 0;
149     /* create the setup list */
150     hInfo = SetupDiGetClassDevsW(classGUID, NULL, NULL, DIGCF_PRESENT|DIGCF_PROFILE);
151     if (hInfo == INVALID_HANDLE_VALUE)
152         return;
153 
154     do
155     {
156         ZeroMemory(&InfoData, sizeof(InfoData));
157         InfoData.cbSize = sizeof(InfoData);
158 
159         if (SetupDiEnumDeviceInfo(hInfo, dwIndex, &InfoData))
160         {
161             /* set device name */
162             if (SetupDiGetDeviceInstanceId(hInfo, &InfoData, szText, sizeof(szText)/sizeof(WCHAR), NULL))
163                 SendDlgItemMessageW(hwndDlg, IDC_STATIC_DSOUND_DEVICEID, WM_SETTEXT, 0, (LPARAM)szText);
164 
165             /* set the manufacturer name */
166             if (SetupDiGetDeviceRegistryPropertyW(hInfo, &InfoData, SPDRP_MFG, NULL, (PBYTE)szText, sizeof(szText), NULL))
167                 SendDlgItemMessageW(hwndDlg, IDC_STATIC_ADAPTER_PROVIDER, WM_SETTEXT, 0, (LPARAM)szText);
168 
169             /* FIXME
170              * we currently enumerate only the first adapter
171              */
172             hDlgCtrls[0] = GetDlgItem(hwndDlg, IDC_STATIC_DSOUND_DRIVER);
173             hDlgCtrls[1] = GetDlgItem(hwndDlg, IDC_STATIC_DSOUND_VERSION);
174             hDlgCtrls[2] = GetDlgItem(hwndDlg, IDC_STATIC_DSOUND_DATE);
175             EnumerateDrivers(hDlgCtrls, hInfo, &InfoData);
176             break;
177         }
178 
179         if (GetLastError() == ERROR_NO_MORE_ITEMS)
180             break;
181 
182         dwIndex++;
183     }while(TRUE);
184 
185     /* destroy the setup list */
186     SetupDiDestroyDeviceInfoList(hInfo);
187 }
188 
189 
190 
191 BOOL CALLBACK DSEnumCallback(LPGUID lpGuid, LPCWSTR lpcstrDescription, LPCWSTR lpcstrModule, LPVOID lpContext)
192 {
193     PDXDIAG_CONTEXT pContext = (PDXDIAG_CONTEXT)lpContext;
194     HWND * hDlgs;
195     HWND hwndDlg;
196     WCHAR szSound[20];
197     WCHAR szText[30];
198     IDirectSound8 *pObj;
199     HRESULT hResult;
200     DWORD dwCertified;
201 
202     if (!lpGuid)
203         return TRUE;
204 
205     if (pContext->NumSoundAdapter)
206         hDlgs = HeapReAlloc(GetProcessHeap(), 0, pContext->hSoundWnd, (pContext->NumSoundAdapter + 1) * sizeof(HWND));
207     else
208         hDlgs = HeapAlloc(GetProcessHeap(), 0, (pContext->NumSoundAdapter + 1) * sizeof(HWND));
209 
210     if (!hDlgs)
211         return FALSE;
212 
213     pContext->hSoundWnd = hDlgs;
214     hwndDlg = CreateDialogParamW(hInst, MAKEINTRESOURCEW(IDD_SOUND_DIALOG), pContext->hMainDialog, SoundPageWndProc, (LPARAM)pContext); EnableDialogTheme(hwndDlg);
215     if (!hwndDlg)
216         return FALSE;
217 
218     hResult = DirectSoundCreate8(lpGuid, (LPDIRECTSOUND8*)&pObj, NULL);
219     if (hResult == DS_OK)
220     {
221         szText[0] = L'\0';
222         if (IDirectSound8_VerifyCertification(pObj, &dwCertified) == DS_OK)
223         {
224             if (dwCertified == DS_CERTIFIED)
225                 LoadStringW(hInst, IDS_OPTION_YES, szText, sizeof(szText)/sizeof(WCHAR));
226             else if (dwCertified == DS_UNCERTIFIED)
227                 LoadStringW(hInst, IDS_NOT_APPLICABLE, szText, sizeof(szText)/sizeof(WCHAR));
228         }
229         else
230         {
231             LoadStringW(hInst, IDS_OPTION_NO, szText, sizeof(szText)/sizeof(WCHAR));
232         }
233         szText[(sizeof(szText)/sizeof(WCHAR))-1] = L'\0';
234         SendDlgItemMessageW(hwndDlg, IDC_STATIC_DSOUND_LOGO, WM_SETTEXT, 0, (LPARAM)szText);
235         IDirectSound8_Release(pObj);
236     }
237 
238     /* set device name */
239     SendDlgItemMessageW(hwndDlg, IDC_STATIC_DSOUND_NAME, WM_SETTEXT, 0, (LPARAM)lpcstrDescription);
240 
241     /* set range for slider */
242     SendDlgItemMessageW(hwndDlg, IDC_SLIDER_DSOUND, TBM_SETRANGE, TRUE, MAKELONG(0, 3));
243 
244     /* FIXME set correct position */
245     SendDlgItemMessageW(hwndDlg, IDC_SLIDER_DSOUND, TBM_SETSEL, FALSE, 0);
246 
247     /* set further device details */
248     SetDeviceDetails(hwndDlg, &GUID_DEVCLASS_MEDIA, lpcstrDescription);
249 
250     /* load sound resource string */
251     szSound[0] = L'\0';
252     LoadStringW(hInst, IDS_SOUND_DIALOG, szSound, sizeof(szSound)/sizeof(WCHAR));
253     szSound[(sizeof(szSound)/sizeof(WCHAR))-1] = L'\0';
254     /* output the device id */
255     wsprintfW (szText, L"%s %u", szSound, pContext->NumSoundAdapter + 1);
256     /* insert it into general tab */
257     InsertTabCtrlItem(pContext->hTabCtrl, pContext->NumDisplayAdapter + pContext->NumSoundAdapter + 1, szText);
258     /* store dialog window */
259     hDlgs[pContext->NumSoundAdapter] = hwndDlg;
260     pContext->NumSoundAdapter++;
261     return TRUE;
262 }
263 
264 
265 void InitializeDirectSoundPage(PDXDIAG_CONTEXT pContext)
266 {
267     HRESULT hResult;
268 
269 
270     /* create DSound object */
271 
272 //    if (hResult != DS_OK)
273 //        return;
274     hResult = DirectSoundEnumerateW(DSEnumCallback, pContext);
275 
276     /* release the DSound object */
277 //    pObj->lpVtbl->Release(pObj);
278     (void)hResult;
279 }
280 
281 
282 INT_PTR CALLBACK
283 SoundPageWndProc(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
284 {
285     switch (message)
286     {
287         case WM_INITDIALOG:
288         {
289             SetWindowPos(hDlg, NULL, 10, 32, 0, 0, SWP_NOACTIVATE | SWP_NOOWNERZORDER | SWP_NOSIZE | SWP_NOZORDER);
290             return TRUE;
291         }
292         case WM_COMMAND:
293         {
294             if (LOWORD(wParam) == IDC_BUTTON_TESTDSOUND)
295             {
296                 return FALSE;
297             }
298             break;
299         }
300     }
301 
302     return FALSE;
303 }
304