Skip to content

Commit c69dfb3

Browse files
BabuSubashChandar Chexameron
BabuSubashChandar C
authored and
hexameron
committed
Add support for new clock rate and mute gpios.
Signed-off-by: Baswaraj K <[email protected]> Reviewed-by: Deepak <[email protected]> Reviewed-by: BabuSubashChandar <[email protected]>
1 parent a700948 commit c69dfb3

File tree

6 files changed

+122
-33
lines changed

6 files changed

+122
-33
lines changed

arch/arm/boot/dts/overlays/allo-boss-dac-pcm512x-audio-overlay.dts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@
4747
boss_dac: __overlay__ {
4848
compatible = "allo,boss-dac";
4949
i2s-controller = <&i2s>;
50+
mute-gpios = <&gpio 6 1>;
5051
status = "okay";
5152
};
5253
};

arch/arm/configs/bcm2709_defconfig

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -883,6 +883,7 @@ CONFIG_SND_AUDIOINJECTOR_OCTO_SOUNDCARD=m
883883
CONFIG_SND_DIGIDAC1_SOUNDCARD=m
884884
CONFIG_SND_BCM2708_SOC_DIONAUDIO_LOCO=m
885885
CONFIG_SND_BCM2708_SOC_DIONAUDIO_LOCO_V2=m
886+
CONFIG_SND_BCM2708_SOC_ALLO_BOSS_DAC=m
886887
CONFIG_SND_BCM2708_SOC_ALLO_PIANO_DAC=m
887888
CONFIG_SND_BCM2708_SOC_FE_PI_AUDIO=m
888889
CONFIG_SND_PISOUND=m

drivers/clk/Makefile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ endif
1717

1818
# hardware specific clock types
1919
# please keep this section sorted lexicographically by file path name
20-
obj-$(CONFIG_SND_BCM2708_SOC_ALLO_BOSS_DAC) += clk-allo-dac-45Mhz.o
20+
obj-$(CONFIG_SND_BCM2708_SOC_ALLO_BOSS_DAC) += clk-allo-dac.o
2121
obj-$(CONFIG_MACH_ASM9260) += clk-asm9260.o
2222
obj-$(CONFIG_COMMON_CLK_AXI_CLKGEN) += clk-axi-clkgen.o
2323
obj-$(CONFIG_ARCH_AXXIA) += clk-axm5516.o

drivers/clk/clk-allo-dac-45Mhz.c renamed to drivers/clk/clk-allo-dac.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,7 @@ static int clk_allo_dac_probe(struct platform_device *pdev)
110110

111111
init.name = "clk-allo-dac";
112112
init.ops = &clk_allo_dac_rate_ops;
113-
init.flags = CLK_IS_ROOT | CLK_IS_BASIC;
113+
init.flags = CLK_IS_BASIC;
114114
init.parent_names = NULL;
115115
init.num_parents = 0;
116116

sound/soc/bcm/Kconfig

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -177,11 +177,11 @@ config SND_BCM2708_SOC_FE_PI_AUDIO
177177
Say Y or M if you want to add support for Fe-Pi-Audio.
178178

179179
config SND_BCM2708_SOC_ALLO_BOSS_DAC
180-
tristate "Support for allo Boss DAC"
180+
tristate "Support for Allo Boss DAC"
181181
depends on SND_BCM2708_SOC_I2S || SND_BCM2835_SOC_I2S
182182
select SND_SOC_PCM512x_I2C
183183
help
184-
Say Y or M if you want to add support for allo Boss DAC.
184+
Say Y or M if you want to add support for Allo Boss DAC.
185185

186186

187187
config SND_PISOUND

sound/soc/bcm/allo-boss-dac.c

Lines changed: 116 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,9 @@
22
* ALSA ASoC Machine Driver for Allo Boss DAC
33
*
44
* Author: Baswaraj K <[email protected]>
5-
* Copyright 2016
6-
* based on code by Daniel Matuschek, Stuart MacLean <[email protected]>
5+
* Copyright 2017
6+
* based on code by Daniel Matuschek,
7+
* Stuart MacLean <[email protected]>
78
* based on code by Florian Meier <[email protected]>
89
*
910
* This program is free software; you can redistribute it and/or
@@ -17,6 +18,7 @@
1718
*/
1819

1920
#include <linux/module.h>
21+
#include <linux/gpio/consumer.h>
2022
#include <linux/platform_device.h>
2123
#include <linux/clk.h>
2224
#include <linux/delay.h>
@@ -36,6 +38,8 @@ struct pcm512x_priv {
3638
struct clk *sclk;
3739
};
3840

