From fe05a9318b6a6724027eaab06703c2e8a2f52746 Mon Sep 17 00:00:00 2001
From: Michele Tartara <mtartara@google.com>
Date: Mon, 8 Apr 2013 12:33:37 +0000
Subject: [PATCH] Fix job queue directory permission problems

If split users are used, the queue directory could only be accessed
by masterd, but also confd needs to be able to read it, e.g. when it
is queried as part of "gnt-job list"

This commit fixes the permissions in such a way to allow proper access rights.

Fixes Issue 406.

Signed-off-by: Michele Tartara <mtartara@google.com>
Reviewed-by: Guido Trotter <ultrotter@google.com>
---
 UPGRADE                  |  4 ++++
 lib/backend.py           |  6 +++---
 lib/constants.py         |  1 +
 lib/jqueue.py            |  3 ++-
 lib/jstore.py            |  9 ++++++---
 lib/tools/ensure_dirs.py | 26 +++++++++++++-------------
 6 files changed, 29 insertions(+), 20 deletions(-)

diff --git a/UPGRADE b/UPGRADE
index 61e1b9c1d..14022528a 100644
--- a/UPGRADE
+++ b/UPGRADE
@@ -47,6 +47,10 @@ To run commands on all nodes, the `distributed shell (dsh)
    (``cfgupgrade`` supports a number of parameters, run it with
    ``--help`` for more information)
 
+#. Upgrade the directory permissions on all nodes::
+
+    $ /usr/lib/ganeti/ensure-dirs --full-run
+
 #. Restart daemons on all nodes::
 
     $ /etc/init.d/ganeti restart
diff --git a/lib/backend.py b/lib/backend.py
index 569a6167d..9347d67ca 100644
--- a/lib/backend.py
+++ b/lib/backend.py
@@ -2962,7 +2962,7 @@ def JobQueueUpdate(file_name, content):
 
   # Write and replace the file atomically
   utils.WriteFile(file_name, data=_Decompress(content), uid=getents.masterd_uid,
-                  gid=getents.masterd_gid)
+                  gid=getents.daemons_gid, mode=constants.JOB_QUEUE_FILES_PERMS)
 
 
 def JobQueueRename(old, new):
@@ -2986,8 +2986,8 @@ def JobQueueRename(old, new):
 
   getents = runtime.GetEnts()
 
-  utils.RenameFile(old, new, mkdir=True, mkdir_mode=0700,
-                   dir_uid=getents.masterd_uid, dir_gid=getents.masterd_gid)
+  utils.RenameFile(old, new, mkdir=True, mkdir_mode=0750,
+                   dir_uid=getents.masterd_uid, dir_gid=getents.daemons_gid)
 
 
 def BlockdevClose(instance_name, disks):
diff --git a/lib/constants.py b/lib/constants.py
index 0fa47de32..03c241e5d 100644
--- a/lib/constants.py
+++ b/lib/constants.py
@@ -1677,6 +1677,7 @@ NODE_EVAC_MODES = compat.UniqueFrozenset([
 # Job queue
 JOB_QUEUE_VERSION = 1
 JOB_QUEUE_SIZE_HARD_LIMIT = 5000
+JOB_QUEUE_FILES_PERMS = 0640
 
 JOB_ID_TEMPLATE = r"\d+"
 JOB_FILE_RE = re.compile(r"^job-(%s)$" % JOB_ID_TEMPLATE)
diff --git a/lib/jqueue.py b/lib/jqueue.py
index 9752f9306..7ad2ea8ca 100644
--- a/lib/jqueue.py
+++ b/lib/jqueue.py
@@ -1885,7 +1885,8 @@ class JobQueue(object):
     """
     getents = runtime.GetEnts()
     utils.WriteFile(file_name, data=data, uid=getents.masterd_uid,
-                    gid=getents.masterd_gid)
+                    gid=getents.daemons_gid,
+                    mode=constants.JOB_QUEUE_FILES_PERMS)
 
     if replicate:
       names, addrs = self._GetNodeIp()
diff --git a/lib/jstore.py b/lib/jstore.py
index f20da0604..324f91e1f 100644
--- a/lib/jstore.py
+++ b/lib/jstore.py
@@ -111,7 +111,8 @@ def InitAndVerifyQueue(must_lock):
       if version is None:
         # Write new version file
         utils.WriteFile(pathutils.JOB_QUEUE_VERSION_FILE,
-                        uid=getents.masterd_uid, gid=getents.masterd_gid,
+                        uid=getents.masterd_uid, gid=getents.daemons_gid,
+                        mode=constants.JOB_QUEUE_FILES_PERMS,
                         data="%s\n" % constants.JOB_QUEUE_VERSION)
 
         # Read again
@@ -125,7 +126,8 @@ def InitAndVerifyQueue(must_lock):
       if serial is None:
         # Write new serial file
         utils.WriteFile(pathutils.JOB_QUEUE_SERIAL_FILE,
-                        uid=getents.masterd_uid, gid=getents.masterd_gid,
+                        uid=getents.masterd_uid, gid=getents.daemons_gid,
+                        mode=constants.JOB_QUEUE_FILES_PERMS,
                         data="%s\n" % 0)
 
         # Read again
@@ -174,7 +176,8 @@ def SetDrainFlag(drain_flag):
 
   if drain_flag:
     utils.WriteFile(pathutils.JOB_QUEUE_DRAIN_FILE, data="",
-                    uid=getents.masterd_uid, gid=getents.masterd_gid)
+                    uid=getents.masterd_uid, gid=getents.daemons_gid,
+                    mode=constants.JOB_QUEUE_FILES_PERMS)
   else:
     utils.RemoveFile(pathutils.JOB_QUEUE_DRAIN_FILE)
 
diff --git a/lib/tools/ensure_dirs.py b/lib/tools/ensure_dirs.py
index 95d2fcec6..b4409cc49 100644
--- a/lib/tools/ensure_dirs.py
+++ b/lib/tools/ensure_dirs.py
@@ -159,19 +159,19 @@ def GetPaths():
                   getent.noded_uid, getent.noded_gid, False))
 
   paths.extend([
-    (pathutils.QUEUE_DIR, DIR, 0700, getent.masterd_uid, getent.masterd_gid),
-    (pathutils.QUEUE_DIR, QUEUE_DIR, 0600,
-     getent.masterd_uid, getent.masterd_gid),
+    (pathutils.QUEUE_DIR, DIR, 0750, getent.masterd_uid, getent.daemons_gid),
+    (pathutils.QUEUE_DIR, QUEUE_DIR, constants.JOB_QUEUE_FILES_PERMS,
+     getent.masterd_uid, getent.daemons_gid),
     (pathutils.JOB_QUEUE_DRAIN_FILE, FILE, 0644,
-     getent.masterd_uid, getent.masterd_gid, False),
-    (pathutils.JOB_QUEUE_LOCK_FILE, FILE, 0600,
-     getent.masterd_uid, getent.masterd_gid, False),
-    (pathutils.JOB_QUEUE_SERIAL_FILE, FILE, 0600,
-     getent.masterd_uid, getent.masterd_gid, False),
-    (pathutils.JOB_QUEUE_VERSION_FILE, FILE, 0600,
-     getent.masterd_uid, getent.masterd_gid, False),
-    (pathutils.JOB_QUEUE_ARCHIVE_DIR, DIR, 0700,
-     getent.masterd_uid, getent.masterd_gid),
+     getent.masterd_uid, getent.daemons_gid, False),
+    (pathutils.JOB_QUEUE_LOCK_FILE, FILE, constants.JOB_QUEUE_FILES_PERMS,
+     getent.masterd_uid, getent.daemons_gid, False),
+    (pathutils.JOB_QUEUE_SERIAL_FILE, FILE, constants.JOB_QUEUE_FILES_PERMS,
+     getent.masterd_uid, getent.daemons_gid, False),
+    (pathutils.JOB_QUEUE_VERSION_FILE, FILE, constants.JOB_QUEUE_FILES_PERMS,
+     getent.masterd_uid, getent.daemons_gid, False),
+    (pathutils.JOB_QUEUE_ARCHIVE_DIR, DIR, 0740,
+     getent.masterd_uid, getent.daemons_gid),
     (rapi_dir, DIR, 0750, getent.rapi_uid, getent.masterd_gid),
     (pathutils.RAPI_USERS_FILE, FILE, 0640,
      getent.rapi_uid, getent.masterd_gid, False),
@@ -244,7 +244,7 @@ def Main():
 
     if opts.full_run:
       RecursiveEnsure(pathutils.JOB_QUEUE_ARCHIVE_DIR, getent.masterd_uid,
-                      getent.masterd_gid, 0700, 0600)
+                      getent.daemons_gid, 0750, constants.JOB_QUEUE_FILES_PERMS)
   except errors.GenericError, err:
     logging.error("An error occurred while setting permissions: %s", err)
     return constants.EXIT_FAILURE
-- 
GitLab