aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPeter Maydell <peter.maydell@linaro.org>2019-07-05 11:21:29 +0100
committerPeter Maydell <peter.maydell@linaro.org>2019-07-05 11:21:29 +0100
commit0050f9978e47182270c0536906abfd3e9fa91dea (patch)
treef3e56755c749b003f8e12dabf25ec8f478cde2b9
parentc35d17cabc1e2c72ac0adfd47a0dc9ea40875069 (diff)
parent1f4abd81f7dfeb9d622b37368bef22a6481ebc66 (diff)
Merge remote-tracking branch 'remotes/stsquad/tags/pull-testing-next-050719-3' into staging
Various testing fixes: - tests/vm updates and clean-ups - tests/vm serial autobuild on host (-netbsd v3) - ensure MacOS builds do "brew update" - ensure we test --static user builds - fix hyperv compile failure - fix missing var warning for OpenBSD (v2) This brings my testing back to green on all CI services. Please note the BSD installs will throw out some warnings during the setup phase. They shouldn't re-occur once the images are built. NetBSD has been dropped for now given slow install issues. # gpg: Signature made Fri 05 Jul 2019 11:15:21 BST # gpg: using RSA key 6685AE99E75167BCAFC8DF35FBD0DB095A9E2A44 # gpg: Good signature from "Alex Bennée (Master Work Key) <alex.bennee@linaro.org>" [full] # Primary key fingerprint: 6685 AE99 E751 67BC AFC8 DF35 FBD0 DB09 5A9E 2A44 * remotes/stsquad/tags/pull-testing-next-050719-3: migration: move port_attr inside CONFIG_LINUX target/i386: fix feature check in hyperv-stub.c Makefile: Rename the 'vm-test' target as 'vm-help' .travis.yml: force a brew update for MacOS builds .travis.yml: default the --disable-system build to --static tests/vm: ubuntu.i386: apt proxy setup tests/vm: fedora autoinstall, using serial console tests/vm: freebsd autoinstall, using serial console tests/vm: openbsd autoinstall, using serial console tests/vm: serial console support helpers tests/vm: add vm-boot-{ssh,serial}-<guest> targets tests/vm: proper guest shutdown tests/vm: run test builds on snapshot tests/vm: use ssh with pty unconditionally tests/vm: send proxy environment variables over ssh tests/vm: add source repos on ubuntu.i386 tests/vm: pin ubuntu.i386 image tests/vm: avoid image presence check and removal tests/vm: avoid extra compressed image copy Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
-rw-r--r--.travis.yml3
-rw-r--r--Makefile4
-rw-r--r--docs/devel/testing.rst4
-rw-r--r--migration/rdma.c3
-rw-r--r--target/i386/hyperv-stub.c2
-rw-r--r--tests/vm/Makefile.include28
-rwxr-xr-xtests/vm/basevm.py135
-rwxr-xr-xtests/vm/centos6
-rwxr-xr-xtests/vm/fedora189
-rwxr-xr-xtests/vm/freebsd180
-rwxr-xr-xtests/vm/netbsd6
-rwxr-xr-xtests/vm/openbsd159
-rwxr-xr-xtests/vm/ubuntu.i38611
13 files changed, 667 insertions, 63 deletions
diff --git a/.travis.yml b/.travis.yml
index 279658b116..5d3d6ee1d3 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -43,6 +43,7 @@ addons:
- glib
- pixman
- gnu-sed
+ update: true
# The channel name "irc.oftc.net#qemu" is encrypted against qemu/qemu
@@ -80,7 +81,7 @@ script:
matrix:
include:
- env:
- - CONFIG="--disable-system"
+ - CONFIG="--disable-system --static"
# we split the system builds as it takes a while to build them all
diff --git a/Makefile b/Makefile
index 45cc2f4f4d..c63de4e36c 100644
--- a/Makefile
+++ b/Makefile
@@ -13,7 +13,7 @@ SRC_PATH=.
UNCHECKED_GOALS := %clean TAGS cscope ctags dist \
html info pdf txt \
help check-help print-% \
- docker docker-% vm-test vm-build-%
+ docker docker-% vm-help vm-test vm-build-%
print-%:
@echo '$*=$($*)'
@@ -1153,7 +1153,7 @@ endif
@echo 'Test targets:'
@echo ' check - Run all tests (check-help for details)'
@echo ' docker - Help about targets running tests inside Docker containers'
- @echo ' vm-test - Help about targets running tests inside VM'
+ @echo ' vm-help - Help about targets running tests inside VM'
@echo ''
@echo 'Documentation targets:'
@echo ' html info pdf txt'
diff --git a/docs/devel/testing.rst b/docs/devel/testing.rst
index da2d0fc964..68aba3926e 100644
--- a/docs/devel/testing.rst
+++ b/docs/devel/testing.rst
@@ -399,12 +399,12 @@ VM testing
This test suite contains scripts that bootstrap various guest images that have
necessary packages to build QEMU. The basic usage is documented in ``Makefile``
-help which is displayed with ``make vm-test``.
+help which is displayed with ``make vm-help``.
Quickstart
----------
-Run ``make vm-test`` to list available make targets. Invoke a specific make
+Run ``make vm-help`` to list available make targets. Invoke a specific make
command to run build test in an image. For example, ``make vm-build-freebsd``
will build the source tree in the FreeBSD image. The command can be executed
from either the source tree or the build dir; if the former, ``./configure`` is
diff --git a/migration/rdma.c b/migration/rdma.c
index 74cb2aa9f9..3036221ee8 100644
--- a/migration/rdma.c
+++ b/migration/rdma.c
@@ -839,10 +839,9 @@ static void qemu_rdma_dump_gid(const char *who, struct rdma_cm_id *id)
*/
static int qemu_rdma_broken_ipv6_kernel(struct ibv_context *verbs, Error **errp)
{
- struct ibv_port_attr port_attr;
-
/* This bug only exists in linux, to our knowledge. */
#ifdef CONFIG_LINUX
+ struct ibv_port_attr port_attr;
/*
* Verbs are only NULL if management has bound to '[::]'.
diff --git a/target/i386/hyperv-stub.c b/target/i386/hyperv-stub.c
index fe548cbae2..0028527e79 100644
--- a/target/i386/hyperv-stub.c
+++ b/target/i386/hyperv-stub.c
@@ -15,7 +15,7 @@ int kvm_hv_handle_exit(X86CPU *cpu, struct kvm_hyperv_exit *exit)
{
switch (exit->type) {
case KVM_EXIT_HYPERV_SYNIC:
- if (!cpu->hyperv_synic) {
+ if (!hyperv_feat_enabled(cpu, HYPERV_FEAT_SYNIC)) {
return -1;
}
diff --git a/tests/vm/Makefile.include b/tests/vm/Makefile.include
index c59411bee0..3560716092 100644
--- a/tests/vm/Makefile.include
+++ b/tests/vm/Makefile.include
@@ -2,24 +2,30 @@
.PHONY: vm-build-all vm-clean-all
-IMAGES := ubuntu.i386 freebsd netbsd openbsd centos
+IMAGES := ubuntu.i386 freebsd netbsd openbsd centos fedora
IMAGES_DIR := $(HOME)/.cache/qemu-vm/images
IMAGE_FILES := $(patsubst %, $(IMAGES_DIR)/%.img, $(IMAGES))
.PRECIOUS: $(IMAGE_FILES)
-vm-test:
- @echo "vm-test: Test QEMU in preconfigured virtual machines"
+# 'vm-help' target was historically named 'vm-test'
+vm-help vm-test:
+ @echo "vm-help: Test QEMU in preconfigured virtual machines"
@echo
@echo " vm-build-ubuntu.i386 - Build QEMU in ubuntu i386 VM"
@echo " vm-build-freebsd - Build QEMU in FreeBSD VM"
@echo " vm-build-netbsd - Build QEMU in NetBSD VM"
@echo " vm-build-openbsd - Build QEMU in OpenBSD VM"
@echo " vm-build-centos - Build QEMU in CentOS VM, with Docker"
+ @echo " vm-build-fedora - Build QEMU in Fedora VM"
@echo ""
@echo " vm-build-all - Build QEMU in all VMs"
@echo " vm-clean-all - Clean up VM images"
@echo
+ @echo "For trouble-shooting:"
+ @echo " vm-boot-serial-<guest> - Boot guest, serial console on stdio"
+ @echo " vm-boot-ssh-<guest> - Boot guest and login via ssh"
+ @echo
@echo "Special variables:"
@echo " BUILD_TARGET=foo - Override the build target"
@echo " TARGET_LIST=a,b,c - Override target list in builds"
@@ -57,8 +63,24 @@ vm-build-%: $(IMAGES_DIR)/%.img
$(if $(V),--verbose) \
--image "$<" \
$(if $(BUILD_TARGET),--build-target $(BUILD_TARGET)) \
+ --snapshot \
--build-qemu $(SRC_PATH) -- \
$(if $(TARGET_LIST),--target-list=$(TARGET_LIST)) \
$(if $(EXTRA_CONFIGURE_OPTS),$(EXTRA_CONFIGURE_OPTS)), \
" VM-BUILD $*")
+vm-boot-serial-%: $(IMAGES_DIR)/%.img
+ qemu-system-x86_64 -enable-kvm -m 4G -smp 2 -nographic \
+ -drive if=none,id=vblk,cache=writeback,file="$<" \
+ -netdev user,id=vnet \
+ -device virtio-blk-pci,drive=vblk \
+ -device virtio-net-pci,netdev=vnet \
+ || true
+
+vm-boot-ssh-%: $(IMAGES_DIR)/%.img
+ $(call quiet-command, \
+ $(SRC_PATH)/tests/vm/$* \
+ --image "$<" \
+ --interactive \
+ false, \
+ " VM-BOOT-SSH $*") || true
diff --git a/tests/vm/basevm.py b/tests/vm/basevm.py
index 64067c1075..b5d1479bee 100755
--- a/tests/vm/basevm.py
+++ b/tests/vm/basevm.py
@@ -2,10 +2,11 @@
#
# VM testing base class
#
-# Copyright 2017 Red Hat Inc.
+# Copyright 2017-2019 Red Hat Inc.
#
# Authors:
# Fam Zheng <famz@redhat.com>
+# Gerd Hoffmann <kraxel@redhat.com>
#
# This code is licensed under the GPL version 2 or later. See
# the COPYING file in the top-level directory.
@@ -13,7 +14,9 @@
from __future__ import print_function
import os
+import re
import sys
+import socket
import logging
import time
import datetime
@@ -39,12 +42,21 @@ class BaseVM(object):
GUEST_PASS = "qemupass"
ROOT_PASS = "qemupass"
+ envvars = [
+ "https_proxy",
+ "http_proxy",
+ "ftp_proxy",
+ "no_proxy",
+ ]
+
# The script to run in the guest that builds QEMU
BUILD_SCRIPT = ""
# The guest name, to be overridden by subclasses
name = "#base"
# The guest architecture, to be overridden by subclasses
arch = "#arch"
+ # command to halt the guest, can be overridden by subclasses
+ poweroff = "poweroff"
def __init__(self, debug=False, vcpus=None):
self._guest = None
self._tmpdir = os.path.realpath(tempfile.mkdtemp(prefix="vm-test-",
@@ -71,8 +83,7 @@ class BaseVM(object):
"-cpu", "max",
"-netdev", "user,id=vnet,hostfwd=:127.0.0.1:0-:22",
"-device", "virtio-net-pci,netdev=vnet",
- "-vnc", "127.0.0.1:0,to=20",
- "-serial", "file:%s" % os.path.join(self._tmpdir, "serial.out")]
+ "-vnc", "127.0.0.1:0,to=20"]
if vcpus and vcpus > 1:
self._args += ["-smp", "%d" % vcpus]
if kvm_available(self.arch):
@@ -101,14 +112,14 @@ class BaseVM(object):
os.rename(fname + ".download", fname)
return fname
- def _ssh_do(self, user, cmd, check, interactive=False):
- ssh_cmd = ["ssh", "-q",
+ def _ssh_do(self, user, cmd, check):
+ ssh_cmd = ["ssh", "-q", "-t",
"-o", "StrictHostKeyChecking=no",
"-o", "UserKnownHostsFile=" + os.devnull,
"-o", "ConnectTimeout=1",
"-p", self.ssh_port, "-i", self._ssh_key_file]
- if interactive:
- ssh_cmd += ['-t']
+ for var in self.envvars:
+ ssh_cmd += ['-o', "SendEnv=%s" % var ]
assert not isinstance(cmd, str)
ssh_cmd += ["%s@127.0.0.1" % user] + list(cmd)
logging.debug("ssh_cmd: %s", " ".join(ssh_cmd))
@@ -120,9 +131,6 @@ class BaseVM(object):
def ssh(self, *cmd):
return self._ssh_do(self.GUEST_USER, cmd, False)
- def ssh_interactive(self, *cmd):
- return self._ssh_do(self.GUEST_USER, cmd, False, True)
-
def ssh_root(self, *cmd):
return self._ssh_do("root", cmd, False)
@@ -157,6 +165,8 @@ class BaseVM(object):
logging.debug("QEMU args: %s", " ".join(args))
qemu_bin = os.environ.get("QEMU", "qemu-system-" + self.arch)
guest = QEMUMachine(binary=qemu_bin, args=args)
+ guest.set_machine('pc')
+ guest.set_console()
try:
guest.launch()
except:
@@ -179,6 +189,89 @@ class BaseVM(object):
raise Exception("Cannot find ssh port from 'info usernet':\n%s" % \
usernet_info)
+ def console_init(self, timeout = 120):
+ vm = self._guest
+ vm.console_socket.settimeout(timeout)
+
+ def console_log(self, text):
+ for line in re.split("[\r\n]", text):
+ # filter out terminal escape sequences
+ line = re.sub("\x1b\[[0-9;?]*[a-zA-Z]", "", line)
+ line = re.sub("\x1b\([0-9;?]*[a-zA-Z]", "", line)
+ # replace unprintable chars
+ line = re.sub("\x1b", "<esc>", line)
+ line = re.sub("[\x00-\x1f]", ".", line)
+ line = re.sub("[\x80-\xff]", ".", line)
+ if line == "":
+ continue
+ # log console line
+ sys.stderr.write("con recv: %s\n" % line)
+
+ def console_wait(self, expect, expectalt = None):
+ vm = self._guest
+ output = ""
+ while True:
+ try:
+ chars = vm.console_socket.recv(1)
+ except socket.timeout:
+ sys.stderr.write("console: *** read timeout ***\n")
+ sys.stderr.write("console: waiting for: '%s'\n" % expect)
+ if not expectalt is None:
+ sys.stderr.write("console: waiting for: '%s' (alt)\n" % expectalt)
+ sys.stderr.write("console: line buffer:\n")
+ sys.stderr.write("\n")
+ self.console_log(output.rstrip())
+ sys.stderr.write("\n")
+ raise
+ output += chars.decode("latin1")
+ if expect in output:
+ break
+ if not expectalt is None and expectalt in output:
+ break
+ if "\r" in output or "\n" in output:
+ lines = re.split("[\r\n]", output)
+ output = lines.pop()
+ if self.debug:
+ self.console_log("\n".join(lines))
+ if self.debug:
+ self.console_log(output)
+ if not expectalt is None and expectalt in output:
+ return False
+ return True
+
+ def console_send(self, command):
+ vm = self._guest
+ if self.debug:
+ logline = re.sub("\n", "<enter>", command)
+ logline = re.sub("[\x00-\x1f]", ".", logline)
+ sys.stderr.write("con send: %s\n" % logline)
+ for char in list(command):
+ vm.console_socket.send(char.encode("utf-8"))
+ time.sleep(0.01)
+
+ def console_wait_send(self, wait, command):
+ self.console_wait(wait)
+ self.console_send(command)
+
+ def console_ssh_init(self, prompt, user, pw):
+ sshkey_cmd = "echo '%s' > .ssh/authorized_keys\n" % SSH_PUB_KEY.rstrip()
+ self.console_wait_send("login:", "%s\n" % user)
+ self.console_wait_send("Password:", "%s\n" % pw)
+ self.console_wait_send(prompt, "mkdir .ssh\n")
+ self.console_wait_send(prompt, sshkey_cmd)
+ self.console_wait_send(prompt, "chmod 755 .ssh\n")
+ self.console_wait_send(prompt, "chmod 644 .ssh/authorized_keys\n")
+
+ def console_sshd_config(self, prompt):
+ self.console_wait(prompt)
+ self.console_send("echo 'PermitRootLogin yes' >> /etc/ssh/sshd_config\n")
+ for var in self.envvars:
+ self.console_wait(prompt)
+ self.console_send("echo 'AcceptEnv %s' >> /etc/ssh/sshd_config\n" % var)
+
+ def print_step(self, text):
+ sys.stderr.write("### %s ...\n" % text)
+
def wait_ssh(self, seconds=300):
starttime = datetime.datetime.now()
endtime = starttime + datetime.timedelta(seconds=seconds)
@@ -199,6 +292,10 @@ class BaseVM(object):
def wait(self):
self._guest.wait()
+ def graceful_shutdown(self):
+ self.ssh_root(self.poweroff)
+ self._guest.wait()
+
def qmp(self, *args, **kwargs):
return self._guest.qmp(*args, **kwargs)
@@ -275,11 +372,13 @@ def main(vmcls):
traceback.print_exc()
return 2
- if args.interactive:
- if vm.ssh_interactive(*cmd) == 0:
- return 0
- vm.ssh_interactive()
- return 3
- else:
- if vm.ssh(*cmd) != 0:
- return 3
+ exitcode = 0
+ if vm.ssh(*cmd) != 0:
+ exitcode = 3
+ if exitcode != 0 and args.interactive:
+ vm.ssh()
+
+ if not args.snapshot:
+ vm.graceful_shutdown()
+
+ return exitcode
diff --git a/tests/vm/centos b/tests/vm/centos
index 7417b50af4..53976f1c4c 100755
--- a/tests/vm/centos
+++ b/tests/vm/centos
@@ -66,8 +66,8 @@ class CentosVM(basevm.BaseVM):
cimg = self._download_with_cache("https://cloud.centos.org/centos/7/images/CentOS-7-x86_64-GenericCloud-1802.qcow2.xz")
img_tmp = img + ".tmp"
sys.stderr.write("Extracting the image...\n")
- subprocess.check_call(["cp", "-f", cimg, img_tmp + ".xz"])
- subprocess.check_call(["xz", "-dvf", img_tmp + ".xz"])
+ subprocess.check_call(["ln", "-f", cimg, img_tmp + ".xz"])
+ subprocess.check_call(["xz", "--keep", "-dvf", img_tmp + ".xz"])
subprocess.check_call(["qemu-img", "resize", img_tmp, "50G"])
self.boot(img_tmp, extra_args = ["-cdrom", self._gen_cloud_init_iso()])
self.wait_ssh()
@@ -77,8 +77,6 @@ class CentosVM(basevm.BaseVM):
self.ssh_root_check("systemctl enable docker")
self.ssh_root("poweroff")
self.wait()
- if os.path.exists(img):
- os.remove(img)
os.rename(img_tmp, img)
return 0
diff --git a/tests/vm/fedora b/tests/vm/fedora
new file mode 100755
index 0000000000..e8fa5bf0d2
--- /dev/null
+++ b/tests/vm/fedora
@@ -0,0 +1,189 @@
+#!/usr/bin/env python
+#
+# Fedora VM image
+#
+# Copyright 2019 Red Hat Inc.
+#
+# Authors:
+# Gerd Hoffmann <kraxel@redhat.com>
+#
+# This code is licensed under the GPL version 2 or later. See
+# the COPYING file in the top-level directory.
+#
+
+import os
+import re
+import sys
+import time
+import socket
+import subprocess
+import basevm
+
+class FedoraVM(basevm.BaseVM):
+ name = "fedora"
+ arch = "x86_64"
+
+ base = "http://dl.fedoraproject.org/pub/fedora/linux/releases/30/"
+ link = base + "Server/x86_64/iso/Fedora-Server-netinst-x86_64-30-1.2.iso"
+ repo = base + "Server/x86_64/os/"
+ full = base + "Everything/x86_64/os/"
+ csum = "5e4eac4566d8c572bfb3bcf54b7d6c82006ec3c6c882a2c9235c6d3494d7b100"
+ size = "20G"
+ pkgs = [
+ # tools
+ 'git-core',
+ 'flex', 'bison',
+ 'gcc', 'binutils', 'make',
+
+ # perl
+ 'perl-Test-Harness',
+
+ # libs: usb
+ '"pkgconfig(libusb-1.0)"',
+ '"pkgconfig(libusbredirparser-0.5)"',
+
+ # libs: crypto
+ '"pkgconfig(gnutls)"',
+
+ # libs: ui
+ '"pkgconfig(sdl2)"',
+ '"pkgconfig(gtk+-3.0)"',
+ '"pkgconfig(ncursesw)"',
+
+ # libs: audio
+ '"pkgconfig(libpulse)"',
+ '"pkgconfig(alsa)"',
+ ]
+
+ BUILD_SCRIPT = """
+ set -e;
+ rm -rf /home/qemu/qemu-test.*
+ cd $(mktemp -d /home/qemu/qemu-test.XXXXXX);
+ mkdir src build; cd src;
+ tar -xf /dev/vdb;
+ cd ../build
+ ../src/configure --python=python3 {configure_opts};
+ gmake --output-sync -j{jobs} {target} {verbose};
+ """
+
+ def build_image(self, img):
+ self.print_step("Downloading install iso")
+ cimg = self._download_with_cache(self.link, sha256sum=self.csum)
+ img_tmp = img + ".tmp"
+ iso = img + ".install.iso"
+
+ self.print_step("Preparing iso and disk image")
+ subprocess.check_call(["cp", "-f", cimg, iso])
+ subprocess.check_call(["qemu-img", "create", "-f", "qcow2",
+ img_tmp, self.size])
+
+ self.print_step("Booting installer")
+ self.boot(img_tmp, extra_args = [
+ "-bios", "pc-bios/bios-256k.bin",
+ "-machine", "graphics=off",
+ "-cdrom", iso
+ ])
+ self.console_init(300)
+ self.console_wait("installation process.")
+ time.sleep(0.3)
+ self.console_send("\t")
+ time.sleep(0.3)
+ self.console_send(" console=ttyS0")
+ proxy = os.environ.get("http_proxy")
+ if not proxy is None:
+ self.console_send(" proxy=%s" % proxy)
+ self.console_send(" inst.proxy=%s" % proxy)
+ self.console_send(" inst.repo=%s" % self.repo)
+ self.console_send("\n")
+
+ self.console_wait_send("2) Use text mode", "2\n")
+
+ self.console_wait_send("5) [!] Installation Dest", "5\n")
+ self.console_wait_send("1) [x]", "c\n")
+ self.console_wait_send("2) [ ] Use All Space", "2\n")
+ self.console_wait_send("2) [x] Use All Space", "c\n")
+ self.console_wait_send("1) [ ] Standard Part", "1\n")
+ self.console_wait_send("1) [x] Standard Part", "c\n")
+
+ self.console_wait_send("7) [!] Root password", "7\n")
+ self.console_wait("Password:")
+ self.console_send("%s\n" % self.ROOT_PASS)
+ self.console_wait("Password (confirm):")
+ self.console_send("%s\n" % self.ROOT_PASS)
+
+ self.console_wait_send("8) [ ] User creation", "8\n")
+ self.console_wait_send("1) [ ] Create user", "1\n")
+ self.console_wait_send("3) User name", "3\n")
+ self.console_wait_send("ENTER:", "%s\n" % self.GUEST_USER)
+ self.console_wait_send("4) [ ] Use password", "4\n")
+ self.console_wait_send("5) Password", "5\n")
+ self.console_wait("Password:")
+ self.console_send("%s\n" % self.GUEST_PASS)
+ self.console_wait("Password (confirm):")
+ self.console_send("%s\n" % self.GUEST_PASS)
+ self.console_wait_send("7) Groups", "c\n")
+
+ while True:
+ good = self.console_wait("3) [x] Installation",
+ "3) [!] Installation")
+ self.console_send("r\n")
+ if good:
+ break
+ time.sleep(10)
+
+ while True:
+ good = self.console_wait("4) [x] Software",
+ "4) [!] Software")
+ self.console_send("r\n")
+ if good:
+ break
+ time.sleep(10)
+ self.console_send("r\n" % self.GUEST_PASS)
+
+ self.console_wait_send("'b' to begin install", "b\n")
+
+ self.print_step("Installation started now, this will take a while")
+
+ self.console_wait_send("Installation complete", "\n")
+ self.print_step("Installation finished, rebooting")
+
+ # setup qemu user
+ prompt = " ~]$"
+ self.console_ssh_init(prompt, self.GUEST_USER, self.GUEST_PASS)
+ self.console_wait_send(prompt, "exit\n")
+
+ # setup root user
+ prompt = " ~]#"
+ self.console_ssh_init(prompt, "root", self.ROOT_PASS)
+ self.console_sshd_config(prompt)
+
+ # setup virtio-blk #1 (tarfile)
+ self.console_wait(prompt)
+ self.console_send("echo 'KERNEL==\"vdb\" MODE=\"666\"' >> %s\n" %
+ "/etc/udev/rules.d/99-qemu.rules")
+
+ self.print_step("Configuration finished, rebooting")
+ self.console_wait_send(prompt, "reboot\n")
+ self.console_wait("login:")
+ self.wait_ssh()
+
+ self.print_step("Installing packages")
+ self.ssh_root_check("rm -vf /etc/yum.repos.d/fedora*.repo\n")
+ self.ssh_root_check("echo '[fedora]' >> /etc/yum.repos.d/qemu.repo\n")
+ self.ssh_root_check("echo 'baseurl=%s' >> /etc/yum.repos.d/qemu.repo\n" % self.full)
+ self.ssh_root_check("echo 'gpgcheck=0' >> /etc/yum.repos.d/qemu.repo\n")
+ self.ssh_root_check("dnf install -y %s\n" % " ".join(self.pkgs))
+
+ # shutdown
+ self.ssh_root(self.poweroff)
+ self.console_wait("sleep state S5")
+ self.wait()
+
+ if os.path.exists(img):
+ os.remove(img)
+ os.rename(img_tmp, img)
+ os.remove(iso)
+ self.print_step("All done")
+
+if __name__ == "__main__":
+ sys.exit(basevm.main(FedoraVM))
diff --git a/tests/vm/freebsd b/tests/vm/freebsd
index b0066017a6..2a19461a90 100755
--- a/tests/vm/freebsd
+++ b/tests/vm/freebsd
@@ -2,43 +2,203 @@
#
# FreeBSD VM image
#
-# Copyright 2017 Red Hat Inc.
+# Copyright 2017-2019 Red Hat Inc.
#
# Authors:
# Fam Zheng <famz@redhat.com>
+# Gerd Hoffmann <kraxel@redhat.com>
#
# This code is licensed under the GPL version 2 or later. See
# the COPYING file in the top-level directory.
#
import os
+import re
import sys
+import time
+import socket
import subprocess
import basevm
class FreeBSDVM(basevm.BaseVM):
name = "freebsd"
arch = "x86_64"
+
+ link = "https://download.freebsd.org/ftp/releases/ISO-IMAGES/12.0/FreeBSD-12.0-RELEASE-amd64-disc1.iso.xz"
+ csum = "1d40015bea89d05b8bd13e2ed80c40b522a9ec1abd8e7c8b80954fb485fb99db"
+ size = "20G"
+ pkgs = [
+ # build tools
+ "git",
+ "pkgconf",
+ "bzip2",
+
+ # gnu tools
+ "bash",
+ "gmake",
+ "gsed",
+ "flex", "bison",
+
+ # libs: crypto
+ "gnutls",
+
+ # libs: images
+ "jpeg-turbo",
+ "png",
+
+ # libs: ui
+ "sdl2",
+ "gtk3",
+ "libxkbcommon",
+
+ # libs: opengl
+ "libepoxy",
+ "mesa-libs",
+ ]
+
BUILD_SCRIPT = """
set -e;
- rm -rf /var/tmp/qemu-test.*
- cd $(mktemp -d /var/tmp/qemu-test.XXXXXX);
+ rm -rf /home/qemu/qemu-test.*
+ cd $(mktemp -d /home/qemu/qemu-test.XXXXXX);
+ mkdir src build; cd src;
tar -xf /dev/vtbd1;
- ./configure {configure_opts};
+ cd ../build
+ ../src/configure --python=python3.6 {configure_opts};
gmake --output-sync -j{jobs} {target} {verbose};
"""
+ def console_boot_serial(self):
+ self.console_wait_send("Autoboot", "3")
+ self.console_wait_send("OK", "set console=comconsole\n")
+ self.console_wait_send("OK", "boot\n")
+
def build_image(self, img):
- cimg = self._download_with_cache("http://download.patchew.org/freebsd-11.1-amd64.img.xz",
- sha256sum='adcb771549b37bc63826c501f05121a206ed3d9f55f49145908f7e1432d65891')
- img_tmp_xz = img + ".tmp.xz"
+ self.print_step("Downloading install iso")
+ cimg = self._download_with_cache(self.link, sha256sum=self.csum)
img_tmp = img + ".tmp"
- sys.stderr.write("Extracting the image...\n")
- subprocess.check_call(["cp", "-f", cimg, img_tmp_xz])
- subprocess.check_call(["xz", "-dvf", img_tmp_xz])
+ iso = img + ".install.iso"
+ iso_xz = iso + ".xz"
+
+ self.print_step("Preparing iso and disk image")
+ subprocess.check_call(["cp", "-f", cimg, iso_xz])
+ subprocess.check_call(["xz", "-dvf", iso_xz])
+ subprocess.check_call(["qemu-img", "create", "-f", "qcow2",
+ img_tmp, self.size])
+
+ self.print_step("Booting installer")
+ self.boot(img_tmp, extra_args = [
+ "-bios", "pc-bios/bios-256k.bin",
+ "-machine", "graphics=off",
+ "-cdrom", iso
+ ])
+ self.console_init()
+ self.console_boot_serial()
+ self.console_wait_send("Console type", "xterm\n")
+
+ # pre-install configuration
+ self.console_wait_send("Welcome", "\n")
+ self.console_wait_send("Keymap Selection", "\n")
+ self.console_wait_send("Set Hostname", "freebsd\n")
+ self.console_wait_send("Distribution Select", "\n")
+ self.console_wait_send("Partitioning", "\n")
+ self.console_wait_send("Partition", "\n")
+ self.console_wait_send("Scheme", "\n")
+ self.console_wait_send("Editor", "f")
+ self.console_wait_send("Confirmation", "c")
+
+ self.print_step("Installation started now, this will take a while")
+
+ # post-install configuration
+ self.console_wait("New Password:")
+ self.console_send("%s\n" % self.ROOT_PASS)
+ self.console_wait("Retype New Password:")
+ self.console_send("%s\n" % self.ROOT_PASS)
+
+ self.console_wait_send("Network Configuration", "\n")
+ self.console_wait_send("IPv4", "y")
+ self.console_wait_send("DHCP", "y")
+ self.console_wait_send("IPv6", "n")
+ self.console_wait_send("Resolver", "\n")
+
+ self.console_wait_send("Time Zone Selector", "a\n")
+ self.console_wait_send("Confirmation", "y")
+ self.console_wait_send("Time & Date", "\n")
+ self.console_wait_send("Time & Date", "\n")
+
+ self.console_wait_send("System Configuration", "\n")
+ self.console_wait_send("System Hardening", "\n")
+
+ # qemu user
+ self.console_wait_send("Add User Accounts", "y")
+ self.console_wait("Username")
+ self.console_send("%s\n" % self.GUEST_USER)
+ self.console_wait("Full name")
+ self.console_send("%s\n" % self.GUEST_USER)
+ self.console_wait_send("Uid", "\n")
+ self.console_wait_send("Login group", "\n")
+ self.console_wait_send("Login group", "\n")
+ self.console_wait_send("Login class", "\n")
+ self.console_wait_send("Shell", "\n")
+ self.console_wait_send("Home directory", "\n")
+ self.console_wait_send("Home directory perm", "\n")
+ self.console_wait_send("Use password", "\n")
+ self.console_wait_send("Use an empty password", "\n")
+ self.console_wait_send("Use a random password", "\n")
+ self.console_wait("Enter password:")
+ self.console_send("%s\n" % self.GUEST_PASS)
+ self.console_wait("Enter password again:")
+ self.console_send("%s\n" % self.GUEST_PASS)
+ self.console_wait_send("Lock out", "\n")
+ self.console_wait_send("OK", "yes\n")
+ self.console_wait_send("Add another user", "no\n")
+
+ self.console_wait_send("Final Configuration", "\n")
+ self.console_wait_send("Manual Configuration", "\n")
+ self.console_wait_send("Complete", "\n")
+
+ self.print_step("Installation finished, rebooting")
+ self.console_boot_serial()
+
+ # setup qemu user
+ prompt = "$"
+ self.console_ssh_init(prompt, self.GUEST_USER, self.GUEST_PASS)
+ self.console_wait_send(prompt, "exit\n")
+
+ # setup root user
+ prompt = "root@freebsd:~ #"
+ self.console_ssh_init(prompt, "root", self.ROOT_PASS)
+ self.console_sshd_config(prompt)
+
+ # setup serial console
+ self.console_wait(prompt)
+ self.console_send("echo 'console=comconsole' >> /boot/loader.conf\n")
+
+ # setup boot delay
+ self.console_wait(prompt)
+ self.console_send("echo 'autoboot_delay=1' >> /boot/loader.conf\n")
+
+ # setup virtio-blk #1 (tarfile)
+ self.console_wait(prompt)
+ self.console_send("echo 'chmod 666 /dev/vtbd1' >> /etc/rc.local\n")
+
+ self.print_step("Configuration finished, rebooting")
+ self.console_wait_send(prompt, "reboot\n")
+ self.console_wait("login:")
+ self.wait_ssh()
+
+ self.print_step("Installing packages")
+ self.ssh_root_check("pkg install -y %s\n" % " ".join(self.pkgs))
+
+ # shutdown
+ self.ssh_root(self.poweroff)
+ self.console_wait("Uptime:")
+ self.wait()
+
if os.path.exists(img):
os.remove(img)
os.rename(img_tmp, img)
+ os.remove(iso)
+ self.print_step("All done")
if __name__ == "__main__":
sys.exit(basevm.main(FreeBSDVM))
diff --git a/tests/vm/netbsd b/tests/vm/netbsd
index 4c6624ea5e..ee9eaeab50 100755
--- a/tests/vm/netbsd
+++ b/tests/vm/netbsd
@@ -34,10 +34,8 @@ class NetBSDVM(basevm.BaseVM):
img_tmp_xz = img + ".tmp.xz"
img_tmp = img + ".tmp"
sys.stderr.write("Extracting the image...\n")
- subprocess.check_call(["cp", "-f", cimg, img_tmp_xz])
- subprocess.check_call(["xz", "-dvf", img_tmp_xz])
- if os.path.exists(img):
- os.remove(img)
+ subprocess.check_call(["ln", "-f", cimg, img_tmp_xz])
+ subprocess.check_call(["xz", "--keep", "-dvf", img_tmp_xz])
os.rename(img_tmp, img)
if __name__ == "__main__":
diff --git a/tests/vm/openbsd b/tests/vm/openbsd
index 2105c01a26..b92c39f89a 100755
--- a/tests/vm/openbsd
+++ b/tests/vm/openbsd
@@ -2,10 +2,11 @@
#
# OpenBSD VM image
#
-# Copyright 2017 Red Hat Inc.
+# Copyright 2017-2019 Red Hat Inc.
#
# Authors:
# Fam Zheng <famz@redhat.com>
+# Gerd Hoffmann <kraxel@redhat.com>
#
# This code is licensed under the GPL version 2 or later. See
# the COPYING file in the top-level directory.
@@ -13,34 +14,166 @@
import os
import sys
+import socket
import subprocess
import basevm
class OpenBSDVM(basevm.BaseVM):
name = "openbsd"
arch = "x86_64"
+
+ link = "https://cdn.openbsd.org/pub/OpenBSD/6.5/amd64/install65.iso"
+ csum = "38d1f8cadd502f1c27bf05c5abde6cc505dd28f3f34f8a941048ff9a54f9f608"
+ size = "20G"
+ pkgs = [
+ # tools
+ "git",
+ "pkgconf",
+ "bzip2", "xz",
+
+ # gnu tools
+ "bash",
+ "gmake",
+ "gsed",
+ "bison",
+
+ # libs: usb
+ "libusb1",
+
+ # libs: crypto
+ "gnutls",
+
+ # libs: images
+ "jpeg",
+ "png",
+
+ # libs: ui
+ "sdl2",
+ "gtk+3",
+ "libxkbcommon",
+ ]
+
BUILD_SCRIPT = """
set -e;
- rm -rf /var/tmp/qemu-test.*
- cd $(mktemp -d /var/tmp/qemu-test.XXXXXX);
+ rm -rf /home/qemu/qemu-test.*
+ cd $(mktemp -d /home/qemu/qemu-test.XXXXXX);
+ mkdir src build; cd src;
tar -xf /dev/rsd1c;
- ./configure --cc=x86_64-unknown-openbsd6.1-gcc-4.9.4 --python=python2.7 {configure_opts};
- gmake --output-sync -j{jobs} {verbose};
- # XXX: "gmake check" seems to always hang or fail
- #gmake --output-sync -j{jobs} check {verbose};
+ cd ../build
+ ../src/configure --cc=cc --python=python3 {configure_opts};
+ gmake --output-sync -j{jobs} {target} {verbose};
"""
+ poweroff = "halt -p"
def build_image(self, img):
- cimg = self._download_with_cache("http://download.patchew.org/openbsd-6.1-amd64.img.xz",
- sha256sum='8c6cedc483e602cfee5e04f0406c64eb99138495e8ca580bc0293bcf0640c1bf')
- img_tmp_xz = img + ".tmp.xz"
+ self.print_step("Downloading install iso")
+ cimg = self._download_with_cache(self.link, sha256sum=self.csum)
img_tmp = img + ".tmp"
- sys.stderr.write("Extracting the image...\n")
- subprocess.check_call(["cp", "-f", cimg, img_tmp_xz])
- subprocess.check_call(["xz", "-dvf", img_tmp_xz])
+ iso = img + ".install.iso"
+
+ self.print_step("Preparing iso and disk image")
+ subprocess.check_call(["cp", "-f", cimg, iso])
+ subprocess.check_call(["qemu-img", "create", "-f", "qcow2",
+ img_tmp, self.size])
+
+ self.print_step("Booting installer")
+ self.boot(img_tmp, extra_args = [
+ "-bios", "pc-bios/bios-256k.bin",
+ "-machine", "graphics=off",
+ "-cdrom", iso
+ ])
+ self.console_init()
+ self.console_wait_send("boot>", "set tty com0\n")
+ self.console_wait_send("boot>", "\n")
+
+ # pre-install configuration
+ self.console_wait_send("(I)nstall", "i\n")
+ self.console_wait_send("Terminal type", "xterm\n")
+ self.console_wait_send("System hostname", "openbsd\n")
+ self.console_wait_send("Which network interface", "vio0\n")
+ self.console_wait_send("IPv4 address", "dhcp\n")
+ self.console_wait_send("IPv6 address", "none\n")
+ self.console_wait_send("Which network interface", "done\n")
+ self.console_wait_send("DNS domain name", "localnet\n")
+ self.console_wait("Password for root account")
+ self.console_send("%s\n" % self.ROOT_PASS)
+ self.console_wait("Password for root account")
+ self.console_send("%s\n" % self.ROOT_PASS)
+ self.console_wait_send("Start sshd(8)", "yes\n")
+ self.console_wait_send("X Window System", "\n")
+ self.console_wait_send("xenodm", "\n")
+ self.console_wait_send("console to com0", "\n")
+ self.console_wait_send("Which speed", "\n")
+
+ self.console_wait("Setup a user")
+ self.console_send("%s\n" % self.GUEST_USER)
+ self.console_wait("Full name")
+ self.console_send("%s\n" % self.GUEST_USER)
+ self.console_wait("Password")
+ self.console_send("%s\n" % self.GUEST_PASS)
+ self.console_wait("Password")
+ self.console_send("%s\n" % self.GUEST_PASS)
+
+ self.console_wait_send("Allow root ssh login", "yes\n")
+ self.console_wait_send("timezone", "UTC\n")
+ self.console_wait_send("root disk", "\n")
+ self.console_wait_send("(W)hole disk", "\n")
+ self.console_wait_send("(A)uto layout", "\n")
+ self.console_wait_send("Location of sets", "cd0\n")
+ self.console_wait_send("Pathname to the sets", "\n")
+ self.console_wait_send("Set name(s)", "\n")
+ self.console_wait_send("without verification", "yes\n")
+
+ self.print_step("Installation started now, this will take a while")
+ self.console_wait_send("Location of sets", "done\n")
+
+ self.console_wait("successfully completed")
+ self.print_step("Installation finished, rebooting")
+ self.console_wait_send("(R)eboot", "reboot\n")
+
+ # setup qemu user
+ prompt = "$"
+ self.console_ssh_init(prompt, self.GUEST_USER, self.GUEST_PASS)
+ self.console_wait_send(prompt, "exit\n")
+
+ # setup root user
+ prompt = "openbsd#"
+ self.console_ssh_init(prompt, "root", self.ROOT_PASS)
+ self.console_sshd_config(prompt)
+
+ # setup virtio-blk #1 (tarfile)
+ self.console_wait(prompt)
+ self.console_send("echo 'chmod 666 /dev/rsd1c' >> /etc/rc.local\n")
+
+ # enable w+x for /home
+ self.console_wait(prompt)
+ self.console_send("sed -i -e '/home/s/rw,/rw,wxallowed,/' /etc/fstab\n")
+
+ # tweak datasize limit
+ self.console_wait(prompt)
+ self.console_send("sed -i -e 's/\\(datasize[^=]*\\)=[^:]*/\\1=infinity/' /etc/login.conf\n")
+
+ # use http (be proxy cache friendly)
+ self.console_wait(prompt)
+ self.console_send("sed -i -e 's/https/http/' /etc/installurl\n")
+
+ self.print_step("Configuration finished, rebooting")
+ self.console_wait_send(prompt, "reboot\n")
+ self.console_wait("login:")
+ self.wait_ssh()
+
+ self.print_step("Installing packages")
+ self.ssh_root_check("pkg_add %s\n" % " ".join(self.pkgs))
+
+ # shutdown
+ self.ssh_root(self.poweroff)
+ self.wait()
+
if os.path.exists(img):
os.remove(img)
os.rename(img_tmp, img)
+ os.remove(iso)
+ self.print_step("All done")
if __name__ == "__main__":
sys.exit(basevm.main(OpenBSDVM))
diff --git a/tests/vm/ubuntu.i386 b/tests/vm/ubuntu.i386
index a22d137e76..38f740eabf 100755
--- a/tests/vm/ubuntu.i386
+++ b/tests/vm/ubuntu.i386
@@ -51,6 +51,10 @@ class UbuntuX86VM(basevm.BaseVM):
" ssh-authorized-keys:\n",
" - %s\n" % basevm.SSH_PUB_KEY,
"locale: en_US.UTF-8\n"])
+ proxy = os.environ.get("http_proxy")
+ if not proxy is None:
+ udata.writelines(["apt:\n",
+ " proxy: %s" % proxy])
udata.close()
subprocess.check_call(["genisoimage", "-output", "cloud-init.iso",
"-volid", "cidata", "-joliet", "-rock",
@@ -61,7 +65,9 @@ class UbuntuX86VM(basevm.BaseVM):
return os.path.join(cidir, "cloud-init.iso")
def build_image(self, img):
- cimg = self._download_with_cache("https://cloud-images.ubuntu.com/releases/16.04/release/ubuntu-16.04-server-cloudimg-i386-disk1.img")
+ cimg = self._download_with_cache(
+ "https://cloud-images.ubuntu.com/releases/16.04/release-20190605/ubuntu-16.04-server-cloudimg-i386-disk1.img",
+ sha256sum="e30091144c73483822b7c27193e9d47346dd1064229da577c3fedcf943f7cfcc")
img_tmp = img + ".tmp"
subprocess.check_call(["cp", "-f", cimg, img_tmp])
subprocess.check_call(["qemu-img", "resize", img_tmp, "50G"])
@@ -75,13 +81,12 @@ class UbuntuX86VM(basevm.BaseVM):
time.sleep(5)
self.wait_ssh()
# The previous update sometimes doesn't survive a reboot, so do it again
+ self.ssh_root_check("sed -ie s/^#\ deb-src/deb-src/g /etc/apt/sources.list")
self.ssh_root_check("apt-get update")
self.ssh_root_check("apt-get build-dep -y qemu")
self.ssh_root_check("apt-get install -y libfdt-dev flex bison")
self.ssh_root("poweroff")
self.wait()
- if os.path.exists(img):
- os.remove(img)
os.rename(img_tmp, img)
return 0