u8 i2s_mode;
bool use_dma;
bool use_dual_fifo;
+ bool has_ipg_clk_name;
unsigned int fifo_depth;
struct fsl_ssi_rxtx_reg_val rxtx_reg_val;
struct snd_soc_pcm_runtime *rtd = substream->private_data;
struct fsl_ssi_private *ssi_private =
snd_soc_dai_get_drvdata(rtd->cpu_dai);
+ int ret;
+
+ ret = clk_prepare_enable(ssi_private->clk);
+ if (ret)
+ return ret;
/* When using dual fifo mode, it is safer to ensure an even period
* size. If appearing to an odd number while DMA always starts its
return 0;
}
+/**
+ * fsl_ssi_shutdown: shutdown the SSI
+ *
+ */
+static void fsl_ssi_shutdown(struct snd_pcm_substream *substream,
+ struct snd_soc_dai *dai)
+{
+ struct snd_soc_pcm_runtime *rtd = substream->private_data;
+ struct fsl_ssi_private *ssi_private =
+ snd_soc_dai_get_drvdata(rtd->cpu_dai);
+
+ clk_disable_unprepare(ssi_private->clk);
+
+}
+
/**
* fsl_ssi_set_bclk - configure Digital Audio Interface bit clock
*
static const struct snd_soc_dai_ops fsl_ssi_dai_ops = {
.startup = fsl_ssi_startup,
+ .shutdown = fsl_ssi_shutdown,
.hw_params = fsl_ssi_hw_params,
.hw_free = fsl_ssi_hw_free,
.set_fmt = fsl_ssi_set_dai_fmt,
u32 dmas[4];
int ret;
- ssi_private->clk = devm_clk_get(&pdev->dev, NULL);
+ if (ssi_private->has_ipg_clk_name)
+ ssi_private->clk = devm_clk_get(&pdev->dev, "ipg");
+ else
+ ssi_private->clk = devm_clk_get(&pdev->dev, NULL);
if (IS_ERR(ssi_private->clk)) {
ret = PTR_ERR(ssi_private->clk);
dev_err(&pdev->dev, "could not get clock: %d\n", ret);
return ret;
}
- ret = clk_prepare_enable(ssi_private->clk);
- if (ret) {
- dev_err(&pdev->dev, "clk_prepare_enable failed: %d\n", ret);
- return ret;
+ if (!ssi_private->has_ipg_clk_name) {
+ ret = clk_prepare_enable(ssi_private->clk);
+ if (ret) {
+ dev_err(&pdev->dev, "clk_prepare_enable failed: %d\n", ret);
+ return ret;
+ }
}
/* For those SLAVE implementations, we ingore non-baudclk cases
return 0;
error_pcm:
- clk_disable_unprepare(ssi_private->clk);
+ if (!ssi_private->has_ipg_clk_name)
+ clk_disable_unprepare(ssi_private->clk);
return ret;
}
{
if (!ssi_private->use_dma)
imx_pcm_fiq_exit(pdev);
- clk_disable_unprepare(ssi_private->clk);
+ if (!ssi_private->has_ipg_clk_name)
+ clk_disable_unprepare(ssi_private->clk);
}
static int fsl_ssi_probe(struct platform_device *pdev)
return -ENOMEM;
}
- ssi_private->regs = devm_regmap_init_mmio(&pdev->dev, iomem,
+ ret = of_property_match_string(np, "clock-names", "ipg");
+ if (ret < 0) {
+ ssi_private->has_ipg_clk_name = false;
+ ssi_private->regs = devm_regmap_init_mmio(&pdev->dev, iomem,
&fsl_ssi_regconfig);
+ } else {
+ ssi_private->has_ipg_clk_name = true;
+ ssi_private->regs = devm_regmap_init_mmio_clk(&pdev->dev,
+ "ipg", iomem, &fsl_ssi_regconfig);
+ }
if (IS_ERR(ssi_private->regs)) {
dev_err(&pdev->dev, "Failed to init register map\n");
return PTR_ERR(ssi_private->regs);