2 * MMSYSTEM MCI and low level mapping functions
4 * Copyright 1999 Eric Pouech
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
25 #include "wine/winbase16.h"
33 #include "wine/debug.h"
35 WINE_DEFAULT_DEBUG_CHANNEL(winmm);
37 /**************************************************************************
38 * MMDRV_Callback [internal]
40 static void MMDRV_Callback(LPWINE_MLD mld, HDRVR hDev, UINT uMsg, DWORD_PTR dwParam1, DWORD_PTR dwParam2)
42 TRACE("CB (*%08lx)(%p %08x %08lx %08lx %08lx\n",
43 mld->dwCallback, hDev, uMsg, mld->dwClientInstance, dwParam1, dwParam2);
45 if (!mld->bFrom32 && (mld->dwFlags & DCB_TYPEMASK) == DCB_FUNCTION)
48 /* 16 bit func, call it */
49 TRACE("Function (16 bit) !\n");
51 args[7] = HDRVR_16(hDev);
53 args[5] = HIWORD(mld->dwClientInstance);
54 args[4] = LOWORD(mld->dwClientInstance);
55 args[3] = HIWORD(dwParam1);
56 args[2] = LOWORD(dwParam1);
57 args[1] = HIWORD(dwParam2);
58 args[0] = LOWORD(dwParam2);
59 WOWCallback16Ex( mld->dwCallback, WCB16_PASCAL, sizeof(args), args, NULL );
61 DriverCallback(mld->dwCallback, mld->dwFlags, hDev, uMsg,
62 mld->dwClientInstance, dwParam1, dwParam2);
66 /* =================================
68 * ================================= */
70 /**************************************************************************
71 * MMDRV_Aux_Map16To32W [internal]
73 static WINMM_MapType MMDRV_Aux_Map16To32W (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
75 return WINMM_MAP_MSGERROR;
78 /**************************************************************************
79 * MMDRV_Aux_UnMap16To32W [internal]
81 static WINMM_MapType MMDRV_Aux_UnMap16To32W(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
83 return WINMM_MAP_MSGERROR;
86 /**************************************************************************
87 * MMDRV_Aux_Map32WTo16 [internal]
89 static WINMM_MapType MMDRV_Aux_Map32WTo16 (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
91 return WINMM_MAP_MSGERROR;
94 /**************************************************************************
95 * MMDRV_Aux_UnMap32WTo16 [internal]
97 static WINMM_MapType MMDRV_Aux_UnMap32WTo16(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
100 case AUXDM_GETDEVCAPS:
101 lpCaps->wMid = ac16.wMid;
102 lpCaps->wPid = ac16.wPid;
103 lpCaps->vDriverVersion = ac16.vDriverVersion;
104 strcpy(lpCaps->szPname, ac16.szPname);
105 lpCaps->wTechnology = ac16.wTechnology;
106 lpCaps->dwSupport = ac16.dwSupport;
108 return WINMM_MAP_MSGERROR;
111 /**************************************************************************
112 * MMDRV_Aux_Callback [internal]
114 static void CALLBACK MMDRV_Aux_Callback(HDRVR hDev, UINT uMsg, DWORD_PTR dwInstance, DWORD_PTR dwParam1, DWORD_PTR dwParam2)
116 LPWINE_MLD mld = (LPWINE_MLD)dwInstance;
119 MMDRV_Callback(mld, hDev, uMsg, dwParam1, dwParam2);
122 /* =================================
123 * M I X E R M A P P E R S
124 * ================================= */
126 /**************************************************************************
127 * xMMDRV_Mixer_Map16To32W [internal]
129 static WINMM_MapType MMDRV_Mixer_Map16To32W (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
131 return WINMM_MAP_MSGERROR;
134 /**************************************************************************
135 * MMDRV_Mixer_UnMap16To32W [internal]
137 static WINMM_MapType MMDRV_Mixer_UnMap16To32W(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
141 UINT ret = mixerGetDevCapsA(devid, &micA, sizeof(micA));
143 if (ret == MMSYSERR_NOERROR) {
144 mixcaps->wMid = micA.wMid;
145 mixcaps->wPid = micA.wPid;
146 mixcaps->vDriverVersion = micA.vDriverVersion;
147 strcpy(mixcaps->szPname, micA.szPname);
148 mixcaps->fdwSupport = micA.fdwSupport;
149 mixcaps->cDestinations = micA.cDestinations;
153 return WINMM_MAP_MSGERROR;
156 /**************************************************************************
157 * MMDRV_Mixer_Map32WTo16 [internal]
159 static WINMM_MapType MMDRV_Mixer_Map32WTo16 (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
161 return WINMM_MAP_MSGERROR;
164 /**************************************************************************
165 * MMDRV_Mixer_UnMap32WTo16 [internal]
167 static WINMM_MapType MMDRV_Mixer_UnMap32WTo16(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
169 return WINMM_MAP_MSGERROR;
172 /**************************************************************************
173 * MMDRV_Mixer_Callback [internal]
175 static void CALLBACK MMDRV_Mixer_Callback(HDRVR hDev, UINT uMsg, DWORD_PTR dwInstance, DWORD_PTR dwParam1, DWORD_PTR dwParam2)
177 LPWINE_MLD mld = (LPWINE_MLD)dwInstance;
180 MMDRV_Callback(mld, hDev, uMsg, dwParam1, dwParam2);
183 /* =================================
184 * M I D I I N M A P P E R S
185 * ================================= */
187 /**************************************************************************
188 * MMDRV_MidiIn_Map16To32W [internal]
190 static WINMM_MapType MMDRV_MidiIn_Map16To32W (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
192 return WINMM_MAP_MSGERROR;
195 /**************************************************************************
196 * MMDRV_MidiIn_UnMap16To32W [internal]
198 static WINMM_MapType MMDRV_MidiIn_UnMap16To32W(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
200 return WINMM_MAP_MSGERROR;
203 /**************************************************************************
204 * MMDRV_MidiIn_Map32WTo16 [internal]
206 static WINMM_MapType MMDRV_MidiIn_Map32WTo16 (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
208 return WINMM_MAP_MSGERROR;
211 /**************************************************************************
212 * MMDRV_MidiIn_UnMap32WTo16 [internal]
214 static WINMM_MapType MMDRV_MidiIn_UnMap32WTo16(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
216 return WINMM_MAP_MSGERROR;
219 /**************************************************************************
220 * MMDRV_MidiIn_Callback [internal]
222 static void CALLBACK MMDRV_MidiIn_Callback(HDRVR hDev, UINT uMsg, DWORD_PTR dwInstance, DWORD_PTR dwParam1, DWORD_PTR dwParam2)
224 LPWINE_MLD mld = (LPWINE_MLD)dwInstance;
229 /* dwParam1 & dwParam2 are supposed to be 0, nothing to do */
234 /* dwParam1 & dwParam2 are data, nothing to do */
238 /* dwParam1 points to a MidiHdr, work to be done !!! */
239 if (mld->bFrom32 && !MMDRV_Is32(mld->mmdIndex)) {
240 /* initial map is: 32 => 16 */
241 LPMIDIHDR mh16 = MapSL(dwParam1);
242 LPMIDIHDR mh32 = *(LPMIDIHDR*)((LPSTR)mh16 - sizeof(LPMIDIHDR));
244 dwParam1 = (DWORD)mh32;
245 mh32->dwFlags = mh16->dwFlags;
246 mh32->dwBytesRecorded = mh16->dwBytesRecorded;
247 if (mh32->reserved >= sizeof(MIDIHDR))
248 mh32->dwOffset = mh16->dwOffset;
249 } else if (!mld->bFrom32 && MMDRV_Is32(mld->mmdIndex)) {
250 /* initial map is: 16 => 32 */
251 LPMIDIHDR mh32 = (LPMIDIHDR)(dwParam1);
252 SEGPTR segmh16 = *(SEGPTR*)((LPSTR)mh32 - sizeof(LPMIDIHDR));
253 LPMIDIHDR mh16 = MapSL(segmh16);
255 dwParam1 = (DWORD)segmh16;
256 mh16->dwFlags = mh32->dwFlags;
257 mh16->dwBytesRecorded = mh32->dwBytesRecorded;
258 if (mh16->reserved >= sizeof(MIDIHDR))
259 mh16->dwOffset = mh32->dwOffset;
261 /* else { 16 => 16 or 32 => 32, nothing to do, same struct is kept }*/
263 /* case MOM_POSITIONCB: */
265 ERR("Unknown msg %u\n", uMsg);
268 MMDRV_Callback(mld, hDev, uMsg, dwParam1, dwParam2);
271 /* =================================
272 * M I D I O U T M A P P E R S
273 * ================================= */
275 /**************************************************************************
276 * MMDRV_MidiOut_Map16To32W [internal]
278 static WINMM_MapType MMDRV_MidiOut_Map16To32W (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
280 WINMM_MapType ret = WINMM_MAP_MSGERROR;
283 case MODM_GETNUMDEVS:
293 FIXME("Shouldn't be used: the corresponding 16 bit functions use the 32 bit interface\n");
296 case MODM_GETDEVCAPS:
298 LPMIDIOUTCAPSW moc32 = HeapAlloc(GetProcessHeap(), 0, sizeof(LPMIDIOUTCAPS16) + sizeof(MIDIOUTCAPSW));
299 LPMIDIOUTCAPS16 moc16 = MapSL(*lpParam1);
302 *(LPMIDIOUTCAPS16*)moc32 = moc16;
303 moc32 = (LPMIDIOUTCAPSW)((LPSTR)moc32 + sizeof(LPMIDIOUTCAPS16));
304 *lpParam1 = (DWORD)moc32;
305 *lpParam2 = sizeof(MIDIOUTCAPSW);
307 ret = WINMM_MAP_OKMEM;
309 ret = WINMM_MAP_NOMEM;
315 LPMIDIHDR mh32 = HeapAlloc(GetProcessHeap(), 0, sizeof(LPMIDIHDR) + sizeof(MIDIHDR));
316 LPMIDIHDR mh16 = MapSL(*lpParam1);
319 *(LPMIDIHDR*)mh32 = (LPMIDIHDR)*lpParam1;
320 mh32 = (LPMIDIHDR)((LPSTR)mh32 + sizeof(LPMIDIHDR));
321 mh32->lpData = MapSL((SEGPTR)mh16->lpData);
322 mh32->dwBufferLength = mh16->dwBufferLength;
323 mh32->dwBytesRecorded = mh16->dwBytesRecorded;
324 mh32->dwUser = mh16->dwUser;
325 mh32->dwFlags = mh16->dwFlags;
326 /* FIXME: nothing on mh32->lpNext */
327 /* could link the mh32->lpNext at this level for memory house keeping */
328 mh32->dwOffset = (*lpParam2 >= sizeof(MIDIHDR)) ? ((LPMIDIHDR)mh16)->dwOffset : 0;
329 mh16->lpNext = mh32; /* for reuse in unprepare and write */
330 /* store size of passed MIDIHDR?? structure to know if dwOffset is available or not */
331 mh16->reserved = *lpParam2;
332 *lpParam1 = (DWORD)mh32;
333 *lpParam2 = sizeof(MIDIHDR);
335 ret = WINMM_MAP_OKMEM;
337 ret = WINMM_MAP_NOMEM;
344 LPMIDIHDR mh16 = MapSL(*lpParam1);
345 LPMIDIHDR mh32 = (LPMIDIHDR)mh16->lpNext;
347 *lpParam1 = (DWORD)mh32;
348 *lpParam2 = sizeof(MIDIHDR);
349 /* dwBufferLength can be reduced between prepare & write */
350 if (wMsg == MODM_LONGDATA && mh32->dwBufferLength < mh16->dwBufferLength) {
351 ERR("Size of buffer has been increased from %d to %d, keeping initial value\n",
352 mh32->dwBufferLength, mh16->dwBufferLength);
354 mh32->dwBufferLength = mh16->dwBufferLength;
355 ret = WINMM_MAP_OKMEM;
359 case MODM_CACHEPATCHES:
360 case MODM_CACHEDRUMPATCHES:
362 FIXME("NIY: no conversion yet for %u [%lx,%lx]\n", wMsg, *lpParam1, *lpParam2);
368 /**************************************************************************
369 * MMDRV_MidiOut_UnMap16To32W [internal]
371 static WINMM_MapType MMDRV_MidiOut_UnMap16To32W(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
373 WINMM_MapType ret = WINMM_MAP_MSGERROR;
376 case MODM_GETNUMDEVS:
386 FIXME("Shouldn't be used: the corresponding 16 bit functions use the 32 bit interface\n");
389 case MODM_GETDEVCAPS:
391 LPMIDIOUTCAPSW moc32 = (LPMIDIOUTCAPSW)(*lpParam1);
392 LPMIDIOUTCAPS16 moc16 = *(LPMIDIOUTCAPS16*)((LPSTR)moc32 - sizeof(LPMIDIOUTCAPS16));
394 moc16->wMid = moc32->wMid;
395 moc16->wPid = moc32->wPid;
396 moc16->vDriverVersion = moc32->vDriverVersion;
397 WideCharToMultiByte( CP_ACP, 0, moc32->szPname, -1, moc16->szPname,
398 sizeof(moc16->szPname), NULL, NULL );
399 moc16->wTechnology = moc32->wTechnology;
400 moc16->wVoices = moc32->wVoices;
401 moc16->wNotes = moc32->wNotes;
402 moc16->wChannelMask = moc32->wChannelMask;
403 moc16->dwSupport = moc32->dwSupport;
404 HeapFree(GetProcessHeap(), 0, (LPSTR)moc32 - sizeof(LPMIDIOUTCAPS16));
412 LPMIDIHDR mh32 = (LPMIDIHDR)(*lpParam1);
413 LPMIDIHDR mh16 = MapSL(*(SEGPTR*)((LPSTR)mh32 - sizeof(LPMIDIHDR)));
415 assert(mh16->lpNext == mh32);
416 mh16->dwBufferLength = mh32->dwBufferLength;
417 mh16->dwBytesRecorded = mh32->dwBytesRecorded;
418 mh16->dwUser = mh32->dwUser;
419 mh16->dwFlags = mh32->dwFlags;
420 if (mh16->reserved >= sizeof(MIDIHDR))
421 mh16->dwOffset = mh32->dwOffset;
423 if (wMsg == MODM_UNPREPARE && fn_ret == MMSYSERR_NOERROR) {
424 HeapFree(GetProcessHeap(), 0, (LPSTR)mh32 - sizeof(LPMIDIHDR));
431 case MODM_CACHEPATCHES:
432 case MODM_CACHEDRUMPATCHES:
434 FIXME("NIY: no conversion yet for %u [%lx,%lx]\n", wMsg, *lpParam1, *lpParam2);
440 /**************************************************************************
441 * MMDRV_MidiOut_Map32WTo16 [internal]
443 static WINMM_MapType MMDRV_MidiOut_Map32WTo16 (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
445 WINMM_MapType ret = WINMM_MAP_MSGERROR;
449 case MODM_GETNUMDEVS:
455 case MODM_GETDEVCAPS:
457 LPMIDIOUTCAPSW moc32 = (LPMIDIOUTCAPSW)*lpParam1;
458 LPSTR ptr = HeapAlloc( GetProcessHeap(), 0, sizeof(LPMIDIOUTCAPSW)+sizeof(MIDIOUTCAPS16));
461 *(LPMIDIOUTCAPSW*)ptr = moc32;
462 ret = WINMM_MAP_OKMEM;
464 ret = WINMM_MAP_NOMEM;
466 *lpParam1 = (DWORD)MapLS(ptr) + sizeof(LPMIDIOUTCAPSW);
467 *lpParam2 = sizeof(MIDIOUTCAPS16);
472 LPMIDIHDR mh32 = (LPMIDIHDR)*lpParam1;
474 LPVOID ptr = HeapAlloc( GetProcessHeap(), 0,
475 sizeof(LPMIDIHDR) + sizeof(MIDIHDR) + mh32->dwBufferLength);
478 *(LPMIDIHDR*)ptr = mh32;
479 mh16 = (LPMIDIHDR)((LPSTR)ptr + sizeof(LPMIDIHDR));
480 *lpParam1 = MapLS(mh16);
481 mh16->lpData = (LPSTR)*lpParam1 + sizeof(MIDIHDR);
482 /* data will be copied on WODM_WRITE */
483 mh16->dwBufferLength = mh32->dwBufferLength;
484 mh16->dwBytesRecorded = mh32->dwBytesRecorded;
485 mh16->dwUser = mh32->dwUser;
486 mh16->dwFlags = mh32->dwFlags;
487 /* FIXME: nothing on mh32->lpNext */
488 /* could link the mh32->lpNext at this level for memory house keeping */
489 mh16->dwOffset = (*lpParam2 >= sizeof(MIDIHDR)) ? mh32->dwOffset : 0;
491 mh32->lpNext = (LPMIDIHDR)mh16; /* for reuse in unprepare and write */
492 mh32->reserved = *lpParam2;
494 TRACE("mh16=%08lx mh16->lpData=%p mh32->buflen=%u mh32->lpData=%p\n",
495 *lpParam1, mh16->lpData, mh32->dwBufferLength, mh32->lpData);
496 *lpParam2 = sizeof(MIDIHDR);
498 ret = WINMM_MAP_OKMEM;
500 ret = WINMM_MAP_NOMEM;
507 LPMIDIHDR mh32 = (LPMIDIHDR)(*lpParam1);
508 LPMIDIHDR mh16 = (LPMIDIHDR)mh32->lpNext;
509 LPSTR ptr = (LPSTR)mh16 - sizeof(LPMIDIHDR);
511 assert(*(LPMIDIHDR*)ptr == mh32);
513 if (wMsg == MODM_LONGDATA)
514 memcpy((LPSTR)mh16 + sizeof(MIDIHDR), mh32->lpData, mh32->dwBufferLength);
516 *lpParam1 = MapLS(mh16);
517 *lpParam2 = sizeof(MIDIHDR);
518 TRACE("mh16=%08lx mh16->lpData=%p mh32->buflen=%u mh32->lpData=%p\n",
519 *lpParam1, mh16->lpData, mh32->dwBufferLength, mh32->lpData);
521 /* dwBufferLength can be reduced between prepare & write */
522 if (wMsg == MODM_LONGDATA && mh16->dwBufferLength < mh32->dwBufferLength) {
523 ERR("Size of buffer has been increased from %d to %d, keeping initial value\n",
524 mh16->dwBufferLength, mh32->dwBufferLength);
526 mh16->dwBufferLength = mh32->dwBufferLength;
527 ret = WINMM_MAP_OKMEM;
532 LPMIDIOPENDESC mod32 = (LPMIDIOPENDESC)*lpParam1;
534 LPMIDIOPENDESC16 mod16;
536 /* allocated data are mapped as follows:
537 LPMIDIOPENDESC ptr to orig lParam1
538 DWORD orig dwUser, which is a pointer to DWORD:driver dwInstance
539 DWORD dwUser passed to driver
540 MIDIOPENDESC16 mod16: openDesc passed to driver
543 ptr = HeapAlloc( GetProcessHeap(), 0,
544 sizeof(LPMIDIOPENDESC) + 2*sizeof(DWORD) + sizeof(MIDIOPENDESC16) +
545 mod32->cIds ? (mod32->cIds - 1) * sizeof(MIDIOPENSTRMID) : 0);
548 SEGPTR segptr = MapLS(ptr);
549 *(LPMIDIOPENDESC*)ptr = mod32;
550 *(LPDWORD)((char*)ptr + sizeof(LPMIDIOPENDESC)) = *lpdwUser;
551 mod16 = (LPMIDIOPENDESC16)((LPSTR)ptr + sizeof(LPMIDIOPENDESC) + 2*sizeof(DWORD));
553 mod16->hMidi = HMIDI_16(mod32->hMidi);
554 mod16->dwCallback = mod32->dwCallback;
555 mod16->dwInstance = mod32->dwInstance;
556 mod16->dnDevNode = mod32->dnDevNode;
557 mod16->cIds = mod32->cIds;
558 memcpy(&mod16->rgIds, &mod32->rgIds, mod32->cIds * sizeof(MIDIOPENSTRMID));
560 *lpParam1 = (DWORD)segptr + sizeof(LPMIDIOPENDESC) + 2*sizeof(DWORD);
561 *lpdwUser = (DWORD)segptr + sizeof(LPMIDIOPENDESC) + sizeof(DWORD);
563 ret = WINMM_MAP_OKMEM;
565 ret = WINMM_MAP_NOMEM;
570 case MODM_CACHEPATCHES:
571 case MODM_CACHEDRUMPATCHES:
573 FIXME("NIY: no conversion yet for %u [%lx,%lx]\n", wMsg, *lpParam1, *lpParam2);
579 /**************************************************************************
580 * MMDRV_MidiOut_UnMap32WTo16 [internal]
582 static WINMM_MapType MMDRV_MidiOut_UnMap32WTo16(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
584 WINMM_MapType ret = WINMM_MAP_MSGERROR;
588 case MODM_GETNUMDEVS:
594 case MODM_GETDEVCAPS:
596 LPMIDIOUTCAPS16 moc16 = MapSL(*lpParam1);
597 LPSTR ptr = (LPSTR)moc16 - sizeof(LPMIDIOUTCAPSW);
598 LPMIDIOUTCAPSW moc32 = *(LPMIDIOUTCAPSW*)ptr;
600 moc32->wMid = moc16->wMid;
601 moc32->wPid = moc16->wPid;
602 moc32->vDriverVersion = moc16->vDriverVersion;
603 WideCharToMultiByte( CP_ACP, 0, moc32->szPname, -1, moc16->szPname,
604 sizeof(moc16->szPname), NULL, NULL );
605 moc32->wTechnology = moc16->wTechnology;
606 moc32->wVoices = moc16->wVoices;
607 moc32->wNotes = moc16->wNotes;
608 moc32->wChannelMask = moc16->wChannelMask;
609 moc32->dwSupport = moc16->dwSupport;
610 UnMapLS( *lpParam1 );
611 HeapFree( GetProcessHeap(), 0, ptr );
619 LPMIDIHDR mh16 = MapSL(*lpParam1);
620 LPSTR ptr = (LPSTR)mh16 - sizeof(LPMIDIHDR);
621 LPMIDIHDR mh32 = *(LPMIDIHDR*)ptr;
623 assert(mh32->lpNext == (LPMIDIHDR)mh16);
624 UnMapLS( *lpParam1 );
625 mh32->dwBytesRecorded = mh16->dwBytesRecorded;
626 mh32->dwUser = mh16->dwUser;
627 mh32->dwFlags = mh16->dwFlags;
629 if (wMsg == MODM_UNPREPARE && fn_ret == MMSYSERR_NOERROR) {
630 HeapFree( GetProcessHeap(), 0, ptr );
638 LPMIDIOPENDESC16 mod16 = MapSL(*lpParam1);
639 LPSTR ptr = (LPSTR)mod16 - sizeof(LPMIDIOPENDESC) - 2*sizeof(DWORD);
640 UnMapLS( *lpParam1 );
641 **(DWORD**)(ptr + sizeof(LPMIDIOPENDESC)) = *(LPDWORD)(ptr + sizeof(LPMIDIOPENDESC) + sizeof(DWORD));
643 HeapFree( GetProcessHeap(), 0, ptr );
648 case MODM_CACHEPATCHES:
649 case MODM_CACHEDRUMPATCHES:
651 FIXME("NIY: no conversion yet for %u [%lx,%lx]\n", wMsg, *lpParam1, *lpParam2);
657 /**************************************************************************
658 * MMDRV_MidiOut_Callback [internal]
660 static void CALLBACK MMDRV_MidiOut_Callback(HDRVR hDev, UINT uMsg, DWORD_PTR dwInstance, DWORD_PTR dwParam1, DWORD_PTR dwParam2)
662 LPWINE_MLD mld = (LPWINE_MLD)dwInstance;
667 /* dwParam1 & dwParam2 are supposed to be 0, nothing to do */
670 if (mld->bFrom32 && !MMDRV_Is32(mld->mmdIndex)) {
671 /* initial map is: 32 => 16 */
672 LPMIDIHDR mh16 = MapSL(dwParam1);
673 LPMIDIHDR mh32 = *(LPMIDIHDR*)((LPSTR)mh16 - sizeof(LPMIDIHDR));
675 dwParam1 = (DWORD)mh32;
676 mh32->dwFlags = mh16->dwFlags;
677 mh32->dwOffset = mh16->dwOffset;
678 if (mh32->reserved >= sizeof(MIDIHDR))
679 mh32->dwOffset = mh16->dwOffset;
680 } else if (!mld->bFrom32 && MMDRV_Is32(mld->mmdIndex)) {
681 /* initial map is: 16 => 32 */
682 LPMIDIHDR mh32 = (LPMIDIHDR)(dwParam1);
683 SEGPTR segmh16 = *(SEGPTR*)((LPSTR)mh32 - sizeof(LPMIDIHDR));
684 LPMIDIHDR mh16 = MapSL(segmh16);
686 dwParam1 = (DWORD)segmh16;
687 mh16->dwFlags = mh32->dwFlags;
688 if (mh16->reserved >= sizeof(MIDIHDR))
689 mh16->dwOffset = mh32->dwOffset;
691 /* else { 16 => 16 or 32 => 32, nothing to do, same struct is kept }*/
693 /* case MOM_POSITIONCB: */
695 ERR("Unknown msg %u\n", uMsg);
698 MMDRV_Callback(mld, hDev, uMsg, dwParam1, dwParam2);
701 /* =================================
702 * W A V E I N M A P P E R S
703 * ================================= */
705 /**************************************************************************
706 * MMDRV_WaveIn_Map16To32W [internal]
708 static WINMM_MapType MMDRV_WaveIn_Map16To32W (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
710 WINMM_MapType ret = WINMM_MAP_MSGERROR;
713 case WIDM_GETNUMDEVS:
721 FIXME("Shouldn't be used: the corresponding 16 bit functions use the 32 bit interface\n");
723 case WIDM_GETDEVCAPS:
725 LPWAVEINCAPSW wic32 = HeapAlloc(GetProcessHeap(), 0, sizeof(LPWAVEINCAPS16) + sizeof(WAVEINCAPSW));
726 LPWAVEINCAPS16 wic16 = MapSL(*lpParam1);
729 *(LPWAVEINCAPS16*)wic32 = wic16;
730 wic32 = (LPWAVEINCAPSW)((LPSTR)wic32 + sizeof(LPWAVEINCAPS16));
731 *lpParam1 = (DWORD)wic32;
732 *lpParam2 = sizeof(WAVEINCAPSW);
734 ret = WINMM_MAP_OKMEM;
736 ret = WINMM_MAP_NOMEM;
742 LPMMTIME mmt32 = HeapAlloc(GetProcessHeap(), 0, sizeof(LPMMTIME16) + sizeof(MMTIME));
743 LPMMTIME16 mmt16 = MapSL(*lpParam1);
746 *(LPMMTIME16*)mmt32 = mmt16;
747 mmt32 = (LPMMTIME)((LPSTR)mmt32 + sizeof(LPMMTIME16));
749 mmt32->wType = mmt16->wType;
750 *lpParam1 = (DWORD)mmt32;
751 *lpParam2 = sizeof(MMTIME);
753 ret = WINMM_MAP_OKMEM;
755 ret = WINMM_MAP_NOMEM;
761 LPWAVEHDR wh32 = HeapAlloc(GetProcessHeap(), 0, sizeof(LPWAVEHDR) + sizeof(WAVEHDR));
762 LPWAVEHDR wh16 = MapSL(*lpParam1);
765 *(LPWAVEHDR*)wh32 = (LPWAVEHDR)*lpParam1;
766 wh32 = (LPWAVEHDR)((LPSTR)wh32 + sizeof(LPWAVEHDR));
767 wh32->lpData = MapSL((SEGPTR)wh16->lpData);
768 wh32->dwBufferLength = wh16->dwBufferLength;
769 wh32->dwBytesRecorded = wh16->dwBytesRecorded;
770 wh32->dwUser = wh16->dwUser;
771 wh32->dwFlags = wh16->dwFlags;
772 wh32->dwLoops = wh16->dwLoops;
773 /* FIXME: nothing on wh32->lpNext */
774 /* could link the wh32->lpNext at this level for memory house keeping */
775 wh16->lpNext = wh32; /* for reuse in unprepare and write */
776 *lpParam1 = (DWORD)wh32;
777 *lpParam2 = sizeof(WAVEHDR);
779 ret = WINMM_MAP_OKMEM;
781 ret = WINMM_MAP_NOMEM;
788 LPWAVEHDR wh16 = MapSL(*lpParam1);
789 LPWAVEHDR wh32 = (LPWAVEHDR)wh16->lpNext;
791 *lpParam1 = (DWORD)wh32;
792 *lpParam2 = sizeof(WAVEHDR);
793 /* dwBufferLength can be reduced between prepare & write */
794 if (wMsg == WIDM_ADDBUFFER && wh32->dwBufferLength < wh16->dwBufferLength) {
795 ERR("Size of buffer has been increased from %d to %d, keeping initial value\n",
796 wh32->dwBufferLength, wh16->dwBufferLength);
798 wh32->dwBufferLength = wh16->dwBufferLength;
799 ret = WINMM_MAP_OKMEM;
802 case WIDM_MAPPER_STATUS:
803 /* just a single DWORD */
804 *lpParam2 = (DWORD)MapSL(*lpParam2);
808 FIXME("NIY: no conversion yet for %u [%lx,%lx]\n", wMsg, *lpParam1, *lpParam2);
814 /**************************************************************************
815 * MMDRV_WaveIn_UnMap16To32W [internal]
817 static WINMM_MapType MMDRV_WaveIn_UnMap16To32W(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
819 WINMM_MapType ret = WINMM_MAP_MSGERROR;
822 case WIDM_GETNUMDEVS:
826 case WIDM_MAPPER_STATUS:
831 FIXME("Shouldn't be used: the corresponding 16 bit functions use the 32 bit interface\n");
833 case WIDM_GETDEVCAPS:
835 LPWAVEINCAPSW wic32 = (LPWAVEINCAPSW)(*lpParam1);
836 LPWAVEINCAPS16 wic16 = *(LPWAVEINCAPS16*)((LPSTR)wic32 - sizeof(LPWAVEINCAPS16));
838 wic16->wMid = wic32->wMid;
839 wic16->wPid = wic32->wPid;
840 wic16->vDriverVersion = wic32->vDriverVersion;
841 WideCharToMultiByte( CP_ACP, 0, wic32->szPname, -1, wic16->szPname,
842 sizeof(wic16->szPname), NULL, NULL );
843 wic16->dwFormats = wic32->dwFormats;
844 wic16->wChannels = wic32->wChannels;
845 HeapFree(GetProcessHeap(), 0, (LPSTR)wic32 - sizeof(LPWAVEINCAPS16));
851 LPMMTIME mmt32 = (LPMMTIME)(*lpParam1);
852 LPMMTIME16 mmt16 = *(LPMMTIME16*)((LPSTR)mmt32 - sizeof(LPMMTIME16));
854 MMSYSTEM_MMTIME32to16(mmt16, mmt32);
855 HeapFree(GetProcessHeap(), 0, (LPSTR)mmt32 - sizeof(LPMMTIME16));
863 LPWAVEHDR wh32 = (LPWAVEHDR)(*lpParam1);
864 LPWAVEHDR wh16 = MapSL(*(SEGPTR*)((LPSTR)wh32 - sizeof(LPWAVEHDR)));
866 assert(wh16->lpNext == wh32);
867 wh16->dwBufferLength = wh32->dwBufferLength;
868 wh16->dwBytesRecorded = wh32->dwBytesRecorded;
869 wh16->dwUser = wh32->dwUser;
870 wh16->dwFlags = wh32->dwFlags;
871 wh16->dwLoops = wh32->dwLoops;
873 if (wMsg == WIDM_UNPREPARE && fn_ret == MMSYSERR_NOERROR) {
874 HeapFree(GetProcessHeap(), 0, (LPSTR)wh32 - sizeof(LPWAVEHDR));
881 FIXME("NIY: no conversion yet for %u [%lx,%lx]\n", wMsg, *lpParam1, *lpParam2);
887 /**************************************************************************
888 * MMDRV_WaveIn_Map32WTo16 [internal]
890 static WINMM_MapType MMDRV_WaveIn_Map32WTo16 (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
892 WINMM_MapType ret = WINMM_MAP_MSGERROR;
896 case WIDM_GETNUMDEVS:
905 LPWAVEOPENDESC wod32 = (LPWAVEOPENDESC)*lpParam1;
906 int sz = sizeof(WAVEFORMATEX);
908 LPWAVEOPENDESC16 wod16;
910 /* allocated data are mapped as follows:
911 LPWAVEOPENDESC ptr to orig lParam1
912 DWORD orig dwUser, which is a pointer to DWORD:driver dwInstance
913 DWORD dwUser passed to driver
914 WAVEOPENDESC16 wod16: openDesc passed to driver
915 WAVEFORMATEX openDesc->lpFormat passed to driver
916 xxx extra bytes to WAVEFORMATEX
918 if (wod32->lpFormat->wFormatTag != WAVE_FORMAT_PCM) {
919 TRACE("Allocating %u extra bytes (%d)\n", ((LPWAVEFORMATEX)wod32->lpFormat)->cbSize, wod32->lpFormat->wFormatTag);
920 sz += ((LPWAVEFORMATEX)wod32->lpFormat)->cbSize;
923 ptr = HeapAlloc( GetProcessHeap(), 0,
924 sizeof(LPWAVEOPENDESC) + 2*sizeof(DWORD) + sizeof(WAVEOPENDESC16) + sz);
927 SEGPTR seg_ptr = MapLS( ptr );
928 *(LPWAVEOPENDESC*)ptr = wod32;
929 *(LPDWORD)((char*)ptr + sizeof(LPWAVEOPENDESC)) = *lpdwUser;
930 wod16 = (LPWAVEOPENDESC16)((LPSTR)ptr + sizeof(LPWAVEOPENDESC) + 2*sizeof(DWORD));
932 wod16->hWave = HWAVE_16(wod32->hWave);
933 wod16->lpFormat = (LPWAVEFORMATEX)(seg_ptr + sizeof(LPWAVEOPENDESC) + 2*sizeof(DWORD) + sizeof(WAVEOPENDESC16));
934 memcpy(wod16 + 1, wod32->lpFormat, sz);
936 wod16->dwCallback = wod32->dwCallback;
937 wod16->dwInstance = wod32->dwInstance;
938 wod16->uMappedDeviceID = wod32->uMappedDeviceID;
939 wod16->dnDevNode = wod32->dnDevNode;
941 *lpParam1 = seg_ptr + sizeof(LPWAVEOPENDESC) + 2*sizeof(DWORD);
942 *lpdwUser = seg_ptr + sizeof(LPWAVEOPENDESC) + sizeof(DWORD);
944 ret = WINMM_MAP_OKMEM;
946 ret = WINMM_MAP_NOMEM;
952 LPWAVEHDR wh32 = (LPWAVEHDR)*lpParam1;
954 LPVOID ptr = HeapAlloc( GetProcessHeap(), 0,
955 sizeof(LPWAVEHDR) + sizeof(WAVEHDR) + wh32->dwBufferLength);
958 SEGPTR seg_ptr = MapLS( ptr );
959 *(LPWAVEHDR*)ptr = wh32;
960 wh16 = (LPWAVEHDR)((LPSTR)ptr + sizeof(LPWAVEHDR));
961 wh16->lpData = (LPSTR)seg_ptr + sizeof(LPWAVEHDR) + sizeof(WAVEHDR);
962 /* data will be copied on WODM_WRITE */
963 wh16->dwBufferLength = wh32->dwBufferLength;
964 wh16->dwBytesRecorded = wh32->dwBytesRecorded;
965 wh16->dwUser = wh32->dwUser;
966 wh16->dwFlags = wh32->dwFlags;
967 wh16->dwLoops = wh32->dwLoops;
968 /* FIXME: nothing on wh32->lpNext */
969 /* could link the wh32->lpNext at this level for memory house keeping */
970 wh32->lpNext = wh16; /* for reuse in unprepare and write */
971 *lpParam1 = seg_ptr + sizeof(LPWAVEHDR);
972 *lpParam2 = sizeof(WAVEHDR);
973 TRACE("wh16=%08lx wh16->lpData=%p wh32->buflen=%u wh32->lpData=%p\n",
974 *lpParam1, wh16->lpData, wh32->dwBufferLength, wh32->lpData);
976 ret = WINMM_MAP_OKMEM;
978 ret = WINMM_MAP_NOMEM;
985 LPWAVEHDR wh32 = (LPWAVEHDR)(*lpParam1);
986 LPWAVEHDR wh16 = wh32->lpNext;
987 LPSTR ptr = (LPSTR)wh16 - sizeof(LPWAVEHDR);
988 SEGPTR seg_ptr = MapLS( ptr );
990 assert(*(LPWAVEHDR*)ptr == wh32);
992 if (wMsg == WIDM_ADDBUFFER)
993 memcpy((LPSTR)wh16 + sizeof(WAVEHDR), wh32->lpData, wh32->dwBufferLength);
995 *lpParam1 = seg_ptr + sizeof(LPWAVEHDR);
996 *lpParam2 = sizeof(WAVEHDR);
997 TRACE("wh16=%08lx wh16->lpData=%p wh32->buflen=%u wh32->lpData=%p\n",
998 *lpParam1, wh16->lpData, wh32->dwBufferLength, wh32->lpData);
1000 /* dwBufferLength can be reduced between prepare & write */
1001 if (wMsg == WIDM_ADDBUFFER && wh16->dwBufferLength < wh32->dwBufferLength) {
1002 ERR("Size of buffer has been increased from %d to %d, keeping initial value\n",
1003 wh16->dwBufferLength, wh32->dwBufferLength);
1005 wh16->dwBufferLength = wh32->dwBufferLength;
1006 ret = WINMM_MAP_OKMEM;
1009 case WIDM_GETDEVCAPS:
1011 LPWAVEINCAPSW wic32 = (LPWAVEINCAPSW)*lpParam1;
1012 LPSTR ptr = HeapAlloc( GetProcessHeap(), 0 ,sizeof(LPWAVEINCAPSW) + sizeof(WAVEINCAPS16));
1015 *(LPWAVEINCAPSW*)ptr = wic32;
1016 ret = WINMM_MAP_OKMEM;
1018 ret = WINMM_MAP_NOMEM;
1020 *lpParam1 = MapLS(ptr) + sizeof(LPWAVEINCAPSW);
1021 *lpParam2 = sizeof(WAVEINCAPS16);
1026 LPMMTIME mmt32 = (LPMMTIME)*lpParam1;
1027 LPSTR ptr = HeapAlloc( GetProcessHeap(), 0, sizeof(LPMMTIME) + sizeof(MMTIME16));
1028 LPMMTIME16 mmt16 = (LPMMTIME16)(ptr + sizeof(LPMMTIME));
1031 *(LPMMTIME*)ptr = mmt32;
1032 mmt16->wType = mmt32->wType;
1033 ret = WINMM_MAP_OKMEM;
1035 ret = WINMM_MAP_NOMEM;
1037 *lpParam1 = MapLS(ptr) + sizeof(LPMMTIME);
1038 *lpParam2 = sizeof(MMTIME16);
1041 case DRVM_MAPPER_STATUS:
1043 LPDWORD p32 = (LPDWORD)*lpParam2;
1044 *lpParam2 = MapLS(p32);
1045 ret = WINMM_MAP_OKMEM;
1049 FIXME("NIY: no conversion yet for %u [%lx,%lx]\n", wMsg, *lpParam1, *lpParam2);
1055 /**************************************************************************
1056 * MMDRV_WaveIn_UnMap32WTo16 [internal]
1058 static WINMM_MapType MMDRV_WaveIn_UnMap32WTo16(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
1060 WINMM_MapType ret = WINMM_MAP_MSGERROR;
1064 case WIDM_GETNUMDEVS:
1073 LPWAVEOPENDESC16 wod16 = MapSL(*lpParam1);
1074 LPSTR ptr = (LPSTR)wod16 - sizeof(LPWAVEOPENDESC) - 2*sizeof(DWORD);
1075 LPWAVEOPENDESC wod32 = *(LPWAVEOPENDESC*)ptr;
1077 UnMapLS( *lpParam1 );
1078 wod32->uMappedDeviceID = wod16->uMappedDeviceID;
1079 **(DWORD**)(ptr + sizeof(LPWAVEOPENDESC)) = *(LPDWORD)(ptr + sizeof(LPWAVEOPENDESC) + sizeof(DWORD));
1080 HeapFree( GetProcessHeap(), 0, ptr );
1085 case WIDM_ADDBUFFER:
1087 case WIDM_UNPREPARE:
1089 LPWAVEHDR wh16 = MapSL(*lpParam1);
1090 LPSTR ptr = (LPSTR)wh16 - sizeof(LPWAVEHDR);
1091 LPWAVEHDR wh32 = *(LPWAVEHDR*)ptr;
1093 assert(wh32->lpNext == wh16);
1094 wh32->dwBytesRecorded = wh16->dwBytesRecorded;
1095 wh32->dwUser = wh16->dwUser;
1096 wh32->dwFlags = wh16->dwFlags;
1097 wh32->dwLoops = wh16->dwLoops;
1098 UnMapLS( *lpParam1 );
1100 if (wMsg == WIDM_UNPREPARE && fn_ret == MMSYSERR_NOERROR) {
1101 HeapFree( GetProcessHeap(), 0, ptr );
1107 case WIDM_GETDEVCAPS:
1109 LPWAVEINCAPS16 wic16 = MapSL(*lpParam1);
1110 LPSTR ptr = (LPSTR)wic16 - sizeof(LPWAVEINCAPSW);
1111 LPWAVEINCAPSW wic32 = *(LPWAVEINCAPSW*)ptr;
1113 wic32->wMid = wic16->wMid;
1114 wic32->wPid = wic16->wPid;
1115 wic32->vDriverVersion = wic16->vDriverVersion;
1116 WideCharToMultiByte( CP_ACP, 0, wic32->szPname, -1, wic16->szPname,
1117 sizeof(wic16->szPname), NULL, NULL );
1118 wic32->dwFormats = wic16->dwFormats;
1119 wic32->wChannels = wic16->wChannels;
1120 UnMapLS( *lpParam1 );
1121 HeapFree( GetProcessHeap(), 0, ptr );
1127 LPMMTIME16 mmt16 = MapSL(*lpParam1);
1128 LPSTR ptr = (LPSTR)mmt16 - sizeof(LPMMTIME);
1129 LPMMTIME mmt32 = *(LPMMTIME*)ptr;
1131 MMSYSTEM_MMTIME16to32(mmt32, mmt16);
1132 UnMapLS( *lpParam1 );
1133 HeapFree( GetProcessHeap(), 0, ptr );
1137 case DRVM_MAPPER_STATUS:
1139 UnMapLS( *lpParam2 );
1144 FIXME("NIY: no conversion yet for %u [%lx,%lx]\n", wMsg, *lpParam1, *lpParam2);
1150 /**************************************************************************
1151 * MMDRV_WaveIn_Callback [internal]
1153 static void CALLBACK MMDRV_WaveIn_Callback(HDRVR hDev, UINT uMsg, DWORD_PTR dwInstance, DWORD_PTR dwParam1, DWORD_PTR dwParam2)
1155 LPWINE_MLD mld = (LPWINE_MLD)dwInstance;
1160 /* dwParam1 & dwParam2 are supposed to be 0, nothing to do */
1163 if (mld->bFrom32 && !MMDRV_Is32(mld->mmdIndex)) {
1164 /* initial map is: 32 => 16 */
1165 LPWAVEHDR wh16 = MapSL(dwParam1);
1166 LPWAVEHDR wh32 = *(LPWAVEHDR*)((LPSTR)wh16 - sizeof(LPWAVEHDR));
1168 dwParam1 = (DWORD)wh32;
1169 wh32->dwFlags = wh16->dwFlags;
1170 wh32->dwBytesRecorded = wh16->dwBytesRecorded;
1171 } else if (!mld->bFrom32 && MMDRV_Is32(mld->mmdIndex)) {
1172 /* initial map is: 16 => 32 */
1173 LPWAVEHDR wh32 = (LPWAVEHDR)(dwParam1);
1174 SEGPTR segwh16 = *(SEGPTR*)((LPSTR)wh32 - sizeof(LPWAVEHDR));
1175 LPWAVEHDR wh16 = MapSL(segwh16);
1177 dwParam1 = (DWORD)segwh16;
1178 wh16->dwFlags = wh32->dwFlags;
1179 wh16->dwBytesRecorded = wh32->dwBytesRecorded;
1181 /* else { 16 => 16 or 32 => 32, nothing to do, same struct is kept }*/
1184 ERR("Unknown msg %u\n", uMsg);
1187 MMDRV_Callback(mld, hDev, uMsg, dwParam1, dwParam2);
1190 /* =================================
1191 * W A V E O U T M A P P E R S
1192 * ================================= */
1194 /**************************************************************************
1195 * MMDRV_WaveOut_Map16To32W [internal]
1197 static WINMM_MapType MMDRV_WaveOut_Map16To32W (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
1199 WINMM_MapType ret = WINMM_MAP_MSGERROR;
1203 case WODM_BREAKLOOP:
1205 case WODM_GETNUMDEVS:
1210 case WODM_SETPLAYBACKRATE:
1211 case WODM_SETVOLUME:
1216 case WODM_GETPLAYBACKRATE:
1217 case WODM_GETVOLUME:
1219 FIXME("Shouldn't be used: the corresponding 16 bit functions use the 32 bit interface\n");
1222 case WODM_GETDEVCAPS:
1224 LPWAVEOUTCAPSW woc32 = HeapAlloc(GetProcessHeap(), 0, sizeof(LPWAVEOUTCAPS16) + sizeof(WAVEOUTCAPSW));
1225 LPWAVEOUTCAPS16 woc16 = MapSL(*lpParam1);
1228 *(LPWAVEOUTCAPS16*)woc32 = woc16;
1229 woc32 = (LPWAVEOUTCAPSW)((LPSTR)woc32 + sizeof(LPWAVEOUTCAPS16));
1230 *lpParam1 = (DWORD)woc32;
1231 *lpParam2 = sizeof(WAVEOUTCAPSW);
1233 ret = WINMM_MAP_OKMEM;
1235 ret = WINMM_MAP_NOMEM;
1241 LPMMTIME mmt32 = HeapAlloc(GetProcessHeap(), 0, sizeof(LPMMTIME16) + sizeof(MMTIME));
1242 LPMMTIME16 mmt16 = MapSL(*lpParam1);
1245 *(LPMMTIME16*)mmt32 = mmt16;
1246 mmt32 = (LPMMTIME)((LPSTR)mmt32 + sizeof(LPMMTIME16));
1248 mmt32->wType = mmt16->wType;
1249 *lpParam1 = (DWORD)mmt32;
1250 *lpParam2 = sizeof(MMTIME);
1252 ret = WINMM_MAP_OKMEM;
1254 ret = WINMM_MAP_NOMEM;
1260 LPWAVEHDR wh32 = HeapAlloc(GetProcessHeap(), 0, sizeof(LPWAVEHDR) + sizeof(WAVEHDR));
1261 LPWAVEHDR wh16 = MapSL(*lpParam1);
1264 *(LPWAVEHDR*)wh32 = (LPWAVEHDR)*lpParam1;
1265 wh32 = (LPWAVEHDR)((LPSTR)wh32 + sizeof(LPWAVEHDR));
1266 wh32->lpData = MapSL((SEGPTR)wh16->lpData);
1267 wh32->dwBufferLength = wh16->dwBufferLength;
1268 wh32->dwBytesRecorded = wh16->dwBytesRecorded;
1269 wh32->dwUser = wh16->dwUser;
1270 wh32->dwFlags = wh16->dwFlags;
1271 wh32->dwLoops = wh16->dwLoops;
1272 /* FIXME: nothing on wh32->lpNext */
1273 /* could link the wh32->lpNext at this level for memory house keeping */
1274 wh16->lpNext = wh32; /* for reuse in unprepare and write */
1275 *lpParam1 = (DWORD)wh32;
1276 *lpParam2 = sizeof(WAVEHDR);
1278 ret = WINMM_MAP_OKMEM;
1280 ret = WINMM_MAP_NOMEM;
1284 case WODM_UNPREPARE:
1287 LPWAVEHDR wh16 = MapSL(*lpParam1);
1288 LPWAVEHDR wh32 = (LPWAVEHDR)wh16->lpNext;
1290 *lpParam1 = (DWORD)wh32;
1291 *lpParam2 = sizeof(WAVEHDR);
1292 /* dwBufferLength can be reduced between prepare & write */
1293 if (wMsg == WODM_WRITE && wh32->dwBufferLength < wh16->dwBufferLength) {
1294 ERR("Size of buffer has been increased from %d to %d, keeping initial value\n",
1295 wh32->dwBufferLength, wh16->dwBufferLength);
1297 wh32->dwBufferLength = wh16->dwBufferLength;
1298 ret = WINMM_MAP_OKMEM;
1301 case WODM_MAPPER_STATUS:
1302 *lpParam2 = (DWORD)MapSL(*lpParam2);
1306 FIXME("NIY: no conversion yet for %u [%lx,%lx]\n", wMsg, *lpParam1, *lpParam2);
1312 /**************************************************************************
1313 * MMDRV_WaveOut_UnMap16To32W [internal]
1315 static WINMM_MapType MMDRV_WaveOut_UnMap16To32W(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
1317 WINMM_MapType ret = WINMM_MAP_MSGERROR;
1321 case WODM_BREAKLOOP:
1323 case WODM_GETNUMDEVS:
1328 case WODM_SETPLAYBACKRATE:
1329 case WODM_SETVOLUME:
1330 case WODM_MAPPER_STATUS:
1335 case WODM_GETPLAYBACKRATE:
1336 case WODM_GETVOLUME:
1338 FIXME("Shouldn't be used: those 16 bit functions use the 32 bit interface\n");
1341 case WODM_GETDEVCAPS:
1343 LPWAVEOUTCAPSW woc32 = (LPWAVEOUTCAPSW)(*lpParam1);
1344 LPWAVEOUTCAPS16 woc16 = *(LPWAVEOUTCAPS16*)((LPSTR)woc32 - sizeof(LPWAVEOUTCAPS16));
1346 woc16->wMid = woc32->wMid;
1347 woc16->wPid = woc32->wPid;
1348 woc16->vDriverVersion = woc32->vDriverVersion;
1349 WideCharToMultiByte( CP_ACP, 0, woc32->szPname, -1, woc16->szPname,
1350 sizeof(woc16->szPname), NULL, NULL );
1351 woc16->dwFormats = woc32->dwFormats;
1352 woc16->wChannels = woc32->wChannels;
1353 woc16->dwSupport = woc32->dwSupport;
1354 HeapFree(GetProcessHeap(), 0, (LPSTR)woc32 - sizeof(LPWAVEOUTCAPS16));
1360 LPMMTIME mmt32 = (LPMMTIME)(*lpParam1);
1361 LPMMTIME16 mmt16 = *(LPMMTIME16*)((LPSTR)mmt32 - sizeof(LPMMTIME16));
1363 MMSYSTEM_MMTIME32to16(mmt16, mmt32);
1364 HeapFree(GetProcessHeap(), 0, (LPSTR)mmt32 - sizeof(LPMMTIME16));
1369 case WODM_UNPREPARE:
1372 LPWAVEHDR wh32 = (LPWAVEHDR)(*lpParam1);
1373 LPWAVEHDR wh16 = MapSL(*(SEGPTR*)((LPSTR)wh32 - sizeof(LPWAVEHDR)));
1375 assert(wh16->lpNext == wh32);
1376 wh16->dwBufferLength = wh32->dwBufferLength;
1377 wh16->dwBytesRecorded = wh32->dwBytesRecorded;
1378 wh16->dwUser = wh32->dwUser;
1379 wh16->dwFlags = wh32->dwFlags;
1380 wh16->dwLoops = wh32->dwLoops;
1382 if (wMsg == WODM_UNPREPARE && fn_ret == MMSYSERR_NOERROR) {
1383 HeapFree(GetProcessHeap(), 0, (LPSTR)wh32 - sizeof(LPWAVEHDR));
1390 FIXME("NIY: no conversion yet for %u [%lx,%lx]\n", wMsg, *lpParam1, *lpParam2);
1396 /**************************************************************************
1397 * MMDRV_WaveOut_Map32WTo16 [internal]
1399 static WINMM_MapType MMDRV_WaveOut_Map32WTo16 (UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2)
1405 case WODM_BREAKLOOP:
1407 case WODM_GETNUMDEVS:
1412 case WODM_SETPLAYBACKRATE:
1413 case WODM_SETVOLUME:
1417 case WODM_GETDEVCAPS:
1419 LPWAVEOUTCAPSW woc32 = (LPWAVEOUTCAPSW)*lpParam1;
1420 LPSTR ptr = HeapAlloc( GetProcessHeap(), 0,
1421 sizeof(LPWAVEOUTCAPSW) + sizeof(WAVEOUTCAPS16));
1424 *(LPWAVEOUTCAPSW*)ptr = woc32;
1425 ret = WINMM_MAP_OKMEM;
1427 ret = WINMM_MAP_NOMEM;
1429 *lpParam1 = MapLS(ptr) + sizeof(LPWAVEOUTCAPSW);
1430 *lpParam2 = sizeof(WAVEOUTCAPS16);
1434 FIXME("NIY: no conversion yet\n");
1435 ret = WINMM_MAP_MSGERROR;
1437 case WODM_GETPLAYBACKRATE:
1438 FIXME("NIY: no conversion yet\n");
1439 ret = WINMM_MAP_MSGERROR;
1443 LPMMTIME mmt32 = (LPMMTIME)*lpParam1;
1444 LPSTR ptr = HeapAlloc( GetProcessHeap(), 0, sizeof(LPMMTIME) + sizeof(MMTIME16));
1445 LPMMTIME16 mmt16 = (LPMMTIME16)(ptr + sizeof(LPMMTIME));
1448 *(LPMMTIME*)ptr = mmt32;
1449 mmt16->wType = mmt32->wType;
1450 ret = WINMM_MAP_OKMEM;
1452 ret = WINMM_MAP_NOMEM;
1454 *lpParam1 = MapLS(ptr) + sizeof(LPMMTIME);
1455 *lpParam2 = sizeof(MMTIME16);
1458 case WODM_GETVOLUME:
1459 FIXME("NIY: no conversion yet\n");
1460 ret = WINMM_MAP_MSGERROR;
1464 LPWAVEOPENDESC wod32 = (LPWAVEOPENDESC)*lpParam1;
1465 int sz = sizeof(WAVEFORMATEX);
1467 LPWAVEOPENDESC16 wod16;
1469 /* allocated data are mapped as follows:
1470 LPWAVEOPENDESC ptr to orig lParam1
1471 DWORD orig dwUser, which is a pointer to DWORD:driver dwInstance
1472 DWORD dwUser passed to driver
1473 WAVEOPENDESC16 wod16: openDesc passed to driver
1474 WAVEFORMATEX openDesc->lpFormat passed to driver
1475 xxx extra bytes to WAVEFORMATEX
1477 if (wod32->lpFormat->wFormatTag != WAVE_FORMAT_PCM) {
1478 TRACE("Allocating %u extra bytes (%d)\n", ((LPWAVEFORMATEX)wod32->lpFormat)->cbSize, wod32->lpFormat->wFormatTag);
1479 sz += ((LPWAVEFORMATEX)wod32->lpFormat)->cbSize;
1482 ptr = HeapAlloc( GetProcessHeap(), 0,
1483 sizeof(LPWAVEOPENDESC) + 2*sizeof(DWORD) + sizeof(WAVEOPENDESC16) + sz);
1486 SEGPTR seg_ptr = MapLS( ptr );
1487 *(LPWAVEOPENDESC*)ptr = wod32;
1488 *(LPDWORD)((char*)ptr + sizeof(LPWAVEOPENDESC)) = *lpdwUser;
1489 wod16 = (LPWAVEOPENDESC16)((LPSTR)ptr + sizeof(LPWAVEOPENDESC) + 2*sizeof(DWORD));
1491 wod16->hWave = HWAVE_16(wod32->hWave);
1492 wod16->lpFormat = (LPWAVEFORMATEX)(seg_ptr + sizeof(LPWAVEOPENDESC) + 2*sizeof(DWORD) + sizeof(WAVEOPENDESC16));
1493 memcpy(wod16 + 1, wod32->lpFormat, sz);
1495 wod16->dwCallback = wod32->dwCallback;
1496 wod16->dwInstance = wod32->dwInstance;
1497 wod16->uMappedDeviceID = wod32->uMappedDeviceID;
1498 wod16->dnDevNode = wod32->dnDevNode;
1500 *lpParam1 = seg_ptr + sizeof(LPWAVEOPENDESC) + 2*sizeof(DWORD);
1501 *lpdwUser = seg_ptr + sizeof(LPWAVEOPENDESC) + sizeof(DWORD);
1503 ret = WINMM_MAP_OKMEM;
1505 ret = WINMM_MAP_NOMEM;
1511 LPWAVEHDR wh32 = (LPWAVEHDR)*lpParam1;
1513 LPVOID ptr = HeapAlloc( GetProcessHeap(), 0,
1514 sizeof(LPWAVEHDR) + sizeof(WAVEHDR) + wh32->dwBufferLength);
1517 SEGPTR seg_ptr = MapLS( ptr );
1518 *(LPWAVEHDR*)ptr = wh32;
1519 wh16 = (LPWAVEHDR)((LPSTR)ptr + sizeof(LPWAVEHDR));
1520 wh16->lpData = (LPSTR)seg_ptr + sizeof(LPWAVEHDR) + sizeof(WAVEHDR);
1521 /* data will be copied on WODM_WRITE */
1522 wh16->dwBufferLength = wh32->dwBufferLength;
1523 wh16->dwBytesRecorded = wh32->dwBytesRecorded;
1524 wh16->dwUser = wh32->dwUser;
1525 wh16->dwFlags = wh32->dwFlags;
1526 wh16->dwLoops = wh32->dwLoops;
1527 /* FIXME: nothing on wh32->lpNext */
1528 /* could link the wh32->lpNext at this level for memory house keeping */
1529 wh32->lpNext = wh16; /* for reuse in unprepare and write */
1530 *lpParam1 = seg_ptr + sizeof(LPWAVEHDR);
1531 *lpParam2 = sizeof(WAVEHDR);
1532 TRACE("wh16=%08lx wh16->lpData=%p wh32->buflen=%u wh32->lpData=%p\n",
1533 *lpParam1, wh16->lpData, wh32->dwBufferLength, wh32->lpData);
1535 ret = WINMM_MAP_OKMEM;
1537 ret = WINMM_MAP_NOMEM;
1541 case WODM_UNPREPARE:
1544 LPWAVEHDR wh32 = (LPWAVEHDR)(*lpParam1);
1545 LPWAVEHDR wh16 = wh32->lpNext;
1546 LPSTR ptr = (LPSTR)wh16 - sizeof(LPWAVEHDR);
1547 SEGPTR seg_ptr = MapLS( ptr );
1549 assert(*(LPWAVEHDR*)ptr == wh32);
1551 if (wMsg == WODM_WRITE)
1552 memcpy((LPSTR)wh16 + sizeof(WAVEHDR), wh32->lpData, wh32->dwBufferLength);
1554 *lpParam1 = seg_ptr + sizeof(LPWAVEHDR);
1555 *lpParam2 = sizeof(WAVEHDR);
1556 TRACE("wh16=%08lx wh16->lpData=%p wh32->buflen=%u wh32->lpData=%p\n",
1557 *lpParam1, wh16->lpData, wh32->dwBufferLength, wh32->lpData);
1559 /* dwBufferLength can be reduced between prepare & write */
1560 if (wMsg == WODM_WRITE && wh16->dwBufferLength < wh32->dwBufferLength) {
1561 ERR("Size of buffer has been increased from %d to %d, keeping initial value\n",
1562 wh16->dwBufferLength, wh32->dwBufferLength);
1564 wh16->dwBufferLength = wh32->dwBufferLength;
1565 ret = WINMM_MAP_OKMEM;
1568 case DRVM_MAPPER_STATUS:
1570 LPDWORD p32 = (LPDWORD)*lpParam2;
1571 *lpParam2 = MapLS(p32);
1572 ret = WINMM_MAP_OKMEM;
1576 FIXME("NIY: no conversion yet\n");
1577 ret = WINMM_MAP_MSGERROR;
1583 /**************************************************************************
1584 * MMDRV_WaveOut_UnMap32WTo16 [internal]
1586 static WINMM_MapType MMDRV_WaveOut_UnMap32WTo16(UINT wMsg, LPDWORD lpdwUser, DWORD_PTR* lpParam1, DWORD_PTR* lpParam2, MMRESULT fn_ret)
1592 case WODM_BREAKLOOP:
1594 case WODM_GETNUMDEVS:
1599 case WODM_SETPLAYBACKRATE:
1600 case WODM_SETVOLUME:
1604 case WODM_GETDEVCAPS:
1606 LPWAVEOUTCAPS16 woc16 = MapSL(*lpParam1);
1607 LPSTR ptr = (LPSTR)woc16 - sizeof(LPWAVEOUTCAPSW);
1608 LPWAVEOUTCAPSW woc32 = *(LPWAVEOUTCAPSW*)ptr;
1610 woc32->wMid = woc16->wMid;
1611 woc32->wPid = woc16->wPid;
1612 woc32->vDriverVersion = woc16->vDriverVersion;
1613 WideCharToMultiByte( CP_ACP, 0, woc32->szPname, -1, woc16->szPname,
1614 sizeof(woc16->szPname), NULL, NULL );
1615 woc32->dwFormats = woc16->dwFormats;
1616 woc32->wChannels = woc16->wChannels;
1617 woc32->dwSupport = woc16->dwSupport;
1618 UnMapLS( *lpParam1 );
1619 HeapFree( GetProcessHeap(), 0, ptr );
1624 FIXME("NIY: no conversion yet\n");
1625 ret = WINMM_MAP_MSGERROR;
1627 case WODM_GETPLAYBACKRATE:
1628 FIXME("NIY: no conversion yet\n");
1629 ret = WINMM_MAP_MSGERROR;
1633 LPMMTIME16 mmt16 = MapSL(*lpParam1);
1634 LPSTR ptr = (LPSTR)mmt16 - sizeof(LPMMTIME);
1635 LPMMTIME mmt32 = *(LPMMTIME*)ptr;
1637 MMSYSTEM_MMTIME16to32(mmt32, mmt16);
1638 UnMapLS( *lpParam1 );
1639 HeapFree( GetProcessHeap(), 0, ptr );
1645 LPWAVEOPENDESC16 wod16 = MapSL(*lpParam1);
1646 LPSTR ptr = (LPSTR)wod16 - sizeof(LPWAVEOPENDESC) - 2*sizeof(DWORD);
1647 LPWAVEOPENDESC wod32 = *(LPWAVEOPENDESC*)ptr;
1649 wod32->uMappedDeviceID = wod16->uMappedDeviceID;
1650 **(DWORD**)(ptr + sizeof(LPWAVEOPENDESC)) = *(LPDWORD)(ptr + sizeof(LPWAVEOPENDESC) + sizeof(DWORD));
1651 UnMapLS( *lpParam1 );
1652 HeapFree( GetProcessHeap(), 0, ptr );
1657 case WODM_UNPREPARE:
1660 LPWAVEHDR wh16 = MapSL(*lpParam1);
1661 LPSTR ptr = (LPSTR)wh16 - sizeof(LPWAVEHDR);
1662 LPWAVEHDR wh32 = *(LPWAVEHDR*)ptr;
1664 assert(wh32->lpNext == wh16);
1665 wh32->dwBytesRecorded = wh16->dwBytesRecorded;
1666 wh32->dwUser = wh16->dwUser;
1667 wh32->dwFlags = wh16->dwFlags;
1668 wh32->dwLoops = wh16->dwLoops;
1670 UnMapLS( *lpParam1 );
1671 if (wMsg == WODM_UNPREPARE && fn_ret == MMSYSERR_NOERROR) {
1672 HeapFree( GetProcessHeap(), 0, ptr );
1678 case WODM_GETVOLUME:
1679 FIXME("NIY: no conversion yet\n");
1680 ret = WINMM_MAP_MSGERROR;
1682 case DRVM_MAPPER_STATUS:
1684 UnMapLS( *lpParam2 );
1689 FIXME("NIY: no conversion yet\n");
1690 ret = WINMM_MAP_MSGERROR;
1696 /**************************************************************************
1697 * MMDRV_WaveOut_Callback [internal]
1699 static void CALLBACK MMDRV_WaveOut_Callback(HDRVR hDev, UINT uMsg, DWORD_PTR dwInstance, DWORD_PTR dwParam1, DWORD_PTR dwParam2)
1701 LPWINE_MLD mld = (LPWINE_MLD)dwInstance;
1706 /* dwParam1 & dwParam2 are supposed to be 0, nothing to do */
1709 if (mld->bFrom32 && !MMDRV_Is32(mld->mmdIndex)) {
1710 /* initial map is: 32 => 16 */
1711 LPWAVEHDR wh16 = MapSL(dwParam1);
1712 LPWAVEHDR wh32 = *(LPWAVEHDR*)((LPSTR)wh16 - sizeof(LPWAVEHDR));
1714 dwParam1 = (DWORD)wh32;
1715 wh32->dwFlags = wh16->dwFlags;
1716 } else if (!mld->bFrom32 && MMDRV_Is32(mld->mmdIndex)) {
1717 /* initial map is: 16 => 32 */
1718 LPWAVEHDR wh32 = (LPWAVEHDR)(dwParam1);
1719 SEGPTR segwh16 = *(SEGPTR*)((LPSTR)wh32 - sizeof(LPWAVEHDR));
1720 LPWAVEHDR wh16 = MapSL(segwh16);
1722 dwParam1 = (DWORD)segwh16;
1723 wh16->dwFlags = wh32->dwFlags;
1725 /* else { 16 => 16 or 32 => 32, nothing to do, same struct is kept }*/
1728 ERR("Unknown msg %u\n", uMsg);
1731 MMDRV_Callback(mld, hDev, uMsg, dwParam1, dwParam2);
1734 /* =================================
1735 * M A P P E R S H A N D L I N G
1736 * ================================= */
1738 static LRESULT MMDRV_CallMMDrvFunc16(DWORD fp16, WORD dev, WORD msg, LONG instance,
1746 args[5] = HIWORD(instance);
1747 args[4] = LOWORD(instance);
1748 args[3] = HIWORD(lp1);
1749 args[2] = LOWORD(lp1);
1750 args[1] = HIWORD(lp2);
1751 args[0] = LOWORD(lp2);
1752 WOWCallback16Ex( fp16, WCB16_PASCAL, sizeof(args), args, &ret );
1756 /**************************************************************************
1757 * MMDRV_GetDescription16 [internal]
1759 static BOOL MMDRV_GetDescription16(const char* fname, char* buf, int buflen)
1767 if ((hFile = OpenFile(fname, &ofs, OF_READ | OF_SHARE_DENY_WRITE)) == HFILE_ERROR) {
1768 ERR("Can't open file %s (builtin driver ?)\n", fname);
1772 #define E(_x) do {TRACE _x;goto theEnd;} while(0)
1774 if (_lread(hFile, &w, 2) != 2) E(("Can't read sig\n"));
1775 if (w != ('Z' * 256 + 'M')) E(("Bad sig %04x\n", w));
1776 if (_llseek(hFile, 0x3C, SEEK_SET) < 0) E(("Can't seek to ext header offset\n"));
1777 if (_lread(hFile, &dw, 4) != 4) E(("Can't read ext header offset\n"));
1778 if (_llseek(hFile, dw + 0x2C, SEEK_SET) < 0) E(("Can't seek to ext header.nr table %u\n", dw+0x2C));
1779 if (_lread(hFile, &dw, 4) != 4) E(("Can't read nr table offset\n"));
1780 if (_llseek(hFile, dw, SEEK_SET) < 0) E(("Can't seek to nr table %u\n", dw));
1781 if (_lread(hFile, buf, 1) != 1) E(("Can't read descr length\n"));
1782 buflen = min((int)(unsigned)(BYTE)buf[0], buflen - 1);
1783 if (_lread(hFile, buf, buflen) != buflen) E(("Can't read descr (%d)\n", buflen));
1786 TRACE("Got '%s' [%d]\n", buf, buflen);
1792 /******************************************************************
1793 * MMDRV_LoadMMDrvFunc16
1796 unsigned MMDRV_LoadMMDrvFunc16(LPCSTR drvName, LPWINE_DRIVER d,
1797 LPWINE_MM_DRIVER lpDrv)
1799 WINEMM_msgFunc16 func;
1803 * DESCRIPTION 'wave,aux,mixer:Creative Labs Sound Blaster 16 Driver'
1804 * The beginning of the module description indicates the driver supports
1805 * waveform, auxiliary, and mixer devices. Use one of the following
1806 * device-type names, followed by a colon (:) to indicate the type of
1807 * device your driver supports. If the driver supports more than one
1808 * type of device, separate each device-type name with a comma (,).
1810 * wave for waveform audio devices
1811 * wavemapper for wave mappers
1812 * midi for MIDI audio devices
1813 * midimapper for midi mappers
1814 * aux for auxiliary audio devices
1815 * mixer for mixer devices
1818 if (d->d.d16.hDriver16) {
1819 HMODULE16 hMod16 = GetDriverModuleHandle16(d->d.d16.hDriver16);
1821 #define AA(_h,_w,_x,_y,_z) \
1822 func = (WINEMM_msgFunc##_y) _z ((_h), #_x); \
1824 { lpDrv->parts[_w].u.fnMessage##_y = func; count++; \
1825 TRACE("Got %d bit func '%s'\n", _y, #_x); }
1827 #define A(_x,_y) AA(hMod16,_x,_y,16,GetProcAddress16)
1828 A(MMDRV_AUX, auxMessage);
1829 A(MMDRV_MIXER, mxdMessage);
1830 A(MMDRV_MIDIIN, midMessage);
1831 A(MMDRV_MIDIOUT,modMessage);
1832 A(MMDRV_WAVEIN, widMessage);
1833 A(MMDRV_WAVEOUT,wodMessage);
1837 if (TRACE_ON(winmm)) {
1838 if (MMDRV_GetDescription16(drvName, buffer, sizeof(buffer)))
1839 TRACE("%s => %s\n", drvName, buffer);
1841 TRACE("%s => No description\n", drvName);
1847 /* =================================
1849 * ================================= */
1852 /* FIXME: this code is kept for not yet implemented optimisation for an application
1853 * using the 32A MCI interface and calling a 16 bit driver.
1854 * For now, we're doing two conversions:
1855 * - 32A => 32W (in 32 bit MCI code)
1856 * - 32W => 16 in this file
1861 * 0001 squeeze signed 4 bytes to 2 bytes *( LPINT16)D = ( INT16)*( LPINT16)S; D += 2; S += 4
1862 * 0010 squeeze unsigned 4 bytes to 2 bytes *(LPUINT16)D = (UINT16)*(LPUINT16)S; D += 2; S += 4
1865 * 0110 zero 4 bytes *(DWORD)D = 0 D += 4; S += 4
1866 * 0111 copy string *(LPSTR*)D = seg dup(*(LPSTR*)S) D += 4; S += 4
1867 * 1xxx copy xxx + 1 bytes memcpy(D, S, xxx + 1); D += xxx+1; S += xxx+1
1870 /**************************************************************************
1871 * MCI_MsgMapper32ATo16_Create [internal]
1873 * Helper for MCI_MapMsg32ATo16.
1874 * Maps the 32 bit pointer (*ptr), of size bytes, to an allocated 16 bit
1875 * segmented pointer.
1876 * map contains a list of action to be performed for the mapping (see list
1878 * if keep is TRUE, keeps track of in 32 bit ptr in allocated 16 bit area.
1880 static WINMM_MapType MCI_MsgMapper32ATo16_Create(void** ptr, int size16, DWORD map, BOOLEAN keep)
1882 void* lp = HeapAlloc( GetProcessHeap(), 0, (keep ? sizeof(void**) : 0) + size16 );
1886 return WINMM_MAP_NOMEM;
1888 p32 = (LPBYTE)(*ptr);
1891 p16 = (LPBYTE)lp + sizeof(void**);
1892 *ptr = (char*)MapLS(lp) + sizeof(void**);
1895 *ptr = (void*)MapLS(lp);
1899 memcpy(p16, p32, size16);
1907 sz = (nibble & 7) + 1;
1908 memcpy(p16, p32, sz);
1911 size16 -= sz; /* DEBUG only */
1915 *(LPINT16)p16 = *(LPINT)p32;
1916 p16 += sizeof(INT16);
1918 size16 -= sizeof(INT16);
1921 *(LPUINT16)p16 = *(LPUINT)p32;
1922 p16 += sizeof(UINT16);
1923 p32 += sizeof(UINT);
1924 size16 -= sizeof(UINT16);
1928 p16 += sizeof(DWORD);
1929 p32 += sizeof(DWORD);
1930 size16 -= sizeof(DWORD);
1933 *(SEGPTR *)p16 = MapLS( *(LPSTR *)p32 );
1934 p16 += sizeof(SEGPTR);
1935 p32 += sizeof(LPSTR);
1936 size16 -= sizeof(SEGPTR);
1939 FIXME("Unknown nibble for mapping (%x)\n", nibble);
1944 if (size16 != 0) /* DEBUG only */
1945 FIXME("Mismatch between 16 bit struct size and map nibbles serie\n");
1947 return WINMM_MAP_OKMEM;
1950 /**************************************************************************
1951 * MCI_MsgMapper32ATo16_Destroy [internal]
1953 * Helper for MCI_UnMapMsg32ATo16.
1955 static WINMM_MapType MCI_MsgMapper32ATo16_Destroy(void* ptr, int size16, DWORD map, BOOLEAN kept)
1958 void* msg16 = MapSL((SEGPTR)ptr);
1963 UnMapLS( (SEGPTR)ptr );
1965 alloc = (char*)msg16 - sizeof(void**);
1966 p32 = *(void**)alloc;
1970 memcpy(p32, p16, size16);
1975 memcpy(p32, p16, (nibble & 7) + 1);
1976 p16 += (nibble & 7) + 1;
1977 p32 += (nibble & 7) + 1;
1978 size16 -= (nibble & 7) + 1;
1982 *(LPINT)p32 = *(LPINT16)p16;
1983 p16 += sizeof(INT16);
1985 size16 -= sizeof(INT16);
1988 *(LPUINT)p32 = *(LPUINT16)p16;
1989 p16 += sizeof(UINT16);
1990 p32 += sizeof(UINT);
1991 size16 -= sizeof(UINT16);
1994 p16 += sizeof(UINT);
1995 p32 += sizeof(UINT);
1996 size16 -= sizeof(UINT);
1999 UnMapLS( *(SEGPTR *)p16 );
2000 p16 += sizeof(SEGPTR);
2001 p32 += sizeof(char*);
2002 size16 -= sizeof(SEGPTR);
2005 FIXME("Unknown nibble for mapping (%x)\n", nibble);
2010 if (size16 != 0) /* DEBUG only */
2011 FIXME("Mismatch between 16 bit struct size and map nibbles serie\n");
2017 HeapFree( GetProcessHeap(), 0, alloc );
2019 return WINMM_MAP_OK;
2022 /**************************************************************************
2023 * MCI_MapMsg32ATo16 [internal]
2025 * Map a 32-A bit MCI message to a 16 bit MCI message.
2027 static WINMM_MapType MCI_MapMsg32ATo16(WORD uDevType, WORD wMsg, DWORD dwFlags, DWORD* lParam)
2030 BOOLEAN keep = FALSE;
2034 return WINMM_MAP_OK;
2036 /* FIXME: to add also (with seg/linear modifications to do):
2037 * MCI_LIST, MCI_LOAD, MCI_QUALITY, MCI_RESERVE, MCI_RESTORE, MCI_SAVE
2038 * MCI_SETAUDIO, MCI_SETTUNER, MCI_SETVIDEO
2042 size = sizeof(MCI_BREAK_PARMS);
2044 /* case MCI_CAPTURE */
2046 case MCI_CLOSE_DRIVER:
2048 size = sizeof(MCI_GENERIC_PARMS);
2050 /* case MCI_COPY: */
2053 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_CUE_PARMS); break;
2054 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_CUE_PARMS); break;*/ FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
2055 default: size = sizeof(MCI_GENERIC_PARMS); break;
2061 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_DELETE_PARMS16); map = 0x0F1111FB; break;
2062 case MCI_DEVTYPE_WAVEFORM_AUDIO:size = sizeof(MCI_WAVE_DELETE_PARMS); break;
2063 default: size = sizeof(MCI_GENERIC_PARMS); break;
2066 /* case MCI_ESCAPE: */
2069 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_FREEZE_PARMS); map = 0x0001111B; break;
2070 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_RECT_PARMS); map = 0x0001111B; break;
2071 default: size = sizeof(MCI_GENERIC_PARMS); break;
2074 case MCI_GETDEVCAPS:
2076 size = sizeof(MCI_GETDEVCAPS_PARMS);
2078 /* case MCI_INDEX: */
2081 LPMCI_INFO_PARMSA mip32a = (LPMCI_INFO_PARMSA)(*lParam);
2082 LPMCI_INFO_PARMS16 mip16;
2085 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_INFO_PARMS16); break;
2086 default: size = sizeof(MCI_INFO_PARMS16); break;
2088 mip16 = HeapAlloc( GetProcessHeap(), 0, size);
2091 mip16->dwCallback = mip32a->dwCallback;
2092 mip16->lpstrReturn = MapLS( mip32a->lpstrReturn );
2093 mip16->dwRetSize = mip32a->dwRetSize;
2094 if (uDevType == MCI_DEVTYPE_DIGITAL_VIDEO) {
2095 ((LPMCI_DGV_INFO_PARMS16)mip16)->dwItem = ((LPMCI_DGV_INFO_PARMSA)mip32a)->dwItem;
2098 return WINMM_MAP_NOMEM;
2100 *lParam = MapLS(mip16);
2102 return WINMM_MAP_OKMEM;
2103 /* case MCI_MARK: */
2104 /* case MCI_MONITOR: */
2106 case MCI_OPEN_DRIVER:
2108 LPMCI_OPEN_PARMSA mop32a = (LPMCI_OPEN_PARMSA)(*lParam);
2109 char* ptr = HeapAlloc( GetProcessHeap(), 0,
2110 sizeof(LPMCI_OPEN_PARMSA) + sizeof(MCI_OPEN_PARMS16) + 2 * sizeof(DWORD));
2111 LPMCI_OPEN_PARMS16 mop16;
2115 *(LPMCI_OPEN_PARMSA*)(ptr) = mop32a;
2116 mop16 = (LPMCI_OPEN_PARMS16)(ptr + sizeof(LPMCI_OPEN_PARMSA));
2117 mop16->dwCallback = mop32a->dwCallback;
2118 mop16->wDeviceID = mop32a->wDeviceID;
2119 if (dwFlags & MCI_OPEN_TYPE) {
2120 if (dwFlags & MCI_OPEN_TYPE_ID) {
2121 /* dword "transparent" value */
2122 mop16->lpstrDeviceType = (SEGPTR)mop32a->lpstrDeviceType;
2125 mop16->lpstrDeviceType = MapLS( mop32a->lpstrDeviceType );
2129 mop16->lpstrDeviceType = 0;
2131 if (dwFlags & MCI_OPEN_ELEMENT) {
2132 if (dwFlags & MCI_OPEN_ELEMENT_ID) {
2133 mop16->lpstrElementName = (SEGPTR)mop32a->lpstrElementName;
2135 mop16->lpstrElementName = MapLS( mop32a->lpstrElementName );
2138 mop16->lpstrElementName = 0;
2140 if (dwFlags & MCI_OPEN_ALIAS) {
2141 mop16->lpstrAlias = MapLS( mop32a->lpstrAlias );
2143 mop16->lpstrAlias = 0;
2145 /* copy extended information if any...
2146 * FIXME: this may seg fault if initial structure does not contain them and
2147 * the reads after msip16 fail under LDT limits...
2148 * NOTE: this should be split in two. First pass, while calling MCI_OPEN, and
2149 * should not take care of extended parameters, and should be used by MCI_Open
2150 * to fetch uDevType. When, this is known, the mapping for sending the
2151 * MCI_OPEN_DRIVER shall be done depending on uDevType.
2153 memcpy(mop16 + 1, mop32a + 1, 2 * sizeof(DWORD));
2155 return WINMM_MAP_NOMEM;
2157 *lParam = (LPARAM)MapLS(ptr) + sizeof(LPMCI_OPEN_PARMSA);
2159 return WINMM_MAP_OKMEM;
2160 /* case MCI_PASTE:*/
2162 size = sizeof(MCI_GENERIC_PARMS);
2165 size = sizeof(MCI_PLAY_PARMS);
2169 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_RECT_PARMS16); map = 0x0001111B; break;
2170 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_RECT_PARMS); map = 0x0001111B; break;
2171 default: size = sizeof(MCI_GENERIC_PARMS); break;
2175 size = sizeof(MCI_GENERIC_PARMS);
2179 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_RECORD_PARMS16); map = 0x0F1111FB; break;
2180 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_RECORD_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
2181 default: size = sizeof(MCI_RECORD_PARMS); break;
2185 size = sizeof(MCI_GENERIC_PARMS);
2189 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_SEEK_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
2190 default: size = sizeof(MCI_SEEK_PARMS); break;
2195 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_SET_PARMS); break;
2196 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_SET_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
2197 case MCI_DEVTYPE_SEQUENCER: size = sizeof(MCI_SEQ_SET_PARMS); break;
2198 /* FIXME: normally the 16 and 32 bit structures are byte by byte aligned,
2199 * so not doing anything should work...
2201 case MCI_DEVTYPE_WAVEFORM_AUDIO:size = sizeof(MCI_WAVE_SET_PARMS); break;
2202 default: size = sizeof(MCI_SET_PARMS); break;
2207 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_SETAUDIO_PARMS16);map = 0x0000077FF; break;
2208 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_SETAUDIO_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
2209 default: size = sizeof(MCI_GENERIC_PARMS); break;
2212 /* case MCI_SETTIMECODE:*/
2213 /* case MCI_SIGNAL:*/
2214 /* case MCI_SOUND:*/
2216 size = sizeof(MCI_SET_PARMS);
2222 * don't know if buffer for value is the one passed through lpstrDevice
2223 * or is provided by MCI driver.
2224 * Assuming solution 2: provided by MCI driver, so zeroing on entry
2226 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_STATUS_PARMS16); map = 0x0B6FF; break;
2227 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_STATUS_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
2228 default: size = sizeof(MCI_STATUS_PARMS); break;
2233 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_STEP_PARMS); break;
2234 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_STEP_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
2235 case MCI_DEVTYPE_VIDEODISC: size = sizeof(MCI_VD_STEP_PARMS); break;
2236 default: size = sizeof(MCI_GENERIC_PARMS); break;
2240 size = sizeof(MCI_SET_PARMS);
2244 LPMCI_SYSINFO_PARMSA msip32a = (LPMCI_SYSINFO_PARMSA)(*lParam);
2245 LPMCI_SYSINFO_PARMS16 msip16;
2246 char* ptr = HeapAlloc( GetProcessHeap(), 0,
2247 sizeof(LPMCI_SYSINFO_PARMSA) + sizeof(MCI_SYSINFO_PARMS16) );
2250 *(LPMCI_SYSINFO_PARMSA*)(ptr) = msip32a;
2251 msip16 = (LPMCI_SYSINFO_PARMS16)(ptr + sizeof(LPMCI_SYSINFO_PARMSA));
2253 msip16->dwCallback = msip32a->dwCallback;
2254 msip16->lpstrReturn = MapLS( msip32a->lpstrReturn );
2255 msip16->dwRetSize = msip32a->dwRetSize;
2256 msip16->dwNumber = msip32a->dwNumber;
2257 msip16->wDeviceType = msip32a->wDeviceType;
2259 return WINMM_MAP_NOMEM;
2261 *lParam = (LPARAM)MapLS(ptr) + sizeof(LPMCI_SYSINFO_PARMSA);
2263 return WINMM_MAP_OKMEM;
2264 /* case MCI_UNDO: */
2267 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_RECT_PARMS16); map = 0x0001111B; break;
2268 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_RECT_PARMS16); map = 0x0001111B; break;
2269 default: size = sizeof(MCI_GENERIC_PARMS); break;
2274 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_UPDATE_PARMS16); map = 0x000B1111B; break;
2275 default: size = sizeof(MCI_GENERIC_PARMS); break;
2280 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_RECT_PARMS16); map = 0x0001111B; keep = TRUE; break;
2281 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_RECT_PARMS16); map = 0x0001111B; keep = TRUE; break;
2282 default: size = sizeof(MCI_GENERIC_PARMS); break;
2287 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_WINDOW_PARMS16); if (dwFlags & MCI_DGV_WINDOW_TEXT) map = 0x7FB; break;
2288 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_WINDOW_PARMS16); if (dwFlags & MCI_OVLY_WINDOW_TEXT) map = 0x7FB; break;
2289 default: size = sizeof(MCI_GENERIC_PARMS); break;
2294 LPMCI_OPEN_DRIVER_PARMSA modp32a = (LPMCI_OPEN_DRIVER_PARMSA)(*lParam);
2295 LPMCI_OPEN_DRIVER_PARMS16 modp16;
2296 char *ptr = HeapAlloc( GetProcessHeap(), 0,
2297 sizeof(LPMCI_OPEN_DRIVER_PARMSA) + sizeof(MCI_OPEN_DRIVER_PARMS16));
2300 *(LPMCI_OPEN_DRIVER_PARMSA*)(ptr) = modp32a;
2301 modp16 = (LPMCI_OPEN_DRIVER_PARMS16)(ptr + sizeof(LPMCI_OPEN_DRIVER_PARMSA));
2302 modp16->wDeviceID = modp32a->wDeviceID;
2303 modp16->lpstrParams = MapLS( modp32a->lpstrParams );
2304 /* other fields are gonna be filled by the driver, don't copy them */
2306 return WINMM_MAP_NOMEM;
2308 *lParam = (LPARAM)MapLS(ptr) + sizeof(LPMCI_OPEN_DRIVER_PARMSA);
2310 return WINMM_MAP_OKMEM;
2317 case DRV_QUERYCONFIGURE:
2320 case DRV_EXITSESSION:
2321 case DRV_EXITAPPLICATION:
2323 return WINMM_MAP_OK;
2326 FIXME("Don't know how to map msg=%s\n", MCI_MessageToString(wMsg));
2327 return WINMM_MAP_MSGERROR;
2329 return MCI_MsgMapper32ATo16_Create((void**)lParam, size, map, keep);
2332 /**************************************************************************
2333 * MCI_UnMapMsg32ATo16 [internal]
2335 static WINMM_MapType MCI_UnMapMsg32ATo16(WORD uDevType, WORD wMsg, DWORD dwFlags, DWORD lParam)
2338 BOOLEAN kept = FALSE; /* there is no need to compute size when kept is FALSE */
2344 /* case MCI_CAPTURE */
2346 case MCI_CLOSE_DRIVER:
2349 /* case MCI_COPY: */
2355 /* case MCI_ESCAPE: */
2358 case MCI_GETDEVCAPS:
2360 size = sizeof(MCI_GETDEVCAPS_PARMS);
2362 /* case MCI_INDEX: */
2365 LPMCI_INFO_PARMS16 mip16 = (LPMCI_INFO_PARMS16)MapSL(lParam);
2367 UnMapLS( mip16->lpstrReturn );
2368 HeapFree( GetProcessHeap(), 0, mip16 );
2370 return WINMM_MAP_OK;
2371 /* case MCI_MARK: */
2372 /* case MCI_MONITOR: */
2374 case MCI_OPEN_DRIVER:
2376 LPMCI_OPEN_PARMS16 mop16 = (LPMCI_OPEN_PARMS16)MapSL(lParam);
2377 LPMCI_OPEN_PARMSA mop32a = *(LPMCI_OPEN_PARMSA*)((char*)mop16 - sizeof(LPMCI_OPEN_PARMSA));
2379 mop32a->wDeviceID = mop16->wDeviceID;
2380 if ((dwFlags & MCI_OPEN_TYPE) && !(dwFlags & MCI_OPEN_TYPE_ID))
2381 UnMapLS( mop16->lpstrDeviceType );
2382 if ((dwFlags & MCI_OPEN_ELEMENT) && !(dwFlags & MCI_OPEN_ELEMENT_ID))
2383 UnMapLS( mop16->lpstrElementName );
2384 if (dwFlags & MCI_OPEN_ALIAS)
2385 UnMapLS( mop16->lpstrAlias );
2386 HeapFree( GetProcessHeap(), 0, (char*)mop16 - sizeof(LPMCI_OPEN_PARMSA) );
2388 return WINMM_MAP_OK;
2389 /* case MCI_PASTE:*/
2408 case MCI_DEVTYPE_DIGITAL_VIDEO: map = 0x0000077FF; break;
2409 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_SETAUDIO_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
2412 /* case MCI_SETTIMECODE:*/
2413 /* case MCI_SIGNAL:*/
2414 /* case MCI_SOUND:*/
2420 case MCI_DEVTYPE_DIGITAL_VIDEO:
2422 LPMCI_DGV_STATUS_PARMS16 mdsp16 = (LPMCI_DGV_STATUS_PARMS16)MapSL(lParam);
2423 LPMCI_DGV_STATUS_PARMSA mdsp32a = *(LPMCI_DGV_STATUS_PARMSA*)((char*)mdsp16 - sizeof(LPMCI_DGV_STATUS_PARMSA));
2427 mdsp32a->dwReturn = mdsp16->dwReturn;
2428 if (dwFlags & MCI_DGV_STATUS_DISKSPACE) {
2429 TRACE("MCI_STATUS (DGV) lpstrDrive=%08lx\n", mdsp16->lpstrDrive);
2430 TRACE("MCI_STATUS (DGV) lpstrDrive=%s\n", (LPSTR)MapSL(mdsp16->lpstrDrive));
2431 UnMapLS( mdsp16->lpstrDrive );
2433 HeapFree( GetProcessHeap(), 0, (char*)mdsp16 - sizeof(LPMCI_DGV_STATUS_PARMSA) );
2435 return WINMM_MAP_NOMEM;
2438 return WINMM_MAP_OKMEM;
2439 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_STATUS_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
2440 default: size = sizeof(MCI_STATUS_PARMS); break;
2449 LPMCI_SYSINFO_PARMS16 msip16 = (LPMCI_SYSINFO_PARMS16)MapSL(lParam);
2450 LPMCI_SYSINFO_PARMSA msip32a = *(LPMCI_SYSINFO_PARMSA*)((char*)msip16 - sizeof(LPMCI_SYSINFO_PARMSA));
2454 msip16->dwCallback = msip32a->dwCallback;
2455 UnMapLS( msip16->lpstrReturn );
2456 HeapFree( GetProcessHeap(), 0, (char*)msip16 - sizeof(LPMCI_SYSINFO_PARMSA) );
2458 return WINMM_MAP_NOMEM;
2461 return WINMM_MAP_OKMEM;
2462 /* case MCI_UNDO: */
2469 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_RECT_PARMS16); map = 0x0001111B; kept = TRUE; break;
2470 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_RECT_PARMS16); map = 0x0001111B; kept = TRUE; break;
2476 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_WINDOW_PARMS16); if (dwFlags & MCI_DGV_WINDOW_TEXT) map = 0x7666; break;
2477 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_WINDOW_PARMS16); if (dwFlags & MCI_OVLY_WINDOW_TEXT) map = 0x7666; break;
2480 /* FIXME: see map function */
2485 LPMCI_OPEN_DRIVER_PARMS16 modp16 = (LPMCI_OPEN_DRIVER_PARMS16)MapSL(lParam);
2486 LPMCI_OPEN_DRIVER_PARMSA modp32a = *(LPMCI_OPEN_DRIVER_PARMSA*)((char*)modp16 - sizeof(LPMCI_OPEN_DRIVER_PARMSA));
2489 modp32a->wCustomCommandTable = modp16->wCustomCommandTable;
2490 modp32a->wType = modp16->wType;
2491 UnMapLS( modp16->lpstrParams );
2492 HeapFree( GetProcessHeap(), 0, (char *)modp16 - sizeof(LPMCI_OPEN_DRIVER_PARMSA) );
2494 return WINMM_MAP_OK;
2501 case DRV_QUERYCONFIGURE:
2504 case DRV_EXITSESSION:
2505 case DRV_EXITAPPLICATION:
2507 FIXME("This is a hack\n");
2508 return WINMM_MAP_OK;
2510 FIXME("Map/Unmap internal error on msg=%s\n", MCI_MessageToString(wMsg));
2511 return WINMM_MAP_MSGERROR;
2513 return MCI_MsgMapper32ATo16_Destroy((void*)lParam, size, map, kept);
2517 /**************************************************************************
2518 * MCI_MapMsg16To32W [internal]
2520 static WINMM_MapType MCI_MapMsg16To32W(WORD uDevType, WORD wMsg, DWORD dwFlags, DWORD_PTR* lParam)
2523 return WINMM_MAP_OK;
2524 /* FIXME: to add also (with seg/linear modifications to do):
2525 * MCI_LIST, MCI_LOAD, MCI_QUALITY, MCI_RESERVE, MCI_RESTORE, MCI_SAVE
2526 * MCI_SETAUDIO, MCI_SETTUNER, MCI_SETVIDEO
2529 /* case MCI_CAPTURE */
2531 case MCI_CLOSE_DRIVER:
2538 case MCI_GETDEVCAPS:
2539 /* case MCI_INDEX: */
2540 /* case MCI_MARK: */
2541 /* case MCI_MONITOR: */
2551 /* case MCI_SETTIMECODE:*/
2552 /* case MCI_SIGNAL:*/
2554 case MCI_STATUS: /* FIXME: is wrong for digital video */
2557 /* case MCI_UNDO: */
2561 *lParam = (DWORD)MapSL(*lParam);
2562 return WINMM_MAP_OK;
2564 /* in fact, I would also need the dwFlags... to see
2565 * which members of lParam are effectively used
2567 *lParam = (DWORD)MapSL(*lParam);
2568 FIXME("Current mapping may be wrong\n");
2572 LPMCI_BREAK_PARMS mbp32 = HeapAlloc(GetProcessHeap(), 0, sizeof(MCI_BREAK_PARMS));
2573 LPMCI_BREAK_PARMS16 mbp16 = MapSL(*lParam);
2576 mbp32->dwCallback = mbp16->dwCallback;
2577 mbp32->nVirtKey = mbp16->nVirtKey;
2578 mbp32->hwndBreak = HWND_32(mbp16->hwndBreak);
2580 return WINMM_MAP_NOMEM;
2582 *lParam = (DWORD)mbp32;
2584 return WINMM_MAP_OKMEM;
2587 LPMCI_VD_ESCAPE_PARMSW mvep32w = HeapAlloc(GetProcessHeap(), 0, sizeof(MCI_VD_ESCAPE_PARMSW));
2588 LPMCI_VD_ESCAPE_PARMS16 mvep16 = MapSL(*lParam);
2591 mvep32w->dwCallback = mvep16->dwCallback;
2592 mvep32w->lpstrCommand = MCI_strdupAtoW(MapSL(mvep16->lpstrCommand));
2594 return WINMM_MAP_NOMEM;
2596 *lParam = (DWORD)mvep32w;
2598 return WINMM_MAP_OKMEM;
2601 LPMCI_INFO_PARMSW mip32w = HeapAlloc(GetProcessHeap(), 0, sizeof(LPMCI_OPEN_PARMS16) + sizeof(MCI_INFO_PARMSW));
2602 LPMCI_INFO_PARMS16 mip16 = MapSL(*lParam);
2604 /* FIXME this is wrong if device is of type
2605 * MCI_DEVTYPE_DIGITAL_VIDEO, some members are not mapped
2608 *(LPMCI_INFO_PARMS16*)(mip32w) = mip16;
2609 mip32w = (LPMCI_INFO_PARMSW)((char*)mip32w + sizeof(LPMCI_INFO_PARMS16));
2610 mip32w->dwCallback = mip16->dwCallback;
2611 mip32w->lpstrReturn = HeapAlloc(GetProcessHeap(), 0, mip16->dwRetSize * sizeof(WCHAR));
2612 mip32w->dwRetSize = mip16->dwRetSize * sizeof(WCHAR);
2614 return WINMM_MAP_NOMEM;
2616 *lParam = (DWORD)mip32w;
2618 return WINMM_MAP_OKMEM;
2620 case MCI_OPEN_DRIVER:
2622 LPMCI_OPEN_PARMSW mop32w = HeapAlloc(GetProcessHeap(), 0, sizeof(LPMCI_OPEN_PARMS16) + sizeof(MCI_OPEN_PARMSW) + 2 * sizeof(DWORD));
2623 LPMCI_OPEN_PARMS16 mop16 = MapSL(*lParam);
2626 *(LPMCI_OPEN_PARMS16*)(mop32w) = mop16;
2627 mop32w = (LPMCI_OPEN_PARMSW)((char*)mop32w + sizeof(LPMCI_OPEN_PARMS16));
2628 mop32w->dwCallback = mop16->dwCallback;
2629 mop32w->wDeviceID = mop16->wDeviceID;
2630 if( ( dwFlags & ( MCI_OPEN_TYPE | MCI_OPEN_TYPE_ID)) == MCI_OPEN_TYPE)
2631 mop32w->lpstrDeviceType = MCI_strdupAtoW(MapSL(mop16->lpstrDeviceType));
2633 mop32w->lpstrDeviceType = (LPWSTR) mop16->lpstrDeviceType;
2634 if( ( dwFlags & ( MCI_OPEN_ELEMENT | MCI_OPEN_ELEMENT_ID)) == MCI_OPEN_ELEMENT)
2635 mop32w->lpstrElementName = MCI_strdupAtoW(MapSL(mop16->lpstrElementName));
2637 mop32w->lpstrElementName = (LPWSTR) mop16->lpstrElementName;
2638 if( ( dwFlags & MCI_OPEN_ALIAS))
2639 mop32w->lpstrAlias = MCI_strdupAtoW(MapSL(mop16->lpstrAlias));
2641 mop32w->lpstrAlias = (LPWSTR) mop16->lpstrAlias;
2642 /* copy extended information if any...
2643 * FIXME: this may seg fault if initial structure does not contain them and
2644 * the reads after msip16 fail under LDT limits...
2645 * NOTE: this should be split in two. First pass, while calling MCI_OPEN, and
2646 * should not take care of extended parameters, and should be used by MCI_Open
2647 * to fetch uDevType. When, this is known, the mapping for sending the
2648 * MCI_OPEN_DRIVER shall be done depending on uDevType.
2650 memcpy(mop32w + 1, mop16 + 1, 2 * sizeof(DWORD));
2652 return WINMM_MAP_NOMEM;
2654 *lParam = (DWORD)mop32w;
2656 return WINMM_MAP_OKMEM;
2659 LPMCI_SYSINFO_PARMSW msip32w = HeapAlloc(GetProcessHeap(), 0, sizeof(LPMCI_OPEN_PARMS16) + sizeof(MCI_SYSINFO_PARMSW));
2660 LPMCI_SYSINFO_PARMS16 msip16 = MapSL(*lParam);
2663 *(LPMCI_SYSINFO_PARMS16*)(msip32w) = msip16;
2664 msip32w = (LPMCI_SYSINFO_PARMSW)((char*)msip32w + sizeof(LPMCI_OPEN_PARMS16));
2665 msip32w->dwCallback = msip16->dwCallback;
2666 msip32w->lpstrReturn = HeapAlloc(GetProcessHeap(), 0, msip16->dwRetSize * sizeof(WCHAR));
2667 msip32w->dwRetSize = msip16->dwRetSize;
2668 msip32w->dwNumber = msip16->dwNumber;
2669 msip32w->wDeviceType = msip16->wDeviceType;
2671 return WINMM_MAP_NOMEM;
2673 *lParam = (DWORD)msip32w;
2675 return WINMM_MAP_OKMEM;
2678 LPMCI_SOUND_PARMSW mbp32 = HeapAlloc(GetProcessHeap(), 0, sizeof(MCI_SOUND_PARMSW));
2679 LPMCI_SOUND_PARMS16 mbp16 = MapSL(*lParam);
2682 mbp32->dwCallback = mbp16->dwCallback;
2683 mbp32->lpstrSoundName = MCI_strdupAtoW(MapSL(mbp16->lpstrSoundName));
2685 return WINMM_MAP_NOMEM;
2687 *lParam = (DWORD)mbp32;
2689 return WINMM_MAP_OKMEM;
2697 case DRV_QUERYCONFIGURE:
2700 case DRV_EXITSESSION:
2701 case DRV_EXITAPPLICATION:
2703 FIXME("This is a hack\n");
2704 return WINMM_MAP_OK;
2706 FIXME("Don't know how to map msg=%s\n", MCI_MessageToString(wMsg));
2708 return WINMM_MAP_MSGERROR;
2711 /**************************************************************************
2712 * MCI_UnMapMsg16To32W [internal]
2714 static WINMM_MapType MCI_UnMapMsg16To32W(WORD uDevType, WORD wMsg, DWORD dwFlags, DWORD_PTR lParam)
2717 /* case MCI_CAPTURE */
2719 case MCI_CLOSE_DRIVER:
2726 case MCI_GETDEVCAPS:
2727 /* case MCI_INDEX: */
2728 /* case MCI_MARK: */
2729 /* case MCI_MONITOR: */
2739 /* case MCI_SETTIMECODE:*/
2740 /* case MCI_SIGNAL:*/
2745 /* case MCI_UNDO: */
2749 return WINMM_MAP_OK;
2752 /* FIXME ?? see Map function */
2753 return WINMM_MAP_OK;
2756 HeapFree(GetProcessHeap(), 0, (LPVOID)lParam);
2757 return WINMM_MAP_OK;
2760 LPMCI_VD_ESCAPE_PARMSW mvep32W = (LPMCI_VD_ESCAPE_PARMSW)lParam;
2761 HeapFree(GetProcessHeap(), 0, (LPVOID)mvep32W->lpstrCommand);
2762 HeapFree(GetProcessHeap(), 0, (LPVOID)lParam);
2764 return WINMM_MAP_OK;
2767 LPMCI_INFO_PARMSW mip32w = (LPMCI_INFO_PARMSW)lParam;
2768 LPMCI_INFO_PARMS16 mip16 = *(LPMCI_INFO_PARMS16*)((char*)mip32w - sizeof(LPMCI_INFO_PARMS16));
2770 WideCharToMultiByte(CP_ACP, 0,
2771 mip32w->lpstrReturn, mip32w->dwRetSize / sizeof(WCHAR),
2772 MapSL(mip16->lpstrReturn), mip16->dwRetSize,
2774 HeapFree(GetProcessHeap(), 0, (LPVOID)mip32w->lpstrReturn);
2775 HeapFree(GetProcessHeap(), 0, (LPVOID)lParam);
2777 return WINMM_MAP_OK;
2780 LPMCI_SYSINFO_PARMSW msip32w = (LPMCI_SYSINFO_PARMSW)lParam;
2781 LPMCI_SYSINFO_PARMS16 msip16 = *(LPMCI_SYSINFO_PARMS16*)((char*)msip32w - sizeof(LPMCI_SYSINFO_PARMS16));
2783 WideCharToMultiByte(CP_ACP, 0,
2784 msip32w->lpstrReturn, msip32w->dwRetSize,
2785 MapSL(msip16->lpstrReturn), msip16->dwRetSize,
2787 HeapFree(GetProcessHeap(), 0, (LPVOID)msip32w->lpstrReturn);
2788 HeapFree(GetProcessHeap(), 0, (LPVOID)lParam);
2790 return WINMM_MAP_OK;
2793 LPMCI_SOUND_PARMSW msp32W = (LPMCI_SOUND_PARMSW)lParam;
2794 HeapFree(GetProcessHeap(), 0, (LPVOID)msp32W->lpstrSoundName);
2795 HeapFree(GetProcessHeap(), 0, (LPVOID)lParam);
2797 return WINMM_MAP_OK;
2799 case MCI_OPEN_DRIVER:
2801 LPMCI_OPEN_PARMSW mop32w = (LPMCI_OPEN_PARMSW)lParam;
2802 LPMCI_OPEN_PARMS16 mop16 = *(LPMCI_OPEN_PARMS16*)((char*)mop32w - sizeof(LPMCI_OPEN_PARMS16));
2804 mop16->wDeviceID = mop32w->wDeviceID;
2805 if( ( dwFlags & ( MCI_OPEN_TYPE | MCI_OPEN_TYPE_ID)) == MCI_OPEN_TYPE)
2806 HeapFree(GetProcessHeap(), 0, (LPWSTR)mop32w->lpstrDeviceType);
2807 if( ( dwFlags & ( MCI_OPEN_ELEMENT | MCI_OPEN_ELEMENT_ID)) == MCI_OPEN_ELEMENT)
2808 HeapFree(GetProcessHeap(), 0, (LPWSTR)mop32w->lpstrElementName);
2809 if( ( dwFlags & MCI_OPEN_ALIAS))
2810 HeapFree(GetProcessHeap(), 0, (LPWSTR)mop32w->lpstrAlias);
2811 if (!HeapFree(GetProcessHeap(), 0, (LPVOID)(lParam - sizeof(LPMCI_OPEN_PARMS16))))
2812 FIXME("bad free line=%d\n", __LINE__);
2814 return WINMM_MAP_OK;
2822 case DRV_QUERYCONFIGURE:
2825 case DRV_EXITSESSION:
2826 case DRV_EXITAPPLICATION:
2828 FIXME("This is a hack\n");
2829 return WINMM_MAP_OK;
2831 FIXME("Map/Unmap internal error on msg=%s\n", MCI_MessageToString(wMsg));
2833 return WINMM_MAP_MSGERROR;
2838 * 0001 squeeze signed 4 bytes to 2 bytes *( LPINT16)D = ( INT16)*( LPINT16)S; D += 2; S += 4
2839 * 0010 squeeze unsigned 4 bytes to 2 bytes *(LPUINT16)D = (UINT16)*(LPUINT16)S; D += 2; S += 4
2842 * 0110 zero 4 bytes *(DWORD)D = 0 D += 4; S += 4
2843 * 0111 copy string *(LPSTR*)D = seg dup(*(LPSTR*)S) D += 4; S += 4
2844 * 1xxx copy xxx + 1 bytes memcpy(D, S, xxx + 1); D += xxx+1; S += xxx+1
2847 /**************************************************************************
2848 * MCI_MsgMapper32WTo16_Create [internal]
2850 * Helper for MCI_MapMsg32WTo16.
2851 * Maps the 32 bit pointer (*ptr), of size bytes, to an allocated 16 bit
2852 * segmented pointer.
2853 * map contains a list of action to be performed for the mapping (see list
2855 * if keep is TRUE, keeps track of in 32 bit ptr in allocated 16 bit area.
2857 static WINMM_MapType MCI_MsgMapper32WTo16_Create(void** ptr, int size16, DWORD map, BOOLEAN keep)
2859 void* lp = HeapAlloc( GetProcessHeap(), 0, (keep ? sizeof(void**) : 0) + size16 );
2863 return WINMM_MAP_NOMEM;
2865 p32 = (LPBYTE)(*ptr);
2868 p16 = (LPBYTE)lp + sizeof(void**);
2869 *ptr = (char*)MapLS(lp) + sizeof(void**);
2872 *ptr = (void*)MapLS(lp);
2876 memcpy(p16, p32, size16);
2884 sz = (nibble & 7) + 1;
2885 memcpy(p16, p32, sz);
2888 size16 -= sz; /* DEBUG only */
2892 *(LPINT16)p16 = *(LPINT)p32;
2893 p16 += sizeof(INT16);
2895 size16 -= sizeof(INT16);
2898 *(LPUINT16)p16 = *(LPUINT)p32;
2899 p16 += sizeof(UINT16);
2900 p32 += sizeof(UINT);
2901 size16 -= sizeof(UINT16);
2905 p16 += sizeof(DWORD);
2906 p32 += sizeof(DWORD);
2907 size16 -= sizeof(DWORD);
2910 *(SEGPTR *)p16 = MapLS( MCI_strdupWtoA( *(LPCWSTR *)p32 ) );
2911 p16 += sizeof(SEGPTR);
2912 p32 += sizeof(LPSTR);
2913 size16 -= sizeof(SEGPTR);
2916 FIXME("Unknown nibble for mapping (%x)\n", nibble);
2921 if (size16 != 0) /* DEBUG only */
2922 FIXME("Mismatch between 16 bit struct size and map nibbles serie\n");
2924 return WINMM_MAP_OKMEM;
2927 /**************************************************************************
2928 * MCI_MsgMapper32WTo16_Destroy [internal]
2930 * Helper for MCI_UnMapMsg32WTo16.
2932 static WINMM_MapType MCI_MsgMapper32WTo16_Destroy(void* ptr, int size16, DWORD map, BOOLEAN kept)
2935 void* msg16 = MapSL((SEGPTR)ptr);
2940 UnMapLS( (SEGPTR)ptr );
2942 alloc = (char*)msg16 - sizeof(void**);
2943 p32 = *(void**)alloc;
2947 memcpy(p32, p16, size16);
2952 memcpy(p32, p16, (nibble & 7) + 1);
2953 p16 += (nibble & 7) + 1;
2954 p32 += (nibble & 7) + 1;
2955 size16 -= (nibble & 7) + 1;
2959 *(LPINT)p32 = *(LPINT16)p16;
2960 p16 += sizeof(INT16);
2962 size16 -= sizeof(INT16);
2965 *(LPUINT)p32 = *(LPUINT16)p16;
2966 p16 += sizeof(UINT16);
2967 p32 += sizeof(UINT);
2968 size16 -= sizeof(UINT16);
2971 p16 += sizeof(UINT);
2972 p32 += sizeof(UINT);
2973 size16 -= sizeof(UINT);
2976 HeapFree(GetProcessHeap(), 0, MapSL(*(SEGPTR *)p16));
2977 UnMapLS( *(SEGPTR *)p16 );
2978 p16 += sizeof(SEGPTR);
2979 p32 += sizeof(char*);
2980 size16 -= sizeof(SEGPTR);
2983 FIXME("Unknown nibble for mapping (%x)\n", nibble);
2988 if (size16 != 0) /* DEBUG only */
2989 FIXME("Mismatch between 16 bit struct size and map nibbles serie\n");
2995 HeapFree( GetProcessHeap(), 0, alloc );
2997 return WINMM_MAP_OK;
3000 /**************************************************************************
3001 * MCI_MapMsg32WTo16 [internal]
3003 * Map a 32W bit MCI message to a 16 bit MCI message.
3005 static WINMM_MapType MCI_MapMsg32WTo16(WORD uDevType, WORD wMsg, DWORD dwFlags, DWORD_PTR* lParam)
3008 BOOLEAN keep = FALSE;
3012 return WINMM_MAP_OK;
3014 /* FIXME: to add also (with seg/linear modifications to do):
3015 * MCI_LIST, MCI_LOAD, MCI_QUALITY, MCI_RESERVE, MCI_RESTORE, MCI_SAVE
3016 * MCI_SETAUDIO, MCI_SETTUNER, MCI_SETVIDEO
3020 size = sizeof(MCI_BREAK_PARMS);
3022 /* case MCI_CAPTURE */
3024 case MCI_CLOSE_DRIVER:
3026 size = sizeof(MCI_GENERIC_PARMS);
3028 /* case MCI_COPY: */
3031 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_CUE_PARMS); break;
3032 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_CUE_PARMS); break;*/ FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
3033 default: size = sizeof(MCI_GENERIC_PARMS); break;
3039 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_DELETE_PARMS16); map = 0x0F1111FB; break;
3040 case MCI_DEVTYPE_WAVEFORM_AUDIO:size = sizeof(MCI_WAVE_DELETE_PARMS); break;
3041 default: size = sizeof(MCI_GENERIC_PARMS); break;
3044 /* case MCI_ESCAPE: */
3047 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_FREEZE_PARMS); map = 0x0001111B; break;
3048 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_RECT_PARMS); map = 0x0001111B; break;
3049 default: size = sizeof(MCI_GENERIC_PARMS); break;
3052 case MCI_GETDEVCAPS:
3054 size = sizeof(MCI_GETDEVCAPS_PARMS);
3056 /* case MCI_INDEX: */
3059 LPMCI_INFO_PARMSW mip32w = (LPMCI_INFO_PARMSW)(*lParam);
3061 LPMCI_INFO_PARMS16 mip16;
3064 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_INFO_PARMS16); break;
3065 default: size = sizeof(MCI_INFO_PARMS16); break;
3067 ptr = HeapAlloc( GetProcessHeap(), 0, sizeof(LPMCI_INFO_PARMSW) + size);
3070 *(LPMCI_INFO_PARMSW*)ptr = mip32w;
3071 mip16 = (LPMCI_INFO_PARMS16)(ptr + sizeof(LPMCI_INFO_PARMSW));
3072 mip16->dwCallback = mip32w->dwCallback;
3073 mip16->lpstrReturn = MapLS( HeapAlloc(GetProcessHeap(), 0, mip32w->dwRetSize / sizeof(WCHAR)) );
3074 mip16->dwRetSize = mip32w->dwRetSize / sizeof(WCHAR);
3075 if (uDevType == MCI_DEVTYPE_DIGITAL_VIDEO) {
3076 ((LPMCI_DGV_INFO_PARMS16)mip16)->dwItem = ((LPMCI_DGV_INFO_PARMSW)mip32w)->dwItem;
3079 return WINMM_MAP_NOMEM;
3081 *lParam = (LPARAM)MapLS(ptr) + sizeof(LPMCI_INFO_PARMSW);
3083 return WINMM_MAP_OKMEM;
3084 /* case MCI_MARK: */
3085 /* case MCI_MONITOR: */
3087 case MCI_OPEN_DRIVER:
3089 LPMCI_OPEN_PARMSW mop32w = (LPMCI_OPEN_PARMSW)(*lParam);
3090 char* ptr = HeapAlloc( GetProcessHeap(), 0,
3091 sizeof(LPMCI_OPEN_PARMSW) + sizeof(MCI_OPEN_PARMS16) + 2 * sizeof(DWORD));
3092 LPMCI_OPEN_PARMS16 mop16;
3096 *(LPMCI_OPEN_PARMSW*)(ptr) = mop32w;
3097 mop16 = (LPMCI_OPEN_PARMS16)(ptr + sizeof(LPMCI_OPEN_PARMSW));
3098 mop16->dwCallback = mop32w->dwCallback;
3099 mop16->wDeviceID = mop32w->wDeviceID;
3100 if (dwFlags & MCI_OPEN_TYPE) {
3101 if (dwFlags & MCI_OPEN_TYPE_ID) {
3102 /* dword "transparent" value */
3103 mop16->lpstrDeviceType = (SEGPTR)mop32w->lpstrDeviceType;
3106 mop16->lpstrDeviceType = MapLS( MCI_strdupWtoA(mop32w->lpstrDeviceType) );
3110 mop16->lpstrDeviceType = 0;
3112 if (dwFlags & MCI_OPEN_ELEMENT) {
3113 if (dwFlags & MCI_OPEN_ELEMENT_ID) {
3114 mop16->lpstrElementName = (SEGPTR)mop32w->lpstrElementName;
3116 mop16->lpstrElementName = MapLS( MCI_strdupWtoA(mop32w->lpstrElementName) );
3119 mop16->lpstrElementName = 0;
3121 if (dwFlags & MCI_OPEN_ALIAS) {
3122 mop16->lpstrAlias = MapLS( MCI_strdupWtoA(mop32w->lpstrAlias) );
3124 mop16->lpstrAlias = 0;
3126 /* copy extended information if any...
3127 * FIXME: this may seg fault if initial structure does not contain them and
3128 * the reads after msip16 fail under LDT limits...
3129 * NOTE: this should be split in two. First pass, while calling MCI_OPEN, and
3130 * should not take care of extended parameters, and should be used by MCI_Open
3131 * to fetch uDevType. When, this is known, the mapping for sending the
3132 * MCI_OPEN_DRIVER shall be done depending on uDevType.
3134 memcpy(mop16 + 1, mop32w + 1, 2 * sizeof(DWORD));
3136 return WINMM_MAP_NOMEM;
3138 *lParam = (LPARAM)MapLS(ptr) + sizeof(LPMCI_OPEN_PARMSW);
3140 return WINMM_MAP_OKMEM;
3141 /* case MCI_PASTE:*/
3143 size = sizeof(MCI_GENERIC_PARMS);
3146 size = sizeof(MCI_PLAY_PARMS);
3150 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_RECT_PARMS16); map = 0x0001111B; break;
3151 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_RECT_PARMS); map = 0x0001111B; break;
3152 default: size = sizeof(MCI_GENERIC_PARMS); break;
3156 size = sizeof(MCI_GENERIC_PARMS);
3160 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_RECORD_PARMS16); map = 0x0F1111FB; break;
3161 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_RECORD_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
3162 default: size = sizeof(MCI_RECORD_PARMS); break;
3166 size = sizeof(MCI_GENERIC_PARMS);
3170 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_SEEK_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
3171 default: size = sizeof(MCI_SEEK_PARMS); break;
3176 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_SET_PARMS); break;
3177 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_SET_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
3178 case MCI_DEVTYPE_SEQUENCER: size = sizeof(MCI_SEQ_SET_PARMS); break;
3179 /* FIXME: normally the 16 and 32 bit structures are byte by byte aligned,
3180 * so not doing anything should work...
3182 case MCI_DEVTYPE_WAVEFORM_AUDIO:size = sizeof(MCI_WAVE_SET_PARMS); break;
3183 default: size = sizeof(MCI_SET_PARMS); break;
3188 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_SETAUDIO_PARMS16);map = 0x0000077FF; break;
3189 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_SETAUDIO_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
3190 default: size = sizeof(MCI_GENERIC_PARMS); break;
3193 /* case MCI_SETTIMECODE:*/
3194 /* case MCI_SIGNAL:*/
3195 /* case MCI_SOUND:*/
3197 size = sizeof(MCI_SET_PARMS);
3203 * don't know if buffer for value is the one passed through lpstrDevice
3204 * or is provided by MCI driver.
3205 * Assuming solution 2: provided by MCI driver, so zeroing on entry
3207 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_STATUS_PARMS16); map = 0x0B6FF; break;
3208 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_STATUS_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
3209 default: size = sizeof(MCI_STATUS_PARMS); break;
3214 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_STEP_PARMS); break;
3215 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_STEP_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
3216 case MCI_DEVTYPE_VIDEODISC: size = sizeof(MCI_VD_STEP_PARMS); break;
3217 default: size = sizeof(MCI_GENERIC_PARMS); break;
3221 size = sizeof(MCI_SET_PARMS);
3225 LPMCI_SYSINFO_PARMSW msip32w = (LPMCI_SYSINFO_PARMSW)(*lParam);
3226 LPMCI_SYSINFO_PARMS16 msip16;
3227 char* ptr = HeapAlloc( GetProcessHeap(), 0,
3228 sizeof(LPMCI_SYSINFO_PARMSW) + sizeof(MCI_SYSINFO_PARMS16) );
3231 *(LPMCI_SYSINFO_PARMSW*)(ptr) = msip32w;
3232 msip16 = (LPMCI_SYSINFO_PARMS16)(ptr + sizeof(LPMCI_SYSINFO_PARMSW));
3234 msip16->dwCallback = msip32w->dwCallback;
3235 msip16->lpstrReturn = MapLS( HeapAlloc(GetProcessHeap(), 0, msip32w->dwRetSize) );
3236 msip16->dwRetSize = msip32w->dwRetSize;
3237 msip16->dwNumber = msip32w->dwNumber;
3238 msip16->wDeviceType = msip32w->wDeviceType;
3240 return WINMM_MAP_NOMEM;
3242 *lParam = (LPARAM)MapLS(ptr) + sizeof(LPMCI_SYSINFO_PARMSW);
3244 return WINMM_MAP_OKMEM;
3245 /* case MCI_UNDO: */
3248 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_RECT_PARMS16); map = 0x0001111B; break;
3249 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_RECT_PARMS16); map = 0x0001111B; break;
3250 default: size = sizeof(MCI_GENERIC_PARMS); break;
3255 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_UPDATE_PARMS16); map = 0x000B1111B; break;
3256 default: size = sizeof(MCI_GENERIC_PARMS); break;
3261 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_RECT_PARMS16); map = 0x0001111B; keep = TRUE; break;
3262 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_RECT_PARMS16); map = 0x0001111B; keep = TRUE; break;
3263 default: size = sizeof(MCI_GENERIC_PARMS); break;
3268 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_WINDOW_PARMS16); if (dwFlags & MCI_DGV_WINDOW_TEXT) map = 0x7FB; break;
3269 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_WINDOW_PARMS16); if (dwFlags & MCI_OVLY_WINDOW_TEXT) map = 0x7FB; break;
3270 default: size = sizeof(MCI_GENERIC_PARMS); break;
3275 LPMCI_OPEN_DRIVER_PARMSW modp32w = (LPMCI_OPEN_DRIVER_PARMSW)(*lParam);
3276 LPMCI_OPEN_DRIVER_PARMS16 modp16;
3277 char *ptr = HeapAlloc( GetProcessHeap(), 0,
3278 sizeof(LPMCI_OPEN_DRIVER_PARMSW) + sizeof(MCI_OPEN_DRIVER_PARMS16));
3281 *(LPMCI_OPEN_DRIVER_PARMSW*)(ptr) = modp32w;
3282 modp16 = (LPMCI_OPEN_DRIVER_PARMS16)(ptr + sizeof(LPMCI_OPEN_DRIVER_PARMSW));
3283 modp16->wDeviceID = modp32w->wDeviceID;
3284 modp16->lpstrParams = MapLS( MCI_strdupWtoA(modp32w->lpstrParams) );
3285 /* other fields are gonna be filled by the driver, don't copy them */
3287 return WINMM_MAP_NOMEM;
3289 *lParam = (LPARAM)MapLS(ptr) + sizeof(LPMCI_OPEN_DRIVER_PARMSW);
3291 return WINMM_MAP_OKMEM;
3298 case DRV_QUERYCONFIGURE:
3301 case DRV_EXITSESSION:
3302 case DRV_EXITAPPLICATION:
3304 return WINMM_MAP_OK;
3307 FIXME("Don't know how to map msg=%s\n", MCI_MessageToString(wMsg));
3308 return WINMM_MAP_MSGERROR;
3310 return MCI_MsgMapper32WTo16_Create((void**)lParam, size, map, keep);
3313 /**************************************************************************
3314 * MCI_UnMapMsg32WTo16 [internal]
3316 static WINMM_MapType MCI_UnMapMsg32WTo16(WORD uDevType, WORD wMsg, DWORD dwFlags, DWORD_PTR lParam)
3319 BOOLEAN kept = FALSE; /* there is no need to compute size when kept is FALSE */
3325 /* case MCI_CAPTURE */
3327 case MCI_CLOSE_DRIVER:
3330 /* case MCI_COPY: */
3336 /* case MCI_ESCAPE: */
3339 case MCI_GETDEVCAPS:
3341 size = sizeof(MCI_GETDEVCAPS_PARMS);
3343 /* case MCI_INDEX: */
3346 LPMCI_INFO_PARMS16 mip16 = (LPMCI_INFO_PARMS16)MapSL(lParam);
3347 LPMCI_INFO_PARMSW mip32w = *(LPMCI_INFO_PARMSW*)((char*)mip16 - sizeof(LPMCI_INFO_PARMSW));
3349 MultiByteToWideChar(CP_ACP, 0, MapSL(mip16->lpstrReturn), mip16->dwRetSize,
3350 mip32w->lpstrReturn, mip32w->dwRetSize / sizeof(WCHAR));
3352 UnMapLS( mip16->lpstrReturn );
3353 HeapFree( GetProcessHeap(), 0, (void*)MapSL(mip16->lpstrReturn) );
3354 HeapFree( GetProcessHeap(), 0, (char*)mip16 - sizeof(LPMCI_OPEN_PARMSW) );
3356 return WINMM_MAP_OK;
3357 /* case MCI_MARK: */
3358 /* case MCI_MONITOR: */
3360 case MCI_OPEN_DRIVER:
3362 LPMCI_OPEN_PARMS16 mop16 = (LPMCI_OPEN_PARMS16)MapSL(lParam);
3363 LPMCI_OPEN_PARMSW mop32w = *(LPMCI_OPEN_PARMSW*)((char*)mop16 - sizeof(LPMCI_OPEN_PARMSW));
3365 mop32w->wDeviceID = mop16->wDeviceID;
3366 if ((dwFlags & MCI_OPEN_TYPE) && !(dwFlags & MCI_OPEN_TYPE_ID))
3368 HeapFree(GetProcessHeap(), 0, MapSL(mop16->lpstrDeviceType));
3369 UnMapLS( mop16->lpstrDeviceType );
3371 if ((dwFlags & MCI_OPEN_ELEMENT) && !(dwFlags & MCI_OPEN_ELEMENT_ID))
3373 HeapFree(GetProcessHeap(), 0, MapSL(mop16->lpstrElementName));
3374 UnMapLS( mop16->lpstrElementName );
3376 if (dwFlags & MCI_OPEN_ALIAS)
3378 HeapFree(GetProcessHeap(), 0, MapSL(mop16->lpstrAlias));
3379 UnMapLS( mop16->lpstrAlias );
3381 HeapFree( GetProcessHeap(), 0, (char*)mop16 - sizeof(LPMCI_OPEN_PARMSW) );
3383 return WINMM_MAP_OK;
3384 /* case MCI_PASTE:*/
3403 case MCI_DEVTYPE_DIGITAL_VIDEO: map = 0x0000077FF; break;
3404 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_SETAUDIO_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
3407 /* case MCI_SETTIMECODE:*/
3408 /* case MCI_SIGNAL:*/
3409 /* case MCI_SOUND:*/
3415 case MCI_DEVTYPE_DIGITAL_VIDEO:
3417 LPMCI_DGV_STATUS_PARMS16 mdsp16 = (LPMCI_DGV_STATUS_PARMS16)MapSL(lParam);
3418 LPMCI_DGV_STATUS_PARMSA mdsp32a = *(LPMCI_DGV_STATUS_PARMSA*)((char*)mdsp16 - sizeof(LPMCI_DGV_STATUS_PARMSA));
3422 mdsp32a->dwReturn = mdsp16->dwReturn;
3423 if (dwFlags & MCI_DGV_STATUS_DISKSPACE) {
3424 TRACE("MCI_STATUS (DGV) lpstrDrive=%08x\n", mdsp16->lpstrDrive);
3425 TRACE("MCI_STATUS (DGV) lpstrDrive=%s\n", (LPSTR)MapSL(mdsp16->lpstrDrive));
3426 UnMapLS( mdsp16->lpstrDrive );
3428 HeapFree( GetProcessHeap(), 0, (char*)mdsp16 - sizeof(LPMCI_DGV_STATUS_PARMSA) );
3430 return WINMM_MAP_NOMEM;
3433 return WINMM_MAP_OKMEM;
3434 case MCI_DEVTYPE_VCR: /*size = sizeof(MCI_VCR_STATUS_PARMS); break;*/FIXME("NIY vcr\n"); return WINMM_MAP_NOMEM;
3435 default: size = sizeof(MCI_STATUS_PARMS); break;
3444 LPMCI_SYSINFO_PARMS16 msip16 = (LPMCI_SYSINFO_PARMS16)MapSL(lParam);
3445 LPMCI_SYSINFO_PARMSW msip32w = *(LPMCI_SYSINFO_PARMSW*)((char*)msip16 - sizeof(LPMCI_SYSINFO_PARMSW));
3449 MultiByteToWideChar(CP_ACP, 0, MapSL(msip16->lpstrReturn), msip16->dwRetSize,
3450 msip32w->lpstrReturn, msip32w->dwRetSize/sizeof(WCHAR));
3451 UnMapLS( msip16->lpstrReturn );
3452 HeapFree( GetProcessHeap(), 0, MapSL(msip16->lpstrReturn) );
3453 HeapFree( GetProcessHeap(), 0, (char*)msip16 - sizeof(LPMCI_SYSINFO_PARMSW) );
3455 return WINMM_MAP_NOMEM;
3458 return WINMM_MAP_OKMEM;
3459 /* case MCI_UNDO: */
3466 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_RECT_PARMS16); map = 0x0001111B; kept = TRUE; break;
3467 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_RECT_PARMS16); map = 0x0001111B; kept = TRUE; break;
3473 case MCI_DEVTYPE_DIGITAL_VIDEO: size = sizeof(MCI_DGV_WINDOW_PARMS16); if (dwFlags & MCI_DGV_WINDOW_TEXT) map = 0x7666; break;
3474 case MCI_DEVTYPE_OVERLAY: size = sizeof(MCI_OVLY_WINDOW_PARMS16); if (dwFlags & MCI_OVLY_WINDOW_TEXT) map = 0x7666; break;
3477 /* FIXME: see map function */
3481 LPMCI_OPEN_DRIVER_PARMS16 modp16 = (LPMCI_OPEN_DRIVER_PARMS16)MapSL(lParam);
3482 LPMCI_OPEN_DRIVER_PARMSW modp32w = *(LPMCI_OPEN_DRIVER_PARMSW*)((char*)modp16 - sizeof(LPMCI_OPEN_DRIVER_PARMSW));
3485 modp32w->wCustomCommandTable = modp16->wCustomCommandTable;
3486 modp32w->wType = modp16->wType;
3487 HeapFree(GetProcessHeap(), 0, MapSL(modp16->lpstrParams));
3488 UnMapLS( modp16->lpstrParams );
3489 HeapFree( GetProcessHeap(), 0, (char *)modp16 - sizeof(LPMCI_OPEN_DRIVER_PARMSW) );
3491 return WINMM_MAP_OK;
3498 case DRV_QUERYCONFIGURE:
3501 case DRV_EXITSESSION:
3502 case DRV_EXITAPPLICATION:
3504 FIXME("This is a hack\n");
3505 return WINMM_MAP_OK;
3508 FIXME("Map/Unmap internal error on msg=%s\n", MCI_MessageToString(wMsg));
3509 return WINMM_MAP_MSGERROR;
3511 return MCI_MsgMapper32WTo16_Destroy((void*)lParam, size, map, kept);
3514 void MMDRV_Init16(void)
3516 #define A(_x,_y) MMDRV_InstallMap(_x, \
3517 MMDRV_##_y##_Map16To32W, MMDRV_##_y##_UnMap16To32W, \
3518 MMDRV_##_y##_Map32WTo16, MMDRV_##_y##_UnMap32WTo16, \
3519 MMDRV_##_y##_Callback)
3521 A(MMDRV_MIXER, Mixer);
3522 A(MMDRV_MIDIIN, MidiIn);
3523 A(MMDRV_MIDIOUT, MidiOut);
3524 A(MMDRV_WAVEIN, WaveIn);
3525 A(MMDRV_WAVEOUT, WaveOut);
3528 pFnCallMMDrvFunc16 = MMDRV_CallMMDrvFunc16;
3529 pFnLoadMMDrvFunc16 = MMDRV_LoadMMDrvFunc16;
3531 pFnMciMapMsg16To32W = MCI_MapMsg16To32W;
3532 pFnMciUnMapMsg16To32W = MCI_UnMapMsg16To32W;
3533 pFnMciMapMsg32WTo16 = MCI_MapMsg32WTo16;
3534 pFnMciUnMapMsg32WTo16 = MCI_UnMapMsg32WTo16;