[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]

[Libguestfs] [PATCH 8/9] v2v: Pass target_buses to output object (RHBZ#1238053).



Pass the target_buses assignment to the output#create_metadata method.

Now output modes have a choice: they can either ignore the new
parameter and continue to use the flat list of targets.  This is
suitable for output modes that cannot model multiple buses (eg.
-o glance) or can model it but don't bother (currently -o rhev).

Or they can ignore the flat targets parameter and use the new
target_buses parameter, translating that into the appropriate list of
devices.  This is implemented in this commit for these modes:

 -o libvirt
 -o local
 -o qemu
---
 v2v/output_glance.ml   |  2 +-
 v2v/output_libvirt.ml  | 76 ++++++++++++++++++++++----------------------------
 v2v/output_libvirt.mli |  2 +-
 v2v/output_local.ml    |  4 +--
 v2v/output_null.ml     |  2 +-
 v2v/output_qemu.ml     | 61 +++++++++++++++++++++++++++++-----------
 v2v/output_rhev.ml     |  2 +-
 v2v/output_vdsm.ml     |  2 +-
 v2v/test-v2v-i-ova.xml |  2 +-
 v2v/types.ml           |  2 +-
 v2v/types.mli          |  2 +-
 v2v/v2v.ml             |  3 +-
 12 files changed, 91 insertions(+), 69 deletions(-)

diff --git a/v2v/output_glance.ml b/v2v/output_glance.ml
index ad9ec18..e775229 100644
--- a/v2v/output_glance.ml
+++ b/v2v/output_glance.ml
@@ -62,7 +62,7 @@ object
         { t with target_file = target_file }
     ) targets
 
-  method create_metadata source targets guestcaps inspect target_firmware =
+  method create_metadata source targets _ guestcaps inspect target_firmware =
     (* See #supported_firmware above. *)
     assert (target_firmware = TargetBIOS);
 
diff --git a/v2v/output_libvirt.ml b/v2v/output_libvirt.ml
index 7f02e45..cc18580 100644
--- a/v2v/output_libvirt.ml
+++ b/v2v/output_libvirt.ml
@@ -69,7 +69,7 @@ let target_features_of_capabilities_doc doc arch =
     !features
   )
 
-let create_libvirt_xml ?pool source targets guestcaps
+let create_libvirt_xml ?pool source target_buses guestcaps
                        target_features target_firmware =
   let memory_k = source.s_memory /^ 1024L in
 
@@ -124,16 +124,12 @@ let create_libvirt_xml ?pool source targets guestcaps
 
     (e "type" ["arch", guestcaps.gcaps_arch] [PCData "hvm"]) :: loader in
 
-  (* Disks. *)
+  (* Fixed and removable disks. *)
   let disks =
-    let block_prefix =
-      match guestcaps.gcaps_block_bus with
-      | Virtio_blk -> "vd" | IDE -> "hd" in
-    let block_bus =
-      match guestcaps.gcaps_block_bus with
-      | Virtio_blk -> "virtio" | IDE -> "ide" in
-    mapi (
-      fun i t ->
+    let make_disk bus_name drive_prefix i = function
+    | BusSlotEmpty -> Comment (sprintf "%s slot %d is empty" bus_name i)
+
+    | BusSlotTarget t ->
         e "disk" [
           "type", if pool = None then "file" else "volume";
           "device", "disk"
@@ -155,45 +151,41 @@ let create_libvirt_xml ?pool source targets guestcaps
             ] []
           );
           e "target" [
-            "dev", block_prefix ^ (drive_name i);
-            "bus", block_bus;
+            "dev", drive_prefix ^ drive_name i;
+            "bus", bus_name;
           ] [];
         ]
-    ) targets in
 
-  let removables =
-    (* CDs will be added as IDE devices if we're using virtio, else
-     * they will be added as the same as the disk bus.  The original
-     * s_removable_controller is ignored (same as old virt-v2v).
-     *)
-    let cdrom_bus, cdrom_block_prefix, cdrom_index =
-      match guestcaps.gcaps_block_bus with
-      | Virtio_blk | IDE -> "ide", "hd", ref 0
-      (* | bus -> bus, "sd", ref (List.length targets) *) in
-
-    (* Floppy disks always occupy their own virtual bus. *)
-    let fd_bus = "fdc" and fd_index = ref 0 in
-
-    List.map (
-      function
-      | { s_removable_type = CDROM } ->
-        let i = !cdrom_index in
-        incr cdrom_index;
-        let name = cdrom_block_prefix ^ drive_name i in
+    | BusSlotRemovable { s_removable_type = CDROM } ->
         e "disk" [ "device", "cdrom"; "type", "file" ] [
           e "driver" [ "name", "qemu"; "type", "raw" ] [];
-          e "target" [ "dev", name; "bus", cdrom_bus ] []
+          e "target" [
+            "dev", drive_prefix ^ drive_name i;
+            "bus", bus_name
+          ] []
         ]
 
-      | { s_removable_type = Floppy } ->
-        let i = !fd_index in
-        incr fd_index;
-        let name = "fd" ^ drive_name i in
+    | BusSlotRemovable { s_removable_type = Floppy } ->
         e "disk" [ "device", "floppy"; "type", "file" ] [
           e "driver" [ "name", "qemu"; "type", "raw" ] [];
-          e "target" [ "dev", name; "bus", fd_bus ] []
+          e "target" [
+            "dev", drive_prefix ^ drive_name i;
+            "bus", bus_name
+          ] []
         ]
-    ) source.s_removables in
+    in
+
+    List.flatten [
+      Array.to_list
+        (Array.mapi (make_disk "virtio" "vd")
+                    target_buses.target_virtio_blk_bus);
+      Array.to_list
+        (Array.mapi (make_disk "ide" "hd")
+                    target_buses.target_ide_bus);
+      Array.to_list
+        (Array.mapi (make_disk "scsi" "sd")
+                    target_buses.target_scsi_bus)
+    ] in
 
   let nics =
     let net_model =
@@ -278,7 +270,7 @@ let create_libvirt_xml ?pool source targets guestcaps
        else
          [] in
 
-  let devices = disks @ removables @ nics @ [video] @ [graphics] @ sound @
+  let devices = disks @ nics @ [video] @ [graphics] @ sound @
   (* Standard devices added to every guest. *) [
     e "input" ["type", "tablet"; "bus", "usb"] [];
     e "input" ["type", "mouse"; "bus", "ps2"] [];
@@ -376,7 +368,7 @@ class output_libvirt oc output_pool = object
         { t with target_file = target_file }
     ) targets
 
-  method create_metadata source targets guestcaps _ target_firmware =
+  method create_metadata source _ target_buses guestcaps _ target_firmware =
     (* We copied directly into the final pool directory.  However we
      * have to tell libvirt.
      *)
@@ -400,7 +392,7 @@ class output_libvirt oc output_pool = object
 
     (* Create the metadata. *)
     let doc =
-      create_libvirt_xml ~pool:output_pool source targets
+      create_libvirt_xml ~pool:output_pool source target_buses
         guestcaps target_features target_firmware in
 
     let tmpfile, chan = Filename.open_temp_file "v2vlibvirt" ".xml" in
diff --git a/v2v/output_libvirt.mli b/v2v/output_libvirt.mli
index 9f2c20b..471a2e8 100644
--- a/v2v/output_libvirt.mli
+++ b/v2v/output_libvirt.mli
@@ -23,5 +23,5 @@ val output_libvirt : string option -> string -> Types.output
     {!Types.output} object specialized for writing output to
     libvirt. *)
 
-val create_libvirt_xml : ?pool:string -> Types.source -> Types.target list -> Types.guestcaps -> string list -> Types.target_firmware -> DOM.doc
+val create_libvirt_xml : ?pool:string -> Types.source -> Types.target_buses -> Types.guestcaps -> string list -> Types.target_firmware -> DOM.doc
 (** This is called from {!Output_local} to generate the libvirt XML. *)
diff --git a/v2v/output_local.ml b/v2v/output_local.ml
index 0e82a3a..c8db359 100644
--- a/v2v/output_local.ml
+++ b/v2v/output_local.ml
@@ -38,7 +38,7 @@ class output_local dir = object
         { t with target_file = target_file }
     ) targets
 
-  method create_metadata source targets guestcaps _ target_firmware =
+  method create_metadata source _ target_buses guestcaps _ target_firmware =
     (* We don't know what target features the hypervisor supports, but
      * assume a common set that libvirt supports.
      *)
@@ -49,7 +49,7 @@ class output_local dir = object
       | _ -> [] in
 
     let doc =
-      Output_libvirt.create_libvirt_xml source targets
+      Output_libvirt.create_libvirt_xml source target_buses
         guestcaps target_features target_firmware in
 
     let name = source.s_name in
diff --git a/v2v/output_null.ml b/v2v/output_null.ml
index 5cc89a2..2cada46 100644
--- a/v2v/output_null.ml
+++ b/v2v/output_null.ml
@@ -48,7 +48,7 @@ object
         { t with target_file = target_file }
     ) targets
 
-  method create_metadata _ _ _ _ _ = ()
+  method create_metadata _ _ _ _ _ _ = ()
 end
 
 let output_null () = new output_null
diff --git a/v2v/output_qemu.ml b/v2v/output_qemu.ml
index 81d819e..3b782ba 100644
--- a/v2v/output_qemu.ml
+++ b/v2v/output_qemu.ml
@@ -40,7 +40,8 @@ object
         { t with target_file = target_file }
     ) targets
 
-  method create_metadata source targets guestcaps inspect target_firmware =
+  method create_metadata source _ target_buses guestcaps inspect
+                         target_firmware =
     let name = source.s_name in
     let file = dir // name ^ ".sh" in
 
@@ -82,22 +83,50 @@ object
     if source.s_vcpu > 1 then
       fpf "%s-smp %d" nl source.s_vcpu;
 
-    let block_bus =
-      match guestcaps.gcaps_block_bus with
-      | Virtio_blk -> "virtio"
-      | IDE -> "ide" in
-    List.iter (
-      fun t ->
-        let qemu_quoted_filename = replace_str t.target_file "," ",," in
-        let drive_param =
-          sprintf "file=%s,format=%s,if=%s"
-            qemu_quoted_filename t.target_format block_bus in
-        fpf "%s-drive %s" nl (quote drive_param)
-    ) targets;
+    let make_disk if_name i = function
+    | BusSlotEmpty -> ()
 
-    (* XXX Missing:
-     * - removable devices
-     *)
+    | BusSlotTarget t ->
+       let qemu_quoted_filename = replace_str t.target_file "," ",," in
+       let drive_param =
+          sprintf "file=%s,format=%s,if=%s,index=%d,media=disk"
+                  qemu_quoted_filename t.target_format if_name i in
+       fpf "%s-drive %s" nl (quote drive_param)
+
+    | BusSlotRemovable { s_removable_type = CDROM } ->
+       let drive_param =
+          sprintf "format=raw,if=%s,index=%d,media=cdrom" if_name i in
+       fpf "%s-drive %s" nl (quote drive_param)
+
+    | BusSlotRemovable { s_removable_type = Floppy } ->
+       let drive_param =
+          sprintf "format=raw,if=%s,index=%d,media=floppy" if_name i in
+       fpf "%s-drive %s" nl (quote drive_param)
+    in
+    Array.iteri (make_disk "virtio") target_buses.target_virtio_blk_bus;
+    Array.iteri (make_disk "ide") target_buses.target_ide_bus;
+
+    let make_scsi i = function
+    | BusSlotEmpty -> ()
+
+    | BusSlotTarget t ->
+       let qemu_quoted_filename = replace_str t.target_file "," ",," in
+       let drive_param =
+          sprintf "file=%s,format=%s,if=scsi,bus=0,unit=%d,media=disk"
+                  qemu_quoted_filename t.target_format i in
+       fpf "%s-drive %s" nl (quote drive_param)
+
+    | BusSlotRemovable { s_removable_type = CDROM } ->
+       let drive_param =
+          sprintf "format=raw,if=scsi,bus=0,unit=%d,media=cdrom" i in
+       fpf "%s-drive %s" nl (quote drive_param)
+
+    | BusSlotRemovable { s_removable_type = Floppy } ->
+       let drive_param =
+          sprintf "format=raw,if=scsi,bus=0,unit=%d,media=floppy" i in
+       fpf "%s-drive %s" nl (quote drive_param)
+    in
+    Array.iteri make_scsi target_buses.target_scsi_bus;
 
     let net_bus =
       match guestcaps.gcaps_net_bus with
