aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Documentation/devicetree/bindings/sound/rt5677.txt10
-rw-r--r--include/sound/rt5677.h7
-rw-r--r--sound/soc/codecs/rt5677.c134
-rw-r--r--sound/soc/codecs/rt5677.h49
4 files changed, 200 insertions, 0 deletions
diff --git a/Documentation/devicetree/bindings/sound/rt5677.txt b/Documentation/devicetree/bindings/sound/rt5677.txt
index f82f0e906cd9..740ff771aa8b 100644
--- a/Documentation/devicetree/bindings/sound/rt5677.txt
+++ b/Documentation/devicetree/bindings/sound/rt5677.txt
@@ -33,6 +33,15 @@ Optional properties:
33 1 - pull down 33 1 - pull down
34 2 - pull up 34 2 - pull up
35 35
36- realtek,jd1-gpio
37 Configures GPIO Mic Jack detection 1.
38 Select 0 ~ 3 as OFF, GPIO1, GPIO2 and GPIO3 respectively.
39
40- realtek,jd2-gpio
41- realtek,jd3-gpio
42 Configures GPIO Mic Jack detection 2 and 3.
43 Select 0 ~ 3 as OFF, GPIO4, GPIO5 and GPIO6 respectively.
44
36Pins on the device (for linking into audio routes): 45Pins on the device (for linking into audio routes):
37 46
38 * IN1P 47 * IN1P
@@ -63,4 +72,5 @@ rt5677 {
63 <&gpio TEGRA_GPIO(V, 3) GPIO_ACTIVE_HIGH>; 72 <&gpio TEGRA_GPIO(V, 3) GPIO_ACTIVE_HIGH>;
64 realtek,in1-differential = "true"; 73 realtek,in1-differential = "true";
65 realtek,gpio-config = /bits/ 8 <0 0 0 0 0 2>; /* pull up GPIO6 */ 74 realtek,gpio-config = /bits/ 8 <0 0 0 0 0 2>; /* pull up GPIO6 */
75 realtek,jd2-gpio = <3>; /* Enables Jack detection for GPIO6 */
66}; 76};
diff --git a/include/sound/rt5677.h b/include/sound/rt5677.h
index a56b429a1dbc..d9eb7d861cd0 100644
--- a/include/sound/rt5677.h
+++ b/include/sound/rt5677.h
@@ -30,6 +30,13 @@ struct rt5677_platform_data {
30 30
31 /* configures GPIO, 0 - floating, 1 - pulldown, 2 - pullup */ 31 /* configures GPIO, 0 - floating, 1 - pulldown, 2 - pullup */
32 u8 gpio_config[6]; 32 u8 gpio_config[6];
33
34 /* jd1 can select 0 ~ 3 as OFF, GPIO1, GPIO2 and GPIO3 respectively */
35 unsigned int jd1_gpio;
36 /* jd2 and jd3 can select 0 ~ 3 as
37 OFF, GPIO4, GPIO5 and GPIO6 respectively */
38 unsigned int jd2_gpio;
39 unsigned int jd3_gpio;
33}; 40};
34 41
35#endif 42#endif
diff --git a/sound/soc/codecs/rt5677.c b/sound/soc/codecs/rt5677.c
index d17d079fdcf3..6c73dfd22a0c 100644
--- a/sound/soc/codecs/rt5677.c
+++ b/sound/soc/codecs/rt5677.c
@@ -3614,6 +3614,46 @@ static void rt5677_gpio_config(struct rt5677_priv *rt5677, unsigned offset,
3614 } 3614 }
3615} 3615}
3616 3616
3617static int rt5677_to_irq(struct gpio_chip *chip, unsigned offset)
3618{
3619 struct rt5677_priv *rt5677 = gpio_to_rt5677(chip);
3620 struct regmap_irq_chip_data *data = rt5677->irq_data;
3621 int irq;
3622
3623 if (offset >= RT5677_GPIO1 && offset <= RT5677_GPIO3) {
3624 if ((rt5677->pdata.jd1_gpio == 1 && offset == RT5677_GPIO1) ||
3625 (rt5677->pdata.jd1_gpio == 2 &&
3626 offset == RT5677_GPIO2) ||
3627 (rt5677->pdata.jd1_gpio == 3 &&
3628 offset == RT5677_GPIO3)) {
3629 irq = RT5677_IRQ_JD1;
3630 } else {
3631 return -ENXIO;
3632 }
3633 }
3634
3635 if (offset >= RT5677_GPIO4 && offset <= RT5677_GPIO6) {
3636 if ((rt5677->pdata.jd2_gpio == 1 && offset == RT5677_GPIO4) ||
3637 (rt5677->pdata.jd2_gpio == 2 &&
3638 offset == RT5677_GPIO5) ||
3639 (rt5677->pdata.jd2_gpio == 3 &&
3640 offset == RT5677_GPIO6)) {
3641 irq = RT5677_IRQ_JD2;
3642 } else if ((rt5677->pdata.jd3_gpio == 1 &&
3643 offset == RT5677_GPIO4) ||
3644 (rt5677->pdata.jd3_gpio == 2 &&
3645 offset == RT5677_GPIO5) ||
3646 (rt5677->pdata.jd3_gpio == 3 &&
3647 offset == RT5677_GPIO6)) {
3648 irq = RT5677_IRQ_JD3;
3649 } else {
3650 return -ENXIO;
3651 }
3652 }
3653
3654 return regmap_irq_get_virq(data, irq);
3655}
3656
3617static struct gpio_chip rt5677_template_chip = { 3657static struct gpio_chip rt5677_template_chip = {
3618 .label = "rt5677", 3658 .label = "rt5677",
3619 .owner = THIS_MODULE, 3659 .owner = THIS_MODULE,
@@ -3621,6 +3661,7 @@ static struct gpio_chip rt5677_template_chip = {
3621 .set = rt5677_gpio_set, 3661 .set = rt5677_gpio_set,
3622 .direction_input = rt5677_gpio_direction_in, 3662 .direction_input = rt5677_gpio_direction_in,
3623 .get = rt5677_gpio_get, 3663 .get = rt5677_gpio_get,
3664 .to_irq = rt5677_to_irq,
3624 .can_sleep = 1, 3665 .can_sleep = 1,
3625}; 3666};
3626 3667
@@ -3685,6 +3726,31 @@ static int rt5677_probe(struct snd_soc_codec *codec)
3685 for (i = 0; i < RT5677_GPIO_NUM; i++) 3726 for (i = 0; i < RT5677_GPIO_NUM; i++)
3686 rt5677_gpio_config(rt5677, i, rt5677->pdata.gpio_config[i]); 3727 rt5677_gpio_config(rt5677, i, rt5677->pdata.gpio_config[i]);
3687 3728
3729 if (rt5677->irq_data) {
3730 regmap_update_bits(rt5677->regmap, RT5677_GPIO_CTRL1, 0x8000,
3731 0x8000);
3732 regmap_update_bits(rt5677->regmap, RT5677_DIG_MISC, 0x0018,
3733 0x0008);
3734
3735 if (rt5677->pdata.jd1_gpio)
3736 regmap_update_bits(rt5677->regmap, RT5677_JD_CTRL1,
3737 RT5677_SEL_GPIO_JD1_MASK,
3738 rt5677->pdata.jd1_gpio <<
3739 RT5677_SEL_GPIO_JD1_SFT);
3740
3741 if (rt5677->pdata.jd2_gpio)
3742 regmap_update_bits(rt5677->regmap, RT5677_JD_CTRL1,
3743 RT5677_SEL_GPIO_JD2_MASK,
3744 rt5677->pdata.jd2_gpio <<
3745 RT5677_SEL_GPIO_JD2_SFT);
3746
3747 if (rt5677->pdata.jd3_gpio)
3748 regmap_update_bits(rt5677->regmap, RT5677_JD_CTRL1,
3749 RT5677_SEL_GPIO_JD3_MASK,
3750 rt5677->pdata.jd3_gpio <<
3751 RT5677_SEL_GPIO_JD3_SFT);
3752 }
3753
3688 mutex_init(&rt5677->dsp_cmd_lock); 3754 mutex_init(&rt5677->dsp_cmd_lock);
3689 3755
3690 return 0; 3756 return 0;
@@ -3915,9 +3981,74 @@ static int rt5677_parse_dt(struct rt5677_priv *rt5677, struct device_node *np)
3915 of_property_read_u8_array(np, "realtek,gpio-config", 3981 of_property_read_u8_array(np, "realtek,gpio-config",
3916 rt5677->pdata.gpio_config, RT5677_GPIO_NUM); 3982 rt5677->pdata.gpio_config, RT5677_GPIO_NUM);
3917 3983
3984 of_property_read_u32(np, "realtek,jd1-gpio", &rt5677->pdata.jd1_gpio);
3985 of_property_read_u32(np, "realtek,jd2-gpio", &rt5677->pdata.jd2_gpio);
3986 of_property_read_u32(np, "realtek,jd3-gpio", &rt5677->pdata.jd3_gpio);
3987
3918 return 0; 3988 return 0;
3919} 3989}
3920 3990
3991static struct regmap_irq rt5677_irqs[] = {
3992 [RT5677_IRQ_JD1] = {
3993 .reg_offset = 0,
3994 .mask = RT5677_EN_IRQ_GPIO_JD1,
3995 },
3996 [RT5677_IRQ_JD2] = {
3997 .reg_offset = 0,
3998 .mask = RT5677_EN_IRQ_GPIO_JD2,
3999 },
4000 [RT5677_IRQ_JD3] = {
4001 .reg_offset = 0,
4002 .mask = RT5677_EN_IRQ_GPIO_JD3,
4003 },
4004};
4005
4006static struct regmap_irq_chip rt5677_irq_chip = {
4007 .name = "rt5677",
4008 .irqs = rt5677_irqs,
4009 .num_irqs = ARRAY_SIZE(rt5677_irqs),
4010
4011 .num_regs = 1,
4012 .status_base = RT5677_IRQ_CTRL1,
4013 .mask_base = RT5677_IRQ_CTRL1,
4014 .mask_invert = 1,
4015};
4016
4017int rt5677_irq_init(struct i2c_client *i2c)
4018{
4019 int ret;
4020 struct rt5677_priv *rt5677 = i2c_get_clientdata(i2c);
4021
4022 if (!rt5677->pdata.jd1_gpio &&
4023 !rt5677->pdata.jd2_gpio &&
4024 !rt5677->pdata.jd3_gpio)
4025 return 0;
4026
4027 if (!i2c->irq) {
4028 dev_err(&i2c->dev, "No interrupt specified\n");
4029 return -EINVAL;
4030 }
4031
4032 ret = regmap_add_irq_chip(rt5677->regmap, i2c->irq,
4033 IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING | IRQF_ONESHOT, 0,
4034 &rt5677_irq_chip, &rt5677->irq_data);
4035
4036 if (ret != 0) {
4037 dev_err(&i2c->dev, "Failed to register IRQ chip: %d\n", ret);
4038 return ret;
4039 }
4040
4041 return 0;
4042}
4043
4044void rt5677_irq_exit(struct i2c_client *i2c)
4045{
4046 struct rt5677_priv *rt5677 = i2c_get_clientdata(i2c);
4047
4048 if (rt5677->irq_data)
4049 regmap_del_irq_chip(i2c->irq, rt5677->irq_data);
4050}
4051
3921static int rt5677_i2c_probe(struct i2c_client *i2c, 4052static int rt5677_i2c_probe(struct i2c_client *i2c,
3922 const struct i2c_device_id *id) 4053 const struct i2c_device_id *id)
3923{ 4054{
@@ -4015,6 +4146,7 @@ static int rt5677_i2c_probe(struct i2c_client *i2c,
4015 } 4146 }
4016 4147
4017 rt5677_init_gpio(i2c); 4148 rt5677_init_gpio(i2c);
4149 rt5677_irq_init(i2c);
4018 4150
4019 return snd_soc_register_codec(&i2c->dev, &soc_codec_dev_rt5677, 4151 return snd_soc_register_codec(&i2c->dev, &soc_codec_dev_rt5677,
4020 rt5677_dai, ARRAY_SIZE(rt5677_dai)); 4152 rt5677_dai, ARRAY_SIZE(rt5677_dai));
@@ -4022,6 +4154,8 @@ static int rt5677_i2c_probe(struct i2c_client *i2c,
4022 4154
4023static int rt5677_i2c_remove(struct i2c_client *i2c) 4155static int rt5677_i2c_remove(struct i2c_client *i2c)
4024{ 4156{
4157 rt5677_irq_exit(i2c);
4158
4025 snd_soc_unregister_codec(&i2c->dev); 4159 snd_soc_unregister_codec(&i2c->dev);
4026 rt5677_free_gpio(i2c); 4160 rt5677_free_gpio(i2c);
4027 4161
diff --git a/sound/soc/codecs/rt5677.h b/sound/soc/codecs/rt5677.h
index 20efa4a4c82c..d2c743c255a1 100644
--- a/sound/soc/codecs/rt5677.h
+++ b/sound/soc/codecs/rt5677.h
@@ -1368,6 +1368,48 @@
1368#define RT5677_SEL_SRC_IB01 (0x1 << 0) 1368#define RT5677_SEL_SRC_IB01 (0x1 << 0)
1369#define RT5677_SEL_SRC_IB01_SFT 0 1369#define RT5677_SEL_SRC_IB01_SFT 0
1370 1370
1371/* Jack Detect Control 1 (0xb5) */
1372#define RT5677_SEL_GPIO_JD1_MASK (0x3 << 14)
1373#define RT5677_SEL_GPIO_JD1_SFT 14
1374#define RT5677_SEL_GPIO_JD2_MASK (0x3 << 12)
1375#define RT5677_SEL_GPIO_JD2_SFT 12
1376#define RT5677_SEL_GPIO_JD3_MASK (0x3 << 10)
1377#define RT5677_SEL_GPIO_JD3_SFT 10
1378
1379/* IRQ Control 1 (0xbd) */
1380#define RT5677_STA_GPIO_JD1 (0x1 << 15)
1381#define RT5677_STA_GPIO_JD1_SFT 15
1382#define RT5677_EN_IRQ_GPIO_JD1 (0x1 << 14)
1383#define RT5677_EN_IRQ_GPIO_JD1_SFT 14
1384#define RT5677_EN_GPIO_JD1_STICKY (0x1 << 13)
1385#define RT5677_EN_GPIO_JD1_STICKY_SFT 13
1386#define RT5677_INV_GPIO_JD1 (0x1 << 12)
1387#define RT5677_INV_GPIO_JD1_SFT 12
1388#define RT5677_STA_GPIO_JD2 (0x1 << 11)
1389#define RT5677_STA_GPIO_JD2_SFT 11
1390#define RT5677_EN_IRQ_GPIO_JD2 (0x1 << 10)
1391#define RT5677_EN_IRQ_GPIO_JD2_SFT 10
1392#define RT5677_EN_GPIO_JD2_STICKY (0x1 << 9)
1393#define RT5677_EN_GPIO_JD2_STICKY_SFT 9
1394#define RT5677_INV_GPIO_JD2 (0x1 << 8)
1395#define RT5677_INV_GPIO_JD2_SFT 8
1396#define RT5677_STA_MICBIAS1_OVCD (0x1 << 7)
1397#define RT5677_STA_MICBIAS1_OVCD_SFT 7
1398#define RT5677_EN_IRQ_MICBIAS1_OVCD (0x1 << 6)
1399#define RT5677_EN_IRQ_MICBIAS1_OVCD_SFT 6
1400#define RT5677_EN_MICBIAS1_OVCD_STICKY (0x1 << 5)
1401#define RT5677_EN_MICBIAS1_OVCD_STICKY_SFT 5
1402#define RT5677_INV_MICBIAS1_OVCD (0x1 << 4)
1403#define RT5677_INV_MICBIAS1_OVCD_SFT 4
1404#define RT5677_STA_GPIO_JD3 (0x1 << 3)
1405#define RT5677_STA_GPIO_JD3_SFT 3
1406#define RT5677_EN_IRQ_GPIO_JD3 (0x1 << 2)
1407#define RT5677_EN_IRQ_GPIO_JD3_SFT 2
1408#define RT5677_EN_GPIO_JD3_STICKY (0x1 << 1)
1409#define RT5677_EN_GPIO_JD3_STICKY_SFT 1
1410#define RT5677_INV_GPIO_JD3 (0x1 << 0)
1411#define RT5677_INV_GPIO_JD3_SFT 0
1412
1371/* GPIO status (0xbf) */ 1413/* GPIO status (0xbf) */
1372#define RT5677_GPIO6_STATUS_MASK (0x1 << 5) 1414#define RT5677_GPIO6_STATUS_MASK (0x1 << 5)
1373#define RT5677_GPIO6_STATUS_SFT 5 1415#define RT5677_GPIO6_STATUS_SFT 5
@@ -1545,6 +1587,12 @@ enum {
1545 RT5677_GPIO_NUM, 1587 RT5677_GPIO_NUM,
1546}; 1588};
1547 1589
1590enum {
1591 RT5677_IRQ_JD1,
1592 RT5677_IRQ_JD2,
1593 RT5677_IRQ_JD3,
1594};
1595
1548struct rt5677_priv { 1596struct rt5677_priv {
1549 struct snd_soc_codec *codec; 1597 struct snd_soc_codec *codec;
1550 struct rt5677_platform_data pdata; 1598 struct rt5677_platform_data pdata;
@@ -1565,6 +1613,7 @@ struct rt5677_priv {
1565 struct gpio_chip gpio_chip; 1613 struct gpio_chip gpio_chip;
1566#endif 1614#endif
1567 bool dsp_vad_en; 1615 bool dsp_vad_en;
1616 struct regmap_irq_chip_data *irq_data;
1568}; 1617};
1569 1618
1570#endif /* __RT5677_H__ */ 1619#endif /* __RT5677_H__ */