44#define MIDI_NOTEOFF 0x80
45#define MIDI_NOTEON 0x90
114 if (!modp)
return 0xFFFFFFFF;
140 return (dwDevID == 0xFFFFFFFF) ? 1 : 0;
151 WARN(
"Invalid wDevID=%u\n", wDevID);
183 WARN(
"Error reading wmm=%p\n", wmm);
200 *lpw = ((
WORD)hibyte << 8) + lobyte;
237 }
while (
byte & 0x80);
269 if (evtLength >= 0x10000u) {
271 WARN(
"Ouch !! Implementation limitation to 64k bytes for a MIDI event is overflowed\n");
286 switch ((
b1 >> 4) & 0x07) {
287 case 0:
case 1:
case 2:
case 3:
case 6:
294 WARN(
"Strange indeed b1=0x%02x\n",
b1);
326 if (fourcc !=
mmioFOURCC(
'M',
'T',
'r',
'k')) {
327 WARN(
"Can't synchronize on 'MTrk' !\n");
352 WARN(
"Buffer for text is too small (%u are needed)\n",
len);
391 WARN(
"Ouch, out of sync seek=%u track=%u\n",
419 if (fourcc !=
mmioFOURCC(
'M',
'T',
'h',
'd')) {
420 WARN(
"Can't synchronize on 'MThd' !\n");
433 TRACE(
"toberead=0x%08X, wFormat=0x%04X nTracks=0x%04X nDivision=0x%04X\n",
446 FIXME(
"Handling SMPTE time in MIDI files has not been tested\n"
447 "Please report to comp.emulators.ms-windows.wine with MIDI file !\n");
469 WARN(
"Number of division is 0, can't support that !!\n");
478 WARN(
"Got type 0 file whose number of track is not 1. Setting it to 1\n");
486 WARN(
"Handling MIDI files which format = %d is not (yet) supported\n"
487 "Please report with MIDI file !\n", wmm->
wFormat);
493 FIXME(
"Truncating MIDI file with %u tracks\n", wmm->
nTracks);
501 toberead -= 3 *
sizeof(
WORD);
503 TRACE(
"Size of MThd > 6, skipping %d extra bytes\n", toberead);
510 WARN(
"Can't read 'MTrk' header\n");
531 FIXME(
"Shouldn't happen. wmm->nDivision = 0\n");
535 ret = (pulse * 1000) / (nf * nsf);
549#define TIME_MS_IN_ONE_HOUR (60*60*1000)
550#define TIME_MS_IN_ONE_MINUTE (60*1000)
551#define TIME_MS_IN_ONE_SECOND (1000)
609 f = (
val * 3) / 125;
val -= (
f * 125) / 3;
617 f = (
val * 3) / 100;
val -= (
f * 100) / 3;
620 FIXME(
"There must be some bad bad programmer\n");
625 ret = (
f << 24) | (
s << 16) | (
m << 8) | (
h << 0);
689 if (wmm->
hFile == 0) {
708 if (wmm->
hFile != 0) {
716 TRACE(
"ParentChunk ckid=%.4s fccType=%.4s cksize=%08X\n",
723 TRACE(
"... is a 'RMID' file\n");
730 WARN(
"Can't read 'MThd' header\n");
735 TRACE(
"hFile==0, setting #tracks to 0; is this correct ?\n");
806 if (wmm->
hFile != 0) {
809 TRACE(
"hFile closed !\n");
838 *hiPulse = 0xFFFFFFFFul;
850 return (cnt == 0xFFFFu) ? 0
897 TRACE(
"wmm->dwStatus=%d, doPlay=%c\n", wmm->
dwStatus, doPlay ?
'T' :
'F');
917 TRACE(
"Pulses hi=0x%08x <> cur=0x%08x\n", hiPulse, wmm->
dwPulse);
918 TRACE(
"Wait until %u => %u ms\n",
930 FIXME(
"Not handling SysEx events (yet)\n");
942 TRACE(
"Got sequence number %u\n", twd);
955 static const char*
const info[8] = {
"",
"Text",
"Copyright",
"Seq/Trk name",
956 "Instrument",
"Lyric",
"Marker",
"Cue-point"};
960 WARN(
"Buffer for text is too small (%u are needed)\n",
len);
977 FIXME(
"NIY: MIDI channel=%u, track=%u\n", bt, mmt->
wTrackNr);
997 WARN(
"For format #1 MIDI files, tempo can only be changed on track #0 (%u)\n", mmt->
wTrackNr);
1011 WARN(
"For format #1 MIDI files, SMPTE track start can only be expressed on track #0 (%u)\n", mmt->
wTrackNr);
1013 WARN(
"SMPTE track start can only be expressed at start of track (%u)\n", mmt->
dwEventPulse);
1022 FIXME(
"NIY: SMPTE track start %u:%u:%u %u.%u\n",
h,
m,
s,
f, ff);
1034 TRACE(
"%u/%u, clock per metronome click=%u, 32nd notes by 1/4 note=%u\n",
num, 1 << den, cpmc, _32npqn);
1044 if (sf >= 0x80)
TRACE(
"%d flats\n", -(
char)sf);
1045 else if (sf > 0)
TRACE(
"%d sharps\n", (
char)sf);
1046 else TRACE(
"Key of C\n");
1047 TRACE(
"Mode: %s\n", (mm == 0) ?
"major" :
"minor");
1139 DWORD dwStartMS, dwEndMS;
1145 if (wmm->
hFile == 0) {
1154 dwEndMS = 0xFFFFFFFFul;
1161 if (dwEndMS < dwStartMS)
1169 if (wmm->
dwEndMS != dwEndMS) {
1175 TRACE(
"Playing from %u to %u\n", dwStartMS, dwEndMS);
1203 for (chn = 0; chn < 16; chn++)
1240 TRACE(
"MCI_FORMAT_MILLISECONDS !\n");
1244 TRACE(
"MCI_FORMAT_SMPTE_24 !\n");
1248 TRACE(
"MCI_FORMAT_SMPTE_25 !\n");
1252 TRACE(
"MCI_FORMAT_SMPTE_30 !\n");
1261 TRACE(
"No support for video !\n");
1265 TRACE(
"No support for door open !\n");
1269 TRACE(
"No support for door close !\n");
1274 TRACE(
"MCI_SET_ON audio !\n");
1276 TRACE(
"MCI_SET_OFF audio !\n");
1278 WARN(
"MCI_SET_AUDIO without SET_ON or SET_OFF\n");
1287 default:
WARN(
"Unknown audio channel %u\n", lpParms->
dwAudio);
break;
1292 TRACE(
"MCI_SEQ_SET_MASTER !\n");
1294 TRACE(
"MCI_SEQ_SET_SLAVE !\n");
1296 TRACE(
"MCI_SEQ_SET_OFFSET !\n");
1298 TRACE(
"MCI_SEQ_SET_PORT = %d\n", lpParms->
dwPort);
1307 TRACE(
"MCI_SEQ_SET_TEMPO !\n");
1325 switch (lpParms->
dwItem) {
1329 TRACE(
"MCI_STATUS_CURRENT_TRACK => %lu\n", lpParms->
dwReturn);
1350 TRACE(
"MCI_STATUS_MEDIA_PRESENT => TRUE\n");
1356 TRACE(
"MCI_STATUS_NUMBER_OF_TRACKS => %lu\n", lpParms->
dwReturn);
1363 TRACE(
"MCI_STATUS_POSITION %s => %lu\n",
1378 TRACE(
"MCI_SEQ_STATUS_DIVTYPE !\n");
1385 default:
FIXME(
"There is a bad bad programmer\n");
1394 TRACE(
"MCI_SEQ_STATUS_MASTER !\n");
1399 TRACE(
"MCI_SEQ_STATUS_SLAVE !\n");
1404 TRACE(
"MCI_SEQ_STATUS_OFFSET !\n");
1417 TRACE(
"MCI_SEQ_STATUS_TEMPO !\n");
1421 FIXME(
"Unknown command %08X !\n", lpParms->
dwItem);
1445 switch (lpParms->
dwItem) {
1447 TRACE(
"MCI_GETDEVCAPS_DEVICE_TYPE !\n");
1452 TRACE(
"MCI_GETDEVCAPS_HAS_AUDIO !\n");
1457 TRACE(
"MCI_GETDEVCAPS_HAS_VIDEO !\n");
1462 TRACE(
"MCI_GETDEVCAPS_USES_FILES !\n");
1467 TRACE(
"MCI_GETDEVCAPS_COMPOUND_DEVICE !\n");
1472 TRACE(
"MCI_GETDEVCAPS_CAN_EJECT !\n");
1477 TRACE(
"MCI_GETDEVCAPS_CAN_PLAY !\n");
1482 TRACE(
"MCI_GETDEVCAPS_CAN_RECORD !\n");
1487 TRACE(
"MCI_GETDEVCAPS_CAN_SAVE !\n");
1492 FIXME(
"Unknown capability (%08x) !\n", lpParms->
dwItem);
1496 WARN(
"No GetDevCaps-Item !\n");
1511 static const WCHAR wszMidiSeq[] = {
'W',
'i',
'n',
'e',
'\'',
's',
' ',
'M',
'I',
'D',
'I',
' ',
's',
'e',
'q',
'u',
'e',
'n',
'c',
'e',
'r',0};
1526 WARN(
"Don't know this info command (%u)\n",
dwFlags);
1599 TRACE(
"Sending msg %04x to default driver proc\n", wMsg);
1600 return DefDriverProc(dwDevID, hDriv, wMsg, dwParam1, dwParam2);
1620 FIXME(
"Shouldn't receive a MCI_OPEN or CLOSE message\n");
1623 TRACE(
"Unsupported command [0x%x]\n", wMsg);
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
#define HeapFree(x, y, z)
#define MultiByteToWideChar
BOOL WINAPI SetThreadPriority(IN HANDLE hThread, IN int nPriority)
HANDLE WINAPI DECLSPEC_HOTPATCH CreateThread(IN LPSECURITY_ATTRIBUTES lpThreadAttributes, IN DWORD dwStackSize, IN LPTHREAD_START_ROUTINE lpStartAddress, IN LPVOID lpParameter, IN DWORD dwCreationFlags, OUT LPDWORD lpThreadId)
BOOL WINAPI GetExitCodeThread(IN HANDLE hThread, OUT LPDWORD lpExitCode)
DWORD WINAPI GetTickCount(VOID)
#define MCI_NO_COMMAND_TABLE
#define MCI_FORMAT_RETURN_BASE
#define MAKEMCIRESOURCE(wRet, wRes)
BOOL WINAPI mciDriverNotify(HWND hwndCallback, UINT uDeviceID, UINT uStatus)
#define MCI_RESOURCE_RETURNED
BOOL WINAPI mciSetDriverData(UINT uDeviceID, DWORD dwData)
DWORD WINAPI mciGetDriverData(UINT uDeviceID)
LRESULT WINAPI DefDriverProc(DWORD_PTR dwDriverIdentifier, HDRVR hDrv, UINT Msg, LPARAM lParam1, LPARAM lParam2)
LONG WINAPI mmioSeek(HMMIO hmmio, LONG lOffset, INT iOrigin)
MMRESULT WINAPI mmioClose(HMMIO hmmio, UINT uFlags)
MMRESULT WINAPI mmioDescend(HMMIO hmmio, LPMMCKINFO lpck, const MMCKINFO *lpckParent, UINT uFlags)
LONG WINAPI mmioRead(HMMIO hmmio, HPSTR pch, LONG cch)
HMMIO WINAPI mmioOpenW(LPWSTR szFileName, MMIOINFO *lpmmioinfo, DWORD dwOpenFlags)
#define InterlockedExchangePointer(Target, Value)
GLenum GLuint GLenum GLsizei const GLchar * buf
GLfloat GLfloat GLfloat GLfloat h
static DWORD CALLBACK MIDI_Starter(void *ptr)
static DWORD MIDI_ConvertMSToTimeFormat(WINE_MCIMIDI *wmm, DWORD _val)
static DWORD MIDI_mciStatus(WINE_MCIMIDI *wmm, DWORD dwFlags, LPMCI_STATUS_PARMS lpParms)
static DWORD MIDI_mciSeek(WINE_MCIMIDI *wmm, DWORD dwFlags, LPMCI_SEEK_PARMS lpParms)
static DWORD MIDI_GetMThdLengthMS(WINE_MCIMIDI *wmm)
static DWORD MIDI_ConvertTimeFormatToMS(WINE_MCIMIDI *wmm, DWORD val)
static DWORD MIDI_drvOpen(LPCWSTR str, LPMCI_OPEN_DRIVER_PARMSW modp)
static DWORD MIDI_mciReadByte(WINE_MCIMIDI *wmm, BYTE *lpbyt)
static DWORD MIDI_ConvertPulseToMS(WINE_MCIMIDI *wmm, DWORD pulse)
static DWORD MIDI_mciReadWord(WINE_MCIMIDI *wmm, LPWORD lpw)
static DWORD MIDI_mciSet(WINE_MCIMIDI *wmm, DWORD dwFlags, LPMCI_SEQ_SET_PARMS lpParms)
struct tagWINE_MCIMIDI WINE_MCIMIDI
static DWORD MIDI_mciReadMThd(WINE_MCIMIDI *wmm, DWORD dwOffset)
static DWORD MIDI_mciInfo(WINE_MCIMIDI *wmm, DWORD dwFlags, LPMCI_INFO_PARMSW lpParms)
static DWORD MIDI_mciPlay(WINE_MCIMIDI *wmm, DWORD dwFlags, LPMCI_PLAY_PARMS lpParms)
static DWORD MIDI_mciOpen(WINE_MCIMIDI *wmm, DWORD dwFlags, LPMCI_OPEN_PARMSW lpParms)
static WORD MIDI_mciReadVaryLen(WINE_MCIMIDI *wmm, LPDWORD lpdw)
static DWORD MIDI_mciReadNextEvent(WINE_MCIMIDI *wmm, MCI_MIDITRACK *mmt)
static DWORD mmr2mci(DWORD ret)
#define TIME_MS_IN_ONE_MINUTE
static DWORD MIDI_player(WINE_MCIMIDI *wmm, DWORD dwFlags)
LRESULT CALLBACK MCIMIDI_DriverProc(DWORD_PTR dwDevID, HDRVR hDriv, UINT wMsg, LPARAM dwParam1, LPARAM dwParam2)
static DWORD MIDI_mciClose(WINE_MCIMIDI *wmm, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
#define TIME_MS_IN_ONE_HOUR
static DWORD MIDI_mciPause(WINE_MCIMIDI *wmm, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
static DWORD MIDI_mciReadMTrk(WINE_MCIMIDI *wmm, MCI_MIDITRACK *mmt)
static MCI_MIDITRACK * MIDI_mciFindNextEvent(WINE_MCIMIDI *wmm, LPDWORD hiPulse)
static DWORD MIDI_mciStop(WINE_MCIMIDI *wmm, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
static DWORD MIDI_mciReadLong(WINE_MCIMIDI *wmm, LPDWORD lpdw)
static WINE_MCIMIDI * MIDI_mciGetOpenDev(MCIDEVICEID wDevID, UINT wMsg)
static DWORD MIDI_mciGetDevCaps(WINE_MCIMIDI *wmm, DWORD dwFlags, LPMCI_GETDEVCAPS_PARMS lpParms)
static DWORD ensurePlayerThread(WINE_MCIMIDI *wmm)
#define TIME_MS_IN_ONE_SECOND
static DWORD MIDI_drvClose(DWORD dwDevID)
static DWORD MIDI_mciResume(WINE_MCIMIDI *wmm, DWORD dwFlags, LPMCI_GENERIC_PARMS lpParms)
static void MIDI_mciNotify(DWORD_PTR hWndCallBack, WINE_MCIMIDI *wmm, UINT wStatus)
#define MCI_SEQ_STATUS_TEMPO
#define MCIERR_FLAGS_NOT_COMPATIBLE
#define MCI_OPEN_SHAREABLE
#define MCI_SEQ_STATUS_DIVTYPE
#define MCI_NOTIFY_SUPERSEDED
#define MCI_GETDEVCAPS_CAN_SAVE
#define MCI_GETDEVCAPS_HAS_VIDEO
#define MCI_FORMAT_SMPTE_30
#define MCI_STATUS_POSITION
#define MCI_SEQ_SET_OFFSET
#define DRV_QUERYCONFIGURE
#define MIDIERR_INVALIDSETUP
#define MCI_GETDEVCAPS_CAN_RECORD
#define MCI_FORMAT_MILLISECONDS
#define MCIERR_FILE_NOT_FOUND
#define MCI_SEQ_DIV_SMPTE_25
#define MCI_FORMAT_SMPTE_24
#define MCI_GETDEVCAPS_DEVICE_TYPE
#define MCI_SEQ_STATUS_OFFSET
#define MCI_SEQ_STATUS_PORT
#define MCIERR_UNRECOGNIZED_COMMAND
#define MCI_SEQ_DIV_SMPTE_30
#define MCIERR_SEQ_PORT_MAPNODEVICE
#define MCI_GETDEVCAPS_COMPOUND_DEVICE
#define MCI_SEQ_STATUS_SLAVE
#define MCIERR_BAD_INTEGER
#define MCI_SET_DOOR_OPEN
#define MCI_GETDEVCAPS_USES_FILES
#define MCI_GETDEVCAPS_CAN_PLAY
#define MCIERR_PARAM_OVERFLOW
#define MCIERR_INVALID_DEVICE_ID
#define MCI_SET_TIME_FORMAT
#define MCI_SEQ_SET_MASTER
#define MCIERR_SEQ_PORT_NONEXISTENT
#define MCI_SEQ_SET_TEMPO
#define MCIERR_INVALID_FILE
#define MCI_GETDEVCAPS_CAN_EJECT
#define MCIERR_DEVICE_OPEN
#define MCIERR_MISSING_PARAMETER
#define MCI_FORMAT_SMPTE_25
#define MCI_SET_AUDIO_RIGHT
#define MCIERR_NULL_PARAMETER_BLOCK
#define MCI_NOTIFY_ABORTED
#define MCI_SET_AUDIO_ALL
#define MCI_SEQ_SET_SLAVE
#define MCIERR_OUTOFRANGE
#define MCI_INFO_COPYRIGHT
#define MCI_STATUS_CURRENT_TRACK
#define MCI_SEQ_DIV_SMPTE_30DROP
#define MCI_STATUS_NUMBER_OF_TRACKS
#define MCIERR_OUT_OF_MEMORY
#define MCI_SET_DOOR_CLOSED
#define MCIERR_SEQ_PORT_INUSE
#define MCI_GETDEVCAPS_ITEM
#define MMSYSERR_ALLOCATED
#define MCI_STATUS_LENGTH
#define MCI_DEVTYPE_SEQUENCER
#define MCI_FORMAT_SMPTE_30DROP
#define MCI_SET_AUDIO_LEFT
#define mmioFOURCC(c0, c1, c2, c3)
#define MCI_SEQ_STATUS_MASTER
#define MCI_SEEK_TO_START
#define MCI_NOTIFY_SUCCESSFUL
#define MCI_NOTIFY_FAILURE
#define MCI_SEQ_DIV_SMPTE_24
#define MCI_MODE_NOT_READY
#define MCI_STATUS_MEDIA_PRESENT
#define MCIERR_BAD_TIME_FORMAT
#define MMSYSERR_BADDEVICEID
#define MCIERR_NONAPPLICABLE_FUNCTION
#define MCIERR_UNSUPPORTED_FUNCTION
#define MCI_STATUS_TIME_FORMAT
#define MCI_GETDEVCAPS_HAS_AUDIO
static CRYPT_DATA_BLOB b3[]
static CRYPT_DATA_BLOB b2[]
static CRYPT_DATA_BLOB b1[]
static const char mbstate_t *static wchar_t const char mbstate_t *static const wchar_t int *static double
_In_ DWORD _In_ DWORD dwOffset
DWORD WINAPI WaitForSingleObject(IN HANDLE hHandle, IN DWORD dwMilliseconds)
VOID WINAPI DECLSPEC_HOTPATCH Sleep(IN DWORD dwMilliseconds)
#define THREAD_PRIORITY_TIME_CRITICAL
_In_ PCCERT_CONTEXT _In_ DWORD dwFlags
UINT WINAPI midiOutReset(HMIDIOUT hMidiOut)
UINT WINAPI midiOutGetNumDevs(void)
UINT WINAPI midiOutClose(HMIDIOUT hMidiOut)
UINT WINAPI midiOutShortMsg(HMIDIOUT hMidiOut, DWORD dwMsg)
MMRESULT WINAPI midiOutOpen(LPHMIDIOUT lphMidiOut, UINT uDeviceID, DWORD_PTR dwCallback, DWORD_PTR dwInstance, DWORD dwFlags)
int WINAPI MessageBoxA(_In_opt_ HWND hWnd, _In_opt_ LPCSTR lpText, _In_opt_ LPCSTR lpCaption, _In_ UINT uType)