fix analog sound station-p1 (#3166)

This commit is contained in:
Oleg 2021-10-07 17:48:09 +03:00 committed by GitHub
parent 5059acac6a
commit b2d54059f7
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 275 additions and 3 deletions

View File

@ -1,8 +1,6 @@
new file mode 100644
index 000000000000..b85508c12742
--- /dev/null
+++ b/arch/arm64/boot/dts/rockchip/rk3399-roc-pc-plus.dts
@@ -0,0 +1,33 @@
@@ -0,0 +1,130 @@
+// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
+/*
+ * Copyright (c) 2017 T-Chip Intelligent Technology Co., Ltd
@ -14,6 +12,45 @@ index 000000000000..b85508c12742
+/ {
+ model = "Firefly roc-rk3399-pc PLUS";
+ compatible = "firefly,roc-rk3399-pc", "rockchip,rk3399";
+
+ vcc_sys: vcc-sys {
+/delete-property/ gpio;
+/delete-property/ pinctrl-names;
+/delete-property/ pinctrl-0;
+ };
+
+ es8388-sound {
+ status = "okay";
+ compatible = "simple-audio-card";
+ simple-audio-card,format = "i2s";
+ simple-audio-card,name = "rockchip,es8388-codec";
+ simple-audio-card,mclk-fs = <256>;
+ simple-audio-card,cpu {
+ sound-dai = <&i2s1>;
+ system-clock-frequency = <11289600>;
+ };
+ simple-audio-card,codec {
+ sound-dai = <&es8388>;
+ system-clock-frequency = <11289600>;
+ };
+ };
+
+ leds {
+ compatible = "gpio-leds";
+
+ yellow_led: led-2 {
+ label = "yellow:yellow-led";
+ gpios = <&gpio0 13 GPIO_ACTIVE_HIGH>;
+ default-state = "off";
+ linux,default-trigger = "mmc1";
+ };
+
+ FAN_EN {
+ //fan power
+ gpios = <&gpio1 1 GPIO_ACTIVE_HIGH>; //GPIO1_A1
+ default-state = "on";
+ };
+ };
+};
+
+&rk808{
@ -36,3 +73,62 @@ index 000000000000..b85508c12742
+ clock-output-names = "xin32k";
+ };
+};
+
+&i2s1 {
+ status = "okay";
+};
+
+&i2c1 {
+ status = "okay";
+ es8388: es8388@11 {
+ compatible = "everest,es8388";
+ status = "okay";
+ reg = <0x11>;
+ hp-det-gpio = <&gpio2 6 GPIO_ACTIVE_HIGH>;
+ hp-ctl-gpio = <&gpio0 2 GPIO_ACTIVE_HIGH>;
+ clock-names = "mclk";
+ clocks = <&cru SCLK_I2S_8CH_OUT>;
+ pinctrl-names = "default";
+ pinctrl-0 = <&i2s_8ch_mclk>;
+ pinctrl-1 = <&ear_ctl_h>;
+ #sound-dai-cells = <0>;
+ };
+};
+
+&pinctrl {
+
+ i2s0 {
+
+ i2s0_8ch_bus: i2s0-8ch-bus {
+ rockchip,pins =
+ <3 RK_PD0 1 &pcfg_pull_none>,
+ <3 RK_PD1 1 &pcfg_pull_none>,
+ <3 RK_PD2 1 &pcfg_pull_none>,
+ <3 RK_PD3 1 &pcfg_pull_none>,
+ <3 RK_PD4 1 &pcfg_pull_none>,
+ <3 RK_PD5 1 &pcfg_pull_none>,
+ <3 RK_PD6 1 &pcfg_pull_none>,
+ <3 RK_PD7 1 &pcfg_pull_none>;
+ };
+
+ i2s_8ch_mclk: i2s-8ch-mclk {
+ rockchip,pins = <4 0 1 &pcfg_pull_none>;
+ };
+
+ };
+
+ leds {
+
+ yellow_led_pin: yellow-led-pin {
+ rockchip,pins = <0 13 RK_FUNC_GPIO &pcfg_pull_none>;
+ };
+ };
+
+ es8388-pins {
+ ear_ctl_h: ear-ctl-h {
+ rockchip,pins = <0 2 RK_FUNC_GPIO &pcfg_pull_down>;
+ };
+ };
+
+};

View File

@ -0,0 +1,176 @@
--- a/sound/soc/codecs/es8328.c
+++ b/sound/soc/codecs/es8328.c
@@ -21,8 +21,13 @@
#include <sound/pcm_params.h>
#include <sound/soc.h>
#include <sound/tlv.h>
+#include <linux/of_gpio.h>
+#include <linux/gpio.h>
#include "es8328.h"
+#define INVALID_GPIO -1
+#define ES8328_CODEC_SET_HP 1
+
static const unsigned int rates_12288[] = {
8000, 12000, 16000, 24000, 32000, 48000, 96000,
};
@@ -86,8 +91,18 @@ struct es8328_priv {
const int *mclk_ratios;
bool master;
struct regulator_bulk_data supplies[ES8328_SUPPLY_NUM];
+
+ int hp_ctl_gpio;
+ int hp_det_gpio;
+
+ bool muted;
+ bool hp_inserted;
+ bool hp_gpio_level;
+ bool hp_det_level;
};
+static struct es8328_priv *es8328_private;
+
/*
* ES8328 Controls
*/
@@ -112,6 +127,42 @@ static const struct {
{ 48000, ES8328_DACCONTROL6_DEEMPH_48k },
};
+static int es8328_set_gpio(int gpio, bool level)
+{
+ struct es8328_priv *es8328 = es8328_private;
+
+ if (!es8328) {
+ return 0;
+ }
+
+ if ((gpio & ES8328_CODEC_SET_HP) && es8328
+ && es8328->hp_ctl_gpio != INVALID_GPIO) {
+ gpio_set_value(es8328->hp_ctl_gpio, level);
+ }
+
+ return 0;
+}
+
+static irqreturn_t hp_det_irq_handler(int irq, void *dev_id)
+{
+ struct es8328_priv *es8328 = es8328_private;
+
+ if(gpio_get_value(es8328->hp_det_gpio)) {
+ es8328->hp_inserted = 1;
+ } else {
+ es8328->hp_inserted = 0;
+ }
+
+ if(!es8328->muted && es8328->hp_inserted) {
+ es8328_set_gpio(ES8328_CODEC_SET_HP, es8328->hp_gpio_level);
+ } else {
+ es8328_set_gpio(ES8328_CODEC_SET_HP, !es8328->hp_gpio_level);
+ }
+ return IRQ_HANDLED;
+}
+
+
+
static int es8328_set_deemph(struct snd_soc_component *component)
{
struct es8328_priv *es8328 = snd_soc_component_get_drvdata(component);
@@ -451,6 +502,14 @@ static const struct snd_soc_dapm_route es8328_dapm_routes[] = {
static int es8328_mute(struct snd_soc_dai *dai, int mute, int direction)
{
+ struct es8328_priv *es8328 = snd_soc_component_get_drvdata(dai->component);
+ es8328->muted = mute;
+ if (!mute && es8328->hp_inserted) {
+ es8328_set_gpio(ES8328_CODEC_SET_HP, es8328->hp_gpio_level);
+ } else {
+ es8328_set_gpio(ES8328_CODEC_SET_HP, !es8328->hp_gpio_level);
+ }
+
return snd_soc_component_update_bits(dai->component, ES8328_DACCONTROL3,
ES8328_DACCONTROL3_DACMUTE,
mute ? ES8328_DACCONTROL3_DACMUTE : 0);
@@ -795,6 +854,21 @@ static int es8328_component_probe(struct snd_soc_component *component)
goto clk_fail;
}
+ if (es8328->hp_det_gpio != INVALID_GPIO) {
+ if (gpio_get_value(es8328->hp_det_gpio) == es8328->hp_det_level)
+ es8328->hp_inserted = 1;
+ } else {
+ es8328->hp_inserted = 1;
+ }
+
+
+ if (!strncmp(component->dev->of_node->name, "es8388", 6)) {
+ usleep_range(18000, 20000);
+ snd_soc_component_update_bits(component, ES8328_DACCONTROL17,
+ ES8328_DACCONTROL17_LD2LO, ES8328_DACCONTROL17_LD2LO);
+ snd_soc_component_update_bits(component, ES8328_DACCONTROL20,
+ ES8328_DACCONTROL20_RD2RO, ES8328_DACCONTROL20_RD2RO);
+ }
return 0;
clk_fail:
@@ -850,6 +924,8 @@ int es8328_probe(struct device *dev, struct regmap *regmap)
struct es8328_priv *es8328;
int ret;
int i;
+ int hp_irq = 0;
+ enum of_gpio_flags flags;
if (IS_ERR(regmap))
return PTR_ERR(regmap);
@@ -859,6 +935,7 @@ int es8328_probe(struct device *dev, struct regmap *regmap)
return -ENOMEM;
es8328->regmap = regmap;
+ es8328_private = es8328;
for (i = 0; i < ARRAY_SIZE(es8328->supplies); i++)
es8328->supplies[i].supply = supply_names[i];
@@ -870,6 +947,43 @@ int es8328_probe(struct device *dev, struct regmap *regmap)
return ret;
}
+ es8328->hp_ctl_gpio = of_get_named_gpio_flags(dev->of_node, "hp-ctl-gpio", 0, &flags);
+ if (es8328->hp_ctl_gpio < 0) {
+ dev_info(dev, "Can not read property hp_ctl_gpio\n");
+ es8328->hp_ctl_gpio = INVALID_GPIO;
+ } else {
+ es8328->hp_gpio_level = (flags & OF_GPIO_ACTIVE_LOW) ? 0 : 1;
+ ret = devm_gpio_request_one(dev, es8328->hp_ctl_gpio, GPIOF_DIR_OUT, "hp_ctl_gpio");
+ if (ret != 0) {
+ dev_err(dev, "Failed to request hp_ctl_gpio\n");
+ return ret;
+ }
+ es8328_set_gpio(ES8328_CODEC_SET_HP, !es8328->hp_gpio_level);
+ }
+
+ es8328->hp_det_gpio = of_get_named_gpio_flags(dev->of_node, "hp-det-gpio", 0, &flags);
+ if (es8328->hp_det_gpio < 0) {
+ dev_info(dev, "Can not read property hp_det_gpio\n");
+ es8328->hp_det_gpio = INVALID_GPIO;
+ } else {
+ es8328->hp_det_level = (flags & OF_GPIO_ACTIVE_LOW) ? 0 : 1;
+ ret = devm_gpio_request_one(dev, es8328->hp_det_gpio, GPIOF_IN, NULL);
+ if (ret != 0) {
+ dev_err(dev, "Failed to request hp_det_gpio\n");
+ return ret;
+ }
+ hp_irq = gpio_to_irq(es8328->hp_det_gpio);
+
+ if (hp_irq) {
+ ret = devm_request_threaded_irq(dev, hp_irq, NULL, hp_det_irq_handler,
+ IRQ_TYPE_EDGE_BOTH | IRQF_ONESHOT, "ES8323", NULL);
+ if (ret < 0) {
+ dev_err(dev, "request_irq failed: %d\n", ret);
+ return ret;
+ }
+ }
+ }
+
dev_set_drvdata(dev, es8328);
return devm_snd_soc_register_component(dev,