]> err.no Git - linux-2.6/blobdiff - sound/pci/cs4281.c
[ALSA] continue on IS_ERR from platform device registration
[linux-2.6] / sound / pci / cs4281.c
index 116cdc1c55288d1183f44706906d3957ab81a206..ac4e73f69c1d3de12e38b7036ecd00307f47c505 100644 (file)
@@ -1046,7 +1046,7 @@ static int snd_cs4281_put_volume(struct snd_kcontrol *kcontrol,
                snd_cs4281_pokeBA0(chip, regL, volL);
                change = 1;
        }
-       if (ucontrol->value.integer.value[0] != volL) {
+       if (ucontrol->value.integer.value[1] != volR) {
                volR = CS_VOL_MASK - (ucontrol->value.integer.value[1] & CS_VOL_MASK);
                snd_cs4281_pokeBA0(chip, regR, volR);
                change = 1;
@@ -1339,10 +1339,6 @@ static int snd_cs4281_dev_free(struct snd_device *device)
 }
 
 static int snd_cs4281_chip_init(struct cs4281 *chip); /* defined below */
-#ifdef CONFIG_PM
-static int cs4281_suspend(struct snd_card *card, pm_message_t state);
-static int cs4281_resume(struct snd_card *card);
-#endif
 
 static int __devinit snd_cs4281_create(struct snd_card *card,
                                       struct pci_dev *pci,
@@ -1411,8 +1407,6 @@ static int __devinit snd_cs4281_create(struct snd_card *card,
 
        snd_cs4281_proc_init(chip);
 
-       snd_card_set_pm_callback(card, cs4281_suspend, cs4281_resume, chip);
-
        snd_card_set_dev(card, &pci->dev);
 
        *rchip = chip;
@@ -1422,7 +1416,7 @@ static int __devinit snd_cs4281_create(struct snd_card *card,
 static int snd_cs4281_chip_init(struct cs4281 *chip)
 {
        unsigned int tmp;
-       int timeout;
+       unsigned long end_time;
        int retry_count = 2;
 
        /* Having EPPMC.FPDN=1 prevent proper chip initialisation */
@@ -1502,7 +1496,7 @@ static int snd_cs4281_chip_init(struct cs4281 *chip)
        /*
         * Wait for the DLL ready signal from the clock logic.
         */
-       timeout = 100;
+       end_time = jiffies + HZ;
        do {
                /*
                 *  Read the AC97 status register to see if we've seen a CODEC
@@ -1510,8 +1504,8 @@ static int snd_cs4281_chip_init(struct cs4281 *chip)
                 */
                if (snd_cs4281_peekBA0(chip, BA0_CLKCR1) & BA0_CLKCR1_DLLRDY)
                        goto __ok0;
-               msleep(1);
-       } while (timeout-- > 0);
+               schedule_timeout_uninterruptible(1);
+       } while (time_after_eq(end_time, jiffies));
 
        snd_printk(KERN_ERR "DLLRDY not seen\n");
        return -EIO;
@@ -1528,7 +1522,7 @@ static int snd_cs4281_chip_init(struct cs4281 *chip)
        /*
         * Wait for the codec ready signal from the AC97 codec.
         */
-       timeout = 100;
+       end_time = jiffies + HZ;
        do {
                /*
                 *  Read the AC97 status register to see if we've seen a CODEC
@@ -1536,20 +1530,20 @@ static int snd_cs4281_chip_init(struct cs4281 *chip)
                 */
                if (snd_cs4281_peekBA0(chip, BA0_ACSTS) & BA0_ACSTS_CRDY)
                        goto __ok1;
-               msleep(1);
-       } while (timeout-- > 0);
+               schedule_timeout_uninterruptible(1);
+       } while (time_after_eq(end_time, jiffies));
 
        snd_printk(KERN_ERR "never read codec ready from AC'97 (0x%x)\n", snd_cs4281_peekBA0(chip, BA0_ACSTS));
        return -EIO;
 
       __ok1:
        if (chip->dual_codec) {
-               timeout = 100;
+               end_time = jiffies + HZ;
                do {
                        if (snd_cs4281_peekBA0(chip, BA0_ACSTS2) & BA0_ACSTS_CRDY)
                                goto __codec2_ok;
-                       msleep(1);
-               } while (timeout-- > 0);
+                       schedule_timeout_uninterruptible(1);
+               } while (time_after_eq(end_time, jiffies));
                snd_printk(KERN_INFO "secondary codec doesn't respond. disable it...\n");
                chip->dual_codec = 0;
        __codec2_ok: ;
@@ -1567,7 +1561,7 @@ static int snd_cs4281_chip_init(struct cs4281 *chip)
         *  the codec is pumping ADC data across the AC-link.
         */
 
-       timeout = 100;
+       end_time = jiffies + HZ;
        do {
                /*
                 *  Read the input slot valid register and see if input slots 3
@@ -1575,8 +1569,8 @@ static int snd_cs4281_chip_init(struct cs4281 *chip)
                 */
                 if ((snd_cs4281_peekBA0(chip, BA0_ACISV) & (BA0_ACISV_SLV(3) | BA0_ACISV_SLV(4))) == (BA0_ACISV_SLV(3) | BA0_ACISV_SLV(4)))
                         goto __ok2;
-               msleep(1);
-       } while (timeout-- > 0);
+               schedule_timeout_uninterruptible(1);
+       } while (time_after_eq(end_time, jiffies));
 
        if (--retry_count > 0)
                goto __retry;
@@ -1936,6 +1930,7 @@ static int __devinit snd_cs4281_probe(struct pci_dev *pci,
                snd_card_free(card);
                return err;
        }
+       card->private_data = chip;
 
        if ((err = snd_cs4281_mixer(chip)) < 0) {
                snd_card_free(card);
@@ -2007,18 +2002,18 @@ static int saved_regs[SUSPEND_REGISTERS] = {
 
 #define CLKCR1_CKRA                             0x00010000L
 
-static int cs4281_suspend(struct snd_card *card, pm_message_t state)
+static int cs4281_suspend(struct pci_dev *pci, pm_message_t state)
 {
-       struct cs4281 *chip = card->pm_private_data;
+       struct snd_card *card = pci_get_drvdata(pci);
+       struct cs4281 *chip = card->private_data;
        u32 ulCLK;
        unsigned int i;
 
+       snd_power_change_state(card, SNDRV_CTL_POWER_D3hot);
        snd_pcm_suspend_all(chip->pcm);
 
-       if (chip->ac97)
-               snd_ac97_suspend(chip->ac97);
-       if (chip->ac97_secondary)
-               snd_ac97_suspend(chip->ac97_secondary);
+       snd_ac97_suspend(chip->ac97);
+       snd_ac97_suspend(chip->ac97_secondary);
 
        ulCLK = snd_cs4281_peekBA0(chip, BA0_CLKCR1);
        ulCLK |= CLKCR1_CKRA;
@@ -2048,18 +2043,21 @@ static int cs4281_suspend(struct snd_card *card, pm_message_t state)
        ulCLK &= ~CLKCR1_CKRA;
        snd_cs4281_pokeBA0(chip, BA0_CLKCR1, ulCLK);
 
-       pci_disable_device(chip->pci);
+       pci_disable_device(pci);
+       pci_save_state(pci);
        return 0;
 }
 
-static int cs4281_resume(struct snd_card *card)
+static int cs4281_resume(struct pci_dev *pci)
 {
-       struct cs4281 *chip = card->pm_private_data;
+       struct snd_card *card = pci_get_drvdata(pci);
+       struct cs4281 *chip = card->private_data;
        unsigned int i;
        u32 ulCLK;
 
-       pci_enable_device(chip->pci);
-       pci_set_master(chip->pci);
+       pci_restore_state(pci);
+       pci_enable_device(pci);
+       pci_set_master(pci);
 
        ulCLK = snd_cs4281_peekBA0(chip, BA0_CLKCR1);
        ulCLK |= CLKCR1_CKRA;
@@ -2072,15 +2070,14 @@ static int cs4281_resume(struct snd_card *card)
                if (saved_regs[i])
                        snd_cs4281_pokeBA0(chip, saved_regs[i], chip->suspend_regs[i]);
 
-       if (chip->ac97)
-               snd_ac97_resume(chip->ac97);
-       if (chip->ac97_secondary)
-               snd_ac97_resume(chip->ac97_secondary);
+       snd_ac97_resume(chip->ac97);
+       snd_ac97_resume(chip->ac97_secondary);
 
        ulCLK = snd_cs4281_peekBA0(chip, BA0_CLKCR1);
        ulCLK &= ~CLKCR1_CKRA;
        snd_cs4281_pokeBA0(chip, BA0_CLKCR1, ulCLK);
 
+       snd_power_change_state(card, SNDRV_CTL_POWER_D0);
        return 0;
 }
 #endif /* CONFIG_PM */
@@ -2090,7 +2087,10 @@ static struct pci_driver driver = {
        .id_table = snd_cs4281_ids,
        .probe = snd_cs4281_probe,
        .remove = __devexit_p(snd_cs4281_remove),
-       SND_PCI_PM_CALLBACKS
+#ifdef CONFIG_PM
+       .suspend = cs4281_suspend,
+       .resume = cs4281_resume,
+#endif
 };
        
 static int __init alsa_card_cs4281_init(void)