From: Lucas Meneghel Rodrigues <lmr@redhat.com>
To: autotest@test.kernel.org
Cc: kvm@vger.kernel.org
Subject: [PATCH 11/11] Virt: add support for XEN via libvirt installs and auto url
Date: Tue, 11 Oct 2011 18:07:17 -0300 [thread overview]
Message-ID: <1318367237-26081-12-git-send-email-lmr@redhat.com> (raw)
In-Reply-To: <1318367237-26081-1-git-send-email-lmr@redhat.com>
From: Cleber Rosa <crosa@redhat.com>
This patch adds support to unattended installs via libvirt+XEN and
serving installation content via the auto url feature (using a
builtin http server).
A sample configuration is provided to run a Fedora 15 64 bits PV
based test (libvirt_xenpv_f15_quick).
Signed-off-by: Cleber Rosa <crosa@redhat.com>
---
client/tests/libvirt/tests.cfg.sample | 15 ++
client/tests/libvirt/tests_base.cfg.sample | 7 +
client/virt/tests/unattended_install.py | 197 +++++++++++++++++++++++++---
3 files changed, 203 insertions(+), 16 deletions(-)
diff --git a/client/tests/libvirt/tests.cfg.sample b/client/tests/libvirt/tests.cfg.sample
index a068587..8a1d318 100644
--- a/client/tests/libvirt/tests.cfg.sample
+++ b/client/tests/libvirt/tests.cfg.sample
@@ -38,6 +38,21 @@ variants:
only Fedora.15.64
only unattended_install.cdrom, boot, reboot, shutdown
+ # Runs virt-install, f15 64 as a 64 bit PV guest OS, install, boot, shutdown
+ - @libvirt_xenpv_f15_quick:
+ virt_install_binary = /usr/bin/virt-install
+ qemu_img_binary = /usr/bin/qemu-img
+ url = auto
+ cdrom_cd1 = isos/linux/Fedora-15-x86_64-DVD.iso
+ only raw
+ only xennet
+ only xenblk
+ only smp2
+ only no_pci_assignable
+ only smallpages
+ only Fedora.15.64
+ only unattended_install.url, boot, reboot, shutdown
+
# Runs virt-install, RHEL 6.0 64 bit guest OS, install, boot, shutdown
- @libvirt_rhel60_quick:
virt_install_binary = /usr/bin/virt-install
diff --git a/client/tests/libvirt/tests_base.cfg.sample b/client/tests/libvirt/tests_base.cfg.sample
index f2a4e35..5fe8b01 100644
--- a/client/tests/libvirt/tests_base.cfg.sample
+++ b/client/tests/libvirt/tests_base.cfg.sample
@@ -90,6 +90,9 @@ use_os_variant = no
use_os_type = yes
# libvirt network to use examples network=default or bridge=br0
virsh_network = network=default
+# if using 'url = auto' to install, url_auto_ip must match IP on
+# selected virsh network or bridge
+url_auto_ip = 192.168.122.1
# wait in minutes for virt-install to finish (bz still open)
use_virt_install_wait = no
virt_install_wait_time = 300
@@ -1165,6 +1168,8 @@ variants:
# Device selection for the NDISTest server machine
dp_regex_servermsgdev = VirtIO Ethernet Adapter$
dp_regex_serversupportdev = VirtIO Ethernet Adapter #2$
+ -xennet:
+ # placeholder
# Guests
variants:
@@ -2865,6 +2870,8 @@ variants:
drive_format=usb2
- usb.cdrom:
cd_format=usb2
+ - xenblk:
+ # placeholder
virtio_net, virtio_blk, e1000, balloon_check:
diff --git a/client/virt/tests/unattended_install.py b/client/virt/tests/unattended_install.py
index efa3c10..ea3e9f4 100644
--- a/client/virt/tests/unattended_install.py
+++ b/client/virt/tests/unattended_install.py
@@ -1,8 +1,45 @@
import logging, time, socket, re, os, shutil, tempfile, glob, ConfigParser
+import threading
import xml.dom.minidom
from autotest_lib.client.common_lib import error
from autotest_lib.client.bin import utils
-from autotest_lib.client.virt import virt_vm, virt_utils
+from autotest_lib.client.virt import virt_vm, virt_utils, virt_http_server
+
+
+_url_auto_content_server_thread = None
+_url_auto_content_server_thread_event = None
+
+_unattended_server_thread = None
+_unattended_server_thread_event = None
+
+
+def terminate_auto_content_server_thread():
+ global _url_auto_content_server_thread
+ global _url_auto_content_server_thread_event
+
+ if _url_auto_content_server_thread is None:
+ return False
+ if _url_auto_content_server_thread_event is None:
+ return False
+
+ if _url_auto_content_server_thread_event.isSet():
+ return True
+
+ return False
+
+
+def terminate_unattended_server_thread():
+ global _unattended_server_thread, _unattended_server_thread_event
+
+ if _unattended_server_thread is None:
+ return False
+ if _unattended_server_thread_event is None:
+ return False
+
+ if _unattended_server_thread_event.isSet():
+ return True
+
+ return False
@error.context_aware
@@ -213,12 +250,13 @@ class UnattendedInstallConfig(object):
root_dir = test.bindir
self.deps_dir = os.path.join(test.virtdir, 'deps')
self.unattended_dir = os.path.join(test.virtdir, 'unattended')
+ self.params = params
attributes = ['kernel_args', 'finish_program', 'cdrom_cd1',
'unattended_file', 'medium', 'url', 'kernel', 'initrd',
'nfs_server', 'nfs_dir', 'install_virtio', 'floppy',
'cdrom_unattended', 'boot_path', 'extra_params',
- 'qemu_img_binary', 'cdkey', 'finish_program']
+ 'qemu_img_binary', 'cdkey', 'finish_program', 'vm_type']
for a in attributes:
setattr(self, a, params.get(a, ''))
@@ -258,6 +296,14 @@ class UnattendedInstallConfig(object):
self.image_path = os.path.dirname(self.kernel)
+ # Content server params
+ self.url_auto_content_ip = params.get('url_auto_ip', '192.168.122.1')
+ self.url_auto_content_port = None
+
+ # Kickstart server params
+ # use the same IP as url_auto_content_ip, but a different port
+ self.unattended_server_port = None
+
def answer_kickstart(self, answer_path):
"""
@@ -278,7 +324,13 @@ class UnattendedInstallConfig(object):
if self.medium in ["cdrom", "kernel_initrd"]:
content = "cdrom"
elif self.medium == "url":
- content = "url --url %s" % self.url
+ if self.url == 'auto':
+ url = "http://%s:%s" % (self.url_auto_content_ip,
+ self.url_auto_content_port)
+ else:
+ url = self.url
+ content = "url --url %s" % url
+
elif self.medium == "nfs":
content = "nfs --server=%s --dir=%s" % (self.nfs_server,
self.nfs_dir)
@@ -407,6 +459,51 @@ class UnattendedInstallConfig(object):
doc.writexml(fp)
+ def setup_unattended_http_server(self):
+ '''
+ Setup a builtin http server for serving the kickstart file
+
+ Does nothing if unattended file is not a kickstart file
+ '''
+ global _unattended_server_thread, _unattended_server_thread_event
+
+ if self.unattended_file.endswith('.ks'):
+ # Red Hat kickstart install
+ dest_fname = 'ks.cfg'
+
+ answer_path = os.path.join(self.tmpdir, dest_fname)
+ self.answer_kickstart(answer_path)
+
+ if self.unattended_server_port is None:
+ self.unattended_server_port = virt_utils.find_free_port(
+ 8000,
+ 8100,
+ self.url_auto_content_ip)
+
+ if _unattended_server_thread is None:
+ _unattended_server_thread_event = threading.Event()
+ _unattended_server_thread = threading.Thread(
+ target=virt_http_server.http_server,
+ args=(self.unattended_server_port, self.tmpdir,
+ terminate_unattended_server_thread))
+ _unattended_server_thread.start()
+
+ # Point installation to this kickstart url
+ ks_param = 'ks=http://%s:%s/%s' % (self.url_auto_content_ip,
+ self.unattended_server_port,
+ dest_fname)
+ if 'ks=' in self.extra_params:
+ extra_params = re.sub('ks\=[\w\d\:\.\/]+',
+ ks_param,
+ self.extra_params)
+ else:
+ extra_params += ' %s ' % ks_param
+
+ # reflect change on params
+ self.extra_params = extra_params
+ self.params['extra_params'] = self.extra_params
+
+
def setup_boot_disk(self):
if self.unattended_file.endswith('.sif'):
dest_fname = 'winnt.sif'
@@ -497,24 +594,70 @@ class UnattendedInstallConfig(object):
@error.context_aware
+ def setup_url_auto(self):
+ """
+ Configures the builtin web server for serving content
+ """
+ global _url_auto_content_server_thread
+ global _url_auto_content_server_thread_event
+
+ logging.debug("starting unattended content web server")
+
+ if self.params.get('cdrom_cd1'):
+ # setup and mount cdrom contents to be served by http server
+ m_cmd = ('mount -t iso9660 -v -o loop,ro %s %s' %
+ (self.cdrom_cd1, self.cdrom_cd1_mount))
+ utils.run(m_cmd)
+
+ self.url_auto_content_port = virt_utils.find_free_port(
+ 8000,
+ 8100,
+ self.url_auto_content_ip)
+
+ if _url_auto_content_server_thread is None:
+ _url_auto_content_server_thread_event = threading.Event()
+ _url_auto_content_server_thread = threading.Thread(
+ target=virt_http_server.http_server,
+ args=(self.url_auto_content_port, self.cdrom_cd1_mount,
+ terminate_auto_content_server_thread))
+ _url_auto_content_server_thread.start()
+
+ auto_content_url = 'http://%s:%s' % (self.url_auto_content_ip,
+ self.url_auto_content_port)
+ self.params['auto_content_url'] = auto_content_url
+
+
+ @error.context_aware
def setup_url(self):
"""
Download the vmlinuz and initrd.img from URL.
"""
- error.context("downloading vmlinuz and initrd.img from %s" % self.url)
- os.chdir(self.image_path)
- kernel_fetch_cmd = "wget -q %s/%s/%s" % (self.url, self.boot_path,
- os.path.basename(self.kernel))
- initrd_fetch_cmd = "wget -q %s/%s/%s" % (self.url, self.boot_path,
- os.path.basename(self.initrd))
+ # it's only necessary to download kernel/initrd if running bare qemu
+ if self.vm_type == 'kvm':
+ error.context("downloading vmlinuz/initrd.img from %s" % self.url)
+ os.chdir(self.image_path)
+ kernel_cmd = "wget -q %s/%s/%s" % (self.url,
+ self.boot_path,
+ os.path.basename(self.kernel))
+ initrd_cmd = "wget -q %s/%s/%s" % (self.url,
+ self.boot_path,
+ os.path.basename(self.initrd))
+
+ if os.path.exists(self.kernel):
+ os.remove(self.kernel)
+ if os.path.exists(self.initrd):
+ os.remove(self.initrd)
- if os.path.exists(self.kernel):
- os.remove(self.kernel)
- if os.path.exists(self.initrd):
- os.remove(self.initrd)
+ utils.run(kernel_fetch_cmd)
+ utils.run(initrd_fetch_cmd)
+
+ elif self.vm_type == 'libvirt':
+ error.context("not downloading vmlinuz/initrd.img from %s, "
+ "letting virt-install do it instead")
- utils.run(kernel_fetch_cmd)
- utils.run(initrd_fetch_cmd)
+ else:
+ error.context("no action defined/needed for the current virt "
+ "type: '%s'" % self.vm_type)
def setup_nfs(self):
@@ -556,6 +699,9 @@ class UnattendedInstallConfig(object):
self.setup_cdrom()
elif self.medium == "url":
self.setup_url()
+ if self.url == 'auto':
+ self.setup_url_auto()
+ self.setup_unattended_http_server()
elif self.medium == "nfs":
self.setup_nfs()
else:
@@ -577,7 +723,10 @@ def run_unattended_install(test, params, env):
unattended_install_config = UnattendedInstallConfig(test, params)
unattended_install_config.setup()
vm = env.get_vm(params["main_vm"])
- vm.create()
+
+ # params passed explicitly, because they may have been updated by
+ # unattended install config code, such as when params['url'] == auto
+ vm.create(params=params)
install_timeout = int(params.get("timeout", 3000))
port = vm.get_port(int(params.get("guest_port_unattended_install")))
@@ -620,6 +769,22 @@ def run_unattended_install(test, params, env):
raise error.TestFail("Timeout elapsed while waiting for install to "
"finish")
+ logging.debug('cleaning up threads and mounts that may be active')
+ global _url_auto_content_server_thread
+ global _url_auto_content_server_thread_event
+ if _url_auto_content_server_thread is not None:
+ _url_auto_content_server_thread_event.set()
+ _url_auto_content_server_thread.join(3)
+ _url_auto_content_server_thread = None
+ cleanup(unattended_install_config.cdrom_cd1_mount)
+
+ global _unattended_server_thread
+ global _unattended_server_thread_event
+ if _unattended_server_thread is not None:
+ _unattended_server_thread_event.set()
+ _unattended_server_thread.join(3)
+ _unattended_server_thread = None
+
time_elapsed = time.time() - start_time
logging.info("Guest reported successful installation after %d s (%d min)",
time_elapsed, time_elapsed/60)
--
1.7.6.4
prev parent reply other threads:[~2011-10-11 21:07 UTC|newest]
Thread overview: 16+ messages / expand[flat|nested] mbox.gz Atom feed top
2011-10-11 21:07 [PATCH 00/11] [RFC] Libvirt test v2 Lucas Meneghel Rodrigues
2011-10-11 21:07 ` [PATCH 02/11] virt: Introducing virt_test.virt_test class Lucas Meneghel Rodrigues
2011-10-11 21:07 ` [PATCH 03/11] Moving unattended_install test from kvm test to common virt location Lucas Meneghel Rodrigues
2011-10-11 21:07 ` [PATCH 04/11] Moving get_started code to client.virt.virt_utils Lucas Meneghel Rodrigues
2011-10-11 21:07 ` [PATCH 05/11] virt: Introducing libvirt VM class Lucas Meneghel Rodrigues
2011-10-12 6:51 ` [Autotest] " Amos Kong
2011-10-12 8:14 ` Daniel P. Berrange
2011-10-13 17:26 ` Lucas Meneghel Rodrigues
2011-10-11 21:07 ` [PATCH 06/11] virt: Introducing libvirt monitor Lucas Meneghel Rodrigues
2011-10-12 7:48 ` [Autotest] " Amos Kong
2011-10-13 17:12 ` Lucas Meneghel Rodrigues
2011-10-11 21:07 ` [PATCH 07/11] virt.virt_env_process: Add libvirt vm handling Lucas Meneghel Rodrigues
2011-10-11 21:07 ` [PATCH 08/11] client.tests: Introducing libvirt test Lucas Meneghel Rodrigues
2011-10-11 21:07 ` [PATCH 09/11] Virt: builtin HTTP server for unattended installs Lucas Meneghel Rodrigues
2011-10-11 21:07 ` [PATCH 10/11] Virt: support XEN via libvirt and auto url installer Lucas Meneghel Rodrigues
2011-10-11 21:07 ` Lucas Meneghel Rodrigues [this message]
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=1318367237-26081-12-git-send-email-lmr@redhat.com \
--to=lmr@redhat.com \
--cc=autotest@test.kernel.org \
--cc=kvm@vger.kernel.org \
/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.
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 NNTP newsgroup(s).