diff options
-rw-r--r-- | sound/soc/omap/omap-abe-dsp.c | 3 | ||||
-rw-r--r-- | sound/soc/omap/omap-mcpdm.c | 29 | ||||
-rw-r--r-- | sound/soc/omap/omap-mcpdm.h | 1 |
3 files changed, 31 insertions, 2 deletions
diff --git a/sound/soc/omap/omap-abe-dsp.c b/sound/soc/omap/omap-abe-dsp.c index c90c228..b66db25 100644 --- a/sound/soc/omap/omap-abe-dsp.c +++ b/sound/soc/omap/omap-abe-dsp.c @@ -2664,7 +2664,8 @@ static int abe_probe(struct snd_soc_platform *platform) fw_data + sizeof(struct fw_header) + abe->hdr.coeff_size, abe->hdr.firmware_size); - ret = request_irq(abe->irq, abe_irq_handler, 0, "ABE", (void *)abe); + ret = request_threaded_irq(abe->irq, NULL, abe_irq_handler, + IRQF_ONESHOT, "ABE", (void *)abe); if (ret) { dev_err(platform->dev, "request for ABE IRQ %d failed %d\n", abe->irq, ret); diff --git a/sound/soc/omap/omap-mcpdm.c b/sound/soc/omap/omap-mcpdm.c index 81e6866..d06f315 100644 --- a/sound/soc/omap/omap-mcpdm.c +++ b/sound/soc/omap/omap-mcpdm.c @@ -69,6 +69,7 @@ struct omap_mcpdm { struct mutex mutex; struct omap_mcpdm_platform_data *pdata; struct completion irq_completion; + struct delayed_work esd_work; struct abe *abe; struct omap_abe_port *dl_port; struct omap_abe_port *ul_port; @@ -397,7 +398,7 @@ static int omap_mcpdm_dai_startup(struct snd_pcm_substream *substream, omap_mcpdm_set_offset(mcpdm); omap_mcpdm_open(mcpdm); - + schedule_delayed_work(&mcpdm->esd_work, msecs_to_jiffies(250)); out: mutex_unlock(&mcpdm->mutex); return err; @@ -427,6 +428,7 @@ static void omap_mcpdm_dai_shutdown(struct snd_pcm_substream *substream, omap_mcpdm_stop(mcpdm); } + cancel_delayed_work_sync(&mcpdm->esd_work); omap_mcpdm_close(mcpdm); pm_runtime_put_sync(mcpdm->dev); @@ -542,6 +544,29 @@ static int omap_mcpdm_dai_trigger(struct snd_pcm_substream *substream, return 0; } +static void mcpdm_esd_work(struct work_struct *work) +{ + struct omap_mcpdm *mcpdm = container_of(work, struct omap_mcpdm, + esd_work.work); + + if (omap_mcpdm_read(mcpdm, MCPDM_STATUS)) { + if (mcpdm->abe_mode) { + omap_abe_port_disable(mcpdm->abe, mcpdm->dl_port); + omap_abe_port_disable(mcpdm->abe, mcpdm->ul_port); + udelay(250); + } + omap_mcpdm_stop(mcpdm); + + if (mcpdm->abe_mode) { + omap_abe_port_enable(mcpdm->abe, mcpdm->dl_port); + omap_abe_port_enable(mcpdm->abe, mcpdm->ul_port); + udelay(250); + } + omap_mcpdm_start(mcpdm); + } + schedule_delayed_work(&mcpdm->esd_work, msecs_to_jiffies(250)); +} + static struct snd_soc_dai_ops omap_mcpdm_dai_ops = { .startup = omap_mcpdm_dai_startup, .shutdown = omap_mcpdm_dai_shutdown, @@ -811,6 +836,8 @@ static __devinit int asoc_mcpdm_probe(struct platform_device *pdev) goto err_dl; #endif + INIT_DELAYED_WORK(&mcpdm->esd_work, mcpdm_esd_work); + ret = snd_soc_register_dais(&pdev->dev, omap_mcpdm_dai, ARRAY_SIZE(omap_mcpdm_dai)); if (ret < 0) diff --git a/sound/soc/omap/omap-mcpdm.h b/sound/soc/omap/omap-mcpdm.h index 79fdf30..3aa5011 100644 --- a/sound/soc/omap/omap-mcpdm.h +++ b/sound/soc/omap/omap-mcpdm.h @@ -42,6 +42,7 @@ #define MCPDM_FIFO_CTRL_DN 0x50 #define MCPDM_FIFO_CTRL_UP 0x54 #define MCPDM_DN_OFFSET 0x58 +#define MCPDM_STATUS 0x68 /* * MCPDM_IRQ bit fields |