WARNING - OLD ARCHIVES

This is an archived copy of the Xen.org mailing list, which we have preserved to ensure that existing links to archives are not broken. The live archive, which contains the latest emails, can be found at http://lists.xen.org/
   
 
 
Xen 
 
Home Products Support Community News
 
   
 

xen-changelog

[Xen-changelog] [xen-unstable] Implement new booting parameters for Xen-

To: xen-changelog@xxxxxxxxxxxxxxxxxxx
Subject: [Xen-changelog] [xen-unstable] Implement new booting parameters for Xen-API, and backwards compatibility for
From: Xen patchbot-unstable <patchbot-unstable@xxxxxxxxxxxxxxxxxxx>
Date: Fri, 15 Dec 2006 10:50:25 +0000
Delivery-date: Fri, 15 Dec 2006 02:50:47 -0800
Envelope-to: www-data@xxxxxxxxxxxxxxxxxx
List-help: <mailto:xen-changelog-request@lists.xensource.com?subject=help>
List-id: BK change log <xen-changelog.lists.xensource.com>
List-post: <mailto:xen-changelog@lists.xensource.com>
List-subscribe: <http://lists.xensource.com/cgi-bin/mailman/listinfo/xen-changelog>, <mailto:xen-changelog-request@lists.xensource.com?subject=subscribe>
List-unsubscribe: <http://lists.xensource.com/cgi-bin/mailman/listinfo/xen-changelog>, <mailto:xen-changelog-request@lists.xensource.com?subject=unsubscribe>
Reply-to: xen-devel@xxxxxxxxxxxxxxxxxxx
Sender: xen-changelog-bounces@xxxxxxxxxxxxxxxxxxx
# HG changeset patch
# User Ewan Mellor <ewan@xxxxxxxxxxxxx>
# Node ID 0ee4e33b4401be41ba3a30811eeefe05ae2aca3b
# Parent  da0849b741707e07723f97f7b3fc4b16a88636da
Implement new booting parameters for Xen-API, and backwards compatibility for
the old bootloader settings.

We now have two mutually exclusive config groups HVM and PV, with HVM/boot
and PV/{bootloader,kernel,ramdisk,args,bootloader_args}.

Signed-off-by: Ewan Mellor <ewan@xxxxxxxxxxxxx>
---
 tools/libxen/include/xen_vm.h           |  223 ++++++++--------
 tools/libxen/src/xen_vm.c               |  421 ++++++++++++++------------------
 tools/python/xen/xend/XendAPI.py        |  149 +++++------
 tools/python/xen/xend/XendBootloader.py |   17 -
 tools/python/xen/xend/XendConfig.py     |   81 +-----
 tools/python/xen/xend/XendDomainInfo.py |  164 +++++++-----
 tools/python/xen/xend/image.py          |   13 
 7 files changed, 518 insertions(+), 550 deletions(-)

diff -r da0849b74170 -r 0ee4e33b4401 tools/libxen/include/xen_vm.h
--- a/tools/libxen/include/xen_vm.h     Thu Dec 14 17:43:41 2006 +0000
+++ b/tools/libxen/include/xen_vm.h     Thu Dec 14 18:24:14 2006 +0000
@@ -19,7 +19,6 @@
 #ifndef XEN_VM_H
 #define XEN_VM_H
 
-#include "xen_boot_type.h"
 #include "xen_common.h"
 #include "xen_console_decl.h"
 #include "xen_cpu_feature.h"
@@ -36,9 +35,36 @@
 
 
 /*
- * The VM class. 
- *  
+ * The VM class.
+ * 
  * A virtual machine (or 'guest').
+ * 
+ * VM booting is controlled by setting one of the two mutually exclusive
+ * groups: "PV", and "HVM".  If HVM.boot is the empty string, then paravirtual
+ * domain building and booting will be used; otherwise the VM will be loaded
+ * as an HVM domain, and booted using an emulated BIOS.
+ * 
+ * When paravirtual booting is in use, the PV/bootloader field indicates the
+ * bootloader to use.  It may be "pygrub", in which case the platform's
+ * default installation of pygrub will be used, or a full path within the
+ * control domain to some other bootloader.  The other fields, PV/kernel,
+ * PV/ramdisk, PV/args and PV/bootloader_args will be passed to the bootloader
+ * unmodified, and interpretation of those fields is then specific to the
+ * bootloader itself, including the possibility that the bootloader will
+ * ignore some or all of those given values.
+ * 
+ * If the bootloader is pygrub, then the menu.lst is parsed if present in the
+ * guest's filesystem, otherwise the specified kernel and ramdisk are used, or
+ * an autodetected kernel is used if nothing is specified and autodetection is
+ * possible.  PV/args is appended to the kernel command line, no matter which
+ * mechanism is used for finding the kernel.
+ * 
+ * If PV/bootloader is empty but PV/kernel is specified, then the kernel and
+ * ramdisk values will be treated as paths within the control domain.  If both
+ * PV/bootloader and PV/kernel are empty, then the behaviour is as if
+ * PV/bootloader was specified as "pygrub".
+ * 
+ * When using HVM booting, HVM/boot specifies the order of the boot devices.
  */
 
 
@@ -102,18 +128,17 @@ typedef struct xen_vm_record
     struct xen_vif_record_opt_set *vifs;
     struct xen_vbd_record_opt_set *vbds;
     struct xen_vtpm_record_opt_set *vtpms;
-    char *bios_boot;
+    char *pv_bootloader;
+    char *pv_kernel;
+    char *pv_ramdisk;
+    char *pv_args;
+    char *pv_bootloader_args;
+    char *hvm_boot;
     bool platform_std_vga;
     char *platform_serial;
     bool platform_localtime;
     bool platform_clock_offset;
     bool platform_enable_audio;
-    char *builder;
-    enum xen_boot_type boot_method;
-    char *kernel_kernel;
-    char *kernel_initrd;
-    char *kernel_args;
-    char *grub_cmdline;
     char *pci_bus;
     xen_string_string_map *tools_version;
     xen_string_string_map *otherconfig;
