patch-2.3.13 linux/drivers/sbus/audio/cs4231.c
Next file: linux/drivers/sbus/char/bpp.c
Previous file: linux/drivers/sbus/audio/audio.c
Back to the patch index
Back to the overall index
- Lines: 218
- Date:
Fri Aug 6 11:58:00 1999
- Orig file:
v2.3.12/linux/drivers/sbus/audio/cs4231.c
- Orig date:
Wed Apr 28 08:47:39 1999
diff -u --recursive --new-file v2.3.12/linux/drivers/sbus/audio/cs4231.c linux/drivers/sbus/audio/cs4231.c
@@ -1421,7 +1421,7 @@
status += 2;
}
- sparcaudio_input_done(drv, 1);
+ sparcaudio_input_done(drv, status);
return 1;
}
@@ -1484,26 +1484,23 @@
cs4231_chip->perchip_info.play.active = 1;
cs4231_chip->playing_count = 0;
+ cs4231_playintr(drv);
if ((cs4231_chip->regs->dmacsr & APC_PPAUSE) ||
!(cs4231_chip->regs->dmacsr & APC_PDMA_READY)) {
- cs4231_chip->regs->dmacsr &= ~APC_XINT_PLAY;
- cs4231_chip->regs->dmacsr &= ~APC_PPAUSE;
-
- cs4231_playintr(drv);
-
- cs4231_chip->regs->dmacsr |= APC_PLAY_SETUP;
+ cs4231_chip->regs->dmacsr &= ~(APC_XINT_PLAY | APC_PPAUSE);
+ cs4231_chip->regs->dmacsr |= APC_GENL_INT | APC_XINT_ENA | APC_XINT_PLAY
+ | APC_XINT_GENL | APC_XINT_PENA | APC_PDMA_READY;
cs4231_enable_play(drv);
-
+
cs4231_ready(drv);
- } else
- cs4231_playintr(drv);
+ }
}
#ifdef EB4231_SUPPORT
static void eb4231_stop_output(struct sparcaudio_driver *drv)
{
struct cs4231_chip *cs4231_chip = (struct cs4231_chip *)drv->private;
- int dcsr;
+ unsigned int dcsr;
dprintk(("eb4231_stop_output: dcsr 0x%x dacr 0x%x dbcr %d\n",
readl(&cs4231_chip->eb2p->dcsr),
@@ -1525,6 +1522,7 @@
/* Else subsequent speed setting changes are ignored by the chip. */
cs4231_disable_play(drv);
+ cs4231_chip->perchip_info.play.active = 0;
}
#endif
@@ -1547,9 +1545,14 @@
cs4231_chip->output_next_dma_handle = 0;
cs4231_chip->output_next_dma_size = 0;
}
-#if 0 /* Not safe without shutting off the DMA controller as well. -DaveM */
+#if 1 /* Not safe without shutting off the DMA controller as well. -DaveM */
/* Else subsequent speed setting changes are ignored by the chip. */
+ cs4231_chip->regs->dmacsr &= ~(APC_GENL_INT | APC_XINT_ENA | APC_XINT_PLAY
+ | APC_XINT_GENL | APC_PDMA_READY
+ | APC_XINT_PENA | APC_PPAUSE );
+ printk("in cs4231_stop_output: 0x%x\n", cs4231_chip->regs->dmacsr);
cs4231_disable_play(drv);
+ cs4231_chip->perchip_info.play.active = 0;
#endif
}
@@ -1635,6 +1638,68 @@
cs4231_pollinput(drv);
}
+#ifdef EB4231_SUPPORT
+static void eb4231_start_input(struct sparcaudio_driver *drv, __u8 * buffer,
+ unsigned long count)
+{
+ struct cs4231_chip *cs4231_chip = (struct cs4231_chip *)drv->private;
+ unsigned int dcsr;
+
+ cs4231_chip->input_ptr = buffer;
+ cs4231_chip->input_size = count;
+
+ if (cs4231_chip->perchip_info.record.active ||
+ (cs4231_chip->perchip_info.record.pause))
+ return;
+
+ cs4231_ready(drv);
+
+ cs4231_chip->perchip_info.record.active = 1;
+ cs4231_chip->recording_count = 0;
+
+ dcsr = readl(&cs4231_chip->eb2c->dcsr);
+ if (!(dcsr & EBUS_DCSR_EN_DMA)) {
+ writel(EBUS_DCSR_RESET, &(cs4231_chip->eb2c->dcsr));
+ writel(EBUS_DCSR_BURST_SZ_16, &(cs4231_chip->eb2c->dcsr));
+
+ eb4231_recintr(drv);
+
+ writel(EBUS_DCSR_BURST_SZ_16 |
+ (EBUS_DCSR_EN_DMA | EBUS_DCSR_INT_EN | EBUS_DCSR_EN_CNT | EBUS_DCSR_EN_NEXT),
+ &(cs4231_chip->eb2c->dcsr));
+
+ cs4231_enable_rec(drv);
+ cs4231_ready(drv);
+ } else
+ eb4231_recintr(drv);
+}
+
+static void eb4231_stop_input(struct sparcaudio_driver *drv)
+{
+ struct cs4231_chip *cs4231_chip = (struct cs4231_chip *)drv->private;
+ unsigned int dcsr;
+
+ cs4231_chip->perchip_info.record.active = 0;
+
+ cs4231_chip->input_ptr = NULL;
+ cs4231_chip->input_size = 0;
+ if (cs4231_chip->input_dma_handle) {
+ cs4231_chip->input_dma_handle = 0;
+ cs4231_chip->input_dma_size = 0;
+ }
+ if (cs4231_chip->input_next_dma_handle) {
+ cs4231_chip->input_next_dma_handle = 0;
+ cs4231_chip->input_next_dma_size = 0;
+ }
+
+ dcsr = readl(&(cs4231_chip->eb2c->dcsr));
+ if (dcsr & EBUS_DCSR_EN_DMA)
+ writel(dcsr & ~EBUS_DCSR_EN_DMA, &(cs4231_chip->eb2c->dcsr));
+
+ cs4231_disable_rec(drv);
+}
+#endif
+
static int cs4231_set_output_pause(struct sparcaudio_driver *drv, int value)
{
struct cs4231_chip *cs4231_chip = (struct cs4231_chip *)drv->private;
@@ -1763,13 +1828,25 @@
struct cs4231_chip *cs4231_chip = (struct cs4231_chip *)drv->private;
int dummy;
- /* Read status. */
- dummy = readl(&cs4231_chip->eb2c->dcsr);
+ /* Clear the interrupt. */
+ dummy = readl(&(cs4231_chip->eb2c->dcsr));
+ writel(dummy, &(cs4231_chip->eb2c->dcsr));
- cs4231_chip->perchip_info.record.samples +=
- cs4231_length_to_samplecount(&(cs4231_chip->perchip_info.record),
- cs4231_chip->reclen);
- eb4231_recintr(drv);
+ if ((dummy & EBUS_DCSR_TC) != 0
+ /*&& (dummy & EBUS_DCSR_A_LOADED) != 0*/) {
+ cs4231_chip->perchip_info.record.samples +=
+ cs4231_length_to_samplecount(&(cs4231_chip->perchip_info.record),
+ cs4231_chip->reclen);
+ eb4231_recintr(drv);
+ }
+
+ if ((dummy & EBUS_DCSR_A_LOADED) == 0) {
+ cs4231_chip->perchip_info.record.active = 0;
+ eb4231_recintr(drv);
+#if 1
+ eb4231_getsamplecount(drv, cs4231_chip->reclen, 1);
+#endif
+ }
}
/* ebus audio play interrupt handler. */
@@ -1797,7 +1874,6 @@
}
if((dummy & EBUS_DCSR_A_LOADED) == 0) {
- cs4231_chip->perchip_info.play.active = 0;
eb4231_playintr(drv);
eb4231_getsamplecount(drv, cs4231_chip->playlen, 0);
@@ -1822,13 +1898,11 @@
* if anything since we may be doing shared interrupts
*/
- if (dummy & APC_PLAY_INT) {
- if (dummy & APC_XINT_PNVA) {
+ if (dummy & (APC_PLAY_INT|APC_XINT_PNVA|APC_XINT_PLAY|APC_XINT_EMPT|APC_XINT_PEMP)) {
cs4231_chip->perchip_info.play.samples +=
cs4231_length_to_samplecount(&(cs4231_chip->perchip_info.play),
cs4231_chip->playlen);
cs4231_playintr(drv);
- }
/* Any other conditions we need worry about? */
}
@@ -1853,6 +1927,7 @@
}
if (dummy & APC_XINT_EMPT) {
+#if 0 /* Call to stop_output from midlevel will get this */
if (!cs4231_chip->output_next_dma_handle) {
cs4231_chip->regs->dmacsr |= (APC_PPAUSE);
cs4231_disable_play(drv);
@@ -1860,6 +1935,7 @@
}
cs4231_chip->perchip_info.play.active = 0;
cs4231_playintr(drv);
+#endif
cs4231_getsamplecount(drv, cs4231_chip->playlen, 0);
}
@@ -1937,8 +2013,8 @@
cs4231_ioctl,
eb4231_start_output,
eb4231_stop_output,
- cs4231_start_input,
- cs4231_stop_input,
+ eb4231_start_input,
+ eb4231_stop_input,
cs4231_audio_getdev,
cs4231_set_output_volume,
cs4231_get_output_volume,
FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)