~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

TOMOYO Linux Cross Reference
Linux/sound/soc/ti/davinci-i2s.c

Version: ~ [ linux-6.11.5 ] ~ [ linux-6.10.14 ] ~ [ linux-6.9.12 ] ~ [ linux-6.8.12 ] ~ [ linux-6.7.12 ] ~ [ linux-6.6.58 ] ~ [ linux-6.5.13 ] ~ [ linux-6.4.16 ] ~ [ linux-6.3.13 ] ~ [ linux-6.2.16 ] ~ [ linux-6.1.114 ] ~ [ linux-6.0.19 ] ~ [ linux-5.19.17 ] ~ [ linux-5.18.19 ] ~ [ linux-5.17.15 ] ~ [ linux-5.16.20 ] ~ [ linux-5.15.169 ] ~ [ linux-5.14.21 ] ~ [ linux-5.13.19 ] ~ [ linux-5.12.19 ] ~ [ linux-5.11.22 ] ~ [ linux-5.10.228 ] ~ [ linux-5.9.16 ] ~ [ linux-5.8.18 ] ~ [ linux-5.7.19 ] ~ [ linux-5.6.19 ] ~ [ linux-5.5.19 ] ~ [ linux-5.4.284 ] ~ [ linux-5.3.18 ] ~ [ linux-5.2.21 ] ~ [ linux-5.1.21 ] ~ [ linux-5.0.21 ] ~ [ linux-4.20.17 ] ~ [ linux-4.19.322 ] ~ [ linux-4.18.20 ] ~ [ linux-4.17.19 ] ~ [ linux-4.16.18 ] ~ [ linux-4.15.18 ] ~ [ linux-4.14.336 ] ~ [ linux-4.13.16 ] ~ [ linux-4.12.14 ] ~ [ linux-4.11.12 ] ~ [ linux-4.10.17 ] ~ [ linux-4.9.337 ] ~ [ linux-4.4.302 ] ~ [ linux-3.10.108 ] ~ [ linux-2.6.32.71 ] ~ [ linux-2.6.0 ] ~ [ linux-2.4.37.11 ] ~ [ unix-v6-master ] ~ [ ccs-tools-1.8.9 ] ~ [ policy-sample ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 // SPDX-License-Identifier: GPL-2.0-only
  2 /*
  3  * ALSA SoC I2S (McBSP) Audio Layer for TI DAVINCI processor
  4  *
  5  * Author:      Vladimir Barinov, <vbarinov@embeddedalley.com>
  6  * Copyright:   (C) 2007 MontaVista Software, Inc., <source@mvista.com>
  7  *
  8  * DT support   (c) 2016 Petr Kulhavy, Barix AG <petr@barix.com>
  9  *              based on davinci-mcasp.c DT support
 10  *
 11  * TODO:
 12  * on DA850 implement HW FIFOs instead of DMA into DXR and DRR registers
 13  */
 14 
 15 #include <linux/init.h>
 16 #include <linux/module.h>
 17 #include <linux/device.h>
 18 #include <linux/slab.h>
 19 #include <linux/delay.h>
 20 #include <linux/io.h>
 21 #include <linux/clk.h>
 22 
 23 #include <sound/core.h>
 24 #include <sound/pcm.h>
 25 #include <sound/pcm_params.h>
 26 #include <sound/initval.h>
 27 #include <sound/soc.h>
 28 #include <sound/dmaengine_pcm.h>
 29 
 30 #include "edma-pcm.h"
 31 #include "davinci-i2s.h"
 32 
 33 #define DRV_NAME "davinci-i2s"
 34 
 35 /*
 36  * NOTE:  terminology here is confusing.
 37  *
 38  *  - This driver supports the "Audio Serial Port" (ASP),
 39  *    found on dm6446, dm355, and other DaVinci chips.
 40  *
 41  *  - But it labels it a "Multi-channel Buffered Serial Port"
 42  *    (McBSP) as on older chips like the dm642 ... which was
 43  *    backward-compatible, possibly explaining that confusion.
 44  *
 45  *  - OMAP chips have a controller called McBSP, which is
 46  *    incompatible with the DaVinci flavor of McBSP.
 47  *
 48  *  - Newer DaVinci chips have a controller called McASP,
 49  *    incompatible with ASP and with either McBSP.
 50  *
 51  * In short:  this uses ASP to implement I2S, not McBSP.
 52  * And it won't be the only DaVinci implemention of I2S.
 53  */
 54 #define DAVINCI_MCBSP_DRR_REG   0x00
 55 #define DAVINCI_MCBSP_DXR_REG   0x04
 56 #define DAVINCI_MCBSP_SPCR_REG  0x08
 57 #define DAVINCI_MCBSP_RCR_REG   0x0c
 58 #define DAVINCI_MCBSP_XCR_REG   0x10
 59 #define DAVINCI_MCBSP_SRGR_REG  0x14
 60 #define DAVINCI_MCBSP_PCR_REG   0x24
 61 
 62 #define DAVINCI_MCBSP_SPCR_RRST         (1 << 0)
 63 #define DAVINCI_MCBSP_SPCR_RINTM(v)     ((v) << 4)
 64 #define DAVINCI_MCBSP_SPCR_RJUST(v)     ((v) << 13)
 65 #define DAVINCI_MCBSP_SPCR_RJUST_Z_LE   DAVINCI_MCBSP_SPCR_RJUST(0)
 66 #define DAVINCI_MCBSP_SPCR_RJUST_S_LE   DAVINCI_MCBSP_SPCR_RJUST(1)
 67 #define DAVINCI_MCBSP_SPCR_XRST         (1 << 16)
 68 #define DAVINCI_MCBSP_SPCR_XINTM(v)     ((v) << 20)
 69 #define DAVINCI_MCBSP_SPCR_GRST         (1 << 22)
 70 #define DAVINCI_MCBSP_SPCR_FRST         (1 << 23)
 71 #define DAVINCI_MCBSP_SPCR_FREE         (1 << 25)
 72 
 73 #define DAVINCI_MCBSP_RCR_RWDLEN1(v)    ((v) << 5)
 74 #define DAVINCI_MCBSP_RCR_RFRLEN1(v)    ((v) << 8)
 75 #define DAVINCI_MCBSP_RCR_RDATDLY(v)    ((v) << 16)
 76 #define DAVINCI_MCBSP_RCR_RFIG          (1 << 18)
 77 #define DAVINCI_MCBSP_RCR_RWDLEN2(v)    ((v) << 21)
 78 #define DAVINCI_MCBSP_RCR_RFRLEN2(v)    ((v) << 24)
 79 #define DAVINCI_MCBSP_RCR_RPHASE        BIT(31)
 80 
 81 #define DAVINCI_MCBSP_XCR_XWDLEN1(v)    ((v) << 5)
 82 #define DAVINCI_MCBSP_XCR_XFRLEN1(v)    ((v) << 8)
 83 #define DAVINCI_MCBSP_XCR_XDATDLY(v)    ((v) << 16)
 84 #define DAVINCI_MCBSP_XCR_XFIG          (1 << 18)
 85 #define DAVINCI_MCBSP_XCR_XWDLEN2(v)    ((v) << 21)
 86 #define DAVINCI_MCBSP_XCR_XFRLEN2(v)    ((v) << 24)
 87 #define DAVINCI_MCBSP_XCR_XPHASE        BIT(31)
 88 
 89 #define DAVINCI_MCBSP_SRGR_FWID(v)      ((v) << 8)
 90 #define DAVINCI_MCBSP_SRGR_FPER(v)      ((v) << 16)
 91 #define DAVINCI_MCBSP_SRGR_FSGM         (1 << 28)
 92 #define DAVINCI_MCBSP_SRGR_CLKSM        BIT(29)
 93 
 94 #define DAVINCI_MCBSP_PCR_CLKRP         (1 << 0)
 95 #define DAVINCI_MCBSP_PCR_CLKXP         (1 << 1)
 96 #define DAVINCI_MCBSP_PCR_FSRP          (1 << 2)
 97 #define DAVINCI_MCBSP_PCR_FSXP          (1 << 3)
 98 #define DAVINCI_MCBSP_PCR_SCLKME        (1 << 7)
 99 #define DAVINCI_MCBSP_PCR_CLKRM         (1 << 8)
100 #define DAVINCI_MCBSP_PCR_CLKXM         (1 << 9)
101 #define DAVINCI_MCBSP_PCR_FSRM          (1 << 10)
102 #define DAVINCI_MCBSP_PCR_FSXM          (1 << 11)
103 
104 enum {
105         DAVINCI_MCBSP_WORD_8 = 0,
106         DAVINCI_MCBSP_WORD_12,
107         DAVINCI_MCBSP_WORD_16,
108         DAVINCI_MCBSP_WORD_20,
109         DAVINCI_MCBSP_WORD_24,
110         DAVINCI_MCBSP_WORD_32,
111 };
112 
113 static const unsigned char asp_word_length[SNDRV_PCM_FORMAT_S32_LE + 1] = {
114         [SNDRV_PCM_FORMAT_S8]           = DAVINCI_MCBSP_WORD_8,
115         [SNDRV_PCM_FORMAT_S16_LE]       = DAVINCI_MCBSP_WORD_16,
116         [SNDRV_PCM_FORMAT_S24_LE]       = DAVINCI_MCBSP_WORD_24,
117         [SNDRV_PCM_FORMAT_S32_LE]       = DAVINCI_MCBSP_WORD_32,
118 };
119 
120 static const unsigned char double_fmt[SNDRV_PCM_FORMAT_S32_LE + 1] = {
121         [SNDRV_PCM_FORMAT_S8]           = SNDRV_PCM_FORMAT_S16_LE,
122         [SNDRV_PCM_FORMAT_S16_LE]       = SNDRV_PCM_FORMAT_S32_LE,
123 };
124 
125 struct davinci_mcbsp_dev {
126         struct device *dev;
127         struct snd_dmaengine_dai_dma_data dma_data[2];
128         int dma_request[2];
129         void __iomem                    *base;
130 #define MOD_DSP_A       0
131 #define MOD_DSP_B       1
132         int                             mode;
133         u32                             pcr;
134         struct clk                      *clk;
135         struct clk                      *ext_clk;
136         /*
137          * Combining both channels into 1 element will at least double the
138          * amount of time between servicing the dma channel, increase
139          * effiency, and reduce the chance of overrun/underrun. But,
140          * it will result in the left & right channels being swapped.
141          *
142          * If relabeling the left and right channels is not possible,
143          * you may want to let the codec know to swap them back.
144          *
145          * It may allow x10 the amount of time to service dma requests,
146          * if the codec is master and is using an unnecessarily fast bit clock
147          * (ie. tlvaic23b), independent of the sample rate. So, having an
148          * entire frame at once means it can be serviced at the sample rate
149          * instead of the bit clock rate.
150          *
151          * In the now unlikely case that an underrun still
152          * occurs, both the left and right samples will be repeated
153          * so that no pops are heard, and the left and right channels
154          * won't end up being swapped because of the underrun.
155          */
156         unsigned enable_channel_combine:1;
157 
158         unsigned int fmt;
159         int clk_div;
160         bool i2s_accurate_sck;
161 
162         int tdm_slots;
163         int slot_width;
164 
165         bool tx_framing_bit;
166         bool rx_framing_bit;
167 };
168 
169 static inline void davinci_mcbsp_write_reg(struct davinci_mcbsp_dev *dev,
170                                            int reg, u32 val)
171 {
172         __raw_writel(val, dev->base + reg);
173 }
174 
175 static inline u32 davinci_mcbsp_read_reg(struct davinci_mcbsp_dev *dev, int reg)
176 {
177         return __raw_readl(dev->base + reg);
178 }
179 
180 static void toggle_clock(struct davinci_mcbsp_dev *dev, int playback)
181 {
182         u32 m = playback ? DAVINCI_MCBSP_PCR_CLKXP : DAVINCI_MCBSP_PCR_CLKRP;
183         /* The clock needs to toggle to complete reset.
184          * So, fake it by toggling the clk polarity.
185          */
186         davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_PCR_REG, dev->pcr ^ m);
187         davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_PCR_REG, dev->pcr);
188 }
189 
190 static void davinci_mcbsp_start(struct davinci_mcbsp_dev *dev,
191                 struct snd_pcm_substream *substream)
192 {
193         int playback = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK);
194         u32 spcr;
195         u32 mask = playback ? DAVINCI_MCBSP_SPCR_XRST : DAVINCI_MCBSP_SPCR_RRST;
196 
197         /* Enable transmitter or receiver */
198         spcr = davinci_mcbsp_read_reg(dev, DAVINCI_MCBSP_SPCR_REG);
199         spcr |= mask;
200 
201         if (dev->pcr & (DAVINCI_MCBSP_PCR_FSXM | DAVINCI_MCBSP_PCR_FSRM)) {
202                 /* Start frame sync */
203                 spcr |= DAVINCI_MCBSP_SPCR_FRST;
204         }
205         davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_SPCR_REG, spcr);
206 }
207 
208 static void davinci_mcbsp_stop(struct davinci_mcbsp_dev *dev, int playback)
209 {
210         u32 spcr;
211 
212         /* Reset transmitter/receiver and sample rate/frame sync generators */
213         spcr = davinci_mcbsp_read_reg(dev, DAVINCI_MCBSP_SPCR_REG);
214         spcr &= ~(DAVINCI_MCBSP_SPCR_GRST | DAVINCI_MCBSP_SPCR_FRST);
215         spcr &= playback ? ~DAVINCI_MCBSP_SPCR_XRST : ~DAVINCI_MCBSP_SPCR_RRST;
216         davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_SPCR_REG, spcr);
217         toggle_clock(dev, playback);
218 }
219 
220 static int davinci_i2s_tdm_word_length(int tdm_slot_width)
221 {
222         switch (tdm_slot_width) {
223         case 8:
224                 return DAVINCI_MCBSP_WORD_8;
225         case 12:
226                 return DAVINCI_MCBSP_WORD_12;
227         case 16:
228                 return DAVINCI_MCBSP_WORD_16;
229         case 20:
230                 return DAVINCI_MCBSP_WORD_20;
231         case 24:
232                 return DAVINCI_MCBSP_WORD_24;
233         case 32:
234                 return DAVINCI_MCBSP_WORD_32;
235         default:
236                 return -EINVAL;
237         }
238 }
239 
240 static int davinci_i2s_set_tdm_slot(struct snd_soc_dai *cpu_dai,
241                                     unsigned int tx_mask,
242                                     unsigned int rx_mask,
243                                     int slots, int slot_width)
244 {
245         struct davinci_mcbsp_dev *dev = snd_soc_dai_get_drvdata(cpu_dai);
246 
247         dev_dbg(dev->dev, "slots %d, slot_width %d\n", slots, slot_width);
248 
249         if (slots > 128 || !slots) {
250                 dev_err(dev->dev, "Invalid number of slots\n");
251                 return -EINVAL;
252         }
253 
254         if (rx_mask != (1 << slots) - 1) {
255                 dev_err(dev->dev, "Invalid RX mask (0x%08x) : all slots must be used by McBSP\n",
256                         rx_mask);
257                 return -EINVAL;
258         }
259 
260         if (tx_mask != (1 << slots) - 1) {
261                 dev_err(dev->dev, "Invalid TX mask (0x%08x) : all slots must be used by McBSP\n",
262                         tx_mask);
263                 return -EINVAL;
264         }
265 
266         if (davinci_i2s_tdm_word_length(slot_width) < 0) {
267                 dev_err(dev->dev, "%s: Unsupported slot_width %d\n", __func__, slot_width);
268                 return -EINVAL;
269         }
270 
271         dev->tdm_slots = slots;
272         dev->slot_width = slot_width;
273 
274         return 0;
275 }
276 
277 #define DEFAULT_BITPERSAMPLE    16
278 
279 static int davinci_i2s_set_dai_fmt(struct snd_soc_dai *cpu_dai,
280                                    unsigned int fmt)
281 {
282         struct davinci_mcbsp_dev *dev = snd_soc_dai_get_drvdata(cpu_dai);
283         unsigned int pcr;
284         unsigned int spcr;
285         unsigned int srgr;
286         bool inv_fs = false;
287         /* Attention srgr is updated by hw_params! */
288         srgr = DAVINCI_MCBSP_SRGR_FSGM |
289                 DAVINCI_MCBSP_SRGR_FPER(DEFAULT_BITPERSAMPLE * 2 - 1) |
290                 DAVINCI_MCBSP_SRGR_FWID(DEFAULT_BITPERSAMPLE - 1);
291 
292         dev->fmt = fmt;
293 
294         spcr = davinci_mcbsp_read_reg(dev, DAVINCI_MCBSP_SPCR_REG);
295         switch (fmt & SND_SOC_DAIFMT_CLOCK_MASK) {
296         case SND_SOC_DAIFMT_CONT:
297                 spcr |= DAVINCI_MCBSP_SPCR_FREE;
298                 dev_dbg(dev->dev, "Free-running mode ON\n");
299                 break;
300         case SND_SOC_DAIFMT_GATED:
301                 spcr &= ~DAVINCI_MCBSP_SPCR_FREE;
302                 dev_dbg(dev->dev, "Free-running mode OFF\n");
303                 break;
304         default:
305                 dev_err(dev->dev, "Invalid clock gating\n");
306                 return -EINVAL;
307         }
308         davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_SPCR_REG, spcr);
309 
310         /* set master/slave audio interface */
311         switch (fmt & SND_SOC_DAIFMT_CLOCK_PROVIDER_MASK) {
312         case SND_SOC_DAIFMT_BP_FP:
313                 /* cpu is master */
314                 pcr = DAVINCI_MCBSP_PCR_FSXM |
315                         DAVINCI_MCBSP_PCR_FSRM |
316                         DAVINCI_MCBSP_PCR_CLKXM |
317                         DAVINCI_MCBSP_PCR_CLKRM;
318                 break;
319         case SND_SOC_DAIFMT_BC_FP:
320                 if (dev->tdm_slots || dev->slot_width) {
321                         dev_err(dev->dev, "TDM is not supported for BC_FP format\n");
322                         return -EINVAL;
323                 }
324 
325                 /*
326                  * McBSP CLKR pin is the input for the Sample Rate Generator.
327                  * McBSP FSR and FSX are driven by the Sample Rate Generator.
328                  */
329                 pcr = DAVINCI_MCBSP_PCR_FSRM | DAVINCI_MCBSP_PCR_FSXM;
330                 pcr |= DAVINCI_MCBSP_PCR_SCLKME;
331                 break;
332         case SND_SOC_DAIFMT_BP_FC:
333                 /* cpu is bitclock provider */
334                 pcr = DAVINCI_MCBSP_PCR_CLKXM |
335                         DAVINCI_MCBSP_PCR_CLKRM;
336                 break;
337 
338         case SND_SOC_DAIFMT_BC_FC:
339                 if (dev->tdm_slots || dev->slot_width) {
340                         dev_err(dev->dev, "TDM is not supported for BC_FC format\n");
341                         return -EINVAL;
342                 }
343 
344                 /* codec is master */
345                 pcr = 0;
346                 break;
347         default:
348                 printk(KERN_ERR "%s:bad master\n", __func__);
349                 return -EINVAL;
350         }
351 
352         /* interface format */
353         switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
354         case SND_SOC_DAIFMT_I2S:
355                 /* Davinci doesn't support TRUE I2S, but some codecs will have
356                  * the left and right channels contiguous. This allows
357                  * dsp_a mode to be used with an inverted normal frame clk.
358                  * If your codec is master and does not have contiguous
359                  * channels, then you will have sound on only one channel.
360                  * Try using a different mode, or codec as slave.
361                  *
362                  * The TLV320AIC33 is an example of a codec where this works.
363                  * It has a variable bit clock frequency allowing it to have
364                  * valid data on every bit clock.
365                  *
366                  * The TLV320AIC23 is an example of a codec where this does not
367                  * work. It has a fixed bit clock frequency with progressively
368                  * more empty bit clock slots between channels as the sample
369                  * rate is lowered.
370                  */
371                 inv_fs = true;
372                 fallthrough;
373         case SND_SOC_DAIFMT_DSP_A:
374                 dev->mode = MOD_DSP_A;
375                 break;
376         case SND_SOC_DAIFMT_DSP_B:
377                 dev->mode = MOD_DSP_B;
378                 break;
379         default:
380                 printk(KERN_ERR "%s:bad format\n", __func__);
381                 return -EINVAL;
382         }
383 
384         switch (fmt & SND_SOC_DAIFMT_INV_MASK) {
385         case SND_SOC_DAIFMT_NB_NF:
386                 /* CLKRP Receive clock polarity,
387                  *      1 - sampled on rising edge of CLKR
388                  *      valid on rising edge
389                  * CLKXP Transmit clock polarity,
390                  *      1 - clocked on falling edge of CLKX
391                  *      valid on rising edge
392                  * FSRP  Receive frame sync pol, 0 - active high
393                  * FSXP  Transmit frame sync pol, 0 - active high
394                  */
395                 pcr |= (DAVINCI_MCBSP_PCR_CLKXP | DAVINCI_MCBSP_PCR_CLKRP);
396                 break;
397         case SND_SOC_DAIFMT_IB_IF:
398                 /* CLKRP Receive clock polarity,
399                  *      0 - sampled on falling edge of CLKR
400                  *      valid on falling edge
401                  * CLKXP Transmit clock polarity,
402                  *      0 - clocked on rising edge of CLKX
403                  *      valid on falling edge
404                  * FSRP  Receive frame sync pol, 1 - active low
405                  * FSXP  Transmit frame sync pol, 1 - active low
406                  */
407                 pcr |= (DAVINCI_MCBSP_PCR_FSXP | DAVINCI_MCBSP_PCR_FSRP);
408                 break;
409         case SND_SOC_DAIFMT_NB_IF:
410                 /* CLKRP Receive clock polarity,
411                  *      1 - sampled on rising edge of CLKR
412                  *      valid on rising edge
413                  * CLKXP Transmit clock polarity,
414                  *      1 - clocked on falling edge of CLKX
415                  *      valid on rising edge
416                  * FSRP  Receive frame sync pol, 1 - active low
417                  * FSXP  Transmit frame sync pol, 1 - active low
418                  */
419                 pcr |= (DAVINCI_MCBSP_PCR_CLKXP | DAVINCI_MCBSP_PCR_CLKRP |
420                         DAVINCI_MCBSP_PCR_FSXP | DAVINCI_MCBSP_PCR_FSRP);
421                 break;
422         case SND_SOC_DAIFMT_IB_NF:
423                 /* CLKRP Receive clock polarity,
424                  *      0 - sampled on falling edge of CLKR
425                  *      valid on falling edge
426                  * CLKXP Transmit clock polarity,
427                  *      0 - clocked on rising edge of CLKX
428                  *      valid on falling edge
429                  * FSRP  Receive frame sync pol, 0 - active high
430                  * FSXP  Transmit frame sync pol, 0 - active high
431                  */
432                 break;
433         default:
434                 return -EINVAL;
435         }
436         if (inv_fs == true)
437                 pcr ^= (DAVINCI_MCBSP_PCR_FSXP | DAVINCI_MCBSP_PCR_FSRP);
438         davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_SRGR_REG, srgr);
439         dev->pcr = pcr;
440         davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_PCR_REG, pcr);
441         return 0;
442 }
443 
444 static int davinci_i2s_dai_set_clkdiv(struct snd_soc_dai *cpu_dai,
445                                 int div_id, int div)
446 {
447         struct davinci_mcbsp_dev *dev = snd_soc_dai_get_drvdata(cpu_dai);
448 
449         if (div_id != DAVINCI_MCBSP_CLKGDV)
450                 return -ENODEV;
451 
452         dev->clk_div = div;
453         return 0;
454 }
455 
456 static int davinci_i2s_hw_params(struct snd_pcm_substream *substream,
457                                  struct snd_pcm_hw_params *params,
458                                  struct snd_soc_dai *dai)
459 {
460         struct davinci_mcbsp_dev *dev = snd_soc_dai_get_drvdata(dai);
461         struct snd_interval *i = NULL;
462         int mcbsp_word_length, master;
463         unsigned int clk_div, freq, framesize;
464         unsigned int srgr = 0;
465         unsigned int rcr = 0;
466         unsigned int xcr = 0;
467         u32 spcr;
468         snd_pcm_format_t fmt;
469         unsigned element_cnt = 1;
470 
471         spcr = davinci_mcbsp_read_reg(dev, DAVINCI_MCBSP_SPCR_REG);
472 
473         /* Determine xfer data type */
474         fmt = params_format(params);
475         switch (fmt) {
476         case SNDRV_PCM_FORMAT_S16_LE:
477         case SNDRV_PCM_FORMAT_S32_LE:
478                 break;
479         case SNDRV_PCM_FORMAT_S24_LE:
480                 spcr |= DAVINCI_MCBSP_SPCR_RJUST_S_LE;
481                 break;
482         default:
483                 dev_warn(dev->dev, "davinci-i2s: unsupported PCM format\n");
484                 return -EINVAL;
485         }
486 
487         /* general line settings */
488         if (substream->stream == SNDRV_PCM_STREAM_CAPTURE) {
489                 spcr |= DAVINCI_MCBSP_SPCR_RINTM(3);
490                 davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_SPCR_REG, spcr);
491         } else {
492                 spcr |= DAVINCI_MCBSP_SPCR_XINTM(3);
493                 davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_SPCR_REG, spcr);
494         }
495 
496         master = dev->fmt & SND_SOC_DAIFMT_CLOCK_PROVIDER_MASK;
497         fmt = params_format(params);
498         if (dev->slot_width)
499                 mcbsp_word_length = davinci_i2s_tdm_word_length(dev->slot_width);
500         else
501                 mcbsp_word_length = asp_word_length[fmt];
502 
503         if (mcbsp_word_length < 0)
504                 return mcbsp_word_length;
505 
506         switch (master) {
507         case SND_SOC_DAIFMT_BP_FP:
508                 if (dev->ext_clk) {
509                         freq = clk_get_rate(dev->ext_clk);
510                 } else {
511                         freq = clk_get_rate(dev->clk);
512                         srgr = DAVINCI_MCBSP_SRGR_CLKSM;
513                 }
514                 srgr |= DAVINCI_MCBSP_SRGR_FSGM;
515                 srgr |= DAVINCI_MCBSP_SRGR_FWID(mcbsp_word_length *
516                                                 8 - 1);
517                 if (dev->i2s_accurate_sck) {
518                         clk_div = 256;
519                         do {
520                                 framesize = (freq / (--clk_div)) /
521                                 params->rate_num *
522                                         params->rate_den;
523                         } while (((framesize < 33) || (framesize > 4095)) &&
524                                  (clk_div));
525                         clk_div--;
526                         srgr |= DAVINCI_MCBSP_SRGR_FPER(framesize - 1);
527                 } else {
528                         /* symmetric waveforms */
529                         clk_div = freq / (mcbsp_word_length * 16) /
530                                   params->rate_num * params->rate_den;
531                         srgr |= DAVINCI_MCBSP_SRGR_FPER(mcbsp_word_length *
532                                                         16 - 1);
533                 }
534                 clk_div &= 0xFF;
535                 srgr |= clk_div;
536                 break;
537         case SND_SOC_DAIFMT_BC_FP:
538                 srgr = DAVINCI_MCBSP_SRGR_FSGM;
539                 clk_div = dev->clk_div - 1;
540                 srgr |= DAVINCI_MCBSP_SRGR_FWID(mcbsp_word_length * 8 - 1);
541                 srgr |= DAVINCI_MCBSP_SRGR_FPER(mcbsp_word_length * 16 - 1);
542                 clk_div &= 0xFF;
543                 srgr |= clk_div;
544                 break;
545         case SND_SOC_DAIFMT_BP_FC:
546                 if (dev->ext_clk) {
547                         freq = clk_get_rate(dev->ext_clk);
548                 } else {
549                         freq = clk_get_rate(dev->clk);
550                         srgr = DAVINCI_MCBSP_SRGR_CLKSM;
551                 }
552                 if (dev->tdm_slots && dev->slot_width) {
553                         clk_div = freq / (params->rate_num * params->rate_den)
554                                  / (dev->tdm_slots * dev->slot_width) - 1;
555                 } else {
556                         clk_div = freq / (mcbsp_word_length * 16) /
557                                   params->rate_num * params->rate_den;
558                 }
559                 clk_div &= 0xFF;
560                 srgr |= clk_div;
561                 break;
562         case SND_SOC_DAIFMT_BC_FC:
563                 /* Clock and frame sync given from external sources */
564                 i = hw_param_interval(params, SNDRV_PCM_HW_PARAM_SAMPLE_BITS);
565                 srgr = DAVINCI_MCBSP_SRGR_FSGM;
566                 srgr |= DAVINCI_MCBSP_SRGR_FWID(snd_interval_value(i) - 1);
567                 pr_debug("%s - %d  FWID set: re-read srgr = %X\n",
568                         __func__, __LINE__, snd_interval_value(i) - 1);
569 
570                 i = hw_param_interval(params, SNDRV_PCM_HW_PARAM_FRAME_BITS);
571                 srgr |= DAVINCI_MCBSP_SRGR_FPER(snd_interval_value(i) - 1);
572                 break;
573         default:
574                 return -EINVAL;
575         }
576         davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_SRGR_REG, srgr);
577 
578         if (dev->mode == MOD_DSP_B) {
579                 rcr |= DAVINCI_MCBSP_RCR_RDATDLY(0);
580                 xcr |= DAVINCI_MCBSP_XCR_XDATDLY(0);
581         } else {
582                 rcr |= DAVINCI_MCBSP_RCR_RDATDLY(1);
583                 xcr |= DAVINCI_MCBSP_XCR_XDATDLY(1);
584         }
585 
586         if (dev->tx_framing_bit) {
587                 xcr &= ~DAVINCI_MCBSP_XCR_XDATDLY(1);
588                 xcr |= DAVINCI_MCBSP_XCR_XDATDLY(2);
589         }
590         if (dev->rx_framing_bit) {
591                 rcr &= ~DAVINCI_MCBSP_RCR_RDATDLY(1);
592                 rcr |= DAVINCI_MCBSP_RCR_RDATDLY(2);
593         }
594 
595         if (params_channels(params) == 2) {
596                 element_cnt = 2;
597                 if (double_fmt[fmt] && dev->enable_channel_combine) {
598                         element_cnt = 1;
599                         fmt = double_fmt[fmt];
600                 }
601                 switch (master) {
602                 case SND_SOC_DAIFMT_BP_FP:
603                 case SND_SOC_DAIFMT_BP_FC:
604                         rcr |= DAVINCI_MCBSP_RCR_RFRLEN2(0);
605                         xcr |= DAVINCI_MCBSP_XCR_XFRLEN2(0);
606                         rcr |= DAVINCI_MCBSP_RCR_RPHASE;
607                         xcr |= DAVINCI_MCBSP_XCR_XPHASE;
608                         break;
609                 case SND_SOC_DAIFMT_BC_FC:
610                 case SND_SOC_DAIFMT_BC_FP:
611                         rcr |= DAVINCI_MCBSP_RCR_RFRLEN2(element_cnt - 1);
612                         xcr |= DAVINCI_MCBSP_XCR_XFRLEN2(element_cnt - 1);
613                         break;
614                 default:
615                         return -EINVAL;
616                 }
617         }
618 
619         switch (master) {
620         case SND_SOC_DAIFMT_BP_FP:
621         case SND_SOC_DAIFMT_BP_FC:
622                 if (dev->tdm_slots > 0) {
623                         rcr |= DAVINCI_MCBSP_RCR_RFRLEN1(dev->tdm_slots - 1);
624                         xcr |= DAVINCI_MCBSP_XCR_XFRLEN1(dev->tdm_slots - 1);
625                 } else {
626                         rcr |= DAVINCI_MCBSP_RCR_RFRLEN1(0);
627                         xcr |= DAVINCI_MCBSP_XCR_XFRLEN1(0);
628                 }
629                 break;
630         case SND_SOC_DAIFMT_BC_FC:
631         case SND_SOC_DAIFMT_BC_FP:
632                 rcr |= DAVINCI_MCBSP_RCR_RFRLEN1(element_cnt - 1);
633                 xcr |= DAVINCI_MCBSP_XCR_XFRLEN1(element_cnt - 1);
634                 break;
635         default:
636                 return -EINVAL;
637         }
638 
639         rcr |= DAVINCI_MCBSP_RCR_RWDLEN1(mcbsp_word_length) |
640                 DAVINCI_MCBSP_RCR_RWDLEN2(mcbsp_word_length);
641         xcr |= DAVINCI_MCBSP_XCR_XWDLEN1(mcbsp_word_length) |
642                 DAVINCI_MCBSP_XCR_XWDLEN2(mcbsp_word_length);
643 
644         if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
645                 davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_XCR_REG, xcr);
646         else
647                 davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_RCR_REG, rcr);
648 
649         pr_debug("%s - %d  srgr=%X\n", __func__, __LINE__, srgr);
650         pr_debug("%s - %d  xcr=%X\n", __func__, __LINE__, xcr);
651         pr_debug("%s - %d  rcr=%X\n", __func__, __LINE__, rcr);
652         return 0;
653 }
654 
655 static int davinci_i2s_prepare(struct snd_pcm_substream *substream,
656                 struct snd_soc_dai *dai)
657 {
658         struct davinci_mcbsp_dev *dev = snd_soc_dai_get_drvdata(dai);
659         int playback = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK);
660         u32 spcr;
661         u32 mask = playback ? DAVINCI_MCBSP_SPCR_XRST : DAVINCI_MCBSP_SPCR_RRST;
662 
663         davinci_mcbsp_stop(dev, playback);
664 
665         spcr = davinci_mcbsp_read_reg(dev, DAVINCI_MCBSP_SPCR_REG);
666         if (spcr & mask) {
667                 /* start off disabled */
668                 davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_SPCR_REG,
669                                         spcr & ~mask);
670                 toggle_clock(dev, playback);
671         }
672         if (dev->pcr & (DAVINCI_MCBSP_PCR_FSXM | DAVINCI_MCBSP_PCR_FSRM |
673                         DAVINCI_MCBSP_PCR_CLKXM | DAVINCI_MCBSP_PCR_CLKRM)) {
674                 /* Start the sample generator */
675                 spcr |= DAVINCI_MCBSP_SPCR_GRST;
676                 davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_SPCR_REG, spcr);
677         }
678 
679         if (playback) {
680                 /* Enable the transmitter */
681                 spcr = davinci_mcbsp_read_reg(dev, DAVINCI_MCBSP_SPCR_REG);
682                 spcr |= DAVINCI_MCBSP_SPCR_XRST;
683                 davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_SPCR_REG, spcr);
684 
685                 /* wait for any unexpected frame sync error to occur */
686                 udelay(100);
687 
688                 /* Disable the transmitter to clear any outstanding XSYNCERR */
689                 spcr = davinci_mcbsp_read_reg(dev, DAVINCI_MCBSP_SPCR_REG);
690                 spcr &= ~DAVINCI_MCBSP_SPCR_XRST;
691                 davinci_mcbsp_write_reg(dev, DAVINCI_MCBSP_SPCR_REG, spcr);
692                 toggle_clock(dev, playback);
693         }
694 
695         return 0;
696 }
697 
698 static int davinci_i2s_trigger(struct snd_pcm_substream *substream, int cmd,
699                                struct snd_soc_dai *dai)
700 {
701         struct davinci_mcbsp_dev *dev = snd_soc_dai_get_drvdata(dai);
702         int ret = 0;
703         int playback = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK);
704 
705         switch (cmd) {
706         case SNDRV_PCM_TRIGGER_START:
707         case SNDRV_PCM_TRIGGER_RESUME:
708         case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
709                 davinci_mcbsp_start(dev, substream);
710                 break;
711         case SNDRV_PCM_TRIGGER_STOP:
712         case SNDRV_PCM_TRIGGER_SUSPEND:
713         case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
714                 davinci_mcbsp_stop(dev, playback);
715                 break;
716         default:
717                 ret = -EINVAL;
718         }
719         return ret;
720 }
721 
722 static void davinci_i2s_shutdown(struct snd_pcm_substream *substream,
723                 struct snd_soc_dai *dai)
724 {
725         struct davinci_mcbsp_dev *dev = snd_soc_dai_get_drvdata(dai);
726         int playback = (substream->stream == SNDRV_PCM_STREAM_PLAYBACK);
727         davinci_mcbsp_stop(dev, playback);
728 }
729 
730 #define DAVINCI_I2S_RATES       SNDRV_PCM_RATE_8000_96000
731 #define DAVINCI_I2S_FORMATS     (SNDRV_PCM_FMTBIT_S16_LE | \
732                                  SNDRV_PCM_FMTBIT_S24_LE | \
733                                  SNDRV_PCM_FMTBIT_S32_LE)
734 
735 static int davinci_i2s_dai_probe(struct snd_soc_dai *dai)
736 {
737         struct davinci_mcbsp_dev *dev = snd_soc_dai_get_drvdata(dai);
738         int stream;
739 
740         for_each_pcm_streams(stream)
741                 snd_soc_dai_dma_data_set(dai, stream, &dev->dma_data[stream]);
742 
743         return 0;
744 }
745 
746 static const struct snd_soc_dai_ops davinci_i2s_dai_ops = {
747         .probe          = davinci_i2s_dai_probe,
748         .shutdown       = davinci_i2s_shutdown,
749         .prepare        = davinci_i2s_prepare,
750         .trigger        = davinci_i2s_trigger,
751         .hw_params      = davinci_i2s_hw_params,
752         .set_fmt        = davinci_i2s_set_dai_fmt,
753         .set_clkdiv     = davinci_i2s_dai_set_clkdiv,
754         .set_tdm_slot   = davinci_i2s_set_tdm_slot,
755 
756 };
757 
758 static struct snd_soc_dai_driver davinci_i2s_dai = {
759         .playback = {
760                 .channels_min = 2,
761                 .channels_max = 128,
762                 .rates = DAVINCI_I2S_RATES,
763                 .formats = DAVINCI_I2S_FORMATS,
764         },
765         .capture = {
766                 .channels_min = 2,
767                 .channels_max = 128,
768                 .rates = DAVINCI_I2S_RATES,
769                 .formats = DAVINCI_I2S_FORMATS,
770         },
771         .ops = &davinci_i2s_dai_ops,
772 
773 };
774 
775 static const struct snd_soc_component_driver davinci_i2s_component = {
776         .name                   = DRV_NAME,
777         .legacy_dai_naming      = 1,
778 };
779 
780 static int davinci_i2s_probe(struct platform_device *pdev)
781 {
782         struct snd_dmaengine_dai_dma_data *dma_data;
783         struct davinci_mcbsp_dev *dev;
784         struct resource *mem, *res;
785         void __iomem *io_base;
786         int *dma;
787         int ret;
788 
789         mem = platform_get_resource_byname(pdev, IORESOURCE_MEM, "mpu");
790         if (!mem) {
791                 dev_warn(&pdev->dev,
792                          "\"mpu\" mem resource not found, using index 0\n");
793                 mem = platform_get_resource(pdev, IORESOURCE_MEM, 0);
794                 if (!mem) {
795                         dev_err(&pdev->dev, "no mem resource?\n");
796                         return -ENODEV;
797                 }
798         }
799 
800         io_base = devm_ioremap_resource(&pdev->dev, mem);
801         if (IS_ERR(io_base))
802                 return PTR_ERR(io_base);
803 
804         dev = devm_kzalloc(&pdev->dev, sizeof(struct davinci_mcbsp_dev),
805                            GFP_KERNEL);
806         if (!dev)
807                 return -ENOMEM;
808 
809         dev->base = io_base;
810 
811         dev->tx_framing_bit = of_property_read_bool(pdev->dev.of_node, "ti,T1-framing-tx");
812         dev->rx_framing_bit = of_property_read_bool(pdev->dev.of_node, "ti,T1-framing-rx");
813 
814         /* setup DMA, first TX, then RX */
815         dma_data = &dev->dma_data[SNDRV_PCM_STREAM_PLAYBACK];
816         dma_data->addr = (dma_addr_t)(mem->start + DAVINCI_MCBSP_DXR_REG);
817 
818         res = platform_get_resource(pdev, IORESOURCE_DMA, 0);
819         if (res) {
820                 dma = &dev->dma_request[SNDRV_PCM_STREAM_PLAYBACK];
821                 *dma = res->start;
822                 dma_data->filter_data = dma;
823         } else if (IS_ENABLED(CONFIG_OF) && pdev->dev.of_node) {
824                 dma_data->filter_data = "tx";
825         } else {
826                 dev_err(&pdev->dev, "Missing DMA tx resource\n");
827                 return -ENODEV;
828         }
829 
830         dma_data = &dev->dma_data[SNDRV_PCM_STREAM_CAPTURE];
831         dma_data->addr = (dma_addr_t)(mem->start + DAVINCI_MCBSP_DRR_REG);
832 
833         res = platform_get_resource(pdev, IORESOURCE_DMA, 1);
834         if (res) {
835                 dma = &dev->dma_request[SNDRV_PCM_STREAM_CAPTURE];
836                 *dma = res->start;
837                 dma_data->filter_data = dma;
838         } else if (IS_ENABLED(CONFIG_OF) && pdev->dev.of_node) {
839                 dma_data->filter_data = "rx";
840         } else {
841                 dev_err(&pdev->dev, "Missing DMA rx resource\n");
842                 return -ENODEV;
843         }
844 
845         /*
846          * The optional is there for backward compatibility.
847          * If 'fck' is not present, the clk_get(dev, NULL) that follows may find something
848          */
849         dev->clk = devm_clk_get_optional(&pdev->dev, "fck");
850         if (IS_ERR(dev->clk))
851                 return dev_err_probe(&pdev->dev, PTR_ERR(dev->clk), "Invalid functional clock\n");
852         if (!dev->clk) {
853                 dev->clk = devm_clk_get(&pdev->dev, NULL);
854                 if (IS_ERR(dev->clk))
855                         return dev_err_probe(&pdev->dev, PTR_ERR(dev->clk),
856                                              "Missing functional clock\n");
857         }
858 
859         dev->ext_clk = devm_clk_get_optional(&pdev->dev, "clks");
860         if (IS_ERR(dev->ext_clk))
861                 return dev_err_probe(&pdev->dev, PTR_ERR(dev->ext_clk), "Invalid external clock\n");
862 
863         ret = clk_prepare_enable(dev->clk);
864         if (ret)
865                 return ret;
866 
867         if (dev->ext_clk) {
868                 dev_dbg(&pdev->dev, "External clock used for sample rate generator\n");
869                 ret = clk_prepare_enable(dev->ext_clk);
870                 if (ret) {
871                         dev_err_probe(&pdev->dev, ret, "Failed to enable external clock\n");
872                         goto err_disable_clk;
873                 }
874         }
875 
876         dev->dev = &pdev->dev;
877         dev_set_drvdata(&pdev->dev, dev);
878 
879         ret = snd_soc_register_component(&pdev->dev, &davinci_i2s_component,
880                                          &davinci_i2s_dai, 1);
881         if (ret != 0)
882                 goto err_disable_ext_clk;
883 
884         ret = edma_pcm_platform_register(&pdev->dev);
885         if (ret) {
886                 dev_err_probe(&pdev->dev, ret, "register PCM failed\n");
887                 goto err_unregister_component;
888         }
889 
890         return 0;
891 
892 err_unregister_component:
893         snd_soc_unregister_component(&pdev->dev);
894 err_disable_ext_clk:
895         if (dev->ext_clk)
896                 clk_disable_unprepare(dev->ext_clk);
897 err_disable_clk:
898         clk_disable_unprepare(dev->clk);
899 
900         return ret;
901 }
902 
903 static void davinci_i2s_remove(struct platform_device *pdev)
904 {
905         struct davinci_mcbsp_dev *dev = dev_get_drvdata(&pdev->dev);
906 
907         snd_soc_unregister_component(&pdev->dev);
908 
909         clk_disable_unprepare(dev->clk);
910 
911         if (dev->ext_clk)
912                 clk_disable_unprepare(dev->ext_clk);
913 }
914 
915 static const struct of_device_id davinci_i2s_match[] __maybe_unused = {
916         { .compatible = "ti,da850-mcbsp" },
917         {},
918 };
919 MODULE_DEVICE_TABLE(of, davinci_i2s_match);
920 
921 static struct platform_driver davinci_mcbsp_driver = {
922         .probe          = davinci_i2s_probe,
923         .remove_new     = davinci_i2s_remove,
924         .driver         = {
925                 .name   = "davinci-mcbsp",
926                 .of_match_table = of_match_ptr(davinci_i2s_match),
927         },
928 };
929 
930 module_platform_driver(davinci_mcbsp_driver);
931 
932 MODULE_AUTHOR("Vladimir Barinov");
933 MODULE_DESCRIPTION("TI DAVINCI I2S (McBSP) SoC Interface");
934 MODULE_LICENSE("GPL");
935 

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

kernel.org | git.kernel.org | LWN.net | Project Home | SVN repository | Mail admin

Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.

sflogo.php