@@ -439,10 +464,45 @@ xen_vm_get_vtpms(xen_session *session, s
 
 
 /**
- * Get the bios/boot field of the given VM.
- */
-extern bool
-xen_vm_get_bios_boot(xen_session *session, char **result, xen_vm vm);
+ * Get the PV/bootloader field of the given VM.
+ */
+extern bool
+xen_vm_get_pv_bootloader(xen_session *session, char **result, xen_vm vm);
+
+
+/**
+ * Get the PV/kernel field of the given VM.
+ */
+extern bool
+xen_vm_get_pv_kernel(xen_session *session, char **result, xen_vm vm);
+
+
+/**
+ * Get the PV/ramdisk field of the given VM.
+ */
+extern bool
+xen_vm_get_pv_ramdisk(xen_session *session, char **result, xen_vm vm);
+
+
+/**
+ * Get the PV/args field of the given VM.
+ */
+extern bool
+xen_vm_get_pv_args(xen_session *session, char **result, xen_vm vm);
+
+
+/**
+ * Get the PV/bootloader_args field of the given VM.
+ */
+extern bool
+xen_vm_get_pv_bootloader_args(xen_session *session, char **result, xen_vm vm);
+
+
+/**
+ * Get the HVM/boot field of the given VM.
+ */
+extern bool
+xen_vm_get_hvm_boot(xen_session *session, char **result, xen_vm vm);
 
 
 /**
@@ -478,48 +538,6 @@ xen_vm_get_platform_clock_offset(xen_ses
  */
 extern bool
 xen_vm_get_platform_enable_audio(xen_session *session, bool *result, xen_vm 
vm);
-
-
-/**
- * Get the builder field of the given VM.
- */
-extern bool
-xen_vm_get_builder(xen_session *session, char **result, xen_vm vm);
-
-
-/**
- * Get the boot_method field of the given VM.
- */
-extern bool
-xen_vm_get_boot_method(xen_session *session, enum xen_boot_type *result, 
xen_vm vm);
-
-
-/**
- * Get the kernel/kernel field of the given VM.
- */
-extern bool
-xen_vm_get_kernel_kernel(xen_session *session, char **result, xen_vm vm);
-
-
-/**
- * Get the kernel/initrd field of the given VM.
- */
-extern bool
-xen_vm_get_kernel_initrd(xen_session *session, char **result, xen_vm vm);
-
-
-/**
- * Get the kernel/args field of the given VM.
- */
-extern bool
-xen_vm_get_kernel_args(xen_session *session, char **result, xen_vm vm);
-
-
-/**
- * Get the grub/cmdline field of the given VM.
- */
-extern bool
-xen_vm_get_grub_cmdline(xen_session *session, char **result, xen_vm vm);
 
 
 /**
@@ -688,10 +706,45 @@ xen_vm_set_actions_after_crash(xen_sessi
 
 
 /**
- * Set the bios/boot field of the given VM.
- */
-extern bool
-xen_vm_set_bios_boot(xen_session *session, xen_vm vm, char *boot);
+ * Set the PV/bootloader field of the given VM.
+ */
+extern bool
+xen_vm_set_pv_bootloader(xen_session *session, xen_vm vm, char *bootloader);
+
+
+/**
+ * Set the PV/kernel field of the given VM.
+ */
+extern bool
+xen_vm_set_pv_kernel(xen_session *session, xen_vm vm, char *kernel);
+
+
+/**
+ * Set the PV/ramdisk field of the given VM.
+ */
+extern bool
+xen_vm_set_pv_ramdisk(xen_session *session, xen_vm vm, char *ramdisk);
+
+
+/**
+ * Set the PV/args field of the given VM.
+ */
+extern bool
+xen_vm_set_pv_args(xen_session *session, xen_vm vm, char *args);
+
+
+/**
+ * Set the PV/bootloader_args field of the given VM.
+ */
+extern bool
+xen_vm_set_pv_bootloader_args(xen_session *session, xen_vm vm, char 
*bootloader_args);
+
+
+/**
+ * Set the HVM/boot field of the given VM.
+ */
+extern bool
+xen_vm_set_hvm_boot(xen_session *session, xen_vm vm, char *boot);
 
 
 /**
@@ -727,48 +780,6 @@ xen_vm_set_platform_clock_offset(xen_ses
  */
 extern bool
 xen_vm_set_platform_enable_audio(xen_session *session, xen_vm vm, bool 
enable_audio);
-
-
-/**
- * Set the builder field of the given VM.
- */
-extern bool
-xen_vm_set_builder(xen_session *session, xen_vm vm, char *builder);
-
-
-/**
- * Set the boot_method field of the given VM.
- */
-extern bool
-xen_vm_set_boot_method(xen_session *session, xen_vm vm, enum xen_boot_type 
boot_method);
-
-
-/**
- * Set the kernel/kernel field of the given VM.
- */
-extern bool
-xen_vm_set_kernel_kernel(xen_session *session, xen_vm vm, char *kernel);
-
-
-/**
- * Set the kernel/initrd field of the given VM.
- */
-extern bool
-xen_vm_set_kernel_initrd(xen_session *session, xen_vm vm, char *initrd);
-
-
-/**
- * Set the kernel/args field of the given VM.
- */
-extern bool
-xen_vm_set_kernel_args(xen_session *session, xen_vm vm, char *args);
-
-
-/**
- * Set the grub/cmdline field of the given VM.
- */
-extern bool
-xen_vm_set_grub_cmdline(xen_session *session, xen_vm vm, char *cmdline);
 
 
 /**
@@ -814,8 +825,8 @@ xen_vm_unpause(xen_session *session, xen
 
 /**
  * Attempt to cleanly shutdown the specified VM. (Note: this may not be
- * supported---e.g. if a guest agent is not installed). 
- *  
+ * supported---e.g. if a guest agent is not installed).
+ * 
  * Once shutdown has been completed perform poweroff action specified in guest
  * configuration.
  */
@@ -825,8 +836,8 @@ xen_vm_clean_shutdown(xen_session *sessi
 
 /**
  * Attempt to cleanly shutdown the specified VM (Note: this may not be
- * supported---e.g. if a guest agent is not installed). 
- *  
+ * supported---e.g. if a guest agent is not installed).
+ * 
  * Once shutdown has been completed perform reboot action specified in guest
  * configuration.
  */
diff -r da0849b74170 -r 0ee4e33b4401 tools/libxen/src/xen_vm.c
--- a/tools/libxen/src/xen_vm.c Thu Dec 14 17:43:41 2006 +0000
+++ b/tools/libxen/src/xen_vm.c Thu Dec 14 18:24:14 2006 +0000
@@ -20,7 +20,6 @@
 #include <stddef.h>
 #include <stdlib.h>
 
-#include "xen_boot_type_internal.h"
 #include "xen_common.h"
 #include "xen_console.h"
 #include "xen_cpu_feature.h"
@@ -136,9 +135,24 @@ static const struct_member xen_vm_record
         { .key = "VTPMs",
           .type = &abstract_type_ref_set,
           .offset = offsetof(xen_vm_record, vtpms) },
-        { .key = "bios_boot",
+        { .key = "PV_bootloader",
           .type = &abstract_type_string,
-          .offset = offsetof(xen_vm_record, bios_boot) },
+          .offset = offsetof(xen_vm_record, pv_bootloader) },
+        { .key = "PV_kernel",
+          .type = &abstract_type_string,
+          .offset = offsetof(xen_vm_record, pv_kernel) },
+        { .key = "PV_ramdisk",
+          .type = &abstract_type_string,
+          .offset = offsetof(xen_vm_record, pv_ramdisk) },
+        { .key = "PV_args",
+          .type = &abstract_type_string,
+          .offset = offsetof(xen_vm_record, pv_args) },
+        { .key = "PV_bootloader_args",
+          .type = &abstract_type_string,
+          .offset = offsetof(xen_vm_record, pv_bootloader_args) },
+        { .key = "HVM_boot",
+          .type = &abstract_type_string,
+          .offset = offsetof(xen_vm_record, hvm_boot) },
         { .key = "platform_std_VGA",
           .type = &abstract_type_bool,
           .offset = offsetof(xen_vm_record, platform_std_vga) },
@@ -154,24 +168,6 @@ static const struct_member xen_vm_record
         { .key = "platform_enable_audio",
           .type = &abstract_type_bool,
           .offset = offsetof(xen_vm_record, platform_enable_audio) },
-        { .key = "builder",
-          .type = &abstract_type_string,
-          .offset = offsetof(xen_vm_record, builder) },
-        { .key = "boot_method",
-          .type = &xen_boot_type_abstract_type_,
-          .offset = offsetof(xen_vm_record, boot_method) },
-        { .key = "kernel_kernel",
-          .type = &abstract_type_string,
-          .offset = offsetof(xen_vm_record, kernel_kernel) },
-        { .key = "kernel_initrd",
-          .type = &abstract_type_string,
-          .offset = offsetof(xen_vm_record, kernel_initrd) },
-        { .key = "kernel_args",
-          .type = &abstract_type_string,
-          .offset = offsetof(xen_vm_record, kernel_args) },
-        { .key = "grub_cmdline",
-          .type = &abstract_type_string,
-          .offset = offsetof(xen_vm_record, grub_cmdline) },
         { .key = "PCI_bus",
           .type = &abstract_type_string,
           .offset = offsetof(xen_vm_record, pci_bus) },
@@ -216,13 +212,13 @@ xen_vm_record_free(xen_vm_record *record
     xen_vif_record_opt_set_free(record->vifs);
     xen_vbd_record_opt_set_free(record->vbds);
     xen_vtpm_record_opt_set_free(record->vtpms);
-    free(record->bios_boot);
+    free(record->pv_bootloader);
+    free(record->pv_kernel);
+    free(record->pv_ramdisk);
+    free(record->pv_args);
+    free(record->pv_bootloader_args);
+    free(record->hvm_boot);
     free(record->platform_serial);
-    free(record->builder);
-    free(record->kernel_kernel);
-    free(record->kernel_initrd);
-    free(record->kernel_args);
-    free(record->grub_cmdline);
     free(record->pci_bus);
     xen_string_string_map_free(record->tools_version);
     xen_string_string_map_free(record->otherconfig);
@@ -786,7 +782,7 @@ xen_vm_get_vtpms(xen_session *session, s
 
 
 bool
-xen_vm_get_bios_boot(xen_session *session, char **result, xen_vm vm)
+xen_vm_get_pv_bootloader(xen_session *session, char **result, xen_vm vm)
 {
     abstract_value param_values[] =
         {
@@ -797,7 +793,92 @@ xen_vm_get_bios_boot(xen_session *sessio
     abstract_type result_type = abstract_type_string;
 
     *result = NULL;
-    XEN_CALL_("VM.get_bios_boot");
+    XEN_CALL_("VM.get_PV_bootloader");
+    return session->ok;
+}
+
+
+bool
+xen_vm_get_pv_kernel(xen_session *session, char **result, xen_vm vm)
+{
+    abstract_value param_values[] =
+        {
+            { .type = &abstract_type_string,
+              .u.string_val = vm }
+        };
+
+    abstract_type result_type = abstract_type_string;
+
+    *result = NULL;
+    XEN_CALL_("VM.get_PV_kernel");
+    return session->ok;
+}
+
+
+bool
+xen_vm_get_pv_ramdisk(xen_session *session, char **result, xen_vm vm)
+{
+    abstract_value param_values[] =
+        {
+            { .type = &abstract_type_string,
+              .u.string_val = vm }
+        };
+
+    abstract_type result_type = abstract_type_string;
+
+    *result = NULL;
+    XEN_CALL_("VM.get_PV_ramdisk");
+    return session->ok;
+}
+
+
+bool
+xen_vm_get_pv_args(xen_session *session, char **result, xen_vm vm)
+{
+    abstract_value param_values[] =
+        {
+            { .type = &abstract_type_string,
+              .u.string_val = vm }
+        };
+
+    abstract_type result_type = abstract_type_string;
+
+    *result = NULL;
+    XEN_CALL_("VM.get_PV_args");
+    return session->ok;
+}
+
+
+bool
+xen_vm_get_pv_bootloader_args(xen_session *session, char **result, xen_vm vm)
+{
+    abstract_value param_values[] =
+        {
+            { .type = &abstract_type_string,
+              .u.string_val = vm }
+        };
+
+    abstract_type result_type = abstract_type_string;
+
+    *result = NULL;
+    XEN_CALL_("VM.get_PV_bootloader_args");
+    return session->ok;
+}
+
+
+bool
+xen_vm_get_hvm_boot(xen_session *session, char **result, xen_vm vm)
+{
+    abstract_value param_values[] =
+        {
+            { .type = &abstract_type_string,
+              .u.string_val = vm }
+        };
+
+    abstract_type result_type = abstract_type_string;
+
+    *result = NULL;
+    XEN_CALL_("VM.get_HVM_boot");
     return session->ok;
 }
 
@@ -879,108 +960,6 @@ xen_vm_get_platform_enable_audio(xen_ses
     abstract_type result_type = abstract_type_bool;
 
     XEN_CALL_("VM.get_platform_enable_audio");
-    return session->ok;
-}
-
-
-bool
-xen_vm_get_builder(xen_session *session, char **result, xen_vm vm)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm }
-        };
-
-    abstract_type result_type = abstract_type_string;
-
-    *result = NULL;
-    XEN_CALL_("VM.get_builder");
-    return session->ok;
-}
-
-
-bool
-xen_vm_get_boot_method(xen_session *session, enum xen_boot_type *result, 
xen_vm vm)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm }
-        };
-
-    abstract_type result_type = xen_boot_type_abstract_type_;
-    char *result_str = NULL;
-    XEN_CALL_("VM.get_boot_method");
-    *result = xen_boot_type_from_string(session, result_str);
-    return session->ok;
-}
-
-
-bool
-xen_vm_get_kernel_kernel(xen_session *session, char **result, xen_vm vm)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm }
-        };
-
-    abstract_type result_type = abstract_type_string;
-
-    *result = NULL;
-    XEN_CALL_("VM.get_kernel_kernel");
-    return session->ok;
-}
-
-
-bool
-xen_vm_get_kernel_initrd(xen_session *session, char **result, xen_vm vm)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm }
-        };
-
-    abstract_type result_type = abstract_type_string;
-
-    *result = NULL;
-    XEN_CALL_("VM.get_kernel_initrd");
-    return session->ok;
-}
-
-
-bool
-xen_vm_get_kernel_args(xen_session *session, char **result, xen_vm vm)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm }
-        };
-
-    abstract_type result_type = abstract_type_string;
-
-    *result = NULL;
-    XEN_CALL_("VM.get_kernel_args");
-    return session->ok;
-}
-
-
-bool
-xen_vm_get_grub_cmdline(xen_session *session, char **result, xen_vm vm)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm }
-        };
-
-    abstract_type result_type = abstract_type_string;
-
-    *result = NULL;
-    XEN_CALL_("VM.get_grub_cmdline");
     return session->ok;
 }
 
@@ -1357,7 +1336,87 @@ xen_vm_set_actions_after_crash(xen_sessi
 
 
 bool
-xen_vm_set_bios_boot(xen_session *session, xen_vm vm, char *boot)
+xen_vm_set_pv_bootloader(xen_session *session, xen_vm vm, char *bootloader)
+{
+    abstract_value param_values[] =
+        {
+            { .type = &abstract_type_string,
+              .u.string_val = vm },
+            { .type = &abstract_type_string,
+              .u.string_val = bootloader }
+        };
+
+    xen_call_(session, "VM.set_PV_bootloader", param_values, 2, NULL, NULL);
+    return session->ok;
+}
+
+
+bool
+xen_vm_set_pv_kernel(xen_session *session, xen_vm vm, char *kernel)
+{
+    abstract_value param_values[] =
+        {
+            { .type = &abstract_type_string,
+              .u.string_val = vm },
+            { .type = &abstract_type_string,
+              .u.string_val = kernel }
+        };
+
+    xen_call_(session, "VM.set_PV_kernel", param_values, 2, NULL, NULL);
+    return session->ok;
+}
+
+
+bool
+xen_vm_set_pv_ramdisk(xen_session *session, xen_vm vm, char *ramdisk)
+{
+    abstract_value param_values[] =
+        {
+            { .type = &abstract_type_string,
+              .u.string_val = vm },
+            { .type = &abstract_type_string,
+              .u.string_val = ramdisk }
+        };
+
+    xen_call_(session, "VM.set_PV_ramdisk", param_values, 2, NULL, NULL);
+    return session->ok;
+}
+
+
+bool
+xen_vm_set_pv_args(xen_session *session, xen_vm vm, char *args)
+{
+    abstract_value param_values[] =
+        {
+            { .type = &abstract_type_string,
+              .u.string_val = vm },
+            { .type = &abstract_type_string,
+              .u.string_val = args }
+        };
+
+    xen_call_(session, "VM.set_PV_args", param_values, 2, NULL, NULL);
+    return session->ok;
+}
+
+
+bool
+xen_vm_set_pv_bootloader_args(xen_session *session, xen_vm vm, char 
*bootloader_args)
+{
+    abstract_value param_values[] =
+        {
+            { .type = &abstract_type_string,
+              .u.string_val = vm },
+            { .type = &abstract_type_string,
+              .u.string_val = bootloader_args }
+        };
+
+    xen_call_(session, "VM.set_PV_bootloader_args", param_values, 2, NULL, 
NULL);
+    return session->ok;
+}
+
+
+bool
+xen_vm_set_hvm_boot(xen_session *session, xen_vm vm, char *boot)
 {
     abstract_value param_values[] =
         {
@@ -1367,7 +1426,7 @@ xen_vm_set_bios_boot(xen_session *sessio
               .u.string_val = boot }
         };
 
-    xen_call_(session, "VM.set_bios_boot", param_values, 2, NULL, NULL);
+    xen_call_(session, "VM.set_HVM_boot", param_values, 2, NULL, NULL);
     return session->ok;
 }
 
@@ -1453,102 +1512,6 @@ xen_vm_set_platform_enable_audio(xen_ses
 
 
 bool
-xen_vm_set_builder(xen_session *session, xen_vm vm, char *builder)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm },
-            { .type = &abstract_type_string,
-              .u.string_val = builder }
-        };
-
-    xen_call_(session, "VM.set_builder", param_values, 2, NULL, NULL);
-    return session->ok;
-}
-
-
-bool
-xen_vm_set_boot_method(xen_session *session, xen_vm vm, enum xen_boot_type 
boot_method)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm },
-            { .type = &xen_boot_type_abstract_type_,
-              .u.string_val = xen_boot_type_to_string(boot_method) }
-        };
-
-    xen_call_(session, "VM.set_boot_method", param_values, 2, NULL, NULL);
-    return session->ok;
-}
-
-
-bool
-xen_vm_set_kernel_kernel(xen_session *session, xen_vm vm, char *kernel)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm },
-            { .type = &abstract_type_string,
-              .u.string_val = kernel }
-        };
-
-    xen_call_(session, "VM.set_kernel_kernel", param_values, 2, NULL, NULL);
-    return session->ok;
-}
-
-
-bool
-xen_vm_set_kernel_initrd(xen_session *session, xen_vm vm, char *initrd)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm },
-            { .type = &abstract_type_string,
-              .u.string_val = initrd }
-        };
-
-    xen_call_(session, "VM.set_kernel_initrd", param_values, 2, NULL, NULL);
-    return session->ok;
-}
-
-
-bool
-xen_vm_set_kernel_args(xen_session *session, xen_vm vm, char *args)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm },
-            { .type = &abstract_type_string,
-              .u.string_val = args }
-        };
-
-    xen_call_(session, "VM.set_kernel_args", param_values, 2, NULL, NULL);
-    return session->ok;
-}
-
-
-bool
-xen_vm_set_grub_cmdline(xen_session *session, xen_vm vm, char *cmdline)
-{
-    abstract_value param_values[] =
-        {
-            { .type = &abstract_type_string,
-              .u.string_val = vm },
-            { .type = &abstract_type_string,
-              .u.string_val = cmdline }
-        };
-
-    xen_call_(session, "VM.set_grub_cmdline", param_values, 2, NULL, NULL);
-    return session->ok;
-}
-
-
-bool
 xen_vm_set_otherconfig(xen_session *session, xen_vm vm, xen_string_string_map 
*otherconfig)
 {
     abstract_value param_values[] =
diff -r da0849b74170 -r 0ee4e33b4401 tools/python/xen/xend/XendAPI.py
--- a/tools/python/xen/xend/XendAPI.py  Thu Dec 14 17:43:41 2006 +0000
+++ b/tools/python/xen/xend/XendAPI.py  Thu Dec 14 18:24:14 2006 +0000
@@ -118,11 +118,16 @@ def valid_vm(func):
     @param func: function with params: (self, session, vm_ref)
     @rtype: callable object
     """    
-    def check_vm_ref(self, session, vm_ref, *args, **kwargs):
+    def check_vm_ref(self, session, *args, **kwargs):
+        if len(args) == 0:
+            return {'Status': 'Failure',
+                    'ErrorDescription': XEND_ERROR_VM_INVALID}
+
+        vm_ref = args[0]
         xendom = XendDomain.instance()
         if type(vm_ref) == type(str()) and \
                xendom.is_valid_vm(vm_ref):
-            return func(self, session, vm_ref, *args, **kwargs)
+            return func(self, session, *args, **kwargs)
         else:
             return {'Status': 'Failure',
                     'ErrorDescription': XEND_ERROR_VM_INVALID}
@@ -590,19 +595,18 @@ class XendAPI:
                   'actions_after_reboot',
                   'actions_after_suspend',
                   'actions_after_crash',
-                  'bios_boot',
+                  'PV_bootloader',
+                  'PV_kernel',
+                  'PV_ramdisk',
+                  'PV_args',
+                  'PV_bootloader_args',
+                  'HVM_boot',
                   'platform_std_VGA',
                   'platform_serial',
                   'platform_localtime',
                   'platform_clock_offset',
                   'platform_enable_audio',
                   'platform_keymap',
-                  'builder',
-                  'boot_method',
-                  'kernel_kernel',
-                  'kernel_initrd',
-                  'kernel_args',
-                  'grub_cmdline',
                   'otherConfig']
 
     VM_methods = ['clone',
@@ -638,22 +642,30 @@ class XendAPI:
         'actions_after_reboot',
         'actions_after_suspend',
         'actions_after_crash',
-        'bios_boot',
+        'PV_bootloader',
+        'PV_kernel',
+        'PV_ramdisk',
+        'PV_args',
+        'PV_bootloader_args',
+        'HVM_boot',
         'platform_std_VGA',
         'platform_serial',
         'platform_localtime',
         'platform_clock_offset',
         'platform_enable_audio',
         'platform_keymap',
-        'builder',
-        'boot_method',
-        'kernel_kernel',
-        'kernel_initrd',
-        'kernel_args',
         'grub_cmdline',
         'PCI_bus',
         'otherConfig']
         
+    def VM_get(self, name, session, vm_ref):
+        return xen_api_success(
+            XendDomain.instance().get_vm_by_uuid(vm_ref).info[name])
+
+    def VM_set(self, name, session, vm_ref, value):
+        XendDomain.instance().get_vm_by_uuid(vm_ref).info[name] = value
+        return xen_api_success_void()
+
     # attributes (ro)
     def VM_get_power_state(self, session, vm_ref):
         dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
@@ -767,9 +779,23 @@ class XendAPI:
         dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
         return xen_api_success(dom.get_on_crash())
     
-    def VM_get_bios_boot(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success(dom.get_bios_boot())
+    def VM_get_PV_bootloader(self, session, vm_ref):
+        return self.VM_get('PV_bootloader', session, vm_ref)
+    
+    def VM_get_PV_kernel(self, session, vm_ref):
+        return self.VM_get('PV_kernel', session, vm_ref)
+    
+    def VM_get_PV_ramdisk(self, session, vm_ref):
+        return self.VM_get('PV_ramdisk', session, vm_ref)
+    
+    def VM_get_PV_args(self, session, vm_ref):
+        return self.VM_get('PV_args', session, vm_ref)
+
+    def VM_get_PV_bootloader_args(self, session, vm_ref):
+        return self.VM_get('PV_bootloader_args', session, vm_ref)
+
+    def VM_get_HVM_boot(self, session, vm_ref):
+        return self.VM_get('HVM_boot', session, vm_ref)
     
     def VM_get_platform_std_VGA(self, session, vm_ref):
         dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
@@ -795,34 +821,10 @@ class XendAPI:
         dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
         return xen_api_todo()
     
-    def VM_get_builder(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success(dom.get_builder())
-    
-    def VM_get_boot_method(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success(dom.get_boot_method())
-    
-    def VM_get_kernel_kernel(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success('')
-    
-    def VM_get_kernel_initrd(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success('')
-    
-    def VM_get_kernel_args(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success('')
-    
-    def VM_get_grub_cmdline(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success('')
-    
     def VM_get_otherConfig(self, session, vm_ref):
         dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
         return xen_api_todo()
-    
+
     def VM_set_name_label(self, session, vm_ref, label):
         dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
         dom.setName(label)
@@ -879,11 +881,25 @@ class XendAPI:
     def VM_set_actions_after_crash(self, session, vm_ref):
         dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
         return xen_api_success_void()
-    
-    def VM_set_bios_boot(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success_void()
-    
+
+    def VM_set_HVM_boot(self, session, vm_ref, value):
+        return self.VM_set('HVM_boot', session, vm_ref, value)
+
+    def VM_set_PV_bootloader(self, session, vm_ref, value):
+        return self.VM_set('PV_bootloader', session, vm_ref, value)
+
+    def VM_set_PV_kernel(self, session, vm_ref, value):
+        return self.VM_set('PV_kernel', session, vm_ref, value)
+
+    def VM_set_PV_ramdisk(self, session, vm_ref, value):
+        return self.VM_set('PV_ramdisk', session, vm_ref, value)
+
+    def VM_set_PV_args(self, session, vm_ref, value):
+        return self.VM_set('PV_args', session, vm_ref, value)
+
+    def VM_set_PV_bootloader_args(self, session, vm_ref, value):
+        return self.VM_set('PV_bootloader_args', session, vm_ref, value)
+
     def VM_set_platform_std_VGA(self, session, vm_ref):
         dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
         return xen_api_success_void()
@@ -901,30 +917,6 @@ class XendAPI:
         return xen_api_success_void()
     
     def VM_set_platform_enable_audio(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success_void()
-    
-    def VM_set_builder(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success_void()
-    
-    def VM_set_boot_method(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success_void()
-    
-    def VM_set_kernel_kernel(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success_void()
-    
-    def VM_set_kernel_initrd(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success_void()
-    
-    def VM_set_kernel_args(self, session, vm_ref):
-        dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
-        return xen_api_success_void()
-    
-    def VM_set_grub_cmdline(self, session, vm_ref):
         dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
         return xen_api_success_void()
     
@@ -986,19 +978,18 @@ class XendAPI:
             'VIFs': xeninfo.get_vifs(),
             'VBDs': xeninfo.get_vbds(),
             'VTPMs': xeninfo.get_vtpms(),
-            'bios_boot': xeninfo.get_bios_boot(),
+            'PV_bootloader': xeninfo.info.get('PV_bootloader'),
+            'PV_kernel': xeninfo.info.get('PV_kernel'),
+            'PV_ramdisk': xeninfo.info.get('PV_ramdisk'),
+            'PV_args': xeninfo.info.get('PV_args'),
+            'PV_bootloader_args': xeninfo.info.get('PV_bootloader_args'),
+            'HVM_boot': xeninfo.info.get('HVM_boot'),
             'platform_std_VGA': xeninfo.get_platform_std_vga(),
             'platform_serial': xeninfo.get_platform_serial(),
             'platform_localtime': xeninfo.get_platform_localtime(),
             'platform_clock_offset': xeninfo.get_platform_clock_offset(),
             'platform_enable_audio': xeninfo.get_platform_enable_audio(),
             'platform_keymap': xeninfo.get_platform_keymap(),
-            'builder': xeninfo.get_builder(),
-            'boot_method': xeninfo.get_boot_method(),
-            'kernel_kernel': xeninfo.get_kernel_image(),
-            'kernel_initrd': xeninfo.get_kernel_initrd(),
-            'kernel_args': xeninfo.get_kernel_args(),
-            'grub_cmdline': xeninfo.get_grub_cmdline(),
             'PCI_bus': xeninfo.get_pci_bus(),
             'tools_version': xeninfo.get_tools_version(),
             'otherConfig': xeninfo.get_other_config()
diff -r da0849b74170 -r 0ee4e33b4401 tools/python/xen/xend/XendBootloader.py
--- a/tools/python/xen/xend/XendBootloader.py   Thu Dec 14 17:43:41 2006 +0000
+++ b/tools/python/xen/xend/XendBootloader.py   Thu Dec 14 18:24:14 2006 +0000
@@ -21,7 +21,8 @@ from XendLogging import log
 from XendLogging import log
 from XendError import VmError
 
-def bootloader(blexec, disk, quiet = 0, blargs = None, imgcfg = None):
+def bootloader(blexec, disk, quiet = False, blargs = '', kernel = '',
+               ramdisk = '', kernel_args = ''):
     """Run the boot loader executable on the given disk and return a
     config image.
     @param blexec  Binary to use as the boot loader
@@ -55,18 +56,19 @@ def bootloader(blexec, disk, quiet = 0, 
         if quiet:
             args.append("-q")
         args.append("--output=%s" % fifo)
-        if blargs is not None:
+        if blargs:
             args.extend(shlex.split(blargs))
         args.append(disk)
 
         try:
+            log.debug("Launching bootloader as %s." % str(args))
             os.execvp(args[0], args)
         except OSError, e:
             print e
             pass
         os._exit(1)
 
-    while 1:
+    while True:
         try:
             r = os.open(fifo, os.O_RDONLY)
         except OSError, e:
@@ -74,7 +76,7 @@ def bootloader(blexec, disk, quiet = 0, 
                 continue
         break
     ret = ""
-    while 1:
+    while True:
         select.select([r], [], [])
         s = os.read(r, 1024)
         ret = ret + s
@@ -94,9 +96,4 @@ def bootloader(blexec, disk, quiet = 0, 
     pin.input(ret)
     pin.input_eof()
     blcfg = pin.val
-
-    if imgcfg is None:
-        return blcfg
-    else:
-        c = sxp.merge(blcfg, imgcfg)
-        return c
+    return blcfg
diff -r da0849b74170 -r 0ee4e33b4401 tools/python/xen/xend/XendConfig.py
--- a/tools/python/xen/xend/XendConfig.py       Thu Dec 14 17:43:41 2006 +0000
+++ b/tools/python/xen/xend/XendConfig.py       Thu Dec 14 18:24:14 2006 +0000
@@ -103,7 +103,7 @@ XENAPI_HVM_CFG = {
     'platform_keymap' : 'keymap',
 }    
 
-# List of XendConfig configuration keys that have no equivalent
+# List of XendConfig configuration keys that have no direct equivalent
 # in the old world.
 
 XENAPI_CFG_TYPES = {
@@ -132,19 +132,18 @@ XENAPI_CFG_TYPES = {
     'actions_after_crash': str,
     'tpm_instance': int,
     'tpm_backend': int,    
-    'bios_boot': str,
+    'PV_bootloader': str,
+    'PV_kernel': str,
+    'PV_initrd': str,
+    'PV_args': str,
+    'PV_bootloader_args': str,
+    'HVM_boot': str,
     'platform_std_vga': bool0,
     'platform_serial': str,
     'platform_localtime': bool0,
     'platform_clock_offset': bool0,
     'platform_enable_audio': bool0,
     'platform_keymap': str,
-    'boot_method': str,
-    'builder': str,
-    'kernel_kernel': str,
-    'kernel_initrd': str,
-    'kernel_args': str,
-    'grub_cmdline': str,
     'pci_bus': str,
     'tools_version': dict,
     'otherconfig': dict,
@@ -160,8 +159,6 @@ LEGACY_UNSUPPORTED_BY_XENAPI_CFG = [
     'vcpu_avail',
     'cpu_weight',
     'cpu_cap',
-    'bootloader',
-    'bootloader_args',
     'features',
     # read/write
     'on_xend_start',
@@ -188,8 +185,6 @@ LEGACY_CFG_TYPES = {
     'cpu_cap':         int,
     'cpu_weight':      int,
     'cpu_time':      float,
-    'bootloader':      str,
-    'bootloader_args': str,
     'features':        str,
     'localtime':       int,
     'name':        str,
@@ -331,16 +326,18 @@ class XendConfig(dict):
             'actions_after_crash': 'restart',
             'actions_after_suspend': '',
             'features': '',
-            'builder': 'linux',
+            'PV_bootloader': '',
+            'PV_kernel': '',
+            'PV_ramdisk': '',
+            'PV_args': '',
+            'PV_bootloader_args': '',
+            'HVM_boot': '',
             'memory_static_min': 0,
             'memory_dynamic_min': 0,
             'shadow_memory': 0,
             'memory_static_max': 0,
             'memory_dynamic_max': 0,
             'memory_actual': 0,
-            'boot_method': None,
-            'bootloader': None,
-            'bootloader_args': None,
             'devices': {},
             'image': {},
             'security': None,
@@ -383,10 +380,6 @@ class XendConfig(dict):
                 raise XendConfigError('Invalid event handling mode: ' +
                                       event)
 
-    def _builder_sanity_check(self):
-        if self['builder'] not in ('hvm', 'linux'):
-            raise XendConfigError('Invalid builder configuration')
-
     def _vcpus_sanity_check(self):
         if self.get('vcpus_number') != None:
             self['vcpu_avail'] = (1 << self['vcpus_number']) - 1
@@ -398,7 +391,6 @@ class XendConfig(dict):
     def validate(self):
         self._memory_sanity_check()
         self._actions_sanity_check()
-        self._builder_sanity_check()
         self._vcpus_sanity_check()
         self._uuid_sanity_check()
 
@@ -598,38 +590,18 @@ class XendConfig(dict):
             except KeyError:
                 pass
 
-        # Convert Legacy "image" config to Xen API kernel_*
-        # configuration
+        self['PV_bootloader']      = cfg.get('bootloader',      '')
+        self['PV_bootloader_args'] = cfg.get('bootloader_args', '')
+        
         image_sxp = sxp.child_value(sxp_cfg, 'image', [])
         if image_sxp:
-            self['kernel_kernel'] = sxp.child_value(image_sxp, 'kernel','')
-            self['kernel_initrd'] = sxp.child_value(image_sxp, 'ramdisk','')
-            kernel_args = sxp.child_value(image_sxp, 'args', '')
-
-            # attempt to extract extra arguments from SXP config
-            arg_ip = sxp.child_value(image_sxp, 'ip')
-            if arg_ip and not re.search(r'ip=[^ ]+', kernel_args):
-                kernel_args += ' ip=%s' % arg_ip
-            arg_root = sxp.child_value(image_sxp, 'root')
-            if arg_root and not re.search(r'root=[^ ]+', kernel_args):
-                kernel_args += ' root=%s' % arg_root
-            
-            self['kernel_args'] = kernel_args
+            self.update_with_image_sxp(image_sxp)
 
         # Convert Legacy HVM parameters to Xen API configuration
         self['platform_std_vga'] = bool0(cfg.get('stdvga', 0))
         self['platform_serial'] = str(cfg.get('serial', ''))
         self['platform_localtime'] = bool0(cfg.get('localtime', 0))
         self['platform_enable_audio'] = bool0(cfg.get('soundhw', 0))
-
-        # Convert path to bootloader to boot_method
-        if not cfg.get('bootloader'):
-            if self.get('kernel_kernel','').endswith('hvmloader'):
-                self['boot_method'] = 'bios'
-            else:
-                self['boot_method'] = 'kernel_external'
-        else:
-            self['boot_method'] = 'grub'
 
         # make sure a sane maximum is set
         if self['memory_static_max'] <= 0:
@@ -705,9 +677,6 @@ class XendConfig(dict):
         if backend:
             self['backend'] = backend
 
-        if self['image'].has_key('hvm'):
-            self['builder'] = 'hvm'
-            
         # Parse and convert other Non Xen API parameters.
         def _set_cfg_if_exists(sxp_arg):
             val = sxp.child_value(sxp_cfg, sxp_arg)
@@ -717,7 +686,6 @@ class XendConfig(dict):
                 else:
                     self[sxp_arg] = val
 
-        _set_cfg_if_exists('bootloader')
         _set_cfg_if_exists('shadow_memory')
         _set_cfg_if_exists('security')
         _set_cfg_if_exists('features')
@@ -741,8 +709,9 @@ class XendConfig(dict):
         """
 
         # populate image
-        self['image']['type'] = self['builder']
-        if self['builder'] == 'hvm':
+        hvm = self['HVM_boot'] != ''
+        self['image']['type'] = hvm and 'hvm' or 'linux'
+        if hvm:
             self['image']['hvm'] = {}
             for xapi, cfgapi in XENAPI_HVM_CFG.items():
                 self['image']['hvm'][cfgapi] = self[xapi]
@@ -780,8 +749,10 @@ class XendConfig(dict):
         @type xapi: dict
         """
         for key, val in xapi.items():
-            key = key.lower()
             type_conv = XENAPI_CFG_TYPES.get(key)
+            if type_conv is None:
+                key = key.lower()
+                type_conv = XENAPI_CFG_TYPES.get(key)
             if callable(type_conv):
                 self[key] = type_conv(val)
             else:
@@ -1100,8 +1071,8 @@ class XendConfig(dict):
     def update_with_image_sxp(self, image_sxp):
         # Convert Legacy "image" config to Xen API kernel_*
         # configuration
-        self['kernel_kernel'] = sxp.child_value(image_sxp, 'kernel','')
-        self['kernel_initrd'] = sxp.child_value(image_sxp, 'ramdisk','')
+        self['PV_kernel'] = sxp.child_value(image_sxp, 'kernel','')
+        self['PV_ramdisk'] = sxp.child_value(image_sxp, 'ramdisk','')
         kernel_args = sxp.child_value(image_sxp, 'args', '')
         
         # attempt to extract extra arguments from SXP config
@@ -1111,7 +1082,7 @@ class XendConfig(dict):
         arg_root = sxp.child_value(image_sxp, 'root')
         if arg_root and not re.search(r'root=', kernel_args):
             kernel_args += ' root=%s' % arg_root
-        self['kernel_args'] = kernel_args
+        self['PV_args'] = kernel_args
 
         # Store image SXP in python dictionary format
         image = {}
diff -r da0849b74170 -r 0ee4e33b4401 tools/python/xen/xend/XendDomainInfo.py
--- a/tools/python/xen/xend/XendDomainInfo.py   Thu Dec 14 17:43:41 2006 +0000
+++ b/tools/python/xen/xend/XendDomainInfo.py   Thu Dec 14 18:24:14 2006 +0000
@@ -51,6 +51,7 @@ from xen.xend.XendAPIConstants import *
 from xen.xend.XendAPIConstants import *
 
 MIGRATE_TIMEOUT = 30.0
+BOOTLOADER_LOOPBACK_DEVICE = '/dev/xvdp'
 
 xc = xen.lowlevel.xc.xc()
 xroot = XendRoot.instance()
@@ -438,6 +439,7 @@ class XendDomainInfo:
             xc.domain_pause(self.domid)
             self._stateSet(DOM_STATE_PAUSED)
         except Exception, ex:
+            log.exception(ex)
             raise XendError("Domain unable to be paused: %s" % str(ex))
 
     def unpause(self):
@@ -449,6 +451,7 @@ class XendDomainInfo:
             xc.domain_unpause(self.domid)
             self._stateSet(DOM_STATE_RUNNING)
         except Exception, ex:
+            log.exception(ex)
             raise XendError("Domain unable to be unpaused: %s" % str(ex))
 
     def send_sysrq(self, key):
@@ -467,7 +470,8 @@ class XendDomainInfo:
         dev_uuid = self.info.device_add(dev_type, cfg_sxp = dev_config)
         dev_config_dict = self.info['devices'][dev_uuid][1]
         log.debug("XendDomainInfo.device_create: %s" % 
scrub_password(dev_config_dict))
-        devid = self._createDevice(dev_type, dev_config_dict)
+        dev_config_dict['devid'] = devid = \
+             self._createDevice(dev_type, dev_config_dict)
         self._waitForDevice(dev_type, devid)
         return self.getDeviceController(dev_type).sxpr(devid)
 
@@ -504,7 +508,7 @@ class XendDomainInfo:
         for devclass in XendDevices.valid_devices():
             self.getDeviceController(devclass).waitForDevices()
 
-    def destroyDevice(self, deviceClass, devid, force=None):
+    def destroyDevice(self, deviceClass, devid, force = False):
         try:
             devid = int(devid)
         except ValueError:
@@ -972,7 +976,8 @@ class XendDomainInfo:
             self.refresh_shutdown_lock.release()
 
         if restart_reason:
-            self._maybeRestart(restart_reason)
+            threading.Thread(target = self._maybeRestart,
+                             args = (restart_reason,)).start()
 
 
     #
@@ -1015,7 +1020,6 @@ class XendDomainInfo:
         """
         from xen.xend import XendDomain
         
-        self._configureBootloader()
         config = self.sxpr()
 
         if self._infoIsSet('cpus') and len(self.info['cpus']) != 0:
@@ -1141,6 +1145,10 @@ class XendDomainInfo:
     def _waitForDevice(self, deviceClass, devid):
         return self.getDeviceController(deviceClass).waitForDevice(devid)
 
+    def _waitForDeviceUUID(self, dev_uuid):
+        deviceClass, config = self.info['devices'].get(dev_uuid)
+        self._waitForDevice(deviceClass, config['devid'])
+
     def _reconfigureDevice(self, deviceClass, devid, devconfig):
         return self.getDeviceController(deviceClass).reconfigureDevice(
             devid, devconfig)
@@ -1244,6 +1252,8 @@ class XendDomainInfo:
 
         log.debug('XendDomainInfo.constructDomain')
 
+        self.shutdownStartTime = None
+
         image_cfg = self.info.get('image', {})
         hvm = image_cfg.has_key('hvm')
 
@@ -1288,10 +1298,7 @@ class XendDomainInfo:
                   self.domid,
                   self.info['cpu_weight'])
 
-        # if we have a boot loader but no image, then we need to set things
-        # up by running the boot loader non-interactively
-        if self.info.get('bootloader'):
-            self._configureBootloader()
+        self._configureBootloader()
 
         if not self._infoIsSet('image'):
             raise VmError('Missing image in configuration')
@@ -1352,17 +1359,14 @@ class XendDomainInfo:
 
             self._createDevices()
 
-            if self.info['bootloader']:
-                self.image.cleanupBootloading()
+            self.image.cleanupBootloading()
 
             self.info['start_time'] = time.time()
 
             self._stateSet(DOM_STATE_RUNNING)
         except RuntimeError, exn:
             log.exception("XendDomainInfo.initDomain: exception occurred")
-            if self.info['bootloader'] not in (None, 'kernel_external') \
-                   and self.image is not None:
-                self.image.cleanupBootloading()
+            self.image.cleanupBootloading()
             raise VmError(str(exn))
 
 
@@ -1493,33 +1497,78 @@ class XendDomainInfo:
 
     def _configureBootloader(self):
         """Run the bootloader if we're configured to do so."""
-        if not self.info.get('bootloader'):
-            return
-        blcfg = None
-
-        # FIXME: this assumes that we want to use the first disk device
-        for (devtype, devinfo) in self.info.all_devices_sxpr():
-            if not devtype or not devinfo or devtype not in ('vbd', 'tap'):
-                continue
-            disk = None
-            for param in devinfo:
-                if param[0] == 'uname':
-                    disk = param[1]
-                    break
-
-            if disk is None:
-                continue
-            fn = blkdev_uname_to_file(disk)
-            blcfg = bootloader(self.info['bootloader'], fn, 1,
-                               self.info['bootloader_args'],
-                               self.info['image'])
-            break
-        if blcfg is None:
-            msg = "Had a bootloader specified, but can't find disk"
-            log.error(msg)
-            raise VmError(msg)
-        
-        self.info.update_with_image_sxp(blcfg)
+
+        blexec          = self.info['PV_bootloader']
+        bootloader_args = self.info['PV_bootloader_args']
+        kernel          = self.info['PV_kernel']
+        ramdisk         = self.info['PV_ramdisk']
+        args            = self.info['PV_args']
+        boot            = self.info['HVM_boot']
+
+        if boot:
+            # HVM booting.
+            self.info['image']['type'] = 'hvm'
+            self.info['image']['devices']['boot'] = boot
+        elif not blexec and kernel:
+            # Boot from dom0.  Nothing left to do -- the kernel and ramdisk
+            # will be picked up by image.py.
+            pass
+        else:
+            # Boot using bootloader
+            if not blexec or blexec == 'pygrub':
+                blexec = '/usr/bin/pygrub'
+
+            blcfg = None
+            for (devtype, devinfo) in self.info.all_devices_sxpr():
+                if not devtype or not devinfo or devtype not in ('vbd', 'tap'):
+                    continue
+                disk = None
+                for param in devinfo:
+                    if param[0] == 'uname':
+                        disk = param[1]
+                        break
+
+                if disk is None:
+                    continue
+                fn = blkdev_uname_to_file(disk)
+                mounted = devtype == 'tap' and not os.stat(fn).st_rdev
+                if mounted:
+                    # This is a file, not a device.  pygrub can cope with a
+                    # file if it's raw, but if it's QCOW or other such formats
+                    # used through blktap, then we need to mount it first.
+
+                    log.info("Mounting %s on %s." %
+                             (fn, BOOTLOADER_LOOPBACK_DEVICE))
+
+                    vbd = {
+                        'mode': 'RO',
+                        'device': BOOTLOADER_LOOPBACK_DEVICE,
+                        }
+
+                    from xen.xend import XendDomain
+                    dom0 = XendDomain.instance().privilegedDomain()
+                    dom0._waitForDeviceUUID(dom0.create_vbd_with_vdi(vbd, fn))
+                    fn = BOOTLOADER_LOOPBACK_DEVICE
+
+                try:
+                    blcfg = bootloader(blexec, fn, True,
+                                       bootloader_args, kernel, ramdisk, args)
+                finally:
+                    if mounted:
+                        log.info("Unmounting %s from %s." %
+                                 (fn, BOOTLOADER_LOOPBACK_DEVICE))
+
+                        dom0.destroyDevice('tap', '/dev/xvdp')
+
+                break
+
+            if blcfg is None:
+                msg = "Had a bootloader specified, but can't find disk"
+                log.error(msg)
+                raise VmError(msg)
+        
+            self.info.update_with_image_sxp(blcfg)
+
 
     # 
     # VM Functions
@@ -1764,8 +1813,6 @@ class XendDomainInfo:
         return '' # TODO
     def get_power_state(self):
         return XEN_API_VM_POWER_STATE[self.state]
-    def get_bios_boot(self):
-        return '' # TODO
     def get_platform_std_vga(self):
         return self.info.get('platform_std_vga', False)    
     def get_platform_keymap(self):
@@ -1780,18 +1827,6 @@ class XendDomainInfo:
         return self.info.get('platform_enable_audio', False)
     def get_platform_keymap(self):
         return self.info.get('platform_keymap', '')
-    def get_builder(self):
-        return self.info.get('builder', 0)
-    def get_boot_method(self):
-        return self.info.get('boot_method', XEN_API_BOOT_TYPE[2])
-    def get_kernel_image(self):
-        return self.info.get('kernel_kernel', '')
-    def get_kernel_initrd(self):
-        return self.info.get('kernel_initrd', '')
-    def get_kernel_args(self):
-        return self.info.get('kernel_args', '')
-    def get_grub_cmdline(self):
-        return '' # TODO
     def get_pci_bus(self):
         return '' # TODO
     def get_tools_version(self):
@@ -1950,10 +1985,9 @@ class XendDomainInfo:
         if not dev_uuid:
             raise XendError('Failed to create device')
         
-        if self.state in (XEN_API_VM_POWER_STATE_RUNNING,):
-            sxpr = self.info.device_sxpr(dev_uuid)
-            devid = self.getDeviceController('vbd').createDevice(sxpr)
-            raise XendError("Device creation failed")
+        if self.state == XEN_API_VM_POWER_STATE_RUNNING:
+            _, config = self.info['devices'][dev_uuid]
+            config['devid'] = 
self.getDeviceController('vbd').createDevice(config)
 
         return dev_uuid
 
@@ -1971,10 +2005,9 @@ class XendDomainInfo:
         if not dev_uuid:
             raise XendError('Failed to create device')
 
-        if self.state in (XEN_API_VM_POWER_STATE_RUNNING,):
-            sxpr = self.info.device_sxpr(dev_uuid)
-            devid = self.getDeviceController('tap').createDevice(sxpr)
-            raise XendError("Device creation failed")
+        if self.state == XEN_API_VM_POWER_STATE_RUNNING:
+            _, config = self.info['devices'][dev_uuid]
+            config['devid'] = 
self.getDeviceController('tap').createDevice(config)
 
         return dev_uuid
 
@@ -1989,10 +2022,9 @@ class XendDomainInfo:
         if not dev_uuid:
             raise XendError('Failed to create device')
         
-        if self.state in (XEN_API_VM_POWER_STATE_RUNNING,):
-            sxpr = self.info.device_sxpr(dev_uuid)
-            devid = self.getDeviceController('vif').createDevice(sxpr)
-            raise XendError("Device creation failed")
+        if self.state == XEN_API_VM_POWER_STATE_RUNNING:
+            _, config = self.info['devices'][dev_uuid]
+            config['devid'] = 
self.getDeviceController('vif').createDevice(config)
 
         return dev_uuid
 
diff -r da0849b74170 -r 0ee4e33b4401 tools/python/xen/xend/image.py
--- a/tools/python/xen/xend/image.py    Thu Dec 14 17:43:41 2006 +0000
+++ b/tools/python/xen/xend/image.py    Thu Dec 14 18:24:14 2006 +0000
@@ -68,6 +68,7 @@ class ImageHandler:
     def __init__(self, vm, vmConfig, imageConfig, deviceConfig):
         self.vm = vm
 
+        self.bootloader = None
         self.kernel = None
         self.ramdisk = None
         self.cmdline = None
@@ -76,9 +77,10 @@ class ImageHandler:
 
     def configure(self, vmConfig, imageConfig, _):
         """Config actions common to all unix-like domains."""
-        self.kernel = vmConfig['kernel_kernel']
-        self.cmdline = vmConfig['kernel_args']
-        self.ramdisk = vmConfig['kernel_initrd']
+        self.bootloader = vmConfig['PV_bootloader']
+        self.kernel = vmConfig['PV_kernel']
+        self.cmdline = vmConfig['PV_args']
+        self.ramdisk = vmConfig['PV_ramdisk']
         self.vm.storeVm(("image/ostype", self.ostype),
                         ("image/kernel", self.kernel),
                         ("image/cmdline", self.cmdline),
@@ -86,8 +88,9 @@ class ImageHandler:
 
 
     def cleanupBootloading(self):
-        self.unlink(self.kernel)
-        self.unlink(self.ramdisk)
+        if self.bootloader:
+            self.unlink(self.kernel)
+            self.unlink(self.ramdisk)
 
 
     def unlink(self, f):

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog

<Prev in Thread] Current Thread [Next in Thread>
  • [Xen-changelog] [xen-unstable] Implement new booting parameters for Xen-API, and backwards compatibility for, Xen patchbot-unstable <=