Skip to content

Commit edb5a1d

Browse files
committed
Merge: ac108 work for 4mic & 8mic
1 parent add8afa commit edb5a1d

12 files changed

+417
-66
lines changed

ac101.c

Lines changed: 15 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919
* the License, or (at your option) any later version.
2020
*
2121
*/
22+
#undef AC10X_DEBG
2223
#include <linux/module.h>
2324
#include <linux/init.h>
2425
#include <linux/slab.h>
@@ -64,7 +65,9 @@ static int adc_digital_val = 0;
6465
static bool agc_used = false;
6566
static bool drc_used = false;
6667

67-
#define ac10x_RATES (SNDRV_PCM_RATE_8000_96000|SNDRV_PCM_RATE_KNOT)
68+
#define ac10x_RATES (SNDRV_PCM_RATE_8000_96000 & \
69+
~(SNDRV_PCM_RATE_32000 | SNDRV_PCM_RATE_64000 | \
70+
SNDRV_PCM_RATE_88200))
6871
#define ac10x_FORMATS ( /*SNDRV_PCM_FMTBIT_S8 | \
6972
SNDRV_PCM_FMTBIT_S16_LE | \
7073
SNDRV_PCM_FMTBIT_S18_3LE | \
@@ -103,7 +106,6 @@ struct ac10x_priv {
103106

104107
struct work_struct codec_resume;
105108
struct delayed_work dlywork;
106-
int trgr_cnt;
107109

108110
struct gpio_desc* gpiod_spk_amp_switch;
109111
};
@@ -1192,15 +1194,15 @@ static const struct pll_div codec_pll_div[] = {
11921194
};
11931195

11941196
static const struct aif1_fs codec_aif1_fs[] = {
1195-
{44100, 2, 7, _SERIES_22_579K},
1196-
{48000, 2, 8},
11971197
{8000, 12, 0},
11981198
{11025, 8, 1, _SERIES_22_579K},
11991199
{12000, 8, 2},
12001200
{16000, 6, 3},
12011201
{22050, 4, 4, _SERIES_22_579K},
12021202
{24000, 4, 5},
1203-
/* {32000, 3, 6}, not support */
1203+
/* {32000, 3, 6}, dividing by 3 is not support */
1204+
{44100, 2, 7, _SERIES_22_579K},
1205+
{48000, 2, 8},
12041206
{96000, 1, 9},
12051207
};
12061208

