1 // SPDX-License-Identifier: (GPL-2.0 OR MIT) 2 // 3 // Copyright (c) 2018 BayLibre, SAS. 4 // Author: Jerome Brunet <jbrunet@baylibre.com> 5 6 #include <linux/module.h> 7 #include <linux/of_platform.h> 8 #include <sound/soc.h> 9 #include <sound/soc-dai.h> 10 11 #include "axg-tdm.h" 12 13 struct axg_card { 14 struct snd_soc_card card; 15 void **link_data; 16 }; 17 18 struct axg_dai_link_tdm_mask { 19 u32 tx; 20 u32 rx; 21 }; 22 23 struct axg_dai_link_tdm_data { 24 unsigned int mclk_fs; 25 unsigned int slots; 26 unsigned int slot_width; 27 u32 *tx_mask; 28 u32 *rx_mask; 29 struct axg_dai_link_tdm_mask *codec_masks; 30 }; 31 32 #define PREFIX "amlogic," 33 34 static int axg_card_reallocate_links(struct axg_card *priv, 35 unsigned int num_links) 36 { 37 struct snd_soc_dai_link *links; 38 void **ldata; 39 40 links = krealloc(priv->card.dai_link, 41 num_links * sizeof(*priv->card.dai_link), 42 GFP_KERNEL | __GFP_ZERO); 43 ldata = krealloc(priv->link_data, 44 num_links * sizeof(*priv->link_data), 45 GFP_KERNEL | __GFP_ZERO); 46 47 if (!links || !ldata) { 48 dev_err(priv->card.dev, "failed to allocate links\n"); 49 return -ENOMEM; 50 } 51 52 priv->card.dai_link = links; 53 priv->link_data = ldata; 54 priv->card.num_links = num_links; 55 return 0; 56 } 57 58 static int axg_card_parse_dai(struct snd_soc_card *card, 59 struct device_node *node, 60 struct device_node **dai_of_node, 61 const char **dai_name) 62 { 63 struct of_phandle_args args; 64 int ret; 65 66 if (!dai_name || !dai_of_node || !node) 67 return -EINVAL; 68 69 ret = of_parse_phandle_with_args(node, "sound-dai", 70 "#sound-dai-cells", 0, &args); 71 if (ret) { 72 if (ret != -EPROBE_DEFER) 73 dev_err(card->dev, "can't parse dai %d\n", ret); 74 return ret; 75 } 76 *dai_of_node = args.np; 77 78 return snd_soc_get_dai_name(&args, dai_name); 79 } 80 81 static int axg_card_set_link_name(struct snd_soc_card *card, 82 struct snd_soc_dai_link *link, 83 const char *prefix) 84 { 85 char *name = devm_kasprintf(card->dev, GFP_KERNEL, "%s.%s", 86 prefix, link->cpu_of_node->full_name); 87 if (!name) 88 return -ENOMEM; 89 90 link->name = name; 91 link->stream_name = name; 92 93 return 0; 94 } 95 96 static void axg_card_clean_references(struct axg_card *priv) 97 { 98 struct snd_soc_card *card = &priv->card; 99 struct snd_soc_dai_link *link; 100 struct snd_soc_dai_link_component *codec; 101 int i, j; 102 103 if (card->dai_link) { 104 for_each_card_prelinks(card, i, link) { 105 of_node_put(link->cpu_of_node); 106 for_each_link_codecs(link, j, codec) 107 of_node_put(codec->of_node); 108 } 109 } 110 111 if (card->aux_dev) { 112 for (i = 0; i < card->num_aux_devs; i++) 113 of_node_put(card->aux_dev[i].codec_of_node); 114 } 115 116 kfree(card->dai_link); 117 kfree(priv->link_data); 118 } 119 120 static int axg_card_add_aux_devices(struct snd_soc_card *card) 121 { 122 struct device_node *node = card->dev->of_node; 123 struct snd_soc_aux_dev *aux; 124 int num, i; 125 126 num = of_count_phandle_with_args(node, "audio-aux-devs", NULL); 127 if (num == -ENOENT) { 128 /* 129 * It is ok to have no auxiliary devices but for this card it 130 * is a strange situtation. Let's warn the about it. 131 */ 132 dev_warn(card->dev, "card has no auxiliary devices\n"); 133 return 0; 134 } else if (num < 0) { 135 dev_err(card->dev, "error getting auxiliary devices: %d\n", 136 num); 137 return num; 138 } 139 140 aux = devm_kcalloc(card->dev, num, sizeof(*aux), GFP_KERNEL); 141 if (!aux) 142 return -ENOMEM; 143 card->aux_dev = aux; 144 card->num_aux_devs = num; 145 146 for (i = 0; i < card->num_aux_devs; i++, aux++) { 147 aux->codec_of_node = 148 of_parse_phandle(node, "audio-aux-devs", i); 149 if (!aux->codec_of_node) 150 return -EINVAL; 151 } 152 153 return 0; 154 } 155 156 static int axg_card_tdm_be_hw_params(struct snd_pcm_substream *substream, 157 struct snd_pcm_hw_params *params) 158 { 159 struct snd_soc_pcm_runtime *rtd = substream->private_data; 160 struct axg_card *priv = snd_soc_card_get_drvdata(rtd->card); 161 struct axg_dai_link_tdm_data *be = 162 (struct axg_dai_link_tdm_data *)priv->link_data[rtd->num]; 163 struct snd_soc_dai *codec_dai; 164 unsigned int mclk; 165 int ret, i; 166 167 if (be->mclk_fs) { 168 mclk = params_rate(params) * be->mclk_fs; 169 170 for_each_rtd_codec_dai(rtd, i, codec_dai) { 171 ret = snd_soc_dai_set_sysclk(codec_dai, 0, mclk, 172 SND_SOC_CLOCK_IN); 173 if (ret && ret != -ENOTSUPP) 174 return ret; 175 } 176 177 ret = snd_soc_dai_set_sysclk(rtd->cpu_dai, 0, mclk, 178 SND_SOC_CLOCK_OUT); 179 if (ret && ret != -ENOTSUPP) 180 return ret; 181 } 182 183 return 0; 184 } 185 186 static const struct snd_soc_ops axg_card_tdm_be_ops = { 187 .hw_params = axg_card_tdm_be_hw_params, 188 }; 189 190 static int axg_card_tdm_dai_init(struct snd_soc_pcm_runtime *rtd) 191 { 192 struct axg_card *priv = snd_soc_card_get_drvdata(rtd->card); 193 struct axg_dai_link_tdm_data *be = 194 (struct axg_dai_link_tdm_data *)priv->link_data[rtd->num]; 195 struct snd_soc_dai *codec_dai; 196 int ret, i; 197 198 for_each_rtd_codec_dai(rtd, i, codec_dai) { 199 ret = snd_soc_dai_set_tdm_slot(codec_dai, 200 be->codec_masks[i].tx, 201 be->codec_masks[i].rx, 202 be->slots, be->slot_width); 203 if (ret && ret != -ENOTSUPP) { 204 dev_err(codec_dai->dev, 205 "setting tdm link slots failed\n"); 206 return ret; 207 } 208 } 209 210 ret = axg_tdm_set_tdm_slots(rtd->cpu_dai, be->tx_mask, be->rx_mask, 211 be->slots, be->slot_width); 212 if (ret) { 213 dev_err(rtd->cpu_dai->dev, "setting tdm link slots failed\n"); 214 return ret; 215 } 216 217 return 0; 218 } 219 220 static int axg_card_tdm_dai_lb_init(struct snd_soc_pcm_runtime *rtd) 221 { 222 struct axg_card *priv = snd_soc_card_get_drvdata(rtd->card); 223 struct axg_dai_link_tdm_data *be = 224 (struct axg_dai_link_tdm_data *)priv->link_data[rtd->num]; 225 int ret; 226 227 /* The loopback rx_mask is the pad tx_mask */ 228 ret = axg_tdm_set_tdm_slots(rtd->cpu_dai, NULL, be->tx_mask, 229 be->slots, be->slot_width); 230 if (ret) { 231 dev_err(rtd->cpu_dai->dev, "setting tdm link slots failed\n"); 232 return ret; 233 } 234 235 return 0; 236 } 237 238 static int axg_card_add_tdm_loopback(struct snd_soc_card *card, 239 int *index) 240 { 241 struct axg_card *priv = snd_soc_card_get_drvdata(card); 242 struct snd_soc_dai_link *pad = &card->dai_link[*index]; 243 struct snd_soc_dai_link *lb; 244 int ret; 245 246 /* extend links */ 247 ret = axg_card_reallocate_links(priv, card->num_links + 1); 248 if (ret) 249 return ret; 250 251 lb = &card->dai_link[*index + 1]; 252 253 lb->name = kasprintf(GFP_KERNEL, "%s-lb", pad->name); 254 if (!lb->name) 255 return -ENOMEM; 256 257 lb->stream_name = lb->name; 258 lb->cpu_of_node = pad->cpu_of_node; 259 lb->cpu_dai_name = "TDM Loopback"; 260 lb->codec_name = "snd-soc-dummy"; 261 lb->codec_dai_name = "snd-soc-dummy-dai"; 262 lb->dpcm_capture = 1; 263 lb->no_pcm = 1; 264 lb->ops = &axg_card_tdm_be_ops; 265 lb->init = axg_card_tdm_dai_lb_init; 266 267 /* Provide the same link data to the loopback */ 268 priv->link_data[*index + 1] = priv->link_data[*index]; 269 270 /* 271 * axg_card_clean_references() will iterate over this link, 272 * make sure the node count is balanced 273 */ 274 of_node_get(lb->cpu_of_node); 275 276 /* Let add_links continue where it should */ 277 *index += 1; 278 279 return 0; 280 } 281 282 static unsigned int axg_card_parse_daifmt(struct device_node *node, 283 struct device_node *cpu_node) 284 { 285 struct device_node *bitclkmaster = NULL; 286 struct device_node *framemaster = NULL; 287 unsigned int daifmt; 288 289 daifmt = snd_soc_of_parse_daifmt(node, PREFIX, 290 &bitclkmaster, &framemaster); 291 daifmt &= ~SND_SOC_DAIFMT_MASTER_MASK; 292 293 /* If no master is provided, default to cpu master */ 294 if (!bitclkmaster || bitclkmaster == cpu_node) { 295 daifmt |= (!framemaster || framemaster == cpu_node) ? 296 SND_SOC_DAIFMT_CBS_CFS : SND_SOC_DAIFMT_CBS_CFM; 297 } else { 298 daifmt |= (!framemaster || framemaster == cpu_node) ? 299 SND_SOC_DAIFMT_CBM_CFS : SND_SOC_DAIFMT_CBM_CFM; 300 } 301 302 of_node_put(bitclkmaster); 303 of_node_put(framemaster); 304 305 return daifmt; 306 } 307 308 static int axg_card_parse_cpu_tdm_slots(struct snd_soc_card *card, 309 struct snd_soc_dai_link *link, 310 struct device_node *node, 311 struct axg_dai_link_tdm_data *be) 312 { 313 char propname[32]; 314 u32 tx, rx; 315 int i; 316 317 be->tx_mask = devm_kcalloc(card->dev, AXG_TDM_NUM_LANES, 318 sizeof(*be->tx_mask), GFP_KERNEL); 319 be->rx_mask = devm_kcalloc(card->dev, AXG_TDM_NUM_LANES, 320 sizeof(*be->rx_mask), GFP_KERNEL); 321 if (!be->tx_mask || !be->rx_mask) 322 return -ENOMEM; 323 324 for (i = 0, tx = 0; i < AXG_TDM_NUM_LANES; i++) { 325 snprintf(propname, 32, "dai-tdm-slot-tx-mask-%d", i); 326 snd_soc_of_get_slot_mask(node, propname, &be->tx_mask[i]); 327 tx = max(tx, be->tx_mask[i]); 328 } 329 330 /* Disable playback is the interface has no tx slots */ 331 if (!tx) 332 link->dpcm_playback = 0; 333 334 for (i = 0, rx = 0; i < AXG_TDM_NUM_LANES; i++) { 335 snprintf(propname, 32, "dai-tdm-slot-rx-mask-%d", i); 336 snd_soc_of_get_slot_mask(node, propname, &be->rx_mask[i]); 337 rx = max(rx, be->rx_mask[i]); 338 } 339 340 /* Disable capture is the interface has no rx slots */ 341 if (!rx) 342 link->dpcm_capture = 0; 343 344 /* ... but the interface should at least have one of them */ 345 if (!tx && !rx) { 346 dev_err(card->dev, "tdm link has no cpu slots\n"); 347 return -EINVAL; 348 } 349 350 of_property_read_u32(node, "dai-tdm-slot-num", &be->slots); 351 if (!be->slots) { 352 /* 353 * If the slot number is not provided, set it such as it 354 * accommodates the largest mask 355 */ 356 be->slots = fls(max(tx, rx)); 357 } else if (be->slots < fls(max(tx, rx)) || be->slots > 32) { 358 /* 359 * Error if the slots can't accommodate the largest mask or 360 * if it is just too big 361 */ 362 dev_err(card->dev, "bad slot number\n"); 363 return -EINVAL; 364 } 365 366 of_property_read_u32(node, "dai-tdm-slot-width", &be->slot_width); 367 368 return 0; 369 } 370 371 static int axg_card_parse_codecs_masks(struct snd_soc_card *card, 372 struct snd_soc_dai_link *link, 373 struct device_node *node, 374 struct axg_dai_link_tdm_data *be) 375 { 376 struct axg_dai_link_tdm_mask *codec_mask; 377 struct device_node *np; 378 379 codec_mask = devm_kcalloc(card->dev, link->num_codecs, 380 sizeof(*codec_mask), GFP_KERNEL); 381 if (!codec_mask) 382 return -ENOMEM; 383 384 be->codec_masks = codec_mask; 385 386 for_each_child_of_node(node, np) { 387 snd_soc_of_get_slot_mask(np, "dai-tdm-slot-rx-mask", 388 &codec_mask->rx); 389 snd_soc_of_get_slot_mask(np, "dai-tdm-slot-tx-mask", 390 &codec_mask->tx); 391 392 codec_mask++; 393 } 394 395 return 0; 396 } 397 398 static int axg_card_parse_tdm(struct snd_soc_card *card, 399 struct device_node *node, 400 int *index) 401 { 402 struct axg_card *priv = snd_soc_card_get_drvdata(card); 403 struct snd_soc_dai_link *link = &card->dai_link[*index]; 404 struct axg_dai_link_tdm_data *be; 405 int ret; 406 407 /* Allocate tdm link parameters */ 408 be = devm_kzalloc(card->dev, sizeof(*be), GFP_KERNEL); 409 if (!be) 410 return -ENOMEM; 411 priv->link_data[*index] = be; 412 413 /* Setup tdm link */ 414 link->ops = &axg_card_tdm_be_ops; 415 link->init = axg_card_tdm_dai_init; 416 link->dai_fmt = axg_card_parse_daifmt(node, link->cpu_of_node); 417 418 of_property_read_u32(node, "mclk-fs", &be->mclk_fs); 419 420 ret = axg_card_parse_cpu_tdm_slots(card, link, node, be); 421 if (ret) { 422 dev_err(card->dev, "error parsing tdm link slots\n"); 423 return ret; 424 } 425 426 ret = axg_card_parse_codecs_masks(card, link, node, be); 427 if (ret) 428 return ret; 429 430 /* Add loopback if the pad dai has playback */ 431 if (link->dpcm_playback) { 432 ret = axg_card_add_tdm_loopback(card, index); 433 if (ret) 434 return ret; 435 } 436 437 return 0; 438 } 439 440 static int axg_card_set_be_link(struct snd_soc_card *card, 441 struct snd_soc_dai_link *link, 442 struct device_node *node) 443 { 444 struct snd_soc_dai_link_component *codec; 445 struct device_node *np; 446 int ret, num_codecs; 447 448 link->no_pcm = 1; 449 link->dpcm_playback = 1; 450 link->dpcm_capture = 1; 451 452 num_codecs = of_get_child_count(node); 453 if (!num_codecs) { 454 dev_err(card->dev, "be link %s has no codec\n", 455 node->full_name); 456 return -EINVAL; 457 } 458 459 codec = devm_kcalloc(card->dev, num_codecs, sizeof(*codec), GFP_KERNEL); 460 if (!codec) 461 return -ENOMEM; 462 463 link->codecs = codec; 464 link->num_codecs = num_codecs; 465 466 for_each_child_of_node(node, np) { 467 ret = axg_card_parse_dai(card, np, &codec->of_node, 468 &codec->dai_name); 469 if (ret) { 470 of_node_put(np); 471 return ret; 472 } 473 474 codec++; 475 } 476 477 ret = axg_card_set_link_name(card, link, "be"); 478 if (ret) 479 dev_err(card->dev, "error setting %pOFn link name\n", np); 480 481 return ret; 482 } 483 484 static int axg_card_set_fe_link(struct snd_soc_card *card, 485 struct snd_soc_dai_link *link, 486 bool is_playback) 487 { 488 link->dynamic = 1; 489 link->dpcm_merged_format = 1; 490 link->dpcm_merged_chan = 1; 491 link->dpcm_merged_rate = 1; 492 link->codec_dai_name = "snd-soc-dummy-dai"; 493 link->codec_name = "snd-soc-dummy"; 494 495 if (is_playback) 496 link->dpcm_playback = 1; 497 else 498 link->dpcm_capture = 1; 499 500 return axg_card_set_link_name(card, link, "fe"); 501 } 502 503 static int axg_card_cpu_is_capture_fe(struct device_node *np) 504 { 505 return of_device_is_compatible(np, PREFIX "axg-toddr"); 506 } 507 508 static int axg_card_cpu_is_playback_fe(struct device_node *np) 509 { 510 return of_device_is_compatible(np, PREFIX "axg-frddr"); 511 } 512 513 static int axg_card_cpu_is_tdm_iface(struct device_node *np) 514 { 515 return of_device_is_compatible(np, PREFIX "axg-tdm-iface"); 516 } 517 518 static int axg_card_add_link(struct snd_soc_card *card, struct device_node *np, 519 int *index) 520 { 521 struct snd_soc_dai_link *dai_link = &card->dai_link[*index]; 522 int ret; 523 524 ret = axg_card_parse_dai(card, np, &dai_link->cpu_of_node, 525 &dai_link->cpu_dai_name); 526 if (ret) 527 return ret; 528 529 if (axg_card_cpu_is_playback_fe(dai_link->cpu_of_node)) 530 ret = axg_card_set_fe_link(card, dai_link, true); 531 else if (axg_card_cpu_is_capture_fe(dai_link->cpu_of_node)) 532 ret = axg_card_set_fe_link(card, dai_link, false); 533 else 534 ret = axg_card_set_be_link(card, dai_link, np); 535 536 if (ret) 537 return ret; 538 539 if (axg_card_cpu_is_tdm_iface(dai_link->cpu_of_node)) 540 ret = axg_card_parse_tdm(card, np, index); 541 542 return ret; 543 } 544 545 static int axg_card_add_links(struct snd_soc_card *card) 546 { 547 struct axg_card *priv = snd_soc_card_get_drvdata(card); 548 struct device_node *node = card->dev->of_node; 549 struct device_node *np; 550 int num, i, ret; 551 552 num = of_get_child_count(node); 553 if (!num) { 554 dev_err(card->dev, "card has no links\n"); 555 return -EINVAL; 556 } 557 558 ret = axg_card_reallocate_links(priv, num); 559 if (ret) 560 return ret; 561 562 i = 0; 563 for_each_child_of_node(node, np) { 564 ret = axg_card_add_link(card, np, &i); 565 if (ret) { 566 of_node_put(np); 567 return ret; 568 } 569 570 i++; 571 } 572 573 return 0; 574 } 575 576 static int axg_card_parse_of_optional(struct snd_soc_card *card, 577 const char *propname, 578 int (*func)(struct snd_soc_card *c, 579 const char *p)) 580 { 581 /* If property is not provided, don't fail ... */ 582 if (!of_property_read_bool(card->dev->of_node, propname)) 583 return 0; 584 585 /* ... but do fail if it is provided and the parsing fails */ 586 return func(card, propname); 587 } 588 589 static const struct of_device_id axg_card_of_match[] = { 590 { .compatible = "amlogic,axg-sound-card", }, 591 {} 592 }; 593 MODULE_DEVICE_TABLE(of, axg_card_of_match); 594 595 static int axg_card_probe(struct platform_device *pdev) 596 { 597 struct device *dev = &pdev->dev; 598 struct axg_card *priv; 599 int ret; 600 601 priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); 602 if (!priv) 603 return -ENOMEM; 604 605 platform_set_drvdata(pdev, priv); 606 snd_soc_card_set_drvdata(&priv->card, priv); 607 608 priv->card.owner = THIS_MODULE; 609 priv->card.dev = dev; 610 611 ret = snd_soc_of_parse_card_name(&priv->card, "model"); 612 if (ret < 0) 613 return ret; 614 615 ret = axg_card_parse_of_optional(&priv->card, "audio-routing", 616 snd_soc_of_parse_audio_routing); 617 if (ret) { 618 dev_err(dev, "error while parsing routing\n"); 619 return ret; 620 } 621 622 ret = axg_card_parse_of_optional(&priv->card, "audio-widgets", 623 snd_soc_of_parse_audio_simple_widgets); 624 if (ret) { 625 dev_err(dev, "error while parsing widgets\n"); 626 return ret; 627 } 628 629 ret = axg_card_add_links(&priv->card); 630 if (ret) 631 goto out_err; 632 633 ret = axg_card_add_aux_devices(&priv->card); 634 if (ret) 635 goto out_err; 636 637 ret = devm_snd_soc_register_card(dev, &priv->card); 638 if (ret) 639 goto out_err; 640 641 return 0; 642 643 out_err: 644 axg_card_clean_references(priv); 645 return ret; 646 } 647 648 static int axg_card_remove(struct platform_device *pdev) 649 { 650 struct axg_card *priv = platform_get_drvdata(pdev); 651 652 axg_card_clean_references(priv); 653 654 return 0; 655 } 656 657 static struct platform_driver axg_card_pdrv = { 658 .probe = axg_card_probe, 659 .remove = axg_card_remove, 660 .driver = { 661 .name = "axg-sound-card", 662 .of_match_table = axg_card_of_match, 663 }, 664 }; 665 module_platform_driver(axg_card_pdrv); 666 667 MODULE_DESCRIPTION("Amlogic AXG ALSA machine driver"); 668 MODULE_AUTHOR("Jerome Brunet <jbrunet@baylibre.com>"); 669 MODULE_LICENSE("GPL v2"); 670