~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

TOMOYO Linux Cross Reference
Linux/sound/pci/ice1712/wtm.c

Version: ~ [ linux-6.11.5 ] ~ [ linux-6.10.14 ] ~ [ linux-6.9.12 ] ~ [ linux-6.8.12 ] ~ [ linux-6.7.12 ] ~ [ linux-6.6.58 ] ~ [ linux-6.5.13 ] ~ [ linux-6.4.16 ] ~ [ linux-6.3.13 ] ~ [ linux-6.2.16 ] ~ [ linux-6.1.114 ] ~ [ linux-6.0.19 ] ~ [ linux-5.19.17 ] ~ [ linux-5.18.19 ] ~ [ linux-5.17.15 ] ~ [ linux-5.16.20 ] ~ [ linux-5.15.169 ] ~ [ linux-5.14.21 ] ~ [ linux-5.13.19 ] ~ [ linux-5.12.19 ] ~ [ linux-5.11.22 ] ~ [ linux-5.10.228 ] ~ [ linux-5.9.16 ] ~ [ linux-5.8.18 ] ~ [ linux-5.7.19 ] ~ [ linux-5.6.19 ] ~ [ linux-5.5.19 ] ~ [ linux-5.4.284 ] ~ [ linux-5.3.18 ] ~ [ linux-5.2.21 ] ~ [ linux-5.1.21 ] ~ [ linux-5.0.21 ] ~ [ linux-4.20.17 ] ~ [ linux-4.19.322 ] ~ [ linux-4.18.20 ] ~ [ linux-4.17.19 ] ~ [ linux-4.16.18 ] ~ [ linux-4.15.18 ] ~ [ linux-4.14.336 ] ~ [ linux-4.13.16 ] ~ [ linux-4.12.14 ] ~ [ linux-4.11.12 ] ~ [ linux-4.10.17 ] ~ [ linux-4.9.337 ] ~ [ linux-4.4.302 ] ~ [ linux-3.10.108 ] ~ [ linux-2.6.32.71 ] ~ [ linux-2.6.0 ] ~ [ linux-2.4.37.11 ] ~ [ unix-v6-master ] ~ [ ccs-tools-1.8.9 ] ~ [ policy-sample ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 // SPDX-License-Identifier: GPL-2.0-or-later
  2 /*
  3  *      ALSA driver for ICEnsemble VT1724 (Envy24HT)
  4  *
  5  *      Lowlevel functions for Ego Sys Waveterminal 192M
  6  *
  7  *              Copyright (c) 2006 Guedez Clement <klem.dev@gmail.com>
  8  *              Some functions are taken from the Prodigy192 driver
  9  *              source
 10  */
 11 
 12 
 13 
 14 #include <linux/delay.h>
 15 #include <linux/interrupt.h>
 16 #include <linux/init.h>
 17 #include <sound/core.h>
 18 #include <sound/tlv.h>
 19 #include <linux/slab.h>
 20 
 21 #include "ice1712.h"
 22 #include "envy24ht.h"
 23 #include "wtm.h"
 24 #include "stac946x.h"
 25 
 26 struct wtm_spec {
 27         /* rate change needs atomic mute/unmute of all dacs*/
 28         struct mutex mute_mutex;
 29 };
 30 
 31 
 32 /*
 33  *      2*ADC 6*DAC no1 ringbuffer r/w on i2c bus
 34  */
 35 static inline void stac9460_put(struct snd_ice1712 *ice, int reg,
 36                                                 unsigned char val)
 37 {
 38         snd_vt1724_write_i2c(ice, STAC9460_I2C_ADDR, reg, val);
 39 }
 40 
 41 static inline unsigned char stac9460_get(struct snd_ice1712 *ice, int reg)
 42 {
 43         return snd_vt1724_read_i2c(ice, STAC9460_I2C_ADDR, reg);
 44 }
 45 
 46 /*
 47  *      2*ADC 2*DAC no2 ringbuffer r/w on i2c bus
 48  */
 49 static inline void stac9460_2_put(struct snd_ice1712 *ice, int reg,
 50                                                 unsigned char val)
 51 {
 52         snd_vt1724_write_i2c(ice, STAC9460_2_I2C_ADDR, reg, val);
 53 }
 54 
 55 static inline unsigned char stac9460_2_get(struct snd_ice1712 *ice, int reg)
 56 {
 57         return snd_vt1724_read_i2c(ice, STAC9460_2_I2C_ADDR, reg);
 58 }
 59 
 60 
 61 /*
 62  *      DAC mute control
 63  */
 64 static void stac9460_dac_mute_all(struct snd_ice1712 *ice, unsigned char mute,
 65                                 unsigned short int *change_mask)
 66 {
 67         unsigned char new, old;
 68         int id, idx, change;
 69 
 70         /*stac9460 1*/
 71         for (id = 0; id < 7; id++) {
 72                 if (*change_mask & (0x01 << id)) {
 73                         if (id == 0)
 74                                 idx = STAC946X_MASTER_VOLUME;
 75                         else
 76                                 idx = STAC946X_LF_VOLUME - 1 + id;
 77                         old = stac9460_get(ice, idx);
 78                         new = (~mute << 7 & 0x80) | (old & ~0x80);
 79                         change = (new != old);
 80                         if (change) {
 81                                 stac9460_put(ice, idx, new);
 82                                 *change_mask = *change_mask | (0x01 << id);
 83                         } else {
 84                                 *change_mask = *change_mask & ~(0x01 << id);
 85                         }
 86                 }
 87         }
 88 
 89         /*stac9460 2*/
 90         for (id = 0; id < 3; id++) {
 91                 if (*change_mask & (0x01 << (id + 7))) {
 92                         if (id == 0)
 93                                 idx = STAC946X_MASTER_VOLUME;
 94                         else
 95                                 idx = STAC946X_LF_VOLUME - 1 + id;
 96                         old = stac9460_2_get(ice, idx);
 97                         new = (~mute << 7 & 0x80) | (old & ~0x80);
 98                         change = (new != old);
 99                         if (change) {
100                                 stac9460_2_put(ice, idx, new);
101                                 *change_mask = *change_mask | (0x01 << id);
102                         } else {
103                                 *change_mask = *change_mask & ~(0x01 << id);
104                         }
105                 }
106         }
107 }
108 
109 
110 
111 #define stac9460_dac_mute_info          snd_ctl_boolean_mono_info
112 
113 static int stac9460_dac_mute_get(struct snd_kcontrol *kcontrol,
114                                 struct snd_ctl_elem_value *ucontrol)
115 {
116         struct snd_ice1712 *ice = snd_kcontrol_chip(kcontrol);
117         struct wtm_spec *spec = ice->spec;
118         unsigned char val;
119         int idx, id;
120 
121         mutex_lock(&spec->mute_mutex);
122 
123         if (kcontrol->private_value) {
124                 idx = STAC946X_MASTER_VOLUME;
125                 id = 0;
126         } else {
127                 id = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
128                 idx = id + STAC946X_LF_VOLUME;
129         }
130         if (id < 6)
131                 val = stac9460_get(ice, idx);
132         else
133                 val = stac9460_2_get(ice, idx - 6);
134         ucontrol->value.integer.value[0] = (~val >> 7) & 0x1;
135 
136         mutex_unlock(&spec->mute_mutex);
137         return 0;
138 }
139 
140 static int stac9460_dac_mute_put(struct snd_kcontrol *kcontrol,
141                                 struct snd_ctl_elem_value *ucontrol)
142 {
143         struct snd_ice1712 *ice = snd_kcontrol_chip(kcontrol);
144         unsigned char new, old;
145         int id, idx;
146         int change;
147 
148         if (kcontrol->private_value) {
149                 idx = STAC946X_MASTER_VOLUME;
150                 old = stac9460_get(ice, idx);
151                 new = (~ucontrol->value.integer.value[0] << 7 & 0x80) |
152                                                         (old & ~0x80);
153                 change = (new != old);
154                 if (change) {
155                         stac9460_put(ice, idx, new);
156                         stac9460_2_put(ice, idx, new);
157                 }
158         } else {
159                 id = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
160                 idx = id + STAC946X_LF_VOLUME;
161                 if (id < 6)
162                         old = stac9460_get(ice, idx);
163                 else
164                         old = stac9460_2_get(ice, idx - 6);
165                 new = (~ucontrol->value.integer.value[0] << 7 & 0x80) |
166                                                         (old & ~0x80);
167                 change = (new != old);
168                 if (change) {
169                         if (id < 6)
170                                 stac9460_put(ice, idx, new);
171                         else
172                                 stac9460_2_put(ice, idx - 6, new);
173                 }
174         }
175         return change;
176 }
177 
178 /*
179  *      DAC volume attenuation mixer control
180  */
181 static int stac9460_dac_vol_info(struct snd_kcontrol *kcontrol,
182                                 struct snd_ctl_elem_info *uinfo)
183 {
184         uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
185         uinfo->count = 1;
186         uinfo->value.integer.min = 0;                   /* mute */
187         uinfo->value.integer.max = 0x7f;                /* 0dB */
188         return 0;
189 }
190 
191 static int stac9460_dac_vol_get(struct snd_kcontrol *kcontrol,
192                                 struct snd_ctl_elem_value *ucontrol)
193 {
194         struct snd_ice1712 *ice = snd_kcontrol_chip(kcontrol);
195         int idx, id;
196         unsigned char vol;
197 
198         if (kcontrol->private_value) {
199                 idx = STAC946X_MASTER_VOLUME;
200                 id = 0;
201         } else {
202                 id = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
203                 idx = id + STAC946X_LF_VOLUME;
204         }
205         if (id < 6)
206                 vol = stac9460_get(ice, idx) & 0x7f;
207         else
208                 vol = stac9460_2_get(ice, idx - 6) & 0x7f;
209         ucontrol->value.integer.value[0] = 0x7f - vol;
210         return 0;
211 }
212 
213 static int stac9460_dac_vol_put(struct snd_kcontrol *kcontrol,
214                                 struct snd_ctl_elem_value *ucontrol)
215 {
216         struct snd_ice1712 *ice = snd_kcontrol_chip(kcontrol);
217         int idx, id;
218         unsigned char tmp, ovol, nvol;
219         int change;
220 
221         if (kcontrol->private_value) {
222                 idx = STAC946X_MASTER_VOLUME;
223                 nvol = ucontrol->value.integer.value[0] & 0x7f;
224                 tmp = stac9460_get(ice, idx);
225                 ovol = 0x7f - (tmp & 0x7f);
226                 change = (ovol != nvol);
227                 if (change) {
228                         stac9460_put(ice, idx, (0x7f - nvol) | (tmp & 0x80));
229                         stac9460_2_put(ice, idx, (0x7f - nvol) | (tmp & 0x80));
230                 }
231         } else {
232                 id = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
233                 idx = id + STAC946X_LF_VOLUME;
234                 nvol = ucontrol->value.integer.value[0] & 0x7f;
235                 if (id < 6)
236                         tmp = stac9460_get(ice, idx);
237                 else
238                         tmp = stac9460_2_get(ice, idx - 6);
239                 ovol = 0x7f - (tmp & 0x7f);
240                 change = (ovol != nvol);
241                 if (change) {
242                         if (id < 6)
243                                 stac9460_put(ice, idx, (0x7f - nvol) |
244                                                         (tmp & 0x80));
245                         else
246                                 stac9460_2_put(ice, idx-6, (0x7f - nvol) |
247                                                         (tmp & 0x80));
248                 }
249         }
250         return change;
251 }
252 
253 /*
254  * ADC mute control
255  */
256 #define stac9460_adc_mute_info          snd_ctl_boolean_stereo_info
257 
258 static int stac9460_adc_mute_get(struct snd_kcontrol *kcontrol,
259                                 struct snd_ctl_elem_value *ucontrol)
260 {
261         struct snd_ice1712 *ice = snd_kcontrol_chip(kcontrol);
262         unsigned char val;
263         int i, id;
264 
265         id = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
266         if (id == 0) {
267                 for (i = 0; i < 2; ++i) {
268                         val = stac9460_get(ice, STAC946X_MIC_L_VOLUME + i);
269                         ucontrol->value.integer.value[i] = ~val>>7 & 0x1;
270                 }
271         } else {
272                 for (i = 0; i < 2; ++i) {
273                         val = stac9460_2_get(ice, STAC946X_MIC_L_VOLUME + i);
274                         ucontrol->value.integer.value[i] = ~val>>7 & 0x1;
275                 }
276         }
277         return 0;
278 }
279 
280 static int stac9460_adc_mute_put(struct snd_kcontrol *kcontrol,
281                                 struct snd_ctl_elem_value *ucontrol)
282 {
283         struct snd_ice1712 *ice = snd_kcontrol_chip(kcontrol);
284         unsigned char new, old;
285         int i, reg, id;
286         int change;
287 
288         id = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
289         if (id == 0) {
290                 for (i = 0; i < 2; ++i) {
291                         reg = STAC946X_MIC_L_VOLUME + i;
292                         old = stac9460_get(ice, reg);
293                         new = (~ucontrol->value.integer.value[i]<<7&0x80) |
294                                                                 (old&~0x80);
295                         change = (new != old);
296                         if (change)
297                                 stac9460_put(ice, reg, new);
298                 }
299         } else {
300                 for (i = 0; i < 2; ++i) {
301                         reg = STAC946X_MIC_L_VOLUME + i;
302                         old = stac9460_2_get(ice, reg);
303                         new = (~ucontrol->value.integer.value[i]<<7&0x80) |
304                                                                 (old&~0x80);
305                         change = (new != old);
306                         if (change)
307                                 stac9460_2_put(ice, reg, new);
308                 }
309         }
310         return change;
311 }
312 
313 /*
314  *ADC gain mixer control
315  */
316 static int stac9460_adc_vol_info(struct snd_kcontrol *kcontrol,
317                                 struct snd_ctl_elem_info *uinfo)
318 {
319         uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
320         uinfo->count = 2;
321         uinfo->value.integer.min = 0;           /* 0dB */
322         uinfo->value.integer.max = 0x0f;        /* 22.5dB */
323         return 0;
324 }
325 
326 static int stac9460_adc_vol_get(struct snd_kcontrol *kcontrol,
327                                 struct snd_ctl_elem_value *ucontrol)
328 {
329         struct snd_ice1712 *ice = snd_kcontrol_chip(kcontrol);
330         int i, reg, id;
331         unsigned char vol;
332 
333         id = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
334         if (id == 0) {
335                 for (i = 0; i < 2; ++i) {
336                         reg = STAC946X_MIC_L_VOLUME + i;
337                         vol = stac9460_get(ice, reg) & 0x0f;
338                         ucontrol->value.integer.value[i] = 0x0f - vol;
339                 }
340         } else {
341                 for (i = 0; i < 2; ++i) {
342                         reg = STAC946X_MIC_L_VOLUME + i;
343                         vol = stac9460_2_get(ice, reg) & 0x0f;
344                         ucontrol->value.integer.value[i] = 0x0f - vol;
345                 }
346         }
347         return 0;
348 }
349 
350 static int stac9460_adc_vol_put(struct snd_kcontrol *kcontrol,
351                                 struct snd_ctl_elem_value *ucontrol)
352 {
353         struct snd_ice1712 *ice = snd_kcontrol_chip(kcontrol);
354         int i, reg, id;
355         unsigned char ovol, nvol;
356         int change;
357 
358         id = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
359         if (id == 0) {
360                 for (i = 0; i < 2; ++i) {
361                         reg = STAC946X_MIC_L_VOLUME + i;
362                         nvol = ucontrol->value.integer.value[i] & 0x0f;
363                         ovol = 0x0f - stac9460_get(ice, reg);
364                         change = ((ovol & 0x0f) != nvol);
365                         if (change)
366                                 stac9460_put(ice, reg, (0x0f - nvol) |
367                                                         (ovol & ~0x0f));
368                 }
369         } else {
370                 for (i = 0; i < 2; ++i) {
371                         reg = STAC946X_MIC_L_VOLUME + i;
372                         nvol = ucontrol->value.integer.value[i] & 0x0f;
373                         ovol = 0x0f - stac9460_2_get(ice, reg);
374                         change = ((ovol & 0x0f) != nvol);
375                         if (change)
376                                 stac9460_2_put(ice, reg, (0x0f - nvol) |
377                                                         (ovol & ~0x0f));
378                 }
379         }
380         return change;
381 }
382 
383 /*
384  * MIC / LINE switch fonction
385  */
386 static int stac9460_mic_sw_info(struct snd_kcontrol *kcontrol,
387                                 struct snd_ctl_elem_info *uinfo)
388 {
389         static const char * const texts[2] = { "Line In", "Mic" };
390 
391         return snd_ctl_enum_info(uinfo, 1, 2, texts);
392 }
393 
394 
395 static int stac9460_mic_sw_get(struct snd_kcontrol *kcontrol,
396                                 struct snd_ctl_elem_value *ucontrol)
397 {
398         struct snd_ice1712 *ice = snd_kcontrol_chip(kcontrol);
399         unsigned char val;
400         int id;
401 
402         id = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
403         if (id == 0)
404                 val = stac9460_get(ice, STAC946X_GENERAL_PURPOSE);
405         else
406                 val = stac9460_2_get(ice, STAC946X_GENERAL_PURPOSE);
407         ucontrol->value.enumerated.item[0] = (val >> 7) & 0x1;
408         return 0;
409 }
410 
411 static int stac9460_mic_sw_put(struct snd_kcontrol *kcontrol,
412                                 struct snd_ctl_elem_value *ucontrol)
413 {
414         struct snd_ice1712 *ice = snd_kcontrol_chip(kcontrol);
415         unsigned char new, old;
416         int change, id;
417 
418         id = snd_ctl_get_ioffidx(kcontrol, &ucontrol->id);
419         if (id == 0)
420                 old = stac9460_get(ice, STAC946X_GENERAL_PURPOSE);
421         else
422                 old = stac9460_2_get(ice, STAC946X_GENERAL_PURPOSE);
423         new = (ucontrol->value.enumerated.item[0] << 7 & 0x80) | (old & ~0x80);
424         change = (new != old);
425         if (change) {
426                 if (id == 0)
427                         stac9460_put(ice, STAC946X_GENERAL_PURPOSE, new);
428                 else
429                         stac9460_2_put(ice, STAC946X_GENERAL_PURPOSE, new);
430         }
431         return change;
432 }
433 
434 
435 /*
436  * Handler for setting correct codec rate - called when rate change is detected
437  */
438 static void stac9460_set_rate_val(struct snd_ice1712 *ice, unsigned int rate)
439 {
440         unsigned char old, new;
441         unsigned short int changed;
442         struct wtm_spec *spec = ice->spec;
443 
444         if (rate == 0)  /* no hint - S/PDIF input is master, simply return */
445                 return;
446         else if (rate <= 48000)
447                 new = 0x08;     /* 256x, base rate mode */
448         else if (rate <= 96000)
449                 new = 0x11;     /* 256x, mid rate mode */
450         else
451                 new = 0x12;     /* 128x, high rate mode */
452 
453         old = stac9460_get(ice, STAC946X_MASTER_CLOCKING);
454         if (old == new)
455                 return;
456         /* change detected, setting master clock, muting first */
457         /* due to possible conflicts with mute controls - mutexing */
458         mutex_lock(&spec->mute_mutex);
459         /* we have to remember current mute status for each DAC */
460         changed = 0xFFFF;
461         stac9460_dac_mute_all(ice, 0, &changed);
462         /*printk(KERN_DEBUG "Rate change: %d, new MC: 0x%02x\n", rate, new);*/
463         stac9460_put(ice, STAC946X_MASTER_CLOCKING, new);
464         stac9460_2_put(ice, STAC946X_MASTER_CLOCKING, new);
465         udelay(10);
466         /* unmuting - only originally unmuted dacs -
467         * i.e. those changed when muting */
468         stac9460_dac_mute_all(ice, 1, &changed);
469         mutex_unlock(&spec->mute_mutex);
470 }
471 
472 
473 /*Limits value in dB for fader*/
474 static const DECLARE_TLV_DB_SCALE(db_scale_dac, -19125, 75, 0);
475 static const DECLARE_TLV_DB_SCALE(db_scale_adc, 0, 150, 0);
476 
477 /*
478  * Control tabs
479  */
480 static const struct snd_kcontrol_new stac9640_controls[] = {
481         {
482                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
483                 .access = (SNDRV_CTL_ELEM_ACCESS_READWRITE |
484                             SNDRV_CTL_ELEM_ACCESS_TLV_READ),
485                 .name = "Master Playback Switch",
486                 .info = stac9460_dac_mute_info,
487                 .get = stac9460_dac_mute_get,
488                 .put = stac9460_dac_mute_put,
489                 .private_value = 1,
490                 .tlv = { .p = db_scale_dac }
491         },
492         {
493                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
494                 .name = "Master Playback Volume",
495                 .info = stac9460_dac_vol_info,
496                 .get = stac9460_dac_vol_get,
497                 .put = stac9460_dac_vol_put,
498                 .private_value = 1,
499         },
500         {
501                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
502                 .name = "MIC/Line Input Enum",
503                 .count = 2,
504                 .info = stac9460_mic_sw_info,
505                 .get = stac9460_mic_sw_get,
506                 .put = stac9460_mic_sw_put,
507 
508         },
509         {
510                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
511                 .name = "DAC Switch",
512                 .count = 8,
513                 .info = stac9460_dac_mute_info,
514                 .get = stac9460_dac_mute_get,
515                 .put = stac9460_dac_mute_put,
516         },
517         {
518                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
519                 .access = (SNDRV_CTL_ELEM_ACCESS_READWRITE |
520                             SNDRV_CTL_ELEM_ACCESS_TLV_READ),
521 
522                 .name = "DAC Volume",
523                 .count = 8,
524                 .info = stac9460_dac_vol_info,
525                 .get = stac9460_dac_vol_get,
526                 .put = stac9460_dac_vol_put,
527                 .tlv = { .p = db_scale_dac }
528         },
529         {
530                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
531                 .name = "ADC Switch",
532                 .count = 2,
533                 .info = stac9460_adc_mute_info,
534                 .get = stac9460_adc_mute_get,
535                 .put = stac9460_adc_mute_put,
536         },
537         {
538                 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
539                 .access = (SNDRV_CTL_ELEM_ACCESS_READWRITE |
540                             SNDRV_CTL_ELEM_ACCESS_TLV_READ),
541 
542                 .name = "ADC Volume",
543                 .count = 2,
544                 .info = stac9460_adc_vol_info,
545                 .get = stac9460_adc_vol_get,
546                 .put = stac9460_adc_vol_put,
547                 .tlv = { .p = db_scale_adc }
548         }
549 };
550 
551 
552 
553 /*INIT*/
554 static int wtm_add_controls(struct snd_ice1712 *ice)
555 {
556         unsigned int i;
557         int err;
558 
559         for (i = 0; i < ARRAY_SIZE(stac9640_controls); i++) {
560                 err = snd_ctl_add(ice->card,
561                                 snd_ctl_new1(&stac9640_controls[i], ice));
562                 if (err < 0)
563                         return err;
564         }
565         return 0;
566 }
567 
568 static int wtm_init(struct snd_ice1712 *ice)
569 {
570         static const unsigned short stac_inits_wtm[] = {
571                 STAC946X_RESET, 0,
572                 STAC946X_MASTER_CLOCKING, 0x11,
573                 (unsigned short)-1
574         };
575         const unsigned short *p;
576         struct wtm_spec *spec;
577 
578         /*WTM 192M*/
579         ice->num_total_dacs = 8;
580         ice->num_total_adcs = 4;
581         ice->force_rdma1 = 1;
582 
583         /*init mutex for dac mute conflict*/
584         spec = kzalloc(sizeof(*spec), GFP_KERNEL);
585         if (!spec)
586                 return -ENOMEM;
587         ice->spec = spec;
588         mutex_init(&spec->mute_mutex);
589 
590 
591         /*initialize codec*/
592         p = stac_inits_wtm;
593         for (; *p != (unsigned short)-1; p += 2) {
594                 stac9460_put(ice, p[0], p[1]);
595                 stac9460_2_put(ice, p[0], p[1]);
596         }
597         ice->gpio.set_pro_rate = stac9460_set_rate_val;
598         return 0;
599 }
600 
601 
602 static const unsigned char wtm_eeprom[] = {
603         [ICE_EEP2_SYSCONF]      = 0x67, /*SYSCONF: clock 192KHz, mpu401,
604                                                         4ADC, 8DAC */
605         [ICE_EEP2_ACLINK]       = 0x80, /* ACLINK : I2S */
606         [ICE_EEP2_I2S]          = 0xf8, /* I2S: vol; 96k, 24bit, 192k */
607         [ICE_EEP2_SPDIF]        = 0xc1, /*SPDIF: out-en, spidf ext out*/
608         [ICE_EEP2_GPIO_DIR]     = 0x9f,
609         [ICE_EEP2_GPIO_DIR1]    = 0xff,
610         [ICE_EEP2_GPIO_DIR2]    = 0x7f,
611         [ICE_EEP2_GPIO_MASK]    = 0x9f,
612         [ICE_EEP2_GPIO_MASK1]   = 0xff,
613         [ICE_EEP2_GPIO_MASK2]   = 0x7f,
614         [ICE_EEP2_GPIO_STATE]   = 0x16,
615         [ICE_EEP2_GPIO_STATE1]  = 0x80,
616         [ICE_EEP2_GPIO_STATE2]  = 0x00,
617 };
618 
619 
620 /*entry point*/
621 struct snd_ice1712_card_info snd_vt1724_wtm_cards[] = {
622         {
623                 .subvendor = VT1724_SUBDEVICE_WTM,
624                 .name = "ESI Waveterminal 192M",
625                 .model = "WT192M",
626                 .chip_init = wtm_init,
627                 .build_controls = wtm_add_controls,
628                 .eeprom_size = sizeof(wtm_eeprom),
629                 .eeprom_data = wtm_eeprom,
630         },
631         {} /*terminator*/
632 };
633 

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

kernel.org | git.kernel.org | LWN.net | Project Home | SVN repository | Mail admin

Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.

sflogo.php