* [PATCH net-next v3 0/2] ipv6: update NUD_FAILED neighbors from NA messages
@ 2026-09-18 22:13 Lawrence Lee
2026-09-18 22:13 ` [PATCH net-next v3 1/2] " Lawrence Lee
2026-09-18 22:13 ` [PATCH net-next v3 2/2] selftests: net: test untracked NA recovery of FAILED neighbors Lawrence Lee
0 siblings, 2 replies; 8+ messages in thread
From: Lawrence Lee @ 2026-09-18 22:13 UTC (permalink / raw)
To: David Ahern, Ido Schimmel, David S. Miller, Eric Dumazet,
Jakub Kicinski, Paolo Abeni
Cc: Simon Horman, Randy Dunlap, netdev, Arun Ajith S, Roopa Prabhu,
Jaehee Park, Jonathan Corbet, Shuah Khan, Shuah Khan, linux-doc,
linux-kselftest, linux-kernel
Neighbor Advertisements for existing NUD_FAILED entries are currently
ignored. This can leave a first-hop router with an unusable neighbor after
the host becomes reachable and announces itself, particularly when
forwarding is offloaded away from the kernel and traffic destined to the
FAILED neighbor is unable to trigger the kernel's normal neighbor
resolution process.
Allowing neighbor entries to be updated from NAs already received by the
kernel is preferable since it creates less work compared to periodically
probing FAILED neighbors (e.g. using NTF_EXT_MANAGED).
Extend accept_untracked_na to treat FAILED entries like absent entries.
Require a target link-layer address, IPv6 forwarding, and acceptance by the
sysctl, including its source-prefix check in mode 2. Recover the entry only
to STALE, including for solicited NAs, to maintain parity with handling of
non-existent neighbor cache entries.
Patch #1 implements the behavior and updates RFC 9131-related comments and
accept_untracked_na documentation.
Patch #2 extends ndisc_unsolicited_na_test.sh to cover FAILED-entry
recovery and each acceptance gate, including in-prefix and out-of-prefix
mode 2.
Thanks to Ido Schimmel for feedback on the original RFC.
---
v3:
- Cite RFC 4861 section 7.3.3 when describing FAILED entries.
- Simplify the FAILED-entry path as suggested by Ido Schimmel.
- Drop the NDISC callback and 6LoWPAN changes. The existing 6LoWPAN
override-only behavior also applies to INCOMPLETE entries and is left
unchanged.
- Restore the existing rt6_clean_tohost() source-address behavior. The
source-versus-target behavior applies to all neighbor states and is left
unchanged.
- Verify the link-layer address learned during recovery in selftests.
- Keep the NA source, target, and neighbor key fixed while varying the
router prefix in the mode 2 selftest cases.
- Arm packet capture in selftest before starting host DAD and wait for
capture readiness and receive completion.
v2:
- Full implementation of logic to update FAILED entries to STALE.
- Update the RFC 9131-related comments and sysctl documentation.
- Add selftests to verify state changes only when the accept_untracked_na
setting is enabled.
v1 (RFC):
https://lore.kernel.org/r/20260813233344.445265-1-lfqlee314@gmail.com
Testing:
- x86_64 allyesconfig build with W=1
- Sparse on net/ipv6/ndisc.c
- tools/testing/selftests/net/ndisc_unsolicited_na_test.sh: 14 passed
- Local NIPA checks: all 45 checks passed
- Sashiko local review completed
Lawrence Lee (2):
ipv6: update NUD_FAILED neighbors from NA messages
selftests: net: test untracked NA recovery of FAILED neighbors
Documentation/networking/ip-sysctl.rst | 28 +--
net/ipv6/ndisc.c | 47 +++--
.../net/ndisc_unsolicited_na_test.sh | 195 ++++++++++++++----
3 files changed, 201 insertions(+), 69 deletions(-)
base-commit: 4bb9710c6a68d35207f123aef55dcd50e7195ec5
--
2.43.0
^ permalink raw reply [flat|nested] 8+ messages in thread
* [PATCH net-next v3 1/2] ipv6: update NUD_FAILED neighbors from NA messages
2026-09-18 22:13 [PATCH net-next v3 0/2] ipv6: update NUD_FAILED neighbors from NA messages Lawrence Lee
@ 2026-09-18 22:13 ` Lawrence Lee
2026-09-20 8:09 ` Ido Schimmel
2026-09-22 22:37 ` netdev-bot+sashiko
2026-09-18 22:13 ` [PATCH net-next v3 2/2] selftests: net: test untracked NA recovery of FAILED neighbors Lawrence Lee
1 sibling, 2 replies; 8+ messages in thread
From: Lawrence Lee @ 2026-09-18 22:13 UTC (permalink / raw)
To: David Ahern, Ido Schimmel, David S. Miller, Eric Dumazet,
Jakub Kicinski, Paolo Abeni
Cc: Simon Horman, Randy Dunlap, netdev, Arun Ajith S, Roopa Prabhu,
Jaehee Park, Jonathan Corbet, Shuah Khan, Shuah Khan, linux-doc,
linux-kselftest, linux-kernel
Transition a FAILED neighbor entry to STALE upon receipt of an NA
message on routers when accept_untracked_na is enabled. This extends the
RFC 9131 accept_untracked_na behavior so that FAILED entries are treated
the same as non-existent entries.
RFC 4861 section 7.3.3 says that an entry should be deleted when address
resolution fails. Linux instead retains the entry in NUD_FAILED, so
treating it as untracked is consistent with the protocol model.
Trying to resolve FAILED neighbors via periodic probing (e.g. using
NTF_EXT_MANAGED) is more work compared to this approach which uses
information in NAs that the kernel may already be receiving. Note that
because this behavior in IPv6 is dependent on the accept_untracked_na
sysctl setting, this approach is more conservative than IPv4 which
transitions FAILED neighbors to STALE by default upon receiving GARPs.
Link: https://lore.kernel.org/r/20260813233344.445265-1-lfqlee314@gmail.com
Assisted-by: LLM Sashiko sparse
Signed-off-by: Lawrence Lee <lfqlee314@gmail.com>
---
The existing 6LoWPAN override-only handling also applies to INCOMPLETE
entries and is intentionally left unchanged. The existing
rt6_clean_tohost() source-versus-target behavior applies to all neighbor
states and is also left unchanged.
Documentation/networking/ip-sysctl.rst | 28 ++++++++-------
net/ipv6/ndisc.c | 47 ++++++++++++++------------
2 files changed, 41 insertions(+), 34 deletions(-)
diff --git a/Documentation/networking/ip-sysctl.rst b/Documentation/networking/ip-sysctl.rst
index f7af0286341c..685c84cf543d 100644
--- a/Documentation/networking/ip-sysctl.rst
+++ b/Documentation/networking/ip-sysctl.rst
@@ -3225,18 +3225,19 @@ drop_unsolicited_na - BOOLEAN
Default: 0 (disabled).
accept_untracked_na - INTEGER
- Define behavior for accepting neighbor advertisements from devices that
- are absent in the neighbor cache:
+ Define behavior for accepting neighbor advertisements for IPv6 addresses
+ that are absent from the neighbor cache or whose entries are in FAILED
+ state:
- - 0 - (default) Do not accept unsolicited and untracked neighbor
- advertisements.
+ - 0 - (default) Do not create new neighbor cache entries or update
+ FAILED entries from neighbor advertisements.
- - 1 - Add a new neighbor cache entry in STALE state for routers on
- receiving a neighbor advertisement (either solicited or unsolicited)
- with target link-layer address option specified if no neighbor entry
- is already present for the advertised IPv6 address. Without this knob,
- NAs received for untracked addresses (absent in neighbor cache) are
- silently ignored.
+ - 1 - For routers, add a new neighbor cache entry or update an existing
+ FAILED entry to STALE upon receiving a neighbor advertisement (either
+ solicited or unsolicited) with the target link-layer address option
+ specified. Without this knob, NAs received for untracked addresses
+ (absent from the neighbor cache or in FAILED state) are silently
+ ignored.
This is as per router-side behavior documented in RFC9131.
@@ -3251,9 +3252,10 @@ accept_untracked_na - INTEGER
used in conjunction with the ndisc_notify setting on the host to
satisfy this prerequisite.
- - 2 - Extend option (1) to add a new neighbor cache entry only if the
- source IP address is in the same subnet as an address configured on
- the interface that received the neighbor advertisement.
+ - 2 - Extend option (1) to add a new neighbor cache entry or update a
+ FAILED entry only if the source IP address is in the same subnet as
+ an address configured on the interface that received the neighbor
+ advertisement.
enhanced_dad - BOOLEAN
Include a nonce option in the IPv6 neighbor solicitation messages used for
diff --git a/net/ipv6/ndisc.c b/net/ipv6/ndisc.c
index 90cd5d852569..12d85d7f8234 100644
--- a/net/ipv6/ndisc.c
+++ b/net/ipv6/ndisc.c
@@ -973,13 +973,13 @@ static enum skb_drop_reason ndisc_recv_ns(struct sk_buff *skb)
static int accept_untracked_na(struct inet6_dev *idev, struct in6_addr *saddr)
{
switch (READ_ONCE(idev->cnf.accept_untracked_na)) {
- case 0: /* Don't accept untracked na (absent in neighbor cache) */
+ case 0: /* Don't accept untracked NA (absent or FAILED) */
return 0;
- case 1: /* Create new entries from na if currently untracked */
+ case 1: /* Create new or update FAILED entries from NA */
return 1;
- case 2: /* Create new entries from untracked na only if saddr is in the
+ case 2: /* Create new or update FAILED entries only if saddr is in the
* same subnet as an address configured on the interface that
- * received the na
+ * received the NA
*/
return !!ipv6_chk_prefix(saddr, idev->dev);
default:
@@ -1067,34 +1067,39 @@ static enum skb_drop_reason ndisc_recv_na(struct sk_buff *skb)
neigh = neigh_lookup(tbl, &msg->target, dev);
/* RFC 9131 updates original Neighbour Discovery RFC 4861.
- * NAs with Target LL Address option without a corresponding
- * entry in the neighbour cache can now create a STALE neighbour
- * cache entry on routers.
+ * NAs with Target LL Address option can now create a STALE neighbor
+ * cache entry on routers if the NA does not have a corresponding entry
+ * in the neighbour cache or has a corresponding FAILED entry.
*
- * entry accept fwding solicited behaviour
- * ------- ------ ------ --------- ----------------------
- * present X X 0 Set state to STALE
- * present X X 1 Set state to REACHABLE
- * absent 0 X X Do nothing
- * absent 1 0 X Do nothing
- * absent 1 1 X Add a new STALE entry
+ * entry accept fwding solicited behaviour
+ * ----------- ------ ------ --------- ----------------------
+ * non-FAILED X X 0 Set state to STALE
+ * non-FAILED X X 1 Set state to REACHABLE
+ * FAILED 0 X X Do nothing
+ * FAILED 1 0 X Do nothing
+ * FAILED 1 1 X Set state to STALE
+ * absent 0 X X Do nothing
+ * absent 1 0 X Do nothing
+ * absent 1 1 X Add a new STALE entry
*
* Note that we don't do a (daddr == all-routers-mcast) check.
*/
new_state = msg->icmph.icmp6_solicited ? NUD_REACHABLE : NUD_STALE;
- if (!neigh && lladdr && idev && READ_ONCE(idev->cnf.forwarding)) {
- if (accept_untracked_na(idev, saddr)) {
- neigh = neigh_create(tbl, &msg->target, dev);
- new_state = NUD_STALE;
+ if (!neigh || (READ_ONCE(neigh->nud_state) & NUD_FAILED)) {
+ if (!lladdr || !idev || !READ_ONCE(idev->cnf.forwarding) ||
+ !accept_untracked_na(idev, saddr)) {
+ if (neigh)
+ neigh_release(neigh);
+ return reason;
}
+ if (!neigh)
+ neigh = neigh_create(tbl, &msg->target, dev);
+ new_state = NUD_STALE;
}
if (neigh && !IS_ERR(neigh)) {
u8 old_flags = neigh->flags;
- if (READ_ONCE(neigh->nud_state) & NUD_FAILED)
- goto out;
-
/*
* Don't update the neighbor cache entry on a proxy NA from
* ourselves because either the proxied node is off link or it
--
2.43.0
^ permalink raw reply [flat|nested] 8+ messages in thread
* [PATCH net-next v3 2/2] selftests: net: test untracked NA recovery of FAILED neighbors
2026-09-18 22:13 [PATCH net-next v3 0/2] ipv6: update NUD_FAILED neighbors from NA messages Lawrence Lee
2026-09-18 22:13 ` [PATCH net-next v3 1/2] " Lawrence Lee
@ 2026-09-18 22:13 ` Lawrence Lee
2026-09-22 22:38 ` netdev-bot+sashiko
1 sibling, 1 reply; 8+ messages in thread
From: Lawrence Lee @ 2026-09-18 22:13 UTC (permalink / raw)
To: David Ahern, Ido Schimmel, David S. Miller, Eric Dumazet,
Jakub Kicinski, Paolo Abeni
Cc: Simon Horman, Randy Dunlap, netdev, Arun Ajith S, Roopa Prabhu,
Jaehee Park, Jonathan Corbet, Shuah Khan, Shuah Khan, linux-doc,
linux-kselftest, linux-kernel
Seed a FAILED neighbor before triggering an unsolicited NA. Verify that
the entry transitions to STALE and learns the advertised link-layer
address only when drop_unsolicited_na is disabled, accept_untracked_na
mode 1 or in-prefix mode 2 is enabled, and IPv6 forwarding is enabled.
Verify that disabling each gate keeps the entry in FAILED without a
link-layer address.
Mark the seed externally learned and disable carrier-based eviction so
the entry cannot be garbage-collected before the NA arrives. Require the
marker after processing to prove that a recovered entry was updated in
place instead of deleted and recreated.
Keep the NA source, target, and neighbor key fixed for the mode 2 cases.
Vary the prefix configured on the router to exercise the source-prefix
check without changing the entry under test.
Arm packet capture before bringing up the host interface and starting
DAD. Wait for the capture to become ready and for tcpdump to exit so the
NA cannot be missed and receive processing is complete before checking
the neighbor entry.
Link: https://lore.kernel.org/r/20260813233344.445265-1-lfqlee314@gmail.com
Assisted-by: LLM Sashiko sparse
Signed-off-by: Lawrence Lee <lfqlee314@gmail.com>
---
.../net/ndisc_unsolicited_na_test.sh | 195 ++++++++++++++----
1 file changed, 160 insertions(+), 35 deletions(-)
diff --git a/tools/testing/selftests/net/ndisc_unsolicited_na_test.sh b/tools/testing/selftests/net/ndisc_unsolicited_na_test.sh
index 5db69dad0cfc..ba9e670b5149 100755
--- a/tools/testing/selftests/net/ndisc_unsolicited_na_test.sh
+++ b/tools/testing/selftests/net/ndisc_unsolicited_na_test.sh
@@ -3,12 +3,18 @@
# This test is for the accept_untracked_na feature to
# enable RFC9131 behaviour. The following is the test-matrix.
-# drop accept fwding behaviour
-# ---- ------ ------ ----------------------------------------------
-# 1 X X Don't update NC
-# 0 0 X Don't update NC
-# 0 1 0 Don't update NC
-# 0 1 1 Add a STALE NC entry
+# state drop accept fwding behaviour
+# ------ ---- ------ ------ ----------------------------------------------
+# absent 1 X X Don't update NC
+# absent 0 0 X Don't update NC
+# absent 0 1 0 Don't update NC
+# absent 0 1 1 Add a STALE NC entry
+# failed 1 X X Keep the NC entry in FAILED state
+# failed 0 0 X Keep the NC entry in FAILED state
+# failed 0 1 0 Keep the NC entry in FAILED state
+# failed 0 1 1 Update the NC entry to STALE
+# failed 0 2 1 Update the NC entry to STALE if in-network
+# failed 0 2 1 Keep the NC entry FAILED if out-of-network
source lib.sh
ret=0
@@ -19,14 +25,18 @@ PAUSE=no
HOST_INTF="veth-host"
ROUTER_INTF="veth-router"
-ROUTER_ADDR="2000:20::1"
+ROUTER_ADDR_IN_NETWORK="2000:20::1"
+ROUTER_ADDR_OUT_OF_NETWORK="2000:21::1"
+ROUTER_ADDR="${ROUTER_ADDR_IN_NETWORK}"
HOST_ADDR="2000:20::2"
+HOST_LLADDR="02:00:00:00:00:02"
SUBNET_WIDTH=64
ROUTER_ADDR_WITH_MASK="${ROUTER_ADDR}/${SUBNET_WIDTH}"
HOST_ADDR_WITH_MASK="${HOST_ADDR}/${SUBNET_WIDTH}"
tcpdump_stdout=
tcpdump_stderr=
+tcpdump_pid=
log_test()
{
@@ -75,6 +85,7 @@ setup()
${IP_ROUTER} link add ${ROUTER_INTF} type veth \
peer name ${HOST_INTF} netns ${HOST_NS}
+ ${IP_HOST} link set dev "${HOST_INTF}" address "${HOST_LLADDR}"
# Enable IPv6 on both router and host, and configure static addresses.
# The router here is the DUT
@@ -88,6 +99,8 @@ setup()
${ROUTER_CONF}.drop_unsolicited_na=${drop_unsolicited_na}
${IP_ROUTER_EXEC} sysctl -qw \
${ROUTER_CONF}.accept_untracked_na=${accept_untracked_na}
+ ${IP_ROUTER_EXEC} sysctl -qw \
+ ${ROUTER_CONF}.ndisc_evict_nocarrier=0
${IP_ROUTER_EXEC} sysctl -qw ${ROUTER_CONF}.disable_ipv6=0
${IP_ROUTER} addr add ${ROUTER_ADDR_WITH_MASK} dev ${ROUTER_INTF}
@@ -102,24 +115,39 @@ setup()
}
start_tcpdump() {
- set -e
- tcpdump_stdout=`mktemp`
- tcpdump_stderr=`mktemp`
+ tcpdump_stdout=$(mktemp) || return 1
+ tcpdump_stderr=$(mktemp) || return 1
${IP_ROUTER_EXEC} timeout 15s \
tcpdump --immediate-mode -tpni ${ROUTER_INTF} -c 1 \
"icmp6 && icmp6[0] == 136 && src ${HOST_ADDR}" \
- > ${tcpdump_stdout} 2> /dev/null
- set +e
+ > "${tcpdump_stdout}" 2> "${tcpdump_stderr}" &
+ tcpdump_pid=$!
+
+ slowwait 5 grep -q "listening on ${ROUTER_INTF}" "${tcpdump_stderr}"
+}
+
+wait_tcpdump()
+{
+ local rc
+
+ wait "${tcpdump_pid}"
+ rc=$?
+ tcpdump_pid=
+
+ return "${rc}"
}
cleanup_tcpdump()
{
- set -e
- [[ ! -z ${tcpdump_stdout} ]] && rm -f ${tcpdump_stdout}
- [[ ! -z ${tcpdump_stderr} ]] && rm -f ${tcpdump_stderr}
+ if [ -n "${tcpdump_pid}" ]; then
+ kill "${tcpdump_pid}" 2> /dev/null
+ wait "${tcpdump_pid}" 2> /dev/null
+ fi
+ [ -n "${tcpdump_stdout}" ] && rm -f "${tcpdump_stdout}"
+ [ -n "${tcpdump_stderr}" ] && rm -f "${tcpdump_stderr}"
tcpdump_stdout=
tcpdump_stderr=
- set +e
+ tcpdump_pid=
}
cleanup()
@@ -129,58 +157,145 @@ cleanup()
ip netns del ${ROUTER_NS}
}
-link_up() {
- set -e
+router_link_up()
+{
${IP_ROUTER} link set dev ${ROUTER_INTF} up
+}
+
+host_link_up()
+{
${IP_HOST} link set dev ${HOST_INTF} up
- set +e
}
verify_ndisc() {
local drop_unsolicited_na=$1
local accept_untracked_na=$2
local forwarding=$3
+ local initial_state=${4:-absent}
+ local same_subnet=${5:-1}
+ local expected_lladdr
+ local neigh_show_output
+ local expected_state
+
+ if [ "${drop_unsolicited_na}" -eq 0 ] &&
+ [ "${forwarding}" -eq 1 ]; then
+ case "${accept_untracked_na}" in
+ 1)
+ expected_state=STALE
+ expected_lladdr="${HOST_LLADDR}"
+ ;;
+ 2)
+ if [ "${same_subnet}" -eq 1 ]; then
+ expected_state=STALE
+ expected_lladdr="${HOST_LLADDR}"
+ fi
+ ;;
+ esac
+ fi
+ if [ -z "${expected_state}" ] &&
+ [ "${initial_state}" = "failed" ]; then
+ expected_state=FAILED
+ fi
- neigh_show_output=$(${IP_ROUTER} neigh show \
- to ${HOST_ADDR} dev ${ROUTER_INTF} nud stale)
- if [ ${drop_unsolicited_na} -eq 0 ] && \
- [ ${accept_untracked_na} -eq 1 ] && \
- [ ${forwarding} -eq 1 ]; then
- # Neighbour entry expected to be present for 011 case
- [[ ${neigh_show_output} ]]
+ if [ -n "${expected_state}" ]; then
+ neigh_show_output=$(${IP_ROUTER} neigh show \
+ to "${HOST_ADDR}" dev "${ROUTER_INTF}")
+ if [[ " ${neigh_show_output} " != \
+ *" ${expected_state} "* ]]; then
+ return 1
+ fi
+ if [ -n "${expected_lladdr}" ] &&
+ [[ " ${neigh_show_output} " != \
+ *" lladdr ${expected_lladdr} "* ]]; then
+ return 1
+ fi
+ if [[ "${expected_state}" == "FAILED" &&
+ "${neigh_show_output}" == *"lladdr"* ]]; then
+ return 1
+ fi
+ if [ "${initial_state}" = "failed" ]; then
+ [[ "${neigh_show_output}" == *"extern_learn"* ]]
+ fi
else
- # Neighbour entry expected to be absent for all other cases
+ neigh_show_output=$(${IP_ROUTER} neigh show \
+ to "${HOST_ADDR}" dev "${ROUTER_INTF}")
[[ -z ${neigh_show_output} ]]
fi
}
test_unsolicited_na_common()
{
+ local same_subnet=${5:-1}
+ local neigh_show_output
+
+ if [ "${same_subnet}" -eq 1 ]; then
+ ROUTER_ADDR="${ROUTER_ADDR_IN_NETWORK}"
+ else
+ ROUTER_ADDR="${ROUTER_ADDR_OUT_OF_NETWORK}"
+ fi
+ ROUTER_ADDR_WITH_MASK="${ROUTER_ADDR}/${SUBNET_WIDTH}"
+
# Setup the test bed, but keep links down
- setup $1 $2 $3
+ setup "$1" "$2" "$3"
+
+ if [ "${4:-absent}" = "failed" ]; then
+ if ! ${IP_ROUTER} neigh replace "${HOST_ADDR}" \
+ dev "${ROUTER_INTF}" \
+ nud failed extern_learn; then
+ echo "Unable to create NUD_FAILED neighbor entry"
+ return 1
+ fi
+ neigh_show_output=$(${IP_ROUTER} neigh show \
+ to "${HOST_ADDR}" dev "${ROUTER_INTF}")
+ if [[ " ${neigh_show_output} " != *" FAILED "* ]]; then
+ echo "Unable to verify NUD_FAILED neighbor entry"
+ return 1
+ fi
+ if [[ "${neigh_show_output}" != *"extern_learn"* ]]; then
+ echo "Neighbor entry is not externally learned"
+ return 1
+ fi
+ fi
- # Bring the link up, wait for the NA,
- # and add a delay to ensure neighbour processing is done.
- link_up
- start_tcpdump
+ # Arm the capture before bringing up the host and starting DAD.
+ router_link_up || return 1
+ start_tcpdump || return 1
+ host_link_up || return 1
+
+ # Closing tcpdump's packet socket calls synchronize_net(), so waiting
+ # for it also waits for receive processing of the captured NA.
+ wait_tcpdump || return 1
# Verify the neighbour table
- verify_ndisc $1 $2 $3
+ verify_ndisc "$1" "$2" "$3" "$4" "${same_subnet}"
}
test_unsolicited_na_combination() {
- test_unsolicited_na_common $1 $2 $3
+ local initial_state=${4:-absent}
+ local same_subnet=${5:-1}
+ local rc
+
+ test_unsolicited_na_common "$1" "$2" "$3" "${initial_state}" \
+ "${same_subnet}"
+ rc=$?
test_msg=("test_unsolicited_na: "
"drop_unsolicited_na=$1 "
"accept_untracked_na=$2 "
"forwarding=$3")
- log_test $? 0 "${test_msg[*]}"
+ if [ "${initial_state}" = "failed" ]; then
+ test_msg+=("initial_state=failed")
+ fi
+ if [ "$2" -eq 2 ]; then
+ test_msg+=("same_subnet=${same_subnet}")
+ fi
+ log_test "${rc}" 0 "${test_msg[*]}"
cleanup
}
test_unsolicited_na_combinations() {
# Args: drop_unsolicited_na accept_untracked_na forwarding
+ # [initial_state] [same_subnet]
# Expect entry
test_unsolicited_na_combination 0 1 1
@@ -193,6 +308,16 @@ test_unsolicited_na_combinations() {
test_unsolicited_na_combination 1 0 1
test_unsolicited_na_combination 1 1 0
test_unsolicited_na_combination 1 1 1
+
+ # Expect FAILED entry to become STALE
+ test_unsolicited_na_combination 0 1 1 failed
+ test_unsolicited_na_combination 0 2 1 failed 1
+
+ # Expect FAILED entry to remain FAILED
+ test_unsolicited_na_combination 0 0 1 failed
+ test_unsolicited_na_combination 0 1 0 failed
+ test_unsolicited_na_combination 1 1 1 failed
+ test_unsolicited_na_combination 0 2 1 failed 0
}
###############################################################################
--
2.43.0
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [PATCH net-next v3 1/2] ipv6: update NUD_FAILED neighbors from NA messages
2026-09-18 22:13 ` [PATCH net-next v3 1/2] " Lawrence Lee
@ 2026-09-20 8:09 ` Ido Schimmel
2026-09-22 22:37 ` netdev-bot+sashiko
1 sibling, 0 replies; 8+ messages in thread
From: Ido Schimmel @ 2026-09-20 8:09 UTC (permalink / raw)
To: Lawrence Lee
Cc: David Ahern, David S. Miller, Eric Dumazet, Jakub Kicinski,
Paolo Abeni, Simon Horman, Randy Dunlap, netdev, Arun Ajith S,
Roopa Prabhu, Jaehee Park, Jonathan Corbet, Shuah Khan,
Shuah Khan, linux-doc, linux-kselftest, linux-kernel
On Fri, Sep 18, 2026 at 10:13:23PM +0000, Lawrence Lee wrote:
> Transition a FAILED neighbor entry to STALE upon receipt of an NA
> message on routers when accept_untracked_na is enabled. This extends the
> RFC 9131 accept_untracked_na behavior so that FAILED entries are treated
> the same as non-existent entries.
>
> RFC 4861 section 7.3.3 says that an entry should be deleted when address
> resolution fails. Linux instead retains the entry in NUD_FAILED, so
> treating it as untracked is consistent with the protocol model.
>
> Trying to resolve FAILED neighbors via periodic probing (e.g. using
> NTF_EXT_MANAGED) is more work compared to this approach which uses
> information in NAs that the kernel may already be receiving. Note that
> because this behavior in IPv6 is dependent on the accept_untracked_na
> sysctl setting, this approach is more conservative than IPv4 which
> transitions FAILED neighbors to STALE by default upon receiving GARPs.
>
> Link: https://lore.kernel.org/r/20260813233344.445265-1-lfqlee314@gmail.com
> Assisted-by: LLM Sashiko sparse
> Signed-off-by: Lawrence Lee <lfqlee314@gmail.com>
Reviewed-by: Ido Schimmel <idosch@nvidia.com>
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [PATCH net-next v3 1/2] ipv6: update NUD_FAILED neighbors from NA messages
2026-09-18 22:13 ` [PATCH net-next v3 1/2] " Lawrence Lee
2026-09-20 8:09 ` Ido Schimmel
@ 2026-09-22 22:37 ` netdev-bot+sashiko
2026-09-22 22:57 ` Lawrence Lee
1 sibling, 1 reply; 8+ messages in thread
From: netdev-bot+sashiko @ 2026-09-22 22:37 UTC (permalink / raw)
To: lfqlee314
Cc: dsahern, idosch, davem, edumazet, kuba, pabeni, horms, rdunlap,
netdev, aajith, roopa, jhpark1013, corbet, skhan, shuah,
linux-doc, linux-kselftest, linux-kernel
Thank you for your contribution! Sashiko AI review found more severe
issue(s) in other patches of this series. This mail is only an FYI, in case
you want to address the nit picks below when you respin.
Low priority / nit picks for your consideration:
- [Low] Claimed missing selftest coverage for the newly documented
FAILED->STALE behaviour of accept_untracked_na: the in-tree tests…
--
ipv6: update NUD_FAILED neighbors from NA messages
This changes ndisc_recv_na() so that a neighbor entry in NUD_FAILED is
treated like an absent entry and moved to STALE when accept_untracked_na
is enabled and forwarding is on. The ip-sysctl documentation for
accept_untracked_na is updated to describe the new FAILED handling.
Link: https://lore.kernel.org/r/20260813233344.445265-1-lfqlee314@gmail.com
> diff --git a/Documentation/networking/ip-sysctl.rst b/Documentation/networking/ip-sysctl.rst
> index f7af0286341c..685c84cf543d 100644
> --- a/Documentation/networking/ip-sysctl.rst
> +++ b/Documentation/networking/ip-sysctl.rst
> @@ -3225,18 +3225,19 @@ drop_unsolicited_na - BOOLEAN
> Default: 0 (disabled).
>
> accept_untracked_na - INTEGER
> - Define behavior for accepting neighbor advertisements from devices that
> - are absent in the neighbor cache:
> + Define behavior for accepting neighbor advertisements for IPv6 addresses
> + that are absent from the neighbor cache or whose entries are in FAILED
> + state:
>
> - - 0 - (default) Do not accept unsolicited and untracked neighbor
> - advertisements.
> + - 0 - (default) Do not create new neighbor cache entries or update
> + FAILED entries from neighbor advertisements.
>
> - - 1 - Add a new neighbor cache entry in STALE state for routers on
> - receiving a neighbor advertisement (either solicited or unsolicited)
> - with target link-layer address option specified if no neighbor entry
> - is already present for the advertised IPv6 address. Without this knob,
> - NAs received for untracked addresses (absent in neighbor cache) are
> - silently ignored.
> + - 1 - For routers, add a new neighbor cache entry or update an existing
> + FAILED entry to STALE upon receiving a neighbor advertisement (either
> + solicited or unsolicited) with the target link-layer address option
> + specified. Without this knob, NAs received for untracked addresses
> + (absent from the neighbor cache or in FAILED state) are silently
> + ignored.
>
> This is as per router-side behavior documented in RFC9131.
>
> @@ -3251,9 +3252,10 @@ accept_untracked_na - INTEGER
> used in conjunction with the ndisc_notify setting on the host to
> satisfy this prerequisite.
>
> - - 2 - Extend option (1) to add a new neighbor cache entry only if the
> - source IP address is in the same subnet as an address configured on
> - the interface that received the neighbor advertisement.
> + - 2 - Extend option (1) to add a new neighbor cache entry or update a
> + FAILED entry only if the source IP address is in the same subnet as
> + an address configured on the interface that received the neighbor
> + advertisement.
[ ... ]
> diff --git a/net/ipv6/ndisc.c b/net/ipv6/ndisc.c
> index 90cd5d852569..12d85d7f8234 100644
> --- a/net/ipv6/ndisc.c
> +++ b/net/ipv6/ndisc.c
[ ... ]
> @@ -1067,34 +1067,39 @@ static enum skb_drop_reason ndisc_recv_na(struct sk_buff *skb)
> new_state = msg->icmph.icmp6_solicited ? NUD_REACHABLE : NUD_STALE;
> - if (!neigh && lladdr && idev && READ_ONCE(idev->cnf.forwarding)) {
> - if (accept_untracked_na(idev, saddr)) {
> - neigh = neigh_create(tbl, &msg->target, dev);
> - new_state = NUD_STALE;
> + if (!neigh || (READ_ONCE(neigh->nud_state) & NUD_FAILED)) {
> + if (!lladdr || !idev || !READ_ONCE(idev->cnf.forwarding) ||
> + !accept_untracked_na(idev, saddr)) {
> + if (neigh)
> + neigh_release(neigh);
> + return reason;
> }
> + if (!neigh)
> + neigh = neigh_create(tbl, &msg->target, dev);
> + new_state = NUD_STALE;
> }
[Severity: Low]
This isn't a bug, but a note on test coverage for the new FAILED branch in
ndisc_recv_na().
At the time this patch is applied on its own, the in-tree selftests only
walk the "absent entry" rows of the matrix: the matrix comment in
tools/testing/selftests/net/ndisc_unsolicited_na_test.sh and verify_ndisc()
start from an empty neighbor cache, and arp_ndisc_untracked_subnets.sh does
the same for the accept=2 subnet rule. That leaves the new
if (!neigh || (READ_ONCE(neigh->nud_state) & NUD_FAILED)) {
path, and the FAILED rows now documented for accept_untracked_na, without a
test.
This is addressed later in the same series by "selftests: net: test
untracked NA recovery of FAILED neighbors", which extends the matrix
comment in ndisc_unsolicited_na_test.sh with the six "failed" rows, adds
initial_state/same_subnet parameters to verify_ndisc() and
test_unsolicited_na_common() that seed the entry with
ip neigh replace ${HOST_ADDR} dev ${ROUTER_INTF} nud failed extern_learn
and then adds cases for accept=1, accept=0, forwarding=0, drop=1 and both
in-prefix and out-of-prefix accept=2, checking that the lladdr is learned
for the STALE rows and absent for the rows that must stay FAILED. So the
gap exists only for this commit in isolation, not for the final state of
the series.
Would it be worth mentioning the follow-up selftest patch in this commit
message so the coverage relationship is visible when this commit is read
alone?
--
Sashiko AI review · https://netdev-ai.bots.linux.dev/sashiko/#/patchset/cover.1789734885.git.lfqlee314%40gmail.com
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [PATCH net-next v3 2/2] selftests: net: test untracked NA recovery of FAILED neighbors
2026-09-18 22:13 ` [PATCH net-next v3 2/2] selftests: net: test untracked NA recovery of FAILED neighbors Lawrence Lee
@ 2026-09-22 22:38 ` netdev-bot+sashiko
2026-09-23 1:20 ` Lawrence Lee
0 siblings, 1 reply; 8+ messages in thread
From: netdev-bot+sashiko @ 2026-09-22 22:38 UTC (permalink / raw)
To: lfqlee314
Cc: dsahern, idosch, davem, edumazet, kuba, pabeni, horms, rdunlap,
netdev, aajith, roopa, jhpark1013, corbet, skhan, shuah,
linux-doc, linux-kselftest, linux-kernel
Thank you for your contribution! Sashiko AI review found 2 potential
issue(s) to consider.
Critical: 0 · High: 0 · Medium: 1 · Low: 1 (1)
If you believe none of the issues are legitimate, please reply to each
issue of Medium severity or higher and explain why the AI is wrong.
If any of them are legitimate and you plan to respin, please let patchwork
know by including "pw-bot: cr" as a separate line at the end of your reply
(one such reply per series is enough).
- [Medium] Undisclosed fix of a pre-existing false-PASS defect, without a
Fixes: tag.
- [Low] No `trap cleanup EXIT INT TERM` is registered, while the patch
converts tcpdump from a foreground command into a backgrounded child…
Pre-existing issues:
- [Low] Claimed issue (validated as a pre-existing Low-severity
robustness nit): in verify_ndisc(), the absent-entry branch (lines…
--
selftests: net: test untracked NA recovery of FAILED neighbors
This extends the accept_untracked_na selftest to seed a FAILED neighbour
entry before triggering an unsolicited NA, and checks the resulting state,
link-layer address and extern_learn marker for modes 1 and 2. It also
reworks the tcpdump handling so the capture is armed before the host link
comes up and is waited for before the neighbour table is inspected.
Link: https://lore.kernel.org/r/20260813233344.445265-1-lfqlee314@gmail.com
A few questions below.
> diff --git a/tools/testing/selftests/net/ndisc_unsolicited_na_test.sh b/tools/testing/selftests/net/ndisc_unsolicited_na_test.sh
> index 5db69dad0cfc..ba9e670b5149 100755
> --- a/tools/testing/selftests/net/ndisc_unsolicited_na_test.sh
> +++ b/tools/testing/selftests/net/ndisc_unsolicited_na_test.sh
[ ... ]
> @@ -102,24 +115,39 @@ setup()
> }
>
> start_tcpdump() {
> - set -e
> - tcpdump_stdout=`mktemp`
> - tcpdump_stderr=`mktemp`
> + tcpdump_stdout=$(mktemp) || return 1
> + tcpdump_stderr=$(mktemp) || return 1
> ${IP_ROUTER_EXEC} timeout 15s \
> tcpdump --immediate-mode -tpni ${ROUTER_INTF} -c 1 \
> "icmp6 && icmp6[0] == 136 && src ${HOST_ADDR}" \
> - > ${tcpdump_stdout} 2> /dev/null
> - set +e
> + > "${tcpdump_stdout}" 2> "${tcpdump_stderr}" &
> + tcpdump_pid=$!
> +
> + slowwait 5 grep -q "listening on ${ROUTER_INTF}" "${tcpdump_stderr}"
> +}
> +
> +wait_tcpdump()
> +{
> + local rc
> +
> + wait "${tcpdump_pid}"
> + rc=$?
> + tcpdump_pid=
> +
> + return "${rc}"
> }
>
> cleanup_tcpdump()
> {
> - set -e
> - [[ ! -z ${tcpdump_stdout} ]] && rm -f ${tcpdump_stdout}
> - [[ ! -z ${tcpdump_stderr} ]] && rm -f ${tcpdump_stderr}
> + if [ -n "${tcpdump_pid}" ]; then
> + kill "${tcpdump_pid}" 2> /dev/null
> + wait "${tcpdump_pid}" 2> /dev/null
> + fi
[Severity: Low]
tcpdump is now a background child, and cleanup_tcpdump() is the only place
that kills and reaps it. Can that child be left running when the script
leaves through a path that never reaches cleanup()?
cleanup_tcpdump() is reached only from cleanup(), which runs at the tail of
test_unsolicited_na_combination() after log_test() returns:
log_test "${rc}" 0 "${test_msg[*]}"
cleanup
log_test() can exit first when the script is run with -p or -P and the
operator answers 'q':
if [ "${PAUSE}" = "yes" ]; then
echo
echo "hit enter to continue, 'q' to quit"
read a
[ "$a" = "q" ] && exit 1
fi
setup() also runs under set -e, so a failing sysctl there (for example
accept_untracked_na=2 on a kernel without mode 2) exits the shell directly.
There is no trap cleanup EXIT INT TERM anywhere in the file, so in those
cases the two namespaces from setup_ns and both mktemp files are left
behind, and if the failure happens between start_tcpdump() and
wait_tcpdump() (for instance the new slowwait 5 grep for "listening on"
timing out, or host_link_up failing) a live timeout 15s tcpdump keeps a
packet socket and a netns reference until its own timeout expires.
Would adding a trap that calls cleanup on EXIT, INT and TERM be reasonable
here?
> + [ -n "${tcpdump_stdout}" ] && rm -f "${tcpdump_stdout}"
> + [ -n "${tcpdump_stderr}" ] && rm -f "${tcpdump_stderr}"
> tcpdump_stdout=
> tcpdump_stderr=
> - set +e
> + tcpdump_pid=
> }
>
> cleanup()
[ ... ]
> @@ -129,58 +157,145 @@ cleanup()
[ ... ]
> + if [ -n "${expected_state}" ]; then
> + neigh_show_output=$(${IP_ROUTER} neigh show \
> + to "${HOST_ADDR}" dev "${ROUTER_INTF}")
[ ... ]
> else
> - # Neighbour entry expected to be absent for all other cases
> + neigh_show_output=$(${IP_ROUTER} neigh show \
> + to "${HOST_ADDR}" dev "${ROUTER_INTF}")
> [[ -z ${neigh_show_output} ]]
> fi
> }
[Severity: Low]
This isn't a problem introduced by this patch, but the absent-entry branch
of verify_ndisc() still discards the exit status of ip neigh show and only
tests that the output is empty. If the command itself fails, is the empty
output then reported as a pass without the neighbour table ever having been
read? The same pattern is present in the baseline version of the function,
so this is pre-existing; the new expected_state branch fails closed. Would
checking the exit status of the query in the else branch be worth folding
in while this function is being touched?
>
> test_unsolicited_na_common()
> {
[ ... ]
> - # Bring the link up, wait for the NA,
> - # and add a delay to ensure neighbour processing is done.
> - link_up
> - start_tcpdump
> + # Arm the capture before bringing up the host and starting DAD.
> + router_link_up || return 1
> + start_tcpdump || return 1
> + host_link_up || return 1
> +
> + # Closing tcpdump's packet socket calls synchronize_net(), so waiting
> + # for it also waits for receive processing of the captured NA.
> + wait_tcpdump || return 1
>
> # Verify the neighbour table
> - verify_ndisc $1 $2 $3
> + verify_ndisc "$1" "$2" "$3" "$4" "${same_subnet}"
>
> }
>
> test_unsolicited_na_combination() {
> - test_unsolicited_na_common $1 $2 $3
> + local initial_state=${4:-absent}
> + local same_subnet=${5:-1}
> + local rc
> +
> + test_unsolicited_na_common "$1" "$2" "$3" "${initial_state}" \
> + "${same_subnet}"
> + rc=$?
> test_msg=("test_unsolicited_na: "
> "drop_unsolicited_na=$1 "
> "accept_untracked_na=$2 "
> "forwarding=$3")
> - log_test $? 0 "${test_msg[*]}"
> + if [ "${initial_state}" = "failed" ]; then
> + test_msg+=("initial_state=failed")
> + fi
> + if [ "$2" -eq 2 ]; then
> + test_msg+=("same_subnet=${same_subnet}")
> + fi
> + log_test "${rc}" 0 "${test_msg[*]}"
> cleanup
> }
[Severity: Medium]
The new rc=$? capture also repairs a reporting bug that existed before this
patch. In the baseline the sequence was:
test_unsolicited_na_common $1 $2 $3
test_msg=("test_unsolicited_na: "
"drop_unsolicited_na=$1 "
"accept_untracked_na=$2 "
"forwarding=$3")
log_test $? 0 "${test_msg[*]}"
The array assignment between the helper call and log_test sets $? to 0
(none of the assigned words contain a command substitution), so log_test
always received 0 and all eight existing combinations reported OK no matter
what verify_ndisc returned. Capturing rc immediately after
test_unsolicited_na_common() changes the pass/fail semantics of those eight
pre-existing cases so they can now actually fail.
The changelog describes only the new FAILED-neighbour coverage and does not
mention that the existing reporting was broken, and there is no Fixes: tag
(git blame points the log_test $? line at f9a2fb73318eb).
Would it make sense to split this into its own patch with a Fixes: tag, so
it can be applied and backported independently of the new mode 2 and
FAILED-state coverage, which needs kernel features not present in older
trees?
[ ... ]
--
Sashiko AI review · https://netdev-ai.bots.linux.dev/sashiko/#/patchset/cover.1789734885.git.lfqlee314%40gmail.com
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [PATCH net-next v3 1/2] ipv6: update NUD_FAILED neighbors from NA messages
2026-09-22 22:37 ` netdev-bot+sashiko
@ 2026-09-22 22:57 ` Lawrence Lee
0 siblings, 0 replies; 8+ messages in thread
From: Lawrence Lee @ 2026-09-22 22:57 UTC (permalink / raw)
To: netdev-bot+sashiko
Cc: dsahern, idosch, davem, edumazet, kuba, pabeni, horms, rdunlap,
netdev, aajith, roopa, jhpark1013, corbet, skhan, shuah,
linux-doc, linux-kselftest, linux-kernel
On Tue Sep 22, 2026 at 10:37 PM UTC, wrote:
> [Severity: Low]
> This isn't a bug, but a note on test coverage for the new FAILED branch in
> ndisc_recv_na().
>
> At the time this patch is applied on its own, the in-tree selftests only
> walk the "absent entry" rows of the matrix: the matrix comment in
> tools/testing/selftests/net/ndisc_unsolicited_na_test.sh and verify_ndisc()
> start from an empty neighbor cache, and arp_ndisc_untracked_subnets.sh does
> the same for the accept=2 subnet rule. That leaves the new
>
> if (!neigh || (READ_ONCE(neigh->nud_state) & NUD_FAILED)) {
>
> path, and the FAILED rows now documented for accept_untracked_na, without a
> test.
>
> This is addressed later in the same series by "selftests: net: test
> untracked NA recovery of FAILED neighbors", which extends the matrix
> comment in ndisc_unsolicited_na_test.sh with the six "failed" rows, adds
> initial_state/same_subnet parameters to verify_ndisc() and
> test_unsolicited_na_common() that seed the entry with
>
> ip neigh replace ${HOST_ADDR} dev ${ROUTER_INTF} nud failed extern_learn
>
> and then adds cases for accept=1, accept=0, forwarding=0, drop=1 and both
> in-prefix and out-of-prefix accept=2, checking that the lladdr is learned
> for the STALE rows and absent for the rows that must stay FAILED. So the
> gap exists only for this commit in isolation, not for the final state of
> the series.
>
> Would it be worth mentioning the follow-up selftest patch in this commit
> message so the coverage relationship is visible when this commit is read
> alone?
The cover letter already mentions that tests are added in a separate
patch in this series. I'm not aware of any precedent or convention to
mention follow-up selftest patches in commit messages for earlier
patches in the series.
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [PATCH net-next v3 2/2] selftests: net: test untracked NA recovery of FAILED neighbors
2026-09-22 22:38 ` netdev-bot+sashiko
@ 2026-09-23 1:20 ` Lawrence Lee
0 siblings, 0 replies; 8+ messages in thread
From: Lawrence Lee @ 2026-09-23 1:20 UTC (permalink / raw)
To: netdev-bot+sashiko
Cc: dsahern, idosch, davem, edumazet, kuba, pabeni, horms, rdunlap,
netdev, aajith, roopa, jhpark1013, corbet, skhan, shuah,
linux-doc, linux-kselftest, linux-kernel
On Tue Sep 22, 2026 at 10:38 PM UTC, wrote:
> [Severity: Low]
> tcpdump is now a background child, and cleanup_tcpdump() is the only place
> that kills and reaps it. Can that child be left running when the script
> leaves through a path that never reaches cleanup()?
>
> cleanup_tcpdump() is reached only from cleanup(), which runs at the tail of
> test_unsolicited_na_combination() after log_test() returns:
>
> log_test "${rc}" 0 "${test_msg[*]}"
> cleanup
>
> log_test() can exit first when the script is run with -p or -P and the
> operator answers 'q':
>
> if [ "${PAUSE}" = "yes" ]; then
> echo
> echo "hit enter to continue, 'q' to quit"
> read a
> [ "$a" = "q" ] && exit 1
> fi
>
> setup() also runs under set -e, so a failing sysctl there (for example
> accept_untracked_na=2 on a kernel without mode 2) exits the shell directly.
> There is no trap cleanup EXIT INT TERM anywhere in the file, so in those
> cases the two namespaces from setup_ns and both mktemp files are left
> behind, and if the failure happens between start_tcpdump() and
> wait_tcpdump() (for instance the new slowwait 5 grep for "listening on"
> timing out, or host_link_up failing) a live timeout 15s tcpdump keeps a
> packet socket and a netns reference until its own timeout expires.
>
> Would adding a trap that calls cleanup on EXIT, INT and TERM be reasonable
> here?
>
I would lean towards no, since tcpdump already times out on its own and
any orphaned tempfiles or netns are a pre-existing issue. No change
planned.
> [Severity: Low]
> This isn't a problem introduced by this patch, but the absent-entry branch
> of verify_ndisc() still discards the exit status of ip neigh show and only
> tests that the output is empty. If the command itself fails, is the empty
> output then reported as a pass without the neighbour table ever having been
> read? The same pattern is present in the baseline version of the function,
> so this is pre-existing; the new expected_state branch fails closed. Would
> checking the exit status of the query in the else branch be worth folding
> in while this function is being touched?
>
Pre-existing issue, will leave as-is
> [Severity: Medium]
> The new rc=$? capture also repairs a reporting bug that existed before this
> patch. In the baseline the sequence was:
>
> test_unsolicited_na_common $1 $2 $3
> test_msg=("test_unsolicited_na: "
> "drop_unsolicited_na=$1 "
> "accept_untracked_na=$2 "
> "forwarding=$3")
> log_test $? 0 "${test_msg[*]}"
>
> The array assignment between the helper call and log_test sets $? to 0
> (none of the assigned words contain a command substitution), so log_test
> always received 0 and all eight existing combinations reported OK no matter
> what verify_ndisc returned. Capturing rc immediately after
> test_unsolicited_na_common() changes the pass/fail semantics of those eight
> pre-existing cases so they can now actually fail.
>
> The changelog describes only the new FAILED-neighbour coverage and does not
> mention that the existing reporting was broken, and there is no Fixes: tag
> (git blame points the log_test $? line at f9a2fb73318eb).
>
> Would it make sense to split this into its own patch with a Fixes: tag, so
> it can be applied and backported independently of the new mode 2 and
> FAILED-state coverage, which needs kernel features not present in older
> trees?
>
An entirely new patch submission seems like overkill for this. I'll
update the commit message to mention this change and add the Fixes tag.
pw-bot: changes-requested
^ permalink raw reply [flat|nested] 8+ messages in thread
end of thread, other threads:[~2026-09-23 1:20 UTC | newest]
Thread overview: 8+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-09-18 22:13 [PATCH net-next v3 0/2] ipv6: update NUD_FAILED neighbors from NA messages Lawrence Lee
2026-09-18 22:13 ` [PATCH net-next v3 1/2] " Lawrence Lee
2026-09-20 8:09 ` Ido Schimmel
2026-09-22 22:37 ` netdev-bot+sashiko
2026-09-22 22:57 ` Lawrence Lee
2026-09-18 22:13 ` [PATCH net-next v3 2/2] selftests: net: test untracked NA recovery of FAILED neighbors Lawrence Lee
2026-09-22 22:38 ` netdev-bot+sashiko
2026-09-23 1:20 ` Lawrence Lee
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
all inboxes | Powered by JetHome®