1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37static int enable_midi_input(struct echoaudio *chip, char enable)
38{
39 DE_MID(("enable_midi_input(%d)\n", enable));
40
41 if (wait_handshake(chip))
42 return -EIO;
43
44 if (enable) {
45 chip->mtc_state = MIDI_IN_STATE_NORMAL;
46 chip->comm_page->flags |=
47 __constant_cpu_to_le32(DSP_FLAG_MIDI_INPUT);
48 } else
49 chip->comm_page->flags &=
50 ~__constant_cpu_to_le32(DSP_FLAG_MIDI_INPUT);
51
52 clear_handshake(chip);
53 return send_vector(chip, DSP_VC_UPDATE_FLAGS);
54}
55
56
57
58
59
60static int write_midi(struct echoaudio *chip, u8 *data, int bytes)
61{
62 snd_assert(bytes > 0 && bytes < MIDI_OUT_BUFFER_SIZE, return -EINVAL);
63
64 if (wait_handshake(chip))
65 return -EIO;
66
67
68 if (! (get_dsp_register(chip, CHI32_STATUS_REG) & CHI32_STATUS_REG_HF4))
69 return 0;
70
71 chip->comm_page->midi_output[0] = bytes;
72 memcpy(&chip->comm_page->midi_output[1], data, bytes);
73 chip->comm_page->midi_out_free_count = 0;
74 clear_handshake(chip);
75 send_vector(chip, DSP_VC_MIDI_WRITE);
76 DE_MID(("write_midi: %d\n", bytes));
77 return bytes;
78}
79
80
81
82
83
84
85
86
87
88
89static inline int mtc_process_data(struct echoaudio *chip, short midi_byte)
90{
91 switch (chip->mtc_state) {
92 case MIDI_IN_STATE_NORMAL:
93 if (midi_byte == 0xF1)
94 chip->mtc_state = MIDI_IN_STATE_TS_HIGH;
95 break;
96 case MIDI_IN_STATE_TS_HIGH:
97 chip->mtc_state = MIDI_IN_STATE_TS_LOW;
98 return MIDI_IN_SKIP_DATA;
99 break;
100 case MIDI_IN_STATE_TS_LOW:
101 chip->mtc_state = MIDI_IN_STATE_F1_DATA;
102 return MIDI_IN_SKIP_DATA;
103 break;
104 case MIDI_IN_STATE_F1_DATA:
105 chip->mtc_state = MIDI_IN_STATE_NORMAL;
106 break;
107 }
108 return 0;
109}
110
111
112
113
114
115static int midi_service_irq(struct echoaudio *chip)
116{
117 short int count, midi_byte, i, received;
118
119
120 count = le16_to_cpu(chip->comm_page->midi_input[0]);
121
122 snd_assert(count < MIDI_IN_BUFFER_SIZE, return 0);
123
124
125 i = 1;
126 received = 0;
127 for (i = 1; i <= count; i++) {
128
129 midi_byte = le16_to_cpu(chip->comm_page->midi_input[i]);
130
131
132
133
134
135
136
137 if (mtc_process_data(chip, midi_byte) == MIDI_IN_SKIP_DATA)
138 continue;
139
140 chip->midi_buffer[received++] = (u8)midi_byte;
141 }
142
143 return received;
144}
145
146
147
148
149
150
151
152
153static int snd_echo_midi_input_open(struct snd_rawmidi_substream *substream)
154{
155 struct echoaudio *chip = substream->rmidi->private_data;
156
157 chip->midi_in = substream;
158 DE_MID(("rawmidi_iopen\n"));
159 return 0;
160}
161
162
163
164static void snd_echo_midi_input_trigger(struct snd_rawmidi_substream *substream,
165 int up)
166{
167 struct echoaudio *chip = substream->rmidi->private_data;
168
169 if (up != chip->midi_input_enabled) {
170 spin_lock_irq(&chip->lock);
171 enable_midi_input(chip, up);
172 spin_unlock_irq(&chip->lock);
173 chip->midi_input_enabled = up;
174 }
175}
176
177
178
179static int snd_echo_midi_input_close(struct snd_rawmidi_substream *substream)
180{
181 struct echoaudio *chip = substream->rmidi->private_data;
182
183 chip->midi_in = NULL;
184 DE_MID(("rawmidi_iclose\n"));
185 return 0;
186}
187
188
189
190static int snd_echo_midi_output_open(struct snd_rawmidi_substream *substream)
191{
192 struct echoaudio *chip = substream->rmidi->private_data;
193
194 chip->tinuse = 0;
195 chip->midi_full = 0;
196 chip->midi_out = substream;
197 DE_MID(("rawmidi_oopen\n"));
198 return 0;
199}
200
201
202
203static void snd_echo_midi_output_write(unsigned long data)
204{
205 struct echoaudio *chip = (struct echoaudio *)data;
206 unsigned long flags;
207 int bytes, sent, time;
208 unsigned char buf[MIDI_OUT_BUFFER_SIZE - 1];
209
210 DE_MID(("snd_echo_midi_output_write\n"));
211
212
213 sent = bytes = 0;
214 spin_lock_irqsave(&chip->lock, flags);
215 chip->midi_full = 0;
216 if (!snd_rawmidi_transmit_empty(chip->midi_out)) {
217 bytes = snd_rawmidi_transmit_peek(chip->midi_out, buf,
218 MIDI_OUT_BUFFER_SIZE - 1);
219 DE_MID(("Try to send %d bytes...\n", bytes));
220 sent = write_midi(chip, buf, bytes);
221 if (sent < 0) {
222 snd_printk(KERN_ERR "write_midi() error %d\n", sent);
223
224 sent = 9000;
225 chip->midi_full = 1;
226 } else if (sent > 0) {
227 DE_MID(("%d bytes sent\n", sent));
228 snd_rawmidi_transmit_ack(chip->midi_out, sent);
229 } else {
230
231
232 DE_MID(("Full\n"));
233 sent = 32;
234 chip->midi_full = 1;
235 }
236 }
237
238
239 if (!snd_rawmidi_transmit_empty(chip->midi_out) && chip->tinuse) {
240
241
242 time = (sent << 3) / 25 + 1;
243 mod_timer(&chip->timer, jiffies + (time * HZ + 999) / 1000);
244 DE_MID(("Timer armed(%d)\n", ((time * HZ + 999) / 1000)));
245 }
246 spin_unlock_irqrestore(&chip->lock, flags);
247}
248
249
250
251static void snd_echo_midi_output_trigger(struct snd_rawmidi_substream *substream,
252 int up)
253{
254 struct echoaudio *chip = substream->rmidi->private_data;
255
256 DE_MID(("snd_echo_midi_output_trigger(%d)\n", up));
257 spin_lock_irq(&chip->lock);
258 if (up) {
259 if (!chip->tinuse) {
260 init_timer(&chip->timer);
261 chip->timer.function = snd_echo_midi_output_write;
262 chip->timer.data = (unsigned long)chip;
263 chip->tinuse = 1;
264 }
265 } else {
266 if (chip->tinuse) {
267 chip->tinuse = 0;
268 spin_unlock_irq(&chip->lock);
269 del_timer_sync(&chip->timer);
270 DE_MID(("Timer removed\n"));
271 return;
272 }
273 }
274 spin_unlock_irq(&chip->lock);
275
276 if (up && !chip->midi_full)
277 snd_echo_midi_output_write((unsigned long)chip);
278}
279
280
281
282static int snd_echo_midi_output_close(struct snd_rawmidi_substream *substream)
283{
284 struct echoaudio *chip = substream->rmidi->private_data;
285
286 chip->midi_out = NULL;
287 DE_MID(("rawmidi_oclose\n"));
288 return 0;
289}
290
291
292
293static struct snd_rawmidi_ops snd_echo_midi_input = {
294 .open = snd_echo_midi_input_open,
295 .close = snd_echo_midi_input_close,
296 .trigger = snd_echo_midi_input_trigger,
297};
298
299static struct snd_rawmidi_ops snd_echo_midi_output = {
300 .open = snd_echo_midi_output_open,
301 .close = snd_echo_midi_output_close,
302 .trigger = snd_echo_midi_output_trigger,
303};
304
305
306
307
308static int __devinit snd_echo_midi_create(struct snd_card *card,
309 struct echoaudio *chip)
310{
311 int err;
312
313 if ((err = snd_rawmidi_new(card, card->shortname, 0, 1, 1,
314 &chip->rmidi)) < 0)
315 return err;
316
317 strcpy(chip->rmidi->name, card->shortname);
318 chip->rmidi->private_data = chip;
319
320 snd_rawmidi_set_ops(chip->rmidi, SNDRV_RAWMIDI_STREAM_INPUT,
321 &snd_echo_midi_input);
322 snd_rawmidi_set_ops(chip->rmidi, SNDRV_RAWMIDI_STREAM_OUTPUT,
323 &snd_echo_midi_output);
324
325 chip->rmidi->info_flags |= SNDRV_RAWMIDI_INFO_OUTPUT |
326 SNDRV_RAWMIDI_INFO_INPUT | SNDRV_RAWMIDI_INFO_DUPLEX;
327 DE_INIT(("MIDI ok\n"));
328 return 0;
329}
330