Hi Hugh > We don't really want to put OS-specific stuff into the virt-install code > if we can help it; we made an exception for the config flag setting > stuff because we're just abstracting behavior (setting acpi= and apic=) > that is already available. All right. In fact, I think OS-specific stuff shouldn't put into the virt-install, too. > However I don't see any reason why a patch that would allow a virtinst > argument like "--keep-cdrom" and then put something like "<disk > type="block" device="cdrom">... etc" in the domain's permanent xml > wouldn't work. This would mean that the domain would have access to the > cdrom drive every time it reboots. Of course, it also means we'll need > to provide some way to disconnect the domain from that drive once the > install process is finished, but we'll get to that later. > > Let me know if that works for you... I remaked a patch. This time, it has the flag in FullVirtGuest.OS_TYPES. The OS-specific code is removed from virt-inst. How about this correction? Signed-off-by: Nobuhiro Itou <fj0873gn@xxxxxxxxxxxxxxxxx> Thanks, Nobuhiro Itou. ------------------------------------------------------------- diff -r 36a9973c2e28 virt-install --- a/virt-install Tue Mar 27 08:13:38 2007 -0400 +++ b/virt-install Tue Mar 27 19:24:31 2007 +0900 @@ -535,6 +535,7 @@ def main(): if not hvm: # paravirt get_paravirt_install(options.location, guest) get_paravirt_extraargs(options.extra, guest) + continue_inst = False else: get_fullvirt_cdrom(options.cdrom, guest) guest.set_os_type(options.os_type) @@ -543,6 +544,7 @@ def main(): guest.features["acpi"] = False if options.noapic: guest.features["apic"] = False + continue_inst = guest.get_continue_inst() if options.autoconsole is False: conscb = None @@ -577,6 +579,17 @@ def main(): struct.unpack("H", buf[0x1fe: 0x200]) == (0xaa55,): # things installed enough that we should be able to restart # the domain + if continue_inst: + # continue to installation. + dom = guest.continue_install(conscb,progresscb) + if dom is None: + print "Guest installation failed" + sys.exit(0) + elif dom.info()[0] != libvirt.VIR_DOMAIN_SHUTOFF: + # domain seems to be running + print "Domain installation still in progress. You can reconnect " + print "to the console to complete the installation process." + sys.exit(0) print "Guest installation complete... restarting guest." dom.create() guest.connect_console(conscb) diff -r 36a9973c2e28 virtinst/Guest.py --- a/virtinst/Guest.py Tue Mar 27 08:13:38 2007 -0400 +++ b/virtinst/Guest.py Tue Mar 27 15:02:39 2007 +0900 @@ -580,9 +580,12 @@ class Guest(object): "networks": self._get_network_xml(install), \ "graphics": self._get_graphics_xml(install) } - def get_config_xml(self, install = True): + def get_config_xml(self, install = True, disk_boot = False): if install: - osblob = self._get_install_xml() + if disk_boot: + osblob = self._get_runtime_xml() + else: + osblob = self._get_install_xml() action = "destroy" else: osblob = self._get_runtime_xml() diff -r 36a9973c2e28 virtinst/FullVirtGuest.py --- a/virtinst/FullVirtGuest.py Tue Mar 27 08:13:38 2007 -0400 +++ b/virtinst/FullVirtGuest.py Wed Mar 28 16:29:01 2007 +0900 @@ -17,26 +17,27 @@ import Guest import Guest import util import DistroManager +import logging class FullVirtGuest(Guest.XenGuest): - OS_TYPES = { "Linux" : { "Red Hat Enterprise Linux AS 2.1/3" : { "acpi" : True, "apic": True }, \ - "Red Hat Enterprise Linux 4" : { "acpi" : True, "apic": True }, \ - "Red Hat Enterprise Linux 5" : { "acpi" : True, "apic": True }, \ - "Fedora Core 4-6" : { "acpi" : True, "apic": True }, \ - "Suse Linux Enterprise Server" : { "acpi" : True, "apic": True }, \ - "Other Linux 2.6 kernel" : { "acpi" : True, "apic": True } }, \ - "Microsoft Windows" : { "Windows 2000" : { "acpi": False, "apic" : False }, \ - "Windows XP" : { "acpi": True, "apic" : True }, \ - "Windows Server 2003" : { "acpi": True, "apic" : True }, \ - "Windows Vista" : { "acpi": True, "apic" : True } }, \ - "Novell Netware" : { "Netware 4" : { "acpi": True, "apic": True }, \ - "Netware 5" : { "acpi": True, "apic": True }, \ - "Netware 6" : { "acpi": True, "apic": True } }, \ - "Sun Solaris" : { "Solaris 10" : { "acpi": True, "apic": True }, \ - "Solaris 9" : { "acpi": True, "apic": True } }, \ - "Other" : { "MS-DOS" : { "acpi": False, "apic" : False }, \ - "Free BSD" : { "acpi": True, "apic" : True }, \ - "Other" : { "acpi": True, "apic" : True } } } + OS_TYPES = { "Linux" : { "Red Hat Enterprise Linux AS 2.1/3" : { "acpi" : True, "apic": True, "continue": False }, \ + "Red Hat Enterprise Linux 4" : { "acpi" : True, "apic": True, "continue": False }, \ + "Red Hat Enterprise Linux 5" : { "acpi" : True, "apic": True, "continue": False }, \ + "Fedora Core 4-6" : { "acpi" : True, "apic": True, "continue": False }, \ + "Suse Linux Enterprise Server" : { "acpi" : True, "apic": True, "continue": False }, \ + "Other Linux 2.6 kernel" : { "acpi" : True, "apic": True, "continue": False } }, \ + "Microsoft Windows" : { "Windows 2000" : { "acpi": False, "apic" : False, "continue": True }, \ + "Windows XP" : { "acpi": True, "apic" : True, "continue": True }, \ + "Windows Server 2003" : { "acpi": True, "apic" : True, "continue": True }, \ + "Windows Vista" : { "acpi": True, "apic" : True, "continue": True } }, \ + "Novell Netware" : { "Netware 4" : { "acpi": True, "apic": True, "continue": False }, \ + "Netware 5" : { "acpi": True, "apic": True, "continue": False }, \ + "Netware 6" : { "acpi": True, "apic": True, "continue": False } }, \ + "Sun Solaris" : { "Solaris 10" : { "acpi": True, "apic": True, "continue": False }, \ + "Solaris 9" : { "acpi": True, "apic": True, "continue": False } }, \ + "Other" : { "MS-DOS" : { "acpi": False, "apic" : False, "continue": False }, \ + "Free BSD" : { "acpi": True, "apic" : True, "continue": False }, \ + "Other" : { "acpi": True, "apic" : True, "continue": False } } } def __init__(self, type=None, arch=None, connection=None, hypervisorURI=None, emulator=None): Guest.Guest.__init__(self, type=type, connection=connection, hypervisorURI=hypervisorURI) @@ -190,3 +191,26 @@ class FullVirtGuest(Guest.XenGuest): self.disks.append(Guest.VirtualDisk(cdrom, device=Guest.VirtualDisk.DEVICE_CDROM, readOnly=True, transient=True)) return tmpfiles + + def get_continue_inst(self): + return FullVirtGuest.OS_TYPES[self._os_type][self._os_variant]["continue"] + + def continue_install(self, consolecb, meter): + install_xml = self.get_config_xml(disk_boot = True) + logging.debug("Starting guest from '%s'" % ( install_xml )) + meter.start(size=None, text="Starting domain...") + self.domain = self.conn.createLinux(install_xml, 0) + if self.domain is None: + raise RuntimeError, "Unable to start domain for guest, aborting installation!" + meter.end(0) + + self.connect_console(consolecb) + + # ensure there's time for the domain to finish destroying if the + # install has finished or the guest crashed + if consolecb: + time.sleep(1) + + # This should always work, because it'll lookup a config file + # for inactive guest, or get the still running install.. + return self.conn.lookupByName(self.name)