ASoC: dt-bindings: max98388: add amplifier driver
Subsystems (4)
PATCH v2 1/2 ASoC: dt-bindings: max98388: add amplifier driver
From: Ryan Lee <[email protected]>
Add dt-bindings information for Analog Devices MAX98388 I2S Amplifier
---
Changes from v1:
Removed unnecessary blank line and description. Modified quotes.
.../bindings/sound/adi,max98388.yaml | 79 +++++++++++++++++++ 1 file changed, 79 insertions(+) create mode 100644 Documentation/devicetree/bindings/sound/adi,max98388.yaml
Documentation/devicetree/bindings/sound/adi,max98388.yaml new file +79 -0
@@ -0,0 +1,79 @@ +# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/sound/adi,max98388.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Analog Devices MAX98388 Speaker Amplifier + +maintainers: + - Ryan Lee <[email protected]> + +description: + The MAX98388 is a mono Class-D speaker amplifier with I/V feedback. + The device provides a PCM interface for audio data and a standard + I2C interface for control data communication. + +allOf: + - $ref: dai-common.yaml# + +properties: + compatible: + enum: + - adi,max98388 + + reg: + maxItems: 1 + + '#sound-dai-cells': + const: 0 + + adi,vmon-slot-no: + description: slot number of the voltage feedback monitor + $ref: /schemas/types.yaml#/definitions/uint32 + minimum: 0 + maximum: 15 + default: 0 + + adi,imon-slot-no: + description: slot number of the current feedback monitor + $ref: /schemas/types.yaml#/definitions/uint32 + minimum: 0 + maximum: 15 + default: 1 + + adi,interleave-mode: + description: + For cases where a single combined channel for the I/V feedback data + is not sufficient, the device can also be configured to share + a single data output channel on alternating frames. + In this configuration, the current and voltage data will be frame + interleaved on a single output channel. + type: boolean + + reset-gpios: + maxItems: 1 + +required: + - compatible + - reg + - '#sound-dai-cells' + +unevaluatedProperties: false + +examples: + - | + #include <dt-bindings/gpio/gpio.h> + i2c { + #address-cells = <1>; + #size-cells = <0>; + max98388: amplifier@39 { + compatible = "adi,max98388"; + reg = <0x39>; + #sound-dai-cells = <0>; + adi,vmon-slot-no = <0>; + adi,imon-slot-no = <1>; + adi,interleave-mode; + reset-gpios = <&gpio 4 GPIO_ACTIVE_LOW>; + }; + };
base-commit: 53ab6975c12d1ad86c599a8927e8c698b144d669
Signature · 1 line
2.34.1
PATCH v2 2/2 ASoC: max98388: add amplifier driver
From: Ryan Lee <[email protected]>
Added Analog Devices MAX98388 amplifier driver.
MAX98388 provides a PCM interface for audio data and a standard I2C interface for control data communication.
Closes:
https://urldefense.com/v3/__https://lore.kernel.org/oe-kbuild-all/2023
[email protected]/__;!!A3Ni8CS0y2Y!46sHiAsmIiXxZ_QXIobho mY8F1f7F2yMYd_65NNFwRlcgut33--RdFjVAbg6jKf7Vs8GaYZ7oA$
---
Changes from v1:
Fixed build warnings.
sound/soc/codecs/Kconfig | 10 + sound/soc/codecs/Makefile | 2 + sound/soc/codecs/max98388.c | 1042 +++++++++++++++++++++++++++++++++++ sound/soc/codecs/max98388.h | 234 ++++++++ 4 files changed, 1288 insertions(+) create mode 100644 sound/soc/codecs/max98388.c create mode 100644 sound/soc/codecs/max98388.h
sound/soc/codecs/Kconfig +10 -0
@@ -137,6 +137,7 @@ config SND_SOC_ALL_CODECS imply SND_SOC_MAX98363 imply SND_SOC_MAX98373_I2C imply SND_SOC_MAX98373_SDW + imply SND_SOC_MAX98388 imply SND_SOC_MAX98390 imply SND_SOC_MAX98396 imply SND_SOC_MAX9850
@@ -1175,6 +1176,15 @@ config SND_SOC_MAX98373_SDW interface for control data. Select this if MAX98373 is connected via soundwire. +config SND_SOC_MAX98388 + tristate "Analog Devices MAX98388 Speaker Amplifier" + depends on I2C + help + Enable support for Analog Devices MAX98388 audio + amplifier. The device provides a PCM interface for + audio data and a standard I2C interface for control + data communication. + config SND_SOC_MAX98390 tristate "Maxim Integrated MAX98390 Speaker Amplifier" depends on I2C
sound/soc/codecs/Makefile +2 -0
@@ -153,6 +153,7 @@ snd-soc-max98363-objs := max98363.o snd-soc-max98373-objs := max98373.o snd-soc-max98373-i2c-objs := max98373-i2c.o snd-soc-max98373-sdw-objs := max98373-sdw.o +snd-soc-max98388-objs := max98388.o snd-soc-max98390-objs := max98390.o snd-soc-max98396-objs := max98396.o snd-soc-max9850-objs := max9850.o
@@ -525,6 +526,7 @@ obj-$(CONFIG_SND_SOC_MAX98363) += snd-soc-max98363.o obj-$(CONFIG_SND_SOC_MAX98373) += snd-soc-max98373.o obj-$(CONFIG_SND_SOC_MAX98373_I2C) += snd-soc-max98373-i2c.o obj-$(CONFIG_SND_SOC_MAX98373_SDW) += snd-soc-max98373-sdw.o +obj-$(CONFIG_SND_SOC_MAX98388) += snd-soc-max98388.o obj-$(CONFIG_SND_SOC_MAX98390) += snd-soc-max98390.o obj-$(CONFIG_SND_SOC_MAX98396) += snd-soc-max98396.o obj-$(CONFIG_SND_SOC_MAX9850) += snd-soc-max9850.o
sound/soc/codecs/max98388.c new file +1042 -0
1,042 lines not on this page · raw message
sound/soc/codecs/max98388.h new file +234 -0
234 lines not on this page · raw message
Signature · 1 line
2.34.1
Re: [PATCH V2 2/2] ASoC: max98388: add amplifier driver
Quoted 8 lines · “Ryan
From: Ryan Lee <[email protected]>
Added Analog Devices MAX98388 amplifier driver.
MAX98388 provides a PCM interface for audio data and a standard I2C interface for control data communication.Signed-off-by Ryan Lee <[email protected]>Reported-by kernel test robot <[email protected]>
There is nothing to report here.
Quoted 4 lines
Closes:
https://urldefense.com/v3/__https://lore.kernel.org/oe-kbuild-all/2023
[email protected]/__;!!A3Ni8CS0y2Y!46sHiAsmIiXxZ_QXIobho mY8F1f7F2yMYd_65NNFwRlcgut33--RdFjVAbg6jKf7Vs8GaYZ7oA$
Nothing to close and also broken link. Fix your mailer.
Quoted 11 lines
---
Changes from v1:
Fixed build warnings.sound/soc/codecs/Kconfig | 10 + sound/soc/codecs/Makefile | 2 + sound/soc/codecs/max98388.c | 1042 +++++++++++++++++++++++++++++++++++ sound/soc/codecs/max98388.h | 234 ++++++++ 4 files changed, 1288 insertions(+) create mode 100644 sound/soc/codecs/max98388.c create mode 100644 sound/soc/codecs/max98388.h
...
Quoted 14 lines
sound/soc/codecs/max98388.c new file +14
-0+ +static void max98388_read_deveice_property (struct device *dev, +struct max98388_priv *max98388) +{ +int value; + +if (!device_property_read_u32 (dev,"adi,vmon-slot-no" , &value)) + max98388->v_slot = value &0xF ; +else + max98388->v_slot =0 ; + +if (!device_property_read_u32 (dev,"adi,imon-slot-no" , &value)) + max98388->i_slot = value &0xF ; +else
sound/soc/codecs/max98388.c line 926
Quoted 10 lines
sound/soc/codecs/max98388.c new file +10
-0+ max98388->i_slot =1 ; + +if (device_property_read_bool (dev,"adi,interleave-mode" )) + max98388->interleave_mode = true; +else + max98388->interleave_mode = false; + +if (dev->of_node) { + max98388->reset_gpio =of_get_named_gpio (dev->of_node, +"reset-gpio" ,0 );
Nope, use devm
sound/soc/codecs/max98388.c line 937
Quoted 11 lines
sound/soc/codecs/max98388.c new file +11
-0+if (!gpio_is_valid (max98388->reset_gpio)) { +dev_err (dev,"Looking up %s property in node %s failed %d\n" , +"reset-gpio" , dev->of_node->full_name, + max98388->reset_gpio); + }else { +dev_dbg (dev,"reset-gpio=%d" , + max98388->reset_gpio); + } + }else { +/* this makes reset_gpio as invalid */ + max98388->reset_gpio =-1 ;
Why? To request it again? It does not make sense.
sound/soc/codecs/max98388.c line 949
Quoted 12 lines
sound/soc/codecs/max98388.c new file +12
-0+ } +} + +static int max98388_i2c_probe (struct i2c_client *i2c) +{ +int ret =0 ; +int reg =0 ; + +struct max98388_priv *max98388 =NULL ; + + max98388 =devm_kzalloc (&i2c->dev,sizeof (*max98388),GFP_KERNEL ); +
Drop blank line.
sound/soc/codecs/max98388.c line 951
Quoted 2 lines
sound/soc/codecs/max98388.c new file +2
-0+if (!max98388) { + ret = -ENOMEM ;
return -ENOMEM;
sound/soc/codecs/max98388.c line 962
Quoted 11 lines
sound/soc/codecs/max98388.c new file +11
-0+return ret; + } +i2c_set_clientdata (i2c, max98388); + +/* regmap initialization */ + max98388->regmap =devm_regmap_init_i2c (i2c, &max98388_regmap); +if (IS_ERR (max98388->regmap)) { + ret =PTR_ERR (max98388->regmap); +dev_err (&i2c->dev, +"Failed to allocate regmap: %d\n" , ret); +return ret;
return dev_err_probe
sound/soc/codecs/max98388.c line 969
Quoted 7 lines
sound/soc/codecs/max98388.c new file +7
-0+ } + +/* voltage/current slot & gpio configuration */ +max98388_read_deveice_property (&i2c->dev, max98388); + +/* Power on device */ +if (gpio_is_valid (max98388->reset_gpio)) {
What's this? You request it twice? No.
sound/soc/codecs/max98388.c line 974
Quoted 5 lines
sound/soc/codecs/max98388.c new file +5
-0+ ret =devm_gpio_request (&i2c->dev, max98388->reset_gpio, +"MAX98388_RESET" ); +if (ret) { +dev_err (&i2c->dev,"%s: Failed to request gpio %d\n" , + __func__, max98388->reset_gpio);
return dev_err_probe
sound/soc/codecs/max98388.c line 979
Quoted 5 lines
sound/soc/codecs/max98388.c new file +5
-0+return -EINVAL ; + } +gpio_direction_output (max98388->reset_gpio,0 ); +msleep (50 ); +gpio_direction_output (max98388->reset_gpio,1 );
1 means keep in reset, so why do you keep deviec reset afterwards? Was it tested? You probably messed up values used for GPIOs as you stated in example that it is active low.
sound/soc/codecs/max98388.c line 989
Quoted 10 lines
sound/soc/codecs/max98388.c new file +10
-0+msleep (20 ); + } + +/* Read Revision ID */ + ret =regmap_read (max98388->regmap, +MAX98388_R22FF_REV_ID , ®); +if (ret <0 ) { +dev_err (&i2c->dev, +"Failed to read: 0x%02X\n" ,MAX98388_R22FF_REV_ID ); +return ret;
return dev_err_probe
Quoted 12 lines
sound/soc/codecs/max98388.c new file +12
-0+ } +dev_info (&i2c->dev,"MAX98388 revisionID: 0x%02X\n" , reg); + +/* codec registration */ + ret =devm_snd_soc_register_component (&i2c->dev, + &soc_codec_dev_max98388, + max98388_dai, +ARRAY_SIZE (max98388_dai)); +if (ret <0 ) +dev_err (&i2c->dev,"Failed to register codec: %d\n" , ret); + +return ret;
sound/soc/codecs/max98388.c line 1011
Quoted 10 lines
sound/soc/codecs/max98388.c new file +10
-0+} + +static const struct i2c_device_id max98388_i2c_id[] = { + {"max98388" ,0 }, + { }, +}; + +MODULE_DEVICE_TABLE (i2c, max98388_i2c_id); + +#if defined(CONFIG_OF )
Drop
sound/soc/codecs/max98388.c line 1019
Quoted 8 lines
sound/soc/codecs/max98388.c new file +8
-0+static const struct of_device_id max98388_of_match[] = { + { .compatible ="adi,max98388" , }, + { } +}; +MODULE_DEVICE_TABLE (of, max98388_of_match); +#endif + +#ifdef CONFIG_ACPI
Drop
sound/soc/codecs/max98388.c line 1031
Quoted 12 lines
sound/soc/codecs/max98388.c new file +12
-0+static const struct acpi_device_id max98388_acpi_match[] = { + {"ADS8388" ,0 }, + {}, +}; +MODULE_DEVICE_TABLE (acpi, max98388_acpi_match); +#endif + +static struct i2c_driver max98388_i2c_driver = { + .driver = { + .name ="max98388" , + .of_match_table =of_match_ptr (max98388_of_match), + .acpi_match_table =ACPI_PTR (max98388_acpi_match),
Just drop all wrappers. They are useless and only limit your driver (OF can be used on some ACPI platforms).
Best regards,
Krzysztof
RE: [PATCH V2 2/2] ASoC: max98388: add amplifier driver
Quoted 20 lines
-----Original Message-----
From: Krzysztof Kozlowski <[email protected]>
Sent: Saturday, June 10, 2023 2:24 AM
To: “Ryan <[email protected]>; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; Lee, RyanS <[email protected]>; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; [email protected]; linux- [email protected]
Cc: [email protected]; kernel test robot <[email protected]>
Subject: Re: [PATCH V2 2/2] ASoC: max98388: add amplifier driver[External]
Quoted 2 lines · “Ryan
From: Ryan Lee <[email protected]>
Quoted 8 lines
Quoted 6 lines
Added Analog Devices MAX98388 amplifier driver.
MAX98388 provides a PCM interface for audio data and a standard I2C interface for control data communication.Signed-off-by Ryan Lee <[email protected]>Reported-by kernel test robot <[email protected]>There is nothing to report here.
Probably I misunderstood the mail from the kernel test robot. Removing the line.
Quoted 41 lines
Quoted 4 lines
Closes:
https://urldefense.com/v3/__https://lore.kernel.org/oe-kbuild-all/2023
06082054.jIU9oENf-[email protected]/__;!!A3Ni8CS0y2Y!46sHiAsmIiXxZ_QXIobho
Quoted 1 line
mY8F1f7F2yMYd_65NNFwRlcgut33--RdFjVAbg6jKf7Vs8GaYZ7oA$
Nothing to close and also broken link. Fix your mailer.
Quoted 12 lines
---
Changes from v1:
Fixed build warnings.sound/soc/codecs/Kconfig | 10 + sound/soc/codecs/Makefile | 2 + sound/soc/codecs/max98388.c | 1042 +++++++++++++++++++++++++++++++++++ sound/soc/codecs/max98388.h | 234 ++++++++ 4 files changed, 1288 insertions(+) create mode 100644 sound/soc/codecs/max98388.c create mode 100644
sound/soc/codecs/max98388.h...
Quoted 17 lines
sound/soc/codecs/max98388.c new file +17
-0+ +static void max98388_read_deveice_property (struct device *dev, +struct max98388_priv *max98388) { +int value; + +if (!device_property_read_u32 (dev,"adi,vmon-slot-no" , &value)) + max98388->v_slot = value &0xF ; +else + max98388->v_slot =0 ; + +if (!device_property_read_u32 (dev,"adi,imon-slot-no" , &value)) + max98388->i_slot = value &0xF ; +else + max98388->i_slot =1 ; + +if (device_property_read_bool (dev,"adi,interleave-mode" )) + max98388->interleave_mode = true;
Quoted 8 lines
sound/soc/codecs/max98388.c line 926
Quoted 6 lines
sound/soc/codecs/max98388.c new file +6
-0+else + max98388->interleave_mode = false; + +if (dev->of_node) { + max98388->reset_gpio =of_get_named_gpio (dev->of_node, +"reset-gpio" ,0 );Nope, use devm
OK.
Quoted 4 lines
Review
Quoted 3 lines
(quoted diff) +2
-0+ if (!gpio_is_valid(max98388->reset_gpio)) { + dev_err(dev, "Looking up %s property in node %sfailed %d\n",
Quoted 11 lines
sound/soc/codecs/max98388.c line 937
Quoted 9 lines
sound/soc/codecs/max98388.c new file +9
-0+"reset-gpio" , dev->of_node->full_name, + max98388->reset_gpio); + }else { +dev_dbg (dev,"reset-gpio=%d" , + max98388->reset_gpio); + } + }else { +/* this makes reset_gpio as invalid */ + max98388->reset_gpio =-1 ;Why? To request it again? It does not make sense.
This was to make gpio_is_valid() = false in order to skip the reset GPIO control in i2c_probe(). I shall remove these codes and keep the minimum configuration in i2c_probe() function.
Quoted 12 lines
sound/soc/codecs/max98388.c
Quoted 11 lines
sound/soc/codecs/max98388.c new file +10
-0+ } +} + +static int max98388_i2c_probe (struct i2c_client *i2c) { +int ret =0 ; +int reg =0 ; + +struct max98388_priv *max98388 =NULL ; + + max98388 = devm_kzalloc(&i2c->dev, sizeof(*max98388),
GFP_KERNEL);
Quoted 3 lines
Quoted 1 line
+
Drop blank line.
OK.
Quoted 5 lines
sound/soc/codecs/max98388.c line 951
Quoted 3 lines
sound/soc/codecs/max98388.c new file +2
-0+if (!max98388) { + ret = -ENOMEM ;return
-ENOMEM;
OK.
Quoted 8 lines
sound/soc/codecs/max98388.c
Quoted 7 lines
sound/soc/codecs/max98388.c new file +6
-0+return ret; + } +i2c_set_clientdata (i2c, max98388); + +/* regmap initialization */ + max98388->regmap = devm_regmap_init_i2c(i2c,
&max98388_regmap);
Quoted 7 lines
sound/soc/codecs/max98388.c line 962
Quoted 5 lines
sound/soc/codecs/max98388.c new file +5
-0+if (IS_ERR (max98388->regmap)) { + ret =PTR_ERR (max98388->regmap); +dev_err (&i2c->dev, +"Failed to allocate regmap: %d\n" , ret); +return ret;return
dev_err_probe
OK. Shall fix it.
Quoted 10 lines
sound/soc/codecs/max98388.c line 969
Quoted 8 lines
sound/soc/codecs/max98388.c new file +7
-0+ } + +/* voltage/current slot & gpio configuration */ +max98388_read_deveice_property (&i2c->dev, max98388); + +/* Power on device */ +if (gpio_is_valid (max98388->reset_gpio)) {What's this? You request it twice? No.
Will modify the code.
Quoted 9 lines
sound/soc/codecs/max98388.c line 974
Quoted 7 lines
sound/soc/codecs/max98388.c new file +5
-0+ ret =devm_gpio_request (&i2c->dev, max98388->reset_gpio, +"MAX98388_RESET" ); +if (ret) { +dev_err (&i2c->dev,"%s: Failed to request gpio %d\n" , + __func__, max98388->reset_gpio);return
dev_err_probe
OK
Quoted 10 lines
sound/soc/codecs/max98388.c line 979
Quoted 6 lines
sound/soc/codecs/max98388.c new file +5
-0+return -EINVAL ; + } +gpio_direction_output (max98388->reset_gpio,0 ); +msleep (50 ); +gpio_direction_output (max98388->reset_gpio,1 );1 means keep in reset, so why do you keep deviec reset afterwards? Was it tested? You probably messed up values used for GPIOs as you stated in example that it is active low.
The hardware reset function is active low, so the state needs to be high to restart the amp. The code was functional, but I see room for improvement. I shall modify the code.
Quoted 11 lines
sound/soc/codecs/max98388.c
Quoted 10 lines
sound/soc/codecs/max98388.c new file +9
-0+msleep (20 ); + } + +/* Read Revision ID */ + ret =regmap_read (max98388->regmap, +MAX98388_R22FF_REV_ID , ®); +if (ret <0 ) { + dev_err(&i2c->dev, + "Failed to read: 0x%02X\n",
MAX98388_R22FF_REV_ID);
Quoted 3 lines
Review
Quoted 1 line
(quoted diff) +1
-0+ return ret;return
dev_err_probe
OK.
Quoted 17 lines
Quoted 17 lines
sound/soc/codecs/max98388.c new file +16
-0+ } +dev_info (&i2c->dev,"MAX98388 revisionID: 0x%02X\n" , reg); + +/* codec registration */ + ret =devm_snd_soc_register_component (&i2c->dev, + &soc_codec_dev_max98388, + max98388_dai, +ARRAY_SIZE (max98388_dai)); +if (ret <0 ) +dev_err (&i2c->dev,"Failed to register codec: %d\n" , ret); + +return ret; +} + +static const struct i2c_device_id max98388_i2c_id[] = { + {"max98388" ,0 },
Quoted 8 lines
sound/soc/codecs/max98388.c line 1011
Quoted 6 lines
sound/soc/codecs/max98388.c new file +6
-0+ { }, +}; + +MODULE_DEVICE_TABLE (i2c, max98388_i2c_id); + +#if defined(CONFIG_OF )Drop
OK Thanks.
Quoted 10 lines
sound/soc/codecs/max98388.c line 1019
Quoted 8 lines
sound/soc/codecs/max98388.c new file +7
-0+static const struct of_device_id max98388_of_match[] = { + { .compatible ="adi,max98388" , }, + { } +}; +MODULE_DEVICE_TABLE (of, max98388_of_match);#endif + +#ifdef CONFIG_ACPI Drop
OK.
Quoted 15 lines
sound/soc/codecs/max98388.c line 1031
Quoted 12 lines
sound/soc/codecs/max98388.c new file +11
-0+static const struct acpi_device_id max98388_acpi_match[] = { + {"ADS8388" ,0 }, + {}, +}; +MODULE_DEVICE_TABLE (acpi, max98388_acpi_match);#endif + +static struct i2c_driver max98388_i2c_driver = { + .driver = { + .name ="max98388" , + .of_match_table =of_match_ptr (max98388_of_match), + .acpi_match_table =ACPI_PTR (max98388_acpi_match),Just drop all wrappers. They are useless and only limit your driver (OF can be used on some ACPI platforms).
I shall remove all wrappers.
Thanks for the review.
Quoted 4 lines
Best regards,
Krzysztof
Quoted 8 lines · “Ryan
From: Ryan Lee <[email protected]>
Add dt-bindings information for Analog Devices MAX98388 I2S Amplifier
Signed-off-by Ryan Lee <[email protected]>---
Changes from v1:
Removed unnecessary blank line and description. Modified quotes.
Best regards,
Krzysztof