Commit c5e64c76 authored by Mark Brown's avatar Mark Brown

Merge remote-tracking branches 'asoc/topic/tlv', 'asoc/topic/tlv320aic23',...

Merge remote-tracking branches 'asoc/topic/tlv', 'asoc/topic/tlv320aic23', 'asoc/topic/tlv320aic31xx' and 'asoc/topic/tlv320aic32x4' into asoc-next
......@@ -31,10 +31,15 @@ typedef int (snd_kcontrol_info_t) (struct snd_kcontrol * kcontrol, struct snd_ct
typedef int (snd_kcontrol_get_t) (struct snd_kcontrol * kcontrol, struct snd_ctl_elem_value * ucontrol);
typedef int (snd_kcontrol_put_t) (struct snd_kcontrol * kcontrol, struct snd_ctl_elem_value * ucontrol);
typedef int (snd_kcontrol_tlv_rw_t)(struct snd_kcontrol *kcontrol,
int op_flag, /* 0=read,1=write,-1=command */
int op_flag, /* SNDRV_CTL_TLV_OP_XXX */
unsigned int size,
unsigned int __user *tlv);
enum {
SNDRV_CTL_TLV_OP_READ = 0,
SNDRV_CTL_TLV_OP_WRITE = 1,
SNDRV_CTL_TLV_OP_CMD = -1,
};
struct snd_kcontrol_new {
snd_ctl_elem_iface_t iface; /* interface identifier */
......
......@@ -272,7 +272,14 @@
.get = xhandler_get, .put = xhandler_put, \
.private_value = (unsigned long)&(struct soc_bytes_ext) \
{.max = xcount} }
#define SND_SOC_BYTES_TLV(xname, xcount, xhandler_get, xhandler_put) \
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \
.access = SNDRV_CTL_ELEM_ACCESS_TLV_READWRITE | \
SNDRV_CTL_ELEM_ACCESS_TLV_CALLBACK, \
.tlv.c = (snd_soc_bytes_tlv_callback), \
.info = snd_soc_info_bytes_ext, \
.private_value = (unsigned long)&(struct soc_bytes_ext) \
{.max = xcount, .get = xhandler_get, .put = xhandler_put, } }
#define SOC_SINGLE_XR_SX(xname, xregbase, xregcount, xnbits, \
xmin, xmax, xinvert) \
{ .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = (xname), \
......@@ -560,6 +567,8 @@ int snd_soc_bytes_put(struct snd_kcontrol *kcontrol,
struct snd_ctl_elem_value *ucontrol);
int snd_soc_bytes_info_ext(struct snd_kcontrol *kcontrol,
struct snd_ctl_elem_info *ucontrol);
int snd_soc_bytes_tlv_callback(struct snd_kcontrol *kcontrol, int op_flag,
unsigned int size, unsigned int __user *tlv);
int snd_soc_info_xr_sx(struct snd_kcontrol *kcontrol,
struct snd_ctl_elem_info *uinfo);
int snd_soc_get_xr_sx(struct snd_kcontrol *kcontrol,
......@@ -1132,6 +1141,9 @@ struct soc_bytes {
struct soc_bytes_ext {
int max;
/* used for TLV byte control */
int (*get)(unsigned int __user *bytes, unsigned int size);
int (*put)(const unsigned int __user *bytes, unsigned int size);
};
/* multi register control */
......
......@@ -1406,11 +1406,11 @@ static long snd_ctl_ioctl(struct file *file, unsigned int cmd, unsigned long arg
case SNDRV_CTL_IOCTL_SUBSCRIBE_EVENTS:
return snd_ctl_subscribe_events(ctl, ip);
case SNDRV_CTL_IOCTL_TLV_READ:
return snd_ctl_tlv_ioctl(ctl, argp, 0);
return snd_ctl_tlv_ioctl(ctl, argp, SNDRV_CTL_TLV_OP_READ);
case SNDRV_CTL_IOCTL_TLV_WRITE:
return snd_ctl_tlv_ioctl(ctl, argp, 1);
return snd_ctl_tlv_ioctl(ctl, argp, SNDRV_CTL_TLV_OP_WRITE);
case SNDRV_CTL_IOCTL_TLV_COMMAND:
return snd_ctl_tlv_ioctl(ctl, argp, -1);
return snd_ctl_tlv_ioctl(ctl, argp, SNDRV_CTL_TLV_OP_CMD);
case SNDRV_CTL_IOCTL_POWER:
return -ENOPROTOOPT;
case SNDRV_CTL_IOCTL_POWER_STATE:
......
......@@ -564,7 +564,9 @@ config SND_SOC_TLV320AIC26
depends on SPI
config SND_SOC_TLV320AIC31XX
tristate
tristate "Texas Instruments TLV320AIC31xx CODECs"
depends on I2C
select REGMAP_I2C
config SND_SOC_TLV320AIC32X4
tristate
......
......@@ -364,16 +364,16 @@ static int tlv320aic23_hw_params(struct snd_pcm_substream *substream,
iface_reg = snd_soc_read(codec, TLV320AIC23_DIGT_FMT) & ~(0x03 << 2);
switch (params_format(params)) {
case SNDRV_PCM_FORMAT_S16_LE:
switch (params_width(params)) {
case 16:
break;
case SNDRV_PCM_FORMAT_S20_3LE:
case 20:
iface_reg |= (0x01 << 2);
break;
case SNDRV_PCM_FORMAT_S24_LE:
case 24:
iface_reg |= (0x02 << 2);
break;
case SNDRV_PCM_FORMAT_S32_LE:
case 32:
iface_reg |= (0x03 << 2);
break;
}
......
......@@ -249,17 +249,16 @@ static const char * const mic_select_text[] = {
"Off", "FFR 10 Ohm", "FFR 20 Ohm", "FFR 40 Ohm"
};
static const
SOC_ENUM_SINGLE_DECL(mic1lp_p_enum, AIC31XX_MICPGAPI, 6, mic_select_text);
static const
SOC_ENUM_SINGLE_DECL(mic1rp_p_enum, AIC31XX_MICPGAPI, 4, mic_select_text);
static const
SOC_ENUM_SINGLE_DECL(mic1lm_p_enum, AIC31XX_MICPGAPI, 2, mic_select_text);
static const
SOC_ENUM_SINGLE_DECL(cm_m_enum, AIC31XX_MICPGAMI, 6, mic_select_text);
static const
SOC_ENUM_SINGLE_DECL(mic1lm_m_enum, AIC31XX_MICPGAMI, 4, mic_select_text);
static SOC_ENUM_SINGLE_DECL(mic1lp_p_enum, AIC31XX_MICPGAPI, 6,
mic_select_text);
static SOC_ENUM_SINGLE_DECL(mic1rp_p_enum, AIC31XX_MICPGAPI, 4,
mic_select_text);
static SOC_ENUM_SINGLE_DECL(mic1lm_p_enum, AIC31XX_MICPGAPI, 2,
mic_select_text);
static SOC_ENUM_SINGLE_DECL(cm_m_enum, AIC31XX_MICPGAMI, 6, mic_select_text);
static SOC_ENUM_SINGLE_DECL(mic1lm_m_enum, AIC31XX_MICPGAMI, 4,
mic_select_text);
static const DECLARE_TLV_DB_SCALE(dac_vol_tlv, -6350, 50, 0);
static const DECLARE_TLV_DB_SCALE(adc_fgain_tlv, 0, 10, 0);
......@@ -329,6 +328,7 @@ static int aic31xx_wait_bits(struct aic31xx_priv *aic31xx, unsigned int reg,
unsigned int bits;
int counter = count;
int ret = regmap_read(aic31xx->regmap, reg, &bits);
while ((bits & mask) != wbits && counter && !ret) {
usleep_range(sleep, sleep * 2);
ret = regmap_read(aic31xx->regmap, reg, &bits);
......@@ -435,6 +435,7 @@ static int mic_bias_event(struct snd_soc_dapm_widget *w,
{
struct snd_soc_codec *codec = w->codec;
struct aic31xx_priv *aic31xx = snd_soc_codec_get_drvdata(codec);
switch (event) {
case SND_SOC_DAPM_POST_PMU:
/* change mic bias voltage to user defined */
......
......@@ -626,32 +626,33 @@ static int aic32x4_probe(struct snd_soc_codec *codec)
snd_soc_write(codec, AIC32X4_MICBIAS, AIC32X4_MICBIAS_LDOIN |
AIC32X4_MICBIAS_2075V);
}
if (aic32x4->power_cfg & AIC32X4_PWR_AVDD_DVDD_WEAK_DISABLE) {
if (aic32x4->power_cfg & AIC32X4_PWR_AVDD_DVDD_WEAK_DISABLE)
snd_soc_write(codec, AIC32X4_PWRCFG, AIC32X4_AVDDWEAKDISABLE);
}
tmp_reg = (aic32x4->power_cfg & AIC32X4_PWR_AIC32X4_LDO_ENABLE) ?
AIC32X4_LDOCTLEN : 0;
snd_soc_write(codec, AIC32X4_LDOCTL, tmp_reg);
tmp_reg = snd_soc_read(codec, AIC32X4_CMMODE);
if (aic32x4->power_cfg & AIC32X4_PWR_CMMODE_LDOIN_RANGE_18_36) {
if (aic32x4->power_cfg & AIC32X4_PWR_CMMODE_LDOIN_RANGE_18_36)
tmp_reg |= AIC32X4_LDOIN_18_36;
}
if (aic32x4->power_cfg & AIC32X4_PWR_CMMODE_HP_LDOIN_POWERED) {
if (aic32x4->power_cfg & AIC32X4_PWR_CMMODE_HP_LDOIN_POWERED)
tmp_reg |= AIC32X4_LDOIN2HP;
}
snd_soc_write(codec, AIC32X4_CMMODE, tmp_reg);
/* Mic PGA routing */
if (aic32x4->micpga_routing & AIC32X4_MICPGA_ROUTE_LMIC_IN2R_10K)
snd_soc_write(codec, AIC32X4_LMICPGANIN, AIC32X4_LMICPGANIN_IN2R_10K);
snd_soc_write(codec, AIC32X4_LMICPGANIN,
AIC32X4_LMICPGANIN_IN2R_10K);
else
snd_soc_write(codec, AIC32X4_LMICPGANIN, AIC32X4_LMICPGANIN_CM1L_10K);
snd_soc_write(codec, AIC32X4_LMICPGANIN,
AIC32X4_LMICPGANIN_CM1L_10K);
if (aic32x4->micpga_routing & AIC32X4_MICPGA_ROUTE_RMIC_IN1L_10K)
snd_soc_write(codec, AIC32X4_RMICPGANIN, AIC32X4_RMICPGANIN_IN1L_10K);
snd_soc_write(codec, AIC32X4_RMICPGANIN,
AIC32X4_RMICPGANIN_IN1L_10K);
else
snd_soc_write(codec, AIC32X4_RMICPGANIN, AIC32X4_RMICPGANIN_CM1R_10K);
snd_soc_write(codec, AIC32X4_RMICPGANIN,
AIC32X4_RMICPGANIN_CM1R_10K);
aic32x4_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
......
......@@ -3289,6 +3289,27 @@ int snd_soc_bytes_info_ext(struct snd_kcontrol *kcontrol,
}
EXPORT_SYMBOL_GPL(snd_soc_bytes_info_ext);
int snd_soc_bytes_tlv_callback(struct snd_kcontrol *kcontrol, int op_flag,
unsigned int size, unsigned int __user *tlv)
{
struct soc_bytes_ext *params = (void *)kcontrol->private_value;
unsigned int count = size < params->max ? size : params->max;
int ret = -ENXIO;
switch (op_flag) {
case SNDRV_CTL_TLV_OP_READ:
if (params->get)
ret = params->get(tlv, count);
break;
case SNDRV_CTL_TLV_OP_WRITE:
if (params->put)
ret = params->put(tlv, count);
break;
}
return ret;
}
EXPORT_SYMBOL_GPL(snd_soc_bytes_tlv_callback);
/**
* snd_soc_info_xr_sx - signed multi register info callback
* @kcontrol: mreg control
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment