summaryrefslogtreecommitdiff
path: root/sound/isa/sscape.c
diff options
context:
space:
mode:
Diffstat (limited to 'sound/isa/sscape.c')
-rw-r--r--sound/isa/sscape.c290
1 files changed, 134 insertions, 156 deletions
diff --git a/sound/isa/sscape.c b/sound/isa/sscape.c
index 0bc0025f7c19..a31ca75774a6 100644
--- a/sound/isa/sscape.c
+++ b/sound/isa/sscape.c
@@ -138,6 +138,7 @@ struct soundscape {
struct snd_wss *chip;
unsigned char midi_vol;
+ struct device *dev;
};
#define INVALID_IRQ ((unsigned)-1)
@@ -161,9 +162,9 @@ static struct snd_dma_buffer *get_dmabuf(struct soundscape *s,
if (snd_dma_alloc_pages_fallback(SNDRV_DMA_TYPE_DEV,
s->chip->card->dev,
size, buf) < 0) {
- snd_printk(KERN_ERR "sscape: Failed to allocate "
- "%lu bytes for DMA\n",
- size);
+ dev_err(s->dev,
+ "sscape: Failed to allocate %lu bytes for DMA\n",
+ size);
return NULL;
}
}
@@ -199,11 +200,8 @@ static inline void sscape_write_unsafe(unsigned io_base, enum GA_REG reg,
static void sscape_write(struct soundscape *s, enum GA_REG reg,
unsigned char val)
{
- unsigned long flags;
-
- spin_lock_irqsave(&s->lock, flags);
+ guard(spinlock_irqsave)(&s->lock);
sscape_write_unsafe(s->io_base, reg, val);
- spin_unlock_irqrestore(&s->lock, flags);
}
/*
@@ -366,12 +364,11 @@ static int obp_startup_ack(struct soundscape *s, unsigned timeout)
unsigned long end_time = jiffies + msecs_to_jiffies(timeout);
do {
- unsigned long flags;
int x;
- spin_lock_irqsave(&s->lock, flags);
- x = host_read_unsafe(s->io_base);
- spin_unlock_irqrestore(&s->lock, flags);
+ scoped_guard(spinlock_irqsave, &s->lock) {
+ x = host_read_unsafe(s->io_base);
+ }
if (x == 0xfe || x == 0xff)
return 1;
@@ -393,12 +390,11 @@ static int host_startup_ack(struct soundscape *s, unsigned timeout)
unsigned long end_time = jiffies + msecs_to_jiffies(timeout);
do {
- unsigned long flags;
int x;
- spin_lock_irqsave(&s->lock, flags);
- x = host_read_unsafe(s->io_base);
- spin_unlock_irqrestore(&s->lock, flags);
+ scoped_guard(spinlock_irqsave, &s->lock) {
+ x = host_read_unsafe(s->io_base);
+ }
if (x == 0xfe)
return 1;
@@ -414,7 +410,6 @@ static int host_startup_ack(struct soundscape *s, unsigned timeout)
static int upload_dma_data(struct soundscape *s, const unsigned char *data,
size_t size)
{
- unsigned long flags;
struct snd_dma_buffer dma;
int ret;
unsigned char val;
@@ -422,63 +417,57 @@ static int upload_dma_data(struct soundscape *s, const unsigned char *data,
if (!get_dmabuf(s, &dma, PAGE_ALIGN(32 * 1024)))
return -ENOMEM;
- spin_lock_irqsave(&s->lock, flags);
-
- /*
- * Reset the board ...
- */
- val = sscape_read_unsafe(s->io_base, GA_HMCTL_REG);
- sscape_write_unsafe(s->io_base, GA_HMCTL_REG, val & 0x3f);
-
- /*
- * Enable the DMA channels and configure them ...
- */
- val = (s->chip->dma1 << 4) | DMA_8BIT;
- sscape_write_unsafe(s->io_base, GA_DMAA_REG, val);
- sscape_write_unsafe(s->io_base, GA_DMAB_REG, 0x20);
-
- /*
- * Take the board out of reset ...
- */
- val = sscape_read_unsafe(s->io_base, GA_HMCTL_REG);
- sscape_write_unsafe(s->io_base, GA_HMCTL_REG, val | 0x80);
+ scoped_guard(spinlock_irqsave, &s->lock) {
- /*
- * Upload the firmware to the SoundScape
- * board through the DMA channel ...
- */
- while (size != 0) {
- unsigned long len;
+ /*
+ * Reset the board ...
+ */
+ val = sscape_read_unsafe(s->io_base, GA_HMCTL_REG);
+ sscape_write_unsafe(s->io_base, GA_HMCTL_REG, val & 0x3f);
- len = min(size, dma.bytes);
- memcpy(dma.area, data, len);
- data += len;
- size -= len;
+ /*
+ * Enable the DMA channels and configure them ...
+ */
+ val = (s->chip->dma1 << 4) | DMA_8BIT;
+ sscape_write_unsafe(s->io_base, GA_DMAA_REG, val);
+ sscape_write_unsafe(s->io_base, GA_DMAB_REG, 0x20);
- snd_dma_program(s->chip->dma1, dma.addr, len, DMA_MODE_WRITE);
- sscape_start_dma_unsafe(s->io_base, GA_DMAA_REG);
- if (!sscape_wait_dma_unsafe(s->io_base, GA_DMAA_REG, 5000)) {
- /*
- * Don't forget to release this spinlock we're holding
- */
- spin_unlock_irqrestore(&s->lock, flags);
+ /*
+ * Take the board out of reset ...
+ */
+ val = sscape_read_unsafe(s->io_base, GA_HMCTL_REG);
+ sscape_write_unsafe(s->io_base, GA_HMCTL_REG, val | 0x80);
- snd_printk(KERN_ERR
- "sscape: DMA upload has timed out\n");
- ret = -EAGAIN;
- goto _release_dma;
- }
- } /* while */
+ /*
+ * Upload the firmware to the SoundScape
+ * board through the DMA channel ...
+ */
+ while (size != 0) {
+ unsigned long len;
+
+ len = min(size, dma.bytes);
+ memcpy(dma.area, data, len);
+ data += len;
+ size -= len;
+
+ snd_dma_program(s->chip->dma1, dma.addr, len, DMA_MODE_WRITE);
+ sscape_start_dma_unsafe(s->io_base, GA_DMAA_REG);
+ if (!sscape_wait_dma_unsafe(s->io_base, GA_DMAA_REG, 5000)) {
+ dev_err(s->dev, "sscape: DMA upload has timed out\n");
+ ret = -EAGAIN;
+ goto _release_dma;
+ }
+ } /* while */
- set_host_mode_unsafe(s->io_base);
- outb(0x0, s->io_base);
+ set_host_mode_unsafe(s->io_base);
+ outb(0x0, s->io_base);
- /*
- * Boot the board ... (I think)
- */
- val = sscape_read_unsafe(s->io_base, GA_HMCTL_REG);
- sscape_write_unsafe(s->io_base, GA_HMCTL_REG, val | 0x40);
- spin_unlock_irqrestore(&s->lock, flags);
+ /*
+ * Boot the board ... (I think)
+ */
+ val = sscape_read_unsafe(s->io_base, GA_HMCTL_REG);
+ sscape_write_unsafe(s->io_base, GA_HMCTL_REG, val | 0x40);
+ }
/*
* If all has gone well, then the board should acknowledge
@@ -487,12 +476,11 @@ static int upload_dma_data(struct soundscape *s, const unsigned char *data,
*/
ret = 0;
if (!obp_startup_ack(s, 5000)) {
- snd_printk(KERN_ERR "sscape: No response "
- "from on-board processor after upload\n");
+ dev_err(s->dev,
+ "sscape: No response from on-board processor after upload\n");
ret = -EAGAIN;
} else if (!host_startup_ack(s, 5000)) {
- snd_printk(KERN_ERR
- "sscape: SoundScape failed to initialise\n");
+ dev_err(s->dev, "sscape: SoundScape failed to initialise\n");
ret = -EAGAIN;
}
@@ -514,33 +502,30 @@ _release_dma:
static int sscape_upload_bootblock(struct snd_card *card)
{
struct soundscape *sscape = get_card_soundscape(card);
- unsigned long flags;
const struct firmware *init_fw = NULL;
int data = 0;
int ret;
ret = request_firmware(&init_fw, "scope.cod", card->dev);
if (ret < 0) {
- snd_printk(KERN_ERR "sscape: Error loading scope.cod");
+ dev_err(card->dev, "sscape: Error loading scope.cod");
return ret;
}
ret = upload_dma_data(sscape, init_fw->data, init_fw->size);
release_firmware(init_fw);
- spin_lock_irqsave(&sscape->lock, flags);
+ guard(spinlock_irqsave)(&sscape->lock);
if (ret == 0)
data = host_read_ctrl_unsafe(sscape->io_base, 100);
if (data & 0x10)
sscape_write_unsafe(sscape->io_base, GA_SMCFGA_REG, 0x2f);
- spin_unlock_irqrestore(&sscape->lock, flags);
-
data &= 0xf;
if (ret == 0 && data > 7) {
- snd_printk(KERN_ERR
- "sscape: timeout reading firmware version\n");
+ dev_err(card->dev,
+ "sscape: timeout reading firmware version\n");
ret = -EAGAIN;
}
@@ -557,18 +542,18 @@ static int sscape_upload_microcode(struct snd_card *card, int version)
char name[14];
int err;
- snprintf(name, sizeof(name), "sndscape.co%d", version);
+ scnprintf(name, sizeof(name), "sndscape.co%d", version);
err = request_firmware(&init_fw, name, card->dev);
if (err < 0) {
- snd_printk(KERN_ERR "sscape: Error loading sndscape.co%d",
- version);
+ dev_err(card->dev, "sscape: Error loading sndscape.co%d",
+ version);
return err;
}
err = upload_dma_data(sscape, init_fw->data, init_fw->size);
if (err == 0)
- snd_printk(KERN_INFO "sscape: MIDI firmware loaded %zu KBs\n",
- init_fw->size >> 10);
+ dev_info(card->dev, "sscape: MIDI firmware loaded %zu KBs\n",
+ init_fw->size >> 10);
release_firmware(init_fw);
@@ -594,11 +579,9 @@ static int sscape_midi_get(struct snd_kcontrol *kctl,
struct snd_wss *chip = snd_kcontrol_chip(kctl);
struct snd_card *card = chip->card;
register struct soundscape *s = get_card_soundscape(card);
- unsigned long flags;
- spin_lock_irqsave(&s->lock, flags);
+ guard(spinlock_irqsave)(&s->lock);
uctl->value.integer.value[0] = s->midi_vol;
- spin_unlock_irqrestore(&s->lock, flags);
return 0;
}
@@ -608,11 +591,10 @@ static int sscape_midi_put(struct snd_kcontrol *kctl,
struct snd_wss *chip = snd_kcontrol_chip(kctl);
struct snd_card *card = chip->card;
struct soundscape *s = get_card_soundscape(card);
- unsigned long flags;
int change;
unsigned char new_val;
- spin_lock_irqsave(&s->lock, flags);
+ guard(spinlock_irqsave)(&s->lock);
new_val = uctl->value.integer.value[0] & 127;
/*
@@ -643,7 +625,6 @@ __skip_change:
*/
set_midi_mode_unsafe(s->io_base);
- spin_unlock_irqrestore(&s->lock, flags);
return change;
}
@@ -783,8 +764,8 @@ _done:
static int mpu401_open(struct snd_mpu401 *mpu)
{
if (!verify_mpu401(mpu)) {
- snd_printk(KERN_ERR "sscape: MIDI disabled, "
- "please load firmware\n");
+ dev_err(mpu->rmidi->card->dev,
+ "sscape: MIDI disabled, please load firmware\n");
return -ENODEV;
}
@@ -853,8 +834,6 @@ static int create_ad1845(struct snd_card *card, unsigned port,
err = snd_wss_create(card, port, -1, irq, dma1, dma2,
codec_type, WSS_HWSHARE_DMA1, &chip);
if (!err) {
- unsigned long flags;
-
if (sscape->type != SSCAPE_VIVO) {
/*
* The input clock frequency on the SoundScape must
@@ -862,31 +841,31 @@ static int create_ad1845(struct snd_card *card, unsigned port,
* to get the playback to sound correct ...
*/
snd_wss_mce_up(chip);
- spin_lock_irqsave(&chip->reg_lock, flags);
- snd_wss_out(chip, AD1845_CLOCK, 0x20);
- spin_unlock_irqrestore(&chip->reg_lock, flags);
+ scoped_guard(spinlock_irqsave, &chip->reg_lock) {
+ snd_wss_out(chip, AD1845_CLOCK, 0x20);
+ }
snd_wss_mce_down(chip);
}
err = snd_wss_pcm(chip, 0);
if (err < 0) {
- snd_printk(KERN_ERR "sscape: No PCM device "
- "for AD1845 chip\n");
+ dev_err(card->dev,
+ "sscape: No PCM device for AD1845 chip\n");
goto _error;
}
err = snd_wss_mixer(chip);
if (err < 0) {
- snd_printk(KERN_ERR "sscape: No mixer device "
- "for AD1845 chip\n");
+ dev_err(card->dev,
+ "sscape: No mixer device for AD1845 chip\n");
goto _error;
}
if (chip->hardware != WSS_HW_AD1848) {
err = snd_wss_timer(chip, 0);
if (err < 0) {
- snd_printk(KERN_ERR "sscape: No timer device "
- "for AD1845 chip\n");
+ dev_err(card->dev,
+ "sscape: No timer device for AD1845 chip\n");
goto _error;
}
}
@@ -895,8 +874,8 @@ static int create_ad1845(struct snd_card *card, unsigned port,
err = snd_ctl_add(card,
snd_ctl_new1(&midi_mixer_ctl, chip));
if (err < 0) {
- snd_printk(KERN_ERR "sscape: Could not create "
- "MIDI mixer control\n");
+ dev_err(card->dev,
+ "sscape: Could not create MIDI mixer control\n");
goto _error;
}
}
@@ -921,7 +900,6 @@ static int create_sscape(int dev, struct snd_card *card)
unsigned mpu_irq_cfg;
struct resource *io_res;
struct resource *wss_res;
- unsigned long flags;
int err;
int val;
const char *name;
@@ -932,8 +910,8 @@ static int create_sscape(int dev, struct snd_card *card)
*/
io_res = devm_request_region(card->dev, port[dev], 8, "SoundScape");
if (!io_res) {
- snd_printk(KERN_ERR
- "sscape: can't grab port 0x%lx\n", port[dev]);
+ dev_err(card->dev,
+ "sscape: can't grab port 0x%lx\n", port[dev]);
return -EBUSY;
}
wss_res = NULL;
@@ -941,8 +919,8 @@ static int create_sscape(int dev, struct snd_card *card)
wss_res = devm_request_region(card->dev, wss_port[dev], 4,
"SoundScape");
if (!wss_res) {
- snd_printk(KERN_ERR "sscape: can't grab port 0x%lx\n",
- wss_port[dev]);
+ dev_err(card->dev, "sscape: can't grab port 0x%lx\n",
+ wss_port[dev]);
return -EBUSY;
}
}
@@ -952,7 +930,7 @@ static int create_sscape(int dev, struct snd_card *card)
*/
err = snd_devm_request_dma(card->dev, dma[dev], "SoundScape");
if (err < 0) {
- snd_printk(KERN_ERR "sscape: can't grab DMA %d\n", dma[dev]);
+ dev_err(card->dev, "sscape: can't grab DMA %d\n", dma[dev]);
return err;
}
@@ -962,7 +940,7 @@ static int create_sscape(int dev, struct snd_card *card)
sscape->io_base = port[dev];
if (!detect_sscape(sscape, wss_port[dev])) {
- printk(KERN_ERR "sscape: hardware not detected at 0x%x\n",
+ dev_err(card->dev, "sscape: hardware not detected at 0x%x\n",
sscape->io_base);
return -ENODEV;
}
@@ -985,21 +963,21 @@ static int create_sscape(int dev, struct snd_card *card)
break;
}
- printk(KERN_INFO "sscape: %s card detected at 0x%x, using IRQ %d, DMA %d\n",
- name, sscape->io_base, irq[dev], dma[dev]);
+ dev_info(card->dev, "sscape: %s card detected at 0x%x, using IRQ %d, DMA %d\n",
+ name, sscape->io_base, irq[dev], dma[dev]);
/*
* Check that the user didn't pass us garbage data ...
*/
irq_cfg = get_irq_config(sscape->type, irq[dev]);
if (irq_cfg == INVALID_IRQ) {
- snd_printk(KERN_ERR "sscape: Invalid IRQ %d\n", irq[dev]);
+ dev_err(card->dev, "sscape: Invalid IRQ %d\n", irq[dev]);
return -ENXIO;
}
mpu_irq_cfg = get_irq_config(sscape->type, mpu_irq[dev]);
if (mpu_irq_cfg == INVALID_IRQ) {
- snd_printk(KERN_ERR "sscape: Invalid IRQ %d\n", mpu_irq[dev]);
+ dev_err(card->dev, "sscape: Invalid IRQ %d\n", mpu_irq[dev]);
return -ENXIO;
}
@@ -1007,34 +985,34 @@ static int create_sscape(int dev, struct snd_card *card)
* Tell the on-board devices where their resources are (I think -
* I can't be sure without a datasheet ... So many magic values!)
*/
- spin_lock_irqsave(&sscape->lock, flags);
+ scoped_guard(spinlock_irqsave, &sscape->lock) {
- sscape_write_unsafe(sscape->io_base, GA_SMCFGA_REG, 0x2e);
- sscape_write_unsafe(sscape->io_base, GA_SMCFGB_REG, 0x00);
+ sscape_write_unsafe(sscape->io_base, GA_SMCFGA_REG, 0x2e);
+ sscape_write_unsafe(sscape->io_base, GA_SMCFGB_REG, 0x00);
- /*
- * Enable and configure the DMA channels ...
- */
- sscape_write_unsafe(sscape->io_base, GA_DMACFG_REG, 0x50);
- dma_cfg = (sscape->ic_type == IC_OPUS ? 0x40 : 0x70);
- sscape_write_unsafe(sscape->io_base, GA_DMAA_REG, dma_cfg);
- sscape_write_unsafe(sscape->io_base, GA_DMAB_REG, 0x20);
-
- mpu_irq_cfg |= mpu_irq_cfg << 2;
- val = sscape_read_unsafe(sscape->io_base, GA_HMCTL_REG) & 0xF7;
- if (joystick[dev])
- val |= 8;
- sscape_write_unsafe(sscape->io_base, GA_HMCTL_REG, val | 0x10);
- sscape_write_unsafe(sscape->io_base, GA_INTCFG_REG, 0xf0 | mpu_irq_cfg);
- sscape_write_unsafe(sscape->io_base,
- GA_CDCFG_REG, 0x09 | DMA_8BIT
- | (dma[dev] << 4) | (irq_cfg << 1));
- /*
- * Enable the master IRQ ...
- */
- sscape_write_unsafe(sscape->io_base, GA_INTENA_REG, 0x80);
+ /*
+ * Enable and configure the DMA channels ...
+ */
+ sscape_write_unsafe(sscape->io_base, GA_DMACFG_REG, 0x50);
+ dma_cfg = (sscape->ic_type == IC_OPUS ? 0x40 : 0x70);
+ sscape_write_unsafe(sscape->io_base, GA_DMAA_REG, dma_cfg);
+ sscape_write_unsafe(sscape->io_base, GA_DMAB_REG, 0x20);
+
+ mpu_irq_cfg |= mpu_irq_cfg << 2;
+ val = sscape_read_unsafe(sscape->io_base, GA_HMCTL_REG) & 0xF7;
+ if (joystick[dev])
+ val |= 8;
+ sscape_write_unsafe(sscape->io_base, GA_HMCTL_REG, val | 0x10);
+ sscape_write_unsafe(sscape->io_base, GA_INTCFG_REG, 0xf0 | mpu_irq_cfg);
+ sscape_write_unsafe(sscape->io_base,
+ GA_CDCFG_REG, 0x09 | DMA_8BIT
+ | (dma[dev] << 4) | (irq_cfg << 1));
+ /*
+ * Enable the master IRQ ...
+ */
+ sscape_write_unsafe(sscape->io_base, GA_INTENA_REG, 0x80);
- spin_unlock_irqrestore(&sscape->lock, flags);
+ }
/*
* We have now enabled the codec chip, and so we should
@@ -1043,13 +1021,13 @@ static int create_sscape(int dev, struct snd_card *card)
err = create_ad1845(card, wss_port[dev], irq[dev],
dma[dev], dma2[dev]);
if (err < 0) {
- snd_printk(KERN_ERR
- "sscape: No AD1845 device at 0x%lx, IRQ %d\n",
- wss_port[dev], irq[dev]);
+ dev_err(card->dev,
+ "sscape: No AD1845 device at 0x%lx, IRQ %d\n",
+ wss_port[dev], irq[dev]);
return err;
}
- strcpy(card->driver, "SoundScape");
- strcpy(card->shortname, name);
+ strscpy(card->driver, "SoundScape");
+ strscpy(card->shortname, name);
snprintf(card->longname, sizeof(card->longname),
"%s at 0x%lx, IRQ %d, DMA1 %d, DMA2 %d\n",
name, sscape->chip->port, sscape->chip->irq,
@@ -1065,16 +1043,16 @@ static int create_sscape(int dev, struct snd_card *card)
err = create_mpu401(card, MIDI_DEVNUM, port[dev],
mpu_irq[dev]);
if (err < 0) {
- snd_printk(KERN_ERR "sscape: Failed to create "
- "MPU-401 device at 0x%lx\n",
- port[dev]);
+ dev_err(card->dev,
+ "sscape: Failed to create MPU-401 device at 0x%lx\n",
+ port[dev]);
return err;
}
/*
* Initialize mixer
*/
- spin_lock_irqsave(&sscape->lock, flags);
+ guard(spinlock_irqsave)(&sscape->lock);
sscape->midi_vol = 0;
host_write_ctrl_unsafe(sscape->io_base,
CMD_SET_MIDI_VOL, 100);
@@ -1091,7 +1069,6 @@ static int create_sscape(int dev, struct snd_card *card)
host_write_ctrl_unsafe(sscape->io_base, CMD_ACK, 100);
set_midi_mode_unsafe(sscape->io_base);
- spin_unlock_irqrestore(&sscape->lock, flags);
}
}
@@ -1110,9 +1087,8 @@ static int snd_sscape_match(struct device *pdev, unsigned int i)
if (irq[i] == SNDRV_AUTO_IRQ ||
mpu_irq[i] == SNDRV_AUTO_IRQ ||
dma[i] == SNDRV_AUTO_DMA) {
- printk(KERN_INFO
- "sscape: insufficient parameters, "
- "need IO, IRQ, MPU-IRQ and DMA\n");
+ dev_info(pdev,
+ "sscape: insufficient parameters, need IO, IRQ, MPU-IRQ and DMA\n");
return 0;
}
@@ -1131,6 +1107,7 @@ static int snd_sscape_probe(struct device *pdev, unsigned int dev)
return ret;
sscape = get_card_soundscape(card);
+ sscape->dev = pdev;
sscape->type = SSCAPE;
dma[dev] &= 0x03;
@@ -1141,7 +1118,7 @@ static int snd_sscape_probe(struct device *pdev, unsigned int dev)
ret = snd_card_register(card);
if (ret < 0) {
- snd_printk(KERN_ERR "sscape: Failed to register sound card\n");
+ dev_err(pdev, "sscape: Failed to register sound card\n");
return ret;
}
dev_set_drvdata(pdev, card);
@@ -1194,7 +1171,7 @@ static int sscape_pnp_detect(struct pnp_card_link *pcard,
if (!pnp_is_active(dev)) {
if (pnp_activate_dev(dev) < 0) {
- snd_printk(KERN_INFO "sscape: device is inactive\n");
+ dev_info(&dev->dev, "sscape: device is inactive\n");
return -EBUSY;
}
}
@@ -1210,6 +1187,7 @@ static int sscape_pnp_detect(struct pnp_card_link *pcard,
return ret;
sscape = get_card_soundscape(card);
+ sscape->dev = card->dev;
/*
* Identify card model ...
@@ -1240,7 +1218,7 @@ static int sscape_pnp_detect(struct pnp_card_link *pcard,
ret = snd_card_register(card);
if (ret < 0) {
- snd_printk(KERN_ERR "sscape: Failed to register sound card\n");
+ dev_err(card->dev, "sscape: Failed to register sound card\n");
return ret;
}