📄 winmm.c
字号:
mocA.vDriverVersion = mocW.vDriverVersion;
WideCharToMultiByte( CP_ACP, 0, mocW.szPname, -1, mocA.szPname,
sizeof(mocA.szPname), NULL, NULL );
mocA.wTechnology = mocW.wTechnology;
mocA.wVoices = mocW.wVoices;
mocA.wNotes = mocW.wNotes;
mocA.wChannelMask = mocW.wChannelMask;
mocA.dwSupport = mocW.dwSupport;
memcpy(lpCaps, &mocA, min(uSize, sizeof(mocA)));
}
return ret;
}
/**************************************************************************
* midiOutGetErrorTextA [WINMM.@]
* midiInGetErrorTextA [WINMM.@]
*/
UINT WINAPI midiOutGetErrorTextA(UINT uError, LPSTR lpText, UINT uSize)
{
UINT ret;
if (lpText == NULL) ret = MMSYSERR_INVALPARAM;
else if (uSize == 0) ret = MMSYSERR_NOERROR;
else
{
LPWSTR xstr = HeapAlloc(GetProcessHeap(), 0, uSize * sizeof(WCHAR));
if (!xstr) ret = MMSYSERR_NOMEM;
else
{
ret = midiOutGetErrorTextW(uError, xstr, uSize);
if (ret == MMSYSERR_NOERROR)
WideCharToMultiByte(CP_ACP, 0, xstr, -1, lpText, uSize, NULL, NULL);
HeapFree(GetProcessHeap(), 0, xstr);
}
}
return ret;
}
/**************************************************************************
* midiOutGetErrorTextW [WINMM.@]
* midiInGetErrorTextW [WINMM.@]
*/
UINT WINAPI midiOutGetErrorTextW(UINT uError, LPWSTR lpText, UINT uSize)
{
UINT ret = MMSYSERR_BADERRNUM;
if (lpText == NULL) ret = MMSYSERR_INVALPARAM;
else if (uSize == 0) ret = MMSYSERR_NOERROR;
else if (
/* test has been removed 'coz MMSYSERR_BASE is 0, and gcc did emit
* a warning for the test was always true */
(/*uError >= MMSYSERR_BASE && */ uError <= MMSYSERR_LASTERROR) ||
(uError >= MIDIERR_BASE && uError <= MIDIERR_LASTERROR)) {
if (LoadStringW(WINMM_IData.hWinMM32Instance,
uError, lpText, uSize) > 0) {
ret = MMSYSERR_NOERROR;
}
}
return ret;
}
/**************************************************************************
* MIDI_OutAlloc [internal]
*/
static LPWINE_MIDI MIDI_OutAlloc(HMIDIOUT* lphMidiOut, LPDWORD lpdwCallback,
LPDWORD lpdwInstance, LPDWORD lpdwFlags,
DWORD cIDs, MIDIOPENSTRMID* lpIDs, BOOL bFrom32)
{
HANDLE hMidiOut;
LPWINE_MIDI lpwm;
UINT size;
size = sizeof(WINE_MIDI) + (cIDs ? (cIDs-1) : 0) * sizeof(MIDIOPENSTRMID);
lpwm = (LPWINE_MIDI)MMDRV_Alloc(size, MMDRV_MIDIOUT, &hMidiOut, lpdwFlags,
lpdwCallback, lpdwInstance, bFrom32);
if (lphMidiOut != NULL)
*lphMidiOut = hMidiOut;
if (lpwm) {
lpwm->mod.hMidi = (HMIDI) hMidiOut;
lpwm->mod.dwCallback = *lpdwCallback;
lpwm->mod.dwInstance = *lpdwInstance;
lpwm->mod.dnDevNode = 0;
lpwm->mod.cIds = cIDs;
if (cIDs)
memcpy(&(lpwm->mod.rgIds), lpIDs, cIDs * sizeof(MIDIOPENSTRMID));
}
return lpwm;
}
UINT MIDI_OutOpen(LPHMIDIOUT lphMidiOut, UINT uDeviceID, DWORD_PTR dwCallback,
DWORD_PTR dwInstance, DWORD dwFlags, BOOL bFrom32)
{
HMIDIOUT hMidiOut;
LPWINE_MIDI lpwm;
UINT dwRet = 0;
TRACE("(%p, %d, %08lX, %08lX, %08lX);\n",
lphMidiOut, uDeviceID, dwCallback, dwInstance, dwFlags);
if (lphMidiOut != NULL) *lphMidiOut = 0;
lpwm = MIDI_OutAlloc(&hMidiOut, &dwCallback, &dwInstance, &dwFlags,
0, NULL, bFrom32);
if (lpwm == NULL)
return MMSYSERR_NOMEM;
lpwm->mld.uDeviceID = uDeviceID;
dwRet = MMDRV_Open((LPWINE_MLD)lpwm, MODM_OPEN, (DWORD)&lpwm->mod, dwFlags);
if (dwRet != MMSYSERR_NOERROR) {
MMDRV_Free(hMidiOut, (LPWINE_MLD)lpwm);
hMidiOut = 0;
}
if (lphMidiOut) *lphMidiOut = hMidiOut;
TRACE("=> %d hMidi=%p\n", dwRet, hMidiOut);
return dwRet;
}
/**************************************************************************
* midiOutOpen [WINMM.@]
*/
UINT WINAPI midiOutOpen(LPHMIDIOUT lphMidiOut, UINT uDeviceID,
DWORD_PTR dwCallback, DWORD_PTR dwInstance, DWORD dwFlags)
{
return MIDI_OutOpen(lphMidiOut, uDeviceID, dwCallback, dwInstance, dwFlags, TRUE);
}
/**************************************************************************
* midiOutClose [WINMM.@]
*/
UINT WINAPI midiOutClose(HMIDIOUT hMidiOut)
{
LPWINE_MLD wmld;
DWORD dwRet;
TRACE("(%p)\n", hMidiOut);
if ((wmld = MMDRV_Get(hMidiOut, MMDRV_MIDIOUT, FALSE)) == NULL)
return MMSYSERR_INVALHANDLE;
dwRet = MMDRV_Close(wmld, MODM_CLOSE);
MMDRV_Free(hMidiOut, wmld);
return dwRet;
}
/**************************************************************************
* midiOutPrepareHeader [WINMM.@]
*/
UINT WINAPI midiOutPrepareHeader(HMIDIOUT hMidiOut,
MIDIHDR* lpMidiOutHdr, UINT uSize)
{
LPWINE_MLD wmld;
TRACE("(%p, %p, %d)\n", hMidiOut, lpMidiOutHdr, uSize);
if (lpMidiOutHdr == NULL || uSize < sizeof (MIDIHDR))
return MMSYSERR_INVALPARAM;
if ((wmld = MMDRV_Get(hMidiOut, MMDRV_MIDIOUT, FALSE)) == NULL)
return MMSYSERR_INVALHANDLE;
return MMDRV_Message(wmld, MODM_PREPARE, (DWORD_PTR)lpMidiOutHdr, uSize, TRUE);
}
/**************************************************************************
* midiOutUnprepareHeader [WINMM.@]
*/
UINT WINAPI midiOutUnprepareHeader(HMIDIOUT hMidiOut,
MIDIHDR* lpMidiOutHdr, UINT uSize)
{
LPWINE_MLD wmld;
TRACE("(%p, %p, %d)\n", hMidiOut, lpMidiOutHdr, uSize);
if (lpMidiOutHdr == NULL || uSize < sizeof (MIDIHDR))
return MMSYSERR_INVALPARAM;
if (!(lpMidiOutHdr->dwFlags & MHDR_PREPARED)) {
return MMSYSERR_NOERROR;
}
if ((wmld = MMDRV_Get(hMidiOut, MMDRV_MIDIOUT, FALSE)) == NULL)
return MMSYSERR_INVALHANDLE;
return MMDRV_Message(wmld, MODM_UNPREPARE, (DWORD_PTR)lpMidiOutHdr, uSize, TRUE);
}
/**************************************************************************
* midiOutShortMsg [WINMM.@]
*/
UINT WINAPI midiOutShortMsg(HMIDIOUT hMidiOut, DWORD dwMsg)
{
LPWINE_MLD wmld;
TRACE("(%p, %08lX)\n", hMidiOut, dwMsg);
if ((wmld = MMDRV_Get(hMidiOut, MMDRV_MIDIOUT, FALSE)) == NULL)
return MMSYSERR_INVALHANDLE;
return MMDRV_Message(wmld, MODM_DATA, dwMsg, 0L, TRUE);
}
/**************************************************************************
* midiOutLongMsg [WINMM.@]
*/
UINT WINAPI midiOutLongMsg(HMIDIOUT hMidiOut,
MIDIHDR* lpMidiOutHdr, UINT uSize)
{
LPWINE_MLD wmld;
TRACE("(%p, %p, %d)\n", hMidiOut, lpMidiOutHdr, uSize);
if ((wmld = MMDRV_Get(hMidiOut, MMDRV_MIDIOUT, FALSE)) == NULL)
return MMSYSERR_INVALHANDLE;
return MMDRV_Message(wmld, MODM_LONGDATA, (DWORD_PTR)lpMidiOutHdr, uSize, TRUE);
}
/**************************************************************************
* midiOutReset [WINMM.@]
*/
UINT WINAPI midiOutReset(HMIDIOUT hMidiOut)
{
LPWINE_MLD wmld;
TRACE("(%p)\n", hMidiOut);
if ((wmld = MMDRV_Get(hMidiOut, MMDRV_MIDIOUT, FALSE)) == NULL)
return MMSYSERR_INVALHANDLE;
return MMDRV_Message(wmld, MODM_RESET, 0L, 0L, TRUE);
}
/**************************************************************************
* midiOutGetVolume [WINMM.@]
*/
UINT WINAPI midiOutGetVolume(HMIDIOUT hMidiOut, DWORD* lpdwVolume)
{
LPWINE_MLD wmld;
TRACE("(%p, %p);\n", hMidiOut, lpdwVolume);
if ((wmld = MMDRV_Get(hMidiOut, MMDRV_MIDIOUT, TRUE)) == NULL)
return MMSYSERR_INVALHANDLE;
return MMDRV_Message(wmld, MODM_GETVOLUME, (DWORD_PTR)lpdwVolume, 0L, TRUE);
}
/**************************************************************************
* midiOutSetVolume [WINMM.@]
*/
UINT WINAPI midiOutSetVolume(HMIDIOUT hMidiOut, DWORD dwVolume)
{
LPWINE_MLD wmld;
TRACE("(%p, %ld);\n", hMidiOut, dwVolume);
if ((wmld = MMDRV_Get(hMidiOut, MMDRV_MIDIOUT, TRUE)) == NULL)
return MMSYSERR_INVALHANDLE;
return MMDRV_Message(wmld, MODM_SETVOLUME, dwVolume, 0L, TRUE);
}
/**************************************************************************
* midiOutCachePatches [WINMM.@]
*/
UINT WINAPI midiOutCachePatches(HMIDIOUT hMidiOut, UINT uBank,
WORD* lpwPatchArray, UINT uFlags)
{
/* not really necessary to support this */
FIXME("not supported yet\n");
return MMSYSERR_NOTSUPPORTED;
}
/**************************************************************************
* midiOutCacheDrumPatches [WINMM.@]
*/
UINT WINAPI midiOutCacheDrumPatches(HMIDIOUT hMidiOut, UINT uPatch,
WORD* lpwKeyArray, UINT uFlags)
{
FIXME("not supported yet\n");
return MMSYSERR_NOTSUPPORTED;
}
/**************************************************************************
* midiOutGetID [WINMM.@]
*/
UINT WINAPI midiOutGetID(HMIDIOUT hMidiOut, UINT* lpuDeviceID)
{
LPWINE_MLD wmld;
TRACE("(%p, %p)\n", hMidiOut, lpuDeviceID);
if (lpuDeviceID == NULL) return MMSYSERR_INVALPARAM;
if ((wmld = MMDRV_Get(hMidiOut, MMDRV_MIDIOUT, FALSE)) == NULL)
return MMSYSERR_INVALHANDLE;
*lpuDeviceID = wmld->uDeviceID;
return MMSYSERR_NOERROR;
}
/**************************************************************************
* midiOutMessage [WINMM.@]
*/
UINT WINAPI midiOutMessage(HMIDIOUT hMidiOut, UINT uMessage,
DWORD_PTR dwParam1, DWORD_PTR dwParam2)
{
LPWINE_MLD wmld;
TRACE("(%p, %04X, %08lX, %08lX)\n", hMidiOut, uMessage, dwParam1, dwParam2);
if ((wmld = MMDRV_Get(hMidiOut, MMDRV_MIDIOUT, FALSE)) == NULL) {
/* HACK... */
if (uMessage == 0x0001) {
*(LPDWORD)dwParam1 = 1;
return 0;
}
if ((wmld = MMDRV_Get(hMidiOut, MMDRV_MIDIOUT, TRUE)) != NULL) {
return MMDRV_PhysicalFeatures(wmld, uMessage, dwParam1, dwParam2);
}
return MMSYSERR_INVALHANDLE;
}
switch (uMessage) {
case MODM_OPEN:
case MODM_CLOSE:
FIXME("can't handle OPEN or CLOSE message!\n");
return MMSYSERR_NOTSUPPORTED;
}
return MMDRV_Message(wmld, uMessage, dwParam1, dwParam2, TRUE);
}
/**************************************************************************
* midiInGetNumDevs [WINMM.@]
*/
UINT WINAPI midiInGetNumDevs(void)
{
return MMDRV_GetNum(MMDRV_MIDIIN);
}
/**************************************************************************
* midiInGetDevCapsW [WINMM.@]
*/
UINT WINAPI midiInGetDevCapsW(UINT_PTR uDeviceID, LPMIDIINCAPSW lpCaps, UINT uSize)
{
LPWINE_MLD wmld;
TRACE("(%d, %p, %d);\n", uDeviceID, lpCaps, uSize);
if (lpCaps == NULL) return MMSYSERR_INVALPARAM;
if ((wmld = MMDRV_Get((HANDLE)uDeviceID, MMDRV_MIDIIN, TRUE)) == NULL)
return MMSYSERR_INVALHANDLE;
return MMDRV_Message(wmld, MIDM_GETDEVCAPS, (DWORD_PTR)lpCaps, uSize, TRUE);
}
/**************************************************************************
* midiInGetDevCapsA [WINMM.@]
*/
UINT WINAPI midiInGetDevCapsA(UINT_PTR uDeviceID, LPMIDIINCAPSA lpCaps, UINT uSize)
{
MIDIINCAPSW micW;
UINT ret;
if (lpCaps == NULL) return MMSYSERR_INVALPARAM;
ret = midiInGetDevCapsW(uDeviceID, &micW, sizeof(micW));
if (ret == MMSYSERR_NOERROR) {
MIDIINCAPSA micA;
micA.wMid = micW.wMid;
micA.wPid = micW.wPid;
micA.vDriverVersion = micW.vDriverVersion;
WideCharToMultiByte( CP_ACP, 0, micW.szPname, -1, micA.szPname,
sizeof(micA.szPname), NULL, NULL );
micA.dwSupport = micW.dwSupport;
memcpy(lpCaps, &micA, min(uSize, sizeof(micA)));
}
return ret;
}
UINT MIDI_InOpen(HMIDIIN* lphMidiIn, UINT uDeviceID, DWORD_PTR dwCallback,
DWORD_PTR dwInstance, DWORD dwFlags, BOOL bFrom32)
{
HANDLE hMidiIn;
LPWINE_MIDI lpwm;
DWORD dwRet = 0;
TRACE("(%p, %d, %08lX, %08lX, %08lX);\n",
lphMidiIn, uDeviceID, dwCallback, dwInstance, dwFlags);
if (lphMidiIn != NULL) *lphMidiIn = 0;
lpwm = (LPWINE_MIDI)MMDRV_Alloc(sizeof(WINE_MIDI), MMDRV_MIDIIN, &hMidiIn,
&dwFlags, &dwCallback, &dwInstance, bFrom32);
if (lpwm == NULL)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -