pacemaker 2.1.5-a3f44794f94
Scalable High-Availability cluster resource manager
ipc_internal.h
Go to the documentation of this file.
1/*
2 * Copyright 2013-2022 the Pacemaker project contributors
3 *
4 * The version control history for this file may have further details.
5 *
6 * This source code is licensed under the GNU Lesser General Public License
7 * version 2.1 or later (LGPLv2.1+) WITHOUT ANY WARRANTY.
8 */
9
10#ifndef PCMK__IPC_INTERNAL_H
11#define PCMK__IPC_INTERNAL_H
12
13#ifdef __cplusplus
14extern "C" {
15#endif
16
17#include <stdbool.h> // bool
18#include <stdint.h> // uint32_t, uint64_t, UINT64_C()
19#include <sys/uio.h> // struct iovec
20#include <sys/types.h> // uid_t, gid_t, pid_t, size_t
21
22#ifdef HAVE_GNUTLS_GNUTLS_H
23# include <gnutls/gnutls.h> // gnutls_session_t
24#endif
25
26#include <glib.h> // guint, gpointer, GQueue, ...
27#include <libxml/tree.h> // xmlNode
28#include <qb/qbipcs.h> // qb_ipcs_connection_t, ...
29
30#include <crm_config.h> // HAVE_GETPEEREID
31#include <crm/common/ipc.h>
32#include <crm/common/ipc_pacemakerd.h> // enum pcmk_pacemakerd_state
33#include <crm/common/mainloop.h> // mainloop_io_t
34
35/*
36 * XML attribute names used only by internal code
37 */
38
39#define PCMK__XA_IPC_PROTO_VERSION "ipc-protocol-version"
40
41/* denotes "non yieldable PID" on FreeBSD, or actual PID1 in scenarios that
42 require a delicate handling anyway (socket-based activation with systemd);
43 we can be reasonably sure that this PID is never possessed by the actual
44 child daemon, as it gets taken either by the proper init, or by pacemakerd
45 itself (i.e. this precludes anything else); note that value of zero
46 is meant to carry "unset" meaning, and better not to bet on/conditionalize
47 over signedness of pid_t */
48#define PCMK__SPECIAL_PID 1
49
50// Timeout (in seconds) to use for IPC client sends, reply waits, etc.
51#define PCMK__IPC_TIMEOUT 120
52
53#if defined(HAVE_GETPEEREID)
54/* on FreeBSD, we don't want to expose "non-yieldable PID" (leading to
55 "IPC liveness check only") as its nominal representation, which could
56 cause confusion -- this is unambiguous as long as there's no
57 socket-based activation like with systemd (very improbable) */
58#define PCMK__SPECIAL_PID_AS_0(p) (((p) == PCMK__SPECIAL_PID) ? 0 : (p))
59#else
60#define PCMK__SPECIAL_PID_AS_0(p) (p)
61#endif
62
95int pcmk__ipc_is_authentic_process_active(const char *name, uid_t refuid,
96 gid_t refgid, pid_t *gotpid);
97
98
99/*
100 * Server-related
101 */
102
104
106 /* Shared */
107 char *buffer;
113
114 /* CIB-only */
115 char *token;
116
117 /* TLS only */
118# ifdef HAVE_GNUTLS_GNUTLS_H
119 gnutls_session_t *tls_session;
120# endif
121};
122
124 // Lower 32 bits are reserved for server (not library) use
125
126 // Next 8 bits are reserved for client type (sort of a cheap enum)
127
129 pcmk__client_ipc = (UINT64_C(1) << 32),
130
132 pcmk__client_tcp = (UINT64_C(1) << 33),
133
136 pcmk__client_tls = (UINT64_C(1) << 34),
137# endif
138
139 // The rest are client attributes
140
142 pcmk__client_proxied = (UINT64_C(1) << 40),
143
145 pcmk__client_privileged = (UINT64_C(1) << 41),
146
148 pcmk__client_to_proxy = (UINT64_C(1) << 42),
149
155 pcmk__client_authenticated = (UINT64_C(1) << 43),
156
159 pcmk__client_tls_handshake_complete = (UINT64_C(1) << 44),
160# endif
161};
162
163#define PCMK__CLIENT_TYPE(client) ((client)->flags & UINT64_C(0xff00000000))
164
166 unsigned int pid;
167
168 char *id;
169 char *name;
170 char *user;
171 uint64_t flags; // Group of pcmk__client_flags
172
174 void *userdata;
175
177 GQueue *event_queue;
178
179 /* Depending on the client type, only some of the following will be
180 * populated/valid. @TODO Maybe convert to a union.
181 */
182
183 qb_ipcs_connection_t *ipcs; /* IPC */
184
185 struct pcmk__remote_s *remote; /* TCP/TLS */
186
187 unsigned int queue_backlog; /* IPC queue length after last flush */
188 unsigned int queue_max; /* Evict client whose queue grows this big */
189};
190
191#define pcmk__set_client_flags(client, flags_to_set) do { \
192 (client)->flags = pcmk__set_flags_as(__func__, __LINE__, \
193 LOG_TRACE, \
194 "Client", pcmk__client_name(client), \
195 (client)->flags, (flags_to_set), #flags_to_set); \
196 } while (0)
197
198#define pcmk__clear_client_flags(client, flags_to_clear) do { \
199 (client)->flags = pcmk__clear_flags_as(__func__, __LINE__, \
200 LOG_TRACE, \
201 "Client", pcmk__client_name(client), \
202 (client)->flags, (flags_to_clear), #flags_to_clear); \
203 } while (0)
204
205#define pcmk__set_ipc_flags(ipc_flags, ipc_name, flags_to_set) do { \
206 ipc_flags = pcmk__set_flags_as(__func__, __LINE__, LOG_TRACE, \
207 "IPC", (ipc_name), \
208 (ipc_flags), (flags_to_set), \
209 #flags_to_set); \
210 } while (0)
211
212#define pcmk__clear_ipc_flags(ipc_flags, ipc_name, flags_to_clear) do { \
213 ipc_flags = pcmk__clear_flags_as(__func__, __LINE__, LOG_TRACE, \
214 "IPC", (ipc_name), \
215 (ipc_flags), (flags_to_clear), \
216 #flags_to_clear); \
217 } while (0)
218
219guint pcmk__ipc_client_count(void);
220void pcmk__foreach_ipc_client(GHFunc func, gpointer user_data);
221
222void pcmk__client_cleanup(void);
223
224pcmk__client_t *pcmk__find_client(const qb_ipcs_connection_t *c);
226const char *pcmk__client_name(const pcmk__client_t *c);
227const char *pcmk__client_type_str(uint64_t client_type);
228
230pcmk__client_t *pcmk__new_client(qb_ipcs_connection_t *c, uid_t uid, gid_t gid);
232void pcmk__drop_all_clients(qb_ipcs_service_t *s);
233bool pcmk__set_client_queue_max(pcmk__client_t *client, const char *qmax);
234
235xmlNode *pcmk__ipc_create_ack_as(const char *function, int line, uint32_t flags,
236 const char *tag, const char *ver, crm_exit_t status);
237#define pcmk__ipc_create_ack(flags, tag, ver, st) \
238 pcmk__ipc_create_ack_as(__func__, __LINE__, (flags), (tag), (ver), (st))
239
240int pcmk__ipc_send_ack_as(const char *function, int line, pcmk__client_t *c,
241 uint32_t request, uint32_t flags, const char *tag,
242 const char *ver, crm_exit_t status);
243#define pcmk__ipc_send_ack(c, req, flags, tag, ver, st) \
244 pcmk__ipc_send_ack_as(__func__, __LINE__, (c), (req), (flags), (tag), (ver), (st))
245
246int pcmk__ipc_prepare_iov(uint32_t request, xmlNode *message,
247 uint32_t max_send_size,
248 struct iovec **result, ssize_t *bytes);
249int pcmk__ipc_send_xml(pcmk__client_t *c, uint32_t request, xmlNode *message,
250 uint32_t flags);
251int pcmk__ipc_send_iov(pcmk__client_t *c, struct iovec *iov, uint32_t flags);
252xmlNode *pcmk__client_data2xml(pcmk__client_t *c, void *data,
253 uint32_t *id, uint32_t *flags);
254
255int pcmk__client_pid(qb_ipcs_connection_t *c);
256
257void pcmk__serve_attrd_ipc(qb_ipcs_service_t **ipcs,
258 struct qb_ipcs_service_handlers *cb);
259void pcmk__serve_fenced_ipc(qb_ipcs_service_t **ipcs,
260 struct qb_ipcs_service_handlers *cb);
261void pcmk__serve_pacemakerd_ipc(qb_ipcs_service_t **ipcs,
262 struct qb_ipcs_service_handlers *cb);
263qb_ipcs_service_t *pcmk__serve_schedulerd_ipc(struct qb_ipcs_service_handlers *cb);
264qb_ipcs_service_t *pcmk__serve_controld_ipc(struct qb_ipcs_service_handlers *cb);
265
266void pcmk__serve_based_ipc(qb_ipcs_service_t **ipcs_ro,
267 qb_ipcs_service_t **ipcs_rw,
268 qb_ipcs_service_t **ipcs_shm,
269 struct qb_ipcs_service_handlers *ro_cb,
270 struct qb_ipcs_service_handlers *rw_cb);
271
272void pcmk__stop_based_ipc(qb_ipcs_service_t *ipcs_ro,
273 qb_ipcs_service_t *ipcs_rw,
274 qb_ipcs_service_t *ipcs_shm);
275
276static inline const char *
277pcmk__ipc_sys_name(const char *ipc_name, const char *fallback)
278{
279 return ipc_name ? ipc_name : ((crm_system_name ? crm_system_name : fallback));
280}
281
283
284#ifdef __cplusplus
285}
286#endif
287
288#endif
const char * name
Definition: cib.c:24
void gnutls_session_t
Definition: cib_remote.c:42
uint64_t flags
Definition: remote.c:3
#define HAVE_GNUTLS_GNUTLS_H
Definition: config.h:181
char data[0]
Definition: cpg.c:10
char * crm_system_name
Definition: utils.c:51
IPC interface to Pacemaker daemons.
pcmk__client_t * pcmk__new_client(qb_ipcs_connection_t *c, uid_t uid, gid_t gid)
Definition: ipc_server.c:218
pcmk__client_t * pcmk__find_client_by_id(const char *id)
Definition: ipc_server.c:70
const char * pcmk__client_name(const pcmk__client_t *c)
Definition: ipc_server.c:98
const char * pcmk__client_type_str(uint64_t client_type)
Definition: ipc_common.c:96
const char * pcmk__pcmkd_state_enum2friendly(enum pcmk_pacemakerd_state state)
xmlNode * pcmk__client_data2xml(pcmk__client_t *c, void *data, uint32_t *id, uint32_t *flags)
Definition: ipc_server.c:386
int pcmk__client_pid(qb_ipcs_connection_t *c)
Definition: ipc_server.c:365
pcmk__client_flags
Definition: ipc_internal.h:123
@ pcmk__client_proxied
Client IPC is proxied.
Definition: ipc_internal.h:142
@ pcmk__client_ipc
Client uses plain IPC.
Definition: ipc_internal.h:129
@ pcmk__client_privileged
Client is run by root or cluster user.
Definition: ipc_internal.h:145
@ pcmk__client_to_proxy
Local client to be proxied.
Definition: ipc_internal.h:148
@ pcmk__client_tcp
Client uses TCP connection.
Definition: ipc_internal.h:132
@ pcmk__client_authenticated
Client IPC connection accepted.
Definition: ipc_internal.h:155
int pcmk__ipc_send_xml(pcmk__client_t *c, uint32_t request, xmlNode *message, uint32_t flags)
Definition: ipc_server.c:744
pcmk__client_t * pcmk__find_client(const qb_ipcs_connection_t *c)
Definition: ipc_server.c:59
int pcmk__ipc_send_ack_as(const char *function, int line, pcmk__client_t *c, uint32_t request, uint32_t flags, const char *tag, const char *ver, crm_exit_t status)
Definition: ipc_server.c:812
pcmk__client_t * pcmk__new_unauth_client(void *key)
Allocate a new pcmk__client_t object and generate its ID.
Definition: ipc_server.c:209
void pcmk__drop_all_clients(qb_ipcs_service_t *s)
Definition: ipc_server.c:130
guint pcmk__ipc_client_count(void)
Definition: ipc_server.c:36
void pcmk__serve_fenced_ipc(qb_ipcs_service_t **ipcs, struct qb_ipcs_service_handlers *cb)
Definition: ipc_server.c:930
qb_ipcs_service_t * pcmk__serve_controld_ipc(struct qb_ipcs_service_handlers *cb)
Definition: ipc_server.c:893
void pcmk__stop_based_ipc(qb_ipcs_service_t *ipcs_ro, qb_ipcs_service_t *ipcs_rw, qb_ipcs_service_t *ipcs_shm)
Definition: ipc_server.c:875
void pcmk__free_client(pcmk__client_t *c)
Definition: ipc_server.c:299
int pcmk__ipc_is_authentic_process_active(const char *name, uid_t refuid, gid_t refgid, pid_t *gotpid)
Definition: ipc_client.c:1458
bool pcmk__set_client_queue_max(pcmk__client_t *client, const char *qmax)
Definition: ipc_server.c:350
void pcmk__serve_based_ipc(qb_ipcs_service_t **ipcs_ro, qb_ipcs_service_t **ipcs_rw, qb_ipcs_service_t **ipcs_shm, struct qb_ipcs_service_handlers *ro_cb, struct qb_ipcs_service_handlers *rw_cb)
Definition: ipc_server.c:841
xmlNode * pcmk__ipc_create_ack_as(const char *function, int line, uint32_t flags, const char *tag, const char *ver, crm_exit_t status)
Definition: ipc_server.c:781
void pcmk__client_cleanup(void)
Definition: ipc_server.c:115
int pcmk__ipc_prepare_iov(uint32_t request, xmlNode *message, uint32_t max_send_size, struct iovec **result, ssize_t *bytes)
Definition: ipc_server.c:580
void pcmk__foreach_ipc_client(GHFunc func, gpointer user_data)
Definition: ipc_server.c:51
int pcmk__ipc_send_iov(pcmk__client_t *c, struct iovec *iov, uint32_t flags)
Definition: ipc_server.c:665
void pcmk__serve_attrd_ipc(qb_ipcs_service_t **ipcs, struct qb_ipcs_service_handlers *cb)
Definition: ipc_server.c:908
qb_ipcs_service_t * pcmk__serve_schedulerd_ipc(struct qb_ipcs_service_handlers *cb)
Definition: ipc_server.c:980
void pcmk__serve_pacemakerd_ipc(qb_ipcs_service_t **ipcs, struct qb_ipcs_service_handlers *cb)
Definition: ipc_server.c:953
IPC commands for Pacemakerd.
pcmk_pacemakerd_state
Wrappers for and extensions to glib mainloop.
struct mainloop_io_s mainloop_io_t
Definition: mainloop.h:33
pcmk__action_result_t result
Definition: pcmk_fence.c:35
enum crm_exit_e crm_exit_t
qb_ipcs_connection_t * ipcs
Definition: ipc_internal.h:183
unsigned int queue_backlog
Definition: ipc_internal.h:187
unsigned int pid
Definition: ipc_internal.h:166
struct pcmk__remote_s * remote
Definition: ipc_internal.h:185
GQueue * event_queue
Definition: ipc_internal.h:177
unsigned int queue_max
Definition: ipc_internal.h:188
uint64_t flags
Definition: ipc_internal.h:171
size_t buffer_offset
Definition: ipc_internal.h:109
mainloop_io_t * source
Definition: ipc_internal.h:112
size_t buffer_size
Definition: ipc_internal.h:108