/src/pacemaker/include/crm/common/nodes_internal.h
Line | Count | Source |
1 | | /* |
2 | | * Copyright 2024 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__CRM_COMMON_NODES_INTERNAL__H |
11 | | #define PCMK__CRM_COMMON_NODES_INTERNAL__H |
12 | | |
13 | | #include <stdio.h> // NULL |
14 | | #include <stdbool.h> // bool |
15 | | #include <stdint.h> // uint32_t, UINT32_C() |
16 | | |
17 | | #include <glib.h> // gpointer, GList, GHashTable |
18 | | #include <crm/common/nodes.h> |
19 | | |
20 | | #ifdef __cplusplus |
21 | | extern "C" { |
22 | | #endif |
23 | | |
24 | | /* |
25 | | * Special node attributes |
26 | | */ |
27 | | |
28 | | #define PCMK__NODE_ATTR_SHUTDOWN "shutdown" |
29 | | |
30 | | /* @COMPAT Deprecated since 2.1.8. Use a location constraint with |
31 | | * PCMK_XA_RSC_PATTERN=".*" and PCMK_XA_RESOURCE_DISCOVERY="never" instead of |
32 | | * PCMK__NODE_ATTR_RESOURCE_DISCOVERY_ENABLED="false". |
33 | | */ |
34 | | #define PCMK__NODE_ATTR_RESOURCE_DISCOVERY_ENABLED "resource-discovery-enabled" |
35 | | |
36 | | enum pcmk__node_variant { // Possible node types |
37 | | pcmk__node_variant_cluster = 1, // Cluster layer node |
38 | | pcmk__node_variant_remote = 2, // Pacemaker Remote node |
39 | | }; |
40 | | |
41 | | enum pcmk__node_flags { |
42 | | pcmk__node_none = UINT32_C(0), |
43 | | |
44 | | // Whether node is in standby mode |
45 | | pcmk__node_standby = (UINT32_C(1) << 0), |
46 | | |
47 | | // Whether node is in standby mode due to PCMK_META_ON_FAIL |
48 | | pcmk__node_fail_standby = (UINT32_C(1) << 1), |
49 | | |
50 | | // Whether node has ever joined cluster (and thus has node state in CIB) |
51 | | pcmk__node_seen = (UINT32_C(1) << 2), |
52 | | |
53 | | // Whether expected join state is member |
54 | | pcmk__node_expected_up = (UINT32_C(1) << 3), |
55 | | |
56 | | // Whether probes are allowed on node |
57 | | pcmk__node_probes_allowed = (UINT32_C(1) << 4), |
58 | | |
59 | | /* Whether this either is a guest node whose guest resource must be |
60 | | * recovered or a remote node that must be fenced |
61 | | */ |
62 | | pcmk__node_remote_reset = (UINT32_C(1) << 5), |
63 | | |
64 | | /* Whether this is a Pacemaker Remote node that was fenced since it was last |
65 | | * connected by the cluster |
66 | | */ |
67 | | pcmk__node_remote_fenced = (UINT32_C(1) << 6), |
68 | | |
69 | | /* |
70 | | * Whether this is a Pacemaker Remote node previously marked in its |
71 | | * node state as being in maintenance mode |
72 | | */ |
73 | | pcmk__node_remote_maint = (UINT32_C(1) << 7), |
74 | | |
75 | | // Whether node history has been unpacked |
76 | | pcmk__node_unpacked = (UINT32_C(1) << 8), |
77 | | }; |
78 | | |
79 | | // When to probe a resource on a node (as specified in location constraints) |
80 | | enum pcmk__probe_mode { |
81 | | pcmk__probe_always = 0, // Always probe resource on node |
82 | | pcmk__probe_never = 1, // Never probe resource on node |
83 | | pcmk__probe_exclusive = 2, // Probe only on designated nodes |
84 | | }; |
85 | | |
86 | | /* Per-node data used in resource assignment |
87 | | * |
88 | | * @COMPAT When we can make the pcmk_node_t implementation internal, move these |
89 | | * there and drop this struct. |
90 | | */ |
91 | | struct pcmk__node_assignment { |
92 | | int score; // Node's score for relevant resource |
93 | | int count; // Counter reused by assignment and promotion code |
94 | | enum pcmk__probe_mode probe_mode; // When to probe resource on this node |
95 | | }; |
96 | | |
97 | | /* Implementation of pcmk__node_private_t (pcmk_node_t objects are shallow |
98 | | * copies, so all pcmk_node_t objects for the same node will share the same |
99 | | * private data) |
100 | | */ |
101 | | struct pcmk__node_private { |
102 | | /* Node's XML ID in the CIB (the cluster layer ID for cluster nodes, |
103 | | * the node name for Pacemaker Remote nodes) |
104 | | */ |
105 | | const char *id; |
106 | | |
107 | | /* |
108 | | * Sum of priorities of all resources active on node and on any guest nodes |
109 | | * connected to this node, with +1 for promoted instances (used to compare |
110 | | * nodes for PCMK_OPT_PRIORITY_FENCING_DELAY) |
111 | | */ |
112 | | int priority; |
113 | | |
114 | | const char *name; // Node name in cluster |
115 | | enum pcmk__node_variant variant; // Node variant |
116 | | uint32_t flags; // Group of enum pcmk__node_flags |
117 | | GHashTable *attrs; // Node attributes |
118 | | GHashTable *utilization; // Node utilization attributes |
119 | | int num_resources; // Number of active resources on node |
120 | | GList *assigned_resources; // List of resources assigned to node |
121 | | GHashTable *digest_cache; // Cache of calculated resource digests |
122 | | pcmk_resource_t *remote; // Pacemaker Remote connection (if any) |
123 | | pcmk_scheduler_t *scheduler; // Scheduler data that node is part of |
124 | | }; |
125 | | |
126 | | void pcmk__free_node_copy(void *data); |
127 | | pcmk_node_t *pcmk__find_node_in_list(const GList *nodes, const char *node_name); |
128 | | |
129 | | /*! |
130 | | * \internal |
131 | | * \brief Set node flags |
132 | | * |
133 | | * \param[in,out] node Node to set flags for |
134 | | * \param[in] flags_to_set Group of enum pcmk_node_flags to set |
135 | | */ |
136 | | #define pcmk__set_node_flags(node, flags_to_set) do { \ |
137 | | (node)->priv->flags = pcmk__set_flags_as(__func__, __LINE__, \ |
138 | | LOG_TRACE, "Node", pcmk__node_name(node), \ |
139 | | (node)->priv->flags, (flags_to_set), #flags_to_set); \ |
140 | | } while (0) |
141 | | |
142 | | /*! |
143 | | * \internal |
144 | | * \brief Clear node flags |
145 | | * |
146 | | * \param[in,out] node Node to clear flags for |
147 | | * \param[in] flags_to_clear Group of enum pcmk_node_flags to clear |
148 | | */ |
149 | | #define pcmk__clear_node_flags(node, flags_to_clear) do { \ |
150 | | (node)->priv->flags = pcmk__clear_flags_as(__func__, __LINE__, \ |
151 | | LOG_TRACE, "Node", pcmk__node_name(node), \ |
152 | | (node)->priv->flags, (flags_to_clear), #flags_to_clear); \ |
153 | | } while (0) |
154 | | |
155 | | void pcmk__free_node(gpointer user_data); |
156 | | |
157 | | /*! |
158 | | * \internal |
159 | | * \brief Return a string suitable for logging as a node name |
160 | | * |
161 | | * \param[in] node Node to return a node name string for |
162 | | * |
163 | | * \return Node name if available, otherwise node ID if available, |
164 | | * otherwise "unspecified node" if node is NULL or "unidentified node" |
165 | | * if node has neither a name nor ID. |
166 | | */ |
167 | | static inline const char * |
168 | | pcmk__node_name(const pcmk_node_t *node) |
169 | 0 | { |
170 | 0 | if (node == NULL) { |
171 | 0 | return "unspecified node"; |
172 | |
|
173 | 0 | } else if (node->priv->name != NULL) { |
174 | 0 | return node->priv->name; |
175 | |
|
176 | 0 | } else if (node->priv->id != NULL) { |
177 | 0 | return node->priv->id; |
178 | |
|
179 | 0 | } else { |
180 | 0 | return "unidentified node"; |
181 | 0 | } |
182 | 0 | } Unexecuted instantiation: results.c:pcmk__node_name Unexecuted instantiation: scores.c:pcmk__node_name Unexecuted instantiation: strings.c:pcmk__node_name Unexecuted instantiation: utils.c:pcmk__node_name Unexecuted instantiation: iso8601.c:pcmk__node_name Unexecuted instantiation: logging.c:pcmk__node_name Unexecuted instantiation: mainloop.c:pcmk__node_name Unexecuted instantiation: options.c:pcmk__node_name Unexecuted instantiation: output.c:pcmk__node_name Unexecuted instantiation: output_log.c:pcmk__node_name Unexecuted instantiation: output_text.c:pcmk__node_name Unexecuted instantiation: output_xml.c:pcmk__node_name Unexecuted instantiation: patchset_display.c:pcmk__node_name Unexecuted instantiation: schemas.c:pcmk__node_name Unexecuted instantiation: xml.c:pcmk__node_name Unexecuted instantiation: xml_attr.c:pcmk__node_name Unexecuted instantiation: xml_comment.c:pcmk__node_name Unexecuted instantiation: xml_display.c:pcmk__node_name Unexecuted instantiation: xml_element.c:pcmk__node_name Unexecuted instantiation: xml_idref.c:pcmk__node_name Unexecuted instantiation: xml_io.c:pcmk__node_name Unexecuted instantiation: xpath.c:pcmk__node_name Unexecuted instantiation: acl.c:pcmk__node_name Unexecuted instantiation: actions.c:pcmk__node_name Unexecuted instantiation: agents.c:pcmk__node_name Unexecuted instantiation: cmdline.c:pcmk__node_name Unexecuted instantiation: digest.c:pcmk__node_name Unexecuted instantiation: health.c:pcmk__node_name Unexecuted instantiation: io.c:pcmk__node_name Unexecuted instantiation: ipc_client.c:pcmk__node_name Unexecuted instantiation: ipc_common.c:pcmk__node_name Unexecuted instantiation: ipc_controld.c:pcmk__node_name Unexecuted instantiation: ipc_pacemakerd.c:pcmk__node_name Unexecuted instantiation: ipc_schedulerd.c:pcmk__node_name Unexecuted instantiation: ipc_server.c:pcmk__node_name Unexecuted instantiation: messages.c:pcmk__node_name Unexecuted instantiation: nodes.c:pcmk__node_name Unexecuted instantiation: nvpair.c:pcmk__node_name Unexecuted instantiation: options_display.c:pcmk__node_name Unexecuted instantiation: patchset.c:pcmk__node_name Unexecuted instantiation: procfs.c:pcmk__node_name Unexecuted instantiation: rules.c:pcmk__node_name Unexecuted instantiation: servers.c:pcmk__node_name Unexecuted instantiation: cib.c:pcmk__node_name Unexecuted instantiation: ipc_attrd.c:pcmk__node_name Unexecuted instantiation: pid.c:pcmk__node_name Unexecuted instantiation: attrs.c:pcmk__node_name Unexecuted instantiation: strings_fuzzer.c:pcmk__node_name Unexecuted instantiation: cib_file_fuzzer.c:pcmk__node_name Unexecuted instantiation: cib_client.c:pcmk__node_name Unexecuted instantiation: cib_file.c:pcmk__node_name Unexecuted instantiation: cib_native.c:pcmk__node_name Unexecuted instantiation: cib_ops.c:pcmk__node_name Unexecuted instantiation: cib_remote.c:pcmk__node_name Unexecuted instantiation: cib_utils.c:pcmk__node_name Unexecuted instantiation: remote.c:pcmk__node_name Unexecuted instantiation: tls.c:pcmk__node_name Unexecuted instantiation: watchdog.c:pcmk__node_name |
183 | | |
184 | | /*! |
185 | | * \internal |
186 | | * \brief Check whether two node objects refer to the same node |
187 | | * |
188 | | * \param[in] node1 First node object to compare |
189 | | * \param[in] node2 Second node object to compare |
190 | | * |
191 | | * \return true if \p node1 and \p node2 refer to the same node |
192 | | */ |
193 | | static inline bool |
194 | | pcmk__same_node(const pcmk_node_t *node1, const pcmk_node_t *node2) |
195 | 0 | { |
196 | 0 | return (node1 != NULL) && (node2 != NULL) |
197 | 0 | && (node1->priv == node2->priv); |
198 | 0 | } Unexecuted instantiation: results.c:pcmk__same_node Unexecuted instantiation: scores.c:pcmk__same_node Unexecuted instantiation: strings.c:pcmk__same_node Unexecuted instantiation: utils.c:pcmk__same_node Unexecuted instantiation: iso8601.c:pcmk__same_node Unexecuted instantiation: logging.c:pcmk__same_node Unexecuted instantiation: mainloop.c:pcmk__same_node Unexecuted instantiation: options.c:pcmk__same_node Unexecuted instantiation: output.c:pcmk__same_node Unexecuted instantiation: output_log.c:pcmk__same_node Unexecuted instantiation: output_text.c:pcmk__same_node Unexecuted instantiation: output_xml.c:pcmk__same_node Unexecuted instantiation: patchset_display.c:pcmk__same_node Unexecuted instantiation: schemas.c:pcmk__same_node Unexecuted instantiation: xml.c:pcmk__same_node Unexecuted instantiation: xml_attr.c:pcmk__same_node Unexecuted instantiation: xml_comment.c:pcmk__same_node Unexecuted instantiation: xml_display.c:pcmk__same_node Unexecuted instantiation: xml_element.c:pcmk__same_node Unexecuted instantiation: xml_idref.c:pcmk__same_node Unexecuted instantiation: xml_io.c:pcmk__same_node Unexecuted instantiation: xpath.c:pcmk__same_node Unexecuted instantiation: acl.c:pcmk__same_node Unexecuted instantiation: actions.c:pcmk__same_node Unexecuted instantiation: agents.c:pcmk__same_node Unexecuted instantiation: cmdline.c:pcmk__same_node Unexecuted instantiation: digest.c:pcmk__same_node Unexecuted instantiation: health.c:pcmk__same_node Unexecuted instantiation: io.c:pcmk__same_node Unexecuted instantiation: ipc_client.c:pcmk__same_node Unexecuted instantiation: ipc_common.c:pcmk__same_node Unexecuted instantiation: ipc_controld.c:pcmk__same_node Unexecuted instantiation: ipc_pacemakerd.c:pcmk__same_node Unexecuted instantiation: ipc_schedulerd.c:pcmk__same_node Unexecuted instantiation: ipc_server.c:pcmk__same_node Unexecuted instantiation: messages.c:pcmk__same_node Unexecuted instantiation: nodes.c:pcmk__same_node Unexecuted instantiation: nvpair.c:pcmk__same_node Unexecuted instantiation: options_display.c:pcmk__same_node Unexecuted instantiation: patchset.c:pcmk__same_node Unexecuted instantiation: procfs.c:pcmk__same_node Unexecuted instantiation: rules.c:pcmk__same_node Unexecuted instantiation: servers.c:pcmk__same_node Unexecuted instantiation: cib.c:pcmk__same_node Unexecuted instantiation: ipc_attrd.c:pcmk__same_node Unexecuted instantiation: pid.c:pcmk__same_node Unexecuted instantiation: attrs.c:pcmk__same_node Unexecuted instantiation: strings_fuzzer.c:pcmk__same_node Unexecuted instantiation: cib_file_fuzzer.c:pcmk__same_node Unexecuted instantiation: cib_client.c:pcmk__same_node Unexecuted instantiation: cib_file.c:pcmk__same_node Unexecuted instantiation: cib_native.c:pcmk__same_node Unexecuted instantiation: cib_ops.c:pcmk__same_node Unexecuted instantiation: cib_remote.c:pcmk__same_node Unexecuted instantiation: cib_utils.c:pcmk__same_node Unexecuted instantiation: remote.c:pcmk__same_node Unexecuted instantiation: tls.c:pcmk__same_node Unexecuted instantiation: watchdog.c:pcmk__same_node |
199 | | |
200 | | #ifdef __cplusplus |
201 | | } |
202 | | #endif |
203 | | |
204 | | #endif // PCMK__CRM_COMMON_NODES_INTERNAL__H |