diff --git a/Documentation/kernel.md b/Documentation/kernel.md index 593601402..a5fc74b85 100644 --- a/Documentation/kernel.md +++ b/Documentation/kernel.md @@ -6,7 +6,7 @@ | Open Virtual Applicance | 4.14.82 | | Raspberry Pi | 4.14.81 | | Tinker Board | 4.14.82 | -| Odroid-C2 | 4.18.20 | +| Odroid-C2 | 4.19.15 | | Odroid-XU4 | 4.19.15 | | Orangepi-Prime | 4.19.13 | | Intel NUC | 4.14.82 | diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/README b/buildroot-external/board/hardkernel/odroid-c2/patches/README deleted file mode 100644 index 0eafac24c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/README +++ /dev/null @@ -1,2 +0,0 @@ -kernel patches from scpcom -https://forum.odroid.com/viewtopic.php?f=135&t=22717&start=900#p233963 diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/000_arm64-set-default-target-to-Image.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/000_arm64-set-default-target-to-Image.patch deleted file mode 100644 index 51bf570c2..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/000_arm64-set-default-target-to-Image.patch +++ /dev/null @@ -1,13 +0,0 @@ -diff --git a/arch/arm64/Makefile b/arch/arm64/Makefile -index f839ecd9..cd276162 100644 ---- a/arch/arm64/Makefile -+++ b/arch/arm64/Makefile -@@ -103,7 +103,7 @@ core-$(CONFIG_EFI_STUB) += $(objtree)/drivers/firmware/efi/libstub/lib.a - - # Default target when executing plain make - boot := arch/arm64/boot --KBUILD_IMAGE := $(boot)/Image.gz -+KBUILD_IMAGE := $(boot)/Image - KBUILD_DTBS := dtbs - - all: Image.gz $(KBUILD_DTBS) diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/001_linux-4.18.y-v4l-0001-dt-bindings-soc-amlogic-add_meson-canvas_documentation.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/001_linux-4.18.y-v4l-0001-dt-bindings-soc-amlogic-add_meson-canvas_documentation.patch deleted file mode 100644 index 8e0675a2b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/001_linux-4.18.y-v4l-0001-dt-bindings-soc-amlogic-add_meson-canvas_documentation.patch +++ /dev/null @@ -1,49 +0,0 @@ -From 4796e434b5785e3d9f95e988363c407b1e09bb91 Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Sat, 28 Jul 2018 22:40:27 +0200 -Subject: [PATCH] dt-bindings: soc: amlogic: add meson-canvas documentation - -DT bindings doc for amlogic,meson-canvas - -Reviewed-by: Jerome Brunet -Signed-off-by: Maxime Jourdan ---- - .../bindings/soc/amlogic/amlogic,canvas.txt | 29 +++++++++++++++++++ - 1 file changed, 29 insertions(+) - create mode 100644 Documentation/devicetree/bindings/soc/amlogic/amlogic,canvas.txt - -diff --git a/Documentation/devicetree/bindings/soc/amlogic/amlogic,canvas.txt b/Documentation/devicetree/bindings/soc/amlogic/amlogic,canvas.txt -new file mode 100644 -index 0000000000000..436d2106e80da ---- /dev/null -+++ b/Documentation/devicetree/bindings/soc/amlogic/amlogic,canvas.txt -@@ -0,0 +1,29 @@ -+Amlogic Canvas -+================================ -+ -+A canvas is a collection of metadata that describes a pixel buffer. -+Those metadata include: width, height, phyaddr, wrapping, block mode -+and endianness. -+ -+Many IPs within Amlogic SoCs rely on canvas indexes to read/write pixel data -+rather than use the phy addresses directly. For instance, this is the case for -+the video decoders and the display. -+ -+Amlogic SoCs have 256 canvas. -+ -+Device Tree Bindings: -+--------------------- -+ -+Video Lookup Table -+-------------------------- -+ -+Required properties: -+- compatible: "amlogic,canvas" -+- reg: Base physical address and size of the canvas registers. -+ -+Example: -+ -+canvas: video-lut@48 { -+ compatible = "amlogic,canvas"; -+ reg = <0x0 0x48 0x0 0x14>; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/002_linux-4.18.y-v4l-0002-soc-amlogic-add_meson-canvas_driver.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/002_linux-4.18.y-v4l-0002-soc-amlogic-add_meson-canvas_driver.patch deleted file mode 100644 index e09fd826d..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/002_linux-4.18.y-v4l-0002-soc-amlogic-add_meson-canvas_driver.patch +++ /dev/null @@ -1,313 +0,0 @@ -From 21c3e7d31208b0c4fb4a6c0a8c52e6820a40596a Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Fri, 20 Apr 2018 13:17:07 +0200 -Subject: [PATCH] soc: amlogic: add meson-canvas driver - -Amlogic SoCs have a repository of 256 canvas which they use to -describe pixel buffers. - -They contain metadata like width, height, block mode, endianness [..] - -Many IPs within those SoCs like vdec/vpu rely on those canvas to read/write -pixels. - -Reviewed-by: Jerome Brunet -Tested-by: Neil Armstrong -Signed-off-by: Maxime Jourdan ---- - drivers/soc/amlogic/Kconfig | 7 + - drivers/soc/amlogic/Makefile | 1 + - drivers/soc/amlogic/meson-canvas.c | 185 +++++++++++++++++++++++ - include/linux/soc/amlogic/meson-canvas.h | 65 ++++++++ - 4 files changed, 258 insertions(+) - create mode 100644 drivers/soc/amlogic/meson-canvas.c - create mode 100644 include/linux/soc/amlogic/meson-canvas.h - -diff --git a/drivers/soc/amlogic/Kconfig b/drivers/soc/amlogic/Kconfig -index b04f6e4aedbc1..2f282b4729120 100644 ---- a/drivers/soc/amlogic/Kconfig -+++ b/drivers/soc/amlogic/Kconfig -@@ -1,5 +1,12 @@ - menu "Amlogic SoC drivers" - -+config MESON_CANVAS -+ tristate "Amlogic Meson Canvas driver" -+ depends on ARCH_MESON || COMPILE_TEST -+ default n -+ help -+ Say yes to support the canvas IP for Amlogic SoCs. -+ - config MESON_GX_SOCINFO - bool "Amlogic Meson GX SoC Information driver" - depends on ARCH_MESON || COMPILE_TEST -diff --git a/drivers/soc/amlogic/Makefile b/drivers/soc/amlogic/Makefile -index 8fa321893928d..0ab16d35ac36d 100644 ---- a/drivers/soc/amlogic/Makefile -+++ b/drivers/soc/amlogic/Makefile -@@ -1,3 +1,4 @@ -+obj-$(CONFIG_MESON_CANVAS) += meson-canvas.o - obj-$(CONFIG_MESON_GX_SOCINFO) += meson-gx-socinfo.o - obj-$(CONFIG_MESON_GX_PM_DOMAINS) += meson-gx-pwrc-vpu.o - obj-$(CONFIG_MESON_MX_SOCINFO) += meson-mx-socinfo.o -diff --git a/drivers/soc/amlogic/meson-canvas.c b/drivers/soc/amlogic/meson-canvas.c -new file mode 100644 -index 0000000000000..fce33ca76bb62 ---- /dev/null -+++ b/drivers/soc/amlogic/meson-canvas.c -@@ -0,0 +1,185 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Copyright (C) 2015 Amlogic, Inc. All rights reserved. -+ * Copyright (C) 2014 Endless Mobile -+ */ -+ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#define NUM_CANVAS 256 -+ -+/* DMC Registers */ -+#define DMC_CAV_LUT_DATAL 0x00 -+ #define CANVAS_WIDTH_LBIT 29 -+ #define CANVAS_WIDTH_LWID 3 -+#define DMC_CAV_LUT_DATAH 0x04 -+ #define CANVAS_WIDTH_HBIT 0 -+ #define CANVAS_HEIGHT_BIT 9 -+ #define CANVAS_WRAP_BIT 22 -+ #define CANVAS_BLKMODE_BIT 24 -+ #define CANVAS_ENDIAN_BIT 26 -+#define DMC_CAV_LUT_ADDR 0x08 -+ #define CANVAS_LUT_WR_EN BIT(9) -+ #define CANVAS_LUT_RD_EN BIT(8) -+ -+struct meson_canvas { -+ struct device *dev; -+ void __iomem *reg_base; -+ spinlock_t lock; /* canvas device lock */ -+ u8 used[NUM_CANVAS]; -+}; -+ -+static void canvas_write(struct meson_canvas *canvas, u32 reg, u32 val) -+{ -+ writel_relaxed(val, canvas->reg_base + reg); -+} -+ -+static u32 canvas_read(struct meson_canvas *canvas, u32 reg) -+{ -+ return readl_relaxed(canvas->reg_base + reg); -+} -+ -+struct meson_canvas *meson_canvas_get(struct device *dev) -+{ -+ struct device_node *canvas_node; -+ struct platform_device *canvas_pdev; -+ -+ canvas_node = of_parse_phandle(dev->of_node, "amlogic,canvas", 0); -+ if (!canvas_node) -+ return ERR_PTR(-ENODEV); -+ -+ canvas_pdev = of_find_device_by_node(canvas_node); -+ if (!canvas_pdev) -+ return ERR_PTR(-EPROBE_DEFER); -+ -+ return dev_get_drvdata(&canvas_pdev->dev); -+} -+EXPORT_SYMBOL_GPL(meson_canvas_get); -+ -+int meson_canvas_config(struct meson_canvas *canvas, u8 canvas_index, -+ u32 addr, u32 stride, u32 height, -+ unsigned int wrap, -+ unsigned int blkmode, -+ unsigned int endian) -+{ -+ unsigned long flags; -+ -+ spin_lock_irqsave(&canvas->lock, flags); -+ if (!canvas->used[canvas_index]) { -+ dev_err(canvas->dev, -+ "Trying to setup non allocated canvas %u\n", -+ canvas_index); -+ spin_unlock_irqrestore(&canvas->lock, flags); -+ return -EINVAL; -+ } -+ -+ canvas_write(canvas, DMC_CAV_LUT_DATAL, -+ ((addr + 7) >> 3) | -+ (((stride + 7) >> 3) << CANVAS_WIDTH_LBIT)); -+ -+ canvas_write(canvas, DMC_CAV_LUT_DATAH, -+ ((((stride + 7) >> 3) >> CANVAS_WIDTH_LWID) << -+ CANVAS_WIDTH_HBIT) | -+ (height << CANVAS_HEIGHT_BIT) | -+ (wrap << CANVAS_WRAP_BIT) | -+ (blkmode << CANVAS_BLKMODE_BIT) | -+ (endian << CANVAS_ENDIAN_BIT)); -+ -+ canvas_write(canvas, DMC_CAV_LUT_ADDR, -+ CANVAS_LUT_WR_EN | canvas_index); -+ -+ /* Force a read-back to make sure everything is flushed. */ -+ canvas_read(canvas, DMC_CAV_LUT_DATAH); -+ spin_unlock_irqrestore(&canvas->lock, flags); -+ -+ return 0; -+} -+EXPORT_SYMBOL_GPL(meson_canvas_config); -+ -+int meson_canvas_alloc(struct meson_canvas *canvas, u8 *canvas_index) -+{ -+ int i; -+ unsigned long flags; -+ -+ spin_lock_irqsave(&canvas->lock, flags); -+ for (i = 0; i < NUM_CANVAS; ++i) { -+ if (!canvas->used[i]) { -+ canvas->used[i] = 1; -+ spin_unlock_irqrestore(&canvas->lock, flags); -+ *canvas_index = i; -+ return 0; -+ } -+ } -+ spin_unlock_irqrestore(&canvas->lock, flags); -+ -+ dev_err(canvas->dev, "No more canvas available\n"); -+ return -ENODEV; -+} -+EXPORT_SYMBOL_GPL(meson_canvas_alloc); -+ -+int meson_canvas_free(struct meson_canvas *canvas, u8 canvas_index) -+{ -+ unsigned long flags; -+ -+ spin_lock_irqsave(&canvas->lock, flags); -+ if (!canvas->used[canvas_index]) { -+ dev_err(canvas->dev, -+ "Trying to free unused canvas %u\n", canvas_index); -+ spin_unlock_irqrestore(&canvas->lock, flags); -+ return -EINVAL; -+ } -+ canvas->used[canvas_index] = 0; -+ spin_unlock_irqrestore(&canvas->lock, flags); -+ -+ return 0; -+} -+EXPORT_SYMBOL_GPL(meson_canvas_free); -+ -+static int meson_canvas_probe(struct platform_device *pdev) -+{ -+ struct resource *res; -+ struct meson_canvas *canvas; -+ struct device *dev = &pdev->dev; -+ -+ canvas = devm_kzalloc(dev, sizeof(*canvas), GFP_KERNEL); -+ if (!canvas) -+ return -ENOMEM; -+ -+ res = platform_get_resource(pdev, IORESOURCE_MEM, 0); -+ canvas->reg_base = devm_ioremap_resource(dev, res); -+ if (IS_ERR(canvas->reg_base)) -+ return PTR_ERR(canvas->reg_base); -+ -+ canvas->dev = dev; -+ spin_lock_init(&canvas->lock); -+ dev_set_drvdata(dev, canvas); -+ -+ return 0; -+} -+ -+static const struct of_device_id canvas_dt_match[] = { -+ { .compatible = "amlogic,canvas" }, -+ {} -+}; -+MODULE_DEVICE_TABLE(of, canvas_dt_match); -+ -+static struct platform_driver meson_canvas_driver = { -+ .probe = meson_canvas_probe, -+ .driver = { -+ .name = "amlogic-canvas", -+ .of_match_table = canvas_dt_match, -+ }, -+}; -+module_platform_driver(meson_canvas_driver); -+ -+MODULE_DESCRIPTION("Amlogic Canvas driver"); -+MODULE_AUTHOR("Maxime Jourdan "); -+MODULE_LICENSE("GPL"); -diff --git a/include/linux/soc/amlogic/meson-canvas.h b/include/linux/soc/amlogic/meson-canvas.h -new file mode 100644 -index 0000000000000..b4dde2fbeb3fb ---- /dev/null -+++ b/include/linux/soc/amlogic/meson-canvas.h -@@ -0,0 +1,65 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ */ -+#ifndef __SOC_MESON_CANVAS_H -+#define __SOC_MESON_CANVAS_H -+ -+#include -+ -+#define MESON_CANVAS_WRAP_NONE 0x00 -+#define MESON_CANVAS_WRAP_X 0x01 -+#define MESON_CANVAS_WRAP_Y 0x02 -+ -+#define MESON_CANVAS_BLKMODE_LINEAR 0x00 -+#define MESON_CANVAS_BLKMODE_32x32 0x01 -+#define MESON_CANVAS_BLKMODE_64x64 0x02 -+ -+#define MESON_CANVAS_ENDIAN_SWAP16 0x1 -+#define MESON_CANVAS_ENDIAN_SWAP32 0x3 -+#define MESON_CANVAS_ENDIAN_SWAP64 0x7 -+#define MESON_CANVAS_ENDIAN_SWAP128 0xf -+ -+struct meson_canvas; -+ -+/** -+ * meson_canvas_get() - get a canvas provider instance -+ * -+ * @dev: consumer device pointer -+ */ -+struct meson_canvas *meson_canvas_get(struct device *dev); -+ -+/** -+ * meson_canvas_alloc() - take ownership of a canvas -+ * -+ * @canvas: canvas provider instance retrieved from meson_canvas_get() -+ * @canvas_index: will be filled with the canvas ID -+ */ -+int meson_canvas_alloc(struct meson_canvas *canvas, u8 *canvas_index); -+ -+/** -+ * meson_canvas_free() - remove ownership from a canvas -+ * -+ * @canvas: canvas provider instance retrieved from meson_canvas_get() -+ * @canvas_index: canvas ID that was obtained via meson_canvas_alloc() -+ */ -+int meson_canvas_free(struct meson_canvas *canvas, u8 canvas_index); -+ -+/** -+ * meson_canvas_config() - configure a canvas -+ * -+ * @canvas: canvas provider instance retrieved from meson_canvas_get() -+ * @canvas_index: canvas ID that was obtained via meson_canvas_alloc() -+ * @addr: physical address to the pixel buffer -+ * @stride: width of the buffer -+ * @height: height of the buffer -+ * @wrap: undocumented -+ * @blkmode: block mode (linear, 32x32, 64x64) -+ * @endian: byte swapping (swap16, swap32, swap64, swap128) -+ */ -+int meson_canvas_config(struct meson_canvas *canvas, u8 canvas_index, -+ u32 addr, u32 stride, u32 height, -+ unsigned int wrap, unsigned int blkmode, -+ unsigned int endian); -+ -+#endif diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/003_linux-4.18.y-v4l-0003-arm64-dts-meson-gx-add_dmcbus_and_canvas_nodes..patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/003_linux-4.18.y-v4l-0003-arm64-dts-meson-gx-add_dmcbus_and_canvas_nodes..patch deleted file mode 100644 index e148eb20f..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/003_linux-4.18.y-v4l-0003-arm64-dts-meson-gx-add_dmcbus_and_canvas_nodes..patch +++ /dev/null @@ -1,38 +0,0 @@ -From e4c19f493a541cd00df42c02ec8f544f9835cbe5 Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Fri, 20 Apr 2018 16:09:09 +0200 -Subject: [PATCH] ARM64: dts: meson-gx: add dmcbus and canvas nodes. - -DMC is a small memory region with various registers, -including the ones needed for the canvas module. - -Reviewed-by: Jerome Brunet -Signed-off-by: Maxime Jourdan ---- - arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 13 +++++++++++++ - 1 file changed, 13 insertions(+) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -index b8dc4dbb391b6..5dd63ecf8b05b 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -423,6 +423,19 @@ - }; - }; - -+ dmcbus: bus@c8838000 { -+ compatible = "simple-bus"; -+ reg = <0x0 0xc8838000 0x0 0x400>; -+ #address-cells = <2>; -+ #size-cells = <2>; -+ ranges = <0x0 0x0 0x0 0xc8838000 0x0 0x400>; -+ -+ canvas: video-lut@48 { -+ compatible = "amlogic,canvas"; -+ reg = <0x0 0x48 0x0 0x14>; -+ }; -+ }; -+ - hiubus: bus@c883c000 { - compatible = "simple-bus"; - reg = <0x0 0xc883c000 0x0 0x2000>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/004_linux-4.18.y-v4l-0004-drm_meson-convert_to_the_new_canvas_module.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/004_linux-4.18.y-v4l-0004-drm_meson-convert_to_the_new_canvas_module.patch deleted file mode 100644 index d7a91b420..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/004_linux-4.18.y-v4l-0004-drm_meson-convert_to_the_new_canvas_module.patch +++ /dev/null @@ -1,366 +0,0 @@ -From 665dbad80386dcb9ac78ec6153d8d518da9bb50e Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Fri, 20 Apr 2018 16:22:17 +0200 -Subject: [PATCH] drm/meson: convert to the new canvas module - -This removes the meson_canvas files within the meson/drm layer -and makes use of the new canvas module that is referenced in the dts. - -Canvases can be used by different IPs and modules, and it is as such -preferable to rely on a module that can safely dispatch canvases on -demand. - -Signed-off-by: Maxime Jourdan ---- - .../bindings/display/amlogic,meson-vpu.txt | 9 +-- - arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 7 +- - drivers/gpu/drm/meson/Kconfig | 1 + - drivers/gpu/drm/meson/Makefile | 2 +- - drivers/gpu/drm/meson/meson_canvas.c | 70 ------------------- - drivers/gpu/drm/meson/meson_canvas.h | 42 ----------- - drivers/gpu/drm/meson/meson_crtc.c | 9 ++- - drivers/gpu/drm/meson/meson_drv.c | 22 ++---- - drivers/gpu/drm/meson/meson_drv.h | 5 +- - drivers/gpu/drm/meson/meson_plane.c | 3 +- - drivers/gpu/drm/meson/meson_viu.c | 1 - - 11 files changed, 26 insertions(+), 145 deletions(-) - delete mode 100644 drivers/gpu/drm/meson/meson_canvas.c - delete mode 100644 drivers/gpu/drm/meson/meson_canvas.h - -diff --git a/Documentation/devicetree/bindings/display/amlogic,meson-vpu.txt b/Documentation/devicetree/bindings/display/amlogic,meson-vpu.txt -index 057b81335775e..60b6e13986365 100644 ---- a/Documentation/devicetree/bindings/display/amlogic,meson-vpu.txt -+++ b/Documentation/devicetree/bindings/display/amlogic,meson-vpu.txt -@@ -60,9 +60,9 @@ Required properties: - - reg: base address and size of he following memory-mapped regions : - - vpu - - hhi -- - dmc - - reg-names: should contain the names of the previous memory regions - - interrupts: should contain the VENC Vsync interrupt number -+- amlogic,canvas: should point to a meson canvas provider node - - Optional properties: - - power-domains: Optional phandle to associated power domain as described in -@@ -98,13 +98,14 @@ tv-connector { - vpu: vpu@d0100000 { - compatible = "amlogic,meson-gxbb-vpu"; - reg = <0x0 0xd0100000 0x0 0x100000>, -- <0x0 0xc883c000 0x0 0x1000>, -- <0x0 0xc8838000 0x0 0x1000>; -- reg-names = "vpu", "hhi", "dmc"; -+ <0x0 0xc883c000 0x0 0x1000>; -+ reg-names = "vpu", "hhi"; - interrupts = ; - #address-cells = <1>; - #size-cells = <0>; - -+ amlogic,canvas = <&canvas>; -+ - /* CVBS VDAC output port */ - port@0 { - reg = <0>; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -index 5dd63ecf8b05b..737b741df0355 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -499,13 +499,14 @@ - vpu: vpu@d0100000 { - compatible = "amlogic,meson-gx-vpu"; - reg = <0x0 0xd0100000 0x0 0x100000>, -- <0x0 0xc883c000 0x0 0x1000>, -- <0x0 0xc8838000 0x0 0x1000>; -- reg-names = "vpu", "hhi", "dmc"; -+ <0x0 0xc883c000 0x0 0x1000>; -+ reg-names = "vpu", "hhi"; - interrupts = ; - #address-cells = <1>; - #size-cells = <0>; - -+ amlogic,canvas = <&canvas>; -+ - /* CVBS VDAC output port */ - cvbs_vdac_port: port@0 { - reg = <0>; -diff --git a/drivers/gpu/drm/meson/Kconfig b/drivers/gpu/drm/meson/Kconfig -index 3ce51d8dfe1c8..c28b69f485555 100644 ---- a/drivers/gpu/drm/meson/Kconfig -+++ b/drivers/gpu/drm/meson/Kconfig -@@ -7,6 +7,7 @@ config DRM_MESON - select DRM_GEM_CMA_HELPER - select VIDEOMODE_HELPERS - select REGMAP_MMIO -+ select MESON_CANVAS - - config DRM_MESON_DW_HDMI - tristate "HDMI Synopsys Controller support for Amlogic Meson Display" -diff --git a/drivers/gpu/drm/meson/Makefile b/drivers/gpu/drm/meson/Makefile -index c5c4cc362f024..bd67429185ff7 100644 ---- a/drivers/gpu/drm/meson/Makefile -+++ b/drivers/gpu/drm/meson/Makefile -@@ -1,5 +1,5 @@ - meson-drm-y := meson_drv.o meson_plane.o meson_crtc.o meson_venc_cvbs.o --meson-drm-y += meson_viu.o meson_vpp.o meson_venc.o meson_vclk.o meson_canvas.o -+meson-drm-y += meson_viu.o meson_vpp.o meson_venc.o meson_vclk.o - - obj-$(CONFIG_DRM_MESON) += meson-drm.o - obj-$(CONFIG_DRM_MESON_DW_HDMI) += meson_dw_hdmi.o -diff --git a/drivers/gpu/drm/meson/meson_canvas.c b/drivers/gpu/drm/meson/meson_canvas.c -deleted file mode 100644 -index 08f6073d967e0..0000000000000 ---- a/drivers/gpu/drm/meson/meson_canvas.c -+++ /dev/null -@@ -1,70 +0,0 @@ --/* -- * Copyright (C) 2016 BayLibre, SAS -- * Author: Neil Armstrong -- * Copyright (C) 2015 Amlogic, Inc. All rights reserved. -- * Copyright (C) 2014 Endless Mobile -- * -- * 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 "meson_drv.h" --#include "meson_canvas.h" --#include "meson_registers.h" -- --/** -- * DOC: Canvas -- * -- * CANVAS is a memory zone where physical memory frames information -- * are stored for the VIU to scanout. -- */ -- --/* DMC Registers */ --#define DMC_CAV_LUT_DATAL 0x48 /* 0x12 offset in data sheet */ --#define CANVAS_WIDTH_LBIT 29 --#define CANVAS_WIDTH_LWID 3 --#define DMC_CAV_LUT_DATAH 0x4c /* 0x13 offset in data sheet */ --#define CANVAS_WIDTH_HBIT 0 --#define CANVAS_HEIGHT_BIT 9 --#define CANVAS_BLKMODE_BIT 24 --#define DMC_CAV_LUT_ADDR 0x50 /* 0x14 offset in data sheet */ --#define CANVAS_LUT_WR_EN (0x2 << 8) --#define CANVAS_LUT_RD_EN (0x1 << 8) -- --void meson_canvas_setup(struct meson_drm *priv, -- uint32_t canvas_index, uint32_t addr, -- uint32_t stride, uint32_t height, -- unsigned int wrap, -- unsigned int blkmode) --{ -- unsigned int val; -- -- regmap_write(priv->dmc, DMC_CAV_LUT_DATAL, -- (((addr + 7) >> 3)) | -- (((stride + 7) >> 3) << CANVAS_WIDTH_LBIT)); -- -- regmap_write(priv->dmc, DMC_CAV_LUT_DATAH, -- ((((stride + 7) >> 3) >> CANVAS_WIDTH_LWID) << -- CANVAS_WIDTH_HBIT) | -- (height << CANVAS_HEIGHT_BIT) | -- (wrap << 22) | -- (blkmode << CANVAS_BLKMODE_BIT)); -- -- regmap_write(priv->dmc, DMC_CAV_LUT_ADDR, -- CANVAS_LUT_WR_EN | canvas_index); -- -- /* Force a read-back to make sure everything is flushed. */ -- regmap_read(priv->dmc, DMC_CAV_LUT_DATAH, &val); --} -diff --git a/drivers/gpu/drm/meson/meson_canvas.h b/drivers/gpu/drm/meson/meson_canvas.h -deleted file mode 100644 -index af1759da4b275..0000000000000 ---- a/drivers/gpu/drm/meson/meson_canvas.h -+++ /dev/null -@@ -1,42 +0,0 @@ --/* -- * Copyright (C) 2016 BayLibre, SAS -- * Author: Neil Armstrong -- * Copyright (C) 2014 Endless Mobile -- * -- * 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 . -- */ -- --/* Canvas LUT Memory */ -- --#ifndef __MESON_CANVAS_H --#define __MESON_CANVAS_H -- --#define MESON_CANVAS_ID_OSD1 0x4e -- --/* Canvas configuration. */ --#define MESON_CANVAS_WRAP_NONE 0x00 --#define MESON_CANVAS_WRAP_X 0x01 --#define MESON_CANVAS_WRAP_Y 0x02 -- --#define MESON_CANVAS_BLKMODE_LINEAR 0x00 --#define MESON_CANVAS_BLKMODE_32x32 0x01 --#define MESON_CANVAS_BLKMODE_64x64 0x02 -- --void meson_canvas_setup(struct meson_drm *priv, -- uint32_t canvas_index, uint32_t addr, -- uint32_t stride, uint32_t height, -- unsigned int wrap, -- unsigned int blkmode); -- --#endif /* __MESON_CANVAS_H */ -diff --git a/drivers/gpu/drm/meson/meson_crtc.c b/drivers/gpu/drm/meson/meson_crtc.c -index 05520202c9677..1ca9c6c45f9b9 100644 ---- a/drivers/gpu/drm/meson/meson_crtc.c -+++ b/drivers/gpu/drm/meson/meson_crtc.c -@@ -36,7 +36,6 @@ - #include "meson_venc.h" - #include "meson_vpp.h" - #include "meson_viu.h" --#include "meson_canvas.h" - #include "meson_registers.h" - - /* CRTC definition */ -@@ -193,10 +192,10 @@ void meson_crtc_irq(struct meson_drm *priv) - } else - meson_vpp_disable_interlace_vscaler_osd1(priv); - -- meson_canvas_setup(priv, MESON_CANVAS_ID_OSD1, -- priv->viu.osd1_addr, priv->viu.osd1_stride, -- priv->viu.osd1_height, MESON_CANVAS_WRAP_NONE, -- MESON_CANVAS_BLKMODE_LINEAR); -+ meson_canvas_config(priv->canvas, priv->canvas_id_osd1, -+ priv->viu.osd1_addr, priv->viu.osd1_stride, -+ priv->viu.osd1_height, MESON_CANVAS_WRAP_NONE, -+ MESON_CANVAS_BLKMODE_LINEAR, 0); - - /* Enable OSD1 */ - writel_bits_relaxed(VPP_OSD1_POSTBLEND, VPP_OSD1_POSTBLEND, -diff --git a/drivers/gpu/drm/meson/meson_drv.c b/drivers/gpu/drm/meson/meson_drv.c -index d3443125e6616..fb5b0e3c5efce 100644 ---- a/drivers/gpu/drm/meson/meson_drv.c -+++ b/drivers/gpu/drm/meson/meson_drv.c -@@ -47,7 +47,6 @@ - #include "meson_vpp.h" - #include "meson_viu.h" - #include "meson_venc.h" --#include "meson_canvas.h" - #include "meson_registers.h" - - #define DRIVER_NAME "meson" -@@ -216,25 +215,15 @@ static int meson_drv_bind_master(struct device *dev, bool has_components) - goto free_drm; - } - -- res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "dmc"); -- if (!res) { -- ret = -EINVAL; -- goto free_drm; -- } -- /* Simply ioremap since it may be a shared register zone */ -- regs = devm_ioremap(dev, res->start, resource_size(res)); -- if (!regs) { -- ret = -EADDRNOTAVAIL; -+ priv->canvas = meson_canvas_get(dev); -+ if (IS_ERR(priv->canvas)) { -+ ret = PTR_ERR(priv->canvas); - goto free_drm; - } - -- priv->dmc = devm_regmap_init_mmio(dev, regs, -- &meson_regmap_config); -- if (IS_ERR(priv->dmc)) { -- dev_err(&pdev->dev, "Couldn't create the DMC regmap\n"); -- ret = PTR_ERR(priv->dmc); -+ ret = meson_canvas_alloc(priv->canvas, &priv->canvas_id_osd1); -+ if (ret) - goto free_drm; -- } - - priv->vsync_irq = platform_get_irq(pdev, 0); - -@@ -315,6 +304,7 @@ static void meson_drv_unbind(struct device *dev) - struct drm_device *drm = dev_get_drvdata(dev); - struct meson_drm *priv = drm->dev_private; - -+ meson_canvas_free(priv->canvas, priv->canvas_id_osd1); - drm_dev_unregister(drm); - drm_kms_helper_poll_fini(drm); - drm_fbdev_cma_fini(priv->fbdev); -diff --git a/drivers/gpu/drm/meson/meson_drv.h b/drivers/gpu/drm/meson/meson_drv.h -index 8450d6ac8c9bc..9e902a6df7843 100644 ---- a/drivers/gpu/drm/meson/meson_drv.h -+++ b/drivers/gpu/drm/meson/meson_drv.h -@@ -22,15 +22,18 @@ - #include - #include - #include -+#include - #include - - struct meson_drm { - struct device *dev; - void __iomem *io_base; - struct regmap *hhi; -- struct regmap *dmc; - int vsync_irq; - -+ struct meson_canvas *canvas; -+ u8 canvas_id_osd1; -+ - struct drm_device *drm; - struct drm_crtc *crtc; - struct drm_fbdev_cma *fbdev; -diff --git a/drivers/gpu/drm/meson/meson_plane.c b/drivers/gpu/drm/meson/meson_plane.c -index 12c80dfcff59b..8745f9209625b 100644 ---- a/drivers/gpu/drm/meson/meson_plane.c -+++ b/drivers/gpu/drm/meson/meson_plane.c -@@ -36,7 +36,6 @@ - #include "meson_plane.h" - #include "meson_vpp.h" - #include "meson_viu.h" --#include "meson_canvas.h" - #include "meson_registers.h" - - struct meson_plane { -@@ -105,7 +104,7 @@ static void meson_plane_atomic_update(struct drm_plane *plane, - OSD_BLK0_ENABLE; - - /* Set up BLK0 to point to the right canvas */ -- priv->viu.osd1_blk0_cfg[0] = ((MESON_CANVAS_ID_OSD1 << OSD_CANVAS_SEL) | -+ priv->viu.osd1_blk0_cfg[0] = ((priv->canvas_id_osd1 << OSD_CANVAS_SEL) | - OSD_ENDIANNESS_LE); - - /* On GXBB, Use the old non-HDR RGB2YUV converter */ -diff --git a/drivers/gpu/drm/meson/meson_viu.c b/drivers/gpu/drm/meson/meson_viu.c -index 6bcfa527c1801..5b48c4c0985b5 100644 ---- a/drivers/gpu/drm/meson/meson_viu.c -+++ b/drivers/gpu/drm/meson/meson_viu.c -@@ -25,7 +25,6 @@ - #include "meson_viu.h" - #include "meson_vpp.h" - #include "meson_venc.h" --#include "meson_canvas.h" - #include "meson_registers.h" - - /** diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/005_linux-4.18.y-v4l-0005-dt-bindings-media-add_amlogic_video_decoder_bindings.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/005_linux-4.18.y-v4l-0005-dt-bindings-media-add_amlogic_video_decoder_bindings.patch deleted file mode 100644 index 389e3486b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/005_linux-4.18.y-v4l-0005-dt-bindings-media-add_amlogic_video_decoder_bindings.patch +++ /dev/null @@ -1,82 +0,0 @@ -From 0ceff9fb866173338b3ca79657ce6bf9aa3b2a9a Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Wed, 29 Aug 2018 15:05:05 +0200 -Subject: [PATCH] dt-bindings: media: add Amlogic Video Decoder Bindings - -Add documentation for the meson vdec dts node. - -Signed-off-by: Maxime Jourdan ---- - .../bindings/media/amlogic,vdec.txt | 63 +++++++++++++++++++ - 1 file changed, 63 insertions(+) - create mode 100644 Documentation/devicetree/bindings/media/amlogic,vdec.txt - -diff --git a/Documentation/devicetree/bindings/media/amlogic,vdec.txt b/Documentation/devicetree/bindings/media/amlogic,vdec.txt -new file mode 100644 -index 0000000000000..c6450f2e7f28f ---- /dev/null -+++ b/Documentation/devicetree/bindings/media/amlogic,vdec.txt -@@ -0,0 +1,63 @@ -+Amlogic Video Decoder -+================================ -+ -+The VDEC IP is composed of the following blocks : -+ -+- ESPARSER is a bitstream parser that outputs to a VIFIFO. Further VDEC blocks -+then feed from this VIFIFO. -+- VDEC_1 can decode MPEG-1, MPEG-2, MPEG-4 part 2, H.263, H.264. -+- VDEC_2 is used as a helper for corner cases like H.264 4K on older SoCs. -+It is not handled by this driver. -+- VDEC_HCODEC is the H.264 encoding block. It is not handled by this driver. -+- VDEC_HEVC can decode HEVC and VP9. -+ -+Device Tree Bindings: -+--------------------- -+ -+VDEC: Video Decoder -+-------------------------- -+ -+Required properties: -+- compatible: value should be different for each SoC family as : -+ - GXBB (S905) : "amlogic,gxbb-vdec" -+ - GXL (S905X, S905D) : "amlogic,gxl-vdec" -+ - GXM (S912) : "amlogic,gxm-vdec" -+- reg: base address and size of he following memory-mapped regions : -+ - dos -+ - esparser -+- reg-names: should contain the names of the previous memory regions -+- interrupts: should contain the vdec and esparser IRQs. -+- amlogic,ao-sysctrl: should point to the AOBUS sysctrl node -+- amlogic,canvas: should point to a canvas provider node -+- clocks: should contain the following clocks : -+ - dos_parser -+ - dos -+ - vdec_1 -+ - vdec_hevc -+- clock-names: should contain the names of the previous clocks -+- resets: should contain the parser reset. -+- reset-names: should be "esparser". -+ -+Example: -+ -+vdec: video-decoder@c8820000 { -+ compatible = "amlogic,gxbb-vdec"; -+ reg = <0x0 0xc8820000 0x0 0x10000>, -+ <0x0 0xc110a580 0x0 0xe4>; -+ reg-names = "dos", "esparser"; -+ -+ interrupts = , -+ ; -+ -+ amlogic,ao-sysctrl = <&sysctrl_AO>; -+ amlogic,canvas = <&canvas>; -+ -+ clocks = <&clkc CLKID_DOS_PARSER>, -+ <&clkc CLKID_DOS>, -+ <&clkc CLKID_VDEC_1>, -+ <&clkc CLKID_VDEC_HEVC>; -+ clock-names = "dos_parser", "dos", "vdec_1", "vdec_hevc"; -+ -+ resets = <&reset RESET_PARSER>; -+ reset-names = "esparser"; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/006_linux-4.18.y-v4l-0006-media-meson-add_v4l2_m2m_video_decoder_driver.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/006_linux-4.18.y-v4l-0006-media-meson-add_v4l2_m2m_video_decoder_driver.patch deleted file mode 100644 index 3ef259e6a..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/006_linux-4.18.y-v4l-0006-media-meson-add_v4l2_m2m_video_decoder_driver.patch +++ /dev/null @@ -1,2844 +0,0 @@ -From c975acbed7ff7904523600a4fd5e4b45b4c41ec3 Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Wed, 29 Aug 2018 15:17:22 +0200 -Subject: [PATCH] media: meson: add v4l2 m2m video decoder driver - -Amlogic SoCs feature a powerful video decoder unit able to -decode many formats, with a performance of usually up to 4k60. - -This is a driver for this IP that is based around the v4l2 m2m framework. - -It features decoding for: -- MPEG 1 -- MPEG 2 - -Supported SoCs are: GXBB (S905), GXL (S905X/W/D), GXM (S912) - -There is also a hardware bitstream parser (ESPARSER) that is handled here. - -Signed-off-by: Maxime Jourdan ---- - drivers/media/platform/Kconfig | 10 + - drivers/media/platform/meson/Makefile | 1 + - drivers/media/platform/meson/vdec/Makefile | 8 + - .../media/platform/meson/vdec/codec_mpeg12.c | 170 +++ - .../media/platform/meson/vdec/codec_mpeg12.h | 14 + - drivers/media/platform/meson/vdec/dos_regs.h | 98 ++ - drivers/media/platform/meson/vdec/esparser.c | 368 +++++++ - drivers/media/platform/meson/vdec/esparser.h | 28 + - drivers/media/platform/meson/vdec/vdec.c | 988 ++++++++++++++++++ - drivers/media/platform/meson/vdec/vdec.h | 234 +++++ - drivers/media/platform/meson/vdec/vdec_1.c | 228 ++++ - drivers/media/platform/meson/vdec/vdec_1.h | 14 + - .../media/platform/meson/vdec/vdec_helpers.c | 354 +++++++ - .../media/platform/meson/vdec/vdec_helpers.h | 45 + - .../media/platform/meson/vdec/vdec_platform.c | 101 ++ - .../media/platform/meson/vdec/vdec_platform.h | 30 + - 16 files changed, 2691 insertions(+) - create mode 100644 drivers/media/platform/meson/vdec/Makefile - create mode 100644 drivers/media/platform/meson/vdec/codec_mpeg12.c - create mode 100644 drivers/media/platform/meson/vdec/codec_mpeg12.h - create mode 100644 drivers/media/platform/meson/vdec/dos_regs.h - create mode 100644 drivers/media/platform/meson/vdec/esparser.c - create mode 100644 drivers/media/platform/meson/vdec/esparser.h - create mode 100644 drivers/media/platform/meson/vdec/vdec.c - create mode 100644 drivers/media/platform/meson/vdec/vdec.h - create mode 100644 drivers/media/platform/meson/vdec/vdec_1.c - create mode 100644 drivers/media/platform/meson/vdec/vdec_1.h - create mode 100644 drivers/media/platform/meson/vdec/vdec_helpers.c - create mode 100644 drivers/media/platform/meson/vdec/vdec_helpers.h - create mode 100644 drivers/media/platform/meson/vdec/vdec_platform.c - create mode 100644 drivers/media/platform/meson/vdec/vdec_platform.h - -diff --git a/drivers/media/platform/Kconfig b/drivers/media/platform/Kconfig -index 2728376b04b53..1c33d95dd92f9 100644 ---- a/drivers/media/platform/Kconfig -+++ b/drivers/media/platform/Kconfig -@@ -482,6 +482,16 @@ config VIDEO_QCOM_VENUS - on various Qualcomm SoCs. - To compile this driver as a module choose m here. - -+config VIDEO_MESON_VDEC -+ tristate "Amlogic video decoder driver" -+ depends on VIDEO_DEV && VIDEO_V4L2 && HAS_DMA -+ depends on (ARCH_MESON) || COMPILE_TEST -+ select VIDEOBUF2_DMA_CONTIG -+ select V4L2_MEM2MEM_DEV -+ select MESON_CANVAS -+ help -+ Support for the video decoder found in gxbb/gxl/gxm chips. -+ - endif # V4L_MEM2MEM_DRIVERS - - # TI VIDEO PORT Helper Modules -diff --git a/drivers/media/platform/meson/Makefile b/drivers/media/platform/meson/Makefile -index 597beb8f34d15..f7c6e1031f25d 100644 ---- a/drivers/media/platform/meson/Makefile -+++ b/drivers/media/platform/meson/Makefile -@@ -1 +1,2 @@ - obj-$(CONFIG_VIDEO_MESON_AO_CEC) += ao-cec.o -+obj-$(CONFIG_VIDEO_MESON_VDEC) += vdec/ -diff --git a/drivers/media/platform/meson/vdec/Makefile b/drivers/media/platform/meson/vdec/Makefile -new file mode 100644 -index 0000000000000..6bea129084b76 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/Makefile -@@ -0,0 +1,8 @@ -+# SPDX-License-Identifier: GPL-2.0 -+# Makefile for Amlogic meson video decoder driver -+ -+meson-vdec-objs = esparser.o vdec.o vdec_helpers.o vdec_platform.o -+meson-vdec-objs += vdec_1.o -+meson-vdec-objs += codec_mpeg12.o -+ -+obj-$(CONFIG_VIDEO_MESON_VDEC) += meson-vdec.o -diff --git a/drivers/media/platform/meson/vdec/codec_mpeg12.c b/drivers/media/platform/meson/vdec/codec_mpeg12.c -new file mode 100644 -index 0000000000000..18709319cff7f ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/codec_mpeg12.c -@@ -0,0 +1,170 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ */ -+ -+#include -+#include -+ -+#include "vdec_helpers.h" -+#include "dos_regs.h" -+ -+#define SIZE_WORKSPACE SZ_128K -+/* Offset substracted by the firmware from the workspace paddr */ -+#define WORKSPACE_OFFSET (5 * SZ_1K) -+ -+/* map firmware registers to known MPEG1/2 functions */ -+#define MREG_SEQ_INFO AV_SCRATCH_4 -+#define MREG_PIC_INFO AV_SCRATCH_5 -+#define MREG_PIC_WIDTH AV_SCRATCH_6 -+#define MREG_PIC_HEIGHT AV_SCRATCH_7 -+#define MREG_BUFFERIN AV_SCRATCH_8 -+#define MREG_BUFFEROUT AV_SCRATCH_9 -+#define MREG_CMD AV_SCRATCH_A -+#define MREG_CO_MV_START AV_SCRATCH_B -+#define MREG_ERROR_COUNT AV_SCRATCH_C -+#define MREG_FRAME_OFFSET AV_SCRATCH_D -+#define MREG_WAIT_BUFFER AV_SCRATCH_E -+#define MREG_FATAL_ERROR AV_SCRATCH_F -+ -+#define PICINFO_PROG 0x00008000 -+#define PICINFO_TOP_FIRST 0x00002000 -+ -+struct codec_mpeg12 { -+ /* Buffer for the MPEG1/2 Workspace */ -+ void *workspace_vaddr; -+ dma_addr_t workspace_paddr; -+}; -+ -+static int codec_mpeg12_can_recycle(struct amvdec_core *core) -+{ -+ return !amvdec_read_dos(core, MREG_BUFFERIN); -+} -+ -+static void codec_mpeg12_recycle(struct amvdec_core *core, u32 buf_idx) -+{ -+ amvdec_write_dos(core, MREG_BUFFERIN, buf_idx + 1); -+} -+ -+static int codec_mpeg12_start(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_mpeg12 *mpeg12 = sess->priv; -+ int ret; -+ -+ mpeg12 = kzalloc(sizeof(*mpeg12), GFP_KERNEL); -+ if (!mpeg12) -+ return -ENOMEM; -+ -+ /* Allocate some memory for the MPEG1/2 decoder's state */ -+ mpeg12->workspace_vaddr = dma_alloc_coherent(core->dev, SIZE_WORKSPACE, -+ &mpeg12->workspace_paddr, -+ GFP_KERNEL); -+ if (!mpeg12->workspace_vaddr) { -+ dev_err(core->dev, "Failed to request MPEG 1/2 Workspace\n"); -+ ret = -ENOMEM; -+ goto free_mpeg12; -+ } -+ -+ ret = amvdec_set_canvases(sess, (u32[]){ AV_SCRATCH_0, 0 }, -+ (u32[]){ 8, 0 }); -+ if (ret) -+ goto free_workspace; -+ -+ amvdec_write_dos(core, POWER_CTL_VLD, BIT(4)); -+ amvdec_write_dos(core, MREG_CO_MV_START, -+ mpeg12->workspace_paddr + WORKSPACE_OFFSET); -+ -+ amvdec_write_dos(core, MPEG1_2_REG, 0); -+ amvdec_write_dos(core, PSCALE_CTRL, 0); -+ amvdec_write_dos(core, PIC_HEAD_INFO, 0x380); -+ amvdec_write_dos(core, M4_CONTROL_REG, 0); -+ amvdec_write_dos(core, MREG_BUFFERIN, 0); -+ amvdec_write_dos(core, MREG_BUFFEROUT, 0); -+ amvdec_write_dos(core, MREG_CMD, (sess->width << 16) | sess->height); -+ amvdec_write_dos(core, MREG_ERROR_COUNT, 0); -+ amvdec_write_dos(core, MREG_FATAL_ERROR, 0); -+ amvdec_write_dos(core, MREG_WAIT_BUFFER, 0); -+ -+ sess->keyframe_found = 1; -+ sess->priv = mpeg12; -+ -+ return 0; -+ -+free_workspace: -+ dma_free_coherent(core->dev, SIZE_WORKSPACE, mpeg12->workspace_vaddr, -+ mpeg12->workspace_paddr); -+free_mpeg12: -+ kfree(mpeg12); -+ -+ return ret; -+} -+ -+static int codec_mpeg12_stop(struct amvdec_session *sess) -+{ -+ struct codec_mpeg12 *mpeg12 = sess->priv; -+ struct amvdec_core *core = sess->core; -+ -+ if (mpeg12->workspace_vaddr) -+ dma_free_coherent(core->dev, SIZE_WORKSPACE, -+ mpeg12->workspace_vaddr, -+ mpeg12->workspace_paddr); -+ -+ return 0; -+} -+ -+static irqreturn_t codec_mpeg12_threaded_isr(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ u32 reg; -+ u32 pic_info; -+ u32 is_progressive; -+ u32 buffer_index; -+ u32 field = V4L2_FIELD_NONE; -+ -+ amvdec_write_dos(core, ASSIST_MBOX1_CLR_REG, 1); -+ reg = amvdec_read_dos(core, MREG_FATAL_ERROR); -+ if (reg == 1) { -+ dev_err(core->dev, "MPEG1/2 fatal error\n"); -+ amvdec_abort(sess); -+ return IRQ_HANDLED; -+ } -+ -+ reg = amvdec_read_dos(core, MREG_BUFFEROUT); -+ if (!reg) -+ return IRQ_HANDLED; -+ -+ /* Unclear what this means */ -+ if ((reg & GENMASK(23, 17)) == GENMASK(23, 17)) -+ goto end; -+ -+ pic_info = amvdec_read_dos(core, MREG_PIC_INFO); -+ is_progressive = pic_info & PICINFO_PROG; -+ -+ if (!is_progressive) -+ field = (pic_info & PICINFO_TOP_FIRST) ? -+ V4L2_FIELD_INTERLACED_TB : -+ V4L2_FIELD_INTERLACED_BT; -+ -+ buffer_index = ((reg & 0xf) - 1) & 7; -+ amvdec_dst_buf_done_idx(sess, buffer_index, field); -+ -+end: -+ amvdec_write_dos(core, MREG_BUFFEROUT, 0); -+ return IRQ_HANDLED; -+} -+ -+static irqreturn_t codec_mpeg12_isr(struct amvdec_session *sess) -+{ -+ return IRQ_WAKE_THREAD; -+} -+ -+struct amvdec_codec_ops codec_mpeg12_ops = { -+ .start = codec_mpeg12_start, -+ .stop = codec_mpeg12_stop, -+ .isr = codec_mpeg12_isr, -+ .threaded_isr = codec_mpeg12_threaded_isr, -+ .can_recycle = codec_mpeg12_can_recycle, -+ .recycle = codec_mpeg12_recycle, -+}; -diff --git a/drivers/media/platform/meson/vdec/codec_mpeg12.h b/drivers/media/platform/meson/vdec/codec_mpeg12.h -new file mode 100644 -index 0000000000000..43cab5f39ca05 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/codec_mpeg12.h -@@ -0,0 +1,14 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ */ -+ -+#ifndef __MESON_VDEC_CODEC_MPEG12_H_ -+#define __MESON_VDEC_CODEC_MPEG12_H_ -+ -+#include "vdec.h" -+ -+extern struct amvdec_codec_ops codec_mpeg12_ops; -+ -+#endif -diff --git a/drivers/media/platform/meson/vdec/dos_regs.h b/drivers/media/platform/meson/vdec/dos_regs.h -new file mode 100644 -index 0000000000000..abd810542dbb5 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/dos_regs.h -@@ -0,0 +1,98 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ */ -+ -+#ifndef __MESON_VDEC_DOS_REGS_H_ -+#define __MESON_VDEC_DOS_REGS_H_ -+ -+/* DOS registers */ -+#define VDEC_ASSIST_AMR1_INT8 0x00b4 -+ -+#define ASSIST_MBOX1_CLR_REG 0x01d4 -+#define ASSIST_MBOX1_MASK 0x01d8 -+ -+#define MPSR 0x0c04 -+#define MCPU_INTR_MSK 0x0c10 -+#define CPSR 0x0c84 -+ -+#define IMEM_DMA_CTRL 0x0d00 -+#define IMEM_DMA_ADR 0x0d04 -+#define IMEM_DMA_COUNT 0x0d08 -+#define LMEM_DMA_CTRL 0x0d40 -+ -+#define MC_STATUS0 0x2424 -+#define MC_CTRL1 0x242c -+ -+#define PSCALE_RST 0x2440 -+#define PSCALE_CTRL 0x2444 -+#define PSCALE_BMEM_ADDR 0x247c -+#define PSCALE_BMEM_DAT 0x2480 -+ -+#define DBLK_CTRL 0x2544 -+#define DBLK_STATUS 0x254c -+ -+#define GCLK_EN 0x260c -+#define MDEC_PIC_DC_CTRL 0x2638 -+#define MDEC_PIC_DC_STATUS 0x263c -+#define ANC0_CANVAS_ADDR 0x2640 -+#define MDEC_PIC_DC_THRESH 0x26e0 -+ -+/* Firmware interface registers */ -+#define AV_SCRATCH_0 0x2700 -+#define AV_SCRATCH_1 0x2704 -+#define AV_SCRATCH_2 0x2708 -+#define AV_SCRATCH_3 0x270c -+#define AV_SCRATCH_4 0x2710 -+#define AV_SCRATCH_5 0x2714 -+#define AV_SCRATCH_6 0x2718 -+#define AV_SCRATCH_7 0x271c -+#define AV_SCRATCH_8 0x2720 -+#define AV_SCRATCH_9 0x2724 -+#define AV_SCRATCH_A 0x2728 -+#define AV_SCRATCH_B 0x272c -+#define AV_SCRATCH_C 0x2730 -+#define AV_SCRATCH_D 0x2734 -+#define AV_SCRATCH_E 0x2738 -+#define AV_SCRATCH_F 0x273c -+#define AV_SCRATCH_G 0x2740 -+#define AV_SCRATCH_H 0x2744 -+#define AV_SCRATCH_I 0x2748 -+#define AV_SCRATCH_J 0x274c -+#define AV_SCRATCH_K 0x2750 -+#define AV_SCRATCH_L 0x2754 -+ -+#define MPEG1_2_REG 0x3004 -+#define PIC_HEAD_INFO 0x300c -+#define POWER_CTL_VLD 0x3020 -+#define M4_CONTROL_REG 0x30a4 -+ -+/* Stream Buffer (stbuf) regs */ -+#define VLD_MEM_VIFIFO_START_PTR 0x3100 -+#define VLD_MEM_VIFIFO_CURR_PTR 0x3104 -+#define VLD_MEM_VIFIFO_END_PTR 0x3108 -+#define VLD_MEM_VIFIFO_CONTROL 0x3110 -+ #define MEM_FIFO_CNT_BIT 16 -+ #define MEM_FILL_ON_LEVEL BIT(10) -+ #define MEM_CTRL_EMPTY_EN BIT(2) -+ #define MEM_CTRL_FILL_EN BIT(1) -+#define VLD_MEM_VIFIFO_WP 0x3114 -+#define VLD_MEM_VIFIFO_RP 0x3118 -+#define VLD_MEM_VIFIFO_LEVEL 0x311c -+#define VLD_MEM_VIFIFO_BUF_CNTL 0x3120 -+ #define MEM_BUFCTRL_MANUAL BIT(1) -+#define VLD_MEM_VIFIFO_WRAP_COUNT 0x3144 -+ -+#define DCAC_DMA_CTRL 0x3848 -+ -+#define DOS_SW_RESET0 0xfc00 -+#define DOS_GCLK_EN0 0xfc04 -+#define DOS_GEN_CTRL0 0xfc08 -+#define DOS_MEM_PD_VDEC 0xfcc0 -+#define DOS_MEM_PD_HEVC 0xfccc -+#define DOS_SW_RESET3 0xfcd0 -+#define DOS_GCLK_EN3 0xfcd4 -+#define DOS_VDEC_MCRCC_STALL_CTRL 0xfd00 -+ -+#endif -diff --git a/drivers/media/platform/meson/vdec/esparser.c b/drivers/media/platform/meson/vdec/esparser.c -new file mode 100644 -index 0000000000000..098c7d76ad3fe ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/esparser.c -@@ -0,0 +1,368 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ * -+ * The Elementary Stream Parser is a HW bitstream parser. -+ * It reads bitstream buffers and feeds them to the VIFIFO -+ */ -+ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include "dos_regs.h" -+#include "esparser.h" -+#include "vdec_helpers.h" -+ -+/* PARSER REGS (CBUS) */ -+#define PARSER_CONTROL 0x00 -+ #define ES_PACK_SIZE_BIT 8 -+ #define ES_WRITE BIT(5) -+ #define ES_SEARCH BIT(1) -+ #define ES_PARSER_START BIT(0) -+#define PARSER_FETCH_ADDR 0x4 -+#define PARSER_FETCH_CMD 0x8 -+#define PARSER_CONFIG 0x14 -+ #define PS_CFG_MAX_FETCH_CYCLE_BIT 0 -+ #define PS_CFG_STARTCODE_WID_24_BIT 10 -+ #define PS_CFG_MAX_ES_WR_CYCLE_BIT 12 -+ #define PS_CFG_PFIFO_EMPTY_CNT_BIT 16 -+#define PFIFO_WR_PTR 0x18 -+#define PFIFO_RD_PTR 0x1c -+#define PARSER_SEARCH_PATTERN 0x24 -+ #define ES_START_CODE_PATTERN 0x00000100 -+#define PARSER_SEARCH_MASK 0x28 -+ #define ES_START_CODE_MASK 0xffffff00 -+ #define FETCH_ENDIAN_BIT 27 -+#define PARSER_INT_ENABLE 0x2c -+ #define PARSER_INT_HOST_EN_BIT 8 -+#define PARSER_INT_STATUS 0x30 -+ #define PARSER_INTSTAT_SC_FOUND 1 -+#define PARSER_ES_CONTROL 0x5c -+#define PARSER_VIDEO_START_PTR 0x80 -+#define PARSER_VIDEO_END_PTR 0x84 -+#define PARSER_VIDEO_HOLE 0x90 -+ -+#define SEARCH_PATTERN_LEN 512 -+#define MIN_PACKET_SIZE (4 * SZ_1K) -+ -+/* Buffer to send to the ESPARSER to signal End Of Stream. -+ * Credits to Endless Mobile. -+ */ -+#define EOS_TAIL_BUF_SIZE 1024 -+static const u8 eos_tail_data[EOS_TAIL_BUF_SIZE] = { -+ 0x00, 0x00, 0x00, 0x01, 0x06, 0x05, 0xff, 0xe4, 0xdc, 0x45, 0xe9, 0xbd, -+ 0xe6, 0xd9, 0x48, 0xb7, 0x96, 0x2c, 0xd8, 0x20, 0xd9, 0x23, 0xee, 0xef, -+ 0x78, 0x32, 0x36, 0x34, 0x20, 0x2d, 0x20, 0x63, 0x6f, 0x72, 0x65, 0x20, -+ 0x36, 0x37, 0x20, 0x72, 0x31, 0x31, 0x33, 0x30, 0x20, 0x38, 0x34, 0x37, -+ 0x35, 0x39, 0x37, 0x37, 0x20, 0x2d, 0x20, 0x48, 0x2e, 0x32, 0x36, 0x34, -+ 0x2f, 0x4d, 0x50, 0x45, 0x47, 0x2d, 0x34, 0x20, 0x41, 0x56, 0x43, 0x20, -+ 0x63, 0x6f, 0x64, 0x65, 0x63, 0x20, 0x2d, 0x20, 0x43, 0x6f, 0x70, 0x79, -+ 0x6c, 0x65, 0x66, 0x74, 0x20, 0x32, 0x30, 0x30, 0x33, 0x2d, 0x32, 0x30, -+ 0x30, 0x39, 0x20, 0x2d, 0x20, 0x68, 0x74, 0x74, 0x70, 0x3a, 0x2f, 0x2f, -+ 0x77, 0x77, 0x77, 0x2e, 0x76, 0x69, 0x64, 0x65, 0x6f, 0x6c, 0x61, 0x6e, -+ 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x78, 0x32, 0x36, 0x34, 0x2e, 0x68, 0x74, -+ 0x6d, 0x6c, 0x20, 0x2d, 0x20, 0x6f, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x73, -+ 0x3a, 0x20, 0x63, 0x61, 0x62, 0x61, 0x63, 0x3d, 0x31, 0x20, 0x72, 0x65, -+ 0x66, 0x3d, 0x31, 0x20, 0x64, 0x65, 0x62, 0x6c, 0x6f, 0x63, 0x6b, 0x3d, -+ 0x31, 0x3a, 0x30, 0x3a, 0x30, 0x20, 0x61, 0x6e, 0x61, 0x6c, 0x79, 0x73, -+ 0x65, 0x3d, 0x30, 0x78, 0x31, 0x3a, 0x30, 0x78, 0x31, 0x31, 0x31, 0x20, -+ 0x6d, 0x65, 0x3d, 0x68, 0x65, 0x78, 0x20, 0x73, 0x75, 0x62, 0x6d, 0x65, -+ 0x3d, 0x36, 0x20, 0x70, 0x73, 0x79, 0x5f, 0x72, 0x64, 0x3d, 0x31, 0x2e, -+ 0x30, 0x3a, 0x30, 0x2e, 0x30, 0x20, 0x6d, 0x69, 0x78, 0x65, 0x64, 0x5f, -+ 0x72, 0x65, 0x66, 0x3d, 0x30, 0x20, 0x6d, 0x65, 0x5f, 0x72, 0x61, 0x6e, -+ 0x67, 0x65, 0x3d, 0x31, 0x36, 0x20, 0x63, 0x68, 0x72, 0x6f, 0x6d, 0x61, -+ 0x5f, 0x6d, 0x65, 0x3d, 0x31, 0x20, 0x74, 0x72, 0x65, 0x6c, 0x6c, 0x69, -+ 0x73, 0x3d, 0x30, 0x20, 0x38, 0x78, 0x38, 0x64, 0x63, 0x74, 0x3d, 0x30, -+ 0x20, 0x63, 0x71, 0x6d, 0x3d, 0x30, 0x20, 0x64, 0x65, 0x61, 0x64, 0x7a, -+ 0x6f, 0x6e, 0x65, 0x3d, 0x32, 0x31, 0x2c, 0x31, 0x31, 0x20, 0x63, 0x68, -+ 0x72, 0x6f, 0x6d, 0x61, 0x5f, 0x71, 0x70, 0x5f, 0x6f, 0x66, 0x66, 0x73, -+ 0x65, 0x74, 0x3d, 0x2d, 0x32, 0x20, 0x74, 0x68, 0x72, 0x65, 0x61, 0x64, -+ 0x73, 0x3d, 0x31, 0x20, 0x6e, 0x72, 0x3d, 0x30, 0x20, 0x64, 0x65, 0x63, -+ 0x69, 0x6d, 0x61, 0x74, 0x65, 0x3d, 0x31, 0x20, 0x6d, 0x62, 0x61, 0x66, -+ 0x66, 0x3d, 0x30, 0x20, 0x62, 0x66, 0x72, 0x61, 0x6d, 0x65, 0x73, 0x3d, -+ 0x30, 0x20, 0x6b, 0x65, 0x79, 0x69, 0x6e, 0x74, 0x3d, 0x32, 0x35, 0x30, -+ 0x20, 0x6b, 0x65, 0x79, 0x69, 0x6e, 0x74, 0x5f, 0x6d, 0x69, 0x6e, 0x3d, -+ 0x32, 0x35, 0x20, 0x73, 0x63, 0x65, 0x6e, 0x65, 0x63, 0x75, 0x74, 0x3d, -+ 0x34, 0x30, 0x20, 0x72, 0x63, 0x3d, 0x61, 0x62, 0x72, 0x20, 0x62, 0x69, -+ 0x74, 0x72, 0x61, 0x74, 0x65, 0x3d, 0x31, 0x30, 0x20, 0x72, 0x61, 0x74, -+ 0x65, 0x74, 0x6f, 0x6c, 0x3d, 0x31, 0x2e, 0x30, 0x20, 0x71, 0x63, 0x6f, -+ 0x6d, 0x70, 0x3d, 0x30, 0x2e, 0x36, 0x30, 0x20, 0x71, 0x70, 0x6d, 0x69, -+ 0x6e, 0x3d, 0x31, 0x30, 0x20, 0x71, 0x70, 0x6d, 0x61, 0x78, 0x3d, 0x35, -+ 0x31, 0x20, 0x71, 0x70, 0x73, 0x74, 0x65, 0x70, 0x3d, 0x34, 0x20, 0x69, -+ 0x70, 0x5f, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x3d, 0x31, 0x2e, 0x34, 0x30, -+ 0x20, 0x61, 0x71, 0x3d, 0x31, 0x3a, 0x31, 0x2e, 0x30, 0x30, 0x00, 0x80, -+ 0x00, 0x00, 0x00, 0x01, 0x67, 0x4d, 0x40, 0x0a, 0x9a, 0x74, 0xf4, 0x20, -+ 0x00, 0x00, 0x03, 0x00, 0x20, 0x00, 0x00, 0x06, 0x51, 0xe2, 0x44, 0xd4, -+ 0x00, 0x00, 0x00, 0x01, 0x68, 0xee, 0x32, 0xc8, 0x00, 0x00, 0x00, 0x01, -+ 0x65, 0x88, 0x80, 0x20, 0x00, 0x08, 0x7f, 0xea, 0x6a, 0xe2, 0x99, 0xb6, -+ 0x57, 0xae, 0x49, 0x30, 0xf5, 0xfe, 0x5e, 0x46, 0x0b, 0x72, 0x44, 0xc4, -+ 0xe1, 0xfc, 0x62, 0xda, 0xf1, 0xfb, 0xa2, 0xdb, 0xd6, 0xbe, 0x5c, 0xd7, -+ 0x24, 0xa3, 0xf5, 0xb9, 0x2f, 0x57, 0x16, 0x49, 0x75, 0x47, 0x77, 0x09, -+ 0x5c, 0xa1, 0xb4, 0xc3, 0x4f, 0x60, 0x2b, 0xb0, 0x0c, 0xc8, 0xd6, 0x66, -+ 0xba, 0x9b, 0x82, 0x29, 0x33, 0x92, 0x26, 0x99, 0x31, 0x1c, 0x7f, 0x9b -+}; -+ -+static DECLARE_WAIT_QUEUE_HEAD(wq); -+static int search_done; -+ -+static irqreturn_t esparser_isr(int irq, void *dev) -+{ -+ int int_status; -+ struct amvdec_core *core = dev; -+ -+ int_status = amvdec_read_parser(core, PARSER_INT_STATUS); -+ amvdec_write_parser(core, PARSER_INT_STATUS, int_status); -+ -+ if (int_status & PARSER_INTSTAT_SC_FOUND) { -+ amvdec_write_parser(core, PFIFO_RD_PTR, 0); -+ amvdec_write_parser(core, PFIFO_WR_PTR, 0); -+ search_done = 1; -+ wake_up_interruptible(&wq); -+ } -+ -+ return IRQ_HANDLED; -+} -+ -+/* Pad the packet to at least 4KiB bytes otherwise the VDEC unit won't trigger -+ * ISRs. -+ * Also append a start code 000001ff at the end to trigger -+ * the ESPARSER interrupt. -+ */ -+static u32 esparser_pad_start_code(struct vb2_buffer *vb) -+{ -+ u32 payload_size = vb2_get_plane_payload(vb, 0); -+ u32 pad_size = 0; -+ u8 *vaddr = vb2_plane_vaddr(vb, 0) + payload_size; -+ -+ if (payload_size < MIN_PACKET_SIZE) { -+ pad_size = MIN_PACKET_SIZE - payload_size; -+ memset(vaddr, 0, pad_size); -+ } -+ -+ memset(vaddr + pad_size, 0, SEARCH_PATTERN_LEN); -+ vaddr[pad_size] = 0x00; -+ vaddr[pad_size + 1] = 0x00; -+ vaddr[pad_size + 2] = 0x01; -+ vaddr[pad_size + 3] = 0xff; -+ -+ return pad_size; -+} -+ -+static int -+esparser_write_data(struct amvdec_core *core, dma_addr_t addr, u32 size) -+{ -+ amvdec_write_parser(core, PFIFO_RD_PTR, 0); -+ amvdec_write_parser(core, PFIFO_WR_PTR, 0); -+ amvdec_write_parser(core, PARSER_CONTROL, -+ ES_WRITE | -+ ES_PARSER_START | -+ ES_SEARCH | -+ (size << ES_PACK_SIZE_BIT)); -+ -+ amvdec_write_parser(core, PARSER_FETCH_ADDR, addr); -+ amvdec_write_parser(core, PARSER_FETCH_CMD, -+ (7 << FETCH_ENDIAN_BIT) | -+ (size + SEARCH_PATTERN_LEN)); -+ -+ search_done = 0; -+ return wait_event_interruptible_timeout(wq, search_done, (HZ / 5)); -+} -+ -+static u32 esparser_vififo_get_free_space(struct amvdec_session *sess) -+{ -+ u32 vififo_usage; -+ struct amvdec_ops *vdec_ops = sess->fmt_out->vdec_ops; -+ struct amvdec_core *core = sess->core; -+ -+ vififo_usage = vdec_ops->vififo_level(sess); -+ vififo_usage += amvdec_read_parser(core, PARSER_VIDEO_HOLE); -+ vififo_usage += (6 * SZ_1K); -+ -+ if (vififo_usage > sess->vififo_size) { -+ dev_warn(sess->core->dev, -+ "VIFIFO usage (%u) > VIFIFO size (%u)\n", -+ vififo_usage, sess->vififo_size); -+ return 0; -+ } -+ -+ return sess->vififo_size - vififo_usage; -+} -+ -+int esparser_queue_eos(struct amvdec_core *core) -+{ -+ struct device *dev = core->dev; -+ void *eos_vaddr; -+ dma_addr_t eos_paddr; -+ int ret; -+ -+ eos_vaddr = dma_alloc_coherent(dev, -+ EOS_TAIL_BUF_SIZE + SEARCH_PATTERN_LEN, -+ &eos_paddr, GFP_KERNEL); -+ if (!eos_vaddr) -+ return -ENOMEM; -+ -+ memset(eos_vaddr, 0, EOS_TAIL_BUF_SIZE + SEARCH_PATTERN_LEN); -+ memcpy(eos_vaddr, eos_tail_data, sizeof(eos_tail_data)); -+ ret = esparser_write_data(core, eos_paddr, EOS_TAIL_BUF_SIZE); -+ dma_free_coherent(dev, EOS_TAIL_BUF_SIZE + SEARCH_PATTERN_LEN, -+ eos_vaddr, eos_paddr); -+ -+ return ret; -+} -+ -+static int -+esparser_queue(struct amvdec_session *sess, struct vb2_v4l2_buffer *vbuf) -+{ -+ int ret; -+ struct vb2_buffer *vb = &vbuf->vb2_buf; -+ struct amvdec_core *core = sess->core; -+ struct amvdec_codec_ops *codec_ops = sess->fmt_out->codec_ops; -+ u32 num_dst_bufs = 0; -+ u32 payload_size = vb2_get_plane_payload(vb, 0); -+ dma_addr_t phy = vb2_dma_contig_plane_dma_addr(vb, 0); -+ u32 pad_size; -+ -+ if (!payload_size) { -+ esparser_queue_eos(core); -+ return 0; -+ } -+ -+ if (codec_ops->num_pending_bufs) -+ num_dst_bufs = codec_ops->num_pending_bufs(sess); -+ -+ num_dst_bufs += v4l2_m2m_num_dst_bufs_ready(sess->m2m_ctx); -+ -+ if (esparser_vififo_get_free_space(sess) < payload_size || -+ atomic_read(&sess->esparser_queued_bufs) >= num_dst_bufs) -+ return -EAGAIN; -+ -+ v4l2_m2m_src_buf_remove_by_buf(sess->m2m_ctx, vbuf); -+ amvdec_add_ts_reorder(sess, vb->timestamp); -+ dev_dbg(core->dev, "esparser: Queuing ts = %llu ; pld_size = %u\n", -+ vb->timestamp, payload_size); -+ -+ pad_size = esparser_pad_start_code(vb); -+ ret = esparser_write_data(core, phy, payload_size + pad_size); -+ -+ if (ret > 0) { -+ /* We need to wait until we parse/decode the first keyframe. -+ * All buffers prior to the first keyframe must be dropped. -+ */ -+ if (!sess->keyframe_found) -+ usleep_range(1000, 2000); -+ -+ if (sess->keyframe_found) -+ atomic_inc(&sess->esparser_queued_bufs); -+ else -+ amvdec_remove_ts(sess, vb->timestamp); -+ -+ vbuf->flags = 0; -+ vbuf->field = V4L2_FIELD_NONE; -+ v4l2_m2m_buf_done(vbuf, VB2_BUF_STATE_DONE); -+ return 0; -+ } -+ -+ dev_warn(core->dev, "esparser: input parsing error\n"); -+ amvdec_remove_ts(sess, vb->timestamp); -+ v4l2_m2m_buf_done(vbuf, VB2_BUF_STATE_ERROR); -+ amvdec_write_parser(core, PARSER_FETCH_CMD, 0); -+ -+ return 0; -+} -+ -+void esparser_queue_all_src(struct work_struct *work) -+{ -+ struct v4l2_m2m_buffer *buf, *n; -+ struct amvdec_session *sess = -+ container_of(work, struct amvdec_session, esparser_queue_work); -+ -+ mutex_lock(&sess->lock); -+ v4l2_m2m_for_each_src_buf_safe(sess->m2m_ctx, buf, n) { -+ if (esparser_queue(sess, &buf->vb) < 0) -+ break; -+ -+ /* Some codecs don't like having data queued in too fast */ -+ usleep_range(1000, 2000); -+ } -+ mutex_unlock(&sess->lock); -+} -+ -+int esparser_power_up(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct amvdec_ops *vdec_ops = sess->fmt_out->vdec_ops; -+ -+ reset_control_reset(core->esparser_reset); -+ amvdec_write_parser(core, PARSER_CONFIG, -+ (10 << PS_CFG_PFIFO_EMPTY_CNT_BIT) | -+ (1 << PS_CFG_MAX_ES_WR_CYCLE_BIT) | -+ (16 << PS_CFG_MAX_FETCH_CYCLE_BIT)); -+ -+ amvdec_write_parser(core, PFIFO_RD_PTR, 0); -+ amvdec_write_parser(core, PFIFO_WR_PTR, 0); -+ -+ amvdec_write_parser(core, PARSER_SEARCH_PATTERN, -+ ES_START_CODE_PATTERN); -+ amvdec_write_parser(core, PARSER_SEARCH_MASK, ES_START_CODE_MASK); -+ -+ amvdec_write_parser(core, PARSER_CONFIG, -+ (10 << PS_CFG_PFIFO_EMPTY_CNT_BIT) | -+ (1 << PS_CFG_MAX_ES_WR_CYCLE_BIT) | -+ (16 << PS_CFG_MAX_FETCH_CYCLE_BIT) | -+ (2 << PS_CFG_STARTCODE_WID_24_BIT)); -+ -+ amvdec_write_parser(core, PARSER_CONTROL, -+ (ES_SEARCH | ES_PARSER_START)); -+ -+ amvdec_write_parser(core, PARSER_VIDEO_START_PTR, sess->vififo_paddr); -+ amvdec_write_parser(core, PARSER_VIDEO_END_PTR, -+ sess->vififo_paddr + sess->vififo_size - 8); -+ amvdec_write_parser(core, PARSER_ES_CONTROL, -+ amvdec_read_parser(core, PARSER_ES_CONTROL) & ~1); -+ -+ if (vdec_ops->conf_esparser) -+ vdec_ops->conf_esparser(sess); -+ -+ amvdec_write_parser(core, PARSER_INT_STATUS, 0xffff); -+ amvdec_write_parser(core, PARSER_INT_ENABLE, -+ BIT(PARSER_INT_HOST_EN_BIT)); -+ -+ return 0; -+} -+ -+int esparser_init(struct platform_device *pdev, struct amvdec_core *core) -+{ -+ struct device *dev = &pdev->dev; -+ int ret; -+ int irq; -+ -+ irq = platform_get_irq(pdev, 1); -+ if (irq < 0) { -+ dev_err(dev, "Failed getting ESPARSER IRQ from dtb\n"); -+ return irq; -+ } -+ -+ ret = devm_request_irq(dev, irq, esparser_isr, IRQF_SHARED, -+ "esparserirq", core); -+ if (ret) { -+ dev_err(dev, "Failed requesting ESPARSER IRQ\n"); -+ return ret; -+ } -+ -+ core->esparser_reset = -+ devm_reset_control_get_exclusive(dev, "esparser"); -+ if (IS_ERR(core->esparser_reset)) { -+ dev_err(dev, "Failed to get esparser_reset\n"); -+ return PTR_ERR(core->esparser_reset); -+ } -+ -+ return 0; -+} -diff --git a/drivers/media/platform/meson/vdec/esparser.h b/drivers/media/platform/meson/vdec/esparser.h -new file mode 100644 -index 0000000000000..22c2ac5c6d35b ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/esparser.h -@@ -0,0 +1,28 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ */ -+ -+#ifndef __MESON_VDEC_ESPARSER_H_ -+#define __MESON_VDEC_ESPARSER_H_ -+ -+#include "vdec.h" -+ -+int esparser_init(struct platform_device *pdev, struct amvdec_core *core); -+int esparser_power_up(struct amvdec_session *sess); -+ -+/** -+ * esparser_queue_eos() - write End Of Stream sequence to the ESPARSER -+ * -+ * @core vdec core struct -+ */ -+int esparser_queue_eos(struct amvdec_core *core); -+ -+/** -+ * esparser_queue_all_src() - work handler that writes as many src buffers -+ * as possible to the ESPARSER -+ */ -+void esparser_queue_all_src(struct work_struct *work); -+ -+#endif -diff --git a/drivers/media/platform/meson/vdec/vdec.c b/drivers/media/platform/meson/vdec/vdec.c -new file mode 100644 -index 0000000000000..32e1e22282970 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/vdec.c -@@ -0,0 +1,988 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ */ -+ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include "vdec.h" -+#include "esparser.h" -+#include "vdec_helpers.h" -+ -+struct dummy_buf { -+ struct vb2_v4l2_buffer vb; -+ struct list_head list; -+}; -+ -+/* 16 MiB for parsed bitstream swap exchange */ -+#define SIZE_VIFIFO SZ_16M -+ -+static u32 get_output_size(u32 width, u32 height) -+{ -+ return ALIGN(width * height, SZ_64K); -+} -+ -+u32 amvdec_get_output_size(struct amvdec_session *sess) -+{ -+ return get_output_size(sess->width, sess->height); -+} -+EXPORT_SYMBOL_GPL(amvdec_get_output_size); -+ -+static int vdec_codec_needs_recycle(struct amvdec_session *sess) -+{ -+ struct amvdec_codec_ops *codec_ops = sess->fmt_out->codec_ops; -+ -+ return codec_ops->can_recycle && codec_ops->recycle; -+} -+ -+static int vdec_recycle_thread(void *data) -+{ -+ struct amvdec_session *sess = data; -+ struct amvdec_core *core = sess->core; -+ struct amvdec_codec_ops *codec_ops = sess->fmt_out->codec_ops; -+ struct amvdec_buffer *tmp, *n; -+ -+ while (!kthread_should_stop()) { -+ mutex_lock(&sess->bufs_recycle_lock); -+ list_for_each_entry_safe(tmp, n, &sess->bufs_recycle, list) { -+ if (!codec_ops->can_recycle(core)) -+ break; -+ -+ codec_ops->recycle(core, tmp->vb->index); -+ dev_dbg(core->dev, "Buffer %d recycled\n", -+ tmp->vb->index); -+ list_del(&tmp->list); -+ kfree(tmp); -+ } -+ mutex_unlock(&sess->bufs_recycle_lock); -+ -+ usleep_range(5000, 10000); -+ } -+ -+ return 0; -+} -+ -+static int vdec_poweron(struct amvdec_session *sess) -+{ -+ int ret; -+ struct amvdec_ops *vdec_ops = sess->fmt_out->vdec_ops; -+ -+ ret = clk_prepare_enable(sess->core->dos_parser_clk); -+ if (ret) -+ return ret; -+ -+ ret = clk_prepare_enable(sess->core->dos_clk); -+ if (ret) -+ goto disable_dos_parser; -+ -+ ret = vdec_ops->start(sess); -+ if (ret) -+ goto disable_dos; -+ -+ esparser_power_up(sess); -+ -+ return 0; -+ -+disable_dos: -+ clk_disable_unprepare(sess->core->dos_clk); -+disable_dos_parser: -+ clk_disable_unprepare(sess->core->dos_parser_clk); -+ -+ return ret; -+} -+ -+static void vdec_wait_inactive(struct amvdec_session *sess) -+{ -+ /* We consider 50ms with no IRQ to be inactive. */ -+ while (time_is_after_jiffies64(sess->last_irq_jiffies + -+ msecs_to_jiffies(50))) -+ msleep(25); -+} -+ -+static void vdec_poweroff(struct amvdec_session *sess) -+{ -+ struct amvdec_ops *vdec_ops = sess->fmt_out->vdec_ops; -+ struct amvdec_codec_ops *codec_ops = sess->fmt_out->codec_ops; -+ -+ vdec_wait_inactive(sess); -+ if (codec_ops->drain) -+ codec_ops->drain(sess); -+ -+ vdec_ops->stop(sess); -+ clk_disable_unprepare(sess->core->dos_clk); -+ clk_disable_unprepare(sess->core->dos_parser_clk); -+} -+ -+static void -+vdec_queue_recycle(struct amvdec_session *sess, struct vb2_buffer *vb) -+{ -+ struct amvdec_buffer *new_buf; -+ -+ new_buf = kmalloc(sizeof(*new_buf), GFP_KERNEL); -+ new_buf->vb = vb; -+ -+ mutex_lock(&sess->bufs_recycle_lock); -+ list_add_tail(&new_buf->list, &sess->bufs_recycle); -+ mutex_unlock(&sess->bufs_recycle_lock); -+} -+ -+static void vdec_m2m_device_run(void *priv) -+{ -+ struct amvdec_session *sess = priv; -+ -+ schedule_work(&sess->esparser_queue_work); -+} -+ -+static void vdec_m2m_job_abort(void *priv) -+{ -+ struct amvdec_session *sess = priv; -+ -+ v4l2_m2m_job_finish(sess->m2m_dev, sess->m2m_ctx); -+} -+ -+static const struct v4l2_m2m_ops vdec_m2m_ops = { -+ .device_run = vdec_m2m_device_run, -+ .job_abort = vdec_m2m_job_abort, -+}; -+ -+static int vdec_queue_setup(struct vb2_queue *q, -+ unsigned int *num_buffers, unsigned int *num_planes, -+ unsigned int sizes[], struct device *alloc_devs[]) -+{ -+ struct amvdec_session *sess = vb2_get_drv_priv(q); -+ struct amvdec_core *core = sess->core; -+ const struct amvdec_format *fmt_out = sess->fmt_out; -+ u32 pixfmt_cap = sess->pixfmt_cap; -+ -+ switch (q->type) { -+ case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE: -+ sizes[0] = amvdec_get_output_size(sess); -+ *num_planes = 1; -+ break; -+ case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE: -+ if (pixfmt_cap == V4L2_PIX_FMT_NV12M) { -+ sizes[0] = amvdec_get_output_size(sess); -+ sizes[1] = amvdec_get_output_size(sess) / 2; -+ *num_planes = 2; -+ } else if (pixfmt_cap == V4L2_PIX_FMT_YUV420M) { -+ sizes[0] = amvdec_get_output_size(sess); -+ sizes[1] = amvdec_get_output_size(sess) / 4; -+ sizes[2] = amvdec_get_output_size(sess) / 4; -+ *num_planes = 3; -+ } -+ *num_buffers = min(max(*num_buffers, fmt_out->min_buffers), -+ fmt_out->max_buffers); -+ break; -+ default: -+ return -EINVAL; -+ } -+ -+ mutex_lock(&core->lock); -+ if (core->cur_sess && core->cur_sess != sess) { -+ mutex_unlock(&core->lock); -+ return -EBUSY; -+ } -+ -+ core->cur_sess = sess; -+ mutex_unlock(&core->lock); -+ -+ return 0; -+} -+ -+static void vdec_vb2_buf_queue(struct vb2_buffer *vb) -+{ -+ struct vb2_v4l2_buffer *vbuf = to_vb2_v4l2_buffer(vb); -+ struct amvdec_session *sess = vb2_get_drv_priv(vb->vb2_queue); -+ struct v4l2_m2m_ctx *m2m_ctx = sess->m2m_ctx; -+ -+ mutex_lock(&sess->lock); -+ v4l2_m2m_buf_queue(m2m_ctx, vbuf); -+ -+ if (!sess->streamon_out || !sess->streamon_cap) -+ goto unlock; -+ -+ if (vb->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE && -+ vdec_codec_needs_recycle(sess)) -+ vdec_queue_recycle(sess, vb); -+ -+ schedule_work(&sess->esparser_queue_work); -+unlock: -+ mutex_unlock(&sess->lock); -+} -+ -+static int vdec_start_streaming(struct vb2_queue *q, unsigned int count) -+{ -+ struct amvdec_session *sess = vb2_get_drv_priv(q); -+ struct vb2_v4l2_buffer *buf; -+ int ret; -+ -+ mutex_lock(&sess->lock); -+ -+ if (q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) -+ sess->streamon_out = 1; -+ else -+ sess->streamon_cap = 1; -+ -+ if (!sess->streamon_out || !sess->streamon_cap) { -+ mutex_unlock(&sess->lock); -+ return 0; -+ } -+ -+ sess->vififo_size = SIZE_VIFIFO; -+ sess->vififo_vaddr = -+ dma_alloc_coherent(sess->core->dev, sess->vififo_size, -+ &sess->vififo_paddr, GFP_KERNEL); -+ if (!sess->vififo_vaddr) { -+ dev_err(sess->core->dev, "Failed to request VIFIFO buffer\n"); -+ ret = -ENOMEM; -+ goto bufs_done; -+ } -+ -+ sess->should_stop = 0; -+ sess->keyframe_found = 0; -+ atomic_set(&sess->esparser_queued_bufs, 0); -+ ret = vdec_poweron(sess); -+ if (ret) -+ goto vififo_free; -+ -+ sess->sequence_cap = 0; -+ if (vdec_codec_needs_recycle(sess)) -+ sess->recycle_thread = kthread_run(vdec_recycle_thread, sess, -+ "vdec_recycle"); -+ mutex_unlock(&sess->lock); -+ -+ return 0; -+ -+vififo_free: -+ dma_free_coherent(sess->core->dev, sess->vififo_size, -+ sess->vififo_vaddr, sess->vififo_paddr); -+bufs_done: -+ while ((buf = v4l2_m2m_src_buf_remove(sess->m2m_ctx))) -+ v4l2_m2m_buf_done(buf, VB2_BUF_STATE_QUEUED); -+ while ((buf = v4l2_m2m_dst_buf_remove(sess->m2m_ctx))) -+ v4l2_m2m_buf_done(buf, VB2_BUF_STATE_QUEUED); -+ -+ if (q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) -+ sess->streamon_out = 0; -+ else -+ sess->streamon_cap = 0; -+ mutex_unlock(&sess->lock); -+ return ret; -+} -+ -+static void vdec_free_canvas(struct amvdec_session *sess) -+{ -+ int i; -+ -+ for (i = 0; i < sess->canvas_num; ++i) -+ meson_canvas_free(sess->core->canvas, sess->canvas_alloc[i]); -+ -+ sess->canvas_num = 0; -+} -+ -+static void vdec_reset_timestamps(struct amvdec_session *sess) -+{ -+ struct amvdec_timestamp *tmp, *n; -+ -+ list_for_each_entry_safe(tmp, n, &sess->timestamps, list) { -+ list_del(&tmp->list); -+ kfree(tmp); -+ } -+} -+ -+static void vdec_reset_bufs_recycle(struct amvdec_session *sess) -+{ -+ struct amvdec_buffer *tmp, *n; -+ -+ list_for_each_entry_safe(tmp, n, &sess->bufs_recycle, list) { -+ list_del(&tmp->list); -+ kfree(tmp); -+ } -+} -+ -+static void vdec_stop_streaming(struct vb2_queue *q) -+{ -+ struct amvdec_session *sess = vb2_get_drv_priv(q); -+ struct vb2_v4l2_buffer *buf; -+ -+ mutex_lock(&sess->lock); -+ -+ if (sess->streamon_out && sess->streamon_cap) { -+ if (vdec_codec_needs_recycle(sess)) -+ kthread_stop(sess->recycle_thread); -+ -+ vdec_poweroff(sess); -+ vdec_free_canvas(sess); -+ dma_free_coherent(sess->core->dev, sess->vififo_size, -+ sess->vififo_vaddr, sess->vififo_paddr); -+ vdec_reset_timestamps(sess); -+ vdec_reset_bufs_recycle(sess); -+ kfree(sess->priv); -+ sess->priv = NULL; -+ } -+ -+ if (q->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) { -+ while ((buf = v4l2_m2m_src_buf_remove(sess->m2m_ctx))) -+ v4l2_m2m_buf_done(buf, VB2_BUF_STATE_ERROR); -+ -+ sess->streamon_out = 0; -+ } else { -+ while ((buf = v4l2_m2m_dst_buf_remove(sess->m2m_ctx))) -+ v4l2_m2m_buf_done(buf, VB2_BUF_STATE_ERROR); -+ -+ sess->streamon_cap = 0; -+ } -+ -+ mutex_unlock(&sess->lock); -+} -+ -+static const struct vb2_ops vdec_vb2_ops = { -+ .queue_setup = vdec_queue_setup, -+ .start_streaming = vdec_start_streaming, -+ .stop_streaming = vdec_stop_streaming, -+ .buf_queue = vdec_vb2_buf_queue, -+}; -+ -+static int -+vdec_querycap(struct file *file, void *fh, struct v4l2_capability *cap) -+{ -+ strlcpy(cap->driver, "meson-vdec", sizeof(cap->driver)); -+ strlcpy(cap->card, "Amlogic Video Decoder", sizeof(cap->card)); -+ strlcpy(cap->bus_info, "platform:meson-vdec", sizeof(cap->bus_info)); -+ -+ return 0; -+} -+ -+static const struct amvdec_format * -+find_format(const struct amvdec_format *fmts, u32 size, u32 pixfmt) -+{ -+ unsigned int i; -+ -+ for (i = 0; i < size; i++) { -+ if (fmts[i].pixfmt == pixfmt) -+ return &fmts[i]; -+ } -+ -+ return NULL; -+} -+ -+static unsigned int -+vdec_supports_pixfmt_cap(const struct amvdec_format *fmt_out, u32 pixfmt_cap) -+{ -+ int i; -+ -+ for (i = 0; fmt_out->pixfmts_cap[i]; i++) -+ if (fmt_out->pixfmts_cap[i] == pixfmt_cap) -+ return 1; -+ -+ return 0; -+} -+ -+static const struct amvdec_format * -+vdec_try_fmt_common(struct amvdec_session *sess, u32 size, -+ struct v4l2_format *f) -+{ -+ struct v4l2_pix_format_mplane *pixmp = &f->fmt.pix_mp; -+ struct v4l2_plane_pix_format *pfmt = pixmp->plane_fmt; -+ const struct amvdec_format *fmts = sess->core->platform->formats; -+ const struct amvdec_format *fmt_out; -+ -+ memset(pfmt[0].reserved, 0, sizeof(pfmt[0].reserved)); -+ memset(pixmp->reserved, 0, sizeof(pixmp->reserved)); -+ -+ if (f->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) { -+ fmt_out = find_format(fmts, size, pixmp->pixelformat); -+ if (!fmt_out) { -+ pixmp->pixelformat = V4L2_PIX_FMT_MPEG2; -+ fmt_out = find_format(fmts, size, pixmp->pixelformat); -+ pixmp->width = 1280; -+ pixmp->height = 720; -+ } -+ -+ pfmt[0].sizeimage = -+ get_output_size(pixmp->width, pixmp->height); -+ pfmt[0].bytesperline = 0; -+ pixmp->num_planes = 1; -+ } else if (f->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE) { -+ fmt_out = sess->fmt_out; -+ if (!vdec_supports_pixfmt_cap(fmt_out, pixmp->pixelformat)) -+ pixmp->pixelformat = fmt_out->pixfmts_cap[0]; -+ -+ memset(pfmt[1].reserved, 0, sizeof(pfmt[1].reserved)); -+ if (pixmp->pixelformat == V4L2_PIX_FMT_NV12M) { -+ pfmt[0].sizeimage = -+ get_output_size(pixmp->width, pixmp->height); -+ pfmt[0].bytesperline = ALIGN(pixmp->width, 64); -+ -+ pfmt[1].sizeimage = -+ get_output_size(pixmp->width, pixmp->height) / 2; -+ pfmt[1].bytesperline = ALIGN(pixmp->width, 64); -+ pixmp->num_planes = 2; -+ } else if (pixmp->pixelformat == V4L2_PIX_FMT_YUV420M) { -+ pfmt[0].sizeimage = -+ get_output_size(pixmp->width, pixmp->height); -+ pfmt[0].bytesperline = ALIGN(pixmp->width, 64); -+ -+ pfmt[1].sizeimage = -+ get_output_size(pixmp->width, pixmp->height) / 4; -+ pfmt[1].bytesperline = ALIGN(pixmp->width, 64) / 2; -+ -+ pfmt[2].sizeimage = -+ get_output_size(pixmp->width, pixmp->height) / 4; -+ pfmt[2].bytesperline = ALIGN(pixmp->width, 64) / 2; -+ pixmp->num_planes = 3; -+ } -+ } else { -+ return NULL; -+ } -+ -+ pixmp->width = clamp(pixmp->width, (u32)256, fmt_out->max_width); -+ pixmp->height = clamp(pixmp->height, (u32)144, fmt_out->max_height); -+ -+ if (pixmp->field == V4L2_FIELD_ANY) -+ pixmp->field = V4L2_FIELD_NONE; -+ -+ pixmp->flags = 0; -+ -+ return fmt_out; -+} -+ -+static int vdec_try_fmt(struct file *file, void *fh, struct v4l2_format *f) -+{ -+ struct amvdec_session *sess = -+ container_of(file->private_data, struct amvdec_session, fh); -+ -+ vdec_try_fmt_common(sess, sess->core->platform->num_formats, f); -+ -+ return 0; -+} -+ -+static int vdec_g_fmt(struct file *file, void *fh, struct v4l2_format *f) -+{ -+ struct amvdec_session *sess = -+ container_of(file->private_data, struct amvdec_session, fh); -+ struct v4l2_pix_format_mplane *pixmp = &f->fmt.pix_mp; -+ -+ if (f->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE) -+ pixmp->pixelformat = sess->pixfmt_cap; -+ else if (f->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) -+ pixmp->pixelformat = sess->fmt_out->pixfmt; -+ -+ if (f->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE) { -+ pixmp->width = sess->width; -+ pixmp->height = sess->height; -+ pixmp->colorspace = sess->colorspace; -+ pixmp->ycbcr_enc = sess->ycbcr_enc; -+ pixmp->quantization = sess->quantization; -+ pixmp->xfer_func = sess->xfer_func; -+ } else if (f->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) { -+ pixmp->width = sess->width; -+ pixmp->height = sess->height; -+ } -+ -+ vdec_try_fmt_common(sess, sess->core->platform->num_formats, f); -+ -+ return 0; -+} -+ -+static int vdec_s_fmt(struct file *file, void *fh, struct v4l2_format *f) -+{ -+ struct amvdec_session *sess = -+ container_of(file->private_data, struct amvdec_session, fh); -+ struct v4l2_pix_format_mplane *pixmp = &f->fmt.pix_mp; -+ u32 num_formats = sess->core->platform->num_formats; -+ const struct amvdec_format *fmt_out; -+ struct v4l2_pix_format_mplane orig_pixmp; -+ struct v4l2_format format; -+ u32 pixfmt_out = 0, pixfmt_cap = 0; -+ -+ orig_pixmp = *pixmp; -+ -+ fmt_out = vdec_try_fmt_common(sess, num_formats, f); -+ -+ if (f->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) { -+ pixfmt_out = pixmp->pixelformat; -+ pixfmt_cap = sess->pixfmt_cap; -+ } else if (f->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE) { -+ pixfmt_cap = pixmp->pixelformat; -+ pixfmt_out = sess->fmt_out->pixfmt; -+ } -+ -+ memset(&format, 0, sizeof(format)); -+ -+ format.type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE; -+ format.fmt.pix_mp.pixelformat = pixfmt_out; -+ format.fmt.pix_mp.width = orig_pixmp.width; -+ format.fmt.pix_mp.height = orig_pixmp.height; -+ vdec_try_fmt_common(sess, num_formats, &format); -+ -+ if (f->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) { -+ sess->width = format.fmt.pix_mp.width; -+ sess->height = format.fmt.pix_mp.height; -+ sess->colorspace = pixmp->colorspace; -+ sess->ycbcr_enc = pixmp->ycbcr_enc; -+ sess->quantization = pixmp->quantization; -+ sess->xfer_func = pixmp->xfer_func; -+ } -+ -+ memset(&format, 0, sizeof(format)); -+ -+ format.type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE; -+ format.fmt.pix_mp.pixelformat = pixfmt_cap; -+ format.fmt.pix_mp.width = orig_pixmp.width; -+ format.fmt.pix_mp.height = orig_pixmp.height; -+ vdec_try_fmt_common(sess, num_formats, &format); -+ -+ sess->width = format.fmt.pix_mp.width; -+ sess->height = format.fmt.pix_mp.height; -+ -+ if (f->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) -+ sess->fmt_out = fmt_out; -+ else if (f->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE) -+ sess->pixfmt_cap = format.fmt.pix_mp.pixelformat; -+ -+ return 0; -+} -+ -+static int vdec_enum_fmt(struct file *file, void *fh, struct v4l2_fmtdesc *f) -+{ -+ struct amvdec_session *sess = -+ container_of(file->private_data, struct amvdec_session, fh); -+ const struct vdec_platform *platform = sess->core->platform; -+ const struct amvdec_format *fmt_out; -+ -+ memset(f->reserved, 0, sizeof(f->reserved)); -+ -+ if (f->type == V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) { -+ if (f->index >= platform->num_formats) -+ return -EINVAL; -+ -+ fmt_out = &platform->formats[f->index]; -+ f->pixelformat = fmt_out->pixfmt; -+ } else if (f->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE) { -+ fmt_out = sess->fmt_out; -+ if (f->index >= 4 || !fmt_out->pixfmts_cap[f->index]) -+ return -EINVAL; -+ -+ f->pixelformat = fmt_out->pixfmts_cap[f->index]; -+ } else { -+ return -EINVAL; -+ } -+ -+ return 0; -+} -+ -+static int vdec_enum_framesizes(struct file *file, void *fh, -+ struct v4l2_frmsizeenum *fsize) -+{ -+ struct amvdec_session *sess = -+ container_of(file->private_data, struct amvdec_session, fh); -+ const struct amvdec_format *formats = sess->core->platform->formats; -+ const struct amvdec_format *fmt; -+ u32 num_formats = sess->core->platform->num_formats; -+ -+ fmt = find_format(formats, num_formats, fsize->pixel_format); -+ if (!fmt || fsize->index) -+ return -EINVAL; -+ -+ fsize->type = V4L2_FRMSIZE_TYPE_STEPWISE; -+ -+ fsize->stepwise.min_width = 256; -+ fsize->stepwise.max_width = fmt->max_width; -+ fsize->stepwise.step_width = 1; -+ fsize->stepwise.min_height = 144; -+ fsize->stepwise.max_height = fmt->max_height; -+ fsize->stepwise.step_height = 1; -+ -+ return 0; -+} -+ -+static int -+vdec_try_decoder_cmd(struct file *file, void *fh, struct v4l2_decoder_cmd *cmd) -+{ -+ switch (cmd->cmd) { -+ case V4L2_DEC_CMD_STOP: -+ if (cmd->flags & V4L2_DEC_CMD_STOP_TO_BLACK) -+ return -EINVAL; -+ break; -+ default: -+ return -EINVAL; -+ } -+ -+ return 0; -+} -+ -+static int -+vdec_decoder_cmd(struct file *file, void *fh, struct v4l2_decoder_cmd *cmd) -+{ -+ struct amvdec_session *sess = -+ container_of(file->private_data, struct amvdec_session, fh); -+ struct amvdec_codec_ops *codec_ops = sess->fmt_out->codec_ops; -+ int ret; -+ -+ ret = vdec_try_decoder_cmd(file, fh, cmd); -+ if (ret) -+ return ret; -+ -+ if (!(sess->streamon_out & sess->streamon_cap)) -+ goto unlock; -+ -+ dev_dbg(sess->core->dev, "Received V4L2_DEC_CMD_STOP\n"); -+ sess->should_stop = 1; -+ -+ vdec_wait_inactive(sess); -+ -+ mutex_lock(&sess->lock); -+ if (codec_ops->drain) -+ codec_ops->drain(sess); -+ else -+ esparser_queue_eos(sess->core); -+ -+unlock: -+ mutex_unlock(&sess->lock); -+ return ret; -+} -+ -+static int vdec_subscribe_event(struct v4l2_fh *fh, -+ const struct v4l2_event_subscription *sub) -+{ -+ switch (sub->type) { -+ case V4L2_EVENT_EOS: -+ return v4l2_event_subscribe(fh, sub, 2, NULL); -+ default: -+ return -EINVAL; -+ } -+} -+ -+static const struct v4l2_ioctl_ops vdec_ioctl_ops = { -+ .vidioc_querycap = vdec_querycap, -+ .vidioc_enum_fmt_vid_cap_mplane = vdec_enum_fmt, -+ .vidioc_enum_fmt_vid_out_mplane = vdec_enum_fmt, -+ .vidioc_s_fmt_vid_cap_mplane = vdec_s_fmt, -+ .vidioc_s_fmt_vid_out_mplane = vdec_s_fmt, -+ .vidioc_g_fmt_vid_cap_mplane = vdec_g_fmt, -+ .vidioc_g_fmt_vid_out_mplane = vdec_g_fmt, -+ .vidioc_try_fmt_vid_cap_mplane = vdec_try_fmt, -+ .vidioc_try_fmt_vid_out_mplane = vdec_try_fmt, -+ .vidioc_reqbufs = v4l2_m2m_ioctl_reqbufs, -+ .vidioc_querybuf = v4l2_m2m_ioctl_querybuf, -+ .vidioc_create_bufs = v4l2_m2m_ioctl_create_bufs, -+ .vidioc_prepare_buf = v4l2_m2m_ioctl_prepare_buf, -+ .vidioc_qbuf = v4l2_m2m_ioctl_qbuf, -+ .vidioc_expbuf = v4l2_m2m_ioctl_expbuf, -+ .vidioc_dqbuf = v4l2_m2m_ioctl_dqbuf, -+ .vidioc_streamon = v4l2_m2m_ioctl_streamon, -+ .vidioc_streamoff = v4l2_m2m_ioctl_streamoff, -+ .vidioc_enum_framesizes = vdec_enum_framesizes, -+ .vidioc_subscribe_event = vdec_subscribe_event, -+ .vidioc_unsubscribe_event = v4l2_event_unsubscribe, -+ .vidioc_try_decoder_cmd = vdec_try_decoder_cmd, -+ .vidioc_decoder_cmd = vdec_decoder_cmd, -+}; -+ -+static int m2m_queue_init(void *priv, struct vb2_queue *src_vq, -+ struct vb2_queue *dst_vq) -+{ -+ struct amvdec_session *sess = priv; -+ int ret; -+ -+ src_vq->type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE; -+ src_vq->io_modes = VB2_MMAP | VB2_DMABUF; -+ src_vq->timestamp_flags = V4L2_BUF_FLAG_TIMESTAMP_COPY; -+ src_vq->ops = &vdec_vb2_ops; -+ src_vq->mem_ops = &vb2_dma_contig_memops; -+ src_vq->drv_priv = sess; -+ src_vq->buf_struct_size = sizeof(struct dummy_buf); -+ src_vq->allow_zero_bytesused = 1; -+ src_vq->min_buffers_needed = 1; -+ src_vq->dev = sess->core->dev; -+ ret = vb2_queue_init(src_vq); -+ if (ret) -+ return ret; -+ -+ dst_vq->type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE; -+ dst_vq->io_modes = VB2_MMAP | VB2_DMABUF; -+ dst_vq->timestamp_flags = V4L2_BUF_FLAG_TIMESTAMP_COPY; -+ dst_vq->ops = &vdec_vb2_ops; -+ dst_vq->mem_ops = &vb2_dma_contig_memops; -+ dst_vq->drv_priv = sess; -+ dst_vq->buf_struct_size = sizeof(struct dummy_buf); -+ dst_vq->allow_zero_bytesused = 1; -+ dst_vq->min_buffers_needed = 1; -+ dst_vq->dev = sess->core->dev; -+ ret = vb2_queue_init(dst_vq); -+ if (ret) { -+ vb2_queue_release(src_vq); -+ return ret; -+ } -+ -+ return 0; -+} -+ -+static int vdec_open(struct file *file) -+{ -+ struct amvdec_core *core = video_drvdata(file); -+ struct device *dev = core->dev; -+ const struct amvdec_format *formats = core->platform->formats; -+ struct amvdec_session *sess; -+ int ret; -+ -+ sess = kzalloc(sizeof(*sess), GFP_KERNEL); -+ if (!sess) { -+ mutex_unlock(&core->lock); -+ return -ENOMEM; -+ } -+ -+ sess->core = core; -+ -+ sess->m2m_dev = v4l2_m2m_init(&vdec_m2m_ops); -+ if (IS_ERR(sess->m2m_dev)) { -+ dev_err(dev, "Fail to v4l2_m2m_init\n"); -+ ret = PTR_ERR(sess->m2m_dev); -+ goto err_free_sess; -+ } -+ -+ sess->m2m_ctx = v4l2_m2m_ctx_init(sess->m2m_dev, sess, m2m_queue_init); -+ if (IS_ERR(sess->m2m_ctx)) { -+ dev_err(dev, "Fail to v4l2_m2m_ctx_init\n"); -+ ret = PTR_ERR(sess->m2m_ctx); -+ goto err_m2m_release; -+ } -+ -+ sess->pixfmt_cap = formats[0].pixfmts_cap[0]; -+ sess->fmt_out = &formats[0]; -+ sess->width = 1280; -+ sess->height = 720; -+ -+ INIT_LIST_HEAD(&sess->timestamps); -+ INIT_LIST_HEAD(&sess->bufs_recycle); -+ INIT_WORK(&sess->esparser_queue_work, esparser_queue_all_src); -+ mutex_init(&sess->lock); -+ mutex_init(&sess->bufs_recycle_lock); -+ spin_lock_init(&sess->ts_spinlock); -+ -+ v4l2_fh_init(&sess->fh, core->vdev_dec); -+ v4l2_fh_add(&sess->fh); -+ sess->fh.m2m_ctx = sess->m2m_ctx; -+ file->private_data = &sess->fh; -+ -+ return 0; -+ -+err_m2m_release: -+ v4l2_m2m_release(sess->m2m_dev); -+err_free_sess: -+ kfree(sess); -+ return ret; -+} -+ -+static int vdec_close(struct file *file) -+{ -+ struct amvdec_session *sess = -+ container_of(file->private_data, struct amvdec_session, fh); -+ struct amvdec_core *core = sess->core; -+ -+ v4l2_m2m_ctx_release(sess->m2m_ctx); -+ v4l2_m2m_release(sess->m2m_dev); -+ v4l2_fh_del(&sess->fh); -+ v4l2_fh_exit(&sess->fh); -+ -+ mutex_destroy(&sess->lock); -+ mutex_destroy(&sess->bufs_recycle_lock); -+ -+ kfree(sess); -+ -+ if (core->cur_sess == sess) -+ core->cur_sess = NULL; -+ -+ return 0; -+} -+ -+static const struct v4l2_file_operations vdec_fops = { -+ .owner = THIS_MODULE, -+ .open = vdec_open, -+ .release = vdec_close, -+ .unlocked_ioctl = video_ioctl2, -+ .poll = v4l2_m2m_fop_poll, -+ .mmap = v4l2_m2m_fop_mmap, -+#ifdef CONFIG_COMPAT -+ .compat_ioctl32 = v4l2_compat_ioctl32, -+#endif -+}; -+ -+static irqreturn_t vdec_isr(int irq, void *data) -+{ -+ struct amvdec_core *core = data; -+ struct amvdec_session *sess = core->cur_sess; -+ -+ sess->last_irq_jiffies = get_jiffies_64(); -+ -+ return sess->fmt_out->codec_ops->isr(sess); -+} -+ -+static irqreturn_t vdec_threaded_isr(int irq, void *data) -+{ -+ struct amvdec_core *core = data; -+ struct amvdec_session *sess = core->cur_sess; -+ -+ return sess->fmt_out->codec_ops->threaded_isr(sess); -+} -+ -+static const struct of_device_id vdec_dt_match[] = { -+ { .compatible = "amlogic,gxbb-vdec", -+ .data = &vdec_platform_gxbb }, -+ { .compatible = "amlogic,gxm-vdec", -+ .data = &vdec_platform_gxm }, -+ { .compatible = "amlogic,gxl-vdec", -+ .data = &vdec_platform_gxl }, -+ {} -+}; -+MODULE_DEVICE_TABLE(of, vdec_dt_match); -+ -+static int vdec_probe(struct platform_device *pdev) -+{ -+ struct device *dev = &pdev->dev; -+ struct video_device *vdev; -+ struct amvdec_core *core; -+ struct resource *r; -+ const struct of_device_id *of_id; -+ int irq; -+ int ret; -+ -+ core = devm_kzalloc(dev, sizeof(*core), GFP_KERNEL); -+ if (!core) -+ return -ENOMEM; -+ -+ core->dev = dev; -+ platform_set_drvdata(pdev, core); -+ -+ r = platform_get_resource_byname(pdev, IORESOURCE_MEM, "dos"); -+ core->dos_base = devm_ioremap_resource(dev, r); -+ if (IS_ERR(core->dos_base)) { -+ dev_err(dev, "Couldn't remap DOS memory\n"); -+ return PTR_ERR(core->dos_base); -+ } -+ -+ r = platform_get_resource_byname(pdev, IORESOURCE_MEM, "esparser"); -+ core->esparser_base = devm_ioremap_resource(dev, r); -+ if (IS_ERR(core->esparser_base)) { -+ dev_err(dev, "Couldn't remap ESPARSER memory\n"); -+ return PTR_ERR(core->esparser_base); -+ } -+ -+ core->regmap_ao = syscon_regmap_lookup_by_phandle(dev->of_node, -+ "amlogic,ao-sysctrl"); -+ if (IS_ERR(core->regmap_ao)) { -+ dev_err(dev, "Couldn't regmap AO sysctrl\n"); -+ return PTR_ERR(core->regmap_ao); -+ } -+ -+ core->canvas = meson_canvas_get(dev); -+ if (!core->canvas) -+ return PTR_ERR(core->canvas); -+ -+ core->dos_parser_clk = devm_clk_get(dev, "dos_parser"); -+ if (IS_ERR(core->dos_parser_clk)) -+ return -EPROBE_DEFER; -+ -+ core->dos_clk = devm_clk_get(dev, "dos"); -+ if (IS_ERR(core->dos_clk)) -+ return -EPROBE_DEFER; -+ -+ core->vdec_1_clk = devm_clk_get(dev, "vdec_1"); -+ if (IS_ERR(core->vdec_1_clk)) -+ return -EPROBE_DEFER; -+ -+ core->vdec_hevc_clk = devm_clk_get(dev, "vdec_hevc"); -+ if (IS_ERR(core->vdec_hevc_clk)) -+ return -EPROBE_DEFER; -+ -+ irq = platform_get_irq(pdev, 0); -+ if (irq < 0) -+ return irq; -+ -+ ret = devm_request_threaded_irq(core->dev, irq, vdec_isr, -+ vdec_threaded_isr, IRQF_ONESHOT, -+ "vdec", core); -+ if (ret) -+ return ret; -+ -+ ret = esparser_init(pdev, core); -+ if (ret) -+ return ret; -+ -+ ret = v4l2_device_register(dev, &core->v4l2_dev); -+ if (ret) { -+ dev_err(dev, "Couldn't register v4l2 device\n"); -+ return -ENOMEM; -+ } -+ -+ vdev = video_device_alloc(); -+ if (!vdev) { -+ ret = -ENOMEM; -+ goto err_vdev_release; -+ } -+ -+ strlcpy(vdev->name, "meson-video-decoder", sizeof(vdev->name)); -+ vdev->release = video_device_release; -+ vdev->fops = &vdec_fops; -+ vdev->ioctl_ops = &vdec_ioctl_ops; -+ vdev->vfl_dir = VFL_DIR_M2M; -+ vdev->v4l2_dev = &core->v4l2_dev; -+ vdev->device_caps = V4L2_CAP_VIDEO_M2M_MPLANE | V4L2_CAP_STREAMING; -+ -+ ret = video_register_device(vdev, VFL_TYPE_GRABBER, -1); -+ if (ret) { -+ dev_err(dev, "Failed registering video device\n"); -+ goto err_vdev_release; -+ } -+ -+ of_id = of_match_node(vdec_dt_match, dev->of_node); -+ core->platform = of_id->data; -+ core->vdev_dec = vdev; -+ core->dev_dec = dev; -+ mutex_init(&core->lock); -+ -+ video_set_drvdata(vdev, core); -+ -+ return 0; -+ -+err_vdev_release: -+ video_device_release(vdev); -+ return ret; -+} -+ -+static int vdec_remove(struct platform_device *pdev) -+{ -+ struct amvdec_core *core = platform_get_drvdata(pdev); -+ -+ video_unregister_device(core->vdev_dec); -+ -+ return 0; -+} -+ -+static struct platform_driver meson_vdec_driver = { -+ .probe = vdec_probe, -+ .remove = vdec_remove, -+ .driver = { -+ .name = "meson-vdec", -+ .of_match_table = vdec_dt_match, -+ }, -+}; -+module_platform_driver(meson_vdec_driver); -+ -+MODULE_DESCRIPTION("Meson video decoder driver for GXBB/GXL/GXM"); -+MODULE_AUTHOR("Maxime Jourdan "); -+MODULE_LICENSE("GPL"); -diff --git a/drivers/media/platform/meson/vdec/vdec.h b/drivers/media/platform/meson/vdec/vdec.h -new file mode 100644 -index 0000000000000..8250fb82dfabe ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/vdec.h -@@ -0,0 +1,234 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ */ -+ -+#ifndef __MESON_VDEC_CORE_H_ -+#define __MESON_VDEC_CORE_H_ -+ -+/* 32 buffers in 3-plane YUV420 */ -+#define MAX_CANVAS (32 * 3) -+ -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include "vdec_platform.h" -+ -+struct amvdec_buffer { -+ struct list_head list; -+ struct vb2_buffer *vb; -+}; -+ -+struct amvdec_timestamp { -+ struct list_head list; -+ u64 ts; -+}; -+ -+struct amvdec_session; -+ -+/** -+ * struct amvdec_core - device parameters, singleton -+ * -+ * @dos_base: DOS memory base address -+ * @esparser_base: PARSER memory base address -+ * @regmap_ao: regmap for the AO bus -+ * @dev: core device -+ * @dev_dec: decoder device -+ * @platform: platform-specific data -+ * @canvas: canvas provider reference -+ * @dos_parser_clk: DOS_PARSER clock -+ * @dos_clk: DOS clock -+ * @vdec_1_clk: VDEC_1 clock -+ * @vdec_hevc_clk: VDEC_HEVC clock -+ * @esparser_reset: RESET for the PARSER -+ * @vdec_dec: video device for the decoder -+ * @v4l2_dev: v4l2 device -+ * @cur_sess: current decoding session -+ * @lock: lock for this structure -+ */ -+struct amvdec_core { -+ void __iomem *dos_base; -+ void __iomem *esparser_base; -+ struct regmap *regmap_ao; -+ -+ struct device *dev; -+ struct device *dev_dec; -+ const struct vdec_platform *platform; -+ -+ struct meson_canvas *canvas; -+ -+ struct clk *dos_parser_clk; -+ struct clk *dos_clk; -+ struct clk *vdec_1_clk; -+ struct clk *vdec_hevc_clk; -+ -+ struct reset_control *esparser_reset; -+ -+ struct video_device *vdev_dec; -+ struct v4l2_device v4l2_dev; -+ -+ struct amvdec_session *cur_sess; -+ struct mutex lock; -+}; -+ -+/** -+ * struct amvdec_ops - vdec operations -+ * -+ * @start: mandatory call when the vdec needs to initialize -+ * @stop: mandatory call when the vdec needs to stop -+ * @conf_esparser: mandatory call to let the vdec configure the ESPARSER -+ * @vififo_level: mandatory call to get the current amount of data -+ * in the VIFIFO -+ */ -+struct amvdec_ops { -+ int (*start)(struct amvdec_session *sess); -+ int (*stop)(struct amvdec_session *sess); -+ void (*conf_esparser)(struct amvdec_session *sess); -+ u32 (*vififo_level)(struct amvdec_session *sess); -+}; -+ -+/** -+ * struct amvdec_codec_ops - codec operations -+ * -+ * @start: mandatory call when the codec needs to initialize -+ * @stop: mandatory call when the codec needs to stop -+ * @load_extended_firmware: optional call to load additional firmware bits -+ * @num_pending_bufs: optional call to get the number of dst buffers on hold -+ * @can_recycle: optional call to know if the codec is ready to recycle -+ * a dst buffer -+ * @recycle: optional call to tell the codec to recycle a dst buffer. Must go -+ * in pair with can_recycle -+ * @drain: optional call if the codec has a custom way of draining -+ * @isr: mandatory call when the ISR triggers -+ * @threaded_isr: mandatory call for the threaded ISR -+ */ -+struct amvdec_codec_ops { -+ int (*start)(struct amvdec_session *sess); -+ int (*stop)(struct amvdec_session *sess); -+ int (*load_extended_firmware)(struct amvdec_session *sess, -+ const u8 *data, u32 len); -+ u32 (*num_pending_bufs)(struct amvdec_session *sess); -+ int (*can_recycle)(struct amvdec_core *core); -+ void (*recycle)(struct amvdec_core *core, u32 buf_idx); -+ void (*drain)(struct amvdec_session *sess); -+ irqreturn_t (*isr)(struct amvdec_session *sess); -+ irqreturn_t (*threaded_isr)(struct amvdec_session *sess); -+}; -+ -+/** -+ * struct amvdec_format - describes one of the OUTPUT (src) format supported -+ * -+ * @pixfmt: V4L2 pixel format -+ * @min_buffers: minimum amount of CAPTURE (dst) buffers -+ * @max_buffers: maximum amount of CAPTURE (dst) buffers -+ * @max_width: maximum picture width supported -+ * @max_height: maximum picture height supported -+ * @vdec_ops: the VDEC operations that support this format -+ * @codec_ops: the codec operations that support this format -+ * @firmware_path: Path to the firmware that supports this format -+ * @pixfmts_cap: list of CAPTURE pixel formats available with pixfmt -+ */ -+struct amvdec_format { -+ u32 pixfmt; -+ u32 min_buffers; -+ u32 max_buffers; -+ u32 max_width; -+ u32 max_height; -+ -+ struct amvdec_ops *vdec_ops; -+ struct amvdec_codec_ops *codec_ops; -+ -+ char *firmware_path; -+ u32 pixfmts_cap[4]; -+}; -+ -+/** -+ * struct amvdec_session - decoding session parameters -+ * -+ * @core: reference to the vdec core struct -+ * @fh: v4l2 file handle -+ * @m2m_dev: v4l2 m2m device -+ * @m2m_ctx: v4l2 m2m context -+ * @lock: session lock -+ * @fmt_out: vdec pixel format for the OUTPUT queue -+ * @pixfmt_cap: V4L2 pixel format for the CAPTURE queue -+ * @width: current picture width -+ * @height: current picture height -+ * @colorspace: current colorspace -+ * @ycbcr_enc: current ycbcr_enc -+ * @quantization: current quantization -+ * @xfer_func: current transfer function -+ * @esparser_queued_bufs: number of buffers currently queued into ESPARSER -+ * @esparser_queue_work: work struct for the ESPARSER to process src buffers -+ * @streamon_cap: stream on flag for capture queue -+ * @streamon_out: stream on flag for output queue -+ * @sequence_cap: capture sequence counter -+ * @should_stop: flag set is userspacec signaled EOS via command -+ * or empty buffer -+ * @keyframe_found: flag set once a keyframe has been parsed -+ * @canvas_alloc: array of all the canvas IDs allocated -+ * @canvas_num: number of canvas IDs allocated -+ * @vififo_vaddr: virtual address for the VIFIFO -+ * @vififo_paddr: physical address for the VIFIFO -+ * @vififo_size: size of the VIFIFO dma alloc -+ * @bufs_recycle: list of buffers that need to be recycled -+ * @bufs_recycle_lock: lock for the bufs_recycle list -+ * @recycle_thread: task struct for the recycling thread -+ * @timestamps: chronological list of src timestamps -+ * @ts_spinlock: spinlock for the timestamps list -+ * @last_irq_jiffies: tracks last time the vdec triggered an IRQ -+ * @priv: codec private data -+ */ -+struct amvdec_session { -+ struct amvdec_core *core; -+ -+ struct v4l2_fh fh; -+ struct v4l2_m2m_dev *m2m_dev; -+ struct v4l2_m2m_ctx *m2m_ctx; -+ struct mutex lock; -+ -+ const struct amvdec_format *fmt_out; -+ u32 pixfmt_cap; -+ -+ u32 width; -+ u32 height; -+ u32 colorspace; -+ u8 ycbcr_enc; -+ u8 quantization; -+ u8 xfer_func; -+ -+ atomic_t esparser_queued_bufs; -+ struct work_struct esparser_queue_work; -+ -+ unsigned int streamon_cap, streamon_out; -+ unsigned int sequence_cap; -+ unsigned int should_stop; -+ unsigned int keyframe_found; -+ -+ u8 canvas_alloc[MAX_CANVAS]; -+ u32 canvas_num; -+ -+ void *vififo_vaddr; -+ dma_addr_t vififo_paddr; -+ u32 vififo_size; -+ -+ struct list_head bufs_recycle; -+ struct mutex bufs_recycle_lock; -+ struct task_struct *recycle_thread; -+ -+ struct list_head timestamps; -+ spinlock_t ts_spinlock; -+ -+ u64 last_irq_jiffies; -+ -+ void *priv; -+}; -+ -+u32 amvdec_get_output_size(struct amvdec_session *sess); -+ -+#endif -diff --git a/drivers/media/platform/meson/vdec/vdec_1.c b/drivers/media/platform/meson/vdec/vdec_1.c -new file mode 100644 -index 0000000000000..29f6305a6276b ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/vdec_1.c -@@ -0,0 +1,228 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ * -+ * VDEC_1 is a video decoding block that allows decoding of -+ * MPEG 1/2/4, H.263, H.264, MJPEG, VC1 -+ */ -+ -+#include -+#include -+ -+#include "vdec_1.h" -+#include "vdec_helpers.h" -+#include "dos_regs.h" -+ -+/* AO Registers */ -+#define AO_RTI_GEN_PWR_SLEEP0 0xe8 -+#define AO_RTI_GEN_PWR_ISO0 0xec -+ #define GEN_PWR_VDEC_1 (BIT(3) | BIT(2)) -+ -+#define MC_SIZE (4096 * 4) -+ -+static int -+vdec_1_load_firmware(struct amvdec_session *sess, const char *fwname) -+{ -+ const struct firmware *fw; -+ struct amvdec_core *core = sess->core; -+ struct device *dev = core->dev_dec; -+ struct amvdec_codec_ops *codec_ops = sess->fmt_out->codec_ops; -+ static void *mc_addr; -+ static dma_addr_t mc_addr_map; -+ int ret; -+ u32 i = 1000; -+ -+ ret = request_firmware(&fw, fwname, dev); -+ if (ret < 0) -+ return -EINVAL; -+ -+ if (fw->size < MC_SIZE) { -+ dev_err(dev, "Firmware size %zu is too small. Expected %u.\n", -+ fw->size, MC_SIZE); -+ ret = -EINVAL; -+ goto release_firmware; -+ } -+ -+ mc_addr = dma_alloc_coherent(core->dev, MC_SIZE, -+ &mc_addr_map, GFP_KERNEL); -+ if (!mc_addr) { -+ dev_err(dev, -+ "Failed allocating memory for firmware loading\n"); -+ ret = -ENOMEM; -+ goto release_firmware; -+ } -+ -+ memcpy(mc_addr, fw->data, MC_SIZE); -+ -+ amvdec_write_dos(core, MPSR, 0); -+ amvdec_write_dos(core, CPSR, 0); -+ -+ amvdec_clear_dos_bits(core, MDEC_PIC_DC_CTRL, BIT(31)); -+ -+ amvdec_write_dos(core, IMEM_DMA_ADR, mc_addr_map); -+ amvdec_write_dos(core, IMEM_DMA_COUNT, MC_SIZE / 4); -+ amvdec_write_dos(core, IMEM_DMA_CTRL, (0x8000 | (7 << 16))); -+ -+ while (--i && amvdec_read_dos(core, IMEM_DMA_CTRL) & 0x8000) { } -+ -+ if (i == 0) { -+ dev_err(dev, "Firmware load fail (DMA hang?)\n"); -+ ret = -EINVAL; -+ goto free_mc; -+ } -+ -+ if (codec_ops->load_extended_firmware) -+ codec_ops->load_extended_firmware(sess, fw->data + MC_SIZE, -+ fw->size - MC_SIZE); -+ -+free_mc: -+ dma_free_coherent(core->dev, MC_SIZE, mc_addr, mc_addr_map); -+release_firmware: -+ release_firmware(fw); -+ return ret; -+} -+ -+int vdec_1_stbuf_power_up(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ -+ amvdec_write_dos(core, VLD_MEM_VIFIFO_CONTROL, 0); -+ amvdec_write_dos(core, VLD_MEM_VIFIFO_WRAP_COUNT, 0); -+ amvdec_write_dos(core, POWER_CTL_VLD, BIT(4)); -+ -+ amvdec_write_dos(core, VLD_MEM_VIFIFO_START_PTR, sess->vififo_paddr); -+ amvdec_write_dos(core, VLD_MEM_VIFIFO_CURR_PTR, sess->vififo_paddr); -+ amvdec_write_dos(core, VLD_MEM_VIFIFO_END_PTR, -+ sess->vififo_paddr + sess->vififo_size - 8); -+ -+ amvdec_write_dos_bits(core, VLD_MEM_VIFIFO_CONTROL, 1); -+ amvdec_clear_dos_bits(core, VLD_MEM_VIFIFO_CONTROL, 1); -+ -+ amvdec_write_dos(core, VLD_MEM_VIFIFO_BUF_CNTL, MEM_BUFCTRL_MANUAL); -+ amvdec_write_dos(core, VLD_MEM_VIFIFO_WP, sess->vififo_paddr); -+ -+ amvdec_write_dos_bits(core, VLD_MEM_VIFIFO_BUF_CNTL, 1); -+ amvdec_clear_dos_bits(core, VLD_MEM_VIFIFO_BUF_CNTL, 1); -+ -+ amvdec_write_dos_bits(core, VLD_MEM_VIFIFO_CONTROL, -+ (0x11 << MEM_FIFO_CNT_BIT) | MEM_FILL_ON_LEVEL | -+ MEM_CTRL_FILL_EN | MEM_CTRL_EMPTY_EN); -+ -+ return 0; -+} -+ -+static void vdec_1_conf_esparser(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ -+ /* VDEC_1 specific ESPARSER stuff */ -+ amvdec_write_dos(core, DOS_GEN_CTRL0, 0); -+ amvdec_write_dos(core, VLD_MEM_VIFIFO_BUF_CNTL, 1); -+ amvdec_clear_dos_bits(core, VLD_MEM_VIFIFO_BUF_CNTL, 1); -+} -+ -+static u32 vdec_1_vififo_level(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ -+ return amvdec_read_dos(core, VLD_MEM_VIFIFO_LEVEL); -+} -+ -+static int vdec_1_stop(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct amvdec_codec_ops *codec_ops = sess->fmt_out->codec_ops; -+ -+ amvdec_write_dos(core, MPSR, 0); -+ amvdec_write_dos(core, CPSR, 0); -+ amvdec_write_dos(core, ASSIST_MBOX1_MASK, 0); -+ -+ amvdec_write_dos(core, DOS_SW_RESET0, BIT(12) | BIT(11)); -+ amvdec_write_dos(core, DOS_SW_RESET0, 0); -+ amvdec_read_dos(core, DOS_SW_RESET0); -+ -+ /* enable vdec1 isolation */ -+ regmap_write(core->regmap_ao, AO_RTI_GEN_PWR_ISO0, 0xc0); -+ /* power off vdec1 memories */ -+ amvdec_write_dos(core, DOS_MEM_PD_VDEC, 0xffffffff); -+ /* power off vdec1 */ -+ regmap_update_bits(core->regmap_ao, AO_RTI_GEN_PWR_SLEEP0, -+ GEN_PWR_VDEC_1, GEN_PWR_VDEC_1); -+ -+ clk_disable_unprepare(core->vdec_1_clk); -+ -+ if (sess->priv) -+ codec_ops->stop(sess); -+ -+ return 0; -+} -+ -+static int vdec_1_start(struct amvdec_session *sess) -+{ -+ int ret; -+ struct amvdec_core *core = sess->core; -+ struct amvdec_codec_ops *codec_ops = sess->fmt_out->codec_ops; -+ -+ /* Configure the vdec clk to the maximum available */ -+ clk_set_rate(core->vdec_1_clk, 666666666); -+ ret = clk_prepare_enable(core->vdec_1_clk); -+ if (ret) -+ return ret; -+ -+ regmap_update_bits(core->regmap_ao, AO_RTI_GEN_PWR_SLEEP0, -+ GEN_PWR_VDEC_1, 0); -+ udelay(10); -+ -+ /* Reset VDEC1 */ -+ amvdec_write_dos(core, DOS_SW_RESET0, 0xfffffffc); -+ amvdec_write_dos(core, DOS_SW_RESET0, 0x00000000); -+ -+ amvdec_write_dos(core, DOS_GCLK_EN0, 0x3ff); -+ -+ /* enable VDEC Memories */ -+ amvdec_write_dos(core, DOS_MEM_PD_VDEC, 0); -+ /* Remove VDEC1 Isolation */ -+ regmap_write(core->regmap_ao, AO_RTI_GEN_PWR_ISO0, 0); -+ /* Reset DOS top registers */ -+ amvdec_write_dos(core, DOS_VDEC_MCRCC_STALL_CTRL, 0); -+ -+ amvdec_write_dos(core, GCLK_EN, 0x3ff); -+ amvdec_clear_dos_bits(core, MDEC_PIC_DC_CTRL, BIT(31)); -+ -+ vdec_1_stbuf_power_up(sess); -+ -+ ret = vdec_1_load_firmware(sess, sess->fmt_out->firmware_path); -+ if (ret) -+ goto stop; -+ -+ ret = codec_ops->start(sess); -+ if (ret) -+ goto stop; -+ -+ /* Enable IRQ */ -+ amvdec_write_dos(core, ASSIST_MBOX1_CLR_REG, 1); -+ amvdec_write_dos(core, ASSIST_MBOX1_MASK, 1); -+ -+ /* Enable 2-plane output */ -+ if (sess->pixfmt_cap == V4L2_PIX_FMT_NV12M) -+ amvdec_write_dos_bits(core, MDEC_PIC_DC_CTRL, BIT(17)); -+ -+ /* Enable firmware processor */ -+ amvdec_write_dos(core, MPSR, 1); -+ /* Let the firmware settle */ -+ udelay(10); -+ -+ return 0; -+ -+stop: -+ vdec_1_stop(sess); -+ return ret; -+} -+ -+struct amvdec_ops vdec_1_ops = { -+ .start = vdec_1_start, -+ .stop = vdec_1_stop, -+ .conf_esparser = vdec_1_conf_esparser, -+ .vififo_level = vdec_1_vififo_level, -+}; -diff --git a/drivers/media/platform/meson/vdec/vdec_1.h b/drivers/media/platform/meson/vdec/vdec_1.h -new file mode 100644 -index 0000000000000..042d930c40d77 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/vdec_1.h -@@ -0,0 +1,14 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ */ -+ -+#ifndef __MESON_VDEC_VDEC_1_H_ -+#define __MESON_VDEC_VDEC_1_H_ -+ -+#include "vdec.h" -+ -+extern struct amvdec_ops vdec_1_ops; -+ -+#endif -diff --git a/drivers/media/platform/meson/vdec/vdec_helpers.c b/drivers/media/platform/meson/vdec/vdec_helpers.c -new file mode 100644 -index 0000000000000..6151076297655 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/vdec_helpers.c -@@ -0,0 +1,354 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ */ -+ -+#include -+#include -+#include -+ -+#include "vdec_helpers.h" -+ -+#define NUM_CANVAS_NV12 2 -+#define NUM_CANVAS_YUV420 3 -+ -+u32 amvdec_read_dos(struct amvdec_core *core, u32 reg) -+{ -+ return readl_relaxed(core->dos_base + reg); -+} -+EXPORT_SYMBOL_GPL(amvdec_read_dos); -+ -+void amvdec_write_dos(struct amvdec_core *core, u32 reg, u32 val) -+{ -+ writel_relaxed(val, core->dos_base + reg); -+} -+EXPORT_SYMBOL_GPL(amvdec_write_dos); -+ -+void amvdec_write_dos_bits(struct amvdec_core *core, u32 reg, u32 val) -+{ -+ amvdec_write_dos(core, reg, amvdec_read_dos(core, reg) | val); -+} -+EXPORT_SYMBOL_GPL(amvdec_write_dos_bits); -+ -+void amvdec_clear_dos_bits(struct amvdec_core *core, u32 reg, u32 val) -+{ -+ amvdec_write_dos(core, reg, amvdec_read_dos(core, reg) & ~val); -+} -+EXPORT_SYMBOL_GPL(amvdec_clear_dos_bits); -+ -+u32 amvdec_read_parser(struct amvdec_core *core, u32 reg) -+{ -+ return readl_relaxed(core->esparser_base + reg); -+} -+EXPORT_SYMBOL_GPL(amvdec_read_parser); -+ -+void amvdec_write_parser(struct amvdec_core *core, u32 reg, u32 val) -+{ -+ writel_relaxed(val, core->esparser_base + reg); -+} -+EXPORT_SYMBOL_GPL(amvdec_write_parser); -+ -+static int canvas_alloc(struct amvdec_session *sess, u8 *canvas_id) -+{ -+ int ret; -+ -+ if (sess->canvas_num >= MAX_CANVAS) { -+ dev_err(sess->core->dev, "Reached max number of canvas\n"); -+ return -ENOMEM; -+ } -+ -+ ret = meson_canvas_alloc(sess->core->canvas, canvas_id); -+ if (ret) -+ return ret; -+ -+ sess->canvas_alloc[sess->canvas_num++] = *canvas_id; -+ return 0; -+} -+ -+static int set_canvas_yuv420m(struct amvdec_session *sess, -+ struct vb2_buffer *vb, u32 width, -+ u32 height, u32 reg) -+{ -+ struct amvdec_core *core = sess->core; -+ u8 canvas_id[NUM_CANVAS_YUV420]; /* Y U V */ -+ dma_addr_t buf_paddr[NUM_CANVAS_YUV420]; /* Y U V */ -+ int ret, i; -+ -+ for (i = 0; i < NUM_CANVAS_YUV420; ++i) { -+ ret = canvas_alloc(sess, &canvas_id[i]); -+ if (ret) -+ return ret; -+ -+ buf_paddr[i] = -+ vb2_dma_contig_plane_dma_addr(vb, i); -+ } -+ -+ /* Y plane */ -+ meson_canvas_config(core->canvas, canvas_id[0], buf_paddr[0], -+ width, height, MESON_CANVAS_WRAP_NONE, -+ MESON_CANVAS_BLKMODE_LINEAR, -+ MESON_CANVAS_ENDIAN_SWAP64); -+ -+ /* U plane */ -+ meson_canvas_config(core->canvas, canvas_id[1], buf_paddr[1], -+ width / 2, height / 2, MESON_CANVAS_WRAP_NONE, -+ MESON_CANVAS_BLKMODE_LINEAR, -+ MESON_CANVAS_ENDIAN_SWAP64); -+ -+ /* V plane */ -+ meson_canvas_config(core->canvas, canvas_id[2], buf_paddr[2], -+ width / 2, height / 2, MESON_CANVAS_WRAP_NONE, -+ MESON_CANVAS_BLKMODE_LINEAR, -+ MESON_CANVAS_ENDIAN_SWAP64); -+ -+ amvdec_write_dos(core, reg, -+ ((canvas_id[2]) << 16) | -+ ((canvas_id[1]) << 8) | -+ (canvas_id[0])); -+ -+ return 0; -+} -+ -+static int set_canvas_nv12m(struct amvdec_session *sess, -+ struct vb2_buffer *vb, u32 width, -+ u32 height, u32 reg) -+{ -+ struct amvdec_core *core = sess->core; -+ u8 canvas_id[NUM_CANVAS_NV12]; /* Y U/V */ -+ dma_addr_t buf_paddr[NUM_CANVAS_NV12]; /* Y U/V */ -+ int ret, i; -+ -+ for (i = 0; i < NUM_CANVAS_NV12; ++i) { -+ ret = canvas_alloc(sess, &canvas_id[i]); -+ if (ret) -+ return ret; -+ -+ buf_paddr[i] = -+ vb2_dma_contig_plane_dma_addr(vb, i); -+ } -+ -+ /* Y plane */ -+ meson_canvas_config(core->canvas, canvas_id[0], buf_paddr[0], -+ width, height, MESON_CANVAS_WRAP_NONE, -+ MESON_CANVAS_BLKMODE_LINEAR, -+ MESON_CANVAS_ENDIAN_SWAP64); -+ -+ /* U/V plane */ -+ meson_canvas_config(core->canvas, canvas_id[1], buf_paddr[1], -+ width, height / 2, MESON_CANVAS_WRAP_NONE, -+ MESON_CANVAS_BLKMODE_LINEAR, -+ MESON_CANVAS_ENDIAN_SWAP64); -+ -+ amvdec_write_dos(core, reg, -+ ((canvas_id[1]) << 16) | -+ ((canvas_id[1]) << 8) | -+ (canvas_id[0])); -+ -+ return 0; -+} -+ -+int amvdec_set_canvases(struct amvdec_session *sess, -+ u32 reg_base[], u32 reg_num[]) -+{ -+ struct v4l2_m2m_buffer *buf; -+ u32 pixfmt = sess->pixfmt_cap; -+ u32 width = ALIGN(sess->width, 64); -+ u32 height = ALIGN(sess->height, 64); -+ u32 reg_cur = reg_base[0]; -+ u32 reg_num_cur = 0; -+ u32 reg_base_cur = 0; -+ int ret; -+ -+ v4l2_m2m_for_each_dst_buf(sess->m2m_ctx, buf) { -+ if (!reg_base[reg_base_cur]) -+ return -EINVAL; -+ -+ reg_cur = reg_base[reg_base_cur] + reg_num_cur * 4; -+ -+ switch (pixfmt) { -+ case V4L2_PIX_FMT_NV12M: -+ ret = set_canvas_nv12m(sess, &buf->vb.vb2_buf, width, -+ height, reg_cur); -+ if (ret) -+ return ret; -+ break; -+ case V4L2_PIX_FMT_YUV420M: -+ ret = set_canvas_yuv420m(sess, &buf->vb.vb2_buf, width, -+ height, reg_cur); -+ if (ret) -+ return ret; -+ break; -+ default: -+ dev_err(sess->core->dev, "Unsupported pixfmt %08X\n", -+ pixfmt); -+ return -EINVAL; -+ }; -+ -+ reg_num_cur++; -+ if (reg_num_cur >= reg_num[reg_base_cur]) { -+ reg_base_cur++; -+ reg_num_cur = 0; -+ } -+ } -+ -+ return 0; -+} -+EXPORT_SYMBOL_GPL(amvdec_set_canvases); -+ -+void amvdec_dst_buf_done(struct amvdec_session *sess, -+ struct vb2_v4l2_buffer *vbuf, u32 field) -+{ -+ struct device *dev = sess->core->dev_dec; -+ struct amvdec_timestamp *tmp; -+ struct list_head *timestamps = &sess->timestamps; -+ u32 output_size = amvdec_get_output_size(sess); -+ unsigned long flags; -+ -+ spin_lock_irqsave(&sess->ts_spinlock, flags); -+ if (list_empty(timestamps)) { -+ dev_err(dev, "Buffer %u done but list is empty\n", -+ vbuf->vb2_buf.index); -+ -+ v4l2_m2m_buf_done(vbuf, VB2_BUF_STATE_ERROR); -+ amvdec_abort(sess); -+ spin_unlock_irqrestore(&sess->ts_spinlock, flags); -+ goto end; -+ } -+ -+ tmp = list_first_entry(timestamps, struct amvdec_timestamp, list); -+ -+ switch (sess->pixfmt_cap) { -+ case V4L2_PIX_FMT_NV12M: -+ vbuf->vb2_buf.planes[0].bytesused = output_size; -+ vbuf->vb2_buf.planes[1].bytesused = output_size / 2; -+ break; -+ case V4L2_PIX_FMT_YUV420M: -+ vbuf->vb2_buf.planes[0].bytesused = output_size; -+ vbuf->vb2_buf.planes[1].bytesused = output_size / 4; -+ vbuf->vb2_buf.planes[2].bytesused = output_size / 4; -+ break; -+ } -+ vbuf->vb2_buf.timestamp = tmp->ts; -+ vbuf->sequence = sess->sequence_cap++; -+ -+ list_del(&tmp->list); -+ kfree(tmp); -+ spin_unlock_irqrestore(&sess->ts_spinlock, flags); -+ -+ atomic_dec(&sess->esparser_queued_bufs); -+ -+ if (sess->should_stop && list_empty(timestamps)) { -+ const struct v4l2_event ev = { .type = V4L2_EVENT_EOS }; -+ -+ dev_dbg(dev, "Signaling EOS\n"); -+ v4l2_event_queue_fh(&sess->fh, &ev); -+ vbuf->flags |= V4L2_BUF_FLAG_LAST; -+ } else if (sess->should_stop) -+ dev_dbg(dev, "should_stop, %u bufs remain\n", -+ atomic_read(&sess->esparser_queued_bufs)); -+ -+ vbuf->field = field; -+ v4l2_m2m_buf_done(vbuf, VB2_BUF_STATE_DONE); -+ -+end: -+ /* Buffer done probably means the vififo got freed */ -+ schedule_work(&sess->esparser_queue_work); -+} -+EXPORT_SYMBOL_GPL(amvdec_dst_buf_done); -+ -+void -+amvdec_dst_buf_done_idx(struct amvdec_session *sess, u32 buf_idx, u32 field) -+{ -+ struct vb2_v4l2_buffer *vbuf; -+ struct device *dev = sess->core->dev_dec; -+ -+ vbuf = v4l2_m2m_dst_buf_remove_by_idx(sess->m2m_ctx, buf_idx); -+ if (!vbuf) { -+ dev_err(dev, -+ "Buffer %u done but it doesn't exist in m2m_ctx\n", -+ buf_idx); -+ amvdec_rm_first_ts(sess); -+ return; -+ } -+ -+ amvdec_dst_buf_done(sess, vbuf, field); -+} -+EXPORT_SYMBOL_GPL(amvdec_dst_buf_done_idx); -+ -+void amvdec_add_ts_reorder(struct amvdec_session *sess, u64 ts) -+{ -+ struct amvdec_timestamp *new_ts, *tmp; -+ unsigned long flags; -+ -+ new_ts = kmalloc(sizeof(*new_ts), GFP_KERNEL); -+ new_ts->ts = ts; -+ -+ spin_lock_irqsave(&sess->ts_spinlock, flags); -+ -+ if (list_empty(&sess->timestamps)) -+ goto add_tail; -+ -+ list_for_each_entry(tmp, &sess->timestamps, list) { -+ if (ts < tmp->ts) { -+ list_add_tail(&new_ts->list, &tmp->list); -+ goto unlock; -+ } -+ } -+ -+add_tail: -+ list_add_tail(&new_ts->list, &sess->timestamps); -+unlock: -+ spin_unlock_irqrestore(&sess->ts_spinlock, flags); -+} -+EXPORT_SYMBOL_GPL(amvdec_add_ts_reorder); -+ -+void amvdec_remove_ts(struct amvdec_session *sess, u64 ts) -+{ -+ struct amvdec_timestamp *tmp; -+ unsigned long flags; -+ -+ spin_lock_irqsave(&sess->ts_spinlock, flags); -+ list_for_each_entry(tmp, &sess->timestamps, list) { -+ if (tmp->ts == ts) { -+ list_del(&tmp->list); -+ kfree(tmp); -+ goto unlock; -+ } -+ } -+ dev_warn(sess->core->dev_dec, -+ "Couldn't remove buffer with timestamp %llu from list\n", ts); -+ -+unlock: -+ spin_unlock_irqrestore(&sess->ts_spinlock, flags); -+} -+EXPORT_SYMBOL_GPL(amvdec_remove_ts); -+ -+void amvdec_rm_first_ts(struct amvdec_session *sess) -+{ -+ unsigned long flags; -+ struct amvdec_buffer *tmp; -+ struct device *dev = sess->core->dev_dec; -+ -+ spin_lock_irqsave(&sess->ts_spinlock, flags); -+ if (list_empty(&sess->timestamps)) { -+ dev_err(dev, "Can't rm first timestamp: list empty\n"); -+ goto unlock; -+ } -+ -+ tmp = list_first_entry(&sess->timestamps, struct amvdec_buffer, list); -+ list_del(&tmp->list); -+ kfree(tmp); -+ atomic_dec(&sess->esparser_queued_bufs); -+ -+unlock: -+ spin_unlock_irqrestore(&sess->ts_spinlock, flags); -+} -+ -+void amvdec_abort(struct amvdec_session *sess) -+{ -+ dev_info(sess->core->dev, "Aborting decoding session!\n"); -+ vb2_queue_error(&sess->m2m_ctx->cap_q_ctx.q); -+ vb2_queue_error(&sess->m2m_ctx->out_q_ctx.q); -+} -+EXPORT_SYMBOL_GPL(amvdec_abort); -diff --git a/drivers/media/platform/meson/vdec/vdec_helpers.h b/drivers/media/platform/meson/vdec/vdec_helpers.h -new file mode 100644 -index 0000000000000..352c6b4c4b84c ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/vdec_helpers.h -@@ -0,0 +1,45 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ */ -+ -+#ifndef __MESON_VDEC_HELPERS_H_ -+#define __MESON_VDEC_HELPERS_H_ -+ -+#include "vdec.h" -+ -+/** -+ * amvdec_set_canvases() - Map VB2 buffers to canvases -+ * -+ * @sess: current session -+ * @reg_base: Registry bases of where to write the canvas indexes -+ * @reg_num: number of contiguous registers after each reg_base (including it) -+ */ -+int amvdec_set_canvases(struct amvdec_session *sess, -+ u32 reg_base[], u32 reg_num[]); -+ -+u32 amvdec_read_dos(struct amvdec_core *core, u32 reg); -+void amvdec_write_dos(struct amvdec_core *core, u32 reg, u32 val); -+void amvdec_write_dos_bits(struct amvdec_core *core, u32 reg, u32 val); -+void amvdec_clear_dos_bits(struct amvdec_core *core, u32 reg, u32 val); -+u32 amvdec_read_parser(struct amvdec_core *core, u32 reg); -+void amvdec_write_parser(struct amvdec_core *core, u32 reg, u32 val); -+ -+void amvdec_dst_buf_done_idx(struct amvdec_session *sess, u32 buf_idx, -+ u32 field); -+void amvdec_dst_buf_done(struct amvdec_session *sess, -+ struct vb2_v4l2_buffer *vbuf, u32 field); -+ -+/** -+ * amvdec_add_ts_reorder() - Add a timestamp to the list in chronological order -+ * -+ * @sess: current session -+ * @ts: timestamp to add -+ */ -+void amvdec_add_ts_reorder(struct amvdec_session *sess, u64 ts); -+void amvdec_remove_ts(struct amvdec_session *sess, u64 ts); -+void amvdec_rm_first_ts(struct amvdec_session *sess); -+ -+void amvdec_abort(struct amvdec_session *sess); -+#endif -diff --git a/drivers/media/platform/meson/vdec/vdec_platform.c b/drivers/media/platform/meson/vdec/vdec_platform.c -new file mode 100644 -index 0000000000000..46eeb7426f547 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/vdec_platform.c -@@ -0,0 +1,101 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ */ -+ -+#include "vdec_platform.h" -+#include "vdec.h" -+ -+#include "vdec_1.h" -+#include "codec_mpeg12.h" -+ -+static const struct amvdec_format vdec_formats_gxbb[] = { -+ { -+ .pixfmt = V4L2_PIX_FMT_MPEG1, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg12_ops, -+ .firmware_path = "meson/gx/vmpeg12_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { -+ .pixfmt = V4L2_PIX_FMT_MPEG2, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg12_ops, -+ .firmware_path = "meson/gx/vmpeg12_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, -+}; -+ -+static const struct amvdec_format vdec_formats_gxl[] = { -+ { -+ .pixfmt = V4L2_PIX_FMT_MPEG1, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg12_ops, -+ .firmware_path = "meson/gx/vmpeg12_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { -+ .pixfmt = V4L2_PIX_FMT_MPEG2, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg12_ops, -+ .firmware_path = "meson/gx/vmpeg12_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, -+}; -+ -+static const struct amvdec_format vdec_formats_gxm[] = { -+ { -+ .pixfmt = V4L2_PIX_FMT_MPEG1, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg12_ops, -+ .firmware_path = "meson/gx/vmpeg12_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { -+ .pixfmt = V4L2_PIX_FMT_MPEG2, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg12_ops, -+ .firmware_path = "meson/gx/vmpeg12_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, -+}; -+ -+const struct vdec_platform vdec_platform_gxbb = { -+ .formats = vdec_formats_gxbb, -+ .num_formats = ARRAY_SIZE(vdec_formats_gxbb), -+ .revision = VDEC_REVISION_GXBB, -+}; -+ -+const struct vdec_platform vdec_platform_gxl = { -+ .formats = vdec_formats_gxl, -+ .num_formats = ARRAY_SIZE(vdec_formats_gxl), -+ .revision = VDEC_REVISION_GXL, -+}; -+ -+const struct vdec_platform vdec_platform_gxm = { -+ .formats = vdec_formats_gxm, -+ .num_formats = ARRAY_SIZE(vdec_formats_gxm), -+ .revision = VDEC_REVISION_GXM, -+}; -diff --git a/drivers/media/platform/meson/vdec/vdec_platform.h b/drivers/media/platform/meson/vdec/vdec_platform.h -new file mode 100644 -index 0000000000000..f6025326db1d6 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/vdec_platform.h -@@ -0,0 +1,30 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Maxime Jourdan -+ */ -+ -+#ifndef __MESON_VDEC_PLATFORM_H_ -+#define __MESON_VDEC_PLATFORM_H_ -+ -+#include "vdec.h" -+ -+struct amvdec_format; -+ -+enum vdec_revision { -+ VDEC_REVISION_GXBB, -+ VDEC_REVISION_GXL, -+ VDEC_REVISION_GXM, -+}; -+ -+struct vdec_platform { -+ const struct amvdec_format *formats; -+ const u32 num_formats; -+ enum vdec_revision revision; -+}; -+ -+extern const struct vdec_platform vdec_platform_gxbb; -+extern const struct vdec_platform vdec_platform_gxm; -+extern const struct vdec_platform vdec_platform_gxl; -+ -+#endif diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/007_linux-4.18.y-v4l-0007-arm64-dts-meson-gx-add_vdec_entry.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/007_linux-4.18.y-v4l-0007-arm64-dts-meson-gx-add_vdec_entry.patch deleted file mode 100644 index e5d678fb4..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/007_linux-4.18.y-v4l-0007-arm64-dts-meson-gx-add_vdec_entry.patch +++ /dev/null @@ -1,36 +0,0 @@ -From b73062fd0c0c9630ad00ec5c0e9880798a994875 Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Wed, 29 Aug 2018 15:24:02 +0200 -Subject: [PATCH] ARM64: dts: meson-gx: add vdec entry - -Add the video decoder dts entry - -Signed-off-by: Maxime Jourdan ---- - arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 13 +++++++++++++ - 1 file changed, 13 insertions(+) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -index 737b741df0355..d9e0fea71dbe3 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -410,6 +410,19 @@ - }; - }; - -+ vdec: video-decoder@c8820000 { -+ compatible = "amlogic,gx-vdec"; -+ reg = <0x0 0xc8820000 0x0 0x10000>, -+ <0x0 0xc110a580 0x0 0xe4>; -+ reg-names = "dos", "esparser"; -+ -+ interrupts = , -+ ; -+ -+ amlogic,ao-sysctrl = <&sysctrl_AO>; -+ amlogic,canvas = <&canvas>; -+ }; -+ - periphs: periphs@c8834000 { - compatible = "simple-bus"; - reg = <0x0 0xc8834000 0x0 0x2000>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/008_linux-4.18.y-v4l-0008-arm64-dts-meson-add_vdec_entries.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/008_linux-4.18.y-v4l-0008-arm64-dts-meson-add_vdec_entries.patch deleted file mode 100644 index 2fe470c4b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/008_linux-4.18.y-v4l-0008-arm64-dts-meson-add_vdec_entries.patch +++ /dev/null @@ -1,64 +0,0 @@ -From c7b0311f4676661ad445f9e36c669886f1bc7835 Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Wed, 29 Aug 2018 15:24:22 +0200 -Subject: [PATCH] ARM64: dts: meson: add vdec entries - -This enables the video decoder for gxbb, gxl and gxm chips - -Signed-off-by: Maxime Jourdan ---- - arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 11 +++++++++++ - arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 11 +++++++++++ - arch/arm64/boot/dts/amlogic/meson-gxm.dtsi | 4 ++++ - 3 files changed, 26 insertions(+) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -index 98cbba6809caa..daee53a755d75 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -@@ -774,3 +774,14 @@ - compatible = "amlogic,meson-gxbb-vpu", "amlogic,meson-gx-vpu"; - power-domains = <&pwrc_vpu>; - }; -+ -+&vdec { -+ compatible = "amlogic,gxbb-vdec"; -+ clocks = <&clkc CLKID_DOS_PARSER>, -+ <&clkc CLKID_DOS>, -+ <&clkc CLKID_VDEC_1>, -+ <&clkc CLKID_VDEC_HEVC>; -+ clock-names = "dos_parser", "dos", "vdec_1", "vdec_hevc"; -+ resets = <&reset RESET_PARSER>; -+ reset-names = "esparser"; -+}; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -index c87a80e9bcc6a..bfd65d1a89591 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -775,3 +775,14 @@ - compatible = "amlogic,meson-gxl-vpu", "amlogic,meson-gx-vpu"; - power-domains = <&pwrc_vpu>; - }; -+ -+&vdec { -+ compatible = "amlogic,gxl-vdec"; -+ clocks = <&clkc CLKID_DOS_PARSER>, -+ <&clkc CLKID_DOS>, -+ <&clkc CLKID_VDEC_1>, -+ <&clkc CLKID_VDEC_HEVC>; -+ clock-names = "dos_parser", "dos", "vdec_1", "vdec_hevc"; -+ resets = <&reset RESET_PARSER>; -+ reset-names = "esparser"; -+}; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxm.dtsi -index 247888d68a3aa..2f356495be5ef 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm.dtsi -@@ -117,3 +117,7 @@ - &dwc3 { - phys = <&usb3_phy>, <&usb2_phy0>, <&usb2_phy1>, <&usb2_phy2>; - }; -+ -+&vdec { -+ compatible = "amlogic,gxm-vdec"; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/009_linux-4.18.y-v4l-0009-media-meson-vdec-add_h.264_decoding_support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/009_linux-4.18.y-v4l-0009-media-meson-vdec-add_h.264_decoding_support.patch deleted file mode 100644 index eeb39e22b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/009_linux-4.18.y-v4l-0009-media-meson-vdec-add_h.264_decoding_support.patch +++ /dev/null @@ -1,466 +0,0 @@ -From 9d2683700060a36200da3b296671485b7fec747f Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Wed, 29 Aug 2018 15:42:56 +0200 -Subject: [PATCH] media: meson: vdec: add H.264 decoding support - -Add support for V4L2_PIX_FMT_H264 ---- - drivers/media/platform/meson/vdec/Makefile | 2 +- - .../media/platform/meson/vdec/codec_h264.c | 354 ++++++++++++++++++ - .../media/platform/meson/vdec/codec_h264.h | 13 + - .../media/platform/meson/vdec/vdec_platform.c | 31 ++ - 4 files changed, 399 insertions(+), 1 deletion(-) - create mode 100644 drivers/media/platform/meson/vdec/codec_h264.c - create mode 100644 drivers/media/platform/meson/vdec/codec_h264.h - -diff --git a/drivers/media/platform/meson/vdec/Makefile b/drivers/media/platform/meson/vdec/Makefile -index 6bea129084b76..711d990c760e0 100644 ---- a/drivers/media/platform/meson/vdec/Makefile -+++ b/drivers/media/platform/meson/vdec/Makefile -@@ -3,6 +3,6 @@ - - meson-vdec-objs = esparser.o vdec.o vdec_helpers.o vdec_platform.o - meson-vdec-objs += vdec_1.o --meson-vdec-objs += codec_mpeg12.o -+meson-vdec-objs += codec_mpeg12.o codec_h264.o - - obj-$(CONFIG_VIDEO_MESON_VDEC) += meson-vdec.o -diff --git a/drivers/media/platform/meson/vdec/codec_h264.c b/drivers/media/platform/meson/vdec/codec_h264.c -new file mode 100644 -index 0000000000000..7c47ec35efa54 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/codec_h264.c -@@ -0,0 +1,354 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 Maxime Jourdan -+ */ -+ -+#include -+#include -+ -+#include "vdec_helpers.h" -+#include "dos_regs.h" -+ -+#define SIZE_EXT_FW (20 * SZ_1K) -+#define SIZE_WORKSPACE 0x1ee000 -+#define SIZE_SEI (8 * SZ_1K) -+ -+/* Offset added by the firmware which must be substracted -+ * from the workspace phyaddr -+ */ -+#define WORKSPACE_BUF_OFFSET 0x1000000 -+ -+#define SEI_DATA_READY BIT(15) -+ -+/* ISR status */ -+#define CMD_SET_PARAM 1 -+#define CMD_FRAMES_READY 2 -+#define CMD_FATAL_ERROR 6 -+#define CMD_BAD_WIDTH 7 -+#define CMD_BAD_HEIGHT 8 -+ -+/* Picture type */ -+#define PIC_SINGLE_FRAME 0 -+#define PIC_TOP_BOT_TOP 1 -+#define PIC_BOT_TOP_BOT 2 -+#define PIC_DOUBLE_FRAME 3 -+#define PIC_TRIPLE_FRAME 4 -+#define PIC_TOP_BOT 5 -+#define PIC_BOT_TOP 6 -+#define PIC_INVALID 7 -+ -+/* Size of Motion Vector per macroblock */ -+#define MB_MV_SIZE 96 -+ -+struct codec_h264 { -+ /* H.264 decoder requires an extended firmware */ -+ void *ext_fw_vaddr; -+ dma_addr_t ext_fw_paddr; -+ -+ /* Buffer for the H.264 Workspace */ -+ void *workspace_vaddr; -+ dma_addr_t workspace_paddr; -+ -+ /* Buffer for the H.264 references MV */ -+ void *ref_vaddr; -+ dma_addr_t ref_paddr; -+ u32 ref_size; -+ -+ /* Buffer for parsed SEI data */ -+ void *sei_vaddr; -+ dma_addr_t sei_paddr; -+ -+ int received_0; -+}; -+ -+static int codec_h264_can_recycle(struct amvdec_core *core) -+{ -+ return !amvdec_read_dos(core, AV_SCRATCH_7) || -+ !amvdec_read_dos(core, AV_SCRATCH_8); -+} -+ -+static void codec_h264_recycle(struct amvdec_core *core, u32 buf_idx) -+{ -+ /* Tell the decoder he can recycle this buffer. -+ * AV_SCRATCH_8 serves the same purpose. -+ */ -+ if (!amvdec_read_dos(core, AV_SCRATCH_7)) -+ amvdec_write_dos(core, AV_SCRATCH_7, buf_idx + 1); -+ else -+ amvdec_write_dos(core, AV_SCRATCH_8, buf_idx + 1); -+} -+ -+static int codec_h264_start(struct amvdec_session *sess) { -+ u32 workspace_offset; -+ struct amvdec_core *core = sess->core; -+ struct codec_h264 *h264 = sess->priv; -+ -+ /* Allocate some memory for the H.264 decoder's state */ -+ h264->workspace_vaddr = -+ dma_alloc_coherent(core->dev, SIZE_WORKSPACE, &h264->workspace_paddr, GFP_KERNEL); -+ if (!h264->workspace_vaddr) { -+ dev_err(core->dev, "Failed to alloc H.264 Workspace\n"); -+ return -ENOMEM; -+ } -+ -+ /* Allocate some memory for the H.264 SEI dump */ -+ h264->sei_vaddr = -+ dma_alloc_coherent(core->dev, SIZE_SEI, &h264->sei_paddr, GFP_KERNEL); -+ if (!h264->sei_vaddr) { -+ dev_err(core->dev, "Failed to alloc H.264 SEI\n"); -+ return -ENOMEM; -+ } -+ -+ amvdec_write_dos_bits(core, POWER_CTL_VLD, BIT(9) | BIT(6)); -+ -+ amvdec_write_dos(core, PSCALE_CTRL, 0); -+ amvdec_write_dos(core, AV_SCRATCH_0, 0); -+ -+ workspace_offset = h264->workspace_paddr - WORKSPACE_BUF_OFFSET; -+ amvdec_write_dos(core, AV_SCRATCH_1, workspace_offset); -+ amvdec_write_dos(core, AV_SCRATCH_G, h264->ext_fw_paddr); -+ amvdec_write_dos(core, AV_SCRATCH_I, h264->sei_paddr - workspace_offset); -+ -+ amvdec_write_dos(core, AV_SCRATCH_7, 0); -+ amvdec_write_dos(core, AV_SCRATCH_8, 0); -+ amvdec_write_dos(core, AV_SCRATCH_9, 0); -+ -+ /* Enable "error correction" */ -+ amvdec_write_dos(core, AV_SCRATCH_F, (amvdec_read_dos(core, AV_SCRATCH_F) & 0xffffffc3) | BIT(4) | BIT(7)); -+ -+ amvdec_write_dos(core, MDEC_PIC_DC_THRESH, 0x404038aa); -+ -+ return 0; -+} -+ -+static int codec_h264_stop(struct amvdec_session *sess) -+{ -+ struct codec_h264 *h264 = sess->priv; -+ struct amvdec_core *core = sess->core; -+ -+ if (h264->ext_fw_vaddr) -+ dma_free_coherent(core->dev, SIZE_EXT_FW, -+ h264->ext_fw_vaddr, h264->ext_fw_paddr); -+ -+ if (h264->workspace_vaddr) -+ dma_free_coherent(core->dev, SIZE_WORKSPACE, -+ h264->workspace_vaddr, h264->workspace_paddr); -+ -+ if (h264->ref_vaddr) -+ dma_free_coherent(core->dev, h264->ref_size, -+ h264->ref_vaddr, h264->ref_paddr); -+ -+ if (h264->sei_vaddr) -+ dma_free_coherent(core->dev, SIZE_SEI, -+ h264->sei_vaddr, h264->sei_paddr); -+ -+ return 0; -+} -+ -+static int codec_h264_load_extended_firmware(struct amvdec_session *sess, const u8 *data, u32 len) -+{ -+ struct codec_h264 *h264; -+ struct amvdec_core *core = sess->core; -+ -+ h264 = kzalloc(sizeof(*h264), GFP_KERNEL); -+ if (!h264) -+ return -ENOMEM; -+ -+ sess->priv = h264; -+ -+ if (len < SIZE_EXT_FW) -+ return -EINVAL; -+ -+ h264->ext_fw_vaddr = dma_alloc_coherent(core->dev, SIZE_EXT_FW, -+ &h264->ext_fw_paddr, GFP_KERNEL); -+ if (!h264->ext_fw_vaddr) { -+ dev_err(core->dev, "Failed to alloc H.264 extended fw\n"); -+ return -ENOMEM; -+ } -+ -+ memcpy(h264->ext_fw_vaddr, data, SIZE_EXT_FW); -+ -+ return 0; -+} -+ -+/* Configure the H.264 decoder when the esparser finished parsing -+ * the first keyframe -+ */ -+static void codec_h264_set_param(struct amvdec_session *sess) { -+ struct amvdec_core *core = sess->core; -+ struct codec_h264 *h264 = sess->priv; -+ u32 max_reference_size; -+ u32 parsed_info, mb_width, mb_height, mb_total; -+ u32 actual_dpb_size = v4l2_m2m_num_dst_bufs_ready(sess->m2m_ctx); -+ u32 max_dpb_size = 4; -+ -+ sess->keyframe_found = 1; -+ -+ amvdec_write_dos(core, AV_SCRATCH_7, 0); -+ amvdec_write_dos(core, AV_SCRATCH_8, 0); -+ amvdec_write_dos(core, AV_SCRATCH_9, 0); -+ -+ parsed_info = amvdec_read_dos(core, AV_SCRATCH_1); -+ -+ /* Total number of 16x16 macroblocks */ -+ mb_total = (parsed_info >> 8) & 0xffff; -+ -+ /* Number of macroblocks per line */ -+ mb_width = parsed_info & 0xff; -+ -+ /* Number of macroblock lines */ -+ mb_height = mb_total / mb_width; -+ -+ max_reference_size = (parsed_info >> 24) & 0x7f; -+ -+ /* Align to a multiple of 4 macroblocks */ -+ mb_width = ALIGN(mb_width, 4); -+ mb_height = ALIGN(mb_height, 4); -+ mb_total = mb_width * mb_height; -+ -+ amvdec_set_canvases(sess, (u32[]){ ANC0_CANVAS_ADDR, 0 }, -+ (u32[]){ 24, 0 }); -+ -+ if (max_reference_size > max_dpb_size) -+ max_dpb_size = max_reference_size; -+ -+ max_reference_size++; -+ dev_dbg(core->dev, -+ "max_ref_size = %u; max_dpb_size = %u; actual_dpb_size = %u\n", -+ max_reference_size, max_dpb_size, actual_dpb_size); -+ -+ h264->ref_size = mb_total * MB_MV_SIZE * max_reference_size; -+ h264->ref_vaddr = dma_alloc_coherent(core->dev, h264->ref_size, -+ &h264->ref_paddr, GFP_KERNEL); -+ if (!h264->ref_vaddr) { -+ dev_err(core->dev, "Failed to alloc refs (%u)\n", -+ h264->ref_size); -+ amvdec_abort(sess); -+ return; -+ } -+ -+ /* Address to store the references' MVs */ -+ amvdec_write_dos(core, AV_SCRATCH_1, h264->ref_paddr); -+ /* End of ref MV */ -+ amvdec_write_dos(core, AV_SCRATCH_4, h264->ref_paddr + h264->ref_size); -+ -+ amvdec_write_dos(core, AV_SCRATCH_0, (max_reference_size << 24) | -+ (actual_dpb_size << 16) | -+ (max_dpb_size << 8)); -+} -+ -+static void codec_h264_frames_ready(struct amvdec_session *sess, u32 status) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_h264 *h264 = sess->priv; -+ int error_count; -+ int num_frames; -+ int i; -+ -+ error_count = amvdec_read_dos(core, AV_SCRATCH_D); -+ num_frames = (status >> 8) & 0xff; -+ if (error_count) { -+ dev_warn(core->dev, -+ "decoder error(s) happened, count %d\n", error_count); -+ amvdec_write_dos(core, AV_SCRATCH_D, 0); -+ } -+ -+ for (i = 0; i < num_frames; i++) { -+ u32 frame_status = amvdec_read_dos(core, AV_SCRATCH_1 + i * 4); -+ u32 buffer_index = frame_status & 0x1f; -+ u32 error = frame_status & 0x200; -+ u32 pic_struct = (frame_status >> 5) & 0x7; -+ u32 field = V4L2_FIELD_NONE; -+ -+ /* A buffer decode error means it was decoded, -+ * but part of the picture will have artifacts. -+ * Typical reason is a temporarily corrupted bitstream -+ */ -+ if (error) -+ dev_info(core->dev, "Buffer %d decode error\n", -+ buffer_index); -+ -+ if (pic_struct == PIC_TOP_BOT) -+ field = V4L2_FIELD_INTERLACED_TB; -+ else if (pic_struct == PIC_BOT_TOP) -+ field = V4L2_FIELD_INTERLACED_BT; -+ -+ amvdec_dst_buf_done_idx(sess, buffer_index, field); -+ -+ if (field != V4L2_FIELD_NONE && !h264->received_0) -+ amvdec_rm_first_ts(sess); -+ -+ h264->received_0 = 0; -+ } -+} -+ -+static irqreturn_t codec_h264_threaded_isr(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_h264 *h264 = sess->priv; -+ u32 status; -+ u32 size; -+ u8 cmd; -+ -+ status = amvdec_read_dos(core, AV_SCRATCH_0); -+ cmd = status & 0xff; -+ -+ switch (cmd) { -+ case CMD_SET_PARAM: -+ codec_h264_set_param(sess); -+ break; -+ case CMD_FRAMES_READY: -+ codec_h264_frames_ready(sess, status); -+ break; -+ case CMD_FATAL_ERROR: -+ dev_err(core->dev, "H.264 decoder fatal error\n"); -+ goto abort; -+ case CMD_BAD_WIDTH: -+ size = (amvdec_read_dos(core, AV_SCRATCH_1) + 1) * 16; -+ dev_err(core->dev, "Unsupported video width: %u\n", size); -+ goto abort; -+ case CMD_BAD_HEIGHT: -+ size = (amvdec_read_dos(core, AV_SCRATCH_1) + 1) * 16; -+ dev_err(core->dev, "Unsupported video height: %u\n", size); -+ goto abort; -+ case 0: -+ h264->received_0 = 1; -+ break; -+ case 9: /* Unused but not worth printing for */ -+ break; -+ default: -+ dev_info(core->dev, "Unexpected H264 ISR: %08X\n", cmd); -+ break; -+ } -+ -+ if (cmd && cmd != CMD_SET_PARAM) -+ amvdec_write_dos(core, AV_SCRATCH_0, 0); -+ -+ /* Decoder has some SEI data for us ; ignore */ -+ if (amvdec_read_dos(core, AV_SCRATCH_J) & SEI_DATA_READY) -+ amvdec_write_dos(core, AV_SCRATCH_J, 0); -+ -+ return IRQ_HANDLED; -+abort: -+ amvdec_abort(sess); -+ return IRQ_HANDLED; -+} -+ -+static irqreturn_t codec_h264_isr(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ -+ amvdec_write_dos(core, ASSIST_MBOX1_CLR_REG, 1); -+ -+ return IRQ_WAKE_THREAD; -+} -+ -+struct amvdec_codec_ops codec_h264_ops = { -+ .start = codec_h264_start, -+ .stop = codec_h264_stop, -+ .load_extended_firmware = codec_h264_load_extended_firmware, -+ .isr = codec_h264_isr, -+ .threaded_isr = codec_h264_threaded_isr, -+ .can_recycle = codec_h264_can_recycle, -+ .recycle = codec_h264_recycle, -+}; -diff --git a/drivers/media/platform/meson/vdec/codec_h264.h b/drivers/media/platform/meson/vdec/codec_h264.h -new file mode 100644 -index 0000000000000..7a1597611faff ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/codec_h264.h -@@ -0,0 +1,13 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 Maxime Jourdan -+ */ -+ -+#ifndef __MESON_VDEC_CODEC_H264_H_ -+#define __MESON_VDEC_CODEC_H264_H_ -+ -+#include "vdec.h" -+ -+extern struct amvdec_codec_ops codec_h264_ops; -+ -+#endif -\ No newline at end of file -diff --git a/drivers/media/platform/meson/vdec/vdec_platform.c b/drivers/media/platform/meson/vdec/vdec_platform.c -index 46eeb7426f547..9f7872feef74d 100644 ---- a/drivers/media/platform/meson/vdec/vdec_platform.c -+++ b/drivers/media/platform/meson/vdec/vdec_platform.c -@@ -9,9 +9,20 @@ - - #include "vdec_1.h" - #include "codec_mpeg12.h" -+#include "codec_h264.h" - - static const struct amvdec_format vdec_formats_gxbb[] = { - { -+ .pixfmt = V4L2_PIX_FMT_H264, -+ .min_buffers = 21, -+ .max_buffers = 24, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_h264_ops, -+ .firmware_path = "meson/gxbb/vh264_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_MPEG1, - .min_buffers = 8, - .max_buffers = 8, -@@ -36,6 +47,16 @@ static const struct amvdec_format vdec_formats_gxbb[] = { - - static const struct amvdec_format vdec_formats_gxl[] = { - { -+ .pixfmt = V4L2_PIX_FMT_H264, -+ .min_buffers = 21, -+ .max_buffers = 24, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_h264_ops, -+ .firmware_path = "meson/gxl/vh264_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_MPEG1, - .min_buffers = 8, - .max_buffers = 8, -@@ -60,6 +81,16 @@ static const struct amvdec_format vdec_formats_gxl[] = { - - static const struct amvdec_format vdec_formats_gxm[] = { - { -+ .pixfmt = V4L2_PIX_FMT_H264, -+ .min_buffers = 21, -+ .max_buffers = 24, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_h264_ops, -+ .firmware_path = "meson/gxm/vh264_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_MPEG1, - .min_buffers = 8, - .max_buffers = 8, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/010_linux-4.18.y-v4l-0010-media-meson-vdec-add_mpeg4_decoding_support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/010_linux-4.18.y-v4l-0010-media-meson-vdec-add_mpeg4_decoding_support.patch deleted file mode 100644 index 067f6d5ef..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/010_linux-4.18.y-v4l-0010-media-meson-vdec-add_mpeg4_decoding_support.patch +++ /dev/null @@ -1,304 +0,0 @@ -From 4e628eee07aed9d006a4c4b4a75d41f05924b4c8 Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Wed, 29 Aug 2018 16:01:55 +0200 -Subject: [PATCH] media: meson: vdec: add MPEG4 decoding support - -Add support for V4L2_PIX_FMT_MPEG4, V4L2_PIX_FMT_XVID and -V4L2_PIX_FMT_H.263 ---- - drivers/media/platform/meson/vdec/Makefile | 2 +- - .../media/platform/meson/vdec/codec_mpeg4.c | 131 ++++++++++++++++++ - .../media/platform/meson/vdec/codec_mpeg4.h | 13 ++ - .../media/platform/meson/vdec/vdec_platform.c | 91 ++++++++++++ - 4 files changed, 236 insertions(+), 1 deletion(-) - create mode 100644 drivers/media/platform/meson/vdec/codec_mpeg4.c - create mode 100644 drivers/media/platform/meson/vdec/codec_mpeg4.h - -diff --git a/drivers/media/platform/meson/vdec/Makefile b/drivers/media/platform/meson/vdec/Makefile -index 711d990c760e0..f167a61acb36d 100644 ---- a/drivers/media/platform/meson/vdec/Makefile -+++ b/drivers/media/platform/meson/vdec/Makefile -@@ -3,6 +3,6 @@ - - meson-vdec-objs = esparser.o vdec.o vdec_helpers.o vdec_platform.o - meson-vdec-objs += vdec_1.o --meson-vdec-objs += codec_mpeg12.o codec_h264.o -+meson-vdec-objs += codec_mpeg12.o codec_h264.o codec_mpeg4.o - - obj-$(CONFIG_VIDEO_MESON_VDEC) += meson-vdec.o -diff --git a/drivers/media/platform/meson/vdec/codec_mpeg4.c b/drivers/media/platform/meson/vdec/codec_mpeg4.c -new file mode 100644 -index 0000000000000..c6db2640c91a7 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/codec_mpeg4.c -@@ -0,0 +1,131 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 Maxime Jourdan -+ */ -+ -+#include -+#include -+ -+#include "vdec_helpers.h" -+#include "dos_regs.h" -+ -+#define SIZE_WORKSPACE SZ_1M -+/* Offset added by firmware, to substract from workspace paddr */ -+#define DCAC_BUFF_START_IP 0x02b00000 -+ -+/* map FW registers to known MPEG4 functions */ -+#define MP4_PIC_RATIO AV_SCRATCH_5 -+#define MP4_ERR_COUNT AV_SCRATCH_6 -+#define MP4_PIC_WH AV_SCRATCH_7 -+#define MREG_BUFFERIN AV_SCRATCH_8 -+#define MREG_BUFFEROUT AV_SCRATCH_9 -+#define MP4_NOT_CODED_CNT AV_SCRATCH_A -+#define MP4_VOP_TIME_INC AV_SCRATCH_B -+#define MP4_OFFSET_REG AV_SCRATCH_C -+#define MP4_SYS_RATE AV_SCRATCH_E -+#define MEM_OFFSET_REG AV_SCRATCH_F -+#define MREG_FATAL_ERROR AV_SCRATCH_L -+ -+struct codec_mpeg4 { -+ /* Buffer for the MPEG4 Workspace */ -+ void *workspace_vaddr; -+ dma_addr_t workspace_paddr; -+}; -+ -+static int codec_mpeg4_can_recycle(struct amvdec_core *core) -+{ -+ return !amvdec_read_dos(core, MREG_BUFFERIN); -+} -+ -+static void codec_mpeg4_recycle(struct amvdec_core *core, u32 buf_idx) -+{ -+ amvdec_write_dos(core, MREG_BUFFERIN, ~(1 << buf_idx)); -+} -+ -+static int codec_mpeg4_start(struct amvdec_session *sess) { -+ struct amvdec_core *core = sess->core; -+ struct codec_mpeg4 *mpeg4 = sess->priv; -+ int ret; -+ -+ mpeg4 = kzalloc(sizeof(*mpeg4), GFP_KERNEL); -+ if (!mpeg4) -+ return -ENOMEM; -+ -+ sess->priv = mpeg4; -+ -+ /* Allocate some memory for the MPEG4 decoder's state */ -+ mpeg4->workspace_vaddr = dma_alloc_coherent(core->dev, SIZE_WORKSPACE, -+ &mpeg4->workspace_paddr, -+ GFP_KERNEL); -+ if (!mpeg4->workspace_vaddr) { -+ dev_err(core->dev, "Failed to request MPEG4 Workspace\n"); -+ ret = -ENOMEM; -+ goto free_mpeg4; -+ } -+ -+ amvdec_set_canvases(sess, (u32[]){ AV_SCRATCH_0, AV_SCRATCH_G, 0 }, -+ (u32[]){ 4, 4, 0 }); -+ -+ amvdec_write_dos(core, MEM_OFFSET_REG, -+ mpeg4->workspace_paddr - DCAC_BUFF_START_IP); -+ amvdec_write_dos(core, PSCALE_CTRL, 0); -+ amvdec_write_dos(core, MP4_NOT_CODED_CNT, 0); -+ amvdec_write_dos(core, MREG_BUFFERIN, 0); -+ amvdec_write_dos(core, MREG_BUFFEROUT, 0); -+ amvdec_write_dos(core, MREG_FATAL_ERROR, 0); -+ amvdec_write_dos(core, MDEC_PIC_DC_THRESH, 0x404038aa); -+ -+ return 0; -+ -+free_mpeg4: -+ kfree(mpeg4); -+ return ret; -+} -+ -+static int codec_mpeg4_stop(struct amvdec_session *sess) -+{ -+ struct codec_mpeg4 *mpeg4 = sess->priv; -+ struct amvdec_core *core = sess->core; -+ -+ if (mpeg4->workspace_vaddr) { -+ dma_free_coherent(core->dev, SIZE_WORKSPACE, -+ mpeg4->workspace_vaddr, -+ mpeg4->workspace_paddr); -+ mpeg4->workspace_vaddr = 0; -+ } -+ -+ return 0; -+} -+ -+static irqreturn_t codec_mpeg4_isr(struct amvdec_session *sess) -+{ -+ u32 reg; -+ u32 buffer_index; -+ struct amvdec_core *core = sess->core; -+ -+ reg = amvdec_read_dos(core, MREG_FATAL_ERROR); -+ if (reg == 1) -+ dev_err(core->dev, "mpeg4 fatal error\n"); -+ -+ reg = amvdec_read_dos(core, MREG_BUFFEROUT); -+ if (reg) { -+ sess->keyframe_found = 1; -+ amvdec_read_dos(core, MP4_NOT_CODED_CNT); -+ amvdec_read_dos(core, MP4_VOP_TIME_INC); -+ buffer_index = reg & 0x7; -+ amvdec_dst_buf_done_idx(sess, buffer_index, V4L2_FIELD_NONE); -+ amvdec_write_dos(core, MREG_BUFFEROUT, 0); -+ } -+ -+ amvdec_write_dos(core, ASSIST_MBOX1_CLR_REG, 1); -+ -+ return IRQ_HANDLED; -+} -+ -+struct amvdec_codec_ops codec_mpeg4_ops = { -+ .start = codec_mpeg4_start, -+ .stop = codec_mpeg4_stop, -+ .isr = codec_mpeg4_isr, -+ .can_recycle = codec_mpeg4_can_recycle, -+ .recycle = codec_mpeg4_recycle, -+}; -diff --git a/drivers/media/platform/meson/vdec/codec_mpeg4.h b/drivers/media/platform/meson/vdec/codec_mpeg4.h -new file mode 100644 -index 0000000000000..b91b264131854 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/codec_mpeg4.h -@@ -0,0 +1,13 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 Maxime Jourdan -+ */ -+ -+#ifndef __MESON_VDEC_CODEC_MPEG4_H_ -+#define __MESON_VDEC_CODEC_MPEG4_H_ -+ -+#include "vdec.h" -+ -+extern struct amvdec_codec_ops codec_mpeg4_ops; -+ -+#endif -\ No newline at end of file -diff --git a/drivers/media/platform/meson/vdec/vdec_platform.c b/drivers/media/platform/meson/vdec/vdec_platform.c -index 9f7872feef74d..135d7566d716a 100644 ---- a/drivers/media/platform/meson/vdec/vdec_platform.c -+++ b/drivers/media/platform/meson/vdec/vdec_platform.c -@@ -10,9 +10,40 @@ - #include "vdec_1.h" - #include "codec_mpeg12.h" - #include "codec_h264.h" -+#include "codec_mpeg4.h" - - static const struct amvdec_format vdec_formats_gxbb[] = { - { -+ .pixfmt = V4L2_PIX_FMT_MPEG4, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg4_ops, -+ .firmware_path = "meson/gx/vmpeg4_mc_5", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { -+ .pixfmt = V4L2_PIX_FMT_H263, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg4_ops, -+ .firmware_path = "meson/gx/h263_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { -+ .pixfmt = V4L2_PIX_FMT_XVID, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg4_ops, -+ .firmware_path = "meson/gx/vmpeg4_mc_5", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_H264, - .min_buffers = 21, - .max_buffers = 24, -@@ -47,6 +78,36 @@ static const struct amvdec_format vdec_formats_gxbb[] = { - - static const struct amvdec_format vdec_formats_gxl[] = { - { -+ .pixfmt = V4L2_PIX_FMT_MPEG4, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg4_ops, -+ .firmware_path = "meson/gx/vmpeg4_mc_5", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { -+ .pixfmt = V4L2_PIX_FMT_H263, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg4_ops, -+ .firmware_path = "meson/gx/h263_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { -+ .pixfmt = V4L2_PIX_FMT_XVID, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg4_ops, -+ .firmware_path = "meson/gx/vmpeg4_mc_5", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_H264, - .min_buffers = 21, - .max_buffers = 24, -@@ -81,6 +142,36 @@ static const struct amvdec_format vdec_formats_gxl[] = { - - static const struct amvdec_format vdec_formats_gxm[] = { - { -+ .pixfmt = V4L2_PIX_FMT_MPEG4, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg4_ops, -+ .firmware_path = "meson/gx/vmpeg4_mc_5", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { -+ .pixfmt = V4L2_PIX_FMT_H263, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg4_ops, -+ .firmware_path = "meson/gx/h263_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { -+ .pixfmt = V4L2_PIX_FMT_XVID, -+ .min_buffers = 8, -+ .max_buffers = 8, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mpeg4_ops, -+ .firmware_path = "meson/gx/vmpeg4_mc_5", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_H264, - .min_buffers = 21, - .max_buffers = 24, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/011_linux-4.18.y-v4l-0011-media-meson-vdec-add_mjpeg_decoding_support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/011_linux-4.18.y-v4l-0011-media-meson-vdec-add_mjpeg_decoding_support.patch deleted file mode 100644 index 64b92694e..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/011_linux-4.18.y-v4l-0011-media-meson-vdec-add_mjpeg_decoding_support.patch +++ /dev/null @@ -1,249 +0,0 @@ -From 920fefae2df25f616552de3c842965f671dd9bae Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Wed, 29 Aug 2018 16:05:28 +0200 -Subject: [PATCH] media: meson: vdec: add MJPEG decoding support - -Add support for V4L2_PIX_FMT_MJPEG ---- - drivers/media/platform/meson/vdec/Makefile | 2 +- - .../media/platform/meson/vdec/codec_mjpeg.c | 137 ++++++++++++++++++ - .../media/platform/meson/vdec/codec_mjpeg.h | 13 ++ - .../media/platform/meson/vdec/vdec_platform.c | 31 ++++ - 4 files changed, 182 insertions(+), 1 deletion(-) - create mode 100644 drivers/media/platform/meson/vdec/codec_mjpeg.c - create mode 100644 drivers/media/platform/meson/vdec/codec_mjpeg.h - -diff --git a/drivers/media/platform/meson/vdec/Makefile b/drivers/media/platform/meson/vdec/Makefile -index f167a61acb36d..20c23f9015ebd 100644 ---- a/drivers/media/platform/meson/vdec/Makefile -+++ b/drivers/media/platform/meson/vdec/Makefile -@@ -3,6 +3,6 @@ - - meson-vdec-objs = esparser.o vdec.o vdec_helpers.o vdec_platform.o - meson-vdec-objs += vdec_1.o --meson-vdec-objs += codec_mpeg12.o codec_h264.o codec_mpeg4.o -+meson-vdec-objs += codec_mpeg12.o codec_h264.o codec_mpeg4.o codec_mjpeg.o - - obj-$(CONFIG_VIDEO_MESON_VDEC) += meson-vdec.o -diff --git a/drivers/media/platform/meson/vdec/codec_mjpeg.c b/drivers/media/platform/meson/vdec/codec_mjpeg.c -new file mode 100644 -index 0000000000000..f632c51c8fffe ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/codec_mjpeg.c -@@ -0,0 +1,137 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 Maxime Jourdan -+ */ -+ -+#include -+#include -+ -+#include "vdec_helpers.h" -+#include "dos_regs.h" -+ -+/* map FW registers to known MJPEG functions */ -+#define MREG_DECODE_PARAM AV_SCRATCH_2 -+#define MREG_TO_AMRISC AV_SCRATCH_8 -+#define MREG_FROM_AMRISC AV_SCRATCH_9 -+ -+static int codec_mjpeg_can_recycle(struct amvdec_core *core) -+{ -+ return !amvdec_read_dos(core, MREG_TO_AMRISC); -+} -+ -+static void codec_mjpeg_recycle(struct amvdec_core *core, u32 buf_idx) -+{ -+ amvdec_write_dos(core, MREG_TO_AMRISC, buf_idx + 1); -+} -+ -+/* 4 point triangle */ -+static const uint32_t filt_coef[] = { -+ 0x20402000, 0x20402000, 0x1f3f2101, 0x1f3f2101, -+ 0x1e3e2202, 0x1e3e2202, 0x1d3d2303, 0x1d3d2303, -+ 0x1c3c2404, 0x1c3c2404, 0x1b3b2505, 0x1b3b2505, -+ 0x1a3a2606, 0x1a3a2606, 0x19392707, 0x19392707, -+ 0x18382808, 0x18382808, 0x17372909, 0x17372909, -+ 0x16362a0a, 0x16362a0a, 0x15352b0b, 0x15352b0b, -+ 0x14342c0c, 0x14342c0c, 0x13332d0d, 0x13332d0d, -+ 0x12322e0e, 0x12322e0e, 0x11312f0f, 0x11312f0f, -+ 0x10303010 -+}; -+ -+static void codec_mjpeg_init_scaler(struct amvdec_core *core) -+{ -+ int i; -+ -+ /* PSCALE cbus bmem enable */ -+ amvdec_write_dos(core, PSCALE_CTRL, 0xc000); -+ -+ amvdec_write_dos(core, PSCALE_BMEM_ADDR, 0); -+ for (i = 0; i < ARRAY_SIZE(filt_coef); ++i) { -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, filt_coef[i]); -+ } -+ -+ amvdec_write_dos(core, PSCALE_BMEM_ADDR, 74); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x0008); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x60000000); -+ -+ amvdec_write_dos(core, PSCALE_BMEM_ADDR, 82); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x0008); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x60000000); -+ -+ amvdec_write_dos(core, PSCALE_BMEM_ADDR, 78); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x0008); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x60000000); -+ -+ amvdec_write_dos(core, PSCALE_BMEM_ADDR, 86); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x0008); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x60000000); -+ -+ amvdec_write_dos(core, PSCALE_BMEM_ADDR, 73); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x10000); -+ amvdec_write_dos(core, PSCALE_BMEM_ADDR, 81); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x10000); -+ -+ amvdec_write_dos(core, PSCALE_BMEM_ADDR, 77); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x10000); -+ amvdec_write_dos(core, PSCALE_BMEM_ADDR, 85); -+ amvdec_write_dos(core, PSCALE_BMEM_DAT, 0x10000); -+ -+ amvdec_write_dos(core, PSCALE_RST, 0x7); -+ amvdec_write_dos(core, PSCALE_RST, 0); -+} -+ -+static int codec_mjpeg_start(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ -+ amvdec_write_dos(core, AV_SCRATCH_0, 12); -+ amvdec_write_dos(core, AV_SCRATCH_1, 0x031a); -+ -+ amvdec_set_canvases(sess, (u32[]){ AV_SCRATCH_4, 0 }, -+ (u32[]){ 4, 0 }); -+ codec_mjpeg_init_scaler(core); -+ -+ amvdec_write_dos(core, MREG_TO_AMRISC, 0); -+ amvdec_write_dos(core, MREG_FROM_AMRISC, 0); -+ amvdec_write_dos(core, MCPU_INTR_MSK, 0xffff); -+ amvdec_write_dos(core, MREG_DECODE_PARAM, -+ (sess->height << 4) | 0x8000); -+ amvdec_write_dos(core, VDEC_ASSIST_AMR1_INT8, 8); -+ -+ /* Intra-only codec */ -+ sess->keyframe_found = 1; -+ -+ return 0; -+} -+ -+static int codec_mjpeg_stop(struct amvdec_session *sess) -+{ -+ return 0; -+} -+ -+static irqreturn_t codec_mjpeg_isr(struct amvdec_session *sess) -+{ -+ u32 reg; -+ u32 buffer_index; -+ struct amvdec_core *core = sess->core; -+ -+ amvdec_write_dos(core, ASSIST_MBOX1_CLR_REG, 1); -+ -+ reg = amvdec_read_dos(core, MREG_FROM_AMRISC); -+ if (!(reg & 0x7)) -+ return IRQ_HANDLED; -+ -+ buffer_index = ((reg & 0x7) - 1) & 3; -+ amvdec_dst_buf_done_idx(sess, buffer_index, V4L2_FIELD_NONE); -+ -+ amvdec_write_dos(core, MREG_FROM_AMRISC, 0); -+ return IRQ_HANDLED; -+} -+ -+struct amvdec_codec_ops codec_mjpeg_ops = { -+ .start = codec_mjpeg_start, -+ .stop = codec_mjpeg_stop, -+ .isr = codec_mjpeg_isr, -+ .can_recycle = codec_mjpeg_can_recycle, -+ .recycle = codec_mjpeg_recycle, -+}; -diff --git a/drivers/media/platform/meson/vdec/codec_mjpeg.h b/drivers/media/platform/meson/vdec/codec_mjpeg.h -new file mode 100644 -index 0000000000000..cc1cf731050d1 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/codec_mjpeg.h -@@ -0,0 +1,13 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 Maxime Jourdan -+ */ -+ -+#ifndef __MESON_VDEC_CODEC_MJPEG_H_ -+#define __MESON_VDEC_CODEC_MJPEG_H_ -+ -+#include "vdec.h" -+ -+extern struct amvdec_codec_ops codec_mjpeg_ops; -+ -+#endif -\ No newline at end of file -diff --git a/drivers/media/platform/meson/vdec/vdec_platform.c b/drivers/media/platform/meson/vdec/vdec_platform.c -index 135d7566d716a..1181832b5fe1e 100644 ---- a/drivers/media/platform/meson/vdec/vdec_platform.c -+++ b/drivers/media/platform/meson/vdec/vdec_platform.c -@@ -11,9 +11,20 @@ - #include "codec_mpeg12.h" - #include "codec_h264.h" - #include "codec_mpeg4.h" -+#include "codec_mjpeg.h" - - static const struct amvdec_format vdec_formats_gxbb[] = { - { -+ .pixfmt = V4L2_PIX_FMT_MJPEG, -+ .min_buffers = 4, -+ .max_buffers = 4, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mjpeg_ops, -+ .firmware_path = "meson/gx/vmjpeg_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_MPEG4, - .min_buffers = 8, - .max_buffers = 8, -@@ -78,6 +89,16 @@ static const struct amvdec_format vdec_formats_gxbb[] = { - - static const struct amvdec_format vdec_formats_gxl[] = { - { -+ .pixfmt = V4L2_PIX_FMT_MJPEG, -+ .min_buffers = 4, -+ .max_buffers = 4, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mjpeg_ops, -+ .firmware_path = "meson/gx/vmjpeg_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_MPEG4, - .min_buffers = 8, - .max_buffers = 8, -@@ -142,6 +163,16 @@ static const struct amvdec_format vdec_formats_gxl[] = { - - static const struct amvdec_format vdec_formats_gxm[] = { - { -+ .pixfmt = V4L2_PIX_FMT_MJPEG, -+ .min_buffers = 4, -+ .max_buffers = 4, -+ .max_width = 1920, -+ .max_height = 1080, -+ .vdec_ops = &vdec_1_ops, -+ .codec_ops = &codec_mjpeg_ops, -+ .firmware_path = "meson/gx/vmjpeg_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_YUV420M, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_MPEG4, - .min_buffers = 8, - .max_buffers = 8, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/012_linux-4.18.y-v4l-0012-media-videodev2.h_add_amlogic_compressed_format.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/012_linux-4.18.y-v4l-0012-media-videodev2.h_add_amlogic_compressed_format.patch deleted file mode 100644 index 0ce67418c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/012_linux-4.18.y-v4l-0012-media-videodev2.h_add_amlogic_compressed_format.patch +++ /dev/null @@ -1,26 +0,0 @@ -From 4f40ed63fe484c78d02e3d0583a7f44f815980f3 Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Wed, 29 Aug 2018 18:36:09 +0200 -Subject: [PATCH] media: videodev2.h; Add Amlogic compressed format - -Add V4L2_PIX_FMT_AM21C which is a lossless, compressed framebuffer -format. - -It is used by the video decoding and the display IP on many Amlogic -SoCs. ---- - include/uapi/linux/videodev2.h | 1 + - 1 file changed, 1 insertion(+) - -diff --git a/include/uapi/linux/videodev2.h b/include/uapi/linux/videodev2.h -index 600877be5c229..0568053e3aff9 100644 ---- a/include/uapi/linux/videodev2.h -+++ b/include/uapi/linux/videodev2.h -@@ -668,6 +668,7 @@ struct v4l2_pix_format { - #define V4L2_PIX_FMT_Y12I v4l2_fourcc('Y', '1', '2', 'I') /* Greyscale 12-bit L/R interleaved */ - #define V4L2_PIX_FMT_Z16 v4l2_fourcc('Z', '1', '6', ' ') /* Depth data 16-bit */ - #define V4L2_PIX_FMT_MT21C v4l2_fourcc('M', 'T', '2', '1') /* Mediatek compressed block mode */ -+#define V4L2_PIX_FMT_AM21C v4l2_fourcc('A', 'M', '2', '1') /* Amlogic compressed block mode */ - #define V4L2_PIX_FMT_INZI v4l2_fourcc('I', 'N', 'Z', 'I') /* Intel Planar Greyscale 10-bit and Depth 16-bit */ - - /* 10bit raw bayer packed, 32 bytes for every 25 pixels, last LSB 6 bits unused */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/013_linux-4.18.y-v4l-0013-media-meson-vdec-add_v4l2_pix_fmt_am21c_support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/013_linux-4.18.y-v4l-0013-media-meson-vdec-add_v4l2_pix_fmt_am21c_support.patch deleted file mode 100644 index bec43de46..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/013_linux-4.18.y-v4l-0013-media-meson-vdec-add_v4l2_pix_fmt_am21c_support.patch +++ /dev/null @@ -1,103 +0,0 @@ -From 88eb5d85f62d7a41559f3b9c15ec69b07c4ee005 Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Wed, 29 Aug 2018 18:46:31 +0200 -Subject: [PATCH] media: meson: vdec: add V4L2_PIX_FMT_AM21C support - -Support the lossless, framebuffer compression format from Amlogic. - -Signed-off-by: Maxime Jourdan ---- - drivers/media/platform/meson/vdec/vdec.c | 7 +++++ - .../media/platform/meson/vdec/vdec_helpers.c | 31 +++++++++++++++++++ - .../media/platform/meson/vdec/vdec_helpers.h | 4 +++ - 3 files changed, 42 insertions(+) - -diff --git a/drivers/media/platform/meson/vdec/vdec.c b/drivers/media/platform/meson/vdec/vdec.c -index 32e1e22282970..d5f8fed2886f5 100644 ---- a/drivers/media/platform/meson/vdec/vdec.c -+++ b/drivers/media/platform/meson/vdec/vdec.c -@@ -182,6 +182,9 @@ static int vdec_queue_setup(struct vb2_queue *q, - sizes[1] = amvdec_get_output_size(sess) / 4; - sizes[2] = amvdec_get_output_size(sess) / 4; - *num_planes = 3; -+ } else if (pixfmt_cap == V4L2_PIX_FMT_AM21C) { -+ sizes[0] = amvdec_am21c_size(sess->width, sess->height); -+ *num_planes = 1; - } - *num_buffers = min(max(*num_buffers, fmt_out->min_buffers), - fmt_out->max_buffers); -@@ -444,6 +447,10 @@ vdec_try_fmt_common(struct amvdec_session *sess, u32 size, - get_output_size(pixmp->width, pixmp->height) / 4; - pfmt[2].bytesperline = ALIGN(pixmp->width, 64) / 2; - pixmp->num_planes = 3; -+ } else if (pixmp->pixelformat == V4L2_PIX_FMT_AM21C) { -+ pfmt[0].sizeimage = -+ amvdec_am21c_size(pixmp->width, pixmp->height); -+ pfmt[0].bytesperline = 0; - } - } else { - return NULL; -diff --git a/drivers/media/platform/meson/vdec/vdec_helpers.c b/drivers/media/platform/meson/vdec/vdec_helpers.c -index 6151076297655..1c3a015eb3b33 100644 ---- a/drivers/media/platform/meson/vdec/vdec_helpers.c -+++ b/drivers/media/platform/meson/vdec/vdec_helpers.c -@@ -49,6 +49,33 @@ void amvdec_write_parser(struct amvdec_core *core, u32 reg, u32 val) - } - EXPORT_SYMBOL_GPL(amvdec_write_parser); - -+/* 4 KiB per 64x32 block */ -+u32 amvdec_am21c_body_size(u32 width, u32 height) -+{ -+ u32 width_64 = ALIGN(width, 64) / 64; -+ u32 height_32 = ALIGN(height, 32) / 32; -+ -+ return SZ_4K * width_64 * height_32; -+} -+EXPORT_SYMBOL_GPL(amvdec_am21c_body_size); -+ -+/* 32 bytes per 128x64 block */ -+u32 amvdec_am21c_head_size(u32 width, u32 height) -+{ -+ u32 width_128 = ALIGN(width, 128) / 128; -+ u32 height_64 = ALIGN(height, 64) / 64; -+ -+ return 32 * width_128 * height_64; -+} -+EXPORT_SYMBOL_GPL(amvdec_am21c_head_size); -+ -+u32 amvdec_am21c_size(u32 width, u32 height) -+{ -+ return ALIGN(amvdec_am21c_body_size(width, height) + -+ amvdec_am21c_head_size(width, height), SZ_64K); -+} -+EXPORT_SYMBOL_GPL(amvdec_am21c_size); -+ - static int canvas_alloc(struct amvdec_session *sess, u8 *canvas_id) - { - int ret; -@@ -228,6 +255,10 @@ void amvdec_dst_buf_done(struct amvdec_session *sess, - vbuf->vb2_buf.planes[1].bytesused = output_size / 4; - vbuf->vb2_buf.planes[2].bytesused = output_size / 4; - break; -+ case V4L2_PIX_FMT_AM21C: -+ vbuf->vb2_buf.planes[0].bytesused = -+ amvdec_am21c_size(sess->width, sess->height); -+ break; - } - vbuf->vb2_buf.timestamp = tmp->ts; - vbuf->sequence = sess->sequence_cap++; -diff --git a/drivers/media/platform/meson/vdec/vdec_helpers.h b/drivers/media/platform/meson/vdec/vdec_helpers.h -index 352c6b4c4b84c..d8a4a2c563af0 100644 ---- a/drivers/media/platform/meson/vdec/vdec_helpers.h -+++ b/drivers/media/platform/meson/vdec/vdec_helpers.h -@@ -26,6 +26,10 @@ void amvdec_clear_dos_bits(struct amvdec_core *core, u32 reg, u32 val); - u32 amvdec_read_parser(struct amvdec_core *core, u32 reg); - void amvdec_write_parser(struct amvdec_core *core, u32 reg, u32 val); - -+u32 amvdec_am21c_body_size(u32 width, u32 height); -+u32 amvdec_am21c_head_size(u32 width, u32 height); -+u32 amvdec_am21c_size(u32 width, u32 height); -+ - void amvdec_dst_buf_done_idx(struct amvdec_session *sess, u32 buf_idx, - u32 field); - void amvdec_dst_buf_done(struct amvdec_session *sess, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/014_linux-4.18.y-v4l-0014-media-meson-vdec-add_hevc_decoding_support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/014_linux-4.18.y-v4l-0014-media-meson-vdec-add_hevc_decoding_support.patch deleted file mode 100644 index c178dad35..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/014_linux-4.18.y-v4l-0014-media-meson-vdec-add_hevc_decoding_support.patch +++ /dev/null @@ -1,2617 +0,0 @@ -From 3ff8b6ea023464f8de12835ed90211e3f66ed0f4 Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Wed, 29 Aug 2018 18:48:35 +0200 -Subject: [PATCH] media: meson: vdec: add HEVC decoding support - -Add support for V4L2_PIX_FMT_HEVC ---- - drivers/media/platform/meson/vdec/Makefile | 4 +- - .../media/platform/meson/vdec/codec_hevc.c | 1517 +++++++++++++++++ - .../media/platform/meson/vdec/codec_hevc.h | 13 + - drivers/media/platform/meson/vdec/hevc_regs.h | 742 ++++++++ - drivers/media/platform/meson/vdec/vdec_hevc.c | 191 +++ - drivers/media/platform/meson/vdec/vdec_hevc.h | 22 + - .../media/platform/meson/vdec/vdec_platform.c | 32 + - 7 files changed, 2519 insertions(+), 2 deletions(-) - create mode 100644 drivers/media/platform/meson/vdec/codec_hevc.c - create mode 100644 drivers/media/platform/meson/vdec/codec_hevc.h - create mode 100644 drivers/media/platform/meson/vdec/hevc_regs.h - create mode 100644 drivers/media/platform/meson/vdec/vdec_hevc.c - create mode 100644 drivers/media/platform/meson/vdec/vdec_hevc.h - -diff --git a/drivers/media/platform/meson/vdec/Makefile b/drivers/media/platform/meson/vdec/Makefile -index 20c23f9015ebd..f34b7a2961511 100644 ---- a/drivers/media/platform/meson/vdec/Makefile -+++ b/drivers/media/platform/meson/vdec/Makefile -@@ -2,7 +2,7 @@ - # Makefile for Amlogic meson video decoder driver - - meson-vdec-objs = esparser.o vdec.o vdec_helpers.o vdec_platform.o --meson-vdec-objs += vdec_1.o --meson-vdec-objs += codec_mpeg12.o codec_h264.o codec_mpeg4.o codec_mjpeg.o -+meson-vdec-objs += vdec_1.o vdec_hevc.o -+meson-vdec-objs += codec_mpeg12.o codec_h264.o codec_mpeg4.o codec_mjpeg.o codec_hevc.o - - obj-$(CONFIG_VIDEO_MESON_VDEC) += meson-vdec.o -diff --git a/drivers/media/platform/meson/vdec/codec_hevc.c b/drivers/media/platform/meson/vdec/codec_hevc.c -new file mode 100644 -index 0000000000000..5e69717ba0570 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/codec_hevc.c -@@ -0,0 +1,1517 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 Maxime Jourdan -+ * Copyright (C) 2015 Amlogic, Inc. All rights reserved. -+ */ -+ -+#include -+#include -+ -+#include "codec_hevc.h" -+#include "dos_regs.h" -+#include "hevc_regs.h" -+#include "vdec_helpers.h" -+ -+/* HEVC reg mapping */ -+#define HEVC_DEC_STATUS_REG HEVC_ASSIST_SCRATCH_0 -+ #define HEVC_ACTION_DONE 0xff -+#define HEVC_RPM_BUFFER HEVC_ASSIST_SCRATCH_1 -+#define HEVC_DECODE_INFO HEVC_ASSIST_SCRATCH_1 -+#define HEVC_SHORT_TERM_RPS HEVC_ASSIST_SCRATCH_2 -+#define HEVC_VPS_BUFFER HEVC_ASSIST_SCRATCH_3 -+#define HEVC_SPS_BUFFER HEVC_ASSIST_SCRATCH_4 -+#define HEVC_PPS_BUFFER HEVC_ASSIST_SCRATCH_5 -+#define HEVC_SAO_UP HEVC_ASSIST_SCRATCH_6 -+#define HEVC_STREAM_SWAP_BUFFER HEVC_ASSIST_SCRATCH_7 -+#define H265_MMU_MAP_BUFFER HEVC_ASSIST_SCRATCH_7 -+#define HEVC_STREAM_SWAP_BUFFER2 HEVC_ASSIST_SCRATCH_8 -+#define HEVC_sao_mem_unit HEVC_ASSIST_SCRATCH_9 -+#define HEVC_SAO_ABV HEVC_ASSIST_SCRATCH_A -+#define HEVC_sao_vb_size HEVC_ASSIST_SCRATCH_B -+#define HEVC_SAO_VB HEVC_ASSIST_SCRATCH_C -+#define HEVC_SCALELUT HEVC_ASSIST_SCRATCH_D -+#define HEVC_WAIT_FLAG HEVC_ASSIST_SCRATCH_E -+#define RPM_CMD_REG HEVC_ASSIST_SCRATCH_F -+#define LMEM_DUMP_ADR HEVC_ASSIST_SCRATCH_F -+#define DEBUG_REG1 HEVC_ASSIST_SCRATCH_G -+#define HEVC_DECODE_MODE2 HEVC_ASSIST_SCRATCH_H -+#define NAL_SEARCH_CTL HEVC_ASSIST_SCRATCH_I -+#define HEVC_DECODE_MODE HEVC_ASSIST_SCRATCH_J -+ #define DECODE_MODE_SINGLE 0 -+#define DECODE_STOP_POS HEVC_ASSIST_SCRATCH_K -+#define HEVC_AUX_ADR HEVC_ASSIST_SCRATCH_L -+#define HEVC_AUX_DATA_SIZE HEVC_ASSIST_SCRATCH_M -+#define HEVC_DECODE_SIZE HEVC_ASSIST_SCRATCH_N -+ -+#define HEVCD_MPP_ANC2AXI_TBL_DATA (0x3464 * 4) -+ -+#define HEVC_CM_BODY_START_ADDR (0x3626 * 4) -+#define HEVC_CM_BODY_LENGTH (0x3627 * 4) -+#define HEVC_CM_HEADER_LENGTH (0x3629 * 4) -+#define HEVC_CM_HEADER_OFFSET (0x362b * 4) -+ -+#define AMRISC_MAIN_REQ 0x04 -+ -+/* HEVC Constants */ -+#define MAX_REF_PIC_NUM 24 -+#define MAX_REF_ACTIVE 16 -+#define MPRED_MV_BUF_SIZE 0x120000 -+#define MAX_TILE_COL_NUM 10 -+#define MAX_TILE_ROW_NUM 20 -+#define MAX_SLICE_NUM 800 -+#define INVALID_POC 0x80000000 -+ -+/* HEVC Workspace layout */ -+#define IPP_OFFSET 0x00 -+#define SAO_ABV_OFFSET (IPP_OFFSET + 0x4000) -+#define SAO_VB_OFFSET (SAO_ABV_OFFSET + 0x30000) -+#define SH_TM_RPS_OFFSET (SAO_VB_OFFSET + 0x30000) -+#define VPS_OFFSET (SH_TM_RPS_OFFSET + 0x800) -+#define SPS_OFFSET (VPS_OFFSET + 0x800) -+#define PPS_OFFSET (SPS_OFFSET + 0x800) -+#define SAO_UP_OFFSET (PPS_OFFSET + 0x2000) -+#define SWAP_BUF_OFFSET (SAO_UP_OFFSET + 0x800) -+#define SWAP_BUF2_OFFSET (SWAP_BUF_OFFSET + 0x800) -+#define SCALELUT_OFFSET (SWAP_BUF2_OFFSET + 0x800) -+#define DBLK_PARA_OFFSET (SCALELUT_OFFSET + 0x8000) -+#define DBLK_DATA_OFFSET (DBLK_PARA_OFFSET + 0x20000) -+#define MMU_VBH_OFFSET (DBLK_DATA_OFFSET + 0x40000) -+#define MPRED_ABV_OFFSET (MMU_VBH_OFFSET + 0x5000) -+#define MPRED_MV_OFFSET (MPRED_ABV_OFFSET + 0x8000) -+#define RPM_OFFSET (MPRED_MV_OFFSET + MPRED_MV_BUF_SIZE * MAX_REF_PIC_NUM) -+#define LMEM_OFFSET (RPM_OFFSET + 0x100) -+ -+/* ISR decode status */ -+#define HEVC_DEC_IDLE 0x0 -+#define HEVC_NAL_UNIT_VPS 0x1 -+#define HEVC_NAL_UNIT_SPS 0x2 -+#define HEVC_NAL_UNIT_PPS 0x3 -+#define HEVC_NAL_UNIT_CODED_SLICE_SEGMENT 0x4 -+#define HEVC_CODED_SLICE_SEGMENT_DAT 0x5 -+#define HEVC_SLICE_DECODING 0x6 -+#define HEVC_NAL_UNIT_SEI 0x7 -+#define HEVC_SLICE_SEGMENT_DONE 0x8 -+#define HEVC_NAL_SEARCH_DONE 0x9 -+#define HEVC_DECPIC_DATA_DONE 0xa -+#define HEVC_DECPIC_DATA_ERROR 0xb -+#define HEVC_SEI_DAT 0xc -+#define HEVC_SEI_DAT_DONE 0xd -+ -+/* RPM misc_flag0 */ -+#define PCM_LOOP_FILTER_DISABLED_FLAG_BIT 0 -+#define PCM_ENABLE_FLAG_BIT 1 -+#define LOOP_FILER_ACROSS_TILES_ENABLED_FLAG_BIT 2 -+#define PPS_LOOP_FILTER_ACROSS_SLICES_ENABLED_FLAG_BIT 3 -+#define DEBLOCKING_FILTER_OVERRIDE_ENABLED_FLAG_BIT 4 -+#define PPS_DEBLOCKING_FILTER_DISABLED_FLAG_BIT 5 -+#define DEBLOCKING_FILTER_OVERRIDE_FLAG_BIT 6 -+#define SLICE_DEBLOCKING_FILTER_DISABLED_FLAG_BIT 7 -+#define SLICE_SAO_LUMA_FLAG_BIT 8 -+#define SLICE_SAO_CHROMA_FLAG_BIT 9 -+#define SLICE_LOOP_FILTER_ACROSS_SLICES_ENABLED_FLAG_BIT 10 -+ -+/* Buffer sizes */ -+#define SIZE_WORKSPACE ALIGN(LMEM_OFFSET + 0xA00, 64 * SZ_1K) -+#define SIZE_AUX (SZ_1K * 16) -+#define SIZE_FRAME_MMU (0x1200 * 4) -+#define RPM_SIZE 0x80 -+#define RPS_USED_BIT 14 -+ -+#define PARSER_CMD_SKIP_CFG_0 0x0000090b -+#define PARSER_CMD_SKIP_CFG_1 0x1b14140f -+#define PARSER_CMD_SKIP_CFG_2 0x001b1910 -+static const u16 parser_cmd[] = { -+ 0x0401, 0x8401, 0x0800, 0x0402, -+ 0x9002, 0x1423, 0x8CC3, 0x1423, -+ 0x8804, 0x9825, 0x0800, 0x04FE, -+ 0x8406, 0x8411, 0x1800, 0x8408, -+ 0x8409, 0x8C2A, 0x9C2B, 0x1C00, -+ 0x840F, 0x8407, 0x8000, 0x8408, -+ 0x2000, 0xA800, 0x8410, 0x04DE, -+ 0x840C, 0x840D, 0xAC00, 0xA000, -+ 0x08C0, 0x08E0, 0xA40E, 0xFC00, -+ 0x7C00 -+}; -+ -+/* Data received from the HW in this form, do not rearrange */ -+union rpm_param { -+ struct { -+ u16 data[RPM_SIZE]; -+ } l; -+ struct { -+ u16 CUR_RPS[MAX_REF_ACTIVE]; -+ u16 num_ref_idx_l0_active; -+ u16 num_ref_idx_l1_active; -+ u16 slice_type; -+ u16 slice_temporal_mvp_enable_flag; -+ u16 dependent_slice_segment_flag; -+ u16 slice_segment_address; -+ u16 num_title_rows_minus1; -+ u16 pic_width_in_luma_samples; -+ u16 pic_height_in_luma_samples; -+ u16 log2_min_coding_block_size_minus3; -+ u16 log2_diff_max_min_coding_block_size; -+ u16 log2_max_pic_order_cnt_lsb_minus4; -+ u16 POClsb; -+ u16 collocated_from_l0_flag; -+ u16 collocated_ref_idx; -+ u16 log2_parallel_merge_level; -+ u16 five_minus_max_num_merge_cand; -+ u16 sps_num_reorder_pics_0; -+ u16 modification_flag; -+ u16 tiles_flags; -+ u16 num_tile_columns_minus1; -+ u16 num_tile_rows_minus1; -+ u16 tile_width[8]; -+ u16 tile_height[8]; -+ u16 misc_flag0; -+ u16 pps_beta_offset_div2; -+ u16 pps_tc_offset_div2; -+ u16 slice_beta_offset_div2; -+ u16 slice_tc_offset_div2; -+ u16 pps_cb_qp_offset; -+ u16 pps_cr_qp_offset; -+ u16 first_slice_segment_in_pic_flag; -+ u16 m_temporalId; -+ u16 m_nalUnitType; -+ u16 vui_num_units_in_tick_hi; -+ u16 vui_num_units_in_tick_lo; -+ u16 vui_time_scale_hi; -+ u16 vui_time_scale_lo; -+ u16 bit_depth; -+ u16 profile_etc; -+ u16 sei_frame_field_info; -+ u16 video_signal_type; -+ u16 modification_list[0x20]; -+ u16 conformance_window_flag; -+ u16 conf_win_left_offset; -+ u16 conf_win_right_offset; -+ u16 conf_win_top_offset; -+ u16 conf_win_bottom_offset; -+ u16 chroma_format_idc; -+ u16 color_description; -+ u16 aspect_ratio_idc; -+ u16 sar_width; -+ u16 sar_height; -+ } p; -+}; -+ -+enum nal_unit_type { -+ NAL_UNIT_CODED_SLICE_BLA = 16, -+ NAL_UNIT_CODED_SLICE_BLANT = 17, -+ NAL_UNIT_CODED_SLICE_BLA_N_LP = 18, -+ NAL_UNIT_CODED_SLICE_IDR = 19, -+ NAL_UNIT_CODED_SLICE_IDR_N_LP = 20, -+}; -+ -+enum slice_type { -+ B_SLICE = 0, -+ P_SLICE = 1, -+ I_SLICE = 2, -+}; -+ -+/* A frame being decoded */ -+struct hevc_frame { -+ struct list_head list; -+ struct vb2_v4l2_buffer *vbuf; -+ u32 poc; -+ -+ int referenced; -+ u32 num_reorder_pic; -+ -+ u32 cur_slice_idx; -+ u32 cur_slice_type; -+ -+ /* 2 lists (L0/L1) ; 800 slices ; 16 refs */ -+ u32 ref_poc_list[2][MAX_SLICE_NUM][MAX_REF_ACTIVE]; -+ u32 ref_num[2]; -+}; -+ -+struct hevc_tile { -+ int width; -+ int height; -+ int start_cu_x; -+ int start_cu_y; -+ -+ dma_addr_t sao_vb_start_addr; -+ dma_addr_t sao_abv_start_addr; -+}; -+ -+struct codec_hevc { -+ /* Current decoding status provided by the ISR */ -+ u32 dec_status; -+ -+ struct mutex lock; -+ -+ /* Buffer for the HEVC Workspace */ -+ void *workspace_vaddr; -+ dma_addr_t workspace_paddr; -+ -+ /* AUX buffer */ -+ void *aux_vaddr; -+ dma_addr_t aux_paddr; -+ -+ /* Frame MMU buffer (>= GXL) ; unused for now */ -+ void *frame_mmu_vaddr; -+ dma_addr_t frame_mmu_paddr; -+ -+ /* Contains many information parsed from the bitstream */ -+ union rpm_param rpm_param; -+ -+ /* Information computed from the RPM */ -+ u32 lcu_size; // Largest Coding Unit -+ u32 lcu_x_num; -+ u32 lcu_y_num; -+ u32 lcu_total; -+ -+ /* Current Frame being handled */ -+ struct hevc_frame *cur_frame; -+ u32 curr_poc; -+ /* Collocated Reference Picture */ -+ struct hevc_frame *col_frame; -+ u32 col_poc; -+ -+ /* All ref frames used by the HW at a given time */ -+ struct list_head ref_frames_list; -+ u32 frames_num; -+ -+ /* Resolution reported by the hardware */ -+ u32 width; -+ u32 height; -+ -+ u32 iPrevTid0POC; -+ u32 slice_segment_addr; -+ u32 slice_addr; -+ u32 ldc_flag; -+ -+ /* Tiles */ -+ u32 num_tile_col; -+ u32 num_tile_row; -+ struct hevc_tile m_tile[MAX_TILE_ROW_NUM][MAX_TILE_COL_NUM]; -+ u32 tile_start_lcu_x; -+ u32 tile_start_lcu_y; -+ u32 tile_width_lcu; -+ u32 tile_height_lcu; -+ -+ /* Whether we detected the bitstream as 10-bit */ -+ int is_10bit; -+ -+ /* Whether we already configured the buffer list in HW */ -+ int is_buflist_init; -+ -+ /* In case of downsampling (decoding with FBC but outputting in NV12M), -+ * we need to allocate additional buffers for FBC. -+ */ -+ void *fbc_buffer_vaddr[24]; -+ dma_addr_t fbc_buffer_paddr[24]; -+}; -+ -+/* Returns 1 if we must use framebuffer compression */ -+static int codec_hevc_use_fbc(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ return sess->pixfmt_cap == V4L2_PIX_FMT_AM21C || hevc->is_10bit; -+} -+ -+/* Returns 1 if we are decoding 10-bit but outputting 8-bit NV12 */ -+static int codec_hevc_use_downsample(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ return sess->pixfmt_cap == V4L2_PIX_FMT_NV12M && hevc->is_10bit; -+} -+ -+static u32 codec_hevc_num_pending_bufs(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc; -+ u32 ret; -+ -+ hevc = sess->priv; -+ if (!hevc) -+ return 0; -+ -+ mutex_lock(&hevc->lock); -+ ret = hevc->frames_num; -+ mutex_unlock(&hevc->lock); -+ -+ return ret; -+} -+ -+/* Update the L0 and L1 reference lists for a given frame */ -+static void codec_hevc_update_frame_refs(struct amvdec_session *sess, struct hevc_frame *frame) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ union rpm_param *params = &hevc->rpm_param; -+ int i; -+ int num_neg = 0; -+ int num_pos = 0; -+ int total_num; -+ int num_ref_idx_l0_active = -+ (params->p.num_ref_idx_l0_active > MAX_REF_ACTIVE) ? -+ MAX_REF_ACTIVE : params->p.num_ref_idx_l0_active; -+ int num_ref_idx_l1_active = -+ (params->p.num_ref_idx_l1_active > MAX_REF_ACTIVE) ? -+ MAX_REF_ACTIVE : params->p.num_ref_idx_l1_active; -+ int ref_picset0[MAX_REF_ACTIVE] = { 0 }; -+ int ref_picset1[MAX_REF_ACTIVE] = { 0 }; -+ -+ for (i = 0; i < MAX_REF_ACTIVE; i++) { -+ frame->ref_poc_list[0][frame->cur_slice_idx][i] = 0; -+ frame->ref_poc_list[1][frame->cur_slice_idx][i] = 0; -+ } -+ -+ for (i = 0; i < MAX_REF_ACTIVE; i++) { -+ u16 cur_rps = params->p.CUR_RPS[i]; -+ int delt = cur_rps & ((1 << (RPS_USED_BIT - 1)) - 1); -+ -+ if (cur_rps & 0x8000) -+ break; -+ -+ if (!((cur_rps >> RPS_USED_BIT) & 1)) -+ continue; -+ -+ if ((cur_rps >> (RPS_USED_BIT - 1)) & 1) { -+ ref_picset0[num_neg] = -+ frame->poc - ((1 << (RPS_USED_BIT - 1)) - delt); -+ num_neg++; -+ } else { -+ ref_picset1[num_pos] = frame->poc + delt; -+ num_pos++; -+ } -+ } -+ -+ total_num = num_neg + num_pos; -+ -+ if (total_num <= 0) -+ goto end; -+ -+ for (i = 0; i < num_ref_idx_l0_active; i++) { -+ int cidx; -+ if (params->p.modification_flag & 0x1) -+ cidx = params->p.modification_list[i]; -+ else -+ cidx = i % total_num; -+ -+ frame->ref_poc_list[0][frame->cur_slice_idx][i] = -+ cidx >= num_neg ? ref_picset1[cidx - num_neg] : -+ ref_picset0[cidx]; -+ } -+ -+ if (params->p.slice_type != B_SLICE) -+ goto end; -+ -+ if (params->p.modification_flag & 0x2) { -+ for (i = 0; i < num_ref_idx_l1_active; i++) { -+ int cidx; -+ if (params->p.modification_flag & 0x1) -+ cidx = -+ params->p.modification_list[num_ref_idx_l0_active + i]; -+ else -+ cidx = params->p.modification_list[i]; -+ -+ frame->ref_poc_list[1][frame->cur_slice_idx][i] = -+ (cidx >= num_pos) ? ref_picset0[cidx - num_pos] -+ : ref_picset1[cidx]; -+ } -+ } else { -+ for (i = 0; i < num_ref_idx_l1_active; i++) { -+ int cidx = i % total_num; -+ frame->ref_poc_list[1][frame->cur_slice_idx][i] = -+ cidx >= num_pos ? ref_picset0[cidx - num_pos] : -+ ref_picset1[cidx]; -+ } -+ } -+ -+end: -+ frame->ref_num[0] = num_ref_idx_l0_active; -+ frame->ref_num[1] = num_ref_idx_l1_active; -+ -+ dev_dbg(sess->core->dev, -+ "Frame %u; slice %u; slice_type %u; num_l0 %u; num_l1 %u\n", -+ frame->poc, frame->cur_slice_idx, params->p.slice_type, -+ frame->ref_num[0], frame->ref_num[1]); -+} -+ -+static void codec_hevc_update_ldc_flag(struct codec_hevc *hevc) -+{ -+ struct hevc_frame *frame = hevc->cur_frame; -+ u32 slice_type = frame->cur_slice_type; -+ int i; -+ -+ hevc->ldc_flag = 0; -+ -+ if (slice_type == I_SLICE) -+ return; -+ -+ hevc->ldc_flag = 1; -+ for (i = 0; (i < frame->ref_num[0]) && hevc->ldc_flag; i++) { -+ if (frame->ref_poc_list[0][frame->cur_slice_idx][i] > frame->poc) { -+ hevc->ldc_flag = 0; -+ break; -+ } -+ } -+ -+ if (slice_type == P_SLICE) -+ return; -+ -+ for (i = 0; (i < frame->ref_num[1]) && hevc->ldc_flag; i++) { -+ if (frame->ref_poc_list[1][frame->cur_slice_idx][i] > frame->poc) { -+ hevc->ldc_flag = 0; -+ break; -+ } -+ } -+} -+ -+/* Tag "old" frames that are no longer referenced */ -+static void codec_hevc_update_referenced(struct codec_hevc *hevc) -+{ -+ union rpm_param *param = &hevc->rpm_param; -+ struct hevc_frame *frame; -+ int i; -+ u32 curr_poc = hevc->curr_poc; -+ -+ list_for_each_entry(frame, &hevc->ref_frames_list, list) { -+ int is_referenced = 0; -+ u32 poc_tmp; -+ -+ if (!frame->referenced) -+ continue; -+ -+ for (i = 0; i < MAX_REF_ACTIVE; i++) { -+ int delt; -+ if (param->p.CUR_RPS[i] & 0x8000) -+ break; -+ -+ delt = param->p.CUR_RPS[i] & ((1 << (RPS_USED_BIT - 1)) - 1); -+ if (param->p.CUR_RPS[i] & (1 << (RPS_USED_BIT - 1))) { -+ poc_tmp = curr_poc - ((1 << (RPS_USED_BIT - 1)) - delt); -+ } else -+ poc_tmp = curr_poc + delt; -+ if (poc_tmp == frame->poc) { -+ is_referenced = 1; -+ break; -+ } -+ } -+ -+ frame->referenced = is_referenced; -+ } -+} -+ -+static struct hevc_frame *codec_hevc_get_lowest_poc_frame(struct codec_hevc *hevc) -+{ -+ struct hevc_frame *tmp, *ret = NULL; -+ u32 poc = INT_MAX; -+ -+ list_for_each_entry(tmp, &hevc->ref_frames_list, list) { -+ if (tmp->poc < poc) { -+ ret = tmp; -+ poc = tmp->poc; -+ } -+ } -+ -+ return ret; -+} -+ -+/* Try to output as many frames as possible */ -+static void codec_hevc_output_frames(struct amvdec_session *sess) -+{ -+ struct hevc_frame *tmp; -+ struct codec_hevc *hevc = sess->priv; -+ -+ while ((tmp = codec_hevc_get_lowest_poc_frame(hevc))) { -+ if (hevc->curr_poc && -+ (tmp->referenced || tmp->num_reorder_pic >= hevc->frames_num)) -+ break; -+ -+ dev_dbg(sess->core->dev, "DONE frame poc %u; vbuf %u\n", -+ tmp->poc, tmp->vbuf->vb2_buf.index); -+ amvdec_dst_buf_done(sess, tmp->vbuf, V4L2_FIELD_NONE); -+ list_del(&tmp->list); -+ kfree(tmp); -+ hevc->frames_num--; -+ } -+} -+ -+/* Configure frame buffer decompression */ -+static void codec_hevc_setup_decode_head(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ u32 body_size = amvdec_am21c_body_size(sess->width, sess->height); -+ u32 head_size = amvdec_am21c_head_size(sess->width, sess->height); -+ -+ if (!codec_hevc_use_fbc(sess)) { -+ /* Enable 2-plane reference read mode for MC */ -+ amvdec_write_dos(core, HEVCD_MPP_DECOMP_CTL1, BIT(31)); -+ return; -+ } -+ -+ amvdec_write_dos(core, HEVCD_MPP_DECOMP_CTL1, 0); -+ amvdec_write_dos(core, HEVCD_MPP_DECOMP_CTL2, body_size / 32); -+ amvdec_write_dos(core, HEVC_CM_BODY_LENGTH, body_size); -+ amvdec_write_dos(core, HEVC_CM_HEADER_OFFSET, body_size); -+ amvdec_write_dos(core, HEVC_CM_HEADER_LENGTH, head_size); -+} -+ -+static void codec_hevc_setup_buffers_gxbb(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_hevc *hevc = sess->priv; -+ struct v4l2_m2m_buffer *buf; -+ u32 buf_num = v4l2_m2m_num_dst_bufs_ready(sess->m2m_ctx); -+ dma_addr_t buf_y_paddr = 0; -+ dma_addr_t buf_uv_paddr = 0; -+ u32 idx = 0; -+ u32 val; -+ int i; -+ -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_CONF_ADDR, 0); -+ -+ v4l2_m2m_for_each_dst_buf(sess->m2m_ctx, buf) { -+ idx = buf->vb.vb2_buf.index; -+ -+ if (codec_hevc_use_downsample(sess)) -+ buf_y_paddr = hevc->fbc_buffer_paddr[idx]; -+ else -+ buf_y_paddr = vb2_dma_contig_plane_dma_addr(&buf->vb.vb2_buf, 0); -+ -+ if (codec_hevc_use_fbc(sess)) { -+ val = buf_y_paddr | (idx << 8) | 1; -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_CMD_ADDR, val); -+ } else if (sess->pixfmt_cap == V4L2_PIX_FMT_NV12M) { -+ buf_uv_paddr = vb2_dma_contig_plane_dma_addr(&buf->vb.vb2_buf, 1); -+ val = buf_y_paddr | ((idx * 2) << 8) | 1; -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_CMD_ADDR, val); -+ val = buf_uv_paddr | ((idx * 2 + 1) << 8) | 1; -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_CMD_ADDR, val); -+ } -+ } -+ -+ if (codec_hevc_use_fbc(sess)) -+ val = buf_y_paddr | (idx << 8) | 1; -+ else -+ val = buf_y_paddr | ((idx * 2) << 8) | 1; -+ -+ /* Fill the remaining unused slots with the last buffer's Y addr */ -+ for (i = buf_num; i < MAX_REF_PIC_NUM; ++i) -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_CMD_ADDR, val); -+ -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_CONF_ADDR, 1); -+ amvdec_write_dos(core, HEVCD_MPP_ANC_CANVAS_ACCCONFIG_ADDR, 1); -+ for (i = 0; i < 32; ++i) -+ amvdec_write_dos(core, HEVCD_MPP_ANC_CANVAS_DATA_ADDR, 0); -+} -+ -+static void codec_hevc_setup_buffers_gxl(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_hevc *hevc = sess->priv; -+ struct v4l2_m2m_buffer *buf; -+ u32 buf_num = v4l2_m2m_num_dst_bufs_ready(sess->m2m_ctx); -+ dma_addr_t buf_y_paddr = 0; -+ dma_addr_t buf_uv_paddr = 0; -+ int i; -+ -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_CONF_ADDR, BIT(2) | BIT(1)); -+ -+ v4l2_m2m_for_each_dst_buf(sess->m2m_ctx, buf) { -+ u32 idx = buf->vb.vb2_buf.index; -+ -+ if (codec_hevc_use_downsample(sess)) -+ buf_y_paddr = hevc->fbc_buffer_paddr[idx]; -+ else -+ buf_y_paddr = vb2_dma_contig_plane_dma_addr(&buf->vb.vb2_buf, 0); -+ -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_DATA, buf_y_paddr >> 5); -+ if (!codec_hevc_use_fbc(sess)) { -+ buf_uv_paddr = vb2_dma_contig_plane_dma_addr(&buf->vb.vb2_buf, 1); -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_DATA, buf_uv_paddr >> 5); -+ } -+ } -+ -+ /* Fill the remaining unused slots with the last buffer's Y addr */ -+ for (i = buf_num; i < MAX_REF_PIC_NUM; ++i) { -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_DATA, buf_y_paddr >> 5); -+ if (!codec_hevc_use_fbc(sess)) -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_DATA, buf_uv_paddr >> 5); -+ } -+ -+ amvdec_write_dos(core, HEVCD_MPP_ANC2AXI_TBL_CONF_ADDR, 1); -+ amvdec_write_dos(core, HEVCD_MPP_ANC_CANVAS_ACCCONFIG_ADDR, 1); -+ for (i = 0; i < 32; ++i) -+ amvdec_write_dos(core, HEVCD_MPP_ANC_CANVAS_DATA_ADDR, 0); -+} -+ -+static void codec_hevc_free_fbc_buffers(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ struct device *dev = sess->core->dev; -+ int i; -+ -+ for (i = 0; i < 24; ++i) -+ if (hevc->fbc_buffer_vaddr[i]) { -+ dma_free_coherent(dev, amvdec_am21c_size(sess->width, sess->height), hevc->fbc_buffer_vaddr[i], hevc->fbc_buffer_paddr[i]); -+ hevc->fbc_buffer_vaddr[i] = NULL; -+ } -+} -+ -+static int codec_hevc_alloc_fbc_buffers(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ struct device *dev = sess->core->dev; -+ struct v4l2_m2m_buffer *buf; -+ -+ v4l2_m2m_for_each_dst_buf(sess->m2m_ctx, buf) { -+ u32 idx = buf->vb.vb2_buf.index; -+ hevc->fbc_buffer_vaddr[idx] = dma_alloc_coherent(dev, amvdec_am21c_size(sess->width, sess->height), &hevc->fbc_buffer_paddr[idx], GFP_KERNEL); -+ if (!hevc->fbc_buffer_vaddr[idx]) { -+ dev_err(dev, "Couldn't allocate FBC buffer %u\n", idx); -+ codec_hevc_free_fbc_buffers(sess); -+ return -ENOMEM; -+ } -+ } -+ -+ return 0; -+} -+ -+static int codec_hevc_setup_buffers(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ int ret; -+ -+ if (codec_hevc_use_downsample(sess)) { -+ ret = codec_hevc_alloc_fbc_buffers(sess); -+ if (ret) -+ return ret; -+ } -+ -+ if (core->platform->revision == VDEC_REVISION_GXBB) -+ codec_hevc_setup_buffers_gxbb(sess); -+ else -+ codec_hevc_setup_buffers_gxl(sess); -+ -+ return 0; -+} -+ -+static int -+codec_hevc_setup_workspace(struct amvdec_core *core, struct codec_hevc *hevc) -+{ -+ dma_addr_t wkaddr; -+ -+ /* Allocate some memory for the HEVC decoder's state */ -+ hevc->workspace_vaddr = dma_alloc_coherent(core->dev, SIZE_WORKSPACE, &wkaddr, GFP_KERNEL); -+ if (!hevc->workspace_vaddr) { -+ dev_err(core->dev, "Failed to allocate HEVC Workspace\n"); -+ return -ENOMEM; -+ } -+ -+ hevc->workspace_paddr = wkaddr; -+ -+ amvdec_write_dos(core, HEVCD_IPP_LINEBUFF_BASE, wkaddr + IPP_OFFSET); -+ amvdec_write_dos(core, HEVC_RPM_BUFFER, wkaddr + RPM_OFFSET); -+ amvdec_write_dos(core, HEVC_SHORT_TERM_RPS, wkaddr + SH_TM_RPS_OFFSET); -+ amvdec_write_dos(core, HEVC_VPS_BUFFER, wkaddr + VPS_OFFSET); -+ amvdec_write_dos(core, HEVC_SPS_BUFFER, wkaddr + SPS_OFFSET); -+ amvdec_write_dos(core, HEVC_PPS_BUFFER, wkaddr + PPS_OFFSET); -+ amvdec_write_dos(core, HEVC_SAO_UP, wkaddr + SAO_UP_OFFSET); -+ -+ /* No MMU */ -+ amvdec_write_dos(core, HEVC_STREAM_SWAP_BUFFER, -+ wkaddr + SWAP_BUF_OFFSET); -+ amvdec_write_dos(core, HEVC_STREAM_SWAP_BUFFER2, -+ wkaddr + SWAP_BUF2_OFFSET); -+ amvdec_write_dos(core, HEVC_SCALELUT, wkaddr + SCALELUT_OFFSET); -+ amvdec_write_dos(core, HEVC_DBLK_CFG4, wkaddr + DBLK_PARA_OFFSET); -+ amvdec_write_dos(core, HEVC_DBLK_CFG5, wkaddr + DBLK_DATA_OFFSET); -+ -+ return 0; -+} -+ -+static int codec_hevc_start(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_hevc *hevc; -+ int ret; -+ int i; -+ -+ hevc = kzalloc(sizeof(*hevc), GFP_KERNEL); -+ if (!hevc) -+ return -ENOMEM; -+ -+ INIT_LIST_HEAD(&hevc->ref_frames_list); -+ hevc->curr_poc = INVALID_POC; -+ -+ ret = codec_hevc_setup_workspace(core, hevc); -+ if (ret) -+ goto free_hevc; -+ -+ amvdec_write_dos(core, HEVC_PARSER_VERSION, 0x5a5a55aa); -+ amvdec_write_dos(core, DOS_SW_RESET3, BIT(14)); -+ amvdec_write_dos(core, HEVC_CABAC_CONTROL, 0); -+ amvdec_write_dos(core, HEVC_PARSER_CORE_CONTROL, 0); -+ amvdec_write_dos(core, HEVC_STREAM_CONTROL, amvdec_read_dos(core, HEVC_STREAM_CONTROL) | 1); -+ amvdec_write_dos(core, HEVC_SHIFT_STARTCODE, 0x00000100); -+ amvdec_write_dos(core, HEVC_SHIFT_EMULATECODE, 0x00000300); -+ writel_relaxed((amvdec_read_dos(core, HEVC_PARSER_INT_CONTROL) & 0x03ffffff) | -+ (3 << 29) | (2 << 26) | BIT(24) | BIT(22) | BIT(7) | BIT(4) | 1, core->dos_base + HEVC_PARSER_INT_CONTROL); -+ amvdec_write_dos(core, HEVC_SHIFT_STATUS, amvdec_read_dos(core, HEVC_SHIFT_STATUS) | BIT(1) | 1); -+ amvdec_write_dos(core, HEVC_SHIFT_CONTROL, (3 << 6) | (2 << 4) | (2 << 1) | 1); -+ amvdec_write_dos(core, HEVC_CABAC_CONTROL, 1); -+ amvdec_write_dos(core, HEVC_PARSER_CORE_CONTROL, 1); -+ amvdec_write_dos(core, HEVC_DEC_STATUS_REG, 0); -+ -+ amvdec_write_dos(core, HEVC_IQIT_SCALELUT_WR_ADDR, 0); -+ for (i = 0; i < 1024; ++i) -+ amvdec_write_dos(core, HEVC_IQIT_SCALELUT_DATA, 0); -+ -+ amvdec_write_dos(core, HEVC_DECODE_SIZE, 0); -+ -+ amvdec_write_dos(core, HEVC_PARSER_CMD_WRITE, BIT(16)); -+ for (i = 0; i < ARRAY_SIZE(parser_cmd); ++i) -+ amvdec_write_dos(core, HEVC_PARSER_CMD_WRITE, parser_cmd[i]); -+ -+ amvdec_write_dos(core, HEVC_PARSER_CMD_SKIP_0, PARSER_CMD_SKIP_CFG_0); -+ amvdec_write_dos(core, HEVC_PARSER_CMD_SKIP_1, PARSER_CMD_SKIP_CFG_1); -+ amvdec_write_dos(core, HEVC_PARSER_CMD_SKIP_2, PARSER_CMD_SKIP_CFG_2); -+ amvdec_write_dos(core, HEVC_PARSER_IF_CONTROL, BIT(5) | BIT(2) | 1); -+ -+ amvdec_write_dos(core, HEVCD_IPP_TOP_CNTL, 1); -+ amvdec_write_dos(core, HEVCD_IPP_TOP_CNTL, BIT(1)); -+ -+ amvdec_write_dos(core, HEVC_WAIT_FLAG, 1); -+ -+ /* clear mailbox interrupt */ -+ amvdec_write_dos(core, HEVC_ASSIST_MBOX1_CLR_REG, 1); -+ /* enable mailbox interrupt */ -+ amvdec_write_dos(core, HEVC_ASSIST_MBOX1_MASK, 1); -+ /* disable PSCALE for hardware sharing */ -+ amvdec_write_dos(core, HEVC_PSCALE_CTRL, 0); -+ /* Let the uCode do all the parsing */ -+ amvdec_write_dos(core, NAL_SEARCH_CTL, 0xc); -+ -+ amvdec_write_dos(core, DECODE_STOP_POS, 0); -+ amvdec_write_dos(core, HEVC_DECODE_MODE, DECODE_MODE_SINGLE); -+ amvdec_write_dos(core, HEVC_DECODE_MODE2, 0); -+ -+ /* AUX buffers */ -+ hevc->aux_vaddr = dma_alloc_coherent(core->dev, SIZE_AUX, &hevc->aux_paddr, GFP_KERNEL); -+ if (!hevc->aux_vaddr) { -+ dev_err(core->dev, "Failed to request HEVC AUX\n"); -+ ret = -ENOMEM; -+ goto free_hevc; -+ } -+ -+ amvdec_write_dos(core, HEVC_AUX_ADR, hevc->aux_paddr); -+ amvdec_write_dos(core, HEVC_AUX_DATA_SIZE, (((SIZE_AUX) >> 4) << 16) | 0); -+ mutex_init(&hevc->lock); -+ sess->priv = hevc; -+ -+ return 0; -+ -+free_hevc: -+ kfree(hevc); -+ return ret; -+} -+ -+static void codec_hevc_flush_output(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ struct hevc_frame *tmp; -+ -+ while (!list_empty(&hevc->ref_frames_list)) { -+ tmp = codec_hevc_get_lowest_poc_frame(hevc); -+ amvdec_dst_buf_done(sess, tmp->vbuf, V4L2_FIELD_NONE); -+ list_del(&tmp->list); -+ kfree(tmp); -+ hevc->frames_num--; -+ } -+} -+ -+static int codec_hevc_stop(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ struct amvdec_core *core = sess->core; -+ -+ mutex_lock(&hevc->lock); -+ codec_hevc_flush_output(sess); -+ -+ if (hevc->workspace_vaddr) -+ dma_free_coherent(core->dev, SIZE_WORKSPACE, -+ hevc->workspace_vaddr, -+ hevc->workspace_paddr); -+ -+ if (hevc->frame_mmu_vaddr) -+ dma_free_coherent(core->dev, SIZE_FRAME_MMU, -+ hevc->frame_mmu_vaddr, -+ hevc->frame_mmu_paddr); -+ -+ if (hevc->aux_vaddr) -+ dma_free_coherent(core->dev, SIZE_AUX, -+ hevc->aux_vaddr, hevc->aux_paddr); -+ -+ codec_hevc_free_fbc_buffers(sess); -+ mutex_unlock(&hevc->lock); -+ mutex_destroy(&hevc->lock); -+ -+ return 0; -+} -+ -+static void codec_hevc_update_tiles(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ struct amvdec_core *core = sess->core; -+ u32 sao_mem_unit = (hevc->lcu_size == 16 ? 9 : hevc->lcu_size == 32 ? 14 : 24) << 4; -+ u32 pic_height_cu = (hevc->height + hevc->lcu_size - 1) / hevc->lcu_size; -+ u32 pic_width_cu = (hevc->width + hevc->lcu_size - 1) / hevc->lcu_size; -+ u32 sao_vb_size = (sao_mem_unit + (2 << 4)) * pic_height_cu; -+ u32 tiles_flags = hevc->rpm_param.p.tiles_flags; -+ -+ if (tiles_flags & 1) { -+ /* TODO; */ -+ dev_err(core->dev, "Bitstream uses tiles, NotImplemented!\n"); -+ return; -+ } -+ -+ hevc->num_tile_col = 1; -+ hevc->num_tile_row = 1; -+ hevc->m_tile[0][0].width = pic_width_cu; -+ hevc->m_tile[0][0].height = pic_height_cu; -+ hevc->m_tile[0][0].start_cu_x = 0; -+ hevc->m_tile[0][0].start_cu_y = 0; -+ hevc->m_tile[0][0].sao_vb_start_addr = hevc->workspace_paddr + SAO_VB_OFFSET; -+ hevc->m_tile[0][0].sao_abv_start_addr = hevc->workspace_paddr + SAO_ABV_OFFSET; -+ -+ hevc->tile_start_lcu_x = 0; -+ hevc->tile_start_lcu_y = 0; -+ hevc->tile_width_lcu = pic_width_cu; -+ hevc->tile_height_lcu = pic_height_cu; -+ -+ amvdec_write_dos(core, HEVC_sao_mem_unit, sao_mem_unit); -+ amvdec_write_dos(core, HEVC_SAO_ABV, hevc->workspace_paddr + SAO_ABV_OFFSET); -+ amvdec_write_dos(core, HEVC_sao_vb_size, sao_vb_size); -+ amvdec_write_dos(core, HEVC_SAO_VB, hevc->workspace_paddr + SAO_VB_OFFSET); -+} -+ -+static struct hevc_frame * codec_hevc_get_frame_by_poc(struct codec_hevc *hevc, u32 poc) -+{ -+ struct hevc_frame *tmp; -+ -+ list_for_each_entry(tmp, &hevc->ref_frames_list, list) { -+ if (tmp->poc == poc) -+ return tmp; -+ } -+ -+ return NULL; -+} -+ -+static struct hevc_frame * codec_hevc_prepare_new_frame(struct amvdec_session *sess) -+{ -+ struct vb2_v4l2_buffer *vbuf; -+ struct hevc_frame *new_frame = NULL; -+ struct codec_hevc *hevc = sess->priv; -+ union rpm_param *params = &hevc->rpm_param; -+ -+ new_frame = kzalloc(sizeof(*new_frame), GFP_KERNEL); -+ if (!new_frame) -+ return NULL; -+ -+ vbuf = v4l2_m2m_dst_buf_remove(sess->m2m_ctx); -+ if (!vbuf) { -+ dev_err(sess->core->dev, "No dst buffer available\n"); -+ return NULL; -+ } -+ -+ new_frame->vbuf = vbuf; -+ new_frame->referenced = 1; -+ new_frame->poc = hevc->curr_poc; -+ new_frame->cur_slice_type = params->p.slice_type; -+ new_frame->num_reorder_pic = params->p.sps_num_reorder_pics_0; -+ -+ list_add_tail(&new_frame->list, &hevc->ref_frames_list); -+ hevc->frames_num++; -+ -+ return new_frame; -+} -+ -+static void codec_hevc_set_sao(struct amvdec_session *sess, struct hevc_frame *frame) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_hevc *hevc = sess->priv; -+ union rpm_param *param = &hevc->rpm_param; -+ dma_addr_t buf_y_paddr; -+ dma_addr_t buf_u_v_paddr; -+ u32 misc_flag0 = param->p.misc_flag0; -+ u32 slice_deblocking_filter_disabled_flag; -+ u32 val, val_2; -+ -+ val = (amvdec_read_dos(core, HEVC_SAO_CTRL0) & ~0xf) | -+ ilog2(hevc->lcu_size); -+ amvdec_write_dos(core, HEVC_SAO_CTRL0, val); -+ -+ amvdec_write_dos(core, HEVC_SAO_PIC_SIZE, -+ hevc->width | (hevc->height << 16)); -+ amvdec_write_dos(core, HEVC_SAO_PIC_SIZE_LCU, -+ (hevc->lcu_x_num - 1) | (hevc->lcu_y_num - 1) << 16); -+ -+ if (codec_hevc_use_downsample(sess)) -+ buf_y_paddr = -+ hevc->fbc_buffer_paddr[frame->vbuf->vb2_buf.index]; -+ else -+ buf_y_paddr = -+ vb2_dma_contig_plane_dma_addr(&frame->vbuf->vb2_buf, 0); -+ -+ if (codec_hevc_use_fbc(sess)) { -+ val = amvdec_read_dos(core, HEVC_SAO_CTRL5) & ~0xff0200; -+ amvdec_write_dos(core, HEVC_SAO_CTRL5, val); -+ amvdec_write_dos(core, HEVC_CM_BODY_START_ADDR, buf_y_paddr); -+ } -+ -+ if (sess->pixfmt_cap == V4L2_PIX_FMT_NV12M) { -+ buf_y_paddr = -+ vb2_dma_contig_plane_dma_addr(&frame->vbuf->vb2_buf, 0); -+ buf_u_v_paddr = -+ vb2_dma_contig_plane_dma_addr(&frame->vbuf->vb2_buf, 1); -+ amvdec_write_dos(core, HEVC_SAO_Y_START_ADDR, buf_y_paddr); -+ amvdec_write_dos(core, HEVC_SAO_C_START_ADDR, buf_u_v_paddr); -+ amvdec_write_dos(core, HEVC_SAO_Y_WPTR, buf_y_paddr); -+ amvdec_write_dos(core, HEVC_SAO_C_WPTR, buf_u_v_paddr); -+ } -+ -+ amvdec_write_dos(core, HEVC_SAO_Y_LENGTH, amvdec_get_output_size(sess)); -+ amvdec_write_dos(core, HEVC_SAO_C_LENGTH, -+ (amvdec_get_output_size(sess) / 2)); -+ -+ if (frame->cur_slice_idx == 0) { -+ amvdec_write_dos(core, HEVC_DBLK_CFG2, hevc->width | (hevc->height << 16)); -+ -+ val = 0; -+ if ((misc_flag0 >> PCM_ENABLE_FLAG_BIT) & 0x1) -+ val |= ((misc_flag0 >> PCM_LOOP_FILTER_DISABLED_FLAG_BIT) & 0x1) << 3; -+ -+ val |= (param->p.pps_cb_qp_offset & 0x1f) << 4; -+ val |= (param->p.pps_cr_qp_offset & 0x1f) << 9; -+ val |= (hevc->lcu_size == 64) ? 0 : ((hevc->lcu_size == 32) ? 1 : 2); -+ amvdec_write_dos(core, HEVC_DBLK_CFG1, val); -+ } -+ -+ val = amvdec_read_dos(core, HEVC_SAO_CTRL1) & ~0x3ff3; -+ val |= 0xff0; /* Set endianness for 2-bytes swaps (nv12) */ -+ if (!codec_hevc_use_fbc(sess)) -+ val |= BIT(0); /* disable cm compression */ -+ else if (sess->pixfmt_cap == V4L2_PIX_FMT_AM21C) -+ val |= BIT(1); /* Disable double write */ -+ -+ amvdec_write_dos(core, HEVC_SAO_CTRL1, val); -+ -+ if (!codec_hevc_use_fbc(sess)) { -+ /* no downscale for NV12 */ -+ val = amvdec_read_dos(core, HEVC_SAO_CTRL5) & ~0xff0000; -+ amvdec_write_dos(core, HEVC_SAO_CTRL5, val); -+ } -+ -+ val = amvdec_read_dos(core, HEVCD_IPP_AXIIF_CONFIG) & ~0x30; -+ val |= 0xf; -+ amvdec_write_dos(core, HEVCD_IPP_AXIIF_CONFIG, val); -+ -+ val = 0; -+ val_2 = amvdec_read_dos(core, HEVC_SAO_CTRL0); -+ val_2 &= (~0x300); -+ -+ /* TODO: handle tiles here if enabled */ -+ slice_deblocking_filter_disabled_flag = (misc_flag0 >> -+ SLICE_DEBLOCKING_FILTER_DISABLED_FLAG_BIT) & 0x1; -+ if ((misc_flag0 & (1 << DEBLOCKING_FILTER_OVERRIDE_ENABLED_FLAG_BIT)) -+ && (misc_flag0 & (1 << DEBLOCKING_FILTER_OVERRIDE_FLAG_BIT))) { -+ val |= slice_deblocking_filter_disabled_flag << 2; -+ -+ if (!slice_deblocking_filter_disabled_flag) { -+ val |= (param->p.slice_beta_offset_div2 & 0xf) << 3; -+ val |= (param->p.slice_tc_offset_div2 & 0xf) << 7; -+ } -+ } else { -+ val |= -+ ((misc_flag0 >> -+ PPS_DEBLOCKING_FILTER_DISABLED_FLAG_BIT) & 0x1) << 2; -+ -+ if (((misc_flag0 >> PPS_DEBLOCKING_FILTER_DISABLED_FLAG_BIT) & -+ 0x1) == 0) { -+ val |= (param->p.pps_beta_offset_div2 & 0xf) << 3; -+ val |= (param->p.pps_tc_offset_div2 & 0xf) << 7; -+ } -+ } -+ if ((misc_flag0 & (1 << PPS_LOOP_FILTER_ACROSS_SLICES_ENABLED_FLAG_BIT)) -+ && ((misc_flag0 & (1 << SLICE_SAO_LUMA_FLAG_BIT)) -+ || (misc_flag0 & (1 << SLICE_SAO_CHROMA_FLAG_BIT)) -+ || (!slice_deblocking_filter_disabled_flag))) { -+ val |= -+ ((misc_flag0 >> -+ SLICE_LOOP_FILTER_ACROSS_SLICES_ENABLED_FLAG_BIT) -+ & 0x1) << 1; -+ val_2 |= -+ ((misc_flag0 >> -+ SLICE_LOOP_FILTER_ACROSS_SLICES_ENABLED_FLAG_BIT) -+ & 0x1) << 9; -+ } else { -+ val |= -+ ((misc_flag0 >> -+ PPS_LOOP_FILTER_ACROSS_SLICES_ENABLED_FLAG_BIT) -+ & 0x1) << 1; -+ val_2 |= -+ ((misc_flag0 >> -+ PPS_LOOP_FILTER_ACROSS_SLICES_ENABLED_FLAG_BIT) -+ & 0x1) << 9; -+ } -+ -+ amvdec_write_dos(core, HEVC_DBLK_CFG9, val); -+ amvdec_write_dos(core, HEVC_SAO_CTRL0, val_2); -+} -+ -+static dma_addr_t codec_hevc_get_frame_mv_paddr(struct codec_hevc *hevc, struct hevc_frame *frame) -+{ -+ return hevc->workspace_paddr + MPRED_MV_OFFSET + -+ (frame->vbuf->vb2_buf.index * MPRED_MV_BUF_SIZE); -+} -+ -+/* Update the necessary information for motion prediction with the current slice */ -+static void codec_hevc_set_mpred(struct amvdec_session *sess, struct hevc_frame *frame, struct hevc_frame *col_frame) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_hevc *hevc = sess->priv; -+ union rpm_param *param = &hevc->rpm_param; -+ u32 *ref_num = frame->ref_num; -+ u32 *ref_poc_l0 = frame->ref_poc_list[0][frame->cur_slice_idx]; -+ u32 *ref_poc_l1 = frame->ref_poc_list[1][frame->cur_slice_idx]; -+ u32 lcu_size_log2 = ilog2(hevc->lcu_size); -+ u32 mv_mem_unit = lcu_size_log2 == 6 ? 0x200 : lcu_size_log2 == 5 ? 0x80 : 0x20; -+ u32 slice_segment_address = param->p.slice_segment_address; -+ u32 max_num_merge_cand = 5 - param->p.five_minus_max_num_merge_cand; -+ u32 plevel = param->p.log2_parallel_merge_level; -+ u32 col_from_l0_flag = param->p.collocated_from_l0_flag; -+ u32 tmvp_flag = param->p.slice_temporal_mvp_enable_flag; -+ u32 is_next_slice_segment = param->p.dependent_slice_segment_flag ? 1 : 0; -+ u32 slice_type = param->p.slice_type; -+ dma_addr_t col_mv_rd_start_addr, col_mv_rd_ptr, col_mv_rd_end_addr; -+ dma_addr_t mpred_mv_wr_ptr; -+ u32 mv_rd_en = 1; -+ u32 val; -+ int i; -+ -+ val = amvdec_read_dos(core, HEVC_MPRED_CURR_LCU); -+ -+ col_mv_rd_start_addr = codec_hevc_get_frame_mv_paddr(hevc, col_frame); -+ mpred_mv_wr_ptr = codec_hevc_get_frame_mv_paddr(hevc, frame) + (hevc->slice_addr * mv_mem_unit); -+ col_mv_rd_ptr = col_mv_rd_start_addr + (hevc->slice_addr * mv_mem_unit); -+ col_mv_rd_end_addr = col_mv_rd_start_addr + ((hevc->lcu_x_num * hevc->lcu_y_num) * mv_mem_unit); -+ -+ amvdec_write_dos(core, HEVC_MPRED_MV_WR_START_ADDR, codec_hevc_get_frame_mv_paddr(hevc, frame)); -+ amvdec_write_dos(core, HEVC_MPRED_MV_RD_START_ADDR, col_mv_rd_start_addr); -+ -+ val = ((hevc->lcu_x_num - hevc->tile_width_lcu) * mv_mem_unit); -+ amvdec_write_dos(core, HEVC_MPRED_MV_WR_ROW_JUMP, val); -+ amvdec_write_dos(core, HEVC_MPRED_MV_RD_ROW_JUMP, val); -+ -+ if (slice_type == I_SLICE) -+ mv_rd_en = 0; -+ -+ val = slice_type | -+ BIT(3) | /* new tile */ -+ is_next_slice_segment << 4 | -+ tmvp_flag << 5 | -+ hevc->ldc_flag << 6 | -+ col_from_l0_flag << 7 | -+ BIT(9) | -+ BIT(10) | -+ mv_rd_en << 11 | -+ BIT(13) | -+ lcu_size_log2 << 16 | -+ 3 << 20 | plevel << 24; -+ -+ if (slice_segment_address == 0) -+ val |= BIT(2); /* new frame */ -+ -+ amvdec_write_dos(core, HEVC_MPRED_CTRL0, val); -+ -+ val = max_num_merge_cand | 2 << 4 | 3 << 8 | 5 << 12 | 36 << 16; -+ amvdec_write_dos(core, HEVC_MPRED_CTRL1, val); -+ -+ amvdec_write_dos(core, HEVC_MPRED_PIC_SIZE, hevc->width | (hevc->height << 16)); -+ -+ val = ((hevc->lcu_x_num - 1) | (hevc->lcu_y_num - 1) << 16); -+ amvdec_write_dos(core, HEVC_MPRED_PIC_SIZE_LCU, val); -+ val = (hevc->tile_start_lcu_x | hevc->tile_start_lcu_y << 16); -+ amvdec_write_dos(core, HEVC_MPRED_TILE_START, val); -+ val = (hevc->tile_width_lcu | hevc->tile_height_lcu << 16); -+ amvdec_write_dos(core, HEVC_MPRED_TILE_SIZE_LCU, val); -+ -+ amvdec_write_dos(core, HEVC_MPRED_REF_NUM, (ref_num[1] << 8) | ref_num[0]); -+ amvdec_write_dos(core, HEVC_MPRED_REF_EN_L0, (1 << ref_num[0]) - 1); -+ amvdec_write_dos(core, HEVC_MPRED_REF_EN_L1, (1 << ref_num[1]) - 1); -+ -+ amvdec_write_dos(core, HEVC_MPRED_CUR_POC, hevc->curr_poc); -+ amvdec_write_dos(core, HEVC_MPRED_COL_POC, hevc->col_poc); -+ -+ for (i = 0; i < MAX_REF_ACTIVE; ++i) { -+ amvdec_write_dos(core, HEVC_MPRED_L0_REF00_POC + i * 4, ref_poc_l0[i]); -+ amvdec_write_dos(core, HEVC_MPRED_L1_REF00_POC + i * 4, ref_poc_l1[i]); -+ } -+ -+ if (slice_segment_address == 0) { -+ amvdec_write_dos(core, HEVC_MPRED_ABV_START_ADDR, -+ hevc->workspace_paddr + MPRED_ABV_OFFSET); -+ amvdec_write_dos(core, HEVC_MPRED_MV_WPTR, mpred_mv_wr_ptr); -+ amvdec_write_dos(core, HEVC_MPRED_MV_RPTR, col_mv_rd_start_addr); -+ } else { -+ amvdec_write_dos(core, HEVC_MPRED_MV_RPTR, col_mv_rd_ptr); -+ } -+ -+ amvdec_write_dos(core, HEVC_MPRED_MV_RD_END_ADDR, col_mv_rd_end_addr); -+} -+ -+/* motion compensation reference cache controller */ -+static void codec_hevc_set_mcrcc(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_hevc *hevc = sess->priv; -+ u32 val, val_2; -+ int l0_cnt = 0; -+ int l1_cnt = 0x7fff; -+ -+ if (!codec_hevc_use_fbc(sess)) { -+ l0_cnt = hevc->cur_frame->ref_num[0]; -+ l1_cnt = hevc->cur_frame->ref_num[1]; -+ } -+ -+ /* reset mcrcc */ -+ amvdec_write_dos(core, HEVCD_MCRCC_CTL1, 0x02); -+ -+ if (hevc->cur_frame->cur_slice_type == I_SLICE) { -+ /* remove reset -- disables clock */ -+ amvdec_write_dos(core, HEVCD_MCRCC_CTL1, 0); -+ return; -+ } -+ -+ if (hevc->cur_frame->cur_slice_type == P_SLICE) { -+ amvdec_write_dos(core, HEVCD_MPP_ANC_CANVAS_ACCCONFIG_ADDR, BIT(1)); -+ val = amvdec_read_dos(core, HEVCD_MPP_ANC_CANVAS_DATA_ADDR); -+ val &= 0xffff; -+ val |= (val << 16); -+ amvdec_write_dos(core, HEVCD_MCRCC_CTL2, val); -+ -+ if (l0_cnt == 1) { -+ amvdec_write_dos(core, HEVCD_MCRCC_CTL3, val); -+ } else { -+ val = amvdec_read_dos(core, HEVCD_MPP_ANC_CANVAS_DATA_ADDR); -+ val &= 0xffff; -+ val |= (val << 16); -+ amvdec_write_dos(core, HEVCD_MCRCC_CTL3, val); -+ } -+ } else { /* B_SLICE */ -+ amvdec_write_dos(core, HEVCD_MPP_ANC_CANVAS_ACCCONFIG_ADDR, 0); -+ val = amvdec_read_dos(core, HEVCD_MPP_ANC_CANVAS_DATA_ADDR); -+ val &= 0xffff; -+ val |= (val << 16); -+ amvdec_write_dos(core, HEVCD_MCRCC_CTL2, val); -+ -+ amvdec_write_dos(core, HEVCD_MPP_ANC_CANVAS_ACCCONFIG_ADDR, (16 << 8) | BIT(1)); -+ val_2 = amvdec_read_dos(core, HEVCD_MPP_ANC_CANVAS_DATA_ADDR); -+ val_2 &= 0xffff; -+ val_2 |= (val_2 << 16); -+ if (val == val_2 && l1_cnt > 1) { -+ val_2 = amvdec_read_dos(core, HEVCD_MPP_ANC_CANVAS_DATA_ADDR); -+ val_2 &= 0xffff; -+ val_2 |= (val_2 << 16); -+ } -+ amvdec_write_dos(core, HEVCD_MCRCC_CTL3, val); -+ } -+ -+ /* enable mcrcc progressive-mode */ -+ amvdec_write_dos(core, HEVCD_MCRCC_CTL1, 0xff0); -+} -+ -+static void codec_hevc_set_ref_list(struct amvdec_session *sess, -+ u32 ref_num, u32 *ref_poc_list) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ struct hevc_frame *ref_frame; -+ struct amvdec_core *core = sess->core; -+ int i; -+ u32 buf_id_y; -+ u32 buf_id_uv; -+ -+ for (i = 0; i < ref_num; i++) { -+ ref_frame = codec_hevc_get_frame_by_poc(hevc, ref_poc_list[i]); -+ -+ if (!ref_frame) { -+ dev_warn(core->dev, "Couldn't find ref. frame %u\n", -+ ref_poc_list[i]); -+ continue; -+ } -+ -+ if (codec_hevc_use_fbc(sess)) { -+ buf_id_y = buf_id_uv = ref_frame->vbuf->vb2_buf.index; -+ } else { -+ buf_id_y = ref_frame->vbuf->vb2_buf.index * 2; -+ buf_id_uv = buf_id_y + 1; -+ } -+ -+ writel_relaxed((buf_id_uv << 16) | -+ (buf_id_uv << 8) | -+ buf_id_y, -+ core->dos_base + HEVCD_MPP_ANC_CANVAS_DATA_ADDR); -+ } -+} -+ -+static void codec_hevc_set_mc(struct amvdec_session *sess, struct hevc_frame *frame) -+{ -+ struct amvdec_core *core = sess->core; -+ -+ if (frame->cur_slice_type == I_SLICE) -+ return; -+ -+ amvdec_write_dos(core, HEVCD_MPP_ANC_CANVAS_ACCCONFIG_ADDR, 1); -+ codec_hevc_set_ref_list(sess, frame->ref_num[0], -+ frame->ref_poc_list[0][frame->cur_slice_idx]); -+ -+ if (frame->cur_slice_type == P_SLICE) -+ return; -+ -+ amvdec_write_dos(core, HEVCD_MPP_ANC_CANVAS_ACCCONFIG_ADDR, (16 << 8) | 1); -+ codec_hevc_set_ref_list(sess, frame->ref_num[1], -+ frame->ref_poc_list[1][frame->cur_slice_idx]); -+} -+ -+static void codec_hevc_update_col_frame(struct codec_hevc *hevc) -+{ -+ struct hevc_frame *cur_frame = hevc->cur_frame; -+ union rpm_param *param = &hevc->rpm_param; -+ u32 list_no = 0; -+ u32 col_ref = param->p.collocated_ref_idx; -+ u32 col_from_l0 = param->p.collocated_from_l0_flag; -+ -+ if (cur_frame->cur_slice_type == B_SLICE) -+ list_no = 1 - col_from_l0; -+ -+ if (col_ref >= cur_frame->ref_num[list_no]) -+ hevc->col_poc = INVALID_POC; -+ else -+ hevc->col_poc = cur_frame->ref_poc_list[list_no][cur_frame->cur_slice_idx][col_ref]; -+ -+ if (cur_frame->cur_slice_type == I_SLICE) -+ goto end; -+ -+ if (hevc->col_poc != INVALID_POC) -+ hevc->col_frame = codec_hevc_get_frame_by_poc(hevc, hevc->col_poc); -+ else -+ hevc->col_frame = hevc->cur_frame; -+ -+end: -+ if (!hevc->col_frame) -+ hevc->col_frame = hevc->cur_frame; -+} -+ -+static void codec_hevc_update_pocs(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ union rpm_param *param = &hevc->rpm_param; -+ u32 nal_unit_type = param->p.m_nalUnitType; -+ u32 temporal_id = param->p.m_temporalId & 0x7; -+ int max_poc_lsb = 1 << (param->p.log2_max_pic_order_cnt_lsb_minus4 + 4); -+ int prev_poc_lsb; -+ int prev_poc_msb; -+ int poc_msb; -+ int poc_lsb = param->p.POClsb; -+ -+ if (nal_unit_type == NAL_UNIT_CODED_SLICE_IDR || -+ nal_unit_type == NAL_UNIT_CODED_SLICE_IDR_N_LP) { -+ hevc->curr_poc = 0; -+ if ((temporal_id - 1) == 0) -+ hevc->iPrevTid0POC = hevc->curr_poc; -+ -+ return; -+ } -+ -+ prev_poc_lsb = hevc->iPrevTid0POC % max_poc_lsb; -+ prev_poc_msb = hevc->iPrevTid0POC - prev_poc_lsb; -+ -+ if ((poc_lsb < prev_poc_lsb) && ((prev_poc_lsb - poc_lsb) >= (max_poc_lsb / 2))) -+ poc_msb = prev_poc_msb + max_poc_lsb; -+ else if ((poc_lsb > prev_poc_lsb) && ((poc_lsb - prev_poc_lsb) > (max_poc_lsb / 2))) -+ poc_msb = prev_poc_msb - max_poc_lsb; -+ else -+ poc_msb = prev_poc_msb; -+ -+ if (nal_unit_type == NAL_UNIT_CODED_SLICE_BLA || -+ nal_unit_type == NAL_UNIT_CODED_SLICE_BLANT || -+ nal_unit_type == NAL_UNIT_CODED_SLICE_BLA_N_LP) -+ poc_msb = 0; -+ -+ hevc->curr_poc = (poc_msb + poc_lsb); -+ if ((temporal_id - 1) == 0) -+ hevc->iPrevTid0POC = hevc->curr_poc; -+} -+ -+static void codec_hevc_process_segment_header(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ union rpm_param *param = &hevc->rpm_param; -+ -+ if (param->p.first_slice_segment_in_pic_flag == 0) { -+ hevc->slice_segment_addr = param->p.slice_segment_address; -+ if (!param->p.dependent_slice_segment_flag) -+ hevc->slice_addr = hevc->slice_segment_addr; -+ } else { -+ hevc->slice_segment_addr = 0; -+ hevc->slice_addr = 0; -+ } -+ -+ codec_hevc_update_pocs(sess); -+} -+ -+static int codec_hevc_process_segment(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ struct amvdec_core *core = sess->core; -+ union rpm_param *param = &hevc->rpm_param; -+ u32 slice_segment_address = param->p.slice_segment_address; -+ -+ /* First slice: new frame */ -+ if (slice_segment_address == 0) { -+ codec_hevc_update_referenced(hevc); -+ codec_hevc_output_frames(sess); -+ -+ hevc->cur_frame = codec_hevc_prepare_new_frame(sess); -+ if (!hevc->cur_frame) -+ return -1; -+ -+ codec_hevc_update_tiles(sess); -+ } else { -+ hevc->cur_frame->cur_slice_idx++; -+ } -+ -+ codec_hevc_update_frame_refs(sess, hevc->cur_frame); -+ codec_hevc_update_col_frame(hevc); -+ codec_hevc_update_ldc_flag(hevc); -+ codec_hevc_set_mc(sess, hevc->cur_frame); -+ codec_hevc_set_mcrcc(sess); -+ codec_hevc_set_mpred(sess, hevc->cur_frame, hevc->col_frame); -+ codec_hevc_set_sao(sess, hevc->cur_frame); -+ -+ amvdec_write_dos(core, HEVC_WAIT_FLAG, amvdec_read_dos(core, HEVC_WAIT_FLAG) | 2); -+ amvdec_write_dos(core, HEVC_DEC_STATUS_REG, HEVC_CODED_SLICE_SEGMENT_DAT); -+ -+ /* Interrupt the firmware's processor */ -+ amvdec_write_dos(core, HEVC_MCPU_INTR_REQ, AMRISC_MAIN_REQ); -+ -+ return 0; -+} -+ -+static int codec_hevc_process_rpm(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_hevc *hevc = sess->priv; -+ union rpm_param *rpm_param = &hevc->rpm_param; -+ u32 lcu_x_num_div, lcu_y_num_div; -+ -+ if (rpm_param->p.bit_depth) -+ hevc->is_10bit = 1; -+ -+ hevc->width = rpm_param->p.pic_width_in_luma_samples; -+ hevc->height = rpm_param->p.pic_height_in_luma_samples; -+ -+ /*if (hevc->width != sess->width || -+ hevc->height != sess->height) { -+ dev_err(sess->core->dev_dec, -+ "Size mismatch: bitstream %ux%u ; driver %ux%u\n", -+ hevc->width, hevc->height, -+ sess->width, sess->height); -+ return -EINVAL; -+ }*/ -+ -+ hevc->lcu_size = 1 << (rpm_param->p.log2_min_coding_block_size_minus3 + -+ 3 + rpm_param->p.log2_diff_max_min_coding_block_size); -+ -+ lcu_x_num_div = (hevc->width / hevc->lcu_size); -+ lcu_y_num_div = (hevc->height / hevc->lcu_size); -+ hevc->lcu_x_num = ((hevc->width % hevc->lcu_size) == 0) ? lcu_x_num_div : lcu_x_num_div + 1; -+ hevc->lcu_y_num = ((hevc->height % hevc->lcu_size) == 0) ? lcu_y_num_div : lcu_y_num_div + 1; -+ hevc->lcu_total = hevc->lcu_x_num * hevc->lcu_y_num; -+ -+ dev_dbg(core->dev, "lcu_size = %u ; lcu_x_num = %u; lcu_y_num = %u", -+ hevc->lcu_size, hevc->lcu_x_num, hevc->lcu_y_num); -+ -+ return 0; -+} -+ -+/* The RPM section within the workspace contains -+ * many information regarding the parsed bitstream -+ */ -+static void codec_hevc_fetch_rpm(struct amvdec_session *sess) -+{ -+ struct codec_hevc *hevc = sess->priv; -+ u16 *rpm_vaddr = hevc->workspace_vaddr + RPM_OFFSET; -+ int i, j; -+ -+ for (i = 0; i < RPM_SIZE; i += 4) -+ for (j = 0; j < 4; j++) -+ hevc->rpm_param.l.data[i + j] = rpm_vaddr[i + 3 - j]; -+} -+ -+static irqreturn_t codec_hevc_threaded_isr(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_hevc *hevc; -+ -+ hevc = sess->priv; -+ if (!hevc) -+ return IRQ_HANDLED; -+ -+ mutex_lock(&hevc->lock); -+ if (hevc->dec_status != HEVC_SLICE_SEGMENT_DONE) { -+ dev_err(core->dev_dec, "Unrecognized dec_status: %08X\n", -+ hevc->dec_status); -+ amvdec_abort(sess); -+ goto unlock; -+ } -+ -+ sess->keyframe_found = 1; -+ codec_hevc_fetch_rpm(sess); -+ if (codec_hevc_process_rpm(sess)) { -+ amvdec_abort(sess); -+ goto unlock; -+ } -+ -+ if (!hevc->is_buflist_init) { -+ if (codec_hevc_setup_buffers(sess)) { -+ amvdec_abort(sess); -+ goto unlock; -+ } -+ -+ codec_hevc_setup_decode_head(sess); -+ hevc->is_buflist_init = 1; -+ } -+ -+ codec_hevc_process_segment_header(sess); -+ if (codec_hevc_process_segment(sess)) -+ amvdec_abort(sess); -+ -+unlock: -+ mutex_unlock(&hevc->lock); -+ return IRQ_HANDLED; -+} -+ -+static irqreturn_t codec_hevc_isr(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct codec_hevc *hevc = sess->priv; -+ -+ hevc->dec_status = amvdec_read_dos(core, HEVC_DEC_STATUS_REG); -+ -+ return IRQ_WAKE_THREAD; -+} -+ -+struct amvdec_codec_ops codec_hevc_ops = { -+ .start = codec_hevc_start, -+ .stop = codec_hevc_stop, -+ .isr = codec_hevc_isr, -+ .threaded_isr = codec_hevc_threaded_isr, -+ .num_pending_bufs = codec_hevc_num_pending_bufs, -+ .drain = codec_hevc_flush_output, -+}; -diff --git a/drivers/media/platform/meson/vdec/codec_hevc.h b/drivers/media/platform/meson/vdec/codec_hevc.h -new file mode 100644 -index 0000000000000..5017e874e3ddc ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/codec_hevc.h -@@ -0,0 +1,13 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2018 Maxime Jourdan -+ */ -+ -+#ifndef __MESON_VDEC_CODEC_HEVC_H_ -+#define __MESON_VDEC_CODEC_HEVC_H_ -+ -+#include "vdec.h" -+ -+extern struct amvdec_codec_ops codec_hevc_ops; -+ -+#endif -\ No newline at end of file -diff --git a/drivers/media/platform/meson/vdec/hevc_regs.h b/drivers/media/platform/meson/vdec/hevc_regs.h -new file mode 100644 -index 0000000000000..ae9b38e463f7e ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/hevc_regs.h -@@ -0,0 +1,742 @@ -+/* SPDX-License-Identifier: GPL-2.0+ */ -+/* -+ * Copyright (C) 2015 Amlogic, Inc. All rights reserved. -+ */ -+ -+#ifndef HEVC_REGS_HEADERS__ -+#define HEVC_REGS_HEADERS__ -+/*add from M8M2*/ -+#define HEVC_ASSIST_AFIFO_CTRL (0x3001 * 4) -+#define HEVC_ASSIST_AFIFO_CTRL1 (0x3002 * 4) -+#define HEVC_ASSIST_GCLK_EN (0x3003 * 4) -+#define HEVC_ASSIST_SW_RESET (0x3004 * 4) -+#define HEVC_ASSIST_AMR1_INT0 (0x3025 * 4) -+#define HEVC_ASSIST_AMR1_INT1 (0x3026 * 4) -+#define HEVC_ASSIST_AMR1_INT2 (0x3027 * 4) -+#define HEVC_ASSIST_AMR1_INT3 (0x3028 * 4) -+#define HEVC_ASSIST_AMR1_INT4 (0x3029 * 4) -+#define HEVC_ASSIST_AMR1_INT5 (0x302a * 4) -+#define HEVC_ASSIST_AMR1_INT6 (0x302b * 4) -+#define HEVC_ASSIST_AMR1_INT7 (0x302c * 4) -+#define HEVC_ASSIST_AMR1_INT8 (0x302d * 4) -+#define HEVC_ASSIST_AMR1_INT9 (0x302e * 4) -+#define HEVC_ASSIST_AMR1_INTA (0x302f * 4) -+#define HEVC_ASSIST_AMR1_INTB (0x3030 * 4) -+#define HEVC_ASSIST_AMR1_INTC (0x3031 * 4) -+#define HEVC_ASSIST_AMR1_INTD (0x3032 * 4) -+#define HEVC_ASSIST_AMR1_INTE (0x3033 * 4) -+#define HEVC_ASSIST_AMR1_INTF (0x3034 * 4) -+#define HEVC_ASSIST_AMR2_INT0 (0x3035 * 4) -+#define HEVC_ASSIST_AMR2_INT1 (0x3036 * 4) -+#define HEVC_ASSIST_AMR2_INT2 (0x3037 * 4) -+#define HEVC_ASSIST_AMR2_INT3 (0x3038 * 4) -+#define HEVC_ASSIST_AMR2_INT4 (0x3039 * 4) -+#define HEVC_ASSIST_AMR2_INT5 (0x303a * 4) -+#define HEVC_ASSIST_AMR2_INT6 (0x303b * 4) -+#define HEVC_ASSIST_AMR2_INT7 (0x303c * 4) -+#define HEVC_ASSIST_AMR2_INT8 (0x303d * 4) -+#define HEVC_ASSIST_AMR2_INT9 (0x303e * 4) -+#define HEVC_ASSIST_AMR2_INTA (0x303f * 4) -+#define HEVC_ASSIST_AMR2_INTB (0x3040 * 4) -+#define HEVC_ASSIST_AMR2_INTC (0x3041 * 4) -+#define HEVC_ASSIST_AMR2_INTD (0x3042 * 4) -+#define HEVC_ASSIST_AMR2_INTE (0x3043 * 4) -+#define HEVC_ASSIST_AMR2_INTF (0x3044 * 4) -+#define HEVC_ASSIST_MBX_SSEL (0x3045 * 4) -+#define HEVC_ASSIST_TIMER0_LO (0x3060 * 4) -+#define HEVC_ASSIST_TIMER0_HI (0x3061 * 4) -+#define HEVC_ASSIST_TIMER1_LO (0x3062 * 4) -+#define HEVC_ASSIST_TIMER1_HI (0x3063 * 4) -+#define HEVC_ASSIST_DMA_INT (0x3064 * 4) -+#define HEVC_ASSIST_DMA_INT_MSK (0x3065 * 4) -+#define HEVC_ASSIST_DMA_INT2 (0x3066 * 4) -+#define HEVC_ASSIST_DMA_INT_MSK2 (0x3067 * 4) -+#define HEVC_ASSIST_MBOX0_IRQ_REG (0x3070 * 4) -+#define HEVC_ASSIST_MBOX0_CLR_REG (0x3071 * 4) -+#define HEVC_ASSIST_MBOX0_MASK (0x3072 * 4) -+#define HEVC_ASSIST_MBOX0_FIQ_SEL (0x3073 * 4) -+#define HEVC_ASSIST_MBOX1_IRQ_REG (0x3074 * 4) -+#define HEVC_ASSIST_MBOX1_CLR_REG (0x3075 * 4) -+#define HEVC_ASSIST_MBOX1_MASK (0x3076 * 4) -+#define HEVC_ASSIST_MBOX1_FIQ_SEL (0x3077 * 4) -+#define HEVC_ASSIST_MBOX2_IRQ_REG (0x3078 * 4) -+#define HEVC_ASSIST_MBOX2_CLR_REG (0x3079 * 4) -+#define HEVC_ASSIST_MBOX2_MASK (0x307a * 4) -+#define HEVC_ASSIST_MBOX2_FIQ_SEL (0x307b * 4) -+#define HEVC_ASSIST_AXI_CTRL (0x307c * 4) -+#define HEVC_ASSIST_AXI_STATUS (0x307d * 4) -+#define HEVC_ASSIST_SCRATCH_0 (0x30c0 * 4) -+#define HEVC_ASSIST_SCRATCH_1 (0x30c1 * 4) -+#define HEVC_ASSIST_SCRATCH_2 (0x30c2 * 4) -+#define HEVC_ASSIST_SCRATCH_3 (0x30c3 * 4) -+#define HEVC_ASSIST_SCRATCH_4 (0x30c4 * 4) -+#define HEVC_ASSIST_SCRATCH_5 (0x30c5 * 4) -+#define HEVC_ASSIST_SCRATCH_6 (0x30c6 * 4) -+#define HEVC_ASSIST_SCRATCH_7 (0x30c7 * 4) -+#define HEVC_ASSIST_SCRATCH_8 (0x30c8 * 4) -+#define HEVC_ASSIST_SCRATCH_9 (0x30c9 * 4) -+#define HEVC_ASSIST_SCRATCH_A (0x30ca * 4) -+#define HEVC_ASSIST_SCRATCH_B (0x30cb * 4) -+#define HEVC_ASSIST_SCRATCH_C (0x30cc * 4) -+#define HEVC_ASSIST_SCRATCH_D (0x30cd * 4) -+#define HEVC_ASSIST_SCRATCH_E (0x30ce * 4) -+#define HEVC_ASSIST_SCRATCH_F (0x30cf * 4) -+#define HEVC_ASSIST_SCRATCH_G (0x30d0 * 4) -+#define HEVC_ASSIST_SCRATCH_H (0x30d1 * 4) -+#define HEVC_ASSIST_SCRATCH_I (0x30d2 * 4) -+#define HEVC_ASSIST_SCRATCH_J (0x30d3 * 4) -+#define HEVC_ASSIST_SCRATCH_K (0x30d4 * 4) -+#define HEVC_ASSIST_SCRATCH_L (0x30d5 * 4) -+#define HEVC_ASSIST_SCRATCH_M (0x30d6 * 4) -+#define HEVC_ASSIST_SCRATCH_N (0x30d7 * 4) -+#define HEVC_PARSER_VERSION (0x3100 * 4) -+#define HEVC_STREAM_CONTROL (0x3101 * 4) -+#define HEVC_STREAM_START_ADDR (0x3102 * 4) -+#define HEVC_STREAM_END_ADDR (0x3103 * 4) -+#define HEVC_STREAM_WR_PTR (0x3104 * 4) -+#define HEVC_STREAM_RD_PTR (0x3105 * 4) -+#define HEVC_STREAM_LEVEL (0x3106 * 4) -+#define HEVC_STREAM_FIFO_CTL (0x3107 * 4) -+#define HEVC_SHIFT_CONTROL (0x3108 * 4) -+#define HEVC_SHIFT_STARTCODE (0x3109 * 4) -+#define HEVC_SHIFT_EMULATECODE (0x310a * 4) -+#define HEVC_SHIFT_STATUS (0x310b * 4) -+#define HEVC_SHIFTED_DATA (0x310c * 4) -+#define HEVC_SHIFT_BYTE_COUNT (0x310d * 4) -+#define HEVC_SHIFT_COMMAND (0x310e * 4) -+#define HEVC_ELEMENT_RESULT (0x310f * 4) -+#define HEVC_CABAC_CONTROL (0x3110 * 4) -+#define HEVC_PARSER_SLICE_INFO (0x3111 * 4) -+#define HEVC_PARSER_CMD_WRITE (0x3112 * 4) -+#define HEVC_PARSER_CORE_CONTROL (0x3113 * 4) -+#define HEVC_PARSER_CMD_FETCH (0x3114 * 4) -+#define HEVC_PARSER_CMD_STATUS (0x3115 * 4) -+#define HEVC_PARSER_LCU_INFO (0x3116 * 4) -+#define HEVC_PARSER_HEADER_INFO (0x3117 * 4) -+#define HEVC_PARSER_RESULT_0 (0x3118 * 4) -+#define HEVC_PARSER_RESULT_1 (0x3119 * 4) -+#define HEVC_PARSER_RESULT_2 (0x311a * 4) -+#define HEVC_PARSER_RESULT_3 (0x311b * 4) -+#define HEVC_CABAC_TOP_INFO (0x311c * 4) -+#define HEVC_CABAC_TOP_INFO_2 (0x311d * 4) -+#define HEVC_CABAC_LEFT_INFO (0x311e * 4) -+#define HEVC_CABAC_LEFT_INFO_2 (0x311f * 4) -+#define HEVC_PARSER_INT_CONTROL (0x3120 * 4) -+#define HEVC_PARSER_INT_STATUS (0x3121 * 4) -+#define HEVC_PARSER_IF_CONTROL (0x3122 * 4) -+#define HEVC_PARSER_PICTURE_SIZE (0x3123 * 4) -+#define HEVC_PARSER_LCU_START (0x3124 * 4) -+#define HEVC_PARSER_HEADER_INFO2 (0x3125 * 4) -+#define HEVC_PARSER_QUANT_READ (0x3126 * 4) -+#define HEVC_PARSER_RESERVED_27 (0x3127 * 4) -+#define HEVC_PARSER_CMD_SKIP_0 (0x3128 * 4) -+#define HEVC_PARSER_CMD_SKIP_1 (0x3129 * 4) -+#define HEVC_PARSER_CMD_SKIP_2 (0x312a * 4) -+#define HEVC_PARSER_MANUAL_CMD (0x312b * 4) -+#define HEVC_PARSER_MEM_RD_ADDR (0x312c * 4) -+#define HEVC_PARSER_MEM_WR_ADDR (0x312d * 4) -+#define HEVC_PARSER_MEM_RW_DATA (0x312e * 4) -+#define HEVC_SAO_IF_STATUS (0x3130 * 4) -+#define HEVC_SAO_IF_DATA_Y (0x3131 * 4) -+#define HEVC_SAO_IF_DATA_U (0x3132 * 4) -+#define HEVC_SAO_IF_DATA_V (0x3133 * 4) -+#define HEVC_STREAM_SWAP_ADDR (0x3134 * 4) -+#define HEVC_STREAM_SWAP_CTRL (0x3135 * 4) -+#define HEVC_IQIT_IF_WAIT_CNT (0x3136 * 4) -+#define HEVC_MPRED_IF_WAIT_CNT (0x3137 * 4) -+#define HEVC_SAO_IF_WAIT_CNT (0x3138 * 4) -+#define HEVC_PARSER_DEBUG_IDX (0x313e * 4) -+#define HEVC_PARSER_DEBUG_DAT (0x313f * 4) -+#define HEVC_MPRED_VERSION (0x3200 * 4) -+#define HEVC_MPRED_CTRL0 (0x3201 * 4) -+#define HEVC_MPRED_CTRL1 (0x3202 * 4) -+#define HEVC_MPRED_INT_EN (0x3203 * 4) -+#define HEVC_MPRED_INT_STATUS (0x3204 * 4) -+#define HEVC_MPRED_PIC_SIZE (0x3205 * 4) -+#define HEVC_MPRED_PIC_SIZE_LCU (0x3206 * 4) -+#define HEVC_MPRED_TILE_START (0x3207 * 4) -+#define HEVC_MPRED_TILE_SIZE_LCU (0x3208 * 4) -+#define HEVC_MPRED_REF_NUM (0x3209 * 4) -+#define HEVC_MPRED_LT_REF (0x320a * 4) -+#define HEVC_MPRED_LT_COLREF (0x320b * 4) -+#define HEVC_MPRED_REF_EN_L0 (0x320c * 4) -+#define HEVC_MPRED_REF_EN_L1 (0x320d * 4) -+#define HEVC_MPRED_COLREF_EN_L0 (0x320e * 4) -+#define HEVC_MPRED_COLREF_EN_L1 (0x320f * 4) -+#define HEVC_MPRED_AXI_WCTRL (0x3210 * 4) -+#define HEVC_MPRED_AXI_RCTRL (0x3211 * 4) -+#define HEVC_MPRED_ABV_START_ADDR (0x3212 * 4) -+#define HEVC_MPRED_MV_WR_START_ADDR (0x3213 * 4) -+#define HEVC_MPRED_MV_RD_START_ADDR (0x3214 * 4) -+#define HEVC_MPRED_MV_WPTR (0x3215 * 4) -+#define HEVC_MPRED_MV_RPTR (0x3216 * 4) -+#define HEVC_MPRED_MV_WR_ROW_JUMP (0x3217 * 4) -+#define HEVC_MPRED_MV_RD_ROW_JUMP (0x3218 * 4) -+#define HEVC_MPRED_CURR_LCU (0x3219 * 4) -+#define HEVC_MPRED_ABV_WPTR (0x321a * 4) -+#define HEVC_MPRED_ABV_RPTR (0x321b * 4) -+#define HEVC_MPRED_CTRL2 (0x321c * 4) -+#define HEVC_MPRED_CTRL3 (0x321d * 4) -+#define HEVC_MPRED_MV_WLCUY (0x321e * 4) -+#define HEVC_MPRED_MV_RLCUY (0x321f * 4) -+#define HEVC_MPRED_L0_REF00_POC (0x3220 * 4) -+#define HEVC_MPRED_L0_REF01_POC (0x3221 * 4) -+#define HEVC_MPRED_L0_REF02_POC (0x3222 * 4) -+#define HEVC_MPRED_L0_REF03_POC (0x3223 * 4) -+#define HEVC_MPRED_L0_REF04_POC (0x3224 * 4) -+#define HEVC_MPRED_L0_REF05_POC (0x3225 * 4) -+#define HEVC_MPRED_L0_REF06_POC (0x3226 * 4) -+#define HEVC_MPRED_L0_REF07_POC (0x3227 * 4) -+#define HEVC_MPRED_L0_REF08_POC (0x3228 * 4) -+#define HEVC_MPRED_L0_REF09_POC (0x3229 * 4) -+#define HEVC_MPRED_L0_REF10_POC (0x322a * 4) -+#define HEVC_MPRED_L0_REF11_POC (0x322b * 4) -+#define HEVC_MPRED_L0_REF12_POC (0x322c * 4) -+#define HEVC_MPRED_L0_REF13_POC (0x322d * 4) -+#define HEVC_MPRED_L0_REF14_POC (0x322e * 4) -+#define HEVC_MPRED_L0_REF15_POC (0x322f * 4) -+#define HEVC_MPRED_L1_REF00_POC (0x3230 * 4) -+#define HEVC_MPRED_L1_REF01_POC (0x3231 * 4) -+#define HEVC_MPRED_L1_REF02_POC (0x3232 * 4) -+#define HEVC_MPRED_L1_REF03_POC (0x3233 * 4) -+#define HEVC_MPRED_L1_REF04_POC (0x3234 * 4) -+#define HEVC_MPRED_L1_REF05_POC (0x3235 * 4) -+#define HEVC_MPRED_L1_REF06_POC (0x3236 * 4) -+#define HEVC_MPRED_L1_REF07_POC (0x3237 * 4) -+#define HEVC_MPRED_L1_REF08_POC (0x3238 * 4) -+#define HEVC_MPRED_L1_REF09_POC (0x3239 * 4) -+#define HEVC_MPRED_L1_REF10_POC (0x323a * 4) -+#define HEVC_MPRED_L1_REF11_POC (0x323b * 4) -+#define HEVC_MPRED_L1_REF12_POC (0x323c * 4) -+#define HEVC_MPRED_L1_REF13_POC (0x323d * 4) -+#define HEVC_MPRED_L1_REF14_POC (0x323e * 4) -+#define HEVC_MPRED_L1_REF15_POC (0x323f * 4) -+#define HEVC_MPRED_PIC_SIZE_EXT (0x3240 * 4) -+#define HEVC_MPRED_DBG_MODE0 (0x3241 * 4) -+#define HEVC_MPRED_DBG_MODE1 (0x3242 * 4) -+#define HEVC_MPRED_DBG2_MODE (0x3243 * 4) -+#define HEVC_MPRED_IMP_CMD0 (0x3244 * 4) -+#define HEVC_MPRED_IMP_CMD1 (0x3245 * 4) -+#define HEVC_MPRED_IMP_CMD2 (0x3246 * 4) -+#define HEVC_MPRED_IMP_CMD3 (0x3247 * 4) -+#define HEVC_MPRED_DBG2_DATA_0 (0x3248 * 4) -+#define HEVC_MPRED_DBG2_DATA_1 (0x3249 * 4) -+#define HEVC_MPRED_DBG2_DATA_2 (0x324a * 4) -+#define HEVC_MPRED_DBG2_DATA_3 (0x324b * 4) -+#define HEVC_MPRED_DBG_DATA_0 (0x3250 * 4) -+#define HEVC_MPRED_DBG_DATA_1 (0x3251 * 4) -+#define HEVC_MPRED_DBG_DATA_2 (0x3252 * 4) -+#define HEVC_MPRED_DBG_DATA_3 (0x3253 * 4) -+#define HEVC_MPRED_DBG_DATA_4 (0x3254 * 4) -+#define HEVC_MPRED_DBG_DATA_5 (0x3255 * 4) -+#define HEVC_MPRED_DBG_DATA_6 (0x3256 * 4) -+#define HEVC_MPRED_DBG_DATA_7 (0x3257 * 4) -+#define HEVC_MPRED_CUR_POC (0x3260 * 4) -+#define HEVC_MPRED_COL_POC (0x3261 * 4) -+#define HEVC_MPRED_MV_RD_END_ADDR (0x3262 * 4) -+#define HEVCD_IPP_TOP_CNTL (0x3400 * 4) -+#define HEVCD_IPP_TOP_STATUS (0x3401 * 4) -+#define HEVCD_IPP_TOP_FRMCONFIG (0x3402 * 4) -+#define HEVCD_IPP_TOP_TILECONFIG1 (0x3403 * 4) -+#define HEVCD_IPP_TOP_TILECONFIG2 (0x3404 * 4) -+#define HEVCD_IPP_TOP_TILECONFIG3 (0x3405 * 4) -+#define HEVCD_IPP_TOP_LCUCONFIG (0x3406 * 4) -+#define HEVCD_IPP_TOP_FRMCTL (0x3407 * 4) -+#define HEVCD_IPP_CONFIG (0x3408 * 4) -+#define HEVCD_IPP_LINEBUFF_BASE (0x3409 * 4) -+#define HEVCD_IPP_INTR_MASK (0x340a * 4) -+#define HEVCD_IPP_AXIIF_CONFIG (0x340b * 4) -+#define HEVCD_IPP_BITDEPTH_CONFIG (0x340c * 4) -+#define HEVCD_IPP_SWMPREDIF_CONFIG (0x3410 * 4) -+#define HEVCD_IPP_SWMPREDIF_STATUS (0x3411 * 4) -+#define HEVCD_IPP_SWMPREDIF_CTBINFO (0x3412 * 4) -+#define HEVCD_IPP_SWMPREDIF_PUINFO0 (0x3413 * 4) -+#define HEVCD_IPP_SWMPREDIF_PUINFO1 (0x3414 * 4) -+#define HEVCD_IPP_SWMPREDIF_PUINFO2 (0x3415 * 4) -+#define HEVCD_IPP_SWMPREDIF_PUINFO3 (0x3416 * 4) -+#define HEVCD_IPP_DYNCLKGATE_CONFIG (0x3420 * 4) -+#define HEVCD_IPP_DYNCLKGATE_STATUS (0x3421 * 4) -+#define HEVCD_IPP_DBG_SEL (0x3430 * 4) -+#define HEVCD_IPP_DBG_DATA (0x3431 * 4) -+#define HEVCD_MPP_ANC2AXI_TBL_CONF_ADDR (0x3460 * 4) -+#define HEVCD_MPP_ANC2AXI_TBL_CMD_ADDR (0x3461 * 4) -+#define HEVCD_MPP_ANC2AXI_TBL_WDATA_ADDR (0x3462 * 4) -+#define HEVCD_MPP_ANC2AXI_TBL_RDATA_ADDR (0x3463 * 4) -+#define HEVCD_MPP_WEIGHTPRED_CNTL_ADDR (0x347b * 4) -+#define HEVCD_MPP_L0_WEIGHT_FLAG_ADDR (0x347c * 4) -+#define HEVCD_MPP_L1_WEIGHT_FLAG_ADDR (0x347d * 4) -+#define HEVCD_MPP_YLOG2WGHTDENOM_ADDR (0x347e * 4) -+#define HEVCD_MPP_DELTACLOG2WGHTDENOM_ADDR (0x347f * 4) -+#define HEVCD_MPP_WEIGHT_ADDR (0x3480 * 4) -+#define HEVCD_MPP_WEIGHT_DATA (0x3481 * 4) -+#define HEVCD_MPP_ANC_CANVAS_ACCCONFIG_ADDR (0x34c0 * 4) -+#define HEVCD_MPP_ANC_CANVAS_DATA_ADDR (0x34c1 * 4) -+#define HEVCD_MPP_DECOMP_CTL1 (0x34c2 * 4) -+#define HEVCD_MPP_DECOMP_CTL2 (0x34c3 * 4) -+#define HEVCD_MCRCC_CTL1 (0x34f0 * 4) -+#define HEVCD_MCRCC_CTL2 (0x34f1 * 4) -+#define HEVCD_MCRCC_CTL3 (0x34f2 * 4) -+#define HEVCD_MCRCC_PERFMON_CTL (0x34f3 * 4) -+#define HEVCD_MCRCC_PERFMON_DATA (0x34f4 * 4) -+#define HEVC_DBLK_CFG0 (0x3500 * 4) -+#define HEVC_DBLK_CFG1 (0x3501 * 4) -+#define HEVC_DBLK_CFG2 (0x3502 * 4) -+#define HEVC_DBLK_CFG3 (0x3503 * 4) -+#define HEVC_DBLK_CFG4 (0x3504 * 4) -+#define HEVC_DBLK_CFG5 (0x3505 * 4) -+#define HEVC_DBLK_CFG6 (0x3506 * 4) -+#define HEVC_DBLK_CFG7 (0x3507 * 4) -+#define HEVC_DBLK_CFG8 (0x3508 * 4) -+#define HEVC_DBLK_CFG9 (0x3509 * 4) -+#define HEVC_DBLK_CFGA (0x350a * 4) -+#define HEVC_DBLK_STS0 (0x350b * 4) -+#define HEVC_DBLK_STS1 (0x350c * 4) -+#define HEVC_SAO_VERSION (0x3600 * 4) -+#define HEVC_SAO_CTRL0 (0x3601 * 4) -+#define HEVC_SAO_CTRL1 (0x3602 * 4) -+#define HEVC_SAO_INT_EN (0x3603 * 4) -+#define HEVC_SAO_INT_STATUS (0x3604 * 4) -+#define HEVC_SAO_PIC_SIZE (0x3605 * 4) -+#define HEVC_SAO_PIC_SIZE_LCU (0x3606 * 4) -+#define HEVC_SAO_TILE_START (0x3607 * 4) -+#define HEVC_SAO_TILE_SIZE_LCU (0x3608 * 4) -+#define HEVC_SAO_AXI_WCTRL (0x3609 * 4) -+#define HEVC_SAO_AXI_RCTRL (0x360a * 4) -+#define HEVC_SAO_Y_START_ADDR (0x360b * 4) -+#define HEVC_SAO_Y_LENGTH (0x360c * 4) -+#define HEVC_SAO_C_START_ADDR (0x360d * 4) -+#define HEVC_SAO_C_LENGTH (0x360e * 4) -+#define HEVC_SAO_Y_WPTR (0x360f * 4) -+#define HEVC_SAO_C_WPTR (0x3610 * 4) -+#define HEVC_SAO_ABV_START_ADDR (0x3611 * 4) -+#define HEVC_SAO_VB_WR_START_ADDR (0x3612 * 4) -+#define HEVC_SAO_VB_RD_START_ADDR (0x3613 * 4) -+#define HEVC_SAO_ABV_WPTR (0x3614 * 4) -+#define HEVC_SAO_ABV_RPTR (0x3615 * 4) -+#define HEVC_SAO_VB_WPTR (0x3616 * 4) -+#define HEVC_SAO_VB_RPTR (0x3617 * 4) -+#define HEVC_SAO_DBG_MODE0 (0x361e * 4) -+#define HEVC_SAO_DBG_MODE1 (0x361f * 4) -+#define HEVC_SAO_CTRL2 (0x3620 * 4) -+#define HEVC_SAO_CTRL3 (0x3621 * 4) -+#define HEVC_SAO_CTRL4 (0x3622 * 4) -+#define HEVC_SAO_CTRL5 (0x3623 * 4) -+#define HEVC_SAO_CTRL6 (0x3624 * 4) -+#define HEVC_SAO_CTRL7 (0x3625 * 4) -+#define HEVC_SAO_DBG_DATA_0 (0x3630 * 4) -+#define HEVC_SAO_DBG_DATA_1 (0x3631 * 4) -+#define HEVC_SAO_DBG_DATA_2 (0x3632 * 4) -+#define HEVC_SAO_DBG_DATA_3 (0x3633 * 4) -+#define HEVC_SAO_DBG_DATA_4 (0x3634 * 4) -+#define HEVC_SAO_DBG_DATA_5 (0x3635 * 4) -+#define HEVC_SAO_DBG_DATA_6 (0x3636 * 4) -+#define HEVC_SAO_DBG_DATA_7 (0x3637 * 4) -+#define HEVC_IQIT_CLK_RST_CTRL (0x3700 * 4) -+#define HEVC_IQIT_DEQUANT_CTRL (0x3701 * 4) -+#define HEVC_IQIT_SCALELUT_WR_ADDR (0x3702 * 4) -+#define HEVC_IQIT_SCALELUT_RD_ADDR (0x3703 * 4) -+#define HEVC_IQIT_SCALELUT_DATA (0x3704 * 4) -+#define HEVC_IQIT_SCALELUT_IDX_4 (0x3705 * 4) -+#define HEVC_IQIT_SCALELUT_IDX_8 (0x3706 * 4) -+#define HEVC_IQIT_SCALELUT_IDX_16_32 (0x3707 * 4) -+#define HEVC_IQIT_STAT_GEN0 (0x3708 * 4) -+#define HEVC_QP_WRITE (0x3709 * 4) -+#define HEVC_IQIT_STAT_GEN1 (0x370a * 4) -+/**/ -+ -+/*add from M8M2*/ -+#define HEVC_MC_CTRL_REG (0x3900 * 4) -+#define HEVC_MC_MB_INFO (0x3901 * 4) -+#define HEVC_MC_PIC_INFO (0x3902 * 4) -+#define HEVC_MC_HALF_PEL_ONE (0x3903 * 4) -+#define HEVC_MC_HALF_PEL_TWO (0x3904 * 4) -+#define HEVC_POWER_CTL_MC (0x3905 * 4) -+#define HEVC_MC_CMD (0x3906 * 4) -+#define HEVC_MC_CTRL0 (0x3907 * 4) -+#define HEVC_MC_PIC_W_H (0x3908 * 4) -+#define HEVC_MC_STATUS0 (0x3909 * 4) -+#define HEVC_MC_STATUS1 (0x390a * 4) -+#define HEVC_MC_CTRL1 (0x390b * 4) -+#define HEVC_MC_MIX_RATIO0 (0x390c * 4) -+#define HEVC_MC_MIX_RATIO1 (0x390d * 4) -+#define HEVC_MC_DP_MB_XY (0x390e * 4) -+#define HEVC_MC_OM_MB_XY (0x390f * 4) -+#define HEVC_PSCALE_RST (0x3910 * 4) -+#define HEVC_PSCALE_CTRL (0x3911 * 4) -+#define HEVC_PSCALE_PICI_W (0x3912 * 4) -+#define HEVC_PSCALE_PICI_H (0x3913 * 4) -+#define HEVC_PSCALE_PICO_W (0x3914 * 4) -+#define HEVC_PSCALE_PICO_H (0x3915 * 4) -+#define HEVC_PSCALE_PICO_START_X (0x3916 * 4) -+#define HEVC_PSCALE_PICO_START_Y (0x3917 * 4) -+#define HEVC_PSCALE_DUMMY (0x3918 * 4) -+#define HEVC_PSCALE_FILT0_COEF0 (0x3919 * 4) -+#define HEVC_PSCALE_FILT0_COEF1 (0x391a * 4) -+#define HEVC_PSCALE_CMD_CTRL (0x391b * 4) -+#define HEVC_PSCALE_CMD_BLK_X (0x391c * 4) -+#define HEVC_PSCALE_CMD_BLK_Y (0x391d * 4) -+#define HEVC_PSCALE_STATUS (0x391e * 4) -+#define HEVC_PSCALE_BMEM_ADDR (0x391f * 4) -+#define HEVC_PSCALE_BMEM_DAT (0x3920 * 4) -+#define HEVC_PSCALE_DRAM_BUF_CTRL (0x3921 * 4) -+#define HEVC_PSCALE_MCMD_CTRL (0x3922 * 4) -+#define HEVC_PSCALE_MCMD_XSIZE (0x3923 * 4) -+#define HEVC_PSCALE_MCMD_YSIZE (0x3924 * 4) -+#define HEVC_PSCALE_RBUF_START_BLKX (0x3925 * 4) -+#define HEVC_PSCALE_RBUF_START_BLKY (0x3926 * 4) -+#define HEVC_PSCALE_PICO_SHIFT_XY (0x3928 * 4) -+#define HEVC_PSCALE_CTRL1 (0x3929 * 4) -+#define HEVC_PSCALE_SRCKEY_CTRL0 (0x392a * 4) -+#define HEVC_PSCALE_SRCKEY_CTRL1 (0x392b * 4) -+#define HEVC_PSCALE_CANVAS_RD_ADDR (0x392c * 4) -+#define HEVC_PSCALE_CANVAS_WR_ADDR (0x392d * 4) -+#define HEVC_PSCALE_CTRL2 (0x392e * 4) -+#define HEVC_HDEC_MC_OMEM_AUTO (0x3930 * 4) -+#define HEVC_HDEC_MC_MBRIGHT_IDX (0x3931 * 4) -+#define HEVC_HDEC_MC_MBRIGHT_RD (0x3932 * 4) -+#define HEVC_MC_MPORT_CTRL (0x3940 * 4) -+#define HEVC_MC_MPORT_DAT (0x3941 * 4) -+#define HEVC_MC_WT_PRED_CTRL (0x3942 * 4) -+#define HEVC_MC_MBBOT_ST_EVEN_ADDR (0x3944 * 4) -+#define HEVC_MC_MBBOT_ST_ODD_ADDR (0x3945 * 4) -+#define HEVC_MC_DPDN_MB_XY (0x3946 * 4) -+#define HEVC_MC_OMDN_MB_XY (0x3947 * 4) -+#define HEVC_MC_HCMDBUF_H (0x3948 * 4) -+#define HEVC_MC_HCMDBUF_L (0x3949 * 4) -+#define HEVC_MC_HCMD_H (0x394a * 4) -+#define HEVC_MC_HCMD_L (0x394b * 4) -+#define HEVC_MC_IDCT_DAT (0x394c * 4) -+#define HEVC_MC_CTRL_GCLK_CTRL (0x394d * 4) -+#define HEVC_MC_OTHER_GCLK_CTRL (0x394e * 4) -+#define HEVC_MC_CTRL2 (0x394f * 4) -+#define HEVC_MDEC_PIC_DC_CTRL (0x398e * 4) -+#define HEVC_MDEC_PIC_DC_STATUS (0x398f * 4) -+#define HEVC_ANC0_CANVAS_ADDR (0x3990 * 4) -+#define HEVC_ANC1_CANVAS_ADDR (0x3991 * 4) -+#define HEVC_ANC2_CANVAS_ADDR (0x3992 * 4) -+#define HEVC_ANC3_CANVAS_ADDR (0x3993 * 4) -+#define HEVC_ANC4_CANVAS_ADDR (0x3994 * 4) -+#define HEVC_ANC5_CANVAS_ADDR (0x3995 * 4) -+#define HEVC_ANC6_CANVAS_ADDR (0x3996 * 4) -+#define HEVC_ANC7_CANVAS_ADDR (0x3997 * 4) -+#define HEVC_ANC8_CANVAS_ADDR (0x3998 * 4) -+#define HEVC_ANC9_CANVAS_ADDR (0x3999 * 4) -+#define HEVC_ANC10_CANVAS_ADDR (0x399a * 4) -+#define HEVC_ANC11_CANVAS_ADDR (0x399b * 4) -+#define HEVC_ANC12_CANVAS_ADDR (0x399c * 4) -+#define HEVC_ANC13_CANVAS_ADDR (0x399d * 4) -+#define HEVC_ANC14_CANVAS_ADDR (0x399e * 4) -+#define HEVC_ANC15_CANVAS_ADDR (0x399f * 4) -+#define HEVC_ANC16_CANVAS_ADDR (0x39a0 * 4) -+#define HEVC_ANC17_CANVAS_ADDR (0x39a1 * 4) -+#define HEVC_ANC18_CANVAS_ADDR (0x39a2 * 4) -+#define HEVC_ANC19_CANVAS_ADDR (0x39a3 * 4) -+#define HEVC_ANC20_CANVAS_ADDR (0x39a4 * 4) -+#define HEVC_ANC21_CANVAS_ADDR (0x39a5 * 4) -+#define HEVC_ANC22_CANVAS_ADDR (0x39a6 * 4) -+#define HEVC_ANC23_CANVAS_ADDR (0x39a7 * 4) -+#define HEVC_ANC24_CANVAS_ADDR (0x39a8 * 4) -+#define HEVC_ANC25_CANVAS_ADDR (0x39a9 * 4) -+#define HEVC_ANC26_CANVAS_ADDR (0x39aa * 4) -+#define HEVC_ANC27_CANVAS_ADDR (0x39ab * 4) -+#define HEVC_ANC28_CANVAS_ADDR (0x39ac * 4) -+#define HEVC_ANC29_CANVAS_ADDR (0x39ad * 4) -+#define HEVC_ANC30_CANVAS_ADDR (0x39ae * 4) -+#define HEVC_ANC31_CANVAS_ADDR (0x39af * 4) -+#define HEVC_DBKR_CANVAS_ADDR (0x39b0 * 4) -+#define HEVC_DBKW_CANVAS_ADDR (0x39b1 * 4) -+#define HEVC_REC_CANVAS_ADDR (0x39b2 * 4) -+#define HEVC_CURR_CANVAS_CTRL (0x39b3 * 4) -+#define HEVC_MDEC_PIC_DC_THRESH (0x39b8 * 4) -+#define HEVC_MDEC_PICR_BUF_STATUS (0x39b9 * 4) -+#define HEVC_MDEC_PICW_BUF_STATUS (0x39ba * 4) -+#define HEVC_MCW_DBLK_WRRSP_CNT (0x39bb * 4) -+#define HEVC_MC_MBBOT_WRRSP_CNT (0x39bc * 4) -+#define HEVC_MDEC_PICW_BUF2_STATUS (0x39bd * 4) -+#define HEVC_WRRSP_FIFO_PICW_DBK (0x39be * 4) -+#define HEVC_WRRSP_FIFO_PICW_MC (0x39bf * 4) -+#define HEVC_AV_SCRATCH_0 (0x39c0 * 4) -+#define HEVC_AV_SCRATCH_1 (0x39c1 * 4) -+#define HEVC_AV_SCRATCH_2 (0x39c2 * 4) -+#define HEVC_AV_SCRATCH_3 (0x39c3 * 4) -+#define HEVC_AV_SCRATCH_4 (0x39c4 * 4) -+#define HEVC_AV_SCRATCH_5 (0x39c5 * 4) -+#define HEVC_AV_SCRATCH_6 (0x39c6 * 4) -+#define HEVC_AV_SCRATCH_7 (0x39c7 * 4) -+#define HEVC_AV_SCRATCH_8 (0x39c8 * 4) -+#define HEVC_AV_SCRATCH_9 (0x39c9 * 4) -+#define HEVC_AV_SCRATCH_A (0x39ca * 4) -+#define HEVC_AV_SCRATCH_B (0x39cb * 4) -+#define HEVC_AV_SCRATCH_C (0x39cc * 4) -+#define HEVC_AV_SCRATCH_D (0x39cd * 4) -+#define HEVC_AV_SCRATCH_E (0x39ce * 4) -+#define HEVC_AV_SCRATCH_F (0x39cf * 4) -+#define HEVC_AV_SCRATCH_G (0x39d0 * 4) -+#define HEVC_AV_SCRATCH_H (0x39d1 * 4) -+#define HEVC_AV_SCRATCH_I (0x39d2 * 4) -+#define HEVC_AV_SCRATCH_J (0x39d3 * 4) -+#define HEVC_AV_SCRATCH_K (0x39d4 * 4) -+#define HEVC_AV_SCRATCH_L (0x39d5 * 4) -+#define HEVC_AV_SCRATCH_M (0x39d6 * 4) -+#define HEVC_AV_SCRATCH_N (0x39d7 * 4) -+#define HEVC_WRRSP_CO_MB (0x39d8 * 4) -+#define HEVC_WRRSP_DCAC (0x39d9 * 4) -+#define HEVC_WRRSP_VLD (0x39da * 4) -+#define HEVC_MDEC_DOUBLEW_CFG0 (0x39db * 4) -+#define HEVC_MDEC_DOUBLEW_CFG1 (0x39dc * 4) -+#define HEVC_MDEC_DOUBLEW_CFG2 (0x39dd * 4) -+#define HEVC_MDEC_DOUBLEW_CFG3 (0x39de * 4) -+#define HEVC_MDEC_DOUBLEW_CFG4 (0x39df * 4) -+#define HEVC_MDEC_DOUBLEW_CFG5 (0x39e0 * 4) -+#define HEVC_MDEC_DOUBLEW_CFG6 (0x39e1 * 4) -+#define HEVC_MDEC_DOUBLEW_CFG7 (0x39e2 * 4) -+#define HEVC_MDEC_DOUBLEW_STATUS (0x39e3 * 4) -+#define HEVC_DBLK_RST (0x3950 * 4) -+#define HEVC_DBLK_CTRL (0x3951 * 4) -+#define HEVC_DBLK_MB_WID_HEIGHT (0x3952 * 4) -+#define HEVC_DBLK_STATUS (0x3953 * 4) -+#define HEVC_DBLK_CMD_CTRL (0x3954 * 4) -+#define HEVC_DBLK_MB_XY (0x3955 * 4) -+#define HEVC_DBLK_QP (0x3956 * 4) -+#define HEVC_DBLK_Y_BHFILT (0x3957 * 4) -+#define HEVC_DBLK_Y_BHFILT_HIGH (0x3958 * 4) -+#define HEVC_DBLK_Y_BVFILT (0x3959 * 4) -+#define HEVC_DBLK_CB_BFILT (0x395a * 4) -+#define HEVC_DBLK_CR_BFILT (0x395b * 4) -+#define HEVC_DBLK_Y_HFILT (0x395c * 4) -+#define HEVC_DBLK_Y_HFILT_HIGH (0x395d * 4) -+#define HEVC_DBLK_Y_VFILT (0x395e * 4) -+#define HEVC_DBLK_CB_FILT (0x395f * 4) -+#define HEVC_DBLK_CR_FILT (0x3960 * 4) -+#define HEVC_DBLK_BETAX_QP_SEL (0x3961 * 4) -+#define HEVC_DBLK_CLIP_CTRL0 (0x3962 * 4) -+#define HEVC_DBLK_CLIP_CTRL1 (0x3963 * 4) -+#define HEVC_DBLK_CLIP_CTRL2 (0x3964 * 4) -+#define HEVC_DBLK_CLIP_CTRL3 (0x3965 * 4) -+#define HEVC_DBLK_CLIP_CTRL4 (0x3966 * 4) -+#define HEVC_DBLK_CLIP_CTRL5 (0x3967 * 4) -+#define HEVC_DBLK_CLIP_CTRL6 (0x3968 * 4) -+#define HEVC_DBLK_CLIP_CTRL7 (0x3969 * 4) -+#define HEVC_DBLK_CLIP_CTRL8 (0x396a * 4) -+#define HEVC_DBLK_STATUS1 (0x396b * 4) -+#define HEVC_DBLK_GCLK_FREE (0x396c * 4) -+#define HEVC_DBLK_GCLK_OFF (0x396d * 4) -+#define HEVC_DBLK_AVSFLAGS (0x396e * 4) -+#define HEVC_DBLK_CBPY (0x3970 * 4) -+#define HEVC_DBLK_CBPY_ADJ (0x3971 * 4) -+#define HEVC_DBLK_CBPC (0x3972 * 4) -+#define HEVC_DBLK_CBPC_ADJ (0x3973 * 4) -+#define HEVC_DBLK_VHMVD (0x3974 * 4) -+#define HEVC_DBLK_STRONG (0x3975 * 4) -+#define HEVC_DBLK_RV8_QUANT (0x3976 * 4) -+#define HEVC_DBLK_CBUS_HCMD2 (0x3977 * 4) -+#define HEVC_DBLK_CBUS_HCMD1 (0x3978 * 4) -+#define HEVC_DBLK_CBUS_HCMD0 (0x3979 * 4) -+#define HEVC_DBLK_VLD_HCMD2 (0x397a * 4) -+#define HEVC_DBLK_VLD_HCMD1 (0x397b * 4) -+#define HEVC_DBLK_VLD_HCMD0 (0x397c * 4) -+#define HEVC_DBLK_OST_YBASE (0x397d * 4) -+#define HEVC_DBLK_OST_CBCRDIFF (0x397e * 4) -+#define HEVC_DBLK_CTRL1 (0x397f * 4) -+#define HEVC_MCRCC_CTL1 (0x3980 * 4) -+#define HEVC_MCRCC_CTL2 (0x3981 * 4) -+#define HEVC_MCRCC_CTL3 (0x3982 * 4) -+#define HEVC_GCLK_EN (0x3983 * 4) -+#define HEVC_MDEC_SW_RESET (0x3984 * 4) -+ -+/*add from M8M2*/ -+#define HEVC_VLD_STATUS_CTRL (0x3c00 * 4) -+#define HEVC_MPEG1_2_REG (0x3c01 * 4) -+#define HEVC_F_CODE_REG (0x3c02 * 4) -+#define HEVC_PIC_HEAD_INFO (0x3c03 * 4) -+#define HEVC_SLICE_VER_POS_PIC_TYPE (0x3c04 * 4) -+#define HEVC_QP_VALUE_REG (0x3c05 * 4) -+#define HEVC_MBA_INC (0x3c06 * 4) -+#define HEVC_MB_MOTION_MODE (0x3c07 * 4) -+#define HEVC_POWER_CTL_VLD (0x3c08 * 4) -+#define HEVC_MB_WIDTH (0x3c09 * 4) -+#define HEVC_SLICE_QP (0x3c0a * 4) -+#define HEVC_PRE_START_CODE (0x3c0b * 4) -+#define HEVC_SLICE_START_BYTE_01 (0x3c0c * 4) -+#define HEVC_SLICE_START_BYTE_23 (0x3c0d * 4) -+#define HEVC_RESYNC_MARKER_LENGTH (0x3c0e * 4) -+#define HEVC_DECODER_BUFFER_INFO (0x3c0f * 4) -+#define HEVC_FST_FOR_MV_X (0x3c10 * 4) -+#define HEVC_FST_FOR_MV_Y (0x3c11 * 4) -+#define HEVC_SCD_FOR_MV_X (0x3c12 * 4) -+#define HEVC_SCD_FOR_MV_Y (0x3c13 * 4) -+#define HEVC_FST_BAK_MV_X (0x3c14 * 4) -+#define HEVC_FST_BAK_MV_Y (0x3c15 * 4) -+#define HEVC_SCD_BAK_MV_X (0x3c16 * 4) -+#define HEVC_SCD_BAK_MV_Y (0x3c17 * 4) -+#define HEVC_VLD_DECODE_CONTROL (0x3c18 * 4) -+#define HEVC_VLD_REVERVED_19 (0x3c19 * 4) -+#define HEVC_VIFF_BIT_CNT (0x3c1a * 4) -+#define HEVC_BYTE_ALIGN_PEAK_HI (0x3c1b * 4) -+#define HEVC_BYTE_ALIGN_PEAK_LO (0x3c1c * 4) -+#define HEVC_NEXT_ALIGN_PEAK (0x3c1d * 4) -+#define HEVC_VC1_CONTROL_REG (0x3c1e * 4) -+#define HEVC_PMV1_X (0x3c20 * 4) -+#define HEVC_PMV1_Y (0x3c21 * 4) -+#define HEVC_PMV2_X (0x3c22 * 4) -+#define HEVC_PMV2_Y (0x3c23 * 4) -+#define HEVC_PMV3_X (0x3c24 * 4) -+#define HEVC_PMV3_Y (0x3c25 * 4) -+#define HEVC_PMV4_X (0x3c26 * 4) -+#define HEVC_PMV4_Y (0x3c27 * 4) -+#define HEVC_M4_TABLE_SELECT (0x3c28 * 4) -+#define HEVC_M4_CONTROL_REG (0x3c29 * 4) -+#define HEVC_BLOCK_NUM (0x3c2a * 4) -+#define HEVC_PATTERN_CODE (0x3c2b * 4) -+#define HEVC_MB_INFO (0x3c2c * 4) -+#define HEVC_VLD_DC_PRED (0x3c2d * 4) -+#define HEVC_VLD_ERROR_MASK (0x3c2e * 4) -+#define HEVC_VLD_DC_PRED_C (0x3c2f * 4) -+#define HEVC_LAST_SLICE_MV_ADDR (0x3c30 * 4) -+#define HEVC_LAST_MVX (0x3c31 * 4) -+#define HEVC_LAST_MVY (0x3c32 * 4) -+#define HEVC_VLD_C38 (0x3c38 * 4) -+#define HEVC_VLD_C39 (0x3c39 * 4) -+#define HEVC_VLD_STATUS (0x3c3a * 4) -+#define HEVC_VLD_SHIFT_STATUS (0x3c3b * 4) -+#define HEVC_VOFF_STATUS (0x3c3c * 4) -+#define HEVC_VLD_C3D (0x3c3d * 4) -+#define HEVC_VLD_DBG_INDEX (0x3c3e * 4) -+#define HEVC_VLD_DBG_DATA (0x3c3f * 4) -+#define HEVC_VLD_MEM_VIFIFO_START_PTR (0x3c40 * 4) -+#define HEVC_VLD_MEM_VIFIFO_CURR_PTR (0x3c41 * 4) -+#define HEVC_VLD_MEM_VIFIFO_END_PTR (0x3c42 * 4) -+#define HEVC_VLD_MEM_VIFIFO_BYTES_AVAIL (0x3c43 * 4) -+#define HEVC_VLD_MEM_VIFIFO_CONTROL (0x3c44 * 4) -+#define HEVC_VLD_MEM_VIFIFO_WP (0x3c45 * 4) -+#define HEVC_VLD_MEM_VIFIFO_RP (0x3c46 * 4) -+#define HEVC_VLD_MEM_VIFIFO_LEVEL (0x3c47 * 4) -+#define HEVC_VLD_MEM_VIFIFO_BUF_CNTL (0x3c48 * 4) -+#define HEVC_VLD_TIME_STAMP_CNTL (0x3c49 * 4) -+#define HEVC_VLD_TIME_STAMP_SYNC_0 (0x3c4a * 4) -+#define HEVC_VLD_TIME_STAMP_SYNC_1 (0x3c4b * 4) -+#define HEVC_VLD_TIME_STAMP_0 (0x3c4c * 4) -+#define HEVC_VLD_TIME_STAMP_1 (0x3c4d * 4) -+#define HEVC_VLD_TIME_STAMP_2 (0x3c4e * 4) -+#define HEVC_VLD_TIME_STAMP_3 (0x3c4f * 4) -+#define HEVC_VLD_TIME_STAMP_LENGTH (0x3c50 * 4) -+#define HEVC_VLD_MEM_VIFIFO_WRAP_COUNT (0x3c51 * 4) -+#define HEVC_VLD_MEM_VIFIFO_MEM_CTL (0x3c52 * 4) -+#define HEVC_VLD_MEM_VBUF_RD_PTR (0x3c53 * 4) -+#define HEVC_VLD_MEM_VBUF2_RD_PTR (0x3c54 * 4) -+#define HEVC_VLD_MEM_SWAP_ADDR (0x3c55 * 4) -+#define HEVC_VLD_MEM_SWAP_CTL (0x3c56 * 4) -+/**/ -+ -+/*add from M8M2*/ -+#define HEVC_VCOP_CTRL_REG (0x3e00 * 4) -+#define HEVC_QP_CTRL_REG (0x3e01 * 4) -+#define HEVC_INTRA_QUANT_MATRIX (0x3e02 * 4) -+#define HEVC_NON_I_QUANT_MATRIX (0x3e03 * 4) -+#define HEVC_DC_SCALER (0x3e04 * 4) -+#define HEVC_DC_AC_CTRL (0x3e05 * 4) -+#define HEVC_DC_AC_SCALE_MUL (0x3e06 * 4) -+#define HEVC_DC_AC_SCALE_DIV (0x3e07 * 4) -+#define HEVC_POWER_CTL_IQIDCT (0x3e08 * 4) -+#define HEVC_RV_AI_Y_X (0x3e09 * 4) -+#define HEVC_RV_AI_U_X (0x3e0a * 4) -+#define HEVC_RV_AI_V_X (0x3e0b * 4) -+#define HEVC_RV_AI_MB_COUNT (0x3e0c * 4) -+#define HEVC_NEXT_INTRA_DMA_ADDRESS (0x3e0d * 4) -+#define HEVC_IQIDCT_CONTROL (0x3e0e * 4) -+#define HEVC_IQIDCT_DEBUG_INFO_0 (0x3e0f * 4) -+#define HEVC_DEBLK_CMD (0x3e10 * 4) -+#define HEVC_IQIDCT_DEBUG_IDCT (0x3e11 * 4) -+#define HEVC_DCAC_DMA_CTRL (0x3e12 * 4) -+#define HEVC_DCAC_DMA_ADDRESS (0x3e13 * 4) -+#define HEVC_DCAC_CPU_ADDRESS (0x3e14 * 4) -+#define HEVC_DCAC_CPU_DATA (0x3e15 * 4) -+#define HEVC_DCAC_MB_COUNT (0x3e16 * 4) -+#define HEVC_IQ_QUANT (0x3e17 * 4) -+#define HEVC_VC1_BITPLANE_CTL (0x3e18 * 4) -+ -+ -+/*add from M8M2*/ -+#define HEVC_MSP (0x3300 * 4) -+#define HEVC_MPSR (0x3301 * 4) -+#define HEVC_MINT_VEC_BASE (0x3302 * 4) -+#define HEVC_MCPU_INTR_GRP (0x3303 * 4) -+#define HEVC_MCPU_INTR_MSK (0x3304 * 4) -+#define HEVC_MCPU_INTR_REQ (0x3305 * 4) -+#define HEVC_MPC_P (0x3306 * 4) -+#define HEVC_MPC_D (0x3307 * 4) -+#define HEVC_MPC_E (0x3308 * 4) -+#define HEVC_MPC_W (0x3309 * 4) -+#define HEVC_MINDEX0_REG (0x330a * 4) -+#define HEVC_MINDEX1_REG (0x330b * 4) -+#define HEVC_MINDEX2_REG (0x330c * 4) -+#define HEVC_MINDEX3_REG (0x330d * 4) -+#define HEVC_MINDEX4_REG (0x330e * 4) -+#define HEVC_MINDEX5_REG (0x330f * 4) -+#define HEVC_MINDEX6_REG (0x3310 * 4) -+#define HEVC_MINDEX7_REG (0x3311 * 4) -+#define HEVC_MMIN_REG (0x3312 * 4) -+#define HEVC_MMAX_REG (0x3313 * 4) -+#define HEVC_MBREAK0_REG (0x3314 * 4) -+#define HEVC_MBREAK1_REG (0x3315 * 4) -+#define HEVC_MBREAK2_REG (0x3316 * 4) -+#define HEVC_MBREAK3_REG (0x3317 * 4) -+#define HEVC_MBREAK_TYPE (0x3318 * 4) -+#define HEVC_MBREAK_CTRL (0x3319 * 4) -+#define HEVC_MBREAK_STAUTS (0x331a * 4) -+#define HEVC_MDB_ADDR_REG (0x331b * 4) -+#define HEVC_MDB_DATA_REG (0x331c * 4) -+#define HEVC_MDB_CTRL (0x331d * 4) -+#define HEVC_MSFTINT0 (0x331e * 4) -+#define HEVC_MSFTINT1 (0x331f * 4) -+#define HEVC_CSP (0x3320 * 4) -+#define HEVC_CPSR (0x3321 * 4) -+#define HEVC_CINT_VEC_BASE (0x3322 * 4) -+#define HEVC_CCPU_INTR_GRP (0x3323 * 4) -+#define HEVC_CCPU_INTR_MSK (0x3324 * 4) -+#define HEVC_CCPU_INTR_REQ (0x3325 * 4) -+#define HEVC_CPC_P (0x3326 * 4) -+#define HEVC_CPC_D (0x3327 * 4) -+#define HEVC_CPC_E (0x3328 * 4) -+#define HEVC_CPC_W (0x3329 * 4) -+#define HEVC_CINDEX0_REG (0x332a * 4) -+#define HEVC_CINDEX1_REG (0x332b * 4) -+#define HEVC_CINDEX2_REG (0x332c * 4) -+#define HEVC_CINDEX3_REG (0x332d * 4) -+#define HEVC_CINDEX4_REG (0x332e * 4) -+#define HEVC_CINDEX5_REG (0x332f * 4) -+#define HEVC_CINDEX6_REG (0x3330 * 4) -+#define HEVC_CINDEX7_REG (0x3331 * 4) -+#define HEVC_CMIN_REG (0x3332 * 4) -+#define HEVC_CMAX_REG (0x3333 * 4) -+#define HEVC_CBREAK0_REG (0x3334 * 4) -+#define HEVC_CBREAK1_REG (0x3335 * 4) -+#define HEVC_CBREAK2_REG (0x3336 * 4) -+#define HEVC_CBREAK3_REG (0x3337 * 4) -+#define HEVC_CBREAK_TYPE (0x3338 * 4) -+#define HEVC_CBREAK_CTRL (0x3339 * 4) -+#define HEVC_CBREAK_STAUTS (0x333a * 4) -+#define HEVC_CDB_ADDR_REG (0x333b * 4) -+#define HEVC_CDB_DATA_REG (0x333c * 4) -+#define HEVC_CDB_CTRL (0x333d * 4) -+#define HEVC_CSFTINT0 (0x333e * 4) -+#define HEVC_CSFTINT1 (0x333f * 4) -+#define HEVC_IMEM_DMA_CTRL (0x3340 * 4) -+#define HEVC_IMEM_DMA_ADR (0x3341 * 4) -+#define HEVC_IMEM_DMA_COUNT (0x3342 * 4) -+#define HEVC_WRRSP_IMEM (0x3343 * 4) -+#define HEVC_LMEM_DMA_CTRL (0x3350 * 4) -+#define HEVC_LMEM_DMA_ADR (0x3351 * 4) -+#define HEVC_LMEM_DMA_COUNT (0x3352 * 4) -+#define HEVC_WRRSP_LMEM (0x3353 * 4) -+#define HEVC_MAC_CTRL1 (0x3360 * 4) -+#define HEVC_ACC0REG1 (0x3361 * 4) -+#define HEVC_ACC1REG1 (0x3362 * 4) -+#define HEVC_MAC_CTRL2 (0x3370 * 4) -+#define HEVC_ACC0REG2 (0x3371 * 4) -+#define HEVC_ACC1REG2 (0x3372 * 4) -+#define HEVC_CPU_TRACE (0x3380 * 4) -+/**/ -+ -+#endif -+ -diff --git a/drivers/media/platform/meson/vdec/vdec_hevc.c b/drivers/media/platform/meson/vdec/vdec_hevc.c -new file mode 100644 -index 0000000000000..8872f58d39fea ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/vdec_hevc.c -@@ -0,0 +1,191 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 Maxime Jourdan -+ * -+ * VDEC_HEVC is a video decoding block that allows decoding of -+ * HEVC, VP9 -+ */ -+ -+#include -+#include -+ -+#include "vdec_1.h" -+#include "vdec_helpers.h" -+#include "hevc_regs.h" -+#include "dos_regs.h" -+ -+/* AO Registers */ -+#define AO_RTI_GEN_PWR_SLEEP0 0xe8 -+#define AO_RTI_GEN_PWR_ISO0 0xec -+ #define GEN_PWR_VDEC_HEVC (BIT(7) | BIT(6)) -+ -+#define MC_SIZE (4096 * 4) -+ -+static int vdec_hevc_load_firmware(struct amvdec_session *sess, const char* fwname) -+{ -+ struct amvdec_core *core = sess->core; -+ struct device *dev = core->dev_dec; -+ const struct firmware *fw; -+ static void *mc_addr; -+ static dma_addr_t mc_addr_map; -+ int ret; -+ u32 i = 100; -+ -+ ret = request_firmware(&fw, fwname, dev); -+ if (ret < 0) { -+ dev_err(dev, "Unable to request firmware %s\n", fwname); -+ return ret; -+ } -+ -+ if (fw->size < MC_SIZE) { -+ dev_err(dev, "Firmware size %zu is too small. Expected %u.\n", -+ fw->size, MC_SIZE); -+ ret = -EINVAL; -+ goto release_firmware; -+ } -+ -+ mc_addr = dma_alloc_coherent(core->dev, MC_SIZE, &mc_addr_map, GFP_KERNEL); -+ if (!mc_addr) { -+ dev_err(dev, "Failed allocating memory for firmware loading\n"); -+ ret = -ENOMEM; -+ goto release_firmware; -+ } -+ -+ memcpy(mc_addr, fw->data, MC_SIZE); -+ -+ amvdec_write_dos(core, HEVC_MPSR, 0); -+ amvdec_write_dos(core, HEVC_CPSR, 0); -+ -+ amvdec_write_dos(core, HEVC_IMEM_DMA_ADR, mc_addr_map); -+ amvdec_write_dos(core, HEVC_IMEM_DMA_COUNT, MC_SIZE / 4); -+ amvdec_write_dos(core, HEVC_IMEM_DMA_CTRL, (0x8000 | (7 << 16))); -+ -+ while (--i && readl(core->dos_base + HEVC_IMEM_DMA_CTRL) & 0x8000) { } -+ -+ if (i == 0) { -+ dev_err(dev, "Firmware load fail (DMA hang?)\n"); -+ ret = -ENODEV; -+ } -+ -+ dma_free_coherent(core->dev, MC_SIZE, mc_addr, mc_addr_map); -+release_firmware: -+ release_firmware(fw); -+ return ret; -+} -+ -+static void vdec_hevc_stbuf_init(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ -+ amvdec_write_dos(core, HEVC_STREAM_CONTROL, amvdec_read_dos(core, HEVC_STREAM_CONTROL) & ~1); -+ amvdec_write_dos(core, HEVC_STREAM_START_ADDR, sess->vififo_paddr); -+ amvdec_write_dos(core, HEVC_STREAM_END_ADDR, sess->vififo_paddr + sess->vififo_size); -+ amvdec_write_dos(core, HEVC_STREAM_RD_PTR, sess->vififo_paddr); -+ amvdec_write_dos(core, HEVC_STREAM_WR_PTR, sess->vififo_paddr); -+} -+ -+/* VDEC_HEVC specific ESPARSER configuration */ -+static void vdec_hevc_conf_esparser(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ -+ /* set vififo_vbuf_rp_sel=>vdec_hevc */ -+ amvdec_write_dos(core, DOS_GEN_CTRL0, 3 << 1); -+ amvdec_write_dos(core, HEVC_STREAM_CONTROL, amvdec_read_dos(core, HEVC_STREAM_CONTROL) | BIT(3)); -+ amvdec_write_dos(core, HEVC_STREAM_CONTROL, amvdec_read_dos(core, HEVC_STREAM_CONTROL) | 1); -+ amvdec_write_dos(core, HEVC_STREAM_FIFO_CTL, amvdec_read_dos(core, HEVC_STREAM_FIFO_CTL) | BIT(29)); -+} -+ -+static u32 vdec_hevc_vififo_level(struct amvdec_session *sess) -+{ -+ return readl_relaxed(sess->core->dos_base + HEVC_STREAM_LEVEL); -+} -+ -+static int vdec_hevc_stop(struct amvdec_session *sess) -+{ -+ struct amvdec_core *core = sess->core; -+ struct amvdec_codec_ops *codec_ops = sess->fmt_out->codec_ops; -+ -+ /* Disable interrupt */ -+ amvdec_write_dos(core, HEVC_ASSIST_MBOX1_MASK, 0); -+ /* Disable firmware processor */ -+ amvdec_write_dos(core, HEVC_MPSR, 0); -+ -+ if (sess->priv) -+ codec_ops->stop(sess); -+ -+ /* Enable VDEC_HEVC Isolation */ -+ regmap_update_bits(core->regmap_ao, AO_RTI_GEN_PWR_ISO0, 0xc00, 0xc00); -+ -+ /* VDEC_HEVC Memories */ -+ amvdec_write_dos(core, DOS_MEM_PD_HEVC, 0xffffffffUL); -+ -+ regmap_update_bits(core->regmap_ao, AO_RTI_GEN_PWR_SLEEP0, -+ GEN_PWR_VDEC_HEVC, GEN_PWR_VDEC_HEVC); -+ -+ clk_disable_unprepare(core->vdec_hevc_clk); -+ -+ return 0; -+} -+ -+static int vdec_hevc_start(struct amvdec_session *sess) -+{ -+ int ret; -+ struct amvdec_core *core = sess->core; -+ struct amvdec_codec_ops *codec_ops = sess->fmt_out->codec_ops; -+ -+ clk_set_rate(core->vdec_hevc_clk, 666666666); -+ ret = clk_prepare_enable(core->vdec_hevc_clk); -+ if (ret) -+ return ret; -+ -+ regmap_update_bits(core->regmap_ao, AO_RTI_GEN_PWR_SLEEP0, -+ GEN_PWR_VDEC_HEVC, 0); -+ udelay(10); -+ -+ /* Reset VDEC_HEVC*/ -+ amvdec_write_dos(core, DOS_SW_RESET3, 0xffffffff); -+ amvdec_write_dos(core, DOS_SW_RESET3, 0x00000000); -+ -+ amvdec_write_dos(core, DOS_GCLK_EN3, 0xffffffff); -+ -+ /* VDEC_HEVC Memories */ -+ amvdec_write_dos(core, DOS_MEM_PD_HEVC, 0x00000000); -+ -+ /* Remove VDEC_HEVC Isolation */ -+ regmap_update_bits(core->regmap_ao, AO_RTI_GEN_PWR_ISO0, 0xc00, 0); -+ -+ amvdec_write_dos(core, DOS_SW_RESET3, 0xffffffff); -+ amvdec_write_dos(core, DOS_SW_RESET3, 0x00000000); -+ -+ vdec_hevc_stbuf_init(sess); -+ -+ ret = vdec_hevc_load_firmware(sess, sess->fmt_out->firmware_path); -+ if (ret) -+ goto stop; -+ -+ ret = codec_ops->start(sess); -+ if (ret) -+ goto stop; -+ -+ amvdec_write_dos(core, DOS_SW_RESET3, BIT(12)|BIT(11)); -+ amvdec_write_dos(core, DOS_SW_RESET3, 0); -+ amvdec_read_dos(core, DOS_SW_RESET3); -+ -+ amvdec_write_dos(core, HEVC_MPSR, 1); -+ /* Let the firmware settle */ -+ udelay(10); -+ -+ return 0; -+ -+stop: -+ vdec_hevc_stop(sess); -+ return ret; -+} -+ -+struct amvdec_ops vdec_hevc_ops = { -+ .start = vdec_hevc_start, -+ .stop = vdec_hevc_stop, -+ .conf_esparser = vdec_hevc_conf_esparser, -+ .vififo_level = vdec_hevc_vififo_level, -+}; -\ No newline at end of file -diff --git a/drivers/media/platform/meson/vdec/vdec_hevc.h b/drivers/media/platform/meson/vdec/vdec_hevc.h -new file mode 100644 -index 0000000000000..f1ccad7d5f949 ---- /dev/null -+++ b/drivers/media/platform/meson/vdec/vdec_hevc.h -@@ -0,0 +1,22 @@ -+/* -+ * Copyright (C) 2018 Maxime Jourdan -+ * -+ * This program is free software; you can redistribute it and/or modify -+ * it under the terms of the GNU General Public License version 2 and -+ * only version 2 as published by the Free Software Foundation. -+ * -+ * This program is distributed in the hope that it will be useful, -+ * but WITHOUT ANY WARRANTY; without even the implied warranty of -+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -+ * GNU General Public License for more details. -+ * -+ */ -+ -+#ifndef __MESON_VDEC_VDEC_HEVC_H_ -+#define __MESON_VDEC_VDEC_HEVC_H_ -+ -+#include "vdec.h" -+ -+extern struct amvdec_ops vdec_hevc_ops; -+ -+#endif -\ No newline at end of file -diff --git a/drivers/media/platform/meson/vdec/vdec_platform.c b/drivers/media/platform/meson/vdec/vdec_platform.c -index 1181832b5fe1e..a8d03426e53d0 100644 ---- a/drivers/media/platform/meson/vdec/vdec_platform.c -+++ b/drivers/media/platform/meson/vdec/vdec_platform.c -@@ -8,13 +8,25 @@ - #include "vdec.h" - - #include "vdec_1.h" -+#include "vdec_hevc.h" - #include "codec_mpeg12.h" - #include "codec_h264.h" - #include "codec_mpeg4.h" - #include "codec_mjpeg.h" -+#include "codec_hevc.h" - - static const struct amvdec_format vdec_formats_gxbb[] = { - { -+ .pixfmt = V4L2_PIX_FMT_HEVC, -+ .min_buffers = 16, -+ .max_buffers = 24, -+ .max_width = 3840, -+ .max_height = 2160, -+ .vdec_ops = &vdec_hevc_ops, -+ .codec_ops = &codec_hevc_ops, -+ .firmware_path = "meson/gx/vh265_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_AM21C, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_MJPEG, - .min_buffers = 4, - .max_buffers = 4, -@@ -89,6 +101,16 @@ static const struct amvdec_format vdec_formats_gxbb[] = { - - static const struct amvdec_format vdec_formats_gxl[] = { - { -+ .pixfmt = V4L2_PIX_FMT_HEVC, -+ .min_buffers = 16, -+ .max_buffers = 24, -+ .max_width = 3840, -+ .max_height = 2160, -+ .vdec_ops = &vdec_hevc_ops, -+ .codec_ops = &codec_hevc_ops, -+ .firmware_path = "meson/gx/vh265_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_AM21C, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_MJPEG, - .min_buffers = 4, - .max_buffers = 4, -@@ -163,6 +185,16 @@ static const struct amvdec_format vdec_formats_gxl[] = { - - static const struct amvdec_format vdec_formats_gxm[] = { - { -+ .pixfmt = V4L2_PIX_FMT_HEVC, -+ .min_buffers = 16, -+ .max_buffers = 24, -+ .max_width = 3840, -+ .max_height = 2160, -+ .vdec_ops = &vdec_hevc_ops, -+ .codec_ops = &codec_hevc_ops, -+ .firmware_path = "meson/gx/vh265_mc", -+ .pixfmts_cap = { V4L2_PIX_FMT_NV12M, V4L2_PIX_FMT_AM21C, 0 }, -+ }, { - .pixfmt = V4L2_PIX_FMT_MJPEG, - .min_buffers = 4, - .max_buffers = 4, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/015_linux-4.18.y-v4l-0015-mpeg4-fixes_and_cleanups.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/015_linux-4.18.y-v4l-0015-mpeg4-fixes_and_cleanups.patch deleted file mode 100644 index 5d3c4c4e7..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/015_linux-4.18.y-v4l-0015-mpeg4-fixes_and_cleanups.patch +++ /dev/null @@ -1,127 +0,0 @@ -From 36c532fff8000ef7a125b9260753a374ec746426 Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Fri, 31 Aug 2018 14:03:23 +0200 -Subject: [PATCH] mpeg4: fixes & cleanups - -* Remove unused registers -* Use constants for bits and masks -* abort on fatal error -* Don't set sess->priv until the end ---- - .../media/platform/meson/vdec/codec_mpeg4.c | 59 +++++++++++-------- - 1 file changed, 33 insertions(+), 26 deletions(-) - -diff --git a/drivers/media/platform/meson/vdec/codec_mpeg4.c b/drivers/media/platform/meson/vdec/codec_mpeg4.c -index c6db2640c91a7..b28e3d477df0d 100644 ---- a/drivers/media/platform/meson/vdec/codec_mpeg4.c -+++ b/drivers/media/platform/meson/vdec/codec_mpeg4.c -@@ -13,18 +13,16 @@ - /* Offset added by firmware, to substract from workspace paddr */ - #define DCAC_BUFF_START_IP 0x02b00000 - --/* map FW registers to known MPEG4 functions */ --#define MP4_PIC_RATIO AV_SCRATCH_5 --#define MP4_ERR_COUNT AV_SCRATCH_6 --#define MP4_PIC_WH AV_SCRATCH_7 --#define MREG_BUFFERIN AV_SCRATCH_8 --#define MREG_BUFFEROUT AV_SCRATCH_9 --#define MP4_NOT_CODED_CNT AV_SCRATCH_A --#define MP4_VOP_TIME_INC AV_SCRATCH_B --#define MP4_OFFSET_REG AV_SCRATCH_C --#define MP4_SYS_RATE AV_SCRATCH_E --#define MEM_OFFSET_REG AV_SCRATCH_F --#define MREG_FATAL_ERROR AV_SCRATCH_L -+/* map firmware registers to known MPEG4 functions */ -+#define MREG_BUFFERIN AV_SCRATCH_8 -+#define MREG_BUFFEROUT AV_SCRATCH_9 -+#define MP4_NOT_CODED_CNT AV_SCRATCH_A -+#define MEM_OFFSET_REG AV_SCRATCH_F -+#define MREG_FATAL_ERROR AV_SCRATCH_L -+ -+#define BUF_IDX_MASK GENMASK(2, 0) -+#define INTERLACE_FLAG BIT(7) -+#define TOP_FIELD_FIRST_FLAG BIT(6) - - struct codec_mpeg4 { - /* Buffer for the MPEG4 Workspace */ -@@ -39,7 +37,7 @@ static int codec_mpeg4_can_recycle(struct amvdec_core *core) - - static void codec_mpeg4_recycle(struct amvdec_core *core, u32 buf_idx) - { -- amvdec_write_dos(core, MREG_BUFFERIN, ~(1 << buf_idx)); -+ amvdec_write_dos(core, MREG_BUFFERIN, ~BIT(buf_idx)); - } - - static int codec_mpeg4_start(struct amvdec_session *sess) { -@@ -51,8 +49,6 @@ static int codec_mpeg4_start(struct amvdec_session *sess) { - if (!mpeg4) - return -ENOMEM; - -- sess->priv = mpeg4; -- - /* Allocate some memory for the MPEG4 decoder's state */ - mpeg4->workspace_vaddr = dma_alloc_coherent(core->dev, SIZE_WORKSPACE, - &mpeg4->workspace_paddr, -@@ -63,6 +59,7 @@ static int codec_mpeg4_start(struct amvdec_session *sess) { - goto free_mpeg4; - } - -+ /* Canvas regs: AV_SCRATCH_0-AV_SCRATCH_4;AV_SCRATCH_G-AV_SCRATCH_J */ - amvdec_set_canvases(sess, (u32[]){ AV_SCRATCH_0, AV_SCRATCH_G, 0 }, - (u32[]){ 4, 4, 0 }); - -@@ -75,6 +72,8 @@ static int codec_mpeg4_start(struct amvdec_session *sess) { - amvdec_write_dos(core, MREG_FATAL_ERROR, 0); - amvdec_write_dos(core, MDEC_PIC_DC_THRESH, 0x404038aa); - -+ sess->priv = mpeg4; -+ - return 0; - - free_mpeg4: -@@ -99,26 +98,34 @@ static int codec_mpeg4_stop(struct amvdec_session *sess) - - static irqreturn_t codec_mpeg4_isr(struct amvdec_session *sess) - { -+ struct amvdec_core *core = sess->core; - u32 reg; - u32 buffer_index; -- struct amvdec_core *core = sess->core; -+ u32 field = V4L2_FIELD_NONE; - - reg = amvdec_read_dos(core, MREG_FATAL_ERROR); -- if (reg == 1) -+ if (reg == 1) { - dev_err(core->dev, "mpeg4 fatal error\n"); -+ amvdec_abort(sess); -+ return IRQ_HANDLED; -+ } - - reg = amvdec_read_dos(core, MREG_BUFFEROUT); -- if (reg) { -- sess->keyframe_found = 1; -- amvdec_read_dos(core, MP4_NOT_CODED_CNT); -- amvdec_read_dos(core, MP4_VOP_TIME_INC); -- buffer_index = reg & 0x7; -- amvdec_dst_buf_done_idx(sess, buffer_index, V4L2_FIELD_NONE); -- amvdec_write_dos(core, MREG_BUFFEROUT, 0); -- } -+ if (!reg) -+ goto end; - -- amvdec_write_dos(core, ASSIST_MBOX1_CLR_REG, 1); -+ sess->keyframe_found = 1; -+ buffer_index = reg & BUF_IDX_MASK; -+ if (reg & INTERLACE_FLAG) -+ field = (reg & TOP_FIELD_FIRST_FLAG) ? -+ V4L2_FIELD_INTERLACED_TB : -+ V4L2_FIELD_INTERLACED_BT; - -+ amvdec_dst_buf_done_idx(sess, buffer_index, field); -+ amvdec_write_dos(core, MREG_BUFFEROUT, 0); -+ -+end: -+ amvdec_write_dos(core, ASSIST_MBOX1_CLR_REG, 1); - return IRQ_HANDLED; - } - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/016_linux-4.18.y-v4l-0016-h.264-fixes_and_cleanups.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/016_linux-4.18.y-v4l-0016-h.264-fixes_and_cleanups.patch deleted file mode 100644 index 07985c9f4..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/016_linux-4.18.y-v4l-0016-h.264-fixes_and_cleanups.patch +++ /dev/null @@ -1,117 +0,0 @@ -From 89c2edfb991fb85fab722d087e98a40758f8ff8c Mon Sep 17 00:00:00 2001 -From: Maxime Jourdan -Date: Fri, 31 Aug 2018 14:04:10 +0200 -Subject: [PATCH] H.264: fixes & cleanups - -* fix GXL and GXM max width/height -* 80+ lines -* remove unused defines ---- - .../media/platform/meson/vdec/codec_h264.c | 24 +++++++++---------- - .../media/platform/meson/vdec/vdec_platform.c | 8 +++---- - 2 files changed, 15 insertions(+), 17 deletions(-) - -diff --git a/drivers/media/platform/meson/vdec/codec_h264.c b/drivers/media/platform/meson/vdec/codec_h264.c -index 7c47ec35efa54..decd3c601cde3 100644 ---- a/drivers/media/platform/meson/vdec/codec_h264.c -+++ b/drivers/media/platform/meson/vdec/codec_h264.c -@@ -28,14 +28,8 @@ - #define CMD_BAD_HEIGHT 8 - - /* Picture type */ --#define PIC_SINGLE_FRAME 0 --#define PIC_TOP_BOT_TOP 1 --#define PIC_BOT_TOP_BOT 2 --#define PIC_DOUBLE_FRAME 3 --#define PIC_TRIPLE_FRAME 4 - #define PIC_TOP_BOT 5 - #define PIC_BOT_TOP 6 --#define PIC_INVALID 7 - - /* Size of Motion Vector per macroblock */ - #define MB_MV_SIZE 96 -@@ -84,16 +78,16 @@ static int codec_h264_start(struct amvdec_session *sess) { - struct codec_h264 *h264 = sess->priv; - - /* Allocate some memory for the H.264 decoder's state */ -- h264->workspace_vaddr = -- dma_alloc_coherent(core->dev, SIZE_WORKSPACE, &h264->workspace_paddr, GFP_KERNEL); -+ h264->workspace_vaddr = dma_alloc_coherent(core->dev, SIZE_WORKSPACE, -+ &h264->workspace_paddr, GFP_KERNEL); - if (!h264->workspace_vaddr) { - dev_err(core->dev, "Failed to alloc H.264 Workspace\n"); - return -ENOMEM; - } - - /* Allocate some memory for the H.264 SEI dump */ -- h264->sei_vaddr = -- dma_alloc_coherent(core->dev, SIZE_SEI, &h264->sei_paddr, GFP_KERNEL); -+ h264->sei_vaddr = dma_alloc_coherent(core->dev, SIZE_SEI, -+ &h264->sei_paddr, GFP_KERNEL); - if (!h264->sei_vaddr) { - dev_err(core->dev, "Failed to alloc H.264 SEI\n"); - return -ENOMEM; -@@ -114,7 +108,9 @@ static int codec_h264_start(struct amvdec_session *sess) { - amvdec_write_dos(core, AV_SCRATCH_9, 0); - - /* Enable "error correction" */ -- amvdec_write_dos(core, AV_SCRATCH_F, (amvdec_read_dos(core, AV_SCRATCH_F) & 0xffffffc3) | BIT(4) | BIT(7)); -+ amvdec_write_dos(core, AV_SCRATCH_F, -+ (amvdec_read_dos(core, AV_SCRATCH_F) & 0xffffffc3) | -+ BIT(4) | BIT(7)); - - amvdec_write_dos(core, MDEC_PIC_DC_THRESH, 0x404038aa); - -@@ -145,7 +141,8 @@ static int codec_h264_stop(struct amvdec_session *sess) - return 0; - } - --static int codec_h264_load_extended_firmware(struct amvdec_session *sess, const u8 *data, u32 len) -+static int codec_h264_load_extended_firmware(struct amvdec_session *sess, -+ const u8 *data, u32 len) - { - struct codec_h264 *h264; - struct amvdec_core *core = sess->core; -@@ -160,7 +157,7 @@ static int codec_h264_load_extended_firmware(struct amvdec_session *sess, const - return -EINVAL; - - h264->ext_fw_vaddr = dma_alloc_coherent(core->dev, SIZE_EXT_FW, -- &h264->ext_fw_paddr, GFP_KERNEL); -+ &h264->ext_fw_paddr, GFP_KERNEL); - if (!h264->ext_fw_vaddr) { - dev_err(core->dev, "Failed to alloc H.264 extended fw\n"); - return -ENOMEM; -@@ -275,6 +272,7 @@ static void codec_h264_frames_ready(struct amvdec_session *sess, u32 status) - - amvdec_dst_buf_done_idx(sess, buffer_index, field); - -+ /* 2 src packets per dst frame ; delete additional timestamp */ - if (field != V4L2_FIELD_NONE && !h264->received_0) - amvdec_rm_first_ts(sess); - -diff --git a/drivers/media/platform/meson/vdec/vdec_platform.c b/drivers/media/platform/meson/vdec/vdec_platform.c -index a8d03426e53d0..99dd3ae9c463b 100644 ---- a/drivers/media/platform/meson/vdec/vdec_platform.c -+++ b/drivers/media/platform/meson/vdec/vdec_platform.c -@@ -154,8 +154,8 @@ static const struct amvdec_format vdec_formats_gxl[] = { - .pixfmt = V4L2_PIX_FMT_H264, - .min_buffers = 21, - .max_buffers = 24, -- .max_width = 1920, -- .max_height = 1080, -+ .max_width = 3840, -+ .max_height = 2160, - .vdec_ops = &vdec_1_ops, - .codec_ops = &codec_h264_ops, - .firmware_path = "meson/gxl/vh264_mc", -@@ -238,8 +238,8 @@ static const struct amvdec_format vdec_formats_gxm[] = { - .pixfmt = V4L2_PIX_FMT_H264, - .min_buffers = 21, - .max_buffers = 24, -- .max_width = 1920, -- .max_height = 1080, -+ .max_width = 3840, -+ .max_height = 2160, - .vdec_ops = &vdec_1_ops, - .codec_ops = &codec_h264_ops, - .firmware_path = "meson/gxm/vh264_mc", diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/017_linux-4.18.y-v4l-1001-WIP-drm-meson-support_overlay_plane_for_video_rendering.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/017_linux-4.18.y-v4l-1001-WIP-drm-meson-support_overlay_plane_for_video_rendering.patch deleted file mode 100644 index f688e981c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/017_linux-4.18.y-v4l-1001-WIP-drm-meson-support_overlay_plane_for_video_rendering.patch +++ /dev/null @@ -1,1146 +0,0 @@ -From e7d20033306bbbb66fd83fb98795e573d70d8f7b Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Thu, 2 Aug 2018 10:00:01 +0200 -Subject: [PATCH] [WIP] drm/meson: Support Overlay plane for video rendering - -The Amlogic Meson GX SoCs support an Overlay plane behind the primary -plan for video rendering. -This Overlay plane support various YUV layouts and a non-alpha RGB32 -layout. ---- - drivers/gpu/drm/meson/Makefile | 2 +- - drivers/gpu/drm/meson/meson_crtc.c | 172 ++++++- - drivers/gpu/drm/meson/meson_drv.c | 14 + - drivers/gpu/drm/meson/meson_drv.h | 52 +++ - drivers/gpu/drm/meson/meson_overlay.c | 595 ++++++++++++++++++++++++ - drivers/gpu/drm/meson/meson_overlay.h | 14 + - drivers/gpu/drm/meson/meson_registers.h | 3 + - drivers/gpu/drm/meson/meson_viu.c | 15 + - drivers/gpu/drm/meson/meson_vpp.c | 44 +- - drivers/soc/amlogic/meson-gx-pwrc-vpu.c | 8 +- - 10 files changed, 912 insertions(+), 7 deletions(-) - create mode 100644 drivers/gpu/drm/meson/meson_overlay.c - create mode 100644 drivers/gpu/drm/meson/meson_overlay.h - -diff --git a/drivers/gpu/drm/meson/Makefile b/drivers/gpu/drm/meson/Makefile -index bd67429185ff7..d4ea82fc493b6 100644 ---- a/drivers/gpu/drm/meson/Makefile -+++ b/drivers/gpu/drm/meson/Makefile -@@ -1,5 +1,5 @@ - meson-drm-y := meson_drv.o meson_plane.o meson_crtc.o meson_venc_cvbs.o --meson-drm-y += meson_viu.o meson_vpp.o meson_venc.o meson_vclk.o -+meson-drm-y += meson_viu.o meson_vpp.o meson_venc.o meson_vclk.o meson_overlay.o - - obj-$(CONFIG_DRM_MESON) += meson-drm.o - obj-$(CONFIG_DRM_MESON_DW_HDMI) += meson_dw_hdmi.o -diff --git a/drivers/gpu/drm/meson/meson_crtc.c b/drivers/gpu/drm/meson/meson_crtc.c -index 1ca9c6c45f9b9..a4b9463f8125a 100644 ---- a/drivers/gpu/drm/meson/meson_crtc.c -+++ b/drivers/gpu/drm/meson/meson_crtc.c -@@ -25,6 +25,7 @@ - #include - #include - #include -+#include - #include - #include - #include -@@ -97,6 +98,10 @@ static void meson_crtc_atomic_enable(struct drm_crtc *crtc, - writel(crtc_state->mode.hdisplay, - priv->io_base + _REG(VPP_POSTBLEND_H_SIZE)); - -+ /* VD1 Preblend vertical start/end */ -+ writel(FIELD_PREP(GENMASK(11, 0), 2303), -+ priv->io_base + _REG(VPP_PREBLEND_VD1_V_START_END)); -+ - writel_bits_relaxed(VPP_POSTBLEND_ENABLE, VPP_POSTBLEND_ENABLE, - priv->io_base + _REG(VPP_MISC)); - -@@ -109,11 +114,17 @@ static void meson_crtc_atomic_disable(struct drm_crtc *crtc, - struct meson_crtc *meson_crtc = to_meson_crtc(crtc); - struct meson_drm *priv = meson_crtc->priv; - -+ DRM_DEBUG_DRIVER("\n"); -+ - priv->viu.osd1_enabled = false; - priv->viu.osd1_commit = false; - -+ priv->viu.vd1_enabled = false; -+ priv->viu.vd1_commit = false; -+ - /* Disable VPP Postblend */ -- writel_bits_relaxed(VPP_POSTBLEND_ENABLE, 0, -+ writel_bits_relaxed(VPP_OSD1_POSTBLEND | VPP_VD1_POSTBLEND | -+ VPP_VD1_PREBLEND | VPP_POSTBLEND_ENABLE, 0, - priv->io_base + _REG(VPP_MISC)); - - if (crtc->state->event && !crtc->state->active) { -@@ -148,6 +159,7 @@ static void meson_crtc_atomic_flush(struct drm_crtc *crtc, - struct meson_drm *priv = meson_crtc->priv; - - priv->viu.osd1_commit = true; -+ priv->viu.vd1_commit = true; - } - - static const struct drm_crtc_helper_funcs meson_crtc_helper_funcs = { -@@ -204,6 +216,164 @@ void meson_crtc_irq(struct meson_drm *priv) - priv->viu.osd1_commit = false; - } - -+ /* Update the VD1 registers */ -+ if (priv->viu.vd1_enabled && priv->viu.vd1_commit) { -+ -+ switch (priv->viu.vd1_planes) { -+ case 3: -+ meson_canvas_config(priv->canvas, priv->canvas_id_vd1_2, -+ priv->viu.vd1_addr2, priv->viu.vd1_stride2, -+ priv->viu.vd1_height2, MESON_CANVAS_WRAP_NONE, -+ MESON_CANVAS_BLKMODE_LINEAR, MESON_CANVAS_ENDIAN_SWAP64); -+ case 2: -+ meson_canvas_config(priv->canvas, priv->canvas_id_vd1_1, -+ priv->viu.vd1_addr1, priv->viu.vd1_stride1, -+ priv->viu.vd1_height1, MESON_CANVAS_WRAP_NONE, -+ MESON_CANVAS_BLKMODE_LINEAR, MESON_CANVAS_ENDIAN_SWAP64); -+ case 1: -+ meson_canvas_config(priv->canvas, priv->canvas_id_vd1_0, -+ priv->viu.vd1_addr0, priv->viu.vd1_stride0, -+ priv->viu.vd1_height0, MESON_CANVAS_WRAP_NONE, -+ MESON_CANVAS_BLKMODE_LINEAR, MESON_CANVAS_ENDIAN_SWAP64); -+ }; -+ -+ writel_relaxed(priv->viu.vd1_if0_gen_reg, -+ priv->io_base + _REG(VD1_IF0_GEN_REG)); -+ writel_relaxed(priv->viu.vd1_if0_gen_reg, -+ priv->io_base + _REG(VD2_IF0_GEN_REG)); -+ writel_relaxed(priv->viu.vd1_if0_gen_reg2, -+ priv->io_base + _REG(VD1_IF0_GEN_REG2)); -+ writel_relaxed(priv->viu.viu_vd1_fmt_ctrl, -+ priv->io_base + _REG(VIU_VD1_FMT_CTRL)); -+ writel_relaxed(priv->viu.viu_vd1_fmt_ctrl, -+ priv->io_base + _REG(VIU_VD2_FMT_CTRL)); -+ writel_relaxed(priv->viu.viu_vd1_fmt_w, -+ priv->io_base + _REG(VIU_VD1_FMT_W)); -+ writel_relaxed(priv->viu.viu_vd1_fmt_w, -+ priv->io_base + _REG(VIU_VD2_FMT_W)); -+ writel_relaxed(priv->viu.vd1_if0_canvas0, -+ priv->io_base + _REG(VD1_IF0_CANVAS0)); -+ writel_relaxed(priv->viu.vd1_if0_canvas0, -+ priv->io_base + _REG(VD1_IF0_CANVAS1)); -+ writel_relaxed(priv->viu.vd1_if0_canvas0, -+ priv->io_base + _REG(VD2_IF0_CANVAS0)); -+ writel_relaxed(priv->viu.vd1_if0_canvas0, -+ priv->io_base + _REG(VD2_IF0_CANVAS1)); -+ writel_relaxed(priv->viu.vd1_if0_luma_x0, -+ priv->io_base + _REG(VD1_IF0_LUMA_X0)); -+ writel_relaxed(priv->viu.vd1_if0_luma_x0, -+ priv->io_base + _REG(VD1_IF0_LUMA_X1)); -+ writel_relaxed(priv->viu.vd1_if0_luma_x0, -+ priv->io_base + _REG(VD2_IF0_LUMA_X0)); -+ writel_relaxed(priv->viu.vd1_if0_luma_x0, -+ priv->io_base + _REG(VD2_IF0_LUMA_X1)); -+ writel_relaxed(priv->viu.vd1_if0_luma_y0, -+ priv->io_base + _REG(VD1_IF0_LUMA_Y0)); -+ writel_relaxed(priv->viu.vd1_if0_luma_y0, -+ priv->io_base + _REG(VD1_IF0_LUMA_Y1)); -+ writel_relaxed(priv->viu.vd1_if0_luma_y0, -+ priv->io_base + _REG(VD2_IF0_LUMA_Y0)); -+ writel_relaxed(priv->viu.vd1_if0_luma_y0, -+ priv->io_base + _REG(VD2_IF0_LUMA_Y1)); -+ writel_relaxed(priv->viu.vd1_if0_chroma_x0, -+ priv->io_base + _REG(VD1_IF0_CHROMA_X0)); -+ writel_relaxed(priv->viu.vd1_if0_chroma_x0, -+ priv->io_base + _REG(VD1_IF0_CHROMA_X1)); -+ writel_relaxed(priv->viu.vd1_if0_chroma_x0, -+ priv->io_base + _REG(VD2_IF0_CHROMA_X0)); -+ writel_relaxed(priv->viu.vd1_if0_chroma_x0, -+ priv->io_base + _REG(VD2_IF0_CHROMA_X1)); -+ writel_relaxed(priv->viu.vd1_if0_chroma_y0, -+ priv->io_base + _REG(VD1_IF0_CHROMA_Y0)); -+ writel_relaxed(priv->viu.vd1_if0_chroma_y0, -+ priv->io_base + _REG(VD1_IF0_CHROMA_Y1)); -+ writel_relaxed(priv->viu.vd1_if0_chroma_y0, -+ priv->io_base + _REG(VD2_IF0_CHROMA_Y0)); -+ writel_relaxed(priv->viu.vd1_if0_chroma_y0, -+ priv->io_base + _REG(VD2_IF0_CHROMA_Y1)); -+ writel_relaxed(priv->viu.vd1_if0_repeat_loop, -+ priv->io_base + _REG(VD1_IF0_RPT_LOOP)); -+ writel_relaxed(priv->viu.vd1_if0_repeat_loop, -+ priv->io_base + _REG(VD2_IF0_RPT_LOOP)); -+ writel_relaxed(priv->viu.vd1_if0_luma0_rpt_pat, -+ priv->io_base + _REG(VD1_IF0_LUMA0_RPT_PAT)); -+ writel_relaxed(priv->viu.vd1_if0_luma0_rpt_pat, -+ priv->io_base + _REG(VD2_IF0_LUMA0_RPT_PAT)); -+ writel_relaxed(priv->viu.vd1_if0_luma0_rpt_pat, -+ priv->io_base + _REG(VD1_IF0_LUMA1_RPT_PAT)); -+ writel_relaxed(priv->viu.vd1_if0_luma0_rpt_pat, -+ priv->io_base + _REG(VD2_IF0_LUMA1_RPT_PAT)); -+ writel_relaxed(priv->viu.vd1_if0_chroma0_rpt_pat, -+ priv->io_base + _REG(VD1_IF0_CHROMA0_RPT_PAT)); -+ writel_relaxed(priv->viu.vd1_if0_chroma0_rpt_pat, -+ priv->io_base + _REG(VD2_IF0_CHROMA0_RPT_PAT)); -+ writel_relaxed(priv->viu.vd1_if0_chroma0_rpt_pat, -+ priv->io_base + _REG(VD1_IF0_CHROMA1_RPT_PAT)); -+ writel_relaxed(priv->viu.vd1_if0_chroma0_rpt_pat, -+ priv->io_base + _REG(VD2_IF0_CHROMA1_RPT_PAT)); -+ writel_relaxed(0, priv->io_base + _REG(VD1_IF0_LUMA_PSEL)); -+ writel_relaxed(0, priv->io_base + _REG(VD1_IF0_CHROMA_PSEL)); -+ writel_relaxed(0, priv->io_base + _REG(VD2_IF0_LUMA_PSEL)); -+ writel_relaxed(0, priv->io_base + _REG(VD2_IF0_CHROMA_PSEL)); -+ writel_relaxed(priv->viu.vd1_range_map_y, -+ priv->io_base + _REG(VD1_IF0_RANGE_MAP_Y)); -+ writel_relaxed(priv->viu.vd1_range_map_cb, -+ priv->io_base + _REG(VD1_IF0_RANGE_MAP_CB)); -+ writel_relaxed(priv->viu.vd1_range_map_cr, -+ priv->io_base + _REG(VD1_IF0_RANGE_MAP_CR)); -+ writel_relaxed(0x78404, -+ priv->io_base + _REG(VPP_SC_MISC)); -+ writel_relaxed(priv->viu.vpp_pic_in_height, -+ priv->io_base + _REG(VPP_PIC_IN_HEIGHT)); -+ writel_relaxed(priv->viu.vpp_postblend_vd1_h_start_end, -+ priv->io_base + _REG(VPP_POSTBLEND_VD1_H_START_END)); -+ writel_relaxed(priv->viu.vpp_blend_vd2_h_start_end, -+ priv->io_base + _REG(VPP_BLEND_VD2_H_START_END)); -+ writel_relaxed(priv->viu.vpp_postblend_vd1_v_start_end, -+ priv->io_base + _REG(VPP_POSTBLEND_VD1_V_START_END)); -+ writel_relaxed(priv->viu.vpp_blend_vd2_v_start_end, -+ priv->io_base + _REG(VPP_BLEND_VD2_V_START_END)); -+ writel_relaxed(priv->viu.vpp_hsc_region12_startp, -+ priv->io_base + _REG(VPP_HSC_REGION12_STARTP)); -+ writel_relaxed(priv->viu.vpp_hsc_region34_startp, -+ priv->io_base + _REG(VPP_HSC_REGION34_STARTP)); -+ writel_relaxed(priv->viu.vpp_hsc_region4_endp, -+ priv->io_base + _REG(VPP_HSC_REGION4_ENDP)); -+ writel_relaxed(priv->viu.vpp_hsc_start_phase_step, -+ priv->io_base + _REG(VPP_HSC_START_PHASE_STEP)); -+ writel_relaxed(priv->viu.vpp_hsc_region1_phase_slope, -+ priv->io_base + _REG(VPP_HSC_REGION1_PHASE_SLOPE)); -+ writel_relaxed(priv->viu.vpp_hsc_region3_phase_slope, -+ priv->io_base + _REG(VPP_HSC_REGION3_PHASE_SLOPE)); -+ writel_relaxed(priv->viu.vpp_line_in_length, -+ priv->io_base + _REG(VPP_LINE_IN_LENGTH)); -+ writel_relaxed(priv->viu.vpp_preblend_h_size, -+ priv->io_base + _REG(VPP_PREBLEND_H_SIZE)); -+ writel_relaxed(priv->viu.vpp_vsc_region12_startp, -+ priv->io_base + _REG(VPP_VSC_REGION12_STARTP)); -+ writel_relaxed(priv->viu.vpp_vsc_region34_startp, -+ priv->io_base + _REG(VPP_VSC_REGION34_STARTP)); -+ writel_relaxed(priv->viu.vpp_vsc_region4_endp, -+ priv->io_base + _REG(VPP_VSC_REGION4_ENDP)); -+ writel_relaxed(priv->viu.vpp_vsc_start_phase_step, -+ priv->io_base + _REG(VPP_VSC_START_PHASE_STEP)); -+ writel_relaxed(priv->viu.vpp_vsc_ini_phase, -+ priv->io_base + _REG(VPP_VSC_INI_PHASE)); -+ writel_relaxed(priv->viu.vpp_vsc_phase_ctrl, -+ priv->io_base + _REG(VPP_VSC_PHASE_CTRL)); -+ writel_relaxed(priv->viu.vpp_hsc_phase_ctrl, -+ priv->io_base + _REG(VPP_HSC_PHASE_CTRL)); -+ writel_relaxed(0x00000042, -+ priv->io_base + _REG(VPP_SCALE_COEF_IDX)); -+ -+ /* Enable VD1 */ -+ writel_bits_relaxed(VPP_VD1_PREBLEND | VPP_VD1_POSTBLEND | VPP_COLOR_MNG_ENABLE, -+ VPP_VD1_PREBLEND | VPP_VD1_POSTBLEND | VPP_COLOR_MNG_ENABLE, -+ priv->io_base + _REG(VPP_MISC)); -+ -+ priv->viu.vd1_commit = false; -+ } -+ - drm_crtc_handle_vblank(priv->crtc); - - spin_lock_irqsave(&priv->drm->event_lock, flags); -diff --git a/drivers/gpu/drm/meson/meson_drv.c b/drivers/gpu/drm/meson/meson_drv.c -index fb5b0e3c5efce..04b634eade20d 100644 ---- a/drivers/gpu/drm/meson/meson_drv.c -+++ b/drivers/gpu/drm/meson/meson_drv.c -@@ -41,6 +41,7 @@ - - #include "meson_drv.h" - #include "meson_plane.h" -+#include "meson_overlay.h" - #include "meson_crtc.h" - #include "meson_venc_cvbs.h" - -@@ -222,6 +223,15 @@ static int meson_drv_bind_master(struct device *dev, bool has_components) - } - - ret = meson_canvas_alloc(priv->canvas, &priv->canvas_id_osd1); -+ if (ret) -+ goto free_drm; -+ ret = meson_canvas_alloc(priv->canvas, &priv->canvas_id_vd1_0); -+ if (ret) -+ goto free_drm; -+ ret = meson_canvas_alloc(priv->canvas, &priv->canvas_id_vd1_1); -+ if (ret) -+ goto free_drm; -+ ret = meson_canvas_alloc(priv->canvas, &priv->canvas_id_vd1_2); - if (ret) - goto free_drm; - -@@ -261,6 +271,10 @@ static int meson_drv_bind_master(struct device *dev, bool has_components) - if (ret) - goto free_drm; - -+ ret = meson_overlay_create(priv); -+ if (ret) -+ goto free_drm; -+ - ret = meson_crtc_create(priv); - if (ret) - goto free_drm; -diff --git a/drivers/gpu/drm/meson/meson_drv.h b/drivers/gpu/drm/meson/meson_drv.h -index 9e902a6df7843..cc2288cc3858e 100644 ---- a/drivers/gpu/drm/meson/meson_drv.h -+++ b/drivers/gpu/drm/meson/meson_drv.h -@@ -33,11 +33,15 @@ struct meson_drm { - - struct meson_canvas *canvas; - u8 canvas_id_osd1; -+ u8 canvas_id_vd1_0; -+ u8 canvas_id_vd1_1; -+ u8 canvas_id_vd1_2; - - struct drm_device *drm; - struct drm_crtc *crtc; - struct drm_fbdev_cma *fbdev; - struct drm_plane *primary_plane; -+ struct drm_plane *overlay_plane; - - /* Components Data */ - struct { -@@ -49,6 +53,54 @@ struct meson_drm { - uint32_t osd1_addr; - uint32_t osd1_stride; - uint32_t osd1_height; -+ -+ bool vd1_enabled; -+ bool vd1_commit; -+ unsigned int vd1_planes; -+ uint32_t vd1_if0_gen_reg; -+ uint32_t vd1_if0_luma_x0; -+ uint32_t vd1_if0_luma_y0; -+ uint32_t vd1_if0_chroma_x0; -+ uint32_t vd1_if0_chroma_y0; -+ uint32_t vd1_if0_repeat_loop; -+ uint32_t vd1_if0_luma0_rpt_pat; -+ uint32_t vd1_if0_chroma0_rpt_pat; -+ uint32_t vd1_range_map_y; -+ uint32_t vd1_range_map_cb; -+ uint32_t vd1_range_map_cr; -+ uint32_t viu_vd1_fmt_w; -+ uint32_t vd1_if0_canvas0; -+ uint32_t vd1_if0_gen_reg2; -+ uint32_t viu_vd1_fmt_ctrl; -+ uint32_t vd1_addr0; -+ uint32_t vd1_addr1; -+ uint32_t vd1_addr2; -+ uint32_t vd1_stride0; -+ uint32_t vd1_stride1; -+ uint32_t vd1_stride2; -+ uint32_t vd1_height0; -+ uint32_t vd1_height1; -+ uint32_t vd1_height2; -+ uint32_t vpp_pic_in_height; -+ uint32_t vpp_postblend_vd1_h_start_end; -+ uint32_t vpp_postblend_vd1_v_start_end; -+ uint32_t vpp_hsc_region12_startp; -+ uint32_t vpp_hsc_region34_startp; -+ uint32_t vpp_hsc_region4_endp; -+ uint32_t vpp_hsc_start_phase_step; -+ uint32_t vpp_hsc_region1_phase_slope; -+ uint32_t vpp_hsc_region3_phase_slope; -+ uint32_t vpp_line_in_length; -+ uint32_t vpp_preblend_h_size; -+ uint32_t vpp_vsc_region12_startp; -+ uint32_t vpp_vsc_region34_startp; -+ uint32_t vpp_vsc_region4_endp; -+ uint32_t vpp_vsc_start_phase_step; -+ uint32_t vpp_vsc_ini_phase; -+ uint32_t vpp_vsc_phase_ctrl; -+ uint32_t vpp_hsc_phase_ctrl; -+ uint32_t vpp_blend_vd2_h_start_end; -+ uint32_t vpp_blend_vd2_v_start_end; - } viu; - - struct { -diff --git a/drivers/gpu/drm/meson/meson_overlay.c b/drivers/gpu/drm/meson/meson_overlay.c -new file mode 100644 -index 0000000000000..ea7261aa2bdd5 ---- /dev/null -+++ b/drivers/gpu/drm/meson/meson_overlay.c -@@ -0,0 +1,595 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Neil Armstrong -+ * Copyright (C) 2015 Amlogic, Inc. All rights reserved. -+ */ -+ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include "meson_overlay.h" -+#include "meson_vpp.h" -+#include "meson_viu.h" -+#include "meson_registers.h" -+ -+/* VD1_IF0_GEN_REG */ -+#define VD_URGENT_CHROMA BIT(28) -+#define VD_URGENT_LUMA BIT(27) -+#define VD_HOLD_LINES(lines) FIELD_PREP(GENMASK(24, 19), lines) -+#define VD_DEMUX_MODE_RGB BIT(16) -+#define VD_BYTES_PER_PIXEL(val) FIELD_PREP(GENMASK(15, 14), val) -+#define VD_CHRO_RPT_LASTL_CTRL BIT(6) -+#define VD_LITTLE_ENDIAN BIT(4) -+#define VD_SEPARATE_EN BIT(1) -+#define VD_ENABLE BIT(0) -+ -+/* VD1_IF0_CANVAS0 */ -+#define CANVAS_ADDR2(addr) FIELD_PREP(GENMASK(23, 16), addr) -+#define CANVAS_ADDR1(addr) FIELD_PREP(GENMASK(15, 8), addr) -+#define CANVAS_ADDR0(addr) FIELD_PREP(GENMASK(7, 0), addr) -+ -+/* VD1_IF0_LUMA_X0 VD1_IF0_CHROMA_X0 */ -+#define VD_X_START(value) FIELD_PREP(GENMASK(14, 0), value) -+#define VD_X_END(value) FIELD_PREP(GENMASK(30, 16), value) -+ -+/* VD1_IF0_LUMA_Y0 VD1_IF0_CHROMA_Y0 */ -+#define VD_Y_START(value) FIELD_PREP(GENMASK(12, 0), value) -+#define VD_Y_END(value) FIELD_PREP(GENMASK(28, 16), value) -+ -+/* VD1_IF0_GEN_REG2 */ -+#define VD_COLOR_MAP(value) FIELD_PREP(GENMASK(1, 0), value) -+ -+/* VIU_VD1_FMT_CTRL */ -+#define VD_HORZ_Y_C_RATIO(value) FIELD_PREP(GENMASK(22, 21), value) -+#define VD_HORZ_FMT_EN BIT(20) -+#define VD_VERT_RPT_LINE0 BIT(16) -+#define VD_VERT_INITIAL_PHASE(value) FIELD_PREP(GENMASK(11, 8), value) -+#define VD_VERT_PHASE_STEP(value) FIELD_PREP(GENMASK(7, 1), value) -+#define VD_VERT_FMT_EN BIT(0) -+ -+/* VPP_POSTBLEND_VD1_H_START_END */ -+#define VD_H_END(value) FIELD_PREP(GENMASK(11, 0), value) -+#define VD_H_START(value) FIELD_PREP(GENMASK(27, 16), value) -+ -+/* VPP_POSTBLEND_VD1_V_START_END */ -+#define VD_V_END(value) FIELD_PREP(GENMASK(11, 0), value) -+#define VD_V_START(value) FIELD_PREP(GENMASK(27, 16), value) -+ -+/* VPP_BLEND_VD2_V_START_END */ -+#define VD2_V_END(value) FIELD_PREP(GENMASK(11, 0), value) -+#define VD2_V_START(value) FIELD_PREP(GENMASK(27, 16), value) -+ -+/* VIU_VD1_FMT_W */ -+#define VD_V_WIDTH(value) FIELD_PREP(GENMASK(11, 0), value) -+#define VD_H_WIDTH(value) FIELD_PREP(GENMASK(27, 16), value) -+ -+/* VPP_HSC_REGION12_STARTP VPP_HSC_REGION34_STARTP */ -+#define VD_REGION24_START(value) FIELD_PREP(GENMASK(11, 0), value) -+#define VD_REGION13_END(value) FIELD_PREP(GENMASK(27, 16), value) -+ -+struct meson_overlay { -+ struct drm_plane base; -+ struct meson_drm *priv; -+}; -+#define to_meson_overlay(x) container_of(x, struct meson_overlay, base) -+ -+#define FRAC_16_16(mult, div) (((mult) << 16) / (div)) -+ -+static int meson_overlay_atomic_check(struct drm_plane *plane, -+ struct drm_plane_state *state) -+{ -+ struct drm_crtc_state *crtc_state; -+ -+ if (!state->crtc) -+ return 0; -+ -+ crtc_state = drm_atomic_get_crtc_state(state->state, state->crtc); -+ if (IS_ERR(crtc_state)) -+ return PTR_ERR(crtc_state); -+ -+ return drm_atomic_helper_check_plane_state(state, crtc_state, -+ FRAC_16_16(1, 5), -+ FRAC_16_16(5, 1), -+ true, true); -+} -+ -+/* Takes a fixed 16.16 number and converts it to integer. */ -+static inline int64_t fixed16_to_int(int64_t value) -+{ -+ return value >> 16; -+} -+ -+static const uint8_t skip_tab[6] = {0x24, 0x04, 0x68, 0x48, 0x28, 0x08}; -+ -+static void meson_overlay_get_vertical_phase(unsigned ratio_y, -+ int *phase, -+ int *repeat, -+ bool interlace) -+{ -+ int offset_in = 0; -+ int offset_out = 0; -+ int repeat_skip = 0; -+ -+ if (!interlace && ratio_y > (1 << 18)) { -+ offset_out = (1 * ratio_y) >> 10; -+ } -+ -+ while ((offset_in + (4 << 8)) <= offset_out) { -+ repeat_skip++; -+ offset_in += 4 << 8; -+ } -+ -+ *phase = (offset_out - offset_in) >> 2; -+ -+ if (*phase > 0x100) -+ repeat_skip++; -+ -+ *phase = *phase & 0xff; -+ -+ if (repeat_skip > 5) -+ repeat_skip = 5; -+ -+ *repeat = skip_tab[repeat_skip]; -+} -+ -+static void meson_overlay_setup_scaler_params(struct meson_drm *priv, -+ struct drm_plane *plane, -+ bool interlace_mode) -+{ -+ struct drm_plane_state *state = plane->state; -+ struct drm_crtc_state *crtc_state = priv->crtc->state; -+ int video_top, video_left, video_width, video_height; -+ unsigned int crop_top, crop_left; -+ unsigned int crtc_height, crtc_width; -+ unsigned int vd_start_lines, vd_end_lines; -+ unsigned int hd_start_lines, hd_end_lines; -+ unsigned int vsc_startp, vsc_endp; -+ unsigned int hsc_startp, hsc_endp; -+ unsigned int ratio_x, ratio_y; -+ unsigned int w_in, h_in; -+ int vphase, vphase_repeat_skip; -+ int temp_height, temp_width; -+ int temp, start, end; -+ -+ if (!crtc_state) { -+ DRM_ERROR("Invalid crtc_state\n"); -+ return; -+ } -+ -+ crtc_height = crtc_state->mode.vdisplay; -+ crtc_width = crtc_state->mode.hdisplay; -+ -+ w_in = fixed16_to_int(state->src_w); -+ h_in = fixed16_to_int(state->src_h); -+ crop_top = fixed16_to_int(state->src_x); -+ crop_left = fixed16_to_int(state->src_x); -+ -+ video_top = state->crtc_y; -+ video_left = state->crtc_x; -+ video_width = state->crtc_w; -+ video_height = state->crtc_h; -+ -+ DRM_DEBUG("crtc_width %d crtc_height %d interlace %d\n", -+ crtc_width, crtc_height, interlace_mode); -+ DRM_DEBUG("w_in %d h_in %d crop_top %d crop_left %d\n", -+ w_in, h_in, crop_top, crop_left); -+ DRM_DEBUG("video top %d left %d width %d height %d\n", -+ video_top, video_left, video_width, video_height); -+ -+ ratio_x = (w_in << 18) / video_width; -+ ratio_y = (h_in << 18) / video_height; -+ -+ /* TOFIX Interlace output */ -+ if (interlace_mode) -+ ratio_y <<= 1; -+ -+ if (ratio_x * video_width < (w_in << 18)) -+ ratio_x++; -+ -+ DRM_DEBUG("ratio x 0x%x y 0x%x\n", ratio_x, ratio_y); -+ -+ meson_overlay_get_vertical_phase(ratio_y, &vphase, &vphase_repeat_skip, -+ interlace_mode); -+ -+ DRM_DEBUG("vphase 0x%x skip %d\n", vphase, vphase_repeat_skip); -+ -+ /* Vertical */ -+ -+ start = video_top + video_height / 2 - ((h_in << 17) / ratio_x); -+ end = (h_in << 18) / ratio_y + start - 1; -+ -+ if (video_top < 0 && start < 0) -+ vd_start_lines = (-(start) * ratio_y) >> 18; -+ else if (start < video_top) -+ vd_start_lines = ((video_top - start) * ratio_y) >> 18; -+ else -+ vd_start_lines = 0; -+ -+ if (video_top < 0) -+ temp_height = min_t(unsigned int, (video_top + video_height - 1), -+ (crtc_height - 1)); -+ else -+ temp_height = min_t(unsigned int, (video_top + video_height - 1), -+ (crtc_height - 1)) - video_top + 1; -+ -+ temp = vd_start_lines + (temp_height * ratio_y >> 18); -+ vd_end_lines = (temp <= (h_in - 1)) ? temp : (h_in - 1); -+ -+ vd_start_lines += crop_left; -+ vd_end_lines += crop_left; -+ -+ if (interlace_mode) { -+ start >>= 1; -+ end >>= 1; -+ } -+ -+ vsc_startp = max_t(int, start, -+ max_t(int, 0, video_top)); -+ vsc_endp = min_t(int, end, -+ min_t(int, crtc_height - 1, -+ video_top + video_height - 1)); -+ -+ DRM_DEBUG("vsc startp %d endp %d start_lines %d end_lines %d\n", -+ vsc_startp, vsc_endp, vd_start_lines, vd_end_lines); -+ -+ /* Horizontal */ -+ -+ start = video_left + video_width / 2 - ((w_in << 17) / ratio_x); -+ end = (w_in << 18) / ratio_x + start - 1; -+ -+ if (video_left < 0 && start < 0) -+ hd_start_lines = (-(start) * ratio_x) >> 18; -+ else if (start < video_left) -+ hd_start_lines = ((video_left - start) * ratio_x) >> 18; -+ else -+ hd_start_lines = 0; -+ -+ if (video_left < 0) -+ temp_width = min_t(unsigned int, (video_left + video_width - 1), -+ (crtc_width - 1)); -+ else -+ temp_width = min_t(unsigned int, (video_left + video_width - 1), -+ (crtc_width - 1)) - video_left + 1; -+ -+ temp = hd_start_lines + (temp_width * ratio_x >> 18); -+ hd_end_lines = (temp <= (w_in - 1)) ? temp : (w_in - 1); -+ -+ priv->viu.vpp_line_in_length = hd_end_lines - hd_start_lines + 1; -+ hsc_startp = max_t(int, start, -+ max_t(int, 0, video_left)); -+ hsc_endp = min_t(int, end, -+ min_t(int, crtc_width - 1, -+ video_left + video_width - 1)); -+ -+ hd_start_lines += crop_top; -+ hd_end_lines += crop_top; -+ -+ DRM_DEBUG("hsc startp %d endp %d start_lines %d end_lines %d\n", -+ hsc_startp, hsc_endp, hd_start_lines, hd_end_lines); -+ -+ priv->viu.vpp_vsc_start_phase_step = ratio_y << 6; -+ -+ priv->viu.vpp_vsc_ini_phase = vphase << 8; -+ priv->viu.vpp_vsc_phase_ctrl = (1 << 13) | (4 << 8) | -+ vphase_repeat_skip; -+ -+ priv->viu.vd1_if0_luma_x0 = VD_X_START(hd_start_lines) | -+ VD_X_END(hd_end_lines); -+ priv->viu.vd1_if0_chroma_x0 = VD_X_START(hd_start_lines >> 1) | -+ VD_X_END(hd_end_lines >> 1); -+ -+ priv->viu.viu_vd1_fmt_w = VD_H_WIDTH(hd_end_lines - hd_start_lines + 1) | -+ VD_V_WIDTH(hd_end_lines/2 - hd_start_lines/2 + 1); -+ -+ priv->viu.vd1_if0_luma_y0 = VD_Y_START(vd_start_lines) | -+ VD_Y_END(vd_end_lines); -+ -+ priv->viu.vd1_if0_chroma_y0 = VD_Y_START(vd_start_lines >> 1) | -+ VD_Y_END(vd_end_lines >> 1); -+ -+ priv->viu.vpp_pic_in_height = h_in; -+ -+ priv->viu.vpp_postblend_vd1_h_start_end = VD_H_START(hsc_startp) | -+ VD_H_END(hsc_endp); -+ priv->viu.vpp_blend_vd2_h_start_end = VD_H_START(hd_start_lines) | -+ VD_H_END(hd_end_lines); -+ priv->viu.vpp_hsc_region12_startp = VD_REGION13_END(0) | -+ VD_REGION24_START(hsc_startp); -+ priv->viu.vpp_hsc_region34_startp = VD_REGION13_END(hsc_startp) | -+ VD_REGION24_START(hsc_endp - hsc_startp); -+ priv->viu.vpp_hsc_region4_endp = hsc_endp - hsc_startp; -+ priv->viu.vpp_hsc_start_phase_step = ratio_x << 6; -+ priv->viu.vpp_hsc_region1_phase_slope = 0; -+ priv->viu.vpp_hsc_region3_phase_slope = 0; -+ priv->viu.vpp_hsc_phase_ctrl = (1 << 21) | (4 << 16); -+ -+ priv->viu.vpp_line_in_length = hd_end_lines - hd_start_lines + 1; -+ priv->viu.vpp_preblend_h_size = hd_end_lines - hd_start_lines + 1; -+ -+ priv->viu.vpp_postblend_vd1_v_start_end = VD_V_START(vsc_startp) | -+ VD_V_END(vsc_endp); -+ priv->viu.vpp_blend_vd2_v_start_end = -+ VD2_V_START((vd_end_lines + 1) >> 1) | -+ VD2_V_END(vd_end_lines); -+ -+ priv->viu.vpp_vsc_region12_startp = 0; -+ priv->viu.vpp_vsc_region34_startp = -+ VD_REGION13_END(vsc_endp - vsc_startp) | -+ VD_REGION24_START(vsc_endp - vsc_startp); -+ priv->viu.vpp_vsc_region4_endp = vsc_endp - vsc_startp; -+ priv->viu.vpp_vsc_start_phase_step = ratio_y << 6; -+} -+ -+static void meson_overlay_atomic_update(struct drm_plane *plane, -+ struct drm_plane_state *old_state) -+{ -+ struct meson_overlay *meson_overlay = to_meson_overlay(plane); -+ struct drm_plane_state *state = plane->state; -+ struct drm_framebuffer *fb = state->fb; -+ struct meson_drm *priv = meson_overlay->priv; -+ struct drm_gem_cma_object *gem; -+ unsigned long flags; -+ bool interlace_mode; -+ -+ DRM_DEBUG_DRIVER("\n"); -+ -+ interlace_mode = state->crtc->mode.flags & DRM_MODE_FLAG_INTERLACE; -+ -+ /* -+ * Update Coordinates -+ * Update Formats -+ * Update Buffer -+ * Enable Plane -+ */ -+ spin_lock_irqsave(&priv->drm->event_lock, flags); -+ -+ priv->viu.vd1_if0_gen_reg = VD_URGENT_CHROMA | -+ VD_URGENT_LUMA | -+ VD_HOLD_LINES(9) | -+ VD_CHRO_RPT_LASTL_CTRL | -+ VD_ENABLE; -+ -+ /* Setup scaler params */ -+ meson_overlay_setup_scaler_params(priv, plane, interlace_mode); -+ -+ //VD1_IF0_CANVAS1=0 -+ //VD1_IF0_CHROMA_X1=0 -+ //VD1_IF0_CHROMA_Y1=0 -+ priv->viu.vd1_if0_repeat_loop = 0; -+ priv->viu.vd1_if0_luma0_rpt_pat = interlace_mode ? 8 : 0; -+ priv->viu.vd1_if0_chroma0_rpt_pat = interlace_mode ? 8 : 0; -+ //VD1_IF0_LUMA1_RPT_PAT=0 -+ //VD1_IF0_CHROMA1_RPT_PAT=0 -+ //VD1_IF0_LUMA_PSEL=0 -+ //VD1_IF0_CHROMA_PSEL=0 -+ //VD1_IF0_DUMMY_PIXEL=? -+ priv->viu.vd1_range_map_y = 0; -+ priv->viu.vd1_range_map_cb = 0; -+ priv->viu.vd1_range_map_cr = 0; -+ -+ /* Default values for RGB888/YUV444 */ -+ priv->viu.vd1_if0_gen_reg2 = 0; -+ priv->viu.viu_vd1_fmt_ctrl = 0; -+ -+ switch (fb->format->format) { -+ case DRM_FORMAT_RGB888: -+ /* TOFIX enable RGB2YUV somewhere ! */ -+ priv->viu.vd1_if0_gen_reg |= VD_DEMUX_MODE_RGB | -+ VD_BYTES_PER_PIXEL(2); -+ priv->viu.vd1_if0_canvas0 = -+ CANVAS_ADDR2(priv->canvas_id_vd1_0) | -+ CANVAS_ADDR1(priv->canvas_id_vd1_0) | -+ CANVAS_ADDR0(priv->canvas_id_vd1_0); -+ break; -+ case DRM_FORMAT_YUYV: -+ priv->viu.vd1_if0_gen_reg |= VD_BYTES_PER_PIXEL(1); -+ priv->viu.vd1_if0_canvas0 = -+ CANVAS_ADDR2(priv->canvas_id_vd1_0) | -+ CANVAS_ADDR1(priv->canvas_id_vd1_0) | -+ CANVAS_ADDR0(priv->canvas_id_vd1_0); -+ priv->viu.viu_vd1_fmt_ctrl = VD_HORZ_Y_C_RATIO(1) | /* /2 */ -+ VD_HORZ_FMT_EN | -+ VD_VERT_RPT_LINE0 | -+ VD_VERT_INITIAL_PHASE(12) | -+ VD_VERT_PHASE_STEP(16) | /* /2 */ -+ VD_VERT_FMT_EN; -+ break; -+ case DRM_FORMAT_NV12: -+ case DRM_FORMAT_NV21: -+ priv->viu.vd1_if0_gen_reg |= VD_SEPARATE_EN; -+ priv->viu.vd1_if0_canvas0 = -+ CANVAS_ADDR2(priv->canvas_id_vd1_1) | -+ CANVAS_ADDR1(priv->canvas_id_vd1_1) | -+ CANVAS_ADDR0(priv->canvas_id_vd1_0); -+ if (fb->format->format == DRM_FORMAT_NV12) -+ priv->viu.vd1_if0_gen_reg2 = VD_COLOR_MAP(1); -+ else -+ priv->viu.vd1_if0_gen_reg2 = VD_COLOR_MAP(2); -+ priv->viu.viu_vd1_fmt_ctrl = VD_HORZ_Y_C_RATIO(1) | /* /2 */ -+ VD_HORZ_FMT_EN | -+ VD_VERT_RPT_LINE0 | -+ VD_VERT_INITIAL_PHASE(12) | -+ VD_VERT_PHASE_STEP(8) | /* /4 */ -+ VD_VERT_FMT_EN; -+ break; -+ case DRM_FORMAT_YUV444: -+ case DRM_FORMAT_YUV422: -+ case DRM_FORMAT_YUV420: -+ case DRM_FORMAT_YUV411: -+ case DRM_FORMAT_YUV410: -+ priv->viu.vd1_if0_gen_reg |= VD_SEPARATE_EN; -+ priv->viu.vd1_if0_canvas0 = -+ CANVAS_ADDR2(priv->canvas_id_vd1_2) | -+ CANVAS_ADDR1(priv->canvas_id_vd1_1) | -+ CANVAS_ADDR0(priv->canvas_id_vd1_0); -+ switch (fb->format->format) { -+ case DRM_FORMAT_YUV422: -+ priv->viu.viu_vd1_fmt_ctrl = -+ VD_HORZ_Y_C_RATIO(1) | /* /2 */ -+ VD_HORZ_FMT_EN | -+ VD_VERT_RPT_LINE0 | -+ VD_VERT_INITIAL_PHASE(12) | -+ VD_VERT_PHASE_STEP(16) | /* /2 */ -+ VD_VERT_FMT_EN; -+ break; -+ case DRM_FORMAT_YUV420: -+ priv->viu.viu_vd1_fmt_ctrl = -+ VD_HORZ_Y_C_RATIO(1) | /* /2 */ -+ VD_HORZ_FMT_EN | -+ VD_VERT_RPT_LINE0 | -+ VD_VERT_INITIAL_PHASE(12) | -+ VD_VERT_PHASE_STEP(8) | /* /4 */ -+ VD_VERT_FMT_EN; -+ break; -+ case DRM_FORMAT_YUV411: -+ priv->viu.viu_vd1_fmt_ctrl = -+ VD_HORZ_Y_C_RATIO(2) | /* /4 */ -+ VD_HORZ_FMT_EN | -+ VD_VERT_RPT_LINE0 | -+ VD_VERT_INITIAL_PHASE(12) | -+ VD_VERT_PHASE_STEP(16) | /* /2 */ -+ VD_VERT_FMT_EN; -+ break; -+ case DRM_FORMAT_YUV410: -+ priv->viu.viu_vd1_fmt_ctrl = -+ VD_HORZ_Y_C_RATIO(2) | /* /4 */ -+ VD_HORZ_FMT_EN | -+ VD_VERT_RPT_LINE0 | -+ VD_VERT_INITIAL_PHASE(12) | -+ VD_VERT_PHASE_STEP(8) | /* /4 */ -+ VD_VERT_FMT_EN; -+ break; -+ } -+ break; -+ } -+ -+ /* Update Canvas with buffer address */ -+ priv->viu.vd1_planes = drm_format_num_planes(fb->format->format); -+ -+ switch (priv->viu.vd1_planes) { -+ case 3: -+ gem = drm_fb_cma_get_gem_obj(fb, 2); -+ priv->viu.vd1_addr2 = gem->paddr + fb->offsets[2]; -+ priv->viu.vd1_stride2 = fb->pitches[2]; -+ priv->viu.vd1_height2 = -+ drm_format_plane_height(fb->height, -+ fb->format->format, 2); -+ DRM_DEBUG("plane 2 addr 0x%x stride %d height %d\n", -+ priv->viu.vd1_addr2, -+ priv->viu.vd1_stride2, -+ priv->viu.vd1_height2); -+ case 2: -+ gem = drm_fb_cma_get_gem_obj(fb, 1); -+ priv->viu.vd1_addr1 = gem->paddr + fb->offsets[1]; -+ priv->viu.vd1_stride1 = fb->pitches[1]; -+ priv->viu.vd1_height1 = -+ drm_format_plane_height(fb->height, -+ fb->format->format, 1); -+ DRM_DEBUG("plane 1 addr 0x%x stride %d height %d\n", -+ priv->viu.vd1_addr1, -+ priv->viu.vd1_stride1, -+ priv->viu.vd1_height1); -+ case 1: -+ gem = drm_fb_cma_get_gem_obj(fb, 0); -+ priv->viu.vd1_addr0 = gem->paddr + fb->offsets[0]; -+ priv->viu.vd1_stride0 = fb->pitches[0]; -+ priv->viu.vd1_height0 = -+ drm_format_plane_height(fb->height, -+ fb->format->format, 0); -+ DRM_DEBUG("plane 0 addr 0x%x stride %d height %d\n", -+ priv->viu.vd1_addr0, -+ priv->viu.vd1_stride0, -+ priv->viu.vd1_height0); -+ } -+ -+ priv->viu.vd1_enabled = true; -+ -+ spin_unlock_irqrestore(&priv->drm->event_lock, flags); -+ -+ DRM_DEBUG_DRIVER("\n"); -+} -+ -+static void meson_overlay_atomic_disable(struct drm_plane *plane, -+ struct drm_plane_state *old_state) -+{ -+ struct meson_overlay *meson_overlay = to_meson_overlay(plane); -+ struct meson_drm *priv = meson_overlay->priv; -+ -+ DRM_DEBUG_DRIVER("\n"); -+ -+ priv->viu.vd1_enabled = false; -+ -+ /* Disable VD1 */ -+ writel_bits_relaxed(VPP_VD1_POSTBLEND | VPP_VD1_PREBLEND, 0, -+ priv->io_base + _REG(VPP_MISC)); -+ -+} -+ -+static const struct drm_plane_helper_funcs meson_overlay_helper_funcs = { -+ .atomic_check = meson_overlay_atomic_check, -+ .atomic_disable = meson_overlay_atomic_disable, -+ .atomic_update = meson_overlay_atomic_update, -+}; -+ -+static const struct drm_plane_funcs meson_overlay_funcs = { -+ .update_plane = drm_atomic_helper_update_plane, -+ .disable_plane = drm_atomic_helper_disable_plane, -+ .destroy = drm_plane_cleanup, -+ .reset = drm_atomic_helper_plane_reset, -+ .atomic_duplicate_state = drm_atomic_helper_plane_duplicate_state, -+ .atomic_destroy_state = drm_atomic_helper_plane_destroy_state, -+}; -+ -+static const uint32_t supported_drm_formats[] = { -+ DRM_FORMAT_RGB888, -+ DRM_FORMAT_YUYV, -+ DRM_FORMAT_NV12, -+ DRM_FORMAT_NV21, -+ DRM_FORMAT_YUV444, -+ DRM_FORMAT_YUV422, -+ DRM_FORMAT_YUV420, -+ DRM_FORMAT_YUV411, -+ DRM_FORMAT_YUV410, -+}; -+ -+int meson_overlay_create(struct meson_drm *priv) -+{ -+ struct meson_overlay *meson_overlay; -+ struct drm_plane *plane; -+ -+ DRM_DEBUG_DRIVER("\n"); -+ -+ meson_overlay = devm_kzalloc(priv->drm->dev, sizeof(*meson_overlay), -+ GFP_KERNEL); -+ if (!meson_overlay) -+ return -ENOMEM; -+ -+ meson_overlay->priv = priv; -+ plane = &meson_overlay->base; -+ -+ drm_universal_plane_init(priv->drm, plane, 0xFF, -+ &meson_overlay_funcs, -+ supported_drm_formats, -+ ARRAY_SIZE(supported_drm_formats), -+ NULL, -+ DRM_PLANE_TYPE_OVERLAY, "meson_overlay_plane"); -+ -+ drm_plane_helper_add(plane, &meson_overlay_helper_funcs); -+ -+ priv->overlay_plane = plane; -+ -+ DRM_DEBUG_DRIVER("\n"); -+ -+ return 0; -+} -diff --git a/drivers/gpu/drm/meson/meson_overlay.h b/drivers/gpu/drm/meson/meson_overlay.h -new file mode 100644 -index 0000000000000..0fd63dabcb964 ---- /dev/null -+++ b/drivers/gpu/drm/meson/meson_overlay.h -@@ -0,0 +1,14 @@ -+// SPDX-License-Identifier: GPL-2.0+ -+/* -+ * Copyright (C) 2018 BayLibre, SAS -+ * Author: Neil Armstrong -+ */ -+ -+#ifndef __MESON_OVERLAY_H -+#define __MESON_OVERLAY_H -+ -+#include "meson_drv.h" -+ -+int meson_overlay_create(struct meson_drm *priv); -+ -+#endif /* __MESON_OVERLAY_H */ -diff --git a/drivers/gpu/drm/meson/meson_registers.h b/drivers/gpu/drm/meson/meson_registers.h -index bca87143e5488..5c7e02c703bc7 100644 ---- a/drivers/gpu/drm/meson/meson_registers.h -+++ b/drivers/gpu/drm/meson/meson_registers.h -@@ -286,6 +286,7 @@ - #define VIU_OSD1_MATRIX_COEF22_30 0x1a9d - #define VIU_OSD1_MATRIX_COEF31_32 0x1a9e - #define VIU_OSD1_MATRIX_COEF40_41 0x1a9f -+#define VD1_IF0_GEN_REG3 0x1aa7 - #define VIU_OSD1_EOTF_CTL 0x1ad4 - #define VIU_OSD1_EOTF_COEF00_01 0x1ad5 - #define VIU_OSD1_EOTF_COEF02_10 0x1ad6 -@@ -297,6 +298,7 @@ - #define VIU_OSD1_OETF_CTL 0x1adc - #define VIU_OSD1_OETF_LUT_ADDR_PORT 0x1add - #define VIU_OSD1_OETF_LUT_DATA_PORT 0x1ade -+#define AFBC_ENABLE 0x1ae0 - - /* vpp */ - #define VPP_DUMMY_DATA 0x1d00 -@@ -349,6 +351,7 @@ - #define VPP_VD2_PREBLEND BIT(15) - #define VPP_OSD1_PREBLEND BIT(16) - #define VPP_OSD2_PREBLEND BIT(17) -+#define VPP_COLOR_MNG_ENABLE BIT(28) - #define VPP_OFIFO_SIZE 0x1d27 - #define VPP_FIFO_STATUS 0x1d28 - #define VPP_SMOKE_CTRL 0x1d29 -diff --git a/drivers/gpu/drm/meson/meson_viu.c b/drivers/gpu/drm/meson/meson_viu.c -index 5b48c4c0985b5..a423e7a61bf2c 100644 ---- a/drivers/gpu/drm/meson/meson_viu.c -+++ b/drivers/gpu/drm/meson/meson_viu.c -@@ -328,6 +328,21 @@ void meson_viu_init(struct meson_drm *priv) - 0xff << OSD_REPLACE_SHIFT, - priv->io_base + _REG(VIU_OSD2_CTRL_STAT2)); - -+ /* Disable VD1 AFBC */ -+ /* di_mif0_en=0 mif0_to_vpp_en=0 di_mad_en=0 */ -+ writel_bits_relaxed(0x7 << 16, 0, -+ priv->io_base + _REG(VIU_MISC_CTRL0)); -+ /* afbc vd1 set=0 */ -+ writel_bits_relaxed(BIT(20), 0, -+ priv->io_base + _REG(VIU_MISC_CTRL0)); -+ writel_relaxed(0, priv->io_base + _REG(AFBC_ENABLE)); -+ -+ writel_relaxed(0x00FF00C0, -+ priv->io_base + _REG(VD1_IF0_LUMA_FIFO_SIZE)); -+ writel_relaxed(0x00FF00C0, -+ priv->io_base + _REG(VD2_IF0_LUMA_FIFO_SIZE)); -+ -+ - priv->viu.osd1_enabled = false; - priv->viu.osd1_commit = false; - priv->viu.osd1_interlace = false; -diff --git a/drivers/gpu/drm/meson/meson_vpp.c b/drivers/gpu/drm/meson/meson_vpp.c -index 27356f81a0abe..5dc24a99e978b 100644 ---- a/drivers/gpu/drm/meson/meson_vpp.c -+++ b/drivers/gpu/drm/meson/meson_vpp.c -@@ -122,6 +122,31 @@ static void meson_vpp_write_scaling_filter_coefs(struct meson_drm *priv, - priv->io_base + _REG(VPP_OSD_SCALE_COEF)); - } - -+static const uint32_t vpp_filter_coefs_bicubic[] = { -+ 0x00800000, 0x007f0100, 0xff7f0200, 0xfe7f0300, -+ 0xfd7e0500, 0xfc7e0600, 0xfb7d0800, 0xfb7c0900, -+ 0xfa7b0b00, 0xfa7a0dff, 0xf9790fff, 0xf97711ff, -+ 0xf87613ff, 0xf87416fe, 0xf87218fe, 0xf8701afe, -+ 0xf76f1dfd, 0xf76d1ffd, 0xf76b21fd, 0xf76824fd, -+ 0xf76627fc, 0xf76429fc, 0xf7612cfc, 0xf75f2ffb, -+ 0xf75d31fb, 0xf75a34fb, 0xf75837fa, 0xf7553afa, -+ 0xf8523cfa, 0xf8503ff9, 0xf84d42f9, 0xf84a45f9, -+ 0xf84848f8 -+}; -+ -+static void meson_vpp_write_vd_scaling_filter_coefs(struct meson_drm *priv, -+ const unsigned int *coefs, -+ bool is_horizontal) -+{ -+ int i; -+ -+ writel_relaxed(is_horizontal ? BIT(8) : 0, -+ priv->io_base + _REG(VPP_SCALE_COEF_IDX)); -+ for (i = 0; i < 33; i++) -+ writel_relaxed(coefs[i], -+ priv->io_base + _REG(VPP_SCALE_COEF)); -+} -+ - void meson_vpp_init(struct meson_drm *priv) - { - /* set dummy data default YUV black */ -@@ -150,17 +175,34 @@ void meson_vpp_init(struct meson_drm *priv) - - /* Force all planes off */ - writel_bits_relaxed(VPP_OSD1_POSTBLEND | VPP_OSD2_POSTBLEND | -- VPP_VD1_POSTBLEND | VPP_VD2_POSTBLEND, 0, -+ VPP_VD1_POSTBLEND | VPP_VD2_POSTBLEND | -+ VPP_VD1_PREBLEND | VPP_VD2_PREBLEND, 0, - priv->io_base + _REG(VPP_MISC)); - -+ /* Setup default VD settings */ -+ writel_relaxed(4096, -+ priv->io_base + _REG(VPP_PREBLEND_VD1_H_START_END)); -+ writel_relaxed(4096, -+ priv->io_base + _REG(VPP_BLEND_VD2_H_START_END)); -+ - /* Disable Scalers */ - writel_relaxed(0, priv->io_base + _REG(VPP_OSD_SC_CTRL0)); - writel_relaxed(0, priv->io_base + _REG(VPP_OSD_VSC_CTRL0)); - writel_relaxed(0, priv->io_base + _REG(VPP_OSD_HSC_CTRL0)); -+ writel_relaxed(4 | (4 << 8) | BIT(15), -+ priv->io_base + _REG(VPP_SC_MISC)); -+ -+ writel_relaxed(1, priv->io_base + _REG(VPP_VADJ_CTRL)); - - /* Write in the proper filter coefficients. */ - meson_vpp_write_scaling_filter_coefs(priv, - vpp_filter_coefs_4point_bspline, false); - meson_vpp_write_scaling_filter_coefs(priv, - vpp_filter_coefs_4point_bspline, true); -+ -+ /* Write the VD proper filter coefficients. */ -+ meson_vpp_write_vd_scaling_filter_coefs(priv, vpp_filter_coefs_bicubic, -+ false); -+ meson_vpp_write_vd_scaling_filter_coefs(priv, vpp_filter_coefs_bicubic, -+ true); - } -diff --git a/drivers/soc/amlogic/meson-gx-pwrc-vpu.c b/drivers/soc/amlogic/meson-gx-pwrc-vpu.c -index 6289965c42e98..05421d029dff9 100644 ---- a/drivers/soc/amlogic/meson-gx-pwrc-vpu.c -+++ b/drivers/soc/amlogic/meson-gx-pwrc-vpu.c -@@ -54,12 +54,12 @@ static int meson_gx_pwrc_vpu_power_off(struct generic_pm_domain *genpd) - /* 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); -+ 0x3 << 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); -+ 0x3 << i, 0x3 << i); - udelay(5); - } - for (i = 8; i < 16; i++) { -@@ -108,13 +108,13 @@ static int meson_gx_pwrc_vpu_power_on(struct generic_pm_domain *genpd) - /* Power Up Memories */ - for (i = 0; i < 32; i += 2) { - regmap_update_bits(pd->regmap_hhi, HHI_VPU_MEM_PD_REG0, -- 0x2 << i, 0); -+ 0x3 << 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); -+ 0x3 << i, 0); - udelay(5); - } - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/018_linux-4.18-yocto-meson64-0001-ARM64-dts-meson-gxbb-nanopi-k2-Add-HDMI-CEC-and-CVBS.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/018_linux-4.18-yocto-meson64-0001-ARM64-dts-meson-gxbb-nanopi-k2-Add-HDMI-CEC-and-CVBS.patch deleted file mode 100644 index aad63ba8f..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/018_linux-4.18-yocto-meson64-0001-ARM64-dts-meson-gxbb-nanopi-k2-Add-HDMI-CEC-and-CVBS.patch +++ /dev/null @@ -1,81 +0,0 @@ -From 6c5aaf27886c9b308e9c4e4d613990e540f23ec8 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Tue, 26 Jun 2018 09:37:39 +0200 -Subject: [PATCH] ARM64: dts: meson-gxbb-nanopi-k2: Add HDMI, CEC and CVBS - nodes - -The Amlogic Meson GXBB based Nanopi-K2 board has an HDMI connector -with CEC and CVBS available on the 40pin header. -This patch adds the nodes to enable HDMI, CEC and CVBS functionnalities. - -Signed-off-by: Neil Armstrong ---- - .../boot/dts/amlogic/meson-gxbb-nanopi-k2.dts | 48 ++++++++++++++++++++++ - 1 file changed, 48 insertions(+) - -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 7d5709c..cbe99bd 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -@@ -106,6 +106,42 @@ - compatible = "mmc-pwrseq-emmc"; - reset-gpios = <&gpio BOOT_9 GPIO_ACTIVE_LOW>; - }; -+ -+ /* CVBS is available on CON1 pin 36, disabled by default */ -+ cvbs-connector { -+ compatible = "composite-video-connector"; -+ status = "disabled"; -+ -+ port { -+ cvbs_connector_in: endpoint { -+ remote-endpoint = <&cvbs_vdac_out>; -+ }; -+ }; -+ }; -+ -+ 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>; -+}; -+ -+&cvbs_vdac_port { -+ cvbs_vdac_out: endpoint { -+ remote-endpoint = <&cvbs_connector_in>; -+ }; - }; - - ðmac { -@@ -137,6 +173,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>; -+ }; -+}; -+ - &ir { - status = "okay"; - pinctrl-0 = <&remote_input_ao_pins>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/020_linux-4.18-yocto-meson64-0003-ARM64-defconfig-enable-CEC-support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/020_linux-4.18-yocto-meson64-0003-ARM64-defconfig-enable-CEC-support.patch deleted file mode 100644 index 7c0471753..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/020_linux-4.18-yocto-meson64-0003-ARM64-defconfig-enable-CEC-support.patch +++ /dev/null @@ -1,44 +0,0 @@ -From e41c06328d1cd0989899d6a0897c6857d0cf9a4b Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Mon, 13 Nov 2017 12:09:40 +0100 -Subject: [PATCH] ARM64: defconfig: enable CEC support - -Turn on CONFIG_CEC_SUPPORT and CONFIG_CEC_PLATFORM_DRIVERS -Turn on CONFIG_VIDEO_MESON_AO_CEC as module -Turn on CONFIG_DRM_DW_HDMI_CEC as module - -Signed-off-by: Jerome Brunet -Signed-off-by: Neil Armstrong ---- - arch/arm64/configs/defconfig | 4 ++++ - 1 file changed, 4 insertions(+) - -diff --git a/arch/arm64/configs/defconfig b/arch/arm64/configs/defconfig -index f9a186f..2584605 100644 ---- a/arch/arm64/configs/defconfig -+++ b/arch/arm64/configs/defconfig -@@ -402,6 +402,7 @@ CONFIG_MEDIA_SUPPORT=m - CONFIG_MEDIA_CAMERA_SUPPORT=y - CONFIG_MEDIA_ANALOG_TV_SUPPORT=y - CONFIG_MEDIA_DIGITAL_TV_SUPPORT=y -+CONFIG_MEDIA_CEC_SUPPORT=y - CONFIG_MEDIA_CONTROLLER=y - CONFIG_VIDEO_V4L2_SUBDEV_API=y - # CONFIG_DVB_NET is not set -@@ -411,6 +412,8 @@ CONFIG_VIDEO_SAMSUNG_S5P_MFC=m - CONFIG_VIDEO_SAMSUNG_EXYNOS_GSC=m - CONFIG_VIDEO_RENESAS_FCP=m - CONFIG_VIDEO_RENESAS_VSP1=m -+CONFIG_CEC_PLATFORM_DRIVERS=y -+CONFIG_VIDEO_MESON_AO_CEC=m - CONFIG_DRM=m - CONFIG_DRM_NOUVEAU=m - CONFIG_DRM_EXYNOS=m -@@ -431,6 +434,7 @@ CONFIG_DRM_RCAR_LVDS=m - CONFIG_DRM_TEGRA=m - CONFIG_DRM_PANEL_SIMPLE=m - CONFIG_DRM_I2C_ADV7511=m -+CONFIG_DRM_DW_HDMI_CEC=m - CONFIG_DRM_VC4=m - CONFIG_DRM_HISI_HIBMC=m - CONFIG_DRM_HISI_KIRIN=m diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/021_linux-4.18-yocto-meson64-0004-clk-meson-switch-gxbb-cts-amclk-div-to-the-generic-d.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/021_linux-4.18-yocto-meson64-0004-clk-meson-switch-gxbb-cts-amclk-div-to-the-generic-d.patch deleted file mode 100644 index e2b3860f5..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/021_linux-4.18-yocto-meson64-0004-clk-meson-switch-gxbb-cts-amclk-div-to-the-generic-d.patch +++ /dev/null @@ -1,44 +0,0 @@ -From 0cecf963b9d815699fe50b7a7ee4a93ece3ed834 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Tue, 19 Jun 2018 18:14:49 +0200 -Subject: [PATCH] clk: meson: switch gxbb cts-amclk div to the generic divider - -clk-audio-divider was a (poor) attempt to use CCF rate propagation -while making sure the PLL rate would be high enough to work with -audio use cases. The result is far from optimal. We can do better -by carefully choosing the PLL rates for the audio use cases. -Doing so, we don't need to use clk-audio-divider anymore. The -generic will do - -Signed-off-by: Jerome Brunet ---- - drivers/clk/meson/gxbb.c | 12 +++++------- - 1 file changed, 5 insertions(+), 7 deletions(-) - -diff --git a/drivers/clk/meson/gxbb.c b/drivers/clk/meson/gxbb.c -index 177fffb..69a58cb 100644 ---- a/drivers/clk/meson/gxbb.c -+++ b/drivers/clk/meson/gxbb.c -@@ -982,17 +982,15 @@ static struct clk_regmap gxbb_cts_amclk_sel = { - }; - - static struct clk_regmap gxbb_cts_amclk_div = { -- .data = &(struct meson_clk_audio_div_data){ -- .div = { -- .reg_off = HHI_AUD_CLK_CNTL, -- .shift = 0, -- .width = 8, -- }, -+ .data = &(struct clk_regmap_div_data) { -+ .offset = HHI_AUD_CLK_CNTL, -+ .shift = 0, -+ .width = 8, - .flags = CLK_DIVIDER_ROUND_CLOSEST, - }, - .hw.init = &(struct clk_init_data){ - .name = "cts_amclk_div", -- .ops = &meson_clk_audio_divider_ops, -+ .ops = &clk_regmap_divider_ops, - .parent_names = (const char *[]){ "cts_amclk_sel" }, - .num_parents = 1, - .flags = CLK_SET_RATE_PARENT, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/022_linux-4.18-yocto-meson64-0005-clk-meson-remove-unused-clk-audio-divider-driver.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/022_linux-4.18-yocto-meson64-0005-clk-meson-remove-unused-clk-audio-divider-driver.patch deleted file mode 100644 index cd6da8cf5..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/022_linux-4.18-yocto-meson64-0005-clk-meson-remove-unused-clk-audio-divider-driver.patch +++ /dev/null @@ -1,48 +0,0 @@ -From e87dd7b11611e4ac5279ba4ad4f1fea4d0900273 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Tue, 19 Jun 2018 18:23:28 +0200 -Subject: [PATCH] clk: meson: remove unused clk-audio-divider driver - -Signed-off-by: Jerome Brunet ---- - drivers/clk/meson/Makefile | 2 +- - drivers/clk/meson/clkc.h | 7 ------- - 2 files changed, 1 insertion(+), 8 deletions(-) - -diff --git a/drivers/clk/meson/Makefile b/drivers/clk/meson/Makefile -index d0d13ae..e40fea9 100644 ---- a/drivers/clk/meson/Makefile -+++ b/drivers/clk/meson/Makefile -@@ -2,7 +2,7 @@ - # Makefile for Meson specific clk - # - --obj-$(CONFIG_COMMON_CLK_AMLOGIC) += clk-pll.o clk-mpll.o clk-audio-divider.o -+obj-$(CONFIG_COMMON_CLK_AMLOGIC) += clk-pll.o clk-mpll.o - obj-$(CONFIG_COMMON_CLK_MESON_AO) += meson-aoclk.o - obj-$(CONFIG_COMMON_CLK_MESON8B) += meson8b.o - obj-$(CONFIG_COMMON_CLK_GXBB) += gxbb.o gxbb-aoclk.o gxbb-aoclk-32k.o -diff --git a/drivers/clk/meson/clkc.h b/drivers/clk/meson/clkc.h -index 2fb0843..48db024 100644 ---- a/drivers/clk/meson/clkc.h -+++ b/drivers/clk/meson/clkc.h -@@ -91,11 +91,6 @@ struct meson_clk_mpll_data { - - #define CLK_MESON_MPLL_ROUND_CLOSEST BIT(0) - --struct meson_clk_audio_div_data { -- struct parm div; -- u8 flags; --}; -- - #define MESON_GATE(_name, _reg, _bit) \ - struct clk_regmap _name = { \ - .data = &(struct clk_regmap_gate_data){ \ -@@ -117,7 +112,5 @@ extern const struct clk_ops meson_clk_pll_ops; - extern const struct clk_ops meson_clk_cpu_ops; - extern const struct clk_ops meson_clk_mpll_ro_ops; - extern const struct clk_ops meson_clk_mpll_ops; --extern const struct clk_ops meson_clk_audio_divider_ro_ops; --extern const struct clk_ops meson_clk_audio_divider_ops; - - #endif /* __CLKC_H */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/023_linux-4.18-yocto-meson64-0006-ASoC-meson-add-meson-audio-core-driver.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/023_linux-4.18-yocto-meson64-0006-ASoC-meson-add-meson-audio-core-driver.patch deleted file mode 100644 index 69c0ab299..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/023_linux-4.18-yocto-meson64-0006-ASoC-meson-add-meson-audio-core-driver.patch +++ /dev/null @@ -1,308 +0,0 @@ -From 878d41be386f0bcbe1475f65acd8b9fb304529a0 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 30 Mar 2017 11:49:55 +0200 -Subject: [PATCH] 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 ---- - 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 41af6b9..1cf11cf 100644 ---- a/sound/soc/Kconfig -+++ b/sound/soc/Kconfig -@@ -57,6 +57,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 06389a5..62a5f87 100644 ---- a/sound/soc/Makefile -+++ b/sound/soc/Makefile -@@ -38,6 +38,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..ca0e3e9 ---- /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 -+ 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_ */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/024_linux-4.18-yocto-meson64-0007-ASoC-meson-add-register-definitions.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/024_linux-4.18-yocto-meson64-0007-ASoC-meson-add-register-definitions.patch deleted file mode 100644 index 0a13a427c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/024_linux-4.18-yocto-meson64-0007-ASoC-meson-add-register-definitions.patch +++ /dev/null @@ -1,357 +0,0 @@ -From f6c0ce626b08f5ba85bd9bfe000044c4f9e7da24 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 30 Mar 2017 12:00:10 +0200 -Subject: [PATCH] ASoC: meson: add register definitions - -Add the register definition for the AIU and AUDIN blocks - -Signed-off-by: Jerome Brunet ---- - 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_ */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/025_linux-4.18-yocto-meson64-0008-ASoC-meson-add-aiu-i2s-dma-support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/025_linux-4.18-yocto-meson64-0008-ASoC-meson-add-aiu-i2s-dma-support.patch deleted file mode 100644 index 1de0e444a..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/025_linux-4.18-yocto-meson64-0008-ASoC-meson-add-aiu-i2s-dma-support.patch +++ /dev/null @@ -1,416 +0,0 @@ -From bb5102086db1579c1289440fa8aa184a70cb7c64 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 30 Mar 2017 12:14:40 +0200 -Subject: [PATCH] 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 ---- - sound/soc/meson/Kconfig | 7 + - sound/soc/meson/Makefile | 2 + - sound/soc/meson/aiu-i2s-dma.c | 370 ++++++++++++++++++++++++++++++++++++++++++ - 3 files changed, 379 insertions(+) - create mode 100644 sound/soc/meson/aiu-i2s-dma.c - -diff --git a/sound/soc/meson/Kconfig b/sound/soc/meson/Kconfig -index ca0e3e9..88fbfc2 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..2684bd0 ---- /dev/null -+++ b/sound/soc/meson/aiu-i2s-dma.c -@@ -0,0 +1,370 @@ -+/* -+ * 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; -+ struct snd_soc_component *component = snd_soc_rtdcom_lookup(rtd, DRV_NAME); -+ -+ return snd_soc_component_get_drvdata(component); -+} -+ -+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); -+} -+ -+static const struct snd_soc_component_driver aiu_i2s_platform = { -+ .ops = &aiu_i2s_dma_ops, -+ .pcm_new = aiu_i2s_dma_new, -+ .name = DRV_NAME, -+}; -+ -+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 devm_snd_soc_register_component(dev, &aiu_i2s_platform, -+ NULL, 0); -+} -+ -+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"); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/026_linux-4.18-yocto-meson64-0009-ASoC-meson-add-initial-i2s-dai-support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/026_linux-4.18-yocto-meson64-0009-ASoC-meson-add-initial-i2s-dai-support.patch deleted file mode 100644 index f3bac343f..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/026_linux-4.18-yocto-meson64-0009-ASoC-meson-add-initial-i2s-dai-support.patch +++ /dev/null @@ -1,511 +0,0 @@ -From 6a5036e9f7dbd99023c6f9482fed3a747868b1c2 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 30 Mar 2017 12:17:27 +0200 -Subject: [PATCH] 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 ---- - 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 88fbfc2..478f29a 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"); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/027_linux-4.18-yocto-meson64-0010-ASoC-meson-add-aiu-spdif-dma-support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/027_linux-4.18-yocto-meson64-0010-ASoC-meson-add-aiu-spdif-dma-support.patch deleted file mode 100644 index 380f5d5b2..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/027_linux-4.18-yocto-meson64-0010-ASoC-meson-add-aiu-spdif-dma-support.patch +++ /dev/null @@ -1,438 +0,0 @@ -From 8dd5edaf984e4c8d6f7ca1e7709b3109cf7dd780 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 30 Mar 2017 13:43:52 +0200 -Subject: [PATCH] ASoC: meson: add aiu spdif dma support - -Add support for the spdif output dma which is part of the AIU block - -Signed-off-by: Jerome Brunet ---- - sound/soc/meson/Kconfig | 7 + - sound/soc/meson/Makefile | 2 + - sound/soc/meson/aiu-spdif-dma.c | 388 ++++++++++++++++++++++++++++++++++++++++ - 3 files changed, 397 insertions(+) - create mode 100644 sound/soc/meson/aiu-spdif-dma.c - -diff --git a/sound/soc/meson/Kconfig b/sound/soc/meson/Kconfig -index 478f29a..3fb93b9 100644 ---- a/sound/soc/meson/Kconfig -+++ b/sound/soc/meson/Kconfig -@@ -14,3 +14,10 @@ config SND_SOC_MESON_I2S - help - Say Y or M if you want to add support for i2s driver for Amlogic - Meson SoCs. -+ -+config SND_SOC_MESON_SPDIF -+ tristate "Meson spdif interface" -+ depends on SND_SOC_MESON -+ help -+ Say Y or M if you want to add support for spdif dma driver for Amlogic -+ Meson SoCs. -diff --git a/sound/soc/meson/Makefile b/sound/soc/meson/Makefile -index ea06dde..cef9a9d 100644 ---- a/sound/soc/meson/Makefile -+++ b/sound/soc/meson/Makefile -@@ -1,7 +1,9 @@ - snd-soc-meson-audio-core-objs := audio-core.o - snd-soc-meson-aiu-i2s-dma-objs := aiu-i2s-dma.o -+snd-soc-meson-aiu-spdif-dma-objs := aiu-spdif-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 -+obj-$(CONFIG_SND_SOC_MESON_SPDIF) += snd-soc-meson-aiu-spdif-dma.o -diff --git a/sound/soc/meson/aiu-spdif-dma.c b/sound/soc/meson/aiu-spdif-dma.c -new file mode 100644 -index 0000000..81c3b85 ---- /dev/null -+++ b/sound/soc/meson/aiu-spdif-dma.c -@@ -0,0 +1,388 @@ -+/* -+ * 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-spdif-dma" -+ -+struct aiu_spdif_dma { -+ struct meson_audio_core_data *core; -+ struct clk *fast; -+ int irq; -+}; -+ -+#define AIU_958_DCU_FF_CTRL_EN BIT(0) -+#define AIU_958_DCU_FF_CTRL_AUTO_DISABLE BIT(1) -+#define AIU_958_DCU_FF_CTRL_IRQ_MODE_MASK GENMASK(3, 2) -+#define AIU_958_DCU_FF_CTRL_IRQ_OUT_THD BIT(2) -+#define AIU_958_DCU_FF_CTRL_IRQ_FRAME_READ BIT(3) -+#define AIU_958_DCU_FF_CTRL_SYNC_HEAD_EN BIT(4) -+#define AIU_958_DCU_FF_CTRL_BYTE_SEEK BIT(5) -+#define AIU_958_DCU_FF_CTRL_CONTINUE BIT(6) -+#define AIU_MEM_IEC958_BUF_CNTL_INIT BIT(0) -+#define AIU_MEM_IEC958_CONTROL_INIT BIT(0) -+#define AIU_MEM_IEC958_CONTROL_FILL_EN BIT(1) -+#define AIU_MEM_IEC958_CONTROL_EMPTY_EN BIT(2) -+#define AIU_MEM_IEC958_CONTROL_ENDIAN_MASK GENMASK(5, 3) -+#define AIU_MEM_IEC958_CONTROL_RD_DDR BIT(6) -+#define AIU_MEM_IEC958_CONTROL_MODE_16BIT BIT(7) -+#define AIU_MEM_IEC958_MASKS_CH_MEM_MASK GENMASK(15, 8) -+#define AIU_MEM_IEC958_MASKS_CH_MEM(ch) ((ch) << 8) -+#define AIU_MEM_IEC958_MASKS_CH_RD_MASK GENMASK(7, 0) -+#define AIU_MEM_IEC958_MASKS_CH_RD(ch) ((ch) << 0) -+ -+#define AIU_SPDIF_DMA_BURST 8 -+#define AIU_SPDIF_BPF_MAX USHRT_MAX -+ -+static struct snd_pcm_hardware aiu_spdif_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), -+ -+ .rates = (SNDRV_PCM_RATE_32000 | -+ SNDRV_PCM_RATE_44100 | -+ SNDRV_PCM_RATE_48000 | -+ SNDRV_PCM_RATE_96000 | -+ SNDRV_PCM_RATE_192000), -+ /* -+ * TODO: The DMA can change the endianness, the msb position -+ * and deal with unsigned - support this later on -+ */ -+ -+ .channels_min = 2, -+ .channels_max = 2, -+ .period_bytes_min = AIU_SPDIF_DMA_BURST, -+ .period_bytes_max = AIU_SPDIF_BPF_MAX, -+ .periods_min = 2, -+ .periods_max = UINT_MAX, -+ .buffer_bytes_max = 1 * 1024 * 1024, -+ .fifo_size = 0, -+}; -+ -+static struct aiu_spdif_dma *aiu_spdif_dma_priv(struct snd_pcm_substream *s) -+{ -+ struct snd_soc_pcm_runtime *rtd = s->private_data; -+ struct snd_soc_component *component = snd_soc_rtdcom_lookup(rtd, DRV_NAME); -+ -+ return snd_soc_component_get_drvdata(component); -+} -+ -+static snd_pcm_uframes_t -+aiu_spdif_dma_pointer(struct snd_pcm_substream *substream) -+{ -+ struct snd_pcm_runtime *runtime = substream->runtime; -+ struct aiu_spdif_dma *priv = aiu_spdif_dma_priv(substream); -+ unsigned int addr; -+ int ret; -+ -+ ret = regmap_read(priv->core->aiu, AIU_MEM_IEC958_RD_PTR, -+ &addr); -+ if (ret) -+ return 0; -+ -+ return bytes_to_frames(runtime, addr - (unsigned int)runtime->dma_addr); -+} -+ -+static void __dma_enable(struct aiu_spdif_dma *priv, bool enable) -+{ -+ unsigned int en_mask = (AIU_MEM_IEC958_CONTROL_FILL_EN | -+ AIU_MEM_IEC958_CONTROL_EMPTY_EN); -+ -+ regmap_update_bits(priv->core->aiu, AIU_MEM_IEC958_CONTROL, en_mask, -+ enable ? en_mask : 0); -+} -+ -+static void __dcu_fifo_enable(struct aiu_spdif_dma *priv, bool enable) -+{ -+ regmap_update_bits(priv->core->aiu, AIU_958_DCU_FF_CTRL, -+ AIU_958_DCU_FF_CTRL_EN, -+ enable ? AIU_958_DCU_FF_CTRL_EN : 0); -+} -+ -+static int aiu_spdif_dma_trigger(struct snd_pcm_substream *substream, int cmd) -+{ -+ struct aiu_spdif_dma *priv = aiu_spdif_dma_priv(substream); -+ -+ switch (cmd) { -+ case SNDRV_PCM_TRIGGER_START: -+ case SNDRV_PCM_TRIGGER_RESUME: -+ case SNDRV_PCM_TRIGGER_PAUSE_RELEASE: -+ __dcu_fifo_enable(priv, true); -+ __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); -+ __dcu_fifo_enable(priv, false); -+ break; -+ default: -+ return -EINVAL; -+ } -+ -+ return 0; -+} -+ -+static void __dma_init_mem(struct aiu_spdif_dma *priv) -+{ -+ regmap_update_bits(priv->core->aiu, AIU_MEM_IEC958_CONTROL, -+ AIU_MEM_IEC958_CONTROL_INIT, -+ AIU_MEM_IEC958_CONTROL_INIT); -+ regmap_update_bits(priv->core->aiu, AIU_MEM_IEC958_BUF_CNTL, -+ AIU_MEM_IEC958_BUF_CNTL_INIT, -+ AIU_MEM_IEC958_BUF_CNTL_INIT); -+ -+ regmap_update_bits(priv->core->aiu, AIU_MEM_IEC958_CONTROL, -+ AIU_MEM_IEC958_CONTROL_INIT, -+ 0); -+ regmap_update_bits(priv->core->aiu, AIU_MEM_IEC958_BUF_CNTL, -+ AIU_MEM_IEC958_BUF_CNTL_INIT, -+ 0); -+} -+ -+static int aiu_spdif_dma_prepare(struct snd_pcm_substream *substream) -+{ -+ struct aiu_spdif_dma *priv = aiu_spdif_dma_priv(substream); -+ -+ __dma_init_mem(priv); -+ -+ return 0; -+} -+ -+static int __setup_memory_layout(struct aiu_spdif_dma *priv, -+ unsigned int width) -+{ -+ u32 mem_ctl = AIU_MEM_IEC958_CONTROL_RD_DDR; -+ -+ if (width == 16) -+ mem_ctl |= AIU_MEM_IEC958_CONTROL_MODE_16BIT; -+ -+ regmap_update_bits(priv->core->aiu, AIU_MEM_IEC958_CONTROL, -+ AIU_MEM_IEC958_CONTROL_ENDIAN_MASK | -+ AIU_MEM_IEC958_CONTROL_MODE_16BIT | -+ AIU_MEM_IEC958_CONTROL_RD_DDR, -+ mem_ctl); -+ -+ return 0; -+} -+ -+static int aiu_spdif_dma_hw_params(struct snd_pcm_substream *substream, -+ struct snd_pcm_hw_params *params) -+{ -+ struct snd_pcm_runtime *runtime = substream->runtime; -+ struct aiu_spdif_dma *priv = aiu_spdif_dma_priv(substream); -+ int ret; -+ dma_addr_t end_ptr; -+ -+ ret = snd_pcm_lib_malloc_pages(substream, params_buffer_bytes(params)); -+ if (ret < 0) -+ return ret; -+ -+ ret = __setup_memory_layout(priv, params_physical_width(params)); -+ if (ret) -+ return ret; -+ -+ /* Initialize memory pointers */ -+ regmap_write(priv->core->aiu, -+ AIU_MEM_IEC958_START_PTR, runtime->dma_addr); -+ regmap_write(priv->core->aiu, -+ AIU_MEM_IEC958_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_SPDIF_DMA_BURST; -+ regmap_write(priv->core->aiu, AIU_MEM_IEC958_END_PTR, end_ptr); -+ -+ /* Memory masks */ -+ regmap_write(priv->core->aiu, AIU_MEM_IEC958_MASKS, -+ AIU_MEM_IEC958_MASKS_CH_RD(0xff) | -+ AIU_MEM_IEC958_MASKS_CH_MEM(0xff)); -+ -+ /* Setup the number bytes read by the FIFO between each IRQ */ -+ regmap_write(priv->core->aiu, AIU_958_BPF, params_period_bytes(params)); -+ -+ /* -+ * AUTO_DISABLE and SYNC_HEAD are enabled by default but -+ * this should be disabled in PCM (uncompressed) mode -+ */ -+ regmap_update_bits(priv->core->aiu, AIU_958_DCU_FF_CTRL, -+ AIU_958_DCU_FF_CTRL_AUTO_DISABLE | -+ AIU_958_DCU_FF_CTRL_IRQ_MODE_MASK | -+ AIU_958_DCU_FF_CTRL_SYNC_HEAD_EN, -+ AIU_958_DCU_FF_CTRL_IRQ_FRAME_READ); -+ -+ return 0; -+} -+ -+static int aiu_spdif_dma_hw_free(struct snd_pcm_substream *substream) -+{ -+ return snd_pcm_lib_free_pages(substream); -+} -+ -+static irqreturn_t aiu_spdif_dma_irq(int irq, void *dev_id) -+{ -+ struct snd_pcm_substream *playback = dev_id; -+ -+ snd_pcm_period_elapsed(playback); -+ -+ return IRQ_HANDLED; -+} -+ -+static int aiu_spdif_dma_open(struct snd_pcm_substream *substream) -+{ -+ struct aiu_spdif_dma *priv = aiu_spdif_dma_priv(substream); -+ int ret; -+ -+ snd_soc_set_runtime_hwparams(substream, &aiu_spdif_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_SPDIF_DMA_BURST); -+ if (ret) -+ return ret; -+ -+ ret = snd_pcm_hw_constraint_step(substream->runtime, 0, -+ SNDRV_PCM_HW_PARAM_PERIOD_BYTES, -+ AIU_SPDIF_DMA_BURST); -+ if (ret) -+ return ret; -+ -+ /* Request the SPDIF DDR irq */ -+ ret = request_irq(priv->irq, aiu_spdif_dma_irq, 0, -+ DRV_NAME, substream); -+ if (ret) -+ return ret; -+ -+ /* Power up the spdif fast domain - can't write the register w/o it */ -+ ret = clk_prepare_enable(priv->fast); -+ if (ret) -+ return ret; -+ -+ /* Make sure the dma is initially halted */ -+ __dma_enable(priv, false); -+ __dcu_fifo_enable(priv, false); -+ -+ return 0; -+} -+ -+static int aiu_spdif_dma_close(struct snd_pcm_substream *substream) -+{ -+ struct aiu_spdif_dma *priv = aiu_spdif_dma_priv(substream); -+ -+ clk_disable_unprepare(priv->fast); -+ free_irq(priv->irq, substream); -+ -+ return 0; -+} -+ -+static const struct snd_pcm_ops aiu_spdif_dma_ops = { -+ .open = aiu_spdif_dma_open, -+ .close = aiu_spdif_dma_close, -+ .ioctl = snd_pcm_lib_ioctl, -+ .hw_params = aiu_spdif_dma_hw_params, -+ .hw_free = aiu_spdif_dma_hw_free, -+ .prepare = aiu_spdif_dma_prepare, -+ .pointer = aiu_spdif_dma_pointer, -+ .trigger = aiu_spdif_dma_trigger, -+}; -+ -+static int aiu_spdif_dma_new(struct snd_soc_pcm_runtime *rtd) -+{ -+ struct snd_card *card = rtd->card->snd_card; -+ size_t size = aiu_spdif_dma_hw.buffer_bytes_max; -+ -+ return snd_pcm_lib_preallocate_pages_for_all(rtd->pcm, -+ SNDRV_DMA_TYPE_DEV, -+ card->dev, size, size); -+} -+ -+static const struct snd_soc_component_driver aiu_spdif_platform = { -+ .ops = &aiu_spdif_dma_ops, -+ .pcm_new = aiu_spdif_dma_new, -+ .name = DRV_NAME, -+}; -+ -+static int aiu_spdif_dma_probe(struct platform_device *pdev) -+{ -+ struct device *dev = &pdev->dev; -+ struct aiu_spdif_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 spdif 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 spdif ddr irq\n"); -+ return priv->irq; -+ } -+ -+ return devm_snd_soc_register_component(dev, &aiu_spdif_platform, -+ NULL, 0); -+} -+ -+static const struct of_device_id aiu_spdif_dma_of_match[] = { -+ { .compatible = "amlogic,meson-aiu-spdif-dma", }, -+ { .compatible = "amlogic,meson-gxbb-aiu-spdif-dma", }, -+ { .compatible = "amlogic,meson-gxl-aiu-spdif-dma", }, -+ {} -+}; -+MODULE_DEVICE_TABLE(of, aiu_spdif_dma_of_match); -+ -+static struct platform_driver aiu_spdif_dma_pdrv = { -+ .probe = aiu_spdif_dma_probe, -+ .driver = { -+ .name = DRV_NAME, -+ .of_match_table = aiu_spdif_dma_of_match, -+ }, -+}; -+module_platform_driver(aiu_spdif_dma_pdrv); -+ -+MODULE_DESCRIPTION("Meson AIU spdif DMA ASoC Driver"); -+MODULE_AUTHOR("Jerome Brunet "); -+MODULE_LICENSE("GPL"); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/028_linux-4.18-yocto-meson64-0011-ASoC-meson-add-initial-spdif-dai-support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/028_linux-4.18-yocto-meson64-0011-ASoC-meson-add-initial-spdif-dai-support.patch deleted file mode 100644 index 3d36f4b06..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/028_linux-4.18-yocto-meson64-0011-ASoC-meson-add-initial-spdif-dai-support.patch +++ /dev/null @@ -1,426 +0,0 @@ -From e635299f76dc27b97a768f2a044d04c1917b9ad1 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 30 Mar 2017 13:46:03 +0200 -Subject: [PATCH] ASoC: meson: add initial spdif dai support - -Add support for the spdif dai found on Amlogic Meson SoC family. -With this initial implementation, only uncompressed pcm playback -from the spdif dma is supported. Future work will add compressed -support, pcm playback from i2s dma and capture. - -Signed-off-by: Jerome Brunet ---- - sound/soc/meson/Kconfig | 3 +- - sound/soc/meson/Makefile | 2 + - sound/soc/meson/spdif-dai.c | 374 ++++++++++++++++++++++++++++++++++++++++++++ - 3 files changed, 378 insertions(+), 1 deletion(-) - create mode 100644 sound/soc/meson/spdif-dai.c - -diff --git a/sound/soc/meson/Kconfig b/sound/soc/meson/Kconfig -index 3fb93b9..301d3a3 100644 ---- a/sound/soc/meson/Kconfig -+++ b/sound/soc/meson/Kconfig -@@ -18,6 +18,7 @@ config SND_SOC_MESON_I2S - config SND_SOC_MESON_SPDIF - tristate "Meson spdif interface" - depends on SND_SOC_MESON -+ select SND_PCM_IEC958 - help -- Say Y or M if you want to add support for spdif dma driver for Amlogic -+ Say Y or M if you want to add support for spdif driver for Amlogic - Meson SoCs. -diff --git a/sound/soc/meson/Makefile b/sound/soc/meson/Makefile -index cef9a9d..bc4391c 100644 ---- a/sound/soc/meson/Makefile -+++ b/sound/soc/meson/Makefile -@@ -2,8 +2,10 @@ snd-soc-meson-audio-core-objs := audio-core.o - snd-soc-meson-aiu-i2s-dma-objs := aiu-i2s-dma.o - snd-soc-meson-aiu-spdif-dma-objs := aiu-spdif-dma.o - snd-soc-meson-i2s-dai-objs := i2s-dai.o -+snd-soc-meson-spdif-dai-objs := spdif-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 - obj-$(CONFIG_SND_SOC_MESON_SPDIF) += snd-soc-meson-aiu-spdif-dma.o -+obj-$(CONFIG_SND_SOC_MESON_SPDIF) += snd-soc-meson-spdif-dai.o -diff --git a/sound/soc/meson/spdif-dai.c b/sound/soc/meson/spdif-dai.c -new file mode 100644 -index 0000000..e763000 ---- /dev/null -+++ b/sound/soc/meson/spdif-dai.c -@@ -0,0 +1,374 @@ -+/* -+ * 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 -+ -+#include "aiu-regs.h" -+#include "audio-core.h" -+ -+#define DRV_NAME "meson-spdif-dai" -+ -+struct meson_spdif_dai { -+ struct meson_audio_core_data *core; -+ struct clk *iface; -+ struct clk *fast; -+ struct clk *mclk_i958; -+ struct clk *mclk; -+}; -+ -+#define AIU_CLK_CTRL_958_DIV_EN BIT(1) -+#define AIU_CLK_CTRL_958_DIV_MASK GENMASK(5, 4) -+#define AIU_CLK_CTRL_958_DIV_MORE BIT(12) -+#define AIU_MEM_IEC958_CONTROL_MODE_LINEAR BIT(8) -+#define AIU_958_CTRL_HOLD_EN BIT(0) -+#define AIU_958_MISC_NON_PCM BIT(0) -+#define AIU_958_MISC_MODE_16BITS BIT(1) -+#define AIU_958_MISC_16BITS_ALIGN_MASK GENMASK(6, 5) -+#define AIU_958_MISC_16BITS_ALIGN(val) ((val) << 5) -+#define AIU_958_MISC_MODE_32BITS BIT(7) -+#define AIU_958_MISC_32BITS_SHIFT_MASK GENMASK(10, 8) -+#define AIU_958_MISC_32BITS_SHIFT(val) ((val) << 8) -+#define AIU_958_MISC_U_FROM_STREAM BIT(12) -+#define AIU_958_MISC_FORCE_LR BIT(13) -+ -+#define AIU_CS_WORD_LEN 4 -+ -+static void __hold(struct meson_spdif_dai *priv, bool enable) -+{ -+ regmap_update_bits(priv->core->aiu, AIU_958_CTRL, -+ AIU_958_CTRL_HOLD_EN, -+ enable ? AIU_958_CTRL_HOLD_EN : 0); -+} -+ -+static void __divider_enable(struct meson_spdif_dai *priv, bool enable) -+{ -+ regmap_update_bits(priv->core->aiu, AIU_CLK_CTRL, -+ AIU_CLK_CTRL_958_DIV_EN, -+ enable ? AIU_CLK_CTRL_958_DIV_EN : 0); -+} -+ -+static void __playback_start(struct meson_spdif_dai *priv) -+{ -+ __divider_enable(priv, true); -+ __hold(priv, false); -+} -+ -+static void __playback_stop(struct meson_spdif_dai *priv) -+{ -+ __hold(priv, true); -+ __divider_enable(priv, false); -+} -+ -+static int meson_spdif_dai_trigger(struct snd_pcm_substream *substream, int cmd, -+ struct snd_soc_dai *dai) -+{ -+ struct meson_spdif_dai *priv = snd_soc_dai_get_drvdata(dai); -+ -+ 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: -+ case SNDRV_PCM_TRIGGER_PAUSE_PUSH: -+ __playback_stop(priv); -+ return 0; -+ -+ default: -+ return -EINVAL; -+ } -+} -+ -+static int __setup_spdif_clk(struct meson_spdif_dai *priv, unsigned int rate) -+{ -+ unsigned int mrate; -+ -+ /* Leave the internal divisor alone */ -+ regmap_update_bits(priv->core->aiu, AIU_CLK_CTRL, -+ AIU_CLK_CTRL_958_DIV_MASK | -+ AIU_CLK_CTRL_958_DIV_MORE, -+ 0); -+ -+ /* 2 * 32bits per subframe * 2 channels = 128 */ -+ mrate = rate * 128; -+ return clk_set_rate(priv->mclk, mrate); -+} -+ -+static int __setup_cs_word(struct meson_spdif_dai *priv, -+ struct snd_pcm_hw_params *params) -+{ -+ u8 cs[AIU_CS_WORD_LEN]; -+ u32 val; -+ int ret; -+ -+ ret = snd_pcm_create_iec958_consumer_hw_params(params, cs, -+ AIU_CS_WORD_LEN); -+ if (ret < 0) -+ return -EINVAL; -+ -+ /* Write the 1st half word */ -+ val = cs[1] | cs[0] << 8; -+ regmap_write(priv->core->aiu, AIU_958_CHSTAT_L0, val); -+ regmap_write(priv->core->aiu, AIU_958_CHSTAT_R0, val); -+ -+ /* Write the 2nd half word */ -+ val = cs[3] | cs[2] << 8; -+ regmap_write(priv->core->aiu, AIU_958_CHSTAT_L1, val); -+ regmap_write(priv->core->aiu, AIU_958_CHSTAT_R1, val); -+ -+ return 0; -+} -+ -+static int __setup_pcm_fmt(struct meson_spdif_dai *priv, -+ unsigned int width) -+{ -+ u32 val = 0; -+ -+ switch (width) { -+ case 16: -+ val |= AIU_958_MISC_MODE_16BITS; -+ val |= AIU_958_MISC_16BITS_ALIGN(2); -+ break; -+ case 32: -+ case 24: -+ /* -+ * Looks like this should only be set for 32bits mode, but the -+ * vendor kernel sets it like this for 24bits as well, let's -+ * try and see -+ */ -+ val |= AIU_958_MISC_MODE_32BITS; -+ break; -+ default: -+ return -EINVAL; -+ } -+ -+ /* No idea what this actually does, copying the vendor kernel for now */ -+ val |= AIU_958_MISC_FORCE_LR; -+ val |= AIU_958_MISC_U_FROM_STREAM; -+ -+ regmap_update_bits(priv->core->aiu, AIU_958_MISC, -+ AIU_958_MISC_NON_PCM | -+ AIU_958_MISC_MODE_16BITS | -+ AIU_958_MISC_16BITS_ALIGN_MASK | -+ AIU_958_MISC_MODE_32BITS | -+ AIU_958_MISC_FORCE_LR, -+ val); -+ -+ return 0; -+} -+ -+static int meson_spdif_dai_hw_params(struct snd_pcm_substream *substream, -+ struct snd_pcm_hw_params *params, -+ struct snd_soc_dai *dai) -+{ -+ struct meson_spdif_dai *priv = snd_soc_dai_get_drvdata(dai); -+ int ret; -+ -+ ret = __setup_spdif_clk(priv, params_rate(params)); -+ if (ret) { -+ dev_err(dai->dev, "Unable to set the spdif clock\n"); -+ return ret; -+ } -+ -+ ret = __setup_cs_word(priv, params); -+ if (ret) { -+ dev_err(dai->dev, "Unable to set the channel status word\n"); -+ return ret; -+ } -+ -+ ret = __setup_pcm_fmt(priv, params_width(params)); -+ if (ret) { -+ dev_err(dai->dev, "Unable to set the pcm format\n"); -+ return ret; -+ } -+ -+ return 0; -+} -+ -+static int meson_spdif_dai_startup(struct snd_pcm_substream *substream, -+ struct snd_soc_dai *dai) -+{ -+ struct meson_spdif_dai *priv = snd_soc_dai_get_drvdata(dai); -+ int ret; -+ -+ /* Power up the spdif 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); -+ -+ ret = clk_set_parent(priv->mclk, priv->mclk_i958); -+ if (ret) -+ return ret; -+ -+ /* Enable the clock gate */ -+ ret = clk_prepare_enable(priv->iface); -+ if (ret) -+ goto out_clk_iface; -+ -+ /* Enable the spdif clock */ -+ ret = clk_prepare_enable(priv->mclk); -+ if (ret) -+ goto out_mclk; -+ -+ /* -+ * Make sure the interface expect a memory layout we can work with -+ * MEM prefixed register usually belong to the DMA, but when the spdif -+ * DAI takes data from the i2s buffer, we need to make sure it works in -+ * split mode and not the "normal mode" (channel samples packed in -+ * 32 bytes groups) -+ */ -+ regmap_update_bits(priv->core->aiu, AIU_MEM_IEC958_CONTROL, -+ AIU_MEM_IEC958_CONTROL_MODE_LINEAR, -+ AIU_MEM_IEC958_CONTROL_MODE_LINEAR); -+ -+ return 0; -+ -+out_mclk: -+ clk_disable_unprepare(priv->iface); -+out_clk_iface: -+ clk_disable_unprepare(priv->fast); -+out_clk_fast: -+ return ret; -+} -+ -+static void meson_spdif_dai_shutdown(struct snd_pcm_substream *substream, -+ struct snd_soc_dai *dai) -+{ -+ struct meson_spdif_dai *priv = snd_soc_dai_get_drvdata(dai); -+ -+ clk_disable_unprepare(priv->iface); -+ clk_disable_unprepare(priv->mclk); -+ clk_disable_unprepare(priv->fast); -+} -+ -+static const struct snd_soc_dai_ops meson_spdif_dai_ops = { -+ .startup = meson_spdif_dai_startup, -+ .shutdown = meson_spdif_dai_shutdown, -+ .trigger = meson_spdif_dai_trigger, -+ .hw_params = meson_spdif_dai_hw_params, -+}; -+ -+static struct snd_soc_dai_driver meson_spdif_dai = { -+ .playback = { -+ .stream_name = "Playback", -+ .channels_min = 2, -+ .channels_max = 2, -+ .rates = (SNDRV_PCM_RATE_32000 | -+ SNDRV_PCM_RATE_44100 | -+ SNDRV_PCM_RATE_48000 | -+ SNDRV_PCM_RATE_96000 | -+ SNDRV_PCM_RATE_192000), -+ .formats = (SNDRV_PCM_FMTBIT_S16_LE | -+ SNDRV_PCM_FMTBIT_S24_LE) -+ }, -+ .ops = &meson_spdif_dai_ops, -+}; -+ -+static const struct snd_soc_component_driver meson_spdif_dai_component = { -+ .name = DRV_NAME, -+}; -+ -+static int meson_spdif_dai_probe(struct platform_device *pdev) -+{ -+ struct device *dev = &pdev->dev; -+ struct meson_spdif_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 spdif fast domain clockt\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 the dai clock gate\n"); -+ return PTR_ERR(priv->iface); -+ } -+ -+ priv->mclk_i958 = devm_clk_get(dev, "mclk_i958"); -+ if (IS_ERR(priv->mclk_i958)) { -+ if (PTR_ERR(priv->mclk_i958) != -EPROBE_DEFER) -+ dev_err(dev, "Can't get the spdif master clock\n"); -+ return PTR_ERR(priv->mclk_i958); -+ } -+ -+ /* -+ * TODO: the spdif dai can also get its data from the i2s fifo. -+ * For this use-case, the DAI driver will need to get the i2s master -+ * clock in order to reparent the spdif clock from cts_mclk_i958 to -+ * cts_amclk -+ */ -+ -+ priv->mclk = devm_clk_get(dev, "mclk"); -+ if (IS_ERR(priv->mclk)) { -+ if (PTR_ERR(priv->mclk) != -EPROBE_DEFER) -+ dev_err(dev, "Can't get the spdif input mux clock\n"); -+ return PTR_ERR(priv->mclk); -+ } -+ -+ return devm_snd_soc_register_component(dev, &meson_spdif_dai_component, -+ &meson_spdif_dai, 1); -+} -+ -+static const struct of_device_id meson_spdif_dai_of_match[] = { -+ { .compatible = "amlogic,meson-spdif-dai", }, -+ { .compatible = "amlogic,meson-gxbb-spdif-dai", }, -+ { .compatible = "amlogic,meson-gxl-spdif-dai", }, -+ {} -+}; -+MODULE_DEVICE_TABLE(of, meson_spdif_dai_of_match); -+ -+static struct platform_driver meson_spdif_dai_pdrv = { -+ .probe = meson_spdif_dai_probe, -+ .driver = { -+ .name = DRV_NAME, -+ .of_match_table = meson_spdif_dai_of_match, -+ }, -+}; -+module_platform_driver(meson_spdif_dai_pdrv); -+ -+MODULE_DESCRIPTION("Meson spdif DAI ASoC Driver"); -+MODULE_AUTHOR("Jerome Brunet "); -+MODULE_LICENSE("GPL v2"); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/029_linux-4.18-yocto-meson64-0012-ARM64-defconfig-enable-audio-support-for-meson-SoCs-.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/029_linux-4.18-yocto-meson64-0012-ARM64-defconfig-enable-audio-support-for-meson-SoCs-.patch deleted file mode 100644 index ff2035ecc..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/029_linux-4.18-yocto-meson64-0012-ARM64-defconfig-enable-audio-support-for-meson-SoCs-.patch +++ /dev/null @@ -1,29 +0,0 @@ -From 5ddca63ac5c5d81c6d6a6745670a3f136970eaef Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Fri, 31 Mar 2017 15:55:03 +0200 -Subject: [PATCH] ARM64: defconfig: enable audio support for meson SoCs as - module - -Add audio support for meson SoCs. This includes the audio core -driver and the i2s and spdif output interfaces - -Signed-off-by: Jerome Brunet ---- - arch/arm64/configs/defconfig | 4 ++++ - 1 file changed, 4 insertions(+) - -diff --git a/arch/arm64/configs/defconfig b/arch/arm64/configs/defconfig -index 2584605..ae1f774 100644 ---- a/arch/arm64/configs/defconfig -+++ b/arch/arm64/configs/defconfig -@@ -451,6 +451,10 @@ CONFIG_SOUND=y - CONFIG_SND=y - CONFIG_SND_SOC=y - CONFIG_SND_BCM2835_SOC_I2S=m -+CONFIG_SND_SOC_MESON=m -+CONFIG_SND_SOC_MESON_I2S=m -+CONFIG_SND_SOC_MESON_SPDIF=m -+CONFIG_SND_SOC_RCAR=y - CONFIG_SND_SOC_SAMSUNG=y - CONFIG_SND_SOC_RCAR=m - CONFIG_SND_SOC_AK4613=m diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/030_linux-4.18-yocto-meson64-0013-ARM64-dts-meson-gx-add-audio-controller-nodes.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/030_linux-4.18-yocto-meson64-0013-ARM64-dts-meson-gx-add-audio-controller-nodes.patch deleted file mode 100644 index f58d3ef3c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/030_linux-4.18-yocto-meson64-0013-ARM64-dts-meson-gx-add-audio-controller-nodes.patch +++ /dev/null @@ -1,186 +0,0 @@ -From f4d7ad156ad2253d5ec3e79ea36309e27b8fabc7 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 30 Mar 2017 15:19:04 +0200 -Subject: [PATCH] ARM64: dts: meson-gx: add audio controller nodes - -Add audio controller nodes for Amlogic meson gxbb and gxl. -This includes the audio-core node, the i2s and spdif DAIs, i2s and spdif -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, etc ...) - -Signed-off-by: Jerome Brunet ---- - arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 35 ++++++++++++++++++++++++++ - arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 39 +++++++++++++++++++++++++++++ - arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 38 ++++++++++++++++++++++++++++ - 3 files changed, 112 insertions(+) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -index b8dc4db..6b64b63 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -203,6 +203,41 @@ - #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"; -+ }; -+ -+ aiu_spdif_dma: aiu_spdif_dma { -+ #sound-dai-cells = <0>; -+ compatible = "amlogic,meson-aiu-spdif-dma"; -+ interrupts = ; -+ status = "disabled"; -+ }; -+ -+ i2s_dai: i2s_dai { -+ #sound-dai-cells = <0>; -+ compatible = "amlogic,meson-i2s-dai"; -+ status = "disabled"; -+ }; -+ -+ spdif_dai: spdif_dai { -+ #sound-dai-cells = <0>; -+ compatible = "amlogic,meson-spdif-dai"; -+ status = "disabled"; -+ }; -+ -+ }; -+ - uart_A: serial@84c0 { - compatible = "amlogic,meson-gx-uart"; - reg = <0x0 0x84c0 0x0 0x18>; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -index 98cbba6..7913249 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -@@ -659,6 +659,35 @@ - }; - }; - -+&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"; -+}; -+ -+&aiu_spdif_dma { -+ clocks = <&clkc CLKID_IEC958>; -+ 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"; -+}; -+ - &pwrc_vpu { - resets = <&reset RESET_VIU>, - <&reset RESET_VENC>, -@@ -741,6 +770,15 @@ - num-cs = <1>; - }; - -+&spdif_dai { -+ clocks = <&clkc CLKID_IEC958>, -+ <&clkc CLKID_IEC958_GATE>, -+ <&clkc CLKID_CTS_MCLK_I958>, -+ <&clkc CLKID_CTS_AMCLK>, -+ <&clkc CLKID_CTS_I958>; -+ clock-names = "fast", "iface", "mclk_i958", "mclk_i2s", "mclk"; -+}; -+ - &spifc { - clocks = <&clkc CLKID_SPI>; - }; -@@ -774,3 +812,4 @@ - 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 c87a80e..20922cd 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -660,6 +660,34 @@ - }; - }; - -+&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"; -+}; -+ -+&aiu_spdif_dma { -+ clocks = <&clkc CLKID_IEC958>; -+ 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"; -+}; -+ - &pwrc_vpu { - resets = <&reset RESET_VIU>, - <&reset RESET_VENC>, -@@ -742,6 +770,15 @@ - num-cs = <1>; - }; - -+&spdif_dai { -+ clocks = <&clkc CLKID_IEC958>, -+ <&clkc CLKID_IEC958_GATE>, -+ <&clkc CLKID_CTS_MCLK_I958>, -+ <&clkc CLKID_CTS_AMCLK>, -+ <&clkc CLKID_CTS_I958>; -+ clock-names = "fast", "iface", "mclk_i958", "mclk_i2s", "mclk"; -+}; -+ - &spifc { - clocks = <&clkc CLKID_SPI>; - }; -@@ -775,3 +812,4 @@ - compatible = "amlogic,meson-gxl-vpu", "amlogic,meson-gx-vpu"; - power-domains = <&pwrc_vpu>; - }; -+ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/031_linux-4.18-yocto-meson64-0014-snd-meson-activate-HDMI-audio-path.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/031_linux-4.18-yocto-meson64-0014-snd-meson-activate-HDMI-audio-path.patch deleted file mode 100644 index 26dedf3d2..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/031_linux-4.18-yocto-meson64-0014-snd-meson-activate-HDMI-audio-path.patch +++ /dev/null @@ -1,52 +0,0 @@ -From 69d2f200d91fbd48e2388a8c5346f10d889a2928 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Fri, 7 Jul 2017 17:39:21 +0200 -Subject: [PATCH] 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; - } - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/032_linux-4.18-yocto-meson64-0015-drm-meson-select-dw-hdmi-i2s-audio-for-meson-hdmi.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/032_linux-4.18-yocto-meson64-0015-drm-meson-select-dw-hdmi-i2s-audio-for-meson-hdmi.patch deleted file mode 100644 index cb88ebaf1..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/032_linux-4.18-yocto-meson64-0015-drm-meson-select-dw-hdmi-i2s-audio-for-meson-hdmi.patch +++ /dev/null @@ -1,19 +0,0 @@ -From 223d7ef1a49981c597094e8519e150108cba9ef9 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Tue, 14 Feb 2017 19:18:04 +0100 -Subject: [PATCH] drm/meson: select dw-hdmi i2s audio for meson hdmi - -Signed-off-by: Jerome Brunet ---- - 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 diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/033_linux-4.18-yocto-meson64-0016-ARM64-dts-meson-gx-add-sound-dai-cells-to-HDMI-node.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/033_linux-4.18-yocto-meson64-0016-ARM64-dts-meson-gx-add-sound-dai-cells-to-HDMI-node.patch deleted file mode 100644 index a5e4fab7a..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/033_linux-4.18-yocto-meson64-0016-ARM64-dts-meson-gx-add-sound-dai-cells-to-HDMI-node.patch +++ /dev/null @@ -1,35 +0,0 @@ -From 00ce6fbb804c6aaecd3bde8f2978d091fbc0546c Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Wed, 20 Sep 2017 18:01:26 +0200 -Subject: [PATCH] ARM64: dts: meson-gx: add sound-dai-cells to HDMI node - -Signed-off-by: Jerome Brunet ---- - arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 1 + - arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 1 + - 2 files changed, 2 insertions(+) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -index 7913249..2a4d506 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -@@ -305,6 +305,7 @@ - <&clkc CLKID_CLK81>, - <&clkc CLKID_GCLK_VENCI_INT0>; - clock-names = "isfr", "iahb", "venci"; -+ #sound-dai-cells = <0>; - }; - - &sysctrl { -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -index 20922cd..9f4b618 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -257,6 +257,7 @@ - <&clkc CLKID_CLK81>, - <&clkc CLKID_GCLK_VENCI_INT0>; - clock-names = "isfr", "iahb", "venci"; -+ #sound-dai-cells = <0>; - }; - - &sysctrl { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/034_linux-4.18-yocto-meson64-0017-ARM64-dts-meson-activate-hdmi-audio-HDMI-enabled-boa.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/034_linux-4.18-yocto-meson64-0017-ARM64-dts-meson-activate-hdmi-audio-HDMI-enabled-boa.patch deleted file mode 100644 index e02abbfe2..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/034_linux-4.18-yocto-meson64-0017-ARM64-dts-meson-activate-hdmi-audio-HDMI-enabled-boa.patch +++ /dev/null @@ -1,860 +0,0 @@ -From 2df1a3a93bc1ce2d04fa0f0743c9c30195c7057a Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Wed, 20 Sep 2017 18:10:08 +0200 -Subject: [PATCH] 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 | 45 ++++++++++++++++++++++ - .../boot/dts/amlogic/meson-gxbb-nanopi-k2.dts | 45 ++++++++++++++++++++++ - .../boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts | 45 ++++++++++++++++++++++ - .../arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts | 45 ++++++++++++++++++++++ - arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi | 45 ++++++++++++++++++++++ - arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi | 45 ++++++++++++++++++++++ - .../dts/amlogic/meson-gxl-s905x-khadas-vim.dts | 45 ++++++++++++++++++++++ - .../dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 45 ++++++++++++++++++++++ - .../dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts | 45 ++++++++++++++++++++++ - .../boot/dts/amlogic/meson-gxl-s905x-p212.dts | 45 ++++++++++++++++++++++ - .../boot/dts/amlogic/meson-gxm-khadas-vim2.dts | 45 ++++++++++++++++++++++ - .../arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts | 45 ++++++++++++++++++++++ - 12 files changed, 540 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 88e712e..319512e 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi -@@ -95,6 +95,39 @@ - }; - }; - }; -+ -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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 { -@@ -104,6 +137,14 @@ - hdmi-phandle = <&hdmi_tx>; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ - &cvbs_vdac_port { - cvbs_vdac_out: endpoint { - remote-endpoint = <&cvbs_connector_in>; -@@ -126,6 +167,10 @@ - }; - }; - -+&i2s_dai { -+ status = "okay"; -+}; -+ - &ir { - status = "okay"; - pinctrl-0 = <&remote_input_ao_pins>; -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 cbe99bd..5b10de9 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -@@ -88,6 +88,39 @@ - clock-names = "ext_clock"; - }; - -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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>; -+ }; -+ }; -+ }; -+ - vcc1v8: regulator-vcc1v8 { - compatible = "regulator-fixed"; - regulator-name = "VCC1.8V"; -@@ -131,6 +164,14 @@ - }; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ - &cec_AO { - status = "okay"; - pinctrl-0 = <&ao_cec_pins>; -@@ -185,6 +226,10 @@ - }; - }; - -+&i2s_dai { -+ status = "okay"; -+}; -+ - &ir { - status = "okay"; - pinctrl-0 = <&remote_input_ao_pins>; -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 4cf7f6e..ff87bdc 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts -@@ -119,6 +119,39 @@ - clock-names = "ext_clock"; - }; - -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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"; - -@@ -154,6 +187,14 @@ - hdmi-phandle = <&hdmi_tx>; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ - ðmac { - status = "okay"; - pinctrl-0 = <ð_rmii_pins>; -@@ -190,6 +231,10 @@ - }; - }; - -+&i2s_dai { -+ status = "okay"; -+}; -+ - &ir { - status = "okay"; - pinctrl-0 = <&remote_input_ao_pins>; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -index 54954b3..3da3309 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -@@ -110,6 +110,39 @@ - }; - }; - }; -+ -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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 { -@@ -119,6 +152,14 @@ - hdmi-phandle = <&hdmi_tx>; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ - ðmac { - status = "okay"; - pinctrl-0 = <ð_rgmii_pins>; -@@ -181,6 +222,10 @@ - pinctrl-names = "default"; - }; - -+&i2s_dai { -+ status = "okay"; -+}; -+ - &ir { - status = "okay"; - pinctrl-0 = <&remote_input_ao_pins>; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi -index ce86226..84eb93b 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi -@@ -113,6 +113,39 @@ - }; - }; - }; -+ -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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 { -@@ -122,6 +155,14 @@ - hdmi-phandle = <&hdmi_tx>; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ - &cvbs_vdac_port { - cvbs_vdac_out: endpoint { - remote-endpoint = <&cvbs_connector_in>; -@@ -140,6 +181,10 @@ - }; - }; - -+&i2s_dai { -+ status = "okay"; -+}; -+ - &ir { - status = "okay"; - pinctrl-0 = <&remote_input_ao_pins>; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi -index 70325b2..7d1f172 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi -@@ -105,6 +105,47 @@ - }; - }; - }; -+ -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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>; -+ }; -+ }; -+ }; -+}; -+ -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; - }; - - &cec_AO { -@@ -159,6 +200,10 @@ - }; - }; - -+&i2s_dai { -+ status = "okay"; -+}; -+ - &ir { - status = "okay"; - pinctrl-0 = <&remote_input_ao_pins>; -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 d32cf38..f053595 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,39 @@ - }; - }; - }; -+ -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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 +107,14 @@ - hdmi-phandle = <&hdmi_tx>; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ - &hdmi_tx { - status = "okay"; - pinctrl-0 = <&hdmi_hpd_pins>, <&hdmi_i2c_pins>; -@@ -86,6 +127,10 @@ - }; - }; - -+&i2s_dai { -+ status = "okay"; -+}; -+ - &i2c_A { - status = "okay"; - pinctrl-0 = <&i2c_a_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 f63bceb..f56969e 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 -@@ -84,6 +84,39 @@ - regulator-always-on; - }; - -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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"; -@@ -130,6 +163,14 @@ - hdmi-phandle = <&hdmi_tx>; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ - &cvbs_vdac_port { - cvbs_vdac_out: endpoint { - remote-endpoint = <&cvbs_connector_in>; -@@ -151,6 +192,10 @@ - pinctrl-names = "default"; - }; - -+&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-nexbox-a95x.dts b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts -index 6739697..e3e777f 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 -@@ -102,6 +102,39 @@ - }; - }; - }; -+ -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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 { -@@ -111,6 +144,14 @@ - hdmi-phandle = <&hdmi_tx>; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ - &cvbs_vdac_port { - cvbs_vdac_out: endpoint { - remote-endpoint = <&cvbs_connector_in>; -@@ -135,6 +176,10 @@ - }; - }; - -+&i2s_dai { -+ status = "okay"; -+}; -+ - &ir { - status = "okay"; - pinctrl-0 = <&remote_input_ao_pins>; -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 5896e8a..f8c66a7 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts -@@ -32,6 +32,39 @@ - }; - }; - }; -+ -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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 { -@@ -41,12 +74,24 @@ - hdmi-phandle = <&hdmi_tx>; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ - &cvbs_vdac_port { - cvbs_vdac_out: endpoint { - remote-endpoint = <&cvbs_connector_in>; - }; - }; - -+&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-gxm-khadas-vim2.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -index 0868da4..ea71261 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -@@ -85,6 +85,39 @@ - }; - }; - -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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"; - -@@ -205,6 +238,14 @@ - hdmi-phandle = <&hdmi_tx>; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ - &cpu0 { - #cooling-cells = <2>; - }; -@@ -255,6 +296,10 @@ - }; - }; - -+&i2s_dai { -+ status = "okay"; -+}; -+ - &i2c_A { - status = "okay"; - pinctrl-0 = <&i2c_a_pins>; -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 f7a1cff..b9c5e64 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts -@@ -75,6 +75,39 @@ - }; - }; - }; -+ -+ sound { -+ compatible = "simple-audio-card"; -+ simple-audio-card,name = "meson-gx-audio"; -+ -+ assigned-clocks = <&clkc CLKID_MPLL2>, -+ <&clkc CLKID_MPLL0>, -+ <&clkc CLKID_MPLL1>; -+ assigned-clock-parents = <0>, <0>, <0>; -+ assigned-clock-rates = <294912000>, -+ <270950400>, -+ <393216000>; -+ -+ 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 { -@@ -84,6 +117,14 @@ - hdmi-phandle = <&hdmi_tx>; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ - &cvbs_vdac_port { - cvbs_vdac_out: endpoint { - remote-endpoint = <&cvbs_connector_in>; -@@ -129,6 +170,10 @@ - }; - }; - -+&i2s_dai { -+ status = "okay"; -+}; -+ - &ir { - status = "okay"; - pinctrl-0 = <&remote_input_ao_pins>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/035_linux-4.18-yocto-meson64-0018-drm-bridge-dw-hdmi-Use-AUTO-CTS-setup-mode-when-non-.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/035_linux-4.18-yocto-meson64-0018-drm-bridge-dw-hdmi-Use-AUTO-CTS-setup-mode-when-non-.patch deleted file mode 100644 index fbff6c8d8..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/035_linux-4.18-yocto-meson64-0018-drm-bridge-dw-hdmi-Use-AUTO-CTS-setup-mode-when-non-.patch +++ /dev/null @@ -1,75 +0,0 @@ -From e282ad866be628951a95d297207c9a5580f4101d Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Mon, 2 Jul 2018 12:21:55 +0200 -Subject: [PATCH] drm: bridge: dw-hdmi: Use AUTO CTS setup mode when non-AHB - audio - -Signed-off-by: Neil Armstrong ---- - drivers/gpu/drm/bridge/synopsys/dw-hdmi.c | 41 ++++++++++++++++++++----------- - 1 file changed, 26 insertions(+), 15 deletions(-) - -diff --git a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -index 3c136f2b..a68ffbb 100644 ---- a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -+++ b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -@@ -430,8 +430,12 @@ static void hdmi_set_cts_n(struct dw_hdmi *hdmi, unsigned int cts, - /* nshift factor = 0 */ - hdmi_modb(hdmi, 0, HDMI_AUD_CTS3_N_SHIFT_MASK, HDMI_AUD_CTS3); - -- hdmi_writeb(hdmi, ((cts >> 16) & HDMI_AUD_CTS3_AUDCTS19_16_MASK) | -- HDMI_AUD_CTS3_CTS_MANUAL, HDMI_AUD_CTS3); -+ /* Use Auto CTS mode with CTS is unknown */ -+ if (cts) -+ hdmi_writeb(hdmi, ((cts >> 16) & HDMI_AUD_CTS3_AUDCTS19_16_MASK) | -+ HDMI_AUD_CTS3_CTS_MANUAL, HDMI_AUD_CTS3); -+ else -+ hdmi_writeb(hdmi, 0, HDMI_AUD_CTS3); - hdmi_writeb(hdmi, (cts >> 8) & 0xff, HDMI_AUD_CTS2); - hdmi_writeb(hdmi, cts & 0xff, HDMI_AUD_CTS1); - -@@ -501,24 +505,31 @@ static void hdmi_set_clk_regenerator(struct dw_hdmi *hdmi, - { - unsigned long ftdms = pixel_clk; - unsigned int n, cts; -+ u8 config3; - u64 tmp; - - n = hdmi_compute_n(sample_rate, pixel_clk); - -- /* -- * Compute the CTS value from the N value. Note that CTS and N -- * can be up to 20 bits in total, so we need 64-bit math. Also -- * note that our TDMS clock is not fully accurate; it is accurate -- * to kHz. This can introduce an unnecessary remainder in the -- * calculation below, so we don't try to warn about that. -- */ -- tmp = (u64)ftdms * n; -- do_div(tmp, 128 * sample_rate); -- cts = tmp; -+ config3 = hdmi_readb(hdmi, HDMI_CONFIG3_ID); - -- dev_dbg(hdmi->dev, "%s: fs=%uHz ftdms=%lu.%03luMHz N=%d cts=%d\n", -- __func__, sample_rate, ftdms / 1000000, (ftdms / 1000) % 1000, -- n, cts); -+ if (config3 & HDMI_CONFIG3_AHBAUDDMA) { -+ /* -+ * Compute the CTS value from the N value. Note that CTS and N -+ * can be up to 20 bits in total, so we need 64-bit math. Also -+ * note that our TDMS clock is not fully accurate; it is -+ * accurate to kHz. This can introduce an unnecessary remainder -+ * in the calculation below, so we don't try to warn about that. -+ */ -+ tmp = (u64)ftdms * n; -+ do_div(tmp, 128 * sample_rate); -+ cts = tmp; -+ -+ dev_dbg(hdmi->dev, "%s: fs=%uHz ftdms=%lu.%03luMHz N=%d cts=%d\n", -+ __func__, sample_rate, -+ ftdms / 1000000, (ftdms / 1000) % 1000, -+ n, cts); -+ } else -+ cts = 0; - - spin_lock_irq(&hdmi->audio_lock); - hdmi->audio_n = n; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/036_linux-4.18-yocto-meson64-0019-drm-meson-Call-drm_crtc_vblank_on-drm_crtc_vblank_of.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/036_linux-4.18-yocto-meson64-0019-drm-meson-Call-drm_crtc_vblank_on-drm_crtc_vblank_of.patch deleted file mode 100644 index 314ff482b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/036_linux-4.18-yocto-meson64-0019-drm-meson-Call-drm_crtc_vblank_on-drm_crtc_vblank_of.patch +++ /dev/null @@ -1,36 +0,0 @@ -From 4a3a6d04d4996ff0a0acc8405fdd0b0347a62138 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Wed, 28 Feb 2018 16:07:18 +0100 -Subject: [PATCH] drm/meson: Call drm_crtc_vblank_on / drm_crtc_vblank_off - -Make sure that the CRTC code will call the enable/disable_vblank hooks. - -Signed-off-by: Neil Armstrong ---- - drivers/gpu/drm/meson/meson_crtc.c | 6 ++++++ - 1 file changed, 6 insertions(+) - -diff --git a/drivers/gpu/drm/meson/meson_crtc.c b/drivers/gpu/drm/meson/meson_crtc.c -index 0552020..4dd0df0 100644 ---- a/drivers/gpu/drm/meson/meson_crtc.c -+++ b/drivers/gpu/drm/meson/meson_crtc.c -@@ -102,6 +102,8 @@ static void meson_crtc_atomic_enable(struct drm_crtc *crtc, - priv->io_base + _REG(VPP_MISC)); - - priv->viu.osd1_enabled = true; -+ -+ drm_crtc_vblank_on(crtc); - } - - static void meson_crtc_atomic_disable(struct drm_crtc *crtc, -@@ -110,6 +112,10 @@ static void meson_crtc_atomic_disable(struct drm_crtc *crtc, - struct meson_crtc *meson_crtc = to_meson_crtc(crtc); - struct meson_drm *priv = meson_crtc->priv; - -+ DRM_DEBUG_DRIVER("\n"); -+ -+ drm_crtc_vblank_off(crtc); -+ - priv->viu.osd1_enabled = false; - priv->viu.osd1_commit = false; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/037_linux-4.18-yocto-meson64-0020-media-platform-meson-ao-cec-make-busy-TX-warning-sil.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/037_linux-4.18-yocto-meson64-0020-media-platform-meson-ao-cec-make-busy-TX-warning-sil.patch deleted file mode 100644 index 81569fc4d..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/037_linux-4.18-yocto-meson64-0020-media-platform-meson-ao-cec-make-busy-TX-warning-sil.patch +++ /dev/null @@ -1,32 +0,0 @@ -From 830bb1ab9ee8999566a4d98086590ac824cdeb4e Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Tue, 10 Jul 2018 15:00:45 +0200 -Subject: [PATCH] media: platform: meson-ao-cec: make busy TX warning silent - -Switch to dev_dbg for the busy TX message to avoid having a flood of: -[ 228.064570] meson-ao-cec c8100100.cec: meson_ao_cec_transmit: busy TX: aborting -[ 230.368489] meson-ao-cec c8100100.cec: meson_ao_cec_transmit: busy TX: aborting -[ 234.208655] meson-ao-cec c8100100.cec: meson_ao_cec_transmit: busy TX: aborting -[ 236.512558] meson-ao-cec c8100100.cec: meson_ao_cec_transmit: busy TX: aborting - -This message is only a debug hint and not an error. - -Fixes: 7ec2c0f72cb1 ("media: platform: Add Amlogic Meson AO CEC Controller driver") -Signed-off-by: Neil Armstrong ---- - drivers/media/platform/meson/ao-cec.c | 2 +- - 1 file changed, 1 insertion(+), 1 deletion(-) - -diff --git a/drivers/media/platform/meson/ao-cec.c b/drivers/media/platform/meson/ao-cec.c -index 8040a62..cd4be38 100644 ---- a/drivers/media/platform/meson/ao-cec.c -+++ b/drivers/media/platform/meson/ao-cec.c -@@ -524,7 +524,7 @@ static int meson_ao_cec_transmit(struct cec_adapter *adap, u8 attempts, - return ret; - - if (reg == TX_BUSY) { -- dev_err(&ao_cec->pdev->dev, "%s: busy TX: aborting\n", -+ dev_dbg(&ao_cec->pdev->dev, "%s: busy TX: aborting\n", - __func__); - meson_ao_cec_write(ao_cec, CEC_TX_MSG_CMD, TX_ABORT, &ret); - } diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/045_linux-4.18-yocto-meson64-0001-libretech-cc-disable-CVBS-connector.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/045_linux-4.18-yocto-meson64-0001-libretech-cc-disable-CVBS-connector.patch deleted file mode 100644 index 7f8298118..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/045_linux-4.18-yocto-meson64-0001-libretech-cc-disable-CVBS-connector.patch +++ /dev/null @@ -1,24 +0,0 @@ -From baa0a8ee8b8a0a14ddab6b14c37846dfed261007 Mon Sep 17 00:00:00 2001 -From: Koen Kooi -Date: Fri, 11 May 2018 13:51:20 +0200 -Subject: [PATCH] libretech-cc: disable CVBS connector - -Signed-off-by: Koen Kooi ---- - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 3 ++- - 1 file changed, 2 insertions(+), 1 deletion(-) - -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 f56969e..ac3a150 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 -@@ -24,7 +24,8 @@ - stdout-path = "serial0:115200n8"; - }; - -- cvbs-connector { -+ cvbs_connector: cvbs-connector { -+ status = "disabled"; - compatible = "composite-video-connector"; - - port { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/048_linux-4.18.y-jeromebrunet-0001-clk-qcom-drop_clk_set_rate_gate_from_sdc_clocks.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/048_linux-4.18.y-jeromebrunet-0001-clk-qcom-drop_clk_set_rate_gate_from_sdc_clocks.patch deleted file mode 100644 index 0cd5bcd06..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/048_linux-4.18.y-jeromebrunet-0001-clk-qcom-drop_clk_set_rate_gate_from_sdc_clocks.patch +++ /dev/null @@ -1,161 +0,0 @@ -From e18fe49cfa5a989d0e8aca1b95a989f71c1916e7 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Tue, 19 Jun 2018 11:03:03 +0200 -Subject: [PATCH] clk: qcom: drop CLK_SET_RATE_GATE from sdc clocks - -the mmci driver (drivers/mmc/host/mmci.c) does the following sequence: -* clk_prepare_enable() -* clk_set_rate() - -on SDCx_clk which is a children of SDCx_src. SDCx_src has -CLK_SET_RATE_GATE so this sequence should not be allowed but this was not -enforced. IOW, the flag is ignored. Dropping the flag won't change -anything to the current behaviour of the platform. - -CLK_SET_RATE_GATE is being fixed and enforced now. If the flag was kept, -the mmci driver would receive -EBUSY when calling clk_set_rate() - -Signed-off-by: Jerome Brunet ---- - drivers/clk/qcom/gcc-ipq806x.c | 3 --- - drivers/clk/qcom/gcc-mdm9615.c | 2 -- - drivers/clk/qcom/gcc-msm8660.c | 5 ----- - drivers/clk/qcom/gcc-msm8960.c | 5 ----- - 4 files changed, 15 deletions(-) - -diff --git a/drivers/clk/qcom/gcc-ipq806x.c b/drivers/clk/qcom/gcc-ipq806x.c -index 28eb200d0f1ee..5f61225657abb 100644 ---- a/drivers/clk/qcom/gcc-ipq806x.c -+++ b/drivers/clk/qcom/gcc-ipq806x.c -@@ -1220,7 +1220,6 @@ static struct clk_rcg sdc1_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -@@ -1269,7 +1268,6 @@ static struct clk_rcg sdc3_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -@@ -1353,7 +1351,6 @@ static struct clk_rcg tsif_ref_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -diff --git a/drivers/clk/qcom/gcc-mdm9615.c b/drivers/clk/qcom/gcc-mdm9615.c -index b99dd406e9071..849046fbed6d4 100644 ---- a/drivers/clk/qcom/gcc-mdm9615.c -+++ b/drivers/clk/qcom/gcc-mdm9615.c -@@ -947,7 +947,6 @@ static struct clk_rcg sdc1_src = { - .parent_names = gcc_cxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -@@ -996,7 +995,6 @@ static struct clk_rcg sdc2_src = { - .parent_names = gcc_cxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -diff --git a/drivers/clk/qcom/gcc-msm8660.c b/drivers/clk/qcom/gcc-msm8660.c -index c347a0d44bc8b..7e930e25c79f1 100644 ---- a/drivers/clk/qcom/gcc-msm8660.c -+++ b/drivers/clk/qcom/gcc-msm8660.c -@@ -1558,7 +1558,6 @@ static struct clk_rcg sdc1_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -@@ -1607,7 +1606,6 @@ static struct clk_rcg sdc2_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -@@ -1656,7 +1654,6 @@ static struct clk_rcg sdc3_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -@@ -1705,7 +1702,6 @@ static struct clk_rcg sdc4_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -@@ -1754,7 +1750,6 @@ static struct clk_rcg sdc5_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -diff --git a/drivers/clk/qcom/gcc-msm8960.c b/drivers/clk/qcom/gcc-msm8960.c -index eb551c75fba6a..fd495e0471bb4 100644 ---- a/drivers/clk/qcom/gcc-msm8960.c -+++ b/drivers/clk/qcom/gcc-msm8960.c -@@ -1628,7 +1628,6 @@ static struct clk_rcg sdc1_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -@@ -1677,7 +1676,6 @@ static struct clk_rcg sdc2_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -@@ -1726,7 +1724,6 @@ static struct clk_rcg sdc3_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -@@ -1775,7 +1772,6 @@ static struct clk_rcg sdc4_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; -@@ -1824,7 +1820,6 @@ static struct clk_rcg sdc5_src = { - .parent_names = gcc_pxo_pll8, - .num_parents = 2, - .ops = &clk_rcg_ops, -- .flags = CLK_SET_RATE_GATE, - }, - } - }; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/049_linux-4.18.y-jeromebrunet-0002-clk-fix_clk_set_rate_gate_with_clock_rate_protection.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/049_linux-4.18.y-jeromebrunet-0002-clk-fix_clk_set_rate_gate_with_clock_rate_protection.patch deleted file mode 100644 index daba9ee1b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/049_linux-4.18.y-jeromebrunet-0002-clk-fix_clk_set_rate_gate_with_clock_rate_protection.patch +++ /dev/null @@ -1,70 +0,0 @@ -From b2ae7fbfe34642d87aeac299d9cec8f1e01ed0b2 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Fri, 1 Dec 2017 22:51:58 +0100 -Subject: [PATCH] clk: fix CLK_SET_RATE_GATE with clock rate protection - -CLK_SET_RATE_GATE should prevent any operation which may result in a rate -change or glitch while the clock is prepared/enabled. - -IOW, the following sequence is not allowed anymore with CLK_SET_RATE_GATE: -* clk_get() -* clk_prepare_enable() -* clk_get_rate() -* clk_set_rate() - -At the moment this is enforced on the leaf clock of the operation, not -along the tree. This problematic because, if a PLL has the CLK_RATE_GATE, -it won't be enforced if the clk_set_rate() is called on its child clocks. - -Using clock rate protection, we can now enforce CLK_SET_RATE_GATE along the -clock tree - -Acked-by: Linus Walleij -Tested-by: Quentin Schulz -Tested-by: Maxime Ripard -Signed-off-by: Jerome Brunet ---- - drivers/clk/clk.c | 16 +++++++++++++--- - 1 file changed, 13 insertions(+), 3 deletions(-) - -diff --git a/drivers/clk/clk.c b/drivers/clk/clk.c -index 9760b526ca31d..97c09243fb21c 100644 ---- a/drivers/clk/clk.c -+++ b/drivers/clk/clk.c -@@ -691,6 +691,9 @@ static void clk_core_unprepare(struct clk_core *core) - "Unpreparing critical %s\n", core->name)) - return; - -+ if (core->flags & CLK_SET_RATE_GATE) -+ clk_core_rate_unprotect(core); -+ - if (--core->prepare_count > 0) - return; - -@@ -765,6 +768,16 @@ static int clk_core_prepare(struct clk_core *core) - - core->prepare_count++; - -+ /* -+ * CLK_SET_RATE_GATE is a special case of clock protection -+ * Instead of a consumer claiming exclusive rate control, it is -+ * actually the provider which prevents any consumer from making any -+ * operation which could result in a rate change or rate glitch while -+ * the clock is prepared. -+ */ -+ if (core->flags & CLK_SET_RATE_GATE) -+ clk_core_rate_protect(core); -+ - return 0; - unprepare: - clk_core_unprepare(core->parent); -@@ -1888,9 +1901,6 @@ static int clk_core_set_rate_nolock(struct clk_core *core, - if (clk_core_rate_is_protected(core)) - return -EBUSY; - -- if ((core->flags & CLK_SET_RATE_GATE) && core->prepare_count) -- return -EBUSY; -- - /* calculate new rates and get the topmost changed clock */ - top = clk_calc_new_rates(core, req_rate); - if (!top) diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/050_linux-4.18.y-jeromebrunet-0003-media-rc-meson-rc_rc0-two_consecutive_events_of_type.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/050_linux-4.18.y-jeromebrunet-0003-media-rc-meson-rc_rc0-two_consecutive_events_of_type.patch deleted file mode 100644 index 4cd4c3aa4..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/050_linux-4.18.y-jeromebrunet-0003-media-rc-meson-rc_rc0-two_consecutive_events_of_type.patch +++ /dev/null @@ -1,29 +0,0 @@ -From df17d1808dd4899a9469e4e7f2d9b1120b7fc208 Mon Sep 17 00:00:00 2001 -From: Sean Young -Date: Tue, 19 Jun 2018 13:50:36 +0100 -Subject: [PATCH] media: rc: meson: rc rc0: two consecutive events of type - space - -The meson generates one edge per interrupt. The duration is encoded in 12 -bits of 10 microseconds, so it can only encoding a maximum of 40 -milliseconds. As a result, it can produce multiple space events. - -Signed-off-by: Sean Young ---- - drivers/media/rc/meson-ir.c | 3 ++- - 1 file changed, 2 insertions(+), 1 deletion(-) - -diff --git a/drivers/media/rc/meson-ir.c b/drivers/media/rc/meson-ir.c -index f449b35d25e73..9747426719b29 100644 ---- a/drivers/media/rc/meson-ir.c -+++ b/drivers/media/rc/meson-ir.c -@@ -97,7 +97,8 @@ static irqreturn_t meson_ir_irq(int irqno, void *dev_id) - status = readl_relaxed(ir->reg + IR_DEC_STATUS); - rawir.pulse = !!(status & STATUS_IR_DEC_IN); - -- ir_raw_event_store_with_timeout(ir->rc, &rawir); -+ if (ir_raw_event_store_with_filter(ir->rc, &rawir)) -+ ir_raw_event_handle(ir->rc); - - spin_unlock(&ir->lock); - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/051_linux-4.18.y-jeromebrunet-0004-clk-add_duty_cycle_support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/051_linux-4.18.y-jeromebrunet-0004-clk-add_duty_cycle_support.patch deleted file mode 100644 index 9547c408c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/051_linux-4.18.y-jeromebrunet-0004-clk-add_duty_cycle_support.patch +++ /dev/null @@ -1,461 +0,0 @@ -From 28d675fabd5e66be0ccc3cba655de36c7625f4a5 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Fri, 20 Apr 2018 23:11:41 +0200 -Subject: [PATCH] clk: add duty cycle support - -Add the possibility to apply and query the clock signal duty cycle ratio. - -This is useful when the duty cycle of the clock signal depends on some -other parameters controlled by the clock framework. - -For example, the duty cycle of a divider may depends on the raw divider -setting (ratio = N / div) , which is controlled by the CCF. In such case, -going through the pwm framework to control the duty cycle ratio of this -clock would be a burden. - -A clock provider is not required to implement the operation to set and get -the duty cycle. If it does not implement .get_duty_cycle(), the ratio is -assumed to be 50%. - -This change also adds a new flag, CLK_DUTY_CYCLE_PARENT. This flag should -be used to indicate that a clock, such as gates and muxes, may inherit -the duty cycle ratio of its parent clock. If a clock does not provide a -get_duty_cycle() callback and has CLK_DUTY_CYCLE_PARENT, then the call -will be directly forwarded to its parent clock, if any. For -set_duty_cycle(), the clock should also have CLK_SET_RATE_PARENT for the -call to be forwarded - -Signed-off-by: Jerome Brunet ---- - drivers/clk/clk.c | 199 ++++++++++++++++++++++++++++++++++- - include/linux/clk-provider.h | 26 +++++ - include/linux/clk.h | 33 ++++++ - include/trace/events/clk.h | 36 +++++++ - 4 files changed, 289 insertions(+), 5 deletions(-) - -diff --git a/drivers/clk/clk.c b/drivers/clk/clk.c -index 97c09243fb21c..e108f591d84a9 100644 ---- a/drivers/clk/clk.c -+++ b/drivers/clk/clk.c -@@ -68,6 +68,7 @@ struct clk_core { - unsigned long max_rate; - unsigned long accuracy; - int phase; -+ struct clk_duty duty; - struct hlist_head children; - struct hlist_node child_node; - struct hlist_head clks; -@@ -2412,6 +2413,172 @@ int clk_get_phase(struct clk *clk) - } - EXPORT_SYMBOL_GPL(clk_get_phase); - -+static void clk_core_reset_duty_cycle_nolock(struct clk_core *core) -+{ -+ /* Assume a default value of 50% */ -+ core->duty.num = 1; -+ core->duty.den = 2; -+} -+ -+static int clk_core_update_duty_cycle_parent_nolock(struct clk_core *core); -+ -+static int clk_core_update_duty_cycle_nolock(struct clk_core *core) -+{ -+ struct clk_duty *duty = &core->duty; -+ int ret = 0; -+ -+ if (!core->ops->get_duty_cycle) -+ return clk_core_update_duty_cycle_parent_nolock(core); -+ -+ ret = core->ops->get_duty_cycle(core->hw, duty); -+ if (ret) -+ goto reset; -+ -+ /* Don't trust the clock provider too much */ -+ if (duty->den == 0 || duty->num > duty->den) { -+ ret = -EINVAL; -+ goto reset; -+ } -+ -+ return 0; -+ -+reset: -+ clk_core_reset_duty_cycle_nolock(core); -+ return ret; -+} -+ -+static int clk_core_update_duty_cycle_parent_nolock(struct clk_core *core) -+{ -+ int ret = 0; -+ -+ if (core->parent && -+ core->flags & CLK_DUTY_CYCLE_PARENT) { -+ ret = clk_core_update_duty_cycle_nolock(core->parent); -+ memcpy(&core->duty, &core->parent->duty, sizeof(core->duty)); -+ } else { -+ clk_core_reset_duty_cycle_nolock(core); -+ } -+ -+ return ret; -+} -+ -+static int clk_core_set_duty_cycle_parent_nolock(struct clk_core *core, -+ struct clk_duty *duty); -+ -+static int clk_core_set_duty_cycle_nolock(struct clk_core *core, -+ struct clk_duty *duty) -+{ -+ int ret; -+ -+ lockdep_assert_held(&prepare_lock); -+ -+ if (clk_core_rate_is_protected(core)) -+ return -EBUSY; -+ -+ trace_clk_set_duty_cycle(core, duty); -+ -+ if (!core->ops->set_duty_cycle) -+ return clk_core_set_duty_cycle_parent_nolock(core, duty); -+ -+ ret = core->ops->set_duty_cycle(core->hw, duty); -+ if (!ret) -+ memcpy(&core->duty, duty, sizeof(*duty)); -+ -+ trace_clk_set_duty_cycle_complete(core, duty); -+ -+ return ret; -+} -+ -+static int clk_core_set_duty_cycle_parent_nolock(struct clk_core *core, -+ struct clk_duty *duty) -+{ -+ int ret = 0; -+ -+ if (core->parent && -+ core->flags & (CLK_DUTY_CYCLE_PARENT | CLK_SET_RATE_PARENT)) { -+ ret = clk_core_set_duty_cycle_nolock(core->parent, duty); -+ memcpy(&core->duty, &core->parent->duty, sizeof(core->duty)); -+ } -+ -+ return ret; -+} -+ -+/** -+ * clk_set_duty_cycle - adjust the duty cycle ratio of a clock signal -+ * @clk: clock signal source -+ * @num: numerator of the duty cycle ratio to be applied -+ * @den: denominator of the duty cycle ratio to be applied -+ * -+ * Apply the duty cycle ratio if the ratio is valid and the clock can -+ * perform this operation -+ * -+ * Returns (0) on success, a negative errno otherwise. -+ */ -+int clk_set_duty_cycle(struct clk *clk, unsigned int num, unsigned int den) -+{ -+ int ret; -+ struct clk_duty duty; -+ -+ if (!clk) -+ return 0; -+ -+ /* sanity check the ratio */ -+ if (den == 0 || num > den) -+ return -EINVAL; -+ -+ duty.num = num; -+ duty.den = den; -+ -+ clk_prepare_lock(); -+ -+ if (clk->exclusive_count) -+ clk_core_rate_unprotect(clk->core); -+ -+ ret = clk_core_set_duty_cycle_nolock(clk->core, &duty); -+ -+ if (clk->exclusive_count) -+ clk_core_rate_protect(clk->core); -+ -+ clk_prepare_unlock(); -+ -+ return ret; -+} -+EXPORT_SYMBOL_GPL(clk_set_duty_cycle); -+ -+static int clk_core_get_scaled_duty_cycle(struct clk_core *core, -+ unsigned int scale) -+{ -+ struct clk_duty *duty = &core->duty; -+ int ret; -+ -+ clk_prepare_lock(); -+ -+ ret = clk_core_update_duty_cycle_nolock(core); -+ if (!ret) -+ ret = mult_frac(scale, duty->num, duty->den); -+ -+ clk_prepare_unlock(); -+ -+ return ret; -+} -+ -+/** -+ * clk_get_scaled_duty_cycle - return the duty cycle ratio of a clock signal -+ * @clk: clock signal source -+ * @scale: scaling factor to be applied to represent the ratio as an integer -+ * -+ * Returns the duty cycle ratio of a clock node multiplied by the provided -+ * scaling factor, or negative errno on error. -+ */ -+int clk_get_scaled_duty_cycle(struct clk *clk, unsigned int scale) -+{ -+ if (!clk) -+ return 0; -+ -+ return clk_core_get_scaled_duty_cycle(clk->core, scale); -+} -+EXPORT_SYMBOL_GPL(clk_get_scaled_duty_cycle); -+ - /** - * clk_is_match - check if two clk's point to the same hardware clock - * @p: clk compared against q -@@ -2465,12 +2632,13 @@ static void clk_summary_show_one(struct seq_file *s, struct clk_core *c, - if (!c) - return; - -- seq_printf(s, "%*s%-*s %7d %8d %8d %11lu %10lu %-3d\n", -+ seq_printf(s, "%*s%-*s %7d %8d %8d %11lu %10lu %5d %6d\n", - level * 3 + 1, "", - 30 - level * 3, c->name, - c->enable_count, c->prepare_count, c->protect_count, - clk_core_get_rate(c), clk_core_get_accuracy(c), -- clk_core_get_phase(c)); -+ clk_core_get_phase(c), -+ clk_core_get_scaled_duty_cycle(c, 100000)); - } - - static void clk_summary_show_subtree(struct seq_file *s, struct clk_core *c, -@@ -2492,9 +2660,9 @@ static int clk_summary_show(struct seq_file *s, void *data) - struct clk_core *c; - struct hlist_head **lists = (struct hlist_head **)s->private; - -- seq_puts(s, " enable prepare protect \n"); -- seq_puts(s, " clock count count count rate accuracy phase\n"); -- seq_puts(s, "----------------------------------------------------------------------------------------\n"); -+ seq_puts(s, " enable prepare protect duty\n"); -+ seq_puts(s, " clock count count count rate accuracy phase cycle\n"); -+ seq_puts(s, "---------------------------------------------------------------------------------------------\n"); - - clk_prepare_lock(); - -@@ -2521,6 +2689,8 @@ static void clk_dump_one(struct seq_file *s, struct clk_core *c, int level) - seq_printf(s, "\"rate\": %lu,", clk_core_get_rate(c)); - seq_printf(s, "\"accuracy\": %lu,", clk_core_get_accuracy(c)); - seq_printf(s, "\"phase\": %d", clk_core_get_phase(c)); -+ seq_printf(s, "\"duty_cycle\": %u", -+ clk_core_get_scaled_duty_cycle(c, 100000)); - } - - static void clk_dump_subtree(struct seq_file *s, struct clk_core *c, int level) -@@ -2582,6 +2752,7 @@ static const struct { - ENTRY(CLK_SET_RATE_UNGATE), - ENTRY(CLK_IS_CRITICAL), - ENTRY(CLK_OPS_PARENT_ENABLE), -+ ENTRY(CLK_DUTY_CYCLE_PARENT), - #undef ENTRY - }; - -@@ -2620,6 +2791,17 @@ static int possible_parents_show(struct seq_file *s, void *data) - } - DEFINE_SHOW_ATTRIBUTE(possible_parents); - -+static int clk_duty_cycle_show(struct seq_file *s, void *data) -+{ -+ struct clk_core *core = s->private; -+ struct clk_duty *duty = &core->duty; -+ -+ seq_printf(s, "%u/%u\n", duty->num, duty->den); -+ -+ return 0; -+} -+DEFINE_SHOW_ATTRIBUTE(clk_duty_cycle); -+ - static void clk_debug_create_one(struct clk_core *core, struct dentry *pdentry) - { - struct dentry *root; -@@ -2638,6 +2820,8 @@ static void clk_debug_create_one(struct clk_core *core, struct dentry *pdentry) - debugfs_create_u32("clk_enable_count", 0444, root, &core->enable_count); - debugfs_create_u32("clk_protect_count", 0444, root, &core->protect_count); - debugfs_create_u32("clk_notifier_count", 0444, root, &core->notifier_count); -+ debugfs_create_file("clk_duty_cycle", 0444, root, core, -+ &clk_duty_cycle_fops); - - if (core->num_parents > 1) - debugfs_create_file("clk_possible_parents", 0444, root, core, -@@ -2855,6 +3039,11 @@ static int __clk_core_init(struct clk_core *core) - else - core->phase = 0; - -+ /* -+ * Set clk's duty cycle. -+ */ -+ clk_core_update_duty_cycle_nolock(core); -+ - /* - * Set clk's rate. The preferred method is to use .recalc_rate. For - * simple clocks and lazy developers the default fallback is to use the -diff --git a/include/linux/clk-provider.h b/include/linux/clk-provider.h -index b7cfa037e593e..08b1aa70a38d3 100644 ---- a/include/linux/clk-provider.h -+++ b/include/linux/clk-provider.h -@@ -38,6 +38,8 @@ - #define CLK_IS_CRITICAL BIT(11) /* do not gate, ever */ - /* parents need enable during gate/ungate, set rate and re-parent */ - #define CLK_OPS_PARENT_ENABLE BIT(12) -+/* duty cycle call may be forwarded to the parent clock */ -+#define CLK_DUTY_CYCLE_PARENT BIT(13) - - struct clk; - struct clk_hw; -@@ -66,6 +68,17 @@ struct clk_rate_request { - struct clk_hw *best_parent_hw; - }; - -+/** -+ * struct clk_duty - Struture encoding the duty cycle ratio of a clock -+ * -+ * @num: Numerator of the duty cycle ratio -+ * @den: Denominator of the duty cycle ratio -+ */ -+struct clk_duty { -+ unsigned int num; -+ unsigned int den; -+}; -+ - /** - * struct clk_ops - Callback operations for hardware clocks; these are to - * be provided by the clock implementation, and will be called by drivers -@@ -169,6 +182,15 @@ struct clk_rate_request { - * by the second argument. Valid values for degrees are - * 0-359. Return 0 on success, otherwise -EERROR. - * -+ * @get_duty_cycle: Queries the hardware to get the current duty cycle ratio -+ * of a clock. Returned values denominator cannot be 0 and must be -+ * superior or equal to the numerator. -+ * -+ * @set_duty_cycle: Apply the duty cycle ratio to this clock signal specified by -+ * the numerator (2nd argurment) and denominator (3rd argument). -+ * Argument must be a valid ratio (denominator > 0 -+ * and >= numerator) Return 0 on success, otherwise -EERROR. -+ * - * @init: Perform platform-specific initialization magic. - * This is not not used by any of the basic clock types. - * Please consider other ways of solving initialization problems -@@ -218,6 +240,10 @@ struct clk_ops { - unsigned long parent_accuracy); - int (*get_phase)(struct clk_hw *hw); - int (*set_phase)(struct clk_hw *hw, int degrees); -+ int (*get_duty_cycle)(struct clk_hw *hw, -+ struct clk_duty *duty); -+ int (*set_duty_cycle)(struct clk_hw *hw, -+ struct clk_duty *duty); - void (*init)(struct clk_hw *hw); - void (*debug_init)(struct clk_hw *hw, struct dentry *dentry); - }; -diff --git a/include/linux/clk.h b/include/linux/clk.h -index 0dbd0885b2c23..4f750c481b82b 100644 ---- a/include/linux/clk.h -+++ b/include/linux/clk.h -@@ -141,6 +141,27 @@ int clk_set_phase(struct clk *clk, int degrees); - */ - int clk_get_phase(struct clk *clk); - -+/** -+ * clk_set_duty_cycle - adjust the duty cycle ratio of a clock signal -+ * @clk: clock signal source -+ * @num: numerator of the duty cycle ratio to be applied -+ * @den: denominator of the duty cycle ratio to be applied -+ * -+ * Adjust the duty cycle of a clock signal by the specified ratio. Returns 0 on -+ * success, -EERROR otherwise. -+ */ -+int clk_set_duty_cycle(struct clk *clk, unsigned int num, unsigned int den); -+ -+/** -+ * clk_get_duty_cycle - return the duty cycle ratio of a clock signal -+ * @clk: clock signal source -+ * @scale: scaling factor to be applied to represent the ratio as an integer -+ * -+ * Returns the duty cycle ratio multiplied by the scale provided, otherwise -+ * returns -EERROR. -+ */ -+int clk_get_scaled_duty_cycle(struct clk *clk, unsigned int scale); -+ - /** - * clk_is_match - check if two clk's point to the same hardware clock - * @p: clk compared against q -@@ -183,6 +204,18 @@ static inline long clk_get_phase(struct clk *clk) - return -ENOTSUPP; - } - -+static inline int clk_set_duty_cycle(struct clk *clk, unsigned int num, -+ unsigned int den) -+{ -+ return -ENOTSUPP; -+} -+ -+static inline unsigned int clk_get_scaled_duty_cycle(struct clk *clk, -+ unsigned int scale) -+{ -+ return 0; -+} -+ - static inline bool clk_is_match(const struct clk *p, const struct clk *q) - { - return p == q; -diff --git a/include/trace/events/clk.h b/include/trace/events/clk.h -index 2cd449328aee3..9004ffff7f326 100644 ---- a/include/trace/events/clk.h -+++ b/include/trace/events/clk.h -@@ -192,6 +192,42 @@ DEFINE_EVENT(clk_phase, clk_set_phase_complete, - TP_ARGS(core, phase) - ); - -+DECLARE_EVENT_CLASS(clk_duty_cycle, -+ -+ TP_PROTO(struct clk_core *core, struct clk_duty *duty), -+ -+ TP_ARGS(core, duty), -+ -+ TP_STRUCT__entry( -+ __string( name, core->name ) -+ __field( unsigned int, num ) -+ __field( unsigned int, den ) -+ ), -+ -+ TP_fast_assign( -+ __assign_str(name, core->name); -+ __entry->num = duty->num; -+ __entry->den = duty->den; -+ ), -+ -+ TP_printk("%s %u/%u", __get_str(name), (unsigned int)__entry->num, -+ (unsigned int)__entry->den) -+); -+ -+DEFINE_EVENT(clk_duty_cycle, clk_set_duty_cycle, -+ -+ TP_PROTO(struct clk_core *core, struct clk_duty *duty), -+ -+ TP_ARGS(core, duty) -+); -+ -+DEFINE_EVENT(clk_duty_cycle, clk_set_duty_cycle_complete, -+ -+ TP_PROTO(struct clk_core *core, struct clk_duty *duty), -+ -+ TP_ARGS(core, duty) -+); -+ - #endif /* _TRACE_CLK_H */ - - /* This part must be outside protection */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/053_linux-4.18.y-jeromebrunet-0006-clk-meson-remove_obsolete_register_access.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/053_linux-4.18.y-jeromebrunet-0006-clk-meson-remove_obsolete_register_access.patch deleted file mode 100644 index 0472a46df..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/053_linux-4.18.y-jeromebrunet-0006-clk-meson-remove_obsolete_register_access.patch +++ /dev/null @@ -1,142 +0,0 @@ -From c46829185836ce19b9b14ee301d891e3f67fbe3d Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Wed, 10 Jan 2018 17:05:57 +0100 -Subject: [PATCH] clk: meson: remove obsolete register access - -The legacy method to access the hhi register space is not longer used. -We can safely drop it now. - -Signed-off-by: Jerome Brunet ---- - drivers/clk/meson/axg.c | 37 ++----------------------------------- - drivers/clk/meson/gxbb.c | 36 ++---------------------------------- - 2 files changed, 4 insertions(+), 69 deletions(-) - -diff --git a/drivers/clk/meson/axg.c b/drivers/clk/meson/axg.c -index bd4dbc696b88f..3fb884db1b10f 100644 ---- a/drivers/clk/meson/axg.c -+++ b/drivers/clk/meson/axg.c -@@ -12,7 +12,6 @@ - #include - #include - #include --#include - #include - #include - #include -@@ -995,49 +994,17 @@ static const struct of_device_id clkc_match_table[] = { - {} - }; - --static const struct regmap_config clkc_regmap_config = { -- .reg_bits = 32, -- .val_bits = 32, -- .reg_stride = 4, --}; -- - static int axg_clkc_probe(struct platform_device *pdev) - { - struct device *dev = &pdev->dev; -- struct resource *res; -- void __iomem *clk_base = NULL; - struct regmap *map; - int ret, i; - - /* Get the hhi system controller node if available */ - map = syscon_node_to_regmap(of_get_parent(dev->of_node)); - if (IS_ERR(map)) { -- dev_err(dev, -- "failed to get HHI regmap - Trying obsolete regs\n"); -- -- /* -- * FIXME: HHI registers should be accessed through -- * the appropriate system controller. This is required because -- * there is more than just clocks in this register space -- * -- * This fallback method is only provided temporarily until -- * all the platform DTs are properly using the syscon node -- */ -- res = platform_get_resource(pdev, IORESOURCE_MEM, 0); -- if (!res) -- return -EINVAL; -- -- -- clk_base = devm_ioremap(dev, res->start, resource_size(res)); -- if (!clk_base) { -- dev_err(dev, "Unable to map clk base\n"); -- return -ENXIO; -- } -- -- map = devm_regmap_init_mmio(dev, clk_base, -- &clkc_regmap_config); -- if (IS_ERR(map)) -- return PTR_ERR(map); -+ dev_err(dev, "failed to get HHI regmap\n"); -+ return PTR_ERR(map); - } - - /* Populate regmap for the regmap backed clocks */ -diff --git a/drivers/clk/meson/gxbb.c b/drivers/clk/meson/gxbb.c -index 177fffb9ebefe..297ebc3914750 100644 ---- a/drivers/clk/meson/gxbb.c -+++ b/drivers/clk/meson/gxbb.c -@@ -7,7 +7,6 @@ - #include - #include - #include --#include - #include - #include - #include -@@ -2228,17 +2227,9 @@ static const struct of_device_id clkc_match_table[] = { - {}, - }; - --static const struct regmap_config clkc_regmap_config = { -- .reg_bits = 32, -- .val_bits = 32, -- .reg_stride = 4, --}; -- - static int gxbb_clkc_probe(struct platform_device *pdev) - { - const struct clkc_data *clkc_data; -- struct resource *res; -- void __iomem *clk_base; - struct regmap *map; - int ret, i; - struct device *dev = &pdev->dev; -@@ -2250,31 +2241,8 @@ static int gxbb_clkc_probe(struct platform_device *pdev) - /* Get the hhi system controller node if available */ - map = syscon_node_to_regmap(of_get_parent(dev->of_node)); - if (IS_ERR(map)) { -- dev_err(dev, -- "failed to get HHI regmap - Trying obsolete regs\n"); -- -- /* -- * FIXME: HHI registers should be accessed through -- * the appropriate system controller. This is required because -- * there is more than just clocks in this register space -- * -- * This fallback method is only provided temporarily until -- * all the platform DTs are properly using the syscon node -- */ -- res = platform_get_resource(pdev, IORESOURCE_MEM, 0); -- if (!res) -- return -EINVAL; -- -- clk_base = devm_ioremap(dev, res->start, resource_size(res)); -- if (!clk_base) { -- dev_err(dev, "Unable to map clk base\n"); -- return -ENXIO; -- } -- -- map = devm_regmap_init_mmio(dev, clk_base, -- &clkc_regmap_config); -- if (IS_ERR(map)) -- return PTR_ERR(map); -+ dev_err(dev, "failed to get HHI regmap\n"); -+ return PTR_ERR(map); - } - - /* Populate regmap for the common regmap backed clocks */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/054_linux-4.18.y-jeromebrunet-0007-clk-meson-stop_rate_propagation_for_audio_clocks.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/054_linux-4.18.y-jeromebrunet-0007-clk-meson-stop_rate_propagation_for_audio_clocks.patch deleted file mode 100644 index 45c1f85e8..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/054_linux-4.18.y-jeromebrunet-0007-clk-meson-stop_rate_propagation_for_audio_clocks.patch +++ /dev/null @@ -1,51 +0,0 @@ -From baa2bf58a7e8c243b89fe2de4a20784ddcbd6403 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Tue, 19 Jun 2018 18:06:30 +0200 -Subject: [PATCH] clk: meson: stop rate propagation for audio clocks - -It is actually a lot easier and precise to setup the PLL with -carefully chosen rates than relying on CCF clock propagation for -this use case. - -For this, we stop the rate propagation at the mux picking the -PLL and let it round to the closest matching PLL - -Signed-off-by: Jerome Brunet ---- - drivers/clk/meson/gxbb.c | 4 ++-- - 1 file changed, 2 insertions(+), 2 deletions(-) - -diff --git a/drivers/clk/meson/gxbb.c b/drivers/clk/meson/gxbb.c -index 297ebc3914750..7d4a4e597385c 100644 ---- a/drivers/clk/meson/gxbb.c -+++ b/drivers/clk/meson/gxbb.c -@@ -970,13 +970,13 @@ static struct clk_regmap gxbb_cts_amclk_sel = { - .mask = 0x3, - .shift = 9, - .table = (u32[]){ 1, 2, 3 }, -+ .flags = CLK_MUX_ROUND_CLOSEST, - }, - .hw.init = &(struct clk_init_data){ - .name = "cts_amclk_sel", - .ops = &clk_regmap_mux_ops, - .parent_names = (const char *[]){ "mpll0", "mpll1", "mpll2" }, - .num_parents = 3, -- .flags = CLK_SET_RATE_PARENT, - }, - }; - -@@ -1018,13 +1018,13 @@ static struct clk_regmap gxbb_cts_mclk_i958_sel = { - .mask = 0x3, - .shift = 25, - .table = (u32[]){ 1, 2, 3 }, -+ .flags = CLK_MUX_ROUND_CLOSEST, - }, - .hw.init = &(struct clk_init_data) { - .name = "cts_mclk_i958_sel", - .ops = &clk_regmap_mux_ops, - .parent_names = (const char *[]){ "mpll0", "mpll1", "mpll2" }, - .num_parents = 3, -- .flags = CLK_SET_RATE_PARENT, - }, - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/055_linux-4.18.y-jeromebrunet-2008-asoc-codecs-force-enable-pcm5102a.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/055_linux-4.18.y-jeromebrunet-2008-asoc-codecs-force-enable-pcm5102a.patch deleted file mode 100644 index 8c47826ac..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/055_linux-4.18.y-jeromebrunet-2008-asoc-codecs-force-enable-pcm5102a.patch +++ /dev/null @@ -1,13 +0,0 @@ ---- a/sound/soc/codecs/Kconfig 2018-09-25 02:40:11.206734417 +0200 -+++ b/sound/soc/codecs/Kconfig 2018-09-25 03:32:51.395650591 +0200 -@@ -747,7 +747,9 @@ - select REGMAP_SPI - - config SND_SOC_PCM5102A -- tristate -+ tristate "PCM5102A Simple driver" -+ default m if SND_SOC_MESON=m -+ default y if SND_SOC_MESON=y - - config SND_SOC_PCM512x - tristate diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/056_linux-4.18.y-jeromebrunet-2009-arm64-dts-meson-gxbb-odroidc2-add-testing-i2s-entries.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/056_linux-4.18.y-jeromebrunet-2009-arm64-dts-meson-gxbb-odroidc2-add-testing-i2s-entries.patch deleted file mode 100644 index 72f6b624c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/056_linux-4.18.y-jeromebrunet-2009-arm64-dts-meson-gxbb-odroidc2-add-testing-i2s-entries.patch +++ /dev/null @@ -1,68 +0,0 @@ ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-09-25 02:40:03.744549370 +0200 -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-09-25 03:42:03.505596966 +0200 -@@ -147,10 +147,27 @@ - }; - }; - -+ i2s_codec: external-codec { -+ #sound-dai-cells = <0>; -+ compatible = "ti,pcm5102a"; -+ status = "okay"; -+ }; -+ - sound { - compatible = "simple-audio-card"; - simple-audio-card,name = "meson-gx-audio"; - -+ simple-audio-card,widgets = -+ "Line", "Analog Left Output", -+ "Line", "Analog Right Output"; -+ simple-audio-card,routing = -+ "Analog Left Output", "OUTL", -+ "Analog Right Output", "OUTR", -+ "INL", "AOUTL", -+ "INR", "AOUTR"; -+ -+ status = "okay"; -+ - assigned-clocks = <&clkc CLKID_MPLL2>, - <&clkc CLKID_MPLL0>, - <&clkc CLKID_MPLL1>; -@@ -178,6 +195,27 @@ - sound-dai = <&hdmi_tx>; - }; - }; -+ -+ simple-audio-card,dai-link@1 { -+ /* I2C external codec Output */ -+ format = "i2s"; -+ bitclock-inversion; -+ 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 = <&i2s_codec>; -+ }; -+ }; - }; - }; - -@@ -264,6 +302,9 @@ - - &i2s_dai { - status = "okay"; -+ pinctrl-0 = <&i2s_am_clk_pins>, <&i2s_out_ao_clk_pins>, -+ <&i2s_out_lr_clk_pins>, <&i2s_out_ch01_ao_pins>; -+ pinctrl-names = "default"; - }; - - &ir { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/058_linux-4.16-le-amlogic-gx-1001-usb-enable-otg-as-host.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/058_linux-4.16-le-amlogic-gx-1001-usb-enable-otg-as-host.patch deleted file mode 100644 index 8f9c1cd27..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/058_linux-4.16-le-amlogic-gx-1001-usb-enable-otg-as-host.patch +++ /dev/null @@ -1,51 +0,0 @@ - ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-04-28 19:24:56.090524456 +0200 -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-04-29 23:09:48.559371108 +0200 -@@ -409,6 +409,7 @@ - &usb0_phy { - status = "okay"; - phy-supply = <&usb_otg_pwr>; -+ dr_mode = "otg"; - }; - - &usb1_phy { -@@ -418,6 +419,7 @@ - - &usb0 { - status = "okay"; -+ dr_mode = "host"; - }; - - &usb1 { - ---- a/drivers/phy/amlogic/phy-meson8b-usb2.c 2018-04-28 19:22:57.420144229 +0200 -+++ b/drivers/phy/amlogic/phy-meson8b-usb2.c 2018-04-29 23:13:57.136515043 +0200 -@@ -113,6 +113,7 @@ - struct phy_meson8b_usb2_priv { - void __iomem *regs; - enum usb_dr_mode dr_mode; -+ enum usb_dr_mode phy_mode; - struct clk *clk_usb_general; - struct clk *clk_usb; - struct reset_control *reset; -@@ -181,7 +182,7 @@ - phy_meson8b_usb2_mask_bits(priv, REG_CTRL, REG_CTRL_SOF_TOGGLE_OUT, - REG_CTRL_SOF_TOGGLE_OUT); - -- if (priv->dr_mode == USB_DR_MODE_HOST) { -+ if (priv->phy_mode == USB_DR_MODE_HOST) { - phy_meson8b_usb2_mask_bits(priv, REG_ADP_BC, - REG_ADP_BC_ACA_ENABLE, - REG_ADP_BC_ACA_ENABLE); -@@ -251,6 +252,11 @@ - return -EINVAL; - } - -+ priv->phy_mode = usb_get_dr_mode(&pdev->dev); -+ if (priv->phy_mode == USB_DR_MODE_UNKNOWN) { -+ priv->phy_mode = priv->dr_mode; -+ } -+ - phy = devm_phy_create(&pdev->dev, NULL, &phy_meson8b_usb2_ops); - if (IS_ERR(phy)) { - dev_err(&pdev->dev, "failed to create PHY\n"); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/064_linux-4.14.y-le-amlogic-gx-scpi-1004-mailbox-revert_switch_to_hrtimer_for_tx_complete_polling.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/064_linux-4.14.y-le-amlogic-gx-scpi-1004-mailbox-revert_switch_to_hrtimer_for_tx_complete_polling.patch deleted file mode 100644 index 2dd8b1c9c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/064_linux-4.14.y-le-amlogic-gx-scpi-1004-mailbox-revert_switch_to_hrtimer_for_tx_complete_polling.patch +++ /dev/null @@ -1,103 +0,0 @@ -diff --git a/drivers/mailbox/mailbox.c b/drivers/mailbox/mailbox.c -index 674b35f40..3497cabda 100644 ---- a/drivers/mailbox/mailbox.c -+++ b/drivers/mailbox/mailbox.c -@@ -26,6 +26,8 @@ - static LIST_HEAD(mbox_cons); - static DEFINE_MUTEX(con_mutex); - -+static void poll_txdone(struct timer_list *t); -+ - static int add_to_rbuf(struct mbox_chan *chan, void *mssg) - { - int idx; -@@ -86,8 +88,7 @@ static void msg_submit(struct mbox_chan *chan) - spin_unlock_irqrestore(&chan->lock, flags); - - if (!err && (chan->txdone_method & TXDONE_BY_POLL)) -- /* kick start the timer immediately to avoid delays */ -- hrtimer_start(&chan->mbox->poll_hrt, 0, HRTIMER_MODE_REL); -+ poll_txdone(&chan->mbox->poll); - } - - static void tx_tick(struct mbox_chan *chan, int r) -@@ -114,10 +115,9 @@ static void tx_tick(struct mbox_chan *chan, int r) - complete(&chan->tx_complete); - } - --static enum hrtimer_restart txdone_hrtimer(struct hrtimer *hrtimer) -+static void poll_txdone(struct timer_list *t) - { -- struct mbox_controller *mbox = -- container_of(hrtimer, struct mbox_controller, poll_hrt); -+ struct mbox_controller *mbox = from_timer(mbox, t, poll); - bool txdone, resched = false; - int i; - -@@ -133,11 +133,9 @@ static enum hrtimer_restart txdone_hrtimer(struct hrtimer *hrtimer) - } - } - -- if (resched) { -- hrtimer_forward_now(hrtimer, ms_to_ktime(mbox->txpoll_period)); -- return HRTIMER_RESTART; -- } -- return HRTIMER_NORESTART; -+ if (resched) -+ mod_timer(&mbox->poll, jiffies + -+ msecs_to_jiffies(mbox->txpoll_period)); - } - - /** -@@ -466,9 +464,7 @@ int mbox_controller_register(struct mbox_controller *mbox) - return -EINVAL; - } - -- hrtimer_init(&mbox->poll_hrt, CLOCK_MONOTONIC, -- HRTIMER_MODE_REL); -- mbox->poll_hrt.function = txdone_hrtimer; -+ timer_setup(&mbox->poll, &poll_txdone, 0); - } - - for (i = 0; i < mbox->num_chans; i++) { -@@ -510,7 +506,7 @@ void mbox_controller_unregister(struct mbox_controller *mbox) - mbox_free_channel(&mbox->chans[i]); - - if (mbox->txdone_poll) -- hrtimer_cancel(&mbox->poll_hrt); -+ del_timer_sync(&mbox->poll); - - mutex_unlock(&con_mutex); - } -diff --git a/include/linux/mailbox_controller.h b/include/linux/mailbox_controller.h -index 74deadb42..68c424544 100644 ---- a/include/linux/mailbox_controller.h -+++ b/include/linux/mailbox_controller.h -@@ -9,7 +9,7 @@ - - #include - #include --#include -+#include - #include - #include - -@@ -67,8 +67,7 @@ struct mbox_chan_ops { - * @txpoll_period: If 'txdone_poll' is in effect, the API polls for - * last TX's status after these many millisecs - * @of_xlate: Controller driver specific mapping of channel via DT -- * @poll_hrt: API private. hrtimer used to poll for TXDONE on all -- * channels. -+ * @poll: API private. Used to poll for TXDONE on all channels. - * @node: API private. To hook into list of controllers. - */ - struct mbox_controller { -@@ -82,7 +81,7 @@ struct mbox_controller { - struct mbox_chan *(*of_xlate)(struct mbox_controller *mbox, - const struct of_phandle_args *sp); - /* Internal to API */ -- struct hrtimer poll_hrt; -+ struct timer_list poll; - struct list_head node; - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/068_linux-4.17-amlogic-dmt-extended-0001-make_dmt_timings_parameter_generic_and_add_more_frequencies.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/068_linux-4.17-amlogic-dmt-extended-0001-make_dmt_timings_parameter_generic_and_add_more_frequencies.patch deleted file mode 100644 index c0859bcf3..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/068_linux-4.17-amlogic-dmt-extended-0001-make_dmt_timings_parameter_generic_and_add_more_frequencies.patch +++ /dev/null @@ -1,714 +0,0 @@ -From 2d49cff77c34c63ae5aa32537cc5fef1ea2e165d Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Fri, 27 Apr 2018 17:19:46 +0200 -Subject: [PATCH] drm/meson: Make DMT timings parameter generic and add more - frequencies - -Add more frequencies to support more timings with the generic timings -parameters calculation. - -Signed-off-by: Neil Armstrong ---- - drivers/gpu/drm/meson/meson_dw_hdmi.c | 10 +- - drivers/gpu/drm/meson/meson_vclk.c | 184 ++++++++++++++++++- - drivers/gpu/drm/meson/meson_venc.c | 330 +++++----------------------------- - drivers/gpu/drm/meson/meson_venc.h | 3 +- - 4 files changed, 231 insertions(+), 296 deletions(-) - -diff --git a/drivers/gpu/drm/meson/meson_dw_hdmi.c b/drivers/gpu/drm/meson/meson_dw_hdmi.c -index a393095aac1a6..7ebfef86383fe 100644 ---- a/drivers/gpu/drm/meson/meson_dw_hdmi.c -+++ b/drivers/gpu/drm/meson/meson_dw_hdmi.c -@@ -546,6 +546,7 @@ dw_hdmi_mode_valid(struct drm_connector *connector, - unsigned int venc_freq; - unsigned int hdmi_freq; - int vic = drm_match_cea_mode(mode); -+ enum drm_mode_status status; - - DRM_DEBUG_DRIVER("Modeline %d:\"%s\" %d %d %d %d %d %d %d %d %d %d 0x%x 0x%x\n", - mode->base.id, mode->name, mode->vrefresh, mode->clock, -@@ -556,8 +557,9 @@ dw_hdmi_mode_valid(struct drm_connector *connector, - - /* Check against non-VIC supported modes */ - if (!vic) { -- if (!meson_venc_hdmi_supported_mode(mode)) -- return MODE_BAD; -+ status = meson_venc_hdmi_supported_mode(mode); -+ if (status != MODE_OK) -+ return status; - /* Check against supported VIC modes */ - } else if (!meson_venc_hdmi_supported_vic(vic)) - return MODE_BAD; -@@ -587,6 +589,10 @@ dw_hdmi_mode_valid(struct drm_connector *connector, - switch (vclk_freq) { - case 25175: - case 40000: -+ case 32000: -+ case 36000: -+ case 33750: -+ case 33900: - case 54000: - case 65000: - case 74250: -diff --git a/drivers/gpu/drm/meson/meson_vclk.c b/drivers/gpu/drm/meson/meson_vclk.c -index f0511220317f9..86975f245c361 100644 ---- a/drivers/gpu/drm/meson/meson_vclk.c -+++ b/drivers/gpu/drm/meson/meson_vclk.c -@@ -330,22 +330,30 @@ static void meson_venci_cvbs_clock_config(struct meson_drm *priv) - #define MESON_VCLK_HDMI_DDR_148500 3 - /* 4028 /4 /4 /1 /5 /2 => /1 /1 */ - #define MESON_VCLK_HDMI_25175 4 -+/* 2560 /4 /2 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_32000 5 -+/* 2700 /4 /2 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_33750 6 -+/* 2712 /4 /2 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_33900 7 -+/* 2880 /4 /2 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_36000 8 - /* 3200 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_40000 5 -+#define MESON_VCLK_HDMI_40000 9 - /* 5200 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_65000 6 -+#define MESON_VCLK_HDMI_65000 10 - /* 2970 /2 /2 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_74250 7 -+#define MESON_VCLK_HDMI_74250 11 - /* 4320 /4 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_108000 8 -+#define MESON_VCLK_HDMI_108000 12 - /* 2970 /1 /2 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_148500 9 -+#define MESON_VCLK_HDMI_148500 13 - /* 3240 /2 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_162000 10 -+#define MESON_VCLK_HDMI_162000 14 - /* 2970 /1 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_297000 11 -+#define MESON_VCLK_HDMI_297000 15 - /* 5940 /1 /1 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_594000 12 -+#define MESON_VCLK_HDMI_594000 16 - - struct meson_vclk_params { - unsigned int pll_base_freq; -@@ -419,6 +427,38 @@ struct meson_vclk_params { - .vid_pll_div = VID_PLL_DIV_5, - .vclk_div = 2, - }, -+ [MESON_VCLK_HDMI_32000] = { -+ .pll_base_freq = 2560000, -+ .pll_od1 = 4, -+ .pll_od2 = 2, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, -+ [MESON_VCLK_HDMI_33750] = { -+ .pll_base_freq = 2700000, -+ .pll_od1 = 4, -+ .pll_od2 = 2, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, -+ [MESON_VCLK_HDMI_33900] = { -+ .pll_base_freq = 2712000, -+ .pll_od1 = 4, -+ .pll_od2 = 2, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, -+ [MESON_VCLK_HDMI_36000] = { -+ .pll_base_freq = 2880000, -+ .pll_od1 = 4, -+ .pll_od2 = 2, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, - [MESON_VCLK_HDMI_40000] = { - .pll_base_freq = 3200000, - .pll_od1 = 4, -@@ -480,6 +520,86 @@ void meson_hdmi_pll_set(struct meson_drm *priv, - - if (meson_vpu_is_compatible(priv, "amlogic,meson-gxbb-vpu")) { - switch (base) { -+ case 2560000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000235); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* Enable and unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ 0x7 << 28, 0x4 << 28); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4555); -+ break; -+ -+ case 2700000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000238); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* Enable and unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ 0x7 << 28, 0x4 << 28); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4400); -+ break; -+ -+ case 2712000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000238); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* Enable and unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ 0x7 << 28, 0x4 << 28); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4800); -+ break; -+ -+ case 2880000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x5800023c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* Enable and unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ 0x7 << 28, 0x4 << 28); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ break; -+ - case 2970000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x5800023d); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -@@ -640,6 +760,42 @@ void meson_hdmi_pll_set(struct meson_drm *priv, - } else if (meson_vpu_is_compatible(priv, "amlogic,meson-gxm-vpu") || - meson_vpu_is_compatible(priv, "amlogic,meson-gxl-vpu")) { - switch (base) { -+ case 2560000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x4000026a); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb2ab); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ -+ case 2700000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000270); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb200); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ -+ case 2712000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000271); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ -+ case 2880000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000278); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ - case 2970000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x4000027b); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb300); -@@ -789,6 +945,18 @@ void meson_vclk_setup(struct meson_drm *priv, unsigned int target, - case 25175: - freq = MESON_VCLK_HDMI_25175; - break; -+ case 32000: -+ freq = MESON_VCLK_HDMI_32000; -+ break; -+ case 33750: -+ freq = MESON_VCLK_HDMI_33750; -+ break; -+ case 33900: -+ freq = MESON_VCLK_HDMI_33900; -+ break; -+ case 36000: -+ freq = MESON_VCLK_HDMI_36000; -+ break; - case 40000: - freq = MESON_VCLK_HDMI_40000; - break; -diff --git a/drivers/gpu/drm/meson/meson_venc.c b/drivers/gpu/drm/meson/meson_venc.c -index 6e27013898013..ea178151399c5 100644 ---- a/drivers/gpu/drm/meson/meson_venc.c -+++ b/drivers/gpu/drm/meson/meson_venc.c -@@ -697,258 +697,6 @@ union meson_hdmi_venc_mode meson_hdmi_encp_mode_1080p60 = { - }, - }; - --union meson_hdmi_venc_mode meson_hdmi_encp_mode_640x480_60 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 0x31f, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 0x90, -- .havon_end = 0x30f, -- .vavon_bline = 0x23, -- .vavon_eline = 0x202, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 0x60, -- .vso_begin = 0x1e, -- .vso_end = 0x32, -- .vso_bline = 0, -- .vso_eline = 2, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 0x20c, -- }, --}; -- --union meson_hdmi_venc_mode meson_hdmi_encp_mode_800x600_60 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 0x41f, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 0xD8, -- .havon_end = 0x3f7, -- .vavon_bline = 0x1b, -- .vavon_eline = 0x272, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 0x80, -- .vso_begin = 0x1e, -- .vso_end = 0x32, -- .vso_bline = 0, -- .vso_eline = 4, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 0x273, -- }, --}; -- --union meson_hdmi_venc_mode meson_hdmi_encp_mode_1024x768_60 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 1343, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 296, -- .havon_end = 1319, -- .vavon_bline = 35, -- .vavon_eline = 802, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 136, -- .vso_begin = 30, -- .vso_end = 50, -- .vso_bline = 0, -- .vso_eline = 6, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 805, -- }, --}; -- --union meson_hdmi_venc_mode meson_hdmi_encp_mode_1152x864_75 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 0x63f, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 0x180, -- .havon_end = 0x5ff, -- .vavon_bline = 0x23, -- .vavon_eline = 0x382, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 0x80, -- .vso_begin = 0x1e, -- .vso_end = 0x32, -- .vso_bline = 0, -- .vso_eline = 3, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 0x383, -- }, --}; -- --union meson_hdmi_venc_mode meson_hdmi_encp_mode_1280x1024_60 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 0x697, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 0x168, -- .havon_end = 0x667, -- .vavon_bline = 0x29, -- .vavon_eline = 0x428, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 0x70, -- .vso_begin = 0x1e, -- .vso_end = 0x32, -- .vso_bline = 0, -- .vso_eline = 3, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 0x429, -- }, --}; -- --union meson_hdmi_venc_mode meson_hdmi_encp_mode_1600x1200_60 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 0x86f, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 0x1f0, -- .havon_end = 0x82f, -- .vavon_bline = 0x31, -- .vavon_eline = 0x4e0, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 0xc0, -- .vso_begin = 0x1e, -- .vso_end = 0x32, -- .vso_bline = 0, -- .vso_eline = 3, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 0x4e1, -- }, --}; -- - struct meson_hdmi_venc_dmt_mode { - struct drm_display_mode drm_mode; - union meson_hdmi_venc_mode *mode; -@@ -958,49 +706,42 @@ struct meson_hdmi_venc_dmt_mode { - { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 25175, 640, 656, - 752, 800, 0, 480, 490, 492, 525, 0, - DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, -- &meson_hdmi_encp_mode_640x480_60, - }, - /* 800x600@60Hz */ - { - { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 40000, 800, 840, - 968, 1056, 0, 600, 601, 605, 628, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -- &meson_hdmi_encp_mode_800x600_60, - }, - /* 1024x768@60Hz */ - { - { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 65000, 1024, - 1048, 1184, 1344, 0, 768, 771, 777, 806, 0, - DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, -- &meson_hdmi_encp_mode_1024x768_60, - }, - /* 1152x864@75Hz */ - { - { DRM_MODE("1152x864", DRM_MODE_TYPE_DRIVER, 108000, 1152, - 1216, 1344, 1600, 0, 864, 865, 868, 900, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -- &meson_hdmi_encp_mode_1152x864_75, - }, - /* 1280x1024@60Hz */ - { - { DRM_MODE("1280x1024", DRM_MODE_TYPE_DRIVER, 108000, 1280, - 1328, 1440, 1688, 0, 1024, 1025, 1028, 1066, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -- &meson_hdmi_encp_mode_1280x1024_60, - }, - /* 1600x1200@60Hz */ - { - { DRM_MODE("1600x1200", DRM_MODE_TYPE_DRIVER, 162000, 1600, - 1664, 1856, 2160, 0, 1200, 1201, 1204, 1250, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -- &meson_hdmi_encp_mode_1600x1200_60, - }, - /* 1920x1080@60Hz */ - { - { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 148500, 1920, - 2008, 2052, 2200, 0, 1080, 1084, 1089, 1125, 0, - DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, -- &meson_hdmi_encp_mode_1080p60 - }, - { }, /* sentinel */ - }; -@@ -1044,17 +785,20 @@ static unsigned long modulo(unsigned long a, unsigned long b) - return a; - } - --bool meson_venc_hdmi_supported_mode(const struct drm_display_mode *mode) -+enum drm_mode_status -+meson_venc_hdmi_supported_mode(const struct drm_display_mode *mode) - { -- struct meson_hdmi_venc_dmt_mode *vmode = meson_hdmi_venc_dmt_modes; -+ if (mode->flags & ~(DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NHSYNC | -+ DRM_MODE_FLAG_PVSYNC | DRM_MODE_FLAG_NVSYNC)) -+ return MODE_BAD; - -- while (vmode->mode) { -- if (drm_mode_equal(&vmode->drm_mode, mode)) -- return true; -- vmode++; -- } -+ if (mode->hdisplay < 640 || mode->hdisplay > 1920) -+ return MODE_BAD_HVALUE; - -- return false; -+ if (mode->vdisplay < 480 || mode->vdisplay > 1200) -+ return MODE_BAD_VVALUE; -+ -+ return MODE_OK; - } - EXPORT_SYMBOL_GPL(meson_venc_hdmi_supported_mode); - -@@ -1072,18 +816,29 @@ bool meson_venc_hdmi_supported_vic(int vic) - } - EXPORT_SYMBOL_GPL(meson_venc_hdmi_supported_vic); - --static union meson_hdmi_venc_mode --*meson_venc_hdmi_get_dmt_vmode(const struct drm_display_mode *mode) -+void meson_venc_hdmi_get_dmt_vmode(const struct drm_display_mode *mode, -+ union meson_hdmi_venc_mode *dmt_mode) - { -- struct meson_hdmi_venc_dmt_mode *vmode = meson_hdmi_venc_dmt_modes; -- -- while (vmode->mode) { -- if (drm_mode_equal(&vmode->drm_mode, mode)) -- return vmode->mode; -- vmode++; -- } -- -- return NULL; -+ memset(dmt_mode, 0, sizeof(*dmt_mode)); -+ -+ dmt_mode->encp.dvi_settings = 0x21; -+ dmt_mode->encp.video_mode = 0x4040; -+ dmt_mode->encp.video_mode_adv = 0x18; -+ dmt_mode->encp.max_pxcnt = mode->htotal - 1; -+ dmt_mode->encp.havon_begin = mode->htotal - mode->hsync_start; -+ dmt_mode->encp.havon_end = dmt_mode->encp.havon_begin + -+ mode->hdisplay - 1; -+ dmt_mode->encp.vavon_bline = mode->vtotal - mode->vsync_start; -+ dmt_mode->encp.vavon_eline = dmt_mode->encp.vavon_bline + -+ mode->vdisplay - 1; -+ dmt_mode->encp.hso_begin = 0; -+ dmt_mode->encp.hso_end = mode->hsync_end - mode->hsync_start; -+ dmt_mode->encp.vso_begin = 30; -+ dmt_mode->encp.vso_end = 50; -+ dmt_mode->encp.vso_bline = 0; -+ dmt_mode->encp.vso_eline = mode->vsync_end - mode->vsync_start; -+ dmt_mode->encp.vso_eline_present = true; -+ dmt_mode->encp.max_lncnt = mode->vtotal - 1; - } - - static union meson_hdmi_venc_mode *meson_venc_hdmi_get_vic_vmode(int vic) -@@ -1120,6 +875,7 @@ void meson_venc_hdmi_mode_set(struct meson_drm *priv, int vic, - struct drm_display_mode *mode) - { - union meson_hdmi_venc_mode *vmode = NULL; -+ union meson_hdmi_venc_mode vmode_dmt; - bool use_enci = false; - bool venc_repeat = false; - bool hdmi_repeat = false; -@@ -1147,14 +903,18 @@ void meson_venc_hdmi_mode_set(struct meson_drm *priv, int vic, - unsigned int sof_lines; - unsigned int vsync_lines; - -- if (meson_venc_hdmi_supported_vic(vic)) -+ if (meson_venc_hdmi_supported_vic(vic)) { - vmode = meson_venc_hdmi_get_vic_vmode(vic); -- else -- vmode = meson_venc_hdmi_get_dmt_vmode(mode); -- if (!vmode) { -- dev_err(priv->dev, "%s: Fatal Error, unsupported mode " -- DRM_MODE_FMT "\n", __func__, DRM_MODE_ARG(mode)); -- return; -+ if (!vmode) { -+ dev_err(priv->dev, "%s: Fatal Error, unsupported mode " -+ DRM_MODE_FMT "\n", __func__, -+ DRM_MODE_ARG(mode)); -+ return; -+ } -+ } -+ else { -+ meson_venc_hdmi_get_dmt_vmode(mode, &vmode_dmt); -+ vmode = &vmode_dmt; - } - - /* Use VENCI for 480i and 576i and double HDMI pixels */ -diff --git a/drivers/gpu/drm/meson/meson_venc.h b/drivers/gpu/drm/meson/meson_venc.h -index 7c18a36a0dd0c..97eaebbfa0c4a 100644 ---- a/drivers/gpu/drm/meson/meson_venc.h -+++ b/drivers/gpu/drm/meson/meson_venc.h -@@ -58,7 +58,8 @@ struct meson_cvbs_enci_mode { - }; - - /* HDMI Clock parameters */ --bool meson_venc_hdmi_supported_mode(const struct drm_display_mode *mode); -+enum drm_mode_status -+meson_venc_hdmi_supported_mode(const struct drm_display_mode *mode); - bool meson_venc_hdmi_supported_vic(int vic); - bool meson_venc_hdmi_venc_repeat(int vic); - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/069_linux-4.17-amlogic-dmt-extended-1001-fix-32000khz.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/069_linux-4.17-amlogic-dmt-extended-1001-fix-32000khz.patch deleted file mode 100644 index a359376a7..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/069_linux-4.17-amlogic-dmt-extended-1001-fix-32000khz.patch +++ /dev/null @@ -1,119 +0,0 @@ -diff -ur a/drivers/gpu/drm/meson/meson_vclk.c b/drivers/gpu/drm/meson/meson_vclk.c ---- a/drivers/gpu/drm/meson/meson_vclk.c 2018-06-02 20:21:48.000000000 +0200 -+++ b/drivers/gpu/drm/meson/meson_vclk.c 2018-06-02 20:16:44.008061996 +0200 -@@ -428,9 +428,9 @@ - .vclk_div = 2, - }, - [MESON_VCLK_HDMI_32000] = { -- .pll_base_freq = 2560000, -+ .pll_base_freq = 5120000, - .pll_od1 = 4, -- .pll_od2 = 2, -+ .pll_od2 = 4, - .pll_od3 = 1, - .vid_pll_div = VID_PLL_DIV_5, - .vclk_div = 2, -@@ -520,27 +520,6 @@ - - if (meson_vpu_is_compatible(priv, "amlogic,meson-gxbb-vpu")) { - switch (base) { -- case 2560000: -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000235); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -- -- /* Enable and unreset */ -- regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -- 0x7 << 28, 0x4 << 28); -- -- /* Poll for lock bit */ -- regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -- val, (val & HDMI_PLL_LOCK), 10, 0); -- -- /* div_frac */ -- regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -- 0xFFFF, 0x4555); -- break; -- - case 2700000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000238); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -@@ -722,6 +701,27 @@ - val, (val & HDMI_PLL_LOCK), 10, 0); - break; - -+ case 5120000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x5800026a); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x135c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ BIT(28), 0); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4aab); -+ break; -+ - case 5940000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x5800027b); - regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -@@ -760,15 +760,6 @@ - } else if (meson_vpu_is_compatible(priv, "amlogic,meson-gxm-vpu") || - meson_vpu_is_compatible(priv, "amlogic,meson-gxl-vpu")) { - switch (base) { -- case 2560000: -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x4000026a); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb2ab); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -- break; -- - case 2700000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000270); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb200); -@@ -847,6 +838,15 @@ - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ -+ case 5120000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x400002d5); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb155); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); - break; - -diff -ur a/drivers/gpu/drm/meson/meson_venc.c b/drivers/gpu/drm/meson/meson_venc.c ---- a/drivers/gpu/drm/meson/meson_venc.c 2018-06-02 16:39:27.777402009 +0200 -+++ b/drivers/gpu/drm/meson/meson_venc.c 2018-06-02 20:23:23.744646670 +0200 -@@ -713,6 +713,12 @@ - 968, 1056, 0, 600, 601, 605, 628, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, - }, -+ /* 1024x600@43Hz */ -+ { -+ { DRM_MODE("1024x600", DRM_MODE_TYPE_DRIVER, 32000, 1024, -+ 1064, 1112, 1152, 0, 600, 613, 616, 645, 0, -+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, -+ }, - /* 1024x768@60Hz */ - { - { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 65000, 1024, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/070_linux-4.17-amlogic-dmt-extended-1002-custom-mode.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/070_linux-4.17-amlogic-dmt-extended-1002-custom-mode.patch deleted file mode 100644 index 97136bd0c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/070_linux-4.17-amlogic-dmt-extended-1002-custom-mode.patch +++ /dev/null @@ -1,547 +0,0 @@ -diff -ur a/drivers/gpu/drm/meson/meson_dw_hdmi.c b/drivers/gpu/drm/meson/meson_dw_hdmi.c ---- a/drivers/gpu/drm/meson/meson_dw_hdmi.c 2018-06-02 16:39:27.777402009 +0200 -+++ b/drivers/gpu/drm/meson/meson_dw_hdmi.c 2018-06-02 17:25:33.803332054 +0200 -@@ -588,22 +588,28 @@ - /* Finally filter by configurable vclk frequencies */ - switch (vclk_freq) { - case 25175: -- case 40000: -+ case 29750: - case 32000: - case 36000: - case 33750: - case 33900: -+ case 40000: - case 54000: - case 65000: - case 74250: -+ case 106500: - case 108000: - case 148500: - case 162000: -+ case 193250: - case 297000: - case 594000: - return MODE_OK; - } - -+ if (meson_vclk_supported(vclk_freq)) -+ return MODE_OK; -+ - return MODE_CLOCK_RANGE; - } - -diff -ur a/drivers/gpu/drm/meson/meson_vclk.c b/drivers/gpu/drm/meson/meson_vclk.c ---- a/drivers/gpu/drm/meson/meson_vclk.c 2018-06-02 20:16:44.008061996 +0200 -+++ b/drivers/gpu/drm/meson/meson_vclk.c 2018-06-04 03:26:22.092619417 +0200 -@@ -321,39 +321,49 @@ - } - - --/* PLL O1 O2 O3 VP DV EN TX */ --/* 4320 /4 /4 /1 /5 /1 => /2 /2 */ --#define MESON_VCLK_HDMI_ENCI_54000 1 --/* 4320 /4 /4 /1 /5 /1 => /1 /2 */ --#define MESON_VCLK_HDMI_DDR_54000 2 --/* 2970 /4 /1 /1 /5 /1 => /1 /2 */ --#define MESON_VCLK_HDMI_DDR_148500 3 --/* 4028 /4 /4 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_25175 4 --/* 2560 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_32000 5 --/* 2700 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_33750 6 --/* 2712 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_33900 7 --/* 2880 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_36000 8 --/* 3200 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_40000 9 --/* 5200 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_65000 10 --/* 2970 /2 /2 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_74250 11 --/* 4320 /4 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_108000 12 --/* 2970 /1 /2 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_148500 13 --/* 3240 /2 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_162000 14 --/* 2970 /1 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_297000 15 --/* 5940 /1 /1 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_594000 16 -+enum { -+ /* PLL O1 O2 O3 VP DV EN TX */ -+ /* 4320 /4 /4 /1 /5 /1 => /2 /2 */ -+ MESON_VCLK_HDMI_ENCI_54000 = 1, -+ /* 4320 /4 /4 /1 /5 /1 => /1 /2 */ -+ MESON_VCLK_HDMI_DDR_54000, -+ /* 2970 /4 /1 /1 /5 /1 => /1 /2 */ -+ MESON_VCLK_HDMI_DDR_148500, -+ /* 4028 /4 /4 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_25175, -+ /* 4760 /4 /4 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_29750, -+ /* 2560 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_32000, -+ /* 2700 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_33750, -+ /* 2712 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_33900, -+ /* 2880 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_36000, -+ /* 3200 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_40000, -+ /* 5200 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_65000, -+ /* 2970 /2 /2 /2 /5 /1 => /1 /1 */ -+ MESON_VCLK_HDMI_74250, -+ /* 4260 /4 /1 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_106500, -+ /* 4320 /4 /1 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_108000, -+ /* 2970 /1 /2 /2 /5 /1 => /1 /1 */ -+ MESON_VCLK_HDMI_148500, -+ /* 3240 /2 /1 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_162000, -+ /* 3865 /2 /1 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_193250, -+ /* 2970 /1 /1 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_297000, -+ /* 5940 /1 /1 /2 /5 /1 => /1 /1 */ -+ MESON_VCLK_HDMI_594000, -+ /* custom calculated mode */ -+ MESON_VCLK_HDMI_CUSTOM, -+}; - - struct meson_vclk_params { - unsigned int pll_base_freq; -@@ -427,6 +437,14 @@ - .vid_pll_div = VID_PLL_DIV_5, - .vclk_div = 2, - }, -+ [MESON_VCLK_HDMI_29750] = { -+ .pll_base_freq = 4760000, -+ .pll_od1 = 4, -+ .pll_od2 = 4, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, - [MESON_VCLK_HDMI_32000] = { - .pll_base_freq = 5120000, - .pll_od1 = 4, -@@ -475,6 +493,14 @@ - .vid_pll_div = VID_PLL_DIV_5, - .vclk_div = 2, - }, -+ [MESON_VCLK_HDMI_106500] = { -+ .pll_base_freq = 4260000, -+ .pll_od1 = 4, -+ .pll_od2 = 1, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, - [MESON_VCLK_HDMI_108000] = { - .pll_base_freq = 4320000, - .pll_od1 = 4, -@@ -491,6 +517,14 @@ - .vid_pll_div = VID_PLL_DIV_5, - .vclk_div = 2, - }, -+ [MESON_VCLK_HDMI_193250] = { -+ .pll_base_freq = 3865000, -+ .pll_od1 = 2, -+ .pll_od2 = 1, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, - }; - - static inline unsigned int pll_od_to_reg(unsigned int od) -@@ -519,6 +553,18 @@ - unsigned int val; - - if (meson_vpu_is_compatible(priv, "amlogic,meson-gxbb-vpu")) { -+ unsigned int step = 48000; -+ unsigned int range = 0x1000; -+ unsigned int round = step / range / 2; -+ unsigned int frac = base % step; -+ unsigned int m = (base - frac) / step; -+ -+ frac = (frac + round) * range / step; -+ if (frac >= range) -+ frac = range-1; -+ -+ dev_info(priv->dev, "%s: base=%d, m=0x%.2x, frac=0x%.3x\n", __func__, base, m, frac); -+ - switch (base) { - case 2700000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000238); -@@ -755,10 +801,49 @@ - /* Poll for lock bit */ - regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, - val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4555); -+ break; -+ -+ default: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000200 | m); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x135c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ BIT(28), 0); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ if (frac) -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4000 | frac); - break; -+ - }; - } else if (meson_vpu_is_compatible(priv, "amlogic,meson-gxm-vpu") || - meson_vpu_is_compatible(priv, "amlogic,meson-gxl-vpu")) { -+ unsigned int step = 24000; -+ unsigned int range = 0x400; -+ unsigned int round = step / range / 2; -+ unsigned int frac = base % step; -+ unsigned int m = (base - frac) / step; -+ -+ frac = (frac + round) * range / step; -+ if (frac >= range) -+ frac = range-1; -+ -+ pr_info("%s: base=%d, m=0x%.2x, frac=0x%.3x", __func__, base, m, frac); -+ - switch (base) { - case 2700000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000270); -@@ -868,6 +953,14 @@ - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); - break; - -+ default: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000200 | m); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb000 | frac); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; - }; - - /* Reset PLL */ -@@ -906,6 +999,151 @@ - 3 << 19, pll_od_to_reg(od3) << 19); - } - -+unsigned int meson_vclk_freq_from_params(struct meson_vclk_params* vclk_params) -+{ -+ unsigned int vclk_freq = vclk_params->pll_base_freq / -+ vclk_params->pll_od1 / vclk_params->pll_od2 / -+ vclk_params->pll_od3 / vclk_params->vclk_div; -+ -+ switch (vclk_params->vid_pll_div) { -+ case VID_PLL_DIV_2: -+ vclk_freq /= 2; -+ break; -+ case VID_PLL_DIV_2p5: -+ vclk_freq *= 4; -+ vclk_freq /= 10; -+ break; -+ case VID_PLL_DIV_3: -+ vclk_freq /= 3; -+ break; -+ case VID_PLL_DIV_3p5: -+ vclk_freq *= 2; -+ vclk_freq /= 7; -+ break; -+ case VID_PLL_DIV_3p75: -+ vclk_freq *= 4; -+ vclk_freq /= 15; -+ break; -+ case VID_PLL_DIV_4: -+ vclk_freq /= 4; -+ break; -+ case VID_PLL_DIV_5: -+ vclk_freq /= 5; -+ break; -+ case VID_PLL_DIV_6: -+ vclk_freq /= 6; -+ break; -+ case VID_PLL_DIV_6p25: -+ vclk_freq *= 8; -+ vclk_freq /= 50; -+ break; -+ case VID_PLL_DIV_7: -+ vclk_freq /= 7; -+ break; -+ case VID_PLL_DIV_7p5: -+ vclk_freq *= 4; -+ vclk_freq /= 30; -+ break; -+ case VID_PLL_DIV_12: -+ vclk_freq /= 12; -+ break; -+ case VID_PLL_DIV_14: -+ vclk_freq /= 14; -+ break; -+ case VID_PLL_DIV_15: -+ vclk_freq /= 15; -+ break; -+ default: -+ return 0; -+ } -+ -+ return vclk_freq; -+} -+ -+static bool meson_get_vclk_params(unsigned int freq, -+ struct meson_vclk_params* vclk_params) -+{ -+ unsigned int vclk_freq = freq; -+ unsigned int base_freq, od1_od2, od3_vpll_vclk; -+ int p, jit; -+ bool found = false; -+ -+ if ((vclk_freq < 13500) || (vclk_freq > 594000)) -+ return false; -+ -+ if (vclk_freq % 25 > 12) -+ vclk_freq += 25; -+ vclk_freq -= vclk_freq % 25; -+ -+ for (p = 1; p < sizeof(params) / sizeof(struct meson_vclk_params); p++) { -+ if (params[p].vid_pll_div != VID_PLL_DIV_5) -+ continue; -+ -+ od1_od2 = params[p].pll_od1 * params[p].pll_od2; -+ od3_vpll_vclk = params[p].pll_od3 * 5 * params[p].vclk_div; -+ -+ if ((od3_vpll_vclk != 10) && (vclk_freq > 54000 + 175)) -+ continue; -+ -+ base_freq = vclk_freq * od1_od2 * od3_vpll_vclk; -+ -+ if ((base_freq < 2700000) || (base_freq > 5940000)) -+ continue; -+ -+ vclk_params->pll_base_freq = base_freq; -+ vclk_params->pll_od1 = params[p].pll_od1; -+ vclk_params->pll_od2 = params[p].pll_od2; -+ vclk_params->pll_od3 = params[p].pll_od3; -+ vclk_params->vid_pll_div = params[p].vid_pll_div; -+ vclk_params->vclk_div = params[p].vclk_div; -+ -+ found = true; -+ -+ if (params[p].pll_base_freq > vclk_params->pll_base_freq) -+ jit = params[p].pll_base_freq - vclk_params->pll_base_freq; -+ else -+ jit = vclk_params->pll_base_freq - params[p].pll_base_freq; -+ -+ if (jit < 175 * od1_od2 * od3_vpll_vclk) { -+ vclk_params->pll_base_freq = params[p].pll_base_freq; -+ vclk_freq = vclk_params->pll_base_freq / od1_od2 / od3_vpll_vclk; -+ } -+ -+ if (jit < 40000) -+ break; -+ } -+ -+ return found; -+} -+ -+static void meson_print_vclk_params(struct meson_drm *priv, unsigned int freq, -+ struct meson_vclk_params* vclk_params) -+{ -+ unsigned int vclk_freq = meson_vclk_freq_from_params(vclk_params); -+ -+ if (vclk_params->vid_pll_div != VID_PLL_DIV_5) -+ return; -+ -+ if (vclk_freq != freq) -+ dev_info(priv->dev, "adjusted %d -> %d", freq, vclk_freq); -+ -+ dev_info(priv->dev, "params %d / %d / %d / %d / %d / %d = %d\n", -+ vclk_params->pll_base_freq, -+ vclk_params->pll_od1, -+ vclk_params->pll_od2, -+ vclk_params->pll_od3, -+ 5, vclk_params->vclk_div, -+ vclk_freq); -+} -+ -+bool meson_vclk_supported(unsigned int vclk_freq) -+{ -+ struct meson_vclk_params custom_params; -+ -+ return (meson_get_vclk_params(vclk_freq, &custom_params)); -+} -+EXPORT_SYMBOL_GPL(meson_vclk_supported); -+ - void meson_vclk_setup(struct meson_drm *priv, unsigned int target, - unsigned int vclk_freq, unsigned int venc_freq, - unsigned int dac_freq, bool hdmi_use_enci) -@@ -913,6 +1151,8 @@ - unsigned int freq; - unsigned int hdmi_tx_div; - unsigned int venc_div; -+ struct meson_vclk_params custom_params; -+ struct meson_vclk_params* vclk_params; - - if (target == MESON_VCLK_TARGET_CVBS) { - meson_venci_cvbs_clock_config(priv); -@@ -945,6 +1185,9 @@ - case 25175: - freq = MESON_VCLK_HDMI_25175; - break; -+ case 29750: -+ freq = MESON_VCLK_HDMI_29750; -+ break; - case 32000: - freq = MESON_VCLK_HDMI_32000; - break; -@@ -966,6 +1209,9 @@ - case 74250: - freq = MESON_VCLK_HDMI_74250; - break; -+ case 106500: -+ freq = MESON_VCLK_HDMI_106500; -+ break; - case 108000: - freq = MESON_VCLK_HDMI_108000; - break; -@@ -978,6 +1224,9 @@ - case 162000: - freq = MESON_VCLK_HDMI_162000; - break; -+ case 193250: -+ freq = MESON_VCLK_HDMI_193250; -+ break; - case 297000: - freq = MESON_VCLK_HDMI_297000; - break; -@@ -985,9 +1234,8 @@ - freq = MESON_VCLK_HDMI_594000; - break; - default: -- pr_err("Fatal Error, invalid HDMI vclk freq %d\n", -- vclk_freq); -- return; -+ freq = MESON_VCLK_HDMI_CUSTOM; -+ break; - } - - /* Set HDMI-TX sys clock */ -@@ -998,20 +1246,35 @@ - regmap_update_bits(priv->hhi, HHI_HDMI_CLK_CNTL, - CTS_HDMI_SYS_EN, CTS_HDMI_SYS_EN); - -+ vclk_params = NULL; -+ -+ if (freq != MESON_VCLK_HDMI_CUSTOM) -+ vclk_params = ¶ms[freq]; -+ else if (meson_get_vclk_params(vclk_freq, &custom_params)) -+ vclk_params = &custom_params; -+ -+ if (!vclk_params) { -+ pr_err("Fatal Error, invalid HDMI vclk freq %d\n", -+ vclk_freq); -+ return; -+ } -+ -+ meson_print_vclk_params(priv, vclk_freq, vclk_params); -+ - /* Set HDMI PLL rate */ -- meson_hdmi_pll_set(priv, params[freq].pll_base_freq, -- params[freq].pll_od1, -- params[freq].pll_od2, -- params[freq].pll_od3); -+ meson_hdmi_pll_set(priv, vclk_params->pll_base_freq, -+ vclk_params->pll_od1, -+ vclk_params->pll_od2, -+ vclk_params->pll_od3); - - /* Setup vid_pll divider */ -- meson_vid_pll_set(priv, params[freq].vid_pll_div); -+ meson_vid_pll_set(priv, vclk_params->vid_pll_div); - - /* Set VCLK div */ - regmap_update_bits(priv->hhi, HHI_VID_CLK_CNTL, - VCLK_SEL_MASK, 0); - regmap_update_bits(priv->hhi, HHI_VID_CLK_DIV, -- VCLK_DIV_MASK, params[freq].vclk_div - 1); -+ VCLK_DIV_MASK, vclk_params->vclk_div - 1); - - /* Set HDMI-TX source */ - switch (hdmi_tx_div) { -diff -ur a/drivers/gpu/drm/meson/meson_vclk.h b/drivers/gpu/drm/meson/meson_vclk.h ---- a/drivers/gpu/drm/meson/meson_vclk.h 2018-05-26 22:29:37.112948771 +0200 -+++ b/drivers/gpu/drm/meson/meson_vclk.h 2018-05-31 05:15:53.342134304 +0200 -@@ -29,6 +29,8 @@ - /* 27MHz is the CVBS Pixel Clock */ - #define MESON_VCLK_CVBS 27000 - -+bool meson_vclk_supported(unsigned int vclk_freq); -+ - void meson_vclk_setup(struct meson_drm *priv, unsigned int target, - unsigned int vclk_freq, unsigned int venc_freq, - unsigned int dac_freq, bool hdmi_use_enci); -diff -ur a/drivers/gpu/drm/meson/meson_venc.c b/drivers/gpu/drm/meson/meson_venc.c ---- a/drivers/gpu/drm/meson/meson_venc.c 2018-06-02 20:23:23.744646670 +0200 -+++ b/drivers/gpu/drm/meson/meson_venc.c 2018-06-02 17:25:33.807332121 +0200 -@@ -707,6 +707,12 @@ - 752, 800, 0, 480, 490, 492, 525, 0, - DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, - }, -+ /* 800x480@60Hz */ -+ { -+ { DRM_MODE("800x480", DRM_MODE_TYPE_DRIVER, 29750, 800, 824, -+ 896, 992, 0, 480, 483, 490, 500, 0, -+ DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -+ }, - /* 800x600@60Hz */ - { - { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 40000, 800, 840, -@@ -737,6 +743,12 @@ - 1328, 1440, 1688, 0, 1024, 1025, 1028, 1066, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, - }, -+ /* 1440x900@60Hz */ -+ { -+ { DRM_MODE("1440x900", DRM_MODE_TYPE_DRIVER, 106500, 1440, -+ 1520, 1672, 1904, 0, 900, 903, 909, 934, 0, -+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) }, -+ }, - /* 1600x1200@60Hz */ - { - { DRM_MODE("1600x1200", DRM_MODE_TYPE_DRIVER, 162000, 1600, -@@ -749,6 +761,12 @@ - 2008, 2052, 2200, 0, 1080, 1084, 1089, 1125, 0, - DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, - }, -+ /* 1920x1200@60Hz */ -+ { -+ { DRM_MODE("1920x1200", DRM_MODE_TYPE_DRIVER, 193250, 1920, -+ 2056, 2256, 2592, 0, 1200, 1203, 1209, 1245, 0, -+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) }, -+ }, - { }, /* sentinel */ - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/071_linux-4.17-amlogic-dmt-extended-1003-calculate-clock-dividers.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/071_linux-4.17-amlogic-dmt-extended-1003-calculate-clock-dividers.patch deleted file mode 100644 index 5dfcace64..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/071_linux-4.17-amlogic-dmt-extended-1003-calculate-clock-dividers.patch +++ /dev/null @@ -1,115 +0,0 @@ -diff -u a/drivers/gpu/drm/meson/meson_vclk.c b/drivers/gpu/drm/meson/meson_vclk.c ---- a/drivers/gpu/drm/meson/meson_vclk.c 2018-06-10 06:10:59.071504595 +0200 -+++ b/drivers/gpu/drm/meson/meson_vclk.c 2018-06-10 05:33:51.347202114 +0200 -@@ -842,7 +842,7 @@ - if (frac >= range) - frac = range-1; - -- pr_info("%s: base=%d, m=0x%.2x, frac=0x%.3x", __func__, base, m, frac); -+ dev_info(priv->dev, "%s: base=%d, m=0x%.2x, frac=0x%.3x\n", __func__, base, m, frac); - - switch (base) { - case 2700000: -@@ -1065,25 +1065,36 @@ - { - unsigned int vclk_freq = freq; - unsigned int base_freq, od1_od2, od3_vpll_vclk; -- int p, jit; -+ int od1, od2, od3, p, jit; - bool found = false; - -- if ((vclk_freq < 13500) || (vclk_freq > 594000)) -+ if ((vclk_freq < 12000) || (vclk_freq > 594000)) - return false; - - if (vclk_freq % 25 > 12) - vclk_freq += 25; - vclk_freq -= vclk_freq % 25; - -- for (p = 1; p < sizeof(params) / sizeof(struct meson_vclk_params); p++) { -- if (params[p].vid_pll_div != VID_PLL_DIV_5) -+ for (p = 0; p < 6; p++) { -+ od1 = (1 << p); -+ od2 = 1; -+ od3 = 1; -+ -+ if ((vclk_freq > 18550) && (od1 > 16)) - continue; - -- od1_od2 = params[p].pll_od1 * params[p].pll_od2; -- od3_vpll_vclk = params[p].pll_od3 * 5 * params[p].vclk_div; -+ if (od1 > 16) { -+ od3 = od1 / 16; -+ od1 = 16; -+ } - -- if ((od3_vpll_vclk != 10) && (vclk_freq > 54000 + 175)) -- continue; -+ if (od1 > 4) { -+ od2 = od1 / 4; -+ od1 = 4; -+ } -+ -+ od1_od2 = od1 * od2; -+ od3_vpll_vclk = od3 * 5 * 2; - - base_freq = vclk_freq * od1_od2 * od3_vpll_vclk; - -@@ -1091,21 +1102,32 @@ - continue; - - vclk_params->pll_base_freq = base_freq; -- vclk_params->pll_od1 = params[p].pll_od1; -- vclk_params->pll_od2 = params[p].pll_od2; -- vclk_params->pll_od3 = params[p].pll_od3; -- vclk_params->vid_pll_div = params[p].vid_pll_div; -- vclk_params->vclk_div = params[p].vclk_div; -+ vclk_params->pll_od1 = od1; -+ vclk_params->pll_od2 = od2; -+ vclk_params->pll_od3 = od3; -+ vclk_params->vid_pll_div = VID_PLL_DIV_5; -+ vclk_params->vclk_div = 2; - - found = true; - -- if (params[p].pll_base_freq > vclk_params->pll_base_freq) -- jit = params[p].pll_base_freq - vclk_params->pll_base_freq; -+ jit = od1_od2 * od3_vpll_vclk * 125; -+ if (p < 3) -+ jit <<= (3-p); -+ -+ if ((base_freq % 24000) < (base_freq % jit)) -+ jit = 24000; -+ -+ if ((base_freq % jit) > (jit / 2)) -+ base_freq = base_freq+jit; -+ base_freq -= base_freq % jit; -+ -+ if (base_freq > vclk_params->pll_base_freq) -+ jit = base_freq - vclk_params->pll_base_freq; - else -- jit = vclk_params->pll_base_freq - params[p].pll_base_freq; -+ jit = vclk_params->pll_base_freq - base_freq; - - if (jit < 175 * od1_od2 * od3_vpll_vclk) { -- vclk_params->pll_base_freq = params[p].pll_base_freq; -+ vclk_params->pll_base_freq = base_freq; - vclk_freq = vclk_params->pll_base_freq / od1_od2 / od3_vpll_vclk; - } - -diff -u a/drivers/gpu/drm/meson/meson_venc.c b/drivers/gpu/drm/meson/meson_venc.c ---- a/drivers/gpu/drm/meson/meson_venc.c 2018-06-10 06:10:59.071504595 +0200 -+++ b/drivers/gpu/drm/meson/meson_venc.c 2018-06-10 05:26:59.995203463 +0200 -@@ -816,10 +816,10 @@ - DRM_MODE_FLAG_PVSYNC | DRM_MODE_FLAG_NVSYNC)) - return MODE_BAD; - -- if (mode->hdisplay < 640 || mode->hdisplay > 1920) -+ if (mode->hdisplay < 416 || mode->hdisplay > 1920) - return MODE_BAD_HVALUE; - -- if (mode->vdisplay < 480 || mode->vdisplay > 1200) -+ if (mode->vdisplay < 360 || mode->vdisplay > 1200) - return MODE_BAD_VVALUE; - - return MODE_OK; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/072_linux-4.16.y-input_touchscreen-vu5-vu7plus.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/072_linux-4.16.y-input_touchscreen-vu5-vu7plus.patch deleted file mode 100644 index 3693d959d..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/072_linux-4.16.y-input_touchscreen-vu5-vu7plus.patch +++ /dev/null @@ -1,1235 +0,0 @@ -diff --git a/drivers/hid/hid-quirks.c b/drivers/hid/hid-quirks.c -index e92b77fa5..53bdf9725 100644 ---- a/drivers/hid/hid-quirks.c -+++ b/drivers/hid/hid-quirks.c -@@ -869,6 +869,8 @@ static const struct hid_device_id hid_ignore_list[] = { - { HID_USB_DEVICE(USB_VENDOR_ID_SYNAPTICS, USB_DEVICE_ID_SYNAPTICS_DPAD) }, - #endif - { HID_USB_DEVICE(USB_VENDOR_ID_YEALINK, USB_DEVICE_ID_YEALINK_P1K_P4K_B2K) }, -+ { HID_USB_DEVICE(USB_VENDOR_ID_ODROID, USB_DEVICE_ID_VU5) }, -+ { HID_USB_DEVICE(USB_VENDOR_ID_ODROID, USB_DEVICE_ID_VU7PLUS) }, - { } - }; - -diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h -index ff539c0b4..b09d5ea03 100644 ---- a/drivers/hid/hid-ids.h -+++ b/drivers/hid/hid-ids.h -@@ -1164,4 +1164,10 @@ - #define USB_VENDOR_ID_UGTIZER 0x2179 - #define USB_DEVICE_ID_UGTIZER_TABLET_GP0610 0x0053 - -+#define USB_DEVICE_ID_DWAV_MULTITOUCH 0x0005 -+ -+#define USB_VENDOR_ID_ODROID 0x16b4 -+#define USB_DEVICE_ID_VU5 0x0704 -+#define USB_DEVICE_ID_VU7PLUS 0x0705 -+ - #endif -diff --git a/drivers/input/touchscreen/Kconfig b/drivers/input/touchscreen/Kconfig -index 64b30fe27..05e834eed 100644 ---- a/drivers/input/touchscreen/Kconfig -+++ b/drivers/input/touchscreen/Kconfig -@@ -1246,4 +1246,23 @@ config TOUCHSCREEN_ROHM_BU21023 - To compile this driver as a module, choose M here: the - module will be called bu21023_ts. - -+config TOUCHSCREEN_DWAV_USB_MT -+ tristate "D-WAV Scientific USB MultiTouch" -+ depends on USB_ARCH_HAS_HCD -+ select USB -+ help -+ Say Y here if you have a D-WAV Scientific USB(HID) based MultiTouch -+ controller. -+ -+ If unsure, say N. -+ -+ To compile this driver as a module, choose M here: the -+ module will be called dwav-usb-mt. -+ -+config TOUCHSCREEN_SX865X -+ tristate "Semtech multitouch resistive touchscreen" -+ depends on I2C -+ help -+ This enables support for Semtech multitouch resistive touchscreen. -+ - endif -diff --git a/drivers/input/touchscreen/Makefile b/drivers/input/touchscreen/Makefile -index 850c15625..bc3f0e1d5 100644 ---- a/drivers/input/touchscreen/Makefile -+++ b/drivers/input/touchscreen/Makefile -@@ -104,3 +104,5 @@ obj-$(CONFIG_TOUCHSCREEN_ZET6223) += zet6223.o - obj-$(CONFIG_TOUCHSCREEN_ZFORCE) += zforce_ts.o - obj-$(CONFIG_TOUCHSCREEN_COLIBRI_VF50) += colibri-vf50-ts.o - obj-$(CONFIG_TOUCHSCREEN_ROHM_BU21023) += rohm_bu21023.o -+obj-$(CONFIG_TOUCHSCREEN_DWAV_USB_MT) += dwav-usb-mt.o -+obj-$(CONFIG_TOUCHSCREEN_SX865X) += sx865x.o -diff -urN a/drivers/input/touchscreen/dwav-usb-mt.c b/drivers/input/touchscreen/dwav-usb-mt.c ---- a/drivers/input/touchscreen/dwav-usb-mt.c 1970-01-01 01:00:00.000000000 +0100 -+++ b/drivers/input/touchscreen/dwav-usb-mt.c 2018-05-06 10:03:40.485939294 +0200 -@@ -0,0 +1,577 @@ -+/*------------------------------------------------------------------------- -+ -+ D-WAV Scientific USB(HID) MultiTouch Screen Driver(Based on usbtouchscreen.c) -+ Hardkernel : 2015/09/17 -+ -+-------------------------------------------------------------------------*/ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include -+ -+/*-------------------------------------------------------------------------*/ -+#define USB_VENDOR_ID_DWAV 0x0eef /* 800 x 480, 7" DWAV touch */ -+#define USB_DEVICE_ID_VU7 0x0005 -+ -+#define USB_VENDOR_ID_ODROID 0x16b4 -+#define USB_DEVICE_ID_VU5 0x0704 -+#define USB_DEVICE_ID_VU7PLUS 0x0705 -+ -+enum { -+ ODROID_VU7 = 0, /* 800 x 480, 7" Touch */ -+ ODROID_VU5, /* 800 x 480, 5" Touch */ -+ ODROID_VU7PLUS, /* 1024 x 600, 7" Touch */ -+}; -+ -+/*-------------------------------------------------------------------------*/ -+struct usbtouch_device_info { -+ char name[64]; -+ int max_x; -+ int max_y; -+ int max_press; -+ int max_finger; -+}; -+ -+/*-------------------------------------------------------------------------*/ -+const struct usbtouch_device_info DEV_INFO[] = { -+ [ODROID_VU7] = { -+ .name = "ODROID VU7 MultiTouch(800x480)", -+ .max_x = 800, -+ .max_y = 480, -+ .max_press = 255, -+ .max_finger = 5, -+ }, -+ [ODROID_VU5] = { -+ .name = "ODROID VU5 MultiTouch(800x480)", -+ .max_x = 800, -+ .max_y = 480, -+ .max_press = 255, -+ .max_finger = 5, -+ }, -+ [ODROID_VU7PLUS] = { -+ .name = "ODROID VU7 Plus MultiTouch(1024x600)", -+ .max_x = 1024, -+ .max_y = 600, -+ .max_press = 255, -+ .max_finger = 5, -+ }, -+}; -+ -+/*-------------------------------------------------------------------------*/ -+static const struct usb_device_id dwav_usb_mt_devices[] = { -+ {USB_DEVICE(USB_VENDOR_ID_DWAV, USB_DEVICE_ID_VU7), -+ .driver_info = ODROID_VU7}, -+ {USB_DEVICE(USB_VENDOR_ID_ODROID, USB_DEVICE_ID_VU5), -+ .driver_info = ODROID_VU5}, -+ {USB_DEVICE(USB_VENDOR_ID_ODROID, USB_DEVICE_ID_VU7PLUS), -+ .driver_info = ODROID_VU7PLUS}, -+ {} -+}; -+ -+/*-------------------------------------------------------------------------*/ -+struct dwav_raw { /* Total 25 bytes */ -+ unsigned char header; /* frame header 0xAA*/ -+ unsigned char press; -+ /* Touch flag (1:valid touch data, 0:touch finished) */ -+ unsigned short x1; /* 1st x */ -+ unsigned short y1; /* 1st y */ -+ unsigned char end; -+ /* 1st touch finish flags 0xBB, RPI only uses the first 7 bytes */ -+ unsigned char ids; /* touch ID(bit field) */ -+ unsigned short y2; -+ unsigned short x2; -+ unsigned short y3; -+ unsigned short x3; -+ unsigned short y4; -+ unsigned short x4; -+ unsigned short y5; -+ unsigned short x5; -+ unsigned char tail; /* frame end 0xCC */ -+}; -+ -+/*------------------------------------------------------------------------- -+ Touch Event type define -+-------------------------------------------------------------------------*/ -+#define TS_EVENT_UNKNOWN 0x00 -+#define TS_EVENT_PRESS 0x01 -+#define TS_EVENT_RELEASE 0x02 -+ -+struct finger_t { -+ unsigned int status; /* ts event type */ -+ unsigned int x; /* ts data x */ -+ unsigned int y; /* ts data y */ -+} __packed; -+ -+struct dwav_usb_mt { -+ char name[128], phys[64]; -+ -+ int dev_id; -+ /* for URB Data DMA */ -+ dma_addr_t data_dma; -+ unsigned char *data; -+ int data_size; -+ -+ struct urb *irq; -+ struct usb_interface *interface; -+ struct input_dev *input; -+ -+ struct finger_t *finger; -+}; -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_report(struct dwav_usb_mt *dwav_usb_mt) -+{ -+ int id, max_x, max_y, max_press, max_finger; -+ -+ max_x = DEV_INFO[dwav_usb_mt->dev_id].max_x; -+ max_y = DEV_INFO[dwav_usb_mt->dev_id].max_y; -+ max_press = DEV_INFO[dwav_usb_mt->dev_id].max_press; -+ max_finger = DEV_INFO[dwav_usb_mt->dev_id].max_finger; -+ -+ for (id = 0; id < max_finger; id++) { -+ -+ if (dwav_usb_mt->finger[id].status == TS_EVENT_UNKNOWN) -+ continue; -+ -+ if (dwav_usb_mt->finger[id].x >= max_x || -+ dwav_usb_mt->finger[id].y >= max_y) -+ continue; -+ -+ input_mt_slot(dwav_usb_mt->input, id); -+ -+ if (dwav_usb_mt->finger[id].status != TS_EVENT_RELEASE) { -+ input_mt_report_slot_state(dwav_usb_mt->input, -+ MT_TOOL_FINGER, true); -+ input_report_abs(dwav_usb_mt->input, -+ ABS_MT_POSITION_X, -+ dwav_usb_mt->finger[id].x); -+ input_report_abs(dwav_usb_mt->input, -+ ABS_MT_POSITION_Y, -+ dwav_usb_mt->finger[id].y); -+ input_report_abs(dwav_usb_mt->input, -+ ABS_MT_PRESSURE, -+ max_press); -+ } else { -+ input_mt_report_slot_state(dwav_usb_mt->input, -+ MT_TOOL_FINGER, false); -+ dwav_usb_mt->finger[id].status = TS_EVENT_UNKNOWN; -+ } -+ input_mt_report_pointer_emulation(dwav_usb_mt->input, true); -+ input_sync(dwav_usb_mt->input); -+ } -+} -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_process(struct dwav_usb_mt *dwav_usb_mt, -+ unsigned char *pkt, int len) -+{ -+ struct dwav_raw *dwav_raw = (struct dwav_raw *)pkt; -+ unsigned char bit_mask, cnt; -+ -+ for (cnt = 0, bit_mask = 0x01; -+ cnt < DEV_INFO[dwav_usb_mt->dev_id].max_finger; -+ cnt++, bit_mask <<= 1) { -+ if ((dwav_raw->ids & bit_mask) && dwav_raw->press) { -+ dwav_usb_mt->finger[cnt].status = TS_EVENT_PRESS; -+ switch (cnt) { -+ case 0: -+ dwav_usb_mt->finger[cnt].x -+ = cpu_to_be16(dwav_raw->x1); -+ dwav_usb_mt->finger[cnt].y -+ = cpu_to_be16(dwav_raw->y1); -+ break; -+ case 1: -+ dwav_usb_mt->finger[cnt].x -+ = cpu_to_be16(dwav_raw->x2); -+ dwav_usb_mt->finger[cnt].y -+ = cpu_to_be16(dwav_raw->y2); -+ break; -+ case 2: -+ dwav_usb_mt->finger[cnt].x -+ = cpu_to_be16(dwav_raw->x3); -+ dwav_usb_mt->finger[cnt].y -+ = cpu_to_be16(dwav_raw->y3); -+ break; -+ case 3: -+ dwav_usb_mt->finger[cnt].x -+ = cpu_to_be16(dwav_raw->x4); -+ dwav_usb_mt->finger[cnt].y -+ = cpu_to_be16(dwav_raw->y4); -+ break; -+ case 4: -+ dwav_usb_mt->finger[cnt].x -+ = cpu_to_be16(dwav_raw->x5); -+ dwav_usb_mt->finger[cnt].y -+ = cpu_to_be16(dwav_raw->y5); -+ break; -+ default: -+ break; -+ } -+ } else { -+ if (dwav_usb_mt->finger[cnt].status == TS_EVENT_PRESS) -+ dwav_usb_mt->finger[cnt].status -+ = TS_EVENT_RELEASE; -+ else -+ dwav_usb_mt->finger[cnt].status -+ = TS_EVENT_UNKNOWN; -+ } -+ } -+ dwav_usb_mt_report(dwav_usb_mt); -+} -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_irq(struct urb *urb) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = urb->context; -+ struct device *dev = &dwav_usb_mt->interface->dev; -+ int retval; -+ -+ switch (urb->status) { -+ case 0: -+ /* success */ -+ break; -+ case -ETIME: -+ /* this urb is timing out */ -+ dev_dbg(dev, "%s - urb timed out - was the device unplugged?\n", -+ __func__); -+ return; -+ case -ECONNRESET: -+ case -ENOENT: -+ case -ESHUTDOWN: -+ case -EPIPE: -+ /* this urb is terminated, clean up */ -+ dev_dbg(dev, "%s - urb shutting down with status: %d\n", -+ __func__, urb->status); -+ return; -+ default: -+ dev_dbg(dev, "%s - nonzero urb status received: %d\n", -+ __func__, urb->status); -+ goto exit; -+ } -+ -+ dwav_usb_mt_process(dwav_usb_mt, dwav_usb_mt->data, urb->actual_length); -+ -+exit: -+ usb_mark_last_busy(interface_to_usbdev(dwav_usb_mt->interface)); -+ retval = usb_submit_urb(urb, GFP_ATOMIC); -+ if (retval) { -+ dev_err(dev, "%s - usb_submit_urb failed with result: %d\n", -+ __func__, retval); -+ } -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_open(struct input_dev *input) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = input_get_drvdata(input); -+ int r; -+ -+ dwav_usb_mt->irq->dev = interface_to_usbdev(dwav_usb_mt->interface); -+ -+ r = usb_autopm_get_interface(dwav_usb_mt->interface) ? -EIO : 0; -+ if (r < 0) -+ goto out; -+ -+ if (usb_submit_urb(dwav_usb_mt->irq, GFP_KERNEL)) { -+ r = -EIO; -+ goto out_put; -+ } -+ -+ dwav_usb_mt->interface->needs_remote_wakeup = 1; -+out_put: -+ usb_autopm_put_interface(dwav_usb_mt->interface); -+out: -+ return r; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_close(struct input_dev *input) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = input_get_drvdata(input); -+ int r; -+ -+ usb_kill_urb(dwav_usb_mt->irq); -+ -+ r = usb_autopm_get_interface(dwav_usb_mt->interface); -+ -+ dwav_usb_mt->interface->needs_remote_wakeup = 0; -+ if (!r) -+ usb_autopm_put_interface(dwav_usb_mt->interface); -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_suspend(struct usb_interface *intf, pm_message_t message) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = usb_get_intfdata(intf); -+ -+ usb_kill_urb(dwav_usb_mt->irq); -+ -+ return 0; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_resume(struct usb_interface *intf) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = usb_get_intfdata(intf); -+ struct input_dev *input = dwav_usb_mt->input; -+ int result = 0; -+ -+ mutex_lock(&input->mutex); -+ if (input->users) -+ result = usb_submit_urb(dwav_usb_mt->irq, GFP_NOIO); -+ mutex_unlock(&input->mutex); -+ -+ return result; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_reset_resume(struct usb_interface *intf) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = usb_get_intfdata(intf); -+ struct input_dev *input = dwav_usb_mt->input; -+ int err = 0; -+ -+ /* restart IO if needed */ -+ mutex_lock(&input->mutex); -+ if (input->users) -+ err = usb_submit_urb(dwav_usb_mt->irq, GFP_NOIO); -+ mutex_unlock(&input->mutex); -+ -+ return err; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_free_buffers(struct usb_device *udev, -+ struct dwav_usb_mt *dwav_usb_mt) -+{ -+ usb_free_coherent(udev, dwav_usb_mt->data_size, -+ dwav_usb_mt->data, dwav_usb_mt->data_dma); -+} -+ -+/*-------------------------------------------------------------------------*/ -+static struct usb_endpoint_descriptor *dwav_usb_mt_get_input_endpoint( -+ struct usb_host_interface *interface) -+{ -+ int i; -+ -+ for (i = 0; i < interface->desc.bNumEndpoints; i++) { -+ if (usb_endpoint_dir_in(&interface->endpoint[i].desc)) -+ return &interface->endpoint[i].desc; -+ } -+ -+ return NULL; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_init(struct dwav_usb_mt *dwav_usb_mt, void *dev) -+{ -+ int err; -+ struct input_dev *input_dev = (struct input_dev *)dev; -+ -+ input_dev->name = dwav_usb_mt->name; -+ input_dev->phys = dwav_usb_mt->phys; -+ -+ input_set_drvdata(input_dev, dwav_usb_mt); -+ -+ input_dev->open = dwav_usb_mt_open; -+ input_dev->close = dwav_usb_mt_close; -+ -+ input_dev->id.bustype = BUS_USB; -+ -+ /* single touch */ -+ input_dev->evbit[0] = BIT_MASK(EV_KEY) | BIT_MASK(EV_ABS); -+ input_dev->keybit[BIT_WORD(BTN_TOUCH)] = BIT_MASK(BTN_TOUCH); -+ -+ input_set_abs_params(input_dev, ABS_X, 0, -+ DEV_INFO[dwav_usb_mt->dev_id].max_x, 0, 0); -+ input_set_abs_params(input_dev, ABS_Y, 0, -+ DEV_INFO[dwav_usb_mt->dev_id].max_y, 0, 0); -+ -+ /* multi touch */ -+ input_set_abs_params(input_dev, ABS_MT_POSITION_X, 0, -+ DEV_INFO[dwav_usb_mt->dev_id].max_x, 0, 0); -+ input_set_abs_params(input_dev, ABS_MT_POSITION_Y, 0, -+ DEV_INFO[dwav_usb_mt->dev_id].max_y, 0, 0); -+ input_mt_init_slots(input_dev, -+ DEV_INFO[dwav_usb_mt->dev_id].max_finger, 0); -+ -+ err = input_register_device(input_dev); -+ if (err) { -+ pr_err("%s - input_register_device failed, err: %d\n", -+ __func__, err); -+ return err; -+ } -+ -+ dwav_usb_mt->input = input_dev; -+ -+ return 0; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_probe(struct usb_interface *intf, -+ const struct usb_device_id *id) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = NULL; -+ struct input_dev *input_dev = NULL; -+ struct usb_endpoint_descriptor *endpoint; -+ struct usb_device *udev = interface_to_usbdev(intf); -+ -+ int err = 0; -+ -+ endpoint = dwav_usb_mt_get_input_endpoint(intf->cur_altsetting); -+ if (!endpoint) -+ return -ENXIO; -+ -+ dwav_usb_mt = kzalloc(sizeof(struct dwav_usb_mt), GFP_KERNEL); -+ if (!dwav_usb_mt) -+ return -ENOMEM; -+ -+ dwav_usb_mt->dev_id = id->driver_info; -+ -+ dwav_usb_mt->finger = kzalloc(sizeof(struct finger_t) * -+ DEV_INFO[dwav_usb_mt->dev_id].max_finger, -+ GFP_KERNEL); -+ -+ if (!dwav_usb_mt->finger) -+ goto err_free_mem; -+ -+ input_dev = input_allocate_device(); -+ if (!input_dev) -+ goto err_free_mem; -+ -+ dwav_usb_mt->data_size = sizeof(struct dwav_raw); -+ dwav_usb_mt->data = usb_alloc_coherent(udev, dwav_usb_mt->data_size, -+ GFP_KERNEL, &dwav_usb_mt->data_dma); -+ if (!dwav_usb_mt->data) -+ goto err_free_mem; -+ -+ dwav_usb_mt->irq = usb_alloc_urb(0, GFP_KERNEL); -+ if (!dwav_usb_mt->irq) { -+ dev_dbg(&intf->dev, -+ "%s - usb_alloc_urb failed: usbtouch->irq\n", -+ __func__); -+ goto err_free_buffers; -+ } -+ -+ if (usb_endpoint_type(endpoint) == USB_ENDPOINT_XFER_INT) { -+ usb_fill_int_urb(dwav_usb_mt->irq, udev, -+ usb_rcvintpipe(udev, endpoint->bEndpointAddress), -+ dwav_usb_mt->data, dwav_usb_mt->data_size, -+ dwav_usb_mt_irq, dwav_usb_mt, endpoint->bInterval); -+ } else { -+ usb_fill_bulk_urb(dwav_usb_mt->irq, udev, -+ usb_rcvbulkpipe(udev, endpoint->bEndpointAddress), -+ dwav_usb_mt->data, dwav_usb_mt->data_size, -+ dwav_usb_mt_irq, dwav_usb_mt); -+ } -+ -+ dwav_usb_mt->irq->dev = udev; -+ dwav_usb_mt->irq->transfer_dma = dwav_usb_mt->data_dma; -+ dwav_usb_mt->irq->transfer_flags |= URB_NO_TRANSFER_DMA_MAP; -+ -+ dwav_usb_mt->interface = intf; -+ -+ if (udev->manufacturer) -+ strlcpy(dwav_usb_mt->name, -+ udev->manufacturer, sizeof(dwav_usb_mt->name)); -+ -+ if (udev->product) { -+ if (udev->manufacturer) -+ strlcat(dwav_usb_mt->name, -+ " ", sizeof(dwav_usb_mt->name)); -+ -+ strlcat(dwav_usb_mt->name, -+ udev->product, sizeof(dwav_usb_mt->name)); -+ } -+ -+ if (!strlen(dwav_usb_mt->name)) { -+ snprintf(dwav_usb_mt->name, sizeof(dwav_usb_mt->name), -+ "D-WAV Scientific MultiTouch %04x:%04x", -+ le16_to_cpu(udev->descriptor.idVendor), -+ le16_to_cpu(udev->descriptor.idProduct)); -+ } -+ -+ usb_make_path(udev, dwav_usb_mt->phys, sizeof(dwav_usb_mt->phys)); -+ strlcat(dwav_usb_mt->phys, "/input0", sizeof(dwav_usb_mt->phys)); -+ -+ usb_to_input_id(udev, &input_dev->id); -+ -+ input_dev->dev.parent = &intf->dev; -+ -+ err = dwav_usb_mt_init(dwav_usb_mt, (void *)input_dev); -+ if (err) -+ goto err_free_urb; -+ -+ usb_set_intfdata(intf, dwav_usb_mt); -+ -+ dev_info(&intf->dev, "%s\n", DEV_INFO[dwav_usb_mt->dev_id].name); -+ -+ return 0; -+ -+err_free_urb: -+ usb_free_urb(dwav_usb_mt->irq); -+ -+err_free_buffers: -+ dwav_usb_mt_free_buffers(udev, dwav_usb_mt); -+ -+err_free_mem: -+ if (input_dev) -+ input_free_device(input_dev); -+ kfree(dwav_usb_mt); -+ -+ return err; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_disconnect(struct usb_interface *intf) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = usb_get_intfdata(intf); -+ -+ if (!dwav_usb_mt) -+ return; -+ -+ dev_dbg(&intf->dev, -+ "%s - dwav_usb_mt is initialized, cleaning up\n", -+ __func__); -+ -+ usb_set_intfdata(intf, NULL); -+ -+ /* this will stop IO via close */ -+ input_unregister_device(dwav_usb_mt->input); -+ -+ usb_free_urb(dwav_usb_mt->irq); -+ -+ dwav_usb_mt_free_buffers(interface_to_usbdev(intf), dwav_usb_mt); -+ -+ kfree(dwav_usb_mt); -+} -+ -+/*-------------------------------------------------------------------------*/ -+MODULE_DEVICE_TABLE(usb, dwav_usb_mt_devices); -+ -+static struct usb_driver dwav_usb_mt_driver = { -+ .name = "dwav_usb_mt", -+ .probe = dwav_usb_mt_probe, -+ .disconnect = dwav_usb_mt_disconnect, -+ .suspend = dwav_usb_mt_suspend, -+ .resume = dwav_usb_mt_resume, -+ .reset_resume = dwav_usb_mt_reset_resume, -+ .id_table = dwav_usb_mt_devices, -+ .supports_autosuspend = 1, -+}; -+ -+module_usb_driver(dwav_usb_mt_driver); -+ -+/*-------------------------------------------------------------------------*/ -+MODULE_AUTHOR("Hardkernel Co.,Ltd"); -+MODULE_DESCRIPTION("D-WAV USB(HID) MultiTouch Driver"); -+MODULE_LICENSE("GPL"); -+ -+MODULE_ALIAS("dwav_usb_mt"); -+/*-------------------------------------------------------------------------*/ -diff -urN a/drivers/input/touchscreen/sx865x.c b/drivers/input/touchscreen/sx865x.c ---- a/drivers/input/touchscreen/sx865x.c 1970-01-01 01:00:00.000000000 +0100 -+++ b/drivers/input/touchscreen/sx865x.c 2018-05-06 10:03:40.553940699 +0200 -@@ -0,0 +1,584 @@ -+/* -+ * drivers/input/touchscreen/sx865x.c -+ * -+ * Copyright (c) 2013 U-MoBo Srl -+ * Pierluigi Passaro -+ * -+ * Using code from: -+ * - sx8650.c -+ * Copyright (c) 2009 Wayne Roberts -+ * - tsc2007.c -+ * Copyright (c) 2008 Kwangwoo Lee -+ * - ads7846.c -+ * Copyright (c) 2005 David Brownell -+ * Copyright (c) 2006 Nokia Corporation -+ * - corgi_ts.c -+ * Copyright (C) 2004-2005 Richard Purdie -+ * - omap_ts.[hc], ads7846.h, ts_osk.c -+ * Copyright (C) 2002 MontaVista Software -+ * Copyright (C) 2004 Texas Instruments -+ * Copyright (C) 2005 Dirk Behme -+ * -+ * 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. -+ */ -+ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+ -+#include -+#include -+ -+#define AMLGPIO_IRQ_BASE 96 -+ -+#endif -+ -+/* timeout expires after pen is lifted, no more PENIRQs comming */ -+/* adjust with POWDLY setting */ -+#define TS_TIMEOUT (8 * 1000000) -+ -+/* analog channels */ -+#define CH_X 0 -+#define CH_Y 1 -+#define CH_Z1 2 -+#define CH_Z2 3 -+#define CH_AUX 4 -+#define CH_RX 5 -+#define CH_RY 6 -+#define CH_SEQ 7 -+ -+/* commands */ -+#define SX865X_WRITE_REGISTER 0x00 -+#define SX865X_READ_REGISTER 0x40 -+#define SX865X_SELECT_CH(ch) (0x80 | ch) -+#define SX865X_CONVERT_CH(ch) (0x90 | ch) -+#define SX865X_POWDWN 0xb0 /* power down, ignore pen */ -+#define SX865X_PENDET 0xc0 /* " " with pen sensitivity */ -+#define SX865X_PENTRG 0xe0 /* " " " " and sample channels */ -+ -+/* register addresses */ -+#define I2C_REG_CTRL0 0x00 -+#define I2C_REG_CTRL1 0x01 -+#define I2C_REG_CTRL2 0x02 -+#define I2C_REG_CTRL3 0x03 -+#define I2C_REG_CHANMASK 0x04 -+#define I2C_REG_STAT 0x05 -+#define I2C_REG_SOFTRESET 0x1f -+ -+#define I2C_EXTENDED_REG_STAT 0x24 -+#define I2C_EXTENDED_REG_SOFTRESET 0x3f -+ -+#define SOFTRESET_VALUE 0xde -+ -+/* bits for I2C_REG_STAT */ -+/* I2C_REG_STAT: end of conversion flag */ -+#define STATUS_CONVIRQ 0x80 -+/* I2C_REG_STAT: pen detected */ -+#define STATUS_PENIRQ 0x40 -+ -+/* bits for I2C_EXTENDED_REG_STAT */ -+/* I2C_EXTENDED_REG_STAT: end of conversion flag */ -+#define EXTENDED_STATUS_CONVIRQ 0x08 -+/* I2C_EXTENDED_REG_STAT: pen detected */ -+#define EXTENDED_STATUS_PENIRQ 0x04 -+ -+/* sx865x bits for RegCtrl1 */ -+#define CONDIRQ 0x20 -+/* no averaging */ -+#define FILT_NONE 0x00 -+/* 3 sample averaging */ -+#define FILT_3SA 0x01 -+/* 5 sample averaging */ -+#define FILT_5SA 0x02 -+/* 7 samples, sort, then average of 3 middle samples */ -+#define FILT_7SA 0x03 -+ -+/* bits for register 2, I2CRegChanMsk */ -+#define CONV_X 0x80 -+#define CONV_Y 0x40 -+#define CONV_Z1 0x20 -+#define CONV_Z2 0x10 -+#define CONV_AUX 0x08 -+#define CONV_RX 0x04 -+#define CONV_RY 0x02 -+ -+/* power delay: lower nibble of CTRL0 register */ -+#define POWDLY_IMMEDIATE 0x00 -+#define POWDLY_1_1US 0x01 -+#define POWDLY_2_2US 0x02 -+#define POWDLY_4_4US 0x03 -+#define POWDLY_8_9US 0x04 -+#define POWDLY_17_8US 0x05 -+#define POWDLY_35_5US 0x06 -+#define POWDLY_71US 0x07 -+#define POWDLY_140US 0x08 -+#define POWDLY_280US 0x09 -+#define POWDLY_570US 0x0a -+#define POWDLY_1_1MS 0x0b -+#define POWDLY_2_3MS 0x0c -+#define POWDLY_4_6MS 0x0d -+#define POWDLY_9MS 0x0e -+#define POWDLY_18MS 0x0f -+ -+#define MAX_12BIT ((1 << 12) - 1) -+ -+/* when changing the channel mask, also change the read length appropriately */ -+#define CHAN_MASK (CONV_X | CONV_Y | CONV_Z1 | CONV_RX | CONV_RY) -+#define NUM_CHANNELS_SEQ 5 -+#define CHAN_READ_LENGTH (NUM_CHANNELS_SEQ * 2) -+ -+#define SX_MULTITOUCH 0x01 -+#define SX_PROXIMITY_SENSING 0x02 -+#define SX_HAPTICS_GENERIC 0x04 -+#define SX_HAPTICS_IMMERSION 0x08 -+#define SX_EXTENDED_REGS (SX_PROXIMITY_SENSING | SX_HAPTICS_GENERIC | SX_HAPTICS_IMMERSION) -+ -+#define SX865X_UP_SCANTIME_MS (100) -+#define SX865X_DOWN_SCANTIME_MS (20) -+ -+struct ts_event { -+ u16 x, y; -+ u16 z1; -+ u16 rx, ry; -+}; -+ -+struct sx865x { -+ struct input_dev *input; -+ struct ts_event tc; -+ -+ struct i2c_client *client; -+ -+ u32 invert_x; -+ u32 invert_y; -+ u32 swap_xy; -+ u32 gpio_pendown; -+ u32 gpio_reset; -+ -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+ int irq_bank; -+#endif -+ unsigned pendown; -+ int irq; -+}; -+ -+static struct i2c_device_id sx865x_idtable[] = { -+ { "sx8650", 0 }, -+ { } -+}; -+ -+MODULE_DEVICE_TABLE(i2c, sx865x_idtable); -+ -+static const struct of_device_id sx865x_of_match[] = { -+ { .compatible = "semtech,sx8650", .data = (void *)0 }, -+ {} -+}; -+ -+MODULE_DEVICE_TABLE(of, sx865x_of_match); -+ -+static void sx865x_send_event(struct sx865x *ts) -+{ -+ u32 rt; -+ u16 x, y, z1; -+ -+ x = ts->tc.x; -+ y = ts->tc.y; -+ z1 = ts->tc.z1; -+ -+ /* range filtering */ -+ if (y == MAX_12BIT) -+ y = 0; -+ -+ /* compute touch pressure resistance */ -+ if (likely(y && z1)) -+ rt = z1; -+ else -+ rt = 0; -+ -+ /* Sample found inconsistent by debouncing or pressure is beyond -+ * the maximum. Don't report it to user space, repeat at least -+ * once more the measurement -+ */ -+ if (rt > MAX_12BIT) { -+ dev_dbg(&ts->client->dev, "ignored pressure %d\n", rt); -+ return; -+ } -+ -+ /* NOTE: We can't rely on the pressure to determine the pen down -+ * state, even this controller has a pressure sensor. The pressure -+ * value can fluctuate for quite a while after lifting the pen and -+ * in some cases may not even settle at the expected value. -+ * -+ * The only safe way to check for the pen up condition is in the -+ * timer by reading the pen signal state (it's a GPIO _and_ IRQ). -+ */ -+ if (rt) { -+ struct input_dev *input = ts->input; -+ -+ if (ts->invert_x) x = (~x) & MAX_12BIT; -+ -+ if (ts->invert_y) y = (~y) & MAX_12BIT; -+ -+ if (ts->swap_xy) swap(x, y); -+ -+ if (!ts->pendown) { -+ dev_dbg(&ts->client->dev, "DOWN\n"); -+ ts->pendown = 1; -+ input_report_key(input, BTN_TOUCH, 1); -+ } -+ -+ input_report_abs(input, ABS_X, x); -+ input_report_abs(input, ABS_Y, y); -+ input_report_abs(input, ABS_PRESSURE, rt); -+ input_sync(input); -+ -+ dev_dbg(&ts->client->dev, "point(%4d,%4d), pressure (%4u)\n", -+ x, y, rt); -+ } -+} -+ -+static int sx865x_read_values(struct sx865x *ts) -+{ -+ s32 data; -+ u16 vals[NUM_CHANNELS_SEQ+1]; /* +1 for last dummy read */ -+ int length; -+ int i; -+ -+ memset(&(ts->tc), 0, sizeof(ts->tc)); -+ /* The protocol and raw data format from i2c interface: -+ * S Addr R A [DataLow] A [DataHigh] A (repeat) NA P -+ * Where DataLow has (channel | [D11-D8]), DataHigh has [D7-D0]. -+ */ -+ length = i2c_master_recv(ts->client, (char *)vals, CHAN_READ_LENGTH); -+ -+ if (likely(length == CHAN_READ_LENGTH)) { -+ length >>= 1; -+ for (i = 0; i < length; i++) { -+ u16 ch; -+ data = swab16(vals[i]); -+ if (unlikely(data & 0x8000)) { -+ dev_dbg(&ts->client->dev, -+ "hibit @ %d [0x%04x]\n", i, data); -+ continue; -+ } -+ ch = data >> 12; -+ if (ch == CH_X) { -+ ts->tc.x = data & 0xfff; -+ } else if (ch == CH_Y) { -+ ts->tc.y = data & 0xfff; -+ } else if (ch == CH_Z1) { -+ ts->tc.z1 = data & 0xfff; -+ } else if (ch == CH_RX) { -+ ts->tc.rx = data & 0xfff; -+ } else if (ch == CH_RY) { -+ ts->tc.ry = data & 0xfff; -+ } else { -+ dev_err(&ts->client->dev, "? CH%d %x\n", -+ ch, data & 0xfff); -+ } -+ } -+ } else { -+ dev_err(&ts->client->dev, "%d = recv()\n", length); -+ } -+ -+ dev_dbg(&ts->client->dev, "X:%03x Y:%03x Z1:%03x RX:%03x RY:%03x\n", -+ ts->tc.x, ts->tc.y, ts->tc.z1, ts->tc.rx, ts->tc.ry); -+ -+ return !ts->tc.z1; /* return 0 only if pressure not 0 */ -+} -+ -+static void sx865x_pen_up(struct sx865x *ts) -+{ -+ struct input_dev *input = ts->input; -+ -+ /* This timer expires after PENIRQs havent been coming in for some time. -+ * It means that the pen is now UP. */ -+ input_report_key(input, BTN_TOUCH, 0); -+ input_report_abs(input, ABS_PRESSURE, 0); -+ input_sync(input); -+ -+ ts->pendown = 0; -+ dev_dbg(&ts->client->dev, "UP\n"); -+} -+ -+static int sx865x_data_available(struct sx865x *ts) -+{ -+ u8 status; -+ -+ status = i2c_smbus_read_byte_data(ts->client, -+ (SX865X_READ_REGISTER | I2C_REG_STAT)); -+ return status & STATUS_CONVIRQ; -+} -+ -+static int get_pendown_status(struct sx865x *ts) -+{ -+ return gpio_get_value(ts->gpio_pendown) ? 0 : 1; -+} -+ -+static irqreturn_t sx865x_hw_irq(int irq, void *handle) -+{ -+ struct sx865x *ts = handle; -+ -+ return get_pendown_status(ts) ? IRQ_WAKE_THREAD : IRQ_HANDLED; -+} -+ -+static irqreturn_t sx865x_irq(int irq, void *handle) -+{ -+ struct sx865x *ts = handle; -+ -+ while (sx865x_data_available(ts)) { -+ /* valid data was read in */ -+ if (likely(sx865x_read_values(ts) == 0)) -+ sx865x_send_event(ts); -+ else -+ dev_dbg(&ts->client->dev, "data error!\n"); -+ -+ msleep(SX865X_DOWN_SCANTIME_MS); -+ } -+ -+ if (ts->pendown) -+ sx865x_pen_up(ts); -+ -+ return IRQ_HANDLED; -+} -+ -+static void sx865x_hw_reset(struct sx865x *ts) -+{ -+ gpio_direction_output(ts->gpio_reset, 0); -+ udelay(1000); -+ gpio_direction_output(ts->gpio_reset, 1); -+ udelay(1000); -+} -+ -+static int sx865x_dt_probe(struct i2c_client *client, struct sx865x *ts) -+{ -+ struct device_node *node = client->dev.of_node; -+ const struct of_device_id *match; -+ -+ if (!node) { -+ dev_err(&client->dev, -+ "Device dost not have associated DT data\n"); -+ return -EINVAL; -+ } -+ -+ match = of_match_device(sx865x_of_match, &client->dev); -+ if (!match) { -+ dev_err(&client->dev, -+ "Unknown device model\n"); -+ return -EINVAL; -+ } -+ -+ of_property_read_u32(node, "swap-xy", &ts->swap_xy); -+ of_property_read_u32(node, "invert-x", &ts->invert_x); -+ of_property_read_u32(node, "invert-y", &ts->invert_y); -+ -+ ts->gpio_pendown = of_get_named_gpio(node, "gpio-pendown", 0); -+ ts->gpio_reset = of_get_named_gpio(node, "gpio-reset", 0); -+ -+ if (gpio_request(ts->gpio_pendown, "ts-pendown")) -+ dev_err(&client->dev, -+ "gpio request fail (%d)!\n", ts->gpio_pendown); -+ else -+ gpio_direction_input(ts->gpio_pendown); -+ -+ if (gpio_request(ts->gpio_reset, "ts-reset")) -+ dev_err(&client->dev, -+ "gpio request fail (%d)!\n", ts->gpio_reset); -+ else -+ sx865x_hw_reset(ts); -+ -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+ /* irq setup */ -+ ts->irq_bank = meson_fix_irqbank(ts->irq_bank); -+ if (ts->irq_bank < 0) { -+ dev_err(&client->dev, -+ "Could not find irq bank!\n"); -+ return -EINVAL; -+ } -+ -+ { -+ int ret; -+ /* AMLogic gpio irq setup */ -+ ret = gpio_for_irq(ts->gpio_pendown, -+ AML_GPIO_IRQ(ts->irq_bank, FILTER_NUM7, GPIO_IRQ_FALLING)); -+ -+ if (ret) { -+ dev_err(&client->dev, -+ "AML_GPIO_IRQ setup fail!\n"); -+ return -EINVAL; -+ } -+ /* Amlogic gpio based irq setup */ -+ ts->irq = AMLGPIO_IRQ_BASE + ts->irq_bank; -+ } -+#else -+ ts->irq = gpio_to_irq(ts->gpio_pendown); -+ if (ts->irq < 0) -+ return -EINVAL; -+#endif -+ -+ /* platform data info display */ -+ dev_info(&client->dev, "swap_xy (%d)\n", ts->swap_xy); -+ dev_info(&client->dev, "invert_x (%d)\n", ts->invert_x); -+ dev_info(&client->dev, "invert_y (%d)\n", ts->invert_y); -+ dev_info(&client->dev, "gpio pendown (%d)\n", ts->gpio_pendown); -+ dev_info(&client->dev, "gpio reset (%d)\n", ts->gpio_reset); -+ dev_info(&client->dev, "gpio irq (%d)\n", ts->irq); -+ -+ return 0; -+} -+ -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+static void sx865x_irq_free(struct i2c_client *client, struct sx865x *ts) -+{ -+ int irq_banks[2]; -+ -+ meson_free_irq(gpio_to_irq(ts->gpio_pendown), &irq_banks[0]); -+ -+ /* rising irq bank */ -+ if (irq_banks[0] != -1) -+ free_irq(irq_banks[0] + AMLGPIO_IRQ_BASE, ts); -+ -+ /* falling irq bank */ -+ if (irq_banks[1] != -1) -+ free_irq(irq_banks[1] + AMLGPIO_IRQ_BASE, ts); -+} -+#endif -+ -+static int sx865x_probe(struct i2c_client *client, -+ const struct i2c_device_id *id) -+{ -+ struct sx865x *ts; -+ struct input_dev *input_dev; -+ int err = 0; -+ -+ dev_info(&client->dev, "sx865x_probe()\n"); -+ -+ if (!i2c_check_functionality(client->adapter, -+ I2C_FUNC_SMBUS_READ_WORD_DATA)) -+ return -EIO; -+ -+ ts = devm_kzalloc(&client->dev, sizeof(struct sx865x), GFP_KERNEL); -+ input_dev = devm_input_allocate_device(&client->dev); -+ if (!ts || !input_dev) -+ return -ENOMEM; -+ -+ if (sx865x_dt_probe(client, ts) != 0) -+ return -EIO; -+ -+ i2c_set_clientdata(client, ts); -+ -+ input_dev->name = "SX865X Touchscreen"; -+ input_dev->id.bustype = BUS_I2C; -+ input_dev->dev.parent = &client->dev; -+ input_set_drvdata(input_dev, ts); -+ -+ input_dev->evbit[0] = BIT_MASK(EV_KEY) | BIT_MASK(EV_ABS); -+ input_dev->keybit[BIT_WORD(BTN_TOUCH)] = BIT_MASK(BTN_TOUCH); -+ -+ input_set_abs_params(input_dev, ABS_X, 0, MAX_12BIT, 0, 0); -+ input_set_abs_params(input_dev, ABS_Y, 0, MAX_12BIT, 0, 0); -+ input_set_abs_params(input_dev, ABS_PRESSURE, 0, MAX_12BIT, 0, 0); -+ -+ /* soft reset: SX8650 fails to nak at the end, ignore return value */ -+ i2c_smbus_write_byte_data(client, I2C_REG_SOFTRESET, SOFTRESET_VALUE); -+ -+ /* set mask to convert X, Y, Z1, RX, RY for CH_SEQ */ -+ err = i2c_smbus_write_byte_data(client, I2C_REG_CHANMASK, CHAN_MASK); -+ if (err != 0) return -EIO; -+ -+ err = i2c_smbus_write_byte_data(client, I2C_REG_CTRL1, -+ CONDIRQ | FILT_7SA); -+ if (err != 0) return -EIO; -+ -+ /* set POWDLY settling time -- adjust TS_TIMEOUT accordingly */ -+ err = i2c_smbus_write_byte_data(client, I2C_REG_CTRL0, POWDLY_1_1MS); -+ if (err != 0) return -EIO; -+ -+ /* enter pen-trigger mode */ -+ err = i2c_smbus_write_byte(client, SX865X_PENTRG); -+ if (err != 0) return -EIO; -+ -+ err = request_threaded_irq(ts->irq, sx865x_hw_irq, sx865x_irq, -+ IRQF_ONESHOT, -+ client->dev.driver->name, ts); -+ -+ if (err < 0) { -+ dev_err(&client->dev, "irq %d busy?\n", ts->irq); -+ return -EIO; -+ } -+ -+ err = input_register_device(input_dev); -+ if (err) -+ goto err_free_irq; -+ -+ ts->client = client; -+ ts->input = input_dev; -+ -+ dev_info(&client->dev, "probe ok! registered with irq (%d)\n", ts->irq); -+ -+ return 0; -+ -+err_free_irq: -+ if (ts->gpio_pendown) -+ gpio_free(ts->gpio_pendown); -+ if (ts->gpio_reset) -+ gpio_free(ts->gpio_reset); -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+ sx865x_irq_free(client, ts); -+#else -+ if (ts->irq) -+ free_irq(ts->irq, ts); -+#endif -+ return err; -+} -+ -+static int sx865x_remove(struct i2c_client *client) -+{ -+ struct sx865x *ts = i2c_get_clientdata(client); -+ struct sx865x_platform_data *pdata; -+ -+ pdata = client->dev.platform_data; -+ -+ if (ts->gpio_pendown) -+ gpio_free(ts->gpio_pendown); -+ if (ts->gpio_reset) -+ gpio_free(ts->gpio_reset); -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+ sx865x_irq_free(client, ts); -+#else -+ if (ts->irq) -+ free_irq(ts->irq, ts); -+#endif -+ input_unregister_device(ts->input); -+ -+ return 0; -+} -+ -+static struct i2c_driver sx865x_driver = { -+ .driver = { -+ .owner = THIS_MODULE, -+ .name = "sx865x", -+ .of_match_table = of_match_ptr(sx865x_of_match), -+ }, -+ .id_table = sx865x_idtable, -+ .probe = sx865x_probe, -+ .remove = sx865x_remove, -+}; -+ -+module_i2c_driver(sx865x_driver); -+ -+MODULE_AUTHOR("Pierluigi Passaro "); -+MODULE_DESCRIPTION("SX865X TouchScreen Driver"); -+MODULE_LICENSE("GPL"); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/073_linux-4.18.y-drm-fb_helper-ump-ioctls.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/073_linux-4.18.y-drm-fb_helper-ump-ioctls.patch deleted file mode 100644 index b4cd89375..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/073_linux-4.18.y-drm-fb_helper-ump-ioctls.patch +++ /dev/null @@ -1,151 +0,0 @@ -diff --git a/drivers/gpu/drm/drm_fb_helper.c b/drivers/gpu/drm/drm_fb_helper.c -index cab14f25..cafc60ea 100644 ---- a/drivers/gpu/drm/drm_fb_helper.c -+++ b/drivers/gpu/drm/drm_fb_helper.c -@@ -1544,6 +1544,14 @@ int drm_fb_helper_ioctl(struct fb_info *info, unsigned int cmd, - - ret = 0; - goto unlock; -+#if defined(CONFIG_UMP) -+ case GET_UMP_SECURE_ID_BUF1: -+ ret = drm_get_ump_secure_id(info, fb_helper, arg, 0); -+ goto unlock; -+ case GET_UMP_SECURE_ID_BUF2: -+ ret = drm_get_ump_secure_id(info, fb_helper, arg, 1); -+ goto unlock; -+#endif - default: - ret = -ENOTTY; - } -diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile -index 69c13517..55673ac6 100644 ---- a/drivers/gpu/drm/Makefile -+++ b/drivers/gpu/drm/Makefile -@@ -44,6 +44,7 @@ drm_kms_helper-$(CONFIG_DRM_DP_AUX_CHARDEV) += drm_dp_aux_dev.o - - obj-$(CONFIG_DRM_KMS_HELPER) += drm_kms_helper.o - obj-$(CONFIG_DRM_DEBUG_SELFTEST) += selftests/ -+obj-$(CONFIG_UMP) += drm_fb_ump.o - - obj-$(CONFIG_DRM) += drm.o - obj-$(CONFIG_DRM_MIPI_DSI) += drm_mipi_dsi.o -diff --git a/include/drm/drm_fb_helper.h b/include/drm/drm_fb_helper.h -index b069433e..95657b76 100644 ---- a/include/drm/drm_fb_helper.h -+++ b/include/drm/drm_fb_helper.h -@@ -36,6 +36,10 @@ struct drm_fb_helper; - #include - #include - -+#if defined(CONFIG_UMP) -+#include -+#endif -+ - enum mode_set_atomic { - LEAVE_ATOMIC_MODE_SET, - ENTER_ATOMIC_MODE_SET, -@@ -131,6 +135,8 @@ struct drm_fb_helper_connector { - struct drm_connector *connector; - }; - -+#define DRM_FB_UMP_COUNT 1 /* only enable one FB UMP layer */ -+ - /** - * struct drm_fb_helper - main structure to emulate fbdev on top of KMS - * @fb: Scanout framebuffer object -@@ -232,6 +238,9 @@ struct drm_fb_helper { - * See also: @deferred_setup - */ - int preferred_bpp; -+#if defined(CONFIG_UMP) -+ ump_dd_handle ump_wrapped_buffer[DRM_FB_UMP_COUNT][2]; -+#endif - }; - - /** -@@ -577,4 +586,11 @@ drm_fb_helper_remove_conflicting_framebuffers(struct apertures_struct *a, - #endif - } - -+#if defined(CONFIG_UMP) -+extern int (*drm_get_ump_secure_id) (struct fb_info *info, -+ struct drm_fb_helper *g_fbi, unsigned long arg, int buf); -+#define GET_UMP_SECURE_ID_BUF1 _IOWR('m', 311, unsigned int) -+#define GET_UMP_SECURE_ID_BUF2 _IOWR('m', 312, unsigned int) -+#endif -+ - #endif ---- /dev/null 2018-07-12 16:39:19.544000000 +0200 -+++ b/drivers/gpu/drm/drm_fb_ump.c 2018-07-22 22:20:45.166145058 +0200 -@@ -0,0 +1,71 @@ -+/* -+ * Copyright (C) 2016 Hardkernel Co. Ltd. -+ * -+ * 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, write to the Free Software -+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, -+ * MA 02111-1307 USA -+ */ -+ -+#include -+ -+#include -+#include -+#include -+#include -+#include -+ -+int (*drm_get_ump_secure_id) (struct fb_info *info, -+ struct drm_fb_helper *g_fbi, unsigned long arg, int buf); -+EXPORT_SYMBOL(drm_get_ump_secure_id); -+ -+static int _drm_get_ump_secure_id(struct fb_info *info, -+ struct drm_fb_helper *g_fbi, unsigned long arg, int buf) -+{ -+ u32 __user *psecureid = (u32 __user *) arg; -+ ump_secure_id secure_id; -+ -+ if (!g_fbi->ump_wrapped_buffer[info->node][buf]) { -+ ump_dd_physical_block ump_memory_description; -+ printk("ump: create disp: %d\n", buf); -+ -+ ump_memory_description.addr = info->fix.smem_start; -+ ump_memory_description.size = info->fix.smem_len; -+ g_fbi->ump_wrapped_buffer[info->node][buf] = -+ ump_dd_handle_create_from_phys_blocks( -+ &ump_memory_description, 1); -+ } -+ secure_id = ump_dd_secure_id_get( -+ g_fbi->ump_wrapped_buffer[info->node][buf]); -+ -+ return put_user((unsigned int)secure_id, psecureid); -+} -+ -+static int __init drm_ump_module_init(void) -+{ -+ int ret = 0; -+ drm_get_ump_secure_id = _drm_get_ump_secure_id; -+ return ret; -+} -+ -+static void __exit drm_ump_module_exit(void) -+{ -+ drm_get_ump_secure_id = NULL; -+} -+ -+module_init(drm_ump_module_init); -+module_exit(drm_ump_module_exit); -+ -+MODULE_AUTHOR("Mauro Ribeiro "); -+MODULE_DESCRIPTION("UMP Glue for DRM Framebuffer"); -+MODULE_LICENSE("GPL"); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/074_odroidc2-enable-scpi-dvfs.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/074_odroidc2-enable-scpi-dvfs.patch deleted file mode 100644 index dbe1e637f..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/074_odroidc2-enable-scpi-dvfs.patch +++ /dev/null @@ -1,14 +0,0 @@ -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -index d147c853a..dbde670ba 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -@@ -246,7 +246,8 @@ - }; - - &scpi_clocks { -- status = "disabled"; -+ /* Works only with new blobs that have limited DVFS table */ -+ status = "okay"; - }; - - /* SD */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/075_odroidc2-enable-scpi-cpu-thermal.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/075_odroidc2-enable-scpi-cpu-thermal.patch deleted file mode 100644 index e05b711aa..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/075_odroidc2-enable-scpi-cpu-thermal.patch +++ /dev/null @@ -1,63 +0,0 @@ ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-04-29 05:46:55.636313674 +0200 -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-04-29 00:07:14.412005049 +0200 -@@ -46,6 +46,7 @@ - - #include "meson-gxbb.dtsi" - #include -+#include - - / { - compatible = "hardkernel,odroid-c2", "amlogic,meson-gxbb"; -@@ -117,6 +118,41 @@ - 1800000 1>; - }; - -+ 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>; -+ hysteresis = <2000>; -+ type = "passive"; -+ }; -+ cpu_alert1: cpu-alert1 { -+ temperature = <85000>; -+ hysteresis = <2000>; -+ type = "passive"; -+ }; -+ cpu_crit: cpu_crit { -+ temperature = <95000>; -+ hysteresis = <2000>; -+ type = "critical"; -+ }; -+ }; -+ -+ cooling-maps { -+ map0 { -+ trip = <&cpu_alert1>; -+ cooling-device = -+ <&cpu0 THERMAL_NO_LIMIT THERMAL_NO_LIMIT>; -+ }; -+ }; -+ }; -+ }; -+ - vcc1v8: regulator-vcc1v8 { - compatible = "regulator-fixed"; - regulator-name = "VCC1V8"; -@@ -192,6 +228,10 @@ - status = "okay"; - }; - -+&cpu0 { -+ #cooling-cells = <2>; -+}; -+ - ðmac { - status = "okay"; - pinctrl-0 = <ð_rgmii_pins>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/000_linux-4.14.y-le-amlogic-gx-0000-net-before.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/000_linux-4.14.y-le-amlogic-gx-0000-net-before.patch deleted file mode 100644 index 5e07a33bc..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/000_linux-4.14.y-le-amlogic-gx-0000-net-before.patch +++ /dev/null @@ -1,19 +0,0 @@ - ---- b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c 2018-04-12 01:40:29.029325568 +0200 -+++ a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c 2018-04-14 01:12:07.301469106 +0200 -@@ -364,15 +364,9 @@ - bool stmmac_eee_init(struct stmmac_priv *priv) - { - struct net_device *ndev = priv->dev; -- int interface = priv->plat->interface; - unsigned long flags; - bool ret = false; - -- if ((interface != PHY_INTERFACE_MODE_MII) && -- (interface != PHY_INTERFACE_MODE_GMII) && -- !phy_interface_mode_is_rgmii(interface)) -- goto out; -- - /* Using PCS we cannot dial with the phy registers at this stage - * so we do not support extra feature like EEE. - */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/001_linux-4.14.y-le-amlogic-gx-0002-arm64-dts-meson-gxbb-allow_child_devices_on_the_usb.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/001_linux-4.14.y-le-amlogic-gx-0002-arm64-dts-meson-gxbb-allow_child_devices_on_the_usb.patch deleted file mode 100644 index d46bc071b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/001_linux-4.14.y-le-amlogic-gx-0002-arm64-dts-meson-gxbb-allow_child_devices_on_the_usb.patch +++ /dev/null @@ -1,38 +0,0 @@ -From 9724ee442cf7bf4da885433b28029ac559f1f26a Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Thu, 12 Jan 2017 01:38:26 +0100 -Subject: [PATCH] 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 af834cdbba791..7d38d55869c94 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>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/002_linux-4.14.y-le-amlogic-gx-0003-arm64-dts-meson-gxbb-odroidc2-take_usb_hub_out_of_reset.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/002_linux-4.14.y-le-amlogic-gx-0003-arm64-dts-meson-gxbb-odroidc2-take_usb_hub_out_of_reset.patch deleted file mode 100644 index 233b4840f..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/002_linux-4.14.y-le-amlogic-gx-0003-arm64-dts-meson-gxbb-odroidc2-take_usb_hub_out_of_reset.patch +++ /dev/null @@ -1,30 +0,0 @@ -From 53d19221222d8fe49aae75721a9547c7d104e9ed Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Thu, 12 Jan 2017 01:39:20 +0100 -Subject: [PATCH] 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 1ffa1c238a725..b035c728a4821 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>; -+ }; - }; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/003_linux-4.14.y-le-amlogic-gx-0004-phy-meson-add_usb3_phy_support_for_meson_gxl.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/003_linux-4.14.y-le-amlogic-gx-0004-phy-meson-add_usb3_phy_support_for_meson_gxl.patch deleted file mode 100644 index 5cbaa9478..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/003_linux-4.14.y-le-amlogic-gx-0004-phy-meson-add_usb3_phy_support_for_meson_gxl.patch +++ /dev/null @@ -1,257 +0,0 @@ -From 1b68976e2e05b3e10e4f3070ef5b9e08640ad7a0 Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Sat, 26 Nov 2016 15:56:32 +0100 -Subject: [PATCH] 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 cb8f4501652b1..5d11a3e698d4a 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 cfdc98715c30a..4fd8848c194d6 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 0000000000000..9af5222fe754f ---- /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"); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/004_linux-4.14.y-le-amlogic-gx-0005-usb-host-add_a_generic_platform_usb_roothub_driver.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/004_linux-4.14.y-le-amlogic-gx-0005-usb-host-add_a_generic_platform_usb_roothub_driver.patch deleted file mode 100644 index 812471960..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/004_linux-4.14.y-le-amlogic-gx-0005-usb-host-add_a_generic_platform_usb_roothub_driver.patch +++ /dev/null @@ -1,290 +0,0 @@ -From 0e1b7fc3afdff8b63a2ed34ae6222cc02b043d62 Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Tue, 10 Jan 2017 18:59:43 +0100 -Subject: [PATCH] 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 -enabled to make the USB controller actually work. They also have to be -disabled again on shutdown/suspend. - -Currently (at least) the following HCI platform drivers are using custom -code to obtain all PHYs via devicetree for the roothub/controller and -disable/enable them when required: -- ehci-platform.c has ehci_platform_power_{on,off} -- xhci-mtk.c has xhci_mtk_phy_{init,exit,power_on,power_off} -- ohci-platform.c has ohci_platform_power_{on,off} - -These drivers are not using the generic devicetree USB device bindings -yet which were only introduced recently (documentation is available in -devicetree/bindings/usb/usb-device.txt). -With this new driver the usb2-phy and usb3-phy can be specified directly -in the child-node of the corresponding port of the roothub via -devicetree. This can be extended by not just parsing PHYs (some of the -other drivers listed above are for example also parsing a list of clocks -as well) when required. - -Signed-off-by: Martin Blumenstingl -Signed-off-by: Neil Armstrong ---- - .../devicetree/bindings/usb/usb-roothub.txt | 46 +++++++ - drivers/usb/host/Kconfig | 3 + - drivers/usb/host/Makefile | 2 + - drivers/usb/host/platform-roothub.c | 146 +++++++++++++++++++++ - drivers/usb/host/platform-roothub.h | 14 ++ - 5 files changed, 211 insertions(+) - create mode 100644 Documentation/devicetree/bindings/usb/usb-roothub.txt - create mode 100644 drivers/usb/host/platform-roothub.c - create mode 100644 drivers/usb/host/platform-roothub.h - -diff --git a/Documentation/devicetree/bindings/usb/usb-roothub.txt b/Documentation/devicetree/bindings/usb/usb-roothub.txt -new file mode 100644 -index 0000000000000..23b24b68d74df ---- /dev/null -+++ b/Documentation/devicetree/bindings/usb/usb-roothub.txt -@@ -0,0 +1,46 @@ -+Generic USB root-hub Properties -+ -+similar to the USB device bindings (documented in usb-device.txt from the -+current directory) this provides support for configuring the root-hub. -+ -+Required properties: -+- compatible: should be at least one of "usb1d6b,3", "usb1d6b,2" -+- reg: must be 0. -+- address-cells: must be 1 -+- size-cells: must be 0 -+ -+Required sub-nodes: -+a sub-node per actual USB port is required. each sub-node supports the -+following properties: -+ Required properties: -+ - reg: the port number on the root-hub (mandatory) -+ Optional properties: -+ - phys: optional, from the *Generic PHY* bindings (mandatory needed -+ when phy-names is given) -+ - phy-names: optional, from the *Generic PHY* bindings; supported names -+ are "usb2-phy" or "usb3-phy" -+ -+Example: -+ &usb1 { -+ #address-cells = <1>; -+ #size-cells = <0>; -+ -+ roothub@0 { -+ compatible = "usb1d6b,3", "usb1d6b,2"; -+ #address-cells = <1>; -+ #size-cells = <0>; -+ reg = <0>; -+ -+ port@1 { -+ reg = <1>; -+ usb-phy = <&usb2_phy1>, <&usb3_phy1>; -+ phy-names = "usb2-phy", "usb3-phy"; -+ }; -+ -+ port@2 { -+ reg = <2>; -+ usb-phy = <&usb2_phy2>, <&usb3_phy2>; -+ phy-names = "usb2-phy", "usb3-phy"; -+ }; -+ }; -+ } -diff --git a/drivers/usb/host/Kconfig b/drivers/usb/host/Kconfig -index fa5692dec8320..b8b05c786b2a2 100644 ---- a/drivers/usb/host/Kconfig -+++ b/drivers/usb/host/Kconfig -@@ -805,6 +805,9 @@ config USB_HCD_SSB - - If unsure, say N. - -+config USB_PLATFORM_ROOTHUB -+ bool -+ - config USB_HCD_TEST_MODE - bool "HCD test mode support" - ---help--- -diff --git a/drivers/usb/host/Makefile b/drivers/usb/host/Makefile -index 4ab2689c8952b..873ebd9250d3b 100644 ---- a/drivers/usb/host/Makefile -+++ b/drivers/usb/host/Makefile -@@ -30,6 +30,8 @@ obj-$(CONFIG_USB_WHCI_HCD) += whci/ - - obj-$(CONFIG_USB_PCI) += pci-quirks.o - -+obj-$(CONFIG_USB_PLATFORM_ROOTHUB) += platform-roothub.o -+ - obj-$(CONFIG_USB_EHCI_HCD) += ehci-hcd.o - obj-$(CONFIG_USB_EHCI_PCI) += ehci-pci.o - obj-$(CONFIG_USB_EHCI_HCD_PLATFORM) += ehci-platform.o -diff --git a/drivers/usb/host/platform-roothub.c b/drivers/usb/host/platform-roothub.c -new file mode 100644 -index 0000000000000..84837e42b0063 ---- /dev/null -+++ b/drivers/usb/host/platform-roothub.c -@@ -0,0 +1,146 @@ -+/* -+ * platform roothub driver - a virtual PHY device which passes all phy_* -+ * function calls to multiple (actual) PHY devices. This is comes handy when -+ * initializing all PHYs on a root-hub (to keep them all in the same state). -+ * -+ * Copyright (C) 2017 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 "platform-roothub.h" -+ -+#define ROOTHUB_PORTNUM 0 -+ -+struct platform_roothub { -+ struct phy *phy; -+ struct list_head list; -+}; -+ -+static struct platform_roothub *platform_roothub_alloc(struct device *dev) -+{ -+ struct platform_roothub *roothub_entry; -+ -+ roothub_entry = devm_kzalloc(dev, sizeof(*roothub_entry), GFP_KERNEL); -+ if (!roothub_entry) -+ return ERR_PTR(-ENOMEM); -+ -+ INIT_LIST_HEAD(&roothub_entry->list); -+ -+ return roothub_entry; -+} -+ -+static int platform_roothub_add_phy(struct device *dev, -+ struct device_node *port_np, -+ const char *con_id, struct list_head *list) -+{ -+ struct platform_roothub *roothub_entry; -+ struct phy *phy = devm_of_phy_get(dev, port_np, con_id); -+ -+ if (IS_ERR_OR_NULL(phy)) { -+ if (!phy || PTR_ERR(phy) == -ENODEV) -+ return 0; -+ else -+ return PTR_ERR(phy); -+ } -+ -+ roothub_entry = platform_roothub_alloc(dev); -+ if (IS_ERR(roothub_entry)) -+ return PTR_ERR(roothub_entry); -+ -+ roothub_entry->phy = phy; -+ -+ list_add_tail(&roothub_entry->list, list); -+ -+ return 0; -+} -+ -+struct platform_roothub *platform_roothub_init(struct device *dev) -+{ -+ struct device_node *roothub_np, *port_np; -+ struct platform_roothub *plat_roothub; -+ int err; -+ -+ roothub_np = usb_of_get_child_node(dev->of_node, ROOTHUB_PORTNUM); -+ if (!of_device_is_available(roothub_np)) -+ return NULL; -+ -+ plat_roothub = platform_roothub_alloc(dev); -+ if (IS_ERR(plat_roothub)) -+ return plat_roothub; -+ -+ for_each_available_child_of_node(roothub_np, port_np) { -+ err = platform_roothub_add_phy(dev, port_np, "usb2-phy", -+ &plat_roothub->list); -+ if (err) -+ return ERR_PTR(err); -+ -+ err = platform_roothub_add_phy(dev, port_np, "usb3-phy", -+ &plat_roothub->list); -+ if (err) -+ return ERR_PTR(err); -+ } -+ -+ return plat_roothub; -+} -+EXPORT_SYMBOL_GPL(platform_roothub_init); -+ -+int platform_roothub_power_on(struct platform_roothub *plat_roothub) -+{ -+ struct platform_roothub *roothub_entry; -+ struct list_head *head; -+ int err; -+ -+ if (!plat_roothub) -+ return 0; -+ -+ head = &plat_roothub->list; -+ -+ list_for_each_entry(roothub_entry, head, list) { -+ err = phy_init(roothub_entry->phy); -+ if (err) -+ goto err_out; -+ -+ err = phy_power_on(roothub_entry->phy); -+ if (err) { -+ phy_exit(roothub_entry->phy); -+ goto err_out; -+ } -+ } -+ -+ return 0; -+ -+err_out: -+ list_for_each_entry_continue_reverse(roothub_entry, head, list) { -+ phy_power_off(roothub_entry->phy); -+ phy_exit(roothub_entry->phy); -+ } -+ -+ return err; -+} -+EXPORT_SYMBOL_GPL(platform_roothub_power_on); -+ -+void platform_roothub_power_off(struct platform_roothub *plat_roothub) -+{ -+ struct platform_roothub *roothub_entry; -+ -+ if (!plat_roothub) -+ return; -+ -+ list_for_each_entry_reverse(roothub_entry, &plat_roothub->list, list) { -+ phy_power_off(roothub_entry->phy); -+ phy_exit(roothub_entry->phy); -+ } -+} -+EXPORT_SYMBOL_GPL(platform_roothub_power_off); -diff --git a/drivers/usb/host/platform-roothub.h b/drivers/usb/host/platform-roothub.h -new file mode 100644 -index 0000000000000..bde0bf299e3b5 ---- /dev/null -+++ b/drivers/usb/host/platform-roothub.h -@@ -0,0 +1,14 @@ -+#ifndef USB_HOST_PLATFORM_ROOTHUB_H -+#define USB_HOST_PLATFORM_ROOTHUB_H -+ -+struct phy; -+struct device_node; -+ -+struct platform_roothub; -+ -+struct platform_roothub *platform_roothub_init(struct device *dev); -+ -+int platform_roothub_power_on(struct platform_roothub *plat_roothub); -+void platform_roothub_power_off(struct platform_roothub *plat_roothub); -+ -+#endif /* USB_HOST_PLATFORM_ROOTHUB_H */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/005_linux-4.14.y-le-amlogic-gx-0014-clk-meson-gxbb-add_vpu_and_vapb_clockids.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/005_linux-4.14.y-le-amlogic-gx-0014-clk-meson-gxbb-add_vpu_and_vapb_clockids.patch deleted file mode 100644 index 29648b755..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/005_linux-4.14.y-le-amlogic-gx-0014-clk-meson-gxbb-add_vpu_and_vapb_clockids.patch +++ /dev/null @@ -1,52 +0,0 @@ -From 7a03fa7ed4d552f8e1397a18d9f0046f9c8a8076 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Mon, 16 Oct 2017 17:29:33 +0200 -Subject: [PATCH] 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 5b1d4b374d1c2..aee6fbba20043 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 8c92528aa48ad..8ba99a5e3fd34 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 */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/006_linux-4.14.y-le-amlogic-gx-0015-clk-meson-gxbb-add_vpu_and_vapb_clocks_data.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/006_linux-4.14.y-le-amlogic-gx-0015-clk-meson-gxbb-add_vpu_and_vapb_clocks_data.patch deleted file mode 100644 index 1154fee31..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/006_linux-4.14.y-le-amlogic-gx-0015-clk-meson-gxbb-add_vpu_and_vapb_clocks_data.patch +++ /dev/null @@ -1,354 +0,0 @@ -From 89e3cdb01f2bf01810474984fd2c676a88973ac5 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Fri, 13 Oct 2017 14:38:37 +0200 -Subject: [PATCH] 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 b2d1e8ed7152b..a71374464c92d 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[] = { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/007_linux-4.14.y-le-amlogic-gx-0018-reset-meson-add_level_reset_support_for_gx_soc_family.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/007_linux-4.14.y-le-amlogic-gx-0018-reset-meson-add_level_reset_support_for_gx_soc_family.patch deleted file mode 100644 index 84ef1fb45..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/007_linux-4.14.y-le-amlogic-gx-0018-reset-meson-add_level_reset_support_for_gx_soc_family.patch +++ /dev/null @@ -1,129 +0,0 @@ -From 434a32bab28ccf277229338b33849b24ace9cc35 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Fri, 13 Oct 2017 14:05:01 +0200 -Subject: [PATCH] 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 a8b915eb8b581..f3b9d6989267e 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); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/008_linux-4.14.y-le-amlogic-gx-0019-soc-amlogic-add_meson_gx_vpu_domains_driver.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/008_linux-4.14.y-le-amlogic-gx-0019-soc-amlogic-add_meson_gx_vpu_domains_driver.patch deleted file mode 100644 index b0d638834..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/008_linux-4.14.y-le-amlogic-gx-0019-soc-amlogic-add_meson_gx_vpu_domains_driver.patch +++ /dev/null @@ -1,283 +0,0 @@ -From 375dd688f29cc0e8da629b3896c86c7e263030ae Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Fri, 13 Oct 2017 17:05:00 +0200 -Subject: [PATCH] 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 22acf064531ff..c2c0513b18ff5 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 3e85fc462c213..3174e93e72e9c 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 0000000000000..bf5190b65ad9b ---- /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); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/009_linux-4.14.y-le-amlogic-gx-0020-soc-amlogic-meson-gx-pwrc-vpu-fix_power-off_when_powered.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/009_linux-4.14.y-le-amlogic-gx-0020-soc-amlogic-meson-gx-pwrc-vpu-fix_power-off_when_powered.patch deleted file mode 100644 index ac73f19b5..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/009_linux-4.14.y-le-amlogic-gx-0020-soc-amlogic-meson-gx-pwrc-vpu-fix_power-off_when_powered.patch +++ /dev/null @@ -1,102 +0,0 @@ -From 6747193c223e945901f42d7e7bc1d3ddea663585 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Fri, 3 Nov 2017 16:43:24 +0100 -Subject: [PATCH] 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 bf5190b65ad9b..2bdeebc48901d 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[] = { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/010_linux-4.14.y-le-amlogic-gx-0037-net-phy-meson-gxl-detect_lpa_corruption.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/010_linux-4.14.y-le-amlogic-gx-0037-net-phy-meson-gxl-detect_lpa_corruption.patch deleted file mode 100644 index f98fdef58..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/010_linux-4.14.y-le-amlogic-gx-0037-net-phy-meson-gxl-detect_lpa_corruption.patch +++ /dev/null @@ -1,128 +0,0 @@ -From b940b2533f1bb3718ed50f4dc9091f8494e6f37a Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Fri, 8 Dec 2017 12:08:11 +0100 -Subject: [PATCH] net: phy: meson-gxl: detect LPA corruption - -The purpose of this change is to fix the incorrect detection of the link -partner (LP) advertised capabilities which sometimes happens with this PHY -(roughly 1 time in a dozen) - -This issue may cause the link to be negotiated at 10Mbps/Full or -10Mbps/Half when 100MBps/Full is actually possible. In some case, the link -is even completely broken and no communication is possible. - -To detect the corruption, we must look for a magic undocumented bit in the -WOL bank (hint given by the SoC vendor kernel) but this is not enough to -cover all cases. We also have to look at the LPA ack. If the LP supports -Aneg but did not ack our base code when aneg is completed, we assume -something went wrong. - -The detection of a corrupted LPA triggers a restart of the aneg process. -This solves the problem but may take up to 6 retries to complete. - -Fixes: 7334b3e47aee ("net: phy: Add Meson GXL Internal PHY driver") -Signed-off-by: Jerome Brunet -Signed-off-by: David S. Miller ---- - drivers/net/phy/meson-gxl.c | 74 ++++++++++++++++++++++++++++++++++++++++++++- - 1 file changed, 73 insertions(+), 1 deletion(-) - -diff --git a/drivers/net/phy/meson-gxl.c b/drivers/net/phy/meson-gxl.c -index 1ea69b7585d9b..700007dd4be56 100644 ---- a/drivers/net/phy/meson-gxl.c -+++ b/drivers/net/phy/meson-gxl.c -@@ -22,6 +22,7 @@ - #include - #include - #include -+#include - - static int meson_gxl_config_init(struct phy_device *phydev) - { -@@ -50,6 +51,77 @@ static int meson_gxl_config_init(struct phy_device *phydev) - return 0; - } - -+/* This function is provided to cope with the possible failures of this phy -+ * during aneg process. When aneg fails, the PHY reports that aneg is done -+ * but the value found in MII_LPA is wrong: -+ * - Early failures: MII_LPA is just 0x0001. if MII_EXPANSION reports that -+ * the link partner (LP) supports aneg but the LP never acked our base -+ * code word, it is likely that we never sent it to begin with. -+ * - Late failures: MII_LPA is filled with a value which seems to make sense -+ * but it actually is not what the LP is advertising. It seems that we -+ * can detect this using a magic bit in the WOL bank (reg 12 - bit 12). -+ * If this particular bit is not set when aneg is reported being done, -+ * it means MII_LPA is likely to be wrong. -+ * -+ * In both case, forcing a restart of the aneg process solve the problem. -+ * When this failure happens, the first retry is usually successful but, -+ * in some cases, it may take up to 6 retries to get a decent result -+ */ -+int meson_gxl_read_status(struct phy_device *phydev) -+{ -+ int ret, wol, lpa, exp; -+ -+ if (phydev->autoneg == AUTONEG_ENABLE) { -+ ret = genphy_aneg_done(phydev); -+ if (ret < 0) -+ return ret; -+ else if (!ret) -+ goto read_status_continue; -+ -+ /* Need to access WOL bank, make sure the access is open */ -+ ret = phy_write(phydev, 0x14, 0x0000); -+ if (ret) -+ return ret; -+ ret = phy_write(phydev, 0x14, 0x0400); -+ if (ret) -+ return ret; -+ ret = phy_write(phydev, 0x14, 0x0000); -+ if (ret) -+ return ret; -+ ret = phy_write(phydev, 0x14, 0x0400); -+ if (ret) -+ return ret; -+ -+ /* Request LPI_STATUS WOL register */ -+ ret = phy_write(phydev, 0x14, 0x8D80); -+ if (ret) -+ return ret; -+ -+ /* Read LPI_STATUS value */ -+ wol = phy_read(phydev, 0x15); -+ if (wol < 0) -+ return wol; -+ -+ lpa = phy_read(phydev, MII_LPA); -+ if (lpa < 0) -+ return lpa; -+ -+ exp = phy_read(phydev, MII_EXPANSION); -+ if (exp < 0) -+ return exp; -+ -+ if (!(wol & BIT(12)) || -+ ((exp & EXPANSION_NWAY) && !(lpa & LPA_LPACK))) { -+ /* Looks like aneg failed after all */ -+ phydev_dbg(phydev, "LPA corruption - aneg restart\n"); -+ return genphy_restart_aneg(phydev); -+ } -+ } -+ -+read_status_continue: -+ return genphy_read_status(phydev); -+} -+ - static struct phy_driver meson_gxl_phy[] = { - { - .phy_id = 0x01814400, -@@ -60,7 +132,7 @@ static struct phy_driver meson_gxl_phy[] = { - .config_init = meson_gxl_config_init, - .config_aneg = genphy_config_aneg, - .aneg_done = genphy_aneg_done, -- .read_status = genphy_read_status, -+ .read_status = meson_gxl_read_status, - .suspend = genphy_suspend, - .resume = genphy_resume, - }, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/011_linux-4.14.y-le-amlogic-gx-0038-net-stmmac-enable_eee_in_mii,_gmii_or_rgmii_only.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/011_linux-4.14.y-le-amlogic-gx-0038-net-stmmac-enable_eee_in_mii,_gmii_or_rgmii_only.patch deleted file mode 100644 index d68652014..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/011_linux-4.14.y-le-amlogic-gx-0038-net-stmmac-enable_eee_in_mii,_gmii_or_rgmii_only.patch +++ /dev/null @@ -1,42 +0,0 @@ -From 0b4f75b1bbf8c1bd22cf62b5100f930e75b9229e Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Wed, 3 Jan 2018 16:46:29 +0100 -Subject: [PATCH] net: stmmac: enable EEE in MII, GMII or RGMII only - -Note in the databook - Section 4.4 - EEE : -" The EEE feature is not supported when the MAC is configured to use the -TBI, RTBI, SMII, RMII or SGMII single PHY interface. Even if the MAC -supports multiple PHY interfaces, you should activate the EEE mode only -when the MAC is operating with GMII, MII, or RGMII interface." - -Applying this restriction solves a stability issue observed on Amlogic -gxl platforms operating with RMII interface and the internal PHY. - -Fixes: 83bf79b6bb64 ("stmmac: disable at run-time the EEE if not supported") -Signed-off-by: Jerome Brunet -Tested-by: Arnaud Patard -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 6 ++++++ - 1 file changed, 6 insertions(+) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -index 16bd509290844..294a19f0fc1be 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -@@ -364,9 +364,15 @@ static void stmmac_eee_ctrl_timer(unsigned long arg) - bool stmmac_eee_init(struct stmmac_priv *priv) - { - struct net_device *ndev = priv->dev; -+ int interface = priv->plat->interface; - unsigned long flags; - bool ret = false; - -+ if ((interface != PHY_INTERFACE_MODE_MII) && -+ (interface != PHY_INTERFACE_MODE_GMII) && -+ !phy_interface_mode_is_rgmii(interface)) -+ goto out; -+ - /* Using PCS we cannot dial with the phy registers at this stage - * so we do not support extra feature like EEE. - */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/020_linux-4.16.y-le-amlogic-gx-0037-media-rc-meson-ir-add_timeout_on_idle.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/020_linux-4.16.y-le-amlogic-gx-0037-media-rc-meson-ir-add_timeout_on_idle.patch deleted file mode 100644 index e70ded913..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/020_linux-4.16.y-le-amlogic-gx-0037-media-rc-meson-ir-add_timeout_on_idle.patch +++ /dev/null @@ -1,82 +0,0 @@ -From 20705cd911573220254947a6338b0804d1382720 Mon Sep 17 00:00:00 2001 -From: Matthias Reichl -Date: Tue, 23 Jan 2018 09:40:02 +0100 -Subject: [PATCH] media: rc: meson-ir: add timeout on idle - -Meson hardware doesn't generate timeout events, so install a -software timer to prevent "ghost keypresses". - -Signed-off-by: Matthias Reichl ---- - drivers/media/rc/meson-ir.c | 22 ++++++++++++++++++++++ - 1 file changed, 22 insertions(+) - -diff --git a/drivers/media/rc/meson-ir.c b/drivers/media/rc/meson-ir.c -index f2204eb77e2ab..f34c5836412be 100644 ---- a/drivers/media/rc/meson-ir.c -+++ b/drivers/media/rc/meson-ir.c -@@ -69,6 +69,7 @@ struct meson_ir { - void __iomem *reg; - struct rc_dev *rc; - spinlock_t lock; -+ struct timer_list timeout_timer; - }; - - static void meson_ir_set_mask(struct meson_ir *ir, unsigned int reg, -@@ -98,6 +99,10 @@ static irqreturn_t meson_ir_irq(int irqno, void *dev_id) - rawir.pulse = !!(status & STATUS_IR_DEC_IN); - - ir_raw_event_store(ir->rc, &rawir); -+ -+ mod_timer(&ir->timeout_timer, -+ jiffies + nsecs_to_jiffies(ir->rc->timeout)); -+ - ir_raw_event_handle(ir->rc); - - spin_unlock(&ir->lock); -@@ -105,6 +110,17 @@ static irqreturn_t meson_ir_irq(int irqno, void *dev_id) - return IRQ_HANDLED; - } - -+static void meson_ir_timeout_timer(struct timer_list *t) -+{ -+ struct meson_ir *ir = from_timer(ir, t, timeout_timer); -+ DEFINE_IR_RAW_EVENT(rawir); -+ -+ rawir.timeout = true; -+ rawir.duration = ir->rc->timeout; -+ ir_raw_event_store(ir->rc, &rawir); -+ ir_raw_event_handle(ir->rc); -+} -+ - static int meson_ir_probe(struct platform_device *pdev) - { - struct device *dev = &pdev->dev; -@@ -145,7 +161,9 @@ static int meson_ir_probe(struct platform_device *pdev) - ir->rc->map_name = map_name ? map_name : RC_MAP_EMPTY; - ir->rc->allowed_protocols = RC_PROTO_BIT_ALL_IR_DECODER; - ir->rc->rx_resolution = US_TO_NS(MESON_TRATE); -+ ir->rc->min_timeout = 1; - ir->rc->timeout = MS_TO_NS(200); -+ ir->rc->max_timeout = 10 * IR_DEFAULT_TIMEOUT; - ir->rc->driver_name = DRIVER_NAME; - - spin_lock_init(&ir->lock); -@@ -157,6 +175,8 @@ static int meson_ir_probe(struct platform_device *pdev) - return ret; - } - -+ timer_setup(&ir->timeout_timer, meson_ir_timeout_timer, 0); -+ - ret = devm_request_irq(dev, irq, meson_ir_irq, 0, NULL, ir); - if (ret) { - dev_err(dev, "failed to request irq\n"); -@@ -198,6 +218,8 @@ static int meson_ir_remove(struct platform_device *pdev) - meson_ir_set_mask(ir, IR_DEC_REG1, REG1_ENABLE, 0); - spin_unlock_irqrestore(&ir->lock, flags); - -+ del_timer_sync(&ir->timeout_timer); -+ - return 0; - } - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/021_linux-4.16-le-amlogic-gx-1001-usb-enable-otg-as-host.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/021_linux-4.16-le-amlogic-gx-1001-usb-enable-otg-as-host.patch deleted file mode 100644 index 8f9c1cd27..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/021_linux-4.16-le-amlogic-gx-1001-usb-enable-otg-as-host.patch +++ /dev/null @@ -1,51 +0,0 @@ - ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-04-28 19:24:56.090524456 +0200 -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-04-29 23:09:48.559371108 +0200 -@@ -409,6 +409,7 @@ - &usb0_phy { - status = "okay"; - phy-supply = <&usb_otg_pwr>; -+ dr_mode = "otg"; - }; - - &usb1_phy { -@@ -418,6 +419,7 @@ - - &usb0 { - status = "okay"; -+ dr_mode = "host"; - }; - - &usb1 { - ---- a/drivers/phy/amlogic/phy-meson8b-usb2.c 2018-04-28 19:22:57.420144229 +0200 -+++ b/drivers/phy/amlogic/phy-meson8b-usb2.c 2018-04-29 23:13:57.136515043 +0200 -@@ -113,6 +113,7 @@ - struct phy_meson8b_usb2_priv { - void __iomem *regs; - enum usb_dr_mode dr_mode; -+ enum usb_dr_mode phy_mode; - struct clk *clk_usb_general; - struct clk *clk_usb; - struct reset_control *reset; -@@ -181,7 +182,7 @@ - phy_meson8b_usb2_mask_bits(priv, REG_CTRL, REG_CTRL_SOF_TOGGLE_OUT, - REG_CTRL_SOF_TOGGLE_OUT); - -- if (priv->dr_mode == USB_DR_MODE_HOST) { -+ if (priv->phy_mode == USB_DR_MODE_HOST) { - phy_meson8b_usb2_mask_bits(priv, REG_ADP_BC, - REG_ADP_BC_ACA_ENABLE, - REG_ADP_BC_ACA_ENABLE); -@@ -251,6 +252,11 @@ - return -EINVAL; - } - -+ priv->phy_mode = usb_get_dr_mode(&pdev->dev); -+ if (priv->phy_mode == USB_DR_MODE_UNKNOWN) { -+ priv->phy_mode = priv->dr_mode; -+ } -+ - phy = devm_phy_create(&pdev->dev, NULL, &phy_meson8b_usb2_ops); - if (IS_ERR(phy)) { - dev_err(&pdev->dev, "failed to create PHY\n"); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/022_linux-4.14.y-le-amlogic-gx-scpi-1004-mailbox-revert_switch_to_hrtimer_for_tx_complete_polling.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/022_linux-4.14.y-le-amlogic-gx-scpi-1004-mailbox-revert_switch_to_hrtimer_for_tx_complete_polling.patch deleted file mode 100644 index 2dd8b1c9c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/022_linux-4.14.y-le-amlogic-gx-scpi-1004-mailbox-revert_switch_to_hrtimer_for_tx_complete_polling.patch +++ /dev/null @@ -1,103 +0,0 @@ -diff --git a/drivers/mailbox/mailbox.c b/drivers/mailbox/mailbox.c -index 674b35f40..3497cabda 100644 ---- a/drivers/mailbox/mailbox.c -+++ b/drivers/mailbox/mailbox.c -@@ -26,6 +26,8 @@ - static LIST_HEAD(mbox_cons); - static DEFINE_MUTEX(con_mutex); - -+static void poll_txdone(struct timer_list *t); -+ - static int add_to_rbuf(struct mbox_chan *chan, void *mssg) - { - int idx; -@@ -86,8 +88,7 @@ static void msg_submit(struct mbox_chan *chan) - spin_unlock_irqrestore(&chan->lock, flags); - - if (!err && (chan->txdone_method & TXDONE_BY_POLL)) -- /* kick start the timer immediately to avoid delays */ -- hrtimer_start(&chan->mbox->poll_hrt, 0, HRTIMER_MODE_REL); -+ poll_txdone(&chan->mbox->poll); - } - - static void tx_tick(struct mbox_chan *chan, int r) -@@ -114,10 +115,9 @@ static void tx_tick(struct mbox_chan *chan, int r) - complete(&chan->tx_complete); - } - --static enum hrtimer_restart txdone_hrtimer(struct hrtimer *hrtimer) -+static void poll_txdone(struct timer_list *t) - { -- struct mbox_controller *mbox = -- container_of(hrtimer, struct mbox_controller, poll_hrt); -+ struct mbox_controller *mbox = from_timer(mbox, t, poll); - bool txdone, resched = false; - int i; - -@@ -133,11 +133,9 @@ static enum hrtimer_restart txdone_hrtimer(struct hrtimer *hrtimer) - } - } - -- if (resched) { -- hrtimer_forward_now(hrtimer, ms_to_ktime(mbox->txpoll_period)); -- return HRTIMER_RESTART; -- } -- return HRTIMER_NORESTART; -+ if (resched) -+ mod_timer(&mbox->poll, jiffies + -+ msecs_to_jiffies(mbox->txpoll_period)); - } - - /** -@@ -466,9 +464,7 @@ int mbox_controller_register(struct mbox_controller *mbox) - return -EINVAL; - } - -- hrtimer_init(&mbox->poll_hrt, CLOCK_MONOTONIC, -- HRTIMER_MODE_REL); -- mbox->poll_hrt.function = txdone_hrtimer; -+ timer_setup(&mbox->poll, &poll_txdone, 0); - } - - for (i = 0; i < mbox->num_chans; i++) { -@@ -510,7 +506,7 @@ void mbox_controller_unregister(struct mbox_controller *mbox) - mbox_free_channel(&mbox->chans[i]); - - if (mbox->txdone_poll) -- hrtimer_cancel(&mbox->poll_hrt); -+ del_timer_sync(&mbox->poll); - - mutex_unlock(&con_mutex); - } -diff --git a/include/linux/mailbox_controller.h b/include/linux/mailbox_controller.h -index 74deadb42..68c424544 100644 ---- a/include/linux/mailbox_controller.h -+++ b/include/linux/mailbox_controller.h -@@ -9,7 +9,7 @@ - - #include - #include --#include -+#include - #include - #include - -@@ -67,8 +67,7 @@ struct mbox_chan_ops { - * @txpoll_period: If 'txdone_poll' is in effect, the API polls for - * last TX's status after these many millisecs - * @of_xlate: Controller driver specific mapping of channel via DT -- * @poll_hrt: API private. hrtimer used to poll for TXDONE on all -- * channels. -+ * @poll: API private. Used to poll for TXDONE on all channels. - * @node: API private. To hook into list of controllers. - */ - struct mbox_controller { -@@ -82,7 +81,7 @@ struct mbox_controller { - struct mbox_chan *(*of_xlate)(struct mbox_controller *mbox, - const struct of_phandle_args *sp); - /* Internal to API */ -- struct hrtimer poll_hrt; -+ struct timer_list poll; - struct list_head node; - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/023_linux-4.14.y-backport-net-0001-drivers-net-stmmac-use_setup_timer_helper..patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/023_linux-4.14.y-backport-net-0001-drivers-net-stmmac-use_setup_timer_helper..patch deleted file mode 100644 index fe0312b0b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/023_linux-4.14.y-backport-net-0001-drivers-net-stmmac-use_setup_timer_helper..patch +++ /dev/null @@ -1,30 +0,0 @@ -From 997decfb6aeaa9be41ff557741845bb9fb4bf5bc Mon Sep 17 00:00:00 2001 -From: Allen Pais -Date: Thu, 21 Sep 2017 22:35:18 +0530 -Subject: [PATCH] drivers: net: stmmac: use setup_timer() helper. - -Use setup_timer function instead of initializing timer with the - function and data fields. - -Signed-off-by: Allen Pais -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 4 +--- - 1 file changed, 1 insertion(+), 3 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -index 1763e48c84e20..f41661a04f237 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -@@ -2217,10 +2217,8 @@ static void stmmac_init_tx_coalesce(struct stmmac_priv *priv) - { - priv->tx_coal_frames = STMMAC_TX_FRAMES; - priv->tx_coal_timer = STMMAC_COAL_TX_TIMER; -- init_timer(&priv->txtimer); -+ setup_timer(&priv->txtimer, stmmac_tx_timer, (unsigned long)priv); - priv->txtimer.expires = STMMAC_COAL_TIMER(priv->tx_coal_timer); -- priv->txtimer.data = (unsigned long)priv; -- priv->txtimer.function = stmmac_tx_timer; - add_timer(&priv->txtimer); - } - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/024_linux-4.14.y-backport-net-0002-net-ethernet-stmmac-clean_up_dead_code.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/024_linux-4.14.y-backport-net-0002-net-ethernet-stmmac-clean_up_dead_code.patch deleted file mode 100644 index ca015c02c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/024_linux-4.14.y-backport-net-0002-net-ethernet-stmmac-clean_up_dead_code.patch +++ /dev/null @@ -1,70 +0,0 @@ -From c778c32118167adcfe6b40063c49bfeac6bc1cf1 Mon Sep 17 00:00:00 2001 -From: Christos Gkekas -Date: Sun, 8 Oct 2017 20:13:49 +0100 -Subject: [PATCH] net: ethernet: stmmac: Clean up dead code - -Many macros in dwmac-ipq806x are unused and should be removed. -Moreover gmac->id is an unsigned variable and therefore checking -whether it is less than zero is redundant. - -Signed-off-by: Christos Gkekas -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c | 14 +------------- - 1 file changed, 1 insertion(+), 13 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c -index 866444b6c82fa..2c6d7c69c8f74 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c -@@ -51,15 +51,11 @@ - #define NSS_COMMON_CLK_SRC_CTRL_RGMII(x) 1 - #define NSS_COMMON_CLK_SRC_CTRL_SGMII(x) ((x >= 2) ? 1 : 0) - --#define NSS_COMMON_MACSEC_CTL 0x28 --#define NSS_COMMON_MACSEC_CTL_EXT_BYPASS_EN(x) (1 << x) -- - #define NSS_COMMON_GMAC_CTL(x) (0x30 + (x * 4)) - #define NSS_COMMON_GMAC_CTL_CSYS_REQ BIT(19) - #define NSS_COMMON_GMAC_CTL_PHY_IFACE_SEL BIT(16) - #define NSS_COMMON_GMAC_CTL_IFG_LIMIT_OFFSET 8 - #define NSS_COMMON_GMAC_CTL_IFG_OFFSET 0 --#define NSS_COMMON_GMAC_CTL_IFG_MASK 0x3f - - #define NSS_COMMON_CLK_DIV_RGMII_1000 1 - #define NSS_COMMON_CLK_DIV_RGMII_100 9 -@@ -68,9 +64,6 @@ - #define NSS_COMMON_CLK_DIV_SGMII_100 4 - #define NSS_COMMON_CLK_DIV_SGMII_10 49 - --#define QSGMII_PCS_MODE_CTL 0x68 --#define QSGMII_PCS_MODE_CTL_AUTONEG_EN(x) BIT((x * 8) + 7) -- - #define QSGMII_PCS_CAL_LCKDT_CTL 0x120 - #define QSGMII_PCS_CAL_LCKDT_CTL_RST BIT(19) - -@@ -83,15 +76,10 @@ - #define QSGMII_PHY_TX_DRIVER_EN BIT(3) - #define QSGMII_PHY_QSGMII_EN BIT(7) - #define QSGMII_PHY_PHASE_LOOP_GAIN_OFFSET 12 --#define QSGMII_PHY_PHASE_LOOP_GAIN_MASK 0x7 - #define QSGMII_PHY_RX_DC_BIAS_OFFSET 18 --#define QSGMII_PHY_RX_DC_BIAS_MASK 0x3 - #define QSGMII_PHY_RX_INPUT_EQU_OFFSET 20 --#define QSGMII_PHY_RX_INPUT_EQU_MASK 0x3 - #define QSGMII_PHY_CDR_PI_SLEW_OFFSET 22 --#define QSGMII_PHY_CDR_PI_SLEW_MASK 0x3 - #define QSGMII_PHY_TX_DRV_AMP_OFFSET 28 --#define QSGMII_PHY_TX_DRV_AMP_MASK 0xf - - struct ipq806x_gmac { - struct platform_device *pdev; -@@ -217,7 +205,7 @@ static int ipq806x_gmac_of_parse(struct ipq806x_gmac *gmac) - * code and keep it consistent with the Linux convention, we'll number - * them from 0 to 3 here. - */ -- if (gmac->id < 0 || gmac->id > 3) { -+ if (gmac->id > 3) { - dev_err(dev, "invalid gmac id\n"); - return -EINVAL; - } diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/025_linux-4.14.y-backport-net-0003-net-stmmac-use_correct_values_in_tqs-rqs_fields.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/025_linux-4.14.y-backport-net-0003-net-stmmac-use_correct_values_in_tqs-rqs_fields.patch deleted file mode 100644 index 0f7210435..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/025_linux-4.14.y-backport-net-0003-net-stmmac-use_correct_values_in_tqs-rqs_fields.patch +++ /dev/null @@ -1,135 +0,0 @@ -From 52a76235d0c4dd259cd0df503afed4757c04ba1d Mon Sep 17 00:00:00 2001 -From: Jose Abreu -Date: Fri, 13 Oct 2017 10:58:36 +0100 -Subject: [PATCH] net: stmmac: Use correct values in TQS/RQS fields - -Currently we are using all the available fifo size in RQS and -TQS fields. This will not work correctly in multi-queues IP's -because total fifo size must be splitted to the enabled queues. - -Correct this by computing the available fifo size per queue and -setting the right value in TQS and RQS fields. - -Signed-off-by: Jose Abreu -Cc: David S. Miller -Cc: Joao Pinto -Cc: Giuseppe Cavallaro -Cc: Alexandre Torgue -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/common.h | 3 ++- - drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c | 15 +++++++++------ - drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 22 ++++++++++++++++++++-- - 3 files changed, 31 insertions(+), 9 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/common.h b/drivers/net/ethernet/stmicro/stmmac/common.h -index e82b4b70b7be3..c26c8a7f957f5 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/common.h -+++ b/drivers/net/ethernet/stmicro/stmmac/common.h -@@ -443,7 +443,8 @@ struct stmmac_dma_ops { - int rxfifosz); - void (*dma_rx_mode)(void __iomem *ioaddr, int mode, u32 channel, - int fifosz); -- void (*dma_tx_mode)(void __iomem *ioaddr, int mode, u32 channel); -+ void (*dma_tx_mode)(void __iomem *ioaddr, int mode, u32 channel, -+ int fifosz); - /* To track extra statistic (if supported) */ - void (*dma_diagnostic_fr) (void *data, struct stmmac_extra_stats *x, - void __iomem *ioaddr); -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c b/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c -index e84831e1b63b3..898849bbc7d44 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c -@@ -271,9 +271,10 @@ static void dwmac4_dma_rx_chan_op_mode(void __iomem *ioaddr, int mode, - } - - static void dwmac4_dma_tx_chan_op_mode(void __iomem *ioaddr, int mode, -- u32 channel) -+ u32 channel, int fifosz) - { - u32 mtl_tx_op = readl(ioaddr + MTL_CHAN_TX_OP_MODE(channel)); -+ unsigned int tqs = fifosz / 256 - 1; - - if (mode == SF_DMA_MODE) { - pr_debug("GMAC: enable TX store and forward mode\n"); -@@ -306,12 +307,14 @@ static void dwmac4_dma_tx_chan_op_mode(void __iomem *ioaddr, int mode, - * For an IP with DWC_EQOS_NUM_TXQ > 1, the fields TXQEN and TQS are R/W - * with reset values: TXQEN off, TQS 256 bytes. - * -- * Write the bits in both cases, since it will have no effect when RO. -- * For DWC_EQOS_NUM_TXQ > 1, the top bits in MTL_OP_MODE_TQS_MASK might -- * be RO, however, writing the whole TQS field will result in a value -- * equal to DWC_EQOS_TXFIFO_SIZE, just like for DWC_EQOS_NUM_TXQ == 1. -+ * TXQEN must be written for multi-channel operation and TQS must -+ * reflect the available fifo size per queue (total fifo size / number -+ * of enabled queues). - */ -- mtl_tx_op |= MTL_OP_MODE_TXQEN | MTL_OP_MODE_TQS_MASK; -+ mtl_tx_op |= MTL_OP_MODE_TXQEN; -+ mtl_tx_op &= ~MTL_OP_MODE_TQS_MASK; -+ mtl_tx_op |= tqs << MTL_OP_MODE_TQS_SHIFT; -+ - writel(mtl_tx_op, ioaddr + MTL_CHAN_TX_OP_MODE(channel)); - } - -diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -index f41661a04f237..edf245b8bce32 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -@@ -1750,12 +1750,19 @@ static void stmmac_dma_operation_mode(struct stmmac_priv *priv) - u32 rx_channels_count = priv->plat->rx_queues_to_use; - u32 tx_channels_count = priv->plat->tx_queues_to_use; - int rxfifosz = priv->plat->rx_fifo_size; -+ int txfifosz = priv->plat->tx_fifo_size; - u32 txmode = 0; - u32 rxmode = 0; - u32 chan = 0; - - if (rxfifosz == 0) - rxfifosz = priv->dma_cap.rx_fifo_size; -+ if (txfifosz == 0) -+ txfifosz = priv->dma_cap.tx_fifo_size; -+ -+ /* Adjust for real per queue fifo size */ -+ rxfifosz /= rx_channels_count; -+ txfifosz /= tx_channels_count; - - if (priv->plat->force_thresh_dma_mode) { - txmode = tc; -@@ -1783,7 +1790,8 @@ static void stmmac_dma_operation_mode(struct stmmac_priv *priv) - rxfifosz); - - for (chan = 0; chan < tx_channels_count; chan++) -- priv->hw->dma->dma_tx_mode(priv->ioaddr, txmode, chan); -+ priv->hw->dma->dma_tx_mode(priv->ioaddr, txmode, chan, -+ txfifosz); - } else { - priv->hw->dma->dma_mode(priv->ioaddr, txmode, rxmode, - rxfifosz); -@@ -1946,15 +1954,25 @@ static void stmmac_tx_err(struct stmmac_priv *priv, u32 chan) - static void stmmac_set_dma_operation_mode(struct stmmac_priv *priv, u32 txmode, - u32 rxmode, u32 chan) - { -+ u32 rx_channels_count = priv->plat->rx_queues_to_use; -+ u32 tx_channels_count = priv->plat->tx_queues_to_use; - int rxfifosz = priv->plat->rx_fifo_size; -+ int txfifosz = priv->plat->tx_fifo_size; - - if (rxfifosz == 0) - rxfifosz = priv->dma_cap.rx_fifo_size; -+ if (txfifosz == 0) -+ txfifosz = priv->dma_cap.tx_fifo_size; -+ -+ /* Adjust for real per queue fifo size */ -+ rxfifosz /= rx_channels_count; -+ txfifosz /= tx_channels_count; - - if (priv->synopsys_id >= DWMAC_CORE_4_00) { - priv->hw->dma->dma_rx_mode(priv->ioaddr, rxmode, chan, - rxfifosz); -- priv->hw->dma->dma_tx_mode(priv->ioaddr, txmode, chan); -+ priv->hw->dma->dma_tx_mode(priv->ioaddr, txmode, chan, -+ txfifosz); - } else { - priv->hw->dma->dma_mode(priv->ioaddr, txmode, rxmode, - rxfifosz); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/026_linux-4.14.y-backport-net-0004-net-stmmac-disable_flow_ctrl_for_rx_avb_queues_and_really.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/026_linux-4.14.y-backport-net-0004-net-stmmac-disable_flow_ctrl_for_rx_avb_queues_and_really.patch deleted file mode 100644 index d000df779..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/026_linux-4.14.y-backport-net-0004-net-stmmac-disable_flow_ctrl_for_rx_avb_queues_and_really.patch +++ /dev/null @@ -1,160 +0,0 @@ -From a0daae13776994cf90e9a7bc81cd8e4ad3959093 Mon Sep 17 00:00:00 2001 -From: Jose Abreu -Date: Fri, 13 Oct 2017 10:58:37 +0100 -Subject: [PATCH] net: stmmac: Disable flow ctrl for RX AVB queues and really - enable TX AVB queues - -Flow control must be disabled for AVB enabled queues and TX -AVB queues must be enabled by setting BIT(2) of TXQEN. - -Correct this by passing the queue mode to DMA callbacks -and by checking in these functions wether we are in AVB -performing the necessary adjustments. - -Signed-off-by: Jose Abreu -Cc: David S. Miller -Cc: Joao Pinto -Cc: Giuseppe Cavallaro -Cc: Alexandre Torgue -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/common.h | 4 ++-- - drivers/net/ethernet/stmicro/stmmac/dwmac4.h | 2 ++ - drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c | 16 +++++++++++----- - drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 21 +++++++++++++++------ - 4 files changed, 30 insertions(+), 13 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/common.h b/drivers/net/ethernet/stmicro/stmmac/common.h -index c26c8a7f957f5..e1e5ac0537606 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/common.h -+++ b/drivers/net/ethernet/stmicro/stmmac/common.h -@@ -442,9 +442,9 @@ struct stmmac_dma_ops { - void (*dma_mode)(void __iomem *ioaddr, int txmode, int rxmode, - int rxfifosz); - void (*dma_rx_mode)(void __iomem *ioaddr, int mode, u32 channel, -- int fifosz); -+ int fifosz, u8 qmode); - void (*dma_tx_mode)(void __iomem *ioaddr, int mode, u32 channel, -- int fifosz); -+ int fifosz, u8 qmode); - /* To track extra statistic (if supported) */ - void (*dma_diagnostic_fr) (void *data, struct stmmac_extra_stats *x, - void __iomem *ioaddr); -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4.h b/drivers/net/ethernet/stmicro/stmmac/dwmac4.h -index d74cedf2a3975..aeda3ab2d761c 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac4.h -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4.h -@@ -225,6 +225,8 @@ enum power_event { - #define MTL_CHAN_RX_DEBUG(x) (MTL_CHANX_BASE_ADDR(x) + 0x38) - - #define MTL_OP_MODE_RSF BIT(5) -+#define MTL_OP_MODE_TXQEN_MASK GENMASK(3, 2) -+#define MTL_OP_MODE_TXQEN_AV BIT(2) - #define MTL_OP_MODE_TXQEN BIT(3) - #define MTL_OP_MODE_TSF BIT(1) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c b/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c -index 898849bbc7d44..c110f6850ffa3 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c -@@ -191,7 +191,7 @@ static void dwmac4_rx_watchdog(void __iomem *ioaddr, u32 riwt, u32 number_chan) - } - - static void dwmac4_dma_rx_chan_op_mode(void __iomem *ioaddr, int mode, -- u32 channel, int fifosz) -+ u32 channel, int fifosz, u8 qmode) - { - unsigned int rqs = fifosz / 256 - 1; - u32 mtl_rx_op, mtl_rx_int; -@@ -218,8 +218,10 @@ static void dwmac4_dma_rx_chan_op_mode(void __iomem *ioaddr, int mode, - mtl_rx_op &= ~MTL_OP_MODE_RQS_MASK; - mtl_rx_op |= rqs << MTL_OP_MODE_RQS_SHIFT; - -- /* enable flow control only if each channel gets 4 KiB or more FIFO */ -- if (fifosz >= 4096) { -+ /* Enable flow control only if each channel gets 4 KiB or more FIFO and -+ * only if channel is not an AVB channel. -+ */ -+ if ((fifosz >= 4096) && (qmode != MTL_QUEUE_AVB)) { - unsigned int rfd, rfa; - - mtl_rx_op |= MTL_OP_MODE_EHFC; -@@ -271,7 +273,7 @@ static void dwmac4_dma_rx_chan_op_mode(void __iomem *ioaddr, int mode, - } - - static void dwmac4_dma_tx_chan_op_mode(void __iomem *ioaddr, int mode, -- u32 channel, int fifosz) -+ u32 channel, int fifosz, u8 qmode) - { - u32 mtl_tx_op = readl(ioaddr + MTL_CHAN_TX_OP_MODE(channel)); - unsigned int tqs = fifosz / 256 - 1; -@@ -311,7 +313,11 @@ static void dwmac4_dma_tx_chan_op_mode(void __iomem *ioaddr, int mode, - * reflect the available fifo size per queue (total fifo size / number - * of enabled queues). - */ -- mtl_tx_op |= MTL_OP_MODE_TXQEN; -+ mtl_tx_op &= ~MTL_OP_MODE_TXQEN_MASK; -+ if (qmode != MTL_QUEUE_AVB) -+ mtl_tx_op |= MTL_OP_MODE_TXQEN; -+ else -+ mtl_tx_op |= MTL_OP_MODE_TXQEN_AV; - mtl_tx_op &= ~MTL_OP_MODE_TQS_MASK; - mtl_tx_op |= tqs << MTL_OP_MODE_TQS_SHIFT; - -diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -index edf245b8bce32..0e1b0a3d7b766 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -@@ -1754,6 +1754,7 @@ static void stmmac_dma_operation_mode(struct stmmac_priv *priv) - u32 txmode = 0; - u32 rxmode = 0; - u32 chan = 0; -+ u8 qmode = 0; - - if (rxfifosz == 0) - rxfifosz = priv->dma_cap.rx_fifo_size; -@@ -1785,13 +1786,19 @@ static void stmmac_dma_operation_mode(struct stmmac_priv *priv) - - /* configure all channels */ - if (priv->synopsys_id >= DWMAC_CORE_4_00) { -- for (chan = 0; chan < rx_channels_count; chan++) -+ for (chan = 0; chan < rx_channels_count; chan++) { -+ qmode = priv->plat->rx_queues_cfg[chan].mode_to_use; -+ - priv->hw->dma->dma_rx_mode(priv->ioaddr, rxmode, chan, -- rxfifosz); -+ rxfifosz, qmode); -+ } -+ -+ for (chan = 0; chan < tx_channels_count; chan++) { -+ qmode = priv->plat->tx_queues_cfg[chan].mode_to_use; - -- for (chan = 0; chan < tx_channels_count; chan++) - priv->hw->dma->dma_tx_mode(priv->ioaddr, txmode, chan, -- txfifosz); -+ txfifosz, qmode); -+ } - } else { - priv->hw->dma->dma_mode(priv->ioaddr, txmode, rxmode, - rxfifosz); -@@ -1954,6 +1961,8 @@ static void stmmac_tx_err(struct stmmac_priv *priv, u32 chan) - static void stmmac_set_dma_operation_mode(struct stmmac_priv *priv, u32 txmode, - u32 rxmode, u32 chan) - { -+ u8 rxqmode = priv->plat->rx_queues_cfg[chan].mode_to_use; -+ u8 txqmode = priv->plat->tx_queues_cfg[chan].mode_to_use; - u32 rx_channels_count = priv->plat->rx_queues_to_use; - u32 tx_channels_count = priv->plat->tx_queues_to_use; - int rxfifosz = priv->plat->rx_fifo_size; -@@ -1970,9 +1979,9 @@ static void stmmac_set_dma_operation_mode(struct stmmac_priv *priv, u32 txmode, - - if (priv->synopsys_id >= DWMAC_CORE_4_00) { - priv->hw->dma->dma_rx_mode(priv->ioaddr, rxmode, chan, -- rxfifosz); -+ rxfifosz, rxqmode); - priv->hw->dma->dma_tx_mode(priv->ioaddr, txmode, chan, -- txfifosz); -+ txfifosz, txqmode); - } else { - priv->hw->dma->dma_mode(priv->ioaddr, txmode, rxmode, - rxfifosz); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/027_linux-4.14.y-backport-net-0005-net-ethernet-stmmac-convert_timers_to_use_timer_setup.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/027_linux-4.14.y-backport-net-0005-net-ethernet-stmmac-convert_timers_to_use_timer_setup.patch deleted file mode 100644 index 972bba081..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/027_linux-4.14.y-backport-net-0005-net-ethernet-stmmac-convert_timers_to_use_timer_setup.patch +++ /dev/null @@ -1,90 +0,0 @@ -From abec4be3ee68c8572adb39da68fbfd86e63daa84 Mon Sep 17 00:00:00 2001 -From: Kees Cook -Date: Mon, 16 Oct 2017 17:29:00 -0700 -Subject: [PATCH] net: ethernet: stmmac: Convert timers to use timer_setup() - -In preparation for unconditionally passing the struct timer_list pointer to -all timer callbacks, switch to using the new timer_setup() and from_timer() -to pass the timer pointer explicitly. - -Cc: Giuseppe Cavallaro -Cc: Alexandre Torgue -Cc: netdev@vger.kernel.org -Signed-off-by: Kees Cook -Acked-by: Giuseppe Cavallaro -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/altr_tse_pcs.c | 22 ++++++++++------------ - 1 file changed, 10 insertions(+), 12 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/altr_tse_pcs.c b/drivers/net/ethernet/stmicro/stmmac/altr_tse_pcs.c -index 6a9c954492f22..8b50afcdb52df 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/altr_tse_pcs.c -+++ b/drivers/net/ethernet/stmicro/stmmac/altr_tse_pcs.c -@@ -118,10 +118,9 @@ int tse_pcs_init(void __iomem *base, struct tse_pcs *pcs) - return ret; - } - --static void pcs_link_timer_callback(unsigned long data) -+static void pcs_link_timer_callback(struct tse_pcs *pcs) - { - u16 val = 0; -- struct tse_pcs *pcs = (struct tse_pcs *)data; - void __iomem *tse_pcs_base = pcs->tse_pcs_base; - void __iomem *sgmii_adapter_base = pcs->sgmii_adapter_base; - -@@ -138,12 +137,11 @@ static void pcs_link_timer_callback(unsigned long data) - } - } - --static void auto_nego_timer_callback(unsigned long data) -+static void auto_nego_timer_callback(struct tse_pcs *pcs) - { - u16 val = 0; - u16 speed = 0; - u16 duplex = 0; -- struct tse_pcs *pcs = (struct tse_pcs *)data; - void __iomem *tse_pcs_base = pcs->tse_pcs_base; - void __iomem *sgmii_adapter_base = pcs->sgmii_adapter_base; - -@@ -201,14 +199,14 @@ static void auto_nego_timer_callback(unsigned long data) - } - } - --static void aneg_link_timer_callback(unsigned long data) -+static void aneg_link_timer_callback(struct timer_list *t) - { -- struct tse_pcs *pcs = (struct tse_pcs *)data; -+ struct tse_pcs *pcs = from_timer(pcs, t, aneg_link_timer); - - if (pcs->autoneg == AUTONEG_ENABLE) -- auto_nego_timer_callback(data); -+ auto_nego_timer_callback(pcs); - else if (pcs->autoneg == AUTONEG_DISABLE) -- pcs_link_timer_callback(data); -+ pcs_link_timer_callback(pcs); - } - - void tse_pcs_fix_mac_speed(struct tse_pcs *pcs, struct phy_device *phy_dev, -@@ -237,8 +235,8 @@ void tse_pcs_fix_mac_speed(struct tse_pcs *pcs, struct phy_device *phy_dev, - - tse_pcs_reset(tse_pcs_base, pcs); - -- setup_timer(&pcs->aneg_link_timer, -- aneg_link_timer_callback, (unsigned long)pcs); -+ timer_setup(&pcs->aneg_link_timer, aneg_link_timer_callback, -+ 0); - mod_timer(&pcs->aneg_link_timer, jiffies + - msecs_to_jiffies(AUTONEGO_LINK_TIMER)); - } else if (phy_dev->autoneg == AUTONEG_DISABLE) { -@@ -270,8 +268,8 @@ void tse_pcs_fix_mac_speed(struct tse_pcs *pcs, struct phy_device *phy_dev, - - tse_pcs_reset(tse_pcs_base, pcs); - -- setup_timer(&pcs->aneg_link_timer, -- aneg_link_timer_callback, (unsigned long)pcs); -+ timer_setup(&pcs->aneg_link_timer, aneg_link_timer_callback, -+ 0); - mod_timer(&pcs->aneg_link_timer, jiffies + - msecs_to_jiffies(AUTONEGO_LINK_TIMER)); - } diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/028_linux-4.14.y-backport-net-0006-net-stmmac-snps,_dwmac-mdio_mdios_are_automatically.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/028_linux-4.14.y-backport-net-0006-net-stmmac-snps,_dwmac-mdio_mdios_are_automatically.patch deleted file mode 100644 index 2719bfd29..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/028_linux-4.14.y-backport-net-0006-net-stmmac-snps,_dwmac-mdio_mdios_are_automatically.patch +++ /dev/null @@ -1,35 +0,0 @@ -From b5beecb580376cd8d959eb990abece6a748a3ce3 Mon Sep 17 00:00:00 2001 -From: Corentin Labbe -Date: Tue, 24 Oct 2017 19:57:12 +0200 -Subject: [PATCH] net: stmmac: snps, dwmac-mdio MDIOs are automatically - registered - -stmmac bindings docs said that its mdio node must have -compatible = "snps,dwmac-mdio"; -Since dwmac-sun8i does not have any good reasons to not doing it, all -their MDIO node must have it. - -Since these compatible is automatically registered, dwmac-sun8i compatible -does not need to be in need_mdio_ids. - -Signed-off-by: Corentin Labbe -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/stmmac_platform.c | 4 ---- - 1 file changed, 4 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_platform.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_platform.c -index 8a280b48e3a9f..9e616da0745d6 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_platform.c -+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_platform.c -@@ -311,10 +311,6 @@ static int stmmac_dt_phy(struct plat_stmmacenet_data *plat, - bool mdio = true; - static const struct of_device_id need_mdio_ids[] = { - { .compatible = "snps,dwc-qos-ethernet-4.10" }, -- { .compatible = "allwinner,sun8i-a83t-emac" }, -- { .compatible = "allwinner,sun8i-h3-emac" }, -- { .compatible = "allwinner,sun8i-v3s-emac" }, -- { .compatible = "allwinner,sun50i-a64-emac" }, - {}, - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/029_linux-4.14.y-backport-net-0007-net-stmmac-dwmac-sun8i-handle_integrated-external_mdios.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/029_linux-4.14.y-backport-net-0007-net-stmmac-dwmac-sun8i-handle_integrated-external_mdios.patch deleted file mode 100644 index 841e83e8b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/029_linux-4.14.y-backport-net-0007-net-stmmac-dwmac-sun8i-handle_integrated-external_mdios.patch +++ /dev/null @@ -1,510 +0,0 @@ -From 634db83b82658f4641d8026e340c6027cf74a6bb Mon Sep 17 00:00:00 2001 -From: Corentin Labbe -Date: Tue, 24 Oct 2017 19:57:13 +0200 -Subject: [PATCH] net: stmmac: dwmac-sun8i: Handle integrated/external MDIOs - -The Allwinner H3 SoC have two distinct MDIO bus, only one could be -active at the same time. -The selection of the active MDIO bus are done via some bits in the EMAC -register of the system controller. - -This patch implement this MDIO switch via a custom MDIO-mux. - -Signed-off-by: Corentin Labbe -Reviewed-by: Andrew Lunn -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/Kconfig | 1 + - drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c | 353 ++++++++++++++-------- - 2 files changed, 224 insertions(+), 130 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/Kconfig b/drivers/net/ethernet/stmicro/stmmac/Kconfig -index 97035766c291b..e28c0d2c58e91 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/Kconfig -+++ b/drivers/net/ethernet/stmicro/stmmac/Kconfig -@@ -159,6 +159,7 @@ config DWMAC_SUN8I - tristate "Allwinner sun8i GMAC support" - default ARCH_SUNXI - depends on OF && (ARCH_SUNXI || COMPILE_TEST) -+ select MDIO_BUS_MUX - ---help--- - Support for Allwinner H3 A83T A64 EMAC ethernet controllers. - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -index 39c2122a4f269..b3eb344bb158d 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -@@ -17,6 +17,7 @@ - #include - #include - #include -+#include - #include - #include - #include -@@ -41,14 +42,14 @@ - * This value is used for disabling properly EMAC - * and used as a good starting value in case of the - * boot process(uboot) leave some stuff. -- * @internal_phy: Does the MAC embed an internal PHY -+ * @soc_has_internal_phy: Does the MAC embed an internal PHY - * @support_mii: Does the MAC handle MII - * @support_rmii: Does the MAC handle RMII - * @support_rgmii: Does the MAC handle RGMII - */ - struct emac_variant { - u32 default_syscon_value; -- int internal_phy; -+ bool soc_has_internal_phy; - bool support_mii; - bool support_rmii; - bool support_rgmii; -@@ -61,7 +62,8 @@ struct emac_variant { - * @rst_ephy: reference to the optional EPHY reset for the internal PHY - * @variant: reference to the current board variant - * @regmap: regmap for using the syscon -- * @use_internal_phy: Does the current PHY choice imply using the internal PHY -+ * @internal_phy_powered: Does the internal PHY is enabled -+ * @mux_handle: Internal pointer used by mdio-mux lib - */ - struct sunxi_priv_data { - struct clk *tx_clk; -@@ -70,12 +72,13 @@ struct sunxi_priv_data { - struct reset_control *rst_ephy; - const struct emac_variant *variant; - struct regmap *regmap; -- bool use_internal_phy; -+ bool internal_phy_powered; -+ void *mux_handle; - }; - - static const struct emac_variant emac_variant_h3 = { - .default_syscon_value = 0x58000, -- .internal_phy = PHY_INTERFACE_MODE_MII, -+ .soc_has_internal_phy = true, - .support_mii = true, - .support_rmii = true, - .support_rgmii = true -@@ -83,20 +86,20 @@ static const struct emac_variant emac_variant_h3 = { - - static const struct emac_variant emac_variant_v3s = { - .default_syscon_value = 0x38000, -- .internal_phy = PHY_INTERFACE_MODE_MII, -+ .soc_has_internal_phy = true, - .support_mii = true - }; - - static const struct emac_variant emac_variant_a83t = { - .default_syscon_value = 0, -- .internal_phy = 0, -+ .soc_has_internal_phy = false, - .support_mii = true, - .support_rgmii = true - }; - - static const struct emac_variant emac_variant_a64 = { - .default_syscon_value = 0, -- .internal_phy = 0, -+ .soc_has_internal_phy = false, - .support_mii = true, - .support_rmii = true, - .support_rgmii = true -@@ -195,6 +198,9 @@ static const struct emac_variant emac_variant_a64 = { - #define H3_EPHY_LED_POL BIT(17) /* 1: active low, 0: active high */ - #define H3_EPHY_SHUTDOWN BIT(16) /* 1: shutdown, 0: power up */ - #define H3_EPHY_SELECT BIT(15) /* 1: internal PHY, 0: external PHY */ -+#define H3_EPHY_MUX_MASK (H3_EPHY_SHUTDOWN | H3_EPHY_SELECT) -+#define DWMAC_SUN8I_MDIO_MUX_INTERNAL_ID 1 -+#define DWMAC_SUN8I_MDIO_MUX_EXTERNAL_ID 2 - - /* H3/A64 specific bits */ - #define SYSCON_RMII_EN BIT(13) /* 1: enable RMII (overrides EPIT) */ -@@ -634,6 +640,159 @@ static int sun8i_dwmac_reset(struct stmmac_priv *priv) - return 0; - } - -+/* Search in mdio-mux node for internal PHY node and get its clk/reset */ -+static int get_ephy_nodes(struct stmmac_priv *priv) -+{ -+ struct sunxi_priv_data *gmac = priv->plat->bsp_priv; -+ struct device_node *mdio_mux, *iphynode; -+ struct device_node *mdio_internal; -+ int ret; -+ -+ mdio_mux = of_get_child_by_name(priv->device->of_node, "mdio-mux"); -+ if (!mdio_mux) { -+ dev_err(priv->device, "Cannot get mdio-mux node\n"); -+ return -ENODEV; -+ } -+ -+ mdio_internal = of_find_compatible_node(mdio_mux, NULL, -+ "allwinner,sun8i-h3-mdio-internal"); -+ if (!mdio_internal) { -+ dev_err(priv->device, "Cannot get internal_mdio node\n"); -+ return -ENODEV; -+ } -+ -+ /* Seek for internal PHY */ -+ for_each_child_of_node(mdio_internal, iphynode) { -+ gmac->ephy_clk = of_clk_get(iphynode, 0); -+ if (IS_ERR(gmac->ephy_clk)) -+ continue; -+ gmac->rst_ephy = of_reset_control_get_exclusive(iphynode, NULL); -+ if (IS_ERR(gmac->rst_ephy)) { -+ ret = PTR_ERR(gmac->rst_ephy); -+ if (ret == -EPROBE_DEFER) -+ return ret; -+ continue; -+ } -+ dev_info(priv->device, "Found internal PHY node\n"); -+ return 0; -+ } -+ return -ENODEV; -+} -+ -+static int sun8i_dwmac_power_internal_phy(struct stmmac_priv *priv) -+{ -+ struct sunxi_priv_data *gmac = priv->plat->bsp_priv; -+ int ret; -+ -+ if (gmac->internal_phy_powered) { -+ dev_warn(priv->device, "Internal PHY already powered\n"); -+ return 0; -+ } -+ -+ dev_info(priv->device, "Powering internal PHY\n"); -+ ret = clk_prepare_enable(gmac->ephy_clk); -+ if (ret) { -+ dev_err(priv->device, "Cannot enable internal PHY\n"); -+ return ret; -+ } -+ -+ /* Make sure the EPHY is properly reseted, as U-Boot may leave -+ * it at deasserted state, and thus it may fail to reset EMAC. -+ */ -+ reset_control_assert(gmac->rst_ephy); -+ -+ ret = reset_control_deassert(gmac->rst_ephy); -+ if (ret) { -+ dev_err(priv->device, "Cannot deassert internal phy\n"); -+ clk_disable_unprepare(gmac->ephy_clk); -+ return ret; -+ } -+ -+ gmac->internal_phy_powered = true; -+ -+ return 0; -+} -+ -+static int sun8i_dwmac_unpower_internal_phy(struct sunxi_priv_data *gmac) -+{ -+ if (!gmac->internal_phy_powered) -+ return 0; -+ -+ clk_disable_unprepare(gmac->ephy_clk); -+ reset_control_assert(gmac->rst_ephy); -+ gmac->internal_phy_powered = false; -+ return 0; -+} -+ -+/* MDIO multiplexing switch function -+ * This function is called by the mdio-mux layer when it thinks the mdio bus -+ * multiplexer needs to switch. -+ * 'current_child' is the current value of the mux register -+ * 'desired_child' is the value of the 'reg' property of the target child MDIO -+ * node. -+ * The first time this function is called, current_child == -1. -+ * If current_child == desired_child, then the mux is already set to the -+ * correct bus. -+ */ -+static int mdio_mux_syscon_switch_fn(int current_child, int desired_child, -+ void *data) -+{ -+ struct stmmac_priv *priv = data; -+ struct sunxi_priv_data *gmac = priv->plat->bsp_priv; -+ u32 reg, val; -+ int ret = 0; -+ bool need_power_ephy = false; -+ -+ if (current_child ^ desired_child) { -+ regmap_read(gmac->regmap, SYSCON_EMAC_REG, ®); -+ switch (desired_child) { -+ case DWMAC_SUN8I_MDIO_MUX_INTERNAL_ID: -+ dev_info(priv->device, "Switch mux to internal PHY"); -+ val = (reg & ~H3_EPHY_MUX_MASK) | H3_EPHY_SELECT; -+ -+ need_power_ephy = true; -+ break; -+ case DWMAC_SUN8I_MDIO_MUX_EXTERNAL_ID: -+ dev_info(priv->device, "Switch mux to external PHY"); -+ val = (reg & ~H3_EPHY_MUX_MASK) | H3_EPHY_SHUTDOWN; -+ need_power_ephy = false; -+ break; -+ default: -+ dev_err(priv->device, "Invalid child ID %x\n", -+ desired_child); -+ return -EINVAL; -+ } -+ regmap_write(gmac->regmap, SYSCON_EMAC_REG, val); -+ if (need_power_ephy) { -+ ret = sun8i_dwmac_power_internal_phy(priv); -+ if (ret) -+ return ret; -+ } else { -+ sun8i_dwmac_unpower_internal_phy(gmac); -+ } -+ /* After changing syscon value, the MAC need reset or it will -+ * use the last value (and so the last PHY set). -+ */ -+ ret = sun8i_dwmac_reset(priv); -+ } -+ return ret; -+} -+ -+static int sun8i_dwmac_register_mdio_mux(struct stmmac_priv *priv) -+{ -+ int ret; -+ struct device_node *mdio_mux; -+ struct sunxi_priv_data *gmac = priv->plat->bsp_priv; -+ -+ mdio_mux = of_get_child_by_name(priv->device->of_node, "mdio-mux"); -+ if (!mdio_mux) -+ return -ENODEV; -+ -+ ret = mdio_mux_init(priv->device, mdio_mux, mdio_mux_syscon_switch_fn, -+ &gmac->mux_handle, priv, priv->mii); -+ return ret; -+} -+ - static int sun8i_dwmac_set_syscon(struct stmmac_priv *priv) - { - struct sunxi_priv_data *gmac = priv->plat->bsp_priv; -@@ -648,35 +807,25 @@ static int sun8i_dwmac_set_syscon(struct stmmac_priv *priv) - "Current syscon value is not the default %x (expect %x)\n", - val, reg); - -- if (gmac->variant->internal_phy) { -- if (!gmac->use_internal_phy) { -- /* switch to external PHY interface */ -- reg &= ~H3_EPHY_SELECT; -- } else { -- reg |= H3_EPHY_SELECT; -- reg &= ~H3_EPHY_SHUTDOWN; -- dev_dbg(priv->device, "Select internal_phy %x\n", reg); -- -- if (of_property_read_bool(priv->plat->phy_node, -- "allwinner,leds-active-low")) -- reg |= H3_EPHY_LED_POL; -- else -- reg &= ~H3_EPHY_LED_POL; -- -- /* Force EPHY xtal frequency to 24MHz. */ -- reg |= H3_EPHY_CLK_SEL; -- -- ret = of_mdio_parse_addr(priv->device, -- priv->plat->phy_node); -- if (ret < 0) { -- dev_err(priv->device, "Could not parse MDIO addr\n"); -- return ret; -- } -- /* of_mdio_parse_addr returns a valid (0 ~ 31) PHY -- * address. No need to mask it again. -- */ -- reg |= ret << H3_EPHY_ADDR_SHIFT; -+ if (gmac->variant->soc_has_internal_phy) { -+ if (of_property_read_bool(priv->plat->phy_node, -+ "allwinner,leds-active-low")) -+ reg |= H3_EPHY_LED_POL; -+ else -+ reg &= ~H3_EPHY_LED_POL; -+ -+ /* Force EPHY xtal frequency to 24MHz. */ -+ reg |= H3_EPHY_CLK_SEL; -+ -+ ret = of_mdio_parse_addr(priv->device, priv->plat->phy_node); -+ if (ret < 0) { -+ dev_err(priv->device, "Could not parse MDIO addr\n"); -+ return ret; - } -+ /* of_mdio_parse_addr returns a valid (0 ~ 31) PHY -+ * address. No need to mask it again. -+ */ -+ reg |= 1 << H3_EPHY_ADDR_SHIFT; - } - - if (!of_property_read_u32(node, "allwinner,tx-delay-ps", &val)) { -@@ -746,81 +895,21 @@ static void sun8i_dwmac_unset_syscon(struct sunxi_priv_data *gmac) - regmap_write(gmac->regmap, SYSCON_EMAC_REG, reg); - } - --static int sun8i_dwmac_power_internal_phy(struct stmmac_priv *priv) -+static void sun8i_dwmac_exit(struct platform_device *pdev, void *priv) - { -- struct sunxi_priv_data *gmac = priv->plat->bsp_priv; -- int ret; -- -- if (!gmac->use_internal_phy) -- return 0; -- -- ret = clk_prepare_enable(gmac->ephy_clk); -- if (ret) { -- dev_err(priv->device, "Cannot enable ephy\n"); -- return ret; -- } -- -- /* Make sure the EPHY is properly reseted, as U-Boot may leave -- * it at deasserted state, and thus it may fail to reset EMAC. -- */ -- reset_control_assert(gmac->rst_ephy); -+ struct sunxi_priv_data *gmac = priv; - -- ret = reset_control_deassert(gmac->rst_ephy); -- if (ret) { -- dev_err(priv->device, "Cannot deassert ephy\n"); -- clk_disable_unprepare(gmac->ephy_clk); -- return ret; -+ if (gmac->variant->soc_has_internal_phy) { -+ /* sun8i_dwmac_exit could be called with mdiomux uninit */ -+ if (gmac->mux_handle) -+ mdio_mux_uninit(gmac->mux_handle); -+ if (gmac->internal_phy_powered) -+ sun8i_dwmac_unpower_internal_phy(gmac); - } - -- return 0; --} -- --static int sun8i_dwmac_unpower_internal_phy(struct sunxi_priv_data *gmac) --{ -- if (!gmac->use_internal_phy) -- return 0; -- -- clk_disable_unprepare(gmac->ephy_clk); -- reset_control_assert(gmac->rst_ephy); -- return 0; --} -- --/* sun8i_power_phy() - Activate the PHY: -- * In case of error, no need to call sun8i_unpower_phy(), -- * it will be called anyway by sun8i_dwmac_exit() -- */ --static int sun8i_power_phy(struct stmmac_priv *priv) --{ -- int ret; -- -- ret = sun8i_dwmac_power_internal_phy(priv); -- if (ret) -- return ret; -- -- ret = sun8i_dwmac_set_syscon(priv); -- if (ret) -- return ret; -- -- /* After changing syscon value, the MAC need reset or it will use -- * the last value (and so the last PHY set. -- */ -- ret = sun8i_dwmac_reset(priv); -- if (ret) -- return ret; -- return 0; --} -- --static void sun8i_unpower_phy(struct sunxi_priv_data *gmac) --{ - sun8i_dwmac_unset_syscon(gmac); -- sun8i_dwmac_unpower_internal_phy(gmac); --} -- --static void sun8i_dwmac_exit(struct platform_device *pdev, void *priv) --{ -- struct sunxi_priv_data *gmac = priv; - -- sun8i_unpower_phy(gmac); -+ reset_control_put(gmac->rst_ephy); - - clk_disable_unprepare(gmac->tx_clk); - -@@ -849,7 +938,7 @@ static struct mac_device_info *sun8i_dwmac_setup(void *ppriv) - if (!mac) - return NULL; - -- ret = sun8i_power_phy(priv); -+ ret = sun8i_dwmac_set_syscon(priv); - if (ret) - return NULL; - -@@ -889,6 +978,8 @@ static int sun8i_dwmac_probe(struct platform_device *pdev) - struct sunxi_priv_data *gmac; - struct device *dev = &pdev->dev; - int ret; -+ struct stmmac_priv *priv; -+ struct net_device *ndev; - - ret = stmmac_get_platform_resources(pdev, &stmmac_res); - if (ret) -@@ -932,29 +1023,6 @@ static int sun8i_dwmac_probe(struct platform_device *pdev) - } - - plat_dat->interface = of_get_phy_mode(dev->of_node); -- if (plat_dat->interface == gmac->variant->internal_phy) { -- dev_info(&pdev->dev, "Will use internal PHY\n"); -- gmac->use_internal_phy = true; -- gmac->ephy_clk = of_clk_get(plat_dat->phy_node, 0); -- if (IS_ERR(gmac->ephy_clk)) { -- ret = PTR_ERR(gmac->ephy_clk); -- dev_err(&pdev->dev, "Cannot get EPHY clock: %d\n", ret); -- return -EINVAL; -- } -- -- gmac->rst_ephy = of_reset_control_get(plat_dat->phy_node, NULL); -- if (IS_ERR(gmac->rst_ephy)) { -- ret = PTR_ERR(gmac->rst_ephy); -- if (ret == -EPROBE_DEFER) -- return ret; -- dev_err(&pdev->dev, "No EPHY reset control found %d\n", -- ret); -- return -EINVAL; -- } -- } else { -- dev_info(&pdev->dev, "Will use external PHY\n"); -- gmac->use_internal_phy = false; -- } - - /* platform data specifying hardware features and callbacks. - * hardware features were copied from Allwinner drivers. -@@ -973,9 +1041,34 @@ static int sun8i_dwmac_probe(struct platform_device *pdev) - - ret = stmmac_dvr_probe(&pdev->dev, plat_dat, &stmmac_res); - if (ret) -- sun8i_dwmac_exit(pdev, plat_dat->bsp_priv); -+ goto dwmac_exit; -+ -+ ndev = dev_get_drvdata(&pdev->dev); -+ priv = netdev_priv(ndev); -+ /* The mux must be registered after parent MDIO -+ * so after stmmac_dvr_probe() -+ */ -+ if (gmac->variant->soc_has_internal_phy) { -+ ret = get_ephy_nodes(priv); -+ if (ret) -+ goto dwmac_exit; -+ ret = sun8i_dwmac_register_mdio_mux(priv); -+ if (ret) { -+ dev_err(&pdev->dev, "Failed to register mux\n"); -+ goto dwmac_mux; -+ } -+ } else { -+ ret = sun8i_dwmac_reset(priv); -+ if (ret) -+ goto dwmac_exit; -+ } - - return ret; -+dwmac_mux: -+ sun8i_dwmac_unset_syscon(gmac); -+dwmac_exit: -+ sun8i_dwmac_exit(pdev, plat_dat->bsp_priv); -+return ret; - } - - static const struct of_device_id sun8i_dwmac_match[] = { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/030_linux-4.14.y-backport-net-0008-net-stmmac-sun8i-restore_the_compatibles.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/030_linux-4.14.y-backport-net-0008-net-stmmac-sun8i-restore_the_compatibles.patch deleted file mode 100644 index 6cfb68188..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/030_linux-4.14.y-backport-net-0008-net-stmmac-sun8i-restore_the_compatibles.patch +++ /dev/null @@ -1,37 +0,0 @@ -From a8ff8ccb45d37efa64476958fc5e9a8d9716b23b Mon Sep 17 00:00:00 2001 -From: Corentin Labbe -Date: Tue, 24 Oct 2017 19:57:14 +0200 -Subject: [PATCH] net: stmmac: sun8i: Restore the compatibles - -The original dwmac-sun8i DT bindings have some issue on how to handle -integrated PHY and was reverted in last RC of 4.13. -But now we have a solution so we need to get back that was reverted. - -This patch restore compatibles about dwmac-sun8i -This reverts commit ad4540cc5aa3 ("net: stmmac: sun8i: Remove the compatibles") - -Signed-off-by: Corentin Labbe -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c | 8 ++++++++ - 1 file changed, 8 insertions(+) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -index b3eb344bb158d..e5ff734d4f9b2 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -@@ -1072,6 +1072,14 @@ return ret; - } - - static const struct of_device_id sun8i_dwmac_match[] = { -+ { .compatible = "allwinner,sun8i-h3-emac", -+ .data = &emac_variant_h3 }, -+ { .compatible = "allwinner,sun8i-v3s-emac", -+ .data = &emac_variant_v3s }, -+ { .compatible = "allwinner,sun8i-a83t-emac", -+ .data = &emac_variant_a83t }, -+ { .compatible = "allwinner,sun50i-a64-emac", -+ .data = &emac_variant_a64 }, - { } - }; - MODULE_DEVICE_TABLE(of, sun8i_dwmac_match); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/031_linux-4.14.y-backport-net-0009-net-stmmac-fix_lpi_transitioning_for_dwmac4.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/031_linux-4.14.y-backport-net-0009-net-stmmac-fix_lpi_transitioning_for_dwmac4.patch deleted file mode 100644 index b31f8dae4..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/031_linux-4.14.y-backport-net-0009-net-stmmac-fix_lpi_transitioning_for_dwmac4.patch +++ /dev/null @@ -1,106 +0,0 @@ -From 4497478c60c04d2bf37082e27fc98f4f835db96b Mon Sep 17 00:00:00 2001 -From: Niklas Cassel -Date: Tue, 14 Nov 2017 11:15:54 +0100 -Subject: [PATCH] net: stmmac: fix LPI transitioning for dwmac4 - -The LPI transitioning logic in stmmac_main uses -priv->tx_path_in_lpi_mode to enter/exit LPI. - -However, priv->tx_path_in_lpi_mode is assigned -using the return value from host_irq_status(). - -So for dwmac4, priv->tx_path_in_lpi_mode was always false, -so stmmac_tx_clean() would always try to put us in eee mode, -and stmmac_xmit() would never take us out of eee mode. - -To fix this, make host_irq_status() read and return the LPI -irq status also for dwmac4. - -This also increments the existing LPI counters, so that -ethtool --statistics shows LPI transitions also for dwmac4. - -For dwmac1000, irqs are enabled/disabled using the register -named "Interrupt Mask Register", and thus setting a bit disables -that specific irq. - -For dwmac4 the matching register is named "MAC_Interrupt_Enable", -and thus setting a bit enables that specific irq. - -Looking at dwmac1000_core.c, the irqs that are always enabled are: -LPI and PMT. - -Looking at dwmac4_core.c, the irqs that are always enabled are: -PMT. - -To be able to read the LPI irq status, we need to enable the LPI -irq also for dwmac4. - -Signed-off-by: Niklas Cassel -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/dwmac4.h | 7 ++++++- - drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c | 19 +++++++++++++++++++ - 2 files changed, 25 insertions(+), 1 deletion(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4.h b/drivers/net/ethernet/stmicro/stmmac/dwmac4.h -index aeda3ab2d761c..789dad8a07b5c 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac4.h -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4.h -@@ -98,7 +98,7 @@ - #define GMAC_PCS_IRQ_DEFAULT (GMAC_INT_RGSMIIS | GMAC_INT_PCS_LINK | \ - GMAC_INT_PCS_ANE) - --#define GMAC_INT_DEFAULT_MASK GMAC_INT_PMT_EN -+#define GMAC_INT_DEFAULT_MASK (GMAC_INT_PMT_EN | GMAC_INT_LPI_EN) - - enum dwmac4_irq_status { - time_stamp_irq = 0x00001000, -@@ -106,6 +106,7 @@ enum dwmac4_irq_status { - mmc_tx_irq = 0x00000400, - mmc_rx_irq = 0x00000200, - mmc_irq = 0x00000100, -+ lpi_irq = 0x00000020, - pmt_irq = 0x00000010, - }; - -@@ -132,6 +133,10 @@ enum power_event { - #define GMAC4_LPI_CTRL_STATUS_LPITXA BIT(19) /* Enable LPI TX Automate */ - #define GMAC4_LPI_CTRL_STATUS_PLS BIT(17) /* PHY Link Status */ - #define GMAC4_LPI_CTRL_STATUS_LPIEN BIT(16) /* LPI Enable */ -+#define GMAC4_LPI_CTRL_STATUS_RLPIEX BIT(3) /* Receive LPI Exit */ -+#define GMAC4_LPI_CTRL_STATUS_RLPIEN BIT(2) /* Receive LPI Entry */ -+#define GMAC4_LPI_CTRL_STATUS_TLPIEX BIT(1) /* Transmit LPI Exit */ -+#define GMAC4_LPI_CTRL_STATUS_TLPIEN BIT(0) /* Transmit LPI Entry */ - - /* MAC Debug bitmap */ - #define GMAC_DEBUG_TFCSTS_MASK GENMASK(18, 17) -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c b/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -index 2f7d7ec59962a..f3ed8f7853eb4 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -@@ -580,6 +580,25 @@ static int dwmac4_irq_status(struct mac_device_info *hw, - x->irq_receive_pmt_irq_n++; - } - -+ /* MAC tx/rx EEE LPI entry/exit interrupts */ -+ if (intr_status & lpi_irq) { -+ /* Clear LPI interrupt by reading MAC_LPI_Control_Status */ -+ u32 status = readl(ioaddr + GMAC4_LPI_CTRL_STATUS); -+ -+ if (status & GMAC4_LPI_CTRL_STATUS_TLPIEN) { -+ ret |= CORE_IRQ_TX_PATH_IN_LPI_MODE; -+ x->irq_tx_path_in_lpi_mode_n++; -+ } -+ if (status & GMAC4_LPI_CTRL_STATUS_TLPIEX) { -+ ret |= CORE_IRQ_TX_PATH_EXIT_LPI_MODE; -+ x->irq_tx_path_exit_lpi_mode_n++; -+ } -+ if (status & GMAC4_LPI_CTRL_STATUS_RLPIEN) -+ x->irq_rx_path_in_lpi_mode_n++; -+ if (status & GMAC4_LPI_CTRL_STATUS_RLPIEX) -+ x->irq_rx_path_exit_lpi_mode_n++; -+ } -+ - dwmac_pcs_isr(ioaddr, GMAC_PCS_BASE, intr_status, x); - if (intr_status & PCS_RGSMIIIS_IRQ) - dwmac4_phystatus(ioaddr, x); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/032_linux-4.14.y-backport-net-0010-net-stmmac-dwmac-sun8i-fix_allwinner,leds-active-low.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/032_linux-4.14.y-backport-net-0010-net-stmmac-dwmac-sun8i-fix_allwinner,leds-active-low.patch deleted file mode 100644 index 7435b7af2..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/032_linux-4.14.y-backport-net-0010-net-stmmac-dwmac-sun8i-fix_allwinner,leds-active-low.patch +++ /dev/null @@ -1,32 +0,0 @@ -From 1c08ac0c4bd8e9d66c4dde29bc496c3b430dd028 Mon Sep 17 00:00:00 2001 -From: Corentin Labbe -Date: Tue, 28 Nov 2017 17:48:22 +0100 -Subject: [PATCH] net: stmmac: dwmac-sun8i: fix allwinner,leds-active-low - handling - -The driver expect "allwinner,leds-active-low" to be in PHY node, but -the binding doc expect it to be in MAC node. - -Since all board DT use it also in MAC node, the driver need to search -allwinner,leds-active-low in MAC node. - -Signed-off-by: Corentin Labbe -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c | 3 +-- - 1 file changed, 1 insertion(+), 2 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -index e5ff734d4f9b2..9eb7f65d8000d 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -@@ -808,8 +808,7 @@ static int sun8i_dwmac_set_syscon(struct stmmac_priv *priv) - val, reg); - - if (gmac->variant->soc_has_internal_phy) { -- if (of_property_read_bool(priv->plat->phy_node, -- "allwinner,leds-active-low")) -+ if (of_property_read_bool(node, "allwinner,leds-active-low")) - reg |= H3_EPHY_LED_POL; - else - reg &= ~H3_EPHY_LED_POL; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/033_linux-4.14.y-backport-net-0011-ethernet-dwmac-stm32-fix_copyright.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/033_linux-4.14.y-backport-net-0011-ethernet-dwmac-stm32-fix_copyright.patch deleted file mode 100644 index ae376676a..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/033_linux-4.14.y-backport-net-0011-ethernet-dwmac-stm32-fix_copyright.patch +++ /dev/null @@ -1,30 +0,0 @@ -From f6454f80e8a965fca203dab28723f68ec78db608 Mon Sep 17 00:00:00 2001 -From: Benjamin Gaignard -Date: Wed, 29 Nov 2017 15:20:00 +0100 -Subject: [PATCH] ethernet: dwmac-stm32: Fix copyright - -Uniformize STMicroelectronics copyrights header - -Signed-off-by: Benjamin Gaignard -CC: Alexandre Torgue -Acked-by: Alexandre TORGUE -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/dwmac-stm32.c | 4 ++-- - 1 file changed, 2 insertions(+), 2 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-stm32.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-stm32.c -index 61cb24810d101..9e6db16af663b 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac-stm32.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-stm32.c -@@ -1,8 +1,8 @@ - /* - * dwmac-stm32.c - DWMAC Specific Glue layer for STM32 MCU - * -- * Copyright (C) Alexandre Torgue 2015 -- * Author: Alexandre Torgue -+ * Copyright (C) STMicroelectronics SA 2017 -+ * Author: Alexandre Torgue for STMicroelectronics. - * License terms: GNU General Public License (GPL), version 2 - * - */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/034_linux-4.14.y-backport-net-0012-net-stmmac-fix_broken_dma_interrupt_handling_for.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/034_linux-4.14.y-backport-net-0012-net-stmmac-fix_broken_dma_interrupt_handling_for.patch deleted file mode 100644 index cf763e6da..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/034_linux-4.14.y-backport-net-0012-net-stmmac-fix_broken_dma_interrupt_handling_for.patch +++ /dev/null @@ -1,128 +0,0 @@ -From 5a6a0445d1edb28fc89fd12b49cda2d5114e2665 Mon Sep 17 00:00:00 2001 -From: Niklas Cassel -Date: Thu, 7 Dec 2017 23:56:10 +0100 -Subject: [PATCH] net: stmmac: fix broken dma_interrupt handling for - multi-queues - -There is nothing that says that number of TX queues == number of RX -queues. E.g. the ARTPEC-6 SoC has 2 TX queues and 1 RX queue. - -This code is obviously wrong: -for (chan = 0; chan < tx_channel_count; chan++) { - struct stmmac_rx_queue *rx_q = &priv->rx_queue[chan]; - -priv->rx_queue has size MTL_MAX_RX_QUEUES, so this will send an -uninitialized napi_struct to __napi_schedule(), causing us to -crash in net_rx_action(), because napi_struct->poll is zero. - -[12846.759880] Unable to handle kernel NULL pointer dereference at virtual address 00000000 -[12846.768014] pgd = (ptrval) -[12846.770742] [00000000] *pgd=39ec7831, *pte=00000000, *ppte=00000000 -[12846.777023] Internal error: Oops: 80000007 [#1] PREEMPT SMP ARM -[12846.782942] Modules linked in: -[12846.785998] CPU: 0 PID: 161 Comm: dropbear Not tainted 4.15.0-rc2-00285-gf5fb5f2f39a7 #36 -[12846.794177] Hardware name: Axis ARTPEC-6 Platform -[12846.798879] task: (ptrval) task.stack: (ptrval) -[12846.803407] PC is at 0x0 -[12846.805942] LR is at net_rx_action+0x274/0x43c -[12846.810383] pc : [<00000000>] lr : [<80bff064>] psr: 200e0113 -[12846.816648] sp : b90d9ae8 ip : b90d9ae8 fp : b90d9b44 -[12846.821871] r10: 00000008 r9 : 0013250e r8 : 00000100 -[12846.827094] r7 : 0000012c r6 : 00000000 r5 : 00000001 r4 : bac84900 -[12846.833619] r3 : 00000000 r2 : b90d9b08 r1 : 00000000 r0 : bac84900 - -Since each DMA channel can be used for rx and tx simultaneously, -the current code should probably be rewritten so that napi_struct is -embedded in a new struct stmmac_channel. -That way, stmmac_poll() can call stmmac_tx_clean() on just the tx queue -where we got the IRQ, instead of looping through all tx queues. -This is also how the xgbe driver does it (another driver for this IP). - -Fixes: c22a3f48ef99 ("net: stmmac: adding multiple napi mechanism") -Signed-off-by: Niklas Cassel -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 54 +++++++++++++++++++---- - 1 file changed, 46 insertions(+), 8 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -index d7250539d0bd0..c52a9963c19d5 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -@@ -1997,22 +1997,60 @@ static void stmmac_set_dma_operation_mode(struct stmmac_priv *priv, u32 txmode, - static void stmmac_dma_interrupt(struct stmmac_priv *priv) - { - u32 tx_channel_count = priv->plat->tx_queues_to_use; -- int status; -+ u32 rx_channel_count = priv->plat->rx_queues_to_use; -+ u32 channels_to_check = tx_channel_count > rx_channel_count ? -+ tx_channel_count : rx_channel_count; - u32 chan; -+ bool poll_scheduled = false; -+ int status[channels_to_check]; -+ -+ /* Each DMA channel can be used for rx and tx simultaneously, yet -+ * napi_struct is embedded in struct stmmac_rx_queue rather than in a -+ * stmmac_channel struct. -+ * Because of this, stmmac_poll currently checks (and possibly wakes) -+ * all tx queues rather than just a single tx queue. -+ */ -+ for (chan = 0; chan < channels_to_check; chan++) -+ status[chan] = priv->hw->dma->dma_interrupt(priv->ioaddr, -+ &priv->xstats, -+ chan); - -- for (chan = 0; chan < tx_channel_count; chan++) { -- struct stmmac_rx_queue *rx_q = &priv->rx_queue[chan]; -+ for (chan = 0; chan < rx_channel_count; chan++) { -+ if (likely(status[chan] & handle_rx)) { -+ struct stmmac_rx_queue *rx_q = &priv->rx_queue[chan]; - -- status = priv->hw->dma->dma_interrupt(priv->ioaddr, -- &priv->xstats, chan); -- if (likely((status & handle_rx)) || (status & handle_tx)) { - if (likely(napi_schedule_prep(&rx_q->napi))) { - stmmac_disable_dma_irq(priv, chan); - __napi_schedule(&rx_q->napi); -+ poll_scheduled = true; -+ } -+ } -+ } -+ -+ /* If we scheduled poll, we already know that tx queues will be checked. -+ * If we didn't schedule poll, see if any DMA channel (used by tx) has a -+ * completed transmission, if so, call stmmac_poll (once). -+ */ -+ if (!poll_scheduled) { -+ for (chan = 0; chan < tx_channel_count; chan++) { -+ if (status[chan] & handle_tx) { -+ /* It doesn't matter what rx queue we choose -+ * here. We use 0 since it always exists. -+ */ -+ struct stmmac_rx_queue *rx_q = -+ &priv->rx_queue[0]; -+ -+ if (likely(napi_schedule_prep(&rx_q->napi))) { -+ stmmac_disable_dma_irq(priv, chan); -+ __napi_schedule(&rx_q->napi); -+ } -+ break; - } - } -+ } - -- if (unlikely(status & tx_hard_error_bump_tc)) { -+ for (chan = 0; chan < tx_channel_count; chan++) { -+ if (unlikely(status[chan] & tx_hard_error_bump_tc)) { - /* Try to bump up the dma threshold on this failure */ - if (unlikely(priv->xstats.threshold != SF_DMA_MODE) && - (tc <= 256)) { -@@ -2029,7 +2067,7 @@ static void stmmac_dma_interrupt(struct stmmac_priv *priv) - chan); - priv->xstats.threshold = tc; - } -- } else if (unlikely(status == tx_hard_error)) { -+ } else if (unlikely(status[chan] == tx_hard_error)) { - stmmac_tx_err(priv, chan); - } - } diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/035_linux-4.14.y-backport-net-0013-net-stmmac-pad_ring_number_with_zeroes_in_display_ring.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/035_linux-4.14.y-backport-net-0013-net-stmmac-pad_ring_number_with_zeroes_in_display_ring.patch deleted file mode 100644 index d6a39b820..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/035_linux-4.14.y-backport-net-0013-net-stmmac-pad_ring_number_with_zeroes_in_display_ring.patch +++ /dev/null @@ -1,56 +0,0 @@ -From bdb421663d936eb9b29c743a668614276cf3b97d Mon Sep 17 00:00:00 2001 -From: Florian Fainelli -Date: Fri, 29 Dec 2017 19:56:32 -0800 -Subject: [PATCH] net: stmmac: Pad ring number with zeroes in display_ring() - -Make the printing of the ring number consistent and properly aligned by -padding the ring number with up to 3 zeroes, which covers the maximum -ring size. This makes it a lot easier to see outliers in debug prints. - -Signed-off-by: Florian Fainelli -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c | 2 +- - drivers/net/ethernet/stmicro/stmmac/enh_desc.c | 2 +- - drivers/net/ethernet/stmicro/stmmac/norm_desc.c | 2 +- - 3 files changed, 3 insertions(+), 3 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c b/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c -index 7e089bf906b4f..2fd8456999f69 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c -@@ -406,7 +406,7 @@ static void dwmac4_display_ring(void *head, unsigned int size, bool rx) - pr_info("%s descriptor ring:\n", rx ? "RX" : "TX"); - - for (i = 0; i < size; i++) { -- pr_info("%d [0x%x]: 0x%x 0x%x 0x%x 0x%x\n", -+ pr_info("%03d [0x%x]: 0x%x 0x%x 0x%x 0x%x\n", - i, (unsigned int)virt_to_phys(p), - le32_to_cpu(p->des0), le32_to_cpu(p->des1), - le32_to_cpu(p->des2), le32_to_cpu(p->des3)); -diff --git a/drivers/net/ethernet/stmicro/stmmac/enh_desc.c b/drivers/net/ethernet/stmicro/stmmac/enh_desc.c -index 2a828a3128142..b47cb5c4da513 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/enh_desc.c -+++ b/drivers/net/ethernet/stmicro/stmmac/enh_desc.c -@@ -428,7 +428,7 @@ static void enh_desc_display_ring(void *head, unsigned int size, bool rx) - u64 x; - - x = *(u64 *)ep; -- pr_info("%d [0x%x]: 0x%x 0x%x 0x%x 0x%x\n", -+ pr_info("%03d [0x%x]: 0x%x 0x%x 0x%x 0x%x\n", - i, (unsigned int)virt_to_phys(ep), - (unsigned int)x, (unsigned int)(x >> 32), - ep->basic.des2, ep->basic.des3); -diff --git a/drivers/net/ethernet/stmicro/stmmac/norm_desc.c b/drivers/net/ethernet/stmicro/stmmac/norm_desc.c -index db4cee57bb246..ebd9e5e00f161 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/norm_desc.c -+++ b/drivers/net/ethernet/stmicro/stmmac/norm_desc.c -@@ -288,7 +288,7 @@ static void ndesc_display_ring(void *head, unsigned int size, bool rx) - u64 x; - - x = *(u64 *)p; -- pr_info("%d [0x%x]: 0x%x 0x%x 0x%x 0x%x", -+ pr_info("%03d [0x%x]: 0x%x 0x%x 0x%x 0x%x", - i, (unsigned int)virt_to_phys(p), - (unsigned int)x, (unsigned int)(x >> 32), - p->des2, p->des3); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/036_linux-4.14.y-backport-net-0014-net-stmmac-dwmac-meson8b-only_configure_the_clocks_in.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/036_linux-4.14.y-backport-net-0014-net-stmmac-dwmac-meson8b-only_configure_the_clocks_in.patch deleted file mode 100644 index c68200318..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/036_linux-4.14.y-backport-net-0014-net-stmmac-dwmac-meson8b-only_configure_the_clocks_in.patch +++ /dev/null @@ -1,133 +0,0 @@ -From 37512b42f082d784a012c3734ef109f25d199786 Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Mon, 15 Jan 2018 18:10:12 +0100 -Subject: [PATCH] net: stmmac: dwmac-meson8b: only configure the clocks in - RGMII mode - -Neither the m25_div_clk nor the m250_div_clk or m250_mux_clk are used in -RMII mode. The m25_div_clk output is routed to the RGMII PHY's "RGMII -clock". -This means that we don't need to configure the clocks in RMII mode. The -driver however did this - with no effect since the clocks are not routed -to the PHY in RMII mode. - -While here also rename meson8b_init_clk to meson8b_init_rgmii_tx_clk to -make it easier to understand the code. - -Fixes: 566e8251625304 ("net: stmmac: add a glue driver for the Amlogic Meson 8b / GXBB DWMAC") -Signed-off-by: Martin Blumenstingl -Tested-by: Jerome Brunet -Signed-off-by: David S. Miller ---- - .../net/ethernet/stmicro/stmmac/dwmac-meson8b.c | 46 ++++++++++------------ - 1 file changed, 21 insertions(+), 25 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-meson8b.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-meson8b.c -index 4404650b32c5e..c6f87e9c4ccb3 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac-meson8b.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-meson8b.c -@@ -81,7 +81,7 @@ static void meson8b_dwmac_mask_bits(struct meson8b_dwmac *dwmac, u32 reg, - writel(data, dwmac->regs + reg); - } - --static int meson8b_init_clk(struct meson8b_dwmac *dwmac) -+static int meson8b_init_rgmii_tx_clk(struct meson8b_dwmac *dwmac) - { - struct clk_init_data init; - int i, ret; -@@ -176,7 +176,6 @@ static int meson8b_init_clk(struct meson8b_dwmac *dwmac) - static int meson8b_init_prg_eth(struct meson8b_dwmac *dwmac) - { - int ret; -- unsigned long clk_rate; - u8 tx_dly_val = 0; - - switch (dwmac->phy_mode) { -@@ -191,9 +190,6 @@ static int meson8b_init_prg_eth(struct meson8b_dwmac *dwmac) - - case PHY_INTERFACE_MODE_RGMII_ID: - case PHY_INTERFACE_MODE_RGMII_TXID: -- /* Generate a 25MHz clock for the PHY */ -- clk_rate = 25 * 1000 * 1000; -- - /* enable RGMII mode */ - meson8b_dwmac_mask_bits(dwmac, PRG_ETH0, PRG_ETH0_RGMII_MODE, - PRG_ETH0_RGMII_MODE); -@@ -204,12 +200,24 @@ static int meson8b_init_prg_eth(struct meson8b_dwmac *dwmac) - - meson8b_dwmac_mask_bits(dwmac, PRG_ETH0, PRG_ETH0_TXDLY_MASK, - tx_dly_val << PRG_ETH0_TXDLY_SHIFT); -+ -+ ret = clk_prepare_enable(dwmac->m25_div_clk); -+ if (ret) { -+ dev_err(&dwmac->pdev->dev, "failed to enable the PHY clock\n"); -+ return ret; -+ } -+ -+ /* Generate the 25MHz RGMII clock for the PHY */ -+ ret = clk_set_rate(dwmac->m25_div_clk, 25 * 1000 * 1000); -+ if (ret) { -+ clk_disable_unprepare(dwmac->m25_div_clk); -+ -+ dev_err(&dwmac->pdev->dev, "failed to set PHY clock\n"); -+ return ret; -+ } - break; - - case PHY_INTERFACE_MODE_RMII: -- /* Use the rate of the mux clock for the internal RMII PHY */ -- clk_rate = clk_get_rate(dwmac->m250_mux_clk); -- - /* disable RGMII mode -> enables RMII mode */ - meson8b_dwmac_mask_bits(dwmac, PRG_ETH0, PRG_ETH0_RGMII_MODE, - 0); -@@ -231,20 +239,6 @@ static int meson8b_init_prg_eth(struct meson8b_dwmac *dwmac) - return -EINVAL; - } - -- ret = clk_prepare_enable(dwmac->m25_div_clk); -- if (ret) { -- dev_err(&dwmac->pdev->dev, "failed to enable the PHY clock\n"); -- return ret; -- } -- -- ret = clk_set_rate(dwmac->m25_div_clk, clk_rate); -- if (ret) { -- clk_disable_unprepare(dwmac->m25_div_clk); -- -- dev_err(&dwmac->pdev->dev, "failed to set PHY clock\n"); -- return ret; -- } -- - /* enable TX_CLK and PHY_REF_CLK generator */ - meson8b_dwmac_mask_bits(dwmac, PRG_ETH0, PRG_ETH0_TX_AND_PHY_REF_CLK, - PRG_ETH0_TX_AND_PHY_REF_CLK); -@@ -294,7 +288,7 @@ static int meson8b_dwmac_probe(struct platform_device *pdev) - &dwmac->tx_delay_ns)) - dwmac->tx_delay_ns = 2; - -- ret = meson8b_init_clk(dwmac); -+ ret = meson8b_init_rgmii_tx_clk(dwmac); - if (ret) - goto err_remove_config_dt; - -@@ -311,7 +305,8 @@ static int meson8b_dwmac_probe(struct platform_device *pdev) - return 0; - - err_clk_disable: -- clk_disable_unprepare(dwmac->m25_div_clk); -+ if (phy_interface_mode_is_rgmii(dwmac->phy_mode)) -+ clk_disable_unprepare(dwmac->m25_div_clk); - err_remove_config_dt: - stmmac_remove_config_dt(pdev, plat_dat); - -@@ -322,7 +317,8 @@ static int meson8b_dwmac_remove(struct platform_device *pdev) - { - struct meson8b_dwmac *dwmac = get_stmmac_bsp_priv(&pdev->dev); - -- clk_disable_unprepare(dwmac->m25_div_clk); -+ if (phy_interface_mode_is_rgmii(dwmac->phy_mode)) -+ clk_disable_unprepare(dwmac->m25_div_clk); - - return stmmac_pltfr_remove(pdev); - } diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/037_linux-4.14.y-backport-net-0015-net-stmmac-dwmac-meson8b-fix_internal_rgmii_clock.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/037_linux-4.14.y-backport-net-0015-net-stmmac-dwmac-meson8b-fix_internal_rgmii_clock.patch deleted file mode 100644 index 31786ee28..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/037_linux-4.14.y-backport-net-0015-net-stmmac-dwmac-meson8b-fix_internal_rgmii_clock.patch +++ /dev/null @@ -1,215 +0,0 @@ -From 4f6a71b84e1afdf13827741e7421a844203cf8d0 Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Mon, 15 Jan 2018 18:10:13 +0100 -Subject: [PATCH] net: stmmac: dwmac-meson8b: fix internal RGMII clock - configuration -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -Tests (using an oscilloscope and an Odroid-C1 board with a RTL8211F -RGMII PHY) have shown that the PRG_ETH0 register behaves as follows: -- bit 4 is a mux to choose between two parent clocks. according to the - public S805 datasheet the only supported parent clock is MPLL2 (this - was not verified using the oscilloscope). - The public S805/S905 datasheet claims that this bit is reserved. -- bits 9:7 control a one-based divider (register value 1 means "divide - by 1", etc.) for the input clock. we call this clock the "m250_div" - clock because it's value is always supposed to be (close to) 250MHz - (see below for an explanation). - The description in the public S805/S905 datasheet is a bit cryptic, - but it comes down to "input clock = 250MHz * value" (which could also - be expressed as "250MHz = input clock / value") -- there seems to be an internal fixed divide-by-2 clock which takes the - output from the m250_div and divides it by 2. This is not unusual on - Amlogic SoCs, since the SDIO (MMC) driver also uses an internal fixed - divide-by-2 clock. - This is not documented in the public S805/S905 datasheet -- bit 10 controls a gate clock which enables or disables the RGMII TX - clock (which is an output on the MAC/SoC and an input in the PHY). we - call this the "rgmii_tx_en" clock. if this bit is set to "0" the RGMII - TX clock output is close to 0 - The description for this bit in the public S805/S905 datasheet is - "Generate 25MHz clock for PHY". Based on these tests it's believed - that this is wrong, and should probably read "Generate the 125MHz - RGMII TX clock for the PHY" -- the RGMII TX clock has to be set to 125MHz - the IP block adjusts the - output (automatically) depending on the line speed (RGMII specifies - that Gbit connections use a 125MHz clock, 100Mbit/s connections use a - 25MHz clock and 10Mbit/s connections use a 2.5MHz clock. only Gbit and - 100Mbit/s were tested with an oscilloscope). Due to the requirement - that this clock always has to be set to 125MHz and due to the fixed - divide-by-2 parent clock this means that m250_div will always end up - with a rate of (close to) 250MHz. -- bits 6:5 are the TX delay, which is also named "clock phase" in some - of Amlogic's older GPL kernel sources. - -The PHY also has an XTAL_IN pin where a 25MHz clock has to be provided. -Tests with the oscilloscope have shown that this is routed to a crystal -right next to the RTL8211F PHY. The same seems to be true on the Khadas -VIM2 (which uses a GXM SoC) board - however the 25MHz crystal is on the -other side of the PCB there. - -This updates the clocks in the dwmac-meson8b driver by replacing the -"m25_div" with the "rgmii_tx_en" clock and additionally introducing a -fixed divide-by-2 clock between "m250_div" and "rgmii_tx_en". -Now we also need to set a frequency of 125MHz on the RGMII clock -(opposed to the 25MHz we set before, with that non-existing -divide-by-5-or-10 divider). - -Special thanks go to Linus Lüssing for testing the various bits and -checking the results with an oscilloscope on his Odroid-C1! - -Fixes: 566e8251625304 ("net: stmmac: add a glue driver for the Amlogic Meson 8b / GXBB DWMAC") -Reported-by: Emiliano Ingrassia -Signed-off-by: Martin Blumenstingl -Acked-by: Jerome Brunet -Tested-by: Jerome Brunet -Signed-off-by: David S. Miller ---- - .../net/ethernet/stmicro/stmmac/dwmac-meson8b.c | 79 +++++++++++++--------- - 1 file changed, 47 insertions(+), 32 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-meson8b.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-meson8b.c -index c6f87e9c4ccb3..7930a152dd634 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac-meson8b.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-meson8b.c -@@ -40,9 +40,7 @@ - #define PRG_ETH0_CLK_M250_DIV_SHIFT 7 - #define PRG_ETH0_CLK_M250_DIV_WIDTH 3 - --/* divides the result of m25_sel by either 5 (bit unset) or 10 (bit set) */ --#define PRG_ETH0_CLK_M25_DIV_SHIFT 10 --#define PRG_ETH0_CLK_M25_DIV_WIDTH 1 -+#define PRG_ETH0_RGMII_TX_CLK_EN 10 - - #define PRG_ETH0_INVERTED_RMII_CLK BIT(11) - #define PRG_ETH0_TX_AND_PHY_REF_CLK BIT(12) -@@ -63,8 +61,11 @@ struct meson8b_dwmac { - struct clk_divider m250_div; - struct clk *m250_div_clk; - -- struct clk_divider m25_div; -- struct clk *m25_div_clk; -+ struct clk_fixed_factor fixed_div2; -+ struct clk *fixed_div2_clk; -+ -+ struct clk_gate rgmii_tx_en; -+ struct clk *rgmii_tx_en_clk; - - u32 tx_delay_ns; - }; -@@ -89,11 +90,6 @@ static int meson8b_init_rgmii_tx_clk(struct meson8b_dwmac *dwmac) - char clk_name[32]; - const char *clk_div_parents[1]; - const char *mux_parent_names[MUX_CLK_NUM_PARENTS]; -- static const struct clk_div_table clk_25m_div_table[] = { -- { .val = 0, .div = 5 }, -- { .val = 1, .div = 10 }, -- { /* sentinel */ }, -- }; - - /* get the mux parents from DT */ - for (i = 0; i < MUX_CLK_NUM_PARENTS; i++) { -@@ -150,25 +146,40 @@ static int meson8b_init_rgmii_tx_clk(struct meson8b_dwmac *dwmac) - if (WARN_ON(IS_ERR(dwmac->m250_div_clk))) - return PTR_ERR(dwmac->m250_div_clk); - -- /* create the m25_div */ -- snprintf(clk_name, sizeof(clk_name), "%s#m25_div", dev_name(dev)); -+ /* create the fixed_div2 */ -+ snprintf(clk_name, sizeof(clk_name), "%s#fixed_div2", dev_name(dev)); - init.name = devm_kstrdup(dev, clk_name, GFP_KERNEL); -- init.ops = &clk_divider_ops; -- init.flags = CLK_IS_BASIC | CLK_SET_RATE_PARENT; -+ init.ops = &clk_fixed_factor_ops; -+ init.flags = CLK_SET_RATE_PARENT; - clk_div_parents[0] = __clk_get_name(dwmac->m250_div_clk); - init.parent_names = clk_div_parents; - init.num_parents = ARRAY_SIZE(clk_div_parents); - -- dwmac->m25_div.reg = dwmac->regs + PRG_ETH0; -- dwmac->m25_div.shift = PRG_ETH0_CLK_M25_DIV_SHIFT; -- dwmac->m25_div.width = PRG_ETH0_CLK_M25_DIV_WIDTH; -- dwmac->m25_div.table = clk_25m_div_table; -- dwmac->m25_div.hw.init = &init; -- dwmac->m25_div.flags = CLK_DIVIDER_ALLOW_ZERO; -+ dwmac->fixed_div2.mult = 1; -+ dwmac->fixed_div2.div = 2; -+ dwmac->fixed_div2.hw.init = &init; - -- dwmac->m25_div_clk = devm_clk_register(dev, &dwmac->m25_div.hw); -- if (WARN_ON(IS_ERR(dwmac->m25_div_clk))) -- return PTR_ERR(dwmac->m25_div_clk); -+ dwmac->fixed_div2_clk = devm_clk_register(dev, &dwmac->fixed_div2.hw); -+ if (WARN_ON(IS_ERR(dwmac->fixed_div2_clk))) -+ return PTR_ERR(dwmac->fixed_div2_clk); -+ -+ /* create the rgmii_tx_en */ -+ init.name = devm_kasprintf(dev, GFP_KERNEL, "%s#rgmii_tx_en", -+ dev_name(dev)); -+ init.ops = &clk_gate_ops; -+ init.flags = CLK_SET_RATE_PARENT; -+ clk_div_parents[0] = __clk_get_name(dwmac->fixed_div2_clk); -+ init.parent_names = clk_div_parents; -+ init.num_parents = ARRAY_SIZE(clk_div_parents); -+ -+ dwmac->rgmii_tx_en.reg = dwmac->regs + PRG_ETH0; -+ dwmac->rgmii_tx_en.bit_idx = PRG_ETH0_RGMII_TX_CLK_EN; -+ dwmac->rgmii_tx_en.hw.init = &init; -+ -+ dwmac->rgmii_tx_en_clk = devm_clk_register(dev, -+ &dwmac->rgmii_tx_en.hw); -+ if (WARN_ON(IS_ERR(dwmac->rgmii_tx_en_clk))) -+ return PTR_ERR(dwmac->rgmii_tx_en_clk); - - return 0; - } -@@ -201,18 +212,22 @@ static int meson8b_init_prg_eth(struct meson8b_dwmac *dwmac) - meson8b_dwmac_mask_bits(dwmac, PRG_ETH0, PRG_ETH0_TXDLY_MASK, - tx_dly_val << PRG_ETH0_TXDLY_SHIFT); - -- ret = clk_prepare_enable(dwmac->m25_div_clk); -+ /* Configure the 125MHz RGMII TX clock, the IP block changes -+ * the output automatically (= without us having to configure -+ * a register) based on the line-speed (125MHz for Gbit speeds, -+ * 25MHz for 100Mbit/s and 2.5MHz for 10Mbit/s). -+ */ -+ ret = clk_set_rate(dwmac->rgmii_tx_en_clk, 125 * 1000 * 1000); - if (ret) { -- dev_err(&dwmac->pdev->dev, "failed to enable the PHY clock\n"); -+ dev_err(&dwmac->pdev->dev, -+ "failed to set RGMII TX clock\n"); - return ret; - } - -- /* Generate the 25MHz RGMII clock for the PHY */ -- ret = clk_set_rate(dwmac->m25_div_clk, 25 * 1000 * 1000); -+ ret = clk_prepare_enable(dwmac->rgmii_tx_en_clk); - if (ret) { -- clk_disable_unprepare(dwmac->m25_div_clk); -- -- dev_err(&dwmac->pdev->dev, "failed to set PHY clock\n"); -+ dev_err(&dwmac->pdev->dev, -+ "failed to enable the RGMII TX clock\n"); - return ret; - } - break; -@@ -306,7 +321,7 @@ static int meson8b_dwmac_probe(struct platform_device *pdev) - - err_clk_disable: - if (phy_interface_mode_is_rgmii(dwmac->phy_mode)) -- clk_disable_unprepare(dwmac->m25_div_clk); -+ clk_disable_unprepare(dwmac->rgmii_tx_en_clk); - err_remove_config_dt: - stmmac_remove_config_dt(pdev, plat_dat); - -@@ -318,7 +333,7 @@ static int meson8b_dwmac_remove(struct platform_device *pdev) - struct meson8b_dwmac *dwmac = get_stmmac_bsp_priv(&pdev->dev); - - if (phy_interface_mode_is_rgmii(dwmac->phy_mode)) -- clk_disable_unprepare(dwmac->m25_div_clk); -+ clk_disable_unprepare(dwmac->rgmii_tx_en_clk); - - return stmmac_pltfr_remove(pdev); - } diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/038_linux-4.14.y-backport-net-0018-net-stmmac-fix_reception_of_broadcom_switches_tags.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/038_linux-4.14.y-backport-net-0018-net-stmmac-fix_reception_of_broadcom_switches_tags.patch deleted file mode 100644 index 292b5a417..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/038_linux-4.14.y-backport-net-0018-net-stmmac-fix_reception_of_broadcom_switches_tags.patch +++ /dev/null @@ -1,168 +0,0 @@ -From 8cad443eacf661796a740903a75cb8944c675b4e Mon Sep 17 00:00:00 2001 -From: Florian Fainelli -Date: Thu, 18 Jan 2018 15:12:21 -0800 -Subject: [PATCH] net: stmmac: Fix reception of Broadcom switches tags - -Broadcom tags inserted by Broadcom switches put a 4 byte header after -the MAC SA and before the EtherType, which may look like some sort of 0 -length LLC/SNAP packet (tcpdump and wireshark do think that way). With -ACS enabled in stmmac the packets were truncated to 8 bytes on -reception, whereas clearing this bit allowed normal reception to occur. - -In order to make that possible, we need to pass a net_device argument to -the different core_init() functions and we are dependent on the Broadcom -tagger padding packets correctly (which it now does). To be as little -invasive as possible, this is only done for gmac1000 when the network -device is DSA-enabled (netdev_uses_dsa() returns true). - -Signed-off-by: Florian Fainelli -Acked-by: Giuseppe Cavallaro -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/common.h | 2 +- - drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c | 3 ++- - drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c | 12 +++++++++++- - drivers/net/ethernet/stmicro/stmmac/dwmac100_core.c | 15 +++++++++++++-- - drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c | 12 +++++++++++- - drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 2 +- - 6 files changed, 39 insertions(+), 7 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/common.h b/drivers/net/ethernet/stmicro/stmmac/common.h -index ce2ea2d491aca..2ffe76c0ff742 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/common.h -+++ b/drivers/net/ethernet/stmicro/stmmac/common.h -@@ -474,7 +474,7 @@ struct mac_device_info; - /* Helpers to program the MAC core */ - struct stmmac_ops { - /* MAC core initialization */ -- void (*core_init)(struct mac_device_info *hw, int mtu); -+ void (*core_init)(struct mac_device_info *hw, struct net_device *dev); - /* Enable the MAC RX/TX */ - void (*set_mac)(void __iomem *ioaddr, bool enable); - /* Enable and verify that the IPC module is supported */ -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -index 9eb7f65d8000d..a3fa65b1ca8e5 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-sun8i.c -@@ -483,7 +483,8 @@ static int sun8i_dwmac_init(struct platform_device *pdev, void *priv) - return 0; - } - --static void sun8i_dwmac_core_init(struct mac_device_info *hw, int mtu) -+static void sun8i_dwmac_core_init(struct mac_device_info *hw, -+ struct net_device *dev) - { - void __iomem *ioaddr = hw->pcsr; - u32 v; -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c b/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c -index 8a86340ff2d34..540d21786a43b 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c -@@ -25,18 +25,28 @@ - #include - #include - #include -+#include - #include - #include "stmmac_pcs.h" - #include "dwmac1000.h" - --static void dwmac1000_core_init(struct mac_device_info *hw, int mtu) -+static void dwmac1000_core_init(struct mac_device_info *hw, -+ struct net_device *dev) - { - void __iomem *ioaddr = hw->pcsr; - u32 value = readl(ioaddr + GMAC_CONTROL); -+ int mtu = dev->mtu; - - /* Configure GMAC core */ - value |= GMAC_CORE_INIT; - -+ /* Clear ACS bit because Ethernet switch tagging formats such as -+ * Broadcom tags can look like invalid LLC/SNAP packets and cause the -+ * hardware to truncate packets on reception. -+ */ -+ if (netdev_uses_dsa(dev)) -+ value &= ~GMAC_CONTROL_ACS; -+ - if (mtu > 1500) - value |= GMAC_CONTROL_2K; - if (mtu > 2000) -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac100_core.c b/drivers/net/ethernet/stmicro/stmmac/dwmac100_core.c -index 8ef5173563134..91b23f9db31ad 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac100_core.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac100_core.c -@@ -25,15 +25,26 @@ - *******************************************************************************/ - - #include -+#include - #include - #include "dwmac100.h" - --static void dwmac100_core_init(struct mac_device_info *hw, int mtu) -+static void dwmac100_core_init(struct mac_device_info *hw, -+ struct net_device *dev) - { - void __iomem *ioaddr = hw->pcsr; - u32 value = readl(ioaddr + MAC_CONTROL); - -- writel((value | MAC_CORE_INIT), ioaddr + MAC_CONTROL); -+ value |= MAC_CORE_INIT; -+ -+ /* Clear ASTP bit because Ethernet switch tagging formats such as -+ * Broadcom tags can look like invalid LLC/SNAP packets and cause the -+ * hardware to truncate packets on reception. -+ */ -+ if (netdev_uses_dsa(dev)) -+ value &= ~MAC_CONTROL_ASTP; -+ -+ writel(value, ioaddr + MAC_CONTROL); - - #ifdef STMMAC_VLAN_TAG_USED - writel(ETH_P_8021Q, ioaddr + MAC_VLAN1); -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c b/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -index f3ed8f7853eb4..ed222b20fcf19 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -@@ -17,16 +17,26 @@ - #include - #include - #include -+#include - #include "stmmac_pcs.h" - #include "dwmac4.h" - --static void dwmac4_core_init(struct mac_device_info *hw, int mtu) -+static void dwmac4_core_init(struct mac_device_info *hw, -+ struct net_device *dev) - { - void __iomem *ioaddr = hw->pcsr; - u32 value = readl(ioaddr + GMAC_CONFIG); -+ int mtu = dev->mtu; - - value |= GMAC_CORE_INIT; - -+ /* Clear ACS bit because Ethernet switch tagging formats such as -+ * Broadcom tags can look like invalid LLC/SNAP packets and cause the -+ * hardware to truncate packets on reception. -+ */ -+ if (netdev_uses_dsa(dev)) -+ value &= ~GMAC_CONFIG_ACS; -+ - if (mtu > 1500) - value |= GMAC_CONFIG_2K; - if (mtu > 2000) -diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -index f99f14c35063d..7ad841434ec8d 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -@@ -2527,7 +2527,7 @@ static int stmmac_hw_setup(struct net_device *dev, bool init_ptp) - } - - /* Initialize the MAC Core */ -- priv->hw->mac->core_init(priv->hw, dev->mtu); -+ priv->hw->mac->core_init(priv->hw, dev); - - /* Initialize MTL*/ - if (priv->synopsys_id >= DWMAC_CORE_4_00) diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/039_linux-4.14.y-backport-net-0019-net-stmmac-do_not_use_a_bitwise_and_operator_with_a_bool.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/039_linux-4.14.y-backport-net-0019-net-stmmac-do_not_use_a_bitwise_and_operator_with_a_bool.patch deleted file mode 100644 index 7ae271b9a..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/039_linux-4.14.y-backport-net-0019-net-stmmac-do_not_use_a_bitwise_and_operator_with_a_bool.patch +++ /dev/null @@ -1,59 +0,0 @@ -From d8f8b9542a4d8d560c0292a492f4edd922dd4ece Mon Sep 17 00:00:00 2001 -From: Niklas Cassel -Date: Mon, 22 Jan 2018 16:59:50 +0100 -Subject: [PATCH] net: stmmac: do not use a bitwise AND operator with a bool - operand - -Doing a bitwise AND between a bool and an int is generally not a good idea. -The bool will be promoted to an int with value 0 or 1, -the int is generally regarded as true with a non-zero value, -thus ANDing them has the potential to yield an undesired result. - -This commit fixes the following smatch warnings: - -drivers/net/ethernet/stmicro/stmmac/enh_desc.c:344 enh_desc_prepare_tx_desc() warn: maybe use && instead of & -drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c:337 dwmac4_rd_prepare_tx_desc() warn: maybe use && instead of & -drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c:380 dwmac4_rd_prepare_tso_tx_desc() warn: maybe use && instead of & - -Signed-off-by: Niklas Cassel -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c | 4 ++-- - drivers/net/ethernet/stmicro/stmmac/enh_desc.c | 2 +- - 2 files changed, 3 insertions(+), 3 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c b/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c -index 2fd8456999f69..c728ffa095de0 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c -@@ -334,7 +334,7 @@ static void dwmac4_rd_prepare_tx_desc(struct dma_desc *p, int is_fs, int len, - if (tx_own) - tdes3 |= TDES3_OWN; - -- if (is_fs & tx_own) -+ if (is_fs && tx_own) - /* When the own bit, for the first frame, has to be set, all - * descriptors for the same frame has to be set before, to - * avoid race condition. -@@ -377,7 +377,7 @@ static void dwmac4_rd_prepare_tso_tx_desc(struct dma_desc *p, int is_fs, - if (tx_own) - tdes3 |= TDES3_OWN; - -- if (is_fs & tx_own) -+ if (is_fs && tx_own) - /* When the own bit, for the first frame, has to be set, all - * descriptors for the same frame has to be set before, to - * avoid race condition. -diff --git a/drivers/net/ethernet/stmicro/stmmac/enh_desc.c b/drivers/net/ethernet/stmicro/stmmac/enh_desc.c -index b47cb5c4da513..6768a25b6aa09 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/enh_desc.c -+++ b/drivers/net/ethernet/stmicro/stmmac/enh_desc.c -@@ -341,7 +341,7 @@ static void enh_desc_prepare_tx_desc(struct dma_desc *p, int is_fs, int len, - if (tx_own) - tdes0 |= ETDES0_OWN; - -- if (is_fs & tx_own) -+ if (is_fs && tx_own) - /* When the own bit, for the first frame, has to be set, all - * descriptors for the same frame has to be set before, to - * avoid race condition. diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/040_linux-4.14.y-backport-net-0020-net-stmmac-rename_gmac_int_default_mask_for_dwmac4.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/040_linux-4.14.y-backport-net-0020-net-stmmac-rename_gmac_int_default_mask_for_dwmac4.patch deleted file mode 100644 index 6eddc7a3b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/040_linux-4.14.y-backport-net-0020-net-stmmac-rename_gmac_int_default_mask_for_dwmac4.patch +++ /dev/null @@ -1,46 +0,0 @@ -From e879b7ab3739d8f9990961fc7df2f63861bd780b Mon Sep 17 00:00:00 2001 -From: Niklas Cassel -Date: Fri, 9 Feb 2018 17:22:46 +0100 -Subject: [PATCH] net: stmmac: rename GMAC_INT_DEFAULT_MASK for dwmac4 - -GMAC_INT_DEFAULT_MASK is written to the interrupt enable register. -In previous versions of the IP (e.g. dwmac1000), this register was -instead an interrupt mask register. -To improve clarity and reflect reality, rename GMAC_INT_DEFAULT_MASK -to GMAC_INT_DEFAULT_ENABLE. - -Signed-off-by: Niklas Cassel -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/dwmac4.h | 2 +- - drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c | 4 ++-- - 2 files changed, 3 insertions(+), 3 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4.h b/drivers/net/ethernet/stmicro/stmmac/dwmac4.h -index 789dad8a07b5c..7761a26ec9c56 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac4.h -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4.h -@@ -98,7 +98,7 @@ - #define GMAC_PCS_IRQ_DEFAULT (GMAC_INT_RGSMIIS | GMAC_INT_PCS_LINK | \ - GMAC_INT_PCS_ANE) - --#define GMAC_INT_DEFAULT_MASK (GMAC_INT_PMT_EN | GMAC_INT_LPI_EN) -+#define GMAC_INT_DEFAULT_ENABLE (GMAC_INT_PMT_EN | GMAC_INT_LPI_EN) - - enum dwmac4_irq_status { - time_stamp_irq = 0x00001000, -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c b/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -index 1e0a7668b7529..6badc63d8e6d3 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -@@ -61,8 +61,8 @@ static void dwmac4_core_init(struct mac_device_info *hw, - - writel(value, ioaddr + GMAC_CONFIG); - -- /* Mask GMAC interrupts */ -- value = GMAC_INT_DEFAULT_MASK; -+ /* Enable GMAC interrupts */ -+ value = GMAC_INT_DEFAULT_ENABLE; - if (hw->pmt) - value |= GMAC_INT_PMT_EN; - if (hw->pcs) diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/041_linux-4.14.y-backport-net-0021-net-stmmac-remove_redundant_enable_of_pmt_irq.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/041_linux-4.14.y-backport-net-0021-net-stmmac-remove_redundant_enable_of_pmt_irq.patch deleted file mode 100644 index a50ae8011..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/041_linux-4.14.y-backport-net-0021-net-stmmac-remove_redundant_enable_of_pmt_irq.patch +++ /dev/null @@ -1,49 +0,0 @@ -From 1029117127540fef4edcf4f0887dc3e1f7d5adb2 Mon Sep 17 00:00:00 2001 -From: Niklas Cassel -Date: Fri, 9 Feb 2018 17:22:47 +0100 -Subject: [PATCH] net: stmmac: remove redundant enable of PMT irq - -For dwmac4, GMAC_INT_DEFAULT_ENABLE already includes -GMAC_INT_PMT_EN, so it is redundant to check if hw->pmt -is set, and if so, setting the bit again. - -For dwmac1000, GMAC_INT_DEFAULT_MASK does not include -GMAC_INT_DISABLE_PMT, so it is redundant to check if -hw->pmt is set, and if so, clearing an already cleared bit. - -Improve code readability by removing this redundant code. - -Signed-off-by: Niklas Cassel -Signed-off-by: David S. Miller ---- - drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c | 2 -- - drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c | 3 +-- - 2 files changed, 1 insertion(+), 4 deletions(-) - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c b/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c -index 540d21786a43b..ef10baf141862 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac1000_core.c -@@ -74,8 +74,6 @@ static void dwmac1000_core_init(struct mac_device_info *hw, - /* Mask GMAC interrupts */ - value = GMAC_INT_DEFAULT_MASK; - -- if (hw->pmt) -- value &= ~GMAC_INT_DISABLE_PMT; - if (hw->pcs) - value &= ~GMAC_INT_DISABLE_PCS; - -diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c b/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -index 6badc63d8e6d3..63795ecafc8dc 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -+++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c -@@ -63,8 +63,7 @@ static void dwmac4_core_init(struct mac_device_info *hw, - - /* Enable GMAC interrupts */ - value = GMAC_INT_DEFAULT_ENABLE; -- if (hw->pmt) -- value |= GMAC_INT_PMT_EN; -+ - if (hw->pcs) - value |= GMAC_PCS_IRQ_DEFAULT; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/042_linux-4.14.y-backport-net-1000-net-stmmac-setup_timer_-_timer_setup.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/042_linux-4.14.y-backport-net-1000-net-stmmac-setup_timer_-_timer_setup.patch deleted file mode 100644 index 7bff6097d..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/042_linux-4.14.y-backport-net-1000-net-stmmac-setup_timer_-_timer_setup.patch +++ /dev/null @@ -1,60 +0,0 @@ -From e99e88a9d2b067465adaa9c111ada99a041bef9a Mon Sep 17 00:00:00 2001 -From: Kees Cook -Date: Mon, 16 Oct 2017 14:43:17 -0700 -Subject: [PATCH] net: stmmac: setup_timer() -> timer_setup() - -This converts all remaining cases of the old setup_timer() API into using -timer_setup(), where the callback argument is the structure already -holding the struct timer_list. These should have no behavioral changes, -since they just change which pointer is passed into the callback with -the same available pointers after conversion. - -diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -index ff4fb5eae1af3..f63c2ddced3c9 100644 ---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c -@@ -345,9 +345,9 @@ void stmmac_disable_eee_mode(struct stmmac_priv *priv) - * if there is no data transfer and if we are not in LPI state, - * then MAC Transmitter can be moved to LPI state. - */ --static void stmmac_eee_ctrl_timer(unsigned long arg) -+static void stmmac_eee_ctrl_timer(struct timer_list *t) - { -- struct stmmac_priv *priv = (struct stmmac_priv *)arg; -+ struct stmmac_priv *priv = from_timer(priv, t, eee_ctrl_timer); - - stmmac_enable_eee_mode(priv); - mod_timer(&priv->eee_ctrl_timer, STMMAC_LPI_T(eee_timer)); -@@ -401,9 +401,8 @@ bool stmmac_eee_init(struct stmmac_priv *priv) - spin_lock_irqsave(&priv->lock, flags); - if (!priv->eee_active) { - priv->eee_active = 1; -- setup_timer(&priv->eee_ctrl_timer, -- stmmac_eee_ctrl_timer, -- (unsigned long)priv); -+ timer_setup(&priv->eee_ctrl_timer, -+ stmmac_eee_ctrl_timer, 0); - mod_timer(&priv->eee_ctrl_timer, - STMMAC_LPI_T(eee_timer)); - -@@ -2221,9 +2220,9 @@ static int stmmac_init_dma_engine(struct stmmac_priv *priv) - * Description: - * This is the timer handler to directly invoke the stmmac_tx_clean. - */ --static void stmmac_tx_timer(unsigned long data) -+static void stmmac_tx_timer(struct timer_list *t) - { -- struct stmmac_priv *priv = (struct stmmac_priv *)data; -+ struct stmmac_priv *priv = from_timer(priv, t, txtimer); - u32 tx_queues_count = priv->plat->tx_queues_to_use; - u32 queue; - -@@ -2244,7 +2243,7 @@ static void stmmac_init_tx_coalesce(struct stmmac_priv *priv) - { - priv->tx_coal_frames = STMMAC_TX_FRAMES; - priv->tx_coal_timer = STMMAC_COAL_TX_TIMER; -- setup_timer(&priv->txtimer, stmmac_tx_timer, (unsigned long)priv); -+ timer_setup(&priv->txtimer, stmmac_tx_timer, 0); - priv->txtimer.expires = STMMAC_COAL_TIMER(priv->tx_coal_timer); - add_timer(&priv->txtimer); - } diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/043_linux-4.14.y-backport-net-1001-net-stmmac-replace_all_pr_xxx_by_their_netdev_xxx.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/043_linux-4.14.y-backport-net-1001-net-stmmac-replace_all_pr_xxx_by_their_netdev_xxx.patch deleted file mode 100644 index af1431118..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/043_linux-4.14.y-backport-net-1001-net-stmmac-replace_all_pr_xxx_by_their_netdev_xxx.patch +++ /dev/null @@ -1,15 +0,0 @@ -diff -urN a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c ---- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c 2018-05-01 18:26:12.093131654 +0200 -+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c 2018-04-29 05:32:21.590669392 +0200 -@@ -3442,9 +3442,8 @@ - if (netif_msg_rx_status(priv)) { - netdev_dbg(priv->dev, "\tdesc: %p [entry %d] buff=0x%x\n", - p, entry, des); -- if (frame_len > ETH_FRAME_LEN) -- netdev_dbg(priv->dev, "frame size %d, COE: %d\n", -- frame_len, status); -+ netdev_dbg(priv->dev, "frame size %d, COE: %d\n", -+ frame_len, status); - } - - /* The zero-copy is always used for all the sizes diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/044_linux-4.14.y-bpo-dts-0001-arm64-dts-meson-gxl-libretech-cc-enable_saradc.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/044_linux-4.14.y-bpo-dts-0001-arm64-dts-meson-gxl-libretech-cc-enable_saradc.patch deleted file mode 100644 index 421ccc6ba..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/044_linux-4.14.y-bpo-dts-0001-arm64-dts-meson-gxl-libretech-cc-enable_saradc.patch +++ /dev/null @@ -1,45 +0,0 @@ -From dd47e4a36afd6c606f20e6d58e58f8e7e472c8fe Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Tue, 5 Sep 2017 19:09:55 +0200 -Subject: [PATCH] ARM64: dts: meson-gxl-libretech-cc: enable saradc - -Enable saradc and add the reference 1.8v regulator required. -The libretech-cc has saradc channel 0 and 2 available on the 2 first -pins of 2J3 header - -Signed-off-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 12 ++++++++++++ - 1 file changed, 12 insertions(+) - -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 64c54c92e214d..a8aa9ce5f55e3 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 -@@ -96,6 +96,13 @@ - regulator-settling-time-down-us = <50000>; - }; - -+ 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"; -@@ -196,6 +203,11 @@ - "7J1 Header Pin15"; - }; - -+&saradc { -+ status = "okay"; -+ vref-supply = <&vddio_ao18>; -+}; -+ - /* SD card */ - &sd_emmc_b { - status = "okay"; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/045_linux-4.14.y-bpo-dts-0002-arm64-dts-meson-gxl-libretech-cc-enable_internal_phy_leds.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/045_linux-4.14.y-bpo-dts-0002-arm64-dts-meson-gxl-libretech-cc-enable_internal_phy_leds.patch deleted file mode 100644 index 440f4c98f..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/045_linux-4.14.y-bpo-dts-0002-arm64-dts-meson-gxl-libretech-cc-enable_internal_phy_leds.patch +++ /dev/null @@ -1,29 +0,0 @@ -From dac161871fb592816826ef11b742554fb3dc2fe3 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Wed, 6 Sep 2017 14:25:47 +0200 -Subject: [PATCH] ARM64: dts: meson-gxl-libretech-cc: enable internal phy leds - -Enable the internal phy ACT and LINK leds pinmux - -Signed-off-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 5 +++++ - 1 file changed, 5 insertions(+) - -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 a8aa9ce5f55e3..6d023fa27067b 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 -@@ -128,6 +128,11 @@ - status = "okay"; - }; - -+&internal_phy { -+ pinctrl-0 = <ð_link_led_pins>, <ð_act_led_pins>; -+ pinctrl-names = "default"; -+}; -+ - &ir { - status = "okay"; - pinctrl-0 = <&remote_input_ao_pins>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/046_linux-4.14.y-bpo-dts-0003-arm64-dts-meson-gxbb-adjust_nanopi-k2_gpio-line-names.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/046_linux-4.14.y-bpo-dts-0003-arm64-dts-meson-gxbb-adjust_nanopi-k2_gpio-line-names.patch deleted file mode 100644 index acdff4b8e..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/046_linux-4.14.y-bpo-dts-0003-arm64-dts-meson-gxbb-adjust_nanopi-k2_gpio-line-names.patch +++ /dev/null @@ -1,43 +0,0 @@ -From 1ce2c00878dbd4f8adfd2f0d64f01855072340a5 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 21 Sep 2017 19:14:47 +0200 -Subject: [PATCH] ARM64: dts: meson-gxbb: adjust nanopi-k2 gpio-line-names - -GPIOX22 is now declared properly and TEST_N has been moved so -the gpio-line-names of the nanopi-k2 must be adjusted accordingly - -Signed-off-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts | 10 +++++----- - 1 file changed, 5 insertions(+), 5 deletions(-) - -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 4b17a76959b2f..745d77f7cde13 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -@@ -183,7 +183,9 @@ - "VCCK En", "CON1 Header Pin31", - "I2S Header Pin6", "IR In", "I2S Header Pin7", - "I2S Header Pin3", "I2S Header Pin4", -- "I2S Header Pin5", "HDMI CEC", "SYS LED"; -+ "I2S Header Pin5", "HDMI CEC", "SYS LED", -+ /* GPIO_TEST_N */ -+ ""; - }; - - &pinctrl_periphs { -@@ -229,11 +231,9 @@ - "Bluetooth UART TX", "Bluetooth UART RX", - "Bluetooth UART CTS", "Bluetooth UART RTS", - "", "", "", "WIFI 32K", "Bluetooth Enable", -- "Bluetooth WAKE HOST", -+ "Bluetooth WAKE HOST", "", - /* Bank GPIOCLK */ -- "", "CON1 Header Pin35", "", "", -- /* GPIO_TEST_N */ -- ""; -+ "", "CON1 Header Pin35", "", ""; - }; - - &pwm_ef { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/047_linux-4.14.y-bpo-dts-0004-arm64-dts-meson-gxbb-adjust_odroid-c2_gpio-line-names.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/047_linux-4.14.y-bpo-dts-0004-arm64-dts-meson-gxbb-adjust_odroid-c2_gpio-line-names.patch deleted file mode 100644 index aad3e9581..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/047_linux-4.14.y-bpo-dts-0004-arm64-dts-meson-gxbb-adjust_odroid-c2_gpio-line-names.patch +++ /dev/null @@ -1,43 +0,0 @@ -From e43f20e844290655eecdd8a5038bc80964837889 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 21 Sep 2017 19:14:48 +0200 -Subject: [PATCH] ARM64: dts: meson-gxbb: adjust odroid-c2 gpio-line-names - -GPIOX22 is now declared properly and TEST_N has been moved so -the gpio-line-names of the odroid-c2 must be adjusted accordingly - -Signed-off-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts | 10 +++++----- - 1 file changed, 5 insertions(+), 5 deletions(-) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -index 1ffa1c238a725..a2f75194bc0cc 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -@@ -194,7 +194,9 @@ - "USB HUB nRESET", "USB OTG Power En", - "J7 Header Pin2", "IR In", "J7 Header Pin4", - "J7 Header Pin6", "J7 Header Pin5", "J7 Header Pin7", -- "HDMI CEC", "SYS LED"; -+ "HDMI CEC", "SYS LED", -+ /* GPIO_TEST_N */ -+ ""; - }; - - &pinctrl_periphs { -@@ -233,11 +235,9 @@ - "J2 Header Pin12", "J2 Header Pin13", - "J2 Header Pin8", "J2 Header Pin10", - "", "", "", "", "", -- "J2 Header Pin11", "", "J2 Header Pin7", -+ "J2 Header Pin11", "", "J2 Header Pin7", "", - /* Bank GPIOCLK */ -- "", "", "", "", -- /* GPIO_TEST_N */ -- ""; -+ "", "", "", ""; - }; - - &saradc { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/048_linux-4.14.y-bpo-dts-0005-arm64-dts-meson-gxl-adjust_kvim_gpio-line-names.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/048_linux-4.14.y-bpo-dts-0005-arm64-dts-meson-gxl-adjust_kvim_gpio-line-names.patch deleted file mode 100644 index fc42dce94..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/048_linux-4.14.y-bpo-dts-0005-arm64-dts-meson-gxl-adjust_kvim_gpio-line-names.patch +++ /dev/null @@ -1,40 +0,0 @@ -From c6496b47aeaef38fcd5a4fa5a90c82caebde538f Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 21 Sep 2017 19:14:49 +0200 -Subject: [PATCH] ARM64: dts: meson-gxl: adjust kvim gpio-line-names - -TEST_N gpio has been moved so the gpio-line-names of the kvim -must be adjusted accordingly - -Signed-off-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts | 8 ++++---- - 1 file changed, 4 insertions(+), 4 deletions(-) - -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 edc512ad0bac3..71a6e1ce7ad58 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 -@@ -122,7 +122,9 @@ - "J9 Header Pin33", - "IR In", - "HDMI CEC", -- "SYS LED"; -+ "SYS LED", -+ /* GPIO_TEST_N */ -+ ""; - }; - - &pinctrl_periphs { -@@ -163,9 +165,7 @@ - "WIFI 32K", "Bluetooth Enable", - "Bluetooth WAKE HOST", - /* Bank GPIOCLK */ -- "", "J9 Header Pin39", -- /* GPIO_TEST_N */ -- ""; -+ "", "J9 Header Pin39"; - }; - - &pwm_AO_ab { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/049_linux-4.14.y-bpo-dts-0006-arm64-dts-meson-gxl-adjust_libretech-cc_gpio-line-names.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/049_linux-4.14.y-bpo-dts-0006-arm64-dts-meson-gxl-adjust_libretech-cc_gpio-line-names.patch deleted file mode 100644 index 5702f0861..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/049_linux-4.14.y-bpo-dts-0006-arm64-dts-meson-gxl-adjust_libretech-cc_gpio-line-names.patch +++ /dev/null @@ -1,40 +0,0 @@ -From 1d70eaada70a355acd95a9022a84e476858ceba1 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 21 Sep 2017 19:16:04 +0200 -Subject: [PATCH] ARM64: dts: meson-gxl: adjust libretech-cc gpio-line-names - -TEST_N gpio has been moved so the gpio-line-names of the cc -must be adjusted accordingly - -Signed-off-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 8 ++++---- - 1 file changed, 4 insertions(+), 4 deletions(-) - -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 6d023fa27067b..c862540749384 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 -@@ -161,7 +161,9 @@ - "7J1 Header Pin12", - "IR In", - "9J3 Switch HDMI CEC/7J1 Header Pin11", -- "7J1 Header Pin13"; -+ "7J1 Header Pin13", -+ /* GPIO_TEST_N */ -+ "7J1 Header Pin15"; - }; - - &pinctrl_periphs { -@@ -203,9 +205,7 @@ - "7J1 Header Pin32", "7J1 Header Pin29", - "7J1 Header Pin31", - /* Bank GPIOCLK */ -- "7J1 Header Pin7", "", -- /* GPIO_TEST_N */ -- "7J1 Header Pin15"; -+ "7J1 Header Pin7", ""; - }; - - &saradc { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/050_linux-4.14.y-bpo-dts-0007-arm64-dts-meson-gxl-take_emmc_data_strobe_out_of_emmc_pins.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/050_linux-4.14.y-bpo-dts-0007-arm64-dts-meson-gxl-take_emmc_data_strobe_out_of_emmc_pins.patch deleted file mode 100644 index 60e4e1a32..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/050_linux-4.14.y-bpo-dts-0007-arm64-dts-meson-gxl-take_emmc_data_strobe_out_of_emmc_pins.patch +++ /dev/null @@ -1,226 +0,0 @@ -From ab36be660bad40133e1c6a028ba79e46c5d6f3c7 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Tue, 3 Oct 2017 17:24:42 +0200 -Subject: [PATCH] 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 -Tested-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - 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 4157987f4a3d2..7d4b95e499935 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 745d77f7cde13..2e853c082a654 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 38dfdde5c1473..9a773239dcef9 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 a2f75194bc0cc..1deaa53c9fb56 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 23c08c3afd0ab..932158a778ef8 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 f2bc6dea1fc62..1fe8e24cf675c 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 99ec6216c84a2..3d41db9c9d226 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -@@ -386,8 +386,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 977b4240f3c1b..e82582574160c 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 c862540749384..dc9c3b8216c2b 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 -@@ -238,7 +238,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 1b8f32867aa10..271f142791808 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 129af9068814d..ff09df1fd5a32 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 e7cfe87be3b44..19c001abb0c51 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -275,8 +275,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 22c697732f668..e7a228f6cc7e7 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 470f72bb863c5..a5e9b955d5ed3 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>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/051_linux-4.14.y-bpo-dts-0008-arm64-dts-meson-gxm-add_support_for_khadas_vim2.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/051_linux-4.14.y-bpo-dts-0008-arm64-dts-meson-gxm-add_support_for_khadas_vim2.patch deleted file mode 100644 index ffb48af7c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/051_linux-4.14.y-bpo-dts-0008-arm64-dts-meson-gxm-add_support_for_khadas_vim2.patch +++ /dev/null @@ -1,454 +0,0 @@ -From b8b74dda3908660f49a5d5cec28725e3950e00d5 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Tue, 3 Oct 2017 17:24:43 +0200 -Subject: [PATCH] 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 -Tested-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - 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 4e4bc0bae597a..a44599739746b 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 7a9f48c27b1f5..70246e3ecd5c6 100644 ---- a/arch/arm64/boot/dts/amlogic/Makefile -+++ b/arch/arm64/boot/dts/amlogic/Makefile -@@ -15,6 +15,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 0000000000000..32c138ec0e587 ---- /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>; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/052_linux-4.14.y-bpo-dts-0009-arm64-dts-meson-gxbb-nexbox-a95x-enable_usb_nodes.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/052_linux-4.14.y-bpo-dts-0009-arm64-dts-meson-gxbb-nexbox-a95x-enable_usb_nodes.patch deleted file mode 100644 index 9ec860c2f..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/052_linux-4.14.y-bpo-dts-0009-arm64-dts-meson-gxbb-nexbox-a95x-enable_usb_nodes.patch +++ /dev/null @@ -1,59 +0,0 @@ -From e2f4d749e73a468902f2d2453b1575602427c069 Mon Sep 17 00:00:00 2001 -From: Peter Korsgaard -Date: Thu, 5 Oct 2017 15:21:18 +0200 -Subject: [PATCH] ARM64: dts: meson-gxbb-nexbox-a95x: Enable USB Nodes - -Enable both gxbb USB controllers and add a 5V regulator for the OTG port -VBUS, similar to p20x. - -Signed-off-by: Peter Korsgaard -Acked-by: Neil Armstrong -Signed-off-by: Kevin Hilman ---- - .../boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts | 29 ++++++++++++++++++++++ - 1 file changed, 29 insertions(+) - -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 9a773239dcef9..818954b1d57f8 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts -@@ -88,6 +88,18 @@ - }; - }; - -+ usb_pwr: regulator-usb-pwrs { -+ compatible = "regulator-fixed"; -+ -+ regulator-name = "USB_PWR"; -+ -+ regulator-min-microvolt = <5000000>; -+ regulator-max-microvolt = <5000000>; -+ -+ gpio = <&gpio GPIODV_24 GPIO_ACTIVE_HIGH>; -+ enable-active-high; -+ }; -+ - vddio_card: gpio-regulator { - compatible = "regulator-gpio"; - -@@ -294,3 +306,20 @@ - pinctrl-0 = <&uart_ao_a_pins>; - pinctrl-names = "default"; - }; -+ -+&usb0_phy { -+ status = "okay"; -+ phy-supply = <&usb_pwr>; -+}; -+ -+&usb1_phy { -+ status = "okay"; -+}; -+ -+&usb0 { -+ status = "okay"; -+}; -+ -+&usb1 { -+ status = "okay"; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/053_linux-4.14.y-bpo-dts-0010-arm64-dts-meson-gxm-enable_hs400_on_the_vim2.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/053_linux-4.14.y-bpo-dts-0010-arm64-dts-meson-gxm-enable_hs400_on_the_vim2.patch deleted file mode 100644 index 0ce3c8a49..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/053_linux-4.14.y-bpo-dts-0010-arm64-dts-meson-gxm-enable_hs400_on_the_vim2.patch +++ /dev/null @@ -1,25 +0,0 @@ -From a1d759cf528064e73c06d318cd03213c4eafbc35 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Tue, 10 Oct 2017 16:18:22 +0200 -Subject: [PATCH] ARM64: dts: meson-gxm: enable HS400 on the vim2 - -Enable HS400 high speed eMMC mode on the khadas vim2 - -Signed-off-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts | 1 + - 1 file changed, 1 insertion(+) - -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 32c138ec0e587..34a41b26a4ed2 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -@@ -348,6 +348,7 @@ - disable-wp; - mmc-ddr-1_8v; - mmc-hs200-1_8v; -+ mmc-hs400-1_8v; - - mmc-pwrseq = <&emmc_pwrseq>; - vmmc-supply = <&vcc_3v3>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/054_linux-4.14.y-bpo-dts-0011-arm64-dts-meson-gx-remove_unnecessary_clocks_properties.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/054_linux-4.14.y-bpo-dts-0011-arm64-dts-meson-gx-remove_unnecessary_clocks_properties.patch deleted file mode 100644 index 265485c24..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/054_linux-4.14.y-bpo-dts-0011-arm64-dts-meson-gx-remove_unnecessary_clocks_properties.patch +++ /dev/null @@ -1,44 +0,0 @@ -From ab29891e953fd7c3410f3edeb50457812f7694d8 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Wed, 11 Oct 2017 17:39:39 +0200 -Subject: [PATCH] ARM64: dts: meson-gx: remove unnecessary clocks properties - -Since the switch to documented uart bindings, the clocks are -redefined in the SoC family dtsi file. - -This patch removes these unneeded properties. - -Signed-off-by: Neil Armstrong -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 3 --- - 1 file changed, 3 deletions(-) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -index f175db8462861..2be981a547dfc 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -228,7 +228,6 @@ - compatible = "amlogic,meson-gx-uart", "amlogic,meson-uart"; - reg = <0x0 0x84c0 0x0 0x14>; - interrupts = ; -- clocks = <&xtal>; - status = "disabled"; - }; - -@@ -236,7 +235,6 @@ - compatible = "amlogic,meson-gx-uart", "amlogic,meson-uart"; - reg = <0x0 0x84dc 0x0 0x14>; - interrupts = ; -- clocks = <&xtal>; - status = "disabled"; - }; - -@@ -282,7 +280,6 @@ - compatible = "amlogic,meson-gx-uart", "amlogic,meson-uart"; - reg = <0x0 0x8700 0x0 0x14>; - interrupts = ; -- clocks = <&xtal>; - status = "disabled"; - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/055_linux-4.14.y-bpo-dts-0012-arm64-dts-meson-gx-remove_unnecessary_uart_compatible.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/055_linux-4.14.y-bpo-dts-0012-arm64-dts-meson-gx-remove_unnecessary_uart_compatible.patch deleted file mode 100644 index 10514abf9..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/055_linux-4.14.y-bpo-dts-0012-arm64-dts-meson-gx-remove_unnecessary_uart_compatible.patch +++ /dev/null @@ -1,63 +0,0 @@ -From a87f854ddcf7ff7e044d72db0aa6da82f26d69a6 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Wed, 11 Oct 2017 17:39:40 +0200 -Subject: [PATCH] ARM64: dts: meson-gx: remove unnecessary uart compatible - -Since the switch to documented uart bindings, the old undocumented -compatible binding was left for simplicity. - -This patch removes these unneeded compatible strings. - -Signed-off-by: Neil Armstrong -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 10 +++++----- - 1 file changed, 5 insertions(+), 5 deletions(-) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -index 2be981a547dfc..b7723436a04b2 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -225,14 +225,14 @@ - }; - - uart_A: serial@84c0 { -- compatible = "amlogic,meson-gx-uart", "amlogic,meson-uart"; -+ compatible = "amlogic,meson-gx-uart"; - reg = <0x0 0x84c0 0x0 0x14>; - interrupts = ; - status = "disabled"; - }; - - uart_B: serial@84dc { -- compatible = "amlogic,meson-gx-uart", "amlogic,meson-uart"; -+ compatible = "amlogic,meson-gx-uart"; - reg = <0x0 0x84dc 0x0 0x14>; - interrupts = ; - status = "disabled"; -@@ -277,7 +277,7 @@ - }; - - uart_C: serial@8700 { -- compatible = "amlogic,meson-gx-uart", "amlogic,meson-uart"; -+ compatible = "amlogic,meson-gx-uart"; - reg = <0x0 0x8700 0x0 0x14>; - interrupts = ; - status = "disabled"; -@@ -388,14 +388,14 @@ - }; - - uart_AO: serial@4c0 { -- compatible = "amlogic,meson-gx-uart", "amlogic,meson-ao-uart", "amlogic,meson-uart"; -+ compatible = "amlogic,meson-gx-uart", "amlogic,meson-ao-uart"; - reg = <0x0 0x004c0 0x0 0x14>; - interrupts = ; - status = "disabled"; - }; - - uart_AO_B: serial@4e0 { -- compatible = "amlogic,meson-gx-uart", "amlogic,meson-ao-uart", "amlogic,meson-uart"; -+ compatible = "amlogic,meson-gx-uart", "amlogic,meson-ao-uart"; - reg = <0x0 0x004e0 0x0 0x14>; - interrupts = ; - status = "disabled"; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/056_linux-4.14.y-bpo-dts-0013-arm64-dts-meson-gx-add_gpio_interrupt_controller.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/056_linux-4.14.y-bpo-dts-0013-arm64-dts-meson-gx-add_gpio_interrupt_controller.patch deleted file mode 100644 index 5850e71ae..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/056_linux-4.14.y-bpo-dts-0013-arm64-dts-meson-gx-add_gpio_interrupt_controller.patch +++ /dev/null @@ -1,70 +0,0 @@ -From 9dbb56ea0917a036dc966663a09baf3d5a471f54 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 19 Oct 2017 14:01:42 +0200 -Subject: [PATCH] ARM64: dts: meson-gx: add gpio interrupt controller - -Add gpio interrupt controller to Amlogic GX family SoCs - -Signed-off-by: Jerome Brunet -Reviewed-by: Neil Armstrong -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 9 +++++++++ - arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 6 ++++++ - arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 6 ++++++ - 3 files changed, 21 insertions(+) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -index b7723436a04b2..ab7ce1644cdc5 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -218,6 +218,15 @@ - #size-cells = <2>; - ranges = <0x0 0x0 0x0 0xc1100000 0x0 0x100000>; - -+ gpio_intc: interrupt-controller@9880 { -+ compatible = "amlogic,meson-gpio-intc"; -+ reg = <0x0 0x9880 0x0 0x10>; -+ interrupt-controller; -+ #interrupt-cells = <2>; -+ amlogic,channel-interrupts = <64 65 66 67 68 69 70 71>; -+ status = "disabled"; -+ }; -+ - reset: reset-controller@4404 { - compatible = "amlogic,meson-gx-reset", "amlogic,meson-gxbb-reset"; - reg = <0x0 0x04404 0x0 0x20>; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -index 3d41db9c9d226..ead895a4e9a5c 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -@@ -323,6 +323,12 @@ - clock-names = "stmmaceth", "clkin0", "clkin1"; - }; - -+&gpio_intc { -+ compatible = "amlogic,meson-gpio-intc", -+ "amlogic,meson-gxbb-gpio-intc"; -+ status = "okay"; -+}; -+ - &hdmi_tx { - compatible = "amlogic,meson-gxbb-dw-hdmi", "amlogic,meson-gx-dw-hdmi"; - resets = <&reset RESET_HDMITX_CAPB3>, -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -index d3a51031a7111..0aa71a35ce64c 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -225,6 +225,12 @@ - compatible = "amlogic,meson-gxl-aoclkc", "amlogic,meson-gx-aoclkc"; - }; - -+&gpio_intc { -+ compatible = "amlogic,meson-gpio-intc", -+ "amlogic,meson-gxl-gpio-intc"; -+ status = "okay"; -+}; -+ - &hdmi_tx { - compatible = "amlogic,meson-gxl-dw-hdmi", "amlogic,meson-gx-dw-hdmi"; - resets = <&reset RESET_HDMITX_CAPB3>, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/057_linux-4.14.y-bpo-dts-0014-arm64-dts-meson-gx-add_external_phy_interrupt_on_some.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/057_linux-4.14.y-bpo-dts-0014-arm64-dts-meson-gx-add_external_phy_interrupt_on_some.patch deleted file mode 100644 index ecbeff4d5..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/057_linux-4.14.y-bpo-dts-0014-arm64-dts-meson-gx-add_external_phy_interrupt_on_some.patch +++ /dev/null @@ -1,85 +0,0 @@ -From b94d22d94ad226eeea3b6ec4579fb4bf8a199e5c Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 19 Oct 2017 14:01:43 +0200 -Subject: [PATCH] ARM64: dts: meson-gx: add external PHY interrupt on some - platforms - -Add the external PHY interrupt on the nanopi-k2, odroid-c2, p200, p230 -and q200 - -Signed-off-by: Jerome Brunet -Reviewed-by: Neil Armstrong -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts | 2 ++ - arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts | 2 ++ - arch/arm64/boot/dts/amlogic/meson-gxbb-p200.dts | 2 ++ - arch/arm64/boot/dts/amlogic/meson-gxl-s905d-p230.dts | 2 ++ - arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts | 2 ++ - 5 files changed, 10 insertions(+) - -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 2e853c082a654..4a4251001bfd5 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -@@ -168,6 +168,8 @@ - eth_phy0: ethernet-phy@0 { - /* Realtek RTL8211F (0x001cc916) */ - reg = <0>; -+ interrupt-parent = <&gpio_intc>; -+ interrupts = <29 IRQ_TYPE_LEVEL_LOW>; - }; - }; - }; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -index 2e5ed59e697ed..f8d221463c60a 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -@@ -157,6 +157,8 @@ - - eth_phy0: ethernet-phy@0 { - reg = <0>; -+ interrupt-parent = <&gpio_intc>; -+ interrupts = <29 IRQ_TYPE_LEVEL_LOW>; - eee-broken-1000t; - }; - }; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-p200.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-p200.dts -index 2054a474e0a91..9bf16bb7c491b 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-p200.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-p200.dts -@@ -117,6 +117,8 @@ - eth_phy0: ethernet-phy@3 { - /* Micrel KSZ9031 (0x00221620) */ - reg = <3>; -+ interrupt-parent = <&gpio_intc>; -+ interrupts = <29 IRQ_TYPE_LEVEL_LOW>; - }; - }; - }; -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 6827f235d7cfe..4f3f03fc31b0d 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905d-p230.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905d-p230.dts -@@ -128,6 +128,8 @@ - compatible = "ethernet-phy-id001c.c916", "ethernet-phy-ieee802.3-c22"; - reg = <0>; - max-speed = <1000>; -+ interrupt-parent = <&gpio_intc>; -+ interrupts = <29 IRQ_TYPE_LEVEL_LOW>; - }; - }; - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts -index b65776b019118..66c6da7e112cf 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts -@@ -110,6 +110,8 @@ - compatible = "ethernet-phy-id001c.c916", "ethernet-phy-ieee802.3-c22"; - reg = <0>; - max-speed = <1000>; -+ interrupt-parent = <&gpio_intc>; -+ interrupts = <29 IRQ_TYPE_LEVEL_LOW>; - }; - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/058_linux-4.14.y-bpo-dts-0015-arm64-dts-meson-gx-add_vpu_power_domain.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/058_linux-4.14.y-bpo-dts-0015-arm64-dts-meson-gx-add_vpu_power_domain.patch deleted file mode 100644 index b02d6c2b3..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/058_linux-4.14.y-bpo-dts-0015-arm64-dts-meson-gx-add_vpu_power_domain.patch +++ /dev/null @@ -1,163 +0,0 @@ -From 74d1c6e9af69dc6aec07a1dd5c628ae184b15e41 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Mon, 20 Nov 2017 15:19:54 +0100 -Subject: [PATCH] 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 -Signed-off-by: Kevin Hilman ---- - 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 ab7ce1644cdc5..668d891b23a0f 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -377,6 +377,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>; -@@ -454,6 +460,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 ead895a4e9a5c..6904872f08af5 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -@@ -694,6 +694,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>, -@@ -763,4 +805,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 8ed981f59e5ae..49b8ec159603c 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -644,6 +644,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-gxl-saradc", "amlogic,meson-saradc"; - clocks = <&xtal>, -@@ -713,4 +755,5 @@ - - &vpu { - compatible = "amlogic,meson-gxl-vpu", "amlogic,meson-gx-vpu"; -+ power-domains = <&pwrc_vpu>; - }; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/059_linux-4.14.y-bpo-dts-0016-arm64-dts-meson-drop_sana_clock_from_sar_adc.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/059_linux-4.14.y-bpo-dts-0016-arm64-dts-meson-drop_sana_clock_from_sar_adc.patch deleted file mode 100644 index 3823adf4a..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/059_linux-4.14.y-bpo-dts-0016-arm64-dts-meson-drop_sana_clock_from_sar_adc.patch +++ /dev/null @@ -1,48 +0,0 @@ -From e102da498ec3001009433d8d2d160eebbe6d1d69 Mon Sep 17 00:00:00 2001 -From: Xingyu Chen -Date: Thu, 16 Nov 2017 17:01:14 +0800 -Subject: [PATCH] ARM64: dts: meson: drop "sana" clock from SAR ADC - -The SAR ADC modules doesn't require The "sana" clock. - -Acked-by: Martin Blumenstingl -Singed-off-by: Xingyu Chen -Signed-off-by: Yixun Lan -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 3 +-- - arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 3 +-- - 2 files changed, 2 insertions(+), 4 deletions(-) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -index 6904872f08af5..eeaf10c7ba74d 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -@@ -740,10 +740,9 @@ - compatible = "amlogic,meson-gxbb-saradc", "amlogic,meson-saradc"; - clocks = <&xtal>, - <&clkc CLKID_SAR_ADC>, -- <&clkc CLKID_SANA>, - <&clkc CLKID_SAR_ADC_CLK>, - <&clkc CLKID_SAR_ADC_SEL>; -- clock-names = "clkin", "core", "sana", "adc_clk", "adc_sel"; -+ clock-names = "clkin", "core", "adc_clk", "adc_sel"; - }; - - &sd_emmc_a { -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -index 49b8ec159603c..4a316a11a00e8 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -690,10 +690,9 @@ - compatible = "amlogic,meson-gxl-saradc", "amlogic,meson-saradc"; - clocks = <&xtal>, - <&clkc CLKID_SAR_ADC>, -- <&clkc CLKID_SANA>, - <&clkc CLKID_SAR_ADC_CLK>, - <&clkc CLKID_SAR_ADC_SEL>; -- clock-names = "clkin", "core", "sana", "adc_clk", "adc_sel"; -+ clock-names = "clkin", "core", "adc_clk", "adc_sel"; - }; - - &sd_emmc_a { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/060_linux-4.14.y-bpo-dts-0017-arm64-dts-meson-gx-add_hdmi_5v_regulator_on_selected.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/060_linux-4.14.y-bpo-dts-0017-arm64-dts-meson-gx-add_hdmi_5v_regulator_on_selected.patch deleted file mode 100644 index ca1bb4dbe..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/060_linux-4.14.y-bpo-dts-0017-arm64-dts-meson-gx-add_hdmi_5v_regulator_on_selected.patch +++ /dev/null @@ -1,111 +0,0 @@ -From b409f625a6d55e0f0ebc570d1350c1813e65400a Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Mon, 20 Nov 2017 15:19:55 +0100 -Subject: [PATCH] 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 set it always-on for now. - -Signed-off-by: Neil Armstrong -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi | 12 ++++++++++++ - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 12 ++++++++++++ - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi | 12 ++++++++++++ - arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts | 12 ++++++++++++ - 4 files changed, 48 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 7d4b95e499935..aeb6d21a3beca 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,18 @@ - 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; -+ regulator-always-on; -+ }; -+ - vddio_boot: regulator-vddio_boot { - compatible = "regulator-fixed"; - regulator-name = "VDDIO_BOOT"; -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 dc9c3b8216c2b..9671f1e3c74a9 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,18 @@ - 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; -+ regulator-always-on; -+ }; -+ - vcc_3v3: regulator-vcc_3v3 { - compatible = "regulator-fixed"; - regulator-name = "VCC_3V3"; -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 ff09df1fd5a32..7005068346a09 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,18 @@ - 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; -+ regulator-always-on; -+ }; -+ - 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 34a41b26a4ed2..d2595c08ebe7d 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,18 @@ - }; - }; - -+ 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; -+ regulator-always-on; -+ }; -+ - vcc_3v3: regulator-vcc_3v3 { - compatible = "regulator-fixed"; - regulator-name = "VCC_3V3"; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/061_linux-4.14.y-bpo-dts-0018-arm64-dts-meson-gx-grow_reset_controller_memory_zone.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/061_linux-4.14.y-bpo-dts-0018-arm64-dts-meson-gx-grow_reset_controller_memory_zone.patch deleted file mode 100644 index 07a02d6f9..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/061_linux-4.14.y-bpo-dts-0018-arm64-dts-meson-gx-grow_reset_controller_memory_zone.patch +++ /dev/null @@ -1,27 +0,0 @@ -From 1eb0919836c76ed844d604f1d4a600bbfa9c9a02 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Mon, 20 Nov 2017 15:19:56 +0100 -Subject: [PATCH] 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 -Signed-off-by: Kevin Hilman ---- - 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 668d891b23a0f..7cdbf58a062f4 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -229,7 +229,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>; - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/062_linux-4.14.y-bpo-dts-0019-arm64-dts-odroid-c2-add_hdmi_and_cec_nodes.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/062_linux-4.14.y-bpo-dts-0019-arm64-dts-odroid-c2-add_hdmi_and_cec_nodes.patch deleted file mode 100644 index 738d115ba..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/062_linux-4.14.y-bpo-dts-0019-arm64-dts-odroid-c2-add_hdmi_and_cec_nodes.patch +++ /dev/null @@ -1,62 +0,0 @@ -From fc19afa1b4aad3bcbf29bda4a52dcec10879ce15 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Mon, 20 Nov 2017 15:19:57 +0100 -Subject: [PATCH] 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 -Signed-off-by: Kevin Hilman ---- - .../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 f8d221463c60a..d6d3af5eaf553 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 { -@@ -179,6 +197,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>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/063_linux-4.14.y-bpo-dts-0020-arm64-dts-meson-add_comments_with_the_gpio_for_the_phy.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/063_linux-4.14.y-bpo-dts-0020-arm64-dts-meson-add_comments_with_the_gpio_for_the_phy.patch deleted file mode 100644 index 4f898717b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/063_linux-4.14.y-bpo-dts-0020-arm64-dts-meson-add_comments_with_the_gpio_for_the_phy.patch +++ /dev/null @@ -1,75 +0,0 @@ -From 50290cfe50bd94deb221731a25347d0ac12d9f40 Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Sat, 2 Dec 2017 22:40:36 +0100 -Subject: [PATCH] ARM64: dts: meson: add comments with the GPIO for the PHY - interrupts - -Currently one has to look/calculate the GPIO for the PHY interrupts -manually. Add a comment for the existing PHY interrupt lines to make it -easier to find out which GPIO is used. -This is done using the following calculation: -- number of GPIO AO pins (14 on GXBB: GPIOAO_0..13) -- add the offset of the pin which is used for the interrupt (for example - GPIOZ_15 = 15 on Odroid-C2) - -Signed-off-by: Martin Blumenstingl -Reviewed-By: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts | 1 + - arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts | 2 ++ - arch/arm64/boot/dts/amlogic/meson-gxbb-p200.dts | 1 + - arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts | 1 + - 4 files changed, 5 insertions(+) - -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 4a4251001bfd5..011e8e08e429b 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -@@ -169,6 +169,7 @@ - /* Realtek RTL8211F (0x001cc916) */ - reg = <0>; - interrupt-parent = <&gpio_intc>; -+ /* MAC_INTR on GPIOZ_15 */ - interrupts = <29 IRQ_TYPE_LEVEL_LOW>; - }; - }; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -index d6d3af5eaf553..ee4ada61c59cf 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -@@ -174,8 +174,10 @@ - #size-cells = <0>; - - eth_phy0: ethernet-phy@0 { -+ /* Realtek RTL8211F (0x001cc916) */ - reg = <0>; - interrupt-parent = <&gpio_intc>; -+ /* MAC_INTR on GPIOZ_15 */ - interrupts = <29 IRQ_TYPE_LEVEL_LOW>; - eee-broken-1000t; - }; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-p200.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-p200.dts -index 9bf16bb7c491b..09f34f7ef0845 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-p200.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-p200.dts -@@ -118,6 +118,7 @@ - /* Micrel KSZ9031 (0x00221620) */ - reg = <3>; - interrupt-parent = <&gpio_intc>; -+ /* MAC_INTR on GPIOZ_15 */ - interrupts = <29 IRQ_TYPE_LEVEL_LOW>; - }; - }; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts -index 66c6da7e112cf..9847fce443a85 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts -@@ -111,6 +111,7 @@ - reg = <0>; - max-speed = <1000>; - interrupt-parent = <&gpio_intc>; -+ /* MAC_INTR on GPIOH_3 */ - interrupts = <29 IRQ_TYPE_LEVEL_LOW>; - }; - }; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/064_linux-4.14.y-bpo-dts-0021-arm64-dts-meson-gxm-add_the_phy_interrupt_line_on_khadas.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/064_linux-4.14.y-bpo-dts-0021-arm64-dts-meson-gxm-add_the_phy_interrupt_line_on_khadas.patch deleted file mode 100644 index 4ad7d2467..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/064_linux-4.14.y-bpo-dts-0021-arm64-dts-meson-gxm-add_the_phy_interrupt_line_on_khadas.patch +++ /dev/null @@ -1,32 +0,0 @@ -From 45293920c62cc391ce0b601646d90b33e379ee96 Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Sat, 2 Dec 2017 22:40:37 +0100 -Subject: [PATCH] ARM64: dts: meson-gxm: add the PHY interrupt line on Khadas - VIM2 - -The INTB/PMEB pin of the RTL8211F PHY on the Khadas VIM2 is routed to -GPIOZ_15. Add the corresponding interrupt using the GPIO interrupt -controller so the PHY framework doesn't have to poll the PHY for it's -status. - -Signed-off-by: Martin Blumenstingl -Reviewed-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts | 3 +++ - 1 file changed, 3 insertions(+) - -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 d2595c08ebe7d..1448c3dba08e8 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -@@ -244,6 +244,9 @@ - external_phy: ethernet-phy@0 { - /* Realtek RTL8211F (0x001cc916) */ - reg = <0>; -+ interrupt-parent = <&gpio_intc>; -+ /* MAC_INTR on GPIOZ_15 */ -+ interrupts = <25 IRQ_TYPE_LEVEL_LOW>; - }; - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/065_linux-4.14.y-bpo-dts-0022-arm64-dts-meson-gx-fix_uart_pclk_clock_name.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/065_linux-4.14.y-bpo-dts-0022-arm64-dts-meson-gx-fix_uart_pclk_clock_name.patch deleted file mode 100644 index 4e2f0a492..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/065_linux-4.14.y-bpo-dts-0022-arm64-dts-meson-gx-fix_uart_pclk_clock_name.patch +++ /dev/null @@ -1,68 +0,0 @@ -From 39005e562a88c61fa77acef1d2c0cb81ee6b0423 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Mon, 4 Dec 2017 10:04:53 +0100 -Subject: [PATCH] ARM64: dts: meson-gx: fix UART pclk clock name -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -The clock-names for pclk was wrongly set to "core", but the bindings -specifies "pclk". -This was not cathed until the legacy non-documented bindings were removed. - -Reported-by: Andreas Färber -Fixes: f72d6f6037b7 ("ARM64: dts: meson-gx: use stable UART bindings with correct gate clock") -Signed-off-by: Neil Armstrong -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 4 ++-- - arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 6 +++--- - 2 files changed, 5 insertions(+), 5 deletions(-) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -index ead895a4e9a5c..1fb8b9d6cb4ea 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -@@ -753,12 +753,12 @@ - - &uart_B { - clocks = <&xtal>, <&clkc CLKID_UART1>, <&xtal>; -- clock-names = "xtal", "core", "baud"; -+ clock-names = "xtal", "pclk", "baud"; - }; - - &uart_C { - clocks = <&xtal>, <&clkc CLKID_UART2>, <&xtal>; -- clock-names = "xtal", "core", "baud"; -+ clock-names = "xtal", "pclk", "baud"; - }; - - &vpu { -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -index 8ed981f59e5ae..6524b89e7115b 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -688,7 +688,7 @@ - - &uart_A { - clocks = <&xtal>, <&clkc CLKID_UART0>, <&xtal>; -- clock-names = "xtal", "core", "baud"; -+ clock-names = "xtal", "pclk", "baud"; - }; - - &uart_AO { -@@ -703,12 +703,12 @@ - - &uart_B { - clocks = <&xtal>, <&clkc CLKID_UART1>, <&xtal>; -- clock-names = "xtal", "core", "baud"; -+ clock-names = "xtal", "pclk", "baud"; - }; - - &uart_C { - clocks = <&xtal>, <&clkc CLKID_UART2>, <&xtal>; -- clock-names = "xtal", "core", "baud"; -+ clock-names = "xtal", "pclk", "baud"; - }; - - &vpu { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/066_linux-4.14.y-bpo-dts-0023-arm64-dts-meson-gxm-fix_q200_interrupt_number.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/066_linux-4.14.y-bpo-dts-0023-arm64-dts-meson-gxm-fix_q200_interrupt_number.patch deleted file mode 100644 index c74b65300..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/066_linux-4.14.y-bpo-dts-0023-arm64-dts-meson-gxm-fix_q200_interrupt_number.patch +++ /dev/null @@ -1,30 +0,0 @@ -From 3106507e1004dd398ef75d0caf048f97ba2dfd0b Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Mon, 4 Dec 2017 11:05:04 +0100 -Subject: [PATCH] ARM64: dts: meson-gxm: fix q200 interrupt number - -Correct the interrupt number assigned to the Realtek PHY in the q200 - -Fixes: b94d22d94ad2 ("ARM64: dts: meson-gx: add external PHY interrupt on some platforms") -Reported-by: Martin Blumenstingl -Signed-off-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts | 4 ++-- - 1 file changed, 2 insertions(+), 2 deletions(-) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts b/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts -index 9847fce443a85..388fac4f2d977 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-q200.dts -@@ -111,8 +111,8 @@ - reg = <0>; - max-speed = <1000>; - interrupt-parent = <&gpio_intc>; -- /* MAC_INTR on GPIOH_3 */ -- interrupts = <29 IRQ_TYPE_LEVEL_LOW>; -+ /* MAC_INTR on GPIOZ_15 */ -+ interrupts = <25 IRQ_TYPE_LEVEL_LOW>; - }; - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/067_linux-4.14.y-bpo-dts-0024-arm64-dts-amlogic-use_generic_bus_node_names.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/067_linux-4.14.y-bpo-dts-0024-arm64-dts-amlogic-use_generic_bus_node_names.patch deleted file mode 100644 index d9e377d2e..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/067_linux-4.14.y-bpo-dts-0024-arm64-dts-amlogic-use_generic_bus_node_names.patch +++ /dev/null @@ -1,47 +0,0 @@ -From 0cb6c604232ccb6bbbd148c7451f99f9101b46d7 Mon Sep 17 00:00:00 2001 -From: Kevin Hilman -Date: Wed, 6 Dec 2017 11:30:05 -0800 -Subject: [PATCH] ARM64: dts: amlogic: use generic bus node names - -The DT spec recommends that node-names have generic names like "bus". -Fix that in the Amlogic DTs, while leaving the label names to have more -SoC-specific names that match with the HW documentation. - -Suggested-by: Stephen Boyd -Reviewed-by: Neil Armstrong -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 6 +++--- - 1 files changed, 3 insertions(+), 3 deletions(-) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -index 7cdbf58a062f4..6cb3c2a52bafe 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -211,7 +211,7 @@ - #size-cells = <2>; - ranges; - -- cbus: cbus@c1100000 { -+ cbus: bus@c1100000 { - compatible = "simple-bus"; - reg = <0x0 0xc1100000 0x0 0x100000>; - #address-cells = <2>; -@@ -366,7 +366,7 @@ - }; - }; - -- aobus: aobus@c8100000 { -+ aobus: bus@c8100000 { - compatible = "simple-bus"; - reg = <0x0 0xc8100000 0x0 0x100000>; - #address-cells = <2>; -@@ -453,7 +453,7 @@ - }; - }; - -- hiubus: hiubus@c883c000 { -+ hiubus: bus@c883c000 { - compatible = "simple-bus"; - reg = <0x0 0xc883c000 0x0 0x2000>; - #address-cells = <2>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/068_linux-4.14.y-bpo-dts-0025-arm64-dts-meson-uart-fix_address_space_range.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/068_linux-4.14.y-bpo-dts-0025-arm64-dts-meson-uart-fix_address_space_range.patch deleted file mode 100644 index 7505ed2d9..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/068_linux-4.14.y-bpo-dts-0025-arm64-dts-meson-uart-fix_address_space_range.patch +++ /dev/null @@ -1,61 +0,0 @@ -From 77f5cdbd78ec5e17022725a5da476f4ca08b1dfa Mon Sep 17 00:00:00 2001 -From: Yixun Lan -Date: Thu, 11 Jan 2018 10:33:57 +0800 -Subject: [PATCH] ARM64: dts: meson: uart: fix address space range - -The address space range is actually 0x18, fixed here. - -Reviewed-by: Jerome Brunet -Signed-off-by: Yixun Lan -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 10 +++++----- - 1 files changed, 5 insertions(+), 5 deletions(-) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -index 6cb3c2a52bafe..4ee2e7951482f 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -235,14 +235,14 @@ - - uart_A: serial@84c0 { - compatible = "amlogic,meson-gx-uart"; -- reg = <0x0 0x84c0 0x0 0x14>; -+ reg = <0x0 0x84c0 0x0 0x18>; - interrupts = ; - status = "disabled"; - }; - - uart_B: serial@84dc { - compatible = "amlogic,meson-gx-uart"; -- reg = <0x0 0x84dc 0x0 0x14>; -+ reg = <0x0 0x84dc 0x0 0x18>; - interrupts = ; - status = "disabled"; - }; -@@ -287,7 +287,7 @@ - - uart_C: serial@8700 { - compatible = "amlogic,meson-gx-uart"; -- reg = <0x0 0x8700 0x0 0x14>; -+ reg = <0x0 0x8700 0x0 0x18>; - interrupts = ; - status = "disabled"; - }; -@@ -404,14 +404,14 @@ - - uart_AO: serial@4c0 { - compatible = "amlogic,meson-gx-uart", "amlogic,meson-ao-uart"; -- reg = <0x0 0x004c0 0x0 0x14>; -+ reg = <0x0 0x004c0 0x0 0x18>; - interrupts = ; - status = "disabled"; - }; - - uart_AO_B: serial@4e0 { - compatible = "amlogic,meson-gx-uart", "amlogic,meson-ao-uart"; -- reg = <0x0 0x004e0 0x0 0x14>; -+ reg = <0x0 0x004e0 0x0 0x18>; - interrupts = ; - status = "disabled"; - }; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/069_linux-4.14.y-bpo-dts-0026-arm64-dts-meson_s905x-accept_mac_addr_from_u-boot.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/069_linux-4.14.y-bpo-dts-0026-arm64-dts-meson_s905x-accept_mac_addr_from_u-boot.patch deleted file mode 100644 index beae5faba..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/069_linux-4.14.y-bpo-dts-0026-arm64-dts-meson_s905x-accept_mac_addr_from_u-boot.patch +++ /dev/null @@ -1,32 +0,0 @@ -From f7c36209c46c4d162202b65eed2e66962ad8c3c1 Mon Sep 17 00:00:00 2001 -From: Jorge Ramirez-Ortiz -Date: Wed, 17 Jan 2018 11:55:43 +0100 -Subject: [PATCH] ARM64: dts: meson s905x: accept MAC addr from u-boot - environment - -With the adequate configuration settings, u-boot will loop through the -list of aliases looking for "ethernetX". - -By adding an ethernet alias, u-boot can fixup the local-mac-address -property in the kernel's device tree using a value held in its -environment variable ethaddr. - -Tested-by: Jorge Ramirez-Ortiz -Signed-off-by: Jorge Ramirez-Ortiz -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 1 + - 1 file changed, 1 insertion(+) - -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 9671f1e3c74a9..a011d51fec244 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 -@@ -18,6 +18,7 @@ - - aliases { - serial0 = &uart_AO; -+ ethernet0 = ðmac; - }; - - chosen { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/070_linux-4.14.y-bpo-dts-0027-arm64-dts-meson-accept_mac_addr_from_u-boot_environment.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/070_linux-4.14.y-bpo-dts-0027-arm64-dts-meson-accept_mac_addr_from_u-boot_environment.patch deleted file mode 100644 index cfc1aa40b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/070_linux-4.14.y-bpo-dts-0027-arm64-dts-meson-accept_mac_addr_from_u-boot_environment.patch +++ /dev/null @@ -1,171 +0,0 @@ -From 059a58fcd53a78b898f26c26a1c37816ba306933 Mon Sep 17 00:00:00 2001 -From: Jorge Ramirez-Ortiz -Date: Wed, 17 Jan 2018 11:56:27 +0100 -Subject: [PATCH] ARM64: dts: meson: accept MAC addr from u-boot environment - -Extend configuring the MAC address from u-boot to all meson boards. - -I didn't test this changeset but having checked libretech's u-boot -tree I believe it should just work. - -Signed-off-by: Jorge Ramirez-Ortiz -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi | 1 + - arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts | 1 + - arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts | 1 + - arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts | 1 + - arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi | 1 + - arch/arm64/boot/dts/amlogic/meson-gxbb-vega-s95.dtsi | 1 + - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-hwacom-amazetv.dts | 1 + - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-khadas-vim.dts | 1 + - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts | 1 + - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi | 1 + - arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts | 1 + - arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts | 1 + - 12 files changed, 12 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 aeb6d21a3beca..4b28a6e31175b 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi -@@ -48,6 +48,7 @@ - / { - aliases { - serial0 = &uart_AO; -+ ethernet0 = ðmac; - }; - - chosen { -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 011e8e08e429b..2ce7258a147bb 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nanopi-k2.dts -@@ -52,6 +52,7 @@ - - aliases { - serial0 = &uart_AO; -+ ethernet0 = ðmac; - }; - - chosen { -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 818954b1d57f8..855dd9ae07160 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts -@@ -54,6 +54,7 @@ - - aliases { - serial0 = &uart_AO; -+ ethernet0 = ðmac; - }; - - chosen { -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -index ee4ada61c59cf..73a030a5ecf33 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -@@ -53,6 +53,7 @@ - - aliases { - serial0 = &uart_AO; -+ ethernet0 = ðmac; - }; - - chosen { -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi -index 932158a778ef8..c6f7b51e2ec8f 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi -@@ -47,6 +47,7 @@ - / { - aliases { - serial0 = &uart_AO; -+ ethernet0 = ðmac; - }; - - chosen { -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 1fe8e24cf675c..383f9de734c10 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-vega-s95.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-vega-s95.dtsi -@@ -47,6 +47,7 @@ - - aliases { - serial0 = &uart_AO; -+ ethernet0 = ðmac; - }; - - chosen { -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 e82582574160c..386fab4d1c8f3 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 -@@ -16,6 +16,7 @@ - - aliases { - serial0 = &uart_AO; -+ ethernet0 = ðmac; - }; - - chosen { -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 71a6e1ce7ad58..94cddf59646ae 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 -@@ -29,6 +29,7 @@ - - aliases { - serial2 = &uart_AO_B; -+ ethernet0 = ðmac; - }; - - gpio-keys-polled { -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 271f142791808..6b05c0e577248 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 -@@ -52,6 +52,7 @@ - - aliases { - serial0 = &uart_AO; -+ ethernet0 = ðmac; - }; - - chosen { -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 7005068346a09..9cde3d2eef972 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi -@@ -17,6 +17,7 @@ - aliases { - serial0 = &uart_AO; - serial1 = &uart_A; -+ ethernet0 = ðmac; - }; - - chosen { -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 e7a228f6cc7e7..15cdd938f6a21 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts -@@ -54,6 +54,7 @@ - - aliases { - serial0 = &uart_AO; -+ ethernet0 = ðmac; - }; - - chosen { -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 a5e9b955d5ed3..67fadea68e075 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-rbox-pro.dts -@@ -58,6 +58,7 @@ - - aliases { - serial0 = &uart_AO; -+ ethernet0 = ðmac; - }; - - chosen { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/071_linux-4.14.y-bpo-dts-0028-arm64-dts-meson-remove_cooling-min_max-level_for_cpu.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/071_linux-4.14.y-bpo-dts-0028-arm64-dts-meson-remove_cooling-min_max-level_for_cpu.patch deleted file mode 100644 index f55196cdf..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/071_linux-4.14.y-bpo-dts-0028-arm64-dts-meson-remove_cooling-min_max-level_for_cpu.patch +++ /dev/null @@ -1,38 +0,0 @@ -From f65f2df29d7b4e77318635ec33e95d801a9e40dd Mon Sep 17 00:00:00 2001 -From: Viresh Kumar -Date: Fri, 9 Feb 2018 14:28:06 +0530 -Subject: [PATCH] ARM64: dts: meson: Remove "cooling-{min|max}-level" for CPU - nodes - -The "cooling-min-level" and "cooling-max-level" properties are not -parsed by any part of the kernel currently and the max cooling state of -a CPU cooling device is found by referring to the cpufreq table instead. - -Remove the unused properties from the CPU nodes. - -Signed-off-by: Viresh Kumar -Acked-by: Neil Armstrong -Signed-off-by: Arnd Bergmann ---- - arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts | 4 ---- - 1 file changed, 4 deletions(-) - -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 447b9e22cf8e3..f9a50f861cd38 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -@@ -208,14 +208,10 @@ - }; - - &cpu0 { -- cooling-min-level = <0>; -- cooling-max-level = <6>; - #cooling-cells = <2>; - }; - - &cpu4 { -- cooling-min-level = <0>; -- cooling-max-level = <4>; - #cooling-cells = <2>; - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/072_linux-4.14.y-bpo-dts-0029-arm64-dts-meson-remove_cooling-min_max-level_for.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/072_linux-4.14.y-bpo-dts-0029-arm64-dts-meson-remove_cooling-min_max-level_for.patch deleted file mode 100644 index d22f34de0..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/072_linux-4.14.y-bpo-dts-0029-arm64-dts-meson-remove_cooling-min_max-level_for.patch +++ /dev/null @@ -1,33 +0,0 @@ -From b6f67b039c64572adced5d5c0f01dc944e251bc2 Mon Sep 17 00:00:00 2001 -From: Viresh Kumar -Date: Fri, 9 Feb 2018 14:28:08 +0530 -Subject: [PATCH] ARM64: dts: meson: Remove "cooling-{min|max}-level" for - gpio-fan node - -The "cooling-min-level" and "cooling-max-level" properties are not -parsed by any part of the kernel currently and the max cooling state of -gpio-fan cooling device is found by referring to the -"gpio-fan,speed-map" instead. - -Remove the unused properties from the gpio-fan node. - -Signed-off-by: Viresh Kumar -Acked-by: Neil Armstrong -Signed-off-by: Arnd Bergmann ---- - arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts | 2 -- - 1 file changed, 2 deletions(-) - -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 f9a50f861cd38..4fd46c1546a7e 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -@@ -58,8 +58,6 @@ - 1 1 - 2 2 - 3 3>; -- cooling-min-level = <0>; -- cooling-max-level = <3>; - #cooling-cells = <2>; - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/073_linux-4.14.y-bpo-dts-0030-arm64-dts-meson-gxbb-wetek-add_a_wetek_specific_dtsi_to.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/073_linux-4.14.y-bpo-dts-0030-arm64-dts-meson-gxbb-wetek-add_a_wetek_specific_dtsi_to.patch deleted file mode 100644 index d20967415..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/073_linux-4.14.y-bpo-dts-0030-arm64-dts-meson-gxbb-wetek-add_a_wetek_specific_dtsi_to.patch +++ /dev/null @@ -1,454 +0,0 @@ -From fb72c03e0e32068a0a2ff66c2787814142d9a211 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Tue, 6 Mar 2018 17:19:33 +0100 -Subject: [PATCH] ARM64: dts: meson-gxbb-wetek: add a wetek specific dtsi to - cleanup hub and play2 - -This patch adds a specific wetek dtsi to handle the specific Hub and Play2 -boards by no more depending on the p20x dtsi. -This simplifies the hub and play2 dts and will avoid breaking these -boards when adding p200 and p201 specific changes. - -Signed-off-by: Neil Armstrong -Signed-off-by: Kevin Hilman ---- - .../boot/dts/amlogic/meson-gxbb-wetek-hub.dts | 43 +--- - .../boot/dts/amlogic/meson-gxbb-wetek-play2.dts | 83 +------ - arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi | 256 +++++++++++++++++++++ - 3 files changed, 262 insertions(+), 120 deletions(-) - create mode 100644 arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-hub.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-hub.dts -index ce80d5d0982c0..2bfe69902552e 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-hub.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-hub.dts -@@ -6,50 +6,9 @@ - - /dts-v1/; - --#include "meson-gxbb-p20x.dtsi" -+#include "meson-gxbb-wetek.dtsi" - - / { - compatible = "wetek,hub", "amlogic,meson-gxbb"; - model = "WeTek Hub"; -- -- leds { -- compatible = "gpio-leds"; -- -- system { -- label = "wetek-play:system-status"; -- gpios = <&gpio_ao GPIOAO_13 GPIO_ACTIVE_HIGH>; -- default-state = "on"; -- panic-indicator; -- }; -- }; --}; -- --&cvbs_connector { -- status = "disabled"; --}; -- --ðmac { -- status = "okay"; -- pinctrl-0 = <ð_rgmii_pins>; -- pinctrl-names = "default"; -- -- phy-handle = <ð_phy0>; -- phy-mode = "rgmii"; -- -- amlogic,tx-delay-ns = <2>; -- -- snps,reset-gpio = <&gpio GPIOZ_14 0>; -- snps,reset-delays-us = <0 10000 1000000>; -- snps,reset-active-low; -- -- mdio { -- compatible = "snps,dwmac-mdio"; -- #address-cells = <1>; -- #size-cells = <0>; -- -- eth_phy0: ethernet-phy@0 { -- /* Realtek RTL8211F (0x001cc916) */ -- reg = <0>; -- }; -- }; - }; -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 0d1f080cbb3e6..0038522315de7 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-play2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek-play2.dts -@@ -6,7 +6,7 @@ - - /dts-v1/; - --#include "meson-gxbb-p20x.dtsi" -+#include "meson-gxbb-wetek.dtsi" - #include - - / { -@@ -14,15 +14,6 @@ - model = "WeTek Play 2"; - - leds { -- compatible = "gpio-leds"; -- -- system { -- label = "wetek-play:system-status"; -- gpios = <&gpio_ao GPIOAO_13 GPIO_ACTIVE_HIGH>; -- default-state = "on"; -- panic-indicator; -- }; -- - wifi { - label = "wetek-play:wifi-status"; - gpios = <&gpio GPIODV_26 GPIO_ACTIVE_HIGH>; -@@ -48,82 +39,18 @@ - gpios = <&gpio_ao GPIOAO_3 GPIO_ACTIVE_LOW>; - }; - }; -- -- cvbs-connector { -- compatible = "composite-video-connector"; -- -- port { -- cvbs_connector_in: endpoint { -- remote-endpoint = <&cvbs_vdac_out>; -- }; -- }; -- }; -- -- 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>; --}; -- --&cvbs_vdac_port { -- cvbs_vdac_out: endpoint { -- remote-endpoint = <&cvbs_connector_in>; -- }; - }; - --ðmac { -+&i2c_A { - status = "okay"; -- pinctrl-0 = <ð_rgmii_pins>; -+ pinctrl-0 = <&i2c_a_pins>; - pinctrl-names = "default"; -- -- phy-handle = <ð_phy0>; -- phy-mode = "rgmii"; -- -- amlogic,tx-delay-ns = <2>; -- -- snps,reset-gpio = <&gpio GPIOZ_14 0>; -- snps,reset-delays-us = <0 10000 1000000>; -- snps,reset-active-low; -- -- mdio { -- compatible = "snps,dwmac-mdio"; -- #address-cells = <1>; -- #size-cells = <0>; -- -- eth_phy0: ethernet-phy@0 { -- /* Realtek RTL8211F (0x001cc916) */ -- reg = <0>; -- }; -- }; - }; - --&hdmi_tx { -+&usb1_phy { - 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 { -+&usb1 { - status = "okay"; -- pinctrl-0 = <&i2c_a_pins>; -- pinctrl-names = "default"; - }; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi -new file mode 100644 -index 0000000000000..70325b273bd2b ---- /dev/null -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi -@@ -0,0 +1,256 @@ -+// SPDX-License-Identifier: (GPL-2.0+ OR MIT) -+/* -+ * Copyright (c) 2016 Andreas Färber -+ * Copyright (c) 2016 BayLibre, Inc. -+ * Author: Kevin Hilman -+ */ -+ -+#include "meson-gxbb.dtsi" -+ -+/ { -+ aliases { -+ serial0 = &uart_AO; -+ ethernet0 = ðmac; -+ }; -+ -+ chosen { -+ stdout-path = "serial0:115200n8"; -+ }; -+ -+ memory@0 { -+ device_type = "memory"; -+ reg = <0x0 0x0 0x0 0x40000000>; -+ }; -+ -+ leds { -+ compatible = "gpio-leds"; -+ -+ system { -+ label = "wetek-play:system-status"; -+ gpios = <&gpio_ao GPIOAO_13 GPIO_ACTIVE_HIGH>; -+ default-state = "on"; -+ panic-indicator; -+ }; -+ }; -+ -+ usb_pwr: regulator-usb-pwrs { -+ compatible = "regulator-fixed"; -+ -+ regulator-name = "USB_PWR"; -+ -+ regulator-min-microvolt = <5000000>; -+ regulator-max-microvolt = <5000000>; -+ -+ gpio = <&gpio GPIODV_24 GPIO_ACTIVE_HIGH>; -+ enable-active-high; -+ }; -+ -+ 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>; -+ }; -+ -+ vcc_3v3: regulator-vcc_3v3 { -+ compatible = "regulator-fixed"; -+ regulator-name = "VCC_3V3"; -+ regulator-min-microvolt = <3300000>; -+ regulator-max-microvolt = <3300000>; -+ }; -+ -+ emmc_pwrseq: emmc-pwrseq { -+ compatible = "mmc-pwrseq-emmc"; -+ reset-gpios = <&gpio BOOT_9 GPIO_ACTIVE_LOW>; -+ }; -+ -+ wifi32k: wifi32k { -+ compatible = "pwm-clock"; -+ #clock-cells = <0>; -+ clock-frequency = <32768>; -+ pwms = <&pwm_ef 0 30518 0>; /* PWM_E at 32.768KHz */ -+ }; -+ -+ sdio_pwrseq: sdio-pwrseq { -+ compatible = "mmc-pwrseq-simple"; -+ reset-gpios = <&gpio GPIOX_6 GPIO_ACTIVE_LOW>; -+ clocks = <&wifi32k>; -+ clock-names = "ext_clock"; -+ }; -+ -+ cvbs-connector { -+ compatible = "composite-video-connector"; -+ -+ port { -+ cvbs_connector_in: endpoint { -+ remote-endpoint = <&cvbs_vdac_out>; -+ }; -+ }; -+ }; -+ -+ 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>; -+}; -+ -+&cvbs_vdac_port { -+ cvbs_vdac_out: endpoint { -+ remote-endpoint = <&cvbs_connector_in>; -+ }; -+}; -+ -+ðmac { -+ status = "okay"; -+ pinctrl-0 = <ð_rgmii_pins>; -+ pinctrl-names = "default"; -+ -+ phy-handle = <ð_phy0>; -+ phy-mode = "rgmii"; -+ -+ amlogic,tx-delay-ns = <2>; -+ -+ snps,reset-gpio = <&gpio GPIOZ_14 0>; -+ snps,reset-delays-us = <0 10000 1000000>; -+ snps,reset-active-low; -+ -+ mdio { -+ compatible = "snps,dwmac-mdio"; -+ #address-cells = <1>; -+ #size-cells = <0>; -+ -+ eth_phy0: ethernet-phy@0 { -+ /* Realtek RTL8211F (0x001cc916) */ -+ reg = <0>; -+ eee-broken-1000t; -+ }; -+ }; -+}; -+ -+&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>; -+ }; -+}; -+ -+&ir { -+ status = "okay"; -+ pinctrl-0 = <&remote_input_ao_pins>; -+ pinctrl-names = "default"; -+}; -+ -+&pwm_ef { -+ status = "okay"; -+ pinctrl-0 = <&pwm_e_pins>; -+ pinctrl-names = "default"; -+ clocks = <&clkc CLKID_FCLK_DIV4>; -+ clock-names = "clkin0"; -+}; -+ -+/* Wireless SDIO Module */ -+&sd_emmc_a { -+ status = "okay"; -+ pinctrl-0 = <&sdio_pins>; -+ pinctrl-1 = <&sdio_clk_gate_pins>; -+ pinctrl-names = "default", "clk-gate"; -+ #address-cells = <1>; -+ #size-cells = <0>; -+ -+ bus-width = <4>; -+ cap-sd-highspeed; -+ 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-1 = <&sdcard_clk_gate_pins>; -+ pinctrl-names = "default", "clk-gate"; -+ -+ 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 = <&vcc_3v3>; -+}; -+ -+/* eMMC */ -+&sd_emmc_c { -+ status = "okay"; -+ pinctrl-0 = <&emmc_pins>, <&emmc_ds_pins>; -+ pinctrl-1 = <&emmc_clk_gate_pins>; -+ pinctrl-names = "default", "clk-gate"; -+ -+ bus-width = <8>; -+ 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>; -+}; -+ -+/* This UART is brought out to the DB9 connector */ -+&uart_AO { -+ status = "okay"; -+ pinctrl-0 = <&uart_ao_a_pins>; -+ pinctrl-names = "default"; -+}; -+ -+&usb0_phy { -+ status = "okay"; -+ phy-supply = <&usb_pwr>; -+}; -+ -+&usb0 { -+ status = "okay"; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/074_linux-4.14.y-bpo-dts-0031-arm64-dts-meson-bump_mali450_clk_to_744mhz.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/074_linux-4.14.y-bpo-dts-0031-arm64-dts-meson-bump_mali450_clk_to_744mhz.patch deleted file mode 100644 index ebdb54757..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/074_linux-4.14.y-bpo-dts-0031-arm64-dts-meson-bump_mali450_clk_to_744mhz.patch +++ /dev/null @@ -1,68 +0,0 @@ -From 97ac00930970bc9e3982182891e350ae1764fbb5 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Mon, 12 Mar 2018 12:10:21 +0100 -Subject: [PATCH] ARM64: dts: meson: bump mali450 clk to 744MHz - -The Mali-450 IP can run up to 744MHz, bump the frequency using -the GP0 PLL clock. - -Cc: Michal Lazo -Signed-off-by: Neil Armstrong -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi | 11 +++++++---- - arch/arm64/boot/dts/amlogic/meson-gxl-mali.dtsi | 11 +++++++---- - 2 files changed, 14 insertions(+), 8 deletions(-) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -index cac72acb85b1a..562c26a0ba333 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -@@ -247,14 +247,17 @@ - * MALI_0 and MALI_1 muxed to a single clock by a glitch - * free mux to safely change frequency while running. - */ -- assigned-clocks = <&clkc CLKID_MALI_0_SEL>, -+ assigned-clocks = <&clkc CLKID_GP0_PLL>, -+ <&clkc CLKID_MALI_0_SEL>, - <&clkc CLKID_MALI_0>, - <&clkc CLKID_MALI>; /* Glitch free mux */ -- assigned-clock-parents = <&clkc CLKID_FCLK_DIV3>, -+ assigned-clock-parents = <0>, /* Do Nothing */ -+ <&clkc CLKID_GP0_PLL>, - <0>, /* Do Nothing */ - <&clkc CLKID_MALI_0>; -- assigned-clock-rates = <0>, /* Do Nothing */ -- <666666666>, -+ assigned-clock-rates = <744000000>, -+ <0>, /* Do Nothing */ -+ <744000000>, - <0>; /* Do Nothing */ - }; - }; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl-mali.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl-mali.dtsi -index f825506cdf64f..eb327664a4d8c 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl-mali.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl-mali.dtsi -@@ -29,14 +29,17 @@ - * MALI_0 and MALI_1 muxed to a single clock by a glitch - * free mux to safely change frequency while running. - */ -- assigned-clocks = <&clkc CLKID_MALI_0_SEL>, -+ assigned-clocks = <&clkc CLKID_GP0_PLL>, -+ <&clkc CLKID_MALI_0_SEL>, - <&clkc CLKID_MALI_0>, - <&clkc CLKID_MALI>; /* Glitch free mux */ -- assigned-clock-parents = <&clkc CLKID_FCLK_DIV3>, -+ assigned-clock-parents = <0>, /* Do Nothing */ -+ <&clkc CLKID_GP0_PLL>, - <0>, /* Do Nothing */ - <&clkc CLKID_MALI_0>; -- assigned-clock-rates = <0>, /* Do Nothing */ -- <666666666>, -+ assigned-clock-rates = <744000000>, -+ <0>, /* Do Nothing */ -+ <744000000>, - <0>; /* Do Nothing */ - }; - }; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/075_linux-4.14.y-bpo-dts-0032-arm64-dts-meson-gx-make_efuse_read-only.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/075_linux-4.14.y-bpo-dts-0032-arm64-dts-meson-gx-make_efuse_read-only.patch deleted file mode 100644 index aa603bf8c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/075_linux-4.14.y-bpo-dts-0032-arm64-dts-meson-gx-make_efuse_read-only.patch +++ /dev/null @@ -1,27 +0,0 @@ -From c339f0e29ce9f9cd1cd2b6759a29a298bce1e948 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Fri, 16 Mar 2018 15:50:21 +0100 -Subject: [PATCH] ARM64: dts: meson-gx: make efuse read-only - -efuse is one time programmable, so it is safer to deny write request -to this memory, unless the user is savvy enough to remove the read-only -flag from DTB - -Signed-off-by: Jerome Brunet -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gx.dtsi | 1 + - 1 file changed, 1 insertion(+) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -index 2d51ccd60628e..3c31e21cbed7f 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -132,6 +132,7 @@ - compatible = "amlogic,meson-gx-efuse", "amlogic,meson-gxbb-efuse"; - #address-cells = <1>; - #size-cells = <1>; -+ read-only; - - sn: sn@14 { - reg = <0x14 0x10>; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/076_linux-4.14.y-bpo-dts-0033-arm64-dts-meson-gxl-s905x-p212-enable_the_usb_controller.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/076_linux-4.14.y-bpo-dts-0033-arm64-dts-meson-gxl-s905x-p212-enable_the_usb_controller.patch deleted file mode 100644 index 49cc0e2ae..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/076_linux-4.14.y-bpo-dts-0033-arm64-dts-meson-gxl-s905x-p212-enable_the_usb_controller.patch +++ /dev/null @@ -1,30 +0,0 @@ -From b9f07cb4f41fccbe7616482015d28e6e26aec3a3 Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Mon, 26 Mar 2018 23:17:44 +0200 -Subject: [PATCH] ARM64: dts: meson-gxl-s905x-p212: enable the USB controller - -All boards based on the P212 reference design (the P212 reference board -itself and the Khadas VIM) have USB connectors (in case of the Khadas -VIM the first port is exposed through the USB Type-C connector, the -second port is connected to a 4-port USB hub). -This enables the USB controller on these boards to make the USB ports -actually usable. - -Signed-off-by: Martin Blumenstingl -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi | 4 ++++ - 1 file changed, 4 insertions(+) - -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 0a0953fbc7d42..0cfd701809dec 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dtsi -@@ -185,3 +185,7 @@ - pinctrl-0 = <&uart_ao_a_pins>; - pinctrl-names = "default"; - }; -+ -+&usb0 { -+ status = "okay"; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/077_linux-4.14.y-bpo-dts-0034-arm64-dts-meson-gxl-s905x-libretech-cc-enable_the_usb.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/077_linux-4.14.y-bpo-dts-0034-arm64-dts-meson-gxl-s905x-libretech-cc-enable_the_usb.patch deleted file mode 100644 index d89de01fc..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/077_linux-4.14.y-bpo-dts-0034-arm64-dts-meson-gxl-s905x-libretech-cc-enable_the_usb.patch +++ /dev/null @@ -1,39 +0,0 @@ -From b83687f359d9b4128073f06ab7a06489eb04aa7c Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Mon, 26 Mar 2018 23:17:46 +0200 -Subject: [PATCH] ARM64: dts: meson-gxl-s905x-libretech-cc: enable the USB - controller - -The LibreTech CC ("Le Potato") board provides four USB connectors. -These are provided by a hub which is connected to the SoC's USB -controller. -Enable the SoC's USB controller to make the USB ports usable. Also turn -on the HDMI_5V regulator when powering on the PHY because (even though -it's not shown in the schematics) HDMI_5V also supplies the USB VBUS. - -Signed-off-by: Martin Blumenstingl -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-libretech-cc.dts | 12 ++++++++++++ - 1 file changed, 12 insertions(+) - -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 22bf37404ff1b..3e3eb31748a35 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 -@@ -271,3 +271,15 @@ - pinctrl-0 = <&uart_ao_a_pins>; - pinctrl-names = "default"; - }; -+ -+&usb0 { -+ status = "okay"; -+}; -+ -+&usb2_phy0 { -+ /* -+ * even though the schematics don't show it: -+ * HDMI_5V is also used as supply for the USB VBUS. -+ */ -+ phy-supply = <&hdmi_5v>; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/078_linux-4.14.y-bpo-dts-0035-arm64-dts-meson-gxl-add_usb_host_support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/078_linux-4.14.y-bpo-dts-0035-arm64-dts-meson-gxl-add_usb_host_support.patch deleted file mode 100644 index e3e606887..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/078_linux-4.14.y-bpo-dts-0035-arm64-dts-meson-gxl-add_usb_host_support.patch +++ /dev/null @@ -1,105 +0,0 @@ -From 8aec5fc1d4d881fe446addb94309efb39d4e5b23 Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Mon, 26 Mar 2018 23:17:42 +0200 -Subject: [PATCH] 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 (not added in this patch -because I could not get it working) is used for device-mode only. - -The dwc3 controller's internal roothub has two USB2 ports enabled but no -USB3 port. Each of the ports is supplied by a separate PHY. The USB pins -are connected to the SoC's USBHOST_A and USBOTG_B pins. -Due to the way the roothub works internally the USB PHYs are left -enabled. When the dwc3 controller is disabled the PHY is never powered on -so it does not draw any extra power. However, when the dwc3 host -controller is enabled then all PHYs also have to be enabled, otherwise -USB devices will not be detected (regardless of whether they are plugged -into an enabled port or not). This means that only the dwc3 controller -has to be enabled on boards with USB support (instead of requiring all -boards to enable the PHYs additionally with the chance of forgetting to -enable one and breaking all other ports with that as well). - -This also adds the USB3 PHY which currently only does some basic -initialization. That however is required because without it high-speed -devices (like USB thumb drives) do not work on some devices (probably -because the bootloader does not configure the USB3 PHY registers). - -Signed-off-by: Martin Blumenstingl -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 61 ++++++++++++++++++++++++++++++ - 1 file changed, 61 insertions(+) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -index e1a39cbed8c9c..dba365ed4bd5f 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -20,6 +20,67 @@ - no-map; - }; - }; -+ -+ soc { -+ usb0: usb@c9000000 { -+ status = "disabled"; -+ compatible = "amlogic,meson-gxl-dwc3"; -+ #address-cells = <2>; -+ #size-cells = <2>; -+ ranges; -+ -+ clocks = <&clkc CLKID_USB>; -+ clock-names = "usb_general"; -+ resets = <&reset RESET_USB_OTG>; -+ reset-names = "usb_otg"; -+ -+ dwc3: dwc3@c9000000 { -+ compatible = "snps,dwc3"; -+ reg = <0x0 0xc9000000 0x0 0x100000>; -+ interrupts = ; -+ dr_mode = "host"; -+ maximum-speed = "high-speed"; -+ snps,dis_u2_susphy_quirk; -+ phys = <&usb3_phy>, <&usb2_phy0>, <&usb2_phy1>; -+ }; -+ }; -+ }; -+}; -+ -+&apb { -+ usb2_phy0: phy@78000 { -+ compatible = "amlogic,meson-gxl-usb2-phy"; -+ #phy-cells = <0>; -+ reg = <0x0 0x78000 0x0 0x20>; -+ clocks = <&clkc CLKID_USB>; -+ clock-names = "phy"; -+ resets = <&reset RESET_USB_OTG>; -+ reset-names = "phy"; -+ status = "okay"; -+ }; -+ -+ usb2_phy1: phy@78020 { -+ compatible = "amlogic,meson-gxl-usb2-phy"; -+ #phy-cells = <0>; -+ reg = <0x0 0x78020 0x0 0x20>; -+ clocks = <&clkc CLKID_USB>; -+ clock-names = "phy"; -+ resets = <&reset RESET_USB_OTG>; -+ reset-names = "phy"; -+ status = "okay"; -+ }; -+ -+ usb3_phy: phy@78080 { -+ compatible = "amlogic,meson-gxl-usb3-phy"; -+ #phy-cells = <0>; -+ reg = <0x0 0x78080 0x0 0x20>; -+ interrupts = ; -+ clocks = <&clkc CLKID_USB>, <&clkc_AO CLKID_AO_CEC_32K>; -+ clock-names = "phy", "peripheral"; -+ resets = <&reset RESET_USB_OTG>, <&reset RESET_USB_OTG>; -+ reset-names = "phy", "peripheral"; -+ status = "okay"; -+ }; - }; - - ðmac { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/079_linux-4.14.y-bpo-dts-0036-arm64-dts-meson-gxm-add_gxm_specific_usb_host.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/079_linux-4.14.y-bpo-dts-0036-arm64-dts-meson-gxm-add_gxm_specific_usb_host.patch deleted file mode 100644 index 4820d9853..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/079_linux-4.14.y-bpo-dts-0036-arm64-dts-meson-gxm-add_gxm_specific_usb_host.patch +++ /dev/null @@ -1,53 +0,0 @@ -From 458baa95c86406c81c6ebac0a98d1689075a3ec4 Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Mon, 26 Mar 2018 23:17:43 +0200 -Subject: [PATCH] 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. -Passing the third PHY is required though, because without it none of the -other USB ports is working (this seems to be a limitation of how the -internal USB hub works, if one PHY is disabled then no USB port works). - -Signed-off-by: Martin Blumenstingl -Signed-off-by: Kevin Hilman ---- - 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 d076a7c425ddd..247888d68a3aa 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm.dtsi -@@ -80,6 +80,19 @@ - }; - }; - -+&apb { -+ usb2_phy2: phy@78040 { -+ compatible = "amlogic,meson-gxl-usb2-phy"; -+ #phy-cells = <0>; -+ reg = <0x0 0x78040 0x0 0x20>; -+ clocks = <&clkc CLKID_USB>; -+ clock-names = "phy"; -+ resets = <&reset RESET_USB_OTG>; -+ reset-names = "phy"; -+ status = "okay"; -+ }; -+}; -+ - &clkc_AO { - compatible = "amlogic,meson-gxm-aoclkc", "amlogic,meson-gx-aoclkc"; - }; -@@ -100,3 +113,7 @@ - &hdmi_tx { - compatible = "amlogic,meson-gxm-dw-hdmi", "amlogic,meson-gx-dw-hdmi"; - }; -+ -+&dwc3 { -+ phys = <&usb3_phy>, <&usb2_phy0>, <&usb2_phy1>, <&usb2_phy2>; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/080_linux-4.14.y-bpo-dts-0037-arm64-dts-meson-gx-p23x-q20x-enable_the_usb_controller.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/080_linux-4.14.y-bpo-dts-0037-arm64-dts-meson-gx-p23x-q20x-enable_the_usb_controller.patch deleted file mode 100644 index aefbc6704..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/080_linux-4.14.y-bpo-dts-0037-arm64-dts-meson-gx-p23x-q20x-enable_the_usb_controller.patch +++ /dev/null @@ -1,28 +0,0 @@ -From 972cd12a027256061c19c164021f2a771e860438 Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Mon, 26 Mar 2018 23:17:45 +0200 -Subject: [PATCH] ARM64: dts: meson-gx-p23x-q20x: enable the USB controller - -All S905D (GXL) and S912 (GXM) reference boards (namely these are -P230, P231, Q200 and Q201) provide USB connectors. -This enables the USB controller on these boards to make the USB ports -actually usable. - -Signed-off-by: Martin Blumenstingl -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi | 4 ++++ - 1 file changed, 4 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 4eef36b225386..88e712ea757a2 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi -@@ -212,3 +212,7 @@ - pinctrl-0 = <&uart_ao_a_pins>; - pinctrl-names = "default"; - }; -+ -+&usb0 { -+ status = "okay"; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/081_linux-4.14.y-bpo-dts-0038-arm64-dts-meson-gxl-nexbox-a95x-enable_the_usb_controller.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/081_linux-4.14.y-bpo-dts-0038-arm64-dts-meson-gxl-nexbox-a95x-enable_the_usb_controller.patch deleted file mode 100644 index 9109f75e8..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/081_linux-4.14.y-bpo-dts-0038-arm64-dts-meson-gxl-nexbox-a95x-enable_the_usb_controller.patch +++ /dev/null @@ -1,26 +0,0 @@ -From 55ef32249bb647c6b64adcf943918d302a0020a7 Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Mon, 26 Mar 2018 23:17:47 +0200 -Subject: [PATCH] ARM64: dts: meson-gxl-nexbox-a95x: enable the USB controller - -The Nexbox A95X provides two USB ports. Enable the SoC's USB controller -on this board to make these USB ports usable. - -Signed-off-by: Martin Blumenstingl -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxl-s905x-nexbox-a95x.dts | 4 ++++ - 1 file changed, 4 insertions(+) - -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 69c721a70e44b..6739697be1def 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 -@@ -215,3 +215,7 @@ - pinctrl-0 = <&uart_ao_a_pins>; - pinctrl-names = "default"; - }; -+ -+&usb0 { -+ status = "okay"; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/082_linux-4.14.y-bpo-dts-0039-arm64-dts-meson-gxm-khadas-vim2-enable_the_usb_controller.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/082_linux-4.14.y-bpo-dts-0039-arm64-dts-meson-gxm-khadas-vim2-enable_the_usb_controller.patch deleted file mode 100644 index 2d930e1b6..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/082_linux-4.14.y-bpo-dts-0039-arm64-dts-meson-gxm-khadas-vim2-enable_the_usb_controller.patch +++ /dev/null @@ -1,28 +0,0 @@ -From 4b7b0d7b25538d2ad421a1041267d5208d3425bc Mon Sep 17 00:00:00 2001 -From: Martin Blumenstingl -Date: Mon, 26 Mar 2018 23:17:48 +0200 -Subject: [PATCH] ARM64: dts: meson-gxm-khadas-vim2: enable the USB controller - -The Khadas VIM2 board connects the dwc3 controller to an internal 4-port -USB hub which. Two of these ports are accessible directly soldered to -the board, while the other two are accessible through the 40-pin "GPIO" -header. - -Signed-off-by: Martin Blumenstingl -Signed-off-by: Kevin Hilman ---- - arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts | 4 ++++ - 1 file changed, 4 insertions(+) - -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 4fd46c1546a7e..0868da476e41f 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -@@ -406,3 +406,7 @@ - status = "okay"; - vref-supply = <&vddio_ao18>; - }; -+ -+&usb0 { -+ status = "okay"; -+}; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/083_linux-4.14.y-bpo-drm-0131-drm-bridge-synopsys-dw-hdmi-revert_fix_overflow_workaround_for_amlogic.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/083_linux-4.14.y-bpo-drm-0131-drm-bridge-synopsys-dw-hdmi-revert_fix_overflow_workaround_for_amlogic.patch deleted file mode 100644 index bf1023a1c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/083_linux-4.14.y-bpo-drm-0131-drm-bridge-synopsys-dw-hdmi-revert_fix_overflow_workaround_for_amlogic.patch +++ /dev/null @@ -1,21 +0,0 @@ -diff --git a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -index 4db31b895..bf14214fa 100644 ---- a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -+++ b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -@@ -1634,8 +1634,6 @@ static void dw_hdmi_clear_overflow(struct dw_hdmi *hdmi) - * (and possibly on the platform). So far only i.MX6Q (v1.30a) and - * i.MX6DL (v1.31a) have been identified as needing the workaround, with - * 4 and 1 iterations respectively. -- * The Amlogic Meson GX SoCs (v2.01a) have been identified as needing -- * the workaround with a single iteration. - */ - - switch (hdmi->version) { -@@ -1643,7 +1641,6 @@ static void dw_hdmi_clear_overflow(struct dw_hdmi *hdmi) - count = 4; - break; - case 0x131a: -- case 0x201a: - count = 1; - break; - default: diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/084_linux-4.14.y-bpo-drm-0132-drm-bridge-synopsys-dw-hdmi-enable_cec_clock.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/084_linux-4.14.y-bpo-drm-0132-drm-bridge-synopsys-dw-hdmi-enable_cec_clock.patch deleted file mode 100644 index 07b93d4b4..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/084_linux-4.14.y-bpo-drm-0132-drm-bridge-synopsys-dw-hdmi-enable_cec_clock.patch +++ /dev/null @@ -1,87 +0,0 @@ -From ebe32c3e282a62974b190b9d514864fc0d56716e Mon Sep 17 00:00:00 2001 -From: Pierre-Hugues Husson -Date: Sat, 25 Nov 2017 21:18:44 +0100 -Subject: [PATCH] drm/bridge: synopsys/dw-hdmi: Enable cec clock - -Support the "cec" optional clock. The documentation already mentions "cec" -optional clock and it is used by several boards, but currently the driver -doesn't enable it, thus preventing cec from working on those boards. - -And even worse: a /dev/cecX device will appear for those boards, but it -won't be functioning without configuring this clock. - -Changes: -v4: -- Change commit message to stress the importance of this patch - -v3: -- Drop useless braces - -v2: -- Separate ENOENT errors from others -- Propagate other errors (especially -EPROBE_DEFER) - -Signed-off-by: Pierre-Hugues Husson -Signed-off-by: Archit Taneja -Link: https://patchwork.freedesktop.org/patch/msgid/20171125201844.11353-1-phh@phh.me ---- - drivers/gpu/drm/bridge/synopsys/dw-hdmi.c | 25 +++++++++++++++++++++++++ - 1 file changed, 25 insertions(+) - -diff --git a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -index bf14214fa4640..b72259bf6e2fb 100644 ---- a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -+++ b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -@@ -138,6 +138,7 @@ struct dw_hdmi { - struct device *dev; - struct clk *isfr_clk; - struct clk *iahb_clk; -+ struct clk *cec_clk; - struct dw_hdmi_i2c *i2c; - - struct hdmi_data_info hdmi_data; -@@ -2382,6 +2383,26 @@ __dw_hdmi_probe(struct platform_device *pdev, - goto err_isfr; - } - -+ hdmi->cec_clk = devm_clk_get(hdmi->dev, "cec"); -+ if (PTR_ERR(hdmi->cec_clk) == -ENOENT) { -+ hdmi->cec_clk = NULL; -+ } else if (IS_ERR(hdmi->cec_clk)) { -+ ret = PTR_ERR(hdmi->cec_clk); -+ if (ret != -EPROBE_DEFER) -+ dev_err(hdmi->dev, "Cannot get HDMI cec clock: %d\n", -+ ret); -+ -+ hdmi->cec_clk = NULL; -+ goto err_iahb; -+ } else { -+ ret = clk_prepare_enable(hdmi->cec_clk); -+ if (ret) { -+ dev_err(hdmi->dev, "Cannot enable HDMI cec clock: %d\n", -+ ret); -+ goto err_iahb; -+ } -+ } -+ - /* Product and revision IDs */ - hdmi->version = (hdmi_readb(hdmi, HDMI_DESIGN_ID) << 8) - | (hdmi_readb(hdmi, HDMI_REVISION_ID) << 0); -@@ -2518,6 +2539,8 @@ __dw_hdmi_probe(struct platform_device *pdev, - cec_notifier_put(hdmi->cec_notifier); - - clk_disable_unprepare(hdmi->iahb_clk); -+ if (hdmi->cec_clk) -+ clk_disable_unprepare(hdmi->cec_clk); - err_isfr: - clk_disable_unprepare(hdmi->isfr_clk); - err_res: -@@ -2541,6 +2564,8 @@ static void __dw_hdmi_remove(struct dw_hdmi *hdmi) - - clk_disable_unprepare(hdmi->iahb_clk); - clk_disable_unprepare(hdmi->isfr_clk); -+ if (hdmi->cec_clk) -+ clk_disable_unprepare(hdmi->cec_clk); - - if (hdmi->i2c) - i2c_del_adapter(&hdmi->i2c->adap); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/085_linux-4.14.y-bpo-drm-0133-drm-bridge-synopsys-dw-hdmi-enable_workaround_for_v1.32a.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/085_linux-4.14.y-bpo-drm-0133-drm-bridge-synopsys-dw-hdmi-enable_workaround_for_v1.32a.patch deleted file mode 100644 index abf433bf3..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/085_linux-4.14.y-bpo-drm-0133-drm-bridge-synopsys-dw-hdmi-enable_workaround_for_v1.32a.patch +++ /dev/null @@ -1,45 +0,0 @@ -From 46d1b42bfac6ea085169a23b266178719b19a778 Mon Sep 17 00:00:00 2001 -From: Jernej Skrabec -Date: Wed, 14 Feb 2018 21:08:57 +0100 -Subject: [PATCH] drm/bridge/synopsys: dw-hdmi: Enable workaround for v1.32a - -Allwinner SoCs have dw hdmi controller v1.32a which exhibits same -magenta line issue as i.MX6Q and i.MX6DL. Enable workaround for it. - -Tests show that one iteration is enough. - -Acked-by: Laurent Pinchart -Reviewed-by: Archit Taneja -Signed-off-by: Jernej Skrabec -Signed-off-by: Maxime Ripard -Link: https://patchwork.freedesktop.org/patch/msgid/20180214200906.31509-4-jernej.skrabec@siol.net ---- - drivers/gpu/drm/bridge/synopsys/dw-hdmi.c | 8 +++++--- - 1 file changed, 5 insertions(+), 3 deletions(-) - -diff --git a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -index a38db40ce990d..7ca14d7325b51 100644 ---- a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -+++ b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -@@ -1634,9 +1634,10 @@ static void dw_hdmi_clear_overflow(struct dw_hdmi *hdmi) - * then write one of the FC registers several times. - * - * The number of iterations matters and depends on the HDMI TX revision -- * (and possibly on the platform). So far only i.MX6Q (v1.30a) and -- * i.MX6DL (v1.31a) have been identified as needing the workaround, with -- * 4 and 1 iterations respectively. -+ * (and possibly on the platform). So far i.MX6Q (v1.30a), i.MX6DL -+ * (v1.31a) and multiple Allwinner SoCs (v1.32a) have been identified -+ * as needing the workaround, with 4 iterations for v1.30a and 1 -+ * iteration for others. - */ - - switch (hdmi->version) { -@@ -1644,6 +1645,7 @@ static void dw_hdmi_clear_overflow(struct dw_hdmi *hdmi) - count = 4; - break; - case 0x131a: -+ case 0x132a: - count = 1; - break; - default: diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/086_linux-4.14.y-bpo-drm-0134-drm-bridge-dw-hdmi-fix_overflow_workaround_for_amlogic.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/086_linux-4.14.y-bpo-drm-0134-drm-bridge-dw-hdmi-fix_overflow_workaround_for_amlogic.patch deleted file mode 100644 index 76e33dd49..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/086_linux-4.14.y-bpo-drm-0134-drm-bridge-dw-hdmi-fix_overflow_workaround_for_amlogic.patch +++ /dev/null @@ -1,41 +0,0 @@ -From 9c305eb442f3b371fc722ade827bbf673514123e Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Fri, 23 Feb 2018 12:44:37 +0100 -Subject: [PATCH] drm: bridge: dw-hdmi: Fix overflow workaround for Amlogic - Meson GX SoCs - -The Amlogic Meson GX SoCs, embedded the v2.01a controller, has been also -identified needing this workaround. -This patch adds the corresponding version to enable a single iteration for -this specific version. - -Fixes: be41fc55f1aa ("drm: bridge: dw-hdmi: Handle overflow workaround based on device version") -Acked-by: Archit Taneja -[narmstrong: s/identifies/identified and rebased against Jernej's change] -Signed-off-by: Neil Armstrong -Link: https://patchwork.freedesktop.org/patch/msgid/1519386277-25902-1-git-send-email-narmstrong@baylibre.com ---- - drivers/gpu/drm/bridge/synopsys/dw-hdmi.c | 3 +++ - 1 file changed, 3 insertions(+) - -diff --git a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -index f9802399cc0de..53ebbe2904b66 100644 ---- a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -+++ b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -@@ -1654,6 +1654,8 @@ static void dw_hdmi_clear_overflow(struct dw_hdmi *hdmi) - * (v1.31a) and multiple Allwinner SoCs (v1.32a) have been identified - * as needing the workaround, with 4 iterations for v1.30a and 1 - * iteration for others. -+ * The Amlogic Meson GX SoCs (v2.01a) have been identified as needing -+ * the workaround with a single iteration. - */ - - switch (hdmi->version) { -@@ -1662,6 +1664,7 @@ static void dw_hdmi_clear_overflow(struct dw_hdmi *hdmi) - break; - case 0x131a: - case 0x132a: -+ case 0x201a: - count = 1; - break; - default: diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/087_linux-4.14.y-bpo-drm-0135-drm-bridge-synopsys-dw-hdmi-export_some_phy_related.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/087_linux-4.14.y-bpo-drm-0135-drm-bridge-synopsys-dw-hdmi-export_some_phy_related.patch deleted file mode 100644 index d3b3332cb..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/087_linux-4.14.y-bpo-drm-0135-drm-bridge-synopsys-dw-hdmi-export_some_phy_related.patch +++ /dev/null @@ -1,187 +0,0 @@ -From 5765916afa4e859b92457a4a14f82ef2a9876758 Mon Sep 17 00:00:00 2001 -From: Jernej Skrabec -Date: Wed, 14 Feb 2018 21:08:58 +0100 -Subject: [PATCH] drm/bridge/synopsys: dw-hdmi: Export some PHY related - functions - -Parts of PHY code could be useful also for custom PHYs. For example, -Allwinner A83T has custom PHY which is probably Synopsys gen2 PHY -with few additional memory mapped registers, so most of the Synopsys PHY -related code could be reused. - -Functions exported here are actually not specific to Synopsys PHYs but -to DWC HDMI controller PHY interface. This means that even if the PHY is -completely custom, i.e. not designed by Synopsys, exported functions can -be useful. - -Reviewed-by: Archit Taneja -Reviewed-by: Neil Armstrong -Reviewed-by: Laurent Pinchart -Signed-off-by: Jernej Skrabec -Signed-off-by: Maxime Ripard -Link: https://patchwork.freedesktop.org/patch/msgid/20180214200906.31509-5-jernej.skrabec@siol.net ---- - drivers/gpu/drm/bridge/synopsys/dw-hdmi.c | 44 +++++++++++++++++++++---------- - drivers/gpu/drm/meson/meson_dw_hdmi.c | 8 +++--- - include/drm/bridge/dw_hdmi.h | 11 ++++++++ - 3 files changed, 45 insertions(+), 18 deletions(-) - -diff --git a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -index 7ca14d7325b51..7d80f4b566831 100644 ---- a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -+++ b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -@@ -1037,19 +1037,21 @@ static void dw_hdmi_phy_enable_svsret(struct dw_hdmi *hdmi, u8 enable) - HDMI_PHY_CONF0_SVSRET_MASK); - } - --static void dw_hdmi_phy_gen2_pddq(struct dw_hdmi *hdmi, u8 enable) -+void dw_hdmi_phy_gen2_pddq(struct dw_hdmi *hdmi, u8 enable) - { - hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0, - HDMI_PHY_CONF0_GEN2_PDDQ_OFFSET, - HDMI_PHY_CONF0_GEN2_PDDQ_MASK); - } -+EXPORT_SYMBOL_GPL(dw_hdmi_phy_gen2_pddq); - --static void dw_hdmi_phy_gen2_txpwron(struct dw_hdmi *hdmi, u8 enable) -+void dw_hdmi_phy_gen2_txpwron(struct dw_hdmi *hdmi, u8 enable) - { - hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0, - HDMI_PHY_CONF0_GEN2_TXPWRON_OFFSET, - HDMI_PHY_CONF0_GEN2_TXPWRON_MASK); - } -+EXPORT_SYMBOL_GPL(dw_hdmi_phy_gen2_txpwron); - - static void dw_hdmi_phy_sel_data_en_pol(struct dw_hdmi *hdmi, u8 enable) - { -@@ -1065,6 +1067,22 @@ static void dw_hdmi_phy_sel_interface_control(struct dw_hdmi *hdmi, u8 enable) - HDMI_PHY_CONF0_SELDIPIF_MASK); - } - -+void dw_hdmi_phy_reset(struct dw_hdmi *hdmi) -+{ -+ /* PHY reset. The reset signal is active high on Gen2 PHYs. */ -+ hdmi_writeb(hdmi, HDMI_MC_PHYRSTZ_PHYRSTZ, HDMI_MC_PHYRSTZ); -+ hdmi_writeb(hdmi, 0, HDMI_MC_PHYRSTZ); -+} -+EXPORT_SYMBOL_GPL(dw_hdmi_phy_reset); -+ -+void dw_hdmi_phy_i2c_set_addr(struct dw_hdmi *hdmi, u8 address) -+{ -+ hdmi_phy_test_clear(hdmi, 1); -+ hdmi_writeb(hdmi, address, HDMI_PHY_I2CM_SLAVE_ADDR); -+ hdmi_phy_test_clear(hdmi, 0); -+} -+EXPORT_SYMBOL_GPL(dw_hdmi_phy_i2c_set_addr); -+ - static void dw_hdmi_phy_power_off(struct dw_hdmi *hdmi) - { - const struct dw_hdmi_phy_data *phy = hdmi->phy.data; -@@ -1203,16 +1221,11 @@ static int hdmi_phy_configure(struct dw_hdmi *hdmi) - if (phy->has_svsret) - dw_hdmi_phy_enable_svsret(hdmi, 1); - -- /* PHY reset. The reset signal is active high on Gen2 PHYs. */ -- hdmi_writeb(hdmi, HDMI_MC_PHYRSTZ_PHYRSTZ, HDMI_MC_PHYRSTZ); -- hdmi_writeb(hdmi, 0, HDMI_MC_PHYRSTZ); -+ dw_hdmi_phy_reset(hdmi); - - hdmi_writeb(hdmi, HDMI_MC_HEACPHY_RST_ASSERT, HDMI_MC_HEACPHY_RST); - -- hdmi_phy_test_clear(hdmi, 1); -- hdmi_writeb(hdmi, HDMI_PHY_I2CM_SLAVE_ADDR_PHY_GEN2, -- HDMI_PHY_I2CM_SLAVE_ADDR); -- hdmi_phy_test_clear(hdmi, 0); -+ dw_hdmi_phy_i2c_set_addr(hdmi, HDMI_PHY_I2CM_SLAVE_ADDR_PHY_GEN2); - - /* Write to the PHY as configured by the platform */ - if (pdata->configure_phy) -@@ -1251,15 +1264,16 @@ static void dw_hdmi_phy_disable(struct dw_hdmi *hdmi, void *data) - dw_hdmi_phy_power_off(hdmi); - } - --static enum drm_connector_status dw_hdmi_phy_read_hpd(struct dw_hdmi *hdmi, -- void *data) -+enum drm_connector_status dw_hdmi_phy_read_hpd(struct dw_hdmi *hdmi, -+ void *data) - { - return hdmi_readb(hdmi, HDMI_PHY_STAT0) & HDMI_PHY_HPD ? - connector_status_connected : connector_status_disconnected; - } -+EXPORT_SYMBOL_GPL(dw_hdmi_phy_read_hpd); - --static void dw_hdmi_phy_update_hpd(struct dw_hdmi *hdmi, void *data, -- bool force, bool disabled, bool rxsense) -+void dw_hdmi_phy_update_hpd(struct dw_hdmi *hdmi, void *data, -+ bool force, bool disabled, bool rxsense) - { - u8 old_mask = hdmi->phy_mask; - -@@ -1271,8 +1285,9 @@ static void dw_hdmi_phy_update_hpd(struct dw_hdmi *hdmi, void *data, - if (old_mask != hdmi->phy_mask) - hdmi_writeb(hdmi, hdmi->phy_mask, HDMI_PHY_MASK0); - } -+EXPORT_SYMBOL_GPL(dw_hdmi_phy_update_hpd); - --static void dw_hdmi_phy_setup_hpd(struct dw_hdmi *hdmi, void *data) -+void dw_hdmi_phy_setup_hpd(struct dw_hdmi *hdmi, void *data) - { - /* - * Configure the PHY RX SENSE and HPD interrupts polarities and clear -@@ -1291,6 +1306,7 @@ static void dw_hdmi_phy_setup_hpd(struct dw_hdmi *hdmi, void *data) - hdmi_writeb(hdmi, ~(HDMI_IH_PHY_STAT0_HPD | HDMI_IH_PHY_STAT0_RX_SENSE), - HDMI_IH_MUTE_PHY_STAT0); - } -+EXPORT_SYMBOL_GPL(dw_hdmi_phy_setup_hpd); - - static const struct dw_hdmi_phy_ops dw_hdmi_synopsys_phy_ops = { - .init = dw_hdmi_phy_init, -diff --git a/drivers/gpu/drm/meson/meson_dw_hdmi.c b/drivers/gpu/drm/meson/meson_dw_hdmi.c -index 17de3afd98f6a..e8c3ef8a94ce3 100644 ---- a/drivers/gpu/drm/meson/meson_dw_hdmi.c -+++ b/drivers/gpu/drm/meson/meson_dw_hdmi.c -@@ -302,7 +302,7 @@ static void meson_hdmi_phy_setup_mode(struct meson_dw_hdmi *dw_hdmi, - } - } - --static inline void dw_hdmi_phy_reset(struct meson_dw_hdmi *dw_hdmi) -+static inline void meson_dw_hdmi_phy_reset(struct meson_dw_hdmi *dw_hdmi) - { - struct meson_drm *priv = dw_hdmi->priv; - -@@ -409,9 +409,9 @@ static int dw_hdmi_phy_init(struct dw_hdmi *hdmi, void *data, - msleep(100); - - /* Reset PHY 3 times in a row */ -- dw_hdmi_phy_reset(dw_hdmi); -- dw_hdmi_phy_reset(dw_hdmi); -- dw_hdmi_phy_reset(dw_hdmi); -+ meson_dw_hdmi_phy_reset(dw_hdmi); -+ meson_dw_hdmi_phy_reset(dw_hdmi); -+ meson_dw_hdmi_phy_reset(dw_hdmi); - - /* Temporary Disable VENC video stream */ - if (priv->venc.hdmi_use_enci) -diff --git a/include/drm/bridge/dw_hdmi.h b/include/drm/bridge/dw_hdmi.h -index 182f83283e247..f3f3f0e1b2d3a 100644 ---- a/include/drm/bridge/dw_hdmi.h -+++ b/include/drm/bridge/dw_hdmi.h -@@ -157,7 +157,18 @@ void dw_hdmi_audio_enable(struct dw_hdmi *hdmi); - void dw_hdmi_audio_disable(struct dw_hdmi *hdmi); - - /* PHY configuration */ -+void dw_hdmi_phy_i2c_set_addr(struct dw_hdmi *hdmi, u8 address); - void dw_hdmi_phy_i2c_write(struct dw_hdmi *hdmi, unsigned short data, - unsigned char addr); - -+void dw_hdmi_phy_gen2_pddq(struct dw_hdmi *hdmi, u8 enable); -+void dw_hdmi_phy_gen2_txpwron(struct dw_hdmi *hdmi, u8 enable); -+void dw_hdmi_phy_reset(struct dw_hdmi *hdmi); -+ -+enum drm_connector_status dw_hdmi_phy_read_hpd(struct dw_hdmi *hdmi, -+ void *data); -+void dw_hdmi_phy_update_hpd(struct dw_hdmi *hdmi, void *data, -+ bool force, bool disabled, bool rxsense); -+void dw_hdmi_phy_setup_hpd(struct dw_hdmi *hdmi, void *data); -+ - #endif /* __IMX_HDMI_H__ */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/088_linux-4.14.y-bpo-drm-0136-drm-bridge-synopsys-dw-hdmi-dont_clobber_drvdata.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/088_linux-4.14.y-bpo-drm-0136-drm-bridge-synopsys-dw-hdmi-dont_clobber_drvdata.patch deleted file mode 100644 index d3b30c4c7..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/088_linux-4.14.y-bpo-drm-0136-drm-bridge-synopsys-dw-hdmi-dont_clobber_drvdata.patch +++ /dev/null @@ -1,294 +0,0 @@ -From eea034af90c64802fd747a9dc534c26a7ebe7754 Mon Sep 17 00:00:00 2001 -From: Jernej Skrabec -Date: Wed, 14 Feb 2018 21:08:59 +0100 -Subject: [PATCH] drm/bridge/synopsys: dw-hdmi: don't clobber drvdata - -dw_hdmi shouldn't set drvdata since some drivers might need to store -it's own data there. Rework dw_hdmi in a way to return struct dw_hdmi -instead to store it in drvdata. This way drivers are responsible to -store and pass structure when needed. - -Idea was taken from the following commit: -8242ecbd597d ("drm/bridge/synopsys: stop clobbering drvdata") - -Cc: p.zabel@pengutronix.de -Cc: Laurent.pinchart@ideasonboard.com -Cc: hjc@rock-chips.com -Acked-by: Heiko Stuebner -Acked-by: Neil Armstrong -Reviewed-by: Archit Taneja -Tested-by: Heiko Stuebner -Signed-off-by: Jernej Skrabec -Signed-off-by: Maxime Ripard -Link: https://patchwork.freedesktop.org/patch/msgid/20180214200906.31509-6-jernej.skrabec@siol.net ---- - drivers/gpu/drm/bridge/synopsys/dw-hdmi.c | 31 ++++++++++++----------------- - drivers/gpu/drm/imx/dw_hdmi-imx.c | 13 +++++++++--- - drivers/gpu/drm/meson/meson_dw_hdmi.c | 14 +++++++++---- - drivers/gpu/drm/rcar-du/rcar_dw_hdmi.c | 12 +++++++++-- - drivers/gpu/drm/rockchip/dw_hdmi-rockchip.c | 13 +++++++++--- - include/drm/bridge/dw_hdmi.h | 13 ++++++------ - 6 files changed, 60 insertions(+), 36 deletions(-) - -diff --git a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -index 7d80f4b566831..f9802399cc0de 100644 ---- a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -+++ b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c -@@ -2543,8 +2543,6 @@ __dw_hdmi_probe(struct platform_device *pdev, - if (hdmi->i2c) - dw_hdmi_i2c_init(hdmi); - -- platform_set_drvdata(pdev, hdmi); -- - return hdmi; - - err_iahb: -@@ -2594,25 +2592,23 @@ static void __dw_hdmi_remove(struct dw_hdmi *hdmi) - /* ----------------------------------------------------------------------------- - * Probe/remove API, used from platforms based on the DRM bridge API. - */ --int dw_hdmi_probe(struct platform_device *pdev, -- const struct dw_hdmi_plat_data *plat_data) -+struct dw_hdmi *dw_hdmi_probe(struct platform_device *pdev, -+ const struct dw_hdmi_plat_data *plat_data) - { - struct dw_hdmi *hdmi; - - hdmi = __dw_hdmi_probe(pdev, plat_data); - if (IS_ERR(hdmi)) -- return PTR_ERR(hdmi); -+ return hdmi; - - drm_bridge_add(&hdmi->bridge); - -- return 0; -+ return hdmi; - } - EXPORT_SYMBOL_GPL(dw_hdmi_probe); - --void dw_hdmi_remove(struct platform_device *pdev) -+void dw_hdmi_remove(struct dw_hdmi *hdmi) - { -- struct dw_hdmi *hdmi = platform_get_drvdata(pdev); -- - drm_bridge_remove(&hdmi->bridge); - - __dw_hdmi_remove(hdmi); -@@ -2622,31 +2618,30 @@ EXPORT_SYMBOL_GPL(dw_hdmi_remove); - /* ----------------------------------------------------------------------------- - * Bind/unbind API, used from platforms based on the component framework. - */ --int dw_hdmi_bind(struct platform_device *pdev, struct drm_encoder *encoder, -- const struct dw_hdmi_plat_data *plat_data) -+struct dw_hdmi *dw_hdmi_bind(struct platform_device *pdev, -+ struct drm_encoder *encoder, -+ const struct dw_hdmi_plat_data *plat_data) - { - struct dw_hdmi *hdmi; - int ret; - - hdmi = __dw_hdmi_probe(pdev, plat_data); - if (IS_ERR(hdmi)) -- return PTR_ERR(hdmi); -+ return hdmi; - - ret = drm_bridge_attach(encoder, &hdmi->bridge, NULL); - if (ret) { -- dw_hdmi_remove(pdev); -+ dw_hdmi_remove(hdmi); - DRM_ERROR("Failed to initialize bridge with drm\n"); -- return ret; -+ return ERR_PTR(ret); - } - -- return 0; -+ return hdmi; - } - EXPORT_SYMBOL_GPL(dw_hdmi_bind); - --void dw_hdmi_unbind(struct device *dev) -+void dw_hdmi_unbind(struct dw_hdmi *hdmi) - { -- struct dw_hdmi *hdmi = dev_get_drvdata(dev); -- - __dw_hdmi_remove(hdmi); - } - EXPORT_SYMBOL_GPL(dw_hdmi_unbind); -diff --git a/drivers/gpu/drm/imx/dw_hdmi-imx.c b/drivers/gpu/drm/imx/dw_hdmi-imx.c -index b62763aa87069..fe6becdcc29ed 100644 ---- a/drivers/gpu/drm/imx/dw_hdmi-imx.c -+++ b/drivers/gpu/drm/imx/dw_hdmi-imx.c -@@ -25,6 +25,7 @@ - struct imx_hdmi { - struct device *dev; - struct drm_encoder encoder; -+ struct dw_hdmi *hdmi; - struct regmap *regmap; - }; - -@@ -239,14 +240,18 @@ static int dw_hdmi_imx_bind(struct device *dev, struct device *master, - drm_encoder_init(drm, encoder, &dw_hdmi_imx_encoder_funcs, - DRM_MODE_ENCODER_TMDS, NULL); - -- ret = dw_hdmi_bind(pdev, encoder, plat_data); -+ platform_set_drvdata(pdev, hdmi); -+ -+ hdmi->hdmi = dw_hdmi_bind(pdev, encoder, plat_data); - - /* - * If dw_hdmi_bind() fails we'll never call dw_hdmi_unbind(), - * which would have called the encoder cleanup. Do it manually. - */ -- if (ret) -+ if (IS_ERR(hdmi->hdmi)) { -+ ret = PTR_ERR(hdmi->hdmi); - drm_encoder_cleanup(encoder); -+ } - - return ret; - } -@@ -254,7 +259,9 @@ static int dw_hdmi_imx_bind(struct device *dev, struct device *master, - static void dw_hdmi_imx_unbind(struct device *dev, struct device *master, - void *data) - { -- return dw_hdmi_unbind(dev); -+ struct imx_hdmi *hdmi = dev_get_drvdata(dev); -+ -+ dw_hdmi_unbind(hdmi->hdmi); - } - - static const struct component_ops dw_hdmi_imx_ops = { -diff --git a/drivers/gpu/drm/meson/meson_dw_hdmi.c b/drivers/gpu/drm/meson/meson_dw_hdmi.c -index e8c3ef8a94ce3..d49af17310c99 100644 ---- a/drivers/gpu/drm/meson/meson_dw_hdmi.c -+++ b/drivers/gpu/drm/meson/meson_dw_hdmi.c -@@ -140,6 +140,7 @@ struct meson_dw_hdmi { - struct clk *venci_clk; - struct regulator *hdmi_supply; - u32 irq_stat; -+ struct dw_hdmi *hdmi; - }; - #define encoder_to_meson_dw_hdmi(x) \ - container_of(x, struct meson_dw_hdmi, encoder) -@@ -878,9 +879,12 @@ static int meson_dw_hdmi_bind(struct device *dev, struct device *master, - dw_plat_data->input_bus_format = MEDIA_BUS_FMT_YUV8_1X24; - dw_plat_data->input_bus_encoding = V4L2_YCBCR_ENC_709; - -- ret = dw_hdmi_bind(pdev, encoder, &meson_dw_hdmi->dw_plat_data); -- if (ret) -- return ret; -+ platform_set_drvdata(pdev, meson_dw_hdmi); -+ -+ meson_dw_hdmi->hdmi = dw_hdmi_bind(pdev, encoder, -+ &meson_dw_hdmi->dw_plat_data); -+ if (IS_ERR(meson_dw_hdmi->hdmi)) -+ return PTR_ERR(meson_dw_hdmi->hdmi); - - DRM_DEBUG_DRIVER("HDMI controller initialized\n"); - -@@ -890,7 +894,9 @@ static int meson_dw_hdmi_bind(struct device *dev, struct device *master, - static void meson_dw_hdmi_unbind(struct device *dev, struct device *master, - void *data) - { -- dw_hdmi_unbind(dev); -+ struct meson_dw_hdmi *meson_dw_hdmi = dev_get_drvdata(dev); -+ -+ dw_hdmi_unbind(meson_dw_hdmi->hdmi); - } - - static const struct component_ops meson_dw_hdmi_ops = { -diff --git a/drivers/gpu/drm/rcar-du/rcar_dw_hdmi.c b/drivers/gpu/drm/rcar-du/rcar_dw_hdmi.c -index dc85b53d58ef2..3bebc6821e9cc 100644 ---- a/drivers/gpu/drm/rcar-du/rcar_dw_hdmi.c -+++ b/drivers/gpu/drm/rcar-du/rcar_dw_hdmi.c -@@ -68,12 +68,20 @@ static const struct dw_hdmi_plat_data rcar_dw_hdmi_plat_data = { - - static int rcar_dw_hdmi_probe(struct platform_device *pdev) - { -- return dw_hdmi_probe(pdev, &rcar_dw_hdmi_plat_data); -+ struct dw_hdmi *hdmi; -+ -+ hdmi = dw_hdmi_probe(pdev, &rcar_dw_hdmi_plat_data); -+ if (IS_ERR(hdmi)) -+ return PTR_ERR(hdmi); -+ -+ platform_set_drvdata(pdev, hdmi); - } - - static int rcar_dw_hdmi_remove(struct platform_device *pdev) - { -- dw_hdmi_remove(pdev); -+ struct dw_hdmi *hdmi = platform_get_drvdata(dev); -+ -+ dw_hdmi_remove(hdmi); - - return 0; - } -diff --git a/drivers/gpu/drm/rockchip/dw_hdmi-rockchip.c b/drivers/gpu/drm/rockchip/dw_hdmi-rockchip.c -index 1eb02a82fd918..3574b0ae2ad19 100644 ---- a/drivers/gpu/drm/rockchip/dw_hdmi-rockchip.c -+++ b/drivers/gpu/drm/rockchip/dw_hdmi-rockchip.c -@@ -48,6 +48,7 @@ struct rockchip_hdmi { - const struct rockchip_hdmi_chip_data *chip_data; - struct clk *vpll_clk; - struct clk *grf_clk; -+ struct dw_hdmi *hdmi; - }; - - #define to_rockchip_hdmi(x) container_of(x, struct rockchip_hdmi, x) -@@ -377,14 +378,18 @@ static int dw_hdmi_rockchip_bind(struct device *dev, struct device *master, - drm_encoder_init(drm, encoder, &dw_hdmi_rockchip_encoder_funcs, - DRM_MODE_ENCODER_TMDS, NULL); - -- ret = dw_hdmi_bind(pdev, encoder, plat_data); -+ platform_set_drvdata(pdev, hdmi); -+ -+ hdmi->hdmi = dw_hdmi_bind(pdev, encoder, plat_data); - - /* - * If dw_hdmi_bind() fails we'll never call dw_hdmi_unbind(), - * which would have called the encoder cleanup. Do it manually. - */ -- if (ret) -+ if (IS_ERR(hdmi->hdmi)) { -+ ret = PTR_ERR(hdmi->hdmi); - drm_encoder_cleanup(encoder); -+ } - - return ret; - } -@@ -392,7 +397,9 @@ static int dw_hdmi_rockchip_bind(struct device *dev, struct device *master, - static void dw_hdmi_rockchip_unbind(struct device *dev, struct device *master, - void *data) - { -- return dw_hdmi_unbind(dev); -+ struct rockchip_hdmi *hdmi = dev_get_drvdata(dev); -+ -+ dw_hdmi_unbind(hdmi->hdmi); - } - - static const struct component_ops dw_hdmi_rockchip_ops = { -diff --git a/include/drm/bridge/dw_hdmi.h b/include/drm/bridge/dw_hdmi.h -index f3f3f0e1b2d3a..dd2a8cf7d20b8 100644 ---- a/include/drm/bridge/dw_hdmi.h -+++ b/include/drm/bridge/dw_hdmi.h -@@ -143,12 +143,13 @@ struct dw_hdmi_plat_data { - unsigned long mpixelclock); - }; - --int dw_hdmi_probe(struct platform_device *pdev, -- const struct dw_hdmi_plat_data *plat_data); --void dw_hdmi_remove(struct platform_device *pdev); --void dw_hdmi_unbind(struct device *dev); --int dw_hdmi_bind(struct platform_device *pdev, struct drm_encoder *encoder, -- const struct dw_hdmi_plat_data *plat_data); -+struct dw_hdmi *dw_hdmi_probe(struct platform_device *pdev, -+ const struct dw_hdmi_plat_data *plat_data); -+void dw_hdmi_remove(struct dw_hdmi *hdmi); -+void dw_hdmi_unbind(struct dw_hdmi *hdmi); -+struct dw_hdmi *dw_hdmi_bind(struct platform_device *pdev, -+ struct drm_encoder *encoder, -+ const struct dw_hdmi_plat_data *plat_data); - - void dw_hdmi_setup_rx_sense(struct device *dev, bool hpd, bool rx_sense); - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/089_linux-4.17-yocto-meson64-0002-drm-meson-select-dw-hdmi-i2s-audio-for-meson-hdmi.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/089_linux-4.17-yocto-meson64-0002-drm-meson-select-dw-hdmi-i2s-audio-for-meson-hdmi.patch deleted file mode 100644 index 6f1d3e25d..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/089_linux-4.17-yocto-meson64-0002-drm-meson-select-dw-hdmi-i2s-audio-for-meson-hdmi.patch +++ /dev/null @@ -1,23 +0,0 @@ -From 13253828e625fad26802c497672d1ebc2588a61e Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Tue, 14 Feb 2017 19:18:04 +0100 -Subject: [PATCH 02/14] 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/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/090_linux-4.17-yocto-meson64-0003-ASoC-meson-add-meson-audio-core-driver.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/090_linux-4.17-yocto-meson64-0003-ASoC-meson-add-meson-audio-core-driver.patch deleted file mode 100644 index b7efebb87..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/090_linux-4.17-yocto-meson64-0003-ASoC-meson-add-meson-audio-core-driver.patch +++ /dev/null @@ -1,312 +0,0 @@ -From 0d24a1c3cd2bc015eb3c22e7b1322ab39a5f8dda Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 30 Mar 2017 11:49:55 +0200 -Subject: [PATCH 03/14] 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 41af6b9..1cf11cf 100644 ---- a/sound/soc/Kconfig -+++ b/sound/soc/Kconfig -@@ -57,6 +57,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 8d92492..4d642ea 100644 ---- a/sound/soc/Makefile -+++ b/sound/soc/Makefile -@@ -38,6 +38,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/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/091_linux-4.17-yocto-meson64-0004-ASoC-meson-add-register-definitions.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/091_linux-4.17-yocto-meson64-0004-ASoC-meson-add-register-definitions.patch deleted file mode 100644 index 742e8b3df..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/091_linux-4.17-yocto-meson64-0004-ASoC-meson-add-register-definitions.patch +++ /dev/null @@ -1,361 +0,0 @@ -From 04b110f288ec7436b0d714b090498562ab93c04b Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 30 Mar 2017 12:00:10 +0200 -Subject: [PATCH 04/14] 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/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/092_linux-4.17-yocto-meson64-0005-ASoC-meson-add-aiu-i2s-dma-support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/092_linux-4.17-yocto-meson64-0005-ASoC-meson-add-aiu-i2s-dma-support.patch deleted file mode 100644 index fec22f4d9..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/092_linux-4.17-yocto-meson64-0005-ASoC-meson-add-aiu-i2s-dma-support.patch +++ /dev/null @@ -1,417 +0,0 @@ -From 298241f7155bfeed607b68840950c4d193cbaf55 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 30 Mar 2017 12:14:40 +0200 -Subject: [PATCH 05/14] 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/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/093_linux-4.17-yocto-meson64-0006-ASoC-meson-add-initial-i2s-dai-support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/093_linux-4.17-yocto-meson64-0006-ASoC-meson-add-initial-i2s-dai-support.patch deleted file mode 100644 index c3cd903ee..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/093_linux-4.17-yocto-meson64-0006-ASoC-meson-add-initial-i2s-dai-support.patch +++ /dev/null @@ -1,515 +0,0 @@ -From 583f1a4a1120f751a26f7c78218e54e449930308 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Thu, 30 Mar 2017 12:17:27 +0200 -Subject: [PATCH 06/14] 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/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/094_linux-4.17-yocto-meson64-0007-snd-meson-activate-HDMI-audio-path.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/094_linux-4.17-yocto-meson64-0007-snd-meson-activate-HDMI-audio-path.patch deleted file mode 100644 index 6ade016d4..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/094_linux-4.17-yocto-meson64-0007-snd-meson-activate-HDMI-audio-path.patch +++ /dev/null @@ -1,55 +0,0 @@ -From 7833a66101aabad7f882fdf6dee62c7de9c3c71b Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Fri, 7 Jul 2017 17:39:21 +0200 -Subject: [PATCH 07/14] 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/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/095_linux-4.17-yocto-meson64-0010-ARM64-defconfig-enable-audio-support-for-meson-SoCs-.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/095_linux-4.17-yocto-meson64-0010-ARM64-defconfig-enable-audio-support-for-meson-SoCs-.patch deleted file mode 100644 index 7fd89f084..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/095_linux-4.17-yocto-meson64-0010-ARM64-defconfig-enable-audio-support-for-meson-SoCs-.patch +++ /dev/null @@ -1,31 +0,0 @@ -From e3fec781d3684fa264dfd68877b59b70a30f8929 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Fri, 31 Mar 2017 15:55:03 +0200 -Subject: [PATCH 10/14] ARM64: defconfig: enable audio support for meson SoCs - as module - -Add audio support for meson SoCs. This includes the audio core -driver and the i2s output interface - -Signed-off-by: Jerome Brunet -Signed-off-by: Neil Armstrong ---- - arch/arm64/configs/defconfig | 2 ++ - 1 file changed, 2 insertions(+) - -diff --git a/arch/arm64/configs/defconfig b/arch/arm64/configs/defconfig -index 43716e1..639cb12 100644 ---- a/arch/arm64/configs/defconfig -+++ b/arch/arm64/configs/defconfig -@@ -440,6 +440,8 @@ CONFIG_SOUND=y - CONFIG_SND=y - CONFIG_SND_SOC=y - CONFIG_SND_BCM2835_SOC_I2S=m -+CONFIG_SND_SOC_MESON=m -+CONFIG_SND_SOC_MESON_I2S=m - CONFIG_SND_SOC_SAMSUNG=y - CONFIG_SND_SOC_RCAR=m - CONFIG_SND_SOC_AK4613=m --- -2.7.4 - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/096_linux-4.17-yocto-meson64-0011-ARM64-dts-meson-gx-add-audio-controller-nodes.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/096_linux-4.17-yocto-meson64-0011-ARM64-dts-meson-gx-add-audio-controller-nodes.patch deleted file mode 100644 index c2fb3c5d8..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/096_linux-4.17-yocto-meson64-0011-ARM64-dts-meson-gx-add-audio-controller-nodes.patch +++ /dev/null @@ -1,121 +0,0 @@ -From c9a242f21d67baf22cb113ba37e9f77b96ba1027 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Wed, 20 Sep 2017 17:22:47 +0200 -Subject: [PATCH] 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-gxbb.dtsi | 23 +++++++++++++++++++++++ - arch/arm64/boot/dts/amlogic/meson-gxl.dtsi | 23 +++++++++++++++++++++++ - 3 files changed, 68 insertions(+) - -diff --git a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -index 3c31e21cbed7f..e4ebc8751fd27 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx.dtsi -@@ -197,6 +197,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"; - reg = <0x0 0x84c0 0x0 0x18>; -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -index 562c26a0ba333..67d794bee9034 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi -@@ -702,6 +702,29 @@ - <0>; /* Do Nothing */ - }; - -+&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-gxbb-saradc", "amlogic,meson-saradc"; - clocks = <&xtal>, -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -index dba365ed4bd5f..0a41e2ed490bc 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -711,6 +711,29 @@ - <0>; /* Do Nothing */ - }; - -+&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>, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/097_linux-4.17-yocto-meson64-0012-ARM64-dts-meson-gxl-add-sound-dai-cells-to-HDMI-node.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/097_linux-4.17-yocto-meson64-0012-ARM64-dts-meson-gxl-add-sound-dai-cells-to-HDMI-node.patch deleted file mode 100644 index 466ed5a62..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/097_linux-4.17-yocto-meson64-0012-ARM64-dts-meson-gxl-add-sound-dai-cells-to-HDMI-node.patch +++ /dev/null @@ -1,23 +0,0 @@ -From fb45bc4b076c17a3f9c1dab64e652dce752371c2 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Wed, 20 Sep 2017 18:01:26 +0200 -Subject: [PATCH] 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 0a41e2ed490bc..a11ac158df7a1 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl.dtsi -@@ -265,6 +265,7 @@ - <&clkc CLKID_CLK81>, - <&clkc CLKID_GCLK_VENCI_INT0>; - clock-names = "isfr", "iahb", "venci"; -+ #sound-dai-cells = <0>; - }; - - &hiubus { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/098_linux-4.17-yocto-meson64-0013-ARM64-dts-meson-activate-hdmi-audio-HDMI-enabled-boa.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/098_linux-4.17-yocto-meson64-0013-ARM64-dts-meson-activate-hdmi-audio-HDMI-enabled-boa.patch deleted file mode 100644 index 5cac91968..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/098_linux-4.17-yocto-meson64-0013-ARM64-dts-meson-activate-hdmi-audio-HDMI-enabled-boa.patch +++ /dev/null @@ -1,626 +0,0 @@ -From e6794244bc4c59ffcf1ed4cbb452836dca10ad55 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Wed, 20 Sep 2017 18:10:08 +0200 -Subject: [PATCH] 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 +++++++++++++++++++++ - arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi | 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 88e712ea757a2..7256912413e1a 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gx-p23x-q20x.dtsi -@@ -95,6 +95,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 { -@@ -104,6 +129,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 4cf7f6e80c6a0..43586e9099616 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-nexbox-a95x.dts -@@ -119,6 +119,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"; - -@@ -154,6 +179,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 54954b314a452..b24d2f79ccc34 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -@@ -110,6 +110,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 { -@@ -119,6 +144,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 ce862266b9aac..f89a094daf98d 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-p20x.dtsi -@@ -113,6 +113,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 { -@@ -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-gxbb-wetek.dtsi b/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi -index 70325b273bd2b..b3b6ce7e665b9 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-wetek.dtsi -@@ -105,6 +105,43 @@ - }; - }; - }; -+ -+ 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>; -+ }; -+ }; -+ }; -+}; -+ -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ -+&i2s_dai { -+ status = "okay"; - }; - - &cec_AO { -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 d32cf38463702..1b2171d76a7bb 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 3e3eb31748a35..9717c831a54f0 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 -@@ -84,6 +84,31 @@ - regulator-always-on; - }; - -+ 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"; -@@ -130,6 +155,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 6739697be1def..1c2f62984c8ad 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 -@@ -102,6 +102,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 { -@@ -111,6 +136,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 5896e8a5d86bc..02582371fa4e8 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxl-s905x-p212.dts -@@ -32,6 +32,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 { -@@ -41,6 +66,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 0868da476e41f..22707afa0b6d8 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-khadas-vim2.dts -@@ -85,6 +85,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"; - -@@ -205,6 +230,18 @@ - hdmi-phandle = <&hdmi_tx>; - }; - -+&audio { -+ status = "okay"; -+}; -+ -+&aiu_i2s_dma { -+ status = "okay"; -+}; -+ -+&i2s_dai { -+ status = "okay"; -+}; -+ - &cpu0 { - #cooling-cells = <2>; - }; -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 f7a1cffab4a88..1af4891bdb06b 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxm-nexbox-a1.dts -@@ -75,6 +75,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 { -@@ -84,6 +109,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/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/099_linux-4.14.y-le-amlogic-gx-0010-arm64-defconfig-add_config_meson_efuse.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/099_linux-4.14.y-le-amlogic-gx-0010-arm64-defconfig-add_config_meson_efuse.patch deleted file mode 100644 index 02f2d5fae..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/099_linux-4.14.y-le-amlogic-gx-0010-arm64-defconfig-add_config_meson_efuse.patch +++ /dev/null @@ -1,24 +0,0 @@ -From f1aaa72f808ab876ffe8c16820b5a4726b711933 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Mon, 13 Nov 2017 12:02:59 +0100 -Subject: [PATCH] ARM64: defconfig: add CONFIG_MESON_EFUSE - -Turn on CONFIG_MESON_EFUSE as module - -Signed-off-by: Jerome Brunet ---- - arch/arm64/configs/defconfig | 1 + - 1 file changed, 1 insertion(+) - -diff --git a/arch/arm64/configs/defconfig b/arch/arm64/configs/defconfig -index 34480e9af2e71..3cdfc7490707b 100644 ---- a/arch/arm64/configs/defconfig -+++ b/arch/arm64/configs/defconfig -@@ -541,6 +541,7 @@ CONFIG_PHY_XGENE=y - CONFIG_PHY_TEGRA_XUSB=y - CONFIG_QCOM_L2_PMU=y - CONFIG_QCOM_L3_PMU=y -+CONFIG_MESON_EFUSE=m - CONFIG_TEE=y - CONFIG_OPTEE=y - CONFIG_ARM_SCPI_PROTOCOL=y diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/100_linux-4.14.y-le-amlogic-gx-0011-arm64-defconfig-enable_cec_support.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/100_linux-4.14.y-le-amlogic-gx-0011-arm64-defconfig-enable_cec_support.patch deleted file mode 100644 index 143ac0634..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/100_linux-4.14.y-le-amlogic-gx-0011-arm64-defconfig-enable_cec_support.patch +++ /dev/null @@ -1,32 +0,0 @@ -From 6ea4d5e0afcdb84fc76cd5bfbc9b7d8f7009c512 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Mon, 13 Nov 2017 12:09:40 +0100 -Subject: [PATCH] ARM64: defconfig: enable CEC support - -Turn on CONFIG_CEC_SUPPORT and CONFIG_CEC_PLATFORM_DRIVERS - -Signed-off-by: Jerome Brunet ---- - arch/arm64/configs/defconfig | 2 ++ - 1 file changed, 2 insertions(+) - -diff --git a/arch/arm64/configs/defconfig b/arch/arm64/configs/defconfig -index 3cdfc7490707b..944b93b1c0268 100644 ---- a/arch/arm64/configs/defconfig -+++ b/arch/arm64/configs/defconfig -@@ -350,6 +350,7 @@ CONFIG_MEDIA_SUPPORT=m - CONFIG_MEDIA_CAMERA_SUPPORT=y - CONFIG_MEDIA_ANALOG_TV_SUPPORT=y - CONFIG_MEDIA_DIGITAL_TV_SUPPORT=y -+CONFIG_MEDIA_CEC_SUPPORT=y - CONFIG_MEDIA_CONTROLLER=y - CONFIG_MEDIA_RC_SUPPORT=y - CONFIG_RC_CORE=m -@@ -364,6 +365,7 @@ CONFIG_VIDEO_SAMSUNG_S5P_MFC=m - CONFIG_VIDEO_SAMSUNG_EXYNOS_GSC=m - CONFIG_VIDEO_RENESAS_FCP=m - CONFIG_VIDEO_RENESAS_VSP1=m -+CONFIG_CEC_PLATFORM_DRIVERS=y - CONFIG_DRM=m - CONFIG_DRM_NOUVEAU=m - CONFIG_DRM_EXYNOS=m diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/101_linux-4.14.y-le-amlogic-gx-0012-arm64-defconfig-enable_config_video_meson_ao_cec.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/101_linux-4.14.y-le-amlogic-gx-0012-arm64-defconfig-enable_config_video_meson_ao_cec.patch deleted file mode 100644 index a83f80069..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/101_linux-4.14.y-le-amlogic-gx-0012-arm64-defconfig-enable_config_video_meson_ao_cec.patch +++ /dev/null @@ -1,24 +0,0 @@ -From 0682a78ae935a272c73a281d6c320a6cd017ce28 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Mon, 13 Nov 2017 12:11:41 +0100 -Subject: [PATCH] ARM64: defconfig: enable CONFIG_VIDEO_MESON_AO_CEC - -Turn on CONFIG_VIDEO_MESON_AO_CEC as module - -Signed-off-by: Jerome Brunet ---- - arch/arm64/configs/defconfig | 1 + - 1 file changed, 1 insertion(+) - -diff --git a/arch/arm64/configs/defconfig b/arch/arm64/configs/defconfig -index 944b93b1c0268..fdf94cbd56a28 100644 ---- a/arch/arm64/configs/defconfig -+++ b/arch/arm64/configs/defconfig -@@ -366,6 +366,7 @@ CONFIG_VIDEO_SAMSUNG_EXYNOS_GSC=m - CONFIG_VIDEO_RENESAS_FCP=m - CONFIG_VIDEO_RENESAS_VSP1=m - CONFIG_CEC_PLATFORM_DRIVERS=y -+CONFIG_VIDEO_MESON_AO_CEC=m - CONFIG_DRM=m - CONFIG_DRM_NOUVEAU=m - CONFIG_DRM_EXYNOS=m diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/102_linux-4.14.y-le-amlogic-gx-0013-arm64-defconfig-enable_config_drm_dw_hdmi_cec.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/102_linux-4.14.y-le-amlogic-gx-0013-arm64-defconfig-enable_config_drm_dw_hdmi_cec.patch deleted file mode 100644 index 5e3622af2..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/102_linux-4.14.y-le-amlogic-gx-0013-arm64-defconfig-enable_config_drm_dw_hdmi_cec.patch +++ /dev/null @@ -1,24 +0,0 @@ -From d537685003beb9f008c50075e66cb245e265dea2 Mon Sep 17 00:00:00 2001 -From: Jerome Brunet -Date: Mon, 13 Nov 2017 12:15:18 +0100 -Subject: [PATCH] ARM64: defconfig: enable CONFIG_DRM_DW_HDMI_CEC - -Turn on CONFIG_DRM_DW_HDMI_CEC as module - -Signed-off-by: Jerome Brunet ---- - arch/arm64/configs/defconfig | 1 + - 1 file changed, 1 insertion(+) - -diff --git a/arch/arm64/configs/defconfig b/arch/arm64/configs/defconfig -index fdf94cbd56a28..dcf10903f6340 100644 ---- a/arch/arm64/configs/defconfig -+++ b/arch/arm64/configs/defconfig -@@ -388,6 +388,7 @@ CONFIG_DRM_RCAR_VSP=y - CONFIG_DRM_TEGRA=m - CONFIG_DRM_PANEL_SIMPLE=m - CONFIG_DRM_I2C_ADV7511=m -+CONFIG_DRM_DW_HDMI_CEC=m - CONFIG_DRM_VC4=m - CONFIG_DRM_HISI_KIRIN=m - CONFIG_DRM_MESON=m diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/103_linux-4.14.y-le-amlogic-gx-1001-dts-meson-gxbb-add_sound-dai-cells_to_hdmi_node.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/103_linux-4.14.y-le-amlogic-gx-1001-dts-meson-gxbb-add_sound-dai-cells_to_hdmi_node.patch deleted file mode 100644 index e2ea19c1a..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/103_linux-4.14.y-le-amlogic-gx-1001-dts-meson-gxbb-add_sound-dai-cells_to_hdmi_node.patch +++ /dev/null @@ -1,10 +0,0 @@ ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi 2018-04-14 00:32:29.116806877 +0200 -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb.dtsi 2018-04-13 18:58:49.474094592 +0200 -@@ -343,6 +343,7 @@ - <&clkc CLKID_CLK81>, - <&clkc CLKID_GCLK_VENCI_INT0>; - clock-names = "isfr", "iahb", "venci"; -+ #sound-dai-cells = <0>; - }; - - &hiubus { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/104_linux-4.14.y-le-amlogic-gx-1002-dts-meson-gxbb-rename_audio_card.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/104_linux-4.14.y-le-amlogic-gx-1002-dts-meson-gxbb-rename_audio_card.patch deleted file mode 100644 index 9480f4c72..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/104_linux-4.14.y-le-amlogic-gx-1002-dts-meson-gxbb-rename_audio_card.patch +++ /dev/null @@ -1,11 +0,0 @@ ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-05-01 01:15:01.378785083 +0200 -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-05-02 00:16:22.834304176 +0200 -@@ -185,7 +185,7 @@ - - sound { - compatible = "simple-audio-card"; -- simple-audio-card,name = "meson-gx-preview"; -+ simple-audio-card,name = "meson-gxbb-audio"; - status = "okay"; - - simple-audio-card,dai-link@0 { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/105_linux-4.17.y-amlogic-drm-0001-drm-meson-use_drm_gem_fb_create.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/105_linux-4.17.y-amlogic-drm-0001-drm-meson-use_drm_gem_fb_create.patch deleted file mode 100644 index b59baebbd..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/105_linux-4.17.y-amlogic-drm-0001-drm-meson-use_drm_gem_fb_create.patch +++ /dev/null @@ -1,40 +0,0 @@ -From 24ef8157fcc092b5bd87cd1eb4dc0f540601d533 Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Noralf=20Tr=C3=B8nnes?= -Date: Sun, 24 Sep 2017 14:26:19 +0200 -Subject: [PATCH] drm/meson: Use drm_gem_fb_create() -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -drm_fb_cma_create() is just a wrapper around drm_gem_fb_create() now, -so use the function directly. - -Cc: Neil Armstrong -Signed-off-by: Noralf Trønnes -Reviewed-by: Eric Anholt -Link: https://patchwork.freedesktop.org/patch/msgid/1506255985-61113-5-git-send-email-noralf@tronnes.org ---- - drivers/gpu/drm/meson/meson_drv.c | 3 ++- - 1 file changed, 2 insertions(+), 1 deletion(-) - -diff --git a/drivers/gpu/drm/meson/meson_drv.c b/drivers/gpu/drm/meson/meson_drv.c -index 7742c7d81ed8f..3b804fdaf7a05 100644 ---- a/drivers/gpu/drm/meson/meson_drv.c -+++ b/drivers/gpu/drm/meson/meson_drv.c -@@ -34,6 +34,7 @@ - #include - #include - #include -+#include - #include - #include - #include -@@ -78,7 +79,7 @@ static const struct drm_mode_config_funcs meson_mode_config_funcs = { - .output_poll_changed = meson_fb_output_poll_changed, - .atomic_check = drm_atomic_helper_check, - .atomic_commit = drm_atomic_helper_commit, -- .fb_create = drm_fb_cma_create, -+ .fb_create = drm_gem_fb_create, - }; - - static irqreturn_t meson_irq(int irq, void *arg) diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/106_linux-4.17.y-amlogic-drm-0004-drm-meson-dw_hdmi-add_support_for_an_optional_external_5v.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/106_linux-4.17.y-amlogic-drm-0004-drm-meson-dw_hdmi-add_support_for_an_optional_external_5v.patch deleted file mode 100644 index 88e5f15c6..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/106_linux-4.17.y-amlogic-drm-0004-drm-meson-dw_hdmi-add_support_for_an_optional_external_5v.patch +++ /dev/null @@ -1,56 +0,0 @@ -From 161a803fe32d2b8c7a54d9819e3f2dc222f42e22 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Wed, 6 Dec 2017 12:54:27 +0100 -Subject: [PATCH] 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 -Tested-by: Jerome Brunet -Reviewed-by: Jerome Brunet -Link: https://patchwork.freedesktop.org/patch/msgid/1512561268-29806-4-git-send-email-narmstrong@baylibre.com ---- - 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 cef414466f9fe..17de3afd98f6a 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)) { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/107_linux-4.17.y-amlogic-drm-0005-drm-meson-add_missing_vpu_init.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/107_linux-4.17.y-amlogic-drm-0005-drm-meson-add_missing_vpu_init.patch deleted file mode 100644 index ef68fc02c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/107_linux-4.17.y-amlogic-drm-0005-drm-meson-add_missing_vpu_init.patch +++ /dev/null @@ -1,59 +0,0 @@ -From 09762525d6eafb394a637e9ef8b602d3cd227939 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Wed, 6 Dec 2017 12:54:28 +0100 -Subject: [PATCH] drm/meson: Add missing VPU init - -The VPU init misses these configurations values. - -Signed-off-by: Neil Armstrong -Acked-by: Chris Wilson -Tested-by: Jerome Brunet -Reviewed-by: Jerome Brunet -Link: https://patchwork.freedesktop.org/patch/msgid/1512561268-29806-5-git-send-email-narmstrong@baylibre.com ---- - 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 3b804fdaf7a05..f9ad0e960263f 100644 ---- a/drivers/gpu/drm/meson/meson_drv.c -+++ b/drivers/gpu/drm/meson/meson_drv.c -@@ -151,6 +151,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); -@@ -222,6 +230,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 284738196af9c..bca87143e5488 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 diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/108_linux-4.17.y-amlogic-drm-0006-drm-meson-use_drm_mode_get_hv_timing_to_populate_plane.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/108_linux-4.17.y-amlogic-drm-0006-drm-meson-use_drm_mode_get_hv_timing_to_populate_plane.patch deleted file mode 100644 index d619a85e4..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/108_linux-4.17.y-amlogic-drm-0006-drm-meson-use_drm_mode_get_hv_timing_to_populate_plane.patch +++ /dev/null @@ -1,44 +0,0 @@ -From 13eff9ae5210b3858e462cc73c3133b41ac261dc Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Ville=20Syrj=C3=A4l=C3=A4?= -Date: Thu, 23 Nov 2017 21:04:55 +0200 -Subject: [PATCH] drm/meson: Use drm_mode_get_hv_timing() to populate plane - clip rectangle -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -Use drm_mode_get_hv_timing() to fill out the plane clip rectangle. - -No functional changes as the code already uses crtc_state->mode -to populate the clip, which is also what drm_mode_get_hv_timing() -uses. - -Once everyone agrees on this we can move the clip handling into -drm_atomic_helper_check_plane_state(). - -Cc: Laurent Pinchart -Cc: Neil Armstrong -Cc: linux-amlogic@lists.infradead.org -Signed-off-by: Ville Syrjälä -Link: https://patchwork.freedesktop.org/patch/msgid/20171123190502.28449-9-ville.syrjala@linux.intel.com -Reviewed-by: Thierry Reding ---- - drivers/gpu/drm/meson/meson_plane.c | 5 +++-- - 1 file changed, 3 insertions(+), 2 deletions(-) - -diff --git a/drivers/gpu/drm/meson/meson_plane.c b/drivers/gpu/drm/meson/meson_plane.c -index d0a6ac8390f39..3801bee1f9e62 100644 ---- a/drivers/gpu/drm/meson/meson_plane.c -+++ b/drivers/gpu/drm/meson/meson_plane.c -@@ -58,8 +58,9 @@ static int meson_plane_atomic_check(struct drm_plane *plane, - if (IS_ERR(crtc_state)) - return PTR_ERR(crtc_state); - -- clip.x2 = crtc_state->mode.hdisplay; -- clip.y2 = crtc_state->mode.vdisplay; -+ if (crtc_state->enable) -+ drm_mode_get_hv_timing(&crtc_state->mode, -+ &clip.x2, &clip.y2); - - return drm_atomic_helper_check_plane_state(state, crtc_state, &clip, - DRM_PLANE_HELPER_NO_SCALING, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/109_linux-4.17.y-amlogic-drm-0014-drm-meson-add_support_for_dmt_modes_on_hdmi.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/109_linux-4.17.y-amlogic-drm-0014-drm-meson-add_support_for_dmt_modes_on_hdmi.patch deleted file mode 100644 index 16b03f3f4..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/109_linux-4.17.y-amlogic-drm-0014-drm-meson-add_support_for_dmt_modes_on_hdmi.patch +++ /dev/null @@ -1,772 +0,0 @@ -From 9c936b12f15019b38edb5f8bae77bb5b0046d1b7 Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Tue, 13 Mar 2018 11:07:50 +0100 -Subject: [PATCH] drm/meson: Add support for DMT modes on HDMI - -This patch adds support for DMT display modes over HDMI. -The modes timings configurations are from the Amlogic Vendor linux tree -and tested over multiples monitors. -Previously only a selected number of CEA modes were supported. - -Only these following modes are supported with these changes: -- 640x480@60Hz -- 800x600@60Hz -- 1024x768@60Hz -- 1152x864@75Hz -- 1280x1024@60Hz -- 1600x1200@60Hz -- 1920x1080@60Hz - -The associated code to handle the clock rates is also added. - -Acked-by: Jerome Brunet -Signed-off-by: Neil Armstrong -Link: https://patchwork.freedesktop.org/patch/msgid/1520935670-14187-1-git-send-email-narmstrong@baylibre.com ---- - drivers/gpu/drm/meson/meson_dw_hdmi.c | 22 +-- - drivers/gpu/drm/meson/meson_vclk.c | 219 ++++++++++++++++++++- - drivers/gpu/drm/meson/meson_venc.c | 347 +++++++++++++++++++++++++++++++++- - drivers/gpu/drm/meson/meson_venc.h | 1 + - 4 files changed, 570 insertions(+), 19 deletions(-) - -diff --git a/drivers/gpu/drm/meson/meson_dw_hdmi.c b/drivers/gpu/drm/meson/meson_dw_hdmi.c -index d49af17310c99..a393095aac1a6 100644 ---- a/drivers/gpu/drm/meson/meson_dw_hdmi.c -+++ b/drivers/gpu/drm/meson/meson_dw_hdmi.c -@@ -538,7 +538,6 @@ static irqreturn_t dw_hdmi_top_thread_irq(int irq, void *dev_id) - return IRQ_HANDLED; - } - --/* TOFIX Enable support for non-vic modes */ - static enum drm_mode_status - dw_hdmi_mode_valid(struct drm_connector *connector, - const struct drm_display_mode *mode) -@@ -555,12 +554,12 @@ dw_hdmi_mode_valid(struct drm_connector *connector, - mode->vdisplay, mode->vsync_start, - mode->vsync_end, mode->vtotal, mode->type, mode->flags); - -- /* For now, only accept VIC modes */ -- if (!vic) -- return MODE_BAD; -- -- /* For now, filter by supported VIC modes */ -- if (!meson_venc_hdmi_supported_vic(vic)) -+ /* Check against non-VIC supported modes */ -+ if (!vic) { -+ if (!meson_venc_hdmi_supported_mode(mode)) -+ return MODE_BAD; -+ /* Check against supported VIC modes */ -+ } else if (!meson_venc_hdmi_supported_vic(vic)) - return MODE_BAD; - - vclk_freq = mode->clock; -@@ -586,9 +585,14 @@ dw_hdmi_mode_valid(struct drm_connector *connector, - - /* Finally filter by configurable vclk frequencies */ - switch (vclk_freq) { -+ case 25175: -+ case 40000: - case 54000: -+ case 65000: - case 74250: -+ case 108000: - case 148500: -+ case 162000: - case 297000: - case 594000: - return MODE_OK; -@@ -653,10 +657,6 @@ static void meson_venc_hdmi_encoder_mode_set(struct drm_encoder *encoder, - DRM_DEBUG_DRIVER("%d:\"%s\" vic %d\n", - mode->base.id, mode->name, vic); - -- /* Should have been filtered */ -- if (!vic) -- return; -- - /* VENC + VENC-DVI Mode setup */ - meson_venc_hdmi_mode_set(priv, vic, mode); - -diff --git a/drivers/gpu/drm/meson/meson_vclk.c b/drivers/gpu/drm/meson/meson_vclk.c -index 47677047e42dd..f0511220317f9 100644 ---- a/drivers/gpu/drm/meson/meson_vclk.c -+++ b/drivers/gpu/drm/meson/meson_vclk.c -@@ -328,14 +328,24 @@ static void meson_venci_cvbs_clock_config(struct meson_drm *priv) - #define MESON_VCLK_HDMI_DDR_54000 2 - /* 2970 /4 /1 /1 /5 /1 => /1 /2 */ - #define MESON_VCLK_HDMI_DDR_148500 3 -+/* 4028 /4 /4 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_25175 4 -+/* 3200 /4 /2 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_40000 5 -+/* 5200 /4 /2 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_65000 6 - /* 2970 /2 /2 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_74250 4 -+#define MESON_VCLK_HDMI_74250 7 -+/* 4320 /4 /1 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_108000 8 - /* 2970 /1 /2 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_148500 5 -+#define MESON_VCLK_HDMI_148500 9 -+/* 3240 /2 /1 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_162000 10 - /* 2970 /1 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_297000 6 -+#define MESON_VCLK_HDMI_297000 11 - /* 5940 /1 /1 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_594000 7 -+#define MESON_VCLK_HDMI_594000 12 - - struct meson_vclk_params { - unsigned int pll_base_freq; -@@ -401,6 +411,46 @@ struct meson_vclk_params { - .vid_pll_div = VID_PLL_DIV_5, - .vclk_div = 1, - }, -+ [MESON_VCLK_HDMI_25175] = { -+ .pll_base_freq = 4028000, -+ .pll_od1 = 4, -+ .pll_od2 = 4, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, -+ [MESON_VCLK_HDMI_40000] = { -+ .pll_base_freq = 3200000, -+ .pll_od1 = 4, -+ .pll_od2 = 2, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, -+ [MESON_VCLK_HDMI_65000] = { -+ .pll_base_freq = 5200000, -+ .pll_od1 = 4, -+ .pll_od2 = 2, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, -+ [MESON_VCLK_HDMI_108000] = { -+ .pll_base_freq = 4320000, -+ .pll_od1 = 4, -+ .pll_od2 = 1, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, -+ [MESON_VCLK_HDMI_162000] = { -+ .pll_base_freq = 3240000, -+ .pll_od1 = 2, -+ .pll_od2 = 1, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, - }; - - static inline unsigned int pll_od_to_reg(unsigned int od) -@@ -451,6 +501,90 @@ void meson_hdmi_pll_set(struct meson_drm *priv, - 0xFFFF, 0x4e00); - break; - -+ case 3200000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000242); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ BIT(28), 0); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4aab); -+ break; -+ -+ case 3240000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000243); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ BIT(28), 0); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4800); -+ break; -+ -+ case 3865000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000250); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ BIT(28), 0); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4855); -+ break; -+ -+ case 4028000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000253); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ BIT(28), 0); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4eab); -+ break; -+ - case 4320000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x5800025a); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -@@ -477,6 +611,23 @@ void meson_hdmi_pll_set(struct meson_drm *priv, - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); - -+ /* unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ BIT(28), 0); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ break; -+ -+ case 5200000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x5800026c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x135c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ - /* unreset */ - regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, - BIT(28), 0); -@@ -498,6 +649,42 @@ void meson_hdmi_pll_set(struct meson_drm *priv, - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); - break; - -+ case 3200000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000285); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb155); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ -+ case 3240000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000287); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ -+ case 3865000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x400002a1); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb02b); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ -+ case 4028000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x400002a7); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb355); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ - case 4320000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x400002b4); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb000); -@@ -516,6 +703,15 @@ void meson_hdmi_pll_set(struct meson_drm *priv, - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); - break; - -+ case 5200000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x400002d8); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb2ab); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ - }; - - /* Reset PLL */ -@@ -590,15 +786,30 @@ void meson_vclk_setup(struct meson_drm *priv, unsigned int target, - else - freq = MESON_VCLK_HDMI_DDR_54000; - break; -+ case 25175: -+ freq = MESON_VCLK_HDMI_25175; -+ break; -+ case 40000: -+ freq = MESON_VCLK_HDMI_40000; -+ break; -+ case 65000: -+ freq = MESON_VCLK_HDMI_65000; -+ break; - case 74250: - freq = MESON_VCLK_HDMI_74250; - break; -+ case 108000: -+ freq = MESON_VCLK_HDMI_108000; -+ break; - case 148500: - if (dac_freq != 148500) - freq = MESON_VCLK_HDMI_DDR_148500; - else - freq = MESON_VCLK_HDMI_148500; - break; -+ case 162000: -+ freq = MESON_VCLK_HDMI_162000; -+ break; - case 297000: - freq = MESON_VCLK_HDMI_297000; - break; -diff --git a/drivers/gpu/drm/meson/meson_venc.c b/drivers/gpu/drm/meson/meson_venc.c -index 9509017dbded1..6e27013898013 100644 ---- a/drivers/gpu/drm/meson/meson_venc.c -+++ b/drivers/gpu/drm/meson/meson_venc.c -@@ -697,6 +697,314 @@ union meson_hdmi_venc_mode meson_hdmi_encp_mode_1080p60 = { - }, - }; - -+union meson_hdmi_venc_mode meson_hdmi_encp_mode_640x480_60 = { -+ .encp = { -+ .dvi_settings = 0x21, -+ .video_mode = 0x4040, -+ .video_mode_adv = 0x18, -+ /* video_prog_mode */ -+ /* video_sync_mode */ -+ /* video_yc_dly */ -+ /* video_rgb_ctrl */ -+ /* video_filt_ctrl */ -+ /* video_ofld_voav_ofst */ -+ /* yfp1_htime */ -+ /* yfp2_htime */ -+ .max_pxcnt = 0x31f, -+ /* hspuls_begin */ -+ /* hspuls_end */ -+ /* hspuls_switch */ -+ /* vspuls_begin */ -+ /* vspuls_end */ -+ /* vspuls_bline */ -+ /* vspuls_eline */ -+ .havon_begin = 0x90, -+ .havon_end = 0x30f, -+ .vavon_bline = 0x23, -+ .vavon_eline = 0x202, -+ /* eqpuls_begin */ -+ /* eqpuls_end */ -+ /* eqpuls_bline */ -+ /* eqpuls_eline */ -+ .hso_begin = 0, -+ .hso_end = 0x60, -+ .vso_begin = 0x1e, -+ .vso_end = 0x32, -+ .vso_bline = 0, -+ .vso_eline = 2, -+ .vso_eline_present = true, -+ /* sy_val */ -+ /* sy2_val */ -+ .max_lncnt = 0x20c, -+ }, -+}; -+ -+union meson_hdmi_venc_mode meson_hdmi_encp_mode_800x600_60 = { -+ .encp = { -+ .dvi_settings = 0x21, -+ .video_mode = 0x4040, -+ .video_mode_adv = 0x18, -+ /* video_prog_mode */ -+ /* video_sync_mode */ -+ /* video_yc_dly */ -+ /* video_rgb_ctrl */ -+ /* video_filt_ctrl */ -+ /* video_ofld_voav_ofst */ -+ /* yfp1_htime */ -+ /* yfp2_htime */ -+ .max_pxcnt = 0x41f, -+ /* hspuls_begin */ -+ /* hspuls_end */ -+ /* hspuls_switch */ -+ /* vspuls_begin */ -+ /* vspuls_end */ -+ /* vspuls_bline */ -+ /* vspuls_eline */ -+ .havon_begin = 0xD8, -+ .havon_end = 0x3f7, -+ .vavon_bline = 0x1b, -+ .vavon_eline = 0x272, -+ /* eqpuls_begin */ -+ /* eqpuls_end */ -+ /* eqpuls_bline */ -+ /* eqpuls_eline */ -+ .hso_begin = 0, -+ .hso_end = 0x80, -+ .vso_begin = 0x1e, -+ .vso_end = 0x32, -+ .vso_bline = 0, -+ .vso_eline = 4, -+ .vso_eline_present = true, -+ /* sy_val */ -+ /* sy2_val */ -+ .max_lncnt = 0x273, -+ }, -+}; -+ -+union meson_hdmi_venc_mode meson_hdmi_encp_mode_1024x768_60 = { -+ .encp = { -+ .dvi_settings = 0x21, -+ .video_mode = 0x4040, -+ .video_mode_adv = 0x18, -+ /* video_prog_mode */ -+ /* video_sync_mode */ -+ /* video_yc_dly */ -+ /* video_rgb_ctrl */ -+ /* video_filt_ctrl */ -+ /* video_ofld_voav_ofst */ -+ /* yfp1_htime */ -+ /* yfp2_htime */ -+ .max_pxcnt = 1343, -+ /* hspuls_begin */ -+ /* hspuls_end */ -+ /* hspuls_switch */ -+ /* vspuls_begin */ -+ /* vspuls_end */ -+ /* vspuls_bline */ -+ /* vspuls_eline */ -+ .havon_begin = 296, -+ .havon_end = 1319, -+ .vavon_bline = 35, -+ .vavon_eline = 802, -+ /* eqpuls_begin */ -+ /* eqpuls_end */ -+ /* eqpuls_bline */ -+ /* eqpuls_eline */ -+ .hso_begin = 0, -+ .hso_end = 136, -+ .vso_begin = 30, -+ .vso_end = 50, -+ .vso_bline = 0, -+ .vso_eline = 6, -+ .vso_eline_present = true, -+ /* sy_val */ -+ /* sy2_val */ -+ .max_lncnt = 805, -+ }, -+}; -+ -+union meson_hdmi_venc_mode meson_hdmi_encp_mode_1152x864_75 = { -+ .encp = { -+ .dvi_settings = 0x21, -+ .video_mode = 0x4040, -+ .video_mode_adv = 0x18, -+ /* video_prog_mode */ -+ /* video_sync_mode */ -+ /* video_yc_dly */ -+ /* video_rgb_ctrl */ -+ /* video_filt_ctrl */ -+ /* video_ofld_voav_ofst */ -+ /* yfp1_htime */ -+ /* yfp2_htime */ -+ .max_pxcnt = 0x63f, -+ /* hspuls_begin */ -+ /* hspuls_end */ -+ /* hspuls_switch */ -+ /* vspuls_begin */ -+ /* vspuls_end */ -+ /* vspuls_bline */ -+ /* vspuls_eline */ -+ .havon_begin = 0x180, -+ .havon_end = 0x5ff, -+ .vavon_bline = 0x23, -+ .vavon_eline = 0x382, -+ /* eqpuls_begin */ -+ /* eqpuls_end */ -+ /* eqpuls_bline */ -+ /* eqpuls_eline */ -+ .hso_begin = 0, -+ .hso_end = 0x80, -+ .vso_begin = 0x1e, -+ .vso_end = 0x32, -+ .vso_bline = 0, -+ .vso_eline = 3, -+ .vso_eline_present = true, -+ /* sy_val */ -+ /* sy2_val */ -+ .max_lncnt = 0x383, -+ }, -+}; -+ -+union meson_hdmi_venc_mode meson_hdmi_encp_mode_1280x1024_60 = { -+ .encp = { -+ .dvi_settings = 0x21, -+ .video_mode = 0x4040, -+ .video_mode_adv = 0x18, -+ /* video_prog_mode */ -+ /* video_sync_mode */ -+ /* video_yc_dly */ -+ /* video_rgb_ctrl */ -+ /* video_filt_ctrl */ -+ /* video_ofld_voav_ofst */ -+ /* yfp1_htime */ -+ /* yfp2_htime */ -+ .max_pxcnt = 0x697, -+ /* hspuls_begin */ -+ /* hspuls_end */ -+ /* hspuls_switch */ -+ /* vspuls_begin */ -+ /* vspuls_end */ -+ /* vspuls_bline */ -+ /* vspuls_eline */ -+ .havon_begin = 0x168, -+ .havon_end = 0x667, -+ .vavon_bline = 0x29, -+ .vavon_eline = 0x428, -+ /* eqpuls_begin */ -+ /* eqpuls_end */ -+ /* eqpuls_bline */ -+ /* eqpuls_eline */ -+ .hso_begin = 0, -+ .hso_end = 0x70, -+ .vso_begin = 0x1e, -+ .vso_end = 0x32, -+ .vso_bline = 0, -+ .vso_eline = 3, -+ .vso_eline_present = true, -+ /* sy_val */ -+ /* sy2_val */ -+ .max_lncnt = 0x429, -+ }, -+}; -+ -+union meson_hdmi_venc_mode meson_hdmi_encp_mode_1600x1200_60 = { -+ .encp = { -+ .dvi_settings = 0x21, -+ .video_mode = 0x4040, -+ .video_mode_adv = 0x18, -+ /* video_prog_mode */ -+ /* video_sync_mode */ -+ /* video_yc_dly */ -+ /* video_rgb_ctrl */ -+ /* video_filt_ctrl */ -+ /* video_ofld_voav_ofst */ -+ /* yfp1_htime */ -+ /* yfp2_htime */ -+ .max_pxcnt = 0x86f, -+ /* hspuls_begin */ -+ /* hspuls_end */ -+ /* hspuls_switch */ -+ /* vspuls_begin */ -+ /* vspuls_end */ -+ /* vspuls_bline */ -+ /* vspuls_eline */ -+ .havon_begin = 0x1f0, -+ .havon_end = 0x82f, -+ .vavon_bline = 0x31, -+ .vavon_eline = 0x4e0, -+ /* eqpuls_begin */ -+ /* eqpuls_end */ -+ /* eqpuls_bline */ -+ /* eqpuls_eline */ -+ .hso_begin = 0, -+ .hso_end = 0xc0, -+ .vso_begin = 0x1e, -+ .vso_end = 0x32, -+ .vso_bline = 0, -+ .vso_eline = 3, -+ .vso_eline_present = true, -+ /* sy_val */ -+ /* sy2_val */ -+ .max_lncnt = 0x4e1, -+ }, -+}; -+ -+struct meson_hdmi_venc_dmt_mode { -+ struct drm_display_mode drm_mode; -+ union meson_hdmi_venc_mode *mode; -+} meson_hdmi_venc_dmt_modes[] = { -+ /* 640x480@60Hz */ -+ { -+ { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 25175, 640, 656, -+ 752, 800, 0, 480, 490, 492, 525, 0, -+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, -+ &meson_hdmi_encp_mode_640x480_60, -+ }, -+ /* 800x600@60Hz */ -+ { -+ { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 40000, 800, 840, -+ 968, 1056, 0, 600, 601, 605, 628, 0, -+ DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -+ &meson_hdmi_encp_mode_800x600_60, -+ }, -+ /* 1024x768@60Hz */ -+ { -+ { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 65000, 1024, -+ 1048, 1184, 1344, 0, 768, 771, 777, 806, 0, -+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, -+ &meson_hdmi_encp_mode_1024x768_60, -+ }, -+ /* 1152x864@75Hz */ -+ { -+ { DRM_MODE("1152x864", DRM_MODE_TYPE_DRIVER, 108000, 1152, -+ 1216, 1344, 1600, 0, 864, 865, 868, 900, 0, -+ DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -+ &meson_hdmi_encp_mode_1152x864_75, -+ }, -+ /* 1280x1024@60Hz */ -+ { -+ { DRM_MODE("1280x1024", DRM_MODE_TYPE_DRIVER, 108000, 1280, -+ 1328, 1440, 1688, 0, 1024, 1025, 1028, 1066, 0, -+ DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -+ &meson_hdmi_encp_mode_1280x1024_60, -+ }, -+ /* 1600x1200@60Hz */ -+ { -+ { DRM_MODE("1600x1200", DRM_MODE_TYPE_DRIVER, 162000, 1600, -+ 1664, 1856, 2160, 0, 1200, 1201, 1204, 1250, 0, -+ DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -+ &meson_hdmi_encp_mode_1600x1200_60, -+ }, -+ /* 1920x1080@60Hz */ -+ { -+ { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 148500, 1920, -+ 2008, 2052, 2200, 0, 1080, 1084, 1089, 1125, 0, -+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, -+ &meson_hdmi_encp_mode_1080p60 -+ }, -+ { }, /* sentinel */ -+}; -+ - struct meson_hdmi_venc_vic_mode { - unsigned int vic; - union meson_hdmi_venc_mode *mode; -@@ -736,6 +1044,20 @@ static unsigned long modulo(unsigned long a, unsigned long b) - return a; - } - -+bool meson_venc_hdmi_supported_mode(const struct drm_display_mode *mode) -+{ -+ struct meson_hdmi_venc_dmt_mode *vmode = meson_hdmi_venc_dmt_modes; -+ -+ while (vmode->mode) { -+ if (drm_mode_equal(&vmode->drm_mode, mode)) -+ return true; -+ vmode++; -+ } -+ -+ return false; -+} -+EXPORT_SYMBOL_GPL(meson_venc_hdmi_supported_mode); -+ - bool meson_venc_hdmi_supported_vic(int vic) - { - struct meson_hdmi_venc_vic_mode *vmode = meson_hdmi_venc_vic_modes; -@@ -750,6 +1072,20 @@ bool meson_venc_hdmi_supported_vic(int vic) - } - EXPORT_SYMBOL_GPL(meson_venc_hdmi_supported_vic); - -+static union meson_hdmi_venc_mode -+*meson_venc_hdmi_get_dmt_vmode(const struct drm_display_mode *mode) -+{ -+ struct meson_hdmi_venc_dmt_mode *vmode = meson_hdmi_venc_dmt_modes; -+ -+ while (vmode->mode) { -+ if (drm_mode_equal(&vmode->drm_mode, mode)) -+ return vmode->mode; -+ vmode++; -+ } -+ -+ return NULL; -+} -+ - static union meson_hdmi_venc_mode *meson_venc_hdmi_get_vic_vmode(int vic) - { - struct meson_hdmi_venc_vic_mode *vmode = meson_hdmi_venc_vic_modes; -@@ -811,10 +1147,13 @@ void meson_venc_hdmi_mode_set(struct meson_drm *priv, int vic, - unsigned int sof_lines; - unsigned int vsync_lines; - -- vmode = meson_venc_hdmi_get_vic_vmode(vic); -+ if (meson_venc_hdmi_supported_vic(vic)) -+ vmode = meson_venc_hdmi_get_vic_vmode(vic); -+ else -+ vmode = meson_venc_hdmi_get_dmt_vmode(mode); - if (!vmode) { -- dev_err(priv->dev, "%s: Fatal Error, unsupported vic %d\n", -- __func__, vic); -+ dev_err(priv->dev, "%s: Fatal Error, unsupported mode " -+ DRM_MODE_FMT "\n", __func__, DRM_MODE_ARG(mode)); - return; - } - -@@ -864,7 +1203,7 @@ void meson_venc_hdmi_mode_set(struct meson_drm *priv, int vic, - hsync_pixels_venc *= 2; - - /* Disable VDACs */ -- writel_bits_relaxed(0x1f, 0x1f, -+ writel_bits_relaxed(0xff, 0xff, - priv->io_base + _REG(VENC_VDAC_SETTING)); - - writel_relaxed(0, priv->io_base + _REG(ENCI_VIDEO_EN)); -diff --git a/drivers/gpu/drm/meson/meson_venc.h b/drivers/gpu/drm/meson/meson_venc.h -index a1b96e898c14e..7c18a36a0dd0c 100644 ---- a/drivers/gpu/drm/meson/meson_venc.h -+++ b/drivers/gpu/drm/meson/meson_venc.h -@@ -58,6 +58,7 @@ struct meson_cvbs_enci_mode { - }; - - /* HDMI Clock parameters */ -+bool meson_venc_hdmi_supported_mode(const struct drm_display_mode *mode); - bool meson_venc_hdmi_supported_vic(int vic); - bool meson_venc_hdmi_venc_repeat(int vic); - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/110_linux-4.17.y-amlogic-drm-0015-drm-meson-fix_potential_null_dereference_in.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/110_linux-4.17.y-amlogic-drm-0015-drm-meson-fix_potential_null_dereference_in.patch deleted file mode 100644 index cdff10fe5..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/110_linux-4.17.y-amlogic-drm-0015-drm-meson-fix_potential_null_dereference_in.patch +++ /dev/null @@ -1,52 +0,0 @@ -From acaa3f13b8dd77da3c6c0fe18cb1159eef7ea286 Mon Sep 17 00:00:00 2001 -From: Wei Yongjun -Date: Tue, 20 Mar 2018 14:20:30 +0000 -Subject: [PATCH] drm/meson: Fix potential NULL dereference in - meson_drv_bind_master() - -platform_get_resource_byname() may fail and return NULL, so we should -better check it's return value to avoid a NULL pointer dereference -a bit later in the code. - -This is detected by Coccinelle semantic patch. - -@@ -expression pdev, res, n, t, e, e1, e2; -@@ - -res = platform_get_resource_byname(pdev, t, n); -+ if (!res) -+ return -EINVAL; -... when != res == NULL -e = devm_ioremap(e1, res->start, e2); - -Signed-off-by: Wei Yongjun -Signed-off-by: Neil Armstrong -Acked-by: Neil Armstrong -Link: https://patchwork.freedesktop.org/patch/msgid/1521555630-29284-1-git-send-email-weiyongjun1@huawei.com ---- - drivers/gpu/drm/meson/meson_drv.c | 4 ++++ - 1 file changed, 4 insertions(+) - -diff --git a/drivers/gpu/drm/meson/meson_drv.c b/drivers/gpu/drm/meson/meson_drv.c -index 3baceb744beb8..32b1a6cdecfc0 100644 ---- a/drivers/gpu/drm/meson/meson_drv.c -+++ b/drivers/gpu/drm/meson/meson_drv.c -@@ -197,6 +197,8 @@ static int meson_drv_bind_master(struct device *dev, bool has_components) - priv->io_base = regs; - - res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "hhi"); -+ if (!res) -+ return -EINVAL; - /* Simply ioremap since it may be a shared register zone */ - regs = devm_ioremap(dev, res->start, resource_size(res)); - if (!regs) { -@@ -213,6 +215,8 @@ static int meson_drv_bind_master(struct device *dev, bool has_components) - } - - res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "dmc"); -+ if (!res) -+ return -EINVAL; - /* Simply ioremap since it may be a shared register zone */ - regs = devm_ioremap(dev, res->start, resource_size(res)); - if (!regs) { diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/111_linux-4.17-amlogic-dmt-extended-0001-make_dmt_timings_parameter_generic_and_add_more_frequencies.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/111_linux-4.17-amlogic-dmt-extended-0001-make_dmt_timings_parameter_generic_and_add_more_frequencies.patch deleted file mode 100644 index c0859bcf3..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/111_linux-4.17-amlogic-dmt-extended-0001-make_dmt_timings_parameter_generic_and_add_more_frequencies.patch +++ /dev/null @@ -1,714 +0,0 @@ -From 2d49cff77c34c63ae5aa32537cc5fef1ea2e165d Mon Sep 17 00:00:00 2001 -From: Neil Armstrong -Date: Fri, 27 Apr 2018 17:19:46 +0200 -Subject: [PATCH] drm/meson: Make DMT timings parameter generic and add more - frequencies - -Add more frequencies to support more timings with the generic timings -parameters calculation. - -Signed-off-by: Neil Armstrong ---- - drivers/gpu/drm/meson/meson_dw_hdmi.c | 10 +- - drivers/gpu/drm/meson/meson_vclk.c | 184 ++++++++++++++++++- - drivers/gpu/drm/meson/meson_venc.c | 330 +++++----------------------------- - drivers/gpu/drm/meson/meson_venc.h | 3 +- - 4 files changed, 231 insertions(+), 296 deletions(-) - -diff --git a/drivers/gpu/drm/meson/meson_dw_hdmi.c b/drivers/gpu/drm/meson/meson_dw_hdmi.c -index a393095aac1a6..7ebfef86383fe 100644 ---- a/drivers/gpu/drm/meson/meson_dw_hdmi.c -+++ b/drivers/gpu/drm/meson/meson_dw_hdmi.c -@@ -546,6 +546,7 @@ dw_hdmi_mode_valid(struct drm_connector *connector, - unsigned int venc_freq; - unsigned int hdmi_freq; - int vic = drm_match_cea_mode(mode); -+ enum drm_mode_status status; - - DRM_DEBUG_DRIVER("Modeline %d:\"%s\" %d %d %d %d %d %d %d %d %d %d 0x%x 0x%x\n", - mode->base.id, mode->name, mode->vrefresh, mode->clock, -@@ -556,8 +557,9 @@ dw_hdmi_mode_valid(struct drm_connector *connector, - - /* Check against non-VIC supported modes */ - if (!vic) { -- if (!meson_venc_hdmi_supported_mode(mode)) -- return MODE_BAD; -+ status = meson_venc_hdmi_supported_mode(mode); -+ if (status != MODE_OK) -+ return status; - /* Check against supported VIC modes */ - } else if (!meson_venc_hdmi_supported_vic(vic)) - return MODE_BAD; -@@ -587,6 +589,10 @@ dw_hdmi_mode_valid(struct drm_connector *connector, - switch (vclk_freq) { - case 25175: - case 40000: -+ case 32000: -+ case 36000: -+ case 33750: -+ case 33900: - case 54000: - case 65000: - case 74250: -diff --git a/drivers/gpu/drm/meson/meson_vclk.c b/drivers/gpu/drm/meson/meson_vclk.c -index f0511220317f9..86975f245c361 100644 ---- a/drivers/gpu/drm/meson/meson_vclk.c -+++ b/drivers/gpu/drm/meson/meson_vclk.c -@@ -330,22 +330,30 @@ static void meson_venci_cvbs_clock_config(struct meson_drm *priv) - #define MESON_VCLK_HDMI_DDR_148500 3 - /* 4028 /4 /4 /1 /5 /2 => /1 /1 */ - #define MESON_VCLK_HDMI_25175 4 -+/* 2560 /4 /2 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_32000 5 -+/* 2700 /4 /2 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_33750 6 -+/* 2712 /4 /2 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_33900 7 -+/* 2880 /4 /2 /1 /5 /2 => /1 /1 */ -+#define MESON_VCLK_HDMI_36000 8 - /* 3200 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_40000 5 -+#define MESON_VCLK_HDMI_40000 9 - /* 5200 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_65000 6 -+#define MESON_VCLK_HDMI_65000 10 - /* 2970 /2 /2 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_74250 7 -+#define MESON_VCLK_HDMI_74250 11 - /* 4320 /4 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_108000 8 -+#define MESON_VCLK_HDMI_108000 12 - /* 2970 /1 /2 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_148500 9 -+#define MESON_VCLK_HDMI_148500 13 - /* 3240 /2 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_162000 10 -+#define MESON_VCLK_HDMI_162000 14 - /* 2970 /1 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_297000 11 -+#define MESON_VCLK_HDMI_297000 15 - /* 5940 /1 /1 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_594000 12 -+#define MESON_VCLK_HDMI_594000 16 - - struct meson_vclk_params { - unsigned int pll_base_freq; -@@ -419,6 +427,38 @@ struct meson_vclk_params { - .vid_pll_div = VID_PLL_DIV_5, - .vclk_div = 2, - }, -+ [MESON_VCLK_HDMI_32000] = { -+ .pll_base_freq = 2560000, -+ .pll_od1 = 4, -+ .pll_od2 = 2, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, -+ [MESON_VCLK_HDMI_33750] = { -+ .pll_base_freq = 2700000, -+ .pll_od1 = 4, -+ .pll_od2 = 2, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, -+ [MESON_VCLK_HDMI_33900] = { -+ .pll_base_freq = 2712000, -+ .pll_od1 = 4, -+ .pll_od2 = 2, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, -+ [MESON_VCLK_HDMI_36000] = { -+ .pll_base_freq = 2880000, -+ .pll_od1 = 4, -+ .pll_od2 = 2, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, - [MESON_VCLK_HDMI_40000] = { - .pll_base_freq = 3200000, - .pll_od1 = 4, -@@ -480,6 +520,86 @@ void meson_hdmi_pll_set(struct meson_drm *priv, - - if (meson_vpu_is_compatible(priv, "amlogic,meson-gxbb-vpu")) { - switch (base) { -+ case 2560000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000235); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* Enable and unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ 0x7 << 28, 0x4 << 28); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4555); -+ break; -+ -+ case 2700000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000238); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* Enable and unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ 0x7 << 28, 0x4 << 28); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4400); -+ break; -+ -+ case 2712000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000238); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* Enable and unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ 0x7 << 28, 0x4 << 28); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4800); -+ break; -+ -+ case 2880000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x5800023c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* Enable and unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ 0x7 << 28, 0x4 << 28); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ break; -+ - case 2970000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x5800023d); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -@@ -640,6 +760,42 @@ void meson_hdmi_pll_set(struct meson_drm *priv, - } else if (meson_vpu_is_compatible(priv, "amlogic,meson-gxm-vpu") || - meson_vpu_is_compatible(priv, "amlogic,meson-gxl-vpu")) { - switch (base) { -+ case 2560000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x4000026a); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb2ab); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ -+ case 2700000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000270); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb200); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ -+ case 2712000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000271); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ -+ case 2880000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000278); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ - case 2970000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x4000027b); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb300); -@@ -789,6 +945,18 @@ void meson_vclk_setup(struct meson_drm *priv, unsigned int target, - case 25175: - freq = MESON_VCLK_HDMI_25175; - break; -+ case 32000: -+ freq = MESON_VCLK_HDMI_32000; -+ break; -+ case 33750: -+ freq = MESON_VCLK_HDMI_33750; -+ break; -+ case 33900: -+ freq = MESON_VCLK_HDMI_33900; -+ break; -+ case 36000: -+ freq = MESON_VCLK_HDMI_36000; -+ break; - case 40000: - freq = MESON_VCLK_HDMI_40000; - break; -diff --git a/drivers/gpu/drm/meson/meson_venc.c b/drivers/gpu/drm/meson/meson_venc.c -index 6e27013898013..ea178151399c5 100644 ---- a/drivers/gpu/drm/meson/meson_venc.c -+++ b/drivers/gpu/drm/meson/meson_venc.c -@@ -697,258 +697,6 @@ union meson_hdmi_venc_mode meson_hdmi_encp_mode_1080p60 = { - }, - }; - --union meson_hdmi_venc_mode meson_hdmi_encp_mode_640x480_60 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 0x31f, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 0x90, -- .havon_end = 0x30f, -- .vavon_bline = 0x23, -- .vavon_eline = 0x202, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 0x60, -- .vso_begin = 0x1e, -- .vso_end = 0x32, -- .vso_bline = 0, -- .vso_eline = 2, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 0x20c, -- }, --}; -- --union meson_hdmi_venc_mode meson_hdmi_encp_mode_800x600_60 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 0x41f, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 0xD8, -- .havon_end = 0x3f7, -- .vavon_bline = 0x1b, -- .vavon_eline = 0x272, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 0x80, -- .vso_begin = 0x1e, -- .vso_end = 0x32, -- .vso_bline = 0, -- .vso_eline = 4, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 0x273, -- }, --}; -- --union meson_hdmi_venc_mode meson_hdmi_encp_mode_1024x768_60 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 1343, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 296, -- .havon_end = 1319, -- .vavon_bline = 35, -- .vavon_eline = 802, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 136, -- .vso_begin = 30, -- .vso_end = 50, -- .vso_bline = 0, -- .vso_eline = 6, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 805, -- }, --}; -- --union meson_hdmi_venc_mode meson_hdmi_encp_mode_1152x864_75 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 0x63f, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 0x180, -- .havon_end = 0x5ff, -- .vavon_bline = 0x23, -- .vavon_eline = 0x382, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 0x80, -- .vso_begin = 0x1e, -- .vso_end = 0x32, -- .vso_bline = 0, -- .vso_eline = 3, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 0x383, -- }, --}; -- --union meson_hdmi_venc_mode meson_hdmi_encp_mode_1280x1024_60 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 0x697, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 0x168, -- .havon_end = 0x667, -- .vavon_bline = 0x29, -- .vavon_eline = 0x428, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 0x70, -- .vso_begin = 0x1e, -- .vso_end = 0x32, -- .vso_bline = 0, -- .vso_eline = 3, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 0x429, -- }, --}; -- --union meson_hdmi_venc_mode meson_hdmi_encp_mode_1600x1200_60 = { -- .encp = { -- .dvi_settings = 0x21, -- .video_mode = 0x4040, -- .video_mode_adv = 0x18, -- /* video_prog_mode */ -- /* video_sync_mode */ -- /* video_yc_dly */ -- /* video_rgb_ctrl */ -- /* video_filt_ctrl */ -- /* video_ofld_voav_ofst */ -- /* yfp1_htime */ -- /* yfp2_htime */ -- .max_pxcnt = 0x86f, -- /* hspuls_begin */ -- /* hspuls_end */ -- /* hspuls_switch */ -- /* vspuls_begin */ -- /* vspuls_end */ -- /* vspuls_bline */ -- /* vspuls_eline */ -- .havon_begin = 0x1f0, -- .havon_end = 0x82f, -- .vavon_bline = 0x31, -- .vavon_eline = 0x4e0, -- /* eqpuls_begin */ -- /* eqpuls_end */ -- /* eqpuls_bline */ -- /* eqpuls_eline */ -- .hso_begin = 0, -- .hso_end = 0xc0, -- .vso_begin = 0x1e, -- .vso_end = 0x32, -- .vso_bline = 0, -- .vso_eline = 3, -- .vso_eline_present = true, -- /* sy_val */ -- /* sy2_val */ -- .max_lncnt = 0x4e1, -- }, --}; -- - struct meson_hdmi_venc_dmt_mode { - struct drm_display_mode drm_mode; - union meson_hdmi_venc_mode *mode; -@@ -958,49 +706,42 @@ struct meson_hdmi_venc_dmt_mode { - { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 25175, 640, 656, - 752, 800, 0, 480, 490, 492, 525, 0, - DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, -- &meson_hdmi_encp_mode_640x480_60, - }, - /* 800x600@60Hz */ - { - { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 40000, 800, 840, - 968, 1056, 0, 600, 601, 605, 628, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -- &meson_hdmi_encp_mode_800x600_60, - }, - /* 1024x768@60Hz */ - { - { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 65000, 1024, - 1048, 1184, 1344, 0, 768, 771, 777, 806, 0, - DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, -- &meson_hdmi_encp_mode_1024x768_60, - }, - /* 1152x864@75Hz */ - { - { DRM_MODE("1152x864", DRM_MODE_TYPE_DRIVER, 108000, 1152, - 1216, 1344, 1600, 0, 864, 865, 868, 900, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -- &meson_hdmi_encp_mode_1152x864_75, - }, - /* 1280x1024@60Hz */ - { - { DRM_MODE("1280x1024", DRM_MODE_TYPE_DRIVER, 108000, 1280, - 1328, 1440, 1688, 0, 1024, 1025, 1028, 1066, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -- &meson_hdmi_encp_mode_1280x1024_60, - }, - /* 1600x1200@60Hz */ - { - { DRM_MODE("1600x1200", DRM_MODE_TYPE_DRIVER, 162000, 1600, - 1664, 1856, 2160, 0, 1200, 1201, 1204, 1250, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -- &meson_hdmi_encp_mode_1600x1200_60, - }, - /* 1920x1080@60Hz */ - { - { DRM_MODE("1920x1080", DRM_MODE_TYPE_DRIVER, 148500, 1920, - 2008, 2052, 2200, 0, 1080, 1084, 1089, 1125, 0, - DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, -- &meson_hdmi_encp_mode_1080p60 - }, - { }, /* sentinel */ - }; -@@ -1044,17 +785,20 @@ static unsigned long modulo(unsigned long a, unsigned long b) - return a; - } - --bool meson_venc_hdmi_supported_mode(const struct drm_display_mode *mode) -+enum drm_mode_status -+meson_venc_hdmi_supported_mode(const struct drm_display_mode *mode) - { -- struct meson_hdmi_venc_dmt_mode *vmode = meson_hdmi_venc_dmt_modes; -+ if (mode->flags & ~(DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_NHSYNC | -+ DRM_MODE_FLAG_PVSYNC | DRM_MODE_FLAG_NVSYNC)) -+ return MODE_BAD; - -- while (vmode->mode) { -- if (drm_mode_equal(&vmode->drm_mode, mode)) -- return true; -- vmode++; -- } -+ if (mode->hdisplay < 640 || mode->hdisplay > 1920) -+ return MODE_BAD_HVALUE; - -- return false; -+ if (mode->vdisplay < 480 || mode->vdisplay > 1200) -+ return MODE_BAD_VVALUE; -+ -+ return MODE_OK; - } - EXPORT_SYMBOL_GPL(meson_venc_hdmi_supported_mode); - -@@ -1072,18 +816,29 @@ bool meson_venc_hdmi_supported_vic(int vic) - } - EXPORT_SYMBOL_GPL(meson_venc_hdmi_supported_vic); - --static union meson_hdmi_venc_mode --*meson_venc_hdmi_get_dmt_vmode(const struct drm_display_mode *mode) -+void meson_venc_hdmi_get_dmt_vmode(const struct drm_display_mode *mode, -+ union meson_hdmi_venc_mode *dmt_mode) - { -- struct meson_hdmi_venc_dmt_mode *vmode = meson_hdmi_venc_dmt_modes; -- -- while (vmode->mode) { -- if (drm_mode_equal(&vmode->drm_mode, mode)) -- return vmode->mode; -- vmode++; -- } -- -- return NULL; -+ memset(dmt_mode, 0, sizeof(*dmt_mode)); -+ -+ dmt_mode->encp.dvi_settings = 0x21; -+ dmt_mode->encp.video_mode = 0x4040; -+ dmt_mode->encp.video_mode_adv = 0x18; -+ dmt_mode->encp.max_pxcnt = mode->htotal - 1; -+ dmt_mode->encp.havon_begin = mode->htotal - mode->hsync_start; -+ dmt_mode->encp.havon_end = dmt_mode->encp.havon_begin + -+ mode->hdisplay - 1; -+ dmt_mode->encp.vavon_bline = mode->vtotal - mode->vsync_start; -+ dmt_mode->encp.vavon_eline = dmt_mode->encp.vavon_bline + -+ mode->vdisplay - 1; -+ dmt_mode->encp.hso_begin = 0; -+ dmt_mode->encp.hso_end = mode->hsync_end - mode->hsync_start; -+ dmt_mode->encp.vso_begin = 30; -+ dmt_mode->encp.vso_end = 50; -+ dmt_mode->encp.vso_bline = 0; -+ dmt_mode->encp.vso_eline = mode->vsync_end - mode->vsync_start; -+ dmt_mode->encp.vso_eline_present = true; -+ dmt_mode->encp.max_lncnt = mode->vtotal - 1; - } - - static union meson_hdmi_venc_mode *meson_venc_hdmi_get_vic_vmode(int vic) -@@ -1120,6 +875,7 @@ void meson_venc_hdmi_mode_set(struct meson_drm *priv, int vic, - struct drm_display_mode *mode) - { - union meson_hdmi_venc_mode *vmode = NULL; -+ union meson_hdmi_venc_mode vmode_dmt; - bool use_enci = false; - bool venc_repeat = false; - bool hdmi_repeat = false; -@@ -1147,14 +903,18 @@ void meson_venc_hdmi_mode_set(struct meson_drm *priv, int vic, - unsigned int sof_lines; - unsigned int vsync_lines; - -- if (meson_venc_hdmi_supported_vic(vic)) -+ if (meson_venc_hdmi_supported_vic(vic)) { - vmode = meson_venc_hdmi_get_vic_vmode(vic); -- else -- vmode = meson_venc_hdmi_get_dmt_vmode(mode); -- if (!vmode) { -- dev_err(priv->dev, "%s: Fatal Error, unsupported mode " -- DRM_MODE_FMT "\n", __func__, DRM_MODE_ARG(mode)); -- return; -+ if (!vmode) { -+ dev_err(priv->dev, "%s: Fatal Error, unsupported mode " -+ DRM_MODE_FMT "\n", __func__, -+ DRM_MODE_ARG(mode)); -+ return; -+ } -+ } -+ else { -+ meson_venc_hdmi_get_dmt_vmode(mode, &vmode_dmt); -+ vmode = &vmode_dmt; - } - - /* Use VENCI for 480i and 576i and double HDMI pixels */ -diff --git a/drivers/gpu/drm/meson/meson_venc.h b/drivers/gpu/drm/meson/meson_venc.h -index 7c18a36a0dd0c..97eaebbfa0c4a 100644 ---- a/drivers/gpu/drm/meson/meson_venc.h -+++ b/drivers/gpu/drm/meson/meson_venc.h -@@ -58,7 +58,8 @@ struct meson_cvbs_enci_mode { - }; - - /* HDMI Clock parameters */ --bool meson_venc_hdmi_supported_mode(const struct drm_display_mode *mode); -+enum drm_mode_status -+meson_venc_hdmi_supported_mode(const struct drm_display_mode *mode); - bool meson_venc_hdmi_supported_vic(int vic); - bool meson_venc_hdmi_venc_repeat(int vic); - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/112_linux-4.17-amlogic-dmt-extended-1001-fix-32000khz.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/112_linux-4.17-amlogic-dmt-extended-1001-fix-32000khz.patch deleted file mode 100644 index a359376a7..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/112_linux-4.17-amlogic-dmt-extended-1001-fix-32000khz.patch +++ /dev/null @@ -1,119 +0,0 @@ -diff -ur a/drivers/gpu/drm/meson/meson_vclk.c b/drivers/gpu/drm/meson/meson_vclk.c ---- a/drivers/gpu/drm/meson/meson_vclk.c 2018-06-02 20:21:48.000000000 +0200 -+++ b/drivers/gpu/drm/meson/meson_vclk.c 2018-06-02 20:16:44.008061996 +0200 -@@ -428,9 +428,9 @@ - .vclk_div = 2, - }, - [MESON_VCLK_HDMI_32000] = { -- .pll_base_freq = 2560000, -+ .pll_base_freq = 5120000, - .pll_od1 = 4, -- .pll_od2 = 2, -+ .pll_od2 = 4, - .pll_od3 = 1, - .vid_pll_div = VID_PLL_DIV_5, - .vclk_div = 2, -@@ -520,27 +520,6 @@ - - if (meson_vpu_is_compatible(priv, "amlogic,meson-gxbb-vpu")) { - switch (base) { -- case 2560000: -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000235); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x0d5c5091); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -- -- /* Enable and unreset */ -- regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -- 0x7 << 28, 0x4 << 28); -- -- /* Poll for lock bit */ -- regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -- val, (val & HDMI_PLL_LOCK), 10, 0); -- -- /* div_frac */ -- regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -- 0xFFFF, 0x4555); -- break; -- - case 2700000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000238); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -@@ -722,6 +701,27 @@ - val, (val & HDMI_PLL_LOCK), 10, 0); - break; - -+ case 5120000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x5800026a); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x135c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ BIT(28), 0); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4aab); -+ break; -+ - case 5940000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x5800027b); - regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -@@ -760,15 +760,6 @@ - } else if (meson_vpu_is_compatible(priv, "amlogic,meson-gxm-vpu") || - meson_vpu_is_compatible(priv, "amlogic,meson-gxl-vpu")) { - switch (base) { -- case 2560000: -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x4000026a); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb2ab); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -- regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -- break; -- - case 2700000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000270); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb200); -@@ -847,6 +838,15 @@ - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; -+ -+ case 5120000: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x400002d5); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb155); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); - break; - -diff -ur a/drivers/gpu/drm/meson/meson_venc.c b/drivers/gpu/drm/meson/meson_venc.c ---- a/drivers/gpu/drm/meson/meson_venc.c 2018-06-02 16:39:27.777402009 +0200 -+++ b/drivers/gpu/drm/meson/meson_venc.c 2018-06-02 20:23:23.744646670 +0200 -@@ -713,6 +713,12 @@ - 968, 1056, 0, 600, 601, 605, 628, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, - }, -+ /* 1024x600@43Hz */ -+ { -+ { DRM_MODE("1024x600", DRM_MODE_TYPE_DRIVER, 32000, 1024, -+ 1064, 1112, 1152, 0, 600, 613, 616, 645, 0, -+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, -+ }, - /* 1024x768@60Hz */ - { - { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 65000, 1024, diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/113_linux-4.17-amlogic-dmt-extended-1002-custom-mode.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/113_linux-4.17-amlogic-dmt-extended-1002-custom-mode.patch deleted file mode 100644 index 97136bd0c..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/113_linux-4.17-amlogic-dmt-extended-1002-custom-mode.patch +++ /dev/null @@ -1,547 +0,0 @@ -diff -ur a/drivers/gpu/drm/meson/meson_dw_hdmi.c b/drivers/gpu/drm/meson/meson_dw_hdmi.c ---- a/drivers/gpu/drm/meson/meson_dw_hdmi.c 2018-06-02 16:39:27.777402009 +0200 -+++ b/drivers/gpu/drm/meson/meson_dw_hdmi.c 2018-06-02 17:25:33.803332054 +0200 -@@ -588,22 +588,28 @@ - /* Finally filter by configurable vclk frequencies */ - switch (vclk_freq) { - case 25175: -- case 40000: -+ case 29750: - case 32000: - case 36000: - case 33750: - case 33900: -+ case 40000: - case 54000: - case 65000: - case 74250: -+ case 106500: - case 108000: - case 148500: - case 162000: -+ case 193250: - case 297000: - case 594000: - return MODE_OK; - } - -+ if (meson_vclk_supported(vclk_freq)) -+ return MODE_OK; -+ - return MODE_CLOCK_RANGE; - } - -diff -ur a/drivers/gpu/drm/meson/meson_vclk.c b/drivers/gpu/drm/meson/meson_vclk.c ---- a/drivers/gpu/drm/meson/meson_vclk.c 2018-06-02 20:16:44.008061996 +0200 -+++ b/drivers/gpu/drm/meson/meson_vclk.c 2018-06-04 03:26:22.092619417 +0200 -@@ -321,39 +321,49 @@ - } - - --/* PLL O1 O2 O3 VP DV EN TX */ --/* 4320 /4 /4 /1 /5 /1 => /2 /2 */ --#define MESON_VCLK_HDMI_ENCI_54000 1 --/* 4320 /4 /4 /1 /5 /1 => /1 /2 */ --#define MESON_VCLK_HDMI_DDR_54000 2 --/* 2970 /4 /1 /1 /5 /1 => /1 /2 */ --#define MESON_VCLK_HDMI_DDR_148500 3 --/* 4028 /4 /4 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_25175 4 --/* 2560 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_32000 5 --/* 2700 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_33750 6 --/* 2712 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_33900 7 --/* 2880 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_36000 8 --/* 3200 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_40000 9 --/* 5200 /4 /2 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_65000 10 --/* 2970 /2 /2 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_74250 11 --/* 4320 /4 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_108000 12 --/* 2970 /1 /2 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_148500 13 --/* 3240 /2 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_162000 14 --/* 2970 /1 /1 /1 /5 /2 => /1 /1 */ --#define MESON_VCLK_HDMI_297000 15 --/* 5940 /1 /1 /2 /5 /1 => /1 /1 */ --#define MESON_VCLK_HDMI_594000 16 -+enum { -+ /* PLL O1 O2 O3 VP DV EN TX */ -+ /* 4320 /4 /4 /1 /5 /1 => /2 /2 */ -+ MESON_VCLK_HDMI_ENCI_54000 = 1, -+ /* 4320 /4 /4 /1 /5 /1 => /1 /2 */ -+ MESON_VCLK_HDMI_DDR_54000, -+ /* 2970 /4 /1 /1 /5 /1 => /1 /2 */ -+ MESON_VCLK_HDMI_DDR_148500, -+ /* 4028 /4 /4 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_25175, -+ /* 4760 /4 /4 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_29750, -+ /* 2560 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_32000, -+ /* 2700 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_33750, -+ /* 2712 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_33900, -+ /* 2880 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_36000, -+ /* 3200 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_40000, -+ /* 5200 /4 /2 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_65000, -+ /* 2970 /2 /2 /2 /5 /1 => /1 /1 */ -+ MESON_VCLK_HDMI_74250, -+ /* 4260 /4 /1 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_106500, -+ /* 4320 /4 /1 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_108000, -+ /* 2970 /1 /2 /2 /5 /1 => /1 /1 */ -+ MESON_VCLK_HDMI_148500, -+ /* 3240 /2 /1 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_162000, -+ /* 3865 /2 /1 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_193250, -+ /* 2970 /1 /1 /1 /5 /2 => /1 /1 */ -+ MESON_VCLK_HDMI_297000, -+ /* 5940 /1 /1 /2 /5 /1 => /1 /1 */ -+ MESON_VCLK_HDMI_594000, -+ /* custom calculated mode */ -+ MESON_VCLK_HDMI_CUSTOM, -+}; - - struct meson_vclk_params { - unsigned int pll_base_freq; -@@ -427,6 +437,14 @@ - .vid_pll_div = VID_PLL_DIV_5, - .vclk_div = 2, - }, -+ [MESON_VCLK_HDMI_29750] = { -+ .pll_base_freq = 4760000, -+ .pll_od1 = 4, -+ .pll_od2 = 4, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, - [MESON_VCLK_HDMI_32000] = { - .pll_base_freq = 5120000, - .pll_od1 = 4, -@@ -475,6 +493,14 @@ - .vid_pll_div = VID_PLL_DIV_5, - .vclk_div = 2, - }, -+ [MESON_VCLK_HDMI_106500] = { -+ .pll_base_freq = 4260000, -+ .pll_od1 = 4, -+ .pll_od2 = 1, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, - [MESON_VCLK_HDMI_108000] = { - .pll_base_freq = 4320000, - .pll_od1 = 4, -@@ -491,6 +517,14 @@ - .vid_pll_div = VID_PLL_DIV_5, - .vclk_div = 2, - }, -+ [MESON_VCLK_HDMI_193250] = { -+ .pll_base_freq = 3865000, -+ .pll_od1 = 2, -+ .pll_od2 = 1, -+ .pll_od3 = 1, -+ .vid_pll_div = VID_PLL_DIV_5, -+ .vclk_div = 2, -+ }, - }; - - static inline unsigned int pll_od_to_reg(unsigned int od) -@@ -519,6 +553,18 @@ - unsigned int val; - - if (meson_vpu_is_compatible(priv, "amlogic,meson-gxbb-vpu")) { -+ unsigned int step = 48000; -+ unsigned int range = 0x1000; -+ unsigned int round = step / range / 2; -+ unsigned int frac = base % step; -+ unsigned int m = (base - frac) / step; -+ -+ frac = (frac + round) * range / step; -+ if (frac >= range) -+ frac = range-1; -+ -+ dev_info(priv->dev, "%s: base=%d, m=0x%.2x, frac=0x%.3x\n", __func__, base, m, frac); -+ - switch (base) { - case 2700000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000238); -@@ -755,10 +801,49 @@ - /* Poll for lock bit */ - regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, - val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4555); -+ break; -+ -+ default: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x58000200 | m); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x00000000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x135c5091); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x801da72c); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x71486980); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x00000e55); -+ -+ /* unreset */ -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL, -+ BIT(28), 0); -+ -+ /* Poll for lock bit */ -+ regmap_read_poll_timeout(priv->hhi, HHI_HDMI_PLL_CNTL, -+ val, (val & HDMI_PLL_LOCK), 10, 0); -+ -+ /* div_frac */ -+ if (frac) -+ regmap_update_bits(priv->hhi, HHI_HDMI_PLL_CNTL2, -+ 0xFFFF, 0x4000 | frac); - break; -+ - }; - } else if (meson_vpu_is_compatible(priv, "amlogic,meson-gxm-vpu") || - meson_vpu_is_compatible(priv, "amlogic,meson-gxl-vpu")) { -+ unsigned int step = 24000; -+ unsigned int range = 0x400; -+ unsigned int round = step / range / 2; -+ unsigned int frac = base % step; -+ unsigned int m = (base - frac) / step; -+ -+ frac = (frac + round) * range / step; -+ if (frac >= range) -+ frac = range-1; -+ -+ pr_info("%s: base=%d, m=0x%.2x, frac=0x%.3x", __func__, base, m, frac); -+ - switch (base) { - case 2700000: - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000270); -@@ -868,6 +953,14 @@ - regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); - break; - -+ default: -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL, 0x40000200 | m); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL2, 0x800cb000 | frac); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL3, 0x860f30c4); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL4, 0x0c8e0000); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL5, 0x001fa729); -+ regmap_write(priv->hhi, HHI_HDMI_PLL_CNTL6, 0x01a31500); -+ break; - }; - - /* Reset PLL */ -@@ -906,6 +999,151 @@ - 3 << 19, pll_od_to_reg(od3) << 19); - } - -+unsigned int meson_vclk_freq_from_params(struct meson_vclk_params* vclk_params) -+{ -+ unsigned int vclk_freq = vclk_params->pll_base_freq / -+ vclk_params->pll_od1 / vclk_params->pll_od2 / -+ vclk_params->pll_od3 / vclk_params->vclk_div; -+ -+ switch (vclk_params->vid_pll_div) { -+ case VID_PLL_DIV_2: -+ vclk_freq /= 2; -+ break; -+ case VID_PLL_DIV_2p5: -+ vclk_freq *= 4; -+ vclk_freq /= 10; -+ break; -+ case VID_PLL_DIV_3: -+ vclk_freq /= 3; -+ break; -+ case VID_PLL_DIV_3p5: -+ vclk_freq *= 2; -+ vclk_freq /= 7; -+ break; -+ case VID_PLL_DIV_3p75: -+ vclk_freq *= 4; -+ vclk_freq /= 15; -+ break; -+ case VID_PLL_DIV_4: -+ vclk_freq /= 4; -+ break; -+ case VID_PLL_DIV_5: -+ vclk_freq /= 5; -+ break; -+ case VID_PLL_DIV_6: -+ vclk_freq /= 6; -+ break; -+ case VID_PLL_DIV_6p25: -+ vclk_freq *= 8; -+ vclk_freq /= 50; -+ break; -+ case VID_PLL_DIV_7: -+ vclk_freq /= 7; -+ break; -+ case VID_PLL_DIV_7p5: -+ vclk_freq *= 4; -+ vclk_freq /= 30; -+ break; -+ case VID_PLL_DIV_12: -+ vclk_freq /= 12; -+ break; -+ case VID_PLL_DIV_14: -+ vclk_freq /= 14; -+ break; -+ case VID_PLL_DIV_15: -+ vclk_freq /= 15; -+ break; -+ default: -+ return 0; -+ } -+ -+ return vclk_freq; -+} -+ -+static bool meson_get_vclk_params(unsigned int freq, -+ struct meson_vclk_params* vclk_params) -+{ -+ unsigned int vclk_freq = freq; -+ unsigned int base_freq, od1_od2, od3_vpll_vclk; -+ int p, jit; -+ bool found = false; -+ -+ if ((vclk_freq < 13500) || (vclk_freq > 594000)) -+ return false; -+ -+ if (vclk_freq % 25 > 12) -+ vclk_freq += 25; -+ vclk_freq -= vclk_freq % 25; -+ -+ for (p = 1; p < sizeof(params) / sizeof(struct meson_vclk_params); p++) { -+ if (params[p].vid_pll_div != VID_PLL_DIV_5) -+ continue; -+ -+ od1_od2 = params[p].pll_od1 * params[p].pll_od2; -+ od3_vpll_vclk = params[p].pll_od3 * 5 * params[p].vclk_div; -+ -+ if ((od3_vpll_vclk != 10) && (vclk_freq > 54000 + 175)) -+ continue; -+ -+ base_freq = vclk_freq * od1_od2 * od3_vpll_vclk; -+ -+ if ((base_freq < 2700000) || (base_freq > 5940000)) -+ continue; -+ -+ vclk_params->pll_base_freq = base_freq; -+ vclk_params->pll_od1 = params[p].pll_od1; -+ vclk_params->pll_od2 = params[p].pll_od2; -+ vclk_params->pll_od3 = params[p].pll_od3; -+ vclk_params->vid_pll_div = params[p].vid_pll_div; -+ vclk_params->vclk_div = params[p].vclk_div; -+ -+ found = true; -+ -+ if (params[p].pll_base_freq > vclk_params->pll_base_freq) -+ jit = params[p].pll_base_freq - vclk_params->pll_base_freq; -+ else -+ jit = vclk_params->pll_base_freq - params[p].pll_base_freq; -+ -+ if (jit < 175 * od1_od2 * od3_vpll_vclk) { -+ vclk_params->pll_base_freq = params[p].pll_base_freq; -+ vclk_freq = vclk_params->pll_base_freq / od1_od2 / od3_vpll_vclk; -+ } -+ -+ if (jit < 40000) -+ break; -+ } -+ -+ return found; -+} -+ -+static void meson_print_vclk_params(struct meson_drm *priv, unsigned int freq, -+ struct meson_vclk_params* vclk_params) -+{ -+ unsigned int vclk_freq = meson_vclk_freq_from_params(vclk_params); -+ -+ if (vclk_params->vid_pll_div != VID_PLL_DIV_5) -+ return; -+ -+ if (vclk_freq != freq) -+ dev_info(priv->dev, "adjusted %d -> %d", freq, vclk_freq); -+ -+ dev_info(priv->dev, "params %d / %d / %d / %d / %d / %d = %d\n", -+ vclk_params->pll_base_freq, -+ vclk_params->pll_od1, -+ vclk_params->pll_od2, -+ vclk_params->pll_od3, -+ 5, vclk_params->vclk_div, -+ vclk_freq); -+} -+ -+bool meson_vclk_supported(unsigned int vclk_freq) -+{ -+ struct meson_vclk_params custom_params; -+ -+ return (meson_get_vclk_params(vclk_freq, &custom_params)); -+} -+EXPORT_SYMBOL_GPL(meson_vclk_supported); -+ - void meson_vclk_setup(struct meson_drm *priv, unsigned int target, - unsigned int vclk_freq, unsigned int venc_freq, - unsigned int dac_freq, bool hdmi_use_enci) -@@ -913,6 +1151,8 @@ - unsigned int freq; - unsigned int hdmi_tx_div; - unsigned int venc_div; -+ struct meson_vclk_params custom_params; -+ struct meson_vclk_params* vclk_params; - - if (target == MESON_VCLK_TARGET_CVBS) { - meson_venci_cvbs_clock_config(priv); -@@ -945,6 +1185,9 @@ - case 25175: - freq = MESON_VCLK_HDMI_25175; - break; -+ case 29750: -+ freq = MESON_VCLK_HDMI_29750; -+ break; - case 32000: - freq = MESON_VCLK_HDMI_32000; - break; -@@ -966,6 +1209,9 @@ - case 74250: - freq = MESON_VCLK_HDMI_74250; - break; -+ case 106500: -+ freq = MESON_VCLK_HDMI_106500; -+ break; - case 108000: - freq = MESON_VCLK_HDMI_108000; - break; -@@ -978,6 +1224,9 @@ - case 162000: - freq = MESON_VCLK_HDMI_162000; - break; -+ case 193250: -+ freq = MESON_VCLK_HDMI_193250; -+ break; - case 297000: - freq = MESON_VCLK_HDMI_297000; - break; -@@ -985,9 +1234,8 @@ - freq = MESON_VCLK_HDMI_594000; - break; - default: -- pr_err("Fatal Error, invalid HDMI vclk freq %d\n", -- vclk_freq); -- return; -+ freq = MESON_VCLK_HDMI_CUSTOM; -+ break; - } - - /* Set HDMI-TX sys clock */ -@@ -998,20 +1246,35 @@ - regmap_update_bits(priv->hhi, HHI_HDMI_CLK_CNTL, - CTS_HDMI_SYS_EN, CTS_HDMI_SYS_EN); - -+ vclk_params = NULL; -+ -+ if (freq != MESON_VCLK_HDMI_CUSTOM) -+ vclk_params = ¶ms[freq]; -+ else if (meson_get_vclk_params(vclk_freq, &custom_params)) -+ vclk_params = &custom_params; -+ -+ if (!vclk_params) { -+ pr_err("Fatal Error, invalid HDMI vclk freq %d\n", -+ vclk_freq); -+ return; -+ } -+ -+ meson_print_vclk_params(priv, vclk_freq, vclk_params); -+ - /* Set HDMI PLL rate */ -- meson_hdmi_pll_set(priv, params[freq].pll_base_freq, -- params[freq].pll_od1, -- params[freq].pll_od2, -- params[freq].pll_od3); -+ meson_hdmi_pll_set(priv, vclk_params->pll_base_freq, -+ vclk_params->pll_od1, -+ vclk_params->pll_od2, -+ vclk_params->pll_od3); - - /* Setup vid_pll divider */ -- meson_vid_pll_set(priv, params[freq].vid_pll_div); -+ meson_vid_pll_set(priv, vclk_params->vid_pll_div); - - /* Set VCLK div */ - regmap_update_bits(priv->hhi, HHI_VID_CLK_CNTL, - VCLK_SEL_MASK, 0); - regmap_update_bits(priv->hhi, HHI_VID_CLK_DIV, -- VCLK_DIV_MASK, params[freq].vclk_div - 1); -+ VCLK_DIV_MASK, vclk_params->vclk_div - 1); - - /* Set HDMI-TX source */ - switch (hdmi_tx_div) { -diff -ur a/drivers/gpu/drm/meson/meson_vclk.h b/drivers/gpu/drm/meson/meson_vclk.h ---- a/drivers/gpu/drm/meson/meson_vclk.h 2018-05-26 22:29:37.112948771 +0200 -+++ b/drivers/gpu/drm/meson/meson_vclk.h 2018-05-31 05:15:53.342134304 +0200 -@@ -29,6 +29,8 @@ - /* 27MHz is the CVBS Pixel Clock */ - #define MESON_VCLK_CVBS 27000 - -+bool meson_vclk_supported(unsigned int vclk_freq); -+ - void meson_vclk_setup(struct meson_drm *priv, unsigned int target, - unsigned int vclk_freq, unsigned int venc_freq, - unsigned int dac_freq, bool hdmi_use_enci); -diff -ur a/drivers/gpu/drm/meson/meson_venc.c b/drivers/gpu/drm/meson/meson_venc.c ---- a/drivers/gpu/drm/meson/meson_venc.c 2018-06-02 20:23:23.744646670 +0200 -+++ b/drivers/gpu/drm/meson/meson_venc.c 2018-06-02 17:25:33.807332121 +0200 -@@ -707,6 +707,12 @@ - 752, 800, 0, 480, 490, 492, 525, 0, - DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, - }, -+ /* 800x480@60Hz */ -+ { -+ { DRM_MODE("800x480", DRM_MODE_TYPE_DRIVER, 29750, 800, 824, -+ 896, 992, 0, 480, 483, 490, 500, 0, -+ DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, -+ }, - /* 800x600@60Hz */ - { - { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 40000, 800, 840, -@@ -737,6 +743,12 @@ - 1328, 1440, 1688, 0, 1024, 1025, 1028, 1066, 0, - DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) }, - }, -+ /* 1440x900@60Hz */ -+ { -+ { DRM_MODE("1440x900", DRM_MODE_TYPE_DRIVER, 106500, 1440, -+ 1520, 1672, 1904, 0, 900, 903, 909, 934, 0, -+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) }, -+ }, - /* 1600x1200@60Hz */ - { - { DRM_MODE("1600x1200", DRM_MODE_TYPE_DRIVER, 162000, 1600, -@@ -749,6 +761,12 @@ - 2008, 2052, 2200, 0, 1080, 1084, 1089, 1125, 0, - DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) }, - }, -+ /* 1920x1200@60Hz */ -+ { -+ { DRM_MODE("1920x1200", DRM_MODE_TYPE_DRIVER, 193250, 1920, -+ 2056, 2256, 2592, 0, 1200, 1203, 1209, 1245, 0, -+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) }, -+ }, - { }, /* sentinel */ - }; - diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/114_linux-4.17-amlogic-dmt-extended-1003-calculate-clock-dividers.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/114_linux-4.17-amlogic-dmt-extended-1003-calculate-clock-dividers.patch deleted file mode 100644 index 5dfcace64..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/114_linux-4.17-amlogic-dmt-extended-1003-calculate-clock-dividers.patch +++ /dev/null @@ -1,115 +0,0 @@ -diff -u a/drivers/gpu/drm/meson/meson_vclk.c b/drivers/gpu/drm/meson/meson_vclk.c ---- a/drivers/gpu/drm/meson/meson_vclk.c 2018-06-10 06:10:59.071504595 +0200 -+++ b/drivers/gpu/drm/meson/meson_vclk.c 2018-06-10 05:33:51.347202114 +0200 -@@ -842,7 +842,7 @@ - if (frac >= range) - frac = range-1; - -- pr_info("%s: base=%d, m=0x%.2x, frac=0x%.3x", __func__, base, m, frac); -+ dev_info(priv->dev, "%s: base=%d, m=0x%.2x, frac=0x%.3x\n", __func__, base, m, frac); - - switch (base) { - case 2700000: -@@ -1065,25 +1065,36 @@ - { - unsigned int vclk_freq = freq; - unsigned int base_freq, od1_od2, od3_vpll_vclk; -- int p, jit; -+ int od1, od2, od3, p, jit; - bool found = false; - -- if ((vclk_freq < 13500) || (vclk_freq > 594000)) -+ if ((vclk_freq < 12000) || (vclk_freq > 594000)) - return false; - - if (vclk_freq % 25 > 12) - vclk_freq += 25; - vclk_freq -= vclk_freq % 25; - -- for (p = 1; p < sizeof(params) / sizeof(struct meson_vclk_params); p++) { -- if (params[p].vid_pll_div != VID_PLL_DIV_5) -+ for (p = 0; p < 6; p++) { -+ od1 = (1 << p); -+ od2 = 1; -+ od3 = 1; -+ -+ if ((vclk_freq > 18550) && (od1 > 16)) - continue; - -- od1_od2 = params[p].pll_od1 * params[p].pll_od2; -- od3_vpll_vclk = params[p].pll_od3 * 5 * params[p].vclk_div; -+ if (od1 > 16) { -+ od3 = od1 / 16; -+ od1 = 16; -+ } - -- if ((od3_vpll_vclk != 10) && (vclk_freq > 54000 + 175)) -- continue; -+ if (od1 > 4) { -+ od2 = od1 / 4; -+ od1 = 4; -+ } -+ -+ od1_od2 = od1 * od2; -+ od3_vpll_vclk = od3 * 5 * 2; - - base_freq = vclk_freq * od1_od2 * od3_vpll_vclk; - -@@ -1091,21 +1102,32 @@ - continue; - - vclk_params->pll_base_freq = base_freq; -- vclk_params->pll_od1 = params[p].pll_od1; -- vclk_params->pll_od2 = params[p].pll_od2; -- vclk_params->pll_od3 = params[p].pll_od3; -- vclk_params->vid_pll_div = params[p].vid_pll_div; -- vclk_params->vclk_div = params[p].vclk_div; -+ vclk_params->pll_od1 = od1; -+ vclk_params->pll_od2 = od2; -+ vclk_params->pll_od3 = od3; -+ vclk_params->vid_pll_div = VID_PLL_DIV_5; -+ vclk_params->vclk_div = 2; - - found = true; - -- if (params[p].pll_base_freq > vclk_params->pll_base_freq) -- jit = params[p].pll_base_freq - vclk_params->pll_base_freq; -+ jit = od1_od2 * od3_vpll_vclk * 125; -+ if (p < 3) -+ jit <<= (3-p); -+ -+ if ((base_freq % 24000) < (base_freq % jit)) -+ jit = 24000; -+ -+ if ((base_freq % jit) > (jit / 2)) -+ base_freq = base_freq+jit; -+ base_freq -= base_freq % jit; -+ -+ if (base_freq > vclk_params->pll_base_freq) -+ jit = base_freq - vclk_params->pll_base_freq; - else -- jit = vclk_params->pll_base_freq - params[p].pll_base_freq; -+ jit = vclk_params->pll_base_freq - base_freq; - - if (jit < 175 * od1_od2 * od3_vpll_vclk) { -- vclk_params->pll_base_freq = params[p].pll_base_freq; -+ vclk_params->pll_base_freq = base_freq; - vclk_freq = vclk_params->pll_base_freq / od1_od2 / od3_vpll_vclk; - } - -diff -u a/drivers/gpu/drm/meson/meson_venc.c b/drivers/gpu/drm/meson/meson_venc.c ---- a/drivers/gpu/drm/meson/meson_venc.c 2018-06-10 06:10:59.071504595 +0200 -+++ b/drivers/gpu/drm/meson/meson_venc.c 2018-06-10 05:26:59.995203463 +0200 -@@ -816,10 +816,10 @@ - DRM_MODE_FLAG_PVSYNC | DRM_MODE_FLAG_NVSYNC)) - return MODE_BAD; - -- if (mode->hdisplay < 640 || mode->hdisplay > 1920) -+ if (mode->hdisplay < 416 || mode->hdisplay > 1920) - return MODE_BAD_HVALUE; - -- if (mode->vdisplay < 480 || mode->vdisplay > 1200) -+ if (mode->vdisplay < 360 || mode->vdisplay > 1200) - return MODE_BAD_VVALUE; - - return MODE_OK; diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/115_linux-4.14.y-input_touchscreen-vu5-vu7plus.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/115_linux-4.14.y-input_touchscreen-vu5-vu7plus.patch deleted file mode 100644 index e1cb84e1b..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/115_linux-4.14.y-input_touchscreen-vu5-vu7plus.patch +++ /dev/null @@ -1,1235 +0,0 @@ -diff --git a/drivers/hid/hid-core.c b/drivers/hid/hid-core.c -index 672b0be41..f46efab94 100644 ---- a/drivers/hid/hid-core.c -+++ b/drivers/hid/hid-core.c -@@ -2776,6 +2776,8 @@ static const struct hid_device_id hid_ignore_list[] = { - { HID_USB_DEVICE(USB_VENDOR_ID_SYNAPTICS, USB_DEVICE_ID_SYNAPTICS_DPAD) }, - #endif - { HID_USB_DEVICE(USB_VENDOR_ID_YEALINK, USB_DEVICE_ID_YEALINK_P1K_P4K_B2K) }, -+ { HID_USB_DEVICE(USB_VENDOR_ID_ODROID, USB_DEVICE_ID_VU5) }, -+ { HID_USB_DEVICE(USB_VENDOR_ID_ODROID, USB_DEVICE_ID_VU7PLUS) }, - { } - }; - -diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h -index ff539c0b4..b09d5ea03 100644 ---- a/drivers/hid/hid-ids.h -+++ b/drivers/hid/hid-ids.h -@@ -1164,4 +1164,10 @@ - #define USB_VENDOR_ID_UGTIZER 0x2179 - #define USB_DEVICE_ID_UGTIZER_TABLET_GP0610 0x0053 - -+#define USB_DEVICE_ID_DWAV_MULTITOUCH 0x0005 -+ -+#define USB_VENDOR_ID_ODROID 0x16b4 -+#define USB_DEVICE_ID_VU5 0x0704 -+#define USB_DEVICE_ID_VU7PLUS 0x0705 -+ - #endif -diff --git a/drivers/input/touchscreen/Kconfig b/drivers/input/touchscreen/Kconfig -index 64b30fe27..05e834eed 100644 ---- a/drivers/input/touchscreen/Kconfig -+++ b/drivers/input/touchscreen/Kconfig -@@ -1246,4 +1246,23 @@ config TOUCHSCREEN_ROHM_BU21023 - To compile this driver as a module, choose M here: the - module will be called bu21023_ts. - -+config TOUCHSCREEN_DWAV_USB_MT -+ tristate "D-WAV Scientific USB MultiTouch" -+ depends on USB_ARCH_HAS_HCD -+ select USB -+ help -+ Say Y here if you have a D-WAV Scientific USB(HID) based MultiTouch -+ controller. -+ -+ If unsure, say N. -+ -+ To compile this driver as a module, choose M here: the -+ module will be called dwav-usb-mt. -+ -+config TOUCHSCREEN_SX865X -+ tristate "Semtech multitouch resistive touchscreen" -+ depends on I2C -+ help -+ This enables support for Semtech multitouch resistive touchscreen. -+ - endif -diff --git a/drivers/input/touchscreen/Makefile b/drivers/input/touchscreen/Makefile -index 850c15625..bc3f0e1d5 100644 ---- a/drivers/input/touchscreen/Makefile -+++ b/drivers/input/touchscreen/Makefile -@@ -104,3 +104,5 @@ obj-$(CONFIG_TOUCHSCREEN_ZET6223) += zet6223.o - obj-$(CONFIG_TOUCHSCREEN_ZFORCE) += zforce_ts.o - obj-$(CONFIG_TOUCHSCREEN_COLIBRI_VF50) += colibri-vf50-ts.o - obj-$(CONFIG_TOUCHSCREEN_ROHM_BU21023) += rohm_bu21023.o -+obj-$(CONFIG_TOUCHSCREEN_DWAV_USB_MT) += dwav-usb-mt.o -+obj-$(CONFIG_TOUCHSCREEN_SX865X) += sx865x.o -diff -urN a/drivers/input/touchscreen/dwav-usb-mt.c b/drivers/input/touchscreen/dwav-usb-mt.c ---- a/drivers/input/touchscreen/dwav-usb-mt.c 1970-01-01 01:00:00.000000000 +0100 -+++ b/drivers/input/touchscreen/dwav-usb-mt.c 2018-05-06 10:03:40.485939294 +0200 -@@ -0,0 +1,577 @@ -+/*------------------------------------------------------------------------- -+ -+ D-WAV Scientific USB(HID) MultiTouch Screen Driver(Based on usbtouchscreen.c) -+ Hardkernel : 2015/09/17 -+ -+-------------------------------------------------------------------------*/ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include -+ -+/*-------------------------------------------------------------------------*/ -+#define USB_VENDOR_ID_DWAV 0x0eef /* 800 x 480, 7" DWAV touch */ -+#define USB_DEVICE_ID_VU7 0x0005 -+ -+#define USB_VENDOR_ID_ODROID 0x16b4 -+#define USB_DEVICE_ID_VU5 0x0704 -+#define USB_DEVICE_ID_VU7PLUS 0x0705 -+ -+enum { -+ ODROID_VU7 = 0, /* 800 x 480, 7" Touch */ -+ ODROID_VU5, /* 800 x 480, 5" Touch */ -+ ODROID_VU7PLUS, /* 1024 x 600, 7" Touch */ -+}; -+ -+/*-------------------------------------------------------------------------*/ -+struct usbtouch_device_info { -+ char name[64]; -+ int max_x; -+ int max_y; -+ int max_press; -+ int max_finger; -+}; -+ -+/*-------------------------------------------------------------------------*/ -+const struct usbtouch_device_info DEV_INFO[] = { -+ [ODROID_VU7] = { -+ .name = "ODROID VU7 MultiTouch(800x480)", -+ .max_x = 800, -+ .max_y = 480, -+ .max_press = 255, -+ .max_finger = 5, -+ }, -+ [ODROID_VU5] = { -+ .name = "ODROID VU5 MultiTouch(800x480)", -+ .max_x = 800, -+ .max_y = 480, -+ .max_press = 255, -+ .max_finger = 5, -+ }, -+ [ODROID_VU7PLUS] = { -+ .name = "ODROID VU7 Plus MultiTouch(1024x600)", -+ .max_x = 1024, -+ .max_y = 600, -+ .max_press = 255, -+ .max_finger = 5, -+ }, -+}; -+ -+/*-------------------------------------------------------------------------*/ -+static const struct usb_device_id dwav_usb_mt_devices[] = { -+ {USB_DEVICE(USB_VENDOR_ID_DWAV, USB_DEVICE_ID_VU7), -+ .driver_info = ODROID_VU7}, -+ {USB_DEVICE(USB_VENDOR_ID_ODROID, USB_DEVICE_ID_VU5), -+ .driver_info = ODROID_VU5}, -+ {USB_DEVICE(USB_VENDOR_ID_ODROID, USB_DEVICE_ID_VU7PLUS), -+ .driver_info = ODROID_VU7PLUS}, -+ {} -+}; -+ -+/*-------------------------------------------------------------------------*/ -+struct dwav_raw { /* Total 25 bytes */ -+ unsigned char header; /* frame header 0xAA*/ -+ unsigned char press; -+ /* Touch flag (1:valid touch data, 0:touch finished) */ -+ unsigned short x1; /* 1st x */ -+ unsigned short y1; /* 1st y */ -+ unsigned char end; -+ /* 1st touch finish flags 0xBB, RPI only uses the first 7 bytes */ -+ unsigned char ids; /* touch ID(bit field) */ -+ unsigned short y2; -+ unsigned short x2; -+ unsigned short y3; -+ unsigned short x3; -+ unsigned short y4; -+ unsigned short x4; -+ unsigned short y5; -+ unsigned short x5; -+ unsigned char tail; /* frame end 0xCC */ -+}; -+ -+/*------------------------------------------------------------------------- -+ Touch Event type define -+-------------------------------------------------------------------------*/ -+#define TS_EVENT_UNKNOWN 0x00 -+#define TS_EVENT_PRESS 0x01 -+#define TS_EVENT_RELEASE 0x02 -+ -+struct finger_t { -+ unsigned int status; /* ts event type */ -+ unsigned int x; /* ts data x */ -+ unsigned int y; /* ts data y */ -+} __packed; -+ -+struct dwav_usb_mt { -+ char name[128], phys[64]; -+ -+ int dev_id; -+ /* for URB Data DMA */ -+ dma_addr_t data_dma; -+ unsigned char *data; -+ int data_size; -+ -+ struct urb *irq; -+ struct usb_interface *interface; -+ struct input_dev *input; -+ -+ struct finger_t *finger; -+}; -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_report(struct dwav_usb_mt *dwav_usb_mt) -+{ -+ int id, max_x, max_y, max_press, max_finger; -+ -+ max_x = DEV_INFO[dwav_usb_mt->dev_id].max_x; -+ max_y = DEV_INFO[dwav_usb_mt->dev_id].max_y; -+ max_press = DEV_INFO[dwav_usb_mt->dev_id].max_press; -+ max_finger = DEV_INFO[dwav_usb_mt->dev_id].max_finger; -+ -+ for (id = 0; id < max_finger; id++) { -+ -+ if (dwav_usb_mt->finger[id].status == TS_EVENT_UNKNOWN) -+ continue; -+ -+ if (dwav_usb_mt->finger[id].x >= max_x || -+ dwav_usb_mt->finger[id].y >= max_y) -+ continue; -+ -+ input_mt_slot(dwav_usb_mt->input, id); -+ -+ if (dwav_usb_mt->finger[id].status != TS_EVENT_RELEASE) { -+ input_mt_report_slot_state(dwav_usb_mt->input, -+ MT_TOOL_FINGER, true); -+ input_report_abs(dwav_usb_mt->input, -+ ABS_MT_POSITION_X, -+ dwav_usb_mt->finger[id].x); -+ input_report_abs(dwav_usb_mt->input, -+ ABS_MT_POSITION_Y, -+ dwav_usb_mt->finger[id].y); -+ input_report_abs(dwav_usb_mt->input, -+ ABS_MT_PRESSURE, -+ max_press); -+ } else { -+ input_mt_report_slot_state(dwav_usb_mt->input, -+ MT_TOOL_FINGER, false); -+ dwav_usb_mt->finger[id].status = TS_EVENT_UNKNOWN; -+ } -+ input_mt_report_pointer_emulation(dwav_usb_mt->input, true); -+ input_sync(dwav_usb_mt->input); -+ } -+} -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_process(struct dwav_usb_mt *dwav_usb_mt, -+ unsigned char *pkt, int len) -+{ -+ struct dwav_raw *dwav_raw = (struct dwav_raw *)pkt; -+ unsigned char bit_mask, cnt; -+ -+ for (cnt = 0, bit_mask = 0x01; -+ cnt < DEV_INFO[dwav_usb_mt->dev_id].max_finger; -+ cnt++, bit_mask <<= 1) { -+ if ((dwav_raw->ids & bit_mask) && dwav_raw->press) { -+ dwav_usb_mt->finger[cnt].status = TS_EVENT_PRESS; -+ switch (cnt) { -+ case 0: -+ dwav_usb_mt->finger[cnt].x -+ = cpu_to_be16(dwav_raw->x1); -+ dwav_usb_mt->finger[cnt].y -+ = cpu_to_be16(dwav_raw->y1); -+ break; -+ case 1: -+ dwav_usb_mt->finger[cnt].x -+ = cpu_to_be16(dwav_raw->x2); -+ dwav_usb_mt->finger[cnt].y -+ = cpu_to_be16(dwav_raw->y2); -+ break; -+ case 2: -+ dwav_usb_mt->finger[cnt].x -+ = cpu_to_be16(dwav_raw->x3); -+ dwav_usb_mt->finger[cnt].y -+ = cpu_to_be16(dwav_raw->y3); -+ break; -+ case 3: -+ dwav_usb_mt->finger[cnt].x -+ = cpu_to_be16(dwav_raw->x4); -+ dwav_usb_mt->finger[cnt].y -+ = cpu_to_be16(dwav_raw->y4); -+ break; -+ case 4: -+ dwav_usb_mt->finger[cnt].x -+ = cpu_to_be16(dwav_raw->x5); -+ dwav_usb_mt->finger[cnt].y -+ = cpu_to_be16(dwav_raw->y5); -+ break; -+ default: -+ break; -+ } -+ } else { -+ if (dwav_usb_mt->finger[cnt].status == TS_EVENT_PRESS) -+ dwav_usb_mt->finger[cnt].status -+ = TS_EVENT_RELEASE; -+ else -+ dwav_usb_mt->finger[cnt].status -+ = TS_EVENT_UNKNOWN; -+ } -+ } -+ dwav_usb_mt_report(dwav_usb_mt); -+} -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_irq(struct urb *urb) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = urb->context; -+ struct device *dev = &dwav_usb_mt->interface->dev; -+ int retval; -+ -+ switch (urb->status) { -+ case 0: -+ /* success */ -+ break; -+ case -ETIME: -+ /* this urb is timing out */ -+ dev_dbg(dev, "%s - urb timed out - was the device unplugged?\n", -+ __func__); -+ return; -+ case -ECONNRESET: -+ case -ENOENT: -+ case -ESHUTDOWN: -+ case -EPIPE: -+ /* this urb is terminated, clean up */ -+ dev_dbg(dev, "%s - urb shutting down with status: %d\n", -+ __func__, urb->status); -+ return; -+ default: -+ dev_dbg(dev, "%s - nonzero urb status received: %d\n", -+ __func__, urb->status); -+ goto exit; -+ } -+ -+ dwav_usb_mt_process(dwav_usb_mt, dwav_usb_mt->data, urb->actual_length); -+ -+exit: -+ usb_mark_last_busy(interface_to_usbdev(dwav_usb_mt->interface)); -+ retval = usb_submit_urb(urb, GFP_ATOMIC); -+ if (retval) { -+ dev_err(dev, "%s - usb_submit_urb failed with result: %d\n", -+ __func__, retval); -+ } -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_open(struct input_dev *input) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = input_get_drvdata(input); -+ int r; -+ -+ dwav_usb_mt->irq->dev = interface_to_usbdev(dwav_usb_mt->interface); -+ -+ r = usb_autopm_get_interface(dwav_usb_mt->interface) ? -EIO : 0; -+ if (r < 0) -+ goto out; -+ -+ if (usb_submit_urb(dwav_usb_mt->irq, GFP_KERNEL)) { -+ r = -EIO; -+ goto out_put; -+ } -+ -+ dwav_usb_mt->interface->needs_remote_wakeup = 1; -+out_put: -+ usb_autopm_put_interface(dwav_usb_mt->interface); -+out: -+ return r; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_close(struct input_dev *input) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = input_get_drvdata(input); -+ int r; -+ -+ usb_kill_urb(dwav_usb_mt->irq); -+ -+ r = usb_autopm_get_interface(dwav_usb_mt->interface); -+ -+ dwav_usb_mt->interface->needs_remote_wakeup = 0; -+ if (!r) -+ usb_autopm_put_interface(dwav_usb_mt->interface); -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_suspend(struct usb_interface *intf, pm_message_t message) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = usb_get_intfdata(intf); -+ -+ usb_kill_urb(dwav_usb_mt->irq); -+ -+ return 0; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_resume(struct usb_interface *intf) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = usb_get_intfdata(intf); -+ struct input_dev *input = dwav_usb_mt->input; -+ int result = 0; -+ -+ mutex_lock(&input->mutex); -+ if (input->users) -+ result = usb_submit_urb(dwav_usb_mt->irq, GFP_NOIO); -+ mutex_unlock(&input->mutex); -+ -+ return result; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_reset_resume(struct usb_interface *intf) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = usb_get_intfdata(intf); -+ struct input_dev *input = dwav_usb_mt->input; -+ int err = 0; -+ -+ /* restart IO if needed */ -+ mutex_lock(&input->mutex); -+ if (input->users) -+ err = usb_submit_urb(dwav_usb_mt->irq, GFP_NOIO); -+ mutex_unlock(&input->mutex); -+ -+ return err; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_free_buffers(struct usb_device *udev, -+ struct dwav_usb_mt *dwav_usb_mt) -+{ -+ usb_free_coherent(udev, dwav_usb_mt->data_size, -+ dwav_usb_mt->data, dwav_usb_mt->data_dma); -+} -+ -+/*-------------------------------------------------------------------------*/ -+static struct usb_endpoint_descriptor *dwav_usb_mt_get_input_endpoint( -+ struct usb_host_interface *interface) -+{ -+ int i; -+ -+ for (i = 0; i < interface->desc.bNumEndpoints; i++) { -+ if (usb_endpoint_dir_in(&interface->endpoint[i].desc)) -+ return &interface->endpoint[i].desc; -+ } -+ -+ return NULL; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_init(struct dwav_usb_mt *dwav_usb_mt, void *dev) -+{ -+ int err; -+ struct input_dev *input_dev = (struct input_dev *)dev; -+ -+ input_dev->name = dwav_usb_mt->name; -+ input_dev->phys = dwav_usb_mt->phys; -+ -+ input_set_drvdata(input_dev, dwav_usb_mt); -+ -+ input_dev->open = dwav_usb_mt_open; -+ input_dev->close = dwav_usb_mt_close; -+ -+ input_dev->id.bustype = BUS_USB; -+ -+ /* single touch */ -+ input_dev->evbit[0] = BIT_MASK(EV_KEY) | BIT_MASK(EV_ABS); -+ input_dev->keybit[BIT_WORD(BTN_TOUCH)] = BIT_MASK(BTN_TOUCH); -+ -+ input_set_abs_params(input_dev, ABS_X, 0, -+ DEV_INFO[dwav_usb_mt->dev_id].max_x, 0, 0); -+ input_set_abs_params(input_dev, ABS_Y, 0, -+ DEV_INFO[dwav_usb_mt->dev_id].max_y, 0, 0); -+ -+ /* multi touch */ -+ input_set_abs_params(input_dev, ABS_MT_POSITION_X, 0, -+ DEV_INFO[dwav_usb_mt->dev_id].max_x, 0, 0); -+ input_set_abs_params(input_dev, ABS_MT_POSITION_Y, 0, -+ DEV_INFO[dwav_usb_mt->dev_id].max_y, 0, 0); -+ input_mt_init_slots(input_dev, -+ DEV_INFO[dwav_usb_mt->dev_id].max_finger, 0); -+ -+ err = input_register_device(input_dev); -+ if (err) { -+ pr_err("%s - input_register_device failed, err: %d\n", -+ __func__, err); -+ return err; -+ } -+ -+ dwav_usb_mt->input = input_dev; -+ -+ return 0; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static int dwav_usb_mt_probe(struct usb_interface *intf, -+ const struct usb_device_id *id) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = NULL; -+ struct input_dev *input_dev = NULL; -+ struct usb_endpoint_descriptor *endpoint; -+ struct usb_device *udev = interface_to_usbdev(intf); -+ -+ int err = 0; -+ -+ endpoint = dwav_usb_mt_get_input_endpoint(intf->cur_altsetting); -+ if (!endpoint) -+ return -ENXIO; -+ -+ dwav_usb_mt = kzalloc(sizeof(struct dwav_usb_mt), GFP_KERNEL); -+ if (!dwav_usb_mt) -+ return -ENOMEM; -+ -+ dwav_usb_mt->dev_id = id->driver_info; -+ -+ dwav_usb_mt->finger = kzalloc(sizeof(struct finger_t) * -+ DEV_INFO[dwav_usb_mt->dev_id].max_finger, -+ GFP_KERNEL); -+ -+ if (!dwav_usb_mt->finger) -+ goto err_free_mem; -+ -+ input_dev = input_allocate_device(); -+ if (!input_dev) -+ goto err_free_mem; -+ -+ dwav_usb_mt->data_size = sizeof(struct dwav_raw); -+ dwav_usb_mt->data = usb_alloc_coherent(udev, dwav_usb_mt->data_size, -+ GFP_KERNEL, &dwav_usb_mt->data_dma); -+ if (!dwav_usb_mt->data) -+ goto err_free_mem; -+ -+ dwav_usb_mt->irq = usb_alloc_urb(0, GFP_KERNEL); -+ if (!dwav_usb_mt->irq) { -+ dev_dbg(&intf->dev, -+ "%s - usb_alloc_urb failed: usbtouch->irq\n", -+ __func__); -+ goto err_free_buffers; -+ } -+ -+ if (usb_endpoint_type(endpoint) == USB_ENDPOINT_XFER_INT) { -+ usb_fill_int_urb(dwav_usb_mt->irq, udev, -+ usb_rcvintpipe(udev, endpoint->bEndpointAddress), -+ dwav_usb_mt->data, dwav_usb_mt->data_size, -+ dwav_usb_mt_irq, dwav_usb_mt, endpoint->bInterval); -+ } else { -+ usb_fill_bulk_urb(dwav_usb_mt->irq, udev, -+ usb_rcvbulkpipe(udev, endpoint->bEndpointAddress), -+ dwav_usb_mt->data, dwav_usb_mt->data_size, -+ dwav_usb_mt_irq, dwav_usb_mt); -+ } -+ -+ dwav_usb_mt->irq->dev = udev; -+ dwav_usb_mt->irq->transfer_dma = dwav_usb_mt->data_dma; -+ dwav_usb_mt->irq->transfer_flags |= URB_NO_TRANSFER_DMA_MAP; -+ -+ dwav_usb_mt->interface = intf; -+ -+ if (udev->manufacturer) -+ strlcpy(dwav_usb_mt->name, -+ udev->manufacturer, sizeof(dwav_usb_mt->name)); -+ -+ if (udev->product) { -+ if (udev->manufacturer) -+ strlcat(dwav_usb_mt->name, -+ " ", sizeof(dwav_usb_mt->name)); -+ -+ strlcat(dwav_usb_mt->name, -+ udev->product, sizeof(dwav_usb_mt->name)); -+ } -+ -+ if (!strlen(dwav_usb_mt->name)) { -+ snprintf(dwav_usb_mt->name, sizeof(dwav_usb_mt->name), -+ "D-WAV Scientific MultiTouch %04x:%04x", -+ le16_to_cpu(udev->descriptor.idVendor), -+ le16_to_cpu(udev->descriptor.idProduct)); -+ } -+ -+ usb_make_path(udev, dwav_usb_mt->phys, sizeof(dwav_usb_mt->phys)); -+ strlcat(dwav_usb_mt->phys, "/input0", sizeof(dwav_usb_mt->phys)); -+ -+ usb_to_input_id(udev, &input_dev->id); -+ -+ input_dev->dev.parent = &intf->dev; -+ -+ err = dwav_usb_mt_init(dwav_usb_mt, (void *)input_dev); -+ if (err) -+ goto err_free_urb; -+ -+ usb_set_intfdata(intf, dwav_usb_mt); -+ -+ dev_info(&intf->dev, "%s\n", DEV_INFO[dwav_usb_mt->dev_id].name); -+ -+ return 0; -+ -+err_free_urb: -+ usb_free_urb(dwav_usb_mt->irq); -+ -+err_free_buffers: -+ dwav_usb_mt_free_buffers(udev, dwav_usb_mt); -+ -+err_free_mem: -+ if (input_dev) -+ input_free_device(input_dev); -+ kfree(dwav_usb_mt); -+ -+ return err; -+} -+ -+/*-------------------------------------------------------------------------*/ -+static void dwav_usb_mt_disconnect(struct usb_interface *intf) -+{ -+ struct dwav_usb_mt *dwav_usb_mt = usb_get_intfdata(intf); -+ -+ if (!dwav_usb_mt) -+ return; -+ -+ dev_dbg(&intf->dev, -+ "%s - dwav_usb_mt is initialized, cleaning up\n", -+ __func__); -+ -+ usb_set_intfdata(intf, NULL); -+ -+ /* this will stop IO via close */ -+ input_unregister_device(dwav_usb_mt->input); -+ -+ usb_free_urb(dwav_usb_mt->irq); -+ -+ dwav_usb_mt_free_buffers(interface_to_usbdev(intf), dwav_usb_mt); -+ -+ kfree(dwav_usb_mt); -+} -+ -+/*-------------------------------------------------------------------------*/ -+MODULE_DEVICE_TABLE(usb, dwav_usb_mt_devices); -+ -+static struct usb_driver dwav_usb_mt_driver = { -+ .name = "dwav_usb_mt", -+ .probe = dwav_usb_mt_probe, -+ .disconnect = dwav_usb_mt_disconnect, -+ .suspend = dwav_usb_mt_suspend, -+ .resume = dwav_usb_mt_resume, -+ .reset_resume = dwav_usb_mt_reset_resume, -+ .id_table = dwav_usb_mt_devices, -+ .supports_autosuspend = 1, -+}; -+ -+module_usb_driver(dwav_usb_mt_driver); -+ -+/*-------------------------------------------------------------------------*/ -+MODULE_AUTHOR("Hardkernel Co.,Ltd"); -+MODULE_DESCRIPTION("D-WAV USB(HID) MultiTouch Driver"); -+MODULE_LICENSE("GPL"); -+ -+MODULE_ALIAS("dwav_usb_mt"); -+/*-------------------------------------------------------------------------*/ -diff -urN a/drivers/input/touchscreen/sx865x.c b/drivers/input/touchscreen/sx865x.c ---- a/drivers/input/touchscreen/sx865x.c 1970-01-01 01:00:00.000000000 +0100 -+++ b/drivers/input/touchscreen/sx865x.c 2018-05-06 10:03:40.553940699 +0200 -@@ -0,0 +1,584 @@ -+/* -+ * drivers/input/touchscreen/sx865x.c -+ * -+ * Copyright (c) 2013 U-MoBo Srl -+ * Pierluigi Passaro -+ * -+ * Using code from: -+ * - sx8650.c -+ * Copyright (c) 2009 Wayne Roberts -+ * - tsc2007.c -+ * Copyright (c) 2008 Kwangwoo Lee -+ * - ads7846.c -+ * Copyright (c) 2005 David Brownell -+ * Copyright (c) 2006 Nokia Corporation -+ * - corgi_ts.c -+ * Copyright (C) 2004-2005 Richard Purdie -+ * - omap_ts.[hc], ads7846.h, ts_osk.c -+ * Copyright (C) 2002 MontaVista Software -+ * Copyright (C) 2004 Texas Instruments -+ * Copyright (C) 2005 Dirk Behme -+ * -+ * 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. -+ */ -+ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+ -+#include -+#include -+ -+#define AMLGPIO_IRQ_BASE 96 -+ -+#endif -+ -+/* timeout expires after pen is lifted, no more PENIRQs comming */ -+/* adjust with POWDLY setting */ -+#define TS_TIMEOUT (8 * 1000000) -+ -+/* analog channels */ -+#define CH_X 0 -+#define CH_Y 1 -+#define CH_Z1 2 -+#define CH_Z2 3 -+#define CH_AUX 4 -+#define CH_RX 5 -+#define CH_RY 6 -+#define CH_SEQ 7 -+ -+/* commands */ -+#define SX865X_WRITE_REGISTER 0x00 -+#define SX865X_READ_REGISTER 0x40 -+#define SX865X_SELECT_CH(ch) (0x80 | ch) -+#define SX865X_CONVERT_CH(ch) (0x90 | ch) -+#define SX865X_POWDWN 0xb0 /* power down, ignore pen */ -+#define SX865X_PENDET 0xc0 /* " " with pen sensitivity */ -+#define SX865X_PENTRG 0xe0 /* " " " " and sample channels */ -+ -+/* register addresses */ -+#define I2C_REG_CTRL0 0x00 -+#define I2C_REG_CTRL1 0x01 -+#define I2C_REG_CTRL2 0x02 -+#define I2C_REG_CTRL3 0x03 -+#define I2C_REG_CHANMASK 0x04 -+#define I2C_REG_STAT 0x05 -+#define I2C_REG_SOFTRESET 0x1f -+ -+#define I2C_EXTENDED_REG_STAT 0x24 -+#define I2C_EXTENDED_REG_SOFTRESET 0x3f -+ -+#define SOFTRESET_VALUE 0xde -+ -+/* bits for I2C_REG_STAT */ -+/* I2C_REG_STAT: end of conversion flag */ -+#define STATUS_CONVIRQ 0x80 -+/* I2C_REG_STAT: pen detected */ -+#define STATUS_PENIRQ 0x40 -+ -+/* bits for I2C_EXTENDED_REG_STAT */ -+/* I2C_EXTENDED_REG_STAT: end of conversion flag */ -+#define EXTENDED_STATUS_CONVIRQ 0x08 -+/* I2C_EXTENDED_REG_STAT: pen detected */ -+#define EXTENDED_STATUS_PENIRQ 0x04 -+ -+/* sx865x bits for RegCtrl1 */ -+#define CONDIRQ 0x20 -+/* no averaging */ -+#define FILT_NONE 0x00 -+/* 3 sample averaging */ -+#define FILT_3SA 0x01 -+/* 5 sample averaging */ -+#define FILT_5SA 0x02 -+/* 7 samples, sort, then average of 3 middle samples */ -+#define FILT_7SA 0x03 -+ -+/* bits for register 2, I2CRegChanMsk */ -+#define CONV_X 0x80 -+#define CONV_Y 0x40 -+#define CONV_Z1 0x20 -+#define CONV_Z2 0x10 -+#define CONV_AUX 0x08 -+#define CONV_RX 0x04 -+#define CONV_RY 0x02 -+ -+/* power delay: lower nibble of CTRL0 register */ -+#define POWDLY_IMMEDIATE 0x00 -+#define POWDLY_1_1US 0x01 -+#define POWDLY_2_2US 0x02 -+#define POWDLY_4_4US 0x03 -+#define POWDLY_8_9US 0x04 -+#define POWDLY_17_8US 0x05 -+#define POWDLY_35_5US 0x06 -+#define POWDLY_71US 0x07 -+#define POWDLY_140US 0x08 -+#define POWDLY_280US 0x09 -+#define POWDLY_570US 0x0a -+#define POWDLY_1_1MS 0x0b -+#define POWDLY_2_3MS 0x0c -+#define POWDLY_4_6MS 0x0d -+#define POWDLY_9MS 0x0e -+#define POWDLY_18MS 0x0f -+ -+#define MAX_12BIT ((1 << 12) - 1) -+ -+/* when changing the channel mask, also change the read length appropriately */ -+#define CHAN_MASK (CONV_X | CONV_Y | CONV_Z1 | CONV_RX | CONV_RY) -+#define NUM_CHANNELS_SEQ 5 -+#define CHAN_READ_LENGTH (NUM_CHANNELS_SEQ * 2) -+ -+#define SX_MULTITOUCH 0x01 -+#define SX_PROXIMITY_SENSING 0x02 -+#define SX_HAPTICS_GENERIC 0x04 -+#define SX_HAPTICS_IMMERSION 0x08 -+#define SX_EXTENDED_REGS (SX_PROXIMITY_SENSING | SX_HAPTICS_GENERIC | SX_HAPTICS_IMMERSION) -+ -+#define SX865X_UP_SCANTIME_MS (100) -+#define SX865X_DOWN_SCANTIME_MS (20) -+ -+struct ts_event { -+ u16 x, y; -+ u16 z1; -+ u16 rx, ry; -+}; -+ -+struct sx865x { -+ struct input_dev *input; -+ struct ts_event tc; -+ -+ struct i2c_client *client; -+ -+ u32 invert_x; -+ u32 invert_y; -+ u32 swap_xy; -+ u32 gpio_pendown; -+ u32 gpio_reset; -+ -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+ int irq_bank; -+#endif -+ unsigned pendown; -+ int irq; -+}; -+ -+static struct i2c_device_id sx865x_idtable[] = { -+ { "sx8650", 0 }, -+ { } -+}; -+ -+MODULE_DEVICE_TABLE(i2c, sx865x_idtable); -+ -+static const struct of_device_id sx865x_of_match[] = { -+ { .compatible = "semtech,sx8650", .data = (void *)0 }, -+ {} -+}; -+ -+MODULE_DEVICE_TABLE(of, sx865x_of_match); -+ -+static void sx865x_send_event(struct sx865x *ts) -+{ -+ u32 rt; -+ u16 x, y, z1; -+ -+ x = ts->tc.x; -+ y = ts->tc.y; -+ z1 = ts->tc.z1; -+ -+ /* range filtering */ -+ if (y == MAX_12BIT) -+ y = 0; -+ -+ /* compute touch pressure resistance */ -+ if (likely(y && z1)) -+ rt = z1; -+ else -+ rt = 0; -+ -+ /* Sample found inconsistent by debouncing or pressure is beyond -+ * the maximum. Don't report it to user space, repeat at least -+ * once more the measurement -+ */ -+ if (rt > MAX_12BIT) { -+ dev_dbg(&ts->client->dev, "ignored pressure %d\n", rt); -+ return; -+ } -+ -+ /* NOTE: We can't rely on the pressure to determine the pen down -+ * state, even this controller has a pressure sensor. The pressure -+ * value can fluctuate for quite a while after lifting the pen and -+ * in some cases may not even settle at the expected value. -+ * -+ * The only safe way to check for the pen up condition is in the -+ * timer by reading the pen signal state (it's a GPIO _and_ IRQ). -+ */ -+ if (rt) { -+ struct input_dev *input = ts->input; -+ -+ if (ts->invert_x) x = (~x) & MAX_12BIT; -+ -+ if (ts->invert_y) y = (~y) & MAX_12BIT; -+ -+ if (ts->swap_xy) swap(x, y); -+ -+ if (!ts->pendown) { -+ dev_dbg(&ts->client->dev, "DOWN\n"); -+ ts->pendown = 1; -+ input_report_key(input, BTN_TOUCH, 1); -+ } -+ -+ input_report_abs(input, ABS_X, x); -+ input_report_abs(input, ABS_Y, y); -+ input_report_abs(input, ABS_PRESSURE, rt); -+ input_sync(input); -+ -+ dev_dbg(&ts->client->dev, "point(%4d,%4d), pressure (%4u)\n", -+ x, y, rt); -+ } -+} -+ -+static int sx865x_read_values(struct sx865x *ts) -+{ -+ s32 data; -+ u16 vals[NUM_CHANNELS_SEQ+1]; /* +1 for last dummy read */ -+ int length; -+ int i; -+ -+ memset(&(ts->tc), 0, sizeof(ts->tc)); -+ /* The protocol and raw data format from i2c interface: -+ * S Addr R A [DataLow] A [DataHigh] A (repeat) NA P -+ * Where DataLow has (channel | [D11-D8]), DataHigh has [D7-D0]. -+ */ -+ length = i2c_master_recv(ts->client, (char *)vals, CHAN_READ_LENGTH); -+ -+ if (likely(length == CHAN_READ_LENGTH)) { -+ length >>= 1; -+ for (i = 0; i < length; i++) { -+ u16 ch; -+ data = swab16(vals[i]); -+ if (unlikely(data & 0x8000)) { -+ dev_dbg(&ts->client->dev, -+ "hibit @ %d [0x%04x]\n", i, data); -+ continue; -+ } -+ ch = data >> 12; -+ if (ch == CH_X) { -+ ts->tc.x = data & 0xfff; -+ } else if (ch == CH_Y) { -+ ts->tc.y = data & 0xfff; -+ } else if (ch == CH_Z1) { -+ ts->tc.z1 = data & 0xfff; -+ } else if (ch == CH_RX) { -+ ts->tc.rx = data & 0xfff; -+ } else if (ch == CH_RY) { -+ ts->tc.ry = data & 0xfff; -+ } else { -+ dev_err(&ts->client->dev, "? CH%d %x\n", -+ ch, data & 0xfff); -+ } -+ } -+ } else { -+ dev_err(&ts->client->dev, "%d = recv()\n", length); -+ } -+ -+ dev_dbg(&ts->client->dev, "X:%03x Y:%03x Z1:%03x RX:%03x RY:%03x\n", -+ ts->tc.x, ts->tc.y, ts->tc.z1, ts->tc.rx, ts->tc.ry); -+ -+ return !ts->tc.z1; /* return 0 only if pressure not 0 */ -+} -+ -+static void sx865x_pen_up(struct sx865x *ts) -+{ -+ struct input_dev *input = ts->input; -+ -+ /* This timer expires after PENIRQs havent been coming in for some time. -+ * It means that the pen is now UP. */ -+ input_report_key(input, BTN_TOUCH, 0); -+ input_report_abs(input, ABS_PRESSURE, 0); -+ input_sync(input); -+ -+ ts->pendown = 0; -+ dev_dbg(&ts->client->dev, "UP\n"); -+} -+ -+static int sx865x_data_available(struct sx865x *ts) -+{ -+ u8 status; -+ -+ status = i2c_smbus_read_byte_data(ts->client, -+ (SX865X_READ_REGISTER | I2C_REG_STAT)); -+ return status & STATUS_CONVIRQ; -+} -+ -+static int get_pendown_status(struct sx865x *ts) -+{ -+ return gpio_get_value(ts->gpio_pendown) ? 0 : 1; -+} -+ -+static irqreturn_t sx865x_hw_irq(int irq, void *handle) -+{ -+ struct sx865x *ts = handle; -+ -+ return get_pendown_status(ts) ? IRQ_WAKE_THREAD : IRQ_HANDLED; -+} -+ -+static irqreturn_t sx865x_irq(int irq, void *handle) -+{ -+ struct sx865x *ts = handle; -+ -+ while (sx865x_data_available(ts)) { -+ /* valid data was read in */ -+ if (likely(sx865x_read_values(ts) == 0)) -+ sx865x_send_event(ts); -+ else -+ dev_dbg(&ts->client->dev, "data error!\n"); -+ -+ msleep(SX865X_DOWN_SCANTIME_MS); -+ } -+ -+ if (ts->pendown) -+ sx865x_pen_up(ts); -+ -+ return IRQ_HANDLED; -+} -+ -+static void sx865x_hw_reset(struct sx865x *ts) -+{ -+ gpio_direction_output(ts->gpio_reset, 0); -+ udelay(1000); -+ gpio_direction_output(ts->gpio_reset, 1); -+ udelay(1000); -+} -+ -+static int sx865x_dt_probe(struct i2c_client *client, struct sx865x *ts) -+{ -+ struct device_node *node = client->dev.of_node; -+ const struct of_device_id *match; -+ -+ if (!node) { -+ dev_err(&client->dev, -+ "Device dost not have associated DT data\n"); -+ return -EINVAL; -+ } -+ -+ match = of_match_device(sx865x_of_match, &client->dev); -+ if (!match) { -+ dev_err(&client->dev, -+ "Unknown device model\n"); -+ return -EINVAL; -+ } -+ -+ of_property_read_u32(node, "swap-xy", &ts->swap_xy); -+ of_property_read_u32(node, "invert-x", &ts->invert_x); -+ of_property_read_u32(node, "invert-y", &ts->invert_y); -+ -+ ts->gpio_pendown = of_get_named_gpio(node, "gpio-pendown", 0); -+ ts->gpio_reset = of_get_named_gpio(node, "gpio-reset", 0); -+ -+ if (gpio_request(ts->gpio_pendown, "ts-pendown")) -+ dev_err(&client->dev, -+ "gpio request fail (%d)!\n", ts->gpio_pendown); -+ else -+ gpio_direction_input(ts->gpio_pendown); -+ -+ if (gpio_request(ts->gpio_reset, "ts-reset")) -+ dev_err(&client->dev, -+ "gpio request fail (%d)!\n", ts->gpio_reset); -+ else -+ sx865x_hw_reset(ts); -+ -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+ /* irq setup */ -+ ts->irq_bank = meson_fix_irqbank(ts->irq_bank); -+ if (ts->irq_bank < 0) { -+ dev_err(&client->dev, -+ "Could not find irq bank!\n"); -+ return -EINVAL; -+ } -+ -+ { -+ int ret; -+ /* AMLogic gpio irq setup */ -+ ret = gpio_for_irq(ts->gpio_pendown, -+ AML_GPIO_IRQ(ts->irq_bank, FILTER_NUM7, GPIO_IRQ_FALLING)); -+ -+ if (ret) { -+ dev_err(&client->dev, -+ "AML_GPIO_IRQ setup fail!\n"); -+ return -EINVAL; -+ } -+ /* Amlogic gpio based irq setup */ -+ ts->irq = AMLGPIO_IRQ_BASE + ts->irq_bank; -+ } -+#else -+ ts->irq = gpio_to_irq(ts->gpio_pendown); -+ if (ts->irq < 0) -+ return -EINVAL; -+#endif -+ -+ /* platform data info display */ -+ dev_info(&client->dev, "swap_xy (%d)\n", ts->swap_xy); -+ dev_info(&client->dev, "invert_x (%d)\n", ts->invert_x); -+ dev_info(&client->dev, "invert_y (%d)\n", ts->invert_y); -+ dev_info(&client->dev, "gpio pendown (%d)\n", ts->gpio_pendown); -+ dev_info(&client->dev, "gpio reset (%d)\n", ts->gpio_reset); -+ dev_info(&client->dev, "gpio irq (%d)\n", ts->irq); -+ -+ return 0; -+} -+ -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+static void sx865x_irq_free(struct i2c_client *client, struct sx865x *ts) -+{ -+ int irq_banks[2]; -+ -+ meson_free_irq(gpio_to_irq(ts->gpio_pendown), &irq_banks[0]); -+ -+ /* rising irq bank */ -+ if (irq_banks[0] != -1) -+ free_irq(irq_banks[0] + AMLGPIO_IRQ_BASE, ts); -+ -+ /* falling irq bank */ -+ if (irq_banks[1] != -1) -+ free_irq(irq_banks[1] + AMLGPIO_IRQ_BASE, ts); -+} -+#endif -+ -+static int sx865x_probe(struct i2c_client *client, -+ const struct i2c_device_id *id) -+{ -+ struct sx865x *ts; -+ struct input_dev *input_dev; -+ int err = 0; -+ -+ dev_info(&client->dev, "sx865x_probe()\n"); -+ -+ if (!i2c_check_functionality(client->adapter, -+ I2C_FUNC_SMBUS_READ_WORD_DATA)) -+ return -EIO; -+ -+ ts = devm_kzalloc(&client->dev, sizeof(struct sx865x), GFP_KERNEL); -+ input_dev = devm_input_allocate_device(&client->dev); -+ if (!ts || !input_dev) -+ return -ENOMEM; -+ -+ if (sx865x_dt_probe(client, ts) != 0) -+ return -EIO; -+ -+ i2c_set_clientdata(client, ts); -+ -+ input_dev->name = "SX865X Touchscreen"; -+ input_dev->id.bustype = BUS_I2C; -+ input_dev->dev.parent = &client->dev; -+ input_set_drvdata(input_dev, ts); -+ -+ input_dev->evbit[0] = BIT_MASK(EV_KEY) | BIT_MASK(EV_ABS); -+ input_dev->keybit[BIT_WORD(BTN_TOUCH)] = BIT_MASK(BTN_TOUCH); -+ -+ input_set_abs_params(input_dev, ABS_X, 0, MAX_12BIT, 0, 0); -+ input_set_abs_params(input_dev, ABS_Y, 0, MAX_12BIT, 0, 0); -+ input_set_abs_params(input_dev, ABS_PRESSURE, 0, MAX_12BIT, 0, 0); -+ -+ /* soft reset: SX8650 fails to nak at the end, ignore return value */ -+ i2c_smbus_write_byte_data(client, I2C_REG_SOFTRESET, SOFTRESET_VALUE); -+ -+ /* set mask to convert X, Y, Z1, RX, RY for CH_SEQ */ -+ err = i2c_smbus_write_byte_data(client, I2C_REG_CHANMASK, CHAN_MASK); -+ if (err != 0) return -EIO; -+ -+ err = i2c_smbus_write_byte_data(client, I2C_REG_CTRL1, -+ CONDIRQ | FILT_7SA); -+ if (err != 0) return -EIO; -+ -+ /* set POWDLY settling time -- adjust TS_TIMEOUT accordingly */ -+ err = i2c_smbus_write_byte_data(client, I2C_REG_CTRL0, POWDLY_1_1MS); -+ if (err != 0) return -EIO; -+ -+ /* enter pen-trigger mode */ -+ err = i2c_smbus_write_byte(client, SX865X_PENTRG); -+ if (err != 0) return -EIO; -+ -+ err = request_threaded_irq(ts->irq, sx865x_hw_irq, sx865x_irq, -+ IRQF_ONESHOT, -+ client->dev.driver->name, ts); -+ -+ if (err < 0) { -+ dev_err(&client->dev, "irq %d busy?\n", ts->irq); -+ return -EIO; -+ } -+ -+ err = input_register_device(input_dev); -+ if (err) -+ goto err_free_irq; -+ -+ ts->client = client; -+ ts->input = input_dev; -+ -+ dev_info(&client->dev, "probe ok! registered with irq (%d)\n", ts->irq); -+ -+ return 0; -+ -+err_free_irq: -+ if (ts->gpio_pendown) -+ gpio_free(ts->gpio_pendown); -+ if (ts->gpio_reset) -+ gpio_free(ts->gpio_reset); -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+ sx865x_irq_free(client, ts); -+#else -+ if (ts->irq) -+ free_irq(ts->irq, ts); -+#endif -+ return err; -+} -+ -+static int sx865x_remove(struct i2c_client *client) -+{ -+ struct sx865x *ts = i2c_get_clientdata(client); -+ struct sx865x_platform_data *pdata; -+ -+ pdata = client->dev.platform_data; -+ -+ if (ts->gpio_pendown) -+ gpio_free(ts->gpio_pendown); -+ if (ts->gpio_reset) -+ gpio_free(ts->gpio_reset); -+#if defined(CONFIG_ARCH_MESON64_ODROIDC2) -+ sx865x_irq_free(client, ts); -+#else -+ if (ts->irq) -+ free_irq(ts->irq, ts); -+#endif -+ input_unregister_device(ts->input); -+ -+ return 0; -+} -+ -+static struct i2c_driver sx865x_driver = { -+ .driver = { -+ .owner = THIS_MODULE, -+ .name = "sx865x", -+ .of_match_table = of_match_ptr(sx865x_of_match), -+ }, -+ .id_table = sx865x_idtable, -+ .probe = sx865x_probe, -+ .remove = sx865x_remove, -+}; -+ -+module_i2c_driver(sx865x_driver); -+ -+MODULE_AUTHOR("Pierluigi Passaro "); -+MODULE_DESCRIPTION("SX865X TouchScreen Driver"); -+MODULE_LICENSE("GPL"); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/116_linux-4.14.y-drm-fb_helper-ump-ioctls.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/116_linux-4.14.y-drm-fb_helper-ump-ioctls.patch deleted file mode 100644 index 81a727526..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/116_linux-4.14.y-drm-fb_helper-ump-ioctls.patch +++ /dev/null @@ -1,151 +0,0 @@ -diff --git a/drivers/gpu/drm/drm_fb_helper.c b/drivers/gpu/drm/drm_fb_helper.c -index cab14f25..cafc60ea 100644 ---- a/drivers/gpu/drm/drm_fb_helper.c -+++ b/drivers/gpu/drm/drm_fb_helper.c -@@ -1544,6 +1544,14 @@ int drm_fb_helper_ioctl(struct fb_info *info, unsigned int cmd, - - ret = 0; - goto unlock; -+#if defined(CONFIG_UMP) -+ case GET_UMP_SECURE_ID_BUF1: -+ ret = drm_get_ump_secure_id(info, fb_helper, arg, 0); -+ goto unlock; -+ case GET_UMP_SECURE_ID_BUF2: -+ ret = drm_get_ump_secure_id(info, fb_helper, arg, 1); -+ goto unlock; -+#endif - default: - ret = -ENOTTY; - } -diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile -index 8ce07039b..fdf946be3 100644 ---- a/drivers/gpu/drm/Makefile -+++ b/drivers/gpu/drm/Makefile -@@ -44,6 +44,7 @@ drm_kms_helper-$(CONFIG_DRM_DP_AUX_CHARDEV) += drm_dp_aux_dev.o - - obj-$(CONFIG_DRM_KMS_HELPER) += drm_kms_helper.o - obj-$(CONFIG_DRM_DEBUG_MM_SELFTEST) += selftests/ -+obj-$(CONFIG_UMP) += drm_fb_ump.o - - CFLAGS_drm_trace_points.o := -I$(src) - -diff --git a/include/drm/drm_fb_helper.h b/include/drm/drm_fb_helper.h -index b069433e..95657b76 100644 ---- a/include/drm/drm_fb_helper.h -+++ b/include/drm/drm_fb_helper.h -@@ -36,6 +36,10 @@ struct drm_fb_helper; - #include - #include - -+#if defined(CONFIG_UMP) -+#include -+#endif -+ - enum mode_set_atomic { - LEAVE_ATOMIC_MODE_SET, - ENTER_ATOMIC_MODE_SET, -@@ -131,6 +135,8 @@ struct drm_fb_helper_connector { - struct drm_connector *connector; - }; - -+#define DRM_FB_UMP_COUNT 1 /* only enable one FB UMP layer */ -+ - /** - * struct drm_fb_helper - main structure to emulate fbdev on top of KMS - * @fb: Scanout framebuffer object -@@ -232,6 +238,9 @@ struct drm_fb_helper { - * See also: @deferred_setup - */ - int preferred_bpp; -+#if defined(CONFIG_UMP) -+ ump_dd_handle ump_wrapped_buffer[DRM_FB_UMP_COUNT][2]; -+#endif - }; - - /** -@@ -577,4 +586,11 @@ drm_fb_helper_remove_conflicting_framebuffers(struct apertures_struct *a, - #endif - } - -+#if defined(CONFIG_UMP) -+extern int (*drm_get_ump_secure_id) (struct fb_info *info, -+ struct drm_fb_helper *g_fbi, unsigned long arg, int buf); -+#define GET_UMP_SECURE_ID_BUF1 _IOWR('m', 311, unsigned int) -+#define GET_UMP_SECURE_ID_BUF2 _IOWR('m', 312, unsigned int) -+#endif -+ - #endif ---- /dev/null 2018-07-12 16:39:19.544000000 +0200 -+++ b/drivers/gpu/drm/drm_fb_ump.c 2018-07-22 22:20:45.166145058 +0200 -@@ -0,0 +1,71 @@ -+/* -+ * Copyright (C) 2016 Hardkernel Co. Ltd. -+ * -+ * 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, write to the Free Software -+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, -+ * MA 02111-1307 USA -+ */ -+ -+#include -+ -+#include -+#include -+#include -+#include -+#include -+ -+int (*drm_get_ump_secure_id) (struct fb_info *info, -+ struct drm_fb_helper *g_fbi, unsigned long arg, int buf); -+EXPORT_SYMBOL(drm_get_ump_secure_id); -+ -+static int _drm_get_ump_secure_id(struct fb_info *info, -+ struct drm_fb_helper *g_fbi, unsigned long arg, int buf) -+{ -+ u32 __user *psecureid = (u32 __user *) arg; -+ ump_secure_id secure_id; -+ -+ if (!g_fbi->ump_wrapped_buffer[info->node][buf]) { -+ ump_dd_physical_block ump_memory_description; -+ printk("ump: create disp: %d\n", buf); -+ -+ ump_memory_description.addr = info->fix.smem_start; -+ ump_memory_description.size = info->fix.smem_len; -+ g_fbi->ump_wrapped_buffer[info->node][buf] = -+ ump_dd_handle_create_from_phys_blocks( -+ &ump_memory_description, 1); -+ } -+ secure_id = ump_dd_secure_id_get( -+ g_fbi->ump_wrapped_buffer[info->node][buf]); -+ -+ return put_user((unsigned int)secure_id, psecureid); -+} -+ -+static int __init drm_ump_module_init(void) -+{ -+ int ret = 0; -+ drm_get_ump_secure_id = _drm_get_ump_secure_id; -+ return ret; -+} -+ -+static void __exit drm_ump_module_exit(void) -+{ -+ drm_get_ump_secure_id = NULL; -+} -+ -+module_init(drm_ump_module_init); -+module_exit(drm_ump_module_exit); -+ -+MODULE_AUTHOR("Mauro Ribeiro "); -+MODULE_DESCRIPTION("UMP Glue for DRM Framebuffer"); -+MODULE_LICENSE("GPL"); diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/117_arm64_increasing_DMA_block_memory_allocation_to_2048.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/117_arm64_increasing_DMA_block_memory_allocation_to_2048.patch deleted file mode 100644 index a848ed52e..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/117_arm64_increasing_DMA_block_memory_allocation_to_2048.patch +++ /dev/null @@ -1,13 +0,0 @@ -diff --git a/arch/arm64/mm/dma-mapping.c b/arch/arm64/mm/dma-mapping.c -index 614af886b7ef..632d32109755 100644 ---- a/arch/arm64/mm/dma-mapping.c -+++ b/arch/arm64/mm/dma-mapping.c -@@ -44,7 +44,7 @@ static pgprot_t __get_dma_pgprot(unsigned long attrs, pgprot_t prot, - - static struct gen_pool *atomic_pool __ro_after_init; - --#define DEFAULT_DMA_COHERENT_POOL_SIZE SZ_256K -+#define DEFAULT_DMA_COHERENT_POOL_SIZE SZ_2M - static size_t atomic_pool_size __initdata = DEFAULT_DMA_COHERENT_POOL_SIZE; - - static int __init early_coherent_pool(char *p) diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/118_arm64-set-default-target-to-Image.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/118_arm64-set-default-target-to-Image.patch deleted file mode 100644 index 51bf570c2..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/118_arm64-set-default-target-to-Image.patch +++ /dev/null @@ -1,13 +0,0 @@ -diff --git a/arch/arm64/Makefile b/arch/arm64/Makefile -index f839ecd9..cd276162 100644 ---- a/arch/arm64/Makefile -+++ b/arch/arm64/Makefile -@@ -103,7 +103,7 @@ core-$(CONFIG_EFI_STUB) += $(objtree)/drivers/firmware/efi/libstub/lib.a - - # Default target when executing plain make - boot := arch/arm64/boot --KBUILD_IMAGE := $(boot)/Image.gz -+KBUILD_IMAGE := $(boot)/Image - KBUILD_DTBS := dtbs - - all: Image.gz $(KBUILD_DTBS) diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/119_odroidc2-enable-scpi-dvfs.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/119_odroidc2-enable-scpi-dvfs.patch deleted file mode 100644 index dbe1e637f..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/119_odroidc2-enable-scpi-dvfs.patch +++ /dev/null @@ -1,14 +0,0 @@ -diff --git a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -index d147c853a..dbde670ba 100644 ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts -@@ -246,7 +246,8 @@ - }; - - &scpi_clocks { -- status = "disabled"; -+ /* Works only with new blobs that have limited DVFS table */ -+ status = "okay"; - }; - - /* SD */ diff --git a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/120_odroidc2-enable-scpi-cpu-thermal.patch b/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/120_odroidc2-enable-scpi-cpu-thermal.patch deleted file mode 100644 index e05b711aa..000000000 --- a/buildroot-external/board/hardkernel/odroid-c2/patches/linux/aside/120_odroidc2-enable-scpi-cpu-thermal.patch +++ /dev/null @@ -1,63 +0,0 @@ ---- a/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-04-29 05:46:55.636313674 +0200 -+++ b/arch/arm64/boot/dts/amlogic/meson-gxbb-odroidc2.dts 2018-04-29 00:07:14.412005049 +0200 -@@ -46,6 +46,7 @@ - - #include "meson-gxbb.dtsi" - #include -+#include - - / { - compatible = "hardkernel,odroid-c2", "amlogic,meson-gxbb"; -@@ -117,6 +118,41 @@ - 1800000 1>; - }; - -+ 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>; -+ hysteresis = <2000>; -+ type = "passive"; -+ }; -+ cpu_alert1: cpu-alert1 { -+ temperature = <85000>; -+ hysteresis = <2000>; -+ type = "passive"; -+ }; -+ cpu_crit: cpu_crit { -+ temperature = <95000>; -+ hysteresis = <2000>; -+ type = "critical"; -+ }; -+ }; -+ -+ cooling-maps { -+ map0 { -+ trip = <&cpu_alert1>; -+ cooling-device = -+ <&cpu0 THERMAL_NO_LIMIT THERMAL_NO_LIMIT>; -+ }; -+ }; -+ }; -+ }; -+ - vcc1v8: regulator-vcc1v8 { - compatible = "regulator-fixed"; - regulator-name = "VCC1V8"; -@@ -192,6 +228,10 @@ - status = "okay"; - }; - -+&cpu0 { -+ #cooling-cells = <2>; -+}; -+ - ðmac { - status = "okay"; - pinctrl-0 = <ð_rgmii_pins>; diff --git a/buildroot-external/configs/odroid_c2_defconfig b/buildroot-external/configs/odroid_c2_defconfig index 4805a6790..4dcd505d2 100644 --- a/buildroot-external/configs/odroid_c2_defconfig +++ b/buildroot-external/configs/odroid_c2_defconfig @@ -2,9 +2,8 @@ BR2_aarch64=y BR2_DL_DIR="/cache/dl" BR2_CCACHE=y BR2_CCACHE_DIR="/cache/cc" -BR2_GLOBAL_PATCH_DIR="$(BR2_EXTERNAL_HASSOS_PATH)/patches $(BR2_EXTERNAL_HASSOS_PATH)/board/hardkernel/odroid-c2/patches" +BR2_GLOBAL_PATCH_DIR="$(BR2_EXTERNAL_HASSOS_PATH)/patches" BR2_TOOLCHAIN_BUILDROOT_GLIBC=y -BR2_KERNEL_HEADERS_4_18=y BR2_GCC_VERSION_7_X=y BR2_TOOLCHAIN_BUILDROOT_CXX=y BR2_BINUTILS_ENABLE_LTO=y @@ -20,7 +19,7 @@ BR2_ROOTFS_POST_IMAGE_SCRIPT="$(BR2_EXTERNAL_HASSOS_PATH)/scripts/post-image.sh" BR2_ROOTFS_POST_SCRIPT_ARGS="$(BR2_EXTERNAL_HASSOS_PATH)/board/hardkernel/odroid-c2 $(BR2_EXTERNAL_HASSOS_PATH)/board/hardkernel/odroid-c2/hassos-hook.sh" BR2_LINUX_KERNEL=y BR2_LINUX_KERNEL_CUSTOM_VERSION=y -BR2_LINUX_KERNEL_CUSTOM_VERSION_VALUE="4.18.20" +BR2_LINUX_KERNEL_CUSTOM_VERSION_VALUE="4.19.15" BR2_LINUX_KERNEL_USE_CUSTOM_CONFIG=y BR2_LINUX_KERNEL_CUSTOM_CONFIG_FILE="$(BR2_EXTERNAL_HASSOS_PATH)/board/hardkernel/odroid-c2/kernel.config" BR2_LINUX_KERNEL_CONFIG_FRAGMENT_FILES="$(BR2_EXTERNAL_HASSOS_PATH)/kernel/hassos.config $(BR2_EXTERNAL_HASSOS_PATH)/kernel/docker.config $(BR2_EXTERNAL_HASSOS_PATH)/kernel/device-support.config"