fedora core 6 1.2949 + vserver 2.2.0
[linux-2.6.git] / sound / pci / ice1712 / ice1712.c
index c56793b..8ba31cf 100644 (file)
@@ -61,8 +61,8 @@
 #include <sound/core.h>
 #include <sound/cs8427.h>
 #include <sound/info.h>
-#include <sound/mpu401.h>
 #include <sound/initval.h>
+#include <sound/tlv.h>
 
 #include <sound/asoundef.h>
 
@@ -107,7 +107,7 @@ module_param_array(dxr_enable, int, NULL, 0444);
 MODULE_PARM_DESC(dxr_enable, "Enable DXR support for Terratec DMX6FIRE.");
 
 
-static struct pci_device_id snd_ice1712_ids[] __devinitdata = {
+static struct pci_device_id snd_ice1712_ids[] = {
        { PCI_VENDOR_ID_ICE, PCI_DEVICE_ID_ICE_1712, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },   /* ICE1712 */
        { 0, }
 };
@@ -420,7 +420,7 @@ static void snd_ice1712_set_input_clock_source(struct snd_ice1712 *ice, int spdi
  *  Interrupt handler
  */
 
-static irqreturn_t snd_ice1712_interrupt(int irq, void *dev_id, struct pt_regs *regs)
+static irqreturn_t snd_ice1712_interrupt(int irq, void *dev_id)
 {
        struct snd_ice1712 *ice = dev_id;
        unsigned char status;
@@ -433,7 +433,7 @@ static irqreturn_t snd_ice1712_interrupt(int irq, void *dev_id, struct pt_regs *
                handled = 1;
                if (status & ICE1712_IRQ_MPU1) {
                        if (ice->rmidi[0])
-                               snd_mpu401_uart_interrupt(irq, ice->rmidi[0]->private_data, regs);
+                               snd_mpu401_uart_interrupt(irq, ice->rmidi[0]->private_data);
                        outb(ICE1712_IRQ_MPU1, ICEREG(ice, IRQSTAT));
                        status &= ~ICE1712_IRQ_MPU1;
                }
@@ -441,7 +441,7 @@ static irqreturn_t snd_ice1712_interrupt(int irq, void *dev_id, struct pt_regs *
                        outb(ICE1712_IRQ_TIMER, ICEREG(ice, IRQSTAT));
                if (status & ICE1712_IRQ_MPU2) {
                        if (ice->rmidi[1])
-                               snd_mpu401_uart_interrupt(irq, ice->rmidi[1]->private_data, regs);
+                               snd_mpu401_uart_interrupt(irq, ice->rmidi[1]->private_data);
                        outb(ICE1712_IRQ_MPU2, ICEREG(ice, IRQSTAT));
                        status &= ~ICE1712_IRQ_MPU2;
                }
@@ -1378,6 +1378,7 @@ static int snd_ice1712_pro_mixer_volume_put(struct snd_kcontrol *kcontrol, struc
        return change;
 }
 
+static DECLARE_TLV_DB_SCALE(db_scale_playback, -14400, 150, 0);
 
 static struct snd_kcontrol_new snd_ice1712_multi_playback_ctrls[] __devinitdata = {
        {
@@ -1391,12 +1392,15 @@ static struct snd_kcontrol_new snd_ice1712_multi_playback_ctrls[] __devinitdata
        },
        {
                .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
+               .access = (SNDRV_CTL_ELEM_ACCESS_READWRITE |
+                          SNDRV_CTL_ELEM_ACCESS_TLV_READ),
                .name = "Multi Playback Volume",
                .info = snd_ice1712_pro_mixer_volume_info,
                .get = snd_ice1712_pro_mixer_volume_get,
                .put = snd_ice1712_pro_mixer_volume_put,
                .private_value = 0,
                .count = 10,
+               .tlv = { .p = db_scale_playback }
        },
 };
 
@@ -1421,11 +1425,14 @@ static struct snd_kcontrol_new snd_ice1712_multi_capture_spdif_switch __devinitd
 
 static struct snd_kcontrol_new snd_ice1712_multi_capture_analog_volume __devinitdata = {
        .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
+       .access = (SNDRV_CTL_ELEM_ACCESS_READWRITE |
+                  SNDRV_CTL_ELEM_ACCESS_TLV_READ),
        .name = "H/W Multi Capture Volume",
        .info = snd_ice1712_pro_mixer_volume_info,
        .get = snd_ice1712_pro_mixer_volume_get,
        .put = snd_ice1712_pro_mixer_volume_put,
        .private_value = 10,
+       .tlv = { .p = db_scale_playback }
 };
 
 static struct snd_kcontrol_new snd_ice1712_multi_capture_spdif_volume __devinitdata = {
@@ -1596,7 +1603,7 @@ static void __devinit snd_ice1712_proc_init(struct snd_ice1712 * ice)
        struct snd_info_entry *entry;
 
        if (! snd_card_proc_new(ice->card, "ice1712", &entry))
-               snd_info_set_text_ops(entry, ice, 1024, snd_ice1712_proc_read);
+               snd_info_set_text_ops(entry, ice, snd_ice1712_proc_read);
 }
 
 /*
@@ -1858,7 +1865,7 @@ static int snd_ice1712_pro_internal_clock_put(struct snd_kcontrol *kcontrol,
 {
        struct snd_ice1712 *ice = snd_kcontrol_chip(kcontrol);
        static unsigned int xrate[13] = {
-               8000, 9600, 11025, 12000, 1600, 22050, 24000,
+               8000, 9600, 11025, 12000, 16000, 22050, 24000,
                32000, 44100, 48000, 64000, 88200, 96000
        };
        unsigned char oval;
@@ -1925,7 +1932,7 @@ static int snd_ice1712_pro_internal_clock_default_get(struct snd_kcontrol *kcont
 {
        int val;
        static unsigned int xrate[13] = {
-               8000, 9600, 11025, 12000, 1600, 22050, 24000,
+               8000, 9600, 11025, 12000, 16000, 22050, 24000,
                32000, 44100, 48000, 64000, 88200, 96000
        };
 
@@ -1942,7 +1949,7 @@ static int snd_ice1712_pro_internal_clock_default_put(struct snd_kcontrol *kcont
                                                      struct snd_ctl_elem_value *ucontrol)
 {
        static unsigned int xrate[13] = {
-               8000, 9600, 11025, 12000, 1600, 22050, 24000,
+               8000, 9600, 11025, 12000, 16000, 22050, 24000,
                32000, 44100, 48000, 64000, 88200, 96000
        };
        unsigned char oval;
@@ -2398,13 +2405,14 @@ static int __devinit snd_ice1712_chip_init(struct snd_ice1712 *ice)
        udelay(200);
        outb(ICE1712_NATIVE, ICEREG(ice, CONTROL));
        udelay(200);
-       if (ice->eeprom.subvendor == ICE1712_SUBDEVICE_DMX6FIRE && !ice->dxr_enable) {
-                /* Limit active ADCs and DACs to 6;  */
-                /* Note: DXR extension not supported */
-               pci_write_config_byte(ice->pci, 0x60, 0x2a);
-       } else {
-               pci_write_config_byte(ice->pci, 0x60, ice->eeprom.data[ICE_EEP1_CODEC]);
-       }
+       if (ice->eeprom.subvendor == ICE1712_SUBDEVICE_DMX6FIRE &&
+           !ice->dxr_enable)
+               /*  Set eeprom value to limit active ADCs and DACs to 6;
+                *  Also disable AC97 as no hardware in standard 6fire card/box
+                *  Note: DXR extensions are not currently supported
+                */
+               ice->eeprom.data[ICE_EEP1_CODEC] = 0x3a;
+       pci_write_config_byte(ice->pci, 0x60, ice->eeprom.data[ICE_EEP1_CODEC]);
        pci_write_config_byte(ice->pci, 0x61, ice->eeprom.data[ICE_EEP1_ACLINK]);
        pci_write_config_byte(ice->pci, 0x62, ice->eeprom.data[ICE_EEP1_I2SID]);
        pci_write_config_byte(ice->pci, 0x63, ice->eeprom.data[ICE_EEP1_SPDIF]);
@@ -2606,7 +2614,7 @@ static int __devinit snd_ice1712_create(struct snd_card *card,
        ice->dmapath_port = pci_resource_start(pci, 2);
        ice->profi_port = pci_resource_start(pci, 3);
 
-       if (request_irq(pci->irq, snd_ice1712_interrupt, SA_INTERRUPT|SA_SHIRQ,
+       if (request_irq(pci->irq, snd_ice1712_interrupt, IRQF_SHARED,
                        "ICE1712", ice)) {
                snd_printk(KERN_ERR "unable to grab IRQ %d\n", pci->irq);
                snd_ice1712_free(ice);
@@ -2737,21 +2745,38 @@ static int __devinit snd_ice1712_probe(struct pci_dev *pci,
 
        if (! c->no_mpu401) {
                if ((err = snd_mpu401_uart_new(card, 0, MPU401_HW_ICE1712,
-                                              ICEREG(ice, MPU1_CTRL), 1,
+                                              ICEREG(ice, MPU1_CTRL),
+                                              (c->mpu401_1_info_flags |
+                                               MPU401_INFO_INTEGRATED),
                                               ice->irq, 0,
                                               &ice->rmidi[0])) < 0) {
                        snd_card_free(card);
                        return err;
                }
-
-               if (ice->eeprom.data[ICE_EEP1_CODEC] & ICE1712_CFG_2xMPU401)
+               if (c->mpu401_1_name)
+                       /*  Prefered name available in card_info */
+                       snprintf(ice->rmidi[0]->name,
+                                sizeof(ice->rmidi[0]->name),
+                                "%s %d", c->mpu401_1_name, card->number);
+
+               if (ice->eeprom.data[ICE_EEP1_CODEC] & ICE1712_CFG_2xMPU401) {
+                       /*  2nd port used  */
                        if ((err = snd_mpu401_uart_new(card, 1, MPU401_HW_ICE1712,
-                                                      ICEREG(ice, MPU2_CTRL), 1,
+                                                      ICEREG(ice, MPU2_CTRL),
+                                                      (c->mpu401_2_info_flags |
+                                                       MPU401_INFO_INTEGRATED),
                                                       ice->irq, 0,
                                                       &ice->rmidi[1])) < 0) {
                                snd_card_free(card);
                                return err;
                        }
+                       if (c->mpu401_2_name)
+                               /*  Prefered name available in card_info */
+                               snprintf(ice->rmidi[1]->name,
+                                        sizeof(ice->rmidi[1]->name),
+                                        "%s %d", c->mpu401_2_name,
+                                        card->number);
+               }
        }
 
        snd_ice1712_set_input_clock_source(ice, 0);