diff --git a/config/kernel/linux-meson64-dev.config b/config/kernel/linux-meson64-dev.config index f886f1be3e..22b8b8da42 100644 --- a/config/kernel/linux-meson64-dev.config +++ b/config/kernel/linux-meson64-dev.config @@ -3527,7 +3527,7 @@ CONFIG_DRM_I2C_ADV7533=y CONFIG_DRM_DW_HDMI=m # CONFIG_DRM_DW_HDMI_AHB_AUDIO is not set CONFIG_DRM_DW_HDMI_I2S_AUDIO=m -# CONFIG_DRM_DW_HDMI_CEC is not set +CONFIG_DRM_DW_HDMI_CEC=m # CONFIG_DRM_ARCPGU is not set # CONFIG_DRM_HISI_HIBMC is not set # CONFIG_DRM_HISI_KIRIN is not set @@ -3784,6 +3784,8 @@ CONFIG_SND_SOC=y # CONFIG_SND_SOC_IMX_AUDMUX is not set # CONFIG_SND_I2S_HI6210_I2S is not set # CONFIG_SND_SOC_IMG is not set +CONFIG_SND_SOC_MESON=y +CONFIG_SND_SOC_MESON_I2S=y # # STMicroelectronics STM32 SOC audio support @@ -4098,7 +4100,7 @@ CONFIG_USB_DWC3_DUAL_ROLE=y # # Platform Glue Driver Support # -CONFIG_USB_DWC3_PCI=y +# CONFIG_USB_DWC3_PCI is not set CONFIG_USB_DWC3_OF_SIMPLE=y CONFIG_USB_DWC2=y # CONFIG_USB_DWC2_HOST is not set @@ -4115,12 +4117,10 @@ CONFIG_USB_CHIPIDEA=y CONFIG_USB_CHIPIDEA_OF=y CONFIG_USB_CHIPIDEA_UDC=y CONFIG_USB_CHIPIDEA_HOST=y -CONFIG_USB_ISP1760=y -CONFIG_USB_ISP1760_HCD=y -CONFIG_USB_ISP1761_UDC=y +# CONFIG_USB_ISP1760 is not set # CONFIG_USB_ISP1760_HOST_ROLE is not set # CONFIG_USB_ISP1760_GADGET_ROLE is not set -CONFIG_USB_ISP1760_DUAL_ROLE=y +# CONFIG_USB_ISP1760_DUAL_ROLE is not set # # USB port drivers @@ -4721,6 +4721,7 @@ CONFIG_ARM_SMMU_V3=y # Amlogic SoC drivers # CONFIG_MESON_GX_SOCINFO=y +CONFIG_MESON_GX_PM_DOMAINS=y # # Broadcom SoC drivers @@ -5118,8 +5119,8 @@ CONFIG_RESET_MESON=y CONFIG_GENERIC_PHY=y # CONFIG_PHY_XGENE is not set CONFIG_PHY_MESON8B_USB2=m -CONFIG_PHY_MESON_GXL_USB2=m CONFIG_PHY_MESON_GXL_USB3=m +CONFIG_PHY_MESON_GXL_USB2=m # CONFIG_BCM_KONA_USB2_PHY is not set # CONFIG_PHY_PXA_28NM_HSIC is not set # CONFIG_PHY_PXA_28NM_USB2 is not set diff --git a/patch/kernel/meson64-dev/0001-ARM64-dts-meson-gxm-Add-support-for-Khadas-VIM2.patch b/patch/kernel/meson64-dev/0001-ARM64-dts-meson-gxm-Add-support-for-Khadas-VIM2.patch new file mode 100644 index 0000000000..763d37b371 --- /dev/null +++ b/patch/kernel/meson64-dev/0001-ARM64-dts-meson-gxm-Add-support-for-Khadas-VIM2.patch @@ -0,0 +1,455 @@ +From a28fee9bdfb0fb386ef3e80d0a998ae3137cf3c0 Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Wed, 2 Aug 2017 16:11:23 +0200 +Subject: [PATCH 01/36] ARM64: dts: meson-gxm: Add support for Khadas VIM2 + +The Khadas VIM2 is a Single Board Computer, respin of the origin +Khadas VIM board, using an Amlogic S912 SoC and more server oriented. + +It provides the same external connectors and header pinout, plus a SPI +NOR Flash, a reprogrammable STM8S003 MCU, FPC Connector, Cooling FAN header +and Pogo Pads Arrays. + +Cc: Gouwa +Acked-by: Martin Blumenstingl +Acked-by: Rob Herring +Signed-off-by: Neil Armstrong +--- + Documentation/devicetree/bindings/arm/amlogic.txt | 1 + + arch/arm64/boot/dts/amlogic/Makefile | 1 + + .../boot/dts/amlogic/meson-gxm-khadas-vim2.dts | 399 +++++++++++++++++++++ + 3 files changed, 401 insertions(+) + create mode 100644 arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts + +diff --git a/Documentation/devicetree/bindings/arm/amlogic.txt b/Documentation/devicetree/bindings/arm/amlogic.txt +index 4e4bc0b..a445997 100644 +--- a/Documentation/devicetree/bindings/arm/amlogic.txt ++++ b/Documentation/devicetree/bindings/arm/amlogic.txt +@@ -71,6 +71,7 @@ Board compatible values (alphabetically, grouped by SoC): + + - "amlogic,q200" (Meson gxm s912) + - "amlogic,q201" (Meson gxm s912) ++ - "khadas,vim2" (Meson gxm s912) + - "kingnovel,r-box-pro" (Meson gxm S912) + - "nexbox,a1" (Meson gxm s912) + +diff --git a/arch/arm64/boot/dts/amlogic/Makefile b/arch/arm64/boot/dts/amlogic/Makefile +index 543416b..747bcc3 100644 +--- a/arch/arm64/boot/dts/amlogic/Makefile ++++ b/arch/arm64/boot/dts/amlogic/Makefile +@@ -16,6 +16,7 @@ dtb-$(CONFIG_ARCH_MESON) += meson-gxl-s905x-nexbox-a95x.dtb + dtb-$(CONFIG_ARCH_MESON) += meson-gxl-s905x-p212.dtb + dtb-$(CONFIG_ARCH_MESON) += meson-gxl-s905d-p230.dtb + dtb-$(CONFIG_ARCH_MESON) += meson-gxl-s905d-p231.dtb ++dtb-$(CONFIG_ARCH_MESON) += meson-gxm-khadas-vim2.dtb + dtb-$(CONFIG_ARCH_MESON) += meson-gxm-nexbox-a1.dtb + dtb-$(CONFIG_ARCH_MESON) += meson-gxm-q200.dtb + dtb-$(CONFIG_ARCH_MESON) += meson-gxm-q201.dtb +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts +new file mode 100644 +index 0000000..32c138e +--- /dev/null ++++ b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts +@@ -0,0 +1,399 @@ ++/* ++ * Copyright (c) 2017 Martin Blumenstingl . ++ * Copyright (c) 2017 BayLibre, SAS ++ * Author: Neil Armstrong ++ * ++ * SPDX-License-Identifier: (GPL-2.0+ OR MIT) ++ */ ++ ++/dts-v1/; ++ ++#include ++#include ++ ++#include "meson-gxm.dtsi" ++ ++/ { ++ compatible = "khadas,vim2", "amlogic,s912", "amlogic,meson-gxm"; ++ model = "Khadas VIM2"; ++ ++ aliases { ++ serial0 = &uart_AO; ++ serial1 = &uart_A; ++ serial2 = &uart_AO_B; ++ }; ++ ++ chosen { ++ stdout-path = "serial0:115200n8"; ++ }; ++ ++ memory@0 { ++ device_type = "memory"; ++ reg = <0x0 0x0 0x0 0x80000000>; ++ }; ++ ++ adc-keys { ++ compatible = "adc-keys"; ++ io-channels = <&saradc 0>; ++ io-channel-names = "buttons"; ++ keyup-threshold-microvolt = <1710000>; ++ ++ button-function { ++ label = "Function"; ++ linux,code = ; ++ press-threshold-microvolt = <10000>; ++ }; ++ }; ++ ++ emmc_pwrseq: emmc-pwrseq { ++ compatible = "mmc-pwrseq-emmc"; ++ reset-gpios = <&gpio BOOT_9 GPIO_ACTIVE_LOW>; ++ }; ++ ++ gpio_fan: gpio-fan { ++ compatible = "gpio-fan"; ++ gpios = <&gpio GPIODV_14 GPIO_ACTIVE_HIGH ++ &gpio GPIODV_15 GPIO_ACTIVE_HIGH>; ++ /* Dummy RPM values since fan is optional */ ++ gpio-fan,speed-map = <0 0 ++ 1 1 ++ 2 2 ++ 3 3>; ++ cooling-min-level = <0>; ++ cooling-max-level = <3>; ++ #cooling-cells = <2>; ++ }; ++ ++ gpio-keys-polled { ++ compatible = "gpio-keys-polled"; ++ #address-cells = <1>; ++ #size-cells = <0>; ++ poll-interval = <100>; ++ ++ button@0 { ++ label = "power"; ++ linux,code = ; ++ gpios = <&gpio_ao GPIOAO_2 GPIO_ACTIVE_LOW>; ++ }; ++ }; ++ ++ hdmi-connector { ++ compatible = "hdmi-connector"; ++ type = "a"; ++ ++ port { ++ hdmi_connector_in: endpoint { ++ remote-endpoint = <&hdmi_tx_tmds_out>; ++ }; ++ }; ++ }; ++ ++ pwmleds { ++ compatible = "pwm-leds"; ++ ++ power { ++ label = "vim:red:power"; ++ pwms = <&pwm_AO_ab 1 7812500 0>; ++ max-brightness = <255>; ++ linux,default-trigger = "default-on"; ++ }; ++ }; ++ ++ sdio_pwrseq: sdio-pwrseq { ++ compatible = "mmc-pwrseq-simple"; ++ reset-gpios = <&gpio GPIOX_6 GPIO_ACTIVE_LOW>; ++ clocks = <&wifi32k>; ++ clock-names = "ext_clock"; ++ }; ++ ++ thermal-zones { ++ cpu-thermal { ++ polling-delay-passive = <250>; /* milliseconds */ ++ polling-delay = <1000>; /* milliseconds */ ++ ++ thermal-sensors = <&scpi_sensors 0>; ++ ++ trips { ++ cpu_alert0: cpu-alert0 { ++ temperature = <70000>; /* millicelsius */ ++ hysteresis = <2000>; /* millicelsius */ ++ type = "active"; ++ }; ++ ++ cpu_alert1: cpu-alert1 { ++ temperature = <80000>; /* millicelsius */ ++ hysteresis = <2000>; /* millicelsius */ ++ type = "passive"; ++ }; ++ }; ++ ++ cooling-maps { ++ map0 { ++ trip = <&cpu_alert0>; ++ cooling-device = <&gpio_fan THERMAL_NO_LIMIT 1>; ++ }; ++ ++ map1 { ++ trip = <&cpu_alert1>; ++ cooling-device = <&gpio_fan 2 THERMAL_NO_LIMIT>; ++ }; ++ ++ map2 { ++ trip = <&cpu_alert1>; ++ cooling-device = ++ <&cpu0 THERMAL_NO_LIMIT THERMAL_NO_LIMIT>; ++ }; ++ ++ map3 { ++ trip = <&cpu_alert1>; ++ cooling-device = ++ <&cpu4 THERMAL_NO_LIMIT THERMAL_NO_LIMIT>; ++ }; ++ }; ++ }; ++ }; ++ ++ vcc_3v3: regulator-vcc_3v3 { ++ compatible = "regulator-fixed"; ++ regulator-name = "VCC_3V3"; ++ regulator-min-microvolt = <3300000>; ++ regulator-max-microvolt = <3300000>; ++ }; ++ ++ vddio_ao18: regulator-vddio_ao18 { ++ compatible = "regulator-fixed"; ++ regulator-name = "VDDIO_AO18"; ++ regulator-min-microvolt = <1800000>; ++ regulator-max-microvolt = <1800000>; ++ }; ++ ++ vddio_boot: regulator-vddio_boot { ++ compatible = "regulator-fixed"; ++ regulator-name = "VDDIO_BOOT"; ++ regulator-min-microvolt = <1800000>; ++ regulator-max-microvolt = <1800000>; ++ }; ++ ++ vddao_3v3: regulator-vddao_3v3 { ++ compatible = "regulator-fixed"; ++ regulator-name = "VDDAO_3V3"; ++ regulator-min-microvolt = <3300000>; ++ regulator-max-microvolt = <3300000>; ++ }; ++ ++ wifi32k: wifi32k { ++ compatible = "pwm-clock"; ++ #clock-cells = <0>; ++ clock-frequency = <32768>; ++ pwms = <&pwm_ef 0 30518 0>; /* PWM_E at 32.768KHz */ ++ }; ++}; ++ ++&cec_AO { ++ status = "okay"; ++ pinctrl-0 = <&ao_cec_pins>; ++ pinctrl-names = "default"; ++ hdmi-phandle = <&hdmi_tx>; ++}; ++ ++&cpu0 { ++ cooling-min-level = <0>; ++ cooling-max-level = <6>; ++ #cooling-cells = <2>; ++}; ++ ++&cpu4 { ++ cooling-min-level = <0>; ++ cooling-max-level = <4>; ++ #cooling-cells = <2>; ++}; ++ ++ðmac { ++ pinctrl-0 = <ð_pins>; ++ pinctrl-names = "default"; ++ ++ /* Select external PHY by default */ ++ phy-handle = <&external_phy>; ++ ++ amlogic,tx-delay-ns = <2>; ++ ++ /* External PHY reset is shared with internal PHY Led signals */ ++ snps,reset-gpio = <&gpio GPIOZ_14 0>; ++ snps,reset-delays-us = <0 10000 1000000>; ++ snps,reset-active-low; ++ ++ /* External PHY is in RGMII */ ++ phy-mode = "rgmii"; ++ ++ status = "okay"; ++}; ++ ++&external_mdio { ++ external_phy: ethernet-phy@0 { ++ /* Realtek RTL8211F (0x001cc916) */ ++ reg = <0>; ++ }; ++}; ++ ++&hdmi_tx { ++ status = "okay"; ++ pinctrl-0 = <&hdmi_hpd_pins>, <&hdmi_i2c_pins>; ++ pinctrl-names = "default"; ++}; ++ ++&hdmi_tx_tmds_port { ++ hdmi_tx_tmds_out: endpoint { ++ remote-endpoint = <&hdmi_connector_in>; ++ }; ++}; ++ ++&i2c_A { ++ status = "okay"; ++ pinctrl-0 = <&i2c_a_pins>; ++ pinctrl-names = "default"; ++}; ++ ++&i2c_B { ++ status = "okay"; ++ pinctrl-0 = <&i2c_b_pins>; ++ pinctrl-names = "default"; ++ ++ rtc: rtc@51 { ++ /* has to be enabled manually when a battery is connected: */ ++ status = "disabled"; ++ compatible = "haoyu,hym8563"; ++ reg = <0x51>; ++ #clock-cells = <0>; ++ clock-frequency = <32768>; ++ clock-output-names = "xin32k"; ++ }; ++}; ++ ++&ir { ++ status = "okay"; ++ pinctrl-0 = <&remote_input_ao_pins>; ++ pinctrl-names = "default"; ++ linux,rc-map-name = "rc-geekbox"; ++}; ++ ++&pwm_AO_ab { ++ status = "okay"; ++ pinctrl-0 = <&pwm_ao_a_3_pins>, <&pwm_ao_b_pins>; ++ pinctrl-names = "default"; ++ clocks = <&clkc CLKID_FCLK_DIV4>; ++ clock-names = "clkin0"; ++}; ++ ++&pwm_ef { ++ status = "okay"; ++ pinctrl-0 = <&pwm_e_pins>, <&pwm_f_clk_pins>; ++ pinctrl-names = "default"; ++ clocks = <&clkc CLKID_FCLK_DIV4>; ++ clock-names = "clkin0"; ++}; ++ ++&sd_emmc_a { ++ status = "okay"; ++ pinctrl-0 = <&sdio_pins>; ++ pinctrl-names = "default"; ++ #address-cells = <1>; ++ #size-cells = <0>; ++ ++ bus-width = <4>; ++ max-frequency = <100000000>; ++ ++ non-removable; ++ disable-wp; ++ ++ mmc-pwrseq = <&sdio_pwrseq>; ++ ++ vmmc-supply = <&vddao_3v3>; ++ vqmmc-supply = <&vddio_boot>; ++ ++ brcmf: wifi@1 { ++ reg = <1>; ++ compatible = "brcm,bcm4329-fmac"; ++ }; ++}; ++ ++/* SD card */ ++&sd_emmc_b { ++ status = "okay"; ++ pinctrl-0 = <&sdcard_pins>; ++ pinctrl-names = "default"; ++ ++ bus-width = <4>; ++ cap-sd-highspeed; ++ max-frequency = <100000000>; ++ disable-wp; ++ ++ cd-gpios = <&gpio CARD_6 GPIO_ACTIVE_HIGH>; ++ cd-inverted; ++ ++ vmmc-supply = <&vddao_3v3>; ++ vqmmc-supply = <&vddio_boot>; ++}; ++ ++/* eMMC */ ++&sd_emmc_c { ++ status = "okay"; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; ++ pinctrl-names = "default"; ++ ++ bus-width = <8>; ++ cap-sd-highspeed; ++ cap-mmc-highspeed; ++ max-frequency = <200000000>; ++ non-removable; ++ disable-wp; ++ mmc-ddr-1_8v; ++ mmc-hs200-1_8v; ++ ++ mmc-pwrseq = <&emmc_pwrseq>; ++ vmmc-supply = <&vcc_3v3>; ++ vqmmc-supply = <&vddio_boot>; ++}; ++ ++/* ++ * EMMC_DS pin is shared between SPI NOR CS and eMMC Data Strobe ++ * Remove emmc_ds_pins from sd_emmc_c pinctrl-0 then spifc can be enabled ++ */ ++&spifc { ++ status = "disabled"; ++ pinctrl-0 = <&nor_pins>; ++ pinctrl-names = "default"; ++ ++ w25q32: spi-flash@0 { ++ #address-cells = <1>; ++ #size-cells = <1>; ++ compatible = "winbond,w25q16", "jedec,spi-nor"; ++ reg = <0>; ++ spi-max-frequency = <3000000>; ++ }; ++}; ++ ++/* This one is connected to the Bluetooth module */ ++&uart_A { ++ status = "okay"; ++ pinctrl-0 = <&uart_a_pins>; ++ pinctrl-names = "default"; ++}; ++ ++/* This is brought out on the Linux_RX (18) and Linux_TX (19) pins: */ ++&uart_AO { ++ status = "okay"; ++ pinctrl-0 = <&uart_ao_a_pins>; ++ pinctrl-names = "default"; ++}; ++ ++/* This is brought out on the UART_RX_AO_B (15) and UART_TX_AO_B (16) pins: */ ++&uart_AO_B { ++ status = "okay"; ++ pinctrl-0 = <&uart_ao_b_pins>; ++ pinctrl-names = "default"; ++}; ++ ++&saradc { ++ status = "okay"; ++ vref-supply = <&vddio_ao18>; ++}; +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0002-ARM64-dts-meson-gxbb-allow-child-devices-on-the-USB-.patch b/patch/kernel/meson64-dev/0002-ARM64-dts-meson-gxbb-allow-child-devices-on-the-USB-.patch new file mode 100644 index 0000000000..d30865e590 --- /dev/null +++ b/patch/kernel/meson64-dev/0002-ARM64-dts-meson-gxbb-allow-child-devices-on-the-USB-.patch @@ -0,0 +1,41 @@ +From 9724ee442cf7bf4da885433b28029ac559f1f26a Mon Sep 17 00:00:00 2001 +From: Martin Blumenstingl +Date: Thu, 12 Jan 2017 01:38:26 +0100 +Subject: [PATCH 02/36] ARM64: dts: meson-gxbb: allow child devices on the USB + controller + +Add the size and adress cells to the USB controllers to allow specifying +child devices (for example the USB hub on the Odroid-C2 which must be +taken out of reset to work). + +Signed-off-by: Martin Blumenstingl +Signed-off-by: Neil Armstrong +--- + arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi +index af834cd..7d38d55 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi +@@ -73,6 +73,8 @@ + + usb0: usb@c9000000 { + compatible = "amlogic,meson-gxbb-usb", "snps,dwc2"; ++ #address-cells = <1>; ++ #size-cells = <0>; + reg = <0x0 0xc9000000 0x0 0x40000>; + interrupts = ; + clocks = <&clkc CLKID_USB0_DDR_BRIDGE>; +@@ -85,6 +87,8 @@ + + usb1: usb@c9100000 { + compatible = "amlogic,meson-gxbb-usb", "snps,dwc2"; ++ #address-cells = <1>; ++ #size-cells = <0>; + reg = <0x0 0xc9100000 0x0 0x40000>; + interrupts = ; + clocks = <&clkc CLKID_USB1_DDR_BRIDGE>; +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0003-ARM64-dts-meson-gxbb-odroidc2-take-USB-hub-out-of-re.patch b/patch/kernel/meson64-dev/0003-ARM64-dts-meson-gxbb-odroidc2-take-USB-hub-out-of-re.patch new file mode 100644 index 0000000000..a6af2007f4 --- /dev/null +++ b/patch/kernel/meson64-dev/0003-ARM64-dts-meson-gxbb-odroidc2-take-USB-hub-out-of-re.patch @@ -0,0 +1,34 @@ +From 53d19221222d8fe49aae75721a9547c7d104e9ed Mon Sep 17 00:00:00 2001 +From: Martin Blumenstingl +Date: Thu, 12 Jan 2017 01:39:20 +0100 +Subject: [PATCH 03/36] ARM64: dts: meson-gxbb-odroidc2: take USB hub out of + reset + +This takes the USB hub out of reset, otherwise the hub is not working. + +Fixes: 5a0803bd5ae ("ARM64: dts: meson-gxbb-odroidc2: Enable USB Nodes") +Signed-off-by: Martin Blumenstingl +Signed-off-by: Neil Armstrong +--- + arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts | 7 +++++++ + 1 file changed, 7 insertions(+) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts +index 1ffa1c2..b035c72 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts +@@ -309,4 +309,11 @@ + + &usb1 { + status = "okay"; ++ ++ hub@1 { ++ compatible = "usb5e3,610"; ++ reg = <1>; ++ reset-gpios = <&gpio GPIOAO_4 GPIO_ACTIVE_LOW>; ++ reset-duration-us = <3000>; ++ }; + }; +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0004-phy-meson-add-USB3-PHY-support-for-Meson-GXL.patch b/patch/kernel/meson64-dev/0004-phy-meson-add-USB3-PHY-support-for-Meson-GXL.patch new file mode 100644 index 0000000000..6a16aa1033 --- /dev/null +++ b/patch/kernel/meson64-dev/0004-phy-meson-add-USB3-PHY-support-for-Meson-GXL.patch @@ -0,0 +1,260 @@ +From 1b68976e2e05b3e10e4f3070ef5b9e08640ad7a0 Mon Sep 17 00:00:00 2001 +From: Martin Blumenstingl +Date: Sat, 26 Nov 2016 15:56:32 +0100 +Subject: [PATCH 04/36] phy: meson: add USB3 PHY support for Meson GXL + +This adds USB3 PHY driver found on Meson GXL and GXM SoCs. + +Unfortunately there are no datasheets available for any of these PHYs. +Both drivers were written by reading the reference drivers provided by +Amlogic and analyzing the registers on the kernel that was shipped with +my board. + +Signed-off-by: Martin Blumenstingl +Signed-off-by: Neil Armstrong +--- + drivers/phy/amlogic/Kconfig | 13 ++ + drivers/phy/amlogic/Makefile | 1 + + drivers/phy/amlogic/phy-meson-gxl-usb3.c | 198 +++++++++++++++++++++++++++++++ + 3 files changed, 212 insertions(+) + create mode 100644 drivers/phy/amlogic/phy-meson-gxl-usb3.c + +diff --git a/drivers/phy/amlogic/Kconfig b/drivers/phy/amlogic/Kconfig +index cb8f450..5d11a3e 100644 +--- a/drivers/phy/amlogic/Kconfig ++++ b/drivers/phy/amlogic/Kconfig +@@ -13,6 +13,19 @@ config PHY_MESON8B_USB2 + Meson8b and GXBB SoCs. + If unsure, say N. + ++config PHY_MESON_GXL_USB3 ++ tristate "Meson GXL and GXM USB3 PHY drivers" ++ default ARCH_MESON ++ depends on OF && (ARCH_MESON || COMPILE_TEST) ++ depends on USB_SUPPORT ++ select USB_COMMON ++ select GENERIC_PHY ++ select REGMAP_MMIO ++ help ++ Enable this to support the Meson USB3 PHY found in Meson ++ GXL and GXM SoCs. ++ If unsure, say N. ++ + config PHY_MESON_GXL_USB2 + tristate "Meson GXL and GXM USB2 PHY drivers" + default ARCH_MESON +diff --git a/drivers/phy/amlogic/Makefile b/drivers/phy/amlogic/Makefile +index cfdc987..4fd8848 100644 +--- a/drivers/phy/amlogic/Makefile ++++ b/drivers/phy/amlogic/Makefile +@@ -1,2 +1,3 @@ + obj-$(CONFIG_PHY_MESON8B_USB2) += phy-meson8b-usb2.o + obj-$(CONFIG_PHY_MESON_GXL_USB2) += phy-meson-gxl-usb2.o ++obj-$(CONFIG_PHY_MESON_GXL_USB3) += phy-meson-gxl-usb3.o +diff --git a/drivers/phy/amlogic/phy-meson-gxl-usb3.c b/drivers/phy/amlogic/phy-meson-gxl-usb3.c +new file mode 100644 +index 0000000..9af5222 +--- /dev/null ++++ b/drivers/phy/amlogic/phy-meson-gxl-usb3.c +@@ -0,0 +1,198 @@ ++/* ++ * Meson GXL USB3 PHY driver ++ * ++ * Copyright (C) 2016 Martin Blumenstingl ++ * ++ * 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. ++ * ++ * You should have received a copy of the GNU General Public License ++ * along with this program. If not, see . ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#define USB_R0 0x00 ++ #define USB_R0_P30_FSEL_SHIFT 0 ++ #define USB_R0_P30_FSEL_MASK GENMASK(5, 0) ++ #define USB_R0_P30_PHY_RESET BIT(6) ++ #define USB_R0_P30_TEST_POWERDOWN_HSP BIT(7) ++ #define USB_R0_P30_TEST_POWERDOWN_SSP BIT(8) ++ #define USB_R0_P30_ACJT_LEVEL_SHIFT 9 ++ #define USB_R0_P30_ACJT_LEVEL_MASK GENMASK(13, 9) ++ #define USB_R0_P30_TX_BOOST_LEVEL_SHIFT 14 ++ #define USB_R0_P30_TX_BOOST_LEVEL_MASK GENMASK(16, 14) ++ #define USB_R0_P30_LANE0_TX2RX_LOOPBACK BIT(17) ++ #define USB_R0_P30_LANE0_EXT_PCLK_REQ BIT(18) ++ #define USB_R0_P30_PCS_RX_LOS_MASK_VAL_SHIFT 19 ++ #define USB_R0_P30_PCS_RX_LOS_MASK_VAL_MASK GENMASK(28, 19) ++ #define USB_R0_U2D_SS_SCALEDOWN_MODE_SHIFT 29 ++ #define USB_R0_U2D_SS_SCALEDOWN_MODE_MASK GENMASK(30, 29) ++ #define USB_R0_U2D_ACT BIT(31) ++ ++#define USB_R1 0x04 ++ #define USB_R1_U3H_BIGENDIAN_GS BIT(0) ++ #define USB_R1_U3H_PME_ENABLE BIT(1) ++ #define USB_R1_U3H_HUB_PORT_OVERCURRENT_SHIFT 2 ++ #define USB_R1_U3H_HUB_PORT_OVERCURRENT_MASK GENMASK(6, 2) ++ #define USB_R1_U3H_HUB_PORT_PERM_ATTACH_SHIFT 7 ++ #define USB_R1_U3H_HUB_PORT_PERM_ATTACH_MASK GENMASK(11, 7) ++ #define USB_R1_U3H_HOST_U2_PORT_DISABLE_SHIFT 12 ++ #define USB_R1_U3H_HOST_U2_PORT_DISABLE_MASK GENMASK(15, 12) ++ #define USB_R1_U3H_HOST_U3_PORT_DISABLE BIT(16) ++ #define USB_R1_U3H_HOST_PORT_POWER_CONTROL_PRESENT BIT(17) ++ #define USB_R1_U3H_HOST_MSI_ENABLE BIT(18) ++ #define USB_R1_U3H_FLADJ_30MHZ_REG_SHIFT 19 ++ #define USB_R1_U3H_FLADJ_30MHZ_REG_MASK GENMASK(24, 19) ++ #define USB_R1_P30_PCS_TX_SWING_FULL_SHIFT 25 ++ #define USB_R1_P30_PCS_TX_SWING_FULL_MASK GENMASK(31, 25) ++ ++#define USB_R2 0x08 ++ #define USB_R2_P30_CR_DATA_IN_SHIFT 0 ++ #define USB_R2_P30_CR_DATA_IN_MASK GENMASK(15, 0) ++ #define USB_R2_P30_CR_READ BIT(16) ++ #define USB_R2_P30_CR_WRITE BIT(17) ++ #define USB_R2_P30_CR_CAP_ADDR BIT(18) ++ #define USB_R2_P30_CR_CAP_DATA BIT(19) ++ #define USB_R2_P30_PCS_TX_DEEMPH_3P5DB_SHIFT 20 ++ #define USB_R2_P30_PCS_TX_DEEMPH_3P5DB_MASK GENMASK(25, 20) ++ #define USB_R2_P30_PCS_TX_DEEMPH_6DB_SHIFT 26 ++ #define USB_R2_P30_PCS_TX_DEEMPH_6DB_MASK GENMASK(31, 26) ++ ++#define USB_R3 0x0c ++ #define USB_R3_P30_SSC_ENABLE BIT(0) ++ #define USB_R3_P30_SSC_RANGE_SHIFT 1 ++ #define USB_R3_P30_SSC_RANGE_MASK GENMASK(3, 1) ++ #define USB_R3_P30_SSC_REF_CLK_SEL_SHIFT 4 ++ #define USB_R3_P30_SSC_REF_CLK_SEL_MASK GENMASK(12, 4) ++ #define USB_R3_P30_REF_SSP_EN BIT(13) ++ #define USB_R3_P30_LOS_BIAS_SHIFT 16 ++ #define USB_R3_P30_LOS_BIAS_MASK GENMASK(18, 16) ++ #define USB_R3_P30_LOS_LEVEL_SHIFT 19 ++ #define USB_R3_P30_LOS_LEVEL_MASK GENMASK(23, 19) ++ #define USB_R3_P30_MPLL_MULTIPLIER_SHIFT 24 ++ #define USB_R3_P30_MPLL_MULTIPLIER_MASK GENMASK(30, 24) ++ ++#define USB_R4 0x10 ++ #define USB_R4_P21_PORT_RESET_0 BIT(0) ++ #define USB_R4_P21_SLEEP_M0 BIT(1) ++ #define USB_R4_MEM_PD_SHIFT 2 ++ #define USB_R4_MEM_PD_MASK GENMASK(3, 2) ++ #define USB_R4_P21_ONLY BIT(4) ++ ++#define USB_R5 0x14 ++ #define USB_R5_ID_DIG_SYNC BIT(0) ++ #define USB_R5_ID_DIG_REG BIT(1) ++ #define USB_R5_ID_DIG_CFG_SHIFT 2 ++ #define USB_R5_ID_DIG_CFG_MASK GENMASK(3, 2) ++ #define USB_R5_ID_DIG_EN_0 BIT(4) ++ #define USB_R5_ID_DIG_EN_1 BIT(5) ++ #define USB_R5_ID_DIG_CURR BIT(6) ++ #define USB_R5_ID_DIG_IRQ BIT(7) ++ #define USB_R5_ID_DIG_TH_SHIFT 8 ++ #define USB_R5_ID_DIG_TH_MASK GENMASK(15, 8) ++ #define USB_R5_ID_DIG_CNT_SHIFT 16 ++ #define USB_R5_ID_DIG_CNT_MASK GENMASK(23, 16) ++ ++/* read-only register */ ++#define USB_R6 0x18 ++ #define USB_R6_P30_CR_DATA_OUT_SHIFT 0 ++ #define USB_R6_P30_CR_DATA_OUT_MASK GENMASK(15, 0) ++ #define USB_R6_P30_CR_ACK BIT(16) ++ ++#define RESET_COMPLETE_TIME 500 ++ ++struct phy_meson_gxl_usb3_priv { ++ struct regmap *regmap; ++ struct phy *this_phy; ++}; ++ ++static const struct regmap_config phy_meson_gxl_usb3_regmap_conf = { ++ .reg_bits = 32, ++ .val_bits = 32, ++ .reg_stride = 4, ++ .max_register = USB_R6, ++}; ++ ++static int phy_meson_gxl_usb3_power_on(struct phy *phy) ++{ ++ struct phy_meson_gxl_usb3_priv *priv = phy_get_drvdata(phy); ++ ++ regmap_update_bits(priv->regmap, USB_R1, ++ USB_R1_U3H_FLADJ_30MHZ_REG_MASK, ++ 0x20 << USB_R1_U3H_FLADJ_30MHZ_REG_SHIFT); ++ ++ return 0; ++} ++ ++static const struct phy_ops phy_meson_gxl_usb3_ops = { ++ .power_on = phy_meson_gxl_usb3_power_on, ++ .owner = THIS_MODULE, ++}; ++ ++static int phy_meson_gxl_usb3_probe(struct platform_device *pdev) ++{ ++ struct device *dev = &pdev->dev; ++ struct device_node *np = dev->of_node; ++ struct phy_meson_gxl_usb3_priv *priv; ++ struct resource *res; ++ struct phy *phy; ++ struct phy_provider *phy_provider; ++ void __iomem *base; ++ ++ priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); ++ if (!priv) ++ return -ENOMEM; ++ ++ res = platform_get_resource(pdev, IORESOURCE_MEM, 0); ++ base = devm_ioremap_resource(dev, res); ++ if (IS_ERR(base)) ++ return PTR_ERR(base); ++ ++ priv->regmap = devm_regmap_init_mmio(dev, base, ++ &phy_meson_gxl_usb3_regmap_conf); ++ if (IS_ERR(priv->regmap)) ++ return PTR_ERR(priv->regmap); ++ ++ phy = devm_phy_create(dev, np, &phy_meson_gxl_usb3_ops); ++ if (IS_ERR(phy)) { ++ dev_err(dev, "failed to create PHY\n"); ++ return PTR_ERR(phy); ++ } ++ ++ phy_set_drvdata(phy, priv); ++ ++ phy_provider = devm_of_phy_provider_register(dev, of_phy_simple_xlate); ++ ++ return PTR_ERR_OR_ZERO(phy_provider); ++} ++ ++static const struct of_device_id phy_meson_gxl_usb3_of_match[] = { ++ { .compatible = "amlogic,meson-gxl-usb3-phy", }, ++ { }, ++}; ++MODULE_DEVICE_TABLE(of, phy_meson_gxl_usb3_of_match); ++ ++static struct platform_driver phy_meson_gxl_usb3_driver = { ++ .probe = phy_meson_gxl_usb3_probe, ++ .driver = { ++ .name = "phy-meson-gxl-usb3", ++ .of_match_table = phy_meson_gxl_usb3_of_match, ++ }, ++}; ++module_platform_driver(phy_meson_gxl_usb3_driver); ++ ++MODULE_AUTHOR("Martin Blumenstingl "); ++MODULE_DESCRIPTION("Meson GXL USB3 PHY driver"); ++MODULE_LICENSE("GPL"); +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/1001-usb-host-add-a-generic-platform-USB-roothub-driver.patch b/patch/kernel/meson64-dev/0005-usb-host-add-a-generic-platform-USB-roothub-driver.patch similarity index 96% rename from patch/kernel/meson64-dev/1001-usb-host-add-a-generic-platform-USB-roothub-driver.patch rename to patch/kernel/meson64-dev/0005-usb-host-add-a-generic-platform-USB-roothub-driver.patch index 7cfb43b434..85051b8c70 100644 --- a/patch/kernel/meson64-dev/1001-usb-host-add-a-generic-platform-USB-roothub-driver.patch +++ b/patch/kernel/meson64-dev/0005-usb-host-add-a-generic-platform-USB-roothub-driver.patch @@ -1,7 +1,7 @@ -From acfe799c4e00a726cdb0bbd37aaaa123070ed59e Mon Sep 17 00:00:00 2001 +From 0e1b7fc3afdff8b63a2ed34ae6222cc02b043d62 Mon Sep 17 00:00:00 2001 From: Martin Blumenstingl Date: Tue, 10 Jan 2017 18:59:43 +0100 -Subject: [PATCH 75/79] usb: host: add a generic platform USB roothub driver +Subject: [PATCH 05/36] usb: host: add a generic platform USB roothub driver Many SoC platforms have separate devices for the USB PHY which are registered through the generic PHY framework. These PHYs have to be @@ -90,10 +90,10 @@ index 0000000..23b24b6 + }; + } diff --git a/drivers/usb/host/Kconfig b/drivers/usb/host/Kconfig -index ababb91..3f450e0 100644 +index fa5692d..b8b05c7 100644 --- a/drivers/usb/host/Kconfig +++ b/drivers/usb/host/Kconfig -@@ -797,6 +797,9 @@ config USB_HCD_SSB +@@ -805,6 +805,9 @@ config USB_HCD_SSB If unsure, say N. @@ -104,10 +104,10 @@ index ababb91..3f450e0 100644 bool "HCD test mode support" ---help--- diff --git a/drivers/usb/host/Makefile b/drivers/usb/host/Makefile -index c77b0a3..93f0dd2 100644 +index 4ab2689..873ebd9 100644 --- a/drivers/usb/host/Makefile +++ b/drivers/usb/host/Makefile -@@ -29,6 +29,8 @@ obj-$(CONFIG_USB_WHCI_HCD) += whci/ +@@ -30,6 +30,8 @@ obj-$(CONFIG_USB_WHCI_HCD) += whci/ obj-$(CONFIG_USB_PCI) += pci-quirks.o @@ -289,5 +289,5 @@ index 0000000..bde0bf2 + +#endif /* USB_HOST_PLATFORM_ROOTHUB_H */ -- -1.9.1 +2.7.4 diff --git a/patch/kernel/meson64-dev/1002-usb-host-xhci-plat-integrate-the-platform-roothub.patch b/patch/kernel/meson64-dev/0006-usb-host-xhci-plat-integrate-the-platform-roothub.patch similarity index 88% rename from patch/kernel/meson64-dev/1002-usb-host-xhci-plat-integrate-the-platform-roothub.patch rename to patch/kernel/meson64-dev/0006-usb-host-xhci-plat-integrate-the-platform-roothub.patch index 09e4f6af37..494cc338cf 100644 --- a/patch/kernel/meson64-dev/1002-usb-host-xhci-plat-integrate-the-platform-roothub.patch +++ b/patch/kernel/meson64-dev/0006-usb-host-xhci-plat-integrate-the-platform-roothub.patch @@ -1,7 +1,7 @@ -From 9dfd5d48fbcd31b12825e81d532aca76c2b769f8 Mon Sep 17 00:00:00 2001 +From 09527e1e94f404929f3cb73730cf2b7a1eb044cd Mon Sep 17 00:00:00 2001 From: Martin Blumenstingl Date: Wed, 11 Jan 2017 11:34:59 +0100 -Subject: [PATCH 76/79] usb: host: xhci: plat: integrate the platform-roothub +Subject: [PATCH 06/36] usb: host: xhci: plat: integrate the platform-roothub This enables the platform-roothub for the xhci-plat driver. This allows specifying a PHY for each port via devicetree. All PHYs will then be @@ -41,7 +41,7 @@ index 2d80b60..31b4f68 100644 usb@f0931000 { compatible = "generic-xhci"; diff --git a/drivers/usb/host/Kconfig b/drivers/usb/host/Kconfig -index 3f450e0..d6279d7 100644 +index b8b05c7..3bdc49e8 100644 --- a/drivers/usb/host/Kconfig +++ b/drivers/usb/host/Kconfig @@ -36,6 +36,7 @@ config USB_XHCI_PCI @@ -53,10 +53,10 @@ index 3f450e0..d6279d7 100644 Adds an xHCI host driver for a generic platform device, which provides a memory space and an irq. diff --git a/drivers/usb/host/xhci-plat.c b/drivers/usb/host/xhci-plat.c -index c04144b..4de20b5 100644 +index 1cb6eae..a80d585 100644 --- a/drivers/usb/host/xhci-plat.c +++ b/drivers/usb/host/xhci-plat.c -@@ -285,10 +285,20 @@ static int xhci_plat_probe(struct platform_device *pdev) +@@ -281,10 +281,20 @@ static int xhci_plat_probe(struct platform_device *pdev) goto put_usb3_hcd; } @@ -78,7 +78,7 @@ index c04144b..4de20b5 100644 if (HCC_MAX_PSA(xhci->hcc_params) >= 4) xhci->shared_hcd->can_do_streams = 1; -@@ -311,6 +321,9 @@ static int xhci_plat_probe(struct platform_device *pdev) +@@ -307,6 +317,9 @@ static int xhci_plat_probe(struct platform_device *pdev) dealloc_usb2_hcd: usb_remove_hcd(hcd); @@ -88,7 +88,7 @@ index c04144b..4de20b5 100644 disable_usb_phy: usb_phy_shutdown(hcd->usb_phy); -@@ -342,6 +355,8 @@ static int xhci_plat_remove(struct platform_device *dev) +@@ -338,6 +351,8 @@ static int xhci_plat_remove(struct platform_device *dev) usb_remove_hcd(xhci->shared_hcd); usb_phy_shutdown(hcd->usb_phy); @@ -97,7 +97,7 @@ index c04144b..4de20b5 100644 usb_remove_hcd(hcd); usb_put_hcd(xhci->shared_hcd); -@@ -374,6 +389,11 @@ static int __maybe_unused xhci_plat_suspend(struct device *dev) +@@ -370,6 +385,11 @@ static int __maybe_unused xhci_plat_suspend(struct device *dev) if (!device_may_wakeup(dev) && !IS_ERR(xhci->clk)) clk_disable_unprepare(xhci->clk); @@ -109,7 +109,7 @@ index c04144b..4de20b5 100644 return ret; } -@@ -386,6 +406,10 @@ static int __maybe_unused xhci_plat_resume(struct device *dev) +@@ -382,6 +402,10 @@ static int __maybe_unused xhci_plat_resume(struct device *dev) if (!device_may_wakeup(dev) && !IS_ERR(xhci->clk)) clk_prepare_enable(xhci->clk); @@ -121,7 +121,7 @@ index c04144b..4de20b5 100644 if (ret) return ret; diff --git a/drivers/usb/host/xhci.h b/drivers/usb/host/xhci.h -index 73a28a9..7f3d15e 100644 +index 2b48aa4..f340aa0 100644 --- a/drivers/usb/host/xhci.h +++ b/drivers/usb/host/xhci.h @@ -34,6 +34,8 @@ @@ -133,7 +133,7 @@ index 73a28a9..7f3d15e 100644 /* xHCI PCI Configuration Registers */ #define XHCI_SBRN_OFFSET (0x60) -@@ -1725,6 +1727,7 @@ struct xhci_hcd { +@@ -1734,6 +1736,7 @@ struct xhci_hcd { int msix_count; /* optional clock */ struct clk *clk; @@ -142,5 +142,5 @@ index 73a28a9..7f3d15e 100644 struct xhci_device_context_array *dcbaa; struct xhci_ring *cmd_ring; -- -1.9.1 +2.7.4 diff --git a/patch/kernel/meson64-dev/1000-ARM64-dts-meson-gxl-add-USB-host-support.patch b/patch/kernel/meson64-dev/0007-ARM64-dts-meson-gxl-add-USB-host-support.patch similarity index 83% rename from patch/kernel/meson64-dev/1000-ARM64-dts-meson-gxl-add-USB-host-support.patch rename to patch/kernel/meson64-dev/0007-ARM64-dts-meson-gxl-add-USB-host-support.patch index c97fd1ddd6..7abd6dde3b 100644 --- a/patch/kernel/meson64-dev/1000-ARM64-dts-meson-gxl-add-USB-host-support.patch +++ b/patch/kernel/meson64-dev/0007-ARM64-dts-meson-gxl-add-USB-host-support.patch @@ -1,7 +1,7 @@ -From 6006726ba262f50d61f3a001cc87fbc82dd8318a Mon Sep 17 00:00:00 2001 +From 8ef5d73fcc737279094fa9a904fdd45ddc2da765 Mon Sep 17 00:00:00 2001 From: Martin Blumenstingl Date: Sun, 20 Nov 2016 00:23:52 +0100 -Subject: [PATCH 73/79] ARM64: dts: meson-gxl: add USB host support +Subject: [PATCH 07/36] ARM64: dts: meson-gxl: add USB host support This adds USB host support to the Meson GXL SoC. A dwc3 controller is used for host-mode, while a dwc2 controller is used for device-mode only. @@ -21,14 +21,14 @@ enable one and breaking all other ports with that as well). Signed-off-by: Martin Blumenstingl Signed-off-by: Neil Armstrong --- - arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 50 ++++++++++++++++++++++++++++++ - 1 file changed, 50 insertions(+) + arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 59 ++++++++++++++++++++++++++++++ + 1 file changed, 59 insertions(+) diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -index 1e65b0f..c33c29f 100644 +index d8dd329..ebcb5eb 100644 --- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi +++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -49,6 +49,56 @@ +@@ -49,6 +49,65 @@ / { compatible = "amlogic,meson-gxl"; @@ -44,6 +44,8 @@ index 1e65b0f..c33c29f 100644 + dr_mode = "host"; + maximum-speed = "high-speed"; + snps,dis_u2_susphy_quirk; ++ phys = <&usb3_phy0>; ++ phy-names = "usb3-phy"; + status = "disabled"; + + dwc3_roothub: roothub@0 { @@ -81,10 +83,17 @@ index 1e65b0f..c33c29f 100644 + #phy-cells = <0>; + reg = <0x0 0x78020 0x0 0x20>; + status = "okay"; ++ }; ++ ++ usb3_phy0: phy@78080 { ++ compatible = "amlogic,meson-gxl-usb3-phy"; ++ #phy-cells = <0>; ++ reg = <0x0 0x78080 0x0 0x20>; ++ status = "okay"; + }; }; ðmac { -- -1.9.1 +2.7.4 diff --git a/patch/kernel/meson64-dev/0008-ARM64-dts-meson-gxm-add-GXM-specific-USB-host-config.patch b/patch/kernel/meson64-dev/0008-ARM64-dts-meson-gxm-add-GXM-specific-USB-host-config.patch new file mode 100644 index 0000000000..e348f0e0c9 --- /dev/null +++ b/patch/kernel/meson64-dev/0008-ARM64-dts-meson-gxm-add-GXM-specific-USB-host-config.patch @@ -0,0 +1,49 @@ +From a79f891909933ae1613c752913a28e2f273a61c8 Mon Sep 17 00:00:00 2001 +From: Martin Blumenstingl +Date: Sat, 26 Nov 2016 00:17:22 +0100 +Subject: [PATCH 08/36] ARM64: dts: meson-gxm: add GXM specific USB host + configuration + +The USB configuration on GXM is slightly different than on GXL. The dwc3 +controller's internal hub has three USB2 ports (instead of 2 on GXL) +along with a dedicated USB2 PHY for this port. However, it seems that +there are no pins on GXM which would allow connecting the third port to +a physical USB port. + +Signed-off-by: Martin Blumenstingl +Signed-off-by: Neil Armstrong +--- + arch/arm64/boot/dts/amlogic/meson-gxm.dtsi | 17 +++++++++++++++++ + 1 file changed, 17 insertions(+) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxm.dtsi +index 19a798d..5e4cb90 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxm.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxm.dtsi +@@ -121,6 +121,23 @@ + compatible = "amlogic,meson-gxm-aoclkc", "amlogic,meson-gx-aoclkc"; + }; + ++&apb { ++ usb2_phy2: phy@78040 { ++ compatible = "amlogic,meson-gxl-usb2-phy"; ++ #phy-cells = <0>; ++ reg = <0x0 0x78040 0x0 0x20>; ++ status = "disabled"; ++ }; ++}; ++ ++&dwc3_roothub { ++ port@3 { ++ reg = <3>; ++ phys = <&usb2_phy2>; ++ phy-names = "usb2-phy"; ++ }; ++}; ++ + &saradc { + compatible = "amlogic,meson-gxm-saradc", "amlogic,meson-saradc"; + }; +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0009-ARM64-dts-meson-gx-Enable-USB-on-GXL-and-GXM-boards.patch b/patch/kernel/meson64-dev/0009-ARM64-dts-meson-gx-Enable-USB-on-GXL-and-GXM-boards.patch new file mode 100644 index 0000000000..0426ef310a --- /dev/null +++ b/patch/kernel/meson64-dev/0009-ARM64-dts-meson-gx-Enable-USB-on-GXL-and-GXM-boards.patch @@ -0,0 +1,129 @@ +From b03b8bf4a793bbc201461c1f9284a6409b803986 Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Thu, 13 Jul 2017 15:02:33 +0200 +Subject: [PATCH 09/36] ARM64: dts: meson-gx: Enable USB on GXL and GXM boards + +Signed-off-by: Neil Armstrong +--- + arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi | 4 ++++ + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-hwacom-amazetv.dts | 4 ++++ + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts | 4 ++++ + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 4 ++++ + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts | 4 ++++ + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi | 4 ++++ + arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts | 4 ++++ + arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts | 4 ++++ + arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts | 4 ++++ + 9 files changed, 36 insertions(+) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi +index 4157987..7ce9a62 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi +@@ -236,3 +236,7 @@ + pinctrl-0 = <&uart_ao_a_pins>; + pinctrl-names = "default"; + }; ++ ++&usb0 { ++ status = "okay"; ++}; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-hwacom-amazetv.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-hwacom-amazetv.dts +index 977b424..6f2cd8e 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-hwacom-amazetv.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-hwacom-amazetv.dts +@@ -163,3 +163,7 @@ + pinctrl-0 = <&uart_ao_a_pins>; + pinctrl-names = "default"; + }; ++ ++&usb0 { ++ status = "okay"; ++}; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts +index edc512a..89a5fd9 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts +@@ -198,3 +198,7 @@ + pinctrl-0 = <&uart_ao_b_pins>; + pinctrl-names = "default"; + }; ++ ++&usb0 { ++ status = "okay"; ++}; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts +index 64c54c9..4035891 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts +@@ -242,3 +242,7 @@ + pinctrl-0 = <&uart_ao_a_pins>; + pinctrl-names = "default"; + }; ++ ++&usb0 { ++ status = "okay"; ++}; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts +index 1b8f328..6338e6c 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts +@@ -251,3 +251,7 @@ + pinctrl-0 = <&uart_ao_a_pins>; + pinctrl-names = "default"; + }; ++ ++&usb0 { ++ status = "okay"; ++}; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi +index 129af90..7a1c20e 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi +@@ -173,3 +173,7 @@ + pinctrl-0 = <&uart_ao_a_pins>; + pinctrl-names = "default"; + }; ++ ++&usb0 { ++ status = "okay"; ++}; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts +index 32c138e..103575a 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts +@@ -397,3 +397,7 @@ + status = "okay"; + vref-supply = <&vddio_ao18>; + }; ++ ++&usb0 { ++ status = "okay"; ++}; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts +index 22c6977..cfde246 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts +@@ -215,3 +215,7 @@ + pinctrl-0 = <&uart_ao_a_pins>; + pinctrl-names = "default"; + }; ++ ++&usb0 { ++ status = "okay"; ++}; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts +index 470f72b..9837a48 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts +@@ -237,3 +237,7 @@ + pinctrl-0 = <&uart_ao_a_pins>; + pinctrl-names = "default"; + }; ++ ++&usb0 { ++ status = "okay"; ++}; +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0014-clk-meson-gxbb-Add-VPU-and-VAPB-clockids.patch b/patch/kernel/meson64-dev/0014-clk-meson-gxbb-Add-VPU-and-VAPB-clockids.patch new file mode 100644 index 0000000000..315e0bbbc9 --- /dev/null +++ b/patch/kernel/meson64-dev/0014-clk-meson-gxbb-Add-VPU-and-VAPB-clockids.patch @@ -0,0 +1,55 @@ +From 7a03fa7ed4d552f8e1397a18d9f0046f9c8a8076 Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Mon, 16 Oct 2017 17:29:33 +0200 +Subject: [PATCH 14/36] clk: meson: gxbb: Add VPU and VAPB clockids + +Add the clkids for the clocks feeding the Video Processing Unit. + +Signed-off-by: Neil Armstrong +--- + drivers/clk/meson/gxbb.h | 6 +++++- + include/dt-bindings/clock/gxbb-clkc.h | 11 +++++++++++ + 2 files changed, 16 insertions(+), 1 deletion(-) + +diff --git a/drivers/clk/meson/gxbb.h b/drivers/clk/meson/gxbb.h +index 5b1d4b3..aee6fbb 100644 +--- a/drivers/clk/meson/gxbb.h ++++ b/drivers/clk/meson/gxbb.h +@@ -190,8 +190,12 @@ + #define CLKID_SD_EMMC_B_CLK0_DIV 121 + #define CLKID_SD_EMMC_C_CLK0_SEL 123 + #define CLKID_SD_EMMC_C_CLK0_DIV 124 ++#define CLKID_VPU_0_DIV 127 ++#define CLKID_VPU_1_DIV 130 ++#define CLKID_VAPB_0_DIV 134 ++#define CLKID_VAPB_1_DIV 137 + +-#define NR_CLKS 126 ++#define NR_CLKS 141 + + /* include the CLKIDs that have been made part of the DT binding */ + #include +diff --git a/include/dt-bindings/clock/gxbb-clkc.h b/include/dt-bindings/clock/gxbb-clkc.h +index 8c92528..8ba99a5 100644 +--- a/include/dt-bindings/clock/gxbb-clkc.h ++++ b/include/dt-bindings/clock/gxbb-clkc.h +@@ -114,5 +114,16 @@ + #define CLKID_SD_EMMC_A_CLK0 119 + #define CLKID_SD_EMMC_B_CLK0 122 + #define CLKID_SD_EMMC_C_CLK0 125 ++#define CLKID_VPU_0_SEL 126 ++#define CLKID_VPU_0 128 ++#define CLKID_VPU_1_SEL 129 ++#define CLKID_VPU_1 131 ++#define CLKID_VPU 132 ++#define CLKID_VAPB_0_SEL 133 ++#define CLKID_VAPB_0 135 ++#define CLKID_VAPB_1_SEL 136 ++#define CLKID_VAPB_1 138 ++#define CLKID_VAPB_SEL 139 ++#define CLKID_VAPB 140 + + #endif /* __GXBB_CLKC_H */ +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0015-clk-meson-gxbb-Add-VPU-and-VAPB-clocks-data.patch b/patch/kernel/meson64-dev/0015-clk-meson-gxbb-Add-VPU-and-VAPB-clocks-data.patch new file mode 100644 index 0000000000..d5ba5efd2d --- /dev/null +++ b/patch/kernel/meson64-dev/0015-clk-meson-gxbb-Add-VPU-and-VAPB-clocks-data.patch @@ -0,0 +1,357 @@ +From 89e3cdb01f2bf01810474984fd2c676a88973ac5 Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Fri, 13 Oct 2017 14:38:37 +0200 +Subject: [PATCH 15/36] clk: meson: gxbb: Add VPU and VAPB clocks data + +The Amlogic Meson GX SoCs needs these two clocks to power up the +VPU power domain. + +These two clocks are similar to the MALI clocks by having a glitch-free +mux and two similar clocks with gate, divider and muxes. + +Signed-off-by: Neil Armstrong +--- + drivers/clk/meson/gxbb.c | 292 +++++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 292 insertions(+) + +diff --git a/drivers/clk/meson/gxbb.c b/drivers/clk/meson/gxbb.c +index b2d1e8e..a713744 100644 +--- a/drivers/clk/meson/gxbb.c ++++ b/drivers/clk/meson/gxbb.c +@@ -1131,6 +1131,253 @@ static struct clk_gate gxbb_sd_emmc_c_clk0 = { + }, + }; + ++/* VPU Clock */ ++ ++static u32 mux_table_vpu[] = {0, 1, 2, 3}; ++static const char * const gxbb_vpu_parent_names[] = { ++ "fclk_div4", "fclk_div3", "fclk_div5", "fclk_div7" ++}; ++ ++static struct clk_mux gxbb_vpu_0_sel = { ++ .reg = (void *)HHI_VPU_CLK_CNTL, ++ .mask = 0x3, ++ .shift = 9, ++ .lock = &clk_lock, ++ .table = mux_table_vpu, ++ .hw.init = &(struct clk_init_data){ ++ .name = "vpu_0_sel", ++ .ops = &clk_mux_ops, ++ /* ++ * bits 9:10 selects from 4 possible parents: ++ * fclk_div4, fclk_div3, fclk_div5, fclk_div7, ++ */ ++ .parent_names = gxbb_vpu_parent_names, ++ .num_parents = ARRAY_SIZE(gxbb_vpu_parent_names), ++ .flags = CLK_SET_RATE_NO_REPARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_divider gxbb_vpu_0_div = { ++ .reg = (void *)HHI_VPU_CLK_CNTL, ++ .shift = 0, ++ .width = 7, ++ .lock = &clk_lock, ++ .hw.init = &(struct clk_init_data){ ++ .name = "vpu_0_div", ++ .ops = &clk_divider_ops, ++ .parent_names = (const char *[]){ "vpu_0_sel" }, ++ .num_parents = 1, ++ .flags = CLK_SET_RATE_PARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_gate gxbb_vpu_0 = { ++ .reg = (void *)HHI_VPU_CLK_CNTL, ++ .bit_idx = 8, ++ .lock = &clk_lock, ++ .hw.init = &(struct clk_init_data) { ++ .name = "vpu_0", ++ .ops = &clk_gate_ops, ++ .parent_names = (const char *[]){ "vpu_0_div" }, ++ .num_parents = 1, ++ .flags = CLK_SET_RATE_PARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_mux gxbb_vpu_1_sel = { ++ .reg = (void *)HHI_VPU_CLK_CNTL, ++ .mask = 0x3, ++ .shift = 25, ++ .lock = &clk_lock, ++ .table = mux_table_vpu, ++ .hw.init = &(struct clk_init_data){ ++ .name = "vpu_1_sel", ++ .ops = &clk_mux_ops, ++ /* ++ * bits 25:26 selects from 4 possible parents: ++ * fclk_div4, fclk_div3, fclk_div5, fclk_div7, ++ */ ++ .parent_names = gxbb_vpu_parent_names, ++ .num_parents = ARRAY_SIZE(gxbb_vpu_parent_names), ++ .flags = CLK_SET_RATE_NO_REPARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_divider gxbb_vpu_1_div = { ++ .reg = (void *)HHI_VPU_CLK_CNTL, ++ .shift = 16, ++ .width = 7, ++ .lock = &clk_lock, ++ .hw.init = &(struct clk_init_data){ ++ .name = "vpu_1_div", ++ .ops = &clk_divider_ops, ++ .parent_names = (const char *[]){ "vpu_1_sel" }, ++ .num_parents = 1, ++ .flags = CLK_SET_RATE_PARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_gate gxbb_vpu_1 = { ++ .reg = (void *)HHI_VPU_CLK_CNTL, ++ .bit_idx = 24, ++ .lock = &clk_lock, ++ .hw.init = &(struct clk_init_data) { ++ .name = "vpu_1", ++ .ops = &clk_gate_ops, ++ .parent_names = (const char *[]){ "vpu_1_div" }, ++ .num_parents = 1, ++ .flags = CLK_SET_RATE_PARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_mux gxbb_vpu = { ++ .reg = (void *)HHI_VPU_CLK_CNTL, ++ .mask = 1, ++ .shift = 31, ++ .lock = &clk_lock, ++ .hw.init = &(struct clk_init_data){ ++ .name = "vpu", ++ .ops = &clk_mux_ops, ++ /* ++ * bit 31 selects from 2 possible parents: ++ * vpu_0 or vpu_1 ++ */ ++ .parent_names = (const char *[]){ "vpu_0", "vpu_1" }, ++ .num_parents = 2, ++ .flags = CLK_SET_RATE_NO_REPARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++/* VAPB Clock */ ++ ++static u32 mux_table_vapb[] = {0, 1, 2, 3}; ++static const char * const gxbb_vapb_parent_names[] = { ++ "fclk_div4", "fclk_div3", "fclk_div5", "fclk_div7" ++}; ++ ++static struct clk_mux gxbb_vapb_0_sel = { ++ .reg = (void *)HHI_VAPBCLK_CNTL, ++ .mask = 0x3, ++ .shift = 9, ++ .lock = &clk_lock, ++ .table = mux_table_vapb, ++ .hw.init = &(struct clk_init_data){ ++ .name = "vapb_0_sel", ++ .ops = &clk_mux_ops, ++ /* ++ * bits 9:10 selects from 4 possible parents: ++ * fclk_div4, fclk_div3, fclk_div5, fclk_div7, ++ */ ++ .parent_names = gxbb_vapb_parent_names, ++ .num_parents = ARRAY_SIZE(gxbb_vapb_parent_names), ++ .flags = CLK_SET_RATE_NO_REPARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_divider gxbb_vapb_0_div = { ++ .reg = (void *)HHI_VAPBCLK_CNTL, ++ .shift = 0, ++ .width = 7, ++ .lock = &clk_lock, ++ .hw.init = &(struct clk_init_data){ ++ .name = "vapb_0_div", ++ .ops = &clk_divider_ops, ++ .parent_names = (const char *[]){ "vapb_0_sel" }, ++ .num_parents = 1, ++ .flags = CLK_SET_RATE_PARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_gate gxbb_vapb_0 = { ++ .reg = (void *)HHI_VAPBCLK_CNTL, ++ .bit_idx = 8, ++ .lock = &clk_lock, ++ .hw.init = &(struct clk_init_data) { ++ .name = "vapb_0", ++ .ops = &clk_gate_ops, ++ .parent_names = (const char *[]){ "vapb_0_div" }, ++ .num_parents = 1, ++ .flags = CLK_SET_RATE_PARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_mux gxbb_vapb_1_sel = { ++ .reg = (void *)HHI_VAPBCLK_CNTL, ++ .mask = 0x3, ++ .shift = 25, ++ .lock = &clk_lock, ++ .table = mux_table_vapb, ++ .hw.init = &(struct clk_init_data){ ++ .name = "vapb_1_sel", ++ .ops = &clk_mux_ops, ++ /* ++ * bits 25:26 selects from 4 possible parents: ++ * fclk_div4, fclk_div3, fclk_div5, fclk_div7, ++ */ ++ .parent_names = gxbb_vapb_parent_names, ++ .num_parents = ARRAY_SIZE(gxbb_vapb_parent_names), ++ .flags = CLK_SET_RATE_NO_REPARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_divider gxbb_vapb_1_div = { ++ .reg = (void *)HHI_VAPBCLK_CNTL, ++ .shift = 16, ++ .width = 7, ++ .lock = &clk_lock, ++ .hw.init = &(struct clk_init_data){ ++ .name = "vapb_1_div", ++ .ops = &clk_divider_ops, ++ .parent_names = (const char *[]){ "vapb_1_sel" }, ++ .num_parents = 1, ++ .flags = CLK_SET_RATE_PARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_gate gxbb_vapb_1 = { ++ .reg = (void *)HHI_VAPBCLK_CNTL, ++ .bit_idx = 24, ++ .lock = &clk_lock, ++ .hw.init = &(struct clk_init_data) { ++ .name = "vapb_1", ++ .ops = &clk_gate_ops, ++ .parent_names = (const char *[]){ "vapb_1_div" }, ++ .num_parents = 1, ++ .flags = CLK_SET_RATE_PARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_mux gxbb_vapb_sel = { ++ .reg = (void *)HHI_VAPBCLK_CNTL, ++ .mask = 1, ++ .shift = 31, ++ .lock = &clk_lock, ++ .hw.init = &(struct clk_init_data){ ++ .name = "vapb_sel", ++ .ops = &clk_mux_ops, ++ /* ++ * bit 31 selects from 2 possible parents: ++ * vapb_0 or vapb_1 ++ */ ++ .parent_names = (const char *[]){ "vapb_0", "vapb_1" }, ++ .num_parents = 2, ++ .flags = CLK_SET_RATE_NO_REPARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ ++static struct clk_gate gxbb_vapb = { ++ .reg = (void *)HHI_VAPBCLK_CNTL, ++ .bit_idx = 30, ++ .lock = &clk_lock, ++ .hw.init = &(struct clk_init_data) { ++ .name = "vapb", ++ .ops = &clk_gate_ops, ++ .parent_names = (const char *[]){ "vapb_sel" }, ++ .num_parents = 1, ++ .flags = CLK_SET_RATE_PARENT | CLK_IGNORE_UNUSED, ++ }, ++}; ++ + /* Everything Else (EE) domain gates */ + static MESON_GATE(gxbb_ddr, HHI_GCLK_MPEG0, 0); + static MESON_GATE(gxbb_dos, HHI_GCLK_MPEG0, 1); +@@ -1349,6 +1596,21 @@ static struct clk_hw_onecell_data gxbb_hw_onecell_data = { + [CLKID_SD_EMMC_C_CLK0_SEL] = &gxbb_sd_emmc_c_clk0_sel.hw, + [CLKID_SD_EMMC_C_CLK0_DIV] = &gxbb_sd_emmc_c_clk0_div.hw, + [CLKID_SD_EMMC_C_CLK0] = &gxbb_sd_emmc_c_clk0.hw, ++ [CLKID_VPU_0_SEL] = &gxbb_vpu_0_sel.hw, ++ [CLKID_VPU_0_DIV] = &gxbb_vpu_0_div.hw, ++ [CLKID_VPU_0] = &gxbb_vpu_0.hw, ++ [CLKID_VPU_1_SEL] = &gxbb_vpu_1_sel.hw, ++ [CLKID_VPU_1_DIV] = &gxbb_vpu_1_div.hw, ++ [CLKID_VPU_1] = &gxbb_vpu_1.hw, ++ [CLKID_VPU] = &gxbb_vpu.hw, ++ [CLKID_VAPB_0_SEL] = &gxbb_vapb_0_sel.hw, ++ [CLKID_VAPB_0_DIV] = &gxbb_vapb_0_div.hw, ++ [CLKID_VAPB_0] = &gxbb_vapb_0.hw, ++ [CLKID_VAPB_1_SEL] = &gxbb_vapb_1_sel.hw, ++ [CLKID_VAPB_1_DIV] = &gxbb_vapb_1_div.hw, ++ [CLKID_VAPB_1] = &gxbb_vapb_1.hw, ++ [CLKID_VAPB_SEL] = &gxbb_vapb_sel.hw, ++ [CLKID_VAPB] = &gxbb_vapb.hw, + [NR_CLKS] = NULL, + }, + .num = NR_CLKS, +@@ -1481,6 +1743,21 @@ static struct clk_hw_onecell_data gxl_hw_onecell_data = { + [CLKID_SD_EMMC_C_CLK0_SEL] = &gxbb_sd_emmc_c_clk0_sel.hw, + [CLKID_SD_EMMC_C_CLK0_DIV] = &gxbb_sd_emmc_c_clk0_div.hw, + [CLKID_SD_EMMC_C_CLK0] = &gxbb_sd_emmc_c_clk0.hw, ++ [CLKID_VPU_0_SEL] = &gxbb_vpu_0_sel.hw, ++ [CLKID_VPU_0_DIV] = &gxbb_vpu_0_div.hw, ++ [CLKID_VPU_0] = &gxbb_vpu_0.hw, ++ [CLKID_VPU_1_SEL] = &gxbb_vpu_1_sel.hw, ++ [CLKID_VPU_1_DIV] = &gxbb_vpu_1_div.hw, ++ [CLKID_VPU_1] = &gxbb_vpu_1.hw, ++ [CLKID_VPU] = &gxbb_vpu.hw, ++ [CLKID_VAPB_0_SEL] = &gxbb_vapb_0_sel.hw, ++ [CLKID_VAPB_0_DIV] = &gxbb_vapb_0_div.hw, ++ [CLKID_VAPB_0] = &gxbb_vapb_0.hw, ++ [CLKID_VAPB_1_SEL] = &gxbb_vapb_1_sel.hw, ++ [CLKID_VAPB_1_DIV] = &gxbb_vapb_1_div.hw, ++ [CLKID_VAPB_1] = &gxbb_vapb_1.hw, ++ [CLKID_VAPB_SEL] = &gxbb_vapb_sel.hw, ++ [CLKID_VAPB] = &gxbb_vapb.hw, + [NR_CLKS] = NULL, + }, + .num = NR_CLKS, +@@ -1600,6 +1877,11 @@ static struct clk_gate *const gxbb_clk_gates[] = { + &gxbb_sd_emmc_a_clk0, + &gxbb_sd_emmc_b_clk0, + &gxbb_sd_emmc_c_clk0, ++ &gxbb_vpu_0, ++ &gxbb_vpu_1, ++ &gxbb_vapb_0, ++ &gxbb_vapb_1, ++ &gxbb_vapb, + }; + + static struct clk_mux *const gxbb_clk_muxes[] = { +@@ -1615,6 +1897,12 @@ static struct clk_mux *const gxbb_clk_muxes[] = { + &gxbb_sd_emmc_a_clk0_sel, + &gxbb_sd_emmc_b_clk0_sel, + &gxbb_sd_emmc_c_clk0_sel, ++ &gxbb_vpu_0_sel, ++ &gxbb_vpu_1_sel, ++ &gxbb_vpu, ++ &gxbb_vapb_0_sel, ++ &gxbb_vapb_1_sel, ++ &gxbb_vapb_sel, + }; + + static struct clk_divider *const gxbb_clk_dividers[] = { +@@ -1627,6 +1915,10 @@ static struct clk_divider *const gxbb_clk_dividers[] = { + &gxbb_sd_emmc_a_clk0_div, + &gxbb_sd_emmc_b_clk0_div, + &gxbb_sd_emmc_c_clk0_div, ++ &gxbb_vpu_0_div, ++ &gxbb_vpu_1_div, ++ &gxbb_vapb_0_div, ++ &gxbb_vapb_1_div, + }; + + static struct meson_clk_audio_divider *const gxbb_audio_dividers[] = { +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0016-drm-meson-dw_hdmi-Add-support-for-an-optional-extern.patch b/patch/kernel/meson64-dev/0016-drm-meson-dw_hdmi-Add-support-for-an-optional-extern.patch new file mode 100644 index 0000000000..e722b9eccf --- /dev/null +++ b/patch/kernel/meson64-dev/0016-drm-meson-dw_hdmi-Add-support-for-an-optional-extern.patch @@ -0,0 +1,56 @@ +From 4c9cc11e8b99da324f977a25f2d556e9cc3b7633 Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Mon, 16 Oct 2017 15:35:00 +0200 +Subject: [PATCH 16/36] drm/meson: dw_hdmi: Add support for an optional + external 5V regulator + +On reference boards and derivatives, the HDMI Logic is powered by an external +5V regulator. +This regulator was set by the Vendor U-Boot, add optional support for it. + +Signed-off-by: Neil Armstrong +--- + drivers/gpu/drm/meson/meson_dw_hdmi.c | 13 +++++++++++++ + 1 file changed, 13 insertions(+) + +diff --git a/drivers/gpu/drm/meson/meson_dw_hdmi.c b/drivers/gpu/drm/meson/meson_dw_hdmi.c +index cef4144..17de3af 100644 +--- a/drivers/gpu/drm/meson/meson_dw_hdmi.c ++++ b/drivers/gpu/drm/meson/meson_dw_hdmi.c +@@ -23,6 +23,7 @@ + #include + #include + #include ++#include + + #include + #include +@@ -137,6 +138,7 @@ struct meson_dw_hdmi { + struct reset_control *hdmitx_phy; + struct clk *hdmi_pclk; + struct clk *venci_clk; ++ struct regulator *hdmi_supply; + u32 irq_stat; + }; + #define encoder_to_meson_dw_hdmi(x) \ +@@ -751,6 +753,17 @@ static int meson_dw_hdmi_bind(struct device *dev, struct device *master, + dw_plat_data = &meson_dw_hdmi->dw_plat_data; + encoder = &meson_dw_hdmi->encoder; + ++ meson_dw_hdmi->hdmi_supply = devm_regulator_get_optional(dev, "hdmi"); ++ if (IS_ERR(meson_dw_hdmi->hdmi_supply)) { ++ if (PTR_ERR(meson_dw_hdmi->hdmi_supply) == -EPROBE_DEFER) ++ return -EPROBE_DEFER; ++ meson_dw_hdmi->hdmi_supply = NULL; ++ } else { ++ ret = regulator_enable(meson_dw_hdmi->hdmi_supply); ++ if (ret) ++ return ret; ++ } ++ + meson_dw_hdmi->hdmitx_apb = devm_reset_control_get_exclusive(dev, + "hdmitx_apb"); + if (IS_ERR(meson_dw_hdmi->hdmitx_apb)) { +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0017-drm-meson-Add-missing-VPU-init.patch b/patch/kernel/meson64-dev/0017-drm-meson-Add-missing-VPU-init.patch new file mode 100644 index 0000000000..7b3b4bd1ca --- /dev/null +++ b/patch/kernel/meson64-dev/0017-drm-meson-Add-missing-VPU-init.patch @@ -0,0 +1,58 @@ +From 7ce5f752df490a622f7b60b119deb78fe06aa89c Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Mon, 16 Oct 2017 15:34:21 +0200 +Subject: [PATCH 17/36] drm/meson: Add missing VPU init + +The VPU init misses these configurations values. + +Signed-off-by: Neil Armstrong +--- + drivers/gpu/drm/meson/meson_drv.c | 9 +++++++++ + drivers/gpu/drm/meson/meson_registers.h | 4 ++++ + 2 files changed, 13 insertions(+) + +diff --git a/drivers/gpu/drm/meson/meson_drv.c b/drivers/gpu/drm/meson/meson_drv.c +index 7742c7d..19a0d8d 100644 +--- a/drivers/gpu/drm/meson/meson_drv.c ++++ b/drivers/gpu/drm/meson/meson_drv.c +@@ -150,6 +150,14 @@ static struct regmap_config meson_regmap_config = { + .max_register = 0x1000, + }; + ++static void meson_vpu_init(struct meson_drm *priv) ++{ ++ writel_relaxed(0x210000, priv->io_base + _REG(VPU_RDARB_MODE_L1C1)); ++ writel_relaxed(0x10000, priv->io_base + _REG(VPU_RDARB_MODE_L1C2)); ++ writel_relaxed(0x900000, priv->io_base + _REG(VPU_RDARB_MODE_L2C1)); ++ writel_relaxed(0x20000, priv->io_base + _REG(VPU_WRARB_MODE_L2C1)); ++} ++ + static int meson_drv_bind_master(struct device *dev, bool has_components) + { + struct platform_device *pdev = to_platform_device(dev); +@@ -221,6 +229,7 @@ static int meson_drv_bind_master(struct device *dev, bool has_components) + + /* Hardware Initialization */ + ++ meson_vpu_init(priv); + meson_venc_init(priv); + meson_vpp_init(priv); + meson_viu_init(priv); +diff --git a/drivers/gpu/drm/meson/meson_registers.h b/drivers/gpu/drm/meson/meson_registers.h +index 2847381..bca8714 100644 +--- a/drivers/gpu/drm/meson/meson_registers.h ++++ b/drivers/gpu/drm/meson/meson_registers.h +@@ -1363,6 +1363,10 @@ + #define VPU_PROT3_STAT_1 0x277a + #define VPU_PROT3_STAT_2 0x277b + #define VPU_PROT3_REQ_ONOFF 0x277c ++#define VPU_RDARB_MODE_L1C1 0x2790 ++#define VPU_RDARB_MODE_L1C2 0x2799 ++#define VPU_RDARB_MODE_L2C1 0x279d ++#define VPU_WRARB_MODE_L2C1 0x27a2 + + /* osd super scale */ + #define OSDSR_HV_SIZEIN 0x3130 +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0018-reset-meson-add-level-reset-support-for-GX-SoC-famil.patch b/patch/kernel/meson64-dev/0018-reset-meson-add-level-reset-support-for-GX-SoC-famil.patch new file mode 100644 index 0000000000..f302e89e03 --- /dev/null +++ b/patch/kernel/meson64-dev/0018-reset-meson-add-level-reset-support-for-GX-SoC-famil.patch @@ -0,0 +1,132 @@ +From 434a32bab28ccf277229338b33849b24ace9cc35 Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Fri, 13 Oct 2017 14:05:01 +0200 +Subject: [PATCH 18/36] reset: meson: add level reset support for GX SoC family + +The Amlogic GX SoC family embeds alternate registers to drive the reset +levels next to the pulse registers. + +This patch adds support for level reset handling on the GX family only. + +The Meson8 family has an alternate way to handle level reset. + +Signed-off-by: Neil Armstrong +--- + drivers/reset/reset-meson.c | 62 ++++++++++++++++++++++++++++++++++++++++++--- + 1 file changed, 58 insertions(+), 4 deletions(-) + +diff --git a/drivers/reset/reset-meson.c b/drivers/reset/reset-meson.c +index a8b915e..f3b9d69 100644 +--- a/drivers/reset/reset-meson.c ++++ b/drivers/reset/reset-meson.c +@@ -62,13 +62,16 @@ + #include + #include + #include ++#include + + #define REG_COUNT 8 + #define BITS_PER_REG 32 ++#define LEVEL_OFFSET 0x7c + + struct meson_reset { + void __iomem *reg_base; + struct reset_controller_dev rcdev; ++ spinlock_t lock; + }; + + static int meson_reset_reset(struct reset_controller_dev *rcdev, +@@ -88,18 +91,63 @@ static int meson_reset_reset(struct reset_controller_dev *rcdev, + return 0; + } + +-static const struct reset_control_ops meson_reset_ops = { ++static int meson_reset_level(struct reset_controller_dev *rcdev, ++ unsigned long id, bool assert) ++{ ++ struct meson_reset *data = ++ container_of(rcdev, struct meson_reset, rcdev); ++ unsigned int bank = id / BITS_PER_REG; ++ unsigned int offset = id % BITS_PER_REG; ++ void __iomem *reg_addr = data->reg_base + LEVEL_OFFSET + (bank << 2); ++ unsigned long flags; ++ u32 reg; ++ ++ spin_lock_irqsave(&data->lock, flags); ++ ++ reg = readl(reg_addr); ++ if (assert) ++ writel(reg & ~BIT(offset), reg_addr); ++ else ++ writel(reg | BIT(offset), reg_addr); ++ ++ spin_unlock_irqrestore(&data->lock, flags); ++ ++ return 0; ++} ++ ++static int meson_reset_assert(struct reset_controller_dev *rcdev, ++ unsigned long id) ++{ ++ return meson_reset_level(rcdev, id, true); ++} ++ ++static int meson_reset_deassert(struct reset_controller_dev *rcdev, ++ unsigned long id) ++{ ++ return meson_reset_level(rcdev, id, false); ++} ++ ++static const struct reset_control_ops meson_reset_meson8_ops = { + .reset = meson_reset_reset, + }; + ++static const struct reset_control_ops meson_reset_gx_ops = { ++ .reset = meson_reset_reset, ++ .assert = meson_reset_assert, ++ .deassert = meson_reset_deassert, ++}; ++ + static const struct of_device_id meson_reset_dt_ids[] = { +- { .compatible = "amlogic,meson8b-reset", }, +- { .compatible = "amlogic,meson-gxbb-reset", }, ++ { .compatible = "amlogic,meson8b-reset", ++ .data = &meson_reset_meson8_ops, }, ++ { .compatible = "amlogic,meson-gxbb-reset", ++ .data = &meson_reset_gx_ops, }, + { /* sentinel */ }, + }; + + static int meson_reset_probe(struct platform_device *pdev) + { ++ const struct reset_control_ops *ops; + struct meson_reset *data; + struct resource *res; + +@@ -107,6 +155,10 @@ static int meson_reset_probe(struct platform_device *pdev) + if (!data) + return -ENOMEM; + ++ ops = of_device_get_match_data(&pdev->dev); ++ if (!ops) ++ return -EINVAL; ++ + res = platform_get_resource(pdev, IORESOURCE_MEM, 0); + data->reg_base = devm_ioremap_resource(&pdev->dev, res); + if (IS_ERR(data->reg_base)) +@@ -114,9 +166,11 @@ static int meson_reset_probe(struct platform_device *pdev) + + platform_set_drvdata(pdev, data); + ++ spin_lock_init(&data->lock); ++ + data->rcdev.owner = THIS_MODULE; + data->rcdev.nr_resets = REG_COUNT * BITS_PER_REG; +- data->rcdev.ops = &meson_reset_ops; ++ data->rcdev.ops = ops; + data->rcdev.of_node = pdev->dev.of_node; + + return devm_reset_controller_register(&pdev->dev, &data->rcdev); +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0019-soc-amlogic-add-Meson-GX-VPU-Domains-driver.patch b/patch/kernel/meson64-dev/0019-soc-amlogic-add-Meson-GX-VPU-Domains-driver.patch new file mode 100644 index 0000000000..413f1feba2 --- /dev/null +++ b/patch/kernel/meson64-dev/0019-soc-amlogic-add-Meson-GX-VPU-Domains-driver.patch @@ -0,0 +1,286 @@ +From 375dd688f29cc0e8da629b3896c86c7e263030ae Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Fri, 13 Oct 2017 17:05:00 +0200 +Subject: [PATCH 19/36] soc: amlogic: add Meson GX VPU Domains driver + +The Video Processing Unit needs a specific Power Domain powering scheme +this driver handles this as a PM Power Domain driver. + +Signed-off-by: Neil Armstrong +--- + drivers/soc/amlogic/Kconfig | 10 ++ + drivers/soc/amlogic/Makefile | 1 + + drivers/soc/amlogic/meson-gx-pwrc-vpu.c | 234 ++++++++++++++++++++++++++++++++ + 3 files changed, 245 insertions(+) + create mode 100644 drivers/soc/amlogic/meson-gx-pwrc-vpu.c + +diff --git a/drivers/soc/amlogic/Kconfig b/drivers/soc/amlogic/Kconfig +index 22acf06..c2c0513 100644 +--- a/drivers/soc/amlogic/Kconfig ++++ b/drivers/soc/amlogic/Kconfig +@@ -8,5 +8,15 @@ config MESON_GX_SOCINFO + help + Say yes to support decoding of Amlogic Meson GX SoC family + information about the type, package and version. ++ ++config MESON_GX_PM_DOMAINS ++ bool "Amlogic Meson GX Power Domains driver" ++ depends on ARCH_MESON || COMPILE_TEST ++ default ARCH_MESON ++ select PM_GENERIC_DOMAINS ++ select PM_GENERIC_DOMAINS_OF ++ help ++ Say yes to expose Amlogic Meson GX Power Domains as ++ Generic Power Domains. + + endmenu +diff --git a/drivers/soc/amlogic/Makefile b/drivers/soc/amlogic/Makefile +index 3e85fc4..3174e93 100644 +--- a/drivers/soc/amlogic/Makefile ++++ b/drivers/soc/amlogic/Makefile +@@ -1 +1,2 @@ + obj-$(CONFIG_MESON_GX_SOCINFO) += meson-gx-socinfo.o ++obj-$(CONFIG_MESON_GX_PM_DOMAINS) += meson-gx-pwrc-vpu.o +diff --git a/drivers/soc/amlogic/meson-gx-pwrc-vpu.c b/drivers/soc/amlogic/meson-gx-pwrc-vpu.c +new file mode 100644 +index 0000000..bf5190b +--- /dev/null ++++ b/drivers/soc/amlogic/meson-gx-pwrc-vpu.c +@@ -0,0 +1,234 @@ ++/* ++ * Copyright (c) 2017 BayLibre, SAS ++ * Author: Neil Armstrong ++ * ++ * SPDX-License-Identifier: GPL-2.0+ ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++/* AO Offsets */ ++ ++#define AO_RTI_GEN_PWR_SLEEP0 (0x3a << 2) ++ ++#define GEN_PWR_VPU_HDMI BIT(8) ++#define GEN_PWR_VPU_HDMI_ISO BIT(9) ++ ++/* HHI Offsets */ ++ ++#define HHI_MEM_PD_REG0 (0x40 << 2) ++#define HHI_VPU_MEM_PD_REG0 (0x41 << 2) ++#define HHI_VPU_MEM_PD_REG1 (0x42 << 2) ++ ++struct meson_gx_pwrc_vpu { ++ struct generic_pm_domain genpd; ++ struct regmap *regmap_ao; ++ struct regmap *regmap_hhi; ++ struct reset_control *rstc; ++ struct clk *vpu_clk; ++ struct clk *vapb_clk; ++ bool powered; ++}; ++ ++static inline ++struct meson_gx_pwrc_vpu *genpd_to_pd(struct generic_pm_domain *d) ++{ ++ return container_of(d, struct meson_gx_pwrc_vpu, genpd); ++} ++ ++static int meson_gx_pwrc_vpu_power_off(struct generic_pm_domain *genpd) ++{ ++ struct meson_gx_pwrc_vpu *pd = genpd_to_pd(genpd); ++ int i; ++ ++ regmap_update_bits(pd->regmap_ao, AO_RTI_GEN_PWR_SLEEP0, ++ GEN_PWR_VPU_HDMI_ISO, GEN_PWR_VPU_HDMI_ISO); ++ udelay(20); ++ ++ /* Power Down Memories */ ++ for (i = 0; i < 32; i += 2) { ++ regmap_update_bits(pd->regmap_hhi, HHI_VPU_MEM_PD_REG0, ++ 0x2 << i, 0x3 << i); ++ udelay(5); ++ } ++ for (i = 0; i < 32; i += 2) { ++ regmap_update_bits(pd->regmap_hhi, HHI_VPU_MEM_PD_REG1, ++ 0x2 << i, 0x3 << i); ++ udelay(5); ++ } ++ for (i = 8; i < 16; i++) { ++ regmap_update_bits(pd->regmap_hhi, HHI_MEM_PD_REG0, ++ BIT(i), BIT(i)); ++ udelay(5); ++ } ++ udelay(20); ++ ++ regmap_update_bits(pd->regmap_ao, AO_RTI_GEN_PWR_SLEEP0, ++ GEN_PWR_VPU_HDMI, GEN_PWR_VPU_HDMI); ++ ++ msleep(20); ++ ++ clk_disable_unprepare(pd->vpu_clk); ++ clk_disable_unprepare(pd->vapb_clk); ++ ++ pd->powered = false; ++ ++ return 0; ++} ++ ++static int meson_gx_pwrc_vpu_setup_clk(struct meson_gx_pwrc_vpu *pd) ++{ ++ int ret; ++ ++ ret = clk_prepare_enable(pd->vpu_clk); ++ if (ret) ++ return ret; ++ ++ return clk_prepare_enable(pd->vapb_clk); ++} ++ ++static int meson_gx_pwrc_vpu_power_on(struct generic_pm_domain *genpd) ++{ ++ struct meson_gx_pwrc_vpu *pd = genpd_to_pd(genpd); ++ int ret; ++ int i; ++ ++ regmap_update_bits(pd->regmap_ao, AO_RTI_GEN_PWR_SLEEP0, ++ GEN_PWR_VPU_HDMI, 0); ++ udelay(20); ++ ++ /* Power Up Memories */ ++ for (i = 0; i < 32; i += 2) { ++ regmap_update_bits(pd->regmap_hhi, HHI_VPU_MEM_PD_REG0, ++ 0x2 << i, 0); ++ udelay(5); ++ } ++ ++ for (i = 0; i < 32; i += 2) { ++ regmap_update_bits(pd->regmap_hhi, HHI_VPU_MEM_PD_REG1, ++ 0x2 << i, 0); ++ udelay(5); ++ } ++ ++ for (i = 8; i < 16; i++) { ++ regmap_update_bits(pd->regmap_hhi, HHI_MEM_PD_REG0, ++ BIT(i), 0); ++ udelay(5); ++ } ++ udelay(20); ++ ++ ret = reset_control_assert(pd->rstc); ++ if (ret) ++ return ret; ++ ++ regmap_update_bits(pd->regmap_ao, AO_RTI_GEN_PWR_SLEEP0, ++ GEN_PWR_VPU_HDMI_ISO, 0); ++ ++ ret = reset_control_deassert(pd->rstc); ++ if (ret) ++ return ret; ++ ++ ret = meson_gx_pwrc_vpu_setup_clk(pd); ++ if (ret) ++ return ret; ++ ++ pd->powered = true; ++ ++ return 0; ++} ++ ++static bool meson_gx_pwrc_vpu_get_power(struct meson_gx_pwrc_vpu *pd) ++{ ++ u32 reg; ++ ++ regmap_read(pd->regmap_ao, AO_RTI_GEN_PWR_SLEEP0, ®); ++ ++ return (reg & GEN_PWR_VPU_HDMI); ++} ++ ++static struct meson_gx_pwrc_vpu vpu_hdmi_pd = { ++ .genpd = { ++ .name = "vpu_hdmi", ++ .power_off = meson_gx_pwrc_vpu_power_off, ++ .power_on = meson_gx_pwrc_vpu_power_on, ++ }, ++}; ++ ++static int meson_gx_pwrc_vpu_probe(struct platform_device *pdev) ++{ ++ struct regmap *regmap_ao, *regmap_hhi; ++ struct reset_control *rstc; ++ struct clk *vpu_clk; ++ struct clk *vapb_clk; ++ ++ regmap_ao = syscon_node_to_regmap(of_get_parent(pdev->dev.of_node)); ++ if (IS_ERR(regmap_ao)) { ++ dev_err(&pdev->dev, "failed to get regmap\n"); ++ return PTR_ERR(regmap_ao); ++ } ++ ++ regmap_hhi = syscon_regmap_lookup_by_phandle(pdev->dev.of_node, ++ "amlogic,hhi-sysctrl"); ++ if (IS_ERR(regmap_hhi)) { ++ dev_err(&pdev->dev, "failed to get HHI regmap\n"); ++ return PTR_ERR(regmap_hhi); ++ } ++ ++ rstc = devm_reset_control_array_get(&pdev->dev, false, false); ++ if (IS_ERR(rstc)) { ++ dev_err(&pdev->dev, "failed to get reset lines\n"); ++ return PTR_ERR(rstc); ++ } ++ ++ vpu_clk = devm_clk_get(&pdev->dev, "vpu"); ++ if (IS_ERR(vpu_clk)) { ++ dev_err(&pdev->dev, "vpu clock request failed\n"); ++ return PTR_ERR(vpu_clk); ++ } ++ ++ vapb_clk = devm_clk_get(&pdev->dev, "vapb"); ++ if (IS_ERR(vapb_clk)) { ++ dev_err(&pdev->dev, "vapb clock request failed\n"); ++ return PTR_ERR(vapb_clk); ++ } ++ ++ vpu_hdmi_pd.regmap_ao = regmap_ao; ++ vpu_hdmi_pd.regmap_hhi = regmap_hhi; ++ vpu_hdmi_pd.rstc = rstc; ++ vpu_hdmi_pd.vpu_clk = vpu_clk; ++ vpu_hdmi_pd.vapb_clk = vapb_clk; ++ ++ pm_genpd_init(&vpu_hdmi_pd.genpd, &simple_qos_governor, ++ meson_gx_pwrc_vpu_get_power(&vpu_hdmi_pd)); ++ ++ return of_genpd_add_provider_simple(pdev->dev.of_node, ++ &vpu_hdmi_pd.genpd); ++} ++ ++static void meson_gx_pwrc_vpu_shutdown(struct platform_device *pdev) ++{ ++ if (vpu_hdmi_pd.powered) ++ meson_gx_pwrc_vpu_power_off(&vpu_hdmi_pd.genpd); ++} ++ ++static const struct of_device_id meson_gx_pwrc_vpu_match_table[] = { ++ { .compatible = "amlogic,meson-gx-pwrc-vpu" }, ++ { /* sentinel */ } ++}; ++ ++static struct platform_driver meson_gx_pwrc_vpu_driver = { ++ .probe = meson_gx_pwrc_vpu_probe, ++ .shutdown = meson_gx_pwrc_vpu_shutdown, ++ .driver = { ++ .name = "meson_gx_pwrc_vpu", ++ .of_match_table = meson_gx_pwrc_vpu_match_table, ++ }, ++}; ++builtin_platform_driver(meson_gx_pwrc_vpu_driver); +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0020-soc-amlogic-meson-gx-pwrc-vpu-fix-power-off-when-pow.patch b/patch/kernel/meson64-dev/0020-soc-amlogic-meson-gx-pwrc-vpu-fix-power-off-when-pow.patch new file mode 100644 index 0000000000..0ce3a27360 --- /dev/null +++ b/patch/kernel/meson64-dev/0020-soc-amlogic-meson-gx-pwrc-vpu-fix-power-off-when-pow.patch @@ -0,0 +1,105 @@ +From 6747193c223e945901f42d7e7bc1d3ddea663585 Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Fri, 3 Nov 2017 16:43:24 +0100 +Subject: [PATCH 20/36] soc: amlogic: meson-gx-pwrc-vpu: fix power-off when + powered by bootloader + +In the case the VPU power domain has been powered on by the bootloader +and no driver are attached to this power domain, the genpd will power it +off after a certain amount of time, but the clocks hasn't been enabled +by the kernel itself and the power-off will trigger some faults. +This patch enable the clocks to have a coherent state for an eventual +poweroff and switches to the pm_domain_always_on_gov governor. + +Fixes: 75fcb5ca4b46 ("soc: amlogic: add Meson GX VPU Domains driver") +Signed-off-by: Neil Armstrong +Tested-by: Kevin Hilman +--- + drivers/soc/amlogic/meson-gx-pwrc-vpu.c | 29 +++++++++++++++++++---------- + 1 file changed, 19 insertions(+), 10 deletions(-) + +diff --git a/drivers/soc/amlogic/meson-gx-pwrc-vpu.c b/drivers/soc/amlogic/meson-gx-pwrc-vpu.c +index bf5190b..2bdeebc 100644 +--- a/drivers/soc/amlogic/meson-gx-pwrc-vpu.c ++++ b/drivers/soc/amlogic/meson-gx-pwrc-vpu.c +@@ -34,7 +34,6 @@ struct meson_gx_pwrc_vpu { + struct reset_control *rstc; + struct clk *vpu_clk; + struct clk *vapb_clk; +- bool powered; + }; + + static inline +@@ -78,8 +77,6 @@ static int meson_gx_pwrc_vpu_power_off(struct generic_pm_domain *genpd) + clk_disable_unprepare(pd->vpu_clk); + clk_disable_unprepare(pd->vapb_clk); + +- pd->powered = false; +- + return 0; + } + +@@ -91,7 +88,11 @@ static int meson_gx_pwrc_vpu_setup_clk(struct meson_gx_pwrc_vpu *pd) + if (ret) + return ret; + +- return clk_prepare_enable(pd->vapb_clk); ++ ret = clk_prepare_enable(pd->vapb_clk); ++ if (ret) ++ clk_disable_unprepare(pd->vpu_clk); ++ ++ return ret; + } + + static int meson_gx_pwrc_vpu_power_on(struct generic_pm_domain *genpd) +@@ -139,8 +140,6 @@ static int meson_gx_pwrc_vpu_power_on(struct generic_pm_domain *genpd) + if (ret) + return ret; + +- pd->powered = true; +- + return 0; + } + +@@ -167,6 +166,8 @@ static int meson_gx_pwrc_vpu_probe(struct platform_device *pdev) + struct reset_control *rstc; + struct clk *vpu_clk; + struct clk *vapb_clk; ++ bool powered_off; ++ int ret; + + regmap_ao = syscon_node_to_regmap(of_get_parent(pdev->dev.of_node)); + if (IS_ERR(regmap_ao)) { +@@ -205,8 +206,17 @@ static int meson_gx_pwrc_vpu_probe(struct platform_device *pdev) + vpu_hdmi_pd.vpu_clk = vpu_clk; + vpu_hdmi_pd.vapb_clk = vapb_clk; + +- pm_genpd_init(&vpu_hdmi_pd.genpd, &simple_qos_governor, +- meson_gx_pwrc_vpu_get_power(&vpu_hdmi_pd)); ++ powered_off = meson_gx_pwrc_vpu_get_power(&vpu_hdmi_pd); ++ ++ /* If already powered, sync the clock states */ ++ if (!powered_off) { ++ ret = meson_gx_pwrc_vpu_setup_clk(&vpu_hdmi_pd); ++ if (ret) ++ return ret; ++ } ++ ++ pm_genpd_init(&vpu_hdmi_pd.genpd, &pm_domain_always_on_gov, ++ powered_off); + + return of_genpd_add_provider_simple(pdev->dev.of_node, + &vpu_hdmi_pd.genpd); +@@ -214,8 +224,7 @@ static int meson_gx_pwrc_vpu_probe(struct platform_device *pdev) + + static void meson_gx_pwrc_vpu_shutdown(struct platform_device *pdev) + { +- if (vpu_hdmi_pd.powered) +- meson_gx_pwrc_vpu_power_off(&vpu_hdmi_pd.genpd); ++ meson_gx_pwrc_vpu_power_off(&vpu_hdmi_pd.genpd); + } + + static const struct of_device_id meson_gx_pwrc_vpu_match_table[] = { +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0021-ASoC-meson-add-meson-audio-core-driver.patch b/patch/kernel/meson64-dev/0021-ASoC-meson-add-meson-audio-core-driver.patch new file mode 100644 index 0000000000..770c74f785 --- /dev/null +++ b/patch/kernel/meson64-dev/0021-ASoC-meson-add-meson-audio-core-driver.patch @@ -0,0 +1,312 @@ +From c22611fa1218870a469e9c107fd15782921294e4 Mon Sep 17 00:00:00 2001 +From: Jerome Brunet +Date: Thu, 30 Mar 2017 11:49:55 +0200 +Subject: [PATCH 21/36] ASoC: meson: add meson audio core driver + +This patch adds support for the audio core driver for the Amlogic Meson SoC +family. The purpose of this driver is to properly reset the audio block and +provide register access for the different devices scattered in this address +space. This includes output and input DMAs, pcm, i2s and spdif dai, card +level routing, internal codec for the gxl variant + +For more information, please refer to the section 5 of the public datasheet +of the S905 (gxbb). This datasheet is available here: [0]. + +[0]: http://dn.odroid.com/S905/DataSheet/S905_Public_Datasheet_V1.1.4.pdf + +Signed-off-by: Jerome Brunet +Signed-off-by: Neil Armstrong +--- + sound/soc/Kconfig | 1 + + sound/soc/Makefile | 1 + + sound/soc/meson/Kconfig | 9 ++ + sound/soc/meson/Makefile | 3 + + sound/soc/meson/audio-core.c | 190 +++++++++++++++++++++++++++++++++++++++++++ + sound/soc/meson/audio-core.h | 28 +++++++ + 6 files changed, 232 insertions(+) + create mode 100644 sound/soc/meson/Kconfig + create mode 100644 sound/soc/meson/Makefile + create mode 100644 sound/soc/meson/audio-core.c + create mode 100644 sound/soc/meson/audio-core.h + +diff --git a/sound/soc/Kconfig b/sound/soc/Kconfig +index c0abad2..7db316f 100644 +--- a/sound/soc/Kconfig ++++ b/sound/soc/Kconfig +@@ -55,6 +55,7 @@ source "sound/soc/kirkwood/Kconfig" + source "sound/soc/img/Kconfig" + source "sound/soc/intel/Kconfig" + source "sound/soc/mediatek/Kconfig" ++source "sound/soc/meson/Kconfig" + source "sound/soc/mxs/Kconfig" + source "sound/soc/pxa/Kconfig" + source "sound/soc/qcom/Kconfig" +diff --git a/sound/soc/Makefile b/sound/soc/Makefile +index bf8c1e2..d4c0a51 100644 +--- a/sound/soc/Makefile ++++ b/sound/soc/Makefile +@@ -33,6 +33,7 @@ obj-$(CONFIG_SND_SOC) += jz4740/ + obj-$(CONFIG_SND_SOC) += img/ + obj-$(CONFIG_SND_SOC) += intel/ + obj-$(CONFIG_SND_SOC) += mediatek/ ++obj-$(CONFIG_SND_SOC) += meson/ + obj-$(CONFIG_SND_SOC) += mxs/ + obj-$(CONFIG_SND_SOC) += nuc900/ + obj-$(CONFIG_SND_SOC) += omap/ +diff --git a/sound/soc/meson/Kconfig b/sound/soc/meson/Kconfig +new file mode 100644 +index 0000000..216c850 +--- /dev/null ++++ b/sound/soc/meson/Kconfig +@@ -0,0 +1,9 @@ ++menuconfig SND_SOC_MESON ++ tristate "ASoC support for Amlogic Meson SoCs" ++ depends on ARCH_MESON || COMPILE_TEST ++ select MFD_CORE ++ select REGMAP_MMIO ++ help ++ Say Y or M if you want to add support for codecs attached to ++ the Amlogic Meson SoCs Audio interfaces. You will also need to ++ select the audio interfaces to support below. +diff --git a/sound/soc/meson/Makefile b/sound/soc/meson/Makefile +new file mode 100644 +index 0000000..22028ab +--- /dev/null ++++ b/sound/soc/meson/Makefile +@@ -0,0 +1,3 @@ ++snd-soc-meson-audio-core-objs := audio-core.o ++ ++obj-$(CONFIG_SND_SOC_MESON) += snd-soc-meson-audio-core.o +diff --git a/sound/soc/meson/audio-core.c b/sound/soc/meson/audio-core.c +new file mode 100644 +index 0000000..99993ec +--- /dev/null ++++ b/sound/soc/meson/audio-core.c +@@ -0,0 +1,190 @@ ++/* ++ * Copyright (C) 2017 BayLibre, SAS ++ * Author: Jerome Brunet ++ * Copyright (C) 2017 Amlogic, Inc. All rights reserved. ++ * ++ * This program is free software; you can redistribute it and/or ++ * modify it under the terms of the GNU General Public License as ++ * published by the Free Software Foundation; either version 2 of the ++ * License, or (at your option) any later version. ++ * ++ * 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. ++ * ++ * You should have received a copy of the GNU General Public License ++ * along with this program; if not, see . ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include "audio-core.h" ++ ++#define DRV_NAME "meson-audio-core" ++ ++static const char * const acore_clock_names[] = { "aiu_top", ++ "aiu_glue", ++ "audin" }; ++ ++static int meson_acore_init_clocks(struct device *dev) ++{ ++ struct clk *clock; ++ int i, ret; ++ ++ for (i = 0; i < ARRAY_SIZE(acore_clock_names); i++) { ++ clock = devm_clk_get(dev, acore_clock_names[i]); ++ if (IS_ERR(clock)) { ++ if (PTR_ERR(clock) != -EPROBE_DEFER) ++ dev_err(dev, "Failed to get %s clock\n", ++ acore_clock_names[i]); ++ return PTR_ERR(clock); ++ } ++ ++ ret = clk_prepare_enable(clock); ++ if (ret) { ++ dev_err(dev, "Failed to enable %s clock\n", ++ acore_clock_names[i]); ++ return ret; ++ } ++ ++ ret = devm_add_action_or_reset(dev, ++ (void(*)(void *))clk_disable_unprepare, ++ clock); ++ if (ret) ++ return ret; ++ } ++ ++ return 0; ++} ++ ++static const char * const acore_reset_names[] = { "aiu", ++ "audin" }; ++ ++static int meson_acore_init_resets(struct device *dev) ++{ ++ struct reset_control *reset; ++ int i, ret; ++ ++ for (i = 0; i < ARRAY_SIZE(acore_reset_names); i++) { ++ reset = devm_reset_control_get_exclusive(dev, ++ acore_reset_names[i]); ++ if (IS_ERR(reset)) { ++ if (PTR_ERR(reset) != -EPROBE_DEFER) ++ dev_err(dev, "Failed to get %s reset\n", ++ acore_reset_names[i]); ++ return PTR_ERR(reset); ++ } ++ ++ ret = reset_control_reset(reset); ++ if (ret) { ++ dev_err(dev, "Failed to pulse %s reset\n", ++ acore_reset_names[i]); ++ return ret; ++ } ++ } ++ ++ return 0; ++} ++ ++static const struct regmap_config meson_acore_regmap_config = { ++ .reg_bits = 32, ++ .val_bits = 32, ++ .reg_stride = 4, ++}; ++ ++static const struct mfd_cell meson_acore_devs[] = { ++ { ++ .name = "meson-i2s-dai", ++ .of_compatible = "amlogic,meson-i2s-dai", ++ }, ++ { ++ .name = "meson-spdif-dai", ++ .of_compatible = "amlogic,meson-spdif-dai", ++ }, ++ { ++ .name = "meson-aiu-i2s-dma", ++ .of_compatible = "amlogic,meson-aiu-i2s-dma", ++ }, ++ { ++ .name = "meson-aiu-spdif-dma", ++ .of_compatible = "amlogic,meson-aiu-spdif-dma", ++ }, ++}; ++ ++static int meson_acore_probe(struct platform_device *pdev) ++{ ++ struct device *dev = &pdev->dev; ++ struct meson_audio_core_data *data; ++ struct resource *res; ++ void __iomem *regs; ++ int ret; ++ ++ data = devm_kzalloc(dev, sizeof(*data), GFP_KERNEL); ++ if (!data) ++ return -ENOMEM; ++ platform_set_drvdata(pdev, data); ++ ++ ret = meson_acore_init_clocks(dev); ++ if (ret) ++ return ret; ++ ++ ret = meson_acore_init_resets(dev); ++ if (ret) ++ return ret; ++ ++ res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "aiu"); ++ regs = devm_ioremap_resource(dev, res); ++ if (IS_ERR(regs)) ++ return PTR_ERR(regs); ++ ++ data->aiu = devm_regmap_init_mmio(dev, regs, ++ &meson_acore_regmap_config); ++ if (IS_ERR(data->aiu)) { ++ dev_err(dev, "Couldn't create the AIU regmap\n"); ++ return PTR_ERR(data->aiu); ++ } ++ ++ res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "audin"); ++ regs = devm_ioremap_resource(dev, res); ++ if (IS_ERR(regs)) ++ return PTR_ERR(regs); ++ ++ data->audin = devm_regmap_init_mmio(dev, regs, ++ &meson_acore_regmap_config); ++ if (IS_ERR(data->audin)) { ++ dev_err(dev, "Couldn't create the AUDIN regmap\n"); ++ return PTR_ERR(data->audin); ++ } ++ ++ return devm_mfd_add_devices(dev, PLATFORM_DEVID_AUTO, meson_acore_devs, ++ ARRAY_SIZE(meson_acore_devs), NULL, 0, ++ NULL); ++} ++ ++static const struct of_device_id meson_acore_of_match[] = { ++ { .compatible = "amlogic,meson-audio-core", }, ++ { .compatible = "amlogic,meson-gxbb-audio-core", }, ++ { .compatible = "amlogic,meson-gxl-audio-core", }, ++ {} ++}; ++MODULE_DEVICE_TABLE(of, meson_acore_of_match); ++ ++static struct platform_driver meson_acore_pdrv = { ++ .probe = meson_acore_probe, ++ .driver = { ++ .name = DRV_NAME, ++ .of_match_table = meson_acore_of_match, ++ }, ++}; ++module_platform_driver(meson_acore_pdrv); ++ ++MODULE_DESCRIPTION("Meson Audio Core Driver"); ++MODULE_AUTHOR("Jerome Brunet "); ++MODULE_LICENSE("GPL v2"); +diff --git a/sound/soc/meson/audio-core.h b/sound/soc/meson/audio-core.h +new file mode 100644 +index 0000000..6e7a24c +--- /dev/null ++++ b/sound/soc/meson/audio-core.h +@@ -0,0 +1,28 @@ ++/* ++ * Copyright (C) 2017 BayLibre, SAS ++ * Author: Jerome Brunet ++ * Copyright (C) 2017 Amlogic, Inc. All rights reserved. ++ * ++ * This program is free software; you can redistribute it and/or ++ * modify it under the terms of the GNU General Public License as ++ * published by the Free Software Foundation; either version 2 of the ++ * License, or (at your option) any later version. ++ * ++ * 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. ++ * ++ * You should have received a copy of the GNU General Public License ++ * along with this program; if not, see . ++ */ ++ ++#ifndef _MESON_AUDIO_CORE_H_ ++#define _MESON_AUDIO_CORE_H_ ++ ++struct meson_audio_core_data { ++ struct regmap *aiu; ++ struct regmap *audin; ++}; ++ ++#endif /* _MESON_AUDIO_CORE_H_ */ +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0022-ASoC-meson-add-register-definitions.patch b/patch/kernel/meson64-dev/0022-ASoC-meson-add-register-definitions.patch new file mode 100644 index 0000000000..b0c92e6983 --- /dev/null +++ b/patch/kernel/meson64-dev/0022-ASoC-meson-add-register-definitions.patch @@ -0,0 +1,361 @@ +From ee8202e5395cae89733d6a9957c55df50ce6ddbd Mon Sep 17 00:00:00 2001 +From: Jerome Brunet +Date: Thu, 30 Mar 2017 12:00:10 +0200 +Subject: [PATCH 22/36] ASoC: meson: add register definitions + +Add the register definition for the AIU and AUDIN blocks + +Signed-off-by: Jerome Brunet +Signed-off-by: Neil Armstrong +--- + sound/soc/meson/aiu-regs.h | 182 +++++++++++++++++++++++++++++++++++++++++++ + sound/soc/meson/audin-regs.h | 148 +++++++++++++++++++++++++++++++++++ + 2 files changed, 330 insertions(+) + create mode 100644 sound/soc/meson/aiu-regs.h + create mode 100644 sound/soc/meson/audin-regs.h + +diff --git a/sound/soc/meson/aiu-regs.h b/sound/soc/meson/aiu-regs.h +new file mode 100644 +index 0000000..67391e6 +--- /dev/null ++++ b/sound/soc/meson/aiu-regs.h +@@ -0,0 +1,182 @@ ++/* ++ * Copyright (C) 2017 BayLibre, SAS ++ * Author: Jerome Brunet ++ * Copyright (C) 2017 Amlogic, Inc. All rights reserved. ++ * ++ * This program is free software; you can redistribute it and/or ++ * modify it under the terms of the GNU General Public License as ++ * published by the Free Software Foundation; either version 2 of the ++ * License, or (at your option) any later version. ++ * ++ * 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. ++ * ++ * You should have received a copy of the GNU General Public License ++ * along with this program; if not, see . ++ */ ++ ++#ifndef _AIU_REGS_H_ ++#define _AIU_REGS_H_ ++ ++#define AIU_958_BPF 0x000 ++#define AIU_958_BRST 0x004 ++#define AIU_958_LENGTH 0x008 ++#define AIU_958_PADDSIZE 0x00C ++#define AIU_958_MISC 0x010 ++#define AIU_958_FORCE_LEFT 0x014 /* Unknown */ ++#define AIU_958_DISCARD_NUM 0x018 ++#define AIU_958_DCU_FF_CTRL 0x01C ++#define AIU_958_CHSTAT_L0 0x020 ++#define AIU_958_CHSTAT_L1 0x024 ++#define AIU_958_CTRL 0x028 ++#define AIU_958_RPT 0x02C ++#define AIU_I2S_MUTE_SWAP 0x030 ++#define AIU_I2S_SOURCE_DESC 0x034 ++#define AIU_I2S_MED_CTRL 0x038 ++#define AIU_I2S_MED_THRESH 0x03C ++#define AIU_I2S_DAC_CFG 0x040 ++#define AIU_I2S_SYNC 0x044 /* Unknown */ ++#define AIU_I2S_MISC 0x048 ++#define AIU_I2S_OUT_CFG 0x04C ++#define AIU_I2S_FF_CTRL 0x050 /* Unknown */ ++#define AIU_RST_SOFT 0x054 ++#define AIU_CLK_CTRL 0x058 ++#define AIU_MIX_ADCCFG 0x05C ++#define AIU_MIX_CTRL 0x060 ++#define AIU_CLK_CTRL_MORE 0x064 ++#define AIU_958_POP 0x068 ++#define AIU_MIX_GAIN 0x06C ++#define AIU_958_SYNWORD1 0x070 ++#define AIU_958_SYNWORD2 0x074 ++#define AIU_958_SYNWORD3 0x078 ++#define AIU_958_SYNWORD1_MASK 0x07C ++#define AIU_958_SYNWORD2_MASK 0x080 ++#define AIU_958_SYNWORD3_MASK 0x084 ++#define AIU_958_FFRDOUT_THD 0x088 ++#define AIU_958_LENGTH_PER_PAUSE 0x08C ++#define AIU_958_PAUSE_NUM 0x090 ++#define AIU_958_PAUSE_PAYLOAD 0x094 ++#define AIU_958_AUTO_PAUSE 0x098 ++#define AIU_958_PAUSE_PD_LENGTH 0x09C ++#define AIU_CODEC_DAC_LRCLK_CTRL 0x0A0 ++#define AIU_CODEC_ADC_LRCLK_CTRL 0x0A4 ++#define AIU_HDMI_CLK_DATA_CTRL 0x0A8 ++#define AIU_CODEC_CLK_DATA_CTRL 0x0AC ++#define AIU_ACODEC_CTRL 0x0B0 ++#define AIU_958_CHSTAT_R0 0x0C0 ++#define AIU_958_CHSTAT_R1 0x0C4 ++#define AIU_958_VALID_CTRL 0x0C8 ++#define AIU_AUDIO_AMP_REG0 0x0F0 /* Unknown */ ++#define AIU_AUDIO_AMP_REG1 0x0F4 /* Unknown */ ++#define AIU_AUDIO_AMP_REG2 0x0F8 /* Unknown */ ++#define AIU_AUDIO_AMP_REG3 0x0FC /* Unknown */ ++#define AIU_AIFIFO2_CTRL 0x100 ++#define AIU_AIFIFO2_STATUS 0x104 ++#define AIU_AIFIFO2_GBIT 0x108 ++#define AIU_AIFIFO2_CLB 0x10C ++#define AIU_CRC_CTRL 0x110 ++#define AIU_CRC_STATUS 0x114 ++#define AIU_CRC_SHIFT_REG 0x118 ++#define AIU_CRC_IREG 0x11C ++#define AIU_CRC_CAL_REG1 0x120 ++#define AIU_CRC_CAL_REG0 0x124 ++#define AIU_CRC_POLY_COEF1 0x128 ++#define AIU_CRC_POLY_COEF0 0x12C ++#define AIU_CRC_BIT_SIZE1 0x130 ++#define AIU_CRC_BIT_SIZE0 0x134 ++#define AIU_CRC_BIT_CNT1 0x138 ++#define AIU_CRC_BIT_CNT0 0x13C ++#define AIU_AMCLK_GATE_HI 0x140 ++#define AIU_AMCLK_GATE_LO 0x144 ++#define AIU_AMCLK_MSR 0x148 ++#define AIU_AUDAC_CTRL0 0x14C /* Unknown */ ++#define AIU_DELTA_SIGMA0 0x154 /* Unknown */ ++#define AIU_DELTA_SIGMA1 0x158 /* Unknown */ ++#define AIU_DELTA_SIGMA2 0x15C /* Unknown */ ++#define AIU_DELTA_SIGMA3 0x160 /* Unknown */ ++#define AIU_DELTA_SIGMA4 0x164 /* Unknown */ ++#define AIU_DELTA_SIGMA5 0x168 /* Unknown */ ++#define AIU_DELTA_SIGMA6 0x16C /* Unknown */ ++#define AIU_DELTA_SIGMA7 0x170 /* Unknown */ ++#define AIU_DELTA_SIGMA_LCNTS 0x174 /* Unknown */ ++#define AIU_DELTA_SIGMA_RCNTS 0x178 /* Unknown */ ++#define AIU_MEM_I2S_START_PTR 0x180 ++#define AIU_MEM_I2S_RD_PTR 0x184 ++#define AIU_MEM_I2S_END_PTR 0x188 ++#define AIU_MEM_I2S_MASKS 0x18C ++#define AIU_MEM_I2S_CONTROL 0x190 ++#define AIU_MEM_IEC958_START_PTR 0x194 ++#define AIU_MEM_IEC958_RD_PTR 0x198 ++#define AIU_MEM_IEC958_END_PTR 0x19C ++#define AIU_MEM_IEC958_MASKS 0x1A0 ++#define AIU_MEM_IEC958_CONTROL 0x1A4 ++#define AIU_MEM_AIFIFO2_START_PTR 0x1A8 ++#define AIU_MEM_AIFIFO2_CURR_PTR 0x1AC ++#define AIU_MEM_AIFIFO2_END_PTR 0x1B0 ++#define AIU_MEM_AIFIFO2_BYTES_AVAIL 0x1B4 ++#define AIU_MEM_AIFIFO2_CONTROL 0x1B8 ++#define AIU_MEM_AIFIFO2_MAN_WP 0x1BC ++#define AIU_MEM_AIFIFO2_MAN_RP 0x1C0 ++#define AIU_MEM_AIFIFO2_LEVEL 0x1C4 ++#define AIU_MEM_AIFIFO2_BUF_CNTL 0x1C8 ++#define AIU_MEM_I2S_MAN_WP 0x1CC ++#define AIU_MEM_I2S_MAN_RP 0x1D0 ++#define AIU_MEM_I2S_LEVEL 0x1D4 ++#define AIU_MEM_I2S_BUF_CNTL 0x1D8 ++#define AIU_MEM_I2S_BUF_WRAP_COUNT 0x1DC ++#define AIU_MEM_I2S_MEM_CTL 0x1E0 ++#define AIU_MEM_IEC958_MEM_CTL 0x1E4 ++#define AIU_MEM_IEC958_WRAP_COUNT 0x1E8 ++#define AIU_MEM_IEC958_IRQ_LEVEL 0x1EC ++#define AIU_MEM_IEC958_MAN_WP 0x1F0 ++#define AIU_MEM_IEC958_MAN_RP 0x1F4 ++#define AIU_MEM_IEC958_LEVEL 0x1F8 ++#define AIU_MEM_IEC958_BUF_CNTL 0x1FC ++#define AIU_AIFIFO_CTRL 0x200 ++#define AIU_AIFIFO_STATUS 0x204 ++#define AIU_AIFIFO_GBIT 0x208 ++#define AIU_AIFIFO_CLB 0x20C ++#define AIU_MEM_AIFIFO_START_PTR 0x210 ++#define AIU_MEM_AIFIFO_CURR_PTR 0x214 ++#define AIU_MEM_AIFIFO_END_PTR 0x218 ++#define AIU_MEM_AIFIFO_BYTES_AVAIL 0x21C ++#define AIU_MEM_AIFIFO_CONTROL 0x220 ++#define AIU_MEM_AIFIFO_MAN_WP 0x224 ++#define AIU_MEM_AIFIFO_MAN_RP 0x228 ++#define AIU_MEM_AIFIFO_LEVEL 0x22C ++#define AIU_MEM_AIFIFO_BUF_CNTL 0x230 ++#define AIU_MEM_AIFIFO_BUF_WRAP_COUNT 0x234 ++#define AIU_MEM_AIFIFO2_BUF_WRAP_COUNT 0x238 ++#define AIU_MEM_AIFIFO_MEM_CTL 0x23C ++#define AIFIFO_TIME_STAMP_CNTL 0x240 ++#define AIFIFO_TIME_STAMP_SYNC_0 0x244 ++#define AIFIFO_TIME_STAMP_SYNC_1 0x248 ++#define AIFIFO_TIME_STAMP_0 0x24C ++#define AIFIFO_TIME_STAMP_1 0x250 ++#define AIFIFO_TIME_STAMP_2 0x254 ++#define AIFIFO_TIME_STAMP_3 0x258 ++#define AIFIFO_TIME_STAMP_LENGTH 0x25C ++#define AIFIFO2_TIME_STAMP_CNTL 0x260 ++#define AIFIFO2_TIME_STAMP_SYNC_0 0x264 ++#define AIFIFO2_TIME_STAMP_SYNC_1 0x268 ++#define AIFIFO2_TIME_STAMP_0 0x26C ++#define AIFIFO2_TIME_STAMP_1 0x270 ++#define AIFIFO2_TIME_STAMP_2 0x274 ++#define AIFIFO2_TIME_STAMP_3 0x278 ++#define AIFIFO2_TIME_STAMP_LENGTH 0x27C ++#define IEC958_TIME_STAMP_CNTL 0x280 ++#define IEC958_TIME_STAMP_SYNC_0 0x284 ++#define IEC958_TIME_STAMP_SYNC_1 0x288 ++#define IEC958_TIME_STAMP_0 0x28C ++#define IEC958_TIME_STAMP_1 0x290 ++#define IEC958_TIME_STAMP_2 0x294 ++#define IEC958_TIME_STAMP_3 0x298 ++#define IEC958_TIME_STAMP_LENGTH 0x29C ++#define AIU_MEM_AIFIFO2_MEM_CTL 0x2A0 ++#define AIU_I2S_CBUS_DDR_CNTL 0x2A4 ++#define AIU_I2S_CBUS_DDR_WDATA 0x2A8 ++#define AIU_I2S_CBUS_DDR_ADDR 0x2AC ++ ++#endif /* _AIU_REGS_H_ */ +diff --git a/sound/soc/meson/audin-regs.h b/sound/soc/meson/audin-regs.h +new file mode 100644 +index 0000000..f224610 +--- /dev/null ++++ b/sound/soc/meson/audin-regs.h +@@ -0,0 +1,148 @@ ++/* ++ * Copyright (C) 2017 BayLibre, SAS ++ * Author: Jerome Brunet ++ * Copyright (C) 2017 Amlogic, Inc. All rights reserved. ++ * ++ * This program is free software; you can redistribute it and/or ++ * modify it under the terms of the GNU General Public License as ++ * published by the Free Software Foundation; either version 2 of the ++ * License, or (at your option) any later version. ++ * ++ * 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. ++ * ++ * You should have received a copy of the GNU General Public License ++ * along with this program; if not, see . ++ */ ++ ++#ifndef _AUDIN_REGS_H_ ++#define _AUDIN_REGS_H_ ++ ++/* ++ * Note : ++ * Datasheet issue page 196 ++ * AUDIN_MUTE_VAL 0x35 => impossible: Already assigned to AUDIN_FIFO1_PTR ++ * AUDIN_FIFO1_PTR is more likely to be correct here since surrounding registers ++ * also deal with AUDIN_FIFO1 ++ * ++ * Clarification needed from Amlogic ++ */ ++ ++#define AUDIN_SPDIF_MODE 0x000 ++#define AUDIN_SPDIF_FS_CLK_RLTN 0x004 ++#define AUDIN_SPDIF_CHNL_STS_A 0x008 ++#define AUDIN_SPDIF_CHNL_STS_B 0x00C ++#define AUDIN_SPDIF_MISC 0x010 ++#define AUDIN_SPDIF_NPCM_PCPD 0x014 ++#define AUDIN_SPDIF_END 0x03C /* Unknown */ ++#define AUDIN_I2SIN_CTRL 0x040 ++#define AUDIN_SOURCE_SEL 0x044 ++#define AUDIN_DECODE_FORMAT 0x048 ++#define AUDIN_DECODE_CONTROL_STATUS 0x04C ++#define AUDIN_DECODE_CHANNEL_STATUS_A_0 0x050 ++#define AUDIN_DECODE_CHANNEL_STATUS_A_1 0x054 ++#define AUDIN_DECODE_CHANNEL_STATUS_A_2 0x058 ++#define AUDIN_DECODE_CHANNEL_STATUS_A_3 0x05C ++#define AUDIN_DECODE_CHANNEL_STATUS_A_4 0x060 ++#define AUDIN_DECODE_CHANNEL_STATUS_A_5 0x064 ++#define AUDIN_FIFO0_START 0x080 ++#define AUDIN_FIFO0_END 0x084 ++#define AUDIN_FIFO0_PTR 0x088 ++#define AUDIN_FIFO0_INTR 0x08C ++#define AUDIN_FIFO0_RDPTR 0x090 ++#define AUDIN_FIFO0_CTRL 0x094 ++#define AUDIN_FIFO0_CTRL1 0x098 ++#define AUDIN_FIFO0_LVL0 0x09C ++#define AUDIN_FIFO0_LVL1 0x0A0 ++#define AUDIN_FIFO0_LVL2 0x0A4 ++#define AUDIN_FIFO0_REQID 0x0C0 ++#define AUDIN_FIFO0_WRAP 0x0C4 ++#define AUDIN_FIFO1_START 0x0CC ++#define AUDIN_FIFO1_END 0x0D0 ++#define AUDIN_FIFO1_PTR 0x0D4 ++#define AUDIN_FIFO1_INTR 0x0D8 ++#define AUDIN_FIFO1_RDPTR 0x0DC ++#define AUDIN_FIFO1_CTRL 0x0E0 ++#define AUDIN_FIFO1_CTRL1 0x0E4 ++#define AUDIN_FIFO1_LVL0 0x100 ++#define AUDIN_FIFO1_LVL1 0x104 ++#define AUDIN_FIFO1_LVL2 0x108 ++#define AUDIN_FIFO1_REQID 0x10C ++#define AUDIN_FIFO1_WRAP 0x110 ++#define AUDIN_FIFO2_START 0x114 ++#define AUDIN_FIFO2_END 0x118 ++#define AUDIN_FIFO2_PTR 0x11C ++#define AUDIN_FIFO2_INTR 0x120 ++#define AUDIN_FIFO2_RDPTR 0x124 ++#define AUDIN_FIFO2_CTRL 0x128 ++#define AUDIN_FIFO2_CTRL1 0x12C ++#define AUDIN_FIFO2_LVL0 0x130 ++#define AUDIN_FIFO2_LVL1 0x134 ++#define AUDIN_FIFO2_LVL2 0x138 ++#define AUDIN_FIFO2_REQID 0x13C ++#define AUDIN_FIFO2_WRAP 0x140 ++#define AUDIN_INT_CTRL 0x144 ++#define AUDIN_FIFO_INT 0x148 ++#define PCMIN_CTRL0 0x180 ++#define PCMIN_CTRL1 0x184 ++#define PCMIN1_CTRL0 0x188 ++#define PCMIN1_CTRL1 0x18C ++#define PCMOUT_CTRL0 0x1C0 ++#define PCMOUT_CTRL1 0x1C4 ++#define PCMOUT_CTRL2 0x1C8 ++#define PCMOUT_CTRL3 0x1CC ++#define PCMOUT1_CTRL0 0x1D0 ++#define PCMOUT1_CTRL1 0x1D4 ++#define PCMOUT1_CTRL2 0x1D8 ++#define PCMOUT1_CTRL3 0x1DC ++#define AUDOUT_CTRL 0x200 ++#define AUDOUT_CTRL1 0x204 ++#define AUDOUT_BUF0_STA 0x208 ++#define AUDOUT_BUF0_EDA 0x20C ++#define AUDOUT_BUF0_WPTR 0x210 ++#define AUDOUT_BUF1_STA 0x214 ++#define AUDOUT_BUF1_EDA 0x218 ++#define AUDOUT_BUF1_WPTR 0x21C ++#define AUDOUT_FIFO_RPTR 0x220 ++#define AUDOUT_INTR_PTR 0x224 ++#define AUDOUT_FIFO_STS 0x228 ++#define AUDOUT1_CTRL 0x240 ++#define AUDOUT1_CTRL1 0x244 ++#define AUDOUT1_BUF0_STA 0x248 ++#define AUDOUT1_BUF0_EDA 0x24C ++#define AUDOUT1_BUF0_WPTR 0x250 ++#define AUDOUT1_BUF1_STA 0x254 ++#define AUDOUT1_BUF1_EDA 0x258 ++#define AUDOUT1_BUF1_WPTR 0x25C ++#define AUDOUT1_FIFO_RPTR 0x260 ++#define AUDOUT1_INTR_PTR 0x264 ++#define AUDOUT1_FIFO_STS 0x268 ++#define AUDIN_HDMI_MEAS_CTRL 0x280 ++#define AUDIN_HDMI_MEAS_CYCLES_M1 0x284 ++#define AUDIN_HDMI_MEAS_INTR_MASKN 0x288 ++#define AUDIN_HDMI_MEAS_INTR_STAT 0x28C ++#define AUDIN_HDMI_REF_CYCLES_STAT_0 0x290 ++#define AUDIN_HDMI_REF_CYCLES_STAT_1 0x294 ++#define AUDIN_HDMIRX_AFIFO_STAT 0x298 ++#define AUDIN_FIFO0_PIO_STS 0x2C0 ++#define AUDIN_FIFO0_PIO_RDL 0x2C4 ++#define AUDIN_FIFO0_PIO_RDH 0x2C8 ++#define AUDIN_FIFO1_PIO_STS 0x2CC ++#define AUDIN_FIFO1_PIO_RDL 0x2D0 ++#define AUDIN_FIFO1_PIO_RDH 0x2D4 ++#define AUDIN_FIFO2_PIO_STS 0x2D8 ++#define AUDIN_FIFO2_PIO_RDL 0x2DC ++#define AUDIN_FIFO2_PIO_RDH 0x2E0 ++#define AUDOUT_FIFO_PIO_STS 0x2E4 ++#define AUDOUT_FIFO_PIO_WRL 0x2E8 ++#define AUDOUT_FIFO_PIO_WRH 0x2EC ++#define AUDOUT1_FIFO_PIO_STS 0x2F0 /* Unknown */ ++#define AUDOUT1_FIFO_PIO_WRL 0x2F4 /* Unknown */ ++#define AUDOUT1_FIFO_PIO_WRH 0x2F8 /* Unknown */ ++#define AUD_RESAMPLE_CTRL0 0x2FC ++#define AUD_RESAMPLE_CTRL1 0x300 ++#define AUD_RESAMPLE_STATUS 0x304 ++ ++#endif /* _AUDIN_REGS_H_ */ +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0023-ASoC-meson-add-aiu-i2s-dma-support.patch b/patch/kernel/meson64-dev/0023-ASoC-meson-add-aiu-i2s-dma-support.patch new file mode 100644 index 0000000000..c16bf54c1d --- /dev/null +++ b/patch/kernel/meson64-dev/0023-ASoC-meson-add-aiu-i2s-dma-support.patch @@ -0,0 +1,417 @@ +From bb870873e2352770678e151201387f4530f95830 Mon Sep 17 00:00:00 2001 +From: Jerome Brunet +Date: Thu, 30 Mar 2017 12:14:40 +0200 +Subject: [PATCH 23/36] ASoC: meson: add aiu i2s dma support + +Add support for the i2s output dma which is part of the AIU block + +Signed-off-by: Jerome Brunet +Signed-off-by: Neil Armstrong +--- + sound/soc/meson/Kconfig | 7 + + sound/soc/meson/Makefile | 2 + + sound/soc/meson/aiu-i2s-dma.c | 367 ++++++++++++++++++++++++++++++++++++++++++ + 3 files changed, 376 insertions(+) + create mode 100644 sound/soc/meson/aiu-i2s-dma.c + +diff --git a/sound/soc/meson/Kconfig b/sound/soc/meson/Kconfig +index 216c850..ad31a11 100644 +--- a/sound/soc/meson/Kconfig ++++ b/sound/soc/meson/Kconfig +@@ -7,3 +7,10 @@ menuconfig SND_SOC_MESON + Say Y or M if you want to add support for codecs attached to + the Amlogic Meson SoCs Audio interfaces. You will also need to + select the audio interfaces to support below. ++ ++config SND_SOC_MESON_I2S ++ tristate "Meson i2s interface" ++ depends on SND_SOC_MESON ++ help ++ Say Y or M if you want to add support for i2s dma driver for Amlogic ++ Meson SoCs. +diff --git a/sound/soc/meson/Makefile b/sound/soc/meson/Makefile +index 22028ab..273f275 100644 +--- a/sound/soc/meson/Makefile ++++ b/sound/soc/meson/Makefile +@@ -1,3 +1,5 @@ + snd-soc-meson-audio-core-objs := audio-core.o ++snd-soc-meson-aiu-i2s-dma-objs := aiu-i2s-dma.o + + obj-$(CONFIG_SND_SOC_MESON) += snd-soc-meson-audio-core.o ++obj-$(CONFIG_SND_SOC_MESON_I2S) += snd-soc-meson-aiu-i2s-dma.o +diff --git a/sound/soc/meson/aiu-i2s-dma.c b/sound/soc/meson/aiu-i2s-dma.c +new file mode 100644 +index 0000000..bab950d +--- /dev/null ++++ b/sound/soc/meson/aiu-i2s-dma.c +@@ -0,0 +1,367 @@ ++/* ++ * Copyright (C) 2017 BayLibre, SAS ++ * Author: Jerome Brunet ++ * Copyright (C) 2017 Amlogic, Inc. All rights reserved. ++ * ++ * This program is free software; you can redistribute it and/or ++ * modify it under the terms of the GNU General Public License as ++ * published by the Free Software Foundation; either version 2 of the ++ * License, or (at your option) any later version. ++ * ++ * 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. ++ * ++ * You should have received a copy of the GNU General Public License ++ * along with this program; if not, see . ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include ++#include ++ ++#include "aiu-regs.h" ++#include "audio-core.h" ++ ++#define DRV_NAME "meson-aiu-i2s-dma" ++ ++struct aiu_i2s_dma { ++ struct meson_audio_core_data *core; ++ struct clk *fast; ++ int irq; ++}; ++ ++#define AIU_MEM_I2S_BUF_CNTL_INIT BIT(0) ++#define AIU_MEM_I2S_CONTROL_INIT BIT(0) ++#define AIU_MEM_I2S_CONTROL_FILL_EN BIT(1) ++#define AIU_MEM_I2S_CONTROL_EMPTY_EN BIT(2) ++#define AIU_MEM_I2S_CONTROL_MODE_16BIT BIT(6) ++#define AIU_MEM_I2S_CONTROL_BUSY BIT(7) ++#define AIU_MEM_I2S_CONTROL_DATA_READY BIT(8) ++#define AIU_MEM_I2S_CONTROL_LEVEL_CNTL BIT(9) ++#define AIU_MEM_I2S_MASKS_IRQ_BLOCK_MASK GENMASK(31, 16) ++#define AIU_MEM_I2S_MASKS_IRQ_BLOCK(n) ((n) << 16) ++#define AIU_MEM_I2S_MASKS_CH_MEM_MASK GENMASK(15, 8) ++#define AIU_MEM_I2S_MASKS_CH_MEM(ch) ((ch) << 8) ++#define AIU_MEM_I2S_MASKS_CH_RD_MASK GENMASK(7, 0) ++#define AIU_MEM_I2S_MASKS_CH_RD(ch) ((ch) << 0) ++#define AIU_RST_SOFT_I2S_FAST_DOMAIN BIT(0) ++#define AIU_RST_SOFT_I2S_SLOW_DOMAIN BIT(1) ++ ++/* ++ * The DMA works by i2s "blocks" (or DMA burst). The burst size and the memory ++ * layout expected depends on the mode of operation. ++ * ++ * - Normal mode: The channels are expected to be packed in 32 bytes groups ++ * interleaved the buffer. AIU_MEM_I2S_MASKS_CH_MEM is a bitfield representing ++ * the channels present in memory. AIU_MEM_I2S_MASKS_CH_MEM represents the ++ * channels read by the DMA. This is very flexible but the unsual memory layout ++ * makes it less easy to deal with. The burst size is 32 bytes times the number ++ * of channels read. ++ * ++ * - Split mode: ++ * Classical channel interleaved frame organisation. In this mode, ++ * AIU_MEM_I2S_MASKS_CH_MEM and AIU_MEM_I2S_MASKS_CH_MEM must be set to 0xff and ++ * the burst size is fixed to 256 bytes. The input can be either 2 or 8 ++ * channels. ++ * ++ * The following driver implements the split mode. ++ */ ++ ++#define AIU_I2S_DMA_BURST 256 ++ ++static struct snd_pcm_hardware aiu_i2s_dma_hw = { ++ .info = (SNDRV_PCM_INFO_INTERLEAVED | ++ SNDRV_PCM_INFO_MMAP | ++ SNDRV_PCM_INFO_MMAP_VALID | ++ SNDRV_PCM_INFO_PAUSE), ++ ++ .formats = (SNDRV_PCM_FMTBIT_S16_LE | ++ SNDRV_PCM_FMTBIT_S24_LE | ++ SNDRV_PCM_FMTBIT_S32_LE), ++ ++ /* ++ * TODO: The DMA can change the endianness, the msb position ++ * and deal with unsigned - support this later on ++ */ ++ ++ .rate_min = 8000, ++ .rate_max = 192000, ++ .channels_min = 2, ++ .channels_max = 8, ++ .period_bytes_min = AIU_I2S_DMA_BURST, ++ .period_bytes_max = AIU_I2S_DMA_BURST * 65535, ++ .periods_min = 2, ++ .periods_max = UINT_MAX, ++ .buffer_bytes_max = 1 * 1024 * 1024, ++ .fifo_size = 0, ++}; ++ ++static struct aiu_i2s_dma *aiu_i2s_dma_priv(struct snd_pcm_substream *s) ++{ ++ struct snd_soc_pcm_runtime *rtd = s->private_data; ++ ++ return snd_soc_platform_get_drvdata(rtd->platform); ++} ++ ++static snd_pcm_uframes_t ++aiu_i2s_dma_pointer(struct snd_pcm_substream *substream) ++{ ++ struct snd_pcm_runtime *runtime = substream->runtime; ++ struct aiu_i2s_dma *priv = aiu_i2s_dma_priv(substream); ++ unsigned int addr; ++ int ret; ++ ++ ret = regmap_read(priv->core->aiu, AIU_MEM_I2S_RD_PTR, ++ &addr); ++ if (ret) ++ return 0; ++ ++ return bytes_to_frames(runtime, addr - (unsigned int)runtime->dma_addr); ++} ++ ++static void __dma_enable(struct aiu_i2s_dma *priv, bool enable) ++{ ++ unsigned int en_mask = (AIU_MEM_I2S_CONTROL_FILL_EN | ++ AIU_MEM_I2S_CONTROL_EMPTY_EN); ++ ++ regmap_update_bits(priv->core->aiu, AIU_MEM_I2S_CONTROL, en_mask, ++ enable ? en_mask : 0); ++ ++} ++ ++static int aiu_i2s_dma_trigger(struct snd_pcm_substream *substream, int cmd) ++{ ++ struct aiu_i2s_dma *priv = aiu_i2s_dma_priv(substream); ++ ++ switch (cmd) { ++ case SNDRV_PCM_TRIGGER_START: ++ case SNDRV_PCM_TRIGGER_RESUME: ++ case SNDRV_PCM_TRIGGER_PAUSE_RELEASE: ++ __dma_enable(priv, true); ++ break; ++ case SNDRV_PCM_TRIGGER_SUSPEND: ++ case SNDRV_PCM_TRIGGER_PAUSE_PUSH: ++ case SNDRV_PCM_TRIGGER_STOP: ++ __dma_enable(priv, false); ++ break; ++ default: ++ return -EINVAL; ++ } ++ ++ return 0; ++} ++ ++static void __dma_init_mem(struct aiu_i2s_dma *priv) ++{ ++ regmap_update_bits(priv->core->aiu, AIU_MEM_I2S_CONTROL, ++ AIU_MEM_I2S_CONTROL_INIT, ++ AIU_MEM_I2S_CONTROL_INIT); ++ regmap_update_bits(priv->core->aiu, AIU_MEM_I2S_BUF_CNTL, ++ AIU_MEM_I2S_BUF_CNTL_INIT, ++ AIU_MEM_I2S_BUF_CNTL_INIT); ++ ++ regmap_update_bits(priv->core->aiu, AIU_MEM_I2S_CONTROL, ++ AIU_MEM_I2S_CONTROL_INIT, ++ 0); ++ regmap_update_bits(priv->core->aiu, AIU_MEM_I2S_BUF_CNTL, ++ AIU_MEM_I2S_BUF_CNTL_INIT, ++ 0); ++} ++ ++static int aiu_i2s_dma_prepare(struct snd_pcm_substream *substream) ++{ ++ struct aiu_i2s_dma *priv = aiu_i2s_dma_priv(substream); ++ ++ __dma_init_mem(priv); ++ ++ return 0; ++} ++ ++static int aiu_i2s_dma_hw_params(struct snd_pcm_substream *substream, ++ struct snd_pcm_hw_params *params) ++{ ++ struct snd_pcm_runtime *runtime = substream->runtime; ++ struct aiu_i2s_dma *priv = aiu_i2s_dma_priv(substream); ++ int ret; ++ u32 burst_num, mem_ctl; ++ dma_addr_t end_ptr; ++ ++ ret = snd_pcm_lib_malloc_pages(substream, params_buffer_bytes(params)); ++ if (ret < 0) ++ return ret; ++ ++ /* Setup memory layout */ ++ if (params_physical_width(params) == 16) ++ mem_ctl = AIU_MEM_I2S_CONTROL_MODE_16BIT; ++ else ++ mem_ctl = 0; ++ ++ regmap_update_bits(priv->core->aiu, AIU_MEM_I2S_CONTROL, ++ AIU_MEM_I2S_CONTROL_MODE_16BIT, ++ mem_ctl); ++ ++ /* Initialize memory pointers */ ++ regmap_write(priv->core->aiu, AIU_MEM_I2S_START_PTR, runtime->dma_addr); ++ regmap_write(priv->core->aiu, AIU_MEM_I2S_RD_PTR, runtime->dma_addr); ++ ++ /* The end pointer is the address of the last valid block */ ++ end_ptr = runtime->dma_addr + runtime->dma_bytes - AIU_I2S_DMA_BURST; ++ regmap_write(priv->core->aiu, AIU_MEM_I2S_END_PTR, end_ptr); ++ ++ /* Memory masks */ ++ burst_num = params_period_bytes(params) / AIU_I2S_DMA_BURST; ++ regmap_write(priv->core->aiu, AIU_MEM_I2S_MASKS, ++ AIU_MEM_I2S_MASKS_CH_RD(0xff) | ++ AIU_MEM_I2S_MASKS_CH_MEM(0xff) | ++ AIU_MEM_I2S_MASKS_IRQ_BLOCK(burst_num)); ++ ++ return 0; ++} ++ ++static int aiu_i2s_dma_hw_free(struct snd_pcm_substream *substream) ++{ ++ return snd_pcm_lib_free_pages(substream); ++} ++ ++ ++static irqreturn_t aiu_i2s_dma_irq_block(int irq, void *dev_id) ++{ ++ struct snd_pcm_substream *playback = dev_id; ++ ++ snd_pcm_period_elapsed(playback); ++ ++ return IRQ_HANDLED; ++} ++ ++static int aiu_i2s_dma_open(struct snd_pcm_substream *substream) ++{ ++ struct aiu_i2s_dma *priv = aiu_i2s_dma_priv(substream); ++ int ret; ++ ++ snd_soc_set_runtime_hwparams(substream, &aiu_i2s_dma_hw); ++ ++ /* ++ * Make sure the buffer and period size are multiple of the DMA burst ++ * size ++ */ ++ ret = snd_pcm_hw_constraint_step(substream->runtime, 0, ++ SNDRV_PCM_HW_PARAM_BUFFER_BYTES, ++ AIU_I2S_DMA_BURST); ++ if (ret) ++ return ret; ++ ++ ret = snd_pcm_hw_constraint_step(substream->runtime, 0, ++ SNDRV_PCM_HW_PARAM_PERIOD_BYTES, ++ AIU_I2S_DMA_BURST); ++ if (ret) ++ return ret; ++ ++ /* Request the I2S DDR irq */ ++ ret = request_irq(priv->irq, aiu_i2s_dma_irq_block, 0, ++ DRV_NAME, substream); ++ if (ret) ++ return ret; ++ ++ /* Power up the i2s fast domain - can't write the registers w/o it */ ++ ret = clk_prepare_enable(priv->fast); ++ if (ret) ++ return ret; ++ ++ /* Make sure the dma is initially disabled */ ++ __dma_enable(priv, false); ++ ++ return 0; ++} ++ ++static int aiu_i2s_dma_close(struct snd_pcm_substream *substream) ++{ ++ struct aiu_i2s_dma *priv = aiu_i2s_dma_priv(substream); ++ ++ clk_disable_unprepare(priv->fast); ++ free_irq(priv->irq, substream); ++ ++ return 0; ++} ++ ++static const struct snd_pcm_ops aiu_i2s_dma_ops = { ++ .open = aiu_i2s_dma_open, ++ .close = aiu_i2s_dma_close, ++ .ioctl = snd_pcm_lib_ioctl, ++ .hw_params = aiu_i2s_dma_hw_params, ++ .hw_free = aiu_i2s_dma_hw_free, ++ .prepare = aiu_i2s_dma_prepare, ++ .pointer = aiu_i2s_dma_pointer, ++ .trigger = aiu_i2s_dma_trigger, ++}; ++ ++static int aiu_i2s_dma_new(struct snd_soc_pcm_runtime *rtd) ++{ ++ struct snd_card *card = rtd->card->snd_card; ++ size_t size = aiu_i2s_dma_hw.buffer_bytes_max; ++ ++ return snd_pcm_lib_preallocate_pages_for_all(rtd->pcm, ++ SNDRV_DMA_TYPE_DEV, ++ card->dev, size, size); ++} ++ ++struct snd_soc_platform_driver aiu_i2s_platform = { ++ .ops = &aiu_i2s_dma_ops, ++ .pcm_new = aiu_i2s_dma_new, ++}; ++ ++static int aiu_i2s_dma_probe(struct platform_device *pdev) ++{ ++ struct device *dev = &pdev->dev; ++ struct aiu_i2s_dma *priv; ++ ++ priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); ++ if (!priv) ++ return -ENOMEM; ++ ++ platform_set_drvdata(pdev, priv); ++ priv->core = dev_get_drvdata(dev->parent); ++ ++ priv->fast = devm_clk_get(dev, "fast"); ++ if (IS_ERR(priv->fast)) { ++ if (PTR_ERR(priv->fast) != -EPROBE_DEFER) ++ dev_err(dev, "Can't get i2s fast domain clock\n"); ++ return PTR_ERR(priv->fast); ++ } ++ ++ priv->irq = platform_get_irq(pdev, 0); ++ if (priv->irq <= 0) { ++ dev_err(dev, "Can't get i2s ddr irq\n"); ++ return priv->irq; ++ } ++ ++ return snd_soc_register_platform(dev, &aiu_i2s_platform); ++} ++ ++static const struct of_device_id aiu_i2s_dma_of_match[] = { ++ { .compatible = "amlogic,meson-aiu-i2s-dma", }, ++ { .compatible = "amlogic,meson-gxbb-aiu-i2s-dma", }, ++ { .compatible = "amlogic,meson-gxl-aiu-i2s-dma", }, ++ {} ++}; ++MODULE_DEVICE_TABLE(of, aiu_i2s_dma_of_match); ++ ++static struct platform_driver aiu_i2s_dma_pdrv = { ++ .probe = aiu_i2s_dma_probe, ++ .driver = { ++ .name = DRV_NAME, ++ .of_match_table = aiu_i2s_dma_of_match, ++ }, ++}; ++module_platform_driver(aiu_i2s_dma_pdrv); ++ ++MODULE_DESCRIPTION("Meson AIU i2s DMA ASoC Driver"); ++MODULE_AUTHOR("Jerome Brunet "); ++MODULE_LICENSE("GPL v2"); +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0024-ASoC-meson-add-initial-i2s-dai-support.patch b/patch/kernel/meson64-dev/0024-ASoC-meson-add-initial-i2s-dai-support.patch new file mode 100644 index 0000000000..19c6429d91 --- /dev/null +++ b/patch/kernel/meson64-dev/0024-ASoC-meson-add-initial-i2s-dai-support.patch @@ -0,0 +1,515 @@ +From bf2e8e4d3927896ecc52116345640e340f97ba55 Mon Sep 17 00:00:00 2001 +From: Jerome Brunet +Date: Thu, 30 Mar 2017 12:17:27 +0200 +Subject: [PATCH 24/36] ASoC: meson: add initial i2s dai support + +Add support for the i2s dai found on Amlogic Meson SoC family. +With this initial implementation, only playback is supported. +Capture will be part of furture work. + +Signed-off-by: Jerome Brunet +Signed-off-by: Neil Armstrong +--- + sound/soc/meson/Kconfig | 2 +- + sound/soc/meson/Makefile | 2 + + sound/soc/meson/i2s-dai.c | 465 ++++++++++++++++++++++++++++++++++++++++++++++ + 3 files changed, 468 insertions(+), 1 deletion(-) + create mode 100644 sound/soc/meson/i2s-dai.c + +diff --git a/sound/soc/meson/Kconfig b/sound/soc/meson/Kconfig +index ad31a11..604c9e2 100644 +--- a/sound/soc/meson/Kconfig ++++ b/sound/soc/meson/Kconfig +@@ -12,5 +12,5 @@ config SND_SOC_MESON_I2S + tristate "Meson i2s interface" + depends on SND_SOC_MESON + help +- Say Y or M if you want to add support for i2s dma driver for Amlogic ++ Say Y or M if you want to add support for i2s driver for Amlogic + Meson SoCs. +diff --git a/sound/soc/meson/Makefile b/sound/soc/meson/Makefile +index 273f275..ea06dde 100644 +--- a/sound/soc/meson/Makefile ++++ b/sound/soc/meson/Makefile +@@ -1,5 +1,7 @@ + snd-soc-meson-audio-core-objs := audio-core.o + snd-soc-meson-aiu-i2s-dma-objs := aiu-i2s-dma.o ++snd-soc-meson-i2s-dai-objs := i2s-dai.o + + obj-$(CONFIG_SND_SOC_MESON) += snd-soc-meson-audio-core.o + obj-$(CONFIG_SND_SOC_MESON_I2S) += snd-soc-meson-aiu-i2s-dma.o ++obj-$(CONFIG_SND_SOC_MESON_I2S) += snd-soc-meson-i2s-dai.o +diff --git a/sound/soc/meson/i2s-dai.c b/sound/soc/meson/i2s-dai.c +new file mode 100644 +index 0000000..1008af8 +--- /dev/null ++++ b/sound/soc/meson/i2s-dai.c +@@ -0,0 +1,465 @@ ++/* ++ * Copyright (C) 2017 BayLibre, SAS ++ * Author: Jerome Brunet ++ * Copyright (C) 2017 Amlogic, Inc. All rights reserved. ++ * ++ * This program is free software; you can redistribute it and/or ++ * modify it under the terms of the GNU General Public License as ++ * published by the Free Software Foundation; either version 2 of the ++ * License, or (at your option) any later version. ++ * ++ * 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. ++ * ++ * You should have received a copy of the GNU General Public License ++ * along with this program; if not, see . ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include ++#include ++#include ++ ++#include "aiu-regs.h" ++#include "audio-core.h" ++ ++#define DRV_NAME "meson-i2s-dai" ++ ++struct meson_i2s_dai { ++ struct meson_audio_core_data *core; ++ struct clk *mclk; ++ struct clk *bclks; ++ struct clk *iface; ++ struct clk *fast; ++ bool bclks_idle; ++}; ++ ++#define AIU_CLK_CTRL_I2S_DIV_EN BIT(0) ++#define AIU_CLK_CTRL_I2S_DIV_MASK GENMASK(3, 2) ++#define AIU_CLK_CTRL_AOCLK_POLARITY_MASK BIT(6) ++#define AIU_CLK_CTRL_AOCLK_POLARITY_NORMAL (0 << 6) ++#define AIU_CLK_CTRL_AOCLK_POLARITY_INVERTED (1 << 6) ++#define AIU_CLK_CTRL_ALRCLK_POLARITY_MASK BIT(7) ++#define AIU_CLK_CTRL_ALRCLK_POLARITY_NORMAL (0 << 7) ++#define AIU_CLK_CTRL_ALRCLK_POLARITY_INVERTED (1 << 7) ++#define AIU_CLK_CTRL_ALRCLK_SKEW_MASK GENMASK(9, 8) ++#define AIU_CLK_CTRL_ALRCLK_LEFT_J (0 << 8) ++#define AIU_CLK_CTRL_ALRCLK_I2S (1 << 8) ++#define AIU_CLK_CTRL_ALRCLK_RIGHT_J (2 << 8) ++#define AIU_CLK_CTRL_MORE_I2S_DIV_MASK GENMASK(5, 0) ++#define AIU_CLK_CTRL_MORE_I2S_DIV(div) (((div) - 1) << 0) ++#define AIU_CODEC_DAC_LRCLK_CTRL_DIV_MASK GENMASK(11, 0) ++#define AIU_CODEC_DAC_LRCLK_CTRL_DIV(div) (((div) - 1) << 0) ++#define AIU_I2S_DAC_CFG_PAYLOAD_SIZE_MASK GENMASK(1, 0) ++#define AIU_I2S_DAC_CFG_AOCLK_32 (0 << 0) ++#define AIU_I2S_DAC_CFG_AOCLK_48 (2 << 0) ++#define AIU_I2S_DAC_CFG_AOCLK_64 (3 << 0) ++#define AIU_I2S_MISC_HOLD_EN BIT(2) ++#define AIU_I2S_SOURCE_DESC_MODE_8CH BIT(0) ++#define AIU_I2S_SOURCE_DESC_MODE_24BIT BIT(5) ++#define AIU_I2S_SOURCE_DESC_MODE_32BIT BIT(9) ++#define AIU_I2S_SOURCE_DESC_MODE_SPLIT BIT(11) ++ ++static void __hold(struct meson_i2s_dai *priv, bool enable) ++{ ++ regmap_update_bits(priv->core->aiu, AIU_I2S_MISC, ++ AIU_I2S_MISC_HOLD_EN, ++ enable ? AIU_I2S_MISC_HOLD_EN : 0); ++} ++ ++static void __divider_enable(struct meson_i2s_dai *priv, bool enable) ++{ ++ regmap_update_bits(priv->core->aiu, AIU_CLK_CTRL, ++ AIU_CLK_CTRL_I2S_DIV_EN, ++ enable ? AIU_CLK_CTRL_I2S_DIV_EN : 0); ++} ++ ++static void __playback_start(struct meson_i2s_dai *priv) ++{ ++ __divider_enable(priv, true); ++ __hold(priv, false); ++} ++ ++static void __playback_stop(struct meson_i2s_dai *priv, bool clk_force) ++{ ++ __hold(priv, true); ++ /* Disable the bit clks if necessary */ ++ if (clk_force || !priv->bclks_idle) ++ __divider_enable(priv, false); ++} ++ ++static int meson_i2s_dai_trigger(struct snd_pcm_substream *substream, int cmd, ++ struct snd_soc_dai *dai) ++{ ++ struct meson_i2s_dai *priv = snd_soc_dai_get_drvdata(dai); ++ bool clk_force_stop = false; ++ ++ switch (cmd) { ++ case SNDRV_PCM_TRIGGER_START: ++ case SNDRV_PCM_TRIGGER_RESUME: ++ case SNDRV_PCM_TRIGGER_PAUSE_RELEASE: ++ __playback_start(priv); ++ return 0; ++ ++ case SNDRV_PCM_TRIGGER_STOP: ++ case SNDRV_PCM_TRIGGER_SUSPEND: ++ clk_force_stop = true; ++ case SNDRV_PCM_TRIGGER_PAUSE_PUSH: ++ __playback_stop(priv, clk_force_stop); ++ return 0; ++ ++ default: ++ return -EINVAL; ++ } ++} ++ ++static int __bclks_set_rate(struct meson_i2s_dai *priv, unsigned int srate, ++ unsigned int width) ++{ ++ unsigned int fs; ++ ++ /* Get the oversampling factor */ ++ fs = DIV_ROUND_CLOSEST(clk_get_rate(priv->mclk), srate); ++ ++ /* ++ * This DAI is usually connected to the dw-hdmi which does not support ++ * bclk being 32 * lrclk or 48 * lrclk ++ * Restrict to blck = 64 * lrclk ++ */ ++ if (fs % 64) ++ return -EINVAL; ++ ++ /* Set the divider between lrclk and bclk */ ++ regmap_update_bits(priv->core->aiu, AIU_I2S_DAC_CFG, ++ AIU_I2S_DAC_CFG_PAYLOAD_SIZE_MASK, ++ AIU_I2S_DAC_CFG_AOCLK_64); ++ ++ regmap_update_bits(priv->core->aiu, AIU_CODEC_DAC_LRCLK_CTRL, ++ AIU_CODEC_DAC_LRCLK_CTRL_DIV_MASK, ++ AIU_CODEC_DAC_LRCLK_CTRL_DIV(64)); ++ ++ /* Use CLK_MORE for the i2s divider */ ++ regmap_update_bits(priv->core->aiu, AIU_CLK_CTRL, ++ AIU_CLK_CTRL_I2S_DIV_MASK, ++ 0); ++ ++ regmap_update_bits(priv->core->aiu, AIU_CLK_CTRL_MORE, ++ AIU_CLK_CTRL_MORE_I2S_DIV_MASK, ++ AIU_CLK_CTRL_MORE_I2S_DIV(fs / 64)); ++ ++ return 0; ++} ++ ++static int __setup_desc(struct meson_i2s_dai *priv, unsigned int width, ++ unsigned int channels) ++{ ++ u32 desc = 0; ++ ++ switch (width) { ++ case 24: ++ /* ++ * For some reason, 24 bits wide audio don't play well ++ * if the 32 bits mode is not set ++ */ ++ desc |= (AIU_I2S_SOURCE_DESC_MODE_24BIT | ++ AIU_I2S_SOURCE_DESC_MODE_32BIT); ++ break; ++ case 16: ++ break; ++ ++ default: ++ return -EINVAL; ++ } ++ ++ switch (channels) { ++ case 2: /* Nothing to do */ ++ break; ++ case 8: ++ /* TODO: Still requires testing ... */ ++ desc |= AIU_I2S_SOURCE_DESC_MODE_8CH; ++ break; ++ default: ++ return -EINVAL; ++ } ++ ++ regmap_update_bits(priv->core->aiu, AIU_I2S_SOURCE_DESC, ++ AIU_I2S_SOURCE_DESC_MODE_8CH | ++ AIU_I2S_SOURCE_DESC_MODE_24BIT | ++ AIU_I2S_SOURCE_DESC_MODE_32BIT, ++ desc); ++ ++ return 0; ++} ++ ++static int meson_i2s_dai_hw_params(struct snd_pcm_substream *substream, ++ struct snd_pcm_hw_params *params, ++ struct snd_soc_dai *dai) ++{ ++ struct meson_i2s_dai *priv = snd_soc_dai_get_drvdata(dai); ++ unsigned int width = params_width(params); ++ unsigned int channels = params_channels(params); ++ unsigned int rate = params_rate(params); ++ int ret; ++ ++ ret = __setup_desc(priv, width, channels); ++ if (ret) { ++ dev_err(dai->dev, "Unable set to set i2s description\n"); ++ return ret; ++ } ++ ++ ret = __bclks_set_rate(priv, rate, width); ++ if (ret) { ++ dev_err(dai->dev, "Unable set to the i2s clock rates\n"); ++ return ret; ++ } ++ ++ return 0; ++} ++ ++static int meson_i2s_dai_set_fmt(struct snd_soc_dai *dai, unsigned int fmt) ++{ ++ struct meson_i2s_dai *priv = snd_soc_dai_get_drvdata(dai); ++ u32 val; ++ ++ if ((fmt & SND_SOC_DAIFMT_MASTER_MASK) != SND_SOC_DAIFMT_CBS_CFS) ++ return -EINVAL; ++ ++ /* DAI output mode */ ++ switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) { ++ case SND_SOC_DAIFMT_I2S: ++ val = AIU_CLK_CTRL_ALRCLK_I2S; ++ break; ++ case SND_SOC_DAIFMT_LEFT_J: ++ val = AIU_CLK_CTRL_ALRCLK_LEFT_J; ++ break; ++ case SND_SOC_DAIFMT_RIGHT_J: ++ val = AIU_CLK_CTRL_ALRCLK_RIGHT_J; ++ break; ++ default: ++ return -EINVAL; ++ } ++ ++ regmap_update_bits(priv->core->aiu, AIU_CLK_CTRL, ++ AIU_CLK_CTRL_ALRCLK_SKEW_MASK, ++ val); ++ ++ /* DAI clock polarity */ ++ switch (fmt & SND_SOC_DAIFMT_INV_MASK) { ++ case SND_SOC_DAIFMT_IB_IF: ++ /* Invert both clocks */ ++ val = AIU_CLK_CTRL_ALRCLK_POLARITY_INVERTED | ++ AIU_CLK_CTRL_AOCLK_POLARITY_INVERTED; ++ break; ++ case SND_SOC_DAIFMT_IB_NF: ++ /* Invert bit clock */ ++ val = AIU_CLK_CTRL_ALRCLK_POLARITY_NORMAL | ++ AIU_CLK_CTRL_AOCLK_POLARITY_INVERTED; ++ break; ++ case SND_SOC_DAIFMT_NB_IF: ++ /* Invert frame clock */ ++ val = AIU_CLK_CTRL_ALRCLK_POLARITY_INVERTED | ++ AIU_CLK_CTRL_AOCLK_POLARITY_NORMAL; ++ break; ++ case SND_SOC_DAIFMT_NB_NF: ++ /* Normal clocks */ ++ val = AIU_CLK_CTRL_ALRCLK_POLARITY_NORMAL | ++ AIU_CLK_CTRL_AOCLK_POLARITY_NORMAL; ++ break; ++ default: ++ return -EINVAL; ++ } ++ ++ regmap_update_bits(priv->core->aiu, AIU_CLK_CTRL, ++ AIU_CLK_CTRL_ALRCLK_POLARITY_MASK | ++ AIU_CLK_CTRL_AOCLK_POLARITY_MASK, ++ val); ++ ++ switch (fmt & SND_SOC_DAIFMT_CLOCK_MASK) { ++ case SND_SOC_DAIFMT_CONT: ++ priv->bclks_idle = true; ++ break; ++ case SND_SOC_DAIFMT_GATED: ++ priv->bclks_idle = false; ++ break; ++ default: ++ return -EINVAL; ++ } ++ ++ return 0; ++} ++ ++static int meson_i2s_dai_set_sysclk(struct snd_soc_dai *dai, int clk_id, ++ unsigned int freq, int dir) ++{ ++ struct meson_i2s_dai *priv = snd_soc_dai_get_drvdata(dai); ++ int ret; ++ ++ if (WARN_ON(clk_id != 0)) ++ return -EINVAL; ++ ++ if (dir == SND_SOC_CLOCK_IN) ++ return 0; ++ ++ ret = clk_set_rate(priv->mclk, freq); ++ if (ret) { ++ dev_err(dai->dev, "Failed to set sysclk to %uHz", freq); ++ return ret; ++ } ++ ++ return 0; ++} ++ ++static int meson_i2s_dai_startup(struct snd_pcm_substream *substream, ++ struct snd_soc_dai *dai) ++{ ++ struct meson_i2s_dai *priv = snd_soc_dai_get_drvdata(dai); ++ int ret; ++ ++ /* Power up the i2s fast domain - can't write the registers w/o it */ ++ ret = clk_prepare_enable(priv->fast); ++ if (ret) ++ goto out_clk_fast; ++ ++ /* Make sure nothing gets out of the DAI yet */ ++ __hold(priv, true); ++ ++ /* I2S encoder needs the mixer interface gate */ ++ ret = clk_prepare_enable(priv->iface); ++ if (ret) ++ goto out_clk_iface; ++ ++ /* Enable the i2s master clock */ ++ ret = clk_prepare_enable(priv->mclk); ++ if (ret) ++ goto out_mclk; ++ ++ /* Enable the bit clock gate */ ++ ret = clk_prepare_enable(priv->bclks); ++ if (ret) ++ goto out_bclks; ++ ++ /* Make sure the interface expect a memory layout we can work with */ ++ regmap_update_bits(priv->core->aiu, AIU_I2S_SOURCE_DESC, ++ AIU_I2S_SOURCE_DESC_MODE_SPLIT, ++ AIU_I2S_SOURCE_DESC_MODE_SPLIT); ++ ++ return 0; ++ ++out_bclks: ++ clk_disable_unprepare(priv->mclk); ++out_mclk: ++ clk_disable_unprepare(priv->iface); ++out_clk_iface: ++ clk_disable_unprepare(priv->fast); ++out_clk_fast: ++ return ret; ++} ++ ++static void meson_i2s_dai_shutdown(struct snd_pcm_substream *substream, ++ struct snd_soc_dai *dai) ++{ ++ struct meson_i2s_dai *priv = snd_soc_dai_get_drvdata(dai); ++ ++ clk_disable_unprepare(priv->bclks); ++ clk_disable_unprepare(priv->mclk); ++ clk_disable_unprepare(priv->iface); ++ clk_disable_unprepare(priv->fast); ++} ++ ++static const struct snd_soc_dai_ops meson_i2s_dai_ops = { ++ .startup = meson_i2s_dai_startup, ++ .shutdown = meson_i2s_dai_shutdown, ++ .trigger = meson_i2s_dai_trigger, ++ .hw_params = meson_i2s_dai_hw_params, ++ .set_fmt = meson_i2s_dai_set_fmt, ++ .set_sysclk = meson_i2s_dai_set_sysclk, ++}; ++ ++static struct snd_soc_dai_driver meson_i2s_dai = { ++ .playback = { ++ .stream_name = "Playback", ++ .channels_min = 2, ++ .channels_max = 8, ++ .rates = SNDRV_PCM_RATE_8000_192000, ++ .formats = (SNDRV_PCM_FMTBIT_S16_LE | ++ SNDRV_PCM_FMTBIT_S24_LE) ++ }, ++ .ops = &meson_i2s_dai_ops, ++}; ++ ++static const struct snd_soc_component_driver meson_i2s_dai_component = { ++ .name = DRV_NAME, ++}; ++ ++static int meson_i2s_dai_probe(struct platform_device *pdev) ++{ ++ struct device *dev = &pdev->dev; ++ struct meson_i2s_dai *priv; ++ ++ priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); ++ if (!priv) ++ return -ENOMEM; ++ ++ platform_set_drvdata(pdev, priv); ++ priv->core = dev_get_drvdata(dev->parent); ++ ++ priv->fast = devm_clk_get(dev, "fast"); ++ if (IS_ERR(priv->fast)) { ++ if (PTR_ERR(priv->fast) != -EPROBE_DEFER) ++ dev_err(dev, "Can't get the i2s fast domain clock\n"); ++ return PTR_ERR(priv->fast); ++ } ++ ++ priv->iface = devm_clk_get(dev, "iface"); ++ if (IS_ERR(priv->iface)) { ++ if (PTR_ERR(priv->iface) != -EPROBE_DEFER) ++ dev_err(dev, "Can't get i2s dai clock gate\n"); ++ return PTR_ERR(priv->iface); ++ } ++ ++ priv->bclks = devm_clk_get(dev, "bclks"); ++ if (IS_ERR(priv->bclks)) { ++ if (PTR_ERR(priv->bclks) != -EPROBE_DEFER) ++ dev_err(dev, "Can't get bit clocks gate\n"); ++ return PTR_ERR(priv->bclks); ++ } ++ ++ priv->mclk = devm_clk_get(dev, "mclk"); ++ if (IS_ERR(priv->mclk)) { ++ if (PTR_ERR(priv->mclk) != -EPROBE_DEFER) ++ dev_err(dev, "failed to get the i2s master clock\n"); ++ return PTR_ERR(priv->mclk); ++ } ++ ++ return devm_snd_soc_register_component(dev, &meson_i2s_dai_component, ++ &meson_i2s_dai, 1); ++} ++ ++static const struct of_device_id meson_i2s_dai_of_match[] = { ++ { .compatible = "amlogic,meson-i2s-dai", }, ++ { .compatible = "amlogic,meson-gxbb-i2s-dai", }, ++ { .compatible = "amlogic,meson-gxl-i2s-dai", }, ++ {} ++}; ++MODULE_DEVICE_TABLE(of, meson_i2s_dai_of_match); ++ ++static struct platform_driver meson_i2s_dai_pdrv = { ++ .probe = meson_i2s_dai_probe, ++ .driver = { ++ .name = DRV_NAME, ++ .of_match_table = meson_i2s_dai_of_match, ++ }, ++}; ++module_platform_driver(meson_i2s_dai_pdrv); ++ ++MODULE_DESCRIPTION("Meson i2s DAI ASoC Driver"); ++MODULE_AUTHOR("Jerome Brunet "); ++MODULE_LICENSE("GPL v2"); +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0025-snd-meson-activate-HDMI-audio-path.patch b/patch/kernel/meson64-dev/0025-snd-meson-activate-HDMI-audio-path.patch new file mode 100644 index 0000000000..c8fc99f3a1 --- /dev/null +++ b/patch/kernel/meson64-dev/0025-snd-meson-activate-HDMI-audio-path.patch @@ -0,0 +1,55 @@ +From 844704d95e4a08404b154ce6969624e6bc8689a0 Mon Sep 17 00:00:00 2001 +From: Jerome Brunet +Date: Fri, 7 Jul 2017 17:39:21 +0200 +Subject: [PATCH 25/36] snd: meson: activate HDMI audio path + +Signed-off-by: Neil Armstrong +--- + sound/soc/meson/i2s-dai.c | 22 ++++++++++++++++++++++ + 1 file changed, 22 insertions(+) + +diff --git a/sound/soc/meson/i2s-dai.c b/sound/soc/meson/i2s-dai.c +index 1008af8..63fe098 100644 +--- a/sound/soc/meson/i2s-dai.c ++++ b/sound/soc/meson/i2s-dai.c +@@ -56,8 +56,19 @@ struct meson_i2s_dai { + #define AIU_CLK_CTRL_ALRCLK_RIGHT_J (2 << 8) + #define AIU_CLK_CTRL_MORE_I2S_DIV_MASK GENMASK(5, 0) + #define AIU_CLK_CTRL_MORE_I2S_DIV(div) (((div) - 1) << 0) ++#define AIU_CLK_CTRL_MORE_HDMI_TX_SEL_MASK BIT(6) ++#define AIU_CLK_CTRL_MORE_HDMI_TX_I958_CLK (0 << 6) ++#define AIU_CLK_CTRL_MORE_HDMI_TX_INT_CLK (1 << 6) + #define AIU_CODEC_DAC_LRCLK_CTRL_DIV_MASK GENMASK(11, 0) + #define AIU_CODEC_DAC_LRCLK_CTRL_DIV(div) (((div) - 1) << 0) ++#define AIU_HDMI_CLK_DATA_CTRL_CLK_SEL_MASK GENMASK(1, 0) ++#define AIU_HDMI_CLK_DATA_CTRL_CLK_DISABLE (0 << 0) ++#define AIU_HDMI_CLK_DATA_CTRL_CLK_PCM (1 << 0) ++#define AIU_HDMI_CLK_DATA_CTRL_CLK_I2S (2 << 0) ++#define AIU_HDMI_CLK_DATA_CTRL_DATA_SEL_MASK GENMASK(5, 4) ++#define AIU_HDMI_CLK_DATA_CTRL_DATA_MUTE (0 << 4) ++#define AIU_HDMI_CLK_DATA_CTRL_DATA_PCM (1 << 4) ++#define AIU_HDMI_CLK_DATA_CTRL_DATA_I2S (2 << 4) + #define AIU_I2S_DAC_CFG_PAYLOAD_SIZE_MASK GENMASK(1, 0) + #define AIU_I2S_DAC_CFG_AOCLK_32 (0 << 0) + #define AIU_I2S_DAC_CFG_AOCLK_48 (2 << 0) +@@ -221,6 +232,17 @@ static int meson_i2s_dai_hw_params(struct snd_pcm_substream *substream, + return ret; + } + ++ /* Quick and dirty hack for HDMI */ ++ regmap_update_bits(priv->core->aiu, AIU_HDMI_CLK_DATA_CTRL, ++ AIU_HDMI_CLK_DATA_CTRL_CLK_SEL_MASK | ++ AIU_HDMI_CLK_DATA_CTRL_DATA_SEL_MASK, ++ AIU_HDMI_CLK_DATA_CTRL_CLK_I2S | ++ AIU_HDMI_CLK_DATA_CTRL_DATA_I2S); ++ ++ regmap_update_bits(priv->core->aiu, AIU_CLK_CTRL_MORE, ++ AIU_CLK_CTRL_MORE_HDMI_TX_SEL_MASK, ++ AIU_CLK_CTRL_MORE_HDMI_TX_INT_CLK); ++ + return 0; + } + +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0026-drm-meson-select-dw-hdmi-i2s-audio-for-meson-hdmi.patch b/patch/kernel/meson64-dev/0026-drm-meson-select-dw-hdmi-i2s-audio-for-meson-hdmi.patch new file mode 100644 index 0000000000..296fc7d54b --- /dev/null +++ b/patch/kernel/meson64-dev/0026-drm-meson-select-dw-hdmi-i2s-audio-for-meson-hdmi.patch @@ -0,0 +1,23 @@ +From eba7c73a03e4e88b4ae3962c3889eda867b9a746 Mon Sep 17 00:00:00 2001 +From: Jerome Brunet +Date: Tue, 14 Feb 2017 19:18:04 +0100 +Subject: [PATCH 26/36] drm/meson: select dw-hdmi i2s audio for meson hdmi + +Signed-off-by: Jerome Brunet +Signed-off-by: Neil Armstrong +--- + drivers/gpu/drm/meson/Kconfig | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/drivers/gpu/drm/meson/Kconfig b/drivers/gpu/drm/meson/Kconfig +index 3ce51d8..02d400b 100644 +--- a/drivers/gpu/drm/meson/Kconfig ++++ b/drivers/gpu/drm/meson/Kconfig +@@ -13,3 +13,4 @@ config DRM_MESON_DW_HDMI + depends on DRM_MESON + default y if DRM_MESON + select DRM_DW_HDMI ++ select DRM_DW_HDMI_I2S_AUDIO +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0028-ARM64-dts-meson-gx-add-audio-controller-nodes.patch b/patch/kernel/meson64-dev/0028-ARM64-dts-meson-gx-add-audio-controller-nodes.patch new file mode 100644 index 0000000000..6414a4918f --- /dev/null +++ b/patch/kernel/meson64-dev/0028-ARM64-dts-meson-gx-add-audio-controller-nodes.patch @@ -0,0 +1,89 @@ +From 28b35c60a0648febfea7bd4b082b86904900fc2c Mon Sep 17 00:00:00 2001 +From: Jerome Brunet +Date: Wed, 20 Sep 2017 17:22:47 +0200 +Subject: [PATCH 28/36] ARM64: dts: meson-gx: add audio controller nodes + +Add audio controller nodes for Amlogic meson gxl. +This includes the audio-core node, the i2s DAI and i2s +aiu DMAs. + +Audio on this SoC family is still a work in progress. More nodes are likely +to be added later on (pcm DAIs, input DMAs, SPDIF etc ...) + +Signed-off-by: Jerome Brunet +Signed-off-by: Neil Armstrong +--- + arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 22 ++++++++++++++++++++++ + arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 23 +++++++++++++++++++++++ + 2 files changed, 45 insertions(+) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi +index f175db8..ff27ce0 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi +@@ -224,6 +224,28 @@ + #reset-cells = <1>; + }; + ++ audio: audio@5400 { ++ compatible = "amlogic,meson-audio-core"; ++ reg = <0x0 0x5400 0x0 0x2ac>, ++ <0x0 0xa000 0x0 0x304>; ++ reg-names = "aiu", "audin"; ++ status = "disabled"; ++ ++ aiu_i2s_dma: aiu_i2s_dma { ++ #sound-dai-cells = <0>; ++ compatible = "amlogic,meson-aiu-i2s-dma"; ++ interrupts = ; ++ status = "disabled"; ++ }; ++ ++ i2s_dai: i2s_dai { ++ #sound-dai-cells = <0>; ++ compatible = "amlogic,meson-i2s-dai"; ++ status = "disabled"; ++ }; ++ ++ }; ++ + uart_A: serial@84c0 { + compatible = "amlogic,meson-gx-uart", "amlogic,meson-uart"; + reg = <0x0 0x84c0 0x0 0x14>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi +index ebcb5eb..7715ac0 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi +@@ -683,6 +683,29 @@ + }; + }; + ++&audio { ++ clocks = <&clkc CLKID_AIU>, ++ <&clkc CLKID_AIU_GLUE>, ++ <&clkc CLKID_I2S_SPDIF>; ++ clock-names = "aiu_top", "aiu_glue", "audin"; ++ resets = <&reset RESET_AIU>, ++ <&reset RESET_AUDIN>; ++ reset-names = "aiu", "audin"; ++}; ++ ++&aiu_i2s_dma { ++ clocks = <&clkc CLKID_I2S_OUT>; ++ clock-names = "fast"; ++}; ++ ++&i2s_dai { ++ clocks = <&clkc CLKID_I2S_OUT>, ++ <&clkc CLKID_MIXER_IFACE>, ++ <&clkc CLKID_AOCLK_GATE>, ++ <&clkc CLKID_CTS_AMCLK>; ++ clock-names = "fast", "iface", "bclks", "mclk"; ++}; ++ + &saradc { + compatible = "amlogic,meson-gxl-saradc", "amlogic,meson-saradc"; + clocks = <&xtal>, +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0029-ARM64-dts-meson-gxl-add-sound-dai-cells-to-HDMI-node.patch b/patch/kernel/meson64-dev/0029-ARM64-dts-meson-gxl-add-sound-dai-cells-to-HDMI-node.patch new file mode 100644 index 0000000000..9585fbdf93 --- /dev/null +++ b/patch/kernel/meson64-dev/0029-ARM64-dts-meson-gxl-add-sound-dai-cells-to-HDMI-node.patch @@ -0,0 +1,26 @@ +From f23da8c4e62def19dc1704a6533e37ecb3350eb0 Mon Sep 17 00:00:00 2001 +From: Jerome Brunet +Date: Wed, 20 Sep 2017 18:01:26 +0200 +Subject: [PATCH 29/36] ARM64: dts: meson-gxl: add sound-dai-cells to HDMI node + +Signed-off-by: Jerome Brunet +Signed-off-by: Neil Armstrong +--- + arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi +index 7715ac0..fc59a5a 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi +@@ -286,6 +286,7 @@ + <&clkc CLKID_CLK81>, + <&clkc CLKID_GCLK_VENCI_INT0>; + clock-names = "isfr", "iahb", "venci"; ++ #sound-dai-cells = <0>; + }; + + &hiubus { +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0030-ARM64-dts-meson-gxl-Add-alternate-ARM-Trusted-Firmwa.patch b/patch/kernel/meson64-dev/0030-ARM64-dts-meson-gxl-Add-alternate-ARM-Trusted-Firmwa.patch new file mode 100644 index 0000000000..304d6f10a6 --- /dev/null +++ b/patch/kernel/meson64-dev/0030-ARM64-dts-meson-gxl-Add-alternate-ARM-Trusted-Firmwa.patch @@ -0,0 +1,50 @@ +From 157f93b346ac791d42e7dc2e17a6f5540c045719 Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Wed, 11 Oct 2017 17:23:12 +0200 +Subject: [PATCH 30/36] ARM64: dts: meson-gxl: Add alternate ARM Trusted + Firmware reserved memory zone + +This year, Amlogic updated the ARM Trusted Firmware reserved memory mapping +for Meson GXL SoCs and products sold since May 2017 uses this alternate +reserved memory mapping. +But products had been sold using the previous mapping. + +This issue has been explained in [1] and a dynamic solution is yet to be +found to avoid loosing another 3Mbytes of reservable memory. + +In the meantime, this patch adds this alternate memory zone only for +the GXL and GXM SoCs since GXBB based new products stopped earlier. + +[1] http://lists.infradead.org/pipermail/linux-amlogic/2017-October/004860.html + +Fixes: bba8e3f42736 ("ARM64: dts: meson-gx: Add firmware reserved memory zones") +Reported-by: Jerome Brunet +Signed-off-by: Neil Armstrong +Acked-by: Will Deacon +Tested-by: Will Deacon +--- + arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 8 ++++++++ + 1 file changed, 8 insertions(+) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi +index fc59a5a..4a1bd89 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi +@@ -50,6 +50,14 @@ + / { + compatible = "amlogic,meson-gxl"; + ++ reserved-memory { ++ /* Alternate 3 MiB reserved for ARM Trusted Firmware (BL31) */ ++ secmon_reserved_alt: secmon@05000000 { ++ reg = <0x0 0x05000000 0x0 0x300000>; ++ no-map; ++ }; ++ }; ++ + soc { + + usb0: usb@c9000000 { +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0031-ARM64-dts-meson-gxl-Take-eMMC-data-strobe-out-of-eMM.patch b/patch/kernel/meson64-dev/0031-ARM64-dts-meson-gxl-Take-eMMC-data-strobe-out-of-eMM.patch new file mode 100644 index 0000000000..0de45ea623 --- /dev/null +++ b/patch/kernel/meson64-dev/0031-ARM64-dts-meson-gxl-Take-eMMC-data-strobe-out-of-eMM.patch @@ -0,0 +1,228 @@ +From 5d15137e72c78be05dfa4a9228cd956733195dca Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Mon, 28 Aug 2017 12:01:09 +0200 +Subject: [PATCH 31/36] ARM64: dts: meson-gxl: Take eMMC data strobe out of + eMMC pins + +Since the Data Strobe pin is optional, take it out of the default +eMMC pins and add a separate entry. + +Signed-off-by: Neil Armstrong +--- + arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi | 2 +- + arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts | 2 +- + arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts | 2 +- + arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts | 2 +- + arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi | 2 +- + arch/arm64/boot/dts/amlogic/meson-gxbb-vega-s95.dtsi | 2 +- + arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 10 ++++++++-- + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-hwacom-amazetv.dts | 2 +- + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 2 +- + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts | 2 +- + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi | 2 +- + arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 10 ++++++++-- + arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts | 2 +- + arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts | 2 +- + 14 files changed, 28 insertions(+), 16 deletions(-) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi +index 7ce9a62..7f59f30 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi +@@ -213,7 +213,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "okay"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-1 = <&emmc_clk_gate_pins>; + pinctrl-names = "default", "clk-gate"; + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts +index 4b17a76..a42c8f4 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts +@@ -302,7 +302,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "disabled"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-1 = <&emmc_clk_gate_pins>; + pinctrl-names = "default", "clk-gate"; + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts +index 38dfdde..9a77323 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts +@@ -272,7 +272,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "okay"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-1 = <&emmc_clk_gate_pins>; + pinctrl-names = "default", "clk-gate"; + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts +index b035c72..c2b6df4 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts +@@ -271,7 +271,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "okay"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-1 = <&emmc_clk_gate_pins>; + pinctrl-names = "default", "clk-gate"; + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi +index 23c08c3..932158a 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi +@@ -242,7 +242,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "okay"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-1 = <&emmc_clk_gate_pins>; + pinctrl-names = "default", "clk-gate"; + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-vega-s95.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb-vega-s95.dtsi +index f2bc6de..1fe8e24 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb-vega-s95.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-vega-s95.dtsi +@@ -199,7 +199,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "okay"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-1 = <&emmc_clk_gate_pins>; + pinctrl-names = "default", "clk-gate"; + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi +index 7d38d55..ef12d67 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi +@@ -390,8 +390,14 @@ + mux { + groups = "emmc_nand_d07", + "emmc_cmd", +- "emmc_clk", +- "emmc_ds"; ++ "emmc_clk"; ++ function = "emmc"; ++ }; ++ }; ++ ++ emmc_ds_pins: emmc-ds { ++ mux { ++ groups = "emmc_ds"; + function = "emmc"; + }; + }; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-hwacom-amazetv.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-hwacom-amazetv.dts +index 6f2cd8e..5eaafa1 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-hwacom-amazetv.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-hwacom-amazetv.dts +@@ -141,7 +141,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "okay"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-1 = <&emmc_clk_gate_pins>; + pinctrl-names = "default", "clk-gate"; + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts +index 4035891..942fd70 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts +@@ -221,7 +221,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "okay"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-1 = <&emmc_clk_gate_pins>; + pinctrl-names = "default", "clk-gate"; + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts +index 6338e6c..0fdebcc 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts +@@ -229,7 +229,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "okay"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-1 = <&emmc_clk_gate_pins>; + pinctrl-names = "default", "clk-gate"; + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi +index 7a1c20e..0a2be82 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi +@@ -135,7 +135,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "okay"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-1 = <&emmc_clk_gate_pins>; + pinctrl-names = "default", "clk-gate"; + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi +index 4a1bd89..02b52b6 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi +@@ -343,8 +343,14 @@ + mux { + groups = "emmc_nand_d07", + "emmc_cmd", +- "emmc_clk", +- "emmc_ds"; ++ "emmc_clk"; ++ function = "emmc"; ++ }; ++ }; ++ ++ emmc_ds_pins: emmc-ds { ++ mux { ++ groups = "emmc_ds"; + function = "emmc"; + }; + }; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts +index cfde246..e70b5e2 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts +@@ -193,7 +193,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "okay"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-1 = <&emmc_clk_gate_pins>; + pinctrl-names = "default", "clk-gate"; + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts +index 9837a48..9593a28 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts +@@ -216,7 +216,7 @@ + /* eMMC */ + &sd_emmc_c { + status = "okay"; +- pinctrl-0 = <&emmc_pins>; ++ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; + pinctrl-names = "default"; + + bus-width = <8>; +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0032-ARM64-dts-meson-gx-add-VPU-power-domain.patch b/patch/kernel/meson64-dev/0032-ARM64-dts-meson-gx-add-VPU-power-domain.patch new file mode 100644 index 0000000000..1fb6acf80e --- /dev/null +++ b/patch/kernel/meson64-dev/0032-ARM64-dts-meson-gx-add-VPU-power-domain.patch @@ -0,0 +1,165 @@ +From 8fe651551acad197e8c776612b2fc16664d91f17 Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Fri, 13 Oct 2017 14:47:23 +0200 +Subject: [PATCH 32/36] ARM64: dts: meson-gx: add VPU power domain + +This patch adds support for the VPU Power Domain nodes, and attaches the +VPU power domain to the VPU node. + +Signed-off-by: Neil Armstrong +--- + arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 11 ++++++++ + arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 43 +++++++++++++++++++++++++++++ + arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 43 +++++++++++++++++++++++++++++ + 3 files changed, 97 insertions(+) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi +index ff27ce0..ace0e4b 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi +@@ -393,6 +393,12 @@ + compatible = "amlogic,meson-gx-ao-sysctrl", "syscon", "simple-mfd"; + reg = <0x0 0x0 0x0 0x100>; + ++ pwrc_vpu: power-controller-vpu { ++ compatible = "amlogic,meson-gx-pwrc-vpu"; ++ #power-domain-cells = <0>; ++ amlogic,hhi-sysctrl = <&sysctrl>; ++ }; ++ + clkc_AO: clock-controller { + compatible = "amlogic,meson-gx-aoclkc"; + #clock-cells = <1>; +@@ -470,6 +476,11 @@ + #size-cells = <2>; + ranges = <0x0 0x0 0x0 0xc883c000 0x0 0x2000>; + ++ sysctrl: system-controller@0 { ++ compatible = "amlogic,meson-gx-hhi-sysctrl", "syscon", "simple-mfd"; ++ reg = <0 0 0 0x400>; ++ }; ++ + mailbox: mailbox@404 { + compatible = "amlogic,meson-gx-mhu", "amlogic,meson-gxbb-mhu"; + reg = <0 0x404 0 0x4c>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi +index ef12d67..b5b6b33 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi +@@ -692,6 +692,48 @@ + }; + }; + ++&pwrc_vpu { ++ resets = <&reset RESET_VIU>, ++ <&reset RESET_VENC>, ++ <&reset RESET_VCBUS>, ++ <&reset RESET_BT656>, ++ <&reset RESET_DVIN_RESET>, ++ <&reset RESET_RDMA>, ++ <&reset RESET_VENCI>, ++ <&reset RESET_VENCP>, ++ <&reset RESET_VDAC>, ++ <&reset RESET_VDI6>, ++ <&reset RESET_VENCL>, ++ <&reset RESET_VID_LOCK>; ++ clocks = <&clkc CLKID_VPU>, ++ <&clkc CLKID_VAPB>; ++ clock-names = "vpu", "vapb"; ++ /* ++ * VPU clocking is provided by two identical clock paths ++ * VPU_0 and VPU_1 muxed to a single clock by a glitch ++ * free mux to safely change frequency while running. ++ * Same for VAPB but with a final gate after the glitch free mux. ++ */ ++ assigned-clocks = <&clkc CLKID_VPU_0_SEL>, ++ <&clkc CLKID_VPU_0>, ++ <&clkc CLKID_VPU>, /* Glitch free mux */ ++ <&clkc CLKID_VAPB_0_SEL>, ++ <&clkc CLKID_VAPB_0>, ++ <&clkc CLKID_VAPB_SEL>; /* Glitch free mux */ ++ assigned-clock-parents = <&clkc CLKID_FCLK_DIV3>, ++ <0>, /* Do Nothing */ ++ <&clkc CLKID_VPU_0>, ++ <&clkc CLKID_FCLK_DIV4>, ++ <0>, /* Do Nothing */ ++ <&clkc CLKID_VAPB_0>; ++ assigned-clock-rates = <0>, /* Do Nothing */ ++ <666666666>, ++ <0>, /* Do Nothing */ ++ <0>, /* Do Nothing */ ++ <250000000>, ++ <0>; /* Do Nothing */ ++}; ++ + &saradc { + compatible = "amlogic,meson-gxbb-saradc", "amlogic,meson-saradc"; + clocks = <&xtal>, +@@ -761,4 +803,5 @@ + + &vpu { + compatible = "amlogic,meson-gxbb-vpu", "amlogic,meson-gx-vpu"; ++ power-domains = <&pwrc_vpu>; + }; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi +index 02b52b6..d5c8952 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi +@@ -721,6 +721,48 @@ + clock-names = "fast", "iface", "bclks", "mclk"; + }; + ++&pwrc_vpu { ++ resets = <&reset RESET_VIU>, ++ <&reset RESET_VENC>, ++ <&reset RESET_VCBUS>, ++ <&reset RESET_BT656>, ++ <&reset RESET_DVIN_RESET>, ++ <&reset RESET_RDMA>, ++ <&reset RESET_VENCI>, ++ <&reset RESET_VENCP>, ++ <&reset RESET_VDAC>, ++ <&reset RESET_VDI6>, ++ <&reset RESET_VENCL>, ++ <&reset RESET_VID_LOCK>; ++ clocks = <&clkc CLKID_VPU>, ++ <&clkc CLKID_VAPB>; ++ clock-names = "vpu", "vapb"; ++ /* ++ * VPU clocking is provided by two identical clock paths ++ * VPU_0 and VPU_1 muxed to a single clock by a glitch ++ * free mux to safely change frequency while running. ++ * Same for VAPB but with a final gate after the glitch free mux. ++ */ ++ assigned-clocks = <&clkc CLKID_VPU_0_SEL>, ++ <&clkc CLKID_VPU_0>, ++ <&clkc CLKID_VPU>, /* Glitch free mux */ ++ <&clkc CLKID_VAPB_0_SEL>, ++ <&clkc CLKID_VAPB_0>, ++ <&clkc CLKID_VAPB_SEL>; /* Glitch free mux */ ++ assigned-clock-parents = <&clkc CLKID_FCLK_DIV3>, ++ <0>, /* Do Nothing */ ++ <&clkc CLKID_VPU_0>, ++ <&clkc CLKID_FCLK_DIV4>, ++ <0>, /* Do Nothing */ ++ <&clkc CLKID_VAPB_0>; ++ assigned-clock-rates = <0>, /* Do Nothing */ ++ <666666666>, ++ <0>, /* Do Nothing */ ++ <0>, /* Do Nothing */ ++ <250000000>, ++ <0>; /* Do Nothing */ ++}; ++ + &saradc { + compatible = "amlogic,meson-gxl-saradc", "amlogic,meson-saradc"; + clocks = <&xtal>, +@@ -790,4 +832,5 @@ + + &vpu { + compatible = "amlogic,meson-gxl-vpu", "amlogic,meson-gx-vpu"; ++ power-domains = <&pwrc_vpu>; + }; +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0033-ARM64-dts-meson-gx-Add-HDMI_5V-regulator-on-selected.patch b/patch/kernel/meson64-dev/0033-ARM64-dts-meson-gx-Add-HDMI_5V-regulator-on-selected.patch new file mode 100644 index 0000000000..23a92ccff5 --- /dev/null +++ b/patch/kernel/meson64-dev/0033-ARM64-dts-meson-gx-Add-HDMI_5V-regulator-on-selected.patch @@ -0,0 +1,173 @@ +From eabcafafe127288c4e353ce666b0675c88f7fc6f Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Mon, 16 Oct 2017 15:33:30 +0200 +Subject: [PATCH 33/36] ARM64: dts: meson-gx: Add HDMI_5V regulator on selected + boards + +On reference boards and derivatives, the HDMI Logic is powered by an external +5V regulator. +This regulator was set by the Vendor U-Boot, add the regulator and phandle +property to the HDMI node. + +Signed-off-by: Neil Armstrong +--- + arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi | 12 ++++++++++++ + arch/arm64/boot/dts/amlogic/meson-gxl-s905d-p230.dts | 1 + + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts | 1 + + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 12 ++++++++++++ + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts | 1 + + arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi | 11 +++++++++++ + arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts | 12 ++++++++++++ + 7 files changed, 50 insertions(+) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi +index 7f59f30..979abaf 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi +@@ -59,6 +59,17 @@ + reg = <0x0 0x0 0x0 0x80000000>; + }; + ++ hdmi_5v: regulator-hdmi-5v { ++ compatible = "regulator-fixed"; ++ ++ regulator-name = "HDMI_5V"; ++ regulator-min-microvolt = <5000000>; ++ regulator-max-microvolt = <5000000>; ++ ++ gpio = <&gpio GPIOH_3 GPIO_ACTIVE_HIGH>; ++ enable-active-high; ++ }; ++ + vddio_boot: regulator-vddio_boot { + compatible = "regulator-fixed"; + regulator-name = "VDDIO_BOOT"; +@@ -142,6 +153,7 @@ + status = "okay"; + pinctrl-0 = <&hdmi_hpd_pins>, <&hdmi_i2c_pins>; + pinctrl-names = "default"; ++ hdmi-supply = <&hdmi_5v>; + }; + + &hdmi_tx_tmds_port { +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905d-p230.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905d-p230.dts +index 6827f23..8bc540e 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905d-p230.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905d-p230.dts +@@ -135,6 +135,7 @@ + status = "okay"; + pinctrl-0 = <&hdmi_hpd_pins>, <&hdmi_i2c_pins>; + pinctrl-names = "default"; ++ hdmi-supply = <&hdmi_5v>; + }; + + &hdmi_tx_tmds_port { +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts +index 89a5fd9..f7b37de 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts +@@ -78,6 +78,7 @@ + status = "okay"; + pinctrl-0 = <&hdmi_hpd_pins>, <&hdmi_i2c_pins>; + pinctrl-names = "default"; ++ hdmi-supply = <&hdmi_5v>; + }; + + &hdmi_tx_tmds_port { +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts +index 942fd70..0c4ed4e 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts +@@ -72,6 +72,17 @@ + reg = <0x0 0x0 0x0 0x80000000>; + }; + ++ hdmi_5v: regulator-hdmi-5v { ++ compatible = "regulator-fixed"; ++ ++ regulator-name = "HDMI_5V"; ++ regulator-min-microvolt = <5000000>; ++ regulator-max-microvolt = <5000000>; ++ ++ gpio = <&gpio GPIOH_3 GPIO_ACTIVE_HIGH>; ++ enable-active-high; ++ }; ++ + vcc_3v3: regulator-vcc_3v3 { + compatible = "regulator-fixed"; + regulator-name = "VCC_3V3"; +@@ -131,6 +142,7 @@ + status = "okay"; + pinctrl-0 = <&hdmi_hpd_pins>, <&hdmi_i2c_pins>; + pinctrl-names = "default"; ++ hdmi-supply = <&hdmi_5v>; + }; + + &hdmi_tx_tmds_port { +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts +index 6e2bf85..4f6b1c9 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts +@@ -88,6 +88,7 @@ + status = "okay"; + pinctrl-0 = <&hdmi_hpd_pins>, <&hdmi_i2c_pins>; + pinctrl-names = "default"; ++ hdmi-supply = <&hdmi_5v>; + }; + + &hdmi_tx_tmds_port { +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi +index 0a2be82..1a5136a 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi +@@ -28,6 +28,17 @@ + reg = <0x0 0x0 0x0 0x80000000>; + }; + ++ hdmi_5v: regulator-hdmi-5v { ++ compatible = "regulator-fixed"; ++ ++ regulator-name = "HDMI_5V"; ++ regulator-min-microvolt = <5000000>; ++ regulator-max-microvolt = <5000000>; ++ ++ gpio = <&gpio GPIOH_3 GPIO_ACTIVE_HIGH>; ++ enable-active-high; ++ }; ++ + vddio_boot: regulator-vddio_boot { + compatible = "regulator-fixed"; + regulator-name = "VDDIO_BOOT"; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts +index 103575a..4537a81 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts +@@ -153,6 +153,17 @@ + }; + }; + ++ hdmi_5v: regulator-hdmi-5v { ++ compatible = "regulator-fixed"; ++ ++ regulator-name = "HDMI_5V"; ++ regulator-min-microvolt = <5000000>; ++ regulator-max-microvolt = <5000000>; ++ ++ gpio = <&gpio GPIOH_3 GPIO_ACTIVE_HIGH>; ++ enable-active-high; ++ }; ++ + vcc_3v3: regulator-vcc_3v3 { + compatible = "regulator-fixed"; + regulator-name = "VCC_3V3"; +@@ -239,6 +250,7 @@ + status = "okay"; + pinctrl-0 = <&hdmi_hpd_pins>, <&hdmi_i2c_pins>; + pinctrl-names = "default"; ++ hdmi-supply = <&hdmi_5v>; + }; + + &hdmi_tx_tmds_port { +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0034-ARM64-dts-meson-gx-grow-reset-controller-memory-zone.patch b/patch/kernel/meson64-dev/0034-ARM64-dts-meson-gx-grow-reset-controller-memory-zone.patch new file mode 100644 index 0000000000..09b52f34a9 --- /dev/null +++ b/patch/kernel/meson64-dev/0034-ARM64-dts-meson-gx-grow-reset-controller-memory-zone.patch @@ -0,0 +1,29 @@ +From 9b5feb2460d4f7a2993145de3aef1292c6a09549 Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Mon, 16 Oct 2017 17:00:59 +0200 +Subject: [PATCH 34/36] ARM64: dts: meson-gx: grow reset controller memory zone + +Now the Amlogic Meson GX SoCs datasheet documents all the Reset registers, +grow the memory in the node to allow usage of the level registers. + +Signed-off-by: Neil Armstrong +--- + arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi +index ace0e4b..2e0ee17 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi +@@ -220,7 +220,7 @@ + + reset: reset-controller@4404 { + compatible = "amlogic,meson-gx-reset", "amlogic,meson-gxbb-reset"; +- reg = <0x0 0x04404 0x0 0x20>; ++ reg = <0x0 0x04404 0x0 0x9c>; + #reset-cells = <1>; + }; + +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0035-ARM64-dts-odroid-c2-Add-HDMI-and-CEC-Nodes.patch b/patch/kernel/meson64-dev/0035-ARM64-dts-odroid-c2-Add-HDMI-and-CEC-Nodes.patch new file mode 100644 index 0000000000..e8ca299d53 --- /dev/null +++ b/patch/kernel/meson64-dev/0035-ARM64-dts-odroid-c2-Add-HDMI-and-CEC-Nodes.patch @@ -0,0 +1,64 @@ +From 5221675b31e8a3c17a94c7f058c33d0751595c2b Mon Sep 17 00:00:00 2001 +From: Neil Armstrong +Date: Mon, 16 Oct 2017 17:00:26 +0200 +Subject: [PATCH 35/36] ARM64: dts: odroid-c2: Add HDMI and CEC Nodes + +Now the VPU Power Domain has been fixed while boothing from Mainline U-Boot, +VPU and HDMI nodes can finally be added to the Odroid-C2 DTS. + +Signed-off-by: Neil Armstrong +--- + .../arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts | 30 ++++++++++++++++++++++ + 1 file changed, 30 insertions(+) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts +index c2b6df4..896dfb3 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts +@@ -135,6 +135,24 @@ + compatible = "mmc-pwrseq-emmc"; + reset-gpios = <&gpio BOOT_9 GPIO_ACTIVE_LOW>; + }; ++ ++ hdmi-connector { ++ compatible = "hdmi-connector"; ++ type = "a"; ++ ++ port { ++ hdmi_connector_in: endpoint { ++ remote-endpoint = <&hdmi_tx_tmds_out>; ++ }; ++ }; ++ }; ++}; ++ ++&cec_AO { ++ status = "okay"; ++ pinctrl-0 = <&ao_cec_pins>; ++ pinctrl-names = "default"; ++ hdmi-phandle = <&hdmi_tx>; + }; + + ðmac { +@@ -177,6 +195,18 @@ + }; + }; + ++&hdmi_tx { ++ status = "okay"; ++ pinctrl-0 = <&hdmi_hpd_pins>, <&hdmi_i2c_pins>; ++ pinctrl-names = "default"; ++}; ++ ++&hdmi_tx_tmds_port { ++ hdmi_tx_tmds_out: endpoint { ++ remote-endpoint = <&hdmi_connector_in>; ++ }; ++}; ++ + &i2c_A { + status = "okay"; + pinctrl-0 = <&i2c_a_pins>; +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/0036-ARM64-dts-meson-activate-hdmi-audio-HDMI-enabled-boa.patch b/patch/kernel/meson64-dev/0036-ARM64-dts-meson-activate-hdmi-audio-HDMI-enabled-boa.patch new file mode 100644 index 0000000000..46f5281a64 --- /dev/null +++ b/patch/kernel/meson64-dev/0036-ARM64-dts-meson-activate-hdmi-audio-HDMI-enabled-boa.patch @@ -0,0 +1,637 @@ +From db733b2bb5e2e26e1d977953c7c71b8986368cd7 Mon Sep 17 00:00:00 2001 +From: Jerome Brunet +Date: Wed, 20 Sep 2017 18:10:08 +0200 +Subject: [PATCH 36/36] ARM64: dts: meson: activate hdmi audio HDMI enabled + boards + +This patch activate audio over HDMI on selected boards + +Please note that this audio support is based on WIP changes +This should be considered as preview and it does not reflect +the audio I expect to see merged + +Signed-off-by: Jerome Brunet +Signed-off-by: Neil Armstrong +--- + .../arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi | 37 +++++++++++++++++++++ + .../boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts | 38 ++++++++++++++++++++++ + .../arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts | 37 +++++++++++++++++++++ + arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi | 37 +++++++++++++++++++++ + .../boot/dts/amlogic/meson-gxbb-wetek-play2.dts | 37 +++++++++++++++++++++ + .../dts/amlogic/meson-gxl-s905x-khadas-vim.dts | 37 +++++++++++++++++++++ + .../dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 37 +++++++++++++++++++++ + .../dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts | 37 +++++++++++++++++++++ + .../boot/dts/amlogic/meson-gxl-s905x-p212.dts | 37 +++++++++++++++++++++ + .../boot/dts/amlogic/meson-gxm-khadas-vim2.dts | 37 +++++++++++++++++++++ + .../arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts | 37 +++++++++++++++++++++ + 11 files changed, 408 insertions(+) + +diff --git a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi +index 979abaf..91b7ac8 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi +@@ -130,6 +130,31 @@ + }; + }; + }; ++ ++ sound { ++ compatible = "simple-audio-card"; ++ simple-audio-card,name = "meson-gx-preview"; ++ status = "okay"; ++ ++ simple-audio-card,dai-link@0 { ++ /* HDMI Output */ ++ format = "i2s"; ++ mclk-fs = <256>; ++ bitclock-master = <&i2s_dai>; ++ frame-master = <&i2s_dai>; ++ plat { ++ sound-dai = <&aiu_i2s_dma>; ++ }; ++ ++ cpu { ++ sound-dai = <&i2s_dai>; ++ }; ++ ++ codec { ++ sound-dai = <&hdmi_tx>; ++ }; ++ }; ++ }; + }; + + &cec_AO { +@@ -139,6 +164,18 @@ + hdmi-phandle = <&hdmi_tx>; + }; + ++&audio { ++ status = "okay"; ++}; ++ ++&aiu_i2s_dma { ++ status = "okay"; ++}; ++ ++&i2s_dai { ++ status = "okay"; ++}; ++ + &cvbs_vdac_port { + cvbs_vdac_out: endpoint { + remote-endpoint = <&cvbs_connector_in>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts +index 9a77323..2357a38 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts +@@ -143,6 +143,31 @@ + clock-names = "ext_clock"; + }; + ++ sound { ++ compatible = "simple-audio-card"; ++ simple-audio-card,name = "meson-gx-preview"; ++ status = "okay"; ++ ++ simple-audio-card,dai-link@0 { ++ /* HDMI Output */ ++ format = "i2s"; ++ mclk-fs = <256>; ++ bitclock-master = <&i2s_dai>; ++ frame-master = <&i2s_dai>; ++ plat { ++ sound-dai = <&aiu_i2s_dma>; ++ }; ++ ++ cpu { ++ sound-dai = <&i2s_dai>; ++ }; ++ ++ codec { ++ sound-dai = <&hdmi_tx>; ++ }; ++ }; ++ }; ++ + cvbs-connector { + compatible = "composite-video-connector"; + +@@ -178,6 +203,19 @@ + hdmi-phandle = <&hdmi_tx>; + }; + ++ ++&audio { ++ status = "okay"; ++}; ++ ++&aiu_i2s_dma { ++ status = "okay"; ++}; ++ ++&i2s_dai { ++ status = "okay"; ++}; ++ + ðmac { + status = "okay"; + pinctrl-0 = <ð_rmii_pins>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts +index 896dfb3..0e076da 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts +@@ -146,6 +146,31 @@ + }; + }; + }; ++ ++ sound { ++ compatible = "simple-audio-card"; ++ simple-audio-card,name = "meson-gx-preview"; ++ status = "okay"; ++ ++ simple-audio-card,dai-link@0 { ++ /* HDMI Output */ ++ format = "i2s"; ++ mclk-fs = <256>; ++ bitclock-master = <&i2s_dai>; ++ frame-master = <&i2s_dai>; ++ plat { ++ sound-dai = <&aiu_i2s_dma>; ++ }; ++ ++ cpu { ++ sound-dai = <&i2s_dai>; ++ }; ++ ++ codec { ++ sound-dai = <&hdmi_tx>; ++ }; ++ }; ++ }; + }; + + &cec_AO { +@@ -155,6 +180,18 @@ + hdmi-phandle = <&hdmi_tx>; + }; + ++&audio { ++ status = "okay"; ++}; ++ ++&aiu_i2s_dma { ++ status = "okay"; ++}; ++ ++&i2s_dai { ++ status = "okay"; ++}; ++ + ðmac { + status = "okay"; + pinctrl-0 = <ð_rgmii_pins>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi +index 932158a..c9d4870 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi +@@ -149,6 +149,31 @@ + }; + }; + }; ++ ++ sound { ++ compatible = "simple-audio-card"; ++ simple-audio-card,name = "meson-gx-preview"; ++ status = "okay"; ++ ++ simple-audio-card,dai-link@0 { ++ /* HDMI Output */ ++ format = "i2s"; ++ mclk-fs = <256>; ++ bitclock-master = <&i2s_dai>; ++ frame-master = <&i2s_dai>; ++ plat { ++ sound-dai = <&aiu_i2s_dma>; ++ }; ++ ++ cpu { ++ sound-dai = <&i2s_dai>; ++ }; ++ ++ codec { ++ sound-dai = <&hdmi_tx>; ++ }; ++ }; ++ }; + }; + + &cec_AO { +@@ -158,6 +183,18 @@ + hdmi-phandle = <&hdmi_tx>; + }; + ++&audio { ++ status = "okay"; ++}; ++ ++&aiu_i2s_dma { ++ status = "okay"; ++}; ++ ++&i2s_dai { ++ status = "okay"; ++}; ++ + &cvbs_vdac_port { + cvbs_vdac_out: endpoint { + remote-endpoint = <&cvbs_connector_in>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-play2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-play2.dts +index f7144fd..58a0f51 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-play2.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-play2.dts +@@ -106,6 +106,31 @@ + }; + }; + }; ++ ++ sound { ++ compatible = "simple-audio-card"; ++ simple-audio-card,name = "meson-gx-preview"; ++ status = "okay"; ++ ++ simple-audio-card,dai-link@0 { ++ /* HDMI Output */ ++ format = "i2s"; ++ mclk-fs = <256>; ++ bitclock-master = <&i2s_dai>; ++ frame-master = <&i2s_dai>; ++ plat { ++ sound-dai = <&aiu_i2s_dma>; ++ }; ++ ++ cpu { ++ sound-dai = <&i2s_dai>; ++ }; ++ ++ codec { ++ sound-dai = <&hdmi_tx>; ++ }; ++ }; ++ }; + }; + + &cec_AO { +@@ -115,6 +140,18 @@ + hdmi-phandle = <&hdmi_tx>; + }; + ++&audio { ++ status = "okay"; ++}; ++ ++&aiu_i2s_dma { ++ status = "okay"; ++}; ++ ++&i2s_dai { ++ status = "okay"; ++}; ++ + &cvbs_vdac_port { + cvbs_vdac_out: endpoint { + remote-endpoint = <&cvbs_connector_in>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts +index f7b37de..ce92ca5 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts +@@ -65,6 +65,31 @@ + }; + }; + }; ++ ++ sound { ++ compatible = "simple-audio-card"; ++ simple-audio-card,name = "meson-gx-preview"; ++ status = "okay"; ++ ++ simple-audio-card,dai-link@0 { ++ /* HDMI Output */ ++ format = "i2s"; ++ mclk-fs = <256>; ++ bitclock-master = <&i2s_dai>; ++ frame-master = <&i2s_dai>; ++ plat { ++ sound-dai = <&aiu_i2s_dma>; ++ }; ++ ++ cpu { ++ sound-dai = <&i2s_dai>; ++ }; ++ ++ codec { ++ sound-dai = <&hdmi_tx>; ++ }; ++ }; ++ }; + }; + + &cec_AO { +@@ -74,6 +99,18 @@ + hdmi-phandle = <&hdmi_tx>; + }; + ++&audio { ++ status = "okay"; ++}; ++ ++&aiu_i2s_dma { ++ status = "okay"; ++}; ++ ++&i2s_dai { ++ status = "okay"; ++}; ++ + &hdmi_tx { + status = "okay"; + pinctrl-0 = <&hdmi_hpd_pins>, <&hdmi_i2c_pins>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts +index 0c4ed4e..29d8e01 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts +@@ -83,6 +83,31 @@ + enable-active-high; + }; + ++ sound { ++ compatible = "simple-audio-card"; ++ simple-audio-card,name = "meson-gx-preview"; ++ status = "okay"; ++ ++ simple-audio-card,dai-link@0 { ++ /* HDMI Output */ ++ format = "i2s"; ++ mclk-fs = <256>; ++ bitclock-master = <&i2s_dai>; ++ frame-master = <&i2s_dai>; ++ plat { ++ sound-dai = <&aiu_i2s_dma>; ++ }; ++ ++ cpu { ++ sound-dai = <&i2s_dai>; ++ }; ++ ++ codec { ++ sound-dai = <&hdmi_tx>; ++ }; ++ }; ++ }; ++ + vcc_3v3: regulator-vcc_3v3 { + compatible = "regulator-fixed"; + regulator-name = "VCC_3V3"; +@@ -122,6 +147,18 @@ + hdmi-phandle = <&hdmi_tx>; + }; + ++&audio { ++ status = "okay"; ++}; ++ ++&aiu_i2s_dma { ++ status = "okay"; ++}; ++ ++&i2s_dai { ++ status = "okay"; ++}; ++ + &cvbs_vdac_port { + cvbs_vdac_out: endpoint { + remote-endpoint = <&cvbs_connector_in>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts +index 0fdebcc..dcb571a 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts +@@ -138,6 +138,31 @@ + }; + }; + }; ++ ++ sound { ++ compatible = "simple-audio-card"; ++ simple-audio-card,name = "meson-gx-preview"; ++ status = "okay"; ++ ++ simple-audio-card,dai-link@0 { ++ /* HDMI Output */ ++ format = "i2s"; ++ mclk-fs = <256>; ++ bitclock-master = <&i2s_dai>; ++ frame-master = <&i2s_dai>; ++ plat { ++ sound-dai = <&aiu_i2s_dma>; ++ }; ++ ++ cpu { ++ sound-dai = <&i2s_dai>; ++ }; ++ ++ codec { ++ sound-dai = <&hdmi_tx>; ++ }; ++ }; ++ }; + }; + + &cec_AO { +@@ -147,6 +172,18 @@ + hdmi-phandle = <&hdmi_tx>; + }; + ++&audio { ++ status = "okay"; ++}; ++ ++&aiu_i2s_dma { ++ status = "okay"; ++}; ++ ++&i2s_dai { ++ status = "okay"; ++}; ++ + &cvbs_vdac_port { + cvbs_vdac_out: endpoint { + remote-endpoint = <&cvbs_connector_in>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts +index 4f6b1c9..f23f148 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts +@@ -69,6 +69,31 @@ + }; + }; + }; ++ ++ sound { ++ compatible = "simple-audio-card"; ++ simple-audio-card,name = "meson-gx-preview"; ++ status = "okay"; ++ ++ simple-audio-card,dai-link@0 { ++ /* HDMI Output */ ++ format = "i2s"; ++ mclk-fs = <256>; ++ bitclock-master = <&i2s_dai>; ++ frame-master = <&i2s_dai>; ++ plat { ++ sound-dai = <&aiu_i2s_dma>; ++ }; ++ ++ cpu { ++ sound-dai = <&i2s_dai>; ++ }; ++ ++ codec { ++ sound-dai = <&hdmi_tx>; ++ }; ++ }; ++ }; + }; + + &cec_AO { +@@ -78,6 +103,18 @@ + hdmi-phandle = <&hdmi_tx>; + }; + ++&audio { ++ status = "okay"; ++}; ++ ++&aiu_i2s_dma { ++ status = "okay"; ++}; ++ ++&i2s_dai { ++ status = "okay"; ++}; ++ + &cvbs_vdac_port { + cvbs_vdac_out: endpoint { + remote-endpoint = <&cvbs_connector_in>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts +index 4537a81..aed2a54 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts +@@ -88,6 +88,31 @@ + }; + }; + ++ sound { ++ compatible = "simple-audio-card"; ++ simple-audio-card,name = "meson-gx-preview"; ++ status = "okay"; ++ ++ simple-audio-card,dai-link@0 { ++ /* HDMI Output */ ++ format = "i2s"; ++ mclk-fs = <256>; ++ bitclock-master = <&i2s_dai>; ++ frame-master = <&i2s_dai>; ++ plat { ++ sound-dai = <&aiu_i2s_dma>; ++ }; ++ ++ cpu { ++ sound-dai = <&i2s_dai>; ++ }; ++ ++ codec { ++ sound-dai = <&hdmi_tx>; ++ }; ++ }; ++ }; ++ + pwmleds { + compatible = "pwm-leds"; + +@@ -207,6 +232,18 @@ + hdmi-phandle = <&hdmi_tx>; + }; + ++&audio { ++ status = "okay"; ++}; ++ ++&aiu_i2s_dma { ++ status = "okay"; ++}; ++ ++&i2s_dai { ++ status = "okay"; ++}; ++ + &cpu0 { + cooling-min-level = <0>; + cooling-max-level = <6>; +diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts +index e70b5e2..8444f79 100644 +--- a/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts ++++ b/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts +@@ -111,6 +111,31 @@ + }; + }; + }; ++ ++ sound { ++ compatible = "simple-audio-card"; ++ simple-audio-card,name = "meson-gx-preview"; ++ status = "okay"; ++ ++ simple-audio-card,dai-link@0 { ++ /* HDMI Output */ ++ format = "i2s"; ++ mclk-fs = <256>; ++ bitclock-master = <&i2s_dai>; ++ frame-master = <&i2s_dai>; ++ plat { ++ sound-dai = <&aiu_i2s_dma>; ++ }; ++ ++ cpu { ++ sound-dai = <&i2s_dai>; ++ }; ++ ++ codec { ++ sound-dai = <&hdmi_tx>; ++ }; ++ }; ++ }; + }; + + &cec_AO { +@@ -120,6 +145,18 @@ + hdmi-phandle = <&hdmi_tx>; + }; + ++&audio { ++ status = "okay"; ++}; ++ ++&aiu_i2s_dma { ++ status = "okay"; ++}; ++ ++&i2s_dai { ++ status = "okay"; ++}; ++ + &cvbs_vdac_port { + cvbs_vdac_out: endpoint { + remote-endpoint = <&cvbs_connector_in>; +-- +2.7.4 + diff --git a/patch/kernel/meson64-dev/1003-ARM64-dts-meson-gx-Enable-USB-on-GXL-and-GXM-boards.patch b/patch/kernel/meson64-dev/1003-ARM64-dts-meson-gx-Enable-USB-on-GXL-and-GXM-boards.patch deleted file mode 100644 index 600e80f2c2..0000000000 --- a/patch/kernel/meson64-dev/1003-ARM64-dts-meson-gx-Enable-USB-on-GXL-and-GXM-boards.patch +++ /dev/null @@ -1,64 +0,0 @@ -From 7079f88717e54f9ea48c1cbfba09b53cc8b9aefd Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Thu, 13 Jul 2017 15:02:33 +0200 -Subject: [PATCH 77/79] ARM64: dts: meson-gx: Enable USB on GXL and GXM boards - -Signed-off-by: Neil Armstrong ---- - arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi | 4 ++++ - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts | 4 ++++ - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi | 4 ++++ - arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts | 4 ++++ - 4 files changed, 16 insertions(+) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi -index 54718ee..bf49f6f 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi -@@ -234,3 +234,7 @@ - remote-endpoint = <&hdmi_connector_in>; - }; - }; -+ -+&usb0 { -+ status = "okay"; -+}; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts -index 55ec11a..19bb39b 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts -@@ -249,3 +249,7 @@ - remote-endpoint = <&hdmi_connector_in>; - }; - }; -+ -+&usb0 { -+ status = "okay"; -+}; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi -index f3eea8e..a07c34d 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi -@@ -171,3 +171,7 @@ - pinctrl-0 = <&uart_ao_a_pins>; - pinctrl-names = "default"; - }; -+ -+&usb0 { -+ status = "okay"; -+}; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts -index 3a327dd..1b7038d 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts -@@ -215,3 +215,7 @@ - remote-endpoint = <&hdmi_connector_in>; - }; - }; -+ -+&usb0 { -+ status = "okay"; -+}; --- -1.9.1 - diff --git a/patch/kernel/meson64-dev/1005_USB_Adjust_for_4.13.patch b/patch/kernel/meson64-dev/1005_USB_Adjust_for_4.13.patch deleted file mode 100644 index 4ee08e7878..0000000000 --- a/patch/kernel/meson64-dev/1005_USB_Adjust_for_4.13.patch +++ /dev/null @@ -1,27 +0,0 @@ -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts -index 3f0d83b..7590383 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts -@@ -129,6 +129,10 @@ - }; - }; - -+&usb0 { -+ status = "okay"; -+}; -+ - /* SD card */ - &sd_emmc_b { - status = "okay"; -diff --git a/drivers/phy/Makefile b/drivers/phy/Makefile -index f252201..10b2165 100644 ---- a/drivers/phy/Makefile -+++ b/drivers/phy/Makefile -@@ -6,6 +6,7 @@ obj-$(CONFIG_GENERIC_PHY) += phy-core.o - obj-$(CONFIG_PHY_LPC18XX_USB_OTG) += phy-lpc18xx-usb-otg.o - obj-$(CONFIG_PHY_XGENE) += phy-xgene.o - obj-$(CONFIG_PHY_PISTACHIO_USB) += phy-pistachio-usb.o -+obj-$(CONFIG_PHY_MESON_GXL_USB) += phy-meson-gxl-usb2.o - obj-$(CONFIG_ARCH_SUNXI) += allwinner/ - obj-$(CONFIG_ARCH_MESON) += amlogic/ - obj-$(CONFIG_LANTIQ) += lantiq/ diff --git a/patch/kernel/meson64-dev/1021_ATF_memory_allocation_meson_GX.patch b/patch/kernel/meson64-dev/1020_GXBB_memory_allocation_meson_GX.patch similarity index 100% rename from patch/kernel/meson64-dev/1021_ATF_memory_allocation_meson_GX.patch rename to patch/kernel/meson64-dev/1020_GXBB_memory_allocation_meson_GX.patch diff --git a/patch/kernel/meson64-dev/1020_Meson-GXL_ATF_Reserved_Memory_Fix.patch b/patch/kernel/meson64-dev/1020_Meson-GXL_ATF_Reserved_Memory_Fix.patch deleted file mode 100644 index 385102aeeb..0000000000 --- a/patch/kernel/meson64-dev/1020_Meson-GXL_ATF_Reserved_Memory_Fix.patch +++ /dev/null @@ -1,18 +0,0 @@ -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -index 28958f2..a42b90d 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -50,6 +50,13 @@ - / { - compatible = "amlogic,meson-gxl"; - -+ reserved-memory { -+ /* Alternate 3 MiB reserved for ARM Trusted Firmware (BL31) */ -+ secmon_reserved_alt: secmon@05000000 { -+ reg = <0x0 0x05000000 0x0 0x300000>; -+ no-map; -+ }; -+ }; - soc { - - usb0: usb@c9000000 {