From: Lucas Tanure <tanureal@opensource.cirrus.com> To: Liam Girdwood <lgirdwood@gmail.com>, Mark Brown <broonie@kernel.org>, Rob Herring <robh+dt@kernel.org>, Krzysztof Kozlowski <krzysztof.kozlowski+dt@linaro.org>, Jaroslav Kysela <perex@perex.cz>, Takashi Iwai <tiwai@suse.com> Cc: <alsa-devel@alsa-project.org>, <patches@opensource.cirrus.com>, <devicetree@vger.kernel.org>, <linux-kernel@vger.kernel.org>, Lucas Tanure <tanureal@opensource.cirrus.com> Subject: [PATCH v6 14/16] ALSA: hda: cs35l41: Move external boost handling to lib for ASoC use Date: Sat, 9 Apr 2022 10:13:13 +0100 [thread overview] Message-ID: <20220409091315.1663410-15-tanureal@opensource.cirrus.com> (raw) In-Reply-To: <20220409091315.1663410-1-tanureal@opensource.cirrus.com> To add support for external boost for ASoC move the HDA external boost implementation to the shared lib. Signed-off-by: Lucas Tanure <tanureal@opensource.cirrus.com> --- include/sound/cs35l41.h | 4 + sound/pci/hda/cs35l41_hda.c | 119 ++---------------------------- sound/soc/codecs/cs35l41-lib.c | 129 ++++++++++++++++++++++++++++++++- 3 files changed, 137 insertions(+), 115 deletions(-) diff --git a/include/sound/cs35l41.h b/include/sound/cs35l41.h index ecbb140cd723..53b1c28d8223 100644 --- a/include/sound/cs35l41.h +++ b/include/sound/cs35l41.h @@ -804,5 +804,9 @@ int cs35l41_set_channels(struct device *dev, struct regmap *reg, int cs35l41_boost_config(struct device *dev, struct regmap *regmap, int boost_ind, int boost_cap, int boost_ipk); int cs35l41_gpio_config(struct regmap *regmap, struct cs35l41_hw_cfg *hw_cfg); +int cs35l41_init_boost(struct device *dev, struct regmap *regmap, + struct cs35l41_hw_cfg *hw_cfg); +bool cs35l41_safe_reset(struct regmap *regmap, enum cs35l41_boost_type b_type); +int cs35l41_global_enable(struct regmap *regmap, enum cs35l41_boost_type b_type, int enable); #endif /* __CS35L41_H */ diff --git a/sound/pci/hda/cs35l41_hda.c b/sound/pci/hda/cs35l41_hda.c index e54b5fbb6fb5..bc277b352ac9 100644 --- a/sound/pci/hda/cs35l41_hda.c +++ b/sound/pci/hda/cs35l41_hda.c @@ -32,94 +32,6 @@ static const struct reg_sequence cs35l41_hda_mute[] = { { CS35L41_AMP_DIG_VOL_CTRL, 0x0000A678 }, // AMP_VOL_PCM Mute }; -static const struct reg_sequence cs35l41_safe_to_reset[] = { - { 0x00000040, 0x00000055 }, - { 0x00000040, 0x000000AA }, - { 0x0000393C, 0x000000C0, 6000}, - { 0x0000393C, 0x00000000 }, - { 0x00007414, 0x00C82222 }, - { 0x0000742C, 0x00000000 }, - { 0x00000040, 0x000000CC }, - { 0x00000040, 0x00000033 }, -}; - -static const struct reg_sequence cs35l41_safe_to_active[] = { - { 0x00000040, 0x00000055 }, - { 0x00000040, 0x000000AA }, - { 0x0000742C, 0x0000000F }, - { 0x0000742C, 0x00000079 }, - { 0x00007438, 0x00585941 }, - { CS35L41_PWR_CTRL1, 0x00000001, 3000 }, // GLOBAL_EN = 1 - { 0x0000742C, 0x000000F9 }, - { 0x00007438, 0x00580941 }, - { 0x00000040, 0x000000CC }, - { 0x00000040, 0x00000033 }, -}; - -static const struct reg_sequence cs35l41_active_to_safe[] = { - { 0x00000040, 0x00000055 }, - { 0x00000040, 0x000000AA }, - { 0x00007438, 0x00585941 }, - { CS35L41_PWR_CTRL1, 0x00000000 }, - { 0x0000742C, 0x00000009, 3000 }, - { 0x00007438, 0x00580941 }, - { 0x00000040, 0x000000CC }, - { 0x00000040, 0x00000033 }, -}; - -static const struct reg_sequence cs35l41_reset_to_safe[] = { - { 0x00000040, 0x00000055 }, - { 0x00000040, 0x000000AA }, - { 0x00007438, 0x00585941 }, - { 0x00007414, 0x08C82222 }, - { 0x0000742C, 0x00000009 }, - { 0x00000040, 0x000000CC }, - { 0x00000040, 0x00000033 }, -}; - -static bool cs35l41_hda_safe_reset(struct cs35l41_hda *cs35l41) -{ - switch (cs35l41->hw_cfg.bst_type) { - case CS35L41_EXT_BOOST: - regmap_write(cs35l41->regmap, CS35L41_GPIO1_CTRL1, 0x00000001); - regmap_multi_reg_write(cs35l41->regmap, cs35l41_safe_to_reset, - ARRAY_SIZE(cs35l41_safe_to_reset)); - return true; - case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: - return false; - default: - return true; - } -}; - -static int cs35l41_hda_global_enable(struct cs35l41_hda *cs35l41, int enable) -{ - int ret; - - switch (cs35l41->hw_cfg.bst_type) { - case CS35L41_INT_BOOST: - ret = regmap_update_bits(cs35l41->regmap, CS35L41_PWR_CTRL1, - CS35L41_GLOBAL_EN_MASK, - enable << CS35L41_GLOBAL_EN_SHIFT); - usleep_range(3000, 3100); - break; - case CS35L41_EXT_BOOST: - case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: - if (enable) - ret = regmap_multi_reg_write(cs35l41->regmap, cs35l41_safe_to_active, - ARRAY_SIZE(cs35l41_safe_to_active)); - else - ret = regmap_multi_reg_write(cs35l41->regmap, cs35l41_active_to_safe, - ARRAY_SIZE(cs35l41_active_to_safe)); - break; - default: - ret = -EINVAL; - break; - } - - return ret; -}; - static void cs35l41_hda_playback_hook(struct device *dev, int action) { struct cs35l41_hda *cs35l41 = dev_get_drvdata(dev); @@ -135,11 +47,11 @@ static void cs35l41_hda_playback_hook(struct device *dev, int action) regmap_write(reg, CS35L41_GPIO1_CTRL1, 0x00008001); break; case HDA_GEN_PCM_ACT_PREPARE: - ret = cs35l41_hda_global_enable(cs35l41, 1); + ret = cs35l41_global_enable(reg, cs35l41->hw_cfg.bst_type, 1); break; case HDA_GEN_PCM_ACT_CLEANUP: regmap_multi_reg_write(reg, cs35l41_hda_mute, ARRAY_SIZE(cs35l41_hda_mute)); - ret = cs35l41_hda_global_enable(cs35l41, 0); + ret = cs35l41_global_enable(reg, cs35l41->hw_cfg.bst_type, 0); break; case HDA_GEN_PCM_ACT_CLOSE: ret = regmap_update_bits(reg, CS35L41_PWR_CTRL2, @@ -207,26 +119,9 @@ static int cs35l41_hda_apply_properties(struct cs35l41_hda *cs35l41) if (!cs35l41->hw_cfg.valid) return -EINVAL; - switch (hw_cfg->bst_type) { - case CS35L41_INT_BOOST: - ret = cs35l41_boost_config(cs35l41->dev, cs35l41->regmap, - hw_cfg->bst_ind, hw_cfg->bst_cap, hw_cfg->bst_ipk); - if (ret) - return ret; - break; - case CS35L41_EXT_BOOST: - case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: - regmap_multi_reg_write(cs35l41->regmap, cs35l41_reset_to_safe, - ARRAY_SIZE(cs35l41_reset_to_safe)); - ret = regmap_update_bits(cs35l41->regmap, CS35L41_PWR_CTRL2, CS35L41_BST_EN_MASK, - CS35L41_BST_DIS_FET_OFF << CS35L41_BST_EN_SHIFT); - if (ret) - return ret; - break; - default: - dev_err(cs35l41->dev, "Boost type %d not supported\n", hw_cfg->bst_type); - return -EINVAL; - } + ret = cs35l41_init_boost(cs35l41->dev, cs35l41->regmap, hw_cfg); + if (ret) + return ret; if (hw_cfg->gpio1.valid) { switch (hw_cfg->gpio1.func) { @@ -505,7 +400,7 @@ int cs35l41_hda_probe(struct device *dev, const char *device_name, int id, int i return 0; err: - if (cs35l41_hda_safe_reset(cs35l41)) + if (cs35l41_safe_reset(cs35l41->regmap, cs35l41->hw_cfg.bst_type)) gpiod_set_value_cansleep(cs35l41->reset_gpio, 0); gpiod_put(cs35l41->reset_gpio); @@ -519,7 +414,7 @@ void cs35l41_hda_remove(struct device *dev) component_del(cs35l41->dev, &cs35l41_hda_comp_ops); - if (cs35l41_hda_safe_reset(cs35l41)) + if (cs35l41_safe_reset(cs35l41->regmap, cs35l41->hw_cfg.bst_type)) gpiod_set_value_cansleep(cs35l41->reset_gpio, 0); gpiod_put(cs35l41->reset_gpio); } diff --git a/sound/soc/codecs/cs35l41-lib.c b/sound/soc/codecs/cs35l41-lib.c index 1830f9212102..71024b037c35 100644 --- a/sound/soc/codecs/cs35l41-lib.c +++ b/sound/soc/codecs/cs35l41-lib.c @@ -956,9 +956,8 @@ static const unsigned char cs35l41_bst_slope_table[4] = { 0x75, 0x6B, 0x3B, 0x28 }; - -int cs35l41_boost_config(struct device *dev, struct regmap *regmap, int boost_ind, int boost_cap, - int boost_ipk) +int cs35l41_boost_config(struct device *dev, struct regmap *regmap, int boost_ind, + int boost_cap, int boost_ipk) { unsigned char bst_lbst_val, bst_cbst_range, bst_ipk_scaled; int ret; @@ -1045,6 +1044,130 @@ int cs35l41_boost_config(struct device *dev, struct regmap *regmap, int boost_in } EXPORT_SYMBOL_GPL(cs35l41_boost_config); +static const struct reg_sequence cs35l41_safe_to_reset[] = { + { 0x00000040, 0x00000055 }, + { 0x00000040, 0x000000AA }, + { 0x0000393C, 0x000000C0, 6000}, + { 0x0000393C, 0x00000000 }, + { 0x00007414, 0x00C82222 }, + { 0x0000742C, 0x00000000 }, + { 0x00000040, 0x000000CC }, + { 0x00000040, 0x00000033 }, +}; + +static const struct reg_sequence cs35l41_active_to_safe[] = { + { 0x00000040, 0x00000055 }, + { 0x00000040, 0x000000AA }, + { 0x00007438, 0x00585941 }, + { CS35L41_PWR_CTRL1, 0x00000000 }, + { 0x0000742C, 0x00000009, 3000 }, + { 0x00007438, 0x00580941 }, + { 0x00000040, 0x000000CC }, + { 0x00000040, 0x00000033 }, +}; + +static const struct reg_sequence cs35l41_safe_to_active[] = { + { 0x00000040, 0x00000055 }, + { 0x00000040, 0x000000AA }, + { 0x0000742C, 0x0000000F }, + { 0x0000742C, 0x00000079 }, + { 0x00007438, 0x00585941 }, + { CS35L41_PWR_CTRL1, 0x00000001, 3000 }, // GLOBAL_EN = 1 + { 0x0000742C, 0x000000F9 }, + { 0x00007438, 0x00580941 }, + { 0x00000040, 0x000000CC }, + { 0x00000040, 0x00000033 }, +}; + +static const struct reg_sequence cs35l41_reset_to_safe[] = { + { 0x00000040, 0x00000055 }, + { 0x00000040, 0x000000AA }, + { 0x00007438, 0x00585941 }, + { 0x00007414, 0x08C82222 }, + { 0x0000742C, 0x00000009 }, + { 0x00000040, 0x000000CC }, + { 0x00000040, 0x00000033 }, +}; + +int cs35l41_init_boost(struct device *dev, struct regmap *regmap, + struct cs35l41_hw_cfg *hw_cfg) +{ + int ret; + + switch (hw_cfg->bst_type) { + case CS35L41_INT_BOOST: + ret = cs35l41_boost_config(dev, regmap, hw_cfg->bst_ind, + hw_cfg->bst_cap, hw_cfg->bst_ipk); + if (ret) + dev_err(dev, "Error in Boost DT config: %d\n", ret); + break; + case CS35L41_EXT_BOOST: + case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: + /* Only CLSA0100 doesn't use GPIO as VSPK switch, but even on that laptop we can + * toggle GPIO1 as is not connected to anything. + * There will be no other device without VSPK switch. + */ + regmap_write(regmap, CS35L41_GPIO1_CTRL1, 0x00000001); + regmap_multi_reg_write(regmap, cs35l41_reset_to_safe, + ARRAY_SIZE(cs35l41_reset_to_safe)); + ret = regmap_update_bits(regmap, CS35L41_PWR_CTRL2, CS35L41_BST_EN_MASK, + CS35L41_BST_DIS_FET_OFF << CS35L41_BST_EN_SHIFT); + break; + default: + dev_err(dev, "Boost type %d not supported\n", hw_cfg->bst_type); + ret = -EINVAL; + break; + } + + return ret; +} +EXPORT_SYMBOL_GPL(cs35l41_init_boost); + +bool cs35l41_safe_reset(struct regmap *regmap, enum cs35l41_boost_type b_type) +{ + switch (b_type) { + /* There is only one laptop that doesn't have VSPK switch. */ + case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: + return false; + case CS35L41_EXT_BOOST: + regmap_write(regmap, CS35L41_GPIO1_CTRL1, 0x00000001); + regmap_multi_reg_write(regmap, cs35l41_safe_to_reset, + ARRAY_SIZE(cs35l41_safe_to_reset)); + return true; + default: + return true; + } +} +EXPORT_SYMBOL_GPL(cs35l41_safe_reset); + +int cs35l41_global_enable(struct regmap *regmap, enum cs35l41_boost_type b_type, int enable) +{ + int ret; + + switch (b_type) { + case CS35L41_INT_BOOST: + ret = regmap_update_bits(regmap, CS35L41_PWR_CTRL1, CS35L41_GLOBAL_EN_MASK, + enable << CS35L41_GLOBAL_EN_SHIFT); + usleep_range(3000, 3100); + break; + case CS35L41_EXT_BOOST: + case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: + if (enable) + ret = regmap_multi_reg_write(regmap, cs35l41_safe_to_active, + ARRAY_SIZE(cs35l41_safe_to_active)); + else + ret = regmap_multi_reg_write(regmap, cs35l41_active_to_safe, + ARRAY_SIZE(cs35l41_active_to_safe)); + break; + default: + ret = -EINVAL; + break; + } + + return ret; +} +EXPORT_SYMBOL_GPL(cs35l41_global_enable); + int cs35l41_gpio_config(struct regmap *regmap, struct cs35l41_hw_cfg *hw_cfg) { struct cs35l41_gpio_cfg *gpio1 = &hw_cfg->gpio1; -- 2.35.1
WARNING: multiple messages have this Message-ID (diff)
From: Lucas Tanure <tanureal@opensource.cirrus.com> To: Liam Girdwood <lgirdwood@gmail.com>, Mark Brown <broonie@kernel.org>, Rob Herring <robh+dt@kernel.org>, Krzysztof Kozlowski <krzysztof.kozlowski+dt@linaro.org>, Jaroslav Kysela <perex@perex.cz>, Takashi Iwai <tiwai@suse.com> Cc: patches@opensource.cirrus.com, alsa-devel@alsa-project.org, linux-kernel@vger.kernel.org, Lucas Tanure <tanureal@opensource.cirrus.com>, devicetree@vger.kernel.org Subject: [PATCH v6 14/16] ALSA: hda: cs35l41: Move external boost handling to lib for ASoC use Date: Sat, 9 Apr 2022 10:13:13 +0100 [thread overview] Message-ID: <20220409091315.1663410-15-tanureal@opensource.cirrus.com> (raw) In-Reply-To: <20220409091315.1663410-1-tanureal@opensource.cirrus.com> To add support for external boost for ASoC move the HDA external boost implementation to the shared lib. Signed-off-by: Lucas Tanure <tanureal@opensource.cirrus.com> --- include/sound/cs35l41.h | 4 + sound/pci/hda/cs35l41_hda.c | 119 ++---------------------------- sound/soc/codecs/cs35l41-lib.c | 129 ++++++++++++++++++++++++++++++++- 3 files changed, 137 insertions(+), 115 deletions(-) diff --git a/include/sound/cs35l41.h b/include/sound/cs35l41.h index ecbb140cd723..53b1c28d8223 100644 --- a/include/sound/cs35l41.h +++ b/include/sound/cs35l41.h @@ -804,5 +804,9 @@ int cs35l41_set_channels(struct device *dev, struct regmap *reg, int cs35l41_boost_config(struct device *dev, struct regmap *regmap, int boost_ind, int boost_cap, int boost_ipk); int cs35l41_gpio_config(struct regmap *regmap, struct cs35l41_hw_cfg *hw_cfg); +int cs35l41_init_boost(struct device *dev, struct regmap *regmap, + struct cs35l41_hw_cfg *hw_cfg); +bool cs35l41_safe_reset(struct regmap *regmap, enum cs35l41_boost_type b_type); +int cs35l41_global_enable(struct regmap *regmap, enum cs35l41_boost_type b_type, int enable); #endif /* __CS35L41_H */ diff --git a/sound/pci/hda/cs35l41_hda.c b/sound/pci/hda/cs35l41_hda.c index e54b5fbb6fb5..bc277b352ac9 100644 --- a/sound/pci/hda/cs35l41_hda.c +++ b/sound/pci/hda/cs35l41_hda.c @@ -32,94 +32,6 @@ static const struct reg_sequence cs35l41_hda_mute[] = { { CS35L41_AMP_DIG_VOL_CTRL, 0x0000A678 }, // AMP_VOL_PCM Mute }; -static const struct reg_sequence cs35l41_safe_to_reset[] = { - { 0x00000040, 0x00000055 }, - { 0x00000040, 0x000000AA }, - { 0x0000393C, 0x000000C0, 6000}, - { 0x0000393C, 0x00000000 }, - { 0x00007414, 0x00C82222 }, - { 0x0000742C, 0x00000000 }, - { 0x00000040, 0x000000CC }, - { 0x00000040, 0x00000033 }, -}; - -static const struct reg_sequence cs35l41_safe_to_active[] = { - { 0x00000040, 0x00000055 }, - { 0x00000040, 0x000000AA }, - { 0x0000742C, 0x0000000F }, - { 0x0000742C, 0x00000079 }, - { 0x00007438, 0x00585941 }, - { CS35L41_PWR_CTRL1, 0x00000001, 3000 }, // GLOBAL_EN = 1 - { 0x0000742C, 0x000000F9 }, - { 0x00007438, 0x00580941 }, - { 0x00000040, 0x000000CC }, - { 0x00000040, 0x00000033 }, -}; - -static const struct reg_sequence cs35l41_active_to_safe[] = { - { 0x00000040, 0x00000055 }, - { 0x00000040, 0x000000AA }, - { 0x00007438, 0x00585941 }, - { CS35L41_PWR_CTRL1, 0x00000000 }, - { 0x0000742C, 0x00000009, 3000 }, - { 0x00007438, 0x00580941 }, - { 0x00000040, 0x000000CC }, - { 0x00000040, 0x00000033 }, -}; - -static const struct reg_sequence cs35l41_reset_to_safe[] = { - { 0x00000040, 0x00000055 }, - { 0x00000040, 0x000000AA }, - { 0x00007438, 0x00585941 }, - { 0x00007414, 0x08C82222 }, - { 0x0000742C, 0x00000009 }, - { 0x00000040, 0x000000CC }, - { 0x00000040, 0x00000033 }, -}; - -static bool cs35l41_hda_safe_reset(struct cs35l41_hda *cs35l41) -{ - switch (cs35l41->hw_cfg.bst_type) { - case CS35L41_EXT_BOOST: - regmap_write(cs35l41->regmap, CS35L41_GPIO1_CTRL1, 0x00000001); - regmap_multi_reg_write(cs35l41->regmap, cs35l41_safe_to_reset, - ARRAY_SIZE(cs35l41_safe_to_reset)); - return true; - case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: - return false; - default: - return true; - } -}; - -static int cs35l41_hda_global_enable(struct cs35l41_hda *cs35l41, int enable) -{ - int ret; - - switch (cs35l41->hw_cfg.bst_type) { - case CS35L41_INT_BOOST: - ret = regmap_update_bits(cs35l41->regmap, CS35L41_PWR_CTRL1, - CS35L41_GLOBAL_EN_MASK, - enable << CS35L41_GLOBAL_EN_SHIFT); - usleep_range(3000, 3100); - break; - case CS35L41_EXT_BOOST: - case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: - if (enable) - ret = regmap_multi_reg_write(cs35l41->regmap, cs35l41_safe_to_active, - ARRAY_SIZE(cs35l41_safe_to_active)); - else - ret = regmap_multi_reg_write(cs35l41->regmap, cs35l41_active_to_safe, - ARRAY_SIZE(cs35l41_active_to_safe)); - break; - default: - ret = -EINVAL; - break; - } - - return ret; -}; - static void cs35l41_hda_playback_hook(struct device *dev, int action) { struct cs35l41_hda *cs35l41 = dev_get_drvdata(dev); @@ -135,11 +47,11 @@ static void cs35l41_hda_playback_hook(struct device *dev, int action) regmap_write(reg, CS35L41_GPIO1_CTRL1, 0x00008001); break; case HDA_GEN_PCM_ACT_PREPARE: - ret = cs35l41_hda_global_enable(cs35l41, 1); + ret = cs35l41_global_enable(reg, cs35l41->hw_cfg.bst_type, 1); break; case HDA_GEN_PCM_ACT_CLEANUP: regmap_multi_reg_write(reg, cs35l41_hda_mute, ARRAY_SIZE(cs35l41_hda_mute)); - ret = cs35l41_hda_global_enable(cs35l41, 0); + ret = cs35l41_global_enable(reg, cs35l41->hw_cfg.bst_type, 0); break; case HDA_GEN_PCM_ACT_CLOSE: ret = regmap_update_bits(reg, CS35L41_PWR_CTRL2, @@ -207,26 +119,9 @@ static int cs35l41_hda_apply_properties(struct cs35l41_hda *cs35l41) if (!cs35l41->hw_cfg.valid) return -EINVAL; - switch (hw_cfg->bst_type) { - case CS35L41_INT_BOOST: - ret = cs35l41_boost_config(cs35l41->dev, cs35l41->regmap, - hw_cfg->bst_ind, hw_cfg->bst_cap, hw_cfg->bst_ipk); - if (ret) - return ret; - break; - case CS35L41_EXT_BOOST: - case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: - regmap_multi_reg_write(cs35l41->regmap, cs35l41_reset_to_safe, - ARRAY_SIZE(cs35l41_reset_to_safe)); - ret = regmap_update_bits(cs35l41->regmap, CS35L41_PWR_CTRL2, CS35L41_BST_EN_MASK, - CS35L41_BST_DIS_FET_OFF << CS35L41_BST_EN_SHIFT); - if (ret) - return ret; - break; - default: - dev_err(cs35l41->dev, "Boost type %d not supported\n", hw_cfg->bst_type); - return -EINVAL; - } + ret = cs35l41_init_boost(cs35l41->dev, cs35l41->regmap, hw_cfg); + if (ret) + return ret; if (hw_cfg->gpio1.valid) { switch (hw_cfg->gpio1.func) { @@ -505,7 +400,7 @@ int cs35l41_hda_probe(struct device *dev, const char *device_name, int id, int i return 0; err: - if (cs35l41_hda_safe_reset(cs35l41)) + if (cs35l41_safe_reset(cs35l41->regmap, cs35l41->hw_cfg.bst_type)) gpiod_set_value_cansleep(cs35l41->reset_gpio, 0); gpiod_put(cs35l41->reset_gpio); @@ -519,7 +414,7 @@ void cs35l41_hda_remove(struct device *dev) component_del(cs35l41->dev, &cs35l41_hda_comp_ops); - if (cs35l41_hda_safe_reset(cs35l41)) + if (cs35l41_safe_reset(cs35l41->regmap, cs35l41->hw_cfg.bst_type)) gpiod_set_value_cansleep(cs35l41->reset_gpio, 0); gpiod_put(cs35l41->reset_gpio); } diff --git a/sound/soc/codecs/cs35l41-lib.c b/sound/soc/codecs/cs35l41-lib.c index 1830f9212102..71024b037c35 100644 --- a/sound/soc/codecs/cs35l41-lib.c +++ b/sound/soc/codecs/cs35l41-lib.c @@ -956,9 +956,8 @@ static const unsigned char cs35l41_bst_slope_table[4] = { 0x75, 0x6B, 0x3B, 0x28 }; - -int cs35l41_boost_config(struct device *dev, struct regmap *regmap, int boost_ind, int boost_cap, - int boost_ipk) +int cs35l41_boost_config(struct device *dev, struct regmap *regmap, int boost_ind, + int boost_cap, int boost_ipk) { unsigned char bst_lbst_val, bst_cbst_range, bst_ipk_scaled; int ret; @@ -1045,6 +1044,130 @@ int cs35l41_boost_config(struct device *dev, struct regmap *regmap, int boost_in } EXPORT_SYMBOL_GPL(cs35l41_boost_config); +static const struct reg_sequence cs35l41_safe_to_reset[] = { + { 0x00000040, 0x00000055 }, + { 0x00000040, 0x000000AA }, + { 0x0000393C, 0x000000C0, 6000}, + { 0x0000393C, 0x00000000 }, + { 0x00007414, 0x00C82222 }, + { 0x0000742C, 0x00000000 }, + { 0x00000040, 0x000000CC }, + { 0x00000040, 0x00000033 }, +}; + +static const struct reg_sequence cs35l41_active_to_safe[] = { + { 0x00000040, 0x00000055 }, + { 0x00000040, 0x000000AA }, + { 0x00007438, 0x00585941 }, + { CS35L41_PWR_CTRL1, 0x00000000 }, + { 0x0000742C, 0x00000009, 3000 }, + { 0x00007438, 0x00580941 }, + { 0x00000040, 0x000000CC }, + { 0x00000040, 0x00000033 }, +}; + +static const struct reg_sequence cs35l41_safe_to_active[] = { + { 0x00000040, 0x00000055 }, + { 0x00000040, 0x000000AA }, + { 0x0000742C, 0x0000000F }, + { 0x0000742C, 0x00000079 }, + { 0x00007438, 0x00585941 }, + { CS35L41_PWR_CTRL1, 0x00000001, 3000 }, // GLOBAL_EN = 1 + { 0x0000742C, 0x000000F9 }, + { 0x00007438, 0x00580941 }, + { 0x00000040, 0x000000CC }, + { 0x00000040, 0x00000033 }, +}; + +static const struct reg_sequence cs35l41_reset_to_safe[] = { + { 0x00000040, 0x00000055 }, + { 0x00000040, 0x000000AA }, + { 0x00007438, 0x00585941 }, + { 0x00007414, 0x08C82222 }, + { 0x0000742C, 0x00000009 }, + { 0x00000040, 0x000000CC }, + { 0x00000040, 0x00000033 }, +}; + +int cs35l41_init_boost(struct device *dev, struct regmap *regmap, + struct cs35l41_hw_cfg *hw_cfg) +{ + int ret; + + switch (hw_cfg->bst_type) { + case CS35L41_INT_BOOST: + ret = cs35l41_boost_config(dev, regmap, hw_cfg->bst_ind, + hw_cfg->bst_cap, hw_cfg->bst_ipk); + if (ret) + dev_err(dev, "Error in Boost DT config: %d\n", ret); + break; + case CS35L41_EXT_BOOST: + case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: + /* Only CLSA0100 doesn't use GPIO as VSPK switch, but even on that laptop we can + * toggle GPIO1 as is not connected to anything. + * There will be no other device without VSPK switch. + */ + regmap_write(regmap, CS35L41_GPIO1_CTRL1, 0x00000001); + regmap_multi_reg_write(regmap, cs35l41_reset_to_safe, + ARRAY_SIZE(cs35l41_reset_to_safe)); + ret = regmap_update_bits(regmap, CS35L41_PWR_CTRL2, CS35L41_BST_EN_MASK, + CS35L41_BST_DIS_FET_OFF << CS35L41_BST_EN_SHIFT); + break; + default: + dev_err(dev, "Boost type %d not supported\n", hw_cfg->bst_type); + ret = -EINVAL; + break; + } + + return ret; +} +EXPORT_SYMBOL_GPL(cs35l41_init_boost); + +bool cs35l41_safe_reset(struct regmap *regmap, enum cs35l41_boost_type b_type) +{ + switch (b_type) { + /* There is only one laptop that doesn't have VSPK switch. */ + case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: + return false; + case CS35L41_EXT_BOOST: + regmap_write(regmap, CS35L41_GPIO1_CTRL1, 0x00000001); + regmap_multi_reg_write(regmap, cs35l41_safe_to_reset, + ARRAY_SIZE(cs35l41_safe_to_reset)); + return true; + default: + return true; + } +} +EXPORT_SYMBOL_GPL(cs35l41_safe_reset); + +int cs35l41_global_enable(struct regmap *regmap, enum cs35l41_boost_type b_type, int enable) +{ + int ret; + + switch (b_type) { + case CS35L41_INT_BOOST: + ret = regmap_update_bits(regmap, CS35L41_PWR_CTRL1, CS35L41_GLOBAL_EN_MASK, + enable << CS35L41_GLOBAL_EN_SHIFT); + usleep_range(3000, 3100); + break; + case CS35L41_EXT_BOOST: + case CS35L41_EXT_BOOST_NO_VSPK_SWITCH: + if (enable) + ret = regmap_multi_reg_write(regmap, cs35l41_safe_to_active, + ARRAY_SIZE(cs35l41_safe_to_active)); + else + ret = regmap_multi_reg_write(regmap, cs35l41_active_to_safe, + ARRAY_SIZE(cs35l41_active_to_safe)); + break; + default: + ret = -EINVAL; + break; + } + + return ret; +} +EXPORT_SYMBOL_GPL(cs35l41_global_enable); + int cs35l41_gpio_config(struct regmap *regmap, struct cs35l41_hw_cfg *hw_cfg) { struct cs35l41_gpio_cfg *gpio1 = &hw_cfg->gpio1; -- 2.35.1
next prev parent reply other threads:[~2022-04-09 9:14 UTC|newest] Thread overview: 49+ messages / expand[flat|nested] mbox.gz Atom feed top 2022-04-09 9:12 [PATCH v6 00/16] Support external boost at CS35l41 ASoC driver Lucas Tanure 2022-04-09 9:12 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 01/16] ALSA: cs35l41: Unify hardware configuration Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 02/16] ALSA: cs35l41: Check hw_config before using it Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 03/16] ALSA: cs35l41: Move cs35l41_gpio_config to shared lib Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 04/16] ALSA: hda: cs35l41: Fix I2S params comments Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 05/16] ALSA: hda: cs35l41: Always configure the DAI Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 06/16] ALSA: hda: cs35l41: Add Boost type flag Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 07/16] ALSA: hda: cs35l41: Put the device into safe mode for external boost Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 08/16] ALSA: hda: cs35l41: Mute the device before shutdown Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 09/16] ALSA: cs35l41: Enable Internal Boost in shared lib Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 10/16] ALSA: hda: cs35l41: Move boost config to initialization code Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 11/16] ALSA: hda: cs35l41: Remove cs35l41_hda_reg_sequence struct Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 12/16] ALSA: hda: cs35l41: Reorganize log for playback actions Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 13/16] ALSA: hda: cs35l41: Handle all external boost setups the same way Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure [this message] 2022-04-09 9:13 ` [PATCH v6 14/16] ALSA: hda: cs35l41: Move external boost handling to lib for ASoC use Lucas Tanure 2022-04-09 9:13 ` [PATCH v6 15/16] ASoC: cs35l41: Document CS35l41 External Boost Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-12 14:44 ` Mark Brown 2022-04-12 14:44 ` Mark Brown 2022-04-09 9:13 ` [PATCH v6 16/16] ASoC: cs35l41: Support external boost Lucas Tanure 2022-04-09 9:13 ` Lucas Tanure 2022-04-12 14:54 ` Mark Brown 2022-04-12 14:54 ` Mark Brown 2022-04-12 10:40 ` [PATCH v6 00/16] Support external boost at CS35l41 ASoC driver Takashi Iwai 2022-04-12 10:40 ` Takashi Iwai 2022-04-13 7:51 ` Takashi Iwai 2022-04-13 7:51 ` Takashi Iwai 2022-04-13 8:10 ` tanureal 2022-04-13 8:12 ` Takashi Iwai 2022-04-13 8:12 ` Takashi Iwai 2022-04-13 8:21 ` Takashi Iwai 2022-04-13 8:21 ` Takashi Iwai 2022-04-13 8:22 ` Takashi Iwai 2022-04-13 8:22 ` Takashi Iwai
Reply instructions: You may reply publicly to this message via plain-text email using any one of the following methods: * Save the following mbox file, import it into your mail client, and reply-to-all from there: mbox Avoid top-posting and favor interleaved quoting: https://en.wikipedia.org/wiki/Posting_style#Interleaved_style * Reply using the --to, --cc, and --in-reply-to switches of git-send-email(1): git send-email \ --in-reply-to=20220409091315.1663410-15-tanureal@opensource.cirrus.com \ --to=tanureal@opensource.cirrus.com \ --cc=alsa-devel@alsa-project.org \ --cc=broonie@kernel.org \ --cc=devicetree@vger.kernel.org \ --cc=krzysztof.kozlowski+dt@linaro.org \ --cc=lgirdwood@gmail.com \ --cc=linux-kernel@vger.kernel.org \ --cc=patches@opensource.cirrus.com \ --cc=perex@perex.cz \ --cc=robh+dt@kernel.org \ --cc=tiwai@suse.com \ /path/to/YOUR_REPLY https://kernel.org/pub/software/scm/git/docs/git-send-email.html * If your mail client supports setting the In-Reply-To header via mailto: links, try the mailto: linkBe sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes, see mirroring instructions on how to clone and mirror all data and code used by this external index.