]> git.proxmox.com Git - mirror_ubuntu-hirsute-kernel.git/blame - sound/pci/rme9652/hdspm.c
treewide: Replace GPLv2 boilerplate/reference with SPDX - rule 156
[mirror_ubuntu-hirsute-kernel.git] / sound / pci / rme9652 / hdspm.c
CommitLineData
1a59d1b8 1// SPDX-License-Identifier: GPL-2.0-or-later
ef5fa1a4 2/*
763f356c
TI
3 * ALSA driver for RME Hammerfall DSP MADI audio interface(s)
4 *
5 * Copyright (c) 2003 Winfried Ritsch (IEM)
6 * code based on hdsp.c Paul Davis
7 * Marcus Andersson
8 * Thomas Charbonnel
3cee5a60
RB
9 * Modified 2006-06-01 for AES32 support by Remy Bruno
10 * <remy.bruno@trinnov.com>
763f356c 11 *
0dca1793
AK
12 * Modified 2009-04-13 for proper metering by Florian Faber
13 * <faber@faberman.de>
14 *
15 * Modified 2009-04-14 for native float support by Florian Faber
16 * <faber@faberman.de>
17 *
18 * Modified 2009-04-26 fixed bug in rms metering by Florian Faber
19 * <faber@faberman.de>
20 *
21 * Modified 2009-04-30 added hw serial number support by Florian Faber
22 *
23 * Modified 2011-01-14 added S/PDIF input on RayDATs by Adrian Knoth
24 *
25 * Modified 2011-01-25 variable period sizes on RayDAT/AIO by Adrian Knoth
763f356c 26 */
69358fca
MD
27
28/* ************* Register Documentation *******************************************************
29 *
30 * Work in progress! Documentation is based on the code in this file.
31 *
32 * --------- HDSPM_controlRegister ---------
33 * :7654.3210:7654.3210:7654.3210:7654.3210: bit number per byte
34 * :||||.||||:||||.||||:||||.||||:||||.||||:
35 * :3322.2222:2222.1111:1111.1100:0000.0000: bit number
36 * :1098.7654:3210.9876:5432.1098:7654.3210: 0..31
37 * :||||.||||:||||.||||:||||.||||:||||.||||:
38 * :8421.8421:8421.8421:8421.8421:8421.8421: hex digit
39 * : . : . : . : x . : HDSPM_AudioInterruptEnable \_ setting both bits
40 * : . : . : . : . x: HDSPM_Start / enables audio IO
41 * : . : . : . : x. : HDSPM_ClockModeMaster - 1: Master, 0: Slave
42 * : . : . : . : .210 : HDSPM_LatencyMask - 3 Bit value for latency
43 * : . : . : . : . : 0:64, 1:128, 2:256, 3:512,
44 * : . : . : . : . : 4:1024, 5:2048, 6:4096, 7:8192
45 * :x . : . : . x:xx . : HDSPM_FrequencyMask
46 * : . : . : . :10 . : HDSPM_Frequency1|HDSPM_Frequency0: 1=32K,2=44.1K,3=48K,0=??
47 * : . : . : . x: . : <MADI> HDSPM_DoubleSpeed
48 * :x . : . : . : . : <MADI> HDSPM_QuadSpeed
49 * : . 3 : . 10: 2 . : . : HDSPM_SyncRefMask :
50 * : . : . x: . : . : HDSPM_SyncRef0
51 * : . : . x : . : . : HDSPM_SyncRef1
52 * : . : . : x . : . : <AES32> HDSPM_SyncRef2
53 * : . x : . : . : . : <AES32> HDSPM_SyncRef3
54 * : . : . 10: . : . : <MADI> sync ref: 0:WC, 1:Madi, 2:TCO, 3:SyncIn
55 * : . 3 : . 10: 2 . : . : <AES32> 0:WC, 1:AES1 ... 8:AES8, 9: TCO, 10:SyncIn?
56 * : . x : . : . : . : <MADIe> HDSPe_FLOAT_FORMAT
57 * : . : . : x . : . : <MADI> HDSPM_InputSelect0 : 0=optical,1=coax
58 * : . : . :x . : . : <MADI> HDSPM_InputSelect1
59 * : . : .x : . : . : <MADI> HDSPM_clr_tms
60 * : . : . : . x : . : <MADI> HDSPM_TX_64ch
61 * : . : . : . x : . : <AES32> HDSPM_Emphasis
62 * : . : . : .x : . : <MADI> HDSPM_AutoInp
63 * : . : . x : . : . : <MADI> HDSPM_SMUX
64 * : . : .x : . : . : <MADI> HDSPM_clr_tms
65 * : . : x. : . : . : <MADI> HDSPM_taxi_reset
66 * : . x: . : . : . : <MADI> HDSPM_LineOut
67 * : . x: . : . : . : <AES32> ??????????????????
68 * : . : x. : . : . : <AES32> HDSPM_WCK48
69 * : . : . : .x : . : <AES32> HDSPM_Dolby
70 * : . : x . : . : . : HDSPM_Midi0InterruptEnable
71 * : . :x . : . : . : HDSPM_Midi1InterruptEnable
72 * : . : x . : . : . : HDSPM_Midi2InterruptEnable
73 * : . x : . : . : . : <MADI> HDSPM_Midi3InterruptEnable
74 * : . x : . : . : . : <AES32> HDSPM_DS_DoubleWire
75 * : .x : . : . : . : <AES32> HDSPM_QS_DoubleWire
76 * : x. : . : . : . : <AES32> HDSPM_QS_QuadWire
77 * : . : . : . x : . : <AES32> HDSPM_Professional
78 * : x . : . : . : . : HDSPM_wclk_sel
79 * : . : . : . : . :
80 * :7654.3210:7654.3210:7654.3210:7654.3210: bit number per byte
81 * :||||.||||:||||.||||:||||.||||:||||.||||:
82 * :3322.2222:2222.1111:1111.1100:0000.0000: bit number
83 * :1098.7654:3210.9876:5432.1098:7654.3210: 0..31
84 * :||||.||||:||||.||||:||||.||||:||||.||||:
85 * :8421.8421:8421.8421:8421.8421:8421.8421:hex digit
86 *
87 *
88 *
89 * AIO / RayDAT only
90 *
91 * ------------ HDSPM_WR_SETTINGS ----------
92 * :3322.2222:2222.1111:1111.1100:0000.0000: bit number per byte
93 * :1098.7654:3210.9876:5432.1098:7654.3210:
94 * :||||.||||:||||.||||:||||.||||:||||.||||: bit number
95 * :7654.3210:7654.3210:7654.3210:7654.3210: 0..31
96 * :||||.||||:||||.||||:||||.||||:||||.||||:
97 * :8421.8421:8421.8421:8421.8421:8421.8421: hex digit
98 * : . : . : . : . x: HDSPM_c0Master 1: Master, 0: Slave
99 * : . : . : . : . x : HDSPM_c0_SyncRef0
100 * : . : . : . : . x : HDSPM_c0_SyncRef1
101 * : . : . : . : .x : HDSPM_c0_SyncRef2
102 * : . : . : . : x. : HDSPM_c0_SyncRef3
103 * : . : . : . : 3.210 : HDSPM_c0_SyncRefMask:
104 * : . : . : . : . : RayDat: 0:WC, 1:AES, 2:SPDIF, 3..6: ADAT1..4,
105 * : . : . : . : . : 9:TCO, 10:SyncIn
106 * : . : . : . : . : AIO: 0:WC, 1:AES, 2: SPDIF, 3: ATAT,
107 * : . : . : . : . : 9:TCO, 10:SyncIn
108 * : . : . : . : . :
109 * : . : . : . : . :
110 * :3322.2222:2222.1111:1111.1100:0000.0000: bit number per byte
111 * :1098.7654:3210.9876:5432.1098:7654.3210:
112 * :||||.||||:||||.||||:||||.||||:||||.||||: bit number
113 * :7654.3210:7654.3210:7654.3210:7654.3210: 0..31
114 * :||||.||||:||||.||||:||||.||||:||||.||||:
115 * :8421.8421:8421.8421:8421.8421:8421.8421: hex digit
116 *
117 */
763f356c
TI
118#include <linux/init.h>
119#include <linux/delay.h>
120#include <linux/interrupt.h>
65a77217 121#include <linux/module.h>
763f356c
TI
122#include <linux/slab.h>
123#include <linux/pci.h>
3f7440a6 124#include <linux/math64.h>
6cbbfe1c 125#include <linux/io.h>
10513142 126#include <linux/nospec.h>
763f356c
TI
127
128#include <sound/core.h>
129#include <sound/control.h>
130#include <sound/pcm.h>
0dca1793 131#include <sound/pcm_params.h>
763f356c
TI
132#include <sound/info.h>
133#include <sound/asoundef.h>
134#include <sound/rawmidi.h>
135#include <sound/hwdep.h>
136#include <sound/initval.h>
137
138#include <sound/hdspm.h>
139
140static int index[SNDRV_CARDS] = SNDRV_DEFAULT_IDX; /* Index 0-MAX */
141static char *id[SNDRV_CARDS] = SNDRV_DEFAULT_STR; /* ID for this card */
a67ff6a5 142static bool enable[SNDRV_CARDS] = SNDRV_DEFAULT_ENABLE_PNP;/* Enable this card */
763f356c 143
763f356c
TI
144module_param_array(index, int, NULL, 0444);
145MODULE_PARM_DESC(index, "Index value for RME HDSPM interface.");
146
147module_param_array(id, charp, NULL, 0444);
148MODULE_PARM_DESC(id, "ID string for RME HDSPM interface.");
149
150module_param_array(enable, bool, NULL, 0444);
151MODULE_PARM_DESC(enable, "Enable/disable specific HDSPM soundcards.");
152
763f356c
TI
153
154MODULE_AUTHOR
0dca1793
AK
155(
156 "Winfried Ritsch <ritsch_AT_iem.at>, "
157 "Paul Davis <paul@linuxaudiosystems.com>, "
158 "Marcus Andersson, Thomas Charbonnel <thomas@undata.org>, "
159 "Remy Bruno <remy.bruno@trinnov.com>, "
160 "Florian Faber <faberman@linuxproaudio.org>, "
161 "Adrian Knoth <adi@drcomp.erfurt.thur.de>"
162);
763f356c
TI
163MODULE_DESCRIPTION("RME HDSPM");
164MODULE_LICENSE("GPL");
165MODULE_SUPPORTED_DEVICE("{{RME HDSPM-MADI}}");
166
0dca1793 167/* --- Write registers. ---
763f356c
TI
168 These are defined as byte-offsets from the iobase value. */
169
0dca1793
AK
170#define HDSPM_WR_SETTINGS 0
171#define HDSPM_outputBufferAddress 32
172#define HDSPM_inputBufferAddress 36
763f356c
TI
173#define HDSPM_controlRegister 64
174#define HDSPM_interruptConfirmation 96
175#define HDSPM_control2Reg 256 /* not in specs ???????? */
69358fca 176#define HDSPM_freqReg 256 /* for setting arbitrary clock values (DDS feature) */
0dca1793
AK
177#define HDSPM_midiDataOut0 352 /* just believe in old code */
178#define HDSPM_midiDataOut1 356
ffb2c3c0 179#define HDSPM_eeprom_wr 384 /* for AES32 */
763f356c
TI
180
181/* DMA enable for 64 channels, only Bit 0 is relevant */
0dca1793 182#define HDSPM_outputEnableBase 512 /* 512-767 input DMA */
763f356c
TI
183#define HDSPM_inputEnableBase 768 /* 768-1023 output DMA */
184
0dca1793 185/* 16 page addresses for each of the 64 channels DMA buffer in and out
763f356c
TI
186 (each 64k=16*4k) Buffer must be 4k aligned (which is default i386 ????) */
187#define HDSPM_pageAddressBufferOut 8192
188#define HDSPM_pageAddressBufferIn (HDSPM_pageAddressBufferOut+64*16*4)
189
190#define HDSPM_MADI_mixerBase 32768 /* 32768-65535 for 2x64x64 Fader */
191
192#define HDSPM_MATRIX_MIXER_SIZE 8192 /* = 2*64*64 * 4 Byte => 32kB */
193
194/* --- Read registers. ---
195 These are defined as byte-offsets from the iobase value */
196#define HDSPM_statusRegister 0
3cee5a60
RB
197/*#define HDSPM_statusRegister2 96 */
198/* after RME Windows driver sources, status2 is 4-byte word # 48 = word at
199 * offset 192, for AES32 *and* MADI
200 * => need to check that offset 192 is working on MADI */
201#define HDSPM_statusRegister2 192
202#define HDSPM_timecodeRegister 128
763f356c 203
0dca1793
AK
204/* AIO, RayDAT */
205#define HDSPM_RD_STATUS_0 0
206#define HDSPM_RD_STATUS_1 64
207#define HDSPM_RD_STATUS_2 128
208#define HDSPM_RD_STATUS_3 192
209
210#define HDSPM_RD_TCO 256
211#define HDSPM_RD_PLL_FREQ 512
212#define HDSPM_WR_TCO 128
213
214#define HDSPM_TCO1_TCO_lock 0x00000001
215#define HDSPM_TCO1_WCK_Input_Range_LSB 0x00000002
216#define HDSPM_TCO1_WCK_Input_Range_MSB 0x00000004
217#define HDSPM_TCO1_LTC_Input_valid 0x00000008
218#define HDSPM_TCO1_WCK_Input_valid 0x00000010
219#define HDSPM_TCO1_Video_Input_Format_NTSC 0x00000020
220#define HDSPM_TCO1_Video_Input_Format_PAL 0x00000040
221
222#define HDSPM_TCO1_set_TC 0x00000100
223#define HDSPM_TCO1_set_drop_frame_flag 0x00000200
224#define HDSPM_TCO1_LTC_Format_LSB 0x00000400
225#define HDSPM_TCO1_LTC_Format_MSB 0x00000800
226
227#define HDSPM_TCO2_TC_run 0x00010000
228#define HDSPM_TCO2_WCK_IO_ratio_LSB 0x00020000
229#define HDSPM_TCO2_WCK_IO_ratio_MSB 0x00040000
230#define HDSPM_TCO2_set_num_drop_frames_LSB 0x00080000
231#define HDSPM_TCO2_set_num_drop_frames_MSB 0x00100000
232#define HDSPM_TCO2_set_jam_sync 0x00200000
233#define HDSPM_TCO2_set_flywheel 0x00400000
234
235#define HDSPM_TCO2_set_01_4 0x01000000
236#define HDSPM_TCO2_set_pull_down 0x02000000
237#define HDSPM_TCO2_set_pull_up 0x04000000
238#define HDSPM_TCO2_set_freq 0x08000000
239#define HDSPM_TCO2_set_term_75R 0x10000000
240#define HDSPM_TCO2_set_input_LSB 0x20000000
241#define HDSPM_TCO2_set_input_MSB 0x40000000
242#define HDSPM_TCO2_set_freq_from_app 0x80000000
243
244
245#define HDSPM_midiDataOut0 352
246#define HDSPM_midiDataOut1 356
247#define HDSPM_midiDataOut2 368
248
763f356c
TI
249#define HDSPM_midiDataIn0 360
250#define HDSPM_midiDataIn1 364
0dca1793
AK
251#define HDSPM_midiDataIn2 372
252#define HDSPM_midiDataIn3 376
763f356c
TI
253
254/* status is data bytes in MIDI-FIFO (0-128) */
0dca1793
AK
255#define HDSPM_midiStatusOut0 384
256#define HDSPM_midiStatusOut1 388
257#define HDSPM_midiStatusOut2 400
258
259#define HDSPM_midiStatusIn0 392
260#define HDSPM_midiStatusIn1 396
261#define HDSPM_midiStatusIn2 404
262#define HDSPM_midiStatusIn3 408
763f356c
TI
263
264
265/* the meters are regular i/o-mapped registers, but offset
266 considerably from the rest. the peak registers are reset
0dca1793 267 when read; the least-significant 4 bits are full-scale counters;
763f356c
TI
268 the actual peak value is in the most-significant 24 bits.
269*/
0dca1793
AK
270
271#define HDSPM_MADI_INPUT_PEAK 4096
272#define HDSPM_MADI_PLAYBACK_PEAK 4352
273#define HDSPM_MADI_OUTPUT_PEAK 4608
274
275#define HDSPM_MADI_INPUT_RMS_L 6144
276#define HDSPM_MADI_PLAYBACK_RMS_L 6400
277#define HDSPM_MADI_OUTPUT_RMS_L 6656
278
279#define HDSPM_MADI_INPUT_RMS_H 7168
280#define HDSPM_MADI_PLAYBACK_RMS_H 7424
281#define HDSPM_MADI_OUTPUT_RMS_H 7680
763f356c
TI
282
283/* --- Control Register bits --------- */
284#define HDSPM_Start (1<<0) /* start engine */
285
286#define HDSPM_Latency0 (1<<1) /* buffer size = 2^n */
287#define HDSPM_Latency1 (1<<2) /* where n is defined */
288#define HDSPM_Latency2 (1<<3) /* by Latency{2,1,0} */
289
0dca1793
AK
290#define HDSPM_ClockModeMaster (1<<4) /* 1=Master, 0=Autosync */
291#define HDSPM_c0Master 0x1 /* Master clock bit in settings
292 register [RayDAT, AIO] */
763f356c
TI
293
294#define HDSPM_AudioInterruptEnable (1<<5) /* what do you think ? */
295
296#define HDSPM_Frequency0 (1<<6) /* 0=44.1kHz/88.2kHz 1=48kHz/96kHz */
297#define HDSPM_Frequency1 (1<<7) /* 0=32kHz/64kHz */
298#define HDSPM_DoubleSpeed (1<<8) /* 0=normal speed, 1=double speed */
3cee5a60 299#define HDSPM_QuadSpeed (1<<31) /* quad speed bit */
763f356c 300
3cee5a60 301#define HDSPM_Professional (1<<9) /* Professional */ /* AES32 ONLY */
763f356c 302#define HDSPM_TX_64ch (1<<10) /* Output 64channel MODE=1,
3cee5a60
RB
303 56channelMODE=0 */ /* MADI ONLY*/
304#define HDSPM_Emphasis (1<<10) /* Emphasis */ /* AES32 ONLY */
763f356c 305
0dca1793 306#define HDSPM_AutoInp (1<<11) /* Auto Input (takeover) == Safe Mode,
3cee5a60
RB
307 0=off, 1=on */ /* MADI ONLY */
308#define HDSPM_Dolby (1<<11) /* Dolby = "NonAudio" ?? */ /* AES32 ONLY */
763f356c 309
ef5fa1a4
TI
310#define HDSPM_InputSelect0 (1<<14) /* Input select 0= optical, 1=coax
311 * -- MADI ONLY
312 */
763f356c
TI
313#define HDSPM_InputSelect1 (1<<15) /* should be 0 */
314
3cee5a60
RB
315#define HDSPM_SyncRef2 (1<<13)
316#define HDSPM_SyncRef3 (1<<25)
763f356c 317
3cee5a60 318#define HDSPM_SMUX (1<<18) /* Frame ??? */ /* MADI ONY */
0dca1793 319#define HDSPM_clr_tms (1<<19) /* clear track marker, do not use
763f356c
TI
320 AES additional bits in
321 lower 5 Audiodatabits ??? */
3cee5a60
RB
322#define HDSPM_taxi_reset (1<<20) /* ??? */ /* MADI ONLY ? */
323#define HDSPM_WCK48 (1<<20) /* Frame ??? = HDSPM_SMUX */ /* AES32 ONLY */
763f356c 324
0dca1793
AK
325#define HDSPM_Midi0InterruptEnable 0x0400000
326#define HDSPM_Midi1InterruptEnable 0x0800000
327#define HDSPM_Midi2InterruptEnable 0x0200000
328#define HDSPM_Midi3InterruptEnable 0x4000000
763f356c
TI
329
330#define HDSPM_LineOut (1<<24) /* Analog Out on channel 63/64 on=1, mute=0 */
0dca1793 331#define HDSPe_FLOAT_FORMAT 0x2000000
763f356c 332
3cee5a60
RB
333#define HDSPM_DS_DoubleWire (1<<26) /* AES32 ONLY */
334#define HDSPM_QS_DoubleWire (1<<27) /* AES32 ONLY */
335#define HDSPM_QS_QuadWire (1<<28) /* AES32 ONLY */
336
337#define HDSPM_wclk_sel (1<<30)
763f356c 338
384f778f
AK
339/* additional control register bits for AIO*/
340#define HDSPM_c0_Wck48 0x20 /* also RayDAT */
341#define HDSPM_c0_Input0 0x1000
342#define HDSPM_c0_Input1 0x2000
343#define HDSPM_c0_Spdif_Opt 0x4000
344#define HDSPM_c0_Pro 0x8000
345#define HDSPM_c0_clr_tms 0x10000
346#define HDSPM_c0_AEB1 0x20000
347#define HDSPM_c0_AEB2 0x40000
348#define HDSPM_c0_LineOut 0x80000
349#define HDSPM_c0_AD_GAIN0 0x100000
350#define HDSPM_c0_AD_GAIN1 0x200000
351#define HDSPM_c0_DA_GAIN0 0x400000
352#define HDSPM_c0_DA_GAIN1 0x800000
353#define HDSPM_c0_PH_GAIN0 0x1000000
354#define HDSPM_c0_PH_GAIN1 0x2000000
355#define HDSPM_c0_Sym6db 0x4000000
356
357
763f356c
TI
358/* --- bit helper defines */
359#define HDSPM_LatencyMask (HDSPM_Latency0|HDSPM_Latency1|HDSPM_Latency2)
ef5fa1a4
TI
360#define HDSPM_FrequencyMask (HDSPM_Frequency0|HDSPM_Frequency1|\
361 HDSPM_DoubleSpeed|HDSPM_QuadSpeed)
763f356c
TI
362#define HDSPM_InputMask (HDSPM_InputSelect0|HDSPM_InputSelect1)
363#define HDSPM_InputOptical 0
364#define HDSPM_InputCoaxial (HDSPM_InputSelect0)
ef5fa1a4
TI
365#define HDSPM_SyncRefMask (HDSPM_SyncRef0|HDSPM_SyncRef1|\
366 HDSPM_SyncRef2|HDSPM_SyncRef3)
763f356c 367
0dca1793
AK
368#define HDSPM_c0_SyncRef0 0x2
369#define HDSPM_c0_SyncRef1 0x4
370#define HDSPM_c0_SyncRef2 0x8
371#define HDSPM_c0_SyncRef3 0x10
372#define HDSPM_c0_SyncRefMask (HDSPM_c0_SyncRef0 | HDSPM_c0_SyncRef1 |\
373 HDSPM_c0_SyncRef2 | HDSPM_c0_SyncRef3)
374
375#define HDSPM_SYNC_FROM_WORD 0 /* Preferred sync reference */
376#define HDSPM_SYNC_FROM_MADI 1 /* choices - used by "pref_sync_ref" */
377#define HDSPM_SYNC_FROM_TCO 2
378#define HDSPM_SYNC_FROM_SYNC_IN 3
763f356c
TI
379
380#define HDSPM_Frequency32KHz HDSPM_Frequency0
381#define HDSPM_Frequency44_1KHz HDSPM_Frequency1
382#define HDSPM_Frequency48KHz (HDSPM_Frequency1|HDSPM_Frequency0)
383#define HDSPM_Frequency64KHz (HDSPM_DoubleSpeed|HDSPM_Frequency0)
384#define HDSPM_Frequency88_2KHz (HDSPM_DoubleSpeed|HDSPM_Frequency1)
ef5fa1a4
TI
385#define HDSPM_Frequency96KHz (HDSPM_DoubleSpeed|HDSPM_Frequency1|\
386 HDSPM_Frequency0)
3cee5a60
RB
387#define HDSPM_Frequency128KHz (HDSPM_QuadSpeed|HDSPM_Frequency0)
388#define HDSPM_Frequency176_4KHz (HDSPM_QuadSpeed|HDSPM_Frequency1)
ef5fa1a4
TI
389#define HDSPM_Frequency192KHz (HDSPM_QuadSpeed|HDSPM_Frequency1|\
390 HDSPM_Frequency0)
763f356c 391
763f356c
TI
392
393/* Synccheck Status */
394#define HDSPM_SYNC_CHECK_NO_LOCK 0
395#define HDSPM_SYNC_CHECK_LOCK 1
396#define HDSPM_SYNC_CHECK_SYNC 2
397
398/* AutoSync References - used by "autosync_ref" control switch */
399#define HDSPM_AUTOSYNC_FROM_WORD 0
400#define HDSPM_AUTOSYNC_FROM_MADI 1
0dca1793
AK
401#define HDSPM_AUTOSYNC_FROM_TCO 2
402#define HDSPM_AUTOSYNC_FROM_SYNC_IN 3
403#define HDSPM_AUTOSYNC_FROM_NONE 4
763f356c
TI
404
405/* Possible sources of MADI input */
406#define HDSPM_OPTICAL 0 /* optical */
407#define HDSPM_COAXIAL 1 /* BNC */
408
409#define hdspm_encode_latency(x) (((x)<<1) & HDSPM_LatencyMask)
0dca1793 410#define hdspm_decode_latency(x) ((((x) & HDSPM_LatencyMask)>>1))
763f356c
TI
411
412#define hdspm_encode_in(x) (((x)&0x3)<<14)
413#define hdspm_decode_in(x) (((x)>>14)&0x3)
414
415/* --- control2 register bits --- */
416#define HDSPM_TMS (1<<0)
417#define HDSPM_TCK (1<<1)
418#define HDSPM_TDI (1<<2)
419#define HDSPM_JTAG (1<<3)
420#define HDSPM_PWDN (1<<4)
421#define HDSPM_PROGRAM (1<<5)
422#define HDSPM_CONFIG_MODE_0 (1<<6)
423#define HDSPM_CONFIG_MODE_1 (1<<7)
424/*#define HDSPM_VERSION_BIT (1<<8) not defined any more*/
425#define HDSPM_BIGENDIAN_MODE (1<<9)
426#define HDSPM_RD_MULTIPLE (1<<10)
427
3cee5a60 428/* --- Status Register bits --- */ /* MADI ONLY */ /* Bits defined here and
ef5fa1a4
TI
429 that do not conflict with specific bits for AES32 seem to be valid also
430 for the AES32
431 */
763f356c 432#define HDSPM_audioIRQPending (1<<0) /* IRQ is high and pending */
ef5fa1a4
TI
433#define HDSPM_RX_64ch (1<<1) /* Input 64chan. MODE=1, 56chn MODE=0 */
434#define HDSPM_AB_int (1<<2) /* InputChannel Opt=0, Coax=1
435 * (like inp0)
436 */
0dca1793 437
763f356c 438#define HDSPM_madiLock (1<<3) /* MADI Locked =1, no=0 */
0dca1793
AK
439#define HDSPM_madiSync (1<<18) /* MADI is in sync */
440
b0bf5504
AK
441#define HDSPM_tcoLockMadi 0x00000020 /* Optional TCO locked status for HDSPe MADI*/
442#define HDSPM_tcoSync 0x10000000 /* Optional TCO sync status for HDSPe MADI and AES32!*/
0dca1793 443
b0bf5504
AK
444#define HDSPM_syncInLock 0x00010000 /* Sync In lock status for HDSPe MADI! */
445#define HDSPM_syncInSync 0x00020000 /* Sync In sync status for HDSPe MADI! */
763f356c
TI
446
447#define HDSPM_BufferPositionMask 0x000FFC0 /* Bit 6..15 : h/w buffer pointer */
0dca1793
AK
448 /* since 64byte accurate, last 6 bits are not used */
449
450
763f356c 451
763f356c
TI
452#define HDSPM_DoubleSpeedStatus (1<<19) /* (input) card in double speed */
453
454#define HDSPM_madiFreq0 (1<<22) /* system freq 0=error */
455#define HDSPM_madiFreq1 (1<<23) /* 1=32, 2=44.1 3=48 */
456#define HDSPM_madiFreq2 (1<<24) /* 4=64, 5=88.2 6=96 */
457#define HDSPM_madiFreq3 (1<<25) /* 7=128, 8=176.4 9=192 */
458
ef5fa1a4
TI
459#define HDSPM_BufferID (1<<26) /* (Double)Buffer ID toggles with
460 * Interrupt
461 */
0dca1793 462#define HDSPM_tco_detect 0x08000000
b0bf5504 463#define HDSPM_tcoLockAes 0x20000000 /* Optional TCO locked status for HDSPe AES */
0dca1793
AK
464
465#define HDSPM_s2_tco_detect 0x00000040
466#define HDSPM_s2_AEBO_D 0x00000080
467#define HDSPM_s2_AEBI_D 0x00000100
468
469
470#define HDSPM_midi0IRQPending 0x40000000
471#define HDSPM_midi1IRQPending 0x80000000
472#define HDSPM_midi2IRQPending 0x20000000
473#define HDSPM_midi2IRQPendingAES 0x00000020
474#define HDSPM_midi3IRQPending 0x00200000
763f356c
TI
475
476/* --- status bit helpers */
ef5fa1a4
TI
477#define HDSPM_madiFreqMask (HDSPM_madiFreq0|HDSPM_madiFreq1|\
478 HDSPM_madiFreq2|HDSPM_madiFreq3)
763f356c
TI
479#define HDSPM_madiFreq32 (HDSPM_madiFreq0)
480#define HDSPM_madiFreq44_1 (HDSPM_madiFreq1)
481#define HDSPM_madiFreq48 (HDSPM_madiFreq0|HDSPM_madiFreq1)
482#define HDSPM_madiFreq64 (HDSPM_madiFreq2)
483#define HDSPM_madiFreq88_2 (HDSPM_madiFreq0|HDSPM_madiFreq2)
484#define HDSPM_madiFreq96 (HDSPM_madiFreq1|HDSPM_madiFreq2)
485#define HDSPM_madiFreq128 (HDSPM_madiFreq0|HDSPM_madiFreq1|HDSPM_madiFreq2)
486#define HDSPM_madiFreq176_4 (HDSPM_madiFreq3)
487#define HDSPM_madiFreq192 (HDSPM_madiFreq3|HDSPM_madiFreq0)
488
3cee5a60 489/* Status2 Register bits */ /* MADI ONLY */
763f356c 490
25985edc 491#define HDSPM_version0 (1<<0) /* not really defined but I guess */
763f356c
TI
492#define HDSPM_version1 (1<<1) /* in former cards it was ??? */
493#define HDSPM_version2 (1<<2)
494
495#define HDSPM_wcLock (1<<3) /* Wordclock is detected and locked */
496#define HDSPM_wcSync (1<<4) /* Wordclock is in sync with systemclock */
497
498#define HDSPM_wc_freq0 (1<<5) /* input freq detected via autosync */
499#define HDSPM_wc_freq1 (1<<6) /* 001=32, 010==44.1, 011=48, */
a8cd7148
AK
500#define HDSPM_wc_freq2 (1<<7) /* 100=64, 101=88.2, 110=96, 111=128 */
501#define HDSPM_wc_freq3 0x800 /* 1000=176.4, 1001=192 */
763f356c 502
0dca1793
AK
503#define HDSPM_SyncRef0 0x10000 /* Sync Reference */
504#define HDSPM_SyncRef1 0x20000
505
506#define HDSPM_SelSyncRef0 (1<<8) /* AutoSync Source */
763f356c
TI
507#define HDSPM_SelSyncRef1 (1<<9) /* 000=word, 001=MADI, */
508#define HDSPM_SelSyncRef2 (1<<10) /* 111=no valid signal */
509
510#define HDSPM_wc_valid (HDSPM_wcLock|HDSPM_wcSync)
511
a8cd7148
AK
512#define HDSPM_wcFreqMask (HDSPM_wc_freq0|HDSPM_wc_freq1|HDSPM_wc_freq2|\
513 HDSPM_wc_freq3)
763f356c
TI
514#define HDSPM_wcFreq32 (HDSPM_wc_freq0)
515#define HDSPM_wcFreq44_1 (HDSPM_wc_freq1)
516#define HDSPM_wcFreq48 (HDSPM_wc_freq0|HDSPM_wc_freq1)
517#define HDSPM_wcFreq64 (HDSPM_wc_freq2)
518#define HDSPM_wcFreq88_2 (HDSPM_wc_freq0|HDSPM_wc_freq2)
519#define HDSPM_wcFreq96 (HDSPM_wc_freq1|HDSPM_wc_freq2)
a8cd7148
AK
520#define HDSPM_wcFreq128 (HDSPM_wc_freq0|HDSPM_wc_freq1|HDSPM_wc_freq2)
521#define HDSPM_wcFreq176_4 (HDSPM_wc_freq3)
522#define HDSPM_wcFreq192 (HDSPM_wc_freq0|HDSPM_wc_freq3)
763f356c 523
0dca1793
AK
524#define HDSPM_status1_F_0 0x0400000
525#define HDSPM_status1_F_1 0x0800000
526#define HDSPM_status1_F_2 0x1000000
527#define HDSPM_status1_F_3 0x2000000
528#define HDSPM_status1_freqMask (HDSPM_status1_F_0|HDSPM_status1_F_1|HDSPM_status1_F_2|HDSPM_status1_F_3)
529
763f356c 530
ef5fa1a4
TI
531#define HDSPM_SelSyncRefMask (HDSPM_SelSyncRef0|HDSPM_SelSyncRef1|\
532 HDSPM_SelSyncRef2)
763f356c
TI
533#define HDSPM_SelSyncRef_WORD 0
534#define HDSPM_SelSyncRef_MADI (HDSPM_SelSyncRef0)
0dca1793
AK
535#define HDSPM_SelSyncRef_TCO (HDSPM_SelSyncRef1)
536#define HDSPM_SelSyncRef_SyncIn (HDSPM_SelSyncRef0|HDSPM_SelSyncRef1)
ef5fa1a4
TI
537#define HDSPM_SelSyncRef_NVALID (HDSPM_SelSyncRef0|HDSPM_SelSyncRef1|\
538 HDSPM_SelSyncRef2)
763f356c 539
3cee5a60
RB
540/*
541 For AES32, bits for status, status2 and timecode are different
542*/
543/* status */
544#define HDSPM_AES32_wcLock 0x0200000
56bde0f3 545#define HDSPM_AES32_wcSync 0x0100000
3cee5a60 546#define HDSPM_AES32_wcFreq_bit 22
0dca1793 547/* (status >> HDSPM_AES32_wcFreq_bit) & 0xF gives WC frequency (cf function
3cee5a60
RB
548 HDSPM_bit2freq */
549#define HDSPM_AES32_syncref_bit 16
550/* (status >> HDSPM_AES32_syncref_bit) & 0xF gives sync source */
551
552#define HDSPM_AES32_AUTOSYNC_FROM_WORD 0
553#define HDSPM_AES32_AUTOSYNC_FROM_AES1 1
554#define HDSPM_AES32_AUTOSYNC_FROM_AES2 2
555#define HDSPM_AES32_AUTOSYNC_FROM_AES3 3
556#define HDSPM_AES32_AUTOSYNC_FROM_AES4 4
557#define HDSPM_AES32_AUTOSYNC_FROM_AES5 5
558#define HDSPM_AES32_AUTOSYNC_FROM_AES6 6
559#define HDSPM_AES32_AUTOSYNC_FROM_AES7 7
560#define HDSPM_AES32_AUTOSYNC_FROM_AES8 8
b0bf5504
AK
561#define HDSPM_AES32_AUTOSYNC_FROM_TCO 9
562#define HDSPM_AES32_AUTOSYNC_FROM_SYNC_IN 10
563#define HDSPM_AES32_AUTOSYNC_FROM_NONE 11
3cee5a60
RB
564
565/* status2 */
566/* HDSPM_LockAES_bit is given by HDSPM_LockAES >> (AES# - 1) */
567#define HDSPM_LockAES 0x80
568#define HDSPM_LockAES1 0x80
569#define HDSPM_LockAES2 0x40
570#define HDSPM_LockAES3 0x20
571#define HDSPM_LockAES4 0x10
572#define HDSPM_LockAES5 0x8
573#define HDSPM_LockAES6 0x4
574#define HDSPM_LockAES7 0x2
575#define HDSPM_LockAES8 0x1
576/*
577 Timecode
578 After windows driver sources, bits 4*i to 4*i+3 give the input frequency on
579 AES i+1
580 bits 3210
581 0001 32kHz
582 0010 44.1kHz
583 0011 48kHz
584 0100 64kHz
585 0101 88.2kHz
586 0110 96kHz
587 0111 128kHz
588 1000 176.4kHz
589 1001 192kHz
590 NB: Timecode register doesn't seem to work on AES32 card revision 230
591*/
592
763f356c
TI
593/* Mixer Values */
594#define UNITY_GAIN 32768 /* = 65536/2 */
595#define MINUS_INFINITY_GAIN 0
596
763f356c
TI
597/* Number of channels for different Speed Modes */
598#define MADI_SS_CHANNELS 64
599#define MADI_DS_CHANNELS 32
600#define MADI_QS_CHANNELS 16
601
0dca1793
AK
602#define RAYDAT_SS_CHANNELS 36
603#define RAYDAT_DS_CHANNELS 20
604#define RAYDAT_QS_CHANNELS 12
605
606#define AIO_IN_SS_CHANNELS 14
607#define AIO_IN_DS_CHANNELS 10
608#define AIO_IN_QS_CHANNELS 8
609#define AIO_OUT_SS_CHANNELS 16
610#define AIO_OUT_DS_CHANNELS 12
611#define AIO_OUT_QS_CHANNELS 10
612
d2d10a21
AK
613#define AES32_CHANNELS 16
614
763f356c
TI
615/* the size of a substream (1 mono data stream) */
616#define HDSPM_CHANNEL_BUFFER_SAMPLES (16*1024)
617#define HDSPM_CHANNEL_BUFFER_BYTES (4*HDSPM_CHANNEL_BUFFER_SAMPLES)
618
619/* the size of the area we need to allocate for DMA transfers. the
620 size is the same regardless of the number of channels, and
0dca1793 621 also the latency to use.
763f356c
TI
622 for one direction !!!
623*/
ffb2c3c0 624#define HDSPM_DMA_AREA_BYTES (HDSPM_MAX_CHANNELS * HDSPM_CHANNEL_BUFFER_BYTES)
763f356c
TI
625#define HDSPM_DMA_AREA_KILOBYTES (HDSPM_DMA_AREA_BYTES/1024)
626
0dca1793
AK
627#define HDSPM_RAYDAT_REV 211
628#define HDSPM_AIO_REV 212
629#define HDSPM_MADIFACE_REV 213
3cee5a60 630
6534599d
RB
631/* speed factor modes */
632#define HDSPM_SPEED_SINGLE 0
633#define HDSPM_SPEED_DOUBLE 1
634#define HDSPM_SPEED_QUAD 2
0dca1793 635
6534599d
RB
636/* names for speed modes */
637static char *hdspm_speed_names[] = { "single", "double", "quad" };
638
eb0d4dbf 639static const char *const texts_autosync_aes_tco[] = { "Word Clock",
0dca1793
AK
640 "AES1", "AES2", "AES3", "AES4",
641 "AES5", "AES6", "AES7", "AES8",
db2d1a91
AK
642 "TCO", "Sync In"
643};
eb0d4dbf 644static const char *const texts_autosync_aes[] = { "Word Clock",
0dca1793 645 "AES1", "AES2", "AES3", "AES4",
db2d1a91
AK
646 "AES5", "AES6", "AES7", "AES8",
647 "Sync In"
648};
eb0d4dbf 649static const char *const texts_autosync_madi_tco[] = { "Word Clock",
0dca1793 650 "MADI", "TCO", "Sync In" };
eb0d4dbf 651static const char *const texts_autosync_madi[] = { "Word Clock",
0dca1793
AK
652 "MADI", "Sync In" };
653
eb0d4dbf 654static const char *const texts_autosync_raydat_tco[] = {
0dca1793
AK
655 "Word Clock",
656 "ADAT 1", "ADAT 2", "ADAT 3", "ADAT 4",
657 "AES", "SPDIF", "TCO", "Sync In"
658};
eb0d4dbf 659static const char *const texts_autosync_raydat[] = {
0dca1793
AK
660 "Word Clock",
661 "ADAT 1", "ADAT 2", "ADAT 3", "ADAT 4",
662 "AES", "SPDIF", "Sync In"
663};
eb0d4dbf 664static const char *const texts_autosync_aio_tco[] = {
0dca1793
AK
665 "Word Clock",
666 "ADAT", "AES", "SPDIF", "TCO", "Sync In"
667};
eb0d4dbf 668static const char *const texts_autosync_aio[] = { "Word Clock",
0dca1793
AK
669 "ADAT", "AES", "SPDIF", "Sync In" };
670
38816545 671static const char *const texts_freq[] = {
0dca1793
AK
672 "No Lock",
673 "32 kHz",
674 "44.1 kHz",
675 "48 kHz",
676 "64 kHz",
677 "88.2 kHz",
678 "96 kHz",
679 "128 kHz",
680 "176.4 kHz",
681 "192 kHz"
682};
683
0dca1793
AK
684static char *texts_ports_madi[] = {
685 "MADI.1", "MADI.2", "MADI.3", "MADI.4", "MADI.5", "MADI.6",
686 "MADI.7", "MADI.8", "MADI.9", "MADI.10", "MADI.11", "MADI.12",
687 "MADI.13", "MADI.14", "MADI.15", "MADI.16", "MADI.17", "MADI.18",
688 "MADI.19", "MADI.20", "MADI.21", "MADI.22", "MADI.23", "MADI.24",
689 "MADI.25", "MADI.26", "MADI.27", "MADI.28", "MADI.29", "MADI.30",
690 "MADI.31", "MADI.32", "MADI.33", "MADI.34", "MADI.35", "MADI.36",
691 "MADI.37", "MADI.38", "MADI.39", "MADI.40", "MADI.41", "MADI.42",
692 "MADI.43", "MADI.44", "MADI.45", "MADI.46", "MADI.47", "MADI.48",
693 "MADI.49", "MADI.50", "MADI.51", "MADI.52", "MADI.53", "MADI.54",
694 "MADI.55", "MADI.56", "MADI.57", "MADI.58", "MADI.59", "MADI.60",
695 "MADI.61", "MADI.62", "MADI.63", "MADI.64",
696};
697
698
699static char *texts_ports_raydat_ss[] = {
700 "ADAT1.1", "ADAT1.2", "ADAT1.3", "ADAT1.4", "ADAT1.5", "ADAT1.6",
701 "ADAT1.7", "ADAT1.8", "ADAT2.1", "ADAT2.2", "ADAT2.3", "ADAT2.4",
702 "ADAT2.5", "ADAT2.6", "ADAT2.7", "ADAT2.8", "ADAT3.1", "ADAT3.2",
703 "ADAT3.3", "ADAT3.4", "ADAT3.5", "ADAT3.6", "ADAT3.7", "ADAT3.8",
704 "ADAT4.1", "ADAT4.2", "ADAT4.3", "ADAT4.4", "ADAT4.5", "ADAT4.6",
705 "ADAT4.7", "ADAT4.8",
706 "AES.L", "AES.R",
707 "SPDIF.L", "SPDIF.R"
708};
709
710static char *texts_ports_raydat_ds[] = {
711 "ADAT1.1", "ADAT1.2", "ADAT1.3", "ADAT1.4",
712 "ADAT2.1", "ADAT2.2", "ADAT2.3", "ADAT2.4",
713 "ADAT3.1", "ADAT3.2", "ADAT3.3", "ADAT3.4",
714 "ADAT4.1", "ADAT4.2", "ADAT4.3", "ADAT4.4",
715 "AES.L", "AES.R",
716 "SPDIF.L", "SPDIF.R"
717};
718
719static char *texts_ports_raydat_qs[] = {
720 "ADAT1.1", "ADAT1.2",
721 "ADAT2.1", "ADAT2.2",
722 "ADAT3.1", "ADAT3.2",
723 "ADAT4.1", "ADAT4.2",
724 "AES.L", "AES.R",
725 "SPDIF.L", "SPDIF.R"
726};
727
728
729static char *texts_ports_aio_in_ss[] = {
730 "Analogue.L", "Analogue.R",
731 "AES.L", "AES.R",
732 "SPDIF.L", "SPDIF.R",
733 "ADAT.1", "ADAT.2", "ADAT.3", "ADAT.4", "ADAT.5", "ADAT.6",
3de9db26
AK
734 "ADAT.7", "ADAT.8",
735 "AEB.1", "AEB.2", "AEB.3", "AEB.4"
0dca1793
AK
736};
737
738static char *texts_ports_aio_out_ss[] = {
739 "Analogue.L", "Analogue.R",
740 "AES.L", "AES.R",
741 "SPDIF.L", "SPDIF.R",
742 "ADAT.1", "ADAT.2", "ADAT.3", "ADAT.4", "ADAT.5", "ADAT.6",
743 "ADAT.7", "ADAT.8",
3de9db26
AK
744 "Phone.L", "Phone.R",
745 "AEB.1", "AEB.2", "AEB.3", "AEB.4"
0dca1793
AK
746};
747
748static char *texts_ports_aio_in_ds[] = {
749 "Analogue.L", "Analogue.R",
750 "AES.L", "AES.R",
751 "SPDIF.L", "SPDIF.R",
3de9db26
AK
752 "ADAT.1", "ADAT.2", "ADAT.3", "ADAT.4",
753 "AEB.1", "AEB.2", "AEB.3", "AEB.4"
0dca1793
AK
754};
755
756static char *texts_ports_aio_out_ds[] = {
757 "Analogue.L", "Analogue.R",
758 "AES.L", "AES.R",
759 "SPDIF.L", "SPDIF.R",
760 "ADAT.1", "ADAT.2", "ADAT.3", "ADAT.4",
3de9db26
AK
761 "Phone.L", "Phone.R",
762 "AEB.1", "AEB.2", "AEB.3", "AEB.4"
0dca1793
AK
763};
764
765static char *texts_ports_aio_in_qs[] = {
766 "Analogue.L", "Analogue.R",
767 "AES.L", "AES.R",
768 "SPDIF.L", "SPDIF.R",
3de9db26
AK
769 "ADAT.1", "ADAT.2", "ADAT.3", "ADAT.4",
770 "AEB.1", "AEB.2", "AEB.3", "AEB.4"
0dca1793
AK
771};
772
773static char *texts_ports_aio_out_qs[] = {
774 "Analogue.L", "Analogue.R",
775 "AES.L", "AES.R",
776 "SPDIF.L", "SPDIF.R",
777 "ADAT.1", "ADAT.2", "ADAT.3", "ADAT.4",
3de9db26
AK
778 "Phone.L", "Phone.R",
779 "AEB.1", "AEB.2", "AEB.3", "AEB.4"
0dca1793
AK
780};
781
432d2500
AK
782static char *texts_ports_aes32[] = {
783 "AES.1", "AES.2", "AES.3", "AES.4", "AES.5", "AES.6", "AES.7",
784 "AES.8", "AES.9.", "AES.10", "AES.11", "AES.12", "AES.13", "AES.14",
785 "AES.15", "AES.16"
786};
787
55a57606
AK
788/* These tables map the ALSA channels 1..N to the channels that we
789 need to use in order to find the relevant channel buffer. RME
790 refers to this kind of mapping as between "the ADAT channel and
791 the DMA channel." We index it using the logical audio channel,
792 and the value is the DMA channel (i.e. channel buffer number)
793 where the data for that channel can be read/written from/to.
794*/
795
796static char channel_map_unity_ss[HDSPM_MAX_CHANNELS] = {
797 0, 1, 2, 3, 4, 5, 6, 7,
798 8, 9, 10, 11, 12, 13, 14, 15,
799 16, 17, 18, 19, 20, 21, 22, 23,
800 24, 25, 26, 27, 28, 29, 30, 31,
801 32, 33, 34, 35, 36, 37, 38, 39,
802 40, 41, 42, 43, 44, 45, 46, 47,
803 48, 49, 50, 51, 52, 53, 54, 55,
804 56, 57, 58, 59, 60, 61, 62, 63
805};
806
55a57606
AK
807static char channel_map_raydat_ss[HDSPM_MAX_CHANNELS] = {
808 4, 5, 6, 7, 8, 9, 10, 11, /* ADAT 1 */
809 12, 13, 14, 15, 16, 17, 18, 19, /* ADAT 2 */
810 20, 21, 22, 23, 24, 25, 26, 27, /* ADAT 3 */
811 28, 29, 30, 31, 32, 33, 34, 35, /* ADAT 4 */
812 0, 1, /* AES */
813 2, 3, /* SPDIF */
814 -1, -1, -1, -1,
815 -1, -1, -1, -1, -1, -1, -1, -1,
816 -1, -1, -1, -1, -1, -1, -1, -1,
817 -1, -1, -1, -1, -1, -1, -1, -1,
818};
819
820static char channel_map_raydat_ds[HDSPM_MAX_CHANNELS] = {
821 4, 5, 6, 7, /* ADAT 1 */
822 8, 9, 10, 11, /* ADAT 2 */
823 12, 13, 14, 15, /* ADAT 3 */
824 16, 17, 18, 19, /* ADAT 4 */
825 0, 1, /* AES */
826 2, 3, /* SPDIF */
827 -1, -1, -1, -1,
828 -1, -1, -1, -1, -1, -1, -1, -1,
829 -1, -1, -1, -1, -1, -1, -1, -1,
830 -1, -1, -1, -1, -1, -1, -1, -1,
831 -1, -1, -1, -1, -1, -1, -1, -1,
832 -1, -1, -1, -1, -1, -1, -1, -1,
833};
834
835static char channel_map_raydat_qs[HDSPM_MAX_CHANNELS] = {
836 4, 5, /* ADAT 1 */
837 6, 7, /* ADAT 2 */
838 8, 9, /* ADAT 3 */
839 10, 11, /* ADAT 4 */
840 0, 1, /* AES */
841 2, 3, /* SPDIF */
842 -1, -1, -1, -1,
843 -1, -1, -1, -1, -1, -1, -1, -1,
844 -1, -1, -1, -1, -1, -1, -1, -1,
845 -1, -1, -1, -1, -1, -1, -1, -1,
846 -1, -1, -1, -1, -1, -1, -1, -1,
847 -1, -1, -1, -1, -1, -1, -1, -1,
848 -1, -1, -1, -1, -1, -1, -1, -1,
849};
850
851static char channel_map_aio_in_ss[HDSPM_MAX_CHANNELS] = {
852 0, 1, /* line in */
853 8, 9, /* aes in, */
854 10, 11, /* spdif in */
855 12, 13, 14, 15, 16, 17, 18, 19, /* ADAT in */
3de9db26
AK
856 2, 3, 4, 5, /* AEB */
857 -1, -1, -1, -1, -1, -1,
55a57606
AK
858 -1, -1, -1, -1, -1, -1, -1, -1,
859 -1, -1, -1, -1, -1, -1, -1, -1,
860 -1, -1, -1, -1, -1, -1, -1, -1,
861 -1, -1, -1, -1, -1, -1, -1, -1,
862 -1, -1, -1, -1, -1, -1, -1, -1,
863};
864
865static char channel_map_aio_out_ss[HDSPM_MAX_CHANNELS] = {
866 0, 1, /* line out */
867 8, 9, /* aes out */
868 10, 11, /* spdif out */
869 12, 13, 14, 15, 16, 17, 18, 19, /* ADAT out */
870 6, 7, /* phone out */
3de9db26
AK
871 2, 3, 4, 5, /* AEB */
872 -1, -1, -1, -1,
55a57606
AK
873 -1, -1, -1, -1, -1, -1, -1, -1,
874 -1, -1, -1, -1, -1, -1, -1, -1,
875 -1, -1, -1, -1, -1, -1, -1, -1,
876 -1, -1, -1, -1, -1, -1, -1, -1,
877 -1, -1, -1, -1, -1, -1, -1, -1,
878};
879
880static char channel_map_aio_in_ds[HDSPM_MAX_CHANNELS] = {
881 0, 1, /* line in */
882 8, 9, /* aes in */
883 10, 11, /* spdif in */
884 12, 14, 16, 18, /* adat in */
3de9db26
AK
885 2, 3, 4, 5, /* AEB */
886 -1, -1,
55a57606
AK
887 -1, -1, -1, -1, -1, -1, -1, -1,
888 -1, -1, -1, -1, -1, -1, -1, -1,
889 -1, -1, -1, -1, -1, -1, -1, -1,
890 -1, -1, -1, -1, -1, -1, -1, -1,
891 -1, -1, -1, -1, -1, -1, -1, -1,
892 -1, -1, -1, -1, -1, -1, -1, -1
893};
894
895static char channel_map_aio_out_ds[HDSPM_MAX_CHANNELS] = {
896 0, 1, /* line out */
897 8, 9, /* aes out */
898 10, 11, /* spdif out */
899 12, 14, 16, 18, /* adat out */
900 6, 7, /* phone out */
3de9db26 901 2, 3, 4, 5, /* AEB */
55a57606
AK
902 -1, -1, -1, -1, -1, -1, -1, -1,
903 -1, -1, -1, -1, -1, -1, -1, -1,
904 -1, -1, -1, -1, -1, -1, -1, -1,
905 -1, -1, -1, -1, -1, -1, -1, -1,
906 -1, -1, -1, -1, -1, -1, -1, -1,
907 -1, -1, -1, -1, -1, -1, -1, -1
908};
909
910static char channel_map_aio_in_qs[HDSPM_MAX_CHANNELS] = {
911 0, 1, /* line in */
912 8, 9, /* aes in */
913 10, 11, /* spdif in */
914 12, 16, /* adat in */
3de9db26
AK
915 2, 3, 4, 5, /* AEB */
916 -1, -1, -1, -1,
55a57606
AK
917 -1, -1, -1, -1, -1, -1, -1, -1,
918 -1, -1, -1, -1, -1, -1, -1, -1,
919 -1, -1, -1, -1, -1, -1, -1, -1,
920 -1, -1, -1, -1, -1, -1, -1, -1,
921 -1, -1, -1, -1, -1, -1, -1, -1,
922 -1, -1, -1, -1, -1, -1, -1, -1
923};
924
925static char channel_map_aio_out_qs[HDSPM_MAX_CHANNELS] = {
926 0, 1, /* line out */
927 8, 9, /* aes out */
928 10, 11, /* spdif out */
929 12, 16, /* adat out */
930 6, 7, /* phone out */
3de9db26
AK
931 2, 3, 4, 5, /* AEB */
932 -1, -1,
55a57606
AK
933 -1, -1, -1, -1, -1, -1, -1, -1,
934 -1, -1, -1, -1, -1, -1, -1, -1,
935 -1, -1, -1, -1, -1, -1, -1, -1,
936 -1, -1, -1, -1, -1, -1, -1, -1,
937 -1, -1, -1, -1, -1, -1, -1, -1,
938 -1, -1, -1, -1, -1, -1, -1, -1
939};
940
432d2500
AK
941static char channel_map_aes32[HDSPM_MAX_CHANNELS] = {
942 0, 1, 2, 3, 4, 5, 6, 7,
943 8, 9, 10, 11, 12, 13, 14, 15,
944 -1, -1, -1, -1, -1, -1, -1, -1,
945 -1, -1, -1, -1, -1, -1, -1, -1,
946 -1, -1, -1, -1, -1, -1, -1, -1,
947 -1, -1, -1, -1, -1, -1, -1, -1,
948 -1, -1, -1, -1, -1, -1, -1, -1,
949 -1, -1, -1, -1, -1, -1, -1, -1
950};
951
98274f07
TI
952struct hdspm_midi {
953 struct hdspm *hdspm;
763f356c 954 int id;
98274f07
TI
955 struct snd_rawmidi *rmidi;
956 struct snd_rawmidi_substream *input;
957 struct snd_rawmidi_substream *output;
763f356c
TI
958 char istimer; /* timer in use */
959 struct timer_list timer;
960 spinlock_t lock;
961 int pending;
0dca1793
AK
962 int dataIn;
963 int statusIn;
964 int dataOut;
965 int statusOut;
966 int ie;
967 int irq;
968};
969
970struct hdspm_tco {
69358fca
MD
971 int input; /* 0: LTC, 1:Video, 2: WC*/
972 int framerate; /* 0=24, 1=25, 2=29.97, 3=29.97d, 4=30, 5=30d */
973 int wordclock; /* 0=1:1, 1=44.1->48, 2=48->44.1 */
974 int samplerate; /* 0=44.1, 1=48, 2= freq from app */
975 int pull; /* 0=0, 1=+0.1%, 2=-0.1%, 3=+4%, 4=-4%*/
0dca1793 976 int term; /* 0 = off, 1 = on */
763f356c
TI
977};
978
98274f07 979struct hdspm {
763f356c 980 spinlock_t lock;
ef5fa1a4
TI
981 /* only one playback and/or capture stream */
982 struct snd_pcm_substream *capture_substream;
983 struct snd_pcm_substream *playback_substream;
763f356c
TI
984
985 char *card_name; /* for procinfo */
3cee5a60
RB
986 unsigned short firmware_rev; /* dont know if relevant (yes if AES32)*/
987
0dca1793 988 uint8_t io_type;
763f356c 989
763f356c
TI
990 int monitor_outs; /* set up monitoring outs init flag */
991
992 u32 control_register; /* cached value */
993 u32 control2_register; /* cached value */
69358fca 994 u32 settings_register; /* cached value for AIO / RayDat (sync reference, master/slave) */
763f356c 995
0dca1793 996 struct hdspm_midi midi[4];
763f356c
TI
997 struct tasklet_struct midi_tasklet;
998
999 size_t period_bytes;
0dca1793
AK
1000 unsigned char ss_in_channels;
1001 unsigned char ds_in_channels;
1002 unsigned char qs_in_channels;
1003 unsigned char ss_out_channels;
1004 unsigned char ds_out_channels;
1005 unsigned char qs_out_channels;
1006
1007 unsigned char max_channels_in;
1008 unsigned char max_channels_out;
1009
286bed0f
TI
1010 signed char *channel_map_in;
1011 signed char *channel_map_out;
0dca1793 1012
286bed0f
TI
1013 signed char *channel_map_in_ss, *channel_map_in_ds, *channel_map_in_qs;
1014 signed char *channel_map_out_ss, *channel_map_out_ds, *channel_map_out_qs;
0dca1793
AK
1015
1016 char **port_names_in;
1017 char **port_names_out;
1018
1019 char **port_names_in_ss, **port_names_in_ds, **port_names_in_qs;
1020 char **port_names_out_ss, **port_names_out_ds, **port_names_out_qs;
763f356c
TI
1021
1022 unsigned char *playback_buffer; /* suitably aligned address */
1023 unsigned char *capture_buffer; /* suitably aligned address */
1024
1025 pid_t capture_pid; /* process id which uses capture */
1026 pid_t playback_pid; /* process id which uses capture */
1027 int running; /* running status */
1028
1029 int last_external_sample_rate; /* samplerate mystic ... */
1030 int last_internal_sample_rate;
1031 int system_sample_rate;
1032
763f356c
TI
1033 int dev; /* Hardware vars... */
1034 int irq;
1035 unsigned long port;
1036 void __iomem *iobase;
1037
1038 int irq_count; /* for debug */
0dca1793 1039 int midiPorts;
763f356c 1040
98274f07
TI
1041 struct snd_card *card; /* one card */
1042 struct snd_pcm *pcm; /* has one pcm */
1043 struct snd_hwdep *hwdep; /* and a hwdep for additional ioctl */
763f356c
TI
1044 struct pci_dev *pci; /* and an pci info */
1045
1046 /* Mixer vars */
ef5fa1a4
TI
1047 /* fast alsa mixer */
1048 struct snd_kcontrol *playback_mixer_ctls[HDSPM_MAX_CHANNELS];
1049 /* but input to much, so not used */
1050 struct snd_kcontrol *input_mixer_ctls[HDSPM_MAX_CHANNELS];
25985edc 1051 /* full mixer accessible over mixer ioctl or hwdep-device */
ef5fa1a4 1052 struct hdspm_mixer *mixer;
763f356c 1053
0dca1793 1054 struct hdspm_tco *tco; /* NULL if no TCO detected */
763f356c 1055
eb0d4dbf 1056 const char *const *texts_autosync;
0dca1793 1057 int texts_autosync_items;
763f356c 1058
0dca1793 1059 cycles_t last_interrupt;
730a5865 1060
7d53a631
AK
1061 unsigned int serial;
1062
730a5865 1063 struct hdspm_peak_rms peak_rms;
763f356c
TI
1064};
1065
763f356c 1066
9baa3c34 1067static const struct pci_device_id snd_hdspm_ids[] = {
763f356c
TI
1068 {
1069 .vendor = PCI_VENDOR_ID_XILINX,
1070 .device = PCI_DEVICE_ID_XILINX_HAMMERFALL_DSP_MADI,
1071 .subvendor = PCI_ANY_ID,
1072 .subdevice = PCI_ANY_ID,
1073 .class = 0,
1074 .class_mask = 0,
1075 .driver_data = 0},
1076 {0,}
1077};
1078
1079MODULE_DEVICE_TABLE(pci, snd_hdspm_ids);
1080
1081/* prototypes */
e23e7a14
BP
1082static int snd_hdspm_create_alsa_devices(struct snd_card *card,
1083 struct hdspm *hdspm);
1084static int snd_hdspm_create_pcm(struct snd_card *card,
1085 struct hdspm *hdspm);
98274f07 1086
0dca1793 1087static inline void snd_hdspm_initialize_midi_flush(struct hdspm *hdspm);
3f7bf918 1088static inline int hdspm_get_pll_freq(struct hdspm *hdspm);
0dca1793
AK
1089static int hdspm_update_simple_mixer_controls(struct hdspm *hdspm);
1090static int hdspm_autosync_ref(struct hdspm *hdspm);
34be7ebb 1091static int hdspm_set_toggle_setting(struct hdspm *hdspm, u32 regmask, int out);
0dca1793 1092static int snd_hdspm_set_defaults(struct hdspm *hdspm);
21a164df 1093static int hdspm_system_clock_mode(struct hdspm *hdspm);
0dca1793 1094static void hdspm_set_sgbuf(struct hdspm *hdspm,
77a23f26 1095 struct snd_pcm_substream *substream,
763f356c
TI
1096 unsigned int reg, int channels);
1097
5b266354
AK
1098static int hdspm_aes_sync_check(struct hdspm *hdspm, int idx);
1099static int hdspm_wc_sync_check(struct hdspm *hdspm);
1100static int hdspm_tco_sync_check(struct hdspm *hdspm);
1101static int hdspm_sync_in_sync_check(struct hdspm *hdspm);
1102
1103static int hdspm_get_aes_sample_rate(struct hdspm *hdspm, int index);
1104static int hdspm_get_tco_sample_rate(struct hdspm *hdspm);
1105static int hdspm_get_wc_sample_rate(struct hdspm *hdspm);
1106
1107
1108
3cee5a60
RB
1109static inline int HDSPM_bit2freq(int n)
1110{
62cef821
DV
1111 static const int bit2freq_tab[] = {
1112 0, 32000, 44100, 48000, 64000, 88200,
3cee5a60
RB
1113 96000, 128000, 176400, 192000 };
1114 if (n < 1 || n > 9)
1115 return 0;
1116 return bit2freq_tab[n];
1117}
1118
b2ed6326
AK
1119static bool hdspm_is_raydat_or_aio(struct hdspm *hdspm)
1120{
1121 return ((AIO == hdspm->io_type) || (RayDAT == hdspm->io_type));
1122}
1123
1124
0dca1793 1125/* Write/read to/from HDSPM with Adresses in Bytes
763f356c
TI
1126 not words but only 32Bit writes are allowed */
1127
98274f07 1128static inline void hdspm_write(struct hdspm * hdspm, unsigned int reg,
763f356c
TI
1129 unsigned int val)
1130{
1131 writel(val, hdspm->iobase + reg);
1132}
1133
98274f07 1134static inline unsigned int hdspm_read(struct hdspm * hdspm, unsigned int reg)
763f356c
TI
1135{
1136 return readl(hdspm->iobase + reg);
1137}
1138
0dca1793
AK
1139/* for each output channel (chan) I have an Input (in) and Playback (pb) Fader
1140 mixer is write only on hardware so we have to cache him for read
763f356c
TI
1141 each fader is a u32, but uses only the first 16 bit */
1142
98274f07 1143static inline int hdspm_read_in_gain(struct hdspm * hdspm, unsigned int chan,
763f356c
TI
1144 unsigned int in)
1145{
5bab2482 1146 if (chan >= HDSPM_MIXER_CHANNELS || in >= HDSPM_MIXER_CHANNELS)
763f356c
TI
1147 return 0;
1148
1149 return hdspm->mixer->ch[chan].in[in];
1150}
1151
98274f07 1152static inline int hdspm_read_pb_gain(struct hdspm * hdspm, unsigned int chan,
763f356c
TI
1153 unsigned int pb)
1154{
5bab2482 1155 if (chan >= HDSPM_MIXER_CHANNELS || pb >= HDSPM_MIXER_CHANNELS)
763f356c
TI
1156 return 0;
1157 return hdspm->mixer->ch[chan].pb[pb];
1158}
1159
62cef821 1160static int hdspm_write_in_gain(struct hdspm *hdspm, unsigned int chan,
763f356c
TI
1161 unsigned int in, unsigned short data)
1162{
1163 if (chan >= HDSPM_MIXER_CHANNELS || in >= HDSPM_MIXER_CHANNELS)
1164 return -1;
1165
1166 hdspm_write(hdspm,
1167 HDSPM_MADI_mixerBase +
1168 ((in + 128 * chan) * sizeof(u32)),
1169 (hdspm->mixer->ch[chan].in[in] = data & 0xFFFF));
1170 return 0;
1171}
1172
62cef821 1173static int hdspm_write_pb_gain(struct hdspm *hdspm, unsigned int chan,
763f356c
TI
1174 unsigned int pb, unsigned short data)
1175{
1176 if (chan >= HDSPM_MIXER_CHANNELS || pb >= HDSPM_MIXER_CHANNELS)
1177 return -1;
1178
1179 hdspm_write(hdspm,
1180 HDSPM_MADI_mixerBase +
1181 ((64 + pb + 128 * chan) * sizeof(u32)),
1182 (hdspm->mixer->ch[chan].pb[pb] = data & 0xFFFF));
1183 return 0;
1184}
1185
1186
1187/* enable DMA for specific channels, now available for DSP-MADI */
98274f07 1188static inline void snd_hdspm_enable_in(struct hdspm * hdspm, int i, int v)
763f356c
TI
1189{
1190 hdspm_write(hdspm, HDSPM_inputEnableBase + (4 * i), v);
1191}
1192
98274f07 1193static inline void snd_hdspm_enable_out(struct hdspm * hdspm, int i, int v)
763f356c
TI
1194{
1195 hdspm_write(hdspm, HDSPM_outputEnableBase + (4 * i), v);
1196}
1197
1198/* check if same process is writing and reading */
62cef821 1199static int snd_hdspm_use_is_exclusive(struct hdspm *hdspm)
763f356c
TI
1200{
1201 unsigned long flags;
1202 int ret = 1;
1203
1204 spin_lock_irqsave(&hdspm->lock, flags);
1205 if ((hdspm->playback_pid != hdspm->capture_pid) &&
1206 (hdspm->playback_pid >= 0) && (hdspm->capture_pid >= 0)) {
1207 ret = 0;
1208 }
1209 spin_unlock_irqrestore(&hdspm->lock, flags);
1210 return ret;
1211}
1212
fcdc4ba1
AK
1213/* round arbitary sample rates to commonly known rates */
1214static int hdspm_round_frequency(int rate)
1215{
1216 if (rate < 38050)
1217 return 32000;
1218 if (rate < 46008)
1219 return 44100;
1220 else
1221 return 48000;
1222}
1223
a8a729fa
AK
1224/* QS and DS rates normally can not be detected
1225 * automatically by the card. Only exception is MADI
1226 * in 96k frame mode.
1227 *
1228 * So if we read SS values (32 .. 48k), check for
1229 * user-provided DS/QS bits in the control register
1230 * and multiply the base frequency accordingly.
1231 */
1232static int hdspm_rate_multiplier(struct hdspm *hdspm, int rate)
1233{
1234 if (rate <= 48000) {
1235 if (hdspm->control_register & HDSPM_QuadSpeed)
1236 return rate * 4;
1237 else if (hdspm->control_register &
1238 HDSPM_DoubleSpeed)
1239 return rate * 2;
68593c93 1240 }
a8a729fa
AK
1241 return rate;
1242}
1243
5b266354 1244/* check for external sample rate, returns the sample rate in Hz*/
62cef821 1245static int hdspm_external_sample_rate(struct hdspm *hdspm)
763f356c 1246{
df57de17 1247 unsigned int status, status2;
0dca1793 1248 int syncref, rate = 0, rate_bits;
3cee5a60 1249
0dca1793
AK
1250 switch (hdspm->io_type) {
1251 case AES32:
1252 status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
1253 status = hdspm_read(hdspm, HDSPM_statusRegister);
0dca1793
AK
1254
1255 syncref = hdspm_autosync_ref(hdspm);
dbae4a0c
AK
1256 switch (syncref) {
1257 case HDSPM_AES32_AUTOSYNC_FROM_WORD:
1258 /* Check WC sync and get sample rate */
1259 if (hdspm_wc_sync_check(hdspm))
1260 return HDSPM_bit2freq(hdspm_get_wc_sample_rate(hdspm));
1261 break;
1262
1263 case HDSPM_AES32_AUTOSYNC_FROM_AES1:
1264 case HDSPM_AES32_AUTOSYNC_FROM_AES2:
1265 case HDSPM_AES32_AUTOSYNC_FROM_AES3:
1266 case HDSPM_AES32_AUTOSYNC_FROM_AES4:
1267 case HDSPM_AES32_AUTOSYNC_FROM_AES5:
1268 case HDSPM_AES32_AUTOSYNC_FROM_AES6:
1269 case HDSPM_AES32_AUTOSYNC_FROM_AES7:
1270 case HDSPM_AES32_AUTOSYNC_FROM_AES8:
1271 /* Check AES sync and get sample rate */
1272 if (hdspm_aes_sync_check(hdspm, syncref - HDSPM_AES32_AUTOSYNC_FROM_AES1))
1273 return HDSPM_bit2freq(hdspm_get_aes_sample_rate(hdspm,
1274 syncref - HDSPM_AES32_AUTOSYNC_FROM_AES1));
1275 break;
1276
1277
1278 case HDSPM_AES32_AUTOSYNC_FROM_TCO:
1279 /* Check TCO sync and get sample rate */
1280 if (hdspm_tco_sync_check(hdspm))
1281 return HDSPM_bit2freq(hdspm_get_tco_sample_rate(hdspm));
1282 break;
1283 default:
1284 return 0;
1285 } /* end switch(syncref) */
0dca1793
AK
1286 break;
1287
1288 case MADIface:
1289 status = hdspm_read(hdspm, HDSPM_statusRegister);
1290
1291 if (!(status & HDSPM_madiLock)) {
1292 rate = 0; /* no lock */
1293 } else {
1294 switch (status & (HDSPM_status1_freqMask)) {
1295 case HDSPM_status1_F_0*1:
1296 rate = 32000; break;
1297 case HDSPM_status1_F_0*2:
1298 rate = 44100; break;
1299 case HDSPM_status1_F_0*3:
1300 rate = 48000; break;
1301 case HDSPM_status1_F_0*4:
1302 rate = 64000; break;
1303 case HDSPM_status1_F_0*5:
1304 rate = 88200; break;
1305 case HDSPM_status1_F_0*6:
1306 rate = 96000; break;
1307 case HDSPM_status1_F_0*7:
1308 rate = 128000; break;
1309 case HDSPM_status1_F_0*8:
1310 rate = 176400; break;
1311 case HDSPM_status1_F_0*9:
1312 rate = 192000; break;
1313 default:
1314 rate = 0; break;
1315 }
1316 }
1317
1318 break;
1319
1320 case MADI:
1321 case AIO:
1322 case RayDAT:
1323 status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
1324 status = hdspm_read(hdspm, HDSPM_statusRegister);
1325 rate = 0;
763f356c 1326
3cee5a60
RB
1327 /* if wordclock has synced freq and wordclock is valid */
1328 if ((status2 & HDSPM_wcLock) != 0 &&
fedf1535 1329 (status2 & HDSPM_SelSyncRef0) == 0) {
763f356c 1330
3cee5a60 1331 rate_bits = status2 & HDSPM_wcFreqMask;
763f356c 1332
0dca1793 1333
3cee5a60
RB
1334 switch (rate_bits) {
1335 case HDSPM_wcFreq32:
1336 rate = 32000;
1337 break;
1338 case HDSPM_wcFreq44_1:
1339 rate = 44100;
1340 break;
1341 case HDSPM_wcFreq48:
1342 rate = 48000;
1343 break;
1344 case HDSPM_wcFreq64:
1345 rate = 64000;
1346 break;
1347 case HDSPM_wcFreq88_2:
1348 rate = 88200;
1349 break;
1350 case HDSPM_wcFreq96:
1351 rate = 96000;
1352 break;
a8cd7148
AK
1353 case HDSPM_wcFreq128:
1354 rate = 128000;
1355 break;
1356 case HDSPM_wcFreq176_4:
1357 rate = 176400;
1358 break;
1359 case HDSPM_wcFreq192:
1360 rate = 192000;
1361 break;
3cee5a60
RB
1362 default:
1363 rate = 0;
1364 break;
1365 }
763f356c 1366 }
763f356c 1367
ef5fa1a4
TI
1368 /* if rate detected and Syncref is Word than have it,
1369 * word has priority to MADI
1370 */
3cee5a60 1371 if (rate != 0 &&
0dca1793 1372 (status2 & HDSPM_SelSyncRefMask) == HDSPM_SelSyncRef_WORD)
7b559397 1373 return hdspm_rate_multiplier(hdspm, rate);
763f356c 1374
0dca1793 1375 /* maybe a madi input (which is taken if sel sync is madi) */
3cee5a60
RB
1376 if (status & HDSPM_madiLock) {
1377 rate_bits = status & HDSPM_madiFreqMask;
763f356c 1378
3cee5a60
RB
1379 switch (rate_bits) {
1380 case HDSPM_madiFreq32:
1381 rate = 32000;
1382 break;
1383 case HDSPM_madiFreq44_1:
1384 rate = 44100;
1385 break;
1386 case HDSPM_madiFreq48:
1387 rate = 48000;
1388 break;
1389 case HDSPM_madiFreq64:
1390 rate = 64000;
1391 break;
1392 case HDSPM_madiFreq88_2:
1393 rate = 88200;
1394 break;
1395 case HDSPM_madiFreq96:
1396 rate = 96000;
1397 break;
1398 case HDSPM_madiFreq128:
1399 rate = 128000;
1400 break;
1401 case HDSPM_madiFreq176_4:
1402 rate = 176400;
1403 break;
1404 case HDSPM_madiFreq192:
1405 rate = 192000;
1406 break;
1407 default:
1408 rate = 0;
1409 break;
1410 }
d12c51d8 1411
fcdc4ba1
AK
1412 } /* endif HDSPM_madiLock */
1413
1414 /* check sample rate from TCO or SYNC_IN */
1415 {
1416 bool is_valid_input = 0;
1417 bool has_sync = 0;
1418
1419 syncref = hdspm_autosync_ref(hdspm);
1420 if (HDSPM_AUTOSYNC_FROM_TCO == syncref) {
1421 is_valid_input = 1;
1422 has_sync = (HDSPM_SYNC_CHECK_SYNC ==
1423 hdspm_tco_sync_check(hdspm));
1424 } else if (HDSPM_AUTOSYNC_FROM_SYNC_IN == syncref) {
1425 is_valid_input = 1;
1426 has_sync = (HDSPM_SYNC_CHECK_SYNC ==
1427 hdspm_sync_in_sync_check(hdspm));
d12c51d8 1428 }
fcdc4ba1
AK
1429
1430 if (is_valid_input && has_sync) {
1431 rate = hdspm_round_frequency(
1432 hdspm_get_pll_freq(hdspm));
1433 }
1434 }
1435
a8a729fa
AK
1436 rate = hdspm_rate_multiplier(hdspm, rate);
1437
0dca1793 1438 break;
763f356c 1439 }
0dca1793
AK
1440
1441 return rate;
763f356c
TI
1442}
1443
7cb155ff
AK
1444/* return latency in samples per period */
1445static int hdspm_get_latency(struct hdspm *hdspm)
1446{
1447 int n;
1448
1449 n = hdspm_decode_latency(hdspm->control_register);
1450
1451 /* Special case for new RME cards with 32 samples period size.
1452 * The three latency bits in the control register
1453 * (HDSP_LatencyMask) encode latency values of 64 samples as
1454 * 0, 128 samples as 1 ... 4096 samples as 6. For old cards, 7
1455 * denotes 8192 samples, but on new cards like RayDAT or AIO,
1456 * it corresponds to 32 samples.
1457 */
1458 if ((7 == n) && (RayDAT == hdspm->io_type || AIO == hdspm->io_type))
1459 n = -1;
1460
1461 return 1 << (n + 6);
1462}
1463
763f356c 1464/* Latency function */
0dca1793 1465static inline void hdspm_compute_period_size(struct hdspm *hdspm)
763f356c 1466{
7cb155ff 1467 hdspm->period_bytes = 4 * hdspm_get_latency(hdspm);
763f356c
TI
1468}
1469
0dca1793
AK
1470
1471static snd_pcm_uframes_t hdspm_hw_pointer(struct hdspm *hdspm)
763f356c
TI
1472{
1473 int position;
1474
1475 position = hdspm_read(hdspm, HDSPM_statusRegister);
483cee77
AK
1476
1477 switch (hdspm->io_type) {
1478 case RayDAT:
1479 case AIO:
1480 position &= HDSPM_BufferPositionMask;
1481 position /= 4; /* Bytes per sample */
1482 break;
1483 default:
1484 position = (position & HDSPM_BufferID) ?
1485 (hdspm->period_bytes / 4) : 0;
1486 }
763f356c
TI
1487
1488 return position;
1489}
1490
1491
98274f07 1492static inline void hdspm_start_audio(struct hdspm * s)
763f356c
TI
1493{
1494 s->control_register |= (HDSPM_AudioInterruptEnable | HDSPM_Start);
1495 hdspm_write(s, HDSPM_controlRegister, s->control_register);
1496}
1497
98274f07 1498static inline void hdspm_stop_audio(struct hdspm * s)
763f356c
TI
1499{
1500 s->control_register &= ~(HDSPM_Start | HDSPM_AudioInterruptEnable);
1501 hdspm_write(s, HDSPM_controlRegister, s->control_register);
1502}
1503
1504/* should I silence all or only opened ones ? doit all for first even is 4MB*/
62cef821 1505static void hdspm_silence_playback(struct hdspm *hdspm)
763f356c
TI
1506{
1507 int i;
1508 int n = hdspm->period_bytes;
1509 void *buf = hdspm->playback_buffer;
1510
da2ea374 1511 if (!buf)
3cee5a60 1512 return;
763f356c
TI
1513
1514 for (i = 0; i < HDSPM_MAX_CHANNELS; i++) {
1515 memset(buf, 0, n);
1516 buf += HDSPM_CHANNEL_BUFFER_BYTES;
1517 }
1518}
1519
0dca1793 1520static int hdspm_set_interrupt_interval(struct hdspm *s, unsigned int frames)
763f356c
TI
1521{
1522 int n;
1523
1524 spin_lock_irq(&s->lock);
1525
2e610270
AK
1526 if (32 == frames) {
1527 /* Special case for new RME cards like RayDAT/AIO which
1528 * support period sizes of 32 samples. Since latency is
1529 * encoded in the three bits of HDSP_LatencyMask, we can only
1530 * have values from 0 .. 7. While 0 still means 64 samples and
1531 * 6 represents 4096 samples on all cards, 7 represents 8192
1532 * on older cards and 32 samples on new cards.
1533 *
1534 * In other words, period size in samples is calculated by
1535 * 2^(n+6) with n ranging from 0 .. 7.
1536 */
1537 n = 7;
1538 } else {
1539 frames >>= 7;
1540 n = 0;
1541 while (frames) {
1542 n++;
1543 frames >>= 1;
1544 }
763f356c 1545 }
2e610270 1546
763f356c
TI
1547 s->control_register &= ~HDSPM_LatencyMask;
1548 s->control_register |= hdspm_encode_latency(n);
1549
1550 hdspm_write(s, HDSPM_controlRegister, s->control_register);
1551
1552 hdspm_compute_period_size(s);
1553
1554 spin_unlock_irq(&s->lock);
1555
1556 return 0;
1557}
1558
0dca1793
AK
1559static u64 hdspm_calc_dds_value(struct hdspm *hdspm, u64 period)
1560{
1561 u64 freq_const;
1562
1563 if (period == 0)
1564 return 0;
1565
1566 switch (hdspm->io_type) {
1567 case MADI:
1568 case AES32:
1569 freq_const = 110069313433624ULL;
1570 break;
1571 case RayDAT:
1572 case AIO:
1573 freq_const = 104857600000000ULL;
1574 break;
1575 case MADIface:
1576 freq_const = 131072000000000ULL;
3d56c8e6
TI
1577 break;
1578 default:
1579 snd_BUG();
1580 return 0;
0dca1793
AK
1581 }
1582
1583 return div_u64(freq_const, period);
1584}
1585
1586
ffb2c3c0
RB
1587static void hdspm_set_dds_value(struct hdspm *hdspm, int rate)
1588{
1589 u64 n;
0dca1793 1590
c1099c32
TI
1591 if (snd_BUG_ON(rate <= 0))
1592 return;
1593
ffb2c3c0
RB
1594 if (rate >= 112000)
1595 rate /= 4;
1596 else if (rate >= 56000)
1597 rate /= 2;
1598
0dca1793
AK
1599 switch (hdspm->io_type) {
1600 case MADIface:
3d56c8e6
TI
1601 n = 131072000000000ULL; /* 125 MHz */
1602 break;
0dca1793
AK
1603 case MADI:
1604 case AES32:
3d56c8e6
TI
1605 n = 110069313433624ULL; /* 105 MHz */
1606 break;
0dca1793
AK
1607 case RayDAT:
1608 case AIO:
3d56c8e6
TI
1609 n = 104857600000000ULL; /* 100 MHz */
1610 break;
1611 default:
1612 snd_BUG();
1613 return;
0dca1793
AK
1614 }
1615
3f7440a6 1616 n = div_u64(n, rate);
ffb2c3c0 1617 /* n should be less than 2^32 for being written to FREQ register */
da3cec35 1618 snd_BUG_ON(n >> 32);
ffb2c3c0
RB
1619 hdspm_write(hdspm, HDSPM_freqReg, (u32)n);
1620}
763f356c
TI
1621
1622/* dummy set rate lets see what happens */
98274f07 1623static int hdspm_set_rate(struct hdspm * hdspm, int rate, int called_internally)
763f356c 1624{
763f356c
TI
1625 int current_rate;
1626 int rate_bits;
1627 int not_set = 0;
6534599d 1628 int current_speed, target_speed;
763f356c
TI
1629
1630 /* ASSUMPTION: hdspm->lock is either set, or there is no need for
1631 it (e.g. during module initialization).
1632 */
1633
1634 if (!(hdspm->control_register & HDSPM_ClockModeMaster)) {
1635
0dca1793 1636 /* SLAVE --- */
763f356c
TI
1637 if (called_internally) {
1638
0dca1793
AK
1639 /* request from ctl or card initialization
1640 just make a warning an remember setting
1641 for future master mode switching */
1642
e3a471d6
TI
1643 dev_warn(hdspm->card->dev,
1644 "Warning: device is not running as a clock master.\n");
763f356c
TI
1645 not_set = 1;
1646 } else {
1647
1648 /* hw_param request while in AutoSync mode */
1649 int external_freq =
1650 hdspm_external_sample_rate(hdspm);
1651
ef5fa1a4
TI
1652 if (hdspm_autosync_ref(hdspm) ==
1653 HDSPM_AUTOSYNC_FROM_NONE) {
763f356c 1654
e3a471d6 1655 dev_warn(hdspm->card->dev,
07cb3272 1656 "Detected no External Sync\n");
763f356c
TI
1657 not_set = 1;
1658
1659 } else if (rate != external_freq) {
1660
e3a471d6
TI
1661 dev_warn(hdspm->card->dev,
1662 "Warning: No AutoSync source for requested rate\n");
763f356c
TI
1663 not_set = 1;
1664 }
1665 }
1666 }
1667
1668 current_rate = hdspm->system_sample_rate;
1669
1670 /* Changing between Singe, Double and Quad speed is not
1671 allowed if any substreams are open. This is because such a change
1672 causes a shift in the location of the DMA buffers and a reduction
1673 in the number of available buffers.
1674
1675 Note that a similar but essentially insoluble problem exists for
1676 externally-driven rate changes. All we can do is to flag rate
0dca1793 1677 changes in the read/write routines.
763f356c
TI
1678 */
1679
6534599d
RB
1680 if (current_rate <= 48000)
1681 current_speed = HDSPM_SPEED_SINGLE;
1682 else if (current_rate <= 96000)
1683 current_speed = HDSPM_SPEED_DOUBLE;
1684 else
1685 current_speed = HDSPM_SPEED_QUAD;
1686
1687 if (rate <= 48000)
1688 target_speed = HDSPM_SPEED_SINGLE;
1689 else if (rate <= 96000)
1690 target_speed = HDSPM_SPEED_DOUBLE;
1691 else
1692 target_speed = HDSPM_SPEED_QUAD;
3cee5a60 1693
763f356c
TI
1694 switch (rate) {
1695 case 32000:
763f356c
TI
1696 rate_bits = HDSPM_Frequency32KHz;
1697 break;
1698 case 44100:
763f356c
TI
1699 rate_bits = HDSPM_Frequency44_1KHz;
1700 break;
1701 case 48000:
763f356c
TI
1702 rate_bits = HDSPM_Frequency48KHz;
1703 break;
1704 case 64000:
763f356c
TI
1705 rate_bits = HDSPM_Frequency64KHz;
1706 break;
1707 case 88200:
763f356c
TI
1708 rate_bits = HDSPM_Frequency88_2KHz;
1709 break;
1710 case 96000:
763f356c
TI
1711 rate_bits = HDSPM_Frequency96KHz;
1712 break;
3cee5a60 1713 case 128000:
3cee5a60
RB
1714 rate_bits = HDSPM_Frequency128KHz;
1715 break;
1716 case 176400:
3cee5a60
RB
1717 rate_bits = HDSPM_Frequency176_4KHz;
1718 break;
1719 case 192000:
3cee5a60
RB
1720 rate_bits = HDSPM_Frequency192KHz;
1721 break;
763f356c
TI
1722 default:
1723 return -EINVAL;
1724 }
1725
6534599d 1726 if (current_speed != target_speed
763f356c 1727 && (hdspm->capture_pid >= 0 || hdspm->playback_pid >= 0)) {
e3a471d6
TI
1728 dev_err(hdspm->card->dev,
1729 "cannot change from %s speed to %s speed mode (capture PID = %d, playback PID = %d)\n",
1730 hdspm_speed_names[current_speed],
1731 hdspm_speed_names[target_speed],
1732 hdspm->capture_pid, hdspm->playback_pid);
763f356c
TI
1733 return -EBUSY;
1734 }
1735
1736 hdspm->control_register &= ~HDSPM_FrequencyMask;
1737 hdspm->control_register |= rate_bits;
1738 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
1739
ffb2c3c0
RB
1740 /* For AES32, need to set DDS value in FREQ register
1741 For MADI, also apparently */
1742 hdspm_set_dds_value(hdspm, rate);
0dca1793
AK
1743
1744 if (AES32 == hdspm->io_type && rate != current_rate)
ffb2c3c0 1745 hdspm_write(hdspm, HDSPM_eeprom_wr, 0);
763f356c
TI
1746
1747 hdspm->system_sample_rate = rate;
1748
0dca1793
AK
1749 if (rate <= 48000) {
1750 hdspm->channel_map_in = hdspm->channel_map_in_ss;
1751 hdspm->channel_map_out = hdspm->channel_map_out_ss;
1752 hdspm->max_channels_in = hdspm->ss_in_channels;
1753 hdspm->max_channels_out = hdspm->ss_out_channels;
1754 hdspm->port_names_in = hdspm->port_names_in_ss;
1755 hdspm->port_names_out = hdspm->port_names_out_ss;
1756 } else if (rate <= 96000) {
1757 hdspm->channel_map_in = hdspm->channel_map_in_ds;
1758 hdspm->channel_map_out = hdspm->channel_map_out_ds;
1759 hdspm->max_channels_in = hdspm->ds_in_channels;
1760 hdspm->max_channels_out = hdspm->ds_out_channels;
1761 hdspm->port_names_in = hdspm->port_names_in_ds;
1762 hdspm->port_names_out = hdspm->port_names_out_ds;
1763 } else {
1764 hdspm->channel_map_in = hdspm->channel_map_in_qs;
1765 hdspm->channel_map_out = hdspm->channel_map_out_qs;
1766 hdspm->max_channels_in = hdspm->qs_in_channels;
1767 hdspm->max_channels_out = hdspm->qs_out_channels;
1768 hdspm->port_names_in = hdspm->port_names_in_qs;
1769 hdspm->port_names_out = hdspm->port_names_out_qs;
1770 }
1771
763f356c
TI
1772 if (not_set != 0)
1773 return -1;
1774
1775 return 0;
1776}
1777
1778/* mainly for init to 0 on load */
98274f07 1779static void all_in_all_mixer(struct hdspm * hdspm, int sgain)
763f356c
TI
1780{
1781 int i, j;
ef5fa1a4
TI
1782 unsigned int gain;
1783
1784 if (sgain > UNITY_GAIN)
1785 gain = UNITY_GAIN;
1786 else if (sgain < 0)
1787 gain = 0;
1788 else
1789 gain = sgain;
763f356c
TI
1790
1791 for (i = 0; i < HDSPM_MIXER_CHANNELS; i++)
1792 for (j = 0; j < HDSPM_MIXER_CHANNELS; j++) {
1793 hdspm_write_in_gain(hdspm, i, j, gain);
1794 hdspm_write_pb_gain(hdspm, i, j, gain);
1795 }
1796}
1797
1798/*----------------------------------------------------------------------------
1799 MIDI
1800 ----------------------------------------------------------------------------*/
1801
ef5fa1a4
TI
1802static inline unsigned char snd_hdspm_midi_read_byte (struct hdspm *hdspm,
1803 int id)
763f356c
TI
1804{
1805 /* the hardware already does the relevant bit-mask with 0xff */
0dca1793 1806 return hdspm_read(hdspm, hdspm->midi[id].dataIn);
763f356c
TI
1807}
1808
ef5fa1a4
TI
1809static inline void snd_hdspm_midi_write_byte (struct hdspm *hdspm, int id,
1810 int val)
763f356c
TI
1811{
1812 /* the hardware already does the relevant bit-mask with 0xff */
0dca1793 1813 return hdspm_write(hdspm, hdspm->midi[id].dataOut, val);
763f356c
TI
1814}
1815
98274f07 1816static inline int snd_hdspm_midi_input_available (struct hdspm *hdspm, int id)
763f356c 1817{
0dca1793 1818 return hdspm_read(hdspm, hdspm->midi[id].statusIn) & 0xFF;
763f356c
TI
1819}
1820
98274f07 1821static inline int snd_hdspm_midi_output_possible (struct hdspm *hdspm, int id)
763f356c
TI
1822{
1823 int fifo_bytes_used;
1824
0dca1793 1825 fifo_bytes_used = hdspm_read(hdspm, hdspm->midi[id].statusOut) & 0xFF;
763f356c
TI
1826
1827 if (fifo_bytes_used < 128)
1828 return 128 - fifo_bytes_used;
1829 else
1830 return 0;
1831}
1832
62cef821 1833static void snd_hdspm_flush_midi_input(struct hdspm *hdspm, int id)
763f356c
TI
1834{
1835 while (snd_hdspm_midi_input_available (hdspm, id))
1836 snd_hdspm_midi_read_byte (hdspm, id);
1837}
1838
98274f07 1839static int snd_hdspm_midi_output_write (struct hdspm_midi *hmidi)
763f356c
TI
1840{
1841 unsigned long flags;
1842 int n_pending;
1843 int to_write;
1844 int i;
1845 unsigned char buf[128];
1846
1847 /* Output is not interrupt driven */
0dca1793 1848
763f356c 1849 spin_lock_irqsave (&hmidi->lock, flags);
ef5fa1a4
TI
1850 if (hmidi->output &&
1851 !snd_rawmidi_transmit_empty (hmidi->output)) {
1852 n_pending = snd_hdspm_midi_output_possible (hmidi->hdspm,
1853 hmidi->id);
1854 if (n_pending > 0) {
1855 if (n_pending > (int)sizeof (buf))
1856 n_pending = sizeof (buf);
0dca1793 1857
ef5fa1a4
TI
1858 to_write = snd_rawmidi_transmit (hmidi->output, buf,
1859 n_pending);
1860 if (to_write > 0) {
0dca1793 1861 for (i = 0; i < to_write; ++i)
ef5fa1a4
TI
1862 snd_hdspm_midi_write_byte (hmidi->hdspm,
1863 hmidi->id,
1864 buf[i]);
763f356c
TI
1865 }
1866 }
1867 }
1868 spin_unlock_irqrestore (&hmidi->lock, flags);
1869 return 0;
1870}
1871
98274f07 1872static int snd_hdspm_midi_input_read (struct hdspm_midi *hmidi)
763f356c 1873{
ef5fa1a4
TI
1874 unsigned char buf[128]; /* this buffer is designed to match the MIDI
1875 * input FIFO size
1876 */
763f356c
TI
1877 unsigned long flags;
1878 int n_pending;
1879 int i;
1880
1881 spin_lock_irqsave (&hmidi->lock, flags);
ef5fa1a4
TI
1882 n_pending = snd_hdspm_midi_input_available (hmidi->hdspm, hmidi->id);
1883 if (n_pending > 0) {
763f356c 1884 if (hmidi->input) {
ef5fa1a4 1885 if (n_pending > (int)sizeof (buf))
763f356c 1886 n_pending = sizeof (buf);
ef5fa1a4
TI
1887 for (i = 0; i < n_pending; ++i)
1888 buf[i] = snd_hdspm_midi_read_byte (hmidi->hdspm,
1889 hmidi->id);
1890 if (n_pending)
1891 snd_rawmidi_receive (hmidi->input, buf,
1892 n_pending);
763f356c
TI
1893 } else {
1894 /* flush the MIDI input FIFO */
ef5fa1a4
TI
1895 while (n_pending--)
1896 snd_hdspm_midi_read_byte (hmidi->hdspm,
1897 hmidi->id);
763f356c
TI
1898 }
1899 }
1900 hmidi->pending = 0;
c0da0014 1901 spin_unlock_irqrestore(&hmidi->lock, flags);
0dca1793 1902
c0da0014 1903 spin_lock_irqsave(&hmidi->hdspm->lock, flags);
0dca1793 1904 hmidi->hdspm->control_register |= hmidi->ie;
ef5fa1a4
TI
1905 hdspm_write(hmidi->hdspm, HDSPM_controlRegister,
1906 hmidi->hdspm->control_register);
c0da0014 1907 spin_unlock_irqrestore(&hmidi->hdspm->lock, flags);
0dca1793 1908
763f356c
TI
1909 return snd_hdspm_midi_output_write (hmidi);
1910}
1911
ef5fa1a4
TI
1912static void
1913snd_hdspm_midi_input_trigger(struct snd_rawmidi_substream *substream, int up)
763f356c 1914{
98274f07
TI
1915 struct hdspm *hdspm;
1916 struct hdspm_midi *hmidi;
763f356c 1917 unsigned long flags;
763f356c 1918
ef5fa1a4 1919 hmidi = substream->rmidi->private_data;
763f356c 1920 hdspm = hmidi->hdspm;
0dca1793 1921
763f356c
TI
1922 spin_lock_irqsave (&hdspm->lock, flags);
1923 if (up) {
0dca1793 1924 if (!(hdspm->control_register & hmidi->ie)) {
763f356c 1925 snd_hdspm_flush_midi_input (hdspm, hmidi->id);
0dca1793 1926 hdspm->control_register |= hmidi->ie;
763f356c
TI
1927 }
1928 } else {
0dca1793 1929 hdspm->control_register &= ~hmidi->ie;
763f356c
TI
1930 }
1931
1932 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
1933 spin_unlock_irqrestore (&hdspm->lock, flags);
1934}
1935
7211ec63 1936static void snd_hdspm_midi_output_timer(struct timer_list *t)
763f356c 1937{
7211ec63 1938 struct hdspm_midi *hmidi = from_timer(hmidi, t, timer);
763f356c 1939 unsigned long flags;
0dca1793 1940
763f356c
TI
1941 snd_hdspm_midi_output_write(hmidi);
1942 spin_lock_irqsave (&hmidi->lock, flags);
1943
1944 /* this does not bump hmidi->istimer, because the
1945 kernel automatically removed the timer when it
1946 expired, and we are now adding it back, thus
0dca1793 1947 leaving istimer wherever it was set before.
763f356c
TI
1948 */
1949
04018e13
TI
1950 if (hmidi->istimer)
1951 mod_timer(&hmidi->timer, 1 + jiffies);
763f356c
TI
1952
1953 spin_unlock_irqrestore (&hmidi->lock, flags);
1954}
1955
ef5fa1a4
TI
1956static void
1957snd_hdspm_midi_output_trigger(struct snd_rawmidi_substream *substream, int up)
763f356c 1958{
98274f07 1959 struct hdspm_midi *hmidi;
763f356c
TI
1960 unsigned long flags;
1961
ef5fa1a4 1962 hmidi = substream->rmidi->private_data;
763f356c
TI
1963 spin_lock_irqsave (&hmidi->lock, flags);
1964 if (up) {
1965 if (!hmidi->istimer) {
7211ec63
KC
1966 timer_setup(&hmidi->timer,
1967 snd_hdspm_midi_output_timer, 0);
04018e13 1968 mod_timer(&hmidi->timer, 1 + jiffies);
763f356c
TI
1969 hmidi->istimer++;
1970 }
1971 } else {
ef5fa1a4 1972 if (hmidi->istimer && --hmidi->istimer <= 0)
763f356c 1973 del_timer (&hmidi->timer);
763f356c
TI
1974 }
1975 spin_unlock_irqrestore (&hmidi->lock, flags);
1976 if (up)
1977 snd_hdspm_midi_output_write(hmidi);
1978}
1979
98274f07 1980static int snd_hdspm_midi_input_open(struct snd_rawmidi_substream *substream)
763f356c 1981{
98274f07 1982 struct hdspm_midi *hmidi;
763f356c 1983
ef5fa1a4 1984 hmidi = substream->rmidi->private_data;
763f356c
TI
1985 spin_lock_irq (&hmidi->lock);
1986 snd_hdspm_flush_midi_input (hmidi->hdspm, hmidi->id);
1987 hmidi->input = substream;
1988 spin_unlock_irq (&hmidi->lock);
1989
1990 return 0;
1991}
1992
98274f07 1993static int snd_hdspm_midi_output_open(struct snd_rawmidi_substream *substream)
763f356c 1994{
98274f07 1995 struct hdspm_midi *hmidi;
763f356c 1996
ef5fa1a4 1997 hmidi = substream->rmidi->private_data;
763f356c
TI
1998 spin_lock_irq (&hmidi->lock);
1999 hmidi->output = substream;
2000 spin_unlock_irq (&hmidi->lock);
2001
2002 return 0;
2003}
2004
98274f07 2005static int snd_hdspm_midi_input_close(struct snd_rawmidi_substream *substream)
763f356c 2006{
98274f07 2007 struct hdspm_midi *hmidi;
763f356c
TI
2008
2009 snd_hdspm_midi_input_trigger (substream, 0);
2010
ef5fa1a4 2011 hmidi = substream->rmidi->private_data;
763f356c
TI
2012 spin_lock_irq (&hmidi->lock);
2013 hmidi->input = NULL;
2014 spin_unlock_irq (&hmidi->lock);
2015
2016 return 0;
2017}
2018
98274f07 2019static int snd_hdspm_midi_output_close(struct snd_rawmidi_substream *substream)
763f356c 2020{
98274f07 2021 struct hdspm_midi *hmidi;
763f356c
TI
2022
2023 snd_hdspm_midi_output_trigger (substream, 0);
2024
ef5fa1a4 2025 hmidi = substream->rmidi->private_data;
763f356c
TI
2026 spin_lock_irq (&hmidi->lock);
2027 hmidi->output = NULL;
2028 spin_unlock_irq (&hmidi->lock);
2029
2030 return 0;
2031}
2032
485885b9 2033static const struct snd_rawmidi_ops snd_hdspm_midi_output =
763f356c
TI
2034{
2035 .open = snd_hdspm_midi_output_open,
2036 .close = snd_hdspm_midi_output_close,
2037 .trigger = snd_hdspm_midi_output_trigger,
2038};
2039
485885b9 2040static const struct snd_rawmidi_ops snd_hdspm_midi_input =
763f356c
TI
2041{
2042 .open = snd_hdspm_midi_input_open,
2043 .close = snd_hdspm_midi_input_close,
2044 .trigger = snd_hdspm_midi_input_trigger,
2045};
2046
e23e7a14
BP
2047static int snd_hdspm_create_midi(struct snd_card *card,
2048 struct hdspm *hdspm, int id)
763f356c
TI
2049{
2050 int err;
7ad210ac 2051 char buf[64];
763f356c
TI
2052
2053 hdspm->midi[id].id = id;
763f356c 2054 hdspm->midi[id].hdspm = hdspm;
763f356c
TI
2055 spin_lock_init (&hdspm->midi[id].lock);
2056
0dca1793
AK
2057 if (0 == id) {
2058 if (MADIface == hdspm->io_type) {
2059 /* MIDI-over-MADI on HDSPe MADIface */
2060 hdspm->midi[0].dataIn = HDSPM_midiDataIn2;
2061 hdspm->midi[0].statusIn = HDSPM_midiStatusIn2;
2062 hdspm->midi[0].dataOut = HDSPM_midiDataOut2;
2063 hdspm->midi[0].statusOut = HDSPM_midiStatusOut2;
2064 hdspm->midi[0].ie = HDSPM_Midi2InterruptEnable;
2065 hdspm->midi[0].irq = HDSPM_midi2IRQPending;
2066 } else {
2067 hdspm->midi[0].dataIn = HDSPM_midiDataIn0;
2068 hdspm->midi[0].statusIn = HDSPM_midiStatusIn0;
2069 hdspm->midi[0].dataOut = HDSPM_midiDataOut0;
2070 hdspm->midi[0].statusOut = HDSPM_midiStatusOut0;
2071 hdspm->midi[0].ie = HDSPM_Midi0InterruptEnable;
2072 hdspm->midi[0].irq = HDSPM_midi0IRQPending;
2073 }
2074 } else if (1 == id) {
2075 hdspm->midi[1].dataIn = HDSPM_midiDataIn1;
2076 hdspm->midi[1].statusIn = HDSPM_midiStatusIn1;
2077 hdspm->midi[1].dataOut = HDSPM_midiDataOut1;
2078 hdspm->midi[1].statusOut = HDSPM_midiStatusOut1;
2079 hdspm->midi[1].ie = HDSPM_Midi1InterruptEnable;
2080 hdspm->midi[1].irq = HDSPM_midi1IRQPending;
2081 } else if ((2 == id) && (MADI == hdspm->io_type)) {
2082 /* MIDI-over-MADI on HDSPe MADI */
2083 hdspm->midi[2].dataIn = HDSPM_midiDataIn2;
2084 hdspm->midi[2].statusIn = HDSPM_midiStatusIn2;
2085 hdspm->midi[2].dataOut = HDSPM_midiDataOut2;
2086 hdspm->midi[2].statusOut = HDSPM_midiStatusOut2;
2087 hdspm->midi[2].ie = HDSPM_Midi2InterruptEnable;
2088 hdspm->midi[2].irq = HDSPM_midi2IRQPending;
2089 } else if (2 == id) {
2090 /* TCO MTC, read only */
2091 hdspm->midi[2].dataIn = HDSPM_midiDataIn2;
2092 hdspm->midi[2].statusIn = HDSPM_midiStatusIn2;
2093 hdspm->midi[2].dataOut = -1;
2094 hdspm->midi[2].statusOut = -1;
2095 hdspm->midi[2].ie = HDSPM_Midi2InterruptEnable;
2096 hdspm->midi[2].irq = HDSPM_midi2IRQPendingAES;
2097 } else if (3 == id) {
2098 /* TCO MTC on HDSPe MADI */
2099 hdspm->midi[3].dataIn = HDSPM_midiDataIn3;
2100 hdspm->midi[3].statusIn = HDSPM_midiStatusIn3;
2101 hdspm->midi[3].dataOut = -1;
2102 hdspm->midi[3].statusOut = -1;
2103 hdspm->midi[3].ie = HDSPM_Midi3InterruptEnable;
2104 hdspm->midi[3].irq = HDSPM_midi3IRQPending;
2105 }
2106
2107 if ((id < 2) || ((2 == id) && ((MADI == hdspm->io_type) ||
2108 (MADIface == hdspm->io_type)))) {
2109 if ((id == 0) && (MADIface == hdspm->io_type)) {
7ad210ac
AB
2110 snprintf(buf, sizeof(buf), "%s MIDIoverMADI",
2111 card->shortname);
0dca1793 2112 } else if ((id == 2) && (MADI == hdspm->io_type)) {
7ad210ac
AB
2113 snprintf(buf, sizeof(buf), "%s MIDIoverMADI",
2114 card->shortname);
0dca1793 2115 } else {
7ad210ac
AB
2116 snprintf(buf, sizeof(buf), "%s MIDI %d",
2117 card->shortname, id+1);
0dca1793
AK
2118 }
2119 err = snd_rawmidi_new(card, buf, id, 1, 1,
2120 &hdspm->midi[id].rmidi);
2121 if (err < 0)
2122 return err;
763f356c 2123
7ad210ac
AB
2124 snprintf(hdspm->midi[id].rmidi->name,
2125 sizeof(hdspm->midi[id].rmidi->name),
2126 "%s MIDI %d", card->id, id+1);
0dca1793
AK
2127 hdspm->midi[id].rmidi->private_data = &hdspm->midi[id];
2128
2129 snd_rawmidi_set_ops(hdspm->midi[id].rmidi,
2130 SNDRV_RAWMIDI_STREAM_OUTPUT,
2131 &snd_hdspm_midi_output);
2132 snd_rawmidi_set_ops(hdspm->midi[id].rmidi,
2133 SNDRV_RAWMIDI_STREAM_INPUT,
2134 &snd_hdspm_midi_input);
2135
2136 hdspm->midi[id].rmidi->info_flags |=
2137 SNDRV_RAWMIDI_INFO_OUTPUT |
2138 SNDRV_RAWMIDI_INFO_INPUT |
2139 SNDRV_RAWMIDI_INFO_DUPLEX;
2140 } else {
2141 /* TCO MTC, read only */
7ad210ac
AB
2142 snprintf(buf, sizeof(buf), "%s MTC %d",
2143 card->shortname, id+1);
0dca1793
AK
2144 err = snd_rawmidi_new(card, buf, id, 1, 1,
2145 &hdspm->midi[id].rmidi);
2146 if (err < 0)
2147 return err;
2148
7ad210ac
AB
2149 snprintf(hdspm->midi[id].rmidi->name,
2150 sizeof(hdspm->midi[id].rmidi->name),
2151 "%s MTC %d", card->id, id+1);
0dca1793 2152 hdspm->midi[id].rmidi->private_data = &hdspm->midi[id];
763f356c 2153
0dca1793
AK
2154 snd_rawmidi_set_ops(hdspm->midi[id].rmidi,
2155 SNDRV_RAWMIDI_STREAM_INPUT,
2156 &snd_hdspm_midi_input);
763f356c 2157
0dca1793
AK
2158 hdspm->midi[id].rmidi->info_flags |= SNDRV_RAWMIDI_INFO_INPUT;
2159 }
763f356c
TI
2160
2161 return 0;
2162}
2163
2164
2165static void hdspm_midi_tasklet(unsigned long arg)
2166{
98274f07 2167 struct hdspm *hdspm = (struct hdspm *)arg;
0dca1793
AK
2168 int i = 0;
2169
2170 while (i < hdspm->midiPorts) {
2171 if (hdspm->midi[i].pending)
2172 snd_hdspm_midi_input_read(&hdspm->midi[i]);
2173
2174 i++;
2175 }
2176}
763f356c
TI
2177
2178
2179/*-----------------------------------------------------------------------------
2180 Status Interface
2181 ----------------------------------------------------------------------------*/
2182
2183/* get the system sample rate which is set */
2184
0dca1793 2185
3f7bf918
AK
2186static inline int hdspm_get_pll_freq(struct hdspm *hdspm)
2187{
2188 unsigned int period, rate;
2189
2190 period = hdspm_read(hdspm, HDSPM_RD_PLL_FREQ);
2191 rate = hdspm_calc_dds_value(hdspm, period);
2192
2193 return rate;
2194}
2195
ddcecf6b 2196/*
0dca1793
AK
2197 * Calculate the real sample rate from the
2198 * current DDS value.
ddcecf6b 2199 */
0dca1793
AK
2200static int hdspm_get_system_sample_rate(struct hdspm *hdspm)
2201{
3f7bf918 2202 unsigned int rate;
0dca1793 2203
3f7bf918 2204 rate = hdspm_get_pll_freq(hdspm);
0dca1793 2205
a97bda7d 2206 if (rate > 207000) {
21a164df
AK
2207 /* Unreasonable high sample rate as seen on PCI MADI cards. */
2208 if (0 == hdspm_system_clock_mode(hdspm)) {
2209 /* master mode, return internal sample rate */
2210 rate = hdspm->system_sample_rate;
2211 } else {
2212 /* slave mode, return external sample rate */
2213 rate = hdspm_external_sample_rate(hdspm);
c1099c32
TI
2214 if (!rate)
2215 rate = hdspm->system_sample_rate;
21a164df 2216 }
a97bda7d
AK
2217 }
2218
0dca1793
AK
2219 return rate;
2220}
2221
2222
763f356c 2223#define HDSPM_SYSTEM_SAMPLE_RATE(xname, xindex) \
f27a64f9
AK
2224{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2225 .name = xname, \
2226 .index = xindex, \
2227 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE |\
2228 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
2229 .info = snd_hdspm_info_system_sample_rate, \
2230 .put = snd_hdspm_put_system_sample_rate, \
2231 .get = snd_hdspm_get_system_sample_rate \
763f356c
TI
2232}
2233
98274f07
TI
2234static int snd_hdspm_info_system_sample_rate(struct snd_kcontrol *kcontrol,
2235 struct snd_ctl_elem_info *uinfo)
763f356c
TI
2236{
2237 uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
2238 uinfo->count = 1;
0dca1793
AK
2239 uinfo->value.integer.min = 27000;
2240 uinfo->value.integer.max = 207000;
2241 uinfo->value.integer.step = 1;
763f356c
TI
2242 return 0;
2243}
2244
0dca1793 2245
98274f07
TI
2246static int snd_hdspm_get_system_sample_rate(struct snd_kcontrol *kcontrol,
2247 struct snd_ctl_elem_value *
763f356c
TI
2248 ucontrol)
2249{
98274f07 2250 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 2251
0dca1793
AK
2252 ucontrol->value.integer.value[0] = hdspm_get_system_sample_rate(hdspm);
2253 return 0;
2254}
2255
41285a98
AK
2256static int snd_hdspm_put_system_sample_rate(struct snd_kcontrol *kcontrol,
2257 struct snd_ctl_elem_value *
2258 ucontrol)
2259{
2260 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
c1099c32 2261 int rate = ucontrol->value.integer.value[0];
41285a98 2262
c1099c32
TI
2263 if (rate < 27000 || rate > 207000)
2264 return -EINVAL;
537e4813 2265 hdspm_set_dds_value(hdspm, ucontrol->value.integer.value[0]);
41285a98
AK
2266 return 0;
2267}
2268
0dca1793 2269
ddcecf6b 2270/*
0dca1793 2271 * Returns the WordClock sample rate class for the given card.
ddcecf6b 2272 */
0dca1793
AK
2273static int hdspm_get_wc_sample_rate(struct hdspm *hdspm)
2274{
2275 int status;
2276
2277 switch (hdspm->io_type) {
2278 case RayDAT:
2279 case AIO:
2280 status = hdspm_read(hdspm, HDSPM_RD_STATUS_1);
2281 return (status >> 16) & 0xF;
2282 break;
a57fea8e
AK
2283 case AES32:
2284 status = hdspm_read(hdspm, HDSPM_statusRegister);
2285 return (status >> HDSPM_AES32_wcFreq_bit) & 0xF;
0dca1793
AK
2286 default:
2287 break;
2288 }
2289
2290
2291 return 0;
2292}
2293
2294
ddcecf6b 2295/*
0dca1793 2296 * Returns the TCO sample rate class for the given card.
ddcecf6b 2297 */
0dca1793
AK
2298static int hdspm_get_tco_sample_rate(struct hdspm *hdspm)
2299{
2300 int status;
2301
2302 if (hdspm->tco) {
2303 switch (hdspm->io_type) {
2304 case RayDAT:
2305 case AIO:
2306 status = hdspm_read(hdspm, HDSPM_RD_STATUS_1);
2307 return (status >> 20) & 0xF;
2308 break;
051c44fe
AK
2309 case AES32:
2310 status = hdspm_read(hdspm, HDSPM_statusRegister);
2311 return (status >> 1) & 0xF;
0dca1793
AK
2312 default:
2313 break;
2314 }
2315 }
2316
2317 return 0;
2318}
2319
2320
ddcecf6b 2321/*
0dca1793 2322 * Returns the SYNC_IN sample rate class for the given card.
ddcecf6b 2323 */
0dca1793
AK
2324static int hdspm_get_sync_in_sample_rate(struct hdspm *hdspm)
2325{
2326 int status;
2327
2328 if (hdspm->tco) {
2329 switch (hdspm->io_type) {
2330 case RayDAT:
2331 case AIO:
2332 status = hdspm_read(hdspm, HDSPM_RD_STATUS_2);
2333 return (status >> 12) & 0xF;
2334 break;
2335 default:
2336 break;
2337 }
2338 }
2339
763f356c
TI
2340 return 0;
2341}
2342
ddcecf6b 2343/*
d3c36ed8 2344 * Returns the AES sample rate class for the given card.
ddcecf6b 2345 */
d3c36ed8
AK
2346static int hdspm_get_aes_sample_rate(struct hdspm *hdspm, int index)
2347{
2348 int timecode;
2349
2350 switch (hdspm->io_type) {
2351 case AES32:
2352 timecode = hdspm_read(hdspm, HDSPM_timecodeRegister);
2353 return (timecode >> (4*index)) & 0xF;
2354 break;
2355 default:
2356 break;
2357 }
2358 return 0;
2359}
0dca1793 2360
ddcecf6b 2361/*
0dca1793
AK
2362 * Returns the sample rate class for input source <idx> for
2363 * 'new style' cards like the AIO and RayDAT.
ddcecf6b 2364 */
0dca1793
AK
2365static int hdspm_get_s1_sample_rate(struct hdspm *hdspm, unsigned int idx)
2366{
2367 int status = hdspm_read(hdspm, HDSPM_RD_STATUS_2);
2368
2369 return (status >> (idx*4)) & 0xF;
2370}
2371
8cea5710 2372#define ENUMERATED_CTL_INFO(info, texts) \
38816545 2373 snd_ctl_enum_info(info, 1, ARRAY_SIZE(texts), texts)
8cea5710 2374
0dca1793 2375
2336142f
AK
2376/* Helper function to query the external sample rate and return the
2377 * corresponding enum to be returned to userspace.
2378 */
2379static int hdspm_external_rate_to_enum(struct hdspm *hdspm)
2380{
2381 int rate = hdspm_external_sample_rate(hdspm);
2382 int i, selected_rate = 0;
2383 for (i = 1; i < 10; i++)
2384 if (HDSPM_bit2freq(i) == rate) {
2385 selected_rate = i;
2386 break;
2387 }
2388 return selected_rate;
2389}
2390
0dca1793 2391
763f356c 2392#define HDSPM_AUTOSYNC_SAMPLE_RATE(xname, xindex) \
0dca1793
AK
2393{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2394 .name = xname, \
2395 .private_value = xindex, \
2396 .access = SNDRV_CTL_ELEM_ACCESS_READ, \
2397 .info = snd_hdspm_info_autosync_sample_rate, \
2398 .get = snd_hdspm_get_autosync_sample_rate \
763f356c
TI
2399}
2400
0dca1793 2401
98274f07
TI
2402static int snd_hdspm_info_autosync_sample_rate(struct snd_kcontrol *kcontrol,
2403 struct snd_ctl_elem_info *uinfo)
763f356c 2404{
e5b7b1fe 2405 ENUMERATED_CTL_INFO(uinfo, texts_freq);
763f356c
TI
2406 return 0;
2407}
2408
0dca1793 2409
98274f07
TI
2410static int snd_hdspm_get_autosync_sample_rate(struct snd_kcontrol *kcontrol,
2411 struct snd_ctl_elem_value *
763f356c
TI
2412 ucontrol)
2413{
98274f07 2414 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 2415
0dca1793
AK
2416 switch (hdspm->io_type) {
2417 case RayDAT:
2418 switch (kcontrol->private_value) {
2419 case 0:
2420 ucontrol->value.enumerated.item[0] =
2421 hdspm_get_wc_sample_rate(hdspm);
2422 break;
2423 case 7:
2424 ucontrol->value.enumerated.item[0] =
2425 hdspm_get_tco_sample_rate(hdspm);
2426 break;
2427 case 8:
2428 ucontrol->value.enumerated.item[0] =
2429 hdspm_get_sync_in_sample_rate(hdspm);
2430 break;
2431 default:
2432 ucontrol->value.enumerated.item[0] =
2433 hdspm_get_s1_sample_rate(hdspm,
2434 kcontrol->private_value-1);
2435 }
d681deaa 2436 break;
763f356c 2437
0dca1793
AK
2438 case AIO:
2439 switch (kcontrol->private_value) {
2440 case 0: /* WC */
2441 ucontrol->value.enumerated.item[0] =
2442 hdspm_get_wc_sample_rate(hdspm);
2443 break;
2444 case 4: /* TCO */
2445 ucontrol->value.enumerated.item[0] =
2446 hdspm_get_tco_sample_rate(hdspm);
2447 break;
2448 case 5: /* SYNC_IN */
2449 ucontrol->value.enumerated.item[0] =
2450 hdspm_get_sync_in_sample_rate(hdspm);
2451 break;
2452 default:
2453 ucontrol->value.enumerated.item[0] =
2454 hdspm_get_s1_sample_rate(hdspm,
1cb7dbf4 2455 kcontrol->private_value-1);
0dca1793 2456 }
d681deaa 2457 break;
7c4a95b5
AK
2458
2459 case AES32:
2460
2461 switch (kcontrol->private_value) {
2462 case 0: /* WC */
2463 ucontrol->value.enumerated.item[0] =
2464 hdspm_get_wc_sample_rate(hdspm);
2465 break;
2466 case 9: /* TCO */
2467 ucontrol->value.enumerated.item[0] =
2468 hdspm_get_tco_sample_rate(hdspm);
2469 break;
2470 case 10: /* SYNC_IN */
2471 ucontrol->value.enumerated.item[0] =
2472 hdspm_get_sync_in_sample_rate(hdspm);
2473 break;
2d63ec38
AK
2474 case 11: /* External Rate */
2475 ucontrol->value.enumerated.item[0] =
2476 hdspm_external_rate_to_enum(hdspm);
2477 break;
7c4a95b5
AK
2478 default: /* AES1 to AES8 */
2479 ucontrol->value.enumerated.item[0] =
2d63ec38
AK
2480 hdspm_get_aes_sample_rate(hdspm,
2481 kcontrol->private_value -
2482 HDSPM_AES32_AUTOSYNC_FROM_AES1);
7c4a95b5 2483 break;
7c4a95b5 2484 }
d681deaa 2485 break;
b8812c55
AK
2486
2487 case MADI:
2488 case MADIface:
2336142f
AK
2489 ucontrol->value.enumerated.item[0] =
2490 hdspm_external_rate_to_enum(hdspm);
b8812c55 2491 break;
763f356c 2492 default:
0dca1793 2493 break;
763f356c 2494 }
763f356c 2495
0dca1793 2496 return 0;
763f356c
TI
2497}
2498
2499
0dca1793
AK
2500#define HDSPM_SYSTEM_CLOCK_MODE(xname, xindex) \
2501{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2502 .name = xname, \
2503 .index = xindex, \
2504 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE |\
2505 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
2506 .info = snd_hdspm_info_system_clock_mode, \
2507 .get = snd_hdspm_get_system_clock_mode, \
2508 .put = snd_hdspm_put_system_clock_mode, \
2509}
2510
2511
ddcecf6b 2512/*
0dca1793
AK
2513 * Returns the system clock mode for the given card.
2514 * @returns 0 - master, 1 - slave
ddcecf6b 2515 */
0dca1793
AK
2516static int hdspm_system_clock_mode(struct hdspm *hdspm)
2517{
2518 switch (hdspm->io_type) {
2519 case AIO:
2520 case RayDAT:
2521 if (hdspm->settings_register & HDSPM_c0Master)
2522 return 0;
2523 break;
763f356c 2524
0dca1793
AK
2525 default:
2526 if (hdspm->control_register & HDSPM_ClockModeMaster)
2527 return 0;
2528 }
763f356c 2529
763f356c
TI
2530 return 1;
2531}
2532
0dca1793 2533
ddcecf6b 2534/*
0dca1793
AK
2535 * Sets the system clock mode.
2536 * @param mode 0 - master, 1 - slave
ddcecf6b 2537 */
0dca1793
AK
2538static void hdspm_set_system_clock_mode(struct hdspm *hdspm, int mode)
2539{
34be7ebb
AK
2540 hdspm_set_toggle_setting(hdspm,
2541 (hdspm_is_raydat_or_aio(hdspm)) ?
2542 HDSPM_c0Master : HDSPM_ClockModeMaster,
2543 (0 == mode));
0dca1793
AK
2544}
2545
2546
2547static int snd_hdspm_info_system_clock_mode(struct snd_kcontrol *kcontrol,
98274f07 2548 struct snd_ctl_elem_info *uinfo)
763f356c 2549{
38816545 2550 static const char *const texts[] = { "Master", "AutoSync" };
e5b7b1fe 2551 ENUMERATED_CTL_INFO(uinfo, texts);
763f356c
TI
2552 return 0;
2553}
2554
98274f07
TI
2555static int snd_hdspm_get_system_clock_mode(struct snd_kcontrol *kcontrol,
2556 struct snd_ctl_elem_value *ucontrol)
763f356c 2557{
98274f07 2558 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 2559
0dca1793 2560 ucontrol->value.enumerated.item[0] = hdspm_system_clock_mode(hdspm);
763f356c
TI
2561 return 0;
2562}
2563
0dca1793
AK
2564static int snd_hdspm_put_system_clock_mode(struct snd_kcontrol *kcontrol,
2565 struct snd_ctl_elem_value *ucontrol)
2566{
2567 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
2568 int val;
2569
2570 if (!snd_hdspm_use_is_exclusive(hdspm))
2571 return -EBUSY;
2572
2573 val = ucontrol->value.enumerated.item[0];
2574 if (val < 0)
2575 val = 0;
2576 else if (val > 1)
2577 val = 1;
2578
2579 hdspm_set_system_clock_mode(hdspm, val);
2580
2581 return 0;
2582}
2583
2584
2585#define HDSPM_INTERNAL_CLOCK(xname, xindex) \
2586{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
2587 .name = xname, \
2588 .index = xindex, \
2589 .info = snd_hdspm_info_clock_source, \
2590 .get = snd_hdspm_get_clock_source, \
2591 .put = snd_hdspm_put_clock_source \
763f356c
TI
2592}
2593
0dca1793 2594
98274f07 2595static int hdspm_clock_source(struct hdspm * hdspm)
763f356c 2596{
0dca1793
AK
2597 switch (hdspm->system_sample_rate) {
2598 case 32000: return 0;
2599 case 44100: return 1;
2600 case 48000: return 2;
2601 case 64000: return 3;
2602 case 88200: return 4;
2603 case 96000: return 5;
2604 case 128000: return 6;
2605 case 176400: return 7;
2606 case 192000: return 8;
763f356c 2607 }
0dca1793
AK
2608
2609 return -1;
763f356c
TI
2610}
2611
98274f07 2612static int hdspm_set_clock_source(struct hdspm * hdspm, int mode)
763f356c
TI
2613{
2614 int rate;
2615 switch (mode) {
0dca1793
AK
2616 case 0:
2617 rate = 32000; break;
2618 case 1:
2619 rate = 44100; break;
2620 case 2:
2621 rate = 48000; break;
2622 case 3:
2623 rate = 64000; break;
2624 case 4:
2625 rate = 88200; break;
2626 case 5:
2627 rate = 96000; break;
2628 case 6:
2629 rate = 128000; break;
2630 case 7:
2631 rate = 176400; break;
2632 case 8:
2633 rate = 192000; break;
763f356c 2634 default:
0dca1793 2635 rate = 48000;
763f356c 2636 }
763f356c
TI
2637 hdspm_set_rate(hdspm, rate, 1);
2638 return 0;
2639}
2640
98274f07
TI
2641static int snd_hdspm_info_clock_source(struct snd_kcontrol *kcontrol,
2642 struct snd_ctl_elem_info *uinfo)
763f356c 2643{
c69a637b 2644 return snd_ctl_enum_info(uinfo, 1, 9, texts_freq + 1);
763f356c
TI
2645}
2646
98274f07
TI
2647static int snd_hdspm_get_clock_source(struct snd_kcontrol *kcontrol,
2648 struct snd_ctl_elem_value *ucontrol)
763f356c 2649{
98274f07 2650 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2651
2652 ucontrol->value.enumerated.item[0] = hdspm_clock_source(hdspm);
2653 return 0;
2654}
2655
98274f07
TI
2656static int snd_hdspm_put_clock_source(struct snd_kcontrol *kcontrol,
2657 struct snd_ctl_elem_value *ucontrol)
763f356c 2658{
98274f07 2659 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
2660 int change;
2661 int val;
2662
2663 if (!snd_hdspm_use_is_exclusive(hdspm))
2664 return -EBUSY;
2665 val = ucontrol->value.enumerated.item[0];
2666 if (val < 0)
2667 val = 0;
6534599d
RB
2668 if (val > 9)
2669 val = 9;
763f356c
TI
2670 spin_lock_irq(&hdspm->lock);
2671 if (val != hdspm_clock_source(hdspm))
2672 change = (hdspm_set_clock_source(hdspm, val) == 0) ? 1 : 0;
2673 else
2674 change = 0;
2675 spin_unlock_irq(&hdspm->lock);
2676 return change;
2677}
2678
763f356c 2679
0dca1793 2680#define HDSPM_PREF_SYNC_REF(xname, xindex) \
f27a64f9 2681{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
0dca1793
AK
2682 .name = xname, \
2683 .index = xindex, \
2684 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE |\
2685 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
2686 .info = snd_hdspm_info_pref_sync_ref, \
2687 .get = snd_hdspm_get_pref_sync_ref, \
2688 .put = snd_hdspm_put_pref_sync_ref \
2689}
2690
2691
ddcecf6b 2692/*
0dca1793
AK
2693 * Returns the current preferred sync reference setting.
2694 * The semantics of the return value are depending on the
2695 * card, please see the comments for clarification.
ddcecf6b 2696 */
98274f07 2697static int hdspm_pref_sync_ref(struct hdspm * hdspm)
763f356c 2698{
0dca1793
AK
2699 switch (hdspm->io_type) {
2700 case AES32:
3cee5a60 2701 switch (hdspm->control_register & HDSPM_SyncRefMask) {
0dca1793
AK
2702 case 0: return 0; /* WC */
2703 case HDSPM_SyncRef0: return 1; /* AES 1 */
2704 case HDSPM_SyncRef1: return 2; /* AES 2 */
2705 case HDSPM_SyncRef1+HDSPM_SyncRef0: return 3; /* AES 3 */
2706 case HDSPM_SyncRef2: return 4; /* AES 4 */
2707 case HDSPM_SyncRef2+HDSPM_SyncRef0: return 5; /* AES 5 */
2708 case HDSPM_SyncRef2+HDSPM_SyncRef1: return 6; /* AES 6 */
2709 case HDSPM_SyncRef2+HDSPM_SyncRef1+HDSPM_SyncRef0:
2710 return 7; /* AES 7 */
2711 case HDSPM_SyncRef3: return 8; /* AES 8 */
2712 case HDSPM_SyncRef3+HDSPM_SyncRef0: return 9; /* TCO */
3cee5a60 2713 }
0dca1793
AK
2714 break;
2715
2716 case MADI:
2717 case MADIface:
2718 if (hdspm->tco) {
2719 switch (hdspm->control_register & HDSPM_SyncRefMask) {
2720 case 0: return 0; /* WC */
2721 case HDSPM_SyncRef0: return 1; /* MADI */
2722 case HDSPM_SyncRef1: return 2; /* TCO */
2723 case HDSPM_SyncRef1+HDSPM_SyncRef0:
2724 return 3; /* SYNC_IN */
2725 }
2726 } else {
2727 switch (hdspm->control_register & HDSPM_SyncRefMask) {
2728 case 0: return 0; /* WC */
2729 case HDSPM_SyncRef0: return 1; /* MADI */
2730 case HDSPM_SyncRef1+HDSPM_SyncRef0:
2731 return 2; /* SYNC_IN */
2732 }
2733 }
2734 break;
2735
2736 case RayDAT:
2737 if (hdspm->tco) {
2738 switch ((hdspm->settings_register &
2739 HDSPM_c0_SyncRefMask) / HDSPM_c0_SyncRef0) {
2740 case 0: return 0; /* WC */
2741 case 3: return 1; /* ADAT 1 */
2742 case 4: return 2; /* ADAT 2 */
2743 case 5: return 3; /* ADAT 3 */
2744 case 6: return 4; /* ADAT 4 */
2745 case 1: return 5; /* AES */
2746 case 2: return 6; /* SPDIF */
2747 case 9: return 7; /* TCO */
2748 case 10: return 8; /* SYNC_IN */
2749 }
2750 } else {
2751 switch ((hdspm->settings_register &
2752 HDSPM_c0_SyncRefMask) / HDSPM_c0_SyncRef0) {
2753 case 0: return 0; /* WC */
2754 case 3: return 1; /* ADAT 1 */
2755 case 4: return 2; /* ADAT 2 */
2756 case 5: return 3; /* ADAT 3 */
2757 case 6: return 4; /* ADAT 4 */
2758 case 1: return 5; /* AES */
2759 case 2: return 6; /* SPDIF */
2760 case 10: return 7; /* SYNC_IN */
2761 }
3cee5a60 2762 }
0dca1793
AK
2763
2764 break;
2765
2766 case AIO:
2767 if (hdspm->tco) {
2768 switch ((hdspm->settings_register &
2769 HDSPM_c0_SyncRefMask) / HDSPM_c0_SyncRef0) {
2770 case 0: return 0; /* WC */
2771 case 3: return 1; /* ADAT */
2772 case 1: return 2; /* AES */
2773 case 2: return 3; /* SPDIF */
2774 case 9: return 4; /* TCO */
2775 case 10: return 5; /* SYNC_IN */
2776 }
2777 } else {
2778 switch ((hdspm->settings_register &
2779 HDSPM_c0_SyncRefMask) / HDSPM_c0_SyncRef0) {
2780 case 0: return 0; /* WC */
2781 case 3: return 1; /* ADAT */
2782 case 1: return 2; /* AES */
2783 case 2: return 3; /* SPDIF */
2784 case 10: return 4; /* SYNC_IN */
2785 }
2786 }
2787
2788 break;
763f356c
TI
2789 }
2790
0dca1793 2791 return -1;
763f356c
TI
2792}
2793
0dca1793 2794
ddcecf6b 2795/*
0dca1793
AK
2796 * Set the preferred sync reference to <pref>. The semantics
2797 * of <pref> are depending on the card type, see the comments
2798 * for clarification.
ddcecf6b 2799 */
98274f07 2800static int hdspm_set_pref_sync_ref(struct hdspm * hdspm, int pref)
763f356c 2801{
0dca1793 2802 int p = 0;
763f356c 2803
0dca1793
AK
2804 switch (hdspm->io_type) {
2805 case AES32:
2806 hdspm->control_register &= ~HDSPM_SyncRefMask;
3cee5a60 2807 switch (pref) {
0dca1793
AK
2808 case 0: /* WC */
2809 break;
2810 case 1: /* AES 1 */
2811 hdspm->control_register |= HDSPM_SyncRef0;
2812 break;
2813 case 2: /* AES 2 */
2814 hdspm->control_register |= HDSPM_SyncRef1;
2815 break;
2816 case 3: /* AES 3 */
2817 hdspm->control_register |=
2818 HDSPM_SyncRef1+HDSPM_SyncRef0;
2819 break;
2820 case 4: /* AES 4 */
2821 hdspm->control_register |= HDSPM_SyncRef2;
2822 break;
2823 case 5: /* AES 5 */
2824 hdspm->control_register |=
2825 HDSPM_SyncRef2+HDSPM_SyncRef0;
2826 break;
2827 case 6: /* AES 6 */
2828 hdspm->control_register |=
2829 HDSPM_SyncRef2+HDSPM_SyncRef1;
2830 break;
2831 case 7: /* AES 7 */
2832 hdspm->control_register |=
2833 HDSPM_SyncRef2+HDSPM_SyncRef1+HDSPM_SyncRef0;
3cee5a60 2834 break;
0dca1793
AK
2835 case 8: /* AES 8 */
2836 hdspm->control_register |= HDSPM_SyncRef3;
2837 break;
2838 case 9: /* TCO */
2839 hdspm->control_register |=
2840 HDSPM_SyncRef3+HDSPM_SyncRef0;
3cee5a60
RB
2841 break;
2842 default:
2843 return -1;
2844 }
0dca1793
AK
2845
2846 break;
2847
2848 case MADI:
2849 case MADIface:
2850 hdspm->control_register &= ~HDSPM_SyncRefMask;
2851 if (hdspm->tco) {
2852 switch (pref) {
2853 case 0: /* WC */
2854 break;
2855 case 1: /* MADI */
2856 hdspm->control_register |= HDSPM_SyncRef0;
2857 break;
2858 case 2: /* TCO */
2859 hdspm->control_register |= HDSPM_SyncRef1;
2860 break;
2861 case 3: /* SYNC_IN */
2862 hdspm->control_register |=
2863 HDSPM_SyncRef0+HDSPM_SyncRef1;
2864 break;
2865 default:
2866 return -1;
2867 }
2868 } else {
2869 switch (pref) {
2870 case 0: /* WC */
2871 break;
2872 case 1: /* MADI */
2873 hdspm->control_register |= HDSPM_SyncRef0;
2874 break;
2875 case 2: /* SYNC_IN */
2876 hdspm->control_register |=
2877 HDSPM_SyncRef0+HDSPM_SyncRef1;
2878 break;
2879 default:
2880 return -1;
2881 }
2882 }
2883
2884 break;
2885
2886 case RayDAT:
2887 if (hdspm->tco) {
2888 switch (pref) {
2889 case 0: p = 0; break; /* WC */
2890 case 1: p = 3; break; /* ADAT 1 */
2891 case 2: p = 4; break; /* ADAT 2 */
2892 case 3: p = 5; break; /* ADAT 3 */
2893 case 4: p = 6; break; /* ADAT 4 */
2894 case 5: p = 1; break; /* AES */
2895 case 6: p = 2; break; /* SPDIF */
2896 case 7: p = 9; break; /* TCO */
2897 case 8: p = 10; break; /* SYNC_IN */
2898 default: return -1;
2899 }
2900 } else {
2901 switch (pref) {
2902 case 0: p = 0; break; /* WC */
2903 case 1: p = 3; break; /* ADAT 1 */
2904 case 2: p = 4; break; /* ADAT 2 */
2905 case 3: p = 5; break; /* ADAT 3 */
2906 case 4: p = 6; break; /* ADAT 4 */
2907 case 5: p = 1; break; /* AES */
2908 case 6: p = 2; break; /* SPDIF */
2909 case 7: p = 10; break; /* SYNC_IN */
2910 default: return -1;
2911 }
2912 }
2913 break;
2914
2915 case AIO:
2916 if (hdspm->tco) {
2917 switch (pref) {
2918 case 0: p = 0; break; /* WC */
2919 case 1: p = 3; break; /* ADAT */
2920 case 2: p = 1; break; /* AES */
2921 case 3: p = 2; break; /* SPDIF */
2922 case 4: p = 9; break; /* TCO */
2923 case 5: p = 10; break; /* SYNC_IN */
2924 default: return -1;
2925 }
2926 } else {
2927 switch (pref) {
2928 case 0: p = 0; break; /* WC */
2929 case 1: p = 3; break; /* ADAT */
2930 case 2: p = 1; break; /* AES */
2931 case 3: p = 2; break; /* SPDIF */
2932 case 4: p = 10; break; /* SYNC_IN */
2933 default: return -1;
2934 }
2935 }
2936 break;
763f356c 2937 }
0dca1793
AK
2938
2939 switch (hdspm->io_type) {
2940 case RayDAT:
2941 case AIO:
2942 hdspm->settings_register &= ~HDSPM_c0_SyncRefMask;
2943 hdspm->settings_register |= HDSPM_c0_SyncRef0 * p;
2944 hdspm_write(hdspm, HDSPM_WR_SETTINGS, hdspm->settings_register);
2945 break;
2946
2947 case MADI:
2948 case MADIface:
2949 case AES32:
2950 hdspm_write(hdspm, HDSPM_controlRegister,
2951 hdspm->control_register);
2952 }
2953
763f356c
TI
2954 return 0;
2955}
2956
0dca1793 2957
98274f07
TI
2958static int snd_hdspm_info_pref_sync_ref(struct snd_kcontrol *kcontrol,
2959 struct snd_ctl_elem_info *uinfo)
763f356c 2960{
3cee5a60 2961 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 2962
eb0d4dbf 2963 snd_ctl_enum_info(uinfo, 1, hdspm->texts_autosync_items, hdspm->texts_autosync);
3cee5a60 2964
763f356c
TI
2965 return 0;
2966}
2967
98274f07
TI
2968static int snd_hdspm_get_pref_sync_ref(struct snd_kcontrol *kcontrol,
2969 struct snd_ctl_elem_value *ucontrol)
763f356c 2970{
98274f07 2971 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
0dca1793 2972 int psf = hdspm_pref_sync_ref(hdspm);
763f356c 2973
0dca1793
AK
2974 if (psf >= 0) {
2975 ucontrol->value.enumerated.item[0] = psf;
2976 return 0;
2977 }
2978
2979 return -1;
763f356c
TI
2980}
2981
98274f07
TI
2982static int snd_hdspm_put_pref_sync_ref(struct snd_kcontrol *kcontrol,
2983 struct snd_ctl_elem_value *ucontrol)
763f356c 2984{
98274f07 2985 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
0dca1793 2986 int val, change = 0;
763f356c
TI
2987
2988 if (!snd_hdspm_use_is_exclusive(hdspm))
2989 return -EBUSY;
2990
0dca1793
AK
2991 val = ucontrol->value.enumerated.item[0];
2992
2993 if (val < 0)
2994 val = 0;
2995 else if (val >= hdspm->texts_autosync_items)
2996 val = hdspm->texts_autosync_items-1;
763f356c
TI
2997
2998 spin_lock_irq(&hdspm->lock);
0dca1793
AK
2999 if (val != hdspm_pref_sync_ref(hdspm))
3000 change = (0 == hdspm_set_pref_sync_ref(hdspm, val)) ? 1 : 0;
3001
763f356c
TI
3002 spin_unlock_irq(&hdspm->lock);
3003 return change;
3004}
3005
0dca1793 3006
763f356c 3007#define HDSPM_AUTOSYNC_REF(xname, xindex) \
f27a64f9
AK
3008{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3009 .name = xname, \
3010 .index = xindex, \
3011 .access = SNDRV_CTL_ELEM_ACCESS_READ, \
3012 .info = snd_hdspm_info_autosync_ref, \
3013 .get = snd_hdspm_get_autosync_ref, \
763f356c
TI
3014}
3015
0dca1793 3016static int hdspm_autosync_ref(struct hdspm *hdspm)
763f356c 3017{
2d60fc7f 3018 /* This looks at the autosync selected sync reference */
0dca1793 3019 if (AES32 == hdspm->io_type) {
2d60fc7f 3020
3cee5a60 3021 unsigned int status = hdspm_read(hdspm, HDSPM_statusRegister);
2d60fc7f
AK
3022 unsigned int syncref = (status >> HDSPM_AES32_syncref_bit) & 0xF;
3023 if ((syncref >= HDSPM_AES32_AUTOSYNC_FROM_WORD) &&
3024 (syncref <= HDSPM_AES32_AUTOSYNC_FROM_SYNC_IN)) {
3cee5a60 3025 return syncref;
2d60fc7f 3026 }
3cee5a60 3027 return HDSPM_AES32_AUTOSYNC_FROM_NONE;
2d60fc7f 3028
0dca1793 3029 } else if (MADI == hdspm->io_type) {
3cee5a60 3030
2d60fc7f 3031 unsigned int status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
3cee5a60
RB
3032 switch (status2 & HDSPM_SelSyncRefMask) {
3033 case HDSPM_SelSyncRef_WORD:
3034 return HDSPM_AUTOSYNC_FROM_WORD;
3035 case HDSPM_SelSyncRef_MADI:
3036 return HDSPM_AUTOSYNC_FROM_MADI;
0dca1793
AK
3037 case HDSPM_SelSyncRef_TCO:
3038 return HDSPM_AUTOSYNC_FROM_TCO;
3039 case HDSPM_SelSyncRef_SyncIn:
3040 return HDSPM_AUTOSYNC_FROM_SYNC_IN;
3cee5a60
RB
3041 case HDSPM_SelSyncRef_NVALID:
3042 return HDSPM_AUTOSYNC_FROM_NONE;
3043 default:
e71b95ad 3044 return HDSPM_AUTOSYNC_FROM_NONE;
3cee5a60 3045 }
763f356c 3046
763f356c 3047 }
0dca1793 3048 return 0;
763f356c
TI
3049}
3050
0dca1793 3051
98274f07
TI
3052static int snd_hdspm_info_autosync_ref(struct snd_kcontrol *kcontrol,
3053 struct snd_ctl_elem_info *uinfo)
763f356c 3054{
3cee5a60 3055 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 3056
0dca1793 3057 if (AES32 == hdspm->io_type) {
04659f9e 3058 static const char *const texts[] = { "WordClock", "AES1", "AES2", "AES3",
db2d1a91 3059 "AES4", "AES5", "AES6", "AES7", "AES8", "TCO", "Sync In", "None"};
3cee5a60 3060
04659f9e 3061 ENUMERATED_CTL_INFO(uinfo, texts);
0dca1793 3062 } else if (MADI == hdspm->io_type) {
04659f9e 3063 static const char *const texts[] = {"Word Clock", "MADI", "TCO",
0dca1793 3064 "Sync In", "None" };
3cee5a60 3065
04659f9e 3066 ENUMERATED_CTL_INFO(uinfo, texts);
3cee5a60 3067 }
763f356c
TI
3068 return 0;
3069}
3070
98274f07
TI
3071static int snd_hdspm_get_autosync_ref(struct snd_kcontrol *kcontrol,
3072 struct snd_ctl_elem_value *ucontrol)
763f356c 3073{
98274f07 3074 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 3075
6534599d 3076 ucontrol->value.enumerated.item[0] = hdspm_autosync_ref(hdspm);
763f356c
TI
3077 return 0;
3078}
3079
f99c7881
AK
3080
3081
3082#define HDSPM_TCO_VIDEO_INPUT_FORMAT(xname, xindex) \
3083{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3084 .name = xname, \
3085 .access = SNDRV_CTL_ELEM_ACCESS_READ |\
3086 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
3087 .info = snd_hdspm_info_tco_video_input_format, \
3088 .get = snd_hdspm_get_tco_video_input_format, \
3089}
3090
3091static int snd_hdspm_info_tco_video_input_format(struct snd_kcontrol *kcontrol,
3092 struct snd_ctl_elem_info *uinfo)
3093{
38816545 3094 static const char *const texts[] = {"No video", "NTSC", "PAL"};
f99c7881
AK
3095 ENUMERATED_CTL_INFO(uinfo, texts);
3096 return 0;
3097}
3098
3099static int snd_hdspm_get_tco_video_input_format(struct snd_kcontrol *kcontrol,
3100 struct snd_ctl_elem_value *ucontrol)
3101{
3102 u32 status;
3103 int ret = 0;
3104
3105 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
3106 status = hdspm_read(hdspm, HDSPM_RD_TCO + 4);
3107 switch (status & (HDSPM_TCO1_Video_Input_Format_NTSC |
3108 HDSPM_TCO1_Video_Input_Format_PAL)) {
3109 case HDSPM_TCO1_Video_Input_Format_NTSC:
3110 /* ntsc */
3111 ret = 1;
3112 break;
3113 case HDSPM_TCO1_Video_Input_Format_PAL:
3114 /* pal */
3115 ret = 2;
3116 break;
3117 default:
3118 /* no video */
3119 ret = 0;
3120 break;
3121 }
3122 ucontrol->value.enumerated.item[0] = ret;
3123 return 0;
3124}
3125
3126
3127
3128#define HDSPM_TCO_LTC_FRAMES(xname, xindex) \
3129{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3130 .name = xname, \
3131 .access = SNDRV_CTL_ELEM_ACCESS_READ |\
3132 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
3133 .info = snd_hdspm_info_tco_ltc_frames, \
3134 .get = snd_hdspm_get_tco_ltc_frames, \
3135}
3136
3137static int snd_hdspm_info_tco_ltc_frames(struct snd_kcontrol *kcontrol,
3138 struct snd_ctl_elem_info *uinfo)
3139{
38816545 3140 static const char *const texts[] = {"No lock", "24 fps", "25 fps", "29.97 fps",
f99c7881
AK
3141 "30 fps"};
3142 ENUMERATED_CTL_INFO(uinfo, texts);
3143 return 0;
3144}
3145
3146static int hdspm_tco_ltc_frames(struct hdspm *hdspm)
3147{
3148 u32 status;
3149 int ret = 0;
3150
3151 status = hdspm_read(hdspm, HDSPM_RD_TCO + 4);
3152 if (status & HDSPM_TCO1_LTC_Input_valid) {
3153 switch (status & (HDSPM_TCO1_LTC_Format_LSB |
3154 HDSPM_TCO1_LTC_Format_MSB)) {
3155 case 0:
3156 /* 24 fps */
1568b880 3157 ret = fps_24;
f99c7881
AK
3158 break;
3159 case HDSPM_TCO1_LTC_Format_LSB:
3160 /* 25 fps */
1568b880 3161 ret = fps_25;
f99c7881
AK
3162 break;
3163 case HDSPM_TCO1_LTC_Format_MSB:
1568b880
AK
3164 /* 29.97 fps */
3165 ret = fps_2997;
f99c7881
AK
3166 break;
3167 default:
3168 /* 30 fps */
1568b880 3169 ret = fps_30;
f99c7881
AK
3170 break;
3171 }
3172 }
3173
3174 return ret;
3175}
3176
3177static int snd_hdspm_get_tco_ltc_frames(struct snd_kcontrol *kcontrol,
3178 struct snd_ctl_elem_value *ucontrol)
3179{
3180 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
3181
3182 ucontrol->value.enumerated.item[0] = hdspm_tco_ltc_frames(hdspm);
3183 return 0;
3184}
3185
bf0ff87b
AK
3186#define HDSPM_TOGGLE_SETTING(xname, xindex) \
3187{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3188 .name = xname, \
3189 .private_value = xindex, \
3190 .info = snd_hdspm_info_toggle_setting, \
3191 .get = snd_hdspm_get_toggle_setting, \
3192 .put = snd_hdspm_put_toggle_setting \
3193}
3194
3195static int hdspm_toggle_setting(struct hdspm *hdspm, u32 regmask)
3196{
ce13f3f3
AK
3197 u32 reg;
3198
3199 if (hdspm_is_raydat_or_aio(hdspm))
3200 reg = hdspm->settings_register;
3201 else
3202 reg = hdspm->control_register;
3203
3204 return (reg & regmask) ? 1 : 0;
bf0ff87b
AK
3205}
3206
3207static int hdspm_set_toggle_setting(struct hdspm *hdspm, u32 regmask, int out)
3208{
ce13f3f3
AK
3209 u32 *reg;
3210 u32 target_reg;
3211
3212 if (hdspm_is_raydat_or_aio(hdspm)) {
3213 reg = &(hdspm->settings_register);
3214 target_reg = HDSPM_WR_SETTINGS;
3215 } else {
3216 reg = &(hdspm->control_register);
3217 target_reg = HDSPM_controlRegister;
3218 }
3219
bf0ff87b 3220 if (out)
ce13f3f3 3221 *reg |= regmask;
bf0ff87b 3222 else
ce13f3f3
AK
3223 *reg &= ~regmask;
3224
3225 hdspm_write(hdspm, target_reg, *reg);
bf0ff87b
AK
3226
3227 return 0;
3228}
3229
3230#define snd_hdspm_info_toggle_setting snd_ctl_boolean_mono_info
3231
3232static int snd_hdspm_get_toggle_setting(struct snd_kcontrol *kcontrol,
3233 struct snd_ctl_elem_value *ucontrol)
3234{
3235 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
3236 u32 regmask = kcontrol->private_value;
3237
3238 spin_lock_irq(&hdspm->lock);
3239 ucontrol->value.integer.value[0] = hdspm_toggle_setting(hdspm, regmask);
3240 spin_unlock_irq(&hdspm->lock);
3241 return 0;
3242}
3243
3244static int snd_hdspm_put_toggle_setting(struct snd_kcontrol *kcontrol,
3245 struct snd_ctl_elem_value *ucontrol)
3246{
3247 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
3248 u32 regmask = kcontrol->private_value;
3249 int change;
3250 unsigned int val;
3251
3252 if (!snd_hdspm_use_is_exclusive(hdspm))
3253 return -EBUSY;
3254 val = ucontrol->value.integer.value[0] & 1;
3255 spin_lock_irq(&hdspm->lock);
3256 change = (int) val != hdspm_toggle_setting(hdspm, regmask);
3257 hdspm_set_toggle_setting(hdspm, regmask, val);
3258 spin_unlock_irq(&hdspm->lock);
3259 return change;
3260}
3261
3cee5a60 3262#define HDSPM_INPUT_SELECT(xname, xindex) \
f27a64f9
AK
3263{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3264 .name = xname, \
3265 .index = xindex, \
3266 .info = snd_hdspm_info_input_select, \
3267 .get = snd_hdspm_get_input_select, \
3268 .put = snd_hdspm_put_input_select \
3cee5a60
RB
3269}
3270
3271static int hdspm_input_select(struct hdspm * hdspm)
3272{
3273 return (hdspm->control_register & HDSPM_InputSelect0) ? 1 : 0;
3274}
3275
3276static int hdspm_set_input_select(struct hdspm * hdspm, int out)
3277{
3278 if (out)
3279 hdspm->control_register |= HDSPM_InputSelect0;
3280 else
3281 hdspm->control_register &= ~HDSPM_InputSelect0;
3282 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
3283
3284 return 0;
3285}
3286
3287static int snd_hdspm_info_input_select(struct snd_kcontrol *kcontrol,
3288 struct snd_ctl_elem_info *uinfo)
3289{
38816545 3290 static const char *const texts[] = { "optical", "coaxial" };
e5b7b1fe 3291 ENUMERATED_CTL_INFO(uinfo, texts);
3cee5a60
RB
3292 return 0;
3293}
3294
3295static int snd_hdspm_get_input_select(struct snd_kcontrol *kcontrol,
3296 struct snd_ctl_elem_value *ucontrol)
3297{
3298 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
3299
3300 spin_lock_irq(&hdspm->lock);
3301 ucontrol->value.enumerated.item[0] = hdspm_input_select(hdspm);
3302 spin_unlock_irq(&hdspm->lock);
3303 return 0;
3304}
3305
3306static int snd_hdspm_put_input_select(struct snd_kcontrol *kcontrol,
3307 struct snd_ctl_elem_value *ucontrol)
3308{
3309 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
3310 int change;
3311 unsigned int val;
3312
3313 if (!snd_hdspm_use_is_exclusive(hdspm))
3314 return -EBUSY;
3315 val = ucontrol->value.integer.value[0] & 1;
3316 spin_lock_irq(&hdspm->lock);
3317 change = (int) val != hdspm_input_select(hdspm);
3318 hdspm_set_input_select(hdspm, val);
3319 spin_unlock_irq(&hdspm->lock);
3320 return change;
3321}
3322
0dca1793 3323
3cee5a60 3324#define HDSPM_DS_WIRE(xname, xindex) \
f27a64f9
AK
3325{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3326 .name = xname, \
3327 .index = xindex, \
3328 .info = snd_hdspm_info_ds_wire, \
3329 .get = snd_hdspm_get_ds_wire, \
3330 .put = snd_hdspm_put_ds_wire \
3cee5a60
RB
3331}
3332
3333static int hdspm_ds_wire(struct hdspm * hdspm)
763f356c 3334{
3cee5a60 3335 return (hdspm->control_register & HDSPM_DS_DoubleWire) ? 1 : 0;
763f356c
TI
3336}
3337
3cee5a60 3338static int hdspm_set_ds_wire(struct hdspm * hdspm, int ds)
763f356c 3339{
3cee5a60
RB
3340 if (ds)
3341 hdspm->control_register |= HDSPM_DS_DoubleWire;
763f356c 3342 else
3cee5a60 3343 hdspm->control_register &= ~HDSPM_DS_DoubleWire;
763f356c
TI
3344 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
3345
3346 return 0;
3347}
3348
3cee5a60
RB
3349static int snd_hdspm_info_ds_wire(struct snd_kcontrol *kcontrol,
3350 struct snd_ctl_elem_info *uinfo)
763f356c 3351{
38816545 3352 static const char *const texts[] = { "Single", "Double" };
e5b7b1fe 3353 ENUMERATED_CTL_INFO(uinfo, texts);
763f356c
TI
3354 return 0;
3355}
3356
3cee5a60
RB
3357static int snd_hdspm_get_ds_wire(struct snd_kcontrol *kcontrol,
3358 struct snd_ctl_elem_value *ucontrol)
763f356c 3359{
98274f07 3360 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
3361
3362 spin_lock_irq(&hdspm->lock);
3cee5a60 3363 ucontrol->value.enumerated.item[0] = hdspm_ds_wire(hdspm);
763f356c
TI
3364 spin_unlock_irq(&hdspm->lock);
3365 return 0;
3366}
3367
3cee5a60
RB
3368static int snd_hdspm_put_ds_wire(struct snd_kcontrol *kcontrol,
3369 struct snd_ctl_elem_value *ucontrol)
763f356c 3370{
98274f07 3371 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
3372 int change;
3373 unsigned int val;
3374
3375 if (!snd_hdspm_use_is_exclusive(hdspm))
3376 return -EBUSY;
3377 val = ucontrol->value.integer.value[0] & 1;
3378 spin_lock_irq(&hdspm->lock);
3cee5a60
RB
3379 change = (int) val != hdspm_ds_wire(hdspm);
3380 hdspm_set_ds_wire(hdspm, val);
763f356c
TI
3381 spin_unlock_irq(&hdspm->lock);
3382 return change;
3383}
3384
0dca1793 3385
3cee5a60 3386#define HDSPM_QS_WIRE(xname, xindex) \
f27a64f9
AK
3387{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3388 .name = xname, \
3389 .index = xindex, \
3390 .info = snd_hdspm_info_qs_wire, \
3391 .get = snd_hdspm_get_qs_wire, \
3392 .put = snd_hdspm_put_qs_wire \
763f356c
TI
3393}
3394
3cee5a60 3395static int hdspm_qs_wire(struct hdspm * hdspm)
763f356c 3396{
3cee5a60
RB
3397 if (hdspm->control_register & HDSPM_QS_DoubleWire)
3398 return 1;
3399 if (hdspm->control_register & HDSPM_QS_QuadWire)
3400 return 2;
3401 return 0;
763f356c
TI
3402}
3403
3cee5a60 3404static int hdspm_set_qs_wire(struct hdspm * hdspm, int mode)
763f356c 3405{
3cee5a60
RB
3406 hdspm->control_register &= ~(HDSPM_QS_DoubleWire | HDSPM_QS_QuadWire);
3407 switch (mode) {
3408 case 0:
3409 break;
3410 case 1:
3411 hdspm->control_register |= HDSPM_QS_DoubleWire;
3412 break;
3413 case 2:
3414 hdspm->control_register |= HDSPM_QS_QuadWire;
3415 break;
3416 }
763f356c
TI
3417 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
3418
3419 return 0;
3420}
3421
3cee5a60 3422static int snd_hdspm_info_qs_wire(struct snd_kcontrol *kcontrol,
98274f07 3423 struct snd_ctl_elem_info *uinfo)
763f356c 3424{
38816545 3425 static const char *const texts[] = { "Single", "Double", "Quad" };
e5b7b1fe 3426 ENUMERATED_CTL_INFO(uinfo, texts);
763f356c
TI
3427 return 0;
3428}
3429
3cee5a60 3430static int snd_hdspm_get_qs_wire(struct snd_kcontrol *kcontrol,
98274f07 3431 struct snd_ctl_elem_value *ucontrol)
763f356c 3432{
98274f07 3433 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
3434
3435 spin_lock_irq(&hdspm->lock);
3cee5a60 3436 ucontrol->value.enumerated.item[0] = hdspm_qs_wire(hdspm);
763f356c
TI
3437 spin_unlock_irq(&hdspm->lock);
3438 return 0;
3439}
3440
3cee5a60 3441static int snd_hdspm_put_qs_wire(struct snd_kcontrol *kcontrol,
98274f07 3442 struct snd_ctl_elem_value *ucontrol)
763f356c 3443{
98274f07 3444 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 3445 int change;
3cee5a60 3446 int val;
763f356c
TI
3447
3448 if (!snd_hdspm_use_is_exclusive(hdspm))
3449 return -EBUSY;
3cee5a60
RB
3450 val = ucontrol->value.integer.value[0];
3451 if (val < 0)
3452 val = 0;
3453 if (val > 2)
3454 val = 2;
763f356c 3455 spin_lock_irq(&hdspm->lock);
ef5fa1a4 3456 change = val != hdspm_qs_wire(hdspm);
3cee5a60 3457 hdspm_set_qs_wire(hdspm, val);
763f356c
TI
3458 spin_unlock_irq(&hdspm->lock);
3459 return change;
3460}
3461
acf14767
AK
3462#define HDSPM_CONTROL_TRISTATE(xname, xindex) \
3463{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3464 .name = xname, \
3465 .private_value = xindex, \
3466 .info = snd_hdspm_info_tristate, \
3467 .get = snd_hdspm_get_tristate, \
3468 .put = snd_hdspm_put_tristate \
3469}
3470
3471static int hdspm_tristate(struct hdspm *hdspm, u32 regmask)
3472{
3473 u32 reg = hdspm->settings_register & (regmask * 3);
3474 return reg / regmask;
3475}
3476
3477static int hdspm_set_tristate(struct hdspm *hdspm, int mode, u32 regmask)
3478{
3479 hdspm->settings_register &= ~(regmask * 3);
3480 hdspm->settings_register |= (regmask * mode);
3481 hdspm_write(hdspm, HDSPM_WR_SETTINGS, hdspm->settings_register);
3482
3483 return 0;
3484}
3485
3486static int snd_hdspm_info_tristate(struct snd_kcontrol *kcontrol,
3487 struct snd_ctl_elem_info *uinfo)
3488{
3489 u32 regmask = kcontrol->private_value;
3490
38816545
AK
3491 static const char *const texts_spdif[] = { "Optical", "Coaxial", "Internal" };
3492 static const char *const texts_levels[] = { "Hi Gain", "+4 dBu", "-10 dBV" };
acf14767
AK
3493
3494 switch (regmask) {
3495 case HDSPM_c0_Input0:
3496 ENUMERATED_CTL_INFO(uinfo, texts_spdif);
3497 break;
3498 default:
3499 ENUMERATED_CTL_INFO(uinfo, texts_levels);
3500 break;
3501 }
3502 return 0;
3503}
3504
3505static int snd_hdspm_get_tristate(struct snd_kcontrol *kcontrol,
3506 struct snd_ctl_elem_value *ucontrol)
3507{
3508 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
3509 u32 regmask = kcontrol->private_value;
3510
3511 spin_lock_irq(&hdspm->lock);
3512 ucontrol->value.enumerated.item[0] = hdspm_tristate(hdspm, regmask);
3513 spin_unlock_irq(&hdspm->lock);
3514 return 0;
3515}
3516
3517static int snd_hdspm_put_tristate(struct snd_kcontrol *kcontrol,
3518 struct snd_ctl_elem_value *ucontrol)
3519{
3520 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
3521 u32 regmask = kcontrol->private_value;
3522 int change;
3523 int val;
3524
3525 if (!snd_hdspm_use_is_exclusive(hdspm))
3526 return -EBUSY;
3527 val = ucontrol->value.integer.value[0];
3528 if (val < 0)
3529 val = 0;
3530 if (val > 2)
3531 val = 2;
3532
3533 spin_lock_irq(&hdspm->lock);
3534 change = val != hdspm_tristate(hdspm, regmask);
3535 hdspm_set_tristate(hdspm, val, regmask);
3536 spin_unlock_irq(&hdspm->lock);
3537 return change;
3538}
3539
700d1ef3
AK
3540#define HDSPM_MADI_SPEEDMODE(xname, xindex) \
3541{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3542 .name = xname, \
3543 .index = xindex, \
3544 .info = snd_hdspm_info_madi_speedmode, \
3545 .get = snd_hdspm_get_madi_speedmode, \
3546 .put = snd_hdspm_put_madi_speedmode \
3547}
3548
3549static int hdspm_madi_speedmode(struct hdspm *hdspm)
3550{
3551 if (hdspm->control_register & HDSPM_QuadSpeed)
3552 return 2;
3553 if (hdspm->control_register & HDSPM_DoubleSpeed)
3554 return 1;
3555 return 0;
3556}
3557
3558static int hdspm_set_madi_speedmode(struct hdspm *hdspm, int mode)
3559{
3560 hdspm->control_register &= ~(HDSPM_DoubleSpeed | HDSPM_QuadSpeed);
3561 switch (mode) {
3562 case 0:
3563 break;
3564 case 1:
3565 hdspm->control_register |= HDSPM_DoubleSpeed;
3566 break;
3567 case 2:
3568 hdspm->control_register |= HDSPM_QuadSpeed;
3569 break;
3570 }
3571 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
3572
3573 return 0;
3574}
3575
3576static int snd_hdspm_info_madi_speedmode(struct snd_kcontrol *kcontrol,
3577 struct snd_ctl_elem_info *uinfo)
3578{
38816545 3579 static const char *const texts[] = { "Single", "Double", "Quad" };
e5b7b1fe 3580 ENUMERATED_CTL_INFO(uinfo, texts);
700d1ef3
AK
3581 return 0;
3582}
3583
3584static int snd_hdspm_get_madi_speedmode(struct snd_kcontrol *kcontrol,
3585 struct snd_ctl_elem_value *ucontrol)
3586{
3587 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
3588
3589 spin_lock_irq(&hdspm->lock);
3590 ucontrol->value.enumerated.item[0] = hdspm_madi_speedmode(hdspm);
3591 spin_unlock_irq(&hdspm->lock);
3592 return 0;
3593}
3594
3595static int snd_hdspm_put_madi_speedmode(struct snd_kcontrol *kcontrol,
3596 struct snd_ctl_elem_value *ucontrol)
3597{
3598 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
3599 int change;
3600 int val;
3601
3602 if (!snd_hdspm_use_is_exclusive(hdspm))
3603 return -EBUSY;
3604 val = ucontrol->value.integer.value[0];
3605 if (val < 0)
3606 val = 0;
3607 if (val > 2)
3608 val = 2;
3609 spin_lock_irq(&hdspm->lock);
3610 change = val != hdspm_madi_speedmode(hdspm);
3611 hdspm_set_madi_speedmode(hdspm, val);
3612 spin_unlock_irq(&hdspm->lock);
3613 return change;
3614}
763f356c
TI
3615
3616#define HDSPM_MIXER(xname, xindex) \
f27a64f9
AK
3617{ .iface = SNDRV_CTL_ELEM_IFACE_HWDEP, \
3618 .name = xname, \
3619 .index = xindex, \
3620 .device = 0, \
3621 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE | \
3622 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
3623 .info = snd_hdspm_info_mixer, \
3624 .get = snd_hdspm_get_mixer, \
3625 .put = snd_hdspm_put_mixer \
763f356c
TI
3626}
3627
98274f07
TI
3628static int snd_hdspm_info_mixer(struct snd_kcontrol *kcontrol,
3629 struct snd_ctl_elem_info *uinfo)
763f356c
TI
3630{
3631 uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
3632 uinfo->count = 3;
3633 uinfo->value.integer.min = 0;
3634 uinfo->value.integer.max = 65535;
3635 uinfo->value.integer.step = 1;
3636 return 0;
3637}
3638
98274f07
TI
3639static int snd_hdspm_get_mixer(struct snd_kcontrol *kcontrol,
3640 struct snd_ctl_elem_value *ucontrol)
763f356c 3641{
98274f07 3642 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
3643 int source;
3644 int destination;
3645
3646 source = ucontrol->value.integer.value[0];
3647 if (source < 0)
3648 source = 0;
3649 else if (source >= 2 * HDSPM_MAX_CHANNELS)
3650 source = 2 * HDSPM_MAX_CHANNELS - 1;
3651
3652 destination = ucontrol->value.integer.value[1];
3653 if (destination < 0)
3654 destination = 0;
3655 else if (destination >= HDSPM_MAX_CHANNELS)
3656 destination = HDSPM_MAX_CHANNELS - 1;
3657
3658 spin_lock_irq(&hdspm->lock);
3659 if (source >= HDSPM_MAX_CHANNELS)
3660 ucontrol->value.integer.value[2] =
3661 hdspm_read_pb_gain(hdspm, destination,
3662 source - HDSPM_MAX_CHANNELS);
3663 else
3664 ucontrol->value.integer.value[2] =
3665 hdspm_read_in_gain(hdspm, destination, source);
3666
3667 spin_unlock_irq(&hdspm->lock);
3668
3669 return 0;
3670}
3671
98274f07
TI
3672static int snd_hdspm_put_mixer(struct snd_kcontrol *kcontrol,
3673 struct snd_ctl_elem_value *ucontrol)
763f356c 3674{
98274f07 3675 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
3676 int change;
3677 int source;
3678 int destination;
3679 int gain;
3680
3681 if (!snd_hdspm_use_is_exclusive(hdspm))
3682 return -EBUSY;
3683
3684 source = ucontrol->value.integer.value[0];
3685 destination = ucontrol->value.integer.value[1];
3686
3687 if (source < 0 || source >= 2 * HDSPM_MAX_CHANNELS)
3688 return -1;
3689 if (destination < 0 || destination >= HDSPM_MAX_CHANNELS)
3690 return -1;
3691
3692 gain = ucontrol->value.integer.value[2];
3693
3694 spin_lock_irq(&hdspm->lock);
3695
3696 if (source >= HDSPM_MAX_CHANNELS)
3697 change = gain != hdspm_read_pb_gain(hdspm, destination,
3698 source -
3699 HDSPM_MAX_CHANNELS);
3700 else
ef5fa1a4
TI
3701 change = gain != hdspm_read_in_gain(hdspm, destination,
3702 source);
763f356c
TI
3703
3704 if (change) {
3705 if (source >= HDSPM_MAX_CHANNELS)
3706 hdspm_write_pb_gain(hdspm, destination,
3707 source - HDSPM_MAX_CHANNELS,
3708 gain);
3709 else
3710 hdspm_write_in_gain(hdspm, destination, source,
3711 gain);
3712 }
3713 spin_unlock_irq(&hdspm->lock);
3714
3715 return change;
3716}
3717
3718/* The simple mixer control(s) provide gain control for the
3719 basic 1:1 mappings of playback streams to output
0dca1793 3720 streams.
763f356c
TI
3721*/
3722
3723#define HDSPM_PLAYBACK_MIXER \
f27a64f9
AK
3724{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3725 .access = SNDRV_CTL_ELEM_ACCESS_READ | SNDRV_CTL_ELEM_ACCESS_WRITE | \
3726 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
3727 .info = snd_hdspm_info_playback_mixer, \
3728 .get = snd_hdspm_get_playback_mixer, \
3729 .put = snd_hdspm_put_playback_mixer \
763f356c
TI
3730}
3731
98274f07
TI
3732static int snd_hdspm_info_playback_mixer(struct snd_kcontrol *kcontrol,
3733 struct snd_ctl_elem_info *uinfo)
763f356c
TI
3734{
3735 uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
3736 uinfo->count = 1;
3737 uinfo->value.integer.min = 0;
0dca1793 3738 uinfo->value.integer.max = 64;
763f356c
TI
3739 uinfo->value.integer.step = 1;
3740 return 0;
3741}
3742
98274f07
TI
3743static int snd_hdspm_get_playback_mixer(struct snd_kcontrol *kcontrol,
3744 struct snd_ctl_elem_value *ucontrol)
763f356c 3745{
98274f07 3746 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 3747 int channel;
763f356c
TI
3748
3749 channel = ucontrol->id.index - 1;
3750
da3cec35
TI
3751 if (snd_BUG_ON(channel < 0 || channel >= HDSPM_MAX_CHANNELS))
3752 return -EINVAL;
763f356c 3753
763f356c
TI
3754 spin_lock_irq(&hdspm->lock);
3755 ucontrol->value.integer.value[0] =
0dca1793 3756 (hdspm_read_pb_gain(hdspm, channel, channel)*64)/UNITY_GAIN;
763f356c
TI
3757 spin_unlock_irq(&hdspm->lock);
3758
763f356c
TI
3759 return 0;
3760}
3761
98274f07
TI
3762static int snd_hdspm_put_playback_mixer(struct snd_kcontrol *kcontrol,
3763 struct snd_ctl_elem_value *ucontrol)
763f356c 3764{
98274f07 3765 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c
TI
3766 int change;
3767 int channel;
763f356c
TI
3768 int gain;
3769
3770 if (!snd_hdspm_use_is_exclusive(hdspm))
3771 return -EBUSY;
3772
3773 channel = ucontrol->id.index - 1;
3774
da3cec35
TI
3775 if (snd_BUG_ON(channel < 0 || channel >= HDSPM_MAX_CHANNELS))
3776 return -EINVAL;
763f356c 3777
0dca1793 3778 gain = ucontrol->value.integer.value[0]*UNITY_GAIN/64;
763f356c
TI
3779
3780 spin_lock_irq(&hdspm->lock);
3781 change =
0dca1793
AK
3782 gain != hdspm_read_pb_gain(hdspm, channel,
3783 channel);
763f356c 3784 if (change)
0dca1793 3785 hdspm_write_pb_gain(hdspm, channel, channel,
763f356c
TI
3786 gain);
3787 spin_unlock_irq(&hdspm->lock);
3788 return change;
3789}
3790
0dca1793
AK
3791#define HDSPM_SYNC_CHECK(xname, xindex) \
3792{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3793 .name = xname, \
3794 .private_value = xindex, \
3795 .access = SNDRV_CTL_ELEM_ACCESS_READ | SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
3796 .info = snd_hdspm_info_sync_check, \
3797 .get = snd_hdspm_get_sync_check \
763f356c
TI
3798}
3799
34542213
AK
3800#define HDSPM_TCO_LOCK_CHECK(xname, xindex) \
3801{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
3802 .name = xname, \
3803 .private_value = xindex, \
3804 .access = SNDRV_CTL_ELEM_ACCESS_READ | SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
3805 .info = snd_hdspm_tco_info_lock_check, \
3806 .get = snd_hdspm_get_sync_check \
3807}
3808
3809
0dca1793 3810
98274f07
TI
3811static int snd_hdspm_info_sync_check(struct snd_kcontrol *kcontrol,
3812 struct snd_ctl_elem_info *uinfo)
763f356c 3813{
38816545 3814 static const char *const texts[] = { "No Lock", "Lock", "Sync", "N/A" };
e5b7b1fe 3815 ENUMERATED_CTL_INFO(uinfo, texts);
763f356c
TI
3816 return 0;
3817}
3818
34542213
AK
3819static int snd_hdspm_tco_info_lock_check(struct snd_kcontrol *kcontrol,
3820 struct snd_ctl_elem_info *uinfo)
3821{
38816545 3822 static const char *const texts[] = { "No Lock", "Lock" };
34542213
AK
3823 ENUMERATED_CTL_INFO(uinfo, texts);
3824 return 0;
3825}
3826
0dca1793 3827static int hdspm_wc_sync_check(struct hdspm *hdspm)
763f356c 3828{
0dca1793
AK
3829 int status, status2;
3830
3831 switch (hdspm->io_type) {
3832 case AES32:
3833 status = hdspm_read(hdspm, HDSPM_statusRegister);
56bde0f3
AS
3834 if (status & HDSPM_AES32_wcLock) {
3835 if (status & HDSPM_AES32_wcSync)
3836 return 2;
3837 else
3838 return 1;
3839 }
3cee5a60 3840 return 0;
0dca1793
AK
3841 break;
3842
3843 case MADI:
3844 status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
3cee5a60
RB
3845 if (status2 & HDSPM_wcLock) {
3846 if (status2 & HDSPM_wcSync)
3847 return 2;
3848 else
3849 return 1;
3850 }
3851 return 0;
0dca1793 3852 break;
763f356c 3853
0dca1793
AK
3854 case RayDAT:
3855 case AIO:
3856 status = hdspm_read(hdspm, HDSPM_statusRegister);
763f356c 3857
0dca1793
AK
3858 if (status & 0x2000000)
3859 return 2;
3860 else if (status & 0x1000000)
3861 return 1;
3862 return 0;
763f356c 3863
0dca1793 3864 break;
763f356c 3865
0dca1793
AK
3866 case MADIface:
3867 break;
3868 }
3869
3870
3871 return 3;
763f356c
TI
3872}
3873
0dca1793
AK
3874
3875static int hdspm_madi_sync_check(struct hdspm *hdspm)
763f356c
TI
3876{
3877 int status = hdspm_read(hdspm, HDSPM_statusRegister);
3878 if (status & HDSPM_madiLock) {
3879 if (status & HDSPM_madiSync)
3880 return 2;
3881 else
3882 return 1;
3883 }
3884 return 0;
3885}
3886
763f356c 3887
0dca1793
AK
3888static int hdspm_s1_sync_check(struct hdspm *hdspm, int idx)
3889{
3890 int status, lock, sync;
763f356c 3891
0dca1793 3892 status = hdspm_read(hdspm, HDSPM_RD_STATUS_1);
763f356c 3893
0dca1793
AK
3894 lock = (status & (0x1<<idx)) ? 1 : 0;
3895 sync = (status & (0x100<<idx)) ? 1 : 0;
3cee5a60 3896
0dca1793 3897 if (lock && sync)
3cee5a60 3898 return 2;
0dca1793
AK
3899 else if (lock)
3900 return 1;
3cee5a60
RB
3901 return 0;
3902}
3903
0dca1793
AK
3904
3905static int hdspm_sync_in_sync_check(struct hdspm *hdspm)
3906{
3907 int status, lock = 0, sync = 0;
3908
3909 switch (hdspm->io_type) {
3910 case RayDAT:
3911 case AIO:
3912 status = hdspm_read(hdspm, HDSPM_RD_STATUS_3);
3913 lock = (status & 0x400) ? 1 : 0;
3914 sync = (status & 0x800) ? 1 : 0;
3915 break;
3916
3917 case MADI:
2e0452f5
AK
3918 status = hdspm_read(hdspm, HDSPM_statusRegister);
3919 lock = (status & HDSPM_syncInLock) ? 1 : 0;
3920 sync = (status & HDSPM_syncInSync) ? 1 : 0;
3921 break;
3922
0dca1793
AK
3923 case AES32:
3924 status = hdspm_read(hdspm, HDSPM_statusRegister2);
9a215f47
AK
3925 lock = (status & 0x100000) ? 1 : 0;
3926 sync = (status & 0x200000) ? 1 : 0;
0dca1793
AK
3927 break;
3928
3929 case MADIface:
3930 break;
3931 }
3932
3933 if (lock && sync)
3934 return 2;
3935 else if (lock)
3936 return 1;
3937
3938 return 0;
3939}
3940
3941static int hdspm_aes_sync_check(struct hdspm *hdspm, int idx)
3942{
3943 int status2, lock, sync;
3944 status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
3945
3946 lock = (status2 & (0x0080 >> idx)) ? 1 : 0;
3947 sync = (status2 & (0x8000 >> idx)) ? 1 : 0;
3948
3949 if (sync)
3950 return 2;
3951 else if (lock)
3952 return 1;
3953 return 0;
3954}
3955
34542213
AK
3956static int hdspm_tco_input_check(struct hdspm *hdspm, u32 mask)
3957{
3958 u32 status;
3959 status = hdspm_read(hdspm, HDSPM_RD_TCO + 4);
3960
3961 return (status & mask) ? 1 : 0;
3962}
3963
0dca1793
AK
3964
3965static int hdspm_tco_sync_check(struct hdspm *hdspm)
3966{
3967 int status;
3968
3969 if (hdspm->tco) {
3970 switch (hdspm->io_type) {
3971 case MADI:
b0bf5504
AK
3972 status = hdspm_read(hdspm, HDSPM_statusRegister);
3973 if (status & HDSPM_tcoLockMadi) {
3974 if (status & HDSPM_tcoSync)
3975 return 2;
3976 else
3977 return 1;
3978 }
3979 return 0;
0dca1793
AK
3980 case AES32:
3981 status = hdspm_read(hdspm, HDSPM_statusRegister);
b0bf5504 3982 if (status & HDSPM_tcoLockAes) {
0dca1793
AK
3983 if (status & HDSPM_tcoSync)
3984 return 2;
3985 else
3986 return 1;
3987 }
3988 return 0;
0dca1793
AK
3989 case RayDAT:
3990 case AIO:
3991 status = hdspm_read(hdspm, HDSPM_RD_STATUS_1);
3992
3993 if (status & 0x8000000)
3994 return 2; /* Sync */
3995 if (status & 0x4000000)
3996 return 1; /* Lock */
3997 return 0; /* No signal */
0dca1793
AK
3998
3999 default:
4000 break;
4001 }
4002 }
4003
4004 return 3; /* N/A */
4005}
4006
4007
4008static int snd_hdspm_get_sync_check(struct snd_kcontrol *kcontrol,
4009 struct snd_ctl_elem_value *ucontrol)
4010{
4011 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4012 int val = -1;
4013
4014 switch (hdspm->io_type) {
4015 case RayDAT:
4016 switch (kcontrol->private_value) {
4017 case 0: /* WC */
4018 val = hdspm_wc_sync_check(hdspm); break;
4019 case 7: /* TCO */
4020 val = hdspm_tco_sync_check(hdspm); break;
4021 case 8: /* SYNC IN */
4022 val = hdspm_sync_in_sync_check(hdspm); break;
4023 default:
d1a3c98d
AK
4024 val = hdspm_s1_sync_check(hdspm,
4025 kcontrol->private_value-1);
0dca1793 4026 }
fba30fd3 4027 break;
0dca1793
AK
4028
4029 case AIO:
4030 switch (kcontrol->private_value) {
4031 case 0: /* WC */
4032 val = hdspm_wc_sync_check(hdspm); break;
4033 case 4: /* TCO */
4034 val = hdspm_tco_sync_check(hdspm); break;
4035 case 5: /* SYNC IN */
4036 val = hdspm_sync_in_sync_check(hdspm); break;
4037 default:
1cb7dbf4
AK
4038 val = hdspm_s1_sync_check(hdspm,
4039 kcontrol->private_value-1);
0dca1793 4040 }
fba30fd3 4041 break;
0dca1793
AK
4042
4043 case MADI:
4044 switch (kcontrol->private_value) {
4045 case 0: /* WC */
4046 val = hdspm_wc_sync_check(hdspm); break;
4047 case 1: /* MADI */
4048 val = hdspm_madi_sync_check(hdspm); break;
4049 case 2: /* TCO */
4050 val = hdspm_tco_sync_check(hdspm); break;
4051 case 3: /* SYNC_IN */
4052 val = hdspm_sync_in_sync_check(hdspm); break;
4053 }
fba30fd3 4054 break;
0dca1793
AK
4055
4056 case MADIface:
4057 val = hdspm_madi_sync_check(hdspm); /* MADI */
4058 break;
4059
4060 case AES32:
4061 switch (kcontrol->private_value) {
4062 case 0: /* WC */
4063 val = hdspm_wc_sync_check(hdspm); break;
4064 case 9: /* TCO */
4065 val = hdspm_tco_sync_check(hdspm); break;
4066 case 10 /* SYNC IN */:
4067 val = hdspm_sync_in_sync_check(hdspm); break;
7c4a95b5 4068 default: /* AES1 to AES8 */
0dca1793 4069 val = hdspm_aes_sync_check(hdspm,
7c4a95b5 4070 kcontrol->private_value-1);
0dca1793 4071 }
fba30fd3 4072 break;
0dca1793
AK
4073
4074 }
4075
34542213
AK
4076 if (hdspm->tco) {
4077 switch (kcontrol->private_value) {
4078 case 11:
4079 /* Check TCO for lock state of its current input */
4080 val = hdspm_tco_input_check(hdspm, HDSPM_TCO1_TCO_lock);
4081 break;
4082 case 12:
4083 /* Check TCO for valid time code on LTC input. */
4084 val = hdspm_tco_input_check(hdspm,
4085 HDSPM_TCO1_LTC_Input_valid);
4086 break;
4087 default:
4088 break;
4089 }
4090 }
4091
0dca1793
AK
4092 if (-1 == val)
4093 val = 3;
4094
4095 ucontrol->value.enumerated.item[0] = val;
4096 return 0;
4097}
4098
4099
4100
ddcecf6b 4101/*
0dca1793 4102 * TCO controls
ddcecf6b 4103 */
0dca1793
AK
4104static void hdspm_tco_write(struct hdspm *hdspm)
4105{
4106 unsigned int tc[4] = { 0, 0, 0, 0};
4107
4108 switch (hdspm->tco->input) {
4109 case 0:
4110 tc[2] |= HDSPM_TCO2_set_input_MSB;
4111 break;
4112 case 1:
4113 tc[2] |= HDSPM_TCO2_set_input_LSB;
4114 break;
4115 default:
4116 break;
4117 }
4118
4119 switch (hdspm->tco->framerate) {
4120 case 1:
4121 tc[1] |= HDSPM_TCO1_LTC_Format_LSB;
4122 break;
4123 case 2:
4124 tc[1] |= HDSPM_TCO1_LTC_Format_MSB;
4125 break;
4126 case 3:
4127 tc[1] |= HDSPM_TCO1_LTC_Format_MSB +
4128 HDSPM_TCO1_set_drop_frame_flag;
4129 break;
4130 case 4:
4131 tc[1] |= HDSPM_TCO1_LTC_Format_LSB +
4132 HDSPM_TCO1_LTC_Format_MSB;
4133 break;
4134 case 5:
4135 tc[1] |= HDSPM_TCO1_LTC_Format_LSB +
4136 HDSPM_TCO1_LTC_Format_MSB +
4137 HDSPM_TCO1_set_drop_frame_flag;
4138 break;
4139 default:
4140 break;
4141 }
4142
4143 switch (hdspm->tco->wordclock) {
4144 case 1:
4145 tc[2] |= HDSPM_TCO2_WCK_IO_ratio_LSB;
4146 break;
4147 case 2:
4148 tc[2] |= HDSPM_TCO2_WCK_IO_ratio_MSB;
4149 break;
4150 default:
4151 break;
4152 }
4153
4154 switch (hdspm->tco->samplerate) {
4155 case 1:
4156 tc[2] |= HDSPM_TCO2_set_freq;
4157 break;
4158 case 2:
4159 tc[2] |= HDSPM_TCO2_set_freq_from_app;
4160 break;
4161 default:
4162 break;
4163 }
4164
4165 switch (hdspm->tco->pull) {
4166 case 1:
4167 tc[2] |= HDSPM_TCO2_set_pull_up;
4168 break;
4169 case 2:
4170 tc[2] |= HDSPM_TCO2_set_pull_down;
4171 break;
4172 case 3:
4173 tc[2] |= HDSPM_TCO2_set_pull_up + HDSPM_TCO2_set_01_4;
4174 break;
4175 case 4:
4176 tc[2] |= HDSPM_TCO2_set_pull_down + HDSPM_TCO2_set_01_4;
4177 break;
4178 default:
4179 break;
4180 }
4181
4182 if (1 == hdspm->tco->term) {
4183 tc[2] |= HDSPM_TCO2_set_term_75R;
4184 }
4185
4186 hdspm_write(hdspm, HDSPM_WR_TCO, tc[0]);
4187 hdspm_write(hdspm, HDSPM_WR_TCO+4, tc[1]);
4188 hdspm_write(hdspm, HDSPM_WR_TCO+8, tc[2]);
4189 hdspm_write(hdspm, HDSPM_WR_TCO+12, tc[3]);
4190}
4191
4192
4193#define HDSPM_TCO_SAMPLE_RATE(xname, xindex) \
4194{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
4195 .name = xname, \
4196 .index = xindex, \
4197 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE |\
4198 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
4199 .info = snd_hdspm_info_tco_sample_rate, \
4200 .get = snd_hdspm_get_tco_sample_rate, \
4201 .put = snd_hdspm_put_tco_sample_rate \
4202}
4203
4204static int snd_hdspm_info_tco_sample_rate(struct snd_kcontrol *kcontrol,
4205 struct snd_ctl_elem_info *uinfo)
4206{
69358fca 4207 /* TODO freq from app could be supported here, see tco->samplerate */
38816545 4208 static const char *const texts[] = { "44.1 kHz", "48 kHz" };
e5b7b1fe 4209 ENUMERATED_CTL_INFO(uinfo, texts);
0dca1793
AK
4210 return 0;
4211}
4212
4213static int snd_hdspm_get_tco_sample_rate(struct snd_kcontrol *kcontrol,
4214 struct snd_ctl_elem_value *ucontrol)
4215{
4216 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4217
4218 ucontrol->value.enumerated.item[0] = hdspm->tco->samplerate;
4219
4220 return 0;
4221}
4222
4223static int snd_hdspm_put_tco_sample_rate(struct snd_kcontrol *kcontrol,
4224 struct snd_ctl_elem_value *ucontrol)
4225{
4226 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4227
4228 if (hdspm->tco->samplerate != ucontrol->value.enumerated.item[0]) {
4229 hdspm->tco->samplerate = ucontrol->value.enumerated.item[0];
4230
4231 hdspm_tco_write(hdspm);
4232
4233 return 1;
4234 }
4235
4236 return 0;
4237}
4238
4239
4240#define HDSPM_TCO_PULL(xname, xindex) \
4241{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
4242 .name = xname, \
4243 .index = xindex, \
4244 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE |\
4245 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
4246 .info = snd_hdspm_info_tco_pull, \
4247 .get = snd_hdspm_get_tco_pull, \
4248 .put = snd_hdspm_put_tco_pull \
4249}
4250
4251static int snd_hdspm_info_tco_pull(struct snd_kcontrol *kcontrol,
4252 struct snd_ctl_elem_info *uinfo)
4253{
38816545
AK
4254 static const char *const texts[] = { "0", "+ 0.1 %", "- 0.1 %",
4255 "+ 4 %", "- 4 %" };
e5b7b1fe 4256 ENUMERATED_CTL_INFO(uinfo, texts);
0dca1793
AK
4257 return 0;
4258}
4259
4260static int snd_hdspm_get_tco_pull(struct snd_kcontrol *kcontrol,
4261 struct snd_ctl_elem_value *ucontrol)
4262{
4263 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4264
4265 ucontrol->value.enumerated.item[0] = hdspm->tco->pull;
4266
4267 return 0;
4268}
4269
4270static int snd_hdspm_put_tco_pull(struct snd_kcontrol *kcontrol,
4271 struct snd_ctl_elem_value *ucontrol)
4272{
4273 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4274
4275 if (hdspm->tco->pull != ucontrol->value.enumerated.item[0]) {
4276 hdspm->tco->pull = ucontrol->value.enumerated.item[0];
4277
4278 hdspm_tco_write(hdspm);
4279
4280 return 1;
4281 }
4282
4283 return 0;
4284}
4285
4286#define HDSPM_TCO_WCK_CONVERSION(xname, xindex) \
4287{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
4288 .name = xname, \
4289 .index = xindex, \
4290 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE |\
4291 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
4292 .info = snd_hdspm_info_tco_wck_conversion, \
4293 .get = snd_hdspm_get_tco_wck_conversion, \
4294 .put = snd_hdspm_put_tco_wck_conversion \
4295}
4296
4297static int snd_hdspm_info_tco_wck_conversion(struct snd_kcontrol *kcontrol,
4298 struct snd_ctl_elem_info *uinfo)
4299{
38816545 4300 static const char *const texts[] = { "1:1", "44.1 -> 48", "48 -> 44.1" };
e5b7b1fe 4301 ENUMERATED_CTL_INFO(uinfo, texts);
0dca1793
AK
4302 return 0;
4303}
4304
4305static int snd_hdspm_get_tco_wck_conversion(struct snd_kcontrol *kcontrol,
4306 struct snd_ctl_elem_value *ucontrol)
4307{
4308 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4309
4310 ucontrol->value.enumerated.item[0] = hdspm->tco->wordclock;
4311
4312 return 0;
4313}
4314
4315static int snd_hdspm_put_tco_wck_conversion(struct snd_kcontrol *kcontrol,
4316 struct snd_ctl_elem_value *ucontrol)
4317{
4318 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4319
4320 if (hdspm->tco->wordclock != ucontrol->value.enumerated.item[0]) {
4321 hdspm->tco->wordclock = ucontrol->value.enumerated.item[0];
4322
4323 hdspm_tco_write(hdspm);
4324
4325 return 1;
4326 }
4327
4328 return 0;
4329}
4330
4331
4332#define HDSPM_TCO_FRAME_RATE(xname, xindex) \
4333{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
4334 .name = xname, \
4335 .index = xindex, \
4336 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE |\
4337 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
4338 .info = snd_hdspm_info_tco_frame_rate, \
4339 .get = snd_hdspm_get_tco_frame_rate, \
4340 .put = snd_hdspm_put_tco_frame_rate \
4341}
4342
4343static int snd_hdspm_info_tco_frame_rate(struct snd_kcontrol *kcontrol,
4344 struct snd_ctl_elem_info *uinfo)
4345{
38816545 4346 static const char *const texts[] = { "24 fps", "25 fps", "29.97fps",
0dca1793 4347 "29.97 dfps", "30 fps", "30 dfps" };
e5b7b1fe 4348 ENUMERATED_CTL_INFO(uinfo, texts);
0dca1793
AK
4349 return 0;
4350}
4351
4352static int snd_hdspm_get_tco_frame_rate(struct snd_kcontrol *kcontrol,
3cee5a60
RB
4353 struct snd_ctl_elem_value *ucontrol)
4354{
3cee5a60
RB
4355 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4356
0dca1793 4357 ucontrol->value.enumerated.item[0] = hdspm->tco->framerate;
3cee5a60 4358
3cee5a60
RB
4359 return 0;
4360}
763f356c 4361
0dca1793
AK
4362static int snd_hdspm_put_tco_frame_rate(struct snd_kcontrol *kcontrol,
4363 struct snd_ctl_elem_value *ucontrol)
4364{
4365 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
763f356c 4366
0dca1793
AK
4367 if (hdspm->tco->framerate != ucontrol->value.enumerated.item[0]) {
4368 hdspm->tco->framerate = ucontrol->value.enumerated.item[0];
763f356c 4369
0dca1793
AK
4370 hdspm_tco_write(hdspm);
4371
4372 return 1;
4373 }
4374
4375 return 0;
4376}
763f356c 4377
0dca1793
AK
4378
4379#define HDSPM_TCO_SYNC_SOURCE(xname, xindex) \
4380{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
4381 .name = xname, \
4382 .index = xindex, \
4383 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE |\
4384 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
4385 .info = snd_hdspm_info_tco_sync_source, \
4386 .get = snd_hdspm_get_tco_sync_source, \
4387 .put = snd_hdspm_put_tco_sync_source \
4388}
4389
4390static int snd_hdspm_info_tco_sync_source(struct snd_kcontrol *kcontrol,
4391 struct snd_ctl_elem_info *uinfo)
4392{
38816545 4393 static const char *const texts[] = { "LTC", "Video", "WCK" };
e5b7b1fe 4394 ENUMERATED_CTL_INFO(uinfo, texts);
0dca1793
AK
4395 return 0;
4396}
4397
4398static int snd_hdspm_get_tco_sync_source(struct snd_kcontrol *kcontrol,
4399 struct snd_ctl_elem_value *ucontrol)
4400{
4401 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4402
4403 ucontrol->value.enumerated.item[0] = hdspm->tco->input;
4404
4405 return 0;
4406}
4407
4408static int snd_hdspm_put_tco_sync_source(struct snd_kcontrol *kcontrol,
4409 struct snd_ctl_elem_value *ucontrol)
4410{
4411 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4412
4413 if (hdspm->tco->input != ucontrol->value.enumerated.item[0]) {
4414 hdspm->tco->input = ucontrol->value.enumerated.item[0];
4415
4416 hdspm_tco_write(hdspm);
4417
4418 return 1;
4419 }
4420
4421 return 0;
4422}
4423
4424
4425#define HDSPM_TCO_WORD_TERM(xname, xindex) \
4426{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, \
4427 .name = xname, \
4428 .index = xindex, \
4429 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE |\
4430 SNDRV_CTL_ELEM_ACCESS_VOLATILE, \
4431 .info = snd_hdspm_info_tco_word_term, \
4432 .get = snd_hdspm_get_tco_word_term, \
4433 .put = snd_hdspm_put_tco_word_term \
4434}
4435
4436static int snd_hdspm_info_tco_word_term(struct snd_kcontrol *kcontrol,
4437 struct snd_ctl_elem_info *uinfo)
4438{
4439 uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN;
4440 uinfo->count = 1;
4441 uinfo->value.integer.min = 0;
4442 uinfo->value.integer.max = 1;
4443
4444 return 0;
4445}
4446
4447
4448static int snd_hdspm_get_tco_word_term(struct snd_kcontrol *kcontrol,
4449 struct snd_ctl_elem_value *ucontrol)
4450{
4451 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4452
537e4813 4453 ucontrol->value.integer.value[0] = hdspm->tco->term;
0dca1793
AK
4454
4455 return 0;
4456}
4457
4458
4459static int snd_hdspm_put_tco_word_term(struct snd_kcontrol *kcontrol,
4460 struct snd_ctl_elem_value *ucontrol)
4461{
4462 struct hdspm *hdspm = snd_kcontrol_chip(kcontrol);
4463
537e4813
TI
4464 if (hdspm->tco->term != ucontrol->value.integer.value[0]) {
4465 hdspm->tco->term = ucontrol->value.integer.value[0];
0dca1793
AK
4466
4467 hdspm_tco_write(hdspm);
4468
4469 return 1;
4470 }
4471
4472 return 0;
4473}
4474
4475
4476
4477
4478static struct snd_kcontrol_new snd_hdspm_controls_madi[] = {
4479 HDSPM_MIXER("Mixer", 0),
4480 HDSPM_INTERNAL_CLOCK("Internal Clock", 0),
763f356c
TI
4481 HDSPM_SYSTEM_CLOCK_MODE("System Clock Mode", 0),
4482 HDSPM_PREF_SYNC_REF("Preferred Sync Reference", 0),
4483 HDSPM_AUTOSYNC_REF("AutoSync Reference", 0),
4484 HDSPM_SYSTEM_SAMPLE_RATE("System Sample Rate", 0),
b8812c55 4485 HDSPM_AUTOSYNC_SAMPLE_RATE("External Rate", 0),
0dca1793
AK
4486 HDSPM_SYNC_CHECK("WC SyncCheck", 0),
4487 HDSPM_SYNC_CHECK("MADI SyncCheck", 1),
930f4ff0 4488 HDSPM_SYNC_CHECK("TCO SyncCheck", 2),
0dca1793 4489 HDSPM_SYNC_CHECK("SYNC IN SyncCheck", 3),
c9e1668c
AK
4490 HDSPM_TOGGLE_SETTING("Line Out", HDSPM_LineOut),
4491 HDSPM_TOGGLE_SETTING("TX 64 channels mode", HDSPM_TX_64ch),
696be0fb 4492 HDSPM_TOGGLE_SETTING("Disable 96K frames", HDSPM_SMUX),
c9e1668c
AK
4493 HDSPM_TOGGLE_SETTING("Clear Track Marker", HDSPM_clr_tms),
4494 HDSPM_TOGGLE_SETTING("Safe Mode", HDSPM_AutoInp),
700d1ef3
AK
4495 HDSPM_INPUT_SELECT("Input Select", 0),
4496 HDSPM_MADI_SPEEDMODE("MADI Speed Mode", 0)
0dca1793
AK
4497};
4498
4499
4500static struct snd_kcontrol_new snd_hdspm_controls_madiface[] = {
4501 HDSPM_MIXER("Mixer", 0),
4502 HDSPM_INTERNAL_CLOCK("Internal Clock", 0),
4503 HDSPM_SYSTEM_CLOCK_MODE("System Clock Mode", 0),
4504 HDSPM_SYSTEM_SAMPLE_RATE("System Sample Rate", 0),
4505 HDSPM_AUTOSYNC_SAMPLE_RATE("External Rate", 0),
4506 HDSPM_SYNC_CHECK("MADI SyncCheck", 0),
c9e1668c
AK
4507 HDSPM_TOGGLE_SETTING("TX 64 channels mode", HDSPM_TX_64ch),
4508 HDSPM_TOGGLE_SETTING("Clear Track Marker", HDSPM_clr_tms),
4509 HDSPM_TOGGLE_SETTING("Safe Mode", HDSPM_AutoInp),
700d1ef3 4510 HDSPM_MADI_SPEEDMODE("MADI Speed Mode", 0)
763f356c
TI
4511};
4512
0dca1793
AK
4513static struct snd_kcontrol_new snd_hdspm_controls_aio[] = {
4514 HDSPM_MIXER("Mixer", 0),
4515 HDSPM_INTERNAL_CLOCK("Internal Clock", 0),
4516 HDSPM_SYSTEM_CLOCK_MODE("System Clock Mode", 0),
4517 HDSPM_PREF_SYNC_REF("Preferred Sync Reference", 0),
0dca1793
AK
4518 HDSPM_SYSTEM_SAMPLE_RATE("System Sample Rate", 0),
4519 HDSPM_AUTOSYNC_SAMPLE_RATE("External Rate", 0),
4520 HDSPM_SYNC_CHECK("WC SyncCheck", 0),
4521 HDSPM_SYNC_CHECK("AES SyncCheck", 1),
4522 HDSPM_SYNC_CHECK("SPDIF SyncCheck", 2),
4523 HDSPM_SYNC_CHECK("ADAT SyncCheck", 3),
4524 HDSPM_SYNC_CHECK("TCO SyncCheck", 4),
4525 HDSPM_SYNC_CHECK("SYNC IN SyncCheck", 5),
4526 HDSPM_AUTOSYNC_SAMPLE_RATE("WC Frequency", 0),
4527 HDSPM_AUTOSYNC_SAMPLE_RATE("AES Frequency", 1),
4528 HDSPM_AUTOSYNC_SAMPLE_RATE("SPDIF Frequency", 2),
4529 HDSPM_AUTOSYNC_SAMPLE_RATE("ADAT Frequency", 3),
4530 HDSPM_AUTOSYNC_SAMPLE_RATE("TCO Frequency", 4),
fb0f121e 4531 HDSPM_AUTOSYNC_SAMPLE_RATE("SYNC IN Frequency", 5),
42f4c12d 4532 HDSPM_CONTROL_TRISTATE("S/PDIF Input", HDSPM_c0_Input0),
fb0f121e
AK
4533 HDSPM_TOGGLE_SETTING("S/PDIF Out Optical", HDSPM_c0_Spdif_Opt),
4534 HDSPM_TOGGLE_SETTING("S/PDIF Out Professional", HDSPM_c0_Pro),
4535 HDSPM_TOGGLE_SETTING("ADAT internal (AEB/TEB)", HDSPM_c0_AEB1),
4536 HDSPM_TOGGLE_SETTING("XLR Breakout Cable", HDSPM_c0_Sym6db),
42f4c12d
AK
4537 HDSPM_TOGGLE_SETTING("Single Speed WordClock Out", HDSPM_c0_Wck48),
4538 HDSPM_CONTROL_TRISTATE("Input Level", HDSPM_c0_AD_GAIN0),
4539 HDSPM_CONTROL_TRISTATE("Output Level", HDSPM_c0_DA_GAIN0),
4540 HDSPM_CONTROL_TRISTATE("Phones Level", HDSPM_c0_PH_GAIN0)
0dca1793
AK
4541
4542 /*
4543 HDSPM_INPUT_SELECT("Input Select", 0),
4544 HDSPM_SPDIF_OPTICAL("SPDIF Out Optical", 0),
4545 HDSPM_PROFESSIONAL("SPDIF Out Professional", 0);
4546 HDSPM_SPDIF_IN("SPDIF In", 0);
4547 HDSPM_BREAKOUT_CABLE("Breakout Cable", 0);
4548 HDSPM_INPUT_LEVEL("Input Level", 0);
4549 HDSPM_OUTPUT_LEVEL("Output Level", 0);
4550 HDSPM_PHONES("Phones", 0);
4551 */
4552};
3cee5a60 4553
0dca1793
AK
4554static struct snd_kcontrol_new snd_hdspm_controls_raydat[] = {
4555 HDSPM_MIXER("Mixer", 0),
4556 HDSPM_INTERNAL_CLOCK("Internal Clock", 0),
4557 HDSPM_SYSTEM_CLOCK_MODE("Clock Mode", 0),
4558 HDSPM_PREF_SYNC_REF("Pref Sync Ref", 0),
4559 HDSPM_SYSTEM_SAMPLE_RATE("System Sample Rate", 0),
4560 HDSPM_SYNC_CHECK("WC SyncCheck", 0),
4561 HDSPM_SYNC_CHECK("AES SyncCheck", 1),
4562 HDSPM_SYNC_CHECK("SPDIF SyncCheck", 2),
4563 HDSPM_SYNC_CHECK("ADAT1 SyncCheck", 3),
4564 HDSPM_SYNC_CHECK("ADAT2 SyncCheck", 4),
4565 HDSPM_SYNC_CHECK("ADAT3 SyncCheck", 5),
4566 HDSPM_SYNC_CHECK("ADAT4 SyncCheck", 6),
4567 HDSPM_SYNC_CHECK("TCO SyncCheck", 7),
4568 HDSPM_SYNC_CHECK("SYNC IN SyncCheck", 8),
4569 HDSPM_AUTOSYNC_SAMPLE_RATE("WC Frequency", 0),
4570 HDSPM_AUTOSYNC_SAMPLE_RATE("AES Frequency", 1),
4571 HDSPM_AUTOSYNC_SAMPLE_RATE("SPDIF Frequency", 2),
4572 HDSPM_AUTOSYNC_SAMPLE_RATE("ADAT1 Frequency", 3),
4573 HDSPM_AUTOSYNC_SAMPLE_RATE("ADAT2 Frequency", 4),
4574 HDSPM_AUTOSYNC_SAMPLE_RATE("ADAT3 Frequency", 5),
4575 HDSPM_AUTOSYNC_SAMPLE_RATE("ADAT4 Frequency", 6),
4576 HDSPM_AUTOSYNC_SAMPLE_RATE("TCO Frequency", 7),
11a5cd3c
AK
4577 HDSPM_AUTOSYNC_SAMPLE_RATE("SYNC IN Frequency", 8),
4578 HDSPM_TOGGLE_SETTING("S/PDIF Out Professional", HDSPM_c0_Pro),
4579 HDSPM_TOGGLE_SETTING("Single Speed WordClock Out", HDSPM_c0_Wck48)
0dca1793
AK
4580};
4581
4582static struct snd_kcontrol_new snd_hdspm_controls_aes32[] = {
3cee5a60 4583 HDSPM_MIXER("Mixer", 0),
0dca1793 4584 HDSPM_INTERNAL_CLOCK("Internal Clock", 0),
3cee5a60
RB
4585 HDSPM_SYSTEM_CLOCK_MODE("System Clock Mode", 0),
4586 HDSPM_PREF_SYNC_REF("Preferred Sync Reference", 0),
4587 HDSPM_AUTOSYNC_REF("AutoSync Reference", 0),
4588 HDSPM_SYSTEM_SAMPLE_RATE("System Sample Rate", 0),
2d63ec38 4589 HDSPM_AUTOSYNC_SAMPLE_RATE("External Rate", 11),
0dca1793
AK
4590 HDSPM_SYNC_CHECK("WC Sync Check", 0),
4591 HDSPM_SYNC_CHECK("AES1 Sync Check", 1),
4592 HDSPM_SYNC_CHECK("AES2 Sync Check", 2),
4593 HDSPM_SYNC_CHECK("AES3 Sync Check", 3),
4594 HDSPM_SYNC_CHECK("AES4 Sync Check", 4),
4595 HDSPM_SYNC_CHECK("AES5 Sync Check", 5),
4596 HDSPM_SYNC_CHECK("AES6 Sync Check", 6),
4597 HDSPM_SYNC_CHECK("AES7 Sync Check", 7),
4598 HDSPM_SYNC_CHECK("AES8 Sync Check", 8),
4599 HDSPM_SYNC_CHECK("TCO Sync Check", 9),
4600 HDSPM_SYNC_CHECK("SYNC IN Sync Check", 10),
4601 HDSPM_AUTOSYNC_SAMPLE_RATE("WC Frequency", 0),
4602 HDSPM_AUTOSYNC_SAMPLE_RATE("AES1 Frequency", 1),
4603 HDSPM_AUTOSYNC_SAMPLE_RATE("AES2 Frequency", 2),
4604 HDSPM_AUTOSYNC_SAMPLE_RATE("AES3 Frequency", 3),
4605 HDSPM_AUTOSYNC_SAMPLE_RATE("AES4 Frequency", 4),
4606 HDSPM_AUTOSYNC_SAMPLE_RATE("AES5 Frequency", 5),
4607 HDSPM_AUTOSYNC_SAMPLE_RATE("AES6 Frequency", 6),
4608 HDSPM_AUTOSYNC_SAMPLE_RATE("AES7 Frequency", 7),
4609 HDSPM_AUTOSYNC_SAMPLE_RATE("AES8 Frequency", 8),
4610 HDSPM_AUTOSYNC_SAMPLE_RATE("TCO Frequency", 9),
4611 HDSPM_AUTOSYNC_SAMPLE_RATE("SYNC IN Frequency", 10),
c9e1668c
AK
4612 HDSPM_TOGGLE_SETTING("Line Out", HDSPM_LineOut),
4613 HDSPM_TOGGLE_SETTING("Emphasis", HDSPM_Emphasis),
4614 HDSPM_TOGGLE_SETTING("Non Audio", HDSPM_Dolby),
4615 HDSPM_TOGGLE_SETTING("Professional", HDSPM_Professional),
4616 HDSPM_TOGGLE_SETTING("Clear Track Marker", HDSPM_clr_tms),
3cee5a60
RB
4617 HDSPM_DS_WIRE("Double Speed Wire Mode", 0),
4618 HDSPM_QS_WIRE("Quad Speed Wire Mode", 0),
4619};
4620
0dca1793
AK
4621
4622
4623/* Control elements for the optional TCO module */
4624static struct snd_kcontrol_new snd_hdspm_controls_tco[] = {
4625 HDSPM_TCO_SAMPLE_RATE("TCO Sample Rate", 0),
4626 HDSPM_TCO_PULL("TCO Pull", 0),
4627 HDSPM_TCO_WCK_CONVERSION("TCO WCK Conversion", 0),
4628 HDSPM_TCO_FRAME_RATE("TCO Frame Rate", 0),
4629 HDSPM_TCO_SYNC_SOURCE("TCO Sync Source", 0),
a817650e
AK
4630 HDSPM_TCO_WORD_TERM("TCO Word Term", 0),
4631 HDSPM_TCO_LOCK_CHECK("TCO Input Check", 11),
4632 HDSPM_TCO_LOCK_CHECK("TCO LTC Valid", 12),
4633 HDSPM_TCO_LTC_FRAMES("TCO Detected Frame Rate", 0),
4634 HDSPM_TCO_VIDEO_INPUT_FORMAT("Video Input Format", 0)
0dca1793
AK
4635};
4636
4637
98274f07 4638static struct snd_kcontrol_new snd_hdspm_playback_mixer = HDSPM_PLAYBACK_MIXER;
763f356c
TI
4639
4640
98274f07 4641static int hdspm_update_simple_mixer_controls(struct hdspm * hdspm)
763f356c
TI
4642{
4643 int i;
4644
0dca1793 4645 for (i = hdspm->ds_out_channels; i < hdspm->ss_out_channels; ++i) {
763f356c
TI
4646 if (hdspm->system_sample_rate > 48000) {
4647 hdspm->playback_mixer_ctls[i]->vd[0].access =
0dca1793
AK
4648 SNDRV_CTL_ELEM_ACCESS_INACTIVE |
4649 SNDRV_CTL_ELEM_ACCESS_READ |
4650 SNDRV_CTL_ELEM_ACCESS_VOLATILE;
763f356c
TI
4651 } else {
4652 hdspm->playback_mixer_ctls[i]->vd[0].access =
0dca1793
AK
4653 SNDRV_CTL_ELEM_ACCESS_READWRITE |
4654 SNDRV_CTL_ELEM_ACCESS_VOLATILE;
763f356c
TI
4655 }
4656 snd_ctl_notify(hdspm->card, SNDRV_CTL_EVENT_MASK_VALUE |
0dca1793
AK
4657 SNDRV_CTL_EVENT_MASK_INFO,
4658 &hdspm->playback_mixer_ctls[i]->id);
763f356c
TI
4659 }
4660
4661 return 0;
4662}
4663
4664
0dca1793
AK
4665static int snd_hdspm_create_controls(struct snd_card *card,
4666 struct hdspm *hdspm)
763f356c
TI
4667{
4668 unsigned int idx, limit;
4669 int err;
98274f07 4670 struct snd_kcontrol *kctl;
0dca1793 4671 struct snd_kcontrol_new *list = NULL;
763f356c 4672
0dca1793
AK
4673 switch (hdspm->io_type) {
4674 case MADI:
4675 list = snd_hdspm_controls_madi;
4676 limit = ARRAY_SIZE(snd_hdspm_controls_madi);
4677 break;
4678 case MADIface:
4679 list = snd_hdspm_controls_madiface;
4680 limit = ARRAY_SIZE(snd_hdspm_controls_madiface);
4681 break;
4682 case AIO:
4683 list = snd_hdspm_controls_aio;
4684 limit = ARRAY_SIZE(snd_hdspm_controls_aio);
4685 break;
4686 case RayDAT:
4687 list = snd_hdspm_controls_raydat;
4688 limit = ARRAY_SIZE(snd_hdspm_controls_raydat);
4689 break;
4690 case AES32:
4691 list = snd_hdspm_controls_aes32;
4692 limit = ARRAY_SIZE(snd_hdspm_controls_aes32);
4693 break;
4694 }
3cee5a60 4695
da2ea374 4696 if (list) {
0dca1793 4697 for (idx = 0; idx < limit; idx++) {
3cee5a60 4698 err = snd_ctl_add(card,
0dca1793 4699 snd_ctl_new1(&list[idx], hdspm));
3cee5a60
RB
4700 if (err < 0)
4701 return err;
763f356c
TI
4702 }
4703 }
4704
763f356c 4705
0dca1793 4706 /* create simple 1:1 playback mixer controls */
763f356c 4707 snd_hdspm_playback_mixer.name = "Chn";
0dca1793
AK
4708 if (hdspm->system_sample_rate >= 128000) {
4709 limit = hdspm->qs_out_channels;
4710 } else if (hdspm->system_sample_rate >= 64000) {
4711 limit = hdspm->ds_out_channels;
4712 } else {
4713 limit = hdspm->ss_out_channels;
4714 }
763f356c
TI
4715 for (idx = 0; idx < limit; ++idx) {
4716 snd_hdspm_playback_mixer.index = idx + 1;
ef5fa1a4
TI
4717 kctl = snd_ctl_new1(&snd_hdspm_playback_mixer, hdspm);
4718 err = snd_ctl_add(card, kctl);
4719 if (err < 0)
763f356c 4720 return err;
763f356c
TI
4721 hdspm->playback_mixer_ctls[idx] = kctl;
4722 }
4723
0dca1793
AK
4724
4725 if (hdspm->tco) {
4726 /* add tco control elements */
4727 list = snd_hdspm_controls_tco;
4728 limit = ARRAY_SIZE(snd_hdspm_controls_tco);
4729 for (idx = 0; idx < limit; idx++) {
4730 err = snd_ctl_add(card,
4731 snd_ctl_new1(&list[idx], hdspm));
4732 if (err < 0)
4733 return err;
4734 }
4735 }
4736
763f356c
TI
4737 return 0;
4738}
4739
4740/*------------------------------------------------------------
0dca1793 4741 /proc interface
763f356c
TI
4742 ------------------------------------------------------------*/
4743
4744static void
5760107c
AK
4745snd_hdspm_proc_read_tco(struct snd_info_entry *entry,
4746 struct snd_info_buffer *buffer)
763f356c 4747{
ef5fa1a4 4748 struct hdspm *hdspm = entry->private_data;
5760107c 4749 unsigned int status, control;
0dca1793
AK
4750 int a, ltc, frames, seconds, minutes, hours;
4751 unsigned int period;
4752 u64 freq_const = 0;
4753 u32 rate;
4754
5760107c
AK
4755 snd_iprintf(buffer, "--- TCO ---\n");
4756
763f356c 4757 status = hdspm_read(hdspm, HDSPM_statusRegister);
0dca1793 4758 control = hdspm->control_register;
763f356c 4759
763f356c 4760
0dca1793
AK
4761 if (status & HDSPM_tco_detect) {
4762 snd_iprintf(buffer, "TCO module detected.\n");
4763 a = hdspm_read(hdspm, HDSPM_RD_TCO+4);
4764 if (a & HDSPM_TCO1_LTC_Input_valid) {
4765 snd_iprintf(buffer, " LTC valid, ");
4766 switch (a & (HDSPM_TCO1_LTC_Format_LSB |
4767 HDSPM_TCO1_LTC_Format_MSB)) {
4768 case 0:
4769 snd_iprintf(buffer, "24 fps, ");
4770 break;
4771 case HDSPM_TCO1_LTC_Format_LSB:
4772 snd_iprintf(buffer, "25 fps, ");
4773 break;
4774 case HDSPM_TCO1_LTC_Format_MSB:
4775 snd_iprintf(buffer, "29.97 fps, ");
4776 break;
4777 default:
4778 snd_iprintf(buffer, "30 fps, ");
4779 break;
4780 }
4781 if (a & HDSPM_TCO1_set_drop_frame_flag) {
4782 snd_iprintf(buffer, "drop frame\n");
4783 } else {
4784 snd_iprintf(buffer, "full frame\n");
4785 }
4786 } else {
4787 snd_iprintf(buffer, " no LTC\n");
4788 }
4789 if (a & HDSPM_TCO1_Video_Input_Format_NTSC) {
4790 snd_iprintf(buffer, " Video: NTSC\n");
4791 } else if (a & HDSPM_TCO1_Video_Input_Format_PAL) {
4792 snd_iprintf(buffer, " Video: PAL\n");
4793 } else {
4794 snd_iprintf(buffer, " No video\n");
4795 }
4796 if (a & HDSPM_TCO1_TCO_lock) {
4797 snd_iprintf(buffer, " Sync: lock\n");
4798 } else {
4799 snd_iprintf(buffer, " Sync: no lock\n");
4800 }
4801
4802 switch (hdspm->io_type) {
4803 case MADI:
4804 case AES32:
4805 freq_const = 110069313433624ULL;
4806 break;
4807 case RayDAT:
4808 case AIO:
4809 freq_const = 104857600000000ULL;
4810 break;
4811 case MADIface:
4812 break; /* no TCO possible */
4813 }
4814
4815 period = hdspm_read(hdspm, HDSPM_RD_PLL_FREQ);
4816 snd_iprintf(buffer, " period: %u\n", period);
4817
4818
4819 /* rate = freq_const/period; */
4820 rate = div_u64(freq_const, period);
4821
4822 if (control & HDSPM_QuadSpeed) {
4823 rate *= 4;
4824 } else if (control & HDSPM_DoubleSpeed) {
4825 rate *= 2;
4826 }
4827
4828 snd_iprintf(buffer, " Frequency: %u Hz\n",
4829 (unsigned int) rate);
4830
4831 ltc = hdspm_read(hdspm, HDSPM_RD_TCO);
4832 frames = ltc & 0xF;
4833 ltc >>= 4;
4834 frames += (ltc & 0x3) * 10;
4835 ltc >>= 4;
4836 seconds = ltc & 0xF;
4837 ltc >>= 4;
4838 seconds += (ltc & 0x7) * 10;
4839 ltc >>= 4;
4840 minutes = ltc & 0xF;
4841 ltc >>= 4;
4842 minutes += (ltc & 0x7) * 10;
4843 ltc >>= 4;
4844 hours = ltc & 0xF;
4845 ltc >>= 4;
4846 hours += (ltc & 0x3) * 10;
4847 snd_iprintf(buffer,
4848 " LTC In: %02d:%02d:%02d:%02d\n",
4849 hours, minutes, seconds, frames);
4850
4851 } else {
4852 snd_iprintf(buffer, "No TCO module detected.\n");
4853 }
5760107c
AK
4854}
4855
4856static void
4857snd_hdspm_proc_read_madi(struct snd_info_entry *entry,
4858 struct snd_info_buffer *buffer)
4859{
4860 struct hdspm *hdspm = entry->private_data;
df57de17 4861 unsigned int status, status2;
5760107c
AK
4862
4863 char *pref_sync_ref;
4864 char *autosync_ref;
4865 char *system_clock_mode;
5760107c
AK
4866 int x, x2;
4867
4868 status = hdspm_read(hdspm, HDSPM_statusRegister);
4869 status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
5760107c
AK
4870
4871 snd_iprintf(buffer, "%s (Card #%d) Rev.%x Status2first3bits: %x\n",
4872 hdspm->card_name, hdspm->card->number + 1,
4873 hdspm->firmware_rev,
4874 (status2 & HDSPM_version0) |
4875 (status2 & HDSPM_version1) | (status2 &
4876 HDSPM_version2));
4877
4878 snd_iprintf(buffer, "HW Serial: 0x%06x%06x\n",
4879 (hdspm_read(hdspm, HDSPM_midiStatusIn1)>>8) & 0xFFFFFF,
4880 hdspm->serial);
4881
4882 snd_iprintf(buffer, "IRQ: %d Registers bus: 0x%lx VM: 0x%lx\n",
4883 hdspm->irq, hdspm->port, (unsigned long)hdspm->iobase);
4884
4885 snd_iprintf(buffer, "--- System ---\n");
4886
4887 snd_iprintf(buffer,
4888 "IRQ Pending: Audio=%d, MIDI0=%d, MIDI1=%d, IRQcount=%d\n",
4889 status & HDSPM_audioIRQPending,
4890 (status & HDSPM_midi0IRQPending) ? 1 : 0,
4891 (status & HDSPM_midi1IRQPending) ? 1 : 0,
4892 hdspm->irq_count);
4893 snd_iprintf(buffer,
4894 "HW pointer: id = %d, rawptr = %d (%d->%d) "
4895 "estimated= %ld (bytes)\n",
4896 ((status & HDSPM_BufferID) ? 1 : 0),
4897 (status & HDSPM_BufferPositionMask),
4898 (status & HDSPM_BufferPositionMask) %
4899 (2 * (int)hdspm->period_bytes),
4900 ((status & HDSPM_BufferPositionMask) - 64) %
4901 (2 * (int)hdspm->period_bytes),
4902 (long) hdspm_hw_pointer(hdspm) * 4);
4903
4904 snd_iprintf(buffer,
4905 "MIDI FIFO: Out1=0x%x, Out2=0x%x, In1=0x%x, In2=0x%x \n",
4906 hdspm_read(hdspm, HDSPM_midiStatusOut0) & 0xFF,
4907 hdspm_read(hdspm, HDSPM_midiStatusOut1) & 0xFF,
4908 hdspm_read(hdspm, HDSPM_midiStatusIn0) & 0xFF,
4909 hdspm_read(hdspm, HDSPM_midiStatusIn1) & 0xFF);
4910 snd_iprintf(buffer,
4911 "MIDIoverMADI FIFO: In=0x%x, Out=0x%x \n",
4912 hdspm_read(hdspm, HDSPM_midiStatusIn2) & 0xFF,
4913 hdspm_read(hdspm, HDSPM_midiStatusOut2) & 0xFF);
4914 snd_iprintf(buffer,
4915 "Register: ctrl1=0x%x, ctrl2=0x%x, status1=0x%x, "
4916 "status2=0x%x\n",
4917 hdspm->control_register, hdspm->control2_register,
4918 status, status2);
4919
763f356c
TI
4920
4921 snd_iprintf(buffer, "--- Settings ---\n");
4922
7cb155ff 4923 x = hdspm_get_latency(hdspm);
763f356c
TI
4924
4925 snd_iprintf(buffer,
0dca1793
AK
4926 "Size (Latency): %d samples (2 periods of %lu bytes)\n",
4927 x, (unsigned long) hdspm->period_bytes);
763f356c 4928
0dca1793
AK
4929 snd_iprintf(buffer, "Line out: %s\n",
4930 (hdspm->control_register & HDSPM_LineOut) ? "on " : "off");
763f356c 4931
763f356c 4932 snd_iprintf(buffer,
0dca1793
AK
4933 "ClearTrackMarker = %s, Transmit in %s Channel Mode, "
4934 "Auto Input %s\n",
4935 (hdspm->control_register & HDSPM_clr_tms) ? "on" : "off",
4936 (hdspm->control_register & HDSPM_TX_64ch) ? "64" : "56",
4937 (hdspm->control_register & HDSPM_AutoInp) ? "on" : "off");
4938
763f356c 4939
3cee5a60 4940 if (!(hdspm->control_register & HDSPM_ClockModeMaster))
0dca1793 4941 system_clock_mode = "AutoSync";
3cee5a60 4942 else
763f356c 4943 system_clock_mode = "Master";
0dca1793 4944 snd_iprintf(buffer, "AutoSync Reference: %s\n", system_clock_mode);
763f356c
TI
4945
4946 switch (hdspm_pref_sync_ref(hdspm)) {
4947 case HDSPM_SYNC_FROM_WORD:
4948 pref_sync_ref = "Word Clock";
4949 break;
4950 case HDSPM_SYNC_FROM_MADI:
4951 pref_sync_ref = "MADI Sync";
4952 break;
0dca1793
AK
4953 case HDSPM_SYNC_FROM_TCO:
4954 pref_sync_ref = "TCO";
4955 break;
4956 case HDSPM_SYNC_FROM_SYNC_IN:
4957 pref_sync_ref = "Sync In";
4958 break;
763f356c
TI
4959 default:
4960 pref_sync_ref = "XXXX Clock";
4961 break;
4962 }
4963 snd_iprintf(buffer, "Preferred Sync Reference: %s\n",
0dca1793 4964 pref_sync_ref);
763f356c
TI
4965
4966 snd_iprintf(buffer, "System Clock Frequency: %d\n",
0dca1793 4967 hdspm->system_sample_rate);
763f356c
TI
4968
4969
4970 snd_iprintf(buffer, "--- Status:\n");
4971
4972 x = status & HDSPM_madiSync;
4973 x2 = status2 & HDSPM_wcSync;
4974
4975 snd_iprintf(buffer, "Inputs MADI=%s, WordClock=%s\n",
0dca1793
AK
4976 (status & HDSPM_madiLock) ? (x ? "Sync" : "Lock") :
4977 "NoLock",
4978 (status2 & HDSPM_wcLock) ? (x2 ? "Sync" : "Lock") :
4979 "NoLock");
763f356c
TI
4980
4981 switch (hdspm_autosync_ref(hdspm)) {
0dca1793
AK
4982 case HDSPM_AUTOSYNC_FROM_SYNC_IN:
4983 autosync_ref = "Sync In";
4984 break;
4985 case HDSPM_AUTOSYNC_FROM_TCO:
4986 autosync_ref = "TCO";
4987 break;
763f356c
TI
4988 case HDSPM_AUTOSYNC_FROM_WORD:
4989 autosync_ref = "Word Clock";
4990 break;
4991 case HDSPM_AUTOSYNC_FROM_MADI:
4992 autosync_ref = "MADI Sync";
4993 break;
4994 case HDSPM_AUTOSYNC_FROM_NONE:
4995 autosync_ref = "Input not valid";
4996 break;
4997 default:
4998 autosync_ref = "---";
4999 break;
5000 }
5001 snd_iprintf(buffer,
0dca1793
AK
5002 "AutoSync: Reference= %s, Freq=%d (MADI = %d, Word = %d)\n",
5003 autosync_ref, hdspm_external_sample_rate(hdspm),
5004 (status & HDSPM_madiFreqMask) >> 22,
5005 (status2 & HDSPM_wcFreqMask) >> 5);
763f356c
TI
5006
5007 snd_iprintf(buffer, "Input: %s, Mode=%s\n",
0dca1793
AK
5008 (status & HDSPM_AB_int) ? "Coax" : "Optical",
5009 (status & HDSPM_RX_64ch) ? "64 channels" :
5010 "56 channels");
763f356c 5011
5760107c
AK
5012 /* call readout function for TCO specific status */
5013 snd_hdspm_proc_read_tco(entry, buffer);
5014
763f356c
TI
5015 snd_iprintf(buffer, "\n");
5016}
5017
3cee5a60
RB
5018static void
5019snd_hdspm_proc_read_aes32(struct snd_info_entry * entry,
5020 struct snd_info_buffer *buffer)
5021{
ef5fa1a4 5022 struct hdspm *hdspm = entry->private_data;
3cee5a60
RB
5023 unsigned int status;
5024 unsigned int status2;
5025 unsigned int timecode;
56bde0f3 5026 unsigned int wcLock, wcSync;
3cee5a60
RB
5027 int pref_syncref;
5028 char *autosync_ref;
3cee5a60
RB
5029 int x;
5030
5031 status = hdspm_read(hdspm, HDSPM_statusRegister);
5032 status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
5033 timecode = hdspm_read(hdspm, HDSPM_timecodeRegister);
5034
5035 snd_iprintf(buffer, "%s (Card #%d) Rev.%x\n",
5036 hdspm->card_name, hdspm->card->number + 1,
5037 hdspm->firmware_rev);
5038
5039 snd_iprintf(buffer, "IRQ: %d Registers bus: 0x%lx VM: 0x%lx\n",
5040 hdspm->irq, hdspm->port, (unsigned long)hdspm->iobase);
5041
5042 snd_iprintf(buffer, "--- System ---\n");
5043
5044 snd_iprintf(buffer,
5045 "IRQ Pending: Audio=%d, MIDI0=%d, MIDI1=%d, IRQcount=%d\n",
5046 status & HDSPM_audioIRQPending,
5047 (status & HDSPM_midi0IRQPending) ? 1 : 0,
5048 (status & HDSPM_midi1IRQPending) ? 1 : 0,
5049 hdspm->irq_count);
5050 snd_iprintf(buffer,
ef5fa1a4
TI
5051 "HW pointer: id = %d, rawptr = %d (%d->%d) "
5052 "estimated= %ld (bytes)\n",
3cee5a60
RB
5053 ((status & HDSPM_BufferID) ? 1 : 0),
5054 (status & HDSPM_BufferPositionMask),
ef5fa1a4
TI
5055 (status & HDSPM_BufferPositionMask) %
5056 (2 * (int)hdspm->period_bytes),
5057 ((status & HDSPM_BufferPositionMask) - 64) %
5058 (2 * (int)hdspm->period_bytes),
3cee5a60
RB
5059 (long) hdspm_hw_pointer(hdspm) * 4);
5060
5061 snd_iprintf(buffer,
5062 "MIDI FIFO: Out1=0x%x, Out2=0x%x, In1=0x%x, In2=0x%x \n",
5063 hdspm_read(hdspm, HDSPM_midiStatusOut0) & 0xFF,
5064 hdspm_read(hdspm, HDSPM_midiStatusOut1) & 0xFF,
5065 hdspm_read(hdspm, HDSPM_midiStatusIn0) & 0xFF,
5066 hdspm_read(hdspm, HDSPM_midiStatusIn1) & 0xFF);
5067 snd_iprintf(buffer,
0dca1793
AK
5068 "MIDIoverMADI FIFO: In=0x%x, Out=0x%x \n",
5069 hdspm_read(hdspm, HDSPM_midiStatusIn2) & 0xFF,
5070 hdspm_read(hdspm, HDSPM_midiStatusOut2) & 0xFF);
5071 snd_iprintf(buffer,
5072 "Register: ctrl1=0x%x, ctrl2=0x%x, status1=0x%x, "
5073 "status2=0x%x\n",
5074 hdspm->control_register, hdspm->control2_register,
5075 status, status2);
3cee5a60
RB
5076
5077 snd_iprintf(buffer, "--- Settings ---\n");
5078
7cb155ff 5079 x = hdspm_get_latency(hdspm);
3cee5a60
RB
5080
5081 snd_iprintf(buffer,
5082 "Size (Latency): %d samples (2 periods of %lu bytes)\n",
5083 x, (unsigned long) hdspm->period_bytes);
5084
0dca1793 5085 snd_iprintf(buffer, "Line out: %s\n",
3cee5a60 5086 (hdspm->
0dca1793 5087 control_register & HDSPM_LineOut) ? "on " : "off");
3cee5a60
RB
5088
5089 snd_iprintf(buffer,
5090 "ClearTrackMarker %s, Emphasis %s, Dolby %s\n",
5091 (hdspm->
5092 control_register & HDSPM_clr_tms) ? "on" : "off",
5093 (hdspm->
5094 control_register & HDSPM_Emphasis) ? "on" : "off",
5095 (hdspm->
5096 control_register & HDSPM_Dolby) ? "on" : "off");
5097
3cee5a60
RB
5098
5099 pref_syncref = hdspm_pref_sync_ref(hdspm);
5100 if (pref_syncref == 0)
5101 snd_iprintf(buffer, "Preferred Sync Reference: Word Clock\n");
5102 else
5103 snd_iprintf(buffer, "Preferred Sync Reference: AES%d\n",
5104 pref_syncref);
5105
5106 snd_iprintf(buffer, "System Clock Frequency: %d\n",
5107 hdspm->system_sample_rate);
5108
5109 snd_iprintf(buffer, "Double speed: %s\n",
5110 hdspm->control_register & HDSPM_DS_DoubleWire?
5111 "Double wire" : "Single wire");
5112 snd_iprintf(buffer, "Quad speed: %s\n",
5113 hdspm->control_register & HDSPM_QS_DoubleWire?
5114 "Double wire" :
5115 hdspm->control_register & HDSPM_QS_QuadWire?
5116 "Quad wire" : "Single wire");
5117
5118 snd_iprintf(buffer, "--- Status:\n");
5119
56bde0f3
AS
5120 wcLock = status & HDSPM_AES32_wcLock;
5121 wcSync = wcLock && (status & HDSPM_AES32_wcSync);
5122
3cee5a60 5123 snd_iprintf(buffer, "Word: %s Frequency: %d\n",
56bde0f3 5124 (wcLock) ? (wcSync ? "Sync " : "Lock ") : "No Lock",
ef5fa1a4 5125 HDSPM_bit2freq((status >> HDSPM_AES32_wcFreq_bit) & 0xF));
3cee5a60
RB
5126
5127 for (x = 0; x < 8; x++) {
5128 snd_iprintf(buffer, "AES%d: %s Frequency: %d\n",
ef5fa1a4
TI
5129 x+1,
5130 (status2 & (HDSPM_LockAES >> x)) ?
0dca1793 5131 "Sync " : "No Lock",
ef5fa1a4 5132 HDSPM_bit2freq((timecode >> (4*x)) & 0xF));
3cee5a60
RB
5133 }
5134
5135 switch (hdspm_autosync_ref(hdspm)) {
0dca1793
AK
5136 case HDSPM_AES32_AUTOSYNC_FROM_NONE:
5137 autosync_ref = "None"; break;
5138 case HDSPM_AES32_AUTOSYNC_FROM_WORD:
5139 autosync_ref = "Word Clock"; break;
5140 case HDSPM_AES32_AUTOSYNC_FROM_AES1:
5141 autosync_ref = "AES1"; break;
5142 case HDSPM_AES32_AUTOSYNC_FROM_AES2:
5143 autosync_ref = "AES2"; break;
5144 case HDSPM_AES32_AUTOSYNC_FROM_AES3:
5145 autosync_ref = "AES3"; break;
5146 case HDSPM_AES32_AUTOSYNC_FROM_AES4:
5147 autosync_ref = "AES4"; break;
5148 case HDSPM_AES32_AUTOSYNC_FROM_AES5:
5149 autosync_ref = "AES5"; break;
5150 case HDSPM_AES32_AUTOSYNC_FROM_AES6:
5151 autosync_ref = "AES6"; break;
5152 case HDSPM_AES32_AUTOSYNC_FROM_AES7:
5153 autosync_ref = "AES7"; break;
5154 case HDSPM_AES32_AUTOSYNC_FROM_AES8:
5155 autosync_ref = "AES8"; break;
194062da
AK
5156 case HDSPM_AES32_AUTOSYNC_FROM_TCO:
5157 autosync_ref = "TCO"; break;
5158 case HDSPM_AES32_AUTOSYNC_FROM_SYNC_IN:
5159 autosync_ref = "Sync In"; break;
0dca1793
AK
5160 default:
5161 autosync_ref = "---"; break;
3cee5a60
RB
5162 }
5163 snd_iprintf(buffer, "AutoSync ref = %s\n", autosync_ref);
5164
194062da
AK
5165 /* call readout function for TCO specific status */
5166 snd_hdspm_proc_read_tco(entry, buffer);
5167
3cee5a60
RB
5168 snd_iprintf(buffer, "\n");
5169}
5170
0dca1793
AK
5171static void
5172snd_hdspm_proc_read_raydat(struct snd_info_entry *entry,
5173 struct snd_info_buffer *buffer)
5174{
5175 struct hdspm *hdspm = entry->private_data;
df57de17 5176 unsigned int status1, status2, status3, i;
0dca1793
AK
5177 unsigned int lock, sync;
5178
5179 status1 = hdspm_read(hdspm, HDSPM_RD_STATUS_1); /* s1 */
5180 status2 = hdspm_read(hdspm, HDSPM_RD_STATUS_2); /* freq */
5181 status3 = hdspm_read(hdspm, HDSPM_RD_STATUS_3); /* s2 */
5182
0dca1793
AK
5183 snd_iprintf(buffer, "STATUS1: 0x%08x\n", status1);
5184 snd_iprintf(buffer, "STATUS2: 0x%08x\n", status2);
5185 snd_iprintf(buffer, "STATUS3: 0x%08x\n", status3);
5186
5187
5188 snd_iprintf(buffer, "\n*** CLOCK MODE\n\n");
5189
5190 snd_iprintf(buffer, "Clock mode : %s\n",
5191 (hdspm_system_clock_mode(hdspm) == 0) ? "master" : "slave");
5192 snd_iprintf(buffer, "System frequency: %d Hz\n",
5193 hdspm_get_system_sample_rate(hdspm));
5194
5195 snd_iprintf(buffer, "\n*** INPUT STATUS\n\n");
5196
5197 lock = 0x1;
5198 sync = 0x100;
5199
5200 for (i = 0; i < 8; i++) {
5201 snd_iprintf(buffer, "s1_input %d: Lock %d, Sync %d, Freq %s\n",
5202 i,
5203 (status1 & lock) ? 1 : 0,
5204 (status1 & sync) ? 1 : 0,
5205 texts_freq[(status2 >> (i * 4)) & 0xF]);
5206
5207 lock = lock<<1;
5208 sync = sync<<1;
5209 }
5210
5211 snd_iprintf(buffer, "WC input: Lock %d, Sync %d, Freq %s\n",
5212 (status1 & 0x1000000) ? 1 : 0,
5213 (status1 & 0x2000000) ? 1 : 0,
5214 texts_freq[(status1 >> 16) & 0xF]);
5215
5216 snd_iprintf(buffer, "TCO input: Lock %d, Sync %d, Freq %s\n",
5217 (status1 & 0x4000000) ? 1 : 0,
5218 (status1 & 0x8000000) ? 1 : 0,
5219 texts_freq[(status1 >> 20) & 0xF]);
5220
5221 snd_iprintf(buffer, "SYNC IN: Lock %d, Sync %d, Freq %s\n",
5222 (status3 & 0x400) ? 1 : 0,
5223 (status3 & 0x800) ? 1 : 0,
5224 texts_freq[(status2 >> 12) & 0xF]);
5225
5226}
5227
3cee5a60
RB
5228#ifdef CONFIG_SND_DEBUG
5229static void
0dca1793 5230snd_hdspm_proc_read_debug(struct snd_info_entry *entry,
3cee5a60
RB
5231 struct snd_info_buffer *buffer)
5232{
ef5fa1a4 5233 struct hdspm *hdspm = entry->private_data;
3cee5a60
RB
5234
5235 int j,i;
5236
ef5fa1a4 5237 for (i = 0; i < 256 /* 1024*64 */; i += j) {
3cee5a60
RB
5238 snd_iprintf(buffer, "0x%08X: ", i);
5239 for (j = 0; j < 16; j += 4)
5240 snd_iprintf(buffer, "%08X ", hdspm_read(hdspm, i + j));
5241 snd_iprintf(buffer, "\n");
5242 }
5243}
5244#endif
5245
5246
0dca1793
AK
5247static void snd_hdspm_proc_ports_in(struct snd_info_entry *entry,
5248 struct snd_info_buffer *buffer)
5249{
5250 struct hdspm *hdspm = entry->private_data;
5251 int i;
5252
5253 snd_iprintf(buffer, "# generated by hdspm\n");
5254
5255 for (i = 0; i < hdspm->max_channels_in; i++) {
5256 snd_iprintf(buffer, "%d=%s\n", i+1, hdspm->port_names_in[i]);
5257 }
5258}
5259
5260static void snd_hdspm_proc_ports_out(struct snd_info_entry *entry,
5261 struct snd_info_buffer *buffer)
5262{
5263 struct hdspm *hdspm = entry->private_data;
5264 int i;
5265
5266 snd_iprintf(buffer, "# generated by hdspm\n");
5267
5268 for (i = 0; i < hdspm->max_channels_out; i++) {
5269 snd_iprintf(buffer, "%d=%s\n", i+1, hdspm->port_names_out[i]);
5270 }
5271}
5272
3cee5a60 5273
e23e7a14 5274static void snd_hdspm_proc_init(struct hdspm *hdspm)
763f356c 5275{
47f2769b 5276 void (*read)(struct snd_info_entry *, struct snd_info_buffer *) = NULL;
763f356c 5277
47f2769b
TI
5278 switch (hdspm->io_type) {
5279 case AES32:
5280 read = snd_hdspm_proc_read_aes32;
5281 break;
5282 case MADI:
5283 read = snd_hdspm_proc_read_madi;
5284 break;
5285 case MADIface:
5286 /* read = snd_hdspm_proc_read_madiface; */
5287 break;
5288 case RayDAT:
5289 read = snd_hdspm_proc_read_raydat;
5290 break;
5291 case AIO:
5292 break;
0dca1793
AK
5293 }
5294
47f2769b
TI
5295 snd_card_ro_proc_new(hdspm->card, "hdspm", hdspm, read);
5296 snd_card_ro_proc_new(hdspm->card, "ports.in", hdspm,
5297 snd_hdspm_proc_ports_in);
5298 snd_card_ro_proc_new(hdspm->card, "ports.out", hdspm,
5299 snd_hdspm_proc_ports_out);
0dca1793 5300
3cee5a60
RB
5301#ifdef CONFIG_SND_DEBUG
5302 /* debug file to read all hdspm registers */
47f2769b
TI
5303 snd_card_ro_proc_new(hdspm->card, "debug", hdspm,
5304 snd_hdspm_proc_read_debug);
3cee5a60 5305#endif
763f356c
TI
5306}
5307
5308/*------------------------------------------------------------
0dca1793 5309 hdspm intitialize
763f356c
TI
5310 ------------------------------------------------------------*/
5311
98274f07 5312static int snd_hdspm_set_defaults(struct hdspm * hdspm)
763f356c 5313{
763f356c 5314 /* ASSUMPTION: hdspm->lock is either held, or there is no need to
561de31a 5315 hold it (e.g. during module initialization).
0dca1793 5316 */
763f356c
TI
5317
5318 /* set defaults: */
5319
0dca1793
AK
5320 hdspm->settings_register = 0;
5321
5322 switch (hdspm->io_type) {
5323 case MADI:
5324 case MADIface:
5325 hdspm->control_register =
5326 0x2 + 0x8 + 0x10 + 0x80 + 0x400 + 0x4000 + 0x1000000;
5327 break;
5328
5329 case RayDAT:
5330 case AIO:
5331 hdspm->settings_register = 0x1 + 0x1000;
5332 /* Magic values are: LAT_0, LAT_2, Master, freq1, tx64ch, inp_0,
5333 * line_out */
5334 hdspm->control_register =
5335 0x2 + 0x8 + 0x10 + 0x80 + 0x400 + 0x4000 + 0x1000000;
5336 break;
5337
5338 case AES32:
ef5fa1a4 5339 hdspm->control_register =
e71b95ad 5340 HDSPM_ClockModeMaster | /* Master Clock Mode on */
0dca1793 5341 hdspm_encode_latency(7) | /* latency max=8192samples */
3cee5a60
RB
5342 HDSPM_SyncRef0 | /* AES1 is syncclock */
5343 HDSPM_LineOut | /* Analog output in */
5344 HDSPM_Professional; /* Professional mode */
0dca1793
AK
5345 break;
5346 }
763f356c
TI
5347
5348 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
5349
0dca1793 5350 if (AES32 == hdspm->io_type) {
ffb2c3c0 5351 /* No control2 register for AES32 */
763f356c 5352#ifdef SNDRV_BIG_ENDIAN
ffb2c3c0 5353 hdspm->control2_register = HDSPM_BIGENDIAN_MODE;
763f356c 5354#else
ffb2c3c0 5355 hdspm->control2_register = 0;
763f356c
TI
5356#endif
5357
ffb2c3c0
RB
5358 hdspm_write(hdspm, HDSPM_control2Reg, hdspm->control2_register);
5359 }
763f356c
TI
5360 hdspm_compute_period_size(hdspm);
5361
5362 /* silence everything */
5363
5364 all_in_all_mixer(hdspm, 0 * UNITY_GAIN);
5365
b2ed6326 5366 if (hdspm_is_raydat_or_aio(hdspm))
0dca1793 5367 hdspm_write(hdspm, HDSPM_WR_SETTINGS, hdspm->settings_register);
763f356c
TI
5368
5369 /* set a default rate so that the channel map is set up. */
0dca1793 5370 hdspm_set_rate(hdspm, 48000, 1);
763f356c
TI
5371
5372 return 0;
5373}
5374
5375
5376/*------------------------------------------------------------
0dca1793 5377 interrupt
763f356c
TI
5378 ------------------------------------------------------------*/
5379
7d12e780 5380static irqreturn_t snd_hdspm_interrupt(int irq, void *dev_id)
763f356c 5381{
98274f07 5382 struct hdspm *hdspm = (struct hdspm *) dev_id;
763f356c 5383 unsigned int status;
0dca1793
AK
5384 int i, audio, midi, schedule = 0;
5385 /* cycles_t now; */
763f356c
TI
5386
5387 status = hdspm_read(hdspm, HDSPM_statusRegister);
5388
5389 audio = status & HDSPM_audioIRQPending;
0dca1793
AK
5390 midi = status & (HDSPM_midi0IRQPending | HDSPM_midi1IRQPending |
5391 HDSPM_midi2IRQPending | HDSPM_midi3IRQPending);
5392
5393 /* now = get_cycles(); */
ddcecf6b 5394 /*
0dca1793
AK
5395 * LAT_2..LAT_0 period counter (win) counter (mac)
5396 * 6 4096 ~256053425 ~514672358
5397 * 5 2048 ~128024983 ~257373821
5398 * 4 1024 ~64023706 ~128718089
5399 * 3 512 ~32005945 ~64385999
5400 * 2 256 ~16003039 ~32260176
5401 * 1 128 ~7998738 ~16194507
5402 * 0 64 ~3998231 ~8191558
ddcecf6b 5403 */
0dca1793 5404 /*
e3a471d6 5405 dev_info(hdspm->card->dev, "snd_hdspm_interrupt %llu @ %llx\n",
0dca1793
AK
5406 now-hdspm->last_interrupt, status & 0xFFC0);
5407 hdspm->last_interrupt = now;
5408 */
763f356c 5409
0dca1793 5410 if (!audio && !midi)
763f356c
TI
5411 return IRQ_NONE;
5412
5413 hdspm_write(hdspm, HDSPM_interruptConfirmation, 0);
5414 hdspm->irq_count++;
5415
763f356c
TI
5416
5417 if (audio) {
763f356c 5418 if (hdspm->capture_substream)
ef5fa1a4 5419 snd_pcm_period_elapsed(hdspm->capture_substream);
763f356c
TI
5420
5421 if (hdspm->playback_substream)
ef5fa1a4 5422 snd_pcm_period_elapsed(hdspm->playback_substream);
763f356c
TI
5423 }
5424
0dca1793
AK
5425 if (midi) {
5426 i = 0;
5427 while (i < hdspm->midiPorts) {
5428 if ((hdspm_read(hdspm,
5429 hdspm->midi[i].statusIn) & 0xff) &&
5430 (status & hdspm->midi[i].irq)) {
5431 /* we disable interrupts for this input until
5432 * processing is done
5433 */
5434 hdspm->control_register &= ~hdspm->midi[i].ie;
5435 hdspm_write(hdspm, HDSPM_controlRegister,
5436 hdspm->control_register);
5437 hdspm->midi[i].pending = 1;
5438 schedule = 1;
5439 }
5440
5441 i++;
5442 }
5443
5444 if (schedule)
5445 tasklet_hi_schedule(&hdspm->midi_tasklet);
763f356c 5446 }
0dca1793 5447
763f356c
TI
5448 return IRQ_HANDLED;
5449}
5450
5451/*------------------------------------------------------------
0dca1793 5452 pcm interface
763f356c
TI
5453 ------------------------------------------------------------*/
5454
5455
0dca1793
AK
5456static snd_pcm_uframes_t snd_hdspm_hw_pointer(struct snd_pcm_substream
5457 *substream)
763f356c 5458{
98274f07 5459 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
5460 return hdspm_hw_pointer(hdspm);
5461}
5462
763f356c 5463
98274f07 5464static int snd_hdspm_reset(struct snd_pcm_substream *substream)
763f356c 5465{
98274f07
TI
5466 struct snd_pcm_runtime *runtime = substream->runtime;
5467 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
5468 struct snd_pcm_substream *other;
763f356c
TI
5469
5470 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
5471 other = hdspm->capture_substream;
5472 else
5473 other = hdspm->playback_substream;
5474
5475 if (hdspm->running)
5476 runtime->status->hw_ptr = hdspm_hw_pointer(hdspm);
5477 else
5478 runtime->status->hw_ptr = 0;
5479 if (other) {
98274f07
TI
5480 struct snd_pcm_substream *s;
5481 struct snd_pcm_runtime *oruntime = other->runtime;
ef991b95 5482 snd_pcm_group_for_each_entry(s, substream) {
763f356c
TI
5483 if (s == other) {
5484 oruntime->status->hw_ptr =
0dca1793 5485 runtime->status->hw_ptr;
763f356c
TI
5486 break;
5487 }
5488 }
5489 }
5490 return 0;
5491}
5492
98274f07
TI
5493static int snd_hdspm_hw_params(struct snd_pcm_substream *substream,
5494 struct snd_pcm_hw_params *params)
763f356c 5495{
98274f07 5496 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
5497 int err;
5498 int i;
5499 pid_t this_pid;
5500 pid_t other_pid;
763f356c
TI
5501
5502 spin_lock_irq(&hdspm->lock);
5503
5504 if (substream->pstr->stream == SNDRV_PCM_STREAM_PLAYBACK) {
5505 this_pid = hdspm->playback_pid;
5506 other_pid = hdspm->capture_pid;
5507 } else {
5508 this_pid = hdspm->capture_pid;
5509 other_pid = hdspm->playback_pid;
5510 }
5511
ef5fa1a4 5512 if (other_pid > 0 && this_pid != other_pid) {
763f356c
TI
5513
5514 /* The other stream is open, and not by the same
5515 task as this one. Make sure that the parameters
5516 that matter are the same.
0dca1793 5517 */
763f356c
TI
5518
5519 if (params_rate(params) != hdspm->system_sample_rate) {
5520 spin_unlock_irq(&hdspm->lock);
5521 _snd_pcm_hw_param_setempty(params,
0dca1793 5522 SNDRV_PCM_HW_PARAM_RATE);
763f356c
TI
5523 return -EBUSY;
5524 }
5525
5526 if (params_period_size(params) != hdspm->period_bytes / 4) {
5527 spin_unlock_irq(&hdspm->lock);
5528 _snd_pcm_hw_param_setempty(params,
0dca1793 5529 SNDRV_PCM_HW_PARAM_PERIOD_SIZE);
763f356c
TI
5530 return -EBUSY;
5531 }
5532
5533 }
5534 /* We're fine. */
5535 spin_unlock_irq(&hdspm->lock);
5536
5537 /* how to make sure that the rate matches an externally-set one ? */
5538
5539 spin_lock_irq(&hdspm->lock);
ef5fa1a4
TI
5540 err = hdspm_set_rate(hdspm, params_rate(params), 0);
5541 if (err < 0) {
e3a471d6 5542 dev_info(hdspm->card->dev, "err on hdspm_set_rate: %d\n", err);
763f356c
TI
5543 spin_unlock_irq(&hdspm->lock);
5544 _snd_pcm_hw_param_setempty(params,
0dca1793 5545 SNDRV_PCM_HW_PARAM_RATE);
763f356c
TI
5546 return err;
5547 }
5548 spin_unlock_irq(&hdspm->lock);
5549
ef5fa1a4 5550 err = hdspm_set_interrupt_interval(hdspm,
0dca1793 5551 params_period_size(params));
ef5fa1a4 5552 if (err < 0) {
e3a471d6
TI
5553 dev_info(hdspm->card->dev,
5554 "err on hdspm_set_interrupt_interval: %d\n", err);
763f356c 5555 _snd_pcm_hw_param_setempty(params,
0dca1793 5556 SNDRV_PCM_HW_PARAM_PERIOD_SIZE);
763f356c
TI
5557 return err;
5558 }
5559
ef5fa1a4
TI
5560 /* Memory allocation, takashi's method, dont know if we should
5561 * spinlock
5562 */
763f356c 5563 /* malloc all buffer even if not enabled to get sure */
ffb2c3c0
RB
5564 /* Update for MADI rev 204: we need to allocate for all channels,
5565 * otherwise it doesn't work at 96kHz */
0dca1793 5566
763f356c 5567 err =
0dca1793
AK
5568 snd_pcm_lib_malloc_pages(substream, HDSPM_DMA_AREA_BYTES);
5569 if (err < 0) {
e3a471d6
TI
5570 dev_info(hdspm->card->dev,
5571 "err on snd_pcm_lib_malloc_pages: %d\n", err);
763f356c 5572 return err;
0dca1793 5573 }
763f356c 5574
763f356c
TI
5575 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
5576
77a23f26 5577 hdspm_set_sgbuf(hdspm, substream, HDSPM_pageAddressBufferOut,
763f356c
TI
5578 params_channels(params));
5579
5580 for (i = 0; i < params_channels(params); ++i)
5581 snd_hdspm_enable_out(hdspm, i, 1);
5582
5583 hdspm->playback_buffer =
0dca1793 5584 (unsigned char *) substream->runtime->dma_area;
e3a471d6
TI
5585 dev_dbg(hdspm->card->dev,
5586 "Allocated sample buffer for playback at %p\n",
3cee5a60 5587 hdspm->playback_buffer);
763f356c 5588 } else {
77a23f26 5589 hdspm_set_sgbuf(hdspm, substream, HDSPM_pageAddressBufferIn,
763f356c
TI
5590 params_channels(params));
5591
5592 for (i = 0; i < params_channels(params); ++i)
5593 snd_hdspm_enable_in(hdspm, i, 1);
5594
5595 hdspm->capture_buffer =
0dca1793 5596 (unsigned char *) substream->runtime->dma_area;
e3a471d6
TI
5597 dev_dbg(hdspm->card->dev,
5598 "Allocated sample buffer for capture at %p\n",
3cee5a60 5599 hdspm->capture_buffer);
763f356c 5600 }
0dca1793 5601
3cee5a60 5602 /*
e3a471d6
TI
5603 dev_dbg(hdspm->card->dev,
5604 "Allocated sample buffer for %s at 0x%08X\n",
3cee5a60
RB
5605 substream->stream == SNDRV_PCM_STREAM_PLAYBACK ?
5606 "playback" : "capture",
77a23f26 5607 snd_pcm_sgbuf_get_addr(substream, 0));
0dca1793 5608 */
ffb2c3c0 5609 /*
e3a471d6
TI
5610 dev_dbg(hdspm->card->dev,
5611 "set_hwparams: %s %d Hz, %d channels, bs = %d\n",
0dca1793
AK
5612 substream->stream == SNDRV_PCM_STREAM_PLAYBACK ?
5613 "playback" : "capture",
5614 params_rate(params), params_channels(params),
5615 params_buffer_size(params));
5616 */
5617
5618
3ac9b0ac
AK
5619 /* For AES cards, the float format bit is the same as the
5620 * preferred sync reference. Since we don't want to break
5621 * sync settings, we have to skip the remaining part of this
5622 * function.
5623 */
5624 if (hdspm->io_type == AES32) {
5625 return 0;
5626 }
5627
5628
0dca1793
AK
5629 /* Switch to native float format if requested */
5630 if (SNDRV_PCM_FORMAT_FLOAT_LE == params_format(params)) {
5631 if (!(hdspm->control_register & HDSPe_FLOAT_FORMAT))
e3a471d6
TI
5632 dev_info(hdspm->card->dev,
5633 "Switching to native 32bit LE float format.\n");
0dca1793
AK
5634
5635 hdspm->control_register |= HDSPe_FLOAT_FORMAT;
5636 } else if (SNDRV_PCM_FORMAT_S32_LE == params_format(params)) {
5637 if (hdspm->control_register & HDSPe_FLOAT_FORMAT)
e3a471d6
TI
5638 dev_info(hdspm->card->dev,
5639 "Switching to native 32bit LE integer format.\n");
0dca1793
AK
5640
5641 hdspm->control_register &= ~HDSPe_FLOAT_FORMAT;
5642 }
5643 hdspm_write(hdspm, HDSPM_controlRegister, hdspm->control_register);
5644
763f356c
TI
5645 return 0;
5646}
5647
98274f07 5648static int snd_hdspm_hw_free(struct snd_pcm_substream *substream)
763f356c
TI
5649{
5650 int i;
98274f07 5651 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
763f356c
TI
5652
5653 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
5654
0dca1793 5655 /* params_channels(params) should be enough,
763f356c 5656 but to get sure in case of error */
0dca1793 5657 for (i = 0; i < hdspm->max_channels_out; ++i)
763f356c
TI
5658 snd_hdspm_enable_out(hdspm, i, 0);
5659
5660 hdspm->playback_buffer = NULL;
5661 } else {
0dca1793 5662 for (i = 0; i < hdspm->max_channels_in; ++i)
763f356c
TI
5663 snd_hdspm_enable_in(hdspm, i, 0);
5664
5665 hdspm->capture_buffer = NULL;
5666
5667 }
5668
5669 snd_pcm_lib_free_pages(substream);
5670
5671 return 0;
5672}
5673
0dca1793 5674
98274f07 5675static int snd_hdspm_channel_info(struct snd_pcm_substream *substream,
0dca1793 5676 struct snd_pcm_channel_info *info)
763f356c 5677{
98274f07 5678 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
10513142 5679 unsigned int channel = info->channel;
763f356c 5680
0dca1793 5681 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
10513142 5682 if (snd_BUG_ON(channel >= hdspm->max_channels_out)) {
e3a471d6
TI
5683 dev_info(hdspm->card->dev,
5684 "snd_hdspm_channel_info: output channel out of range (%d)\n",
10513142 5685 channel);
0dca1793
AK
5686 return -EINVAL;
5687 }
763f356c 5688
10513142
TI
5689 channel = array_index_nospec(channel, hdspm->max_channels_out);
5690 if (hdspm->channel_map_out[channel] < 0) {
e3a471d6
TI
5691 dev_info(hdspm->card->dev,
5692 "snd_hdspm_channel_info: output channel %d mapped out\n",
10513142 5693 channel);
0dca1793
AK
5694 return -EINVAL;
5695 }
5696
10513142 5697 info->offset = hdspm->channel_map_out[channel] *
0dca1793
AK
5698 HDSPM_CHANNEL_BUFFER_BYTES;
5699 } else {
10513142 5700 if (snd_BUG_ON(channel >= hdspm->max_channels_in)) {
e3a471d6
TI
5701 dev_info(hdspm->card->dev,
5702 "snd_hdspm_channel_info: input channel out of range (%d)\n",
10513142 5703 channel);
0dca1793
AK
5704 return -EINVAL;
5705 }
5706
10513142
TI
5707 channel = array_index_nospec(channel, hdspm->max_channels_in);
5708 if (hdspm->channel_map_in[channel] < 0) {
e3a471d6
TI
5709 dev_info(hdspm->card->dev,
5710 "snd_hdspm_channel_info: input channel %d mapped out\n",
10513142 5711 channel);
0dca1793
AK
5712 return -EINVAL;
5713 }
5714
10513142 5715 info->offset = hdspm->channel_map_in[channel] *
0dca1793
AK
5716 HDSPM_CHANNEL_BUFFER_BYTES;
5717 }
763f356c 5718
763f356c
TI
5719 info->first = 0;
5720 info->step = 32;
5721 return 0;
5722}
5723
0dca1793 5724
98274f07 5725static int snd_hdspm_ioctl(struct snd_pcm_substream *substream,
0dca1793 5726 unsigned int cmd, void *arg)
763f356c
TI
5727{
5728 switch (cmd) {
5729 case SNDRV_PCM_IOCTL1_RESET:
ef5fa1a4 5730 return snd_hdspm_reset(substream);
763f356c
TI
5731
5732 case SNDRV_PCM_IOCTL1_CHANNEL_INFO:
0dca1793
AK
5733 {
5734 struct snd_pcm_channel_info *info = arg;
5735 return snd_hdspm_channel_info(substream, info);
5736 }
763f356c
TI
5737 default:
5738 break;
5739 }
5740
5741 return snd_pcm_lib_ioctl(substream, cmd, arg);
5742}
5743
98274f07 5744static int snd_hdspm_trigger(struct snd_pcm_substream *substream, int cmd)
763f356c 5745{
98274f07
TI
5746 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
5747 struct snd_pcm_substream *other;
763f356c
TI
5748 int running;
5749
5750 spin_lock(&hdspm->lock);
5751 running = hdspm->running;
5752 switch (cmd) {
5753 case SNDRV_PCM_TRIGGER_START:
5754 running |= 1 << substream->stream;
5755 break;
5756 case SNDRV_PCM_TRIGGER_STOP:
5757 running &= ~(1 << substream->stream);
5758 break;
5759 default:
5760 snd_BUG();
5761 spin_unlock(&hdspm->lock);
5762 return -EINVAL;
5763 }
5764 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
5765 other = hdspm->capture_substream;
5766 else
5767 other = hdspm->playback_substream;
5768
5769 if (other) {
98274f07 5770 struct snd_pcm_substream *s;
ef991b95 5771 snd_pcm_group_for_each_entry(s, substream) {
763f356c
TI
5772 if (s == other) {
5773 snd_pcm_trigger_done(s, substream);
5774 if (cmd == SNDRV_PCM_TRIGGER_START)
5775 running |= 1 << s->stream;
5776 else
5777 running &= ~(1 << s->stream);
5778 goto _ok;
5779 }
5780 }
5781 if (cmd == SNDRV_PCM_TRIGGER_START) {
5782 if (!(running & (1 << SNDRV_PCM_STREAM_PLAYBACK))
0dca1793
AK
5783 && substream->stream ==
5784 SNDRV_PCM_STREAM_CAPTURE)
763f356c
TI
5785 hdspm_silence_playback(hdspm);
5786 } else {
5787 if (running &&
0dca1793 5788 substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
763f356c
TI
5789 hdspm_silence_playback(hdspm);
5790 }
5791 } else {
5792 if (substream->stream == SNDRV_PCM_STREAM_CAPTURE)
5793 hdspm_silence_playback(hdspm);
5794 }
0dca1793 5795_ok:
763f356c
TI
5796 snd_pcm_trigger_done(substream, substream);
5797 if (!hdspm->running && running)
5798 hdspm_start_audio(hdspm);
5799 else if (hdspm->running && !running)
5800 hdspm_stop_audio(hdspm);
5801 hdspm->running = running;
5802 spin_unlock(&hdspm->lock);
5803
5804 return 0;
5805}
5806
98274f07 5807static int snd_hdspm_prepare(struct snd_pcm_substream *substream)
763f356c
TI
5808{
5809 return 0;
5810}
5811
98274f07 5812static struct snd_pcm_hardware snd_hdspm_playback_subinfo = {
763f356c
TI
5813 .info = (SNDRV_PCM_INFO_MMAP |
5814 SNDRV_PCM_INFO_MMAP_VALID |
5815 SNDRV_PCM_INFO_NONINTERLEAVED |
5816 SNDRV_PCM_INFO_SYNC_START | SNDRV_PCM_INFO_DOUBLE),
5817 .formats = SNDRV_PCM_FMTBIT_S32_LE,
5818 .rates = (SNDRV_PCM_RATE_32000 |
5819 SNDRV_PCM_RATE_44100 |
5820 SNDRV_PCM_RATE_48000 |
5821 SNDRV_PCM_RATE_64000 |
3cee5a60
RB
5822 SNDRV_PCM_RATE_88200 | SNDRV_PCM_RATE_96000 |
5823 SNDRV_PCM_RATE_176400 | SNDRV_PCM_RATE_192000 ),
763f356c 5824 .rate_min = 32000,
3cee5a60 5825 .rate_max = 192000,
763f356c
TI
5826 .channels_min = 1,
5827 .channels_max = HDSPM_MAX_CHANNELS,
5828 .buffer_bytes_max =
5829 HDSPM_CHANNEL_BUFFER_BYTES * HDSPM_MAX_CHANNELS,
1b6fa108 5830 .period_bytes_min = (32 * 4),
52e6fb48 5831 .period_bytes_max = (8192 * 4) * HDSPM_MAX_CHANNELS,
763f356c 5832 .periods_min = 2,
0dca1793 5833 .periods_max = 512,
763f356c
TI
5834 .fifo_size = 0
5835};
5836
98274f07 5837static struct snd_pcm_hardware snd_hdspm_capture_subinfo = {
763f356c
TI
5838 .info = (SNDRV_PCM_INFO_MMAP |
5839 SNDRV_PCM_INFO_MMAP_VALID |
5840 SNDRV_PCM_INFO_NONINTERLEAVED |
5841 SNDRV_PCM_INFO_SYNC_START),
5842 .formats = SNDRV_PCM_FMTBIT_S32_LE,
5843 .rates = (SNDRV_PCM_RATE_32000 |
5844 SNDRV_PCM_RATE_44100 |
5845 SNDRV_PCM_RATE_48000 |
5846 SNDRV_PCM_RATE_64000 |
3cee5a60
RB
5847 SNDRV_PCM_RATE_88200 | SNDRV_PCM_RATE_96000 |
5848 SNDRV_PCM_RATE_176400 | SNDRV_PCM_RATE_192000),
763f356c 5849 .rate_min = 32000,
3cee5a60 5850 .rate_max = 192000,
763f356c
TI
5851 .channels_min = 1,
5852 .channels_max = HDSPM_MAX_CHANNELS,
5853 .buffer_bytes_max =
5854 HDSPM_CHANNEL_BUFFER_BYTES * HDSPM_MAX_CHANNELS,
1b6fa108 5855 .period_bytes_min = (32 * 4),
52e6fb48 5856 .period_bytes_max = (8192 * 4) * HDSPM_MAX_CHANNELS,
763f356c 5857 .periods_min = 2,
0dca1793 5858 .periods_max = 512,
763f356c
TI
5859 .fifo_size = 0
5860};
5861
0dca1793
AK
5862static int snd_hdspm_hw_rule_in_channels_rate(struct snd_pcm_hw_params *params,
5863 struct snd_pcm_hw_rule *rule)
5864{
5865 struct hdspm *hdspm = rule->private;
5866 struct snd_interval *c =
5867 hw_param_interval(params, SNDRV_PCM_HW_PARAM_CHANNELS);
5868 struct snd_interval *r =
5869 hw_param_interval(params, SNDRV_PCM_HW_PARAM_RATE);
5870
5871 if (r->min > 96000 && r->max <= 192000) {
5872 struct snd_interval t = {
5873 .min = hdspm->qs_in_channels,
5874 .max = hdspm->qs_in_channels,
5875 .integer = 1,
5876 };
5877 return snd_interval_refine(c, &t);
5878 } else if (r->min > 48000 && r->max <= 96000) {
5879 struct snd_interval t = {
5880 .min = hdspm->ds_in_channels,
5881 .max = hdspm->ds_in_channels,
5882 .integer = 1,
5883 };
5884 return snd_interval_refine(c, &t);
5885 } else if (r->max < 64000) {
5886 struct snd_interval t = {
5887 .min = hdspm->ss_in_channels,
5888 .max = hdspm->ss_in_channels,
5889 .integer = 1,
5890 };
5891 return snd_interval_refine(c, &t);
5892 }
5893
5894 return 0;
5895}
763f356c 5896
0dca1793 5897static int snd_hdspm_hw_rule_out_channels_rate(struct snd_pcm_hw_params *params,
98274f07 5898 struct snd_pcm_hw_rule * rule)
763f356c 5899{
98274f07
TI
5900 struct hdspm *hdspm = rule->private;
5901 struct snd_interval *c =
763f356c 5902 hw_param_interval(params, SNDRV_PCM_HW_PARAM_CHANNELS);
98274f07 5903 struct snd_interval *r =
763f356c
TI
5904 hw_param_interval(params, SNDRV_PCM_HW_PARAM_RATE);
5905
0dca1793
AK
5906 if (r->min > 96000 && r->max <= 192000) {
5907 struct snd_interval t = {
5908 .min = hdspm->qs_out_channels,
5909 .max = hdspm->qs_out_channels,
5910 .integer = 1,
5911 };
5912 return snd_interval_refine(c, &t);
5913 } else if (r->min > 48000 && r->max <= 96000) {
98274f07 5914 struct snd_interval t = {
0dca1793
AK
5915 .min = hdspm->ds_out_channels,
5916 .max = hdspm->ds_out_channels,
763f356c
TI
5917 .integer = 1,
5918 };
5919 return snd_interval_refine(c, &t);
5920 } else if (r->max < 64000) {
98274f07 5921 struct snd_interval t = {
0dca1793
AK
5922 .min = hdspm->ss_out_channels,
5923 .max = hdspm->ss_out_channels,
763f356c
TI
5924 .integer = 1,
5925 };
5926 return snd_interval_refine(c, &t);
0dca1793 5927 } else {
763f356c
TI
5928 }
5929 return 0;
5930}
5931
0dca1793 5932static int snd_hdspm_hw_rule_rate_in_channels(struct snd_pcm_hw_params *params,
98274f07 5933 struct snd_pcm_hw_rule * rule)
763f356c 5934{
98274f07
TI
5935 struct hdspm *hdspm = rule->private;
5936 struct snd_interval *c =
763f356c 5937 hw_param_interval(params, SNDRV_PCM_HW_PARAM_CHANNELS);
98274f07 5938 struct snd_interval *r =
763f356c
TI
5939 hw_param_interval(params, SNDRV_PCM_HW_PARAM_RATE);
5940
0dca1793 5941 if (c->min >= hdspm->ss_in_channels) {
98274f07 5942 struct snd_interval t = {
763f356c
TI
5943 .min = 32000,
5944 .max = 48000,
5945 .integer = 1,
5946 };
5947 return snd_interval_refine(r, &t);
0dca1793
AK
5948 } else if (c->max <= hdspm->qs_in_channels) {
5949 struct snd_interval t = {
5950 .min = 128000,
5951 .max = 192000,
5952 .integer = 1,
5953 };
5954 return snd_interval_refine(r, &t);
5955 } else if (c->max <= hdspm->ds_in_channels) {
98274f07 5956 struct snd_interval t = {
763f356c
TI
5957 .min = 64000,
5958 .max = 96000,
5959 .integer = 1,
5960 };
0dca1793
AK
5961 return snd_interval_refine(r, &t);
5962 }
5963
5964 return 0;
5965}
5966static int snd_hdspm_hw_rule_rate_out_channels(struct snd_pcm_hw_params *params,
5967 struct snd_pcm_hw_rule *rule)
5968{
5969 struct hdspm *hdspm = rule->private;
5970 struct snd_interval *c =
5971 hw_param_interval(params, SNDRV_PCM_HW_PARAM_CHANNELS);
5972 struct snd_interval *r =
5973 hw_param_interval(params, SNDRV_PCM_HW_PARAM_RATE);
763f356c 5974
0dca1793
AK
5975 if (c->min >= hdspm->ss_out_channels) {
5976 struct snd_interval t = {
5977 .min = 32000,
5978 .max = 48000,
5979 .integer = 1,
5980 };
5981 return snd_interval_refine(r, &t);
5982 } else if (c->max <= hdspm->qs_out_channels) {
5983 struct snd_interval t = {
5984 .min = 128000,
5985 .max = 192000,
5986 .integer = 1,
5987 };
5988 return snd_interval_refine(r, &t);
5989 } else if (c->max <= hdspm->ds_out_channels) {
5990 struct snd_interval t = {
5991 .min = 64000,
5992 .max = 96000,
5993 .integer = 1,
5994 };
763f356c
TI
5995 return snd_interval_refine(r, &t);
5996 }
0dca1793 5997
763f356c
TI
5998 return 0;
5999}
6000
0dca1793 6001static int snd_hdspm_hw_rule_in_channels(struct snd_pcm_hw_params *params,
ffb2c3c0
RB
6002 struct snd_pcm_hw_rule *rule)
6003{
6004 unsigned int list[3];
6005 struct hdspm *hdspm = rule->private;
6006 struct snd_interval *c = hw_param_interval(params,
6007 SNDRV_PCM_HW_PARAM_CHANNELS);
0dca1793
AK
6008
6009 list[0] = hdspm->qs_in_channels;
6010 list[1] = hdspm->ds_in_channels;
6011 list[2] = hdspm->ss_in_channels;
6012 return snd_interval_list(c, 3, list, 0);
6013}
6014
6015static int snd_hdspm_hw_rule_out_channels(struct snd_pcm_hw_params *params,
6016 struct snd_pcm_hw_rule *rule)
6017{
6018 unsigned int list[3];
6019 struct hdspm *hdspm = rule->private;
6020 struct snd_interval *c = hw_param_interval(params,
6021 SNDRV_PCM_HW_PARAM_CHANNELS);
6022
6023 list[0] = hdspm->qs_out_channels;
6024 list[1] = hdspm->ds_out_channels;
6025 list[2] = hdspm->ss_out_channels;
6026 return snd_interval_list(c, 3, list, 0);
ffb2c3c0
RB
6027}
6028
6029
bdf84db7 6030static const unsigned int hdspm_aes32_sample_rates[] = {
ef5fa1a4
TI
6031 32000, 44100, 48000, 64000, 88200, 96000, 128000, 176400, 192000
6032};
ffb2c3c0 6033
bdf84db7 6034static const struct snd_pcm_hw_constraint_list
ef5fa1a4 6035hdspm_hw_constraints_aes32_sample_rates = {
ffb2c3c0
RB
6036 .count = ARRAY_SIZE(hdspm_aes32_sample_rates),
6037 .list = hdspm_aes32_sample_rates,
6038 .mask = 0
6039};
6040
5ecc5dc7 6041static int snd_hdspm_open(struct snd_pcm_substream *substream)
763f356c 6042{
98274f07
TI
6043 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
6044 struct snd_pcm_runtime *runtime = substream->runtime;
5ecc5dc7 6045 bool playback = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK);
763f356c 6046
763f356c 6047 spin_lock_irq(&hdspm->lock);
763f356c 6048 snd_pcm_set_sync(substream);
5ecc5dc7
AK
6049 runtime->hw = (playback) ? snd_hdspm_playback_subinfo :
6050 snd_hdspm_capture_subinfo;
763f356c 6051
5ecc5dc7 6052 if (playback) {
da2ea374 6053 if (!hdspm->capture_substream)
5ecc5dc7 6054 hdspm_stop_audio(hdspm);
0dca1793 6055
5ecc5dc7
AK
6056 hdspm->playback_pid = current->pid;
6057 hdspm->playback_substream = substream;
6058 } else {
da2ea374 6059 if (!hdspm->playback_substream)
5ecc5dc7 6060 hdspm_stop_audio(hdspm);
763f356c 6061
5ecc5dc7
AK
6062 hdspm->capture_pid = current->pid;
6063 hdspm->capture_substream = substream;
6064 }
763f356c
TI
6065
6066 spin_unlock_irq(&hdspm->lock);
6067
6068 snd_pcm_hw_constraint_msbits(runtime, 0, 32, 24);
d877681d 6069 snd_pcm_hw_constraint_pow2(runtime, 0, SNDRV_PCM_HW_PARAM_PERIOD_SIZE);
763f356c 6070
0dca1793
AK
6071 switch (hdspm->io_type) {
6072 case AIO:
6073 case RayDAT:
d877681d
TI
6074 snd_pcm_hw_constraint_minmax(runtime,
6075 SNDRV_PCM_HW_PARAM_PERIOD_SIZE,
6076 32, 4096);
6077 /* RayDAT & AIO have a fixed buffer of 16384 samples per channel */
b4ffc1be 6078 snd_pcm_hw_constraint_single(runtime,
d877681d 6079 SNDRV_PCM_HW_PARAM_BUFFER_SIZE,
b4ffc1be 6080 16384);
0dca1793
AK
6081 break;
6082
6083 default:
d877681d
TI
6084 snd_pcm_hw_constraint_minmax(runtime,
6085 SNDRV_PCM_HW_PARAM_PERIOD_SIZE,
6086 64, 8192);
b4ffc1be
LPC
6087 snd_pcm_hw_constraint_single(runtime,
6088 SNDRV_PCM_HW_PARAM_PERIODS, 2);
d877681d 6089 break;
0dca1793 6090 }
763f356c 6091
0dca1793 6092 if (AES32 == hdspm->io_type) {
3fa9e3d2 6093 runtime->hw.rates |= SNDRV_PCM_RATE_KNOT;
ffb2c3c0
RB
6094 snd_pcm_hw_constraint_list(runtime, 0, SNDRV_PCM_HW_PARAM_RATE,
6095 &hdspm_hw_constraints_aes32_sample_rates);
6096 } else {
ffb2c3c0 6097 snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_RATE,
5ecc5dc7
AK
6098 (playback ?
6099 snd_hdspm_hw_rule_rate_out_channels :
6100 snd_hdspm_hw_rule_rate_in_channels), hdspm,
0dca1793 6101 SNDRV_PCM_HW_PARAM_CHANNELS, -1);
ffb2c3c0 6102 }
88fabbfc
AK
6103
6104 snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_CHANNELS,
5ecc5dc7
AK
6105 (playback ? snd_hdspm_hw_rule_out_channels :
6106 snd_hdspm_hw_rule_in_channels), hdspm,
88fabbfc
AK
6107 SNDRV_PCM_HW_PARAM_CHANNELS, -1);
6108
6109 snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_CHANNELS,
5ecc5dc7
AK
6110 (playback ? snd_hdspm_hw_rule_out_channels_rate :
6111 snd_hdspm_hw_rule_in_channels_rate), hdspm,
88fabbfc
AK
6112 SNDRV_PCM_HW_PARAM_RATE, -1);
6113
763f356c
TI
6114 return 0;
6115}
6116
8b73b867 6117static int snd_hdspm_release(struct snd_pcm_substream *substream)
763f356c 6118{
98274f07 6119 struct hdspm *hdspm = snd_pcm_substream_chip(substream);
8b73b867 6120 bool playback = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK);
763f356c
TI
6121
6122 spin_lock_irq(&hdspm->lock);
6123
8b73b867
AK
6124 if (playback) {
6125 hdspm->playback_pid = -1;
6126 hdspm->playback_substream = NULL;
6127 } else {
6128 hdspm->capture_pid = -1;
6129 hdspm->capture_substream = NULL;
6130 }
763f356c
TI
6131
6132 spin_unlock_irq(&hdspm->lock);
6133
6134 return 0;
6135}
6136
0dca1793
AK
6137static int snd_hdspm_hwdep_dummy_op(struct snd_hwdep *hw, struct file *file)
6138{
6139 /* we have nothing to initialize but the call is required */
6140 return 0;
6141}
6142
6143static inline int copy_u32_le(void __user *dest, void __iomem *src)
6144{
6145 u32 val = readl(src);
6146 return copy_to_user(dest, &val, 4);
6147}
6148
6149static int snd_hdspm_hwdep_ioctl(struct snd_hwdep *hw, struct file *file,
2ca595ab 6150 unsigned int cmd, unsigned long arg)
763f356c 6151{
0dca1793 6152 void __user *argp = (void __user *)arg;
ef5fa1a4 6153 struct hdspm *hdspm = hw->private_data;
98274f07 6154 struct hdspm_mixer_ioctl mixer;
0dca1793
AK
6155 struct hdspm_config info;
6156 struct hdspm_status status;
98274f07 6157 struct hdspm_version hdspm_version;
730a5865 6158 struct hdspm_peak_rms *levels;
0dca1793
AK
6159 struct hdspm_ltc ltc;
6160 unsigned int statusregister;
6161 long unsigned int s;
6162 int i = 0;
763f356c
TI
6163
6164 switch (cmd) {
6165
763f356c 6166 case SNDRV_HDSPM_IOCTL_GET_PEAK_RMS:
730a5865 6167 levels = &hdspm->peak_rms;
0dca1793 6168 for (i = 0; i < HDSPM_MAX_CHANNELS; i++) {
730a5865 6169 levels->input_peaks[i] =
0dca1793
AK
6170 readl(hdspm->iobase +
6171 HDSPM_MADI_INPUT_PEAK + i*4);
730a5865 6172 levels->playback_peaks[i] =
0dca1793
AK
6173 readl(hdspm->iobase +
6174 HDSPM_MADI_PLAYBACK_PEAK + i*4);
730a5865 6175 levels->output_peaks[i] =
0dca1793
AK
6176 readl(hdspm->iobase +
6177 HDSPM_MADI_OUTPUT_PEAK + i*4);
6178
730a5865 6179 levels->input_rms[i] =
0dca1793
AK
6180 ((uint64_t) readl(hdspm->iobase +
6181 HDSPM_MADI_INPUT_RMS_H + i*4) << 32) |
6182 (uint64_t) readl(hdspm->iobase +
6183 HDSPM_MADI_INPUT_RMS_L + i*4);
730a5865 6184 levels->playback_rms[i] =
0dca1793
AK
6185 ((uint64_t)readl(hdspm->iobase +
6186 HDSPM_MADI_PLAYBACK_RMS_H+i*4) << 32) |
6187 (uint64_t)readl(hdspm->iobase +
6188 HDSPM_MADI_PLAYBACK_RMS_L + i*4);
730a5865 6189 levels->output_rms[i] =
0dca1793
AK
6190 ((uint64_t)readl(hdspm->iobase +
6191 HDSPM_MADI_OUTPUT_RMS_H + i*4) << 32) |
6192 (uint64_t)readl(hdspm->iobase +
6193 HDSPM_MADI_OUTPUT_RMS_L + i*4);
6194 }
6195
6196 if (hdspm->system_sample_rate > 96000) {
730a5865 6197 levels->speed = qs;
0dca1793 6198 } else if (hdspm->system_sample_rate > 48000) {
730a5865 6199 levels->speed = ds;
0dca1793 6200 } else {
730a5865 6201 levels->speed = ss;
0dca1793 6202 }
730a5865 6203 levels->status2 = hdspm_read(hdspm, HDSPM_statusRegister2);
0dca1793 6204
7dfec507 6205 s = copy_to_user(argp, levels, sizeof(*levels));
0dca1793 6206 if (0 != s) {
e3a471d6 6207 /* dev_err(hdspm->card->dev, "copy_to_user(.., .., %lu): %lu
0dca1793
AK
6208 [Levels]\n", sizeof(struct hdspm_peak_rms), s);
6209 */
763f356c 6210 return -EFAULT;
0dca1793
AK
6211 }
6212 break;
6213
6214 case SNDRV_HDSPM_IOCTL_GET_LTC:
6215 ltc.ltc = hdspm_read(hdspm, HDSPM_RD_TCO);
6216 i = hdspm_read(hdspm, HDSPM_RD_TCO + 4);
6217 if (i & HDSPM_TCO1_LTC_Input_valid) {
6218 switch (i & (HDSPM_TCO1_LTC_Format_LSB |
6219 HDSPM_TCO1_LTC_Format_MSB)) {
6220 case 0:
6221 ltc.format = fps_24;
6222 break;
6223 case HDSPM_TCO1_LTC_Format_LSB:
6224 ltc.format = fps_25;
6225 break;
6226 case HDSPM_TCO1_LTC_Format_MSB:
6227 ltc.format = fps_2997;
6228 break;
6229 default:
17d2f008 6230 ltc.format = fps_30;
0dca1793
AK
6231 break;
6232 }
6233 if (i & HDSPM_TCO1_set_drop_frame_flag) {
6234 ltc.frame = drop_frame;
6235 } else {
6236 ltc.frame = full_frame;
6237 }
6238 } else {
6239 ltc.format = format_invalid;
6240 ltc.frame = frame_invalid;
6241 }
6242 if (i & HDSPM_TCO1_Video_Input_Format_NTSC) {
6243 ltc.input_format = ntsc;
6244 } else if (i & HDSPM_TCO1_Video_Input_Format_PAL) {
6245 ltc.input_format = pal;
6246 } else {
6247 ltc.input_format = no_video;
6248 }
6249
7dfec507 6250 s = copy_to_user(argp, &ltc, sizeof(ltc));
0dca1793
AK
6251 if (0 != s) {
6252 /*
e3a471d6 6253 dev_err(hdspm->card->dev, "copy_to_user(.., .., %lu): %lu [LTC]\n", sizeof(struct hdspm_ltc), s); */
763f356c 6254 return -EFAULT;
0dca1793 6255 }
763f356c
TI
6256
6257 break;
763f356c 6258
0dca1793 6259 case SNDRV_HDSPM_IOCTL_GET_CONFIG:
763f356c 6260
4ab69a2b 6261 memset(&info, 0, sizeof(info));
763f356c 6262 spin_lock_irq(&hdspm->lock);
ef5fa1a4
TI
6263 info.pref_sync_ref = hdspm_pref_sync_ref(hdspm);
6264 info.wordclock_sync_check = hdspm_wc_sync_check(hdspm);
763f356c
TI
6265
6266 info.system_sample_rate = hdspm->system_sample_rate;
6267 info.autosync_sample_rate =
0dca1793 6268 hdspm_external_sample_rate(hdspm);
ef5fa1a4
TI
6269 info.system_clock_mode = hdspm_system_clock_mode(hdspm);
6270 info.clock_source = hdspm_clock_source(hdspm);
6271 info.autosync_ref = hdspm_autosync_ref(hdspm);
c9e1668c 6272 info.line_out = hdspm_toggle_setting(hdspm, HDSPM_LineOut);
763f356c
TI
6273 info.passthru = 0;
6274 spin_unlock_irq(&hdspm->lock);
2ca595ab 6275 if (copy_to_user(argp, &info, sizeof(info)))
763f356c
TI
6276 return -EFAULT;
6277 break;
6278
0dca1793 6279 case SNDRV_HDSPM_IOCTL_GET_STATUS:
643d6bbb
DC
6280 memset(&status, 0, sizeof(status));
6281
0dca1793
AK
6282 status.card_type = hdspm->io_type;
6283
6284 status.autosync_source = hdspm_autosync_ref(hdspm);
6285
6286 status.card_clock = 110069313433624ULL;
6287 status.master_period = hdspm_read(hdspm, HDSPM_RD_PLL_FREQ);
6288
6289 switch (hdspm->io_type) {
6290 case MADI:
6291 case MADIface:
6292 status.card_specific.madi.sync_wc =
6293 hdspm_wc_sync_check(hdspm);
6294 status.card_specific.madi.sync_madi =
6295 hdspm_madi_sync_check(hdspm);
6296 status.card_specific.madi.sync_tco =
6297 hdspm_tco_sync_check(hdspm);
6298 status.card_specific.madi.sync_in =
6299 hdspm_sync_in_sync_check(hdspm);
6300
6301 statusregister =
6302 hdspm_read(hdspm, HDSPM_statusRegister);
6303 status.card_specific.madi.madi_input =
6304 (statusregister & HDSPM_AB_int) ? 1 : 0;
6305 status.card_specific.madi.channel_format =
9e6ff520 6306 (statusregister & HDSPM_RX_64ch) ? 1 : 0;
0dca1793
AK
6307 /* TODO: Mac driver sets it when f_s>48kHz */
6308 status.card_specific.madi.frame_format = 0;
6309
6310 default:
6311 break;
6312 }
6313
2ca595ab 6314 if (copy_to_user(argp, &status, sizeof(status)))
0dca1793
AK
6315 return -EFAULT;
6316
6317
6318 break;
6319
763f356c 6320 case SNDRV_HDSPM_IOCTL_GET_VERSION:
643d6bbb
DC
6321 memset(&hdspm_version, 0, sizeof(hdspm_version));
6322
0dca1793 6323 hdspm_version.card_type = hdspm->io_type;
57a4451d 6324 strlcpy(hdspm_version.cardname, hdspm->card_name,
0dca1793 6325 sizeof(hdspm_version.cardname));
7d53a631 6326 hdspm_version.serial = hdspm->serial;
763f356c 6327 hdspm_version.firmware_rev = hdspm->firmware_rev;
0dca1793
AK
6328 hdspm_version.addons = 0;
6329 if (hdspm->tco)
6330 hdspm_version.addons |= HDSPM_ADDON_TCO;
6331
2ca595ab 6332 if (copy_to_user(argp, &hdspm_version,
0dca1793 6333 sizeof(hdspm_version)))
763f356c
TI
6334 return -EFAULT;
6335 break;
6336
6337 case SNDRV_HDSPM_IOCTL_GET_MIXER:
2ca595ab 6338 if (copy_from_user(&mixer, argp, sizeof(mixer)))
763f356c 6339 return -EFAULT;
ef5fa1a4 6340 if (copy_to_user((void __user *)mixer.mixer, hdspm->mixer,
7dfec507 6341 sizeof(*mixer.mixer)))
763f356c
TI
6342 return -EFAULT;
6343 break;
6344
6345 default:
6346 return -EINVAL;
6347 }
6348 return 0;
6349}
6350
6769e988 6351static const struct snd_pcm_ops snd_hdspm_ops = {
5ecc5dc7 6352 .open = snd_hdspm_open,
8b73b867 6353 .close = snd_hdspm_release,
763f356c
TI
6354 .ioctl = snd_hdspm_ioctl,
6355 .hw_params = snd_hdspm_hw_params,
6356 .hw_free = snd_hdspm_hw_free,
6357 .prepare = snd_hdspm_prepare,
6358 .trigger = snd_hdspm_trigger,
6359 .pointer = snd_hdspm_hw_pointer,
763f356c
TI
6360 .page = snd_pcm_sgbuf_ops_page,
6361};
6362
e23e7a14
BP
6363static int snd_hdspm_create_hwdep(struct snd_card *card,
6364 struct hdspm *hdspm)
763f356c 6365{
98274f07 6366 struct snd_hwdep *hw;
763f356c
TI
6367 int err;
6368
ef5fa1a4
TI
6369 err = snd_hwdep_new(card, "HDSPM hwdep", 0, &hw);
6370 if (err < 0)
763f356c
TI
6371 return err;
6372
6373 hdspm->hwdep = hw;
6374 hw->private_data = hdspm;
6375 strcpy(hw->name, "HDSPM hwdep interface");
6376
0dca1793 6377 hw->ops.open = snd_hdspm_hwdep_dummy_op;
763f356c 6378 hw->ops.ioctl = snd_hdspm_hwdep_ioctl;
8de5d6f1 6379 hw->ops.ioctl_compat = snd_hdspm_hwdep_ioctl;
0dca1793 6380 hw->ops.release = snd_hdspm_hwdep_dummy_op;
763f356c
TI
6381
6382 return 0;
6383}
6384
6385
6386/*------------------------------------------------------------
0dca1793 6387 memory interface
763f356c 6388 ------------------------------------------------------------*/
e23e7a14 6389static int snd_hdspm_preallocate_memory(struct hdspm *hdspm)
763f356c 6390{
98274f07 6391 struct snd_pcm *pcm;
763f356c
TI
6392 size_t wanted;
6393
6394 pcm = hdspm->pcm;
6395
3cee5a60 6396 wanted = HDSPM_DMA_AREA_BYTES;
763f356c 6397
5116b94a
TI
6398 snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_DEV_SG,
6399 snd_dma_pci_data(hdspm->pci),
6400 wanted, wanted);
6401 dev_dbg(hdspm->card->dev, " Preallocated %zd Bytes\n", wanted);
763f356c
TI
6402 return 0;
6403}
6404
0dca1793
AK
6405
6406static void hdspm_set_sgbuf(struct hdspm *hdspm,
77a23f26 6407 struct snd_pcm_substream *substream,
763f356c
TI
6408 unsigned int reg, int channels)
6409{
6410 int i;
0dca1793
AK
6411
6412 /* continuous memory segment */
763f356c
TI
6413 for (i = 0; i < (channels * 16); i++)
6414 hdspm_write(hdspm, reg + 4 * i,
0dca1793 6415 snd_pcm_sgbuf_get_addr(substream, 4096 * i));
763f356c
TI
6416}
6417
0dca1793 6418
763f356c 6419/* ------------- ALSA Devices ---------------------------- */
e23e7a14
BP
6420static int snd_hdspm_create_pcm(struct snd_card *card,
6421 struct hdspm *hdspm)
763f356c 6422{
98274f07 6423 struct snd_pcm *pcm;
763f356c
TI
6424 int err;
6425
ef5fa1a4
TI
6426 err = snd_pcm_new(card, hdspm->card_name, 0, 1, 1, &pcm);
6427 if (err < 0)
763f356c
TI
6428 return err;
6429
6430 hdspm->pcm = pcm;
6431 pcm->private_data = hdspm;
6432 strcpy(pcm->name, hdspm->card_name);
6433
6434 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK,
0c8d9485 6435 &snd_hdspm_ops);
763f356c 6436 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_CAPTURE,
0c8d9485 6437 &snd_hdspm_ops);
763f356c
TI
6438
6439 pcm->info_flags = SNDRV_PCM_INFO_JOINT_DUPLEX;
6440
ef5fa1a4
TI
6441 err = snd_hdspm_preallocate_memory(hdspm);
6442 if (err < 0)
763f356c
TI
6443 return err;
6444
6445 return 0;
6446}
6447
98274f07 6448static inline void snd_hdspm_initialize_midi_flush(struct hdspm * hdspm)
763f356c 6449{
7c7102b7
AK
6450 int i;
6451
6452 for (i = 0; i < hdspm->midiPorts; i++)
6453 snd_hdspm_flush_midi_input(hdspm, i);
763f356c
TI
6454}
6455
e23e7a14
BP
6456static int snd_hdspm_create_alsa_devices(struct snd_card *card,
6457 struct hdspm *hdspm)
763f356c 6458{
0dca1793 6459 int err, i;
763f356c 6460
e3a471d6 6461 dev_dbg(card->dev, "Create card...\n");
ef5fa1a4
TI
6462 err = snd_hdspm_create_pcm(card, hdspm);
6463 if (err < 0)
763f356c
TI
6464 return err;
6465
0dca1793
AK
6466 i = 0;
6467 while (i < hdspm->midiPorts) {
6468 err = snd_hdspm_create_midi(card, hdspm, i);
6469 if (err < 0) {
6470 return err;
6471 }
6472 i++;
6473 }
763f356c 6474
ef5fa1a4
TI
6475 err = snd_hdspm_create_controls(card, hdspm);
6476 if (err < 0)
763f356c
TI
6477 return err;
6478
ef5fa1a4
TI
6479 err = snd_hdspm_create_hwdep(card, hdspm);
6480 if (err < 0)
763f356c
TI
6481 return err;
6482
e3a471d6 6483 dev_dbg(card->dev, "proc init...\n");
763f356c
TI
6484 snd_hdspm_proc_init(hdspm);
6485
6486 hdspm->system_sample_rate = -1;
6487 hdspm->last_external_sample_rate = -1;
6488 hdspm->last_internal_sample_rate = -1;
6489 hdspm->playback_pid = -1;
6490 hdspm->capture_pid = -1;
6491 hdspm->capture_substream = NULL;
6492 hdspm->playback_substream = NULL;
6493
e3a471d6 6494 dev_dbg(card->dev, "Set defaults...\n");
ef5fa1a4
TI
6495 err = snd_hdspm_set_defaults(hdspm);
6496 if (err < 0)
763f356c
TI
6497 return err;
6498
e3a471d6 6499 dev_dbg(card->dev, "Update mixer controls...\n");
763f356c
TI
6500 hdspm_update_simple_mixer_controls(hdspm);
6501
1bb6d9e2 6502 dev_dbg(card->dev, "Initializing complete?\n");
763f356c 6503
ef5fa1a4
TI
6504 err = snd_card_register(card);
6505 if (err < 0) {
e3a471d6 6506 dev_err(card->dev, "error registering card\n");
763f356c
TI
6507 return err;
6508 }
6509
e3a471d6 6510 dev_dbg(card->dev, "... yes now\n");
763f356c
TI
6511
6512 return 0;
6513}
6514
e23e7a14
BP
6515static int snd_hdspm_create(struct snd_card *card,
6516 struct hdspm *hdspm)
6517{
0dca1793 6518
763f356c
TI
6519 struct pci_dev *pci = hdspm->pci;
6520 int err;
763f356c
TI
6521 unsigned long io_extent;
6522
6523 hdspm->irq = -1;
763f356c
TI
6524 hdspm->card = card;
6525
6526 spin_lock_init(&hdspm->lock);
6527
763f356c 6528 pci_read_config_word(hdspm->pci,
0dca1793 6529 PCI_CLASS_REVISION, &hdspm->firmware_rev);
3cee5a60 6530
763f356c 6531 strcpy(card->mixername, "Xilinx FPGA");
0dca1793
AK
6532 strcpy(card->driver, "HDSPM");
6533
6534 switch (hdspm->firmware_rev) {
0dca1793
AK
6535 case HDSPM_RAYDAT_REV:
6536 hdspm->io_type = RayDAT;
6537 hdspm->card_name = "RME RayDAT";
6538 hdspm->midiPorts = 2;
6539 break;
6540 case HDSPM_AIO_REV:
6541 hdspm->io_type = AIO;
6542 hdspm->card_name = "RME AIO";
6543 hdspm->midiPorts = 1;
6544 break;
6545 case HDSPM_MADIFACE_REV:
6546 hdspm->io_type = MADIface;
6547 hdspm->card_name = "RME MADIface";
6548 hdspm->midiPorts = 1;
6549 break;
5027f347 6550 default:
c09403dc
AK
6551 if ((hdspm->firmware_rev == 0xf0) ||
6552 ((hdspm->firmware_rev >= 0xe6) &&
6553 (hdspm->firmware_rev <= 0xea))) {
6554 hdspm->io_type = AES32;
6555 hdspm->card_name = "RME AES32";
6556 hdspm->midiPorts = 2;
05c7cc9c 6557 } else if ((hdspm->firmware_rev == 0xd2) ||
c09403dc
AK
6558 ((hdspm->firmware_rev >= 0xc8) &&
6559 (hdspm->firmware_rev <= 0xcf))) {
6560 hdspm->io_type = MADI;
6561 hdspm->card_name = "RME MADI";
6562 hdspm->midiPorts = 3;
6563 } else {
e3a471d6
TI
6564 dev_err(card->dev,
6565 "unknown firmware revision %x\n",
5027f347 6566 hdspm->firmware_rev);
c09403dc
AK
6567 return -ENODEV;
6568 }
3cee5a60 6569 }
763f356c 6570
ef5fa1a4
TI
6571 err = pci_enable_device(pci);
6572 if (err < 0)
763f356c
TI
6573 return err;
6574
6575 pci_set_master(hdspm->pci);
6576
ef5fa1a4
TI
6577 err = pci_request_regions(pci, "hdspm");
6578 if (err < 0)
763f356c
TI
6579 return err;
6580
6581 hdspm->port = pci_resource_start(pci, 0);
6582 io_extent = pci_resource_len(pci, 0);
6583
e3a471d6 6584 dev_dbg(card->dev, "grabbed memory region 0x%lx-0x%lx\n",
0dca1793 6585 hdspm->port, hdspm->port + io_extent - 1);
763f356c 6586
ef5fa1a4
TI
6587 hdspm->iobase = ioremap_nocache(hdspm->port, io_extent);
6588 if (!hdspm->iobase) {
e3a471d6 6589 dev_err(card->dev, "unable to remap region 0x%lx-0x%lx\n",
0dca1793 6590 hdspm->port, hdspm->port + io_extent - 1);
763f356c
TI
6591 return -EBUSY;
6592 }
e3a471d6 6593 dev_dbg(card->dev, "remapped region (0x%lx) 0x%lx-0x%lx\n",
0dca1793
AK
6594 (unsigned long)hdspm->iobase, hdspm->port,
6595 hdspm->port + io_extent - 1);
763f356c
TI
6596
6597 if (request_irq(pci->irq, snd_hdspm_interrupt,
934c2b6d 6598 IRQF_SHARED, KBUILD_MODNAME, hdspm)) {
e3a471d6 6599 dev_err(card->dev, "unable to use IRQ %d\n", pci->irq);
763f356c
TI
6600 return -EBUSY;
6601 }
6602
e3a471d6 6603 dev_dbg(card->dev, "use IRQ %d\n", pci->irq);
763f356c
TI
6604
6605 hdspm->irq = pci->irq;
763f356c 6606
e3a471d6 6607 dev_dbg(card->dev, "kmalloc Mixer memory of %zd Bytes\n",
7dfec507
ME
6608 sizeof(*hdspm->mixer));
6609 hdspm->mixer = kzalloc(sizeof(*hdspm->mixer), GFP_KERNEL);
9dba5429 6610 if (!hdspm->mixer)
b17cbdd8 6611 return -ENOMEM;
763f356c 6612
0dca1793
AK
6613 hdspm->port_names_in = NULL;
6614 hdspm->port_names_out = NULL;
6615
6616 switch (hdspm->io_type) {
6617 case AES32:
d2d10a21
AK
6618 hdspm->ss_in_channels = hdspm->ss_out_channels = AES32_CHANNELS;
6619 hdspm->ds_in_channels = hdspm->ds_out_channels = AES32_CHANNELS;
6620 hdspm->qs_in_channels = hdspm->qs_out_channels = AES32_CHANNELS;
432d2500
AK
6621
6622 hdspm->channel_map_in_ss = hdspm->channel_map_out_ss =
6623 channel_map_aes32;
6624 hdspm->channel_map_in_ds = hdspm->channel_map_out_ds =
6625 channel_map_aes32;
6626 hdspm->channel_map_in_qs = hdspm->channel_map_out_qs =
6627 channel_map_aes32;
6628 hdspm->port_names_in_ss = hdspm->port_names_out_ss =
6629 texts_ports_aes32;
6630 hdspm->port_names_in_ds = hdspm->port_names_out_ds =
6631 texts_ports_aes32;
6632 hdspm->port_names_in_qs = hdspm->port_names_out_qs =
6633 texts_ports_aes32;
6634
d2d10a21
AK
6635 hdspm->max_channels_out = hdspm->max_channels_in =
6636 AES32_CHANNELS;
432d2500
AK
6637 hdspm->port_names_in = hdspm->port_names_out =
6638 texts_ports_aes32;
6639 hdspm->channel_map_in = hdspm->channel_map_out =
6640 channel_map_aes32;
6641
0dca1793
AK
6642 break;
6643
6644 case MADI:
6645 case MADIface:
6646 hdspm->ss_in_channels = hdspm->ss_out_channels =
6647 MADI_SS_CHANNELS;
6648 hdspm->ds_in_channels = hdspm->ds_out_channels =
6649 MADI_DS_CHANNELS;
6650 hdspm->qs_in_channels = hdspm->qs_out_channels =
6651 MADI_QS_CHANNELS;
6652
6653 hdspm->channel_map_in_ss = hdspm->channel_map_out_ss =
6654 channel_map_unity_ss;
01e96078 6655 hdspm->channel_map_in_ds = hdspm->channel_map_out_ds =
0dca1793 6656 channel_map_unity_ss;
01e96078 6657 hdspm->channel_map_in_qs = hdspm->channel_map_out_qs =
0dca1793
AK
6658 channel_map_unity_ss;
6659
6660 hdspm->port_names_in_ss = hdspm->port_names_out_ss =
6661 texts_ports_madi;
6662 hdspm->port_names_in_ds = hdspm->port_names_out_ds =
6663 texts_ports_madi;
6664 hdspm->port_names_in_qs = hdspm->port_names_out_qs =
6665 texts_ports_madi;
6666 break;
6667
6668 case AIO:
0dca1793
AK
6669 hdspm->ss_in_channels = AIO_IN_SS_CHANNELS;
6670 hdspm->ds_in_channels = AIO_IN_DS_CHANNELS;
6671 hdspm->qs_in_channels = AIO_IN_QS_CHANNELS;
6672 hdspm->ss_out_channels = AIO_OUT_SS_CHANNELS;
6673 hdspm->ds_out_channels = AIO_OUT_DS_CHANNELS;
6674 hdspm->qs_out_channels = AIO_OUT_QS_CHANNELS;
6675
3de9db26 6676 if (0 == (hdspm_read(hdspm, HDSPM_statusRegister2) & HDSPM_s2_AEBI_D)) {
e3a471d6 6677 dev_info(card->dev, "AEB input board found\n");
3de9db26
AK
6678 hdspm->ss_in_channels += 4;
6679 hdspm->ds_in_channels += 4;
6680 hdspm->qs_in_channels += 4;
6681 }
6682
6683 if (0 == (hdspm_read(hdspm, HDSPM_statusRegister2) & HDSPM_s2_AEBO_D)) {
e3a471d6 6684 dev_info(card->dev, "AEB output board found\n");
3de9db26
AK
6685 hdspm->ss_out_channels += 4;
6686 hdspm->ds_out_channels += 4;
6687 hdspm->qs_out_channels += 4;
6688 }
6689
0dca1793
AK
6690 hdspm->channel_map_out_ss = channel_map_aio_out_ss;
6691 hdspm->channel_map_out_ds = channel_map_aio_out_ds;
6692 hdspm->channel_map_out_qs = channel_map_aio_out_qs;
6693
6694 hdspm->channel_map_in_ss = channel_map_aio_in_ss;
6695 hdspm->channel_map_in_ds = channel_map_aio_in_ds;
6696 hdspm->channel_map_in_qs = channel_map_aio_in_qs;
6697
6698 hdspm->port_names_in_ss = texts_ports_aio_in_ss;
6699 hdspm->port_names_out_ss = texts_ports_aio_out_ss;
6700 hdspm->port_names_in_ds = texts_ports_aio_in_ds;
6701 hdspm->port_names_out_ds = texts_ports_aio_out_ds;
6702 hdspm->port_names_in_qs = texts_ports_aio_in_qs;
6703 hdspm->port_names_out_qs = texts_ports_aio_out_qs;
6704
6705 break;
6706
6707 case RayDAT:
6708 hdspm->ss_in_channels = hdspm->ss_out_channels =
6709 RAYDAT_SS_CHANNELS;
6710 hdspm->ds_in_channels = hdspm->ds_out_channels =
6711 RAYDAT_DS_CHANNELS;
6712 hdspm->qs_in_channels = hdspm->qs_out_channels =
6713 RAYDAT_QS_CHANNELS;
6714
6715 hdspm->max_channels_in = RAYDAT_SS_CHANNELS;
6716 hdspm->max_channels_out = RAYDAT_SS_CHANNELS;
6717
6718 hdspm->channel_map_in_ss = hdspm->channel_map_out_ss =
6719 channel_map_raydat_ss;
6720 hdspm->channel_map_in_ds = hdspm->channel_map_out_ds =
6721 channel_map_raydat_ds;
6722 hdspm->channel_map_in_qs = hdspm->channel_map_out_qs =
6723 channel_map_raydat_qs;
6724 hdspm->channel_map_in = hdspm->channel_map_out =
6725 channel_map_raydat_ss;
6726
6727 hdspm->port_names_in_ss = hdspm->port_names_out_ss =
6728 texts_ports_raydat_ss;
6729 hdspm->port_names_in_ds = hdspm->port_names_out_ds =
6730 texts_ports_raydat_ds;
6731 hdspm->port_names_in_qs = hdspm->port_names_out_qs =
6732 texts_ports_raydat_qs;
6733
6734
6735 break;
6736
6737 }
6738
6739 /* TCO detection */
6740 switch (hdspm->io_type) {
6741 case AIO:
6742 case RayDAT:
6743 if (hdspm_read(hdspm, HDSPM_statusRegister2) &
6744 HDSPM_s2_tco_detect) {
6745 hdspm->midiPorts++;
7dfec507 6746 hdspm->tco = kzalloc(sizeof(*hdspm->tco), GFP_KERNEL);
da2ea374 6747 if (hdspm->tco)
0dca1793 6748 hdspm_tco_write(hdspm);
da2ea374 6749
e3a471d6 6750 dev_info(card->dev, "AIO/RayDAT TCO module found\n");
0dca1793
AK
6751 } else {
6752 hdspm->tco = NULL;
6753 }
6754 break;
6755
6756 case MADI:
0dc831b9 6757 case AES32:
0dca1793
AK
6758 if (hdspm_read(hdspm, HDSPM_statusRegister) & HDSPM_tco_detect) {
6759 hdspm->midiPorts++;
7dfec507 6760 hdspm->tco = kzalloc(sizeof(*hdspm->tco), GFP_KERNEL);
da2ea374 6761 if (hdspm->tco)
0dca1793 6762 hdspm_tco_write(hdspm);
da2ea374 6763
e3a471d6 6764 dev_info(card->dev, "MADI/AES TCO module found\n");
0dca1793
AK
6765 } else {
6766 hdspm->tco = NULL;
6767 }
6768 break;
6769
6770 default:
6771 hdspm->tco = NULL;
6772 }
6773
6774 /* texts */
6775 switch (hdspm->io_type) {
6776 case AES32:
6777 if (hdspm->tco) {
6778 hdspm->texts_autosync = texts_autosync_aes_tco;
e71b95ad
AK
6779 hdspm->texts_autosync_items =
6780 ARRAY_SIZE(texts_autosync_aes_tco);
0dca1793
AK
6781 } else {
6782 hdspm->texts_autosync = texts_autosync_aes;
e71b95ad
AK
6783 hdspm->texts_autosync_items =
6784 ARRAY_SIZE(texts_autosync_aes);
0dca1793
AK
6785 }
6786 break;
6787
6788 case MADI:
6789 if (hdspm->tco) {
6790 hdspm->texts_autosync = texts_autosync_madi_tco;
6791 hdspm->texts_autosync_items = 4;
6792 } else {
6793 hdspm->texts_autosync = texts_autosync_madi;
6794 hdspm->texts_autosync_items = 3;
6795 }
6796 break;
6797
6798 case MADIface:
6799
6800 break;
6801
6802 case RayDAT:
6803 if (hdspm->tco) {
6804 hdspm->texts_autosync = texts_autosync_raydat_tco;
6805 hdspm->texts_autosync_items = 9;
6806 } else {
6807 hdspm->texts_autosync = texts_autosync_raydat;
6808 hdspm->texts_autosync_items = 8;
6809 }
6810 break;
6811
6812 case AIO:
6813 if (hdspm->tco) {
6814 hdspm->texts_autosync = texts_autosync_aio_tco;
6815 hdspm->texts_autosync_items = 6;
6816 } else {
6817 hdspm->texts_autosync = texts_autosync_aio;
6818 hdspm->texts_autosync_items = 5;
6819 }
6820 break;
6821
6822 }
6823
6824 tasklet_init(&hdspm->midi_tasklet,
6825 hdspm_midi_tasklet, (unsigned long) hdspm);
763f356c 6826
f7de8ba3
AK
6827
6828 if (hdspm->io_type != MADIface) {
6829 hdspm->serial = (hdspm_read(hdspm,
6830 HDSPM_midiStatusIn0)>>8) & 0xFFFFFF;
6831 /* id contains either a user-provided value or the default
6832 * NULL. If it's the default, we're safe to
6833 * fill card->id with the serial number.
6834 *
6835 * If the serial number is 0xFFFFFF, then we're dealing with
6836 * an old PCI revision that comes without a sane number. In
6837 * this case, we don't set card->id to avoid collisions
6838 * when running with multiple cards.
6839 */
da2ea374 6840 if (!id[hdspm->dev] && hdspm->serial != 0xFFFFFF) {
7ad210ac
AB
6841 snprintf(card->id, sizeof(card->id),
6842 "HDSPMx%06x", hdspm->serial);
f7de8ba3
AK
6843 snd_card_set_id(card, card->id);
6844 }
6845 }
6846
e3a471d6 6847 dev_dbg(card->dev, "create alsa devices.\n");
ef5fa1a4
TI
6848 err = snd_hdspm_create_alsa_devices(card, hdspm);
6849 if (err < 0)
763f356c
TI
6850 return err;
6851
6852 snd_hdspm_initialize_midi_flush(hdspm);
6853
6854 return 0;
6855}
6856
0dca1793 6857
98274f07 6858static int snd_hdspm_free(struct hdspm * hdspm)
763f356c
TI
6859{
6860
6861 if (hdspm->port) {
6862
6863 /* stop th audio, and cancel all interrupts */
6864 hdspm->control_register &=
ef5fa1a4 6865 ~(HDSPM_Start | HDSPM_AudioInterruptEnable |
0dca1793
AK
6866 HDSPM_Midi0InterruptEnable | HDSPM_Midi1InterruptEnable |
6867 HDSPM_Midi2InterruptEnable | HDSPM_Midi3InterruptEnable);
763f356c
TI
6868 hdspm_write(hdspm, HDSPM_controlRegister,
6869 hdspm->control_register);
6870 }
6871
6872 if (hdspm->irq >= 0)
6873 free_irq(hdspm->irq, (void *) hdspm);
6874
fc58422a 6875 kfree(hdspm->mixer);
ff6defa6 6876 iounmap(hdspm->iobase);
763f356c 6877
763f356c
TI
6878 if (hdspm->port)
6879 pci_release_regions(hdspm->pci);
6880
6881 pci_disable_device(hdspm->pci);
6882 return 0;
6883}
6884
0dca1793 6885
98274f07 6886static void snd_hdspm_card_free(struct snd_card *card)
763f356c 6887{
ef5fa1a4 6888 struct hdspm *hdspm = card->private_data;
763f356c
TI
6889
6890 if (hdspm)
6891 snd_hdspm_free(hdspm);
6892}
6893
0dca1793 6894
e23e7a14
BP
6895static int snd_hdspm_probe(struct pci_dev *pci,
6896 const struct pci_device_id *pci_id)
763f356c
TI
6897{
6898 static int dev;
98274f07
TI
6899 struct hdspm *hdspm;
6900 struct snd_card *card;
763f356c
TI
6901 int err;
6902
6903 if (dev >= SNDRV_CARDS)
6904 return -ENODEV;
6905 if (!enable[dev]) {
6906 dev++;
6907 return -ENOENT;
6908 }
6909
60c5772b 6910 err = snd_card_new(&pci->dev, index[dev], id[dev],
7dfec507 6911 THIS_MODULE, sizeof(*hdspm), &card);
e58de7ba
TI
6912 if (err < 0)
6913 return err;
763f356c 6914
ef5fa1a4 6915 hdspm = card->private_data;
763f356c
TI
6916 card->private_free = snd_hdspm_card_free;
6917 hdspm->dev = dev;
6918 hdspm->pci = pci;
6919
0dca1793 6920 err = snd_hdspm_create(card, hdspm);
e35e9ddf
ME
6921 if (err < 0)
6922 goto free_card;
763f356c 6923
0dca1793 6924 if (hdspm->io_type != MADIface) {
7ad210ac
AB
6925 snprintf(card->shortname, sizeof(card->shortname), "%s_%x",
6926 hdspm->card_name, hdspm->serial);
6927 snprintf(card->longname, sizeof(card->longname),
6928 "%s S/N 0x%x at 0x%lx, irq %d",
6929 hdspm->card_name, hdspm->serial,
6930 hdspm->port, hdspm->irq);
0dca1793 6931 } else {
7ad210ac
AB
6932 snprintf(card->shortname, sizeof(card->shortname), "%s",
6933 hdspm->card_name);
6934 snprintf(card->longname, sizeof(card->longname),
6935 "%s at 0x%lx, irq %d",
6936 hdspm->card_name, hdspm->port, hdspm->irq);
0dca1793 6937 }
763f356c 6938
ef5fa1a4 6939 err = snd_card_register(card);
e35e9ddf
ME
6940 if (err < 0)
6941 goto free_card;
763f356c
TI
6942
6943 pci_set_drvdata(pci, card);
6944
6945 dev++;
6946 return 0;
e35e9ddf
ME
6947
6948free_card:
6949 snd_card_free(card);
6950 return err;
763f356c
TI
6951}
6952
e23e7a14 6953static void snd_hdspm_remove(struct pci_dev *pci)
763f356c
TI
6954{
6955 snd_card_free(pci_get_drvdata(pci));
763f356c
TI
6956}
6957
e9f66d9b 6958static struct pci_driver hdspm_driver = {
3733e424 6959 .name = KBUILD_MODNAME,
763f356c
TI
6960 .id_table = snd_hdspm_ids,
6961 .probe = snd_hdspm_probe,
e23e7a14 6962 .remove = snd_hdspm_remove,
763f356c
TI
6963};
6964
e9f66d9b 6965module_pci_driver(hdspm_driver);