Blame SOURCES/016-CVE-2020-25654.patch

fc3051
From 3aa33bcc9c70d197b5ed0760b12d65dfab4d4da5 Mon Sep 17 00:00:00 2001
fc3051
From: Ken Gaillot <kgaillot@redhat.com>
fc3051
Date: Fri, 9 Oct 2020 09:56:03 -0500
fc3051
Subject: [PATCH 1/7] Log: executor: show CRM_OP_REGISTER rc in debug message
fc3051
fc3051
Previously, process_lrmd_signon() would add the rc to the client reply
fc3051
but not pass it back to process_lrmd_message(), which would always log "OK" in
fc3051
its debug message, even if the sign-on was rejected.
fc3051
---
fc3051
 daemons/execd/execd_commands.c | 21 +++++++++++----------
fc3051
 1 file changed, 11 insertions(+), 10 deletions(-)
fc3051
fc3051
diff --git a/daemons/execd/execd_commands.c b/daemons/execd/execd_commands.c
fc3051
index 4d0e457..8487dd4 100644
fc3051
--- a/daemons/execd/execd_commands.c
fc3051
+++ b/daemons/execd/execd_commands.c
fc3051
@@ -1494,10 +1494,10 @@ free_rsc(gpointer data)
fc3051
     free(rsc);
fc3051
 }
fc3051
 
fc3051
-static xmlNode *
fc3051
-process_lrmd_signon(pcmk__client_t *client, xmlNode *request, int call_id)
fc3051
+static int
fc3051
+process_lrmd_signon(pcmk__client_t *client, xmlNode *request, int call_id,
fc3051
+                    xmlNode **reply)
fc3051
 {
fc3051
-    xmlNode *reply = NULL;
fc3051
     int rc = pcmk_ok;
fc3051
     const char *is_ipc_provider = crm_element_value(request, F_LRMD_IS_IPC_PROVIDER);
fc3051
     const char *protocol_version = crm_element_value(request, F_LRMD_PROTOCOL_VERSION);
fc3051
@@ -1508,18 +1508,19 @@ process_lrmd_signon(pcmk__client_t *client, xmlNode *request, int call_id)
fc3051
         rc = -EPROTO;
fc3051
     }
fc3051
 
fc3051
-    reply = create_lrmd_reply(__FUNCTION__, rc, call_id);
fc3051
-    crm_xml_add(reply, F_LRMD_OPERATION, CRM_OP_REGISTER);
fc3051
-    crm_xml_add(reply, F_LRMD_CLIENTID, client->id);
fc3051
-    crm_xml_add(reply, F_LRMD_PROTOCOL_VERSION, LRMD_PROTOCOL_VERSION);
fc3051
-
fc3051
     if (crm_is_true(is_ipc_provider)) {
fc3051
         // This is a remote connection from a cluster node's controller
fc3051
 #ifdef SUPPORT_REMOTE
fc3051
         ipc_proxy_add_provider(client);
fc3051
 #endif
fc3051
     }
fc3051
-    return reply;
fc3051
+
fc3051
+    *reply = create_lrmd_reply(__func__, rc, call_id);
fc3051
+    crm_xml_add(*reply, F_LRMD_OPERATION, CRM_OP_REGISTER);
fc3051
+    crm_xml_add(*reply, F_LRMD_CLIENTID, client->id);
fc3051
+    crm_xml_add(*reply, F_LRMD_PROTOCOL_VERSION, LRMD_PROTOCOL_VERSION);
fc3051
+
fc3051
+    return rc;
fc3051
 }
fc3051
 
fc3051
 static int
fc3051
@@ -1832,7 +1833,7 @@ process_lrmd_message(pcmk__client_t *client, uint32_t id, xmlNode *request)
fc3051
 #endif
fc3051
         do_reply = 1;
