cs53l30.c (34893B)
1// SPDX-License-Identifier: GPL-2.0-only 2/* 3 * cs53l30.c -- CS53l30 ALSA Soc Audio driver 4 * 5 * Copyright 2015 Cirrus Logic, Inc. 6 * 7 * Authors: Paul Handrigan <Paul.Handrigan@cirrus.com>, 8 * Tim Howe <Tim.Howe@cirrus.com> 9 */ 10 11#include <linux/clk.h> 12#include <linux/delay.h> 13#include <linux/i2c.h> 14#include <linux/module.h> 15#include <linux/of_gpio.h> 16#include <linux/gpio/consumer.h> 17#include <linux/regulator/consumer.h> 18#include <sound/pcm_params.h> 19#include <sound/soc.h> 20#include <sound/tlv.h> 21 22#include "cs53l30.h" 23#include "cirrus_legacy.h" 24 25#define CS53L30_NUM_SUPPLIES 2 26static const char *const cs53l30_supply_names[CS53L30_NUM_SUPPLIES] = { 27 "VA", 28 "VP", 29}; 30 31struct cs53l30_private { 32 struct regulator_bulk_data supplies[CS53L30_NUM_SUPPLIES]; 33 struct regmap *regmap; 34 struct gpio_desc *reset_gpio; 35 struct gpio_desc *mute_gpio; 36 struct clk *mclk; 37 bool use_sdout2; 38 u32 mclk_rate; 39}; 40 41static const struct reg_default cs53l30_reg_defaults[] = { 42 { CS53L30_PWRCTL, CS53L30_PWRCTL_DEFAULT }, 43 { CS53L30_MCLKCTL, CS53L30_MCLKCTL_DEFAULT }, 44 { CS53L30_INT_SR_CTL, CS53L30_INT_SR_CTL_DEFAULT }, 45 { CS53L30_MICBIAS_CTL, CS53L30_MICBIAS_CTL_DEFAULT }, 46 { CS53L30_ASPCFG_CTL, CS53L30_ASPCFG_CTL_DEFAULT }, 47 { CS53L30_ASP_CTL1, CS53L30_ASP_CTL1_DEFAULT }, 48 { CS53L30_ASP_TDMTX_CTL1, CS53L30_ASP_TDMTX_CTLx_DEFAULT }, 49 { CS53L30_ASP_TDMTX_CTL2, CS53L30_ASP_TDMTX_CTLx_DEFAULT }, 50 { CS53L30_ASP_TDMTX_CTL3, CS53L30_ASP_TDMTX_CTLx_DEFAULT }, 51 { CS53L30_ASP_TDMTX_CTL4, CS53L30_ASP_TDMTX_CTLx_DEFAULT }, 52 { CS53L30_ASP_TDMTX_EN1, CS53L30_ASP_TDMTX_ENx_DEFAULT }, 53 { CS53L30_ASP_TDMTX_EN2, CS53L30_ASP_TDMTX_ENx_DEFAULT }, 54 { CS53L30_ASP_TDMTX_EN3, CS53L30_ASP_TDMTX_ENx_DEFAULT }, 55 { CS53L30_ASP_TDMTX_EN4, CS53L30_ASP_TDMTX_ENx_DEFAULT }, 56 { CS53L30_ASP_TDMTX_EN5, CS53L30_ASP_TDMTX_ENx_DEFAULT }, 57 { CS53L30_ASP_TDMTX_EN6, CS53L30_ASP_TDMTX_ENx_DEFAULT }, 58 { CS53L30_ASP_CTL2, CS53L30_ASP_CTL2_DEFAULT }, 59 { CS53L30_SFT_RAMP, CS53L30_SFT_RMP_DEFAULT }, 60 { CS53L30_LRCK_CTL1, CS53L30_LRCK_CTLx_DEFAULT }, 61 { CS53L30_LRCK_CTL2, CS53L30_LRCK_CTLx_DEFAULT }, 62 { CS53L30_MUTEP_CTL1, CS53L30_MUTEP_CTL1_DEFAULT }, 63 { CS53L30_MUTEP_CTL2, CS53L30_MUTEP_CTL2_DEFAULT }, 64 { CS53L30_INBIAS_CTL1, CS53L30_INBIAS_CTL1_DEFAULT }, 65 { CS53L30_INBIAS_CTL2, CS53L30_INBIAS_CTL2_DEFAULT }, 66 { CS53L30_DMIC1_STR_CTL, CS53L30_DMIC1_STR_CTL_DEFAULT }, 67 { CS53L30_DMIC2_STR_CTL, CS53L30_DMIC2_STR_CTL_DEFAULT }, 68 { CS53L30_ADCDMIC1_CTL1, CS53L30_ADCDMICx_CTL1_DEFAULT }, 69 { CS53L30_ADCDMIC1_CTL2, CS53L30_ADCDMIC1_CTL2_DEFAULT }, 70 { CS53L30_ADC1_CTL3, CS53L30_ADCx_CTL3_DEFAULT }, 71 { CS53L30_ADC1_NG_CTL, CS53L30_ADCx_NG_CTL_DEFAULT }, 72 { CS53L30_ADC1A_AFE_CTL, CS53L30_ADCxy_AFE_CTL_DEFAULT }, 73 { CS53L30_ADC1B_AFE_CTL, CS53L30_ADCxy_AFE_CTL_DEFAULT }, 74 { CS53L30_ADC1A_DIG_VOL, CS53L30_ADCxy_DIG_VOL_DEFAULT }, 75 { CS53L30_ADC1B_DIG_VOL, CS53L30_ADCxy_DIG_VOL_DEFAULT }, 76 { CS53L30_ADCDMIC2_CTL1, CS53L30_ADCDMICx_CTL1_DEFAULT }, 77 { CS53L30_ADCDMIC2_CTL2, CS53L30_ADCDMIC1_CTL2_DEFAULT }, 78 { CS53L30_ADC2_CTL3, CS53L30_ADCx_CTL3_DEFAULT }, 79 { CS53L30_ADC2_NG_CTL, CS53L30_ADCx_NG_CTL_DEFAULT }, 80 { CS53L30_ADC2A_AFE_CTL, CS53L30_ADCxy_AFE_CTL_DEFAULT }, 81 { CS53L30_ADC2B_AFE_CTL, CS53L30_ADCxy_AFE_CTL_DEFAULT }, 82 { CS53L30_ADC2A_DIG_VOL, CS53L30_ADCxy_DIG_VOL_DEFAULT }, 83 { CS53L30_ADC2B_DIG_VOL, CS53L30_ADCxy_DIG_VOL_DEFAULT }, 84 { CS53L30_INT_MASK, CS53L30_DEVICE_INT_MASK }, 85}; 86 87static bool cs53l30_volatile_register(struct device *dev, unsigned int reg) 88{ 89 if (reg == CS53L30_IS) 90 return true; 91 else 92 return false; 93} 94 95static bool cs53l30_writeable_register(struct device *dev, unsigned int reg) 96{ 97 switch (reg) { 98 case CS53L30_DEVID_AB: 99 case CS53L30_DEVID_CD: 100 case CS53L30_DEVID_E: 101 case CS53L30_REVID: 102 case CS53L30_IS: 103 return false; 104 default: 105 return true; 106 } 107} 108 109static bool cs53l30_readable_register(struct device *dev, unsigned int reg) 110{ 111 switch (reg) { 112 case CS53L30_DEVID_AB: 113 case CS53L30_DEVID_CD: 114 case CS53L30_DEVID_E: 115 case CS53L30_REVID: 116 case CS53L30_PWRCTL: 117 case CS53L30_MCLKCTL: 118 case CS53L30_INT_SR_CTL: 119 case CS53L30_MICBIAS_CTL: 120 case CS53L30_ASPCFG_CTL: 121 case CS53L30_ASP_CTL1: 122 case CS53L30_ASP_TDMTX_CTL1: 123 case CS53L30_ASP_TDMTX_CTL2: 124 case CS53L30_ASP_TDMTX_CTL3: 125 case CS53L30_ASP_TDMTX_CTL4: 126 case CS53L30_ASP_TDMTX_EN1: 127 case CS53L30_ASP_TDMTX_EN2: 128 case CS53L30_ASP_TDMTX_EN3: 129 case CS53L30_ASP_TDMTX_EN4: 130 case CS53L30_ASP_TDMTX_EN5: 131 case CS53L30_ASP_TDMTX_EN6: 132 case CS53L30_ASP_CTL2: 133 case CS53L30_SFT_RAMP: 134 case CS53L30_LRCK_CTL1: 135 case CS53L30_LRCK_CTL2: 136 case CS53L30_MUTEP_CTL1: 137 case CS53L30_MUTEP_CTL2: 138 case CS53L30_INBIAS_CTL1: 139 case CS53L30_INBIAS_CTL2: 140 case CS53L30_DMIC1_STR_CTL: 141 case CS53L30_DMIC2_STR_CTL: 142 case CS53L30_ADCDMIC1_CTL1: 143 case CS53L30_ADCDMIC1_CTL2: 144 case CS53L30_ADC1_CTL3: 145 case CS53L30_ADC1_NG_CTL: 146 case CS53L30_ADC1A_AFE_CTL: 147 case CS53L30_ADC1B_AFE_CTL: 148 case CS53L30_ADC1A_DIG_VOL: 149 case CS53L30_ADC1B_DIG_VOL: 150 case CS53L30_ADCDMIC2_CTL1: 151 case CS53L30_ADCDMIC2_CTL2: 152 case CS53L30_ADC2_CTL3: 153 case CS53L30_ADC2_NG_CTL: 154 case CS53L30_ADC2A_AFE_CTL: 155 case CS53L30_ADC2B_AFE_CTL: 156 case CS53L30_ADC2A_DIG_VOL: 157 case CS53L30_ADC2B_DIG_VOL: 158 case CS53L30_INT_MASK: 159 return true; 160 default: 161 return false; 162 } 163} 164 165static DECLARE_TLV_DB_SCALE(adc_boost_tlv, 0, 2000, 0); 166static DECLARE_TLV_DB_SCALE(adc_ng_boost_tlv, 0, 3000, 0); 167static DECLARE_TLV_DB_SCALE(pga_tlv, -600, 50, 0); 168static DECLARE_TLV_DB_SCALE(dig_tlv, -9600, 100, 1); 169static DECLARE_TLV_DB_SCALE(pga_preamp_tlv, 0, 10000, 0); 170 171static const char * const input1_sel_text[] = { 172 "DMIC1 On AB In", 173 "DMIC1 On A In", 174 "DMIC1 On B In", 175 "ADC1 On AB In", 176 "ADC1 On A In", 177 "ADC1 On B In", 178 "DMIC1 Off ADC1 Off", 179}; 180 181static unsigned int const input1_sel_values[] = { 182 CS53L30_CH_TYPE, 183 CS53L30_ADCxB_PDN | CS53L30_CH_TYPE, 184 CS53L30_ADCxA_PDN | CS53L30_CH_TYPE, 185 CS53L30_DMICx_PDN, 186 CS53L30_ADCxB_PDN | CS53L30_DMICx_PDN, 187 CS53L30_ADCxA_PDN | CS53L30_DMICx_PDN, 188 CS53L30_ADCxA_PDN | CS53L30_ADCxB_PDN | CS53L30_DMICx_PDN, 189}; 190 191static const char * const input2_sel_text[] = { 192 "DMIC2 On AB In", 193 "DMIC2 On A In", 194 "DMIC2 On B In", 195 "ADC2 On AB In", 196 "ADC2 On A In", 197 "ADC2 On B In", 198 "DMIC2 Off ADC2 Off", 199}; 200 201static unsigned int const input2_sel_values[] = { 202 0x0, 203 CS53L30_ADCxB_PDN, 204 CS53L30_ADCxA_PDN, 205 CS53L30_DMICx_PDN, 206 CS53L30_ADCxB_PDN | CS53L30_DMICx_PDN, 207 CS53L30_ADCxA_PDN | CS53L30_DMICx_PDN, 208 CS53L30_ADCxA_PDN | CS53L30_ADCxB_PDN | CS53L30_DMICx_PDN, 209}; 210 211static const char * const input1_route_sel_text[] = { 212 "ADC1_SEL", "DMIC1_SEL", 213}; 214 215static const struct soc_enum input1_route_sel_enum = 216 SOC_ENUM_SINGLE(CS53L30_ADCDMIC1_CTL1, CS53L30_CH_TYPE_SHIFT, 217 ARRAY_SIZE(input1_route_sel_text), 218 input1_route_sel_text); 219 220static SOC_VALUE_ENUM_SINGLE_DECL(input1_sel_enum, CS53L30_ADCDMIC1_CTL1, 0, 221 CS53L30_ADCDMICx_PDN_MASK, input1_sel_text, 222 input1_sel_values); 223 224static const struct snd_kcontrol_new input1_route_sel_mux = 225 SOC_DAPM_ENUM("Input 1 Route", input1_route_sel_enum); 226 227static const char * const input2_route_sel_text[] = { 228 "ADC2_SEL", "DMIC2_SEL", 229}; 230 231/* Note: CS53L30_ADCDMIC1_CTL1 CH_TYPE controls inputs 1 and 2 */ 232static const struct soc_enum input2_route_sel_enum = 233 SOC_ENUM_SINGLE(CS53L30_ADCDMIC1_CTL1, 0, 234 ARRAY_SIZE(input2_route_sel_text), 235 input2_route_sel_text); 236 237static SOC_VALUE_ENUM_SINGLE_DECL(input2_sel_enum, CS53L30_ADCDMIC2_CTL1, 0, 238 CS53L30_ADCDMICx_PDN_MASK, input2_sel_text, 239 input2_sel_values); 240 241static const struct snd_kcontrol_new input2_route_sel_mux = 242 SOC_DAPM_ENUM("Input 2 Route", input2_route_sel_enum); 243 244/* 245 * TB = 6144*(MCLK(int) scaling factor)/MCLK(internal) 246 * TB - Time base 247 * NOTE: If MCLK_INT_SCALE = 0, then TB=1 248 */ 249static const char * const cs53l30_ng_delay_text[] = { 250 "TB*50ms", "TB*100ms", "TB*150ms", "TB*200ms", 251}; 252 253static const struct soc_enum adc1_ng_delay_enum = 254 SOC_ENUM_SINGLE(CS53L30_ADC1_NG_CTL, CS53L30_ADCx_NG_DELAY_SHIFT, 255 ARRAY_SIZE(cs53l30_ng_delay_text), 256 cs53l30_ng_delay_text); 257 258static const struct soc_enum adc2_ng_delay_enum = 259 SOC_ENUM_SINGLE(CS53L30_ADC2_NG_CTL, CS53L30_ADCx_NG_DELAY_SHIFT, 260 ARRAY_SIZE(cs53l30_ng_delay_text), 261 cs53l30_ng_delay_text); 262 263/* The noise gate threshold selected will depend on NG Boost */ 264static const char * const cs53l30_ng_thres_text[] = { 265 "-64dB/-34dB", "-66dB/-36dB", "-70dB/-40dB", "-73dB/-43dB", 266 "-76dB/-46dB", "-82dB/-52dB", "-58dB", "-64dB", 267}; 268 269static const struct soc_enum adc1_ng_thres_enum = 270 SOC_ENUM_SINGLE(CS53L30_ADC1_NG_CTL, CS53L30_ADCx_NG_THRESH_SHIFT, 271 ARRAY_SIZE(cs53l30_ng_thres_text), 272 cs53l30_ng_thres_text); 273 274static const struct soc_enum adc2_ng_thres_enum = 275 SOC_ENUM_SINGLE(CS53L30_ADC2_NG_CTL, CS53L30_ADCx_NG_THRESH_SHIFT, 276 ARRAY_SIZE(cs53l30_ng_thres_text), 277 cs53l30_ng_thres_text); 278 279/* Corner frequencies are with an Fs of 48kHz. */ 280static const char * const hpf_corner_freq_text[] = { 281 "1.86Hz", "120Hz", "235Hz", "466Hz", 282}; 283 284static const struct soc_enum adc1_hpf_enum = 285 SOC_ENUM_SINGLE(CS53L30_ADC1_CTL3, CS53L30_ADCx_HPF_CF_SHIFT, 286 ARRAY_SIZE(hpf_corner_freq_text), hpf_corner_freq_text); 287 288static const struct soc_enum adc2_hpf_enum = 289 SOC_ENUM_SINGLE(CS53L30_ADC2_CTL3, CS53L30_ADCx_HPF_CF_SHIFT, 290 ARRAY_SIZE(hpf_corner_freq_text), hpf_corner_freq_text); 291 292static const struct snd_kcontrol_new cs53l30_snd_controls[] = { 293 SOC_SINGLE("Digital Soft-Ramp Switch", CS53L30_SFT_RAMP, 294 CS53L30_DIGSFT_SHIFT, 1, 0), 295 SOC_SINGLE("ADC1 Noise Gate Ganging Switch", CS53L30_ADC1_CTL3, 296 CS53L30_ADCx_NG_ALL_SHIFT, 1, 0), 297 SOC_SINGLE("ADC2 Noise Gate Ganging Switch", CS53L30_ADC2_CTL3, 298 CS53L30_ADCx_NG_ALL_SHIFT, 1, 0), 299 SOC_SINGLE("ADC1A Noise Gate Enable Switch", CS53L30_ADC1_NG_CTL, 300 CS53L30_ADCxA_NG_SHIFT, 1, 0), 301 SOC_SINGLE("ADC1B Noise Gate Enable Switch", CS53L30_ADC1_NG_CTL, 302 CS53L30_ADCxB_NG_SHIFT, 1, 0), 303 SOC_SINGLE("ADC2A Noise Gate Enable Switch", CS53L30_ADC2_NG_CTL, 304 CS53L30_ADCxA_NG_SHIFT, 1, 0), 305 SOC_SINGLE("ADC2B Noise Gate Enable Switch", CS53L30_ADC2_NG_CTL, 306 CS53L30_ADCxB_NG_SHIFT, 1, 0), 307 SOC_SINGLE("ADC1 Notch Filter Switch", CS53L30_ADCDMIC1_CTL2, 308 CS53L30_ADCx_NOTCH_DIS_SHIFT, 1, 1), 309 SOC_SINGLE("ADC2 Notch Filter Switch", CS53L30_ADCDMIC2_CTL2, 310 CS53L30_ADCx_NOTCH_DIS_SHIFT, 1, 1), 311 SOC_SINGLE("ADC1A Invert Switch", CS53L30_ADCDMIC1_CTL2, 312 CS53L30_ADCxA_INV_SHIFT, 1, 0), 313 SOC_SINGLE("ADC1B Invert Switch", CS53L30_ADCDMIC1_CTL2, 314 CS53L30_ADCxB_INV_SHIFT, 1, 0), 315 SOC_SINGLE("ADC2A Invert Switch", CS53L30_ADCDMIC2_CTL2, 316 CS53L30_ADCxA_INV_SHIFT, 1, 0), 317 SOC_SINGLE("ADC2B Invert Switch", CS53L30_ADCDMIC2_CTL2, 318 CS53L30_ADCxB_INV_SHIFT, 1, 0), 319 320 SOC_SINGLE_TLV("ADC1A Digital Boost Volume", CS53L30_ADCDMIC1_CTL2, 321 CS53L30_ADCxA_DIG_BOOST_SHIFT, 1, 0, adc_boost_tlv), 322 SOC_SINGLE_TLV("ADC1B Digital Boost Volume", CS53L30_ADCDMIC1_CTL2, 323 CS53L30_ADCxB_DIG_BOOST_SHIFT, 1, 0, adc_boost_tlv), 324 SOC_SINGLE_TLV("ADC2A Digital Boost Volume", CS53L30_ADCDMIC2_CTL2, 325 CS53L30_ADCxA_DIG_BOOST_SHIFT, 1, 0, adc_boost_tlv), 326 SOC_SINGLE_TLV("ADC2B Digital Boost Volume", CS53L30_ADCDMIC2_CTL2, 327 CS53L30_ADCxB_DIG_BOOST_SHIFT, 1, 0, adc_boost_tlv), 328 SOC_SINGLE_TLV("ADC1 NG Boost Volume", CS53L30_ADC1_NG_CTL, 329 CS53L30_ADCx_NG_BOOST_SHIFT, 1, 0, adc_ng_boost_tlv), 330 SOC_SINGLE_TLV("ADC2 NG Boost Volume", CS53L30_ADC2_NG_CTL, 331 CS53L30_ADCx_NG_BOOST_SHIFT, 1, 0, adc_ng_boost_tlv), 332 333 SOC_DOUBLE_R_TLV("ADC1 Preamplifier Volume", CS53L30_ADC1A_AFE_CTL, 334 CS53L30_ADC1B_AFE_CTL, CS53L30_ADCxy_PREAMP_SHIFT, 335 2, 0, pga_preamp_tlv), 336 SOC_DOUBLE_R_TLV("ADC2 Preamplifier Volume", CS53L30_ADC2A_AFE_CTL, 337 CS53L30_ADC2B_AFE_CTL, CS53L30_ADCxy_PREAMP_SHIFT, 338 2, 0, pga_preamp_tlv), 339 340 SOC_ENUM("Input 1 Channel Select", input1_sel_enum), 341 SOC_ENUM("Input 2 Channel Select", input2_sel_enum), 342 343 SOC_ENUM("ADC1 HPF Select", adc1_hpf_enum), 344 SOC_ENUM("ADC2 HPF Select", adc2_hpf_enum), 345 SOC_ENUM("ADC1 NG Threshold", adc1_ng_thres_enum), 346 SOC_ENUM("ADC2 NG Threshold", adc2_ng_thres_enum), 347 SOC_ENUM("ADC1 NG Delay", adc1_ng_delay_enum), 348 SOC_ENUM("ADC2 NG Delay", adc2_ng_delay_enum), 349 350 SOC_SINGLE_SX_TLV("ADC1A PGA Volume", 351 CS53L30_ADC1A_AFE_CTL, 0, 0x34, 0x24, pga_tlv), 352 SOC_SINGLE_SX_TLV("ADC1B PGA Volume", 353 CS53L30_ADC1B_AFE_CTL, 0, 0x34, 0x24, pga_tlv), 354 SOC_SINGLE_SX_TLV("ADC2A PGA Volume", 355 CS53L30_ADC2A_AFE_CTL, 0, 0x34, 0x24, pga_tlv), 356 SOC_SINGLE_SX_TLV("ADC2B PGA Volume", 357 CS53L30_ADC2B_AFE_CTL, 0, 0x34, 0x24, pga_tlv), 358 359 SOC_SINGLE_SX_TLV("ADC1A Digital Volume", 360 CS53L30_ADC1A_DIG_VOL, 0, 0xA0, 0x6C, dig_tlv), 361 SOC_SINGLE_SX_TLV("ADC1B Digital Volume", 362 CS53L30_ADC1B_DIG_VOL, 0, 0xA0, 0x6C, dig_tlv), 363 SOC_SINGLE_SX_TLV("ADC2A Digital Volume", 364 CS53L30_ADC2A_DIG_VOL, 0, 0xA0, 0x6C, dig_tlv), 365 SOC_SINGLE_SX_TLV("ADC2B Digital Volume", 366 CS53L30_ADC2B_DIG_VOL, 0, 0xA0, 0x6C, dig_tlv), 367}; 368 369static const struct snd_soc_dapm_widget cs53l30_dapm_widgets[] = { 370 SND_SOC_DAPM_INPUT("IN1_DMIC1"), 371 SND_SOC_DAPM_INPUT("IN2"), 372 SND_SOC_DAPM_INPUT("IN3_DMIC2"), 373 SND_SOC_DAPM_INPUT("IN4"), 374 SND_SOC_DAPM_SUPPLY("MIC1 Bias", CS53L30_MICBIAS_CTL, 375 CS53L30_MIC1_BIAS_PDN_SHIFT, 1, NULL, 0), 376 SND_SOC_DAPM_SUPPLY("MIC2 Bias", CS53L30_MICBIAS_CTL, 377 CS53L30_MIC2_BIAS_PDN_SHIFT, 1, NULL, 0), 378 SND_SOC_DAPM_SUPPLY("MIC3 Bias", CS53L30_MICBIAS_CTL, 379 CS53L30_MIC3_BIAS_PDN_SHIFT, 1, NULL, 0), 380 SND_SOC_DAPM_SUPPLY("MIC4 Bias", CS53L30_MICBIAS_CTL, 381 CS53L30_MIC4_BIAS_PDN_SHIFT, 1, NULL, 0), 382 383 SND_SOC_DAPM_AIF_OUT("ASP_SDOUT1", NULL, 0, CS53L30_ASP_CTL1, 384 CS53L30_ASP_SDOUTx_PDN_SHIFT, 1), 385 SND_SOC_DAPM_AIF_OUT("ASP_SDOUT2", NULL, 0, CS53L30_ASP_CTL2, 386 CS53L30_ASP_SDOUTx_PDN_SHIFT, 1), 387 388 SND_SOC_DAPM_MUX("Input Mux 1", SND_SOC_NOPM, 0, 0, 389 &input1_route_sel_mux), 390 SND_SOC_DAPM_MUX("Input Mux 2", SND_SOC_NOPM, 0, 0, 391 &input2_route_sel_mux), 392 393 SND_SOC_DAPM_ADC("ADC1A", NULL, CS53L30_ADCDMIC1_CTL1, 394 CS53L30_ADCxA_PDN_SHIFT, 1), 395 SND_SOC_DAPM_ADC("ADC1B", NULL, CS53L30_ADCDMIC1_CTL1, 396 CS53L30_ADCxB_PDN_SHIFT, 1), 397 SND_SOC_DAPM_ADC("ADC2A", NULL, CS53L30_ADCDMIC2_CTL1, 398 CS53L30_ADCxA_PDN_SHIFT, 1), 399 SND_SOC_DAPM_ADC("ADC2B", NULL, CS53L30_ADCDMIC2_CTL1, 400 CS53L30_ADCxB_PDN_SHIFT, 1), 401 SND_SOC_DAPM_ADC("DMIC1", NULL, CS53L30_ADCDMIC1_CTL1, 402 CS53L30_DMICx_PDN_SHIFT, 1), 403 SND_SOC_DAPM_ADC("DMIC2", NULL, CS53L30_ADCDMIC2_CTL1, 404 CS53L30_DMICx_PDN_SHIFT, 1), 405}; 406 407static const struct snd_soc_dapm_route cs53l30_dapm_routes[] = { 408 /* ADC Input Paths */ 409 {"ADC1A", NULL, "IN1_DMIC1"}, 410 {"Input Mux 1", "ADC1_SEL", "ADC1A"}, 411 {"ADC1B", NULL, "IN2"}, 412 413 {"ADC2A", NULL, "IN3_DMIC2"}, 414 {"Input Mux 2", "ADC2_SEL", "ADC2A"}, 415 {"ADC2B", NULL, "IN4"}, 416 417 /* MIC Bias Paths */ 418 {"ADC1A", NULL, "MIC1 Bias"}, 419 {"ADC1B", NULL, "MIC2 Bias"}, 420 {"ADC2A", NULL, "MIC3 Bias"}, 421 {"ADC2B", NULL, "MIC4 Bias"}, 422 423 /* DMIC Paths */ 424 {"DMIC1", NULL, "IN1_DMIC1"}, 425 {"Input Mux 1", "DMIC1_SEL", "DMIC1"}, 426 427 {"DMIC2", NULL, "IN3_DMIC2"}, 428 {"Input Mux 2", "DMIC2_SEL", "DMIC2"}, 429}; 430 431static const struct snd_soc_dapm_route cs53l30_dapm_routes_sdout1[] = { 432 /* Output Paths when using SDOUT1 only */ 433 {"ASP_SDOUT1", NULL, "ADC1A" }, 434 {"ASP_SDOUT1", NULL, "Input Mux 1"}, 435 {"ASP_SDOUT1", NULL, "ADC1B"}, 436 437 {"ASP_SDOUT1", NULL, "ADC2A"}, 438 {"ASP_SDOUT1", NULL, "Input Mux 2"}, 439 {"ASP_SDOUT1", NULL, "ADC2B"}, 440 441 {"Capture", NULL, "ASP_SDOUT1"}, 442}; 443 444static const struct snd_soc_dapm_route cs53l30_dapm_routes_sdout2[] = { 445 /* Output Paths when using both SDOUT1 and SDOUT2 */ 446 {"ASP_SDOUT1", NULL, "ADC1A" }, 447 {"ASP_SDOUT1", NULL, "Input Mux 1"}, 448 {"ASP_SDOUT1", NULL, "ADC1B"}, 449 450 {"ASP_SDOUT2", NULL, "ADC2A"}, 451 {"ASP_SDOUT2", NULL, "Input Mux 2"}, 452 {"ASP_SDOUT2", NULL, "ADC2B"}, 453 454 {"Capture", NULL, "ASP_SDOUT1"}, 455 {"Capture", NULL, "ASP_SDOUT2"}, 456}; 457 458struct cs53l30_mclk_div { 459 u32 mclk_rate; 460 u32 srate; 461 u8 asp_rate; 462 u8 internal_fs_ratio; 463 u8 mclk_int_scale; 464}; 465 466static const struct cs53l30_mclk_div cs53l30_mclk_coeffs[] = { 467 /* NOTE: Enable MCLK_INT_SCALE to save power. */ 468 469 /* MCLK, Sample Rate, asp_rate, internal_fs_ratio, mclk_int_scale */ 470 {5644800, 11025, 0x4, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 471 {5644800, 22050, 0x8, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 472 {5644800, 44100, 0xC, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 473 474 {6000000, 8000, 0x1, 0, CS53L30_MCLK_INT_SCALE}, 475 {6000000, 11025, 0x2, 0, CS53L30_MCLK_INT_SCALE}, 476 {6000000, 12000, 0x4, 0, CS53L30_MCLK_INT_SCALE}, 477 {6000000, 16000, 0x5, 0, CS53L30_MCLK_INT_SCALE}, 478 {6000000, 22050, 0x6, 0, CS53L30_MCLK_INT_SCALE}, 479 {6000000, 24000, 0x8, 0, CS53L30_MCLK_INT_SCALE}, 480 {6000000, 32000, 0x9, 0, CS53L30_MCLK_INT_SCALE}, 481 {6000000, 44100, 0xA, 0, CS53L30_MCLK_INT_SCALE}, 482 {6000000, 48000, 0xC, 0, CS53L30_MCLK_INT_SCALE}, 483 484 {6144000, 8000, 0x1, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 485 {6144000, 11025, 0x2, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 486 {6144000, 12000, 0x4, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 487 {6144000, 16000, 0x5, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 488 {6144000, 22050, 0x6, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 489 {6144000, 24000, 0x8, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 490 {6144000, 32000, 0x9, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 491 {6144000, 44100, 0xA, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 492 {6144000, 48000, 0xC, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 493 494 {6400000, 8000, 0x1, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 495 {6400000, 11025, 0x2, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 496 {6400000, 12000, 0x4, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 497 {6400000, 16000, 0x5, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 498 {6400000, 22050, 0x6, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 499 {6400000, 24000, 0x8, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 500 {6400000, 32000, 0x9, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 501 {6400000, 44100, 0xA, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 502 {6400000, 48000, 0xC, CS53L30_INTRNL_FS_RATIO, CS53L30_MCLK_INT_SCALE}, 503}; 504 505struct cs53l30_mclkx_div { 506 u32 mclkx; 507 u8 ratio; 508 u8 mclkdiv; 509}; 510 511static const struct cs53l30_mclkx_div cs53l30_mclkx_coeffs[] = { 512 {5644800, 1, CS53L30_MCLK_DIV_BY_1}, 513 {6000000, 1, CS53L30_MCLK_DIV_BY_1}, 514 {6144000, 1, CS53L30_MCLK_DIV_BY_1}, 515 {11289600, 2, CS53L30_MCLK_DIV_BY_2}, 516 {12288000, 2, CS53L30_MCLK_DIV_BY_2}, 517 {12000000, 2, CS53L30_MCLK_DIV_BY_2}, 518 {19200000, 3, CS53L30_MCLK_DIV_BY_3}, 519}; 520 521static int cs53l30_get_mclkx_coeff(int mclkx) 522{ 523 int i; 524 525 for (i = 0; i < ARRAY_SIZE(cs53l30_mclkx_coeffs); i++) { 526 if (cs53l30_mclkx_coeffs[i].mclkx == mclkx) 527 return i; 528 } 529 530 return -EINVAL; 531} 532 533static int cs53l30_get_mclk_coeff(int mclk_rate, int srate) 534{ 535 int i; 536 537 for (i = 0; i < ARRAY_SIZE(cs53l30_mclk_coeffs); i++) { 538 if (cs53l30_mclk_coeffs[i].mclk_rate == mclk_rate && 539 cs53l30_mclk_coeffs[i].srate == srate) 540 return i; 541 } 542 543 return -EINVAL; 544} 545 546static int cs53l30_set_sysclk(struct snd_soc_dai *dai, 547 int clk_id, unsigned int freq, int dir) 548{ 549 struct cs53l30_private *priv = snd_soc_component_get_drvdata(dai->component); 550 int mclkx_coeff; 551 u32 mclk_rate; 552 553 /* MCLKX -> MCLK */ 554 mclkx_coeff = cs53l30_get_mclkx_coeff(freq); 555 if (mclkx_coeff < 0) 556 return mclkx_coeff; 557 558 mclk_rate = cs53l30_mclkx_coeffs[mclkx_coeff].mclkx / 559 cs53l30_mclkx_coeffs[mclkx_coeff].ratio; 560 561 regmap_update_bits(priv->regmap, CS53L30_MCLKCTL, 562 CS53L30_MCLK_DIV_MASK, 563 cs53l30_mclkx_coeffs[mclkx_coeff].mclkdiv); 564 565 priv->mclk_rate = mclk_rate; 566 567 return 0; 568} 569 570static int cs53l30_set_dai_fmt(struct snd_soc_dai *dai, unsigned int fmt) 571{ 572 struct cs53l30_private *priv = snd_soc_component_get_drvdata(dai->component); 573 u8 aspcfg = 0, aspctl1 = 0; 574 575 switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) { 576 case SND_SOC_DAIFMT_CBM_CFM: 577 aspcfg |= CS53L30_ASP_MS; 578 break; 579 case SND_SOC_DAIFMT_CBS_CFS: 580 break; 581 default: 582 return -EINVAL; 583 } 584 585 /* DAI mode */ 586 switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) { 587 case SND_SOC_DAIFMT_I2S: 588 /* Set TDM_PDN to turn off TDM mode -- Reset default */ 589 aspctl1 |= CS53L30_ASP_TDM_PDN; 590 break; 591 case SND_SOC_DAIFMT_DSP_A: 592 /* 593 * Clear TDM_PDN to turn on TDM mode; Use ASP_SCLK_INV = 0 594 * with SHIFT_LEFT = 1 combination as Figure 4-13 shows in 595 * the CS53L30 datasheet 596 */ 597 aspctl1 |= CS53L30_SHIFT_LEFT; 598 break; 599 default: 600 return -EINVAL; 601 } 602 603 /* Check to see if the SCLK is inverted */ 604 switch (fmt & SND_SOC_DAIFMT_INV_MASK) { 605 case SND_SOC_DAIFMT_IB_NF: 606 case SND_SOC_DAIFMT_IB_IF: 607 aspcfg ^= CS53L30_ASP_SCLK_INV; 608 break; 609 default: 610 break; 611 } 612 613 regmap_update_bits(priv->regmap, CS53L30_ASPCFG_CTL, 614 CS53L30_ASP_MS | CS53L30_ASP_SCLK_INV, aspcfg); 615 616 regmap_update_bits(priv->regmap, CS53L30_ASP_CTL1, 617 CS53L30_ASP_TDM_PDN | CS53L30_SHIFT_LEFT, aspctl1); 618 619 return 0; 620} 621 622static int cs53l30_pcm_hw_params(struct snd_pcm_substream *substream, 623 struct snd_pcm_hw_params *params, 624 struct snd_soc_dai *dai) 625{ 626 struct cs53l30_private *priv = snd_soc_component_get_drvdata(dai->component); 627 int srate = params_rate(params); 628 int mclk_coeff; 629 630 /* MCLK -> srate */ 631 mclk_coeff = cs53l30_get_mclk_coeff(priv->mclk_rate, srate); 632 if (mclk_coeff < 0) 633 return -EINVAL; 634 635 regmap_update_bits(priv->regmap, CS53L30_INT_SR_CTL, 636 CS53L30_INTRNL_FS_RATIO_MASK, 637 cs53l30_mclk_coeffs[mclk_coeff].internal_fs_ratio); 638 639 regmap_update_bits(priv->regmap, CS53L30_MCLKCTL, 640 CS53L30_MCLK_INT_SCALE_MASK, 641 cs53l30_mclk_coeffs[mclk_coeff].mclk_int_scale); 642 643 regmap_update_bits(priv->regmap, CS53L30_ASPCFG_CTL, 644 CS53L30_ASP_RATE_MASK, 645 cs53l30_mclk_coeffs[mclk_coeff].asp_rate); 646 647 return 0; 648} 649 650static int cs53l30_set_bias_level(struct snd_soc_component *component, 651 enum snd_soc_bias_level level) 652{ 653 struct snd_soc_dapm_context *dapm = snd_soc_component_get_dapm(component); 654 struct cs53l30_private *priv = snd_soc_component_get_drvdata(component); 655 unsigned int reg; 656 int i, inter_max_check, ret; 657 658 switch (level) { 659 case SND_SOC_BIAS_ON: 660 break; 661 case SND_SOC_BIAS_PREPARE: 662 if (dapm->bias_level == SND_SOC_BIAS_STANDBY) 663 regmap_update_bits(priv->regmap, CS53L30_PWRCTL, 664 CS53L30_PDN_LP_MASK, 0); 665 break; 666 case SND_SOC_BIAS_STANDBY: 667 if (dapm->bias_level == SND_SOC_BIAS_OFF) { 668 ret = clk_prepare_enable(priv->mclk); 669 if (ret) { 670 dev_err(component->dev, 671 "failed to enable MCLK: %d\n", ret); 672 return ret; 673 } 674 regmap_update_bits(priv->regmap, CS53L30_MCLKCTL, 675 CS53L30_MCLK_DIS_MASK, 0); 676 regmap_update_bits(priv->regmap, CS53L30_PWRCTL, 677 CS53L30_PDN_ULP_MASK, 0); 678 msleep(50); 679 } else { 680 regmap_update_bits(priv->regmap, CS53L30_PWRCTL, 681 CS53L30_PDN_ULP_MASK, 682 CS53L30_PDN_ULP); 683 } 684 break; 685 case SND_SOC_BIAS_OFF: 686 regmap_update_bits(priv->regmap, CS53L30_INT_MASK, 687 CS53L30_PDN_DONE, 0); 688 /* 689 * If digital softramp is set, the amount of time required 690 * for power down increases and depends on the digital 691 * volume setting. 692 */ 693 694 /* Set the max possible time if digsft is set */ 695 regmap_read(priv->regmap, CS53L30_SFT_RAMP, ®); 696 if (reg & CS53L30_DIGSFT_MASK) 697 inter_max_check = CS53L30_PDN_POLL_MAX; 698 else 699 inter_max_check = 10; 700 701 regmap_update_bits(priv->regmap, CS53L30_PWRCTL, 702 CS53L30_PDN_ULP_MASK, 703 CS53L30_PDN_ULP); 704 /* PDN_DONE will take a min of 20ms to be set.*/ 705 msleep(20); 706 /* Clr status */ 707 regmap_read(priv->regmap, CS53L30_IS, ®); 708 for (i = 0; i < inter_max_check; i++) { 709 if (inter_max_check < 10) { 710 usleep_range(1000, 1100); 711 regmap_read(priv->regmap, CS53L30_IS, ®); 712 if (reg & CS53L30_PDN_DONE) 713 break; 714 } else { 715 usleep_range(10000, 10100); 716 regmap_read(priv->regmap, CS53L30_IS, ®); 717 if (reg & CS53L30_PDN_DONE) 718 break; 719 } 720 } 721 /* PDN_DONE is set. We now can disable the MCLK */ 722 regmap_update_bits(priv->regmap, CS53L30_INT_MASK, 723 CS53L30_PDN_DONE, CS53L30_PDN_DONE); 724 regmap_update_bits(priv->regmap, CS53L30_MCLKCTL, 725 CS53L30_MCLK_DIS_MASK, 726 CS53L30_MCLK_DIS); 727 clk_disable_unprepare(priv->mclk); 728 break; 729 } 730 731 return 0; 732} 733 734static int cs53l30_set_tristate(struct snd_soc_dai *dai, int tristate) 735{ 736 struct cs53l30_private *priv = snd_soc_component_get_drvdata(dai->component); 737 u8 val = tristate ? CS53L30_ASP_3ST : 0; 738 739 return regmap_update_bits(priv->regmap, CS53L30_ASP_CTL1, 740 CS53L30_ASP_3ST_MASK, val); 741} 742 743static unsigned int const cs53l30_src_rates[] = { 744 8000, 11025, 12000, 16000, 22050, 24000, 32000, 44100, 48000 745}; 746 747static const struct snd_pcm_hw_constraint_list src_constraints = { 748 .count = ARRAY_SIZE(cs53l30_src_rates), 749 .list = cs53l30_src_rates, 750}; 751 752static int cs53l30_pcm_startup(struct snd_pcm_substream *substream, 753 struct snd_soc_dai *dai) 754{ 755 snd_pcm_hw_constraint_list(substream->runtime, 0, 756 SNDRV_PCM_HW_PARAM_RATE, &src_constraints); 757 758 return 0; 759} 760 761/* 762 * Note: CS53L30 counts the slot number per byte while ASoC counts the slot 763 * number per slot_width. So there is a difference between the slots of ASoC 764 * and the slots of CS53L30. 765 */ 766static int cs53l30_set_dai_tdm_slot(struct snd_soc_dai *dai, 767 unsigned int tx_mask, unsigned int rx_mask, 768 int slots, int slot_width) 769{ 770 struct cs53l30_private *priv = snd_soc_component_get_drvdata(dai->component); 771 unsigned int loc[CS53L30_TDM_SLOT_MAX] = {48, 48, 48, 48}; 772 unsigned int slot_next, slot_step; 773 u64 tx_enable = 0; 774 int i; 775 776 if (!rx_mask) { 777 dev_err(dai->dev, "rx masks must not be 0\n"); 778 return -EINVAL; 779 } 780 781 /* Assuming slot_width is not supposed to be greater than 64 */ 782 if (slots <= 0 || slot_width <= 0 || slot_width > 64) { 783 dev_err(dai->dev, "invalid slot number or slot width\n"); 784 return -EINVAL; 785 } 786 787 if (slot_width & 0x7) { 788 dev_err(dai->dev, "slot width must count in byte\n"); 789 return -EINVAL; 790 } 791 792 /* How many bytes in each ASoC slot */ 793 slot_step = slot_width >> 3; 794 795 for (i = 0; rx_mask && i < CS53L30_TDM_SLOT_MAX; i++) { 796 /* Find the first slot from LSB */ 797 slot_next = __ffs(rx_mask); 798 /* Save the slot location by converting to CS53L30 slot */ 799 loc[i] = slot_next * slot_step; 800 /* Create the mask of CS53L30 slot */ 801 tx_enable |= (u64)((u64)(1 << slot_step) - 1) << (u64)loc[i]; 802 /* Clear this slot from rx_mask */ 803 rx_mask &= ~(1 << slot_next); 804 } 805 806 /* Error out to avoid slot shift */ 807 if (rx_mask && i == CS53L30_TDM_SLOT_MAX) { 808 dev_err(dai->dev, "rx_mask exceeds max slot number: %d\n", 809 CS53L30_TDM_SLOT_MAX); 810 return -EINVAL; 811 } 812 813 /* Validate the last active CS53L30 slot */ 814 slot_next = loc[i - 1] + slot_step - 1; 815 if (slot_next > 47) { 816 dev_err(dai->dev, "slot selection out of bounds: %u\n", 817 slot_next); 818 return -EINVAL; 819 } 820 821 for (i = 0; i < CS53L30_TDM_SLOT_MAX && loc[i] != 48; i++) { 822 regmap_update_bits(priv->regmap, CS53L30_ASP_TDMTX_CTL(i), 823 CS53L30_ASP_CHx_TX_LOC_MASK, loc[i]); 824 dev_dbg(dai->dev, "loc[%d]=%x\n", i, loc[i]); 825 } 826 827 for (i = 0; i < CS53L30_ASP_TDMTX_ENx_MAX && tx_enable; i++) { 828 regmap_write(priv->regmap, CS53L30_ASP_TDMTX_ENx(i), 829 tx_enable & 0xff); 830 tx_enable >>= 8; 831 dev_dbg(dai->dev, "en_reg=%x, tx_enable=%llx\n", 832 CS53L30_ASP_TDMTX_ENx(i), tx_enable & 0xff); 833 } 834 835 return 0; 836} 837 838static int cs53l30_mute_stream(struct snd_soc_dai *dai, int mute, int stream) 839{ 840 struct cs53l30_private *priv = snd_soc_component_get_drvdata(dai->component); 841 842 gpiod_set_value_cansleep(priv->mute_gpio, mute); 843 844 return 0; 845} 846 847/* SNDRV_PCM_RATE_KNOT -> 12000, 24000 Hz, limit with constraint list */ 848#define CS53L30_RATES (SNDRV_PCM_RATE_8000_48000 | SNDRV_PCM_RATE_KNOT) 849 850#define CS53L30_FORMATS (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S20_3LE |\ 851 SNDRV_PCM_FMTBIT_S24_LE) 852 853static const struct snd_soc_dai_ops cs53l30_ops = { 854 .startup = cs53l30_pcm_startup, 855 .hw_params = cs53l30_pcm_hw_params, 856 .set_fmt = cs53l30_set_dai_fmt, 857 .set_sysclk = cs53l30_set_sysclk, 858 .set_tristate = cs53l30_set_tristate, 859 .set_tdm_slot = cs53l30_set_dai_tdm_slot, 860 .mute_stream = cs53l30_mute_stream, 861}; 862 863static struct snd_soc_dai_driver cs53l30_dai = { 864 .name = "cs53l30", 865 .capture = { 866 .stream_name = "Capture", 867 .channels_min = 1, 868 .channels_max = 4, 869 .rates = CS53L30_RATES, 870 .formats = CS53L30_FORMATS, 871 }, 872 .ops = &cs53l30_ops, 873 .symmetric_rate = 1, 874}; 875 876static int cs53l30_component_probe(struct snd_soc_component *component) 877{ 878 struct cs53l30_private *priv = snd_soc_component_get_drvdata(component); 879 struct snd_soc_dapm_context *dapm = snd_soc_component_get_dapm(component); 880 881 if (priv->use_sdout2) 882 snd_soc_dapm_add_routes(dapm, cs53l30_dapm_routes_sdout2, 883 ARRAY_SIZE(cs53l30_dapm_routes_sdout2)); 884 else 885 snd_soc_dapm_add_routes(dapm, cs53l30_dapm_routes_sdout1, 886 ARRAY_SIZE(cs53l30_dapm_routes_sdout1)); 887 888 return 0; 889} 890 891static const struct snd_soc_component_driver cs53l30_driver = { 892 .probe = cs53l30_component_probe, 893 .set_bias_level = cs53l30_set_bias_level, 894 .controls = cs53l30_snd_controls, 895 .num_controls = ARRAY_SIZE(cs53l30_snd_controls), 896 .dapm_widgets = cs53l30_dapm_widgets, 897 .num_dapm_widgets = ARRAY_SIZE(cs53l30_dapm_widgets), 898 .dapm_routes = cs53l30_dapm_routes, 899 .num_dapm_routes = ARRAY_SIZE(cs53l30_dapm_routes), 900 .use_pmdown_time = 1, 901 .endianness = 1, 902 .non_legacy_dai_naming = 1, 903}; 904 905static struct regmap_config cs53l30_regmap = { 906 .reg_bits = 8, 907 .val_bits = 8, 908 909 .max_register = CS53L30_MAX_REGISTER, 910 .reg_defaults = cs53l30_reg_defaults, 911 .num_reg_defaults = ARRAY_SIZE(cs53l30_reg_defaults), 912 .volatile_reg = cs53l30_volatile_register, 913 .writeable_reg = cs53l30_writeable_register, 914 .readable_reg = cs53l30_readable_register, 915 .cache_type = REGCACHE_RBTREE, 916 917 .use_single_read = true, 918 .use_single_write = true, 919}; 920 921static int cs53l30_i2c_probe(struct i2c_client *client) 922{ 923 const struct device_node *np = client->dev.of_node; 924 struct device *dev = &client->dev; 925 struct cs53l30_private *cs53l30; 926 unsigned int reg; 927 int ret = 0, i, devid; 928 u8 val; 929 930 cs53l30 = devm_kzalloc(dev, sizeof(*cs53l30), GFP_KERNEL); 931 if (!cs53l30) 932 return -ENOMEM; 933 934 for (i = 0; i < ARRAY_SIZE(cs53l30->supplies); i++) 935 cs53l30->supplies[i].supply = cs53l30_supply_names[i]; 936 937 ret = devm_regulator_bulk_get(dev, ARRAY_SIZE(cs53l30->supplies), 938 cs53l30->supplies); 939 if (ret) { 940 dev_err(dev, "failed to get supplies: %d\n", ret); 941 return ret; 942 } 943 944 ret = regulator_bulk_enable(ARRAY_SIZE(cs53l30->supplies), 945 cs53l30->supplies); 946 if (ret) { 947 dev_err(dev, "failed to enable supplies: %d\n", ret); 948 return ret; 949 } 950 951 /* Reset the Device */ 952 cs53l30->reset_gpio = devm_gpiod_get_optional(dev, "reset", 953 GPIOD_OUT_LOW); 954 if (IS_ERR(cs53l30->reset_gpio)) { 955 ret = PTR_ERR(cs53l30->reset_gpio); 956 goto error_supplies; 957 } 958 959 gpiod_set_value_cansleep(cs53l30->reset_gpio, 1); 960 961 i2c_set_clientdata(client, cs53l30); 962 963 cs53l30->mclk_rate = 0; 964 965 cs53l30->regmap = devm_regmap_init_i2c(client, &cs53l30_regmap); 966 if (IS_ERR(cs53l30->regmap)) { 967 ret = PTR_ERR(cs53l30->regmap); 968 dev_err(dev, "regmap_init() failed: %d\n", ret); 969 goto error; 970 } 971 972 /* Initialize codec */ 973 devid = cirrus_read_device_id(cs53l30->regmap, CS53L30_DEVID_AB); 974 if (devid < 0) { 975 ret = devid; 976 dev_err(dev, "Failed to read device ID: %d\n", ret); 977 goto error; 978 } 979 980 if (devid != CS53L30_DEVID) { 981 ret = -ENODEV; 982 dev_err(dev, "Device ID (%X). Expected %X\n", 983 devid, CS53L30_DEVID); 984 goto error; 985 } 986 987 ret = regmap_read(cs53l30->regmap, CS53L30_REVID, ®); 988 if (ret < 0) { 989 dev_err(dev, "failed to get Revision ID: %d\n", ret); 990 goto error; 991 } 992 993 /* Check if MCLK provided */ 994 cs53l30->mclk = devm_clk_get(dev, "mclk"); 995 if (IS_ERR(cs53l30->mclk)) { 996 if (PTR_ERR(cs53l30->mclk) != -ENOENT) { 997 ret = PTR_ERR(cs53l30->mclk); 998 goto error; 999 } 1000 /* Otherwise mark the mclk pointer to NULL */ 1001 cs53l30->mclk = NULL; 1002 } 1003 1004 /* Fetch the MUTE control */ 1005 cs53l30->mute_gpio = devm_gpiod_get_optional(dev, "mute", 1006 GPIOD_OUT_HIGH); 1007 if (IS_ERR(cs53l30->mute_gpio)) { 1008 ret = PTR_ERR(cs53l30->mute_gpio); 1009 goto error; 1010 } 1011 1012 if (cs53l30->mute_gpio) { 1013 /* Enable MUTE controls via MUTE pin */ 1014 regmap_write(cs53l30->regmap, CS53L30_MUTEP_CTL1, 1015 CS53L30_MUTEP_CTL1_MUTEALL); 1016 /* Flip the polarity of MUTE pin */ 1017 if (gpiod_is_active_low(cs53l30->mute_gpio)) 1018 regmap_update_bits(cs53l30->regmap, CS53L30_MUTEP_CTL2, 1019 CS53L30_MUTE_PIN_POLARITY, 0); 1020 } 1021 1022 if (!of_property_read_u8(np, "cirrus,micbias-lvl", &val)) 1023 regmap_update_bits(cs53l30->regmap, CS53L30_MICBIAS_CTL, 1024 CS53L30_MIC_BIAS_CTRL_MASK, val); 1025 1026 if (of_property_read_bool(np, "cirrus,use-sdout2")) 1027 cs53l30->use_sdout2 = true; 1028 1029 dev_info(dev, "Cirrus Logic CS53L30, Revision: %02X\n", reg & 0xFF); 1030 1031 ret = devm_snd_soc_register_component(dev, &cs53l30_driver, &cs53l30_dai, 1); 1032 if (ret) { 1033 dev_err(dev, "failed to register component: %d\n", ret); 1034 goto error; 1035 } 1036 1037 return 0; 1038 1039error: 1040 gpiod_set_value_cansleep(cs53l30->reset_gpio, 0); 1041error_supplies: 1042 regulator_bulk_disable(ARRAY_SIZE(cs53l30->supplies), 1043 cs53l30->supplies); 1044 return ret; 1045} 1046 1047static int cs53l30_i2c_remove(struct i2c_client *client) 1048{ 1049 struct cs53l30_private *cs53l30 = i2c_get_clientdata(client); 1050 1051 /* Hold down reset */ 1052 gpiod_set_value_cansleep(cs53l30->reset_gpio, 0); 1053 1054 regulator_bulk_disable(ARRAY_SIZE(cs53l30->supplies), 1055 cs53l30->supplies); 1056 1057 return 0; 1058} 1059 1060#ifdef CONFIG_PM 1061static int cs53l30_runtime_suspend(struct device *dev) 1062{ 1063 struct cs53l30_private *cs53l30 = dev_get_drvdata(dev); 1064 1065 regcache_cache_only(cs53l30->regmap, true); 1066 1067 /* Hold down reset */ 1068 gpiod_set_value_cansleep(cs53l30->reset_gpio, 0); 1069 1070 regulator_bulk_disable(ARRAY_SIZE(cs53l30->supplies), 1071 cs53l30->supplies); 1072 1073 return 0; 1074} 1075 1076static int cs53l30_runtime_resume(struct device *dev) 1077{ 1078 struct cs53l30_private *cs53l30 = dev_get_drvdata(dev); 1079 int ret; 1080 1081 ret = regulator_bulk_enable(ARRAY_SIZE(cs53l30->supplies), 1082 cs53l30->supplies); 1083 if (ret) { 1084 dev_err(dev, "failed to enable supplies: %d\n", ret); 1085 return ret; 1086 } 1087 1088 gpiod_set_value_cansleep(cs53l30->reset_gpio, 1); 1089 1090 regcache_cache_only(cs53l30->regmap, false); 1091 ret = regcache_sync(cs53l30->regmap); 1092 if (ret) { 1093 dev_err(dev, "failed to synchronize regcache: %d\n", ret); 1094 return ret; 1095 } 1096 1097 return 0; 1098} 1099#endif 1100 1101static const struct dev_pm_ops cs53l30_runtime_pm = { 1102 SET_RUNTIME_PM_OPS(cs53l30_runtime_suspend, cs53l30_runtime_resume, 1103 NULL) 1104}; 1105 1106static const struct of_device_id cs53l30_of_match[] = { 1107 { .compatible = "cirrus,cs53l30", }, 1108 {}, 1109}; 1110 1111MODULE_DEVICE_TABLE(of, cs53l30_of_match); 1112 1113static const struct i2c_device_id cs53l30_id[] = { 1114 { "cs53l30", 0 }, 1115 {} 1116}; 1117 1118MODULE_DEVICE_TABLE(i2c, cs53l30_id); 1119 1120static struct i2c_driver cs53l30_i2c_driver = { 1121 .driver = { 1122 .name = "cs53l30", 1123 .of_match_table = cs53l30_of_match, 1124 .pm = &cs53l30_runtime_pm, 1125 }, 1126 .id_table = cs53l30_id, 1127 .probe_new = cs53l30_i2c_probe, 1128 .remove = cs53l30_i2c_remove, 1129}; 1130 1131module_i2c_driver(cs53l30_i2c_driver); 1132 1133MODULE_DESCRIPTION("ASoC CS53L30 driver"); 1134MODULE_AUTHOR("Paul Handrigan, Cirrus Logic Inc, <Paul.Handrigan@cirrus.com>"); 1135MODULE_LICENSE("GPL");