2 CTDB protocol marshalling
4 Copyright (C) Amitay Isaacs 2015
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 3 of the License, or
9 (at your option) any later version.
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, see <http://www.gnu.org/licenses/>.
21 #include "system/network.h"
27 #include "protocol_api.h"
28 #include "protocol_private.h"
30 struct ctdb_req_message_wire
{
31 struct ctdb_req_header hdr
;
37 static size_t ctdb_message_data_len(union ctdb_message_data
*mdata
,
43 case CTDB_SRVID_BANNING
:
44 len
= ctdb_uint32_len(mdata
->pnn
);
47 case CTDB_SRVID_ELECTION
:
48 len
= ctdb_election_message_len(mdata
->election
);
51 case CTDB_SRVID_RECONFIGURE
:
54 case CTDB_SRVID_RELEASE_IP
:
55 len
= ctdb_string_len(mdata
->ipaddr
);
58 case CTDB_SRVID_TAKE_IP
:
59 len
= ctdb_string_len(mdata
->ipaddr
);
62 case CTDB_SRVID_SET_NODE_FLAGS
:
63 len
= ctdb_node_flag_change_len(mdata
->flag_change
);
66 case CTDB_SRVID_RECD_UPDATE_IP
:
67 len
= ctdb_public_ip_len(mdata
->pubip
);
70 case CTDB_SRVID_VACUUM_FETCH
:
71 len
= ctdb_rec_buffer_len(mdata
->recbuf
);
74 case CTDB_SRVID_DETACH_DATABASE
:
75 len
= ctdb_uint32_len(mdata
->db_id
);
78 case CTDB_SRVID_MEM_DUMP
:
79 len
= ctdb_srvid_message_len(mdata
->msg
);
82 case CTDB_SRVID_PUSH_NODE_FLAGS
:
83 len
= ctdb_node_flag_change_len(mdata
->flag_change
);
86 case CTDB_SRVID_RELOAD_NODES
:
89 case CTDB_SRVID_TAKEOVER_RUN
:
90 len
= ctdb_srvid_message_len(mdata
->msg
);
93 case CTDB_SRVID_REBALANCE_NODE
:
94 len
= ctdb_uint32_len(mdata
->pnn
);
97 case CTDB_SRVID_DISABLE_TAKEOVER_RUNS
:
98 len
= ctdb_disable_message_len(mdata
->disable
);
101 case CTDB_SRVID_DISABLE_RECOVERIES
:
102 len
= ctdb_disable_message_len(mdata
->disable
);
105 case CTDB_SRVID_DISABLE_IP_CHECK
:
106 len
= ctdb_uint32_len(mdata
->timeout
);
110 len
= ctdb_tdb_data_len(mdata
->data
);
117 static void ctdb_message_data_push(union ctdb_message_data
*mdata
,
118 uint64_t srvid
, uint8_t *buf
)
121 case CTDB_SRVID_BANNING
:
122 ctdb_uint32_push(mdata
->pnn
, buf
);
125 case CTDB_SRVID_ELECTION
:
126 ctdb_election_message_push(mdata
->election
, buf
);
129 case CTDB_SRVID_RECONFIGURE
:
132 case CTDB_SRVID_RELEASE_IP
:
133 ctdb_string_push(mdata
->ipaddr
, buf
);
136 case CTDB_SRVID_TAKE_IP
:
137 ctdb_string_push(mdata
->ipaddr
, buf
);
140 case CTDB_SRVID_SET_NODE_FLAGS
:
141 ctdb_node_flag_change_push(mdata
->flag_change
, buf
);
144 case CTDB_SRVID_RECD_UPDATE_IP
:
145 ctdb_public_ip_push(mdata
->pubip
, buf
);
148 case CTDB_SRVID_VACUUM_FETCH
:
149 ctdb_rec_buffer_push(mdata
->recbuf
, buf
);
152 case CTDB_SRVID_DETACH_DATABASE
:
153 ctdb_uint32_push(mdata
->db_id
, buf
);
156 case CTDB_SRVID_MEM_DUMP
:
157 ctdb_srvid_message_push(mdata
->msg
, buf
);
160 case CTDB_SRVID_PUSH_NODE_FLAGS
:
161 ctdb_node_flag_change_push(mdata
->flag_change
, buf
);
164 case CTDB_SRVID_RELOAD_NODES
:
167 case CTDB_SRVID_TAKEOVER_RUN
:
168 ctdb_srvid_message_push(mdata
->msg
, buf
);
171 case CTDB_SRVID_REBALANCE_NODE
:
172 ctdb_uint32_push(mdata
->pnn
, buf
);
175 case CTDB_SRVID_DISABLE_TAKEOVER_RUNS
:
176 ctdb_disable_message_push(mdata
->disable
, buf
);
179 case CTDB_SRVID_DISABLE_RECOVERIES
:
180 ctdb_disable_message_push(mdata
->disable
, buf
);
183 case CTDB_SRVID_DISABLE_IP_CHECK
:
184 ctdb_uint32_push(mdata
->timeout
, buf
);
188 ctdb_tdb_data_push(mdata
->data
, buf
);
193 static int ctdb_message_data_pull(uint8_t *buf
, size_t buflen
,
194 uint64_t srvid
, TALLOC_CTX
*mem_ctx
,
195 union ctdb_message_data
*mdata
)
200 case CTDB_SRVID_BANNING
:
201 ret
= ctdb_uint32_pull(buf
, buflen
, mem_ctx
, &mdata
->pnn
);
204 case CTDB_SRVID_ELECTION
:
205 ret
= ctdb_election_message_pull(buf
, buflen
, mem_ctx
,
209 case CTDB_SRVID_RECONFIGURE
:
212 case CTDB_SRVID_RELEASE_IP
:
213 ret
= ctdb_string_pull(buf
, buflen
, mem_ctx
, &mdata
->ipaddr
);
216 case CTDB_SRVID_TAKE_IP
:
217 ret
= ctdb_string_pull(buf
, buflen
, mem_ctx
, &mdata
->ipaddr
);
220 case CTDB_SRVID_SET_NODE_FLAGS
:
221 ret
= ctdb_node_flag_change_pull(buf
, buflen
, mem_ctx
,
222 &mdata
->flag_change
);
225 case CTDB_SRVID_RECD_UPDATE_IP
:
226 ret
= ctdb_public_ip_pull(buf
, buflen
, mem_ctx
,
230 case CTDB_SRVID_VACUUM_FETCH
:
231 ret
= ctdb_rec_buffer_pull(buf
, buflen
, mem_ctx
,
235 case CTDB_SRVID_DETACH_DATABASE
:
236 ret
= ctdb_uint32_pull(buf
, buflen
, mem_ctx
, &mdata
->db_id
);
239 case CTDB_SRVID_MEM_DUMP
:
240 ret
= ctdb_srvid_message_pull(buf
, buflen
, mem_ctx
,
244 case CTDB_SRVID_PUSH_NODE_FLAGS
:
245 ret
= ctdb_node_flag_change_pull(buf
, buflen
, mem_ctx
,
246 &mdata
->flag_change
);
249 case CTDB_SRVID_RELOAD_NODES
:
252 case CTDB_SRVID_TAKEOVER_RUN
:
253 ret
= ctdb_srvid_message_pull(buf
, buflen
, mem_ctx
,
257 case CTDB_SRVID_REBALANCE_NODE
:
258 ret
= ctdb_uint32_pull(buf
, buflen
, mem_ctx
, &mdata
->pnn
);
261 case CTDB_SRVID_DISABLE_TAKEOVER_RUNS
:
262 ret
= ctdb_disable_message_pull(buf
, buflen
, mem_ctx
,
266 case CTDB_SRVID_DISABLE_RECOVERIES
:
267 ret
= ctdb_disable_message_pull(buf
, buflen
, mem_ctx
,
271 case CTDB_SRVID_DISABLE_IP_CHECK
:
272 ret
= ctdb_uint32_pull(buf
, buflen
, mem_ctx
, &mdata
->timeout
);
276 ret
= ctdb_tdb_data_pull(buf
, buflen
, mem_ctx
, &mdata
->data
);
283 size_t ctdb_req_message_len(struct ctdb_req_header
*h
,
284 struct ctdb_req_message
*c
)
286 return offsetof(struct ctdb_req_message_wire
, data
) +
287 ctdb_message_data_len(&c
->data
, c
->srvid
);
290 int ctdb_req_message_push(struct ctdb_req_header
*h
,
291 struct ctdb_req_message
*message
,
292 uint8_t *buf
, size_t *buflen
)
294 struct ctdb_req_message_wire
*wire
=
295 (struct ctdb_req_message_wire
*)buf
;
298 length
= ctdb_req_message_len(h
, message
);
299 if (*buflen
< length
) {
305 ctdb_req_header_push(h
, (uint8_t *)&wire
->hdr
);
307 wire
->srvid
= message
->srvid
;
308 wire
->datalen
= ctdb_message_data_len(&message
->data
, message
->srvid
);
309 ctdb_message_data_push(&message
->data
, message
->srvid
, wire
->data
);
314 int ctdb_req_message_pull(uint8_t *buf
, size_t buflen
,
315 struct ctdb_req_header
*h
,
317 struct ctdb_req_message
*c
)
319 struct ctdb_req_message_wire
*wire
=
320 (struct ctdb_req_message_wire
*)buf
;
324 length
= offsetof(struct ctdb_req_message_wire
, data
);
325 if (buflen
< length
) {
328 if (wire
->datalen
> buflen
) {
331 if (length
+ wire
->datalen
< length
) {
334 if (buflen
< length
+ wire
->datalen
) {
339 ret
= ctdb_req_header_pull((uint8_t *)&wire
->hdr
, buflen
, h
);
345 c
->srvid
= wire
->srvid
;
346 ret
= ctdb_message_data_pull(wire
->data
, wire
->datalen
, wire
->srvid
,
351 size_t ctdb_req_message_data_len(struct ctdb_req_header
*h
,
352 struct ctdb_req_message_data
*c
)
354 return offsetof(struct ctdb_req_message_wire
, data
) +
355 ctdb_tdb_data_len(c
->data
);
358 int ctdb_req_message_data_push(struct ctdb_req_header
*h
,
359 struct ctdb_req_message_data
*message
,
360 uint8_t *buf
, size_t *buflen
)
362 struct ctdb_req_message_wire
*wire
=
363 (struct ctdb_req_message_wire
*)buf
;
366 length
= ctdb_req_message_data_len(h
, message
);
367 if (*buflen
< length
) {
373 ctdb_req_header_push(h
, (uint8_t *)&wire
->hdr
);
375 wire
->srvid
= message
->srvid
;
376 wire
->datalen
= ctdb_tdb_data_len(message
->data
);
377 ctdb_tdb_data_push(message
->data
, wire
->data
);
382 int ctdb_req_message_data_pull(uint8_t *buf
, size_t buflen
,
383 struct ctdb_req_header
*h
,
385 struct ctdb_req_message_data
*c
)
387 struct ctdb_req_message_wire
*wire
=
388 (struct ctdb_req_message_wire
*)buf
;
392 length
= offsetof(struct ctdb_req_message_wire
, data
);
393 if (buflen
< length
) {
396 if (wire
->datalen
> buflen
) {
399 if (length
+ wire
->datalen
< length
) {
402 if (buflen
< length
+ wire
->datalen
) {
407 ret
= ctdb_req_header_pull((uint8_t *)&wire
->hdr
, buflen
, h
);
413 c
->srvid
= wire
->srvid
;
415 ret
= ctdb_tdb_data_pull(wire
->data
, wire
->datalen
,