Branch data Line data Source code
1 : : /* SPDX-License-Identifier: GPL-2.0-only */
2 : : /*
3 : : * Copyright (c) 2023 Meta Platforms, Inc. and affiliates.
4 : : */
5 : :
6 : : #include <errno.h>
7 : : #include <string.h>
8 : :
9 : : #include "bpfilter/chain.h"
10 : : #include "bpfilter/counter.h"
11 : : #include "bpfilter/front.h"
12 : : #include "bpfilter/helper.h"
13 : : #include "bpfilter/hook.h"
14 : : #include "bpfilter/io.h"
15 : : #include "bpfilter/list.h"
16 : : #include "bpfilter/logger.h"
17 : : #include "bpfilter/pack.h"
18 : : #include "bpfilter/request.h"
19 : : #include "bpfilter/response.h"
20 : :
21 : 5 : int bf_ruleset_get(bf_list *chains, bf_list *hookopts, bf_list *counters)
22 : : {
23 : 5 : _cleanup_close_ int fd = -1;
24 : 5 : _free_bf_request_ struct bf_request *request = NULL;
25 : 5 : _free_bf_response_ struct bf_response *response = NULL;
26 : 5 : _clean_bf_list_ bf_list _chains = bf_list_default_from(*chains);
27 : 5 : _clean_bf_list_ bf_list _hookopts = bf_list_default_from(*hookopts);
28 : 5 : _clean_bf_list_ bf_list _counters = bf_list_default_from(*counters);
29 : 5 : _free_bf_rpack_ bf_rpack_t *pack = NULL;
30 : : bf_rpack_node_t root, node, child;
31 : : int r;
32 : :
33 : 5 : r = bf_request_new(&request, BF_FRONT_CLI, BF_REQ_RULESET_GET, NULL, 0);
34 [ - + ]: 5 : if (r < 0)
35 [ # # ]: 0 : return bf_err_r(r, "failed to init request");
36 : :
37 : 5 : fd = bf_connect_to_daemon();
38 [ + + ]: 5 : if (fd < 0)
39 [ + - ]: 1 : return bf_err_r(fd, "failed to connect to the daemon");
40 : :
41 : 4 : r = bf_send(fd, request, &response, NULL);
42 [ - + ]: 4 : if (r < 0)
43 [ # # ]: 0 : return bf_err_r(r, "failed to send a ruleset get request");
44 : :
45 [ - + ]: 4 : if (bf_response_status(response) != 0)
46 : 0 : return bf_response_status(response);
47 : :
48 : 4 : r = bf_rpack_new(&pack, bf_response_data(response),
49 : : bf_response_data_len(response));
50 [ + - ]: 4 : if (r)
51 : : return r;
52 : :
53 : 4 : r = bf_rpack_kv_obj(bf_rpack_root(pack), "ruleset", &root);
54 [ + - ]: 4 : if (r)
55 : : return r;
56 : :
57 : 4 : r = bf_rpack_kv_array(root, "chains", &node);
58 [ + - ]: 4 : if (r)
59 : : return r;
60 [ + - + + : 18 : bf_rpack_array_foreach (node, child) {
+ + ]
61 : 0 : _free_bf_chain_ struct bf_chain *chain = NULL;
62 : :
63 [ + - + - : 5 : r = bf_list_emplace(&_chains, bf_chain_new_from_pack, chain, child);
- - - - ]
64 : : if (r)
65 : : return r;
66 : : }
67 : :
68 : 4 : r = bf_rpack_kv_array(root, "hookopts", &node);
69 [ + - ]: 4 : if (r)
70 : : return r;
71 [ + - + + : 18 : bf_rpack_array_foreach (node, child) {
+ + ]
72 : 5 : _free_bf_hookopts_ struct bf_hookopts *hookopts = NULL;
73 : :
74 [ + + ]: 5 : if (!bf_rpack_is_nil(child)) {
75 [ + - + - : 4 : r = bf_list_emplace(&_hookopts, bf_hookopts_new_from_pack, hookopts,
- - - - ]
76 : : child);
77 : : } else {
78 : 1 : r = bf_list_add_tail(&_hookopts, NULL);
79 : : }
80 : :
81 [ - + ]: 1 : if (r)
82 : : return r;
83 : : }
84 : :
85 : 4 : r = bf_rpack_kv_array(root, "counters", &node);
86 [ + - ]: 4 : if (r)
87 : : return r;
88 [ + - + + : 18 : bf_rpack_array_foreach (node, child) {
+ + ]
89 : 0 : _free_bf_list_ bf_list *nested = NULL;
90 : : bf_rpack_node_t subchild;
91 : :
92 [ + - ]: 5 : if (!bf_rpack_is_array(child))
93 : : return -EDOM;
94 : :
95 : 5 : r = bf_list_new(&nested, &bf_list_ops_default(bf_counter_free, NULL));
96 [ + - ]: 5 : if (r)
97 : : return r;
98 : :
99 [ + - + + : 34 : bf_rpack_array_foreach (child, subchild) {
+ + ]
100 : 0 : _free_bf_counter_ struct bf_counter *counter = NULL;
101 : :
102 [ + - + - : 12 : r = bf_list_emplace(nested, bf_counter_new_from_pack, counter,
- - - - ]
103 : : subchild);
104 : : if (r)
105 : : return r;
106 : : }
107 : :
108 : 5 : r = bf_list_add_tail(&_counters, nested);
109 [ + - ]: 5 : if (r)
110 : : return r;
111 : :
112 : 5 : TAKE_PTR(nested);
113 : : }
114 : :
115 : 4 : *chains = bf_list_move(_chains);
116 : 4 : *hookopts = bf_list_move(_hookopts);
117 : 4 : *counters = bf_list_move(_counters);
118 : :
119 : 4 : return 0;
120 : : }
121 : :
122 : 10 : int bf_ruleset_set(bf_list *chains, bf_list *hookopts)
123 : : {
124 : 10 : _cleanup_close_ int fd = -1;
125 : 10 : _free_bf_wpack_ bf_wpack_t *pack = NULL;
126 : 10 : _free_bf_request_ struct bf_request *request = NULL;
127 [ + + ]: 19 : _free_bf_response_ struct bf_response *response = NULL;
128 : : struct bf_list_node *chain_node = bf_list_get_head(chains);
129 : : struct bf_list_node *hookopts_node = bf_list_get_head(hookopts);
130 : : int r;
131 : :
132 [ + + ]: 10 : if (bf_list_size(chains) != bf_list_size(hookopts))
133 : : return -EINVAL;
134 : :
135 : 9 : r = bf_wpack_new(&pack);
136 [ + - ]: 9 : if (r)
137 : : return r;
138 : :
139 : 9 : bf_wpack_open_array(pack, "ruleset");
140 [ + + ]: 22 : while (chain_node && hookopts_node) {
141 : : struct bf_chain *chain = bf_list_node_get_data(chain_node);
142 : : struct bf_hookopts *hookopts = bf_list_node_get_data(hookopts_node);
143 : :
144 : 13 : bf_wpack_open_object(pack, NULL);
145 : :
146 : 13 : bf_wpack_open_object(pack, "chain");
147 : 13 : bf_chain_pack(chain, pack);
148 : 13 : bf_wpack_close_object(pack);
149 : :
150 [ + + ]: 13 : if (hookopts) {
151 : 10 : bf_wpack_open_object(pack, "hookopts");
152 : 10 : bf_hookopts_pack(hookopts, pack);
153 : 10 : bf_wpack_close_object(pack);
154 : : } else {
155 : 3 : bf_wpack_kv_nil(pack, "hookopts");
156 : : }
157 : :
158 : 13 : bf_wpack_close_object(pack);
159 : :
160 : : chain_node = bf_list_node_next(chain_node);
161 : : hookopts_node = bf_list_node_next(hookopts_node);
162 : : }
163 : 9 : bf_wpack_close_array(pack);
164 : :
165 : 9 : r = bf_request_new_from_pack(&request, BF_FRONT_CLI, BF_REQ_RULESET_SET,
166 : : pack);
167 [ - + ]: 9 : if (r)
168 [ # # ]: 0 : return bf_err_r(r, "failed to create request for chain");
169 : :
170 : 9 : fd = bf_connect_to_daemon();
171 [ + + ]: 9 : if (fd < 0)
172 [ + - ]: 1 : return bf_err_r(fd, "failed to connect to the daemon");
173 : :
174 : 8 : r = bf_send(fd, request, &response, NULL);
175 [ - + ]: 8 : if (r)
176 [ # # ]: 0 : return bf_err_r(r, "failed to send chain to the daemon");
177 : :
178 : 8 : return bf_response_status(response);
179 : : }
180 : :
181 : 3 : int bf_ruleset_flush(void)
182 : : {
183 : 3 : _cleanup_close_ int fd = -1;
184 : 3 : _free_bf_request_ struct bf_request *request = NULL;
185 : 3 : _free_bf_response_ struct bf_response *response = NULL;
186 : : int r;
187 : :
188 : 3 : r = bf_request_new(&request, BF_FRONT_CLI, BF_REQ_RULESET_FLUSH, NULL, 0);
189 [ - + ]: 3 : if (r)
190 [ # # ]: 0 : return bf_err_r(r, "failed to create a ruleset flush request");
191 : :
192 : 3 : fd = bf_connect_to_daemon();
193 [ + + ]: 3 : if (fd < 0)
194 [ + - ]: 1 : return bf_err_r(fd, "failed to connect to the daemon");
195 : :
196 : 2 : r = bf_send(fd, request, &response, NULL);
197 [ - + ]: 2 : if (r)
198 [ # # ]: 0 : return bf_err_r(r, "failed to send a ruleset flush request");
199 : :
200 : 2 : return bf_response_status(response);
201 : : }
202 : :
203 : 34 : int bf_chain_set(struct bf_chain *chain, struct bf_hookopts *hookopts)
204 : : {
205 : 34 : _cleanup_close_ int fd = -1;
206 : 34 : _free_bf_wpack_ bf_wpack_t *pack = NULL;
207 : 34 : _free_bf_request_ struct bf_request *request = NULL;
208 : 34 : _free_bf_response_ struct bf_response *response = NULL;
209 : : int r;
210 : :
211 : 34 : r = bf_wpack_new(&pack);
212 [ + - ]: 34 : if (r)
213 : : return r;
214 : :
215 : 34 : bf_wpack_open_object(pack, "chain");
216 : 34 : r = bf_chain_pack(chain, pack);
217 [ + - ]: 34 : if (r)
218 : : return r;
219 : 34 : bf_wpack_close_object(pack);
220 : :
221 [ + + ]: 34 : if (hookopts) {
222 : 6 : bf_wpack_open_object(pack, "hookopts");
223 : 6 : r = bf_hookopts_pack(hookopts, pack);
224 [ + - ]: 6 : if (r)
225 : : return r;
226 : 6 : bf_wpack_close_object(pack);
227 : : } else {
228 : 28 : bf_wpack_kv_nil(pack, "hookopts");
229 : : }
230 : :
231 : 34 : r = bf_request_new_from_pack(&request, BF_FRONT_CLI, BF_REQ_CHAIN_SET,
232 : : pack);
233 [ - + ]: 34 : if (r)
234 [ # # ]: 0 : return bf_err_r(r, "bf_chain_set: failed to create request");
235 : :
236 : 34 : fd = bf_connect_to_daemon();
237 [ + + ]: 34 : if (fd < 0)
238 [ + - ]: 1 : return bf_err_r(fd, "failed to connect to the daemon");
239 : :
240 : 33 : r = bf_send(fd, request, &response, NULL);
241 [ - + ]: 33 : if (r)
242 [ # # ]: 0 : return bf_err_r(r, "bf_chain_set: failed to send request");
243 : :
244 : 33 : return bf_response_status(response);
245 : : }
246 : :
247 : 10 : int bf_chain_get(const char *name, struct bf_chain **chain,
248 : : struct bf_hookopts **hookopts, bf_list *counters)
249 : : {
250 : 10 : _cleanup_close_ int fd = -1;
251 : 10 : _free_bf_request_ struct bf_request *request = NULL;
252 : 10 : _free_bf_response_ struct bf_response *response = NULL;
253 : 10 : _free_bf_chain_ struct bf_chain *_chain = NULL;
254 : 10 : _free_bf_hookopts_ struct bf_hookopts *_hookopts = NULL;
255 : 10 : _clean_bf_list_ bf_list _counters = bf_list_default_from(*counters);
256 : 10 : _free_bf_wpack_ bf_wpack_t *wpack = NULL;
257 : 10 : _free_bf_rpack_ bf_rpack_t *rpack = NULL;
258 : : bf_rpack_node_t child, array_node;
259 : : int r;
260 : :
261 : 10 : r = bf_wpack_new(&wpack);
262 [ + - ]: 10 : if (r)
263 : : return r;
264 : :
265 : 10 : bf_wpack_kv_str(wpack, "name", name);
266 [ + - ]: 10 : if (!bf_wpack_is_valid(wpack))
267 : : return -EINVAL;
268 : :
269 : 10 : r = bf_request_new_from_pack(&request, BF_FRONT_CLI, BF_REQ_CHAIN_GET,
270 : : wpack);
271 [ - + ]: 10 : if (r < 0)
272 [ # # ]: 0 : return bf_err_r(r, "failed to init request");
273 : :
274 : 10 : fd = bf_connect_to_daemon();
275 [ + + ]: 10 : if (fd < 0)
276 [ + - ]: 1 : return bf_err_r(fd, "failed to connect to the daemon");
277 : :
278 : 9 : r = bf_send(fd, request, &response, NULL);
279 [ - + ]: 9 : if (r < 0)
280 [ # # ]: 0 : return bf_err_r(r, "failed to send a ruleset get request");
281 : :
282 [ + + ]: 9 : if (bf_response_status(response) != 0)
283 : 1 : return bf_response_status(response);
284 : :
285 : 8 : r = bf_rpack_new(&rpack, bf_response_data(response),
286 : : bf_response_data_len(response));
287 [ + - ]: 8 : if (r)
288 : : return r;
289 : :
290 : 8 : r = bf_rpack_kv_obj(bf_rpack_root(rpack), "chain", &child);
291 [ + - ]: 8 : if (r)
292 : : return r;
293 : 8 : r = bf_chain_new_from_pack(&_chain, child);
294 [ + - ]: 8 : if (r)
295 : : return r;
296 : :
297 : 8 : r = bf_rpack_kv_node(bf_rpack_root(rpack), "hookopts", &child);
298 [ + - ]: 8 : if (r)
299 : : return r;
300 [ + + ]: 8 : if (!bf_rpack_is_nil(child)) {
301 : 4 : r = bf_hookopts_new_from_pack(&_hookopts, child);
302 [ + - ]: 4 : if (r)
303 : : return r;
304 : : }
305 : :
306 : 8 : r = bf_rpack_kv_array(bf_rpack_root(rpack), "counters", &child);
307 [ + - ]: 8 : if (r)
308 : : return r;
309 [ + - + + : 56 : bf_rpack_array_foreach (child, array_node) {
+ + ]
310 : 0 : _free_bf_counter_ struct bf_counter *counter = NULL;
311 : :
312 [ + - + - : 20 : r = bf_list_emplace(&_counters, bf_counter_new_from_pack, counter,
- - - - ]
313 : : array_node);
314 : : if (r)
315 : : return r;
316 : : }
317 : :
318 : 8 : *chain = TAKE_PTR(_chain);
319 : 8 : *hookopts = TAKE_PTR(_hookopts);
320 : 8 : *counters = bf_list_move(_counters);
321 : :
322 : 8 : return 0;
323 : : }
324 : :
325 : 2 : int bf_chain_prog_fd(const char *name)
326 : : {
327 : 2 : _cleanup_close_ int fd = -1;
328 : 2 : _free_bf_request_ struct bf_request *request = NULL;
329 : 2 : _free_bf_response_ struct bf_response *response = NULL;
330 : 2 : _cleanup_close_ int prog_fd = -1;
331 : 2 : _free_bf_wpack_ bf_wpack_t *wpack = NULL;
332 : : int r;
333 : :
334 [ + + ]: 2 : if (!name)
335 : : return -EINVAL;
336 : :
337 : 1 : r = bf_wpack_new(&wpack);
338 [ + - ]: 1 : if (r)
339 : : return r;
340 : :
341 : 1 : bf_wpack_kv_str(wpack, "name", name);
342 [ - + ]: 1 : if (!bf_wpack_is_valid(wpack))
343 : : return -EINVAL;
344 : :
345 : 1 : r = bf_request_new_from_pack(&request, BF_FRONT_CLI, BF_REQ_CHAIN_PROG_FD,
346 : : wpack);
347 [ - + ]: 1 : if (r < 0)
348 [ # # ]: 0 : return bf_err_r(r, "failed to init request");
349 : :
350 : 1 : fd = bf_connect_to_daemon();
351 [ + - ]: 1 : if (fd < 0)
352 [ + - ]: 1 : return bf_err_r(fd, "failed to connect to the daemon");
353 : :
354 : 0 : r = bf_send(fd, request, &response, &prog_fd);
355 [ # # ]: 0 : if (r)
356 [ # # ]: 0 : return bf_err_r(r, "failed to request prog FD from the daemon");
357 : :
358 [ # # ]: 0 : if (bf_response_status(response) != 0)
359 [ # # ]: 0 : return bf_err_r(bf_response_status(response),
360 : : "BF_REQ_CHAIN_PROG_FD failed");
361 : :
362 : 0 : return TAKE_FD(prog_fd);
363 : : }
364 : :
365 : 2 : int bf_chain_logs_fd(const char *name)
366 : : {
367 : 2 : _cleanup_close_ int fd = -1;
368 : 2 : _free_bf_request_ struct bf_request *request = NULL;
369 : 2 : _free_bf_response_ struct bf_response *response = NULL;
370 : 2 : _cleanup_close_ int logs_fd = -1;
371 : 2 : _free_bf_wpack_ bf_wpack_t *wpack = NULL;
372 : : int r;
373 : :
374 [ + + ]: 2 : if (!name)
375 : : return -EINVAL;
376 : :
377 : 1 : r = bf_wpack_new(&wpack);
378 [ + - ]: 1 : if (r)
379 : : return r;
380 : :
381 : 1 : bf_wpack_kv_str(wpack, "name", name);
382 [ - + ]: 1 : if (!bf_wpack_is_valid(wpack))
383 : : return -EINVAL;
384 : :
385 : 1 : r = bf_request_new_from_pack(&request, BF_FRONT_CLI, BF_REQ_CHAIN_LOGS_FD,
386 : : wpack);
387 [ - + ]: 1 : if (r < 0)
388 [ # # ]: 0 : return bf_err_r(r, "failed to init request");
389 : :
390 : 1 : fd = bf_connect_to_daemon();
391 [ + - ]: 1 : if (fd < 0)
392 [ + - ]: 1 : return bf_err_r(fd, "failed to connect to the daemon");
393 : :
394 : 0 : r = bf_send(fd, request, &response, &logs_fd);
395 [ # # ]: 0 : if (r)
396 [ # # ]: 0 : return bf_err_r(r, "failed to request logs FD from the daemon");
397 : :
398 [ # # ]: 0 : if (bf_response_status(response) != 0)
399 [ # # ]: 0 : return bf_err_r(bf_response_status(response),
400 : : "BF_REQ_CHAIN_LOGS failed");
401 : :
402 : 0 : return TAKE_FD(logs_fd);
403 : : }
404 : :
405 : 13 : int bf_chain_load(struct bf_chain *chain)
406 : : {
407 : 13 : _cleanup_close_ int fd = -1;
408 : 13 : _free_bf_request_ struct bf_request *request = NULL;
409 : 13 : _free_bf_response_ struct bf_response *response = NULL;
410 : 13 : _free_bf_wpack_ bf_wpack_t *wpack = NULL;
411 : : int r;
412 : :
413 : 13 : r = bf_wpack_new(&wpack);
414 [ + - ]: 13 : if (r)
415 : : return r;
416 : :
417 : 13 : bf_wpack_open_object(wpack, "chain");
418 : 13 : r = bf_chain_pack(chain, wpack);
419 [ + - ]: 13 : if (r)
420 : : return r;
421 : 13 : bf_wpack_close_object(wpack);
422 : :
423 : 13 : r = bf_request_new_from_pack(&request, BF_FRONT_CLI, BF_REQ_CHAIN_LOAD,
424 : : wpack);
425 [ - + ]: 13 : if (r)
426 [ # # ]: 0 : return bf_err_r(r, "bf_chain_load: failed to create a new request");
427 : :
428 : 13 : fd = bf_connect_to_daemon();
429 [ + + ]: 13 : if (fd < 0)
430 [ + - ]: 1 : return bf_err_r(fd, "failed to connect to the daemon");
431 : :
432 : 12 : r = bf_send(fd, request, &response, NULL);
433 [ - + ]: 12 : if (r)
434 [ # # ]: 0 : return bf_err_r(r, "bf_chain_set: failed to send request");
435 : :
436 : 12 : return bf_response_status(response);
437 : : }
438 : :
439 : 11 : int bf_chain_attach(const char *name, const struct bf_hookopts *hookopts)
440 : : {
441 : 11 : _cleanup_close_ int fd = -1;
442 : 11 : _free_bf_request_ struct bf_request *request = NULL;
443 : 11 : _free_bf_response_ struct bf_response *response = NULL;
444 : 11 : _free_bf_wpack_ bf_wpack_t *wpack = NULL;
445 : : int r;
446 : :
447 : 11 : r = bf_wpack_new(&wpack);
448 [ + - ]: 11 : if (r)
449 : : return r;
450 : :
451 : 11 : bf_wpack_kv_str(wpack, "name", name);
452 : 11 : bf_wpack_open_object(wpack, "hookopts");
453 : 11 : r = bf_hookopts_pack(hookopts, wpack);
454 [ + - ]: 11 : if (r)
455 : : return r;
456 : 11 : bf_wpack_close_object(wpack);
457 : :
458 : 11 : r = bf_request_new_from_pack(&request, BF_FRONT_CLI, BF_REQ_CHAIN_ATTACH,
459 : : wpack);
460 [ - + ]: 11 : if (r)
461 [ # # ]: 0 : return bf_err_r(r, "bf_chain_attach: failed to create a new request");
462 : :
463 : 11 : fd = bf_connect_to_daemon();
464 [ + + ]: 11 : if (fd < 0)
465 [ + - ]: 1 : return bf_err_r(fd, "failed to connect to the daemon");
466 : :
467 : 10 : r = bf_send(fd, request, &response, NULL);
468 [ - + ]: 10 : if (r)
469 [ # # ]: 0 : return bf_err_r(r, "bf_chain_attach: failed to send request");
470 : :
471 : 10 : return bf_response_status(response);
472 : : }
473 : :
474 : 6 : int bf_chain_update(const struct bf_chain *chain)
475 : : {
476 : 6 : _cleanup_close_ int fd = -1;
477 : 6 : _free_bf_request_ struct bf_request *request = NULL;
478 : 6 : _free_bf_response_ struct bf_response *response = NULL;
479 : 6 : _free_bf_wpack_ bf_wpack_t *wpack = NULL;
480 : : int r;
481 : :
482 : 6 : r = bf_wpack_new(&wpack);
483 [ + - ]: 6 : if (r)
484 : : return r;
485 : :
486 : 6 : bf_wpack_open_object(wpack, "chain");
487 : 6 : r = bf_chain_pack(chain, wpack);
488 [ + - ]: 6 : if (r)
489 : : return r;
490 : 6 : bf_wpack_close_object(wpack);
491 : :
492 : 6 : r = bf_request_new_from_pack(&request, BF_FRONT_CLI, BF_REQ_CHAIN_UPDATE,
493 : : wpack);
494 [ - + ]: 6 : if (r)
495 [ # # ]: 0 : return bf_err_r(r, "bf_chain_update: failed to create a new request");
496 : :
497 : 6 : fd = bf_connect_to_daemon();
498 [ + + ]: 6 : if (fd < 0)
499 [ + - ]: 1 : return bf_err_r(fd, "failed to connect to the daemon");
500 : :
501 : 5 : r = bf_send(fd, request, &response, NULL);
502 [ - + ]: 5 : if (r)
503 [ # # ]: 0 : return bf_err_r(r, "bf_chain_update: failed to send request");
504 : :
505 : 5 : return bf_response_status(response);
506 : : }
507 : :
508 : 19 : int bf_chain_flush(const char *name)
509 : : {
510 : 19 : _cleanup_close_ int fd = -1;
511 : 19 : _free_bf_request_ struct bf_request *request = NULL;
512 : 19 : _free_bf_response_ struct bf_response *response = NULL;
513 : 19 : _free_bf_wpack_ bf_wpack_t *wpack = NULL;
514 : : int r;
515 : :
516 : 19 : r = bf_wpack_new(&wpack);
517 [ + - ]: 19 : if (r)
518 : : return r;
519 : :
520 : 19 : bf_wpack_kv_str(wpack, "name", name);
521 : :
522 : 19 : r = bf_request_new_from_pack(&request, BF_FRONT_CLI, BF_REQ_CHAIN_FLUSH,
523 : : wpack);
524 [ - + ]: 19 : if (r)
525 [ # # ]: 0 : return bf_err_r(r, "failed to create request for chain");
526 : :
527 : 19 : fd = bf_connect_to_daemon();
528 [ + + ]: 19 : if (fd < 0)
529 [ + - ]: 1 : return bf_err_r(fd, "failed to connect to the daemon");
530 : :
531 : 18 : r = bf_send(fd, request, &response, NULL);
532 [ - + ]: 18 : if (r)
533 [ # # ]: 0 : return bf_err_r(r, "failed to send chain to the daemon");
534 : :
535 : 18 : return bf_response_status(response);
536 : : }
|