1#- 2# SPDX-License-Identifier: BSD-2-Clause-FreeBSD 3# 4# Copyright (c) 2019 Ahsan Barkati 5# 6# Redistribution and use in source and binary forms, with or without 7# modification, are permitted provided that the following conditions 8# are met: 9# 1. Redistributions of source code must retain the above copyright 10# notice, this list of conditions and the following disclaimer. 11# 2. Redistributions in binary form must reproduce the above copyright 12# notice, this list of conditions and the following disclaimer in the 13# documentation and/or other materials provided with the distribution. 14# 15# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 16# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 17# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 18# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 19# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 20# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 21# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 23# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 24# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 25# SUCH DAMAGE. 26# 27# $FreeBSD$ 28# 29 30. $(atf_get_srcdir)/utils.subr 31. $(atf_get_srcdir)/runner.subr 32 33basic_head() 34{ 35 atf_set descr 'Basic IPv4 NAT test' 36 atf_set require.user root 37} 38 39basic_body() 40{ 41 firewall=$1 42 firewall_init $firewall 43 nat_init $firewall 44 45 epair_host_nat=$(vnet_mkepair) 46 epair_client1_nat=$(vnet_mkepair) 47 epair_client2_nat=$(vnet_mkepair) 48 49 vnet_mkjail nat ${epair_host_nat}b ${epair_client1_nat}a ${epair_client2_nat}a 50 vnet_mkjail client1 ${epair_client1_nat}b 51 vnet_mkjail client2 ${epair_client2_nat}b 52 53 ifconfig ${epair_host_nat}a 198.51.100.2/24 up 54 jexec nat ifconfig ${epair_host_nat}b 198.51.100.1/24 up 55 56 jexec nat ifconfig ${epair_client1_nat}a 192.0.2.1/24 up 57 jexec client1 ifconfig ${epair_client1_nat}b 192.0.2.2/24 up 58 59 jexec nat ifconfig ${epair_client2_nat}a 192.0.3.1/24 up 60 jexec client2 ifconfig ${epair_client2_nat}b 192.0.3.2/24 up 61 62 jexec nat sysctl net.inet.ip.forwarding=1 63 64 jexec client1 route add -net 198.51.100.0/24 192.0.2.1 65 jexec client2 route add -net 198.51.100.0/24 192.0.3.1 66 67 # ping fails without NAT configuration 68 atf_check -s exit:2 -o ignore jexec client1 ping -t 1 -c 1 198.51.100.2 69 atf_check -s exit:2 -o ignore jexec client2 ping -t 1 -c 1 198.51.100.2 70 71 firewall_config nat ${firewall} \ 72 "pf" \ 73 "nat pass on ${epair_host_nat}b inet from any to any -> (${epair_host_nat}b)" \ 74 "ipfw" \ 75 "ipfw -q nat 123 config if ${epair_host_nat}b" \ 76 "ipfw -q add 1000 nat 123 all from any to any" \ 77 "ipfnat" \ 78 "map ${epair_host_nat}b 192.0.3.0/24 -> 0/32" \ 79 "map ${epair_host_nat}b 192.0.2.0/24 -> 0/32" \ 80 81 82 # ping is successful now 83 atf_check -s exit:0 -o ignore jexec client1 ping -t 1 -c 1 198.51.100.2 84 atf_check -s exit:0 -o ignore jexec client2 ping -t 1 -c 1 198.51.100.2 85 86} 87 88basic_cleanup() 89{ 90 firewall=$1 91 firewall_cleanup $firewall 92} 93 94userspace_nat_head() 95{ 96 atf_set descr 'Nat test for ipfw using userspace natd' 97 atf_set require.user root 98} 99userspace_nat_body() 100{ 101 firewall=$1 102 firewall_init $firewall 103 104 if ! kldstat -q -m ipdivert; then 105 atf_skip "This test requires ipdivert module loaded" 106 fi 107 108 epair_host_nat=$(vnet_mkepair) 109 epair_client1_nat=$(vnet_mkepair) 110 epair_client2_nat=$(vnet_mkepair) 111 112 vnet_mkjail nat ${epair_host_nat}b ${epair_client1_nat}a ${epair_client2_nat}a 113 vnet_mkjail client1 ${epair_client1_nat}b 114 vnet_mkjail client2 ${epair_client2_nat}b 115 116 ifconfig ${epair_host_nat}a 198.51.100.2/24 up 117 jexec nat ifconfig ${epair_host_nat}b 198.51.100.1/24 up 118 119 jexec nat ifconfig ${epair_client1_nat}a 192.0.2.1/24 up 120 jexec client1 ifconfig ${epair_client1_nat}b 192.0.2.2/24 up 121 122 jexec nat ifconfig ${epair_client2_nat}a 192.0.3.1/24 up 123 jexec client2 ifconfig ${epair_client2_nat}b 192.0.3.2/24 up 124 125 jexec nat sysctl net.inet.ip.forwarding=1 126 127 jexec client1 route add -net 198.51.100.0/24 192.0.2.1 128 jexec client2 route add -net 198.51.100.0/24 192.0.3.1 129 # Test the userspace NAT of ipfw 130 # ping fails without NAT configuration 131 atf_check -s exit:2 -o ignore jexec client1 ping -t 1 -c 1 198.51.100.2 132 atf_check -s exit:2 -o ignore jexec client2 ping -t 1 -c 1 198.51.100.2 133 134 firewall_config nat ${firewall} \ 135 "ipfw" \ 136 "natd -interface ${epair_host_nat}b" \ 137 "ipfw -q add divert natd all from any to any via ${epair_host_nat}b" \ 138 139 # ping is successful now 140 atf_check -s exit:0 -o ignore jexec client1 ping -t 1 -c 1 198.51.100.2 141 atf_check -s exit:0 -o ignore jexec client2 ping -t 1 -c 1 198.51.100.2 142} 143 144userspace_nat_cleanup() 145{ 146 firewall=$1 147 firewall_cleanup $firewall 148} 149 150common_cgn() { 151 firewall=$1 152 portalias=$2 153 firewall_init $firewall 154 nat_init $firewall 155 156 epair_host_nat=$(vnet_mkepair) 157 epair_client1_nat=$(vnet_mkepair) 158 epair_client2_nat=$(vnet_mkepair) 159 160 vnet_mkjail nat ${epair_host_nat}b ${epair_client1_nat}a ${epair_client2_nat}a 161 vnet_mkjail client1 ${epair_client1_nat}b 162 vnet_mkjail client2 ${epair_client2_nat}b 163 164 ifconfig ${epair_host_nat}a 198.51.100.2/24 up 165 jexec nat ifconfig ${epair_host_nat}b 198.51.100.1/24 up 166 167 jexec nat ifconfig ${epair_client1_nat}a 100.64.0.1/24 up 168 jexec client1 ifconfig ${epair_client1_nat}b 100.64.0.2/24 up 169 170 jexec nat ifconfig ${epair_client2_nat}a 100.64.1.1/24 up 171 jexec client2 ifconfig ${epair_client2_nat}b 100.64.1.2/24 up 172 173 jexec nat sysctl net.inet.ip.forwarding=1 174 175 jexec client1 route add -net 198.51.100.0/24 100.64.0.1 176 jexec client2 route add -net 198.51.100.0/24 100.64.1.1 177 178 # ping fails without NAT configuration 179 atf_check -s exit:2 -o ignore jexec client1 ping -t 1 -c 1 198.51.100.2 180 atf_check -s exit:2 -o ignore jexec client2 ping -t 1 -c 1 198.51.100.2 181 182 if [[ $portalias ]]; then 183 firewall_config nat $firewall \ 184 "ipfw" \ 185 "ipfw -q nat 123 config if ${epair_host_nat}b unreg_cgn port_alias 2000-2999" \ 186 "ipfw -q nat 456 config if ${epair_host_nat}b unreg_cgn port_alias 3000-3999" \ 187 "ipfw -q add 1000 nat 123 all from any to 198.51.100.2 2000-2999 in via ${epair_host_nat}b" \ 188 "ipfw -q add 2000 nat 456 all from any to 198.51.100.2 3000-3999 in via ${epair_host_nat}b" \ 189 "ipfw -q add 3000 nat 123 all from 100.64.0.2 to any out via ${epair_host_nat}b" \ 190 "ipfw -q add 4000 nat 456 all from 100.64.1.2 to any out via ${epair_host_nat}b" 191 else 192 firewall_config nat $firewall \ 193 "ipfw" \ 194 "ipfw -q nat 123 config if ${epair_host_nat}b unreg_cgn" \ 195 "ipfw -q add 1000 nat 123 all from any to any" 196 fi 197 198 # ping is successful now 199 atf_check -s exit:0 -o ignore jexec client1 ping -t 1 -c 1 198.51.100.2 200 atf_check -s exit:0 -o ignore jexec client2 ping -t 1 -c 1 198.51.100.2 201 202 # if portalias, test a tcp server/client with nc 203 if [[ $portalias ]]; then 204 for inst in 1 2; do 205 daemon nc -p 198.51.100.2 7 206 atf_check -s exit:0 -o ignore jexec client$inst sh -c "echo | nc -N 198.51.100.2 7" 207 done 208 fi 209} 210 211cgn_head() 212{ 213 atf_set descr 'IPv4 CGN (RFC 6598) test' 214 atf_set require.user root 215} 216 217cgn_body() 218{ 219 common_cgn $1 false 220} 221 222cgn_cleanup() 223{ 224 firewall_cleanup ipfw 225} 226 227portalias_head() 228{ 229 atf_set descr 'IPv4 CGN (RFC 6598) port aliasing test' 230 atf_set require.user root 231} 232 233portalias_body() 234{ 235 common_cgn $1 true 236} 237 238portalias_cleanup() 239{ 240 firewall_cleanup ipfw 241} 242 243setup_tests \ 244 basic \ 245 pf \ 246 ipfw \ 247 ipfnat \ 248 userspace_nat \ 249 ipfw \ 250 cgn \ 251 ipfw \ 252 portalias \ 253 ipfw 254