Richard W.M. Jones
2015-Nov-17 22:03 UTC
[Libguestfs] [PATCH 0/3] v2v: windows: Use '*.inf' files to control how Windows drivers are installed.
https://github.com/rwmjones/libguestfs/tree/rewrite-virtio-copy-drivers Instead of trying to split and parse elements from virtio-win paths, use the '*.inf' files supplied with the drivers to control how Windows drivers are installed. The following emails best explain how this works: https://www.redhat.com/archives/libguestfs/2015-October/msg00352.html https://www.redhat.com/archives/libguestfs/2015-November/msg00065.html Currently the product variant (eg. client or server) is ignored (see email I sent earlier today). There's actually a fourth patch which I didn't include, which just adds the content of all of the *.inf files from the virtio-win 1.7.4 ISO and directory, to test-data/fake-virtio-win. I didn't include it because it's a big patch that's not very interesting, but you can get it from the repo above. Rich.
Richard W.M. Jones
2015-Nov-17 22:03 UTC
[Libguestfs] [PATCH 1/3] mllib: Add sort_uniq function.
This is copied from supermin.
---
mllib/common_utils.ml | 16 ++++++++++++++++
mllib/common_utils.mli | 6 ++++++
2 files changed, 22 insertions(+)
diff --git a/mllib/common_utils.ml b/mllib/common_utils.ml
index 13e9256..5fb7183 100644
--- a/mllib/common_utils.ml
+++ b/mllib/common_utils.ml
@@ -267,6 +267,22 @@ let rec assoc ?(cmp = compare) ~default x = function
| (y, y') :: _ when cmp x y = 0 -> y'
| _ :: ys -> assoc ~cmp ~default x ys
+let uniq ?(cmp = Pervasives.compare) xs + let rec loop acc = function
+ | [] -> acc
+ | [x] -> x :: acc
+ | x :: (y :: _ as xs) when cmp x y = 0 ->
+ loop acc xs
+ | x :: (y :: _ as xs) ->
+ loop (x :: acc) xs
+ in
+ List.rev (loop [] xs)
+
+let sort_uniq ?(cmp = Pervasives.compare) xs + let xs = List.sort cmp xs in
+ let xs = uniq ~cmp xs in
+ xs
+
let may f = function
| None -> ()
| Some x -> f x
diff --git a/mllib/common_utils.mli b/mllib/common_utils.mli
index 44b8c93..68f7988 100644
--- a/mllib/common_utils.mli
+++ b/mllib/common_utils.mli
@@ -124,6 +124,12 @@ val assoc : ?cmp:('a -> 'a -> int) ->
default:'b -> 'a -> ('a * 'b) list -> 'b
(** Like {!List.assoc} but with a user-defined comparison function, and
instead of raising [Not_found], it returns the [~default] value. *)
+val uniq : ?cmp:('a -> 'a -> int) -> 'a list -> 'a
list
+ (** Uniquify a list (the list must be sorted first). *)
+
+val sort_uniq : ?cmp:('a -> 'a -> int) -> 'a list ->
'a list
+ (** Sort and uniquify a list. *)
+
val may : ('a -> unit) -> 'a option -> unit
(** [may f (Some x)] runs [f x]. [may f None] does nothing. *)
--
2.5.0
Richard W.M. Jones
2015-Nov-17 22:03 UTC
[Libguestfs] [PATCH 2/3] v2v: windows: Add a Windows '*.inf' file parser.
This simple parser has (limited) understanding of the Windows '*.inf'
file format. This is a Windows config file with some peculiarities.
This commit also has a unit test.
---
po/POTFILES-ml | 1 +
v2v/Makefile.am | 5 +-
v2v/v2v_unit_tests.ml | 104 +++++++++++++++++++++++++++++++++++-
v2v/windows_inf.ml | 143 ++++++++++++++++++++++++++++++++++++++++++++++++++
v2v/windows_inf.mli | 58 ++++++++++++++++++++
5 files changed, 308 insertions(+), 3 deletions(-)
create mode 100644 v2v/windows_inf.ml
create mode 100644 v2v/windows_inf.mli
diff --git a/po/POTFILES-ml b/po/POTFILES-ml
index c02ffc0..88db39b 100644
--- a/po/POTFILES-ml
+++ b/po/POTFILES-ml
@@ -127,4 +127,5 @@ v2v/v2v.ml
v2v/v2v_unit_tests.ml
v2v/vCenter.ml
v2v/windows.ml
+v2v/windows_inf.ml
v2v/xml.ml
diff --git a/v2v/Makefile.am b/v2v/Makefile.am
index 5dfef6e..c46594c 100644
--- a/v2v/Makefile.am
+++ b/v2v/Makefile.am
@@ -69,6 +69,7 @@ SOURCES_MLI = \
utils.mli \
vCenter.mli \
windows.mli \
+ windows_inf.mli \
xml.mli
SOURCES_ML = \
@@ -82,8 +83,9 @@ SOURCES_ML = \
DOM.ml \
changeuid.ml \
OVF.ml \
- linux.ml \
+ windows_inf.ml \
windows.ml \
+ linux.ml \
modules_list.ml \
input_disk.ml \
input_libvirtxml.ml \
@@ -309,6 +311,7 @@ v2v_unit_tests_BOBJECTS = \
utils.cmo \
DOM.cmo \
OVF.cmo \
+ windows_inf.cmo \
windows.cmo \
v2v_unit_tests.cmo
v2v_unit_tests_XOBJECTS = $(v2v_unit_tests_BOBJECTS:.cmo=.cmx)
diff --git a/v2v/v2v_unit_tests.ml b/v2v/v2v_unit_tests.ml
index a2dca32..169eea9 100644
--- a/v2v/v2v_unit_tests.ml
+++ b/v2v/v2v_unit_tests.ml
@@ -18,13 +18,21 @@
(* This file tests individual virt-v2v functions. *)
+open Printf
open OUnit2
+
+open Common_utils
+
open Types
-open Printf
-
external identity : 'a -> 'a = "%identity"
+let (//) = Filename.concat
+
+let srcdir + try Sys.getenv "srcdir"
+ with Not_found -> failwith "environment variable $srcdir must be
set"
+
let inspect_defaults = {
i_type = ""; i_distro = ""; i_arch = "";
i_major_version = 0; i_minor_version = 0;
@@ -126,6 +134,97 @@ let test_drive_index ctx assert_raises exn (fun () ->
Utils.drive_index "Z");
assert_raises exn (fun () -> Utils.drive_index "aB")
+(* Test parsing a [*.inf] file. *)
+let test_windows_inf_of_string ctx + let printer = Windows_inf.to_string in
+
+ (* There is nothing special about this choice. It is just a driver
+ * [*.inf] file picked at random.
+ *)
+ let path = srcdir // ".." // "test-data" //
"fake-virtio-win" //
+ "cd" // "Balloon" // "2k12" //
"amd64" // "balloon.inf" in
+
+ let sections = Windows_inf.load path in
+
+ let expected = [
+ "version", [
+ "signature", "\"$WINDOWS NT$\"";
+ "class", "System";
+ "classguid",
"{4d36e97d-e325-11ce-bfc1-08002be10318}";
+ "provider", "%RHEL%";
+ "driverver", "12/04/2014,62.71.104.9600";
+ "catalogfile", "Balloon.cat";
+ "driverpackagetype", "PlugAndPlay";
+ "driverpackagedisplayname", "%BALLOON.DeviceDesc%";
+ "pnplockdown", "1";
+ ];
+ "destinationdirs", [
+ "defaultdestdir", "12";
+ ];
+ "sourcedisksnames", [
+ "1", "%DiskId1%,,,\"\"";
+ ];
+ "sourcedisksfiles", [
+ "balloon.sys", "1,,";
+ ];
+ "manufacturer", [
+ "%rhel%", "Standard,NTamd64";
+ ];
+ "standard", [
+ "%balloon.devicedesc%", "BALLOON_Device,
PCI\\VEN_1AF4&DEV_1002&SUBSYS_00051AF4&REV_00";
+ ];
+ "standard.ntamd64", [
+ "%balloon.devicedesc%", "BALLOON_Device,
PCI\\VEN_1AF4&DEV_1002&SUBSYS_00051AF4&REV_00";
+ ];
+ "balloon_device.nt", [
+ "copyfiles", "Drivers_Dir";
+ ];
+ "drivers_dir", [];
+ "balloon_device.nt.services", [
+ "addservice", "BALLOON,%SPSVCINST_ASSOCSERVICE%,
BALLOON_Service_Inst, BALLOON_Logging_Inst";
+ ];
+ "balloon_service_inst", [
+ "displayname", "%BALLOON.SVCDESC%";
+ "servicetype", "1";
+ "starttype", "3";
+ "errorcontrol", "1";
+ "servicebinary", "%12%\\balloon.sys";
+ ];
+ "balloon_logging_inst", [
+ "addreg", "BALLOON_Logging_Inst_AddReg";
+ ];
+ "balloon_logging_inst_addreg", [];
+ "destinationdirs", [
+ "balloon_device_coinstaller_copyfiles", "11";
+ ];
+ "balloon_device.nt.coinstallers", [
+ "addreg", "BALLOON_Device_CoInstaller_AddReg";
+ "copyfiles", "BALLOON_Device_CoInstaller_CopyFiles";
+ ];
+ "balloon_device_coinstaller_addreg", [];
+ "balloon_device_coinstaller_copyfiles", [];
+ "sourcedisksfiles", [
+ "wdfcoinstaller01011.dll", "1";
+ ];
+ "balloon_device.nt.wdf", [
+ "kmdfservice", "BALLOON, BALLOON_wdfsect";
+ ];
+ "balloon_wdfsect", [
+ "kmdflibraryversion", "1.11";
+ ];
+ "strings", [
+ "spsvcinst_assocservice", "0x00000002";
+ "rhel", "\"Red Hat, Inc.\"";
+ "diskid1", "\"VirtIO Balloon Installation Disk
#1\"";
+ "balloon.devicedesc", "\"VirtIO Balloon
Driver\"";
+ "balloon.svcdesc", "\"VirtIO Balloon
Service\"";
+ "classname", "\"VirtIO Balloon Device\"";
+ ];
+ ] in
+
+ assert_equal ~printer expected sections
+
+(* Test the code which matches [*.inf] files to Windows guests. *)
let test_virtio_iso_path_matches_guest_os ctx (* Windows OSes fake
inspection data. *)
let make_win name major minor variant arch = {
@@ -772,6 +871,7 @@ let suite "OVF.get_ostype" >::
test_get_ostype;
"Utils.drive_name" >:: test_drive_name;
"Utils.drive_index" >:: test_drive_index;
+ "Windows_inf.of_string" >:: test_windows_inf_of_string;
"Windows.virtio_iso_path_matches_guest_os" >::
test_virtio_iso_path_matches_guest_os;
]
diff --git a/v2v/windows_inf.ml b/v2v/windows_inf.ml
new file mode 100644
index 0000000..2066a2e
--- /dev/null
+++ b/v2v/windows_inf.ml
@@ -0,0 +1,143 @@
+(* virt-v2v
+ * Copyright (C) 2015 Red Hat Inc.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *)
+
+open Printf
+
+open Common_utils
+
+type t = section list
+and section = string * data list
+and data = string * string
+
+let crlf_rex = Str.regexp "\r?\n"
+
+(* Match [[header]] in a Windows [*.inf] file. *)
+let section_header_rex + Str.regexp "^[ \t]*\\[[ \t]*\\(.*\\)[ \t]*\\][
\t]*$"
+
+let match_section_header line = Str.string_match section_header_rex line 0
+let not_section_header line = not (match_section_header line)
+
+(* Match [key = value] in a Windows [*.inf] file. *)
+let key_value_rex + Str.regexp_case_fold
+ "^[ \t]*\\([a-z0-9%_.]+\\)[ \t]*=[ \t]*\\(.*\\)[ \t]*$"
+
+(* Match comment preceeded by whitespace (so comments can be removed). *)
+let comment_rex = Str.regexp "[ \t]*;.*"
+
+(* Parse a Windows [*.inf] file into headers and section lines. *)
+let of_string content + (* Split up the inf file (possibly with DOS line
endings) into lines. *)
+ let lines = Str.split crlf_rex content in
+
+ (* Split the file into section headers + section content. *)
+ let rec loop = function
+ | [] -> []
+ | header :: xs when match_section_header header ->
+ let header = Str.matched_group 1 header in
+ let lines = takewhile not_section_header xs in
+ let ys = dropwhile not_section_header xs in
+ (header, lines) :: loop ys
+ | xs ->
+ (* Put all initial lines before the first section into a
+ * section with no name.
+ *)
+ let lines = takewhile not_section_header xs in
+ let ys = dropwhile not_section_header xs in
+ ("", lines) :: loop ys
+ in
+ let sections = loop lines in
+
+ (* Split the lines that match "key = value" into [(key, value)]
pairs.
+ * Ignore any other lines.
+ *)
+ let sections = List.map (
+ fun (header, lines) ->
+ let lines = filter_map (
+ fun line ->
+ if Str.string_match key_value_rex line 0 then (
+ let key = Str.matched_group 1 line in
+ let value = Str.matched_group 2 line in
+ Some (key, value)
+ )
+ else None (* ignore the non-matching line *)
+ ) lines in
+ header, lines
+ ) sections in
+
+ (* If the dummy section at the beginning is now completely empty,
+ * remove it.
+ *)
+ let sections + match sections with
+ | ("", []) :: sections -> sections
+ | sections -> sections in
+
+ (* Remove any comments from values, conservatively though because
+ * we don't really understand the value format.
+ *)
+ let sections = List.map (
+ fun (header, lines) ->
+ let lines = List.map (
+ fun (key, value) ->
+ let value + if String.contains value '"' then
value
+ else Str.replace_first comment_rex "" value in
+ key, value
+ ) lines in
+ header, lines
+ ) sections in
+
+ (* Normalize (by lowercasing) the section headers and keys (but not
+ * the values).
+ *)
+ let sections = List.map (
+ fun (header, lines) ->
+ let header = String.lowercase_ascii header in
+ let lines = List.map (
+ fun (key, value) ->
+ String.lowercase_ascii key, value
+ ) lines in
+ header, lines
+ ) sections in
+
+ sections
+
+let find_section t section_name + let section_name = String.lowercase_ascii
section_name in
+ List.assoc section_name t
+
+let find_key t section_name key_name + let data = find_section t section_name
in
+ let key_name = String.lowercase_ascii key_name in
+ List.assoc key_name data
+
+let load filename + of_string (read_whole_file filename)
+
+let rec to_string sections + String.concat "\n" (List.map
string_of_section sections)
+
+and string_of_section (header, body) + let header = sprintf "[%s]"
header in
+ let body = List.map string_of_key_value body in
+ String.concat "\n" (header :: body)
+
+and string_of_key_value (key, value) + sprintf "%s = %s" key value
diff --git a/v2v/windows_inf.mli b/v2v/windows_inf.mli
new file mode 100644
index 0000000..1cb8040
--- /dev/null
+++ b/v2v/windows_inf.mli
@@ -0,0 +1,58 @@
+(* virt-v2v
+ * Copyright (C) 2009-2015 Red Hat Inc.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *)
+
+(** Handle Windows driver [*.inf] files. *)
+
+type t = section list
+(** Type of a parsed Windows driver [*.inf] file. *)
+
+and section = string * data list
+(** A single section consists of a header and a list of lines. If
+ the file doesn't start with a section header, then the initial
+ section has a dummy header name [""].
+
+ The section header is always normalized to lowercase ASCII. *)
+
+and data = string * string
+(** A [key = value] pair appearing within a section body. The key
+ (but {i not} the value) is always normalized to lowercase ASCII. *)
+
+val of_string : string -> t
+(** Parse an [*.inf] file from the string. No parse errors are
+ possible since this parser accepts anything as a possible [*.inf]
+ file. *)
+
+val load : string -> t
+(** Same as {!of_string} except we load the content from
+ a host file. *)
+
+val to_string : t -> string
+(** Convert an inf file back to a string. This should probably only
+ be used for debugging, since we don't preserve comments and it's
+ not tested that Windows would be able to parse what we write out. *)
+
+val find_section : t -> string -> data list
+(** [find_section t section_name] finds and returns a section by name.
+
+ Raises [Not_found] if not found. *)
+
+val find_key : t -> string -> string -> string
+(** [find_key t section_name key_name] finds and returns a key within
+ a particular section.
+
+ Raises [Not_found] if not found. *)
--
2.5.0
Richard W.M. Jones
2015-Nov-17 22:03 UTC
[Libguestfs] [PATCH 3/3] v2v: windows: Use '*.inf' files to control how Windows drivers are installed.
Instead of trying to split and parse elements from virtio-win paths,
use the '*.inf' files supplied with the drivers to control how Windows
drivers are installed.
The following emails best explain how this works:
https://www.redhat.com/archives/libguestfs/2015-October/msg00352.html
https://www.redhat.com/archives/libguestfs/2015-November/msg00065.html
Currently the product variant (eg. client or server) is ignored.
---
v2v/v2v_unit_tests.ml | 623 ++++++++------------------------------------------
v2v/windows.ml | 289 +++++++++++++----------
v2v/windows.mli | 2 +-
3 files changed, 265 insertions(+), 649 deletions(-)
diff --git a/v2v/v2v_unit_tests.ml b/v2v/v2v_unit_tests.ml
index 169eea9..5cc1f3e 100644
--- a/v2v/v2v_unit_tests.ml
+++ b/v2v/v2v_unit_tests.ml
@@ -225,7 +225,7 @@ let test_windows_inf_of_string ctx assert_equal ~printer
expected sections
(* Test the code which matches [*.inf] files to Windows guests. *)
-let test_virtio_iso_path_matches_guest_os ctx +let
test_virtio_inf_matches_guest_os ctx (* Windows OSes fake inspection data. *)
let make_win name major minor variant arch = {
inspect_defaults with
@@ -262,591 +262,149 @@ let test_virtio_iso_path_matches_guest_os ctx ] in
let paths = [
- (* Paths from the virtio-win 1.7.4 ISO. *)
- "Balloon/2k12/amd64/WdfCoInstaller01011.dll", None;
- "Balloon/2k12/amd64/balloon.cat", Some win2k12_64;
- "Balloon/2k12/amd64/balloon.inf", Some win2k12_64;
- "Balloon/2k12/amd64/balloon.pdb", Some win2k12_64;
- "Balloon/2k12/amd64/balloon.sys", Some win2k12_64;
- "Balloon/2k12/amd64/blnsvr.exe", None;
- "Balloon/2k12/amd64/blnsvr.pdb", Some win2k12_64;
- "Balloon/2k12R2/amd64/WdfCoInstaller01011.dll", None;
- "Balloon/2k12R2/amd64/balloon.cat", Some win2k12r2_64;
- "Balloon/2k12R2/amd64/balloon.inf", Some win2k12r2_64;
- "Balloon/2k12R2/amd64/balloon.pdb", Some win2k12r2_64;
- "Balloon/2k12R2/amd64/balloon.sys", Some win2k12r2_64;
- "Balloon/2k12R2/amd64/blnsvr.exe", None;
- "Balloon/2k12R2/amd64/blnsvr.pdb", Some win2k12r2_64;
- "Balloon/2k3/amd64/WdfCoInstaller01009.dll", None;
- "Balloon/2k3/amd64/balloon.cat", Some win2k3_64;
- "Balloon/2k3/amd64/balloon.inf", Some win2k3_64;
- "Balloon/2k3/amd64/balloon.pdb", Some win2k3_64;
- "Balloon/2k3/amd64/balloon.sys", Some win2k3_64;
- "Balloon/2k3/amd64/blnsvr.exe", None;
- "Balloon/2k3/amd64/blnsvr.pdb", Some win2k3_64;
- "Balloon/2k3/x86/WdfCoInstaller01009.dll", None;
- "Balloon/2k3/x86/balloon.cat", Some win2k3_32;
- "Balloon/2k3/x86/balloon.inf", Some win2k3_32;
- "Balloon/2k3/x86/balloon.pdb", Some win2k3_32;
- "Balloon/2k3/x86/balloon.sys", Some win2k3_32;
- "Balloon/2k3/x86/blnsvr.exe", None;
- "Balloon/2k3/x86/blnsvr.pdb", Some win2k3_32;
- "Balloon/2k8/amd64/WdfCoInstaller01009.dll", None;
- "Balloon/2k8/amd64/balloon.cat", Some win2k8_64;
- "Balloon/2k8/amd64/balloon.inf", Some win2k8_64;
- "Balloon/2k8/amd64/balloon.pdb", Some win2k8_64;
- "Balloon/2k8/amd64/balloon.sys", Some win2k8_64;
- "Balloon/2k8/amd64/blnsvr.exe", None;
- "Balloon/2k8/amd64/blnsvr.pdb", Some win2k8_64;
- "Balloon/2k8/x86/WdfCoInstaller01009.dll", None;
- "Balloon/2k8/x86/balloon.cat", Some win2k8_32;
- "Balloon/2k8/x86/balloon.inf", Some win2k8_32;
- "Balloon/2k8/x86/balloon.pdb", Some win2k8_32;
- "Balloon/2k8/x86/balloon.sys", Some win2k8_32;
- "Balloon/2k8/x86/blnsvr.exe", None;
- "Balloon/2k8/x86/blnsvr.pdb", Some win2k8_32;
- "Balloon/2k8R2/amd64/WdfCoInstaller01009.dll", None;
- "Balloon/2k8R2/amd64/balloon.cat", Some win2k8r2_64;
- "Balloon/2k8R2/amd64/balloon.inf", Some win2k8r2_64;
- "Balloon/2k8R2/amd64/balloon.pdb", Some win2k8r2_64;
- "Balloon/2k8R2/amd64/balloon.sys", Some win2k8r2_64;
- "Balloon/2k8R2/amd64/blnsvr.exe", None;
- "Balloon/2k8R2/amd64/blnsvr.pdb", Some win2k8r2_64;
- "Balloon/w7/amd64/WdfCoInstaller01009.dll", None;
- "Balloon/w7/amd64/balloon.cat", Some win7_64;
- "Balloon/w7/amd64/balloon.inf", Some win7_64;
- "Balloon/w7/amd64/balloon.pdb", Some win7_64;
- "Balloon/w7/amd64/balloon.sys", Some win7_64;
- "Balloon/w7/amd64/blnsvr.exe", None;
- "Balloon/w7/amd64/blnsvr.pdb", Some win7_64;
- "Balloon/w7/x86/WdfCoInstaller01009.dll", None;
- "Balloon/w7/x86/balloon.cat", Some win7_32;
- "Balloon/w7/x86/balloon.inf", Some win7_32;
- "Balloon/w7/x86/balloon.pdb", Some win7_32;
- "Balloon/w7/x86/balloon.sys", Some win7_32;
- "Balloon/w7/x86/blnsvr.exe", None;
- "Balloon/w7/x86/blnsvr.pdb", Some win7_32;
- "Balloon/w8.1/amd64/WdfCoInstaller01011.dll", None;
- "Balloon/w8.1/amd64/balloon.cat", Some win8_1_64;
- "Balloon/w8.1/amd64/balloon.inf", Some win8_1_64;
- "Balloon/w8.1/amd64/balloon.pdb", Some win8_1_64;
- "Balloon/w8.1/amd64/balloon.sys", Some win8_1_64;
- "Balloon/w8.1/amd64/blnsvr.exe", None;
- "Balloon/w8.1/amd64/blnsvr.pdb", Some win8_1_64;
- "Balloon/w8.1/x86/WdfCoInstaller01011.dll", None;
- "Balloon/w8.1/x86/balloon.cat", Some win8_1_32;
- "Balloon/w8.1/x86/balloon.inf", Some win8_1_32;
- "Balloon/w8.1/x86/balloon.pdb", Some win8_1_32;
- "Balloon/w8.1/x86/balloon.sys", Some win8_1_32;
- "Balloon/w8.1/x86/blnsvr.exe", None;
- "Balloon/w8.1/x86/blnsvr.pdb", Some win8_1_32;
- "Balloon/w8/amd64/WdfCoInstaller01011.dll", None;
- "Balloon/w8/amd64/balloon.cat", Some win8_64;
- "Balloon/w8/amd64/balloon.inf", Some win8_64;
- "Balloon/w8/amd64/balloon.pdb", Some win8_64;
- "Balloon/w8/amd64/balloon.sys", Some win8_64;
- "Balloon/w8/amd64/blnsvr.exe", None;
- "Balloon/w8/amd64/blnsvr.pdb", Some win8_64;
- "Balloon/w8/x86/WdfCoInstaller01011.dll", None;
- "Balloon/w8/x86/balloon.cat", Some win8_32;
- "Balloon/w8/x86/balloon.inf", Some win8_32;
- "Balloon/w8/x86/balloon.pdb", Some win8_32;
- "Balloon/w8/x86/balloon.sys", Some win8_32;
- "Balloon/w8/x86/blnsvr.exe", None;
- "Balloon/w8/x86/blnsvr.pdb", Some win8_32;
- "Balloon/xp/x86/WdfCoInstaller01009.dll", None;
- "Balloon/xp/x86/balloon.cat", Some winxp_32;
- "Balloon/xp/x86/balloon.inf", Some winxp_32;
- "Balloon/xp/x86/balloon.pdb", Some winxp_32;
- "Balloon/xp/x86/balloon.sys", Some winxp_32;
- "Balloon/xp/x86/blnsvr.exe", None;
- "Balloon/xp/x86/blnsvr.pdb", Some winxp_32;
- "NetKVM/2k12/amd64/netkvm.cat", Some win2k12_64;
- "NetKVM/2k12/amd64/netkvm.inf", Some win2k12_64;
- "NetKVM/2k12/amd64/netkvm.pdb", Some win2k12_64;
- "NetKVM/2k12/amd64/netkvm.sys", Some win2k12_64;
- "NetKVM/2k12/amd64/netkvmco.dll", None;
- "NetKVM/2k12/amd64/readme.doc", None;
- "NetKVM/2k12R2/amd64/netkvm.cat", Some win2k12r2_64;
- "NetKVM/2k12R2/amd64/netkvm.inf", Some win2k12r2_64;
- "NetKVM/2k12R2/amd64/netkvm.pdb", Some win2k12r2_64;
- "NetKVM/2k12R2/amd64/netkvm.sys", Some win2k12r2_64;
- "NetKVM/2k12R2/amd64/netkvmco.dll", None;
- "NetKVM/2k12R2/amd64/readme.doc", None;
- "NetKVM/2k3/amd64/netkvm.cat", Some win2k3_64;
- "NetKVM/2k3/amd64/netkvm.inf", Some win2k3_64;
- "NetKVM/2k3/amd64/netkvm.pdb", Some win2k3_64;
- "NetKVM/2k3/amd64/netkvm.sys", Some win2k3_64;
- "NetKVM/2k3/x86/netkvm.cat", Some win2k3_32;
- "NetKVM/2k3/x86/netkvm.inf", Some win2k3_32;
- "NetKVM/2k3/x86/netkvm.pdb", Some win2k3_32;
- "NetKVM/2k3/x86/netkvm.sys", Some win2k3_32;
- "NetKVM/2k8/amd64/netkvm.cat", Some win2k8_64;
- "NetKVM/2k8/amd64/netkvm.inf", Some win2k8_64;
- "NetKVM/2k8/amd64/netkvm.pdb", Some win2k8_64;
- "NetKVM/2k8/amd64/netkvm.sys", Some win2k8_64;
- "NetKVM/2k8/amd64/netkvmco.dll", None;
- "NetKVM/2k8/amd64/readme.doc", None;
- "NetKVM/2k8/x86/netkvm.cat", Some win2k8_32;
- "NetKVM/2k8/x86/netkvm.inf", Some win2k8_32;
- "NetKVM/2k8/x86/netkvm.pdb", Some win2k8_32;
- "NetKVM/2k8/x86/netkvm.sys", Some win2k8_32;
- "NetKVM/2k8/x86/netkvmco.dll", None;
- "NetKVM/2k8/x86/readme.doc", None;
- "NetKVM/2k8R2/amd64/netkvm.cat", Some win2k8r2_64;
- "NetKVM/2k8R2/amd64/netkvm.inf", Some win2k8r2_64;
- "NetKVM/2k8R2/amd64/netkvm.pdb", Some win2k8r2_64;
- "NetKVM/2k8R2/amd64/netkvm.sys", Some win2k8r2_64;
- "NetKVM/2k8R2/amd64/netkvmco.dll", None;
- "NetKVM/2k8R2/amd64/readme.doc", None;
- "NetKVM/w7/amd64/netkvm.cat", Some win7_64;
- "NetKVM/w7/amd64/netkvm.inf", Some win7_64;
- "NetKVM/w7/amd64/netkvm.pdb", Some win7_64;
- "NetKVM/w7/amd64/netkvm.sys", Some win7_64;
- "NetKVM/w7/amd64/netkvmco.dll", None;
- "NetKVM/w7/amd64/readme.doc", None;
- "NetKVM/w7/x86/netkvm.cat", Some win7_32;
- "NetKVM/w7/x86/netkvm.inf", Some win7_32;
- "NetKVM/w7/x86/netkvm.pdb", Some win7_32;
- "NetKVM/w7/x86/netkvm.sys", Some win7_32;
- "NetKVM/w7/x86/netkvmco.dll", None;
- "NetKVM/w7/x86/readme.doc", None;
- "NetKVM/w8.1/amd64/netkvm.cat", Some win8_1_64;
- "NetKVM/w8.1/amd64/netkvm.inf", Some win8_1_64;
- "NetKVM/w8.1/amd64/netkvm.pdb", Some win8_1_64;
- "NetKVM/w8.1/amd64/netkvm.sys", Some win8_1_64;
- "NetKVM/w8.1/amd64/netkvmco.dll", None;
- "NetKVM/w8.1/amd64/readme.doc", None;
- "NetKVM/w8.1/x86/netkvm.cat", Some win8_1_32;
- "NetKVM/w8.1/x86/netkvm.inf", Some win8_1_32;
- "NetKVM/w8.1/x86/netkvm.pdb", Some win8_1_32;
- "NetKVM/w8.1/x86/netkvm.sys", Some win8_1_32;
- "NetKVM/w8.1/x86/netkvmco.dll", None;
- "NetKVM/w8.1/x86/readme.doc", None;
- "NetKVM/w8/amd64/netkvm.cat", Some win8_64;
- "NetKVM/w8/amd64/netkvm.inf", Some win8_64;
- "NetKVM/w8/amd64/netkvm.pdb", Some win8_64;
- "NetKVM/w8/amd64/netkvm.sys", Some win8_64;
- "NetKVM/w8/amd64/netkvmco.dll", None;
- "NetKVM/w8/amd64/readme.doc", None;
- "NetKVM/w8/x86/netkvm.cat", Some win8_32;
- "NetKVM/w8/x86/netkvm.inf", Some win8_32;
- "NetKVM/w8/x86/netkvm.pdb", Some win8_32;
- "NetKVM/w8/x86/netkvm.sys", Some win8_32;
- "NetKVM/w8/x86/netkvmco.dll", None;
- "NetKVM/w8/x86/readme.doc", None;
- "NetKVM/xp/x86/netkvm.cat", Some winxp_32;
- "NetKVM/xp/x86/netkvm.inf", Some winxp_32;
- "NetKVM/xp/x86/netkvm.pdb", Some winxp_32;
- "NetKVM/xp/x86/netkvm.sys", Some winxp_32;
- "guest-agent/qemu-ga-x64.msi", None;
- "guest-agent/qemu-ga-x86.msi", None;
- "qemupciserial/qemupciserial.inf", None;
- "viorng/2k12/amd64/WdfCoInstaller01011.dll", None;
- "viorng/2k12/amd64/viorng.cat", Some win2k12_64;
- "viorng/2k12/amd64/viorng.inf", Some win2k12_64;
- "viorng/2k12/amd64/viorng.pdb", Some win2k12_64;
- "viorng/2k12/amd64/viorng.sys", Some win2k12_64;
- "viorng/2k12/amd64/viorngci.dll", None;
- "viorng/2k12/amd64/viorngum.dll", None;
- "viorng/2k12R2/amd64/WdfCoInstaller01011.dll", None;
- "viorng/2k12R2/amd64/viorng.cat", Some win2k12r2_64;
- "viorng/2k12R2/amd64/viorng.inf", Some win2k12r2_64;
- "viorng/2k12R2/amd64/viorng.pdb", Some win2k12r2_64;
- "viorng/2k12R2/amd64/viorng.sys", Some win2k12r2_64;
- "viorng/2k12R2/amd64/viorngci.dll", None;
- "viorng/2k12R2/amd64/viorngum.dll", None;
- "viorng/2k8/amd64/WdfCoInstaller01009.dll", None;
- "viorng/2k8/amd64/viorng.cat", Some win2k8_64;
- "viorng/2k8/amd64/viorng.inf", Some win2k8_64;
- "viorng/2k8/amd64/viorng.pdb", Some win2k8_64;
- "viorng/2k8/amd64/viorng.sys", Some win2k8_64;
- "viorng/2k8/amd64/viorngci.dll", None;
- "viorng/2k8/amd64/viorngum.dll", None;
- "viorng/2k8/x86/WdfCoInstaller01009.dll", None;
- "viorng/2k8/x86/viorng.cat", Some win2k8_32;
- "viorng/2k8/x86/viorng.inf", Some win2k8_32;
- "viorng/2k8/x86/viorng.pdb", Some win2k8_32;
- "viorng/2k8/x86/viorng.sys", Some win2k8_32;
- "viorng/2k8/x86/viorngci.dll", None;
- "viorng/2k8/x86/viorngum.dll", None;
- "viorng/2k8R2/amd64/WdfCoInstaller01009.dll", None;
- "viorng/2k8R2/amd64/viorng.cat", Some win2k8r2_64;
- "viorng/2k8R2/amd64/viorng.inf", Some win2k8r2_64;
- "viorng/2k8R2/amd64/viorng.pdb", Some win2k8r2_64;
- "viorng/2k8R2/amd64/viorng.sys", Some win2k8r2_64;
- "viorng/2k8R2/amd64/viorngci.dll", None;
- "viorng/2k8R2/amd64/viorngum.dll", None;
- "viorng/w7/amd64/WdfCoInstaller01009.dll", None;
- "viorng/w7/amd64/viorng.cat", Some win7_64;
- "viorng/w7/amd64/viorng.inf", Some win7_64;
- "viorng/w7/amd64/viorng.pdb", Some win7_64;
- "viorng/w7/amd64/viorng.sys", Some win7_64;
- "viorng/w7/amd64/viorngci.dll", None;
- "viorng/w7/amd64/viorngum.dll", None;
- "viorng/w7/x86/WdfCoInstaller01009.dll", None;
- "viorng/w7/x86/viorng.cat", Some win7_32;
- "viorng/w7/x86/viorng.inf", Some win7_32;
- "viorng/w7/x86/viorng.pdb", Some win7_32;
- "viorng/w7/x86/viorng.sys", Some win7_32;
- "viorng/w7/x86/viorngci.dll", None;
- "viorng/w7/x86/viorngum.dll", None;
- "viorng/w8.1/amd64/WdfCoInstaller01011.dll", None;
- "viorng/w8.1/amd64/viorng.cat", Some win8_1_64;
- "viorng/w8.1/amd64/viorng.inf", Some win8_1_64;
- "viorng/w8.1/amd64/viorng.pdb", Some win8_1_64;
- "viorng/w8.1/amd64/viorng.sys", Some win8_1_64;
- "viorng/w8.1/amd64/viorngci.dll", None;
- "viorng/w8.1/amd64/viorngum.dll", None;
- "viorng/w8.1/x86/WdfCoInstaller01011.dll", None;
- "viorng/w8.1/x86/viorng.cat", Some win8_1_32;
- "viorng/w8.1/x86/viorng.inf", Some win8_1_32;
- "viorng/w8.1/x86/viorng.pdb", Some win8_1_32;
- "viorng/w8.1/x86/viorng.sys", Some win8_1_32;
- "viorng/w8.1/x86/viorngci.dll", None;
- "viorng/w8.1/x86/viorngum.dll", None;
- "viorng/w8/amd64/WdfCoInstaller01011.dll", None;
- "viorng/w8/amd64/viorng.cat", Some win8_64;
- "viorng/w8/amd64/viorng.inf", Some win8_64;
- "viorng/w8/amd64/viorng.pdb", Some win8_64;
- "viorng/w8/amd64/viorng.sys", Some win8_64;
- "viorng/w8/amd64/viorngci.dll", None;
- "viorng/w8/amd64/viorngum.dll", None;
- "viorng/w8/x86/WdfCoInstaller01011.dll", None;
- "viorng/w8/x86/viorng.cat", Some win8_32;
- "viorng/w8/x86/viorng.inf", Some win8_32;
- "viorng/w8/x86/viorng.pdb", Some win8_32;
- "viorng/w8/x86/viorng.sys", Some win8_32;
- "viorng/w8/x86/viorngci.dll", None;
- "viorng/w8/x86/viorngum.dll", None;
- "vioscsi/2k12/amd64/vioscsi.cat", Some win2k12_64;
- "vioscsi/2k12/amd64/vioscsi.inf", Some win2k12_64;
- "vioscsi/2k12/amd64/vioscsi.pdb", Some win2k12_64;
- "vioscsi/2k12/amd64/vioscsi.sys", Some win2k12_64;
- "vioscsi/2k12R2/amd64/vioscsi.cat", Some win2k12r2_64;
- "vioscsi/2k12R2/amd64/vioscsi.inf", Some win2k12r2_64;
- "vioscsi/2k12R2/amd64/vioscsi.pdb", Some win2k12r2_64;
- "vioscsi/2k12R2/amd64/vioscsi.sys", Some win2k12r2_64;
- "vioscsi/2k8/amd64/vioscsi.cat", Some win2k8_64;
- "vioscsi/2k8/amd64/vioscsi.inf", Some win2k8_64;
- "vioscsi/2k8/amd64/vioscsi.pdb", Some win2k8_64;
- "vioscsi/2k8/amd64/vioscsi.sys", Some win2k8_64;
- "vioscsi/2k8/x86/vioscsi.cat", Some win2k8_32;
- "vioscsi/2k8/x86/vioscsi.inf", Some win2k8_32;
- "vioscsi/2k8/x86/vioscsi.pdb", Some win2k8_32;
- "vioscsi/2k8/x86/vioscsi.sys", Some win2k8_32;
- "vioscsi/2k8R2/amd64/vioscsi.cat", Some win2k8r2_64;
- "vioscsi/2k8R2/amd64/vioscsi.inf", Some win2k8r2_64;
- "vioscsi/2k8R2/amd64/vioscsi.pdb", Some win2k8r2_64;
- "vioscsi/2k8R2/amd64/vioscsi.sys", Some win2k8r2_64;
- "vioscsi/w7/amd64/vioscsi.cat", Some win7_64;
- "vioscsi/w7/amd64/vioscsi.inf", Some win7_64;
- "vioscsi/w7/amd64/vioscsi.pdb", Some win7_64;
- "vioscsi/w7/amd64/vioscsi.sys", Some win7_64;
- "vioscsi/w7/x86/vioscsi.cat", Some win7_32;
- "vioscsi/w7/x86/vioscsi.inf", Some win7_32;
- "vioscsi/w7/x86/vioscsi.pdb", Some win7_32;
- "vioscsi/w7/x86/vioscsi.sys", Some win7_32;
- "vioscsi/w8.1/amd64/vioscsi.cat", Some win8_1_64;
- "vioscsi/w8.1/amd64/vioscsi.inf", Some win8_1_64;
- "vioscsi/w8.1/amd64/vioscsi.pdb", Some win8_1_64;
- "vioscsi/w8.1/amd64/vioscsi.sys", Some win8_1_64;
- "vioscsi/w8.1/x86/vioscsi.cat", Some win8_1_32;
- "vioscsi/w8.1/x86/vioscsi.inf", Some win8_1_32;
- "vioscsi/w8.1/x86/vioscsi.pdb", Some win8_1_32;
- "vioscsi/w8.1/x86/vioscsi.sys", Some win8_1_32;
- "vioscsi/w8/amd64/vioscsi.cat", Some win8_64;
- "vioscsi/w8/amd64/vioscsi.inf", Some win8_64;
- "vioscsi/w8/amd64/vioscsi.pdb", Some win8_64;
- "vioscsi/w8/amd64/vioscsi.sys", Some win8_64;
- "vioscsi/w8/x86/vioscsi.cat", Some win8_32;
- "vioscsi/w8/x86/vioscsi.inf", Some win8_32;
- "vioscsi/w8/x86/vioscsi.pdb", Some win8_32;
- "vioscsi/w8/x86/vioscsi.sys", Some win8_32;
- "vioserial/2k12/amd64/WdfCoInstaller01011.dll", None;
- "vioserial/2k12/amd64/vioser.cat", Some win2k12_64;
- "vioserial/2k12/amd64/vioser.inf", Some win2k12_64;
- "vioserial/2k12/amd64/vioser.pdb", Some win2k12_64;
- "vioserial/2k12/amd64/vioser.sys", Some win2k12_64;
- "vioserial/2k12R2/amd64/WdfCoInstaller01011.dll", None;
- "vioserial/2k12R2/amd64/vioser.cat", Some win2k12r2_64;
- "vioserial/2k12R2/amd64/vioser.inf", Some win2k12r2_64;
- "vioserial/2k12R2/amd64/vioser.pdb", Some win2k12r2_64;
- "vioserial/2k12R2/amd64/vioser.sys", Some win2k12r2_64;
- "vioserial/2k3/amd64/WdfCoInstaller01009.dll", None;
- "vioserial/2k3/amd64/vioser.cat", Some win2k3_64;
- "vioserial/2k3/amd64/vioser.inf", Some win2k3_64;
- "vioserial/2k3/amd64/vioser.pdb", Some win2k3_64;
- "vioserial/2k3/amd64/vioser.sys", Some win2k3_64;
- "vioserial/2k3/x86/WdfCoInstaller01009.dll", None;
- "vioserial/2k3/x86/vioser.cat", Some win2k3_32;
- "vioserial/2k3/x86/vioser.inf", Some win2k3_32;
- "vioserial/2k3/x86/vioser.pdb", Some win2k3_32;
- "vioserial/2k3/x86/vioser.sys", Some win2k3_32;
- "vioserial/2k8/amd64/WdfCoInstaller01009.dll", None;
- "vioserial/2k8/amd64/vioser.cat", Some win2k8_64;
- "vioserial/2k8/amd64/vioser.inf", Some win2k8_64;
- "vioserial/2k8/amd64/vioser.pdb", Some win2k8_64;
- "vioserial/2k8/amd64/vioser.sys", Some win2k8_64;
- "vioserial/2k8/x86/WdfCoInstaller01009.dll", None;
- "vioserial/2k8/x86/vioser.cat", Some win2k8_32;
- "vioserial/2k8/x86/vioser.inf", Some win2k8_32;
- "vioserial/2k8/x86/vioser.pdb", Some win2k8_32;
- "vioserial/2k8/x86/vioser.sys", Some win2k8_32;
- "vioserial/2k8R2/amd64/WdfCoInstaller01009.dll", None;
- "vioserial/2k8R2/amd64/vioser.cat", Some win2k8r2_64;
- "vioserial/2k8R2/amd64/vioser.inf", Some win2k8r2_64;
- "vioserial/2k8R2/amd64/vioser.pdb", Some win2k8r2_64;
- "vioserial/2k8R2/amd64/vioser.sys", Some win2k8r2_64;
- "vioserial/w7/amd64/WdfCoInstaller01009.dll", None;
- "vioserial/w7/amd64/vioser.cat", Some win7_64;
- "vioserial/w7/amd64/vioser.inf", Some win7_64;
- "vioserial/w7/amd64/vioser.pdb", Some win7_64;
- "vioserial/w7/amd64/vioser.sys", Some win7_64;
- "vioserial/w7/x86/WdfCoInstaller01009.dll", None;
- "vioserial/w7/x86/vioser.cat", Some win7_32;
- "vioserial/w7/x86/vioser.inf", Some win7_32;
- "vioserial/w7/x86/vioser.pdb", Some win7_32;
- "vioserial/w7/x86/vioser.sys", Some win7_32;
- "vioserial/w8.1/amd64/WdfCoInstaller01011.dll", None;
- "vioserial/w8.1/amd64/vioser.cat", Some win8_1_64;
- "vioserial/w8.1/amd64/vioser.inf", Some win8_1_64;
- "vioserial/w8.1/amd64/vioser.pdb", Some win8_1_64;
- "vioserial/w8.1/amd64/vioser.sys", Some win8_1_64;
- "vioserial/w8.1/x86/WdfCoInstaller01011.dll", None;
- "vioserial/w8.1/x86/vioser.cat", Some win8_1_32;
- "vioserial/w8.1/x86/vioser.inf", Some win8_1_32;
- "vioserial/w8.1/x86/vioser.pdb", Some win8_1_32;
- "vioserial/w8.1/x86/vioser.sys", Some win8_1_32;
- "vioserial/w8/amd64/WdfCoInstaller01011.dll", None;
- "vioserial/w8/amd64/vioser.cat", Some win8_64;
- "vioserial/w8/amd64/vioser.inf", Some win8_64;
- "vioserial/w8/amd64/vioser.pdb", Some win8_64;
- "vioserial/w8/amd64/vioser.sys", Some win8_64;
- "vioserial/w8/x86/WdfCoInstaller01011.dll", None;
- "vioserial/w8/x86/vioser.cat", Some win8_32;
- "vioserial/w8/x86/vioser.inf", Some win8_32;
- "vioserial/w8/x86/vioser.pdb", Some win8_32;
- "vioserial/w8/x86/vioser.sys", Some win8_32;
- "vioserial/xp/x86/WdfCoInstaller01009.dll", None;
- "vioserial/xp/x86/vioser.cat", Some winxp_32;
- "vioserial/xp/x86/vioser.inf", Some winxp_32;
- "vioserial/xp/x86/vioser.pdb", Some winxp_32;
- "vioserial/xp/x86/vioser.sys", Some winxp_32;
- "viostor/2k12/amd64/viostor.cat", Some win2k12_64;
- "viostor/2k12/amd64/viostor.inf", Some win2k12_64;
- "viostor/2k12/amd64/viostor.pdb", Some win2k12_64;
- "viostor/2k12/amd64/viostor.sys", Some win2k12_64;
- "viostor/2k12R2/amd64/viostor.cat", Some win2k12r2_64;
- "viostor/2k12R2/amd64/viostor.inf", Some win2k12r2_64;
- "viostor/2k12R2/amd64/viostor.pdb", Some win2k12r2_64;
- "viostor/2k12R2/amd64/viostor.sys", Some win2k12r2_64;
- "viostor/2k3/amd64/viostor.cat", Some win2k3_64;
- "viostor/2k3/amd64/viostor.inf", Some win2k3_64;
- "viostor/2k3/amd64/viostor.pdb", Some win2k3_64;
- "viostor/2k3/amd64/viostor.sys", Some win2k3_64;
- "viostor/2k3/x86/viostor.cat", Some win2k3_32;
- "viostor/2k3/x86/viostor.inf", Some win2k3_32;
- "viostor/2k3/x86/viostor.pdb", Some win2k3_32;
- "viostor/2k3/x86/viostor.sys", Some win2k3_32;
- "viostor/2k8/amd64/viostor.cat", Some win2k8_64;
- "viostor/2k8/amd64/viostor.inf", Some win2k8_64;
- "viostor/2k8/amd64/viostor.pdb", Some win2k8_64;
- "viostor/2k8/amd64/viostor.sys", Some win2k8_64;
- "viostor/2k8/x86/viostor.cat", Some win2k8_32;
- "viostor/2k8/x86/viostor.inf", Some win2k8_32;
- "viostor/2k8/x86/viostor.pdb", Some win2k8_32;
- "viostor/2k8/x86/viostor.sys", Some win2k8_32;
- "viostor/2k8R2/amd64/viostor.cat", Some win2k8r2_64;
- "viostor/2k8R2/amd64/viostor.inf", Some win2k8r2_64;
- "viostor/2k8R2/amd64/viostor.pdb", Some win2k8r2_64;
- "viostor/2k8R2/amd64/viostor.sys", Some win2k8r2_64;
- "viostor/w7/amd64/viostor.cat", Some win7_64;
- "viostor/w7/amd64/viostor.inf", Some win7_64;
- "viostor/w7/amd64/viostor.pdb", Some win7_64;
- "viostor/w7/amd64/viostor.sys", Some win7_64;
- "viostor/w7/x86/viostor.cat", Some win7_32;
- "viostor/w7/x86/viostor.inf", Some win7_32;
- "viostor/w7/x86/viostor.pdb", Some win7_32;
- "viostor/w7/x86/viostor.sys", Some win7_32;
- "viostor/w8.1/amd64/viostor.cat", Some win8_1_64;
- "viostor/w8.1/amd64/viostor.inf", Some win8_1_64;
- "viostor/w8.1/amd64/viostor.pdb", Some win8_1_64;
- "viostor/w8.1/amd64/viostor.sys", Some win8_1_64;
- "viostor/w8.1/x86/viostor.cat", Some win8_1_32;
- "viostor/w8.1/x86/viostor.inf", Some win8_1_32;
- "viostor/w8.1/x86/viostor.pdb", Some win8_1_32;
- "viostor/w8.1/x86/viostor.sys", Some win8_1_32;
- "viostor/w8/amd64/viostor.cat", Some win8_64;
- "viostor/w8/amd64/viostor.inf", Some win8_64;
- "viostor/w8/amd64/viostor.pdb", Some win8_64;
- "viostor/w8/amd64/viostor.sys", Some win8_64;
- "viostor/w8/x86/viostor.cat", Some win8_32;
- "viostor/w8/x86/viostor.inf", Some win8_32;
- "viostor/w8/x86/viostor.pdb", Some win8_32;
- "viostor/w8/x86/viostor.sys", Some win8_32;
- "viostor/xp/x86/viostor.cat", Some winxp_32;
- "viostor/xp/x86/viostor.inf", Some winxp_32;
- "viostor/xp/x86/viostor.pdb", Some winxp_32;
- "viostor/xp/x86/viostor.sys", Some winxp_32;
- "virtio-win-1.7.4_amd64.vfd", None;
- "virtio-win-1.7.4_x86.vfd", None;
- "virtio-win_license.txt", None;
+ (* Paths relative to $srcdir/test-data/fake-virtio-win. *)
+ "cd/Balloon/2k12/amd64/balloon.inf", Some win2k12_64;
+ "cd/Balloon/2k12R2/amd64/balloon.inf", Some win2k12r2_64;
+ "cd/Balloon/2k3/amd64/balloon.inf", Some win2k3_64;
+ "cd/Balloon/2k3/x86/balloon.inf", Some win2k3_32;
+ "cd/Balloon/2k8/amd64/balloon.inf", Some win2k8_64;
+ "cd/Balloon/2k8/x86/balloon.inf", Some win2k8_32;
+ "cd/Balloon/2k8R2/amd64/balloon.inf", Some win2k8r2_64;
+ "cd/Balloon/w7/amd64/balloon.inf", Some win7_64;
+ "cd/Balloon/w7/x86/balloon.inf", Some win7_32;
+ "cd/Balloon/w8.1/amd64/balloon.inf", Some win8_1_64;
+ "cd/Balloon/w8.1/x86/balloon.inf", Some win8_1_32;
+ "cd/Balloon/w8/amd64/balloon.inf", Some win8_64;
+ "cd/Balloon/w8/x86/balloon.inf", Some win8_32;
+ "cd/Balloon/xp/x86/balloon.inf", Some winxp_32;
+ "cd/NetKVM/2k12/amd64/netkvm.inf", Some win2k12_64;
+ "cd/NetKVM/2k12R2/amd64/netkvm.inf", Some win2k12r2_64;
+ "cd/NetKVM/2k3/amd64/netkvm.inf", Some win2k3_64;
+ "cd/NetKVM/2k3/x86/netkvm.inf", Some win2k3_32;
+ "cd/NetKVM/2k8/amd64/netkvm.inf", Some win2k8_64;
+ "cd/NetKVM/2k8/x86/netkvm.inf", Some win2k8_32;
+ "cd/NetKVM/2k8R2/amd64/netkvm.inf", Some win2k8r2_64;
+ "cd/NetKVM/w7/amd64/netkvm.inf", Some win7_64;
+ "cd/NetKVM/w7/x86/netkvm.inf", Some win7_32;
+ "cd/NetKVM/w8.1/amd64/netkvm.inf", Some win8_1_64;
+ "cd/NetKVM/w8.1/x86/netkvm.inf", Some win8_1_32;
+ "cd/NetKVM/w8/amd64/netkvm.inf", Some win8_64;
+ "cd/NetKVM/w8/x86/netkvm.inf", Some win8_32;
+ "cd/NetKVM/xp/x86/netkvm.inf", Some winxp_32;
+ "cd/qemupciserial/qemupciserial.inf", None;
+ "cd/viorng/2k12/amd64/viorng.inf", Some win2k12_64;
+ "cd/viorng/2k12R2/amd64/viorng.inf", Some win2k12r2_64;
+ "cd/viorng/2k8/amd64/viorng.inf", Some win2k8_64;
+ "cd/viorng/2k8/x86/viorng.inf", Some win2k8_32;
+ "cd/viorng/2k8R2/amd64/viorng.inf", Some win2k8r2_64;
+ "cd/viorng/w7/amd64/viorng.inf", Some win7_64;
+ "cd/viorng/w7/x86/viorng.inf", Some win7_32;
+ "cd/viorng/w8.1/amd64/viorng.inf", Some win8_1_64;
+ "cd/viorng/w8.1/x86/viorng.inf", Some win8_1_32;
+ "cd/viorng/w8/amd64/viorng.inf", Some win8_64;
+ "cd/viorng/w8/x86/viorng.inf", Some win8_32;
+ "cd/vioscsi/2k12/amd64/vioscsi.inf", Some win2k12_64;
+ "cd/vioscsi/2k12R2/amd64/vioscsi.inf", Some win2k12r2_64;
+ "cd/vioscsi/2k8/amd64/vioscsi.inf", Some win2k8_64;
+ "cd/vioscsi/2k8/x86/vioscsi.inf", Some win2k8_32;
+ "cd/vioscsi/2k8R2/amd64/vioscsi.inf", Some win2k8r2_64;
+ "cd/vioscsi/w7/amd64/vioscsi.inf", Some win7_64;
+ "cd/vioscsi/w7/x86/vioscsi.inf", Some win7_32;
+ "cd/vioscsi/w8.1/amd64/vioscsi.inf", Some win8_1_64;
+ "cd/vioscsi/w8.1/x86/vioscsi.inf", Some win8_1_32;
+ "cd/vioscsi/w8/amd64/vioscsi.inf", Some win8_64;
+ "cd/vioscsi/w8/x86/vioscsi.inf", Some win8_32;
+ "cd/vioserial/2k12/amd64/vioser.inf", Some win2k12_64;
+ "cd/vioserial/2k12R2/amd64/vioser.inf", Some win2k12r2_64;
+ "cd/vioserial/2k3/amd64/vioser.inf", Some win2k3_64;
+ "cd/vioserial/2k3/x86/vioser.inf", Some win2k3_32;
+ "cd/vioserial/2k8/amd64/vioser.inf", Some win2k8_64;
+ "cd/vioserial/2k8/x86/vioser.inf", Some win2k8_32;
+ "cd/vioserial/2k8R2/amd64/vioser.inf", Some win2k8r2_64;
+ "cd/vioserial/w7/amd64/vioser.inf", Some win7_64;
+ "cd/vioserial/w7/x86/vioser.inf", Some win7_32;
+ "cd/vioserial/w8.1/amd64/vioser.inf", Some win8_1_64;
+ "cd/vioserial/w8.1/x86/vioser.inf", Some win8_1_32;
+ "cd/vioserial/w8/amd64/vioser.inf", Some win8_64;
+ "cd/vioserial/w8/x86/vioser.inf", Some win8_32;
+ "cd/vioserial/w8/x86/vioser.pdb", Some win8_32;
+ "cd/vioserial/xp/x86/vioser.inf", Some winxp_32;
+ "cd/viostor/2k12/amd64/viostor.inf", Some win2k12_64;
+ "cd/viostor/2k12R2/amd64/viostor.inf", Some win2k12r2_64;
+ "cd/viostor/2k3/amd64/viostor.inf", Some win2k3_64;
+ "cd/viostor/2k3/x86/viostor.inf", Some win2k3_32;
+ "cd/viostor/2k8/amd64/viostor.inf", Some win2k8_64;
+ "cd/viostor/2k8/x86/viostor.inf", Some win2k8_32;
+ "cd/viostor/2k8R2/amd64/viostor.inf", Some win2k8r2_64;
+ "cd/viostor/w7/amd64/viostor.inf", Some win7_64;
+ "cd/viostor/w7/x86/viostor.inf", Some win7_32;
+ "cd/viostor/w8.1/amd64/viostor.inf", Some win8_1_64;
+ "cd/viostor/w8.1/x86/viostor.inf", Some win8_1_32;
+ "cd/viostor/w8/amd64/viostor.inf", Some win8_64;
+ "cd/viostor/w8/x86/viostor.inf", Some win8_32;
+ "cd/viostor/xp/x86/viostor.inf", Some winxp_32;
- (* Paths from the unpacked virtio-win 1.7.4 directory. *)
- "virtio-win-1.7.4.iso", None;
- "virtio-win-1.7.4_amd64.vfd", None;
- "guest-agent/qemu-ga-x86.msi", None;
- "guest-agent/qemu-ga-x64.msi", None;
"drivers/i386/Win8.1/viostor.inf", Some win8_1_32;
- "drivers/i386/Win8.1/viostor.sys", Some win8_1_32;
- "drivers/i386/Win8.1/vioscsi.cat", Some win8_1_32;
"drivers/i386/Win8.1/netkvm.inf", Some win8_1_32;
- "drivers/i386/Win8.1/netkvm.sys", Some win8_1_32;
- "drivers/i386/Win8.1/viostor.cat", Some win8_1_32;
- "drivers/i386/Win8.1/vioscsi.sys", Some win8_1_32;
- "drivers/i386/Win8.1/netkvm.cat", Some win8_1_32;
"drivers/i386/Win8.1/vioscsi.inf", Some win8_1_32;
"drivers/i386/Win2008/viostor.inf", Some win2k8_32;
- "drivers/i386/Win2008/viostor.sys", Some win2k8_32;
- "drivers/i386/Win2008/vioscsi.cat", Some win2k8_32;
"drivers/i386/Win2008/netkvm.inf", Some win2k8_32;
- "drivers/i386/Win2008/netkvm.sys", Some win2k8_32;
- "drivers/i386/Win2008/viostor.cat", Some win2k8_32;
- "drivers/i386/Win2008/vioscsi.sys", Some win2k8_32;
- "drivers/i386/Win2008/netkvm.cat", Some win2k8_32;
"drivers/i386/Win2008/vioscsi.inf", Some win2k8_32;
"drivers/i386/Win7/viostor.inf", Some win7_32;
- "drivers/i386/Win7/viostor.sys", Some win7_32;
- "drivers/i386/Win7/qxldd.dll", None;
- "drivers/i386/Win7/qxl.sys", Some win7_32;
- "drivers/i386/Win7/vioscsi.cat", Some win7_32;
"drivers/i386/Win7/netkvm.inf", Some win7_32;
- "drivers/i386/Win7/netkvm.sys", Some win7_32;
- "drivers/i386/Win7/viostor.cat", Some win7_32;
"drivers/i386/Win7/qxl.inf", Some win7_32;
- "drivers/i386/Win7/vioscsi.sys", Some win7_32;
- "drivers/i386/Win7/qxl.cat", Some win7_32;
- "drivers/i386/Win7/netkvm.cat", Some win7_32;
"drivers/i386/Win7/vioscsi.inf", Some win7_32;
"drivers/i386/Win2003/viostor.inf", Some win2k3_32;
- "drivers/i386/Win2003/viostor.sys", Some win2k3_32;
"drivers/i386/Win2003/netkvm.inf", Some win2k3_32;
- "drivers/i386/Win2003/netkvm.sys", Some win2k3_32;
- "drivers/i386/Win2003/viostor.cat", Some win2k3_32;
- "drivers/i386/Win2003/netkvm.cat", Some win2k3_32;
"drivers/i386/Win8/viostor.inf", Some win8_32;
- "drivers/i386/Win8/viostor.sys", Some win8_32;
- "drivers/i386/Win8/vioscsi.cat", Some win8_32;
"drivers/i386/Win8/netkvm.inf", Some win8_32;
- "drivers/i386/Win8/netkvm.sys", Some win8_32;
- "drivers/i386/Win8/viostor.cat", Some win8_32;
- "drivers/i386/Win8/vioscsi.sys", Some win8_32;
- "drivers/i386/Win8/netkvm.cat", Some win8_32;
"drivers/i386/Win8/vioscsi.inf", Some win8_32;
"drivers/i386/WinXP/viostor.inf", Some winxp_32;
- "drivers/i386/WinXP/viostor.sys", Some winxp_32;
- "drivers/i386/WinXP/qxldd.dll", None;
- "drivers/i386/WinXP/qxl.sys", Some winxp_32;
"drivers/i386/WinXP/netkvm.inf", Some winxp_32;
- "drivers/i386/WinXP/netkvm.sys", Some winxp_32;
- "drivers/i386/WinXP/viostor.cat", Some winxp_32;
"drivers/i386/WinXP/qxl.inf", Some winxp_32;
- "drivers/i386/WinXP/qxl.cat", Some winxp_32;
- "drivers/i386/WinXP/netkvm.cat", Some winxp_32;
"drivers/amd64/Win8.1/viostor.inf", Some win8_1_64;
- "drivers/amd64/Win8.1/viostor.sys", Some win8_1_64;
- "drivers/amd64/Win8.1/vioscsi.cat", Some win8_1_64;
"drivers/amd64/Win8.1/netkvm.inf", Some win8_1_64;
- "drivers/amd64/Win8.1/netkvm.sys", Some win8_1_64;
- "drivers/amd64/Win8.1/viostor.cat", Some win8_1_64;
- "drivers/amd64/Win8.1/vioscsi.sys", Some win8_1_64;
- "drivers/amd64/Win8.1/netkvm.cat", Some win8_1_64;
"drivers/amd64/Win8.1/vioscsi.inf", Some win8_1_64;
"drivers/amd64/Win2008/viostor.inf", Some win2k8_64;
- "drivers/amd64/Win2008/viostor.sys", Some win2k8_64;
- "drivers/amd64/Win2008/vioscsi.cat", Some win2k8_64;
"drivers/amd64/Win2008/netkvm.inf", Some win2k8_64;
- "drivers/amd64/Win2008/netkvm.sys", Some win2k8_64;
- "drivers/amd64/Win2008/viostor.cat", Some win2k8_64;
- "drivers/amd64/Win2008/vioscsi.sys", Some win2k8_64;
- "drivers/amd64/Win2008/netkvm.cat", Some win2k8_64;
"drivers/amd64/Win2008/vioscsi.inf", Some win2k8_64;
"drivers/amd64/Win7/viostor.inf", Some win7_64;
- "drivers/amd64/Win7/viostor.sys", Some win7_64;
- "drivers/amd64/Win7/qxldd.dll", None;
- "drivers/amd64/Win7/qxl.sys", Some win7_64;
- "drivers/amd64/Win7/vioscsi.cat", Some win7_64;
"drivers/amd64/Win7/netkvm.inf", Some win7_64;
- "drivers/amd64/Win7/netkvm.sys", Some win7_64;
- "drivers/amd64/Win7/viostor.cat", Some win7_64;
"drivers/amd64/Win7/qxl.inf", Some win7_64;
- "drivers/amd64/Win7/vioscsi.sys", Some win7_64;
- "drivers/amd64/Win7/qxl.cat", Some win7_64;
- "drivers/amd64/Win7/netkvm.cat", Some win7_64;
"drivers/amd64/Win7/vioscsi.inf", Some win7_64;
"drivers/amd64/Win2003/viostor.inf", Some win2k3_64;
- "drivers/amd64/Win2003/viostor.sys", Some win2k3_64;
"drivers/amd64/Win2003/netkvm.inf", Some win2k3_64;
- "drivers/amd64/Win2003/netkvm.sys", Some win2k3_64;
- "drivers/amd64/Win2003/viostor.cat", Some win2k3_64;
- "drivers/amd64/Win2003/netkvm.cat", Some win2k3_64;
"drivers/amd64/Win8/viostor.inf", Some win8_64;
- "drivers/amd64/Win8/viostor.sys", Some win8_64;
- "drivers/amd64/Win8/vioscsi.cat", Some win8_64;
"drivers/amd64/Win8/netkvm.inf", Some win8_64;
- "drivers/amd64/Win8/netkvm.sys", Some win8_64;
- "drivers/amd64/Win8/viostor.cat", Some win8_64;
- "drivers/amd64/Win8/vioscsi.sys", Some win8_64;
- "drivers/amd64/Win8/netkvm.cat", Some win8_64;
"drivers/amd64/Win8/vioscsi.inf", Some win8_64;
"drivers/amd64/Win2012/viostor.inf", Some win2k12_64;
- "drivers/amd64/Win2012/viostor.sys", Some win2k12_64;
- "drivers/amd64/Win2012/vioscsi.cat", Some win2k12_64;
"drivers/amd64/Win2012/netkvm.inf", Some win2k12_64;
- "drivers/amd64/Win2012/netkvm.sys", Some win2k12_64;
- "drivers/amd64/Win2012/viostor.cat", Some win2k12_64;
- "drivers/amd64/Win2012/vioscsi.sys", Some win2k12_64;
- "drivers/amd64/Win2012/netkvm.cat", Some win2k12_64;
"drivers/amd64/Win2012/vioscsi.inf", Some win2k12_64;
"drivers/amd64/Win2008R2/viostor.inf", Some win2k8r2_64;
- "drivers/amd64/Win2008R2/viostor.sys", Some win2k8r2_64;
- "drivers/amd64/Win2008R2/qxldd.dll", None;
- "drivers/amd64/Win2008R2/qxl.sys", Some win2k8r2_64;
- "drivers/amd64/Win2008R2/vioscsi.cat", Some win2k8r2_64;
"drivers/amd64/Win2008R2/netkvm.inf", Some win2k8r2_64;
- "drivers/amd64/Win2008R2/netkvm.sys", Some win2k8r2_64;
- "drivers/amd64/Win2008R2/viostor.cat", Some win2k8r2_64;
"drivers/amd64/Win2008R2/qxl.inf", Some win2k8r2_64;
- "drivers/amd64/Win2008R2/vioscsi.sys", Some win2k8r2_64;
- "drivers/amd64/Win2008R2/qxl.cat", Some win2k8r2_64;
- "drivers/amd64/Win2008R2/netkvm.cat", Some win2k8r2_64;
"drivers/amd64/Win2008R2/vioscsi.inf", Some win2k8r2_64;
"drivers/amd64/Win2012R2/viostor.inf", Some win2k12r2_64;
- "drivers/amd64/Win2012R2/viostor.sys", Some win2k12r2_64;
- "drivers/amd64/Win2012R2/vioscsi.cat", Some win2k12r2_64;
"drivers/amd64/Win2012R2/netkvm.inf", Some win2k12r2_64;
- "drivers/amd64/Win2012R2/netkvm.sys", Some win2k12r2_64;
- "drivers/amd64/Win2012R2/viostor.cat", Some win2k12r2_64;
- "drivers/amd64/Win2012R2/vioscsi.sys", Some win2k12r2_64;
- "drivers/amd64/Win2012R2/netkvm.cat", Some win2k12r2_64;
"drivers/amd64/Win2012R2/vioscsi.inf", Some win2k12r2_64;
- "virtio-win-1.7.4_x86.vfd", None;
] in
- (* Test each path against each version of Windows. *)
+ (* Test each inf file against each version of Windows. *)
let printer = string_of_bool in
List.iter (
fun (path, correct_windows) ->
+ let path = srcdir // ".." // "test-data" //
"fake-virtio-win" // path in
+
match correct_windows with
| None ->
List.iter (
fun win ->
let msg = sprintf "path %s should not match %s"
path win.i_product_name in
+ let content = read_whole_file path in
assert_equal ~printer ~msg false
- (Windows.UNIT_TESTS.virtio_iso_path_matches_guest_os path win)
+ (Windows.UNIT_TESTS.virtio_inf_matches_guest_os content path
win)
) all_windows
| Some correct_windows ->
List.iter (
@@ -859,8 +417,9 @@ let test_virtio_iso_path_matches_guest_os ctx
else
sprintf "path %s should not match %s"
path win.i_product_name in
+ let content = read_whole_file path in
assert_equal ~printer ~msg expected
- (Windows.UNIT_TESTS.virtio_iso_path_matches_guest_os path win)
+ (Windows.UNIT_TESTS.virtio_inf_matches_guest_os content path
win)
) all_windows
) paths
@@ -872,8 +431,8 @@ let suite "Utils.drive_name" >::
test_drive_name;
"Utils.drive_index" >:: test_drive_index;
"Windows_inf.of_string" >:: test_windows_inf_of_string;
- "Windows.virtio_iso_path_matches_guest_os" >::
- test_virtio_iso_path_matches_guest_os;
+ "Windows.virtio_inf_matches_guest_os" >::
+ test_virtio_inf_matches_guest_os;
]
let () diff --git a/v2v/windows.ml b/v2v/windows.ml
index 6503b57..2e18307 100644
--- a/v2v/windows.ml
+++ b/v2v/windows.ml
@@ -50,128 +50,185 @@ and (=~) str rex (* Copy the matching drivers to the
driverdir; return true if any have
* been copied.
*)
+type virtio_win_source + | Virtio_Win_Directory
+ | Virtio_Win_ISO of Guestfs.guestfs
+
let rec copy_virtio_drivers g inspect virtio_win driverdir - let ret = ref
false in
- if is_directory virtio_win then (
- let cmd = sprintf "cd %s && find -type f" (quote
virtio_win) in
- let paths = external_command cmd in
- List.iter (
- fun path ->
- if virtio_iso_path_matches_guest_os path inspect then (
- let source = virtio_win // path in
- let target = driverdir //
- String.lowercase_ascii (Filename.basename path) in
- if verbose () then
- printf "Copying virtio driver bits: 'host:%s' ->
'%s'\n"
- source target;
-
- g#write target (read_whole_file source);
- ret := true
- )
- ) paths
- )
- else if is_regular_file virtio_win then (
- try
- let g2 = open_guestfs ~identifier:"virtio_win" () in
- g2#add_drive_opts virtio_win ~readonly:true;
- g2#launch ();
- let vio_root = "/" in
- g2#mount_ro "/dev/sda" vio_root;
- let paths = g2#find vio_root in
- Array.iter (
- fun path ->
- let source = vio_root // path in
- if g2#is_file source ~followsymlinks:false &&
- virtio_iso_path_matches_guest_os path inspect then (
- let target = driverdir //
- String.lowercase_ascii (Filename.basename path) in
- if verbose () then
- printf "Copying virtio driver bits: '%s:%s' ->
'%s'\n"
- virtio_win path target;
-
- g#write target (g2#read_file source);
- ret := true
- )
- ) paths;
- g2#close()
- with Guestfs.Error msg ->
- error (f_"%s: cannot open virtio-win ISO file: %s") virtio_win
msg
- );
- !ret
-
-(* Given a path of a file relative to the root of the directory tree
- * with virtio-win drivers, figure out if it's suitable for the
- * specific Windows flavor of the current guest.
+ (* Does $VIRTIO_WIN point to a directory or an ISO file? *)
+ let virtio_win_source + if is_directory virtio_win then
+ Some Virtio_Win_Directory
+ else if is_regular_file virtio_win then (
+ try
+ let g2 = open_guestfs ~identifier:"virtio_win" () in
+ g2#add_drive_opts virtio_win ~readonly:true;
+ g2#launch ();
+ g2#mount_ro "/dev/sda" "/";
+ Some (Virtio_Win_ISO g2)
+ with Guestfs.Error msg ->
+ error (f_"%s: cannot open virtio-win ISO file: %s")
virtio_win msg
+ ) else
+ None in
+
+ match virtio_win_source with
+ | None ->
+ (* [$VIRTIO_WIN] does not point to a directory or regular file. This
+ * is not an error, but at the same time, no drivers were copied
+ * so we return [false] here.
+ *)
+ false
+
+ | Some virtio_win_source ->
+ (* Find and load all the *.inf files from the virtio-win directory
+ * or ISO. Returns a list of pairs [(inf_content, inf_name, directory)]
+ * where [inf_content] is the unparsed inf file, [inf_name] is a debug
+ * string we can use in error messages to refer to the inf file,
+ * and [directory] is a string used to track the directory containing
+ * the inf file.
+ *)
+ let inf_files : (string * string * string) list + match
virtio_win_source with
+ | Virtio_Win_Directory ->
+ let cmd + sprintf "find %s -name '*.inf'
-type f" (quote virtio_win) in
+ let paths = external_command cmd in
+ List.map (fun path ->
+ read_whole_file path, path, Filename.dirname path) paths
+ | Virtio_Win_ISO g2 ->
+ let paths = g2#find "/" in
+ let paths = Array.to_list paths in
+ let paths + List.filter (
+ fun path ->
+ String.is_suffix path ".inf" &&
+ g2#is_file path ~followsymlinks:false
+ ) paths in
+ List.map (
+ fun path ->
+ let path = "/" ^ path in
+ let i = String.rindex path '/' in
+ let dir = String.sub path 0 i in
+ g2#read_file path, sprintf "%s:%s" virtio_win path, dir
+ ) paths in
+
+ (* Get only the *.inf files which match the operating system. *)
+ let inf_files + List.filter (
+ fun (inf_content, inf_name, directory) ->
+ virtio_inf_matches_guest_os inf_content inf_name inspect
+ ) inf_files in
+
+ (* If a directory contains any matching *.inf file, then we will
+ * copy all the files from that directory. So get the unique list
+ * of directories that we will copy.
+ *)
+ let directories = List.map (fun (_,_,dir) -> dir) inf_files in
+ let directories = sort_uniq directories in
+
+ (* Copy the directories. *)
+ List.iter (
+ fun dir ->
+ match virtio_win_source with
+ | Virtio_Win_Directory -> copy_host_directory dir g driverdir
+ | Virtio_Win_ISO g2 -> copy_iso_directory g2 dir g driverdir
+ ) directories;
+
+ (* Return true if some drivers were copied. *)
+ directories <> []
+
+(* Copy host files in same directory as inf_path to driverdir. *)
+and copy_host_directory dir g driverdir + g#copy_in dir driverdir
+
+(* Copy files from ISO in same directory as inf_path to driverdir. *)
+and copy_iso_directory g2 dir g driverdir + let files = g2#find dir in
+ let files = Array.to_list files in
+ assert (files <> []); (* at least the .inf file must be here *)
+
+ List.iter (
+ fun filename ->
+ let content = g2#read_file (dir ^ filename) in
+ g#write (driverdir ^ "/" ^ filename) content
+ ) files
+
+(* Given the content of a [*.inf] file from the virtio-win drivers,
+ * figure out if it's suitable for the specific Windows flavor of the
+ * current guest.
+ *)
+and virtio_inf_matches_guest_os inf_content inf_name inspect + let sections =
Windows_inf.of_string inf_content in
+
+ (* Try to find the [Version] / DriverVer. *)
+ let driver_ver = parse_driver_ver inf_name sections in
+
+ (* Try to find the [Manufacturer] line. *)
+ let driver_arch = parse_manufacturer inf_name sections in
+
+ (* If we got both, we can continue, else give up. *)
+ match driver_ver, driver_arch with
+ | None, None | Some _, None | None, Some _ -> false
+ | Some driver_ver, Some driver_arch ->
+ (* XXX This ignores i_product_variant. However that may not matter.
+ * There appears to be no material difference in the inf file.
+ *)
+ let { Types.i_major_version = major; i_minor_version = minor;
+ i_arch = arch } = inspect in
+
+ let ver = major * 10 + minor in
+
+ driver_ver = ver && driver_arch = arch
+
+(* Find the [Version] section in the [*.inf] file, and find the
+ * [DriverVer] from that, and parse it. Returns [None] if we couldn't
+ * find / parse it.
+ * Reference:
https://www.redhat.com/archives/libguestfs/2015-October/msg00352.html
*)
-and virtio_iso_path_matches_guest_os path inspect - let {
Types.i_major_version = os_major; i_minor_version = os_minor;
- i_arch = arch; i_product_variant = os_variant } = inspect in
+and parse_driver_ver inf_name sections try
- (* Lowercased path, since the ISO may contain upper or lowercase path
- * elements.
- *)
- let lc_path = String.lowercase_ascii path in
- let lc_basename = Filename.basename path in
-
- let extension - match last_part_of lc_basename '.' with
- | Some x -> x
- | None -> raise Not_found
- in
-
- (* Skip files without specific extensions. *)
- let extensions = ["cat"; "inf"; "pdb";
"sys"] in
- if not (List.mem extension extensions) then raise Not_found;
-
- (* Using the full path, work out what version of Windows
- * this driver is for. Paths can be things like:
- * "NetKVM/2k12R2/amd64/netkvm.sys" or
- * "./drivers/amd64/Win2012R2/netkvm.sys".
- * Note we check lowercase paths.
- *)
- let pathelem elem = String.find lc_path ("/" ^ elem ^
"/") >= 0 in
- let p_arch - if pathelem "x86" || pathelem "i386"
then "i386"
- else if pathelem "amd64" then "x86_64"
- else raise Not_found in
-
- let is_client os_variant = os_variant = "Client"
- and not_client os_variant = os_variant <> "Client"
- and any_variant os_variant = true in
- let p_os_major, p_os_minor, match_os_variant - if pathelem
"xp" || pathelem "winxp" then
- (5, 1, any_variant)
- else if pathelem "2k3" || pathelem "win2003" then
- (5, 2, any_variant)
- else if pathelem "vista" then
- (6, 0, is_client)
- else if pathelem "2k8" || pathelem "win2008" then
- (6, 0, not_client)
- else if pathelem "w7" || pathelem "win7" then
- (6, 1, is_client)
- else if pathelem "2k8r2" || pathelem "win2008r2" then
- (6, 1, not_client)
- else if pathelem "w8" || pathelem "win8" then
- (6, 2, is_client)
- else if pathelem "2k12" || pathelem "win2012" then
- (6, 2, not_client)
- else if pathelem "w8.1" || pathelem "win8.1" then
- (6, 3, is_client)
- else if pathelem "2k12r2" || pathelem "win2012r2"
then
- (6, 3, not_client)
- else if pathelem "w10" || pathelem "win10" then
- (10, 0, is_client)
- else
- raise Not_found in
-
- arch = p_arch && os_major = p_os_major && os_minor =
p_os_minor &&
- match_os_variant os_variant
-
- with Not_found -> false
+ let driver_ver = Windows_inf.find_key sections "Version"
"DriverVer" in
+ if Str.string_match driver_ver_rex driver_ver 0 then
+ Some (int_of_string (Str.matched_group 1 driver_ver))
+ else
+ raise Not_found
+ with
+ Not_found ->
+ warning (f_"%s: could not find or parse the [Version] DriverVer key
in the Windows inf file")
+ inf_name;
+ None
+
+and driver_ver_rex + Str.regexp "[0-9/]+,\\([0-9]+\\)"
+
+(* Find the [Manufacturer] section and try to find the first line.
+ * There is no consistent naming of this line unfortunately.
+ * Reference:
https://www.redhat.com/archives/libguestfs/2015-November/msg00065.html
+ *)
+and parse_manufacturer inf_name sections + try
+ let lines = Windows_inf.find_section sections "Manufacturer" in
+ match lines with
+ | [] -> raise Not_found
+ | (_, manufacturer) :: _ ->
+ if Str.string_match manufacturer_rex manufacturer 0 then (
+ let arch = Str.matched_group 1 manufacturer in
+ if arch = "x86" || arch = "X86" then Some
"i386" else Some "x86_64"
+ )
+ else
+ raise Not_found
+ with
+ Not_found ->
+ warning (f_"%s: could not find or parse the [Manufacturer] section
in the Windows inf file")
+ inf_name;
+ None
+
+and manufacturer_rex + Str.regexp_case_fold ".*,NT\\(x86\\|amd64\\)"
(* The following function is only exported for unit tests. *)
module UNIT_TESTS = struct
- let virtio_iso_path_matches_guest_os = virtio_iso_path_matches_guest_os
+ let virtio_inf_matches_guest_os = virtio_inf_matches_guest_os
end
(* This is a wrapper that handles opening and closing the hive
diff --git a/v2v/windows.mli b/v2v/windows.mli
index 863a605..4098b27 100644
--- a/v2v/windows.mli
+++ b/v2v/windows.mli
@@ -45,5 +45,5 @@ val get_node : Guestfs.guestfs -> int64 -> string list
-> int64 option
(* The following function is only exported for unit tests. *)
module UNIT_TESTS : sig
- val virtio_iso_path_matches_guest_os : string -> Types.inspect -> bool
+ val virtio_inf_matches_guest_os : string -> string -> Types.inspect
-> bool
end
--
2.5.0
Denis V. Lunev
2015-Nov-18 08:04 UTC
Re: [Libguestfs] [PATCH 0/3] v2v: windows: Use '*.inf' files to control how Windows drivers are installed.
On 11/18/2015 01:03 AM, Richard W.M. Jones wrote:> https://github.com/rwmjones/libguestfs/tree/rewrite-virtio-copy-drivers > > Instead of trying to split and parse elements from virtio-win paths, > use the '*.inf' files supplied with the drivers to control how Windows > drivers are installed. > > The following emails best explain how this works: > > https://www.redhat.com/archives/libguestfs/2015-October/msg00352.html > https://www.redhat.com/archives/libguestfs/2015-November/msg00065.html > > Currently the product variant (eg. client or server) is ignored (see > email I sent earlier today). > > There's actually a fourth patch which I didn't include, which just > adds the content of all of the *.inf files from the virtio-win 1.7.4 > ISO and directory, to test-data/fake-virtio-win. I didn't include it > because it's a big patch that's not very interesting, but you can get > it from the repo above. > > Rich. >adding roman to CC:
Denis V. Lunev
2015-Nov-18 08:05 UTC
Re: [Libguestfs] [PATCH 1/3] mllib: Add sort_uniq function.
On 11/18/2015 01:03 AM, Richard W.M. Jones wrote:> This is copied from supermin. > --- > mllib/common_utils.ml | 16 ++++++++++++++++ > mllib/common_utils.mli | 6 ++++++ > 2 files changed, 22 insertions(+) > > diff --git a/mllib/common_utils.ml b/mllib/common_utils.ml > index 13e9256..5fb7183 100644 > --- a/mllib/common_utils.ml > +++ b/mllib/common_utils.ml > @@ -267,6 +267,22 @@ let rec assoc ?(cmp = compare) ~default x = function > | (y, y') :: _ when cmp x y = 0 -> y' > | _ :: ys -> assoc ~cmp ~default x ys > > +let uniq ?(cmp = Pervasives.compare) xs > + let rec loop acc = function > + | [] -> acc > + | [x] -> x :: acc > + | x :: (y :: _ as xs) when cmp x y = 0 -> > + loop acc xs > + | x :: (y :: _ as xs) -> > + loop (x :: acc) xs > + in > + List.rev (loop [] xs) > + > +let sort_uniq ?(cmp = Pervasives.compare) xs > + let xs = List.sort cmp xs in > + let xs = uniq ~cmp xs in > + xs > + > let may f = function > | None -> () > | Some x -> f x > diff --git a/mllib/common_utils.mli b/mllib/common_utils.mli > index 44b8c93..68f7988 100644 > --- a/mllib/common_utils.mli > +++ b/mllib/common_utils.mli > @@ -124,6 +124,12 @@ val assoc : ?cmp:('a -> 'a -> int) -> default:'b -> 'a -> ('a * 'b) list -> 'b > (** Like {!List.assoc} but with a user-defined comparison function, and > instead of raising [Not_found], it returns the [~default] value. *) > > +val uniq : ?cmp:('a -> 'a -> int) -> 'a list -> 'a list > + (** Uniquify a list (the list must be sorted first). *) > + > +val sort_uniq : ?cmp:('a -> 'a -> int) -> 'a list -> 'a list > + (** Sort and uniquify a list. *) > + > val may : ('a -> unit) -> 'a option -> unit > (** [may f (Some x)] runs [f x]. [may f None] does nothing. *) >adding roman to CC:
Denis V. Lunev
2015-Nov-18 08:05 UTC
Re: [Libguestfs] [PATCH 2/3] v2v: windows: Add a Windows '*.inf' file parser.
On 11/18/2015 01:03 AM, Richard W.M. Jones wrote:> This simple parser has (limited) understanding of the Windows '*.inf' > file format. This is a Windows config file with some peculiarities. > > This commit also has a unit test. > --- > po/POTFILES-ml | 1 + > v2v/Makefile.am | 5 +- > v2v/v2v_unit_tests.ml | 104 +++++++++++++++++++++++++++++++++++- > v2v/windows_inf.ml | 143 ++++++++++++++++++++++++++++++++++++++++++++++++++ > v2v/windows_inf.mli | 58 ++++++++++++++++++++ > 5 files changed, 308 insertions(+), 3 deletions(-) > create mode 100644 v2v/windows_inf.ml > create mode 100644 v2v/windows_inf.mli > > diff --git a/po/POTFILES-ml b/po/POTFILES-ml > index c02ffc0..88db39b 100644 > --- a/po/POTFILES-ml > +++ b/po/POTFILES-ml > @@ -127,4 +127,5 @@ v2v/v2v.ml > v2v/v2v_unit_tests.ml > v2v/vCenter.ml > v2v/windows.ml > +v2v/windows_inf.ml > v2v/xml.ml > diff --git a/v2v/Makefile.am b/v2v/Makefile.am > index 5dfef6e..c46594c 100644 > --- a/v2v/Makefile.am > +++ b/v2v/Makefile.am > @@ -69,6 +69,7 @@ SOURCES_MLI = \ > utils.mli \ > vCenter.mli \ > windows.mli \ > + windows_inf.mli \ > xml.mli > > SOURCES_ML = \ > @@ -82,8 +83,9 @@ SOURCES_ML = \ > DOM.ml \ > changeuid.ml \ > OVF.ml \ > - linux.ml \ > + windows_inf.ml \ > windows.ml \ > + linux.ml \ > modules_list.ml \ > input_disk.ml \ > input_libvirtxml.ml \ > @@ -309,6 +311,7 @@ v2v_unit_tests_BOBJECTS = \ > utils.cmo \ > DOM.cmo \ > OVF.cmo \ > + windows_inf.cmo \ > windows.cmo \ > v2v_unit_tests.cmo > v2v_unit_tests_XOBJECTS = $(v2v_unit_tests_BOBJECTS:.cmo=.cmx) > diff --git a/v2v/v2v_unit_tests.ml b/v2v/v2v_unit_tests.ml > index a2dca32..169eea9 100644 > --- a/v2v/v2v_unit_tests.ml > +++ b/v2v/v2v_unit_tests.ml > @@ -18,13 +18,21 @@ > > (* This file tests individual virt-v2v functions. *) > > +open Printf > open OUnit2 > + > +open Common_utils > + > open Types > > -open Printf > - > external identity : 'a -> 'a = "%identity" > > +let (//) = Filename.concat > + > +let srcdir > + try Sys.getenv "srcdir" > + with Not_found -> failwith "environment variable $srcdir must be set" > + > let inspect_defaults = { > i_type = ""; i_distro = ""; i_arch = ""; > i_major_version = 0; i_minor_version = 0; > @@ -126,6 +134,97 @@ let test_drive_index ctx > assert_raises exn (fun () -> Utils.drive_index "Z"); > assert_raises exn (fun () -> Utils.drive_index "aB") > > +(* Test parsing a [*.inf] file. *) > +let test_windows_inf_of_string ctx > + let printer = Windows_inf.to_string in > + > + (* There is nothing special about this choice. It is just a driver > + * [*.inf] file picked at random. > + *) > + let path = srcdir // ".." // "test-data" // "fake-virtio-win" // > + "cd" // "Balloon" // "2k12" // "amd64" // "balloon.inf" in > + > + let sections = Windows_inf.load path in > + > + let expected = [ > + "version", [ > + "signature", "\"$WINDOWS NT$\""; > + "class", "System"; > + "classguid", "{4d36e97d-e325-11ce-bfc1-08002be10318}"; > + "provider", "%RHEL%"; > + "driverver", "12/04/2014,62.71.104.9600"; > + "catalogfile", "Balloon.cat"; > + "driverpackagetype", "PlugAndPlay"; > + "driverpackagedisplayname", "%BALLOON.DeviceDesc%"; > + "pnplockdown", "1"; > + ]; > + "destinationdirs", [ > + "defaultdestdir", "12"; > + ]; > + "sourcedisksnames", [ > + "1", "%DiskId1%,,,\"\""; > + ]; > + "sourcedisksfiles", [ > + "balloon.sys", "1,,"; > + ]; > + "manufacturer", [ > + "%rhel%", "Standard,NTamd64"; > + ]; > + "standard", [ > + "%balloon.devicedesc%", "BALLOON_Device, PCI\\VEN_1AF4&DEV_1002&SUBSYS_00051AF4&REV_00"; > + ]; > + "standard.ntamd64", [ > + "%balloon.devicedesc%", "BALLOON_Device, PCI\\VEN_1AF4&DEV_1002&SUBSYS_00051AF4&REV_00"; > + ]; > + "balloon_device.nt", [ > + "copyfiles", "Drivers_Dir"; > + ]; > + "drivers_dir", []; > + "balloon_device.nt.services", [ > + "addservice", "BALLOON,%SPSVCINST_ASSOCSERVICE%, BALLOON_Service_Inst, BALLOON_Logging_Inst"; > + ]; > + "balloon_service_inst", [ > + "displayname", "%BALLOON.SVCDESC%"; > + "servicetype", "1"; > + "starttype", "3"; > + "errorcontrol", "1"; > + "servicebinary", "%12%\\balloon.sys"; > + ]; > + "balloon_logging_inst", [ > + "addreg", "BALLOON_Logging_Inst_AddReg"; > + ]; > + "balloon_logging_inst_addreg", []; > + "destinationdirs", [ > + "balloon_device_coinstaller_copyfiles", "11"; > + ]; > + "balloon_device.nt.coinstallers", [ > + "addreg", "BALLOON_Device_CoInstaller_AddReg"; > + "copyfiles", "BALLOON_Device_CoInstaller_CopyFiles"; > + ]; > + "balloon_device_coinstaller_addreg", []; > + "balloon_device_coinstaller_copyfiles", []; > + "sourcedisksfiles", [ > + "wdfcoinstaller01011.dll", "1"; > + ]; > + "balloon_device.nt.wdf", [ > + "kmdfservice", "BALLOON, BALLOON_wdfsect"; > + ]; > + "balloon_wdfsect", [ > + "kmdflibraryversion", "1.11"; > + ]; > + "strings", [ > + "spsvcinst_assocservice", "0x00000002"; > + "rhel", "\"Red Hat, Inc.\""; > + "diskid1", "\"VirtIO Balloon Installation Disk #1\""; > + "balloon.devicedesc", "\"VirtIO Balloon Driver\""; > + "balloon.svcdesc", "\"VirtIO Balloon Service\""; > + "classname", "\"VirtIO Balloon Device\""; > + ]; > + ] in > + > + assert_equal ~printer expected sections > + > +(* Test the code which matches [*.inf] files to Windows guests. *) > let test_virtio_iso_path_matches_guest_os ctx > (* Windows OSes fake inspection data. *) > let make_win name major minor variant arch = { > @@ -772,6 +871,7 @@ let suite > "OVF.get_ostype" >:: test_get_ostype; > "Utils.drive_name" >:: test_drive_name; > "Utils.drive_index" >:: test_drive_index; > + "Windows_inf.of_string" >:: test_windows_inf_of_string; > "Windows.virtio_iso_path_matches_guest_os" >:: > test_virtio_iso_path_matches_guest_os; > ] > diff --git a/v2v/windows_inf.ml b/v2v/windows_inf.ml > new file mode 100644 > index 0000000..2066a2e > --- /dev/null > +++ b/v2v/windows_inf.ml > @@ -0,0 +1,143 @@ > +(* virt-v2v > + * Copyright (C) 2015 Red Hat Inc. > + * > + * This program is free software; you can redistribute it and/or modify > + * it under the terms of the GNU General Public License as published by > + * the Free Software Foundation; either version 2 of the License, or > + * (at your option) any later version. > + * > + * This program is distributed in the hope that it will be useful, > + * but WITHOUT ANY WARRANTY; without even the implied warranty of > + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > + * GNU General Public License for more details. > + * > + * You should have received a copy of the GNU General Public License along > + * with this program; if not, write to the Free Software Foundation, Inc., > + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. > + *) > + > +open Printf > + > +open Common_utils > + > +type t = section list > +and section = string * data list > +and data = string * string > + > +let crlf_rex = Str.regexp "\r?\n" > + > +(* Match [[header]] in a Windows [*.inf] file. *) > +let section_header_rex > + Str.regexp "^[ \t]*\\[[ \t]*\\(.*\\)[ \t]*\\][ \t]*$" > + > +let match_section_header line = Str.string_match section_header_rex line 0 > +let not_section_header line = not (match_section_header line) > + > +(* Match [key = value] in a Windows [*.inf] file. *) > +let key_value_rex > + Str.regexp_case_fold > + "^[ \t]*\\([a-z0-9%_.]+\\)[ \t]*=[ \t]*\\(.*\\)[ \t]*$" > + > +(* Match comment preceeded by whitespace (so comments can be removed). *) > +let comment_rex = Str.regexp "[ \t]*;.*" > + > +(* Parse a Windows [*.inf] file into headers and section lines. *) > +let of_string content > + (* Split up the inf file (possibly with DOS line endings) into lines. *) > + let lines = Str.split crlf_rex content in > + > + (* Split the file into section headers + section content. *) > + let rec loop = function > + | [] -> [] > + | header :: xs when match_section_header header -> > + let header = Str.matched_group 1 header in > + let lines = takewhile not_section_header xs in > + let ys = dropwhile not_section_header xs in > + (header, lines) :: loop ys > + | xs -> > + (* Put all initial lines before the first section into a > + * section with no name. > + *) > + let lines = takewhile not_section_header xs in > + let ys = dropwhile not_section_header xs in > + ("", lines) :: loop ys > + in > + let sections = loop lines in > + > + (* Split the lines that match "key = value" into [(key, value)] pairs. > + * Ignore any other lines. > + *) > + let sections = List.map ( > + fun (header, lines) -> > + let lines = filter_map ( > + fun line -> > + if Str.string_match key_value_rex line 0 then ( > + let key = Str.matched_group 1 line in > + let value = Str.matched_group 2 line in > + Some (key, value) > + ) > + else None (* ignore the non-matching line *) > + ) lines in > + header, lines > + ) sections in > + > + (* If the dummy section at the beginning is now completely empty, > + * remove it. > + *) > + let sections > + match sections with > + | ("", []) :: sections -> sections > + | sections -> sections in > + > + (* Remove any comments from values, conservatively though because > + * we don't really understand the value format. > + *) > + let sections = List.map ( > + fun (header, lines) -> > + let lines = List.map ( > + fun (key, value) -> > + let value > + if String.contains value '"' then value > + else Str.replace_first comment_rex "" value in > + key, value > + ) lines in > + header, lines > + ) sections in > + > + (* Normalize (by lowercasing) the section headers and keys (but not > + * the values). > + *) > + let sections = List.map ( > + fun (header, lines) -> > + let header = String.lowercase_ascii header in > + let lines = List.map ( > + fun (key, value) -> > + String.lowercase_ascii key, value > + ) lines in > + header, lines > + ) sections in > + > + sections > + > +let find_section t section_name > + let section_name = String.lowercase_ascii section_name in > + List.assoc section_name t > + > +let find_key t section_name key_name > + let data = find_section t section_name in > + let key_name = String.lowercase_ascii key_name in > + List.assoc key_name data > + > +let load filename > + of_string (read_whole_file filename) > + > +let rec to_string sections > + String.concat "\n" (List.map string_of_section sections) > + > +and string_of_section (header, body) > + let header = sprintf "[%s]" header in > + let body = List.map string_of_key_value body in > + String.concat "\n" (header :: body) > + > +and string_of_key_value (key, value) > + sprintf "%s = %s" key value > diff --git a/v2v/windows_inf.mli b/v2v/windows_inf.mli > new file mode 100644 > index 0000000..1cb8040 > --- /dev/null > +++ b/v2v/windows_inf.mli > @@ -0,0 +1,58 @@ > +(* virt-v2v > + * Copyright (C) 2009-2015 Red Hat Inc. > + * > + * This program is free software; you can redistribute it and/or modify > + * it under the terms of the GNU General Public License as published by > + * the Free Software Foundation; either version 2 of the License, or > + * (at your option) any later version. > + * > + * This program is distributed in the hope that it will be useful, > + * but WITHOUT ANY WARRANTY; without even the implied warranty of > + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > + * GNU General Public License for more details. > + * > + * You should have received a copy of the GNU General Public License along > + * with this program; if not, write to the Free Software Foundation, Inc., > + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. > + *) > + > +(** Handle Windows driver [*.inf] files. *) > + > +type t = section list > +(** Type of a parsed Windows driver [*.inf] file. *) > + > +and section = string * data list > +(** A single section consists of a header and a list of lines. If > + the file doesn't start with a section header, then the initial > + section has a dummy header name [""]. > + > + The section header is always normalized to lowercase ASCII. *) > + > +and data = string * string > +(** A [key = value] pair appearing within a section body. The key > + (but {i not} the value) is always normalized to lowercase ASCII. *) > + > +val of_string : string -> t > +(** Parse an [*.inf] file from the string. No parse errors are > + possible since this parser accepts anything as a possible [*.inf] > + file. *) > + > +val load : string -> t > +(** Same as {!of_string} except we load the content from > + a host file. *) > + > +val to_string : t -> string > +(** Convert an inf file back to a string. This should probably only > + be used for debugging, since we don't preserve comments and it's > + not tested that Windows would be able to parse what we write out. *) > + > +val find_section : t -> string -> data list > +(** [find_section t section_name] finds and returns a section by name. > + > + Raises [Not_found] if not found. *) > + > +val find_key : t -> string -> string -> string > +(** [find_key t section_name key_name] finds and returns a key within > + a particular section. > + > + Raises [Not_found] if not found. *)adding roman to CC:
Denis V. Lunev
2015-Nov-18 08:05 UTC
Re: [Libguestfs] [PATCH 3/3] v2v: windows: Use '*.inf' files to control how Windows drivers are installed.
On 11/18/2015 01:03 AM, Richard W.M. Jones wrote:> Instead of trying to split and parse elements from virtio-win paths, > use the '*.inf' files supplied with the drivers to control how Windows > drivers are installed. > > The following emails best explain how this works: > > https://www.redhat.com/archives/libguestfs/2015-October/msg00352.html > https://www.redhat.com/archives/libguestfs/2015-November/msg00065.html > > Currently the product variant (eg. client or server) is ignored. > --- > v2v/v2v_unit_tests.ml | 623 ++++++++------------------------------------------ > v2v/windows.ml | 289 +++++++++++++---------- > v2v/windows.mli | 2 +- > 3 files changed, 265 insertions(+), 649 deletions(-) > > diff --git a/v2v/v2v_unit_tests.ml b/v2v/v2v_unit_tests.ml > index 169eea9..5cc1f3e 100644 > --- a/v2v/v2v_unit_tests.ml > +++ b/v2v/v2v_unit_tests.ml > @@ -225,7 +225,7 @@ let test_windows_inf_of_string ctx > assert_equal ~printer expected sections > > (* Test the code which matches [*.inf] files to Windows guests. *) > -let test_virtio_iso_path_matches_guest_os ctx > +let test_virtio_inf_matches_guest_os ctx > (* Windows OSes fake inspection data. *) > let make_win name major minor variant arch = { > inspect_defaults with > @@ -262,591 +262,149 @@ let test_virtio_iso_path_matches_guest_os ctx > ] in > > let paths = [ > - (* Paths from the virtio-win 1.7.4 ISO. *) > - "Balloon/2k12/amd64/WdfCoInstaller01011.dll", None; > - "Balloon/2k12/amd64/balloon.cat", Some win2k12_64; > - "Balloon/2k12/amd64/balloon.inf", Some win2k12_64; > - "Balloon/2k12/amd64/balloon.pdb", Some win2k12_64; > - "Balloon/2k12/amd64/balloon.sys", Some win2k12_64; > - "Balloon/2k12/amd64/blnsvr.exe", None; > - "Balloon/2k12/amd64/blnsvr.pdb", Some win2k12_64; > - "Balloon/2k12R2/amd64/WdfCoInstaller01011.dll", None; > - "Balloon/2k12R2/amd64/balloon.cat", Some win2k12r2_64; > - "Balloon/2k12R2/amd64/balloon.inf", Some win2k12r2_64; > - "Balloon/2k12R2/amd64/balloon.pdb", Some win2k12r2_64; > - "Balloon/2k12R2/amd64/balloon.sys", Some win2k12r2_64; > - "Balloon/2k12R2/amd64/blnsvr.exe", None; > - "Balloon/2k12R2/amd64/blnsvr.pdb", Some win2k12r2_64; > - "Balloon/2k3/amd64/WdfCoInstaller01009.dll", None; > - "Balloon/2k3/amd64/balloon.cat", Some win2k3_64; > - "Balloon/2k3/amd64/balloon.inf", Some win2k3_64; > - "Balloon/2k3/amd64/balloon.pdb", Some win2k3_64; > - "Balloon/2k3/amd64/balloon.sys", Some win2k3_64; > - "Balloon/2k3/amd64/blnsvr.exe", None; > - "Balloon/2k3/amd64/blnsvr.pdb", Some win2k3_64; > - "Balloon/2k3/x86/WdfCoInstaller01009.dll", None; > - "Balloon/2k3/x86/balloon.cat", Some win2k3_32; > - "Balloon/2k3/x86/balloon.inf", Some win2k3_32; > - "Balloon/2k3/x86/balloon.pdb", Some win2k3_32; > - "Balloon/2k3/x86/balloon.sys", Some win2k3_32; > - "Balloon/2k3/x86/blnsvr.exe", None; > - "Balloon/2k3/x86/blnsvr.pdb", Some win2k3_32; > - "Balloon/2k8/amd64/WdfCoInstaller01009.dll", None; > - "Balloon/2k8/amd64/balloon.cat", Some win2k8_64; > - "Balloon/2k8/amd64/balloon.inf", Some win2k8_64; > - "Balloon/2k8/amd64/balloon.pdb", Some win2k8_64; > - "Balloon/2k8/amd64/balloon.sys", Some win2k8_64; > - "Balloon/2k8/amd64/blnsvr.exe", None; > - "Balloon/2k8/amd64/blnsvr.pdb", Some win2k8_64; > - "Balloon/2k8/x86/WdfCoInstaller01009.dll", None; > - "Balloon/2k8/x86/balloon.cat", Some win2k8_32; > - "Balloon/2k8/x86/balloon.inf", Some win2k8_32; > - "Balloon/2k8/x86/balloon.pdb", Some win2k8_32; > - "Balloon/2k8/x86/balloon.sys", Some win2k8_32; > - "Balloon/2k8/x86/blnsvr.exe", None; > - "Balloon/2k8/x86/blnsvr.pdb", Some win2k8_32; > - "Balloon/2k8R2/amd64/WdfCoInstaller01009.dll", None; > - "Balloon/2k8R2/amd64/balloon.cat", Some win2k8r2_64; > - "Balloon/2k8R2/amd64/balloon.inf", Some win2k8r2_64; > - "Balloon/2k8R2/amd64/balloon.pdb", Some win2k8r2_64; > - "Balloon/2k8R2/amd64/balloon.sys", Some win2k8r2_64; > - "Balloon/2k8R2/amd64/blnsvr.exe", None; > - "Balloon/2k8R2/amd64/blnsvr.pdb", Some win2k8r2_64; > - "Balloon/w7/amd64/WdfCoInstaller01009.dll", None; > - "Balloon/w7/amd64/balloon.cat", Some win7_64; > - "Balloon/w7/amd64/balloon.inf", Some win7_64; > - "Balloon/w7/amd64/balloon.pdb", Some win7_64; > - "Balloon/w7/amd64/balloon.sys", Some win7_64; > - "Balloon/w7/amd64/blnsvr.exe", None; > - "Balloon/w7/amd64/blnsvr.pdb", Some win7_64; > - "Balloon/w7/x86/WdfCoInstaller01009.dll", None; > - "Balloon/w7/x86/balloon.cat", Some win7_32; > - "Balloon/w7/x86/balloon.inf", Some win7_32; > - "Balloon/w7/x86/balloon.pdb", Some win7_32; > - "Balloon/w7/x86/balloon.sys", Some win7_32; > - "Balloon/w7/x86/blnsvr.exe", None; > - "Balloon/w7/x86/blnsvr.pdb", Some win7_32; > - "Balloon/w8.1/amd64/WdfCoInstaller01011.dll", None; > - "Balloon/w8.1/amd64/balloon.cat", Some win8_1_64; > - "Balloon/w8.1/amd64/balloon.inf", Some win8_1_64; > - "Balloon/w8.1/amd64/balloon.pdb", Some win8_1_64; > - "Balloon/w8.1/amd64/balloon.sys", Some win8_1_64; > - "Balloon/w8.1/amd64/blnsvr.exe", None; > - "Balloon/w8.1/amd64/blnsvr.pdb", Some win8_1_64; > - "Balloon/w8.1/x86/WdfCoInstaller01011.dll", None; > - "Balloon/w8.1/x86/balloon.cat", Some win8_1_32; > - "Balloon/w8.1/x86/balloon.inf", Some win8_1_32; > - "Balloon/w8.1/x86/balloon.pdb", Some win8_1_32; > - "Balloon/w8.1/x86/balloon.sys", Some win8_1_32; > - "Balloon/w8.1/x86/blnsvr.exe", None; > - "Balloon/w8.1/x86/blnsvr.pdb", Some win8_1_32; > - "Balloon/w8/amd64/WdfCoInstaller01011.dll", None; > - "Balloon/w8/amd64/balloon.cat", Some win8_64; > - "Balloon/w8/amd64/balloon.inf", Some win8_64; > - "Balloon/w8/amd64/balloon.pdb", Some win8_64; > - "Balloon/w8/amd64/balloon.sys", Some win8_64; > - "Balloon/w8/amd64/blnsvr.exe", None; > - "Balloon/w8/amd64/blnsvr.pdb", Some win8_64; > - "Balloon/w8/x86/WdfCoInstaller01011.dll", None; > - "Balloon/w8/x86/balloon.cat", Some win8_32; > - "Balloon/w8/x86/balloon.inf", Some win8_32; > - "Balloon/w8/x86/balloon.pdb", Some win8_32; > - "Balloon/w8/x86/balloon.sys", Some win8_32; > - "Balloon/w8/x86/blnsvr.exe", None; > - "Balloon/w8/x86/blnsvr.pdb", Some win8_32; > - "Balloon/xp/x86/WdfCoInstaller01009.dll", None; > - "Balloon/xp/x86/balloon.cat", Some winxp_32; > - "Balloon/xp/x86/balloon.inf", Some winxp_32; > - "Balloon/xp/x86/balloon.pdb", Some winxp_32; > - "Balloon/xp/x86/balloon.sys", Some winxp_32; > - "Balloon/xp/x86/blnsvr.exe", None; > - "Balloon/xp/x86/blnsvr.pdb", Some winxp_32; > - "NetKVM/2k12/amd64/netkvm.cat", Some win2k12_64; > - "NetKVM/2k12/amd64/netkvm.inf", Some win2k12_64; > - "NetKVM/2k12/amd64/netkvm.pdb", Some win2k12_64; > - "NetKVM/2k12/amd64/netkvm.sys", Some win2k12_64; > - "NetKVM/2k12/amd64/netkvmco.dll", None; > - "NetKVM/2k12/amd64/readme.doc", None; > - "NetKVM/2k12R2/amd64/netkvm.cat", Some win2k12r2_64; > - "NetKVM/2k12R2/amd64/netkvm.inf", Some win2k12r2_64; > - "NetKVM/2k12R2/amd64/netkvm.pdb", Some win2k12r2_64; > - "NetKVM/2k12R2/amd64/netkvm.sys", Some win2k12r2_64; > - "NetKVM/2k12R2/amd64/netkvmco.dll", None; > - "NetKVM/2k12R2/amd64/readme.doc", None; > - "NetKVM/2k3/amd64/netkvm.cat", Some win2k3_64; > - "NetKVM/2k3/amd64/netkvm.inf", Some win2k3_64; > - "NetKVM/2k3/amd64/netkvm.pdb", Some win2k3_64; > - "NetKVM/2k3/amd64/netkvm.sys", Some win2k3_64; > - "NetKVM/2k3/x86/netkvm.cat", Some win2k3_32; > - "NetKVM/2k3/x86/netkvm.inf", Some win2k3_32; > - "NetKVM/2k3/x86/netkvm.pdb", Some win2k3_32; > - "NetKVM/2k3/x86/netkvm.sys", Some win2k3_32; > - "NetKVM/2k8/amd64/netkvm.cat", Some win2k8_64; > - "NetKVM/2k8/amd64/netkvm.inf", Some win2k8_64; > - "NetKVM/2k8/amd64/netkvm.pdb", Some win2k8_64; > - "NetKVM/2k8/amd64/netkvm.sys", Some win2k8_64; > - "NetKVM/2k8/amd64/netkvmco.dll", None; > - "NetKVM/2k8/amd64/readme.doc", None; > - "NetKVM/2k8/x86/netkvm.cat", Some win2k8_32; > - "NetKVM/2k8/x86/netkvm.inf", Some win2k8_32; > - "NetKVM/2k8/x86/netkvm.pdb", Some win2k8_32; > - "NetKVM/2k8/x86/netkvm.sys", Some win2k8_32; > - "NetKVM/2k8/x86/netkvmco.dll", None; > - "NetKVM/2k8/x86/readme.doc", None; > - "NetKVM/2k8R2/amd64/netkvm.cat", Some win2k8r2_64; > - "NetKVM/2k8R2/amd64/netkvm.inf", Some win2k8r2_64; > - "NetKVM/2k8R2/amd64/netkvm.pdb", Some win2k8r2_64; > - "NetKVM/2k8R2/amd64/netkvm.sys", Some win2k8r2_64; > - "NetKVM/2k8R2/amd64/netkvmco.dll", None; > - "NetKVM/2k8R2/amd64/readme.doc", None; > - "NetKVM/w7/amd64/netkvm.cat", Some win7_64; > - "NetKVM/w7/amd64/netkvm.inf", Some win7_64; > - "NetKVM/w7/amd64/netkvm.pdb", Some win7_64; > - "NetKVM/w7/amd64/netkvm.sys", Some win7_64; > - "NetKVM/w7/amd64/netkvmco.dll", None; > - "NetKVM/w7/amd64/readme.doc", None; > - "NetKVM/w7/x86/netkvm.cat", Some win7_32; > - "NetKVM/w7/x86/netkvm.inf", Some win7_32; > - "NetKVM/w7/x86/netkvm.pdb", Some win7_32; > - "NetKVM/w7/x86/netkvm.sys", Some win7_32; > - "NetKVM/w7/x86/netkvmco.dll", None; > - "NetKVM/w7/x86/readme.doc", None; > - "NetKVM/w8.1/amd64/netkvm.cat", Some win8_1_64; > - "NetKVM/w8.1/amd64/netkvm.inf", Some win8_1_64; > - "NetKVM/w8.1/amd64/netkvm.pdb", Some win8_1_64; > - "NetKVM/w8.1/amd64/netkvm.sys", Some win8_1_64; > - "NetKVM/w8.1/amd64/netkvmco.dll", None; > - "NetKVM/w8.1/amd64/readme.doc", None; > - "NetKVM/w8.1/x86/netkvm.cat", Some win8_1_32; > - "NetKVM/w8.1/x86/netkvm.inf", Some win8_1_32; > - "NetKVM/w8.1/x86/netkvm.pdb", Some win8_1_32; > - "NetKVM/w8.1/x86/netkvm.sys", Some win8_1_32; > - "NetKVM/w8.1/x86/netkvmco.dll", None; > - "NetKVM/w8.1/x86/readme.doc", None; > - "NetKVM/w8/amd64/netkvm.cat", Some win8_64; > - "NetKVM/w8/amd64/netkvm.inf", Some win8_64; > - "NetKVM/w8/amd64/netkvm.pdb", Some win8_64; > - "NetKVM/w8/amd64/netkvm.sys", Some win8_64; > - "NetKVM/w8/amd64/netkvmco.dll", None; > - "NetKVM/w8/amd64/readme.doc", None; > - "NetKVM/w8/x86/netkvm.cat", Some win8_32; > - "NetKVM/w8/x86/netkvm.inf", Some win8_32; > - "NetKVM/w8/x86/netkvm.pdb", Some win8_32; > - "NetKVM/w8/x86/netkvm.sys", Some win8_32; > - "NetKVM/w8/x86/netkvmco.dll", None; > - "NetKVM/w8/x86/readme.doc", None; > - "NetKVM/xp/x86/netkvm.cat", Some winxp_32; > - "NetKVM/xp/x86/netkvm.inf", Some winxp_32; > - "NetKVM/xp/x86/netkvm.pdb", Some winxp_32; > - "NetKVM/xp/x86/netkvm.sys", Some winxp_32; > - "guest-agent/qemu-ga-x64.msi", None; > - "guest-agent/qemu-ga-x86.msi", None; > - "qemupciserial/qemupciserial.inf", None; > - "viorng/2k12/amd64/WdfCoInstaller01011.dll", None; > - "viorng/2k12/amd64/viorng.cat", Some win2k12_64; > - "viorng/2k12/amd64/viorng.inf", Some win2k12_64; > - "viorng/2k12/amd64/viorng.pdb", Some win2k12_64; > - "viorng/2k12/amd64/viorng.sys", Some win2k12_64; > - "viorng/2k12/amd64/viorngci.dll", None; > - "viorng/2k12/amd64/viorngum.dll", None; > - "viorng/2k12R2/amd64/WdfCoInstaller01011.dll", None; > - "viorng/2k12R2/amd64/viorng.cat", Some win2k12r2_64; > - "viorng/2k12R2/amd64/viorng.inf", Some win2k12r2_64; > - "viorng/2k12R2/amd64/viorng.pdb", Some win2k12r2_64; > - "viorng/2k12R2/amd64/viorng.sys", Some win2k12r2_64; > - "viorng/2k12R2/amd64/viorngci.dll", None; > - "viorng/2k12R2/amd64/viorngum.dll", None; > - "viorng/2k8/amd64/WdfCoInstaller01009.dll", None; > - "viorng/2k8/amd64/viorng.cat", Some win2k8_64; > - "viorng/2k8/amd64/viorng.inf", Some win2k8_64; > - "viorng/2k8/amd64/viorng.pdb", Some win2k8_64; > - "viorng/2k8/amd64/viorng.sys", Some win2k8_64; > - "viorng/2k8/amd64/viorngci.dll", None; > - "viorng/2k8/amd64/viorngum.dll", None; > - "viorng/2k8/x86/WdfCoInstaller01009.dll", None; > - "viorng/2k8/x86/viorng.cat", Some win2k8_32; > - "viorng/2k8/x86/viorng.inf", Some win2k8_32; > - "viorng/2k8/x86/viorng.pdb", Some win2k8_32; > - "viorng/2k8/x86/viorng.sys", Some win2k8_32; > - "viorng/2k8/x86/viorngci.dll", None; > - "viorng/2k8/x86/viorngum.dll", None; > - "viorng/2k8R2/amd64/WdfCoInstaller01009.dll", None; > - "viorng/2k8R2/amd64/viorng.cat", Some win2k8r2_64; > - "viorng/2k8R2/amd64/viorng.inf", Some win2k8r2_64; > - "viorng/2k8R2/amd64/viorng.pdb", Some win2k8r2_64; > - "viorng/2k8R2/amd64/viorng.sys", Some win2k8r2_64; > - "viorng/2k8R2/amd64/viorngci.dll", None; > - "viorng/2k8R2/amd64/viorngum.dll", None; > - "viorng/w7/amd64/WdfCoInstaller01009.dll", None; > - "viorng/w7/amd64/viorng.cat", Some win7_64; > - "viorng/w7/amd64/viorng.inf", Some win7_64; > - "viorng/w7/amd64/viorng.pdb", Some win7_64; > - "viorng/w7/amd64/viorng.sys", Some win7_64; > - "viorng/w7/amd64/viorngci.dll", None; > - "viorng/w7/amd64/viorngum.dll", None; > - "viorng/w7/x86/WdfCoInstaller01009.dll", None; > - "viorng/w7/x86/viorng.cat", Some win7_32; > - "viorng/w7/x86/viorng.inf", Some win7_32; > - "viorng/w7/x86/viorng.pdb", Some win7_32; > - "viorng/w7/x86/viorng.sys", Some win7_32; > - "viorng/w7/x86/viorngci.dll", None; > - "viorng/w7/x86/viorngum.dll", None; > - "viorng/w8.1/amd64/WdfCoInstaller01011.dll", None; > - "viorng/w8.1/amd64/viorng.cat", Some win8_1_64; > - "viorng/w8.1/amd64/viorng.inf", Some win8_1_64; > - "viorng/w8.1/amd64/viorng.pdb", Some win8_1_64; > - "viorng/w8.1/amd64/viorng.sys", Some win8_1_64; > - "viorng/w8.1/amd64/viorngci.dll", None; > - "viorng/w8.1/amd64/viorngum.dll", None; > - "viorng/w8.1/x86/WdfCoInstaller01011.dll", None; > - "viorng/w8.1/x86/viorng.cat", Some win8_1_32; > - "viorng/w8.1/x86/viorng.inf", Some win8_1_32; > - "viorng/w8.1/x86/viorng.pdb", Some win8_1_32; > - "viorng/w8.1/x86/viorng.sys", Some win8_1_32; > - "viorng/w8.1/x86/viorngci.dll", None; > - "viorng/w8.1/x86/viorngum.dll", None; > - "viorng/w8/amd64/WdfCoInstaller01011.dll", None; > - "viorng/w8/amd64/viorng.cat", Some win8_64; > - "viorng/w8/amd64/viorng.inf", Some win8_64; > - "viorng/w8/amd64/viorng.pdb", Some win8_64; > - "viorng/w8/amd64/viorng.sys", Some win8_64; > - "viorng/w8/amd64/viorngci.dll", None; > - "viorng/w8/amd64/viorngum.dll", None; > - "viorng/w8/x86/WdfCoInstaller01011.dll", None; > - "viorng/w8/x86/viorng.cat", Some win8_32; > - "viorng/w8/x86/viorng.inf", Some win8_32; > - "viorng/w8/x86/viorng.pdb", Some win8_32; > - "viorng/w8/x86/viorng.sys", Some win8_32; > - "viorng/w8/x86/viorngci.dll", None; > - "viorng/w8/x86/viorngum.dll", None; > - "vioscsi/2k12/amd64/vioscsi.cat", Some win2k12_64; > - "vioscsi/2k12/amd64/vioscsi.inf", Some win2k12_64; > - "vioscsi/2k12/amd64/vioscsi.pdb", Some win2k12_64; > - "vioscsi/2k12/amd64/vioscsi.sys", Some win2k12_64; > - "vioscsi/2k12R2/amd64/vioscsi.cat", Some win2k12r2_64; > - "vioscsi/2k12R2/amd64/vioscsi.inf", Some win2k12r2_64; > - "vioscsi/2k12R2/amd64/vioscsi.pdb", Some win2k12r2_64; > - "vioscsi/2k12R2/amd64/vioscsi.sys", Some win2k12r2_64; > - "vioscsi/2k8/amd64/vioscsi.cat", Some win2k8_64; > - "vioscsi/2k8/amd64/vioscsi.inf", Some win2k8_64; > - "vioscsi/2k8/amd64/vioscsi.pdb", Some win2k8_64; > - "vioscsi/2k8/amd64/vioscsi.sys", Some win2k8_64; > - "vioscsi/2k8/x86/vioscsi.cat", Some win2k8_32; > - "vioscsi/2k8/x86/vioscsi.inf", Some win2k8_32; > - "vioscsi/2k8/x86/vioscsi.pdb", Some win2k8_32; > - "vioscsi/2k8/x86/vioscsi.sys", Some win2k8_32; > - "vioscsi/2k8R2/amd64/vioscsi.cat", Some win2k8r2_64; > - "vioscsi/2k8R2/amd64/vioscsi.inf", Some win2k8r2_64; > - "vioscsi/2k8R2/amd64/vioscsi.pdb", Some win2k8r2_64; > - "vioscsi/2k8R2/amd64/vioscsi.sys", Some win2k8r2_64; > - "vioscsi/w7/amd64/vioscsi.cat", Some win7_64; > - "vioscsi/w7/amd64/vioscsi.inf", Some win7_64; > - "vioscsi/w7/amd64/vioscsi.pdb", Some win7_64; > - "vioscsi/w7/amd64/vioscsi.sys", Some win7_64; > - "vioscsi/w7/x86/vioscsi.cat", Some win7_32; > - "vioscsi/w7/x86/vioscsi.inf", Some win7_32; > - "vioscsi/w7/x86/vioscsi.pdb", Some win7_32; > - "vioscsi/w7/x86/vioscsi.sys", Some win7_32; > - "vioscsi/w8.1/amd64/vioscsi.cat", Some win8_1_64; > - "vioscsi/w8.1/amd64/vioscsi.inf", Some win8_1_64; > - "vioscsi/w8.1/amd64/vioscsi.pdb", Some win8_1_64; > - "vioscsi/w8.1/amd64/vioscsi.sys", Some win8_1_64; > - "vioscsi/w8.1/x86/vioscsi.cat", Some win8_1_32; > - "vioscsi/w8.1/x86/vioscsi.inf", Some win8_1_32; > - "vioscsi/w8.1/x86/vioscsi.pdb", Some win8_1_32; > - "vioscsi/w8.1/x86/vioscsi.sys", Some win8_1_32; > - "vioscsi/w8/amd64/vioscsi.cat", Some win8_64; > - "vioscsi/w8/amd64/vioscsi.inf", Some win8_64; > - "vioscsi/w8/amd64/vioscsi.pdb", Some win8_64; > - "vioscsi/w8/amd64/vioscsi.sys", Some win8_64; > - "vioscsi/w8/x86/vioscsi.cat", Some win8_32; > - "vioscsi/w8/x86/vioscsi.inf", Some win8_32; > - "vioscsi/w8/x86/vioscsi.pdb", Some win8_32; > - "vioscsi/w8/x86/vioscsi.sys", Some win8_32; > - "vioserial/2k12/amd64/WdfCoInstaller01011.dll", None; > - "vioserial/2k12/amd64/vioser.cat", Some win2k12_64; > - "vioserial/2k12/amd64/vioser.inf", Some win2k12_64; > - "vioserial/2k12/amd64/vioser.pdb", Some win2k12_64; > - "vioserial/2k12/amd64/vioser.sys", Some win2k12_64; > - "vioserial/2k12R2/amd64/WdfCoInstaller01011.dll", None; > - "vioserial/2k12R2/amd64/vioser.cat", Some win2k12r2_64; > - "vioserial/2k12R2/amd64/vioser.inf", Some win2k12r2_64; > - "vioserial/2k12R2/amd64/vioser.pdb", Some win2k12r2_64; > - "vioserial/2k12R2/amd64/vioser.sys", Some win2k12r2_64; > - "vioserial/2k3/amd64/WdfCoInstaller01009.dll", None; > - "vioserial/2k3/amd64/vioser.cat", Some win2k3_64; > - "vioserial/2k3/amd64/vioser.inf", Some win2k3_64; > - "vioserial/2k3/amd64/vioser.pdb", Some win2k3_64; > - "vioserial/2k3/amd64/vioser.sys", Some win2k3_64; > - "vioserial/2k3/x86/WdfCoInstaller01009.dll", None; > - "vioserial/2k3/x86/vioser.cat", Some win2k3_32; > - "vioserial/2k3/x86/vioser.inf", Some win2k3_32; > - "vioserial/2k3/x86/vioser.pdb", Some win2k3_32; > - "vioserial/2k3/x86/vioser.sys", Some win2k3_32; > - "vioserial/2k8/amd64/WdfCoInstaller01009.dll", None; > - "vioserial/2k8/amd64/vioser.cat", Some win2k8_64; > - "vioserial/2k8/amd64/vioser.inf", Some win2k8_64; > - "vioserial/2k8/amd64/vioser.pdb", Some win2k8_64; > - "vioserial/2k8/amd64/vioser.sys", Some win2k8_64; > - "vioserial/2k8/x86/WdfCoInstaller01009.dll", None; > - "vioserial/2k8/x86/vioser.cat", Some win2k8_32; > - "vioserial/2k8/x86/vioser.inf", Some win2k8_32; > - "vioserial/2k8/x86/vioser.pdb", Some win2k8_32; > - "vioserial/2k8/x86/vioser.sys", Some win2k8_32; > - "vioserial/2k8R2/amd64/WdfCoInstaller01009.dll", None; > - "vioserial/2k8R2/amd64/vioser.cat", Some win2k8r2_64; > - "vioserial/2k8R2/amd64/vioser.inf", Some win2k8r2_64; > - "vioserial/2k8R2/amd64/vioser.pdb", Some win2k8r2_64; > - "vioserial/2k8R2/amd64/vioser.sys", Some win2k8r2_64; > - "vioserial/w7/amd64/WdfCoInstaller01009.dll", None; > - "vioserial/w7/amd64/vioser.cat", Some win7_64; > - "vioserial/w7/amd64/vioser.inf", Some win7_64; > - "vioserial/w7/amd64/vioser.pdb", Some win7_64; > - "vioserial/w7/amd64/vioser.sys", Some win7_64; > - "vioserial/w7/x86/WdfCoInstaller01009.dll", None; > - "vioserial/w7/x86/vioser.cat", Some win7_32; > - "vioserial/w7/x86/vioser.inf", Some win7_32; > - "vioserial/w7/x86/vioser.pdb", Some win7_32; > - "vioserial/w7/x86/vioser.sys", Some win7_32; > - "vioserial/w8.1/amd64/WdfCoInstaller01011.dll", None; > - "vioserial/w8.1/amd64/vioser.cat", Some win8_1_64; > - "vioserial/w8.1/amd64/vioser.inf", Some win8_1_64; > - "vioserial/w8.1/amd64/vioser.pdb", Some win8_1_64; > - "vioserial/w8.1/amd64/vioser.sys", Some win8_1_64; > - "vioserial/w8.1/x86/WdfCoInstaller01011.dll", None; > - "vioserial/w8.1/x86/vioser.cat", Some win8_1_32; > - "vioserial/w8.1/x86/vioser.inf", Some win8_1_32; > - "vioserial/w8.1/x86/vioser.pdb", Some win8_1_32; > - "vioserial/w8.1/x86/vioser.sys", Some win8_1_32; > - "vioserial/w8/amd64/WdfCoInstaller01011.dll", None; > - "vioserial/w8/amd64/vioser.cat", Some win8_64; > - "vioserial/w8/amd64/vioser.inf", Some win8_64; > - "vioserial/w8/amd64/vioser.pdb", Some win8_64; > - "vioserial/w8/amd64/vioser.sys", Some win8_64; > - "vioserial/w8/x86/WdfCoInstaller01011.dll", None; > - "vioserial/w8/x86/vioser.cat", Some win8_32; > - "vioserial/w8/x86/vioser.inf", Some win8_32; > - "vioserial/w8/x86/vioser.pdb", Some win8_32; > - "vioserial/w8/x86/vioser.sys", Some win8_32; > - "vioserial/xp/x86/WdfCoInstaller01009.dll", None; > - "vioserial/xp/x86/vioser.cat", Some winxp_32; > - "vioserial/xp/x86/vioser.inf", Some winxp_32; > - "vioserial/xp/x86/vioser.pdb", Some winxp_32; > - "vioserial/xp/x86/vioser.sys", Some winxp_32; > - "viostor/2k12/amd64/viostor.cat", Some win2k12_64; > - "viostor/2k12/amd64/viostor.inf", Some win2k12_64; > - "viostor/2k12/amd64/viostor.pdb", Some win2k12_64; > - "viostor/2k12/amd64/viostor.sys", Some win2k12_64; > - "viostor/2k12R2/amd64/viostor.cat", Some win2k12r2_64; > - "viostor/2k12R2/amd64/viostor.inf", Some win2k12r2_64; > - "viostor/2k12R2/amd64/viostor.pdb", Some win2k12r2_64; > - "viostor/2k12R2/amd64/viostor.sys", Some win2k12r2_64; > - "viostor/2k3/amd64/viostor.cat", Some win2k3_64; > - "viostor/2k3/amd64/viostor.inf", Some win2k3_64; > - "viostor/2k3/amd64/viostor.pdb", Some win2k3_64; > - "viostor/2k3/amd64/viostor.sys", Some win2k3_64; > - "viostor/2k3/x86/viostor.cat", Some win2k3_32; > - "viostor/2k3/x86/viostor.inf", Some win2k3_32; > - "viostor/2k3/x86/viostor.pdb", Some win2k3_32; > - "viostor/2k3/x86/viostor.sys", Some win2k3_32; > - "viostor/2k8/amd64/viostor.cat", Some win2k8_64; > - "viostor/2k8/amd64/viostor.inf", Some win2k8_64; > - "viostor/2k8/amd64/viostor.pdb", Some win2k8_64; > - "viostor/2k8/amd64/viostor.sys", Some win2k8_64; > - "viostor/2k8/x86/viostor.cat", Some win2k8_32; > - "viostor/2k8/x86/viostor.inf", Some win2k8_32; > - "viostor/2k8/x86/viostor.pdb", Some win2k8_32; > - "viostor/2k8/x86/viostor.sys", Some win2k8_32; > - "viostor/2k8R2/amd64/viostor.cat", Some win2k8r2_64; > - "viostor/2k8R2/amd64/viostor.inf", Some win2k8r2_64; > - "viostor/2k8R2/amd64/viostor.pdb", Some win2k8r2_64; > - "viostor/2k8R2/amd64/viostor.sys", Some win2k8r2_64; > - "viostor/w7/amd64/viostor.cat", Some win7_64; > - "viostor/w7/amd64/viostor.inf", Some win7_64; > - "viostor/w7/amd64/viostor.pdb", Some win7_64; > - "viostor/w7/amd64/viostor.sys", Some win7_64; > - "viostor/w7/x86/viostor.cat", Some win7_32; > - "viostor/w7/x86/viostor.inf", Some win7_32; > - "viostor/w7/x86/viostor.pdb", Some win7_32; > - "viostor/w7/x86/viostor.sys", Some win7_32; > - "viostor/w8.1/amd64/viostor.cat", Some win8_1_64; > - "viostor/w8.1/amd64/viostor.inf", Some win8_1_64; > - "viostor/w8.1/amd64/viostor.pdb", Some win8_1_64; > - "viostor/w8.1/amd64/viostor.sys", Some win8_1_64; > - "viostor/w8.1/x86/viostor.cat", Some win8_1_32; > - "viostor/w8.1/x86/viostor.inf", Some win8_1_32; > - "viostor/w8.1/x86/viostor.pdb", Some win8_1_32; > - "viostor/w8.1/x86/viostor.sys", Some win8_1_32; > - "viostor/w8/amd64/viostor.cat", Some win8_64; > - "viostor/w8/amd64/viostor.inf", Some win8_64; > - "viostor/w8/amd64/viostor.pdb", Some win8_64; > - "viostor/w8/amd64/viostor.sys", Some win8_64; > - "viostor/w8/x86/viostor.cat", Some win8_32; > - "viostor/w8/x86/viostor.inf", Some win8_32; > - "viostor/w8/x86/viostor.pdb", Some win8_32; > - "viostor/w8/x86/viostor.sys", Some win8_32; > - "viostor/xp/x86/viostor.cat", Some winxp_32; > - "viostor/xp/x86/viostor.inf", Some winxp_32; > - "viostor/xp/x86/viostor.pdb", Some winxp_32; > - "viostor/xp/x86/viostor.sys", Some winxp_32; > - "virtio-win-1.7.4_amd64.vfd", None; > - "virtio-win-1.7.4_x86.vfd", None; > - "virtio-win_license.txt", None; > + (* Paths relative to $srcdir/test-data/fake-virtio-win. *) > + "cd/Balloon/2k12/amd64/balloon.inf", Some win2k12_64; > + "cd/Balloon/2k12R2/amd64/balloon.inf", Some win2k12r2_64; > + "cd/Balloon/2k3/amd64/balloon.inf", Some win2k3_64; > + "cd/Balloon/2k3/x86/balloon.inf", Some win2k3_32; > + "cd/Balloon/2k8/amd64/balloon.inf", Some win2k8_64; > + "cd/Balloon/2k8/x86/balloon.inf", Some win2k8_32; > + "cd/Balloon/2k8R2/amd64/balloon.inf", Some win2k8r2_64; > + "cd/Balloon/w7/amd64/balloon.inf", Some win7_64; > + "cd/Balloon/w7/x86/balloon.inf", Some win7_32; > + "cd/Balloon/w8.1/amd64/balloon.inf", Some win8_1_64; > + "cd/Balloon/w8.1/x86/balloon.inf", Some win8_1_32; > + "cd/Balloon/w8/amd64/balloon.inf", Some win8_64; > + "cd/Balloon/w8/x86/balloon.inf", Some win8_32; > + "cd/Balloon/xp/x86/balloon.inf", Some winxp_32; > + "cd/NetKVM/2k12/amd64/netkvm.inf", Some win2k12_64; > + "cd/NetKVM/2k12R2/amd64/netkvm.inf", Some win2k12r2_64; > + "cd/NetKVM/2k3/amd64/netkvm.inf", Some win2k3_64; > + "cd/NetKVM/2k3/x86/netkvm.inf", Some win2k3_32; > + "cd/NetKVM/2k8/amd64/netkvm.inf", Some win2k8_64; > + "cd/NetKVM/2k8/x86/netkvm.inf", Some win2k8_32; > + "cd/NetKVM/2k8R2/amd64/netkvm.inf", Some win2k8r2_64; > + "cd/NetKVM/w7/amd64/netkvm.inf", Some win7_64; > + "cd/NetKVM/w7/x86/netkvm.inf", Some win7_32; > + "cd/NetKVM/w8.1/amd64/netkvm.inf", Some win8_1_64; > + "cd/NetKVM/w8.1/x86/netkvm.inf", Some win8_1_32; > + "cd/NetKVM/w8/amd64/netkvm.inf", Some win8_64; > + "cd/NetKVM/w8/x86/netkvm.inf", Some win8_32; > + "cd/NetKVM/xp/x86/netkvm.inf", Some winxp_32; > + "cd/qemupciserial/qemupciserial.inf", None; > + "cd/viorng/2k12/amd64/viorng.inf", Some win2k12_64; > + "cd/viorng/2k12R2/amd64/viorng.inf", Some win2k12r2_64; > + "cd/viorng/2k8/amd64/viorng.inf", Some win2k8_64; > + "cd/viorng/2k8/x86/viorng.inf", Some win2k8_32; > + "cd/viorng/2k8R2/amd64/viorng.inf", Some win2k8r2_64; > + "cd/viorng/w7/amd64/viorng.inf", Some win7_64; > + "cd/viorng/w7/x86/viorng.inf", Some win7_32; > + "cd/viorng/w8.1/amd64/viorng.inf", Some win8_1_64; > + "cd/viorng/w8.1/x86/viorng.inf", Some win8_1_32; > + "cd/viorng/w8/amd64/viorng.inf", Some win8_64; > + "cd/viorng/w8/x86/viorng.inf", Some win8_32; > + "cd/vioscsi/2k12/amd64/vioscsi.inf", Some win2k12_64; > + "cd/vioscsi/2k12R2/amd64/vioscsi.inf", Some win2k12r2_64; > + "cd/vioscsi/2k8/amd64/vioscsi.inf", Some win2k8_64; > + "cd/vioscsi/2k8/x86/vioscsi.inf", Some win2k8_32; > + "cd/vioscsi/2k8R2/amd64/vioscsi.inf", Some win2k8r2_64; > + "cd/vioscsi/w7/amd64/vioscsi.inf", Some win7_64; > + "cd/vioscsi/w7/x86/vioscsi.inf", Some win7_32; > + "cd/vioscsi/w8.1/amd64/vioscsi.inf", Some win8_1_64; > + "cd/vioscsi/w8.1/x86/vioscsi.inf", Some win8_1_32; > + "cd/vioscsi/w8/amd64/vioscsi.inf", Some win8_64; > + "cd/vioscsi/w8/x86/vioscsi.inf", Some win8_32; > + "cd/vioserial/2k12/amd64/vioser.inf", Some win2k12_64; > + "cd/vioserial/2k12R2/amd64/vioser.inf", Some win2k12r2_64; > + "cd/vioserial/2k3/amd64/vioser.inf", Some win2k3_64; > + "cd/vioserial/2k3/x86/vioser.inf", Some win2k3_32; > + "cd/vioserial/2k8/amd64/vioser.inf", Some win2k8_64; > + "cd/vioserial/2k8/x86/vioser.inf", Some win2k8_32; > + "cd/vioserial/2k8R2/amd64/vioser.inf", Some win2k8r2_64; > + "cd/vioserial/w7/amd64/vioser.inf", Some win7_64; > + "cd/vioserial/w7/x86/vioser.inf", Some win7_32; > + "cd/vioserial/w8.1/amd64/vioser.inf", Some win8_1_64; > + "cd/vioserial/w8.1/x86/vioser.inf", Some win8_1_32; > + "cd/vioserial/w8/amd64/vioser.inf", Some win8_64; > + "cd/vioserial/w8/x86/vioser.inf", Some win8_32; > + "cd/vioserial/w8/x86/vioser.pdb", Some win8_32; > + "cd/vioserial/xp/x86/vioser.inf", Some winxp_32; > + "cd/viostor/2k12/amd64/viostor.inf", Some win2k12_64; > + "cd/viostor/2k12R2/amd64/viostor.inf", Some win2k12r2_64; > + "cd/viostor/2k3/amd64/viostor.inf", Some win2k3_64; > + "cd/viostor/2k3/x86/viostor.inf", Some win2k3_32; > + "cd/viostor/2k8/amd64/viostor.inf", Some win2k8_64; > + "cd/viostor/2k8/x86/viostor.inf", Some win2k8_32; > + "cd/viostor/2k8R2/amd64/viostor.inf", Some win2k8r2_64; > + "cd/viostor/w7/amd64/viostor.inf", Some win7_64; > + "cd/viostor/w7/x86/viostor.inf", Some win7_32; > + "cd/viostor/w8.1/amd64/viostor.inf", Some win8_1_64; > + "cd/viostor/w8.1/x86/viostor.inf", Some win8_1_32; > + "cd/viostor/w8/amd64/viostor.inf", Some win8_64; > + "cd/viostor/w8/x86/viostor.inf", Some win8_32; > + "cd/viostor/xp/x86/viostor.inf", Some winxp_32; > > - (* Paths from the unpacked virtio-win 1.7.4 directory. *) > - "virtio-win-1.7.4.iso", None; > - "virtio-win-1.7.4_amd64.vfd", None; > - "guest-agent/qemu-ga-x86.msi", None; > - "guest-agent/qemu-ga-x64.msi", None; > "drivers/i386/Win8.1/viostor.inf", Some win8_1_32; > - "drivers/i386/Win8.1/viostor.sys", Some win8_1_32; > - "drivers/i386/Win8.1/vioscsi.cat", Some win8_1_32; > "drivers/i386/Win8.1/netkvm.inf", Some win8_1_32; > - "drivers/i386/Win8.1/netkvm.sys", Some win8_1_32; > - "drivers/i386/Win8.1/viostor.cat", Some win8_1_32; > - "drivers/i386/Win8.1/vioscsi.sys", Some win8_1_32; > - "drivers/i386/Win8.1/netkvm.cat", Some win8_1_32; > "drivers/i386/Win8.1/vioscsi.inf", Some win8_1_32; > "drivers/i386/Win2008/viostor.inf", Some win2k8_32; > - "drivers/i386/Win2008/viostor.sys", Some win2k8_32; > - "drivers/i386/Win2008/vioscsi.cat", Some win2k8_32; > "drivers/i386/Win2008/netkvm.inf", Some win2k8_32; > - "drivers/i386/Win2008/netkvm.sys", Some win2k8_32; > - "drivers/i386/Win2008/viostor.cat", Some win2k8_32; > - "drivers/i386/Win2008/vioscsi.sys", Some win2k8_32; > - "drivers/i386/Win2008/netkvm.cat", Some win2k8_32; > "drivers/i386/Win2008/vioscsi.inf", Some win2k8_32; > "drivers/i386/Win7/viostor.inf", Some win7_32; > - "drivers/i386/Win7/viostor.sys", Some win7_32; > - "drivers/i386/Win7/qxldd.dll", None; > - "drivers/i386/Win7/qxl.sys", Some win7_32; > - "drivers/i386/Win7/vioscsi.cat", Some win7_32; > "drivers/i386/Win7/netkvm.inf", Some win7_32; > - "drivers/i386/Win7/netkvm.sys", Some win7_32; > - "drivers/i386/Win7/viostor.cat", Some win7_32; > "drivers/i386/Win7/qxl.inf", Some win7_32; > - "drivers/i386/Win7/vioscsi.sys", Some win7_32; > - "drivers/i386/Win7/qxl.cat", Some win7_32; > - "drivers/i386/Win7/netkvm.cat", Some win7_32; > "drivers/i386/Win7/vioscsi.inf", Some win7_32; > "drivers/i386/Win2003/viostor.inf", Some win2k3_32; > - "drivers/i386/Win2003/viostor.sys", Some win2k3_32; > "drivers/i386/Win2003/netkvm.inf", Some win2k3_32; > - "drivers/i386/Win2003/netkvm.sys", Some win2k3_32; > - "drivers/i386/Win2003/viostor.cat", Some win2k3_32; > - "drivers/i386/Win2003/netkvm.cat", Some win2k3_32; > "drivers/i386/Win8/viostor.inf", Some win8_32; > - "drivers/i386/Win8/viostor.sys", Some win8_32; > - "drivers/i386/Win8/vioscsi.cat", Some win8_32; > "drivers/i386/Win8/netkvm.inf", Some win8_32; > - "drivers/i386/Win8/netkvm.sys", Some win8_32; > - "drivers/i386/Win8/viostor.cat", Some win8_32; > - "drivers/i386/Win8/vioscsi.sys", Some win8_32; > - "drivers/i386/Win8/netkvm.cat", Some win8_32; > "drivers/i386/Win8/vioscsi.inf", Some win8_32; > "drivers/i386/WinXP/viostor.inf", Some winxp_32; > - "drivers/i386/WinXP/viostor.sys", Some winxp_32; > - "drivers/i386/WinXP/qxldd.dll", None; > - "drivers/i386/WinXP/qxl.sys", Some winxp_32; > "drivers/i386/WinXP/netkvm.inf", Some winxp_32; > - "drivers/i386/WinXP/netkvm.sys", Some winxp_32; > - "drivers/i386/WinXP/viostor.cat", Some winxp_32; > "drivers/i386/WinXP/qxl.inf", Some winxp_32; > - "drivers/i386/WinXP/qxl.cat", Some winxp_32; > - "drivers/i386/WinXP/netkvm.cat", Some winxp_32; > "drivers/amd64/Win8.1/viostor.inf", Some win8_1_64; > - "drivers/amd64/Win8.1/viostor.sys", Some win8_1_64; > - "drivers/amd64/Win8.1/vioscsi.cat", Some win8_1_64; > "drivers/amd64/Win8.1/netkvm.inf", Some win8_1_64; > - "drivers/amd64/Win8.1/netkvm.sys", Some win8_1_64; > - "drivers/amd64/Win8.1/viostor.cat", Some win8_1_64; > - "drivers/amd64/Win8.1/vioscsi.sys", Some win8_1_64; > - "drivers/amd64/Win8.1/netkvm.cat", Some win8_1_64; > "drivers/amd64/Win8.1/vioscsi.inf", Some win8_1_64; > "drivers/amd64/Win2008/viostor.inf", Some win2k8_64; > - "drivers/amd64/Win2008/viostor.sys", Some win2k8_64; > - "drivers/amd64/Win2008/vioscsi.cat", Some win2k8_64; > "drivers/amd64/Win2008/netkvm.inf", Some win2k8_64; > - "drivers/amd64/Win2008/netkvm.sys", Some win2k8_64; > - "drivers/amd64/Win2008/viostor.cat", Some win2k8_64; > - "drivers/amd64/Win2008/vioscsi.sys", Some win2k8_64; > - "drivers/amd64/Win2008/netkvm.cat", Some win2k8_64; > "drivers/amd64/Win2008/vioscsi.inf", Some win2k8_64; > "drivers/amd64/Win7/viostor.inf", Some win7_64; > - "drivers/amd64/Win7/viostor.sys", Some win7_64; > - "drivers/amd64/Win7/qxldd.dll", None; > - "drivers/amd64/Win7/qxl.sys", Some win7_64; > - "drivers/amd64/Win7/vioscsi.cat", Some win7_64; > "drivers/amd64/Win7/netkvm.inf", Some win7_64; > - "drivers/amd64/Win7/netkvm.sys", Some win7_64; > - "drivers/amd64/Win7/viostor.cat", Some win7_64; > "drivers/amd64/Win7/qxl.inf", Some win7_64; > - "drivers/amd64/Win7/vioscsi.sys", Some win7_64; > - "drivers/amd64/Win7/qxl.cat", Some win7_64; > - "drivers/amd64/Win7/netkvm.cat", Some win7_64; > "drivers/amd64/Win7/vioscsi.inf", Some win7_64; > "drivers/amd64/Win2003/viostor.inf", Some win2k3_64; > - "drivers/amd64/Win2003/viostor.sys", Some win2k3_64; > "drivers/amd64/Win2003/netkvm.inf", Some win2k3_64; > - "drivers/amd64/Win2003/netkvm.sys", Some win2k3_64; > - "drivers/amd64/Win2003/viostor.cat", Some win2k3_64; > - "drivers/amd64/Win2003/netkvm.cat", Some win2k3_64; > "drivers/amd64/Win8/viostor.inf", Some win8_64; > - "drivers/amd64/Win8/viostor.sys", Some win8_64; > - "drivers/amd64/Win8/vioscsi.cat", Some win8_64; > "drivers/amd64/Win8/netkvm.inf", Some win8_64; > - "drivers/amd64/Win8/netkvm.sys", Some win8_64; > - "drivers/amd64/Win8/viostor.cat", Some win8_64; > - "drivers/amd64/Win8/vioscsi.sys", Some win8_64; > - "drivers/amd64/Win8/netkvm.cat", Some win8_64; > "drivers/amd64/Win8/vioscsi.inf", Some win8_64; > "drivers/amd64/Win2012/viostor.inf", Some win2k12_64; > - "drivers/amd64/Win2012/viostor.sys", Some win2k12_64; > - "drivers/amd64/Win2012/vioscsi.cat", Some win2k12_64; > "drivers/amd64/Win2012/netkvm.inf", Some win2k12_64; > - "drivers/amd64/Win2012/netkvm.sys", Some win2k12_64; > - "drivers/amd64/Win2012/viostor.cat", Some win2k12_64; > - "drivers/amd64/Win2012/vioscsi.sys", Some win2k12_64; > - "drivers/amd64/Win2012/netkvm.cat", Some win2k12_64; > "drivers/amd64/Win2012/vioscsi.inf", Some win2k12_64; > "drivers/amd64/Win2008R2/viostor.inf", Some win2k8r2_64; > - "drivers/amd64/Win2008R2/viostor.sys", Some win2k8r2_64; > - "drivers/amd64/Win2008R2/qxldd.dll", None; > - "drivers/amd64/Win2008R2/qxl.sys", Some win2k8r2_64; > - "drivers/amd64/Win2008R2/vioscsi.cat", Some win2k8r2_64; > "drivers/amd64/Win2008R2/netkvm.inf", Some win2k8r2_64; > - "drivers/amd64/Win2008R2/netkvm.sys", Some win2k8r2_64; > - "drivers/amd64/Win2008R2/viostor.cat", Some win2k8r2_64; > "drivers/amd64/Win2008R2/qxl.inf", Some win2k8r2_64; > - "drivers/amd64/Win2008R2/vioscsi.sys", Some win2k8r2_64; > - "drivers/amd64/Win2008R2/qxl.cat", Some win2k8r2_64; > - "drivers/amd64/Win2008R2/netkvm.cat", Some win2k8r2_64; > "drivers/amd64/Win2008R2/vioscsi.inf", Some win2k8r2_64; > "drivers/amd64/Win2012R2/viostor.inf", Some win2k12r2_64; > - "drivers/amd64/Win2012R2/viostor.sys", Some win2k12r2_64; > - "drivers/amd64/Win2012R2/vioscsi.cat", Some win2k12r2_64; > "drivers/amd64/Win2012R2/netkvm.inf", Some win2k12r2_64; > - "drivers/amd64/Win2012R2/netkvm.sys", Some win2k12r2_64; > - "drivers/amd64/Win2012R2/viostor.cat", Some win2k12r2_64; > - "drivers/amd64/Win2012R2/vioscsi.sys", Some win2k12r2_64; > - "drivers/amd64/Win2012R2/netkvm.cat", Some win2k12r2_64; > "drivers/amd64/Win2012R2/vioscsi.inf", Some win2k12r2_64; > - "virtio-win-1.7.4_x86.vfd", None; > ] in > > - (* Test each path against each version of Windows. *) > + (* Test each inf file against each version of Windows. *) > let printer = string_of_bool in > > List.iter ( > fun (path, correct_windows) -> > + let path = srcdir // ".." // "test-data" // "fake-virtio-win" // path in > + > match correct_windows with > | None -> > List.iter ( > fun win -> > let msg = sprintf "path %s should not match %s" > path win.i_product_name in > + let content = read_whole_file path in > assert_equal ~printer ~msg false > - (Windows.UNIT_TESTS.virtio_iso_path_matches_guest_os path win) > + (Windows.UNIT_TESTS.virtio_inf_matches_guest_os content path win) > ) all_windows > | Some correct_windows -> > List.iter ( > @@ -859,8 +417,9 @@ let test_virtio_iso_path_matches_guest_os ctx > else > sprintf "path %s should not match %s" > path win.i_product_name in > + let content = read_whole_file path in > assert_equal ~printer ~msg expected > - (Windows.UNIT_TESTS.virtio_iso_path_matches_guest_os path win) > + (Windows.UNIT_TESTS.virtio_inf_matches_guest_os content path win) > ) all_windows > ) paths > > @@ -872,8 +431,8 @@ let suite > "Utils.drive_name" >:: test_drive_name; > "Utils.drive_index" >:: test_drive_index; > "Windows_inf.of_string" >:: test_windows_inf_of_string; > - "Windows.virtio_iso_path_matches_guest_os" >:: > - test_virtio_iso_path_matches_guest_os; > + "Windows.virtio_inf_matches_guest_os" >:: > + test_virtio_inf_matches_guest_os; > ] > > let () > diff --git a/v2v/windows.ml b/v2v/windows.ml > index 6503b57..2e18307 100644 > --- a/v2v/windows.ml > +++ b/v2v/windows.ml > @@ -50,128 +50,185 @@ and (=~) str rex > (* Copy the matching drivers to the driverdir; return true if any have > * been copied. > *) > +type virtio_win_source > + | Virtio_Win_Directory > + | Virtio_Win_ISO of Guestfs.guestfs > + > let rec copy_virtio_drivers g inspect virtio_win driverdir > - let ret = ref false in > - if is_directory virtio_win then ( > - let cmd = sprintf "cd %s && find -type f" (quote virtio_win) in > - let paths = external_command cmd in > - List.iter ( > - fun path -> > - if virtio_iso_path_matches_guest_os path inspect then ( > - let source = virtio_win // path in > - let target = driverdir // > - String.lowercase_ascii (Filename.basename path) in > - if verbose () then > - printf "Copying virtio driver bits: 'host:%s' -> '%s'\n" > - source target; > - > - g#write target (read_whole_file source); > - ret := true > - ) > - ) paths > - ) > - else if is_regular_file virtio_win then ( > - try > - let g2 = open_guestfs ~identifier:"virtio_win" () in > - g2#add_drive_opts virtio_win ~readonly:true; > - g2#launch (); > - let vio_root = "/" in > - g2#mount_ro "/dev/sda" vio_root; > - let paths = g2#find vio_root in > - Array.iter ( > - fun path -> > - let source = vio_root // path in > - if g2#is_file source ~followsymlinks:false && > - virtio_iso_path_matches_guest_os path inspect then ( > - let target = driverdir // > - String.lowercase_ascii (Filename.basename path) in > - if verbose () then > - printf "Copying virtio driver bits: '%s:%s' -> '%s'\n" > - virtio_win path target; > - > - g#write target (g2#read_file source); > - ret := true > - ) > - ) paths; > - g2#close() > - with Guestfs.Error msg -> > - error (f_"%s: cannot open virtio-win ISO file: %s") virtio_win msg > - ); > - !ret > - > -(* Given a path of a file relative to the root of the directory tree > - * with virtio-win drivers, figure out if it's suitable for the > - * specific Windows flavor of the current guest. > + (* Does $VIRTIO_WIN point to a directory or an ISO file? *) > + let virtio_win_source > + if is_directory virtio_win then > + Some Virtio_Win_Directory > + else if is_regular_file virtio_win then ( > + try > + let g2 = open_guestfs ~identifier:"virtio_win" () in > + g2#add_drive_opts virtio_win ~readonly:true; > + g2#launch (); > + g2#mount_ro "/dev/sda" "/"; > + Some (Virtio_Win_ISO g2) > + with Guestfs.Error msg -> > + error (f_"%s: cannot open virtio-win ISO file: %s") virtio_win msg > + ) else > + None in > + > + match virtio_win_source with > + | None -> > + (* [$VIRTIO_WIN] does not point to a directory or regular file. This > + * is not an error, but at the same time, no drivers were copied > + * so we return [false] here. > + *) > + false > + > + | Some virtio_win_source -> > + (* Find and load all the *.inf files from the virtio-win directory > + * or ISO. Returns a list of pairs [(inf_content, inf_name, directory)] > + * where [inf_content] is the unparsed inf file, [inf_name] is a debug > + * string we can use in error messages to refer to the inf file, > + * and [directory] is a string used to track the directory containing > + * the inf file. > + *) > + let inf_files : (string * string * string) list > + match virtio_win_source with > + | Virtio_Win_Directory -> > + let cmd > + sprintf "find %s -name '*.inf' -type f" (quote virtio_win) in > + let paths = external_command cmd in > + List.map (fun path -> > + read_whole_file path, path, Filename.dirname path) paths > + | Virtio_Win_ISO g2 -> > + let paths = g2#find "/" in > + let paths = Array.to_list paths in > + let paths > + List.filter ( > + fun path -> > + String.is_suffix path ".inf" && > + g2#is_file path ~followsymlinks:false > + ) paths in > + List.map ( > + fun path -> > + let path = "/" ^ path in > + let i = String.rindex path '/' in > + let dir = String.sub path 0 i in > + g2#read_file path, sprintf "%s:%s" virtio_win path, dir > + ) paths in > + > + (* Get only the *.inf files which match the operating system. *) > + let inf_files > + List.filter ( > + fun (inf_content, inf_name, directory) -> > + virtio_inf_matches_guest_os inf_content inf_name inspect > + ) inf_files in > + > + (* If a directory contains any matching *.inf file, then we will > + * copy all the files from that directory. So get the unique list > + * of directories that we will copy. > + *) > + let directories = List.map (fun (_,_,dir) -> dir) inf_files in > + let directories = sort_uniq directories in > + > + (* Copy the directories. *) > + List.iter ( > + fun dir -> > + match virtio_win_source with > + | Virtio_Win_Directory -> copy_host_directory dir g driverdir > + | Virtio_Win_ISO g2 -> copy_iso_directory g2 dir g driverdir > + ) directories; > + > + (* Return true if some drivers were copied. *) > + directories <> [] > + > +(* Copy host files in same directory as inf_path to driverdir. *) > +and copy_host_directory dir g driverdir > + g#copy_in dir driverdir > + > +(* Copy files from ISO in same directory as inf_path to driverdir. *) > +and copy_iso_directory g2 dir g driverdir > + let files = g2#find dir in > + let files = Array.to_list files in > + assert (files <> []); (* at least the .inf file must be here *) > + > + List.iter ( > + fun filename -> > + let content = g2#read_file (dir ^ filename) in > + g#write (driverdir ^ "/" ^ filename) content > + ) files > + > +(* Given the content of a [*.inf] file from the virtio-win drivers, > + * figure out if it's suitable for the specific Windows flavor of the > + * current guest. > + *) > +and virtio_inf_matches_guest_os inf_content inf_name inspect > + let sections = Windows_inf.of_string inf_content in > + > + (* Try to find the [Version] / DriverVer. *) > + let driver_ver = parse_driver_ver inf_name sections in > + > + (* Try to find the [Manufacturer] line. *) > + let driver_arch = parse_manufacturer inf_name sections in > + > + (* If we got both, we can continue, else give up. *) > + match driver_ver, driver_arch with > + | None, None | Some _, None | None, Some _ -> false > + | Some driver_ver, Some driver_arch -> > + (* XXX This ignores i_product_variant. However that may not matter. > + * There appears to be no material difference in the inf file. > + *) > + let { Types.i_major_version = major; i_minor_version = minor; > + i_arch = arch } = inspect in > + > + let ver = major * 10 + minor in > + > + driver_ver = ver && driver_arch = arch > + > +(* Find the [Version] section in the [*.inf] file, and find the > + * [DriverVer] from that, and parse it. Returns [None] if we couldn't > + * find / parse it. > + * Reference: https://www.redhat.com/archives/libguestfs/2015-October/msg00352.html > *) > -and virtio_iso_path_matches_guest_os path inspect > - let { Types.i_major_version = os_major; i_minor_version = os_minor; > - i_arch = arch; i_product_variant = os_variant } = inspect in > +and parse_driver_ver inf_name sections > try > - (* Lowercased path, since the ISO may contain upper or lowercase path > - * elements. > - *) > - let lc_path = String.lowercase_ascii path in > - let lc_basename = Filename.basename path in > - > - let extension > - match last_part_of lc_basename '.' with > - | Some x -> x > - | None -> raise Not_found > - in > - > - (* Skip files without specific extensions. *) > - let extensions = ["cat"; "inf"; "pdb"; "sys"] in > - if not (List.mem extension extensions) then raise Not_found; > - > - (* Using the full path, work out what version of Windows > - * this driver is for. Paths can be things like: > - * "NetKVM/2k12R2/amd64/netkvm.sys" or > - * "./drivers/amd64/Win2012R2/netkvm.sys". > - * Note we check lowercase paths. > - *) > - let pathelem elem = String.find lc_path ("/" ^ elem ^ "/") >= 0 in > - let p_arch > - if pathelem "x86" || pathelem "i386" then "i386" > - else if pathelem "amd64" then "x86_64" > - else raise Not_found in > - > - let is_client os_variant = os_variant = "Client" > - and not_client os_variant = os_variant <> "Client" > - and any_variant os_variant = true in > - let p_os_major, p_os_minor, match_os_variant > - if pathelem "xp" || pathelem "winxp" then > - (5, 1, any_variant) > - else if pathelem "2k3" || pathelem "win2003" then > - (5, 2, any_variant) > - else if pathelem "vista" then > - (6, 0, is_client) > - else if pathelem "2k8" || pathelem "win2008" then > - (6, 0, not_client) > - else if pathelem "w7" || pathelem "win7" then > - (6, 1, is_client) > - else if pathelem "2k8r2" || pathelem "win2008r2" then > - (6, 1, not_client) > - else if pathelem "w8" || pathelem "win8" then > - (6, 2, is_client) > - else if pathelem "2k12" || pathelem "win2012" then > - (6, 2, not_client) > - else if pathelem "w8.1" || pathelem "win8.1" then > - (6, 3, is_client) > - else if pathelem "2k12r2" || pathelem "win2012r2" then > - (6, 3, not_client) > - else if pathelem "w10" || pathelem "win10" then > - (10, 0, is_client) > - else > - raise Not_found in > - > - arch = p_arch && os_major = p_os_major && os_minor = p_os_minor && > - match_os_variant os_variant > - > - with Not_found -> false > + let driver_ver = Windows_inf.find_key sections "Version" "DriverVer" in > + if Str.string_match driver_ver_rex driver_ver 0 then > + Some (int_of_string (Str.matched_group 1 driver_ver)) > + else > + raise Not_found > + with > + Not_found -> > + warning (f_"%s: could not find or parse the [Version] DriverVer key in the Windows inf file") > + inf_name; > + None > + > +and driver_ver_rex > + Str.regexp "[0-9/]+,\\([0-9]+\\)" > + > +(* Find the [Manufacturer] section and try to find the first line. > + * There is no consistent naming of this line unfortunately. > + * Reference: https://www.redhat.com/archives/libguestfs/2015-November/msg00065.html > + *) > +and parse_manufacturer inf_name sections > + try > + let lines = Windows_inf.find_section sections "Manufacturer" in > + match lines with > + | [] -> raise Not_found > + | (_, manufacturer) :: _ -> > + if Str.string_match manufacturer_rex manufacturer 0 then ( > + let arch = Str.matched_group 1 manufacturer in > + if arch = "x86" || arch = "X86" then Some "i386" else Some "x86_64" > + ) > + else > + raise Not_found > + with > + Not_found -> > + warning (f_"%s: could not find or parse the [Manufacturer] section in the Windows inf file") > + inf_name; > + None > + > +and manufacturer_rex > + Str.regexp_case_fold ".*,NT\\(x86\\|amd64\\)" > > (* The following function is only exported for unit tests. *) > module UNIT_TESTS = struct > - let virtio_iso_path_matches_guest_os = virtio_iso_path_matches_guest_os > + let virtio_inf_matches_guest_os = virtio_inf_matches_guest_os > end > > (* This is a wrapper that handles opening and closing the hive > diff --git a/v2v/windows.mli b/v2v/windows.mli > index 863a605..4098b27 100644 > --- a/v2v/windows.mli > +++ b/v2v/windows.mli > @@ -45,5 +45,5 @@ val get_node : Guestfs.guestfs -> int64 -> string list -> int64 option > > (* The following function is only exported for unit tests. *) > module UNIT_TESTS : sig > - val virtio_iso_path_matches_guest_os : string -> Types.inspect -> bool > + val virtio_inf_matches_guest_os : string -> string -> Types.inspect -> bool > endadding roman to CC:
Roman Kagan
2015-Nov-18 18:33 UTC
Re: [Libguestfs] [PATCH 0/3] v2v: windows: Use '*.inf' files to control how Windows drivers are installed.
On Tue, Nov 17, 2015 at 10:03:22PM +0000, Richard W.M. Jones wrote:> Instead of trying to split and parse elements from virtio-win paths, > use the '*.inf' files supplied with the drivers to control how Windows > drivers are installed.I think it's a bit premature at this point. AFAICS at least drivers for 6.0 (2k8) and 6.1 (7, 2k8r2) are identical, while the .cat files are not: the ones for 2k8 have "Server2008X64" in the .cat, while 7/2k8r2 have "7X64,Server2008R2X64" (can be seen with 'openssl asn1parse -in xxx.cat -inform der -i -dump' and digging through the output, and no, I don't know yet if it can be done reliably). So your code is not unlikely to find a driver with a matching .inf but a non-matching .cat. I've no idea how critical this is but I think we need to figure it out first. Roman.
Maybe Matching Threads
- [PATCH v3 4/8] mllib: Add some imperative list manipulation functions.
- [PATCH 1/2] mllib: move remove_duplicates from v2v
- [PATCH v6 04/41] mllib: Split ‘Common_utils’ into ‘Std_utils’ + ‘Common_utils’.
- [PATCH 4/4] mllib, v2v: Allow open_guestfs to set the handle identifier.
- [PATCH] generator: Share Common_utils code.