41+
static struct gpio_desc *mute_gpio;
42+
3943
/* Clock rate of CLK44EN attached to GPIO6 pin */
4044
#define CLK_44EN_RATE 45158400UL
4145
/* Clock rate of CLK48EN attached to GPIO3 pin */
@@ -111,6 +115,7 @@ static int snd_allo_boss_clk_for_rate(int sample_rate)
111115
case 44100:
112116
case 88200:
113117
case 176400:
118+
case 352800:
114119
type = ALLO_BOSS_CLK44EN;
115120
break;
116121
default:
@@ -138,7 +143,7 @@ static void snd_allo_boss_set_sclk(struct snd_soc_codec *codec,
138143
static int snd_allo_boss_init(struct snd_soc_pcm_runtime *rtd)
139144
{
140145
struct snd_soc_codec *codec = rtd->codec;
141-
struct pcm512x_priv *priv;
146+
struct pcm512x_priv *priv = snd_soc_codec_get_drvdata(codec);
142147

143148
if (slave)
144149
snd_soc_allo_boss_master = false;
@@ -150,15 +155,22 @@ static int snd_allo_boss_init(struct snd_soc_pcm_runtime *rtd)
150155
struct snd_soc_dai_link *dai = rtd->dai_link;
151156

152157
dai->name = "BossDAC";
153-
dai->stream_name = "BossDAC";
158+
dai->stream_name = "Boss DAC HiFi [Master]";
154159
dai->dai_fmt = SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF
155160
| SND_SOC_DAIFMT_CBM_CFM;
156161

157162
snd_soc_update_bits(codec, PCM512x_BCLK_LRCLK_CFG, 0x31, 0x11);
158163
snd_soc_update_bits(codec, PCM512x_MASTER_MODE, 0x03, 0x03);
159164
snd_soc_update_bits(codec, PCM512x_MASTER_CLKDIV_2, 0x7f, 63);
165+
/*
166+
* Default sclk to CLK_48EN_RATE, otherwise codec
167+
* pcm512x_dai_startup_master method could call
168+
* snd_pcm_hw_constraint_ratnums using CLK_44EN/64
169+
* which will mask 384k sample rate.
170+
*/
171+
if (!IS_ERR(priv->sclk))
172+
clk_set_rate(priv->sclk, CLK_48EN_RATE);
160173
} else {
161-
priv = snd_soc_codec_get_drvdata(codec);
162174
priv->sclk = ERR_PTR(-ENOENT);
163175
}
164176

@@ -218,6 +230,52 @@ static int snd_allo_boss_set_bclk_ratio_pro(
218230
return snd_soc_dai_set_bclk_ratio(cpu_dai, bratio);
219231
}
220232

233+
static void snd_allo_boss_gpio_mute(struct snd_soc_card *card)
234+
{
235+
if (mute_gpio)
236+
gpiod_set_value_cansleep(mute_gpio, 1);
237+
}
238+
239+
static void snd_allo_boss_gpio_unmute(struct snd_soc_card *card)
240+
{
241+
if (mute_gpio)
242+
gpiod_set_value_cansleep(mute_gpio, 0);
243+
}
244+
245+
static int snd_allo_boss_set_bias_level(struct snd_soc_card *card,
246+
struct snd_soc_dapm_context *dapm, enum snd_soc_bias_level level)
247+
{
248+
struct snd_soc_pcm_runtime *rtd;
249+
struct snd_soc_dai *codec_dai;
250+
251+
rtd = snd_soc_get_pcm_runtime(card, card->dai_link[0].name);
252+
codec_dai = rtd->codec_dai;
253+
254+
if (dapm->dev != codec_dai->dev)
255+
return 0;
256+
257+
switch (level) {
258+
case SND_SOC_BIAS_PREPARE:
259+
if (dapm->bias_level != SND_SOC_BIAS_STANDBY)
260+
break;
261+
/* UNMUTE DAC */
262+
snd_allo_boss_gpio_unmute(card);
263+
break;
264+
265+
case SND_SOC_BIAS_STANDBY:
266+
if (dapm->bias_level != SND_SOC_BIAS_PREPARE)
267+
break;
268+
/* MUTE DAC */
269+
snd_allo_boss_gpio_mute(card);
270+
break;
271+
272+
default:
273+
break;
274+
}
275+
276+
return 0;
277+
}
278+
221279
static int snd_allo_boss_hw_params(
222280
struct snd_pcm_substream *substream, struct snd_pcm_hw_params *params)
223281
{
@@ -239,23 +297,6 @@ static int snd_allo_boss_hw_params(
239297
ret = snd_allo_boss_update_rate_den(
240298
substream, params);
241299
} else {
242-
if (snd_allo_boss_is_sclk(rtd->codec)) {
243-
snd_soc_update_bits(rtd->codec, PCM512x_PLL_EN,
244-
PCM512x_PLLE, 0x01);
245-
snd_soc_update_bits(rtd->codec, PCM512x_PLL_REF,
246-
PCM512x_SREF, PCM512x_SREF_BCK);
247-
dev_dbg(rtd->codec->dev,
248-
"Setting BCLK as input clock and Enable PLL\n");
249-
} else {
250-
snd_soc_update_bits(rtd->codec, PCM512x_PLL_EN,
251-
PCM512x_PLLE, 0x00);
252-
snd_soc_update_bits(rtd->codec, PCM512x_PLL_REF,
253-
PCM512x_SREF, PCM512x_SREF_SCK);
254-
255-
dev_dbg(rtd->codec->dev,
256-
"Setting SCLK as input clock and disabled PLL\n");
257-
}
258-
259300
ret = snd_soc_dai_set_bclk_ratio(cpu_dai, sample_bits * 2);
260301
}
261302
return ret;
@@ -266,8 +307,23 @@ static int snd_allo_boss_startup(
266307
{
267308
struct snd_soc_pcm_runtime *rtd = substream->private_data;
268309
struct snd_soc_codec *codec = rtd->codec;
310+
struct snd_soc_card *card = rtd->card;
269311

270312
snd_soc_update_bits(codec, PCM512x_GPIO_CONTROL_1, 0x08, 0x08);
313+
snd_allo_boss_gpio_mute(card);
314+
315+
if (snd_soc_allo_boss_master) {
316+
struct pcm512x_priv *priv = snd_soc_codec_get_drvdata(codec);
317+
/*
318+
* Default sclk to CLK_48EN_RATE, otherwise codec
319+
* pcm512x_dai_startup_master method could call
320+
* snd_pcm_hw_constraint_ratnums using CLK_44EN/64
321+
* which will mask 384k sample rate.
322+
*/
323+
if (!IS_ERR(priv->sclk))
324+
clk_set_rate(priv->sclk, CLK_48EN_RATE);
325+
}
326+
271327
return 0;
272328
}
273329

@@ -280,11 +336,21 @@ static void snd_allo_boss_shutdown(
280336
snd_soc_update_bits(codec, PCM512x_GPIO_CONTROL_1, 0x08, 0x00);
281337
}
282338

339+
static int snd_allo_boss_prepare(
340+
struct snd_pcm_substream *substream)
341+
{
342+
struct snd_soc_pcm_runtime *rtd = substream->private_data;
343+
struct snd_soc_card *card = rtd->card;
344+
345+
snd_allo_boss_gpio_unmute(card);
346+
return 0;
347+
}
283348
/* machine stream operations */
284349
static struct snd_soc_ops snd_allo_boss_ops = {
285350
.hw_params = snd_allo_boss_hw_params,
286351
.startup = snd_allo_boss_startup,
287352
.shutdown = snd_allo_boss_shutdown,
353+
.prepare = snd_allo_boss_prepare,
288354
};
289355

290356
static struct snd_soc_dai_link snd_allo_boss_dai[] = {
@@ -335,19 +401,40 @@ static int snd_allo_boss_probe(struct platform_device *pdev)
335401
digital_gain_0db_limit = !of_property_read_bool(
336402
pdev->dev.of_node, "allo,24db_digital_gain");
337403
slave = of_property_read_bool(pdev->dev.of_node,
338-
"allo,slave");
339-
}
404+
"allo,slave");
405+
406+
mute_gpio = devm_gpiod_get_optional(&pdev->dev, "mute",
407+
GPIOD_OUT_LOW);
408+
if (IS_ERR(mute_gpio)) {
409+
ret = PTR_ERR(mute_gpio);
410+
dev_err(&pdev->dev,
411+
"failed to get mute gpio: %d\n", ret);
412+
return ret;
413+
}
340414

341-
ret = snd_soc_register_card(&snd_allo_boss);
342-
if (ret)
343-
dev_err(&pdev->dev,
344-
"snd_soc_register_card() failed: %d\n", ret);
415+
if (mute_gpio)
416+
snd_allo_boss.set_bias_level =
417+
snd_allo_boss_set_bias_level;
345418

346-
return ret;
419+
ret = snd_soc_register_card(&snd_allo_boss);
420+
if (ret) {
421+
dev_err(&pdev->dev,
422+
"snd_soc_register_card() failed: %d\n", ret);
423+
return ret;
424+
}
425+
426+
if (mute_gpio)
427+
snd_allo_boss_gpio_mute(&snd_allo_boss);
428+
429+
return 0;
430+
}
431+
432+
return -EINVAL;
347433
}
348434

349435
static int snd_allo_boss_remove(struct platform_device *pdev)
350436
{
437+
snd_allo_boss_gpio_mute(&snd_allo_boss);
351438
return snd_soc_unregister_card(&snd_allo_boss);
352439
}
353440

0 commit comments

Comments
 (0)