Blame SOURCES/0047-daemon-Move-lvmetad-to-early-in-the-appliance-boot-p.patch

97ae69
From 3ad6840403edac13249d373d29c7d1f72b35c8b0 Mon Sep 17 00:00:00 2001
97ae69
From: "Richard W.M. Jones" <rjones@redhat.com>
97ae69
Date: Thu, 24 May 2018 10:24:25 +0100
97ae69
Subject: [PATCH] daemon: Move lvmetad to early in the appliance boot process.
97ae69
MIME-Version: 1.0
97ae69
Content-Type: text/plain; charset=UTF-8
97ae69
Content-Transfer-Encoding: 8bit
97ae69
97ae69
When the daemon starts up it creates a fresh (empty) LVM configuration
97ae69
and starts up lvmetad (which depends on the LVM configuration).
97ae69
97ae69
However this appears to cause problems: Some types of PV seem to
97ae69
require lvmetad and don't work without it
97ae69
(https://bugzilla.redhat.com/show_bug.cgi?id=1581810).  If we don't
97ae69
start lvmetad earlier, the device nodes are not created.
97ae69
97ae69
Therefore move the whole initialization step into appliance/init.
97ae69
97ae69
Two further changes had to be made:
97ae69
97ae69
Now we are using lvmetad all the time, using vgchange is incorrect.
97ae69
With lvmetad activated early we must use ‘pvscan --cache --activate ay’
97ae69
to scan all disks for PVs and activate any VGs on them (although the
97ae69
documentation is complex, confusing and contradictory so I'm not
97ae69
completely sure about this).
97ae69
97ae69
The ‘lvm_system_dir’ local variable in ‘daemon/lvm-filter.c’
97ae69
previously contained the path of the directory above $LVM_SYSTEM_DIR
97ae69
(eg. $LVM_SYSTEM_DIR = "/etc/lvm", lvm_system_dir = "/etc").  As this
97ae69
was highly confusing, I have changed it so the local variable and the
97ae69
environment variable have identical contents.  This involved removing
97ae69
the ‘lvm/’ component from a couple of paths since it is now included
97ae69
in the local variable.
97ae69
97ae69
(cherry picked from commit dd162d2cd56a2ecf4bcd40a7f463940eaac875b8)
97ae69
---
97ae69
 appliance/init      | 11 +++++-
97ae69
 daemon/daemon.h     |  4 ---
97ae69
 daemon/guestfsd.c   |  8 -----
97ae69
 daemon/lvm-filter.c | 81 +++++++++++++--------------------------------
97ae69
 4 files changed, 33 insertions(+), 71 deletions(-)
97ae69
97ae69
diff --git a/appliance/init b/appliance/init
97ae69
index 1cd264e08..471d83cae 100755
97ae69
--- a/appliance/init
97ae69
+++ b/appliance/init
97ae69
@@ -130,9 +130,17 @@ echo nameserver 169.254.2.3 > /etc/resolv.conf
97ae69
 # Scan for MDs but don't run arrays unless all expected drives are present
97ae69
 mdadm -As --auto=yes --no-degraded
97ae69
 
97ae69
+# Set up a clean LVM environment.
97ae69
+# Empty LVM configuration file means "all defaults".
97ae69
+mkdir -p /tmp/lvm
97ae69
+touch /tmp/lvm/lvm.conf
97ae69
+LVM_SYSTEM_DIR=/tmp/lvm
97ae69
+export LVM_SYSTEM_DIR
97ae69
+lvmetad
97ae69
+
97ae69
 # Scan for LVM.
97ae69
 modprobe dm_mod ||:
97ae69
-lvm vgchange -aay --sysinit
97ae69
+lvm pvscan --cache --activate ay
97ae69
 
97ae69
 # Scan for MDs and run all found arrays even they are in degraded state
97ae69
 mdadm -As --auto=yes --run
97ae69
@@ -146,6 +154,7 @@ if test "$guestfs_verbose" = 1 && test "$guestfs_boot_analysis" != 1; then
97ae69
     ls -lR /dev
97ae69
     cat /proc/mounts
97ae69
     cat /proc/mdstat
97ae69
+    lvm config
97ae69
     lvm pvs
97ae69
     lvm vgs
97ae69
     lvm lvs
97ae69
diff --git a/daemon/daemon.h b/daemon/daemon.h
97ae69
index 7958ba781..faaf1237e 100644
97ae69
--- a/daemon/daemon.h
97ae69
+++ b/daemon/daemon.h
97ae69
@@ -249,10 +249,6 @@ extern char *get_blkid_tag (const char *device, const char *tag);
97ae69
 /* lvm.c */
97ae69
 extern int lv_canonical (const char *device, char **ret);
97ae69
 
97ae69
-/* lvm-filter.c */
97ae69
-extern void clean_lvm_config (void);
97ae69
-extern void start_lvmetad (void);
97ae69
-
97ae69
 /* zero.c */
97ae69
 extern void wipe_device_before_mkfs (const char *device);
97ae69
 
97ae69
diff --git a/daemon/guestfsd.c b/daemon/guestfsd.c
97ae69
index 68d3de2ec..ae428e573 100644
97ae69
--- a/daemon/guestfsd.c
97ae69
+++ b/daemon/guestfsd.c
97ae69
@@ -233,14 +233,6 @@ main (int argc, char *argv[])
97ae69
   _umask (0);
97ae69
 #endif
97ae69
 
97ae69
-  /* Make a private copy of /etc/lvm so we can change the config (see
97ae69
-   * daemon/lvm-filter.c).
97ae69
-   */
97ae69
-  if (!test_mode) {
97ae69
-    clean_lvm_config ();
97ae69
-    start_lvmetad ();
97ae69
-  }
97ae69
-
97ae69
   /* Connect to virtio-serial channel. */
97ae69
   if (!channel)
97ae69
     channel = VIRTIO_SERIAL_CHANNEL;
97ae69
diff --git a/daemon/lvm-filter.c b/daemon/lvm-filter.c
97ae69
index ad85a7cc4..9d877c104 100644
97ae69
--- a/daemon/lvm-filter.c
97ae69
+++ b/daemon/lvm-filter.c
97ae69
@@ -36,71 +36,36 @@
97ae69
 #include "daemon.h"
97ae69
 #include "actions.h"
97ae69
 
97ae69
-/* This runs during daemon start up and creates a fresh LVM
97ae69
- * configuration which we can modify as we desire.  LVM allows
97ae69
- * configuration to be completely empty (meaning "all defaults").
97ae69
- *
97ae69
- * The final directory layout is:
97ae69
- *
97ae69
- *   /tmp/lvmXXXXXX                 (lvm_system_dir set to this)
97ae69
- *   /tmp/lvmXXXXXX/lvm             ($LVM_SYSTEM_DIR set to this)
97ae69
- *   /tmp/lvmXXXXXX/lvm/lvm.conf    (configuration file - initially empty)
97ae69
- */
97ae69
-static char lvm_system_dir[] = "/tmp/lvmXXXXXX";
97ae69
-
97ae69
-static void rm_lvm_system_dir (void);
97ae69
 static void debug_lvm_config (void);
97ae69
 
97ae69
-void
97ae69
-clean_lvm_config (void)
97ae69
-{
97ae69
-  char env[64], conf[64];
97ae69
-  FILE *fp;
97ae69
-
97ae69
-  if (mkdtemp (lvm_system_dir) == NULL)
97ae69
-    error (EXIT_FAILURE, errno, "mkdtemp: %s", lvm_system_dir);
97ae69
-
97ae69
-  snprintf (env, sizeof env, "%s/lvm", lvm_system_dir);
97ae69
-  mkdir (env, 0755);
97ae69
-  snprintf (conf, sizeof conf, "%s/lvm/lvm.conf", lvm_system_dir);
97ae69
-  fp = fopen (conf, "w");
97ae69
-  if (fp == NULL) {
97ae69
-    perror ("clean_lvm_config: cannot create empty lvm.conf");
97ae69
-    exit (EXIT_FAILURE);
97ae69
-  }
97ae69
-  fclose (fp);
97ae69
-
97ae69
-  /* Set environment variable so we use the clean configuration. */
97ae69
-  setenv ("LVM_SYSTEM_DIR", env, 1);
97ae69
-
97ae69
-  /* Set a handler to remove the temporary directory at exit. */
97ae69
-  atexit (rm_lvm_system_dir);
97ae69
+/* Read LVM_SYSTEM_DIR environment variable, or set it to a default
97ae69
+ * value if the environment variable is not set.
97ae69
+ */
97ae69
+static char *lvm_system_dir;
97ae69
+static void get_lvm_system_dir (void) __attribute__((constructor));
97ae69
+static void free_lvm_system_dir (void) __attribute__((destructor));
97ae69
 
97ae69
-  debug_lvm_config ();
97ae69
-}
97ae69
-
97ae69
-/* Try to run lvmetad, without failing if it couldn't. */
97ae69
-void
97ae69
-start_lvmetad (void)
97ae69
+static void
97ae69
+get_lvm_system_dir (void)
97ae69
 {
97ae69
-  int r;
97ae69
+  const char *p;
97ae69
 
97ae69
-  if (verbose)
97ae69
-    printf ("%s\n", "lvmetad");
97ae69
-  r = system ("lvmetad");
97ae69
-  if (r == -1)
97ae69
-    perror ("system/lvmetad");
97ae69
-  else if (!WIFEXITED (r) || WEXITSTATUS (r) != 0)
97ae69
-    fprintf (stderr, "warning: lvmetad command failed\n");
97ae69
+  p = getenv ("LVM_SYSTEM_DIR");
97ae69
+  if (p) {
97ae69
+    lvm_system_dir = strdup (p);
97ae69
+    if (lvm_system_dir == NULL) abort ();
97ae69
+  }
97ae69
+  if (!lvm_system_dir) {
97ae69
+    lvm_system_dir = strdup ("/etc/lvm");
97ae69
+    if (lvm_system_dir == NULL) abort ();
97ae69
+  }
97ae69
+  fprintf (stderr, "lvm_system_dir = %s\n", lvm_system_dir);
97ae69
 }
97ae69
 
97ae69
 static void
97ae69
-rm_lvm_system_dir (void)
97ae69
+free_lvm_system_dir (void)
97ae69
 {
97ae69
-  char cmd[64];
97ae69
-
97ae69
-  snprintf (cmd, sizeof cmd, "rm -rf %s", lvm_system_dir);
97ae69
-  ignore_value (system (cmd));
97ae69
+  free (lvm_system_dir);
97ae69
 }
97ae69
 
97ae69
 /* Rewrite the 'filter = [ ... ]' line in lvm.conf. */
97ae69
@@ -112,7 +77,7 @@ set_filter (char *const *filters)
97ae69
   FILE *fp;
97ae69
   size_t i, j;
97ae69
 
97ae69
-  if (asprintf (&conf, "%s/lvm/lvm.conf", lvm_system_dir) == -1) {
97ae69
+  if (asprintf (&conf, "%s/lvm.conf", lvm_system_dir) == -1) {
97ae69
     reply_with_perror ("asprintf");
97ae69
     return -1;
97ae69
   }
97ae69
@@ -177,7 +142,7 @@ static int
97ae69
 rescan (void)
97ae69
 {
97ae69
   char lvm_cache[64];
97ae69
-  snprintf (lvm_cache, sizeof lvm_cache, "%s/lvm/cache/.cache", lvm_system_dir);
97ae69
+  snprintf (lvm_cache, sizeof lvm_cache, "%s/cache/.cache", lvm_system_dir);
97ae69
 
97ae69
   unlink (lvm_cache);
97ae69
 
97ae69
-- 
97ae69
2.17.1
97ae69