• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2021–2022 Beijing OSWare Technology Co., Ltd
3  * This file contains confidential and proprietary information of
4  * OSWare Technology Co., Ltd
5  *
6  * Licensed under the Apache License, Version 2.0 (the "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  * http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  */
18 
19 #include <linux/clk.h>
20 #include <linux/clk/clk-conf.h>
21 #include <linux/clk-provider.h>
22 #include <linux/delay.h>
23 #include <linux/dmaengine.h>
24 #include <linux/module.h>
25 #include <linux/of_address.h>
26 #include <linux/of_device.h>
27 #include <linux/pm_runtime.h>
28 #include <linux/regmap.h>
29 #include <linux/slab.h>
30 #include <linux/time.h>
31 #include <linux/mfd/syscon/imx6q-iomuxc-gpr.h>
32 #include <linux/mfd/syscon.h>
33 #include <linux/interrupt.h>
34 #include <linux/pinctrl/consumer.h>
35 #include <linux/busfreq-imx.h>
36 
37 #include "audio_driver_log.h"
38 #include "imx8mm_platform.h"
39 #include "imx8mm_common.h"
40 #include "osal_mem.h"
41 #include "sai_driver.h"
42 
43 #include "osal_io.h"
44 #include "osal_irq.h"
45 #include "osal_sem.h"
46 #include "osal_time.h"
47 
48 #define HDF_LOG_TAG imx8mm_sai_driver
49 
50 #define FSL_SAI_FLAGS (FSL_SAI_CSR_SEIE | FSL_SAI_CSR_FEIE)
51 
52 #define FSL_SAI_VERID_0301 (0x0301)
53 struct fsl_sai *g_sai;
54 #define BYTE_NUM  (8)
55 
GetDrvSai(const struct PlatformData * pd)56 static struct fsl_sai *GetDrvSai(const struct PlatformData *pd)
57 {
58     struct PrivPlatformData *ppd = NULL;
59     if (pd == NULL) {
60         AUDIO_DRIVER_LOG_ERR("get drv sai: the input platform data is null");
61         return NULL;
62     }
63     ppd = (struct PrivPlatformData *)pd->dmaPrv;
64     if (ppd != NULL) {
65         return &(ppd->sai);
66     }
67 
68     return NULL;
69 }
70 
SaiPrintTFRegister(void)71 int32_t SaiPrintTFRegister(void)
72 {
73     struct fsl_sai *sai = g_sai;
74     u32 read_val = 0;
75 
76     regmap_read(sai->regmap, FSL_SAI_TFR0, &read_val);
77     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TFR0 %08x", read_val);
78     regmap_read(sai->regmap, FSL_SAI_TFR1, &read_val);
79     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TFR1 %08x", read_val);
80     regmap_read(sai->regmap, FSL_SAI_TFR2, &read_val);
81     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TFR2 %08x", read_val);
82     regmap_read(sai->regmap, FSL_SAI_TFR3, &read_val);
83     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TFR3 %08x", read_val);
84     regmap_read(sai->regmap, FSL_SAI_TFR4, &read_val);
85     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TFR4 %08x", read_val);
86     regmap_read(sai->regmap, FSL_SAI_TFR5, &read_val);
87     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TFR5 %08x", read_val);
88     regmap_read(sai->regmap, FSL_SAI_TFR6, &read_val);
89     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TFR6 %08x", read_val);
90     regmap_read(sai->regmap, FSL_SAI_TFR7, &read_val);
91     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TFR7 %08x", read_val);
92 
93     return 0;
94 }
95 
SaiPrintTDRegister(void)96 int32_t SaiPrintTDRegister(void)
97 {
98     struct fsl_sai *sai = g_sai;
99     u32 read_val = 0;
100 
101     regmap_read(sai->regmap, FSL_SAI_TDR0, &read_val);
102     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TDR0 %08x", read_val);
103     regmap_read(sai->regmap, FSL_SAI_TDR1, &read_val);
104     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TDR1 %08x", read_val);
105     regmap_read(sai->regmap, FSL_SAI_TDR2, &read_val);
106     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TDR2 %08x", read_val);
107     regmap_read(sai->regmap, FSL_SAI_TDR3, &read_val);
108     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TDR3 %08x", read_val);
109     regmap_read(sai->regmap, FSL_SAI_TDR4, &read_val);
110     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TDR4 %08x", read_val);
111     regmap_read(sai->regmap, FSL_SAI_TDR5, &read_val);
112     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TDR5 %08x", read_val);
113     regmap_read(sai->regmap, FSL_SAI_TDR6, &read_val);
114     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TDR6 %08x", read_val);
115     regmap_read(sai->regmap, FSL_SAI_TDR7, &read_val);
116     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TDR7 %08x", read_val);
117 
118     return 0;
119 }
120 
SaiPrintAllRegister(void)121 int32_t SaiPrintAllRegister(void)
122 {
123     struct fsl_sai *sai = g_sai;
124     u32 read_val = 0;
125     regmap_read(sai->regmap, FSL_SAI_TCSR(BYTE_NUM), &read_val);
126     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TCSR %08x", read_val);
127     regmap_read(sai->regmap, FSL_SAI_TCR1(BYTE_NUM), &read_val);
128     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TCR1 %08x", read_val);
129     regmap_read(sai->regmap, FSL_SAI_TCR2(BYTE_NUM), &read_val);
130     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TCR2 %08x", read_val);
131     regmap_read(sai->regmap, FSL_SAI_TCR3(BYTE_NUM), &read_val);
132     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TCR3 %08x", read_val);
133     regmap_read(sai->regmap, FSL_SAI_TCR4(BYTE_NUM), &read_val);
134     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TCR4 %08x", read_val);
135     regmap_read(sai->regmap, FSL_SAI_TCR5(BYTE_NUM), &read_val);
136     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TCR5 %08x", read_val);
137 
138     SaiPrintTDRegister();
139     SaiPrintTFRegister();
140 
141     regmap_read(sai->regmap, FSL_SAI_TMR, &read_val);
142     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TMR %08x", read_val);
143     regmap_read(sai->regmap, FSL_SAI_TTCTL, &read_val);
144     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TTCTL %08x", read_val);
145     regmap_read(sai->regmap, FSL_SAI_TTCTN, &read_val);
146     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TTCTN %08x", read_val);
147     regmap_read(sai->regmap, FSL_SAI_TTCAP, &read_val);
148     AUDIO_DRIVER_LOG_ERR("FSL_SAI_TTCAP %08x", read_val);
149     regmap_read(sai->regmap, FSL_SAI_MCTL, &read_val);
150     AUDIO_DRIVER_LOG_ERR("FSL_SAI_MCTL %08x", read_val);
151     regmap_read(sai->regmap, FSL_SAI_MDIV, &read_val);
152     AUDIO_DRIVER_LOG_ERR("FSL_SAI_MDIV %08x", read_val);
153 
154     return 0;
155 }
156 
fsl_sai_rx_irq(int irq,void * devid)157 static bool fsl_sai_rx_irq(int irq, void *devid)
158 {
159     u32 flags = 0, xcsr = 0, mask = 0;
160     bool irq_none = true;
161     struct PrivPlatformData *ppd = (struct PrivPlatformData *)devid;
162     struct fsl_sai *sai = (struct fsl_sai *)&(ppd->sai);
163     unsigned char offset = sai->reg_offset;
164 
165     regmap_read(sai->regmap, FSL_SAI_RCSR(offset), &xcsr);
166     flags = xcsr & mask;
167 
168     if (flags) {
169         irq_none = false;
170     } else {
171         if (irq_none) {
172             return IRQ_NONE;
173         } else {
174             return IRQ_HANDLED;
175         }
176     }
177 
178     if (flags & FSL_SAI_CSR_FEF) {
179         AUDIO_DRIVER_LOG_ERR("isr: Receive overflow detected\n");
180         /* FIFO reset for safety */
181         xcsr |= FSL_SAI_CSR_FR;
182     }
183 
184     flags &= FSL_SAI_CSR_xF_W_MASK;
185     xcsr &= ~FSL_SAI_CSR_xF_MASK;
186 
187     if (flags) {
188         regmap_write(sai->regmap, FSL_SAI_RCSR(offset), flags | xcsr);
189     }
190 
191     return irq_none;
192 }
193 
fsl_sai_isr(int irq,void * devid)194 static irqreturn_t fsl_sai_isr(int irq, void *devid)
195 {
196     struct PrivPlatformData *ppd = (struct PrivPlatformData *)devid;
197     struct fsl_sai *sai = (struct fsl_sai *)&(ppd->sai);
198     unsigned char offset = sai->reg_offset;
199     u32 flags = 0, xcsr = 0, mask = 0;
200     bool irq_none = true;
201 
202     /*
203      * Both IRQ status bits and IRQ mask bits are in the xCSR but
204      * different shifts. And we here create a mask only for those
205      * IRQs that we activated.
206      */
207     mask = (FSL_SAI_FLAGS >> FSL_SAI_CSR_xIE_SHIFT) << FSL_SAI_CSR_xF_SHIFT;
208 
209     /* Tx IRQ */
210     regmap_read(sai->regmap, FSL_SAI_TCSR(offset), &xcsr);
211     flags = xcsr & mask;
212 
213     if (flags) {
214         irq_none = false;
215     } else {
216         if (flags) {
217             irq_none = false;
218         } else {
219             if (irq_none) {
220                 return IRQ_NONE;
221             } else {
222                 return IRQ_HANDLED;
223             }
224         }
225 
226         if (flags & FSL_SAI_CSR_FEF) {
227             AUDIO_DRIVER_LOG_ERR("isr: Receive overflow detected\n");
228             /* FIFO reset for safety */
229             xcsr |= FSL_SAI_CSR_FR;
230         }
231 
232         flags &= FSL_SAI_CSR_xF_W_MASK;
233         xcsr &= ~FSL_SAI_CSR_xF_MASK;
234 
235         if (flags) {
236             regmap_write(sai->regmap, FSL_SAI_RCSR(offset), flags | xcsr);
237         }
238 
239         if (irq_none) {
240             return IRQ_NONE;
241         } else {
242             return IRQ_HANDLED;
243         }
244     }
245 
246     if (flags & FSL_SAI_CSR_FEF) {
247         AUDIO_DRIVER_LOG_ERR("isr: Transmit underrun detected\n");
248         /* FIFO reset for safety */
249         xcsr |= FSL_SAI_CSR_FR;
250     }
251 
252     flags &= FSL_SAI_CSR_xF_W_MASK;
253     xcsr &= ~FSL_SAI_CSR_xF_MASK;
254 
255     if (flags) {
256         regmap_write(sai->regmap, FSL_SAI_TCSR(offset), flags | xcsr);
257     }
258 
259     /* Rx IRQ */
260     irq_none = fsl_sai_rx_irq(irq, devid);
261     if (irq_none) {
262         return IRQ_NONE;
263     } else {
264         return IRQ_HANDLED;
265     }
266 }
267 
268 static struct reg_default fsl_sai_v3_reg_defaults[] = {
269     {FSL_SAI_TCR1(8), 0},
270     {FSL_SAI_TCR2(8), 0},
271     {FSL_SAI_TCR3(8), 0},
272     {FSL_SAI_TCR4(8), 0},
273     {FSL_SAI_TCR5(8), 0},
274     {FSL_SAI_TDR0, 0},
275     {FSL_SAI_TDR1, 0},
276     {FSL_SAI_TDR2, 0},
277     {FSL_SAI_TDR3, 0},
278     {FSL_SAI_TDR4, 0},
279     {FSL_SAI_TDR5, 0},
280     {FSL_SAI_TDR6, 0},
281     {FSL_SAI_TDR7, 0},
282     {FSL_SAI_TMR,  0},
283     {FSL_SAI_RCR1(8), 0},
284     {FSL_SAI_RCR2(8), 0},
285     {FSL_SAI_RCR3(8), 0},
286     {FSL_SAI_RCR4(8), 0},
287     {FSL_SAI_RCR5(8), 0},
288     {FSL_SAI_RMR,  0},
289     {FSL_SAI_MCTL, 0},
290     {FSL_SAI_MDIV, 0},
291 };
292 
fsl_sai_readable_tfr_reg(unsigned int reg)293 static bool fsl_sai_readable_tfr_reg(unsigned int reg)
294 {
295     bool ret = false;
296     switch (reg) {
297         case FSL_SAI_TFR0: fallthrough;
298         case FSL_SAI_TFR1: fallthrough;
299         case FSL_SAI_TFR2: fallthrough;
300         case FSL_SAI_TFR3: fallthrough;
301         case FSL_SAI_TFR4: fallthrough;
302         case FSL_SAI_TFR5: fallthrough;
303         case FSL_SAI_TFR6: fallthrough;
304         case FSL_SAI_TFR7:
305             ret = true;
306             break;
307 
308         default:
309             ret = false;
310             break;
311     }
312 
313     return ret;
314 }
315 
fsl_sai_readable_rxr_reg(unsigned int reg)316 static bool fsl_sai_readable_rxr_reg(unsigned int reg)
317 {
318     bool ret = false;
319     switch (reg) {
320         case FSL_SAI_RDR0: fallthrough;
321         case FSL_SAI_RDR1: fallthrough;
322         case FSL_SAI_RDR2: fallthrough;
323         case FSL_SAI_RDR3: fallthrough;
324         case FSL_SAI_RDR4: fallthrough;
325         case FSL_SAI_RDR5: fallthrough;
326         case FSL_SAI_RDR6: fallthrough;
327         case FSL_SAI_RDR7: fallthrough;
328         case FSL_SAI_RFR0: fallthrough;
329         case FSL_SAI_RFR1: fallthrough;
330         case FSL_SAI_RFR2: fallthrough;
331         case FSL_SAI_RFR3: fallthrough;
332         case FSL_SAI_RFR4: fallthrough;
333         case FSL_SAI_RFR5: fallthrough;
334         case FSL_SAI_RFR6: fallthrough;
335         case FSL_SAI_RFR7: fallthrough;
336         case FSL_SAI_RMR:
337             ret = true;
338             break;
339 
340         default:
341             ret = false;
342             break;
343     }
344 
345     return ret;
346 }
347 
fsl_sai_readable_reg(struct device * dev,unsigned int reg)348 static bool fsl_sai_readable_reg(struct device *dev, unsigned int reg)
349 {
350     struct fsl_sai *sai = dev_get_drvdata(dev);
351     unsigned char offset = sai->reg_offset;
352 
353     if (reg >= FSL_SAI_TCSR(offset) && reg <= FSL_SAI_TCR5(offset)) {
354         return true;
355     }
356 
357     if (reg >= FSL_SAI_RCSR(offset) && reg <= FSL_SAI_RCR5(offset)) {
358         return true;
359     }
360 
361     if (fsl_sai_readable_tfr_reg(reg) == true) {
362         return true;
363     }
364 
365     if (fsl_sai_readable_rxr_reg(reg) == true) {
366         return true;
367     }
368 
369     switch (reg) {
370         case FSL_SAI_TMR: fallthrough;
371         case FSL_SAI_MCTL: fallthrough;
372         case FSL_SAI_MDIV: fallthrough;
373         case FSL_SAI_VERID: fallthrough;
374         case FSL_SAI_PARAM: fallthrough;
375         case FSL_SAI_TTCTN: fallthrough;
376         case FSL_SAI_RTCTN: fallthrough;
377         case FSL_SAI_TTCTL: fallthrough;
378         case FSL_SAI_TBCTN: fallthrough;
379         case FSL_SAI_TTCAP: fallthrough;
380         case FSL_SAI_RTCTL: fallthrough;
381         case FSL_SAI_RBCTN: fallthrough;
382         case FSL_SAI_RTCAP:
383             return true;
384         default:
385             return false;
386     }
387 }
388 
fsl_sai_volatile_reg(struct device * dev,unsigned int reg)389 static bool fsl_sai_volatile_reg(struct device *dev, unsigned int reg)
390 {
391     struct fsl_sai *sai = dev_get_drvdata(dev);
392     unsigned char offset = sai->reg_offset;
393 
394     if (reg == FSL_SAI_TCSR(offset) || reg == FSL_SAI_RCSR(offset)) {
395         return true;
396     }
397 
398     if (sai->reg_offset == BYTE_NUM && (reg == FSL_SAI_VERID ||
399                                         reg == FSL_SAI_PARAM)) {
400         return true;
401     }
402 
403     switch (reg) {
404         case FSL_SAI_TFR0:
405         case FSL_SAI_TFR1:
406         case FSL_SAI_TFR2:
407         case FSL_SAI_TFR3:
408         case FSL_SAI_TFR4:
409         case FSL_SAI_TFR5:
410         case FSL_SAI_TFR6:
411         case FSL_SAI_TFR7:
412         case FSL_SAI_RFR0:
413         case FSL_SAI_RFR1:
414         case FSL_SAI_RFR2:
415         case FSL_SAI_RFR3:
416         case FSL_SAI_RFR4:
417         case FSL_SAI_RFR5:
418         case FSL_SAI_RFR6:
419         case FSL_SAI_RFR7:
420         case FSL_SAI_RDR0:
421         case FSL_SAI_RDR1:
422         case FSL_SAI_RDR2:
423         case FSL_SAI_RDR3:
424         case FSL_SAI_RDR4:
425         case FSL_SAI_RDR5:
426         case FSL_SAI_RDR6:
427         case FSL_SAI_RDR7:
428             return true;
429         default:
430             return false;
431     }
432 }
433 
fsl_sai_writeable_reg(struct device * dev,unsigned int reg)434 static bool fsl_sai_writeable_reg(struct device *dev, unsigned int reg)
435 {
436     struct fsl_sai *sai = dev_get_drvdata(dev);
437     unsigned char offset = sai->reg_offset;
438 
439     if (reg >= FSL_SAI_TCSR(offset) && reg <= FSL_SAI_TCR5(offset)) {
440         return true;
441     }
442 
443     if (reg >= FSL_SAI_RCSR(offset) && reg <= FSL_SAI_RCR5(offset)) {
444         return true;
445     }
446 
447     switch (reg) {
448         case FSL_SAI_TDR0:
449         case FSL_SAI_TDR1:
450         case FSL_SAI_TDR2:
451         case FSL_SAI_TDR3:
452         case FSL_SAI_TDR4:
453         case FSL_SAI_TDR5:
454         case FSL_SAI_TDR6:
455         case FSL_SAI_TDR7:
456         case FSL_SAI_TMR:
457         case FSL_SAI_RMR:
458         case FSL_SAI_MCTL:
459         case FSL_SAI_MDIV:
460         case FSL_SAI_TTCTL:
461         case FSL_SAI_RTCTL:
462             return true;
463         default:
464             return false;
465     }
466 }
467 
468 static const struct regmap_config fsl_sai_regmap_config = {
469     .reg_bits = 32,
470     .reg_stride = 4,
471     .val_bits = 32,
472 
473     .max_register = FSL_SAI_MDIV,
474     .reg_defaults = fsl_sai_v3_reg_defaults,
475     .num_reg_defaults = ARRAY_SIZE(fsl_sai_v3_reg_defaults),
476     .readable_reg = fsl_sai_readable_reg,
477     .volatile_reg = fsl_sai_volatile_reg,
478     .writeable_reg = fsl_sai_writeable_reg,
479     .cache_type = REGCACHE_FLAT,
480 };
481 
482 #define OFFSET_7 (7)
483 #define OFFSET_8 (8)
fsl_sai_calc_dl_off(unsigned long dl_mask)484 static unsigned int fsl_sai_calc_dl_off(unsigned long dl_mask)
485 {
486     int fbidx = 0, nbidx = 0, offset = 0;
487 
488     fbidx = find_first_bit(&dl_mask, OFFSET_8);
489     nbidx = find_next_bit(&dl_mask, OFFSET_8, fbidx + 1);
490     offset = nbidx - fbidx - 1;
491 
492     return (offset < 0 || offset >= OFFSET_7 ? 0 : offset);
493 }
494 
495 #define ELEMS_3  (3)
fsl_sai_read_dlcfg(struct platform_device * pdev,char * pn,struct fsl_sai_dl_cfg ** rcfg,unsigned int soc_dl)496 static int fsl_sai_read_dlcfg(struct platform_device *pdev, char *pn,
497                               struct fsl_sai_dl_cfg **rcfg, unsigned int soc_dl)
498 {
499     int ret = 0, elems = 0, i = 0, index = 0, num_cfg = 0;
500     struct device_node *np = pdev->dev.of_node;
501     struct fsl_sai_dl_cfg *cfg = NULL;
502     u32 rx = 0, tx = 0, pins = 0;
503 
504     *rcfg = NULL;
505 
506     elems = of_property_count_u32_elems(np, pn);
507     /* consider default value "0 0x1 0x1" if property is missing */
508     if (elems <= 0) {
509         elems = ELEMS_3;
510     }
511 
512     if (elems % ELEMS_3) {
513         AUDIO_DRIVER_LOG_ERR(
514             "Number of elements in %s must be divisible to 3.\n", pn);
515         return -EINVAL;
516     }
517 
518     num_cfg = elems / ELEMS_3;
519     cfg = devm_kzalloc(&pdev->dev, num_cfg * sizeof(*cfg), GFP_KERNEL);
520     if (cfg == NULL) {
521         AUDIO_DRIVER_LOG_ERR("Cannot allocate memory for %s.\n", pn);
522         return -ENOMEM;
523     }
524 
525     for (i = 0, index = 0; i < num_cfg; i++) {
526         ret = of_property_read_u32_index(np, pn, index++, &pins);
527         if (ret) {
528             pins = 0;
529         }
530 
531         ret = of_property_read_u32_index(np, pn, index++, &rx);
532         if (ret) {
533             rx = 1;
534         }
535 
536         ret = of_property_read_u32_index(np, pn, index++, &tx);
537         if (ret) {
538             tx = 1;
539         }
540 
541         if ((rx & ~soc_dl) || (tx & ~soc_dl)) {
542             AUDIO_DRIVER_LOG_ERR(
543                 "%s: dataline cfg[%d] setting error, mask is 0x%x\n",
544                 pn, i, soc_dl);
545             return -EINVAL;
546         }
547 
548         cfg[i].pins = pins;
549         cfg[i].mask[0] = rx;
550         cfg[i].offset[0] = fsl_sai_calc_dl_off(rx);
551         cfg[i].mask[1] = tx;
552         cfg[i].offset[1] = fsl_sai_calc_dl_off(tx);
553     }
554 
555     *rcfg = cfg;
556     return num_cfg;
557 }
558 
fsl_sai_check_ver(struct fsl_sai * sai,struct device * dev)559 static int fsl_sai_check_ver(struct fsl_sai *sai, struct device *dev)
560 {
561     unsigned char offset = sai->reg_offset;
562     unsigned int val = 0;
563     int ret = 0;
564 
565     if (FSL_SAI_TCSR(offset) == FSL_SAI_VERID) {
566         return 0;
567     }
568 
569     if (sai->verid.loaded) {
570         return 0;
571     }
572 
573     ret = regmap_read(sai->regmap, FSL_SAI_VERID, &val);
574     if (ret < 0) {
575         return ret;
576     }
577 
578     AUDIO_DRIVER_LOG_ERR("VERID: 0x%016X\n", val);
579 
580     sai->verid.id = (val & FSL_SAI_VER_ID_MASK) >> FSL_SAI_VER_ID_SHIFT;
581     sai->verid.extfifo_en = (val & FSL_SAI_VER_EFIFO_EN);
582     sai->verid.timestamp_en = (val & FSL_SAI_VER_TSTMP_EN);
583 
584     ret = regmap_read(sai->regmap, FSL_SAI_PARAM, &val);
585     if (ret < 0) {
586         return ret;
587     }
588 
589     AUDIO_DRIVER_LOG_ERR("PARAM: 0x%016X\n", val);
590 
591     /* max slots per frame, power of 2 */
592     sai->param.spf = 1 <<
593         ((val & FSL_SAI_PAR_SPF_MASK) >> FSL_SAI_PAR_SPF_SHIFT);
594 
595     /* words per fifo, power of 2 */
596     sai->param.wpf = 1 <<
597         ((val & FSL_SAI_PAR_WPF_MASK) >> FSL_SAI_PAR_WPF_SHIFT);
598 
599     /* number of datalines implemented */
600     sai->param.dln = val & FSL_SAI_PAR_DLN_MASK;
601 
602     AUDIO_DRIVER_LOG_ERR(
603         "Version: 0x%08X, SPF: %u, WPF: %u, DLN: %u\n",
604         sai->verid.id, sai->param.spf, sai->param.wpf, sai->param.dln);
605 
606     sai->verid.loaded = true;
607 
608     return HDF_SUCCESS;
609 }
610 
611 #define RATIO_1  (1)
612 #define RATIO_2  (2)
613 #define RATIO_512  (512)
614 #define RATE_1000  (1000)
fsl_sai_set_bclk(struct fsl_sai * sai,bool tx,u32 freq)615 static int fsl_sai_set_bclk(struct fsl_sai *sai, bool tx, u32 freq)
616 {
617     unsigned char offset = sai->reg_offset;
618     unsigned long clk_rate = 0;
619     unsigned int reg = 0;
620     u32 ratio = 0, savesub = freq, saveratio = 0, savediv = 0;
621     u32 id = 0;
622     int ret = 0;
623 
624     for (id = 0; id < FSL_SAI_MCLK_MAX; id++) {
625         clk_rate = clk_get_rate(sai->mclk_clk[id]);
626         if (!clk_rate) {
627             continue;
628         }
629 
630         if (freq != 0) {
631             ratio = clk_rate / freq;
632         }
633 
634         ret = clk_rate - ratio * freq;
635         /*
636          * Drop the source that can not be
637          * divided into the required rate.
638          */
639         if (ret != 0 && clk_rate / ret < RATE_1000) {
640             continue;
641         }
642 
643         if ((ratio % RATIO_2 == 0 && ratio >= RATIO_2 && ratio <= RATIO_512) ||
644             (ratio == RATIO_1 && sai->verid.id >= FSL_SAI_VERID_0301)) {
645             if (ret < savesub) {
646                 saveratio = ratio;
647                 sai->mclk_id[tx] = id;
648                 savesub = ret;
649             }
650 
651             if (ret == 0) {
652                 break;
653             }
654         }
655     }
656 
657     /*
658      * 1) For Asynchronous mode, we must set RCR2 register for capture, and
659      *    set TCR2 register for playback.
660      * 2) For Tx sync with Rx clock, we must set RCR2 register for playback
661      *    and capture.
662      * 3) For Rx sync with Tx clock, we must set TCR2 register for playback
663      *    and capture.
664      * 4) For Tx and Rx are both Synchronous with another SAI, we just
665      *    ignore it.
666      */
667     if ((!tx || sai->synchronous[TX]) && !sai->synchronous[RX]) {
668         reg = FSL_SAI_RCR2(offset);
669     } else if ((tx || sai->synchronous[RX]) && !sai->synchronous[TX]) {
670         reg = FSL_SAI_TCR2(offset);
671     }
672 
673     if (reg) {
674         regmap_update_bits(sai->regmap, reg, FSL_SAI_CR2_MSEL_MASK,
675             FSL_SAI_CR2_MSEL(sai->mclk_id[tx]));
676 
677         savediv = (saveratio == 1 ? 0 : (saveratio >> 1) - 1);
678         regmap_update_bits(sai->regmap, reg, FSL_SAI_CR2_DIV_MASK, savediv);
679 
680         if (sai->verid.id >= FSL_SAI_VERID_0301) {
681             regmap_update_bits(sai->regmap, reg, FSL_SAI_CR2_BYP,
682                 (saveratio == 1 ? FSL_SAI_CR2_BYP : 0));
683         }
684     }
685 
686     if (sai->verid.id >= FSL_SAI_VERID_0301) {
687         /* SAI is in master mode at this point, so enable MCLK */
688         regmap_update_bits(sai->regmap, FSL_SAI_MCTL,
689             FSL_SAI_MCTL_MCLK_EN, FSL_SAI_MCTL_MCLK_EN);
690     }
691 
692     return 0;
693 }
694 struct fsl_hwParams_register {
695     u32 cr3;
696     u32 cr4;
697     u32 cr5;
698     u32 mr;
699 };
700 
SaiGetHwParams(const struct PlatformData * pd,const enum AudioStreamType streamType,u32 * channels,u32 * rate,u32 * word_width)701 int32_t SaiGetHwParams(const struct PlatformData *pd,
702                        const enum AudioStreamType streamType,
703                        u32 *channels, u32 *rate,
704                        u32 *word_width)
705 {
706     int32_t ret = 0;
707 
708     if (streamType == AUDIO_RENDER_STREAM) {
709         *channels = pd->renderPcmInfo.channels;
710         *rate = pd->renderPcmInfo.rate;
711         *word_width = pd->renderPcmInfo.bitWidth;
712     } else if (streamType == AUDIO_CAPTURE_STREAM) {
713         *channels = pd->capturePcmInfo.channels;
714         *rate = pd->capturePcmInfo.rate;
715         *word_width = pd->capturePcmInfo.bitWidth;
716     } else {
717         AUDIO_DRIVER_LOG_ERR("streamType is invaild ");
718         return HDF_FAILURE;
719     }
720     return ret;
721 }
722 
SaiSetHwParamsPin(struct fsl_sai * sai,u32 channels,u32 * pins,u32 * slots)723 int32_t SaiSetHwParamsPin(struct fsl_sai *sai, u32 channels, u32 *pins, u32 *slots)
724 {
725     int32_t ret = 0;
726 
727     if (sai->slots) {
728         *slots = sai->slots;
729     }
730 
731     *pins = DIV_ROUND_UP(channels, *slots);
732 
733     if (!IS_ERR_OR_NULL(sai->pinctrl)) {
734         sai->pins_state = pinctrl_lookup_state(sai->pinctrl, "default");
735 
736         if (!IS_ERR_OR_NULL(sai->pins_state)) {
737             ret = pinctrl_select_state(sai->pinctrl, sai->pins_state);
738             if (ret) {
739                 AUDIO_DRIVER_LOG_ERR("failed to set proper pins state");
740                 return ret;
741             }
742         }
743     }
744     return ret;
745 }
746 
SaiSetHwParamsClk(struct fsl_sai * sai,bool tx,u32 bclk,const enum AudioStreamType streamType)747 int32_t SaiSetHwParamsClk(struct fsl_sai *sai, bool tx, u32 bclk, const enum AudioStreamType streamType)
748 {
749     int32_t ret = 0;
750     if (!sai->slave_mode[tx]) {
751         ret = fsl_sai_set_bclk(sai, tx, bclk);
752         if (ret) {
753             return ret;
754         }
755 
756         /* Do not enable the clock if it is already enabled */
757         if (!(sai->mclk_streams & BIT(streamType))) {
758             AUDIO_DRIVER_LOG_ERR("mclk enable %d", sai->mclk_id[tx]);
759             ret = clk_prepare_enable(sai->mclk_clk[sai->mclk_id[tx]]);
760             if (ret) {
761                 return ret;
762             }
763 
764             sai->mclk_streams |= BIT(streamType);
765         }
766     }
767     return ret;
768 }
769 
SaiGetHwParamsCR5(struct fsl_sai * sai,u32 slot_width,u32 word_width)770 u32 SaiGetHwParamsCR5(struct fsl_sai *sai, u32 slot_width, u32 word_width)
771 {
772     u32 val_cr5 = 0;
773 
774     val_cr5 |= FSL_SAI_CR5_WNW(slot_width);
775     val_cr5 |= FSL_SAI_CR5_W0W(slot_width);
776 
777     if (sai->is_lsb_first) {
778         val_cr5 |= FSL_SAI_CR5_FBT(0);
779     } else {
780         val_cr5 |= FSL_SAI_CR5_FBT(word_width - 1);
781     }
782 
783     return val_cr5;
784 }
785 
SaiGetHwParamsCR4(struct fsl_sai * sai,u32 slot_width,u32 slots)786 u32 SaiGetHwParamsCR4(struct fsl_sai *sai, u32 slot_width, u32 slots)
787 {
788     u32 val_cr4 = 0;
789 
790     if (!sai->is_dsp_mode) {
791         val_cr4 |= FSL_SAI_CR4_SYWD(slot_width);
792     }
793     val_cr4 |= FSL_SAI_CR4_FRSZ(slots);
794 
795     /* Output Mode - data pins transmit 0 when slots are masked
796      * or channels are disabled
797      */
798     val_cr4 |= FSL_SAI_CR4_CHMOD;
799     return val_cr4;
800 }
801 
SaiGetdlMask(struct fsl_sai * sai,bool tx,u32 pins)802 u32 SaiGetdlMask(struct fsl_sai *sai, bool tx, u32 pins)
803 {
804     int32_t i = 0, dl_cfg_cnt, dl_cfg_idx = 0;
805     struct fsl_sai_dl_cfg *dl_cfg = NULL;
806 
807     sai->is_dsd = false;
808     dl_cfg = sai->pcm_dl_cfg;
809     dl_cfg_cnt = sai->pcm_dl_cfg_cnt;
810     for (i = 0; i < dl_cfg_cnt; i++) {
811         if (dl_cfg[i].pins == pins) {
812             dl_cfg_idx = i;
813             break;
814         }
815     }
816 
817     if (dl_cfg_idx >= dl_cfg_cnt) {
818         AUDIO_DRIVER_LOG_ERR("fsl,dataline%s invalid or not provided.", sai->is_dsd ? ",dsd" : "");
819         return HDF_FAILURE;
820     }
821 
822     return dl_cfg[dl_cfg_idx].mask[tx];
823 }
824 
SaiSetHwParamsRegister(struct fsl_sai * sai,bool tx,struct fsl_hwParams_register * val,unsigned int dl_mask)825 u32 SaiSetHwParamsRegister(struct fsl_sai *sai, bool tx,
826     struct fsl_hwParams_register *val, unsigned int dl_mask)
827 {
828     unsigned char offset = sai->reg_offset;
829 
830     if (!sai->slave_mode[tx]) {
831         if (!sai->synchronous[TX] && sai->synchronous[RX] && !tx) {
832             regmap_update_bits(sai->regmap, FSL_SAI_TCR4(offset),
833                 FSL_SAI_CR4_SYWD_MASK | FSL_SAI_CR4_FRSZ_MASK |
834                 FSL_SAI_CR4_CHMOD_MASK, val->cr4);
835             regmap_update_bits(sai->regmap, FSL_SAI_TCR5(offset),
836                 FSL_SAI_CR5_WNW_MASK | FSL_SAI_CR5_W0W_MASK |
837                 FSL_SAI_CR5_FBT_MASK, val->cr5);
838         } else if (!sai->synchronous[RX] && sai->synchronous[TX] && tx) {
839             regmap_update_bits(sai->regmap, FSL_SAI_RCR4(offset),
840                 FSL_SAI_CR4_SYWD_MASK | FSL_SAI_CR4_FRSZ_MASK |
841                 FSL_SAI_CR4_CHMOD_MASK, val->cr4);
842             regmap_update_bits(sai->regmap, FSL_SAI_RCR5(offset),
843                 FSL_SAI_CR5_WNW_MASK | FSL_SAI_CR5_W0W_MASK |
844                 FSL_SAI_CR5_FBT_MASK, val->cr5);
845         }
846     }
847 
848     if (sai->dataline != 0x1) {
849         if (dl_mask <= 1 || sai->is_multi_lane) {
850             regmap_update_bits(sai->regmap, FSL_SAI_xCR4(tx, offset),
851                 FSL_SAI_CR4_FCOMB_MASK, 0);
852         } else {
853             regmap_update_bits(sai->regmap, FSL_SAI_xCR4(tx, offset),
854                 FSL_SAI_CR4_FCOMB_MASK, FSL_SAI_CR4_FCOMB_SOFT);
855         }
856     }
857 
858     regmap_update_bits(sai->regmap, FSL_SAI_xCR3(tx, offset),
859         FSL_SAI_CR3_TRCE_MASK,
860         FSL_SAI_CR3_TRCE(val->cr3));
861 
862     regmap_update_bits(sai->regmap, FSL_SAI_xCR4(tx, offset),
863         FSL_SAI_CR4_SYWD_MASK | FSL_SAI_CR4_FRSZ_MASK |
864         FSL_SAI_CR4_CHMOD_MASK,
865         val->cr4);
866 
867     regmap_update_bits(sai->regmap, FSL_SAI_xCR5(tx, offset),
868         FSL_SAI_CR5_WNW_MASK | FSL_SAI_CR5_W0W_MASK |
869         FSL_SAI_CR5_FBT_MASK, val->cr5);
870 
871     regmap_write(sai->regmap, FSL_SAI_xMR(tx), val->mr);
872 
873     return HDF_SUCCESS;
874 }
875 
SaiSetHwParams(const struct PlatformData * pd,const enum AudioStreamType streamType)876 int32_t SaiSetHwParams(const struct PlatformData *pd, const enum AudioStreamType streamType)
877 {
878     struct fsl_sai *sai = GetDrvSai(pd);
879     u32 channels = 0, rate = 0, word_width = 0, pins = 0, bclk = 0;
880     u32 slot_width = word_width, slots = (channels == 1) ? 2 : channels;
881     bool tx = streamType == AUDIO_RENDER_STREAM;
882     struct fsl_hwParams_register val;
883     int32_t trce_mask = 0, ret = 0;
884     unsigned int dl_mask, i;
885 
886     ret = SaiGetHwParams(pd, streamType, &channels, &rate, &word_width);
887     if (ret != HDF_SUCCESS) {
888         ADM_LOG_ERR("SaiGetHwParams fail ret=%d", ret);
889         return ret;
890     }
891 
892     ret = SaiSetHwParamsPin(sai, channels, &pins, &slots);
893     if (ret != HDF_SUCCESS) {
894         ADM_LOG_ERR("SaiSetHwParamsPin fail ret=%d", ret);
895         return ret;
896     }
897 
898     if (sai->slot_width) {
899         slot_width = sai->slot_width;
900     }
901     bclk = rate*(sai->bitclk_ratio ? sai->bitclk_ratio : slots * slot_width);
902     ret = SaiSetHwParamsClk(sai, tx, bclk, streamType);
903     if (ret != HDF_SUCCESS) {
904         ADM_LOG_ERR("SaiSetHwParamsClk fail ret=%d", ret);
905         return ret;
906     }
907 
908     val.cr5 = SaiGetHwParamsCR5(sai, slot_width, word_width);
909     val.cr4 = SaiGetHwParamsCR4(sai, slot_width, slots);
910     dl_mask = SaiGetdlMask(sai, tx, pins);
911     if (__sw_hweight8(dl_mask & 0xFF) < pins) {
912         AUDIO_DRIVER_LOG_ERR("channel not supported");
913         return -EINVAL;
914     }
915     for (i = 0; i < BYTE_NUM; i++) {
916         trce_mask = (1 << (i + 1)) - 1;
917         if (__sw_hweight8(dl_mask & trce_mask) == pins) {
918             break;
919         }
920     }
921     val.cr3 = dl_mask & trce_mask;
922     val.mr = ~0UL - ((1 << min(channels, slots)) - 1);
923 
924     SaiSetHwParamsRegister(sai, tx, &val, dl_mask);
925     return HDF_SUCCESS;
926 }
927 
SaiSetDaiTdmSlot(const struct PlatformData * pd,int32_t tx_mask,int32_t rx_mask,int32_t slots,int32_t slot_width)928 int32_t SaiSetDaiTdmSlot(const struct PlatformData *pd, int32_t tx_mask,
929                          int32_t rx_mask, int32_t slots, int32_t slot_width)
930 {
931     struct fsl_sai *sai = GetDrvSai(pd);
932 
933     if (sai != NULL) {
934         sai->slots = slots;
935         sai->slot_width = slot_width;
936     } else {
937         return HDF_FAILURE;
938     }
939 
940     return HDF_SUCCESS;
941 }
942 
SaiSetSysclkTr(struct fsl_sai * sai,int clk_id,unsigned int freq,int fsl_dir)943 static int32_t SaiSetSysclkTr(struct fsl_sai *sai, int clk_id, unsigned int freq, int fsl_dir)
944 {
945     unsigned char offset = 0;
946     bool tx = fsl_dir == FSL_FMT_TRANSMITTER;
947     uint32_t val_cr2 = 0;
948 
949     offset = sai->reg_offset;
950     switch (clk_id) {
951         case FSL_SAI_CLK_BUS:
952             val_cr2 |= FSL_SAI_CR2_MSEL_BUS;
953             break;
954         case FSL_SAI_CLK_MAST1:
955             val_cr2 |= FSL_SAI_CR2_MSEL_MCLK1;
956             break;
957         case FSL_SAI_CLK_MAST2:
958             val_cr2 |= FSL_SAI_CR2_MSEL_MCLK2;
959             break;
960         case FSL_SAI_CLK_MAST3:
961             val_cr2 |= FSL_SAI_CR2_MSEL_MCLK3;
962             break;
963         default:
964             return -EINVAL;
965     }
966 
967     regmap_update_bits(sai->regmap, FSL_SAI_xCR2(tx, offset),
968                        FSL_SAI_CR2_MSEL_MASK, val_cr2);
969 
970     return HDF_SUCCESS;
971 }
972 
973 #define RATIO_DIV  (8000)
fsl_sai_set_mclk_rate(struct fsl_sai * sai,int clk_id,unsigned int freq)974 static int32_t fsl_sai_set_mclk_rate(struct fsl_sai *sai, int clk_id, unsigned int freq)
975 {
976     struct clk *p = sai->mclk_clk[clk_id], *pll = 0, *npll = 0;
977     u64 ratio = freq;
978     int ret = 0;
979     AUDIO_DRIVER_LOG_ERR("mclk rate in");
980     while (p && sai->pll8k_clk && sai->pll11k_clk) {
981         struct clk *pp = clk_get_parent(p);
982 
983         if (clk_is_match(pp, sai->pll8k_clk) ||
984             clk_is_match(pp, sai->pll11k_clk)) {
985             pll = pp;
986             break;
987         }
988         p = pp;
989     }
990 
991     if (pll) {
992         npll = (do_div(ratio, RATIO_DIV) ? sai->pll11k_clk : sai->pll8k_clk);
993         if (!clk_is_match(pll, npll)) {
994             ret = clk_set_parent(p, npll);
995             if (ret < 0) {
996                 AUDIO_DRIVER_LOG_ERR("failed to set parent %s: %d\n",
997                                      __clk_get_name(npll), ret);
998             }
999         }
1000     }
1001 
1002     ret = clk_set_rate(sai->mclk_clk[clk_id], freq);
1003     AUDIO_DRIVER_LOG_ERR("mclk_clk id %d freq %d", clk_id, freq);
1004     if (ret < 0) {
1005         AUDIO_DRIVER_LOG_ERR("failed to set clock rate (%u): %d\n",
1006                              freq, ret);
1007     }
1008 
1009     return ret;
1010 }
1011 
SaiSetSysclk(const struct PlatformData * pd,int clk_id,unsigned int freq,int dir)1012 int32_t SaiSetSysclk(const struct PlatformData *pd, int clk_id, unsigned int freq, int dir)
1013 {
1014     struct fsl_sai *sai = GetDrvSai(pd);
1015     int32_t ret = 0;
1016 
1017     if (sai == NULL) {
1018         AUDIO_DRIVER_LOG_ERR("sai null");
1019         return HDF_FAILURE;
1020     }
1021 
1022     if (dir == SOC_CLOCK_IN) {
1023         return HDF_SUCCESS;
1024     }
1025 
1026     if (freq > 0 && clk_id != FSL_SAI_CLK_BUS) {
1027         if (clk_id < 0 || clk_id >= FSL_SAI_MCLK_MAX) {
1028             AUDIO_DRIVER_LOG_ERR("Unknown clock id: %d", clk_id);
1029             return -EINVAL;
1030         }
1031 
1032         if (IS_ERR_OR_NULL(sai->mclk_clk[clk_id])) {
1033             AUDIO_DRIVER_LOG_ERR("Unassigned clock: %d", clk_id);
1034             return -EINVAL;
1035         }
1036         AUDIO_DRIVER_LOG_ERR("clock: %d", clk_id);
1037         if (sai->mclk_streams == 0) {
1038             AUDIO_DRIVER_LOG_ERR("mclk rate = %d", freq);
1039             ret = fsl_sai_set_mclk_rate(sai, clk_id, freq);
1040             if (ret < 0) {
1041                 return ret;
1042             }
1043         }
1044     }
1045 
1046     ret = SaiSetSysclkTr(sai, clk_id, freq, FSL_FMT_TRANSMITTER);
1047     if (ret) {
1048         AUDIO_DRIVER_LOG_ERR("cannot set tx sysclk");
1049         return HDF_FAILURE;
1050     }
1051 
1052     ret = SaiSetSysclkTr(sai, clk_id, freq, FSL_FMT_RECEIVER);
1053     if (ret) {
1054         AUDIO_DRIVER_LOG_ERR("cannot set rx sysclk");
1055         return HDF_FAILURE;
1056     }
1057 
1058     return HDF_SUCCESS;
1059 }
1060 
HandleDaiMode(unsigned int fmt,int32_t * val_cr2,int32_t * val_cr4,struct fsl_sai ** sai)1061 static int32_t HandleDaiMode(unsigned int fmt, int32_t *val_cr2, int32_t *val_cr4, struct fsl_sai **sai)
1062 {
1063     /* DAI mode */
1064     switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
1065         case SND_SOC_DAIFMT_I2S:
1066             /*
1067             * Frame low, 1clk before data, one word length for frame sync,
1068             * frame sync starts one serial clock cycle earlier,
1069             * that is, together with the last bit of the previous
1070             * data word.
1071             */
1072             *val_cr2 |= FSL_SAI_CR2_BCP;
1073             *val_cr4 |= FSL_SAI_CR4_FSE | FSL_SAI_CR4_FSP;
1074             break;
1075         case SND_SOC_DAIFMT_LEFT_J:
1076             /*
1077             * Frame high, one word length for frame sync,
1078             * frame sync asserts with the first bit of the frame.
1079             */
1080             *val_cr2 |= FSL_SAI_CR2_BCP;
1081             break;
1082         case SND_SOC_DAIFMT_DSP_A:
1083             /*
1084             * Frame high, 1clk before data, one bit for frame sync,
1085             * frame sync starts one serial clock cycle earlier,
1086             * that is, together with the last bit of the previous
1087             * data word.
1088             */
1089             *val_cr2 |= FSL_SAI_CR2_BCP;
1090             *val_cr4 |= FSL_SAI_CR4_FSE;
1091             (*sai)->is_dsp_mode = true;
1092             break;
1093         case SND_SOC_DAIFMT_DSP_B:
1094             /*
1095             * Frame high, one bit for frame sync,
1096             * frame sync asserts with the first bit of the frame.
1097             */
1098             *val_cr2 |= FSL_SAI_CR2_BCP;
1099             (*sai)->is_dsp_mode = true;
1100             break;
1101         case SND_SOC_DAIFMT_PDM:
1102             *val_cr2 |= FSL_SAI_CR2_BCP;
1103             *val_cr4 &= ~FSL_SAI_CR4_MF;
1104             (*sai)->is_dsp_mode = true;
1105             break;
1106         case SND_SOC_DAIFMT_RIGHT_J:
1107             /* To be done */
1108         default:
1109             return -EINVAL;
1110     }
1111     return 0;
1112 }
1113 
HandleDaiCLK(unsigned int fmt,int32_t * val_cr2,int32_t * val_cr4)1114 static int32_t HandleDaiCLK(unsigned int fmt, int32_t *val_cr2, int32_t *val_cr4)
1115 {
1116     /* DAI clock inversion */
1117     switch (fmt & SND_SOC_DAIFMT_INV_MASK) {
1118         case SND_SOC_DAIFMT_IB_IF:
1119             /* Invert both clocks */
1120             *val_cr2 ^= FSL_SAI_CR2_BCP;
1121             *val_cr4 ^= FSL_SAI_CR4_FSP;
1122             break;
1123         case SND_SOC_DAIFMT_IB_NF:
1124             /* Invert bit clock */
1125             *val_cr2 ^= FSL_SAI_CR2_BCP;
1126             break;
1127         case SND_SOC_DAIFMT_NB_IF:
1128             /* Invert frame clock */
1129             *val_cr4 ^= FSL_SAI_CR4_FSP;
1130             break;
1131         case SND_SOC_DAIFMT_NB_NF:
1132             /* Nothing to do for both normal cases */
1133             break;
1134         default:
1135             return -EINVAL;
1136     }
1137 
1138     return 0;
1139 }
1140 
SaiSetDaiFmtTr(struct PrivPlatformData * ppd,unsigned int fmt,int fsl_dir)1141 static int32_t SaiSetDaiFmtTr(struct PrivPlatformData *ppd, unsigned int fmt, int fsl_dir)
1142 {
1143     struct fsl_sai *sai = NULL;
1144     unsigned char offset = 0;
1145     int32_t val_cr2 = 0, val_cr4 = 0;
1146     bool tx = fsl_dir == FSL_FMT_TRANSMITTER;
1147     uint32_t read_val;
1148 
1149     if (ppd == NULL) {
1150         return HDF_FAILURE;
1151     }
1152 
1153     sai = &ppd->sai;
1154     offset = sai->reg_offset;
1155 
1156     if (!sai->is_lsb_first) {
1157         val_cr4 |= FSL_SAI_CR4_MF;
1158     }
1159 
1160     sai->is_dsp_mode = false;
1161     if (HandleDaiMode(fmt, &val_cr2, &val_cr4, &sai) < 0) {
1162         return -EINVAL;
1163     }
1164 
1165     if (HandleDaiCLK(fmt, &val_cr2, &val_cr4) < 0) {
1166         return -EINVAL;
1167     }
1168 
1169     sai->slave_mode[tx] = false;
1170 
1171     /* DAI clock master masks */
1172     switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) {
1173         case SND_SOC_DAIFMT_CBS_CFS:
1174             val_cr2 |= FSL_SAI_CR2_BCD_MSTR;
1175             val_cr4 |= FSL_SAI_CR4_FSD_MSTR;
1176             break;
1177         case SND_SOC_DAIFMT_CBM_CFM:
1178             sai->slave_mode[tx] = true;
1179             break;
1180         case SND_SOC_DAIFMT_CBS_CFM:
1181             val_cr2 |= FSL_SAI_CR2_BCD_MSTR;
1182             break;
1183         case SND_SOC_DAIFMT_CBM_CFS:
1184             val_cr4 |= FSL_SAI_CR4_FSD_MSTR;
1185             sai->slave_mode[tx] = true;
1186             break;
1187         default:
1188             return -EINVAL;
1189     }
1190 
1191     regmap_read(sai->regmap, FSL_SAI_xCR2(tx, offset), &read_val);
1192     regmap_read(sai->regmap, FSL_SAI_xCR4(tx, offset), &read_val);
1193 
1194     regmap_update_bits(sai->regmap, FSL_SAI_xCR2(tx, offset),
1195                        FSL_SAI_CR2_BCP | FSL_SAI_CR2_BCD_MSTR, val_cr2);
1196     regmap_update_bits(sai->regmap, FSL_SAI_xCR4(tx, offset),
1197                        FSL_SAI_CR4_MF | FSL_SAI_CR4_FSE |
1198                        FSL_SAI_CR4_FSP | FSL_SAI_CR4_FSD_MSTR, val_cr4);
1199 
1200     regmap_read(sai->regmap, FSL_SAI_xCR2(tx, offset), &read_val);
1201     regmap_read(sai->regmap, FSL_SAI_xCR4(tx, offset), &read_val);
1202 
1203     return HDF_SUCCESS;
1204 }
1205 
SaiSetDaiFmt(const struct PlatformData * pd,unsigned int fmt)1206 int32_t SaiSetDaiFmt(const struct PlatformData *pd, unsigned int fmt)
1207 {
1208     struct PrivPlatformData *ppd = (struct PrivPlatformData *)pd->dmaPrv;
1209     int32_t ret;
1210 
1211     ret = SaiSetDaiFmtTr(ppd, fmt, FSL_FMT_TRANSMITTER);
1212     if (ret != HDF_SUCCESS) {
1213         AUDIO_DRIVER_LOG_ERR("set dai fmt tx failed");
1214         return ret;
1215     }
1216 
1217     ret = SaiSetDaiFmtTr(ppd, fmt, FSL_FMT_RECEIVER);
1218     if (ret != HDF_SUCCESS) {
1219         AUDIO_DRIVER_LOG_ERR("set dai fmt tx failed");
1220     }
1221 
1222     return ret;
1223 }
1224 
SaiHwFree(const struct DaiData * pd,int isTx)1225 int32_t SaiHwFree(const struct DaiData *pd, int isTx)
1226 {
1227     struct fsl_sai *sai = g_sai;
1228     unsigned char offset = sai->reg_offset;
1229     bool tx = isTx == TRIGGER_TX;
1230     regmap_update_bits(sai->regmap, FSL_SAI_xCR3(tx, offset),
1231                        FSL_SAI_CR3_TRCE_MASK, 0);
1232 
1233     if (sai->mclk_streams != 0) {
1234         clk_disable_unprepare(sai->mclk_clk[sai->mclk_id[tx]]);
1235         if (sai->mclk_streams & BIT(AUDIO_RENDER_STREAM)) {
1236             sai->mclk_streams &= ~BIT(AUDIO_RENDER_STREAM);
1237         } else if (sai->mclk_streams & BIT(AUDIO_CAPTURE_STREAM)) {
1238             sai->mclk_streams &= ~BIT(AUDIO_CAPTURE_STREAM);
1239         }
1240     }
1241 
1242     return HDF_SUCCESS;
1243 }
1244 
1245 #define NUM_128  (128)
1246 #define DELAY_10 (10)
SaiDriverInitClk(struct PrivPlatformData * ppd,void __iomem * base)1247 int32_t SaiDriverInitClk(struct PrivPlatformData *ppd, void __iomem *base)
1248 {
1249     int ret = 0, i = 0;;
1250     struct fsl_sai *sai = &ppd->sai;
1251     unsigned long clk_rate = 0;
1252     char tmp[8];
1253 
1254     sai->regmap = devm_regmap_init_mmio_clk(&ppd->pdev->dev, "bus", base, &fsl_sai_regmap_config);
1255 
1256     if (IS_ERR(sai->regmap) && PTR_ERR(sai->regmap) != -EPROBE_DEFER) {
1257         sai->regmap = devm_regmap_init_mmio_clk(&ppd->pdev->dev, "sai", base, &fsl_sai_regmap_config);
1258     }
1259     if (IS_ERR(sai->regmap)) {
1260         AUDIO_DRIVER_LOG_ERR("regmap init failed\n");
1261         return PTR_ERR(sai->regmap);
1262     }
1263 
1264     sai->bus_clk = devm_clk_get(&ppd->pdev->dev, "bus");
1265 
1266     if (IS_ERR(sai->bus_clk)) {
1267         AUDIO_DRIVER_LOG_ERR("failed to get bus clk %d", PTR_ERR(sai->bus_clk));
1268         sai->bus_clk = NULL;
1269     }
1270 
1271     clk_rate = clk_get_rate(sai->bus_clk);
1272     AUDIO_DRIVER_LOG_ERR("bus rate %d", clk_rate);
1273 
1274     for (i = 0; i < FSL_SAI_MCLK_MAX; i++) {
1275         ret = snprintf_s(tmp, sizeof(tmp)-1, sizeof(tmp)-1, "mclk%d", i);
1276         if (ret < 0) {
1277             AUDIO_DRIVER_LOG_ERR("failed to write mclk");
1278         }
1279         sai->mclk_clk[i] = devm_clk_get(&ppd->pdev->dev, tmp);
1280         if (IS_ERR(sai->mclk_clk[i])) {
1281             AUDIO_DRIVER_LOG_ERR("failed to get mclk%d clock: %ld\n", i, PTR_ERR(sai->mclk_clk[i]));
1282             sai->mclk_clk[i] = NULL;
1283         }
1284         clk_rate = clk_get_rate(sai->mclk_clk[i]);
1285     }
1286 
1287     sai->pll8k_clk = devm_clk_get(&ppd->pdev->dev, "pll8k");
1288     if (IS_ERR(sai->pll8k_clk)) {
1289         sai->pll8k_clk = NULL;
1290     }
1291 
1292     sai->pll11k_clk = devm_clk_get(&ppd->pdev->dev, "pll11k");
1293     if (IS_ERR(sai->pll11k_clk)) {
1294         sai->pll11k_clk = NULL;
1295     }
1296     return HDF_SUCCESS;
1297 }
1298 
SaiDriverInitDataline(struct PrivPlatformData * ppd)1299 int32_t SaiDriverInitDataline(struct PrivPlatformData *ppd)
1300 {
1301     int ret = 0;
1302     struct fsl_sai *sai = &ppd->sai;
1303 
1304     ret = fsl_sai_read_dlcfg(ppd->pdev, "fsl,dataline", &sai->pcm_dl_cfg,
1305                              sai->dataline);
1306     if (ret < 0) {
1307         return ret;
1308     }
1309 
1310     sai->pcm_dl_cfg_cnt = ret;
1311 
1312     ret = fsl_sai_read_dlcfg(ppd->pdev, "fsl,dataline,dsd", &sai->dsd_dl_cfg,
1313                              sai->dataline);
1314     if (ret < 0) {
1315         return ret;
1316     }
1317 
1318     sai->dsd_dl_cfg_cnt = ret;
1319 
1320     return ret;
1321 }
1322 
SaiDriverInitIrq(struct PrivPlatformData * ppd,struct device_node * np)1323 int32_t SaiDriverInitIrq(struct PrivPlatformData *ppd, struct device_node *np)
1324 {
1325     int irq = 0, ret = 0;
1326     struct fsl_sai *sai = &ppd->sai;
1327 
1328     irq = platform_get_irq(ppd->pdev, 0);
1329     if (irq < 0) {
1330         AUDIO_DRIVER_LOG_ERR("failed to get irq");
1331         return irq;
1332     }
1333 
1334     ret = devm_request_irq(&ppd->pdev->dev, irq, fsl_sai_isr, 0,
1335                            np->name, ppd);
1336     if (ret) {
1337         AUDIO_DRIVER_LOG_ERR("failed to claim irq");
1338         return ret;
1339     }
1340 
1341     sai->synchronous[RX] = true;
1342     sai->synchronous[TX] = false;
1343 
1344     if (of_find_property(np, "fsl,sai-synchronous-rx", NULL) &&
1345         of_find_property(np, "fsl,sai-asynchronous", NULL)) {
1346         /* error out if both synchronous and asynchronous are present */
1347         AUDIO_DRIVER_LOG_ERR("invalid binding for synchronous mode\n");
1348         return -EINVAL;
1349     }
1350 
1351     if (of_find_property(np, "fsl,sai-synchronous-rx", NULL)) {
1352         /* Sync Rx with Tx */
1353         sai->synchronous[RX] = false;
1354         sai->synchronous[TX] = true;
1355     } else if (of_find_property(np, "fsl,sai-asynchronous", NULL)) {
1356         /* Discard all settings for asynchronous mode */
1357         sai->synchronous[RX] = false;
1358         sai->synchronous[TX] = false;
1359     }
1360 
1361     return ret;
1362 }
1363 
SaiDriverInitDma(struct PrivPlatformData * ppd,struct device_node * np,struct resource * res)1364 int32_t SaiDriverInitDma(struct PrivPlatformData *ppd, struct device_node *np, struct resource *res)
1365 {
1366     int ret = 0;
1367     struct fsl_sai *sai = &ppd->sai;
1368 
1369     platform_set_drvdata(ppd->pdev, sai);
1370     ret = fsl_sai_check_ver(sai, &ppd->pdev->dev);
1371     if (ret < 0) {
1372         AUDIO_DRIVER_LOG_ERR("Error reading SAI version: %d", ret);
1373     }
1374 
1375     if (of_find_property(np, "fsl,sai-mclk-direction-output", NULL) &&
1376         sai->verid.id >= FSL_SAI_VERID_0301) {
1377         regmap_update_bits(sai->regmap, FSL_SAI_MCTL,
1378             FSL_SAI_MCTL_MCLK_EN, FSL_SAI_MCTL_MCLK_EN);
1379     }
1380 
1381     ppd->dma_addr_src = res->start + FSL_SAI_RDR0;
1382     ppd->dma_addr_dst = res->start + FSL_SAI_TDR0;
1383     ppd->dma_maxburst_rx = FSL_SAI_MAXBURST_RX;
1384     ppd->dma_maxburst_tx = FSL_SAI_MAXBURST_TX;
1385 
1386     sai->pinctrl = devm_pinctrl_get(&ppd->pdev->dev);
1387     regcache_cache_only(sai->regmap, true);
1388 
1389     pm_runtime_enable(&ppd->pdev->dev);
1390 
1391     return ret;
1392 }
1393 
SaiDriverInit(struct PlatformData * pd)1394 int32_t SaiDriverInit(struct PlatformData *pd)
1395 {
1396     struct PrivPlatformData *ppd = (struct PrivPlatformData *)pd->dmaPrv;
1397     struct device_node *np = ppd->pdev->dev.of_node;
1398     struct resource *res = NULL;
1399     struct fsl_sai *sai = &ppd->sai;
1400     void __iomem *base = NULL;
1401     int ret = 0;
1402     g_sai = sai;
1403 
1404     ret = of_clk_set_defaults(np, false);
1405     if (ret < 0) {
1406         AUDIO_DRIVER_LOG_ERR("sai driver init clk set default failed");
1407         return HDF_FAILURE;
1408     }
1409 
1410     sai->is_lsb_first = of_property_read_bool(np, "lsb-first");
1411     res = platform_get_resource(ppd->pdev, IORESOURCE_MEM, 0);
1412     base = devm_ioremap_resource(&ppd->pdev->dev, res);
1413     if (IS_ERR(base)) {
1414         return PTR_ERR(base);
1415     }
1416 
1417     sai->reg_offset = FSL_REG_OFFSET;
1418     ret = SaiDriverInitClk(ppd, base);
1419     if (ret != HDF_SUCCESS) {
1420         ADM_LOG_ERR("SaiDriverInitClk fail ret=%d", ret);
1421         return ret;
1422     }
1423     sai->dataline = 0xFF;
1424     sai->fifo_depth = NUM_128;
1425     ret = SaiDriverInitDataline(ppd);
1426     if (ret < 0) {
1427         ADM_LOG_ERR("SaiDriverInitDataline fail ret=%d", ret);
1428         return ret;
1429     }
1430     ret = SaiDriverInitIrq(ppd, np);
1431     if (ret != HDF_SUCCESS) {
1432         ADM_LOG_ERR("SaiDriverInitIrq fail ret=%d", ret);
1433         return ret;
1434     }
1435     ret = SaiDriverInitDma(ppd, np, res);
1436     if (ret != HDF_SUCCESS) {
1437         ADM_LOG_ERR("SaiDriverInitDma fail ret=%d", ret);
1438         return ret;
1439     }
1440     AUDIO_DRIVER_LOG_ERR("success probe in sai driver");
1441     return HDF_SUCCESS;
1442 }
1443 
SaiTriggerStart(struct fsl_sai * sai,bool tx,u8 channels,u32 dl_mask,u32 pins)1444 void SaiTriggerStart(struct fsl_sai *sai, bool tx, u8 channels, u32 dl_mask, u32 pins)
1445 {
1446     unsigned char offset = sai->reg_offset;
1447     int i = 0, j = 0, k = 0;
1448     /*
1449      * Asynchronous mode: Clear SYNC for both Tx and Rx.
1450      * Rx sync with Tx clocks: Clear SYNC for Tx, set it for Rx.
1451      * Tx sync with Rx clocks: Clear SYNC for Rx, set it for Tx.
1452     */
1453     regmap_update_bits(sai->regmap, FSL_SAI_TCR2(offset), FSL_SAI_CR2_SYNC,
1454                        sai->synchronous[TX] ? FSL_SAI_CR2_SYNC : 0);
1455     regmap_update_bits(sai->regmap, FSL_SAI_RCR2(offset), FSL_SAI_CR2_SYNC,
1456                        sai->synchronous[RX] ? FSL_SAI_CR2_SYNC : 0);
1457 
1458     while (tx && i < channels) {
1459         if (dl_mask & (1 << j)) {
1460             regmap_write(sai->regmap, FSL_SAI_TDR0 + j * 0x4, 0x0);
1461             i++;
1462             k++;
1463         }
1464         j++;
1465 
1466         if ((pins != 0) && (k % pins) == 0) {
1467             j = 0;
1468         }
1469     }
1470 
1471     regmap_update_bits(sai->regmap, FSL_SAI_xCSR(tx, offset),
1472                        FSL_SAI_CSR_FRDE, FSL_SAI_CSR_FRDE);
1473 
1474     regmap_update_bits(sai->regmap, FSL_SAI_xCSR(tx, offset),
1475                        FSL_SAI_CSR_TERE, FSL_SAI_CSR_TERE);
1476     regmap_update_bits(sai->regmap, FSL_SAI_xCSR(tx, offset),
1477                        FSL_SAI_CSR_SE, FSL_SAI_CSR_SE);
1478     if (!sai->synchronous[TX] && sai->synchronous[RX] && !tx) {
1479         regmap_update_bits(sai->regmap, FSL_SAI_xCSR((!tx), offset),
1480                            FSL_SAI_CSR_TERE, FSL_SAI_CSR_TERE);
1481     } else if (!sai->synchronous[RX] && sai->synchronous[TX] && tx) {
1482         regmap_update_bits(sai->regmap, FSL_SAI_xCSR((!tx), offset),
1483                            FSL_SAI_CSR_TERE, FSL_SAI_CSR_TERE);
1484     }
1485 
1486     regmap_update_bits(sai->regmap, FSL_SAI_xCSR(tx, offset),
1487                        FSL_SAI_CSR_xIE_MASK, FSL_SAI_FLAGS);
1488 }
SaiTriggerStop(struct fsl_sai * sai,bool tx)1489 void SaiTriggerStop(struct fsl_sai *sai, bool tx)
1490 {
1491     unsigned char offset = sai->reg_offset;
1492     u32 xcsr = 0, count = 100;
1493 
1494     regmap_update_bits(sai->regmap, FSL_SAI_xCSR(tx, offset),
1495         FSL_SAI_CSR_FRDE, 0);
1496     regmap_update_bits(sai->regmap, FSL_SAI_xCSR(tx, offset),
1497         FSL_SAI_CSR_xIE_MASK, 0);
1498 
1499     /* Check if the opposite FRDE is also disabled */
1500     regmap_read(sai->regmap, FSL_SAI_xCSR(!tx, offset), &xcsr);
1501     if (!(xcsr & FSL_SAI_CSR_FRDE)) {
1502         /* Disable both directions and reset their FIFOs */
1503         regmap_update_bits(sai->regmap, FSL_SAI_TCSR(offset),
1504             FSL_SAI_CSR_TERE, 0);
1505         regmap_update_bits(sai->regmap, FSL_SAI_RCSR(offset),
1506             FSL_SAI_CSR_TERE, 0);
1507 
1508         /* TERE will remain set till the end of current frame */
1509         do {
1510             udelay(DELAY_10);
1511             regmap_read(sai->regmap, FSL_SAI_xCSR(tx, offset), &xcsr);
1512         } while (((--count) && (xcsr)) & (FSL_SAI_CSR_TERE));
1513 
1514         regmap_update_bits(sai->regmap, FSL_SAI_TCSR(offset),
1515             FSL_SAI_CSR_FR, FSL_SAI_CSR_FR);
1516         regmap_update_bits(sai->regmap, FSL_SAI_RCSR(offset),
1517             FSL_SAI_CSR_FR, FSL_SAI_CSR_FR);
1518 
1519         /*
1520             * For sai master mode, after several open/close sai,
1521             * there will be no frame clock, and can't recover
1522             * anymore. Add software reset to fix this issue.
1523             * This is a hardware bug, and will be fix in the
1524             * next sai version.
1525         */
1526         if (!sai->slave_mode[tx]) {
1527             /* Software Reset for both Tx and Rx */
1528             regmap_write(sai->regmap,
1529                 FSL_SAI_TCSR(offset), FSL_SAI_CSR_SR);
1530             regmap_write(sai->regmap,
1531                 FSL_SAI_RCSR(offset), FSL_SAI_CSR_SR);
1532             /* Clear SR bit to finish the reset */
1533             regmap_write(sai->regmap, FSL_SAI_TCSR(offset), 0);
1534             regmap_write(sai->regmap, FSL_SAI_RCSR(offset), 0);
1535         }
1536     }
1537 }
1538 
SaiTrigger(const struct DaiData * pd,int cmd,int isTx)1539 int32_t SaiTrigger(const struct DaiData *pd, int cmd, int isTx)
1540 {
1541     struct fsl_sai *sai = g_sai;
1542     bool tx = isTx == TRIGGER_TX;
1543     u8 channels = 0;
1544     u32 slots = (channels == 1) ? 2 : channels;
1545     u32 pins = 0;
1546     u32 dl_mask = 0;
1547 
1548     if (isTx == TRIGGER_TX) {
1549         channels = pd->pcmInfo.channels;
1550     } else if (isTx == TRIGGER_RX) {
1551         channels = pd->pcmInfo.channels;
1552     }
1553 
1554     if (sai->slots) {
1555         slots = sai->slots;
1556     }
1557 
1558     pins = DIV_ROUND_UP(channels, slots);
1559     dl_mask = SaiGetdlMask(sai, tx, pins);
1560 
1561     if (cmd == TRIGGER_START) {
1562         SaiTriggerStart(sai, tx, channels, dl_mask, pins);
1563     } else {
1564         SaiTriggerStop(sai, tx);
1565     }
1566 
1567     SaiPrintAllRegister();
1568     return HDF_SUCCESS;
1569 }
1570 
1571 #define DELAY_1000  (1000)
1572 #define DELAY_2000  (2000)
SaiRuntimeResume(const struct PlatformData * platformData)1573 int32_t SaiRuntimeResume(const struct PlatformData *platformData)
1574 {
1575     struct fsl_sai *sai = GetDrvSai(platformData);
1576     uint8_t offset = sai->reg_offset;
1577     int32_t ret;
1578 
1579     AUDIO_DRIVER_LOG_ERR("bus_clk enable");
1580     ret = clk_prepare_enable(sai->bus_clk);
1581     if (ret) {
1582         AUDIO_DRIVER_LOG_ERR("failed to enable bus clock: %d\n", ret);
1583         return ret;
1584     }
1585 
1586     if (sai->mclk_streams & BIT(AUDIO_RENDER_STREAM)) {
1587         AUDIO_DRIVER_LOG_ERR("mclk enable %d", sai->mclk_id[TX]);
1588         ret = clk_prepare_enable(sai->mclk_clk[sai->mclk_id[TX]]);
1589         if (ret) {
1590             clk_disable_unprepare(sai->bus_clk);
1591             return ret;
1592         }
1593     }
1594 
1595     if (sai->mclk_streams & BIT(AUDIO_CAPTURE_STREAM)) {
1596         AUDIO_DRIVER_LOG_ERR("mclk enable %d", sai->mclk_id[RX]);
1597         ret = clk_prepare_enable(sai->mclk_clk[sai->mclk_id[RX]]);
1598         if (ret) {
1599             if (sai->mclk_streams & BIT(AUDIO_RENDER_STREAM)) {
1600                 clk_disable_unprepare(sai->mclk_clk[sai->mclk_id[1]]);
1601             }
1602             clk_disable_unprepare(sai->bus_clk);
1603 
1604             return ret;
1605         }
1606     }
1607 
1608     request_bus_freq(BUS_FREQ_AUDIO);
1609 
1610     regcache_cache_only(sai->regmap, false);
1611     regcache_mark_dirty(sai->regmap);
1612 
1613     regmap_write(sai->regmap, FSL_SAI_TCSR(offset), FSL_SAI_CSR_SR);
1614     regmap_write(sai->regmap, FSL_SAI_RCSR(offset), FSL_SAI_CSR_SR);
1615     usleep_range(DELAY_1000, DELAY_2000);
1616     regmap_write(sai->regmap, FSL_SAI_TCSR(offset), 0);
1617     regmap_write(sai->regmap, FSL_SAI_RCSR(offset), 0);
1618 
1619     ret = regcache_sync(sai->regmap);
1620     if (ret) {
1621         if (sai->mclk_streams & BIT(AUDIO_CAPTURE_STREAM)) {
1622             clk_disable_unprepare(sai->mclk_clk[sai->mclk_id[0]]);
1623         }
1624         if (sai->mclk_streams & BIT(AUDIO_RENDER_STREAM)) {
1625             clk_disable_unprepare(sai->mclk_clk[sai->mclk_id[1]]);
1626         }
1627         clk_disable_unprepare(sai->bus_clk);
1628 
1629         return ret;
1630     }
1631 
1632     return HDF_SUCCESS;
1633 }
1634 
SaiRuntimeSuspend(const struct DaiData * platformData)1635 int32_t SaiRuntimeSuspend(const struct DaiData *platformData)
1636 {
1637     struct fsl_sai *sai = g_sai;
1638 
1639     regcache_cache_only(sai->regmap, true);
1640 
1641     release_bus_freq(BUS_FREQ_AUDIO);
1642 
1643     if (sai->mclk_streams & BIT(AUDIO_CAPTURE_STREAM)) {
1644         clk_disable_unprepare(sai->mclk_clk[sai->mclk_id[0]]);
1645     }
1646 
1647     if (sai->mclk_streams & BIT(AUDIO_RENDER_STREAM)) {
1648         clk_disable_unprepare(sai->mclk_clk[sai->mclk_id[1]]);
1649     }
1650 
1651     clk_disable_unprepare(sai->bus_clk);
1652 
1653     regcache_cache_only(sai->regmap, true);
1654     regcache_mark_dirty(sai->regmap);
1655 
1656     return HDF_SUCCESS;
1657 }
1658 
SaiDaiProbe(const struct PlatformData * platformData)1659 int32_t SaiDaiProbe(const struct PlatformData *platformData)
1660 {
1661     struct fsl_sai *sai = GetDrvSai(platformData);
1662     uint8_t offset = sai->reg_offset;
1663     int32_t ret = 0;
1664 
1665     AUDIO_DRIVER_LOG_ERR("sai dai probe");
1666     regmap_update_bits(sai->regmap, FSL_SAI_TCR1(offset),
1667                        sai->fifo_depth - 1,
1668                        sai->fifo_depth - FSL_SAI_MAXBURST_TX);
1669     regmap_update_bits(sai->regmap, FSL_SAI_RCR1(offset),
1670                        sai->fifo_depth - 1,
1671                        FSL_SAI_MAXBURST_RX - 1);
1672 
1673     if (!IS_ERR_OR_NULL(sai->pinctrl)) {
1674         sai->pins_state = pinctrl_lookup_state(sai->pinctrl, "default");
1675         if (!IS_ERR_OR_NULL(sai->pins_state)) {
1676             ret = pinctrl_select_state(sai->pinctrl, sai->pins_state);
1677             if (ret) {
1678                 AUDIO_DRIVER_LOG_ERR("failed to set properpins state");
1679                 return HDF_FAILURE;
1680             }
1681         }
1682     }
1683 
1684     return HDF_SUCCESS;
1685 }
1686 
SaiWrite(const struct PlatformData * platformData,int i)1687 int32_t SaiWrite(const struct PlatformData *platformData, int i)
1688 {
1689     struct fsl_sai *sai = GetDrvSai(platformData);
1690 
1691     regmap_update_bits(sai->regmap, FSL_SAI_TDR0, 0xFFFF, (i*0xFF+i));
1692 
1693     return 0;
1694 }
1695