Module Name: src
Committed By: riastradh
Date: Wed Aug 26 16:03:42 UTC 2020
Modified Files:
src/distrib/sets/lists/base: shl.mi
src/distrib/sets/lists/comp: mi shl.mi
src/distrib/sets/lists/debug: mi shl.mi
src/distrib/sets/lists/tests: mi
src/doc: CHANGES
src/etc/mtree: NetBSD.dist.tests
src/share/man/man4: wg.4
src/sys/arch/amd64/conf: ALL
src/sys/net: if_types.h if_wg.c
src/sys/rump/net: Makefile.rumpnetcomp
src/tests/net: Makefile
src/usr.sbin/wg-keygen: wg-keygen.8
src/usr.sbin/wg-userspace: wg-userspace.8 wg-userspace.sh
src/usr.sbin/wgconfig: wgconfig.8
Added Files:
src/sys/rump/net/lib/libwg: Makefile WG.ioconf wg_component.c wg_user.c
wg_user.h
src/tests/net/if_wg: Makefile common.sh t_basic.sh
t_interoperability.sh t_misc.sh t_tunnel.sh
Removed Files:
src/sys/rump/net/lib/libwireguard: Makefile WG.ioconf wg_component.c
wg_user.c wg_user.h
src/tests/net/wireguard: Makefile common.sh t_basic.sh
t_interoperability.sh t_misc.sh t_tunnel.sh
Log Message:
Clarify wg(4)'s relation to WireGuard, pending further discussion.
Still planning to replace wgconfig(8) and wg-keygen(8) by one wg(8)
tool compatible with wireguard-tools; update wg(4) for the minor
changes from the 2018-06-30 spec to the 2020-06-01 spec; &c. This just
clarifies the current state of affairs as it exists in the development
tree for now.
Mark the man page EXPERIMENTAL for extra clarity.
To generate a diff of this commit:
cvs rdiff -u -r1.896 -r1.897 src/distrib/sets/lists/base/shl.mi
cvs rdiff -u -r1.2344 -r1.2345 src/distrib/sets/lists/comp/mi
cvs rdiff -u -r1.337 -r1.338 src/distrib/sets/lists/comp/shl.mi
cvs rdiff -u -r1.329 -r1.330 src/distrib/sets/lists/debug/mi
cvs rdiff -u -r1.258 -r1.259 src/distrib/sets/lists/debug/shl.mi
cvs rdiff -u -r1.906 -r1.907 src/distrib/sets/lists/tests/mi
cvs rdiff -u -r1.2732 -r1.2733 src/doc/CHANGES
cvs rdiff -u -r1.175 -r1.176 src/etc/mtree/NetBSD.dist.tests
cvs rdiff -u -r1.4 -r1.5 src/share/man/man4/wg.4
cvs rdiff -u -r1.161 -r1.162 src/sys/arch/amd64/conf/ALL
cvs rdiff -u -r1.30 -r1.31 src/sys/net/if_types.h
cvs rdiff -u -r1.23 -r1.24 src/sys/net/if_wg.c
cvs rdiff -u -r1.21 -r1.22 src/sys/rump/net/Makefile.rumpnetcomp
cvs rdiff -u -r0 -r1.1 src/sys/rump/net/lib/libwg/Makefile \
src/sys/rump/net/lib/libwg/WG.ioconf \
src/sys/rump/net/lib/libwg/wg_component.c \
src/sys/rump/net/lib/libwg/wg_user.c src/sys/rump/net/lib/libwg/wg_user.h
cvs rdiff -u -r1.1 -r0 src/sys/rump/net/lib/libwireguard/Makefile \
src/sys/rump/net/lib/libwireguard/WG.ioconf \
src/sys/rump/net/lib/libwireguard/wg_component.c \
src/sys/rump/net/lib/libwireguard/wg_user.c \
src/sys/rump/net/lib/libwireguard/wg_user.h
cvs rdiff -u -r1.35 -r1.36 src/tests/net/Makefile
cvs rdiff -u -r0 -r1.1 src/tests/net/if_wg/Makefile \
src/tests/net/if_wg/common.sh src/tests/net/if_wg/t_basic.sh \
src/tests/net/if_wg/t_interoperability.sh src/tests/net/if_wg/t_misc.sh \
src/tests/net/if_wg/t_tunnel.sh
cvs rdiff -u -r1.1 -r0 src/tests/net/wireguard/Makefile \
src/tests/net/wireguard/common.sh src/tests/net/wireguard/t_basic.sh \
src/tests/net/wireguard/t_interoperability.sh \
src/tests/net/wireguard/t_misc.sh src/tests/net/wireguard/t_tunnel.sh
cvs rdiff -u -r1.2 -r1.3 src/usr.sbin/wg-keygen/wg-keygen.8
cvs rdiff -u -r1.2 -r1.3 src/usr.sbin/wg-userspace/wg-userspace.8
cvs rdiff -u -r1.1 -r1.2 src/usr.sbin/wg-userspace/wg-userspace.sh
cvs rdiff -u -r1.9 -r1.10 src/usr.sbin/wgconfig/wgconfig.8
Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.
Modified files:
Index: src/distrib/sets/lists/base/shl.mi
diff -u src/distrib/sets/lists/base/shl.mi:1.896 src/distrib/sets/lists/base/shl.mi:1.897
--- src/distrib/sets/lists/base/shl.mi:1.896 Thu Aug 20 21:28:00 2020
+++ src/distrib/sets/lists/base/shl.mi Wed Aug 26 16:03:40 2020
@@ -1,4 +1,4 @@
-# $NetBSD: shl.mi,v 1.896 2020/08/20 21:28:00 riastradh Exp $
+# $NetBSD: shl.mi,v 1.897 2020/08/26 16:03:40 riastradh Exp $
#
# Note: Don't delete entries from here - mark them as "obsolete" instead,
# unless otherwise stated below.
@@ -832,9 +832,12 @@
./usr/lib/librumpnet_vlan.so base-rump-shlib rump
./usr/lib/librumpnet_vlan.so.0 base-rump-shlib rump
./usr/lib/librumpnet_vlan.so.0.0 base-rump-shlib rump
-./usr/lib/librumpnet_wireguard.so base-rump-shlib rump
-./usr/lib/librumpnet_wireguard.so.0 base-rump-shlib rump
-./usr/lib/librumpnet_wireguard.so.0.0 base-rump-shlib rump
+./usr/lib/librumpnet_wg.so base-rump-shlib rump
+./usr/lib/librumpnet_wg.so.0 base-rump-shlib rump
+./usr/lib/librumpnet_wg.so.0.0 base-rump-shlib rump
+./usr/lib/librumpnet_wireguard.so base-obsolete obsolete
+./usr/lib/librumpnet_wireguard.so.0 base-obsolete obsolete
+./usr/lib/librumpnet_wireguard.so.0.0 base-obsolete obsolete
./usr/lib/librumpres.so base-rumpclient-shlib compatfile,rump
./usr/lib/librumpres.so.0 base-rumpclient-shlib compatfile,rump
./usr/lib/librumpres.so.0.0 base-rumpclient-shlib compatfile,rump
Index: src/distrib/sets/lists/comp/mi
diff -u src/distrib/sets/lists/comp/mi:1.2344 src/distrib/sets/lists/comp/mi:1.2345
--- src/distrib/sets/lists/comp/mi:1.2344 Thu Aug 20 21:28:00 2020
+++ src/distrib/sets/lists/comp/mi Wed Aug 26 16:03:40 2020
@@ -1,4 +1,4 @@
-# $NetBSD: mi,v 1.2344 2020/08/20 21:28:00 riastradh Exp $
+# $NetBSD: mi,v 1.2345 2020/08/26 16:03:40 riastradh Exp $
#
# Note: don't delete entries from here - mark them as "obsolete" instead.
./etc/mtree/set.comp comp-sys-root
@@ -3867,8 +3867,10 @@
./usr/lib/librumpnet_virtif_p.a comp-c-proflib rump,profile
./usr/lib/librumpnet_vlan.a comp-c-lib rump
./usr/lib/librumpnet_vlan_p.a comp-c-proflib rump,profile
-./usr/lib/librumpnet_wireguard.a comp-c-lib rump
-./usr/lib/librumpnet_wireguard_p.a comp-c-proflib rump,profile
+./usr/lib/librumpnet_wg.a comp-c-lib rump
+./usr/lib/librumpnet_wg_p.a comp-c-proflib rump,profile
+./usr/lib/librumpnet_wireguard.a comp-obsolete obsolete
+./usr/lib/librumpnet_wireguard_p.a comp-obsolete obsolete
./usr/lib/librumpres.a comp-c-lib compatfile,rump
./usr/lib/librumpres_p.a comp-c-proflib compatfile,rump,profile
./usr/lib/librumpuser.a comp-c-lib compatfile,rump
Index: src/distrib/sets/lists/comp/shl.mi
diff -u src/distrib/sets/lists/comp/shl.mi:1.337 src/distrib/sets/lists/comp/shl.mi:1.338
--- src/distrib/sets/lists/comp/shl.mi:1.337 Thu Aug 20 21:28:00 2020
+++ src/distrib/sets/lists/comp/shl.mi Wed Aug 26 16:03:40 2020
@@ -1,4 +1,4 @@
-# $NetBSD: shl.mi,v 1.337 2020/08/20 21:28:00 riastradh Exp $
+# $NetBSD: shl.mi,v 1.338 2020/08/26 16:03:40 riastradh Exp $
#
# Note: don't delete entries from here - mark them as "obsolete" instead.
#
@@ -248,7 +248,8 @@
./usr/lib/librumpnet_tun_pic.a comp-c-piclib picinstall,rump
./usr/lib/librumpnet_virtif_pic.a comp-c-piclib picinstall,rump
./usr/lib/librumpnet_vlan_pic.a comp-c-piclib picinstall,rump
-./usr/lib/librumpnet_wireguard_pic.a comp-c-piclib picinstall,rump
+./usr/lib/librumpnet_wg_pic.a comp-c-piclib picinstall,rump
+./usr/lib/librumpnet_wireguard_pic.a comp-obsolete obsolete
./usr/lib/librumpres_pic.a comp-c-piclib compatfile,picinstall,rump
./usr/lib/librumpuser_pic.a comp-c-piclib compatfile,picinstall,rump
./usr/lib/librumpvfs_aio_pic.a comp-c-piclib picinstall,rump
Index: src/distrib/sets/lists/debug/mi
diff -u src/distrib/sets/lists/debug/mi:1.329 src/distrib/sets/lists/debug/mi:1.330
--- src/distrib/sets/lists/debug/mi:1.329 Thu Aug 20 21:28:01 2020
+++ src/distrib/sets/lists/debug/mi Wed Aug 26 16:03:41 2020
@@ -1,4 +1,4 @@
-# $NetBSD: mi,v 1.329 2020/08/20 21:28:01 riastradh Exp $
+# $NetBSD: mi,v 1.330 2020/08/26 16:03:41 riastradh Exp $
./etc/mtree/set.debug comp-sys-root
./usr/lib comp-sys-usr compatdir
./usr/lib/i18n/libBIG5_g.a comp-c-debuglib debuglib,compatfile
@@ -237,7 +237,8 @@
./usr/lib/librumpnet_tun_g.a comp-c-debuglib debuglib,rump
./usr/lib/librumpnet_virtif_g.a comp-c-debuglib debuglib,rump
./usr/lib/librumpnet_vlan_g.a comp-c-debuglib debuglib,rump
-./usr/lib/librumpnet_wireguard_g.a comp-c-debuglib debuglib,rump
+./usr/lib/librumpnet_wg_g.a comp-c-debuglib debuglib,rump
+./usr/lib/librumpnet_wireguard_g.a comp-obsolete obsolete
./usr/lib/librumpres_g.a comp-c-debuglib debuglib,compatfile,rump
./usr/lib/librumpuser_g.a comp-c-debuglib debuglib,compatfile,rump
./usr/lib/librumpvfs_aio_g.a comp-c-debuglib debuglib,rump
Index: src/distrib/sets/lists/debug/shl.mi
diff -u src/distrib/sets/lists/debug/shl.mi:1.258 src/distrib/sets/lists/debug/shl.mi:1.259
--- src/distrib/sets/lists/debug/shl.mi:1.258 Thu Aug 20 21:28:01 2020
+++ src/distrib/sets/lists/debug/shl.mi Wed Aug 26 16:03:41 2020
@@ -1,4 +1,4 @@
-# $NetBSD: shl.mi,v 1.258 2020/08/20 21:28:01 riastradh Exp $
+# $NetBSD: shl.mi,v 1.259 2020/08/26 16:03:41 riastradh Exp $
./usr/lib/libbfd_g.a comp-c-debuglib debuglib,compatfile,binutils
./usr/libdata/debug/lib base-sys-usr debug,dynamicroot,compatdir
./usr/libdata/debug/lib/libavl.so.0.0.debug comp-zfs-debug debug,dynamicroot,zfs
@@ -290,7 +290,8 @@
./usr/libdata/debug/usr/lib/librumpnet_tun.so.0.0.debug comp-rump-debug debug,rump
./usr/libdata/debug/usr/lib/librumpnet_virtif.so.0.0.debug comp-rump-debug debug,rump
./usr/libdata/debug/usr/lib/librumpnet_vlan.so.0.0.debug comp-rump-debug debug,rump
-./usr/libdata/debug/usr/lib/librumpnet_wireguard.so.0.0.debug comp-rump-debug debug,rump
+./usr/libdata/debug/usr/lib/librumpnet_wg.so.0.0.debug comp-rump-debug debug,rump
+./usr/libdata/debug/usr/lib/librumpnet_wireguard.so.0.0.debug comp-obsolete obsolete
./usr/libdata/debug/usr/lib/librumpres.so.0.0.debug comp-rump-debug debug,compatfile,rump
./usr/libdata/debug/usr/lib/librumpuser.so.0.1.debug comp-rump-debug debug,compatfile,rump
./usr/libdata/debug/usr/lib/librumpvfs.so.0.0.debug comp-rump-debug debug,compatfile,rump
Index: src/distrib/sets/lists/tests/mi
diff -u src/distrib/sets/lists/tests/mi:1.906 src/distrib/sets/lists/tests/mi:1.907
--- src/distrib/sets/lists/tests/mi:1.906 Mon Aug 24 18:41:22 2020
+++ src/distrib/sets/lists/tests/mi Wed Aug 26 16:03:41 2020
@@ -1,4 +1,4 @@
-# $NetBSD: mi,v 1.906 2020/08/24 18:41:22 riastradh Exp $
+# $NetBSD: mi,v 1.907 2020/08/26 16:03:41 riastradh Exp $
#
# Note: don't delete entries from here - mark them as "obsolete" instead.
#
@@ -3866,13 +3866,20 @@
./usr/tests/net/if_vlan/Kyuafile tests-net-tests atf,rump,kyua
./usr/tests/net/if_vlan/siocXmulti tests-net-tests atf,rump
./usr/tests/net/if_vlan/t_vlan tests-net-tests atf,rump
-./usr/tests/net/wireguard tests-net-tests compattestfile,atf
-./usr/tests/net/wireguard/Atffile tests-net-tests atf,rump
-./usr/tests/net/wireguard/Kyuafile tests-net-tests atf,rump,kyua
-./usr/tests/net/wireguard/t_basic tests-net-tests atf,rump
-./usr/tests/net/wireguard/t_interoperability tests-net-tests atf,rump
-./usr/tests/net/wireguard/t_misc tests-net-tests atf,rump
-./usr/tests/net/wireguard/t_tunnel tests-net-tests atf,rump
+./usr/tests/net/if_wg tests-net-tests compattestfile,atf
+./usr/tests/net/if_wg/Atffile tests-net-tests atf,rump
+./usr/tests/net/if_wg/Kyuafile tests-net-tests atf,rump,kyua
+./usr/tests/net/if_wg/t_basic tests-net-tests atf,rump
+./usr/tests/net/if_wg/t_interoperability tests-net-tests atf,rump
+./usr/tests/net/if_wg/t_misc tests-net-tests atf,rump
+./usr/tests/net/if_wg/t_tunnel tests-net-tests atf,rump
+./usr/tests/net/wireguard tests-obsolete obsolete
+./usr/tests/net/wireguard/Atffile tests-obsolete obsolete
+./usr/tests/net/wireguard/Kyuafile tests-obsolete obsolete
+./usr/tests/net/wireguard/t_basic tests-obsolete obsolete
+./usr/tests/net/wireguard/t_interoperability tests-obsolete obsolete
+./usr/tests/net/wireguard/t_misc tests-obsolete obsolete
+./usr/tests/net/wireguard/t_tunnel tests-obsolete obsolete
./usr/tests/net/in_cksum tests-net-tests compattestfile,atf
./usr/tests/net/in_cksum/Atffile tests-net-tests compattestfile,atf
./usr/tests/net/in_cksum/Kyuafile tests-net-tests compattestfile,atf,kyua
@@ -3953,10 +3960,14 @@
./usr/tests/net/sys/t_listen tests-obsolete obsolete
./usr/tests/net/sys/t_rfc6056 tests-net-tests compattestfile,atf
./usr/tests/net/sys/t_socketpair tests-obsolete obsolete
-./usr/tests/net/wireguard tests-net-tests compattestfile,atf
-./usr/tests/net/wireguard/Atffile tests-net-tests compattestfile,atf
-./usr/tests/net/wireguard/Kyuafile tests-net-tests compattestfile,atf,kyua
-./usr/tests/net/wireguard/t_basic tests-net-tests atf,rump
+./usr/tests/net/if_wg tests-net-tests compattestfile,atf
+./usr/tests/net/if_wg/Atffile tests-net-tests compattestfile,atf
+./usr/tests/net/if_wg/Kyuafile tests-net-tests compattestfile,atf,kyua
+./usr/tests/net/if_wg/t_basic tests-net-tests atf,rump
+./usr/tests/net/wireguard tests-obsolete obsolete
+./usr/tests/net/wireguard/Atffile tests-obsolete obsolete
+./usr/tests/net/wireguard/Kyuafile tests-obsolete obsolete
+./usr/tests/net/wireguard/t_basic tests-obsolete obsolete
./usr/tests/opencrypto tests-obsolete obsolete
./usr/tests/rump tests-rump-tests compattestfile,atf
./usr/tests/rump/Atffile tests-rump-tests atf,rump
Index: src/doc/CHANGES
diff -u src/doc/CHANGES:1.2732 src/doc/CHANGES:1.2733
--- src/doc/CHANGES:1.2732 Thu Aug 20 21:45:46 2020
+++ src/doc/CHANGES Wed Aug 26 16:03:41 2020
@@ -1,4 +1,4 @@
-# LIST OF CHANGES FROM LAST RELEASE: <$Revision: 1.2732 $>
+# LIST OF CHANGES FROM LAST RELEASE: <$Revision: 1.2733 $>
#
#
# [Note: This file does not mention every change made to the NetBSD source tree.
@@ -273,4 +273,4 @@ Changes from NetBSD 9.0 to NetBSD 10.0:
kernel: Add getrandom system call. [riastradh 20200813]
kernel: Disable COMPAT_LINUX by default [jdolecek 20200816]
mips: Port crash(8) to mips. [mrg 20200816]
- wg(4): Add support for WireGuard. [ozaki-r 20200820]
+ wg(4): Add implementation of WireGuard protocol. [ozaki-r 20200820]
Index: src/etc/mtree/NetBSD.dist.tests
diff -u src/etc/mtree/NetBSD.dist.tests:1.175 src/etc/mtree/NetBSD.dist.tests:1.176
--- src/etc/mtree/NetBSD.dist.tests:1.175 Thu Aug 20 21:28:01 2020
+++ src/etc/mtree/NetBSD.dist.tests Wed Aug 26 16:03:41 2020
@@ -1,4 +1,4 @@
-# $NetBSD: NetBSD.dist.tests,v 1.175 2020/08/20 21:28:01 riastradh Exp $
+# $NetBSD: NetBSD.dist.tests,v 1.176 2020/08/26 16:03:41 riastradh Exp $
./usr/libdata/debug/usr/tests
./usr/libdata/debug/usr/tests/atf
@@ -358,6 +358,7 @@
./usr/tests/net/if_tap
./usr/tests/net/if_tun
./usr/tests/net/if_vlan
+./usr/tests/net/if_wg
./usr/tests/net/in_cksum
./usr/tests/net/ipsec
./usr/tests/net/mcast
@@ -367,7 +368,6 @@
./usr/tests/net/npf
./usr/tests/net/route
./usr/tests/net/sys
-./usr/tests/net/wireguard
./usr/tests/rump
./usr/tests/rump/modautoload
./usr/tests/rump/rumpkern
Index: src/share/man/man4/wg.4
diff -u src/share/man/man4/wg.4:1.4 src/share/man/man4/wg.4:1.5
--- src/share/man/man4/wg.4:1.4 Fri Aug 21 08:09:55 2020
+++ src/share/man/man4/wg.4 Wed Aug 26 16:03:41 2020
@@ -1,4 +1,4 @@
-.\" $NetBSD: wg.4,v 1.4 2020/08/21 08:09:55 wiz Exp $
+.\" $NetBSD: wg.4,v 1.5 2020/08/26 16:03:41 riastradh Exp $
.\"
.\" Copyright (c) 2020 The NetBSD Foundation, Inc.
.\" All rights reserved.
@@ -30,7 +30,7 @@
.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
.Sh NAME
.Nm wg
-.Nd WireGuard virtual private network
+.Nd virtual private network tunnel (EXPERIMENTAL)
.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
.Sh SYNOPSIS
.Cd pseudo-device wg
@@ -38,12 +38,16 @@
.Sh DESCRIPTION
The
.Nm
-interface implements the WireGuard point-to-point roaming-capable
-virtual private network tunnel, configured with
+interface implements a point-to-point roaming-capable virtual private
+network tunnel, configured with
.Xr ifconfig 8
and
.Xr wgconfig 8 .
.Pp
+.Sy WARNING:
+.Nm
+is experimental.
+.Pp
Packets exchanged on a
.Nm
interface are authenticated and encrypted with a secret key negotiated
@@ -91,14 +95,14 @@ Stationary server:
.Pp
Generate key pairs on A and B:
.Bd -literal -offset abcd
-A# wg-keygen > /etc/wireguard/wg0
-A# wg-keygen --pub < /etc/wireguard/wg0 > /etc/wireguard/wg0.pub
-A# cat /etc/wireguard/wg0.pub
+A# wg-keygen > /etc/wg/wg0
+A# wg-keygen --pub < /etc/wg/wg0 > /etc/wg/wg0.pub
+A# cat /etc/wg/wg0.pub
N+B4Nelg+4ysvbLW3qenxIwrJVE9MdjMyqrIisH7V0Y=
-B# wg-keygen > /etc/wireguard/wg0
-B# wg-keygen --pub < /etc/wireguard/wg0 > /etc/wireguard/wg0.pub
-B# cat /etc/wireguard/wg0.pub
+B# wg-keygen > /etc/wg/wg0
+B# wg-keygen --pub < /etc/wg/wg0 > /etc/wg/wg0.pub
+B# cat /etc/wg/wg0.pub
X7EGm3T3IfodBcyilkaC89j0SH3XD6+/pwvp7Dgp5SU=
.Ed
.Pp
@@ -106,7 +110,7 @@ Configure A to listen on port 1234 and a
appear in the 10.0.1.0/24 subnet:
.Bd -literal -offset abcd
A# ifconfig wg0 create 10.0.1.0/24
-A# wgconfig wg0 set private-key /etc/wireguard/wg0
+A# wgconfig wg0 set private-key /etc/wg/wg0
A# wgconfig wg0 set listen-port 1234
A# wgconfig wg0 add peer B \e
X7EGm3T3IfodBcyilkaC89j0SH3XD6+/pwvp7Dgp5SU= \e
@@ -121,7 +125,7 @@ Configure B to connect to A at 1.2.3.4 o
begin to flow:
.Bd -literal -offset abcd
B# ifconfig wg0 create 10.0.1.1/24
-B# wgconfig wg0 set private-key /etc/wireguard/wg0
+B# wgconfig wg0 set private-key /etc/wg/wg0
B# wgconfig wg0 add peer A \e
N+B4Nelg+4ysvbLW3qenxIwrJVE9MdjMyqrIisH7V0Y= \e
--allowed-ips=10.0.1.0/32 \e
@@ -139,9 +143,19 @@ PING 10.0.1.0 (10.0.1.0): 56 data bytes
.Sh SEE ALSO
.Xr wg-keygen 8 ,
.Xr wgconfig 8
+.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
+.Sh COMPATIBILITY
+The
+.Nm
+interface aims to be compatible with the WireGuard protocol, as
+described in:
+.Pp
.Rs
-.%T WireGuard: fast, modern, secure VPN tunnel
-.%U https://www.wireguard.com/
+.%A Jason A. Donenfeld
+.%T WireGuard: Next Generation Kernel Network Tunnel
+.%U https://web.archive.org/web/20180805103233/https://www.wireguard.com/papers/wireguard.pdf
+.%O Document ID: 4846ada1492f5d92198df154f48c3d54205657bc
+.%D 2018-06-30
.Re
.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
.Sh HISTORY
Index: src/sys/arch/amd64/conf/ALL
diff -u src/sys/arch/amd64/conf/ALL:1.161 src/sys/arch/amd64/conf/ALL:1.162
--- src/sys/arch/amd64/conf/ALL:1.161 Thu Aug 20 21:36:11 2020
+++ src/sys/arch/amd64/conf/ALL Wed Aug 26 16:03:41 2020
@@ -1,4 +1,4 @@
-# $NetBSD: ALL,v 1.161 2020/08/20 21:36:11 riastradh Exp $
+# $NetBSD: ALL,v 1.162 2020/08/26 16:03:41 riastradh Exp $
# From NetBSD: GENERIC,v 1.787 2006/10/01 18:37:54 bouyer Exp
#
# ALL machine description file
@@ -17,7 +17,7 @@ include "arch/amd64/conf/std.amd64"
options INCLUDE_CONFIG_FILE # embed config file in kernel binary
-#ident "ALL-$Revision: 1.161 $"
+#ident "ALL-$Revision: 1.162 $"
maxusers 64 # estimated number of users
@@ -1641,7 +1641,7 @@ pseudo-device npf # NPF packet filter
pseudo-device kttcp
# srt is EXPERIMENTAL
pseudo-device srt # source-address-based routing
-pseudo-device wg # WireGuard
+pseudo-device wg # VPN tunnel compatible with WireGuard
pseudo-device canloop # CAN loopback interface
Index: src/sys/net/if_types.h
diff -u src/sys/net/if_types.h:1.30 src/sys/net/if_types.h:1.31
--- src/sys/net/if_types.h:1.30 Thu Aug 20 21:21:32 2020
+++ src/sys/net/if_types.h Wed Aug 26 16:03:41 2020
@@ -1,4 +1,4 @@
-/* $NetBSD: if_types.h,v 1.30 2020/08/20 21:21:32 riastradh Exp $ */
+/* $NetBSD: if_types.h,v 1.31 2020/08/26 16:03:41 riastradh Exp $ */
/*
* Copyright (c) 1989, 1993, 1994
@@ -267,6 +267,5 @@
#define IFT_CARP 0xf8 /* Common Address Redundancy Protocol */
#define IFT_IPSEC 0xf9 /* IPsec I/F */
#define IFT_MBIM 0xfa /* Mobile Broadband Interface Model */
-#define IFT_WIREGUARD 0xfb /* WireGuard */
#endif /* !_NET_IF_TYPES_H_ */
Index: src/sys/net/if_wg.c
diff -u src/sys/net/if_wg.c:1.23 src/sys/net/if_wg.c:1.24
--- src/sys/net/if_wg.c:1.23 Sun Aug 23 18:52:53 2020
+++ src/sys/net/if_wg.c Wed Aug 26 16:03:41 2020
@@ -1,4 +1,4 @@
-/* $NetBSD: if_wg.c,v 1.23 2020/08/23 18:52:53 riastradh Exp $ */
+/* $NetBSD: if_wg.c,v 1.24 2020/08/26 16:03:41 riastradh Exp $ */
/*
* Copyright (C) Ryota Ozaki <[email protected]>
@@ -30,20 +30,18 @@
*/
/*
- * This is an implementation of WireGuard, a fast, modern, secure VPN protocol,
- * for the NetBSD kernel and rump kernels.
- *
- * The implementation is based on the paper of WireGuard as of 2018-06-30 [1].
- * The paper is referred in the source code with label [W]. Also the
- * specification of the Noise protocol framework as of 2018-07-11 [2] is
- * referred with label [N].
+ * This network interface aims to implement the WireGuard protocol.
+ * The implementation is based on the paper of WireGuard as of
+ * 2018-06-30 [1]. The paper is referred in the source code with label
+ * [W]. Also the specification of the Noise protocol framework as of
+ * 2018-07-11 [2] is referred with label [N].
*
* [1] https://www.wireguard.com/papers/wireguard.pdf
* [2] http://noiseprotocol.org/noise.pdf
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: if_wg.c,v 1.23 2020/08/23 18:52:53 riastradh Exp $");
+__KERNEL_RCSID(0, "$NetBSD: if_wg.c,v 1.24 2020/08/26 16:03:41 riastradh Exp $");
#ifdef _KERNEL_OPT
#include "opt_inet.h"
@@ -120,7 +118,7 @@ __KERNEL_RCSID(0, "$NetBSD: if_wg.c,v 1.
* Data structures
* - struct wg_softc is an instance of wg interfaces
* - It has a list of peers (struct wg_peer)
- * - It has a kthread that sends/receives WireGuard handshake messages and
+ * - It has a kthread that sends/receives handshake messages and
* runs event handlers
* - It has its own two routing tables: one is for IPv4 and the other IPv6
* - struct wg_peer is a representative of a peer
@@ -3346,7 +3344,7 @@ wg_if_attach(struct wg_softc *wg)
wg->wg_if.if_output = wg_output;
wg->wg_if.if_init = wg_init;
wg->wg_if.if_stop = wg_stop;
- wg->wg_if.if_type = IFT_WIREGUARD;
+ wg->wg_if.if_type = IFT_OTHER;
wg->wg_if.if_dlt = DLT_NULL;
wg->wg_if.if_softc = wg;
IFQ_SET_READY(&wg->wg_if.if_snd);
@@ -4399,14 +4397,14 @@ wg_stop(struct ifnet *ifp, int disable)
}
#ifdef WG_DEBUG_PARAMS
-SYSCTL_SETUP(sysctl_net_wireguard_setup, "sysctl net.wireguard setup")
+SYSCTL_SETUP(sysctl_net_wg_setup, "sysctl net.wg setup")
{
const struct sysctlnode *node = NULL;
sysctl_createv(clog, 0, NULL, &node,
CTLFLAG_PERMANENT,
- CTLTYPE_NODE, "wireguard",
- SYSCTL_DESCR("WireGuard"),
+ CTLTYPE_NODE, "wg",
+ SYSCTL_DESCR("wg(4)"),
NULL, 0, NULL, 0,
CTL_NET, CTL_CREATE, CTL_EOL);
sysctl_createv(clog, 0, &node, NULL,
Index: src/sys/rump/net/Makefile.rumpnetcomp
diff -u src/sys/rump/net/Makefile.rumpnetcomp:1.21 src/sys/rump/net/Makefile.rumpnetcomp:1.22
--- src/sys/rump/net/Makefile.rumpnetcomp:1.21 Thu Aug 20 21:21:32 2020
+++ src/sys/rump/net/Makefile.rumpnetcomp Wed Aug 26 16:03:41 2020
@@ -1,11 +1,11 @@
-# $NetBSD: Makefile.rumpnetcomp,v 1.21 2020/08/20 21:21:32 riastradh Exp $
+# $NetBSD: Makefile.rumpnetcomp,v 1.22 2020/08/26 16:03:41 riastradh Exp $
#
.include <bsd.own.mk>
RUMPNETCOMP= agr bridge net net80211 netbt netcan netinet netinet6 netipsec
RUMPNETCOMP+= gif ipsec netmpls npf l2tp local pppoe shmif tap tun vlan
-RUMPNETCOMP+= wireguard
+RUMPNETCOMP+= wg
.if ${MKSLJIT} != "no" || make(rumpdescribe)
RUMPNETCOMP+= bpfjit
Index: src/tests/net/Makefile
diff -u src/tests/net/Makefile:1.35 src/tests/net/Makefile:1.36
--- src/tests/net/Makefile:1.35 Thu Aug 20 21:21:32 2020
+++ src/tests/net/Makefile Wed Aug 26 16:03:42 2020
@@ -1,4 +1,4 @@
-# $NetBSD: Makefile,v 1.35 2020/08/20 21:21:32 riastradh Exp $
+# $NetBSD: Makefile,v 1.36 2020/08/26 16:03:42 riastradh Exp $
.include <bsd.own.mk>
@@ -8,7 +8,7 @@ TESTS_SUBDIRS= fdpass in_cksum net sys
.if (${MKRUMP} != "no") && !defined(BSD_MK_COMPAT_FILE)
TESTS_SUBDIRS+= arp bpf bpfilter can carp icmp if if_bridge if_gif
TESTS_SUBDIRS+= if_ipsec if_l2tp if_loop if_pppoe if_tap if_tun ipsec
-TESTS_SUBDIRS+= mcast mpls ndp npf route if_vlan wireguard
+TESTS_SUBDIRS+= mcast mpls ndp npf route if_vlan if_wg
.if (${MKSLJIT} != "no")
TESTS_SUBDIRS+= bpfjit
.endif
Index: src/usr.sbin/wg-keygen/wg-keygen.8
diff -u src/usr.sbin/wg-keygen/wg-keygen.8:1.2 src/usr.sbin/wg-keygen/wg-keygen.8:1.3
--- src/usr.sbin/wg-keygen/wg-keygen.8:1.2 Thu Aug 20 21:36:00 2020
+++ src/usr.sbin/wg-keygen/wg-keygen.8 Wed Aug 26 16:03:42 2020
@@ -1,4 +1,4 @@
-.\" $NetBSD: wg-keygen.8,v 1.2 2020/08/20 21:36:00 riastradh Exp $
+.\" $NetBSD: wg-keygen.8,v 1.3 2020/08/26 16:03:42 riastradh Exp $
.\"
.\" Copyright (C) Ryota Ozaki <[email protected]>
.\" All rights reserved.
@@ -33,7 +33,7 @@
.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
.Sh NAME
.Nm wg-keygen
-.Nd generate keys for WireGuard interfaces
+.Nd generate keys for wg interfaces
.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
.Sh SYNOPSIS
.Nm
@@ -42,7 +42,8 @@
.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
.Sh DESCRIPTION
.Nm
-generates keys for WireGuard.
+generates keys for
+.Xr wg 4 .
.Bl -tag -width abcd
.It Nm
Generate a private key and print it to standard output.
Index: src/usr.sbin/wg-userspace/wg-userspace.8
diff -u src/usr.sbin/wg-userspace/wg-userspace.8:1.2 src/usr.sbin/wg-userspace/wg-userspace.8:1.3
--- src/usr.sbin/wg-userspace/wg-userspace.8:1.2 Thu Aug 20 22:17:16 2020
+++ src/usr.sbin/wg-userspace/wg-userspace.8 Wed Aug 26 16:03:42 2020
@@ -1,4 +1,4 @@
-.\" $NetBSD: wg-userspace.8,v 1.2 2020/08/20 22:17:16 riastradh Exp $
+.\" $NetBSD: wg-userspace.8,v 1.3 2020/08/26 16:03:42 riastradh Exp $
.\"
.\" Copyright (C) Ryota Ozaki <[email protected]>
.\" All rights reserved.
@@ -33,7 +33,7 @@
.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
.Sh NAME
.Nm wg-userspace
-.Nd manipulate WireGuard userspace instances
+.Nd manipulate wg userspace instances (EXPERIMENTAL)
.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
.Sh SYNOPSIS
.Ar id
@@ -42,39 +42,45 @@
.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
.Sh DESCRIPTION
.Nm
-is used to create, destroy and configure WireGuard userspace instances.
+is used to create, destroy and configure
+.Xr wg 4
+userspace instances.
+.Pp
+.Sy WARNING:
+.Nm
+is experimental.
.Pp
The following commands are supported:
.Bl -tag -width "destroy"
.It Cm create
-Create a WireGuard interface.
+Create an interface.
The interface will appear as
.Li tun Ns Ar id
to the rest of the system, and will be served by a rump server in whose
context the interface appears as
.Li wg Ns Ar id .
.It Cm destroy
-Destroy a WireGuard interface and stop the rump server behind it.
+Destroy an interface and stop the rump server behind it.
.It Cm ifconfig Ar wgN Ar args...
Run
.Xr ifconfig 8
-in the context of the WireGuard interface's rump server.
+in the context of the interface's rump server.
For example,
.Bd -literal -compact
# wg-userspace 0 ifconfig wg0 10.0.1.0/24
.Ed
-will set the WireGuard interface's IP address.
+will set the interface's IP address.
.It Cm wgconfig Ar wgN Ar args...
Run
.Xr wgconfig 8
-in the context of the WireGuard interface's rump server.
+in the context of the interface's rump server.
For example,
.Bd -literal -compact
# wg-userspace 0 wgconfig wg0 set listen-port 1234
.Ed
-will set the WireGuard interface's listening port.
+will set the interface's listening port.
.It Cm debug Ar command Op Ar args...
-Run an arbitrary command in the context of the WireGuard interface's
+Run an arbitrary command in the context of the interface's
rump server, using
.Xr rumphijack 3 .
.El
Index: src/usr.sbin/wg-userspace/wg-userspace.sh
diff -u src/usr.sbin/wg-userspace/wg-userspace.sh:1.1 src/usr.sbin/wg-userspace/wg-userspace.sh:1.2
--- src/usr.sbin/wg-userspace/wg-userspace.sh:1.1 Thu Aug 20 21:28:02 2020
+++ src/usr.sbin/wg-userspace/wg-userspace.sh Wed Aug 26 16:03:42 2020
@@ -2,7 +2,7 @@
RUMPLIBS="-lrumpnet -lrumpnet_net -lrumpnet_netinet \
-lrumpdev -lrumpvfs -lrumpdev_opencrypto -lrumpkern_z \
- -lrumpkern_crypto -lrumpnet_wireguard -lrumpnet_netinet6"
+ -lrumpkern_crypto -lrumpnet_wg -lrumpnet_netinet6"
HIJACKING="env LD_PRELOAD=/usr/lib/librumphijack.so \
RUMPHIJACK=path=/rump,socket=all:nolocal,sysctl=yes"
Index: src/usr.sbin/wgconfig/wgconfig.8
diff -u src/usr.sbin/wgconfig/wgconfig.8:1.9 src/usr.sbin/wgconfig/wgconfig.8:1.10
--- src/usr.sbin/wgconfig/wgconfig.8:1.9 Fri Aug 21 03:44:58 2020
+++ src/usr.sbin/wgconfig/wgconfig.8 Wed Aug 26 16:03:42 2020
@@ -1,4 +1,4 @@
-.\" $NetBSD: wgconfig.8,v 1.9 2020/08/21 03:44:58 uwe Exp $
+.\" $NetBSD: wgconfig.8,v 1.10 2020/08/26 16:03:42 riastradh Exp $
.\"
.\" Copyright (C) Ryota Ozaki <[email protected]>
.\" All rights reserved.
@@ -33,7 +33,7 @@
.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
.Sh NAME
.Nm wgconfig
-.Nd configure WireGuard interface parameters
+.Nd configure wg interface parameters
.\"""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""""
.Sh SYNOPSIS
.Nm
@@ -74,7 +74,7 @@
.Sh DESCRIPTION
The
.Nm
-utility is used to configure or display a WireGuard
+utility is used to configure or display a
.Xr wg 4
interface's parameters and status.
Every
@@ -91,7 +91,7 @@ have a fixed endpoint IP address and a p
The following commands are supported:
.Bl -tag -width abcd
.It Cm "show all"
-Show all WireGuard peers.
+Show all peers.
No secret keys are included in the output.
.It Cm "show peer" Ar name Op Fl Fl show-preshared-key
Show the peer named
@@ -117,7 +117,7 @@ to the base64-encoded private key in the
.It Cm "set listen-port" Ar port
Set the UDP port number that
.Li wg Ns Ar N\|
-listens for incoming WireGuard sessions on.
+listens for incoming sessions on.
This allows a peer to start a new session without having a specific
endpoint IP address configured.
.It Cm "add peer" Ar name Ar pubkey Op Ar options ...
@@ -146,14 +146,16 @@ Set a secret preshared key generated by
If the preshared key can be arranged in advance on a medium not subject
to eavesdropping, then it defends against possible future quantum
cryptanalysis of the X25519 key agreement.
-WireGuard still uses X25519 key agreements in order to erase past
+.Nm
+still uses X25519 key agreements in order to erase past
session keys so that past session transcripts remain secret should one
of the endpoints be compromised in the future; the preshared key is an
additional measure on top.
.It Fl Fl endpoint Ns Li \&= Ns Ar ip Ns Li \&: Ns Ar port
Set the peer's endpoint address outside the tunnel.
-This is optional for a VPN server if the WireGuard interface is
-configured to listen on a port number.
+This is optional for a VPN server if the
+.Nm
+interface is configured to listen on a port number.
.It Fl Fl allowed-ips Ns Li \&= Ns Ar ip1 Ns Li \&/ Ns Ar cidr1 Ns \
Op Li \&, Ns Ar ip2 Ns Li \&/ Ns Ar cidr2 Ns Li \&, Ns Ar ...
Set the IP address ranges that the peer is allowed to select inside the
Added files:
Index: src/sys/rump/net/lib/libwg/Makefile
diff -u /dev/null src/sys/rump/net/lib/libwg/Makefile:1.1
--- /dev/null Wed Aug 26 16:03:43 2020
+++ src/sys/rump/net/lib/libwg/Makefile Wed Aug 26 16:03:42 2020
@@ -0,0 +1,27 @@
+# $NetBSD: Makefile,v 1.1 2020/08/26 16:03:42 riastradh Exp $
+#
+
+.PATH: ${.CURDIR}/../../../../net ${.CURDIR}/../../../../netinet \
+ ${.CURDIR}/../../../../netinet6
+
+LIB= rumpnet_wg
+COMMENT= virtual private network tunnel
+
+IOCONF= WG.ioconf
+SRCS= if_wg.c
+
+CPPFLAGS.if_wg.c+= -DWG_RUMPKERNEL
+
+# For sysctl knobs
+CPPFLAGS.if_wg.c+= -DWG_DEBUG_PARAMS
+.ifdef RUMP_DEBUG
+CPPFLAGS.if_wg.c+= -DWG_DEBUG_TRACE -DWG_DEBUG_LOG
+.endif
+
+SRCS+= wg_component.c
+
+#SRCS+= wg_user.c
+RUMPCOMP_USER_SRCS= wg_user.c
+
+.include <bsd.lib.mk>
+.include <bsd.klinks.mk>
Index: src/sys/rump/net/lib/libwg/WG.ioconf
diff -u /dev/null src/sys/rump/net/lib/libwg/WG.ioconf:1.1
--- /dev/null Wed Aug 26 16:03:43 2020
+++ src/sys/rump/net/lib/libwg/WG.ioconf Wed Aug 26 16:03:42 2020
@@ -0,0 +1,7 @@
+# $NetBSD: WG.ioconf,v 1.1 2020/08/26 16:03:42 riastradh Exp $
+
+ioconf wg
+
+include "conf/files"
+
+pseudo-device wg
Index: src/sys/rump/net/lib/libwg/wg_component.c
diff -u /dev/null src/sys/rump/net/lib/libwg/wg_component.c:1.1
--- /dev/null Wed Aug 26 16:03:43 2020
+++ src/sys/rump/net/lib/libwg/wg_component.c Wed Aug 26 16:03:42 2020
@@ -0,0 +1,42 @@
+/* $NetBSD: wg_component.c,v 1.1 2020/08/26 16:03:42 riastradh Exp $ */
+
+/*
+ * Copyright (c) 2015 Internet Initiative Japan Inc.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <sys/cdefs.h>
+__KERNEL_RCSID(0, "$NetBSD: wg_component.c,v 1.1 2020/08/26 16:03:42 riastradh Exp $");
+
+#include <sys/param.h>
+
+#include <rump-sys/kern.h>
+
+int wgattach(int);
+
+RUMP_COMPONENT(RUMP_COMPONENT_NET_IF)
+{
+
+ wgattach(0);
+}
Index: src/sys/rump/net/lib/libwg/wg_user.c
diff -u /dev/null src/sys/rump/net/lib/libwg/wg_user.c:1.1
--- /dev/null Wed Aug 26 16:03:43 2020
+++ src/sys/rump/net/lib/libwg/wg_user.c Wed Aug 26 16:03:42 2020
@@ -0,0 +1,423 @@
+/* $NetBSD: wg_user.c,v 1.1 2020/08/26 16:03:42 riastradh Exp $ */
+
+/*
+ * Copyright (C) Ryota Ozaki <[email protected]>
+ * All rights reserved.
+ *
+ * Based on wg_user.c by Antti Kantee.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <sys/cdefs.h>
+__KERNEL_RCSID(0, "$NetBSD: wg_user.c,v 1.1 2020/08/26 16:03:42 riastradh Exp $");
+
+#ifndef _KERNEL
+#include <sys/types.h>
+#include <sys/ioctl.h>
+#include <sys/uio.h>
+#include <sys/socket.h>
+#include <sys/param.h>
+
+#include <net/if.h>
+#include <net/if_tun.h>
+
+#include <netinet/in.h>
+
+#include <assert.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <inttypes.h>
+#include <poll.h>
+#include <pthread.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+
+#include <rump/rumpuser_component.h>
+
+#include "wg_user.h"
+
+struct wg_user {
+ struct wg_softc *wgu_sc;
+ int wgu_devnum;
+ char wgu_tun_name[IFNAMSIZ];
+
+ int wgu_fd;
+ int wgu_sock4;
+ int wgu_sock6;
+ int wgu_pipe[2];
+ pthread_t wgu_rcvthr;
+
+ int wgu_dying;
+
+ char wgu_rcvbuf[9018]; /* jumbo frame max len */
+};
+
+static int
+open_tun(const char *tun_name)
+{
+ char tun_path[MAXPATHLEN];
+ int n, fd, error;
+
+ n = snprintf(tun_path, sizeof(tun_path), "/dev/%s", tun_name);
+ if (n == MAXPATHLEN)
+ return E2BIG;
+
+ fd = open(tun_path, O_RDWR);
+ if (fd == -1) {
+ fprintf(stderr, "%s: can't open %s: %s\n",
+ __func__, tun_name, strerror(errno));
+ }
+
+ int i = 1;
+ error = ioctl(fd, TUNSLMODE, &i);
+ if (error == -1) {
+ close(fd);
+ fd = -1;
+ }
+
+ return fd;
+}
+
+static void
+close_tun(struct wg_user *wgu)
+{
+ int s;
+ struct ifreq ifr = {};
+
+ close(wgu->wgu_fd);
+
+ s = socket(AF_INET, SOCK_DGRAM, 0);
+ if (s == -1)
+ return; /* XXX */
+ strcpy(ifr.ifr_name, wgu->wgu_tun_name);
+ (void)ioctl(s, SIOCIFDESTROY, &ifr);
+ close(s);
+}
+
+static void *
+wg_user_rcvthread(void *aaargh)
+{
+ struct wg_user *wgu = aaargh;
+ struct pollfd pfd[4];
+ ssize_t nn = 0;
+ int prv;
+
+ rumpuser_component_kthread();
+
+ pfd[0].fd = wgu->wgu_fd;
+ pfd[0].events = POLLIN;
+ pfd[1].fd = wgu->wgu_pipe[0];
+ pfd[1].events = POLLIN;
+ pfd[2].fd = wgu->wgu_sock4;
+ pfd[2].events = POLLIN;
+ pfd[3].fd = wgu->wgu_sock6;
+ pfd[3].events = POLLIN;
+
+ while (!wgu->wgu_dying) {
+ struct iovec iov[2];
+
+ prv = poll(pfd, 4, -1);
+ if (prv == 0)
+ continue;
+ if (prv == -1) {
+ /* XXX */
+ fprintf(stderr, "%s: poll error: %d\n",
+ wgu->wgu_tun_name, errno);
+ sleep(1);
+ continue;
+ }
+ if (pfd[1].revents & POLLIN)
+ continue;
+
+ /* Receive user packets from tun */
+ if (pfd[0].revents & POLLIN) {
+ nn = read(wgu->wgu_fd, wgu->wgu_rcvbuf, sizeof(wgu->wgu_rcvbuf));
+ if (nn == -1 && errno == EAGAIN)
+ continue;
+
+ if (nn < 1) {
+ /* XXX */
+ fprintf(stderr, "%s: receive failed\n",
+ wgu->wgu_tun_name);
+ sleep(1);
+ continue;
+ }
+
+ iov[0].iov_base = wgu->wgu_rcvbuf;
+ iov[0].iov_len = ((struct sockaddr *)wgu->wgu_rcvbuf)->sa_len;
+
+ iov[1].iov_base = (char *)wgu->wgu_rcvbuf + iov[0].iov_len;
+ iov[1].iov_len = nn - iov[0].iov_len;
+
+ rumpuser_component_schedule(NULL);
+ rumpkern_wg_recv_user(wgu->wgu_sc, iov, 2);
+ rumpuser_component_unschedule();
+ }
+
+ /* Receive wg UDP/IPv4 packets from a peer */
+ if (pfd[2].revents & POLLIN) {
+ struct sockaddr_in sin;
+ socklen_t len = sizeof(sin);
+ nn = recvfrom(wgu->wgu_sock4, wgu->wgu_rcvbuf,
+ sizeof(wgu->wgu_rcvbuf), 0, (struct sockaddr *)&sin,
+ &len);
+ if (nn == -1 && errno == EAGAIN)
+ continue;
+ if (len != sizeof(sin))
+ continue;
+ iov[0].iov_base = &sin;
+ iov[0].iov_len = sin.sin_len;
+
+ iov[1].iov_base = wgu->wgu_rcvbuf;
+ iov[1].iov_len = nn;
+
+ rumpuser_component_schedule(NULL);
+ rumpkern_wg_recv_peer(wgu->wgu_sc, iov, 2);
+ rumpuser_component_unschedule();
+ }
+
+ /* Receive wg UDP/IPv6 packets from a peer */
+ if (pfd[3].revents & POLLIN) {
+ struct sockaddr_in6 sin6;
+ socklen_t len = sizeof(sin6);
+ nn = recvfrom(wgu->wgu_sock6, wgu->wgu_rcvbuf,
+ sizeof(wgu->wgu_rcvbuf), 0, (struct sockaddr *)&sin6,
+ &len);
+ if (nn == -1 && errno == EAGAIN)
+ continue;
+ if (len != sizeof(sin6))
+ continue;
+ iov[0].iov_base = &sin6;
+ iov[0].iov_len = sin6.sin6_len;
+
+ iov[1].iov_base = wgu->wgu_rcvbuf;
+ iov[1].iov_len = nn;
+
+ rumpuser_component_schedule(NULL);
+ rumpkern_wg_recv_peer(wgu->wgu_sc, iov, 2);
+ rumpuser_component_unschedule();
+ }
+ }
+
+ assert(wgu->wgu_dying);
+
+ rumpuser_component_kthread_release();
+ return NULL;
+}
+
+int
+rumpuser_wg_create(const char *tun_name, struct wg_softc *wg,
+ struct wg_user **wgup)
+{
+ struct wg_user *wgu = NULL;
+ void *cookie;
+ int rv;
+
+ cookie = rumpuser_component_unschedule();
+
+ wgu = malloc(sizeof(*wgu));
+ if (wgu == NULL) {
+ rv = errno;
+ goto oerr1;
+ }
+
+ wgu->wgu_fd = open_tun(tun_name);
+ if (wgu->wgu_fd == -1) {
+ rv = errno;
+ goto oerr2;
+ }
+ strcpy(wgu->wgu_tun_name, tun_name);
+ wgu->wgu_sc = wg;
+
+ if (pipe(wgu->wgu_pipe) == -1) {
+ rv = errno;
+ goto oerr3;
+ }
+
+ wgu->wgu_sock4 = socket(AF_INET, SOCK_DGRAM, 0);
+ wgu->wgu_sock6 = socket(AF_INET6, SOCK_DGRAM, 0);
+ if (wgu->wgu_sock4 == -1 || wgu->wgu_sock6 == -1) {
+ rv = errno;
+ goto oerr4;
+ }
+
+ rv = pthread_create(&wgu->wgu_rcvthr, NULL, wg_user_rcvthread, wgu);
+ if (rv != 0)
+ goto oerr5;
+
+ rumpuser_component_schedule(cookie);
+ *wgup = wgu;
+ return 0;
+
+ oerr5:
+ close(wgu->wgu_pipe[0]);
+ close(wgu->wgu_pipe[1]);
+ oerr4:
+ if (wgu->wgu_sock4 != -1)
+ close(wgu->wgu_sock4);
+ if (wgu->wgu_sock6 != -1)
+ close(wgu->wgu_sock6);
+ oerr3:
+ close_tun(wgu);
+ oerr2:
+ free(wgu);
+ oerr1:
+ rumpuser_component_schedule(cookie);
+ return rumpuser_component_errtrans(rv);
+}
+
+/*
+ * Send decrypted packets to users via a tun.
+ */
+void
+rumpuser_wg_send_user(struct wg_user *wgu, struct iovec *iov, size_t iovlen)
+{
+ void *cookie = rumpuser_component_unschedule();
+ ssize_t idontcare __attribute__((__unused__));
+
+ /*
+ * no need to check for return value; packets may be dropped
+ *
+ * ... sorry, I spoke too soon. We need to check it because
+ * apparently gcc reinvented const poisoning and it's very
+ * hard to say "thanks, I know I'm not using the result,
+ * but please STFU and let's get on with something useful".
+ * So let's trick gcc into letting us share the compiler
+ * experience.
+ */
+ idontcare = writev(wgu->wgu_fd, iov, iovlen);
+
+ rumpuser_component_schedule(cookie);
+}
+
+/*
+ * Send wg messages to a peer.
+ */
+int
+rumpuser_wg_send_peer(struct wg_user *wgu, struct sockaddr *sa,
+ struct iovec *iov, size_t iovlen)
+{
+ void *cookie = rumpuser_component_unschedule();
+ int s, error = 0;
+ size_t i;
+ ssize_t sent;
+
+ if (sa->sa_family == AF_INET)
+ s = wgu->wgu_sock4;
+ else
+ s = wgu->wgu_sock6;
+
+ for (i = 0; i < iovlen; i++) {
+ sent = sendto(s, iov[i].iov_base, iov[i].iov_len, 0, sa,
+ sa->sa_len);
+ if (sent == -1 || (size_t)sent != iov[i].iov_len) {
+ error = errno;
+ break;
+ }
+ }
+
+ rumpuser_component_schedule(cookie);
+
+ return error;
+}
+
+int
+rumpuser_wg_ioctl(struct wg_user *wgu, u_long cmd, void *data, int af)
+{
+ void *cookie = rumpuser_component_unschedule();
+ int s, error;
+
+ s = socket(af, SOCK_DGRAM, 0);
+ if (s == -1)
+ return errno;
+ error = ioctl(s, cmd, data);
+ close(s);
+
+ rumpuser_component_schedule(cookie);
+
+ return error == -1 ? errno : 0;
+}
+
+int
+rumpuser_wg_sock_bind(struct wg_user *wgu, const uint16_t port)
+{
+ int error;
+ struct sockaddr_in sin;
+ struct sockaddr_in6 sin6;
+
+ memset(&sin, 0, sizeof(sin));
+ sin.sin_family = AF_INET;
+ sin.sin_len = sizeof(sin);
+ sin.sin_addr.s_addr = INADDR_ANY;
+ sin.sin_port = htons(port);
+
+ error = bind(wgu->wgu_sock4, (struct sockaddr *)&sin, sizeof(sin));
+ if (error == -1)
+ return errno;
+
+ memset(&sin6, 0, sizeof(sin6));
+ sin6.sin6_family = AF_INET6;
+ sin6.sin6_len = sizeof(sin6);
+ sin6.sin6_addr = in6addr_any;
+ sin6.sin6_port = htons(port);
+
+ error = bind(wgu->wgu_sock6, (struct sockaddr *)&sin6, sizeof(sin6));
+ if (error == -1)
+ return errno;
+
+ return 0;
+}
+
+void
+rumpuser_wg_destroy(struct wg_user *wgu)
+{
+ void *cookie = rumpuser_component_unschedule();
+
+ wgu->wgu_dying = 1;
+ if (write(wgu->wgu_pipe[1],
+ &wgu->wgu_dying, sizeof(wgu->wgu_dying)) == -1) {
+ /*
+ * this is here mostly to avoid a compiler warning
+ * about ignoring the return value of write()
+ */
+ fprintf(stderr, "%s: failed to signal thread\n",
+ wgu->wgu_tun_name);
+ }
+ pthread_join(wgu->wgu_rcvthr, NULL);
+ close_tun(wgu);
+ close(wgu->wgu_pipe[0]);
+ close(wgu->wgu_pipe[1]);
+ free(wgu);
+
+ rumpuser_component_schedule(cookie);
+}
+
+char *
+rumpuser_wg_get_tunname(struct wg_user *wgu)
+{
+
+ return wgu->wgu_tun_name;
+}
+#endif
Index: src/sys/rump/net/lib/libwg/wg_user.h
diff -u /dev/null src/sys/rump/net/lib/libwg/wg_user.h:1.1
--- /dev/null Wed Aug 26 16:03:43 2020
+++ src/sys/rump/net/lib/libwg/wg_user.h Wed Aug 26 16:03:42 2020
@@ -0,0 +1,52 @@
+/* $NetBSD: wg_user.h,v 1.1 2020/08/26 16:03:42 riastradh Exp $ */
+
+/*
+ * Copyright (C) Ryota Ozaki <[email protected]>
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+struct wg_user;
+struct wg_softc;
+
+/*
+ * Defined in wg_user.c and called from if_wg.c.
+ */
+int rumpuser_wg_create(const char *tun_name, struct wg_softc *,
+ struct wg_user **);
+void rumpuser_wg_destroy(struct wg_user *);
+
+void rumpuser_wg_send_user(struct wg_user *, struct iovec *, size_t);
+int rumpuser_wg_send_peer(struct wg_user *, struct sockaddr *,
+ struct iovec *, size_t);
+
+int rumpuser_wg_ioctl(struct wg_user *, u_long, void *, int);
+int rumpuser_wg_sock_bind(struct wg_user *, const uint16_t);
+
+char * rumpuser_wg_get_tunname(struct wg_user *);
+
+/*
+ * Defined in if_wg.c and called from wg_user.c.
+ */
+void rumpkern_wg_recv_user(struct wg_softc *, struct iovec *, size_t);
+void rumpkern_wg_recv_peer(struct wg_softc *, struct iovec *, size_t);
Index: src/tests/net/if_wg/Makefile
diff -u /dev/null src/tests/net/if_wg/Makefile:1.1
--- /dev/null Wed Aug 26 16:03:43 2020
+++ src/tests/net/if_wg/Makefile Wed Aug 26 16:03:42 2020
@@ -0,0 +1,13 @@
+# $NetBSD: Makefile,v 1.1 2020/08/26 16:03:42 riastradh Exp $
+#
+
+.include <bsd.own.mk>
+
+TESTSDIR= ${TESTSBASE}/net/if_wg
+
+.for name in basic interoperability misc tunnel
+TESTS_SH+= t_${name}
+TESTS_SH_SRC_t_${name}= ../net_common.sh ./common.sh t_${name}.sh
+.endfor
+
+.include <bsd.test.mk>
Index: src/tests/net/if_wg/common.sh
diff -u /dev/null src/tests/net/if_wg/common.sh:1.1
--- /dev/null Wed Aug 26 16:03:43 2020
+++ src/tests/net/if_wg/common.sh Wed Aug 26 16:03:42 2020
@@ -0,0 +1,200 @@
+# $NetBSD: common.sh,v 1.1 2020/08/26 16:03:42 riastradh Exp $
+#
+# Copyright (c) 2018 Ryota Ozaki <[email protected]>
+# All rights reserved.
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions
+# are met:
+# 1. Redistributions of source code must retain the above copyright
+# notice, this list of conditions and the following disclaimer.
+# 2. Redistributions in binary form must reproduce the above copyright
+# notice, this list of conditions and the following disclaimer in the
+# documentation and/or other materials provided with the distribution.
+#
+# THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
+# ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+# TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
+# BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+# POSSIBILITY OF SUCH DAMAGE.
+#
+
+escape_key()
+{
+
+ echo $1 | sed 's/\+/\\+/g' | sed 's|\/|\\/|g'
+}
+
+setup_servers()
+{
+
+ rump_server_crypto_start $SOCK_LOCAL netinet6 wg
+ rump_server_add_iface $SOCK_LOCAL shmif0 $BUS
+
+ rump_server_crypto_start $SOCK_PEER netinet6 wg
+ rump_server_add_iface $SOCK_PEER shmif0 $BUS
+}
+
+check_conf_port()
+{
+ local ifname=$1
+ local port=$2
+
+ atf_check -s exit:0 -o match:"listen-port: $port" \
+ $HIJACKING wgconfig $ifname
+}
+
+check_conf_privkey()
+{
+ local ifname=$1
+ local key_priv="$2"
+
+ atf_check -s exit:0 -o match:"private-key: $(escape_key $key_priv)" \
+ $HIJACKING wgconfig $ifname show private-key
+}
+
+setup_common()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ifname=$1
+ local proto=$2
+ local ip=$3
+ local prefix=$4
+
+ $ifconfig $ifname $proto $ip/$prefix
+}
+
+setup_wg_common()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local wgconfig="atf_check -s exit:0 $HIJACKING wgconfig"
+ local ifname=$1
+ local proto=$2
+ local ip=$3
+ local prefix=$4
+ local port=$5
+ local key_priv="$6"
+ local tun=$7
+ local privfile=./tmp
+
+ $ifconfig $ifname create
+ if [ -n "$tun" ]; then
+ $ifconfig $ifname linkstr $tun
+ fi
+ $ifconfig $ifname $proto $ip/$prefix
+ $DEBUG && rump.netstat -nr
+ echo $key_priv > $privfile
+ $wgconfig $ifname set private-key $privfile
+ $wgconfig $ifname set listen-port $port
+ rm -f $privfile
+ $ifconfig $ifname up
+ $DEBUG && rump.ifconfig $ifname
+
+ check_conf_port $ifname $port
+ check_conf_privkey $ifname "$key_priv"
+}
+
+check_ping()
+{
+ local proto=$1
+ local ip=$2
+ local ping=
+
+ if [ $proto = inet ]; then
+ ping="atf_check -s exit:0 -o ignore rump.ping -n -i 0.1 -c 3 -w 1"
+ else
+ ping="atf_check -s exit:0 -o ignore rump.ping6 -n -i 0.1 -c 3 -X 1"
+ fi
+
+ $ping $ip
+}
+
+check_ping_fail()
+{
+ local proto=$1
+ local ip=$2
+ local ping=
+
+ if [ $proto = inet ]; then
+ ping="atf_check -s not-exit:0 -o ignore rump.ping -n -c 1 -w 1"
+ else
+ ping="atf_check -s not-exit:0 -o ignore rump.ping6 -n -c 1 -X 1"
+ fi
+
+ $ping $ip
+}
+
+destroy_wg_interfaces()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ $ifconfig wg0 destroy
+ export RUMP_SERVER=$SOCK_PEER
+ $ifconfig wg0 destroy
+}
+
+add_peer()
+{
+ local wgconfig="atf_check -s exit:0 $HIJACKING wgconfig"
+ local ifname=$1
+ local peername=$2
+ local key=$3
+ local endpoint=$4
+ local allowedips=$5
+ local pskfile=$6
+ local key_psk="$7"
+ local pskopt=
+ local endpoint_opts=
+
+ if [ -n "$pskfile" ]; then
+ pskopt="--preshared-key=$pskfile"
+ fi
+
+ if [ -n "$endpoint" ]; then
+ endpoint_opts="--endpoint=$endpoint"
+ fi
+
+ $wgconfig $ifname add peer $peername $key $endpoint_opts \
+ --allowed-ips=$allowedips $pskopt
+ atf_check -s exit:0 -o match:"allowed-ips: $allowedips" \
+ $HIJACKING wgconfig $ifname show peer $peername
+ if [ -n "$key_psk" ]; then
+ atf_check -s exit:0 \
+ -o match:"preshared-key: $(escape_key $key_psk)" \
+ $HIJACKING wgconfig $ifname show peer $peername \
+ --show-preshared-key
+ else
+ atf_check -s exit:0 -o match:"preshared-key: \(none\)" \
+ $HIJACKING wgconfig $ifname show peer $peername \
+ --show-preshared-key
+ fi
+}
+
+delete_peer()
+{
+ local wgconfig="atf_check -s exit:0 $HIJACKING wgconfig"
+ local ifname=$1
+ local peername=$2
+
+ $wgconfig $ifname delete peer $peername
+ atf_check -s exit:0 -o not-match:"peer: $peername" \
+ $HIJACKING wgconfig $ifname
+}
+
+generate_keys()
+{
+
+ key_priv_local=$(wg-keygen)
+ key_pub_local=$(echo $key_priv_local| wg-keygen --pub)
+ key_priv_peer=$(wg-keygen)
+ key_pub_peer=$(echo $key_priv_peer| wg-keygen --pub)
+
+ export key_priv_local key_pub_local key_priv_peer key_pub_peer
+}
Index: src/tests/net/if_wg/t_basic.sh
diff -u /dev/null src/tests/net/if_wg/t_basic.sh:1.1
--- /dev/null Wed Aug 26 16:03:43 2020
+++ src/tests/net/if_wg/t_basic.sh Wed Aug 26 16:03:42 2020
@@ -0,0 +1,485 @@
+# $NetBSD: t_basic.sh,v 1.1 2020/08/26 16:03:42 riastradh Exp $
+#
+# Copyright (c) 2018 Ryota Ozaki <[email protected]>
+# All rights reserved.
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions
+# are met:
+# 1. Redistributions of source code must retain the above copyright
+# notice, this list of conditions and the following disclaimer.
+# 2. Redistributions in binary form must reproduce the above copyright
+# notice, this list of conditions and the following disclaimer in the
+# documentation and/or other materials provided with the distribution.
+#
+# THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
+# ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+# TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
+# BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+# POSSIBILITY OF SUCH DAMAGE.
+#
+
+BUS=bus
+SOCK_LOCAL=unix://wg_local
+SOCK_PEER=unix://wg_peer
+SOCK_PEER2=unix://wg_peer2
+
+
+check_ping_payload()
+{
+ local proto=$1
+ local ip=$2
+ local ping= size=
+
+ if [ $proto = inet ]; then
+ ping="atf_check -s exit:0 -o ignore rump.ping -n -c 1 -w 1"
+ else
+ ping="atf_check -s exit:0 -o ignore rump.ping6 -n -c 1 -X 1"
+ fi
+
+ for size in $(seq 1 100) $(seq 450 550) $(seq 1400 1500); do
+ $ping -s $size $ip
+ done
+}
+
+test_common()
+{
+ local type=$1
+ local outer_proto=$2
+ local inner_proto=$3
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local port=51820
+ local ip_local= ip_peer=
+ local ip_wg_local= ip_wg_peer=
+ local outer_prefix= outer_prefixall=
+ local inner_prefix= inner_prefixall=
+
+ if [ $outer_proto = inet ]; then
+ ip_local=192.168.1.1
+ ip_peer=192.168.1.2
+ outer_prefix=24
+ outer_prefixall=32
+ else
+ ip_local=fc00::1
+ ip_peer=fc00::2
+ outer_prefix=64
+ outer_prefixall=128
+ fi
+
+ if [ $inner_proto = inet ]; then
+ ip_wg_local=10.0.0.1
+ ip_wg_peer=10.0.0.2
+ inner_prefix=24
+ inner_prefixall=32
+ else
+ ip_wg_local=fd00::1
+ ip_wg_peer=fd00::2
+ inner_prefix=64
+ inner_prefixall=128
+ fi
+
+ setup_servers
+
+ # It sets key_priv_local key_pub_local key_priv_peer key_pub_peer
+ generate_keys
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ setup_common shmif0 $outer_proto $ip_local $outer_prefix
+ setup_wg_common wg0 $inner_proto $ip_wg_local $inner_prefix $port "$key_priv_local"
+
+ export RUMP_SERVER=$SOCK_PEER
+ setup_common shmif0 $outer_proto $ip_peer $outer_prefix
+ setup_wg_common wg0 $inner_proto $ip_wg_peer $inner_prefix $port "$key_priv_peer"
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port $ip_wg_peer/$inner_prefixall
+
+ export RUMP_SERVER=$SOCK_PEER
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/$inner_prefixall
+
+ if [ $type = basic ]; then
+ export RUMP_SERVER=$SOCK_LOCAL
+ check_ping $inner_proto $ip_wg_peer
+ elif [ $type = payload ]; then
+ export RUMP_SERVER=$SOCK_LOCAL
+ check_ping_payload $inner_proto $ip_wg_peer
+ fi
+
+ destroy_wg_interfaces
+}
+
+atf_test_case wg_create_destroy cleanup
+wg_create_destroy_head()
+{
+
+ atf_set "descr" "tests to create/destroy wg(4) interfaces"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+wg_create_destroy_body()
+{
+
+ rump_server_crypto_start $SOCK_LOCAL netinet6 wg
+
+ test_create_destroy_common $SOCK_LOCAL wg0 true
+}
+
+wg_create_destroy_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+wg_create_destroy_peers_common()
+{
+ local proto=$1
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local port=51820
+ local ip_local= ip_peer=
+ local ip_wg_local= ip_wg_peer=
+ local outer_prefix= outer_prefixall=
+ local inner_prefix= inner_prefixall=
+
+ if [ $proto = inet ]; then
+ ip_local=192.168.1.1
+ ip_peer=192.168.1.2
+ outer_prefix=24
+ outer_prefixall=32
+ ip_wg_local=10.0.0.1
+ ip_wg_peer=10.0.0.2
+ inner_prefix=24
+ inner_prefixall=32
+ else
+ ip_local=fc00::1
+ ip_peer=fc00::2
+ outer_prefix=64
+ outer_prefixall=128
+ ip_wg_local=fd00::1
+ ip_wg_peer=fd00::2
+ inner_prefix=64
+ inner_prefixall=128
+ fi
+
+ rump_server_crypto_start $SOCK_LOCAL netinet6 wg
+ rump_server_add_iface $SOCK_LOCAL shmif0 $BUS
+
+ # It sets key_priv_local key_pub_local key_priv_peer key_pub_peer
+ generate_keys
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ setup_common shmif0 $proto $ip_local $outer_prefix
+ setup_wg_common wg0 $proto $ip_wg_local $inner_prefix $port "$key_priv_local"
+
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port $ip_wg_peer/$inner_prefixall
+
+ delete_peer wg0 peer0
+}
+
+atf_test_case wg_create_destroy_peers_ipv4 cleanup
+wg_create_destroy_peers_ipv4_head()
+{
+
+ atf_set "descr" "tests to create/destroy peers (IPv4)"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+wg_create_destroy_peers_ipv4_body()
+{
+
+ wg_create_destroy_peers_common inet
+}
+
+wg_create_destroy_peers_ipv4_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_test_case wg_create_destroy_peers_ipv6 cleanup
+wg_create_destroy_peers_ipv6_head()
+{
+
+ atf_set "descr" "tests to create/destroy peers (IPv6)"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+wg_create_destroy_peers_ipv6_body()
+{
+
+ wg_create_destroy_peers_common inet6
+}
+
+wg_create_destroy_peers_ipv6_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+add_basic_test()
+{
+ local inner=$1
+ local outer=$2
+ local ipv4=inet
+ local ipv6=inet6
+
+ name="wg_basic_${inner}_over_${outer}"
+ fulldesc="Test wg(4) with ${inner} over ${outer}"
+
+ eval inner=\$$inner
+ eval outer=\$$outer
+
+ atf_test_case ${name} cleanup
+ eval "
+ ${name}_head() {
+ atf_set descr \"${fulldesc}\"
+ atf_set require.progs rump_server wgconfig wg-keygen
+ }
+ ${name}_body() {
+ test_common basic $outer $inner
+ rump_server_destroy_ifaces
+ }
+ ${name}_cleanup() {
+ \$DEBUG && dump
+ cleanup
+ }"
+ atf_add_test_case ${name}
+}
+
+add_payload_sizes_test()
+{
+ local inner=$1
+ local outer=$2
+ local ipv4=inet
+ local ipv6=inet6
+
+ name="wg_payload_sizes_${inner}_over_${outer}"
+ fulldesc="Test wg(4) with ${inner} over ${outer} with various payload sizes"
+
+ eval inner=\$$inner
+ eval outer=\$$outer
+
+ atf_test_case ${name} cleanup
+ eval "
+ ${name}_head() {
+ atf_set descr \"${fulldesc}\"
+ atf_set require.progs rump_server wgconfig wg-keygen
+ }
+ ${name}_body() {
+ test_common payload $outer $inner
+ rump_server_destroy_ifaces
+ }
+ ${name}_cleanup() {
+ \$DEBUG && dump
+ cleanup
+ }"
+ atf_add_test_case ${name}
+}
+
+atf_test_case wg_multiple_interfaces cleanup
+wg_multiple_interfaces_head()
+{
+
+ atf_set "descr" "tests multiple wg(4) interfaces"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+wg_multiple_interfaces_body()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ping="atf_check -s exit:0 -o ignore rump.ping -n -i 0.1 -c 3 -w 1"
+ local ping_fail="atf_check -s not-exit:0 -o ignore rump.ping -n -c 1 -w 1"
+ local key_priv_peer2=
+ local key_pub_peer2=
+ local ip_local=192.168.1.1
+ local ip_local2=192.168.2.1
+ local ip_peer=192.168.1.2
+ local ip_peer2=192.168.2.2
+ local ip_wg_local=10.0.0.1
+ local ip_wg_local2=10.0.1.1
+ local ip_wg_peer=10.0.0.2
+ local ip_wg_peer2=10.0.1.2
+ local port=51820
+ local port2=51821
+ local outfile=./out
+
+ setup_servers
+ rump_server_add_iface $SOCK_LOCAL shmif1 $BUS
+
+ rump_server_crypto_start $SOCK_PEER2 netinet6 wg
+ rump_server_add_iface $SOCK_PEER2 shmif0 $BUS
+
+ # It sets key_priv_local key_pub_local key_priv_peer key_pub_peer
+ generate_keys
+ key_priv_peer2=$(wg-keygen)
+ key_pub_peer2=$(echo $key_priv_peer2| wg-keygen --pub)
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ setup_common shmif0 inet $ip_local 24
+ setup_common shmif1 inet $ip_local2 24
+ setup_wg_common wg0 inet $ip_wg_local 24 $port "$key_priv_local"
+ setup_wg_common wg1 inet $ip_wg_local2 24 $port2 "$key_priv_local"
+
+ export RUMP_SERVER=$SOCK_PEER
+ setup_common shmif0 inet $ip_peer 24
+ setup_wg_common wg0 inet $ip_wg_peer 24 $port "$key_priv_peer"
+
+ export RUMP_SERVER=$SOCK_PEER2
+ setup_common shmif0 inet $ip_peer2 24
+ setup_wg_common wg0 inet $ip_wg_peer2 24 $port2 "$key_priv_peer2"
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port $ip_wg_peer/32
+ add_peer wg1 peer0 $key_pub_peer2 $ip_peer2:$port2 $ip_wg_peer2/32
+
+ export RUMP_SERVER=$SOCK_PEER
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/32
+
+ export RUMP_SERVER=$SOCK_PEER2
+ add_peer wg0 peer0 $key_pub_local $ip_local2:$port2 $ip_wg_local2/32
+
+ export RUMP_SERVER=$SOCK_LOCAL
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ $ping $ip_wg_peer
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ $ping $ip_wg_peer2
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ $ifconfig wg0 destroy
+ $ifconfig wg1 destroy
+ export RUMP_SERVER=$SOCK_PEER
+ $ifconfig wg0 destroy
+ export RUMP_SERVER=$SOCK_PEER2
+ $ifconfig wg0 destroy
+}
+
+wg_multiple_interfaces_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_test_case wg_multiple_peers cleanup
+wg_multiple_peers_head()
+{
+
+ atf_set "descr" "tests multiple wg(4) peers"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+wg_multiple_peers_body()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ping="atf_check -s exit:0 -o ignore rump.ping -n -i 0.1 -c 3 -w 1"
+ local ping_fail="atf_check -s not-exit:0 -o ignore rump.ping -n -c 1 -w 1"
+ local key_priv_peer2=
+ local key_pub_peer2=
+ local ip_local=192.168.1.1
+ local ip_peer=192.168.1.2
+ local ip_peer2=192.168.1.3
+ local ip_wg_local=10.0.0.1
+ local ip_wg_peer=10.0.0.2
+ local ip_wg_peer2=10.0.0.3
+ local port=51820
+ local outfile=./out
+
+ setup_servers
+ rump_server_add_iface $SOCK_LOCAL shmif1 $BUS
+
+ rump_server_crypto_start $SOCK_PEER2 netinet6 wg
+ rump_server_add_iface $SOCK_PEER2 shmif0 $BUS
+
+ # It sets key_priv_local key_pub_local key_priv_peer key_pub_peer
+ generate_keys
+ key_priv_peer2=$(wg-keygen)
+ key_pub_peer2=$(echo $key_priv_peer2| wg-keygen --pub)
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ setup_common shmif0 inet $ip_local 24
+ setup_wg_common wg0 inet $ip_wg_local 24 $port "$key_priv_local"
+
+ export RUMP_SERVER=$SOCK_PEER
+ setup_common shmif0 inet $ip_peer 24
+ setup_wg_common wg0 inet $ip_wg_peer 24 $port "$key_priv_peer"
+
+ export RUMP_SERVER=$SOCK_PEER2
+ setup_common shmif0 inet $ip_peer2 24
+ setup_wg_common wg0 inet $ip_wg_peer2 24 $port "$key_priv_peer2"
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port $ip_wg_peer/32
+ add_peer wg0 peer1 $key_pub_peer2 $ip_peer2:$port $ip_wg_peer2/32
+
+ export RUMP_SERVER=$SOCK_PEER
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/32
+
+ export RUMP_SERVER=$SOCK_PEER2
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/32
+
+ export RUMP_SERVER=$SOCK_LOCAL
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ $ping $ip_wg_peer
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ $ping $ip_wg_peer2
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ $ifconfig wg0 destroy
+ export RUMP_SERVER=$SOCK_PEER
+ $ifconfig wg0 destroy
+ export RUMP_SERVER=$SOCK_PEER2
+ $ifconfig wg0 destroy
+}
+
+wg_multiple_peers_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_init_test_cases()
+{
+
+ add_basic_test ipv4 ipv4
+ add_basic_test ipv4 ipv6
+ add_basic_test ipv6 ipv4
+ add_basic_test ipv6 ipv6
+
+ add_payload_sizes_test ipv4 ipv4
+ add_payload_sizes_test ipv4 ipv6
+ add_payload_sizes_test ipv6 ipv4
+ add_payload_sizes_test ipv6 ipv6
+
+ atf_add_test_case wg_create_destroy
+ atf_add_test_case wg_create_destroy_peers_ipv4
+ atf_add_test_case wg_create_destroy_peers_ipv6
+ atf_add_test_case wg_multiple_interfaces
+ atf_add_test_case wg_multiple_peers
+}
Index: src/tests/net/if_wg/t_interoperability.sh
diff -u /dev/null src/tests/net/if_wg/t_interoperability.sh:1.1
--- /dev/null Wed Aug 26 16:03:43 2020
+++ src/tests/net/if_wg/t_interoperability.sh Wed Aug 26 16:03:42 2020
@@ -0,0 +1,279 @@
+# $NetBSD: t_interoperability.sh,v 1.1 2020/08/26 16:03:42 riastradh Exp $
+#
+# Copyright (c) 2018 Ryota Ozaki <[email protected]>
+# All rights reserved.
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions
+# are met:
+# 1. Redistributions of source code must retain the above copyright
+# notice, this list of conditions and the following disclaimer.
+# 2. Redistributions in binary form must reproduce the above copyright
+# notice, this list of conditions and the following disclaimer in the
+# documentation and/or other materials provided with the distribution.
+#
+# THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
+# ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+# TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
+# BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+# POSSIBILITY OF SUCH DAMAGE.
+#
+
+BUS=bus
+SOCK_LOCAL=unix://wg_local
+SOCK_PEER=unix://wg_peer
+
+
+atf_test_case wg_interoperability_basic cleanup
+wg_interoperability_basic_head()
+{
+
+ atf_set "descr" "tests of interoperability with the WireGuard protocol"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+#
+# Set ATF_NET_IF_WG_INTEROPERABILITY=yes to run the test.
+# Also to run the test, the following setups are required on the host and a peer.
+#
+# [Host]
+# ifconfig bridge0 create
+# ifconfig tap0 create
+# brconfig bridge0 add tap0
+# brconfig bridge0 add <external-interface>
+# ifconfig tap0 up
+# ifconfig bridge0 up
+#
+# [Peer]
+# ip addr add 10.0.0.2/24 dev <external-interface>
+# ip link add wg0 type wireguard
+# ip addr add 10.0.1.2/24 dev wg0
+# privkey="EF9D8AOkmxjlkiRFqBnfJS+RJJHbUy02u+VkGlBr9Eo="
+# ip link set wg0 up
+# echo $privkey > /tmp/private-key
+# wg set wg0 listen-port 52428
+# wg set wg0 private-key /tmp/private-key
+# pubkey="2iWFzywbDvYu2gQW5Q7/z/g5/Cv4bDDd6L3OKXLOwxs="
+# wg set wg0 peer $pubkey endpoint 10.0.0.3:52428 allowed-ips 10.0.1.1/32
+#
+wg_interoperability_basic_body()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ping="atf_check -s exit:0 -o ignore rump.ping -n -c 3 -w 3"
+ local ping_fail="atf_check -s not-exit:0 -o ignore rump.ping -n -c 1 -w 3"
+ local key_priv_local=
+ local key_pub_local=
+ local key_priv_peer=
+ local key_pub_peer=
+ local ip_local=10.0.0.3
+ local ip_peer=10.0.0.2
+ local ip_wg_local=10.0.1.1
+ local ip_wg_peer=10.0.1.2
+ local port=52428
+ local outfile=./out
+
+ if [ "$ATF_NET_IF_WG_INTEROPERABILITY" != yes ]; then
+ atf_skip "set ATF_NET_IF_WG_INTEROPERABILITY=yes to run the test"
+ fi
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ rump_server_crypto_start $SOCK_LOCAL virtif wg netinet6
+ atf_check -s exit:0 rump.sysctl -q -w net.inet.ip.dad_count=0
+ atf_check -s exit:0 rump.ifconfig virt0 create
+ atf_check -s exit:0 rump.ifconfig virt0 $ip_local/24
+ atf_check -s exit:0 rump.ifconfig virt0 up
+
+ $ping $ip_peer
+
+ key_priv_local="aK3TbzUNDO4aeDRX54x8bOG+NaKuqXKt7Hwq0Uz69Wo="
+ key_pub_local="2iWFzywbDvYu2gQW5Q7/z/g5/Cv4bDDd6L3OKXLOwxs="
+ key_priv_peer="EF9D8AOkmxjlkiRFqBnfJS+RJJHbUy02u+VkGlBr9Eo="
+ key_pub_peer="2ZM9RvDmMZS/Nuh8OaVaJrwFbO57/WJgeU+JoQ//nko="
+
+ setup_wg_common wg0 inet $ip_wg_local 24 $port "$key_priv_local"
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port $ip_wg_peer/32
+
+ $ping $ip_wg_peer
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ $ifconfig wg0 destroy
+}
+
+wg_interoperability_basic_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_test_case wg_interoperability_cookie cleanup
+wg_interoperability_cookie_head()
+{
+
+ atf_set "descr" "tests of interoperability with the WireGuard protocol"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+wg_interoperability_cookie_body()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ping="atf_check -s exit:0 -o ignore rump.ping -n -c 3 -w 3"
+ local ping_fail="atf_check -s not-exit:0 -o ignore rump.ping -n -c 1 -w 3"
+ local key_priv_local=
+ local key_pub_local=
+ local key_priv_peer=
+ local key_pub_peer=
+ local ip_local=10.0.0.3
+ local ip_peer=10.0.0.2
+ local ip_wg_local=10.0.1.1
+ local ip_wg_peer=10.0.1.2
+ local port=52428
+ local outfile=./out
+ local rekey_timeout=5 # default
+
+ if [ "$ATF_NET_IF_WG_INTEROPERABILITY" != yes ]; then
+ atf_skip "set ATF_NET_IF_WG_INTEROPERABILITY=yes to run the test"
+ fi
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ rump_server_crypto_start $SOCK_LOCAL virtif wg netinet6
+ atf_check -s exit:0 rump.sysctl -q -w net.inet.ip.dad_count=0
+ atf_check -s exit:0 rump.ifconfig virt0 create
+ atf_check -s exit:0 rump.ifconfig virt0 $ip_local/24
+ atf_check -s exit:0 rump.ifconfig virt0 up
+
+ $ping $ip_peer
+
+ key_priv_local="aK3TbzUNDO4aeDRX54x8bOG+NaKuqXKt7Hwq0Uz69Wo="
+ key_pub_local="2iWFzywbDvYu2gQW5Q7/z/g5/Cv4bDDd6L3OKXLOwxs="
+ key_priv_peer="EF9D8AOkmxjlkiRFqBnfJS+RJJHbUy02u+VkGlBr9Eo="
+ key_pub_peer="2ZM9RvDmMZS/Nuh8OaVaJrwFbO57/WJgeU+JoQ//nko="
+
+ setup_wg_common wg0 inet $ip_wg_local 24 $port "$key_priv_local"
+
+ # Emulate load to send back a cookie on receiving a response message
+ atf_check -s exit:0 -o ignore \
+ rump.sysctl -w net.wg.force_underload=1
+
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port $ip_wg_peer/32
+
+ # ping fails because we don't accept a response message and send a cookie
+ $ping_fail $ip_wg_peer
+
+ # Wait for retrying an initialization that works because the peer
+ # send a response message with the cookie we sent
+ atf_check -s exit:0 sleep $rekey_timeout
+
+ # So ping works
+ $ping $ip_wg_peer
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ $ifconfig wg0 destroy
+}
+
+wg_interoperability_cookie_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_test_case wg_userspace_basic cleanup
+wg_userspace_basic_head()
+{
+
+ atf_set "descr" "tests of userspace implementation of wg(4)"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+#
+# Set ATF_NET_IF_WG_USERSPACE=yes to run the test.
+# Also to run the test, the following setups are required on the host and a peer.
+#
+# [Host]
+# ifconfig bridge0 create
+# ifconfig tap0 create
+# brconfig bridge0 add tap0
+# brconfig bridge0 add <external-interface>
+# ifconfig tap0 up
+# ifconfig bridge0 up
+#
+# [Peer]
+# ip addr add 10.0.0.2/24 dev <external-interface>
+# ip link add wg0 type wireguard
+# ip addr add 10.0.4.2/24 dev wg0
+# privkey="EF9D8AOkmxjlkiRFqBnfJS+RJJHbUy02u+VkGlBr9Eo="
+# ip link set wg0 up
+# echo $privkey > /tmp/private-key
+# wg set wg0 listen-port 52428
+# wg set wg0 private-key /tmp/private-key
+# pubkey="6mQ4lUO3oq5O8FfGW52CFXNbmh5iFT1XMqPzpdrc0nE="
+# wg set wg0 peer $pubkey endpoint 10.0.0.3:52428 allowed-ips 10.0.4.1/32
+#
+wg_userspace_basic_body()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ping="atf_check -s exit:0 -o ignore ping -n -c 3 -w 3"
+ local ping_fail="atf_check -s not-exit:0 -o ignore ping -n -c 1 -w 3"
+ local key_priv_local=
+ local key_pub_local=
+ local key_priv_peer=
+ local key_pub_peer=
+ local ip_local=10.0.0.3
+ local ip_peer=10.0.0.2
+ local ip_wg_local=10.0.4.1
+ local ip_wg_peer=10.0.4.2
+ local port_local=52429
+ local port_peer=52428
+ local outfile=./out
+
+ if [ "$ATF_NET_IF_WG_USERSPACE" != yes ]; then
+ atf_skip "set ATF_NET_IF_WG_USERSPACE=yes to run the test"
+ fi
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ rump_server_crypto_start $SOCK_LOCAL virtif wg netinet6
+ atf_check -s exit:0 rump.sysctl -q -w net.inet.ip.dad_count=0
+
+ $DEBUG && netstat -nr -f inet
+
+ $ping $ip_peer
+
+ key_priv_local="6B0dualfIAiEG7/jFGOIHrJMhuypq87xCER/0ieIpE4="
+ key_pub_local="6mQ4lUO3oq5O8FfGW52CFXNbmh5iFT1XMqPzpdrc0nE="
+ key_priv_peer="EF9D8AOkmxjlkiRFqBnfJS+RJJHbUy02u+VkGlBr9Eo="
+ key_pub_peer="2ZM9RvDmMZS/Nuh8OaVaJrwFbO57/WJgeU+JoQ//nko="
+
+ setup_wg_common wg0 inet $ip_wg_local 24 $port_local "$key_priv_local" tun0
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port_peer $ip_wg_peer/32
+
+ $DEBUG && rump.ifconfig wg0
+ $DEBUG && ifconfig tun0
+ $DEBUG && netstat -nr -f inet
+
+ $ping $ip_wg_peer
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ $ifconfig wg0 destroy
+}
+
+wg_userspace_basic_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_init_test_cases()
+{
+
+ atf_add_test_case wg_interoperability_basic
+ atf_add_test_case wg_interoperability_cookie
+ atf_add_test_case wg_userspace_basic
+}
Index: src/tests/net/if_wg/t_misc.sh
diff -u /dev/null src/tests/net/if_wg/t_misc.sh:1.1
--- /dev/null Wed Aug 26 16:03:43 2020
+++ src/tests/net/if_wg/t_misc.sh Wed Aug 26 16:03:42 2020
@@ -0,0 +1,600 @@
+# $NetBSD: t_misc.sh,v 1.1 2020/08/26 16:03:42 riastradh Exp $
+#
+# Copyright (c) 2018 Ryota Ozaki <[email protected]>
+# All rights reserved.
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions
+# are met:
+# 1. Redistributions of source code must retain the above copyright
+# notice, this list of conditions and the following disclaimer.
+# 2. Redistributions in binary form must reproduce the above copyright
+# notice, this list of conditions and the following disclaimer in the
+# documentation and/or other materials provided with the distribution.
+#
+# THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
+# ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+# TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
+# BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+# POSSIBILITY OF SUCH DAMAGE.
+#
+
+BUS=bus
+SOCK_LOCAL=unix://wg_local
+SOCK_PEER=unix://wg_peer
+
+
+atf_test_case wg_rekey cleanup
+wg_rekey_head()
+{
+
+ atf_set "descr" "tests of rekeying of wg(4)"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+wg_rekey_body()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ping="atf_check -s exit:0 -o ignore rump.ping -n -c 1 -w 1"
+ local ip_local=192.168.1.1
+ local ip_peer=192.168.1.2
+ local ip_wg_local=10.0.0.1
+ local ip_wg_peer=10.0.0.2
+ local port=51820
+ local rekey_after_time=3
+ local latest_handshake=
+
+ setup_servers
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ atf_check -s exit:0 -o ignore \
+ rump.sysctl -w net.wg.rekey_after_time=$rekey_after_time
+ export RUMP_SERVER=$SOCK_PEER
+ atf_check -s exit:0 -o ignore \
+ rump.sysctl -w net.wg.rekey_after_time=$rekey_after_time
+
+ # It sets key_priv_local key_pub_local key_priv_peer key_pub_peer
+ generate_keys
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ setup_common shmif0 inet $ip_local 24
+ setup_wg_common wg0 inet $ip_wg_local 24 $port "$key_priv_local"
+
+ export RUMP_SERVER=$SOCK_PEER
+ setup_common shmif0 inet $ip_peer 24
+ setup_wg_common wg0 inet $ip_wg_peer 24 $port "$key_priv_peer"
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port $ip_wg_peer/32
+
+ export RUMP_SERVER=$SOCK_PEER
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/32
+
+ export RUMP_SERVER=$SOCK_LOCAL
+
+ $ping $ip_wg_peer
+
+ latest_handshake=$($HIJACKING wgconfig wg0 show peer peer0 \
+ | awk -F : '/latest-handshake/ {print $2;}')
+ $DEBUG && echo $latest_handshake
+
+ sleep 1
+
+ $ping $ip_wg_peer
+
+ # No reinitiation is performed
+ atf_check -s exit:0 -o match:"$latest_handshake" \
+ $HIJACKING wgconfig wg0 show peer peer0
+
+ # Wait for a reinitiation to be performed
+ sleep $rekey_after_time
+
+ $ping $ip_wg_peer
+
+ # A reinitiation should be performed
+ atf_check -s exit:0 -o not-match:"$latest_handshake" \
+ $HIJACKING wgconfig wg0 show peer peer0
+
+ latest_handshake=$($HIJACKING wgconfig wg0 show peer peer0 \
+ | awk -F : '/latest-handshake/ {print $2;}')
+ $DEBUG && echo $latest_handshake
+
+ # Wait for a reinitiation to be performed again
+ sleep $rekey_after_time
+
+ $ping $ip_wg_peer
+
+ # A reinitiation should be performed
+ atf_check -s exit:0 -o not-match:"$latest_handshake" \
+ $HIJACKING wgconfig wg0 show peer peer0
+
+ destroy_wg_interfaces
+}
+
+wg_rekey_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_test_case wg_handshake_timeout cleanup
+wg_handshake_timeout_head()
+{
+
+ atf_set "descr" "tests of handshake timeout of wg(4)"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+wg_handshake_timeout_body()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ping="atf_check -s exit:0 -o ignore rump.ping -n -c 1 -w 1"
+ local ip_local=192.168.1.1
+ local ip_peer=192.168.1.2
+ local ip_wg_local=10.0.0.1
+ local ip_wg_peer=10.0.0.2
+ local port=51820
+ local rekey_after_time=3
+ local latest_handshake=
+ local outfile=./out
+ local rekey_timeout=3
+ local rekey_attempt_time=8
+ local n=
+
+ setup_servers
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ atf_check -s exit:0 -o ignore \
+ rump.sysctl -w net.wg.rekey_timeout=$rekey_timeout
+ atf_check -s exit:0 -o ignore \
+ rump.sysctl -w net.wg.rekey_attempt_time=$rekey_attempt_time
+ export RUMP_SERVER=$SOCK_PEER
+ atf_check -s exit:0 -o ignore \
+ rump.sysctl -w net.wg.rekey_timeout=$rekey_timeout
+ atf_check -s exit:0 -o ignore \
+ rump.sysctl -w net.wg.rekey_attempt_time=$rekey_attempt_time
+
+ # It sets key_priv_local key_pub_local key_priv_peer key_pub_peer
+ generate_keys
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ setup_common shmif0 inet $ip_local 24
+ setup_wg_common wg0 inet $ip_wg_local 24 $port "$key_priv_local"
+
+ export RUMP_SERVER=$SOCK_PEER
+ setup_common shmif0 inet $ip_peer 24
+ setup_wg_common wg0 inet $ip_wg_peer 24 $port "$key_priv_peer"
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port $ip_wg_peer/32
+
+ export RUMP_SERVER=$SOCK_PEER
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/32
+
+ # Resolve arp
+ export RUMP_SERVER=$SOCK_LOCAL
+ $ping $ip_peer
+
+ export RUMP_SERVER=$SOCK_PEER
+ $ifconfig shmif0 down
+ export RUMP_SERVER=$SOCK_LOCAL
+
+ extract_new_packets $BUS > $outfile
+
+ # Should fail
+ atf_check -s not-exit:0 -o match:'100.0% packet loss' \
+ rump.ping -n -c 1 -w 1 $ip_wg_peer
+
+ sleep $((rekey_attempt_time + rekey_timeout))
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ n=$(grep "$ip_local.$port > $ip_peer.$port" $outfile |wc -l)
+
+ # Give up handshaking after three attempts
+ atf_check_equal $n 3
+
+ export RUMP_SERVER=$SOCK_PEER
+ $ifconfig shmif0 up
+ export RUMP_SERVER=$SOCK_LOCAL
+
+ destroy_wg_interfaces
+}
+
+wg_handshake_timeout_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_test_case wg_cookie cleanup
+wg_cookie_head()
+{
+
+ atf_set "descr" "tests of cookie messages of the wg(4) protocol"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+wg_cookie_body()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ping="atf_check -s exit:0 -o ignore rump.ping -n -i 0.1 -c 3 -w 1"
+ local ping_fail="atf_check -s not-exit:0 -o ignore rump.ping -n -c 1 -w 1"
+ local ip_local=192.168.1.1
+ local ip_peer=192.168.1.2
+ local ip_wg_local=10.0.0.1
+ local ip_wg_peer=10.0.0.2
+ local port=51820
+ local outfile=./out
+ local rekey_timeout=5
+
+ setup_servers
+
+ # It sets key_priv_local key_pub_local key_priv_peer key_pub_peer
+ generate_keys
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ setup_common shmif0 inet $ip_local 24
+ setup_wg_common wg0 inet $ip_wg_local 24 $port "$key_priv_local"
+
+ export RUMP_SERVER=$SOCK_PEER
+ setup_common shmif0 inet $ip_peer 24
+ setup_wg_common wg0 inet $ip_wg_peer 24 $port "$key_priv_peer"
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port $ip_wg_peer/32
+
+ export RUMP_SERVER=$SOCK_PEER
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/32
+
+ export RUMP_SERVER=$SOCK_PEER
+ # Emulate load on the peer
+ atf_check -s exit:0 -o ignore \
+ rump.sysctl -w net.wg.force_underload=1
+
+ export RUMP_SERVER=$SOCK_LOCAL
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ # The peer doesn't return a response message but a cookie message
+ # and a session doesn't start
+ $ping_fail $ip_wg_peer
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+ # XXX length 64 indicates the message is a cookie message
+ atf_check -s exit:0 \
+ -o match:"$ip_peer.$port > $ip_local.$port: UDP, length 64" \
+ cat $outfile
+
+ $DEBUG && $HIJACKING wgconfig wg0 show
+ atf_check -s exit:0 -o match:"latest-handshake: 0" \
+ $HIJACKING wgconfig wg0
+
+ # Wait for restarting a session
+ sleep $rekey_timeout
+
+ # The second attempt should be success because the init message has
+ # a valid cookie.
+ $ping $ip_wg_peer
+
+ $DEBUG && $HIJACKING wgconfig wg0 show
+ atf_check -s exit:0 -o not-match:"latest-handshake: 0" \
+ $HIJACKING wgconfig wg0
+
+ destroy_wg_interfaces
+}
+
+wg_cookie_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_test_case wg_mobility cleanup
+wg_mobility_head()
+{
+
+ atf_set "descr" "tests of the mobility of wg(4)"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+wg_mobility_body()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ping="atf_check -s exit:0 -o ignore rump.ping -n -i 0.1 -c 3 -w 1"
+ local ping_fail="atf_check -s not-exit:0 -o ignore rump.ping -n -c 1 -w 1"
+ local ip_local=192.168.1.1
+ local ip_peer=192.168.1.2
+ local ip_peer_new=192.168.1.3
+ local ip_wg_local=10.0.0.1
+ local ip_wg_peer=10.0.0.2
+ local port=51820
+ local outfile=./out
+
+ setup_servers
+
+ # It sets key_priv_local key_pub_local key_priv_peer key_pub_peer
+ generate_keys
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ setup_common shmif0 inet $ip_local 24
+ setup_wg_common wg0 inet $ip_wg_local 24 $port "$key_priv_local"
+
+ export RUMP_SERVER=$SOCK_PEER
+ setup_common shmif0 inet $ip_peer 24
+ setup_wg_common wg0 inet $ip_wg_peer 24 $port "$key_priv_peer"
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ # Initially, the local doesn't know the endpoint of the peer
+ add_peer wg0 peer0 $key_pub_peer "" $ip_wg_peer/32
+
+ export RUMP_SERVER=$SOCK_PEER
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/32
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ # Ping from the local to the peer doesn't work because the local
+ # doesn't know the endpoint of the peer
+ export RUMP_SERVER=$SOCK_LOCAL
+ $ping_fail $ip_wg_peer
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ export RUMP_SERVER=$SOCK_PEER
+ $ping $ip_wg_local
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ atf_check -s exit:0 -o match:"$ip_local.$port > $ip_peer.$port" cat $outfile
+
+ # Change the IP address of the peer
+ setup_common shmif0 inet $ip_peer_new 24
+ atf_check -s exit:0 rump.ifconfig -w 10
+
+ # Ping from the local to the peer doesn't work because the local
+ # doesn't know the change of the IP address of the peer
+ export RUMP_SERVER=$SOCK_LOCAL
+ $ping_fail $ip_wg_peer
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ atf_check -s exit:0 -o match:"$ip_local.$port > $ip_peer.$port" cat $outfile
+
+ # Ping from the peer to the local works because the local notices
+ # the change and updates the IP address of the peer
+ export RUMP_SERVER=$SOCK_PEER
+ $ping $ip_wg_local
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ atf_check -s exit:0 -o match:"$ip_local.$port > $ip_peer_new.$port" cat $outfile
+ atf_check -s exit:0 -o match:"$ip_peer_new.$port > $ip_local.$port" cat $outfile
+ atf_check -s exit:0 -o not-match:"$ip_local.$port > $ip_peer.$port" cat $outfile
+
+ destroy_wg_interfaces
+}
+
+wg_mobility_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_test_case wg_keepalive cleanup
+wg_keepalive_head()
+{
+
+ atf_set "descr" "tests keepalive messages"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+wg_keepalive_body()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ping="atf_check -s exit:0 -o ignore rump.ping -n -i 0.1 -c 3 -w 1"
+ local ping_fail="atf_check -s not-exit:0 -o ignore rump.ping -n -c 1 -w 1"
+ local ip_local=192.168.1.1
+ local ip_peer=192.168.1.2
+ local ip_peer_new=192.168.1.3
+ local ip_wg_local=10.0.0.1
+ local ip_wg_peer=10.0.0.2
+ local port=51820
+ local outfile=./out
+ local keepalive_timeout=3
+
+ setup_servers
+
+ # It sets key_priv_local key_pub_local key_priv_peer key_pub_peer
+ generate_keys
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ setup_common shmif0 inet $ip_local 24
+ setup_wg_common wg0 inet $ip_wg_local 24 $port "$key_priv_local"
+
+ export RUMP_SERVER=$SOCK_PEER
+ setup_common shmif0 inet $ip_peer 24
+ setup_wg_common wg0 inet $ip_wg_peer 24 $port "$key_priv_peer"
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port $ip_wg_peer/32
+
+ export RUMP_SERVER=$SOCK_PEER
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/32
+
+ # Shorten keepalive_timeout of the peer
+ atf_check -s exit:0 -o ignore \
+ rump.sysctl -w net.wg.keepalive_timeout=$keepalive_timeout
+
+ export RUMP_SERVER=$SOCK_LOCAL
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ $ping $ip_wg_peer
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ sleep $((keepalive_timeout + 1))
+
+ $ping $ip_wg_peer
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ # XXX length 32 indicates the message is a keepalive (empty) message
+ atf_check -s exit:0 -o match:"$ip_peer.$port > $ip_local.$port: UDP, length 32" \
+ cat $outfile
+
+ destroy_wg_interfaces
+}
+
+wg_keepalive_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_test_case wg_psk cleanup
+wg_psk_head()
+{
+
+ atf_set "descr" "tests preshared-key"
+ atf_set "require.progs" "rump_server" "wgconfig" "wg-keygen"
+}
+
+test_psk_common()
+{
+}
+
+wg_psk_body()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local ping="atf_check -s exit:0 -o ignore rump.ping -n -i 0.1 -c 3 -w 1"
+ local ping_fail="atf_check -s not-exit:0 -o ignore rump.ping -n -c 1 -w 1"
+ local ip_local=192.168.1.1
+ local ip_peer=192.168.1.2
+ local ip_peer_new=192.168.1.3
+ local ip_wg_local=10.0.0.1
+ local ip_wg_peer=10.0.0.2
+ local port=51820
+ local outfile=./out
+ local pskfile=./psk
+ local rekey_after_time=3
+
+ setup_servers
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ atf_check -s exit:0 -o ignore \
+ rump.sysctl -w net.wg.rekey_after_time=$rekey_after_time
+ export RUMP_SERVER=$SOCK_PEER
+ atf_check -s exit:0 -o ignore \
+ rump.sysctl -w net.wg.rekey_after_time=$rekey_after_time
+
+ # It sets key_priv_local key_pub_local key_priv_peer key_pub_peer
+ generate_keys
+ key_psk=$(wg-keygen --psk)
+ $DEBUG && echo $key_psk
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ setup_common shmif0 inet $ip_local 24
+ setup_wg_common wg0 inet $ip_wg_local 24 $port "$key_priv_local"
+
+ export RUMP_SERVER=$SOCK_PEER
+ setup_common shmif0 inet $ip_peer 24
+ setup_wg_common wg0 inet $ip_wg_peer 24 $port "$key_priv_peer"
+
+ echo "$key_psk" > $pskfile
+
+ export RUMP_SERVER=$SOCK_LOCAL
+
+ # The local always has the preshared key
+ add_peer wg0 peer0 $key_pub_peer $ip_peer:$port $ip_wg_peer/32 \
+ $pskfile "$key_psk"
+
+ export RUMP_SERVER=$SOCK_PEER
+
+ # First, try the peer without the preshared key
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/32
+
+ export RUMP_SERVER=$SOCK_LOCAL
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ $ping_fail $ip_wg_peer
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ # Next, try with the preshared key
+ export RUMP_SERVER=$SOCK_PEER
+ delete_peer wg0 peer0
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/32 \
+ $pskfile "$key_psk"
+
+ # Need a rekey
+ atf_check -s exit:0 sleep $((rekey_after_time + 1))
+
+ export RUMP_SERVER=$SOCK_LOCAL
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ $ping $ip_wg_peer
+
+ extract_new_packets $BUS > $outfile
+ $DEBUG && cat $outfile
+
+ # Then, try again without the preshared key just in case
+ export RUMP_SERVER=$SOCK_PEER
+ delete_peer wg0 peer0
+ add_peer wg0 peer0 $key_pub_local $ip_local:$port $ip_wg_local/32
+
+ # Need a rekey
+ atf_check -s exit:0 sleep $((rekey_after_time + 1))
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ $ping_fail $ip_wg_peer
+
+ rm -f $pskfile
+
+ destroy_wg_interfaces
+}
+
+wg_psk_cleanup()
+{
+
+ $DEBUG && dump
+ cleanup
+}
+
+atf_init_test_cases()
+{
+
+ atf_add_test_case wg_rekey
+ atf_add_test_case wg_handshake_timeout
+ atf_add_test_case wg_cookie
+ atf_add_test_case wg_mobility
+ atf_add_test_case wg_keepalive
+ atf_add_test_case wg_psk
+}
Index: src/tests/net/if_wg/t_tunnel.sh
diff -u /dev/null src/tests/net/if_wg/t_tunnel.sh:1.1
--- /dev/null Wed Aug 26 16:03:43 2020
+++ src/tests/net/if_wg/t_tunnel.sh Wed Aug 26 16:03:42 2020
@@ -0,0 +1,332 @@
+# $NetBSD: t_tunnel.sh,v 1.1 2020/08/26 16:03:42 riastradh Exp $
+#
+# Copyright (c) 2018 Ryota Ozaki <[email protected]>
+# All rights reserved.
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions
+# are met:
+# 1. Redistributions of source code must retain the above copyright
+# notice, this list of conditions and the following disclaimer.
+# 2. Redistributions in binary form must reproduce the above copyright
+# notice, this list of conditions and the following disclaimer in the
+# documentation and/or other materials provided with the distribution.
+#
+# THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
+# ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+# TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
+# BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+# POSSIBILITY OF SUCH DAMAGE.
+#
+
+BUS_LOCAL=bus_local
+BUS_TUN=bus_tun
+BUS_PEER=bus_peer
+SOCK_LOCAL=unix://wg_local
+SOCK_TUN_LOCAL=unix://wg_tun_local
+SOCK_TUN_PEER=unix://wg_tun_peer
+SOCK_PEER=unix://wg_peer
+
+escape_key()
+{
+
+ echo $1 | sed 's/\+/\\+/g' | sed 's|\/|\\/|g'
+}
+
+setup_servers()
+{
+
+ rump_server_start $SOCK_LOCAL netinet6
+ rump_server_add_iface $SOCK_LOCAL shmif0 $BUS_LOCAL
+
+ rump_server_crypto_start $SOCK_TUN_LOCAL netinet6 wg
+ rump_server_add_iface $SOCK_TUN_LOCAL shmif0 $BUS_LOCAL
+ rump_server_add_iface $SOCK_TUN_LOCAL shmif1 $BUS_TUN
+
+ rump_server_crypto_start $SOCK_TUN_PEER netinet6 wg
+ rump_server_add_iface $SOCK_TUN_PEER shmif0 $BUS_PEER
+ rump_server_add_iface $SOCK_TUN_PEER shmif1 $BUS_TUN
+
+ rump_server_start $SOCK_PEER netinet6
+ rump_server_add_iface $SOCK_PEER shmif0 $BUS_PEER
+}
+
+setup_edge()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local proto=$1
+ local ip=$2
+ local prefix=$3
+ local gw=$4
+ local ip_bad=$5
+ local alias=
+
+ atf_check -s exit:0 rump.sysctl -q -w net.inet.ip.dad_count=0
+ atf_check -s exit:0 rump.sysctl -q -w net.inet6.ip6.dad_count=0
+ $ifconfig shmif0 $proto $ip/$prefix
+ atf_check -s exit:0 -o ignore rump.route add -$proto default $gw
+
+ if [ -z "$ip_bad" ]; then
+ return
+ fi
+
+ if [ $proto = inet ]; then
+ alias="alias"
+ fi
+
+ $ifconfig shmif0 $proto $ip_bad/$prefix $alias
+}
+
+setup_ip()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local proto=$1
+ local ip=$2
+ local prefix=$3
+
+ $ifconfig shmif0 $proto $ip/$prefix
+}
+setup_router()
+{
+
+ atf_check -s exit:0 rump.sysctl -q -w net.inet.ip.forwarding=1
+ atf_check -s exit:0 rump.sysctl -q -w net.inet6.ip6.forwarding=1
+ atf_check -s exit:0 rump.sysctl -q -w net.inet.ip.dad_count=0
+ atf_check -s exit:0 rump.sysctl -q -w net.inet6.ip6.dad_count=0
+}
+
+setup_wg()
+{
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local wgconfig="atf_check -s exit:0 $HIJACKING wgconfig"
+ local proto=$1
+ local ip=$2
+ local prefix=$3
+ local port=$4
+ local key_priv="$5"
+ local privfile=./tmp
+
+ $ifconfig wg0 create
+ $ifconfig wg0 $proto $ip/$prefix
+ $DEBUG && rump.netstat -nr
+ echo $key_priv > $privfile
+ $wgconfig wg0 set private-key $privfile
+ $wgconfig wg0 set listen-port $port
+ rm -f $privfile
+ $ifconfig wg0 up
+
+ check_conf_port wg0 $port
+ check_conf_privkey wg0 "$key_priv"
+}
+
+setup_wg_route()
+{
+ local proto=$1
+ local subnet=$2
+ local subnet_bad=$3
+
+ atf_check -s exit:0 -o ignore rump.route add -$proto -net $subnet -link wg0 -iface
+ if [ -n "$subnet_bad" ]; then
+ atf_check -s exit:0 -o ignore rump.route add -$proto -net $subnet_bad -link wg0 -iface
+ fi
+}
+
+prepare_file()
+{
+ local file=$1
+ local data="0123456789"
+
+ touch $file
+ for i in `seq 1 200`
+ do
+ echo $data >> $file
+ done
+}
+
+test_tcp()
+{
+ local proto=$1
+ local ip_peer=$2
+ local _proto=
+
+ prepare_file ./file_send
+
+ if [ $proto = inet ]; then
+ _proto=ipv4
+ else
+ _proto=ipv6
+ fi
+ start_nc_server $SOCK_PEER 1234 ./file_recv $_proto
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ # Send a file to the server
+ # XXX Need a bit longer timeout value because the packet processing
+ # of the implementation is quite inefficient...
+ atf_check -s exit:0 $HIJACKING \
+ nc -N -w 20 $ip_peer 1234 < ./file_send
+ $DEBUG && extract_new_packets $BUS > ./out
+ $DEBUG && cat ./out
+ stop_nc_server
+ $DEBUG && ls -s ./file_send ./file_recv
+ $DEBUG && wc -l ./file_send
+ $DEBUG && wc -l ./file_recv
+ $DEBUG && diff -u ./file_send ./file_recv
+ atf_check -s exit:0 diff -q ./file_send ./file_recv
+ rm -f ./out ./file_recv ./file_send
+}
+
+wg_tunnel_common()
+{
+ local outer_proto=$1
+ local inner_proto=$2
+ local ifconfig="atf_check -s exit:0 rump.ifconfig"
+ local wgconfig="atf_check -s exit:0 $HIJACKING wgconfig"
+ local port=51820
+ local ip_local= ip_peer=
+ local ip_wg_local= ip_wg_peer=
+ local outer_prefix= outer_prefixall=
+ local inner_prefix= inner_prefixall=
+
+ if [ $outer_proto = inet ]; then
+ ip_tun_local_tun=192.168.10.1
+ ip_tun_peer_tun=192.168.10.2
+ outer_prefix=24
+ outer_prefixall=32
+ else
+ ip_tun_local_tun=fc00:10::1
+ ip_tun_peer_tun=fc00:10::2
+ outer_prefix=64
+ outer_prefixall=128
+ fi
+
+ if [ $inner_proto = inet ]; then
+ ip_local=192.168.1.2
+ ip_tun_local=192.168.1.1
+ ip_wg_local=10.0.0.1
+ ip_wg_peer=10.0.0.2
+ ip_tun_peer=192.168.2.1
+ ip_peer=192.168.2.2
+ ip_peer_bad=192.168.3.2
+ inner_prefix=24
+ inner_prefixall=32
+ subnet_local=192.168.1.0/24
+ subnet_peer=192.168.2.0/24
+ subnet_peer_bad=192.168.3.0/24
+ else
+ ip_tun_local=fc00:1::1
+ ip_local=fc00:1::2
+ ip_wg_local=fd00::1
+ ip_wg_peer=fd00::2
+ ip_tun_peer=fc00:2::1
+ ip_peer=fc00:2::2
+ ip_peer_bad=fc00:3::2
+ inner_prefix=64
+ inner_prefixall=128
+ subnet_local=fc00:1::/64
+ subnet_peer=fc00:2::/64
+ subnet_peer_bad=fc00:3::/64
+ fi
+
+ setup_servers
+
+ # It sets key_priv_local key_pub_local key_priv_peer key_pub_peer
+ generate_keys
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ setup_edge $inner_proto $ip_local $inner_prefix $ip_tun_local
+
+ export RUMP_SERVER=$SOCK_TUN_LOCAL
+ setup_router
+ $ifconfig shmif0 $inner_proto $ip_tun_local/$inner_prefix
+ $ifconfig shmif1 $outer_proto $ip_tun_local_tun/$outer_prefix
+ setup_wg $inner_proto $ip_wg_local $inner_prefix $port "$key_priv_local"
+ setup_wg_route $inner_proto $subnet_peer $subnet_peer_bad
+
+ export RUMP_SERVER=$SOCK_TUN_PEER
+ setup_router
+ $ifconfig shmif0 $inner_proto $ip_tun_peer/$inner_prefix
+ $ifconfig shmif1 $outer_proto $ip_tun_peer_tun/$outer_prefix
+ setup_wg $inner_proto $ip_wg_peer $inner_prefix $port "$key_priv_peer"
+ setup_wg_route $inner_proto $subnet_local
+
+ export RUMP_SERVER=$SOCK_PEER
+ setup_edge $inner_proto $ip_peer $inner_prefix $ip_tun_peer $ip_peer_bad
+
+ export RUMP_SERVER=$SOCK_TUN_LOCAL
+ add_peer wg0 peer0 $key_pub_peer $ip_tun_peer_tun:$port \
+ $ip_wg_peer/$inner_prefixall,$subnet_peer
+
+ export RUMP_SERVER=$SOCK_TUN_PEER
+ add_peer wg0 peer0 $key_pub_local $ip_tun_local_tun:$port \
+ $ip_wg_local/$inner_prefixall,$subnet_local
+
+ export RUMP_SERVER=$SOCK_TUN_LOCAL
+ atf_check -s exit:0 -o match:"latest-handshake: 0" \
+ $HIJACKING wgconfig wg0 show peer peer0
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ check_ping $inner_proto $ip_peer
+
+ export RUMP_SERVER=$SOCK_TUN_LOCAL
+ atf_check -s exit:0 -o not-match:"latest-handshake: 0" \
+ $HIJACKING wgconfig wg0 show peer peer0
+
+ export RUMP_SERVER=$SOCK_LOCAL
+ # ping fails because the subnet of the IP is not allowed
+ check_ping_fail $inner_proto $ip_peer_bad
+
+ #
+ # Test TCP stream over the tunnel
+ #
+ test_tcp $inner_proto $ip_peer
+
+ export RUMP_SERVER=$SOCK_TUN_LOCAL
+ $ifconfig wg0 destroy
+ export RUMP_SERVER=$SOCK_TUN_PEER
+ $ifconfig wg0 destroy
+}
+
+add_tunnel_test()
+{
+ local inner=$1
+ local outer=$2
+ local ipv4=inet
+ local ipv6=inet6
+
+ name="wg_tunnel_${inner}_over_${outer}"
+ fulldesc="Test wg(4) with ${inner} over ${outer}"
+
+ eval inner=\$$inner
+ eval outer=\$$outer
+
+ atf_test_case ${name} cleanup
+ eval "
+ ${name}_head() {
+ atf_set descr \"${fulldesc}\"
+ atf_set require.progs rump_server wgconfig wg-keygen
+ }
+ ${name}_body() {
+ wg_tunnel_common $outer $inner
+ rump_server_destroy_ifaces
+ }
+ ${name}_cleanup() {
+ \$DEBUG && dump
+ cleanup
+ }"
+ atf_add_test_case ${name}
+}
+
+atf_init_test_cases()
+{
+
+ add_tunnel_test ipv4 ipv4
+ add_tunnel_test ipv4 ipv6
+ add_tunnel_test ipv6 ipv4
+ add_tunnel_test ipv6 ipv6
+}