forked from ~ljy/RK356X_SDK_RELEASE

hc
2024-09-20 cf4ce59b3b70238352c7f1729f0f7223214828ad
kernel/sound/soc/rockchip/rockchip_i2s.c
....@@ -1,13 +1,10 @@
1
+// SPDX-License-Identifier: GPL-2.0-only
12 /* sound/soc/rockchip/rockchip_i2s.c
23 *
34 * ALSA SoC Audio Layer - Rockchip I2S Controller driver
45 *
56 * Copyright (c) 2014 Rockchip Electronics Co. Ltd.
67 * Author: Jianqun <jay.xu@rock-chips.com>
7
- *
8
- * This program is free software; you can redistribute it and/or modify
9
- * it under the terms of the GNU General Public License version 2 as
10
- * published by the Free Software Foundation.
118 */
129
1310 #include <linux/module.h>
....@@ -19,17 +16,25 @@
1916 #include <linux/clk/rockchip.h>
2017 #include <linux/pm_runtime.h>
2118 #include <linux/regmap.h>
22
-#include <linux/reset.h>
2319 #include <linux/spinlock.h>
2420 #include <sound/pcm_params.h>
2521 #include <sound/dmaengine_pcm.h>
2622
2723 #include "rockchip_i2s.h"
24
+#include "rockchip_dlp_pcm.h"
25
+#include "rockchip_utils.h"
2826
2927 #define DRV_NAME "rockchip-i2s"
3028
3129 #define CLK_PPM_MIN (-1000)
3230 #define CLK_PPM_MAX (1000)
31
+
32
+#define DEFAULT_MCLK_FS 256
33
+#define DEFAULT_FS 48000
34
+
35
+#define WAIT_TIME_MS_MAX 10000
36
+
37
+#define QUIRK_ALWAYS_ON BIT(0)
3338
3439 struct rk_i2s_pins {
3540 u32 reg_offset;
....@@ -48,8 +53,12 @@
4853
4954 struct regmap *regmap;
5055 struct regmap *grf;
51
- struct reset_control *reset_m;
52
- struct reset_control *reset_h;
56
+
57
+ struct snd_pcm_substream *substreams[SNDRV_PCM_STREAM_LAST + 1];
58
+ unsigned int wait_time[SNDRV_PCM_STREAM_LAST + 1];
59
+
60
+ bool has_capture;
61
+ bool has_playback;
5362
5463 /*
5564 * Used to indicate the tx/rx status.
....@@ -60,7 +69,8 @@
6069 bool rx_start;
6170 bool is_master_mode;
6271 const struct rk_i2s_pins *pins;
63
- unsigned int bclk_fs;
72
+ unsigned int bclk_ratio;
73
+ spinlock_t lock; /* tx/rx lock */
6474 unsigned int clk_trcm;
6575
6676 unsigned int mclk_root_rate;
....@@ -68,10 +78,18 @@
6878 int clk_ppm;
6979 bool mclk_calibrate;
7080
81
+ unsigned int quirks;
7182 };
7283
73
-/* txctrl/rxctrl lock */
74
-static DEFINE_SPINLOCK(lock);
84
+static struct i2s_of_quirks {
85
+ char *quirk;
86
+ int id;
87
+} of_quirks[] = {
88
+ {
89
+ .quirk = "rockchip,always-on",
90
+ .id = QUIRK_ALWAYS_ON,
91
+ },
92
+};
7593
7694 static int i2s_runtime_suspend(struct device *dev)
7795 {
....@@ -109,27 +127,44 @@
109127 return snd_soc_dai_get_drvdata(dai);
110128 }
111129
112
-static void rockchip_i2s_reset(struct rk_i2s_dev *i2s)
130
+static int rockchip_i2s_clear(struct rk_i2s_dev *i2s)
113131 {
114
- if (!IS_ERR(i2s->reset_m))
115
- reset_control_assert(i2s->reset_m);
116
- if (!IS_ERR(i2s->reset_h))
117
- reset_control_assert(i2s->reset_h);
118
- udelay(1);
119
- if (!IS_ERR(i2s->reset_m))
120
- reset_control_deassert(i2s->reset_m);
121
- if (!IS_ERR(i2s->reset_h))
122
- reset_control_deassert(i2s->reset_h);
123
- regcache_mark_dirty(i2s->regmap);
124
- regcache_sync(i2s->regmap);
132
+ unsigned int clr = I2S_CLR_TXC | I2S_CLR_RXC;
133
+ unsigned int val = 0;
134
+ int ret;
135
+
136
+ /*
137
+ * Workaround for FIFO clear on SLAVE mode:
138
+ *
139
+ * A Suggest to do reset hclk domain and then do mclk
140
+ * domain, especially for SLAVE mode without CLK in.
141
+ * at last, recovery regmap config.
142
+ *
143
+ * B Suggest to switch to MASTER, and then do FIFO clr,
144
+ * at last, bring back to SLAVE.
145
+ *
146
+ * Now we choose plan B here.
147
+ */
148
+ if (!i2s->is_master_mode)
149
+ regmap_update_bits(i2s->regmap, I2S_CKR,
150
+ I2S_CKR_MSS_MASK, I2S_CKR_MSS_MASTER);
151
+ regmap_update_bits(i2s->regmap, I2S_CLR, clr, clr);
152
+
153
+ ret = regmap_read_poll_timeout_atomic(i2s->regmap, I2S_CLR, val,
154
+ !(val & clr), 10, 100);
155
+ if (!i2s->is_master_mode)
156
+ regmap_update_bits(i2s->regmap, I2S_CKR,
157
+ I2S_CKR_MSS_MASK, I2S_CKR_MSS_SLAVE);
158
+ if (ret < 0)
159
+ dev_warn(i2s->dev, "failed to clear fifo on %s mode\n",
160
+ i2s->is_master_mode ? "master" : "slave");
161
+
162
+ return ret;
125163 }
126164
127165 static void rockchip_snd_txctrl(struct rk_i2s_dev *i2s, int on)
128166 {
129
- unsigned int val = 0;
130
- int retry = 10;
131
-
132
- spin_lock(&lock);
167
+ spin_lock(&i2s->lock);
133168 if (on) {
134169 regmap_update_bits(i2s->regmap, I2S_DMACR,
135170 I2S_DMACR_TDE_ENABLE, I2S_DMACR_TDE_ENABLE);
....@@ -145,7 +180,7 @@
145180 regmap_update_bits(i2s->regmap, I2S_DMACR,
146181 I2S_DMACR_TDE_ENABLE, I2S_DMACR_TDE_DISABLE);
147182
148
- if (!i2s->rx_start) {
183
+ if (!i2s->rx_start && !(i2s->quirks & QUIRK_ALWAYS_ON)) {
149184 regmap_update_bits(i2s->regmap, I2S_XFER,
150185 I2S_XFER_TXS_START |
151186 I2S_XFER_RXS_START,
....@@ -153,33 +188,15 @@
153188 I2S_XFER_RXS_STOP);
154189
155190 udelay(150);
156
- regmap_update_bits(i2s->regmap, I2S_CLR,
157
- I2S_CLR_TXC | I2S_CLR_RXC,
158
- I2S_CLR_TXC | I2S_CLR_RXC);
159
-
160
- regmap_read(i2s->regmap, I2S_CLR, &val);
161
-
162
- /* Should wait for clear operation to finish */
163
- while (val) {
164
- regmap_read(i2s->regmap, I2S_CLR, &val);
165
- retry--;
166
- if (!retry) {
167
- dev_warn(i2s->dev, "reset\n");
168
- rockchip_i2s_reset(i2s);
169
- break;
170
- }
171
- }
191
+ rockchip_i2s_clear(i2s);
172192 }
173193 }
174
- spin_unlock(&lock);
194
+ spin_unlock(&i2s->lock);
175195 }
176196
177197 static void rockchip_snd_rxctrl(struct rk_i2s_dev *i2s, int on)
178198 {
179
- unsigned int val = 0;
180
- int retry = 10;
181
-
182
- spin_lock(&lock);
199
+ spin_lock(&i2s->lock);
183200 if (on) {
184201 regmap_update_bits(i2s->regmap, I2S_DMACR,
185202 I2S_DMACR_RDE_ENABLE, I2S_DMACR_RDE_ENABLE);
....@@ -195,7 +212,7 @@
195212 regmap_update_bits(i2s->regmap, I2S_DMACR,
196213 I2S_DMACR_RDE_ENABLE, I2S_DMACR_RDE_DISABLE);
197214
198
- if (!i2s->tx_start) {
215
+ if (!i2s->tx_start && !(i2s->quirks & QUIRK_ALWAYS_ON)) {
199216 regmap_update_bits(i2s->regmap, I2S_XFER,
200217 I2S_XFER_TXS_START |
201218 I2S_XFER_RXS_START,
....@@ -203,25 +220,10 @@
203220 I2S_XFER_RXS_STOP);
204221
205222 udelay(150);
206
- regmap_update_bits(i2s->regmap, I2S_CLR,
207
- I2S_CLR_TXC | I2S_CLR_RXC,
208
- I2S_CLR_TXC | I2S_CLR_RXC);
209
-
210
- regmap_read(i2s->regmap, I2S_CLR, &val);
211
-
212
- /* Should wait for clear operation to finish */
213
- while (val) {
214
- regmap_read(i2s->regmap, I2S_CLR, &val);
215
- retry--;
216
- if (!retry) {
217
- dev_warn(i2s->dev, "reset\n");
218
- rockchip_i2s_reset(i2s);
219
- break;
220
- }
221
- }
223
+ rockchip_i2s_clear(i2s);
222224 }
223225 }
224
- spin_unlock(&lock);
226
+ spin_unlock(&i2s->lock);
225227 }
226228
227229 static int rockchip_i2s_set_fmt(struct snd_soc_dai *cpu_dai,
....@@ -333,6 +335,25 @@
333335 return ret;
334336 }
335337
338
+static void rockchip_i2s_get_performance(struct snd_pcm_substream *substream,
339
+ struct snd_pcm_hw_params *params,
340
+ struct snd_soc_dai *dai,
341
+ unsigned int csr)
342
+{
343
+ struct rk_i2s_dev *i2s = to_info(dai);
344
+ unsigned int tdl;
345
+ int fifo;
346
+
347
+ regmap_read(i2s->regmap, I2S_DMACR, &tdl);
348
+
349
+ if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
350
+ fifo = I2S_DMACR_TDL_V(tdl) * I2S_TXCR_CSR_V(csr);
351
+ else
352
+ fifo = I2S_DMACR_RDL_V(tdl) * I2S_RXCR_CSR_V(csr);
353
+
354
+ rockchip_utils_get_performance(substream, params, dai, fifo);
355
+}
356
+
336357 static int rockchip_i2s_hw_params(struct snd_pcm_substream *substream,
337358 struct snd_pcm_hw_params *params,
338359 struct snd_soc_dai *dai)
....@@ -343,7 +364,7 @@
343364
344365 if (i2s->is_master_mode) {
345366 mclk_rate = clk_get_rate(i2s->mclk);
346
- bclk_rate = i2s->bclk_fs * params_rate(params);
367
+ bclk_rate = i2s->bclk_ratio * params_rate(params);
347368 if (!bclk_rate)
348369 return -EINVAL;
349370
....@@ -374,6 +395,7 @@
374395 val |= I2S_TXCR_VDW(24);
375396 break;
376397 case SNDRV_PCM_FORMAT_S32_LE:
398
+ case SNDRV_PCM_FORMAT_IEC958_SUBFRAME_LE:
377399 val |= I2S_TXCR_VDW(32);
378400 break;
379401 default:
....@@ -398,6 +420,8 @@
398420 params_channels(params));
399421 return -EINVAL;
400422 }
423
+
424
+ rockchip_i2s_get_performance(substream, params, dai, val);
401425
402426 if (substream->stream == SNDRV_PCM_STREAM_CAPTURE)
403427 regmap_update_bits(i2s->regmap, I2S_RXCR,
....@@ -440,6 +464,14 @@
440464 return 0;
441465 }
442466
467
+static int rockchip_i2s_hw_free(struct snd_pcm_substream *substream,
468
+ struct snd_soc_dai *dai)
469
+{
470
+ rockchip_utils_put_performance(substream, dai);
471
+
472
+ return 0;
473
+}
474
+
443475 static int rockchip_i2s_trigger(struct snd_pcm_substream *substream,
444476 int cmd, struct snd_soc_dai *dai)
445477 {
....@@ -469,6 +501,16 @@
469501 }
470502
471503 return ret;
504
+}
505
+
506
+static int rockchip_i2s_set_bclk_ratio(struct snd_soc_dai *dai,
507
+ unsigned int ratio)
508
+{
509
+ struct rk_i2s_dev *i2s = to_info(dai);
510
+
511
+ i2s->bclk_ratio = ratio;
512
+
513
+ return 0;
472514 }
473515
474516 static int rockchip_i2s_clk_set_rate(struct rk_i2s_dev *i2s,
....@@ -510,6 +552,9 @@
510552 unsigned int root_rate, div, delta;
511553 uint64_t ppm;
512554 int ret;
555
+
556
+ if (rate == 0)
557
+ return 0;
513558
514559 if (i2s->mclk_calibrate) {
515560 ret = rockchip_i2s_clk_set_rate(i2s, i2s->mclk_root,
....@@ -557,8 +602,8 @@
557602 static int rockchip_i2s_clk_compensation_get(struct snd_kcontrol *kcontrol,
558603 struct snd_ctl_elem_value *ucontrol)
559604 {
560
- struct snd_soc_dai *dai = snd_kcontrol_chip(kcontrol);
561
- struct rk_i2s_dev *i2s = snd_soc_dai_get_drvdata(dai);
605
+ struct snd_soc_component *compnt = snd_soc_kcontrol_component(kcontrol);
606
+ struct rk_i2s_dev *i2s = snd_soc_component_get_drvdata(compnt);
562607
563608 ucontrol->value.integer.value[0] = i2s->clk_ppm;
564609
....@@ -568,8 +613,8 @@
568613 static int rockchip_i2s_clk_compensation_put(struct snd_kcontrol *kcontrol,
569614 struct snd_ctl_elem_value *ucontrol)
570615 {
571
- struct snd_soc_dai *dai = snd_kcontrol_chip(kcontrol);
572
- struct rk_i2s_dev *i2s = snd_soc_dai_get_drvdata(dai);
616
+ struct snd_soc_component *compnt = snd_soc_kcontrol_component(kcontrol);
617
+ struct rk_i2s_dev *i2s = snd_soc_component_get_drvdata(compnt);
573618 int ppm = ucontrol->value.integer.value[0];
574619
575620 if ((ucontrol->value.integer.value[0] < CLK_PPM_MIN) ||
....@@ -591,17 +636,49 @@
591636 {
592637 struct rk_i2s_dev *i2s = snd_soc_dai_get_drvdata(dai);
593638
594
- dai->capture_dma_data = &i2s->capture_dma_data;
595
- dai->playback_dma_data = &i2s->playback_dma_data;
639
+ snd_soc_dai_init_dma_data(dai,
640
+ i2s->has_playback ? &i2s->playback_dma_data : NULL,
641
+ i2s->has_capture ? &i2s->capture_dma_data : NULL);
596642
597643 if (i2s->mclk_calibrate)
598
- snd_soc_add_dai_controls(dai, &rockchip_i2s_compensation_control, 1);
644
+ snd_soc_add_component_controls(dai->component,
645
+ &rockchip_i2s_compensation_control,
646
+ 1);
599647
600648 return 0;
601649 }
602650
651
+static int rockchip_i2s_startup(struct snd_pcm_substream *substream,
652
+ struct snd_soc_dai *dai)
653
+{
654
+ struct rk_i2s_dev *i2s = snd_soc_dai_get_drvdata(dai);
655
+ int stream = substream->stream;
656
+
657
+ if (i2s->substreams[stream])
658
+ return -EBUSY;
659
+
660
+ if (i2s->wait_time[stream])
661
+ substream->wait_time = msecs_to_jiffies(i2s->wait_time[stream]);
662
+
663
+ i2s->substreams[stream] = substream;
664
+
665
+ return 0;
666
+}
667
+
668
+static void rockchip_i2s_shutdown(struct snd_pcm_substream *substream,
669
+ struct snd_soc_dai *dai)
670
+{
671
+ struct rk_i2s_dev *i2s = snd_soc_dai_get_drvdata(dai);
672
+
673
+ i2s->substreams[substream->stream] = NULL;
674
+}
675
+
603676 static const struct snd_soc_dai_ops rockchip_i2s_dai_ops = {
677
+ .startup = rockchip_i2s_startup,
678
+ .shutdown = rockchip_i2s_shutdown,
604679 .hw_params = rockchip_i2s_hw_params,
680
+ .hw_free = rockchip_i2s_hw_free,
681
+ .set_bclk_ratio = rockchip_i2s_set_bclk_ratio,
605682 .set_sysclk = rockchip_i2s_set_sysclk,
606683 .set_fmt = rockchip_i2s_set_fmt,
607684 .trigger = rockchip_i2s_trigger,
....@@ -609,33 +686,119 @@
609686
610687 static struct snd_soc_dai_driver rockchip_i2s_dai = {
611688 .probe = rockchip_i2s_dai_probe,
612
- .playback = {
613
- .stream_name = "Playback",
614
- .channels_min = 2,
615
- .channels_max = 8,
616
- .rates = SNDRV_PCM_RATE_8000_192000,
617
- .formats = (SNDRV_PCM_FMTBIT_S8 |
618
- SNDRV_PCM_FMTBIT_S16_LE |
619
- SNDRV_PCM_FMTBIT_S20_3LE |
620
- SNDRV_PCM_FMTBIT_S24_LE |
621
- SNDRV_PCM_FMTBIT_S32_LE),
622
- },
623
- .capture = {
624
- .stream_name = "Capture",
625
- .channels_min = 2,
626
- .channels_max = 2,
627
- .rates = SNDRV_PCM_RATE_8000_192000,
628
- .formats = (SNDRV_PCM_FMTBIT_S8 |
629
- SNDRV_PCM_FMTBIT_S16_LE |
630
- SNDRV_PCM_FMTBIT_S20_3LE |
631
- SNDRV_PCM_FMTBIT_S24_LE |
632
- SNDRV_PCM_FMTBIT_S32_LE),
633
- },
634689 .ops = &rockchip_i2s_dai_ops,
690
+};
691
+
692
+static int rockchip_i2s_get_bclk_ratio(struct snd_kcontrol *kcontrol,
693
+ struct snd_ctl_elem_value *ucontrol)
694
+{
695
+ struct snd_soc_component *compnt = snd_soc_kcontrol_component(kcontrol);
696
+ struct rk_i2s_dev *i2s = snd_soc_component_get_drvdata(compnt);
697
+
698
+ ucontrol->value.integer.value[0] = i2s->bclk_ratio;
699
+
700
+ return 0;
701
+}
702
+
703
+static int rockchip_i2s_put_bclk_ratio(struct snd_kcontrol *kcontrol,
704
+ struct snd_ctl_elem_value *ucontrol)
705
+{
706
+ struct snd_soc_component *compnt = snd_soc_kcontrol_component(kcontrol);
707
+ struct rk_i2s_dev *i2s = snd_soc_component_get_drvdata(compnt);
708
+ int value = ucontrol->value.integer.value[0];
709
+
710
+ if (value == i2s->bclk_ratio)
711
+ return 0;
712
+
713
+ i2s->bclk_ratio = value;
714
+
715
+ return 1;
716
+}
717
+
718
+static int rockchip_i2s_wait_time_info(struct snd_kcontrol *kcontrol,
719
+ struct snd_ctl_elem_info *uinfo)
720
+{
721
+ uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
722
+ uinfo->count = 1;
723
+ uinfo->value.integer.min = 0;
724
+ uinfo->value.integer.max = WAIT_TIME_MS_MAX;
725
+ uinfo->value.integer.step = 1;
726
+
727
+ return 0;
728
+}
729
+
730
+static int rockchip_i2s_rd_wait_time_get(struct snd_kcontrol *kcontrol,
731
+ struct snd_ctl_elem_value *ucontrol)
732
+{
733
+ struct snd_soc_component *component = snd_soc_kcontrol_component(kcontrol);
734
+ struct rk_i2s_dev *i2s = snd_soc_component_get_drvdata(component);
735
+
736
+ ucontrol->value.integer.value[0] = i2s->wait_time[SNDRV_PCM_STREAM_CAPTURE];
737
+
738
+ return 0;
739
+}
740
+
741
+static int rockchip_i2s_rd_wait_time_put(struct snd_kcontrol *kcontrol,
742
+ struct snd_ctl_elem_value *ucontrol)
743
+{
744
+ struct snd_soc_component *component = snd_soc_kcontrol_component(kcontrol);
745
+ struct rk_i2s_dev *i2s = snd_soc_component_get_drvdata(component);
746
+
747
+ if (ucontrol->value.integer.value[0] > WAIT_TIME_MS_MAX)
748
+ return -EINVAL;
749
+
750
+ i2s->wait_time[SNDRV_PCM_STREAM_CAPTURE] = ucontrol->value.integer.value[0];
751
+
752
+ return 1;
753
+}
754
+
755
+static int rockchip_i2s_wr_wait_time_get(struct snd_kcontrol *kcontrol,
756
+ struct snd_ctl_elem_value *ucontrol)
757
+{
758
+ struct snd_soc_component *component = snd_soc_kcontrol_component(kcontrol);
759
+ struct rk_i2s_dev *i2s = snd_soc_component_get_drvdata(component);
760
+
761
+ ucontrol->value.integer.value[0] = i2s->wait_time[SNDRV_PCM_STREAM_PLAYBACK];
762
+
763
+ return 0;
764
+}
765
+
766
+static int rockchip_i2s_wr_wait_time_put(struct snd_kcontrol *kcontrol,
767
+ struct snd_ctl_elem_value *ucontrol)
768
+{
769
+ struct snd_soc_component *component = snd_soc_kcontrol_component(kcontrol);
770
+ struct rk_i2s_dev *i2s = snd_soc_component_get_drvdata(component);
771
+
772
+ if (ucontrol->value.integer.value[0] > WAIT_TIME_MS_MAX)
773
+ return -EINVAL;
774
+
775
+ i2s->wait_time[SNDRV_PCM_STREAM_PLAYBACK] = ucontrol->value.integer.value[0];
776
+
777
+ return 1;
778
+}
779
+
780
+#define SAI_PCM_WAIT_TIME(xname, xhandler_get, xhandler_put) \
781
+{ .iface = SNDRV_CTL_ELEM_IFACE_PCM, .name = xname, \
782
+ .info = rockchip_i2s_wait_time_info, \
783
+ .get = xhandler_get, .put = xhandler_put }
784
+
785
+static const struct snd_kcontrol_new rockchip_i2s_snd_controls[] = {
786
+ SOC_SINGLE_EXT("BCLK Ratio", 0, 0, INT_MAX, 0,
787
+ rockchip_i2s_get_bclk_ratio,
788
+ rockchip_i2s_put_bclk_ratio),
789
+
790
+ SAI_PCM_WAIT_TIME("PCM Read Wait Time MS",
791
+ rockchip_i2s_rd_wait_time_get,
792
+ rockchip_i2s_rd_wait_time_put),
793
+ SAI_PCM_WAIT_TIME("PCM Write Wait Time MS",
794
+ rockchip_i2s_wr_wait_time_get,
795
+ rockchip_i2s_wr_wait_time_put),
635796 };
636797
637798 static const struct snd_soc_component_driver rockchip_i2s_component = {
638799 .name = DRV_NAME,
800
+ .controls = rockchip_i2s_snd_controls,
801
+ .num_controls = ARRAY_SIZE(rockchip_i2s_snd_controls),
639802 };
640803
641804 static bool rockchip_i2s_wr_reg(struct device *dev, unsigned int reg)
....@@ -667,7 +830,8 @@
667830 case I2S_CLR:
668831 case I2S_TXDR:
669832 case I2S_RXDR:
670
- case I2S_FIFOLR:
833
+ case I2S_TXFIFOLR:
834
+ case I2S_RXFIFOLR:
671835 case I2S_INTSR:
672836 return true;
673837 default:
....@@ -680,7 +844,8 @@
680844 switch (reg) {
681845 case I2S_INTSR:
682846 case I2S_CLR:
683
- case I2S_FIFOLR:
847
+ case I2S_TXFIFOLR:
848
+ case I2S_RXFIFOLR:
684849 case I2S_TXDR:
685850 case I2S_RXDR:
686851 return true;
....@@ -726,7 +891,7 @@
726891 .shift = 11,
727892 };
728893
729
-static const struct of_device_id rockchip_i2s_match[] = {
894
+static const struct of_device_id rockchip_i2s_match[] __maybe_unused = {
730895 #ifdef CONFIG_CPU_PX30
731896 { .compatible = "rockchip,px30-i2s", },
732897 #endif
....@@ -743,6 +908,9 @@
743908 #ifdef CONFIG_CPU_RK3188
744909 { .compatible = "rockchip,rk3188-i2s", },
745910 #endif
911
+#ifdef CONFIG_CPU_RK322X
912
+ { .compatible = "rockchip,rk3228-i2s", },
913
+#endif
746914 #ifdef CONFIG_CPU_RK3288
747915 { .compatible = "rockchip,rk3288-i2s", },
748916 #endif
....@@ -751,6 +919,9 @@
751919 #endif
752920 #ifdef CONFIG_CPU_RK3328
753921 { .compatible = "rockchip,rk3328-i2s", },
922
+#endif
923
+#ifdef CONFIG_CPU_RK3366
924
+ { .compatible = "rockchip,rk3366-i2s", },
754925 #endif
755926 #ifdef CONFIG_CPU_RK3368
756927 { .compatible = "rockchip,rk3368-i2s", },
....@@ -764,21 +935,166 @@
764935 {},
765936 };
766937
938
+static int rockchip_i2s_init_dai(struct rk_i2s_dev *i2s, struct resource *res,
939
+ struct snd_soc_dai_driver **dp)
940
+{
941
+ struct device_node *node = i2s->dev->of_node;
942
+ struct snd_soc_dai_driver *dai;
943
+ struct property *dma_names;
944
+ const char *dma_name;
945
+ unsigned int val;
946
+
947
+ of_property_for_each_string(node, "dma-names", dma_names, dma_name) {
948
+ if (!strcmp(dma_name, "tx"))
949
+ i2s->has_playback = true;
950
+ if (!strcmp(dma_name, "rx"))
951
+ i2s->has_capture = true;
952
+ }
953
+
954
+ dai = devm_kmemdup(i2s->dev, &rockchip_i2s_dai,
955
+ sizeof(*dai), GFP_KERNEL);
956
+ if (!dai)
957
+ return -ENOMEM;
958
+
959
+ if (i2s->has_playback) {
960
+ dai->playback.stream_name = "Playback";
961
+ dai->playback.channels_min = 2;
962
+ dai->playback.channels_max = 8;
963
+ dai->playback.rates = SNDRV_PCM_RATE_8000_192000;
964
+ dai->playback.formats = SNDRV_PCM_FMTBIT_S8 |
965
+ SNDRV_PCM_FMTBIT_S16_LE |
966
+ SNDRV_PCM_FMTBIT_S20_3LE |
967
+ SNDRV_PCM_FMTBIT_S24_LE |
968
+ SNDRV_PCM_FMTBIT_S32_LE |
969
+ SNDRV_PCM_FMTBIT_IEC958_SUBFRAME_LE;
970
+
971
+ i2s->playback_dma_data.addr = res->start + I2S_TXDR;
972
+ i2s->playback_dma_data.addr_width = DMA_SLAVE_BUSWIDTH_4_BYTES;
973
+ i2s->playback_dma_data.maxburst = 8;
974
+
975
+ if (!device_property_read_u32(i2s->dev, "rockchip,playback-channels", &val)) {
976
+ if (val >= 2 && val <= 8)
977
+ dai->playback.channels_max = val;
978
+ }
979
+ }
980
+
981
+ if (i2s->has_capture) {
982
+ dai->capture.stream_name = "Capture";
983
+ dai->capture.channels_min = 2;
984
+ dai->capture.channels_max = 8;
985
+ dai->capture.rates = SNDRV_PCM_RATE_8000_192000;
986
+ dai->capture.formats = SNDRV_PCM_FMTBIT_S8 |
987
+ SNDRV_PCM_FMTBIT_S16_LE |
988
+ SNDRV_PCM_FMTBIT_S20_3LE |
989
+ SNDRV_PCM_FMTBIT_S24_LE |
990
+ SNDRV_PCM_FMTBIT_S32_LE |
991
+ SNDRV_PCM_FMTBIT_IEC958_SUBFRAME_LE;
992
+
993
+ i2s->capture_dma_data.addr = res->start + I2S_RXDR;
994
+ i2s->capture_dma_data.addr_width = DMA_SLAVE_BUSWIDTH_4_BYTES;
995
+ i2s->capture_dma_data.maxburst = 8;
996
+
997
+ if (!device_property_read_u32(i2s->dev, "rockchip,capture-channels", &val)) {
998
+ if (val >= 2 && val <= 8)
999
+ dai->capture.channels_max = val;
1000
+ }
1001
+ }
1002
+
1003
+ i2s->clk_trcm = I2S_CKR_TRCM_TXRX;
1004
+ if (!device_property_read_u32(i2s->dev, "rockchip,clk-trcm", &val)) {
1005
+ if (val >= 0 && val <= 2) {
1006
+ i2s->clk_trcm = val << I2S_CKR_TRCM_SHIFT;
1007
+ if (i2s->clk_trcm)
1008
+ dai->symmetric_rates = 1;
1009
+ }
1010
+ }
1011
+
1012
+ regmap_update_bits(i2s->regmap, I2S_CKR,
1013
+ I2S_CKR_TRCM_MASK, i2s->clk_trcm);
1014
+
1015
+ if (dp)
1016
+ *dp = dai;
1017
+
1018
+ return 0;
1019
+}
1020
+
1021
+static int rockchip_i2s_keep_clk_always_on(struct rk_i2s_dev *i2s)
1022
+{
1023
+ unsigned int mclk_rate = DEFAULT_FS * DEFAULT_MCLK_FS;
1024
+ unsigned int bclk_rate = i2s->bclk_ratio * DEFAULT_FS;
1025
+ unsigned int div_lrck = i2s->bclk_ratio;
1026
+ unsigned int div_bclk;
1027
+
1028
+ div_bclk = DIV_ROUND_CLOSEST(mclk_rate, bclk_rate);
1029
+
1030
+ /* assign generic freq */
1031
+ clk_set_rate(i2s->mclk, mclk_rate);
1032
+
1033
+ regmap_update_bits(i2s->regmap, I2S_CKR,
1034
+ I2S_CKR_MDIV_MASK,
1035
+ I2S_CKR_MDIV(div_bclk));
1036
+ regmap_update_bits(i2s->regmap, I2S_CKR,
1037
+ I2S_CKR_TSD_MASK |
1038
+ I2S_CKR_RSD_MASK,
1039
+ I2S_CKR_TSD(div_lrck) |
1040
+ I2S_CKR_RSD(div_lrck));
1041
+ regmap_update_bits(i2s->regmap, I2S_XFER,
1042
+ I2S_XFER_TXS_START | I2S_XFER_RXS_START,
1043
+ I2S_XFER_TXS_START | I2S_XFER_RXS_START);
1044
+
1045
+ pm_runtime_forbid(i2s->dev);
1046
+
1047
+ dev_info(i2s->dev, "CLK-ALWAYS-ON: mclk: %d, bclk: %d, fsync: %d\n",
1048
+ mclk_rate, bclk_rate, DEFAULT_FS);
1049
+
1050
+ return 0;
1051
+}
1052
+
1053
+static int rockchip_i2s_get_fifo_count(struct device *dev,
1054
+ struct snd_pcm_substream *substream)
1055
+{
1056
+ struct rk_i2s_dev *i2s = dev_get_drvdata(dev);
1057
+ unsigned int tx, rx;
1058
+ int val = 0;
1059
+
1060
+ regmap_read(i2s->regmap, I2S_TXFIFOLR, &tx);
1061
+ regmap_read(i2s->regmap, I2S_RXFIFOLR, &rx);
1062
+
1063
+ if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
1064
+ val = I2S_FIFOLR_XFL3(tx) +
1065
+ I2S_FIFOLR_XFL2(tx) +
1066
+ I2S_FIFOLR_XFL1(tx) +
1067
+ I2S_FIFOLR_XFL0(tx);
1068
+ else
1069
+ /* XFL4 is compatible for old version */
1070
+ val = I2S_FIFOLR_XFL4(tx) +
1071
+ I2S_FIFOLR_XFL3(rx) +
1072
+ I2S_FIFOLR_XFL2(rx) +
1073
+ I2S_FIFOLR_XFL1(rx) +
1074
+ I2S_FIFOLR_XFL0(rx);
1075
+
1076
+ return val;
1077
+}
1078
+
1079
+static const struct snd_dlp_config dconfig = {
1080
+ .get_fifo_count = rockchip_i2s_get_fifo_count,
1081
+};
1082
+
7671083 static int rockchip_i2s_probe(struct platform_device *pdev)
7681084 {
7691085 struct device_node *node = pdev->dev.of_node;
7701086 const struct of_device_id *of_id;
7711087 struct rk_i2s_dev *i2s;
772
- struct snd_soc_dai_driver *soc_dai;
1088
+ struct snd_soc_dai_driver *dai;
7731089 struct resource *res;
7741090 void __iomem *regs;
775
- int ret;
776
- int val;
1091
+ int ret, i, val;
7771092
7781093 i2s = devm_kzalloc(&pdev->dev, sizeof(*i2s), GFP_KERNEL);
7791094 if (!i2s)
7801095 return -ENOMEM;
7811096
1097
+ spin_lock_init(&i2s->lock);
7821098 i2s->dev = &pdev->dev;
7831099
7841100 i2s->grf = syscon_regmap_lookup_by_phandle(node, "rockchip,grf");
....@@ -790,11 +1106,32 @@
7901106 i2s->pins = of_id->data;
7911107 }
7921108
793
- i2s->reset_m = devm_reset_control_get(&pdev->dev, "reset-m");
794
- i2s->reset_h = devm_reset_control_get(&pdev->dev, "reset-h");
1109
+ for (i = 0; i < ARRAY_SIZE(of_quirks); i++)
1110
+ if (device_property_read_bool(i2s->dev, of_quirks[i].quirk))
1111
+ i2s->quirks |= of_quirks[i].id;
1112
+
1113
+ regs = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
1114
+ if (IS_ERR(regs))
1115
+ return PTR_ERR(regs);
1116
+
1117
+ i2s->regmap = devm_regmap_init_mmio(&pdev->dev, regs,
1118
+ &rockchip_i2s_regmap_config);
1119
+ if (IS_ERR(i2s->regmap)) {
1120
+ dev_err(&pdev->dev,
1121
+ "Failed to initialise managed register map\n");
1122
+ return PTR_ERR(i2s->regmap);
1123
+ }
1124
+
1125
+ i2s->bclk_ratio = 64;
1126
+ if (!device_property_read_u32(&pdev->dev, "rockchip,bclk-fs", &val)) {
1127
+ if ((val >= 32) && (val % 2 == 0))
1128
+ i2s->bclk_ratio = val;
1129
+ }
1130
+
1131
+ dev_set_drvdata(&pdev->dev, i2s);
7951132
7961133 i2s->mclk_calibrate =
797
- of_property_read_bool(node, "rockchip,mclk-calibrate");
1134
+ device_property_read_bool(&pdev->dev, "rockchip,mclk-calibrate");
7981135 if (i2s->mclk_calibrate) {
7991136 i2s->mclk_root = devm_clk_get(&pdev->dev, "i2s_clk_root");
8001137 if (IS_ERR(i2s->mclk_root))
....@@ -802,6 +1139,12 @@
8021139
8031140 i2s->mclk_root_initial_rate = clk_get_rate(i2s->mclk_root);
8041141 i2s->mclk_root_rate = i2s->mclk_root_initial_rate;
1142
+ }
1143
+
1144
+ i2s->mclk = devm_clk_get(&pdev->dev, "i2s_clk");
1145
+ if (IS_ERR(i2s->mclk)) {
1146
+ dev_err(&pdev->dev, "Can't retrieve i2s master clock\n");
1147
+ return PTR_ERR(i2s->mclk);
8051148 }
8061149
8071150 /* try to prepare related clocks */
....@@ -816,35 +1159,31 @@
8161159 return ret;
8171160 }
8181161
819
- i2s->mclk = devm_clk_get(&pdev->dev, "i2s_clk");
820
- if (IS_ERR(i2s->mclk)) {
821
- dev_err(&pdev->dev, "Can't retrieve i2s master clock\n");
822
- return PTR_ERR(i2s->mclk);
1162
+ ret = rockchip_i2s_init_dai(i2s, res, &dai);
1163
+ if (ret)
1164
+ goto err_clk;
1165
+
1166
+ /*
1167
+ * CLK_ALWAYS_ON should be placed after all registers write done,
1168
+ * because this situation will enable XFER bit which will make
1169
+ * some registers(depend on XFER) write failed.
1170
+ */
1171
+ if (i2s->quirks & QUIRK_ALWAYS_ON) {
1172
+ ret = rockchip_i2s_keep_clk_always_on(i2s);
1173
+ if (ret)
1174
+ goto err_clk;
8231175 }
8241176
825
- res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
826
- regs = devm_ioremap_resource(&pdev->dev, res);
827
- if (IS_ERR(regs))
828
- return PTR_ERR(regs);
829
-
830
- i2s->regmap = devm_regmap_init_mmio(&pdev->dev, regs,
831
- &rockchip_i2s_regmap_config);
832
- if (IS_ERR(i2s->regmap)) {
833
- dev_err(&pdev->dev,
834
- "Failed to initialise managed register map\n");
835
- return PTR_ERR(i2s->regmap);
836
- }
837
-
838
- i2s->playback_dma_data.addr = res->start + I2S_TXDR;
839
- i2s->playback_dma_data.addr_width = DMA_SLAVE_BUSWIDTH_4_BYTES;
840
- i2s->playback_dma_data.maxburst = 8;
841
-
842
- i2s->capture_dma_data.addr = res->start + I2S_RXDR;
843
- i2s->capture_dma_data.addr_width = DMA_SLAVE_BUSWIDTH_4_BYTES;
844
- i2s->capture_dma_data.maxburst = 8;
845
-
846
- dev_set_drvdata(&pdev->dev, i2s);
847
-
1177
+ /*
1178
+ * MUST: after pm_runtime_enable step, any register R/W
1179
+ * should be wrapped with pm_runtime_get_sync/put.
1180
+ *
1181
+ * Another approach is to enable the regcache true to
1182
+ * avoid access HW registers.
1183
+ *
1184
+ * Alternatively, performing the registers R/W before
1185
+ * pm_runtime_enable is also a good option.
1186
+ */
8481187 pm_runtime_enable(&pdev->dev);
8491188 if (!pm_runtime_enabled(&pdev->dev)) {
8501189 ret = i2s_runtime_resume(&pdev->dev);
....@@ -852,58 +1191,25 @@
8521191 goto err_pm_disable;
8531192 }
8541193
855
- soc_dai = devm_kmemdup(&pdev->dev, &rockchip_i2s_dai,
856
- sizeof(*soc_dai), GFP_KERNEL);
857
- if (!soc_dai) {
858
- ret = -ENOMEM;
859
- goto err_pm_disable;
860
- }
861
-
862
- if (!of_property_read_u32(node, "rockchip,playback-channels", &val)) {
863
- if (val >= 2 && val <= 8)
864
- soc_dai->playback.channels_max = val;
865
- }
866
-
867
- if (!of_property_read_u32(node, "rockchip,capture-channels", &val)) {
868
- if (val >= 2 && val <= 8)
869
- soc_dai->capture.channels_max = val;
870
- }
871
-
872
- if (of_property_read_bool(node, "rockchip,playback-only"))
873
- soc_dai->capture.channels_min = 0;
874
- else if (of_property_read_bool(node, "rockchip,capture-only"))
875
- soc_dai->playback.channels_min = 0;
876
-
877
- i2s->bclk_fs = 64;
878
- if (!of_property_read_u32(node, "rockchip,bclk-fs", &val)) {
879
- if ((val >= 32) && (val % 2 == 0))
880
- i2s->bclk_fs = val;
881
- }
882
-
883
- i2s->clk_trcm = I2S_CKR_TRCM_TXRX;
884
- if (!of_property_read_u32(node, "rockchip,clk-trcm", &val)) {
885
- if (val >= 0 && val <= 2) {
886
- i2s->clk_trcm = val << I2S_CKR_TRCM_SHIFT;
887
- if (i2s->clk_trcm)
888
- soc_dai->symmetric_rates = 1;
889
- }
890
- }
891
-
892
- regmap_update_bits(i2s->regmap, I2S_CKR,
893
- I2S_CKR_TRCM_MASK, i2s->clk_trcm);
894
-
8951194 ret = devm_snd_soc_register_component(&pdev->dev,
8961195 &rockchip_i2s_component,
897
- soc_dai, 1);
1196
+ dai, 1);
8981197
8991198 if (ret) {
9001199 dev_err(&pdev->dev, "Could not register DAI\n");
9011200 goto err_suspend;
9021201 }
9031202
904
- if (of_property_read_bool(node, "rockchip,no-dmaengine"))
905
- return ret;
906
- ret = devm_snd_dmaengine_pcm_register(&pdev->dev, NULL, 0);
1203
+ if (device_property_read_bool(&pdev->dev, "rockchip,no-dmaengine")) {
1204
+ dev_info(&pdev->dev, "Used for Multi-DAI\n");
1205
+ return 0;
1206
+ }
1207
+
1208
+ if (device_property_read_bool(&pdev->dev, "rockchip,digital-loopback"))
1209
+ ret = devm_snd_dmaengine_dlp_register(&pdev->dev, &dconfig);
1210
+ else
1211
+ ret = devm_snd_dmaengine_pcm_register(&pdev->dev, NULL, 0);
1212
+
9071213 if (ret) {
9081214 dev_err(&pdev->dev, "Could not register PCM\n");
9091215 goto err_suspend;
....@@ -916,6 +1222,8 @@
9161222 i2s_runtime_suspend(&pdev->dev);
9171223 err_pm_disable:
9181224 pm_runtime_disable(&pdev->dev);
1225
+err_clk:
1226
+ clk_disable_unprepare(i2s->hclk);
9191227
9201228 return ret;
9211229 }