1 // SPDX-License-Identifier: GPL-2.0 2 // 3 // simple-card-utils.c 4 // 5 // Copyright (c) 2016 Kuninori Morimoto <kuninori.morimoto.gx@renesas.com> 6 7 #include <dt-bindings/sound/audio-graph.h> 8 #include <linux/cleanup.h> 9 #include <linux/clk.h> 10 #include <linux/gpio/consumer.h> 11 #include <linux/module.h> 12 #include <linux/of.h> 13 #include <linux/of_graph.h> 14 #include <sound/jack.h> 15 #include <sound/pcm_params.h> 16 #include <sound/simple_card_utils.h> 17 18 #define simple_ret(priv, ret) _simple_ret(priv, __func__, ret) 19 static inline int _simple_ret(struct simple_util_priv *priv, 20 const char *func, int ret) 21 { 22 return snd_soc_ret(simple_priv_to_dev(priv), ret, "at %s()\n", func); 23 } 24 25 int simple_util_get_sample_fmt(struct simple_util_data *data) 26 { 27 int i; 28 int val = -EINVAL; 29 30 struct { 31 char *fmt; 32 u32 val; 33 } of_sample_fmt_table[] = { 34 { "s8", SNDRV_PCM_FORMAT_S8}, 35 { "s16_le", SNDRV_PCM_FORMAT_S16_LE}, 36 { "s24_le", SNDRV_PCM_FORMAT_S24_LE}, 37 { "s24_3le", SNDRV_PCM_FORMAT_S24_3LE}, 38 { "s32_le", SNDRV_PCM_FORMAT_S32_LE}, 39 }; 40 41 for (i = 0; i < ARRAY_SIZE(of_sample_fmt_table); i++) { 42 if (!strcmp(data->convert_sample_format, 43 of_sample_fmt_table[i].fmt)) { 44 val = of_sample_fmt_table[i].val; 45 break; 46 } 47 } 48 return val; 49 } 50 EXPORT_SYMBOL_GPL(simple_util_get_sample_fmt); 51 52 static void simple_fixup_sample_fmt(struct simple_util_data *data, 53 struct snd_pcm_hw_params *params) 54 { 55 int val; 56 struct snd_mask *mask = hw_param_mask(params, 57 SNDRV_PCM_HW_PARAM_FORMAT); 58 59 val = simple_util_get_sample_fmt(data); 60 if (val >= 0) { 61 snd_mask_none(mask); 62 snd_mask_set(mask, val); 63 } 64 } 65 66 void simple_util_parse_convert(struct device_node *np, 67 char *prefix, 68 struct simple_util_data *data) 69 { 70 char prop[128]; 71 72 if (!np) 73 return; 74 75 if (!prefix) 76 prefix = ""; 77 78 /* sampling rate convert */ 79 snprintf(prop, sizeof(prop), "%s%s", prefix, "convert-rate"); 80 of_property_read_u32(np, prop, &data->convert_rate); 81 82 /* channels transfer */ 83 snprintf(prop, sizeof(prop), "%s%s", prefix, "convert-channels"); 84 of_property_read_u32(np, prop, &data->convert_channels); 85 86 /* convert sample format */ 87 snprintf(prop, sizeof(prop), "%s%s", prefix, "convert-sample-format"); 88 of_property_read_string(np, prop, &data->convert_sample_format); 89 } 90 EXPORT_SYMBOL_GPL(simple_util_parse_convert); 91 92 /** 93 * simple_util_is_convert_required() - Query if HW param conversion was requested 94 * @data: Link data. 95 * 96 * Returns true if any HW param conversion was requested for this DAI link with 97 * any "convert-xxx" properties. 98 */ 99 bool simple_util_is_convert_required(const struct simple_util_data *data) 100 { 101 return data->convert_rate || 102 data->convert_channels || 103 data->convert_sample_format; 104 } 105 EXPORT_SYMBOL_GPL(simple_util_is_convert_required); 106 107 int simple_util_parse_daifmt(struct device *dev, 108 struct device_node *node, 109 struct device_node *codec, 110 char *prefix, 111 unsigned int *retfmt) 112 { 113 struct device_node *bitclkmaster = NULL; 114 struct device_node *framemaster = NULL; 115 unsigned int daifmt; 116 117 daifmt = snd_soc_daifmt_parse_format(node, prefix); 118 119 snd_soc_daifmt_parse_clock_provider_as_phandle(node, prefix, &bitclkmaster, &framemaster); 120 if (!bitclkmaster && !framemaster) { 121 /* 122 * No dai-link level and master setting was not found from 123 * sound node level, revert back to legacy DT parsing and 124 * take the settings from codec node. 125 */ 126 dev_dbg(dev, "Revert to legacy daifmt parsing\n"); 127 128 daifmt |= snd_soc_daifmt_parse_clock_provider_as_flag(codec, NULL); 129 } else { 130 daifmt |= snd_soc_daifmt_clock_provider_from_bitmap( 131 ((codec == bitclkmaster) << 4) | (codec == framemaster)); 132 } 133 134 of_node_put(bitclkmaster); 135 of_node_put(framemaster); 136 137 *retfmt = daifmt; 138 139 return 0; 140 } 141 EXPORT_SYMBOL_GPL(simple_util_parse_daifmt); 142 143 int simple_util_parse_tdm_width_map(struct simple_util_priv *priv, struct device_node *np, 144 struct simple_util_dai *dai) 145 { 146 struct device *dev = simple_priv_to_dev(priv); 147 int n, i, ret; 148 u32 *p; 149 150 /* 151 * NOTE 152 * 153 * Clang doesn't allow to use "goto end" before calling __free(), 154 * because it bypasses the initialization. Use simple_ret() directly. 155 */ 156 157 n = of_property_count_elems_of_size(np, "dai-tdm-slot-width-map", sizeof(u32)); 158 if (n <= 0) 159 return 0; 160 161 if (n % 3) { 162 dev_err(dev, "Invalid number of cells for dai-tdm-slot-width-map\n"); 163 return simple_ret(priv, -EINVAL); /* see NOTE */ 164 } 165 166 ret = -ENOMEM; 167 dai->tdm_width_map = devm_kcalloc(dev, n, sizeof(*dai->tdm_width_map), GFP_KERNEL); 168 if (!dai->tdm_width_map) 169 return simple_ret(priv, ret); /* see NOTE */ 170 171 u32 *array_values __free(kfree) = kcalloc(n, sizeof(*array_values), GFP_KERNEL); 172 if (!array_values) 173 goto end; 174 175 ret = of_property_read_u32_array(np, "dai-tdm-slot-width-map", array_values, n); 176 if (ret < 0) { 177 dev_err(dev, "Could not read dai-tdm-slot-width-map: %d\n", ret); 178 goto end; 179 } 180 181 p = array_values; 182 for (i = 0; i < n / 3; ++i) { 183 dai->tdm_width_map[i].sample_bits = *p++; 184 dai->tdm_width_map[i].slot_width = *p++; 185 dai->tdm_width_map[i].slot_count = *p++; 186 } 187 188 dai->n_tdm_widths = i; 189 ret = 0; 190 end: 191 return simple_ret(priv, ret); 192 } 193 EXPORT_SYMBOL_GPL(simple_util_parse_tdm_width_map); 194 195 int simple_util_set_dailink_name(struct simple_util_priv *priv, 196 struct snd_soc_dai_link *dai_link, 197 const char *fmt, ...) 198 { 199 struct device *dev = simple_priv_to_dev(priv); 200 va_list ap; 201 char *name = NULL; 202 int ret = -ENOMEM; 203 204 va_start(ap, fmt); 205 name = devm_kvasprintf(dev, GFP_KERNEL, fmt, ap); 206 va_end(ap); 207 208 if (name) { 209 ret = 0; 210 211 dai_link->name = name; 212 dai_link->stream_name = name; 213 } 214 215 return simple_ret(priv, ret); 216 } 217 EXPORT_SYMBOL_GPL(simple_util_set_dailink_name); 218 219 int simple_util_parse_card_name(struct simple_util_priv *priv, 220 char *prefix) 221 { 222 struct snd_soc_card *card = simple_priv_to_card(priv); 223 int ret; 224 225 if (!prefix) 226 prefix = ""; 227 228 /* Parse the card name from DT */ 229 ret = snd_soc_of_parse_card_name(card, "label"); 230 if (ret < 0 || !card->name) { 231 char prop[128]; 232 233 snprintf(prop, sizeof(prop), "%sname", prefix); 234 ret = snd_soc_of_parse_card_name(card, prop); 235 if (ret < 0) 236 goto end; 237 } 238 239 if (!card->name && card->dai_link) 240 card->name = card->dai_link->name; 241 end: 242 return simple_ret(priv, ret); 243 } 244 EXPORT_SYMBOL_GPL(simple_util_parse_card_name); 245 246 static int simple_clk_enable(struct simple_util_dai *dai) 247 { 248 if (dai) 249 return clk_prepare_enable(dai->clk); 250 251 return 0; 252 } 253 254 static void simple_clk_disable(struct simple_util_dai *dai) 255 { 256 if (dai) 257 clk_disable_unprepare(dai->clk); 258 } 259 260 int simple_util_parse_clk(struct device *dev, 261 struct device_node *node, 262 struct simple_util_dai *simple_dai, 263 struct snd_soc_dai_link_component *dlc) 264 { 265 struct clk *clk; 266 u32 val; 267 268 /* 269 * Parse dai->sysclk come from "clocks = <&xxx>" 270 * (if system has common clock) 271 * or "system-clock-frequency = <xxx>" 272 * or device's module clock. 273 */ 274 clk = devm_get_clk_from_child(dev, node, NULL); 275 simple_dai->clk_fixed = of_property_read_bool( 276 node, "system-clock-fixed"); 277 if (!IS_ERR(clk)) { 278 simple_dai->sysclk = clk_get_rate(clk); 279 280 simple_dai->clk = clk; 281 } else if (!of_property_read_u32(node, "system-clock-frequency", &val)) { 282 simple_dai->sysclk = val; 283 simple_dai->clk_fixed = true; 284 } else { 285 clk = devm_get_clk_from_child(dev, dlc->of_node, NULL); 286 if (!IS_ERR(clk)) 287 simple_dai->sysclk = clk_get_rate(clk); 288 } 289 290 if (of_property_read_bool(node, "system-clock-direction-out")) 291 simple_dai->clk_direction = SND_SOC_CLOCK_OUT; 292 293 return 0; 294 } 295 EXPORT_SYMBOL_GPL(simple_util_parse_clk); 296 297 static int simple_check_fixed_sysclk(struct device *dev, 298 struct simple_util_dai *dai, 299 unsigned int *fixed_sysclk) 300 { 301 if (dai->clk_fixed) { 302 if (*fixed_sysclk && *fixed_sysclk != dai->sysclk) { 303 dev_err(dev, "inconsistent fixed sysclk rates (%u vs %u)\n", 304 *fixed_sysclk, dai->sysclk); 305 return -EINVAL; 306 } 307 *fixed_sysclk = dai->sysclk; 308 } 309 310 return 0; 311 } 312 313 int simple_util_startup(struct snd_pcm_substream *substream) 314 { 315 struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream); 316 struct simple_util_priv *priv = snd_soc_card_get_drvdata(rtd->card); 317 struct simple_dai_props *props = runtime_simple_priv_to_props(priv, rtd); 318 struct simple_util_dai *dai; 319 unsigned int fixed_sysclk = 0; 320 int i1, i2, i; 321 int ret; 322 323 for_each_prop_dai_cpu(props, i1, dai) { 324 ret = simple_clk_enable(dai); 325 if (ret) 326 goto cpu_err; 327 ret = simple_check_fixed_sysclk(rtd->dev, dai, &fixed_sysclk); 328 if (ret) 329 goto cpu_err; 330 } 331 332 for_each_prop_dai_codec(props, i2, dai) { 333 ret = simple_clk_enable(dai); 334 if (ret) 335 goto codec_err; 336 ret = simple_check_fixed_sysclk(rtd->dev, dai, &fixed_sysclk); 337 if (ret) 338 goto codec_err; 339 } 340 341 if (fixed_sysclk && props->mclk_fs) { 342 unsigned int fixed_rate = fixed_sysclk / props->mclk_fs; 343 344 if (fixed_sysclk % props->mclk_fs) { 345 dev_err(rtd->dev, "fixed sysclk %u not divisible by mclk_fs %u\n", 346 fixed_sysclk, props->mclk_fs); 347 ret = -EINVAL; 348 goto codec_err; 349 } 350 ret = snd_pcm_hw_constraint_minmax(substream->runtime, SNDRV_PCM_HW_PARAM_RATE, 351 fixed_rate, fixed_rate); 352 if (ret < 0) 353 goto codec_err; 354 } 355 356 return 0; 357 358 codec_err: 359 for_each_prop_dai_codec(props, i, dai) { 360 if (i >= i2) 361 break; 362 simple_clk_disable(dai); 363 } 364 cpu_err: 365 for_each_prop_dai_cpu(props, i, dai) { 366 if (i >= i1) 367 break; 368 simple_clk_disable(dai); 369 } 370 371 return simple_ret(priv, ret); 372 } 373 EXPORT_SYMBOL_GPL(simple_util_startup); 374 375 void simple_util_shutdown(struct snd_pcm_substream *substream) 376 { 377 struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream); 378 struct simple_util_priv *priv = snd_soc_card_get_drvdata(rtd->card); 379 struct simple_dai_props *props = runtime_simple_priv_to_props(priv, rtd); 380 struct simple_util_dai *dai; 381 int i; 382 383 for_each_prop_dai_cpu(props, i, dai) { 384 struct snd_soc_dai *cpu_dai = snd_soc_rtd_to_cpu(rtd, i); 385 386 if (props->mclk_fs && !dai->clk_fixed && !snd_soc_dai_active(cpu_dai)) 387 snd_soc_dai_set_sysclk(cpu_dai, 0, 0, dai->clk_direction); 388 389 simple_clk_disable(dai); 390 } 391 for_each_prop_dai_codec(props, i, dai) { 392 struct snd_soc_dai *codec_dai = snd_soc_rtd_to_codec(rtd, i); 393 394 if (props->mclk_fs && !dai->clk_fixed && !snd_soc_dai_active(codec_dai)) 395 snd_soc_dai_set_sysclk(codec_dai, 0, 0, dai->clk_direction); 396 397 simple_clk_disable(dai); 398 } 399 } 400 EXPORT_SYMBOL_GPL(simple_util_shutdown); 401 402 static int simple_set_clk_rate(struct simple_util_priv *priv, 403 struct simple_util_dai *simple_dai, 404 unsigned long rate) 405 { 406 struct device *dev = simple_priv_to_dev(priv); 407 int ret = -EINVAL; 408 409 if (!simple_dai) 410 return 0; 411 412 if (simple_dai->clk_fixed && rate != simple_dai->sysclk) { 413 dev_err(dev, "dai %s invalid clock rate %lu\n", simple_dai->name, rate); 414 goto end; 415 } 416 417 if (!simple_dai->clk) 418 return 0; 419 420 if (clk_get_rate(simple_dai->clk) == rate) 421 return 0; 422 423 ret = clk_set_rate(simple_dai->clk, rate); 424 end: 425 return simple_ret(priv, ret); 426 } 427 428 static int simple_set_tdm(struct simple_util_priv *priv, 429 struct snd_soc_dai *dai, 430 struct simple_util_dai *simple_dai, 431 struct snd_pcm_hw_params *params) 432 { 433 int sample_bits = params_width(params); 434 int slot_width, slot_count; 435 int i, ret; 436 437 if (!simple_dai || !simple_dai->tdm_width_map) 438 return 0; 439 440 slot_width = simple_dai->slot_width; 441 slot_count = simple_dai->slots; 442 443 if (slot_width == 0) 444 slot_width = sample_bits; 445 446 for (i = 0; i < simple_dai->n_tdm_widths; ++i) { 447 if (simple_dai->tdm_width_map[i].sample_bits == sample_bits) { 448 slot_width = simple_dai->tdm_width_map[i].slot_width; 449 slot_count = simple_dai->tdm_width_map[i].slot_count; 450 break; 451 } 452 } 453 454 ret = snd_soc_dai_set_tdm_slot(dai, 455 simple_dai->tx_slot_mask, 456 simple_dai->rx_slot_mask, 457 slot_count, 458 slot_width); 459 460 return simple_ret(priv, ret); 461 } 462 463 int simple_util_hw_params(struct snd_pcm_substream *substream, 464 struct snd_pcm_hw_params *params) 465 { 466 struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream); 467 struct simple_util_dai *pdai; 468 struct snd_soc_dai *sdai; 469 struct simple_util_priv *priv = snd_soc_card_get_drvdata(rtd->card); 470 struct simple_dai_props *props = runtime_simple_priv_to_props(priv, rtd); 471 unsigned int mclk, mclk_fs = 0; 472 int i, ret; 473 474 if (props->mclk_fs) 475 mclk_fs = props->mclk_fs; 476 477 if (mclk_fs) { 478 struct snd_soc_component *component; 479 mclk = params_rate(params) * mclk_fs; 480 481 for_each_prop_dai_codec(props, i, pdai) { 482 ret = simple_set_clk_rate(priv, pdai, mclk); 483 if (ret < 0) 484 goto end; 485 } 486 487 for_each_prop_dai_cpu(props, i, pdai) { 488 ret = simple_set_clk_rate(priv, pdai, mclk); 489 if (ret < 0) 490 goto end; 491 } 492 493 /* Ensure sysclk is set on all components in case any 494 * (such as platform components) are missed by calls to 495 * snd_soc_dai_set_sysclk. 496 */ 497 for_each_rtd_components(rtd, i, component) { 498 ret = snd_soc_component_set_sysclk(component, 0, 0, 499 mclk, SND_SOC_CLOCK_IN); 500 if (ret && ret != -ENOTSUPP) 501 goto end; 502 } 503 504 for_each_rtd_codec_dais(rtd, i, sdai) { 505 pdai = simple_props_to_dai_codec(props, i); 506 ret = snd_soc_dai_set_sysclk(sdai, 0, mclk, pdai->clk_direction); 507 if (ret && ret != -ENOTSUPP) 508 goto end; 509 } 510 511 for_each_rtd_cpu_dais(rtd, i, sdai) { 512 pdai = simple_props_to_dai_cpu(props, i); 513 ret = snd_soc_dai_set_sysclk(sdai, 0, mclk, pdai->clk_direction); 514 if (ret && ret != -ENOTSUPP) 515 goto end; 516 } 517 } 518 519 for_each_prop_dai_codec(props, i, pdai) { 520 sdai = snd_soc_rtd_to_codec(rtd, i); 521 ret = simple_set_tdm(priv, sdai, pdai, params); 522 if (ret < 0) 523 goto end; 524 } 525 526 for_each_prop_dai_cpu(props, i, pdai) { 527 sdai = snd_soc_rtd_to_cpu(rtd, i); 528 ret = simple_set_tdm(priv, sdai, pdai, params); 529 if (ret < 0) 530 goto end; 531 } 532 ret = 0; 533 end: 534 return simple_ret(priv, ret); 535 } 536 EXPORT_SYMBOL_GPL(simple_util_hw_params); 537 538 int simple_util_be_hw_params_fixup(struct snd_soc_pcm_runtime *rtd, 539 struct snd_pcm_hw_params *params) 540 { 541 struct simple_util_priv *priv = snd_soc_card_get_drvdata(rtd->card); 542 struct simple_dai_props *dai_props = runtime_simple_priv_to_props(priv, rtd); 543 struct simple_util_data *data = &dai_props->adata; 544 struct snd_interval *rate = hw_param_interval(params, SNDRV_PCM_HW_PARAM_RATE); 545 struct snd_interval *channels = hw_param_interval(params, SNDRV_PCM_HW_PARAM_CHANNELS); 546 547 if (data->convert_rate) 548 rate->min = 549 rate->max = data->convert_rate; 550 551 if (data->convert_channels) 552 channels->min = 553 channels->max = data->convert_channels; 554 555 if (data->convert_sample_format) 556 simple_fixup_sample_fmt(data, params); 557 558 return 0; 559 } 560 EXPORT_SYMBOL_GPL(simple_util_be_hw_params_fixup); 561 562 static int simple_init_dai(struct simple_util_priv *priv, 563 struct snd_soc_dai *dai, struct simple_util_dai *simple_dai) 564 { 565 int ret; 566 567 if (!simple_dai) 568 return 0; 569 570 if (simple_dai->sysclk) { 571 ret = snd_soc_dai_set_sysclk(dai, 0, simple_dai->sysclk, 572 simple_dai->clk_direction); 573 if (ret && ret != -ENOTSUPP) { 574 dev_err(dai->dev, "simple-card: set_sysclk error\n"); 575 goto end; 576 } 577 } 578 579 if (simple_dai->slots) { 580 ret = snd_soc_dai_set_tdm_slot(dai, 581 simple_dai->tx_slot_mask, 582 simple_dai->rx_slot_mask, 583 simple_dai->slots, 584 simple_dai->slot_width); 585 if (ret && ret != -ENOTSUPP) { 586 dev_err(dai->dev, "simple-card: set_tdm_slot error\n"); 587 goto end; 588 } 589 } 590 ret = 0; 591 end: 592 return simple_ret(priv, ret); 593 } 594 595 static inline int simple_component_is_codec(struct snd_soc_component *component) 596 { 597 return component->driver->endianness; 598 } 599 600 static int simple_init_for_codec2codec(struct simple_util_priv *priv, 601 struct snd_soc_pcm_runtime *rtd, 602 struct simple_dai_props *dai_props) 603 { 604 struct snd_soc_dai_link *dai_link = rtd->dai_link; 605 struct snd_soc_component *component; 606 struct snd_soc_pcm_stream *c2c_params; 607 struct snd_pcm_hardware hw; 608 int i, ret, stream; 609 610 /* Do nothing if it already has Codec2Codec settings */ 611 if (dai_link->c2c_params) 612 return 0; 613 614 /* Do nothing if it was DPCM :: BE */ 615 if (dai_link->no_pcm) 616 return 0; 617 618 /* Only Codecs */ 619 for_each_rtd_components(rtd, i, component) { 620 if (!simple_component_is_codec(component)) 621 return 0; 622 } 623 624 /* Assumes the capabilities are the same for all supported streams */ 625 for_each_pcm_streams(stream) { 626 ret = snd_soc_runtime_calc_hw(rtd, &hw, stream); 627 if (ret == 0) 628 break; 629 } 630 631 if (ret < 0) { 632 dev_err(rtd->dev, "simple-card: no valid dai_link params\n"); 633 goto end; 634 } 635 636 ret = -ENOMEM; 637 c2c_params = devm_kzalloc(rtd->dev, sizeof(*c2c_params), GFP_KERNEL); 638 if (!c2c_params) 639 goto end; 640 641 c2c_params->formats = hw.formats; 642 c2c_params->rates = hw.rates; 643 c2c_params->rate_min = hw.rate_min; 644 c2c_params->rate_max = hw.rate_max; 645 c2c_params->channels_min = hw.channels_min; 646 c2c_params->channels_max = hw.channels_max; 647 648 dai_link->c2c_params = c2c_params; 649 dai_link->num_c2c_params = 1; 650 651 ret = 0; 652 end: 653 return simple_ret(priv, ret); 654 } 655 656 int simple_util_dai_init(struct snd_soc_pcm_runtime *rtd) 657 { 658 struct simple_util_priv *priv = snd_soc_card_get_drvdata(rtd->card); 659 struct simple_dai_props *props = runtime_simple_priv_to_props(priv, rtd); 660 struct simple_util_dai *dai; 661 int i, ret; 662 663 for_each_prop_dai_codec(props, i, dai) { 664 ret = simple_init_dai(priv, snd_soc_rtd_to_codec(rtd, i), dai); 665 if (ret < 0) 666 goto end; 667 } 668 for_each_prop_dai_cpu(props, i, dai) { 669 ret = simple_init_dai(priv, snd_soc_rtd_to_cpu(rtd, i), dai); 670 if (ret < 0) 671 goto end; 672 } 673 674 ret = simple_init_for_codec2codec(priv, rtd, props); 675 end: 676 return simple_ret(priv, ret); 677 } 678 EXPORT_SYMBOL_GPL(simple_util_dai_init); 679 680 void simple_util_canonicalize_platform(struct snd_soc_dai_link_component *platforms, 681 struct snd_soc_dai_link_component *cpus) 682 { 683 /* 684 * Assumes Platform == CPU 685 * 686 * Some CPU might be using soc-generic-dmaengine-pcm. This means CPU and Platform 687 * are different Component, but are sharing same component->dev. 688 * 689 * Let's assume Platform is same as CPU if it doesn't identify Platform on DT. 690 * see 691 * simple-card.c :: simple_count_noml() 692 */ 693 if (!platforms->of_node) 694 snd_soc_dlc_use_cpu_as_platform(platforms, cpus); 695 } 696 EXPORT_SYMBOL_GPL(simple_util_canonicalize_platform); 697 698 void simple_util_canonicalize_cpu(struct snd_soc_dai_link_component *cpus, 699 int is_single_links) 700 { 701 /* 702 * In soc_bind_dai_link() will check cpu name after 703 * of_node matching if dai_link has cpu_dai_name. 704 * but, it will never match if name was created by 705 * fmt_single_name() remove cpu_dai_name if cpu_args 706 * was 0. See: 707 * fmt_single_name() 708 * fmt_multiple_name() 709 */ 710 if (is_single_links) 711 cpus->dai_name = NULL; 712 } 713 EXPORT_SYMBOL_GPL(simple_util_canonicalize_cpu); 714 715 void simple_util_clean_reference(struct snd_soc_card *card) 716 { 717 struct snd_soc_dai_link *dai_link; 718 struct snd_soc_dai_link_component *cpu; 719 struct snd_soc_dai_link_component *codec; 720 int i, j; 721 722 for_each_card_prelinks(card, i, dai_link) { 723 for_each_link_cpus(dai_link, j, cpu) 724 of_node_put(cpu->of_node); 725 for_each_link_codecs(dai_link, j, codec) 726 of_node_put(codec->of_node); 727 } 728 } 729 EXPORT_SYMBOL_GPL(simple_util_clean_reference); 730 731 int simple_util_parse_routing(struct snd_soc_card *card, 732 char *prefix) 733 { 734 struct device_node *node = card->dev->of_node; 735 char prop[128]; 736 737 if (!prefix) 738 prefix = ""; 739 740 snprintf(prop, sizeof(prop), "%s%s", prefix, "routing"); 741 742 if (!of_property_present(node, prop)) 743 return 0; 744 745 return snd_soc_of_parse_audio_routing(card, prop); 746 } 747 EXPORT_SYMBOL_GPL(simple_util_parse_routing); 748 749 int simple_util_parse_widgets(struct snd_soc_card *card, 750 char *prefix) 751 { 752 struct device_node *node = card->dev->of_node; 753 char prop[128]; 754 755 if (!prefix) 756 prefix = ""; 757 758 snprintf(prop, sizeof(prop), "%s%s", prefix, "widgets"); 759 760 if (of_property_present(node, prop)) 761 return snd_soc_of_parse_audio_simple_widgets(card, prop); 762 763 /* no widgets is not error */ 764 return 0; 765 } 766 EXPORT_SYMBOL_GPL(simple_util_parse_widgets); 767 768 int simple_util_parse_pin_switches(struct snd_soc_card *card, 769 char *prefix) 770 { 771 char prop[128]; 772 773 if (!prefix) 774 prefix = ""; 775 776 snprintf(prop, sizeof(prop), "%s%s", prefix, "pin-switches"); 777 778 return snd_soc_of_parse_pin_switches(card, prop); 779 } 780 EXPORT_SYMBOL_GPL(simple_util_parse_pin_switches); 781 782 int simple_util_init_jack(struct snd_soc_card *card, 783 struct simple_util_jack *sjack, 784 int is_hp, char *prefix, 785 char *pin) 786 { 787 struct device *dev = card->dev; 788 struct gpio_desc *desc; 789 char prop[128]; 790 char *pin_name; 791 char *gpio_name; 792 int mask; 793 int error; 794 795 if (!prefix) 796 prefix = ""; 797 798 if (is_hp) { 799 snprintf(prop, sizeof(prop), "%shp-det", prefix); 800 pin_name = pin ? pin : "Headphones"; 801 gpio_name = "Headphone detection"; 802 mask = SND_JACK_HEADPHONE; 803 } else { 804 snprintf(prop, sizeof(prop), "%smic-det", prefix); 805 pin_name = pin ? pin : "Mic Jack"; 806 gpio_name = "Mic detection"; 807 mask = SND_JACK_MICROPHONE; 808 } 809 810 desc = gpiod_get_optional(dev, prop, GPIOD_IN); 811 error = PTR_ERR_OR_ZERO(desc); 812 if (error) 813 return error; 814 815 if (desc) { 816 error = gpiod_set_consumer_name(desc, gpio_name); 817 if (error) 818 return error; 819 820 sjack->pin.pin = pin_name; 821 sjack->pin.mask = mask; 822 823 sjack->gpio.name = gpio_name; 824 sjack->gpio.report = mask; 825 sjack->gpio.desc = desc; 826 sjack->gpio.debounce_time = 150; 827 828 snd_soc_card_jack_new_pins(card, pin_name, mask, &sjack->jack, 829 &sjack->pin, 1); 830 831 snd_soc_jack_add_gpios(&sjack->jack, 1, &sjack->gpio); 832 } 833 834 return 0; 835 } 836 EXPORT_SYMBOL_GPL(simple_util_init_jack); 837 838 int simple_util_init_aux_jacks(struct simple_util_priv *priv, char *prefix) 839 { 840 struct snd_soc_card *card = simple_priv_to_card(priv); 841 struct snd_soc_component *component; 842 int found_jack_index = 0; 843 int type = 0; 844 int num = 0; 845 int ret; 846 847 if (priv->aux_jacks) 848 return 0; 849 850 for_each_card_auxs(card, component) { 851 type = snd_soc_component_get_jack_type(component); 852 if (type > 0) 853 num++; 854 } 855 if (num < 1) 856 return 0; 857 858 priv->aux_jacks = devm_kcalloc(card->dev, num, 859 sizeof(struct snd_soc_jack), GFP_KERNEL); 860 if (!priv->aux_jacks) 861 return simple_ret(priv, -ENOMEM); 862 863 for_each_card_auxs(card, component) { 864 char id[128]; 865 struct snd_soc_jack *jack; 866 867 if (found_jack_index >= num) 868 break; 869 870 type = snd_soc_component_get_jack_type(component); 871 if (type <= 0) 872 continue; 873 874 /* create jack */ 875 jack = &(priv->aux_jacks[found_jack_index++]); 876 snprintf(id, sizeof(id), "%s-jack", component->name); 877 ret = snd_soc_card_jack_new(card, id, type, jack); 878 if (ret) 879 continue; 880 881 (void)snd_soc_component_set_jack(component, jack, NULL); 882 } 883 return 0; 884 } 885 EXPORT_SYMBOL_GPL(simple_util_init_aux_jacks); 886 887 static struct simple_util_dai dummy_util_dais = { 888 .name = "dummy_util_dais", 889 }; 890 891 int simple_util_init_priv(struct simple_util_priv *priv, 892 struct link_info *li) 893 { 894 struct snd_soc_card *card = simple_priv_to_card(priv); 895 struct device *dev = simple_priv_to_dev(priv); 896 struct snd_soc_dai_link *dai_link; 897 struct simple_dai_props *dai_props; 898 struct simple_util_dai *dais; 899 struct snd_soc_dai_link_component *dlcs; 900 struct snd_soc_codec_conf *cconf = NULL; 901 int i, dai_num = 0, dlc_num = 0, cnf_num = 0; 902 903 dai_props = devm_kcalloc(dev, li->link, sizeof(*dai_props), GFP_KERNEL); 904 dai_link = devm_kcalloc(dev, li->link, sizeof(*dai_link), GFP_KERNEL); 905 if (!dai_props || !dai_link) 906 return -ENOMEM; 907 908 /* 909 * dais (= CPU+Codec) 910 * dlcs (= CPU+Codec+Platform) 911 */ 912 for (i = 0; i < li->link; i++) { 913 int cc = li->num[i].cpus + li->num[i].codecs; 914 915 dai_num += cc; 916 dlc_num += cc + li->num[i].platforms; 917 918 if (!li->num[i].cpus) 919 cnf_num += li->num[i].codecs; 920 } 921 922 dais = devm_kcalloc(dev, dai_num, sizeof(*dais), GFP_KERNEL); 923 dlcs = devm_kcalloc(dev, dlc_num, sizeof(*dlcs), GFP_KERNEL); 924 if (!dais || !dlcs) 925 return -ENOMEM; 926 927 if (cnf_num) { 928 cconf = devm_kcalloc(dev, cnf_num, sizeof(*cconf), GFP_KERNEL); 929 if (!cconf) 930 return -ENOMEM; 931 } 932 933 dev_dbg(dev, "link %d, dais %d, ccnf %d\n", 934 li->link, dai_num, cnf_num); 935 936 priv->dai_props = dai_props; 937 priv->dai_link = dai_link; 938 priv->dais = dais; 939 priv->dlcs = dlcs; 940 priv->codec_conf = cconf; 941 942 card->dai_link = priv->dai_link; 943 card->num_links = li->link; 944 card->codec_conf = cconf; 945 card->num_configs = cnf_num; 946 947 for (i = 0; i < li->link; i++) { 948 if (li->num[i].cpus) { 949 /* Normal CPU */ 950 dai_link[i].cpus = dlcs; 951 dai_props[i].num.cpus = 952 dai_link[i].num_cpus = li->num[i].cpus; 953 dai_props[i].cpu_dai = dais; 954 955 dlcs += li->num[i].cpus; 956 dais += li->num[i].cpus; 957 } else { 958 /* DPCM Be's CPU = dummy */ 959 dai_link[i].cpus = &snd_soc_dummy_dlc; 960 dai_props[i].num.cpus = 961 dai_link[i].num_cpus = 1; 962 dai_props[i].cpu_dai = &dummy_util_dais; 963 } 964 965 if (li->num[i].codecs) { 966 /* Normal Codec */ 967 dai_link[i].codecs = dlcs; 968 dai_props[i].num.codecs = 969 dai_link[i].num_codecs = li->num[i].codecs; 970 dai_props[i].codec_dai = dais; 971 972 dlcs += li->num[i].codecs; 973 dais += li->num[i].codecs; 974 975 if (!li->num[i].cpus) { 976 /* DPCM Be's Codec */ 977 dai_props[i].codec_conf = cconf; 978 cconf += li->num[i].codecs; 979 } 980 } else { 981 /* DPCM Fe's Codec = dummy */ 982 dai_link[i].codecs = &snd_soc_dummy_dlc; 983 dai_props[i].num.codecs = 984 dai_link[i].num_codecs = 1; 985 dai_props[i].codec_dai = &dummy_util_dais; 986 } 987 988 if (li->num[i].platforms) { 989 /* Have Platform */ 990 dai_link[i].platforms = dlcs; 991 dai_props[i].num.platforms = 992 dai_link[i].num_platforms = li->num[i].platforms; 993 994 dlcs += li->num[i].platforms; 995 } else { 996 /* Doesn't have Platform */ 997 dai_link[i].platforms = NULL; 998 dai_props[i].num.platforms = 999 dai_link[i].num_platforms = 0; 1000 } 1001 } 1002 1003 return 0; 1004 } 1005 EXPORT_SYMBOL_GPL(simple_util_init_priv); 1006 1007 void simple_util_remove(struct platform_device *pdev) 1008 { 1009 struct snd_soc_card *card = platform_get_drvdata(pdev); 1010 1011 simple_util_clean_reference(card); 1012 } 1013 EXPORT_SYMBOL_GPL(simple_util_remove); 1014 1015 int graph_util_card_probe(struct snd_soc_card *card) 1016 { 1017 struct simple_util_priv *priv = snd_soc_card_get_drvdata(card); 1018 int ret; 1019 1020 ret = simple_util_init_hp(card, &priv->hp_jack, NULL); 1021 if (ret < 0) 1022 goto end; 1023 1024 ret = simple_util_init_mic(card, &priv->mic_jack, NULL); 1025 end: 1026 return simple_ret(priv, ret); 1027 } 1028 EXPORT_SYMBOL_GPL(graph_util_card_probe); 1029 1030 int graph_util_is_ports0(struct device_node *np) 1031 { 1032 struct device_node *parent __free(device_node) = of_get_parent(np); 1033 struct device_node *port; 1034 1035 /* np is "endpoint" or "port" */ 1036 if (of_node_name_eq(np, "endpoint")) 1037 port = parent; 1038 else 1039 port = np; 1040 1041 struct device_node *ports __free(device_node) = of_get_parent(port); 1042 struct device_node *top __free(device_node) = of_get_parent(ports); 1043 struct device_node *ports0 __free(device_node) = of_get_child_by_name(top, "ports"); 1044 1045 return ports0 == ports; 1046 } 1047 EXPORT_SYMBOL_GPL(graph_util_is_ports0); 1048 1049 static int graph_get_dai_id(struct device_node *ep) 1050 { 1051 struct device_node *node __free(device_node) = of_graph_get_port_parent(ep); 1052 struct device_node *port __free(device_node) = of_get_parent(ep); 1053 struct of_endpoint info; 1054 int i, id; 1055 int ret; 1056 1057 /* use driver specified DAI ID if exist */ 1058 ret = snd_soc_get_dai_id(ep); 1059 if (ret != -ENOTSUPP) 1060 return ret; 1061 1062 /* use endpoint/port reg if exist */ 1063 ret = of_graph_parse_endpoint(ep, &info); 1064 if (ret == 0) { 1065 /* 1066 * Because it will count port/endpoint if it doesn't have "reg". 1067 * But, we can't judge whether it has "no reg", or "reg = <0>" 1068 * only of_graph_parse_endpoint(). 1069 * We need to check "reg" property 1070 */ 1071 1072 /* check port first */ 1073 ret = of_property_present(port, "reg"); 1074 if (ret) 1075 return info.port; 1076 1077 /* check endpoint 2nd as backup */ 1078 if (of_property_present(ep, "reg")) 1079 return info.id; 1080 } 1081 1082 /* 1083 * Non HDMI sound case, counting port/endpoint on its DT 1084 * is enough. Let's count it. 1085 */ 1086 i = 0; 1087 id = -1; 1088 for_each_of_graph_port(node, p) { 1089 if (port == p) { 1090 id = i; 1091 break; 1092 } 1093 i++; 1094 } 1095 1096 if (id < 0) 1097 return -ENODEV; 1098 1099 return id; 1100 } 1101 1102 int graph_util_parse_dai(struct simple_util_priv *priv, struct device_node *ep, 1103 struct snd_soc_dai_link_component *dlc, int *is_single_link) 1104 { 1105 struct device *dev = simple_priv_to_dev(priv); 1106 struct device_node *node; 1107 struct of_phandle_args args = {}; 1108 struct snd_soc_dai *dai; 1109 int ret; 1110 1111 if (!ep) 1112 return 0; 1113 1114 node = of_graph_get_port_parent(ep); 1115 1116 /* 1117 * Try to find from DAI node 1118 */ 1119 args.np = ep; 1120 dai = snd_soc_get_dai_via_args(&args); 1121 if (dai) { 1122 const char *dai_name = snd_soc_dai_name_get(dai); 1123 const struct of_phandle_args *dai_args = snd_soc_copy_dai_args(dev, &args); 1124 1125 ret = -ENOMEM; 1126 if (!dai_args) 1127 goto err; 1128 1129 dlc->of_node = node; 1130 dlc->dai_name = dai_name; 1131 dlc->dai_args = dai_args; 1132 1133 goto parse_dai_end; 1134 } 1135 1136 /* Get dai->name */ 1137 args.np = node; 1138 args.args[0] = graph_get_dai_id(ep); 1139 args.args_count = (of_graph_get_endpoint_count(node) > 1); 1140 1141 /* 1142 * FIXME 1143 * 1144 * Here, dlc->dai_name is pointer to CPU/Codec DAI name. 1145 * If user unbinded CPU or Codec driver, but not for Sound Card, 1146 * dlc->dai_name is keeping unbinded CPU or Codec 1147 * driver's pointer. 1148 * 1149 * If user re-bind CPU or Codec driver again, ALSA SoC will try 1150 * to rebind Card via snd_soc_try_rebind_card(), but because of 1151 * above reason, it might can't bind Sound Card. 1152 * Because Sound Card is pointing to released dai_name pointer. 1153 * 1154 * To avoid this rebind Card issue, 1155 * 1) It needs to alloc memory to keep dai_name eventhough 1156 * CPU or Codec driver was unbinded, or 1157 * 2) user need to rebind Sound Card everytime 1158 * if he unbinded CPU or Codec. 1159 */ 1160 ret = snd_soc_get_dlc(&args, dlc); 1161 if (ret < 0) 1162 goto err; 1163 1164 parse_dai_end: 1165 if (is_single_link) 1166 *is_single_link = of_graph_get_endpoint_count(node) == 1; 1167 ret = 0; 1168 err: 1169 if (ret < 0) 1170 of_node_put(node); 1171 1172 return simple_ret(priv, ret); 1173 } 1174 EXPORT_SYMBOL_GPL(graph_util_parse_dai); 1175 1176 void graph_util_parse_link_direction(struct device_node *np, 1177 bool *playback_only, bool *capture_only) 1178 { 1179 bool is_playback_only = of_property_read_bool(np, "playback-only"); 1180 bool is_capture_only = of_property_read_bool(np, "capture-only"); 1181 1182 if (playback_only) 1183 *playback_only = is_playback_only; 1184 if (capture_only) 1185 *capture_only = is_capture_only; 1186 } 1187 EXPORT_SYMBOL_GPL(graph_util_parse_link_direction); 1188 1189 static enum snd_soc_trigger_order 1190 __graph_util_parse_trigger_order(struct simple_util_priv *priv, 1191 struct device_node *np, 1192 const char *prop) 1193 { 1194 u32 val[SND_SOC_TRIGGER_SIZE]; 1195 int ret; 1196 1197 ret = of_property_read_u32_array(np, prop, val, SND_SOC_TRIGGER_SIZE); 1198 if (ret == 0) { 1199 struct device *dev = simple_priv_to_dev(priv); 1200 u32 order = (val[0] << 8) + 1201 (val[1] << 4) + 1202 (val[2]); 1203 1204 switch (order) { 1205 case (SND_SOC_TRIGGER_LINK << 8) + 1206 (SND_SOC_TRIGGER_COMPONENT << 4) + 1207 (SND_SOC_TRIGGER_DAI): 1208 return SND_SOC_TRIGGER_ORDER_DEFAULT; 1209 1210 case (SND_SOC_TRIGGER_LINK << 8) + 1211 (SND_SOC_TRIGGER_DAI << 4) + 1212 (SND_SOC_TRIGGER_COMPONENT): 1213 return SND_SOC_TRIGGER_ORDER_LDC; 1214 1215 default: 1216 dev_err(dev, "unsupported trigger order [0x%x]\n", order); 1217 } 1218 } 1219 1220 /* SND_SOC_TRIGGER_ORDER_MAX means error */ 1221 return SND_SOC_TRIGGER_ORDER_MAX; 1222 } 1223 1224 void graph_util_parse_trigger_order(struct simple_util_priv *priv, 1225 struct device_node *np, 1226 enum snd_soc_trigger_order *trigger_start, 1227 enum snd_soc_trigger_order *trigger_stop) 1228 { 1229 static enum snd_soc_trigger_order order; 1230 1231 /* 1232 * We can use it like below 1233 * 1234 * #include <dt-bindings/sound/audio-graph.h> 1235 * 1236 * link-trigger-order = <SND_SOC_TRIGGER_LINK 1237 * SND_SOC_TRIGGER_COMPONENT 1238 * SND_SOC_TRIGGER_DAI>; 1239 */ 1240 1241 order = __graph_util_parse_trigger_order(priv, np, "link-trigger-order"); 1242 if (order < SND_SOC_TRIGGER_ORDER_MAX) { 1243 *trigger_start = order; 1244 *trigger_stop = order; 1245 } 1246 1247 order = __graph_util_parse_trigger_order(priv, np, "link-trigger-order-start"); 1248 if (order < SND_SOC_TRIGGER_ORDER_MAX) 1249 *trigger_start = order; 1250 1251 order = __graph_util_parse_trigger_order(priv, np, "link-trigger-order-stop"); 1252 if (order < SND_SOC_TRIGGER_ORDER_MAX) 1253 *trigger_stop = order; 1254 1255 return; 1256 } 1257 EXPORT_SYMBOL_GPL(graph_util_parse_trigger_order); 1258 1259 /* Module information */ 1260 MODULE_AUTHOR("Kuninori Morimoto <kuninori.morimoto.gx@renesas.com>"); 1261 MODULE_DESCRIPTION("ALSA SoC Simple Card Utils"); 1262 MODULE_LICENSE("GPL v2"); 1263