public inbox for passt-dev@passt.top
 help / color / mirror / code / Atom feed
From: David Gibson <david@gibson.dropbear.id.au>
To: passt-dev@passt.top
Subject: [PATCH v2 09/32] test: Use context system for guest commands
Date: Thu, 08 Sep 2022 16:15:58 +1000	[thread overview]
Message-ID: <20220908061621.2430844-10-david@gibson.dropbear.id.au> (raw)
In-Reply-To: <20220908061621.2430844-1-david@gibson.dropbear.id.au>

[-- Attachment #1: Type: text/plain, Size: 12809 bytes --]

Extends the context system in the test scripts to allow executing commands
within a guest.  Do this without requiring an existing network in the guest
by using socat to run ssh via a vsock connection.

We do need some additional "sleep"s in the tests, because the new
faster dispatch means that sometimes we attempt to connect before
socat has managed to listen.

For now, only use this for the plain "passt" tests.  The "passt_in_ns" and
other tests have additional complications we still need to deal with.

Signed-off-by: David Gibson <david(a)gibson.dropbear.id.au>
---
 test/.gitignore      |  2 ++
 test/Makefile        |  7 +++++--
 test/lib/context     | 28 +++++++++++++++++++++++++++-
 test/lib/layout      |  4 +---
 test/lib/setup       | 13 +++++++++----
 test/lib/term        |  9 ++++++---
 test/passt.mbuto     | 32 +++++++++++++++++++++++++++++---
 test/tcp/passt       |  2 ++
 test/tcp/passt_in_ns |  8 ++++++++
 test/udp/passt       |  1 +
 10 files changed, 90 insertions(+), 16 deletions(-)

diff --git a/test/.gitignore b/test/.gitignore
index d477a42..0f91c7d 100644
--- a/test/.gitignore
+++ b/test/.gitignore
@@ -11,3 +11,5 @@ QEMU_EFI.fd
 *.stop
 *.js
 nsholder
+guest-key
+guest-key.pub
diff --git a/test/Makefile b/test/Makefile
index e0dc7ac..cc1a818 100644
--- a/test/Makefile
+++ b/test/Makefile
@@ -57,7 +57,7 @@ DOWNLOAD_ASSETS = mbuto \
 LOCAL_ASSETS = mbuto.img QEMU_EFI.fd \
 	$(DEBIAN_IMGS:%=prepared-%) $(FEDORA_IMGS:%=prepared-%) \
 	$(UBUNTU_NEW_IMGS:%=prepared-%) \
-	nsholder
+	nsholder guest-key guest-key.pub
 
 ASSETS = $(DOWNLOAD_ASSETS) $(LOCAL_ASSETS)
 
@@ -68,7 +68,10 @@ assets: $(ASSETS)
 mbuto:
 	git clone git://mbuto.sh/mbuto
 
-mbuto.img: passt.mbuto mbuto
+guest-key guest-key.pub:
+	ssh-keygen -f guest-key -N ''
+
+mbuto.img: passt.mbuto mbuto guest-key.pub
 	./mbuto/mbuto -p ./$< -c lz4 -f $@
 
 nsholder: nsholder.c
diff --git a/test/lib/context b/test/lib/context
index 0d92d8f..ccb0004 100644
--- a/test/lib/context
+++ b/test/lib/context
@@ -41,12 +41,38 @@ context_setup_nsenter() {
 	echo "nsenter $@ sh -c" > "${__prefix}.enter"
 }
 
+# context_setup_guest() - Create a new context for running commands in a guest
+# $1:        Context name
+# $2:        CID to use for vsock
+context_setup_guest() {
+	__name="$1"
+	__cid="$2"
+	__prefix="${LOGDIR}/context_${__name}"
+	context_setup_common "${__name}"
+
+	cat > "${__prefix}.ssh" <<EOF
+Host ${__name}
+	User root
+	UserKnownHostsFile ${__prefix}.hosts
+	StrictHostKeyChecking no
+	IdentityFile ${BASEPATH}/guest-key
+	IdentityAgent none
+	ProxyCommand socat - VSOCK-CONNECT:${__cid}:22
+EOF
+	echo "ssh -F ${__prefix}.ssh ${__name}" > "${__prefix}.enter"
+
+	# Wait for the guest to be booted and accepting connections
+	while ! ssh -F "${__prefix}.ssh" "${__name}" :; do
+		sleep 0.1
+	done
+}
+
 # context_teardown() - Remove a context (leave log files intact)
 # $1:	Context name
 context_teardown() {
 	__name="$1"
 	__prefix="${LOGDIR}/context_${__name}"
-	rm -f "${__prefix}.enter"
+	rm -f "${__prefix}.enter" "${__prefix}.ssh" "${__prefix}.hosts"
 }
 
 # context_exists() - Test if a context currently exists
diff --git a/test/lib/layout b/test/lib/layout
index 1401955..985d31b 100644
--- a/test/lib/layout
+++ b/test/lib/layout
@@ -92,15 +92,13 @@ layout_passt() {
 
 	get_info_cols
 
-	tmux pipe-pane -O -t ${PANE_GUEST} "cat >> ${LOGDIR}/pane_guest.log"
-	tmux select-pane -t ${PANE_GUEST} -T "guest"
-
 	tmux send-keys -l -t ${PANE_INFO} 'while cat /tmp/.passt_test_log_pipe; do :; done'
 	tmux send-keys -t ${PANE_INFO} -N 100 C-m
 	tmux select-pane -t ${PANE_INFO} -T "test log"
 
 	pane_watch_contexts ${PANE_HOST} host host
 	pane_watch_contexts ${PANE_PASST} passt passt
+	pane_watch_contexts ${PANE_GUEST} guest qemu guest
 
 	info_layout "single passt instance with guest"
 
diff --git a/test/lib/setup b/test/lib/setup
index ac36ac3..4d8c81f 100755
--- a/test/lib/setup
+++ b/test/lib/setup
@@ -35,6 +35,7 @@ setup_distro() {
 setup_passt() {
 	context_setup_host host
 	context_setup_host passt
+	context_setup_host qemu
 
 	layout_passt
 
@@ -55,7 +56,8 @@ setup_passt() {
 	context_run_bg passt "valgrind --max-stackframe=$((4 * 1024 * 1024)) --trace-children=yes --vgdb=no --error-exitcode=1 --suppressions=test/valgrind.supp ./passt ${__opts} -f -t 10001 -u 10001 -P passt.pid"
 	sleep 5
 
-	pane_run GUEST './qrap 5 qemu-system-$(uname -m)'                  \
+	GUEST_CID=94557
+	context_run_bg qemu './qrap 5 qemu-system-$(uname -m)'		   \
 		' -machine accel=kvm'                                      \
 		' -m '${VMEM}' -cpu host -smp '${VCPUS}                    \
 		' -kernel ' "/boot/vmlinuz-$(uname -r)"			   \
@@ -65,8 +67,10 @@ setup_passt() {
 		'virtio-net.napi_tx=1"'					   \
 		" -device virtio-net-pci,netdev=hostnet0,x-txburst=16384"  \
 		" -netdev socket,fd=5,id=hostnet0"			   \
-		' -pidfile passt_qemu.pid'
-	pane_status GUEST
+		" -pidfile passt_qemu.pid"				   \
+		" -device vhost-vsock-pci,guest-cid=$GUEST_CID"
+
+	context_setup_guest guest $GUEST_CID
 }
 
 # setup_pasta() - Create a network and user namespace, connect pasta to it
@@ -307,11 +311,12 @@ teardown_distro() {
 # teardown_passt() - Kill qemu, remove passt PID file
 teardown_passt() {
 	kill $(cat passt_qemu.pid)
-	pane_wait GUEST
+
 	rm passt.pid
 
 	teardown_context_watch ${PANE_HOST} host
 	teardown_context_watch ${PANE_PASST} passt
+	teardown_context_watch ${PANE_GUEST} qemu guest
 }
 
 # teardown_passt() - Exit namespace, kill pasta process
diff --git a/test/lib/term b/test/lib/term
index a06c80b..ae99010 100755
--- a/test/lib/term
+++ b/test/lib/term
@@ -266,7 +266,8 @@ pane_or_context_run() {
 	__name="${1}"
 	shift
 	if context_exists "${__name}"; then
-		context_run "${__name}" "$@" >/dev/null 2>&1
+		# Redirect stdin to stop ssh from eating the test instructions file we have on stdin
+		context_run "${__name}" "$@" >/dev/null 2>&1 < /dev/null
 	else
 		__uc="$(echo "${__name}" | tr [a-z] [A-Z])"
 		pane_run "${__uc}" "$@"
@@ -281,7 +282,8 @@ pane_or_context_run_bg() {
 	__name="${1}"
 	shift
 	if context_exists "${__name}"; then
-		context_run_bg "${__name}" "$@" >/dev/null 2>&1
+		# Redirect stdin to stop ssh from eating the test instructions file we have on stdin
+		context_run_bg "${__name}" "$@" >/dev/null 2>&1 < /dev/null
 	else
 		__uc="$(echo "${__name}" | tr [a-z] [A-Z])"
 		pane_run "${__uc}" "$@"
@@ -295,7 +297,8 @@ pane_or_context_output() {
 	__name="${1}"
 	shift
 	if context_exists "${__name}"; then
-		__output=$(context_run "${__name}" "$@" 2>/dev/null)
+		# Redirect stdin to stop ssh from eating the test instructions file we have on stdin
+		__output=$(context_run "${__name}" "$@" 2>/dev/null </dev/null)
 		if [ -z "${__output}" ]; then
 			echo "@EMPTY@"
 		else
diff --git a/test/passt.mbuto b/test/passt.mbuto
index 8b41674..d29f456 100755
--- a/test/passt.mbuto
+++ b/test/passt.mbuto
@@ -13,15 +13,15 @@
 PROGS="${PROGS:-ash,dash,bash ip mount ls insmod mkdir ln cat chmod lsmod
        modprobe find grep mknod mv rm umount jq iperf3 dhclient hostname
        sed tr chown sipcalc cut md5sum socat dd strace ping tail killall sleep
-       sysctl nproc tcp_rr tcp_crr udp_rr which tee seq bc}"
+       sysctl nproc tcp_rr tcp_crr udp_rr which tee seq bc sshd ssh-keygen}"
 
-KMODS="${KMODS:- virtio_net virtio_pci}"
+KMODS="${KMODS:- virtio_net virtio_pci vmw_vsock_virtio_transport}"
 
 LINKS="${LINKS:-
 	 ash,dash,bash		/init
 	 ash,dash,bash		/bin/sh}"
 
-DIRS="${DIRS} /tmp /sbin /var/log /var/run /var/lib"
+DIRS="${DIRS} /tmp /sbin /usr/share /var/log /var/lib /etc/ssh /run/sshd /root/.ssh"
 
 FIXUP="${FIXUP}"'
 	cat > /sbin/dhclient-script << EOF
@@ -46,7 +46,33 @@ exit 0
 EOF
 	chmod 755 /sbin/dhclient-script
 	ln -s /sbin /usr/sbin
+	ln -s /bin /usr/bin
+	ln -s /run /var/run
 	:> /etc/fstab
+
+	# sshd(dropbear) via vsock
+	cat > /etc/passwd << EOF
+root:x:0:0:root:/root:/bin/sh
+sshd:x:100:100:Privilege-separated SSH:/var/empty/sshd:/sbin/nologin
+EOF
+	cat > /etc/shadow << EOF
+root:::0:99999:7:::
+EOF
+	chmod 000 /etc/shadow
+
+	:> /etc/ssh/sshd_config
+	ssh-keygen -A
+	chmod 700 /root/.ssh
+	chmod 700 /run/sshd
+	# Alternative location for the priv separation dir
+	ln -s /run/sshd /usr/share/empty.sshd
+
+	cat > /root/.ssh/authorized_keys <<EOF
+'"$(cat guest-key.pub)"'
+EOF
+	chmod 600 /root/.ssh/authorized_keys
+	chmod 700 /root
+	socat VSOCK-LISTEN:22,fork EXEC:"sshd -i -e" 2> /var/log/vsock-ssh.log &
 	sh +m
 '
 
diff --git a/test/tcp/passt b/test/tcp/passt
index 6e65137..265f270 100644
--- a/test/tcp/passt
+++ b/test/tcp/passt
@@ -17,6 +17,7 @@ htools	dd socat ip jq md5sum cut
 test	TCP/IPv4: host to guest: big transfer
 temp	TEMP_BIG
 guestb	socat -u TCP4-LISTEN:10001,reuseaddr OPEN:test_big.bin,create,trunc
+sleep	1
 host	dd if=/dev/urandom bs=1M count=10 > __TEMP_BIG__
 host	socat -u OPEN:__TEMP_BIG__ TCP4:127.0.0.1:10001
 guestw
@@ -35,6 +36,7 @@ check	[ "__GUEST_MD5_BIG__" = "__HOST_MD5_BIG__" ]
 test	TCP/IPv4: host to guest: small transfer
 temp	TEMP_SMALL
 guestb	socat -u TCP4-LISTEN:10001,reuseaddr OPEN:test_small.bin,create,trunc
+sleep	1
 host	dd if=/dev/urandom bs=2k count=1 > __TEMP_SMALL__
 host	socat -u OPEN:__TEMP_SMALL__ TCP4:127.0.0.1:10001
 guestw
diff --git a/test/tcp/passt_in_ns b/test/tcp/passt_in_ns
index 976e4e9..cb01781 100644
--- a/test/tcp/passt_in_ns
+++ b/test/tcp/passt_in_ns
@@ -18,6 +18,7 @@ nstools	socat ip jq md5sum cut
 test	TCP/IPv4: host to guest: big transfer
 temp	TEMP_BIG
 guestb	socat -u TCP4-LISTEN:10001 OPEN:test_big.bin,create,trunc
+sleep	1
 host	dd if=/dev/urandom bs=1M count=10 of=__TEMP_BIG__
 host	socat -u OPEN:__TEMP_BIG__ TCP4:127.0.0.1:10001
 guestw
@@ -82,6 +83,7 @@ check	[ "__GUEST_MD5_BIG__" = "__MD5_BIG__" ]
 test	TCP/IPv4: host to guest: small transfer
 temp	TEMP_SMALL
 guestb	socat -u TCP4-LISTEN:10001 OPEN:test_small.bin,create,trunc
+sleep	1
 host	dd if=/dev/urandom bs=2k count=100 of=__TEMP_SMALL__
 host	socat -u OPEN:__TEMP_SMALL__ TCP4:127.0.0.1:10001
 guestw
@@ -129,6 +131,7 @@ check	[ "__HOST_MD5_SMALL__" = "__MD5_SMALL__" ]
 
 test	TCP/IPv4: ns to guest (using loopback address): small transfer
 guestb	socat -u TCP4-LISTEN:10001 OPEN:test_small.bin,create,trunc
+sleep	1
 ns	socat -u OPEN:__TEMP_NS_SMALL__ TCP4:127.0.0.1:10001
 guestw
 gout	GUEST_MD5_SMALL md5sum test_small.bin | cut -d' ' -f1
@@ -136,6 +139,7 @@ check	[ "__GUEST_MD5_SMALL__" = "__MD5_SMALL__" ]
 
 test	TCP/IPv4: ns to guest (using namespace address): small transfer
 guestb	socat -u TCP4-LISTEN:10001 OPEN:test_small.bin,create,trunc
+sleep	1
 ns	socat -u OPEN:__TEMP_NS_SMALL__ TCP4:__ADDR__:10001
 guestw
 gout	GUEST_MD5_SMALL md5sum test_small.bin | cut -d' ' -f1
@@ -143,6 +147,7 @@ check	[ "__GUEST_MD5_SMALL__" = "__MD5_SMALL__" ]
 
 test	TCP/IPv6: host to guest: big transfer
 guestb	socat -u TCP6-LISTEN:10001 OPEN:test_big.bin,create,trunc
+sleep	1
 host	socat -u OPEN:__TEMP_BIG__ TCP6:[::1]:10001
 guestw
 gout	GUEST_MD5_BIG md5sum test_big.bin | cut -d' ' -f1
@@ -188,6 +193,7 @@ check	[ "__HOST_MD5_BIG__" = "__MD5_BIG__" ]
 
 test	TCP/IPv6: ns to guest (using loopback address): big transfer
 guestb	socat -u TCP6-LISTEN:10001 OPEN:test_big.bin,create,trunc
+sleep	1
 ns	socat -u OPEN:__TEMP_NS_BIG__ TCP6:[::1]:10001
 guestw
 gout	GUEST_MD5_BIG md5sum test_big.bin | cut -d' ' -f1
@@ -203,6 +209,7 @@ check	[ "__GUEST_MD5_BIG__" = "__MD5_BIG__" ]
 
 test	TCP/IPv6: host to guest: small transfer
 guestb	socat -u TCP6-LISTEN:10001 OPEN:test_small.bin,create,trunc
+sleep	1
 host	socat -u OPEN:__TEMP_SMALL__ TCP6:[::1]:10001
 guestw
 gout	GUEST_MD5_SMALL md5sum test_small.bin | cut -d' ' -f1
@@ -248,6 +255,7 @@ check	[ "__HOST_MD5_SMALL__" = "__MD5_SMALL__" ]
 
 test	TCP/IPv6: ns to guest (using loopback address): small transfer
 guestb	socat -u TCP6-LISTEN:10001 OPEN:test_small.bin,create,trunc
+sleep	1
 ns	socat -u OPEN:__TEMP_NS_SMALL__ TCP6:[::1]:10001
 guestw
 gout	GUEST_MD5_SMALL md5sum test_small.bin | cut -d' ' -f1
diff --git a/test/udp/passt b/test/udp/passt
index 7c58648..a14e6d2 100644
--- a/test/udp/passt
+++ b/test/udp/passt
@@ -18,6 +18,7 @@ test	UDP/IPv4: host to guest
 temp	TEMP
 temp	SC_PID
 guestb	(socat -u UDP4-LISTEN:10001 STDOUT & echo $! > __SC_PID__) | tee test.bin | (grep -qm1 "END_OF_TEST" && kill $(cat __SC_PID__))
+sleep	1
 host	dd if=/dev/urandom bs=1k count=5 > __TEMP__ && printf "\nEND_OF_TEST\n" >> __TEMP__
 host	socat -u OPEN:__TEMP__ UDP4:127.0.0.1:10001
 guestw
-- 
@@ -18,6 +18,7 @@ test	UDP/IPv4: host to guest
 temp	TEMP
 temp	SC_PID
 guestb	(socat -u UDP4-LISTEN:10001 STDOUT & echo $! > __SC_PID__) | tee test.bin | (grep -qm1 "END_OF_TEST" && kill $(cat __SC_PID__))
+sleep	1
 host	dd if=/dev/urandom bs=1k count=5 > __TEMP__ && printf "\nEND_OF_TEST\n" >> __TEMP__
 host	socat -u OPEN:__TEMP__ UDP4:127.0.0.1:10001
 guestw
-- 
2.37.3


  parent reply	other threads:[~2022-09-08  6:15 UTC|newest]

Thread overview: 33+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2022-09-08  6:15 [PATCH v2 00/32] Improve handling of test temporary files David Gibson
2022-09-08  6:15 ` [PATCH v2 01/32] test: Correctly match "background" with "wait" commands David Gibson
2022-09-08  6:15 ` [PATCH v2 02/32] test: Context execution helpers David Gibson
2022-09-08  6:15 ` [PATCH v2 03/32] test: Allow a tmux pane to watch commands executed in contexts David Gibson
2022-09-08  6:15 ` [PATCH v2 04/32] test: Integration of old-style pane execution and new context execution David Gibson
2022-09-08  6:15 ` [PATCH v2 05/32] test: Issue host commands via context for most tests David Gibson
2022-09-08  6:15 ` [PATCH v2 06/32] test: Use new-style contexts for passt pane in the pasta and passt tests David Gibson
2022-09-08  6:15 ` [PATCH v2 07/32] test: Add nsholder utility David Gibson
2022-09-08  6:15 ` [PATCH v2 08/32] test: Extend context system to run commands in namespace for pasta tests David Gibson
2022-09-08  6:15 ` David Gibson [this message]
2022-09-08  6:15 ` [PATCH v2 10/32] test: Use context system for two_guests tests David Gibson
2022-09-08  6:16 ` [PATCH v2 11/32] test: Use new-style command issue for passt_in_ns tests David Gibson
2022-09-08  6:16 ` [PATCH v2 12/32] Don't store UID & GID persistently in the context structure David Gibson
2022-09-08  6:16 ` [PATCH v2 13/32] Split checking for root from dropping root privilege David Gibson
2022-09-08  6:16 ` [PATCH v2 14/32] Consolidate determination of UID/GID to run as David Gibson
2022-09-08  6:16 ` [PATCH v2 15/32] Safer handling if we can't open /proc/self/uid_map David Gibson
2022-09-08  6:16 ` [PATCH v2 16/32] Move self-isolation code into a separate file David Gibson
2022-09-08  6:16 ` [PATCH v2 17/32] Consolidate validation of pasta namespace options David Gibson
2022-09-08  6:16 ` [PATCH v2 18/32] Clean up and rename conf_ns_open() David Gibson
2022-09-08  6:16 ` [PATCH v2 19/32] Correctly handle --netns-only in pasta_start_ns() David Gibson
2022-09-08  6:16 ` [PATCH v2 20/32] Handle userns isolation and dropping root at the same time David Gibson
2022-09-08  6:16 ` [PATCH v2 21/32] Allow --userns when pasta spawns a command David Gibson
2022-09-08  6:16 ` [PATCH v2 22/32] test: Group tests by context then protocol, rather than the reverse David Gibson
2022-09-08  6:16 ` [PATCH v2 23/32] test: Remove unused variable FFMPEG_PID_FILE David Gibson
2022-09-08  6:16 ` [PATCH v2 24/32] test: Actually run cleanup function David Gibson
2022-09-08  6:16 ` [PATCH v2 25/32] test: Create common state directories for temporary files David Gibson
2022-09-08  6:16 ` [PATCH v2 26/32] test: Move context temporary files to state dir David Gibson
2022-09-08  6:16 ` [PATCH v2 27/32] test: Dont regnerate small test file in pasta/tcp David Gibson
2022-09-08  6:16 ` [PATCH v2 28/32] test: Use paths in __STATEDIR__ instead of 'temp' and 'tempdir' directives David Gibson
2022-09-08  6:16 ` [PATCH v2 29/32] test: Move pause temporary file to state directory David Gibson
2022-09-08  6:16 ` [PATCH v2 30/32] test: Store pcap files in $LOGDIR instead of /tmp David Gibson
2022-09-08  6:16 ` [PATCH v2 31/32] test: Move pidfiles and nsholder sockets into state directory David Gibson
2022-09-08  6:16 ` [PATCH v2 32/32] test: Move video processing files to $STATEBASE David Gibson

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20220908061621.2430844-10-david@gibson.dropbear.id.au \
    --to=david@gibson.dropbear.id.au \
    --cc=passt-dev@passt.top \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://passt.top/passt

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for IMAP folder(s).