^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0-only
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * Rockchip PDM ALSA SoC Digital Audio Interface(DAI) driver
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) * Copyright (C) 2017 Fuzhou Rockchip Electronics Co., Ltd
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) #include <linux/clk.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include <linux/of.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include <linux/of_device.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include <linux/pm_runtime.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include <linux/rational.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <linux/regmap.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) #include <linux/reset.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include <sound/dmaengine_pcm.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include <sound/pcm_params.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) #include "rockchip_pdm.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) #define PDM_DMA_BURST_SIZE (8) /* size * width: 8*4 = 32 bytes */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) #define PDM_SIGNOFF_CLK_100M (100000000)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) #define PDM_SIGNOFF_CLK_300M (300000000)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) #define PDM_PATH_MAX (4)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) #define PDM_DEFAULT_RATE (48000)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) #define PDM_START_DELAY_MS_DEFAULT (20)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) #define PDM_START_DELAY_MS_MIN (0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) #define PDM_START_DELAY_MS_MAX (1000)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) #define PDM_FILTER_DELAY_MS_MIN (20)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) #define PDM_FILTER_DELAY_MS_MAX (1000)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) #define PDM_CLK_SHIFT_PPM_MAX (1000000) /* 1 ppm */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) enum rk_pdm_version {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) RK_PDM_RK3229,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) RK_PDM_RK3308,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) RK_PDM_RK3588,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) RK_PDM_RV1126,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) struct rk_pdm_dev {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) struct device *dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) struct clk *clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) struct clk *hclk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) struct regmap *regmap;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) struct snd_dmaengine_dai_dma_data capture_dma_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) struct reset_control *reset;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) unsigned int start_delay_ms;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) unsigned int filter_delay_ms;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) enum rk_pdm_version version;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) struct rk_pdm_clkref {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) unsigned int sr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) unsigned int clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) unsigned int clk_out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) struct rk_pdm_ds_ratio {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) unsigned int ratio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) unsigned int sr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) static struct rk_pdm_clkref clkref[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) { 8000, 40960000, 2048000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) { 11025, 56448000, 2822400 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) { 12000, 61440000, 3072000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) { 8000, 98304000, 2048000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) { 12000, 98304000, 3072000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) static struct rk_pdm_ds_ratio ds_ratio[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) { 0, 192000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) { 0, 176400 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) { 0, 128000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) { 1, 96000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) { 1, 88200 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) { 1, 64000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) { 2, 48000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) { 2, 44100 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) { 2, 32000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) { 3, 24000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) { 3, 22050 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) { 3, 16000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) { 4, 12000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) { 4, 11025 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) { 4, 8000 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) static unsigned int get_pdm_clk(struct rk_pdm_dev *pdm, unsigned int sr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) unsigned int *clk_src, unsigned int *clk_out,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) unsigned int signoff)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) unsigned int i, count, clk, div, rate, delta;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) clk = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) if (!sr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) return clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) count = ARRAY_SIZE(clkref);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) for (i = 0; i < count; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) if (sr % clkref[i].sr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) div = sr / clkref[i].sr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) if ((div & (div - 1)) == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) *clk_out = clkref[i].clk_out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) rate = clk_round_rate(pdm->clk, clkref[i].clk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) delta = clkref[i].clk / PDM_CLK_SHIFT_PPM_MAX;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) if (rate < clkref[i].clk - delta ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) rate > clkref[i].clk + delta)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) clk = clkref[i].clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) *clk_src = clkref[i].clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) if (!clk) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) clk = clk_round_rate(pdm->clk, signoff);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) *clk_src = clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) return clk;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) static unsigned int get_pdm_ds_ratio(unsigned int sr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) unsigned int i, count, ratio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) ratio = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) if (!sr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) return ratio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) count = ARRAY_SIZE(ds_ratio);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) for (i = 0; i < count; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) if (sr == ds_ratio[i].sr)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) ratio = ds_ratio[i].ratio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) return ratio;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) static unsigned int get_pdm_cic_ratio(unsigned int clk)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) switch (clk) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) case 4096000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) case 5644800:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) case 6144000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) case 2048000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) case 2822400:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) case 3072000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) case 1024000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) case 1411200:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) case 1536000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) return 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) static unsigned int samplerate_to_bit(unsigned int samplerate)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) switch (samplerate) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) case 8000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) case 11025:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) case 12000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) case 16000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) case 22050:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) case 24000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) case 32000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) return 2;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) case 44100:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) case 48000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) return 3;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) case 64000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) case 88200:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) case 96000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) return 4;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) case 128000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) case 176400:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) case 192000:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) return 5;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) static inline struct rk_pdm_dev *to_info(struct snd_soc_dai *dai)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) return snd_soc_dai_get_drvdata(dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) static void rockchip_pdm_drop_fifo(struct rk_pdm_dev *pdm)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) int cnt, val, i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) /* drop the dirty data */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) regmap_read(pdm->regmap, PDM_FIFO_CTRL, &cnt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) for (i = 0; i < PDM_FIFO_CNT(cnt); i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) regmap_read(pdm->regmap, PDM_RXFIFO_DATA, &val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) static void rockchip_pdm_rxctrl(struct rk_pdm_dev *pdm, int on)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) if (on) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) rockchip_pdm_drop_fifo(pdm);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) regmap_update_bits(pdm->regmap, PDM_DMA_CTRL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) PDM_DMA_RD_MSK, PDM_DMA_RD_EN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) regmap_update_bits(pdm->regmap, PDM_DMA_CTRL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) PDM_DMA_RD_MSK, PDM_DMA_RD_DIS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) regmap_update_bits(pdm->regmap, PDM_SYSCONFIG,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) PDM_RX_MASK | PDM_RX_CLR_MASK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) PDM_RX_STOP | PDM_RX_CLR_WR);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) static int rockchip_pdm_set_samplerate(struct rk_pdm_dev *pdm, unsigned int samplerate)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) unsigned int val = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) unsigned int clk_rate, clk_div;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) unsigned int clk_src = 0, clk_out = 0, signoff = PDM_SIGNOFF_CLK_100M;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) unsigned long m, n;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) bool change;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) if (pdm->version == RK_PDM_RK3588)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) signoff = PDM_SIGNOFF_CLK_300M;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) clk_rate = get_pdm_clk(pdm, samplerate, &clk_src, &clk_out, signoff);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) if (!clk_rate)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) ret = clk_set_rate(pdm->clk, clk_src);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) if (pdm->version == RK_PDM_RK3308 ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) pdm->version == RK_PDM_RK3588 ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) pdm->version == RK_PDM_RV1126) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) rational_best_approximation(clk_out, clk_src,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) GENMASK(16 - 1, 0),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) GENMASK(16 - 1, 0),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) &m, &n);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) val = (m << PDM_FD_NUMERATOR_SFT) |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) (n << PDM_FD_DENOMINATOR_SFT);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) regmap_update_bits_check(pdm->regmap, PDM_CTRL1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) PDM_FD_NUMERATOR_MSK |
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) PDM_FD_DENOMINATOR_MSK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) val, &change);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) if (change) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) reset_control_assert(pdm->reset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) reset_control_deassert(pdm->reset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) rockchip_pdm_rxctrl(pdm, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) clk_div = n / m;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) if (clk_div >= 40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) val = PDM_CLK_FD_RATIO_40;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) else if (clk_div <= 35)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) val = PDM_CLK_FD_RATIO_35;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) regmap_update_bits(pdm->regmap, PDM_CLK_CTRL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) PDM_CLK_FD_RATIO_MSK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) if (pdm->version == RK_PDM_RK3588 || pdm->version == RK_PDM_RV1126) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) val = get_pdm_cic_ratio(clk_out);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) regmap_update_bits(pdm->regmap, PDM_CLK_CTRL, PDM_CIC_RATIO_MSK, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) val = samplerate_to_bit(samplerate);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) regmap_update_bits(pdm->regmap, PDM_CTRL0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) PDM_SAMPLERATE_MSK, PDM_SAMPLERATE(val));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) val = get_pdm_ds_ratio(samplerate);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) regmap_update_bits(pdm->regmap, PDM_CLK_CTRL, PDM_DS_RATIO_MSK, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) regmap_update_bits(pdm->regmap, PDM_HPF_CTRL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) PDM_HPF_CF_MSK, PDM_HPF_60HZ);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) regmap_update_bits(pdm->regmap, PDM_HPF_CTRL,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) PDM_HPF_LE | PDM_HPF_RE, PDM_HPF_LE | PDM_HPF_RE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) static int rockchip_pdm_hw_params(struct snd_pcm_substream *substream,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) struct snd_pcm_hw_params *params,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) struct snd_soc_dai *dai)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) struct rk_pdm_dev *pdm = to_info(dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) unsigned int val = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) rockchip_pdm_set_samplerate(pdm, params_rate(params));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) if (pdm->version != RK_PDM_RK3229)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) regmap_update_bits(pdm->regmap, PDM_CTRL0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) PDM_MODE_MSK, PDM_MODE_LJ);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) val = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) switch (params_format(params)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) case SNDRV_PCM_FORMAT_S8:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) val |= PDM_VDW(8);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) case SNDRV_PCM_FORMAT_S16_LE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) val |= PDM_VDW(16);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) case SNDRV_PCM_FORMAT_S20_3LE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) val |= PDM_VDW(20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) case SNDRV_PCM_FORMAT_S24_LE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) val |= PDM_VDW(24);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) case SNDRV_PCM_FORMAT_S32_LE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) val |= PDM_VDW(32);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) switch (params_channels(params)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) case 8:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) val |= PDM_PATH3_EN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) fallthrough;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) case 6:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) val |= PDM_PATH2_EN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) fallthrough;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) case 4:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) val |= PDM_PATH1_EN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) fallthrough;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) case 2:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) val |= PDM_PATH0_EN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) dev_err(pdm->dev, "invalid channel: %d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) params_channels(params));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) regmap_update_bits(pdm->regmap, PDM_CTRL0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) PDM_PATH_MSK | PDM_VDW_MSK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) /* all channels share the single FIFO */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) regmap_update_bits(pdm->regmap, PDM_DMA_CTRL, PDM_DMA_RDL_MSK,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) PDM_DMA_RDL(8 * params_channels(params)));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) static int rockchip_pdm_set_fmt(struct snd_soc_dai *cpu_dai,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) unsigned int fmt)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) struct rk_pdm_dev *pdm = to_info(cpu_dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) unsigned int mask = 0, val = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) mask = PDM_CKP_MSK;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) switch (fmt & SND_SOC_DAIFMT_INV_MASK) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) case SND_SOC_DAIFMT_NB_NF:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) val = PDM_CKP_NORMAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) case SND_SOC_DAIFMT_IB_NF:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) val = PDM_CKP_INVERTED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) pm_runtime_get_sync(cpu_dai->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) regmap_update_bits(pdm->regmap, PDM_CLK_CTRL, mask, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) pm_runtime_put(cpu_dai->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) static int rockchip_pdm_trigger(struct snd_pcm_substream *substream, int cmd,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) struct snd_soc_dai *dai)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) struct rk_pdm_dev *pdm = to_info(dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) int ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) switch (cmd) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) case SNDRV_PCM_TRIGGER_START:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) case SNDRV_PCM_TRIGGER_RESUME:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) if (substream->stream == SNDRV_PCM_STREAM_CAPTURE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) rockchip_pdm_rxctrl(pdm, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) case SNDRV_PCM_TRIGGER_SUSPEND:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) case SNDRV_PCM_TRIGGER_STOP:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) if (substream->stream == SNDRV_PCM_STREAM_CAPTURE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) rockchip_pdm_rxctrl(pdm, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) static int rockchip_pdm_start_delay_info(struct snd_kcontrol *kcontrol,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) struct snd_ctl_elem_info *uinfo)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) uinfo->count = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) uinfo->value.integer.min = PDM_START_DELAY_MS_MIN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) uinfo->value.integer.max = PDM_START_DELAY_MS_MAX;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) uinfo->value.integer.step = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) static int rockchip_pdm_start_delay_get(struct snd_kcontrol *kcontrol,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) struct snd_ctl_elem_value *ucontrol)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) struct snd_soc_dai *dai = snd_kcontrol_chip(kcontrol);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) struct rk_pdm_dev *pdm = snd_soc_dai_get_drvdata(dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) ucontrol->value.integer.value[0] = pdm->start_delay_ms;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) static int rockchip_pdm_start_delay_put(struct snd_kcontrol *kcontrol,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) struct snd_ctl_elem_value *ucontrol)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) struct snd_soc_dai *dai = snd_kcontrol_chip(kcontrol);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) struct rk_pdm_dev *pdm = snd_soc_dai_get_drvdata(dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) if ((ucontrol->value.integer.value[0] < PDM_START_DELAY_MS_MIN) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) (ucontrol->value.integer.value[0] > PDM_START_DELAY_MS_MAX))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) pdm->start_delay_ms = ucontrol->value.integer.value[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) static int rockchip_pdm_filter_delay_info(struct snd_kcontrol *kcontrol,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) struct snd_ctl_elem_info *uinfo)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) uinfo->count = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) uinfo->value.integer.min = PDM_FILTER_DELAY_MS_MIN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) uinfo->value.integer.max = PDM_FILTER_DELAY_MS_MAX;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) uinfo->value.integer.step = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) static int rockchip_pdm_filter_delay_get(struct snd_kcontrol *kcontrol,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) struct snd_ctl_elem_value *ucontrol)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) struct snd_soc_dai *dai = snd_kcontrol_chip(kcontrol);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) struct rk_pdm_dev *pdm = snd_soc_dai_get_drvdata(dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) ucontrol->value.integer.value[0] = pdm->filter_delay_ms;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) static int rockchip_pdm_filter_delay_put(struct snd_kcontrol *kcontrol,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) struct snd_ctl_elem_value *ucontrol)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) struct snd_soc_dai *dai = snd_kcontrol_chip(kcontrol);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) struct rk_pdm_dev *pdm = snd_soc_dai_get_drvdata(dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) if ((ucontrol->value.integer.value[0] < PDM_FILTER_DELAY_MS_MIN) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) (ucontrol->value.integer.value[0] > PDM_FILTER_DELAY_MS_MAX))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) pdm->filter_delay_ms = ucontrol->value.integer.value[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) static const struct snd_kcontrol_new rockchip_pdm_controls[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) .iface = SNDRV_CTL_ELEM_IFACE_PCM,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) .name = "PDM Start Delay Ms",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) .info = rockchip_pdm_start_delay_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) .get = rockchip_pdm_start_delay_get,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) .put = rockchip_pdm_start_delay_put,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) .iface = SNDRV_CTL_ELEM_IFACE_PCM,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) .name = "PDM Filter Delay Ms",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) .info = rockchip_pdm_filter_delay_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) .get = rockchip_pdm_filter_delay_get,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) .put = rockchip_pdm_filter_delay_put,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) static int rockchip_pdm_dai_probe(struct snd_soc_dai *dai)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) struct rk_pdm_dev *pdm = to_info(dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503) dai->capture_dma_data = &pdm->capture_dma_data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) snd_soc_add_dai_controls(dai, rockchip_pdm_controls,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) ARRAY_SIZE(rockchip_pdm_controls));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) static void rockchip_pdm_shutdown(struct snd_pcm_substream *substream,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) struct snd_soc_dai *dai)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) struct rk_pdm_dev *pdm = to_info(dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) if (substream->stream != SNDRV_PCM_STREAM_CAPTURE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) regmap_update_bits(pdm->regmap, PDM_CLK_CTRL, PDM_CLK_MSK, PDM_CLK_DIS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) static int rockchip_pdm_prepare(struct snd_pcm_substream *substream,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) struct snd_soc_dai *dai)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) struct rk_pdm_dev *pdm = to_info(dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) if (substream->stream != SNDRV_PCM_STREAM_CAPTURE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) regmap_update_bits(pdm->regmap, PDM_SYSCONFIG, PDM_RX_MASK, PDM_RX_START);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) * after xfer start, a necessary delay for filter to init and will drop
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) * the dirty data in the trigger-START late.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) usleep_range((pdm->filter_delay_ms) * 1000, (pdm->filter_delay_ms + 1) * 1000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) static int rockchip_pdm_startup(struct snd_pcm_substream *substream,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) struct snd_soc_dai *dai)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) struct rk_pdm_dev *pdm = to_info(dai);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) if (substream->stream != SNDRV_PCM_STREAM_CAPTURE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) regmap_update_bits(pdm->regmap, PDM_CLK_CTRL, PDM_CLK_MSK, PDM_CLK_EN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) * a necessary delay for dmics wake-up after clk enabled, and drop the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) * dirty data in this duration.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) usleep_range((pdm->start_delay_ms + 1) * 1000, (pdm->start_delay_ms + 2) * 1000);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) static const struct snd_soc_dai_ops rockchip_pdm_dai_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) .startup = rockchip_pdm_startup,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) .shutdown = rockchip_pdm_shutdown,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) .set_fmt = rockchip_pdm_set_fmt,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) .trigger = rockchip_pdm_trigger,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) .prepare = rockchip_pdm_prepare,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) .hw_params = rockchip_pdm_hw_params,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) #define ROCKCHIP_PDM_RATES SNDRV_PCM_RATE_8000_192000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) #define ROCKCHIP_PDM_FORMATS (SNDRV_PCM_FMTBIT_S16_LE | \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) SNDRV_PCM_FMTBIT_S20_3LE | \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) SNDRV_PCM_FMTBIT_S24_LE | \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569) SNDRV_PCM_FMTBIT_S32_LE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) static struct snd_soc_dai_driver rockchip_pdm_dai = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) .probe = rockchip_pdm_dai_probe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) .capture = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) .stream_name = "Capture",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) .channels_min = 2,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) .channels_max = 8,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) .rates = ROCKCHIP_PDM_RATES,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) .formats = ROCKCHIP_PDM_FORMATS,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580) .ops = &rockchip_pdm_dai_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) .symmetric_rates = 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) static const struct snd_soc_component_driver rockchip_pdm_component = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) .name = "rockchip-pdm",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) static int rockchip_pdm_runtime_suspend(struct device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) struct rk_pdm_dev *pdm = dev_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) regcache_cache_only(pdm->regmap, true);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) clk_disable_unprepare(pdm->clk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) clk_disable_unprepare(pdm->hclk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599) static int rockchip_pdm_runtime_resume(struct device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) struct rk_pdm_dev *pdm = dev_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) ret = clk_prepare_enable(pdm->clk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) dev_err(pdm->dev, "clock enable failed %d\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610) ret = clk_prepare_enable(pdm->hclk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) dev_err(pdm->dev, "hclock enable failed %d\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) rockchip_pdm_rxctrl(pdm, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) regcache_cache_only(pdm->regmap, false);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) regcache_mark_dirty(pdm->regmap);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) ret = regcache_sync(pdm->regmap);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) clk_disable_unprepare(pdm->clk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) clk_disable_unprepare(pdm->hclk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) static bool rockchip_pdm_wr_reg(struct device *dev, unsigned int reg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629) switch (reg) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) case PDM_SYSCONFIG:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631) case PDM_CTRL0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) case PDM_CTRL1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) case PDM_CLK_CTRL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) case PDM_HPF_CTRL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) case PDM_FIFO_CTRL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) case PDM_DMA_CTRL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) case PDM_INT_EN:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638) case PDM_INT_CLR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) case PDM_DATA_VALID:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646) static bool rockchip_pdm_rd_reg(struct device *dev, unsigned int reg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) switch (reg) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649) case PDM_SYSCONFIG:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650) case PDM_CTRL0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) case PDM_CTRL1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) case PDM_CLK_CTRL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) case PDM_HPF_CTRL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) case PDM_FIFO_CTRL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655) case PDM_DMA_CTRL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) case PDM_INT_EN:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) case PDM_INT_CLR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) case PDM_INT_ST:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) case PDM_DATA_VALID:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660) case PDM_RXFIFO_DATA:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661) case PDM_VERSION:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668) static bool rockchip_pdm_volatile_reg(struct device *dev, unsigned int reg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670) switch (reg) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671) case PDM_SYSCONFIG:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) case PDM_FIFO_CTRL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) case PDM_INT_CLR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674) case PDM_INT_ST:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675) case PDM_RXFIFO_DATA:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682) static bool rockchip_pdm_precious_reg(struct device *dev, unsigned int reg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) switch (reg) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685) case PDM_RXFIFO_DATA:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686) return true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688) return false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) static const struct reg_default rockchip_pdm_reg_defaults[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) { PDM_CTRL0, 0x78000017 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) { PDM_CTRL1, 0x0bb8ea60 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695) { PDM_CLK_CTRL, 0x0000e401 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) { PDM_DMA_CTRL, 0x0000001f },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 699) static const struct regmap_config rockchip_pdm_regmap_config = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 700) .reg_bits = 32,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 701) .reg_stride = 4,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702) .val_bits = 32,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703) .max_register = PDM_VERSION,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) .reg_defaults = rockchip_pdm_reg_defaults,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) .num_reg_defaults = ARRAY_SIZE(rockchip_pdm_reg_defaults),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706) .writeable_reg = rockchip_pdm_wr_reg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) .readable_reg = rockchip_pdm_rd_reg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) .volatile_reg = rockchip_pdm_volatile_reg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709) .precious_reg = rockchip_pdm_precious_reg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710) .cache_type = REGCACHE_FLAT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) static const struct of_device_id rockchip_pdm_match[] __maybe_unused = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714) { .compatible = "rockchip,pdm",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) .data = (void *)RK_PDM_RK3229 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716) { .compatible = "rockchip,px30-pdm",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717) .data = (void *)RK_PDM_RK3308 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) { .compatible = "rockchip,rk1808-pdm",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719) .data = (void *)RK_PDM_RK3308 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) { .compatible = "rockchip,rk3308-pdm",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 721) .data = (void *)RK_PDM_RK3308 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 722) { .compatible = "rockchip,rk3568-pdm",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 723) .data = (void *)RK_PDM_RV1126 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 724) { .compatible = "rockchip,rk3588-pdm",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 725) .data = (void *)RK_PDM_RK3588 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 726) { .compatible = "rockchip,rv1126-pdm",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 727) .data = (void *)RK_PDM_RV1126 },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 728) {},
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 729) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 730) MODULE_DEVICE_TABLE(of, rockchip_pdm_match);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 731)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 732) static int rockchip_pdm_path_parse(struct rk_pdm_dev *pdm, struct device_node *node)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 733) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 734) unsigned int path[PDM_PATH_MAX];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 735) int cnt = 0, ret = 0, i = 0, val = 0, msk = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 736)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 737) cnt = of_count_phandle_with_args(node, "rockchip,path-map",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 738) NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 739) if (cnt != PDM_PATH_MAX)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 740) return cnt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 741)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 742) ret = of_property_read_u32_array(node, "rockchip,path-map",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 743) path, cnt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 744) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 745) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 746)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 747) for (i = 0; i < cnt; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 748) if (path[i] >= PDM_PATH_MAX)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 749) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 750) msk |= PDM_PATH_MASK(i);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 751) val |= PDM_PATH(i, path[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 752) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 753)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 754) regmap_update_bits(pdm->regmap, PDM_CLK_CTRL, msk, val);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 755)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 756) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 757) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 758)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 759) static int rockchip_pdm_probe(struct platform_device *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 760) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 761) struct device_node *node = pdev->dev.of_node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 762) const struct of_device_id *match;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 763) struct rk_pdm_dev *pdm;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 764) struct resource *res;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 765) void __iomem *regs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 766) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 767)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 768) pdm = devm_kzalloc(&pdev->dev, sizeof(*pdm), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 769) if (!pdm)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 770) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 771)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 772) match = of_match_device(rockchip_pdm_match, &pdev->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 773) if (match)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 774) pdm->version = (enum rk_pdm_version)match->data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 775)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 776) if (pdm->version == RK_PDM_RK3308) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 777) pdm->reset = devm_reset_control_get(&pdev->dev, "pdm-m");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 778) if (IS_ERR(pdm->reset))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 779) return PTR_ERR(pdm->reset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 780) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 781)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 782) regs = devm_platform_get_and_ioremap_resource(pdev, 0, &res);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 783) if (IS_ERR(regs))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 784) return PTR_ERR(regs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 785)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 786) pdm->regmap = devm_regmap_init_mmio(&pdev->dev, regs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 787) &rockchip_pdm_regmap_config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 788) if (IS_ERR(pdm->regmap))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 789) return PTR_ERR(pdm->regmap);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 790)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 791) pdm->capture_dma_data.addr = res->start + PDM_RXFIFO_DATA;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 792) pdm->capture_dma_data.addr_width = DMA_SLAVE_BUSWIDTH_4_BYTES;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 793) pdm->capture_dma_data.maxburst = PDM_DMA_BURST_SIZE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 794)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 795) pdm->dev = &pdev->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 796) dev_set_drvdata(&pdev->dev, pdm);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 797)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 798) pdm->start_delay_ms = PDM_START_DELAY_MS_DEFAULT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 799) pdm->filter_delay_ms = PDM_FILTER_DELAY_MS_MIN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 800)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 801) pdm->clk = devm_clk_get(&pdev->dev, "pdm_clk");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 802) if (IS_ERR(pdm->clk))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 803) return PTR_ERR(pdm->clk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 804)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 805) pdm->hclk = devm_clk_get(&pdev->dev, "pdm_hclk");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 806) if (IS_ERR(pdm->hclk))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 807) return PTR_ERR(pdm->hclk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 808)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 809) ret = clk_prepare_enable(pdm->hclk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 810) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 811) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 812)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 813) pm_runtime_enable(&pdev->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 814) if (!pm_runtime_enabled(&pdev->dev)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 815) ret = rockchip_pdm_runtime_resume(&pdev->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 816) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 817) goto err_pm_disable;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 818) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 819)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 820) ret = devm_snd_soc_register_component(&pdev->dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 821) &rockchip_pdm_component,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 822) &rockchip_pdm_dai, 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 823)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 824) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 825) dev_err(&pdev->dev, "could not register dai: %d\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 826) goto err_suspend;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 827) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 828)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 829) rockchip_pdm_set_samplerate(pdm, PDM_DEFAULT_RATE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 830) rockchip_pdm_rxctrl(pdm, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 831)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 832) ret = rockchip_pdm_path_parse(pdm, node);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 833) if (ret != 0 && ret != -ENOENT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 834) goto err_suspend;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 835)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 836) if (of_property_read_bool(node, "rockchip,no-dmaengine"))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 837) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 838)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 839) ret = devm_snd_dmaengine_pcm_register(&pdev->dev, NULL, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 840) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 841) dev_err(&pdev->dev, "could not register pcm: %d\n", ret);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 842) goto err_suspend;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 843) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 844)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 845) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 846)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 847) err_suspend:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 848) if (!pm_runtime_status_suspended(&pdev->dev))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 849) rockchip_pdm_runtime_suspend(&pdev->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 850) err_pm_disable:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 851) pm_runtime_disable(&pdev->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 852)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 853) clk_disable_unprepare(pdm->hclk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 854)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 855) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 856) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 857)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 858) static int rockchip_pdm_remove(struct platform_device *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 859) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 860) struct rk_pdm_dev *pdm = dev_get_drvdata(&pdev->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 861)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 862) pm_runtime_disable(&pdev->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 863) if (!pm_runtime_status_suspended(&pdev->dev))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 864) rockchip_pdm_runtime_suspend(&pdev->dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 865)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 866) clk_disable_unprepare(pdm->clk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 867) clk_disable_unprepare(pdm->hclk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 868)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 869) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 870) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 871)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 872) #ifdef CONFIG_PM_SLEEP
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 873) static int rockchip_pdm_suspend(struct device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 874) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 875) struct rk_pdm_dev *pdm = dev_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 876)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 877) regcache_mark_dirty(pdm->regmap);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 878)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 879) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 880) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 881)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 882) static int rockchip_pdm_resume(struct device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 883) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 884) struct rk_pdm_dev *pdm = dev_get_drvdata(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 885) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 886)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 887) ret = pm_runtime_get_sync(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 888) if (ret < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 889) pm_runtime_put(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 890) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 891) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 892)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 893) ret = regcache_sync(pdm->regmap);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 894)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 895) pm_runtime_put(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 896)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 897) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 898) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 899) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 900)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 901) static const struct dev_pm_ops rockchip_pdm_pm_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 902) SET_RUNTIME_PM_OPS(rockchip_pdm_runtime_suspend,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 903) rockchip_pdm_runtime_resume, NULL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 904) SET_SYSTEM_SLEEP_PM_OPS(rockchip_pdm_suspend, rockchip_pdm_resume)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 905) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 906)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 907) static struct platform_driver rockchip_pdm_driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 908) .probe = rockchip_pdm_probe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 909) .remove = rockchip_pdm_remove,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 910) .driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 911) .name = "rockchip-pdm",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 912) .of_match_table = of_match_ptr(rockchip_pdm_match),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 913) .pm = &rockchip_pdm_pm_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 914) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 915) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 916)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 917) module_platform_driver(rockchip_pdm_driver);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 918)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 919) MODULE_AUTHOR("Sugar <sugar.zhang@rock-chips.com>");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 920) MODULE_DESCRIPTION("Rockchip PDM Controller Driver");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 921) MODULE_LICENSE("GPL v2");