1 /* 2 * tas5720.c - ALSA SoC Texas Instruments TAS5720 Mono Audio Amplifier 3 * 4 * Copyright (C)2015-2016 Texas Instruments Incorporated - http://www.ti.com 5 * 6 * Author: Andreas Dannenberg <dannenberg@ti.com> 7 * 8 * This program is free software; you can redistribute it and/or 9 * modify it under the terms of the GNU General Public License 10 * version 2 as published by the Free Software Foundation. 11 * 12 * This program is distributed in the hope that it will be useful, but 13 * WITHOUT ANY WARRANTY; without even the implied warranty of 14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 15 * General Public License for more details. 16 */ 17 18 #include <linux/module.h> 19 #include <linux/errno.h> 20 #include <linux/device.h> 21 #include <linux/i2c.h> 22 #include <linux/pm_runtime.h> 23 #include <linux/regmap.h> 24 #include <linux/slab.h> 25 #include <linux/regulator/consumer.h> 26 #include <linux/delay.h> 27 28 #include <sound/pcm.h> 29 #include <sound/pcm_params.h> 30 #include <sound/soc.h> 31 #include <sound/soc-dapm.h> 32 #include <sound/tlv.h> 33 34 #include "tas5720.h" 35 36 /* Define how often to check (and clear) the fault status register (in ms) */ 37 #define TAS5720_FAULT_CHECK_INTERVAL 200 38 39 enum tas572x_type { 40 TAS5720, 41 TAS5722, 42 }; 43 44 static const char * const tas5720_supply_names[] = { 45 "dvdd", /* Digital power supply. Connect to 3.3-V supply. */ 46 "pvdd", /* Class-D amp and analog power supply (connected). */ 47 }; 48 49 #define TAS5720_NUM_SUPPLIES ARRAY_SIZE(tas5720_supply_names) 50 51 struct tas5720_data { 52 struct snd_soc_component *component; 53 struct regmap *regmap; 54 struct i2c_client *tas5720_client; 55 enum tas572x_type devtype; 56 struct regulator_bulk_data supplies[TAS5720_NUM_SUPPLIES]; 57 struct delayed_work fault_check_work; 58 unsigned int last_fault; 59 }; 60 61 static int tas5720_hw_params(struct snd_pcm_substream *substream, 62 struct snd_pcm_hw_params *params, 63 struct snd_soc_dai *dai) 64 { 65 struct snd_soc_component *component = dai->component; 66 unsigned int rate = params_rate(params); 67 bool ssz_ds; 68 int ret; 69 70 switch (rate) { 71 case 44100: 72 case 48000: 73 ssz_ds = false; 74 break; 75 case 88200: 76 case 96000: 77 ssz_ds = true; 78 break; 79 default: 80 dev_err(component->dev, "unsupported sample rate: %u\n", rate); 81 return -EINVAL; 82 } 83 84 ret = snd_soc_component_update_bits(component, TAS5720_DIGITAL_CTRL1_REG, 85 TAS5720_SSZ_DS, ssz_ds); 86 if (ret < 0) { 87 dev_err(component->dev, "error setting sample rate: %d\n", ret); 88 return ret; 89 } 90 91 return 0; 92 } 93 94 static int tas5720_set_dai_fmt(struct snd_soc_dai *dai, unsigned int fmt) 95 { 96 struct snd_soc_component *component = dai->component; 97 u8 serial_format; 98 int ret; 99 100 if ((fmt & SND_SOC_DAIFMT_MASTER_MASK) != SND_SOC_DAIFMT_CBS_CFS) { 101 dev_vdbg(component->dev, "DAI Format master is not found\n"); 102 return -EINVAL; 103 } 104 105 switch (fmt & (SND_SOC_DAIFMT_FORMAT_MASK | 106 SND_SOC_DAIFMT_INV_MASK)) { 107 case (SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF): 108 /* 1st data bit occur one BCLK cycle after the frame sync */ 109 serial_format = TAS5720_SAIF_I2S; 110 break; 111 case (SND_SOC_DAIFMT_DSP_A | SND_SOC_DAIFMT_NB_NF): 112 /* 113 * Note that although the TAS5720 does not have a dedicated DSP 114 * mode it doesn't care about the LRCLK duty cycle during TDM 115 * operation. Therefore we can use the device's I2S mode with 116 * its delaying of the 1st data bit to receive DSP_A formatted 117 * data. See device datasheet for additional details. 118 */ 119 serial_format = TAS5720_SAIF_I2S; 120 break; 121 case (SND_SOC_DAIFMT_DSP_B | SND_SOC_DAIFMT_NB_NF): 122 /* 123 * Similar to DSP_A, we can use the fact that the TAS5720 does 124 * not care about the LRCLK duty cycle during TDM to receive 125 * DSP_B formatted data in LEFTJ mode (no delaying of the 1st 126 * data bit). 127 */ 128 serial_format = TAS5720_SAIF_LEFTJ; 129 break; 130 case (SND_SOC_DAIFMT_LEFT_J | SND_SOC_DAIFMT_NB_NF): 131 /* No delay after the frame sync */ 132 serial_format = TAS5720_SAIF_LEFTJ; 133 break; 134 default: 135 dev_vdbg(component->dev, "DAI Format is not found\n"); 136 return -EINVAL; 137 } 138 139 ret = snd_soc_component_update_bits(component, TAS5720_DIGITAL_CTRL1_REG, 140 TAS5720_SAIF_FORMAT_MASK, 141 serial_format); 142 if (ret < 0) { 143 dev_err(component->dev, "error setting SAIF format: %d\n", ret); 144 return ret; 145 } 146 147 return 0; 148 } 149 150 static int tas5720_set_dai_tdm_slot(struct snd_soc_dai *dai, 151 unsigned int tx_mask, unsigned int rx_mask, 152 int slots, int slot_width) 153 { 154 struct snd_soc_component *component = dai->component; 155 struct tas5720_data *tas5720 = snd_soc_component_get_drvdata(component); 156 unsigned int first_slot; 157 int ret; 158 159 if (!tx_mask) { 160 dev_err(component->dev, "tx masks must not be 0\n"); 161 return -EINVAL; 162 } 163 164 /* 165 * Determine the first slot that is being requested. We will only 166 * use the first slot that is found since the TAS5720 is a mono 167 * amplifier. 168 */ 169 first_slot = __ffs(tx_mask); 170 171 if (first_slot > 7) { 172 dev_err(component->dev, "slot selection out of bounds (%u)\n", 173 first_slot); 174 return -EINVAL; 175 } 176 177 /* Enable manual TDM slot selection (instead of I2C ID based) */ 178 ret = snd_soc_component_update_bits(component, TAS5720_DIGITAL_CTRL1_REG, 179 TAS5720_TDM_CFG_SRC, TAS5720_TDM_CFG_SRC); 180 if (ret < 0) 181 goto error_snd_soc_component_update_bits; 182 183 /* Configure the TDM slot to process audio from */ 184 ret = snd_soc_component_update_bits(component, TAS5720_DIGITAL_CTRL2_REG, 185 TAS5720_TDM_SLOT_SEL_MASK, first_slot); 186 if (ret < 0) 187 goto error_snd_soc_component_update_bits; 188 189 /* Configure TDM slot width. This is only applicable to TAS5722. */ 190 switch (tas5720->devtype) { 191 case TAS5722: 192 ret = snd_soc_component_update_bits(component, TAS5722_DIGITAL_CTRL2_REG, 193 TAS5722_TDM_SLOT_16B, 194 slot_width == 16 ? 195 TAS5722_TDM_SLOT_16B : 0); 196 if (ret < 0) 197 goto error_snd_soc_component_update_bits; 198 break; 199 default: 200 break; 201 } 202 203 return 0; 204 205 error_snd_soc_component_update_bits: 206 dev_err(component->dev, "error configuring TDM mode: %d\n", ret); 207 return ret; 208 } 209 210 static int tas5720_mute(struct snd_soc_dai *dai, int mute) 211 { 212 struct snd_soc_component *component = dai->component; 213 int ret; 214 215 ret = snd_soc_component_update_bits(component, TAS5720_DIGITAL_CTRL2_REG, 216 TAS5720_MUTE, mute ? TAS5720_MUTE : 0); 217 if (ret < 0) { 218 dev_err(component->dev, "error (un-)muting device: %d\n", ret); 219 return ret; 220 } 221 222 return 0; 223 } 224 225 static void tas5720_fault_check_work(struct work_struct *work) 226 { 227 struct tas5720_data *tas5720 = container_of(work, struct tas5720_data, 228 fault_check_work.work); 229 struct device *dev = tas5720->component->dev; 230 unsigned int curr_fault; 231 int ret; 232 233 ret = regmap_read(tas5720->regmap, TAS5720_FAULT_REG, &curr_fault); 234 if (ret < 0) { 235 dev_err(dev, "failed to read FAULT register: %d\n", ret); 236 goto out; 237 } 238 239 /* Check/handle all errors except SAIF clock errors */ 240 curr_fault &= TAS5720_OCE | TAS5720_DCE | TAS5720_OTE; 241 242 /* 243 * Only flag errors once for a given occurrence. This is needed as 244 * the TAS5720 will take time clearing the fault condition internally 245 * during which we don't want to bombard the system with the same 246 * error message over and over. 247 */ 248 if ((curr_fault & TAS5720_OCE) && !(tas5720->last_fault & TAS5720_OCE)) 249 dev_crit(dev, "experienced an over current hardware fault\n"); 250 251 if ((curr_fault & TAS5720_DCE) && !(tas5720->last_fault & TAS5720_DCE)) 252 dev_crit(dev, "experienced a DC detection fault\n"); 253 254 if ((curr_fault & TAS5720_OTE) && !(tas5720->last_fault & TAS5720_OTE)) 255 dev_crit(dev, "experienced an over temperature fault\n"); 256 257 /* Store current fault value so we can detect any changes next time */ 258 tas5720->last_fault = curr_fault; 259 260 if (!curr_fault) 261 goto out; 262 263 /* 264 * Periodically toggle SDZ (shutdown bit) H->L->H to clear any latching 265 * faults as long as a fault condition persists. Always going through 266 * the full sequence no matter the first return value to minimizes 267 * chances for the device to end up in shutdown mode. 268 */ 269 ret = regmap_write_bits(tas5720->regmap, TAS5720_POWER_CTRL_REG, 270 TAS5720_SDZ, 0); 271 if (ret < 0) 272 dev_err(dev, "failed to write POWER_CTRL register: %d\n", ret); 273 274 ret = regmap_write_bits(tas5720->regmap, TAS5720_POWER_CTRL_REG, 275 TAS5720_SDZ, TAS5720_SDZ); 276 if (ret < 0) 277 dev_err(dev, "failed to write POWER_CTRL register: %d\n", ret); 278 279 out: 280 /* Schedule the next fault check at the specified interval */ 281 schedule_delayed_work(&tas5720->fault_check_work, 282 msecs_to_jiffies(TAS5720_FAULT_CHECK_INTERVAL)); 283 } 284 285 static int tas5720_codec_probe(struct snd_soc_component *component) 286 { 287 struct tas5720_data *tas5720 = snd_soc_component_get_drvdata(component); 288 unsigned int device_id, expected_device_id; 289 int ret; 290 291 tas5720->component = component; 292 293 ret = regulator_bulk_enable(ARRAY_SIZE(tas5720->supplies), 294 tas5720->supplies); 295 if (ret != 0) { 296 dev_err(component->dev, "failed to enable supplies: %d\n", ret); 297 return ret; 298 } 299 300 /* 301 * Take a liberal approach to checking the device ID to allow the 302 * driver to be used even if the device ID does not match, however 303 * issue a warning if there is a mismatch. 304 */ 305 ret = regmap_read(tas5720->regmap, TAS5720_DEVICE_ID_REG, &device_id); 306 if (ret < 0) { 307 dev_err(component->dev, "failed to read device ID register: %d\n", 308 ret); 309 goto probe_fail; 310 } 311 312 switch (tas5720->devtype) { 313 case TAS5720: 314 expected_device_id = TAS5720_DEVICE_ID; 315 break; 316 case TAS5722: 317 expected_device_id = TAS5722_DEVICE_ID; 318 break; 319 default: 320 dev_err(component->dev, "unexpected private driver data\n"); 321 return -EINVAL; 322 } 323 324 if (device_id != expected_device_id) 325 dev_warn(component->dev, "wrong device ID. expected: %u read: %u\n", 326 expected_device_id, device_id); 327 328 /* Set device to mute */ 329 ret = snd_soc_component_update_bits(component, TAS5720_DIGITAL_CTRL2_REG, 330 TAS5720_MUTE, TAS5720_MUTE); 331 if (ret < 0) 332 goto error_snd_soc_component_update_bits; 333 334 /* 335 * Enter shutdown mode - our default when not playing audio - to 336 * minimize current consumption. On the TAS5720 there is no real down 337 * side doing so as all device registers are preserved and the wakeup 338 * of the codec is rather quick which we do using a dapm widget. 339 */ 340 ret = snd_soc_component_update_bits(component, TAS5720_POWER_CTRL_REG, 341 TAS5720_SDZ, 0); 342 if (ret < 0) 343 goto error_snd_soc_component_update_bits; 344 345 INIT_DELAYED_WORK(&tas5720->fault_check_work, tas5720_fault_check_work); 346 347 return 0; 348 349 error_snd_soc_component_update_bits: 350 dev_err(component->dev, "error configuring device registers: %d\n", ret); 351 352 probe_fail: 353 regulator_bulk_disable(ARRAY_SIZE(tas5720->supplies), 354 tas5720->supplies); 355 return ret; 356 } 357 358 static void tas5720_codec_remove(struct snd_soc_component *component) 359 { 360 struct tas5720_data *tas5720 = snd_soc_component_get_drvdata(component); 361 int ret; 362 363 cancel_delayed_work_sync(&tas5720->fault_check_work); 364 365 ret = regulator_bulk_disable(ARRAY_SIZE(tas5720->supplies), 366 tas5720->supplies); 367 if (ret < 0) 368 dev_err(component->dev, "failed to disable supplies: %d\n", ret); 369 }; 370 371 static int tas5720_dac_event(struct snd_soc_dapm_widget *w, 372 struct snd_kcontrol *kcontrol, int event) 373 { 374 struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm); 375 struct tas5720_data *tas5720 = snd_soc_component_get_drvdata(component); 376 int ret; 377 378 if (event & SND_SOC_DAPM_POST_PMU) { 379 /* Take TAS5720 out of shutdown mode */ 380 ret = snd_soc_component_update_bits(component, TAS5720_POWER_CTRL_REG, 381 TAS5720_SDZ, TAS5720_SDZ); 382 if (ret < 0) { 383 dev_err(component->dev, "error waking component: %d\n", ret); 384 return ret; 385 } 386 387 /* 388 * Observe codec shutdown-to-active time. The datasheet only 389 * lists a nominal value however just use-it as-is without 390 * additional padding to minimize the delay introduced in 391 * starting to play audio (actually there is other setup done 392 * by the ASoC framework that will provide additional delays, 393 * so we should always be safe). 394 */ 395 msleep(25); 396 397 /* Turn on TAS5720 periodic fault checking/handling */ 398 tas5720->last_fault = 0; 399 schedule_delayed_work(&tas5720->fault_check_work, 400 msecs_to_jiffies(TAS5720_FAULT_CHECK_INTERVAL)); 401 } else if (event & SND_SOC_DAPM_PRE_PMD) { 402 /* Disable TAS5720 periodic fault checking/handling */ 403 cancel_delayed_work_sync(&tas5720->fault_check_work); 404 405 /* Place TAS5720 in shutdown mode to minimize current draw */ 406 ret = snd_soc_component_update_bits(component, TAS5720_POWER_CTRL_REG, 407 TAS5720_SDZ, 0); 408 if (ret < 0) { 409 dev_err(component->dev, "error shutting down component: %d\n", 410 ret); 411 return ret; 412 } 413 } 414 415 return 0; 416 } 417 418 #ifdef CONFIG_PM 419 static int tas5720_suspend(struct snd_soc_component *component) 420 { 421 struct tas5720_data *tas5720 = snd_soc_component_get_drvdata(component); 422 int ret; 423 424 regcache_cache_only(tas5720->regmap, true); 425 regcache_mark_dirty(tas5720->regmap); 426 427 ret = regulator_bulk_disable(ARRAY_SIZE(tas5720->supplies), 428 tas5720->supplies); 429 if (ret < 0) 430 dev_err(component->dev, "failed to disable supplies: %d\n", ret); 431 432 return ret; 433 } 434 435 static int tas5720_resume(struct snd_soc_component *component) 436 { 437 struct tas5720_data *tas5720 = snd_soc_component_get_drvdata(component); 438 int ret; 439 440 ret = regulator_bulk_enable(ARRAY_SIZE(tas5720->supplies), 441 tas5720->supplies); 442 if (ret < 0) { 443 dev_err(component->dev, "failed to enable supplies: %d\n", ret); 444 return ret; 445 } 446 447 regcache_cache_only(tas5720->regmap, false); 448 449 ret = regcache_sync(tas5720->regmap); 450 if (ret < 0) { 451 dev_err(component->dev, "failed to sync regcache: %d\n", ret); 452 return ret; 453 } 454 455 return 0; 456 } 457 #else 458 #define tas5720_suspend NULL 459 #define tas5720_resume NULL 460 #endif 461 462 static bool tas5720_is_volatile_reg(struct device *dev, unsigned int reg) 463 { 464 switch (reg) { 465 case TAS5720_DEVICE_ID_REG: 466 case TAS5720_FAULT_REG: 467 return true; 468 default: 469 return false; 470 } 471 } 472 473 static const struct regmap_config tas5720_regmap_config = { 474 .reg_bits = 8, 475 .val_bits = 8, 476 477 .max_register = TAS5720_MAX_REG, 478 .cache_type = REGCACHE_RBTREE, 479 .volatile_reg = tas5720_is_volatile_reg, 480 }; 481 482 static const struct regmap_config tas5722_regmap_config = { 483 .reg_bits = 8, 484 .val_bits = 8, 485 486 .max_register = TAS5722_MAX_REG, 487 .cache_type = REGCACHE_RBTREE, 488 .volatile_reg = tas5720_is_volatile_reg, 489 }; 490 491 /* 492 * DAC analog gain. There are four discrete values to select from, ranging 493 * from 19.2 dB to 26.3dB. 494 */ 495 static const DECLARE_TLV_DB_RANGE(dac_analog_tlv, 496 0x0, 0x0, TLV_DB_SCALE_ITEM(1920, 0, 0), 497 0x1, 0x1, TLV_DB_SCALE_ITEM(2070, 0, 0), 498 0x2, 0x2, TLV_DB_SCALE_ITEM(2350, 0, 0), 499 0x3, 0x3, TLV_DB_SCALE_ITEM(2630, 0, 0), 500 ); 501 502 /* 503 * DAC digital volumes. From -103.5 to 24 dB in 0.5 dB or 0.25 dB steps 504 * depending on the device. Note that setting the gain below -100 dB 505 * (register value <0x7) is effectively a MUTE as per device datasheet. 506 * 507 * Note that for the TAS5722 the digital volume controls are actually split 508 * over two registers, so we need custom getters/setters for access. 509 */ 510 static DECLARE_TLV_DB_SCALE(tas5720_dac_tlv, -10350, 50, 0); 511 static DECLARE_TLV_DB_SCALE(tas5722_dac_tlv, -10350, 25, 0); 512 513 static int tas5722_volume_get(struct snd_kcontrol *kcontrol, 514 struct snd_ctl_elem_value *ucontrol) 515 { 516 struct snd_soc_component *component = snd_soc_kcontrol_component(kcontrol); 517 unsigned int val; 518 519 snd_soc_component_read(component, TAS5720_VOLUME_CTRL_REG, &val); 520 ucontrol->value.integer.value[0] = val << 1; 521 522 snd_soc_component_read(component, TAS5722_DIGITAL_CTRL2_REG, &val); 523 ucontrol->value.integer.value[0] |= val & TAS5722_VOL_CONTROL_LSB; 524 525 return 0; 526 } 527 528 static int tas5722_volume_set(struct snd_kcontrol *kcontrol, 529 struct snd_ctl_elem_value *ucontrol) 530 { 531 struct snd_soc_component *component = snd_soc_kcontrol_component(kcontrol); 532 unsigned int sel = ucontrol->value.integer.value[0]; 533 534 snd_soc_component_write(component, TAS5720_VOLUME_CTRL_REG, sel >> 1); 535 snd_soc_component_update_bits(component, TAS5722_DIGITAL_CTRL2_REG, 536 TAS5722_VOL_CONTROL_LSB, sel); 537 538 return 0; 539 } 540 541 static const struct snd_kcontrol_new tas5720_snd_controls[] = { 542 SOC_SINGLE_TLV("Speaker Driver Playback Volume", 543 TAS5720_VOLUME_CTRL_REG, 0, 0xff, 0, tas5720_dac_tlv), 544 SOC_SINGLE_TLV("Speaker Driver Analog Gain", TAS5720_ANALOG_CTRL_REG, 545 TAS5720_ANALOG_GAIN_SHIFT, 3, 0, dac_analog_tlv), 546 }; 547 548 static const struct snd_kcontrol_new tas5722_snd_controls[] = { 549 SOC_SINGLE_EXT_TLV("Speaker Driver Playback Volume", 550 0, 0, 511, 0, 551 tas5722_volume_get, tas5722_volume_set, 552 tas5722_dac_tlv), 553 SOC_SINGLE_TLV("Speaker Driver Analog Gain", TAS5720_ANALOG_CTRL_REG, 554 TAS5720_ANALOG_GAIN_SHIFT, 3, 0, dac_analog_tlv), 555 }; 556 557 static const struct snd_soc_dapm_widget tas5720_dapm_widgets[] = { 558 SND_SOC_DAPM_AIF_IN("DAC IN", "Playback", 0, SND_SOC_NOPM, 0, 0), 559 SND_SOC_DAPM_DAC_E("DAC", NULL, SND_SOC_NOPM, 0, 0, tas5720_dac_event, 560 SND_SOC_DAPM_POST_PMU | SND_SOC_DAPM_PRE_PMD), 561 SND_SOC_DAPM_OUTPUT("OUT") 562 }; 563 564 static const struct snd_soc_dapm_route tas5720_audio_map[] = { 565 { "DAC", NULL, "DAC IN" }, 566 { "OUT", NULL, "DAC" }, 567 }; 568 569 static const struct snd_soc_component_driver soc_component_dev_tas5720 = { 570 .probe = tas5720_codec_probe, 571 .remove = tas5720_codec_remove, 572 .suspend = tas5720_suspend, 573 .resume = tas5720_resume, 574 .controls = tas5720_snd_controls, 575 .num_controls = ARRAY_SIZE(tas5720_snd_controls), 576 .dapm_widgets = tas5720_dapm_widgets, 577 .num_dapm_widgets = ARRAY_SIZE(tas5720_dapm_widgets), 578 .dapm_routes = tas5720_audio_map, 579 .num_dapm_routes = ARRAY_SIZE(tas5720_audio_map), 580 .idle_bias_on = 1, 581 .use_pmdown_time = 1, 582 .endianness = 1, 583 .non_legacy_dai_naming = 1, 584 }; 585 586 static const struct snd_soc_component_driver soc_component_dev_tas5722 = { 587 .probe = tas5720_codec_probe, 588 .remove = tas5720_codec_remove, 589 .suspend = tas5720_suspend, 590 .resume = tas5720_resume, 591 .controls = tas5722_snd_controls, 592 .num_controls = ARRAY_SIZE(tas5722_snd_controls), 593 .dapm_widgets = tas5720_dapm_widgets, 594 .num_dapm_widgets = ARRAY_SIZE(tas5720_dapm_widgets), 595 .dapm_routes = tas5720_audio_map, 596 .num_dapm_routes = ARRAY_SIZE(tas5720_audio_map), 597 .idle_bias_on = 1, 598 .use_pmdown_time = 1, 599 .endianness = 1, 600 .non_legacy_dai_naming = 1, 601 }; 602 603 /* PCM rates supported by the TAS5720 driver */ 604 #define TAS5720_RATES (SNDRV_PCM_RATE_44100 | SNDRV_PCM_RATE_48000 |\ 605 SNDRV_PCM_RATE_88200 | SNDRV_PCM_RATE_96000) 606 607 /* Formats supported by TAS5720 driver */ 608 #define TAS5720_FORMATS (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S18_3LE |\ 609 SNDRV_PCM_FMTBIT_S20_3LE | SNDRV_PCM_FMTBIT_S24_LE) 610 611 static const struct snd_soc_dai_ops tas5720_speaker_dai_ops = { 612 .hw_params = tas5720_hw_params, 613 .set_fmt = tas5720_set_dai_fmt, 614 .set_tdm_slot = tas5720_set_dai_tdm_slot, 615 .digital_mute = tas5720_mute, 616 }; 617 618 /* 619 * TAS5720 DAI structure 620 * 621 * Note that were are advertising .playback.channels_max = 2 despite this being 622 * a mono amplifier. The reason for that is that some serial ports such as TI's 623 * McASP module have a minimum number of channels (2) that they can output. 624 * Advertising more channels than we have will allow us to interface with such 625 * a serial port without really any negative side effects as the TAS5720 will 626 * simply ignore any extra channel(s) asides from the one channel that is 627 * configured to be played back. 628 */ 629 static struct snd_soc_dai_driver tas5720_dai[] = { 630 { 631 .name = "tas5720-amplifier", 632 .playback = { 633 .stream_name = "Playback", 634 .channels_min = 1, 635 .channels_max = 2, 636 .rates = TAS5720_RATES, 637 .formats = TAS5720_FORMATS, 638 }, 639 .ops = &tas5720_speaker_dai_ops, 640 }, 641 }; 642 643 static int tas5720_probe(struct i2c_client *client, 644 const struct i2c_device_id *id) 645 { 646 struct device *dev = &client->dev; 647 struct tas5720_data *data; 648 const struct regmap_config *regmap_config; 649 int ret; 650 int i; 651 652 data = devm_kzalloc(dev, sizeof(*data), GFP_KERNEL); 653 if (!data) 654 return -ENOMEM; 655 656 data->tas5720_client = client; 657 data->devtype = id->driver_data; 658 659 switch (id->driver_data) { 660 case TAS5720: 661 regmap_config = &tas5720_regmap_config; 662 break; 663 case TAS5722: 664 regmap_config = &tas5722_regmap_config; 665 break; 666 default: 667 dev_err(dev, "unexpected private driver data\n"); 668 return -EINVAL; 669 } 670 data->regmap = devm_regmap_init_i2c(client, regmap_config); 671 if (IS_ERR(data->regmap)) { 672 ret = PTR_ERR(data->regmap); 673 dev_err(dev, "failed to allocate register map: %d\n", ret); 674 return ret; 675 } 676 677 for (i = 0; i < ARRAY_SIZE(data->supplies); i++) 678 data->supplies[i].supply = tas5720_supply_names[i]; 679 680 ret = devm_regulator_bulk_get(dev, ARRAY_SIZE(data->supplies), 681 data->supplies); 682 if (ret != 0) { 683 dev_err(dev, "failed to request supplies: %d\n", ret); 684 return ret; 685 } 686 687 dev_set_drvdata(dev, data); 688 689 switch (id->driver_data) { 690 case TAS5720: 691 ret = devm_snd_soc_register_component(&client->dev, 692 &soc_component_dev_tas5720, 693 tas5720_dai, 694 ARRAY_SIZE(tas5720_dai)); 695 break; 696 case TAS5722: 697 ret = devm_snd_soc_register_component(&client->dev, 698 &soc_component_dev_tas5722, 699 tas5720_dai, 700 ARRAY_SIZE(tas5720_dai)); 701 break; 702 default: 703 dev_err(dev, "unexpected private driver data\n"); 704 return -EINVAL; 705 } 706 if (ret < 0) { 707 dev_err(dev, "failed to register component: %d\n", ret); 708 return ret; 709 } 710 711 return 0; 712 } 713 714 static const struct i2c_device_id tas5720_id[] = { 715 { "tas5720", TAS5720 }, 716 { "tas5722", TAS5722 }, 717 { } 718 }; 719 MODULE_DEVICE_TABLE(i2c, tas5720_id); 720 721 #if IS_ENABLED(CONFIG_OF) 722 static const struct of_device_id tas5720_of_match[] = { 723 { .compatible = "ti,tas5720", }, 724 { .compatible = "ti,tas5722", }, 725 { }, 726 }; 727 MODULE_DEVICE_TABLE(of, tas5720_of_match); 728 #endif 729 730 static struct i2c_driver tas5720_i2c_driver = { 731 .driver = { 732 .name = "tas5720", 733 .of_match_table = of_match_ptr(tas5720_of_match), 734 }, 735 .probe = tas5720_probe, 736 .id_table = tas5720_id, 737 }; 738 739 module_i2c_driver(tas5720_i2c_driver); 740 741 MODULE_AUTHOR("Andreas Dannenberg <dannenberg@ti.com>"); 742 MODULE_DESCRIPTION("TAS5720 Audio amplifier driver"); 743 MODULE_LICENSE("GPL"); 744