summaryrefslogtreecommitdiff
path: root/sound/sparc/dbri.c
diff options
context:
space:
mode:
Diffstat (limited to 'sound/sparc/dbri.c')
-rw-r--r--sound/sparc/dbri.c232
1 files changed, 109 insertions, 123 deletions
diff --git a/sound/sparc/dbri.c b/sound/sparc/dbri.c
index 93cbe158009f..75f82a92ff44 100644
--- a/sound/sparc/dbri.c
+++ b/sound/sparc/dbri.c
@@ -758,40 +758,38 @@ static void dbri_initialize(struct snd_dbri *dbri)
u32 dvma_addr = (u32)dbri->dma_dvma;
s32 *cmd;
u32 dma_addr;
- unsigned long flags;
int n;
- spin_lock_irqsave(&dbri->lock, flags);
-
- dbri_reset(dbri);
+ scoped_guard(spinlock_irqsave, &dbri->lock) {
+ dbri_reset(dbri);
- /* Initialize pipes */
- for (n = 0; n < DBRI_NO_PIPES; n++)
- dbri->pipes[n].desc = dbri->pipes[n].first_desc = -1;
+ /* Initialize pipes */
+ for (n = 0; n < DBRI_NO_PIPES; n++)
+ dbri->pipes[n].desc = dbri->pipes[n].first_desc = -1;
- spin_lock_init(&dbri->cmdlock);
- /*
- * Initialize the interrupt ring buffer.
- */
- dma_addr = dvma_addr + dbri_dma_off(intr, 0);
- dbri->dma->intr[0] = dma_addr;
- dbri->dbri_irqp = 1;
- /*
- * Set up the interrupt queue
- */
- spin_lock(&dbri->cmdlock);
- cmd = dbri->cmdptr = dbri->dma->cmd;
- *(cmd++) = DBRI_CMD(D_IIQ, 0, 0);
- *(cmd++) = dma_addr;
- *(cmd++) = DBRI_CMD(D_PAUSE, 0, 0);
- dbri->cmdptr = cmd;
- *(cmd++) = DBRI_CMD(D_WAIT, 1, 0);
- *(cmd++) = DBRI_CMD(D_WAIT, 1, 0);
- dma_addr = dvma_addr + dbri_dma_off(cmd, 0);
- sbus_writel(dma_addr, dbri->regs + REG8);
- spin_unlock(&dbri->cmdlock);
+ spin_lock_init(&dbri->cmdlock);
+ /*
+ * Initialize the interrupt ring buffer.
+ */
+ dma_addr = dvma_addr + dbri_dma_off(intr, 0);
+ dbri->dma->intr[0] = dma_addr;
+ dbri->dbri_irqp = 1;
+ /*
+ * Set up the interrupt queue
+ */
+ scoped_guard(spinlock, &dbri->cmdlock) {
+ cmd = dbri->cmdptr = dbri->dma->cmd;
+ *(cmd++) = DBRI_CMD(D_IIQ, 0, 0);
+ *(cmd++) = dma_addr;
+ *(cmd++) = DBRI_CMD(D_PAUSE, 0, 0);
+ dbri->cmdptr = cmd;
+ *(cmd++) = DBRI_CMD(D_WAIT, 1, 0);
+ *(cmd++) = DBRI_CMD(D_WAIT, 1, 0);
+ dma_addr = dvma_addr + dbri_dma_off(cmd, 0);
+ sbus_writel(dma_addr, dbri->regs + REG8);
+ }
+ }
- spin_unlock_irqrestore(&dbri->lock, flags);
dbri_cmdwait(dbri);
}
@@ -1002,7 +1000,6 @@ static void unlink_time_slot(struct snd_dbri *dbri, int pipe,
static void xmit_fixed(struct snd_dbri *dbri, int pipe, unsigned int data)
{
s32 *cmd;
- unsigned long flags;
if (pipe < 16 || pipe > DBRI_MAX_PIPE) {
printk(KERN_ERR "DBRI: xmit_fixed: Illegal pipe number\n");
@@ -1037,9 +1034,10 @@ static void xmit_fixed(struct snd_dbri *dbri, int pipe, unsigned int data)
*(cmd++) = data;
*(cmd++) = DBRI_CMD(D_PAUSE, 0, 0);
- spin_lock_irqsave(&dbri->lock, flags);
- dbri_cmdsend(dbri, cmd, 3);
- spin_unlock_irqrestore(&dbri->lock, flags);
+ scoped_guard(spinlock_irqsave, &dbri->lock) {
+ dbri_cmdsend(dbri, cmd, 3);
+ }
+
dbri_cmdwait(dbri);
}
@@ -1317,33 +1315,31 @@ to the DBRI via the CHI interface and few of the DBRI's PIO pins.
*/
static void cs4215_setup_pipes(struct snd_dbri *dbri)
{
- unsigned long flags;
-
- spin_lock_irqsave(&dbri->lock, flags);
- /*
- * Data mode:
- * Pipe 4: Send timeslots 1-4 (audio data)
- * Pipe 20: Send timeslots 5-8 (part of ctrl data)
- * Pipe 6: Receive timeslots 1-4 (audio data)
- * Pipe 21: Receive timeslots 6-7. We can only receive 20 bits via
- * interrupt, and the rest of the data (slot 5 and 8) is
- * not relevant for us (only for doublechecking).
- *
- * Control mode:
- * Pipe 17: Send timeslots 1-4 (slots 5-8 are read only)
- * Pipe 18: Receive timeslot 1 (clb).
- * Pipe 19: Receive timeslot 7 (version).
- */
+ scoped_guard(spinlock_irqsave, &dbri->lock) {
+ /*
+ * Data mode:
+ * Pipe 4: Send timeslots 1-4 (audio data)
+ * Pipe 20: Send timeslots 5-8 (part of ctrl data)
+ * Pipe 6: Receive timeslots 1-4 (audio data)
+ * Pipe 21: Receive timeslots 6-7. We can only receive 20 bits via
+ * interrupt, and the rest of the data (slot 5 and 8) is
+ * not relevant for us (only for doublechecking).
+ *
+ * Control mode:
+ * Pipe 17: Send timeslots 1-4 (slots 5-8 are read only)
+ * Pipe 18: Receive timeslot 1 (clb).
+ * Pipe 19: Receive timeslot 7 (version).
+ */
- setup_pipe(dbri, 4, D_SDP_MEM | D_SDP_TO_SER | D_SDP_MSB);
- setup_pipe(dbri, 20, D_SDP_FIXED | D_SDP_TO_SER | D_SDP_MSB);
- setup_pipe(dbri, 6, D_SDP_MEM | D_SDP_FROM_SER | D_SDP_MSB);
- setup_pipe(dbri, 21, D_SDP_FIXED | D_SDP_FROM_SER | D_SDP_MSB);
+ setup_pipe(dbri, 4, D_SDP_MEM | D_SDP_TO_SER | D_SDP_MSB);
+ setup_pipe(dbri, 20, D_SDP_FIXED | D_SDP_TO_SER | D_SDP_MSB);
+ setup_pipe(dbri, 6, D_SDP_MEM | D_SDP_FROM_SER | D_SDP_MSB);
+ setup_pipe(dbri, 21, D_SDP_FIXED | D_SDP_FROM_SER | D_SDP_MSB);
- setup_pipe(dbri, 17, D_SDP_FIXED | D_SDP_TO_SER | D_SDP_MSB);
- setup_pipe(dbri, 18, D_SDP_FIXED | D_SDP_FROM_SER | D_SDP_MSB);
- setup_pipe(dbri, 19, D_SDP_FIXED | D_SDP_FROM_SER | D_SDP_MSB);
- spin_unlock_irqrestore(&dbri->lock, flags);
+ setup_pipe(dbri, 17, D_SDP_FIXED | D_SDP_TO_SER | D_SDP_MSB);
+ setup_pipe(dbri, 18, D_SDP_FIXED | D_SDP_FROM_SER | D_SDP_MSB);
+ setup_pipe(dbri, 19, D_SDP_FIXED | D_SDP_FROM_SER | D_SDP_MSB);
+ }
dbri_cmdwait(dbri);
}
@@ -1418,7 +1414,6 @@ static void cs4215_open(struct snd_dbri *dbri)
{
int data_width;
u32 tmp;
- unsigned long flags;
dprintk(D_MM, "cs4215_open: %d channels, %d bits\n",
dbri->mm.channels, dbri->mm.precision);
@@ -1443,35 +1438,35 @@ static void cs4215_open(struct snd_dbri *dbri)
* bits. The CS4215, it seems, observes TSIN (the delayed signal)
* even if it's the CHI master. Don't ask me...
*/
- spin_lock_irqsave(&dbri->lock, flags);
- tmp = sbus_readl(dbri->regs + REG0);
- tmp &= ~(D_C); /* Disable CHI */
- sbus_writel(tmp, dbri->regs + REG0);
+ scoped_guard(spinlock_irqsave, &dbri->lock) {
+ tmp = sbus_readl(dbri->regs + REG0);
+ tmp &= ~(D_C); /* Disable CHI */
+ sbus_writel(tmp, dbri->regs + REG0);
- /* Switch CS4215 to data mode - set PIO3 to 1 */
- sbus_writel(D_ENPIO | D_PIO1 | D_PIO3 |
- (dbri->mm.onboard ? D_PIO0 : D_PIO2), dbri->regs + REG2);
+ /* Switch CS4215 to data mode - set PIO3 to 1 */
+ sbus_writel(D_ENPIO | D_PIO1 | D_PIO3 |
+ (dbri->mm.onboard ? D_PIO0 : D_PIO2), dbri->regs + REG2);
- reset_chi(dbri, CHIslave, 128);
+ reset_chi(dbri, CHIslave, 128);
- /* Note: this next doesn't work for 8-bit stereo, because the two
- * channels would be on timeslots 1 and 3, with 2 and 4 idle.
- * (See CS4215 datasheet Fig 15)
- *
- * DBRI non-contiguous mode would be required to make this work.
- */
- data_width = dbri->mm.channels * dbri->mm.precision;
+ /* Note: this next doesn't work for 8-bit stereo, because the two
+ * channels would be on timeslots 1 and 3, with 2 and 4 idle.
+ * (See CS4215 datasheet Fig 15)
+ *
+ * DBRI non-contiguous mode would be required to make this work.
+ */
+ data_width = dbri->mm.channels * dbri->mm.precision;
- link_time_slot(dbri, 4, 16, 16, data_width, dbri->mm.offset);
- link_time_slot(dbri, 20, 4, 16, 32, dbri->mm.offset + 32);
- link_time_slot(dbri, 6, 16, 16, data_width, dbri->mm.offset);
- link_time_slot(dbri, 21, 6, 16, 16, dbri->mm.offset + 40);
+ link_time_slot(dbri, 4, 16, 16, data_width, dbri->mm.offset);
+ link_time_slot(dbri, 20, 4, 16, 32, dbri->mm.offset + 32);
+ link_time_slot(dbri, 6, 16, 16, data_width, dbri->mm.offset);
+ link_time_slot(dbri, 21, 6, 16, 16, dbri->mm.offset + 40);
- /* FIXME: enable CHI after _setdata? */
- tmp = sbus_readl(dbri->regs + REG0);
- tmp |= D_C; /* Enable CHI */
- sbus_writel(tmp, dbri->regs + REG0);
- spin_unlock_irqrestore(&dbri->lock, flags);
+ /* FIXME: enable CHI after _setdata? */
+ tmp = sbus_readl(dbri->regs + REG0);
+ tmp |= D_C; /* Enable CHI */
+ sbus_writel(tmp, dbri->regs + REG0);
+ }
cs4215_setdata(dbri, 0);
}
@@ -1483,7 +1478,6 @@ static int cs4215_setctrl(struct snd_dbri *dbri)
{
int i, val;
u32 tmp;
- unsigned long flags;
/* FIXME - let the CPU do something useful during these delays */
@@ -1520,34 +1514,34 @@ static int cs4215_setctrl(struct snd_dbri *dbri)
* done in hardware by a TI 248 that delays the DBRI->4215
* frame sync signal by eight clock cycles. Anybody know why?
*/
- spin_lock_irqsave(&dbri->lock, flags);
- tmp = sbus_readl(dbri->regs + REG0);
- tmp &= ~D_C; /* Disable CHI */
- sbus_writel(tmp, dbri->regs + REG0);
-
- reset_chi(dbri, CHImaster, 128);
-
- /*
- * Control mode:
- * Pipe 17: Send timeslots 1-4 (slots 5-8 are read only)
- * Pipe 18: Receive timeslot 1 (clb).
- * Pipe 19: Receive timeslot 7 (version).
- */
+ scoped_guard(spinlock_irqsave, &dbri->lock) {
+ tmp = sbus_readl(dbri->regs + REG0);
+ tmp &= ~D_C; /* Disable CHI */
+ sbus_writel(tmp, dbri->regs + REG0);
+
+ reset_chi(dbri, CHImaster, 128);
+
+ /*
+ * Control mode:
+ * Pipe 17: Send timeslots 1-4 (slots 5-8 are read only)
+ * Pipe 18: Receive timeslot 1 (clb).
+ * Pipe 19: Receive timeslot 7 (version).
+ */
- link_time_slot(dbri, 17, 16, 16, 32, dbri->mm.offset);
- link_time_slot(dbri, 18, 16, 16, 8, dbri->mm.offset);
- link_time_slot(dbri, 19, 18, 16, 8, dbri->mm.offset + 48);
- spin_unlock_irqrestore(&dbri->lock, flags);
+ link_time_slot(dbri, 17, 16, 16, 32, dbri->mm.offset);
+ link_time_slot(dbri, 18, 16, 16, 8, dbri->mm.offset);
+ link_time_slot(dbri, 19, 18, 16, 8, dbri->mm.offset + 48);
+ }
/* Wait for the chip to echo back CLB (Control Latch Bit) as zero */
dbri->mm.ctrl[0] &= ~CS4215_CLB;
xmit_fixed(dbri, 17, *(int *)dbri->mm.ctrl);
- spin_lock_irqsave(&dbri->lock, flags);
- tmp = sbus_readl(dbri->regs + REG0);
- tmp |= D_C; /* Enable CHI */
- sbus_writel(tmp, dbri->regs + REG0);
- spin_unlock_irqrestore(&dbri->lock, flags);
+ scoped_guard(spinlock_irqsave, &dbri->lock) {
+ tmp = sbus_readl(dbri->regs + REG0);
+ tmp |= D_C; /* Enable CHI */
+ sbus_writel(tmp, dbri->regs + REG0);
+ }
for (i = 10; ((dbri->mm.status & 0xe4) != 0x20); --i)
msleep_interruptible(1);
@@ -1709,7 +1703,6 @@ static void xmit_descs(struct snd_dbri *dbri)
struct dbri_streaminfo *info;
u32 dvma_addr;
s32 *cmd;
- unsigned long flags;
int first_td;
if (dbri == NULL)
@@ -1717,7 +1710,7 @@ static void xmit_descs(struct snd_dbri *dbri)
dvma_addr = (u32)dbri->dma_dvma;
info = &dbri->stream_info[DBRI_REC];
- spin_lock_irqsave(&dbri->lock, flags);
+ guard(spinlock_irqsave)(&dbri->lock);
if (info->pipe >= 0) {
first_td = dbri->pipes[info->pipe].first_desc;
@@ -1760,8 +1753,6 @@ static void xmit_descs(struct snd_dbri *dbri)
dbri->pipes[info->pipe].desc = first_td;
}
}
-
- spin_unlock_irqrestore(&dbri->lock, flags);
}
/* transmission_complete_intr()
@@ -1932,7 +1923,7 @@ static irqreturn_t snd_dbri_interrupt(int irq, void *dev_id)
if (dbri == NULL)
return IRQ_NONE;
- spin_lock(&dbri->lock);
+ guard(spinlock)(&dbri->lock);
/*
* Read it, so the interrupt goes away.
@@ -1977,8 +1968,6 @@ static irqreturn_t snd_dbri_interrupt(int irq, void *dev_id)
dbri_process_interrupt_buffer(dbri);
- spin_unlock(&dbri->lock);
-
return IRQ_HANDLED;
}
@@ -2046,17 +2035,16 @@ static int snd_dbri_open(struct snd_pcm_substream *substream)
struct snd_dbri *dbri = snd_pcm_substream_chip(substream);
struct snd_pcm_runtime *runtime = substream->runtime;
struct dbri_streaminfo *info = DBRI_STREAM(dbri, substream);
- unsigned long flags;
dprintk(D_USR, "open audio output.\n");
runtime->hw = snd_dbri_pcm_hw;
- spin_lock_irqsave(&dbri->lock, flags);
- info->substream = substream;
- info->offset = 0;
- info->dvma_buffer = 0;
- info->pipe = -1;
- spin_unlock_irqrestore(&dbri->lock, flags);
+ scoped_guard(spinlock_irqsave, &dbri->lock) {
+ info->substream = substream;
+ info->offset = 0;
+ info->dvma_buffer = 0;
+ info->pipe = -1;
+ }
snd_pcm_hw_rule_add(runtime, 0, SNDRV_PCM_HW_PARAM_CHANNELS,
snd_hw_rule_format, NULL, SNDRV_PCM_HW_PARAM_FORMAT,
@@ -2160,7 +2148,7 @@ static int snd_dbri_prepare(struct snd_pcm_substream *substream)
else
info->pipe = 6; /* Receive pipe */
- spin_lock_irq(&dbri->lock);
+ guard(spinlock_irq)(&dbri->lock);
info->offset = 0;
/* Setup the all the transmit/receive descriptors to cover the
@@ -2169,8 +2157,6 @@ static int snd_dbri_prepare(struct snd_pcm_substream *substream)
ret = setup_descs(dbri, DBRI_STREAMNO(substream),
snd_pcm_lib_period_bytes(substream));
- spin_unlock_irq(&dbri->lock);
-
dprintk(D_USR, "prepare audio output. %d bytes\n", info->size);
return ret;
}