]> git.proxmox.com Git - mirror_frr.git/blob - bfdd/bfdd_nb_config.c
Merge pull request #6811 from rgirada/test_helper
[mirror_frr.git] / bfdd / bfdd_nb_config.c
1 /*
2 * BFD daemon northbound implementation.
3 *
4 * Copyright (C) 2019 Network Device Education Foundation, Inc. ("NetDEF")
5 * Rafael Zalamena
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
20 * 02110-1301 USA.
21 */
22
23 #include <zebra.h>
24
25 #include "lib/log.h"
26 #include "lib/northbound.h"
27
28 #include "bfd.h"
29 #include "bfdd_nb.h"
30
31 /*
32 * Helpers.
33 */
34 static void bfd_session_get_key(bool mhop, const struct lyd_node *dnode,
35 struct bfd_key *bk)
36 {
37 const char *ifname = NULL, *vrfname = NULL;
38 struct sockaddr_any psa, lsa;
39
40 /* Required destination parameter. */
41 strtosa(yang_dnode_get_string(dnode, "./dest-addr"), &psa);
42
43 /* Get optional source address. */
44 memset(&lsa, 0, sizeof(lsa));
45 if (yang_dnode_exists(dnode, "./source-addr"))
46 strtosa(yang_dnode_get_string(dnode, "./source-addr"), &lsa);
47
48 ifname = yang_dnode_get_string(dnode, "./interface");
49 vrfname = yang_dnode_get_string(dnode, "./vrf");
50
51 if (strcmp(ifname, "*") == 0)
52 ifname = NULL;
53
54 /* Generate the corresponding key. */
55 gen_bfd_key(bk, &psa, &lsa, mhop, ifname, vrfname);
56 }
57
58 static int bfd_session_create(enum nb_event event, const struct lyd_node *dnode,
59 union nb_resource *resource, bool mhop)
60 {
61 struct bfd_session *bs;
62 const char *ifname;
63 struct bfd_key bk;
64 struct prefix p;
65
66 switch (event) {
67 case NB_EV_VALIDATE:
68 /*
69 * When `dest-addr` is IPv6 and link-local we must
70 * require interface name, otherwise we can't figure
71 * which interface to use to send the packets.
72 */
73 yang_dnode_get_prefix(&p, dnode, "./dest-addr");
74
75 ifname = yang_dnode_get_string(dnode, "./interface");
76
77 if (p.family == AF_INET6 && IN6_IS_ADDR_LINKLOCAL(&p.u.prefix6)
78 && strcmp(ifname, "*") == 0) {
79 zlog_warn(
80 "%s: when using link-local you must specify an interface.",
81 __func__);
82 return NB_ERR_VALIDATION;
83 }
84 break;
85
86 case NB_EV_PREPARE:
87 bfd_session_get_key(mhop, dnode, &bk);
88 bs = bfd_key_lookup(bk);
89
90 /* This session was already configured by another daemon. */
91 if (bs != NULL) {
92 /* Now it is configured also by CLI. */
93 SET_FLAG(bs->flags, BFD_SESS_FLAG_CONFIG);
94 bs->refcount++;
95
96 resource->ptr = bs;
97 break;
98 }
99
100 bs = bfd_session_new();
101
102 /* Fill the session key. */
103 bfd_session_get_key(mhop, dnode, &bs->key);
104
105 /* Set configuration flags. */
106 bs->refcount = 1;
107 SET_FLAG(bs->flags, BFD_SESS_FLAG_CONFIG);
108 if (mhop)
109 SET_FLAG(bs->flags, BFD_SESS_FLAG_MH);
110 if (bs->key.family == AF_INET6)
111 SET_FLAG(bs->flags, BFD_SESS_FLAG_IPV6);
112
113 resource->ptr = bs;
114 break;
115
116 case NB_EV_APPLY:
117 bs = resource->ptr;
118
119 /* Only attempt to registrate if freshly allocated. */
120 if (bs->discrs.my_discr == 0 && bs_registrate(bs) == NULL)
121 return NB_ERR_RESOURCE;
122
123 nb_running_set_entry(dnode, bs);
124 break;
125
126 case NB_EV_ABORT:
127 bs = resource->ptr;
128 if (bs->refcount <= 1)
129 bfd_session_free(resource->ptr);
130 break;
131 }
132
133 return NB_OK;
134 }
135
136 static int bfd_session_destroy(enum nb_event event,
137 const struct lyd_node *dnode, bool mhop)
138 {
139 struct bfd_session *bs;
140 struct bfd_key bk;
141
142 switch (event) {
143 case NB_EV_VALIDATE:
144 bfd_session_get_key(mhop, dnode, &bk);
145 if (bfd_key_lookup(bk) == NULL)
146 return NB_ERR_INCONSISTENCY;
147 break;
148
149 case NB_EV_PREPARE:
150 /* NOTHING */
151 break;
152
153 case NB_EV_APPLY:
154 bs = nb_running_unset_entry(dnode);
155 /* CLI is not using this session anymore. */
156 if (CHECK_FLAG(bs->flags, BFD_SESS_FLAG_CONFIG) == 0)
157 break;
158
159 UNSET_FLAG(bs->flags, BFD_SESS_FLAG_CONFIG);
160 bs->refcount--;
161 /* There are still daemons using it. */
162 if (bs->refcount > 0)
163 break;
164
165 bfd_session_free(bs);
166 break;
167
168 case NB_EV_ABORT:
169 /* NOTHING */
170 break;
171 }
172
173 return NB_OK;
174 }
175
176 /*
177 * XPath: /frr-bfdd:bfdd/bfd
178 */
179 int bfdd_bfd_create(struct nb_cb_create_args *args)
180 {
181 /* NOTHING */
182 return NB_OK;
183 }
184
185 int bfdd_bfd_destroy(struct nb_cb_destroy_args *args)
186 {
187 switch (args->event) {
188 case NB_EV_VALIDATE:
189 /* NOTHING */
190 return NB_OK;
191
192 case NB_EV_PREPARE:
193 /* NOTHING */
194 return NB_OK;
195
196 case NB_EV_APPLY:
197 bfd_sessions_remove_manual();
198 break;
199
200 case NB_EV_ABORT:
201 /* NOTHING */
202 return NB_OK;
203 }
204
205 return NB_OK;
206 }
207
208 /*
209 * XPath: /frr-bfdd:bfdd/bfd/profile
210 */
211 int bfdd_bfd_profile_create(struct nb_cb_create_args *args)
212 {
213 struct bfd_profile *bp;
214 const char *name;
215
216 if (args->event != NB_EV_APPLY)
217 return NB_OK;
218
219 name = yang_dnode_get_string(args->dnode, "./name");
220 bp = bfd_profile_new(name);
221 nb_running_set_entry(args->dnode, bp);
222
223 return NB_OK;
224 }
225
226 int bfdd_bfd_profile_destroy(struct nb_cb_destroy_args *args)
227 {
228 struct bfd_profile *bp;
229
230 if (args->event != NB_EV_APPLY)
231 return NB_OK;
232
233 bp = nb_running_unset_entry(args->dnode);
234 bfd_profile_free(bp);
235
236 return NB_OK;
237 }
238
239 /*
240 * XPath: /frr-bfdd:bfdd/bfd/profile/detection-multiplier
241 */
242 int bfdd_bfd_profile_detection_multiplier_modify(struct nb_cb_modify_args *args)
243 {
244 struct bfd_profile *bp;
245
246 if (args->event != NB_EV_APPLY)
247 return NB_OK;
248
249 bp = nb_running_get_entry(args->dnode, NULL, true);
250 bp->detection_multiplier = yang_dnode_get_uint8(args->dnode, NULL);
251 bfd_profile_update(bp);
252
253 return NB_OK;
254 }
255
256 /*
257 * XPath: /frr-bfdd:bfdd/bfd/profile/desired-transmission-interval
258 */
259 int bfdd_bfd_profile_desired_transmission_interval_modify(
260 struct nb_cb_modify_args *args)
261 {
262 struct bfd_profile *bp;
263 uint32_t min_tx;
264
265 switch (args->event) {
266 case NB_EV_VALIDATE:
267 min_tx = yang_dnode_get_uint32(args->dnode, NULL);
268 if (min_tx < 10000 || min_tx > 60000000)
269 return NB_ERR_VALIDATION;
270 break;
271
272 case NB_EV_PREPARE:
273 /* NOTHING */
274 break;
275
276 case NB_EV_APPLY:
277 min_tx = yang_dnode_get_uint32(args->dnode, NULL);
278 bp = nb_running_get_entry(args->dnode, NULL, true);
279 if (bp->min_tx == min_tx)
280 return NB_OK;
281
282 bp->min_tx = min_tx;
283 bfd_profile_update(bp);
284 break;
285
286 case NB_EV_ABORT:
287 /* NOTHING */
288 break;
289 }
290
291 return NB_OK;
292 }
293
294 /*
295 * XPath: /frr-bfdd:bfdd/bfd/profile/required-receive-interval
296 */
297 int bfdd_bfd_profile_required_receive_interval_modify(
298 struct nb_cb_modify_args *args)
299 {
300 struct bfd_profile *bp;
301 uint32_t min_rx;
302
303 switch (args->event) {
304 case NB_EV_VALIDATE:
305 min_rx = yang_dnode_get_uint32(args->dnode, NULL);
306 if (min_rx < 10000 || min_rx > 60000000)
307 return NB_ERR_VALIDATION;
308 break;
309
310 case NB_EV_PREPARE:
311 /* NOTHING */
312 break;
313
314 case NB_EV_APPLY:
315 min_rx = yang_dnode_get_uint32(args->dnode, NULL);
316 bp = nb_running_get_entry(args->dnode, NULL, true);
317 if (bp->min_rx == min_rx)
318 return NB_OK;
319
320 bp->min_rx = min_rx;
321 bfd_profile_update(bp);
322 break;
323
324 case NB_EV_ABORT:
325 /* NOTHING */
326 break;
327 }
328
329 return NB_OK;
330 }
331
332 /*
333 * XPath: /frr-bfdd:bfdd/bfd/profile/administrative-down
334 */
335 int bfdd_bfd_profile_administrative_down_modify(struct nb_cb_modify_args *args)
336 {
337 struct bfd_profile *bp;
338 bool shutdown;
339
340 if (args->event != NB_EV_APPLY)
341 return NB_OK;
342
343 shutdown = yang_dnode_get_bool(args->dnode, NULL);
344 bp = nb_running_get_entry(args->dnode, NULL, true);
345 if (bp->admin_shutdown == shutdown)
346 return NB_OK;
347
348 bp->admin_shutdown = shutdown;
349 bfd_profile_update(bp);
350
351 return NB_OK;
352 }
353
354 /*
355 * XPath: /frr-bfdd:bfdd/bfd/profile/passive-mode
356 */
357 int bfdd_bfd_profile_passive_mode_modify(struct nb_cb_modify_args *args)
358 {
359 struct bfd_profile *bp;
360 bool passive;
361
362 if (args->event != NB_EV_APPLY)
363 return NB_OK;
364
365 passive = yang_dnode_get_bool(args->dnode, NULL);
366 bp = nb_running_get_entry(args->dnode, NULL, true);
367 if (bp->passive == passive)
368 return NB_OK;
369
370 bp->passive = passive;
371 bfd_profile_update(bp);
372
373 return NB_OK;
374 }
375
376 /*
377 * XPath: /frr-bfdd:bfdd/bfd/profile/minimum-ttl
378 */
379 int bfdd_bfd_profile_minimum_ttl_modify(struct nb_cb_modify_args *args)
380 {
381 struct bfd_profile *bp;
382 uint8_t minimum_ttl;
383
384 if (args->event != NB_EV_APPLY)
385 return NB_OK;
386
387 minimum_ttl = yang_dnode_get_uint8(args->dnode, NULL);
388 bp = nb_running_get_entry(args->dnode, NULL, true);
389 if (bp->minimum_ttl == minimum_ttl)
390 return NB_OK;
391
392 bp->minimum_ttl = minimum_ttl;
393 bfd_profile_update(bp);
394
395 return NB_OK;
396 }
397
398 int bfdd_bfd_profile_minimum_ttl_destroy(struct nb_cb_destroy_args *args)
399 {
400 struct bfd_profile *bp;
401
402 if (args->event != NB_EV_APPLY)
403 return NB_OK;
404
405 bp = nb_running_get_entry(args->dnode, NULL, true);
406 bp->minimum_ttl = BFD_DEF_MHOP_TTL;
407 bfd_profile_update(bp);
408
409 return NB_OK;
410 }
411
412 /*
413 * XPath: /frr-bfdd:bfdd/bfd/profile/echo-mode
414 */
415 int bfdd_bfd_profile_echo_mode_modify(struct nb_cb_modify_args *args)
416 {
417 struct bfd_profile *bp;
418 bool echo;
419
420 if (args->event != NB_EV_APPLY)
421 return NB_OK;
422
423 echo = yang_dnode_get_bool(args->dnode, NULL);
424 bp = nb_running_get_entry(args->dnode, NULL, true);
425 if (bp->echo_mode == echo)
426 return NB_OK;
427
428 bp->echo_mode = echo;
429 bfd_profile_update(bp);
430
431 return NB_OK;
432 }
433
434 /*
435 * XPath: /frr-bfdd:bfdd/bfd/profile/desired-echo-echo-transmission-interval
436 */
437 int bfdd_bfd_profile_desired_echo_transmission_interval_modify(
438 struct nb_cb_modify_args *args)
439 {
440 struct bfd_profile *bp;
441 uint32_t min_rx;
442
443 switch (args->event) {
444 case NB_EV_VALIDATE:
445 min_rx = yang_dnode_get_uint32(args->dnode, NULL);
446 if (min_rx < 10000 || min_rx > 60000000)
447 return NB_ERR_VALIDATION;
448 break;
449
450 case NB_EV_PREPARE:
451 /* NOTHING */
452 break;
453
454 case NB_EV_APPLY:
455 min_rx = yang_dnode_get_uint32(args->dnode, NULL);
456 bp = nb_running_get_entry(args->dnode, NULL, true);
457 if (bp->min_echo_rx == min_rx)
458 return NB_OK;
459
460 bp->min_echo_rx = min_rx;
461 bfd_profile_update(bp);
462 break;
463
464 case NB_EV_ABORT:
465 /* NOTHING */
466 break;
467 }
468
469 return NB_OK;
470 }
471
472 /*
473 * XPath: /frr-bfdd:bfdd/bfd/sessions/single-hop
474 */
475 int bfdd_bfd_sessions_single_hop_create(struct nb_cb_create_args *args)
476 {
477 return bfd_session_create(args->event, args->dnode, args->resource,
478 false);
479 }
480
481 int bfdd_bfd_sessions_single_hop_destroy(struct nb_cb_destroy_args *args)
482 {
483 return bfd_session_destroy(args->event, args->dnode, false);
484 }
485
486 /*
487 * XPath: /frr-bfdd:bfdd/bfd/sessions/single-hop/source-addr
488 */
489 int bfdd_bfd_sessions_single_hop_source_addr_modify(
490 struct nb_cb_modify_args *args)
491 {
492 return NB_OK;
493 }
494
495 int bfdd_bfd_sessions_single_hop_source_addr_destroy(
496 struct nb_cb_destroy_args *args)
497 {
498 return NB_OK;
499 }
500
501 /*
502 * XPath: /frr-bfdd:bfdd/bfd/sessions/single-hop/profile
503 */
504 int bfdd_bfd_sessions_single_hop_profile_modify(struct nb_cb_modify_args *args)
505 {
506 struct bfd_session *bs;
507
508 if (args->event != NB_EV_APPLY)
509 return NB_OK;
510
511 bs = nb_running_get_entry(args->dnode, NULL, true);
512 bfd_profile_apply(yang_dnode_get_string(args->dnode, NULL), bs);
513
514 return NB_OK;
515 }
516
517 int bfdd_bfd_sessions_single_hop_profile_destroy(
518 struct nb_cb_destroy_args *args)
519 {
520 struct bfd_session *bs;
521
522 if (args->event != NB_EV_APPLY)
523 return NB_OK;
524
525 bs = nb_running_get_entry(args->dnode, NULL, true);
526 bfd_profile_remove(bs);
527
528 return NB_OK;
529 }
530
531 /*
532 * XPath: /frr-bfdd:bfdd/bfd/sessions/single-hop/detection-multiplier
533 */
534 int bfdd_bfd_sessions_single_hop_detection_multiplier_modify(
535 struct nb_cb_modify_args *args)
536 {
537 uint8_t detection_multiplier = yang_dnode_get_uint8(args->dnode, NULL);
538 struct bfd_session *bs;
539
540 switch (args->event) {
541 case NB_EV_VALIDATE:
542 break;
543
544 case NB_EV_PREPARE:
545 /* NOTHING */
546 break;
547
548 case NB_EV_APPLY:
549 bs = nb_running_get_entry(args->dnode, NULL, true);
550 bs->peer_profile.detection_multiplier = detection_multiplier;
551 bfd_session_apply(bs);
552 break;
553
554 case NB_EV_ABORT:
555 /* NOTHING */
556 break;
557 }
558
559 return NB_OK;
560 }
561
562 /*
563 * XPath: /frr-bfdd:bfdd/bfd/sessions/single-hop/desired-transmission-interval
564 */
565 int bfdd_bfd_sessions_single_hop_desired_transmission_interval_modify(
566 struct nb_cb_modify_args *args)
567 {
568 uint32_t tx_interval = yang_dnode_get_uint32(args->dnode, NULL);
569 struct bfd_session *bs;
570
571 switch (args->event) {
572 case NB_EV_VALIDATE:
573 if (tx_interval < 10000 || tx_interval > 60000000)
574 return NB_ERR_VALIDATION;
575 break;
576
577 case NB_EV_PREPARE:
578 /* NOTHING */
579 break;
580
581 case NB_EV_APPLY:
582 bs = nb_running_get_entry(args->dnode, NULL, true);
583 if (tx_interval == bs->timers.desired_min_tx)
584 return NB_OK;
585
586 bs->peer_profile.min_tx = tx_interval;
587 bfd_session_apply(bs);
588 break;
589
590 case NB_EV_ABORT:
591 /* NOTHING */
592 break;
593 }
594
595 return NB_OK;
596 }
597
598 /*
599 * XPath: /frr-bfdd:bfdd/bfd/sessions/single-hop/required-receive-interval
600 */
601 int bfdd_bfd_sessions_single_hop_required_receive_interval_modify(
602 struct nb_cb_modify_args *args)
603 {
604 uint32_t rx_interval = yang_dnode_get_uint32(args->dnode, NULL);
605 struct bfd_session *bs;
606
607 switch (args->event) {
608 case NB_EV_VALIDATE:
609 if (rx_interval < 10000 || rx_interval > 60000000)
610 return NB_ERR_VALIDATION;
611 break;
612
613 case NB_EV_PREPARE:
614 /* NOTHING */
615 break;
616
617 case NB_EV_APPLY:
618 bs = nb_running_get_entry(args->dnode, NULL, true);
619 if (rx_interval == bs->timers.required_min_rx)
620 return NB_OK;
621
622 bs->peer_profile.min_rx = rx_interval;
623 bfd_session_apply(bs);
624 break;
625
626 case NB_EV_ABORT:
627 /* NOTHING */
628 break;
629 }
630
631 return NB_OK;
632 }
633
634 /*
635 * XPath: /frr-bfdd:bfdd/bfd/sessions/single-hop/administrative-down
636 */
637 int bfdd_bfd_sessions_single_hop_administrative_down_modify(
638 struct nb_cb_modify_args *args)
639 {
640 bool shutdown = yang_dnode_get_bool(args->dnode, NULL);
641 struct bfd_session *bs;
642
643 switch (args->event) {
644 case NB_EV_VALIDATE:
645 case NB_EV_PREPARE:
646 return NB_OK;
647
648 case NB_EV_APPLY:
649 break;
650
651 case NB_EV_ABORT:
652 return NB_OK;
653 }
654
655 bs = nb_running_get_entry(args->dnode, NULL, true);
656 bs->peer_profile.admin_shutdown = shutdown;
657 bfd_session_apply(bs);
658
659 return NB_OK;
660 }
661
662 /*
663 * XPath: /frr-bfdd:bfdd/bfd/sessions/single-hop/passive-mode
664 */
665 int bfdd_bfd_sessions_single_hop_passive_mode_modify(
666 struct nb_cb_modify_args *args)
667 {
668 struct bfd_session *bs;
669 bool passive;
670
671 switch (args->event) {
672 case NB_EV_VALIDATE:
673 case NB_EV_PREPARE:
674 return NB_OK;
675
676 case NB_EV_APPLY:
677 break;
678
679 case NB_EV_ABORT:
680 return NB_OK;
681 }
682
683 passive = yang_dnode_get_bool(args->dnode, NULL);
684
685 bs = nb_running_get_entry(args->dnode, NULL, true);
686 bs->peer_profile.passive = passive;
687 bfd_session_apply(bs);
688
689 return NB_OK;
690 }
691
692 /*
693 * XPath: /frr-bfdd:bfdd/bfd/sessions/single-hop/echo-mode
694 */
695 int bfdd_bfd_sessions_single_hop_echo_mode_modify(
696 struct nb_cb_modify_args *args)
697 {
698 bool echo = yang_dnode_get_bool(args->dnode, NULL);
699 struct bfd_session *bs;
700
701 switch (args->event) {
702 case NB_EV_VALIDATE:
703 case NB_EV_PREPARE:
704 return NB_OK;
705
706 case NB_EV_APPLY:
707 break;
708
709 case NB_EV_ABORT:
710 return NB_OK;
711 }
712
713 bs = nb_running_get_entry(args->dnode, NULL, true);
714 bs->peer_profile.echo_mode = echo;
715 bfd_session_apply(bs);
716
717 return NB_OK;
718 }
719
720 /*
721 * XPath:
722 * /frr-bfdd:bfdd/bfd/sessions/single-hop/desired-echo-transmission-interval
723 */
724 int bfdd_bfd_sessions_single_hop_desired_echo_transmission_interval_modify(
725 struct nb_cb_modify_args *args)
726 {
727 uint32_t echo_interval = yang_dnode_get_uint32(args->dnode, NULL);
728 struct bfd_session *bs;
729
730 switch (args->event) {
731 case NB_EV_VALIDATE:
732 if (echo_interval < 10000 || echo_interval > 60000000)
733 return NB_ERR_VALIDATION;
734 break;
735
736 case NB_EV_PREPARE:
737 /* NOTHING */
738 break;
739
740 case NB_EV_APPLY:
741 bs = nb_running_get_entry(args->dnode, NULL, true);
742 if (echo_interval == bs->timers.required_min_echo)
743 return NB_OK;
744
745 bs->peer_profile.min_echo_rx = echo_interval;
746 bfd_session_apply(bs);
747 break;
748
749 case NB_EV_ABORT:
750 /* NOTHING */
751 break;
752 }
753
754 return NB_OK;
755 }
756
757 /*
758 * XPath: /frr-bfdd:bfdd/bfd/sessions/multi-hop
759 */
760 int bfdd_bfd_sessions_multi_hop_create(struct nb_cb_create_args *args)
761 {
762 return bfd_session_create(args->event, args->dnode, args->resource,
763 true);
764 }
765
766 int bfdd_bfd_sessions_multi_hop_destroy(struct nb_cb_destroy_args *args)
767 {
768 return bfd_session_destroy(args->event, args->dnode, true);
769 }
770
771 /*
772 * XPath: /frr-bfdd:bfdd/bfd/sessions/multi-hop/minimum-ttl
773 */
774 int bfdd_bfd_sessions_multi_hop_minimum_ttl_modify(
775 struct nb_cb_modify_args *args)
776 {
777 struct bfd_session *bs;
778
779 switch (args->event) {
780 case NB_EV_VALIDATE:
781 case NB_EV_PREPARE:
782 return NB_OK;
783
784 case NB_EV_APPLY:
785 break;
786
787 case NB_EV_ABORT:
788 return NB_OK;
789 }
790
791 bs = nb_running_get_entry(args->dnode, NULL, true);
792 bs->peer_profile.minimum_ttl = yang_dnode_get_uint8(args->dnode, NULL);
793 bfd_session_apply(bs);
794
795 return NB_OK;
796 }
797
798 int bfdd_bfd_sessions_multi_hop_minimum_ttl_destroy(
799 struct nb_cb_destroy_args *args)
800 {
801 struct bfd_session *bs;
802
803 switch (args->event) {
804 case NB_EV_VALIDATE:
805 case NB_EV_PREPARE:
806 return NB_OK;
807
808 case NB_EV_APPLY:
809 break;
810
811 case NB_EV_ABORT:
812 return NB_OK;
813 }
814
815 bs = nb_running_get_entry(args->dnode, NULL, true);
816 bs->peer_profile.minimum_ttl = BFD_DEF_MHOP_TTL;
817 bfd_session_apply(bs);
818
819 return NB_OK;
820 }