]> git.proxmox.com Git - mirror_ubuntu-zesty-kernel.git/commitdiff
AudioInjector Octo: sample rates, regulators, reset
authorMatt Flax <flatmax@flatmax.org>
Mon, 27 Mar 2017 11:26:49 +0000 (22:26 +1100)
committerKleber Sacilotto de Souza <kleber.souza@canonical.com>
Tue, 19 Sep 2017 10:07:57 +0000 (12:07 +0200)
This patch adds new sample rates to the Audioinjector Octo sound card. The
new supported rates are (in kHz) :
96, 48, 32, 24, 16, 8, 88.2, 44.1, 29.4, 22.05, 14.7

Reference the bcm270x DT regulators in the overlay.

This patch adds a reset GPIO for the AudioInjector.net octo sound card.

Signed-off-by: Tim Gardner <tim.gardner@canonical.com>
arch/arm/boot/dts/overlays/audioinjector-addons-overlay.dts
sound/soc/bcm/audioinjector-octo-soundcard.c

index dbf2f3cacc2e6bf5b7116fbadd97f2781580a79c..a40bb1193a4cebc5672709e8db861e1167d3a699 100644 (file)
                                reg = <0x48>;
                                clocks = <&cs42448_mclk>;
                                clock-names = "mclk";
+                               VA-supply = <&vdd_5v0_reg>;
+                               VD-supply = <&vdd_3v3_reg>;
+                               VLS-supply = <&vdd_3v3_reg>;
+                               VLC-supply = <&vdd_3v3_reg>;
                                status = "okay";
                        };
 
@@ -42,6 +46,7 @@
                        compatible = "ai,audioinjector-octo-soundcard";
                        mult-gpios = <&gpio 27 0>, <&gpio 22 0>, <&gpio 23 0>,
                                     <&gpio 24 0>;
+                       reset-gpios = <&gpio 5 0>;
                        i2s-controller = <&i2s>;
                        codec = <&cs42448>;
                        status = "okay";
index 9effea725798640887755dfa688da45338718afc..dcf403ab37639ba79e38278d7e4b1ade452c292a 100644 (file)
 #include <sound/control.h>
 
 static struct gpio_descs *mult_gpios;
+static struct gpio_desc *codec_rst_gpio;
 static unsigned int audioinjector_octo_rate;
 
+static const unsigned int audioinjector_octo_rates[] = {
+       96000, 48000, 32000, 24000, 16000, 8000, 88200, 44100, 29400, 22050, 14700,
+};
+
+static struct snd_pcm_hw_constraint_list audioinjector_octo_constraints = {
+       .list = audioinjector_octo_rates,
+       .count = ARRAY_SIZE(audioinjector_octo_rates),
+};
+
 static int audioinjector_octo_dai_init(struct snd_soc_pcm_runtime *rtd)
 {
        return snd_soc_dai_set_bclk_ratio(rtd->cpu_dai, 64);
@@ -42,6 +52,11 @@ static int audioinjector_octo_startup(struct snd_pcm_substream *substream)
        rtd->cpu_dai->driver->capture.channels_min = 8;
        rtd->cpu_dai->driver->capture.channels_max = 8;
        rtd->codec_dai->driver->capture.channels_max = 8;
+       
+       snd_pcm_hw_constraint_list(substream->runtime, 0,
+                               SNDRV_PCM_HW_PARAM_RATE,
+                               &audioinjector_octo_constraints);
+
        return 0;
 }
 
@@ -76,7 +91,43 @@ static int audioinjector_octo_hw_params(struct snd_pcm_substream *substream,
 
        audioinjector_octo_rate = params_rate(params);
 
-       return 0;
+       // Set the correct sysclock for the codec
+       switch (audioinjector_octo_rate) {
+       case 96000:
+       case 48000:
+               return snd_soc_dai_set_sysclk(rtd->codec_dai, 0, 49152000,
+                                                                       0);
+               break;
+       case 24000:
+               return snd_soc_dai_set_sysclk(rtd->codec_dai, 0, 49152000/2,
+                                                                       0);
+               break;
+       case 32000:
+       case 16000:
+               return snd_soc_dai_set_sysclk(rtd->codec_dai, 0, 49152000/3,
+                                                                       0);
+               break;
+       case 8000:
+               return snd_soc_dai_set_sysclk(rtd->codec_dai, 0, 49152000/6,
+                                                                       0);
+               break;
+       case 88200:
+       case 44100:
+               return snd_soc_dai_set_sysclk(rtd->codec_dai, 0, 45185400,
+                                                                       0);
+               break;
+       case 22050:
+               return snd_soc_dai_set_sysclk(rtd->codec_dai, 0, 45185400/2,
+                                                                       0);
+               break;
+       case 29400:
+       case 14700:
+               return snd_soc_dai_set_sysclk(rtd->codec_dai, 0, 45185400/3,
+                                                                       0);
+               break;
+       default:
+               return -EINVAL;
+       }
 }
 
 static int audioinjector_octo_trigger(struct snd_pcm_substream *substream,
@@ -92,25 +143,12 @@ static int audioinjector_octo_trigger(struct snd_pcm_substream *substream,
        case SNDRV_PCM_TRIGGER_RESUME:
        case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
                switch (audioinjector_octo_rate) {
-               case 192000:
-                       mult[3] = 1;
-               case 176640:
-                       mult[0] = 1;
-                       mult[1] = 1;
-                       mult[2] = 1;
-                       break;
                case 96000:
                        mult[3] = 1;
                case 88200:
                        mult[1] = 1;
                        mult[2] = 1;
                        break;
-               case 64000:
-                       mult[3] = 1;
-               case 58800:
-                       mult[0] = 1;
-                       mult[2] = 1;
-                       break;
                case 48000:
                        mult[3] = 1;
                case 44100:
@@ -231,6 +269,21 @@ static int audioinjector_octo_probe(struct platform_device *pdev)
                if (IS_ERR(mult_gpios))
                        return PTR_ERR(mult_gpios);
 
+               codec_rst_gpio = devm_gpiod_get_optional(&pdev->dev, "reset",
+                                                               GPIOD_OUT_LOW);
+               if (IS_ERR(codec_rst_gpio))
+                       return PTR_ERR(codec_rst_gpio);
+
+               if (codec_rst_gpio)
+                       gpiod_set_value(codec_rst_gpio, 1);
+               msleep(500);
+               if (codec_rst_gpio)
+                       gpiod_set_value(codec_rst_gpio, 0);
+               msleep(500);
+               if (codec_rst_gpio)
+                       gpiod_set_value(codec_rst_gpio, 1);
+               msleep(500);
+
                if (i2s_node && codec_node) {
                        dai->cpu_dai_name = NULL;
                        dai->cpu_of_node = i2s_node;