Lines Matching +full:exynos7 +full:- +full:i2s1
3 * ALSA SoC Audio Layer - Samsung I2S Controller driver
13 #include <dt-bindings/sound/samsung-i2s.h>
17 #include <linux/clk-provider.h>
28 #include <linux/platform_data/asoc-s3c.h>
33 #include "i2s-regs.h"
110 return i2s->pri_dai ? true : false; in is_secondary()
113 /* If operating in SoC-Slave mode */
116 u32 mod = readl(i2s->addr + I2SMOD); in is_slave()
117 return (mod & (1 << i2s->variant_regs->mss_off)) ? true : false; in is_slave()
128 active = readl(i2s->addr + I2SCON); in tx_active()
141 return i2s->pri_dai ? : i2s->sec_dai; in get_other_dai()
166 active = readl(i2s->addr + I2SCON) & CON_RXDMA_ACTIVE; in rx_active()
210 if (i2s && (i2s->mode & DAI_OPENED)) in is_opened()
218 if (is_opened(i2s) && (i2s->mode & DAI_MANAGER)) in is_manager()
228 rfs = readl(i2s->addr + I2SMOD) >> i2s->variant_regs->rfs_off; in get_rfs()
229 rfs &= i2s->variant_regs->rfs_mask; in get_rfs()
246 u32 mod = readl(i2s->addr + I2SMOD); in set_rfs()
247 int rfs_shift = i2s->variant_regs->rfs_off; in set_rfs()
249 mod &= ~(i2s->variant_regs->rfs_mask << rfs_shift); in set_rfs()
278 writel(mod, i2s->addr + I2SMOD); in set_rfs()
281 /* Read Bit-Clock of I2S (in multiples of LRCLK) */
285 bfs = readl(i2s->addr + I2SMOD) >> i2s->variant_regs->bfs_off; in get_bfs()
286 bfs &= i2s->variant_regs->bfs_mask; in get_bfs()
301 /* Write Bit-Clock of I2S (in multiples of LRCLK) */
304 u32 mod = readl(i2s->addr + I2SMOD); in set_bfs()
305 int tdm = i2s->quirks & QUIRK_SUPPORTS_TDM; in set_bfs()
306 int bfs_shift = i2s->variant_regs->bfs_off; in set_bfs()
308 /* Non-TDM I2S controllers do not support BCLK > 48 * FS */ in set_bfs()
310 dev_err(&i2s->pdev->dev, "Unsupported BCLK divider\n"); in set_bfs()
314 mod &= ~(i2s->variant_regs->bfs_mask << bfs_shift); in set_bfs()
345 dev_err(&i2s->pdev->dev, "Wrong BCLK Divider!\n"); in set_bfs()
349 writel(mod, i2s->addr + I2SMOD); in set_bfs()
352 /* Sample-Size */
355 int blc = readl(i2s->addr + I2SMOD); in get_blc()
369 void __iomem *addr = i2s->addr; in i2s_txctrl()
370 int txr_off = i2s->variant_regs->txr_off; in i2s_txctrl()
419 void __iomem *addr = i2s->addr; in i2s_rxctrl()
420 int txr_off = i2s->variant_regs->txr_off; in i2s_rxctrl()
456 fic = i2s->addr + I2SFICS; in i2s_fifo()
458 fic = i2s->addr + I2SFIC; in i2s_fifo()
465 while (--val) in i2s_fifo()
476 const struct samsung_i2s_variant_regs *i2s_regs = i2s->variant_regs; in i2s_set_sysclk()
477 unsigned int cdcon_mask = 1 << i2s_regs->cdclkcon_off; in i2s_set_sysclk()
478 unsigned int rsrc_mask = 1 << i2s_regs->rclksrc_off; in i2s_set_sysclk()
483 pm_runtime_get_sync(dai->dev); in i2s_set_sysclk()
485 spin_lock_irqsave(i2s->lock, flags); in i2s_set_sysclk()
486 mod = readl(i2s->addr + I2SMOD); in i2s_set_sysclk()
487 spin_unlock_irqrestore(i2s->lock, flags); in i2s_set_sysclk()
495 mask = 1 << i2s_regs->cdclkcon_off; in i2s_set_sysclk()
500 if ((rfs && other && other->rfs && (other->rfs != rfs)) || in i2s_set_sysclk()
506 dev_err(&i2s->pdev->dev, in i2s_set_sysclk()
508 ret = -EAGAIN; in i2s_set_sysclk()
513 val = 1 << i2s_regs->cdclkcon_off; in i2s_set_sysclk()
515 i2s->rfs = rfs; in i2s_set_sysclk()
520 mask = 1 << i2s_regs->rclksrc_off; in i2s_set_sysclk()
522 if ((i2s->quirks & QUIRK_NO_MUXPSR) in i2s_set_sysclk()
529 if (i2s->op_clk && !IS_ERR(i2s->op_clk)) { in i2s_set_sysclk()
532 clk_disable_unprepare(i2s->op_clk); in i2s_set_sysclk()
533 clk_put(i2s->op_clk); in i2s_set_sysclk()
535 i2s->rclk_srcrate = in i2s_set_sysclk()
536 clk_get_rate(i2s->op_clk); in i2s_set_sysclk()
542 i2s->op_clk = clk_get(&i2s->pdev->dev, in i2s_set_sysclk()
545 i2s->op_clk = clk_get(&i2s->pdev->dev, in i2s_set_sysclk()
548 if (WARN_ON(IS_ERR(i2s->op_clk))) { in i2s_set_sysclk()
549 ret = PTR_ERR(i2s->op_clk); in i2s_set_sysclk()
550 i2s->op_clk = NULL; in i2s_set_sysclk()
554 ret = clk_prepare_enable(i2s->op_clk); in i2s_set_sysclk()
556 clk_put(i2s->op_clk); in i2s_set_sysclk()
557 i2s->op_clk = NULL; in i2s_set_sysclk()
560 i2s->rclk_srcrate = clk_get_rate(i2s->op_clk); in i2s_set_sysclk()
562 /* Over-ride the other's */ in i2s_set_sysclk()
564 other->op_clk = i2s->op_clk; in i2s_set_sysclk()
565 other->rclk_srcrate = i2s->rclk_srcrate; in i2s_set_sysclk()
569 dev_err(&i2s->pdev->dev, in i2s_set_sysclk()
571 ret = -EAGAIN; in i2s_set_sysclk()
575 i2s->op_clk = other->op_clk; in i2s_set_sysclk()
576 i2s->rclk_srcrate = other->rclk_srcrate; in i2s_set_sysclk()
581 val = 1 << i2s_regs->rclksrc_off; in i2s_set_sysclk()
584 dev_err(&i2s->pdev->dev, "We don't serve that!\n"); in i2s_set_sysclk()
585 ret = -EINVAL; in i2s_set_sysclk()
589 spin_lock_irqsave(i2s->lock, flags); in i2s_set_sysclk()
590 mod = readl(i2s->addr + I2SMOD); in i2s_set_sysclk()
592 writel(mod, i2s->addr + I2SMOD); in i2s_set_sysclk()
593 spin_unlock_irqrestore(i2s->lock, flags); in i2s_set_sysclk()
595 pm_runtime_put(dai->dev); in i2s_set_sysclk()
599 pm_runtime_put(dai->dev); in i2s_set_sysclk()
612 lrp_shift = i2s->variant_regs->lrp_off; in i2s_set_fmt()
613 sdf_shift = i2s->variant_regs->sdf_off; in i2s_set_fmt()
614 mod_slave = 1 << i2s->variant_regs->mss_off; in i2s_set_fmt()
633 dev_err(&i2s->pdev->dev, "Format not supported\n"); in i2s_set_fmt()
634 return -EINVAL; in i2s_set_fmt()
638 * INV flag is relative to the FORMAT flag - if set it simply in i2s_set_fmt()
651 dev_err(&i2s->pdev->dev, "Polarity not supported\n"); in i2s_set_fmt()
652 return -EINVAL; in i2s_set_fmt()
665 if (i2s->rclk_srcrate == 0 && i2s->clk_data.clks == NULL && in i2s_set_fmt()
666 other->clk_data.clks == NULL) in i2s_set_fmt()
671 dev_err(&i2s->pdev->dev, "master/slave format not supported\n"); in i2s_set_fmt()
672 return -EINVAL; in i2s_set_fmt()
675 pm_runtime_get_sync(dai->dev); in i2s_set_fmt()
676 spin_lock_irqsave(i2s->lock, flags); in i2s_set_fmt()
677 mod = readl(i2s->addr + I2SMOD); in i2s_set_fmt()
684 spin_unlock_irqrestore(i2s->lock, flags); in i2s_set_fmt()
685 pm_runtime_put(dai->dev); in i2s_set_fmt()
686 dev_err(&i2s->pdev->dev, in i2s_set_fmt()
688 return -EAGAIN; in i2s_set_fmt()
693 writel(mod, i2s->addr + I2SMOD); in i2s_set_fmt()
694 spin_unlock_irqrestore(i2s->lock, flags); in i2s_set_fmt()
695 pm_runtime_put(dai->dev); in i2s_set_fmt()
709 WARN_ON(!pm_runtime_active(dai->dev)); in i2s_hw_params()
722 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) in i2s_hw_params()
723 i2s->dma_playback.addr_width = 4; in i2s_hw_params()
725 i2s->dma_capture.addr_width = 4; in i2s_hw_params()
728 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) in i2s_hw_params()
729 i2s->dma_playback.addr_width = 2; in i2s_hw_params()
731 i2s->dma_capture.addr_width = 2; in i2s_hw_params()
735 dev_err(&i2s->pdev->dev, "%d channels not supported\n", in i2s_hw_params()
737 return -EINVAL; in i2s_hw_params()
774 dev_err(&i2s->pdev->dev, "Format(%d) not supported\n", in i2s_hw_params()
776 return -EINVAL; in i2s_hw_params()
779 spin_lock_irqsave(i2s->lock, flags); in i2s_hw_params()
780 mod = readl(i2s->addr + I2SMOD); in i2s_hw_params()
782 writel(mod, i2s->addr + I2SMOD); in i2s_hw_params()
783 spin_unlock_irqrestore(i2s->lock, flags); in i2s_hw_params()
785 snd_soc_dai_init_dma_data(dai, &i2s->dma_playback, &i2s->dma_capture); in i2s_hw_params()
787 i2s->frmclk = params_rate(params); in i2s_hw_params()
789 rclksrc = i2s->clk_table[CLK_I2S_RCLK_SRC]; in i2s_hw_params()
791 rclksrc = other->clk_table[CLK_I2S_RCLK_SRC]; in i2s_hw_params()
794 i2s->rclk_srcrate = clk_get_rate(rclksrc); in i2s_hw_params()
807 pm_runtime_get_sync(dai->dev); in i2s_startup()
811 i2s->mode |= DAI_OPENED; in i2s_startup()
814 i2s->mode &= ~DAI_MANAGER; in i2s_startup()
816 i2s->mode |= DAI_MANAGER; in i2s_startup()
818 if (!any_active(i2s) && (i2s->quirks & QUIRK_NEED_RSTCLR)) in i2s_startup()
819 writel(CON_RSTCLR, i2s->addr + I2SCON); in i2s_startup()
835 i2s->mode &= ~DAI_OPENED; in i2s_shutdown()
836 i2s->mode &= ~DAI_MANAGER; in i2s_shutdown()
839 other->mode |= DAI_MANAGER; in i2s_shutdown()
842 i2s->rfs = 0; in i2s_shutdown()
843 i2s->bfs = 0; in i2s_shutdown()
847 pm_runtime_put(dai->dev); in i2s_shutdown()
858 bfs = i2s->bfs; in config_setup()
861 bfs = other->bfs; in config_setup()
867 rfs = i2s->rfs; in config_setup()
870 rfs = other->rfs; in config_setup()
873 dev_err(&i2s->pdev->dev, in config_setup()
874 "%d-RFS not supported for 24-blc\n", rfs); in config_setup()
875 return -EINVAL; in config_setup()
887 dev_err(&i2s->pdev->dev, in config_setup()
889 return -EAGAIN; in config_setup()
899 if (!(i2s->quirks & QUIRK_NO_MUXPSR)) { in config_setup()
900 psr = i2s->rclk_srcrate / i2s->frmclk / rfs; in config_setup()
901 writel(((psr - 1) << 8) | PSR_PSREN, i2s->addr + I2SPSR); in config_setup()
902 dev_dbg(&i2s->pdev->dev, in config_setup()
904 i2s->rclk_srcrate, psr, rfs, bfs); in config_setup()
913 int capture = (substream->stream == SNDRV_PCM_STREAM_CAPTURE); in i2s_trigger()
914 struct snd_soc_pcm_runtime *rtd = substream->private_data; in i2s_trigger()
915 struct i2s_dai *i2s = to_info(rtd->cpu_dai); in i2s_trigger()
922 pm_runtime_get_sync(dai->dev); in i2s_trigger()
923 spin_lock_irqsave(i2s->lock, flags); in i2s_trigger()
926 spin_unlock_irqrestore(i2s->lock, flags); in i2s_trigger()
927 return -EINVAL; in i2s_trigger()
935 spin_unlock_irqrestore(i2s->lock, flags); in i2s_trigger()
940 spin_lock_irqsave(i2s->lock, flags); in i2s_trigger()
950 spin_unlock_irqrestore(i2s->lock, flags); in i2s_trigger()
951 pm_runtime_put(dai->dev); in i2s_trigger()
966 pm_runtime_get_sync(dai->dev); in i2s_set_clkdiv()
968 || (other && other->bfs && (other->bfs != div))) { in i2s_set_clkdiv()
969 pm_runtime_put(dai->dev); in i2s_set_clkdiv()
970 dev_err(&i2s->pdev->dev, in i2s_set_clkdiv()
972 return -EAGAIN; in i2s_set_clkdiv()
974 i2s->bfs = div; in i2s_set_clkdiv()
975 pm_runtime_put(dai->dev); in i2s_set_clkdiv()
978 dev_err(&i2s->pdev->dev, in i2s_set_clkdiv()
980 return -EINVAL; in i2s_set_clkdiv()
990 u32 reg = readl(i2s->addr + I2SFIC); in i2s_delay()
992 const struct samsung_i2s_variant_regs *i2s_regs = i2s->variant_regs; in i2s_delay()
994 WARN_ON(!pm_runtime_active(dai->dev)); in i2s_delay()
996 if (substream->stream == SNDRV_PCM_STREAM_CAPTURE) in i2s_delay()
999 delay = FICS_TXCOUNT(readl(i2s->addr + I2SFICS)); in i2s_delay()
1001 delay = (reg >> i2s_regs->ftx0cnt_off) & 0x7f; in i2s_delay()
1009 return pm_runtime_force_suspend(dai->dev); in i2s_suspend()
1014 return pm_runtime_force_resume(dai->dev); in i2s_resume()
1027 pm_runtime_get_sync(dai->dev); in samsung_i2s_dai_probe()
1030 snd_soc_dai_init_dma_data(dai, &other->sec_dai->dma_playback, in samsung_i2s_dai_probe()
1033 snd_soc_dai_init_dma_data(dai, &i2s->dma_playback, in samsung_i2s_dai_probe()
1034 &i2s->dma_capture); in samsung_i2s_dai_probe()
1036 if (i2s->quirks & QUIRK_NEED_RSTCLR) in samsung_i2s_dai_probe()
1037 writel(CON_RSTCLR, i2s->addr + I2SCON); in samsung_i2s_dai_probe()
1039 if (i2s->quirks & QUIRK_SUPPORTS_IDMA) in samsung_i2s_dai_probe()
1040 idma_reg_addr_init(i2s->addr, in samsung_i2s_dai_probe()
1041 i2s->sec_dai->idma_playback.addr); in samsung_i2s_dai_probe()
1045 i2s->rfs = 0; in samsung_i2s_dai_probe()
1046 i2s->bfs = 0; in samsung_i2s_dai_probe()
1047 i2s->rclk_srcrate = 0; in samsung_i2s_dai_probe()
1049 spin_lock_irqsave(i2s->lock, flags); in samsung_i2s_dai_probe()
1055 spin_unlock_irqrestore(i2s->lock, flags); in samsung_i2s_dai_probe()
1061 pm_runtime_put(dai->dev); in samsung_i2s_dai_probe()
1071 pm_runtime_get_sync(dai->dev); in samsung_i2s_dai_remove()
1074 if (i2s->quirks & QUIRK_NEED_RSTCLR) { in samsung_i2s_dai_remove()
1075 spin_lock_irqsave(i2s->lock, flags); in samsung_i2s_dai_remove()
1076 writel(0, i2s->addr + I2SCON); in samsung_i2s_dai_remove()
1077 spin_unlock_irqrestore(i2s->lock, flags); in samsung_i2s_dai_remove()
1081 pm_runtime_put(dai->dev); in samsung_i2s_dai_remove()
1098 .name = "samsung-i2s",
1111 i2s = devm_kzalloc(&pdev->dev, sizeof(struct i2s_dai), GFP_KERNEL); in i2s_alloc_dai()
1115 i2s->pdev = pdev; in i2s_alloc_dai()
1116 i2s->pri_dai = NULL; in i2s_alloc_dai()
1117 i2s->sec_dai = NULL; in i2s_alloc_dai()
1118 i2s->i2s_dai_drv.id = 1; in i2s_alloc_dai()
1119 i2s->i2s_dai_drv.symmetric_rates = 1; in i2s_alloc_dai()
1120 i2s->i2s_dai_drv.probe = samsung_i2s_dai_probe; in i2s_alloc_dai()
1121 i2s->i2s_dai_drv.remove = samsung_i2s_dai_remove; in i2s_alloc_dai()
1122 i2s->i2s_dai_drv.ops = &samsung_i2s_dai_ops; in i2s_alloc_dai()
1123 i2s->i2s_dai_drv.suspend = i2s_suspend; in i2s_alloc_dai()
1124 i2s->i2s_dai_drv.resume = i2s_resume; in i2s_alloc_dai()
1125 i2s->i2s_dai_drv.playback.channels_min = 1; in i2s_alloc_dai()
1126 i2s->i2s_dai_drv.playback.channels_max = 2; in i2s_alloc_dai()
1127 i2s->i2s_dai_drv.playback.rates = i2s_dai_data->pcm_rates; in i2s_alloc_dai()
1128 i2s->i2s_dai_drv.playback.formats = SAMSUNG_I2S_FMTS; in i2s_alloc_dai()
1131 i2s->i2s_dai_drv.name = SAMSUNG_I2S_DAI; in i2s_alloc_dai()
1132 i2s->i2s_dai_drv.capture.channels_min = 1; in i2s_alloc_dai()
1133 i2s->i2s_dai_drv.capture.channels_max = 2; in i2s_alloc_dai()
1134 i2s->i2s_dai_drv.capture.rates = i2s_dai_data->pcm_rates; in i2s_alloc_dai()
1135 i2s->i2s_dai_drv.capture.formats = SAMSUNG_I2S_FMTS; in i2s_alloc_dai()
1137 i2s->i2s_dai_drv.name = SAMSUNG_I2S_DAI_SEC; in i2s_alloc_dai()
1147 i2s->suspend_i2smod = readl(i2s->addr + I2SMOD); in i2s_runtime_suspend()
1148 i2s->suspend_i2scon = readl(i2s->addr + I2SCON); in i2s_runtime_suspend()
1149 i2s->suspend_i2spsr = readl(i2s->addr + I2SPSR); in i2s_runtime_suspend()
1151 if (i2s->op_clk) in i2s_runtime_suspend()
1152 clk_disable_unprepare(i2s->op_clk); in i2s_runtime_suspend()
1153 clk_disable_unprepare(i2s->clk); in i2s_runtime_suspend()
1163 ret = clk_prepare_enable(i2s->clk); in i2s_runtime_resume()
1167 if (i2s->op_clk) { in i2s_runtime_resume()
1168 ret = clk_prepare_enable(i2s->op_clk); in i2s_runtime_resume()
1170 clk_disable_unprepare(i2s->clk); in i2s_runtime_resume()
1175 writel(i2s->suspend_i2scon, i2s->addr + I2SCON); in i2s_runtime_resume()
1176 writel(i2s->suspend_i2smod, i2s->addr + I2SMOD); in i2s_runtime_resume()
1177 writel(i2s->suspend_i2spsr, i2s->addr + I2SPSR); in i2s_runtime_resume()
1187 for (i = 0; i < i2s->clk_data.clk_num; i++) { in i2s_unregister_clocks()
1188 if (!IS_ERR(i2s->clk_table[i])) in i2s_unregister_clocks()
1189 clk_unregister(i2s->clk_table[i]); in i2s_unregister_clocks()
1195 struct i2s_dai *i2s = dev_get_drvdata(&pdev->dev); in i2s_unregister_clock_provider()
1197 of_clk_del_provider(pdev->dev.of_node); in i2s_unregister_clock_provider()
1206 struct device *dev = &pdev->dev; in i2s_register_clock_provider()
1208 const struct samsung_i2s_variant_regs *reg_info = i2s->variant_regs; in i2s_register_clock_provider()
1214 if (!of_find_property(dev->of_node, "#clock-cells", NULL)) in i2s_register_clock_provider()
1230 return -ENOMEM; in i2s_register_clock_provider()
1233 if (!(i2s->quirks & QUIRK_NO_MUXPSR)) { in i2s_register_clock_provider()
1235 u32 val = readl(i2s->addr + I2SPSR); in i2s_register_clock_provider()
1236 writel(val | PSR_PSREN, i2s->addr + I2SPSR); in i2s_register_clock_provider()
1238 i2s->clk_table[CLK_I2S_RCLK_SRC] = clk_register_mux(dev, in i2s_register_clock_provider()
1242 i2s->addr + I2SMOD, reg_info->rclksrc_off, in i2s_register_clock_provider()
1243 1, 0, i2s->lock); in i2s_register_clock_provider()
1245 i2s->clk_table[CLK_I2S_RCLK_PSR] = clk_register_divider(dev, in i2s_register_clock_provider()
1249 i2s->addr + I2SPSR, 8, 6, 0, i2s->lock); in i2s_register_clock_provider()
1252 i2s->clk_data.clk_num = 2; in i2s_register_clock_provider()
1255 i2s->clk_table[CLK_I2S_CDCLK] = clk_register_gate(dev, in i2s_register_clock_provider()
1258 i2s->addr + I2SMOD, reg_info->cdclkcon_off, in i2s_register_clock_provider()
1259 CLK_GATE_SET_TO_DISABLE, i2s->lock); in i2s_register_clock_provider()
1261 i2s->clk_data.clk_num += 1; in i2s_register_clock_provider()
1262 i2s->clk_data.clks = i2s->clk_table; in i2s_register_clock_provider()
1264 ret = of_clk_add_provider(dev->of_node, of_clk_src_onecell_get, in i2s_register_clock_provider()
1265 &i2s->clk_data); in i2s_register_clock_provider()
1277 struct s3c_audio_pdata *i2s_pdata = pdev->dev.platform_data; in samsung_i2s_probe()
1280 struct device_node *np = pdev->dev.of_node; in samsung_i2s_probe()
1284 if (IS_ENABLED(CONFIG_OF) && pdev->dev.of_node) in samsung_i2s_probe()
1285 i2s_dai_data = of_device_get_match_data(&pdev->dev); in samsung_i2s_probe()
1288 platform_get_device_id(pdev)->driver_data; in samsung_i2s_probe()
1292 dev_err(&pdev->dev, "Unable to alloc I2S_pri\n"); in samsung_i2s_probe()
1293 return -ENOMEM; in samsung_i2s_probe()
1296 spin_lock_init(&pri_dai->spinlock); in samsung_i2s_probe()
1297 pri_dai->lock = &pri_dai->spinlock; in samsung_i2s_probe()
1301 dev_err(&pdev->dev, "Can't work without s3c_audio_pdata\n"); in samsung_i2s_probe()
1302 return -EINVAL; in samsung_i2s_probe()
1305 pri_dai->dma_playback.filter_data = i2s_pdata->dma_playback; in samsung_i2s_probe()
1306 pri_dai->dma_capture.filter_data = i2s_pdata->dma_capture; in samsung_i2s_probe()
1307 pri_dai->filter = i2s_pdata->dma_filter; in samsung_i2s_probe()
1309 quirks = i2s_pdata->type.quirks; in samsung_i2s_probe()
1310 idma_addr = i2s_pdata->type.idma_addr; in samsung_i2s_probe()
1312 quirks = i2s_dai_data->quirks; in samsung_i2s_probe()
1313 if (of_property_read_u32(np, "samsung,idma-addr", in samsung_i2s_probe()
1316 dev_info(&pdev->dev, "idma address is not"\ in samsung_i2s_probe()
1324 pri_dai->addr = devm_ioremap_resource(&pdev->dev, res); in samsung_i2s_probe()
1325 if (IS_ERR(pri_dai->addr)) in samsung_i2s_probe()
1326 return PTR_ERR(pri_dai->addr); in samsung_i2s_probe()
1328 regs_base = res->start; in samsung_i2s_probe()
1330 pri_dai->clk = devm_clk_get(&pdev->dev, "iis"); in samsung_i2s_probe()
1331 if (IS_ERR(pri_dai->clk)) { in samsung_i2s_probe()
1332 dev_err(&pdev->dev, "Failed to get iis clock\n"); in samsung_i2s_probe()
1333 return PTR_ERR(pri_dai->clk); in samsung_i2s_probe()
1336 ret = clk_prepare_enable(pri_dai->clk); in samsung_i2s_probe()
1338 dev_err(&pdev->dev, "failed to enable clock: %d\n", ret); in samsung_i2s_probe()
1341 pri_dai->dma_playback.addr = regs_base + I2STXD; in samsung_i2s_probe()
1342 pri_dai->dma_capture.addr = regs_base + I2SRXD; in samsung_i2s_probe()
1343 pri_dai->dma_playback.chan_name = "tx"; in samsung_i2s_probe()
1344 pri_dai->dma_capture.chan_name = "rx"; in samsung_i2s_probe()
1345 pri_dai->dma_playback.addr_width = 4; in samsung_i2s_probe()
1346 pri_dai->dma_capture.addr_width = 4; in samsung_i2s_probe()
1347 pri_dai->quirks = quirks; in samsung_i2s_probe()
1348 pri_dai->variant_regs = i2s_dai_data->i2s_variant_regs; in samsung_i2s_probe()
1351 pri_dai->i2s_dai_drv.playback.channels_max = 6; in samsung_i2s_probe()
1353 ret = samsung_asoc_dma_platform_register(&pdev->dev, pri_dai->filter, in samsung_i2s_probe()
1358 ret = devm_snd_soc_register_component(&pdev->dev, in samsung_i2s_probe()
1360 &pri_dai->i2s_dai_drv, 1); in samsung_i2s_probe()
1367 dev_err(&pdev->dev, "Unable to alloc I2S_sec\n"); in samsung_i2s_probe()
1368 ret = -ENOMEM; in samsung_i2s_probe()
1372 sec_dai->lock = &pri_dai->spinlock; in samsung_i2s_probe()
1373 sec_dai->variant_regs = pri_dai->variant_regs; in samsung_i2s_probe()
1374 sec_dai->dma_playback.addr = regs_base + I2STXDS; in samsung_i2s_probe()
1375 sec_dai->dma_playback.chan_name = "tx-sec"; in samsung_i2s_probe()
1378 sec_dai->dma_playback.filter_data = i2s_pdata->dma_play_sec; in samsung_i2s_probe()
1379 sec_dai->filter = i2s_pdata->dma_filter; in samsung_i2s_probe()
1382 sec_dai->dma_playback.addr_width = 4; in samsung_i2s_probe()
1383 sec_dai->addr = pri_dai->addr; in samsung_i2s_probe()
1384 sec_dai->clk = pri_dai->clk; in samsung_i2s_probe()
1385 sec_dai->quirks = quirks; in samsung_i2s_probe()
1386 sec_dai->idma_playback.addr = idma_addr; in samsung_i2s_probe()
1387 sec_dai->pri_dai = pri_dai; in samsung_i2s_probe()
1388 pri_dai->sec_dai = sec_dai; in samsung_i2s_probe()
1390 ret = samsung_asoc_dma_platform_register(&pdev->dev, in samsung_i2s_probe()
1391 sec_dai->filter, "tx-sec", NULL); in samsung_i2s_probe()
1395 ret = devm_snd_soc_register_component(&pdev->dev, in samsung_i2s_probe()
1397 &sec_dai->i2s_dai_drv, 1); in samsung_i2s_probe()
1402 if (i2s_pdata && i2s_pdata->cfg_gpio && i2s_pdata->cfg_gpio(pdev)) { in samsung_i2s_probe()
1403 dev_err(&pdev->dev, "Unable to configure gpio\n"); in samsung_i2s_probe()
1404 ret = -EINVAL; in samsung_i2s_probe()
1408 dev_set_drvdata(&pdev->dev, pri_dai); in samsung_i2s_probe()
1410 pm_runtime_set_active(&pdev->dev); in samsung_i2s_probe()
1411 pm_runtime_enable(&pdev->dev); in samsung_i2s_probe()
1417 pri_dai->op_clk = clk_get_parent(pri_dai->clk_table[CLK_I2S_RCLK_SRC]); in samsung_i2s_probe()
1422 pm_runtime_disable(&pdev->dev); in samsung_i2s_probe()
1424 clk_disable_unprepare(pri_dai->clk); in samsung_i2s_probe()
1432 pri_dai = dev_get_drvdata(&pdev->dev); in samsung_i2s_remove()
1434 pm_runtime_get_sync(&pdev->dev); in samsung_i2s_remove()
1435 pm_runtime_disable(&pdev->dev); in samsung_i2s_remove()
1438 clk_disable_unprepare(pri_dai->clk); in samsung_i2s_remove()
1439 pm_runtime_put_noidle(&pdev->dev); in samsung_i2s_remove()
1535 .name = "samsung-i2s",
1545 .compatible = "samsung,s3c6410-i2s",
1548 .compatible = "samsung,s5pv210-i2s",
1551 .compatible = "samsung,exynos5420-i2s",
1554 .compatible = "samsung,exynos7-i2s",
1557 .compatible = "samsung,exynos7-i2s1",
1577 .name = "samsung-i2s",
1588 MODULE_ALIAS("platform:samsung-i2s");