fc3051
     } else if (crm_str_eq(op, CRM_OP_REGISTER, TRUE)) {
fc3051
-        reply = process_lrmd_signon(client, request, call_id);
fc3051
+        rc = process_lrmd_signon(client, request, call_id, &reply);
fc3051
         do_reply = 1;
fc3051
     } else if (crm_str_eq(op, LRMD_OP_RSC_REG, TRUE)) {
fc3051
         rc = process_lrmd_rsc_register(client, id, request);
fc3051
-- 
fc3051
1.8.3.1
fc3051
fc3051
fc3051
From d0002343faa4595e42b790119b7f3037db1130c4 Mon Sep 17 00:00:00 2001
fc3051
From: Ken Gaillot <kgaillot@redhat.com>
fc3051
Date: Fri, 9 Oct 2020 15:16:39 -0500
fc3051
Subject: [PATCH 2/7] Low: executor: mark controller connections to
fc3051
 pacemaker-remoted as privileged
fc3051
fc3051
Previously, pcmk__client_privileged was only set when local clients connected
fc3051
(as root or hacluster). Now, set it when pacemaker-remoted successfully
fc3051
completes the TLS handshake with a remote client (i.e., the controller on a
fc3051
cluster node).
fc3051
fc3051
This has no effect as of this commit but will with later commits.
fc3051
---
fc3051
 daemons/execd/remoted_tls.c | 5 +++++
fc3051
 1 file changed, 5 insertions(+)
fc3051
fc3051
diff --git a/daemons/execd/remoted_tls.c b/daemons/execd/remoted_tls.c
fc3051
index 1a1f8b2..c835549 100644
fc3051
--- a/daemons/execd/remoted_tls.c
fc3051
+++ b/daemons/execd/remoted_tls.c
fc3051
@@ -72,6 +72,11 @@ remoted__read_handshake_data(pcmk__client_t *client)
fc3051
     client->remote->tls_handshake_complete = TRUE;
fc3051
     crm_notice("Remote client connection accepted");
fc3051
 
fc3051
+    /* Only a client with access to the TLS key can connect, so we can treat
fc3051
+     * it as privileged.
fc3051
+     */
fc3051
+    set_bit(client->flags, pcmk__client_privileged);
fc3051
+
fc3051
     // Alert other clients of the new connection
fc3051
     notify_of_new_client(client);
fc3051
     return 0;
fc3051
-- 
fc3051
1.8.3.1
fc3051
fc3051
fc3051
From 3db100d775aee214fff8f54eae0076a5fcc41c56 Mon Sep 17 00:00:00 2001
fc3051
From: Ken Gaillot <kgaillot@redhat.com>
fc3051
Date: Thu, 15 Oct 2020 15:33:13 -0500
fc3051
Subject: [PATCH 3/7] Low: executor: return appropriate error code when no
fc3051
 remote support
fc3051
fc3051
---
fc3051
 daemons/execd/execd_commands.c | 6 +++++-
fc3051
 1 file changed, 5 insertions(+), 1 deletion(-)
fc3051
fc3051
diff --git a/daemons/execd/execd_commands.c b/daemons/execd/execd_commands.c
fc3051
index 8487dd4..41c8169 100644
fc3051
--- a/daemons/execd/execd_commands.c
fc3051
+++ b/daemons/execd/execd_commands.c
fc3051
@@ -1509,9 +1509,11 @@ process_lrmd_signon(pcmk__client_t *client, xmlNode *request, int call_id,
fc3051
     }
fc3051
 
fc3051
     if (crm_is_true(is_ipc_provider)) {
fc3051
-        // This is a remote connection from a cluster node's controller
fc3051
 #ifdef SUPPORT_REMOTE
fc3051
+        // This is a remote connection from a cluster node's controller
fc3051
         ipc_proxy_add_provider(client);
fc3051
+#else
fc3051
+        rc = -EPROTONOSUPPORT;
fc3051
 #endif
fc3051
     }
fc3051
 
fc3051
@@ -1830,6 +1832,8 @@ process_lrmd_message(pcmk__client_t *client, uint32_t id, xmlNode *request)
fc3051
     if (crm_str_eq(op, CRM_OP_IPC_FWD, TRUE)) {
fc3051
 #ifdef SUPPORT_REMOTE
fc3051
         ipc_proxy_forward_client(client, request);
fc3051
+#else
fc3051
+        rc = -EPROTONOSUPPORT;
fc3051
 #endif
fc3051
         do_reply = 1;
fc3051
     } else if (crm_str_eq(op, CRM_OP_REGISTER, TRUE)) {
fc3051
-- 
fc3051
1.8.3.1
fc3051
fc3051
fc3051
From f273f1c16f21ff96983797ed5ceb2978dafe545a Mon Sep 17 00:00:00 2001
fc3051
From: Ken Gaillot <kgaillot@redhat.com>
fc3051
Date: Thu, 15 Oct 2020 15:33:57 -0500
fc3051
Subject: [PATCH 4/7] High: executor: restrict certain IPC requests to
fc3051
 Pacemaker daemons
fc3051
fc3051
The executor IPC API allows clients to register resources, request agent
fc3051
execution, and so forth.
fc3051
fc3051
If ACLs are enabled, this could allow an ACL-restricted user to bypass ACLs and
fc3051
execute any code as root. (If ACLs are not enabled, users in the haclient group
fc3051
have full access to the CIB, which already gives them that ability, so there is
fc3051
no additional exposure in that case.)
fc3051
fc3051
When ACLs are supported, this commit effectively disables the executor IPC API
fc3051
for clients that aren't connecting as root or hacluster. Such clients can only
fc3051
register and poke now.
fc3051
---
fc3051
 daemons/execd/execd_commands.c | 91 +++++++++++++++++++++++++++++++++---------
fc3051
 1 file changed, 73 insertions(+), 18 deletions(-)
fc3051
fc3051
diff --git a/daemons/execd/execd_commands.c b/daemons/execd/execd_commands.c
fc3051
index 41c8169..207eb6a 100644
fc3051
--- a/daemons/execd/execd_commands.c
fc3051
+++ b/daemons/execd/execd_commands.c
fc3051
@@ -1510,8 +1510,12 @@ process_lrmd_signon(pcmk__client_t *client, xmlNode *request, int call_id,
fc3051
 
fc3051
     if (crm_is_true(is_ipc_provider)) {
fc3051
 #ifdef SUPPORT_REMOTE
fc3051
-        // This is a remote connection from a cluster node's controller
fc3051
-        ipc_proxy_add_provider(client);
fc3051
+        if ((client->remote != NULL) && client->remote->tls_handshake_complete) {
fc3051
+            // This is a remote connection from a cluster node's controller
fc3051
+            ipc_proxy_add_provider(client);
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
 #else
fc3051
         rc = -EPROTONOSUPPORT;
fc3051
 #endif
fc3051
@@ -1826,12 +1830,26 @@ process_lrmd_message(pcmk__client_t *client, uint32_t id, xmlNode *request)
fc3051
     int do_notify = 0;
fc3051
     xmlNode *reply = NULL;
fc3051
 
fc3051
+    bool allowed = true;
fc3051
+
fc3051
+#if ENABLE_ACL
fc3051
+    /* Certain IPC commands may be done only by privileged users (i.e. root or
fc3051
+     * hacluster) when ACLs are enabled, because they would otherwise provide a
fc3051
+     * means of bypassing ACLs.
fc3051
+     */
fc3051
+    allowed = is_set(client->flags, pcmk__client_privileged);
fc3051
+#endif
fc3051
+
fc3051
     crm_trace("Processing %s operation from %s", op, client->id);
fc3051
     crm_element_value_int(request, F_LRMD_CALLID, &call_id);
fc3051
 
fc3051
     if (crm_str_eq(op, CRM_OP_IPC_FWD, TRUE)) {
fc3051
 #ifdef SUPPORT_REMOTE
fc3051
-        ipc_proxy_forward_client(client, request);
fc3051
+        if (allowed) {
fc3051
+            ipc_proxy_forward_client(client, request);
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
 #else
fc3051
         rc = -EPROTONOSUPPORT;
fc3051
 #endif
fc3051
@@ -1840,38 +1858,70 @@ process_lrmd_message(pcmk__client_t *client, uint32_t id, xmlNode *request)
fc3051
         rc = process_lrmd_signon(client, request, call_id, &reply);
fc3051
         do_reply = 1;
fc3051
     } else if (crm_str_eq(op, LRMD_OP_RSC_REG, TRUE)) {
fc3051
-        rc = process_lrmd_rsc_register(client, id, request);
fc3051
-        do_notify = 1;
fc3051
+        if (allowed) {
fc3051
+            rc = process_lrmd_rsc_register(client, id, request);
fc3051
+            do_notify = 1;
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
         do_reply = 1;
fc3051
     } else if (crm_str_eq(op, LRMD_OP_RSC_INFO, TRUE)) {
fc3051
-        reply = process_lrmd_get_rsc_info(request, call_id);
fc3051
+        if (allowed) {
fc3051
+            reply = process_lrmd_get_rsc_info(request, call_id);
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
         do_reply = 1;
fc3051
     } else if (crm_str_eq(op, LRMD_OP_RSC_UNREG, TRUE)) {
fc3051
-        rc = process_lrmd_rsc_unregister(client, id, request);
fc3051
-        /* don't notify anyone about failed un-registers */
fc3051
-        if (rc == pcmk_ok || rc == -EINPROGRESS) {
fc3051
-            do_notify = 1;
fc3051
+        if (allowed) {
fc3051
+            rc = process_lrmd_rsc_unregister(client, id, request);
fc3051
+            /* don't notify anyone about failed un-registers */
fc3051
+            if (rc == pcmk_ok || rc == -EINPROGRESS) {
fc3051
+                do_notify = 1;
fc3051
+            }
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
         }
fc3051
         do_reply = 1;
fc3051
     } else if (crm_str_eq(op, LRMD_OP_RSC_EXEC, TRUE)) {
fc3051
-        rc = process_lrmd_rsc_exec(client, id, request);
fc3051
+        if (allowed) {
fc3051
+            rc = process_lrmd_rsc_exec(client, id, request);
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
         do_reply = 1;
fc3051
     } else if (crm_str_eq(op, LRMD_OP_RSC_CANCEL, TRUE)) {
fc3051
-        rc = process_lrmd_rsc_cancel(client, id, request);
fc3051
+        if (allowed) {
fc3051
+            rc = process_lrmd_rsc_cancel(client, id, request);
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
         do_reply = 1;
fc3051
     } else if (crm_str_eq(op, LRMD_OP_POKE, TRUE)) {
fc3051
         do_notify = 1;
fc3051
         do_reply = 1;
fc3051
     } else if (crm_str_eq(op, LRMD_OP_CHECK, TRUE)) {
fc3051
-        xmlNode *data = get_message_xml(request, F_LRMD_CALLDATA); 
fc3051
-        const char *timeout = crm_element_value(data, F_LRMD_WATCHDOG);
fc3051
-        CRM_LOG_ASSERT(data != NULL);
fc3051
-        pcmk__valid_sbd_timeout(timeout);
fc3051
+        if (allowed) {
fc3051
+            xmlNode *data = get_message_xml(request, F_LRMD_CALLDATA);
fc3051
+
fc3051
+            CRM_LOG_ASSERT(data != NULL);
fc3051
+            pcmk__valid_sbd_timeout(crm_element_value(data, F_LRMD_WATCHDOG));
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
     } else if (crm_str_eq(op, LRMD_OP_ALERT_EXEC, TRUE)) {
fc3051
-        rc = process_lrmd_alert_exec(client, id, request);
fc3051
+        if (allowed) {
fc3051
+            rc = process_lrmd_alert_exec(client, id, request);
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
         do_reply = 1;
fc3051
     } else if (crm_str_eq(op, LRMD_OP_GET_RECURRING, TRUE)) {
fc3051
-        reply = process_lrmd_get_recurring(request, call_id);
fc3051
+        if (allowed) {
fc3051
+            reply = process_lrmd_get_recurring(request, call_id);
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
         do_reply = 1;
fc3051
     } else {
fc3051
         rc = -EOPNOTSUPP;
fc3051
@@ -1879,6 +1929,11 @@ process_lrmd_message(pcmk__client_t *client, uint32_t id, xmlNode *request)
fc3051
         crm_err("Unknown IPC request '%s' from %s", op, client->name);
fc3051
     }
fc3051
 
fc3051
+    if (rc == -EACCES) {
fc3051
+        crm_warn("Rejecting IPC request '%s' from unprivileged client %s",
fc3051
+                 op, pcmk__client_name(client));
fc3051
+    }
fc3051
+
fc3051
     crm_debug("Processed %s operation from %s: rc=%d, reply=%d, notify=%d",
fc3051
               op, client->id, rc, do_reply, do_notify);
fc3051
 
fc3051
-- 
fc3051
1.8.3.1
fc3051
fc3051
fc3051
From f13759f6971402dac3bea1aac45214a84d838728 Mon Sep 17 00:00:00 2001
fc3051
From: Ken Gaillot <kgaillot@redhat.com>
fc3051
Date: Fri, 9 Oct 2020 11:16:43 -0500
fc3051
Subject: [PATCH 5/7] Low: pacemakerd: check client for NULL before using it
fc3051
fc3051
... to guard against bugs in client tracking
fc3051
---
fc3051
 daemons/pacemakerd/pacemakerd.c | 5 ++++-
fc3051
 1 file changed, 4 insertions(+), 1 deletion(-)
fc3051
fc3051
diff --git a/daemons/pacemakerd/pacemakerd.c b/daemons/pacemakerd/pacemakerd.c
fc3051
index 5ed4626..573ea5a 100644
fc3051
--- a/daemons/pacemakerd/pacemakerd.c
fc3051
+++ b/daemons/pacemakerd/pacemakerd.c
fc3051
@@ -553,9 +553,12 @@ pcmk_ipc_dispatch(qb_ipcs_connection_t * qbc, void *data, size_t size)
fc3051
     uint32_t id = 0;
fc3051
     uint32_t flags = 0;
fc3051
     const char *task = NULL;
fc3051
+    xmlNode *msg = NULL;
fc3051
     pcmk__client_t *c = pcmk__find_client(qbc);
fc3051
-    xmlNode *msg = pcmk__client_data2xml(c, data, &id, &flags);
fc3051
 
fc3051
+    CRM_CHECK(c != NULL, return 0);
fc3051
+
fc3051
+    msg = pcmk__client_data2xml(c, data, &id, &flags);
fc3051
     pcmk__ipc_send_ack(c, id, flags, "ack");
fc3051
     if (msg == NULL) {
fc3051
         return 0;
fc3051
-- 
fc3051
1.8.3.1
fc3051
fc3051
fc3051
From 021081c1e28b254a0f68143fa55e517f0fcc4edb Mon Sep 17 00:00:00 2001
fc3051
From: Ken Gaillot <kgaillot@redhat.com>
fc3051
Date: Fri, 9 Oct 2020 11:17:18 -0500
fc3051
Subject: [PATCH 6/7] High: pacemakerd: ignore shutdown requests from
fc3051
 unprivileged users
fc3051
fc3051
The pacemakerd IPC API supports a shutdown request, along with a
fc3051
command-line interface for using it (pacemakerd --shutdown).
fc3051
fc3051
Only the haclient group has access to the IPC. Without ACLs, that group can
fc3051
already shut down Pacemaker via the CIB, so there's no security implication.
fc3051
fc3051
However, it might not be desired to allow ACL-restricted users to shut down
fc3051
Pacemaker, so block users other than root or hacluster if ACLs are supported.
fc3051
---
fc3051
 daemons/pacemakerd/pacemakerd.c | 24 ++++++++++++++++++++----
fc3051
 1 file changed, 20 insertions(+), 4 deletions(-)
fc3051
fc3051
diff --git a/daemons/pacemakerd/pacemakerd.c b/daemons/pacemakerd/pacemakerd.c
fc3051
index 573ea5a..2e69bd1 100644
fc3051
--- a/daemons/pacemakerd/pacemakerd.c
fc3051
+++ b/daemons/pacemakerd/pacemakerd.c
fc3051
@@ -566,9 +566,26 @@ pcmk_ipc_dispatch(qb_ipcs_connection_t * qbc, void *data, size_t size)
fc3051
 
fc3051
     task = crm_element_value(msg, F_CRM_TASK);
fc3051
     if (crm_str_eq(task, CRM_OP_QUIT, TRUE)) {
fc3051
-        crm_notice("Shutting down in response to IPC request %s from %s",
fc3051
-                   crm_element_value(msg, F_CRM_REFERENCE), crm_element_value(msg, F_CRM_ORIGIN));
fc3051
-        pcmk_shutdown(15);
fc3051
+        bool allowed = true;
fc3051
+
fc3051
+#if ENABLE_ACL
fc3051
+        /* Only allow privileged users (i.e. root or hacluster)
fc3051
+         * to shut down Pacemaker from the command line (or direct IPC).
fc3051
+         *
fc3051
+         * We only check when ACLs are enabled, because without them, any client
fc3051
+         * with IPC access could shut down Pacemaker via the CIB anyway.
fc3051
+         */
fc3051
+        allowed = is_set(c->flags, pcmk__client_privileged);
fc3051
+#endif
fc3051
+        if (allowed) {
fc3051
+            crm_notice("Shutting down in response to IPC request %s from %s",
fc3051
+                       crm_element_value(msg, F_CRM_REFERENCE),
fc3051
+                       crm_element_value(msg, F_CRM_ORIGIN));
fc3051
+            pcmk_shutdown(15);
fc3051
+        } else {
fc3051
+            crm_warn("Ignoring shutdown request from unprivileged client %s",
fc3051
+                     pcmk__client_name(c));
fc3051
+        }
fc3051
 
fc3051
     } else if (crm_str_eq(task, CRM_OP_RM_NODE_CACHE, TRUE)) {
fc3051
         crm_trace("Ignoring IPC request to purge node "
fc3051
-- 
fc3051
1.8.3.1
fc3051
fc3051
fc3051
From 80eb5ddfd529be02214f38669f1b177535186fbc Mon Sep 17 00:00:00 2001
fc3051
From: Ken Gaillot <kgaillot@redhat.com>
fc3051
Date: Fri, 9 Oct 2020 11:55:26 -0500
fc3051
Subject: [PATCH 7/7] Fix: fencer: restrict certain IPC requests to privileged
fc3051
 users
fc3051
fc3051
The fencer IPC API allows clients to register fence devices.
fc3051
fc3051
If ACLs are enabled, this could allow an ACL-restricted user to bypass ACLs to
fc3051
configure fencing. If the user is able to install executables to the standard
fc3051
fencing agent locations, have arbitrary code executed as root (the standard
fc3051
locations generally require root for write access, so that is unlikely to be an
fc3051
issue).
fc3051
fc3051
If ACLs are not enabled, users in the haclient group have full access to the
fc3051
CIB, which already gives them these capabilities, so there is no additional
fc3051
exposure in that case.
fc3051
fc3051
This commit does not restrict unprivileged users from using other fencing API,
fc3051
such as requesting actual fencing.
fc3051
---
fc3051
 daemons/fenced/fenced_commands.c | 41 ++++++++++++++++++++++++++++++++++++----
fc3051
 1 file changed, 37 insertions(+), 4 deletions(-)
fc3051
fc3051
diff --git a/daemons/fenced/fenced_commands.c b/daemons/fenced/fenced_commands.c
fc3051
index 859e7b7..a8c90a6 100644
fc3051
--- a/daemons/fenced/fenced_commands.c
fc3051
+++ b/daemons/fenced/fenced_commands.c
fc3051
@@ -2531,6 +2531,18 @@ handle_request(pcmk__client_t *client, uint32_t id, uint32_t flags,
fc3051
     const char *op = crm_element_value(request, F_STONITH_OPERATION);
fc3051
     const char *client_id = crm_element_value(request, F_STONITH_CLIENTID);
fc3051
 
fc3051
+    bool allowed = true;
fc3051
+
fc3051
+#if ENABLE_ACL
fc3051
+    /* IPC commands related to fencing configuration may be done only by
fc3051
+     * privileged users (i.e. root or hacluster) when ACLs are supported,
fc3051
+     * because all other users should go through the CIB to have ACLs applied.
fc3051
+     */
fc3051
+    if (client != NULL) {
fc3051
+        allowed = is_set(client->flags, pcmk__client_privileged);
fc3051
+    }
fc3051
+#endif
fc3051
+
fc3051
     crm_element_value_int(request, F_STONITH_CALLOPTS, &call_options);
fc3051
 
fc3051
     if (is_set(call_options, st_opt_sync_call)) {
fc3051
@@ -2687,27 +2699,43 @@ handle_request(pcmk__client_t *client, uint32_t id, uint32_t flags,
fc3051
     } else if (crm_str_eq(op, STONITH_OP_DEVICE_ADD, TRUE)) {
fc3051
         const char *device_id = NULL;
fc3051
 
fc3051
-        rc = stonith_device_register(request, &device_id, FALSE);
fc3051
+        if (allowed) {
fc3051
+            rc = stonith_device_register(request, &device_id, FALSE);
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
         do_stonith_notify_device(call_options, op, rc, device_id);
fc3051
 
fc3051
     } else if (crm_str_eq(op, STONITH_OP_DEVICE_DEL, TRUE)) {
fc3051
         xmlNode *dev = get_xpath_object("//" F_STONITH_DEVICE, request, LOG_ERR);
fc3051
         const char *device_id = crm_element_value(dev, XML_ATTR_ID);
fc3051
 
fc3051
-        rc = stonith_device_remove(device_id, FALSE);
fc3051
+        if (allowed) {
fc3051
+            rc = stonith_device_remove(device_id, FALSE);
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
         do_stonith_notify_device(call_options, op, rc, device_id);
fc3051
 
fc3051
     } else if (crm_str_eq(op, STONITH_OP_LEVEL_ADD, TRUE)) {
fc3051
         char *device_id = NULL;
fc3051
 
fc3051
-        rc = stonith_level_register(request, &device_id);
fc3051
+        if (allowed) {
fc3051
+            rc = stonith_level_register(request, &device_id);
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
         do_stonith_notify_level(call_options, op, rc, device_id);
fc3051
         free(device_id);
fc3051
 
fc3051
     } else if (crm_str_eq(op, STONITH_OP_LEVEL_DEL, TRUE)) {
fc3051
         char *device_id = NULL;
fc3051
 
fc3051
-        rc = stonith_level_remove(request, &device_id);
fc3051
+        if (allowed) {
fc3051
+            rc = stonith_level_remove(request, &device_id);
fc3051
+        } else {
fc3051
+            rc = -EACCES;
fc3051
+        }
fc3051
         do_stonith_notify_level(call_options, op, rc, device_id);
fc3051
 
fc3051
     } else if(safe_str_eq(op, CRM_OP_RM_NODE_CACHE)) {
fc3051
@@ -2727,6 +2755,11 @@ handle_request(pcmk__client_t *client, uint32_t id, uint32_t flags,
fc3051
 
fc3051
   done:
fc3051
 
fc3051
+    if (rc == -EACCES) {
fc3051
+        crm_warn("Rejecting IPC request '%s' from unprivileged client %s",
fc3051
+                 crm_str(op), pcmk__client_name(client));
fc3051
+    }
fc3051
+
fc3051
     /* Always reply unless the request is in process still.
fc3051
      * If in progress, a reply will happen async after the request
fc3051
      * processing is finished */
fc3051
-- 
fc3051
1.8.3.1
fc3051