@@ -1303,8 +1305,6 @@ static int ac10x_hw_params(struct snd_pcm_substream *substream,
13031305

13041306
AC10X_DBG("%s() L%d +++\n", __func__, __LINE__);
13051307

1306-
ac10x->trgr_cnt = 0;
1307-
13081308
/* get channels count & slot size */
13091309
channels = params_channels(params);
13101310

@@ -1585,17 +1585,16 @@ static void __ac10x_work_start_clock(struct work_struct *work) {
15851585
return;
15861586
}
15871587

1588-
int ac10x_start_clock(void) {
1589-
ac10x_aif1clk(static_ac10x->codec, SND_SOC_DAPM_PRE_PMU);
1588+
extern int register_start_clock(int (*start_clock)(void));
1589+
1590+
static int ac10x_start_clock(void) {
1591+
schedule_delayed_work(&static_ac10x->dlywork, msecs_to_jiffies(30));
15901592
return 0;
15911593
}
1592-
EXPORT_SYMBOL(ac10x_start_clock);
15931594

15941595
static int ac10x_trigger(struct snd_pcm_substream *substream, int cmd,
15951596
struct snd_soc_dai *dai)
15961597
{
1597-
struct snd_soc_codec *codec = dai->codec;
1598-
struct ac10x_priv *ac10x = snd_soc_codec_get_drvdata(codec);
15991598
int ret = 0;
16001599

16011600
AC10X_DBG("%s() stream=%d cmd=%d\n",
@@ -1605,13 +1604,6 @@ static int ac10x_trigger(struct snd_pcm_substream *substream, int cmd,
16051604
case SNDRV_PCM_TRIGGER_START:
16061605
case SNDRV_PCM_TRIGGER_RESUME:
16071606
case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
1608-
if (ac10x->trgr_cnt++ > 0) {
1609-
break;
1610-
}
1611-
1612-
/* delayed clock starting */
1613-
schedule_delayed_work(&ac10x->dlywork, msecs_to_jiffies(30));
1614-
break;
16151607

16161608
case SNDRV_PCM_TRIGGER_STOP:
16171609
case SNDRV_PCM_TRIGGER_SUSPEND:
@@ -1620,9 +1612,7 @@ static int ac10x_trigger(struct snd_pcm_substream *substream, int cmd,
16201612
default:
16211613
ret = -EINVAL;
16221614
}
1623-
1624-
1625-
return 0;
1615+
return ret;
16261616
}
16271617

16281618
static const struct snd_soc_dai_ops ac10x_aif1_dai_ops = {
@@ -1702,7 +1692,7 @@ static ssize_t ac10x_debug_store(struct device *dev,
17021692
struct ac10x_priv *ac10x = dev_get_drvdata(dev);
17031693
val = simple_strtol(buf, NULL, 16);
17041694
flag = (val >> 24) & 0xF;
1705-
if(flag) {//write
1695+
if(flag) {
17061696
reg = (val >> 16) & 0xFF;
17071697
value_w = val & 0xFFFF;
17081698
snd_soc_write(ac10x->codec, reg, value_w);
@@ -1781,6 +1771,8 @@ static int ac10x_codec_probe(struct snd_soc_codec *codec)
17811771
mutex_init(&ac10x->adc_mutex);
17821772
mutex_init(&ac10x->aifclk_mutex);
17831773

1774+
register_start_clock(ac10x_start_clock);
1775+
17841776
ac10x->num_supplies = ARRAY_SIZE(ac10x_supplies);
17851777
ac10x->supplies = devm_kzalloc(ac10x->codec->dev,
17861778
sizeof(struct regulator_bulk_data) *

ac101.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -424,7 +424,6 @@ struct spk_gpio {
424424
u32 gpio;
425425
bool used;
426426
};
427-
#define AC10X_DEBG
428427
#ifdef AC10X_DEBG
429428
#define AC10X_DBG(format,args...) printk("[AC101] "format,##args)
430429
#else

ac108.c

Lines changed: 106 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
* it under the terms of the GNU General Public License version 2 as
99
* published by the Free Software Foundation.
1010
*/
11-
#define DEBUG
11+
#undef DEBUG
1212
#include <linux/module.h>
1313
#include <linux/moduleparam.h>
1414
#include <linux/init.h>
@@ -27,7 +27,7 @@
2727
#include "ac108.h"
2828

2929
#define _USE_CAPTURE 0
30-
#define _MASTER_INDEX 1
30+
#define _MASTER_INDEX 0
3131

3232
/**
3333
* TODO:
@@ -56,6 +56,7 @@ struct ac108_priv {
5656
unsigned char data_protocol;
5757
struct delayed_work dlywork;
5858
int trgr_cnt;
59+
int tdm_chips_cnt;
5960
};
6061
static struct ac108_priv *ac108;
6162

@@ -165,8 +166,13 @@ static const struct pll_div ac108_pll_div_list[] = {
165166

166167
/* AC108 definition */
167168
#define AC108_CHANNELS_MAX 16 /* range[1, 16] */
168-
#define AC108_RATES (SNDRV_PCM_RATE_8000_96000 | SNDRV_PCM_RATE_KNOT)
169-
#define AC108_FORMATS (/* SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S20_3LE | SNDRV_PCM_FMTBIT_S24_LE |*/ SNDRV_PCM_FMTBIT_S32_LE)
169+
#define AC108_RATES (SNDRV_PCM_RATE_8000_96000 & \
170+
~(SNDRV_PCM_RATE_32000 | SNDRV_PCM_RATE_64000 | \
171+
SNDRV_PCM_RATE_88200))
172+
#define AC108_FORMATS (/*SNDRV_PCM_FMTBIT_S16_LE | \
173+
SNDRV_PCM_FMTBIT_S20_3LE | \
174+
SNDRV_PCM_FMTBIT_S24_LE |*/ \
175+
SNDRV_PCM_FMTBIT_S32_LE)
170176

171177
static const DECLARE_TLV_DB_SCALE(tlv_adc_pga_gain, 0, 100, 0);
172178
static const DECLARE_TLV_DB_SCALE(tlv_ch_digital_vol, -11925,75,0);
@@ -463,6 +469,7 @@ static int snd_ac108_put_volsw(struct snd_kcontrol *kcontrol,
463469
.private_value = SOC_SINGLE_VALUE(reg, shift, max, invert, chip) }
464470

465471
static const struct snd_kcontrol_new ac108_snd_controls[] = {
472+
/* ### chip 0 ### */
466473
/*0x70: ADC1 Digital Channel Volume Control Register*/
467474
SOC_AC108_SINGLE_TLV("CH1 digital volume", ADC1_DVOL_CTRL, 0, 0xff, 0, 0, tlv_ch_digital_vol),
468475
/*0x71: ADC2 Digital Channel Volume Control Register*/
@@ -472,6 +479,16 @@ static const struct snd_kcontrol_new ac108_snd_controls[] = {
472479
/*0x73: ADC4 Digital Channel Volume Control Register*/
473480
SOC_AC108_SINGLE_TLV("CH4 digital volume", ADC4_DVOL_CTRL, 0, 0xff, 0, 0, tlv_ch_digital_vol),
474481

482+
/*0x90: Analog PGA1 Control Register*/
483+
SOC_AC108_SINGLE_TLV("ADC1 PGA gain", ANA_PGA1_CTRL, ADC1_ANALOG_PGA, 0x1f, 0, 0, tlv_adc_pga_gain),
484+
/*0x91: Analog PGA2 Control Register*/
485+
SOC_AC108_SINGLE_TLV("ADC2 PGA gain", ANA_PGA2_CTRL, ADC2_ANALOG_PGA, 0x1f, 0, 0, tlv_adc_pga_gain),
486+
/*0x92: Analog PGA3 Control Register*/
487+
SOC_AC108_SINGLE_TLV("ADC3 PGA gain", ANA_PGA3_CTRL, ADC3_ANALOG_PGA, 0x1f, 0, 0, tlv_adc_pga_gain),
488+
/*0x93: Analog PGA4 Control Register*/
489+
SOC_AC108_SINGLE_TLV("ADC4 PGA gain", ANA_PGA4_CTRL, ADC4_ANALOG_PGA, 0x1f, 0, 0, tlv_adc_pga_gain),
490+
491+
/* ### chip 1 ### */
475492
/*0x70: ADC1 Digital Channel Volume Control Register*/
476493
SOC_AC108_SINGLE_TLV("CH5 digital volume", ADC1_DVOL_CTRL, 0, 0xff, 0, 1, tlv_ch_digital_vol),
477494
/*0x71: ADC2 Digital Channel Volume Control Register*/
@@ -481,14 +498,6 @@ static const struct snd_kcontrol_new ac108_snd_controls[] = {
481498
/*0x73: ADC4 Digital Channel Volume Control Register*/
482499
SOC_AC108_SINGLE_TLV("CH8 digital volume", ADC4_DVOL_CTRL, 0, 0xff, 0, 1, tlv_ch_digital_vol),
483500

484-
/*0x90: Analog PGA1 Control Register*/
485-
SOC_AC108_SINGLE_TLV("ADC1 PGA gain", ANA_PGA1_CTRL, ADC1_ANALOG_PGA, 0x1f, 0, 0, tlv_adc_pga_gain),
486-
/*0x91: Analog PGA2 Control Register*/
487-
SOC_AC108_SINGLE_TLV("ADC2 PGA gain", ANA_PGA2_CTRL, ADC2_ANALOG_PGA, 0x1f, 0, 0, tlv_adc_pga_gain),
488-
/*0x92: Analog PGA3 Control Register*/
489-
SOC_AC108_SINGLE_TLV("ADC3 PGA gain", ANA_PGA3_CTRL, ADC3_ANALOG_PGA, 0x1f, 0, 0, tlv_adc_pga_gain),
490-
/*0x93: Analog PGA4 Control Register*/
491-
SOC_AC108_SINGLE_TLV("ADC4 PGA gain", ANA_PGA4_CTRL, ADC4_ANALOG_PGA, 0x1f, 0, 0, tlv_adc_pga_gain),
492501
/*0x90: Analog PGA1 Control Register*/
493502
SOC_AC108_SINGLE_TLV("ADC5 PGA gain", ANA_PGA1_CTRL, ADC1_ANALOG_PGA, 0x1f, 0, 1, tlv_adc_pga_gain),
494503
/*0x91: Analog PGA2 Control Register*/
@@ -631,8 +640,6 @@ static const struct snd_soc_dapm_widget ac108_dapm_widgets[] = {
631640
/*0x62:Digital MIC Enable Register*/
632641
SND_SOC_DAPM_MICBIAS("DMIC1 enable", DMIC_EN, 0, 0),
633642
SND_SOC_DAPM_MICBIAS("DMIC2 enable", DMIC_EN, 1, 0),
634-
635-
/**/
636643
};
637644

638645
static const struct snd_soc_dapm_route ac108_dapm_routes[] = {
@@ -860,20 +867,61 @@ static int ac108_configure_clocking(struct ac108_priv *ac108, unsigned int rate)
860867
static int ac108_multi_chips_slots(struct ac108_priv *ac, int slots) {
861868
int i;
862869

863-
/* codec0 enable slots 1,2,3,4
864-
* codec1 enable slots 5,6,7,8 etc
870+
/*
871+
* codec0 enable slots 2,3,0,1 when 1 codec
872+
*
873+
* codec0 enable slots 6,7,0,1 when 2 codec
874+
* codec1 enable slots 2,3,4,5
875+
*
876+
* ...
865877
*/
866878
for (i = 0; i < ac->codec_index; i++) {
879+
const unsigned vec_mask[] = {
880+
0x3 << 6 | 0x3, // slots 6,7,0,1
881+
0xF << 2, // slots 2,3,4,5
882+
0,
883+
0,
884+
};
885+
const unsigned vec_maps[] = {
886+
/*
887+
* chip 0,
888+
* mic 0 sample -> slot 6
889+
* mic 1 sample -> slot 7
890+
* mic 2 sample -> slot 0
891+
* mic 3 sample -> slot 1
892+
*/
893+
0x0 << 12 | 0x1 << 14 | 0x2 << 0 | 0x3 << 2,
894+
/*
895+
* chip 1,
896+
* mic 0 sample -> slot 2
897+
* mic 1 sample -> slot 3
898+
* mic 2 sample -> slot 4
899+
* mic 3 sample -> slot 5
900+
*/
901+
0x0 << 4 | 0x1 << 6 | 0x2 << 8 | 0x3 << 10,
902+
0,
903+
0,
904+
};
867905
unsigned vec;
868906

869907
/* 0x38-0x3A I2S_TX1_CTRLx */
870-
vec = 0xFUL << (i << 2);
908+
/* rotate map, due to channels rotated by CPU_DAI */
909+
if (ac->codec_index == 1) {
910+
vec = 0xFUL;
911+
} else {
912+
vec = vec_mask[i];
913+
}
871914
ac108_write(I2S_TX1_CTRL1, slots - 1, ac->i2c[i]);
872915
ac108_write(I2S_TX1_CTRL2, (vec >> 0) & 0xFF, ac->i2c[i]);
873916
ac108_write(I2S_TX1_CTRL3, (vec >> 8) & 0xFF, ac->i2c[i]);
874917

875918
/* 0x3C-0x3F I2S_TX1_CHMP_CTRLx */
876-
vec = (0x0 << 0 | 0x1 << 2 | 0x2 << 4 | 0x3 << 6) << (i << 3);
919+
if (ac->codec_index == 1) {
920+
vec = (0x2 << 0 | 0x3 << 2 | 0x0 << 4 | 0x1 << 6);
921+
} else if (ac->codec_index == 2) {
922+
vec = vec_maps[i];
923+
}
924+
877925
ac108_write(I2S_TX1_CHMP_CTRL1, (vec >> 0) & 0xFF, ac->i2c[i]);
878926
ac108_write(I2S_TX1_CHMP_CTRL2, (vec >> 8) & 0xFF, ac->i2c[i]);
879927
ac108_write(I2S_TX1_CHMP_CTRL3, (vec >> 16) & 0xFF, ac->i2c[i]);
@@ -1064,17 +1112,20 @@ static int ac108_set_fmt(struct snd_soc_dai *dai, unsigned int fmt) {
10641112

10651113
switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) {
10661114
case SND_SOC_DAIFMT_CBM_CFM: /*AC108 Master*/
1067-
dev_dbg(dai->dev, "AC108 set to work as Master\n");
1068-
#if 0
1069-
/**
1070-
* 0x30:chip is master mode ,BCLK & LRCK output
1071-
*/
1072-
ac108_multi_chips_update_bits(I2S_CTRL, 0x03 << LRCK_IOEN | 0x03 << SDO1_EN | 0x1 << TXEN | 0x1 << GEN,
1115+
if (ac108->tdm_chips_cnt < 2) {
1116+
dev_dbg(dai->dev, "AC108 set to work as Master\n");
1117+
/**
1118+
* 0x30:chip is master mode ,BCLK & LRCK output
1119+
*/
1120+
ac108_multi_chips_update_bits(I2S_CTRL, 0x03 << LRCK_IOEN | 0x03 << SDO1_EN | 0x1 << TXEN | 0x1 << GEN,
10731121
0x00 << LRCK_IOEN | 0x03 << SDO1_EN | 0x1 << TXEN | 0x1 << GEN, ac108);
1074-
/* multi_chips: only one chip set as Master, and the others also need to set as Slave */
1075-
ac108_update_bits(I2S_CTRL, 0x3 << LRCK_IOEN, 0x2 << LRCK_IOEN, ac108->i2c[_MASTER_INDEX]);
1076-
break;
1077-
#endif
1122+
/* multi_chips: only one chip set as Master, and the others also need to set as Slave */
1123+
ac108_update_bits(I2S_CTRL, 0x3 << LRCK_IOEN, 0x2 << LRCK_IOEN, ac108->i2c[_MASTER_INDEX]);
1124+
break;
1125+
} else {
1126+
/* TODO: Both cpu_dai and codec_dai(AC108) be set as slave in DTS */
1127+
dev_dbg(dai->dev, "used as slave when AC101 is master\n");
1128+
}
10781129
case SND_SOC_DAIFMT_CBS_CFS: /*AC108 Slave*/
10791130
dev_dbg(dai->dev, "AC108 set to work as Slave\n");
10801131
/**
@@ -1148,6 +1199,14 @@ static int ac108_set_fmt(struct snd_soc_dai *dai, unsigned int fmt) {
11481199
pr_err("AC108 config BCLK/LRCLK polarity error:%u\n\n", (fmt & SND_SOC_DAIFMT_INV_MASK) >> 8);
11491200
return -EINVAL;
11501201
}
1202+
1203+
#if 0
1204+
/* revert LRCK polarity if it's single chip (master mode) */
1205+
if (ac108->tdm_chips_cnt < 2) {
1206+
lrck_polarity = (lrck_polarity == LRCK_LEFT_HIGH_RIGHT_LOW)?
1207+
LRCK_LEFT_LOW_RIGHT_HIGH: LRCK_LEFT_HIGH_RIGHT_LOW;
1208+
}
1209+
#endif
11511210
ac108_configure_power(ac108);
11521211

11531212
/**
@@ -1358,10 +1417,15 @@ static struct snd_soc_dai_driver *ac108_dai[] = {
13581417
};
13591418

13601419
static int ac108_add_widgets(struct snd_soc_codec *codec) {
1420+
struct ac108_priv *ac108 = snd_soc_codec_get_drvdata(codec);
13611421
struct snd_soc_dapm_context *dapm = snd_soc_codec_get_dapm(codec);
1422+
int ctrl_cnt = ARRAY_SIZE(ac108_snd_controls);
13621423

1363-
snd_soc_add_codec_controls(codec, ac108_snd_controls,
1364-
ARRAY_SIZE(ac108_snd_controls));
1424+
/* only register controls correspond to exist chips */
1425+
if (ac108->tdm_chips_cnt < 2) {
1426+
ctrl_cnt /= 2;
1427+
}
1428+
snd_soc_add_codec_controls(codec, ac108_snd_controls, ctrl_cnt);
13651429

13661430
snd_soc_dapm_new_controls(dapm, ac108_dapm_widgets,
13671431
ARRAY_SIZE(ac108_dapm_widgets));
@@ -1508,19 +1572,25 @@ static int ac108_i2c_probe(struct i2c_client *i2c,
15081572
}
15091573
ac108->data_protocol = val;
15101574

1511-
/*Writing this register 0x12 resets all register to their default state.*/
1575+
ret = of_property_read_u32(np, "tdm-chips-count", &val);
1576+
if (ret) {
1577+
val = 1;
1578+
}
1579+
ac108->tdm_chips_cnt = val;
1580+
1581+
/* Writing this register with 0x12 will resets all register to their default state. */
15121582
ac108_write(CHIP_RST, CHIP_RST_VAL, i2c);
15131583
msleep(1);
15141584

1515-
pr_err(" i2c_id number :%d\n", (int)(i2c_id->driver_data));
1516-
pr_err(" ac108 codec_index :%d\n", ac108->codec_index);
1517-
pr_err(" ac108 I2S data protocol type :%d\n", ac108->data_protocol);
1585+
pr_err(" i2c_id number : %d\n", (int)(i2c_id->driver_data));
1586+
pr_err(" ac108 codec_index : %d\n", ac108->codec_index);
1587+
pr_err(" ac108 data protocol: %d\n", ac108->data_protocol);
15181588

15191589
ac108->i2c[i2c_id->driver_data] = i2c;
15201590
ac108->codec_index++;
15211591

1522-
/* we need i2c[0] && i2c[1], codec bind with i2c[_MASTER_INDEX] */
1523-
if (ac108->codec_index == 2) {
1592+
/* when all i2c prepared, we bind codec to i2c[_MASTER_INDEX] */
1593+
if (ac108->codec_index == ac108->tdm_chips_cnt) {
15241594
ret = snd_soc_register_codec(&ac108->i2c[_MASTER_INDEX]->dev, &ac108_soc_codec_driver,
15251595
ac108_dai[_MASTER_INDEX], 1);
15261596
if (ret < 0) {

seeed-4mic-voicecard-overlay.dts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,7 @@
5151

5252
simple-audio-card,bitclock-master = <&codec_dai>;
5353
simple-audio-card,frame-master = <&codec_dai>;
54-
simple-audio-card,channels-playback-override = <2>;
54+
simple-audio-card,channels-playback-override = <4>;
5555
simple-audio-card,channels-capture-override = <4>;
5656

5757
cpu_dai: simple-audio-card,cpu {

seeed-4mic-voicecard.dtbo

0 Bytes
Binary file not shown.

0 commit comments

Comments
 (0)