From nobody Sat Oct 7 17:16:55 2023 X-Original-To: dev-commits-src-all@mlmmj.nyi.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2610:1c1:1:606c::19:1]) by mlmmj.nyi.freebsd.org (Postfix) with ESMTP id 4S2sRC6Z8Sz4x1bT; Sat, 7 Oct 2023 17:16:55 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from mxrelay.nyi.freebsd.org (mxrelay.nyi.freebsd.org [IPv6:2610:1c1:1:606c::19:3]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256 client-signature RSA-PSS (4096 bits) client-digest SHA256) (Client CN "mxrelay.nyi.freebsd.org", Issuer "R3" (verified OK)) by mx1.freebsd.org (Postfix) with ESMTPS id 4S2sRC5qGrz3SMW; Sat, 7 Oct 2023 17:16:55 +0000 (UTC) (envelope-from git@FreeBSD.org) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=freebsd.org; s=dkim; t=1696699015; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=+awxEkHhx9kkVByTgm/gxkOH9sYBmM0rwBEOvqTao90=; b=xIyQwosO8Kc5AGsoY9J5HaukLNMQaGIQF4vmAL3U4WezNZtw6tIR5k5pkus7X/VaTVrKWa oJKVx4ZpP0GwitCLa+MLXmpJz6NdpOAwPti9QZoSV2c8q2LTT+aQ2CTTs+wZErfsIWZi5x 4ITbSkSaohKvDVwGFihORTc7XA4ERizsdfEmNIzPqYub7UytNnS4kvWkQEcM/BmLshpPGj WwdTLKdh9sNVhIKf3BqCGVCiKuIObKrP/pHLby8Pz4FuRC87tDa+wuvhN9UWEpDYhO7NtY NayvaUhbM693xiL3/aJRbM0KF53WiK+sraVMkVFFdWDcKEjUdRbXUGGcSWTCwQ== ARC-Seal: i=1; s=dkim; d=freebsd.org; t=1696699015; a=rsa-sha256; cv=none; b=qS2YRE26SXkd/xyvXtrDFpU+8Ptycqnfxp1hdgtxpz75wOQ/EVXp2XjT4vwhaFwSu7jB5J AEfkceMltPavO55+mkUDfv3K+VHklpdjaoKSZ+fP6+cHNulpnSTh5rVi6+Y6H+RKljuwwm K6hkr+26XWQcjrGY7W40qC4hsi2UZ76tbEbi1Q92SAGj2+OaobLonQa7nMUt7tLWqVMIBP DGaD3LY3FzPDmgxUKb5uOxz8txArRDngngG99b55MCngFJzs+fKb4R7Quc1WB2O5/B1yZF p0Od3QbAL9WT05c5m87+eUUE86eX4SGzCLeVzfHmD4YQ50kJXAjOQ5wWfT+/sQ== ARC-Authentication-Results: i=1; mx1.freebsd.org; none ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=freebsd.org; s=dkim; t=1696699015; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=+awxEkHhx9kkVByTgm/gxkOH9sYBmM0rwBEOvqTao90=; b=oWD5KQzfzqrZkTpDw0+ZX9DZ1vCbR6/ko2TF6eLpRcnFy+T9GKCxcOAS72szTDCHEj7iDs LYUb5uUAE28thrsr0M32oAfWW4QWJC/O/Ik2yQ232MrTLfnV7AovkY8aIc6eO/2fnyV//+ IH18u5qF7m2DXqoVitu9DZk0Z5MBVH8opd7arOz59h9sJhocRazEMtsKgnjnb/vzC4OlmU qPit1wUQtOnFcNhG/cwVv0YwSkTvfqI+BWDaRd0CGx07P0Eru6bUoxYA4f3xa+yIzhg5QS bxuzOHdGq7LZMD4sOpDHRn82L44lgrHwoFaGwutrl3frlZ/LAi1uymy+1lOkHw== Received: from gitrepo.freebsd.org (gitrepo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:5]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256) (Client did not present a certificate) by mxrelay.nyi.freebsd.org (Postfix) with ESMTPS id 4S2sRC4ZH7zfK3; Sat, 7 Oct 2023 17:16:55 +0000 (UTC) (envelope-from git@FreeBSD.org) Received: from gitrepo.freebsd.org ([127.0.1.44]) by gitrepo.freebsd.org (8.17.1/8.17.1) with ESMTP id 397HGt6E070546; Sat, 7 Oct 2023 17:16:55 GMT (envelope-from git@gitrepo.freebsd.org) Received: (from git@localhost) by gitrepo.freebsd.org (8.17.1/8.17.1/Submit) id 397HGtqr070543; Sat, 7 Oct 2023 17:16:55 GMT (envelope-from git) Date: Sat, 7 Oct 2023 17:16:55 GMT Message-Id: <202310071716.397HGtqr070543@gitrepo.freebsd.org> To: src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org, dev-commits-src-branches@FreeBSD.org From: Kristof Provost Subject: git: 0b42158e5ef5 - releng/14.0 - pf: cope with missing rpool.cur List-Id: Commit messages for all branches of the src repository List-Archive: https://lists.freebsd.org/archives/dev-commits-src-all List-Help: List-Post: List-Subscribe: List-Unsubscribe: Sender: owner-dev-commits-src-all@freebsd.org X-BeenThere: dev-commits-src-all@freebsd.org MIME-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 8bit X-Git-Committer: kp X-Git-Repository: src X-Git-Refname: refs/heads/releng/14.0 X-Git-Reftype: branch X-Git-Commit: 0b42158e5ef5b2d9ed05bc8dff7fbfd106e1bcac Auto-Submitted: auto-generated The branch releng/14.0 has been updated by kp: URL: https://cgit.FreeBSD.org/src/commit/?id=0b42158e5ef5b2d9ed05bc8dff7fbfd106e1bcac commit 0b42158e5ef5b2d9ed05bc8dff7fbfd106e1bcac Author: Kristof Provost AuthorDate: 2023-10-03 15:11:44 +0000 Commit: Kristof Provost CommitDate: 2023-10-07 17:16:25 +0000 pf: cope with missing rpool.cur If we're evaluating a pfsync'd state (and have different rules on both ends) our state may point to the default rule, which does not have rpool.cur set. As a result we can end up dereferencing a NULL pointer. Explicitly check for this when we try to re-construct the route-to interface. Also add a test case which can trigger this issue. MFC after: 3 days See also: https://redmine.pfsense.org/issues/14804 Sponsored by: Rubicon Communications, LLC ("Netgate") Approved by: gjb (re) (cherry picked from commit 74c2461386ea5eeb41e674df6b16a44b0509a882) (cherry picked from commit f69181e9de1b021f4689ce50b420f9c694268ec8) --- sys/netpfil/pf/pf.c | 9 ++-- tests/sys/netpfil/pf/pfsync.sh | 96 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 101 insertions(+), 4 deletions(-) diff --git a/sys/netpfil/pf/pf.c b/sys/netpfil/pf/pf.c index a5d7c1ba0155..0973c829644a 100644 --- a/sys/netpfil/pf/pf.c +++ b/sys/netpfil/pf/pf.c @@ -6737,7 +6737,7 @@ pf_route(struct mbuf **m, struct pf_krule *r, struct ifnet *oifp, } else { ifp = s->rt_kif ? s->rt_kif->pfik_ifp : NULL; /* If pfsync'd */ - if (ifp == NULL) + if (ifp == NULL && r->rpool.cur != NULL) ifp = r->rpool.cur->kif ? r->rpool.cur->kif->pfik_ifp : NULL; PF_STATE_UNLOCK(s); @@ -6794,9 +6794,10 @@ pf_route(struct mbuf **m, struct pf_krule *r, struct ifnet *oifp, s->rt_addr.v4.s_addr; ifp = s->rt_kif ? s->rt_kif->pfik_ifp : NULL; /* If pfsync'd */ - if (ifp == NULL) + if (ifp == NULL && r->rpool.cur != NULL) { ifp = r->rpool.cur->kif ? r->rpool.cur->kif->pfik_ifp : NULL; + } PF_STATE_UNLOCK(s); } @@ -6950,7 +6951,7 @@ pf_route6(struct mbuf **m, struct pf_krule *r, struct ifnet *oifp, } else { ifp = s->rt_kif ? s->rt_kif->pfik_ifp : NULL; /* If pfsync'd */ - if (ifp == NULL) + if (ifp == NULL && r->rpool.cur != NULL) ifp = r->rpool.cur->kif ? r->rpool.cur->kif->pfik_ifp : NULL; PF_STATE_UNLOCK(s); @@ -7008,7 +7009,7 @@ pf_route6(struct mbuf **m, struct pf_krule *r, struct ifnet *oifp, &s->rt_addr, AF_INET6); ifp = s->rt_kif ? s->rt_kif->pfik_ifp : NULL; /* If pfsync'd */ - if (ifp == NULL) + if (ifp == NULL && r->rpool.cur != NULL) ifp = r->rpool.cur->kif ? r->rpool.cur->kif->pfik_ifp : NULL; } diff --git a/tests/sys/netpfil/pf/pfsync.sh b/tests/sys/netpfil/pf/pfsync.sh index d62cdddd504a..91c7b8410a08 100644 --- a/tests/sys/netpfil/pf/pfsync.sh +++ b/tests/sys/netpfil/pf/pfsync.sh @@ -825,6 +825,101 @@ basic_ipv6_cleanup() pfsynct_cleanup } +atf_test_case "route_to" "cleanup" +route_to_head() +{ + atf_set descr 'Test route-to with default rule' + atf_set require.user root + atf_set require.progs scapy +} + +route_to_body() +{ + pfsynct_init + + epair_sync=$(vnet_mkepair) + epair_one=$(vnet_mkepair) + epair_two=$(vnet_mkepair) + epair_out_one=$(vnet_mkepair) + epair_out_two=$(vnet_mkepair) + + vnet_mkjail one ${epair_one}a ${epair_sync}a ${epair_out_one}a + vnet_mkjail two ${epair_two}a ${epair_sync}b ${epair_out_two}a + + # pfsync interface + jexec one ifconfig ${epair_sync}a 192.0.2.1/24 up + jexec one ifconfig ${epair_one}a 198.51.100.1/24 up + jexec one ifconfig ${epair_out_one}a 203.0.113.1/24 up + jexec one ifconfig ${epair_out_one}a name outif + jexec one sysctl net.inet.ip.forwarding=1 + jexec one arp -s 203.0.113.254 00:01:02:03:04:05 + jexec one ifconfig pfsync0 \ + syncdev ${epair_sync}a \ + maxupd 1 \ + up + + jexec two ifconfig ${epair_sync}b 192.0.2.2/24 up + jexec two ifconfig ${epair_two}a 198.51.100.2/24 up + jexec two ifconfig ${epair_out_two}a 203.0.113.2/24 up + #jexec two ifconfig ${epair_out_two}a name outif + jexec two sysctl net.inet.ip.forwarding=1 + jexec two arp -s 203.0.113.254 00:01:02:03:04:05 + jexec two ifconfig pfsync0 \ + syncdev ${epair_sync}b \ + maxupd 1 \ + up + + # Enable pf! + jexec one pfctl -e + pft_set_rules one \ + "set skip on ${epair_sync}a" \ + "pass out route-to (outif 203.0.113.254)" + jexec two pfctl -e + + # Make sure we have different rulesets so the synced state is associated with + # V_pf_default_rule + pft_set_rules two \ + "set skip on ${epair_sync}b" \ + "pass out route-to (outif 203.0.113.254)" \ + "pass out proto tcp" + + ifconfig ${epair_one}b 198.51.100.254/24 up + ifconfig ${epair_two}b 198.51.100.253/24 up + route add -net 203.0.113.0/24 198.51.100.1 + ifconfig ${epair_two}b up + ifconfig ${epair_out_one}b up + ifconfig ${epair_out_two}b up + + atf_check -s exit:0 env PYTHONPATH=${common_dir} \ + ${common_dir}/pft_ping.py \ + --sendif ${epair_one}b \ + --fromaddr 198.51.100.254 \ + --to 203.0.113.254 \ + --recvif ${epair_out_one}b + + # Allow time for sync + ifconfig ${epair_one}b inet 198.51.100.254 -alias + route del -net 203.0.113.0/24 198.51.100.1 + route add -net 203.0.113.0/24 198.51.100.2 + + sleep 2 + + # Now try to trigger the state on the other pfsync member + env PYTHONPATH=${common_dir} \ + ${common_dir}/pft_ping.py \ + --sendif ${epair_two}b \ + --fromaddr 198.51.100.254 \ + --to 203.0.113.254 \ + --recvif ${epair_out_two}b + + true +} + +route_to_cleanup() +{ + pfsynct_cleanup +} + atf_init_test_cases() { atf_add_test_case "basic" @@ -837,4 +932,5 @@ atf_init_test_cases() atf_add_test_case "timeout" atf_add_test_case "basic_ipv6_unicast" atf_add_test_case "basic_ipv6" + atf_add_test_case "route_to" }