diff --git a/v2v/output_rhev.ml b/v2v/output_rhev.ml
index 365c35e..d3f367e 100644
--- a/v2v/output_rhev.ml
+++ b/v2v/output_rhev.ml
@@ -278,7 +278,7 @@ object
     )
 
   (* This is called after conversion to write the OVF metadata. *)
-  method create_metadata source targets guestcaps inspect target_firmware =
+  method create_metadata source targets _ guestcaps inspect target_firmware =
     (* See #supported_firmware above. *)
     assert (target_firmware = TargetBIOS);
 
diff --git a/v2v/output_vdsm.ml b/v2v/output_vdsm.ml
index 44f0041..670d8ba 100644
--- a/v2v/output_vdsm.ml
+++ b/v2v/output_vdsm.ml
@@ -165,7 +165,7 @@ object
       ?clustersize path format size
 
   (* This is called after conversion to write the OVF metadata. *)
-  method create_metadata source targets guestcaps inspect target_firmware =
+  method create_metadata source targets _ guestcaps inspect target_firmware =
     (* See #supported_firmware above. *)
     assert (target_firmware = TargetBIOS);
 
diff --git a/v2v/test-v2v-i-ova.xml b/v2v/test-v2v-i-ova.xml
index 994727b..2eeff83 100644
--- a/v2v/test-v2v-i-ova.xml
+++ b/v2v/test-v2v-i-ova.xml
@@ -27,7 +27,7 @@
     </disk>
     <disk device='floppy' type='file'>
       <driver name='qemu' type='raw'/>
-      <target dev='fda' bus='fdc'/>
+      <target dev='hdb' bus='ide'/>
     </disk>
     <interface type='network'>
       <source network='Ethernet 1'/>
diff --git a/v2v/types.ml b/v2v/types.ml
index 522814e..9a0b24b 100644
--- a/v2v/types.ml
+++ b/v2v/types.ml
@@ -391,7 +391,7 @@ class virtual output = object
   method virtual supported_firmware : target_firmware list
   method check_target_free_space (_ : source) (_ : target list) = ()
   method disk_create = (new Guestfs.guestfs ())#disk_create
-  method virtual create_metadata : source -> target list -> guestcaps -> inspect -> target_firmware -> unit
+  method virtual create_metadata : source -> target list -> target_buses -> guestcaps -> inspect -> target_firmware -> unit
   method keep_serial_console = true
 end
 
diff --git a/v2v/types.mli b/v2v/types.mli
index 45014a7..70c6fc7 100644
--- a/v2v/types.mli
+++ b/v2v/types.mli
@@ -234,7 +234,7 @@ class virtual output : object
   method check_target_free_space : source -> target list -> unit
   (** Called before conversion.  Can be used to check there is enough space
       on the target, using the [target.target_estimated_size] field. *)
-  method virtual create_metadata : source -> target list -> guestcaps -> inspect -> target_firmware -> unit
+  method virtual create_metadata : source -> target list -> target_buses -> guestcaps -> inspect -> target_firmware -> unit
   (** Called after conversion to finish off and create metadata. *)
   method disk_create : ?backingfile:string -> ?backingformat:string -> ?preallocation:string -> ?compat:string -> ?clustersize:int -> string -> string -> int64 -> unit
   (** Called in order to create disks on the target.  The method has the
diff --git a/v2v/v2v.ml b/v2v/v2v.ml
index 61ef4c1..bee0377 100644
--- a/v2v/v2v.ml
+++ b/v2v/v2v.ml
@@ -444,7 +444,8 @@ let rec main () =
 
   (* Create output metadata. *)
   message (f_"Creating output metadata");
-  output#create_metadata source targets guestcaps inspect target_firmware;
+  output#create_metadata source targets target_buses guestcaps inspect
+                         target_firmware;
 
   (* Save overlays if --debug-overlays option was used. *)
   if debug_overlays then (
-- 
2.3.1


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]