From 1d7c1a41987ae463700224c08a3629e4086a8f39 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Tue, 23 Nov 2021 10:14:22 +0100 Subject: [PATCH 01/22] bcm53xx: use new USB 2.0 PHY binding MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This fixes: [ 10.440495] bcm_ns_usb2 1800c000.usb2-phy: can't request region for resource [mem 0x1800c000-0x1800cfff] [ 10.450039] bcm_ns_usb2 1800c000.usb2-phy: Failed to map DMU regs [ 10.456183] bcm_ns_usb2: probe of 1800c000.usb2-phy failed with error -16 caused by conflict in allocating resources. Fixes: f55f1dbaad33 ("bcm53xx: switch to the kernel 5.10") Signed-off-by: Rafał Miłecki --- ...support-updated-DT-binding-with-PHY-.patch | 131 ++++++++++++++++++ ...-use-non-deprecated-USB-2.0-PHY-bind.patch | 52 +++++++ 2 files changed, 183 insertions(+) create mode 100644 target/linux/bcm53xx/patches-5.10/070-v5.17-phy-bcm-ns-usb2-support-updated-DT-binding-with-PHY-.patch create mode 100644 target/linux/bcm53xx/patches-5.10/130-ARM-dts-BCM5301X-use-non-deprecated-USB-2.0-PHY-bind.patch diff --git a/target/linux/bcm53xx/patches-5.10/070-v5.17-phy-bcm-ns-usb2-support-updated-DT-binding-with-PHY-.patch b/target/linux/bcm53xx/patches-5.10/070-v5.17-phy-bcm-ns-usb2-support-updated-DT-binding-with-PHY-.patch new file mode 100644 index 0000000000..464849bc69 --- /dev/null +++ b/target/linux/bcm53xx/patches-5.10/070-v5.17-phy-bcm-ns-usb2-support-updated-DT-binding-with-PHY-.patch @@ -0,0 +1,131 @@ +From d3bc6269e21fc474763708e79c7a118740befb94 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= +Date: Tue, 26 Oct 2021 11:37:16 +0200 +Subject: [PATCH] phy: bcm-ns-usb2: support updated DT binding with PHY reg + space +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +Updated DT binding maps just a PHY's register space instead of the whole +DMU block. Accessing a common CRU reg is handled using syscon & +regmap. + +The old binding has been deprecated and remains supported as a fallback +method. + +Signed-off-by: Rafał Miłecki +Link: https://lore.kernel.org/r/20211026093716.5567-1-zajec5@gmail.com +Signed-off-by: Vinod Koul +--- + drivers/phy/broadcom/phy-bcm-ns-usb2.c | 52 +++++++++++++++++++++----- + 1 file changed, 43 insertions(+), 9 deletions(-) + +--- a/drivers/phy/broadcom/phy-bcm-ns-usb2.c ++++ b/drivers/phy/broadcom/phy-bcm-ns-usb2.c +@@ -9,17 +9,23 @@ + #include + #include + #include ++#include + #include + #include + #include + #include + #include ++#include + #include + + struct bcm_ns_usb2 { + struct device *dev; + struct clk *ref_clk; + struct phy *phy; ++ struct regmap *clkset; ++ void __iomem *base; ++ ++ /* Deprecated binding */ + void __iomem *dmu; + }; + +@@ -27,7 +33,6 @@ static int bcm_ns_usb2_phy_init(struct p + { + struct bcm_ns_usb2 *usb2 = phy_get_drvdata(phy); + struct device *dev = usb2->dev; +- void __iomem *dmu = usb2->dmu; + u32 ref_clk_rate, usb2ctl, usb_pll_ndiv, usb_pll_pdiv; + int err = 0; + +@@ -44,7 +49,10 @@ static int bcm_ns_usb2_phy_init(struct p + goto err_clk_off; + } + +- usb2ctl = readl(dmu + BCMA_DMU_CRU_USB2_CONTROL); ++ if (usb2->base) ++ usb2ctl = readl(usb2->base); ++ else ++ usb2ctl = readl(usb2->dmu + BCMA_DMU_CRU_USB2_CONTROL); + + if (usb2ctl & BCMA_DMU_CRU_USB2_CONTROL_USB_PLL_PDIV_MASK) { + usb_pll_pdiv = usb2ctl; +@@ -58,15 +66,24 @@ static int bcm_ns_usb2_phy_init(struct p + usb_pll_ndiv = (1920000000 * usb_pll_pdiv) / ref_clk_rate; + + /* Unlock DMU PLL settings with some magic value */ +- writel(0x0000ea68, dmu + BCMA_DMU_CRU_CLKSET_KEY); ++ if (usb2->clkset) ++ regmap_write(usb2->clkset, 0, 0x0000ea68); ++ else ++ writel(0x0000ea68, usb2->dmu + BCMA_DMU_CRU_CLKSET_KEY); + + /* Write USB 2.0 PLL control setting */ + usb2ctl &= ~BCMA_DMU_CRU_USB2_CONTROL_USB_PLL_NDIV_MASK; + usb2ctl |= usb_pll_ndiv << BCMA_DMU_CRU_USB2_CONTROL_USB_PLL_NDIV_SHIFT; +- writel(usb2ctl, dmu + BCMA_DMU_CRU_USB2_CONTROL); ++ if (usb2->base) ++ writel(usb2ctl, usb2->base); ++ else ++ writel(usb2ctl, usb2->dmu + BCMA_DMU_CRU_USB2_CONTROL); + + /* Lock DMU PLL settings */ +- writel(0x00000000, dmu + BCMA_DMU_CRU_CLKSET_KEY); ++ if (usb2->clkset) ++ regmap_write(usb2->clkset, 0, 0x00000000); ++ else ++ writel(0x00000000, usb2->dmu + BCMA_DMU_CRU_CLKSET_KEY); + + err_clk_off: + clk_disable_unprepare(usb2->ref_clk); +@@ -91,11 +108,28 @@ static int bcm_ns_usb2_probe(struct plat + return -ENOMEM; + usb2->dev = dev; + +- res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "dmu"); +- usb2->dmu = devm_ioremap_resource(dev, res); +- if (IS_ERR(usb2->dmu)) { +- dev_err(dev, "Failed to map DMU regs\n"); +- return PTR_ERR(usb2->dmu); ++ if (of_find_property(dev->of_node, "brcm,syscon-clkset", NULL)) { ++ usb2->base = devm_platform_ioremap_resource(pdev, 0); ++ if (IS_ERR(usb2->base)) { ++ dev_err(dev, "Failed to map control reg\n"); ++ return PTR_ERR(usb2->base); ++ } ++ ++ usb2->clkset = syscon_regmap_lookup_by_phandle(dev->of_node, ++ "brcm,syscon-clkset"); ++ if (IS_ERR(usb2->clkset)) { ++ dev_err(dev, "Failed to lookup clkset regmap\n"); ++ return PTR_ERR(usb2->clkset); ++ } ++ } else { ++ res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "dmu"); ++ usb2->dmu = devm_ioremap_resource(dev, res); ++ if (IS_ERR(usb2->dmu)) { ++ dev_err(dev, "Failed to map DMU regs\n"); ++ return PTR_ERR(usb2->dmu); ++ } ++ ++ dev_warn(dev, "using deprecated DT binding\n"); + } + + usb2->ref_clk = devm_clk_get(dev, "phy-ref-clk"); diff --git a/target/linux/bcm53xx/patches-5.10/130-ARM-dts-BCM5301X-use-non-deprecated-USB-2.0-PHY-bind.patch b/target/linux/bcm53xx/patches-5.10/130-ARM-dts-BCM5301X-use-non-deprecated-USB-2.0-PHY-bind.patch new file mode 100644 index 0000000000..e50bcd9f25 --- /dev/null +++ b/target/linux/bcm53xx/patches-5.10/130-ARM-dts-BCM5301X-use-non-deprecated-USB-2.0-PHY-bind.patch @@ -0,0 +1,52 @@ +From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= +Date: Tue, 23 Nov 2021 09:55:06 +0100 +Subject: [PATCH] ARM: dts: BCM5301X: use non-deprecated USB 2.0 PHY binding +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +The new binding covers a single reg and uses syscon to reference shared +register. + +References: 55b9b741712d ("dt-bindings: phy: brcm,ns-usb2-phy: bind just a PHY block") +Signed-off-by: Rafał Miłecki +--- + arch/arm/boot/dts/bcm5301x.dtsi | 20 ++++++++++---------- + 1 file changed, 10 insertions(+), 10 deletions(-) + +--- a/arch/arm/boot/dts/bcm5301x.dtsi ++++ b/arch/arm/boot/dts/bcm5301x.dtsi +@@ -148,15 +148,6 @@ + }; + }; + +- usb2_phy: usb2-phy@1800c000 { +- compatible = "brcm,ns-usb2-phy"; +- reg = <0x1800c000 0x1000>; +- reg-names = "dmu"; +- #phy-cells = <0>; +- clocks = <&genpll BCM_NSP_GENPLL_USB_PHY_REF_CLK>; +- clock-names = "phy-ref-clk"; +- }; +- + axi@18000000 { + compatible = "brcm,bus-axi"; + reg = <0x18000000 0x1000>; +@@ -450,7 +441,16 @@ + "sata1", "sata2"; + }; + +- syscon@180 { ++ usb2_phy: phy@164 { ++ compatible = "brcm,ns-usb2-phy"; ++ reg = <0x164 0x4>; ++ brcm,syscon-clkset = <&cru_clkset>; ++ clocks = <&genpll BCM_NSP_GENPLL_USB_PHY_REF_CLK>; ++ clock-names = "phy-ref-clk"; ++ #phy-cells = <0>; ++ }; ++ ++ cru_clkset: syscon@180 { + compatible = "brcm,cru-clkset", "syscon"; + reg = <0x180 0x4>; + }; From 824ac6e11c843828140201cfba6ce0e12424916a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= Date: Tue, 23 Nov 2021 13:45:36 +0100 Subject: [PATCH 02/22] bcm53xx: fix platform clocks & USB 2.0 PHY MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This fixes WARNing, missing clocks and [ 10.422481] bcm_ns_usb2 1800c164.usb2-phy: Clock not defined Fixes: 5901917b936d ("bcm53xx: use more upsteam DT patches from 5.16 / 5.17") Signed-off-by: Rafał Miłecki --- ...-Switch-back-to-old-clock-nodes-name.patch | 62 +++++++++++++++++++ 1 file changed, 62 insertions(+) create mode 100644 target/linux/bcm53xx/patches-5.10/320-ARM-dts-BCM5301X-Switch-back-to-old-clock-nodes-name.patch diff --git a/target/linux/bcm53xx/patches-5.10/320-ARM-dts-BCM5301X-Switch-back-to-old-clock-nodes-name.patch b/target/linux/bcm53xx/patches-5.10/320-ARM-dts-BCM5301X-Switch-back-to-old-clock-nodes-name.patch new file mode 100644 index 0000000000..cee37732ab --- /dev/null +++ b/target/linux/bcm53xx/patches-5.10/320-ARM-dts-BCM5301X-Switch-back-to-old-clock-nodes-name.patch @@ -0,0 +1,62 @@ +From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= +Date: Tue, 23 Nov 2021 13:13:05 +0100 +Subject: [PATCH] ARM: dts: BCM5301X: Switch back to old clock nodes names +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +First of all using the same node name prefix resulted in trying to +register 2 clocks under the same "clock-controller" name: + +[ 0.000000] __clk_core_init: clk clock-controller already initialized +[ 0.000000] ------------[ cut here ]------------ +[ 0.000000] WARNING: CPU: 0 PID: 0 at drivers/clk/bcm/clk-iproc-pll.c:802 iproc_pll_clk_setup+0x4c8/0x4f4 +[ 0.000000] Modules linked in: +[ 0.000000] CPU: 0 PID: 0 Comm: swapper/0 Not tainted 5.10.80 #0 +[ 0.000000] Hardware name: BCM5301X +[ 0.000000] [] (unwind_backtrace) from [] (show_stack+0x10/0x14) +[ 0.000000] [] (show_stack) from [] (dump_stack+0x94/0xa8) +[ 0.000000] [] (dump_stack) from [] (__warn+0xb8/0x114) +[ 0.000000] [] (__warn) from [] (warn_slowpath_fmt+0x68/0x78) +[ 0.000000] [] (warn_slowpath_fmt) from [] (iproc_pll_clk_setup+0x4c8/0x4f4) +[ 0.000000] [] (iproc_pll_clk_setup) from [] (nsp_genpll_clk_init+0x30/0x38) +[ 0.000000] [] (nsp_genpll_clk_init) from [] (of_clk_init+0x118/0x1f8) +[ 0.000000] [] (of_clk_init) from [] (time_init+0x24/0x30) +[ 0.000000] [] (time_init) from [] (start_kernel+0x398/0x50c) +[ 0.000000] [] (start_kernel) from [<00000000>] (0x0) +[ 0.000000] ---[ end trace fe236bfe9559ee50 ]--- + +Secondly using any other names than "lcpll0" and "genpll" breaks output +clocks: + +$ cat /sys/kernel/debug/clk/usbclk/clk_rate +0 + +For some reason iproc_clk_recalc_rate() gets called with "parent_rate" +argument 0 whenever clocks aren't named "lcpll0" and "genpll". + +Signed-off-by: Rafał Miłecki +--- + arch/arm/boot/dts/bcm5301x.dtsi | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +--- a/arch/arm/boot/dts/bcm5301x.dtsi ++++ b/arch/arm/boot/dts/bcm5301x.dtsi +@@ -421,7 +421,7 @@ + #address-cells = <1>; + #size-cells = <1>; + +- lcpll0: clock-controller@100 { ++ lcpll0: lcpll0@100 { + #clock-cells = <1>; + compatible = "brcm,nsp-lcpll0"; + reg = <0x100 0x14>; +@@ -430,7 +430,7 @@ + "sdio", "ddr_phy"; + }; + +- genpll: clock-controller@140 { ++ genpll: genpll@140 { + #clock-cells = <1>; + compatible = "brcm,nsp-genpll"; + reg = <0x140 0x24>; From 507f50df0771935ee389d383c0543e36f914f949 Mon Sep 17 00:00:00 2001 From: Daniel Golle Date: Tue, 23 Nov 2021 14:00:42 +0000 Subject: [PATCH 03/22] procd: update to git HEAD 8de12de system: add diskfree infos to ubus bf3fe0e service: move jail parsing to end of instance parser 87b5836 procd: add full service shutdown prior to sysupgrade 01ac2c4 procd: service_stop_all: also kill inittab actions Signed-off-by: Daniel Golle --- package/system/procd/Makefile | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/package/system/procd/Makefile b/package/system/procd/Makefile index f87572aef9..228eecfebc 100644 --- a/package/system/procd/Makefile +++ b/package/system/procd/Makefile @@ -12,9 +12,9 @@ PKG_RELEASE:=$(AUTORELEASE) PKG_SOURCE_PROTO:=git PKG_SOURCE_URL=$(PROJECT_GIT)/project/procd.git -PKG_MIRROR_HASH:=0ff42d965b6c07fe9d1731395623b78967b83bbeb85deda900dd430a2883643f -PKG_SOURCE_DATE:=2021-11-11 -PKG_SOURCE_VERSION:=9d1431e1309e1acee06c016acc08cb7650b1d0af +PKG_MIRROR_HASH:=39f24aa076a61a3d570f4e5f7a3f38eb6b6e3b96a967c8be7f0dc3e3ffaeed1a +PKG_SOURCE_DATE:=2021-11-23 +PKG_SOURCE_VERSION:=01ac2c4500cb0c7934640e6d2e5f99b08483bdf4 CMAKE_INSTALL:=1 PKG_LICENSE:=GPL-2.0 From 50bc06e774f89517f98c89c76a7626f35c3ff659 Mon Sep 17 00:00:00 2001 From: Jo-Philipp Wich Date: Thu, 18 Nov 2021 13:00:09 +0100 Subject: [PATCH 04/22] procd: setup /dev/stdin, /dev/stdout and /dev/stderr symlinks Extend the hotplug.json ruleset to setup the common /dev/std{in,out,err} symbolic links which are needed by some applications, e.g. nftables when applying rulesets from stdin. Signed-off-by: Jo-Philipp Wich --- package/system/procd/files/hotplug.json | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/package/system/procd/files/hotplug.json b/package/system/procd/files/hotplug.json index 7e0f129d35..b930b307a4 100644 --- a/package/system/procd/files/hotplug.json +++ b/package/system/procd/files/hotplug.json @@ -7,9 +7,19 @@ [ "has", "MINOR" ] ], [ + [ "if", + [ "eq", "DEVNAME", "null" ], + [ + [ "makedev", "/dev/%DEVNAME%", "0666" ], + [ "exec", "/bin/ln", "-s", "/proc/self/fd/0", "/dev/stdin" ], + [ "exec", "/bin/ln", "-s", "/proc/self/fd/1", "/dev/stdout" ], + [ "exec", "/bin/ln", "-s", "/proc/self/fd/2", "/dev/stderr" ], + [ "return" ] + ] + ], [ "if", [ "eq", "DEVNAME", - [ "null", "full", "ptmx", "zero", "tty", "net", "random", "urandom" ] + [ "full", "ptmx", "zero", "tty", "net", "random", "urandom" ] ], [ [ "makedev", "/dev/%DEVNAME%", "0666" ], From 1818157daa538a97bb128d40750bfba6c98d3abe Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Old=C5=99ich=20Jedli=C4=8Dka?= Date: Sun, 7 Nov 2021 21:56:12 +0100 Subject: [PATCH 05/22] dnsmasq: fix ismounted check MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fix the return value, shell return codes should be 0 to indicate success (i.e. mount point found), 1 should be failure (i.e. mount point not-found). Fixes: ac4e8aa ("dnsmasq: fix more dnsmasq jail issues") Signed-off-by: Oldřich Jedlička --- package/network/services/dnsmasq/files/dnsmasq.init | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/package/network/services/dnsmasq/files/dnsmasq.init b/package/network/services/dnsmasq/files/dnsmasq.init index 1e53f8f2c1..09dce0a78d 100755 --- a/package/network/services/dnsmasq/files/dnsmasq.init +++ b/package/network/services/dnsmasq/files/dnsmasq.init @@ -197,12 +197,12 @@ ismounted() { for dirname in $EXTRA_MOUNT ; do case "$filename" in "${dirname}/"* | "${dirname}" ) - return 1 + return 0 ;; esac done - return 0 + return 1 } append_addnhosts() { From d1ea575baa1b53bb477a020974afcec1b1193edc Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Tue, 23 Nov 2021 13:18:03 +0100 Subject: [PATCH 06/22] mac80211: fix crash in drivers relying on mac80211 retransmitting packets for powersave clients This showed up primarily on rt2x00 Signed-off-by: Felix Fietkau --- ...ate-control-for-retransmitted-frames.patch | 35 +++++++++++++++++++ 1 file changed, 35 insertions(+) create mode 100644 package/kernel/mac80211/patches/subsys/301-mac80211-fix-rate-control-for-retransmitted-frames.patch diff --git a/package/kernel/mac80211/patches/subsys/301-mac80211-fix-rate-control-for-retransmitted-frames.patch b/package/kernel/mac80211/patches/subsys/301-mac80211-fix-rate-control-for-retransmitted-frames.patch new file mode 100644 index 0000000000..42f7d6bfe7 --- /dev/null +++ b/package/kernel/mac80211/patches/subsys/301-mac80211-fix-rate-control-for-retransmitted-frames.patch @@ -0,0 +1,35 @@ +From: Felix Fietkau +Date: Mon, 22 Nov 2021 21:39:38 +0100 +Subject: [PATCH] mac80211: fix rate control for retransmitted frames + +Since retransmission clears info->control, rate control needs to be called +again, otherwise the driver might crash due to invalid rates. + +Cc: stable@vger.kernel.org # 5.14+ +Reported-by: Aaro Koskinen +Reported-by: Robert W +Fixes: 03c3911d2d67 ("mac80211: call ieee80211_tx_h_rate_ctrl() when dequeue") +Signed-off-by: Felix Fietkau +--- + +--- a/net/mac80211/tx.c ++++ b/net/mac80211/tx.c +@@ -1825,15 +1825,15 @@ static int invoke_tx_handlers_late(struc + struct ieee80211_tx_info *info = IEEE80211_SKB_CB(tx->skb); + ieee80211_tx_result res = TX_CONTINUE; + ++ if (!ieee80211_hw_check(&tx->local->hw, HAS_RATE_CONTROL)) ++ CALL_TXH(ieee80211_tx_h_rate_ctrl); ++ + if (unlikely(info->flags & IEEE80211_TX_INTFL_RETRANSMISSION)) { + __skb_queue_tail(&tx->skbs, tx->skb); + tx->skb = NULL; + goto txh_done; + } + +- if (!ieee80211_hw_check(&tx->local->hw, HAS_RATE_CONTROL)) +- CALL_TXH(ieee80211_tx_h_rate_ctrl); +- + CALL_TXH(ieee80211_tx_h_michael_mic_add); + CALL_TXH(ieee80211_tx_h_sequence); + CALL_TXH(ieee80211_tx_h_fragment); From 5aa62cb7996803fa256a7b9f5beef818a7fe34d8 Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Tue, 23 Nov 2021 16:58:08 +0100 Subject: [PATCH 07/22] mt76: update to the latest version f0a5b1118fa4 mt76: mt7915: fix decap offload corner case with 4-addr VLAN frames 67f93aa9a207 mt76: mt7615: fix decap offload corner case with 4-addr VLAN frames 46261d4bbfb5 mt76: fix possible pktid leak a7fdd272efee mt76: mt7921: move mt76_connac_mcu_set_hif_suspend to bus-related files 3d9e13f567a4 mt76: mt7921s: fix the device cannot sleep deeply in suspend 99225b985cbc mt76: mt7615: fix unused tx antenna mask in testmode Signed-off-by: Felix Fietkau --- package/kernel/mt76/Makefile | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/package/kernel/mt76/Makefile b/package/kernel/mt76/Makefile index a571b49f08..e947f1a2f3 100644 --- a/package/kernel/mt76/Makefile +++ b/package/kernel/mt76/Makefile @@ -8,9 +8,9 @@ PKG_LICENSE_FILES:= PKG_SOURCE_URL:=https://github.com/openwrt/mt76 PKG_SOURCE_PROTO:=git -PKG_SOURCE_DATE:=2021-11-22 -PKG_SOURCE_VERSION:=b1d0ad2e74fe8cad563556bb8781d5d92b24b690 -PKG_MIRROR_HASH:=7507fdc31aa5f3d90bfffa3c7db4957c4ac16df8426e1b017b112e7e6c97735b +PKG_SOURCE_DATE:=2021-11-23 +PKG_SOURCE_VERSION:=99225b985cbcab4707589f1fa313436f4bf1e368 +PKG_MIRROR_HASH:=6444c7d49d778c7621b03f0f201ce41f6dc9ac00dedb29c66478360b4fd60492 PKG_MAINTAINER:=Felix Fietkau PKG_USE_NINJA:=0 From 398cbb76fa88f2d5dcc05b0ecc24ced1bbcad9ca Mon Sep 17 00:00:00 2001 From: Mark Mentovai Date: Tue, 23 Nov 2021 12:28:55 -0500 Subject: [PATCH 08/22] hostapd: allow hostapd under ujail to communicate with hostapd_cli When procd-ujail is available, 1f785383875a runs hostapd as user "network", with only limited additional capabilities (CAP_NET_ADMIN and CAP_NET_RAW). hostapd_cli (CONFIG_PACKAGE_hostapd-utils) communicates with hostapd over a named UNIX-domain socket. hostapd_cli is responsible for creating this socket at /tmp/wpa_ctrl_$pid_$counter. Since it typically runs as root, this endpoint is normally created with uid root, gid root, mode 0755. As a result, hostapd running as uid network is able to receive control messages sent through this interface, but is not able to respond to them. If debug-level logging is enabled (CONFIG_WPA_MSG_MIN_PRIORITY <= 2 at build, and log_level <= 2 in /etc/config/wireless wifi-device), this message will appear from hostapd: CTRL: sendto failed: Permission denied As a fix, hostapd_cli should create the socket node in the filesystem with uid network, gid network, mode 0770. This borrows the presently Android-only strategy already in hostapd intended to solve the same problem on Android. If procd-ujail is not available and hostapd falls back to running as root, it will still be able to read from and write to the socket even if the node in the filesystem has been restricted to the network user and group. This matches the logic in package/network/services/hostapd/files/wpad.init, which sets the uid and gid of /var/run/hostapd to network regardless of whether procd-ujail is available. As it appears that the "network" user and group are statically allocated uid 101 and gid 101, respectively, per package/base-files/files/etc/passwd and USERID in package/network/services/hostapd/Makefile, this patch also uses a constant 101 for the uid and gid. Signed-off-by: Mark Mentovai [refreshed patch] Signed-off-by: Daniel Golle --- .../610-hostapd_cli_ujail_permission.patch | 33 +++++++++++++++++++ 1 file changed, 33 insertions(+) create mode 100644 package/network/services/hostapd/patches/610-hostapd_cli_ujail_permission.patch diff --git a/package/network/services/hostapd/patches/610-hostapd_cli_ujail_permission.patch b/package/network/services/hostapd/patches/610-hostapd_cli_ujail_permission.patch new file mode 100644 index 0000000000..a03fcc9f92 --- /dev/null +++ b/package/network/services/hostapd/patches/610-hostapd_cli_ujail_permission.patch @@ -0,0 +1,33 @@ +--- a/src/common/wpa_ctrl.c ++++ b/src/common/wpa_ctrl.c +@@ -135,7 +135,7 @@ try_again: + return NULL; + } + tries++; +-#ifdef ANDROID ++ + /* Set client socket file permissions so that bind() creates the client + * socket with these permissions and there is no need to try to change + * them with chmod() after bind() which would have potential issues with +@@ -147,7 +147,7 @@ try_again: + * operations to allow the response to go through. Those are using the + * no-deference-symlinks version to avoid races. */ + fchmod(ctrl->s, S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP); +-#endif /* ANDROID */ ++ + if (bind(ctrl->s, (struct sockaddr *) &ctrl->local, + sizeof(ctrl->local)) < 0) { + if (errno == EADDRINUSE && tries < 2) { +@@ -165,7 +165,11 @@ try_again: + return NULL; + } + +-#ifdef ANDROID ++#ifndef ANDROID ++ /* Set group even if we do not have privileges to change owner */ ++ lchown(ctrl->local.sun_path, -1, 101); ++ lchown(ctrl->local.sun_path, 101, 101); ++#else + /* Set group even if we do not have privileges to change owner */ + lchown(ctrl->local.sun_path, -1, AID_WIFI); + lchown(ctrl->local.sun_path, AID_SYSTEM, AID_WIFI); From ddd977fcc5838eb6bfb6cb9dad99dfe09a8ff67e Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Wed, 24 Nov 2021 10:45:28 +0100 Subject: [PATCH 09/22] mac80211: fix regression in SSN handling of addba tx Some drivers that do their own sequence number allocation (e.g. ath9k, mwlwifi) rely on being able to modify params->ssn on starting tx ampdu sessions. This was broken by a change that modified it to use sta->tid_seq[tid] instead. Signed-off-by: Felix Fietkau --- ...gression-in-SSN-handling-of-addba-tx.patch | 44 +++++++++++++++++++ 1 file changed, 44 insertions(+) create mode 100644 package/kernel/mac80211/patches/subsys/305-mac80211-fix-regression-in-SSN-handling-of-addba-tx.patch diff --git a/package/kernel/mac80211/patches/subsys/305-mac80211-fix-regression-in-SSN-handling-of-addba-tx.patch b/package/kernel/mac80211/patches/subsys/305-mac80211-fix-regression-in-SSN-handling-of-addba-tx.patch new file mode 100644 index 0000000000..dc8afb9186 --- /dev/null +++ b/package/kernel/mac80211/patches/subsys/305-mac80211-fix-regression-in-SSN-handling-of-addba-tx.patch @@ -0,0 +1,44 @@ +From: Felix Fietkau +Date: Wed, 24 Nov 2021 10:30:41 +0100 +Subject: [PATCH] mac80211: fix regression in SSN handling of addba tx + +Some drivers that do their own sequence number allocation (e.g. ath9k) rely +on being able to modify params->ssn on starting tx ampdu sessions. +This was broken by a change that modified it to use sta->tid_seq[tid] instead. + +Cc: stable@vger.kernel.org +Fixes: 31d8bb4e07f8 ("mac80211: agg-tx: refactor sending addba") +Reported-by: Eneas U de Queiroz +Signed-off-by: Felix Fietkau +--- + +--- a/net/mac80211/agg-tx.c ++++ b/net/mac80211/agg-tx.c +@@ -480,8 +480,7 @@ static void ieee80211_send_addba_with_ti + + /* send AddBA request */ + ieee80211_send_addba_request(sdata, sta->sta.addr, tid, +- tid_tx->dialog_token, +- sta->tid_seq[tid] >> 4, ++ tid_tx->dialog_token, tid_tx->ssn, + buf_size, tid_tx->timeout); + + WARN_ON(test_and_set_bit(HT_AGG_STATE_SENT_ADDBA, &tid_tx->state)); +@@ -523,6 +522,7 @@ void ieee80211_tx_ba_session_handle_star + + params.ssn = sta->tid_seq[tid] >> 4; + ret = drv_ampdu_action(local, sdata, ¶ms); ++ tid_tx->ssn = params.ssn; + if (ret == IEEE80211_AMPDU_TX_START_DELAY_ADDBA) { + return; + } else if (ret == IEEE80211_AMPDU_TX_START_IMMEDIATE) { +--- a/net/mac80211/sta_info.h ++++ b/net/mac80211/sta_info.h +@@ -199,6 +199,7 @@ struct tid_ampdu_tx { + u8 stop_initiator; + bool tx_stop; + u16 buf_size; ++ u16 ssn; + + u16 failed_bar_ssn; + bool bar_pending; From d439c7d85a05c3548e5566bec292292a4f6b7ef5 Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Wed, 24 Nov 2021 14:02:09 +0100 Subject: [PATCH 10/22] mac80211: add a fix for kernel warnings when forwarding packets in mesh mode Signed-off-by: Felix Fietkau --- ...-the-fwd_skb-dev-for-mesh-forwarding.patch | 62 +++++++++++++++++++ 1 file changed, 62 insertions(+) create mode 100644 package/kernel/mac80211/patches/subsys/306-mac80211-set-up-the-fwd_skb-dev-for-mesh-forwarding.patch diff --git a/package/kernel/mac80211/patches/subsys/306-mac80211-set-up-the-fwd_skb-dev-for-mesh-forwarding.patch b/package/kernel/mac80211/patches/subsys/306-mac80211-set-up-the-fwd_skb-dev-for-mesh-forwarding.patch new file mode 100644 index 0000000000..68fa8a91c2 --- /dev/null +++ b/package/kernel/mac80211/patches/subsys/306-mac80211-set-up-the-fwd_skb-dev-for-mesh-forwarding.patch @@ -0,0 +1,62 @@ +From: Xing Song +Date: Tue, 23 Nov 2021 11:31:23 +0800 +Subject: [PATCH] mac80211: set up the fwd_skb->dev for mesh forwarding + +Mesh forwarding requires that the fwd_skb->dev is set up for TX handling, +otherwise the following warning will be generated, so set it up for the +pending frames. + +[ 72.835674 ] WARNING: CPU: 0 PID: 1193 at __skb_flow_dissect+0x284/0x1298 +[ 72.842379 ] Modules linked in: ksmbd pppoe ppp_async l2tp_ppp ... +[ 72.962020 ] CPU: 0 PID: 1193 Comm: kworker/u5:1 Tainted: P S 5.4.137 #0 +[ 72.969938 ] Hardware name: MT7622_MT7531 RFB (DT) +[ 72.974659 ] Workqueue: napi_workq napi_workfn +[ 72.979025 ] pstate: 60000005 (nZCv daif -PAN -UAO) +[ 72.983822 ] pc : __skb_flow_dissect+0x284/0x1298 +[ 72.988444 ] lr : __skb_flow_dissect+0x54/0x1298 +[ 72.992977 ] sp : ffffffc010c738c0 +[ 72.996293 ] x29: ffffffc010c738c0 x28: 0000000000000000 +[ 73.001615 ] x27: 000000000000ffc2 x26: ffffff800c2eb818 +[ 73.006937 ] x25: ffffffc010a987c8 x24: 00000000000000ce +[ 73.012259 ] x23: ffffffc010c73a28 x22: ffffffc010a99c60 +[ 73.017581 ] x21: 000000000000ffc2 x20: ffffff80094da800 +[ 73.022903 ] x19: 0000000000000000 x18: 0000000000000014 +[ 73.028226 ] x17: 00000000084d16af x16: 00000000d1fc0bab +[ 73.033548 ] x15: 00000000715f6034 x14: 000000009dbdd301 +[ 73.038870 ] x13: 00000000ea4dcbc3 x12: 0000000000000040 +[ 73.044192 ] x11: 000000000eb00ff0 x10: 0000000000000000 +[ 73.049513 ] x9 : 000000000eb00073 x8 : 0000000000000088 +[ 73.054834 ] x7 : 0000000000000000 x6 : 0000000000000001 +[ 73.060155 ] x5 : 0000000000000000 x4 : 0000000000000000 +[ 73.065476 ] x3 : ffffffc010a98000 x2 : 0000000000000000 +[ 73.070797 ] x1 : 0000000000000000 x0 : 0000000000000000 +[ 73.076120 ] Call trace: +[ 73.078572 ] __skb_flow_dissect+0x284/0x1298 +[ 73.082846 ] __skb_get_hash+0x7c/0x228 +[ 73.086629 ] ieee80211_txq_may_transmit+0x7fc/0x17b8 [mac80211] +[ 73.092564 ] ieee80211_tx_prepare_skb+0x20c/0x268 [mac80211] +[ 73.098238 ] ieee80211_tx_pending+0x144/0x330 [mac80211] +[ 73.103560 ] tasklet_action_common.isra.16+0xb4/0x158 +[ 73.108618 ] tasklet_action+0x2c/0x38 +[ 73.112286 ] __do_softirq+0x168/0x3b0 +[ 73.115954 ] do_softirq.part.15+0x88/0x98 +[ 73.119969 ] __local_bh_enable_ip+0xb0/0xb8 +[ 73.124156 ] napi_workfn+0x58/0x90 +[ 73.127565 ] process_one_work+0x20c/0x478 +[ 73.131579 ] worker_thread+0x50/0x4f0 +[ 73.135249 ] kthread+0x124/0x128 +[ 73.138484 ] ret_from_fork+0x10/0x1c + +Signed-off-by: Xing Song +--- + +--- a/net/mac80211/rx.c ++++ b/net/mac80211/rx.c +@@ -2947,6 +2947,7 @@ ieee80211_rx_h_mesh_fwding(struct ieee80 + if (!fwd_skb) + goto out; + ++ fwd_skb->dev = sdata->dev; + fwd_hdr = (struct ieee80211_hdr *) fwd_skb->data; + fwd_hdr->frame_control &= ~cpu_to_le16(IEEE80211_FCTL_RETRY); + info = IEEE80211_SKB_CB(fwd_skb); From f84053af5c0b0a159ea4d3e90b0c06574b4fde8d Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Wed, 24 Nov 2021 17:02:26 +0100 Subject: [PATCH 11/22] hostapd: add a patch that allows processing auth requests for peers in blocked state If authentication fails repeatedly e.g. because of a weak signal, the link can end up in blocked state. If one of the nodes tries to establish a link again before it is unblocked on the other side, it will block the link to that other side. The same happens on the other side when it unblocks the link. In that scenario, the link never recovers on its own. To fix this, allow restarting authentication even if the link is in blocked state, but don't initiate the attempt until the blocked period is over. Signed-off-by: Felix Fietkau --- ...ssing-authentication-frames-in-block.patch | 34 +++++++++++++++++++ .../hostapd/patches/600-ubus_support.patch | 10 +++--- ...750-qos_map_set_without_interworking.patch | 2 +- 3 files changed, 40 insertions(+), 6 deletions(-) create mode 100644 package/network/services/hostapd/patches/040-mesh-allow-processing-authentication-frames-in-block.patch diff --git a/package/network/services/hostapd/patches/040-mesh-allow-processing-authentication-frames-in-block.patch b/package/network/services/hostapd/patches/040-mesh-allow-processing-authentication-frames-in-block.patch new file mode 100644 index 0000000000..6d9fd81acf --- /dev/null +++ b/package/network/services/hostapd/patches/040-mesh-allow-processing-authentication-frames-in-block.patch @@ -0,0 +1,34 @@ +From: Felix Fietkau +Date: Mon, 18 Feb 2019 12:57:11 +0100 +Subject: [PATCH] mesh: allow processing authentication frames in blocked state + +If authentication fails repeatedly e.g. because of a weak signal, the link +can end up in blocked state. If one of the nodes tries to establish a link +again before it is unblocked on the other side, it will block the link to +that other side. The same happens on the other side when it unblocks the +link. In that scenario, the link never recovers on its own. + +To fix this, allow restarting authentication even if the link is in blocked +state, but don't initiate the attempt until the blocked period is over. + +Signed-off-by: Felix Fietkau +--- + +--- a/src/ap/ieee802_11.c ++++ b/src/ap/ieee802_11.c +@@ -3761,15 +3761,6 @@ static void handle_auth(struct hostapd_d + seq_ctrl); + return; + } +-#ifdef CONFIG_MESH +- if ((hapd->conf->mesh & MESH_ENABLED) && +- sta->plink_state == PLINK_BLOCKED) { +- wpa_printf(MSG_DEBUG, "Mesh peer " MACSTR +- " is blocked - drop Authentication frame", +- MAC2STR(mgmt->sa)); +- return; +- } +-#endif /* CONFIG_MESH */ + #ifdef CONFIG_PASN + if (auth_alg == WLAN_AUTH_PASN && + (sta->flags & WLAN_STA_ASSOC)) { diff --git a/package/network/services/hostapd/patches/600-ubus_support.patch b/package/network/services/hostapd/patches/600-ubus_support.patch index b7f156bceb..358c53167a 100644 --- a/package/network/services/hostapd/patches/600-ubus_support.patch +++ b/package/network/services/hostapd/patches/600-ubus_support.patch @@ -126,7 +126,7 @@ if (res == HOSTAPD_ACL_PENDING) return; -@@ -5454,7 +5466,7 @@ static void handle_assoc(struct hostapd_ +@@ -5445,7 +5457,7 @@ static void handle_assoc(struct hostapd_ int resp = WLAN_STATUS_SUCCESS; u16 reply_res = WLAN_STATUS_UNSPECIFIED_FAILURE; const u8 *pos; @@ -135,7 +135,7 @@ struct sta_info *sta; u8 *tmp = NULL; #ifdef CONFIG_FILS -@@ -5667,6 +5679,11 @@ static void handle_assoc(struct hostapd_ +@@ -5658,6 +5670,11 @@ static void handle_assoc(struct hostapd_ left = res; } #endif /* CONFIG_FILS */ @@ -147,7 +147,7 @@ /* followed by SSID and Supported rates; and HT capabilities if 802.11n * is used */ -@@ -5765,6 +5782,13 @@ static void handle_assoc(struct hostapd_ +@@ -5756,6 +5773,13 @@ static void handle_assoc(struct hostapd_ } #endif /* CONFIG_FILS */ @@ -161,7 +161,7 @@ fail: /* -@@ -5858,6 +5882,7 @@ static void handle_disassoc(struct hosta +@@ -5849,6 +5873,7 @@ static void handle_disassoc(struct hosta wpa_printf(MSG_DEBUG, "disassocation: STA=" MACSTR " reason_code=%d", MAC2STR(mgmt->sa), le_to_host16(mgmt->u.disassoc.reason_code)); @@ -169,7 +169,7 @@ sta = ap_get_sta(hapd, mgmt->sa); if (sta == NULL) { -@@ -5927,6 +5952,8 @@ static void handle_deauth(struct hostapd +@@ -5918,6 +5943,8 @@ static void handle_deauth(struct hostapd /* Clear the PTKSA cache entries for PASN */ ptksa_cache_flush(hapd->ptksa, mgmt->sa, WPA_CIPHER_NONE); diff --git a/package/network/services/hostapd/patches/750-qos_map_set_without_interworking.patch b/package/network/services/hostapd/patches/750-qos_map_set_without_interworking.patch index 1e6892e375..a7a221352f 100644 --- a/package/network/services/hostapd/patches/750-qos_map_set_without_interworking.patch +++ b/package/network/services/hostapd/patches/750-qos_map_set_without_interworking.patch @@ -65,7 +65,7 @@ wpabuf_free(sta->hs20_ie); --- a/src/ap/ieee802_11.c +++ b/src/ap/ieee802_11.c -@@ -4136,13 +4136,11 @@ static u16 copy_supp_rates(struct hostap +@@ -4127,13 +4127,11 @@ static u16 copy_supp_rates(struct hostap static u16 check_ext_capab(struct hostapd_data *hapd, struct sta_info *sta, const u8 *ext_capab_ie, size_t ext_capab_ie_len) { From 72ae8314f5315e57caa82eb8c43f2606a7e6694c Mon Sep 17 00:00:00 2001 From: Sander Vanheule Date: Thu, 18 Nov 2021 18:39:18 +0100 Subject: [PATCH 12/22] realtek: reset both ethernet NIC and queues Recent versions of Realtek's SDK reset both the ethernet NIC and queues (SW_NIC_RST and SW_Q_RST bits) when initialising the hardware. Furthermore, when issuing a CPU reset on the Zyxel GS1900-8 (not supported by any current driver), the networking part of the SoC is not reset. This leads to unresponsive network after the restart. By resetting both the ethernet NIC and queues, networking always comes up reliably. Suggested-by: Birger Koblitz Signed-off-by: Sander Vanheule Tested-by: Stijn Tintel --- .../files-5.10/drivers/net/ethernet/rtl838x_eth.c | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/target/linux/realtek/files-5.10/drivers/net/ethernet/rtl838x_eth.c b/target/linux/realtek/files-5.10/drivers/net/ethernet/rtl838x_eth.c index c966746f02..dd3d3b66f9 100644 --- a/target/linux/realtek/files-5.10/drivers/net/ethernet/rtl838x_eth.c +++ b/target/linux/realtek/files-5.10/drivers/net/ethernet/rtl838x_eth.c @@ -630,6 +630,7 @@ static const struct rtl838x_reg rtl931x_reg = { static void rtl838x_hw_reset(struct rtl838x_eth_priv *priv) { u32 int_saved, nbuf; + u32 reset_mask; int i, pos; pr_info("RESETTING %x, CPU_PORT %d\n", priv->family_id, priv->cpu_port); @@ -662,15 +663,17 @@ static void rtl838x_hw_reset(struct rtl838x_eth_priv *priv) sw_w32(0xffffffff, priv->r->dma_if_intr_sts); } - /* Reset NIC */ + /* Reset NIC (SW_NIC_RST) and queues (SW_Q_RST) */ if (priv->family_id == RTL9300_FAMILY_ID || priv->family_id == RTL9310_FAMILY_ID) - sw_w32(0x4, priv->r->rst_glb_ctrl); + reset_mask = 0x6; else - sw_w32(0x8, priv->r->rst_glb_ctrl); + reset_mask = 0xc; + + sw_w32(reset_mask, priv->r->rst_glb_ctrl); do { /* Wait for reset of NIC and Queues done */ udelay(20); - } while (sw_r32(priv->r->rst_glb_ctrl) & 0xc); + } while (sw_r32(priv->r->rst_glb_ctrl) & reset_mask); mdelay(100); /* Setup Head of Line */ From af2cfbda2bf544666b30b2730e9486b2d6eff76f Mon Sep 17 00:00:00 2001 From: Sander Vanheule Date: Sun, 14 Nov 2021 19:45:30 +0100 Subject: [PATCH 13/22] realtek: Consolidate bootargs All current devices use identical bootargs, so let's move that to the common devicetree includes. Signed-off-by: Sander Vanheule Tested-by: Stijn Segers Tested-by: Paul Fertser Tested-by: Stijn Tintel --- target/linux/realtek/dts-5.10/rtl8380_netgear_gigabit.dtsi | 4 ---- target/linux/realtek/dts-5.10/rtl8380_zyxel_gs1900.dtsi | 4 ---- target/linux/realtek/dts-5.10/rtl8382_allnet_all-sg8208m.dts | 4 ---- target/linux/realtek/dts-5.10/rtl8382_d-link_dgs-1210-10p.dts | 4 ---- target/linux/realtek/dts-5.10/rtl8382_d-link_dgs-1210.dtsi | 4 ---- target/linux/realtek/dts-5.10/rtl8382_inaba_aml2-17gp.dts | 4 ---- target/linux/realtek/dts-5.10/rtl838x.dtsi | 2 +- target/linux/realtek/dts-5.10/rtl930x.dtsi | 2 +- 8 files changed, 2 insertions(+), 26 deletions(-) diff --git a/target/linux/realtek/dts-5.10/rtl8380_netgear_gigabit.dtsi b/target/linux/realtek/dts-5.10/rtl8380_netgear_gigabit.dtsi index e98a9bfc61..6eb316231b 100644 --- a/target/linux/realtek/dts-5.10/rtl8380_netgear_gigabit.dtsi +++ b/target/linux/realtek/dts-5.10/rtl8380_netgear_gigabit.dtsi @@ -8,10 +8,6 @@ / { compatible = "realtek,rtl838x-soc"; - chosen { - bootargs = "console=ttyS0,115200"; - }; - memory@0 { device_type = "memory"; reg = <0x0 0x8000000>; diff --git a/target/linux/realtek/dts-5.10/rtl8380_zyxel_gs1900.dtsi b/target/linux/realtek/dts-5.10/rtl8380_zyxel_gs1900.dtsi index 7233f6086c..7095006454 100644 --- a/target/linux/realtek/dts-5.10/rtl8380_zyxel_gs1900.dtsi +++ b/target/linux/realtek/dts-5.10/rtl8380_zyxel_gs1900.dtsi @@ -13,10 +13,6 @@ led-upgrade = &led_sys; }; - chosen { - bootargs = "console=ttyS0,115200"; - }; - memory@0 { device_type = "memory"; reg = <0x0 0x8000000>; diff --git a/target/linux/realtek/dts-5.10/rtl8382_allnet_all-sg8208m.dts b/target/linux/realtek/dts-5.10/rtl8382_allnet_all-sg8208m.dts index f4ca1686dd..320cb08ac7 100644 --- a/target/linux/realtek/dts-5.10/rtl8382_allnet_all-sg8208m.dts +++ b/target/linux/realtek/dts-5.10/rtl8382_allnet_all-sg8208m.dts @@ -16,10 +16,6 @@ led-upgrade = &led_sys; }; - chosen { - bootargs = "console=ttyS0,115200"; - }; - memory@0 { device_type = "memory"; reg = <0x0 0x8000000>; diff --git a/target/linux/realtek/dts-5.10/rtl8382_d-link_dgs-1210-10p.dts b/target/linux/realtek/dts-5.10/rtl8382_d-link_dgs-1210-10p.dts index 119eaadc16..a0f377c4f4 100644 --- a/target/linux/realtek/dts-5.10/rtl8382_d-link_dgs-1210-10p.dts +++ b/target/linux/realtek/dts-5.10/rtl8382_d-link_dgs-1210-10p.dts @@ -16,10 +16,6 @@ led-upgrade = &led_power; }; - chosen { - bootargs = "console=ttyS0,115200"; - }; - memory@0 { device_type = "memory"; reg = <0x0 0x8000000>; diff --git a/target/linux/realtek/dts-5.10/rtl8382_d-link_dgs-1210.dtsi b/target/linux/realtek/dts-5.10/rtl8382_d-link_dgs-1210.dtsi index a4811dbf30..312a36c1a8 100644 --- a/target/linux/realtek/dts-5.10/rtl8382_d-link_dgs-1210.dtsi +++ b/target/linux/realtek/dts-5.10/rtl8382_d-link_dgs-1210.dtsi @@ -13,10 +13,6 @@ led-upgrade = &led_power; }; - chosen { - bootargs = "console=ttyS0,115200"; - }; - memory@0 { device_type = "memory"; reg = <0x0 0x8000000>; diff --git a/target/linux/realtek/dts-5.10/rtl8382_inaba_aml2-17gp.dts b/target/linux/realtek/dts-5.10/rtl8382_inaba_aml2-17gp.dts index 1dc9e272fe..30960afff4 100644 --- a/target/linux/realtek/dts-5.10/rtl8382_inaba_aml2-17gp.dts +++ b/target/linux/realtek/dts-5.10/rtl8382_inaba_aml2-17gp.dts @@ -9,10 +9,6 @@ compatible = "inaba,aml2-17gp", "realtek,rtl838x-soc"; model = "INABA Abaniact AML2-17GP"; - chosen { - bootargs = "console=ttyS0,115200"; - }; - memory@0 { device_type = "memory"; reg = <0x0 0x8000000>; diff --git a/target/linux/realtek/dts-5.10/rtl838x.dtsi b/target/linux/realtek/dts-5.10/rtl838x.dtsi index a72addcf36..a33b6d899e 100644 --- a/target/linux/realtek/dts-5.10/rtl838x.dtsi +++ b/target/linux/realtek/dts-5.10/rtl838x.dtsi @@ -65,7 +65,7 @@ }; chosen { - bootargs = "console=ttyS0,38400"; + bootargs = "console=ttyS0,115200"; }; cpuintc: cpuintc { diff --git a/target/linux/realtek/dts-5.10/rtl930x.dtsi b/target/linux/realtek/dts-5.10/rtl930x.dtsi index e78e9ebeb8..e53f506a95 100644 --- a/target/linux/realtek/dts-5.10/rtl930x.dtsi +++ b/target/linux/realtek/dts-5.10/rtl930x.dtsi @@ -70,7 +70,7 @@ }; chosen { - bootargs = "console=ttyS0,38400"; + bootargs = "console=ttyS0,115200"; }; cpuintc: cpuintc { From d3a62bea085ddd959d195671dcbeba9829e47dae Mon Sep 17 00:00:00 2001 From: Sander Vanheule Date: Sun, 14 Nov 2021 19:45:31 +0100 Subject: [PATCH 14/22] realtek: Add Lexra bus clock The CPU peripherals on RTL83xx/RTL930x are connected to the CPU via the Lexra bus. This bus can provide a clock signal to these peripherals, but no clock driver is currently available. Instead, use a fixed-clock to provide the clock frequency, and update the dependent peripherals. Lexra bus clock frequencies: - RTL838x: 200MHz - RTL839x: 200MHz - RTL930x: 175MHz Signed-off-by: Sander Vanheule Tested-by: Stijn Segers Tested-by: Paul Fertser Tested-by: Stijn Tintel --- target/linux/realtek/dts-5.10/rtl838x.dtsi | 10 ++++++++-- target/linux/realtek/dts-5.10/rtl930x.dtsi | 11 +++++------ 2 files changed, 13 insertions(+), 8 deletions(-) diff --git a/target/linux/realtek/dts-5.10/rtl838x.dtsi b/target/linux/realtek/dts-5.10/rtl838x.dtsi index a33b6d899e..dc60e12bad 100644 --- a/target/linux/realtek/dts-5.10/rtl838x.dtsi +++ b/target/linux/realtek/dts-5.10/rtl838x.dtsi @@ -68,6 +68,12 @@ bootargs = "console=ttyS0,115200"; }; + lx_clk: lx_clk { + compatible = "fixed-clock"; + #clock-cells = <0>; + clock-frequency = <200000000>; + }; + cpuintc: cpuintc { compatible = "mti,cpu-interrupt-controller"; #address-cells = <0>; @@ -116,7 +122,7 @@ compatible = "ns16550a"; reg = <0x2000 0x100>; - clock-frequency = <200000000>; + clocks = <&lx_clk>; interrupt-parent = <&intc>; interrupts = <31>; @@ -134,7 +140,7 @@ compatible = "ns16550a"; reg = <0x2100 0x100>; - clock-frequency = <200000000>; + clocks = <&lx_clk>; interrupt-parent = <&intc>; interrupts = <30>; diff --git a/target/linux/realtek/dts-5.10/rtl930x.dtsi b/target/linux/realtek/dts-5.10/rtl930x.dtsi index e53f506a95..9e9501d51a 100644 --- a/target/linux/realtek/dts-5.10/rtl930x.dtsi +++ b/target/linux/realtek/dts-5.10/rtl930x.dtsi @@ -80,11 +80,10 @@ interrupt-controller; }; - osc: oscillator { + lx_clk: lx_clk { compatible = "fixed-clock"; - #clock-cells = <1>; + #clock-cells = <0>; clock-frequency = <175000000>; - clock-output-names = "osc"; }; soc: soc { @@ -119,7 +118,7 @@ interrupt-parent = <&intc>; interrupts = <8>; interrupt-names = "ostimer"; - clocks = <&osc 0>; + clocks = <&lx_clk>; }; spi0: spi@1200 { @@ -134,7 +133,7 @@ compatible = "ns16550a"; reg = <0x2000 0x100>; - clock-frequency = <175000000>; + clocks = <&lx_clk>; interrupt-parent = <&intc>; interrupts = <30>; @@ -149,7 +148,7 @@ compatible = "ns16550a"; reg = <0x2100 0x100>; - clock-frequency = <175000000>; + clocks = <&lx_clk>; interrupt-parent = <&intc>; interrupts = <31>; From b8fc5eecdc5d33cf261986436597b5482ab856da Mon Sep 17 00:00:00 2001 From: Sander Vanheule Date: Sun, 14 Nov 2021 19:45:32 +0100 Subject: [PATCH 15/22] realtek: Backport Realtek Otto WDT driver Add patch submitted upstream to linux-watchdog and replace the MIPS architecture symbols. Requires one extra patch for the DIV_ROUND_* macros, which have moved to a different header since 5.10. Signed-off-by: Sander Vanheule Tested-by: Stijn Segers Tested-by: Paul Fertser Tested-by: Stijn Tintel --- ...hdog-add-realtek-otto-watchdog-timer.patch | 456 ++++++++++++++++++ ...date-dependency-for-realtek-otto-wdt.patch | 17 + ...308-otto-wdt-fix-missing-math-header.patch | 13 + 3 files changed, 486 insertions(+) create mode 100644 target/linux/realtek/patches-5.10/100-watchdog-add-realtek-otto-watchdog-timer.patch create mode 100644 target/linux/realtek/patches-5.10/307-wdt-update-dependency-for-realtek-otto-wdt.patch create mode 100644 target/linux/realtek/patches-5.10/308-otto-wdt-fix-missing-math-header.patch diff --git a/target/linux/realtek/patches-5.10/100-watchdog-add-realtek-otto-watchdog-timer.patch b/target/linux/realtek/patches-5.10/100-watchdog-add-realtek-otto-watchdog-timer.patch new file mode 100644 index 0000000000..5aa988dc55 --- /dev/null +++ b/target/linux/realtek/patches-5.10/100-watchdog-add-realtek-otto-watchdog-timer.patch @@ -0,0 +1,456 @@ +From 2dbf0c6e0eebf523008c15794434d2d1a9b1260e Mon Sep 17 00:00:00 2001 +Message-Id: <2dbf0c6e0eebf523008c15794434d2d1a9b1260e.1636018117.git.sander@svanheule.net> +In-Reply-To: +References: +From: Sander Vanheule +Date: Sun, 3 Oct 2021 09:25:27 +0200 +Subject: [PATCH v3 2/2] watchdog: Add Realtek Otto watchdog timer + +Realtek MIPS SoCs (platform name Otto) have a watchdog timer with +pretimeout notifitication support. The WDT can (partially) hard reset, +or soft reset the SoC. + +This driver implements all features as described in the devicetree +binding, except the phase2 interrupt, and also functions as a restart +handler. The cpu reset mode is considered to be a "warm" restart, since +this mode does not reset all peripherals. Being an embedded system +though, the "cpu" and "software" modes will still cause the bootloader +to run on restart. + +It is not known how a forced system reset can be disabled on the +supported platforms. This means that the phase2 interrupt will only fire +at the same time as reset, so implementing phase2 is of little use. + +Signed-off-by: Sander Vanheule +--- + MAINTAINERS | 7 + + drivers/watchdog/Kconfig | 13 + + drivers/watchdog/Makefile | 1 + + drivers/watchdog/realtek_otto_wdt.c | 361 ++++++++++++++++++++++++++++ + 4 files changed, 382 insertions(+) + create mode 100644 drivers/watchdog/realtek_otto_wdt.c + +diff --git a/MAINTAINERS b/MAINTAINERS +index 2c9070aeba2a..54c8f788d3e5 100644 +--- a/MAINTAINERS ++++ b/MAINTAINERS +@@ -15991,6 +15991,13 @@ S: Maintained + F: include/sound/rt*.h + F: sound/soc/codecs/rt* + ++REALTEK OTTO WATCHDOG ++M: Sander Vanheule ++L: linux-watchdog@vger.kernel.org ++S: Maintained ++F: Documentation/devicetree/bindings/watchdog/realtek,otto-wdt.yaml ++F: driver/watchdog/realtek_otto_wdt.c ++ + REALTEK RTL83xx SMI DSA ROUTER CHIPS + M: Linus Walleij + S: Maintained +diff --git a/drivers/watchdog/Kconfig b/drivers/watchdog/Kconfig +index bf59faeb3de1..d308e13a9aa1 100644 +--- a/drivers/watchdog/Kconfig ++++ b/drivers/watchdog/Kconfig +@@ -954,6 +954,19 @@ config RTD119X_WATCHDOG + Say Y here to include support for the watchdog timer in + Realtek RTD1295 SoCs. + ++config REALTEK_OTTO_WDT ++ tristate "Realtek Otto MIPS watchdog support" ++ depends on MACH_REALTEK_RTL || COMPILE_TEST ++ depends on COMMON_CLK ++ select WATCHDOG_CORE ++ default MACH_REALTEK_RTL ++ help ++ Say Y here to include support for the watchdog timer on Realtek ++ RTL838x, RTL839x, RTL930x SoCs. This watchdog has pretimeout ++ notifications and system reset on timeout. ++ ++ When built as a module this will be called realtek_otto_wdt. ++ + config SPRD_WATCHDOG + tristate "Spreadtrum watchdog support" + depends on ARCH_SPRD || COMPILE_TEST +diff --git a/drivers/watchdog/Makefile b/drivers/watchdog/Makefile +index 1bd2d6f37c53..a8dccf819163 100644 +--- a/drivers/watchdog/Makefile ++++ b/drivers/watchdog/Makefile +@@ -171,6 +171,7 @@ obj-$(CONFIG_IMGPDC_WDT) += imgpdc_wdt.o + obj-$(CONFIG_MT7621_WDT) += mt7621_wdt.o + obj-$(CONFIG_PIC32_WDT) += pic32-wdt.o + obj-$(CONFIG_PIC32_DMT) += pic32-dmt.o ++obj-$(CONFIG_REALTEK_OTTO_WDT) += realtek_otto_wdt.o + + # PARISC Architecture + +diff --git a/drivers/watchdog/realtek_otto_wdt.c b/drivers/watchdog/realtek_otto_wdt.c +new file mode 100644 +index 000000000000..48bc8dfefc25 +--- /dev/null ++++ b/drivers/watchdog/realtek_otto_wdt.c +@@ -0,0 +1,361 @@ ++// SPDX-License-Identifier: GPL-2.0-only ++ ++/* ++ * Realtek Otto MIPS platform watchdog ++ * ++ * Watchdog timer that will reset the system after timeout, using the selected ++ * reset mode. ++ * ++ * Counter scaling and timeouts: ++ * - Base prescale of (2 << 25), providing tick duration T_0: 168ms @ 200MHz ++ * - PRESCALE: logarithmic prescaler adding a factor of {1, 2, 4, 8} ++ * - Phase 1: Times out after (PHASE1 + 1) × PRESCALE × T_0 ++ * Generates an interrupt, WDT cannot be stopped after phase 1 ++ * - Phase 2: starts after phase 1, times out after (PHASE2 + 1) × PRESCALE × T_0 ++ * Resets the system according to RST_MODE ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#define OTTO_WDT_REG_CNTR 0x0 ++#define OTTO_WDT_CNTR_PING BIT(31) ++ ++#define OTTO_WDT_REG_INTR 0x4 ++#define OTTO_WDT_INTR_PHASE_1 BIT(31) ++#define OTTO_WDT_INTR_PHASE_2 BIT(30) ++ ++#define OTTO_WDT_REG_CTRL 0x8 ++#define OTTO_WDT_CTRL_ENABLE BIT(31) ++#define OTTO_WDT_CTRL_PRESCALE GENMASK(30, 29) ++#define OTTO_WDT_CTRL_PHASE1 GENMASK(26, 22) ++#define OTTO_WDT_CTRL_PHASE2 GENMASK(19, 15) ++#define OTTO_WDT_CTRL_RST_MODE GENMASK(1, 0) ++#define OTTO_WDT_MODE_SOC 0 ++#define OTTO_WDT_MODE_CPU 1 ++#define OTTO_WDT_MODE_SOFTWARE 2 ++#define OTTO_WDT_CTRL_DEFAULT OTTO_WDT_MODE_CPU ++ ++#define OTTO_WDT_PRESCALE_MAX 3 ++ ++/* ++ * One higher than the max values contained in PHASE{1,2}, since a value of 0 ++ * corresponds to one tick. ++ */ ++#define OTTO_WDT_PHASE_TICKS_MAX 32 ++ ++/* ++ * The maximum reset delay is actually 2×32 ticks, but that would require large ++ * pretimeout values for timeouts longer than 32 ticks. Limit the maximum timeout ++ * to 32 + 1 to ensure small pretimeout values can be configured as expected. ++ */ ++#define OTTO_WDT_TIMEOUT_TICKS_MAX (OTTO_WDT_PHASE_TICKS_MAX + 1) ++ ++struct otto_wdt_ctrl { ++ struct watchdog_device wdev; ++ struct device *dev; ++ void __iomem *base; ++ struct clk *clk; ++ int irq_phase1; ++}; ++ ++static int otto_wdt_start(struct watchdog_device *wdev) ++{ ++ struct otto_wdt_ctrl *ctrl = watchdog_get_drvdata(wdev); ++ u32 v; ++ ++ v = ioread32(ctrl->base + OTTO_WDT_REG_CTRL); ++ v |= OTTO_WDT_CTRL_ENABLE; ++ iowrite32(v, ctrl->base + OTTO_WDT_REG_CTRL); ++ ++ return 0; ++} ++ ++static int otto_wdt_stop(struct watchdog_device *wdev) ++{ ++ struct otto_wdt_ctrl *ctrl = watchdog_get_drvdata(wdev); ++ u32 v; ++ ++ v = ioread32(ctrl->base + OTTO_WDT_REG_CTRL); ++ v &= ~OTTO_WDT_CTRL_ENABLE; ++ iowrite32(v, ctrl->base + OTTO_WDT_REG_CTRL); ++ ++ return 0; ++} ++ ++static int otto_wdt_ping(struct watchdog_device *wdev) ++{ ++ struct otto_wdt_ctrl *ctrl = watchdog_get_drvdata(wdev); ++ ++ iowrite32(OTTO_WDT_CNTR_PING, ctrl->base + OTTO_WDT_REG_CNTR); ++ ++ return 0; ++} ++ ++static int otto_wdt_tick_ms(struct otto_wdt_ctrl *ctrl, int prescale) ++{ ++ unsigned int rate_khz = clk_get_rate(ctrl->clk) / 1000; ++ ++ if (!rate_khz) ++ return 0; ++ ++ return DIV_ROUND_CLOSEST(1 << (25 + prescale), rate_khz); ++} ++ ++/* ++ * The timer asserts the PHASE1/PHASE2 IRQs when the number of ticks exceeds ++ * the value stored in those fields. This means each phase will run for at least ++ * one tick, so small values need to be clamped to correctly reflect the timeout. ++ */ ++static inline unsigned int div_round_ticks(unsigned int val, unsigned int tick_duration, ++ unsigned int min_ticks) ++{ ++ return max(min_ticks, DIV_ROUND_UP(val, tick_duration)); ++} ++ ++static int otto_wdt_determine_timeouts(struct watchdog_device *wdev, unsigned int timeout, ++ unsigned int pretimeout) ++{ ++ struct otto_wdt_ctrl *ctrl = watchdog_get_drvdata(wdev); ++ unsigned int pretimeout_ms = pretimeout * 1000; ++ unsigned int timeout_ms = timeout * 1000; ++ unsigned int prescale_next = 0; ++ unsigned int phase1_ticks; ++ unsigned int phase2_ticks; ++ unsigned int total_ticks; ++ unsigned int prescale; ++ unsigned int tick_ms; ++ u32 v; ++ ++ do { ++ prescale = prescale_next; ++ if (prescale > OTTO_WDT_PRESCALE_MAX) ++ return -EINVAL; ++ ++ tick_ms = otto_wdt_tick_ms(ctrl, prescale); ++ total_ticks = div_round_ticks(timeout_ms, tick_ms, 2); ++ phase1_ticks = div_round_ticks(timeout_ms - pretimeout_ms, tick_ms, 1); ++ phase2_ticks = total_ticks - phase1_ticks; ++ ++ prescale_next++; ++ } while (phase1_ticks > OTTO_WDT_PHASE_TICKS_MAX ++ || phase2_ticks > OTTO_WDT_PHASE_TICKS_MAX); ++ ++ v = ioread32(ctrl->base + OTTO_WDT_REG_CTRL); ++ ++ v &= ~(OTTO_WDT_CTRL_PRESCALE | OTTO_WDT_CTRL_PHASE1 | OTTO_WDT_CTRL_PHASE2); ++ v |= FIELD_PREP(OTTO_WDT_CTRL_PHASE1, phase1_ticks - 1); ++ v |= FIELD_PREP(OTTO_WDT_CTRL_PHASE2, phase2_ticks - 1); ++ v |= FIELD_PREP(OTTO_WDT_CTRL_PRESCALE, prescale); ++ ++ iowrite32(v, ctrl->base + OTTO_WDT_REG_CTRL); ++ ++ timeout_ms = total_ticks * tick_ms; ++ ctrl->wdev.timeout = timeout_ms / 1000; ++ ++ pretimeout_ms = phase2_ticks * tick_ms; ++ ctrl->wdev.pretimeout = pretimeout_ms / 1000; ++ ++ return 0; ++} ++ ++static int otto_wdt_set_timeout(struct watchdog_device *wdev, unsigned int val) ++{ ++ return otto_wdt_determine_timeouts(wdev, val, min(wdev->pretimeout, val - 1)); ++} ++ ++static int otto_wdt_set_pretimeout(struct watchdog_device *wdev, unsigned int val) ++{ ++ return otto_wdt_determine_timeouts(wdev, wdev->timeout, val); ++} ++ ++static int otto_wdt_restart(struct watchdog_device *wdev, unsigned long reboot_mode, ++ void *data) ++{ ++ struct otto_wdt_ctrl *ctrl = watchdog_get_drvdata(wdev); ++ u32 reset_mode; ++ u32 v; ++ ++ disable_irq(ctrl->irq_phase1); ++ ++ switch (reboot_mode) { ++ case REBOOT_SOFT: ++ reset_mode = OTTO_WDT_MODE_SOFTWARE; ++ break; ++ case REBOOT_WARM: ++ reset_mode = OTTO_WDT_MODE_CPU; ++ break; ++ default: ++ reset_mode = OTTO_WDT_MODE_SOC; ++ break; ++ } ++ ++ /* Configure for shortest timeout and wait for reset to occur */ ++ v = FIELD_PREP(OTTO_WDT_CTRL_RST_MODE, reset_mode) | OTTO_WDT_CTRL_ENABLE; ++ iowrite32(v, ctrl->base + OTTO_WDT_REG_CTRL); ++ ++ mdelay(3 * otto_wdt_tick_ms(ctrl, 0)); ++ ++ return 0; ++} ++ ++static irqreturn_t otto_wdt_phase1_isr(int irq, void *dev_id) ++{ ++ struct otto_wdt_ctrl *ctrl = dev_id; ++ ++ iowrite32(OTTO_WDT_INTR_PHASE_1, ctrl->base + OTTO_WDT_REG_INTR); ++ dev_crit(ctrl->dev, "phase 1 timeout\n"); ++ watchdog_notify_pretimeout(&ctrl->wdev); ++ ++ return IRQ_HANDLED; ++} ++ ++static const struct watchdog_ops otto_wdt_ops = { ++ .owner = THIS_MODULE, ++ .start = otto_wdt_start, ++ .stop = otto_wdt_stop, ++ .ping = otto_wdt_ping, ++ .set_timeout = otto_wdt_set_timeout, ++ .set_pretimeout = otto_wdt_set_pretimeout, ++ .restart = otto_wdt_restart, ++}; ++ ++static const struct watchdog_info otto_wdt_info = { ++ .identity = "Realtek Otto watchdog timer", ++ .options = WDIOF_KEEPALIVEPING | ++ WDIOF_MAGICCLOSE | ++ WDIOF_SETTIMEOUT | ++ WDIOF_PRETIMEOUT, ++}; ++ ++static int otto_wdt_probe_reset_mode(struct otto_wdt_ctrl *ctrl) ++{ ++ static const char *mode_property = "realtek,reset-mode"; ++ const struct fwnode_handle *node = ctrl->dev->fwnode; ++ int mode_count; ++ u32 mode; ++ u32 v; ++ ++ if (!node) ++ return -ENXIO; ++ ++ mode_count = fwnode_property_string_array_count(node, mode_property); ++ if (mode_count < 0) ++ return mode_count; ++ else if (mode_count == 0) ++ return 0; ++ else if (mode_count != 1) ++ return -EINVAL; ++ ++ if (fwnode_property_match_string(node, mode_property, "soc") == 0) ++ mode = OTTO_WDT_MODE_SOC; ++ else if (fwnode_property_match_string(node, mode_property, "cpu") == 0) ++ mode = OTTO_WDT_MODE_CPU; ++ else if (fwnode_property_match_string(node, mode_property, "software") == 0) ++ mode = OTTO_WDT_MODE_SOFTWARE; ++ else ++ return -EINVAL; ++ ++ v = ioread32(ctrl->base + OTTO_WDT_REG_CTRL); ++ v &= ~OTTO_WDT_CTRL_RST_MODE; ++ v |= FIELD_PREP(OTTO_WDT_CTRL_RST_MODE, mode); ++ iowrite32(v, ctrl->base + OTTO_WDT_REG_CTRL); ++ ++ return 0; ++} ++ ++static int otto_wdt_probe(struct platform_device *pdev) ++{ ++ struct device *dev = &pdev->dev; ++ struct otto_wdt_ctrl *ctrl; ++ unsigned int max_tick_ms; ++ int ret; ++ ++ ctrl = devm_kzalloc(dev, sizeof(*ctrl), GFP_KERNEL); ++ if (!ctrl) ++ return -ENOMEM; ++ ++ ctrl->dev = dev; ++ ctrl->base = devm_platform_ioremap_resource(pdev, 0); ++ if (IS_ERR(ctrl->base)) ++ return PTR_ERR(ctrl->base); ++ ++ /* Clear any old interrupts and reset initial state */ ++ iowrite32(OTTO_WDT_INTR_PHASE_1 | OTTO_WDT_INTR_PHASE_2, ++ ctrl->base + OTTO_WDT_REG_INTR); ++ iowrite32(OTTO_WDT_CTRL_DEFAULT, ctrl->base + OTTO_WDT_REG_CTRL); ++ ++ ctrl->clk = devm_clk_get(dev, NULL); ++ if (IS_ERR(ctrl->clk)) ++ return dev_err_probe(dev, PTR_ERR(ctrl->clk), "Failed to get clock\n"); ++ ++ ctrl->irq_phase1 = platform_get_irq_byname(pdev, "phase1"); ++ if (ctrl->irq_phase1 < 0) ++ return dev_err_probe(dev, ctrl->irq_phase1, "phase1 IRQ not found\n"); ++ ++ ret = devm_request_irq(dev, ctrl->irq_phase1, otto_wdt_phase1_isr, 0, ++ "realtek-otto-wdt", ctrl); ++ if (ret) ++ return dev_err_probe(dev, ret, "Failed to get IRQ for phase1\n"); ++ ++ ret = otto_wdt_probe_reset_mode(ctrl); ++ if (ret) ++ return dev_err_probe(dev, ret, "Invalid reset mode specified\n"); ++ ++ ctrl->wdev.parent = dev; ++ ctrl->wdev.info = &otto_wdt_info; ++ ctrl->wdev.ops = &otto_wdt_ops; ++ ++ /* ++ * Since pretimeout cannot be disabled, min. timeout is twice the ++ * subsystem resolution. max. timeout is ca. 43s at a bus clock of 200MHz. ++ */ ++ ctrl->wdev.min_timeout = 2; ++ max_tick_ms = otto_wdt_tick_ms(ctrl, OTTO_WDT_PRESCALE_MAX); ++ ctrl->wdev.max_hw_heartbeat_ms = max_tick_ms * OTTO_WDT_TIMEOUT_TICKS_MAX; ++ ctrl->wdev.timeout = min(30U, ctrl->wdev.max_hw_heartbeat_ms / 1000); ++ ++ watchdog_set_drvdata(&ctrl->wdev, ctrl); ++ watchdog_init_timeout(&ctrl->wdev, 0, dev); ++ watchdog_stop_on_reboot(&ctrl->wdev); ++ watchdog_set_restart_priority(&ctrl->wdev, 128); ++ ++ ret = otto_wdt_determine_timeouts(&ctrl->wdev, ctrl->wdev.timeout, 1); ++ if (ret) ++ return dev_err_probe(dev, ret, "Failed to set timeout\n"); ++ ++ return devm_watchdog_register_device(dev, &ctrl->wdev); ++} ++ ++static const struct of_device_id otto_wdt_ids[] = { ++ { .compatible = "realtek,rtl8380-wdt" }, ++ { .compatible = "realtek,rtl8390-wdt" }, ++ { .compatible = "realtek,rtl9300-wdt" }, ++ { } ++}; ++MODULE_DEVICE_TABLE(of, otto_wdt_ids); ++ ++static struct platform_driver otto_wdt_driver = { ++ .probe = otto_wdt_probe, ++ .driver = { ++ .name = "realtek-otto-watchdog", ++ .of_match_table = otto_wdt_ids, ++ }, ++}; ++module_platform_driver(otto_wdt_driver); ++ ++MODULE_LICENSE("GPL v2"); ++MODULE_AUTHOR("Sander Vanheule "); ++MODULE_DESCRIPTION("Realtek Otto watchdog timer driver"); +-- +2.31.1 + diff --git a/target/linux/realtek/patches-5.10/307-wdt-update-dependency-for-realtek-otto-wdt.patch b/target/linux/realtek/patches-5.10/307-wdt-update-dependency-for-realtek-otto-wdt.patch new file mode 100644 index 0000000000..32c3e2bb69 --- /dev/null +++ b/target/linux/realtek/patches-5.10/307-wdt-update-dependency-for-realtek-otto-wdt.patch @@ -0,0 +1,17 @@ +Index: linux-5.10.76/drivers/watchdog/Kconfig +=================================================================== +--- linux-5.10.76.orig/drivers/watchdog/Kconfig ++++ linux-5.10.76/drivers/watchdog/Kconfig +@@ -997,10 +997,10 @@ config RTD119X_WATCHDOG + + config REALTEK_OTTO_WDT + tristate "Realtek Otto MIPS watchdog support" +- depends on MACH_REALTEK_RTL || COMPILE_TEST ++ depends on RTL838X + depends on COMMON_CLK + select WATCHDOG_CORE +- default MACH_REALTEK_RTL ++ default RTL838X + help + Say Y here to include support for the watchdog timer on Realtek + RTL838x, RTL839x, RTL930x SoCs. This watchdog has pretimeout diff --git a/target/linux/realtek/patches-5.10/308-otto-wdt-fix-missing-math-header.patch b/target/linux/realtek/patches-5.10/308-otto-wdt-fix-missing-math-header.patch new file mode 100644 index 0000000000..20f86ed7e2 --- /dev/null +++ b/target/linux/realtek/patches-5.10/308-otto-wdt-fix-missing-math-header.patch @@ -0,0 +1,13 @@ +Index: linux-5.10.72/drivers/watchdog/realtek_otto_wdt.c +=================================================================== +--- linux-5.10.72.orig/drivers/watchdog/realtek_otto_wdt.c ++++ linux-5.10.72/drivers/watchdog/realtek_otto_wdt.c +@@ -21,7 +21,7 @@ + #include + #include + #include +-#include ++#include + #include + #include + #include From 927570f0a3d0ea82d5b6a3bc3b175ace3ad45e66 Mon Sep 17 00:00:00 2001 From: Sander Vanheule Date: Sun, 14 Nov 2021 19:45:33 +0100 Subject: [PATCH 16/22] realtek: Add and enable watchdog node Add and enable the Realtek Otto WDT peripheral found on these SoCs. Default all devices to use standard (cold) reboot and "soc" resets. Devices that require the PLL value fixup before restarting, should pick the "cpu" or "software" reset mode. These devices also need to provide a custom reboot mode, by adding the reboot argument to the kernel command line: WDT reset mode | kernel reboot mode ----------------+--------------------------------------- soc | reboot=cold (default if not specified) cpu | reboot=warm software | reboot=software Preferrably, these devices should use an alternative restart method like gpio-restart to provide reliable restarts. Note that watchdog restarts are not yet exposed, since the _machine_restart override is still present. Signed-off-by: Sander Vanheule Tested-by: Stijn Segers Tested-by: Paul Fertser Tested-by: Stijn Tintel --- target/linux/realtek/config-5.10 | 2 ++ target/linux/realtek/dts-5.10/rtl838x.dtsi | 14 ++++++++++++++ target/linux/realtek/dts-5.10/rtl930x.dtsi | 18 +++++++++++++++++- 3 files changed, 33 insertions(+), 1 deletion(-) diff --git a/target/linux/realtek/config-5.10 b/target/linux/realtek/config-5.10 index 2c5ab1706a..00f2a6af13 100644 --- a/target/linux/realtek/config-5.10 +++ b/target/linux/realtek/config-5.10 @@ -160,6 +160,7 @@ CONFIG_PINCTRL=y CONFIG_POWER_RESET=y CONFIG_POWER_RESET_SYSCON=y CONFIG_RATIONAL=y +CONFIG_REALTEK_OTTO_WDT=y CONFIG_REALTEK_PHY=y CONFIG_REALTEK_SOC_PHY=y CONFIG_REGMAP=y @@ -190,5 +191,6 @@ CONFIG_TIMER_PROBE=y CONFIG_TINY_SRCU=y CONFIG_USE_GENERIC_EARLY_PRINTK_8250=y CONFIG_USE_OF=y +CONFIG_WATCHDOG_CORE=y CONFIG_ZLIB_DEFLATE=y CONFIG_ZLIB_INFLATE=y diff --git a/target/linux/realtek/dts-5.10/rtl838x.dtsi b/target/linux/realtek/dts-5.10/rtl838x.dtsi index dc60e12bad..f356f8fcde 100644 --- a/target/linux/realtek/dts-5.10/rtl838x.dtsi +++ b/target/linux/realtek/dts-5.10/rtl838x.dtsi @@ -153,6 +153,20 @@ status = "disabled"; }; + watchdog0: watchdog@3150 { + compatible = "realtek,rtl8380-wdt"; + reg = <0x3150 0xc>; + + realtek,reset-mode = "soc"; + + clocks = <&lx_clk>; + timeout-sec = <30>; + + interrupt-parent = <&intc>; + interrupt-names = "phase1", "phase2"; + interrupts = <19>, <18>; + }; + gpio0: gpio-controller@3500 { compatible = "realtek,rtl8380-gpio", "realtek,otto-gpio"; reg = <0x3500 0x20>; diff --git a/target/linux/realtek/dts-5.10/rtl930x.dtsi b/target/linux/realtek/dts-5.10/rtl930x.dtsi index 9e9501d51a..a4c9757505 100644 --- a/target/linux/realtek/dts-5.10/rtl930x.dtsi +++ b/target/linux/realtek/dts-5.10/rtl930x.dtsi @@ -109,7 +109,9 @@ <10 &cpuintc 1>, /* TC3 */ <9 &cpuintc 1>, /* TC2 */ <8 &cpuintc 1>, /* TC1 */ - <7 &cpuintc 5>; /* TC0 */ + <7 &cpuintc 5>, /* TC0 */ + <6 &cpuintc 5>, /* WDT_IP2 */ + <5 &cpuintc 4>; /* WDT_IP1 */ }; timer: timer@3200 { @@ -161,6 +163,20 @@ status = "disabled"; }; + watchdog0: watchdog@3260 { + compatible = "realtek,rtl9300-wdt"; + reg = <0x3260 0xc>; + + realtek,reset-mode = "soc"; + + clocks = <&lx_clk>; + timeout-sec = <30>; + + interrupt-parent = <&intc>; + interrupt-names = "phase1", "phase2"; + interrupts = <5>, <6>; + }; + gpio0: gpio-controller@3500 { compatible = "realtek,rtl8380-gpio", "realtek,otto-gpio"; reg = <0x3500 0x20>; From f8b2bc550bd57e59e5def03e397ccfc6fcc0a81c Mon Sep 17 00:00:00 2001 From: Sander Vanheule Date: Sun, 14 Nov 2021 19:45:34 +0100 Subject: [PATCH 17/22] realtek: Remove _machine_restart and _machine_halt By dropping _machine_restart, users can provide more reliable or device-specific restart modes. _machine_halt was already removed in commit f4b687d1f053 ("realtek: use kernel defined halt"), but quietly reintroduced in commit 8faffa00cb6b ("realtek: add support for the RTL9300 timer"). Let's remove it again. Signed-off-by: Sander Vanheule Tested-by: Stijn Segers Tested-by: Paul Fertser Tested-by: Stijn Tintel --- .../files-5.10/arch/mips/rtl838x/setup.c | 85 ------------------- 1 file changed, 85 deletions(-) diff --git a/target/linux/realtek/files-5.10/arch/mips/rtl838x/setup.c b/target/linux/realtek/files-5.10/arch/mips/rtl838x/setup.c index 752a856437..55419c7b0b 100644 --- a/target/linux/realtek/files-5.10/arch/mips/rtl838x/setup.c +++ b/target/linux/realtek/files-5.10/arch/mips/rtl838x/setup.c @@ -20,7 +20,6 @@ #include #include #include -#include #include #include #include @@ -29,100 +28,20 @@ extern struct rtl83xx_soc_info soc_info; -u32 pll_reset_value; - -static void rtl838x_restart(char *command) -{ - u32 pll = sw_r32(RTL838X_PLL_CML_CTRL); - - pr_info("System restart.\n"); - pr_info("PLL control register: %x, applying reset value %x\n", - pll, pll_reset_value); - - sw_w32(3, RTL838X_INT_RW_CTRL); - sw_w32(pll_reset_value, RTL838X_PLL_CML_CTRL); - sw_w32(0, RTL838X_INT_RW_CTRL); - - /* Reset Global Control1 Register */ - sw_w32(1, RTL838X_RST_GLB_CTRL_1); -} - -static void rtl839x_restart(char *command) -{ - /* SoC reset vector (in flash memory): on RTL839x platform preferred way to reset */ - void (*f)(void) = (void *) 0xbfc00000; - - pr_info("System restart.\n"); - /* Reset SoC */ - sw_w32(0xFFFFFFFF, RTL839X_RST_GLB_CTRL); - /* and call reset vector */ - f(); - /* If this fails, halt the CPU */ - while - (1); -} - -static void rtl930x_restart(char *command) -{ - pr_info("System restart.\n"); - sw_w32(0x1, RTL930X_RST_GLB_CTRL_0); - while - (1); -} - -static void rtl931x_restart(char *command) -{ - u32 v; - - pr_info("System restart.\n"); - sw_w32(1, RTL931X_RST_GLB_CTRL); - v = sw_r32(RTL931X_RST_GLB_CTRL); - sw_w32(0x101, RTL931X_RST_GLB_CTRL); - msleep(15); - sw_w32(v, RTL931X_RST_GLB_CTRL); - msleep(15); - sw_w32(0x101, RTL931X_RST_GLB_CTRL); -} - -static void rtl838x_halt(void) -{ - pr_info("System halted.\n"); - while - (1); -} - static void __init rtl838x_setup(void) { - pr_info("Registering _machine_restart\n"); - _machine_restart = rtl838x_restart; - _machine_halt = rtl838x_halt; - - /* This PLL value needs to be restored before a reset and will then be - * preserved over a SoC reset. A wrong value prevents the SoC from - * connecting to the SPI flash controller at boot and reading the - * reset routine */ - pll_reset_value = sw_r32(RTL838X_PLL_CML_CTRL); - /* Setup System LED. Bit 15 then allows to toggle it */ sw_w32_mask(0, 3 << 16, RTL838X_LED_GLB_CTRL); } static void __init rtl839x_setup(void) { - pr_info("Registering _machine_restart\n"); - _machine_restart = rtl839x_restart; - _machine_halt = rtl838x_halt; - /* Setup System LED. Bit 14 of RTL839X_LED_GLB_CTRL then allows to toggle it */ sw_w32_mask(0, 3 << 15, RTL839X_LED_GLB_CTRL); } static void __init rtl930x_setup(void) { - pr_info("Registering _machine_restart\n"); - _machine_restart = rtl930x_restart; - _machine_halt = rtl838x_halt; - if (soc_info.id == 0x9302) sw_w32_mask(0, 3 << 13, RTL9302_LED_GLB_CTRL); else @@ -131,9 +50,6 @@ static void __init rtl930x_setup(void) static void __init rtl931x_setup(void) { - pr_info("Registering _machine_restart\n"); - _machine_restart = rtl931x_restart; - _machine_halt = rtl838x_halt; sw_w32_mask(0, 3 << 12, RTL931X_LED_GLB_CTRL); } @@ -142,7 +58,6 @@ void __init plat_mem_setup(void) void *dtb; set_io_port_base(KSEG1); - _machine_restart = rtl838x_restart; if (fw_passed_dtb) /* UHI interface */ dtb = (void *)fw_passed_dtb; From 3ba98468424db1f081818982dfa2a07ab85ae136 Mon Sep 17 00:00:00 2001 From: David Bauer Date: Mon, 25 Oct 2021 21:33:40 +0200 Subject: [PATCH 18/22] hostapd: add beacon_interval to get_status ubus output Add the beacon interval to hostapd status output. This allows external services to discover the beacon interval for a specific VAP. This way, external wireless management daemons can correctly calculate fields containing TBTT value from absolute time-values. Signed-off-by: David Bauer --- package/network/services/hostapd/src/src/ap/ubus.c | 1 + 1 file changed, 1 insertion(+) diff --git a/package/network/services/hostapd/src/src/ap/ubus.c b/package/network/services/hostapd/src/src/ap/ubus.c index 69778596a4..e0d3d2ae90 100644 --- a/package/network/services/hostapd/src/src/ap/ubus.c +++ b/package/network/services/hostapd/src/src/ap/ubus.c @@ -425,6 +425,7 @@ hostapd_bss_get_status(struct ubus_context *ctx, struct ubus_object *obj, blobmsg_add_u32(&b, "freq", hapd->iface->freq); blobmsg_add_u32(&b, "channel", ieee80211_frequency_to_channel(hapd->iface->freq)); + blobmsg_add_u32(&b, "beacon_interval", hapd->iconf->beacon_int); snprintf(phy_name, 17, "%s", hapd->iface->phy); blobmsg_add_string(&b, "phy", phy_name); From 68189835ac81779f9cf21060dca0c54dcdb0c0a6 Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Fri, 26 Nov 2021 08:40:55 +0100 Subject: [PATCH 19/22] mac80211: backport fix for dealing with stripped IV on rx This fixes potental rx drop issues Signed-off-by: Felix Fietkau --- ...t-access-the-IV-when-it-was-stripped.patch | 26 +++++++++++++++++++ 1 file changed, 26 insertions(+) create mode 100644 package/kernel/mac80211/patches/subsys/307-mac80211-do-not-access-the-IV-when-it-was-stripped.patch diff --git a/package/kernel/mac80211/patches/subsys/307-mac80211-do-not-access-the-IV-when-it-was-stripped.patch b/package/kernel/mac80211/patches/subsys/307-mac80211-do-not-access-the-IV-when-it-was-stripped.patch new file mode 100644 index 0000000000..7b662acdc5 --- /dev/null +++ b/package/kernel/mac80211/patches/subsys/307-mac80211-do-not-access-the-IV-when-it-was-stripped.patch @@ -0,0 +1,26 @@ +From: Xing Song +Date: Mon, 1 Nov 2021 10:46:57 +0800 +Subject: [PATCH] mac80211: do not access the IV when it was stripped + +ieee80211_get_keyid() will return false value if IV has been stripped, +such as return 0 for IP/ARP frames due to LLC header, and return -EINVAL +for disassociation frames due to its length... etc. Don't try to access +it if it's not present. + +Signed-off-by: Xing Song +Link: https://lore.kernel.org/r/20211101024657.143026-1-xing.song@mediatek.com +Signed-off-by: Johannes Berg +--- + +--- a/net/mac80211/rx.c ++++ b/net/mac80211/rx.c +@@ -1952,7 +1952,8 @@ ieee80211_rx_h_decrypt(struct ieee80211_ + int keyid = rx->sta->ptk_idx; + sta_ptk = rcu_dereference(rx->sta->ptk[keyid]); + +- if (ieee80211_has_protected(fc)) { ++ if (ieee80211_has_protected(fc) && ++ !(status->flag & RX_FLAG_IV_STRIPPED)) { + cs = rx->sta->cipher_scheme; + keyid = ieee80211_get_keyid(rx->skb, cs); + From b92a9f607b9af049c8e91a961947b0b10ea253a0 Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Fri, 26 Nov 2021 08:42:25 +0100 Subject: [PATCH 20/22] mac80211: fix a regression in generating radiotap headers Signed-off-by: Felix Fietkau --- ...80211-fix-radiotap-header-generation.patch | 49 +++++++++++++++++++ 1 file changed, 49 insertions(+) create mode 100644 package/kernel/mac80211/patches/subsys/308-mac80211-fix-radiotap-header-generation.patch diff --git a/package/kernel/mac80211/patches/subsys/308-mac80211-fix-radiotap-header-generation.patch b/package/kernel/mac80211/patches/subsys/308-mac80211-fix-radiotap-header-generation.patch new file mode 100644 index 0000000000..a408c3d802 --- /dev/null +++ b/package/kernel/mac80211/patches/subsys/308-mac80211-fix-radiotap-header-generation.patch @@ -0,0 +1,49 @@ +From: Johannes Berg +Date: Tue, 9 Nov 2021 10:02:04 +0100 +Subject: [PATCH] mac80211: fix radiotap header generation + +In commit 8c89f7b3d3f2 ("mac80211: Use flex-array for radiotap header +bitmap") we accidentally pointed the position to the wrong place, so +we overwrite a present bitmap, and thus cause all kinds of trouble. + +To see the issue, note that the previous code read: + + pos = (void *)(it_present + 1); + +The requirement now is that we need to calculate pos via it_optional, +to not trigger the compiler hardening checks, as: + + pos = (void *)&rthdr->it_optional[...]; + +Rewriting the original expression, we get (obviously, since that just +adds "+ x - x" terms): + + pos = (void *)(it_present + 1 + rthdr->it_optional - rthdr->it_optional) + +and moving the "+ rthdr->it_optional" outside to be used as an array: + + pos = (void *)&rthdr->it_optional[it_present + 1 - rthdr->it_optional]; + +The original is off by one, fix it. + +Cc: stable@vger.kernel.org +Fixes: 8c89f7b3d3f2 ("mac80211: Use flex-array for radiotap header bitmap") +Reported-by: Sid Hayn +Signed-off-by: Johannes Berg +Tested-by: Sid Hayn +Reviewed-by: Kees Cook +Link: https://lore.kernel.org/r/20211109100203.c61007433ed6.I1dade57aba7de9c4f48d68249adbae62636fd98c@changeid +Signed-off-by: Johannes Berg +--- + +--- a/net/mac80211/rx.c ++++ b/net/mac80211/rx.c +@@ -364,7 +364,7 @@ ieee80211_add_rx_radiotap_header(struct + * the compiler to think we have walked past the end of the + * struct member. + */ +- pos = (void *)&rthdr->it_optional[it_present - rthdr->it_optional]; ++ pos = (void *)&rthdr->it_optional[it_present + 1 - rthdr->it_optional]; + + /* the order of the following fields is important */ + From e73855b5d1f11751a286cf0029a67a55c853d804 Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Fri, 26 Nov 2021 11:24:39 +0100 Subject: [PATCH 21/22] llvm-bpf: use SOURCE_DATE_EPOCH for generated tarball Signed-off-by: Felix Fietkau --- target/llvm-bpf/Makefile | 1 + 1 file changed, 1 insertion(+) diff --git a/target/llvm-bpf/Makefile b/target/llvm-bpf/Makefile index c9ada017e6..0e8a8826e6 100644 --- a/target/llvm-bpf/Makefile +++ b/target/llvm-bpf/Makefile @@ -17,6 +17,7 @@ LLVM_TAR := $(BIN_DIR)/$(LLVM_BPF_PREFIX).tar.xz $(LLVM_TAR): $(HOST_STAMP_INSTALLED) tar -C $(STAGING_DIR_HOST) \ -I '$(STAGING_DIR_HOST)/bin/xz -7e -T$(if $(filter 1,$(NPROC)),2,0)' \ + $(if $(SOURCE_DATE_EPOCH),--mtime="@$(SOURCE_DATE_EPOCH)") \ -cf $@.tmp llvm-bpf $(LLVM_BPF_PREFIX) mv $@.tmp $@ From fb6c34d355e19152550a8347cde13e1c359f1aca Mon Sep 17 00:00:00 2001 From: Felix Fietkau Date: Fri, 26 Nov 2021 11:25:40 +0100 Subject: [PATCH 22/22] llvm-bpf: fix rebuild check for generating tarball Check the version file, as it will be regenerated on rebuild Signed-off-by: Felix Fietkau --- target/llvm-bpf/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/target/llvm-bpf/Makefile b/target/llvm-bpf/Makefile index 0e8a8826e6..6cadf693ef 100644 --- a/target/llvm-bpf/Makefile +++ b/target/llvm-bpf/Makefile @@ -14,7 +14,7 @@ LLVM_VERSION := $(shell cat $(STAGING_DIR_HOST)/llvm-bpf/.llvm-version) LLVM_BPF_PREFIX := llvm-bpf-$(LLVM_VERSION).$(HOST_OS)-$(HOST_ARCH) LLVM_TAR := $(BIN_DIR)/$(LLVM_BPF_PREFIX).tar.xz -$(LLVM_TAR): $(HOST_STAMP_INSTALLED) +$(LLVM_TAR): $(STAGING_DIR_HOST)/llvm-bpf/.llvm-version tar -C $(STAGING_DIR_HOST) \ -I '$(STAGING_DIR_HOST)/bin/xz -7e -T$(if $(filter 1,$(NPROC)),2,0)' \ $(if $(SOURCE_DATE_EPOCH),--mtime="@$(SOURCE_DATE_EPOCH)") \