max98396.c (77c77f03fef76848c3a1f26e12bdc9268c79d9c3) | max98396.c (d29e0a6e3631724c0b36786c6d9616b6e4ebeaa4) |
---|---|
1// SPDX-License-Identifier: GPL-2.0 2// Copyright (c) 2022, Analog Devices Inc. 3 4#include <linux/gpio/consumer.h> 5#include <linux/i2c.h> 6#include <linux/module.h> 7#include <sound/pcm_params.h> 8#include <linux/regulator/consumer.h> --- 424 unchanged lines hidden (view full) --- 433 bclk_pol); 434 435 if (status && update) 436 max98396_global_enable_onoff(max98396->regmap, true); 437 438 return 0; 439} 440 | 1// SPDX-License-Identifier: GPL-2.0 2// Copyright (c) 2022, Analog Devices Inc. 3 4#include <linux/gpio/consumer.h> 5#include <linux/i2c.h> 6#include <linux/module.h> 7#include <sound/pcm_params.h> 8#include <linux/regulator/consumer.h> --- 424 unchanged lines hidden (view full) --- 433 bclk_pol); 434 435 if (status && update) 436 max98396_global_enable_onoff(max98396->regmap, true); 437 438 return 0; 439} 440 |
441/* BCLKs per LRCLK */ 442static const int bclk_sel_table[] = { 443 32, 48, 64, 96, 128, 192, 256, 384, 512, 320, | 441#define MAX98396_BSEL_32 0x2 442#define MAX98396_BSEL_48 0x3 443#define MAX98396_BSEL_64 0x4 444#define MAX98396_BSEL_96 0x5 445#define MAX98396_BSEL_128 0x6 446#define MAX98396_BSEL_192 0x7 447#define MAX98396_BSEL_256 0x8 448#define MAX98396_BSEL_384 0x9 449#define MAX98396_BSEL_512 0xa 450#define MAX98396_BSEL_320 0xb 451#define MAX98396_BSEL_250 0xc 452#define MAX98396_BSEL_125 0xd 453 454/* Refer to table 5 in the datasheet */ 455static const struct max98396_pcm_config { 456 int in, out, width, bsel, max_sr; 457} max98396_pcm_configs[] = { 458 { .in = 2, .out = 4, .width = 16, .bsel = MAX98396_BSEL_32, .max_sr = 192000 }, 459 { .in = 2, .out = 6, .width = 24, .bsel = MAX98396_BSEL_48, .max_sr = 192000 }, 460 { .in = 2, .out = 8, .width = 32, .bsel = MAX98396_BSEL_64, .max_sr = 192000 }, 461 { .in = 3, .out = 15, .width = 32, .bsel = MAX98396_BSEL_125, .max_sr = 192000 }, 462 { .in = 4, .out = 8, .width = 16, .bsel = MAX98396_BSEL_64, .max_sr = 192000 }, 463 { .in = 4, .out = 12, .width = 24, .bsel = MAX98396_BSEL_96, .max_sr = 192000 }, 464 { .in = 4, .out = 16, .width = 32, .bsel = MAX98396_BSEL_128, .max_sr = 192000 }, 465 { .in = 5, .out = 15, .width = 24, .bsel = MAX98396_BSEL_125, .max_sr = 192000 }, 466 { .in = 7, .out = 15, .width = 16, .bsel = MAX98396_BSEL_125, .max_sr = 192000 }, 467 { .in = 2, .out = 4, .width = 16, .bsel = MAX98396_BSEL_32, .max_sr = 96000 }, 468 { .in = 2, .out = 6, .width = 24, .bsel = MAX98396_BSEL_48, .max_sr = 96000 }, 469 { .in = 2, .out = 8, .width = 32, .bsel = MAX98396_BSEL_64, .max_sr = 96000 }, 470 { .in = 3, .out = 15, .width = 32, .bsel = MAX98396_BSEL_125, .max_sr = 96000 }, 471 { .in = 4, .out = 8, .width = 16, .bsel = MAX98396_BSEL_64, .max_sr = 96000 }, 472 { .in = 4, .out = 12, .width = 24, .bsel = MAX98396_BSEL_96, .max_sr = 96000 }, 473 { .in = 4, .out = 16, .width = 32, .bsel = MAX98396_BSEL_128, .max_sr = 96000 }, 474 { .in = 5, .out = 15, .width = 24, .bsel = MAX98396_BSEL_125, .max_sr = 96000 }, 475 { .in = 7, .out = 15, .width = 16, .bsel = MAX98396_BSEL_125, .max_sr = 96000 }, 476 { .in = 7, .out = 31, .width = 32, .bsel = MAX98396_BSEL_250, .max_sr = 96000 }, 477 { .in = 8, .out = 16, .width = 16, .bsel = MAX98396_BSEL_128, .max_sr = 96000 }, 478 { .in = 8, .out = 24, .width = 24, .bsel = MAX98396_BSEL_192, .max_sr = 96000 }, 479 { .in = 8, .out = 32, .width = 32, .bsel = MAX98396_BSEL_256, .max_sr = 96000 }, 480 { .in = 10, .out = 31, .width = 24, .bsel = MAX98396_BSEL_250, .max_sr = 96000 }, 481 { .in = 15, .out = 31, .width = 16, .bsel = MAX98396_BSEL_250, .max_sr = 96000 }, 482 { .in = 16, .out = 32, .width = 16, .bsel = MAX98396_BSEL_256, .max_sr = 96000 }, 483 { .in = 7, .out = 31, .width = 32, .bsel = MAX98396_BSEL_250, .max_sr = 48000 }, 484 { .in = 10, .out = 31, .width = 24, .bsel = MAX98396_BSEL_250, .max_sr = 48000 }, 485 { .in = 10, .out = 40, .width = 32, .bsel = MAX98396_BSEL_320, .max_sr = 48000 }, 486 { .in = 15, .out = 31, .width = 16, .bsel = MAX98396_BSEL_250, .max_sr = 48000 }, 487 { .in = 16, .out = 48, .width = 24, .bsel = MAX98396_BSEL_384, .max_sr = 48000 }, 488 { .in = 16, .out = 64, .width = 32, .bsel = MAX98396_BSEL_512, .max_sr = 48000 }, |
444}; 445 | 489}; 490 |
446static int max98396_get_bclk_sel(int bclk) | 491static int max98396_pcm_config_index(int in_slots, int out_slots, int width) |
447{ 448 int i; | 492{ 493 int i; |
449 /* match BCLKs per LRCLK */ 450 for (i = 0; i < ARRAY_SIZE(bclk_sel_table); i++) { 451 if (bclk_sel_table[i] == bclk) 452 return i + 2; 453 } 454 return 0; 455} | |
456 | 494 |
457static int max98396_set_clock(struct snd_soc_component *component, 458 struct snd_pcm_hw_params *params) 459{ 460 struct max98396_priv *max98396 = snd_soc_component_get_drvdata(component); 461 /* BCLK/LRCLK ratio calculation */ 462 int blr_clk_ratio = params_channels(params) * max98396->ch_size; 463 int value; | 495 for (i = 0; i < ARRAY_SIZE(max98396_pcm_configs); i++) { 496 const struct max98396_pcm_config *c = &max98396_pcm_configs[i]; |
464 | 497 |
465 if (!max98396->tdm_mode) { 466 /* BCLK configuration */ 467 value = max98396_get_bclk_sel(blr_clk_ratio); 468 if (!value) { 469 dev_err(component->dev, 470 "blr_clk_ratio %d unsupported, format %d\n", 471 blr_clk_ratio, params_format(params)); 472 return -EINVAL; 473 } 474 475 regmap_update_bits(max98396->regmap, 476 MAX98396_R2042_PCM_CLK_SETUP, 477 MAX98396_PCM_CLK_SETUP_BSEL_MASK, 478 value); | 498 if (in_slots == c->in && out_slots <= c->out && width == c->width) 499 return i; |
479 } 480 | 500 } 501 |
481 return 0; | 502 return -1; |
482} 483 484static int max98396_dai_hw_params(struct snd_pcm_substream *substream, 485 struct snd_pcm_hw_params *params, 486 struct snd_soc_dai *dai) 487{ 488 struct snd_soc_component *component = dai->component; 489 struct max98396_priv *max98396 = snd_soc_component_get_drvdata(component); 490 unsigned int sampling_rate = 0; 491 unsigned int chan_sz = 0; | 503} 504 505static int max98396_dai_hw_params(struct snd_pcm_substream *substream, 506 struct snd_pcm_hw_params *params, 507 struct snd_soc_dai *dai) 508{ 509 struct snd_soc_component *component = dai->component; 510 struct max98396_priv *max98396 = snd_soc_component_get_drvdata(component); 511 unsigned int sampling_rate = 0; 512 unsigned int chan_sz = 0; |
492 int ret, reg; 493 int status; | 513 int ret, reg, status, bsel = 0; |
494 bool update = false; 495 496 /* pcm mode configuration */ 497 switch (snd_pcm_format_width(params_format(params))) { 498 case 16: 499 chan_sz = MAX98396_PCM_MODE_CFG_CHANSZ_16; 500 break; 501 case 24: 502 chan_sz = MAX98396_PCM_MODE_CFG_CHANSZ_24; 503 break; 504 case 32: 505 chan_sz = MAX98396_PCM_MODE_CFG_CHANSZ_32; 506 break; 507 default: 508 dev_err(component->dev, "format unsupported %d\n", 509 params_format(params)); 510 goto err; 511 } 512 | 514 bool update = false; 515 516 /* pcm mode configuration */ 517 switch (snd_pcm_format_width(params_format(params))) { 518 case 16: 519 chan_sz = MAX98396_PCM_MODE_CFG_CHANSZ_16; 520 break; 521 case 24: 522 chan_sz = MAX98396_PCM_MODE_CFG_CHANSZ_24; 523 break; 524 case 32: 525 chan_sz = MAX98396_PCM_MODE_CFG_CHANSZ_32; 526 break; 527 default: 528 dev_err(component->dev, "format unsupported %d\n", 529 params_format(params)); 530 goto err; 531 } 532 |
513 max98396->ch_size = snd_pcm_format_width(params_format(params)); 514 | |
515 dev_dbg(component->dev, "format supported %d", 516 params_format(params)); 517 518 /* sampling rate configuration */ 519 switch (params_rate(params)) { 520 case 8000: 521 sampling_rate = MAX98396_PCM_SR_8000; 522 break; --- 31 unchanged lines hidden (view full) --- 554 sampling_rate = MAX98396_PCM_SR_192000; 555 break; 556 default: 557 dev_err(component->dev, "rate %d not supported\n", 558 params_rate(params)); 559 goto err; 560 } 561 | 533 dev_dbg(component->dev, "format supported %d", 534 params_format(params)); 535 536 /* sampling rate configuration */ 537 switch (params_rate(params)) { 538 case 8000: 539 sampling_rate = MAX98396_PCM_SR_8000; 540 break; --- 31 unchanged lines hidden (view full) --- 572 sampling_rate = MAX98396_PCM_SR_192000; 573 break; 574 default: 575 dev_err(component->dev, "rate %d not supported\n", 576 params_rate(params)); 577 goto err; 578 } 579 |
580 if (max98396->tdm_mode) { 581 if (params_rate(params) > max98396->tdm_max_samplerate) { 582 dev_err(component->dev, "TDM sample rate %d too high", 583 params_rate(params)); 584 goto err; 585 } 586 } else { 587 /* BCLK configuration */ 588 ret = max98396_pcm_config_index(params_channels(params), 589 params_channels(params), 590 snd_pcm_format_width(params_format(params))); 591 if (ret < 0) { 592 dev_err(component->dev, 593 "no PCM config for %d channels, format %d\n", 594 params_channels(params), params_format(params)); 595 goto err; 596 } 597 598 bsel = max98396_pcm_configs[ret].bsel; 599 600 if (params_rate(params) > max98396_pcm_configs[ret].max_sr) { 601 dev_err(component->dev, "sample rate %d too high", 602 params_rate(params)); 603 goto err; 604 } 605 } 606 |
|
562 ret = regmap_read(max98396->regmap, MAX98396_R210F_GLOBAL_EN, &status); 563 if (ret < 0) 564 goto err; 565 566 if (status) { 567 ret = regmap_read(max98396->regmap, MAX98396_R2041_PCM_MODE_CFG, ®); 568 if (ret < 0) 569 goto err; --- 29 unchanged lines hidden (view full) --- 599 (sampling_rate - 3) 600 << MAX98396_IVADC_SR_SHIFT); 601 else 602 regmap_update_bits(max98396->regmap, 603 MAX98396_R2043_PCM_SR_SETUP, 604 MAX98396_IVADC_SR_MASK, 605 sampling_rate << MAX98396_IVADC_SR_SHIFT); 606 | 607 ret = regmap_read(max98396->regmap, MAX98396_R210F_GLOBAL_EN, &status); 608 if (ret < 0) 609 goto err; 610 611 if (status) { 612 ret = regmap_read(max98396->regmap, MAX98396_R2041_PCM_MODE_CFG, ®); 613 if (ret < 0) 614 goto err; --- 29 unchanged lines hidden (view full) --- 644 (sampling_rate - 3) 645 << MAX98396_IVADC_SR_SHIFT); 646 else 647 regmap_update_bits(max98396->regmap, 648 MAX98396_R2043_PCM_SR_SETUP, 649 MAX98396_IVADC_SR_MASK, 650 sampling_rate << MAX98396_IVADC_SR_SHIFT); 651 |
607 ret = max98396_set_clock(component, params); | 652 if (bsel) 653 regmap_update_bits(max98396->regmap, 654 MAX98396_R2042_PCM_CLK_SETUP, 655 MAX98396_PCM_CLK_SETUP_BSEL_MASK, 656 bsel); |
608 609 if (status && update) 610 max98396_global_enable_onoff(max98396->regmap, true); 611 | 657 658 if (status && update) 659 max98396_global_enable_onoff(max98396->regmap, true); 660 |
612 return ret; | 661 return 0; |
613 614err: 615 return -EINVAL; 616} 617 618static int max98396_dai_tdm_slot(struct snd_soc_dai *dai, 619 unsigned int tx_mask, unsigned int rx_mask, 620 int slots, int slot_width) --- 8 unchanged lines hidden (view full) --- 629 bool update = false; 630 631 if (!tx_mask && !rx_mask && !slots && !slot_width) 632 max98396->tdm_mode = false; 633 else 634 max98396->tdm_mode = true; 635 636 /* BCLK configuration */ | 662 663err: 664 return -EINVAL; 665} 666 667static int max98396_dai_tdm_slot(struct snd_soc_dai *dai, 668 unsigned int tx_mask, unsigned int rx_mask, 669 int slots, int slot_width) --- 8 unchanged lines hidden (view full) --- 678 bool update = false; 679 680 if (!tx_mask && !rx_mask && !slots && !slot_width) 681 max98396->tdm_mode = false; 682 else 683 max98396->tdm_mode = true; 684 685 /* BCLK configuration */ |
637 bsel = max98396_get_bclk_sel(slots * slot_width); 638 if (bsel == 0) { 639 dev_err(component->dev, "BCLK %d not supported\n", 640 slots * slot_width); | 686 ret = max98396_pcm_config_index(slots, slots, slot_width); 687 if (ret < 0) { 688 dev_err(component->dev, "no TDM config for %d slots %d bits\n", 689 slots, slot_width); |
641 return -EINVAL; 642 } 643 | 690 return -EINVAL; 691 } 692 |
693 bsel = max98396_pcm_configs[ret].bsel; 694 max98396->tdm_max_samplerate = max98396_pcm_configs[ret].max_sr; 695 |
|
644 /* Channel size configuration */ 645 switch (slot_width) { 646 case 16: 647 chan_sz = MAX98396_PCM_MODE_CFG_CHANSZ_16; 648 break; 649 case 24: 650 chan_sz = MAX98396_PCM_MODE_CFG_CHANSZ_24; 651 break; --- 1115 unchanged lines hidden --- | 696 /* Channel size configuration */ 697 switch (slot_width) { 698 case 16: 699 chan_sz = MAX98396_PCM_MODE_CFG_CHANSZ_16; 700 break; 701 case 24: 702 chan_sz = MAX98396_PCM_MODE_CFG_CHANSZ_24; 703 break; --- 1115 unchanged lines hidden --- |