From a8ad881b830fe00bd2036c281693849d8f45c91a Mon Sep 17 00:00:00 2001 From: Christian Lamparter Date: Fri, 24 Dec 2021 14:44:08 +0100 Subject: [PATCH 01/43] apm821xx: fix WD MyBook Live DUO USB-Port where to begin? the USB regulator settings were just a part of the issue. With them changed, according to the forum it still failed when a USB device was connected to the port with: dwc2 4bff80000.usbotg: dwc2_restore_global_registers: no global registers to restore dwc2 4bff80000.usbotg: dwc2_exit_partial_power_down: failed to restore registers dwc2 4bff80000.usbotg: exit partial_power_down failed dwc2 4bff80000.usbotg: HC died; cleaning up One clue was found upstream in commit cc10ce0c51b1 ("usb: dwc2: disable power_down on Amlogic devices") |Disable power_down by setting the parameter to |DWC2_POWER_DOWN_PARAM_NONE. This fixes a problem on various Amlogic |Meson SoCs where USB devices are only recognized when plugged in before |booting Linux. A hot-plugged USB device was not detected even though the |device got power (my USB thumb drive for example has an LED which lit |up). |[...] the same method proposed there worked with APM821xx's USB IP-Core. Link: https://forum.openwrt.org/t/wd-my-book-duo-usb/111926/2 Reported-by: thwe and takimata (openwrt forum) Fixes: b70d3557e05 ("apm821xx: clean up gpio-hogs") Signed-off-by: Christian Lamparter (cherry picked from commit 832b9cbd741cdb6cc8483b2cddfef6de000ec61d) --- target/linux/apm821xx/dts/wd-mybooklive.dts | 4 ++- .../100-dwc2-disable-powerdown.patch | 29 +++++++++++++++++++ 2 files changed, 32 insertions(+), 1 deletion(-) create mode 100644 target/linux/apm821xx/patches-5.4/100-dwc2-disable-powerdown.patch diff --git a/target/linux/apm821xx/dts/wd-mybooklive.dts b/target/linux/apm821xx/dts/wd-mybooklive.dts index 895d914d6b..a35b1683b7 100644 --- a/target/linux/apm821xx/dts/wd-mybooklive.dts +++ b/target/linux/apm821xx/dts/wd-mybooklive.dts @@ -119,9 +119,11 @@ usbpwr: usb-regulator { compatible = "regulator-fixed"; regulator-name = "Power USB Core"; - gpios = <&GPIO1 2 GPIO_ACTIVE_LOW>; + gpios = <&GPIO1 2 GPIO_ACTIVE_HIGH>; regulator-min-microvolt = <5000000>; regulator-max-microvolt = <5000000>; + regulator-boot-on; /* uboot sets this */ + enable-active-high; }; }; diff --git a/target/linux/apm821xx/patches-5.4/100-dwc2-disable-powerdown.patch b/target/linux/apm821xx/patches-5.4/100-dwc2-disable-powerdown.patch new file mode 100644 index 0000000000..ede7d732ff --- /dev/null +++ b/target/linux/apm821xx/patches-5.4/100-dwc2-disable-powerdown.patch @@ -0,0 +1,29 @@ +From 88ca61467a0897c79b1fbf8f5c30691b43b52613 Mon Sep 17 00:00:00 2001 +From: Christian Lamparter +Date: Sun, 26 Dec 2021 22:36:29 +0200 +Subject: [PATCH] dwc2: temporary force to be powered up all times + +the APM821xx's onchip dwc2 misbehaves with 5.4 and 5.10 +when a USB device gets connected. Instead of announcing +and setting up the USB devices it crashes and burns with: + +[ 22.023476] dwc2 4bff80000.usbotg: dwc2_restore_global_registers: no global registers to restore +[ 22.032245] dwc2 4bff80000.usbotg: dwc2_exit_partial_power_down: failed to restore registers +[ 22.040647] dwc2 4bff80000.usbotg: exit partial_power_down failed +[ 22.058765] dwc2 4bff80000.usbotg: HC died; cleaning up + +This is all seemingly fixed with dwc2 from a 5.16-rc6. + +Signed-off-by: Christian Lamparter +--- + +--- a/drivers/usb/dwc2/params.c ++++ b/drivers/usb/dwc2/params.c +@@ -137,6 +137,7 @@ static void dwc2_set_amcc_params(struct + struct dwc2_core_params *p = &hsotg->params; + + p->ahbcfg = GAHBCFG_HBSTLEN_INCR16 << GAHBCFG_HBSTLEN_SHIFT; ++ p->power_down = DWC2_POWER_DOWN_PARAM_NONE; + } + + static void dwc2_set_stm32f4x9_fsotg_params(struct dwc2_hsotg *hsotg) From 32c74552b2310531af593ee0f859a3935a3a7cbd Mon Sep 17 00:00:00 2001 From: Hauke Mehrtens Date: Mon, 27 Dec 2021 20:59:44 +0000 Subject: [PATCH 02/43] kernel: bump 5.4 to 5.4.168 All updated automatically. Compile-tested on: lantiq/xrx200, armvirt/64 Runtime-tested on: lantiq/xrx200, armvirt/64 Signed-off-by: Hauke Mehrtens --- include/kernel-version.mk | 4 ++-- ...i-add-firmware-loader-for-uPD720201-and-uPD72.patch | 10 +++++----- .../802-usb-xhci-force-msi-renesas-xhci.patch | 2 +- ...usb-xhci-Show-that-the-VIA-VL805-supports-LPM.patch | 2 +- ...plement-xhci_fixup_endpoint-for-interval-adju.patch | 2 +- ...d-quirk-for-host-controllers-that-don-t-updat.patch | 6 +++--- ...-Add-device-quirks-for-Freeway-Airmouse-T3-an.patch | 4 ++-- ...mapping-treat-dev-bus_dma_mask-as-a-DMA-limit.patch | 2 +- ...0993-xhci-quirks-add-link-TRB-quirk-for-VL805.patch | 4 ++-- ...xtract-napi-poll-functionality-to-__napi_poll.patch | 8 ++++---- ...mplement-threaded-able-napi-poll-loop-support.patch | 10 +++++----- ...-sysfs-attribute-to-control-napi-threaded-mod.patch | 4 ++-- ...-race-between-napi-kthread-mode-and-busy-poll.patch | 6 +++--- ...-fix-hangup-on-napi_disable-for-threaded-napi.patch | 4 ++-- ...e-allow-fast-GRO-for-skbs-with-Ethernet-heade.patch | 2 +- .../680-NET-skip-GRO-for-foreign-MAC-addresses.patch | 10 +++++----- .../820-libata-Assign-OF-node-to-the-SCSI-device.patch | 4 ++-- .../linux/generic/pending-5.4/834-ledtrig-libata.patch | 8 ++++---- ...1-arch-0008-arm-add-new-non-shareable-ioremap.patch | 2 +- ...80-4-usb-host-xhci-add-EH-SINGLE_STEP_SET_FEA.patch | 6 +++--- ...53-2-usb-host-xhci-do-not-return-error-status.patch | 2 +- ...794-1-usb-host-xhci-add-.bus_suspend-override.patch | 2 +- ...99-usb-host-xhci-do-warm-reset-for-link-state.patch | 2 +- ...ts-marvell-Drop-PCIe-I-O-ranges-from-CP11x-fi.patch | 2 +- target/linux/oxnas/patches-5.4/999-libata-hacks.patch | 4 ++-- 25 files changed, 56 insertions(+), 56 deletions(-) diff --git a/include/kernel-version.mk b/include/kernel-version.mk index ecb2857263..f8da54f606 100644 --- a/include/kernel-version.mk +++ b/include/kernel-version.mk @@ -6,9 +6,9 @@ ifdef CONFIG_TESTING_KERNEL KERNEL_PATCHVER:=$(KERNEL_TESTING_PATCHVER) endif -LINUX_VERSION-5.4 = .163 +LINUX_VERSION-5.4 = .168 -LINUX_KERNEL_HASH-5.4.163 = 6246fe1776d83039d71f74eb839f38ebdec23e1b37a7bf76f3bce13cbf0290be +LINUX_KERNEL_HASH-5.4.168 = ecb79ac4d465623560a6da31e3b0a0cf3fbb7c09e9ba88f06567436757191181 remove_uri_prefix=$(subst git://,,$(subst http://,,$(subst https://,,$(1)))) sanitize_uri=$(call qstrip,$(subst @,_,$(subst :,_,$(subst .,_,$(subst -,_,$(subst /,_,$(1))))))) diff --git a/target/linux/apm821xx/patches-5.4/801-usb-xhci-add-firmware-loader-for-uPD720201-and-uPD72.patch b/target/linux/apm821xx/patches-5.4/801-usb-xhci-add-firmware-loader-for-uPD720201-and-uPD72.patch index b85f62e680..8a4d3f21fa 100644 --- a/target/linux/apm821xx/patches-5.4/801-usb-xhci-add-firmware-loader-for-uPD720201-and-uPD72.patch +++ b/target/linux/apm821xx/patches-5.4/801-usb-xhci-add-firmware-loader-for-uPD720201-and-uPD72.patch @@ -48,7 +48,7 @@ Signed-off-by: Vinod Koul #include "xhci.h" #include "xhci-trace.h" -@@ -72,6 +74,44 @@ +@@ -74,6 +76,44 @@ #define PCI_DEVICE_ID_ASMEDIA_2142_XHCI 0x2142 #define PCI_DEVICE_ID_ASMEDIA_3242_XHCI 0x3242 @@ -93,7 +93,7 @@ Signed-off-by: Vinod Koul static const char hcd_name[] = "xhci_hcd"; static struct hc_driver __read_mostly xhci_pci_hc_driver; -@@ -327,6 +367,873 @@ static void xhci_pme_acpi_rtd3_enable(st +@@ -331,6 +371,873 @@ static void xhci_pme_acpi_rtd3_enable(st static void xhci_pme_acpi_rtd3_enable(struct pci_dev *dev) { } #endif /* CONFIG_ACPI */ @@ -967,7 +967,7 @@ Signed-off-by: Vinod Koul /* called during probe() after chip reset completes */ static int xhci_pci_setup(struct usb_hcd *hcd) { -@@ -368,6 +1275,27 @@ static int xhci_pci_probe(struct pci_dev +@@ -372,6 +1279,27 @@ static int xhci_pci_probe(struct pci_dev struct hc_driver *driver; struct usb_hcd *hcd; @@ -995,7 +995,7 @@ Signed-off-by: Vinod Koul driver = (struct hc_driver *)id->driver_data; /* Prevent runtime suspending between USB-2 and USB-3 initialization */ -@@ -429,6 +1357,16 @@ static void xhci_pci_remove(struct pci_d +@@ -433,6 +1361,16 @@ static void xhci_pci_remove(struct pci_d { struct xhci_hcd *xhci; @@ -1012,7 +1012,7 @@ Signed-off-by: Vinod Koul xhci = hcd_to_xhci(pci_get_drvdata(dev)); xhci->xhc_state |= XHCI_STATE_REMOVING; -@@ -568,6 +1506,11 @@ static int xhci_pci_resume(struct usb_hc +@@ -572,6 +1510,11 @@ static int xhci_pci_resume(struct usb_hc if (pdev->vendor == PCI_VENDOR_ID_INTEL) usb_enable_intel_xhci_ports(pdev); diff --git a/target/linux/apm821xx/patches-5.4/802-usb-xhci-force-msi-renesas-xhci.patch b/target/linux/apm821xx/patches-5.4/802-usb-xhci-force-msi-renesas-xhci.patch index 1fe38dc60a..0bca7ab4d5 100644 --- a/target/linux/apm821xx/patches-5.4/802-usb-xhci-force-msi-renesas-xhci.patch +++ b/target/linux/apm821xx/patches-5.4/802-usb-xhci-force-msi-renesas-xhci.patch @@ -13,7 +13,7 @@ produce a noisy warning. --- a/drivers/usb/host/xhci-pci.c +++ b/drivers/usb/host/xhci-pci.c -@@ -297,6 +297,7 @@ static void xhci_pci_quirks(struct devic +@@ -299,6 +299,7 @@ static void xhci_pci_quirks(struct devic pdev->device == 0x0015) { xhci->quirks |= XHCI_RESET_ON_RESUME; xhci->quirks |= XHCI_ZERO_64B_REGS; diff --git a/target/linux/bcm27xx/patches-5.4/950-0211-usb-xhci-Show-that-the-VIA-VL805-supports-LPM.patch b/target/linux/bcm27xx/patches-5.4/950-0211-usb-xhci-Show-that-the-VIA-VL805-supports-LPM.patch index dfc6193625..4d8f7b98fd 100644 --- a/target/linux/bcm27xx/patches-5.4/950-0211-usb-xhci-Show-that-the-VIA-VL805-supports-LPM.patch +++ b/target/linux/bcm27xx/patches-5.4/950-0211-usb-xhci-Show-that-the-VIA-VL805-supports-LPM.patch @@ -10,7 +10,7 @@ Signed-off-by: Phil Elwell --- a/drivers/usb/host/xhci-pci.c +++ b/drivers/usb/host/xhci-pci.c -@@ -266,6 +266,10 @@ static void xhci_pci_quirks(struct devic +@@ -268,6 +268,10 @@ static void xhci_pci_quirks(struct devic pdev->device == 0x3432) xhci->quirks |= XHCI_BROKEN_STREAMS; diff --git a/target/linux/bcm27xx/patches-5.4/950-0219-xhci-implement-xhci_fixup_endpoint-for-interval-adju.patch b/target/linux/bcm27xx/patches-5.4/950-0219-xhci-implement-xhci_fixup_endpoint-for-interval-adju.patch index b316ef8180..cb3c8aafee 100644 --- a/target/linux/bcm27xx/patches-5.4/950-0219-xhci-implement-xhci_fixup_endpoint-for-interval-adju.patch +++ b/target/linux/bcm27xx/patches-5.4/950-0219-xhci-implement-xhci_fixup_endpoint-for-interval-adju.patch @@ -119,7 +119,7 @@ Signed-off-by: Jonathan Bell * non-error returns are a promise to giveback() the urb later * we drop ownership so next owner (or urb unlink) can get it */ -@@ -5362,6 +5459,7 @@ static const struct hc_driver xhci_hc_dr +@@ -5366,6 +5463,7 @@ static const struct hc_driver xhci_hc_dr .endpoint_reset = xhci_endpoint_reset, .check_bandwidth = xhci_check_bandwidth, .reset_bandwidth = xhci_reset_bandwidth, diff --git a/target/linux/bcm27xx/patches-5.4/950-0264-xhci-add-quirk-for-host-controllers-that-don-t-updat.patch b/target/linux/bcm27xx/patches-5.4/950-0264-xhci-add-quirk-for-host-controllers-that-don-t-updat.patch index e5cff71905..908b906d3e 100644 --- a/target/linux/bcm27xx/patches-5.4/950-0264-xhci-add-quirk-for-host-controllers-that-don-t-updat.patch +++ b/target/linux/bcm27xx/patches-5.4/950-0264-xhci-add-quirk-for-host-controllers-that-don-t-updat.patch @@ -23,7 +23,7 @@ Signed-off-by: Jonathan Bell --- a/drivers/usb/host/xhci-pci.c +++ b/drivers/usb/host/xhci-pci.c -@@ -267,8 +267,10 @@ static void xhci_pci_quirks(struct devic +@@ -269,8 +269,10 @@ static void xhci_pci_quirks(struct devic xhci->quirks |= XHCI_BROKEN_STREAMS; if (pdev->vendor == PCI_VENDOR_ID_VIA && @@ -37,7 +37,7 @@ Signed-off-by: Jonathan Bell pdev->device == PCI_DEVICE_ID_ASMEDIA_1042_XHCI) --- a/drivers/usb/host/xhci-ring.c +++ b/drivers/usb/host/xhci-ring.c -@@ -556,7 +556,10 @@ void xhci_find_new_dequeue_state(struct +@@ -563,7 +563,10 @@ void xhci_find_new_dequeue_state(struct struct xhci_virt_ep *ep = &dev->eps[ep_index]; struct xhci_ring *ep_ring; struct xhci_segment *new_seg; @@ -48,7 +48,7 @@ Signed-off-by: Jonathan Bell dma_addr_t addr; u64 hw_dequeue; bool cycle_found = false; -@@ -594,7 +597,28 @@ void xhci_find_new_dequeue_state(struct +@@ -601,7 +604,28 @@ void xhci_find_new_dequeue_state(struct hw_dequeue = xhci_get_hw_deq(xhci, dev, ep_index, stream_id); new_seg = ep_ring->deq_seg; new_deq = ep_ring->dequeue; diff --git a/target/linux/bcm27xx/patches-5.4/950-0280-hid-usb-Add-device-quirks-for-Freeway-Airmouse-T3-an.patch b/target/linux/bcm27xx/patches-5.4/950-0280-hid-usb-Add-device-quirks-for-Freeway-Airmouse-T3-an.patch index c5e7d5e842..0794f66981 100644 --- a/target/linux/bcm27xx/patches-5.4/950-0280-hid-usb-Add-device-quirks-for-Freeway-Airmouse-T3-an.patch +++ b/target/linux/bcm27xx/patches-5.4/950-0280-hid-usb-Add-device-quirks-for-Freeway-Airmouse-T3-an.patch @@ -33,7 +33,7 @@ Signed-off-by: Jonathan Bell #define USB_VENDOR_ID_BELKIN 0x050d #define USB_DEVICE_ID_FLIP_KVM 0x3201 -@@ -1261,6 +1264,9 @@ +@@ -1263,6 +1266,9 @@ #define USB_VENDOR_ID_XAT 0x2505 #define USB_DEVICE_ID_XAT_CSR 0x0220 @@ -53,7 +53,7 @@ Signed-off-by: Jonathan Bell { HID_USB_DEVICE(USB_VENDOR_ID_CHICONY, USB_DEVICE_ID_CHICONY_MULTI_TOUCH), HID_QUIRK_MULTI_INPUT }, { HID_USB_DEVICE(USB_VENDOR_ID_CHICONY, USB_DEVICE_ID_CHICONY_PIXART_USB_OPTICAL_MOUSE), HID_QUIRK_ALWAYS_POLL }, { HID_USB_DEVICE(USB_VENDOR_ID_CHICONY, USB_DEVICE_ID_CHICONY_PIXART_USB_OPTICAL_MOUSE2), HID_QUIRK_ALWAYS_POLL }, -@@ -192,6 +193,7 @@ static const struct hid_device_id hid_qu +@@ -193,6 +194,7 @@ static const struct hid_device_id hid_qu { HID_USB_DEVICE(USB_VENDOR_ID_WISEGROUP_LTD2, USB_DEVICE_ID_SMARTJOY_DUAL_PLUS), HID_QUIRK_NOGET | HID_QUIRK_MULTI_INPUT }, { HID_USB_DEVICE(USB_VENDOR_ID_WISEGROUP, USB_DEVICE_ID_QUAD_USB_JOYPAD), HID_QUIRK_NOGET | HID_QUIRK_MULTI_INPUT }, { HID_USB_DEVICE(USB_VENDOR_ID_XIN_MO, USB_DEVICE_ID_XIN_MO_DUAL_ARCADE), HID_QUIRK_MULTI_INPUT }, diff --git a/target/linux/bcm27xx/patches-5.4/950-0445-dma-mapping-treat-dev-bus_dma_mask-as-a-DMA-limit.patch b/target/linux/bcm27xx/patches-5.4/950-0445-dma-mapping-treat-dev-bus_dma_mask-as-a-DMA-limit.patch index 711d06fd51..a428c1a5c2 100644 --- a/target/linux/bcm27xx/patches-5.4/950-0445-dma-mapping-treat-dev-bus_dma_mask-as-a-DMA-limit.patch +++ b/target/linux/bcm27xx/patches-5.4/950-0445-dma-mapping-treat-dev-bus_dma_mask-as-a-DMA-limit.patch @@ -187,7 +187,7 @@ Signed-off-by: Christoph Hellwig } --- a/drivers/ata/ahci.c +++ b/drivers/ata/ahci.c -@@ -900,7 +900,7 @@ static int ahci_configure_dma_masks(stru +@@ -901,7 +901,7 @@ static int ahci_configure_dma_masks(stru * value, don't extend it here. This happens on STA2X11, for example. * * XXX: manipulating the DMA mask from platform code is completely diff --git a/target/linux/bcm27xx/patches-5.4/950-0993-xhci-quirks-add-link-TRB-quirk-for-VL805.patch b/target/linux/bcm27xx/patches-5.4/950-0993-xhci-quirks-add-link-TRB-quirk-for-VL805.patch index 639e9325d8..7632e3f703 100644 --- a/target/linux/bcm27xx/patches-5.4/950-0993-xhci-quirks-add-link-TRB-quirk-for-VL805.patch +++ b/target/linux/bcm27xx/patches-5.4/950-0993-xhci-quirks-add-link-TRB-quirk-for-VL805.patch @@ -22,7 +22,7 @@ Signed-off-by: Jonathan Bell --- a/drivers/usb/host/xhci-pci.c +++ b/drivers/usb/host/xhci-pci.c -@@ -270,6 +270,7 @@ static void xhci_pci_quirks(struct devic +@@ -272,6 +272,7 @@ static void xhci_pci_quirks(struct devic pdev->device == 0x3483) { xhci->quirks |= XHCI_LPM_SUPPORT; xhci->quirks |= XHCI_EP_CTX_BROKEN_DCS; @@ -32,7 +32,7 @@ Signed-off-by: Jonathan Bell if (pdev->vendor == PCI_VENDOR_ID_ASMEDIA && --- a/drivers/usb/host/xhci-ring.c +++ b/drivers/usb/host/xhci-ring.c -@@ -653,6 +653,16 @@ void xhci_find_new_dequeue_state(struct +@@ -660,6 +660,16 @@ void xhci_find_new_dequeue_state(struct } while (!cycle_found || !td_last_trb_found); diff --git a/target/linux/generic/backport-5.4/600-v5.12-net-extract-napi-poll-functionality-to-__napi_poll.patch b/target/linux/generic/backport-5.4/600-v5.12-net-extract-napi-poll-functionality-to-__napi_poll.patch index 961140aabb..35aeb96251 100644 --- a/target/linux/generic/backport-5.4/600-v5.12-net-extract-napi-poll-functionality-to-__napi_poll.patch +++ b/target/linux/generic/backport-5.4/600-v5.12-net-extract-napi-poll-functionality-to-__napi_poll.patch @@ -18,7 +18,7 @@ Signed-off-by: David S. Miller --- a/net/core/dev.c +++ b/net/core/dev.c -@@ -6322,15 +6322,10 @@ void netif_napi_del(struct napi_struct * +@@ -6325,15 +6325,10 @@ void netif_napi_del(struct napi_struct * } EXPORT_SYMBOL(netif_napi_del); @@ -35,7 +35,7 @@ Signed-off-by: David S. Miller weight = n->weight; /* This NAPI_STATE_SCHED test is for avoiding a race -@@ -6348,7 +6343,7 @@ static int napi_poll(struct napi_struct +@@ -6351,7 +6346,7 @@ static int napi_poll(struct napi_struct WARN_ON_ONCE(work > weight); if (likely(work < weight)) @@ -44,7 +44,7 @@ Signed-off-by: David S. Miller /* Drivers must not modify the NAPI state if they * consume the entire weight. In such cases this code -@@ -6357,7 +6352,7 @@ static int napi_poll(struct napi_struct +@@ -6360,7 +6355,7 @@ static int napi_poll(struct napi_struct */ if (unlikely(napi_disable_pending(n))) { napi_complete(n); @@ -53,7 +53,7 @@ Signed-off-by: David S. Miller } if (n->gro_bitmask) { -@@ -6375,12 +6370,29 @@ static int napi_poll(struct napi_struct +@@ -6378,12 +6373,29 @@ static int napi_poll(struct napi_struct if (unlikely(!list_empty(&n->poll_list))) { pr_warn_once("%s: Budget exhausted after napi rescheduled\n", n->dev ? n->dev->name : "backlog"); diff --git a/target/linux/generic/backport-5.4/601-v5.12-net-implement-threaded-able-napi-poll-loop-support.patch b/target/linux/generic/backport-5.4/601-v5.12-net-implement-threaded-able-napi-poll-loop-support.patch index c9bd4abb53..0c548f331a 100644 --- a/target/linux/generic/backport-5.4/601-v5.12-net-implement-threaded-able-napi-poll-loop-support.patch +++ b/target/linux/generic/backport-5.4/601-v5.12-net-implement-threaded-able-napi-poll-loop-support.patch @@ -131,7 +131,7 @@ Signed-off-by: David S. Miller static int __dev_open(struct net_device *dev, struct netlink_ext_ack *extack) { const struct net_device_ops *ops = dev->netdev_ops; -@@ -3885,6 +3907,21 @@ int gro_normal_batch __read_mostly = 8; +@@ -3888,6 +3910,21 @@ int gro_normal_batch __read_mostly = 8; static inline void ____napi_schedule(struct softnet_data *sd, struct napi_struct *napi) { @@ -153,7 +153,7 @@ Signed-off-by: David S. Miller list_add_tail(&napi->poll_list, &sd->poll_list); __raise_softirq_irqoff(NET_RX_SOFTIRQ); } -@@ -6276,6 +6313,12 @@ void netif_napi_add(struct net_device *d +@@ -6279,6 +6316,12 @@ void netif_napi_add(struct net_device *d set_bit(NAPI_STATE_NPSVC, &napi->state); list_add_rcu(&napi->dev_list, &dev->napi_list); napi_hash_add(napi); @@ -166,7 +166,7 @@ Signed-off-by: David S. Miller } EXPORT_SYMBOL(netif_napi_add); -@@ -6292,9 +6335,28 @@ void napi_disable(struct napi_struct *n) +@@ -6295,9 +6338,28 @@ void napi_disable(struct napi_struct *n) hrtimer_cancel(&n->timer); clear_bit(NAPI_STATE_DISABLE, &n->state); @@ -195,7 +195,7 @@ Signed-off-by: David S. Miller static void flush_gro_hash(struct napi_struct *napi) { int i; -@@ -6319,6 +6381,11 @@ void netif_napi_del(struct napi_struct * +@@ -6322,6 +6384,11 @@ void netif_napi_del(struct napi_struct * flush_gro_hash(napi); napi->gro_bitmask = 0; @@ -207,7 +207,7 @@ Signed-off-by: David S. Miller } EXPORT_SYMBOL(netif_napi_del); -@@ -6398,6 +6465,51 @@ static int napi_poll(struct napi_struct +@@ -6401,6 +6468,51 @@ static int napi_poll(struct napi_struct return work; } diff --git a/target/linux/generic/backport-5.4/602-v5.12-net-add-sysfs-attribute-to-control-napi-threaded-mod.patch b/target/linux/generic/backport-5.4/602-v5.12-net-add-sysfs-attribute-to-control-napi-threaded-mod.patch index d8b932978c..bdc34a15ea 100644 --- a/target/linux/generic/backport-5.4/602-v5.12-net-add-sysfs-attribute-to-control-napi-threaded-mod.patch +++ b/target/linux/generic/backport-5.4/602-v5.12-net-add-sysfs-attribute-to-control-napi-threaded-mod.patch @@ -57,7 +57,7 @@ Signed-off-by: David S. Miller * @n: NAPI context --- a/net/core/dev.c +++ b/net/core/dev.c -@@ -3911,8 +3911,9 @@ static inline void ____napi_schedule(str +@@ -3914,8 +3914,9 @@ static inline void ____napi_schedule(str if (test_bit(NAPI_STATE_THREADED, &napi->state)) { /* Paired with smp_mb__before_atomic() in @@ -69,7 +69,7 @@ Signed-off-by: David S. Miller * wake_up_process() when it's not NULL. */ thread = READ_ONCE(napi->thread); -@@ -6290,6 +6291,49 @@ static void init_gro_hash(struct napi_st +@@ -6293,6 +6294,49 @@ static void init_gro_hash(struct napi_st napi->gro_bitmask = 0; } diff --git a/target/linux/generic/backport-5.4/603-v5.12-net-fix-race-between-napi-kthread-mode-and-busy-poll.patch b/target/linux/generic/backport-5.4/603-v5.12-net-fix-race-between-napi-kthread-mode-and-busy-poll.patch index 19c5a53a27..764f33e3fc 100644 --- a/target/linux/generic/backport-5.4/603-v5.12-net-fix-race-between-napi-kthread-mode-and-busy-poll.patch +++ b/target/linux/generic/backport-5.4/603-v5.12-net-fix-race-between-napi-kthread-mode-and-busy-poll.patch @@ -45,7 +45,7 @@ Cc: Hannes Frederic Sowa enum gro_result { --- a/net/core/dev.c +++ b/net/core/dev.c -@@ -3918,6 +3918,8 @@ static inline void ____napi_schedule(str +@@ -3921,6 +3921,8 @@ static inline void ____napi_schedule(str */ thread = READ_ONCE(napi->thread); if (thread) { @@ -54,7 +54,7 @@ Cc: Hannes Frederic Sowa wake_up_process(thread); return; } -@@ -6078,7 +6080,8 @@ bool napi_complete_done(struct napi_stru +@@ -6081,7 +6083,8 @@ bool napi_complete_done(struct napi_stru WARN_ON_ONCE(!(val & NAPIF_STATE_SCHED)); @@ -64,7 +64,7 @@ Cc: Hannes Frederic Sowa /* If STATE_MISSED was set, leave STATE_SCHED set, * because we will call napi->poll() one more time. -@@ -6511,16 +6514,25 @@ static int napi_poll(struct napi_struct +@@ -6514,16 +6517,25 @@ static int napi_poll(struct napi_struct static int napi_thread_wait(struct napi_struct *napi) { diff --git a/target/linux/generic/backport-5.4/604-v5.12-net-fix-hangup-on-napi_disable-for-threaded-napi.patch b/target/linux/generic/backport-5.4/604-v5.12-net-fix-hangup-on-napi_disable-for-threaded-napi.patch index 108cf809f8..5c48fdf5c1 100644 --- a/target/linux/generic/backport-5.4/604-v5.12-net-fix-hangup-on-napi_disable-for-threaded-napi.patch +++ b/target/linux/generic/backport-5.4/604-v5.12-net-fix-hangup-on-napi_disable-for-threaded-napi.patch @@ -34,7 +34,7 @@ Signed-off-by: Jakub Kicinski --- a/net/core/dev.c +++ b/net/core/dev.c -@@ -6518,7 +6518,7 @@ static int napi_thread_wait(struct napi_ +@@ -6521,7 +6521,7 @@ static int napi_thread_wait(struct napi_ set_current_state(TASK_INTERRUPTIBLE); @@ -43,7 +43,7 @@ Signed-off-by: Jakub Kicinski /* Testing SCHED_THREADED bit here to make sure the current * kthread owns this napi and could poll on this napi. * Testing SCHED bit is not enough because SCHED bit might be -@@ -6536,6 +6536,7 @@ static int napi_thread_wait(struct napi_ +@@ -6539,6 +6539,7 @@ static int napi_thread_wait(struct napi_ set_current_state(TASK_INTERRUPTIBLE); } __set_current_state(TASK_RUNNING); diff --git a/target/linux/generic/backport-5.4/700-v5.5-net-core-allow-fast-GRO-for-skbs-with-Ethernet-heade.patch b/target/linux/generic/backport-5.4/700-v5.5-net-core-allow-fast-GRO-for-skbs-with-Ethernet-heade.patch index 34ad5a1f4e..24b76cdca4 100644 --- a/target/linux/generic/backport-5.4/700-v5.5-net-core-allow-fast-GRO-for-skbs-with-Ethernet-heade.patch +++ b/target/linux/generic/backport-5.4/700-v5.5-net-core-allow-fast-GRO-for-skbs-with-Ethernet-heade.patch @@ -66,7 +66,7 @@ Signed-off-by: David S. Miller --- a/net/core/dev.c +++ b/net/core/dev.c -@@ -5472,8 +5472,7 @@ static inline void skb_gro_reset_offset( +@@ -5475,8 +5475,7 @@ static inline void skb_gro_reset_offset( NAPI_GRO_CB(skb)->frag0 = NULL; NAPI_GRO_CB(skb)->frag0_len = 0; diff --git a/target/linux/generic/pending-5.4/680-NET-skip-GRO-for-foreign-MAC-addresses.patch b/target/linux/generic/pending-5.4/680-NET-skip-GRO-for-foreign-MAC-addresses.patch index 45f643b650..9795a99bb5 100644 --- a/target/linux/generic/pending-5.4/680-NET-skip-GRO-for-foreign-MAC-addresses.patch +++ b/target/linux/generic/pending-5.4/680-NET-skip-GRO-for-foreign-MAC-addresses.patch @@ -32,7 +32,7 @@ Signed-off-by: Felix Fietkau __u16 tc_index; /* traffic control index */ --- a/net/core/dev.c +++ b/net/core/dev.c -@@ -5538,6 +5538,9 @@ static enum gro_result dev_gro_receive(s +@@ -5541,6 +5541,9 @@ static enum gro_result dev_gro_receive(s int same_flow; int grow; @@ -42,7 +42,7 @@ Signed-off-by: Felix Fietkau if (netif_elide_gro(skb->dev)) goto normal; -@@ -7481,6 +7484,48 @@ static void __netdev_adjacent_dev_unlink +@@ -7484,6 +7487,48 @@ static void __netdev_adjacent_dev_unlink &upper_dev->adj_list.lower); } @@ -91,7 +91,7 @@ Signed-off-by: Felix Fietkau static int __netdev_upper_dev_link(struct net_device *dev, struct net_device *upper_dev, bool master, void *upper_priv, void *upper_info, -@@ -7531,6 +7576,7 @@ static int __netdev_upper_dev_link(struc +@@ -7534,6 +7579,7 @@ static int __netdev_upper_dev_link(struc if (ret) return ret; @@ -99,7 +99,7 @@ Signed-off-by: Felix Fietkau ret = call_netdevice_notifiers_info(NETDEV_CHANGEUPPER, &changeupper_info.info); ret = notifier_to_errno(ret); -@@ -7624,6 +7670,7 @@ void netdev_upper_dev_unlink(struct net_ +@@ -7627,6 +7673,7 @@ void netdev_upper_dev_unlink(struct net_ __netdev_adjacent_dev_unlink_neighbour(dev, upper_dev); @@ -107,7 +107,7 @@ Signed-off-by: Felix Fietkau call_netdevice_notifiers_info(NETDEV_CHANGEUPPER, &changeupper_info.info); -@@ -8354,6 +8401,7 @@ int dev_set_mac_address(struct net_devic +@@ -8357,6 +8404,7 @@ int dev_set_mac_address(struct net_devic if (err) return err; dev->addr_assign_type = NET_ADDR_SET; diff --git a/target/linux/generic/pending-5.4/820-libata-Assign-OF-node-to-the-SCSI-device.patch b/target/linux/generic/pending-5.4/820-libata-Assign-OF-node-to-the-SCSI-device.patch index bec9363fa1..c4cbaaa777 100644 --- a/target/linux/generic/pending-5.4/820-libata-Assign-OF-node-to-the-SCSI-device.patch +++ b/target/linux/generic/pending-5.4/820-libata-Assign-OF-node-to-the-SCSI-device.patch @@ -41,7 +41,7 @@ ChangeLog v1->v2: #include "libata.h" #include "libata-transport.h" -@@ -4579,6 +4580,34 @@ int ata_scsi_add_hosts(struct ata_host * +@@ -4590,6 +4591,34 @@ int ata_scsi_add_hosts(struct ata_host * return rc; } @@ -76,7 +76,7 @@ ChangeLog v1->v2: void ata_scsi_scan_host(struct ata_port *ap, int sync) { int tries = 5; -@@ -4604,6 +4633,7 @@ void ata_scsi_scan_host(struct ata_port +@@ -4615,6 +4644,7 @@ void ata_scsi_scan_host(struct ata_port NULL); if (!IS_ERR(sdev)) { dev->sdev = sdev; diff --git a/target/linux/generic/pending-5.4/834-ledtrig-libata.patch b/target/linux/generic/pending-5.4/834-ledtrig-libata.patch index f33ceec126..2c876ae55e 100644 --- a/target/linux/generic/pending-5.4/834-ledtrig-libata.patch +++ b/target/linux/generic/pending-5.4/834-ledtrig-libata.patch @@ -65,7 +65,7 @@ Signed-off-by: Daniel Golle /** * ata_build_rw_tf - Build ATA taskfile for given read/write request * @tf: Target ATA taskfile -@@ -5149,6 +5162,9 @@ struct ata_queued_cmd *ata_qc_new_init(s +@@ -5151,6 +5164,9 @@ struct ata_queued_cmd *ata_qc_new_init(s if (tag < 0) return NULL; } @@ -75,7 +75,7 @@ Signed-off-by: Daniel Golle qc = __ata_qc_from_tag(ap, tag); qc->tag = qc->hw_tag = tag; -@@ -6085,6 +6101,9 @@ struct ata_port *ata_port_alloc(struct a +@@ -6087,6 +6103,9 @@ struct ata_port *ata_port_alloc(struct a ap->stats.unhandled_irq = 1; ap->stats.idle_irq = 1; #endif @@ -85,7 +85,7 @@ Signed-off-by: Daniel Golle ata_sff_port_init(ap); return ap; -@@ -6120,6 +6139,12 @@ static void ata_host_release(struct kref +@@ -6122,6 +6141,12 @@ static void ata_host_release(struct kref kfree(ap->pmp_link); kfree(ap->slave_link); @@ -98,7 +98,7 @@ Signed-off-by: Daniel Golle kfree(ap); host->ports[i] = NULL; } -@@ -6583,7 +6608,23 @@ int ata_host_register(struct ata_host *h +@@ -6585,7 +6610,23 @@ int ata_host_register(struct ata_host *h host->ports[i]->print_id = atomic_inc_return(&ata_print_id); host->ports[i]->local_port_no = i + 1; } diff --git a/target/linux/layerscape/patches-5.4/301-arch-0008-arm-add-new-non-shareable-ioremap.patch b/target/linux/layerscape/patches-5.4/301-arch-0008-arm-add-new-non-shareable-ioremap.patch index 85a4478cd8..c09efca570 100644 --- a/target/linux/layerscape/patches-5.4/301-arch-0008-arm-add-new-non-shareable-ioremap.patch +++ b/target/linux/layerscape/patches-5.4/301-arch-0008-arm-add-new-non-shareable-ioremap.patch @@ -47,7 +47,7 @@ Signed-off-by: Roy Pledge MT_LOW_VECTORS, --- a/arch/arm/mm/ioremap.c +++ b/arch/arm/mm/ioremap.c -@@ -399,6 +399,13 @@ void __iomem *ioremap_wc(resource_size_t +@@ -401,6 +401,13 @@ void __iomem *ioremap_wc(resource_size_t } EXPORT_SYMBOL(ioremap_wc); diff --git a/target/linux/layerscape/patches-5.4/820-usb-0015-MLK-17380-4-usb-host-xhci-add-EH-SINGLE_STEP_SET_FEA.patch b/target/linux/layerscape/patches-5.4/820-usb-0015-MLK-17380-4-usb-host-xhci-add-EH-SINGLE_STEP_SET_FEA.patch index 9dd1cf5ff5..4f4381c9a5 100644 --- a/target/linux/layerscape/patches-5.4/820-usb-0015-MLK-17380-4-usb-host-xhci-add-EH-SINGLE_STEP_SET_FEA.patch +++ b/target/linux/layerscape/patches-5.4/820-usb-0015-MLK-17380-4-usb-host-xhci-add-EH-SINGLE_STEP_SET_FEA.patch @@ -24,7 +24,7 @@ Signed-off-by: Peter Chen --- a/drivers/usb/host/xhci-hub.c +++ b/drivers/usb/host/xhci-hub.c -@@ -1421,6 +1421,15 @@ int xhci_hub_control(struct usb_hcd *hcd +@@ -1422,6 +1422,15 @@ int xhci_hub_control(struct usb_hcd *hcd /* 4.19.6 Port Test Modes (USB2 Test Mode) */ if (hcd->speed != HCD_USB2) goto error; @@ -42,7 +42,7 @@ Signed-off-by: Peter Chen retval = xhci_enter_test_mode(xhci, test_mode, wIndex, --- a/drivers/usb/host/xhci-ring.c +++ b/drivers/usb/host/xhci-ring.c -@@ -3630,6 +3630,129 @@ int xhci_queue_ctrl_tx(struct xhci_hcd * +@@ -3636,6 +3636,129 @@ int xhci_queue_ctrl_tx(struct xhci_hcd * return 0; } @@ -174,7 +174,7 @@ Signed-off-by: Peter Chen * bursts that are required to move all packets in this TD. Only SuperSpeed --- a/drivers/usb/host/xhci.c +++ b/drivers/usb/host/xhci.c -@@ -5389,6 +5389,7 @@ static const struct hc_driver xhci_hc_dr +@@ -5393,6 +5393,7 @@ static const struct hc_driver xhci_hc_dr .disable_usb3_lpm_timeout = xhci_disable_usb3_lpm_timeout, .find_raw_port_number = xhci_find_raw_port_number, .clear_tt_buffer_complete = xhci_clear_tt_buffer_complete, diff --git a/target/linux/layerscape/patches-5.4/820-usb-0017-MLK-19153-2-usb-host-xhci-do-not-return-error-status.patch b/target/linux/layerscape/patches-5.4/820-usb-0017-MLK-19153-2-usb-host-xhci-do-not-return-error-status.patch index e5394cc6d8..effe5997cd 100644 --- a/target/linux/layerscape/patches-5.4/820-usb-0017-MLK-19153-2-usb-host-xhci-do-not-return-error-status.patch +++ b/target/linux/layerscape/patches-5.4/820-usb-0017-MLK-19153-2-usb-host-xhci-do-not-return-error-status.patch @@ -22,7 +22,7 @@ Signed-off-by: Peter Chen --- a/drivers/usb/host/xhci-ring.c +++ b/drivers/usb/host/xhci-ring.c -@@ -2097,12 +2097,9 @@ static int process_ctrl_td(struct xhci_h +@@ -2103,12 +2103,9 @@ static int process_ctrl_td(struct xhci_h switch (trb_comp_code) { case COMP_SUCCESS: diff --git a/target/linux/layerscape/patches-5.4/820-usb-0018-MLK-18794-1-usb-host-xhci-add-.bus_suspend-override.patch b/target/linux/layerscape/patches-5.4/820-usb-0018-MLK-18794-1-usb-host-xhci-add-.bus_suspend-override.patch index f808b5b556..5947563516 100644 --- a/target/linux/layerscape/patches-5.4/820-usb-0018-MLK-18794-1-usb-host-xhci-add-.bus_suspend-override.patch +++ b/target/linux/layerscape/patches-5.4/820-usb-0018-MLK-18794-1-usb-host-xhci-add-.bus_suspend-override.patch @@ -24,7 +24,7 @@ Signed-off-by: Peter Chen --- a/drivers/usb/host/xhci.c +++ b/drivers/usb/host/xhci.c -@@ -5410,6 +5410,8 @@ void xhci_init_driver(struct hc_driver * +@@ -5414,6 +5414,8 @@ void xhci_init_driver(struct hc_driver * drv->check_bandwidth = over->check_bandwidth; if (over->reset_bandwidth) drv->reset_bandwidth = over->reset_bandwidth; diff --git a/target/linux/layerscape/patches-5.4/820-usb-0021-MLK-22099-usb-host-xhci-do-warm-reset-for-link-state.patch b/target/linux/layerscape/patches-5.4/820-usb-0021-MLK-22099-usb-host-xhci-do-warm-reset-for-link-state.patch index 26c6c007fb..eb5dcb5595 100644 --- a/target/linux/layerscape/patches-5.4/820-usb-0021-MLK-22099-usb-host-xhci-do-warm-reset-for-link-state.patch +++ b/target/linux/layerscape/patches-5.4/820-usb-0021-MLK-22099-usb-host-xhci-do-warm-reset-for-link-state.patch @@ -16,7 +16,7 @@ Signed-off-by: Li Jun --- a/drivers/usb/host/xhci-hub.c +++ b/drivers/usb/host/xhci-hub.c -@@ -1739,7 +1739,8 @@ static bool xhci_port_missing_cas_quirk( +@@ -1740,7 +1740,8 @@ static bool xhci_port_missing_cas_quirk( return false; if (((portsc & PORT_PLS_MASK) != XDEV_POLLING) && diff --git a/target/linux/mvebu/patches-5.4/005-v5.5-arm64-dts-marvell-Drop-PCIe-I-O-ranges-from-CP11x-fi.patch b/target/linux/mvebu/patches-5.4/005-v5.5-arm64-dts-marvell-Drop-PCIe-I-O-ranges-from-CP11x-fi.patch index e06928d130..04942067f8 100644 --- a/target/linux/mvebu/patches-5.4/005-v5.5-arm64-dts-marvell-Drop-PCIe-I-O-ranges-from-CP11x-fi.patch +++ b/target/linux/mvebu/patches-5.4/005-v5.5-arm64-dts-marvell-Drop-PCIe-I-O-ranges-from-CP11x-fi.patch @@ -40,7 +40,7 @@ Signed-off-by: Gregory CLEMENT #undef CP11X_PCIE1_BASE --- a/arch/arm64/boot/dts/marvell/armada-8040-mcbin.dtsi +++ b/arch/arm64/boot/dts/marvell/armada-8040-mcbin.dtsi -@@ -179,8 +179,7 @@ +@@ -182,8 +182,7 @@ num-lanes = <4>; num-viewport = <8>; reset-gpios = <&cp0_gpio2 20 GPIO_ACTIVE_LOW>; diff --git a/target/linux/oxnas/patches-5.4/999-libata-hacks.patch b/target/linux/oxnas/patches-5.4/999-libata-hacks.patch index e536a4c1bc..cac7f48f43 100644 --- a/target/linux/oxnas/patches-5.4/999-libata-hacks.patch +++ b/target/linux/oxnas/patches-5.4/999-libata-hacks.patch @@ -15,7 +15,7 @@ /* initialize internal qc */ qc = __ata_qc_from_tag(ap, ATA_TAG_INTERNAL); -@@ -5156,6 +5164,9 @@ struct ata_queued_cmd *ata_qc_new_init(s +@@ -5158,6 +5166,9 @@ struct ata_queued_cmd *ata_qc_new_init(s if (unlikely(ap->pflags & ATA_PFLAG_FROZEN)) return NULL; @@ -25,7 +25,7 @@ /* libsas case */ if (ap->flags & ATA_FLAG_SAS_HOST) { tag = ata_sas_allocate_tag(ap); -@@ -5201,6 +5212,8 @@ void ata_qc_free(struct ata_queued_cmd * +@@ -5203,6 +5214,8 @@ void ata_qc_free(struct ata_queued_cmd * qc->tag = ATA_TAG_POISON; if (ap->flags & ATA_FLAG_SAS_HOST) ata_sas_free_tag(tag, ap); From 24e564d327943a32181db4568fff43cc18d93b13 Mon Sep 17 00:00:00 2001 From: Klaus Kudielka Date: Sat, 17 Jul 2021 19:32:57 +0200 Subject: [PATCH 03/43] mvebu: backport Turris Omnia DTS changes to 5.4 Kernel 5.4 receives a reduced set, just to make the SFP cage work. While we are at it, move the patches accepted upstream to the 0xx series. Reviewed-by: Noci Reviewed-by: Justin van Steijn Reviewed-by: Nico Rikken Reviewed-by: Julius Schwartzenberg Signed-off-by: Klaus Kudielka (cherry picked from commit 8138cb8737d1475e6e8d57393500f30384e75a82) --- ...s-omnia-enable-HW-buffer-management.patch} | 0 ...rris-omnia-add-comphy-handle-to-eth2.patch | 37 ++++++++ ...rris-omnia-describe-switch-interrupt.patch | 61 +++++++++++++ ...32-ARM-dts-turris-omnia-add-SFP-node.patch | 90 +++++++++++++++++++ ...te-ethernet-phy-node-and-handle-name.patch | 52 +++++++++++ ...mnia-fix-hardware-buffer-management.patch} | 12 ++- 6 files changed, 249 insertions(+), 3 deletions(-) rename target/linux/mvebu/patches-5.4/{317-ARM-dts-turris-omnia-enable-HW-buffer-management.patch => 029-ARM-dts-turris-omnia-enable-HW-buffer-management.patch} (100%) create mode 100644 target/linux/mvebu/patches-5.4/030-ARM-dts-turris-omnia-add-comphy-handle-to-eth2.patch create mode 100644 target/linux/mvebu/patches-5.4/031-ARM-dts-turris-omnia-describe-switch-interrupt.patch create mode 100644 target/linux/mvebu/patches-5.4/032-ARM-dts-turris-omnia-add-SFP-node.patch create mode 100644 target/linux/mvebu/patches-5.4/033-ARM-dts-turris-omnia-update-ethernet-phy-node-and-handle-name.patch rename target/linux/mvebu/patches-5.4/{318-ARM-dts-turris-omnia-fix-hardware-buffer-management.patch => 034-ARM-dts-turris-omnia-fix-hardware-buffer-management.patch} (67%) diff --git a/target/linux/mvebu/patches-5.4/317-ARM-dts-turris-omnia-enable-HW-buffer-management.patch b/target/linux/mvebu/patches-5.4/029-ARM-dts-turris-omnia-enable-HW-buffer-management.patch similarity index 100% rename from target/linux/mvebu/patches-5.4/317-ARM-dts-turris-omnia-enable-HW-buffer-management.patch rename to target/linux/mvebu/patches-5.4/029-ARM-dts-turris-omnia-enable-HW-buffer-management.patch diff --git a/target/linux/mvebu/patches-5.4/030-ARM-dts-turris-omnia-add-comphy-handle-to-eth2.patch b/target/linux/mvebu/patches-5.4/030-ARM-dts-turris-omnia-add-comphy-handle-to-eth2.patch new file mode 100644 index 0000000000..99ed07e13b --- /dev/null +++ b/target/linux/mvebu/patches-5.4/030-ARM-dts-turris-omnia-add-comphy-handle-to-eth2.patch @@ -0,0 +1,37 @@ +From 9ec25ef84832209a8326f9a71fe3ba14f4bcf301 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Marek=20Beh=C3=BAn?= +Date: Sun, 15 Nov 2020 14:59:18 +0100 +Subject: ARM: dts: turris-omnia: add comphy handle to eth2 +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +The eth2 controller on Turris Omnia is connected to SerDes. For SFP to +be able to switch between 1G and 2.5G modes the comphy link has to be +defined. + +Signed-off-by: Marek Behún +Fixes: f3a6a9f3704a ("ARM: dts: add description for Armada 38x ...") +Reviewed-by: Andrew Lunn +Reviewed-by: Andreas Färber +Cc: linux-arm-kernel@lists.infradead.org +Cc: Uwe Kleine-König +Cc: Jason Cooper +Cc: Gregory CLEMENT +Cc: Rob Herring +Cc: devicetree@vger.kernel.org +Signed-off-by: Gregory CLEMENT +--- + arch/arm/boot/dts/armada-385-turris-omnia.dts | 1 + + 1 file changed, 1 insertion(+) + +--- a/arch/arm/boot/dts/armada-385-turris-omnia.dts ++++ b/arch/arm/boot/dts/armada-385-turris-omnia.dts +@@ -129,6 +129,7 @@ + status = "okay"; + phy-mode = "sgmii"; + phy = <&phy1>; ++ phys = <&comphy5 2>; + buffer-manager = <&bm>; + bm,pool-long = <2>; + bm,pool-short = <3>; diff --git a/target/linux/mvebu/patches-5.4/031-ARM-dts-turris-omnia-describe-switch-interrupt.patch b/target/linux/mvebu/patches-5.4/031-ARM-dts-turris-omnia-describe-switch-interrupt.patch new file mode 100644 index 0000000000..4bbd80aac4 --- /dev/null +++ b/target/linux/mvebu/patches-5.4/031-ARM-dts-turris-omnia-describe-switch-interrupt.patch @@ -0,0 +1,61 @@ +From d29b67c220caf5f4905e1f1576e71bcb6de4af9e Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Marek=20Beh=C3=BAn?= +Date: Sun, 15 Nov 2020 14:59:19 +0100 +Subject: ARM: dts: turris-omnia: describe switch interrupt +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +Describe switch interrupt for Turris Omnia so that the CPU does not have +to poll the switch. We also need to to set mpp45 pin to gpio function +for this. + +Signed-off-by: Marek Behún +Fixes: 26ca8b52d6e1 ("ARM: dts: add support for Turris Omnia") +Cc: linux-arm-kernel@lists.infradead.org +Cc: Uwe Kleine-König +Cc: Jason Cooper +Cc: Gregory CLEMENT +Cc: Andreas Färber +Cc: Andrew Lunn +Cc: Rob Herring +Cc: devicetree@vger.kernel.org +Signed-off-by: Gregory CLEMENT +--- + arch/arm/boot/dts/armada-385-turris-omnia.dts | 12 +++++++++++- + 1 file changed, 11 insertions(+), 1 deletion(-) + +--- a/arch/arm/boot/dts/armada-385-turris-omnia.dts ++++ b/arch/arm/boot/dts/armada-385-turris-omnia.dts +@@ -261,13 +261,18 @@ + + /* Switch MV88E6176 at address 0x10 */ + switch@10 { ++ pinctrl-names = "default"; ++ pinctrl-0 = <&swint_pins>; + compatible = "marvell,mv88e6085"; + #address-cells = <1>; + #size-cells = <0>; +- dsa,member = <0 0>; + ++ dsa,member = <0 0>; + reg = <0x10>; + ++ interrupt-parent = <&gpio1>; ++ interrupts = <13 IRQ_TYPE_LEVEL_LOW>; ++ + ports { + #address-cells = <1>; + #size-cells = <0>; +@@ -320,6 +325,11 @@ + marvell,function = "gpio"; + }; + ++ swint_pins: swint-pins { ++ marvell,pins = "mpp45"; ++ marvell,function = "gpio"; ++ }; ++ + spi0cs0_pins: spi0cs0-pins { + marvell,pins = "mpp25"; + marvell,function = "spi0"; diff --git a/target/linux/mvebu/patches-5.4/032-ARM-dts-turris-omnia-add-SFP-node.patch b/target/linux/mvebu/patches-5.4/032-ARM-dts-turris-omnia-add-SFP-node.patch new file mode 100644 index 0000000000..2447a4e240 --- /dev/null +++ b/target/linux/mvebu/patches-5.4/032-ARM-dts-turris-omnia-add-SFP-node.patch @@ -0,0 +1,90 @@ +From add2d65962977caf23ca2fa21a2457d31b636574 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Marek=20Beh=C3=BAn?= +Date: Mon, 16 Nov 2020 13:24:22 +0100 +Subject: ARM: dts: turris-omnia: add SFP node +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +Turris Omnia has an SFP cage that, together with WAN PHY, is connected +to eth2 SerDes via a SerDes multiplexor. When a SFP module is present, +the multiplexor switches the SerDes signal from PHY to SFP. + +Describe the SFP cage, but leave it disabled. Until phylink has support +for such configuration, we are leaving it to U-Boot to enable SFP and +disable WAN PHY at boot time depending on whether a SFP module is +present. + +Signed-off-by: Marek Behún +Fixes: 26ca8b52d6e1 ("ARM: dts: add support for Turris Omnia") +Reviewed-by: Andrew Lunn +Cc: Russell King - ARM Linux admin +Cc: linux-arm-kernel@lists.infradead.org +Cc: Uwe Kleine-König +Cc: Jason Cooper +Cc: Gregory CLEMENT +Cc: Andreas Färber +Cc: Rob Herring +Cc: devicetree@vger.kernel.org +Signed-off-by: Gregory CLEMENT +--- + arch/arm/boot/dts/armada-385-turris-omnia.dts | 30 ++++++++++++++++++++++++++- + 1 file changed, 29 insertions(+), 1 deletion(-) + +--- a/arch/arm/boot/dts/armada-385-turris-omnia.dts ++++ b/arch/arm/boot/dts/armada-385-turris-omnia.dts +@@ -82,6 +82,24 @@ + }; + }; + }; ++ ++ sfp: sfp { ++ compatible = "sff,sfp"; ++ i2c-bus = <&sfp_i2c>; ++ tx-fault-gpios = <&pcawan 0 GPIO_ACTIVE_HIGH>; ++ tx-disable-gpios = <&pcawan 1 GPIO_ACTIVE_HIGH>; ++ rate-select0-gpios = <&pcawan 2 GPIO_ACTIVE_HIGH>; ++ los-gpios = <&pcawan 3 GPIO_ACTIVE_HIGH>; ++ mod-def0-gpios = <&pcawan 4 GPIO_ACTIVE_LOW>; ++ maximum-power-milliwatt = <3000>; ++ ++ /* ++ * For now this has to be enabled at boot time by U-Boot when ++ * a SFP module is present. Read more in the comment in the ++ * eth2 node below. ++ */ ++ status = "disabled"; ++ }; + }; + + &bm { +@@ -126,10 +144,20 @@ + + /* WAN port */ + ð2 { ++ /* ++ * eth2 is connected via a multiplexor to both the SFP cage and to ++ * ethernet-phy@1. The multiplexor switches the signal to SFP cage when ++ * a SFP module is present, as determined by the mode-def0 GPIO. ++ * ++ * Until kernel supports this configuration properly, in case SFP module ++ * is present, U-Boot has to enable the sfp node above, remove phy ++ * handle and add managed = "in-band-status" property. ++ */ + status = "okay"; + phy-mode = "sgmii"; + phy = <&phy1>; + phys = <&comphy5 2>; ++ sfp = <&sfp>; + buffer-manager = <&bm>; + bm,pool-long = <2>; + bm,pool-short = <3>; +@@ -195,7 +223,7 @@ + /* routed to PCIe2 connector (CN62A) */ + }; + +- i2c@4 { ++ sfp_i2c: i2c@4 { + #address-cells = <1>; + #size-cells = <0>; + reg = <4>; diff --git a/target/linux/mvebu/patches-5.4/033-ARM-dts-turris-omnia-update-ethernet-phy-node-and-handle-name.patch b/target/linux/mvebu/patches-5.4/033-ARM-dts-turris-omnia-update-ethernet-phy-node-and-handle-name.patch new file mode 100644 index 0000000000..5ceef5dc46 --- /dev/null +++ b/target/linux/mvebu/patches-5.4/033-ARM-dts-turris-omnia-update-ethernet-phy-node-and-handle-name.patch @@ -0,0 +1,52 @@ +From 8ee4a5f4f40da60bb85e13d9dd218a3c9197e3e3 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Marek=20Beh=C3=BAn?= +Date: Sun, 15 Nov 2020 14:59:22 +0100 +Subject: ARM: dts: turris-omnia: update ethernet-phy node and handle name +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +Use property name `phy-handle` instead of the deprecated `phy` to +connect eth2 to the PHY. +Rename the node from "phy@1" to "ethernet-phy@1", since "phy@1" is +incorrect according to device-tree bindings documentation. +Also remove the "ethernet-phy-id0141.0DD1" compatible string, it is not +needed. Kernel can read the PHY identifier itself. + +Signed-off-by: Marek Behún +Reviewed-by: Andrew Lunn +Cc: linux-arm-kernel@lists.infradead.org +Cc: Uwe Kleine-König +Cc: Jason Cooper +Cc: Gregory CLEMENT +Cc: Andreas Färber +Cc: Rob Herring +Cc: devicetree@vger.kernel.org +Signed-off-by: Gregory CLEMENT +--- + arch/arm/boot/dts/armada-385-turris-omnia.dts | 6 +++--- + 1 file changed, 3 insertions(+), 3 deletions(-) + +--- a/arch/arm/boot/dts/armada-385-turris-omnia.dts ++++ b/arch/arm/boot/dts/armada-385-turris-omnia.dts +@@ -155,7 +155,7 @@ + */ + status = "okay"; + phy-mode = "sgmii"; +- phy = <&phy1>; ++ phy-handle = <&phy1>; + phys = <&comphy5 2>; + sfp = <&sfp>; + buffer-manager = <&bm>; +@@ -278,9 +278,9 @@ + pinctrl-0 = <&mdio_pins>; + status = "okay"; + +- phy1: phy@1 { ++ phy1: ethernet-phy@1 { + status = "okay"; +- compatible = "ethernet-phy-id0141.0DD1", "ethernet-phy-ieee802.3-c22"; ++ compatible = "ethernet-phy-ieee802.3-c22"; + reg = <1>; + marvell,reg-init = <3 18 0 0x4985>; + diff --git a/target/linux/mvebu/patches-5.4/318-ARM-dts-turris-omnia-fix-hardware-buffer-management.patch b/target/linux/mvebu/patches-5.4/034-ARM-dts-turris-omnia-fix-hardware-buffer-management.patch similarity index 67% rename from target/linux/mvebu/patches-5.4/318-ARM-dts-turris-omnia-fix-hardware-buffer-management.patch rename to target/linux/mvebu/patches-5.4/034-ARM-dts-turris-omnia-fix-hardware-buffer-management.patch index a3f41fb5cb..4283a61341 100644 --- a/target/linux/mvebu/patches-5.4/318-ARM-dts-turris-omnia-fix-hardware-buffer-management.patch +++ b/target/linux/mvebu/patches-5.4/034-ARM-dts-turris-omnia-fix-hardware-buffer-management.patch @@ -1,7 +1,10 @@ -From 9704292ed3230ee19dc4dd64f7484301b728ffb7 Mon Sep 17 00:00:00 2001 +From 5b2c7e0ae762fff2b172caf16b2766cc3e1ad859 Mon Sep 17 00:00:00 2001 From: Rui Salvaterra -Date: Wed, 17 Feb 2021 15:19:30 +0000 -Subject: [PATCH] ARM: dts: turris-omnia: fix hardware buffer management +Date: Wed, 17 Feb 2021 15:30:38 +0000 +Subject: ARM: dts: turris-omnia: fix hardware buffer management +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit Hardware buffer management has never worked on the Turris Omnia, as the required MBus window hadn't been reserved. Fix thusly. @@ -9,6 +12,9 @@ required MBus window hadn't been reserved. Fix thusly. Fixes: 018b88eee1a2 ("ARM: dts: turris-omnia: enable HW buffer management") Signed-off-by: Rui Salvaterra +Reviewed-by: Marek Behún +Tested-by: Klaus Kudielka +Signed-off-by: Gregory CLEMENT --- arch/arm/boot/dts/armada-385-turris-omnia.dts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) From 5e2a2b086cee9a7ba9f765dbf62a62f456b6713a Mon Sep 17 00:00:00 2001 From: Klaus Kudielka Date: Sat, 27 Feb 2021 12:56:10 +0100 Subject: [PATCH 04/43] mvebu: Turris Omnia: use SFP module, if present Follow the recommendations stated in the Turris Omnia DTS for eth2: "In case SFP module is present, U-Boot has to enable the sfp node above, remove phy-handle property, and add managed = "in-band-status" property." The boot script is written in a way, that it works for all U-Boot versions deployed by the vendor so far (2015.10-rc2, 2019.07). Reviewed-by: Noci Reviewed-by: Justin van Steijn Reviewed-by: Nico Rikken Reviewed-by: Julius Schwartzenberg Signed-off-by: Klaus Kudielka (cherry picked from commit 23d2690e5a5410576b587bc96e2c2cf5fc693927) --- .../linux/mvebu/image/turris-omnia.bootscript | 17 ++++++++++++++++- 1 file changed, 16 insertions(+), 1 deletion(-) diff --git a/target/linux/mvebu/image/turris-omnia.bootscript b/target/linux/mvebu/image/turris-omnia.bootscript index fcec5fc1b8..9a3fc0d8cb 100644 --- a/target/linux/mvebu/image/turris-omnia.bootscript +++ b/target/linux/mvebu/image/turris-omnia.bootscript @@ -11,7 +11,22 @@ else fi setenv bootargs earlyprintk console=ttyS0,115200 root=${rootdev} rootfstype=auto rootwait -# Load and boot +# Load device tree and prepare for modification load ${devtype} ${devnum}:${distro_bootpart} ${fdt_addr_r} @DTB@.dtb +fdt addr ${fdt_addr_r} +fdt resize + +# Enable SFP cage, if module is present +i2c dev 0 +i2c mw 0x70 0.0 0xf +i2c read 0x71 0 1 0x00fffff1 +setexpr.b mod_def0 *0x00fffff1 \& 0x10 +if test ${mod_def0} -eq 0; then + fdt set /sfp status okay + fdt rm /soc/internal-regs/ethernet@34000 phy-handle + fdt set /soc/internal-regs/ethernet@34000 managed in-band-status +fi + +# Load kernel and boot load ${devtype} ${devnum}:${distro_bootpart} ${kernel_addr_r} zImage bootz ${kernel_addr_r} - ${fdt_addr_r} From 8166bbf6803053224a6b5807ed6d1f8391d2021c Mon Sep 17 00:00:00 2001 From: DENG Qingfang Date: Thu, 22 Apr 2021 12:28:39 +0800 Subject: [PATCH 05/43] ccache: update to 4.2.1 Update ccache to 4.2.1 While compiling on Gentoo, the ccache can not be compiled due to this error: /openwrt/build_dir/host/ccache-4.1/unittest/../src/third_party/doctest.h:4084:47: error: size of array 'altStackMem' is not an integral constant-expression 4084 | static char altStackMem[4 * SIGSTKSZ]; | ^ This was fixed in ccache version 4.2.1 [1] by upgrading doctest [2]. [1] https://github.com/ccache/ccache/issues/825 [2] https://github.com/doctest/doctest/issues/473 Signed-off-by: DENG Qingfang Signed-off-by: Hans Dedecker [refresh patch] (cherry picked from commit 3ebfd0078d6aa4848ee8f72640266bd0390f790a) Signed-off-by: Josef Schlehofer [improved commit message] --- tools/ccache/Makefile | 4 ++-- tools/ccache/patches/100-honour-copts.patch | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/tools/ccache/Makefile b/tools/ccache/Makefile index c69e26bd23..3db6cc0818 100644 --- a/tools/ccache/Makefile +++ b/tools/ccache/Makefile @@ -8,11 +8,11 @@ include $(TOPDIR)/rules.mk include $(INCLUDE_DIR)/target.mk PKG_NAME:=ccache -PKG_VERSION:=4.1 +PKG_VERSION:=4.2.1 PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.xz PKG_SOURCE_URL:=https://github.com/ccache/ccache/releases/download/v$(PKG_VERSION) -PKG_HASH:=5fdc804056632d722a1182e15386696f0ea6c59cb4ab4d65a54f0b269ae86f99 +PKG_HASH:=9d6ba1cdefdc690401f404b747d81a9a1802b17af4235815866b7620d980477e HOST_BUILD_PARALLEL:=1 diff --git a/tools/ccache/patches/100-honour-copts.patch b/tools/ccache/patches/100-honour-copts.patch index e4045ef9be..0dcc6598f5 100644 --- a/tools/ccache/patches/100-honour-copts.patch +++ b/tools/ccache/patches/100-honour-copts.patch @@ -1,6 +1,6 @@ --- a/src/ccache.cpp +++ b/src/ccache.cpp -@@ -1654,6 +1654,7 @@ calculate_result_name(Context& ctx, +@@ -1756,6 +1756,7 @@ calculate_result_name(Context& ctx, "CPLUS_INCLUDE_PATH", "OBJC_INCLUDE_PATH", "OBJCPLUS_INCLUDE_PATH", // clang From e81dd8a10a141936650da707447bdf3f976aab4b Mon Sep 17 00:00:00 2001 From: Javier Marcet Date: Sat, 4 Apr 2020 17:52:29 +0200 Subject: [PATCH 06/43] base-files: upgrade: fix efi partitions size calculation We were missing (not using) the last sector of each partition, compared with the output of gparted. Signed-off-by: Javier Marcet [moved the dot] Signed-off-by: Christian Lamparter (cherry picked from commit 018ada5403f02921be22ee0cf49b88b2700ee105) --- package/base-files/files/lib/upgrade/common.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package/base-files/files/lib/upgrade/common.sh b/package/base-files/files/lib/upgrade/common.sh index 968893e226..13dbb7ab25 100644 --- a/package/base-files/files/lib/upgrade/common.sh +++ b/package/base-files/files/lib/upgrade/common.sh @@ -267,7 +267,7 @@ get_partitions() { # local type="$1" local lba="$(( $(hex_le32_to_cpu $4) * 0x100000000 + $(hex_le32_to_cpu $3) ))" local end="$(( $(hex_le32_to_cpu $6) * 0x100000000 + $(hex_le32_to_cpu $5) ))" - local num="$(( $end - $lba ))" + local num="$(( $end - $lba + 1 ))" [ "$type" = "00000000000000000000000000000000" ] && continue From dbe2a6343f906ddf48142ee72eb81b3f311cfe6f Mon Sep 17 00:00:00 2001 From: Florian Eckert Date: Tue, 15 Jun 2021 08:48:18 +0200 Subject: [PATCH 07/43] base-files: fix service_running check The following command checks if a instance of a service is running. /etc/init.d/ running In the variable `$@`, which is passed to the function `service_running`, the first argument is always the `instance` which should be checked. Because all other variables where removed from `$@` with `shift`. Before this change the first argument of `$@` was set to the `$service` Variable. So the function does not work as expected. The `$service` variable was always the instance which should be checked. This is not what we want. Signed-off-by: Florian Eckert Reviewed-by: Sungbo Eo (cherry picked from commit dd681838d370f1f6f6fa1bf1f22b0414322292f3) --- package/base-files/files/etc/rc.common | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/package/base-files/files/etc/rc.common b/package/base-files/files/etc/rc.common index f39b69464e..5d0d3c23f7 100755 --- a/package/base-files/files/etc/rc.common +++ b/package/base-files/files/etc/rc.common @@ -100,9 +100,9 @@ service_data() { } service_running() { - local service="${1:-$(basename $initscript)}" - local instance="${2:-*}" - procd_running "$service" "$instance" "$@" + local instance="${1:-*}" + + procd_running "$(basename $initscript)" "$instance" } ${INIT_TRACE:+set -x} From a20e9474dfa0f98085ba595167624cad04086e67 Mon Sep 17 00:00:00 2001 From: Nian Bohung Date: Mon, 25 Oct 2021 06:26:51 -0700 Subject: [PATCH 08/43] cypress-nvram: fix firmware is not exist for raspberry pi compute 4 Fixes: brcmfmac: brcmf_fw_alloc_request: using brcm/brcmfmac43455-sdio for chip BCM4345/6 Direct firmware load for brcm/brcmfmac43455-sdio.raspberrypi,4-compute-module.txt failed with error -2 Falling back to sysfs fallback for: brcm/brcmfmac43455-sdio.raspberrypi,4-compute-module.txt Direct firmware load for brcm/brcmfmac43455-sdio.txt failed with error -2 Falling back to sysfs fallback for: brcm/brcmfmac43455-sdio.txt Signed-off-by: Nian Bohung (cherry picked from commit b1db5585557ed069027767a80c31c6f1f2920196) Signed-off-by: Josef Schlehofer [improved commit mesage] --- package/firmware/cypress-nvram/Makefile | 3 +++ 1 file changed, 3 insertions(+) diff --git a/package/firmware/cypress-nvram/Makefile b/package/firmware/cypress-nvram/Makefile index 777b826088..806bfa2d92 100644 --- a/package/firmware/cypress-nvram/Makefile +++ b/package/firmware/cypress-nvram/Makefile @@ -100,6 +100,9 @@ define Package/cypress-nvram-43455-sdio-rpi-4b/install $(INSTALL_DATA) \ $(PKG_BUILD_DIR)/brcmfmac43455-sdio.raspberrypi,4-model-b.txt \ $(1)/lib/firmware/brcm/brcmfmac43455-sdio.raspberrypi,4-model-b.txt + $(INSTALL_DATA) \ + $(PKG_BUILD_DIR)/brcmfmac43455-sdio.raspberrypi,4-model-b.txt \ + $(1)/lib/firmware/brcm/brcmfmac43455-sdio.raspberrypi,4-compute-module.txt endef $(eval $(call BuildPackage,cypress-nvram-43455-sdio-rpi-4b)) From 2ed471a12aecffbd24feaaebf2ad3c5a1902d3e9 Mon Sep 17 00:00:00 2001 From: Tan Zien Date: Fri, 27 Aug 2021 21:27:11 +0800 Subject: [PATCH 09/43] firmware: intel-microcode: update to 20210608 intel-microcode (3.20210608.2) * Correct INTEL-SA-00442 CVE id to CVE-2020-24489 in changelog and debian/changelog (3.20210608.1). intel-microcode (3.20210608.1) * New upstream microcode datafile 20210608 (closes: #989615) * Implements mitigations for CVE-2020-24511 CVE-2020-24512 (INTEL-SA-00464), information leakage through shared resources, and timing discrepancy sidechannels * Implements mitigations for CVE-2020-24513 (INTEL-SA-00465), Domain-bypass transient execution vulnerability in some Intel Atom Processors, affects Intel SGX. * Implements mitigations for CVE-2020-24489 (INTEL-SA-00442), Intel VT-d privilege escalation * Fixes critical errata on several processors * New Microcodes: sig 0x00050655, pf_mask 0xb7, 2018-11-16, rev 0x3000010, size 47104 sig 0x000606a5, pf_mask 0x87, 2021-03-08, rev 0xc0002f0, size 283648 sig 0x000606a6, pf_mask 0x87, 2021-04-25, rev 0xd0002a0, size 283648 sig 0x00080664, pf_mask 0x01, 2021-02-17, rev 0xb00000f, size 130048 sig 0x00080665, pf_mask 0x01, 2021-02-17, rev 0xb00000f, size 130048 sig 0x000806c1, pf_mask 0x80, 2021-03-31, rev 0x0088, size 109568 sig 0x000806c2, pf_mask 0xc2, 2021-04-07, rev 0x0016, size 94208 sig 0x000806d1, pf_mask 0xc2, 2021-04-23, rev 0x002c, size 99328 sig 0x00090661, pf_mask 0x01, 2021-02-04, rev 0x0011, size 19456 sig 0x000906c0, pf_mask 0x01, 2021-03-23, rev 0x001d, size 19456 sig 0x000a0671, pf_mask 0x02, 2021-04-11, rev 0x0040, size 100352 * Updated Microcodes: sig 0x000306f2, pf_mask 0x6f, 2021-01-27, rev 0x0046, size 34816 sig 0x000306f4, pf_mask 0x80, 2021-02-05, rev 0x0019, size 19456 sig 0x000406e3, pf_mask 0xc0, 2021-01-25, rev 0x00ea, size 105472 sig 0x000406f1, pf_mask 0xef, 2021-02-06, rev 0xb00003e, size 31744 sig 0x00050653, pf_mask 0x97, 2021-03-08, rev 0x100015b, size 34816 sig 0x00050654, pf_mask 0xb7, 2021-03-08, rev 0x2006b06, size 36864 sig 0x00050656, pf_mask 0xbf, 2021-03-08, rev 0x4003102, size 30720 sig 0x00050657, pf_mask 0xbf, 2021-03-08, rev 0x5003102, size 30720 sig 0x0005065b, pf_mask 0xbf, 2021-04-23, rev 0x7002302, size 27648 sig 0x00050663, pf_mask 0x10, 2021-02-04, rev 0x700001b, size 24576 sig 0x00050664, pf_mask 0x10, 2021-02-04, rev 0xf000019, size 24576 sig 0x00050665, pf_mask 0x10, 2021-02-04, rev 0xe000012, size 19456 sig 0x000506c9, pf_mask 0x03, 2020-10-23, rev 0x0044, size 17408 sig 0x000506ca, pf_mask 0x03, 2020-10-23, rev 0x0020, size 15360 sig 0x000506e3, pf_mask 0x36, 2021-01-25, rev 0x00ea, size 105472 sig 0x000506f1, pf_mask 0x01, 2020-10-23, rev 0x0034, size 11264 sig 0x000706a1, pf_mask 0x01, 2020-10-23, rev 0x0036, size 74752 sig 0x000706a8, pf_mask 0x01, 2020-10-23, rev 0x001a, size 75776 sig 0x000706e5, pf_mask 0x80, 2020-11-01, rev 0x00a6, size 110592 sig 0x000806a1, pf_mask 0x10, 2020-11-06, rev 0x002a, size 32768 sig 0x000806e9, pf_mask 0x10, 2021-01-05, rev 0x00ea, size 104448 sig 0x000806e9, pf_mask 0xc0, 2021-01-05, rev 0x00ea, size 104448 sig 0x000806ea, pf_mask 0xc0, 2021-01-06, rev 0x00ea, size 103424 sig 0x000806eb, pf_mask 0xd0, 2021-01-05, rev 0x00ea, size 104448 sig 0x000806ec, pf_mask 0x94, 2021-01-05, rev 0x00ea, size 104448 sig 0x000906e9, pf_mask 0x2a, 2021-01-05, rev 0x00ea, size 104448 sig 0x000906ea, pf_mask 0x22, 2021-01-05, rev 0x00ea, size 102400 sig 0x000906eb, pf_mask 0x02, 2021-01-05, rev 0x00ea, size 104448 sig 0x000906ec, pf_mask 0x22, 2021-01-05, rev 0x00ea, size 103424 sig 0x000906ed, pf_mask 0x22, 2021-01-05, rev 0x00ea, size 103424 sig 0x000a0652, pf_mask 0x20, 2021-02-07, rev 0x00ea, size 93184 sig 0x000a0653, pf_mask 0x22, 2021-03-08, rev 0x00ea, size 94208 sig 0x000a0655, pf_mask 0x22, 2021-03-08, rev 0x00ec, size 94208 sig 0x000a0660, pf_mask 0x80, 2020-12-08, rev 0x00e8, size 94208 sig 0x000a0661, pf_mask 0x80, 2021-02-07, rev 0x00ea, size 93184 * source: update symlinks to reflect id of the latest release, 20210608 intel-microcode (3.20210216.1) * New upstream microcode datafile 20210216 * Mitigates an issue on Skylake Server (H0/M0/U0), Xeon-D 21xx, and Cascade Lake Server (B0/B1) when using an active JTAG agent like In Target Probe (ITP), Direct Connect Interface (DCI) or a Baseboard Management Controller (BMC) to take the CPU JTAG/TAP out of reset and then returning it to reset. * This issue is related to the INTEL-SA-00381 mitigation. * Updated Microcodes: sig 0x00050654, pf_mask 0xb7, 2020-12-31, rev 0x2006a0a, size 36864 sig 0x00050656, pf_mask 0xbf, 2020-12-31, rev 0x4003006, size 53248 sig 0x00050657, pf_mask 0xbf, 2020-12-31, rev 0x5003006, size 53248 * source: update symlinks to reflect id of the latest release, 20210216 intel-microcode (3.20201118.1) * New upstream microcode datafile 20201118 * Removes a faulty microcode update from release 2020-11-10 for Tiger Lake processors. Note that Debian already had removed this specific falty microcode update on the 3.20201110.1 release * Add a microcode update for the Pentium Silver N/J5xxx and Celeron N/J4xxx which didn't make it to release 20201110, fixing security issues (INTEL-SA-00381, INTEL-SA-00389) * Updated Microcodes: sig 0x000706a1, pf_mask 0x01, 2020-06-09, rev 0x0034, size 74752 * Removed Microcodes: sig 0x000806c1, pf_mask 0x80, 2020-10-02, rev 0x0068, size 107520 intel-microcode (3.20201110.1) * New upstream microcode datafile 20201110 (closes: #974533) * Implements mitigation for CVE-2020-8696 and CVE-2020-8698, aka INTEL-SA-00381: AVX register information leakage; Fast-Forward store predictor information leakage * Implements mitigation for CVE-2020-8695, Intel SGX information disclosure via RAPL, aka INTEL-SA-00389 * Fixes critical errata on several processor models * Reintroduces SRBDS mitigations(CVE-2020-0543, INTEL-SA-00320) for Skylake-U/Y, Skylake Xeon E3 * New Microcodes sig 0x0005065b, pf_mask 0xbf, 2020-08-20, rev 0x700001e, size 27648 sig 0x000806a1, pf_mask 0x10, 2020-06-26, rev 0x0028, size 32768 sig 0x000806c1, pf_mask 0x80, 2020-10-02, rev 0x0068, size 107520 sig 0x000a0652, pf_mask 0x20, 2020-07-08, rev 0x00e0, size 93184 sig 0x000a0653, pf_mask 0x22, 2020-07-08, rev 0x00e0, size 94208 sig 0x000a0655, pf_mask 0x22, 2020-07-08, rev 0x00e0, size 93184 sig 0x000a0661, pf_mask 0x80, 2020-07-02, rev 0x00e0, size 93184 * Updated Microcodes sig 0x000306f2, pf_mask 0x6f, 2020-05-27, rev 0x0044, size 34816 sig 0x000406e3, pf_mask 0xc0, 2020-07-14, rev 0x00e2, size 105472 sig 0x00050653, pf_mask 0x97, 2020-06-18, rev 0x1000159, size 33792 sig 0x00050654, pf_mask 0xb7, 2020-06-16, rev 0x2006a08, size 35840 sig 0x00050656, pf_mask 0xbf, 2020-06-18, rev 0x4003003, size 52224 sig 0x00050657, pf_mask 0xbf, 2020-06-18, rev 0x5003003, size 52224 sig 0x000506c9, pf_mask 0x03, 2020-02-27, rev 0x0040, size 17408 sig 0x000506ca, pf_mask 0x03, 2020-02-27, rev 0x001e, size 15360 sig 0x000506e3, pf_mask 0x36, 2020-07-14, rev 0x00e2, size 105472 sig 0x000706a8, pf_mask 0x01, 2020-06-09, rev 0x0018, size 75776 sig 0x000706e5, pf_mask 0x80, 2020-07-30, rev 0x00a0, size 109568 sig 0x000806e9, pf_mask 0x10, 2020-05-27, rev 0x00de, size 104448 sig 0x000806e9, pf_mask 0xc0, 2020-05-27, rev 0x00de, size 104448 sig 0x000806ea, pf_mask 0xc0, 2020-06-17, rev 0x00e0, size 104448 sig 0x000806eb, pf_mask 0xd0, 2020-06-03, rev 0x00de, size 104448 sig 0x000806ec, pf_mask 0x94, 2020-05-18, rev 0x00de, size 104448 sig 0x000906e9, pf_mask 0x2a, 2020-05-26, rev 0x00de, size 104448 sig 0x000906ea, pf_mask 0x22, 2020-05-25, rev 0x00de, size 103424 sig 0x000906eb, pf_mask 0x02, 2020-05-25, rev 0x00de, size 104448 sig 0x000906ec, pf_mask 0x22, 2020-06-03, rev 0x00de, size 103424 sig 0x000906ed, pf_mask 0x22, 2020-05-24, rev 0x00de, size 103424 sig 0x000a0660, pf_mask 0x80, 2020-07-08, rev 0x00e0, size 94208 * 0x806c1: remove the new Tiger Lake update: causes hang on cold/warm boot https://github.com/intel/Intel-Linux-Processor-Microcode-Data-Files/issues/44 INTEL-SA-00381 AND INTEL-SA-00389 MITIGATIONS ARE THEREFORE NOT INSTALLED FOR 0x806c1 TIGER LAKE PROCESSORS by this package update. Contact your system vendor for a firmware update, or wait fo a possible fix in a future Intel microcode release. * source: update symlinks to reflect id of the latest release, 20201110 * source: ship new upstream documentation (security.md, releasenote.md) Signed-off-by: Tan Zien [used different .tar.xz source, but with the same content] Signed-off-by: Christian Lamparter (cherry picked from commit 1add2c0d95efb970ab18485e570b146610740bf2) --- package/firmware/intel-microcode/Makefile | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/package/firmware/intel-microcode/Makefile b/package/firmware/intel-microcode/Makefile index f5c66c404d..576d498369 100644 --- a/package/firmware/intel-microcode/Makefile +++ b/package/firmware/intel-microcode/Makefile @@ -8,13 +8,13 @@ include $(TOPDIR)/rules.mk PKG_NAME:=intel-microcode -PKG_VERSION:=20200616 +PKG_VERSION:=20210608 PKG_RELEASE:=1 -PKG_SOURCE:=intel-microcode_3.$(PKG_VERSION).$(PKG_RELEASE).tar.xz +PKG_SOURCE:=intel-microcode_3.$(PKG_VERSION).2.tar.xz PKG_SOURCE_URL:=http://ftp.debian.org/debian/pool/non-free/i/intel-microcode/ -PKG_HASH:=bcc3b81c452fe4649a948c022475d76c1cdfbb730f36749a082f412f1406a3b9 -PKG_BUILD_DIR:=$(BUILD_DIR)/$(PKG_NAME)-3.$(PKG_VERSION).$(PKG_RELEASE) +PKG_HASH:=fbf82688ffd0d87b352a35c57bd097ea014f0ad32c9c8f9629725c1b43d1c84d +PKG_BUILD_DIR:=$(BUILD_DIR)/intel-microcode-3.$(PKG_VERSION).2 PKG_BUILD_DEPENDS:=iucode-tool/host From 209c77e90fdc142f71e65be7b3891958b39ff403 Mon Sep 17 00:00:00 2001 From: Josef Schlehofer Date: Sat, 10 Apr 2021 19:07:40 +0200 Subject: [PATCH 10/43] linux-firmware: ath10k: add support for Qualcomm Atheros QCA9377 Add firmware and board file for Qualcomm Atheros QCA9377 802.11ac Wireless Network Adapter (rev 31) recognized as [168c:0042]. This card supports standard 1x1 802.11ac Wave2, BT5, and MU-MIMO. Signed-off-by: Josef Schlehofer (cherry picked from commit b2656490855f2a90f8895079a9a3853af6512d83) --- package/firmware/linux-firmware/qca_ath10k.mk | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/package/firmware/linux-firmware/qca_ath10k.mk b/package/firmware/linux-firmware/qca_ath10k.mk index bd5d21916a..3bc942b108 100644 --- a/package/firmware/linux-firmware/qca_ath10k.mk +++ b/package/firmware/linux-firmware/qca_ath10k.mk @@ -26,6 +26,23 @@ define Package/ath10k-firmware-qca4019/install endef $(eval $(call BuildPackage,ath10k-firmware-qca4019)) +Package/ath10k-board-qca9377 = $(call Package/firmware-default,ath10k qca9377 board firmware) +define Package/ath10k-board-qca9377/install + $(INSTALL_DIR) $(1)/lib/firmware/ath10k/QCA9377/hw1.0 + $(INSTALL_DATA) \ + $(PKG_BUILD_DIR)/ath10k/QCA9377/hw1.0/board-2.bin \ + $(1)/lib/firmware/ath10k/QCA9377/hw1.0/ +endef +$(eval $(call BuildPackage,ath10k-board-qca9377)) +Package/ath10k-firmware-qca9377 = $(call Package/firmware-default,ath10k qca9377 firmware,+ath10k-board-qca9377) +define Package/ath10k-firmware-qca9377/install + $(INSTALL_DIR) $(1)/lib/firmware/ath10k/QCA9377/hw1.0 + $(INSTALL_DATA) \ + $(PKG_BUILD_DIR)/ath10k/QCA9377/hw1.0/firmware-6.bin \ + $(1)/lib/firmware/ath10k/QCA9377/hw1.0/firmware-6.bin +endef +$(eval $(call BuildPackage,ath10k-firmware-qca9377)) + Package/ath10k-board-qca9887 = $(call Package/firmware-default,ath10k qca9887 board firmware) define Package/ath10k-board-qca9887/install $(INSTALL_DIR) $(1)/lib/firmware/ath10k/QCA9887/hw1.0 From d0b0ebf966a412ddc2b25dffb5eff7effbcd0220 Mon Sep 17 00:00:00 2001 From: Josef Schlehofer Date: Sat, 1 May 2021 08:51:12 +0200 Subject: [PATCH 11/43] linux-firmware: update to version 20210315 and trim down broadcom FW MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit In there linux-firmware repository located in kernel, there were removed old broadcom firmware [1] as they seem to be likely vulnerable to KrØØk vulnerability (CVE-2019-15126), because Cypress released new versions and superseded by it. In OpenWrt, there is Makefile for cypress-firmware, which already provides the same named packages like it was in linux-firmware. For example, cypress-firmware-43455-sdio provides brcmfmac-firmware-43455-sdio [2]. Changelog between 2020118 and 20210315: 3568f96 (tag: 20210315) linux-firmware: Update firmware file for Intel Bluetooth AX210 9e96e50 linux-firmware: Update firmware file for Intel Bluetooth AX200 c8d0db5 linux-firmware: Update firmware file for Intel Bluetooth AX201 5e2a387 Merge tag 'iwlwifi-fw-2021-03-05-v3' of git://git.kernel.org/pub/scm/linux/kernel/git/iwlwifi/linux-firmware into main b0d3e31 rtw88: 8822c: Update normal firmware to v9.9.6 5a2fd63 iwlwifi: add new FWs from core59-66 release 4f54906 iwlwifi: update 9000-family firmwares 11b7607 iwlwifi: update 7265D firmware e425f76 Merge branch 'add-silabs-wf200' of github.com:jerome-pouiller/linux-firmware into main 5ecd13f Mellanox: Add new mlxsw_spectrum firmware xx.2008.2406 58fb90a linux-firmware: add frimware for mediatek bluetooth chip (MT7921) e576a1b rtw89: 8852a: add firmware v0.9.12.2 048a7cb WHENCE: add missing symlink for BananaPi M3 aa6c6e7 Add symlink for BananaPi M2 to brcmfmac43430-sdio config 58825f7 brcm: Fix Raspberry Pi 4B NVRAM file 520f71b silabs: add new firmware for WF200 f7915a0 amdgpu: add initial firmware for green sardine 80cb579 rtw88: RTL8822C: Update normal firmware to v9.9.5 b79d239 (tag: 20210208) Merge branch 'DG1-guc-huc-ADLS-dmc' of git://anongit.freedesktop.org/drm/drm-firmware into main 66970e1 Merge branch 'qcom-rb5' of https://github.com/lumag/linux-firmware into main cf6fc2b Mellanox: Add new mlxsw_spectrum firmware xx.2008.2304 391fd50 linux-firmware: add firmware for MT7921 c5e3240 rtw88: RTL8821C: Update firmware to v24.8 d33d2d8 linux-firmware: Update firmware file for Intel Bluetooth AX210 3027ae4 linux-firmware: Update firmware file for Intel Bluetooth AX200 13979c3 linux-firmware: Update firmware file for Intel Bluetooth AX201 348d8a9 i915: Add DMC v2.01 for ADL-S f33f1f7 i915: Add HuC v7.7.1 for DG1 6a422f5 i915: Add GuC v49.0.1 for DG1 df822a8 qcom: Add venus firmware files for VPU-1.0 11a1db1 qcom: Add SM8250 Compute DSP firmware e55248b qcom: Add SM8250 Audio DSP firmware da74cc6 qcom: add firmware files for Adreno a650 0578970 brcm: Link RPi4's WiFi firmware with DMI machine name. d528862 brcm: Add NVRAM for Vamrs 96boards Rock960 870b805 brcm: Update Raspberry Pi 3B+/4B NVRAM for downstream changes a28a590 cypress: Fix link direction 060ad8b cypress: Link the new cypress firmware to the old brcm files 0f0aefd brcm: remove old brcm firmwares that have newer cypress variants f580dc2 rtl_bt: Update RTL8822C BT(UART I/F) FW to 0x059A_25CB 7df2220 rtl_bt: Update RTL8822C BT(USB I/F) FW to 0x099a_7253 e79405d rtl_bt: Add firmware and config files for RTL8852A BT USB chip ef3813d rtl_bt: Update RTL8821C BT(USB I/F) FW to 0x829a_7644 646f159 (tag: 20201218) make AP6212 in bananpi m2 plus/zero work 28185ec linux-firmware: Update firmware file for Intel Bluetooth AX210 23da869 linux-firmware: Update firmware file for Intel Bluetooth AX200 2099248 linux-firmware: Update firmware file for Intel Bluetooth AX201 94de5e2 linux-firmware: Update firmware file for Intel Bluetooth 9560 27a3689 linux-firmware: Update firmware file for Intel Bluetooth 9260 5c3c4af Merge branch 'lt9611uxc' of https://github.com/lumag/linux-firmware into main aaed4a8 Merge branch 'v1.1.6' of https://github.com/irui-wang/linux_fw_vpu_v1.1.6 into main d8c9865 Merge branch 'master' of https://github.com/sampnimm/linux-firmware-BT into main 63ab3db linux-firmware: add firmware for Lontium LT9611UXC DSI to HDMI bridge 0fe0fe0 mediatek: update MT8173 VPU firmware to v1.1.6 1a08ec9 QCA : Updated firmware files for WCN3991 7455a36 Merge branch 'guc_v49' of git://anongit.freedesktop.org/drm/drm-firmware into main 7eb7fda linux-firmware: Update firmware file for Intel Bluetooth AX210 5cbf459 linux-firmware: Update firmware file for Intel Bluetooth AX210 c487f7d i915: Add GuC firmware v49.0.1 for all platforms d9ffb07 i915: Remove duplicate KBL DMC entry b362fd4 Mellanox: Add new mlxsw_spectrum firmware xx.2008.2018 bc9cd0b linux-firmware: Update AMD SEV firmware 54c797a amdgpu: add sienna cichlid firmware for 20.45 1340e9c amdgpu: update vega20 firmware for 20.45 b260c9c amdgpu: update vega12 firmware for 20.45 d683bd5 amdgpu: update vega10 firmware for 20.45 7c81cc2 amdgpu: update renoir firmware for 20.45 3619e57 amdgpu: update navi14 firmware for 20.45 68ce0fb amdgpu: update navi12 firmware for 20.45 e889b80 amdgpu: update navi10 firmware for 20.45 f4edc15 amdgpu: update raven2 firmware for 20.45 e71210f amdgpu: update raven firmware for 20.45 [1] https://git.kernel.org/pub/scm/linux/kernel/git/firmware/linux-firmware.git/commit/?id=0f0aefd733f70beae4c0246edbd2c158d5ce974c [2] https://github.com/openwrt/openwrt/blob/eeda8652f1655d4f9c11e9c9f51ddcd3377d119a/package/firmware/cypress-firmware/Makefile#L124 Signed-off-by: Josef Schlehofer (cherry picked from commit ff2bb16730f629d54bde8ba85c75d8614741e3fd) (removed sinovoip_bananapi-m2-berry) Signed-off-by: Christian Lamparter --- package/firmware/linux-firmware/Makefile | 6 ++--- package/firmware/linux-firmware/broadcom.mk | 27 --------------------- target/linux/sunxi/image/cortexa7.mk | 6 ++--- 3 files changed, 6 insertions(+), 33 deletions(-) diff --git a/package/firmware/linux-firmware/Makefile b/package/firmware/linux-firmware/Makefile index 7fb99dd2ce..e2fee3b6a2 100644 --- a/package/firmware/linux-firmware/Makefile +++ b/package/firmware/linux-firmware/Makefile @@ -8,12 +8,12 @@ include $(TOPDIR)/rules.mk PKG_NAME:=linux-firmware -PKG_VERSION:=20201118 -PKG_RELEASE:=3 +PKG_VERSION:=20210315 +PKG_RELEASE:=1 PKG_SOURCE_URL:=@KERNEL/linux/kernel/firmware PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.xz -PKG_HASH:=863d5a31da725b856a917280d1e3014929b3bc3d4e6e5faecf530c13afb7e2b9 +PKG_HASH:=a2348f03492713dca9aef202496c6e58f5e63ee5bec6a7bdfcf8b18ce7155e70 PKG_MAINTAINER:=Felix Fietkau diff --git a/package/firmware/linux-firmware/broadcom.mk b/package/firmware/linux-firmware/broadcom.mk index 00f7076104..26f6534632 100644 --- a/package/firmware/linux-firmware/broadcom.mk +++ b/package/firmware/linux-firmware/broadcom.mk @@ -34,24 +34,6 @@ define Package/brcmfmac-firmware-4329-sdio/install endef $(eval $(call BuildPackage,brcmfmac-firmware-4329-sdio)) -Package/brcmfmac-firmware-43362-sdio = $(call Package/firmware-default,Broadcom BCM43362 FullMac SDIO firmware) -define Package/brcmfmac-firmware-43362-sdio/install - $(INSTALL_DIR) $(1)/lib/firmware/brcm - $(INSTALL_DATA) \ - $(PKG_BUILD_DIR)/brcm/brcmfmac43362-sdio.bin \ - $(1)/lib/firmware/brcm/brcmfmac43362-sdio.bin -endef -$(eval $(call BuildPackage,brcmfmac-firmware-43362-sdio)) - -Package/brcmfmac-firmware-43430-sdio = $(call Package/firmware-default,Broadcom BCM43430 FullMac SDIO firmware) -define Package/brcmfmac-firmware-43430-sdio/install - $(INSTALL_DIR) $(1)/lib/firmware/brcm - $(INSTALL_DATA) \ - $(PKG_BUILD_DIR)/brcm/brcmfmac43430-sdio.bin \ - $(1)/lib/firmware/brcm/brcmfmac43430-sdio.bin -endef -$(eval $(call BuildPackage,brcmfmac-firmware-43430-sdio)) - Package/brcmfmac-firmware-43430-sdio-rpi-3b = $(call Package/firmware-default,Broadcom BCM43430 NVRAM for Raspberry Pi 3B) define Package/brcmfmac-firmware-43430-sdio-rpi-3b/install $(INSTALL_DIR) $(1)/lib/firmware/brcm @@ -79,15 +61,6 @@ define Package/brcmfmac-firmware-43430a0-sdio/install endef $(eval $(call BuildPackage,brcmfmac-firmware-43430a0-sdio)) -Package/brcmfmac-firmware-43455-sdio = $(call Package/firmware-default,Broadcom BCM43455 FullMac SDIO firmware) -define Package/brcmfmac-firmware-43455-sdio/install - $(INSTALL_DIR) $(1)/lib/firmware/brcm - $(INSTALL_DATA) \ - $(PKG_BUILD_DIR)/brcm/brcmfmac43455-sdio.bin \ - $(1)/lib/firmware/brcm/brcmfmac43455-sdio.bin -endef -$(eval $(call BuildPackage,brcmfmac-firmware-43455-sdio)) - Package/brcmfmac-firmware-43455-sdio-rpi-3b-plus = $(call Package/firmware-default,Broadcom BCM43455 NVRAM for Raspberry Pi 3B+) define Package/brcmfmac-firmware-43455-sdio-rpi-3b-plus/install $(INSTALL_DIR) $(1)/lib/firmware/brcm diff --git a/target/linux/sunxi/image/cortexa7.mk b/target/linux/sunxi/image/cortexa7.mk index b55e93b7fb..6445ed0bd6 100644 --- a/target/linux/sunxi/image/cortexa7.mk +++ b/target/linux/sunxi/image/cortexa7.mk @@ -23,7 +23,7 @@ define Device/friendlyarm_nanopi-m1-plus DEVICE_VENDOR := FriendlyARM DEVICE_MODEL := NanoPi M1 Plus DEVICE_PACKAGES:=kmod-rtc-sunxi kmod-leds-gpio kmod-brcmfmac \ - brcmfmac-firmware-43430-sdio wpad-basic-wolfssl + cypress-firmware-43430-sdio wpad-basic-wolfssl SOC := sun8i-h3 endef TARGET_DEVICES += friendlyarm_nanopi-m1-plus @@ -39,7 +39,7 @@ define Device/friendlyarm_nanopi-neo-air DEVICE_VENDOR := FriendlyARM DEVICE_MODEL := NanoPi NEO Air DEVICE_PACKAGES := kmod-rtc-sunxi kmod-leds-gpio kmod-brcmfmac \ - brcmfmac-firmware-43430-sdio wpad-basic-wolfssl + cypress-firmware-43430-sdio wpad-basic-wolfssl SOC := sun8i-h3 endef TARGET_DEVICES += friendlyarm_nanopi-neo-air @@ -48,7 +48,7 @@ define Device/friendlyarm_nanopi-r1 DEVICE_VENDOR := FriendlyARM DEVICE_MODEL := NanoPi R1 DEVICE_PACKAGES := kmod-rtc-sunxi kmod-usb-net-rtl8152 kmod-leds-gpio \ - kmod-brcmfmac brcmfmac-firmware-43430-sdio wpad-basic-wolfssl + kmod-brcmfmac cypress-firmware-43430-sdio wpad-basic-wolfssl SOC := sun8i-h3 endef TARGET_DEVICES += friendlyarm_nanopi-r1 From 7306b9e810969657edb42bc24e87a4df712df853 Mon Sep 17 00:00:00 2001 From: Tomas Lara Date: Tue, 1 Jun 2021 14:00:15 -0400 Subject: [PATCH 12/43] linux-firmware: update to 20210511 git log --pretty=oneline --abbrev-commit 20201118..20210511 7685cf4 (HEAD, tag: 20210511) nvidia: Update Tegra194 XUSB firmware to v60.09 cf32752 nvidia: Update Tegra186 XUSB firmware to v55.18 cb8ca82 nvidia: Update Tegra210 XUSB firmware to v50.26 f99d6a1 linux-firmware: update firmware for mhdp8546 ecdfcf8 Merge branch 'adlp_dmc_firmware' of git://anongit.freedesktop.org/drm/drm-firmware into main 547b202 Merge https://github.com/suraj714/linux-firmware-venus into main 3d32f21 i915: Add ADL-P DMC Support 3f23f51 amdgpu: add new polaris 12 MC firmware a2565bb firmware: nvidia: Add VIC firmware for Tegra194 17ec2a5 qcom: add gpu firmwares for sc7280 b653cf4 Merge https://github.com/pkshih/linux-firmware into main 2a96c08 brcm: Add a link to enable khadas VIM2's WiFi ffc64a2 rtw89: 8852a: update fw to v0.13.8.0 3e3497c rtl_bt: Update RTL8852A BT USB firmware to 0xD9A8_7893 c7b11ed qcom: Add venus firmware files for VPU-2.0 2f4f0f8 rtw89: 8852a: update fw to v0.13.8.0 fa0efef linux-firmware: Update firmware file for Intel Bluetooth AX210 9be3daa linux-firmware: Update firmware file for Intel Bluetooth 9560 687d64a linux-firmware: Update firmware file for Intel Bluetooth 9260 a7f1249 linux-firmware: Update firmware file for Intel Bluetooth AX200 47650a0 linux-firmware: Update firmware file for Intel Bluetooth AX201 195ecf1 linux-firmware: Intel BT 7265: Fix Security Issues 4116d72 linux-firmware: Update firmware file for Intel Bluetooth 8265 ca83c73 qcom: update venus firmware files for v5.4 1334578 Merge branch 'mrvl-prestera' of https://github.com/PLVision/linux-firmware into main 16052e4 mrvl: prestera: Add Marvell Prestera Switchdev firmware 3.0 version bdf929d rtw88: 8822c: Update normal firmware to v9.9.9 0b558e8 brcm: add missing symlink for Pi Zero W NVRAM file cfa004c amdgpu: update arcturus firmware from 21.10 d5567c5 amdgpu: update navy flounder firmware from 21.10 ef5ea5d amdgpu: update sienna cichlid firmware from 21.10 f35700f amdgpu: update vega20 firmware from 21.10 1be98f1 amdgpu: update picasso firmware from 21.10 fee0497 amdgpu: update navi14 firmware from 21.10 15003b0 amdgpu: update green sardine firmware from 21.10 64555fb amdgpu: update vega12 firmware from 21.10 eb07276 amdgpu: update navi12 firmware from 21.10 e36c82a amdgpu: update vega10 firmware from 21.10 4a5eaa2 amdgpu: update renoir firmware from 21.10 65eb326 amdgpu: update navi10 firmware from 21.10 8bdca03 amdgpu: update raven2 firmware from 21.10 c9e44ca amdgpu: update raven firmware from 21.10 bc3e610 rtl_nic: add new firmware for RTL8153 and RTL8156 series 8528618 Merge branch 'for-upstream' of git://git.chelsio.net/pub/git/linux-firmware into main 940b7f4 cxgb4: Update firmware to revision 1.25.4.0 f66adc3 Merge branch 'main' of gitolite.kernel.org:/pub/scm/linux/kernel/git/maks/linux-firmware into main f350e91 Merge https://github.com/rjliao-qca/qca-btfw into main 9bc1bcc Merge https://github.com/Netronome/linux-firmware into main 2f30708 Mellanox: Add new mlxsw_spectrum firmware xx.2008.2438 393f272 brcm: Link CM4's WiFi firmware with DMI machine name. 73144e0 linux-firmware: Update firmware file for Intel Bluetooth AX201 8ab7aba amdgpu: update navi14 smc firmware 4fe6e53 amdgpu: update navi10 SMC firmware c296849 QCA: Update Bluetooth firmware for QCA6174 d6a18e9 WHENCE: link to similar config file for rtl8821a support 6c419ae nfp: update Agilio SmartNIC flower firmware to rev AOTC-2.14.A.6 af1ca28 amdgpu: add arcturus firmware 0dd245d Merge branch 'sm8250-new-fw' of https://github.com/lumag/linux-firmware into main 55cab07 rtl_bt: Add rtl8723bs_config-OBDA0623.bin symlink 2548d06 brcm: Add nvram for the Chuwi Hi8 (CWI509) tablet e45c137 brcm: Add nvram for the Predia Basic tablet d8fa0cf qcom: sm8250: update remoteproc firmware 84af0e0 qcom: update a650 firmware files 3f026a2 rtl_bt: Update RTL8822C BT(UART I/F) FW to 0x59A_76A3 c82cb46 amdgpu: update sienna cichlid firmware for 20.50 24fe696 amdgpu: update vega20 firmware for 20.50 e05d197 amdgpu: update picasso firmware for 20.50 76d07cd amdgpu: update navi14 firmware for 20.50 b2fc037 amdgpu: update vega12 firmware for 20.50 25451a4 amdgpu: update navi12 firmware for 20.50 b938597 amdgpu: update vega10 firmware for 20.50 2542ba7 amdgpu: update renoir firmware for 20.50 b55d063 amdgpu: update navi10 firmware for 20.50 1a62f28 amdgpu: update raven2 firmware for 20.50 4df488f amdgpu: update raven firmware for 20.50 a29bdb2 amdgpu: add initial support for navy flounder 3568f96 (tag: 20210315) linux-firmware: Update firmware file for Intel Bluetooth AX210 9e96e50 linux-firmware: Update firmware file for Intel Bluetooth AX200 c8d0db5 linux-firmware: Update firmware file for Intel Bluetooth AX201 5e2a387 Merge tag 'iwlwifi-fw-2021-03-05-v3' of git://git.kernel.org/pub/scm/linux/kernel/git/iwlwifi/linux-firmware into main b0d3e31 rtw88: 8822c: Update normal firmware to v9.9.6 5a2fd63 iwlwifi: add new FWs from core59-66 release 4f54906 iwlwifi: update 9000-family firmwares 11b7607 iwlwifi: update 7265D firmware e425f76 Merge branch 'add-silabs-wf200' of github.com:jerome-pouiller/linux-firmware into main 5ecd13f Mellanox: Add new mlxsw_spectrum firmware xx.2008.2406 58fb90a linux-firmware: add frimware for mediatek bluetooth chip (MT7921) e576a1b rtw89: 8852a: add firmware v0.9.12.2 048a7cb WHENCE: add missing symlink for BananaPi M3 aa6c6e7 Add symlink for BananaPi M2 to brcmfmac43430-sdio config 58825f7 brcm: Fix Raspberry Pi 4B NVRAM file 520f71b silabs: add new firmware for WF200 f7915a0 amdgpu: add initial firmware for green sardine 80cb579 rtw88: RTL8822C: Update normal firmware to v9.9.5 b79d239 (tag: 20210208) Merge branch 'DG1-guc-huc-ADLS-dmc' of git://anongit.freedesktop.org/drm/drm-firmware into main 66970e1 Merge branch 'qcom-rb5' of https://github.com/lumag/linux-firmware into main cf6fc2b Mellanox: Add new mlxsw_spectrum firmware xx.2008.2304 391fd50 linux-firmware: add firmware for MT7921 c5e3240 rtw88: RTL8821C: Update firmware to v24.8 d33d2d8 linux-firmware: Update firmware file for Intel Bluetooth AX210 3027ae4 linux-firmware: Update firmware file for Intel Bluetooth AX200 13979c3 linux-firmware: Update firmware file for Intel Bluetooth AX201 348d8a9 i915: Add DMC v2.01 for ADL-S f33f1f7 i915: Add HuC v7.7.1 for DG1 6a422f5 i915: Add GuC v49.0.1 for DG1 df822a8 qcom: Add venus firmware files for VPU-1.0 11a1db1 qcom: Add SM8250 Compute DSP firmware e55248b qcom: Add SM8250 Audio DSP firmware da74cc6 qcom: add firmware files for Adreno a650 0578970 brcm: Link RPi4's WiFi firmware with DMI machine name. d528862 brcm: Add NVRAM for Vamrs 96boards Rock960 870b805 brcm: Update Raspberry Pi 3B+/4B NVRAM for downstream changes a28a590 cypress: Fix link direction 060ad8b cypress: Link the new cypress firmware to the old brcm files 0f0aefd brcm: remove old brcm firmwares that have newer cypress variants f580dc2 rtl_bt: Update RTL8822C BT(UART I/F) FW to 0x059A_25CB 7df2220 rtl_bt: Update RTL8822C BT(USB I/F) FW to 0x099a_7253 e79405d rtl_bt: Add firmware and config files for RTL8852A BT USB chip ef3813d rtl_bt: Update RTL8821C BT(USB I/F) FW to 0x829a_7644 646f159 (tag: 20201218) make AP6212 in bananpi m2 plus/zero work 28185ec linux-firmware: Update firmware file for Intel Bluetooth AX210 23da869 linux-firmware: Update firmware file for Intel Bluetooth AX200 2099248 linux-firmware: Update firmware file for Intel Bluetooth AX201 94de5e2 linux-firmware: Update firmware file for Intel Bluetooth 9560 27a3689 linux-firmware: Update firmware file for Intel Bluetooth 9260 5c3c4af Merge branch 'lt9611uxc' of https://github.com/lumag/linux-firmware into main aaed4a8 Merge branch 'v1.1.6' of https://github.com/irui-wang/linux_fw_vpu_v1.1.6 into main d8c9865 Merge branch 'master' of https://github.com/sampnimm/linux-firmware-BT into main 63ab3db linux-firmware: add firmware for Lontium LT9611UXC DSI to HDMI bridge 0fe0fe0 mediatek: update MT8173 VPU firmware to v1.1.6 1a08ec9 QCA : Updated firmware files for WCN3991 7455a36 Merge branch 'guc_v49' of git://anongit.freedesktop.org/drm/drm-firmware into main 7eb7fda linux-firmware: Update firmware file for Intel Bluetooth AX210 5cbf459 linux-firmware: Update firmware file for Intel Bluetooth AX210 c487f7d i915: Add GuC firmware v49.0.1 for all platforms d9ffb07 i915: Remove duplicate KBL DMC entry b362fd4 Mellanox: Add new mlxsw_spectrum firmware xx.2008.2018 bc9cd0b linux-firmware: Update AMD SEV firmware 54c797a amdgpu: add sienna cichlid firmware for 20.45 1340e9c amdgpu: update vega20 firmware for 20.45 b260c9c amdgpu: update vega12 firmware for 20.45 d683bd5 amdgpu: update vega10 firmware for 20.45 7c81cc2 amdgpu: update renoir firmware for 20.45 3619e57 amdgpu: update navi14 firmware for 20.45 68ce0fb amdgpu: update navi12 firmware for 20.45 e889b80 amdgpu: update navi10 firmware for 20.45 f4edc15 amdgpu: update raven2 firmware for 20.45 e71210f amdgpu: update raven firmware for 20.45 Signed-off-by: Tomas Lara [rebased; removed brcmfmac changes due to removed firmware] Signed-off-by: David Bauer (cherry picked from commit 441353743095d11c232bb855848a2aa2d1edafa0) --- package/firmware/linux-firmware/Makefile | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/package/firmware/linux-firmware/Makefile b/package/firmware/linux-firmware/Makefile index e2fee3b6a2..2ad213b82b 100644 --- a/package/firmware/linux-firmware/Makefile +++ b/package/firmware/linux-firmware/Makefile @@ -8,12 +8,12 @@ include $(TOPDIR)/rules.mk PKG_NAME:=linux-firmware -PKG_VERSION:=20210315 +PKG_VERSION:=20210511 PKG_RELEASE:=1 PKG_SOURCE_URL:=@KERNEL/linux/kernel/firmware PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.xz -PKG_HASH:=a2348f03492713dca9aef202496c6e58f5e63ee5bec6a7bdfcf8b18ce7155e70 +PKG_HASH:=2aa6ae8b9808408f9811ac38f00c188e53e984a2b3990254f6c9c02c1ab13417 PKG_MAINTAINER:=Felix Fietkau From 600375239460865e3b95e6b2a096a23c42dd88c1 Mon Sep 17 00:00:00 2001 From: Hauke Mehrtens Date: Sat, 18 Dec 2021 12:01:27 +0100 Subject: [PATCH 13/43] linux-firmware: Update to version 20211216 The rtl8723bs firmware was removed and a symlink to the rtl8723bu firmware was created like it is done in upstream linux-firmware. The following OpenWrt packages are changing: * amdgpu-firmware: Multiple updates and new files * ar3k-firmware: Multiple updates and new files * ath10k-firmware-qca6174: Updated ath10k/QCA6174/hw3.0/board-2.bin * bnx2x-firmware: Added bnx2x-e1-7.13.21.0.fw, bnx2x-e1h-7.13.21.0.fw and bnx2x-e2-7.13.21.0.fw * iwlwifi-firmware-iwl8260c: Updated iwlwifi-8000C-36.ucode * iwlwifi-firmware-iwl8265: Updated iwlwifi-8265-36.ucode * iwlwifi-firmware-iwl9000: Updated iwlwifi-9000-pu-b0-jf-b0-46.ucode * iwlwifi-firmware-iwl9260: Updated iwlwifi-9260-th-b0-jf-b0-46.ucode * r8169-firmware: Updated rtl8153c-1.fw * rtl8723bs-firmware: removed * rtl8723bu-firmware: Added rtlwifi/rtl8723bs_nic.bin symlink * rtl8822ce-firmware: Updated rtw8822c_fw.bin Signed-off-by: Hauke Mehrtens (cherry picked from commit 397dfe4a97e61b87f909181ba60b6187d758635f) Signed-off-by: Christian Lamparter (2012->2021) --- package/firmware/linux-firmware/Makefile | 4 ++-- package/firmware/linux-firmware/realtek.mk | 8 +------- 2 files changed, 3 insertions(+), 9 deletions(-) diff --git a/package/firmware/linux-firmware/Makefile b/package/firmware/linux-firmware/Makefile index 2ad213b82b..4786751e8c 100644 --- a/package/firmware/linux-firmware/Makefile +++ b/package/firmware/linux-firmware/Makefile @@ -8,12 +8,12 @@ include $(TOPDIR)/rules.mk PKG_NAME:=linux-firmware -PKG_VERSION:=20210511 +PKG_VERSION:=20211216 PKG_RELEASE:=1 PKG_SOURCE_URL:=@KERNEL/linux/kernel/firmware PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.xz -PKG_HASH:=2aa6ae8b9808408f9811ac38f00c188e53e984a2b3990254f6c9c02c1ab13417 +PKG_HASH:=eeddb4e6bef31fd1a3757f12ccc324929bbad97855c0b9ec5ed780f74de1837d PKG_MAINTAINER:=Felix Fietkau diff --git a/package/firmware/linux-firmware/realtek.mk b/package/firmware/linux-firmware/realtek.mk index b0f6ff7f35..081cc1b37c 100644 --- a/package/firmware/linux-firmware/realtek.mk +++ b/package/firmware/linux-firmware/realtek.mk @@ -76,16 +76,10 @@ Package/rtl8723bu-firmware = $(call Package/firmware-default,RealTek RTL8723BU f define Package/rtl8723bu-firmware/install $(INSTALL_DIR) $(1)/lib/firmware/rtlwifi $(INSTALL_DATA) $(PKG_BUILD_DIR)/rtlwifi/rtl8723bu_nic.bin $(1)/lib/firmware/rtlwifi + ln -s rtl8723bu_nic.bin $(1)/lib/firmware/rtlwifi/rtl8723bs_nic.bin endef $(eval $(call BuildPackage,rtl8723bu-firmware)) -Package/rtl8723bs-firmware = $(call Package/firmware-default,RealTek RTL8723BS firmware) -define Package/rtl8723bs-firmware/install - $(INSTALL_DIR) $(1)/lib/firmware/rtlwifi - $(INSTALL_DATA) $(PKG_BUILD_DIR)/rtlwifi/rtl8723bs*.bin $(1)/lib/firmware/rtlwifi -endef -$(eval $(call BuildPackage,rtl8723bs-firmware)) - Package/rtl8821ae-firmware = $(call Package/firmware-default,RealTek RTL8821AE firmware) define Package/rtl8821ae-firmware/install $(INSTALL_DIR) $(1)/lib/firmware/rtlwifi From 47a5b9744b99559f61f6bd3383605b9738ea225e Mon Sep 17 00:00:00 2001 From: Christian Lamparter Date: Sun, 19 Dec 2021 13:51:41 +0100 Subject: [PATCH 14/43] linux-firmware: amd: consolidate amd's linux-firmware entries this patch consolidates the amd64-microcode (moved to linux-firmware.git, previously this was an extra debian source package download), amdgpu and radeon firmwares into a shared "amd" makefile. this will include a microcode update for ZEN 3 CPUs that came with the 20211216 linux-firmware bump. Signed-off-by: Christian Lamparter (cherry picked from commit cf8ee49c9bd37ea3e17abe710353737e0f5f9608) --- package/firmware/amd64-microcode/Makefile | 47 ----------------------- package/firmware/linux-firmware/amd.mk | 29 ++++++++++++++ package/firmware/linux-firmware/amdgpu.mk | 9 ----- package/firmware/linux-firmware/radeon.mk | 9 ----- 4 files changed, 29 insertions(+), 65 deletions(-) delete mode 100644 package/firmware/amd64-microcode/Makefile create mode 100644 package/firmware/linux-firmware/amd.mk delete mode 100644 package/firmware/linux-firmware/amdgpu.mk delete mode 100644 package/firmware/linux-firmware/radeon.mk diff --git a/package/firmware/amd64-microcode/Makefile b/package/firmware/amd64-microcode/Makefile deleted file mode 100644 index 217d99acdd..0000000000 --- a/package/firmware/amd64-microcode/Makefile +++ /dev/null @@ -1,47 +0,0 @@ -# -# Copyright (C) 2018 OpenWrt.org -# -# This is free software, licensed under the GNU General Public License v2. -# See /LICENSE for more information. -# - -include $(TOPDIR)/rules.mk - -PKG_NAME:=amd64-microcode -PKG_VERSION:=20191218 -PKG_RELEASE:=1 - -PKG_SOURCE:=amd64-microcode_3.$(PKG_VERSION).$(PKG_RELEASE).tar.xz -PKG_SOURCE_URL:=http://ftp.debian.org/debian/pool/non-free/a/amd64-microcode/ -PKG_HASH:=f469b79348097c5f04641b67a39d0ee5a2a1916c9556281626c04f2275d4132d -PKG_BUILD_DIR:=$(BUILD_DIR)/$(PKG_NAME)-3.$(PKG_VERSION).$(PKG_RELEASE) - -PKG_LICENSE_FILE:=LICENSE.amd-ucode - -PKG_FLAGS:=nonshared - -include $(INCLUDE_DIR)/package.mk - -define Package/amd64-microcode - SECTION:=firmware - CATEGORY:=Firmware - URL:=$(PKG_SOURCE_URL) - DEPENDS:=@TARGET_x86 - TITLE:=AMD64 CPU microcode -endef - -define Build/Prepare - rm -rf $(PKG_BUILD_DIR) - mkdir -p $(PKG_BUILD_DIR) - $(TAR) -C $(BUILD_DIR) -xJf $(DL_DIR)/$(PKG_SOURCE) -endef - -define Build/Compile -endef - -define Package/amd64-microcode/install - $(INSTALL_DIR) $(1)/lib/firmware/amd-ucode - $(INSTALL_DATA) $(PKG_BUILD_DIR)/*.bin $(1)/lib/firmware/amd-ucode -endef - -$(eval $(call BuildPackage,amd64-microcode)) diff --git a/package/firmware/linux-firmware/amd.mk b/package/firmware/linux-firmware/amd.mk new file mode 100644 index 0000000000..68b305e862 --- /dev/null +++ b/package/firmware/linux-firmware/amd.mk @@ -0,0 +1,29 @@ +Package/amd64-microcode = $(call Package/firmware-default,AMD64 CPU microcode,@TARGET_x86) +define Package/amd64-microcode/install + $(INSTALL_DIR) $(1)/lib/firmware/amd-ucode + $(CP) \ + $(PKG_BUILD_DIR)/amd-ucode/*.bin \ + $(1)/lib/firmware/amd-ucode +endef + +$(eval $(call BuildPackage,amd64-microcode)) + +Package/amdgpu-firmware = $(call Package/firmware-default,AMDGPU Video Driver firmware) +define Package/amdgpu-firmware/install + $(INSTALL_DIR) $(1)/lib/firmware/amdgpu + $(CP) \ + $(PKG_BUILD_DIR)/amdgpu/*.bin \ + $(1)/lib/firmware/amdgpu +endef + +$(eval $(call BuildPackage,amdgpu-firmware)) + +Package/radeon-firmware = $(call Package/firmware-default,Radeon Video Driver firmware) +define Package/radeon-firmware/install + $(INSTALL_DIR) $(1)/lib/firmware/radeon + $(CP) \ + $(PKG_BUILD_DIR)/radeon/*.bin \ + $(1)/lib/firmware/radeon +endef + +$(eval $(call BuildPackage,radeon-firmware)) diff --git a/package/firmware/linux-firmware/amdgpu.mk b/package/firmware/linux-firmware/amdgpu.mk deleted file mode 100644 index 89f11e7c39..0000000000 --- a/package/firmware/linux-firmware/amdgpu.mk +++ /dev/null @@ -1,9 +0,0 @@ -Package/amdgpu-firmware = $(call Package/firmware-default,AMDGPU Video Driver firmware) -define Package/amdgpu-firmware/install - $(INSTALL_DIR) $(1)/lib/firmware/amdgpu - $(CP) \ - $(PKG_BUILD_DIR)/amdgpu/*.bin \ - $(1)/lib/firmware/amdgpu -endef - -$(eval $(call BuildPackage,amdgpu-firmware)) diff --git a/package/firmware/linux-firmware/radeon.mk b/package/firmware/linux-firmware/radeon.mk deleted file mode 100644 index b750efbfce..0000000000 --- a/package/firmware/linux-firmware/radeon.mk +++ /dev/null @@ -1,9 +0,0 @@ -Package/radeon-firmware = $(call Package/firmware-default,Radeon Video Driver firmware) -define Package/radeon-firmware/install - $(INSTALL_DIR) $(1)/lib/firmware/radeon - $(CP) \ - $(PKG_BUILD_DIR)/radeon/*.bin \ - $(1)/lib/firmware/radeon -endef - -$(eval $(call BuildPackage,radeon-firmware)) From 4dddb7ca3669e93d4da2b1ca43b8bc22bd007e48 Mon Sep 17 00:00:00 2001 From: Hauke Mehrtens Date: Sun, 26 Dec 2021 23:38:52 +0100 Subject: [PATCH 15/43] tcpdump: libpcap: Remove http://www.us.tcpdump.org mirror The http://www.us.tcpdump.org mirror will go offline soon, only use the normal download URL. Reported-by: Denis Ovsienko Signed-off-by: Hauke Mehrtens (cherry picked from commit 18bdfc803bef00fad03f90b73b6e65c3c79cb397) Signed-off-by: Josef Schlehofer [rebased for OpenWrt 21.02 branch] --- package/libs/libpcap/Makefile | 3 +-- package/network/utils/tcpdump/Makefile | 3 +-- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/package/libs/libpcap/Makefile b/package/libs/libpcap/Makefile index 8586300d75..ea82536e9d 100644 --- a/package/libs/libpcap/Makefile +++ b/package/libs/libpcap/Makefile @@ -12,8 +12,7 @@ PKG_VERSION:=1.9.1 PKG_RELEASE:=3.1 PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz -PKG_SOURCE_URL:=http://www.us.tcpdump.org/release/ \ - http://www.tcpdump.org/release/ +PKG_SOURCE_URL:=http://www.tcpdump.org/release/ PKG_HASH:=635237637c5b619bcceba91900666b64d56ecb7be63f298f601ec786ce087094 PKG_MAINTAINER:=Felix Fietkau diff --git a/package/network/utils/tcpdump/Makefile b/package/network/utils/tcpdump/Makefile index f333cf98d2..a14fb9a1b7 100644 --- a/package/network/utils/tcpdump/Makefile +++ b/package/network/utils/tcpdump/Makefile @@ -12,8 +12,7 @@ PKG_VERSION:=4.9.3 PKG_RELEASE:=3 PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz -PKG_SOURCE_URL:=http://www.us.tcpdump.org/release/ \ - http://www.tcpdump.org/release/ +PKG_SOURCE_URL:=http://www.tcpdump.org/release/ PKG_HASH:=2cd47cb3d460b6ff75f4a9940f594317ad456cfbf2bd2c8e5151e16559db6410 PKG_MAINTAINER:=Felix Fietkau From 3b14ddf8d204ee59533ec76ed6018db01f77d6e7 Mon Sep 17 00:00:00 2001 From: Alexander Egorenkov Date: Sat, 10 Apr 2021 01:32:44 +0200 Subject: [PATCH 16/43] build: fix opkg install step for large package selection When the list of packages to be installed in a built image exceeds a certain number, then 'opkg install' executed for target '$(curdir)/install' in package/Makefile fails with: /usr/bin/env: Argument list too long. On Linux, the length of a command-line parameter is limited by MAX_ARG_STRLEN to max 128 kB. * https://elixir.bootlin.com/linux/latest/source/include/uapi/linux/binfmts.h#L15 * https://www.in-ulm.de/~mascheck/various/argmax/ To solve the problem, store the package list being passed to 'opkg install' in a temporary file and use the shell command substitution to pass the content of the file to 'opkg install'. This guarantees that the length of the command-line parameters passed to the bash shell is short. The following bash script demonstrates the problem: ---------------------------------------------------------------------------- count=${1:-1000} FILES="" a_file="/home/egorenar/Repositories/openwrt-rel/bin/targets/alpine/generic/packages/base-files_1414-r16464+19-e887049fbb_arm_cortex-a15_neon-vfpv4.ipk" for i in $(seq 1 $count); do FILES="$FILES $a_file" done env bash -c "echo $FILES >/dev/null" echo "$FILES" | wc -c ---------------------------------------------------------------------------- Test run: ---------------------------------------------------------------------------- $ ./test.sh 916 130989 $ ./test.sh 917 ./test.sh: line 14: /bin/env: Argument list too long 131132 ---------------------------------------------------------------------------- Signed-off-by: Alexander Egorenkov [reword commit subject] Signed-off-by: Paul Spooren (cherry picked from commit 1854aeec4d37079690309dec3171d0864339f73a) --- package/Makefile | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/package/Makefile b/package/Makefile index ec503dc527..209be34674 100644 --- a/package/Makefile +++ b/package/Makefile @@ -66,8 +66,10 @@ $(curdir)/install: $(TMP_DIR)/.build $(curdir)/merge $(if $(CONFIG_TARGET_PER_DE - find $(STAGING_DIR_ROOT) -type d | $(XARGS) chmod 0755 rm -rf $(TARGET_DIR) $(TARGET_DIR_ORIG) mkdir -p $(TARGET_DIR)/tmp - $(call opkg,$(TARGET_DIR)) install \ - $(call opkg_package_files,$(foreach pkg,$(shell cat $(PACKAGE_INSTALL_FILES) 2>/dev/null),$(pkg)$(call GetABISuffix,$(pkg)))) + $(file >$(TMP_DIR)/opkg_install_list,\ + $(call opkg_package_files,\ + $(foreach pkg,$(shell cat $(PACKAGE_INSTALL_FILES) 2>/dev/null),$(pkg)$(call GetABISuffix,$(pkg))))) + $(call opkg,$(TARGET_DIR)) install $$(cat $(TMP_DIR)/opkg_install_list) @for file in $(PACKAGE_INSTALL_FILES); do \ [ -s $$file.flags ] || continue; \ for flag in `cat $$file.flags`; do \ From 99a1e882970f02d3713b3d67022af012b782a5f4 Mon Sep 17 00:00:00 2001 From: Daniel Golle Date: Tue, 21 Dec 2021 16:27:16 +0000 Subject: [PATCH 17/43] mvebu: puzzle-m902: add driver for MCU driving LEDs, fan and buzzer Backport MFD driver for communicating with the on-board MCU found on IEI World Puzzle appliances. Improve the driver to support multiple LEDs, apply a default state and let MCU take care of blinking if timing is within supported range. Wire up LEDs and fan for Puzzle M902 in device tree. Signed-off-by: Daniel Golle (cherry picked from commit f0c0b18234418c6ed6d35fcf1c6e5b0cbdceed49 with commit 962c58558010bd302793ac24284c4f9db8fe287f squashed) --- target/linux/mvebu/cortexa72/config-5.4 | 6 + .../boot/dts/marvell/cn9132-puzzle-m902.dts | 74 +- ...IEI-vendor-prefix-and-IEI-WT61P803-P.patch | 218 ++++ ...a-driver-for-IEI-WT61P803-PUZZLE-MCU.patch | 1034 +++++++++++++++++ ...d-the-IEI-WT61P803-PUZZLE-HWMON-driv.patch | 469 ++++++++ ...d-the-IEI-WT61P803-PUZZLE-LED-driver.patch | 207 ++++ ...I-Add-iei-wt61p803-puzzle-driver-sys.patch | 82 ++ ...mon-Add-iei-wt61p803-puzzle-hwmon-dr.patch | 74 ++ ...an-entry-for-the-IEI-WT61P803-PUZZLE.patch | 41 + ...rs-leds-wt61p803-puzzle-improvements.patch | 247 ++++ 10 files changed, 2451 insertions(+), 1 deletion(-) create mode 100644 target/linux/mvebu/patches-5.4/901-dt-bindings-Add-IEI-vendor-prefix-and-IEI-WT61P803-P.patch create mode 100644 target/linux/mvebu/patches-5.4/902-drivers-mfd-Add-a-driver-for-IEI-WT61P803-PUZZLE-MCU.patch create mode 100644 target/linux/mvebu/patches-5.4/903-drivers-hwmon-Add-the-IEI-WT61P803-PUZZLE-HWMON-driv.patch create mode 100644 target/linux/mvebu/patches-5.4/904-drivers-leds-Add-the-IEI-WT61P803-PUZZLE-LED-driver.patch create mode 100644 target/linux/mvebu/patches-5.4/905-Documentation-ABI-Add-iei-wt61p803-puzzle-driver-sys.patch create mode 100644 target/linux/mvebu/patches-5.4/906-Documentation-hwmon-Add-iei-wt61p803-puzzle-hwmon-dr.patch create mode 100644 target/linux/mvebu/patches-5.4/907-MAINTAINERS-Add-an-entry-for-the-IEI-WT61P803-PUZZLE.patch create mode 100644 target/linux/mvebu/patches-5.4/910-drivers-leds-wt61p803-puzzle-improvements.patch diff --git a/target/linux/mvebu/cortexa72/config-5.4 b/target/linux/mvebu/cortexa72/config-5.4 index 5727ae5918..106724dc3b 100644 --- a/target/linux/mvebu/cortexa72/config-5.4 +++ b/target/linux/mvebu/cortexa72/config-5.4 @@ -130,7 +130,9 @@ CONFIG_INLINE_WRITE_LOCK_IRQ=y CONFIG_INLINE_WRITE_LOCK_IRQSAVE=y CONFIG_INLINE_WRITE_UNLOCK_BH=y CONFIG_INLINE_WRITE_UNLOCK_IRQRESTORE=y +CONFIG_LEDS_IEI_WT61P803_PUZZLE=y CONFIG_MARVELL_10G_PHY=y +CONFIG_MFD_IEI_WT61P803_PUZZLE=y CONFIG_MFD_SYSCON=y CONFIG_MMC_SDHCI_XENON=y CONFIG_MODULES_USE_ELF_RELA=y @@ -161,7 +163,11 @@ CONFIG_QUEUED_RWLOCKS=y CONFIG_QUEUED_SPINLOCKS=y # CONFIG_RANDOMIZE_BASE is not set CONFIG_RAS=y +# CONFIG_RAVE_SP_CORE is not set CONFIG_REGULATOR_GPIO=y +CONFIG_SENSORS_IEI_WT61P803_PUZZLE_HWMON=y +CONFIG_SERIAL_DEV_BUS=y +CONFIG_SERIAL_DEV_CTRL_TTYPORT=y # CONFIG_SERIAL_AMBA_PL011 is not set CONFIG_SPARSEMEM=y CONFIG_SPARSEMEM_EXTREME=y diff --git a/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts b/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts index dc4e6527f1..8d2d53d03c 100644 --- a/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts +++ b/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts @@ -38,7 +38,10 @@ ethernet8 = &cp2_eth2; spi1 = &cp0_spi0; spi2 = &cp0_spi1; - serial1 = &cp0_uart0; + led-boot = &led_power; + led-failsafe = &led_info; + led-running = &led_power; + led-upgrade = &led_info; }; memory@00000000 { @@ -91,6 +94,75 @@ &cp0_uart0 { status = "okay"; + + puzzle-mcu { + compatible = "iei,wt61p803-puzzle"; + #address-cells = <1>; + #size-cells = <1>; + current-speed = <115200>; + enable-beep; + status = "okay"; + + leds { + compatible = "iei,wt61p803-puzzle-leds"; + #address-cells = <1>; + #size-cells = <0>; + status = "okay"; + + led@0 { + reg = <0>; + label = "white:network"; + active-low; + }; + + led@1 { + reg = <1>; + label = "green:cloud"; + active-low; + }; + + led_info: led@2 { + reg = <2>; + label = "orange:info"; + active-low; + }; + + led_power: led@3 { + reg = <3>; + label = "yellow:power"; + active-low; + default-state = "on"; + }; + }; + + hwmon { + compatible = "iei,wt61p803-puzzle-hwmon"; + #address-cells = <1>; + #size-cells = <0>; + + chassis_fan_group0: fan-group@0 { + #cooling-cells = <2>; + reg = <0x00>; + cooling-levels = <64 102 170 230 250>; + }; + }; + }; +}; + +&ap_thermal_cpu1 { + trips { + cpu_active: cpu-active { + temperature = <44000>; + hysteresis = <2000>; + type = "active"; + }; + }; + cooling-maps { + fan-map { + trip = <&cpu_active>; + cooling-device = <&chassis_fan_group0 64 THERMAL_NO_LIMIT>; + }; + }; }; /* on-board eMMC - U9 */ diff --git a/target/linux/mvebu/patches-5.4/901-dt-bindings-Add-IEI-vendor-prefix-and-IEI-WT61P803-P.patch b/target/linux/mvebu/patches-5.4/901-dt-bindings-Add-IEI-vendor-prefix-and-IEI-WT61P803-P.patch new file mode 100644 index 0000000000..fb9ea43e4b --- /dev/null +++ b/target/linux/mvebu/patches-5.4/901-dt-bindings-Add-IEI-vendor-prefix-and-IEI-WT61P803-P.patch @@ -0,0 +1,218 @@ +From aa4a0ccc41997f2da172165c92803abace43bd1c Mon Sep 17 00:00:00 2001 +From: Luka Kovacic +Date: Tue, 24 Aug 2021 12:44:32 +0000 +Subject: [PATCH 1/7] dt-bindings: Add IEI vendor prefix and IEI WT61P803 + PUZZLE driver bindings + +Add the IEI WT61P803 PUZZLE Device Tree bindings for MFD, HWMON and LED +drivers. A new vendor prefix is also added accordingly for +IEI Integration Corp. + +Signed-off-by: Luka Kovacic +Signed-off-by: Pavo Banicevic +Cc: Luka Perkov +Cc: Robert Marko +--- + .../hwmon/iei,wt61p803-puzzle-hwmon.yaml | 53 ++++++++++++ + .../leds/iei,wt61p803-puzzle-leds.yaml | 39 +++++++++ + .../bindings/mfd/iei,wt61p803-puzzle.yaml | 82 +++++++++++++++++++ + .../devicetree/bindings/vendor-prefixes.yaml | 2 + + 4 files changed, 176 insertions(+) + create mode 100644 Documentation/devicetree/bindings/hwmon/iei,wt61p803-puzzle-hwmon.yaml + create mode 100644 Documentation/devicetree/bindings/leds/iei,wt61p803-puzzle-leds.yaml + create mode 100644 Documentation/devicetree/bindings/mfd/iei,wt61p803-puzzle.yaml + +--- /dev/null ++++ b/Documentation/devicetree/bindings/hwmon/iei,wt61p803-puzzle-hwmon.yaml +@@ -0,0 +1,53 @@ ++# SPDX-License-Identifier: GPL-2.0-only OR BSD-2-Clause ++%YAML 1.2 ++--- ++$id: http://devicetree.org/schemas/hwmon/iei,wt61p803-puzzle-hwmon.yaml# ++$schema: http://devicetree.org/meta-schemas/core.yaml# ++ ++title: IEI WT61P803 PUZZLE MCU HWMON module from IEI Integration Corp. ++ ++maintainers: ++ - Luka Kovacic ++ ++description: | ++ This module is a part of the IEI WT61P803 PUZZLE MFD device. For more details ++ see Documentation/devicetree/bindings/mfd/iei,wt61p803-puzzle.yaml. ++ ++ The HWMON module is a sub-node of the MCU node in the Device Tree. ++ ++properties: ++ compatible: ++ const: iei,wt61p803-puzzle-hwmon ++ ++ "#address-cells": ++ const: 1 ++ ++ "#size-cells": ++ const: 0 ++ ++patternProperties: ++ "^fan-group@[0-1]$": ++ type: object ++ properties: ++ reg: ++ minimum: 0 ++ maximum: 1 ++ description: ++ Fan group ID ++ ++ cooling-levels: ++ minItems: 1 ++ maxItems: 255 ++ description: ++ Cooling levels for the fans (PWM value mapping) ++ description: | ++ Properties for each fan group. ++ required: ++ - reg ++ ++required: ++ - compatible ++ - "#address-cells" ++ - "#size-cells" ++ ++additionalProperties: false +--- /dev/null ++++ b/Documentation/devicetree/bindings/leds/iei,wt61p803-puzzle-leds.yaml +@@ -0,0 +1,39 @@ ++# SPDX-License-Identifier: GPL-2.0-only OR BSD-2-Clause ++%YAML 1.2 ++--- ++$id: http://devicetree.org/schemas/leds/iei,wt61p803-puzzle-leds.yaml# ++$schema: http://devicetree.org/meta-schemas/core.yaml# ++ ++title: IEI WT61P803 PUZZLE MCU LED module from IEI Integration Corp. ++ ++maintainers: ++ - Luka Kovacic ++ ++description: | ++ This module is a part of the IEI WT61P803 PUZZLE MFD device. For more details ++ see Documentation/devicetree/bindings/mfd/iei,wt61p803-puzzle.yaml. ++ ++ The LED module is a sub-node of the MCU node in the Device Tree. ++ ++properties: ++ compatible: ++ const: iei,wt61p803-puzzle-leds ++ ++ "#address-cells": ++ const: 1 ++ ++ "#size-cells": ++ const: 0 ++ ++ led@0: ++ type: object ++ $ref: common.yaml ++ description: | ++ Properties for a single LED. ++ ++required: ++ - compatible ++ - "#address-cells" ++ - "#size-cells" ++ ++additionalProperties: false +--- /dev/null ++++ b/Documentation/devicetree/bindings/mfd/iei,wt61p803-puzzle.yaml +@@ -0,0 +1,82 @@ ++# SPDX-License-Identifier: GPL-2.0-only OR BSD-2-Clause ++%YAML 1.2 ++--- ++$id: http://devicetree.org/schemas/mfd/iei,wt61p803-puzzle.yaml# ++$schema: http://devicetree.org/meta-schemas/core.yaml# ++ ++title: IEI WT61P803 PUZZLE MCU from IEI Integration Corp. ++ ++maintainers: ++ - Luka Kovacic ++ ++description: | ++ IEI WT61P803 PUZZLE MCU is embedded in some IEI Puzzle series boards. ++ It's used for controlling system power states, fans, LEDs and temperature ++ sensors. ++ ++ For Device Tree bindings of other sub-modules (HWMON, LEDs) refer to the ++ binding documents under the respective subsystem directories. ++ ++properties: ++ compatible: ++ const: iei,wt61p803-puzzle ++ ++ current-speed: ++ description: ++ Serial bus speed in bps ++ maxItems: 1 ++ ++ enable-beep: true ++ ++ hwmon: ++ $ref: /schemas/hwmon/iei,wt61p803-puzzle-hwmon.yaml ++ ++ leds: ++ $ref: /schemas/leds/iei,wt61p803-puzzle-leds.yaml ++ ++required: ++ - compatible ++ - current-speed ++ ++additionalProperties: false ++ ++examples: ++ - | ++ #include ++ serial { ++ mcu { ++ compatible = "iei,wt61p803-puzzle"; ++ current-speed = <115200>; ++ enable-beep; ++ ++ leds { ++ compatible = "iei,wt61p803-puzzle-leds"; ++ #address-cells = <1>; ++ #size-cells = <0>; ++ ++ led@0 { ++ reg = <0>; ++ function = LED_FUNCTION_POWER; ++ color = ; ++ }; ++ }; ++ ++ hwmon { ++ compatible = "iei,wt61p803-puzzle-hwmon"; ++ #address-cells = <1>; ++ #size-cells = <0>; ++ ++ fan-group@0 { ++ #cooling-cells = <2>; ++ reg = <0x00>; ++ cooling-levels = <64 102 170 230 250>; ++ }; ++ ++ fan-group@1 { ++ #cooling-cells = <2>; ++ reg = <0x01>; ++ cooling-levels = <64 102 170 230 250>; ++ }; ++ }; ++ }; ++ }; +--- a/Documentation/devicetree/bindings/vendor-prefixes.yaml ++++ b/Documentation/devicetree/bindings/vendor-prefixes.yaml +@@ -423,6 +423,8 @@ patternProperties: + description: IC Plus Corp. + "^idt,.*": + description: Integrated Device Technologies, Inc. ++ "^iei,.*": ++ description: IEI Integration Corp. + "^ifi,.*": + description: Ingenieurburo Fur Ic-Technologie (I/F/I) + "^ilitek,.*": diff --git a/target/linux/mvebu/patches-5.4/902-drivers-mfd-Add-a-driver-for-IEI-WT61P803-PUZZLE-MCU.patch b/target/linux/mvebu/patches-5.4/902-drivers-mfd-Add-a-driver-for-IEI-WT61P803-PUZZLE-MCU.patch new file mode 100644 index 0000000000..194feee569 --- /dev/null +++ b/target/linux/mvebu/patches-5.4/902-drivers-mfd-Add-a-driver-for-IEI-WT61P803-PUZZLE-MCU.patch @@ -0,0 +1,1034 @@ +From 692cfa85272dd12995b427c0a7a585ced5d54f32 Mon Sep 17 00:00:00 2001 +From: Luka Kovacic +Date: Tue, 24 Aug 2021 12:44:33 +0000 +Subject: [PATCH 2/7] drivers: mfd: Add a driver for IEI WT61P803 PUZZLE MCU + +Add a driver for the IEI WT61P803 PUZZLE microcontroller, used in some +IEI Puzzle series devices. The microcontroller controls system power, +temperature sensors, fans and LEDs. + +This driver implements the core functionality for device communication +over the system serial (serdev bus). It handles MCU messages and the +internal MCU properties. Some properties can be managed over sysfs. + +Signed-off-by: Luka Kovacic +Signed-off-by: Pavo Banicevic +Cc: Luka Perkov +Cc: Robert Marko +--- + drivers/mfd/Kconfig | 8 + + drivers/mfd/Makefile | 1 + + drivers/mfd/iei-wt61p803-puzzle.c | 908 ++++++++++++++++++++++++ + include/linux/mfd/iei-wt61p803-puzzle.h | 66 ++ + 4 files changed, 983 insertions(+) + create mode 100644 drivers/mfd/iei-wt61p803-puzzle.c + create mode 100644 include/linux/mfd/iei-wt61p803-puzzle.h + +--- a/drivers/mfd/Kconfig ++++ b/drivers/mfd/Kconfig +@@ -531,6 +531,15 @@ config LPC_SCH + LPC bridge function of the Intel SCH provides support for + System Management Bus and General Purpose I/O. + ++config MFD_IEI_WT61P803_PUZZLE ++ tristate "IEI WT61P803 PUZZLE MCU driver" ++ depends on SERIAL_DEV_BUS ++ select MFD_CORE ++ help ++ IEI WT61P803 PUZZLE is a system power management microcontroller ++ used for fan control, temperature sensor reading, LED control ++ and system identification. ++ + config INTEL_SOC_PMIC + bool "Support for Crystal Cove PMIC" + depends on ACPI && HAS_IOMEM && I2C=y && GPIOLIB && COMMON_CLK +--- a/drivers/mfd/Makefile ++++ b/drivers/mfd/Makefile +@@ -232,6 +232,7 @@ obj-$(CONFIG_MFD_HI655X_PMIC) += hi655 + obj-$(CONFIG_MFD_DLN2) += dln2.o + obj-$(CONFIG_MFD_RT5033) += rt5033.o + obj-$(CONFIG_MFD_SKY81452) += sky81452.o ++obj-$(CONFIG_MFD_IEI_WT61P803_PUZZLE) += iei-wt61p803-puzzle.o + + intel-soc-pmic-objs := intel_soc_pmic_core.o intel_soc_pmic_crc.o + obj-$(CONFIG_INTEL_SOC_PMIC) += intel-soc-pmic.o +--- /dev/null ++++ b/drivers/mfd/iei-wt61p803-puzzle.c +@@ -0,0 +1,908 @@ ++// SPDX-License-Identifier: GPL-2.0-only ++/* IEI WT61P803 PUZZLE MCU Driver ++ * System management microcontroller for fan control, temperature sensor reading, ++ * LED control and system identification on IEI Puzzle series ARM-based appliances. ++ * ++ * Copyright (C) 2020 Sartura Ltd. ++ * Author: Luka Kovacic ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++/* start, payload and XOR checksum at end */ ++#define IEI_WT61P803_PUZZLE_MAX_COMMAND_LENGTH (1 + 20 + 1) ++#define IEI_WT61P803_PUZZLE_RESP_BUF_SIZE 512 ++ ++#define IEI_WT61P803_PUZZLE_MAC_LENGTH 17 ++#define IEI_WT61P803_PUZZLE_SN_LENGTH 36 ++#define IEI_WT61P803_PUZZLE_VERSION_LENGTH 6 ++#define IEI_WT61P803_PUZZLE_BUILD_INFO_LENGTH 16 ++#define IEI_WT61P803_PUZZLE_PROTOCOL_VERSION_LENGTH 8 ++#define IEI_WT61P803_PUZZLE_NB_MAC 8 ++ ++/* Use HZ as a timeout value throughout the driver */ ++#define IEI_WT61P803_PUZZLE_GENERAL_TIMEOUT HZ ++ ++enum iei_wt61p803_puzzle_attribute_type { ++ IEI_WT61P803_PUZZLE_VERSION, ++ IEI_WT61P803_PUZZLE_BUILD_INFO, ++ IEI_WT61P803_PUZZLE_BOOTLOADER_MODE, ++ IEI_WT61P803_PUZZLE_PROTOCOL_VERSION, ++ IEI_WT61P803_PUZZLE_SERIAL_NUMBER, ++ IEI_WT61P803_PUZZLE_MAC_ADDRESS, ++ IEI_WT61P803_PUZZLE_AC_RECOVERY_STATUS, ++ IEI_WT61P803_PUZZLE_POWER_LOSS_RECOVERY, ++ IEI_WT61P803_PUZZLE_POWER_STATUS, ++}; ++ ++struct iei_wt61p803_puzzle_device_attribute { ++ struct device_attribute dev_attr; ++ enum iei_wt61p803_puzzle_attribute_type type; ++ u8 index; ++}; ++ ++/** ++ * struct iei_wt61p803_puzzle_mcu_status - MCU flags state ++ * @ac_recovery_status_flag: AC Recovery Status Flag ++ * @power_loss_recovery: System recovery after power loss ++ * @power_status: System Power-on Method ++ */ ++struct iei_wt61p803_puzzle_mcu_status { ++ u8 ac_recovery_status_flag; ++ u8 power_loss_recovery; ++ u8 power_status; ++}; ++ ++/** ++ * struct iei_wt61p803_puzzle_reply - MCU reply ++ * @size: Size of the MCU reply ++ * @data: Full MCU reply buffer ++ * @state: Current state of the packet ++ * @received: Was the response fullfilled ++ */ ++struct iei_wt61p803_puzzle_reply { ++ size_t size; ++ unsigned char data[IEI_WT61P803_PUZZLE_RESP_BUF_SIZE]; ++ struct completion received; ++}; ++ ++/** ++ * struct iei_wt61p803_puzzle_mcu_version - MCU version status ++ * @version: Primary firmware version ++ * @build_info: Build date and time ++ * @bootloader_mode: Status of the MCU operation ++ * @protocol_version: MCU communication protocol version ++ * @serial_number: Device factory serial number ++ * @mac_address: Device factory MAC addresses ++ * ++ * Last element of arrays is reserved for '\0'. ++ */ ++struct iei_wt61p803_puzzle_mcu_version { ++ char version[IEI_WT61P803_PUZZLE_VERSION_LENGTH + 1]; ++ char build_info[IEI_WT61P803_PUZZLE_BUILD_INFO_LENGTH + 1]; ++ bool bootloader_mode; ++ char protocol_version[IEI_WT61P803_PUZZLE_PROTOCOL_VERSION_LENGTH + 1]; ++ char serial_number[IEI_WT61P803_PUZZLE_SN_LENGTH + 1]; ++ char mac_address[IEI_WT61P803_PUZZLE_NB_MAC][IEI_WT61P803_PUZZLE_MAC_LENGTH + 1]; ++}; ++ ++/** ++ * struct iei_wt61p803_puzzle - IEI WT61P803 PUZZLE MCU Driver ++ * @serdev: Pointer to underlying serdev device ++ * @dev: Pointer to underlying dev device ++ * @reply_lock: Reply mutex lock ++ * @reply: Pointer to the iei_wt61p803_puzzle_reply struct ++ * @version: MCU version related data ++ * @status: MCU status related data ++ * @response_buffer Command response buffer allocation ++ * @lock General member mutex lock ++ */ ++struct iei_wt61p803_puzzle { ++ struct serdev_device *serdev; ++ struct device *dev; ++ struct mutex reply_lock; /* lock to prevent multiple firmware calls */ ++ struct iei_wt61p803_puzzle_reply *reply; ++ struct iei_wt61p803_puzzle_mcu_version version; ++ struct iei_wt61p803_puzzle_mcu_status status; ++ unsigned char response_buffer[IEI_WT61P803_PUZZLE_BUF_SIZE]; ++ struct mutex lock; /* lock to protect response buffer */ ++}; ++ ++static unsigned char iei_wt61p803_puzzle_checksum(unsigned char *buf, size_t len) ++{ ++ unsigned char checksum = 0; ++ size_t i; ++ ++ for (i = 0; i < len; i++) ++ checksum ^= buf[i]; ++ return checksum; ++} ++ ++static int iei_wt61p803_puzzle_process_resp(struct iei_wt61p803_puzzle *mcu, ++ const unsigned char *raw_resp_data, size_t size) ++{ ++ unsigned char checksum; ++ ++ /* Check the incoming frame header */ ++ if (!(raw_resp_data[0] == IEI_WT61P803_PUZZLE_CMD_HEADER_START || ++ raw_resp_data[0] == IEI_WT61P803_PUZZLE_CMD_HEADER_START_OTHER || ++ (raw_resp_data[0] == IEI_WT61P803_PUZZLE_CMD_HEADER_EEPROM && ++ raw_resp_data[1] == IEI_WT61P803_PUZZLE_CMD_EEPROM_READ))) { ++ if (mcu->reply->size + size >= sizeof(mcu->reply->data)) ++ return -EIO; ++ ++ /* Append the frame to existing data */ ++ memcpy(mcu->reply->data + mcu->reply->size, raw_resp_data, size); ++ mcu->reply->size += size; ++ } else { ++ if (size >= sizeof(mcu->reply->data)) ++ return -EIO; ++ ++ /* Start processing a new frame */ ++ memcpy(mcu->reply->data, raw_resp_data, size); ++ mcu->reply->size = size; ++ } ++ ++ checksum = iei_wt61p803_puzzle_checksum(mcu->reply->data, mcu->reply->size - 1); ++ if (checksum != mcu->reply->data[mcu->reply->size - 1]) { ++ /* The checksum isn't matched yet, wait for new frames */ ++ return size; ++ } ++ ++ /* Received all the data */ ++ complete(&mcu->reply->received); ++ ++ return size; ++} ++ ++static int iei_wt61p803_puzzle_recv_buf(struct serdev_device *serdev, ++ const unsigned char *data, size_t size) ++{ ++ struct iei_wt61p803_puzzle *mcu = serdev_device_get_drvdata(serdev); ++ int ret; ++ ++ ret = iei_wt61p803_puzzle_process_resp(mcu, data, size); ++ /* Return the number of processed bytes if function returns error, ++ * discard the remaining incoming data, since the frame this data ++ * belongs to is broken anyway ++ */ ++ if (ret < 0) ++ return size; ++ ++ return ret; ++} ++ ++static const struct serdev_device_ops iei_wt61p803_puzzle_serdev_device_ops = { ++ .receive_buf = iei_wt61p803_puzzle_recv_buf, ++ .write_wakeup = serdev_device_write_wakeup, ++}; ++ ++/** ++ * iei_wt61p803_puzzle_write_command_watchdog() - Watchdog of the normal cmd ++ * @mcu: Pointer to the iei_wt61p803_puzzle core MFD struct ++ * @cmd: Pointer to the char array to send (size should be content + 1 (xor)) ++ * @size: Size of the cmd char array ++ * @reply_data: Pointer to the reply/response data array (should be allocated) ++ * @reply_size: Pointer to size_t (size of reply_data) ++ * @retry_count: Number of times to retry sending the command to the MCU ++ */ ++int iei_wt61p803_puzzle_write_command_watchdog(struct iei_wt61p803_puzzle *mcu, ++ unsigned char *cmd, size_t size, ++ unsigned char *reply_data, ++ size_t *reply_size, int retry_count) ++{ ++ struct device *dev = &mcu->serdev->dev; ++ int ret, i; ++ ++ for (i = 0; i < retry_count; i++) { ++ ret = iei_wt61p803_puzzle_write_command(mcu, cmd, size, ++ reply_data, reply_size); ++ if (ret != -ETIMEDOUT) ++ return ret; ++ } ++ ++ dev_err(dev, "Command response timed out. Retries: %d\n", retry_count); ++ ++ return -ETIMEDOUT; ++} ++EXPORT_SYMBOL_GPL(iei_wt61p803_puzzle_write_command_watchdog); ++ ++/** ++ * iei_wt61p803_puzzle_write_command() - Send a structured command to the MCU ++ * @mcu: Pointer to the iei_wt61p803_puzzle core MFD struct ++ * @cmd: Pointer to the char array to send (size should be content + 1 (xor)) ++ * @size: Size of the cmd char array ++ * @reply_data: Pointer to the reply/response data array (should be allocated) ++ * ++ * Sends a structured command to the MCU. ++ */ ++int iei_wt61p803_puzzle_write_command(struct iei_wt61p803_puzzle *mcu, ++ unsigned char *cmd, size_t size, ++ unsigned char *reply_data, ++ size_t *reply_size) ++{ ++ struct device *dev = &mcu->serdev->dev; ++ int ret; ++ ++ if (size <= 1 || size > IEI_WT61P803_PUZZLE_MAX_COMMAND_LENGTH) ++ return -EINVAL; ++ ++ mutex_lock(&mcu->reply_lock); ++ ++ cmd[size - 1] = iei_wt61p803_puzzle_checksum(cmd, size - 1); ++ ++ /* Initialize reply struct */ ++ reinit_completion(&mcu->reply->received); ++ mcu->reply->size = 0; ++ usleep_range(2000, 10000); ++ serdev_device_write_flush(mcu->serdev); ++ ret = serdev_device_write_buf(mcu->serdev, cmd, size); ++ if (ret < 0) ++ goto exit; ++ ++ serdev_device_wait_until_sent(mcu->serdev, IEI_WT61P803_PUZZLE_GENERAL_TIMEOUT); ++ ret = wait_for_completion_timeout(&mcu->reply->received, ++ IEI_WT61P803_PUZZLE_GENERAL_TIMEOUT); ++ if (ret == 0) { ++ dev_err(dev, "Command reply receive timeout\n"); ++ ret = -ETIMEDOUT; ++ goto exit; ++ } ++ ++ *reply_size = mcu->reply->size; ++ /* Copy the received data, as it will not be available after a new frame is received */ ++ memcpy(reply_data, mcu->reply->data, mcu->reply->size); ++ ret = 0; ++exit: ++ mutex_unlock(&mcu->reply_lock); ++ return ret; ++} ++EXPORT_SYMBOL_GPL(iei_wt61p803_puzzle_write_command); ++ ++static int iei_wt61p803_puzzle_buzzer(struct iei_wt61p803_puzzle *mcu, bool long_beep) ++{ ++ unsigned char *resp_buf = mcu->response_buffer; ++ unsigned char buzzer_cmd[4] = {}; ++ size_t reply_size; ++ int ret; ++ ++ buzzer_cmd[0] = IEI_WT61P803_PUZZLE_CMD_HEADER_START; ++ buzzer_cmd[1] = IEI_WT61P803_PUZZLE_CMD_FUNCTION_SINGLE; ++ buzzer_cmd[2] = long_beep ? '3' : '2'; /* Buzzer 1.5 / 0.5 second beep */ ++ ++ mutex_lock(&mcu->lock); ++ ret = iei_wt61p803_puzzle_write_command(mcu, buzzer_cmd, sizeof(buzzer_cmd), ++ resp_buf, &reply_size); ++ if (ret) ++ goto exit; ++ ++ if (reply_size != 3) { ++ ret = -EIO; ++ goto exit; ++ } ++ ++ if (!(resp_buf[0] == IEI_WT61P803_PUZZLE_CMD_HEADER_START && ++ resp_buf[1] == IEI_WT61P803_PUZZLE_CMD_RESPONSE_OK && ++ resp_buf[2] == IEI_WT61P803_PUZZLE_CHECKSUM_RESPONSE_OK)) { ++ ret = -EPROTO; ++ goto exit; ++ } ++exit: ++ mutex_unlock(&mcu->lock); ++ return ret; ++} ++ ++static int iei_wt61p803_puzzle_get_version(struct iei_wt61p803_puzzle *mcu) ++{ ++ unsigned char version_cmd[3] = { ++ IEI_WT61P803_PUZZLE_CMD_HEADER_START_OTHER, ++ IEI_WT61P803_PUZZLE_CMD_OTHER_VERSION, ++ }; ++ unsigned char build_info_cmd[3] = { ++ IEI_WT61P803_PUZZLE_CMD_HEADER_START_OTHER, ++ IEI_WT61P803_PUZZLE_CMD_OTHER_BUILD, ++ }; ++ unsigned char bootloader_mode_cmd[3] = { ++ IEI_WT61P803_PUZZLE_CMD_HEADER_START_OTHER, ++ IEI_WT61P803_PUZZLE_CMD_OTHER_BOOTLOADER_MODE, ++ }; ++ unsigned char protocol_version_cmd[3] = { ++ IEI_WT61P803_PUZZLE_CMD_HEADER_START_OTHER, ++ IEI_WT61P803_PUZZLE_CMD_OTHER_PROTOCOL_VERSION, ++ }; ++ unsigned char *rb = mcu->response_buffer; ++ size_t reply_size; ++ int ret; ++ ++ mutex_lock(&mcu->lock); ++ ++ ret = iei_wt61p803_puzzle_write_command(mcu, version_cmd, sizeof(version_cmd), ++ rb, &reply_size); ++ if (ret) ++ goto err; ++ if (reply_size < 7) { ++ ret = -EIO; ++ goto err; ++ } ++ sprintf(mcu->version.version, "v%c.%.3s", rb[2], &rb[3]); ++ ++ ret = iei_wt61p803_puzzle_write_command(mcu, build_info_cmd, ++ sizeof(build_info_cmd), rb, ++ &reply_size); ++ if (ret) ++ goto err; ++ if (reply_size < 15) { ++ ret = -EIO; ++ goto err; ++ } ++ sprintf(mcu->version.build_info, "%c%c/%c%c/%.4s %c%c:%c%c", ++ rb[8], rb[9], rb[6], rb[7], &rb[2], rb[10], rb[11], ++ rb[12], rb[13]); ++ ++ ret = iei_wt61p803_puzzle_write_command(mcu, bootloader_mode_cmd, ++ sizeof(bootloader_mode_cmd), rb, ++ &reply_size); ++ if (ret) ++ goto err; ++ if (reply_size < 4) { ++ ret = -EIO; ++ goto err; ++ } ++ if (rb[2] == IEI_WT61P803_PUZZLE_CMD_OTHER_MODE_APPS) ++ mcu->version.bootloader_mode = false; ++ else if (rb[2] == IEI_WT61P803_PUZZLE_CMD_OTHER_MODE_BOOTLOADER) ++ mcu->version.bootloader_mode = true; ++ ++ ret = iei_wt61p803_puzzle_write_command(mcu, protocol_version_cmd, ++ sizeof(protocol_version_cmd), rb, ++ &reply_size); ++ if (ret) ++ goto err; ++ if (reply_size < 9) { ++ ret = -EIO; ++ goto err; ++ } ++ sprintf(mcu->version.protocol_version, "v%c.%c%c%c%c%c", ++ rb[7], rb[6], rb[5], rb[4], rb[3], rb[2]); ++err: ++ mutex_unlock(&mcu->lock); ++ return ret; ++} ++ ++static int iei_wt61p803_puzzle_get_mcu_status(struct iei_wt61p803_puzzle *mcu) ++{ ++ unsigned char mcu_status_cmd[5] = { ++ IEI_WT61P803_PUZZLE_CMD_HEADER_START, ++ IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER, ++ IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER_STATUS, ++ IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER_STATUS, ++ }; ++ unsigned char *resp_buf = mcu->response_buffer; ++ size_t reply_size; ++ int ret; ++ ++ mutex_lock(&mcu->lock); ++ ret = iei_wt61p803_puzzle_write_command(mcu, mcu_status_cmd, sizeof(mcu_status_cmd), ++ resp_buf, &reply_size); ++ if (ret) ++ goto exit; ++ if (reply_size < 20) { ++ ret = -EIO; ++ goto exit; ++ } ++ ++ /* Response format: ++ * (IDX RESPONSE) ++ * 0 @ ++ * 1 O ++ * 2 S ++ * 3 S ++ * ... ++ * 5 AC Recovery Status Flag ++ * ... ++ * 10 Power Loss Recovery ++ * ... ++ * 19 Power Status (system power on method) ++ * 20 XOR checksum ++ */ ++ if (resp_buf[0] == IEI_WT61P803_PUZZLE_CMD_HEADER_START && ++ resp_buf[1] == IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER && ++ resp_buf[2] == IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER_STATUS && ++ resp_buf[3] == IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER_STATUS) { ++ mcu->status.ac_recovery_status_flag = resp_buf[5]; ++ mcu->status.power_loss_recovery = resp_buf[10]; ++ mcu->status.power_status = resp_buf[19]; ++ } ++exit: ++ mutex_unlock(&mcu->lock); ++ return ret; ++} ++ ++static int iei_wt61p803_puzzle_get_serial_number(struct iei_wt61p803_puzzle *mcu) ++{ ++ unsigned char *resp_buf = mcu->response_buffer; ++ unsigned char serial_number_cmd[5] = { ++ IEI_WT61P803_PUZZLE_CMD_HEADER_EEPROM, ++ IEI_WT61P803_PUZZLE_CMD_EEPROM_READ, ++ 0x00, /* EEPROM read address */ ++ 0x24, /* Data length */ ++ }; ++ size_t reply_size; ++ int ret; ++ ++ mutex_lock(&mcu->lock); ++ ret = iei_wt61p803_puzzle_write_command(mcu, serial_number_cmd, ++ sizeof(serial_number_cmd), ++ resp_buf, &reply_size); ++ if (ret) ++ goto err; ++ ++ if (reply_size < IEI_WT61P803_PUZZLE_SN_LENGTH + 4) { ++ ret = -EIO; ++ goto err; ++ } ++ ++ sprintf(mcu->version.serial_number, "%.*s", ++ IEI_WT61P803_PUZZLE_SN_LENGTH, resp_buf + 4); ++err: ++ mutex_unlock(&mcu->lock); ++ return ret; ++} ++ ++static int iei_wt61p803_puzzle_write_serial_number(struct iei_wt61p803_puzzle *mcu, ++ unsigned char serial_number[36]) ++{ ++ unsigned char *resp_buf = mcu->response_buffer; ++ unsigned char serial_number_header[4] = { ++ IEI_WT61P803_PUZZLE_CMD_HEADER_EEPROM, ++ IEI_WT61P803_PUZZLE_CMD_EEPROM_WRITE, ++ 0x00, /* EEPROM write address */ ++ 0xC, /* Data length */ ++ }; ++ unsigned char serial_number_cmd[4 + 12 + 1]; /* header, serial number, XOR checksum */ ++ int ret, sn_counter; ++ size_t reply_size; ++ ++ /* The MCU can only handle 22 byte messages, send the S/N in 12 byte chunks */ ++ mutex_lock(&mcu->lock); ++ for (sn_counter = 0; sn_counter < 3; sn_counter++) { ++ serial_number_header[2] = 0x0 + 0xC * sn_counter; ++ ++ memcpy(serial_number_cmd, serial_number_header, sizeof(serial_number_header)); ++ memcpy(serial_number_cmd + sizeof(serial_number_header), ++ serial_number + 0xC * sn_counter, 0xC); ++ ++ ret = iei_wt61p803_puzzle_write_command(mcu, serial_number_cmd, ++ sizeof(serial_number_cmd), ++ resp_buf, &reply_size); ++ if (ret) ++ goto err; ++ if (reply_size != 3) { ++ ret = -EIO; ++ goto err; ++ } ++ if (!(resp_buf[0] == IEI_WT61P803_PUZZLE_CMD_HEADER_START && ++ resp_buf[1] == IEI_WT61P803_PUZZLE_CMD_RESPONSE_OK && ++ resp_buf[2] == IEI_WT61P803_PUZZLE_CHECKSUM_RESPONSE_OK)) { ++ ret = -EPROTO; ++ goto err; ++ } ++ } ++ ++ sprintf(mcu->version.serial_number, "%.*s", ++ IEI_WT61P803_PUZZLE_SN_LENGTH, serial_number); ++err: ++ mutex_unlock(&mcu->lock); ++ return ret; ++} ++ ++static int iei_wt61p803_puzzle_get_mac_address(struct iei_wt61p803_puzzle *mcu, int index) ++{ ++ unsigned char *resp_buf = mcu->response_buffer; ++ unsigned char mac_address_cmd[5] = { ++ IEI_WT61P803_PUZZLE_CMD_HEADER_EEPROM, ++ IEI_WT61P803_PUZZLE_CMD_EEPROM_READ, ++ 0x00, /* EEPROM read address */ ++ 0x11, /* Data length */ ++ }; ++ size_t reply_size; ++ int ret; ++ ++ mutex_lock(&mcu->lock); ++ mac_address_cmd[2] = 0x24 + 0x11 * index; ++ ++ ret = iei_wt61p803_puzzle_write_command(mcu, mac_address_cmd, ++ sizeof(mac_address_cmd), ++ resp_buf, &reply_size); ++ if (ret) ++ goto err; ++ ++ if (reply_size < 22) { ++ ret = -EIO; ++ goto err; ++ } ++ ++ sprintf(mcu->version.mac_address[index], "%.*s", ++ IEI_WT61P803_PUZZLE_MAC_LENGTH, resp_buf + 4); ++err: ++ mutex_unlock(&mcu->lock); ++ return ret; ++} ++ ++static int ++iei_wt61p803_puzzle_write_mac_address(struct iei_wt61p803_puzzle *mcu, ++ unsigned char mac_address[IEI_WT61P803_PUZZLE_MAC_LENGTH], ++ int mac_address_idx) ++{ ++ unsigned char mac_address_cmd[4 + IEI_WT61P803_PUZZLE_MAC_LENGTH + 1]; ++ unsigned char *resp_buf = mcu->response_buffer; ++ unsigned char mac_address_header[4] = { ++ IEI_WT61P803_PUZZLE_CMD_HEADER_EEPROM, ++ IEI_WT61P803_PUZZLE_CMD_EEPROM_WRITE, ++ 0x00, /* EEPROM write address */ ++ 0x11, /* Data length */ ++ }; ++ size_t reply_size; ++ int ret; ++ ++ if (mac_address_idx < 0 || mac_address_idx >= IEI_WT61P803_PUZZLE_NB_MAC) ++ return -EINVAL; ++ ++ mac_address_header[2] = 0x24 + 0x11 * mac_address_idx; ++ ++ /* Concat mac_address_header, mac_address to mac_address_cmd */ ++ memcpy(mac_address_cmd, mac_address_header, sizeof(mac_address_header)); ++ memcpy(mac_address_cmd + sizeof(mac_address_header), mac_address, ++ IEI_WT61P803_PUZZLE_MAC_LENGTH); ++ ++ mutex_lock(&mcu->lock); ++ ret = iei_wt61p803_puzzle_write_command(mcu, mac_address_cmd, ++ sizeof(mac_address_cmd), ++ resp_buf, &reply_size); ++ if (ret) ++ goto err; ++ if (reply_size != 3) { ++ ret = -EIO; ++ goto err; ++ } ++ if (!(resp_buf[0] == IEI_WT61P803_PUZZLE_CMD_HEADER_START && ++ resp_buf[1] == IEI_WT61P803_PUZZLE_CMD_RESPONSE_OK && ++ resp_buf[2] == IEI_WT61P803_PUZZLE_CHECKSUM_RESPONSE_OK)) { ++ ret = -EPROTO; ++ goto err; ++ } ++ ++ sprintf(mcu->version.mac_address[mac_address_idx], "%.*s", ++ IEI_WT61P803_PUZZLE_MAC_LENGTH, mac_address); ++err: ++ mutex_unlock(&mcu->lock); ++ return ret; ++} ++ ++static int iei_wt61p803_puzzle_write_power_loss_recovery(struct iei_wt61p803_puzzle *mcu, ++ int power_loss_recovery_action) ++{ ++ unsigned char *resp_buf = mcu->response_buffer; ++ unsigned char power_loss_recovery_cmd[5] = {}; ++ size_t reply_size; ++ int ret; ++ ++ if (power_loss_recovery_action < 0 || power_loss_recovery_action > 4) ++ return -EINVAL; ++ ++ power_loss_recovery_cmd[0] = IEI_WT61P803_PUZZLE_CMD_HEADER_START; ++ power_loss_recovery_cmd[1] = IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER; ++ power_loss_recovery_cmd[2] = IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER_POWER_LOSS; ++ power_loss_recovery_cmd[3] = hex_asc[power_loss_recovery_action]; ++ ++ mutex_lock(&mcu->lock); ++ ret = iei_wt61p803_puzzle_write_command(mcu, power_loss_recovery_cmd, ++ sizeof(power_loss_recovery_cmd), ++ resp_buf, &reply_size); ++ if (ret) ++ goto exit; ++ mcu->status.power_loss_recovery = power_loss_recovery_action; ++exit: ++ mutex_unlock(&mcu->lock); ++ return ret; ++} ++ ++#define to_puzzle_dev_attr(_attr) \ ++ container_of(_attr, struct iei_wt61p803_puzzle_device_attribute, dev_attr) ++ ++static ssize_t show_output(struct device *dev, ++ struct device_attribute *attr, char *buf) ++{ ++ struct iei_wt61p803_puzzle *mcu = dev_get_drvdata(dev); ++ struct iei_wt61p803_puzzle_device_attribute *pattr = to_puzzle_dev_attr(attr); ++ int ret; ++ ++ switch (pattr->type) { ++ case IEI_WT61P803_PUZZLE_VERSION: ++ return scnprintf(buf, PAGE_SIZE, "%s\n", mcu->version.version); ++ case IEI_WT61P803_PUZZLE_BUILD_INFO: ++ return scnprintf(buf, PAGE_SIZE, "%s\n", mcu->version.build_info); ++ case IEI_WT61P803_PUZZLE_BOOTLOADER_MODE: ++ return scnprintf(buf, PAGE_SIZE, "%d\n", mcu->version.bootloader_mode); ++ case IEI_WT61P803_PUZZLE_PROTOCOL_VERSION: ++ return scnprintf(buf, PAGE_SIZE, "%s\n", mcu->version.protocol_version); ++ case IEI_WT61P803_PUZZLE_SERIAL_NUMBER: ++ ret = iei_wt61p803_puzzle_get_serial_number(mcu); ++ if (!ret) ++ ret = scnprintf(buf, PAGE_SIZE, "%s\n", mcu->version.serial_number); ++ else ++ ret = 0; ++ return ret; ++ case IEI_WT61P803_PUZZLE_MAC_ADDRESS: ++ ret = iei_wt61p803_puzzle_get_mac_address(mcu, pattr->index); ++ if (!ret) ++ ret = scnprintf(buf, PAGE_SIZE, "%s\n", ++ mcu->version.mac_address[pattr->index]); ++ else ++ ret = 0; ++ return ret; ++ case IEI_WT61P803_PUZZLE_AC_RECOVERY_STATUS: ++ case IEI_WT61P803_PUZZLE_POWER_LOSS_RECOVERY: ++ case IEI_WT61P803_PUZZLE_POWER_STATUS: ++ ret = iei_wt61p803_puzzle_get_mcu_status(mcu); ++ if (ret) ++ return ret; ++ ++ mutex_lock(&mcu->lock); ++ switch (pattr->type) { ++ case IEI_WT61P803_PUZZLE_AC_RECOVERY_STATUS: ++ ret = scnprintf(buf, PAGE_SIZE, "%x\n", ++ mcu->status.ac_recovery_status_flag); ++ break; ++ case IEI_WT61P803_PUZZLE_POWER_LOSS_RECOVERY: ++ ret = scnprintf(buf, PAGE_SIZE, "%x\n", mcu->status.power_loss_recovery); ++ break; ++ case IEI_WT61P803_PUZZLE_POWER_STATUS: ++ ret = scnprintf(buf, PAGE_SIZE, "%x\n", mcu->status.power_status); ++ break; ++ default: ++ ret = 0; ++ break; ++ } ++ mutex_unlock(&mcu->lock); ++ return ret; ++ default: ++ return 0; ++ } ++ ++ return 0; ++} ++ ++static ssize_t store_output(struct device *dev, ++ struct device_attribute *attr, ++ const char *buf, size_t len) ++{ ++ unsigned char serial_number[IEI_WT61P803_PUZZLE_SN_LENGTH]; ++ unsigned char mac_address[IEI_WT61P803_PUZZLE_MAC_LENGTH]; ++ struct iei_wt61p803_puzzle *mcu = dev_get_drvdata(dev); ++ struct iei_wt61p803_puzzle_device_attribute *pattr = to_puzzle_dev_attr(attr); ++ int power_loss_recovery_action = 0; ++ int ret; ++ ++ switch (pattr->type) { ++ case IEI_WT61P803_PUZZLE_SERIAL_NUMBER: ++ if (len != (size_t)(IEI_WT61P803_PUZZLE_SN_LENGTH + 1)) ++ return -EINVAL; ++ memcpy(serial_number, buf, sizeof(serial_number)); ++ ret = iei_wt61p803_puzzle_write_serial_number(mcu, serial_number); ++ if (ret) ++ return ret; ++ return len; ++ case IEI_WT61P803_PUZZLE_MAC_ADDRESS: ++ if (len != (size_t)(IEI_WT61P803_PUZZLE_MAC_LENGTH + 1)) ++ return -EINVAL; ++ ++ memcpy(mac_address, buf, sizeof(mac_address)); ++ ++ if (strlen(attr->attr.name) != 13) ++ return -EIO; ++ ++ ret = iei_wt61p803_puzzle_write_mac_address(mcu, mac_address, pattr->index); ++ if (ret) ++ return ret; ++ return len; ++ case IEI_WT61P803_PUZZLE_POWER_LOSS_RECOVERY: ++ ret = kstrtoint(buf, 10, &power_loss_recovery_action); ++ if (ret) ++ return ret; ++ ret = iei_wt61p803_puzzle_write_power_loss_recovery(mcu, ++ power_loss_recovery_action); ++ if (ret) ++ return ret; ++ return len; ++ default: ++ return -EINVAL; ++ } ++ ++ return 0; ++} ++ ++#define IEI_WT61P803_PUZZLE_ATTR(_name, _mode, _show, _store, _type, _index) \ ++ struct iei_wt61p803_puzzle_device_attribute dev_attr_##_name = \ ++ { .dev_attr = __ATTR(_name, _mode, _show, _store), \ ++ .type = _type, \ ++ .index = _index } ++ ++#define IEI_WT61P803_PUZZLE_ATTR_RO(_name, _type, _id) \ ++ IEI_WT61P803_PUZZLE_ATTR(_name, 0444, show_output, NULL, _type, _id) ++ ++#define IEI_WT61P803_PUZZLE_ATTR_RW(_name, _type, _id) \ ++ IEI_WT61P803_PUZZLE_ATTR(_name, 0644, show_output, store_output, _type, _id) ++ ++static IEI_WT61P803_PUZZLE_ATTR_RO(version, IEI_WT61P803_PUZZLE_VERSION, 0); ++static IEI_WT61P803_PUZZLE_ATTR_RO(build_info, IEI_WT61P803_PUZZLE_BUILD_INFO, 0); ++static IEI_WT61P803_PUZZLE_ATTR_RO(bootloader_mode, IEI_WT61P803_PUZZLE_BOOTLOADER_MODE, 0); ++static IEI_WT61P803_PUZZLE_ATTR_RO(protocol_version, IEI_WT61P803_PUZZLE_PROTOCOL_VERSION, 0); ++static IEI_WT61P803_PUZZLE_ATTR_RW(serial_number, IEI_WT61P803_PUZZLE_SERIAL_NUMBER, 0); ++static IEI_WT61P803_PUZZLE_ATTR_RW(mac_address_0, IEI_WT61P803_PUZZLE_MAC_ADDRESS, 0); ++static IEI_WT61P803_PUZZLE_ATTR_RW(mac_address_1, IEI_WT61P803_PUZZLE_MAC_ADDRESS, 1); ++static IEI_WT61P803_PUZZLE_ATTR_RW(mac_address_2, IEI_WT61P803_PUZZLE_MAC_ADDRESS, 2); ++static IEI_WT61P803_PUZZLE_ATTR_RW(mac_address_3, IEI_WT61P803_PUZZLE_MAC_ADDRESS, 3); ++static IEI_WT61P803_PUZZLE_ATTR_RW(mac_address_4, IEI_WT61P803_PUZZLE_MAC_ADDRESS, 4); ++static IEI_WT61P803_PUZZLE_ATTR_RW(mac_address_5, IEI_WT61P803_PUZZLE_MAC_ADDRESS, 5); ++static IEI_WT61P803_PUZZLE_ATTR_RW(mac_address_6, IEI_WT61P803_PUZZLE_MAC_ADDRESS, 6); ++static IEI_WT61P803_PUZZLE_ATTR_RW(mac_address_7, IEI_WT61P803_PUZZLE_MAC_ADDRESS, 7); ++static IEI_WT61P803_PUZZLE_ATTR_RO(ac_recovery_status, IEI_WT61P803_PUZZLE_AC_RECOVERY_STATUS, 0); ++static IEI_WT61P803_PUZZLE_ATTR_RW(power_loss_recovery, IEI_WT61P803_PUZZLE_POWER_LOSS_RECOVERY, 0); ++static IEI_WT61P803_PUZZLE_ATTR_RO(power_status, IEI_WT61P803_PUZZLE_POWER_STATUS, 0); ++ ++static struct attribute *iei_wt61p803_puzzle_attrs[] = { ++ &dev_attr_version.dev_attr.attr, ++ &dev_attr_build_info.dev_attr.attr, ++ &dev_attr_bootloader_mode.dev_attr.attr, ++ &dev_attr_protocol_version.dev_attr.attr, ++ &dev_attr_serial_number.dev_attr.attr, ++ &dev_attr_mac_address_0.dev_attr.attr, ++ &dev_attr_mac_address_1.dev_attr.attr, ++ &dev_attr_mac_address_2.dev_attr.attr, ++ &dev_attr_mac_address_3.dev_attr.attr, ++ &dev_attr_mac_address_4.dev_attr.attr, ++ &dev_attr_mac_address_5.dev_attr.attr, ++ &dev_attr_mac_address_6.dev_attr.attr, ++ &dev_attr_mac_address_7.dev_attr.attr, ++ &dev_attr_ac_recovery_status.dev_attr.attr, ++ &dev_attr_power_loss_recovery.dev_attr.attr, ++ &dev_attr_power_status.dev_attr.attr, ++ NULL ++}; ++ATTRIBUTE_GROUPS(iei_wt61p803_puzzle); ++ ++static int iei_wt61p803_puzzle_sysfs_create(struct device *dev, ++ struct iei_wt61p803_puzzle *mcu) ++{ ++ int ret; ++ ++ ret = sysfs_create_groups(&mcu->dev->kobj, iei_wt61p803_puzzle_groups); ++ if (ret) ++ mfd_remove_devices(mcu->dev); ++ ++ return ret; ++} ++ ++static int iei_wt61p803_puzzle_sysfs_remove(struct device *dev, ++ struct iei_wt61p803_puzzle *mcu) ++{ ++ /* Remove sysfs groups */ ++ sysfs_remove_groups(&mcu->dev->kobj, iei_wt61p803_puzzle_groups); ++ mfd_remove_devices(mcu->dev); ++ ++ return 0; ++} ++ ++static int iei_wt61p803_puzzle_probe(struct serdev_device *serdev) ++{ ++ struct device *dev = &serdev->dev; ++ struct iei_wt61p803_puzzle *mcu; ++ u32 baud; ++ int ret; ++ ++ /* Read the baud rate from 'current-speed', because the MCU supports different rates */ ++ if (device_property_read_u32(dev, "current-speed", &baud)) { ++ dev_err(dev, ++ "'current-speed' is not specified in device node\n"); ++ return -EINVAL; ++ } ++ dev_dbg(dev, "Driver baud rate: %d\n", baud); ++ ++ /* Allocate the memory */ ++ mcu = devm_kzalloc(dev, sizeof(*mcu), GFP_KERNEL); ++ if (!mcu) ++ return -ENOMEM; ++ ++ mcu->reply = devm_kzalloc(dev, sizeof(*mcu->reply), GFP_KERNEL); ++ if (!mcu->reply) ++ return -ENOMEM; ++ ++ /* Initialize device struct data */ ++ mcu->serdev = serdev; ++ mcu->dev = dev; ++ init_completion(&mcu->reply->received); ++ mutex_init(&mcu->reply_lock); ++ mutex_init(&mcu->lock); ++ ++ /* Setup UART interface */ ++ serdev_device_set_drvdata(serdev, mcu); ++ serdev_device_set_client_ops(serdev, &iei_wt61p803_puzzle_serdev_device_ops); ++ ret = devm_serdev_device_open(dev, serdev); ++ if (ret) ++ return ret; ++ serdev_device_set_baudrate(serdev, baud); ++ serdev_device_set_flow_control(serdev, false); ++ ret = serdev_device_set_parity(serdev, SERDEV_PARITY_NONE); ++ if (ret) { ++ dev_err(dev, "Failed to set parity\n"); ++ return ret; ++ } ++ ++ ret = iei_wt61p803_puzzle_get_version(mcu); ++ if (ret) ++ return ret; ++ ++ dev_dbg(dev, "MCU version: %s\n", mcu->version.version); ++ dev_dbg(dev, "MCU firmware build info: %s\n", mcu->version.build_info); ++ dev_dbg(dev, "MCU in bootloader mode: %s\n", ++ mcu->version.bootloader_mode ? "true" : "false"); ++ dev_dbg(dev, "MCU protocol version: %s\n", mcu->version.protocol_version); ++ ++ if (device_property_read_bool(dev, "enable-beep")) { ++ ret = iei_wt61p803_puzzle_buzzer(mcu, false); ++ if (ret) ++ return ret; ++ } ++ ++ ret = iei_wt61p803_puzzle_sysfs_create(dev, mcu); ++ if (ret) ++ return ret; ++ ++ return devm_of_platform_populate(dev); ++} ++ ++static void iei_wt61p803_puzzle_remove(struct serdev_device *serdev) ++{ ++ struct device *dev = &serdev->dev; ++ struct iei_wt61p803_puzzle *mcu = dev_get_drvdata(dev); ++ ++ iei_wt61p803_puzzle_sysfs_remove(dev, mcu); ++} ++ ++static const struct of_device_id iei_wt61p803_puzzle_dt_ids[] = { ++ { .compatible = "iei,wt61p803-puzzle" }, ++ { } ++}; ++ ++MODULE_DEVICE_TABLE(of, iei_wt61p803_puzzle_dt_ids); ++ ++static struct serdev_device_driver iei_wt61p803_puzzle_drv = { ++ .probe = iei_wt61p803_puzzle_probe, ++ .remove = iei_wt61p803_puzzle_remove, ++ .driver = { ++ .name = "iei-wt61p803-puzzle", ++ .of_match_table = iei_wt61p803_puzzle_dt_ids, ++ }, ++}; ++ ++module_serdev_device_driver(iei_wt61p803_puzzle_drv); ++ ++MODULE_LICENSE("GPL v2"); ++MODULE_AUTHOR("Luka Kovacic "); ++MODULE_DESCRIPTION("IEI WT61P803 PUZZLE MCU Driver"); +--- /dev/null ++++ b/include/linux/mfd/iei-wt61p803-puzzle.h +@@ -0,0 +1,66 @@ ++/* SPDX-License-Identifier: GPL-2.0-only */ ++/* IEI WT61P803 PUZZLE MCU Driver ++ * System management microcontroller for fan control, temperature sensor reading, ++ * LED control and system identification on IEI Puzzle series ARM-based appliances. ++ * ++ * Copyright (C) 2020 Sartura Ltd. ++ * Author: Luka Kovacic ++ */ ++ ++#ifndef _MFD_IEI_WT61P803_PUZZLE_H_ ++#define _MFD_IEI_WT61P803_PUZZLE_H_ ++ ++#define IEI_WT61P803_PUZZLE_BUF_SIZE 512 ++ ++/* Command magic numbers */ ++#define IEI_WT61P803_PUZZLE_CMD_HEADER_START 0x40 /* @ */ ++#define IEI_WT61P803_PUZZLE_CMD_HEADER_START_OTHER 0x25 /* % */ ++#define IEI_WT61P803_PUZZLE_CMD_HEADER_EEPROM 0xF7 ++ ++#define IEI_WT61P803_PUZZLE_CMD_RESPONSE_OK 0x30 /* 0 */ ++#define IEI_WT61P803_PUZZLE_CHECKSUM_RESPONSE_OK 0x70 ++ ++#define IEI_WT61P803_PUZZLE_CMD_EEPROM_READ 0xA1 ++#define IEI_WT61P803_PUZZLE_CMD_EEPROM_WRITE 0xA0 ++ ++#define IEI_WT61P803_PUZZLE_CMD_OTHER_VERSION 0x56 /* V */ ++#define IEI_WT61P803_PUZZLE_CMD_OTHER_BUILD 0x42 /* B */ ++#define IEI_WT61P803_PUZZLE_CMD_OTHER_BOOTLOADER_MODE 0x4D /* M */ ++#define IEI_WT61P803_PUZZLE_CMD_OTHER_MODE_BOOTLOADER 0x30 ++#define IEI_WT61P803_PUZZLE_CMD_OTHER_MODE_APPS 0x31 ++#define IEI_WT61P803_PUZZLE_CMD_OTHER_PROTOCOL_VERSION 0x50 /* P */ ++ ++#define IEI_WT61P803_PUZZLE_CMD_FUNCTION_SINGLE 0x43 /* C */ ++#define IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER 0x4F /* O */ ++#define IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER_STATUS 0x53 /* S */ ++#define IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER_POWER_LOSS 0x41 /* A */ ++ ++#define IEI_WT61P803_PUZZLE_CMD_LED 0x52 /* R */ ++#define IEI_WT61P803_PUZZLE_CMD_LED_POWER 0x31 /* 1 */ ++ ++#define IEI_WT61P803_PUZZLE_CMD_TEMP 0x54 /* T */ ++#define IEI_WT61P803_PUZZLE_CMD_TEMP_ALL 0x41 /* A */ ++ ++#define IEI_WT61P803_PUZZLE_CMD_FAN 0x46 /* F */ ++#define IEI_WT61P803_PUZZLE_CMD_FAN_PWM_READ 0x5A /* Z */ ++#define IEI_WT61P803_PUZZLE_CMD_FAN_PWM_WRITE 0x57 /* W */ ++#define IEI_WT61P803_PUZZLE_CMD_FAN_PWM_BASE 0x30 ++#define IEI_WT61P803_PUZZLE_CMD_FAN_RPM_BASE 0x41 /* A */ ++ ++#define IEI_WT61P803_PUZZLE_CMD_FAN_PWM(x) (IEI_WT61P803_PUZZLE_CMD_FAN_PWM_BASE + (x)) /* 0 - 1 */ ++#define IEI_WT61P803_PUZZLE_CMD_FAN_RPM(x) (IEI_WT61P803_PUZZLE_CMD_FAN_RPM_BASE + (x)) /* 0 - 5 */ ++ ++struct iei_wt61p803_puzzle_mcu_version; ++struct iei_wt61p803_puzzle_reply; ++struct iei_wt61p803_puzzle; ++ ++int iei_wt61p803_puzzle_write_command_watchdog(struct iei_wt61p803_puzzle *mcu, ++ unsigned char *cmd, size_t size, ++ unsigned char *reply_data, size_t *reply_size, ++ int retry_count); ++ ++int iei_wt61p803_puzzle_write_command(struct iei_wt61p803_puzzle *mcu, ++ unsigned char *cmd, size_t size, ++ unsigned char *reply_data, size_t *reply_size); ++ ++#endif /* _MFD_IEI_WT61P803_PUZZLE_H_ */ diff --git a/target/linux/mvebu/patches-5.4/903-drivers-hwmon-Add-the-IEI-WT61P803-PUZZLE-HWMON-driv.patch b/target/linux/mvebu/patches-5.4/903-drivers-hwmon-Add-the-IEI-WT61P803-PUZZLE-HWMON-driv.patch new file mode 100644 index 0000000000..550ce6387a --- /dev/null +++ b/target/linux/mvebu/patches-5.4/903-drivers-hwmon-Add-the-IEI-WT61P803-PUZZLE-HWMON-driv.patch @@ -0,0 +1,469 @@ +From e3310a638cd310bfd93dbbc6d2732ab6aea18dd2 Mon Sep 17 00:00:00 2001 +From: Luka Kovacic +Date: Tue, 24 Aug 2021 12:44:34 +0000 +Subject: [PATCH 3/7] drivers: hwmon: Add the IEI WT61P803 PUZZLE HWMON driver + +Add the IEI WT61P803 PUZZLE HWMON driver, that handles the fan speed +control via PWM, reading fan speed and reading on-board temperature +sensors. + +The driver registers a HWMON device and a simple thermal cooling device to +enable in-kernel fan management. + +This driver depends on the IEI WT61P803 PUZZLE MFD driver. + +Signed-off-by: Luka Kovacic +Signed-off-by: Pavo Banicevic +Acked-by: Guenter Roeck +Cc: Luka Perkov +Cc: Robert Marko +--- + drivers/hwmon/Kconfig | 8 + + drivers/hwmon/Makefile | 1 + + drivers/hwmon/iei-wt61p803-puzzle-hwmon.c | 413 ++++++++++++++++++++++ + 3 files changed, 422 insertions(+) + create mode 100644 drivers/hwmon/iei-wt61p803-puzzle-hwmon.c + +--- a/drivers/hwmon/Kconfig ++++ b/drivers/hwmon/Kconfig +@@ -639,6 +639,14 @@ config SENSORS_IBMPOWERNV + This driver can also be built as a module. If so, the module + will be called ibmpowernv. + ++config SENSORS_IEI_WT61P803_PUZZLE_HWMON ++ tristate "IEI WT61P803 PUZZLE MFD HWMON Driver" ++ depends on MFD_IEI_WT61P803_PUZZLE ++ help ++ The IEI WT61P803 PUZZLE MFD HWMON Driver handles reading fan speed ++ and writing fan PWM values. It also supports reading on-board ++ temperature sensors. ++ + config SENSORS_IIO_HWMON + tristate "Hwmon driver that uses channels specified via iio maps" + depends on IIO +--- a/drivers/hwmon/Makefile ++++ b/drivers/hwmon/Makefile +@@ -77,6 +77,7 @@ obj-$(CONFIG_SENSORS_HIH6130) += hih6130 + obj-$(CONFIG_SENSORS_ULTRA45) += ultra45_env.o + obj-$(CONFIG_SENSORS_I5500) += i5500_temp.o + obj-$(CONFIG_SENSORS_I5K_AMB) += i5k_amb.o ++obj-$(CONFIG_SENSORS_IEI_WT61P803_PUZZLE_HWMON) += iei-wt61p803-puzzle-hwmon.o + obj-$(CONFIG_SENSORS_IBMAEM) += ibmaem.o + obj-$(CONFIG_SENSORS_IBMPEX) += ibmpex.o + obj-$(CONFIG_SENSORS_IBMPOWERNV)+= ibmpowernv.o +--- /dev/null ++++ b/drivers/hwmon/iei-wt61p803-puzzle-hwmon.c +@@ -0,0 +1,413 @@ ++// SPDX-License-Identifier: GPL-2.0-only ++/* IEI WT61P803 PUZZLE MCU HWMON Driver ++ * ++ * Copyright (C) 2020 Sartura Ltd. ++ * Author: Luka Kovacic ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#define IEI_WT61P803_PUZZLE_HWMON_MAX_PWM 2 ++#define IEI_WT61P803_PUZZLE_HWMON_MAX_PWM_VAL 255 ++ ++/** ++ * struct iei_wt61p803_puzzle_thermal_cooling_device - Thermal cooling device instance ++ * @mcu_hwmon: Parent driver struct pointer ++ * @tcdev: Thermal cooling device pointer ++ * @name: Thermal cooling device name ++ * @pwm_channel: Controlled PWM channel (0 or 1) ++ * @cooling_levels: Thermal cooling device cooling levels (DT) ++ */ ++struct iei_wt61p803_puzzle_thermal_cooling_device { ++ struct iei_wt61p803_puzzle_hwmon *mcu_hwmon; ++ struct thermal_cooling_device *tcdev; ++ char name[THERMAL_NAME_LENGTH]; ++ int pwm_channel; ++ u8 *cooling_levels; ++}; ++ ++/** ++ * struct iei_wt61p803_puzzle_hwmon - MCU HWMON Driver ++ * @mcu: MCU struct pointer ++ * @response_buffer Global MCU response buffer ++ * @thermal_cooling_dev_present: Per-channel thermal cooling device control indicator ++ * @cdev: Per-channel thermal cooling device private structure ++ */ ++struct iei_wt61p803_puzzle_hwmon { ++ struct iei_wt61p803_puzzle *mcu; ++ unsigned char response_buffer[IEI_WT61P803_PUZZLE_BUF_SIZE]; ++ bool thermal_cooling_dev_present[IEI_WT61P803_PUZZLE_HWMON_MAX_PWM]; ++ struct iei_wt61p803_puzzle_thermal_cooling_device ++ *cdev[IEI_WT61P803_PUZZLE_HWMON_MAX_PWM]; ++ struct mutex lock; /* mutex to protect response_buffer array */ ++}; ++ ++#define raw_temp_to_milidegree_celsius(x) (((x) - 0x80) * 1000) ++static int iei_wt61p803_puzzle_read_temp_sensor(struct iei_wt61p803_puzzle_hwmon *mcu_hwmon, ++ int channel, long *value) ++{ ++ unsigned char *resp_buf = mcu_hwmon->response_buffer; ++ unsigned char temp_sensor_ntc_cmd[4] = { ++ IEI_WT61P803_PUZZLE_CMD_HEADER_START, ++ IEI_WT61P803_PUZZLE_CMD_TEMP, ++ IEI_WT61P803_PUZZLE_CMD_TEMP_ALL, ++ }; ++ size_t reply_size; ++ int ret; ++ ++ mutex_lock(&mcu_hwmon->lock); ++ ret = iei_wt61p803_puzzle_write_command(mcu_hwmon->mcu, temp_sensor_ntc_cmd, ++ sizeof(temp_sensor_ntc_cmd), resp_buf, ++ &reply_size); ++ if (ret) ++ goto exit; ++ ++ if (reply_size != 7) { ++ ret = -EIO; ++ goto exit; ++ } ++ ++ /* Check the number of NTC values */ ++ if (resp_buf[3] != '2') { ++ ret = -EIO; ++ goto exit; ++ } ++ ++ *value = raw_temp_to_milidegree_celsius(resp_buf[4 + channel]); ++exit: ++ mutex_unlock(&mcu_hwmon->lock); ++ return ret; ++} ++ ++#define raw_fan_val_to_rpm(x, y) ((((x) << 8 | (y)) / 2) * 60) ++static int iei_wt61p803_puzzle_read_fan_speed(struct iei_wt61p803_puzzle_hwmon *mcu_hwmon, ++ int channel, long *value) ++{ ++ unsigned char *resp_buf = mcu_hwmon->response_buffer; ++ unsigned char fan_speed_cmd[4] = {}; ++ size_t reply_size; ++ int ret; ++ ++ fan_speed_cmd[0] = IEI_WT61P803_PUZZLE_CMD_HEADER_START; ++ fan_speed_cmd[1] = IEI_WT61P803_PUZZLE_CMD_FAN; ++ fan_speed_cmd[2] = IEI_WT61P803_PUZZLE_CMD_FAN_RPM(channel); ++ ++ mutex_lock(&mcu_hwmon->lock); ++ ret = iei_wt61p803_puzzle_write_command(mcu_hwmon->mcu, fan_speed_cmd, ++ sizeof(fan_speed_cmd), resp_buf, ++ &reply_size); ++ if (ret) ++ goto exit; ++ ++ if (reply_size != 7) { ++ ret = -EIO; ++ goto exit; ++ } ++ ++ *value = raw_fan_val_to_rpm(resp_buf[3], resp_buf[4]); ++exit: ++ mutex_unlock(&mcu_hwmon->lock); ++ return ret; ++} ++ ++static int iei_wt61p803_puzzle_write_pwm_channel(struct iei_wt61p803_puzzle_hwmon *mcu_hwmon, ++ int channel, long pwm_set_val) ++{ ++ unsigned char *resp_buf = mcu_hwmon->response_buffer; ++ unsigned char pwm_set_cmd[6] = {}; ++ size_t reply_size; ++ int ret; ++ ++ pwm_set_cmd[0] = IEI_WT61P803_PUZZLE_CMD_HEADER_START; ++ pwm_set_cmd[1] = IEI_WT61P803_PUZZLE_CMD_FAN; ++ pwm_set_cmd[2] = IEI_WT61P803_PUZZLE_CMD_FAN_PWM_WRITE; ++ pwm_set_cmd[3] = IEI_WT61P803_PUZZLE_CMD_FAN_PWM(channel); ++ pwm_set_cmd[4] = pwm_set_val; ++ ++ mutex_lock(&mcu_hwmon->lock); ++ ret = iei_wt61p803_puzzle_write_command(mcu_hwmon->mcu, pwm_set_cmd, ++ sizeof(pwm_set_cmd), resp_buf, ++ &reply_size); ++ if (ret) ++ goto exit; ++ ++ if (reply_size != 3) { ++ ret = -EIO; ++ goto exit; ++ } ++ ++ if (!(resp_buf[0] == IEI_WT61P803_PUZZLE_CMD_HEADER_START && ++ resp_buf[1] == IEI_WT61P803_PUZZLE_CMD_RESPONSE_OK && ++ resp_buf[2] == IEI_WT61P803_PUZZLE_CHECKSUM_RESPONSE_OK)) { ++ ret = -EIO; ++ goto exit; ++ } ++exit: ++ mutex_unlock(&mcu_hwmon->lock); ++ return ret; ++} ++ ++static int iei_wt61p803_puzzle_read_pwm_channel(struct iei_wt61p803_puzzle_hwmon *mcu_hwmon, ++ int channel, long *value) ++{ ++ unsigned char *resp_buf = mcu_hwmon->response_buffer; ++ unsigned char pwm_get_cmd[5] = {}; ++ size_t reply_size; ++ int ret; ++ ++ pwm_get_cmd[0] = IEI_WT61P803_PUZZLE_CMD_HEADER_START; ++ pwm_get_cmd[1] = IEI_WT61P803_PUZZLE_CMD_FAN; ++ pwm_get_cmd[2] = IEI_WT61P803_PUZZLE_CMD_FAN_PWM_READ; ++ pwm_get_cmd[3] = IEI_WT61P803_PUZZLE_CMD_FAN_PWM(channel); ++ ++ ret = iei_wt61p803_puzzle_write_command(mcu_hwmon->mcu, pwm_get_cmd, ++ sizeof(pwm_get_cmd), resp_buf, ++ &reply_size); ++ if (ret) ++ return ret; ++ ++ if (reply_size != 5) ++ return -EIO; ++ ++ if (resp_buf[2] != IEI_WT61P803_PUZZLE_CMD_FAN_PWM_READ) ++ return -EIO; ++ ++ *value = resp_buf[3]; ++ ++ return 0; ++} ++ ++static int iei_wt61p803_puzzle_read(struct device *dev, enum hwmon_sensor_types type, ++ u32 attr, int channel, long *val) ++{ ++ struct iei_wt61p803_puzzle_hwmon *mcu_hwmon = dev_get_drvdata(dev->parent); ++ ++ switch (type) { ++ case hwmon_pwm: ++ return iei_wt61p803_puzzle_read_pwm_channel(mcu_hwmon, channel, val); ++ case hwmon_fan: ++ return iei_wt61p803_puzzle_read_fan_speed(mcu_hwmon, channel, val); ++ case hwmon_temp: ++ return iei_wt61p803_puzzle_read_temp_sensor(mcu_hwmon, channel, val); ++ default: ++ return -EINVAL; ++ } ++} ++ ++static int iei_wt61p803_puzzle_write(struct device *dev, enum hwmon_sensor_types type, ++ u32 attr, int channel, long val) ++{ ++ struct iei_wt61p803_puzzle_hwmon *mcu_hwmon = dev_get_drvdata(dev->parent); ++ ++ return iei_wt61p803_puzzle_write_pwm_channel(mcu_hwmon, channel, val); ++} ++ ++static umode_t iei_wt61p803_puzzle_is_visible(const void *data, enum hwmon_sensor_types type, ++ u32 attr, int channel) ++{ ++ const struct iei_wt61p803_puzzle_hwmon *mcu_hwmon = data; ++ ++ switch (type) { ++ case hwmon_pwm: ++ if (mcu_hwmon->thermal_cooling_dev_present[channel]) ++ return 0444; ++ if (attr == hwmon_pwm_input) ++ return 0644; ++ break; ++ case hwmon_fan: ++ if (attr == hwmon_fan_input) ++ return 0444; ++ break; ++ case hwmon_temp: ++ if (attr == hwmon_temp_input) ++ return 0444; ++ break; ++ default: ++ return 0; ++ } ++ ++ return 0; ++} ++ ++static const struct hwmon_ops iei_wt61p803_puzzle_hwmon_ops = { ++ .is_visible = iei_wt61p803_puzzle_is_visible, ++ .read = iei_wt61p803_puzzle_read, ++ .write = iei_wt61p803_puzzle_write, ++}; ++ ++static const struct hwmon_channel_info *iei_wt61p803_puzzle_info[] = { ++ HWMON_CHANNEL_INFO(pwm, ++ HWMON_PWM_INPUT, ++ HWMON_PWM_INPUT), ++ HWMON_CHANNEL_INFO(fan, ++ HWMON_F_INPUT, ++ HWMON_F_INPUT, ++ HWMON_F_INPUT, ++ HWMON_F_INPUT, ++ HWMON_F_INPUT), ++ HWMON_CHANNEL_INFO(temp, ++ HWMON_T_INPUT, ++ HWMON_T_INPUT), ++ NULL ++}; ++ ++static const struct hwmon_chip_info iei_wt61p803_puzzle_chip_info = { ++ .ops = &iei_wt61p803_puzzle_hwmon_ops, ++ .info = iei_wt61p803_puzzle_info, ++}; ++ ++static int iei_wt61p803_puzzle_get_max_state(struct thermal_cooling_device *tcdev, ++ unsigned long *state) ++{ ++ *state = IEI_WT61P803_PUZZLE_HWMON_MAX_PWM_VAL; ++ ++ return 0; ++} ++ ++static int iei_wt61p803_puzzle_get_cur_state(struct thermal_cooling_device *tcdev, ++ unsigned long *state) ++{ ++ struct iei_wt61p803_puzzle_thermal_cooling_device *cdev = tcdev->devdata; ++ struct iei_wt61p803_puzzle_hwmon *mcu_hwmon = cdev->mcu_hwmon; ++ long value; ++ int ret; ++ ++ ret = iei_wt61p803_puzzle_read_pwm_channel(mcu_hwmon, cdev->pwm_channel, &value); ++ if (ret) ++ return ret; ++ *state = value; ++ return 0; ++} ++ ++static int iei_wt61p803_puzzle_set_cur_state(struct thermal_cooling_device *tcdev, ++ unsigned long state) ++{ ++ struct iei_wt61p803_puzzle_thermal_cooling_device *cdev = tcdev->devdata; ++ struct iei_wt61p803_puzzle_hwmon *mcu_hwmon = cdev->mcu_hwmon; ++ ++ return iei_wt61p803_puzzle_write_pwm_channel(mcu_hwmon, cdev->pwm_channel, state); ++} ++ ++static const struct thermal_cooling_device_ops iei_wt61p803_puzzle_cooling_ops = { ++ .get_max_state = iei_wt61p803_puzzle_get_max_state, ++ .get_cur_state = iei_wt61p803_puzzle_get_cur_state, ++ .set_cur_state = iei_wt61p803_puzzle_set_cur_state, ++}; ++ ++static int ++iei_wt61p803_puzzle_enable_thermal_cooling_dev(struct device *dev, ++ struct fwnode_handle *child, ++ struct iei_wt61p803_puzzle_hwmon *mcu_hwmon) ++{ ++ struct iei_wt61p803_puzzle_thermal_cooling_device *cdev; ++ u32 pwm_channel; ++ u8 num_levels; ++ int ret; ++ ++ ret = fwnode_property_read_u32(child, "reg", &pwm_channel); ++ if (ret) ++ return ret; ++ ++ mcu_hwmon->thermal_cooling_dev_present[pwm_channel] = true; ++ ++ num_levels = fwnode_property_count_u8(child, "cooling-levels"); ++ if (!num_levels) ++ return -EINVAL; ++ ++ cdev = devm_kzalloc(dev, sizeof(*cdev), GFP_KERNEL); ++ if (!cdev) ++ return -ENOMEM; ++ ++ cdev->cooling_levels = devm_kmalloc_array(dev, num_levels, sizeof(u8), GFP_KERNEL); ++ if (!cdev->cooling_levels) ++ return -ENOMEM; ++ ++ ret = fwnode_property_read_u8_array(child, "cooling-levels", ++ cdev->cooling_levels, ++ num_levels); ++ if (ret) { ++ dev_err(dev, "Couldn't read property 'cooling-levels'\n"); ++ return ret; ++ } ++ ++ snprintf(cdev->name, THERMAL_NAME_LENGTH, "wt61p803_puzzle_%d", pwm_channel); ++ cdev->tcdev = devm_thermal_of_cooling_device_register(dev, NULL, cdev->name, cdev, ++ &iei_wt61p803_puzzle_cooling_ops); ++ if (IS_ERR(cdev->tcdev)) ++ return PTR_ERR(cdev->tcdev); ++ ++ cdev->mcu_hwmon = mcu_hwmon; ++ cdev->pwm_channel = pwm_channel; ++ mcu_hwmon->cdev[pwm_channel] = cdev; ++ ++ return 0; ++} ++ ++static int iei_wt61p803_puzzle_hwmon_probe(struct platform_device *pdev) ++{ ++ struct device *dev = &pdev->dev; ++ struct iei_wt61p803_puzzle *mcu = dev_get_drvdata(dev->parent); ++ struct iei_wt61p803_puzzle_hwmon *mcu_hwmon; ++ struct fwnode_handle *child; ++ struct device *hwmon_dev; ++ int ret; ++ ++ mcu_hwmon = devm_kzalloc(dev, sizeof(*mcu_hwmon), GFP_KERNEL); ++ if (!mcu_hwmon) ++ return -ENOMEM; ++ ++ mcu_hwmon->mcu = mcu; ++ platform_set_drvdata(pdev, mcu_hwmon); ++ mutex_init(&mcu_hwmon->lock); ++ ++ hwmon_dev = devm_hwmon_device_register_with_info(dev, "iei_wt61p803_puzzle", ++ mcu_hwmon, ++ &iei_wt61p803_puzzle_chip_info, ++ NULL); ++ if (IS_ERR(hwmon_dev)) ++ return PTR_ERR(hwmon_dev); ++ ++ /* Control fans via PWM lines via Linux Kernel */ ++ if (IS_ENABLED(CONFIG_THERMAL)) { ++ device_for_each_child_node(dev, child) { ++ ret = iei_wt61p803_puzzle_enable_thermal_cooling_dev(dev, child, mcu_hwmon); ++ if (ret) { ++ dev_err(dev, "Enabling the PWM fan failed\n"); ++ fwnode_handle_put(child); ++ return ret; ++ } ++ } ++ } ++ return 0; ++} ++ ++static const struct of_device_id iei_wt61p803_puzzle_hwmon_id_table[] = { ++ { .compatible = "iei,wt61p803-puzzle-hwmon" }, ++ {} ++}; ++MODULE_DEVICE_TABLE(of, iei_wt61p803_puzzle_hwmon_id_table); ++ ++static struct platform_driver iei_wt61p803_puzzle_hwmon_driver = { ++ .driver = { ++ .name = "iei-wt61p803-puzzle-hwmon", ++ .of_match_table = iei_wt61p803_puzzle_hwmon_id_table, ++ }, ++ .probe = iei_wt61p803_puzzle_hwmon_probe, ++}; ++ ++module_platform_driver(iei_wt61p803_puzzle_hwmon_driver); ++ ++MODULE_DESCRIPTION("IEI WT61P803 PUZZLE MCU HWMON Driver"); ++MODULE_AUTHOR("Luka Kovacic "); ++MODULE_LICENSE("GPL v2"); diff --git a/target/linux/mvebu/patches-5.4/904-drivers-leds-Add-the-IEI-WT61P803-PUZZLE-LED-driver.patch b/target/linux/mvebu/patches-5.4/904-drivers-leds-Add-the-IEI-WT61P803-PUZZLE-LED-driver.patch new file mode 100644 index 0000000000..55224a2a20 --- /dev/null +++ b/target/linux/mvebu/patches-5.4/904-drivers-leds-Add-the-IEI-WT61P803-PUZZLE-LED-driver.patch @@ -0,0 +1,207 @@ +From f3b44eb69cc561cf05d00506dcec0dd9be003ed8 Mon Sep 17 00:00:00 2001 +From: Luka Kovacic +Date: Tue, 24 Aug 2021 12:44:35 +0000 +Subject: [PATCH 4/7] drivers: leds: Add the IEI WT61P803 PUZZLE LED driver + +Add support for the IEI WT61P803 PUZZLE LED driver. +Currently only the front panel power LED is supported, +since it is the only LED on this board wired through the +MCU. + +The LED is wired directly to the on-board MCU controller +and is toggled using an MCU command. + +Support for more LEDs is going to be added in case more +boards implement this microcontroller, as LEDs use many +different GPIOs. + +This driver depends on the IEI WT61P803 PUZZLE MFD driver. + +Signed-off-by: Luka Kovacic +Signed-off-by: Pavo Banicevic +Cc: Luka Perkov +Cc: Robert Marko +--- + drivers/leds/Kconfig | 8 ++ + drivers/leds/Makefile | 1 + + drivers/leds/leds-iei-wt61p803-puzzle.c | 147 ++++++++++++++++++++++++ + 3 files changed, 156 insertions(+) + create mode 100644 drivers/leds/leds-iei-wt61p803-puzzle.c + +--- a/drivers/leds/Kconfig ++++ b/drivers/leds/Kconfig +@@ -278,6 +278,14 @@ config LEDS_IPAQ_MICRO + Choose this option if you want to use the notification LED on + Compaq/HP iPAQ h3100 and h3600. + ++config LEDS_IEI_WT61P803_PUZZLE ++ tristate "LED Support for the IEI WT61P803 PUZZLE MCU" ++ depends on LEDS_CLASS ++ depends on MFD_IEI_WT61P803_PUZZLE ++ help ++ This option enables support for LEDs controlled by the IEI WT61P803 ++ M801 MCU. ++ + config LEDS_HP6XX + tristate "LED Support for the HP Jornada 6xx" + depends on LEDS_CLASS +--- a/drivers/leds/Makefile ++++ b/drivers/leds/Makefile +@@ -43,6 +43,7 @@ obj-$(CONFIG_LEDS_LP8860) += leds-lp886 + obj-$(CONFIG_LEDS_TCA6507) += leds-tca6507.o + obj-$(CONFIG_LEDS_TLC591XX) += leds-tlc591xx.o + obj-$(CONFIG_LEDS_CLEVO_MAIL) += leds-clevo-mail.o ++obj-$(CONFIG_LEDS_IEI_WT61P803_PUZZLE) += leds-iei-wt61p803-puzzle.o + obj-$(CONFIG_LEDS_IPAQ_MICRO) += leds-ipaq-micro.o + obj-$(CONFIG_LEDS_HP6XX) += leds-hp6xx.o + obj-$(CONFIG_LEDS_OT200) += leds-ot200.o +--- /dev/null ++++ b/drivers/leds/leds-iei-wt61p803-puzzle.c +@@ -0,0 +1,147 @@ ++// SPDX-License-Identifier: GPL-2.0-only ++/* IEI WT61P803 PUZZLE MCU LED Driver ++ * ++ * Copyright (C) 2020 Sartura Ltd. ++ * Author: Luka Kovacic ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++enum iei_wt61p803_puzzle_led_state { ++ IEI_LED_OFF = 0x30, ++ IEI_LED_ON = 0x31, ++ IEI_LED_BLINK_5HZ = 0x32, ++ IEI_LED_BLINK_1HZ = 0x33, ++}; ++ ++/** ++ * struct iei_wt61p803_puzzle_led - MCU LED Driver ++ * @cdev: LED classdev ++ * @mcu: MCU struct pointer ++ * @response_buffer Global MCU response buffer ++ * @lock: General mutex lock to protect simultaneous R/W access to led_power_state ++ * @led_power_state: State of the front panel power LED ++ */ ++struct iei_wt61p803_puzzle_led { ++ struct led_classdev cdev; ++ struct iei_wt61p803_puzzle *mcu; ++ unsigned char response_buffer[IEI_WT61P803_PUZZLE_BUF_SIZE]; ++ struct mutex lock; /* mutex to protect led_power_state */ ++ int led_power_state; ++}; ++ ++static inline struct iei_wt61p803_puzzle_led *cdev_to_iei_wt61p803_puzzle_led ++ (struct led_classdev *led_cdev) ++{ ++ return container_of(led_cdev, struct iei_wt61p803_puzzle_led, cdev); ++} ++ ++static int iei_wt61p803_puzzle_led_brightness_set_blocking(struct led_classdev *cdev, ++ enum led_brightness brightness) ++{ ++ struct iei_wt61p803_puzzle_led *priv = cdev_to_iei_wt61p803_puzzle_led(cdev); ++ unsigned char *resp_buf = priv->response_buffer; ++ unsigned char led_power_cmd[5] = {}; ++ size_t reply_size; ++ int ret; ++ ++ led_power_cmd[0] = IEI_WT61P803_PUZZLE_CMD_HEADER_START; ++ led_power_cmd[1] = IEI_WT61P803_PUZZLE_CMD_LED; ++ led_power_cmd[2] = IEI_WT61P803_PUZZLE_CMD_LED_POWER; ++ led_power_cmd[3] = brightness == LED_OFF ? IEI_LED_OFF : IEI_LED_ON; ++ ++ ret = iei_wt61p803_puzzle_write_command(priv->mcu, led_power_cmd, ++ sizeof(led_power_cmd), ++ resp_buf, ++ &reply_size); ++ if (ret) ++ return ret; ++ ++ if (reply_size != 3) ++ return -EIO; ++ ++ if (!(resp_buf[0] == IEI_WT61P803_PUZZLE_CMD_HEADER_START && ++ resp_buf[1] == IEI_WT61P803_PUZZLE_CMD_RESPONSE_OK && ++ resp_buf[2] == IEI_WT61P803_PUZZLE_CHECKSUM_RESPONSE_OK)) ++ return -EIO; ++ ++ mutex_lock(&priv->lock); ++ priv->led_power_state = brightness; ++ mutex_unlock(&priv->lock); ++ ++ return 0; ++} ++ ++static enum led_brightness iei_wt61p803_puzzle_led_brightness_get(struct led_classdev *cdev) ++{ ++ struct iei_wt61p803_puzzle_led *priv = cdev_to_iei_wt61p803_puzzle_led(cdev); ++ int led_state; ++ ++ mutex_lock(&priv->lock); ++ led_state = priv->led_power_state; ++ mutex_unlock(&priv->lock); ++ ++ return led_state; ++} ++ ++static int iei_wt61p803_puzzle_led_probe(struct platform_device *pdev) ++{ ++ struct device *dev = &pdev->dev; ++ struct iei_wt61p803_puzzle *mcu = dev_get_drvdata(dev->parent); ++ struct iei_wt61p803_puzzle_led *priv; ++ struct led_init_data init_data = {}; ++ struct fwnode_handle *child; ++ int ret; ++ ++ if (device_get_child_node_count(dev) != 1) ++ return -EINVAL; ++ ++ priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); ++ if (!priv) ++ return -ENOMEM; ++ ++ priv->mcu = mcu; ++ priv->led_power_state = 1; ++ mutex_init(&priv->lock); ++ dev_set_drvdata(dev, priv); ++ ++ child = device_get_next_child_node(dev, NULL); ++ init_data.fwnode = child; ++ ++ priv->cdev.brightness_set_blocking = iei_wt61p803_puzzle_led_brightness_set_blocking; ++ priv->cdev.brightness_get = iei_wt61p803_puzzle_led_brightness_get; ++ priv->cdev.max_brightness = 1; ++ ++ ret = devm_led_classdev_register_ext(dev, &priv->cdev, &init_data); ++ if (ret) ++ dev_err(dev, "Could not register LED\n"); ++ ++ fwnode_handle_put(child); ++ return ret; ++} ++ ++static const struct of_device_id iei_wt61p803_puzzle_led_of_match[] = { ++ { .compatible = "iei,wt61p803-puzzle-leds" }, ++ { } ++}; ++MODULE_DEVICE_TABLE(of, iei_wt61p803_puzzle_led_of_match); ++ ++static struct platform_driver iei_wt61p803_puzzle_led_driver = { ++ .driver = { ++ .name = "iei-wt61p803-puzzle-led", ++ .of_match_table = iei_wt61p803_puzzle_led_of_match, ++ }, ++ .probe = iei_wt61p803_puzzle_led_probe, ++}; ++module_platform_driver(iei_wt61p803_puzzle_led_driver); ++ ++MODULE_DESCRIPTION("IEI WT61P803 PUZZLE front panel LED driver"); ++MODULE_AUTHOR("Luka Kovacic "); ++MODULE_LICENSE("GPL v2"); ++MODULE_ALIAS("platform:leds-iei-wt61p803-puzzle"); diff --git a/target/linux/mvebu/patches-5.4/905-Documentation-ABI-Add-iei-wt61p803-puzzle-driver-sys.patch b/target/linux/mvebu/patches-5.4/905-Documentation-ABI-Add-iei-wt61p803-puzzle-driver-sys.patch new file mode 100644 index 0000000000..b1d420ef0a --- /dev/null +++ b/target/linux/mvebu/patches-5.4/905-Documentation-ABI-Add-iei-wt61p803-puzzle-driver-sys.patch @@ -0,0 +1,82 @@ +From 2fab3b4956c5b2f83c1e1abffc1df39de2933d83 Mon Sep 17 00:00:00 2001 +From: Luka Kovacic +Date: Tue, 24 Aug 2021 12:44:36 +0000 +Subject: [PATCH 5/7] Documentation/ABI: Add iei-wt61p803-puzzle driver sysfs + interface documentation + +Add the iei-wt61p803-puzzle driver sysfs interface documentation to allow +monitoring and control of the microcontroller from user space. + +Signed-off-by: Luka Kovacic +Signed-off-by: Pavo Banicevic +Cc: Luka Perkov +Cc: Robert Marko +--- + .../testing/sysfs-driver-iei-wt61p803-puzzle | 61 +++++++++++++++++++ + 1 file changed, 61 insertions(+) + create mode 100644 Documentation/ABI/testing/sysfs-driver-iei-wt61p803-puzzle + +--- /dev/null ++++ b/Documentation/ABI/testing/sysfs-driver-iei-wt61p803-puzzle +@@ -0,0 +1,61 @@ ++What: /sys/bus/serial/devices/.../mac_address_* ++Date: September 2020 ++Contact: Luka Kovacic ++Description: (RW) Internal factory assigned MAC address values ++ ++What: /sys/bus/serial/devices/.../serial_number ++Date: September 2020 ++Contact: Luka Kovacic ++Description: (RW) Internal factory assigned serial number ++ ++What: /sys/bus/serial/devices/.../version ++Date: September 2020 ++Contact: Luka Kovacic ++Description: (RO) Internal MCU firmware version ++ ++What: /sys/bus/serial/devices/.../protocol_version ++Date: September 2020 ++Contact: Luka Kovacic ++Description: (RO) Internal MCU communication protocol version ++ ++What: /sys/bus/serial/devices/.../power_loss_recovery ++Date: September 2020 ++Contact: Luka Kovacic ++Description: (RW) Host platform power loss recovery settings ++ Value mapping: 0 - Always-On, 1 - Always-Off, 2 - Always-AC, 3 - Always-WA ++ ++What: /sys/bus/serial/devices/.../bootloader_mode ++Date: September 2020 ++Contact: Luka Kovacic ++Description: (RO) Internal MCU bootloader mode status ++ Value mapping: ++ 0 - normal mode ++ 1 - bootloader mode ++ ++What: /sys/bus/serial/devices/.../power_status ++Date: September 2020 ++Contact: Luka Kovacic ++Description: (RO) Power status indicates the host platform power on method. ++ Value mapping (bitwise list): ++ 0x80 - Null ++ 0x40 - Firmware flag ++ 0x20 - Power loss detection flag (powered off) ++ 0x10 - Power loss detection flag (AC mode) ++ 0x08 - Button power on ++ 0x04 - Wake-on-LAN power on ++ 0x02 - RTC alarm power on ++ 0x01 - AC recover power on ++ ++What: /sys/bus/serial/devices/.../build_info ++Date: September 2020 ++Contact: Luka Kovacic ++Description: (RO) Internal MCU firmware build date ++ Format: yyyy/mm/dd hh:mm ++ ++What: /sys/bus/serial/devices/.../ac_recovery_status ++Date: September 2020 ++Contact: Luka Kovacic ++Description: (RO) Host platform AC recovery status value ++ Value mapping: ++ 0 - board has not been recovered from power down ++ 1 - board has been recovered from power down diff --git a/target/linux/mvebu/patches-5.4/906-Documentation-hwmon-Add-iei-wt61p803-puzzle-hwmon-dr.patch b/target/linux/mvebu/patches-5.4/906-Documentation-hwmon-Add-iei-wt61p803-puzzle-hwmon-dr.patch new file mode 100644 index 0000000000..aaac99ab5d --- /dev/null +++ b/target/linux/mvebu/patches-5.4/906-Documentation-hwmon-Add-iei-wt61p803-puzzle-hwmon-dr.patch @@ -0,0 +1,74 @@ +From 0aff3e5923fecc6842473ad07a688d6e2f2c2d55 Mon Sep 17 00:00:00 2001 +From: Luka Kovacic +Date: Tue, 24 Aug 2021 12:44:37 +0000 +Subject: [PATCH 6/7] Documentation/hwmon: Add iei-wt61p803-puzzle hwmon driver + documentation + +Add the iei-wt61p803-puzzle driver hwmon driver interface documentation. + +Signed-off-by: Luka Kovacic +Signed-off-by: Pavo Banicevic +Cc: Luka Perkov +Cc: Robert Marko +--- + .../hwmon/iei-wt61p803-puzzle-hwmon.rst | 43 +++++++++++++++++++ + Documentation/hwmon/index.rst | 1 + + 2 files changed, 44 insertions(+) + create mode 100644 Documentation/hwmon/iei-wt61p803-puzzle-hwmon.rst + +--- /dev/null ++++ b/Documentation/hwmon/iei-wt61p803-puzzle-hwmon.rst +@@ -0,0 +1,43 @@ ++.. SPDX-License-Identifier: GPL-2.0-only ++ ++Kernel driver iei-wt61p803-puzzle-hwmon ++======================================= ++ ++Supported chips: ++ * IEI WT61P803 PUZZLE for IEI Puzzle M801 ++ ++ Prefix: 'iei-wt61p803-puzzle-hwmon' ++ ++Author: Luka Kovacic ++ ++ ++Description ++----------- ++ ++This driver adds fan and temperature sensor reading for some IEI Puzzle ++series boards. ++ ++Sysfs attributes ++---------------- ++ ++The following attributes are supported: ++ ++- IEI WT61P803 PUZZLE for IEI Puzzle M801 ++ ++/sys files in hwmon subsystem ++----------------------------- ++ ++================= == ===================================================== ++fan[1-5]_input RO files for fan speed (in RPM) ++pwm[1-2] RW files for fan[1-2] target duty cycle (0..255) ++temp[1-2]_input RO files for temperature sensors, in millidegree Celsius ++================= == ===================================================== ++ ++/sys files in thermal subsystem ++------------------------------- ++ ++================= == ===================================================== ++cur_state RW file for current cooling state of the cooling device ++ (0..max_state) ++max_state RO file for maximum cooling state of the cooling device ++================= == ===================================================== +--- a/Documentation/hwmon/index.rst ++++ b/Documentation/hwmon/index.rst +@@ -62,6 +62,7 @@ Hardware Monitoring Kernel Drivers + ibmaem + ibm-cffps + ibmpowernv ++ iei-wt61p803-puzzle-hwmon + ina209 + ina2xx + ina3221 diff --git a/target/linux/mvebu/patches-5.4/907-MAINTAINERS-Add-an-entry-for-the-IEI-WT61P803-PUZZLE.patch b/target/linux/mvebu/patches-5.4/907-MAINTAINERS-Add-an-entry-for-the-IEI-WT61P803-PUZZLE.patch new file mode 100644 index 0000000000..830cf33ce4 --- /dev/null +++ b/target/linux/mvebu/patches-5.4/907-MAINTAINERS-Add-an-entry-for-the-IEI-WT61P803-PUZZLE.patch @@ -0,0 +1,41 @@ +From 12479baad28d2a08c6cb9e83471057635fa1635c Mon Sep 17 00:00:00 2001 +From: Luka Kovacic +Date: Tue, 24 Aug 2021 12:44:38 +0000 +Subject: [PATCH 7/7] MAINTAINERS: Add an entry for the IEI WT61P803 PUZZLE + driver + +Add an entry for the IEI WT61P803 PUZZLE driver (MFD, HWMON, LED drivers). + +Signed-off-by: Luka Kovacic +Signed-off-by: Pavo Banicevic +Cc: Luka Perkov +Cc: Robert Marko +--- + MAINTAINERS | 16 ++++++++++++++++ + 1 file changed, 16 insertions(+) + +--- a/MAINTAINERS ++++ b/MAINTAINERS +@@ -7929,6 +7929,22 @@ F: include/net/cfg802154.h + F: include/net/ieee802154_netdev.h + F: Documentation/networking/ieee802154.rst + ++IEI WT61P803 M801 MFD DRIVER ++M: Luka Kovacic ++M: Luka Perkov ++M: Goran Medic ++L: linux-kernel@vger.kernel.org ++S: Maintained ++F: Documentation/ABI/stable/sysfs-driver-iei-wt61p803-puzzle ++F: Documentation/devicetree/bindings/hwmon/iei,wt61p803-puzzle-hwmon.yaml ++F: Documentation/devicetree/bindings/leds/iei,wt61p803-puzzle-leds.yaml ++F: Documentation/devicetree/bindings/mfd/iei,wt61p803-puzzle.yaml ++F: Documentation/hwmon/iei-wt61p803-puzzle-hwmon.rst ++F: drivers/hwmon/iei-wt61p803-puzzle-hwmon.c ++F: drivers/leds/leds-iei-wt61p803-puzzle.c ++F: drivers/mfd/iei-wt61p803-puzzle.c ++F: include/linux/mfd/iei-wt61p803-puzzle.h ++ + IFE PROTOCOL + M: Yotam Gigi + M: Jamal Hadi Salim diff --git a/target/linux/mvebu/patches-5.4/910-drivers-leds-wt61p803-puzzle-improvements.patch b/target/linux/mvebu/patches-5.4/910-drivers-leds-wt61p803-puzzle-improvements.patch new file mode 100644 index 0000000000..1e065ed6e7 --- /dev/null +++ b/target/linux/mvebu/patches-5.4/910-drivers-leds-wt61p803-puzzle-improvements.patch @@ -0,0 +1,247 @@ +--- a/drivers/leds/leds-iei-wt61p803-puzzle.c ++++ b/drivers/leds/leds-iei-wt61p803-puzzle.c +@@ -9,10 +9,13 @@ + #include + #include + #include ++#include + #include + #include + #include + ++#define IEI_LEDS_MAX 4 ++ + enum iei_wt61p803_puzzle_led_state { + IEI_LED_OFF = 0x30, + IEI_LED_ON = 0x31, +@@ -34,6 +37,9 @@ struct iei_wt61p803_puzzle_led { + unsigned char response_buffer[IEI_WT61P803_PUZZLE_BUF_SIZE]; + struct mutex lock; /* mutex to protect led_power_state */ + int led_power_state; ++ int id; ++ bool blinking; ++ bool active_low; + }; + + static inline struct iei_wt61p803_puzzle_led *cdev_to_iei_wt61p803_puzzle_led +@@ -51,10 +57,20 @@ static int iei_wt61p803_puzzle_led_brigh + size_t reply_size; + int ret; + ++ mutex_lock(&priv->lock); ++ if (priv->blinking) { ++ if (brightness == LED_OFF) ++ priv->blinking = false; ++ else ++ return 0; ++ } ++ mutex_unlock(&priv->lock); ++ + led_power_cmd[0] = IEI_WT61P803_PUZZLE_CMD_HEADER_START; + led_power_cmd[1] = IEI_WT61P803_PUZZLE_CMD_LED; +- led_power_cmd[2] = IEI_WT61P803_PUZZLE_CMD_LED_POWER; +- led_power_cmd[3] = brightness == LED_OFF ? IEI_LED_OFF : IEI_LED_ON; ++ led_power_cmd[2] = IEI_WT61P803_PUZZLE_CMD_LED_SET(priv->id); ++ led_power_cmd[3] = ((brightness == LED_OFF) ^ priv->active_low) ? ++ IEI_LED_OFF : IEI_LED_ON; + + ret = iei_wt61p803_puzzle_write_command(priv->mcu, led_power_cmd, + sizeof(led_power_cmd), +@@ -90,39 +106,164 @@ static enum led_brightness iei_wt61p803_ + return led_state; + } + ++static int iei_wt61p803_puzzle_led_set_blink(struct led_classdev *cdev, ++ unsigned long *delay_on, ++ unsigned long *delay_off) ++{ ++ struct iei_wt61p803_puzzle_led *priv = cdev_to_iei_wt61p803_puzzle_led(cdev); ++ unsigned char led_blink_cmd[5] = {}; ++ unsigned char resp_buf[IEI_WT61P803_PUZZLE_BUF_SIZE]; ++ size_t reply_size; ++ int ret = 0; ++ ++ /* set defaults */ ++ if (!*delay_on && !*delay_off) { ++ *delay_on = 500; ++ *delay_off = 500; ++ } ++ ++ /* minimum delay for soft-driven blinking is 50ms to keep load low */ ++ if (*delay_on < 50) ++ *delay_on = 50; ++ ++ if (*delay_off < 50) ++ *delay_off = 50; ++ ++ if (*delay_on != *delay_off) ++ return -EINVAL; ++ ++ /* aggressively offload blinking to hardware, if possible */ ++ if (*delay_on < 100) { ++ return -EINVAL; ++ } else if (*delay_on < 200) { ++ *delay_on = 100; ++ *delay_off = 100; ++ } else if (*delay_on <= 500) { ++ *delay_on = 500; ++ *delay_off = 500; ++ } else { ++ return -EINVAL; ++ } ++ ++ led_blink_cmd[0] = IEI_WT61P803_PUZZLE_CMD_HEADER_START; ++ led_blink_cmd[1] = IEI_WT61P803_PUZZLE_CMD_LED; ++ led_blink_cmd[2] = IEI_WT61P803_PUZZLE_CMD_LED_SET(priv->id); ++ led_blink_cmd[3] = (*delay_on == 100)?IEI_LED_BLINK_5HZ:IEI_LED_BLINK_1HZ; ++ ++ ret = iei_wt61p803_puzzle_write_command(priv->mcu, led_blink_cmd, ++ sizeof(led_blink_cmd), ++ resp_buf, ++ &reply_size); ++ ++ if (ret) ++ return ret; ++ ++ if (reply_size != 3) ++ return -EIO; ++ ++ if (!(resp_buf[0] == IEI_WT61P803_PUZZLE_CMD_HEADER_START && ++ resp_buf[1] == IEI_WT61P803_PUZZLE_CMD_RESPONSE_OK && ++ resp_buf[2] == IEI_WT61P803_PUZZLE_CHECKSUM_RESPONSE_OK)) ++ return -EIO; ++ ++ mutex_lock(&priv->lock); ++ priv->blinking = true; ++ mutex_unlock(&priv->lock); ++ ++ return ret; ++} ++ ++static int iei_wt61p803_puzzle_led_set_dt_default(struct led_classdev *cdev, ++ struct device_node *np) ++{ ++ const char *state; ++ int ret = 0; ++ ++ state = of_get_property(np, "default-state", NULL); ++ if (state) { ++ if (!strcmp(state, "on")) { ++ ret = ++ iei_wt61p803_puzzle_led_brightness_set_blocking( ++ cdev, cdev->max_brightness); ++ } else { ++ ret = iei_wt61p803_puzzle_led_brightness_set_blocking( ++ cdev, LED_OFF); ++ } ++ } ++ ++ return ret; ++} ++ + static int iei_wt61p803_puzzle_led_probe(struct platform_device *pdev) + { + struct device *dev = &pdev->dev; ++ struct device_node *np = dev_of_node(dev); ++ struct device_node *child; + struct iei_wt61p803_puzzle *mcu = dev_get_drvdata(dev->parent); + struct iei_wt61p803_puzzle_led *priv; +- struct led_init_data init_data = {}; +- struct fwnode_handle *child; + int ret; ++ u32 reg; + +- if (device_get_child_node_count(dev) != 1) ++ if (device_get_child_node_count(dev) > IEI_LEDS_MAX) + return -EINVAL; + +- priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); +- if (!priv) +- return -ENOMEM; +- +- priv->mcu = mcu; +- priv->led_power_state = 1; +- mutex_init(&priv->lock); +- dev_set_drvdata(dev, priv); +- +- child = device_get_next_child_node(dev, NULL); +- init_data.fwnode = child; +- +- priv->cdev.brightness_set_blocking = iei_wt61p803_puzzle_led_brightness_set_blocking; +- priv->cdev.brightness_get = iei_wt61p803_puzzle_led_brightness_get; +- priv->cdev.max_brightness = 1; ++ for_each_available_child_of_node(np, child) { ++ struct led_init_data init_data = {}; + +- ret = devm_led_classdev_register_ext(dev, &priv->cdev, &init_data); +- if (ret) +- dev_err(dev, "Could not register LED\n"); ++ ret = of_property_read_u32(child, "reg", ®); ++ if (ret) { ++ dev_err(dev, "Failed to read led 'reg' property\n"); ++ goto put_child_node; ++ } ++ ++ if (reg > IEI_LEDS_MAX) { ++ dev_err(dev, "Invalid led reg %u\n", reg); ++ ret = -EINVAL; ++ goto put_child_node; ++ } ++ ++ priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); ++ if (!priv) { ++ ret = -ENOMEM; ++ goto put_child_node; ++ } ++ ++ mutex_init(&priv->lock); ++ ++ dev_set_drvdata(dev, priv); ++ ++ if (of_property_read_bool(child, "active-low")) ++ priv->active_low = true; ++ ++ priv->mcu = mcu; ++ priv->id = reg; ++ priv->led_power_state = 1; ++ priv->blinking = false; ++ init_data.fwnode = of_fwnode_handle(child); ++ ++ priv->cdev.brightness_set_blocking = iei_wt61p803_puzzle_led_brightness_set_blocking; ++ priv->cdev.brightness_get = iei_wt61p803_puzzle_led_brightness_get; ++ priv->cdev.blink_set = iei_wt61p803_puzzle_led_set_blink; ++ ++ priv->cdev.max_brightness = 1; ++ ++ ret = iei_wt61p803_puzzle_led_set_dt_default(&priv->cdev, child); ++ if (ret) { ++ dev_err(dev, "Could apply default from DT\n"); ++ goto put_child_node; ++ } ++ ++ ret = devm_led_classdev_register_ext(dev, &priv->cdev, &init_data); ++ if (ret) { ++ dev_err(dev, "Could not register LED\n"); ++ goto put_child_node; ++ } ++ } ++ ++ return ret; + +- fwnode_handle_put(child); ++put_child_node: ++ of_node_put(child); + return ret; + } + +--- a/include/linux/mfd/iei-wt61p803-puzzle.h ++++ b/include/linux/mfd/iei-wt61p803-puzzle.h +@@ -36,7 +36,7 @@ + #define IEI_WT61P803_PUZZLE_CMD_FUNCTION_OTHER_POWER_LOSS 0x41 /* A */ + + #define IEI_WT61P803_PUZZLE_CMD_LED 0x52 /* R */ +-#define IEI_WT61P803_PUZZLE_CMD_LED_POWER 0x31 /* 1 */ ++#define IEI_WT61P803_PUZZLE_CMD_LED_SET(n) (0x30 | (n)) + + #define IEI_WT61P803_PUZZLE_CMD_TEMP 0x54 /* T */ + #define IEI_WT61P803_PUZZLE_CMD_TEMP_ALL 0x41 /* A */ From 1e5df4d5506adbc70c645189e55cef85b07a1196 Mon Sep 17 00:00:00 2001 From: Daniel Golle Date: Tue, 21 Dec 2021 21:44:37 +0000 Subject: [PATCH 18/43] mvebu: puzzle-mcu: improve led driver Set blinking mode using scheduled work instead of blocking which may result in deadlocks. Add dynamic kprintf debugging hexdumps of all MCU rx and tx. Signed-off-by: Daniel Golle (cherry picked from commit 7e4c1cca8a137ca4fe5132b8c058e52ba82defac) --- ...rs-leds-wt61p803-puzzle-improvements.patch | 126 +++++++++++------- 1 file changed, 75 insertions(+), 51 deletions(-) diff --git a/target/linux/mvebu/patches-5.4/910-drivers-leds-wt61p803-puzzle-improvements.patch b/target/linux/mvebu/patches-5.4/910-drivers-leds-wt61p803-puzzle-improvements.patch index 1e065ed6e7..150a65498c 100644 --- a/target/linux/mvebu/patches-5.4/910-drivers-leds-wt61p803-puzzle-improvements.patch +++ b/target/linux/mvebu/patches-5.4/910-drivers-leds-wt61p803-puzzle-improvements.patch @@ -1,6 +1,6 @@ --- a/drivers/leds/leds-iei-wt61p803-puzzle.c +++ b/drivers/leds/leds-iei-wt61p803-puzzle.c -@@ -9,10 +9,13 @@ +@@ -9,9 +9,13 @@ #include #include #include @@ -8,34 +8,34 @@ #include #include #include - -+#define IEI_LEDS_MAX 4 ++#include + ++#define IEI_LEDS_MAX 4 + enum iei_wt61p803_puzzle_led_state { IEI_LED_OFF = 0x30, - IEI_LED_ON = 0x31, -@@ -34,6 +37,9 @@ struct iei_wt61p803_puzzle_led { +@@ -33,7 +37,11 @@ struct iei_wt61p803_puzzle_led { + struct iei_wt61p803_puzzle *mcu; unsigned char response_buffer[IEI_WT61P803_PUZZLE_BUF_SIZE]; struct mutex lock; /* mutex to protect led_power_state */ ++ struct work_struct work; int led_power_state; + int id; -+ bool blinking; ++ u8 blinking; + bool active_low; }; static inline struct iei_wt61p803_puzzle_led *cdev_to_iei_wt61p803_puzzle_led -@@ -51,10 +57,20 @@ static int iei_wt61p803_puzzle_led_brigh +@@ -51,10 +59,18 @@ static int iei_wt61p803_puzzle_led_brigh size_t reply_size; int ret; -+ mutex_lock(&priv->lock); + if (priv->blinking) { + if (brightness == LED_OFF) -+ priv->blinking = false; ++ priv->blinking = 0; + else + return 0; + } -+ mutex_unlock(&priv->lock); + led_power_cmd[0] = IEI_WT61P803_PUZZLE_CMD_HEADER_START; led_power_cmd[1] = IEI_WT61P803_PUZZLE_CMD_LED; @@ -43,22 +43,40 @@ - led_power_cmd[3] = brightness == LED_OFF ? IEI_LED_OFF : IEI_LED_ON; + led_power_cmd[2] = IEI_WT61P803_PUZZLE_CMD_LED_SET(priv->id); + led_power_cmd[3] = ((brightness == LED_OFF) ^ priv->active_low) ? -+ IEI_LED_OFF : IEI_LED_ON; ++ IEI_LED_OFF : priv->blinking?priv->blinking:IEI_LED_ON; ret = iei_wt61p803_puzzle_write_command(priv->mcu, led_power_cmd, sizeof(led_power_cmd), -@@ -90,39 +106,164 @@ static enum led_brightness iei_wt61p803_ +@@ -90,39 +106,166 @@ static enum led_brightness iei_wt61p803_ return led_state; } ++static void iei_wt61p803_puzzle_led_apply_blink(struct work_struct *work) ++{ ++ struct iei_wt61p803_puzzle_led *priv = container_of(work, struct iei_wt61p803_puzzle_led, work); ++ unsigned char led_blink_cmd[5] = {}; ++ unsigned char resp_buf[IEI_WT61P803_PUZZLE_BUF_SIZE]; ++ size_t reply_size; ++ ++ led_blink_cmd[0] = IEI_WT61P803_PUZZLE_CMD_HEADER_START; ++ led_blink_cmd[1] = IEI_WT61P803_PUZZLE_CMD_LED; ++ led_blink_cmd[2] = IEI_WT61P803_PUZZLE_CMD_LED_SET(priv->id); ++ led_blink_cmd[3] = priv->blinking; ++ ++ iei_wt61p803_puzzle_write_command(priv->mcu, led_blink_cmd, ++ sizeof(led_blink_cmd), ++ resp_buf, ++ &reply_size); ++ ++ return; ++} ++ +static int iei_wt61p803_puzzle_led_set_blink(struct led_classdev *cdev, + unsigned long *delay_on, + unsigned long *delay_off) +{ + struct iei_wt61p803_puzzle_led *priv = cdev_to_iei_wt61p803_puzzle_led(cdev); -+ unsigned char led_blink_cmd[5] = {}; -+ unsigned char resp_buf[IEI_WT61P803_PUZZLE_BUF_SIZE]; -+ size_t reply_size; ++ u8 blink_mode = 0; + int ret = 0; + + /* set defaults */ @@ -67,57 +85,39 @@ + *delay_off = 500; + } + -+ /* minimum delay for soft-driven blinking is 50ms to keep load low */ -+ if (*delay_on < 50) -+ *delay_on = 50; ++ /* minimum delay for soft-driven blinking is 100ms to keep load low */ ++ if (*delay_on < 100) ++ *delay_on = 100; + -+ if (*delay_off < 50) -+ *delay_off = 50; ++ if (*delay_off < 100) ++ *delay_off = 100; + -+ if (*delay_on != *delay_off) -+ return -EINVAL; -+ -+ /* aggressively offload blinking to hardware, if possible */ -+ if (*delay_on < 100) { -+ return -EINVAL; -+ } else if (*delay_on < 200) { ++ /* offload blinking to hardware, if possible */ ++ if (*delay_on != *delay_off) { ++ ret = -EINVAL; ++ } else if (*delay_on == 100) { ++ blink_mode = IEI_LED_BLINK_5HZ; + *delay_on = 100; + *delay_off = 100; + } else if (*delay_on <= 500) { ++ blink_mode = IEI_LED_BLINK_1HZ; + *delay_on = 500; + *delay_off = 500; + } else { -+ return -EINVAL; ++ ret = -EINVAL; + } + -+ led_blink_cmd[0] = IEI_WT61P803_PUZZLE_CMD_HEADER_START; -+ led_blink_cmd[1] = IEI_WT61P803_PUZZLE_CMD_LED; -+ led_blink_cmd[2] = IEI_WT61P803_PUZZLE_CMD_LED_SET(priv->id); -+ led_blink_cmd[3] = (*delay_on == 100)?IEI_LED_BLINK_5HZ:IEI_LED_BLINK_1HZ; -+ -+ ret = iei_wt61p803_puzzle_write_command(priv->mcu, led_blink_cmd, -+ sizeof(led_blink_cmd), -+ resp_buf, -+ &reply_size); -+ -+ if (ret) -+ return ret; -+ -+ if (reply_size != 3) -+ return -EIO; -+ -+ if (!(resp_buf[0] == IEI_WT61P803_PUZZLE_CMD_HEADER_START && -+ resp_buf[1] == IEI_WT61P803_PUZZLE_CMD_RESPONSE_OK && -+ resp_buf[2] == IEI_WT61P803_PUZZLE_CHECKSUM_RESPONSE_OK)) -+ return -EIO; -+ + mutex_lock(&priv->lock); -+ priv->blinking = true; ++ priv->blinking = blink_mode; + mutex_unlock(&priv->lock); + ++ if (blink_mode) ++ schedule_work(&priv->work); ++ + return ret; +} + ++ +static int iei_wt61p803_puzzle_led_set_dt_default(struct led_classdev *cdev, + struct device_node *np) +{ @@ -204,7 +204,7 @@ + priv->mcu = mcu; + priv->id = reg; + priv->led_power_state = 1; -+ priv->blinking = false; ++ priv->blinking = 0; + init_data.fwnode = of_fwnode_handle(child); + + priv->cdev.brightness_set_blocking = iei_wt61p803_puzzle_led_brightness_set_blocking; @@ -213,6 +213,8 @@ + + priv->cdev.max_brightness = 1; + ++ INIT_WORK(&priv->work, iei_wt61p803_puzzle_led_apply_blink); ++ + ret = iei_wt61p803_puzzle_led_set_dt_default(&priv->cdev, child); + if (ret) { + dev_err(dev, "Could apply default from DT\n"); @@ -245,3 +247,25 @@ #define IEI_WT61P803_PUZZLE_CMD_TEMP 0x54 /* T */ #define IEI_WT61P803_PUZZLE_CMD_TEMP_ALL 0x41 /* A */ +--- a/drivers/mfd/iei-wt61p803-puzzle.c ++++ b/drivers/mfd/iei-wt61p803-puzzle.c +@@ -176,6 +176,9 @@ static int iei_wt61p803_puzzle_recv_buf( + struct iei_wt61p803_puzzle *mcu = serdev_device_get_drvdata(serdev); + int ret; + ++ print_hex_dump_debug("puzzle-mcu rx: ", DUMP_PREFIX_NONE, ++ 16, 1, data, size, false); ++ + ret = iei_wt61p803_puzzle_process_resp(mcu, data, size); + /* Return the number of processed bytes if function returns error, + * discard the remaining incoming data, since the frame this data +@@ -246,6 +249,9 @@ int iei_wt61p803_puzzle_write_command(st + + cmd[size - 1] = iei_wt61p803_puzzle_checksum(cmd, size - 1); + ++ print_hex_dump_debug("puzzle-mcu tx: ", DUMP_PREFIX_NONE, ++ 16, 1, cmd, size, false); ++ + /* Initialize reply struct */ + reinit_completion(&mcu->reply->received); + mcu->reply->size = 0; From 280bb7c10c37027491879be7da6f1c43d0976f1a Mon Sep 17 00:00:00 2001 From: Daniel Golle Date: Tue, 21 Dec 2021 21:49:25 +0000 Subject: [PATCH 19/43] mvebu: puzzle-m902: add GPIO reset button Add reset button to device tree so it has the function expected from usual OpenWrt devices. Signed-off-by: Daniel Golle (cherry picked from commit ddad936fc60ced1783232af3eddee75347f0d08f) --- .../arm64/boot/dts/marvell/cn9132-puzzle-m902.dts | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts b/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts index 8d2d53d03c..bfa7874a67 100644 --- a/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts +++ b/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts @@ -8,6 +8,7 @@ #include "cn9130.dtsi" #include +#include / { model = "iEi Puzzle-M902"; @@ -49,6 +50,16 @@ reg = <0x0 0x0 0x0 0x80000000>; }; + gpio_keys { + compatible = "gpio-keys"; + + reset { + label = "Reset"; + linux,code = ; + gpios = <&cp0_gpio2 4 GPIO_ACTIVE_LOW>; + }; + }; + cp2_reg_usb3_vbus0: cp2_usb3_vbus@0 { compatible = "regulator-fixed"; regulator-name = "cp2-xhci0-vbus"; From a03840a1a9b9945bd25bdefc481ca877bb19bb7b Mon Sep 17 00:00:00 2001 From: Daniel Golle Date: Tue, 21 Dec 2021 21:50:32 +0000 Subject: [PATCH 20/43] mvebu: puzzle-m901: add LEDs, fan and reset button Wire up MCU driver for LEDs, fan and temperature sensor, and add GPIO reset button just like on the M902 also on the Puzzle M901. Signed-off-by: Daniel Golle (cherry picked from commit 3684b494ddd540b811de44497f0d11309bfd1911) --- .../boot/dts/marvell/cn9131-puzzle-m901.dts | 84 +++++++++++++++++++ 1 file changed, 84 insertions(+) diff --git a/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9131-puzzle-m901.dts b/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9131-puzzle-m901.dts index 58e749490a..acf2ed6422 100644 --- a/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9131-puzzle-m901.dts +++ b/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9131-puzzle-m901.dts @@ -8,6 +8,7 @@ #include "cn9130.dtsi" #include +#include / { model = "iEi Puzzle-M901"; @@ -31,12 +32,26 @@ gpio2 = &cp0_gpio2; gpio3 = &cp1_gpio1; gpio4 = &cp1_gpio2; + led-boot = &led_power; + led-failsafe = &led_info; + led-running = &led_power; + led-upgrade = &led_info; }; memory@00000000 { device_type = "memory"; reg = <0x0 0x0 0x0 0x80000000>; }; + + gpio_keys { + compatible = "gpio-keys"; + + reset { + label = "Reset"; + linux,code = ; + gpios = <&cp0_gpio2 4 GPIO_ACTIVE_LOW>; + }; + }; }; &uart0 { @@ -45,6 +60,75 @@ &cp0_uart0 { status = "okay"; + + puzzle-mcu { + compatible = "iei,wt61p803-puzzle"; + #address-cells = <1>; + #size-cells = <1>; + current-speed = <115200>; + enable-beep; + status = "okay"; + + leds { + compatible = "iei,wt61p803-puzzle-leds"; + #address-cells = <1>; + #size-cells = <0>; + status = "okay"; + + led@0 { + reg = <0>; + label = "white:network"; + active-low; + }; + + led@1 { + reg = <1>; + label = "green:cloud"; + active-low; + }; + + led_info: led@2 { + reg = <2>; + label = "orange:info"; + active-low; + }; + + led_power: led@3 { + reg = <3>; + label = "yellow:power"; + active-low; + default-state = "on"; + }; + }; + + hwmon { + compatible = "iei,wt61p803-puzzle-hwmon"; + #address-cells = <1>; + #size-cells = <0>; + + chassis_fan_group0: fan-group@0 { + #cooling-cells = <2>; + reg = <0x00>; + cooling-levels = <64 102 170 230 250>; + }; + }; + }; +}; + +&ap_thermal_cpu1 { + trips { + cpu_active: cpu-active { + temperature = <44000>; + hysteresis = <2000>; + type = "active"; + }; + }; + cooling-maps { + fan-map { + trip = <&cpu_active>; + cooling-device = <&chassis_fan_group0 64 THERMAL_NO_LIMIT>; + }; + }; }; /* on-board eMMC - U9 */ From ee5750043c83f11f3680fd5b8828043cc6632054 Mon Sep 17 00:00:00 2001 From: Daniel Golle Date: Tue, 2 Nov 2021 00:55:40 +0000 Subject: [PATCH 21/43] mvebu: import patch enabling AQR112 and AQR412 PHY Copy and refresh patch enabling AQR112 and AQR412 Ethernet PHY from layerscape (5.4) target to mvebu (5.4) as AQR112 can also be found in IEI Puzzle devices. Signed-off-by: Daniel Golle --- ...hy-aquantia-enable-AQR112-and-AQR412.patch | 144 ++++++++++++++++++ 1 file changed, 144 insertions(+) create mode 100644 target/linux/mvebu/patches-5.4/721-net-phy-aquantia-enable-AQR112-and-AQR412.patch diff --git a/target/linux/mvebu/patches-5.4/721-net-phy-aquantia-enable-AQR112-and-AQR412.patch b/target/linux/mvebu/patches-5.4/721-net-phy-aquantia-enable-AQR112-and-AQR412.patch new file mode 100644 index 0000000000..843aa7dc9e --- /dev/null +++ b/target/linux/mvebu/patches-5.4/721-net-phy-aquantia-enable-AQR112-and-AQR412.patch @@ -0,0 +1,144 @@ +From 5f62951fba63a9f9cfff564209426bdea5fcc371 Mon Sep 17 00:00:00 2001 +From: Alex Marginean +Date: Tue, 27 Aug 2019 15:16:56 +0300 +Subject: [PATCH] drivers: net: phy: aquantia: enable AQR112 and AQR412 + +Adds support for AQR112 and AQR412 which is mostly based on existing code +with the addition of code configuring the protocol on system side. +This allows changing the system side protocol without having to deploy a +different firmware on the PHY. + +Signed-off-by: Alex Marginean +--- + drivers/net/phy/aquantia_main.c | 88 +++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 88 insertions(+) + +--- a/drivers/net/phy/aquantia_main.c ++++ b/drivers/net/phy/aquantia_main.c +@@ -20,8 +20,11 @@ + #define PHY_ID_AQR105 0x03a1b4a2 + #define PHY_ID_AQR106 0x03a1b4d0 + #define PHY_ID_AQR107 0x03a1b4e0 ++#define PHY_ID_AQR112 0x03a1b662 + #define PHY_ID_AQCS109 0x03a1b5c2 + #define PHY_ID_AQR405 0x03a1b4b0 ++#define PHY_ID_AQR412 0x03a1b712 ++ + + #define MDIO_PHYXS_VEND_IF_STATUS 0xe812 + #define MDIO_PHYXS_VEND_IF_STATUS_TYPE_MASK GENMASK(7, 3) +@@ -121,6 +124,29 @@ + #define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL2 BIT(1) + #define VEND1_GLOBAL_INT_VEND_MASK_GLOBAL3 BIT(0) + ++/* registers in MDIO_MMD_VEND1 region */ ++#define AQUANTIA_VND1_GLOBAL_SC 0x000 ++#define AQUANTIA_VND1_GLOBAL_SC_LP BIT(0xb) ++ ++/* global start rate, the protocol associated with this speed is used by default ++ * on SI. ++ */ ++#define AQUANTIA_VND1_GSTART_RATE 0x31a ++#define AQUANTIA_VND1_GSTART_RATE_OFF 0 ++#define AQUANTIA_VND1_GSTART_RATE_100M 1 ++#define AQUANTIA_VND1_GSTART_RATE_1G 2 ++#define AQUANTIA_VND1_GSTART_RATE_10G 3 ++#define AQUANTIA_VND1_GSTART_RATE_2_5G 4 ++#define AQUANTIA_VND1_GSTART_RATE_5G 5 ++ ++/* SYSCFG registers for 100M, 1G, 2.5G, 5G, 10G */ ++#define AQUANTIA_VND1_GSYSCFG_BASE 0x31b ++#define AQUANTIA_VND1_GSYSCFG_100M 0 ++#define AQUANTIA_VND1_GSYSCFG_1G 1 ++#define AQUANTIA_VND1_GSYSCFG_2_5G 2 ++#define AQUANTIA_VND1_GSYSCFG_5G 3 ++#define AQUANTIA_VND1_GSYSCFG_10G 4 ++ + struct aqr107_hw_stat { + const char *name; + int reg; +@@ -241,6 +267,51 @@ static int aqr_config_aneg(struct phy_de + return genphy_c45_check_and_restart_aneg(phydev, changed); + } + ++static struct { ++ u16 syscfg; ++ int cnt; ++ u16 start_rate; ++} aquantia_syscfg[PHY_INTERFACE_MODE_MAX] = { ++ [PHY_INTERFACE_MODE_SGMII] = {0x04b, AQUANTIA_VND1_GSYSCFG_1G, ++ AQUANTIA_VND1_GSTART_RATE_1G}, ++ [PHY_INTERFACE_MODE_2500BASEX] = {0x144, AQUANTIA_VND1_GSYSCFG_2_5G, ++ AQUANTIA_VND1_GSTART_RATE_2_5G}, ++ [PHY_INTERFACE_MODE_XGMII] = {0x100, AQUANTIA_VND1_GSYSCFG_10G, ++ AQUANTIA_VND1_GSTART_RATE_10G}, ++ [PHY_INTERFACE_MODE_USXGMII] = {0x080, AQUANTIA_VND1_GSYSCFG_10G, ++ AQUANTIA_VND1_GSTART_RATE_10G}, ++}; ++ ++/* Sets up protocol on system side before calling aqr_config_aneg */ ++static int aqr_config_aneg_set_prot(struct phy_device *phydev) ++{ ++ int if_type = phydev->interface; ++ int i; ++ ++ if (!aquantia_syscfg[if_type].cnt) ++ return 0; ++ ++ /* set PHY in low power mode so we can configure protocols */ ++ phy_write_mmd(phydev, MDIO_MMD_VEND1, AQUANTIA_VND1_GLOBAL_SC, ++ AQUANTIA_VND1_GLOBAL_SC_LP); ++ mdelay(10); ++ ++ /* set the default rate to enable the SI link */ ++ phy_write_mmd(phydev, MDIO_MMD_VEND1, AQUANTIA_VND1_GSTART_RATE, ++ aquantia_syscfg[if_type].start_rate); ++ ++ for (i = 0; i <= aquantia_syscfg[if_type].cnt; i++) ++ phy_write_mmd(phydev, MDIO_MMD_VEND1, ++ AQUANTIA_VND1_GSYSCFG_BASE + i, ++ aquantia_syscfg[if_type].syscfg); ++ ++ /* wake PHY back up */ ++ phy_write_mmd(phydev, MDIO_MMD_VEND1, AQUANTIA_VND1_GLOBAL_SC, 0); ++ mdelay(10); ++ ++ return aqr_config_aneg(phydev); ++} ++ + static int aqr_config_intr(struct phy_device *phydev) + { + bool en = phydev->interrupts == PHY_INTERRUPT_ENABLED; +@@ -682,6 +753,22 @@ static struct phy_driver aqr_driver[] = + .ack_interrupt = aqr_ack_interrupt, + .read_status = aqr_read_status, + }, ++{ ++ PHY_ID_MATCH_MODEL(PHY_ID_AQR112), ++ .name = "Aquantia AQR112", ++ .config_aneg = aqr_config_aneg_set_prot, ++ .config_intr = aqr_config_intr, ++ .ack_interrupt = aqr_ack_interrupt, ++ .read_status = aqr107_read_status, ++}, ++{ ++ PHY_ID_MATCH_MODEL(PHY_ID_AQR412), ++ .name = "Aquantia AQR412", ++ .config_aneg = aqr_config_aneg_set_prot, ++ .config_intr = aqr_config_intr, ++ .ack_interrupt = aqr_ack_interrupt, ++ .read_status = aqr107_read_status, ++}, + }; + + module_phy_driver(aqr_driver); +@@ -692,7 +779,9 @@ static struct mdio_device_id __maybe_unu + { PHY_ID_MATCH_MODEL(PHY_ID_AQR105) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQR106) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQR107) }, ++ { PHY_ID_MATCH_MODEL(PHY_ID_AQR112) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQCS109) }, ++ { PHY_ID_MATCH_MODEL(PHY_ID_AQR412) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQR405) }, + { } + }; From daf4301071e7632642e229c4cbe4be9b71a45287 Mon Sep 17 00:00:00 2001 From: Daniel Golle Date: Thu, 23 Dec 2021 17:36:01 +0000 Subject: [PATCH 22/43] mvebu: import patch enabling AQR113 PHY Add PHY ID for the Aquantia AQR113 PHY. Signed-off-by: Daniel Golle --- ...y-aquantia-Add-AQR113-driver-support.patch | 43 +++++++++++++++++++ 1 file changed, 43 insertions(+) create mode 100644 target/linux/mvebu/patches-5.4/722-net-phy-aquantia-Add-AQR113-driver-support.patch diff --git a/target/linux/mvebu/patches-5.4/722-net-phy-aquantia-Add-AQR113-driver-support.patch b/target/linux/mvebu/patches-5.4/722-net-phy-aquantia-Add-AQR113-driver-support.patch new file mode 100644 index 0000000000..2db24149c9 --- /dev/null +++ b/target/linux/mvebu/patches-5.4/722-net-phy-aquantia-Add-AQR113-driver-support.patch @@ -0,0 +1,43 @@ +From 2e677e4ae8f8330f68013163b060d0fda3a43095 Mon Sep 17 00:00:00 2001 +From: "Langer, Thomas" +Date: Fri, 9 Jul 2021 17:36:46 +0200 +Subject: [PATCH] PONRTSYS-8842: aquantia: Add AQR113 driver support + +Add a new entry for AQR113 PHY_ID +--- + drivers/net/phy/aquantia_main.c | 10 ++++++++++ + 1 file changed, 10 insertions(+) + +--- a/drivers/net/phy/aquantia_main.c ++++ b/drivers/net/phy/aquantia_main.c +@@ -21,6 +21,7 @@ + #define PHY_ID_AQR106 0x03a1b4d0 + #define PHY_ID_AQR107 0x03a1b4e0 + #define PHY_ID_AQR112 0x03a1b662 ++#define PHY_ID_AQR113 0x31c31c40 + #define PHY_ID_AQCS109 0x03a1b5c2 + #define PHY_ID_AQR405 0x03a1b4b0 + #define PHY_ID_AQR412 0x03a1b712 +@@ -762,6 +763,14 @@ static struct phy_driver aqr_driver[] = + .read_status = aqr107_read_status, + }, + { ++ PHY_ID_MATCH_MODEL(PHY_ID_AQR113), ++ .name = "Aquantia AQR113", ++ .config_aneg = aqr_config_aneg, ++ .config_intr = aqr_config_intr, ++ .ack_interrupt = aqr_ack_interrupt, ++ .read_status = aqr107_read_status, ++}, ++{ + PHY_ID_MATCH_MODEL(PHY_ID_AQR412), + .name = "Aquantia AQR412", + .config_aneg = aqr_config_aneg_set_prot, +@@ -780,6 +789,7 @@ static struct mdio_device_id __maybe_unu + { PHY_ID_MATCH_MODEL(PHY_ID_AQR106) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQR107) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQR112) }, ++ { PHY_ID_MATCH_MODEL(PHY_ID_AQR113) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQCS109) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQR412) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQR405) }, From 164ed6069cee3c9f9ca4323918a136dc5ea5a15d Mon Sep 17 00:00:00 2001 From: Daniel Golle Date: Thu, 23 Dec 2021 17:36:48 +0000 Subject: [PATCH 23/43] mvebu: add id for AQR112 Ethernet phy variants Add ids for AQR112R and AQR112C 2.5G Ethernet PHYs. Signed-off-by: Daniel Golle --- ...ntia-add-PHY_IDs-for-AQR112-variants.patch | 55 +++++++++++++++++++ 1 file changed, 55 insertions(+) create mode 100644 target/linux/mvebu/patches-5.4/723-net-phy-aquantia-add-PHY_IDs-for-AQR112-variants.patch diff --git a/target/linux/mvebu/patches-5.4/723-net-phy-aquantia-add-PHY_IDs-for-AQR112-variants.patch b/target/linux/mvebu/patches-5.4/723-net-phy-aquantia-add-PHY_IDs-for-AQR112-variants.patch new file mode 100644 index 0000000000..a348f79417 --- /dev/null +++ b/target/linux/mvebu/patches-5.4/723-net-phy-aquantia-add-PHY_IDs-for-AQR112-variants.patch @@ -0,0 +1,55 @@ +From 3b92ee7b7899b6beffb2b484c58326e36612a873 Mon Sep 17 00:00:00 2001 +From: Daniel Golle +Date: Thu, 23 Dec 2021 14:52:56 +0000 +Subject: [PATCH] net: phy: aquantia: add PHY_ID for AQR112R + +As advised by Ian Chang this PHY is used in Puzzle devices. + +Signed-off-by: Daniel Golle +--- + drivers/net/phy/aquantia_main.c | 10 ++++++++++ + 1 file changed, 10 insertions(+) + +--- a/drivers/net/phy/aquantia_main.c ++++ b/drivers/net/phy/aquantia_main.c +@@ -21,6 +21,8 @@ + #define PHY_ID_AQR106 0x03a1b4d0 + #define PHY_ID_AQR107 0x03a1b4e0 + #define PHY_ID_AQR112 0x03a1b662 ++#define PHY_ID_AQR112C 0x03a1b790 ++#define PHY_ID_AQR112R 0x31c31d12 + #define PHY_ID_AQR113 0x31c31c40 + #define PHY_ID_AQCS109 0x03a1b5c2 + #define PHY_ID_AQR405 0x03a1b4b0 +@@ -763,6 +765,22 @@ static struct phy_driver aqr_driver[] = + .read_status = aqr107_read_status, + }, + { ++ PHY_ID_MATCH_MODEL(PHY_ID_AQR112C), ++ .name = "Aquantia AQR112C", ++ .config_aneg = aqr_config_aneg_set_prot, ++ .config_intr = aqr_config_intr, ++ .ack_interrupt = aqr_ack_interrupt, ++ .read_status = aqr107_read_status, ++}, ++{ ++ PHY_ID_MATCH_MODEL(PHY_ID_AQR112R), ++ .name = "Aquantia AQR112R", ++ .config_aneg = aqr_config_aneg_set_prot, ++ .config_intr = aqr_config_intr, ++ .ack_interrupt = aqr_ack_interrupt, ++ .read_status = aqr107_read_status, ++}, ++{ + PHY_ID_MATCH_MODEL(PHY_ID_AQR113), + .name = "Aquantia AQR113", + .config_aneg = aqr_config_aneg, +@@ -789,6 +807,8 @@ static struct mdio_device_id __maybe_unu + { PHY_ID_MATCH_MODEL(PHY_ID_AQR106) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQR107) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQR112) }, ++ { PHY_ID_MATCH_MODEL(PHY_ID_AQR112C) }, ++ { PHY_ID_MATCH_MODEL(PHY_ID_AQR112R) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQR113) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQCS109) }, + { PHY_ID_MATCH_MODEL(PHY_ID_AQR412) }, From 47d82f07105c239e582c8bdf7ac32732f2d5f8f3 Mon Sep 17 00:00:00 2001 From: Daniel Golle Date: Thu, 23 Dec 2021 18:10:05 +0000 Subject: [PATCH 24/43] mvebu: enable Aquantia phy driver for Puzzle devices While on Linux 5.10 this fixes Ethernet link status on all ports and makes 2.5G ports usable in 2.5G and 1G full-duplex mode, when using Linux 5.4 and backported Aquantia phy patches, only 1G mode works on the 2.5G ports and link speed and duplex are not reported correctly from the phy in case of 2.5G. The reasons are probably trivial, but hard to find. As having all ports work at least in 1G speed instead of having them not work at all is still better, push this anyway for now. Signed-off-by: Daniel Golle (cherry picked from commit f81a06408eec28d479f699bd762b703ac65e2150) --- target/linux/mvebu/cortexa72/config-5.4 | 1 + .../boot/dts/marvell/cn9131-puzzle-m901.dts | 12 ++++++------ .../boot/dts/marvell/cn9132-puzzle-m902.dts | 18 +++++++++--------- 3 files changed, 16 insertions(+), 15 deletions(-) diff --git a/target/linux/mvebu/cortexa72/config-5.4 b/target/linux/mvebu/cortexa72/config-5.4 index 106724dc3b..debef1ac2e 100644 --- a/target/linux/mvebu/cortexa72/config-5.4 +++ b/target/linux/mvebu/cortexa72/config-5.4 @@ -1,4 +1,5 @@ CONFIG_64BIT=y +CONFIG_AQUANTIA_PHY=y CONFIG_ARCH_DMA_ADDR_T_64BIT=y CONFIG_ARCH_HAS_CACHE_LINE_SIZE=y CONFIG_ARCH_HAS_FAST_MULTIPLIER=y diff --git a/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9131-puzzle-m901.dts b/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9131-puzzle-m901.dts index acf2ed6422..80d876b4ad 100644 --- a/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9131-puzzle-m901.dts +++ b/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9131-puzzle-m901.dts @@ -169,21 +169,21 @@ status = "okay"; phy-mode = "2500base-x"; phys = <&cp0_comphy2 0>; - managed = "in-band-status"; + phy = <&cp0_nbaset_phy0>; }; &cp0_eth1 { status = "okay"; phy-mode = "2500base-x"; phys = <&cp0_comphy4 1>; - managed = "in-band-status"; + phy = <&cp0_nbaset_phy1>; }; &cp0_eth2 { status = "okay"; phy-mode = "2500base-x"; phys = <&cp0_comphy5 2>; - managed = "in-band-status"; + phy = <&cp0_nbaset_phy2>; }; &cp0_gpio1 { @@ -334,21 +334,21 @@ status = "okay"; phy-mode = "2500base-x"; phys = <&cp1_comphy2 0>; - managed = "in-band-status"; + phy = <&cp1_nbaset_phy0>; }; &cp1_eth1 { status = "okay"; phy-mode = "2500base-x"; phys = <&cp1_comphy4 1>; - managed = "in-band-status"; + phy = <&cp1_nbaset_phy1>; }; &cp1_eth2 { status = "okay"; phy-mode = "2500base-x"; phys = <&cp1_comphy5 2>; - managed = "in-band-status"; + phy = <&cp1_nbaset_phy2>; }; &cp1_sata0 { diff --git a/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts b/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts index bfa7874a67..fd99eb2d13 100644 --- a/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts +++ b/target/linux/mvebu/files/arch/arm64/boot/dts/marvell/cn9132-puzzle-m902.dts @@ -214,21 +214,21 @@ status = "okay"; phy-mode = "10gbase-kr"; phys = <&cp0_comphy2 0>; - managed = "in-band-status"; + phy = <&cp0_nbaset_phy0>; }; &cp0_eth1 { status = "okay"; phy-mode = "2500base-x"; phys = <&cp0_comphy4 1>; - managed = "in-band-status"; + phy = <&cp0_nbaset_phy1>; }; &cp0_eth2 { status = "okay"; phy-mode = "2500base-x"; phys = <&cp0_comphy1 2>; - managed = "in-band-status"; + phy = <&cp0_nbaset_phy2>; }; &cp0_gpio1 { @@ -397,21 +397,21 @@ status = "okay"; phy-mode = "10gbase-kr"; phys = <&cp1_comphy2 0>; - managed = "in-band-status"; + phy = <&cp1_nbaset_phy0>; }; &cp1_eth1 { status = "okay"; phy-mode = "2500base-x"; phys = <&cp1_comphy4 1>; - managed = "in-band-status"; + phy = <&cp1_nbaset_phy1>; }; &cp1_eth2 { status = "okay"; phy-mode = "2500base-x"; phys = <&cp1_comphy1 2>; - managed = "in-band-status"; + phy = <&cp1_nbaset_phy2>; }; &cp1_gpio1 { @@ -498,21 +498,21 @@ status = "okay"; phy-mode = "10gbase-kr"; phys = <&cp2_comphy2 0>; - managed = "in-band-status"; + phy = <&cp2_nbaset_phy0>; }; &cp2_eth1 { status = "okay"; phy-mode = "2500base-x"; phys = <&cp2_comphy4 1>; - managed = "in-band-status"; + phy = <&cp2_nbaset_phy1>; }; &cp2_eth2 { status = "okay"; phy-mode = "2500base-x"; phys = <&cp2_comphy1 2>; - managed = "in-band-status"; + phy = <&cp2_nbaset_phy2>; }; &cp2_gpio1 { From 104774c3b07b1dff14f8987687ad5a99fc5ada8a Mon Sep 17 00:00:00 2001 From: Daniel Golle Date: Thu, 23 Dec 2021 19:01:48 +0000 Subject: [PATCH 25/43] mvebu: puzzle: wan LED and fix default network Fix default network configuration of the Puzzle-M902 so all LAN ports are included in the LAN bridge. Setup network LED to indicate WAN port link status, like vendor firmware does as well. Signed-off-by: Daniel Golle (cherry picked from commit f9782f5bcd13e419abf9c84017ada27fa9764011) --- .../cortexa72/base-files/etc/board.d/01_leds | 20 +++++++++++++++++++ .../base-files/etc/board.d/02_network | 2 +- 2 files changed, 21 insertions(+), 1 deletion(-) create mode 100644 target/linux/mvebu/cortexa72/base-files/etc/board.d/01_leds mode change 100755 => 100644 target/linux/mvebu/cortexa72/base-files/etc/board.d/02_network diff --git a/target/linux/mvebu/cortexa72/base-files/etc/board.d/01_leds b/target/linux/mvebu/cortexa72/base-files/etc/board.d/01_leds new file mode 100644 index 0000000000..809a64a60e --- /dev/null +++ b/target/linux/mvebu/cortexa72/base-files/etc/board.d/01_leds @@ -0,0 +1,20 @@ +# SPDX-License-Identifier: GPL-2.0-only + +. /lib/functions/uci-defaults.sh + +board_config_update + +board=$(board_name) + +case "$board" in +iei,puzzle-m901) + ucidef_set_led_netdev "wan" "WAN" "white:network" "eth0" "link" + ;; +iei,puzzle-m902) + ucidef_set_led_netdev "wan" "WAN" "white:network" "eth2" "link" + ;; +esac + +board_config_flush + +exit 0 diff --git a/target/linux/mvebu/cortexa72/base-files/etc/board.d/02_network b/target/linux/mvebu/cortexa72/base-files/etc/board.d/02_network old mode 100755 new mode 100644 index e0a4bc3015..2b70882eb1 --- a/target/linux/mvebu/cortexa72/base-files/etc/board.d/02_network +++ b/target/linux/mvebu/cortexa72/base-files/etc/board.d/02_network @@ -15,7 +15,7 @@ iei,puzzle-m901) ucidef_set_interfaces_lan_wan "eth1 eth2 eth3 eth4 eth5" "eth0" ;; iei,puzzle-m902) - ucidef_set_interfaces_lan_wan "eth1 eth2 eth3 eth4 eth5 eth10 eth11 eth12" "eth0" + ucidef_set_interfaces_lan_wan "eth0 eth1 eth3 eth4 eth5 eth6 eth7 eth8" "eth2" ;; marvell,armada8040-mcbin-doubleshot|\ marvell,armada8040-mcbin-singleshot) From 27225e35382d018a59078a52fa802e5e56d6be4b Mon Sep 17 00:00:00 2001 From: Nick Hainke Date: Mon, 20 Dec 2021 21:48:38 +0100 Subject: [PATCH 26/43] kernel: ath10k: provide a build variant for small RAM devices Based on: 1ac627024de9 ("kernel: ath10k-ct: provide a build variant for small RAM devices") Like described in the ath10k-ct-smallbuffers version, oom-killer gets triggered frequently by devices with small RAM. That change is necessary for many community mesh networks which use ath10k based devices with too little RAM. The -ct driver has been proven unstable if used with 11s meshing and only wave2 chipsets are supporting 11s. Freifunk Berlin is nowadays assembling its firmware-based completely of vanilla OpenWRT with some package additions which are made through the imagebuilder. Therefore we cannot take the approach other freifunk communities have taken to maintain that patch downstream [1]. Other communities consider these devices as broken and that change would pretty much give those devices a second life [2]. [1] - https://git.freifunk-franken.de/mirror/openwrt/commit/450b306e540bc0f2c8a8841bbe4d9612f2b8cdea [2] - https://github.com/freifunk-gluon/gluon/issues/1988#issuecomment-619532909 Signed-off-by: Simon Polack Signed-off-by: Nick Hainke (cherry picked from commit 694757a08f620a9f24b70003542d9dcd0abeac46) --- package/kernel/mac80211/Makefile | 8 ++- package/kernel/mac80211/ath.mk | 14 +++- .../ath/990-ath10k-small-buffers.patch | 64 +++++++++++++++++++ 3 files changed, 82 insertions(+), 4 deletions(-) create mode 100644 package/kernel/mac80211/patches/ath/990-ath10k-small-buffers.patch diff --git a/package/kernel/mac80211/Makefile b/package/kernel/mac80211/Makefile index 948dd50ccb..3686126053 100644 --- a/package/kernel/mac80211/Makefile +++ b/package/kernel/mac80211/Makefile @@ -434,9 +434,15 @@ config-$(call config_package,rsi91x-sdio) += RSI_SDIO config-$(CONFIG_LEDS_TRIGGERS) += MAC80211_LEDS +C_DEFINES= + +ifeq ($(BUILD_VARIANT),smallbuffers) + C_DEFINES+= -DCONFIG_ATH10K_SMALLBUFFERS +endif + MAKE_OPTS:= -C "$(PKG_BUILD_DIR)" \ $(KERNEL_MAKE_FLAGS) \ - EXTRA_CFLAGS="-I$(PKG_BUILD_DIR)/include $(IREMAP_CFLAGS)" \ + EXTRA_CFLAGS="-I$(PKG_BUILD_DIR)/include $(IREMAP_CFLAGS) $(C_DEFINES)" \ KLIB_BUILD="$(LINUX_DIR)" \ MODPROBE=true \ KLIB=$(TARGET_MODULES_DIR) \ diff --git a/package/kernel/mac80211/ath.mk b/package/kernel/mac80211/ath.mk index 24abb910ff..e815f37e1c 100644 --- a/package/kernel/mac80211/ath.mk +++ b/package/kernel/mac80211/ath.mk @@ -1,5 +1,5 @@ PKG_DRIVERS += \ - ath ath5k ath6kl ath6kl-sdio ath6kl-usb ath9k ath9k-common ath9k-htc ath10k \ + ath ath5k ath6kl ath6kl-sdio ath6kl-usb ath9k ath9k-common ath9k-htc ath10k ath10k-smallbuffers \ carl9170 owl-loader ar5523 wil6210 PKG_CONFIG_DEPENDS += \ @@ -55,6 +55,7 @@ config-$(CONFIG_ATH10K_THERMAL) += ATH10K_THERMAL config-$(call config_package,ath9k-htc) += ATH9K_HTC config-$(call config_package,ath10k) += ATH10K ATH10K_PCI +config-$(call config_package,ath10k-smallbuffers) += ATH10K ATH10K_PCI ATH10K_SMALLBUFFERS config-$(call config_package,ath5k) += ATH5K ifdef CONFIG_TARGET_ath25 @@ -260,6 +261,7 @@ define KernelPackage/ath10k $(PKG_BUILD_DIR)/drivers/net/wireless/ath/ath10k/ath10k_core.ko \ $(PKG_BUILD_DIR)/drivers/net/wireless/ath/ath10k/ath10k_pci.ko AUTOLOAD:=$(call AutoProbe,ath10k_pci) + VARIANT:=regular endef define KernelPackage/ath10k/description @@ -273,14 +275,20 @@ define KernelPackage/ath10k/config config ATH10K_LEDS bool "Enable LED support" default y - depends on PACKAGE_kmod-ath10k + depends on PACKAGE_kmod-ath10k || PACKAGE_kmod-ath10k-smallbuffers config ATH10K_THERMAL bool "Enable thermal sensors and throttling support" - depends on PACKAGE_kmod-ath10k + depends on PACKAGE_kmod-ath10k || PACKAGE_kmod-ath10k-smallbuffers endef +define KernelPackage/ath10k-smallbuffers + $(call KernelPackage/ath10k) + TITLE+= (small buffers for low-RAM devices) + VARIANT:=smallbuffers +endef + define KernelPackage/carl9170 $(call KernelPackage/mac80211/Default) TITLE:=Driver for Atheros AR9170 USB sticks diff --git a/package/kernel/mac80211/patches/ath/990-ath10k-small-buffers.patch b/package/kernel/mac80211/patches/ath/990-ath10k-small-buffers.patch new file mode 100644 index 0000000000..2f560c70a0 --- /dev/null +++ b/package/kernel/mac80211/patches/ath/990-ath10k-small-buffers.patch @@ -0,0 +1,64 @@ +--- a/drivers/net/wireless/ath/ath10k/htt.h ++++ b/drivers/net/wireless/ath/ath10k/htt.h +@@ -235,7 +235,11 @@ enum htt_rx_ring_flags { + }; + + #define HTT_RX_RING_SIZE_MIN 128 ++#ifndef CONFIG_ATH10K_SMALLBUFFERS + #define HTT_RX_RING_SIZE_MAX 2048 ++#else ++#define HTT_RX_RING_SIZE_MAX 512 ++#endif + #define HTT_RX_RING_SIZE HTT_RX_RING_SIZE_MAX + #define HTT_RX_RING_FILL_LEVEL (((HTT_RX_RING_SIZE) / 2) - 1) + #define HTT_RX_RING_FILL_LEVEL_DUAL_MAC (HTT_RX_RING_SIZE - 1) +--- a/drivers/net/wireless/ath/ath10k/pci.c ++++ b/drivers/net/wireless/ath/ath10k/pci.c +@@ -131,7 +131,11 @@ static const struct ce_attr pci_host_ce_ + .flags = CE_ATTR_FLAGS, + .src_nentries = 0, + .src_sz_max = 2048, ++#ifndef CONFIG_ATH10K_SMALLBUFFERS + .dest_nentries = 512, ++#else ++ .dest_nentries = 128, ++#endif + .recv_cb = ath10k_pci_htt_htc_rx_cb, + }, + +@@ -140,7 +144,11 @@ static const struct ce_attr pci_host_ce_ + .flags = CE_ATTR_FLAGS, + .src_nentries = 0, + .src_sz_max = 2048, ++#ifndef CONFIG_ATH10K_SMALLBUFFERS + .dest_nentries = 128, ++#else ++ .dest_nentries = 64, ++#endif + .recv_cb = ath10k_pci_htc_rx_cb, + }, + +@@ -167,7 +175,11 @@ static const struct ce_attr pci_host_ce_ + .flags = CE_ATTR_FLAGS, + .src_nentries = 0, + .src_sz_max = 512, ++#ifndef CONFIG_ATH10K_SMALLBUFFERS + .dest_nentries = 512, ++#else ++ .dest_nentries = 128, ++#endif + .recv_cb = ath10k_pci_htt_rx_cb, + }, + +@@ -192,7 +204,11 @@ static const struct ce_attr pci_host_ce_ + .flags = CE_ATTR_FLAGS, + .src_nentries = 0, + .src_sz_max = 2048, ++#ifndef CONFIG_ATH10K_SMALLBUFFERS + .dest_nentries = 128, ++#else ++ .dest_nentries = 96, ++#endif + .recv_cb = ath10k_pci_pktlog_rx_cb, + }, + From a00854040d9a431c3b99ed427140f513f78db915 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Thu, 10 Jun 2021 07:14:03 +0200 Subject: [PATCH 27/43] ipq40xx: specify FritzBox 7530 LAN port label numbers MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This helps managing LAN ports. Ref: https://forum.openwrt.org/t/openwrt-21-02-0-second-release-candidate/98026/121 Fixes: 95b0c07a618f ("ipq40xx: add support for FritzBox 7530") Cc: David Bauer Signed-off-by: Rafał Miłecki (cherry picked from commit 3342d574be08db8926273678291497769d2365e9) --- target/linux/ipq40xx/base-files/etc/board.d/02_network | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/target/linux/ipq40xx/base-files/etc/board.d/02_network b/target/linux/ipq40xx/base-files/etc/board.d/02_network index 1d4c78833a..c70aa0b95c 100755 --- a/target/linux/ipq40xx/base-files/etc/board.d/02_network +++ b/target/linux/ipq40xx/base-files/etc/board.d/02_network @@ -65,7 +65,7 @@ ipq40xx_setup_interfaces() ;; avm,fritzbox-7530) ucidef_add_switch "switch0" \ - "0u@eth0" "1:lan" "2:lan" "3:lan" "4:lan" + "0u@eth0" "1:lan:4" "2:lan:3" "3:lan:2" "4:lan:1" ;; avm,fritzrepeater-3000) ucidef_add_switch "switch0" \ From 6292d1e354766bc85be83cd4c63e53d6f9ef7570 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Mon, 29 Nov 2021 10:25:30 +0100 Subject: [PATCH 28/43] bcm4908: sysupgrade: refactor handling different firmware formats MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This results in setting format specific data (format info, extract commands) in a single function. It should help maintaining sysupgrade code. This change has been tested on Asus GT-AC5300 and Netgear R8000P. Signed-off-by: Rafał Miłecki (cherry picked from commit 30b168b9b8451d6165833cee75019ef7dbfd8a2e) --- .../base-files/lib/upgrade/platform.sh | 110 ++++++++++++------ 1 file changed, 77 insertions(+), 33 deletions(-) diff --git a/target/linux/bcm4908/base-files/lib/upgrade/platform.sh b/target/linux/bcm4908/base-files/lib/upgrade/platform.sh index ee43e3a713..c057f2dc58 100644 --- a/target/linux/bcm4908/base-files/lib/upgrade/platform.sh +++ b/target/linux/bcm4908/base-files/lib/upgrade/platform.sh @@ -4,6 +4,10 @@ RAMFS_COPY_BIN="bcm4908img expr" PART_NAME=firmware +BCM4908_FW_FORMAT= +BCM4908_FW_BOARD_ID= +BCM4908_FW_INT_IMG_FORMAT= + # $(1): file to read from # $(2): offset in bytes # $(3): length in bytes @@ -34,7 +38,12 @@ platform_identify() { magic=$(get_hex_u32_be "$1" 0) case "$magic" in 2a23245e) - echo "chk" + local header_len=$((0x$(get_hex_u32_be "$1" 4))) + local board_id_len=$(($header_len - 40)) + + BCM4908_FW_FORMAT="chk" + BCM4908_FW_BOARD_ID=$(dd if="$1" skip=40 bs=1 count=$board_id_len 2>/dev/null | hexdump -v -e '1/1 "%c"') + BCM4908_FW_INT_IMG_FORMAT="bcm4908img" return ;; esac @@ -44,12 +53,22 @@ platform_identify() { magic=$(get_content "$1" $((size - 20 - 64 + 8)) 12) case "$magic" in GT-AC5300) - echo "asus" + local size=$(wc -c "$1" | cut -d ' ' -f 1) + + BCM4908_FW_FORMAT="asus" + BCM4908_FW_BOARD_ID=$(get_content "$1" $((size - 20 - 64 + 8)) 12) + BCM4908_FW_INT_IMG_FORMAT="bcm4908img" return ;; esac - echo "unknown" + # Detecting native format is a bit complex (it may start with CFE or + # JFFS2) so just use bcm4908img instead of bash hacks. + # Make it the last attempt as bcm4908img detects also vendor formats. + bcm4908img info -i "$1" > /dev/null && { + BCM4908_FW_FORMAT="bcm4908img" + return + } } platform_check_image() { @@ -58,43 +77,51 @@ platform_check_image() { local expected_image=$(platform_expected_image) local error=0 - bcm4908img info -i "$1" > /dev/null || { - echo "Failed to validate BCM4908 image" >&2 + platform_identify "$1" + [ -z "$BCM4908_FW_FORMAT" ] && { + echo "Invalid image type. Please use firmware specific for this device." notify_firmware_broken return 1 } + echo "Found $BCM4908_FW_FORMAT firmware for device ${BCM4908_FW_BOARD_ID:----}" - bcm4908img bootfs -i "$1" ls | grep -q "1-openwrt" || { - # OpenWrt images have 1-openwrt dummy file in the bootfs. - # Don't allow backup if it's missing - notify_firmware_no_backup + local expected_image="$(platform_expected_image)" + [ -n "$expected_image" -a -n "$BCM4908_FW_BOARD_ID" -a "$BCM4908_FW_FORMAT $BCM4908_FW_BOARD_ID" != "$expected_image" ] && { + echo "Firmware doesn't match device ($expected_image)" + error=1 } - case "$(platform_identify "$1")" in - asus) - local size=$(wc -c "$1" | cut -d ' ' -f 1) - local productid=$(get_content "$1" $((size - 20 - 64 + 8)) 12) - - [ -n "$expected_image" -a "asus $productid" != "$expected_image" ] && { - echo "Firmware productid mismatch ($productid)" >&2 - error=1 + case "$BCM4908_FW_FORMAT" in + "bcm4908img") + bcm4908img info -i "$1" > /dev/null || { + echo "Failed to validate BCM4908 image" >&2 + notify_firmware_broken + return 1 } - ;; - chk) - local header_len=$((0x$(get_hex_u32_be "$1" 4))) - local board_id_len=$(($header_len - 40)) - local board_id=$(dd if="$1" skip=40 bs=1 count=$board_id_len 2>/dev/null | hexdump -v -e '1/1 "%c"') - [ -n "$expected_image" -a "chk $board_id" != "$expected_image" ] && { - echo "Firmware board_id mismatch ($board_id)" >&2 - error=1 + bcm4908img bootfs -i "$1" ls | grep -q "1-openwrt" || { + # OpenWrt images have 1-openwrt dummy file in the bootfs. + # Don't allow backup if it's missing + notify_firmware_no_backup } - ;; + ;; *) - echo "Invalid image type. Please use firmware specific for this device." >&2 - notify_firmware_broken - error=1 - ;; + case "$BCM4908_FW_INT_IMG_FORMAT" in + "bcm4908img") + bcm4908img info -i "$1" > /dev/null || { + echo "Failed to validate BCM4908 image" >&2 + notify_firmware_broken + return 1 + } + + bcm4908img bootfs -i "$1" ls | grep -q "1-openwrt" || { + # OpenWrt images have 1-openwrt dummy file in the bootfs. + # Don't allow backup if it's missing + notify_firmware_no_backup + } + ;; + esac + ;; esac return $error @@ -189,10 +216,27 @@ platform_do_upgrade_ubi() { } platform_do_upgrade() { - # Try NAND aware UBI upgrade for OpenWrt images - # Below call will exit on success - bcm4908img bootfs -i "$1" ls | grep -q "1-openwrt" && platform_do_upgrade_ubi "$1" + platform_identify "$1" + # Try NAND aware UBI upgrade for OpenWrt images + case "$BCM4908_FW_FORMAT" in + "bcm4908img") + bcm4908img bootfs -i "$1" ls | grep -q "1-openwrt" && platform_do_upgrade_ubi "$1" + ;; + *) + case "$BCM4908_FW_INT_IMG_FORMAT" in + "bcm4908img") + bcm4908img bootfs -i "$1" ls | grep -q "1-openwrt" && platform_do_upgrade_ubi "$1" + ;; + *) + echo "NAND aware sysupgrade is unsupported for $BCM4908_FW_FORMAT format" + ;; + esac + ;; + esac + + # Above calls exit on success. + # If we got here it isn't OpenWrt image or something went wrong. echo "Writing whole image to NAND flash. All erase counters will be lost." # Find cferam name for new firmware From ce5d0378bf03b3b890ccec0cc3fc62d44fecd536 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Tue, 7 Dec 2021 13:00:01 +0100 Subject: [PATCH 29/43] dtc: import package for dtc & fdt from packages feed MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit fdt* utils are needed by targets that use U-Boot FIT images for sysupgrade. It includes all recent BCM4908 SoC routers as Broadcom switched from CFE to U-Boot. fdtget is required for extracting images (bootfs & rootfs) from Broadcom's ITB. Extracted images can be then flashed to UBI volumes. sysupgrade is core functionality so it needs dtc as part of base code base. Cc: Yousong Zhou Signed-off-by: Rafał Miłecki --- package/utils/dtc/Makefile | 92 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 92 insertions(+) create mode 100644 package/utils/dtc/Makefile diff --git a/package/utils/dtc/Makefile b/package/utils/dtc/Makefile new file mode 100644 index 0000000000..deec4e3ad6 --- /dev/null +++ b/package/utils/dtc/Makefile @@ -0,0 +1,92 @@ +# SPDX-License-Identifier: GPL-2.0 +# +# Copyright (C) 2016-2019 Yousong Zhou + +include $(TOPDIR)/rules.mk + +PKG_NAME:=dtc +PKG_VERSION:=1.6.0 +PKG_RELEASE:=1 +PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.xz +PKG_HASH:=10503b0217e1b07933e29e8d347a00015b2431bea5f59afe0bed3af30340c82d +PKG_SOURCE_URL:=@KERNEL/software/utils/dtc +PKG_LICENSE:=GPL-2.0 +PKG_LICENSE_FILES:=GPL +PKG_INSTALL:=1 +PKG_MAINTAINER:=Yousong Zhou + +include $(INCLUDE_DIR)/package.mk + + +define Package/dtc + SECTION:=utils + CATEGORY:=Utilities + TITLE:=Device Tree Compiler + URL:=https://git.kernel.org/pub/scm/utils/dtc/dtc.git +endef + +define Package/dtc/description + Device Tree Compiler for Flat Device Trees Device Tree Compiler, dtc, takes + as input a device-tree in a given format and outputs a device-tree in another + format for booting kernels on embedded systems. +endef + +define Package/dtc/install + $(INSTALL_DIR) $(1)/usr/bin + $(CP) $(PKG_INSTALL_DIR)/bin/dtc $(1)/usr/bin +endef + + +# See Documentation/manual.txt for details about each utility +define Package/fdt-utils + SECTION:=utils + CATEGORY:=Utilities + TITLE:=Flat Device Tree Utilities + URL:=https://git.kernel.org/pub/scm/utils/dtc/dtc.git + DEPENDS:=+libfdt +endef + +define Package/fdt-utils/install + $(INSTALL_DIR) $(1)/usr/bin + $(INSTALL_BIN) $(PKG_INSTALL_DIR)/bin/convert-dtsv0 $(1)/usr/bin + $(INSTALL_BIN) $(PKG_INSTALL_DIR)/bin/fdtdump $(1)/usr/bin + $(INSTALL_BIN) $(PKG_INSTALL_DIR)/bin/fdtget $(1)/usr/bin + $(INSTALL_BIN) $(PKG_INSTALL_DIR)/bin/fdtput $(1)/usr/bin + $(INSTALL_BIN) $(PKG_INSTALL_DIR)/bin/fdtoverlay $(1)/usr/bin +endef + + +define Package/libfdt + SECTION:=libs + CATEGORY:=Libraries + TITLE:=a utility library for reading and manipulating dtb files + URL:=https://git.kernel.org/pub/scm/utils/dtc/dtc.git +endef + +define Package/libfdt/description + This is a library containing functions for manipulating Flat Device Trees. +endef + +define Package/libfdt/install + $(INSTALL_DIR) $(1)/usr/lib + $(CP) $(PKG_INSTALL_DIR)/lib/libfdt*.so* $(1)/usr/lib +endef + +# NO_PYTHON is for disabling pylibfdt +MAKE_FLAGS += \ + PREFIX= \ + NO_PYTHON=1 \ + NO_VALGRIND=1 \ + NO_YAML=1 \ + EXTRA_CFLAGS=$(EXTRA_CFLAGS) \ + +define Build/InstallDev + $(INSTALL_DIR) $(1)/usr/lib + $(INSTALL_DIR) $(1)/usr/include + $(CP) $(PKG_INSTALL_DIR)/include/* $(1)/usr/include + $(CP) $(PKG_INSTALL_DIR)/lib/* $(1)/usr/lib +endef + +$(eval $(call BuildPackage,dtc)) +$(eval $(call BuildPackage,fdt-utils)) +$(eval $(call BuildPackage,libfdt)) From 1d4a28d5e10702f2b46b1fc1808c5613cc706db4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Tue, 7 Dec 2021 13:00:02 +0100 Subject: [PATCH 30/43] dtc: support printing binary data with fdtget MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit It's needed for extracting binary images. Cc: Yousong Zhou Signed-off-by: Rafał Miłecki (cherry picked from commit a2cf659ad8ecbc5be6b0fca4efd29441e1a13be1) --- ...t-for-printing-raw-bytes-with-fdtget.patch | 137 ++++++++++++++++++ 1 file changed, 137 insertions(+) create mode 100644 package/utils/dtc/patches/0001-Support-r-format-for-printing-raw-bytes-with-fdtget.patch diff --git a/package/utils/dtc/patches/0001-Support-r-format-for-printing-raw-bytes-with-fdtget.patch b/package/utils/dtc/patches/0001-Support-r-format-for-printing-raw-bytes-with-fdtget.patch new file mode 100644 index 0000000000..f7731f1a9d --- /dev/null +++ b/package/utils/dtc/patches/0001-Support-r-format-for-printing-raw-bytes-with-fdtget.patch @@ -0,0 +1,137 @@ +From 17739b7ef510917471409d71fb45d8eaf6a1e1fb Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= +Date: Thu, 9 Dec 2021 07:14:20 +0100 +Subject: [PATCH] Support 'r' format for printing raw bytes with fdtget +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +FT is sometimes used for storing raw data. That is quite common for +U-Boot FIT images. + +Extracting such data is not trivial currently. Using type 's' (string) +will replace every 0x00 (NUL) with 0x20 (space). Using type 'x' will +print bytes but in xxd incompatible format. + +This commit adds support for 'r' (raw) format. Example usage: +fdtget -t r firmware.itb /images/foo data > image.raw + +Support for encoding isn't added as there isn't any clean way of passing +binary data as command line argument. + +Signed-off-by: Rafał Miłecki +Message-Id: <20211209061420.29466-1-zajec5@gmail.com> +Signed-off-by: David Gibson +--- + Documentation/manual.txt | 2 +- + fdtget.c | 5 +++++ + fdtput.c | 2 ++ + tests/run_tests.sh | 2 ++ + tests/utilfdt_test.c | 5 ++++- + util.c | 4 ++-- + util.h | 3 ++- + 7 files changed, 18 insertions(+), 5 deletions(-) + +--- a/Documentation/manual.txt ++++ b/Documentation/manual.txt +@@ -712,7 +712,7 @@ The syntax of the fdtget command is: + + where options are: + +- s=string, i=int, u=unsigned, x=hex ++ s=string, i=int, u=unsigned, x=hex, r=raw + Optional modifier prefix: + hh or b=byte, h=2 byte, l=4 byte (default) + +--- a/fdtget.c ++++ b/fdtget.c +@@ -91,6 +91,11 @@ static int show_data(struct display_info + if (len == 0) + return 0; + ++ if (disp->type == 'r') { ++ fwrite(data, 1, len, stdout); ++ return 0; ++ } ++ + is_string = (disp->type) == 's' || + (!disp->type && util_is_printable_string(data, len)); + if (is_string) { +--- a/fdtput.c ++++ b/fdtput.c +@@ -433,6 +433,8 @@ int main(int argc, char *argv[]) + if (utilfdt_decode_type(optarg, &disp.type, + &disp.size)) + usage("Invalid type string"); ++ if (disp.type == 'r') ++ usage("Unsupported raw data type"); + break; + + case 'v': +--- a/tests/run_tests.sh ++++ b/tests/run_tests.sh +@@ -852,6 +852,8 @@ fdtget_tests () { + run_fdtget_test 8000 -tx $dtb /cpus/PowerPC,970@1 d-cache-size + run_fdtget_test "61 62 63 0" -tbx $dtb /randomnode tricky1 + run_fdtget_test "a b c d de ea ad be ef" -tbx $dtb /randomnode blob ++ run_fdtget_test "MyBoardName\0MyBoardFamilyName\0" -tr $dtb / compatible ++ run_fdtget_test "\x0a\x0b\x0c\x0d\xde\xea\xad\xbe\xef" -tr $dtb /randomnode blob + + # Here the property size is not a multiple of 4 bytes, so it should fail + run_wrap_error_test $DTGET -tlx $dtb /randomnode mixed +--- a/tests/utilfdt_test.c ++++ b/tests/utilfdt_test.c +@@ -73,6 +73,9 @@ static void check_sizes(char *modifier, + + *ptr = 's'; + check(fmt, 's', -1); ++ ++ *ptr = 'r'; ++ check(fmt, 'r', -1); + } + + static void test_utilfdt_decode_type(void) +@@ -90,7 +93,7 @@ static void test_utilfdt_decode_type(voi + /* try every other character */ + checkfail(""); + for (ch = ' '; ch < 127; ch++) { +- if (!strchr("iuxs", ch)) { ++ if (!strchr("iuxsr", ch)) { + *fmt = ch; + fmt[1] = '\0'; + checkfail(fmt); +--- a/util.c ++++ b/util.c +@@ -353,11 +353,11 @@ int utilfdt_decode_type(const char *fmt, + } + + /* we should now have a type */ +- if ((*fmt == '\0') || !strchr("iuxs", *fmt)) ++ if ((*fmt == '\0') || !strchr("iuxsr", *fmt)) + return -1; + + /* convert qualifier (bhL) to byte size */ +- if (*fmt != 's') ++ if (*fmt != 's' && *fmt != 'r') + *size = qualifier == 'b' ? 1 : + qualifier == 'h' ? 2 : + qualifier == 'l' ? 4 : -1; +--- a/util.h ++++ b/util.h +@@ -143,6 +143,7 @@ int utilfdt_write_err(const char *filena + * i signed integer + * u unsigned integer + * x hex ++ * r raw + * + * TODO: Implement ll modifier (8 bytes) + * TODO: Implement o type (octal) +@@ -160,7 +161,7 @@ int utilfdt_decode_type(const char *fmt, + */ + + #define USAGE_TYPE_MSG \ +- "\ts=string, i=int, u=unsigned, x=hex\n" \ ++ "\ts=string, i=int, u=unsigned, x=hex, r=raw\n" \ + "\tOptional modifier prefix:\n" \ + "\t\thh or b=byte, h=2 byte, l=4 byte (default)"; + From 4cd5d11fa3a8dee67174a460479e3058628308bf Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Tue, 14 Dec 2021 17:57:49 +0100 Subject: [PATCH 31/43] bcm4908: add fdt-utils to default packages MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit It's required by sysupgrade. Signed-off-by: Rafał Miłecki (cherry picked from commit 30b93672ec48d247fcd86b5bca283423db5250b9) --- target/linux/bcm4908/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/target/linux/bcm4908/Makefile b/target/linux/bcm4908/Makefile index bbe5030b65..a9040577c8 100644 --- a/target/linux/bcm4908/Makefile +++ b/target/linux/bcm4908/Makefile @@ -21,7 +21,7 @@ include $(INCLUDE_DIR)/target.mk KERNELNAME:=Image dtbs DEFAULT_PACKAGES += \ - bcm4908img \ + bcm4908img fdt-utils \ kmod-gpio-button-hotplug \ kmod-usb-ohci kmod-usb2 kmod-usb3 From 7e4485fd5bf8e0f9ff4fa28623086c290e6dbbf6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Thu, 16 Dec 2021 08:25:18 +0100 Subject: [PATCH 32/43] bcm4908: add uboot-envtools to default packages MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit It's required by sysupgrade to access UBI metadata partitions. Signed-off-by: Rafał Miłecki (cherry picked from commit 444b4ea4a479d76761ee4833cb340b442dac662a) --- target/linux/bcm4908/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/target/linux/bcm4908/Makefile b/target/linux/bcm4908/Makefile index a9040577c8..3177bd9ded 100644 --- a/target/linux/bcm4908/Makefile +++ b/target/linux/bcm4908/Makefile @@ -21,7 +21,7 @@ include $(INCLUDE_DIR)/target.mk KERNELNAME:=Image dtbs DEFAULT_PACKAGES += \ - bcm4908img fdt-utils \ + bcm4908img fdt-utils uboot-envtools \ kmod-gpio-button-hotplug \ kmod-usb-ohci kmod-usb2 kmod-usb3 From b6ed2641df3c679eced6b51e5aad2e3df1761de1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Thu, 16 Dec 2021 12:36:16 +0100 Subject: [PATCH 33/43] busybox: backport dd support for iflag=count_bytes MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit It's very useful flag for handling various formats in sysupgrade. This commit comes from the 1.34.0 release. Signed-off-by: Rafał Miłecki --- .../001-dd-support-iflag-count_bytes.patch | 140 ++++++++++++++++++ 1 file changed, 140 insertions(+) create mode 100644 package/utils/busybox/patches/001-dd-support-iflag-count_bytes.patch diff --git a/package/utils/busybox/patches/001-dd-support-iflag-count_bytes.patch b/package/utils/busybox/patches/001-dd-support-iflag-count_bytes.patch new file mode 100644 index 0000000000..c195c10cf1 --- /dev/null +++ b/package/utils/busybox/patches/001-dd-support-iflag-count_bytes.patch @@ -0,0 +1,140 @@ +From 4eb46e1be6d88eaf077252ce93127ebf00aa8ef2 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= +Date: Wed, 24 Mar 2021 16:01:42 +0100 +Subject: [PATCH] dd: support iflag=count_bytes +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +It allows passing amount of bytes in the count= + +function old new delta +packed_usage 33599 33617 +18 +static.iflag_words 29 41 +12 +dd_main 1601 1607 +6 +------------------------------------------------------------------------------ +(add/remove: 0/0 grow/shrink: 3/0 up/down: 36/0) Total: 36 bytes + +Signed-off-by: Rafał Miłecki +Signed-off-by: Denys Vlasenko +--- + coreutils/dd.c | 50 ++++++++++++++++++++++++------------- + testsuite/dd/dd-count-bytes | 1 + + 2 files changed, 33 insertions(+), 18 deletions(-) + create mode 100644 testsuite/dd/dd-count-bytes + +--- a/coreutils/dd.c ++++ b/coreutils/dd.c +@@ -59,7 +59,7 @@ + //usage: "[if=FILE] [of=FILE] [" IF_FEATURE_DD_IBS_OBS("ibs=N obs=N/") "bs=N] [count=N] [skip=N] [seek=N]\n" + //usage: IF_FEATURE_DD_IBS_OBS( + //usage: " [conv=notrunc|noerror|sync|fsync]\n" +-//usage: " [iflag=skip_bytes|fullblock|direct] [oflag=seek_bytes|append|direct]" ++//usage: " [iflag=skip_bytes|count_bytes|fullblock|direct] [oflag=seek_bytes|append|direct]" + //usage: ) + //usage:#define dd_full_usage "\n\n" + //usage: "Copy a file with converting and formatting\n" +@@ -82,6 +82,7 @@ + //usage: "\n conv=fsync Physically write data out before finishing" + //usage: "\n conv=swab Swap every pair of bytes" + //usage: "\n iflag=skip_bytes skip=N is in bytes" ++//usage: "\n iflag=count_bytes count=N is in bytes" + //usage: "\n oflag=seek_bytes seek=N is in bytes" + //usage: "\n iflag=direct O_DIRECT input" + //usage: "\n oflag=direct O_DIRECT output" +@@ -136,21 +137,22 @@ enum { + FLAG_SWAB = (1 << 4) * ENABLE_FEATURE_DD_IBS_OBS, + /* end of conv flags */ + /* start of input flags */ +- FLAG_IFLAG_SHIFT = 5, +- FLAG_SKIP_BYTES = (1 << 5) * ENABLE_FEATURE_DD_IBS_OBS, +- FLAG_FULLBLOCK = (1 << 6) * ENABLE_FEATURE_DD_IBS_OBS, +- FLAG_IDIRECT = (1 << 7) * ENABLE_FEATURE_DD_IBS_OBS, ++ FLAG_IFLAG_SHIFT = 5, ++ FLAG_SKIP_BYTES = (1 << 5) * ENABLE_FEATURE_DD_IBS_OBS, ++ FLAG_COUNT_BYTES = (1 << 6) * ENABLE_FEATURE_DD_IBS_OBS, ++ FLAG_FULLBLOCK = (1 << 7) * ENABLE_FEATURE_DD_IBS_OBS, ++ FLAG_IDIRECT = (1 << 8) * ENABLE_FEATURE_DD_IBS_OBS, + /* end of input flags */ + /* start of output flags */ +- FLAG_OFLAG_SHIFT = 8, +- FLAG_SEEK_BYTES = (1 << 8) * ENABLE_FEATURE_DD_IBS_OBS, +- FLAG_APPEND = (1 << 9) * ENABLE_FEATURE_DD_IBS_OBS, +- FLAG_ODIRECT = (1 << 10) * ENABLE_FEATURE_DD_IBS_OBS, ++ FLAG_OFLAG_SHIFT = 9, ++ FLAG_SEEK_BYTES = (1 << 9) * ENABLE_FEATURE_DD_IBS_OBS, ++ FLAG_APPEND = (1 << 10) * ENABLE_FEATURE_DD_IBS_OBS, ++ FLAG_ODIRECT = (1 << 11) * ENABLE_FEATURE_DD_IBS_OBS, + /* end of output flags */ +- FLAG_TWOBUFS = (1 << 11) * ENABLE_FEATURE_DD_IBS_OBS, +- FLAG_COUNT = 1 << 12, +- FLAG_STATUS_NONE = 1 << 13, +- FLAG_STATUS_NOXFER = 1 << 14, ++ FLAG_TWOBUFS = (1 << 12) * ENABLE_FEATURE_DD_IBS_OBS, ++ FLAG_COUNT = 1 << 13, ++ FLAG_STATUS_NONE = 1 << 14, ++ FLAG_STATUS_NOXFER = 1 << 15, + }; + + static void dd_output_status(int UNUSED_PARAM cur_signal) +@@ -175,8 +177,9 @@ static void dd_output_status(int UNUSED_ + //So far we react to it (we print the stats), + //status=none only suppresses final, non-USR1 generated status message. + # endif +- fprintf(stderr, "%llu bytes (%sB) copied, ", +- G.total_bytes, ++ fprintf(stderr, /*G.total_bytes < 1024 ++ ? "%llu bytes copied, " : */ "%llu bytes (%sB) copied, " ++ , G.total_bytes, + /* show fractional digit, use suffixes */ + make_human_readable_str(G.total_bytes, 1, 0) + ); +@@ -317,7 +320,7 @@ int dd_main(int argc UNUSED_PARAM, char + static const char conv_words[] ALIGN1 = + "notrunc\0""sync\0""noerror\0""fsync\0""swab\0"; + static const char iflag_words[] ALIGN1 = +- "skip_bytes\0""fullblock\0""direct\0"; ++ "skip_bytes\0""count_bytes\0""fullblock\0""direct\0"; + static const char oflag_words[] ALIGN1 = + "seek_bytes\0append\0""direct\0"; + #endif +@@ -359,6 +362,7 @@ int dd_main(int argc UNUSED_PARAM, char + /* Partially implemented: */ + //swab swap every pair of input bytes: will abort on non-even reads + OP_iflag_skip_bytes, ++ OP_iflag_count_bytes, + OP_iflag_fullblock, + OP_iflag_direct, + OP_oflag_seek_bytes, +@@ -551,8 +555,17 @@ int dd_main(int argc UNUSED_PARAM, char + goto die_outfile; + } + +- while (!(G.flags & FLAG_COUNT) || (G.in_full + G.in_part != count)) { +- ssize_t n = dd_read(ibuf, ibs); ++ while (1) { ++ ssize_t n = ibs; ++ ++ if (G.flags & FLAG_COUNT) { ++ if (count == 0) ++ break; ++ if ((G.flags & FLAG_COUNT_BYTES) && count < ibs) ++ n = count; ++ } ++ ++ n = dd_read(ibuf, n); + if (n == 0) + break; + if (n < 0) { +@@ -587,6 +600,7 @@ int dd_main(int argc UNUSED_PARAM, char + p16++; + } + } ++ count -= (G.flags & FLAG_COUNT_BYTES) ? n : 1; + if ((size_t)n == ibs) + G.in_full++; + else { +--- /dev/null ++++ b/testsuite/dd/dd-count-bytes +@@ -0,0 +1 @@ ++test "$(echo I WANT | busybox dd count=3 iflag=count_bytes 2>/dev/null)" = "I W" From 608c7dccf27c64ff3c8e09430481b66af18bdaf4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Wed, 8 Dec 2021 12:21:48 +0100 Subject: [PATCH 34/43] bcm4908: sysupgrade: add pkgtb format support MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit BCM4908 devices with U-Boot use pkgtb firmware format. It's based on U-Boot's FIT: DTB with configurations, images & embedded data. This format contains bootfs, rootfs and optionally a first stage U-Boot loader. Contained images need to be extracted & flashed. Broadcom used two sets of firmwares: main & backup. It uses UBI volumes "metadata1" & "metadata2" for storing U-Boot env variables with info about flashed images. Signed-off-by: Rafał Miłecki (cherry picked from commit 5f05795aa7716879e46fabbd0c51ff20ef9f13bf) --- .../base-files/lib/upgrade/platform.sh | 185 +++++++++++++++++- 1 file changed, 183 insertions(+), 2 deletions(-) diff --git a/target/linux/bcm4908/base-files/lib/upgrade/platform.sh b/target/linux/bcm4908/base-files/lib/upgrade/platform.sh index c057f2dc58..e7d4bfe4de 100644 --- a/target/linux/bcm4908/base-files/lib/upgrade/platform.sh +++ b/target/linux/bcm4908/base-files/lib/upgrade/platform.sh @@ -1,6 +1,6 @@ # SPDX-License-Identifier: GPL-2.0 OR BSD-2-Clause -RAMFS_COPY_BIN="bcm4908img expr" +RAMFS_COPY_BIN="bcm4908img expr egrep fdtget fw_printenv fw_setenv tr" PART_NAME=firmware @@ -15,6 +15,12 @@ get_content() { dd if="$1" skip=$2 bs=1 count=$3 2>/dev/null } +# $(1): file to read from +# $(2): offset in bytes +get_hex_u32_le() { + dd if="$1" skip=$2 bs=1 count=4 2>/dev/null | hexdump -v -e '1/4 "%02x"' +} + # $(1): file to read from # $(2): offset in bytes get_hex_u32_be() { @@ -37,13 +43,23 @@ platform_identify() { magic=$(get_hex_u32_be "$1" 0) case "$magic" in + d00dfeed) + BCM4908_FW_FORMAT="pkgtb" + return + ;; 2a23245e) local header_len=$((0x$(get_hex_u32_be "$1" 4))) local board_id_len=$(($header_len - 40)) BCM4908_FW_FORMAT="chk" BCM4908_FW_BOARD_ID=$(dd if="$1" skip=40 bs=1 count=$board_id_len 2>/dev/null | hexdump -v -e '1/1 "%c"') - BCM4908_FW_INT_IMG_FORMAT="bcm4908img" + magic=$(get_hex_u32_be "$1" "$header_len") + [ "$magic" = "d00dfeed" ] && { + BCM4908_FW_INT_IMG_FORMAT="pkgtb" + } || { + BCM4908_FW_INT_IMG_FORMAT="bcm4908img" + } + BCM4908_FW_INT_IMG_EXTRACT_CMD="dd skip=$header_len iflag=skip_bytes" return ;; esac @@ -71,6 +87,117 @@ platform_identify() { } } +# +# pkgtb helpers +# + +platform_pkgtb_get_image_name() { + local configuration=$($2 < $1 | fdtget - /configurations default) + [ -z "$configuration" ] && { + echo "Failed to read default configuration from pkgtb" >&2 + return + } + + local image_name=$($2 < $1 | fdtget - /configurations/$configuration $3) + [ -z "$image_name" ] && { + echo "Failed to read $3 from pkgtb configuration \"$configuration\"" >&2 + return + } + + echo "$image_name" +} + +platform_pkgtb_get_image() { + local cmd="${2:-cat}" + + local image_name=$(platform_pkgtb_get_image_name "$1" "$cmd" "$3") + + $cmd < $1 | fdtget -p - /images/$image_name | egrep -q "^data$" && { + $cmd < $1 | fdtget -t r - /images/$image_name data + return + } + + $cmd < $1 | fdtget -p - /images/$image_name | egrep -q "^data-position$" && { + local data_position=$($cmd < $1 | fdtget - /images/$image_name data-position) + local data_size=$($cmd < $1 | fdtget - /images/$image_name data-size) + $cmd < $1 2>/dev/null | dd skip=$data_position count=$data_size iflag=skip_bytes,count_bytes + return + } + + $cmd < $1 | fdtget -p - /images/$image_name | egrep -q "^data-offset" && { + local data_offset=$($cmd < $1 | fdtget - /images/$image_name data-offset) + local totalsize=$(get_hex_u32_be "$1" 4) + local data_position=$(((0x$totalsize + data_offset + 3) & ~3)) + local data_size=$($cmd < $1 | fdtget - /images/$image_name data-size) + $cmd < $1 2>/dev/null | dd skip=$data_position count=$data_size iflag=skip_bytes,count_bytes + return + } +} + +platform_pkgtb_setup_env_config() { + local size=$((0x$(get_hex_u32_le /dev/ubi0_1 4))) + + dd if=/dev/ubi0_1 of=/tmp/env.head count=8 iflag=count_bytes + dd if=/dev/ubi0_1 of=/tmp/env.body skip=8 iflag=skip_bytes + printf "%s\t0x%x\t0x%x\t0x%x" "/tmp/env.body" 0x0 $size $size > /tmp/env.config +} + +platform_pkgtb_get_upgrade_index() { + platform_pkgtb_setup_env_config + + case "$(fw_printenv -l /tmp -n -c /tmp/env.config COMMITTED)" in + 1) echo 2;; + 2) echo 1;; + *) echo 1;; + esac +} + +platform_pkgtb_commit() { + local size=$((0x$(get_hex_u32_le /dev/ubi0_1 4))) + local valid1=0 + local valid2=0 + local seq1 + local seq2 + local tmp + + platform_pkgtb_setup_env_config + + # Read current values + for valid in $(fw_printenv -l /tmp -n -c /tmp/env.config VALID | tr ',' ' '); do + case "$valid" in + 1) valid0=1;; + 2) valid1=2;; + esac + done + seq0=$(fw_printenv -l /tmp -n -c /tmp/env.config SEQ | cut -d ',' -f 1) + seq1=$(fw_printenv -l /tmp -n -c /tmp/env.config SEQ | cut -d ',' -f 2) + + # Calculate values + case "$1" in + 1) valid0=1; seq0=$(((seq1 + 1) % 1000));; + 2) valid1=2; seq1=$(((seq0 + 1) % 1000));; + esac + + # Update variables + fw_setenv -l /tmp -c /tmp/env.config COMMITTED "$1" + fw_setenv -l /tmp -c /tmp/env.config VALID "$valid0,$valid1" + fw_setenv -l /tmp -c /tmp/env.config SEQ "$seq0,$seq1" + + # Write + tmp=$(cat /tmp/env.head /tmp/env.body | wc -c) + cat /tmp/env.head /tmp/env.body | ubiupdatevol /dev/ubi0_1 -s $tmp - +} + +# +# check +# + +platform_check_pkgtb() { + local cmd="${2:-cat}" + + [ -n "$(platform_pkgtb_get_image_name "$1" "$cmd" "bootfs")" -a -n "$(platform_pkgtb_get_image_name "$1" "$cmd" "rootfs")" ] +} + platform_check_image() { [ "$#" -gt 1 ] && return 1 @@ -105,6 +232,13 @@ platform_check_image() { notify_firmware_no_backup } ;; + "pkgtb") + platform_check_pkgtb "$1" || { + echo "Failed to validate pkgtb firmware" >&2 + notify_firmware_broken + return 1 + } + ;; *) case "$BCM4908_FW_INT_IMG_FORMAT" in "bcm4908img") @@ -120,6 +254,13 @@ platform_check_image() { notify_firmware_no_backup } ;; + "pkgtb") + platform_check_pkgtb "$1" "$BCM4908_FW_INT_IMG_EXTRACT_CMD" || { + echo "Failed to validate pkgtb firmware" >&2 + notify_firmware_broken + return 1 + } + ;; esac ;; esac @@ -127,6 +268,36 @@ platform_check_image() { return $error } +# +# upgrade +# + +platform_do_upgrade_pkgtb() { + local cmd="${2:-cat}" + local size + local idx bootfs_id rootfs_id + + idx=$(platform_pkgtb_get_upgrade_index) + case "$idx" in + 1) bootfs_id=3; rootfs_id=4;; + 2) bootfs_id=5; rootfs_id=6;; + esac + + size=$(platform_pkgtb_get_image "$1" "$cmd" "bootfs" | wc -c) + ubirmvol /dev/ubi0 -N bootfs$idx + ubimkvol /dev/ubi0 -n $bootfs_id -N bootfs$idx -t static -s $size + platform_pkgtb_get_image "$1" "$cmd" "bootfs" | ubiupdatevol /dev/ubi0_$bootfs_id -s $size - + + size=$(platform_pkgtb_get_image "$1" "$cmd" "rootfs" | wc -c) + ubirmvol /dev/ubi0 -N rootfs$idx + ubimkvol /dev/ubi0 -n $rootfs_id -N rootfs$idx -t dynamic -s $size + platform_pkgtb_get_image "$1" "$cmd" "rootfs" | ubiupdatevol /dev/ubi0_$rootfs_id -s $size - + + platform_pkgtb_commit $idx + + nand_do_upgrade_success +} + # $1: cferam index increment value platform_calc_new_cferam() { local inc="$1" @@ -223,11 +394,17 @@ platform_do_upgrade() { "bcm4908img") bcm4908img bootfs -i "$1" ls | grep -q "1-openwrt" && platform_do_upgrade_ubi "$1" ;; + "pkgtb") + platform_do_upgrade_pkgtb "$1" + ;; *) case "$BCM4908_FW_INT_IMG_FORMAT" in "bcm4908img") bcm4908img bootfs -i "$1" ls | grep -q "1-openwrt" && platform_do_upgrade_ubi "$1" ;; + "pkgtb") + platform_do_upgrade_pkgtb "$1" "$BCM4908_FW_INT_IMG_EXTRACT_CMD" + ;; *) echo "NAND aware sysupgrade is unsupported for $BCM4908_FW_FORMAT format" ;; @@ -237,6 +414,10 @@ platform_do_upgrade() { # Above calls exit on success. # If we got here it isn't OpenWrt image or something went wrong. + [ "$BCM4908_FW_FORMAT" = "pkgtb" -o "$BCM4908_FW_INT_IMG_FORMAT" = "pkgtb" ] && { + echo "Failed to upgrade pkgtb. Fallback to raw flashing is impossible for this format." >&2 + exit 1 + } echo "Writing whole image to NAND flash. All erase counters will be lost." # Find cferam name for new firmware From 739e359241a3855bf8f7b6b99978495ad52d1004 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Thu, 16 Dec 2021 07:07:34 +0100 Subject: [PATCH 35/43] kernel: backport support for multicolor & RGB LEDs to 5.4 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This is a requirement for backporting DT files defining such LEDs. Signed-off-by: Rafał Miłecki (cherry picked from commit 85ad48c9579c0482c98fc6b69e885102511e9194) --- ...multicolor-class-dt-bindings-documen.patch | 76 +++++++++++++++++++ ...d-multicolor-ID-to-the-color-ID-list.patch | 29 +++++++ ...or-option-as-that-is-different-from-.patch | 48 ++++++++++++ 3 files changed, 153 insertions(+) create mode 100644 target/linux/generic/backport-5.4/900-v5.9-0001-dt-bindings-Add-multicolor-class-dt-bindings-documen.patch create mode 100644 target/linux/generic/backport-5.4/900-v5.9-0002-leds-Add-multicolor-ID-to-the-color-ID-list.patch create mode 100644 target/linux/generic/backport-5.4/900-v5.9-0003-leds-add-RGB-color-option-as-that-is-different-from-.patch diff --git a/target/linux/generic/backport-5.4/900-v5.9-0001-dt-bindings-Add-multicolor-class-dt-bindings-documen.patch b/target/linux/generic/backport-5.4/900-v5.9-0001-dt-bindings-Add-multicolor-class-dt-bindings-documen.patch new file mode 100644 index 0000000000..acc32b69fb --- /dev/null +++ b/target/linux/generic/backport-5.4/900-v5.9-0001-dt-bindings-Add-multicolor-class-dt-bindings-documen.patch @@ -0,0 +1,76 @@ +From 5c7f8ffe741daae7f8d811a2037b2693f02c90c5 Mon Sep 17 00:00:00 2001 +From: Dan Murphy +Date: Mon, 13 Jul 2020 10:45:31 -0500 +Subject: [PATCH] dt: bindings: Add multicolor class dt bindings documention +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +Add DT bindings for the LEDs multicolor class framework. +Add multicolor ID to the color ID list for device tree bindings. + +CC: Rob Herring +Reviewed-by: Rob Herring +Acked-by: Pavel Machek +Acked-by: Jacek Anaszewski +Signed-off-by: Dan Murphy +Reviewed-by: Marek Behún +Signed-off-by: Pavel Machek +--- + .../bindings/leds/leds-class-multicolor.yaml | 37 +++++++++++++++++++ + include/dt-bindings/leds/common.h | 3 +- + 2 files changed, 39 insertions(+), 1 deletion(-) + create mode 100644 Documentation/devicetree/bindings/leds/leds-class-multicolor.yaml + +--- /dev/null ++++ b/Documentation/devicetree/bindings/leds/leds-class-multicolor.yaml +@@ -0,0 +1,37 @@ ++# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) ++%YAML 1.2 ++--- ++$id: http://devicetree.org/schemas/leds/leds-class-multicolor.yaml# ++$schema: http://devicetree.org/meta-schemas/core.yaml# ++ ++title: Common properties for the multicolor LED class. ++ ++maintainers: ++ - Dan Murphy ++ ++description: | ++ Bindings for multi color LEDs show how to describe current outputs of ++ either integrated multi-color LED elements (like RGB, RGBW, RGBWA-UV ++ etc.) or standalone LEDs, to achieve logically grouped multi-color LED ++ modules. This is achieved by adding multi-led nodes layer to the ++ monochrome LED bindings. ++ The nodes and properties defined in this document are unique to the multicolor ++ LED class. Common LED nodes and properties are inherited from the common.txt ++ within this documentation directory. ++ ++patternProperties: ++ "^multi-led@([0-9a-f])$": ++ type: object ++ description: Represents the LEDs that are to be grouped. ++ properties: ++ color: ++ const: 8 # LED_COLOR_ID_MULTI ++ description: | ++ For multicolor LED support this property should be defined as ++ LED_COLOR_ID_MULTI which can be found in include/linux/leds/common.h. ++ ++ $ref: "common.yaml#" ++ ++ required: ++ - color ++... +--- a/include/dt-bindings/leds/common.h ++++ b/include/dt-bindings/leds/common.h +@@ -29,7 +29,8 @@ + #define LED_COLOR_ID_VIOLET 5 + #define LED_COLOR_ID_YELLOW 6 + #define LED_COLOR_ID_IR 7 +-#define LED_COLOR_ID_MAX 8 ++#define LED_COLOR_ID_MULTI 8 ++#define LED_COLOR_ID_MAX 9 + + /* Standard LED functions */ + #define LED_FUNCTION_ACTIVITY "activity" diff --git a/target/linux/generic/backport-5.4/900-v5.9-0002-leds-Add-multicolor-ID-to-the-color-ID-list.patch b/target/linux/generic/backport-5.4/900-v5.9-0002-leds-Add-multicolor-ID-to-the-color-ID-list.patch new file mode 100644 index 0000000000..5de5dbda04 --- /dev/null +++ b/target/linux/generic/backport-5.4/900-v5.9-0002-leds-Add-multicolor-ID-to-the-color-ID-list.patch @@ -0,0 +1,29 @@ +From 10d3e0d815879129e916cd83e1034438e06efdaa Mon Sep 17 00:00:00 2001 +From: Dan Murphy +Date: Mon, 13 Jul 2020 10:45:32 -0500 +Subject: [PATCH] leds: Add multicolor ID to the color ID list +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +Add a new color ID that is declared as MULTICOLOR as with the +multicolor framework declaring a definitive color is not accurate +as the node can contain multiple colors. + +Signed-off-by: Dan Murphy +Reviewed-by: Marek Behún +Signed-off-by: Pavel Machek +--- + drivers/leds/led-core.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/drivers/leds/led-core.c ++++ b/drivers/leds/led-core.c +@@ -34,6 +34,7 @@ const char * const led_colors[LED_COLOR_ + [LED_COLOR_ID_VIOLET] = "violet", + [LED_COLOR_ID_YELLOW] = "yellow", + [LED_COLOR_ID_IR] = "ir", ++ [LED_COLOR_ID_MULTI] = "multicolor", + }; + EXPORT_SYMBOL_GPL(led_colors); + diff --git a/target/linux/generic/backport-5.4/900-v5.9-0003-leds-add-RGB-color-option-as-that-is-different-from-.patch b/target/linux/generic/backport-5.4/900-v5.9-0003-leds-add-RGB-color-option-as-that-is-different-from-.patch new file mode 100644 index 0000000000..17c28149f6 --- /dev/null +++ b/target/linux/generic/backport-5.4/900-v5.9-0003-leds-add-RGB-color-option-as-that-is-different-from-.patch @@ -0,0 +1,48 @@ +From 54212f5a1ba3123281877e54c1e5f672bf7563d8 Mon Sep 17 00:00:00 2001 +From: Pavel Machek +Date: Mon, 3 Aug 2020 13:20:06 +0200 +Subject: [PATCH] leds: add RGB color option, as that is different from + multicolor. + +Multicolor is a bit too abstract. Yes, we can have +Green-Magenta-Ultraviolet LED, but so far all the LEDs we support are +RGB, and not even RGB-White or RGB-Yellow variants emerged. + +Multicolor is not a good fit for RGB LED. It does not really know +about LED color. In particular, there's no way to make LED "white". + +Userspace is interested in knowing "this LED can produce arbitrary +color", which not all multicolor LEDs can. + +Signed-off-by: Pavel Machek +--- + drivers/leds/led-core.c | 1 + + drivers/leds/leds-lp55xx-common.c | 2 +- + include/dt-bindings/leds/common.h | 6 ++++-- + 3 files changed, 6 insertions(+), 3 deletions(-) + +--- a/drivers/leds/led-core.c ++++ b/drivers/leds/led-core.c +@@ -35,6 +35,7 @@ const char * const led_colors[LED_COLOR_ + [LED_COLOR_ID_YELLOW] = "yellow", + [LED_COLOR_ID_IR] = "ir", + [LED_COLOR_ID_MULTI] = "multicolor", ++ [LED_COLOR_ID_RGB] = "rgb", + }; + EXPORT_SYMBOL_GPL(led_colors); + +--- a/include/dt-bindings/leds/common.h ++++ b/include/dt-bindings/leds/common.h +@@ -29,8 +29,10 @@ + #define LED_COLOR_ID_VIOLET 5 + #define LED_COLOR_ID_YELLOW 6 + #define LED_COLOR_ID_IR 7 +-#define LED_COLOR_ID_MULTI 8 +-#define LED_COLOR_ID_MAX 9 ++#define LED_COLOR_ID_MULTI 8 /* For multicolor LEDs */ ++#define LED_COLOR_ID_RGB 9 /* For multicolor LEDs that can do arbitrary color, ++ so this would include RGBW and similar */ ++#define LED_COLOR_ID_MAX 10 + + /* Standard LED functions */ + #define LED_FUNCTION_ACTIVITY "activity" From 18b10db2f1945e9af4fcd5476fef808c15623cc5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Fri, 17 Dec 2021 11:40:54 +0100 Subject: [PATCH 36/43] arm-trusted-firmware-bcm63xx: add ATF for Broadcom devices MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Right now it includes bcm4908 variant only that is required by BCM4908 family devices with U-Boot. Signed-off-by: Rafał Miłecki (cherry picked from commit f18288e26715f8cdef6c6d62a196dfd4ade8265e) --- .../arm-trusted-firmware-bcm63xx/Makefile | 42 +++++++++++++++++++ 1 file changed, 42 insertions(+) create mode 100644 package/boot/arm-trusted-firmware-bcm63xx/Makefile diff --git a/package/boot/arm-trusted-firmware-bcm63xx/Makefile b/package/boot/arm-trusted-firmware-bcm63xx/Makefile new file mode 100644 index 0000000000..12571e8d96 --- /dev/null +++ b/package/boot/arm-trusted-firmware-bcm63xx/Makefile @@ -0,0 +1,42 @@ +# SPDX-License-Identifier: GPL-2.0 + +include $(TOPDIR)/rules.mk + +PKG_VERSION:=2.2 +PKG_RELEASE:=$(AUTORELEASE) + +PKG_SOURCE_PROTO:=git +PKG_SOURCE_URL=$(PROJECT_GIT)/project/bcm63xx/atf.git +PKG_SOURCE_DATE:=2021-12-24 +PKG_SOURCE_VERSION:=e6d46baf3fae79f693f90bf34f7284c3dfc64aef +PKG_MIRROR_HASH:=9d5d04f572b1b6ddc6eb3064b9cb09f5fe982e82d350790041d35316349af124 + +PKG_MAINTAINER:=Rafał Miłecki + +include $(INCLUDE_DIR)/trusted-firmware-a.mk +include $(INCLUDE_DIR)/package.mk + +define Trusted-Firmware-A/Default + PLAT:=bcm + DEFAULT:=y +endef + +define Trusted-Firmware-A/bcm4908 + BUILD_TARGET:=bcm4908 + NAME:=BCM4908 + BRCM_CHIP=4908 + TFA_IMAGE:=bl31.bin +endef + +TFA_TARGETS:= \ + bcm4908 + +TFA_MAKE_FLAGS += \ + BRCM_CHIP=$(BRCM_CHIP) + +define Package/trusted-firmware-a/install + $(INSTALL_DIR) $(STAGING_DIR_IMAGE) + $(INSTALL_DATA) $(PKG_BUILD_DIR)/build/$(PLAT)/release/$(TFA_IMAGE) $(STAGING_DIR_IMAGE)/ +endef + +$(eval $(call BuildPackage/Trusted-Firmware-A)) From 93842b20dcb87cf55af53a8ff54209aa19adc6a1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Fri, 24 Dec 2021 23:07:39 +0100 Subject: [PATCH 37/43] bcm4908: include ATF in bootfs images MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit It's required for proper booting. Signed-off-by: Rafał Miłecki (cherry picked from commit 65974aa18bf49005509e0c31ee3f3aa6fb186015) --- target/linux/bcm4908/image/Makefile | 1 + target/linux/bcm4908/image/bootfs-generic.its | 15 +++++++++++++++ 2 files changed, 16 insertions(+) diff --git a/target/linux/bcm4908/image/Makefile b/target/linux/bcm4908/image/Makefile index 09a8ddedee..93a28b7e9d 100644 --- a/target/linux/bcm4908/image/Makefile +++ b/target/linux/bcm4908/image/Makefile @@ -9,6 +9,7 @@ DEVICE_VARS += PKGTB_ITS define Image/Prepare cp bootfs-generic.its $(KDIR)/ + sed -i "s=\$$$${images_dir}=$(STAGING_DIR_IMAGE)=" $(KDIR)/bootfs-generic.its sed -i "s=\$$$${dts_dir}=$(DTS_DIR)=" $(KDIR)/bootfs-generic.its endef diff --git a/target/linux/bcm4908/image/bootfs-generic.its b/target/linux/bcm4908/image/bootfs-generic.its index 6d8b3394ae..3cde532d72 100644 --- a/target/linux/bcm4908/image/bootfs-generic.its +++ b/target/linux/bcm4908/image/bootfs-generic.its @@ -7,6 +7,21 @@ #address-cells = <1>; images { + atf { + description = "ATF"; + data = /incbin/("${images_dir}/bl31.bin"); + type = "firmware"; + arch = "arm64"; + os = "arm-trusted-firmware"; + compression = "none"; + load = <0x4000>; + entry = <0x4000>; + + hash-1 { + algo = "sha256"; + }; + }; + kernel { description = "Linux kernel"; data = /incbin/("${kernel}"); From 5beaa75d94c4a981c580905b84c7ef33caf0c3e2 Mon Sep 17 00:00:00 2001 From: Eneas U de Queiroz Date: Mon, 3 Jan 2022 10:52:58 -0300 Subject: [PATCH 38/43] openssl: bump to 1.1.1m This is a bugfix release. Changelog: *) Avoid loading of a dynamic engine twice. *) Fixed building on Debian with kfreebsd kernels *) Prioritise DANE TLSA issuer certs over peer certs *) Fixed random API for MacOS prior to 10.12 Patches were refreshed. Signed-off-by: Eneas U de Queiroz (cherry picked from commit def9565be632b316c82ffc5a7b28c789e9df75b4) --- package/libs/openssl/Makefile | 4 ++-- .../libs/openssl/patches/100-Configure-afalg-support.patch | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/package/libs/openssl/Makefile b/package/libs/openssl/Makefile index 0397ab90c4..e8e10524ca 100644 --- a/package/libs/openssl/Makefile +++ b/package/libs/openssl/Makefile @@ -9,7 +9,7 @@ include $(TOPDIR)/rules.mk PKG_NAME:=openssl PKG_BASE:=1.1.1 -PKG_BUGFIX:=l +PKG_BUGFIX:=m PKG_VERSION:=$(PKG_BASE)$(PKG_BUGFIX) PKG_RELEASE:=1 PKG_USE_MIPS16:=0 @@ -26,7 +26,7 @@ PKG_SOURCE_URL:= \ ftp://ftp.pca.dfn.de/pub/tools/net/openssl/source/ \ ftp://ftp.pca.dfn.de/pub/tools/net/openssl/source/old/$(PKG_BASE)/ -PKG_HASH:=0b7a3e5e59c34827fe0c3a74b7ec8baef302b98fa80088d7f9153aa16fa76bd1 +PKG_HASH:=f89199be8b23ca45fc7cb9f1d8d3ee67312318286ad030f5316aca6462db6c96 PKG_LICENSE:=OpenSSL PKG_LICENSE_FILES:=LICENSE diff --git a/package/libs/openssl/patches/100-Configure-afalg-support.patch b/package/libs/openssl/patches/100-Configure-afalg-support.patch index 98944103b5..d8789f4b45 100644 --- a/package/libs/openssl/patches/100-Configure-afalg-support.patch +++ b/package/libs/openssl/patches/100-Configure-afalg-support.patch @@ -12,7 +12,7 @@ diff --git a/Configure b/Configure index 5a699836f3..74d057c219 100755 --- a/Configure +++ b/Configure -@@ -1545,7 +1545,9 @@ unless ($disabled{"crypto-mdebug-backtrace"}) +@@ -1548,7 +1548,9 @@ unless ($disabled{"crypto-mdebug-backtrace"}) unless ($disabled{afalgeng}) { $config{afalgeng}=""; From 96b5962704611fa37d8ed46b73f4254170529b7a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marek=20Beh=C3=BAn?= Date: Fri, 7 Jan 2022 19:45:15 +0100 Subject: [PATCH 39/43] mvebu: remove patch that was applied into linux stable MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The patch PCI: aardvark: Don't touch PCIe registers if no card connected was applied into Linux stable version 5.4.163. Remove it from patches-5.4. (It applied even though it was applied already, resulting in repeated code.) Fixes: 14940aee4566 ("kernel: bump 5.4 to 5.4.163") Signed-off-by: Marek Behún --- ...-t-touch-PCIe-registers-if-no-card-c.patch | 50 ------------------- ...-initialization-with-old-Marvell-s-A.patch | 2 +- 2 files changed, 1 insertion(+), 51 deletions(-) delete mode 100644 target/linux/mvebu/patches-5.4/024-PCI-aardvark-Don-t-touch-PCIe-registers-if-no-card-c.patch diff --git a/target/linux/mvebu/patches-5.4/024-PCI-aardvark-Don-t-touch-PCIe-registers-if-no-card-c.patch b/target/linux/mvebu/patches-5.4/024-PCI-aardvark-Don-t-touch-PCIe-registers-if-no-card-c.patch deleted file mode 100644 index 7a8c50634f..0000000000 --- a/target/linux/mvebu/patches-5.4/024-PCI-aardvark-Don-t-touch-PCIe-registers-if-no-card-c.patch +++ /dev/null @@ -1,50 +0,0 @@ -From 70e380250c3621c55ff218cbaf2272830d9dbb1d Mon Sep 17 00:00:00 2001 -From: =?UTF-8?q?Pali=20Roh=C3=A1r?= -Date: Thu, 2 Jul 2020 10:30:36 +0200 -Subject: [PATCH] PCI: aardvark: Don't touch PCIe registers if no card - connected -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -When there is no PCIe card connected and advk_pcie_rd_conf() or -advk_pcie_wr_conf() is called for PCI bus which doesn't belong to emulated -root bridge, the aardvark driver throws the following error message: - - advk-pcie d0070000.pcie: config read/write timed out - -Obviously accessing PCIe registers of disconnected card is not possible. - -Extend check in advk_pcie_valid_device() function for validating -availability of PCIe bus. If PCIe link is down, then the device is marked -as Not Found and the driver does not try to access these registers. - -This is just an optimization to prevent accessing PCIe registers when card -is disconnected. Trying to access PCIe registers of disconnected card does -not cause any crash, kernel just needs to wait for a timeout. So if card -disappear immediately after checking for PCIe link (before accessing PCIe -registers), it does not cause any problems. - -Link: https://lore.kernel.org/r/20200702083036.12230-1-pali@kernel.org -Signed-off-by: Pali Rohár -Signed-off-by: Lorenzo Pieralisi ---- - drivers/pci/controller/pci-aardvark.c | 7 +++++++ - 1 file changed, 7 insertions(+) - ---- a/drivers/pci/controller/pci-aardvark.c -+++ b/drivers/pci/controller/pci-aardvark.c -@@ -976,6 +976,13 @@ static bool advk_pcie_valid_device(struc - if (bus->number != pcie->root_bus_nr && !advk_pcie_link_up(pcie)) - return false; - -+ /* -+ * If the link goes down after we check for link-up, nothing bad -+ * happens but the config access times out. -+ */ -+ if (bus->number != pcie->root_bus_nr && !advk_pcie_link_up(pcie)) -+ return false; -+ - return true; - } - diff --git a/target/linux/mvebu/patches-5.4/026-PCI-aardvark-Fix-initialization-with-old-Marvell-s-A.patch b/target/linux/mvebu/patches-5.4/026-PCI-aardvark-Fix-initialization-with-old-Marvell-s-A.patch index bcf63ab8ec..5a6173a666 100644 --- a/target/linux/mvebu/patches-5.4/026-PCI-aardvark-Fix-initialization-with-old-Marvell-s-A.patch +++ b/target/linux/mvebu/patches-5.4/026-PCI-aardvark-Fix-initialization-with-old-Marvell-s-A.patch @@ -31,7 +31,7 @@ Cc: # 5.8+: ea17a0f153af: phy: marvell: comphy: Convert --- a/drivers/pci/controller/pci-aardvark.c +++ b/drivers/pci/controller/pci-aardvark.c -@@ -1533,7 +1533,9 @@ static int advk_pcie_enable_phy(struct a +@@ -1526,7 +1526,9 @@ static int advk_pcie_enable_phy(struct a } ret = phy_power_on(pcie->phy); From bc37a699e5725994857af9383ff7f7d7bd5fe912 Mon Sep 17 00:00:00 2001 From: "Keith T. Garner" Date: Wed, 5 May 2021 09:04:15 -0500 Subject: [PATCH 40/43] kernel: add kmod-leds-uleds The allows userspace LEDs to be created and controlled. This can be useful for testing triggers and can also be used to implement virtual LEDs. Signed-off-by: Keith T. Garner [squash fixup commit and improve option wording] Signed-off-by: Paul Spooren (cherry picked from commit 6a37286c2add96dba42fdd285162228eb55a99f1) --- package/kernel/linux/modules/leds.mk | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/package/kernel/linux/modules/leds.mk b/package/kernel/linux/modules/leds.mk index bc94e54ae1..4c96fa9bf9 100644 --- a/package/kernel/linux/modules/leds.mk +++ b/package/kernel/linux/modules/leds.mk @@ -114,3 +114,17 @@ define KernelPackage/leds-pwm/description endef $(eval $(call KernelPackage,leds-pwm)) + +define KernelPackage/leds-uleds + SUBMENU:=$(LEDS_MENU) + TITLE:=Userspace LEDs + KCONFIG:=CONFIG_LEDS_USER + FILES:=$(LINUX_DIR)/drivers/leds/uleds.ko + AUTOLOAD:=$(call AutoLoad,60,leds-uleds,1) +endef + +define KernelPackage/leds-uleds/description + This option enables support for userspace LEDs. +endef + +$(eval $(call KernelPackage,leds-uleds)) From aa2de44cdd9ec0c8edcd385e69859b47f1d2fd84 Mon Sep 17 00:00:00 2001 From: Evgeny Kolesnikov Date: Tue, 25 May 2021 16:38:33 +0200 Subject: [PATCH 41/43] kernel: fix AutoLoad parameter for uleds module The name of the module is 'uleds', not 'leds-uleds'. Signed-off-by: Evgeny Kolesnikov [improve commit title] Signed-off-by: David Bauer (cherry picked from commit 3e9318f3c0be1ae14d9d4eb705b02e7441d5d26e) --- package/kernel/linux/modules/leds.mk | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package/kernel/linux/modules/leds.mk b/package/kernel/linux/modules/leds.mk index 4c96fa9bf9..a820bbe826 100644 --- a/package/kernel/linux/modules/leds.mk +++ b/package/kernel/linux/modules/leds.mk @@ -120,7 +120,7 @@ define KernelPackage/leds-uleds TITLE:=Userspace LEDs KCONFIG:=CONFIG_LEDS_USER FILES:=$(LINUX_DIR)/drivers/leds/uleds.ko - AUTOLOAD:=$(call AutoLoad,60,leds-uleds,1) + AUTOLOAD:=$(call AutoLoad,60,uleds,1) endef define KernelPackage/leds-uleds/description From 77ee281a3ef44eb8b3c38a8db932737725c233fa Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Karel=20Ko=C4=8D=C3=AD?= Date: Fri, 12 Nov 2021 09:10:45 +0100 Subject: [PATCH 42/43] kernel: add kmod-ledtrig-pattern MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This allows LEDs to be triggered by custom pattern and not just predefined ones. Signed-off-by: Karel Kočí (cherry picked from commit 507911f477cc29531a2fbdf364df42e7e4f3c696) --- package/kernel/linux/modules/leds.mk | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/package/kernel/linux/modules/leds.mk b/package/kernel/linux/modules/leds.mk index a820bbe826..a22ea1e5f4 100644 --- a/package/kernel/linux/modules/leds.mk +++ b/package/kernel/linux/modules/leds.mk @@ -84,6 +84,22 @@ endef $(eval $(call KernelPackage,ledtrig-oneshot)) +define KernelPackage/ledtrig-pattern + SUBMENU:=$(LEDS_MENU) + TITLE:=LED Pattern Trigger + KCONFIG:=CONFIG_LEDS_TRIGGER_PATTERN + FILES:=$(LED_TRIGGER_DIR)/ledtrig-pattern.ko + AUTOLOAD:=$(call AutoLoad,50,ledtrig-pattern) +endef + +define KernelPackage/ledtrig-pattern/description + This allows LEDs to be controlled by a software or hardware pattern + which is a series of tuples, of brightness and duration (ms). +endef + +$(eval $(call KernelPackage,ledtrig-pattern)) + + define KernelPackage/leds-pca963x SUBMENU:=$(LEDS_MENU) TITLE:=PCA963x LED support From 6ced8cad8edd2a04fc6bb914c333c8aac9a1c825 Mon Sep 17 00:00:00 2001 From: Vladimir Markovets Date: Thu, 22 Jul 2021 00:09:22 +0200 Subject: [PATCH 43/43] kernel: backport workaround for Realtek RTL8672 and RTL9601C chips Adds support for GPON SFP modules based on the Realtek RTL8672 and RTL9601C chips, including but not limited to: * V-SOL V2801F * C-Data FD511GX-RM0 * OPTON GP801R * BAUDCOM BD-1234-SFM * CPGOS03-0490 v2.0 * Ubiquiti U-Fiber Instant * EXOT EGS1 Signed-off-by: Vladimir Markovets (cherry picked from commit f032601ed7d70fe1f468219b68750230b6ea1906) --- ...01F-CarlitoxxPro-CPGOS03-0490-v2.0-w.patch | 144 ++++++++++++ ...around-for-Realtek-RTL8672-and-RTL96.patch | 211 ++++++++++++++++++ ...void-tx-fault-with-Nokia-GPON-module.patch | 12 +- ...ncomplete-100BASE-FX-and-100BASE-LX-.patch | 2 +- ...p-add-more-extended-compliance-codes.patch | 4 +- ...le-start-stop-upstream-notifications.patch | 4 +- ...p-move-phy_start-phy_stop-to-phylink.patch | 4 +- ...t-sfp-add-support-for-Clause-45-PHYs.patch | 8 +- .../pending-5.4/754-net-sfp-fix-unbind.patch | 2 +- .../pending-5.4/755-net-sfp-fix-hwmon.patch | 4 +- ...finition-for-the-fault-recovery-atte.patch | 6 +- .../757-net-sfp-rename-sm_retries.patch | 10 +- ...net-sfp-error-handling-for-phy-probe.patch | 10 +- ...9-net-sfp-re-attempt-probing-for-phy.patch | 8 +- 14 files changed, 392 insertions(+), 37 deletions(-) create mode 100644 target/linux/generic/backport-5.4/852-v5.10-0001-net-sfp-VSOL-V2801F-CarlitoxxPro-CPGOS03-0490-v2.0-w.patch create mode 100644 target/linux/generic/backport-5.4/852-v5.10-0002-net-sfp-add-workaround-for-Realtek-RTL8672-and-RTL96.patch diff --git a/target/linux/generic/backport-5.4/852-v5.10-0001-net-sfp-VSOL-V2801F-CarlitoxxPro-CPGOS03-0490-v2.0-w.patch b/target/linux/generic/backport-5.4/852-v5.10-0001-net-sfp-VSOL-V2801F-CarlitoxxPro-CPGOS03-0490-v2.0-w.patch new file mode 100644 index 0000000000..1901054a10 --- /dev/null +++ b/target/linux/generic/backport-5.4/852-v5.10-0001-net-sfp-VSOL-V2801F-CarlitoxxPro-CPGOS03-0490-v2.0-w.patch @@ -0,0 +1,144 @@ +From 0d035bed2a4a6c4878518749348be61bf082d12a Mon Sep 17 00:00:00 2001 +From: Russell King +Date: Wed, 9 Dec 2020 11:22:49 +0000 +Subject: [PATCH] net: sfp: VSOL V2801F / CarlitoxxPro CPGOS03-0490 v2.0 + workaround +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +Add a workaround for the detection of VSOL V2801F / CarlitoxxPro +CPGOS03-0490 v2.0 GPON module which CarlitoxxPro states needs single +byte I2C reads to the EEPROM. + +Pali Rohár reports that he also has a CarlitoxxPro-based V2801F module, +which reports a manufacturer of "OEM". This manufacturer can't be +matched as it appears in many different modules, so also match the part +number too. + +Reported-by: Thomas Schreiber +Reported-by: Pali Rohár +Tested-by: Pali Rohár +Reviewed-by: Andrew Lunn +Signed-off-by: Russell King +Signed-off-by: David S. Miller +--- + drivers/net/phy/sfp.c | 63 +++++++++++++++++++++++++++++++++++++++---- + 1 file changed, 58 insertions(+), 5 deletions(-) + +--- a/drivers/net/phy/sfp.c ++++ b/drivers/net/phy/sfp.c +@@ -191,6 +191,7 @@ struct sfp { + struct sfp_bus *sfp_bus; + struct phy_device *mod_phy; + const struct sff_data *type; ++ size_t i2c_block_size; + u32 max_power_mW; + + unsigned int (*get_state)(struct sfp *); +@@ -305,10 +306,19 @@ static int sfp_i2c_read(struct sfp *sfp, + size_t len) + { + struct i2c_msg msgs[2]; +- u8 bus_addr = a2 ? 0x51 : 0x50; ++ size_t block_size; + size_t this_len; ++ u8 bus_addr; + int ret; + ++ if (a2) { ++ block_size = 16; ++ bus_addr = 0x51; ++ } else { ++ block_size = sfp->i2c_block_size; ++ bus_addr = 0x50; ++ } ++ + msgs[0].addr = bus_addr; + msgs[0].flags = 0; + msgs[0].len = 1; +@@ -320,8 +330,8 @@ static int sfp_i2c_read(struct sfp *sfp, + + while (len) { + this_len = len; +- if (this_len > 16) +- this_len = 16; ++ if (this_len > block_size) ++ this_len = block_size; + + msgs[1].len = this_len; + +@@ -1569,6 +1579,28 @@ static int sfp_sm_mod_hpower(struct sfp + return 0; + } + ++/* Some modules (Nokia 3FE46541AA) lock up if byte 0x51 is read as a ++ * single read. Switch back to reading 16 byte blocks unless we have ++ * a CarlitoxxPro module (rebranded VSOL V2801F). Even more annoyingly, ++ * some VSOL V2801F have the vendor name changed to OEM. ++ */ ++static int sfp_quirk_i2c_block_size(const struct sfp_eeprom_base *base) ++{ ++ if (!memcmp(base->vendor_name, "VSOL ", 16)) ++ return 1; ++ if (!memcmp(base->vendor_name, "OEM ", 16) && ++ !memcmp(base->vendor_pn, "V2801F ", 16)) ++ return 1; ++ ++ /* Some modules can't cope with long reads */ ++ return 16; ++} ++ ++static void sfp_quirks_base(struct sfp *sfp, const struct sfp_eeprom_base *base) ++{ ++ sfp->i2c_block_size = sfp_quirk_i2c_block_size(base); ++} ++ + static int sfp_sm_mod_probe(struct sfp *sfp, bool report) + { + /* SFP module inserted - read I2C data */ +@@ -1577,14 +1609,20 @@ static int sfp_sm_mod_probe(struct sfp * + u8 check; + int ret; + +- ret = sfp_read(sfp, false, 0, &id, sizeof(id)); ++ /* Some modules (CarlitoxxPro CPGOS03-0490) do not support multibyte ++ * reads from the EEPROM, so start by reading the base identifying ++ * information one byte at a time. ++ */ ++ sfp->i2c_block_size = 1; ++ ++ ret = sfp_read(sfp, false, 0, &id.base, sizeof(id.base)); + if (ret < 0) { + if (report) + dev_err(sfp->dev, "failed to read EEPROM: %d\n", ret); + return -EAGAIN; + } + +- if (ret != sizeof(id)) { ++ if (ret != sizeof(id.base)) { + dev_err(sfp->dev, "EEPROM short read: %d\n", ret); + return -EAGAIN; + } +@@ -1612,6 +1650,21 @@ static int sfp_sm_mod_probe(struct sfp * + } + } + ++ /* Apply any early module-specific quirks */ ++ sfp_quirks_base(sfp, &id.base); ++ ++ ret = sfp_read(sfp, false, SFP_CC_BASE + 1, &id.ext, sizeof(id.ext)); ++ if (ret < 0) { ++ if (report) ++ dev_err(sfp->dev, "failed to read EEPROM: %d\n", ret); ++ return -EAGAIN; ++ } ++ ++ if (ret != sizeof(id.ext)) { ++ dev_err(sfp->dev, "EEPROM short read: %d\n", ret); ++ return -EAGAIN; ++ } ++ + check = sfp_check(&id.ext, sizeof(id.ext) - 1); + if (check != id.ext.cc_ext) { + if (cotsworks) { diff --git a/target/linux/generic/backport-5.4/852-v5.10-0002-net-sfp-add-workaround-for-Realtek-RTL8672-and-RTL96.patch b/target/linux/generic/backport-5.4/852-v5.10-0002-net-sfp-add-workaround-for-Realtek-RTL8672-and-RTL96.patch new file mode 100644 index 0000000000..27ae97cee7 --- /dev/null +++ b/target/linux/generic/backport-5.4/852-v5.10-0002-net-sfp-add-workaround-for-Realtek-RTL8672-and-RTL96.patch @@ -0,0 +1,211 @@ +From 426c6cbc409cbda9ab1a9dbf15d3c2ef947eb8c1 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Pali=20Roh=C3=A1r?= +Date: Mon, 25 Jan 2021 16:02:27 +0100 +Subject: [PATCH] net: sfp: add workaround for Realtek RTL8672 and RTL9601C + chips +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +The workaround for VSOL V2801F brand based GPON SFP modules added in commit +0d035bed2a4a ("net: sfp: VSOL V2801F / CarlitoxxPro CPGOS03-0490 v2.0 +workaround") works only for IDs added explicitly to the list. Since there +are rebranded modules where OEM vendors put different strings into the +vendor name field, we cannot base workaround on IDs only. + +Moreover the issue which the above mentioned commit tried to work around is +generic not only to VSOL based modules, but rather to all GPON modules +based on Realtek RTL8672 and RTL9601C chips. + +These include at least the following GPON modules: +* V-SOL V2801F +* C-Data FD511GX-RM0 +* OPTON GP801R +* BAUDCOM BD-1234-SFM +* CPGOS03-0490 v2.0 +* Ubiquiti U-Fiber Instant +* EXOT EGS1 + +These Realtek chips have broken EEPROM emulator which for N-byte read +operation returns just the first byte of EEPROM data, followed by N-1 +zeros. + +Introduce a new function, sfp_id_needs_byte_io(), which detects SFP modules +with broken EEPROM emulator based on N-1 zeros and switch to 1 byte EEPROM +reading operation. + +Function sfp_i2c_read() now always uses single byte reading when it is +required and when function sfp_hwmon_probe() detects single byte access, +it disables registration of hwmon device, because in this case we cannot +reliably and atomically read 2 bytes as is required by the standard for +retrieving values from diagnostic area. + +(These Realtek chips are broken in a way that violates SFP standards for +diagnostic interface. Kernel in this case simply cannot do anything less +of skipping registration of the hwmon interface.) + +This patch fixes reading of EEPROM content from SFP modules based on +Realtek RTL8672 and RTL9601C chips. Diagnostic interface of EEPROM stays +broken and cannot be fixed. + +Fixes: 0d035bed2a4a ("net: sfp: VSOL V2801F / CarlitoxxPro CPGOS03-0490 v2.0 workaround") +Co-developed-by: Russell King +Signed-off-by: Russell King +Signed-off-by: Pali Rohár +Signed-off-by: Jakub Kicinski +--- + drivers/net/phy/sfp.c | 100 ++++++++++++++++++++++++++++-------------- + 1 file changed, 67 insertions(+), 33 deletions(-) + +--- a/drivers/net/phy/sfp.c ++++ b/drivers/net/phy/sfp.c +@@ -306,19 +306,11 @@ static int sfp_i2c_read(struct sfp *sfp, + size_t len) + { + struct i2c_msg msgs[2]; +- size_t block_size; ++ u8 bus_addr = a2 ? 0x51 : 0x50; ++ size_t block_size = sfp->i2c_block_size; + size_t this_len; +- u8 bus_addr; + int ret; + +- if (a2) { +- block_size = 16; +- bus_addr = 0x51; +- } else { +- block_size = sfp->i2c_block_size; +- bus_addr = 0x50; +- } +- + msgs[0].addr = bus_addr; + msgs[0].flags = 0; + msgs[0].len = 1; +@@ -1245,6 +1237,20 @@ static void sfp_hwmon_probe(struct work_ + struct sfp *sfp = container_of(work, struct sfp, hwmon_probe.work); + int err, i; + ++ /* hwmon interface needs to access 16bit registers in atomic way to ++ * guarantee coherency of the diagnostic monitoring data. If it is not ++ * possible to guarantee coherency because EEPROM is broken in such way ++ * that does not support atomic 16bit read operation then we have to ++ * skip registration of hwmon device. ++ */ ++ if (sfp->i2c_block_size < 2) { ++ dev_info(sfp->dev, ++ "skipping hwmon device registration due to broken EEPROM\n"); ++ dev_info(sfp->dev, ++ "diagnostic EEPROM area cannot be read atomically to guarantee data coherency\n"); ++ return; ++ } ++ + err = sfp_read(sfp, true, 0, &sfp->diag, sizeof(sfp->diag)); + if (err < 0) { + if (sfp->hwmon_tries--) { +@@ -1579,26 +1585,30 @@ static int sfp_sm_mod_hpower(struct sfp + return 0; + } + +-/* Some modules (Nokia 3FE46541AA) lock up if byte 0x51 is read as a +- * single read. Switch back to reading 16 byte blocks unless we have +- * a CarlitoxxPro module (rebranded VSOL V2801F). Even more annoyingly, +- * some VSOL V2801F have the vendor name changed to OEM. ++/* GPON modules based on Realtek RTL8672 and RTL9601C chips (e.g. V-SOL ++ * V2801F, CarlitoxxPro CPGOS03-0490, Ubiquiti U-Fiber Instant, ...) do ++ * not support multibyte reads from the EEPROM. Each multi-byte read ++ * operation returns just one byte of EEPROM followed by zeros. There is ++ * no way to identify which modules are using Realtek RTL8672 and RTL9601C ++ * chips. Moreover every OEM of V-SOL V2801F module puts its own vendor ++ * name and vendor id into EEPROM, so there is even no way to detect if ++ * module is V-SOL V2801F. Therefore check for those zeros in the read ++ * data and then based on check switch to reading EEPROM to one byte ++ * at a time. + */ +-static int sfp_quirk_i2c_block_size(const struct sfp_eeprom_base *base) ++static bool sfp_id_needs_byte_io(struct sfp *sfp, void *buf, size_t len) + { +- if (!memcmp(base->vendor_name, "VSOL ", 16)) +- return 1; +- if (!memcmp(base->vendor_name, "OEM ", 16) && +- !memcmp(base->vendor_pn, "V2801F ", 16)) +- return 1; ++ size_t i, block_size = sfp->i2c_block_size; + +- /* Some modules can't cope with long reads */ +- return 16; +-} ++ /* Already using byte IO */ ++ if (block_size == 1) ++ return false; + +-static void sfp_quirks_base(struct sfp *sfp, const struct sfp_eeprom_base *base) +-{ +- sfp->i2c_block_size = sfp_quirk_i2c_block_size(base); ++ for (i = 1; i < len; i += block_size) { ++ if (memchr_inv(buf + i, '\0', min(block_size - 1, len - i))) ++ return false; ++ } ++ return true; + } + + static int sfp_sm_mod_probe(struct sfp *sfp, bool report) +@@ -1609,11 +1619,11 @@ static int sfp_sm_mod_probe(struct sfp * + u8 check; + int ret; + +- /* Some modules (CarlitoxxPro CPGOS03-0490) do not support multibyte +- * reads from the EEPROM, so start by reading the base identifying +- * information one byte at a time. ++ /* Some SFP modules and also some Linux I2C drivers do not like reads ++ * longer than 16 bytes, so read the EEPROM in chunks of 16 bytes at ++ * a time. + */ +- sfp->i2c_block_size = 1; ++ sfp->i2c_block_size = 16; + + ret = sfp_read(sfp, false, 0, &id.base, sizeof(id.base)); + if (ret < 0) { +@@ -1627,6 +1637,33 @@ static int sfp_sm_mod_probe(struct sfp * + return -EAGAIN; + } + ++ /* Some SFP modules (e.g. Nokia 3FE46541AA) lock up if read from ++ * address 0x51 is just one byte at a time. Also SFF-8472 requires ++ * that EEPROM supports atomic 16bit read operation for diagnostic ++ * fields, so do not switch to one byte reading at a time unless it ++ * is really required and we have no other option. ++ */ ++ if (sfp_id_needs_byte_io(sfp, &id.base, sizeof(id.base))) { ++ dev_info(sfp->dev, ++ "Detected broken RTL8672/RTL9601C emulated EEPROM\n"); ++ dev_info(sfp->dev, ++ "Switching to reading EEPROM to one byte at a time\n"); ++ sfp->i2c_block_size = 1; ++ ++ ret = sfp_read(sfp, false, 0, &id.base, sizeof(id.base)); ++ if (ret < 0) { ++ if (report) ++ dev_err(sfp->dev, "failed to read EEPROM: %d\n", ++ ret); ++ return -EAGAIN; ++ } ++ ++ if (ret != sizeof(id.base)) { ++ dev_err(sfp->dev, "EEPROM short read: %d\n", ret); ++ return -EAGAIN; ++ } ++ } ++ + /* Cotsworks do not seem to update the checksums when they + * do the final programming with the final module part number, + * serial number and date code. +@@ -1650,9 +1687,6 @@ static int sfp_sm_mod_probe(struct sfp * + } + } + +- /* Apply any early module-specific quirks */ +- sfp_quirks_base(sfp, &id.base); +- + ret = sfp_read(sfp, false, SFP_CC_BASE + 1, &id.ext, sizeof(id.ext)); + if (ret < 0) { + if (report) diff --git a/target/linux/generic/pending-5.4/739-net-avoid-tx-fault-with-Nokia-GPON-module.patch b/target/linux/generic/pending-5.4/739-net-avoid-tx-fault-with-Nokia-GPON-module.patch index 627d33e2ea..6648d10c81 100644 --- a/target/linux/generic/pending-5.4/739-net-avoid-tx-fault-with-Nokia-GPON-module.patch +++ b/target/linux/generic/pending-5.4/739-net-avoid-tx-fault-with-Nokia-GPON-module.patch @@ -39,7 +39,7 @@ Signed-off-by: Russell King /* SFP module presence detection is poor: the three MOD DEF signals are * the same length on the PCB, which means it's possible for MOD DEF 0 to -@@ -218,6 +228,7 @@ struct sfp { +@@ -219,6 +229,7 @@ struct sfp { struct sfp_eeprom_id id; unsigned int module_power_mW; @@ -47,7 +47,7 @@ Signed-off-by: Russell King #if IS_ENABLED(CONFIG_HWMON) struct sfp_diag diag; -@@ -1655,6 +1666,12 @@ static int sfp_sm_mod_probe(struct sfp * +@@ -1742,6 +1753,12 @@ static int sfp_sm_mod_probe(struct sfp * if (ret < 0) return ret; @@ -60,7 +60,7 @@ Signed-off-by: Russell King return 0; } -@@ -1860,11 +1877,12 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -1947,11 +1964,12 @@ static void sfp_sm_main(struct sfp *sfp, break; if (sfp->state & SFP_F_TX_FAULT) { @@ -77,7 +77,7 @@ Signed-off-by: Russell King if (timeout > T_WAIT) timeout -= T_WAIT; else -@@ -1881,8 +1899,8 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -1968,8 +1986,8 @@ static void sfp_sm_main(struct sfp *sfp, case SFP_S_INIT: if (event == SFP_E_TIMEOUT && sfp->state & SFP_F_TX_FAULT) { @@ -88,7 +88,7 @@ Signed-off-by: Russell King */ sfp_sm_fault(sfp, SFP_S_INIT_TX_FAULT, sfp->sm_retries == 5); -@@ -1901,7 +1919,7 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -1988,7 +2006,7 @@ static void sfp_sm_main(struct sfp *sfp, case SFP_S_INIT_TX_FAULT: if (event == SFP_E_TIMEOUT) { sfp_module_tx_fault_reset(sfp); @@ -97,7 +97,7 @@ Signed-off-by: Russell King } break; -@@ -1925,7 +1943,7 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -2012,7 +2030,7 @@ static void sfp_sm_main(struct sfp *sfp, case SFP_S_TX_FAULT: if (event == SFP_E_TIMEOUT) { sfp_module_tx_fault_reset(sfp); diff --git a/target/linux/generic/pending-5.4/740-net-sfp-remove-incomplete-100BASE-FX-and-100BASE-LX-.patch b/target/linux/generic/pending-5.4/740-net-sfp-remove-incomplete-100BASE-FX-and-100BASE-LX-.patch index 4de6305827..1abc34e94b 100644 --- a/target/linux/generic/pending-5.4/740-net-sfp-remove-incomplete-100BASE-FX-and-100BASE-LX-.patch +++ b/target/linux/generic/pending-5.4/740-net-sfp-remove-incomplete-100BASE-FX-and-100BASE-LX-.patch @@ -30,7 +30,7 @@ Signed-off-by: Russell King if (phylink_test(link_modes, 1000baseX_Full)) --- a/drivers/net/phy/sfp.c +++ b/drivers/net/phy/sfp.c -@@ -1489,18 +1489,7 @@ static void sfp_sm_fault(struct sfp *sfp +@@ -1505,18 +1505,7 @@ static void sfp_sm_fault(struct sfp *sfp static void sfp_sm_probe_for_phy(struct sfp *sfp) { diff --git a/target/linux/generic/pending-5.4/742-net-sfp-add-more-extended-compliance-codes.patch b/target/linux/generic/pending-5.4/742-net-sfp-add-more-extended-compliance-codes.patch index 0ddca287b9..868e14520b 100644 --- a/target/linux/generic/pending-5.4/742-net-sfp-add-more-extended-compliance-codes.patch +++ b/target/linux/generic/pending-5.4/742-net-sfp-add-more-extended-compliance-codes.patch @@ -132,7 +132,7 @@ Signed-off-by: Russell King if (phylink_test(link_modes, 2500baseX_Full)) --- a/drivers/net/phy/sfp.c +++ b/drivers/net/phy/sfp.c -@@ -242,7 +242,7 @@ struct sfp { +@@ -243,7 +243,7 @@ struct sfp { static bool sff_module_supported(const struct sfp_eeprom_id *id) { @@ -141,7 +141,7 @@ Signed-off-by: Russell King id->base.phys_ext_id == SFP_PHYS_EXT_ID_SFP; } -@@ -253,7 +253,7 @@ static const struct sff_data sff_data = +@@ -254,7 +254,7 @@ static const struct sff_data sff_data = static bool sfp_module_supported(const struct sfp_eeprom_id *id) { diff --git a/target/linux/generic/pending-5.4/743-net-sfp-add-module-start-stop-upstream-notifications.patch b/target/linux/generic/pending-5.4/743-net-sfp-add-module-start-stop-upstream-notifications.patch index 44de1b2a32..3dc8f60020 100644 --- a/target/linux/generic/pending-5.4/743-net-sfp-add-module-start-stop-upstream-notifications.patch +++ b/target/linux/generic/pending-5.4/743-net-sfp-add-module-start-stop-upstream-notifications.patch @@ -78,7 +78,7 @@ Signed-off-by: Russell King [SFP_S_WAIT] = "wait", [SFP_S_INIT] = "init", [SFP_S_INIT_TX_FAULT] = "init_tx_fault", -@@ -1831,6 +1833,8 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -1918,6 +1920,8 @@ static void sfp_sm_main(struct sfp *sfp, if (sfp->sm_state == SFP_S_LINK_UP && sfp->sm_dev_state == SFP_DEV_UP) sfp_sm_link_down(sfp); @@ -87,7 +87,7 @@ Signed-off-by: Russell King if (sfp->mod_phy) sfp_sm_phy_detach(sfp); sfp_module_tx_disable(sfp); -@@ -1898,6 +1902,10 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -1985,6 +1989,10 @@ static void sfp_sm_main(struct sfp *sfp, * clear. Probe for the PHY and check the LOS state. */ sfp_sm_probe_for_phy(sfp); diff --git a/target/linux/generic/pending-5.4/744-net-sfp-move-phy_start-phy_stop-to-phylink.patch b/target/linux/generic/pending-5.4/744-net-sfp-move-phy_start-phy_stop-to-phylink.patch index e88a81df2d..98987d5a49 100644 --- a/target/linux/generic/pending-5.4/744-net-sfp-move-phy_start-phy_stop-to-phylink.patch +++ b/target/linux/generic/pending-5.4/744-net-sfp-move-phy_start-phy_stop-to-phylink.patch @@ -54,7 +54,7 @@ Signed-off-by: Russell King .connect_phy = phylink_sfp_connect_phy, --- a/drivers/net/phy/sfp.c +++ b/drivers/net/phy/sfp.c -@@ -1396,7 +1396,6 @@ static void sfp_sm_mod_next(struct sfp * +@@ -1412,7 +1412,6 @@ static void sfp_sm_mod_next(struct sfp * static void sfp_sm_phy_detach(struct sfp *sfp) { @@ -62,7 +62,7 @@ Signed-off-by: Russell King sfp_remove_phy(sfp->sfp_bus); phy_device_remove(sfp->mod_phy); phy_device_free(sfp->mod_phy); -@@ -1427,7 +1426,6 @@ static void sfp_sm_probe_phy(struct sfp +@@ -1443,7 +1442,6 @@ static void sfp_sm_probe_phy(struct sfp } sfp->mod_phy = phy; diff --git a/target/linux/generic/pending-5.4/753-net-sfp-add-support-for-Clause-45-PHYs.patch b/target/linux/generic/pending-5.4/753-net-sfp-add-support-for-Clause-45-PHYs.patch index 338ddc3761..dcd1ba7ef3 100644 --- a/target/linux/generic/pending-5.4/753-net-sfp-add-support-for-Clause-45-PHYs.patch +++ b/target/linux/generic/pending-5.4/753-net-sfp-add-support-for-Clause-45-PHYs.patch @@ -14,7 +14,7 @@ Signed-off-by: Russell King --- a/drivers/net/phy/sfp.c +++ b/drivers/net/phy/sfp.c -@@ -1402,12 +1402,12 @@ static void sfp_sm_phy_detach(struct sfp +@@ -1418,12 +1418,12 @@ static void sfp_sm_phy_detach(struct sfp sfp->mod_phy = NULL; } @@ -29,7 +29,7 @@ Signed-off-by: Russell King if (phy == ERR_PTR(-ENODEV)) { dev_info(sfp->dev, "no PHY detected\n"); return; -@@ -1417,6 +1417,13 @@ static void sfp_sm_probe_phy(struct sfp +@@ -1433,6 +1433,13 @@ static void sfp_sm_probe_phy(struct sfp return; } @@ -43,7 +43,7 @@ Signed-off-by: Russell King err = sfp_add_phy(sfp->sfp_bus, phy); if (err) { phy_device_remove(phy); -@@ -1487,10 +1494,32 @@ static void sfp_sm_fault(struct sfp *sfp +@@ -1503,10 +1510,32 @@ static void sfp_sm_fault(struct sfp *sfp } } @@ -78,7 +78,7 @@ Signed-off-by: Russell King } static int sfp_module_parse_power(struct sfp *sfp) -@@ -1550,6 +1579,13 @@ static int sfp_sm_mod_hpower(struct sfp +@@ -1566,6 +1595,13 @@ static int sfp_sm_mod_hpower(struct sfp return -EAGAIN; } diff --git a/target/linux/generic/pending-5.4/754-net-sfp-fix-unbind.patch b/target/linux/generic/pending-5.4/754-net-sfp-fix-unbind.patch index 8d98a5d7a1..c31922e021 100644 --- a/target/linux/generic/pending-5.4/754-net-sfp-fix-unbind.patch +++ b/target/linux/generic/pending-5.4/754-net-sfp-fix-unbind.patch @@ -15,7 +15,7 @@ Signed-off-by: Russell King --- a/drivers/net/phy/sfp.c +++ b/drivers/net/phy/sfp.c -@@ -2344,6 +2344,10 @@ static int sfp_remove(struct platform_de +@@ -2431,6 +2431,10 @@ static int sfp_remove(struct platform_de sfp_unregister_socket(sfp->sfp_bus); diff --git a/target/linux/generic/pending-5.4/755-net-sfp-fix-hwmon.patch b/target/linux/generic/pending-5.4/755-net-sfp-fix-hwmon.patch index 8bfe37bf4c..a18e4801a2 100644 --- a/target/linux/generic/pending-5.4/755-net-sfp-fix-hwmon.patch +++ b/target/linux/generic/pending-5.4/755-net-sfp-fix-hwmon.patch @@ -15,7 +15,7 @@ Signed-off-by: Russell King --- a/drivers/net/phy/sfp.c +++ b/drivers/net/phy/sfp.c -@@ -1796,6 +1796,10 @@ static void sfp_sm_module(struct sfp *sf +@@ -1883,6 +1883,10 @@ static void sfp_sm_module(struct sfp *sf break; } @@ -26,7 +26,7 @@ Signed-off-by: Russell King sfp_sm_mod_next(sfp, SFP_MOD_WAITDEV, 0); /* fall through */ case SFP_MOD_WAITDEV: -@@ -1845,15 +1849,6 @@ static void sfp_sm_module(struct sfp *sf +@@ -1932,15 +1936,6 @@ static void sfp_sm_module(struct sfp *sf case SFP_MOD_ERROR: break; } diff --git a/target/linux/generic/pending-5.4/756-net-sfp-use-a-definition-for-the-fault-recovery-atte.patch b/target/linux/generic/pending-5.4/756-net-sfp-use-a-definition-for-the-fault-recovery-atte.patch index 47d807813a..ba4f8c40c4 100644 --- a/target/linux/generic/pending-5.4/756-net-sfp-use-a-definition-for-the-fault-recovery-atte.patch +++ b/target/linux/generic/pending-5.4/756-net-sfp-use-a-definition-for-the-fault-recovery-atte.patch @@ -26,7 +26,7 @@ Signed-off-by: Russell King /* SFP module presence detection is poor: the three MOD DEF signals are * the same length on the PCB, which means it's possible for MOD DEF 0 to * connect before the I2C bus on MOD DEF 1/2. -@@ -1885,7 +1893,7 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -1972,7 +1980,7 @@ static void sfp_sm_main(struct sfp *sfp, sfp_module_tx_enable(sfp); /* Initialise the fault clearance retries */ @@ -35,7 +35,7 @@ Signed-off-by: Russell King /* We need to check the TX_FAULT state, which is not defined * while TX_DISABLE is asserted. The earliest we want to do -@@ -1925,7 +1933,7 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -2012,7 +2020,7 @@ static void sfp_sm_main(struct sfp *sfp, * or t_start_up, so assume there is a fault. */ sfp_sm_fault(sfp, SFP_S_INIT_TX_FAULT, @@ -44,7 +44,7 @@ Signed-off-by: Russell King } else if (event == SFP_E_TIMEOUT || event == SFP_E_TX_CLEAR) { init_done: /* TX_FAULT deasserted or we timed out with TX_FAULT * clear. Probe for the PHY and check the LOS state. -@@ -1938,7 +1946,7 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -2025,7 +2033,7 @@ static void sfp_sm_main(struct sfp *sfp, sfp_sm_link_check_los(sfp); /* Reset the fault retry count */ diff --git a/target/linux/generic/pending-5.4/757-net-sfp-rename-sm_retries.patch b/target/linux/generic/pending-5.4/757-net-sfp-rename-sm_retries.patch index 0ca73c9266..13f3b6ccff 100644 --- a/target/linux/generic/pending-5.4/757-net-sfp-rename-sm_retries.patch +++ b/target/linux/generic/pending-5.4/757-net-sfp-rename-sm_retries.patch @@ -13,7 +13,7 @@ Signed-off-by: Russell King --- a/drivers/net/phy/sfp.c +++ b/drivers/net/phy/sfp.c -@@ -234,7 +234,7 @@ struct sfp { +@@ -235,7 +235,7 @@ struct sfp { unsigned char sm_mod_tries; unsigned char sm_dev_state; unsigned short sm_state; @@ -22,7 +22,7 @@ Signed-off-by: Russell King struct sfp_eeprom_id id; unsigned int module_power_mW; -@@ -1490,7 +1490,7 @@ static bool sfp_los_event_inactive(struc +@@ -1506,7 +1506,7 @@ static bool sfp_los_event_inactive(struc static void sfp_sm_fault(struct sfp *sfp, unsigned int next_state, bool warn) { @@ -31,7 +31,7 @@ Signed-off-by: Russell King dev_err(sfp->dev, "module persistently indicates fault, disabling\n"); sfp_sm_next(sfp, SFP_S_TX_DISABLE, 0); -@@ -1893,7 +1893,7 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -1980,7 +1980,7 @@ static void sfp_sm_main(struct sfp *sfp, sfp_module_tx_enable(sfp); /* Initialise the fault clearance retries */ @@ -40,7 +40,7 @@ Signed-off-by: Russell King /* We need to check the TX_FAULT state, which is not defined * while TX_DISABLE is asserted. The earliest we want to do -@@ -1933,7 +1933,7 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -2020,7 +2020,7 @@ static void sfp_sm_main(struct sfp *sfp, * or t_start_up, so assume there is a fault. */ sfp_sm_fault(sfp, SFP_S_INIT_TX_FAULT, @@ -49,7 +49,7 @@ Signed-off-by: Russell King } else if (event == SFP_E_TIMEOUT || event == SFP_E_TX_CLEAR) { init_done: /* TX_FAULT deasserted or we timed out with TX_FAULT * clear. Probe for the PHY and check the LOS state. -@@ -1946,7 +1946,7 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -2033,7 +2033,7 @@ static void sfp_sm_main(struct sfp *sfp, sfp_sm_link_check_los(sfp); /* Reset the fault retry count */ diff --git a/target/linux/generic/pending-5.4/758-net-sfp-error-handling-for-phy-probe.patch b/target/linux/generic/pending-5.4/758-net-sfp-error-handling-for-phy-probe.patch index b0bb905fec..dfa772dc72 100644 --- a/target/linux/generic/pending-5.4/758-net-sfp-error-handling-for-phy-probe.patch +++ b/target/linux/generic/pending-5.4/758-net-sfp-error-handling-for-phy-probe.patch @@ -10,7 +10,7 @@ Signed-off-by: Russell King --- a/drivers/net/phy/sfp.c +++ b/drivers/net/phy/sfp.c -@@ -1410,7 +1410,7 @@ static void sfp_sm_phy_detach(struct sfp +@@ -1426,7 +1426,7 @@ static void sfp_sm_phy_detach(struct sfp sfp->mod_phy = NULL; } @@ -19,7 +19,7 @@ Signed-off-by: Russell King { struct phy_device *phy; int err; -@@ -1418,18 +1418,18 @@ static void sfp_sm_probe_phy(struct sfp +@@ -1434,18 +1434,18 @@ static void sfp_sm_probe_phy(struct sfp phy = get_phy_device(sfp->i2c_mii, SFP_PHY_ADDR, is_c45); if (phy == ERR_PTR(-ENODEV)) { dev_info(sfp->dev, "no PHY detected\n"); @@ -41,7 +41,7 @@ Signed-off-by: Russell King } err = sfp_add_phy(sfp->sfp_bus, phy); -@@ -1437,10 +1437,12 @@ static void sfp_sm_probe_phy(struct sfp +@@ -1453,10 +1453,12 @@ static void sfp_sm_probe_phy(struct sfp phy_device_remove(phy); phy_device_free(phy); dev_err(sfp->dev, "sfp_add_phy failed: %d\n", err); @@ -55,7 +55,7 @@ Signed-off-by: Russell King } static void sfp_sm_link_up(struct sfp *sfp) -@@ -1513,21 +1515,24 @@ static void sfp_sm_fault(struct sfp *sfp +@@ -1529,21 +1531,24 @@ static void sfp_sm_fault(struct sfp *sfp * Clause 45 copper SFP+ modules (10G) appear to switch their interface * mode according to the negotiated line speed. */ @@ -83,7 +83,7 @@ Signed-off-by: Russell King } static int sfp_module_parse_power(struct sfp *sfp) -@@ -1938,7 +1943,10 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -2025,7 +2030,10 @@ static void sfp_sm_main(struct sfp *sfp, init_done: /* TX_FAULT deasserted or we timed out with TX_FAULT * clear. Probe for the PHY and check the LOS state. */ diff --git a/target/linux/generic/pending-5.4/759-net-sfp-re-attempt-probing-for-phy.patch b/target/linux/generic/pending-5.4/759-net-sfp-re-attempt-probing-for-phy.patch index d122bc7c62..aebb6b0398 100644 --- a/target/linux/generic/pending-5.4/759-net-sfp-re-attempt-probing-for-phy.patch +++ b/target/linux/generic/pending-5.4/759-net-sfp-re-attempt-probing-for-phy.patch @@ -48,7 +48,7 @@ Signed-off-by: Russell King /* SFP module presence detection is poor: the three MOD DEF signals are * the same length on the PCB, which means it's possible for MOD DEF 0 to * connect before the I2C bus on MOD DEF 1/2. -@@ -235,6 +243,7 @@ struct sfp { +@@ -236,6 +244,7 @@ struct sfp { unsigned char sm_dev_state; unsigned short sm_state; unsigned char sm_fault_retries; @@ -56,7 +56,7 @@ Signed-off-by: Russell King struct sfp_eeprom_id id; unsigned int module_power_mW; -@@ -1416,10 +1425,8 @@ static int sfp_sm_probe_phy(struct sfp * +@@ -1432,10 +1441,8 @@ static int sfp_sm_probe_phy(struct sfp * int err; phy = get_phy_device(sfp->i2c_mii, SFP_PHY_ADDR, is_c45); @@ -69,7 +69,7 @@ Signed-off-by: Russell King if (IS_ERR(phy)) { dev_err(sfp->dev, "mdiobus scan returned %ld\n", PTR_ERR(phy)); return PTR_ERR(phy); -@@ -1867,6 +1874,7 @@ static void sfp_sm_module(struct sfp *sf +@@ -1954,6 +1961,7 @@ static void sfp_sm_module(struct sfp *sf static void sfp_sm_main(struct sfp *sfp, unsigned int event) { unsigned long timeout; @@ -77,7 +77,7 @@ Signed-off-by: Russell King /* Some events are global */ if (sfp->sm_state != SFP_S_DOWN && -@@ -1940,22 +1948,39 @@ static void sfp_sm_main(struct sfp *sfp, +@@ -2027,22 +2035,39 @@ static void sfp_sm_main(struct sfp *sfp, sfp_sm_fault(sfp, SFP_S_INIT_TX_FAULT, sfp->sm_fault_retries == N_FAULT_INIT); } else if (event == SFP_E_TIMEOUT || event == SFP_E_TX_CLEAR) {