#include <linux/delay.h>
#include <linux/init.h>
#include <linux/interrupt.h>
-#include <linux/pm.h>
#include <linux/slab.h>
#include <linux/ioport.h>
#include <sound/core.h>
{
unsigned long flags;
- down(&chip->open_mutex);
+ mutex_lock(&chip->open_mutex);
if (chip->mode & AD1848_MODE_OPEN) {
- up(&chip->open_mutex);
+ mutex_unlock(&chip->open_mutex);
return -EAGAIN;
}
snd_ad1848_mce_down(chip);
spin_unlock_irqrestore(&chip->reg_lock, flags);
chip->mode = mode;
- up(&chip->open_mutex);
+ mutex_unlock(&chip->open_mutex);
return 0;
}
{
unsigned long flags;
- down(&chip->open_mutex);
+ mutex_lock(&chip->open_mutex);
if (!chip->mode) {
- up(&chip->open_mutex);
+ mutex_unlock(&chip->open_mutex);
return;
}
/* disable IRQ */
spin_unlock_irqrestore(&chip->reg_lock, flags);
chip->mode = 0;
- up(&chip->open_mutex);
+ mutex_unlock(&chip->open_mutex);
}
/*
}
#ifdef CONFIG_PM
-static int snd_ad1848_suspend(struct snd_card *card, pm_message_t state)
+static void snd_ad1848_suspend(struct snd_ad1848 *chip)
{
- struct snd_ad1848 *chip = card->pm_private_data;
-
snd_pcm_suspend_all(chip->pcm);
- /* FIXME: save registers? */
-
if (chip->thinkpad_flag)
snd_ad1848_thinkpad_twiddle(chip, 0);
-
- return 0;
}
-static int snd_ad1848_resume(struct snd_card *card)
+static void snd_ad1848_resume(struct snd_ad1848 *chip)
{
- struct snd_ad1848 *chip = card->pm_private_data;
+ int i;
if (chip->thinkpad_flag)
snd_ad1848_thinkpad_twiddle(chip, 1);
- /* FIXME: restore registers? */
+ /* clear any pendings IRQ */
+ inb(AD1848P(chip, STATUS));
+ outb(0, AD1848P(chip, STATUS));
+ mb();
- return 0;
+ snd_ad1848_mce_down(chip);
+ for (i = 0; i < 16; i++)
+ snd_ad1848_out(chip, i, chip->image[i]);
+ snd_ad1848_mce_up(chip);
+ snd_ad1848_mce_down(chip);
}
#endif /* CONFIG_PM */
if (chip == NULL)
return -ENOMEM;
spin_lock_init(&chip->reg_lock);
- init_MUTEX(&chip->open_mutex);
+ mutex_init(&chip->open_mutex);
chip->card = card;
chip->port = port;
chip->irq = -1;
snd_ad1848_free(chip);
return -EBUSY;
}
- if (request_irq(irq, snd_ad1848_interrupt, SA_INTERRUPT, "AD1848", (void *) chip)) {
+ if (request_irq(irq, snd_ad1848_interrupt, IRQF_DISABLED, "AD1848", (void *) chip)) {
snd_printk(KERN_ERR "ad1848: can't grab IRQ %d\n", irq);
snd_ad1848_free(chip);
return -EBUSY;
chip->thinkpad_flag = 1;
chip->hardware = AD1848_HW_DETECT; /* reset */
snd_ad1848_thinkpad_twiddle(chip, 1);
- snd_card_set_isa_pm_callback(card, snd_ad1848_suspend, snd_ad1848_resume, chip);
}
if (snd_ad1848_probe(chip) < 0) {
return err;
}
+#ifdef CONFIG_PM
+ chip->suspend = snd_ad1848_suspend;
+ chip->resume = snd_ad1848_resume;
+#endif
+
*rchip = chip;
return 0;
}
strlcpy(ctl->id.name, name, sizeof(ctl->id.name));
ctl->id.index = index;
ctl->private_value = value;
- if ((err = snd_ctl_add(chip->card, ctl)) < 0) {
- snd_ctl_free_one(ctl);
+ if ((err = snd_ctl_add(chip->card, ctl)) < 0)
return err;
- }
return 0;
}