This source file includes following definitions.
- attrd_lrmd_callback
- attrd_lrmd_connect
- attrd_lrmd_disconnect
- config_query_callback
- attrd_read_options
- attrd_send_attribute_alert
1
2
3
4
5
6
7
8
9
10 #include <crm_internal.h>
11 #include <crm/crm.h>
12 #include <crm/cib/internal.h>
13 #include <crm/cluster/internal.h>
14 #include <crm/cluster/election_internal.h>
15 #include <crm/common/alerts_internal.h>
16 #include <crm/common/cib_internal.h>
17 #include <crm/common/xml.h>
18 #include <crm/pengine/rules_internal.h>
19 #include <crm/lrmd_internal.h>
20 #include "pacemaker-attrd.h"
21
22 static GList *attrd_alert_list = NULL;
23
24 static void
25 attrd_lrmd_callback(lrmd_event_data_t * op)
26 {
27 CRM_CHECK(op != NULL, return);
28 switch (op->type) {
29 case lrmd_event_disconnect:
30 crm_info("Lost connection to executor");
31 attrd_lrmd_disconnect();
32 break;
33 default:
34 break;
35 }
36 }
37
38 static lrmd_t *
39 attrd_lrmd_connect(void)
40 {
41 if (the_lrmd == NULL) {
42 the_lrmd = lrmd_api_new();
43 the_lrmd->cmds->set_callback(the_lrmd, attrd_lrmd_callback);
44 }
45
46 if (!the_lrmd->cmds->is_connected(the_lrmd)) {
47 const unsigned int max_attempts = 10;
48 int ret = -ENOTCONN;
49
50 for (int fails = 0; fails < max_attempts; ++fails) {
51 ret = the_lrmd->cmds->connect(the_lrmd, PCMK__VALUE_ATTRD, NULL);
52 if (ret == pcmk_ok) {
53 break;
54 }
55
56 crm_debug("Could not connect to executor, %d tries remaining",
57 (max_attempts - fails));
58
59
60
61
62 }
63
64 if (ret != pcmk_ok) {
65 attrd_lrmd_disconnect();
66 }
67 }
68
69 return the_lrmd;
70 }
71
72 void
73 attrd_lrmd_disconnect(void) {
74 if (the_lrmd) {
75 lrmd_t *conn = the_lrmd;
76
77 the_lrmd = NULL;
78 lrmd_api_delete(conn);
79 }
80 }
81
82 static void
83 config_query_callback(xmlNode * msg, int call_id, int rc, xmlNode * output, void *user_data)
84 {
85 xmlNode *crmalerts = NULL;
86
87 if (rc == -ENXIO) {
88 crm_debug("Local CIB has no alerts section");
89 return;
90 } else if (rc != pcmk_ok) {
91 crm_notice("Could not query local CIB: %s", pcmk_strerror(rc));
92 return;
93 }
94
95 crmalerts = output;
96 if ((crmalerts != NULL) && !pcmk__xe_is(crmalerts, PCMK_XE_ALERTS)) {
97 crmalerts = pcmk__xe_first_child(crmalerts, PCMK_XE_ALERTS, NULL, NULL);
98 }
99 if (!crmalerts) {
100 crm_notice("CIB query result has no " PCMK_XE_ALERTS " section");
101 return;
102 }
103
104 pe_free_alert_list(attrd_alert_list);
105 attrd_alert_list = pe_unpack_alerts(crmalerts);
106 }
107
108 gboolean
109 attrd_read_options(gpointer user_data)
110 {
111 int call_id;
112
113 CRM_CHECK(the_cib != NULL, return TRUE);
114
115 call_id = the_cib->cmds->query(the_cib,
116 pcmk__cib_abs_xpath_for(PCMK_XE_ALERTS),
117 NULL, cib_xpath|cib_scope_local);
118
119 the_cib->cmds->register_callback_full(the_cib, call_id, 120, FALSE, NULL,
120 "config_query_callback",
121 config_query_callback, free);
122
123 crm_trace("Querying the CIB... call %d", call_id);
124 return TRUE;
125 }
126
127 int
128 attrd_send_attribute_alert(const char *node, int nodeid,
129 const char *attr, const char *value)
130 {
131 if (attrd_alert_list == NULL) {
132 return pcmk_ok;
133 }
134 return lrmd_send_attribute_alert(attrd_lrmd_connect(), attrd_alert_list,
135 node, nodeid, attr, value);
136 }