本文整理汇总了C++中snd_soc_write函数的典型用法代码示例。如果您正苦于以下问题:C++ snd_soc_write函数的具体用法?C++ snd_soc_write怎么用?C++ snd_soc_write使用的例子?那么恭喜您, 这里精选的函数代码示例或许可以为您提供帮助。
在下文中一共展示了snd_soc_write函数的15个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C++代码示例。
示例1: wm8961_hw_params
static int wm8961_hw_params(struct snd_pcm_substream *substream,
struct snd_pcm_hw_params *params,
struct snd_soc_dai *dai)
{
struct snd_soc_codec *codec = dai->codec;
struct wm8961_priv *wm8961 = snd_soc_codec_get_drvdata(codec);
int i, best, target, fs;
u16 reg;
fs = params_rate(params);
if (!wm8961->sysclk) {
dev_err(codec->dev, "MCLK has not been specified\n");
return -EINVAL;
}
/* Find the closest sample rate for the filters */
best = 0;
for (i = 0; i < ARRAY_SIZE(wm8961_srate); i++) {
if (abs(wm8961_srate[i].rate - fs) <
abs(wm8961_srate[best].rate - fs))
best = i;
}
reg = snd_soc_read(codec, WM8961_ADDITIONAL_CONTROL_3);
reg &= ~WM8961_SAMPLE_RATE_MASK;
reg |= wm8961_srate[best].val;
snd_soc_write(codec, WM8961_ADDITIONAL_CONTROL_3, reg);
dev_dbg(codec->dev, "Selected SRATE %dHz for %dHz\n",
wm8961_srate[best].rate, fs);
/* Select a CLK_SYS/fs ratio equal to or higher than required */
target = wm8961->sysclk / fs;
if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK && target < 64) {
dev_err(codec->dev,
"SYSCLK must be at least 64*fs for DAC\n");
return -EINVAL;
}
if (substream->stream == SNDRV_PCM_STREAM_CAPTURE && target < 256) {
dev_err(codec->dev,
"SYSCLK must be at least 256*fs for ADC\n");
return -EINVAL;
}
for (i = 0; i < ARRAY_SIZE(wm8961_clk_sys_ratio); i++) {
if (wm8961_clk_sys_ratio[i].ratio >= target)
break;
}
if (i == ARRAY_SIZE(wm8961_clk_sys_ratio)) {
dev_err(codec->dev, "Unable to generate CLK_SYS_RATE\n");
return -EINVAL;
}
dev_dbg(codec->dev, "Selected CLK_SYS_RATE of %d for %d/%d=%d\n",
wm8961_clk_sys_ratio[i].ratio, wm8961->sysclk, fs,
wm8961->sysclk / fs);
reg = snd_soc_read(codec, WM8961_CLOCKING_4);
reg &= ~WM8961_CLK_SYS_RATE_MASK;
reg |= wm8961_clk_sys_ratio[i].val << WM8961_CLK_SYS_RATE_SHIFT;
snd_soc_write(codec, WM8961_CLOCKING_4, reg);
reg = snd_soc_read(codec, WM8961_AUDIO_INTERFACE_0);
reg &= ~WM8961_WL_MASK;
switch (params_width(params)) {
case 16:
break;
case 20:
reg |= 1 << WM8961_WL_SHIFT;
break;
case 24:
reg |= 2 << WM8961_WL_SHIFT;
break;
case 32:
reg |= 3 << WM8961_WL_SHIFT;
break;
default:
return -EINVAL;
}
snd_soc_write(codec, WM8961_AUDIO_INTERFACE_0, reg);
/* Sloping stop-band filter is recommended for <= 24kHz */
reg = snd_soc_read(codec, WM8961_ADC_DAC_CONTROL_2);
if (fs <= 24000)
reg |= WM8961_DACSLOPE;
else
reg &= ~WM8961_DACSLOPE;
snd_soc_write(codec, WM8961_ADC_DAC_CONTROL_2, reg);
return 0;
}
示例2: sta32x_hw_params
//.........这里部分代码省略.........
for (i = 0; i < ARRAY_SIZE(interpolation_ratios); i++)
if (interpolation_ratios[i].fs == rate) {
ir = interpolation_ratios[i].ir;
break;
}
if (ir < 0)
return -EINVAL;
for (i = 0; mclk_ratios[ir][i].ratio; i++)
if (mclk_ratios[ir][i].ratio * rate == sta32x->mclk) {
mcs = mclk_ratios[ir][i].mcs;
break;
}
if (mcs < 0)
return -EINVAL;
confa = snd_soc_read(codec, STA32X_CONFA);
confa &= ~(STA32X_CONFA_MCS_MASK | STA32X_CONFA_IR_MASK);
confa |= (ir << STA32X_CONFA_IR_SHIFT) | (mcs << STA32X_CONFA_MCS_SHIFT);
confb = snd_soc_read(codec, STA32X_CONFB);
confb &= ~(STA32X_CONFB_SAI_MASK | STA32X_CONFB_SAIFB);
switch (params_format(params)) {
case SNDRV_PCM_FORMAT_S24_LE:
case SNDRV_PCM_FORMAT_S24_BE:
case SNDRV_PCM_FORMAT_S24_3LE:
case SNDRV_PCM_FORMAT_S24_3BE:
pr_debug("24bit\n");
/* fall through */
case SNDRV_PCM_FORMAT_S32_LE:
case SNDRV_PCM_FORMAT_S32_BE:
pr_debug("24bit or 32bit\n");
switch (sta32x->format) {
case SND_SOC_DAIFMT_I2S:
confb |= 0x0;
break;
case SND_SOC_DAIFMT_LEFT_J:
confb |= 0x1;
break;
case SND_SOC_DAIFMT_RIGHT_J:
confb |= 0x2;
break;
}
break;
case SNDRV_PCM_FORMAT_S20_3LE:
case SNDRV_PCM_FORMAT_S20_3BE:
pr_debug("20bit\n");
switch (sta32x->format) {
case SND_SOC_DAIFMT_I2S:
confb |= 0x4;
break;
case SND_SOC_DAIFMT_LEFT_J:
confb |= 0x5;
break;
case SND_SOC_DAIFMT_RIGHT_J:
confb |= 0x6;
break;
}
break;
case SNDRV_PCM_FORMAT_S18_3LE:
case SNDRV_PCM_FORMAT_S18_3BE:
pr_debug("18bit\n");
switch (sta32x->format) {
case SND_SOC_DAIFMT_I2S:
confb |= 0x8;
break;
case SND_SOC_DAIFMT_LEFT_J:
confb |= 0x9;
break;
case SND_SOC_DAIFMT_RIGHT_J:
confb |= 0xa;
break;
}
break;
case SNDRV_PCM_FORMAT_S16_LE:
case SNDRV_PCM_FORMAT_S16_BE:
pr_debug("16bit\n");
switch (sta32x->format) {
case SND_SOC_DAIFMT_I2S:
confb |= 0x0;
break;
case SND_SOC_DAIFMT_LEFT_J:
confb |= 0xd;
break;
case SND_SOC_DAIFMT_RIGHT_J:
confb |= 0xe;
break;
}
break;
default:
return -EINVAL;
}
snd_soc_write(codec, STA32X_CONFA, confa);
snd_soc_write(codec, STA32X_CONFB, confb);
return 0;
}
示例3: tegra_hifi_hw_params
static int tegra_hifi_hw_params(struct snd_pcm_substream *substream,
struct snd_pcm_hw_params *params)
{
struct snd_soc_pcm_runtime *rtd = substream->private_data;
struct snd_soc_dai *codec_dai = rtd->dai->codec_dai;
struct snd_soc_dai *cpu_dai = rtd->dai->cpu_dai;
int err;
#if 0
struct snd_soc_codec *codec = codec_dai->codec;
int CtrlReg = 0;
int VolumeCtrlReg = 0;
int SidetoneCtrlReg = 0;
int SideToneAtenuation = 0;
#endif
err = snd_soc_dai_set_fmt(codec_dai,
SND_SOC_DAIFMT_I2S | \
SND_SOC_DAIFMT_NB_NF | \
SND_SOC_DAIFMT_CBS_CFS);
if (err < 0) {
printk(KERN_ERR "codec_dai fmt not set \n");
return err;
}
err = snd_soc_dai_set_fmt(cpu_dai,
SND_SOC_DAIFMT_I2S | \
SND_SOC_DAIFMT_NB_NF | \
SND_SOC_DAIFMT_CBS_CFS);
if (err < 0) {
printk(KERN_ERR "cpu_dai fmt not set \n");
return err;
}
err = snd_soc_dai_set_sysclk(codec_dai, WM8994_SYSCLK_MCLK1,
I2S1_CLK, SND_SOC_CLOCK_IN);
if (err < 0) {
printk(KERN_ERR "codec_dai clock not set\n");
return err;
}
err = snd_soc_dai_set_sysclk(cpu_dai, 0, I2S1_CLK, SND_SOC_CLOCK_IN);
if (err < 0) {
printk(KERN_ERR "cpu_dai clock not set\n");
return err;
}
#if 0
if (substream->stream != SNDRV_PCM_STREAM_PLAYBACK) {
snd_soc_write(codec, WM8903_ANALOGUE_LEFT_INPUT_0, 0X7);
snd_soc_write(codec, WM8903_ANALOGUE_RIGHT_INPUT_0, 0X7);
// Mic Bias enable
CtrlReg = (0x1<<B00_MICBIAS_ENA) | (0x1<<B01_MICDET_ENA);
snd_soc_write(codec, WM8903_MIC_BIAS_CONTROL_0, CtrlReg);
// Enable DRC
CtrlReg = snd_soc_read(codec, WM8903_DRC_0);
CtrlReg |= (1<<B15_DRC_ENA);
snd_soc_write(codec, WM8903_DRC_0, CtrlReg);
// Single Ended Mic
CtrlReg = (0x0<<B06_IN_CM_ENA) |
(0x0<<B00_MODE) | (0x0<<B04_IP_SEL_N)
| (0x1<<B02_IP_SEL_P);
VolumeCtrlReg = (0x1C << B00_IN_VOL);
// Mic Setting
snd_soc_write(codec, WM8903_ANALOGUE_LEFT_INPUT_1, CtrlReg);
snd_soc_write(codec, WM8903_ANALOGUE_RIGHT_INPUT_1, CtrlReg);
// voulme for single ended mic
snd_soc_write(codec, WM8903_ANALOGUE_LEFT_INPUT_0,
VolumeCtrlReg);
snd_soc_write(codec, WM8903_ANALOGUE_RIGHT_INPUT_0,
VolumeCtrlReg);
// replicate mic setting on both channels
CtrlReg = snd_soc_read(codec, WM8903_AUDIO_INTERFACE_0);
CtrlReg = SET_REG_VAL(CtrlReg, 0x1, B06_AIF_ADCR, 0x0);
CtrlReg = SET_REG_VAL(CtrlReg, 0x1, B06_AIF_ADCL, 0x0);
snd_soc_write(codec, WM8903_AUDIO_INTERFACE_0, CtrlReg);
// Enable analog inputs
CtrlReg = (0x1<<B01_INL_ENA) | (0x1<<B00_INR_ENA);
snd_soc_write(codec, WM8903_POWER_MANAGEMENT_0, CtrlReg);
// ADC Settings
CtrlReg = snd_soc_read(codec, WM8903_ADC_DIGITAL_0);
CtrlReg |= (0x1<<B04_ADC_HPF_ENA);
snd_soc_write(codec, WM8903_ADC_DIGITAL_0, CtrlReg);
SidetoneCtrlReg = 0;
snd_soc_write(codec, R20_SIDETONE_CTRL, SidetoneCtrlReg);
// Enable ADC
CtrlReg = snd_soc_read(codec, WM8903_POWER_MANAGEMENT_6);
CtrlReg |= (0x1<<B00_ADCR_ENA)|(0x1<<B01_ADCL_ENA);
snd_soc_write(codec, WM8903_POWER_MANAGEMENT_6, CtrlReg);
// Enable Sidetone
SidetoneCtrlReg = (0x1<<2) | (0x2<<0);
SideToneAtenuation = 12 ; // sidetone 0 db
SidetoneCtrlReg |= (SideToneAtenuation<<8)
| (SideToneAtenuation<<4);
snd_soc_write(codec, R20_SIDETONE_CTRL, SidetoneCtrlReg);
CtrlReg = snd_soc_read(codec, R29_DRC_1);
CtrlReg |= 0x3; //mic volume 18 db
snd_soc_write(codec, R29_DRC_1, CtrlReg);
}
#endif
//.........这里部分代码省略.........
示例4: aic31xx_hw_params
static int aic31xx_hw_params(struct snd_pcm_substream *substream,
struct snd_pcm_hw_params *params,
struct snd_soc_dai *tmp)
{
struct snd_soc_pcm_runtime *rtd = substream->private_data;
struct snd_soc_codec *codec = rtd->codec;
struct aic31xx_priv *aic31xx = snd_soc_codec_get_drvdata(codec);
u8 data = 0;
int i;
dev_dbg(codec->dev, "## %s: format %d rate %d\n",
__func__, params_format(params), params_rate(params));
switch (params_format(params)) {
case SNDRV_PCM_FORMAT_S16_LE:
break;
case SNDRV_PCM_FORMAT_S20_3LE:
data = (AIC31XX_WORD_LEN_20BITS <<
AIC31XX_IFACE1_DATALEN_SHIFT);
break;
case SNDRV_PCM_FORMAT_S24_3LE:
data = (AIC31XX_WORD_LEN_24BITS <<
AIC31XX_IFACE1_DATALEN_SHIFT);
break;
case SNDRV_PCM_FORMAT_S32_LE:
data = (AIC31XX_WORD_LEN_32BITS <<
AIC31XX_IFACE1_DATALEN_SHIFT);
break;
}
snd_soc_update_bits(codec, AIC31XX_IFACE1,
AIC31XX_IFACE1_DATALEN_MASK,
data);
/* Use PLL as CODEC_CLKIN and DAC_MOD_CLK as BDIV_CLKIN */
snd_soc_update_bits(codec, AIC31XX_CLKMUX,
AIC31XX_CODEC_CLKIN_MASK, AIC31XX_CODEC_CLKIN_PLL);
snd_soc_update_bits(codec, AIC31XX_IFACE2, AIC31XX_BDIVCLK_MASK,
AIC31XX_DACMOD2BCLK);
for (i = 0; i < ARRAY_SIZE(aic31xx_divs); i++) {
if ((aic31xx_divs[i].rate == params_rate(params))
&& (aic31xx_divs[i].mclk == aic31xx->sysclk)) {
break;
}
}
if (i == ARRAY_SIZE(aic31xx_divs)) {
dev_err(codec->dev, "%s: Sampling rate %u not supported\n",
__func__, params_rate(params));
return -EINVAL;
}
snd_soc_update_bits(codec, AIC31XX_PLLPR, AIC31XX_PLL_MASK,
(aic31xx_divs[i].p_val << 4) | 0x01);
snd_soc_write(codec, AIC31XX_PLLJ, aic31xx_divs[i].pll_j);
snd_soc_write(codec, AIC31XX_PLLDMSB, (aic31xx_divs[i].pll_d >> 8));
snd_soc_write(codec, AIC31XX_PLLDLSB,
(aic31xx_divs[i].pll_d & 0xff));
/* NDAC divider value */
snd_soc_update_bits(codec, AIC31XX_NDAC, AIC31XX_PLL_MASK,
aic31xx_divs[i].ndac);
/* MDAC divider value */
snd_soc_update_bits(codec, AIC31XX_MDAC, AIC31XX_PLL_MASK,
aic31xx_divs[i].mdac);
/* DOSR MSB & LSB values */
snd_soc_write(codec, AIC31XX_DOSRMSB, aic31xx_divs[i].dosr >> 8);
snd_soc_write(codec, AIC31XX_DOSRLSB,
(aic31xx_divs[i].dosr & 0xff));
/* NADC divider value */
snd_soc_update_bits(codec, AIC31XX_NADC, AIC31XX_PLL_MASK,
aic31xx_divs[i].nadc);
/* MADC divider value */
snd_soc_update_bits(codec, AIC31XX_MADC, AIC31XX_PLL_MASK,
aic31xx_divs[i].madc);
/* AOSR value */
snd_soc_write(codec, AIC31XX_AOSR, aic31xx_divs[i].aosr);
/* BCLK N divider */
snd_soc_update_bits(codec, AIC31XX_BCLKN, AIC31XX_PLL_MASK,
aic31xx_divs[i].bclk_n);
return 0;
}
示例5: wm8900_hp_event
static int wm8900_hp_event(struct snd_soc_dapm_widget *w,
struct snd_kcontrol *kcontrol, int event)
{
struct snd_soc_codec *codec = w->codec;
u16 hpctl1 = snd_soc_read(codec, WM8900_REG_HPCTL1);
switch (event) {
case SND_SOC_DAPM_PRE_PMU:
/* Clamp headphone outputs */
hpctl1 = WM8900_REG_HPCTL1_HP_CLAMP_IP |
WM8900_REG_HPCTL1_HP_CLAMP_OP;
snd_soc_write(codec, WM8900_REG_HPCTL1, hpctl1);
break;
case SND_SOC_DAPM_POST_PMU:
/* Enable the input stage */
hpctl1 &= ~WM8900_REG_HPCTL1_HP_CLAMP_IP;
hpctl1 |= WM8900_REG_HPCTL1_HP_SHORT |
WM8900_REG_HPCTL1_HP_SHORT2 |
WM8900_REG_HPCTL1_HP_IPSTAGE_ENA;
snd_soc_write(codec, WM8900_REG_HPCTL1, hpctl1);
msleep(400);
/* Enable the output stage */
hpctl1 &= ~WM8900_REG_HPCTL1_HP_CLAMP_OP;
hpctl1 |= WM8900_REG_HPCTL1_HP_OPSTAGE_ENA;
snd_soc_write(codec, WM8900_REG_HPCTL1, hpctl1);
/* Remove the shorts */
hpctl1 &= ~WM8900_REG_HPCTL1_HP_SHORT2;
snd_soc_write(codec, WM8900_REG_HPCTL1, hpctl1);
hpctl1 &= ~WM8900_REG_HPCTL1_HP_SHORT;
snd_soc_write(codec, WM8900_REG_HPCTL1, hpctl1);
break;
case SND_SOC_DAPM_PRE_PMD:
/* Short the output */
hpctl1 |= WM8900_REG_HPCTL1_HP_SHORT;
snd_soc_write(codec, WM8900_REG_HPCTL1, hpctl1);
/* Disable the output stage */
hpctl1 &= ~WM8900_REG_HPCTL1_HP_OPSTAGE_ENA;
snd_soc_write(codec, WM8900_REG_HPCTL1, hpctl1);
/* Clamp the outputs and power down input */
hpctl1 |= WM8900_REG_HPCTL1_HP_CLAMP_IP |
WM8900_REG_HPCTL1_HP_CLAMP_OP;
hpctl1 &= ~WM8900_REG_HPCTL1_HP_IPSTAGE_ENA;
snd_soc_write(codec, WM8900_REG_HPCTL1, hpctl1);
break;
case SND_SOC_DAPM_POST_PMD:
/* Disable everything */
snd_soc_write(codec, WM8900_REG_HPCTL1, 0);
break;
default:
BUG();
}
return 0;
}
示例6: aic32x4_hw_params
static int aic32x4_hw_params(struct snd_pcm_substream *substream,
struct snd_pcm_hw_params *params,
struct snd_soc_dai *dai)
{
struct snd_soc_codec *codec = dai->codec;
struct aic32x4_priv *aic32x4 = snd_soc_codec_get_drvdata(codec);
u8 data;
int i;
i = aic32x4_get_divs(aic32x4->sysclk, params_rate(params));
if (i < 0) {
printk(KERN_ERR "aic32x4: sampling rate not supported\n");
return i;
}
snd_soc_write(codec, AIC32X4_CLKMUX, AIC32X4_PLLCLKIN);
snd_soc_write(codec, AIC32X4_IFACE3, AIC32X4_DACMOD2BCLK);
data = snd_soc_read(codec, AIC32X4_PLLPR);
data &= ~(7 << 4);
snd_soc_write(codec, AIC32X4_PLLPR,
(data | (aic32x4_divs[i].p_val << 4) | 0x01));
snd_soc_write(codec, AIC32X4_PLLJ, aic32x4_divs[i].pll_j);
snd_soc_write(codec, AIC32X4_PLLDMSB, (aic32x4_divs[i].pll_d >> 8));
snd_soc_write(codec, AIC32X4_PLLDLSB,
(aic32x4_divs[i].pll_d & 0xff));
data = snd_soc_read(codec, AIC32X4_NDAC);
data &= ~(0x7f);
snd_soc_write(codec, AIC32X4_NDAC, data | aic32x4_divs[i].ndac);
data = snd_soc_read(codec, AIC32X4_MDAC);
data &= ~(0x7f);
snd_soc_write(codec, AIC32X4_MDAC, data | aic32x4_divs[i].mdac);
snd_soc_write(codec, AIC32X4_DOSRMSB, aic32x4_divs[i].dosr >> 8);
snd_soc_write(codec, AIC32X4_DOSRLSB,
(aic32x4_divs[i].dosr & 0xff));
data = snd_soc_read(codec, AIC32X4_NADC);
data &= ~(0x7f);
snd_soc_write(codec, AIC32X4_NADC, data | aic32x4_divs[i].nadc);
data = snd_soc_read(codec, AIC32X4_MADC);
data &= ~(0x7f);
snd_soc_write(codec, AIC32X4_MADC, data | aic32x4_divs[i].madc);
snd_soc_write(codec, AIC32X4_AOSR, aic32x4_divs[i].aosr);
data = snd_soc_read(codec, AIC32X4_BCLKN);
data &= ~(0x7f);
snd_soc_write(codec, AIC32X4_BCLKN, data | aic32x4_divs[i].blck_N);
data = snd_soc_read(codec, AIC32X4_IFACE1);
data = data & ~(3 << 4);
switch (params_format(params)) {
case SNDRV_PCM_FORMAT_S16_LE:
break;
case SNDRV_PCM_FORMAT_S20_3LE:
data |= (AIC32X4_WORD_LEN_20BITS << AIC32X4_DOSRMSB_SHIFT);
break;
case SNDRV_PCM_FORMAT_S24_LE:
data |= (AIC32X4_WORD_LEN_24BITS << AIC32X4_DOSRMSB_SHIFT);
break;
case SNDRV_PCM_FORMAT_S32_LE:
data |= (AIC32X4_WORD_LEN_32BITS << AIC32X4_DOSRMSB_SHIFT);
break;
}
snd_soc_write(codec, AIC32X4_IFACE1, data);
return 0;
}
示例7: hpdrv_ev
static int hpdrv_ev(struct snd_soc_dapm_widget *w,
struct snd_kcontrol *kcontrol, int event)
{
dev_dbg(w->codec->dev, "%s called, event = %d\n", __func__, event);
switch (event) {
case SND_SOC_DAPM_PRE_PMU:
cod3022x_hp_playback_init(w->codec);
break;
case SND_SOC_DAPM_POST_PMU:
snd_soc_update_bits(w->codec, COD3022X_17_PWAUTO_DA,
PW_AUTO_DA_MASK | APW_HP_MASK,
(0x1 << PW_AUTO_DA_SHIFT) |
(0x1 << APW_HP_SHIFT));
msleep(10);
snd_soc_update_bits(w->codec, COD3022X_1C_SV_DA,
EN_HP_SV_MASK, 0);
cod3022x_usleep(100);
snd_soc_write(w->codec, COD3022X_30_VOL_HPL, 0x1E);
snd_soc_write(w->codec, COD3022X_31_VOL_HPR, 0x1E);
cod3022x_usleep(100);
snd_soc_update_bits(w->codec, COD3022X_1C_SV_DA,
EN_HP_SV_MASK,
0x1 << EN_HP_SV_SHIFT);
cod3022x_usleep(100);
snd_soc_write(w->codec, COD3022X_30_VOL_HPL, 0x18);
snd_soc_write(w->codec, COD3022X_31_VOL_HPR, 0x18);
cod3022x_usleep(100);
/* Limiter level selection -0.2dB (defult) */
snd_soc_update_bits(w->codec, COD3022X_54_DNC1,
EN_DNC_MASK | DNC_START_GAIN_MASK |
DNC_LIMIT_SEL_MASK,
((0x1 << EN_DNC_SHIFT) |
(0x1 < DNC_START_GAIN_SHIFT) | 0x1));
break;
case SND_SOC_DAPM_PRE_PMD:
snd_soc_update_bits(w->codec, COD3022X_54_DNC1,
EN_DNC_MASK , 0);
cod3022x_usleep(100);
snd_soc_write(w->codec, COD3022X_30_VOL_HPL, 0x1E);
snd_soc_write(w->codec, COD3022X_31_VOL_HPR, 0x1E);
cod3022x_usleep(100);
snd_soc_update_bits(w->codec, COD3022X_1C_SV_DA,
EN_HP_SV_MASK, 0);
cod3022x_usleep(100);
snd_soc_write(w->codec, COD3022X_30_VOL_HPL, 0x26);
snd_soc_write(w->codec, COD3022X_31_VOL_HPR, 0x26);
cod3022x_usleep(100);
snd_soc_update_bits(w->codec, COD3022X_1C_SV_DA,
EN_HP_SV_MASK,
0x1 << EN_HP_SV_SHIFT);
cod3022x_usleep(100);
snd_soc_update_bits(w->codec, COD3022X_17_PWAUTO_DA,
PW_AUTO_DA_MASK | APW_HP_MASK, 0);
cod3022x_usleep(100);
snd_soc_update_bits(w->codec, COD3022X_36_MIX_DA1,
EN_HP_MIXL_DCTL_MASK | EN_HP_MIXR_DCTR_MASK, 0);
break;
default:
break;
}
return 0;
}
示例8: wm9081_set_fll
static int wm9081_set_fll(struct snd_soc_codec *codec, int fll_id,
unsigned int Fref, unsigned int Fout)
{
struct wm9081_priv *wm9081 = snd_soc_codec_get_drvdata(codec);
u16 reg1, reg4, reg5;
struct _fll_div fll_div;
int ret;
int clk_sys_reg;
/* Any change? */
if (Fref == wm9081->fll_fref && Fout == wm9081->fll_fout)
return 0;
/* Disable the FLL */
if (Fout == 0) {
dev_dbg(codec->dev, "FLL disabled\n");
wm9081->fll_fref = 0;
wm9081->fll_fout = 0;
return 0;
}
ret = fll_factors(&fll_div, Fref, Fout);
if (ret != 0)
return ret;
reg5 = snd_soc_read(codec, WM9081_FLL_CONTROL_5);
reg5 &= ~WM9081_FLL_CLK_SRC_MASK;
switch (fll_id) {
case WM9081_SYSCLK_FLL_MCLK:
reg5 |= 0x1;
break;
default:
dev_err(codec->dev, "Unknown FLL ID %d\n", fll_id);
return -EINVAL;
}
/* Disable CLK_SYS while we reconfigure */
clk_sys_reg = snd_soc_read(codec, WM9081_CLOCK_CONTROL_3);
if (clk_sys_reg & WM9081_CLK_SYS_ENA)
snd_soc_write(codec, WM9081_CLOCK_CONTROL_3,
clk_sys_reg & ~WM9081_CLK_SYS_ENA);
/* Any FLL configuration change requires that the FLL be
* disabled first. */
reg1 = snd_soc_read(codec, WM9081_FLL_CONTROL_1);
reg1 &= ~WM9081_FLL_ENA;
snd_soc_write(codec, WM9081_FLL_CONTROL_1, reg1);
/* Apply the configuration */
if (fll_div.k)
reg1 |= WM9081_FLL_FRAC_MASK;
else
reg1 &= ~WM9081_FLL_FRAC_MASK;
snd_soc_write(codec, WM9081_FLL_CONTROL_1, reg1);
snd_soc_write(codec, WM9081_FLL_CONTROL_2,
(fll_div.fll_outdiv << WM9081_FLL_OUTDIV_SHIFT) |
(fll_div.fll_fratio << WM9081_FLL_FRATIO_SHIFT));
snd_soc_write(codec, WM9081_FLL_CONTROL_3, fll_div.k);
reg4 = snd_soc_read(codec, WM9081_FLL_CONTROL_4);
reg4 &= ~WM9081_FLL_N_MASK;
reg4 |= fll_div.n << WM9081_FLL_N_SHIFT;
snd_soc_write(codec, WM9081_FLL_CONTROL_4, reg4);
reg5 &= ~WM9081_FLL_CLK_REF_DIV_MASK;
reg5 |= fll_div.fll_clk_ref_div << WM9081_FLL_CLK_REF_DIV_SHIFT;
snd_soc_write(codec, WM9081_FLL_CONTROL_5, reg5);
/* Set gain to the recommended value */
snd_soc_update_bits(codec, WM9081_FLL_CONTROL_4,
WM9081_FLL_GAIN_MASK, 0);
/* Enable the FLL */
snd_soc_write(codec, WM9081_FLL_CONTROL_1, reg1 | WM9081_FLL_ENA);
/* Then bring CLK_SYS up again if it was disabled */
if (clk_sys_reg & WM9081_CLK_SYS_ENA)
snd_soc_write(codec, WM9081_CLOCK_CONTROL_3, clk_sys_reg);
dev_dbg(codec->dev, "FLL enabled at %dHz->%dHz\n", Fref, Fout);
wm9081->fll_fref = Fref;
wm9081->fll_fout = Fout;
return 0;
}
示例9: STA381xx_resume
static int STA381xx_resume(struct snd_soc_codec *codec)
{
snd_soc_write(codec, STA381xx_MAPSEL, 0x00);
STA381xx_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
return 0;
}
示例10: STA381xx_probe
static int STA381xx_probe(struct snd_soc_codec *codec)
{
struct STA381xx_priv *STA381xx = snd_soc_codec_get_drvdata(codec);
int i, ret = 0;
ret = snd_soc_codec_set_cache_io(codec, 8, 8, SND_SOC_I2C);
if (ret != 0) {
dev_err(codec->dev, "Failed to set cache I/O: %d\n", ret);
return ret;
}
STA381xx->codec = codec;
/* Chip documentation explicitly requires that the reset values
* of reserved register bits are left untouched.
* Write the register default value to cache for reserved registers,
* so the write to the these registers are suppressed by the cache
* restore code when it skips writes of default registers.
*/
snd_soc_write(codec, STA381xx_MAPSEL, 0x00);
snd_soc_write(codec, STA381xx_CONFA, 0x67);
snd_soc_write(codec, STA381xx_CONFB, 0x80);
snd_soc_write(codec, STA381xx_CONFC, 0x9F);
snd_soc_write(codec, STA381xx_CONFD, 0x18);
snd_soc_write(codec, STA381xx_CONFE, 0x82);
snd_soc_write(codec, STA381xx_CONFF, 0x5D);
snd_soc_write(codec, STA381xx_MMUTE, 0x40);
snd_soc_write(codec, STA381xx_MVOL, 0xFE);
snd_soc_write(codec, STA381xx_C1VOL, 0x47);
snd_soc_write(codec, STA381xx_C2VOL, 0x47);
snd_soc_write(codec, STA381xx_C3VOL, 0x56);
snd_soc_write(codec, STA381xx_C1CFG, 0x00);
snd_soc_write(codec, STA381xx_C2CFG, 0x40);
snd_soc_write(codec, STA381xx_C3CFG, 0x80);
snd_soc_write(codec, STA381xx_C1CFG, 0x00);
//subwoofer
snd_soc_write(codec, STA381xx_TONE, 0x7F);
snd_soc_write(codec, STA381xx_AUTO2, 0x70);
snd_soc_update_bits(codec, STA381xx_CONFF,
STA381xx_CONFF_EAPD, STA381xx_CONFF_EAPD);
snd_soc_write(codec, STA381xx_MVOL, 0x00);
//snd_soc_write(codec, STA381xx_F3XCON2, 0x6D);
//snd_soc_write(codec, STA381xx_HPCONFIG, 0x09);
/* set thermal warning adjustment and recovery */
//if (!(STA381xx->pdata->thermal_conf & STA381xx_THERMAL_ADJUSTMENT_ENABLE))
// thermal |= STA381xx_CONFA_TWAB;
//if (!(STA381xx->pdata->thermal_conf & STA381xx_THERMAL_RECOVERY_ENABLE))
// thermal |= STA381xx_CONFA_TWRB;
//snd_soc_update_bits(codec, STA381xx_CONFA,
// STA381xx_CONFA_TWAB | STA381xx_CONFA_TWRB,
// thermal);
#if 0
/* select output configuration */
snd_soc_update_bits(codec, STA381xx_CONFF,
STA381xx_CONFF_OCFG_MASK,
STA381xx->pdata->output_conf
<< STA381xx_CONFF_OCFG_SHIFT);
/* channel to output mapping */
snd_soc_update_bits(codec, STA381xx_C1CFG,
STA381xx_CxCFG_OM_MASK,
STA381xx->pdata->ch1_output_mapping
<< STA381xx_CxCFG_OM_SHIFT);
snd_soc_update_bits(codec, STA381xx_C2CFG,
STA381xx_CxCFG_OM_MASK,
STA381xx->pdata->ch2_output_mapping
<< STA381xx_CxCFG_OM_SHIFT);
snd_soc_update_bits(codec, STA381xx_C3CFG,
STA381xx_CxCFG_OM_MASK,
STA381xx->pdata->ch3_output_mapping
<< STA381xx_CxCFG_OM_SHIFT);
#endif
/* initialize coefficient shadow RAM with reset values */
for (i = 4; i <= 39; i += 5)
STA381xx->coef_shadow[i] = 0x100000;
for (i = 44; i <= 49; i += 5)
STA381xx->coef_shadow[i] = 0x400000;
for (i = 50; i <= 54; i++)
STA381xx->coef_shadow[i] = 0x7fffff;
STA381xx->coef_shadow[55] = 0x5a9df7;
STA381xx->coef_shadow[56] = 0x7fffff;
STA381xx->coef_shadow[59] = 0x7fffff;
STA381xx->coef_shadow[60] = 0x400000;
STA381xx->coef_shadow[61] = 0x400000;
STA381xx_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
/* Bias level configuration will have done an extra enable */
//regulator_bulk_disable(ARRAY_SIZE(STA381xx->supplies), STA381xx->supplies);
return 0;
}
示例11: cs42l51_hw_params
//.........这里部分代码省略.........
int intf_ctl, power_ctl, fmt;
switch (cs42l51->func) {
case MODE_MASTER:
return -EINVAL;
case MODE_SLAVE:
ratios = slave_ratios;
nr_ratios = ARRAY_SIZE(slave_ratios);
break;
case MODE_SLAVE_AUTO:
ratios = slave_auto_ratios;
nr_ratios = ARRAY_SIZE(slave_auto_ratios);
break;
}
rate = params_rate(params);
ratio = cs42l51->mclk / rate;
for (i = 0; i < nr_ratios; i++) {
if (ratios[i].ratio == ratio)
break;
}
if (i == nr_ratios) {
dev_err(codec->dev, "could not find matching ratio\n");
return -EINVAL;
}
intf_ctl = snd_soc_read(codec, CS42L51_INTF_CTL);
power_ctl = snd_soc_read(codec, CS42L51_MIC_POWER_CTL);
intf_ctl &= ~(CS42L51_INTF_CTL_MASTER | CS42L51_INTF_CTL_ADC_I2S
| CS42L51_INTF_CTL_DAC_FORMAT(7));
power_ctl &= ~(CS42L51_MIC_POWER_CTL_SPEED(3)
| CS42L51_MIC_POWER_CTL_MCLK_DIV2);
switch (cs42l51->func) {
case MODE_MASTER:
intf_ctl |= CS42L51_INTF_CTL_MASTER;
power_ctl |= CS42L51_MIC_POWER_CTL_SPEED(ratios[i].speed_mode);
break;
case MODE_SLAVE:
power_ctl |= CS42L51_MIC_POWER_CTL_SPEED(ratios[i].speed_mode);
break;
case MODE_SLAVE_AUTO:
power_ctl |= CS42L51_MIC_POWER_CTL_AUTO;
break;
}
switch (cs42l51->audio_mode) {
case SND_SOC_DAIFMT_I2S:
intf_ctl |= CS42L51_INTF_CTL_ADC_I2S;
intf_ctl |= CS42L51_INTF_CTL_DAC_FORMAT(CS42L51_DAC_DIF_I2S);
break;
case SND_SOC_DAIFMT_LEFT_J:
intf_ctl |= CS42L51_INTF_CTL_DAC_FORMAT(CS42L51_DAC_DIF_LJ24);
break;
case SND_SOC_DAIFMT_RIGHT_J:
switch (params_format(params)) {
case SNDRV_PCM_FORMAT_S16_LE:
case SNDRV_PCM_FORMAT_S16_BE:
fmt = CS42L51_DAC_DIF_RJ16;
break;
case SNDRV_PCM_FORMAT_S18_3LE:
case SNDRV_PCM_FORMAT_S18_3BE:
fmt = CS42L51_DAC_DIF_RJ18;
break;
case SNDRV_PCM_FORMAT_S20_3LE:
case SNDRV_PCM_FORMAT_S20_3BE:
fmt = CS42L51_DAC_DIF_RJ20;
break;
case SNDRV_PCM_FORMAT_S24_LE:
case SNDRV_PCM_FORMAT_S24_BE:
fmt = CS42L51_DAC_DIF_RJ24;
break;
default:
dev_err(codec->dev, "unknown format\n");
return -EINVAL;
}
intf_ctl |= CS42L51_INTF_CTL_DAC_FORMAT(fmt);
break;
default:
dev_err(codec->dev, "unknown format\n");
return -EINVAL;
}
if (ratios[i].mclk)
power_ctl |= CS42L51_MIC_POWER_CTL_MCLK_DIV2;
ret = snd_soc_write(codec, CS42L51_INTF_CTL, intf_ctl);
if (ret < 0)
return ret;
ret = snd_soc_write(codec, CS42L51_MIC_POWER_CTL, power_ctl);
if (ret < 0)
return ret;
return 0;
}
示例12: aic31xx_setup_pll
static int aic31xx_setup_pll(struct snd_soc_codec *codec,
struct snd_pcm_hw_params *params)
{
struct aic31xx_priv *aic31xx = snd_soc_codec_get_drvdata(codec);
int bclk_score = snd_soc_params_to_frame_size(params);
int mclk_p = aic31xx->sysclk / aic31xx->p_div;
int bclk_n = 0;
int match = -1;
int i;
/* Use PLL as CODEC_CLKIN and DAC_CLK as BDIV_CLKIN */
snd_soc_update_bits(codec, AIC31XX_CLKMUX,
AIC31XX_CODEC_CLKIN_MASK, AIC31XX_CODEC_CLKIN_PLL);
snd_soc_update_bits(codec, AIC31XX_IFACE2,
AIC31XX_BDIVCLK_MASK, AIC31XX_DAC2BCLK);
for (i = 0; i < ARRAY_SIZE(aic31xx_divs); i++) {
if (aic31xx_divs[i].rate == params_rate(params) &&
aic31xx_divs[i].mclk_p == mclk_p) {
int s = (aic31xx_divs[i].dosr * aic31xx_divs[i].mdac) %
snd_soc_params_to_frame_size(params);
int bn = (aic31xx_divs[i].dosr * aic31xx_divs[i].mdac) /
snd_soc_params_to_frame_size(params);
if (s < bclk_score && bn > 0) {
match = i;
bclk_n = bn;
bclk_score = s;
}
}
}
if (match == -1) {
dev_err(codec->dev,
"%s: Sample rate (%u) and format not supported\n",
__func__, params_rate(params));
/* See bellow for details how fix this. */
return -EINVAL;
}
if (bclk_score != 0) {
dev_warn(codec->dev, "Can not produce exact bitclock");
/* This is fine if using dsp format, but if using i2s
there may be trouble. To fix the issue edit the
aic31xx_divs table for your mclk and sample
rate. Details can be found from:
http://www.ti.com/lit/ds/symlink/tlv320aic3100.pdf
Section: 5.6 CLOCK Generation and PLL
*/
}
i = match;
/* PLL configuration */
snd_soc_update_bits(codec, AIC31XX_PLLPR, AIC31XX_PLL_MASK,
(aic31xx->p_div << 4) | 0x01);
snd_soc_write(codec, AIC31XX_PLLJ, aic31xx_divs[i].pll_j);
snd_soc_write(codec, AIC31XX_PLLDMSB,
aic31xx_divs[i].pll_d >> 8);
snd_soc_write(codec, AIC31XX_PLLDLSB,
aic31xx_divs[i].pll_d & 0xff);
/* DAC dividers configuration */
snd_soc_update_bits(codec, AIC31XX_NDAC, AIC31XX_PLL_MASK,
aic31xx_divs[i].ndac);
snd_soc_update_bits(codec, AIC31XX_MDAC, AIC31XX_PLL_MASK,
aic31xx_divs[i].mdac);
snd_soc_write(codec, AIC31XX_DOSRMSB, aic31xx_divs[i].dosr >> 8);
snd_soc_write(codec, AIC31XX_DOSRLSB, aic31xx_divs[i].dosr & 0xff);
/* ADC dividers configuration. Write reset value 1 if not used. */
snd_soc_update_bits(codec, AIC31XX_NADC, AIC31XX_PLL_MASK,
aic31xx_divs[i].nadc ? aic31xx_divs[i].nadc : 1);
snd_soc_update_bits(codec, AIC31XX_MADC, AIC31XX_PLL_MASK,
aic31xx_divs[i].madc ? aic31xx_divs[i].madc : 1);
snd_soc_write(codec, AIC31XX_AOSR, aic31xx_divs[i].aosr);
/* Bit clock divider configuration. */
snd_soc_update_bits(codec, AIC31XX_BCLKN,
AIC31XX_PLL_MASK, bclk_n);
aic31xx->rate_div_line = i;
dev_dbg(codec->dev,
"pll %d.%04d/%d dosr %d n %d m %d aosr %d n %d m %d bclk_n %d\n",
aic31xx_divs[i].pll_j, aic31xx_divs[i].pll_d,
aic31xx->p_div, aic31xx_divs[i].dosr,
aic31xx_divs[i].ndac, aic31xx_divs[i].mdac,
aic31xx_divs[i].aosr, aic31xx_divs[i].nadc,
aic31xx_divs[i].madc, bclk_n);
return 0;
}
示例13: wm8961_set_fmt
static int wm8961_set_fmt(struct snd_soc_dai *dai, unsigned int fmt)
{
struct snd_soc_codec *codec = dai->codec;
u16 aif = snd_soc_read(codec, WM8961_AUDIO_INTERFACE_0);
aif &= ~(WM8961_BCLKINV | WM8961_LRP |
WM8961_MS | WM8961_FORMAT_MASK);
switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) {
case SND_SOC_DAIFMT_CBM_CFM:
aif |= WM8961_MS;
break;
case SND_SOC_DAIFMT_CBS_CFS:
break;
default:
return -EINVAL;
}
switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
case SND_SOC_DAIFMT_RIGHT_J:
break;
case SND_SOC_DAIFMT_LEFT_J:
aif |= 1;
break;
case SND_SOC_DAIFMT_I2S:
aif |= 2;
break;
case SND_SOC_DAIFMT_DSP_B:
aif |= WM8961_LRP;
case SND_SOC_DAIFMT_DSP_A:
aif |= 3;
switch (fmt & SND_SOC_DAIFMT_INV_MASK) {
case SND_SOC_DAIFMT_NB_NF:
case SND_SOC_DAIFMT_IB_NF:
break;
default:
return -EINVAL;
}
break;
default:
return -EINVAL;
}
switch (fmt & SND_SOC_DAIFMT_INV_MASK) {
case SND_SOC_DAIFMT_NB_NF:
break;
case SND_SOC_DAIFMT_NB_IF:
aif |= WM8961_LRP;
break;
case SND_SOC_DAIFMT_IB_NF:
aif |= WM8961_BCLKINV;
break;
case SND_SOC_DAIFMT_IB_IF:
aif |= WM8961_BCLKINV | WM8961_LRP;
break;
default:
return -EINVAL;
}
return snd_soc_write(codec, WM8961_AUDIO_INTERFACE_0, aif);
}
示例14: sn95031_enable_jack_btn
static inline void sn95031_enable_jack_btn(struct snd_soc_codec *codec)
{
snd_soc_write(codec, SN95031_BTNCTRL1, 0x77);
snd_soc_write(codec, SN95031_BTNCTRL2, 0x01);
}
示例15: configure_clock
static int configure_clock(struct snd_soc_codec *codec)
{
struct wm9081_priv *wm9081 = snd_soc_codec_get_drvdata(codec);
int new_sysclk, i, target;
unsigned int reg;
int ret = 0;
int mclkdiv = 0;
int fll = 0;
switch (wm9081->sysclk_source) {
case WM9081_SYSCLK_MCLK:
if (wm9081->mclk_rate > 12225000) {
mclkdiv = 1;
wm9081->sysclk_rate = wm9081->mclk_rate / 2;
} else {
wm9081->sysclk_rate = wm9081->mclk_rate;
}
wm9081_set_fll(codec, WM9081_SYSCLK_FLL_MCLK, 0, 0);
break;
case WM9081_SYSCLK_FLL_MCLK:
/* If we have a sample rate calculate a CLK_SYS that
* gives us a suitable DAC configuration, plus BCLK.
* Ideally we would check to see if we can clock
* directly from MCLK and only use the FLL if this is
* not the case, though care must be taken with free
* running mode.
*/
if (wm9081->master && wm9081->bclk) {
/* Make sure we can generate CLK_SYS and BCLK
* and that we've got 3MHz for optimal
* performance. */
for (i = 0; i < ARRAY_SIZE(clk_sys_rates); i++) {
target = wm9081->fs * clk_sys_rates[i].ratio;
new_sysclk = target;
if (target >= wm9081->bclk &&
target > 3000000)
break;
}
if (i == ARRAY_SIZE(clk_sys_rates))
return -EINVAL;
} else if (wm9081->fs) {
for (i = 0; i < ARRAY_SIZE(clk_sys_rates); i++) {
new_sysclk = clk_sys_rates[i].ratio
* wm9081->fs;
if (new_sysclk > 3000000)
break;
}
if (i == ARRAY_SIZE(clk_sys_rates))
return -EINVAL;
} else {
new_sysclk = 12288000;
}
ret = wm9081_set_fll(codec, WM9081_SYSCLK_FLL_MCLK,
wm9081->mclk_rate, new_sysclk);
if (ret == 0) {
wm9081->sysclk_rate = new_sysclk;
/* Switch SYSCLK over to FLL */
fll = 1;
} else {
wm9081->sysclk_rate = wm9081->mclk_rate;
}
break;
default:
return -EINVAL;
}
reg = snd_soc_read(codec, WM9081_CLOCK_CONTROL_1);
if (mclkdiv)
reg |= WM9081_MCLKDIV2;
else
reg &= ~WM9081_MCLKDIV2;
snd_soc_write(codec, WM9081_CLOCK_CONTROL_1, reg);
reg = snd_soc_read(codec, WM9081_CLOCK_CONTROL_3);
if (fll)
reg |= WM9081_CLK_SRC_SEL;
else
reg &= ~WM9081_CLK_SRC_SEL;
snd_soc_write(codec, WM9081_CLOCK_CONTROL_3, reg);
dev_dbg(codec->dev, "CLK_SYS is %dHz\n", wm9081->sysclk_rate);
return ret;
}