2 * Sample MIDI Wine Driver for Linux
4 * Copyright 1994 Martin Ayotte
11 #include <sys/ioctl.h>
22 #include <linux/soundcard.h>
24 #include <machine/soundcard.h>
27 int MMSYSTEM_DevIDToIndex(UINT16
);
29 #if defined(linux) || defined(__FreeBSD__)
30 #define MIDI_DEV "/dev/sequencer"
33 #define IOCTL(a,b,c) ioctl(a,b,&c)
35 #define IOCTL(a,b,c) (c = ioctl(a,b,c) )
38 #define MAX_MIDIINDRV 2
39 #define MAX_MIDIOUTDRV 2
40 #define MAX_MCIMIDIDRV 2
46 MIDIOPENDESC midiDesc
;
56 MIDIOPENDESC midiDesc
;
63 int nUseCount
; /* Incremented for each shared open */
64 BOOL16 fShareable
; /* TRUE if first open was shareable */
65 WORD wNotifyDeviceID
; /* MCI device ID with a pending notification */
66 HANDLE16 hCallback
; /* Callback handle for pending notification */
67 HMMIO16 hFile
; /* mmio file handle open as Element */
73 MCI_OPEN_PARMS openParms
;
78 static LINUX_MIDIIN MidiInDev
[MAX_MIDIINDRV
];
79 static LINUX_MIDIOUT MidiOutDev
[MAX_MIDIOUTDRV
];
80 static LINUX_MCIMIDI MCIMidiDev
[MAX_MCIMIDIDRV
];
84 /**************************************************************************
85 * MIDI_NotifyClient [internal]
87 static DWORD
MIDI_NotifyClient(UINT16 wDevID
, WORD wMsg
,
88 DWORD dwParam1
, DWORD dwParam2
)
90 #if defined(linux) || defined(__FreeBSD__)
91 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
92 if (MidiInDev
[index
].wFlags
!= DCB_NULL
&& !DriverCallback(
93 MidiInDev
[index
].midiDesc
.dwCallback
, MidiInDev
[index
].wFlags
,
94 MidiInDev
[index
].midiDesc
.hMidi
, wMsg
,
95 MidiInDev
[index
].midiDesc
.dwInstance
, dwParam1
, dwParam2
)) {
96 dprintf_midi(stddeb
, "MIDI_NotifyClient // can't notify client !\n");
97 return MMSYSERR_NOERROR
;
101 return MMSYSERR_NOTENABLED
;
106 /**************************************************************************
107 * MIDI_ReadByte [internal]
109 static DWORD
MIDI_ReadByte(UINT16 wDevID
, BYTE
*lpbyt
)
111 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
112 #if defined(linux) || defined(__FreeBSD__)
114 if (mmioRead(MCIMidiDev
[index
].hFile
, (HPSTR
)lpbyt
,
115 (long) sizeof(BYTE
)) == (long) sizeof(BYTE
)) {
119 dprintf_midi(stddeb
, "MIDI_ReadByte // error reading wDevID=%04X\n", wDevID
);
120 return MCIERR_INTERNAL
;
123 return MMSYSERR_NOTENABLED
;
128 /**************************************************************************
129 * MIDI_ReadWord [internal]
131 static DWORD
MIDI_ReadWord(UINT16 wDevID
, LPWORD lpw
)
135 if (MIDI_ReadByte(wDevID
, &hibyte
) == 0) {
136 if (MIDI_ReadByte(wDevID
, &lobyte
) == 0) {
137 *lpw
= ((WORD
)hibyte
<< 8) + lobyte
;
142 dprintf_midi(stddeb
, "MIDI_ReadWord // error reading wDevID=%04X\n", wDevID
);
143 return MCIERR_INTERNAL
;
147 /**************************************************************************
148 * MIDI_ReadLong [internal]
150 static DWORD
MIDI_ReadLong(UINT16 wDevID
, LPDWORD lpdw
)
154 if (MIDI_ReadWord(wDevID
, &hiword
) == 0) {
155 if (MIDI_ReadWord(wDevID
, &loword
) == 0) {
156 *lpdw
= MAKELONG(loword
, hiword
);
161 dprintf_midi(stddeb
, "MIDI_ReadLong // error reading wDevID=%04X\n", wDevID
);
162 return MCIERR_INTERNAL
;
166 /**************************************************************************
167 * MIDI_ReadVaryLen [internal]
169 static DWORD
MIDI_ReadVaryLen(UINT16 wDevID
, LPDWORD lpdw
)
173 if (lpdw
== NULL
) return MCIERR_INTERNAL
;
174 if (MIDI_ReadByte(wDevID
, &byte
) != 0) {
175 dprintf_midi(stddeb
, "MIDI_ReadVaryLen // error reading wDevID=%04X\n", wDevID
);
176 return MCIERR_INTERNAL
;
178 value
= (DWORD
)(byte
& 0x7F);
179 while (byte
& 0x80) {
180 if (MIDI_ReadByte(wDevID
, &byte
) != 0) {
181 dprintf_midi(stddeb
, "MIDI_ReadVaryLen // error reading wDevID=%04X\n", wDevID
);
182 return MCIERR_INTERNAL
;
184 value
= (value
<< 7) + (byte
& 0x7F);
188 dprintf_midi(stddeb, "MIDI_ReadVaryLen // val=%08lX \n", value);
194 /**************************************************************************
195 * MIDI_ReadMThd [internal]
197 static DWORD
MIDI_ReadMThd(UINT16 wDevID
, DWORD dwOffset
)
199 #if defined(linux) || defined(__FreeBSD__)
200 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
203 dprintf_midi(stddeb
, "MIDI_ReadMThd(%04X, %08lX);\n", wDevID
, dwOffset
);
204 if (mmioSeek(MCIMidiDev
[index
].hFile
, dwOffset
, SEEK_SET
) != dwOffset
) {
205 dprintf_midi(stddeb
, "MIDI_ReadMThd // can't seek at %08lX begin of 'MThd' \n", dwOffset
);
206 return MCIERR_INTERNAL
;
208 if (mmioRead(MCIMidiDev
[index
].hFile
, (HPSTR
)&fourcc
,
209 (long) sizeof(FOURCC
)) != (long) sizeof(FOURCC
)) {
210 return MCIERR_INTERNAL
;
212 if (MIDI_ReadLong(wDevID
, &toberead
) != 0) {
213 return MCIERR_INTERNAL
;
215 if (MIDI_ReadWord(wDevID
, &MCIMidiDev
[index
].wFormat
) != 0) {
216 return MCIERR_INTERNAL
;
218 if (MIDI_ReadWord(wDevID
, &MCIMidiDev
[index
].nTracks
) != 0) {
219 return MCIERR_INTERNAL
;
221 if (MIDI_ReadWord(wDevID
, &MCIMidiDev
[index
].nTempo
) != 0) {
222 return MCIERR_INTERNAL
;
224 dprintf_midi(stddeb
, "MIDI_ReadMThd // toberead=%08lX, wFormat=%04X nTracks=%04X nTempo=%04X\n",
225 toberead
, MCIMidiDev
[index
].wFormat
,
226 MCIMidiDev
[index
].nTracks
,
227 MCIMidiDev
[index
].nTempo
);
228 toberead
-= 3 * sizeof(WORD
);
230 ntrks = read16bit ();
231 Mf_division = division = read16bit ();
236 return MMSYSERR_NOTENABLED
;
241 static DWORD
MIDI_ReadMTrk(UINT16 wDevID
, DWORD dwOffset
)
243 #if defined(linux) || defined(__FreeBSD__)
244 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
247 if (mmioSeek(MCIMidiDev
[index
].hFile
, dwOffset
, SEEK_SET
) != dwOffset
) {
248 dprintf_midi(stddeb
, "MIDI_ReadMTrk // can't seek at %08lX begin of 'MThd' \n", dwOffset
);
250 if (mmioRead(MCIMidiDev
[index
].hFile
, (HPSTR
)&fourcc
,
251 (long) sizeof(FOURCC
)) != (long) sizeof(FOURCC
)) {
252 return MCIERR_INTERNAL
;
254 if (MIDI_ReadLong(wDevID
, &toberead
) != 0) {
255 return MCIERR_INTERNAL
;
257 dprintf_midi(stddeb
, "MIDI_ReadMTrk // toberead=%08lX\n", toberead
);
258 toberead
-= 3 * sizeof(WORD
);
259 MCIMidiDev
[index
].dwTotalLen
= toberead
;
262 return MMSYSERR_NOTENABLED
;
267 /**************************************************************************
268 * MIDI_mciOpen [internal]
270 static DWORD
MIDI_mciOpen(UINT16 wDevID
, DWORD dwFlags
, LPMCI_OPEN_PARMS lpParms
)
272 #if defined(linux) || defined(__FreeBSD__)
274 MIDIOPENDESC MidiDesc
;
277 LPSTR lpstrElementName
;
280 dprintf_midi(stddeb
, "MIDI_mciOpen(%08lX, %p)\n", dwFlags
, lpParms
);
281 if (lpParms
== NULL
) return MCIERR_INTERNAL
;
283 wDevID
= lpParms
->wDeviceID
;
284 index
= MMSYSTEM_DevIDToIndex(wDevID
);
286 if (MCIMidiDev
[index
].nUseCount
> 0) {
287 /* The driver already open on this channel */
288 /* If the driver was opened shareable before and this open specifies */
289 /* shareable then increment the use count */
290 if (MCIMidiDev
[index
].fShareable
&& (dwFlags
& MCI_OPEN_SHAREABLE
))
291 ++MCIMidiDev
[index
].nUseCount
;
293 return MCIERR_MUST_USE_SHAREABLE
;
296 MCIMidiDev
[index
].nUseCount
= 1;
297 MCIMidiDev
[index
].fShareable
= dwFlags
& MCI_OPEN_SHAREABLE
;
299 dprintf_midi(stddeb
, "MIDI_mciOpen // wDevID=%04X\n", wDevID
);
300 lpParms
->wDeviceID
= wDevID
;
301 dprintf_midi(stddeb
, "MIDI_mciOpen // lpParms->wDevID=%04X\n", lpParms
->wDeviceID
);
302 dprintf_midi(stddeb
, "MIDI_mciOpen // before OPEN_ELEMENT\n");
303 if (dwFlags
& MCI_OPEN_ELEMENT
) {
304 lpstrElementName
= (LPSTR
)PTR_SEG_TO_LIN(lpParms
->lpstrElementName
);
305 dprintf_midi(stddeb
, "MIDI_mciOpen // MCI_OPEN_ELEMENT '%s' !\n", lpstrElementName
);
306 if (strlen(lpstrElementName
) > 0) {
307 strcpy(str
, lpstrElementName
);
309 MCIMidiDev
[index
].hFile
= mmioOpen(str
, NULL
,
310 MMIO_ALLOCBUF
| MMIO_READWRITE
| MMIO_EXCLUSIVE
);
311 if (MCIMidiDev
[index
].hFile
== 0) {
312 dprintf_midi(stddeb
, "MIDI_mciOpen // can't find file='%s' !\n", str
);
313 return MCIERR_FILE_NOT_FOUND
;
317 MCIMidiDev
[index
].hFile
= 0;
319 dprintf_midi(stddeb
, "MIDI_mciOpen // hFile=%u\n", MCIMidiDev
[index
].hFile
);
320 memcpy(&MCIMidiDev
[index
].openParms
, lpParms
, sizeof(MCI_OPEN_PARMS
));
321 MCIMidiDev
[index
].wNotifyDeviceID
= lpParms
->wDeviceID
;
322 MCIMidiDev
[index
].dwStatus
= MCI_MODE_STOP
;
323 MCIMidiDev
[index
].dwBeginData
= 0;
324 MCIMidiDev
[index
].dwTotalLen
= 0;
326 if (MCIMidiDev
[index
].hFile
!= 0) {
328 if (mmioDescend(MCIMidiDev
[index
].hFile
, &ckMainRIFF
, NULL
, 0) != 0) {
329 return MCIERR_INTERNAL
;
331 dprintf_midi(stddeb
,"MIDI_mciOpen // ParentChunk ckid=%.4s fccType=%.4s cksize=%08lX \n",
332 (LPSTR
)&ckMainRIFF
.ckid
, (LPSTR
)&ckMainRIFF
.fccType
,
335 if (ckMainRIFF
.ckid
== mmioFOURCC('R', 'M', 'I', 'D')) {
336 dprintf_midi(stddeb
, "MIDI_mciOpen // is a 'RMID' file \n");
337 dwOffset
= ckMainRIFF
.dwDataOffset
;
339 if (ckMainRIFF
.ckid
!= mmioFOURCC('M', 'T', 'h', 'd')) {
340 dprintf_midi(stddeb
, "MIDI_mciOpen // unknown format !\n");
341 return MCIERR_INTERNAL
;
343 if (MIDI_ReadMThd(wDevID
, dwOffset
) != 0) {
344 dprintf_midi(stddeb
, "MIDI_mciOpen // can't read 'MThd' header \n");
345 return MCIERR_INTERNAL
;
347 dwOffset
= mmioSeek(MCIMidiDev
[index
].hFile
, 0, SEEK_CUR
);
348 if (MIDI_ReadMTrk(wDevID
, dwOffset
) != 0) {
349 dprintf_midi(stddeb
, "MIDI_mciOpen // can't read 'MTrk' header \n");
350 return MCIERR_INTERNAL
;
352 dwOffset
= mmioSeek(MCIMidiDev
[index
].hFile
, 0, SEEK_CUR
);
353 MCIMidiDev
[index
].dwBeginData
= dwOffset
;
354 dprintf_midi(stddeb
, "MIDI_mciOpen // Chunk Found ckid=%.4s fccType=%.4s cksize=%08lX \n",
355 (LPSTR
)&ckMainRIFF
.ckid
, (LPSTR
)&ckMainRIFF
.fccType
,
358 dwRet
= modMessage(wDevID
, MODM_OPEN
, 0, (DWORD
)&MidiDesc
, CALLBACK_NULL
);
359 dwRet
= midMessage(wDevID
, MIDM_OPEN
, 0, (DWORD
)&MidiDesc
, CALLBACK_NULL
);
362 return MMSYSERR_NOTENABLED
;
367 /**************************************************************************
368 * MIDI_mciStop [internal]
370 static DWORD
MIDI_mciStop(UINT16 wDevID
, DWORD dwFlags
, LPMCI_GENERIC_PARMS lpParms
)
372 #if defined(linux) || defined(__FreeBSD__)
373 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
374 dprintf_midi(stddeb
, "MIDI_mciStop(%04X, %08lX, %p);\n", wDevID
, dwFlags
, lpParms
);
375 if (lpParms
== NULL
) return MCIERR_INTERNAL
;
376 MCIMidiDev
[index
].dwStatus
= MCI_MODE_STOP
;
377 dprintf_midi(stddeb
, "MIDI_mciStop // MCIMidiDev[index].dwStatus=%p %d\n",
378 &MCIMidiDev
[index
].dwStatus
, MCIMidiDev
[index
].dwStatus
);
381 return MCIERR_INTERNAL
;
386 /**************************************************************************
387 * MIDI_mciClose [internal]
389 static DWORD
MIDI_mciClose(UINT16 wDevID
, DWORD dwParam
, LPMCI_GENERIC_PARMS lpParms
)
391 #if defined(linux) || defined(__FreeBSD__)
392 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
394 dprintf_midi(stddeb
, "MIDI_mciClose(%04X, %08lX, %p);\n", wDevID
, dwParam
, lpParms
);
395 if (MCIMidiDev
[index
].dwStatus
!= MCI_MODE_STOP
) {
396 MIDI_mciStop(wDevID
, MCI_WAIT
, lpParms
);
398 MCIMidiDev
[index
].dwStatus
= MCI_MODE_STOP
;
399 MCIMidiDev
[index
].nUseCount
--;
400 if (MCIMidiDev
[index
].nUseCount
== 0) {
401 if (MCIMidiDev
[index
].hFile
!= 0) {
402 mmioClose(MCIMidiDev
[index
].hFile
, 0);
403 MCIMidiDev
[index
].hFile
= 0;
404 dprintf_midi(stddeb
, "MIDI_mciClose // hFile closed !\n");
406 dwRet
= modMessage(wDevID
, MODM_CLOSE
, 0, 0L, 0L);
407 if (dwRet
!= MMSYSERR_NOERROR
) return MCIERR_INTERNAL
;
408 dwRet
= midMessage(wDevID
, MIDM_CLOSE
, 0, 0L, 0L);
409 if (dwRet
!= MMSYSERR_NOERROR
) return MCIERR_INTERNAL
;
418 /**************************************************************************
419 * MIDI_mciPlay [internal]
421 static DWORD
MIDI_mciPlay(UINT16 wDevID
, DWORD dwFlags
, LPMCI_PLAY_PARMS lpParms
)
423 #if defined(linux) || defined(__FreeBSD__)
424 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
431 dprintf_midi(stddeb
, "MIDI_mciPlay(%04X, %08lX, %p);\n", wDevID
, dwFlags
, lpParms
);
432 if (MCIMidiDev
[index
].hFile
== 0) {
433 dprintf_midi(stddeb
, "MIDI_mciPlay // can't find file='%08lx' !\n",
434 MCIMidiDev
[index
].openParms
.lpstrElementName
);
435 return MCIERR_FILE_NOT_FOUND
;
437 start
= 1; end
= 99999;
438 if (dwFlags
& MCI_FROM
) {
439 start
= lpParms
->dwFrom
;
440 dprintf_midi(stddeb
, "MIDI_mciPlay // MCI_FROM=%d \n", start
);
442 if (dwFlags
& MCI_TO
) {
444 dprintf_midi(stddeb
, "MIDI_mciPlay // MCI_TO=%d \n", end
);
447 if (dwFlags
& MCI_NOTIFY
) {
448 dprintf_midi(stddeb
, "MIDI_mciPlay // MCI_NOTIFY %08lX !\n", lpParms
->dwCallback
);
451 dprintf_midi(stddeb
, "MIDI_mciPlay // Can't 'fork' process !\n");
454 dprintf_midi(stddeb
, "MIDI_mciPlay // process started ! play in background ...\n");
457 dprintf_midi(stddeb
, "MIDI_mciPlay // process started ! return to caller...\n");
462 lpMidiHdr
= &MCIMidiDev
[index
].MidiHdr
;
463 lpMidiHdr
->lpData
= (LPSTR
) malloc(1200);
464 if (lpMidiHdr
->lpData
== NULL
) return MCIERR_INTERNAL
;
465 lpMidiHdr
->dwBufferLength
= 1024;
466 lpMidiHdr
->dwUser
= 0L;
467 lpMidiHdr
->dwFlags
= 0L;
468 dwRet
= modMessage(wDevID
, MODM_PREPARE
, 0, (DWORD
)lpMidiHdr
, sizeof(MIDIHDR
));
469 /* dprintf_midi(stddeb, "MIDI_mciPlay // after MODM_PREPARE \n"); */
470 MCIMidiDev
[index
].dwStatus
= MCI_MODE_PLAY
;
471 while(MCIMidiDev
[index
].dwStatus
!= MCI_MODE_STOP
) {
472 dprintf_midi(stddeb
, "MIDI_mciPlay // MCIMidiDev[index].dwStatus=%p %d\n",
473 &MCIMidiDev
[index
].dwStatus
, MCIMidiDev
[index
].dwStatus
);
474 ptr
= (LPWORD
)lpMidiHdr
->lpData
;
475 for (count
= 0; count
< lpMidiHdr
->dwBufferLength
; count
++) {
476 if (MIDI_ReadVaryLen(wDevID
, &dwData
) != 0) break;
477 *ptr
= LOWORD(dwData
);
480 count = mmioRead(MCIMidiDev[index].hFile, lpMidiHdr->lpData, lpMidiHdr->dwBufferLength);
482 if (count
< 1) break;
483 lpMidiHdr
->dwBytesRecorded
= count
;
484 dprintf_midi(stddeb
, "MIDI_mciPlay // before MODM_LONGDATA lpMidiHdr=%p dwBytesRecorded=%lu\n",
485 lpMidiHdr
, lpMidiHdr
->dwBytesRecorded
);
486 dwRet
= modMessage(wDevID
, MODM_LONGDATA
, 0, (DWORD
)lpMidiHdr
, sizeof(MIDIHDR
));
488 dwRet
= modMessage(wDevID
, MODM_UNPREPARE
, 0, (DWORD
)lpMidiHdr
, sizeof(MIDIHDR
));
489 if (lpMidiHdr
->lpData
!= NULL
) {
490 free(lpMidiHdr
->lpData
);
491 lpMidiHdr
->lpData
= NULL
;
493 MCIMidiDev
[index
].dwStatus
= MCI_MODE_STOP
;
494 if (dwFlags
& MCI_NOTIFY
) {
495 dprintf_midi(stddeb
, "MIDI_mciPlay // MCI_NOTIFY_SUCCESSFUL %08lX !\n", lpParms
->dwCallback
);
496 mciDriverNotify((HWND16
)LOWORD(lpParms
->dwCallback
),
497 MCIMidiDev
[index
].wNotifyDeviceID
, MCI_NOTIFY_SUCCESSFUL
);
504 return MMSYSERR_NOTENABLED
;
509 /**************************************************************************
510 * MIDI_mciRecord [internal]
512 static DWORD
MIDI_mciRecord(UINT16 wDevID
, DWORD dwFlags
, LPMCI_RECORD_PARMS lpParms
)
514 #if defined(linux) || defined(__FreeBSD__)
515 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
520 dprintf_midi(stddeb
, "MIDI_mciRecord(%04X, %08lX, %p);\n", wDevID
, dwFlags
, lpParms
);
521 if (MCIMidiDev
[index
].hFile
== 0) {
522 dprintf_midi(stddeb
, "MIDI_mciRecord // can't find file='%08lx' !\n",
523 MCIMidiDev
[index
].openParms
.lpstrElementName
);
524 return MCIERR_FILE_NOT_FOUND
;
526 start
= 1; end
= 99999;
527 if (dwFlags
& MCI_FROM
) {
528 start
= lpParms
->dwFrom
;
529 dprintf_midi(stddeb
, "MIDI_mciRecord // MCI_FROM=%d \n", start
);
531 if (dwFlags
& MCI_TO
) {
533 dprintf_midi(stddeb
, "MIDI_mciRecord // MCI_TO=%d \n", end
);
535 lpMidiHdr
= &MCIMidiDev
[index
].MidiHdr
;
536 lpMidiHdr
->lpData
= (LPSTR
) xmalloc(1200);
537 lpMidiHdr
->dwBufferLength
= 1024;
538 lpMidiHdr
->dwUser
= 0L;
539 lpMidiHdr
->dwFlags
= 0L;
540 dwRet
= midMessage(wDevID
, MIDM_PREPARE
, 0, (DWORD
)lpMidiHdr
, sizeof(MIDIHDR
));
541 dprintf_midi(stddeb
, "MIDI_mciRecord // after MIDM_PREPARE \n");
542 MCIMidiDev
[index
].dwStatus
= MCI_MODE_RECORD
;
543 while(MCIMidiDev
[index
].dwStatus
!= MCI_MODE_STOP
) {
544 dprintf_midi(stddeb
, "MIDI_mciRecord // MCIMidiDev[index].dwStatus=%p %d\n",
545 &MCIMidiDev
[index
].dwStatus
, MCIMidiDev
[index
].dwStatus
);
546 lpMidiHdr
->dwBytesRecorded
= 0;
547 dwRet
= midMessage(wDevID
, MIDM_START
, 0, 0L, 0L);
548 dprintf_midi(stddeb
, "MIDI_mciRecord // after MIDM_START lpMidiHdr=%p dwBytesRecorded=%lu\n",
549 lpMidiHdr
, lpMidiHdr
->dwBytesRecorded
);
550 if (lpMidiHdr
->dwBytesRecorded
== 0) break;
552 dprintf_midi(stddeb
, "MIDI_mciRecord // before MIDM_UNPREPARE \n");
553 dwRet
= midMessage(wDevID
, MIDM_UNPREPARE
, 0, (DWORD
)lpMidiHdr
, sizeof(MIDIHDR
));
554 dprintf_midi(stddeb
, "MIDI_mciRecord // after MIDM_UNPREPARE \n");
555 if (lpMidiHdr
->lpData
!= NULL
) {
556 free(lpMidiHdr
->lpData
);
557 lpMidiHdr
->lpData
= NULL
;
559 MCIMidiDev
[index
].dwStatus
= MCI_MODE_STOP
;
560 if (dwFlags
& MCI_NOTIFY
) {
561 dprintf_midi(stddeb
, "MIDI_mciRecord // MCI_NOTIFY_SUCCESSFUL %08lX !\n", lpParms
->dwCallback
);
562 mciDriverNotify((HWND16
)LOWORD(lpParms
->dwCallback
),
563 MCIMidiDev
[index
].wNotifyDeviceID
, MCI_NOTIFY_SUCCESSFUL
);
567 return MMSYSERR_NOTENABLED
;
572 /**************************************************************************
573 * MIDI_mciPause [internal]
575 static DWORD
MIDI_mciPause(UINT16 wDevID
, DWORD dwFlags
, LPMCI_GENERIC_PARMS lpParms
)
577 #if defined(linux) || defined(__FreeBSD__)
578 dprintf_midi(stddeb
, "MIDI_mciPause(%04X, %08lX, %p);\n", wDevID
, dwFlags
, lpParms
);
579 if (lpParms
== NULL
) return MCIERR_INTERNAL
;
582 return MCIERR_INTERNAL
;
587 /**************************************************************************
588 * MIDI_mciResume [internal]
590 static DWORD
MIDI_mciResume(UINT16 wDevID
, DWORD dwFlags
, LPMCI_GENERIC_PARMS lpParms
)
592 #if defined(linux) || defined(__FreeBSD__)
593 dprintf_midi(stddeb
, "MIDI_mciResume(%04X, %08lX, %p);\n", wDevID
, dwFlags
, lpParms
);
594 if (lpParms
== NULL
) return MCIERR_INTERNAL
;
597 return MCIERR_INTERNAL
;
602 /**************************************************************************
603 * MIDI_mciSet [internal]
605 static DWORD
MIDI_mciSet(UINT16 wDevID
, DWORD dwFlags
, LPMCI_SET_PARMS lpParms
)
607 #if defined(linux) || defined(__FreeBSD__)
608 dprintf_midi(stddeb
, "MIDI_mciSet(%04X, %08lX, %p);\n", wDevID
, dwFlags
, lpParms
);
609 if (lpParms
== NULL
) return MCIERR_INTERNAL
;
610 dprintf_midi(stddeb
, "MIDI_mciSet // dwTimeFormat=%08lX\n", lpParms
->dwTimeFormat
);
611 dprintf_midi(stddeb
, "MIDI_mciSet // dwAudio=%08lX\n", lpParms
->dwAudio
);
612 if (dwFlags
& MCI_SET_TIME_FORMAT
) {
613 switch (lpParms
->dwTimeFormat
) {
614 case MCI_FORMAT_MILLISECONDS
:
615 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_FORMAT_MILLISECONDS !\n");
617 case MCI_FORMAT_BYTES
:
618 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_FORMAT_BYTES !\n");
620 case MCI_FORMAT_SAMPLES
:
621 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_FORMAT_SAMPLES !\n");
624 dprintf_midi(stddeb
, "MIDI_mciSet // bad time format !\n");
625 return MCIERR_BAD_TIME_FORMAT
;
628 if (dwFlags
& MCI_SET_VIDEO
) return MCIERR_UNSUPPORTED_FUNCTION
;
629 if (dwFlags
& MCI_SET_DOOR_OPEN
) return MCIERR_UNSUPPORTED_FUNCTION
;
630 if (dwFlags
& MCI_SET_DOOR_CLOSED
) return MCIERR_UNSUPPORTED_FUNCTION
;
631 if (dwFlags
& MCI_SET_AUDIO
) {
632 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_SET_AUDIO !\n");
634 if (dwFlags
&& MCI_SET_ON
) {
635 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_SET_ON !\n");
636 if (dwFlags
&& MCI_SET_AUDIO_LEFT
) {
637 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_SET_AUDIO_LEFT !\n");
639 if (dwFlags
&& MCI_SET_AUDIO_RIGHT
) {
640 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_SET_AUDIO_RIGHT !\n");
643 if (dwFlags
& MCI_SET_OFF
) {
644 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_SET_OFF !\n");
646 if (dwFlags
& MCI_SEQ_SET_MASTER
) {
647 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_SEQ_SET_MASTER !\n");
649 if (dwFlags
& MCI_SEQ_SET_SLAVE
) {
650 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_SEQ_SET_SLAVE !\n");
652 if (dwFlags
& MCI_SEQ_SET_OFFSET
) {
653 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_SEQ_SET_OFFSET !\n");
655 if (dwFlags
& MCI_SEQ_SET_PORT
) {
656 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_SEQ_SET_PORT !\n");
658 if (dwFlags
& MCI_SEQ_SET_TEMPO
) {
659 dprintf_midi(stddeb
, "MIDI_mciSet // MCI_SEQ_SET_TEMPO !\n");
663 return MCIERR_INTERNAL
;
668 /**************************************************************************
669 * MIDI_mciStatus [internal]
671 static DWORD
MIDI_mciStatus(UINT16 wDevID
, DWORD dwFlags
, LPMCI_STATUS_PARMS lpParms
)
673 #if defined(linux) || defined(__FreeBSD__)
674 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
675 dprintf_midi(stddeb
, "MIDI_mciStatus(%04X, %08lX, %p);\n", wDevID
, dwFlags
, lpParms
);
676 if (lpParms
== NULL
) return MCIERR_INTERNAL
;
677 if (dwFlags
& MCI_STATUS_ITEM
) {
678 switch(lpParms
->dwItem
) {
679 case MCI_STATUS_CURRENT_TRACK
:
680 lpParms
->dwReturn
= 1;
682 case MCI_STATUS_LENGTH
:
683 lpParms
->dwReturn
= 5555;
684 if (dwFlags
& MCI_TRACK
) {
685 lpParms
->dwTrack
= 1;
686 lpParms
->dwReturn
= 2222;
689 case MCI_STATUS_MODE
:
690 lpParms
->dwReturn
= MCI_MODE_STOP
;
692 case MCI_STATUS_MEDIA_PRESENT
:
693 dprintf_midi(stddeb
, "MIDI_mciStatus // MCI_STATUS_MEDIA_PRESENT !\n");
694 lpParms
->dwReturn
= TRUE
;
696 case MCI_STATUS_NUMBER_OF_TRACKS
:
697 lpParms
->dwReturn
= 1;
699 case MCI_STATUS_POSITION
:
700 lpParms
->dwReturn
= 3333;
701 if (dwFlags
& MCI_STATUS_START
) {
704 if (dwFlags
& MCI_TRACK
) {
705 lpParms
->dwTrack
= 1;
706 lpParms
->dwReturn
= 777;
709 case MCI_STATUS_READY
:
710 dprintf_midi(stddeb
, "MIDI_mciStatus // MCI_STATUS_READY !\n");
711 lpParms
->dwReturn
= TRUE
;
713 case MCI_STATUS_TIME_FORMAT
:
714 dprintf_midi(stddeb
, "MIDI_mciStatus // MCI_STATUS_TIME_FORMAT !\n");
715 lpParms
->dwReturn
= MCI_FORMAT_MILLISECONDS
;
717 case MCI_SEQ_STATUS_DIVTYPE
:
718 dprintf_midi(stddeb
, "MIDI_mciStatus // MCI_SEQ_STATUS_DIVTYPE !\n");
719 lpParms
->dwReturn
= 0;
721 case MCI_SEQ_STATUS_MASTER
:
722 dprintf_midi(stddeb
, "MIDI_mciStatus // MCI_SEQ_STATUS_MASTER !\n");
723 lpParms
->dwReturn
= 0;
725 case MCI_SEQ_STATUS_SLAVE
:
726 dprintf_midi(stddeb
, "MIDI_mciStatus // MCI_SEQ_STATUS_SLAVE !\n");
727 lpParms
->dwReturn
= 0;
729 case MCI_SEQ_STATUS_OFFSET
:
730 dprintf_midi(stddeb
, "MIDI_mciStatus // MCI_SEQ_STATUS_OFFSET !\n");
731 lpParms
->dwReturn
= 0;
733 case MCI_SEQ_STATUS_PORT
:
734 dprintf_midi(stddeb
, "MIDI_mciStatus // MCI_SEQ_STATUS_PORT !\n");
735 lpParms
->dwReturn
= 0;
737 case MCI_SEQ_STATUS_TEMPO
:
738 dprintf_midi(stddeb
, "MIDI_mciStatus // MCI_SEQ_STATUS_TEMPO !\n");
739 lpParms
->dwReturn
= 0;
742 dprintf_midi(stddeb
, "MIDI_mciStatus // unknowm command %08lX !\n", lpParms
->dwItem
);
743 return MCIERR_UNRECOGNIZED_COMMAND
;
746 if (dwFlags
& MCI_NOTIFY
) {
747 dprintf_midi(stddeb
, "MIDI_mciStatus // MCI_NOTIFY_SUCCESSFUL %08lX !\n", lpParms
->dwCallback
);
748 mciDriverNotify((HWND16
)LOWORD(lpParms
->dwCallback
),
749 MCIMidiDev
[index
].wNotifyDeviceID
, MCI_NOTIFY_SUCCESSFUL
);
753 return MCIERR_INTERNAL
;
757 /**************************************************************************
758 * MIDI_mciGetDevCaps [internal]
760 static DWORD
MIDI_mciGetDevCaps(UINT16 wDevID
, DWORD dwFlags
,
761 LPMCI_GETDEVCAPS_PARMS lpParms
)
763 #if defined(linux) || defined(__FreeBSD__)
764 dprintf_midi(stddeb
, "MIDI_mciGetDevCaps(%04X, %08lX, %p);\n", wDevID
, dwFlags
, lpParms
);
765 if (lpParms
== NULL
) return MCIERR_INTERNAL
;
766 if (dwFlags
& MCI_GETDEVCAPS_ITEM
) {
767 switch(lpParms
->dwItem
) {
768 case MCI_GETDEVCAPS_CAN_RECORD
:
769 lpParms
->dwReturn
= TRUE
;
771 case MCI_GETDEVCAPS_HAS_AUDIO
:
772 lpParms
->dwReturn
= TRUE
;
774 case MCI_GETDEVCAPS_HAS_VIDEO
:
775 lpParms
->dwReturn
= FALSE
;
777 case MCI_GETDEVCAPS_DEVICE_TYPE
:
778 lpParms
->dwReturn
= MCI_DEVTYPE_SEQUENCER
;
780 case MCI_GETDEVCAPS_USES_FILES
:
781 lpParms
->dwReturn
= TRUE
;
783 case MCI_GETDEVCAPS_COMPOUND_DEVICE
:
784 lpParms
->dwReturn
= TRUE
;
786 case MCI_GETDEVCAPS_CAN_EJECT
:
787 lpParms
->dwReturn
= FALSE
;
789 case MCI_GETDEVCAPS_CAN_PLAY
:
790 lpParms
->dwReturn
= TRUE
;
792 case MCI_GETDEVCAPS_CAN_SAVE
:
793 lpParms
->dwReturn
= FALSE
;
796 return MCIERR_UNRECOGNIZED_COMMAND
;
801 return MCIERR_INTERNAL
;
805 /**************************************************************************
806 * MIDI_mciInfo [internal]
808 static DWORD
MIDI_mciInfo(UINT16 wDevID
, DWORD dwFlags
, LPMCI_INFO_PARMS lpParms
)
810 #if defined(linux) || defined(__FreeBSD__)
811 dprintf_midi(stddeb
, "MIDI_mciInfo(%04X, %08lX, %p);\n", wDevID
, dwFlags
, lpParms
);
812 if (lpParms
== NULL
) return MCIERR_INTERNAL
;
813 lpParms
->lpstrReturn
= NULL
;
815 case MCI_INFO_PRODUCT
:
816 lpParms
->lpstrReturn
= "Linux Sound System 0.5";
819 lpParms
->lpstrReturn
= "FileName";
822 return MCIERR_UNRECOGNIZED_COMMAND
;
824 if (lpParms
->lpstrReturn
!= NULL
)
825 lpParms
->dwRetSize
= strlen(lpParms
->lpstrReturn
);
827 lpParms
->dwRetSize
= 0;
830 return MCIERR_INTERNAL
;
835 /*-----------------------------------------------------------------------*/
838 /**************************************************************************
839 * midGetDevCaps [internal]
841 static DWORD
midGetDevCaps(WORD wDevID
, LPMIDIINCAPS lpCaps
, DWORD dwSize
)
843 dprintf_midi(stddeb
, "midGetDevCaps(%04X, %p, %08lX);\n", wDevID
, lpCaps
, dwSize
);
844 return MMSYSERR_NOTENABLED
;
847 /**************************************************************************
850 static DWORD
midOpen(WORD wDevID
, LPMIDIOPENDESC lpDesc
, DWORD dwFlags
)
852 #if defined(linux) || defined(__FreeBSD__)
853 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
856 "midOpen(%04X, %p, %08lX);\n", wDevID
, lpDesc
, dwFlags
);
857 if (lpDesc
== NULL
) {
858 dprintf_midi(stddeb
,"Linux 'midOpen' // Invalid Parameter !\n");
859 return MMSYSERR_INVALPARAM
;
861 if (index
>= MAX_MIDIINDRV
) {
862 dprintf_midi(stddeb
,"Linux 'midOpen' // MAX_MIDIINDRV reached !\n");
863 return MMSYSERR_ALLOCATED
;
865 MidiInDev
[index
].unixdev
= 0;
866 midi
= open (MIDI_DEV
, O_RDONLY
, 0);
868 dprintf_midi(stddeb
,"Linux 'midOpen' // can't open !\n");
869 return MMSYSERR_NOTENABLED
;
871 MidiInDev
[index
].wFlags
= HIWORD(dwFlags
& CALLBACK_TYPEMASK
);
872 switch(MidiInDev
[index
].wFlags
) {
874 dprintf_midi(stddeb
,"Linux 'midOpen' // CALLBACK_NULL !\n");
878 "Linux 'midOpen' // CALLBACK_WINDOW !\n");
882 "Linux 'midOpen' // CALLBACK_TASK !\n");
886 "Linux 'midOpen' // CALLBACK_FUNCTION !\n");
889 MidiInDev
[index
].lpQueueHdr
= NULL
;
890 MidiInDev
[index
].unixdev
= midi
;
891 MidiInDev
[index
].dwTotalPlayed
= 0;
892 MidiInDev
[index
].bufsize
= 0x3FFF;
893 if (MIDI_NotifyClient(wDevID
, MIM_OPEN
, 0L, 0L) != MMSYSERR_NOERROR
) {
894 dprintf_midi(stddeb
,"Linux 'midOpen' // can't notify client !\n");
895 return MMSYSERR_INVALPARAM
;
897 return MMSYSERR_NOERROR
;
899 return MMSYSERR_NOTENABLED
;
903 /**************************************************************************
904 * midClose [internal]
906 static DWORD
midClose(WORD wDevID
)
908 #if defined(linux) || defined(__FreeBSD__)
909 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
910 dprintf_midi(stddeb
, "midClose(%04X);\n", wDevID
);
911 if (MidiInDev
[index
].unixdev
== 0) {
912 dprintf_midi(stddeb
,"Linux 'midClose' // can't close !\n");
913 return MMSYSERR_NOTENABLED
;
915 close(MidiInDev
[index
].unixdev
);
916 MidiInDev
[index
].unixdev
= 0;
917 MidiInDev
[index
].bufsize
= 0;
918 if (MIDI_NotifyClient(wDevID
, MIM_CLOSE
, 0L, 0L) != MMSYSERR_NOERROR
) {
919 dprintf_midi(stddeb
,"Linux 'midClose' // can't notify client !\n");
920 return MMSYSERR_INVALPARAM
;
922 return MMSYSERR_NOERROR
;
924 return MMSYSERR_NOTENABLED
;
928 /**************************************************************************
929 * midAddBuffer [internal]
931 static DWORD
midAddBuffer(WORD wDevID
, LPMIDIHDR lpMidiHdr
, DWORD dwSize
)
933 dprintf_midi(stddeb
, "midAddBuffer(%04X, %p, %08lX);\n", wDevID
, lpMidiHdr
, dwSize
);
934 return MMSYSERR_NOTENABLED
;
937 /**************************************************************************
938 * midPrepare [internal]
940 static DWORD
midPrepare(WORD wDevID
, LPMIDIHDR lpMidiHdr
, DWORD dwSize
)
942 dprintf_midi(stddeb
, "midPrepare(%04X, %p, %08lX);\n", wDevID
, lpMidiHdr
, dwSize
);
943 return MMSYSERR_NOTENABLED
;
946 /**************************************************************************
947 * midUnprepare [internal]
949 static DWORD
midUnprepare(WORD wDevID
, LPMIDIHDR lpMidiHdr
, DWORD dwSize
)
951 dprintf_midi(stddeb
, "midUnprepare(%04X, %p, %08lX);\n", wDevID
, lpMidiHdr
, dwSize
);
952 return MMSYSERR_NOTENABLED
;
955 /**************************************************************************
956 * midReset [internal]
958 static DWORD
midReset(WORD wDevID
)
960 dprintf_midi(stddeb
, "midReset(%04X);\n", wDevID
);
961 return MMSYSERR_NOTENABLED
;
965 /**************************************************************************
966 * midStart [internal]
968 static DWORD
midStart(WORD wDevID
)
970 dprintf_midi(stddeb
, "midStart(%04X);\n", wDevID
);
971 return MMSYSERR_NOTENABLED
;
975 /**************************************************************************
978 static DWORD
midStop(WORD wDevID
)
980 dprintf_midi(stddeb
, "midStop(%04X);\n", wDevID
);
981 return MMSYSERR_NOTENABLED
;
985 /**************************************************************************
986 * midMessage [sample driver]
988 DWORD
midMessage(WORD wDevID
, WORD wMsg
, DWORD dwUser
,
989 DWORD dwParam1
, DWORD dwParam2
)
991 dprintf_midi(stddeb
, "midMessage(%04X, %04X, %08lX, %08lX, %08lX);\n",
992 wDevID
, wMsg
, dwUser
, dwParam1
, dwParam2
);
995 return midOpen(wDevID
, (LPMIDIOPENDESC
)PTR_SEG_TO_LIN(dwParam1
), dwParam2
);
997 return midClose(wDevID
);
999 return midAddBuffer(wDevID
, (LPMIDIHDR
)PTR_SEG_TO_LIN(dwParam1
), dwParam2
);
1001 return midPrepare(wDevID
, (LPMIDIHDR
)PTR_SEG_TO_LIN(dwParam1
), dwParam2
);
1002 case MIDM_UNPREPARE
:
1003 return midUnprepare(wDevID
, (LPMIDIHDR
)PTR_SEG_TO_LIN(dwParam1
), dwParam2
);
1004 case MIDM_GETDEVCAPS
:
1005 return midGetDevCaps(wDevID
, (LPMIDIINCAPS
)PTR_SEG_TO_LIN(dwParam1
), dwParam2
);
1006 case MIDM_GETNUMDEVS
:
1009 return midReset(wDevID
);
1011 return midStart(wDevID
);
1013 return midStop(wDevID
);
1015 return MMSYSERR_NOTSUPPORTED
;
1020 /*-----------------------------------------------------------------------*/
1023 /**************************************************************************
1024 * modGetDevCaps [internal]
1026 static DWORD
modGetDevCaps(WORD wDevID
, LPMIDIOUTCAPS lpCaps
, DWORD dwSize
)
1028 dprintf_midi(stddeb
, "modGetDevCaps(%04X, %p, %08lX);\n", wDevID
, lpCaps
, dwSize
);
1029 return MMSYSERR_NOTENABLED
;
1033 /**************************************************************************
1034 * modOpen [internal]
1036 static DWORD
modOpen(WORD wDevID
, LPMIDIOPENDESC lpDesc
, DWORD dwFlags
)
1038 #if defined(linux) || defined(__FreeBSD__)
1039 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
1041 dprintf_midi(stddeb
,
1042 "modOpen(%04X, %p, %08lX);\n", wDevID
, lpDesc
, dwFlags
);
1043 if (lpDesc
== NULL
) {
1044 dprintf_midi(stddeb
,"Linux 'modOpen' // Invalid Parameter !\n");
1045 return MMSYSERR_INVALPARAM
;
1047 if (index
>= MAX_MIDIOUTDRV
) {
1048 dprintf_midi(stddeb
,"Linux 'modOpen' // MAX_MIDIOUTDRV reached !\n");
1049 return MMSYSERR_ALLOCATED
;
1051 MidiOutDev
[index
].unixdev
= 0;
1052 midi
= open (MIDI_DEV
, O_WRONLY
, 0);
1054 dprintf_midi(stddeb
,"Linux 'modOpen' // can't open !\n");
1055 return MMSYSERR_NOTENABLED
;
1057 MidiOutDev
[index
].wFlags
= HIWORD(dwFlags
& CALLBACK_TYPEMASK
);
1058 switch(MidiOutDev
[index
].wFlags
) {
1060 dprintf_midi(stddeb
,"Linux 'modOpen' // CALLBACK_NULL !\n");
1063 dprintf_midi(stddeb
,
1064 "Linux 'modOpen' // CALLBACK_WINDOW !\n");
1067 dprintf_midi(stddeb
,
1068 "Linux 'modOpen' // CALLBACK_TASK !\n");
1071 dprintf_midi(stddeb
,
1072 "Linux 'modOpen' // CALLBACK_FUNCTION !\n");
1075 MidiOutDev
[index
].lpQueueHdr
= NULL
;
1076 MidiOutDev
[index
].unixdev
= midi
;
1077 MidiOutDev
[index
].dwTotalPlayed
= 0;
1078 MidiOutDev
[index
].bufsize
= 0x3FFF;
1079 if (MIDI_NotifyClient(wDevID
, MOM_OPEN
, 0L, 0L) != MMSYSERR_NOERROR
) {
1080 dprintf_midi(stddeb
,"Linux 'modOpen' // can't notify client !\n");
1081 return MMSYSERR_INVALPARAM
;
1083 dprintf_midi(stddeb
,
1084 "Linux 'modOpen' // Succesful unixdev=%d !\n", midi
);
1085 return MMSYSERR_NOERROR
;
1087 return MMSYSERR_NOTENABLED
;
1092 /**************************************************************************
1093 * modClose [internal]
1095 static DWORD
modClose(WORD wDevID
)
1097 #if defined(linux) || defined(__FreeBSD__)
1098 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
1099 dprintf_midi(stddeb
, "modClose(%04X);\n", wDevID
);
1100 if (MidiOutDev
[index
].unixdev
== 0) {
1101 dprintf_midi(stddeb
,"Linux 'modClose' // can't close !\n");
1102 return MMSYSERR_NOTENABLED
;
1104 close(MidiOutDev
[index
].unixdev
);
1105 MidiOutDev
[index
].unixdev
= 0;
1106 MidiOutDev
[index
].bufsize
= 0;
1107 if (MIDI_NotifyClient(wDevID
, MOM_CLOSE
, 0L, 0L) != MMSYSERR_NOERROR
) {
1108 dprintf_midi(stddeb
,"Linux 'modClose' // can't notify client !\n");
1109 return MMSYSERR_INVALPARAM
;
1111 return MMSYSERR_NOERROR
;
1113 return MMSYSERR_NOTENABLED
;
1117 /**************************************************************************
1118 * modData [internal]
1120 static DWORD
modData(WORD wDevID
, DWORD dwParam
)
1122 #if defined(linux) || defined(__FreeBSD__)
1123 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
1125 dprintf_midi(stddeb
,
1126 "modData(%04X, %08lX);\n", wDevID
, dwParam
);
1127 if (MidiOutDev
[index
].unixdev
== 0) {
1128 dprintf_midi(stddeb
,"Linux 'modData' // can't play !\n");
1129 return MIDIERR_NODEVICE
;
1131 event
= LOWORD(dwParam
);
1132 if (write (MidiOutDev
[index
].unixdev
,
1133 &event
, sizeof(WORD
)) != sizeof(WORD
)) {
1134 dprintf_midi(stddeb
,
1135 "modData() // error writting unixdev !\n");
1137 return MMSYSERR_NOTENABLED
;
1139 return MMSYSERR_NOTENABLED
;
1143 /**************************************************************************
1144 * modLongData [internal]
1146 static DWORD
modLongData(WORD wDevID
, LPMIDIHDR lpMidiHdr
, DWORD dwSize
)
1148 #if defined(linux) || defined(__FreeBSD__)
1149 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
1152 dprintf_midi(stddeb
,
1153 "modLongData(%04X, %p, %08lX);\n", wDevID
, lpMidiHdr
, dwSize
);
1154 if (MidiOutDev
[index
].unixdev
== 0) {
1155 dprintf_midi(stddeb
,"Linux 'modLongData' // can't play !\n");
1156 return MIDIERR_NODEVICE
;
1158 if (lpMidiHdr
->lpData
== NULL
) return MIDIERR_UNPREPARED
;
1159 if (!(lpMidiHdr
->dwFlags
& MHDR_PREPARED
)) return MIDIERR_UNPREPARED
;
1160 if (lpMidiHdr
->dwFlags
& MHDR_INQUEUE
) return MIDIERR_STILLPLAYING
;
1161 lpMidiHdr
->dwFlags
&= ~MHDR_DONE
;
1162 lpMidiHdr
->dwFlags
|= MHDR_INQUEUE
;
1163 dprintf_midi(stddeb
,
1164 "modLongData() // dwBytesRecorded %lu !\n", lpMidiHdr
->dwBytesRecorded
);
1166 count = write (MidiOutDev[index].unixdev,
1167 lpMidiHdr->lpData, lpMidiHdr->dwBytesRecorded);
1169 ptr
= (LPWORD
)lpMidiHdr
->lpData
;
1170 for (count
= 0; count
< lpMidiHdr
->dwBytesRecorded
; count
++) {
1171 if (write (MidiOutDev
[index
].unixdev
, ptr
,
1172 sizeof(WORD
)) != sizeof(WORD
)) break;
1175 if (count
!= lpMidiHdr
->dwBytesRecorded
) {
1176 dprintf_midi(stddeb
,
1177 "modLongData() // error writting unixdev #%d ! (%d != %ld)\n",
1178 MidiOutDev
[index
].unixdev
, count
, lpMidiHdr
->dwBytesRecorded
);
1179 return MMSYSERR_NOTENABLED
;
1181 lpMidiHdr
->dwFlags
&= ~MHDR_INQUEUE
;
1182 lpMidiHdr
->dwFlags
|= MHDR_DONE
;
1183 if (MIDI_NotifyClient(wDevID
, MOM_DONE
, 0L, 0L) != MMSYSERR_NOERROR
) {
1184 dprintf_midi(stddeb
,"Linux 'modLongData' // can't notify client !\n");
1185 return MMSYSERR_INVALPARAM
;
1187 return MMSYSERR_NOERROR
;
1189 return MMSYSERR_NOTENABLED
;
1193 /**************************************************************************
1194 * modPrepare [internal]
1196 static DWORD
modPrepare(WORD wDevID
, LPMIDIHDR lpMidiHdr
, DWORD dwSize
)
1198 #if defined(linux) || defined(__FreeBSD__)
1199 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
1200 dprintf_midi(stddeb
,
1201 "modPrepare(%04X, %p, %08lX);\n", wDevID
, lpMidiHdr
, dwSize
);
1202 if (MidiOutDev
[index
].unixdev
== 0) {
1203 dprintf_midi(stddeb
,"Linux 'modPrepare' // can't prepare !\n");
1204 return MMSYSERR_NOTENABLED
;
1206 if (MidiOutDev
[index
].lpQueueHdr
!= NULL
) {
1207 dprintf_midi(stddeb
,"Linux 'modPrepare' // already prepare !\n");
1208 return MMSYSERR_NOTENABLED
;
1210 MidiOutDev
[index
].dwTotalPlayed
= 0;
1211 MidiOutDev
[index
].lpQueueHdr
= lpMidiHdr
;
1212 if (lpMidiHdr
->dwFlags
& MHDR_INQUEUE
) return MIDIERR_STILLPLAYING
;
1213 lpMidiHdr
->dwFlags
|= MHDR_PREPARED
;
1214 lpMidiHdr
->dwFlags
&= ~MHDR_DONE
;
1215 return MMSYSERR_NOERROR
;
1217 return MMSYSERR_NOTENABLED
;
1221 /**************************************************************************
1222 * modUnprepare [internal]
1224 static DWORD
modUnprepare(WORD wDevID
, LPMIDIHDR lpMidiHdr
, DWORD dwSize
)
1226 #if defined(linux) || defined(__FreeBSD__)
1227 int index
= MMSYSTEM_DevIDToIndex(wDevID
);
1228 dprintf_midi(stddeb
,
1229 "modUnprepare(%04X, %p, %08lX);\n", wDevID
, lpMidiHdr
, dwSize
);
1230 if (MidiOutDev
[index
].unixdev
== 0) {
1231 dprintf_midi(stddeb
,"Linux 'modUnprepare' // can't unprepare !\n");
1232 return MMSYSERR_NOTENABLED
;
1234 return MMSYSERR_NOERROR
;
1236 return MMSYSERR_NOTENABLED
;
1240 /**************************************************************************
1241 * modReset [internal]
1243 static DWORD
modReset(WORD wDevID
)
1245 dprintf_midi(stddeb
, "modReset(%04X);\n", wDevID
);
1246 return MMSYSERR_NOTENABLED
;
1250 /**************************************************************************
1251 * modMessage [sample driver]
1253 DWORD
modMessage(WORD wDevID
, WORD wMsg
, DWORD dwUser
,
1254 DWORD dwParam1
, DWORD dwParam2
)
1256 dprintf_midi(stddeb
, "modMessage(%04X, %04X, %08lX, %08lX, %08lX);\n",
1257 wDevID
, wMsg
, dwUser
, dwParam1
, dwParam2
);
1260 return modOpen(wDevID
, (LPMIDIOPENDESC
)PTR_SEG_TO_LIN(dwParam1
), dwParam2
);
1262 return modClose(wDevID
);
1264 return modData(wDevID
, dwParam1
);
1266 return modLongData(wDevID
, (LPMIDIHDR
)PTR_SEG_TO_LIN(dwParam1
), dwParam2
);
1268 return modPrepare(wDevID
, (LPMIDIHDR
)PTR_SEG_TO_LIN(dwParam1
), dwParam2
);
1269 case MODM_UNPREPARE
:
1270 return modUnprepare(wDevID
, (LPMIDIHDR
)PTR_SEG_TO_LIN(dwParam1
), dwParam2
);
1271 case MODM_GETDEVCAPS
:
1272 return modGetDevCaps(wDevID
, (LPMIDIOUTCAPS
)PTR_SEG_TO_LIN(dwParam1
), dwParam2
);
1273 case MODM_GETNUMDEVS
:
1275 case MODM_GETVOLUME
:
1277 case MODM_SETVOLUME
:
1280 return modReset(wDevID
);
1282 return MMSYSERR_NOTSUPPORTED
;
1286 /**************************************************************************
1287 * MIDI_DriverProc [sample driver]
1289 LONG
MIDI_DriverProc(DWORD dwDevID
, HDRVR16 hDriv
, WORD wMsg
,
1290 DWORD dwParam1
, DWORD dwParam2
)
1292 #if defined(linux) || defined(__FreeBSD__)
1306 case DRV_QUERYCONFIGURE
:
1309 MessageBox16(0, "Sample Midi Linux Driver !",
1310 "MMLinux Driver", MB_OK
);
1313 return DRVCNF_RESTART
;
1315 return DRVCNF_RESTART
;
1316 case MCI_OPEN_DRIVER
:
1318 return MIDI_mciOpen(dwDevID
, dwParam1
, (LPMCI_OPEN_PARMS
)PTR_SEG_TO_LIN(dwParam2
));
1319 case MCI_CLOSE_DRIVER
:
1321 return MIDI_mciClose(dwDevID
, dwParam1
, (LPMCI_GENERIC_PARMS
)PTR_SEG_TO_LIN(dwParam2
));
1323 return MIDI_mciPlay(dwDevID
, dwParam1
, (LPMCI_PLAY_PARMS
)PTR_SEG_TO_LIN(dwParam2
));
1325 return MIDI_mciRecord(dwDevID
, dwParam1
, (LPMCI_RECORD_PARMS
)PTR_SEG_TO_LIN(dwParam2
));
1327 return MIDI_mciStop(dwDevID
, dwParam1
, (LPMCI_GENERIC_PARMS
)PTR_SEG_TO_LIN(dwParam2
));
1329 return MIDI_mciSet(dwDevID
, dwParam1
, (LPMCI_SET_PARMS
)PTR_SEG_TO_LIN(dwParam2
));
1331 return MIDI_mciPause(dwDevID
, dwParam1
, (LPMCI_GENERIC_PARMS
)PTR_SEG_TO_LIN(dwParam2
));
1333 return MIDI_mciResume(dwDevID
, dwParam1
, (LPMCI_GENERIC_PARMS
)PTR_SEG_TO_LIN(dwParam2
));
1335 return MIDI_mciStatus(dwDevID
, dwParam1
, (LPMCI_STATUS_PARMS
)PTR_SEG_TO_LIN(dwParam2
));
1336 case MCI_GETDEVCAPS
:
1337 return MIDI_mciGetDevCaps(dwDevID
, dwParam1
, (LPMCI_GETDEVCAPS_PARMS
)PTR_SEG_TO_LIN(dwParam2
));
1339 return MIDI_mciInfo(dwDevID
, dwParam1
, (LPMCI_INFO_PARMS
)PTR_SEG_TO_LIN(dwParam2
));
1341 return DefDriverProc(dwDevID
, hDriv
, wMsg
, dwParam1
, dwParam2
);
1344 return MMSYSERR_NOTENABLED
;
1349 /*-----------------------------------------------------------------------*/