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); 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; 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); 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); + 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 */ + 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 diff --git a/package/network/services/dnsmasq/files/dnsmasq.init b/package/network/services/dnsmasq/files/dnsmasq.init index 25e6876194..d84faed51d 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() { 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/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); 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) { 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); 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 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" ], 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>; + }; 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>; 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/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..f356f8fcde 100644 --- a/target/linux/realtek/dts-5.10/rtl838x.dtsi +++ b/target/linux/realtek/dts-5.10/rtl838x.dtsi @@ -65,7 +65,13 @@ }; chosen { - bootargs = "console=ttyS0,38400"; + bootargs = "console=ttyS0,115200"; + }; + + lx_clk: lx_clk { + compatible = "fixed-clock"; + #clock-cells = <0>; + clock-frequency = <200000000>; }; cpuintc: cpuintc { @@ -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>; @@ -147,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 e78e9ebeb8..a4c9757505 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 { @@ -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 { @@ -110,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 { @@ -119,7 +120,7 @@ interrupt-parent = <&intc>; interrupts = <8>; interrupt-names = "ostimer"; - clocks = <&osc 0>; + clocks = <&lx_clk>; }; spi0: spi@1200 { @@ -134,7 +135,7 @@ compatible = "ns16550a"; reg = <0x2000 0x100>; - clock-frequency = <175000000>; + clocks = <&lx_clk>; interrupt-parent = <&intc>; interrupts = <30>; @@ -149,7 +150,7 @@ compatible = "ns16550a"; reg = <0x2100 0x100>; - clock-frequency = <175000000>; + clocks = <&lx_clk>; interrupt-parent = <&intc>; interrupts = <31>; @@ -162,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>; 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; 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 */ 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 diff --git a/target/llvm-bpf/Makefile b/target/llvm-bpf/Makefile index c9ada017e6..6cadf693ef 100644 --- a/target/llvm-bpf/Makefile +++ b/target/llvm-bpf/Makefile @@ -14,9 +14,10 @@ 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)") \ -cf $@.tmp llvm-bpf $(LLVM_BPF_PREFIX) mv $@.tmp $@