static int omap_mcbsp_dai_startup(struct snd_pcm_substream *substream, struct snd_soc_dai *dai) { struct snd_soc_pcm_runtime *rtd = substream->private_data; struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai; struct omap_mcbsp_data *mcbsp_data = to_mcbsp(cpu_dai->private_data); int err = 0; if (cpu_is_omap343x() && mcbsp_data->bus_id == 1) { /* * McBSP2 in OMAP3 has 1024 * 32-bit internal audio buffer. * Set constraint for minimum buffer size to the same than FIFO * size in order to avoid underruns in playback startup because * HW is keeping the DMA request active until FIFO is filled. */ if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) snd_pcm_hw_constraint_minmax(substream->runtime, SNDRV_PCM_HW_PARAM_BUFFER_BYTES, 4096, UINT_MAX); else snd_pcm_hw_constraint_minmax(substream->runtime, SNDRV_PCM_HW_PARAM_BUFFER_BYTES, 1024, UINT_MAX); } if (!cpu_dai->active) { err = omap_mcbsp_request(mcbsp_data->bus_id); cpu_dai->active = 1; } return err; }
static int omap_mcbsp_dai_startup(struct snd_pcm_substream *substream, struct snd_soc_dai *cpu_dai) { struct omap_mcbsp_data *mcbsp_data = snd_soc_dai_get_drvdata(cpu_dai); int bus_id = mcbsp_data->bus_id; int err = 0; if (!cpu_dai->active) err = omap_mcbsp_request(bus_id); /* * OMAP3 McBSP FIFO is word structured. * McBSP2 has 1024 + 256 = 1280 word long buffer, * McBSP1,3,4,5 has 128 word long buffer * This means that the size of the FIFO depends on the sample format. * For example on McBSP3: * 16bit samples: size is 128 * 2 = 256 bytes * 32bit samples: size is 128 * 4 = 512 bytes * It is simpler to place constraint for buffer and period based on * channels. * McBSP3 as example again (16 or 32 bit samples): * 1 channel (mono): size is 128 frames (128 words) * 2 channels (stereo): size is 128 / 2 = 64 frames (2 * 64 words) * 4 channels: size is 128 / 4 = 32 frames (4 * 32 words) */ if (cpu_is_omap34xx() || cpu_is_omap44xx()) { /* * Rule for the buffer size. We should not allow * smaller buffer than the FIFO size to avoid underruns */ } return err; }
/* * ======== dsp_clk_enable ======== * Purpose: * Enable Clock . * */ int dsp_clk_enable(enum dsp_clk_id clk_id) { int status = 0; if (is_dsp_clk_active(dsp_clocks, clk_id)) { dev_err(bridge, "WARN: clock id %d already enabled\n", clk_id); goto out; } switch (get_clk_type(clk_id)) { case IVA2_CLK: clk_enable(iva2_clk); break; case GPT_CLK: timer[clk_id - 1] = omap_dm_timer_request_specific(DMT_ID(clk_id)); break; #ifdef CONFIG_OMAP_MCBSP case MCBSP_CLK: mcbsp_clk_prepare(true, clk_id); omap_mcbsp_set_io_type(MCBSP_ID(clk_id), OMAP_MCBSP_POLL_IO); omap_mcbsp_request(MCBSP_ID(clk_id)); break; #endif case WDT_CLK: dev_err(bridge, "ERROR: DSP requested to enable WDT3 clk\n"); break; case SSI_CLK: clk_enable(ssi.sst_fck); clk_enable(ssi.ssr_fck); clk_enable(ssi.ick); /* * The SSI module need to configured not to have the Forced * idle for master interface. If it is set to forced idle, * the SSI module is transitioning to standby thereby causing * the client in the DSP hang waiting for the SSI module to * be active after enabling the clocks */ ssi_clk_prepare(true); break; default: dev_err(bridge, "Invalid clock id for enable\n"); status = -EPERM; } if (!status) set_dsp_clk_active(&dsp_clocks, clk_id); out: return status; }
static int omap_mcbsp_dai_startup(struct snd_pcm_substream *substream, struct snd_soc_dai *cpu_dai) { struct omap_mcbsp *mcbsp = snd_soc_dai_get_drvdata(cpu_dai); int err = 0; if (!cpu_dai->active) err = omap_mcbsp_request(mcbsp); /* * OMAP3 McBSP FIFO is word structured. * McBSP2 has 1024 + 256 = 1280 word long buffer, * McBSP1,3,4,5 has 128 word long buffer * This means that the size of the FIFO depends on the sample format. * For example on McBSP3: * 16bit samples: size is 128 * 2 = 256 bytes * 32bit samples: size is 128 * 4 = 512 bytes * It is simpler to place constraint for buffer and period based on * channels. * McBSP3 as example again (16 or 32 bit samples): * 1 channel (mono): size is 128 frames (128 words) * 2 channels (stereo): size is 128 / 2 = 64 frames (2 * 64 words) * 4 channels: size is 128 / 4 = 32 frames (4 * 32 words) */ if (mcbsp->pdata->buffer_size) { /* * Rule for the buffer size. We should not allow * smaller buffer than the FIFO size to avoid underruns. * This applies only for the playback stream. */ if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) snd_pcm_hw_rule_add(substream->runtime, 0, SNDRV_PCM_HW_PARAM_BUFFER_SIZE, omap_mcbsp_hwrule_min_buffersize, mcbsp, SNDRV_PCM_HW_PARAM_CHANNELS, -1); /* Make sure, that the period size is always even */ snd_pcm_hw_constraint_step(substream->runtime, 0, SNDRV_PCM_HW_PARAM_PERIOD_SIZE, 2); } snd_soc_dai_set_dma_data(cpu_dai, substream, &mcbsp->dma_data[substream->stream]); return err; }
static int omap_mcbsp_dai_startup(struct snd_pcm_substream *substream, struct snd_soc_dai *cpu_dai) { struct omap_mcbsp_data *mcbsp_data = snd_soc_dai_get_drvdata(cpu_dai); int bus_id = mcbsp_data->bus_id; int err = 0; if (!cpu_dai->active) { err = omap_mcbsp_request(bus_id); cpu_dai->active = 1; } /* * OMAP3 McBSP FIFO is word structured. * McBSP2 has 1024 + 256 = 1280 word long buffer, * McBSP1,3,4,5 has 128 word long buffer * This means that the size of the FIFO depends on the sample format. * For example on McBSP3: * 16bit samples: size is 128 * 2 = 256 bytes * 32bit samples: size is 128 * 4 = 512 bytes * It is simpler to place constraint for buffer and period based on * channels. * McBSP3 as example again (16 or 32 bit samples): * 1 channel (mono): size is 128 frames (128 words) * 2 channels (stereo): size is 128 / 2 = 64 frames (2 * 64 words) * 4 channels: size is 128 / 4 = 32 frames (4 * 32 words) */ if (cpu_is_omap34xx() || cpu_is_omap44xx()) { /* * Rule for the buffer size. We should not allow * smaller buffer than the FIFO size to avoid underruns */ #if 0 // FIXME: All BE must support hw_rules and constraints */ snd_pcm_hw_rule_add(substream->runtime, 0, SNDRV_PCM_HW_PARAM_CHANNELS, omap_mcbsp_hwrule_min_buffersize, mcbsp_data, SNDRV_PCM_HW_PARAM_BUFFER_SIZE, -1); /* Make sure, that the period size is always even */ snd_pcm_hw_constraint_step(substream->runtime, 0, SNDRV_PCM_HW_PARAM_PERIOD_SIZE, 2); #endif } return err; }
static void init_system(void) { omap_mcbsp_request(OMAP_MCBSP3); omap_mcbsp_stop(OMAP_MCBSP3); }