ReactOS 0.4.16-dev-980-g00983aa
playsound.c
Go to the documentation of this file.
1/* -*- tab-width: 8; c-basic-offset: 4 -*- */
2
3/*
4 * MMSYSTEM functions
5 *
6 * Copyright 1993 Martin Ayotte
7 * 1998-2002 Eric Pouech
8 *
9 * Modified for use with ReactOS by Thamatip Chitpong, 2023
10 *
11 * This library is free software; you can redistribute it and/or
12 * modify it under the terms of the GNU Lesser General Public
13 * License as published by the Free Software Foundation; either
14 * version 2.1 of the License, or (at your option) any later version.
15 *
16 * This library is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
19 * Lesser General Public License for more details.
20 *
21 * You should have received a copy of the GNU Lesser General Public
22 * License along with this library; if not, write to the Free Software
23 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
24 */
25
26#include "winemm.h"
27
28#include <winternl.h>
29#include <userenv.h>
30
32
33typedef struct tagWINE_PLAYSOUND
34{
35 unsigned bLoop : 1;
36 HMMIO hmmio;
37 HWAVEOUT hWave;
39
42
43/* An impersonation-aware equivalent of ExpandEnvironmentStringsW */
45{
46 HANDLE hToken;
47 DWORD dwError;
48 DWORD dwLength = 0;
49
52 TRUE,
53 &hToken))
54 {
55 dwError = GetLastError();
56
57 if (dwError == ERROR_NO_TOKEN)
58 {
59 /* We are not impersonating, forward this to ExpandEnvironmentStrings */
60 return ExpandEnvironmentStringsW(lpSrc, lpDst, nSize);
61 }
62
63 ERR("OpenThreadToken failed (0x%x)\n", dwError);
64 return 0;
65 }
66
67 if (!ExpandEnvironmentStringsForUserW(hToken, lpSrc, lpDst, nSize))
68 {
69 dwError = GetLastError();
70
71 if (dwError == ERROR_INSUFFICIENT_BUFFER || nSize == 0)
72 {
73 /* The buffer is too small, find the required buffer size.
74 * NOTE: ExpandEnvironmentStringsForUser doesn't support retrieving buffer size. */
75 WCHAR szExpanded[1024];
76
77 if (ExpandEnvironmentStringsForUserW(hToken, lpSrc, szExpanded, ARRAY_SIZE(szExpanded)))
78 {
79 /* We success, return the required buffer size */
80 dwLength = lstrlenW(szExpanded) + 1;
81 goto Cleanup;
82 }
83 }
84
85 ERR("ExpandEnvironmentStringsForUser failed (0x%x)\n", dwError);
86 }
87 else
88 {
89 /* We success, return the size of the string */
90 dwLength = lstrlenW(lpDst) + 1;
91 }
92
94 CloseHandle(hToken);
95 return dwLength;
96}
97
98static HMMIO get_mmioFromFile(LPCWSTR lpszName)
99{
100 HMMIO ret;
101 WCHAR buf[256];
103
104 ret = mmioOpenW((LPWSTR)lpszName, NULL,
106 if (ret != 0) return ret;
107 if (SearchPathW(NULL, lpszName, L".wav", ARRAY_SIZE(buf), buf, &dummy))
108 {
109 return mmioOpenW(buf, NULL,
111 }
112 return 0;
113}
114
115static HMMIO get_mmioFromProfile(UINT uFlags, LPCWSTR lpszName)
116{
117 WCHAR str[128];
118 LPWSTR ptr, pszSnd;
119 HMMIO hmmio;
120 HKEY hUserKey, hRegSnd, hRegApp, hScheme, hSnd;
122 BOOL bIsDefault;
123
124 TRACE("searching in SystemSound list for %s\n", debugstr_w(lpszName));
125
126 bIsDefault = (_wcsicmp(lpszName, L"SystemDefault") == 0);
127
128 GetProfileStringW(L"Sounds",
129 bIsDefault ? L"Default" : lpszName,
130 L"",
131 str,
132 ARRAY_SIZE(str));
133 if (!*str)
134 goto Next;
135
136 for (ptr = str; *ptr && *ptr != L','; ptr++);
137
138 if (*ptr)
139 *ptr = UNICODE_NULL;
140
142 if (hmmio)
143 return hmmio;
144
145Next:
146 /* we look up the registry under
147 * HKCU\AppEvents\Schemes\Apps\.Default
148 * HKCU\AppEvents\Schemes\Apps<AppName>
149 */
150 err = RegOpenCurrentUser(KEY_READ, &hUserKey);
151 if (err == ERROR_SUCCESS)
152 {
153 err = RegOpenKeyW(hUserKey, L"AppEvents\\Schemes\\Apps", &hRegSnd);
154 RegCloseKey(hUserKey);
155 }
156
157 if (err != ERROR_SUCCESS)
158 goto None;
159
161 {
162 DWORD len;
163
164 err = ERROR_FILE_NOT_FOUND; /* error */
166 if (len > 0 && len < ARRAY_SIZE(str))
167 {
168 for (ptr = str + lstrlenW(str) - 1; ptr >= str; ptr--)
169 {
170 if (*ptr == L'.')
171 *ptr = UNICODE_NULL;
172
173 if (*ptr == L'\\')
174 {
175 err = RegOpenKeyW(hRegSnd, ptr + 1, &hRegApp);
176 break;
177 }
178 }
179 }
180 }
181 else
182 {
183 err = RegOpenKeyW(hRegSnd, L".Default", &hRegApp);
184 }
185
186 RegCloseKey(hRegSnd);
187
188 if (err != ERROR_SUCCESS)
189 goto None;
190
191 err = RegOpenKeyW(hRegApp,
192 bIsDefault ? L".Default" : lpszName,
193 &hScheme);
194
195 RegCloseKey(hRegApp);
196
197 if (err != ERROR_SUCCESS)
198 goto None;
199
200 err = RegOpenKeyW(hScheme, L".Current", &hSnd);
201
202 RegCloseKey(hScheme);
203
204 if (err != ERROR_SUCCESS)
205 goto None;
206
207 count = sizeof(str);
208 err = RegQueryValueExW(hSnd, NULL, 0, &type, (LPBYTE)str, &count);
209
210 RegCloseKey(hSnd);
211
212 if (err != ERROR_SUCCESS || !*str)
213 goto None;
214
215 if (type == REG_EXPAND_SZ)
216 {
218 if (count == 0)
219 goto None;
220
221 pszSnd = HeapAlloc(GetProcessHeap(), 0, count * sizeof(WCHAR));
222 if (!pszSnd)
223 goto None;
224
226 {
227 HeapFree(GetProcessHeap(), 0, pszSnd);
228 goto None;
229 }
230 }
231 else if (type == REG_SZ)
232 {
233 /* The type is REG_SZ, no need to expand */
234 pszSnd = str;
235 }
236 else
237 {
238 /* Invalid type */
239 goto None;
240 }
241
243
244 if (type == REG_EXPAND_SZ)
245 HeapFree(GetProcessHeap(), 0, pszSnd);
246
247 if (hmmio)
248 return hmmio;
249
250None:
251 WARN("can't find SystemSound=%s !\n", debugstr_w(lpszName));
252 return NULL;
253}
254
255static HMMIO PlaySound_GetMMIO(LPCWSTR pszSound, HMODULE hMod, DWORD fdwSound)
256{
257 BOOL bIsDefault = FALSE;
258 HMMIO hmmio = NULL;
259
260 TRACE("SoundName=%s !\n", debugstr_w(pszSound));
261
262 if (fdwSound & SND_MEMORY)
263 {
264 PVOID data;
265 MMIOINFO mminfo;
266
267 /* NOTE: SND_RESOURCE has the SND_MEMORY bit set */
268 if ((fdwSound & SND_RESOURCE) == SND_RESOURCE)
269 {
270 HRSRC hRes;
271 HGLOBAL hGlob;
272
273 hRes = FindResourceW(hMod, pszSound, L"WAVE");
274 hGlob = LoadResource(hMod, hRes);
275 if (!hRes || !hGlob)
276 goto Quit;
277
278 data = LockResource(hGlob);
279 FreeResource(hGlob);
280 if (!data)
281 goto Quit;
282 }
283 else
284 {
285 data = (PVOID)pszSound;
286 }
287
288 ZeroMemory(&mminfo, sizeof(mminfo));
289 mminfo.fccIOProc = FOURCC_MEM;
290 mminfo.pchBuffer = data;
291 mminfo.cchBuffer = -1; /* FIXME: when a resource, could grab real size */
292
293 TRACE("Memory sound %p\n", data);
294
295 hmmio = mmioOpenW(NULL, &mminfo, MMIO_READ);
296 }
297 else if (fdwSound & SND_ALIAS)
298 {
299 LPCWSTR pszName;
300
301 /* NOTE: SND_ALIAS_ID has the SND_ALIAS bit set */
302 if ((fdwSound & SND_ALIAS_ID) == SND_ALIAS_ID)
303 {
304 if (pszSound == (LPCWSTR)SND_ALIAS_SYSTEMASTERISK)
305 pszName = L"SystemAsterisk";
306 else if (pszSound == (LPCWSTR)SND_ALIAS_SYSTEMDEFAULT)
307 pszName = L"SystemDefault";
308 else if (pszSound == (LPCWSTR)SND_ALIAS_SYSTEMEXCLAMATION)
309 pszName = L"SystemExclamation";
310 else if (pszSound == (LPCWSTR)SND_ALIAS_SYSTEMEXIT)
311 pszName = L"SystemExit";
312 else if (pszSound == (LPCWSTR)SND_ALIAS_SYSTEMHAND)
313 pszName = L"SystemHand";
314 else if (pszSound == (LPCWSTR)SND_ALIAS_SYSTEMQUESTION)
315 pszName = L"SystemQuestion";
316 else if (pszSound == (LPCWSTR)SND_ALIAS_SYSTEMSTART)
317 pszName = L"SystemStart";
318 else if (pszSound == (LPCWSTR)SND_ALIAS_SYSTEMWELCOME)
319 pszName = L"SystemWelcome";
320 else
321 goto Quit;
322 }
323 else
324 {
325 pszName = pszSound;
326 }
327
328 bIsDefault = (_wcsicmp(pszName, L"SystemDefault") == 0);
329 hmmio = get_mmioFromProfile(fdwSound, pszName);
330 }
331 else if (fdwSound & SND_FILENAME)
332 {
333 hmmio = get_mmioFromFile(pszSound);
334 }
335 else
336 {
337 hmmio = get_mmioFromProfile(fdwSound, pszSound);
338 if (!hmmio)
339 hmmio = get_mmioFromFile(pszSound);
340 }
341
342Quit:
343 if (!hmmio && !(fdwSound & SND_NODEFAULT))
344 {
345 if (fdwSound & SND_APPLICATION)
346 {
347 if (!bIsDefault)
348 {
349 /* Find application-defined default sound */
350 hmmio = get_mmioFromProfile(fdwSound, L"SystemDefault");
351 if (hmmio)
352 return hmmio;
353 }
354
355 /* Find system default sound */
356 hmmio = get_mmioFromProfile(fdwSound & ~SND_APPLICATION, L"SystemDefault");
357 }
358 else if (!bIsDefault)
359 {
360 hmmio = get_mmioFromProfile(fdwSound, L"SystemDefault");
361 }
362 }
363
364 return hmmio;
365}
366
368{
371};
372
373static void CALLBACK PlaySound_Callback(HWAVEOUT hwo, UINT uMsg,
374 DWORD_PTR dwInstance,
375 DWORD_PTR dwParam1, DWORD_PTR dwParam2)
376{
377 struct playsound_data* s = (struct playsound_data*)dwInstance;
378
379 switch (uMsg) {
380 case WOM_OPEN:
381 case WOM_CLOSE:
382 break;
383 case WOM_DONE:
384 InterlockedIncrement(&s->dwEventCount);
385 TRACE("Returning waveHdr=%lx\n", dwParam1);
386 SetEvent(s->hEvent);
387 break;
388 default:
389 ERR("Unknown uMsg=%d\n", uMsg);
390 }
391}
392
394{
395 for (;;) {
396 if (InterlockedDecrement(&s->dwEventCount) >= 0) break;
397 InterlockedIncrement(&s->dwEventCount);
398
400 }
401}
402
403static BOOL PlaySound_IsString(DWORD fdwSound, const void* psz)
404{
405 /* SND_RESOURCE is 0x40004 while
406 * SND_MEMORY is 0x00004
407 */
408 switch (fdwSound & (SND_RESOURCE | SND_ALIAS_ID | SND_FILENAME))
409 {
410 case SND_RESOURCE:
411 return HIWORD(psz) != 0; /* by name or by ID ? */
412
413 case SND_ALIAS_ID:
414 case SND_MEMORY:
415 return FALSE;
416
417 case SND_ALIAS:
418 case SND_FILENAME:
419 case 0:
420 return TRUE;
421
422 default:
423 FIXME("WTF\n");
424 return FALSE;
425 }
426}
427
429{
434 if (wps->hmmio) mmioClose(wps->hmmio, 0);
435 HeapFree(GetProcessHeap(), 0, wps);
436}
437
439 DWORD fdwSound, BOOL bUnicode)
440{
441 BOOL bIsString;
442 LPCWSTR pszSoundW;
443 UNICODE_STRING usBuffer;
444 WINE_PLAYSOUND* wps;
445
446 bIsString = PlaySound_IsString(fdwSound, pszSound);
447
448 if (bIsString && !bUnicode)
449 {
450 RtlCreateUnicodeStringFromAsciiz(&usBuffer, pszSound);
451 if (!usBuffer.Buffer)
452 return NULL;
453
454 pszSoundW = usBuffer.Buffer;
455 }
456 else
457 {
458 pszSoundW = pszSound;
459 }
460
461 wps = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*wps));
462 if (wps)
463 {
464 /* construct an MMIO stream (either in memory, or from a file) */
465 wps->hmmio = PlaySound_GetMMIO(pszSoundW, hmod, fdwSound);
466 if (!wps->hmmio)
467 {
468 PlaySound_Free(wps);
469 wps = NULL;
470 }
471 }
472
473 if (bIsString && !bUnicode)
474 RtlFreeUnicodeString(&usBuffer);
475
476 return wps;
477}
478
480{
481 BOOL bRet = FALSE;
482 MMCKINFO ckMainRIFF;
483 MMCKINFO mmckInfo;
484 LPWAVEFORMATEX lpWaveFormat = NULL;
485 HWAVEOUT hWave = 0;
486 LPWAVEHDR waveHdr = NULL;
488 struct playsound_data s;
489 LONG r;
490
491 s.hEvent = 0;
492
493 if (mmioDescend(wps->hmmio, &ckMainRIFF, NULL, 0))
494 goto errCleanUp;
495
496 TRACE("ParentChunk ckid=%.4s fccType=%.4s cksize=%08X\n",
497 (LPSTR)&ckMainRIFF.ckid, (LPSTR)&ckMainRIFF.fccType, ckMainRIFF.cksize);
498
499 if ((ckMainRIFF.ckid != FOURCC_RIFF) ||
500 (ckMainRIFF.fccType != mmioFOURCC('W', 'A', 'V', 'E')))
501 goto errCleanUp;
502
503 mmckInfo.ckid = mmioFOURCC('f', 'm', 't', ' ');
504 if (mmioDescend(wps->hmmio, &mmckInfo, &ckMainRIFF, MMIO_FINDCHUNK))
505 goto errCleanUp;
506
507 TRACE("Chunk Found ckid=%.4s fccType=%08x cksize=%08X\n",
508 (LPSTR)&mmckInfo.ckid, mmckInfo.fccType, mmckInfo.cksize);
509
510 lpWaveFormat = HeapAlloc(GetProcessHeap(), 0, mmckInfo.cksize);
511 if (!lpWaveFormat)
512 goto errCleanUp;
513 r = mmioRead(wps->hmmio, (HPSTR)lpWaveFormat, mmckInfo.cksize);
514 if (r < 0 || r < sizeof(PCMWAVEFORMAT))
515 goto errCleanUp;
516
517 TRACE("wFormatTag=%04X !\n", lpWaveFormat->wFormatTag);
518 TRACE("nChannels=%d\n", lpWaveFormat->nChannels);
519 TRACE("nSamplesPerSec=%d\n", lpWaveFormat->nSamplesPerSec);
520 TRACE("nAvgBytesPerSec=%d\n", lpWaveFormat->nAvgBytesPerSec);
521 TRACE("nBlockAlign=%d\n", lpWaveFormat->nBlockAlign);
522 TRACE("wBitsPerSample=%u !\n", lpWaveFormat->wBitsPerSample);
523
524 /* move to end of 'fmt ' chunk */
525 mmioAscend(wps->hmmio, &mmckInfo, 0);
526
527 mmckInfo.ckid = mmioFOURCC('d', 'a', 't', 'a');
528 if (mmioDescend(wps->hmmio, &mmckInfo, &ckMainRIFF, MMIO_FINDCHUNK))
529 goto errCleanUp;
530
531 TRACE("Chunk Found ckid=%.4s fccType=%08x cksize=%08X\n",
532 (LPSTR)&mmckInfo.ckid, mmckInfo.fccType, mmckInfo.cksize);
533
534 s.hEvent = CreateEventW(NULL, FALSE, FALSE, NULL);
535 if (!s.hEvent || bPlaySoundStop)
536 goto errCleanUp;
537
540 goto errCleanUp;
541
542 /* make it so that 3 buffers per second are needed */
543 bufsize = (((lpWaveFormat->nAvgBytesPerSec / 3) - 1) / lpWaveFormat->nBlockAlign + 1) *
544 lpWaveFormat->nBlockAlign;
545 waveHdr = HeapAlloc(GetProcessHeap(), 0, 2 * sizeof(WAVEHDR) + 2 * bufsize);
546 if (!waveHdr)
547 goto errCleanUp;
548 waveHdr[0].lpData = (char*)waveHdr + 2 * sizeof(WAVEHDR);
549 waveHdr[1].lpData = (char*)waveHdr + 2 * sizeof(WAVEHDR) + bufsize;
550 waveHdr[0].dwUser = waveHdr[1].dwUser = 0L;
551 waveHdr[0].dwLoops = waveHdr[1].dwLoops = 0L;
552 waveHdr[0].dwFlags = waveHdr[1].dwFlags = 0L;
553 waveHdr[0].dwBufferLength = waveHdr[1].dwBufferLength = bufsize;
554 if (waveOutPrepareHeader(hWave, &waveHdr[0], sizeof(WAVEHDR)) ||
555 waveOutPrepareHeader(hWave, &waveHdr[1], sizeof(WAVEHDR))) {
556 goto errCleanUp;
557 }
558
559 wps->hWave = hWave;
560 s.dwEventCount = 1L; /* for first buffer */
561 index = 0;
562
563 do {
564 left = mmckInfo.cksize;
565
566 mmioSeek(wps->hmmio, mmckInfo.dwDataOffset, SEEK_SET);
567 while (left)
568 {
569 if (bPlaySoundStop)
570 {
571 wps->bLoop = FALSE;
572 break;
573 }
574 count = mmioRead(wps->hmmio, waveHdr[index].lpData, min(bufsize, left));
575 if (count < 1) break;
576 left -= count;
577 waveHdr[index].dwBufferLength = count;
578 if (waveOutWrite(hWave, &waveHdr[index], sizeof(WAVEHDR)) == MMSYSERR_NOERROR) {
579 index ^= 1;
581 }
582 else {
583 ERR("Aborting play loop, waveOutWrite error\n");
584 wps->bLoop = FALSE;
585 break;
586 }
587 }
588 bRet = TRUE;
589 } while (wps->bLoop);
590
591 PlaySound_WaitDone(&s); /* to balance first buffer */
593
594 waveOutUnprepareHeader(hWave, &waveHdr[0], sizeof(WAVEHDR));
595 waveOutUnprepareHeader(hWave, &waveHdr[1], sizeof(WAVEHDR));
596
597errCleanUp:
598 TRACE("Done playing sound => %s!\n", bRet ? "ok" : "ko");
599 HeapFree(GetProcessHeap(), 0, lpWaveFormat);
600 if (hWave)
601 {
603 /* the CS prevents a concurrent waveOutReset */
604 wps->hWave = 0;
607 Sleep(100);
608 }
609 CloseHandle(s.hEvent);
610 HeapFree(GetProcessHeap(), 0, waveHdr);
611
612 PlaySound_Free(wps);
613
614 return bRet;
615}
616
618{
619 WINE_PLAYSOUND *wps = (WINE_PLAYSOUND*)lpParameter;
620
621 /* Play the sound */
622 proc_PlaySound(wps);
623
624 return 0;
625}
626
628{
630
631 /* Create a thread to play the sound asynchronously */
633 if (hThread)
634 {
637 return TRUE;
638 }
639
640 /* Error cases */
641 PlaySound_Free(wps);
642 return FALSE;
643}
644
645static BOOL MULTIMEDIA_PlaySound(const void* pszSound, HMODULE hmod, DWORD fdwSound, BOOL bUnicode)
646{
647 WINE_PLAYSOUND* wps = NULL;
648
649 TRACE("pszSound='%p' hmod=%p fdwSound=%08X\n",
650 pszSound, hmod, fdwSound);
651
652 /* SND_NOWAIT is ignored in w95/2k/xp. */
653 if ((fdwSound & SND_NOSTOP) && PlaySoundCurrent != NULL)
654 return FALSE;
655
656 /* alloc internal structure, if we need to play something */
657 if (pszSound && !(fdwSound & SND_PURGE))
658 {
659 if (!(wps = PlaySound_AllocAndGetMMIO(pszSound, hmod, fdwSound, bUnicode)))
660 return FALSE;
661 }
662
664 /* since several threads can enter PlaySound in parallel, we're not
665 * sure, at this point, that another thread didn't start a new playsound
666 */
667 while (PlaySoundCurrent != NULL)
668 {
670 /* FIXME: doc says we have to stop all instances of pszSound if it's non
671 * NULL... as of today, we stop all playing instances */
675
679
681 }
682
683 PlaySoundCurrent = wps;
685
686 if (!wps) return TRUE;
687
688 if (fdwSound & SND_ASYNC)
689 {
690 wps->bLoop = (fdwSound & SND_LOOP) ? TRUE : FALSE;
691
692 return proc_PlaySoundAsync(wps);
693 }
694
695 return proc_PlaySound(wps);
696}
697
698/**************************************************************************
699 * PlaySoundA [WINMM.@]
700 */
702{
703 return MULTIMEDIA_PlaySound(pszSoundA, hmod, fdwSound, FALSE);
704}
705
706/**************************************************************************
707 * PlaySoundW [WINMM.@]
708 */
710{
711 return MULTIMEDIA_PlaySound(pszSoundW, hmod, fdwSound, TRUE);
712}
713
714/**************************************************************************
715 * sndPlaySoundA [WINMM.@]
716 */
718{
720 return MULTIMEDIA_PlaySound(pszSoundA, 0, uFlags, FALSE);
721}
722
723/**************************************************************************
724 * sndPlaySoundW [WINMM.@]
725 */
727{
729 return MULTIMEDIA_PlaySound(pszSound, 0, uFlags, TRUE);
730}
731
732/**************************************************************************
733 * mmsystemGetVersion [WINMM.@]
734 */
736{
737 TRACE("3.10 (Win95?)\n");
738 return 0x030a;
739}
#define InterlockedIncrement
Definition: armddk.h:53
#define InterlockedDecrement
Definition: armddk.h:52
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
Definition: precomp.h:23
#define index(s, c)
Definition: various.h:29
#define ARRAY_SIZE(A)
Definition: main.h:20
@ None
Definition: install.h:14
#define FIXME(fmt,...)
Definition: precomp.h:53
#define WARN(fmt,...)
Definition: precomp.h:61
#define ERR(fmt,...)
Definition: precomp.h:57
#define RegCloseKey(hKey)
Definition: registry.h:49
#define ERROR_INSUFFICIENT_BUFFER
Definition: dderror.h:10
#define ERROR_SUCCESS
Definition: deptool.c:10
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
LONG WINAPI RegOpenCurrentUser(IN REGSAM samDesired, OUT PHKEY phkResult)
Definition: reg.c:3209
LONG WINAPI RegOpenKeyW(HKEY hKey, LPCWSTR lpSubKey, PHKEY phkResult)
Definition: reg.c:3268
LONG WINAPI RegQueryValueExW(_In_ HKEY hkeyorg, _In_ LPCWSTR name, _In_ LPDWORD reserved, _In_ LPDWORD type, _In_ LPBYTE data, _In_ LPDWORD count)
Definition: reg.c:4103
BOOL WINAPI OpenThreadToken(HANDLE ThreadHandle, DWORD DesiredAccess, BOOL OpenAsSelf, HANDLE *TokenHandle)
Definition: security.c:336
UINT uFlags
Definition: api.c:59
#define CloseHandle
Definition: compat.h:739
#define GetProcessHeap()
Definition: compat.h:736
#define HeapAlloc
Definition: compat.h:733
#define HeapFree(x, y, z)
Definition: compat.h:735
#define CALLBACK
Definition: compat.h:35
#define HEAP_ZERO_MEMORY
Definition: compat.h:134
#define lstrlenW
Definition: compat.h:750
static DWORD DWORD * dwLength
Definition: fusion.c:86
DWORD WINAPI ExpandEnvironmentStringsW(IN LPCWSTR lpSrc, IN LPWSTR lpDst, IN DWORD nSize)
Definition: environ.c:519
DWORD WINAPI GetModuleFileNameW(HINSTANCE hModule, LPWSTR lpFilename, DWORD nSize)
Definition: loader.c:600
DWORD WINAPI SearchPathW(IN LPCWSTR lpPath OPTIONAL, IN LPCWSTR lpFileName, IN LPCWSTR lpExtension OPTIONAL, IN DWORD nBufferLength, OUT LPWSTR lpBuffer, OUT LPWSTR *lpFilePart OPTIONAL)
Definition: path.c:1298
BOOL WINAPI SetThreadPriority(IN HANDLE hThread, IN int nPriority)
Definition: thread.c:700
HANDLE WINAPI DECLSPEC_HOTPATCH CreateThread(IN LPSECURITY_ATTRIBUTES lpThreadAttributes, IN DWORD dwStackSize, IN LPTHREAD_START_ROUTINE lpStartAddress, IN LPVOID lpParameter, IN DWORD dwCreationFlags, OUT LPDWORD lpThreadId)
Definition: thread.c:137
INT WINAPI GetProfileStringW(LPCWSTR section, LPCWSTR entry, LPCWSTR def_val, LPWSTR buffer, UINT len)
Definition: profile.c:1267
BOOL WINAPI FreeResource(HGLOBAL handle)
Definition: res.c:559
HRSRC WINAPI FindResourceW(HINSTANCE hModule, LPCWSTR name, LPCWSTR type)
Definition: res.c:176
LPVOID WINAPI LockResource(HGLOBAL handle)
Definition: res.c:550
HGLOBAL WINAPI LoadResource(HINSTANCE hModule, HRSRC hRsrc)
Definition: res.c:532
BOOL WINAPI ExpandEnvironmentStringsForUserW(IN HANDLE hToken, IN LPCWSTR lpSrc, OUT LPWSTR lpDest, IN DWORD dwSize)
Definition: environment.c:743
MMRESULT WINAPI mmioAscend(HMMIO hmmio, LPMMCKINFO lpck, UINT uFlags)
Definition: mmio.c:1205
LONG WINAPI mmioSeek(HMMIO hmmio, LONG lOffset, INT iOrigin)
Definition: mmio.c:836
MMRESULT WINAPI mmioClose(HMMIO hmmio, UINT uFlags)
Definition: mmio.c:702
MMRESULT WINAPI mmioDescend(HMMIO hmmio, LPMMCKINFO lpck, const MMCKINFO *lpckParent, UINT uFlags)
Definition: mmio.c:1107
LONG WINAPI mmioRead(HMMIO hmmio, HPSTR pch, LONG cch)
Definition: mmio.c:733
HMMIO WINAPI mmioOpenW(LPWSTR szFileName, MMIOINFO *lpmmioinfo, DWORD dwOpenFlags)
Definition: mmio.c:670
static const WCHAR Cleanup[]
Definition: register.c:80
#define INFINITE
Definition: serial.h:102
HWAVEOUT hWave
Definition: main.h:78
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
GLuint GLuint GLsizei count
Definition: gl.h:1545
GLuint GLuint GLsizei GLenum type
Definition: gl.h:1545
GLdouble s
Definition: gl.h:2039
GLint GLenum GLsizei GLsizei GLsizei GLint GLsizei const GLvoid * data
Definition: gl.h:1950
GLdouble GLdouble GLdouble r
Definition: gl.h:2055
GLuint index
Definition: glext.h:6031
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: glext.h:7751
GLint left
Definition: glext.h:7726
GLenum GLuint GLsizei bufsize
Definition: glext.h:7473
GLenum GLsizei len
Definition: glext.h:6722
#define SEEK_SET
Definition: jmemansi.c:26
#define debugstr_w
Definition: kernel32.h:32
#define REG_SZ
Definition: layer.c:22
#define WAVERR_STILLPLAYING
Definition: mmsystem.h:177
#define WOM_DONE
Definition: mmsystem.h:183
struct wavehdr_tag WAVEHDR
#define MMIO_ALLOCBUF
Definition: mmsystem.h:532
#define FOURCC_RIFF
Definition: mmsystem.h:564
#define WOM_OPEN
Definition: mmsystem.h:181
#define WOM_CLOSE
Definition: mmsystem.h:182
#define MMIO_FINDCHUNK
Definition: mmsystem.h:551
#define SND_ALIAS_SYSTEMEXCLAMATION
Definition: mmsystem.h:174
#define SND_ALIAS_SYSTEMSTART
Definition: mmsystem.h:172
#define SND_ALIAS_SYSTEMDEFAULT
Definition: mmsystem.h:175
#define SND_ALIAS_SYSTEMHAND
Definition: mmsystem.h:170
#define WAVE_MAPPER
Definition: mmsystem.h:187
#define SND_PURGE
Definition: mmsystem.h:164
#define SND_ALIAS_SYSTEMEXIT
Definition: mmsystem.h:171
#define SND_RESOURCE
Definition: mmsystem.h:163
#define MMIO_DENYWRITE
Definition: mmsystem.h:540
#define SND_ALIAS_SYSTEMWELCOME
Definition: mmsystem.h:173
#define SND_FILENAME
Definition: mmsystem.h:162
#define SND_SYNC
Definition: mmsystem.h:153
#define FOURCC_MEM
Definition: mmsystem.h:567
#define SND_ALIAS_ID
Definition: mmsystem.h:161
#define SND_LOOP
Definition: mmsystem.h:157
#define MMSYSERR_NOERROR
Definition: mmsystem.h:96
#define SND_MEMORY
Definition: mmsystem.h:156
#define SND_ALIAS
Definition: mmsystem.h:160
#define mmioFOURCC(c0, c1, c2, c3)
Definition: mmsystem.h:38
#define SND_ASYNC
Definition: mmsystem.h:154
#define SND_ALIAS_SYSTEMQUESTION
Definition: mmsystem.h:169
#define SND_NOSTOP
Definition: mmsystem.h:158
#define MMIO_READ
Definition: mmsystem.h:535
#define CALLBACK_FUNCTION
Definition: mmsystem.h:150
#define SND_NODEFAULT
Definition: mmsystem.h:155
char * HPSTR
Definition: mmsystem.h:1477
#define SND_APPLICATION
Definition: mmsystem.h:165
#define SND_ALIAS_SYSTEMASTERISK
Definition: mmsystem.h:168
#define ERROR_FILE_NOT_FOUND
Definition: disk.h:79
static PVOID ptr
Definition: dispmode.c:27
static PEXPLICIT_ACCESSW *static HMODULE hmod
Definition: security.c:143
#define min(a, b)
Definition: monoChain.cc:55
unsigned int UINT
Definition: ndis.h:50
NTSYSAPI BOOLEAN NTAPI RtlCreateUnicodeStringFromAsciiz(_Out_ PUNICODE_STRING Destination, _In_ PCSZ Source)
HANDLE hThread
Definition: wizard.c:28
#define KEY_READ
Definition: nt_native.h:1023
NTSYSAPI VOID NTAPI RtlFreeUnicodeString(PUNICODE_STRING UnicodeString)
#define REG_EXPAND_SZ
Definition: nt_native.h:1494
#define UNICODE_NULL
#define L(x)
Definition: ntvdm.h:50
long LONG
Definition: pedump.c:60
BOOL WINAPI sndPlaySoundW(LPCWSTR pszSound, UINT uFlags)
Definition: playsound.c:726
static WINE_PLAYSOUND * PlaySoundCurrent
Definition: playsound.c:40
static DWORD WINAPI PlaySoundAsyncThreadProc(LPVOID lpParameter)
Definition: playsound.c:617
static void CALLBACK PlaySound_Callback(HWAVEOUT hwo, UINT uMsg, DWORD_PTR dwInstance, DWORD_PTR dwParam1, DWORD_PTR dwParam2)
Definition: playsound.c:373
static BOOL proc_PlaySound(WINE_PLAYSOUND *wps)
Definition: playsound.c:479
struct tagWINE_PLAYSOUND WINE_PLAYSOUND
static HMMIO get_mmioFromFile(LPCWSTR lpszName)
Definition: playsound.c:98
BOOL WINAPI PlaySoundW(LPCWSTR pszSoundW, HMODULE hmod, DWORD fdwSound)
Definition: playsound.c:709
UINT WINAPI mmsystemGetVersion(void)
Definition: playsound.c:735
static void PlaySound_Free(WINE_PLAYSOUND *wps)
Definition: playsound.c:428
static BOOL MULTIMEDIA_PlaySound(const void *pszSound, HMODULE hmod, DWORD fdwSound, BOOL bUnicode)
Definition: playsound.c:645
static DWORD PlaySound_ExpandEnvironmentStrings(LPCWSTR lpSrc, LPWSTR lpDst, DWORD nSize)
Definition: playsound.c:44
static WINE_PLAYSOUND * PlaySound_AllocAndGetMMIO(const void *pszSound, HMODULE hmod, DWORD fdwSound, BOOL bUnicode)
Definition: playsound.c:438
BOOL WINAPI sndPlaySoundA(LPCSTR pszSoundA, UINT uFlags)
Definition: playsound.c:717
static HMMIO PlaySound_GetMMIO(LPCWSTR pszSound, HMODULE hMod, DWORD fdwSound)
Definition: playsound.c:255
BOOL WINAPI PlaySoundA(LPCSTR pszSoundA, HMODULE hmod, DWORD fdwSound)
Definition: playsound.c:701
static BOOL bPlaySoundStop
Definition: playsound.c:41
static void PlaySound_WaitDone(struct playsound_data *s)
Definition: playsound.c:393
static BOOL proc_PlaySoundAsync(WINE_PLAYSOUND *wps)
Definition: playsound.c:627
static HMMIO get_mmioFromProfile(UINT uFlags, LPCWSTR lpszName)
Definition: playsound.c:115
static BOOL PlaySound_IsString(DWORD fdwSound, const void *psz)
Definition: playsound.c:403
#define err(...)
const WCHAR * str
_Check_return_ _CRTIMP int __cdecl _wcsicmp(_In_z_ const wchar_t *_Str1, _In_z_ const wchar_t *_Str2)
STDMETHOD() Next(THIS_ ULONG celt, IAssociationElement *pElement, ULONG *pceltFetched) PURE
#define TRACE(s)
Definition: solgame.cpp:4
FOURCC ckid
Definition: mmsystem.h:1507
DWORD cksize
Definition: mmsystem.h:1508
DWORD dwDataOffset
Definition: mmsystem.h:1510
FOURCC fccType
Definition: mmsystem.h:1509
LONG cchBuffer
Definition: mmsystem.h:1491
HPSTR pchBuffer
Definition: mmsystem.h:1492
FOURCC fccIOProc
Definition: mmsystem.h:1487
WORD nBlockAlign
Definition: mmreg.h:82
DWORD nAvgBytesPerSec
Definition: mmreg.h:81
DWORD nSamplesPerSec
Definition: mmreg.h:80
WORD nChannels
Definition: mmreg.h:79
WORD wFormatTag
Definition: mmreg.h:78
WORD wBitsPerSample
Definition: mmreg.h:83
HANDLE hEvent
Definition: playsound.c:369
LONG dwEventCount
Definition: playsound.c:370
unsigned bLoop
Definition: playsound.c:35
HWAVEOUT hWave
Definition: playsound.c:37
DWORD dwBufferLength
Definition: mmsystem.h:1015
DWORD dwLoops
Definition: mmsystem.h:1019
DWORD dwFlags
Definition: mmsystem.h:1018
DWORD_PTR dwUser
Definition: mmsystem.h:1017
LPSTR lpData
Definition: mmsystem.h:1014
DWORD WINAPI WaitForSingleObject(IN HANDLE hHandle, IN DWORD dwMilliseconds)
Definition: synch.c:82
VOID WINAPI DECLSPEC_HOTPATCH Sleep(IN DWORD dwMilliseconds)
Definition: synch.c:790
HANDLE WINAPI DECLSPEC_HOTPATCH CreateEventW(IN LPSECURITY_ATTRIBUTES lpEventAttributes OPTIONAL, IN BOOL bManualReset, IN BOOL bInitialState, IN LPCWSTR lpName OPTIONAL)
Definition: synch.c:651
BOOL WINAPI DECLSPEC_HOTPATCH SetEvent(IN HANDLE hEvent)
Definition: synch.c:733
BOOL WINAPI DECLSPEC_HOTPATCH ResetEvent(IN HANDLE hEvent)
Definition: synch.c:714
uint32_t DWORD_PTR
Definition: typedefs.h:65
unsigned char * LPBYTE
Definition: typedefs.h:53
void * PVOID
Definition: typedefs.h:50
int32_t INT
Definition: typedefs.h:58
#define HIWORD(l)
Definition: typedefs.h:247
int ret
#define ZeroMemory
Definition: winbase.h:1743
DWORD WINAPI GetLastError(void)
Definition: except.c:1042
HANDLE WINAPI GetCurrentThread(void)
Definition: proc.c:1148
void WINAPI LeaveCriticalSection(LPCRITICAL_SECTION)
void WINAPI EnterCriticalSection(LPCRITICAL_SECTION)
#define THREAD_PRIORITY_TIME_CRITICAL
Definition: winbase.h:307
*nSize LPSTR _Inout_ LPDWORD nSize
Definition: winbase.h:2115
#define WINAPI
Definition: msvc.h:6
HANDLE psLastEvent
Definition: winmm.c:51
CRITICAL_SECTION WINMM_cs
Definition: winmm.c:53
#define ERROR_NO_TOKEN
Definition: winerror.h:587
UINT WINAPI waveOutReset(HWAVEOUT hWaveOut)
Definition: winmm.c:2385
UINT WINAPI waveOutWrite(HWAVEOUT hWaveOut, LPWAVEHDR lpWaveOutHdr, UINT uSize)
Definition: winmm.c:2341
UINT WINAPI waveOutUnprepareHeader(HWAVEOUT hWaveOut, LPWAVEHDR lpWaveOutHdr, UINT uSize)
Definition: winmm.c:2307
MMRESULT WINAPI waveOutOpen(LPHWAVEOUT lphWaveOut, UINT uDeviceID, LPCWAVEFORMATEX lpFormat, DWORD_PTR dwCallback, DWORD_PTR dwInstance, DWORD dwFlags)
Definition: winmm.c:2246
UINT WINAPI waveOutPrepareHeader(HWAVEOUT hWaveOut, WAVEHDR *lpWaveOutHdr, UINT uSize)
Definition: winmm.c:2277
UINT WINAPI waveOutClose(HWAVEOUT hWaveOut)
Definition: winmm.c:2257
#define TOKEN_DUPLICATE
Definition: setypes.h:926
#define TOKEN_QUERY
Definition: setypes.h:928
#define TOKEN_IMPERSONATE
Definition: setypes.h:927
const char * LPCSTR
Definition: xmlstorage.h:183
char * LPSTR
Definition: xmlstorage.h:182
__wchar_t WCHAR
Definition: xmlstorage.h:180
WCHAR * LPWSTR
Definition: xmlstorage.h:184
const WCHAR * LPCWSTR
Definition: xmlstorage.h:185