Blob Blame History Raw
From 883418f9a3e98eefaba4e9958f1b446270c034cf Mon Sep 17 00:00:00 2001
From: "Richard W.M. Jones" <rjones@redhat.com>
Date: Mon, 22 Jul 2013 13:28:28 +0100
Subject: [PATCH] sysprep: Add new fs-uuids operation.

This creates new random UUIDs for all filesystems in a guest.

Cherry picked from commit 8965368eb89532ac1613fffb0a3a661f005bae81
and modified for virt-sysprep in libguestfs 1.22.
---
 po/POTFILES-ml                        |  1 +
 resize/common_utils.ml                | 23 ++++++++++++++
 sysprep/Makefile.am                   |  1 +
 sysprep/sysprep_operation_fs_uuids.ml | 56 +++++++++++++++++++++++++++++++++++
 4 files changed, 81 insertions(+)
 create mode 100644 sysprep/sysprep_operation_fs_uuids.ml

diff --git a/po/POTFILES-ml b/po/POTFILES-ml
index ba64fa3..6ea4ee2 100644
--- a/po/POTFILES-ml
+++ b/po/POTFILES-ml
@@ -20,6 +20,7 @@ sysprep/sysprep_operation_dhcp_server_state.ml
 sysprep/sysprep_operation_dovecot_data.ml
 sysprep/sysprep_operation_firstboot.ml
 sysprep/sysprep_operation_flag_reconfiguration.ml
+sysprep/sysprep_operation_fs_uuids.ml
 sysprep/sysprep_operation_hostname.ml
 sysprep/sysprep_operation_kerberos_data.ml
 sysprep/sysprep_operation_logfiles.ml
diff --git a/resize/common_utils.ml b/resize/common_utils.ml
index 0f71810..37da8df 100644
--- a/resize/common_utils.ml
+++ b/resize/common_utils.ml
@@ -252,3 +252,26 @@ let display_long_options () =
         printf "%s\n" arg
   ) !long_options;
   exit 0
+
+let uuidgen () =
+  let cmd = "uuidgen -r" in
+  let chan = Unix.open_process_in cmd in
+  let uuid = input_line chan in
+  let stat = Unix.close_process_in chan in
+  (match stat with
+  | Unix.WEXITED 0 -> ()
+  | Unix.WEXITED i ->
+    error (f_"external command '%s' exited with error %d") cmd i
+  | Unix.WSIGNALED i ->
+    error (f_"external command '%s' killed by signal %d") cmd i
+  | Unix.WSTOPPED i ->
+    error (f_"external command '%s' stopped by signal %d") cmd i
+  );
+  let len = String.length uuid in
+  let uuid, len =
+    if len > 0 && uuid.[len-1] = '\n' then
+      String.sub uuid 0 (len-1), len-1
+    else
+      uuid, len in
+  if len < 10 then assert false; (* sanity check on uuidgen *)
+  uuid
diff --git a/sysprep/Makefile.am b/sysprep/Makefile.am
index 6bc5873..3060587 100644
--- a/sysprep/Makefile.am
+++ b/sysprep/Makefile.am
@@ -41,6 +41,7 @@ operations = \
 	dovecot_data \
 	flag_reconfiguration \
 	firstboot \
+	fs_uuids \
 	hostname \
 	kerberos_data \
 	lvm_uuids \
diff --git a/sysprep/sysprep_operation_fs_uuids.ml b/sysprep/sysprep_operation_fs_uuids.ml
new file mode 100644
index 0000000..3c319f0
--- /dev/null
+++ b/sysprep/sysprep_operation_fs_uuids.ml
@@ -0,0 +1,56 @@
+(* virt-sysprep
+ * Copyright (C) 2013 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 Sysprep_operation
+open Common_gettext.Gettext
+
+module G = Guestfs
+
+let rec fs_uuids_perform g root =
+  let fses = g#list_filesystems () in
+  List.iter (function
+  | _, "unknown" -> ()
+  | _, "swap" ->
+    (* XXX Not implemented *) ()
+  | dev, typ ->
+    let new_uuid = Common_utils.uuidgen () in
+    try
+      g#set_uuid dev new_uuid
+    with
+      G.Error msg ->
+        eprintf (f_"warning: cannot set random UUID on filesystem %s type %s: %s\n")
+          dev typ msg
+  ) fses;
+  []
+
+let fs_uuids_op = {
+  name = "fs-uuids";
+  enabled_by_default = true;
+  heading = s_"Change filesystem UUIDs";
+  pod_description = Some (s_"\
+On guests and filesystem types where this is supported,
+new random UUIDs are generated and assigned to filesystems.");
+  pod_notes = None;
+  extra_args = [];
+  perform_on_filesystems = None;
+  perform_on_devices = Some fs_uuids_perform;
+}
+
+let () = register_operation fs_uuids_op
-- 
1.8.3.1