From 011f2c26f1b62e309f2eac6a3101bfe0a3c76c7e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C3=81lvaro=20Fern=C3=A1ndez=20Rojas?= Date: Fri, 2 Dec 2016 11:50:26 +0100 Subject: brcm2708: update linux 4.4 patches to latest version MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit As usual these patches were extracted and rebased from the raspberry pi repo: https://github.com/raspberrypi/linux/tree/rpi-4.4.y Signed-off-by: Álvaro Fernández Rojas --- ...for-RRA-DigiDAC1-soundcard-using-WM8741-W.patch | 602 --------------------- 1 file changed, 602 deletions(-) delete mode 100644 target/linux/brcm2708/patches-4.4/0372-New-driver-for-RRA-DigiDAC1-soundcard-using-WM8741-W.patch (limited to 'target/linux/brcm2708/patches-4.4/0372-New-driver-for-RRA-DigiDAC1-soundcard-using-WM8741-W.patch') diff --git a/target/linux/brcm2708/patches-4.4/0372-New-driver-for-RRA-DigiDAC1-soundcard-using-WM8741-W.patch b/target/linux/brcm2708/patches-4.4/0372-New-driver-for-RRA-DigiDAC1-soundcard-using-WM8741-W.patch deleted file mode 100644 index 303d45d38e..0000000000 --- a/target/linux/brcm2708/patches-4.4/0372-New-driver-for-RRA-DigiDAC1-soundcard-using-WM8741-W.patch +++ /dev/null @@ -1,602 +0,0 @@ -From bcba10e5c5da279fa57920ee1c08ee1dea84a4f6 Mon Sep 17 00:00:00 2001 -From: escalator2015 -Date: Tue, 24 May 2016 16:20:09 +0100 -Subject: [PATCH] New driver for RRA DigiDAC1 soundcard using WM8741 + WM8804 - ---- - arch/arm/boot/dts/overlays/Makefile | 1 + - arch/arm/boot/dts/overlays/README | 6 + - .../overlays/rra-digidac1-wm8741-audio-overlay.dts | 81 ++++ - arch/arm/configs/bcm2709_defconfig | 1 + - arch/arm/configs/bcmrpi_defconfig | 1 + - sound/soc/bcm/Kconfig | 8 + - sound/soc/bcm/Makefile | 2 + - sound/soc/bcm/digidac1-soundcard.c | 422 +++++++++++++++++++++ - 8 files changed, 522 insertions(+) - create mode 100644 arch/arm/boot/dts/overlays/rra-digidac1-wm8741-audio-overlay.dts - create mode 100644 sound/soc/bcm/digidac1-soundcard.c - ---- a/arch/arm/boot/dts/overlays/Makefile -+++ b/arch/arm/boot/dts/overlays/Makefile -@@ -67,6 +67,7 @@ dtbo-$(RPI_DT_OVERLAYS) += rpi-display.d - dtbo-$(RPI_DT_OVERLAYS) += rpi-ft5406.dtbo - dtbo-$(RPI_DT_OVERLAYS) += rpi-proto.dtbo - dtbo-$(RPI_DT_OVERLAYS) += rpi-sense.dtbo -+dtbo-$(RPI_DT_OVERLAYS) += rra-digidac1-wm8741-audio.dtbo - dtbo-$(RPI_DT_OVERLAYS) += sdhost.dtbo - dtbo-$(RPI_DT_OVERLAYS) += sdio.dtbo - dtbo-$(RPI_DT_OVERLAYS) += sdio-1bit.dtbo ---- a/arch/arm/boot/dts/overlays/README -+++ b/arch/arm/boot/dts/overlays/README -@@ -842,6 +842,12 @@ Load: dtoverlay=rpi-sense - Params: - - -+Name: rra-digidac1-wm8741-audio -+Info: Configures the Red Rocks Audio DigiDAC1 soundcard -+Load: dtoverlay=rra-digidac1-wm8741-audio -+Params: -+ -+ - Name: sdhost - Info: Selects the bcm2835-sdhost SD/MMC driver, optionally with overclock. - N.B. This overlay is designed for situations where the mmc driver is ---- /dev/null -+++ b/arch/arm/boot/dts/overlays/rra-digidac1-wm8741-audio-overlay.dts -@@ -0,0 +1,81 @@ -+// Definitions for RRA DigiDAC1 Audio card -+/dts-v1/; -+/plugin/; -+ -+/ { -+ compatible = "brcm,bcm2708"; -+ -+ fragment@0 { -+ target-path = "/"; -+ __overlay__ { -+ aliases { -+ ldo0 = &ldo0; -+ ldo1 = &ldo1; -+ }; -+ }; -+ }; -+ -+ fragment@1 { -+ target-path = "/soc"; -+ __overlay__ { -+ -+ ldo1: ldo1 { -+ compatible = "regulator-fixed"; -+ regulator-name = "DC_5V"; -+ regulator-min-microvolt = <5000000>; -+ regulator-max-microvolt = <5000000>; -+ regulator-always-on; -+ }; -+ -+ ldo0: ldo0 { -+ compatible = "regulator-fixed"; -+ regulator-name = "DC_3V3"; -+ regulator-min-microvolt = <3300000>; -+ regulator-max-microvolt = <3300000>; -+ regulator-always-on; -+ }; -+ }; -+ }; -+ -+ fragment@2 { -+ target = <&i2s>; -+ __overlay__ { -+ status = "okay"; -+ }; -+ }; -+ -+ fragment@3 { -+ target = <&i2c1>; -+ __overlay__ { -+ #address-cells = <1>; -+ #size-cells = <0>; -+ status = "okay"; -+ -+ wm8804@3b { -+ #sound-dai-cells = <0>; -+ compatible = "wlf,wm8804"; -+ reg = <0x3b>; -+ status = "okay"; -+ PVDD-supply = <&ldo0>; -+ DVDD-supply = <&ldo0>; -+ }; -+ -+ wm8742: wm8741@1a { -+ compatible = "wlf,wm8741"; -+ reg = <0x1a>; -+ status = "okay"; -+ AVDD-supply = <&ldo1>; -+ DVDD-supply = <&ldo0>; -+ }; -+ }; -+ }; -+ -+ fragment@4 { -+ target = <&sound>; -+ __overlay__ { -+ compatible = "rra,digidac1-soundcard"; -+ i2s-controller = <&i2s>; -+ status = "okay"; -+ }; -+ }; -+}; ---- a/arch/arm/configs/bcm2709_defconfig -+++ b/arch/arm/configs/bcm2709_defconfig -@@ -866,6 +866,7 @@ CONFIG_SND_BCM2708_SOC_JUSTBOOM_DIGI=m - CONFIG_SND_BCM2708_SOC_IQAUDIO_DAC=m - CONFIG_SND_BCM2708_SOC_RASPIDAC3=m - CONFIG_SND_AUDIOINJECTOR_PI_SOUNDCARD=m -+CONFIG_SND_DIGIDAC1_SOUNDCARD=m - CONFIG_SND_BCM2708_SOC_ADAU1977_ADC=m - CONFIG_SND_SOC_ADAU1701=m - CONFIG_SND_SOC_WM8804_I2C=m ---- a/arch/arm/configs/bcmrpi_defconfig -+++ b/arch/arm/configs/bcmrpi_defconfig -@@ -858,6 +858,7 @@ CONFIG_SND_BCM2708_SOC_JUSTBOOM_DIGI=m - CONFIG_SND_BCM2708_SOC_IQAUDIO_DAC=m - CONFIG_SND_BCM2708_SOC_RASPIDAC3=m - CONFIG_SND_AUDIOINJECTOR_PI_SOUNDCARD=m -+CONFIG_SND_DIGIDAC1_SOUNDCARD=m - CONFIG_SND_BCM2708_SOC_ADAU1977_ADC=m - CONFIG_SND_SOC_ADAU1701=m - CONFIG_SND_SOC_WM8804_I2C=m ---- a/sound/soc/bcm/Kconfig -+++ b/sound/soc/bcm/Kconfig -@@ -92,3 +92,11 @@ config SND_AUDIOINJECTOR_PI_SOUNDCARD - select SND_SOC_WM8731 - help - Say Y or M if you want to add support for audioinjector.net Pi Hat -+ -+config SND_DIGIDAC1_SOUNDCARD -+ tristate "Support for Red Rocks Audio DigiDAC1" -+ depends on SND_BCM2708_SOC_I2S || SND_BCM2835_SOC_I2S -+ select SND_SOC_WM8804 -+ select SND_SOC_WM8741 -+ help -+ Say Y or M if you want to add support for Red Rocks Audio DigiDAC1 board. ---- a/sound/soc/bcm/Makefile -+++ b/sound/soc/bcm/Makefile -@@ -16,6 +16,7 @@ snd-soc-rpi-proto-objs := rpi-proto.o - snd-soc-iqaudio-dac-objs := iqaudio-dac.o - snd-soc-raspidac3-objs := raspidac3.o - snd-soc-audioinjector-pi-soundcard-objs := audioinjector-pi-soundcard.o -+snd-soc-digidac1-soundcard-objs := digidac1-soundcard.o - - obj-$(CONFIG_SND_BCM2708_SOC_ADAU1977_ADC) += snd-soc-adau1977-adc.o - obj-$(CONFIG_SND_BCM2708_SOC_HIFIBERRY_DAC) += snd-soc-hifiberry-dac.o -@@ -29,4 +30,5 @@ obj-$(CONFIG_SND_BCM2708_SOC_RPI_PROTO) - obj-$(CONFIG_SND_BCM2708_SOC_IQAUDIO_DAC) += snd-soc-iqaudio-dac.o - obj-$(CONFIG_SND_BCM2708_SOC_RASPIDAC3) += snd-soc-raspidac3.o - obj-$(CONFIG_SND_AUDIOINJECTOR_PI_SOUNDCARD) += snd-soc-audioinjector-pi-soundcard.o -+obj-$(CONFIG_SND_DIGIDAC1_SOUNDCARD) += snd-soc-digidac1-soundcard.o - ---- /dev/null -+++ b/sound/soc/bcm/digidac1-soundcard.c -@@ -0,0 +1,422 @@ -+/* -+ * ASoC Driver for RRA DigiDAC1 -+ * Copyright 2016 -+ * Author: José M. Tasende -+ * based on the HifiBerry DAC driver by Florian Meier -+ * and the Wolfson card driver by Nikesh Oswal, -+ * This program is free software; you can redistribute it and/or -+ * modify it under the terms of the GNU General Public License -+ * version 2 as published by the Free Software Foundation. -+ * -+ * This program is distributed in the hope that it will be useful, but -+ * WITHOUT ANY WARRANTY; without even the implied warranty of -+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU -+ * General Public License for more details. -+ */ -+ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include "../codecs/wm8804.h" -+#include "../codecs/wm8741.h" -+ -+#define WM8741_NUM_SUPPLIES 2 -+ -+/* codec private data */ -+struct wm8741_priv { -+ struct wm8741_platform_data pdata; -+ struct regmap *regmap; -+ struct regulator_bulk_data supplies[WM8741_NUM_SUPPLIES]; -+ unsigned int sysclk; -+ const struct snd_pcm_hw_constraint_list *sysclk_constraints; -+}; -+ -+static int samplerate = 44100; -+ -+/* New Alsa Controls not exposed by original wm8741 codec driver */ -+/* in actual driver the att. adjustment is wrong because */ -+/* this DAC has a coarse attenuation register with 4dB steps */ -+/* and a fine level register with 0.125dB steps */ -+/* each register has 32 steps so combining both we have 1024 steps */ -+/* of 0.125 dB. */ -+/* The original level controls from driver are removed at startup */ -+/* and replaced by the corrected ones. */ -+/* The same wm8741 driver can be used for wm8741 and wm8742 devices */ -+ -+static const DECLARE_TLV_DB_SCALE(dac_tlv_fine, 0, 13, 0); -+static const DECLARE_TLV_DB_SCALE(dac_tlv_coarse, -12700, 400, 1); -+static const char *w8741_dither[4] = {"Off", "RPDF", "TPDF", "HPDF"}; -+static const char *w8741_filter[5] = { -+ "Type 1", "Type 2", "Type 3", "Type 4", "Type 5"}; -+static const char *w8741_switch[2] = {"Off", "On"}; -+static const struct soc_enum w8741_enum[] = { -+SOC_ENUM_SINGLE(WM8741_MODE_CONTROL_2, 0, 4, w8741_dither),/* dithering type */ -+SOC_ENUM_SINGLE(WM8741_FILTER_CONTROL, 0, 5, w8741_filter),/* filter type */ -+SOC_ENUM_SINGLE(WM8741_FORMAT_CONTROL, 6, 2, w8741_switch),/* phase invert */ -+SOC_ENUM_SINGLE(WM8741_VOLUME_CONTROL, 0, 2, w8741_switch),/* volume ramp */ -+SOC_ENUM_SINGLE(WM8741_VOLUME_CONTROL, 3, 2, w8741_switch),/* soft mute */ -+}; -+ -+static const struct snd_kcontrol_new w8741_snd_controls_stereo[] = { -+SOC_DOUBLE_R_TLV("DAC Fine Playback Volume", WM8741_DACLLSB_ATTENUATION, -+ WM8741_DACRLSB_ATTENUATION, 0, 31, 1, dac_tlv_fine), -+SOC_DOUBLE_R_TLV("Digital Playback Volume", WM8741_DACLMSB_ATTENUATION, -+ WM8741_DACRMSB_ATTENUATION, 0, 31, 1, dac_tlv_coarse), -+SOC_ENUM("DAC Dither", w8741_enum[0]), -+SOC_ENUM("DAC Digital Filter", w8741_enum[1]), -+SOC_ENUM("DAC Phase Invert", w8741_enum[2]), -+SOC_ENUM("DAC Volume Ramp", w8741_enum[3]), -+SOC_ENUM("DAC Soft Mute", w8741_enum[4]), -+}; -+ -+static const struct snd_kcontrol_new w8741_snd_controls_mono_left[] = { -+SOC_SINGLE_TLV("DAC Fine Playback Volume", WM8741_DACLLSB_ATTENUATION, -+ 0, 31, 0, dac_tlv_fine), -+SOC_SINGLE_TLV("Digital Playback Volume", WM8741_DACLMSB_ATTENUATION, -+ 0, 31, 1, dac_tlv_coarse), -+SOC_ENUM("DAC Dither", w8741_enum[0]), -+SOC_ENUM("DAC Digital Filter", w8741_enum[1]), -+SOC_ENUM("DAC Phase Invert", w8741_enum[2]), -+SOC_ENUM("DAC Volume Ramp", w8741_enum[3]), -+SOC_ENUM("DAC Soft Mute", w8741_enum[4]), -+}; -+ -+static const struct snd_kcontrol_new w8741_snd_controls_mono_right[] = { -+SOC_SINGLE_TLV("DAC Fine Playback Volume", WM8741_DACRLSB_ATTENUATION, -+ 0, 31, 0, dac_tlv_fine), -+SOC_SINGLE_TLV("Digital Playback Volume", WM8741_DACRMSB_ATTENUATION, -+ 0, 31, 1, dac_tlv_coarse), -+SOC_ENUM("DAC Dither", w8741_enum[0]), -+SOC_ENUM("DAC Digital Filter", w8741_enum[1]), -+SOC_ENUM("DAC Phase Invert", w8741_enum[2]), -+SOC_ENUM("DAC Volume Ramp", w8741_enum[3]), -+SOC_ENUM("DAC Soft Mute", w8741_enum[4]), -+}; -+ -+static int w8741_add_controls(struct snd_soc_codec *codec) -+{ -+ struct wm8741_priv *wm8741 = snd_soc_codec_get_drvdata(codec); -+ -+ switch (wm8741->pdata.diff_mode) { -+ case WM8741_DIFF_MODE_STEREO: -+ case WM8741_DIFF_MODE_STEREO_REVERSED: -+ snd_soc_add_codec_controls(codec, -+ w8741_snd_controls_stereo, -+ ARRAY_SIZE(w8741_snd_controls_stereo)); -+ break; -+ case WM8741_DIFF_MODE_MONO_LEFT: -+ snd_soc_add_codec_controls(codec, -+ w8741_snd_controls_mono_left, -+ ARRAY_SIZE(w8741_snd_controls_mono_left)); -+ break; -+ case WM8741_DIFF_MODE_MONO_RIGHT: -+ snd_soc_add_codec_controls(codec, -+ w8741_snd_controls_mono_right, -+ ARRAY_SIZE(w8741_snd_controls_mono_right)); -+ break; -+ default: -+ return -EINVAL; -+ } -+ -+ return 0; -+} -+ -+static int digidac1_soundcard_init(struct snd_soc_pcm_runtime *rtd) -+{ -+ struct snd_soc_codec *codec = rtd->codec; -+ struct snd_soc_card *card = rtd->card; -+ struct snd_soc_pcm_runtime *wm8741_rtd; -+ struct snd_soc_codec *wm8741_codec; -+ struct snd_card *sound_card = card->snd_card; -+ struct snd_kcontrol *kctl; -+ int ret; -+ -+ wm8741_rtd = snd_soc_get_pcm_runtime(card, card->dai_link[1].name); -+ if (!wm8741_rtd) { -+ dev_warn(card->dev, "digidac1_soundcard_init: couldn't get wm8741 rtd\n"); -+ return -EFAULT; -+ } -+ wm8741_codec = wm8741_rtd->codec; -+ ret = w8741_add_controls(wm8741_codec); -+ if (ret < 0) -+ dev_warn(card->dev, "Failed to add new wm8741 controls: %d\n", -+ ret); -+ -+ /* enable TX output */ -+ snd_soc_update_bits(codec, WM8804_PWRDN, 0x4, 0x0); -+ -+ kctl = snd_soc_card_get_kcontrol(card, -+ "Playback Volume"); -+ if (kctl) { -+ kctl->vd[0].access = SNDRV_CTL_ELEM_ACCESS_READWRITE; -+ snd_ctl_remove(sound_card, kctl); -+ } -+ kctl = snd_soc_card_get_kcontrol(card, -+ "Fine Playback Volume"); -+ if (kctl) { -+ kctl->vd[0].access = SNDRV_CTL_ELEM_ACCESS_READWRITE; -+ snd_ctl_remove(sound_card, kctl); -+ } -+ return 0; -+} -+ -+static int digidac1_soundcard_startup(struct snd_pcm_substream *substream) -+{ -+ /* turn on wm8804 digital output */ -+ struct snd_soc_pcm_runtime *rtd = substream->private_data; -+ struct snd_soc_codec *codec = rtd->codec; -+ struct snd_soc_card *card = rtd->card; -+ struct snd_soc_pcm_runtime *wm8741_rtd; -+ struct snd_soc_codec *wm8741_codec; -+ -+ snd_soc_update_bits(codec, WM8804_PWRDN, 0x3c, 0x00); -+ wm8741_rtd = snd_soc_get_pcm_runtime(card, card->dai_link[1].name); -+ if (!wm8741_rtd) { -+ dev_warn(card->dev, "digidac1_soundcard_startup: couldn't get WM8741 rtd\n"); -+ return -EFAULT; -+ } -+ wm8741_codec = wm8741_rtd->codec; -+ -+ /* latch wm8741 level */ -+ snd_soc_update_bits(wm8741_codec, WM8741_DACLLSB_ATTENUATION, -+ WM8741_UPDATELL, WM8741_UPDATELL); -+ snd_soc_update_bits(wm8741_codec, WM8741_DACLMSB_ATTENUATION, -+ WM8741_UPDATELM, WM8741_UPDATELM); -+ snd_soc_update_bits(wm8741_codec, WM8741_DACRLSB_ATTENUATION, -+ WM8741_UPDATERL, WM8741_UPDATERL); -+ snd_soc_update_bits(wm8741_codec, WM8741_DACRMSB_ATTENUATION, -+ WM8741_UPDATERM, WM8741_UPDATERM); -+ -+ return 0; -+} -+ -+static void digidac1_soundcard_shutdown(struct snd_pcm_substream *substream) -+{ -+ /* turn off wm8804 digital output */ -+ struct snd_soc_pcm_runtime *rtd = substream->private_data; -+ struct snd_soc_codec *codec = rtd->codec; -+ -+ snd_soc_update_bits(codec, WM8804_PWRDN, 0x3c, 0x3c); -+} -+ -+static int digidac1_soundcard_hw_params(struct snd_pcm_substream *substream, -+ struct snd_pcm_hw_params *params) -+{ -+ struct snd_soc_pcm_runtime *rtd = substream->private_data; -+ struct snd_soc_dai *codec_dai = rtd->codec_dai; -+ struct snd_soc_codec *codec = rtd->codec; -+ struct snd_soc_dai *cpu_dai = rtd->cpu_dai; -+ struct snd_soc_card *card = rtd->card; -+ struct snd_soc_pcm_runtime *wm8741_rtd; -+ struct snd_soc_codec *wm8741_codec; -+ -+ int sysclk = 27000000; -+ long mclk_freq = 0; -+ int mclk_div = 1; -+ int sampling_freq = 1; -+ int ret; -+ -+ wm8741_rtd = snd_soc_get_pcm_runtime(card, card->dai_link[1].name); -+ if (!wm8741_rtd) { -+ dev_warn(card->dev, "digidac1_soundcard_hw_params: couldn't get WM8741 rtd\n"); -+ return -EFAULT; -+ } -+ wm8741_codec = wm8741_rtd->codec; -+ samplerate = params_rate(params); -+ -+ if (samplerate <= 96000) { -+ mclk_freq = samplerate*256; -+ mclk_div = WM8804_MCLKDIV_256FS; -+ } else { -+ mclk_freq = samplerate*128; -+ mclk_div = WM8804_MCLKDIV_128FS; -+ } -+ -+ switch (samplerate) { -+ case 32000: -+ sampling_freq = 0x03; -+ break; -+ case 44100: -+ sampling_freq = 0x00; -+ break; -+ case 48000: -+ sampling_freq = 0x02; -+ break; -+ case 88200: -+ sampling_freq = 0x08; -+ break; -+ case 96000: -+ sampling_freq = 0x0a; -+ break; -+ case 176400: -+ sampling_freq = 0x0c; -+ break; -+ case 192000: -+ sampling_freq = 0x0e; -+ break; -+ default: -+ dev_err(codec->dev, -+ "Failed to set WM8804 SYSCLK, unsupported samplerate %d\n", -+ samplerate); -+ } -+ -+ snd_soc_dai_set_clkdiv(codec_dai, WM8804_MCLK_DIV, mclk_div); -+ snd_soc_dai_set_pll(codec_dai, 0, 0, sysclk, mclk_freq); -+ -+ ret = snd_soc_dai_set_sysclk(codec_dai, WM8804_TX_CLKSRC_PLL, -+ sysclk, SND_SOC_CLOCK_OUT); -+ if (ret < 0) { -+ dev_err(codec->dev, -+ "Failed to set WM8804 SYSCLK: %d\n", ret); -+ return ret; -+ } -+ /* Enable wm8804 TX output */ -+ snd_soc_update_bits(codec, WM8804_PWRDN, 0x4, 0x0); -+ -+ /* wm8804 Power on */ -+ snd_soc_update_bits(codec, WM8804_PWRDN, 0x9, 0); -+ -+ /* wm8804 set sampling frequency status bits */ -+ snd_soc_update_bits(codec, WM8804_SPDTX4, 0x0f, sampling_freq); -+ -+ /* Now update wm8741 registers for the correct oversampling */ -+ if (samplerate <= 48000) -+ snd_soc_update_bits(wm8741_codec, WM8741_MODE_CONTROL_1, -+ WM8741_OSR_MASK, 0x00); -+ else if (samplerate <= 96000) -+ snd_soc_update_bits(wm8741_codec, WM8741_MODE_CONTROL_1, -+ WM8741_OSR_MASK, 0x20); -+ else -+ snd_soc_update_bits(wm8741_codec, WM8741_MODE_CONTROL_1, -+ WM8741_OSR_MASK, 0x40); -+ -+ /* wm8741 bit size */ -+ switch (params_width(params)) { -+ case 16: -+ snd_soc_update_bits(wm8741_codec, WM8741_FORMAT_CONTROL, -+ WM8741_IWL_MASK, 0x00); -+ break; -+ case 20: -+ snd_soc_update_bits(wm8741_codec, WM8741_FORMAT_CONTROL, -+ WM8741_IWL_MASK, 0x01); -+ break; -+ case 24: -+ snd_soc_update_bits(wm8741_codec, WM8741_FORMAT_CONTROL, -+ WM8741_IWL_MASK, 0x02); -+ break; -+ case 32: -+ snd_soc_update_bits(wm8741_codec, WM8741_FORMAT_CONTROL, -+ WM8741_IWL_MASK, 0x03); -+ break; -+ default: -+ dev_dbg(codec->dev, "wm8741_hw_params: Unsupported bit size param = %d", -+ params_width(params)); -+ return -EINVAL; -+ } -+ -+ return snd_soc_dai_set_bclk_ratio(cpu_dai, 64); -+} -+/* machine stream operations */ -+static struct snd_soc_ops digidac1_soundcard_ops = { -+ .hw_params = digidac1_soundcard_hw_params, -+ .startup = digidac1_soundcard_startup, -+ .shutdown = digidac1_soundcard_shutdown, -+}; -+ -+static struct snd_soc_dai_link digidac1_soundcard_dai[] = { -+ { -+ .name = "RRA DigiDAC1", -+ .stream_name = "RRA DigiDAC1 HiFi", -+ .cpu_dai_name = "bcm2708-i2s.0", -+ .codec_dai_name = "wm8804-spdif", -+ .platform_name = "bcm2708-i2s.0", -+ .codec_name = "wm8804.1-003b", -+ .dai_fmt = SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF | -+ SND_SOC_DAIFMT_CBM_CFM, -+ .ops = &digidac1_soundcard_ops, -+ .init = digidac1_soundcard_init, -+ }, -+ { -+ .name = "RRA DigiDAC11", -+ .stream_name = "RRA DigiDAC11 HiFi", -+ .cpu_dai_name = "wm8804-spdif", -+ .codec_dai_name = "wm8741", -+ .codec_name = "wm8741.1-001a", -+ .dai_fmt = SND_SOC_DAIFMT_I2S -+ | SND_SOC_DAIFMT_NB_NF -+ | SND_SOC_DAIFMT_CBS_CFS, -+ }, -+}; -+ -+/* audio machine driver */ -+static struct snd_soc_card digidac1_soundcard = { -+ .name = "digidac1-soundcard", -+ .owner = THIS_MODULE, -+ .dai_link = digidac1_soundcard_dai, -+ .num_links = ARRAY_SIZE(digidac1_soundcard_dai), -+}; -+ -+static int digidac1_soundcard_probe(struct platform_device *pdev) -+{ -+ int ret = 0; -+ -+ digidac1_soundcard.dev = &pdev->dev; -+ -+ if (pdev->dev.of_node) { -+ struct device_node *i2s_node; -+ struct snd_soc_dai_link *dai = &digidac1_soundcard_dai[0]; -+ -+ i2s_node = of_parse_phandle(pdev->dev.of_node, -+ "i2s-controller", 0); -+ -+ if (i2s_node) { -+ dai->cpu_dai_name = NULL; -+ dai->cpu_of_node = i2s_node; -+ dai->platform_name = NULL; -+ dai->platform_of_node = i2s_node; -+ } -+ } -+ -+ ret = snd_soc_register_card(&digidac1_soundcard); -+ if (ret) -+ dev_err(&pdev->dev, "snd_soc_register_card() failed: %d\n", -+ ret); -+ -+ return ret; -+} -+ -+static int digidac1_soundcard_remove(struct platform_device *pdev) -+{ -+ return snd_soc_unregister_card(&digidac1_soundcard); -+} -+ -+static const struct of_device_id digidac1_soundcard_of_match[] = { -+ { .compatible = "rra,digidac1-soundcard", }, -+ {}, -+}; -+MODULE_DEVICE_TABLE(of, digidac1_soundcard_of_match); -+ -+static struct platform_driver digidac1_soundcard_driver = { -+ .driver = { -+ .name = "digidac1-audio", -+ .owner = THIS_MODULE, -+ .of_match_table = digidac1_soundcard_of_match, -+ }, -+ .probe = digidac1_soundcard_probe, -+ .remove = digidac1_soundcard_remove, -+}; -+ -+module_platform_driver(digidac1_soundcard_driver); -+ -+MODULE_AUTHOR("José M. Tasende "); -+MODULE_DESCRIPTION("ASoC Driver for RRA DigiDAC1"); -+MODULE_LICENSE("GPL v2"); -- cgit v1.2.3