aboutsummaryrefslogtreecommitdiffstats
path: root/sound/oss/emu10k1/cardmi.c
diff options
context:
space:
mode:
Diffstat (limited to 'sound/oss/emu10k1/cardmi.c')
-rw-r--r--sound/oss/emu10k1/cardmi.c832
1 files changed, 832 insertions, 0 deletions
diff --git a/sound/oss/emu10k1/cardmi.c b/sound/oss/emu10k1/cardmi.c
new file mode 100644
index 000000000000..0545814cc67d
--- /dev/null
+++ b/sound/oss/emu10k1/cardmi.c
@@ -0,0 +1,832 @@
1/*
2 **********************************************************************
3 * sblive_mi.c - MIDI UART input HAL for emu10k1 driver
4 * Copyright 1999, 2000 Creative Labs, Inc.
5 *
6 **********************************************************************
7 *
8 * Date Author Summary of changes
9 * ---- ------ ------------------
10 * October 20, 1999 Bertrand Lee base code release
11 * November 2, 1999 Alan Cox clean up
12 *
13 **********************************************************************
14 *
15 * This program is free software; you can redistribute it and/or
16 * modify it under the terms of the GNU General Public License as
17 * published by the Free Software Foundation; either version 2 of
18 * the License, or (at your option) any later version.
19 *
20 * This program is distributed in the hope that it will be useful,
21 * but WITHOUT ANY WARRANTY; without even the implied warranty of
22 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
23 * GNU General Public License for more details.
24 *
25 * You should have received a copy of the GNU General Public
26 * License along with this program; if not, write to the Free
27 * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139,
28 * USA.
29 *
30 **********************************************************************
31 */
32
33#include <linux/slab.h>
34#include <linux/jiffies.h>
35
36#include "hwaccess.h"
37#include "8010.h"
38#include "cardmi.h"
39#include "irqmgr.h"
40
41
42static int emu10k1_mpuin_callback(struct emu10k1_mpuin *card_mpuin, u32 msg, unsigned long data, u32 bytesvalid);
43
44static int sblive_miStateInit(struct emu10k1_mpuin *);
45static int sblive_miStateEntry(struct emu10k1_mpuin *, u8);
46static int sblive_miStateParse(struct emu10k1_mpuin *, u8);
47static int sblive_miState3Byte(struct emu10k1_mpuin *, u8);
48static int sblive_miState3ByteKey(struct emu10k1_mpuin *, u8);
49static int sblive_miState3ByteVel(struct emu10k1_mpuin *, u8);
50static int sblive_miState2Byte(struct emu10k1_mpuin *, u8);
51static int sblive_miState2ByteKey(struct emu10k1_mpuin *, u8);
52static int sblive_miStateSysCommon2(struct emu10k1_mpuin *, u8);
53static int sblive_miStateSysCommon2Key(struct emu10k1_mpuin *, u8);
54static int sblive_miStateSysCommon3(struct emu10k1_mpuin *, u8);
55static int sblive_miStateSysCommon3Key(struct emu10k1_mpuin *, u8);
56static int sblive_miStateSysCommon3Vel(struct emu10k1_mpuin *, u8);
57static int sblive_miStateSysExNorm(struct emu10k1_mpuin *, u8);
58static int sblive_miStateSysReal(struct emu10k1_mpuin *, u8);
59
60
61static struct {
62 int (*Fn) (struct emu10k1_mpuin *, u8);
63} midistatefn[] = {
64
65 {
66 sblive_miStateParse}, {
67 sblive_miState3Byte}, /* 0x8n, 0x9n, 0xAn, 0xBn, 0xEn */
68 {
69 sblive_miState3ByteKey}, /* Byte 1 */
70 {
71 sblive_miState3ByteVel}, /* Byte 2 */
72 {
73 sblive_miState2Byte}, /* 0xCn, 0xDn */
74 {
75 sblive_miState2ByteKey}, /* Byte 1 */
76 {
77 sblive_miStateSysCommon2}, /* 0xF1 , 0xF3 */
78 {
79 sblive_miStateSysCommon2Key}, /* 0xF1 , 0xF3, Byte 1 */
80 {
81 sblive_miStateSysCommon3}, /* 0xF2 */
82 {
83 sblive_miStateSysCommon3Key}, /* 0xF2 , Byte 1 */
84 {
85 sblive_miStateSysCommon3Vel}, /* 0xF2 , Byte 2 */
86 {
87 sblive_miStateSysExNorm}, /* 0xF0, 0xF7, Normal mode */
88 {
89 sblive_miStateSysReal} /* 0xF4 - 0xF6 ,0xF8 - 0xFF */
90};
91
92
93/* Installs the IRQ handler for the MPU in port */
94
95/* and initialize parameters */
96
97int emu10k1_mpuin_open(struct emu10k1_card *card, struct midi_openinfo *openinfo)
98{
99 struct emu10k1_mpuin *card_mpuin = card->mpuin;
100
101 DPF(2, "emu10k1_mpuin_open\n");
102
103 if (!(card_mpuin->status & FLAGS_AVAILABLE))
104 return -1;
105
106 /* Copy open info and mark channel as in use */
107 card_mpuin->openinfo = *openinfo;
108 card_mpuin->status &= ~FLAGS_AVAILABLE; /* clear */
109 card_mpuin->status |= FLAGS_READY; /* set */
110 card_mpuin->status &= ~FLAGS_MIDM_STARTED; /* clear */
111 card_mpuin->firstmidiq = NULL;
112 card_mpuin->lastmidiq = NULL;
113 card_mpuin->qhead = 0;
114 card_mpuin->qtail = 0;
115
116 sblive_miStateInit(card_mpuin);
117
118 emu10k1_mpu_reset(card);
119 emu10k1_mpu_acquire(card);
120
121 return 0;
122}
123
124int emu10k1_mpuin_close(struct emu10k1_card *card)
125{
126 struct emu10k1_mpuin *card_mpuin = card->mpuin;
127
128 DPF(2, "emu10k1_mpuin_close()\n");
129
130 /* Check if there are pending input SysEx buffers */
131 if (card_mpuin->firstmidiq != NULL) {
132 ERROR();
133 return -1;
134 }
135
136 /* Disable RX interrupt */
137 emu10k1_irq_disable(card, card->is_audigy ? A_INTE_MIDIRXENABLE : INTE_MIDIRXENABLE);
138
139 emu10k1_mpu_release(card);
140
141 card_mpuin->status |= FLAGS_AVAILABLE; /* set */
142 card_mpuin->status &= ~FLAGS_MIDM_STARTED; /* clear */
143
144 return 0;
145}
146
147/* Adds MIDI buffer to local queue list */
148
149int emu10k1_mpuin_add_buffer(struct emu10k1_mpuin *card_mpuin, struct midi_hdr *midihdr)
150{
151 struct midi_queue *midiq;
152 unsigned long flags;
153
154 DPF(2, "emu10k1_mpuin_add_buffer()\n");
155
156 /* Update MIDI buffer flags */
157 midihdr->flags |= MIDIBUF_INQUEUE; /* set */
158 midihdr->flags &= ~MIDIBUF_DONE; /* clear */
159
160 if ((midiq = (struct midi_queue *) kmalloc(sizeof(struct midi_queue), GFP_ATOMIC)) == NULL) {
161 /* Message lost */
162 return -1;
163 }
164
165 midiq->next = NULL;
166 midiq->qtype = 1;
167 midiq->length = midihdr->bufferlength;
168 midiq->sizeLeft = midihdr->bufferlength;
169 midiq->midibyte = midihdr->data;
170 midiq->refdata = (unsigned long) midihdr;
171
172 spin_lock_irqsave(&card_mpuin->lock, flags);
173
174 if (card_mpuin->firstmidiq == NULL) {
175 card_mpuin->firstmidiq = midiq;
176 card_mpuin->lastmidiq = midiq;
177 } else {
178 (card_mpuin->lastmidiq)->next = midiq;
179 card_mpuin->lastmidiq = midiq;
180 }
181
182 spin_unlock_irqrestore(&card_mpuin->lock, flags);
183
184 return 0;
185}
186
187/* First set the Time Stamp if MIDI IN has not started. */
188
189/* Then enable RX Irq. */
190
191int emu10k1_mpuin_start(struct emu10k1_card *card)
192{
193 struct emu10k1_mpuin *card_mpuin = card->mpuin;
194 u8 dummy;
195
196 DPF(2, "emu10k1_mpuin_start()\n");
197
198 /* Set timestamp if not set */
199 if (card_mpuin->status & FLAGS_MIDM_STARTED) {
200 DPF(2, "Time Stamp not changed\n");
201 } else {
202 while (!emu10k1_mpu_read_data(card, &dummy));
203
204 card_mpuin->status |= FLAGS_MIDM_STARTED; /* set */
205
206 /* Set new time stamp */
207 card_mpuin->timestart = (jiffies * 1000) / HZ;
208 DPD(2, "New Time Stamp = %d\n", card_mpuin->timestart);
209
210 card_mpuin->qhead = 0;
211 card_mpuin->qtail = 0;
212
213 emu10k1_irq_enable(card, card->is_audigy ? A_INTE_MIDIRXENABLE : INTE_MIDIRXENABLE);
214 }
215
216 return 0;
217}
218
219/* Disable the RX Irq. If a partial recorded buffer */
220
221/* exist, send it up to IMIDI level. */
222
223int emu10k1_mpuin_stop(struct emu10k1_card *card)
224{
225 struct emu10k1_mpuin *card_mpuin = card->mpuin;
226 struct midi_queue *midiq;
227 unsigned long flags;
228
229 DPF(2, "emu10k1_mpuin_stop()\n");
230
231 emu10k1_irq_disable(card, card->is_audigy ? A_INTE_MIDIRXENABLE : INTE_MIDIRXENABLE);
232
233 card_mpuin->status &= ~FLAGS_MIDM_STARTED; /* clear */
234
235 if (card_mpuin->firstmidiq) {
236 spin_lock_irqsave(&card_mpuin->lock, flags);
237
238 midiq = card_mpuin->firstmidiq;
239 if (midiq != NULL) {
240 if (midiq->sizeLeft == midiq->length)
241 midiq = NULL;
242 else {
243 card_mpuin->firstmidiq = midiq->next;
244 if (card_mpuin->firstmidiq == NULL)
245 card_mpuin->lastmidiq = NULL;
246 }
247 }
248
249 spin_unlock_irqrestore(&card_mpuin->lock, flags);
250
251 if (midiq) {
252 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INLONGERROR, (unsigned long) midiq, 0);
253 kfree(midiq);
254 }
255 }
256
257 return 0;
258}
259
260/* Disable the RX Irq. If any buffer */
261
262/* exist, send it up to IMIDI level. */
263int emu10k1_mpuin_reset(struct emu10k1_card *card)
264{
265 struct emu10k1_mpuin *card_mpuin = card->mpuin;
266 struct midi_queue *midiq;
267
268 DPF(2, "emu10k1_mpuin_reset()\n");
269
270 emu10k1_irq_disable(card, card->is_audigy ? A_INTE_MIDIRXENABLE : INTE_MIDIRXENABLE);
271
272 while (card_mpuin->firstmidiq) {
273 midiq = card_mpuin->firstmidiq;
274 card_mpuin->firstmidiq = midiq->next;
275
276 if (midiq->sizeLeft == midiq->length)
277 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INLONGDATA, (unsigned long) midiq, 0);
278 else
279 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INLONGERROR, (unsigned long) midiq, 0);
280
281 kfree(midiq);
282 }
283
284 card_mpuin->lastmidiq = NULL;
285 card_mpuin->status &= ~FLAGS_MIDM_STARTED;
286
287 return 0;
288}
289
290/* Passes the message with the data back to the client */
291
292/* via IRQ & DPC callbacks to Ring 3 */
293static int emu10k1_mpuin_callback(struct emu10k1_mpuin *card_mpuin, u32 msg, unsigned long data, u32 bytesvalid)
294{
295 unsigned long timein;
296 struct midi_queue *midiq;
297 unsigned long callback_msg[3];
298 struct midi_hdr *midihdr;
299
300 /* Called during ISR. The data & code touched are:
301 * 1. card_mpuin
302 * 2. The function to be called
303 */
304
305 timein = card_mpuin->timein;
306 if (card_mpuin->timestart <= timein)
307 callback_msg[0] = timein - card_mpuin->timestart;
308 else
309 callback_msg[0] = (~0x0L - card_mpuin->timestart) + timein;
310
311 if (msg == ICARDMIDI_INDATA || msg == ICARDMIDI_INDATAERROR) {
312 callback_msg[1] = data;
313 callback_msg[2] = bytesvalid;
314 DPD(2, "emu10k1_mpuin_callback: midimsg = %#lx\n", data);
315 } else {
316 midiq = (struct midi_queue *) data;
317 midihdr = (struct midi_hdr *) midiq->refdata;
318
319 callback_msg[1] = midiq->length - midiq->sizeLeft;
320 callback_msg[2] = midiq->refdata;
321 midihdr->flags &= ~MIDIBUF_INQUEUE;
322 midihdr->flags |= MIDIBUF_DONE;
323
324 midihdr->bytesrecorded = midiq->length - midiq->sizeLeft;
325 }
326
327 /* Notify client that Sysex buffer has been sent */
328 emu10k1_midi_callback(msg, card_mpuin->openinfo.refdata, callback_msg);
329
330 return 0;
331}
332
333void emu10k1_mpuin_bh(unsigned long refdata)
334{
335 u8 data;
336 unsigned idx;
337 struct emu10k1_mpuin *card_mpuin = (struct emu10k1_mpuin *) refdata;
338 unsigned long flags;
339
340 while (card_mpuin->qhead != card_mpuin->qtail) {
341 spin_lock_irqsave(&card_mpuin->lock, flags);
342 idx = card_mpuin->qhead;
343 data = card_mpuin->midiq[idx].data;
344 card_mpuin->timein = card_mpuin->midiq[idx].timein;
345 idx = (idx + 1) % MIDIIN_MAX_BUFFER_SIZE;
346 card_mpuin->qhead = idx;
347 spin_unlock_irqrestore(&card_mpuin->lock, flags);
348
349 sblive_miStateEntry(card_mpuin, data);
350 }
351
352 return;
353}
354
355/* IRQ callback handler routine for the MPU in port */
356
357int emu10k1_mpuin_irqhandler(struct emu10k1_card *card)
358{
359 unsigned idx;
360 unsigned count;
361 u8 MPUIvalue;
362 struct emu10k1_mpuin *card_mpuin = card->mpuin;
363
364 /* IRQ service routine. The data and code touched are:
365 * 1. card_mpuin
366 */
367
368 count = 0;
369 idx = card_mpuin->qtail;
370
371 while (1) {
372 if (emu10k1_mpu_read_data(card, &MPUIvalue) < 0) {
373 break;
374 } else {
375 ++count;
376 card_mpuin->midiq[idx].data = MPUIvalue;
377 card_mpuin->midiq[idx].timein = (jiffies * 1000) / HZ;
378 idx = (idx + 1) % MIDIIN_MAX_BUFFER_SIZE;
379 }
380 }
381
382 if (count) {
383 card_mpuin->qtail = idx;
384
385 tasklet_hi_schedule(&card_mpuin->tasklet);
386 }
387
388 return 0;
389}
390
391/*****************************************************************************/
392
393/* Supporting functions for Midi-In Interpretation State Machine */
394
395/*****************************************************************************/
396
397/* FIXME: This should be a macro */
398static int sblive_miStateInit(struct emu10k1_mpuin *card_mpuin)
399{
400 card_mpuin->status = 0; /* For MIDI running status */
401 card_mpuin->fstatus = 0; /* For 0xFn status only */
402 card_mpuin->curstate = STIN_PARSE;
403 card_mpuin->laststate = STIN_PARSE;
404 card_mpuin->data = 0;
405 card_mpuin->timestart = 0;
406 card_mpuin->timein = 0;
407
408 return 0;
409}
410
411/* FIXME: This should be a macro */
412static int sblive_miStateEntry(struct emu10k1_mpuin *card_mpuin, u8 data)
413{
414 return midistatefn[card_mpuin->curstate].Fn(card_mpuin, data);
415}
416
417static int sblive_miStateParse(struct emu10k1_mpuin *card_mpuin, u8 data)
418{
419 switch (data & 0xf0) {
420 case 0x80:
421 case 0x90:
422 case 0xA0:
423 case 0xB0:
424 case 0xE0:
425 card_mpuin->curstate = STIN_3BYTE;
426 break;
427
428 case 0xC0:
429 case 0xD0:
430 card_mpuin->curstate = STIN_2BYTE;
431 break;
432
433 case 0xF0:
434 /* System messages do not affect the previous running status! */
435 switch (data & 0x0f) {
436 case 0x0:
437 card_mpuin->laststate = card_mpuin->curstate;
438 card_mpuin->curstate = STIN_SYS_EX_NORM;
439
440 if (card_mpuin->firstmidiq) {
441 struct midi_queue *midiq;
442
443 midiq = card_mpuin->firstmidiq;
444 *midiq->midibyte = data;
445 --midiq->sizeLeft;
446 ++midiq->midibyte;
447 }
448
449 return CTSTATUS_NEXT_BYTE;
450
451 case 0x7:
452 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATAERROR, 0xf7, 0);
453 return -1;
454
455 case 0x2:
456 card_mpuin->laststate = card_mpuin->curstate;
457 card_mpuin->curstate = STIN_SYS_COMMON_3;
458 break;
459
460 case 0x1:
461 case 0x3:
462 card_mpuin->laststate = card_mpuin->curstate;
463 card_mpuin->curstate = STIN_SYS_COMMON_2;
464 break;
465
466 default:
467 /* includes 0xF4 - 0xF6, 0xF8 - 0xFF */
468 return midistatefn[STIN_SYS_REAL].Fn(card_mpuin, data);
469 }
470
471 break;
472
473 default:
474 DPF(2, "BUG: default case hit\n");
475 return -1;
476 }
477
478 return midistatefn[card_mpuin->curstate].Fn(card_mpuin, data);
479}
480
481static int sblive_miState3Byte(struct emu10k1_mpuin *card_mpuin, u8 data)
482{
483 u8 temp = data & 0xf0;
484
485 if (temp < 0x80) {
486 return midistatefn[STIN_3BYTE_KEY].Fn(card_mpuin, data);
487 } else if (temp <= 0xe0 && temp != 0xc0 && temp != 0xd0) {
488 card_mpuin->status = data;
489 card_mpuin->curstate = STIN_3BYTE_KEY;
490
491 return CTSTATUS_NEXT_BYTE;
492 }
493
494 return midistatefn[STIN_PARSE].Fn(card_mpuin, data);
495}
496
497static int sblive_miState3ByteKey(struct emu10k1_mpuin *card_mpuin, u8 data)
498/* byte 1 */
499{
500 unsigned long tmp;
501
502 if (data > 0x7f) {
503 /* Real-time messages check */
504 if (data > 0xf7)
505 return midistatefn[STIN_SYS_REAL].Fn(card_mpuin, data);
506
507 /* Invalid data! */
508 DPF(2, "Invalid data!\n");
509
510 card_mpuin->curstate = STIN_PARSE;
511 tmp = ((unsigned long) data) << 8;
512 tmp |= (unsigned long) card_mpuin->status;
513
514 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATAERROR, tmp, 0);
515
516 return -1;
517 }
518
519 card_mpuin->data = data;
520 card_mpuin->curstate = STIN_3BYTE_VEL;
521
522 return CTSTATUS_NEXT_BYTE;
523}
524
525static int sblive_miState3ByteVel(struct emu10k1_mpuin *card_mpuin, u8 data)
526/* byte 2 */
527{
528 unsigned long tmp;
529
530 if (data > 0x7f) {
531 /* Real-time messages check */
532 if (data > 0xf7)
533 return midistatefn[STIN_SYS_REAL].Fn(card_mpuin, data);
534
535 /* Invalid data! */
536 DPF(2, "Invalid data!\n");
537
538 card_mpuin->curstate = STIN_PARSE;
539 tmp = ((unsigned long) data) << 8;
540 tmp |= card_mpuin->data;
541 tmp = tmp << 8;
542 tmp |= (unsigned long) card_mpuin->status;
543
544 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATAERROR, tmp, 0);
545
546 return -1;
547 }
548
549 card_mpuin->curstate = STIN_3BYTE;
550 tmp = (unsigned long) data;
551 tmp = tmp << 8;
552 tmp |= (unsigned long) card_mpuin->data;
553 tmp = tmp << 8;
554 tmp |= (unsigned long) card_mpuin->status;
555
556 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATA, tmp, 3);
557
558 return 0;
559}
560
561static int sblive_miState2Byte(struct emu10k1_mpuin *card_mpuin, u8 data)
562{
563 u8 temp = data & 0xf0;
564
565 if ((temp == 0xc0) || (temp == 0xd0)) {
566 card_mpuin->status = data;
567 card_mpuin->curstate = STIN_2BYTE_KEY;
568
569 return CTSTATUS_NEXT_BYTE;
570 }
571
572 if (temp < 0x80)
573 return midistatefn[STIN_2BYTE_KEY].Fn(card_mpuin, data);
574
575 return midistatefn[STIN_PARSE].Fn(card_mpuin, data);
576}
577
578static int sblive_miState2ByteKey(struct emu10k1_mpuin *card_mpuin, u8 data)
579/* byte 1 */
580{
581 unsigned long tmp;
582
583 if (data > 0x7f) {
584 /* Real-time messages check */
585 if (data > 0xf7)
586 return midistatefn[STIN_SYS_REAL].Fn(card_mpuin, data);
587
588 /* Invalid data! */
589 DPF(2, "Invalid data!\n");
590
591 card_mpuin->curstate = STIN_PARSE;
592 tmp = (unsigned long) data;
593 tmp = tmp << 8;
594 tmp |= (unsigned long) card_mpuin->status;
595
596 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATAERROR, tmp, 0);
597
598 return -1;
599 }
600
601 card_mpuin->curstate = STIN_2BYTE;
602 tmp = (unsigned long) data;
603 tmp = tmp << 8;
604 tmp |= (unsigned long) card_mpuin->status;
605
606 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATA, tmp, 2);
607
608 return 0;
609}
610
611static int sblive_miStateSysCommon2(struct emu10k1_mpuin *card_mpuin, u8 data)
612{
613 card_mpuin->fstatus = data;
614 card_mpuin->curstate = STIN_SYS_COMMON_2_KEY;
615
616 return CTSTATUS_NEXT_BYTE;
617}
618
619static int sblive_miStateSysCommon2Key(struct emu10k1_mpuin *card_mpuin, u8 data)
620/* byte 1 */
621{
622 unsigned long tmp;
623
624 if (data > 0x7f) {
625 /* Real-time messages check */
626 if (data > 0xf7)
627 return midistatefn[STIN_SYS_REAL].Fn(card_mpuin, data);
628
629 /* Invalid data! */
630 DPF(2, "Invalid data!\n");
631
632 card_mpuin->curstate = card_mpuin->laststate;
633 tmp = (unsigned long) data;
634 tmp = tmp << 8;
635 tmp |= (unsigned long) card_mpuin->fstatus;
636
637 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATAERROR, tmp, 0);
638
639 return -1;
640 }
641
642 card_mpuin->curstate = card_mpuin->laststate;
643 tmp = (unsigned long) data;
644 tmp = tmp << 8;
645 tmp |= (unsigned long) card_mpuin->fstatus;
646
647 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATA, tmp, 2);
648
649 return 0;
650}
651
652static int sblive_miStateSysCommon3(struct emu10k1_mpuin *card_mpuin, u8 data)
653{
654 card_mpuin->fstatus = data;
655 card_mpuin->curstate = STIN_SYS_COMMON_3_KEY;
656
657 return CTSTATUS_NEXT_BYTE;
658}
659
660static int sblive_miStateSysCommon3Key(struct emu10k1_mpuin *card_mpuin, u8 data)
661/* byte 1 */
662{
663 unsigned long tmp;
664
665 if (data > 0x7f) {
666 /* Real-time messages check */
667 if (data > 0xf7)
668 return midistatefn[STIN_SYS_REAL].Fn(card_mpuin, data);
669
670 /* Invalid data! */
671 DPF(2, "Invalid data!\n");
672
673 card_mpuin->curstate = card_mpuin->laststate;
674 tmp = (unsigned long) data;
675 tmp = tmp << 8;
676 tmp |= (unsigned long) card_mpuin->fstatus;
677
678 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATAERROR, tmp, 0);
679
680 return -1;
681 }
682
683 card_mpuin->data = data;
684 card_mpuin->curstate = STIN_SYS_COMMON_3_VEL;
685
686 return CTSTATUS_NEXT_BYTE;
687}
688
689static int sblive_miStateSysCommon3Vel(struct emu10k1_mpuin *card_mpuin, u8 data)
690/* byte 2 */
691{
692 unsigned long tmp;
693
694 if (data > 0x7f) {
695 /* Real-time messages check */
696 if (data > 0xf7)
697 return midistatefn[STIN_SYS_REAL].Fn(card_mpuin, data);
698
699 /* Invalid data! */
700 DPF(2, "Invalid data!\n");
701
702 card_mpuin->curstate = card_mpuin->laststate;
703 tmp = (unsigned long) data;
704 tmp = tmp << 8;
705 tmp |= (unsigned long) card_mpuin->data;
706 tmp = tmp << 8;
707 tmp |= (unsigned long) card_mpuin->fstatus;
708
709 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATAERROR, tmp, 0);
710
711 return -1;
712 }
713
714 card_mpuin->curstate = card_mpuin->laststate;
715 tmp = (unsigned long) data;
716 tmp = tmp << 8;
717 tmp |= (unsigned long) card_mpuin->data;
718 tmp = tmp << 8;
719 tmp |= (unsigned long) card_mpuin->fstatus;
720
721 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATA, tmp, 3);
722
723 return 0;
724}
725
726static int sblive_miStateSysExNorm(struct emu10k1_mpuin *card_mpuin, u8 data)
727{
728 unsigned long flags;
729
730 if ((data > 0x7f) && (data != 0xf7)) {
731 /* Real-time messages check */
732 if (data > 0xf7)
733 return midistatefn[STIN_SYS_REAL].Fn(card_mpuin, data);
734
735 /* Invalid Data! */
736 DPF(2, "Invalid data!\n");
737
738 card_mpuin->curstate = card_mpuin->laststate;
739
740 if (card_mpuin->firstmidiq) {
741 struct midi_queue *midiq;
742
743 midiq = card_mpuin->firstmidiq;
744 *midiq->midibyte = data;
745 --midiq->sizeLeft;
746 ++midiq->midibyte;
747
748 spin_lock_irqsave(&card_mpuin->lock, flags);
749
750 card_mpuin->firstmidiq = midiq->next;
751 if (card_mpuin->firstmidiq == NULL)
752 card_mpuin->lastmidiq = NULL;
753
754 spin_unlock_irqrestore(&card_mpuin->lock, flags);
755
756 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INLONGERROR, (unsigned long) midiq, 0);
757
758 kfree(midiq);
759 }
760
761 return -1;
762 }
763
764 if (card_mpuin->firstmidiq) {
765 struct midi_queue *midiq;
766
767 midiq = card_mpuin->firstmidiq;
768 *midiq->midibyte = data;
769 --midiq->sizeLeft;
770 ++midiq->midibyte;
771 }
772
773 if (data == 0xf7) {
774 /* End of Sysex buffer */
775 /* Send down the buffer */
776
777 card_mpuin->curstate = card_mpuin->laststate;
778
779 if (card_mpuin->firstmidiq) {
780 struct midi_queue *midiq;
781
782 midiq = card_mpuin->firstmidiq;
783
784 spin_lock_irqsave(&card_mpuin->lock, flags);
785
786 card_mpuin->firstmidiq = midiq->next;
787 if (card_mpuin->firstmidiq == NULL)
788 card_mpuin->lastmidiq = NULL;
789
790 spin_unlock_irqrestore(&card_mpuin->lock, flags);
791
792 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INLONGDATA, (unsigned long) midiq, 0);
793
794 kfree(midiq);
795 }
796
797 return 0;
798 }
799
800 if (card_mpuin->firstmidiq) {
801 struct midi_queue *midiq;
802
803 midiq = card_mpuin->firstmidiq;
804
805 if (midiq->sizeLeft == 0) {
806 /* Special case */
807
808 spin_lock_irqsave(&card_mpuin->lock, flags);
809
810 card_mpuin->firstmidiq = midiq->next;
811 if (card_mpuin->firstmidiq == NULL)
812 card_mpuin->lastmidiq = NULL;
813
814 spin_unlock_irqrestore(&card_mpuin->lock, flags);
815
816 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INLONGDATA, (unsigned long) midiq, 0);
817
818 kfree(midiq);
819
820 return CTSTATUS_NEXT_BYTE;
821 }
822 }
823
824 return CTSTATUS_NEXT_BYTE;
825}
826
827static int sblive_miStateSysReal(struct emu10k1_mpuin *card_mpuin, u8 data)
828{
829 emu10k1_mpuin_callback(card_mpuin, ICARDMIDI_INDATA, data, 1);
830
831 return CTSTATUS_NEXT_BYTE;
832}