mirror of https://gitee.com/openkylin/linux.git
ASoC: arizona: Allow number of channels clocked to be restricted
Place a cap on the number of channels clocks are generated for. This is intended for use with systems which have the WM5102 master an I2S bus with multiple data lines. Signed-off-by: Mark Brown <broonie@opensource.wolfsonmicro.com>
This commit is contained in:
parent
f2c26d48d9
commit
c94aa30eda
|
@ -62,6 +62,8 @@
|
||||||
|
|
||||||
#define ARIZONA_MAX_OUTPUT 6
|
#define ARIZONA_MAX_OUTPUT 6
|
||||||
|
|
||||||
|
#define ARIZONA_MAX_AIF 3
|
||||||
|
|
||||||
#define ARIZONA_HAP_ACT_ERM 0
|
#define ARIZONA_HAP_ACT_ERM 0
|
||||||
#define ARIZONA_HAP_ACT_LRA 2
|
#define ARIZONA_HAP_ACT_LRA 2
|
||||||
|
|
||||||
|
@ -96,6 +98,13 @@ struct arizona_pdata {
|
||||||
/** Pin state for GPIO pins */
|
/** Pin state for GPIO pins */
|
||||||
int gpio_defaults[ARIZONA_MAX_GPIO];
|
int gpio_defaults[ARIZONA_MAX_GPIO];
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Maximum number of channels clocks will be generated for,
|
||||||
|
* useful for systems where and I2S bus with multiple data
|
||||||
|
* lines is mastered.
|
||||||
|
*/
|
||||||
|
int max_channels_clocked[ARIZONA_MAX_AIF];
|
||||||
|
|
||||||
/** GPIO for mic detection polarity */
|
/** GPIO for mic detection polarity */
|
||||||
int micd_pol_gpio;
|
int micd_pol_gpio;
|
||||||
|
|
||||||
|
|
|
@ -762,18 +762,28 @@ static int arizona_hw_params(struct snd_pcm_substream *substream,
|
||||||
struct snd_soc_dai *dai)
|
struct snd_soc_dai *dai)
|
||||||
{
|
{
|
||||||
struct snd_soc_codec *codec = dai->codec;
|
struct snd_soc_codec *codec = dai->codec;
|
||||||
|
struct arizona_priv *priv = snd_soc_codec_get_drvdata(codec);
|
||||||
|
struct arizona *arizona = priv->arizona;
|
||||||
int base = dai->driver->base;
|
int base = dai->driver->base;
|
||||||
const int *rates;
|
const int *rates;
|
||||||
int i, ret;
|
int i, ret;
|
||||||
int bclk, lrclk, wl, frame;
|
int chan_limit = arizona->pdata.max_channels_clocked[dai->id - 1];
|
||||||
|
int bclk, lrclk, wl, frame, bclk_target;
|
||||||
|
|
||||||
if (params_rate(params) % 8000)
|
if (params_rate(params) % 8000)
|
||||||
rates = &arizona_44k1_bclk_rates[0];
|
rates = &arizona_44k1_bclk_rates[0];
|
||||||
else
|
else
|
||||||
rates = &arizona_48k_bclk_rates[0];
|
rates = &arizona_48k_bclk_rates[0];
|
||||||
|
|
||||||
|
bclk_target = snd_soc_params_to_bclk(params);
|
||||||
|
if (chan_limit && chan_limit < params_channels(params)) {
|
||||||
|
arizona_aif_dbg(dai, "Limiting to %d channels\n", chan_limit);
|
||||||
|
bclk_target /= params_channels(params);
|
||||||
|
bclk_target *= chan_limit;
|
||||||
|
}
|
||||||
|
|
||||||
for (i = 0; i < ARRAY_SIZE(arizona_44k1_bclk_rates); i++) {
|
for (i = 0; i < ARRAY_SIZE(arizona_44k1_bclk_rates); i++) {
|
||||||
if (rates[i] >= snd_soc_params_to_bclk(params) &&
|
if (rates[i] >= bclk_target &&
|
||||||
rates[i] % params_rate(params) == 0) {
|
rates[i] % params_rate(params) == 0) {
|
||||||
bclk = i;
|
bclk = i;
|
||||||
break;
|
break;
|
||||||
|
|
Loading…
Reference in New Issue