[ALSA] at73c213: replace spinlock in mixer functions with a mutex
[deliverable/linux.git] / sound / pci / rme9652 / hdspm.c
CommitLineData
ef5fa1a4 1/*
763f356c
TI
2 * ALSA driver for RME Hammerfall DSP MADI audio interface(s)
3 *
4 * Copyright (c) 2003 Winfried Ritsch (IEM)
5 * code based on hdsp.c Paul Davis
6 * Marcus Andersson
7 * Thomas Charbonnel
3cee5a60
RB
8 * Modified 2006-06-01 for AES32 support by Remy Bruno
9 * <remy.bruno@trinnov.com>
763f356c
TI
10 *
11 * This program is free software; you can redistribute it and/or modify
12 * it under the terms of the GNU General Public License as published by
13 * the Free Software Foundation; either version 2 of the License, or
14 * (at your option) any later version.
15 *
16 * This program is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU General Public License for more details.
20 *
21 * You should have received a copy of the GNU General Public License
22 * along with this program; if not, write to the Free Software
23 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
24 *
25 */
26#include <sound/driver.h>
27#include <linux/init.h>
28#include <linux/delay.h>
29#include <linux/interrupt.h>
30#include <linux/moduleparam.h>
31#include <linux/slab.h>
32#include <linux/pci.h>
33#include <asm/io.h>
34
35#include <sound/core.h>
36#include <sound/control.h>
37#include <sound/pcm.h>
38#include <sound/info.h>
39#include <sound/asoundef.h>
40#include <sound/rawmidi.h>
41#include <sound/hwdep.h>
42#include <sound/initval.h>
43
44#include <sound/hdspm.h>
45
46static int index[SNDRV_CARDS] = SNDRV_DEFAULT_IDX; /* Index 0-MAX */
47static char *id[SNDRV_CARDS] = SNDRV_DEFAULT_STR; /* ID for this card */
48static int enable[SNDRV_CARDS] = SNDRV_DEFAULT_ENABLE_PNP;/* Enable this card */
49
50/* Disable precise pointer at start */
51static int precise_ptr[SNDRV_CARDS];
52
53/* Send all playback to line outs */
54static int line_outs_monitor[SNDRV_CARDS];
55
56/* Enable Analog Outs on Channel 63/64 by default */
57static int enable_monitor[SNDRV_CARDS];
58
59module_param_array(index, int, NULL, 0444);
60MODULE_PARM_DESC(index, "Index value for RME HDSPM interface.");
61
62module_param_array(id, charp, NULL, 0444);
63MODULE_PARM_DESC(id, "ID string for RME HDSPM interface.");
64
65module_param_array(enable, bool, NULL, 0444);
66MODULE_PARM_DESC(enable, "Enable/disable specific HDSPM soundcards.");
67
68module_param_array(precise_ptr, bool, NULL, 0444);
e8da2fbc 69MODULE_PARM_DESC(precise_ptr, "Enable or disable precise pointer.");
763f356c
TI
70
71module_param_array(line_outs_monitor, bool, NULL, 0444);
72MODULE_PARM_DESC(line_outs_monitor,
73 "Send playback streams to analog outs by default.");
74
75module_param_array(enable_monitor, bool, NULL, 0444);
76MODULE_PARM_DESC(enable_monitor,
77 "Enable Analog Out on Channel 63/64 by default.");
78
79MODULE_AUTHOR
ef5fa1a4
TI
80 ("Winfried Ritsch <ritsch_AT_iem.at>, "
81 "Paul Davis <paul@linuxaudiosystems.com>, "
3cee5a60
RB
82 "Marcus Andersson, Thomas Charbonnel <thomas@undata.org>, "
83 "Remy Bruno <remy.bruno@trinnov.com>");
763f356c
TI
84MODULE_DESCRIPTION("RME HDSPM");
85MODULE_LICENSE("GPL");
86MODULE_SUPPORTED_DEVICE("{{RME HDSPM-MADI}}");
87
88/* --- Write registers. ---
89 These are defined as byte-offsets from the iobase value. */
90
91#define HDSPM_controlRegister 64
92#define HDSPM_interruptConfirmation 96
93#define HDSPM_control2Reg 256 /* not in specs ???????? */
ffb2c3c0 94#define HDSPM_freqReg 256 /* for AES32 */
763f356c
TI
95#define HDSPM_midiDataOut0 352 /* just believe in old code */
96#define HDSPM_midiDataOut1 356
ffb2c3c0 97#define HDSPM_eeprom_wr 384 /* for AES32 */
763f356c
TI
98
99/* DMA enable for 64 channels, only Bit 0 is relevant */
100#define HDSPM_outputEnableBase 512 /* 512-767 input DMA */
101#define HDSPM_inputEnableBase 768 /* 768-1023 output DMA */
102
103/* 16 page addresses for each of the 64 channels DMA buffer in and out
104 (each 64k=16*4k) Buffer must be 4k aligned (which is default i386 ????) */
105#define HDSPM_pageAddressBufferOut 8192
106#define HDSPM_pageAddressBufferIn (HDSPM_pageAddressBufferOut+64*16*4)
107
108#define HDSPM_MADI_mixerBase 32768 /* 32768-65535 for 2x64x64 Fader */
109
110#define HDSPM_MATRIX_MIXER_SIZE 8192 /* = 2*64*64 * 4 Byte => 32kB */
111
112/* --- Read registers. ---
113 These are defined as byte-offsets from the iobase value */
114#define HDSPM_statusRegister 0
3cee5a60
RB
115/*#define HDSPM_statusRegister2 96 */
116/* after RME Windows driver sources, status2 is 4-byte word # 48 = word at
117 * offset 192, for AES32 *and* MADI
118 * => need to check that offset 192 is working on MADI */
119#define HDSPM_statusRegister2 192
120#define HDSPM_timecodeRegister 128
763f356c
TI
121
122#define HDSPM_midiDataIn0 360
123#define HDSPM_midiDataIn1 364
124
125/* status is data bytes in MIDI-FIFO (0-128) */
126#define HDSPM_midiStatusOut0 384
127#define HDSPM_midiStatusOut1 388
128#define HDSPM_midiStatusIn0 392
129#define HDSPM_midiStatusIn1 396
130
131
132/* the meters are regular i/o-mapped registers, but offset
133 considerably from the rest. the peak registers are reset
134 when read; the least-significant 4 bits are full-scale counters;
135 the actual peak value is in the most-significant 24 bits.
136*/
137#define HDSPM_MADI_peakrmsbase 4096 /* 4096-8191 2x64x32Bit Meters */
138
139/* --- Control Register bits --------- */
140#define HDSPM_Start (1<<0) /* start engine */
141
142#define HDSPM_Latency0 (1<<1) /* buffer size = 2^n */
143#define HDSPM_Latency1 (1<<2) /* where n is defined */
144#define HDSPM_Latency2 (1<<3) /* by Latency{2,1,0} */
145
146#define HDSPM_ClockModeMaster (1<<4) /* 1=Master, 0=Slave/Autosync */
147
148#define HDSPM_AudioInterruptEnable (1<<5) /* what do you think ? */
149
150#define HDSPM_Frequency0 (1<<6) /* 0=44.1kHz/88.2kHz 1=48kHz/96kHz */
151#define HDSPM_Frequency1 (1<<7) /* 0=32kHz/64kHz */
152#define HDSPM_DoubleSpeed (1<<8) /* 0=normal speed, 1=double speed */
3cee5a60 153#define HDSPM_QuadSpeed (1<<31) /* quad speed bit */
763f356c 154
3cee5a60 155#define HDSPM_Professional (1<<9) /* Professional */ /* AES32 ONLY */
763f356c 156#define HDSPM_TX_64ch (1<<10) /* Output 64channel MODE=1,
3cee5a60
RB
157 56channelMODE=0 */ /* MADI ONLY*/
158#define HDSPM_Emphasis (1<<10) /* Emphasis */ /* AES32 ONLY */
763f356c
TI
159
160#define HDSPM_AutoInp (1<<11) /* Auto Input (takeover) == Safe Mode,
3cee5a60
RB
161 0=off, 1=on */ /* MADI ONLY */
162#define HDSPM_Dolby (1<<11) /* Dolby = "NonAudio" ?? */ /* AES32 ONLY */
763f356c 163
ef5fa1a4
TI
164#define HDSPM_InputSelect0 (1<<14) /* Input select 0= optical, 1=coax
165 * -- MADI ONLY
166 */
763f356c
TI
167#define HDSPM_InputSelect1 (1<<15) /* should be 0 */
168
169#define HDSPM_SyncRef0 (1<<16) /* 0=WOrd, 1=MADI */
3cee5a60
RB
170#define HDSPM_SyncRef1 (1<<17) /* for AES32: SyncRefN codes the AES # */
171#define HDSPM_SyncRef2 (1<<13)
172#define HDSPM_SyncRef3 (1<<25)
763f356c 173
3cee5a60 174#define HDSPM_SMUX (1<<18) /* Frame ??? */ /* MADI ONY */
763f356c
TI
175#define HDSPM_clr_tms (1<<19) /* clear track marker, do not use
176 AES additional bits in
177 lower 5 Audiodatabits ??? */
3cee5a60
RB
178#define HDSPM_taxi_reset (1<<20) /* ??? */ /* MADI ONLY ? */
179#define HDSPM_WCK48 (1<<20) /* Frame ??? = HDSPM_SMUX */ /* AES32 ONLY */
763f356c
TI
180
181#define HDSPM_Midi0InterruptEnable (1<<22)
182#define HDSPM_Midi1InterruptEnable (1<<23)
183
184#define HDSPM_LineOut (1<<24) /* Analog Out on channel 63/64 on=1, mute=0 */
185
3cee5a60
RB
186#define HDSPM_DS_DoubleWire (1<<26) /* AES32 ONLY */
187#define HDSPM_QS_DoubleWire (1<<27) /* AES32 ONLY */
188#define HDSPM_QS_QuadWire (1<<28) /* AES32 ONLY */
189
190#define HDSPM_wclk_sel (1<<30)
763f356c
TI
191
192/* --- bit helper defines */
193#define HDSPM_LatencyMask (HDSPM_Latency0|HDSPM_Latency1|HDSPM_Latency2)
ef5fa1a4
TI
194#define HDSPM_FrequencyMask (HDSPM_Frequency0|HDSPM_Frequency1|\
195 HDSPM_DoubleSpeed|HDSPM_QuadSpeed)
763f356c
TI
196#define HDSPM_InputMask (HDSPM_InputSelect0|HDSPM_InputSelect1)
197#define HDSPM_InputOptical 0
198#define HDSPM_InputCoaxial (HDSPM_InputSelect0)
ef5fa1a4
TI
199#define HDSPM_SyncRefMask (HDSPM_SyncRef0|HDSPM_SyncRef1|\
200 HDSPM_SyncRef2|HDSPM_SyncRef3)
763f356c
TI
201#define HDSPM_SyncRef_Word 0
202#define HDSPM_SyncRef_MADI (HDSPM_SyncRef0)
203
204#define HDSPM_SYNC_FROM_WORD 0 /* Preferred sync reference */
205#define HDSPM_SYNC_FROM_MADI 1 /* choices - used by "pref_sync_ref" */
206
207#define HDSPM_Frequency32KHz HDSPM_Frequency0
208#define HDSPM_Frequency44_1KHz HDSPM_Frequency1
209#define HDSPM_Frequency48KHz (HDSPM_Frequency1|HDSPM_Frequency0)
210#define HDSPM_Frequency64KHz (HDSPM_DoubleSpeed|HDSPM_Frequency0)
211#define HDSPM_Frequency88_2KHz (HDSPM_DoubleSpeed|HDSPM_Frequency1)
ef5fa1a4
TI
212#define HDSPM_Frequency96KHz (HDSPM_DoubleSpeed|HDSPM_Frequency1|\
213 HDSPM_Frequency0)
3cee5a60
RB
214#define HDSPM_Frequency128KHz (HDSPM_QuadSpeed|HDSPM_Frequency0)
215#define HDSPM_Frequency176_4KHz (HDSPM_QuadSpeed|HDSPM_Frequency1)
ef5fa1a4
TI
216#define HDSPM_Frequency192KHz (HDSPM_QuadSpeed|HDSPM_Frequency1|\
217 HDSPM_Frequency0)
763f356c
TI
218
219/* --- for internal discrimination */
220#define HDSPM_CLOCK_SOURCE_AUTOSYNC 0 /* Sample Clock Sources */
221#define HDSPM_CLOCK_SOURCE_INTERNAL_32KHZ 1
222#define HDSPM_CLOCK_SOURCE_INTERNAL_44_1KHZ 2
223#define HDSPM_CLOCK_SOURCE_INTERNAL_48KHZ 3
224#define HDSPM_CLOCK_SOURCE_INTERNAL_64KHZ 4
225#define HDSPM_CLOCK_SOURCE_INTERNAL_88_2KHZ 5
226#define HDSPM_CLOCK_SOURCE_INTERNAL_96KHZ 6
227#define HDSPM_CLOCK_SOURCE_INTERNAL_128KHZ 7
228#define HDSPM_CLOCK_SOURCE_INTERNAL_176_4KHZ 8
229#define HDSPM_CLOCK_SOURCE_INTERNAL_192KHZ 9
230
231/* Synccheck Status */
232#define HDSPM_SYNC_CHECK_NO_LOCK 0
233#define HDSPM_SYNC_CHECK_LOCK 1
234#define HDSPM_SYNC_CHECK_SYNC 2
235
236/* AutoSync References - used by "autosync_ref" control switch */
237#define HDSPM_AUTOSYNC_FROM_WORD 0
238#define HDSPM_AUTOSYNC_FROM_MADI 1
239#define HDSPM_AUTOSYNC_FROM_NONE 2
240
241/* Possible sources of MADI input */
242#define HDSPM_OPTICAL 0 /* optical */
243#define HDSPM_COAXIAL 1 /* BNC */
244
245#define hdspm_encode_latency(x) (((x)<<1) & HDSPM_LatencyMask)
246#define hdspm_decode_latency(x) (((x) & HDSPM_LatencyMask)>>1)
247
248#define hdspm_encode_in(x) (((x)&0x3)<<14)
249#define hdspm_decode_in(x) (((x)>>14)&0x3)
250
251/* --- control2 register bits --- */
252#define HDSPM_TMS (1<<0)
253#define HDSPM_TCK (1<<1)
254#define HDSPM_TDI (1<<2)
255#define HDSPM_JTAG (1<<3)
256#define HDSPM_PWDN (1<<4)
257#define HDSPM_PROGRAM (1<<5)
258#define HDSPM_CONFIG_MODE_0 (1<<6)
259#define HDSPM_CONFIG_MODE_1 (1<<7)
260/*#define HDSPM_VERSION_BIT (1<<8) not defined any more*/
261#define HDSPM_BIGENDIAN_MODE (1<<9)
262#define HDSPM_RD_MULTIPLE (1<<10)
263
3cee5a60 264/* --- Status Register bits --- */ /* MADI ONLY */ /* Bits defined here and
ef5fa1a4
TI
265 that do not conflict with specific bits for AES32 seem to be valid also
266 for the AES32
267 */
763f356c 268#define HDSPM_audioIRQPending (1<<0) /* IRQ is high and pending */
ef5fa1a4
TI
269#define HDSPM_RX_64ch (1<<1) /* Input 64chan. MODE=1, 56chn MODE=0 */
270#define HDSPM_AB_int (1<<2) /* InputChannel Opt=0, Coax=1
271 * (like inp0)
272 */
763f356c
TI
273#define HDSPM_madiLock (1<<3) /* MADI Locked =1, no=0 */
274
275#define HDSPM_BufferPositionMask 0x000FFC0 /* Bit 6..15 : h/w buffer pointer */
276 /* since 64byte accurate last 6 bits
277 are not used */
278
279#define HDSPM_madiSync (1<<18) /* MADI is in sync */
280#define HDSPM_DoubleSpeedStatus (1<<19) /* (input) card in double speed */
281
282#define HDSPM_madiFreq0 (1<<22) /* system freq 0=error */
283#define HDSPM_madiFreq1 (1<<23) /* 1=32, 2=44.1 3=48 */
284#define HDSPM_madiFreq2 (1<<24) /* 4=64, 5=88.2 6=96 */
285#define HDSPM_madiFreq3 (1<<25) /* 7=128, 8=176.4 9=192 */
286
ef5fa1a4
TI
287#define HDSPM_BufferID (1<<26) /* (Double)Buffer ID toggles with
288 * Interrupt
289 */
763f356c
TI
290#define HDSPM_midi0IRQPending (1<<30) /* MIDI IRQ is pending */
291#define HDSPM_midi1IRQPending (1<<31) /* and aktiv */
292
293/* --- status bit helpers */
ef5fa1a4
TI
294#define HDSPM_madiFreqMask (HDSPM_madiFreq0|HDSPM_madiFreq1|\
295 HDSPM_madiFreq2|HDSPM_madiFreq3)
763f356c
TI
296#define HDSPM_madiFreq32 (HDSPM_madiFreq0)
297#define HDSPM_madiFreq44_1 (HDSPM_madiFreq1)
298#define HDSPM_madiFreq48 (HDSPM_madiFreq0|HDSPM_madiFreq1)
299#define HDSPM_madiFreq64 (HDSPM_madiFreq2)
300#define HDSPM_madiFreq88_2 (HDSPM_madiFreq0|HDSPM_madiFreq2)
301#define HDSPM_madiFreq96 (HDSPM_madiFreq1|HDSPM_madiFreq2)
302#define HDSPM_madiFreq128 (HDSPM_madiFreq0|HDSPM_madiFreq1|HDSPM_madiFreq2)
303#define HDSPM_madiFreq176_4 (HDSPM_madiFreq3)
304#define HDSPM_madiFreq192 (HDSPM_madiFreq3|HDSPM_madiFreq0)
305
3cee5a60 306/* Status2 Register bits */ /* MADI ONLY */
763f356c
TI
307
308#define HDSPM_version0 (1<<0) /* not realy defined but I guess */
309#define HDSPM_version1 (1<<1) /* in former cards it was ??? */
310#define HDSPM_version2 (1<<2)
311
312#define HDSPM_wcLock (1<<3) /* Wordclock is detected and locked */
313#define HDSPM_wcSync (1<<4) /* Wordclock is in sync with systemclock */
314
315#define HDSPM_wc_freq0 (1<<5) /* input freq detected via autosync */
316#define HDSPM_wc_freq1 (1<<6) /* 001=32, 010==44.1, 011=48, */
317#define HDSPM_wc_freq2 (1<<7) /* 100=64, 101=88.2, 110=96, */
318/* missing Bit for 111=128, 1000=176.4, 1001=192 */
319
320#define HDSPM_SelSyncRef0 (1<<8) /* Sync Source in slave mode */
321#define HDSPM_SelSyncRef1 (1<<9) /* 000=word, 001=MADI, */
322#define HDSPM_SelSyncRef2 (1<<10) /* 111=no valid signal */
323
324#define HDSPM_wc_valid (HDSPM_wcLock|HDSPM_wcSync)
325
326#define HDSPM_wcFreqMask (HDSPM_wc_freq0|HDSPM_wc_freq1|HDSPM_wc_freq2)
327#define HDSPM_wcFreq32 (HDSPM_wc_freq0)
328#define HDSPM_wcFreq44_1 (HDSPM_wc_freq1)
329#define HDSPM_wcFreq48 (HDSPM_wc_freq0|HDSPM_wc_freq1)
330#define HDSPM_wcFreq64 (HDSPM_wc_freq2)
331#define HDSPM_wcFreq88_2 (HDSPM_wc_freq0|HDSPM_wc_freq2)
332#define HDSPM_wcFreq96 (HDSPM_wc_freq1|HDSPM_wc_freq2)
333
334
ef5fa1a4
TI
335#define HDSPM_SelSyncRefMask (HDSPM_SelSyncRef0|HDSPM_SelSyncRef1|\
336 HDSPM_SelSyncRef2)
763f356c
TI
337#define HDSPM_SelSyncRef_WORD 0
338#define HDSPM_SelSyncRef_MADI (HDSPM_SelSyncRef0)
ef5fa1a4
TI
339#define HDSPM_SelSyncRef_NVALID (HDSPM_SelSyncRef0|HDSPM_SelSyncRef1|\
340 HDSPM_SelSyncRef2)
763f356c 341
3cee5a60
RB
342/*
343 For AES32, bits for status, status2 and timecode are different
344*/
345/* status */
346#define HDSPM_AES32_wcLock 0x0200000
347#define HDSPM_AES32_wcFreq_bit 22
348/* (status >> HDSPM_AES32_wcFreq_bit) & 0xF gives WC frequency (cf function
349 HDSPM_bit2freq */
350#define HDSPM_AES32_syncref_bit 16
351/* (status >> HDSPM_AES32_syncref_bit) & 0xF gives sync source */
352
353#define HDSPM_AES32_AUTOSYNC_FROM_WORD 0
354#define HDSPM_AES32_AUTOSYNC_FROM_AES1 1
355#define HDSPM_AES32_AUTOSYNC_FROM_AES2 2
356#define HDSPM_AES32_AUTOSYNC_FROM_AES3 3
357#define HDSPM_AES32_AUTOSYNC_FROM_AES4 4
358#define HDSPM_AES32_AUTOSYNC_FROM_AES5 5
359#define HDSPM_AES32_AUTOSYNC_FROM_AES6 6
360#define HDSPM_AES32_AUTOSYNC_FROM_AES7 7
361#define HDSPM_AES32_AUTOSYNC_FROM_AES8 8
6534599d 362#define HDSPM_AES32_AUTOSYNC_FROM_NONE 9
3cee5a60
RB
363
364/* status2 */
365/* HDSPM_LockAES_bit is given by HDSPM_LockAES >> (AES# - 1) */
366#define HDSPM_LockAES 0x80
367#define HDSPM_LockAES1 0x80
368#define HDSPM_LockAES2 0x40
369#define HDSPM_LockAES3 0x20
370#define HDSPM_LockAES4 0x10
371#define HDSPM_LockAES5 0x8
372#define HDSPM_LockAES6 0x4
373#define HDSPM_LockAES7 0x2
374#define HDSPM_LockAES8 0x1
375/*
376 Timecode
377 After windows driver sources, bits 4*i to 4*i+3 give the input frequency on
378 AES i+1
379 bits 3210
380 0001 32kHz
381 0010 44.1kHz
382 0011 48kHz
383 0100 64kHz
384 0101 88.2kHz
385 0110 96kHz
386 0111 128kHz
387 1000 176.4kHz
388 1001 192kHz
389 NB: Timecode register doesn't seem to work on AES32 card revision 230
390*/
391
763f356c
TI
392/* Mixer Values */
393#define UNITY_GAIN 32768 /* = 65536/2 */
394#define MINUS_INFINITY_GAIN 0
395
763f356c
TI
396/* Number of channels for different Speed Modes */
397#define MADI_SS_CHANNELS 64
398#define MADI_DS_CHANNELS 32
399#define MADI_QS_CHANNELS 16
400
401/* the size of a substream (1 mono data stream) */
402#define HDSPM_CHANNEL_BUFFER_SAMPLES (16*1024)
403#define HDSPM_CHANNEL_BUFFER_BYTES (4*HDSPM_CHANNEL_BUFFER_SAMPLES)
404
405/* the size of the area we need to allocate for DMA transfers. the
406 size is the same regardless of the number of channels, and
407 also the latency to use.
408 for one direction !!!
409*/
ffb2c3c0 410#define HDSPM_DMA_AREA_BYTES (HDSPM_MAX_CHANNELS * HDSPM_CHANNEL_BUFFER_BYTES)
763f356c
TI
411#define HDSPM_DMA_AREA_KILOBYTES (HDSPM_DMA_AREA_BYTES/1024)
412
3cee5a60
RB
413/* revisions >= 230 indicate AES32 card */
414#define HDSPM_AESREVISION 230
415
6534599d
RB
416/* speed factor modes */
417#define HDSPM_SPEED_SINGLE 0
418#define HDSPM_SPEED_DOUBLE 1
419#define HDSPM_SPEED_QUAD 2
420/* names for speed modes */
421static char *hdspm_speed_names[] = { "single", "double", "quad" };
422
98274f07
TI
423struct hdspm_midi {
424 struct hdspm *hdspm;
763f356c 425 int id;
98274f07
TI
426 struct snd_rawmidi *rmidi;
427 struct snd_rawmidi_substream *input;
428 struct snd_rawmidi_substream *output;
763f356c
TI
429 char istimer; /* timer in use */
430 struct timer_list timer;
431 spinlock_t lock;
432 int pending;
433};
434
98274f07 435struct hdspm {
763f356c 436 spinlock_t lock;
ef5fa1a4
TI
437 /* only one playback and/or capture stream */
438 struct snd_pcm_substream *capture_substream;
439 struct snd_pcm_substream *playback_substream;
763f356c
TI
440
441 char *card_name; /* for procinfo */
3cee5a60
RB
442 unsigned short firmware_rev; /* dont know if relevant (yes if AES32)*/
443
444 unsigned char is_aes32; /* indicates if card is AES32 */
763f356c
TI
445
446 int precise_ptr; /* use precise pointers, to be tested */
447 int monitor_outs; /* set up monitoring outs init flag */
448
449 u32 control_register; /* cached value */
450 u32 control2_register; /* cached value */
451
98274f07 452 struct hdspm_midi midi[2];
763f356c
TI
453 struct tasklet_struct midi_tasklet;
454
455 size_t period_bytes;
456 unsigned char ss_channels; /* channels of card in single speed */
457 unsigned char ds_channels; /* Double Speed */
458 unsigned char qs_channels; /* Quad Speed */
459
460 unsigned char *playback_buffer; /* suitably aligned address */
461 unsigned char *capture_buffer; /* suitably aligned address */
462
463 pid_t capture_pid; /* process id which uses capture */
464 pid_t playback_pid; /* process id which uses capture */
465 int running; /* running status */
466
467 int last_external_sample_rate; /* samplerate mystic ... */
468 int last_internal_sample_rate;
469 int system_sample_rate;
470
471 char *channel_map; /* channel map for DS and Quadspeed */
472
473 int dev; /* Hardware vars... */
474 int irq;
475 unsigned long port;
476 void __iomem *iobase;
477
478 int irq_count; /* for debug */
479
98274f07
TI
480 struct snd_card *card; /* one card */
481 struct snd_pcm *pcm; /* has one pcm */
482 struct snd_hwdep *hwdep; /* and a hwdep for additional ioctl */
763f356c
TI
483 struct pci_dev *pci; /* and an pci info */
484
485 /* Mixer vars */
ef5fa1a4
TI
486 /* fast alsa mixer */
487 struct snd_kcontrol *playback_mixer_ctls[HDSPM_MAX_CHANNELS];
488 /* but input to much, so not used */
489 struct snd_kcontrol *input_mixer_ctls[HDSPM_MAX_CHANNELS];
490 /* full mixer accessable over mixer ioctl or hwdep-device */
491 struct hdspm_mixer *mixer;
763f356c
TI
492
493};
494
495/* These tables map the ALSA channels 1..N to the channels that we
496 need to use in order to find the relevant channel buffer. RME
497 refer to this kind of mapping as between "the ADAT channel and
498 the DMA channel." We index it using the logical audio channel,
499 and the value is the DMA channel (i.e. channel buffer number)
500 where the data for that channel can be read/written from/to.
501*/
502
503static char channel_map_madi_ss[HDSPM_MAX_CHANNELS] = {
504 0, 1, 2, 3, 4, 5, 6, 7,
505 8, 9, 10, 11, 12, 13, 14, 15,
506 16, 17, 18, 19, 20, 21, 22, 23,
507 24, 25, 26, 27, 28, 29, 30, 31,
508 32, 33, 34, 35, 36, 37, 38, 39,
509 40, 41, 42, 43, 44, 45, 46, 47,
510 48, 49, 50, 51, 52, 53, 54, 55,
511 56, 57, 58, 59, 60, 61, 62, 63
512};
513
763f356c 514
396c9b92 515static struct pci_device_id snd_hdspm_ids[] __devinitdata = {
763f356c
TI
516 {
517 .vendor = PCI_VENDOR_ID_XILINX,
518 .device = PCI_DEVICE_ID_XILINX_HAMMERFALL_DSP_MADI,
519 .subvendor = PCI_ANY_ID,
520 .subdevice = PCI_ANY_ID,
521 .class = 0,
522 .class_mask = 0,
523 .driver_data = 0},
524 {0,}
525};
526
527MODULE_DEVICE_TABLE(pci, snd_hdspm_ids);
528
529/* prototypes */
98274f07
TI
530static int __devinit snd_hdspm_create_alsa_devices(struct snd_card *card,
531 struct hdspm * hdspm);
532static int __devinit snd_hdspm_create_pcm(struct snd_card *card,
533 struct hdspm * hdspm);
534
535static inline void snd_hdspm_initialize_midi_flush(struct hdspm * hdspm);
536static int hdspm_update_simple_mixer_controls(struct hdspm * hdspm);
537static int hdspm_autosync_ref(struct hdspm * hdspm);
538static int snd_hdspm_set_defaults(struct hdspm * hdspm);
539static void hdspm_set_sgbuf(struct hdspm * hdspm, struct snd_sg_buf *sgbuf,
763f356c
TI
540 unsigned int reg, int channels);
541
3cee5a60
RB
542static inline int HDSPM_bit2freq(int n)
543{
544 static int bit2freq_tab[] = { 0, 32000, 44100, 48000, 64000, 88200,
545 96000, 128000, 176400, 192000 };
546 if (n < 1 || n > 9)
547 return 0;
548 return bit2freq_tab[n];
549}
550
763f356c
TI
551/* Write/read to/from HDSPM with Adresses in Bytes
552 not words but only 32Bit writes are allowed */
553
98274f07 554static inline void hdspm_write(struct hdspm * hdspm, unsigned int reg,
763f356c
TI
555 unsigned int val)
556{
557 writel(val, hdspm->iobase + reg);
558}
559
98274f07 560static inline unsigned int hdspm_read(struct hdspm * hdspm, unsigned int reg)
763f356c
TI
561{
562 return readl(hdspm->iobase + reg);
563}
564
565/* for each output channel (chan) I have an Input (in) and Playback (pb) Fader
566 mixer is write only on hardware so we have to cache him for read
567 each fader is a u32, but uses only the first 16 bit */
568
98274f07 569static inline int hdspm_read_in_gain(struct hdspm * hdspm, unsigned int chan,
763f356c
TI
570 unsigned int in)
571{
5bab2482 572 if (chan >= HDSPM_MIXER_CHANNELS || in >= HDSPM_MIXER_CHANNELS)
763f356c
TI
573 return 0;
574
575 return hdspm->mixer->ch[chan].in[in];
576}
577
98274f07 578static inline int hdspm_read_pb_gain(struct hdspm * hdspm, unsigned int chan,
763f356c
TI
579 unsigned int pb)
580{
5bab2482 581 if (chan >= HDSPM_MIXER_CHANNELS || pb >= HDSPM_MIXER_CHANNELS)
763f356c
TI
582 return 0;
583 return hdspm->mixer->ch[chan].pb[pb];
584}
585
98274f07 586static inline int hdspm_write_in_gain(struct hdspm * hdspm, unsigned int chan,
763f356c
TI
587 unsigned int in, unsigned short data)
588{
589 if (chan >= HDSPM_MIXER_CHANNELS || in >= HDSPM_MIXER_CHANNELS)
590 return -1;
591
592 hdspm_write(hdspm,
593 HDSPM_MADI_mixerBase +
594 ((in + 128 * chan) * sizeof(u32)),
595 (hdspm->mixer->ch[chan].in[in] = data & 0xFFFF));
596 return 0;
597}
598
98274f07 599static inline int hdspm_write_pb_gain(struct hdspm * hdspm, unsigned int chan,
763f356c
TI
600 unsigned int pb, unsigned short data)
601{
602 if (chan >= HDSPM_MIXER_CHANNELS || pb >= HDSPM_MIXER_CHANNELS)
603 return -1;
604
605 hdspm_write(hdspm,
606 HDSPM_MADI_mixerBase +
607 ((64 + pb + 128 * chan) * sizeof(u32)),
608 (hdspm->mixer->ch[chan].pb[pb] = data & 0xFFFF));
609 return 0;
610}
611
612
613/* enable DMA for specific channels, now available for DSP-MADI */
98274f07 614static inline void snd_hdspm_enable_in(struct hdspm * hdspm, int i, int v)
763f356c
TI
615{
616 hdspm_write(hdspm, HDSPM_inputEnableBase + (4 * i), v);
617}
618
98274f07 619static inline void snd_hdspm_enable_out(struct hdspm * hdspm, int i, int v)
763f356c
TI
620{
621 hdspm_write(hdspm, HDSPM_outputEnableBase + (4 * i), v);
622}
623
624/* check if same process is writing and reading */
98274f07 625static inline int snd_hdspm_use_is_exclusive(struct hdspm * hdspm)
763f356c
TI
626{
627 unsigned long flags;
628 int ret = 1;
629
630 spin_lock_irqsave(&hdspm->lock, flags);
631 if ((hdspm->playback_pid != hdspm->capture_pid) &&
632 (hdspm->playback_pid >= 0) && (hdspm->capture_pid >= 0)) {
633 ret = 0;
634 }
635 spin_unlock_irqrestore(&hdspm->lock, flags);
636 return ret;
637}
638
639/* check for external sample rate */
98274f07 640static inline int hdspm_external_sample_rate(struct hdspm * hdspm)
763f356c 641{
3cee5a60
RB
642 if (hdspm->is_aes32) {
643 unsigned int status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
644 unsigned int status = hdspm_read(hdspm, HDSPM_statusRegister);
ef5fa1a4
TI
645 unsigned int timecode =
646 hdspm_read(hdspm, HDSPM_timecodeRegister);
3cee5a60
RB
647
648 int syncref = hdspm_autosync_ref(hdspm);
649
650 if (syncref == HDSPM_AES32_AUTOSYNC_FROM_WORD &&
651 status & HDSPM_AES32_wcLock)
ef5fa1a4
TI
652 return HDSPM_bit2freq((status >> HDSPM_AES32_wcFreq_bit)
653 & 0xF);
3cee5a60
RB
654 if (syncref >= HDSPM_AES32_AUTOSYNC_FROM_AES1 &&
655 syncref <= HDSPM_AES32_AUTOSYNC_FROM_AES8 &&
656 status2 & (HDSPM_LockAES >>
657 (syncref - HDSPM_AES32_AUTOSYNC_FROM_AES1)))
658 return HDSPM_bit2freq((timecode >>
659 (4*(syncref-HDSPM_AES32_AUTOSYNC_FROM_AES1))) & 0xF);
660 return 0;
661 } else {
662 unsigned int status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
663 unsigned int status = hdspm_read(hdspm, HDSPM_statusRegister);
664 unsigned int rate_bits;
665 int rate = 0;
763f356c 666
3cee5a60
RB
667 /* if wordclock has synced freq and wordclock is valid */
668 if ((status2 & HDSPM_wcLock) != 0 &&
669 (status & HDSPM_SelSyncRef0) == 0) {
763f356c 670
3cee5a60 671 rate_bits = status2 & HDSPM_wcFreqMask;
763f356c 672
3cee5a60
RB
673 switch (rate_bits) {
674 case HDSPM_wcFreq32:
675 rate = 32000;
676 break;
677 case HDSPM_wcFreq44_1:
678 rate = 44100;
679 break;
680 case HDSPM_wcFreq48:
681 rate = 48000;
682 break;
683 case HDSPM_wcFreq64:
684 rate = 64000;
685 break;
686 case HDSPM_wcFreq88_2:
687 rate = 88200;
688 break;
689 case HDSPM_wcFreq96:
690 rate = 96000;
691 break;
692 /* Quadspeed Bit missing ???? */
693 default:
694 rate = 0;
695 break;
696 }
763f356c 697 }
763f356c 698
ef5fa1a4
TI
699 /* if rate detected and Syncref is Word than have it,
700 * word has priority to MADI
701 */
3cee5a60
RB
702 if (rate != 0 &&
703 (status2 & HDSPM_SelSyncRefMask) == HDSPM_SelSyncRef_WORD)
704 return rate;
763f356c 705
3cee5a60
RB
706 /* maby a madi input (which is taken if sel sync is madi) */
707 if (status & HDSPM_madiLock) {
708 rate_bits = status & HDSPM_madiFreqMask;
763f356c 709
3cee5a60
RB
710 switch (rate_bits) {
711 case HDSPM_madiFreq32:
712 rate = 32000;
713 break;
714 case HDSPM_madiFreq44_1:
715 rate = 44100;
716 break;
717 case HDSPM_madiFreq48:
718 rate = 48000;
719 break;
720 case HDSPM_madiFreq64:
721 rate = 64000;
722 break;
723 case HDSPM_madiFreq88_2:
724 rate = 88200;
725 break;
726 case HDSPM_madiFreq96:
727 rate = 96000;
728 break;
729 case HDSPM_madiFreq128:
730 rate = 128000;
731 break;
732 case HDSPM_madiFreq176_4:
733 rate = 176400;
734 break;
735 case HDSPM_madiFreq192:
736 rate = 192000;
737 break;
738 default:
739 rate = 0;
740 break;
741 }
763f356c 742 }
3cee5a60 743 return rate;
763f356c 744 }
763f356c
TI
745}
746
747/* Latency function */
98274f07 748static inline void hdspm_compute_period_size(struct hdspm * hdspm)
763f356c
TI
749{
750 hdspm->period_bytes =
751 1 << ((hdspm_decode_latency(hdspm->control_register) + 8));
752}
753
98274f07 754static snd_pcm_uframes_t hdspm_hw_pointer(struct hdspm * hdspm)
763f356c
TI
755{
756 int position;
757
758 position = hdspm_read(hdspm, HDSPM_statusRegister);
759
ef5fa1a4
TI
760 if (!hdspm->precise_ptr)
761 return (position & HDSPM_BufferID) ?
762 (hdspm->period_bytes / 4) : 0;
763f356c 763
ef5fa1a4
TI
764 /* hwpointer comes in bytes and is 64Bytes accurate (by docu since
765 PCI Burst)
763f356c
TI
766 i have experimented that it is at most 64 Byte to much for playing
767 so substraction of 64 byte should be ok for ALSA, but use it only
768 for application where you know what you do since if you come to
769 near with record pointer it can be a disaster */
770
771 position &= HDSPM_BufferPositionMask;
772 position = ((position - 64) % (2 * hdspm->period_bytes)) / 4;
773
774 return position;
775}
776
777
98274f07 778static inline void hdspm_start_audio(struct hdspm * s)
763f356c
TI
779{
780 s->control_register |= (HDSPM_AudioInterruptEnable | HDSPM_Start);
781 hdspm_write(s, HDSPM_controlRegister, s->control_register);
782}
783
98274f07 784static inline void hdspm_stop_audio(struct hdspm * s)
763f356c
TI
785{
786 s->control_register &= ~(HDSPM_Start | HDSPM_AudioInterruptEnable);
787 hdspm_write(s, HDSPM_controlRegister, s->control_register);
788}
789
790/* should I silence all or only opened ones ? doit all for first even is 4MB*/
98274f07 791static inline void hdspm_silence_playback(struct hdspm * hdspm)
763f356c
TI
792{
793 int i;
794 int n = hdspm->period_bytes;
795 void *buf = hdspm->playback_buffer;
796
3cee5a60
RB
797 if (buf == NULL)
798 return;
763f356c
TI
799
800 for (i = 0; i < HDSPM_MAX_CHANNELS; i++) {
801 memset(buf, 0, n);
802 buf += HDSPM_CHANNEL_BUFFER_BYTES;
803 }
804}
805
98274f07 806static int hdspm_set_interrupt_interval(struct hdspm * s, unsigned int frames)
763f356c
TI
807{
808 int n;
809
810 spin_lock_irq(&s->lock);
811
812 frames >>= 7;
813 n = 0;
814 while (frames) {
815 n++;
816 frames >>= 1;
817 }
818 s->control_register &= ~HDSPM_LatencyMask;
819 s->control_register |= hdspm_encode_latency(n);
820
821 hdspm_write(s, HDSPM_controlRegister, s->control_register);
822
823 hdspm_compute_period_size(s);
824
825 spin_unlock_irq(&s->lock);
826
827 return 0;
828}
829
ffb2c3c0
RB
830static void hdspm_set_dds_value(struct hdspm *hdspm, int rate)
831{
832 u64 n;
833 u32 r;
834
835 if (rate >= 112000)
836 rate /= 4;
837 else if (rate >= 56000)
838 rate /= 2;
839
840 /* RME says n = 104857600000000, but in the windows MADI driver, I see:
6534599d 841// return 104857600000000 / rate; // 100 MHz
ffb2c3c0
RB
842 return 110100480000000 / rate; // 105 MHz
843 */
ef5fa1a4 844 /* n = 104857600000000ULL; */ /* = 2^20 * 10^8 */
ffb2c3c0
RB
845 n = 110100480000000ULL; /* Value checked for AES32 and MADI */
846 div64_32(&n, rate, &r);
847 /* n should be less than 2^32 for being written to FREQ register */
848 snd_assert((n >> 32) == 0);
849 hdspm_write(hdspm, HDSPM_freqReg, (u32)n);
850}
763f356c
TI
851
852/* dummy set rate lets see what happens */
98274f07 853static int hdspm_set_rate(struct hdspm * hdspm, int rate, int called_internally)
763f356c 854{
763f356c
TI
855 int current_rate;
856 int rate_bits;
857 int not_set = 0;
6534599d 858 int current_speed, target_speed;
763f356c
TI
859
860 /* ASSUMPTION: hdspm->lock is either set, or there is no need for
861 it (e.g. during module initialization).
862 */
863
864 if (!(hdspm->control_register & HDSPM_ClockModeMaster)) {
865
866 /* SLAVE --- */
867 if (called_internally) {
868
869 /* request from ctl or card initialization
870 just make a warning an remember setting
871 for future master mode switching */
872
ef5fa1a4
TI
873 snd_printk(KERN_WARNING "HDSPM: "
874 "Warning: device is not running "
875 "as a clock master.\n");
763f356c
TI
876 not_set = 1;
877 } else {
878
879 /* hw_param request while in AutoSync mode */
880 int external_freq =
881 hdspm_external_sample_rate(hdspm);
882
ef5fa1a4
TI
883 if (hdspm_autosync_ref(hdspm) ==
884 HDSPM_AUTOSYNC_FROM_NONE) {
763f356c 885
ef5fa1a4
TI
886 snd_printk(KERN_WARNING "HDSPM: "
887 "Detected no Externel Sync \n");
763f356c
TI
888 not_set = 1;
889
890 } else if (rate != external_freq) {
891
ef5fa1a4
TI
892 snd_printk(KERN_WARNING "HDSPM: "
893 "Warning: No AutoSync source for "
894 "requested rate\n");
763f356c
TI
895 not_set = 1;
896 }
897 }
898 }
899
900 current_rate = hdspm->system_sample_rate;
901
902 /* Changing between Singe, Double and Quad speed is not
903 allowed if any substreams are open. This is because such a change
904 causes a shift in the location of the DMA buffers and a reduction
905 in the number of available buffers.
906
907 Note that a similar but essentially insoluble problem exists for
908 externally-driven rate changes. All we can do is to flag rate
909 changes in the read/write routines.
910 */
911
6534599d
RB
912 if (current_rate <= 48000)
913 current_speed = HDSPM_SPEED_SINGLE;
914 else if (current_rate <= 96000)
915 current_speed = HDSPM_SPEED_DOUBLE;
916 else
917 current_speed = HDSPM_SPEED_QUAD;
918
919 if (rate <= 48000)
920 target_speed = HDSPM_SPEED_SINGLE;
921 else if (rate <= 96000)
922 target_speed = HDSPM_SPEED_DOUBLE;
923 else
924 target_speed = HDSPM_SPEED_QUAD;
3cee5a60 925
763f356c
TI
926 switch (rate) {
927 case 32000:
763f356c
TI
928 rate_bits = HDSPM_Frequency32KHz;
929 break;
930 case 44100:
763f356c
TI
931 rate_bits = HDSPM_Frequency44_1KHz;
932 break;
933 case 48000:
763f356c
TI
934 rate_bits = HDSPM_Frequency48KHz;
935 break;
936 case 64000:
763f356c
TI
937 rate_bits = HDSPM_Frequency64KHz;
938 break;
939 case 88200:
763f356c
TI
940 rate_bits = HDSPM_Frequency88_2KHz;
941 break;
942 case 96000:
763f356c
TI
943 rate_bits = HDSPM_Frequency96KHz;
944 break;
3cee5a60 945 case 128000:
3cee5a60
RB
946 rate_bits = HDSPM_Frequency128KHz;
947 break;
948 case 176400:
3cee5a60
RB
949 rate_bits = HDSPM_Frequency176_4KHz;
950 break;
951 case 192000:
3cee5a60
RB
952 rate_bits = HDSPM_Frequency192KHz;
953 break;
763f356c
TI
954 default:
955 return -EINVAL;
956 }
957
6534599d 958 if (current_speed != target_speed
763f356c
TI
959 && (hdspm->capture_pid >= 0 || hdspm->playback_pid >= 0)) {
960 snd_printk
ef5fa1a4 961 (KERN_ERR "HDSPM: "
6534599d 962 "cannot change from %s speed to %s speed mode "
ef5fa1a4 963 "(capture PID = %d, playback PID = %d)\n",
6534599d
RB
964 hdspm_speed_names[current_speed],
965 hdspm_speed_names[target_speed],
763f356c
TI
966 hdspm->capture_pid, hdspm->playback_pid);
967 return -EBUSY;
968 }
969
970 hdspm->control_register &= ~HDSPM_FrequencyMask;
971 hdspm->control_register |= rate_bits;
972 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
973
ffb2c3c0
RB
974 /* For AES32, need to set DDS value in FREQ register
975 For MADI, also apparently */
976 hdspm_set_dds_value(hdspm, rate);
977
978 if (hdspm->is_aes32 && rate != current_rate)
979 hdspm_write(hdspm, HDSPM_eeprom_wr, 0);
980
981 /* For AES32 and for MADI (at least rev 204), channel_map needs to
982 * always be channel_map_madi_ss, whatever the sample rate */
983 hdspm->channel_map = channel_map_madi_ss;
763f356c
TI
984
985 hdspm->system_sample_rate = rate;
986
987 if (not_set != 0)
988 return -1;
989
990 return 0;
991}
992
993/* mainly for init to 0 on load */
98274f07 994static void all_in_all_mixer(struct hdspm * hdspm, int sgain)
763f356c
TI
995{
996 int i, j;
ef5fa1a4
TI
997 unsigned int gain;
998
999 if (sgain > UNITY_GAIN)
1000 gain = UNITY_GAIN;
1001 else if (sgain < 0)
1002 gain = 0;
1003 else
1004 gain = sgain;
763f356c
TI
1005
1006 for (i = 0; i < HDSPM_MIXER_CHANNELS; i++)
1007 for (j = 0; j < HDSPM_MIXER_CHANNELS; j++) {
1008 hdspm_write_in_gain(hdspm, i, j, gain);
1009 hdspm_write_pb_gain(hdspm, i, j, gain);
1010 }
1011}
1012
1013/*----------------------------------------------------------------------------
1014 MIDI
1015 ----------------------------------------------------------------------------*/
1016
ef5fa1a4
TI
1017static inline unsigned char snd_hdspm_midi_read_byte (struct hdspm *hdspm,
1018 int id)
763f356c
TI
1019{
1020 /* the hardware already does the relevant bit-mask with 0xff */
1021 if (id)
1022 return hdspm_read(hdspm, HDSPM_midiDataIn1);
1023 else
1024 return hdspm_read(hdspm, HDSPM_midiDataIn0);
1025}
1026
ef5fa1a4
TI
1027static inline void snd_hdspm_midi_write_byte (struct hdspm *hdspm, int id,
1028 int val)
763f356c
TI
1029{
1030 /* the hardware already does the relevant bit-mask with 0xff */
1031 if (id)
1032 return hdspm_write(hdspm, HDSPM_midiDataOut1, val);
1033 else
1034 return hdspm_write(hdspm, HDSPM_midiDataOut0, val);
1035}
1036
98274f07 1037static inline int snd_hdspm_midi_input_available (struct hdspm *hdspm, int id)
763f356c
TI
1038{
1039 if (id)
1040 return (hdspm_read(hdspm, HDSPM_midiStatusIn1) & 0xff);
1041 else
1042 return (hdspm_read(hdspm, HDSPM_midiStatusIn0) & 0xff);
1043}
1044
98274f07 1045static inline int snd_hdspm_midi_output_possible (struct hdspm *hdspm, int id)
763f356c
TI
1046{
1047 int fifo_bytes_used;
1048
1049 if (id)
ef5fa1a4 1050 fifo_bytes_used = hdspm_read(hdspm, HDSPM_midiStatusOut1);
763f356c 1051 else
ef5fa1a4
TI
1052 fifo_bytes_used = hdspm_read(hdspm, HDSPM_midiStatusOut0);
1053 fifo_bytes_used &= 0xff;
763f356c
TI
1054
1055 if (fifo_bytes_used < 128)
1056 return 128 - fifo_bytes_used;
1057 else
1058 return 0;
1059}
1060
98274f07 1061static inline void snd_hdspm_flush_midi_input (struct hdspm *hdspm, int id)
763f356c
TI
1062{
1063 while (snd_hdspm_midi_input_available (hdspm, id))
1064 snd_hdspm_midi_read_byte (hdspm, id);
1065}
1066
98274f07 1067static int snd_hdspm_midi_output_write (struct hdspm_midi *hmidi)
763f356c
TI
1068{
1069 unsigned long flags;
1070 int n_pending;
1071 int to_write;
1072 int i;
1073 unsigned char buf[128];
1074
1075 /* Output is not interrupt driven */
1076
1077 spin_lock_irqsave (&hmidi->lock, flags);
ef5fa1a4
TI
1078 if (hmidi->output &&
1079 !snd_rawmidi_transmit_empty (hmidi->output)) {
1080 n_pending = snd_hdspm_midi_output_possible (hmidi->hdspm,
1081 hmidi->id);
1082 if (n_pending > 0) {
1083 if (n_pending > (int)sizeof (buf))
1084 n_pending = sizeof (buf);
1085
1086 to_write = snd_rawmidi_transmit (hmidi->output, buf,
1087 n_pending);
1088 if (to_write > 0) {
1089 for (i = 0; i < to_write; ++i)
1090 snd_hdspm_midi_write_byte (hmidi->hdspm,
1091 hmidi->id,
1092 buf[i]);
763f356c
TI
1093 }
1094 }
1095 }
1096 spin_unlock_irqrestore (&hmidi->lock, flags);
1097 return 0;
1098}
1099
98274f07 1100static int snd_hdspm_midi_input_read (struct hdspm_midi *hmidi)
763f356c 1101{
ef5fa1a4
TI
1102 unsigned char buf[128]; /* this buffer is designed to match the MIDI
1103 * input FIFO size
1104 */
763f356c
TI
1105 unsigned long flags;
1106 int n_pending;
1107 int i;
1108
1109 spin_lock_irqsave (&hmidi->lock, flags);
ef5fa1a4
TI
1110 n_pending = snd_hdspm_midi_input_available (hmidi->hdspm, hmidi->id);
1111 if (n_pending > 0) {
763f356c 1112 if (hmidi->input) {
ef5fa1a4 1113 if (n_pending > (int)sizeof (buf))
763f356c 1114 n_pending = sizeof (buf);
ef5fa1a4
TI
1115 for (i = 0; i < n_pending; ++i)
1116 buf[i] = snd_hdspm_midi_read_byte (hmidi->hdspm,
1117 hmidi->id);
1118 if (n_pending)
1119 snd_rawmidi_receive (hmidi->input, buf,
1120 n_pending);
763f356c
TI
1121 } else {
1122 /* flush the MIDI input FIFO */
ef5fa1a4
TI
1123 while (n_pending--)
1124 snd_hdspm_midi_read_byte (hmidi->hdspm,
1125 hmidi->id);
763f356c
TI
1126 }
1127 }
1128 hmidi->pending = 0;
ef5fa1a4 1129 if (hmidi->id)
763f356c 1130 hmidi->hdspm->control_register |= HDSPM_Midi1InterruptEnable;
ef5fa1a4 1131 else
763f356c 1132 hmidi->hdspm->control_register |= HDSPM_Midi0InterruptEnable;
ef5fa1a4
TI
1133 hdspm_write(hmidi->hdspm, HDSPM_controlRegister,
1134 hmidi->hdspm->control_register);
763f356c
TI
1135 spin_unlock_irqrestore (&hmidi->lock, flags);
1136 return snd_hdspm_midi_output_write (hmidi);
1137}
1138
ef5fa1a4
TI
1139static void
1140snd_hdspm_midi_input_trigger(struct snd_rawmidi_substream *substream, int up)
763f356c 1141{
98274f07
TI
1142 struct hdspm *hdspm;
1143 struct hdspm_midi *hmidi;
763f356c
TI
1144 unsigned long flags;
1145 u32 ie;
1146
ef5fa1a4 1147 hmidi = substream->rmidi->private_data;
763f356c 1148 hdspm = hmidi->hdspm;
ef5fa1a4
TI
1149 ie = hmidi->id ?
1150 HDSPM_Midi1InterruptEnable : HDSPM_Midi0InterruptEnable;
763f356c
TI
1151 spin_lock_irqsave (&hdspm->lock, flags);
1152 if (up) {
1153 if (!(hdspm->control_register & ie)) {
1154 snd_hdspm_flush_midi_input (hdspm, hmidi->id);
1155 hdspm->control_register |= ie;
1156 }
1157 } else {
1158 hdspm->control_register &= ~ie;
1159 }
1160
1161 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
1162 spin_unlock_irqrestore (&hdspm->lock, flags);
1163}
1164
1165static void snd_hdspm_midi_output_timer(unsigned long data)
1166{
98274f07 1167 struct hdspm_midi *hmidi = (struct hdspm_midi *) data;
763f356c
TI
1168 unsigned long flags;
1169
1170 snd_hdspm_midi_output_write(hmidi);
1171 spin_lock_irqsave (&hmidi->lock, flags);
1172
1173 /* this does not bump hmidi->istimer, because the
1174 kernel automatically removed the timer when it
1175 expired, and we are now adding it back, thus
1176 leaving istimer wherever it was set before.
1177 */
1178
1179 if (hmidi->istimer) {
1180 hmidi->timer.expires = 1 + jiffies;
1181 add_timer(&hmidi->timer);
1182 }
1183
1184 spin_unlock_irqrestore (&hmidi->lock, flags);
1185}
1186
ef5fa1a4
TI
1187static void
1188snd_hdspm_midi_output_trigger(struct snd_rawmidi_substream *substream, int up)
763f356c 1189{
98274f07 1190 struct hdspm_midi *hmidi;
763f356c
TI
1191 unsigned long flags;
1192
ef5fa1a4 1193 hmidi = substream->rmidi->private_data;
763f356c
TI
1194 spin_lock_irqsave (&hmidi->lock, flags);
1195 if (up) {
1196 if (!hmidi->istimer) {
1197 init_timer(&hmidi->timer);
1198 hmidi->timer.function = snd_hdspm_midi_output_timer;
1199 hmidi->timer.data = (unsigned long) hmidi;
1200 hmidi->timer.expires = 1 + jiffies;
1201 add_timer(&hmidi->timer);
1202 hmidi->istimer++;
1203 }
1204 } else {
ef5fa1a4 1205 if (hmidi->istimer && --hmidi->istimer <= 0)
763f356c 1206 del_timer (&hmidi->timer);
763f356c
TI
1207 }
1208 spin_unlock_irqrestore (&hmidi->lock, flags);
1209 if (up)
1210 snd_hdspm_midi_output_write(hmidi);
1211}
1212
98274f07 1213static int snd_hdspm_midi_input_open(struct snd_rawmidi_substream *substream)
763f356c 1214{
98274f07 1215 struct hdspm_midi *hmidi;
763f356c 1216
ef5fa1a4 1217 hmidi = substream->rmidi->private_data;
763f356c
TI
1218 spin_lock_irq (&hmidi->lock);
1219 snd_hdspm_flush_midi_input (hmidi->hdspm, hmidi->id);
1220 hmidi->input = substream;
1221 spin_unlock_irq (&hmidi->lock);
1222
1223 return 0;
1224}
1225
98274f07 1226static int snd_hdspm_midi_output_open(struct snd_rawmidi_substream *substream)
763f356c 1227{
98274f07 1228 struct hdspm_midi *hmidi;
763f356c 1229
ef5fa1a4 1230 hmidi = substream->rmidi->private_data;
763f356c
TI
1231 spin_lock_irq (&hmidi->lock);
1232 hmidi->output = substream;
1233 spin_unlock_irq (&hmidi->lock);
1234
1235 return 0;
1236}
1237
98274f07 1238static int snd_hdspm_midi_input_close(struct snd_rawmidi_substream *substream)
763f356c 1239{
98274f07 1240 struct hdspm_midi *hmidi;
763f356c
TI
1241
1242 snd_hdspm_midi_input_trigger (substream, 0);
1243
ef5fa1a4 1244 hmidi = substream->rmidi->private_data;
763f356c
TI
1245 spin_lock_irq (&hmidi->lock);
1246 hmidi->input = NULL;
1247 spin_unlock_irq (&hmidi->lock);
1248
1249 return 0;
1250}
1251
98274f07 1252static int snd_hdspm_midi_output_close(struct snd_rawmidi_substream *substream)
763f356c 1253{
98274f07 1254 struct hdspm_midi *hmidi;
763f356c
TI
1255
1256 snd_hdspm_midi_output_trigger (substream, 0);
1257
ef5fa1a4 1258 hmidi = substream->rmidi->private_data;
763f356c
TI
1259 spin_lock_irq (&hmidi->lock);
1260 hmidi->output = NULL;
1261 spin_unlock_irq (&hmidi->lock);
1262
1263 return 0;
1264}
1265
98274f07 1266static struct snd_rawmidi_ops snd_hdspm_midi_output =
763f356c
TI
1267{
1268 .open = snd_hdspm_midi_output_open,
1269 .close = snd_hdspm_midi_output_close,
1270 .trigger = snd_hdspm_midi_output_trigger,
1271};
1272
98274f07 1273static struct snd_rawmidi_ops snd_hdspm_midi_input =
763f356c
TI
1274{
1275 .open = snd_hdspm_midi_input_open,
1276 .close = snd_hdspm_midi_input_close,
1277 .trigger = snd_hdspm_midi_input_trigger,
1278};
1279
ef5fa1a4
TI
1280static int __devinit snd_hdspm_create_midi (struct snd_card *card,
1281 struct hdspm *hdspm, int id)
763f356c
TI
1282{
1283 int err;
1284 char buf[32];
1285
1286 hdspm->midi[id].id = id;
763f356c 1287 hdspm->midi[id].hdspm = hdspm;
763f356c
TI
1288 spin_lock_init (&hdspm->midi[id].lock);
1289
1290 sprintf (buf, "%s MIDI %d", card->shortname, id+1);
ef5fa1a4
TI
1291 err = snd_rawmidi_new (card, buf, id, 1, 1, &hdspm->midi[id].rmidi);
1292 if (err < 0)
763f356c
TI
1293 return err;
1294
1295 sprintf (hdspm->midi[id].rmidi->name, "%s MIDI %d", card->id, id+1);
1296 hdspm->midi[id].rmidi->private_data = &hdspm->midi[id];
1297
ef5fa1a4
TI
1298 snd_rawmidi_set_ops(hdspm->midi[id].rmidi, SNDRV_RAWMIDI_STREAM_OUTPUT,
1299 &snd_hdspm_midi_output);
1300 snd_rawmidi_set_ops(hdspm->midi[id].rmidi, SNDRV_RAWMIDI_STREAM_INPUT,
1301 &snd_hdspm_midi_input);
763f356c
TI
1302
1303 hdspm->midi[id].rmidi->info_flags |= SNDRV_RAWMIDI_INFO_OUTPUT |
1304 SNDRV_RAWMIDI_INFO_INPUT |
1305 SNDRV_RAWMIDI_INFO_DUPLEX;
1306
1307 return 0;
1308}
1309
1310
1311static void hdspm_midi_tasklet(unsigned long arg)
1312{
98274f07 1313 struct hdspm *hdspm = (struct hdspm *)arg;
763f356c
TI
1314
1315 if (hdspm->midi[0].pending)
1316 snd_hdspm_midi_input_read (&hdspm->midi[0]);
1317 if (hdspm->midi[1].pending)
1318 snd_hdspm_midi_input_read (&hdspm->midi[1]);
1319}
1320
1321
1322/*-----------------------------------------------------------------------------
1323 Status Interface
1324 ----------------------------------------------------------------------------*/
1325
1326/* get the system sample rate which is set */
1327
1328#define HDSPM_SYSTEM_SAMPLE_RATE(xname, xindex) \
67ed4161 1329{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
1330 .name = xname, \
1331 .index = xindex, \
1332 .access = SNDRV_CTL_ELEM_ACCESS_READ, \
1333 .info = snd_hdspm_info_system_sample_rate, \
1334 .get = snd_hdspm_get_system_sample_rate \
1335}
1336
98274f07
TI
1337static int snd_hdspm_info_system_sample_rate(struct snd_kcontrol *kcontrol,
1338 struct snd_ctl_elem_info *uinfo)
763f356c
TI
1339{
1340 uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
1341 uinfo->count = 1;
1342 return 0;
1343}
1344
98274f07
TI
1345static int snd_hdspm_get_system_sample_rate(struct snd_kcontrol *kcontrol,
1346 struct snd_ctl_elem_value *
763f356c
TI
1347 ucontrol)
1348{
98274f07 1349 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
1350
1351 ucontrol->value.enumerated.item[0] = hdspm->system_sample_rate;
1352 return 0;
1353}
1354
1355#define HDSPM_AUTOSYNC_SAMPLE_RATE(xname, xindex) \
67ed4161 1356{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
1357 .name = xname, \
1358 .index = xindex, \
1359 .access = SNDRV_CTL_ELEM_ACCESS_READ, \
1360 .info = snd_hdspm_info_autosync_sample_rate, \
1361 .get = snd_hdspm_get_autosync_sample_rate \
1362}
1363
98274f07
TI
1364static int snd_hdspm_info_autosync_sample_rate(struct snd_kcontrol *kcontrol,
1365 struct snd_ctl_elem_info *uinfo)
763f356c
TI
1366{
1367 static char *texts[] = { "32000", "44100", "48000",
1368 "64000", "88200", "96000",
1369 "128000", "176400", "192000",
1370 "None"
1371 };
1372 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
1373 uinfo->count = 1;
1374 uinfo->value.enumerated.items = 10;
1375 if (uinfo->value.enumerated.item >= uinfo->value.enumerated.items)
1376 uinfo->value.enumerated.item =
1377 uinfo->value.enumerated.items - 1;
1378 strcpy(uinfo->value.enumerated.name,
1379 texts[uinfo->value.enumerated.item]);
1380 return 0;
1381}
1382
98274f07
TI
1383static int snd_hdspm_get_autosync_sample_rate(struct snd_kcontrol *kcontrol,
1384 struct snd_ctl_elem_value *
763f356c
TI
1385 ucontrol)
1386{
98274f07 1387 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
1388
1389 switch (hdspm_external_sample_rate(hdspm)) {
1390 case 32000:
1391 ucontrol->value.enumerated.item[0] = 0;
1392 break;
1393 case 44100:
1394 ucontrol->value.enumerated.item[0] = 1;
1395 break;
1396 case 48000:
1397 ucontrol->value.enumerated.item[0] = 2;
1398 break;
1399 case 64000:
1400 ucontrol->value.enumerated.item[0] = 3;
1401 break;
1402 case 88200:
1403 ucontrol->value.enumerated.item[0] = 4;
1404 break;
1405 case 96000:
1406 ucontrol->value.enumerated.item[0] = 5;
1407 break;
1408 case 128000:
1409 ucontrol->value.enumerated.item[0] = 6;
1410 break;
1411 case 176400:
1412 ucontrol->value.enumerated.item[0] = 7;
1413 break;
1414 case 192000:
1415 ucontrol->value.enumerated.item[0] = 8;
1416 break;
1417
1418 default:
1419 ucontrol->value.enumerated.item[0] = 9;
1420 }
1421 return 0;
1422}
1423
1424#define HDSPM_SYSTEM_CLOCK_MODE(xname, xindex) \
67ed4161 1425{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
1426 .name = xname, \
1427 .index = xindex, \
1428 .access = SNDRV_CTL_ELEM_ACCESS_READ, \
1429 .info = snd_hdspm_info_system_clock_mode, \
1430 .get = snd_hdspm_get_system_clock_mode, \
1431}
1432
1433
1434
98274f07 1435static int hdspm_system_clock_mode(struct hdspm * hdspm)
763f356c
TI
1436{
1437 /* Always reflect the hardware info, rme is never wrong !!!! */
1438
1439 if (hdspm->control_register & HDSPM_ClockModeMaster)
1440 return 0;
1441 return 1;
1442}
1443
98274f07
TI
1444static int snd_hdspm_info_system_clock_mode(struct snd_kcontrol *kcontrol,
1445 struct snd_ctl_elem_info *uinfo)
763f356c
TI
1446{
1447 static char *texts[] = { "Master", "Slave" };
1448
1449 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
1450 uinfo->count = 1;
1451 uinfo->value.enumerated.items = 2;
1452 if (uinfo->value.enumerated.item >= uinfo->value.enumerated.items)
1453 uinfo->value.enumerated.item =
1454 uinfo->value.enumerated.items - 1;
1455 strcpy(uinfo->value.enumerated.name,
1456 texts[uinfo->value.enumerated.item]);
1457 return 0;
1458}
1459
98274f07
TI
1460static int snd_hdspm_get_system_clock_mode(struct snd_kcontrol *kcontrol,
1461 struct snd_ctl_elem_value *ucontrol)
763f356c 1462{
98274f07 1463 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
1464
1465 ucontrol->value.enumerated.item[0] =
1466 hdspm_system_clock_mode(hdspm);
1467 return 0;
1468}
1469
1470#define HDSPM_CLOCK_SOURCE(xname, xindex) \
67ed4161 1471{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
1472 .name = xname, \
1473 .index = xindex, \
1474 .info = snd_hdspm_info_clock_source, \
1475 .get = snd_hdspm_get_clock_source, \
1476 .put = snd_hdspm_put_clock_source \
1477}
1478
98274f07 1479static int hdspm_clock_source(struct hdspm * hdspm)
763f356c
TI
1480{
1481 if (hdspm->control_register & HDSPM_ClockModeMaster) {
1482 switch (hdspm->system_sample_rate) {
1483 case 32000:
1484 return 1;
1485 case 44100:
1486 return 2;
1487 case 48000:
1488 return 3;
1489 case 64000:
1490 return 4;
1491 case 88200:
1492 return 5;
1493 case 96000:
1494 return 6;
1495 case 128000:
1496 return 7;
1497 case 176400:
1498 return 8;
1499 case 192000:
1500 return 9;
1501 default:
1502 return 3;
1503 }
1504 } else {
1505 return 0;
1506 }
1507}
1508
98274f07 1509static int hdspm_set_clock_source(struct hdspm * hdspm, int mode)
763f356c
TI
1510{
1511 int rate;
1512 switch (mode) {
1513
1514 case HDSPM_CLOCK_SOURCE_AUTOSYNC:
1515 if (hdspm_external_sample_rate(hdspm) != 0) {
1516 hdspm->control_register &= ~HDSPM_ClockModeMaster;
1517 hdspm_write(hdspm, HDSPM_controlRegister,
1518 hdspm->control_register);
1519 return 0;
1520 }
1521 return -1;
1522 case HDSPM_CLOCK_SOURCE_INTERNAL_32KHZ:
1523 rate = 32000;
1524 break;
1525 case HDSPM_CLOCK_SOURCE_INTERNAL_44_1KHZ:
1526 rate = 44100;
1527 break;
1528 case HDSPM_CLOCK_SOURCE_INTERNAL_48KHZ:
1529 rate = 48000;
1530 break;
1531 case HDSPM_CLOCK_SOURCE_INTERNAL_64KHZ:
1532 rate = 64000;
1533 break;
1534 case HDSPM_CLOCK_SOURCE_INTERNAL_88_2KHZ:
1535 rate = 88200;
1536 break;
1537 case HDSPM_CLOCK_SOURCE_INTERNAL_96KHZ:
1538 rate = 96000;
1539 break;
1540 case HDSPM_CLOCK_SOURCE_INTERNAL_128KHZ:
1541 rate = 128000;
1542 break;
1543 case HDSPM_CLOCK_SOURCE_INTERNAL_176_4KHZ:
1544 rate = 176400;
1545 break;
1546 case HDSPM_CLOCK_SOURCE_INTERNAL_192KHZ:
1547 rate = 192000;
1548 break;
1549
1550 default:
1551 rate = 44100;
1552 }
1553 hdspm->control_register |= HDSPM_ClockModeMaster;
1554 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
1555 hdspm_set_rate(hdspm, rate, 1);
1556 return 0;
1557}
1558
98274f07
TI
1559static int snd_hdspm_info_clock_source(struct snd_kcontrol *kcontrol,
1560 struct snd_ctl_elem_info *uinfo)
763f356c
TI
1561{
1562 static char *texts[] = { "AutoSync",
1563 "Internal 32.0 kHz", "Internal 44.1 kHz",
1564 "Internal 48.0 kHz",
1565 "Internal 64.0 kHz", "Internal 88.2 kHz",
1566 "Internal 96.0 kHz",
1567 "Internal 128.0 kHz", "Internal 176.4 kHz",
1568 "Internal 192.0 kHz"
1569 };
1570
1571 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
1572 uinfo->count = 1;
1573 uinfo->value.enumerated.items = 10;
1574
1575 if (uinfo->value.enumerated.item >= uinfo->value.enumerated.items)
1576 uinfo->value.enumerated.item =
1577 uinfo->value.enumerated.items - 1;
1578
1579 strcpy(uinfo->value.enumerated.name,
1580 texts[uinfo->value.enumerated.item]);
1581
1582 return 0;
1583}
1584
98274f07
TI
1585static int snd_hdspm_get_clock_source(struct snd_kcontrol *kcontrol,
1586 struct snd_ctl_elem_value *ucontrol)
763f356c 1587{
98274f07 1588 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
1589
1590 ucontrol->value.enumerated.item[0] = hdspm_clock_source(hdspm);
1591 return 0;
1592}
1593
98274f07
TI
1594static int snd_hdspm_put_clock_source(struct snd_kcontrol *kcontrol,
1595 struct snd_ctl_elem_value *ucontrol)
763f356c 1596{
98274f07 1597 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
1598 int change;
1599 int val;
1600
1601 if (!snd_hdspm_use_is_exclusive(hdspm))
1602 return -EBUSY;
1603 val = ucontrol->value.enumerated.item[0];
1604 if (val < 0)
1605 val = 0;
6534599d
RB
1606 if (val > 9)
1607 val = 9;
763f356c
TI
1608 spin_lock_irq(&hdspm->lock);
1609 if (val != hdspm_clock_source(hdspm))
1610 change = (hdspm_set_clock_source(hdspm, val) == 0) ? 1 : 0;
1611 else
1612 change = 0;
1613 spin_unlock_irq(&hdspm->lock);
1614 return change;
1615}
1616
1617#define HDSPM_PREF_SYNC_REF(xname, xindex) \
67ed4161 1618{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
1619 .name = xname, \
1620 .index = xindex, \
1621 .info = snd_hdspm_info_pref_sync_ref, \
1622 .get = snd_hdspm_get_pref_sync_ref, \
1623 .put = snd_hdspm_put_pref_sync_ref \
1624}
1625
98274f07 1626static int hdspm_pref_sync_ref(struct hdspm * hdspm)
763f356c
TI
1627{
1628 /* Notice that this looks at the requested sync source,
1629 not the one actually in use.
1630 */
3cee5a60
RB
1631 if (hdspm->is_aes32) {
1632 switch (hdspm->control_register & HDSPM_SyncRefMask) {
1633 /* number gives AES index, except for 0 which
1634 corresponds to WordClock */
1635 case 0: return 0;
1636 case HDSPM_SyncRef0: return 1;
1637 case HDSPM_SyncRef1: return 2;
1638 case HDSPM_SyncRef1+HDSPM_SyncRef0: return 3;
1639 case HDSPM_SyncRef2: return 4;
1640 case HDSPM_SyncRef2+HDSPM_SyncRef0: return 5;
1641 case HDSPM_SyncRef2+HDSPM_SyncRef1: return 6;
1642 case HDSPM_SyncRef2+HDSPM_SyncRef1+HDSPM_SyncRef0: return 7;
1643 case HDSPM_SyncRef3: return 8;
1644 }
1645 } else {
1646 switch (hdspm->control_register & HDSPM_SyncRefMask) {
1647 case HDSPM_SyncRef_Word:
1648 return HDSPM_SYNC_FROM_WORD;
1649 case HDSPM_SyncRef_MADI:
1650 return HDSPM_SYNC_FROM_MADI;
1651 }
763f356c
TI
1652 }
1653
1654 return HDSPM_SYNC_FROM_WORD;
1655}
1656
98274f07 1657static int hdspm_set_pref_sync_ref(struct hdspm * hdspm, int pref)
763f356c
TI
1658{
1659 hdspm->control_register &= ~HDSPM_SyncRefMask;
1660
3cee5a60
RB
1661 if (hdspm->is_aes32) {
1662 switch (pref) {
1663 case 0:
1664 hdspm->control_register |= 0;
1665 break;
1666 case 1:
1667 hdspm->control_register |= HDSPM_SyncRef0;
1668 break;
1669 case 2:
1670 hdspm->control_register |= HDSPM_SyncRef1;
1671 break;
1672 case 3:
1673 hdspm->control_register |= HDSPM_SyncRef1+HDSPM_SyncRef0;
1674 break;
1675 case 4:
1676 hdspm->control_register |= HDSPM_SyncRef2;
1677 break;
1678 case 5:
1679 hdspm->control_register |= HDSPM_SyncRef2+HDSPM_SyncRef0;
1680 break;
1681 case 6:
1682 hdspm->control_register |= HDSPM_SyncRef2+HDSPM_SyncRef1;
1683 break;
1684 case 7:
ef5fa1a4
TI
1685 hdspm->control_register |=
1686 HDSPM_SyncRef2+HDSPM_SyncRef1+HDSPM_SyncRef0;
3cee5a60
RB
1687 break;
1688 case 8:
1689 hdspm->control_register |= HDSPM_SyncRef3;
1690 break;
1691 default:
1692 return -1;
1693 }
1694 } else {
1695 switch (pref) {
1696 case HDSPM_SYNC_FROM_MADI:
1697 hdspm->control_register |= HDSPM_SyncRef_MADI;
1698 break;
1699 case HDSPM_SYNC_FROM_WORD:
1700 hdspm->control_register |= HDSPM_SyncRef_Word;
1701 break;
1702 default:
1703 return -1;
1704 }
763f356c
TI
1705 }
1706 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
1707 return 0;
1708}
1709
98274f07
TI
1710static int snd_hdspm_info_pref_sync_ref(struct snd_kcontrol *kcontrol,
1711 struct snd_ctl_elem_info *uinfo)
763f356c 1712{
3cee5a60 1713 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 1714
3cee5a60
RB
1715 if (hdspm->is_aes32) {
1716 static char *texts[] = { "Word", "AES1", "AES2", "AES3",
1717 "AES4", "AES5", "AES6", "AES7", "AES8" };
763f356c 1718
3cee5a60
RB
1719 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
1720 uinfo->count = 1;
763f356c 1721
3cee5a60
RB
1722 uinfo->value.enumerated.items = 9;
1723
ef5fa1a4
TI
1724 if (uinfo->value.enumerated.item >=
1725 uinfo->value.enumerated.items)
3cee5a60
RB
1726 uinfo->value.enumerated.item =
1727 uinfo->value.enumerated.items - 1;
1728 strcpy(uinfo->value.enumerated.name,
1729 texts[uinfo->value.enumerated.item]);
1730 } else {
1731 static char *texts[] = { "Word", "MADI" };
1732
1733 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
1734 uinfo->count = 1;
1735
1736 uinfo->value.enumerated.items = 2;
1737
ef5fa1a4
TI
1738 if (uinfo->value.enumerated.item >=
1739 uinfo->value.enumerated.items)
3cee5a60
RB
1740 uinfo->value.enumerated.item =
1741 uinfo->value.enumerated.items - 1;
1742 strcpy(uinfo->value.enumerated.name,
1743 texts[uinfo->value.enumerated.item]);
1744 }
763f356c
TI
1745 return 0;
1746}
1747
98274f07
TI
1748static int snd_hdspm_get_pref_sync_ref(struct snd_kcontrol *kcontrol,
1749 struct snd_ctl_elem_value *ucontrol)
763f356c 1750{
98274f07 1751 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
1752
1753 ucontrol->value.enumerated.item[0] = hdspm_pref_sync_ref(hdspm);
1754 return 0;
1755}
1756
98274f07
TI
1757static int snd_hdspm_put_pref_sync_ref(struct snd_kcontrol *kcontrol,
1758 struct snd_ctl_elem_value *ucontrol)
763f356c 1759{
98274f07 1760 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
1761 int change, max;
1762 unsigned int val;
1763
3cee5a60 1764 max = hdspm->is_aes32 ? 9 : 2;
763f356c
TI
1765
1766 if (!snd_hdspm_use_is_exclusive(hdspm))
1767 return -EBUSY;
1768
1769 val = ucontrol->value.enumerated.item[0] % max;
1770
1771 spin_lock_irq(&hdspm->lock);
1772 change = (int) val != hdspm_pref_sync_ref(hdspm);
1773 hdspm_set_pref_sync_ref(hdspm, val);
1774 spin_unlock_irq(&hdspm->lock);
1775 return change;
1776}
1777
1778#define HDSPM_AUTOSYNC_REF(xname, xindex) \
67ed4161 1779{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
1780 .name = xname, \
1781 .index = xindex, \
1782 .access = SNDRV_CTL_ELEM_ACCESS_READ, \
1783 .info = snd_hdspm_info_autosync_ref, \
1784 .get = snd_hdspm_get_autosync_ref, \
1785}
1786
98274f07 1787static int hdspm_autosync_ref(struct hdspm * hdspm)
763f356c 1788{
3cee5a60
RB
1789 if (hdspm->is_aes32) {
1790 unsigned int status = hdspm_read(hdspm, HDSPM_statusRegister);
ef5fa1a4
TI
1791 unsigned int syncref = (status >> HDSPM_AES32_syncref_bit) &
1792 0xF;
3cee5a60
RB
1793 if (syncref == 0)
1794 return HDSPM_AES32_AUTOSYNC_FROM_WORD;
1795 if (syncref <= 8)
1796 return syncref;
1797 return HDSPM_AES32_AUTOSYNC_FROM_NONE;
1798 } else {
1799 /* This looks at the autosync selected sync reference */
1800 unsigned int status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
1801
1802 switch (status2 & HDSPM_SelSyncRefMask) {
1803 case HDSPM_SelSyncRef_WORD:
1804 return HDSPM_AUTOSYNC_FROM_WORD;
1805 case HDSPM_SelSyncRef_MADI:
1806 return HDSPM_AUTOSYNC_FROM_MADI;
1807 case HDSPM_SelSyncRef_NVALID:
1808 return HDSPM_AUTOSYNC_FROM_NONE;
1809 default:
1810 return 0;
1811 }
763f356c 1812
763f356c
TI
1813 return 0;
1814 }
763f356c
TI
1815}
1816
98274f07
TI
1817static int snd_hdspm_info_autosync_ref(struct snd_kcontrol *kcontrol,
1818 struct snd_ctl_elem_info *uinfo)
763f356c 1819{
3cee5a60 1820 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 1821
3cee5a60
RB
1822 if (hdspm->is_aes32) {
1823 static char *texts[] = { "WordClock", "AES1", "AES2", "AES3",
1824 "AES4", "AES5", "AES6", "AES7", "AES8", "None"};
1825
1826 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
1827 uinfo->count = 1;
1828 uinfo->value.enumerated.items = 10;
ef5fa1a4
TI
1829 if (uinfo->value.enumerated.item >=
1830 uinfo->value.enumerated.items)
3cee5a60
RB
1831 uinfo->value.enumerated.item =
1832 uinfo->value.enumerated.items - 1;
1833 strcpy(uinfo->value.enumerated.name,
1834 texts[uinfo->value.enumerated.item]);
ef5fa1a4 1835 } else {
3cee5a60
RB
1836 static char *texts[] = { "WordClock", "MADI", "None" };
1837
1838 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
1839 uinfo->count = 1;
1840 uinfo->value.enumerated.items = 3;
ef5fa1a4
TI
1841 if (uinfo->value.enumerated.item >=
1842 uinfo->value.enumerated.items)
3cee5a60
RB
1843 uinfo->value.enumerated.item =
1844 uinfo->value.enumerated.items - 1;
1845 strcpy(uinfo->value.enumerated.name,
1846 texts[uinfo->value.enumerated.item]);
1847 }
763f356c
TI
1848 return 0;
1849}
1850
98274f07
TI
1851static int snd_hdspm_get_autosync_ref(struct snd_kcontrol *kcontrol,
1852 struct snd_ctl_elem_value *ucontrol)
763f356c 1853{
98274f07 1854 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 1855
6534599d 1856 ucontrol->value.enumerated.item[0] = hdspm_autosync_ref(hdspm);
763f356c
TI
1857 return 0;
1858}
1859
1860#define HDSPM_LINE_OUT(xname, xindex) \
67ed4161 1861{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
1862 .name = xname, \
1863 .index = xindex, \
1864 .info = snd_hdspm_info_line_out, \
1865 .get = snd_hdspm_get_line_out, \
1866 .put = snd_hdspm_put_line_out \
1867}
1868
98274f07 1869static int hdspm_line_out(struct hdspm * hdspm)
763f356c
TI
1870{
1871 return (hdspm->control_register & HDSPM_LineOut) ? 1 : 0;
1872}
1873
1874
98274f07 1875static int hdspm_set_line_output(struct hdspm * hdspm, int out)
763f356c
TI
1876{
1877 if (out)
1878 hdspm->control_register |= HDSPM_LineOut;
1879 else
1880 hdspm->control_register &= ~HDSPM_LineOut;
1881 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
1882
1883 return 0;
1884}
1885
a5ce8890 1886#define snd_hdspm_info_line_out snd_ctl_boolean_mono_info
763f356c 1887
98274f07
TI
1888static int snd_hdspm_get_line_out(struct snd_kcontrol *kcontrol,
1889 struct snd_ctl_elem_value *ucontrol)
763f356c 1890{
98274f07 1891 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
1892
1893 spin_lock_irq(&hdspm->lock);
1894 ucontrol->value.integer.value[0] = hdspm_line_out(hdspm);
1895 spin_unlock_irq(&hdspm->lock);
1896 return 0;
1897}
1898
98274f07
TI
1899static int snd_hdspm_put_line_out(struct snd_kcontrol *kcontrol,
1900 struct snd_ctl_elem_value *ucontrol)
763f356c 1901{
98274f07 1902 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
1903 int change;
1904 unsigned int val;
1905
1906 if (!snd_hdspm_use_is_exclusive(hdspm))
1907 return -EBUSY;
1908 val = ucontrol->value.integer.value[0] & 1;
1909 spin_lock_irq(&hdspm->lock);
1910 change = (int) val != hdspm_line_out(hdspm);
1911 hdspm_set_line_output(hdspm, val);
1912 spin_unlock_irq(&hdspm->lock);
1913 return change;
1914}
1915
1916#define HDSPM_TX_64(xname, xindex) \
67ed4161 1917{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
1918 .name = xname, \
1919 .index = xindex, \
1920 .info = snd_hdspm_info_tx_64, \
1921 .get = snd_hdspm_get_tx_64, \
1922 .put = snd_hdspm_put_tx_64 \
1923}
1924
98274f07 1925static int hdspm_tx_64(struct hdspm * hdspm)
763f356c
TI
1926{
1927 return (hdspm->control_register & HDSPM_TX_64ch) ? 1 : 0;
1928}
1929
98274f07 1930static int hdspm_set_tx_64(struct hdspm * hdspm, int out)
763f356c
TI
1931{
1932 if (out)
1933 hdspm->control_register |= HDSPM_TX_64ch;
1934 else
1935 hdspm->control_register &= ~HDSPM_TX_64ch;
1936 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
1937
1938 return 0;
1939}
1940
a5ce8890 1941#define snd_hdspm_info_tx_64 snd_ctl_boolean_mono_info
763f356c 1942
98274f07
TI
1943static int snd_hdspm_get_tx_64(struct snd_kcontrol *kcontrol,
1944 struct snd_ctl_elem_value *ucontrol)
763f356c 1945{
98274f07 1946 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
1947
1948 spin_lock_irq(&hdspm->lock);
1949 ucontrol->value.integer.value[0] = hdspm_tx_64(hdspm);
1950 spin_unlock_irq(&hdspm->lock);
1951 return 0;
1952}
1953
98274f07
TI
1954static int snd_hdspm_put_tx_64(struct snd_kcontrol *kcontrol,
1955 struct snd_ctl_elem_value *ucontrol)
763f356c 1956{
98274f07 1957 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
1958 int change;
1959 unsigned int val;
1960
1961 if (!snd_hdspm_use_is_exclusive(hdspm))
1962 return -EBUSY;
1963 val = ucontrol->value.integer.value[0] & 1;
1964 spin_lock_irq(&hdspm->lock);
1965 change = (int) val != hdspm_tx_64(hdspm);
1966 hdspm_set_tx_64(hdspm, val);
1967 spin_unlock_irq(&hdspm->lock);
1968 return change;
1969}
1970
1971#define HDSPM_C_TMS(xname, xindex) \
67ed4161 1972{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
1973 .name = xname, \
1974 .index = xindex, \
1975 .info = snd_hdspm_info_c_tms, \
1976 .get = snd_hdspm_get_c_tms, \
1977 .put = snd_hdspm_put_c_tms \
1978}
1979
98274f07 1980static int hdspm_c_tms(struct hdspm * hdspm)
763f356c
TI
1981{
1982 return (hdspm->control_register & HDSPM_clr_tms) ? 1 : 0;
1983}
1984
98274f07 1985static int hdspm_set_c_tms(struct hdspm * hdspm, int out)
763f356c
TI
1986{
1987 if (out)
1988 hdspm->control_register |= HDSPM_clr_tms;
1989 else
1990 hdspm->control_register &= ~HDSPM_clr_tms;
1991 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
1992
1993 return 0;
1994}
1995
a5ce8890 1996#define snd_hdspm_info_c_tms snd_ctl_boolean_mono_info
763f356c 1997
98274f07
TI
1998static int snd_hdspm_get_c_tms(struct snd_kcontrol *kcontrol,
1999 struct snd_ctl_elem_value *ucontrol)
763f356c 2000{
98274f07 2001 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2002
2003 spin_lock_irq(&hdspm->lock);
2004 ucontrol->value.integer.value[0] = hdspm_c_tms(hdspm);
2005 spin_unlock_irq(&hdspm->lock);
2006 return 0;
2007}
2008
98274f07
TI
2009static int snd_hdspm_put_c_tms(struct snd_kcontrol *kcontrol,
2010 struct snd_ctl_elem_value *ucontrol)
763f356c 2011{
98274f07 2012 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2013 int change;
2014 unsigned int val;
2015
2016 if (!snd_hdspm_use_is_exclusive(hdspm))
2017 return -EBUSY;
2018 val = ucontrol->value.integer.value[0] & 1;
2019 spin_lock_irq(&hdspm->lock);
2020 change = (int) val != hdspm_c_tms(hdspm);
2021 hdspm_set_c_tms(hdspm, val);
2022 spin_unlock_irq(&hdspm->lock);
2023 return change;
2024}
2025
2026#define HDSPM_SAFE_MODE(xname, xindex) \
67ed4161 2027{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
2028 .name = xname, \
2029 .index = xindex, \
2030 .info = snd_hdspm_info_safe_mode, \
2031 .get = snd_hdspm_get_safe_mode, \
2032 .put = snd_hdspm_put_safe_mode \
2033}
2034
3cee5a60
RB
2035static int hdspm_safe_mode(struct hdspm * hdspm)
2036{
2037 return (hdspm->control_register & HDSPM_AutoInp) ? 1 : 0;
2038}
2039
2040static int hdspm_set_safe_mode(struct hdspm * hdspm, int out)
2041{
2042 if (out)
2043 hdspm->control_register |= HDSPM_AutoInp;
2044 else
2045 hdspm->control_register &= ~HDSPM_AutoInp;
2046 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
2047
2048 return 0;
2049}
2050
a5ce8890 2051#define snd_hdspm_info_safe_mode snd_ctl_boolean_mono_info
3cee5a60
RB
2052
2053static int snd_hdspm_get_safe_mode(struct snd_kcontrol *kcontrol,
2054 struct snd_ctl_elem_value *ucontrol)
2055{
2056 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2057
2058 spin_lock_irq(&hdspm->lock);
2059 ucontrol->value.integer.value[0] = hdspm_safe_mode(hdspm);
2060 spin_unlock_irq(&hdspm->lock);
2061 return 0;
2062}
2063
2064static int snd_hdspm_put_safe_mode(struct snd_kcontrol *kcontrol,
2065 struct snd_ctl_elem_value *ucontrol)
2066{
2067 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2068 int change;
2069 unsigned int val;
2070
2071 if (!snd_hdspm_use_is_exclusive(hdspm))
2072 return -EBUSY;
2073 val = ucontrol->value.integer.value[0] & 1;
2074 spin_lock_irq(&hdspm->lock);
2075 change = (int) val != hdspm_safe_mode(hdspm);
2076 hdspm_set_safe_mode(hdspm, val);
2077 spin_unlock_irq(&hdspm->lock);
2078 return change;
2079}
2080
2081#define HDSPM_EMPHASIS(xname, xindex) \
2082{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2083 .name = xname, \
2084 .index = xindex, \
2085 .info = snd_hdspm_info_emphasis, \
2086 .get = snd_hdspm_get_emphasis, \
2087 .put = snd_hdspm_put_emphasis \
2088}
2089
2090static int hdspm_emphasis(struct hdspm * hdspm)
2091{
2092 return (hdspm->control_register & HDSPM_Emphasis) ? 1 : 0;
2093}
2094
2095static int hdspm_set_emphasis(struct hdspm * hdspm, int emp)
2096{
2097 if (emp)
2098 hdspm->control_register |= HDSPM_Emphasis;
2099 else
2100 hdspm->control_register &= ~HDSPM_Emphasis;
2101 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
2102
2103 return 0;
2104}
2105
a5ce8890 2106#define snd_hdspm_info_emphasis snd_ctl_boolean_mono_info
3cee5a60
RB
2107
2108static int snd_hdspm_get_emphasis(struct snd_kcontrol *kcontrol,
2109 struct snd_ctl_elem_value *ucontrol)
2110{
2111 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2112
2113 spin_lock_irq(&hdspm->lock);
2114 ucontrol->value.enumerated.item[0] = hdspm_emphasis(hdspm);
2115 spin_unlock_irq(&hdspm->lock);
2116 return 0;
2117}
2118
2119static int snd_hdspm_put_emphasis(struct snd_kcontrol *kcontrol,
2120 struct snd_ctl_elem_value *ucontrol)
2121{
2122 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2123 int change;
2124 unsigned int val;
2125
2126 if (!snd_hdspm_use_is_exclusive(hdspm))
2127 return -EBUSY;
2128 val = ucontrol->value.integer.value[0] & 1;
2129 spin_lock_irq(&hdspm->lock);
2130 change = (int) val != hdspm_emphasis(hdspm);
2131 hdspm_set_emphasis(hdspm, val);
2132 spin_unlock_irq(&hdspm->lock);
2133 return change;
2134}
2135
2136#define HDSPM_DOLBY(xname, xindex) \
2137{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2138 .name = xname, \
2139 .index = xindex, \
2140 .info = snd_hdspm_info_dolby, \
2141 .get = snd_hdspm_get_dolby, \
2142 .put = snd_hdspm_put_dolby \
2143}
2144
2145static int hdspm_dolby(struct hdspm * hdspm)
2146{
2147 return (hdspm->control_register & HDSPM_Dolby) ? 1 : 0;
2148}
2149
2150static int hdspm_set_dolby(struct hdspm * hdspm, int dol)
2151{
2152 if (dol)
2153 hdspm->control_register |= HDSPM_Dolby;
2154 else
2155 hdspm->control_register &= ~HDSPM_Dolby;
2156 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
2157
2158 return 0;
2159}
2160
a5ce8890 2161#define snd_hdspm_info_dolby snd_ctl_boolean_mono_info
3cee5a60
RB
2162
2163static int snd_hdspm_get_dolby(struct snd_kcontrol *kcontrol,
2164 struct snd_ctl_elem_value *ucontrol)
2165{
2166 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2167
2168 spin_lock_irq(&hdspm->lock);
2169 ucontrol->value.enumerated.item[0] = hdspm_dolby(hdspm);
2170 spin_unlock_irq(&hdspm->lock);
2171 return 0;
2172}
2173
2174static int snd_hdspm_put_dolby(struct snd_kcontrol *kcontrol,
2175 struct snd_ctl_elem_value *ucontrol)
2176{
2177 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2178 int change;
2179 unsigned int val;
2180
2181 if (!snd_hdspm_use_is_exclusive(hdspm))
2182 return -EBUSY;
2183 val = ucontrol->value.integer.value[0] & 1;
2184 spin_lock_irq(&hdspm->lock);
2185 change = (int) val != hdspm_dolby(hdspm);
2186 hdspm_set_dolby(hdspm, val);
2187 spin_unlock_irq(&hdspm->lock);
2188 return change;
2189}
2190
2191#define HDSPM_PROFESSIONAL(xname, xindex) \
2192{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2193 .name = xname, \
2194 .index = xindex, \
2195 .info = snd_hdspm_info_professional, \
2196 .get = snd_hdspm_get_professional, \
2197 .put = snd_hdspm_put_professional \
2198}
2199
2200static int hdspm_professional(struct hdspm * hdspm)
2201{
2202 return (hdspm->control_register & HDSPM_Professional) ? 1 : 0;
2203}
2204
2205static int hdspm_set_professional(struct hdspm * hdspm, int dol)
2206{
2207 if (dol)
2208 hdspm->control_register |= HDSPM_Professional;
2209 else
2210 hdspm->control_register &= ~HDSPM_Professional;
2211 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
2212
2213 return 0;
2214}
2215
a5ce8890 2216#define snd_hdspm_info_professional snd_ctl_boolean_mono_info
3cee5a60
RB
2217
2218static int snd_hdspm_get_professional(struct snd_kcontrol *kcontrol,
2219 struct snd_ctl_elem_value *ucontrol)
2220{
2221 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2222
2223 spin_lock_irq(&hdspm->lock);
2224 ucontrol->value.enumerated.item[0] = hdspm_professional(hdspm);
2225 spin_unlock_irq(&hdspm->lock);
2226 return 0;
2227}
2228
2229static int snd_hdspm_put_professional(struct snd_kcontrol *kcontrol,
2230 struct snd_ctl_elem_value *ucontrol)
2231{
2232 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2233 int change;
2234 unsigned int val;
2235
2236 if (!snd_hdspm_use_is_exclusive(hdspm))
2237 return -EBUSY;
2238 val = ucontrol->value.integer.value[0] & 1;
2239 spin_lock_irq(&hdspm->lock);
2240 change = (int) val != hdspm_professional(hdspm);
2241 hdspm_set_professional(hdspm, val);
2242 spin_unlock_irq(&hdspm->lock);
2243 return change;
2244}
2245
2246#define HDSPM_INPUT_SELECT(xname, xindex) \
2247{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2248 .name = xname, \
2249 .index = xindex, \
2250 .info = snd_hdspm_info_input_select, \
2251 .get = snd_hdspm_get_input_select, \
2252 .put = snd_hdspm_put_input_select \
2253}
2254
2255static int hdspm_input_select(struct hdspm * hdspm)
2256{
2257 return (hdspm->control_register & HDSPM_InputSelect0) ? 1 : 0;
2258}
2259
2260static int hdspm_set_input_select(struct hdspm * hdspm, int out)
2261{
2262 if (out)
2263 hdspm->control_register |= HDSPM_InputSelect0;
2264 else
2265 hdspm->control_register &= ~HDSPM_InputSelect0;
2266 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
2267
2268 return 0;
2269}
2270
2271static int snd_hdspm_info_input_select(struct snd_kcontrol *kcontrol,
2272 struct snd_ctl_elem_info *uinfo)
2273{
2274 static char *texts[] = { "optical", "coaxial" };
2275
2276 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
2277 uinfo->count = 1;
2278 uinfo->value.enumerated.items = 2;
2279
2280 if (uinfo->value.enumerated.item >= uinfo->value.enumerated.items)
2281 uinfo->value.enumerated.item =
2282 uinfo->value.enumerated.items - 1;
2283 strcpy(uinfo->value.enumerated.name,
2284 texts[uinfo->value.enumerated.item]);
2285
2286 return 0;
2287}
2288
2289static int snd_hdspm_get_input_select(struct snd_kcontrol *kcontrol,
2290 struct snd_ctl_elem_value *ucontrol)
2291{
2292 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2293
2294 spin_lock_irq(&hdspm->lock);
2295 ucontrol->value.enumerated.item[0] = hdspm_input_select(hdspm);
2296 spin_unlock_irq(&hdspm->lock);
2297 return 0;
2298}
2299
2300static int snd_hdspm_put_input_select(struct snd_kcontrol *kcontrol,
2301 struct snd_ctl_elem_value *ucontrol)
2302{
2303 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2304 int change;
2305 unsigned int val;
2306
2307 if (!snd_hdspm_use_is_exclusive(hdspm))
2308 return -EBUSY;
2309 val = ucontrol->value.integer.value[0] & 1;
2310 spin_lock_irq(&hdspm->lock);
2311 change = (int) val != hdspm_input_select(hdspm);
2312 hdspm_set_input_select(hdspm, val);
2313 spin_unlock_irq(&hdspm->lock);
2314 return change;
2315}
2316
2317#define HDSPM_DS_WIRE(xname, xindex) \
2318{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2319 .name = xname, \
2320 .index = xindex, \
2321 .info = snd_hdspm_info_ds_wire, \
2322 .get = snd_hdspm_get_ds_wire, \
2323 .put = snd_hdspm_put_ds_wire \
2324}
2325
2326static int hdspm_ds_wire(struct hdspm * hdspm)
763f356c 2327{
3cee5a60 2328 return (hdspm->control_register & HDSPM_DS_DoubleWire) ? 1 : 0;
763f356c
TI
2329}
2330
3cee5a60 2331static int hdspm_set_ds_wire(struct hdspm * hdspm, int ds)
763f356c 2332{
3cee5a60
RB
2333 if (ds)
2334 hdspm->control_register |= HDSPM_DS_DoubleWire;
763f356c 2335 else
3cee5a60 2336 hdspm->control_register &= ~HDSPM_DS_DoubleWire;
763f356c
TI
2337 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
2338
2339 return 0;
2340}
2341
3cee5a60
RB
2342static int snd_hdspm_info_ds_wire(struct snd_kcontrol *kcontrol,
2343 struct snd_ctl_elem_info *uinfo)
763f356c 2344{
3cee5a60
RB
2345 static char *texts[] = { "Single", "Double" };
2346
2347 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
763f356c 2348 uinfo->count = 1;
3cee5a60
RB
2349 uinfo->value.enumerated.items = 2;
2350
2351 if (uinfo->value.enumerated.item >= uinfo->value.enumerated.items)
2352 uinfo->value.enumerated.item =
2353 uinfo->value.enumerated.items - 1;
2354 strcpy(uinfo->value.enumerated.name,
2355 texts[uinfo->value.enumerated.item]);
2356
763f356c
TI
2357 return 0;
2358}
2359
3cee5a60
RB
2360static int snd_hdspm_get_ds_wire(struct snd_kcontrol *kcontrol,
2361 struct snd_ctl_elem_value *ucontrol)
763f356c 2362{
98274f07 2363 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2364
2365 spin_lock_irq(&hdspm->lock);
3cee5a60 2366 ucontrol->value.enumerated.item[0] = hdspm_ds_wire(hdspm);
763f356c
TI
2367 spin_unlock_irq(&hdspm->lock);
2368 return 0;
2369}
2370
3cee5a60
RB
2371static int snd_hdspm_put_ds_wire(struct snd_kcontrol *kcontrol,
2372 struct snd_ctl_elem_value *ucontrol)
763f356c 2373{
98274f07 2374 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2375 int change;
2376 unsigned int val;
2377
2378 if (!snd_hdspm_use_is_exclusive(hdspm))
2379 return -EBUSY;
2380 val = ucontrol->value.integer.value[0] & 1;
2381 spin_lock_irq(&hdspm->lock);
3cee5a60
RB
2382 change = (int) val != hdspm_ds_wire(hdspm);
2383 hdspm_set_ds_wire(hdspm, val);
763f356c
TI
2384 spin_unlock_irq(&hdspm->lock);
2385 return change;
2386}
2387
3cee5a60 2388#define HDSPM_QS_WIRE(xname, xindex) \
67ed4161 2389{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
2390 .name = xname, \
2391 .index = xindex, \
3cee5a60
RB
2392 .info = snd_hdspm_info_qs_wire, \
2393 .get = snd_hdspm_get_qs_wire, \
2394 .put = snd_hdspm_put_qs_wire \
763f356c
TI
2395}
2396
3cee5a60 2397static int hdspm_qs_wire(struct hdspm * hdspm)
763f356c 2398{
3cee5a60
RB
2399 if (hdspm->control_register & HDSPM_QS_DoubleWire)
2400 return 1;
2401 if (hdspm->control_register & HDSPM_QS_QuadWire)
2402 return 2;
2403 return 0;
763f356c
TI
2404}
2405
3cee5a60 2406static int hdspm_set_qs_wire(struct hdspm * hdspm, int mode)
763f356c 2407{
3cee5a60
RB
2408 hdspm->control_register &= ~(HDSPM_QS_DoubleWire | HDSPM_QS_QuadWire);
2409 switch (mode) {
2410 case 0:
2411 break;
2412 case 1:
2413 hdspm->control_register |= HDSPM_QS_DoubleWire;
2414 break;
2415 case 2:
2416 hdspm->control_register |= HDSPM_QS_QuadWire;
2417 break;
2418 }
763f356c
TI
2419 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
2420
2421 return 0;
2422}
2423
3cee5a60 2424static int snd_hdspm_info_qs_wire(struct snd_kcontrol *kcontrol,
98274f07 2425 struct snd_ctl_elem_info *uinfo)
763f356c 2426{
3cee5a60 2427 static char *texts[] = { "Single", "Double", "Quad" };
763f356c
TI
2428
2429 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
2430 uinfo->count = 1;
3cee5a60 2431 uinfo->value.enumerated.items = 3;
763f356c
TI
2432
2433 if (uinfo->value.enumerated.item >= uinfo->value.enumerated.items)
2434 uinfo->value.enumerated.item =
2435 uinfo->value.enumerated.items - 1;
2436 strcpy(uinfo->value.enumerated.name,
2437 texts[uinfo->value.enumerated.item]);
2438
2439 return 0;
2440}
2441
3cee5a60 2442static int snd_hdspm_get_qs_wire(struct snd_kcontrol *kcontrol,
98274f07 2443 struct snd_ctl_elem_value *ucontrol)
763f356c 2444{
98274f07 2445 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2446
2447 spin_lock_irq(&hdspm->lock);
3cee5a60 2448 ucontrol->value.enumerated.item[0] = hdspm_qs_wire(hdspm);
763f356c
TI
2449 spin_unlock_irq(&hdspm->lock);
2450 return 0;
2451}
2452
3cee5a60 2453static int snd_hdspm_put_qs_wire(struct snd_kcontrol *kcontrol,
98274f07 2454 struct snd_ctl_elem_value *ucontrol)
763f356c 2455{
98274f07 2456 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 2457 int change;
3cee5a60 2458 int val;
763f356c
TI
2459
2460 if (!snd_hdspm_use_is_exclusive(hdspm))
2461 return -EBUSY;
3cee5a60
RB
2462 val = ucontrol->value.integer.value[0];
2463 if (val < 0)
2464 val = 0;
2465 if (val > 2)
2466 val = 2;
763f356c 2467 spin_lock_irq(&hdspm->lock);
ef5fa1a4 2468 change = val != hdspm_qs_wire(hdspm);
3cee5a60 2469 hdspm_set_qs_wire(hdspm, val);
763f356c
TI
2470 spin_unlock_irq(&hdspm->lock);
2471 return change;
2472}
2473
2474/* Simple Mixer
2475 deprecated since to much faders ???
2476 MIXER interface says output (source, destination, value)
2477 where source > MAX_channels are playback channels
2478 on MADICARD
2479 - playback mixer matrix: [channelout+64] [output] [value]
2480 - input(thru) mixer matrix: [channelin] [output] [value]
2481 (better do 2 kontrols for seperation ?)
2482*/
2483
2484#define HDSPM_MIXER(xname, xindex) \
2485{ .iface = SNDRV_CTL_ELEM_IFACE_HWDEP, \
2486 .name = xname, \
2487 .index = xindex, \
67ed4161 2488 .device = 0, \
763f356c
TI
2489 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE | \
2490 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
2491 .info = snd_hdspm_info_mixer, \
2492 .get = snd_hdspm_get_mixer, \
2493 .put = snd_hdspm_put_mixer \
2494}
2495
98274f07
TI
2496static int snd_hdspm_info_mixer(struct snd_kcontrol *kcontrol,
2497 struct snd_ctl_elem_info *uinfo)
763f356c
TI
2498{
2499 uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
2500 uinfo->count = 3;
2501 uinfo->value.integer.min = 0;
2502 uinfo->value.integer.max = 65535;
2503 uinfo->value.integer.step = 1;
2504 return 0;
2505}
2506
98274f07
TI
2507static int snd_hdspm_get_mixer(struct snd_kcontrol *kcontrol,
2508 struct snd_ctl_elem_value *ucontrol)
763f356c 2509{
98274f07 2510 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2511 int source;
2512 int destination;
2513
2514 source = ucontrol->value.integer.value[0];
2515 if (source < 0)
2516 source = 0;
2517 else if (source >= 2 * HDSPM_MAX_CHANNELS)
2518 source = 2 * HDSPM_MAX_CHANNELS - 1;
2519
2520 destination = ucontrol->value.integer.value[1];
2521 if (destination < 0)
2522 destination = 0;
2523 else if (destination >= HDSPM_MAX_CHANNELS)
2524 destination = HDSPM_MAX_CHANNELS - 1;
2525
2526 spin_lock_irq(&hdspm->lock);
2527 if (source >= HDSPM_MAX_CHANNELS)
2528 ucontrol->value.integer.value[2] =
2529 hdspm_read_pb_gain(hdspm, destination,
2530 source - HDSPM_MAX_CHANNELS);
2531 else
2532 ucontrol->value.integer.value[2] =
2533 hdspm_read_in_gain(hdspm, destination, source);
2534
2535 spin_unlock_irq(&hdspm->lock);
2536
2537 return 0;
2538}
2539
98274f07
TI
2540static int snd_hdspm_put_mixer(struct snd_kcontrol *kcontrol,
2541 struct snd_ctl_elem_value *ucontrol)
763f356c 2542{
98274f07 2543 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2544 int change;
2545 int source;
2546 int destination;
2547 int gain;
2548
2549 if (!snd_hdspm_use_is_exclusive(hdspm))
2550 return -EBUSY;
2551
2552 source = ucontrol->value.integer.value[0];
2553 destination = ucontrol->value.integer.value[1];
2554
2555 if (source < 0 || source >= 2 * HDSPM_MAX_CHANNELS)
2556 return -1;
2557 if (destination < 0 || destination >= HDSPM_MAX_CHANNELS)
2558 return -1;
2559
2560 gain = ucontrol->value.integer.value[2];
2561
2562 spin_lock_irq(&hdspm->lock);
2563
2564 if (source >= HDSPM_MAX_CHANNELS)
2565 change = gain != hdspm_read_pb_gain(hdspm, destination,
2566 source -
2567 HDSPM_MAX_CHANNELS);
2568 else
ef5fa1a4
TI
2569 change = gain != hdspm_read_in_gain(hdspm, destination,
2570 source);
763f356c
TI
2571
2572 if (change) {
2573 if (source >= HDSPM_MAX_CHANNELS)
2574 hdspm_write_pb_gain(hdspm, destination,
2575 source - HDSPM_MAX_CHANNELS,
2576 gain);
2577 else
2578 hdspm_write_in_gain(hdspm, destination, source,
2579 gain);
2580 }
2581 spin_unlock_irq(&hdspm->lock);
2582
2583 return change;
2584}
2585
2586/* The simple mixer control(s) provide gain control for the
2587 basic 1:1 mappings of playback streams to output
2588 streams.
2589*/
2590
2591#define HDSPM_PLAYBACK_MIXER \
2592{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2593 .access = SNDRV_CTL_ELEM_ACCESS_READ | SNDRV_CTL_ELEM_ACCESS_WRITE | \
2594 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
2595 .info = snd_hdspm_info_playback_mixer, \
2596 .get = snd_hdspm_get_playback_mixer, \
2597 .put = snd_hdspm_put_playback_mixer \
2598}
2599
98274f07
TI
2600static int snd_hdspm_info_playback_mixer(struct snd_kcontrol *kcontrol,
2601 struct snd_ctl_elem_info *uinfo)
763f356c
TI
2602{
2603 uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
2604 uinfo->count = 1;
2605 uinfo->value.integer.min = 0;
2606 uinfo->value.integer.max = 65536;
2607 uinfo->value.integer.step = 1;
2608 return 0;
2609}
2610
98274f07
TI
2611static int snd_hdspm_get_playback_mixer(struct snd_kcontrol *kcontrol,
2612 struct snd_ctl_elem_value *ucontrol)
763f356c 2613{
98274f07 2614 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2615 int channel;
2616 int mapped_channel;
2617
2618 channel = ucontrol->id.index - 1;
2619
2620 snd_assert(channel >= 0
2621 || channel < HDSPM_MAX_CHANNELS, return -EINVAL);
2622
ef5fa1a4
TI
2623 mapped_channel = hdspm->channel_map[channel];
2624 if (mapped_channel < 0)
763f356c
TI
2625 return -EINVAL;
2626
2627 spin_lock_irq(&hdspm->lock);
2628 ucontrol->value.integer.value[0] =
2629 hdspm_read_pb_gain(hdspm, mapped_channel, mapped_channel);
2630 spin_unlock_irq(&hdspm->lock);
2631
ef5fa1a4
TI
2632 /*
2633 snd_printdd("get pb mixer index %d, channel %d, mapped_channel %d, "
2634 "value %d\n",
2635 ucontrol->id.index, channel, mapped_channel,
2636 ucontrol->value.integer.value[0]);
2637 */
763f356c
TI
2638 return 0;
2639}
2640
98274f07
TI
2641static int snd_hdspm_put_playback_mixer(struct snd_kcontrol *kcontrol,
2642 struct snd_ctl_elem_value *ucontrol)
763f356c 2643{
98274f07 2644 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2645 int change;
2646 int channel;
2647 int mapped_channel;
2648 int gain;
2649
2650 if (!snd_hdspm_use_is_exclusive(hdspm))
2651 return -EBUSY;
2652
2653 channel = ucontrol->id.index - 1;
2654
2655 snd_assert(channel >= 0
2656 || channel < HDSPM_MAX_CHANNELS, return -EINVAL);
2657
ef5fa1a4
TI
2658 mapped_channel = hdspm->channel_map[channel];
2659 if (mapped_channel < 0)
763f356c
TI
2660 return -EINVAL;
2661
2662 gain = ucontrol->value.integer.value[0];
2663
2664 spin_lock_irq(&hdspm->lock);
2665 change =
2666 gain != hdspm_read_pb_gain(hdspm, mapped_channel,
2667 mapped_channel);
2668 if (change)
2669 hdspm_write_pb_gain(hdspm, mapped_channel, mapped_channel,
2670 gain);
2671 spin_unlock_irq(&hdspm->lock);
2672 return change;
2673}
2674
2675#define HDSPM_WC_SYNC_CHECK(xname, xindex) \
67ed4161 2676{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
2677 .name = xname, \
2678 .index = xindex, \
2679 .access = SNDRV_CTL_ELEM_ACCESS_READ | SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
2680 .info = snd_hdspm_info_sync_check, \
2681 .get = snd_hdspm_get_wc_sync_check \
2682}
2683
98274f07
TI
2684static int snd_hdspm_info_sync_check(struct snd_kcontrol *kcontrol,
2685 struct snd_ctl_elem_info *uinfo)
763f356c
TI
2686{
2687 static char *texts[] = { "No Lock", "Lock", "Sync" };
2688 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
2689 uinfo->count = 1;
2690 uinfo->value.enumerated.items = 3;
2691 if (uinfo->value.enumerated.item >= uinfo->value.enumerated.items)
2692 uinfo->value.enumerated.item =
2693 uinfo->value.enumerated.items - 1;
2694 strcpy(uinfo->value.enumerated.name,
2695 texts[uinfo->value.enumerated.item]);
2696 return 0;
2697}
2698
98274f07 2699static int hdspm_wc_sync_check(struct hdspm * hdspm)
763f356c 2700{
3cee5a60
RB
2701 if (hdspm->is_aes32) {
2702 int status = hdspm_read(hdspm, HDSPM_statusRegister);
2703 if (status & HDSPM_AES32_wcLock) {
2704 /* I don't know how to differenciate sync from lock.
2705 Doing as if sync for now */
763f356c 2706 return 2;
3cee5a60
RB
2707 }
2708 return 0;
2709 } else {
2710 int status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
2711 if (status2 & HDSPM_wcLock) {
2712 if (status2 & HDSPM_wcSync)
2713 return 2;
2714 else
2715 return 1;
2716 }
2717 return 0;
763f356c 2718 }
763f356c
TI
2719}
2720
98274f07
TI
2721static int snd_hdspm_get_wc_sync_check(struct snd_kcontrol *kcontrol,
2722 struct snd_ctl_elem_value *ucontrol)
763f356c 2723{
98274f07 2724 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2725
2726 ucontrol->value.enumerated.item[0] = hdspm_wc_sync_check(hdspm);
2727 return 0;
2728}
2729
2730
2731#define HDSPM_MADI_SYNC_CHECK(xname, xindex) \
67ed4161 2732{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
763f356c
TI
2733 .name = xname, \
2734 .index = xindex, \
2735 .access = SNDRV_CTL_ELEM_ACCESS_READ | SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
2736 .info = snd_hdspm_info_sync_check, \
2737 .get = snd_hdspm_get_madisync_sync_check \
2738}
2739
98274f07 2740static int hdspm_madisync_sync_check(struct hdspm * hdspm)
763f356c
TI
2741{
2742 int status = hdspm_read(hdspm, HDSPM_statusRegister);
2743 if (status & HDSPM_madiLock) {
2744 if (status & HDSPM_madiSync)
2745 return 2;
2746 else
2747 return 1;
2748 }
2749 return 0;
2750}
2751
98274f07
TI
2752static int snd_hdspm_get_madisync_sync_check(struct snd_kcontrol *kcontrol,
2753 struct snd_ctl_elem_value *
763f356c
TI
2754 ucontrol)
2755{
98274f07 2756 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2757
2758 ucontrol->value.enumerated.item[0] =
2759 hdspm_madisync_sync_check(hdspm);
2760 return 0;
2761}
2762
2763
3cee5a60
RB
2764#define HDSPM_AES_SYNC_CHECK(xname, xindex) \
2765{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2766 .name = xname, \
2767 .index = xindex, \
2768 .access = SNDRV_CTL_ELEM_ACCESS_READ | SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
2769 .info = snd_hdspm_info_sync_check, \
2770 .get = snd_hdspm_get_aes_sync_check \
2771}
2772
2773static int hdspm_aes_sync_check(struct hdspm * hdspm, int idx)
2774{
2775 int status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
2776 if (status2 & (HDSPM_LockAES >> idx)) {
2777 /* I don't know how to differenciate sync from lock.
2778 Doing as if sync for now */
2779 return 2;
2780 }
2781 return 0;
2782}
2783
2784static int snd_hdspm_get_aes_sync_check(struct snd_kcontrol *kcontrol,
2785 struct snd_ctl_elem_value *ucontrol)
2786{
2787 int offset;
2788 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2789
2790 offset = ucontrol->id.index - 1;
2791 if (offset < 0 || offset >= 8)
2792 return -EINVAL;
2793
2794 ucontrol->value.enumerated.item[0] =
2795 hdspm_aes_sync_check(hdspm, offset);
2796 return 0;
2797}
763f356c
TI
2798
2799
3cee5a60 2800static struct snd_kcontrol_new snd_hdspm_controls_madi[] = {
763f356c
TI
2801
2802 HDSPM_MIXER("Mixer", 0),
2803/* 'Sample Clock Source' complies with the alsa control naming scheme */
2804 HDSPM_CLOCK_SOURCE("Sample Clock Source", 0),
2805
2806 HDSPM_SYSTEM_CLOCK_MODE("System Clock Mode", 0),
2807 HDSPM_PREF_SYNC_REF("Preferred Sync Reference", 0),
2808 HDSPM_AUTOSYNC_REF("AutoSync Reference", 0),
2809 HDSPM_SYSTEM_SAMPLE_RATE("System Sample Rate", 0),
2810/* 'External Rate' complies with the alsa control naming scheme */
2811 HDSPM_AUTOSYNC_SAMPLE_RATE("External Rate", 0),
2812 HDSPM_WC_SYNC_CHECK("Word Clock Lock Status", 0),
2813 HDSPM_MADI_SYNC_CHECK("MADI Sync Lock Status", 0),
2814 HDSPM_LINE_OUT("Line Out", 0),
2815 HDSPM_TX_64("TX 64 channels mode", 0),
2816 HDSPM_C_TMS("Clear Track Marker", 0),
2817 HDSPM_SAFE_MODE("Safe Mode", 0),
2818 HDSPM_INPUT_SELECT("Input Select", 0),
2819};
2820
3cee5a60
RB
2821static struct snd_kcontrol_new snd_hdspm_controls_aes32[] = {
2822
2823 HDSPM_MIXER("Mixer", 0),
2824/* 'Sample Clock Source' complies with the alsa control naming scheme */
2825 HDSPM_CLOCK_SOURCE("Sample Clock Source", 0),
2826
2827 HDSPM_SYSTEM_CLOCK_MODE("System Clock Mode", 0),
2828 HDSPM_PREF_SYNC_REF("Preferred Sync Reference", 0),
2829 HDSPM_AUTOSYNC_REF("AutoSync Reference", 0),
2830 HDSPM_SYSTEM_SAMPLE_RATE("System Sample Rate", 0),
2831/* 'External Rate' complies with the alsa control naming scheme */
2832 HDSPM_AUTOSYNC_SAMPLE_RATE("External Rate", 0),
2833 HDSPM_WC_SYNC_CHECK("Word Clock Lock Status", 0),
2834/* HDSPM_AES_SYNC_CHECK("AES Lock Status", 0),*/ /* created in snd_hdspm_create_controls() */
2835 HDSPM_LINE_OUT("Line Out", 0),
2836 HDSPM_EMPHASIS("Emphasis", 0),
2837 HDSPM_DOLBY("Non Audio", 0),
2838 HDSPM_PROFESSIONAL("Professional", 0),
2839 HDSPM_C_TMS("Clear Track Marker", 0),
2840 HDSPM_DS_WIRE("Double Speed Wire Mode", 0),
2841 HDSPM_QS_WIRE("Quad Speed Wire Mode", 0),
2842};
2843
98274f07 2844static struct snd_kcontrol_new snd_hdspm_playback_mixer = HDSPM_PLAYBACK_MIXER;
763f356c
TI
2845
2846
98274f07 2847static int hdspm_update_simple_mixer_controls(struct hdspm * hdspm)
763f356c
TI
2848{
2849 int i;
2850
2851 for (i = hdspm->ds_channels; i < hdspm->ss_channels; ++i) {
2852 if (hdspm->system_sample_rate > 48000) {
2853 hdspm->playback_mixer_ctls[i]->vd[0].access =
2854 SNDRV_CTL_ELEM_ACCESS_INACTIVE |
2855 SNDRV_CTL_ELEM_ACCESS_READ |
2856 SNDRV_CTL_ELEM_ACCESS_VOLATILE;
2857 } else {
2858 hdspm->playback_mixer_ctls[i]->vd[0].access =
2859 SNDRV_CTL_ELEM_ACCESS_READWRITE |
2860 SNDRV_CTL_ELEM_ACCESS_VOLATILE;
2861 }
2862 snd_ctl_notify(hdspm->card, SNDRV_CTL_EVENT_MASK_VALUE |
2863 SNDRV_CTL_EVENT_MASK_INFO,
2864 &hdspm->playback_mixer_ctls[i]->id);
2865 }
2866
2867 return 0;
2868}
2869
2870
98274f07 2871static int snd_hdspm_create_controls(struct snd_card *card, struct hdspm * hdspm)
763f356c
TI
2872{
2873 unsigned int idx, limit;
2874 int err;
98274f07 2875 struct snd_kcontrol *kctl;
763f356c
TI
2876
2877 /* add control list first */
3cee5a60
RB
2878 if (hdspm->is_aes32) {
2879 struct snd_kcontrol_new aes_sync_ctl =
2880 HDSPM_AES_SYNC_CHECK("AES Lock Status", 0);
2881
2882 for (idx = 0; idx < ARRAY_SIZE(snd_hdspm_controls_aes32);
2883 idx++) {
2884 err = snd_ctl_add(card,
2885 snd_ctl_new1(&snd_hdspm_controls_aes32[idx],
2886 hdspm));
2887 if (err < 0)
2888 return err;
2889 }
2890 for (idx = 1; idx <= 8; idx++) {
2891 aes_sync_ctl.index = idx;
2892 err = snd_ctl_add(card,
2893 snd_ctl_new1(&aes_sync_ctl, hdspm));
2894 if (err < 0)
2895 return err;
2896 }
2897 } else {
2898 for (idx = 0; idx < ARRAY_SIZE(snd_hdspm_controls_madi);
2899 idx++) {
2900 err = snd_ctl_add(card,
2901 snd_ctl_new1(&snd_hdspm_controls_madi[idx],
2902 hdspm));
2903 if (err < 0)
2904 return err;
763f356c
TI
2905 }
2906 }
2907
2908 /* Channel playback mixer as default control
ef5fa1a4
TI
2909 Note: the whole matrix would be 128*HDSPM_MIXER_CHANNELS Faders,
2910 thats too * big for any alsamixer they are accesible via special
2911 IOCTL on hwdep and the mixer 2dimensional mixer control
2912 */
763f356c
TI
2913
2914 snd_hdspm_playback_mixer.name = "Chn";
2915 limit = HDSPM_MAX_CHANNELS;
2916
ef5fa1a4
TI
2917 /* The index values are one greater than the channel ID so that
2918 * alsamixer will display them correctly. We want to use the index
2919 * for fast lookup of the relevant channel, but if we use it at all,
2920 * most ALSA software does the wrong thing with it ...
763f356c
TI
2921 */
2922
2923 for (idx = 0; idx < limit; ++idx) {
2924 snd_hdspm_playback_mixer.index = idx + 1;
ef5fa1a4
TI
2925 kctl = snd_ctl_new1(&snd_hdspm_playback_mixer, hdspm);
2926 err = snd_ctl_add(card, kctl);
2927 if (err < 0)
763f356c 2928 return err;
763f356c
TI
2929 hdspm->playback_mixer_ctls[idx] = kctl;
2930 }
2931
2932 return 0;
2933}
2934
2935/*------------------------------------------------------------
2936 /proc interface
2937 ------------------------------------------------------------*/
2938
2939static void
3cee5a60
RB
2940snd_hdspm_proc_read_madi(struct snd_info_entry * entry,
2941 struct snd_info_buffer *buffer)
763f356c 2942{
ef5fa1a4 2943 struct hdspm *hdspm = entry->private_data;
763f356c
TI
2944 unsigned int status;
2945 unsigned int status2;
2946 char *pref_sync_ref;
2947 char *autosync_ref;
2948 char *system_clock_mode;
2949 char *clock_source;
2950 char *insel;
2951 char *syncref;
2952 int x, x2;
2953
2954 status = hdspm_read(hdspm, HDSPM_statusRegister);
2955 status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
2956
2957 snd_iprintf(buffer, "%s (Card #%d) Rev.%x Status2first3bits: %x\n",
2958 hdspm->card_name, hdspm->card->number + 1,
2959 hdspm->firmware_rev,
2960 (status2 & HDSPM_version0) |
2961 (status2 & HDSPM_version1) | (status2 &
2962 HDSPM_version2));
2963
2964 snd_iprintf(buffer, "IRQ: %d Registers bus: 0x%lx VM: 0x%lx\n",
2965 hdspm->irq, hdspm->port, (unsigned long)hdspm->iobase);
2966
2967 snd_iprintf(buffer, "--- System ---\n");
2968
2969 snd_iprintf(buffer,
2970 "IRQ Pending: Audio=%d, MIDI0=%d, MIDI1=%d, IRQcount=%d\n",
2971 status & HDSPM_audioIRQPending,
2972 (status & HDSPM_midi0IRQPending) ? 1 : 0,
2973 (status & HDSPM_midi1IRQPending) ? 1 : 0,
2974 hdspm->irq_count);
2975 snd_iprintf(buffer,
ef5fa1a4
TI
2976 "HW pointer: id = %d, rawptr = %d (%d->%d) "
2977 "estimated= %ld (bytes)\n",
763f356c
TI
2978 ((status & HDSPM_BufferID) ? 1 : 0),
2979 (status & HDSPM_BufferPositionMask),
ef5fa1a4
TI
2980 (status & HDSPM_BufferPositionMask) %
2981 (2 * (int)hdspm->period_bytes),
2982 ((status & HDSPM_BufferPositionMask) - 64) %
2983 (2 * (int)hdspm->period_bytes),
763f356c
TI
2984 (long) hdspm_hw_pointer(hdspm) * 4);
2985
2986 snd_iprintf(buffer,
2987 "MIDI FIFO: Out1=0x%x, Out2=0x%x, In1=0x%x, In2=0x%x \n",
2988 hdspm_read(hdspm, HDSPM_midiStatusOut0) & 0xFF,
2989 hdspm_read(hdspm, HDSPM_midiStatusOut1) & 0xFF,
2990 hdspm_read(hdspm, HDSPM_midiStatusIn0) & 0xFF,
2991 hdspm_read(hdspm, HDSPM_midiStatusIn1) & 0xFF);
2992 snd_iprintf(buffer,
ef5fa1a4
TI
2993 "Register: ctrl1=0x%x, ctrl2=0x%x, status1=0x%x, "
2994 "status2=0x%x\n",
763f356c
TI
2995 hdspm->control_register, hdspm->control2_register,
2996 status, status2);
2997
2998 snd_iprintf(buffer, "--- Settings ---\n");
2999
ef5fa1a4
TI
3000 x = 1 << (6 + hdspm_decode_latency(hdspm->control_register &
3001 HDSPM_LatencyMask));
763f356c
TI
3002
3003 snd_iprintf(buffer,
3004 "Size (Latency): %d samples (2 periods of %lu bytes)\n",
3005 x, (unsigned long) hdspm->period_bytes);
3006
3007 snd_iprintf(buffer, "Line out: %s, Precise Pointer: %s\n",
ef5fa1a4 3008 (hdspm->control_register & HDSPM_LineOut) ? "on " : "off",
763f356c
TI
3009 (hdspm->precise_ptr) ? "on" : "off");
3010
3011 switch (hdspm->control_register & HDSPM_InputMask) {
3012 case HDSPM_InputOptical:
3013 insel = "Optical";
3014 break;
3015 case HDSPM_InputCoaxial:
3016 insel = "Coaxial";
3017 break;
3018 default:
3019 insel = "Unkown";
3020 }
3021
3022 switch (hdspm->control_register & HDSPM_SyncRefMask) {
3023 case HDSPM_SyncRef_Word:
3024 syncref = "WordClock";
3025 break;
3026 case HDSPM_SyncRef_MADI:
3027 syncref = "MADI";
3028 break;
3029 default:
3030 syncref = "Unkown";
3031 }
3032 snd_iprintf(buffer, "Inputsel = %s, SyncRef = %s\n", insel,
3033 syncref);
3034
3035 snd_iprintf(buffer,
ef5fa1a4
TI
3036 "ClearTrackMarker = %s, Transmit in %s Channel Mode, "
3037 "Auto Input %s\n",
763f356c
TI
3038 (hdspm->
3039 control_register & HDSPM_clr_tms) ? "on" : "off",
3040 (hdspm->
3041 control_register & HDSPM_TX_64ch) ? "64" : "56",
3042 (hdspm->
3043 control_register & HDSPM_AutoInp) ? "on" : "off");
3044
3045 switch (hdspm_clock_source(hdspm)) {
3046 case HDSPM_CLOCK_SOURCE_AUTOSYNC:
3047 clock_source = "AutoSync";
3048 break;
3049 case HDSPM_CLOCK_SOURCE_INTERNAL_32KHZ:
3050 clock_source = "Internal 32 kHz";
3051 break;
3052 case HDSPM_CLOCK_SOURCE_INTERNAL_44_1KHZ:
3053 clock_source = "Internal 44.1 kHz";
3054 break;
3055 case HDSPM_CLOCK_SOURCE_INTERNAL_48KHZ:
3056 clock_source = "Internal 48 kHz";
3057 break;
3058 case HDSPM_CLOCK_SOURCE_INTERNAL_64KHZ:
3059 clock_source = "Internal 64 kHz";
3060 break;
3061 case HDSPM_CLOCK_SOURCE_INTERNAL_88_2KHZ:
3062 clock_source = "Internal 88.2 kHz";
3063 break;
3064 case HDSPM_CLOCK_SOURCE_INTERNAL_96KHZ:
3065 clock_source = "Internal 96 kHz";
3066 break;
3067 default:
3068 clock_source = "Error";
3069 }
3070 snd_iprintf(buffer, "Sample Clock Source: %s\n", clock_source);
3cee5a60 3071 if (!(hdspm->control_register & HDSPM_ClockModeMaster))
763f356c 3072 system_clock_mode = "Slave";
3cee5a60 3073 else
763f356c 3074 system_clock_mode = "Master";
763f356c
TI
3075 snd_iprintf(buffer, "System Clock Mode: %s\n", system_clock_mode);
3076
3077 switch (hdspm_pref_sync_ref(hdspm)) {
3078 case HDSPM_SYNC_FROM_WORD:
3079 pref_sync_ref = "Word Clock";
3080 break;
3081 case HDSPM_SYNC_FROM_MADI:
3082 pref_sync_ref = "MADI Sync";
3083 break;
3084 default:
3085 pref_sync_ref = "XXXX Clock";
3086 break;
3087 }
3088 snd_iprintf(buffer, "Preferred Sync Reference: %s\n",
3089 pref_sync_ref);
3090
3091 snd_iprintf(buffer, "System Clock Frequency: %d\n",
3092 hdspm->system_sample_rate);
3093
3094
3095 snd_iprintf(buffer, "--- Status:\n");
3096
3097 x = status & HDSPM_madiSync;
3098 x2 = status2 & HDSPM_wcSync;
3099
3100 snd_iprintf(buffer, "Inputs MADI=%s, WordClock=%s\n",
3101 (status & HDSPM_madiLock) ? (x ? "Sync" : "Lock") :
3102 "NoLock",
3103 (status2 & HDSPM_wcLock) ? (x2 ? "Sync" : "Lock") :
3104 "NoLock");
3105
3106 switch (hdspm_autosync_ref(hdspm)) {
3107 case HDSPM_AUTOSYNC_FROM_WORD:
3108 autosync_ref = "Word Clock";
3109 break;
3110 case HDSPM_AUTOSYNC_FROM_MADI:
3111 autosync_ref = "MADI Sync";
3112 break;
3113 case HDSPM_AUTOSYNC_FROM_NONE:
3114 autosync_ref = "Input not valid";
3115 break;
3116 default:
3117 autosync_ref = "---";
3118 break;
3119 }
3120 snd_iprintf(buffer,
3121 "AutoSync: Reference= %s, Freq=%d (MADI = %d, Word = %d)\n",
3122 autosync_ref, hdspm_external_sample_rate(hdspm),
3123 (status & HDSPM_madiFreqMask) >> 22,
3124 (status2 & HDSPM_wcFreqMask) >> 5);
3125
3126 snd_iprintf(buffer, "Input: %s, Mode=%s\n",
3127 (status & HDSPM_AB_int) ? "Coax" : "Optical",
3128 (status & HDSPM_RX_64ch) ? "64 channels" :
3129 "56 channels");
3130
3131 snd_iprintf(buffer, "\n");
3132}
3133
3cee5a60
RB
3134static void
3135snd_hdspm_proc_read_aes32(struct snd_info_entry * entry,
3136 struct snd_info_buffer *buffer)
3137{
ef5fa1a4 3138 struct hdspm *hdspm = entry->private_data;
3cee5a60
RB
3139 unsigned int status;
3140 unsigned int status2;
3141 unsigned int timecode;
3142 int pref_syncref;
3143 char *autosync_ref;
3144 char *system_clock_mode;
3145 char *clock_source;
3146 int x;
3147
3148 status = hdspm_read(hdspm, HDSPM_statusRegister);
3149 status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
3150 timecode = hdspm_read(hdspm, HDSPM_timecodeRegister);
3151
3152 snd_iprintf(buffer, "%s (Card #%d) Rev.%x\n",
3153 hdspm->card_name, hdspm->card->number + 1,
3154 hdspm->firmware_rev);
3155
3156 snd_iprintf(buffer, "IRQ: %d Registers bus: 0x%lx VM: 0x%lx\n",
3157 hdspm->irq, hdspm->port, (unsigned long)hdspm->iobase);
3158
3159 snd_iprintf(buffer, "--- System ---\n");
3160
3161 snd_iprintf(buffer,
3162 "IRQ Pending: Audio=%d, MIDI0=%d, MIDI1=%d, IRQcount=%d\n",
3163 status & HDSPM_audioIRQPending,
3164 (status & HDSPM_midi0IRQPending) ? 1 : 0,
3165 (status & HDSPM_midi1IRQPending) ? 1 : 0,
3166 hdspm->irq_count);
3167 snd_iprintf(buffer,
ef5fa1a4
TI
3168 "HW pointer: id = %d, rawptr = %d (%d->%d) "
3169 "estimated= %ld (bytes)\n",
3cee5a60
RB
3170 ((status & HDSPM_BufferID) ? 1 : 0),
3171 (status & HDSPM_BufferPositionMask),
ef5fa1a4
TI
3172 (status & HDSPM_BufferPositionMask) %
3173 (2 * (int)hdspm->period_bytes),
3174 ((status & HDSPM_BufferPositionMask) - 64) %
3175 (2 * (int)hdspm->period_bytes),
3cee5a60
RB
3176 (long) hdspm_hw_pointer(hdspm) * 4);
3177
3178 snd_iprintf(buffer,
3179 "MIDI FIFO: Out1=0x%x, Out2=0x%x, In1=0x%x, In2=0x%x \n",
3180 hdspm_read(hdspm, HDSPM_midiStatusOut0) & 0xFF,
3181 hdspm_read(hdspm, HDSPM_midiStatusOut1) & 0xFF,
3182 hdspm_read(hdspm, HDSPM_midiStatusIn0) & 0xFF,
3183 hdspm_read(hdspm, HDSPM_midiStatusIn1) & 0xFF);
3184 snd_iprintf(buffer,
ef5fa1a4
TI
3185 "Register: ctrl1=0x%x, status1=0x%x, status2=0x%x, "
3186 "timecode=0x%x\n",
ffb2c3c0 3187 hdspm->control_register,
3cee5a60
RB
3188 status, status2, timecode);
3189
3190 snd_iprintf(buffer, "--- Settings ---\n");
3191
ef5fa1a4
TI
3192 x = 1 << (6 + hdspm_decode_latency(hdspm->control_register &
3193 HDSPM_LatencyMask));
3cee5a60
RB
3194
3195 snd_iprintf(buffer,
3196 "Size (Latency): %d samples (2 periods of %lu bytes)\n",
3197 x, (unsigned long) hdspm->period_bytes);
3198
3199 snd_iprintf(buffer, "Line out: %s, Precise Pointer: %s\n",
3200 (hdspm->
3201 control_register & HDSPM_LineOut) ? "on " : "off",
3202 (hdspm->precise_ptr) ? "on" : "off");
3203
3204 snd_iprintf(buffer,
3205 "ClearTrackMarker %s, Emphasis %s, Dolby %s\n",
3206 (hdspm->
3207 control_register & HDSPM_clr_tms) ? "on" : "off",
3208 (hdspm->
3209 control_register & HDSPM_Emphasis) ? "on" : "off",
3210 (hdspm->
3211 control_register & HDSPM_Dolby) ? "on" : "off");
3212
3213 switch (hdspm_clock_source(hdspm)) {
3214 case HDSPM_CLOCK_SOURCE_AUTOSYNC:
3215 clock_source = "AutoSync";
3216 break;
3217 case HDSPM_CLOCK_SOURCE_INTERNAL_32KHZ:
3218 clock_source = "Internal 32 kHz";
3219 break;
3220 case HDSPM_CLOCK_SOURCE_INTERNAL_44_1KHZ:
3221 clock_source = "Internal 44.1 kHz";
3222 break;
3223 case HDSPM_CLOCK_SOURCE_INTERNAL_48KHZ:
3224 clock_source = "Internal 48 kHz";
3225 break;
3226 case HDSPM_CLOCK_SOURCE_INTERNAL_64KHZ:
3227 clock_source = "Internal 64 kHz";
3228 break;
3229 case HDSPM_CLOCK_SOURCE_INTERNAL_88_2KHZ:
3230 clock_source = "Internal 88.2 kHz";
3231 break;
3232 case HDSPM_CLOCK_SOURCE_INTERNAL_96KHZ:
3233 clock_source = "Internal 96 kHz";
3234 break;
3235 case HDSPM_CLOCK_SOURCE_INTERNAL_128KHZ:
3236 clock_source = "Internal 128 kHz";
3237 break;
3238 case HDSPM_CLOCK_SOURCE_INTERNAL_176_4KHZ:
3239 clock_source = "Internal 176.4 kHz";
3240 break;
3241 case HDSPM_CLOCK_SOURCE_INTERNAL_192KHZ:
3242 clock_source = "Internal 192 kHz";
3243 break;
3244 default:
3245 clock_source = "Error";
3246 }
3247 snd_iprintf(buffer, "Sample Clock Source: %s\n", clock_source);
3248 if (!(hdspm->control_register & HDSPM_ClockModeMaster))
3249 system_clock_mode = "Slave";
3250 else
3251 system_clock_mode = "Master";
3252 snd_iprintf(buffer, "System Clock Mode: %s\n", system_clock_mode);
3253
3254 pref_syncref = hdspm_pref_sync_ref(hdspm);
3255 if (pref_syncref == 0)
3256 snd_iprintf(buffer, "Preferred Sync Reference: Word Clock\n");
3257 else
3258 snd_iprintf(buffer, "Preferred Sync Reference: AES%d\n",
3259 pref_syncref);
3260
3261 snd_iprintf(buffer, "System Clock Frequency: %d\n",
3262 hdspm->system_sample_rate);
3263
3264 snd_iprintf(buffer, "Double speed: %s\n",
3265 hdspm->control_register & HDSPM_DS_DoubleWire?
3266 "Double wire" : "Single wire");
3267 snd_iprintf(buffer, "Quad speed: %s\n",
3268 hdspm->control_register & HDSPM_QS_DoubleWire?
3269 "Double wire" :
3270 hdspm->control_register & HDSPM_QS_QuadWire?
3271 "Quad wire" : "Single wire");
3272
3273 snd_iprintf(buffer, "--- Status:\n");
3274
3275 snd_iprintf(buffer, "Word: %s Frequency: %d\n",
ef5fa1a4
TI
3276 (status & HDSPM_AES32_wcLock)? "Sync " : "No Lock",
3277 HDSPM_bit2freq((status >> HDSPM_AES32_wcFreq_bit) & 0xF));
3cee5a60
RB
3278
3279 for (x = 0; x < 8; x++) {
3280 snd_iprintf(buffer, "AES%d: %s Frequency: %d\n",
ef5fa1a4
TI
3281 x+1,
3282 (status2 & (HDSPM_LockAES >> x)) ?
3283 "Sync ": "No Lock",
3284 HDSPM_bit2freq((timecode >> (4*x)) & 0xF));
3cee5a60
RB
3285 }
3286
3287 switch (hdspm_autosync_ref(hdspm)) {
3288 case HDSPM_AES32_AUTOSYNC_FROM_NONE: autosync_ref="None"; break;
3289 case HDSPM_AES32_AUTOSYNC_FROM_WORD: autosync_ref="Word Clock"; break;
3290 case HDSPM_AES32_AUTOSYNC_FROM_AES1: autosync_ref="AES1"; break;
3291 case HDSPM_AES32_AUTOSYNC_FROM_AES2: autosync_ref="AES2"; break;
3292 case HDSPM_AES32_AUTOSYNC_FROM_AES3: autosync_ref="AES3"; break;
3293 case HDSPM_AES32_AUTOSYNC_FROM_AES4: autosync_ref="AES4"; break;
3294 case HDSPM_AES32_AUTOSYNC_FROM_AES5: autosync_ref="AES5"; break;
3295 case HDSPM_AES32_AUTOSYNC_FROM_AES6: autosync_ref="AES6"; break;
3296 case HDSPM_AES32_AUTOSYNC_FROM_AES7: autosync_ref="AES7"; break;
3297 case HDSPM_AES32_AUTOSYNC_FROM_AES8: autosync_ref="AES8"; break;
3298 default: autosync_ref = "---"; break;
3299 }
3300 snd_iprintf(buffer, "AutoSync ref = %s\n", autosync_ref);
3301
3302 snd_iprintf(buffer, "\n");
3303}
3304
3305#ifdef CONFIG_SND_DEBUG
3306static void
3307snd_hdspm_proc_read_debug(struct snd_info_entry * entry,
3308 struct snd_info_buffer *buffer)
3309{
ef5fa1a4 3310 struct hdspm *hdspm = entry->private_data;
3cee5a60
RB
3311
3312 int j,i;
3313
ef5fa1a4 3314 for (i = 0; i < 256 /* 1024*64 */; i += j) {
3cee5a60
RB
3315 snd_iprintf(buffer, "0x%08X: ", i);
3316 for (j = 0; j < 16; j += 4)
3317 snd_iprintf(buffer, "%08X ", hdspm_read(hdspm, i + j));
3318 snd_iprintf(buffer, "\n");
3319 }
3320}
3321#endif
3322
3323
3324
98274f07 3325static void __devinit snd_hdspm_proc_init(struct hdspm * hdspm)
763f356c 3326{
98274f07 3327 struct snd_info_entry *entry;
763f356c
TI
3328
3329 if (!snd_card_proc_new(hdspm->card, "hdspm", &entry))
bf850204 3330 snd_info_set_text_ops(entry, hdspm,
3cee5a60
RB
3331 hdspm->is_aes32 ?
3332 snd_hdspm_proc_read_aes32 :
3333 snd_hdspm_proc_read_madi);
3334#ifdef CONFIG_SND_DEBUG
3335 /* debug file to read all hdspm registers */
3336 if (!snd_card_proc_new(hdspm->card, "debug", &entry))
3337 snd_info_set_text_ops(entry, hdspm,
3338 snd_hdspm_proc_read_debug);
3339#endif
763f356c
TI
3340}
3341
3342/*------------------------------------------------------------
3343 hdspm intitialize
3344 ------------------------------------------------------------*/
3345
98274f07 3346static int snd_hdspm_set_defaults(struct hdspm * hdspm)
763f356c
TI
3347{
3348 unsigned int i;
3349
3350 /* ASSUMPTION: hdspm->lock is either held, or there is no need to
3351 hold it (e.g. during module initalization).
3352 */
3353
3354 /* set defaults: */
3355
3cee5a60 3356 if (hdspm->is_aes32)
ef5fa1a4
TI
3357 hdspm->control_register =
3358 HDSPM_ClockModeMaster | /* Master Cloack Mode on */
3359 hdspm_encode_latency(7) | /* latency maximum =
3360 * 8192 samples
3361 */
3cee5a60
RB
3362 HDSPM_SyncRef0 | /* AES1 is syncclock */
3363 HDSPM_LineOut | /* Analog output in */
3364 HDSPM_Professional; /* Professional mode */
3365 else
ef5fa1a4
TI
3366 hdspm->control_register =
3367 HDSPM_ClockModeMaster | /* Master Cloack Mode on */
3368 hdspm_encode_latency(7) | /* latency maximum =
3369 * 8192 samples
3370 */
3cee5a60
RB
3371 HDSPM_InputCoaxial | /* Input Coax not Optical */
3372 HDSPM_SyncRef_MADI | /* Madi is syncclock */
3373 HDSPM_LineOut | /* Analog output in */
3374 HDSPM_TX_64ch | /* transmit in 64ch mode */
3375 HDSPM_AutoInp; /* AutoInput chossing (takeover) */
763f356c
TI
3376
3377 /* ! HDSPM_Frequency0|HDSPM_Frequency1 = 44.1khz */
3378 /* ! HDSPM_DoubleSpeed HDSPM_QuadSpeed = normal speed */
3379 /* ! HDSPM_clr_tms = do not clear bits in track marks */
3380
3381 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
3382
ffb2c3c0
RB
3383 if (!hdspm->is_aes32) {
3384 /* No control2 register for AES32 */
763f356c 3385#ifdef SNDRV_BIG_ENDIAN
ffb2c3c0 3386 hdspm->control2_register = HDSPM_BIGENDIAN_MODE;
763f356c 3387#else
ffb2c3c0 3388 hdspm->control2_register = 0;
763f356c
TI
3389#endif
3390
ffb2c3c0
RB
3391 hdspm_write(hdspm, HDSPM_control2Reg, hdspm->control2_register);
3392 }
763f356c
TI
3393 hdspm_compute_period_size(hdspm);
3394
3395 /* silence everything */
3396
3397 all_in_all_mixer(hdspm, 0 * UNITY_GAIN);
3398
3399 if (line_outs_monitor[hdspm->dev]) {
3400
ef5fa1a4
TI
3401 snd_printk(KERN_INFO "HDSPM: "
3402 "sending all playback streams to line outs.\n");
763f356c
TI
3403
3404 for (i = 0; i < HDSPM_MIXER_CHANNELS; i++) {
3405 if (hdspm_write_pb_gain(hdspm, i, i, UNITY_GAIN))
3406 return -EIO;
3407 }
3408 }
3409
3410 /* set a default rate so that the channel map is set up. */
3411 hdspm->channel_map = channel_map_madi_ss;
3412 hdspm_set_rate(hdspm, 44100, 1);
3413
3414 return 0;
3415}
3416
3417
3418/*------------------------------------------------------------
3419 interupt
3420 ------------------------------------------------------------*/
3421
7d12e780 3422static irqreturn_t snd_hdspm_interrupt(int irq, void *dev_id)
763f356c 3423{
98274f07 3424 struct hdspm *hdspm = (struct hdspm *) dev_id;
763f356c
TI
3425 unsigned int status;
3426 int audio;
3427 int midi0;
3428 int midi1;
3429 unsigned int midi0status;
3430 unsigned int midi1status;
3431 int schedule = 0;
3432
3433 status = hdspm_read(hdspm, HDSPM_statusRegister);
3434
3435 audio = status & HDSPM_audioIRQPending;
3436 midi0 = status & HDSPM_midi0IRQPending;
3437 midi1 = status & HDSPM_midi1IRQPending;
3438
3439 if (!audio && !midi0 && !midi1)
3440 return IRQ_NONE;
3441
3442 hdspm_write(hdspm, HDSPM_interruptConfirmation, 0);
3443 hdspm->irq_count++;
3444
3445 midi0status = hdspm_read(hdspm, HDSPM_midiStatusIn0) & 0xff;
3446 midi1status = hdspm_read(hdspm, HDSPM_midiStatusIn1) & 0xff;
3447
3448 if (audio) {
3449
3450 if (hdspm->capture_substream)
ef5fa1a4 3451 snd_pcm_period_elapsed(hdspm->capture_substream);
763f356c
TI
3452
3453 if (hdspm->playback_substream)
ef5fa1a4 3454 snd_pcm_period_elapsed(hdspm->playback_substream);
763f356c
TI
3455 }
3456
3457 if (midi0 && midi0status) {
ef5fa1a4
TI
3458 /* we disable interrupts for this input until processing
3459 * is done
3460 */
763f356c
TI
3461 hdspm->control_register &= ~HDSPM_Midi0InterruptEnable;
3462 hdspm_write(hdspm, HDSPM_controlRegister,
3463 hdspm->control_register);
3464 hdspm->midi[0].pending = 1;
3465 schedule = 1;
3466 }
3467 if (midi1 && midi1status) {
ef5fa1a4
TI
3468 /* we disable interrupts for this input until processing
3469 * is done
3470 */
763f356c
TI
3471 hdspm->control_register &= ~HDSPM_Midi1InterruptEnable;
3472 hdspm_write(hdspm, HDSPM_controlRegister,
3473 hdspm->control_register);
3474 hdspm->midi[1].pending = 1;
3475 schedule = 1;
3476 }
3477 if (schedule)
3478 tasklet_hi_schedule(&hdspm->midi_tasklet);
3479 return IRQ_HANDLED;
3480}
3481
3482/*------------------------------------------------------------
3483 pcm interface
3484 ------------------------------------------------------------*/
3485
3486
98274f07 3487static snd_pcm_uframes_t snd_hdspm_hw_pointer(struct snd_pcm_substream *
763f356c
TI
3488 substream)
3489{
98274f07 3490 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
3491 return hdspm_hw_pointer(hdspm);
3492}
3493
98274f07 3494static char *hdspm_channel_buffer_location(struct hdspm * hdspm,
763f356c
TI
3495 int stream, int channel)
3496{
3497 int mapped_channel;
3498
3499 snd_assert(channel >= 0
3500 || channel < HDSPM_MAX_CHANNELS, return NULL);
3501
ef5fa1a4
TI
3502 mapped_channel = hdspm->channel_map[channel];
3503 if (mapped_channel < 0)
763f356c
TI
3504 return NULL;
3505
ef5fa1a4 3506 if (stream == SNDRV_PCM_STREAM_CAPTURE)
763f356c
TI
3507 return hdspm->capture_buffer +
3508 mapped_channel * HDSPM_CHANNEL_BUFFER_BYTES;
ef5fa1a4 3509 else
763f356c
TI
3510 return hdspm->playback_buffer +
3511 mapped_channel * HDSPM_CHANNEL_BUFFER_BYTES;
763f356c
TI
3512}
3513
3514
3515/* dont know why need it ??? */
98274f07 3516static int snd_hdspm_playback_copy(struct snd_pcm_substream *substream,
763f356c
TI
3517 int channel, snd_pcm_uframes_t pos,
3518 void __user *src, snd_pcm_uframes_t count)
3519{
98274f07 3520 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
3521 char *channel_buf;
3522
3523 snd_assert(pos + count <= HDSPM_CHANNEL_BUFFER_BYTES / 4,
3524 return -EINVAL);
3525
ef5fa1a4
TI
3526 channel_buf =
3527 hdspm_channel_buffer_location(hdspm, substream->pstr->stream,
3528 channel);
763f356c
TI
3529
3530 snd_assert(channel_buf != NULL, return -EIO);
3531
3532 return copy_from_user(channel_buf + pos * 4, src, count * 4);
3533}
3534
98274f07 3535static int snd_hdspm_capture_copy(struct snd_pcm_substream *substream,
763f356c
TI
3536 int channel, snd_pcm_uframes_t pos,
3537 void __user *dst, snd_pcm_uframes_t count)
3538{
98274f07 3539 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
3540 char *channel_buf;
3541
3542 snd_assert(pos + count <= HDSPM_CHANNEL_BUFFER_BYTES / 4,
3543 return -EINVAL);
3544
ef5fa1a4
TI
3545 channel_buf =
3546 hdspm_channel_buffer_location(hdspm, substream->pstr->stream,
3547 channel);
763f356c
TI
3548 snd_assert(channel_buf != NULL, return -EIO);
3549 return copy_to_user(dst, channel_buf + pos * 4, count * 4);
3550}
3551
98274f07 3552static int snd_hdspm_hw_silence(struct snd_pcm_substream *substream,
763f356c
TI
3553 int channel, snd_pcm_uframes_t pos,
3554 snd_pcm_uframes_t count)
3555{
98274f07 3556 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
3557 char *channel_buf;
3558
3559 channel_buf =
ef5fa1a4
TI
3560 hdspm_channel_buffer_location(hdspm, substream->pstr->stream,
3561 channel);
763f356c
TI
3562 snd_assert(channel_buf != NULL, return -EIO);
3563 memset(channel_buf + pos * 4, 0, count * 4);
3564 return 0;
3565}
3566
98274f07 3567static int snd_hdspm_reset(struct snd_pcm_substream *substream)
763f356c 3568{
98274f07
TI
3569 struct snd_pcm_runtime *runtime = substream->runtime;
3570 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
3571 struct snd_pcm_substream *other;
763f356c
TI
3572
3573 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
3574 other = hdspm->capture_substream;
3575 else
3576 other = hdspm->playback_substream;
3577
3578 if (hdspm->running)
3579 runtime->status->hw_ptr = hdspm_hw_pointer(hdspm);
3580 else
3581 runtime->status->hw_ptr = 0;
3582 if (other) {
98274f07
TI
3583 struct snd_pcm_substream *s;
3584 struct snd_pcm_runtime *oruntime = other->runtime;
ef991b95 3585 snd_pcm_group_for_each_entry(s, substream) {
763f356c
TI
3586 if (s == other) {
3587 oruntime->status->hw_ptr =
3588 runtime->status->hw_ptr;
3589 break;
3590 }
3591 }
3592 }
3593 return 0;
3594}
3595
98274f07
TI
3596static int snd_hdspm_hw_params(struct snd_pcm_substream *substream,
3597 struct snd_pcm_hw_params *params)
763f356c 3598{
98274f07 3599 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
3600 int err;
3601 int i;
3602 pid_t this_pid;
3603 pid_t other_pid;
3604 struct snd_sg_buf *sgbuf;
3605
3606
3607 spin_lock_irq(&hdspm->lock);
3608
3609 if (substream->pstr->stream == SNDRV_PCM_STREAM_PLAYBACK) {
3610 this_pid = hdspm->playback_pid;
3611 other_pid = hdspm->capture_pid;
3612 } else {
3613 this_pid = hdspm->capture_pid;
3614 other_pid = hdspm->playback_pid;
3615 }
3616
ef5fa1a4 3617 if (other_pid > 0 && this_pid != other_pid) {
763f356c
TI
3618
3619 /* The other stream is open, and not by the same
3620 task as this one. Make sure that the parameters
3621 that matter are the same.
3622 */
3623
3624 if (params_rate(params) != hdspm->system_sample_rate) {
3625 spin_unlock_irq(&hdspm->lock);
3626 _snd_pcm_hw_param_setempty(params,
3627 SNDRV_PCM_HW_PARAM_RATE);
3628 return -EBUSY;
3629 }
3630
3631 if (params_period_size(params) != hdspm->period_bytes / 4) {
3632 spin_unlock_irq(&hdspm->lock);
3633 _snd_pcm_hw_param_setempty(params,
ef5fa1a4 3634 SNDRV_PCM_HW_PARAM_PERIOD_SIZE);
763f356c
TI
3635 return -EBUSY;
3636 }
3637
3638 }
3639 /* We're fine. */
3640 spin_unlock_irq(&hdspm->lock);
3641
3642 /* how to make sure that the rate matches an externally-set one ? */
3643
3644 spin_lock_irq(&hdspm->lock);
ef5fa1a4
TI
3645 err = hdspm_set_rate(hdspm, params_rate(params), 0);
3646 if (err < 0) {
763f356c
TI
3647 spin_unlock_irq(&hdspm->lock);
3648 _snd_pcm_hw_param_setempty(params,
3649 SNDRV_PCM_HW_PARAM_RATE);
3650 return err;
3651 }
3652 spin_unlock_irq(&hdspm->lock);
3653
ef5fa1a4
TI
3654 err = hdspm_set_interrupt_interval(hdspm,
3655 params_period_size(params));
3656 if (err < 0) {
763f356c
TI
3657 _snd_pcm_hw_param_setempty(params,
3658 SNDRV_PCM_HW_PARAM_PERIOD_SIZE);
3659 return err;
3660 }
3661
ef5fa1a4
TI
3662 /* Memory allocation, takashi's method, dont know if we should
3663 * spinlock
3664 */
763f356c 3665 /* malloc all buffer even if not enabled to get sure */
ffb2c3c0
RB
3666 /* Update for MADI rev 204: we need to allocate for all channels,
3667 * otherwise it doesn't work at 96kHz */
763f356c 3668 err =
ffb2c3c0 3669 snd_pcm_lib_malloc_pages(substream, HDSPM_DMA_AREA_BYTES);
763f356c
TI
3670 if (err < 0)
3671 return err;
3672
3673 sgbuf = snd_pcm_substream_sgbuf(substream);
3674
3675 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
3676
3677 hdspm_set_sgbuf(hdspm, sgbuf, HDSPM_pageAddressBufferOut,
3678 params_channels(params));
3679
3680 for (i = 0; i < params_channels(params); ++i)
3681 snd_hdspm_enable_out(hdspm, i, 1);
3682
3683 hdspm->playback_buffer =
3684 (unsigned char *) substream->runtime->dma_area;
54bf5dd9 3685 snd_printdd("Allocated sample buffer for playback at %p\n",
3cee5a60 3686 hdspm->playback_buffer);
763f356c
TI
3687 } else {
3688 hdspm_set_sgbuf(hdspm, sgbuf, HDSPM_pageAddressBufferIn,
3689 params_channels(params));
3690
3691 for (i = 0; i < params_channels(params); ++i)
3692 snd_hdspm_enable_in(hdspm, i, 1);
3693
3694 hdspm->capture_buffer =
3695 (unsigned char *) substream->runtime->dma_area;
54bf5dd9 3696 snd_printdd("Allocated sample buffer for capture at %p\n",
3cee5a60 3697 hdspm->capture_buffer);
763f356c 3698 }
3cee5a60
RB
3699 /*
3700 snd_printdd("Allocated sample buffer for %s at 0x%08X\n",
3701 substream->stream == SNDRV_PCM_STREAM_PLAYBACK ?
3702 "playback" : "capture",
3703 snd_pcm_sgbuf_get_addr(sgbuf, 0));
3704 */
ffb2c3c0
RB
3705 /*
3706 snd_printdd("set_hwparams: %s %d Hz, %d channels, bs = %d\n",
3707 substream->stream == SNDRV_PCM_STREAM_PLAYBACK ?
3708 "playback" : "capture",
3709 params_rate(params), params_channels(params),
3710 params_buffer_size(params));
3711 */
763f356c
TI
3712 return 0;
3713}
3714
98274f07 3715static int snd_hdspm_hw_free(struct snd_pcm_substream *substream)
763f356c
TI
3716{
3717 int i;
98274f07 3718 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
3719
3720 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
3721
3722 /* params_channels(params) should be enough,
3723 but to get sure in case of error */
3724 for (i = 0; i < HDSPM_MAX_CHANNELS; ++i)
3725 snd_hdspm_enable_out(hdspm, i, 0);
3726
3727 hdspm->playback_buffer = NULL;
3728 } else {
3729 for (i = 0; i < HDSPM_MAX_CHANNELS; ++i)
3730 snd_hdspm_enable_in(hdspm, i, 0);
3731
3732 hdspm->capture_buffer = NULL;
3733
3734 }
3735
3736 snd_pcm_lib_free_pages(substream);
3737
3738 return 0;
3739}
3740
98274f07
TI
3741static int snd_hdspm_channel_info(struct snd_pcm_substream *substream,
3742 struct snd_pcm_channel_info * info)
763f356c 3743{
98274f07 3744 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
3745 int mapped_channel;
3746
3747 snd_assert(info->channel < HDSPM_MAX_CHANNELS, return -EINVAL);
3748
ef5fa1a4
TI
3749 mapped_channel = hdspm->channel_map[info->channel];
3750 if (mapped_channel < 0)
763f356c
TI
3751 return -EINVAL;
3752
3753 info->offset = mapped_channel * HDSPM_CHANNEL_BUFFER_BYTES;
3754 info->first = 0;
3755 info->step = 32;
3756 return 0;
3757}
3758
98274f07 3759static int snd_hdspm_ioctl(struct snd_pcm_substream *substream,
763f356c
TI
3760 unsigned int cmd, void *arg)
3761{
3762 switch (cmd) {
3763 case SNDRV_PCM_IOCTL1_RESET:
ef5fa1a4 3764 return snd_hdspm_reset(substream);
763f356c
TI
3765
3766 case SNDRV_PCM_IOCTL1_CHANNEL_INFO:
ef5fa1a4
TI
3767 {
3768 struct snd_pcm_channel_info *info = arg;
3769 return snd_hdspm_channel_info(substream, info);
3770 }
763f356c
TI
3771 default:
3772 break;
3773 }
3774
3775 return snd_pcm_lib_ioctl(substream, cmd, arg);
3776}
3777
98274f07 3778static int snd_hdspm_trigger(struct snd_pcm_substream *substream, int cmd)
763f356c 3779{
98274f07
TI
3780 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
3781 struct snd_pcm_substream *other;
763f356c
TI
3782 int running;
3783
3784 spin_lock(&hdspm->lock);
3785 running = hdspm->running;
3786 switch (cmd) {
3787 case SNDRV_PCM_TRIGGER_START:
3788 running |= 1 << substream->stream;
3789 break;
3790 case SNDRV_PCM_TRIGGER_STOP:
3791 running &= ~(1 << substream->stream);
3792 break;
3793 default:
3794 snd_BUG();
3795 spin_unlock(&hdspm->lock);
3796 return -EINVAL;
3797 }
3798 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
3799 other = hdspm->capture_substream;
3800 else
3801 other = hdspm->playback_substream;
3802
3803 if (other) {
98274f07 3804 struct snd_pcm_substream *s;
ef991b95 3805 snd_pcm_group_for_each_entry(s, substream) {
763f356c
TI
3806 if (s == other) {
3807 snd_pcm_trigger_done(s, substream);
3808 if (cmd == SNDRV_PCM_TRIGGER_START)
3809 running |= 1 << s->stream;
3810 else
3811 running &= ~(1 << s->stream);
3812 goto _ok;
3813 }
3814 }
3815 if (cmd == SNDRV_PCM_TRIGGER_START) {
3816 if (!(running & (1 << SNDRV_PCM_STREAM_PLAYBACK))
3817 && substream->stream ==
3818 SNDRV_PCM_STREAM_CAPTURE)
3819 hdspm_silence_playback(hdspm);
3820 } else {
3821 if (running &&
3822 substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
3823 hdspm_silence_playback(hdspm);
3824 }
3825 } else {
3826 if (substream->stream == SNDRV_PCM_STREAM_CAPTURE)
3827 hdspm_silence_playback(hdspm);
3828 }
3829 _ok:
3830 snd_pcm_trigger_done(substream, substream);
3831 if (!hdspm->running && running)
3832 hdspm_start_audio(hdspm);
3833 else if (hdspm->running && !running)
3834 hdspm_stop_audio(hdspm);
3835 hdspm->running = running;
3836 spin_unlock(&hdspm->lock);
3837
3838 return 0;
3839}
3840
98274f07 3841static int snd_hdspm_prepare(struct snd_pcm_substream *substream)
763f356c
TI
3842{
3843 return 0;
3844}
3845
3846static unsigned int period_sizes[] =
3847 { 64, 128, 256, 512, 1024, 2048, 4096, 8192 };
3848
98274f07 3849static struct snd_pcm_hardware snd_hdspm_playback_subinfo = {
763f356c
TI
3850 .info = (SNDRV_PCM_INFO_MMAP |
3851 SNDRV_PCM_INFO_MMAP_VALID |
3852 SNDRV_PCM_INFO_NONINTERLEAVED |
3853 SNDRV_PCM_INFO_SYNC_START | SNDRV_PCM_INFO_DOUBLE),
3854 .formats = SNDRV_PCM_FMTBIT_S32_LE,
3855 .rates = (SNDRV_PCM_RATE_32000 |
3856 SNDRV_PCM_RATE_44100 |
3857 SNDRV_PCM_RATE_48000 |
3858 SNDRV_PCM_RATE_64000 |
3cee5a60
RB
3859 SNDRV_PCM_RATE_88200 | SNDRV_PCM_RATE_96000 |
3860 SNDRV_PCM_RATE_176400 | SNDRV_PCM_RATE_192000 ),
763f356c 3861 .rate_min = 32000,
3cee5a60 3862 .rate_max = 192000,
763f356c
TI
3863 .channels_min = 1,
3864 .channels_max = HDSPM_MAX_CHANNELS,
3865 .buffer_bytes_max =
3866 HDSPM_CHANNEL_BUFFER_BYTES * HDSPM_MAX_CHANNELS,
3867 .period_bytes_min = (64 * 4),
3868 .period_bytes_max = (8192 * 4) * HDSPM_MAX_CHANNELS,
3869 .periods_min = 2,
3870 .periods_max = 2,
3871 .fifo_size = 0
3872};
3873
98274f07 3874static struct snd_pcm_hardware snd_hdspm_capture_subinfo = {
763f356c
TI
3875 .info = (SNDRV_PCM_INFO_MMAP |
3876 SNDRV_PCM_INFO_MMAP_VALID |
3877 SNDRV_PCM_INFO_NONINTERLEAVED |
3878 SNDRV_PCM_INFO_SYNC_START),
3879 .formats = SNDRV_PCM_FMTBIT_S32_LE,
3880 .rates = (SNDRV_PCM_RATE_32000 |
3881 SNDRV_PCM_RATE_44100 |
3882 SNDRV_PCM_RATE_48000 |
3883 SNDRV_PCM_RATE_64000 |
3cee5a60
RB
3884 SNDRV_PCM_RATE_88200 | SNDRV_PCM_RATE_96000 |
3885 SNDRV_PCM_RATE_176400 | SNDRV_PCM_RATE_192000),
763f356c 3886 .rate_min = 32000,
3cee5a60 3887 .rate_max = 192000,
763f356c
TI
3888 .channels_min = 1,
3889 .channels_max = HDSPM_MAX_CHANNELS,
3890 .buffer_bytes_max =
3891 HDSPM_CHANNEL_BUFFER_BYTES * HDSPM_MAX_CHANNELS,
3892 .period_bytes_min = (64 * 4),
3893 .period_bytes_max = (8192 * 4) * HDSPM_MAX_CHANNELS,
3894 .periods_min = 2,
3895 .periods_max = 2,
3896 .fifo_size = 0
3897};
3898
98274f07 3899static struct snd_pcm_hw_constraint_list hw_constraints_period_sizes = {
763f356c
TI
3900 .count = ARRAY_SIZE(period_sizes),
3901 .list = period_sizes,
3902 .mask = 0
3903};
3904
3905
98274f07
TI
3906static int snd_hdspm_hw_rule_channels_rate(struct snd_pcm_hw_params *params,
3907 struct snd_pcm_hw_rule * rule)
763f356c 3908{
98274f07
TI
3909 struct hdspm *hdspm = rule->private;
3910 struct snd_interval *c =
763f356c 3911 hw_param_interval(params, SNDRV_PCM_HW_PARAM_CHANNELS);
98274f07 3912 struct snd_interval *r =
763f356c
TI
3913 hw_param_interval(params, SNDRV_PCM_HW_PARAM_RATE);
3914
ffb2c3c0 3915 if (r->min > 48000 && r->max <= 96000) {
98274f07 3916 struct snd_interval t = {
ffb2c3c0 3917 .min = hdspm->ds_channels,
763f356c
TI
3918 .max = hdspm->ds_channels,
3919 .integer = 1,
3920 };
3921 return snd_interval_refine(c, &t);
3922 } else if (r->max < 64000) {
98274f07 3923 struct snd_interval t = {
ffb2c3c0 3924 .min = hdspm->ss_channels,
763f356c
TI
3925 .max = hdspm->ss_channels,
3926 .integer = 1,
3927 };
3928 return snd_interval_refine(c, &t);
3929 }
3930 return 0;
3931}
3932
98274f07
TI
3933static int snd_hdspm_hw_rule_rate_channels(struct snd_pcm_hw_params *params,
3934 struct snd_pcm_hw_rule * rule)
763f356c 3935{
98274f07
TI
3936 struct hdspm *hdspm = rule->private;
3937 struct snd_interval *c =
763f356c 3938 hw_param_interval(params, SNDRV_PCM_HW_PARAM_CHANNELS);
98274f07 3939 struct snd_interval *r =
763f356c
TI
3940 hw_param_interval(params, SNDRV_PCM_HW_PARAM_RATE);
3941
ffb2c3c0 3942 if (c->min >= hdspm->ss_channels) {
98274f07 3943 struct snd_interval t = {
763f356c
TI
3944 .min = 32000,
3945 .max = 48000,
3946 .integer = 1,
3947 };
3948 return snd_interval_refine(r, &t);
ffb2c3c0 3949 } else if (c->max <= hdspm->ds_channels) {
98274f07 3950 struct snd_interval t = {
763f356c
TI
3951 .min = 64000,
3952 .max = 96000,
3953 .integer = 1,
3954 };
3955
3956 return snd_interval_refine(r, &t);
3957 }
3958 return 0;
3959}
3960
ffb2c3c0
RB
3961static int snd_hdspm_hw_rule_channels(struct snd_pcm_hw_params *params,
3962 struct snd_pcm_hw_rule *rule)
3963{
3964 unsigned int list[3];
3965 struct hdspm *hdspm = rule->private;
3966 struct snd_interval *c = hw_param_interval(params,
3967 SNDRV_PCM_HW_PARAM_CHANNELS);
3968 if (hdspm->is_aes32) {
3969 list[0] = hdspm->qs_channels;
3970 list[1] = hdspm->ds_channels;
3971 list[2] = hdspm->ss_channels;
3972 return snd_interval_list(c, 3, list, 0);
3973 } else {
3974 list[0] = hdspm->ds_channels;
3975 list[1] = hdspm->ss_channels;
3976 return snd_interval_list(c, 2, list, 0);
3977 }
3978}
3979
3980
ef5fa1a4
TI
3981static unsigned int hdspm_aes32_sample_rates[] = {
3982 32000, 44100, 48000, 64000, 88200, 96000, 128000, 176400, 192000
3983};
ffb2c3c0 3984
ef5fa1a4
TI
3985static struct snd_pcm_hw_constraint_list
3986hdspm_hw_constraints_aes32_sample_rates = {
ffb2c3c0
RB
3987 .count = ARRAY_SIZE(hdspm_aes32_sample_rates),
3988 .list = hdspm_aes32_sample_rates,
3989 .mask = 0
3990};
3991
98274f07 3992static int snd_hdspm_playback_open(struct snd_pcm_substream *substream)
763f356c 3993{
98274f07
TI
3994 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
3995 struct snd_pcm_runtime *runtime = substream->runtime;
763f356c 3996
763f356c
TI
3997 spin_lock_irq(&hdspm->lock);
3998
3999 snd_pcm_set_sync(substream);
4000
4001 runtime->hw = snd_hdspm_playback_subinfo;
4002
4003 if (hdspm->capture_substream == NULL)
4004 hdspm_stop_audio(hdspm);
4005
4006 hdspm->playback_pid = current->pid;
4007 hdspm->playback_substream = substream;
4008
4009 spin_unlock_irq(&hdspm->lock);
4010
4011 snd_pcm_hw_constraint_msbits(runtime, 0, 32, 24);
4012
4013 snd_pcm_hw_constraint_list(runtime, 0,
4014 SNDRV_PCM_HW_PARAM_PERIOD_SIZE,
4015 &hw_constraints_period_sizes);
4016
ffb2c3c0
RB
4017 if (hdspm->is_aes32) {
4018 snd_pcm_hw_constraint_list(runtime, 0, SNDRV_PCM_HW_PARAM_RATE,
4019 &hdspm_hw_constraints_aes32_sample_rates);
4020 } else {
4021 snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_CHANNELS,
4022 snd_hdspm_hw_rule_channels, hdspm,
4023 SNDRV_PCM_HW_PARAM_CHANNELS, -1);
4024 snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_CHANNELS,
4025 snd_hdspm_hw_rule_channels_rate, hdspm,
4026 SNDRV_PCM_HW_PARAM_RATE, -1);
4027
4028 snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_RATE,
4029 snd_hdspm_hw_rule_rate_channels, hdspm,
4030 SNDRV_PCM_HW_PARAM_CHANNELS, -1);
4031 }
763f356c
TI
4032 return 0;
4033}
4034
98274f07 4035static int snd_hdspm_playback_release(struct snd_pcm_substream *substream)
763f356c 4036{
98274f07 4037 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
4038
4039 spin_lock_irq(&hdspm->lock);
4040
4041 hdspm->playback_pid = -1;
4042 hdspm->playback_substream = NULL;
4043
4044 spin_unlock_irq(&hdspm->lock);
4045
4046 return 0;
4047}
4048
4049
98274f07 4050static int snd_hdspm_capture_open(struct snd_pcm_substream *substream)
763f356c 4051{
98274f07
TI
4052 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
4053 struct snd_pcm_runtime *runtime = substream->runtime;
763f356c
TI
4054
4055 spin_lock_irq(&hdspm->lock);
4056 snd_pcm_set_sync(substream);
4057 runtime->hw = snd_hdspm_capture_subinfo;
4058
4059 if (hdspm->playback_substream == NULL)
4060 hdspm_stop_audio(hdspm);
4061
4062 hdspm->capture_pid = current->pid;
4063 hdspm->capture_substream = substream;
4064
4065 spin_unlock_irq(&hdspm->lock);
4066
4067 snd_pcm_hw_constraint_msbits(runtime, 0, 32, 24);
4068 snd_pcm_hw_constraint_list(runtime, 0,
4069 SNDRV_PCM_HW_PARAM_PERIOD_SIZE,
4070 &hw_constraints_period_sizes);
ffb2c3c0
RB
4071 if (hdspm->is_aes32) {
4072 snd_pcm_hw_constraint_list(runtime, 0, SNDRV_PCM_HW_PARAM_RATE,
4073 &hdspm_hw_constraints_aes32_sample_rates);
4074 } else {
4075 snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_CHANNELS,
4076 snd_hdspm_hw_rule_channels, hdspm,
4077 SNDRV_PCM_HW_PARAM_CHANNELS, -1);
4078 snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_CHANNELS,
4079 snd_hdspm_hw_rule_channels_rate, hdspm,
4080 SNDRV_PCM_HW_PARAM_RATE, -1);
4081
4082 snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_RATE,
4083 snd_hdspm_hw_rule_rate_channels, hdspm,
4084 SNDRV_PCM_HW_PARAM_CHANNELS, -1);
4085 }
763f356c
TI
4086 return 0;
4087}
4088
98274f07 4089static int snd_hdspm_capture_release(struct snd_pcm_substream *substream)
763f356c 4090{
98274f07 4091 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
4092
4093 spin_lock_irq(&hdspm->lock);
4094
4095 hdspm->capture_pid = -1;
4096 hdspm->capture_substream = NULL;
4097
4098 spin_unlock_irq(&hdspm->lock);
4099 return 0;
4100}
4101
98274f07 4102static int snd_hdspm_hwdep_dummy_op(struct snd_hwdep * hw, struct file *file)
763f356c
TI
4103{
4104 /* we have nothing to initialize but the call is required */
4105 return 0;
4106}
4107
4108
98274f07 4109static int snd_hdspm_hwdep_ioctl(struct snd_hwdep * hw, struct file *file,
763f356c
TI
4110 unsigned int cmd, unsigned long arg)
4111{
ef5fa1a4 4112 struct hdspm *hdspm = hw->private_data;
98274f07
TI
4113 struct hdspm_mixer_ioctl mixer;
4114 struct hdspm_config_info info;
4115 struct hdspm_version hdspm_version;
4116 struct hdspm_peak_rms_ioctl rms;
763f356c
TI
4117
4118 switch (cmd) {
4119
763f356c
TI
4120 case SNDRV_HDSPM_IOCTL_GET_PEAK_RMS:
4121 if (copy_from_user(&rms, (void __user *)arg, sizeof(rms)))
4122 return -EFAULT;
ef5fa1a4
TI
4123 /* maybe there is a chance to memorymap in future
4124 * so dont touch just copy
4125 */
763f356c
TI
4126 if(copy_to_user_fromio((void __user *)rms.peak,
4127 hdspm->iobase+HDSPM_MADI_peakrmsbase,
98274f07 4128 sizeof(struct hdspm_peak_rms)) != 0 )
763f356c
TI
4129 return -EFAULT;
4130
4131 break;
4132
4133
4134 case SNDRV_HDSPM_IOCTL_GET_CONFIG_INFO:
4135
4136 spin_lock_irq(&hdspm->lock);
ef5fa1a4
TI
4137 info.pref_sync_ref = hdspm_pref_sync_ref(hdspm);
4138 info.wordclock_sync_check = hdspm_wc_sync_check(hdspm);
763f356c
TI
4139
4140 info.system_sample_rate = hdspm->system_sample_rate;
4141 info.autosync_sample_rate =
4142 hdspm_external_sample_rate(hdspm);
ef5fa1a4
TI
4143 info.system_clock_mode = hdspm_system_clock_mode(hdspm);
4144 info.clock_source = hdspm_clock_source(hdspm);
4145 info.autosync_ref = hdspm_autosync_ref(hdspm);
4146 info.line_out = hdspm_line_out(hdspm);
763f356c
TI
4147 info.passthru = 0;
4148 spin_unlock_irq(&hdspm->lock);
4149 if (copy_to_user((void __user *) arg, &info, sizeof(info)))
4150 return -EFAULT;
4151 break;
4152
4153 case SNDRV_HDSPM_IOCTL_GET_VERSION:
4154 hdspm_version.firmware_rev = hdspm->firmware_rev;
4155 if (copy_to_user((void __user *) arg, &hdspm_version,
4156 sizeof(hdspm_version)))
4157 return -EFAULT;
4158 break;
4159
4160 case SNDRV_HDSPM_IOCTL_GET_MIXER:
4161 if (copy_from_user(&mixer, (void __user *)arg, sizeof(mixer)))
4162 return -EFAULT;
ef5fa1a4
TI
4163 if (copy_to_user((void __user *)mixer.mixer, hdspm->mixer,
4164 sizeof(struct hdspm_mixer)))
763f356c
TI
4165 return -EFAULT;
4166 break;
4167
4168 default:
4169 return -EINVAL;
4170 }
4171 return 0;
4172}
4173
98274f07 4174static struct snd_pcm_ops snd_hdspm_playback_ops = {
763f356c
TI
4175 .open = snd_hdspm_playback_open,
4176 .close = snd_hdspm_playback_release,
4177 .ioctl = snd_hdspm_ioctl,
4178 .hw_params = snd_hdspm_hw_params,
4179 .hw_free = snd_hdspm_hw_free,
4180 .prepare = snd_hdspm_prepare,
4181 .trigger = snd_hdspm_trigger,
4182 .pointer = snd_hdspm_hw_pointer,
4183 .copy = snd_hdspm_playback_copy,
4184 .silence = snd_hdspm_hw_silence,
4185 .page = snd_pcm_sgbuf_ops_page,
4186};
4187
98274f07 4188static struct snd_pcm_ops snd_hdspm_capture_ops = {
763f356c
TI
4189 .open = snd_hdspm_capture_open,
4190 .close = snd_hdspm_capture_release,
4191 .ioctl = snd_hdspm_ioctl,
4192 .hw_params = snd_hdspm_hw_params,
4193 .hw_free = snd_hdspm_hw_free,
4194 .prepare = snd_hdspm_prepare,
4195 .trigger = snd_hdspm_trigger,
4196 .pointer = snd_hdspm_hw_pointer,
4197 .copy = snd_hdspm_capture_copy,
4198 .page = snd_pcm_sgbuf_ops_page,
4199};
4200
98274f07
TI
4201static int __devinit snd_hdspm_create_hwdep(struct snd_card *card,
4202 struct hdspm * hdspm)
763f356c 4203{
98274f07 4204 struct snd_hwdep *hw;
763f356c
TI
4205 int err;
4206
ef5fa1a4
TI
4207 err = snd_hwdep_new(card, "HDSPM hwdep", 0, &hw);
4208 if (err < 0)
763f356c
TI
4209 return err;
4210
4211 hdspm->hwdep = hw;
4212 hw->private_data = hdspm;
4213 strcpy(hw->name, "HDSPM hwdep interface");
4214
4215 hw->ops.open = snd_hdspm_hwdep_dummy_op;
4216 hw->ops.ioctl = snd_hdspm_hwdep_ioctl;
4217 hw->ops.release = snd_hdspm_hwdep_dummy_op;
4218
4219 return 0;
4220}
4221
4222
4223/*------------------------------------------------------------
4224 memory interface
4225 ------------------------------------------------------------*/
98274f07 4226static int __devinit snd_hdspm_preallocate_memory(struct hdspm * hdspm)
763f356c
TI
4227{
4228 int err;
98274f07 4229 struct snd_pcm *pcm;
763f356c
TI
4230 size_t wanted;
4231
4232 pcm = hdspm->pcm;
4233
3cee5a60 4234 wanted = HDSPM_DMA_AREA_BYTES;
763f356c 4235
ef5fa1a4 4236 err =
763f356c
TI
4237 snd_pcm_lib_preallocate_pages_for_all(pcm,
4238 SNDRV_DMA_TYPE_DEV_SG,
4239 snd_dma_pci_data(hdspm->pci),
4240 wanted,
ef5fa1a4
TI
4241 wanted);
4242 if (err < 0) {
e2eba3e7 4243 snd_printdd("Could not preallocate %zd Bytes\n", wanted);
763f356c
TI
4244
4245 return err;
4246 } else
e2eba3e7 4247 snd_printdd(" Preallocated %zd Bytes\n", wanted);
763f356c
TI
4248
4249 return 0;
4250}
4251
98274f07 4252static void hdspm_set_sgbuf(struct hdspm * hdspm, struct snd_sg_buf *sgbuf,
763f356c
TI
4253 unsigned int reg, int channels)
4254{
4255 int i;
4256 for (i = 0; i < (channels * 16); i++)
4257 hdspm_write(hdspm, reg + 4 * i,
ef5fa1a4 4258 snd_pcm_sgbuf_get_addr(sgbuf, (size_t) 4096 * i));
763f356c
TI
4259}
4260
4261/* ------------- ALSA Devices ---------------------------- */
98274f07
TI
4262static int __devinit snd_hdspm_create_pcm(struct snd_card *card,
4263 struct hdspm * hdspm)
763f356c 4264{
98274f07 4265 struct snd_pcm *pcm;
763f356c
TI
4266 int err;
4267
ef5fa1a4
TI
4268 err = snd_pcm_new(card, hdspm->card_name, 0, 1, 1, &pcm);
4269 if (err < 0)
763f356c
TI
4270 return err;
4271
4272 hdspm->pcm = pcm;
4273 pcm->private_data = hdspm;
4274 strcpy(pcm->name, hdspm->card_name);
4275
4276 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK,
4277 &snd_hdspm_playback_ops);
4278 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_CAPTURE,
4279 &snd_hdspm_capture_ops);
4280
4281 pcm->info_flags = SNDRV_PCM_INFO_JOINT_DUPLEX;
4282
ef5fa1a4
TI
4283 err = snd_hdspm_preallocate_memory(hdspm);
4284 if (err < 0)
763f356c
TI
4285 return err;
4286
4287 return 0;
4288}
4289
98274f07 4290static inline void snd_hdspm_initialize_midi_flush(struct hdspm * hdspm)
763f356c
TI
4291{
4292 snd_hdspm_flush_midi_input(hdspm, 0);
4293 snd_hdspm_flush_midi_input(hdspm, 1);
4294}
4295
98274f07
TI
4296static int __devinit snd_hdspm_create_alsa_devices(struct snd_card *card,
4297 struct hdspm * hdspm)
763f356c
TI
4298{
4299 int err;
4300
4301 snd_printdd("Create card...\n");
ef5fa1a4
TI
4302 err = snd_hdspm_create_pcm(card, hdspm);
4303 if (err < 0)
763f356c
TI
4304 return err;
4305
ef5fa1a4
TI
4306 err = snd_hdspm_create_midi(card, hdspm, 0);
4307 if (err < 0)
763f356c
TI
4308 return err;
4309
ef5fa1a4
TI
4310 err = snd_hdspm_create_midi(card, hdspm, 1);
4311 if (err < 0)
763f356c
TI
4312 return err;
4313
ef5fa1a4
TI
4314 err = snd_hdspm_create_controls(card, hdspm);
4315 if (err < 0)
763f356c
TI
4316 return err;
4317
ef5fa1a4
TI
4318 err = snd_hdspm_create_hwdep(card, hdspm);
4319 if (err < 0)
763f356c
TI
4320 return err;
4321
4322 snd_printdd("proc init...\n");
4323 snd_hdspm_proc_init(hdspm);
4324
4325 hdspm->system_sample_rate = -1;
4326 hdspm->last_external_sample_rate = -1;
4327 hdspm->last_internal_sample_rate = -1;
4328 hdspm->playback_pid = -1;
4329 hdspm->capture_pid = -1;
4330 hdspm->capture_substream = NULL;
4331 hdspm->playback_substream = NULL;
4332
4333 snd_printdd("Set defaults...\n");
ef5fa1a4
TI
4334 err = snd_hdspm_set_defaults(hdspm);
4335 if (err < 0)
763f356c
TI
4336 return err;
4337
4338 snd_printdd("Update mixer controls...\n");
4339 hdspm_update_simple_mixer_controls(hdspm);
4340
4341 snd_printdd("Initializeing complete ???\n");
4342
ef5fa1a4
TI
4343 err = snd_card_register(card);
4344 if (err < 0) {
763f356c
TI
4345 snd_printk(KERN_ERR "HDSPM: error registering card\n");
4346 return err;
4347 }
4348
4349 snd_printdd("... yes now\n");
4350
4351 return 0;
4352}
4353
ef5fa1a4
TI
4354static int __devinit snd_hdspm_create(struct snd_card *card,
4355 struct hdspm *hdspm,
763f356c
TI
4356 int precise_ptr, int enable_monitor)
4357{
4358 struct pci_dev *pci = hdspm->pci;
4359 int err;
763f356c
TI
4360 unsigned long io_extent;
4361
4362 hdspm->irq = -1;
ef5fa1a4 4363
763f356c
TI
4364 spin_lock_init(&hdspm->midi[0].lock);
4365 spin_lock_init(&hdspm->midi[1].lock);
763f356c
TI
4366
4367 hdspm->card = card;
4368
4369 spin_lock_init(&hdspm->lock);
4370
4371 tasklet_init(&hdspm->midi_tasklet,
4372 hdspm_midi_tasklet, (unsigned long) hdspm);
4373
4374 pci_read_config_word(hdspm->pci,
4375 PCI_CLASS_REVISION, &hdspm->firmware_rev);
4376
3cee5a60
RB
4377 hdspm->is_aes32 = (hdspm->firmware_rev >= HDSPM_AESREVISION);
4378
763f356c 4379 strcpy(card->mixername, "Xilinx FPGA");
3cee5a60
RB
4380 if (hdspm->is_aes32) {
4381 strcpy(card->driver, "HDSPAES32");
4382 hdspm->card_name = "RME HDSPM AES32";
4383 } else {
4384 strcpy(card->driver, "HDSPM");
4385 hdspm->card_name = "RME HDSPM MADI";
4386 }
763f356c 4387
ef5fa1a4
TI
4388 err = pci_enable_device(pci);
4389 if (err < 0)
763f356c
TI
4390 return err;
4391
4392 pci_set_master(hdspm->pci);
4393
ef5fa1a4
TI
4394 err = pci_request_regions(pci, "hdspm");
4395 if (err < 0)
763f356c
TI
4396 return err;
4397
4398 hdspm->port = pci_resource_start(pci, 0);
4399 io_extent = pci_resource_len(pci, 0);
4400
4401 snd_printdd("grabbed memory region 0x%lx-0x%lx\n",
4402 hdspm->port, hdspm->port + io_extent - 1);
4403
4404
ef5fa1a4
TI
4405 hdspm->iobase = ioremap_nocache(hdspm->port, io_extent);
4406 if (!hdspm->iobase) {
4407 snd_printk(KERN_ERR "HDSPM: "
4408 "unable to remap region 0x%lx-0x%lx\n",
763f356c
TI
4409 hdspm->port, hdspm->port + io_extent - 1);
4410 return -EBUSY;
4411 }
4412 snd_printdd("remapped region (0x%lx) 0x%lx-0x%lx\n",
4413 (unsigned long)hdspm->iobase, hdspm->port,
4414 hdspm->port + io_extent - 1);
4415
4416 if (request_irq(pci->irq, snd_hdspm_interrupt,
437a5a46 4417 IRQF_SHARED, "hdspm", hdspm)) {
763f356c
TI
4418 snd_printk(KERN_ERR "HDSPM: unable to use IRQ %d\n", pci->irq);
4419 return -EBUSY;
4420 }
4421
4422 snd_printdd("use IRQ %d\n", pci->irq);
4423
4424 hdspm->irq = pci->irq;
4425 hdspm->precise_ptr = precise_ptr;
4426
4427 hdspm->monitor_outs = enable_monitor;
4428
e2eba3e7 4429 snd_printdd("kmalloc Mixer memory of %zd Bytes\n",
98274f07 4430 sizeof(struct hdspm_mixer));
ef5fa1a4
TI
4431 hdspm->mixer = kzalloc(sizeof(struct hdspm_mixer), GFP_KERNEL);
4432 if (!hdspm->mixer) {
4433 snd_printk(KERN_ERR "HDSPM: "
4434 "unable to kmalloc Mixer memory of %d Bytes\n",
98274f07 4435 (int)sizeof(struct hdspm_mixer));
763f356c
TI
4436 return err;
4437 }
4438
4439 hdspm->ss_channels = MADI_SS_CHANNELS;
4440 hdspm->ds_channels = MADI_DS_CHANNELS;
4441 hdspm->qs_channels = MADI_QS_CHANNELS;
4442
4443 snd_printdd("create alsa devices.\n");
ef5fa1a4
TI
4444 err = snd_hdspm_create_alsa_devices(card, hdspm);
4445 if (err < 0)
763f356c
TI
4446 return err;
4447
4448 snd_hdspm_initialize_midi_flush(hdspm);
4449
4450 return 0;
4451}
4452
98274f07 4453static int snd_hdspm_free(struct hdspm * hdspm)
763f356c
TI
4454{
4455
4456 if (hdspm->port) {
4457
4458 /* stop th audio, and cancel all interrupts */
4459 hdspm->control_register &=
ef5fa1a4
TI
4460 ~(HDSPM_Start | HDSPM_AudioInterruptEnable |
4461 HDSPM_Midi0InterruptEnable | HDSPM_Midi1InterruptEnable);
763f356c
TI
4462 hdspm_write(hdspm, HDSPM_controlRegister,
4463 hdspm->control_register);
4464 }
4465
4466 if (hdspm->irq >= 0)
4467 free_irq(hdspm->irq, (void *) hdspm);
4468
fc58422a 4469 kfree(hdspm->mixer);
763f356c
TI
4470
4471 if (hdspm->iobase)
4472 iounmap(hdspm->iobase);
4473
763f356c
TI
4474 if (hdspm->port)
4475 pci_release_regions(hdspm->pci);
4476
4477 pci_disable_device(hdspm->pci);
4478 return 0;
4479}
4480
98274f07 4481static void snd_hdspm_card_free(struct snd_card *card)
763f356c 4482{
ef5fa1a4 4483 struct hdspm *hdspm = card->private_data;
763f356c
TI
4484
4485 if (hdspm)
4486 snd_hdspm_free(hdspm);
4487}
4488
4489static int __devinit snd_hdspm_probe(struct pci_dev *pci,
4490 const struct pci_device_id *pci_id)
4491{
4492 static int dev;
98274f07
TI
4493 struct hdspm *hdspm;
4494 struct snd_card *card;
763f356c
TI
4495 int err;
4496
4497 if (dev >= SNDRV_CARDS)
4498 return -ENODEV;
4499 if (!enable[dev]) {
4500 dev++;
4501 return -ENOENT;
4502 }
4503
ef5fa1a4
TI
4504 card = snd_card_new(index[dev], id[dev],
4505 THIS_MODULE, sizeof(struct hdspm));
4506 if (!card)
763f356c
TI
4507 return -ENOMEM;
4508
ef5fa1a4 4509 hdspm = card->private_data;
763f356c
TI
4510 card->private_free = snd_hdspm_card_free;
4511 hdspm->dev = dev;
4512 hdspm->pci = pci;
4513
c187c041
TI
4514 snd_card_set_dev(card, &pci->dev);
4515
ef5fa1a4
TI
4516 err = snd_hdspm_create(card, hdspm, precise_ptr[dev],
4517 enable_monitor[dev]);
4518 if (err < 0) {
763f356c
TI
4519 snd_card_free(card);
4520 return err;
4521 }
4522
4523 strcpy(card->shortname, "HDSPM MADI");
4524 sprintf(card->longname, "%s at 0x%lx, irq %d", hdspm->card_name,
4525 hdspm->port, hdspm->irq);
4526
ef5fa1a4
TI
4527 err = snd_card_register(card);
4528 if (err < 0) {
763f356c
TI
4529 snd_card_free(card);
4530 return err;
4531 }
4532
4533 pci_set_drvdata(pci, card);
4534
4535 dev++;
4536 return 0;
4537}
4538
4539static void __devexit snd_hdspm_remove(struct pci_dev *pci)
4540{
4541 snd_card_free(pci_get_drvdata(pci));
4542 pci_set_drvdata(pci, NULL);
4543}
4544
4545static struct pci_driver driver = {
4546 .name = "RME Hammerfall DSP MADI",
4547 .id_table = snd_hdspm_ids,
4548 .probe = snd_hdspm_probe,
4549 .remove = __devexit_p(snd_hdspm_remove),
4550};
4551
4552
4553static int __init alsa_card_hdspm_init(void)
4554{
4555 return pci_register_driver(&driver);
4556}
4557
4558static void __exit alsa_card_hdspm_exit(void)
4559{
4560 pci_unregister_driver(&driver);
4561}
4562
4563module_init(alsa_card_hdspm_init)
4564module_exit(alsa_card_hdspm_exit)
This page took 0.824217 seconds and 5 git commands to generate.