]> git.proxmox.com Git - mirror_frr.git/blob - eigrpd/eigrp_northbound.c
tools: improve explanation of 'wrap' options
[mirror_frr.git] / eigrpd / eigrp_northbound.c
1 /*
2 * EIGRP 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/keychain.h"
26 #include "lib/log.h"
27 #include "lib/northbound.h"
28 #include "lib/table.h"
29 #include "lib/vrf.h"
30 #include "lib/zclient.h"
31
32 #include "eigrp_structs.h"
33 #include "eigrpd.h"
34 #include "eigrp_interface.h"
35 #include "eigrp_network.h"
36 #include "eigrp_zebra.h"
37 #include "eigrp_cli.h"
38
39 /* Helper functions. */
40 static void redistribute_get_metrics(const struct lyd_node *dnode,
41 struct eigrp_metrics *em)
42 {
43 memset(em, 0, sizeof(*em));
44
45 if (yang_dnode_exists(dnode, "./bandwidth"))
46 em->bandwidth = yang_dnode_get_uint32(dnode, "./bandwidth");
47 if (yang_dnode_exists(dnode, "./delay"))
48 em->delay = yang_dnode_get_uint32(dnode, "./delay");
49 #if 0 /* TODO: How does MTU work? */
50 if (yang_dnode_exists(dnode, "./mtu"))
51 em->mtu[0] = yang_dnode_get_uint32(dnode, "./mtu");
52 #endif
53 if (yang_dnode_exists(dnode, "./load"))
54 em->load = yang_dnode_get_uint32(dnode, "./load");
55 if (yang_dnode_exists(dnode, "./reliability"))
56 em->reliability = yang_dnode_get_uint32(dnode, "./reliability");
57 }
58
59 static struct eigrp_interface *eigrp_interface_lookup(const struct eigrp *eigrp,
60 const char *ifname)
61 {
62 struct eigrp_interface *eif;
63 struct listnode *ln;
64
65 for (ALL_LIST_ELEMENTS_RO(eigrp->eiflist, ln, eif)) {
66 if (strcmp(ifname, eif->ifp->name))
67 continue;
68
69 return eif;
70 }
71
72 return NULL;
73 }
74
75 /*
76 * XPath: /frr-eigrpd:eigrpd/instance
77 */
78 static int eigrpd_instance_create(struct nb_cb_create_args *args)
79 {
80 struct eigrp *eigrp;
81 const char *vrf;
82 struct vrf *pVrf;
83 vrf_id_t vrfid;
84
85 switch (args->event) {
86 case NB_EV_VALIDATE:
87 /* NOTHING */
88 break;
89 case NB_EV_PREPARE:
90 vrf = yang_dnode_get_string(args->dnode, "./vrf");
91
92 pVrf = vrf_lookup_by_name(vrf);
93 if (pVrf)
94 vrfid = pVrf->vrf_id;
95 else
96 vrfid = VRF_DEFAULT;
97
98 eigrp = eigrp_get(yang_dnode_get_uint16(args->dnode, "./asn"),
99 vrfid);
100 args->resource->ptr = eigrp;
101 break;
102 case NB_EV_ABORT:
103 eigrp_finish_final(args->resource->ptr);
104 break;
105 case NB_EV_APPLY:
106 nb_running_set_entry(args->dnode, args->resource->ptr);
107 break;
108 }
109
110 return NB_OK;
111 }
112
113 static int eigrpd_instance_destroy(struct nb_cb_destroy_args *args)
114 {
115 struct eigrp *eigrp;
116
117 switch (args->event) {
118 case NB_EV_VALIDATE:
119 case NB_EV_PREPARE:
120 case NB_EV_ABORT:
121 /* NOTHING */
122 break;
123 case NB_EV_APPLY:
124 eigrp = nb_running_unset_entry(args->dnode);
125 eigrp_finish_final(eigrp);
126 break;
127 }
128
129 return NB_OK;
130 }
131
132 /*
133 * XPath: /frr-eigrpd:eigrpd/instance/router-id
134 */
135 static int eigrpd_instance_router_id_modify(struct nb_cb_modify_args *args)
136 {
137 struct eigrp *eigrp;
138
139 switch (args->event) {
140 case NB_EV_VALIDATE:
141 case NB_EV_PREPARE:
142 case NB_EV_ABORT:
143 /* NOTHING */
144 break;
145 case NB_EV_APPLY:
146 eigrp = nb_running_get_entry(args->dnode, NULL, true);
147 yang_dnode_get_ipv4(&eigrp->router_id_static, args->dnode,
148 NULL);
149 break;
150 }
151
152 return NB_OK;
153 }
154
155 static int eigrpd_instance_router_id_destroy(struct nb_cb_destroy_args *args)
156 {
157 struct eigrp *eigrp;
158
159 switch (args->event) {
160 case NB_EV_VALIDATE:
161 case NB_EV_PREPARE:
162 case NB_EV_ABORT:
163 /* NOTHING */
164 break;
165 case NB_EV_APPLY:
166 eigrp = nb_running_get_entry(args->dnode, NULL, true);
167 eigrp->router_id_static.s_addr = INADDR_ANY;
168 break;
169 }
170
171 return NB_OK;
172 }
173
174 /*
175 * XPath: /frr-eigrpd:eigrpd/instance/passive-interface
176 */
177 static int
178 eigrpd_instance_passive_interface_create(struct nb_cb_create_args *args)
179 {
180 struct eigrp_interface *eif;
181 struct eigrp *eigrp;
182 const char *ifname;
183
184 switch (args->event) {
185 case NB_EV_VALIDATE:
186 eigrp = nb_running_get_entry(args->dnode, NULL, false);
187 if (eigrp == NULL) {
188 /*
189 * XXX: we can't verify if the interface exists
190 * and is active until EIGRP is up.
191 */
192 break;
193 }
194
195 ifname = yang_dnode_get_string(args->dnode, NULL);
196 eif = eigrp_interface_lookup(eigrp, ifname);
197 if (eif == NULL)
198 return NB_ERR_INCONSISTENCY;
199 break;
200 case NB_EV_PREPARE:
201 case NB_EV_ABORT:
202 /* NOTHING */
203 break;
204 case NB_EV_APPLY:
205 eigrp = nb_running_get_entry(args->dnode, NULL, true);
206 ifname = yang_dnode_get_string(args->dnode, NULL);
207 eif = eigrp_interface_lookup(eigrp, ifname);
208 if (eif == NULL)
209 return NB_ERR_INCONSISTENCY;
210
211 eif->params.passive_interface = EIGRP_IF_PASSIVE;
212 break;
213 }
214
215 return NB_OK;
216 }
217
218 static int
219 eigrpd_instance_passive_interface_destroy(struct nb_cb_destroy_args *args)
220 {
221 struct eigrp_interface *eif;
222 struct eigrp *eigrp;
223 const char *ifname;
224
225 switch (args->event) {
226 case NB_EV_VALIDATE:
227 case NB_EV_PREPARE:
228 case NB_EV_ABORT:
229 /* NOTHING */
230 break;
231 case NB_EV_APPLY:
232 eigrp = nb_running_get_entry(args->dnode, NULL, true);
233 ifname = yang_dnode_get_string(args->dnode, NULL);
234 eif = eigrp_interface_lookup(eigrp, ifname);
235 if (eif == NULL)
236 break;
237
238 eif->params.passive_interface = EIGRP_IF_ACTIVE;
239 break;
240 }
241
242 return NB_OK;
243 }
244
245 /*
246 * XPath: /frr-eigrpd:eigrpd/instance/active-time
247 */
248 static int eigrpd_instance_active_time_modify(struct nb_cb_modify_args *args)
249 {
250 switch (args->event) {
251 case NB_EV_VALIDATE:
252 /* TODO: Not implemented. */
253 case NB_EV_PREPARE:
254 case NB_EV_ABORT:
255 return NB_OK;
256 case NB_EV_APPLY:
257 snprintf(args->errmsg, args->errmsg_len,
258 "active time not implemented yet");
259 /* NOTHING */
260 break;
261 }
262
263 return NB_OK;
264 }
265
266 /*
267 * XPath: /frr-eigrpd:eigrpd/instance/variance
268 */
269 static int eigrpd_instance_variance_modify(struct nb_cb_modify_args *args)
270 {
271 struct eigrp *eigrp;
272
273 switch (args->event) {
274 case NB_EV_VALIDATE:
275 case NB_EV_PREPARE:
276 case NB_EV_ABORT:
277 /* NOTHING */
278 break;
279 case NB_EV_APPLY:
280 eigrp = nb_running_get_entry(args->dnode, NULL, true);
281 eigrp->variance = yang_dnode_get_uint8(args->dnode, NULL);
282 break;
283 }
284
285 return NB_OK;
286 }
287
288 static int eigrpd_instance_variance_destroy(struct nb_cb_destroy_args *args)
289 {
290 struct eigrp *eigrp;
291
292 switch (args->event) {
293 case NB_EV_VALIDATE:
294 case NB_EV_PREPARE:
295 case NB_EV_ABORT:
296 /* NOTHING */
297 break;
298 case NB_EV_APPLY:
299 eigrp = nb_running_get_entry(args->dnode, NULL, true);
300 eigrp->variance = EIGRP_VARIANCE_DEFAULT;
301 break;
302 }
303
304 return NB_OK;
305 }
306
307 /*
308 * XPath: /frr-eigrpd:eigrpd/instance/maximum-paths
309 */
310 static int eigrpd_instance_maximum_paths_modify(struct nb_cb_modify_args *args)
311 {
312 struct eigrp *eigrp;
313
314 switch (args->event) {
315 case NB_EV_VALIDATE:
316 case NB_EV_PREPARE:
317 case NB_EV_ABORT:
318 /* NOTHING */
319 break;
320 case NB_EV_APPLY:
321 eigrp = nb_running_get_entry(args->dnode, NULL, true);
322 eigrp->max_paths = yang_dnode_get_uint8(args->dnode, NULL);
323 break;
324 }
325
326 return NB_OK;
327 }
328
329 static int
330 eigrpd_instance_maximum_paths_destroy(struct nb_cb_destroy_args *args)
331 {
332 struct eigrp *eigrp;
333
334 switch (args->event) {
335 case NB_EV_VALIDATE:
336 case NB_EV_PREPARE:
337 case NB_EV_ABORT:
338 /* NOTHING */
339 break;
340 case NB_EV_APPLY:
341 eigrp = nb_running_get_entry(args->dnode, NULL, true);
342 eigrp->max_paths = EIGRP_MAX_PATHS_DEFAULT;
343 break;
344 }
345
346 return NB_OK;
347 }
348
349 /*
350 * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K1
351 */
352 static int
353 eigrpd_instance_metric_weights_K1_modify(struct nb_cb_modify_args *args)
354 {
355 struct eigrp *eigrp;
356
357 switch (args->event) {
358 case NB_EV_VALIDATE:
359 case NB_EV_PREPARE:
360 case NB_EV_ABORT:
361 /* NOTHING */
362 break;
363 case NB_EV_APPLY:
364 eigrp = nb_running_get_entry(args->dnode, NULL, true);
365 eigrp->k_values[0] = yang_dnode_get_uint8(args->dnode, NULL);
366 break;
367 }
368
369 return NB_OK;
370 }
371
372 static int
373 eigrpd_instance_metric_weights_K1_destroy(struct nb_cb_destroy_args *args)
374 {
375 struct eigrp *eigrp;
376
377 switch (args->event) {
378 case NB_EV_VALIDATE:
379 case NB_EV_PREPARE:
380 case NB_EV_ABORT:
381 /* NOTHING */
382 break;
383 case NB_EV_APPLY:
384 eigrp = nb_running_get_entry(args->dnode, NULL, true);
385 eigrp->k_values[0] = EIGRP_K1_DEFAULT;
386 break;
387 }
388
389 return NB_OK;
390 }
391
392 /*
393 * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K2
394 */
395 static int
396 eigrpd_instance_metric_weights_K2_modify(struct nb_cb_modify_args *args)
397 {
398 struct eigrp *eigrp;
399
400 switch (args->event) {
401 case NB_EV_VALIDATE:
402 case NB_EV_PREPARE:
403 case NB_EV_ABORT:
404 /* NOTHING */
405 break;
406 case NB_EV_APPLY:
407 eigrp = nb_running_get_entry(args->dnode, NULL, true);
408 eigrp->k_values[1] = yang_dnode_get_uint8(args->dnode, NULL);
409 break;
410 }
411
412 return NB_OK;
413 }
414
415 static int
416 eigrpd_instance_metric_weights_K2_destroy(struct nb_cb_destroy_args *args)
417 {
418 struct eigrp *eigrp;
419
420 switch (args->event) {
421 case NB_EV_VALIDATE:
422 case NB_EV_PREPARE:
423 case NB_EV_ABORT:
424 /* NOTHING */
425 break;
426 case NB_EV_APPLY:
427 eigrp = nb_running_get_entry(args->dnode, NULL, true);
428 eigrp->k_values[1] = EIGRP_K2_DEFAULT;
429 break;
430 }
431
432 return NB_OK;
433 }
434
435 /*
436 * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K3
437 */
438 static int
439 eigrpd_instance_metric_weights_K3_modify(struct nb_cb_modify_args *args)
440 {
441 struct eigrp *eigrp;
442
443 switch (args->event) {
444 case NB_EV_VALIDATE:
445 case NB_EV_PREPARE:
446 case NB_EV_ABORT:
447 /* NOTHING */
448 break;
449 case NB_EV_APPLY:
450 eigrp = nb_running_get_entry(args->dnode, NULL, true);
451 eigrp->k_values[2] = yang_dnode_get_uint8(args->dnode, NULL);
452 break;
453 }
454
455 return NB_OK;
456 }
457
458 static int
459 eigrpd_instance_metric_weights_K3_destroy(struct nb_cb_destroy_args *args)
460 {
461 struct eigrp *eigrp;
462
463 switch (args->event) {
464 case NB_EV_VALIDATE:
465 case NB_EV_PREPARE:
466 case NB_EV_ABORT:
467 /* NOTHING */
468 break;
469 case NB_EV_APPLY:
470 eigrp = nb_running_get_entry(args->dnode, NULL, true);
471 eigrp->k_values[2] = EIGRP_K3_DEFAULT;
472 break;
473 }
474
475 return NB_OK;
476 }
477
478 /*
479 * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K4
480 */
481 static int
482 eigrpd_instance_metric_weights_K4_modify(struct nb_cb_modify_args *args)
483 {
484 struct eigrp *eigrp;
485
486 switch (args->event) {
487 case NB_EV_VALIDATE:
488 case NB_EV_PREPARE:
489 case NB_EV_ABORT:
490 /* NOTHING */
491 break;
492 case NB_EV_APPLY:
493 eigrp = nb_running_get_entry(args->dnode, NULL, true);
494 eigrp->k_values[3] = yang_dnode_get_uint8(args->dnode, NULL);
495 break;
496 }
497
498 return NB_OK;
499 }
500
501 static int
502 eigrpd_instance_metric_weights_K4_destroy(struct nb_cb_destroy_args *args)
503 {
504 struct eigrp *eigrp;
505
506 switch (args->event) {
507 case NB_EV_VALIDATE:
508 case NB_EV_PREPARE:
509 case NB_EV_ABORT:
510 /* NOTHING */
511 break;
512 case NB_EV_APPLY:
513 eigrp = nb_running_get_entry(args->dnode, NULL, true);
514 eigrp->k_values[3] = EIGRP_K4_DEFAULT;
515 break;
516 }
517
518 return NB_OK;
519 }
520
521 /*
522 * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K5
523 */
524 static int
525 eigrpd_instance_metric_weights_K5_modify(struct nb_cb_modify_args *args)
526 {
527 struct eigrp *eigrp;
528
529 switch (args->event) {
530 case NB_EV_VALIDATE:
531 case NB_EV_PREPARE:
532 case NB_EV_ABORT:
533 /* NOTHING */
534 break;
535 case NB_EV_APPLY:
536 eigrp = nb_running_get_entry(args->dnode, NULL, true);
537 eigrp->k_values[4] = yang_dnode_get_uint8(args->dnode, NULL);
538 break;
539 }
540
541 return NB_OK;
542 }
543
544 static int
545 eigrpd_instance_metric_weights_K5_destroy(struct nb_cb_destroy_args *args)
546 {
547 struct eigrp *eigrp;
548
549 switch (args->event) {
550 case NB_EV_VALIDATE:
551 case NB_EV_PREPARE:
552 case NB_EV_ABORT:
553 /* NOTHING */
554 break;
555 case NB_EV_APPLY:
556 eigrp = nb_running_get_entry(args->dnode, NULL, true);
557 eigrp->k_values[4] = EIGRP_K5_DEFAULT;
558 break;
559 }
560
561 return NB_OK;
562 }
563
564 /*
565 * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K6
566 */
567 static int
568 eigrpd_instance_metric_weights_K6_modify(struct nb_cb_modify_args *args)
569 {
570 struct eigrp *eigrp;
571
572 switch (args->event) {
573 case NB_EV_VALIDATE:
574 case NB_EV_PREPARE:
575 case NB_EV_ABORT:
576 /* NOTHING */
577 break;
578 case NB_EV_APPLY:
579 eigrp = nb_running_get_entry(args->dnode, NULL, true);
580 eigrp->k_values[5] = yang_dnode_get_uint8(args->dnode, NULL);
581 break;
582 }
583
584 return NB_OK;
585 }
586
587 static int
588 eigrpd_instance_metric_weights_K6_destroy(struct nb_cb_destroy_args *args)
589 {
590 struct eigrp *eigrp;
591
592 switch (args->event) {
593 case NB_EV_VALIDATE:
594 case NB_EV_PREPARE:
595 case NB_EV_ABORT:
596 /* NOTHING */
597 break;
598 case NB_EV_APPLY:
599 eigrp = nb_running_get_entry(args->dnode, NULL, true);
600 eigrp->k_values[5] = EIGRP_K6_DEFAULT;
601 break;
602 }
603
604 return NB_OK;
605 }
606
607 /*
608 * XPath: /frr-eigrpd:eigrpd/instance/network
609 */
610 static int eigrpd_instance_network_create(struct nb_cb_create_args *args)
611 {
612 struct route_node *rnode;
613 struct prefix prefix;
614 struct eigrp *eigrp;
615 int exists;
616
617 yang_dnode_get_ipv4p(&prefix, args->dnode, NULL);
618
619 switch (args->event) {
620 case NB_EV_VALIDATE:
621 eigrp = nb_running_get_entry(args->dnode, NULL, false);
622 /* If entry doesn't exist it means the list is empty. */
623 if (eigrp == NULL)
624 break;
625
626 rnode = route_node_get(eigrp->networks, &prefix);
627 exists = (rnode->info != NULL);
628 route_unlock_node(rnode);
629 if (exists)
630 return NB_ERR_INCONSISTENCY;
631 break;
632 case NB_EV_PREPARE:
633 case NB_EV_ABORT:
634 /* NOTHING */
635 break;
636 case NB_EV_APPLY:
637 eigrp = nb_running_get_entry(args->dnode, NULL, true);
638 if (eigrp_network_set(eigrp, &prefix) == 0)
639 return NB_ERR_INCONSISTENCY;
640 break;
641 }
642
643 return NB_OK;
644 }
645
646 static int eigrpd_instance_network_destroy(struct nb_cb_destroy_args *args)
647 {
648 struct route_node *rnode;
649 struct prefix prefix;
650 struct eigrp *eigrp;
651 int exists = 0;
652
653 yang_dnode_get_ipv4p(&prefix, args->dnode, NULL);
654
655 switch (args->event) {
656 case NB_EV_VALIDATE:
657 eigrp = nb_running_get_entry(args->dnode, NULL, false);
658 /* If entry doesn't exist it means the list is empty. */
659 if (eigrp == NULL)
660 break;
661
662 rnode = route_node_get(eigrp->networks, &prefix);
663 exists = (rnode->info != NULL);
664 route_unlock_node(rnode);
665 if (exists == 0)
666 return NB_ERR_INCONSISTENCY;
667 break;
668 case NB_EV_PREPARE:
669 case NB_EV_ABORT:
670 /* NOTHING */
671 break;
672 case NB_EV_APPLY:
673 eigrp = nb_running_get_entry(args->dnode, NULL, true);
674 eigrp_network_unset(eigrp, &prefix);
675 break;
676 }
677
678 return NB_OK;
679 }
680
681 /*
682 * XPath: /frr-eigrpd:eigrpd/instance/neighbor
683 */
684 static int eigrpd_instance_neighbor_create(struct nb_cb_create_args *args)
685 {
686 switch (args->event) {
687 case NB_EV_VALIDATE:
688 /* TODO: Not implemented. */
689 case NB_EV_PREPARE:
690 case NB_EV_ABORT:
691 return NB_OK;
692 case NB_EV_APPLY:
693 snprintf(args->errmsg, args->errmsg_len,
694 "neighbor Command is not implemented yet");
695 break;
696 }
697
698 return NB_OK;
699 }
700
701 static int eigrpd_instance_neighbor_destroy(struct nb_cb_destroy_args *args)
702 {
703 switch (args->event) {
704 case NB_EV_VALIDATE:
705 /* TODO: Not implemented. */
706 case NB_EV_PREPARE:
707 case NB_EV_ABORT:
708 return NB_OK;
709 case NB_EV_APPLY:
710 snprintf(args->errmsg, args->errmsg_len,
711 "no neighbor Command is not implemented yet");
712 break;
713 }
714
715 return NB_OK;
716 }
717
718 /*
719 * XPath: /frr-eigrpd:eigrpd/instance/redistribute
720 */
721 static int eigrpd_instance_redistribute_create(struct nb_cb_create_args *args)
722 {
723 struct eigrp_metrics metrics;
724 const char *vrfname;
725 struct eigrp *eigrp;
726 uint32_t proto;
727 vrf_id_t vrfid;
728 struct vrf *pVrf;
729
730 switch (args->event) {
731 case NB_EV_VALIDATE:
732 proto = yang_dnode_get_enum(args->dnode, "./protocol");
733 vrfname = yang_dnode_get_string(args->dnode, "../vrf");
734
735 pVrf = vrf_lookup_by_name(vrfname);
736 if (pVrf)
737 vrfid = pVrf->vrf_id;
738 else
739 vrfid = VRF_DEFAULT;
740
741 if (vrf_bitmap_check(zclient->redist[AFI_IP][proto], vrfid))
742 return NB_ERR_INCONSISTENCY;
743 break;
744 case NB_EV_PREPARE:
745 case NB_EV_ABORT:
746 /* NOTHING */
747 break;
748 case NB_EV_APPLY:
749 eigrp = nb_running_get_entry(args->dnode, NULL, true);
750 proto = yang_dnode_get_enum(args->dnode, "./protocol");
751 redistribute_get_metrics(args->dnode, &metrics);
752 eigrp_redistribute_set(eigrp, proto, metrics);
753 break;
754 }
755
756 return NB_OK;
757 }
758
759 static int eigrpd_instance_redistribute_destroy(struct nb_cb_destroy_args *args)
760 {
761 struct eigrp *eigrp;
762 uint32_t proto;
763
764 switch (args->event) {
765 case NB_EV_VALIDATE:
766 case NB_EV_PREPARE:
767 case NB_EV_ABORT:
768 /* NOTHING */
769 break;
770 case NB_EV_APPLY:
771 eigrp = nb_running_get_entry(args->dnode, NULL, true);
772 proto = yang_dnode_get_enum(args->dnode, "./protocol");
773 eigrp_redistribute_unset(eigrp, proto);
774 break;
775 }
776
777 return NB_OK;
778 }
779
780 /*
781 * XPath: /frr-eigrpd:eigrpd/instance/redistribute/route-map
782 */
783 static int
784 eigrpd_instance_redistribute_route_map_modify(struct nb_cb_modify_args *args)
785 {
786 switch (args->event) {
787 case NB_EV_VALIDATE:
788 /* TODO: Not implemented. */
789 case NB_EV_PREPARE:
790 case NB_EV_ABORT:
791 return NB_OK;
792 case NB_EV_APPLY:
793 snprintf(
794 args->errmsg, args->errmsg_len,
795 "'redistribute X route-map FOO' command not implemented yet");
796 break;
797 }
798
799 return NB_OK;
800 }
801
802 static int
803 eigrpd_instance_redistribute_route_map_destroy(struct nb_cb_destroy_args *args)
804 {
805 switch (args->event) {
806 case NB_EV_VALIDATE:
807 /* TODO: Not implemented. */
808 case NB_EV_PREPARE:
809 case NB_EV_ABORT:
810 return NB_OK;
811 case NB_EV_APPLY:
812 snprintf(
813 args->errmsg, args->errmsg_len,
814 "'no redistribute X route-map FOO' command not implemented yet");
815 break;
816 }
817
818 return NB_OK;
819 }
820
821 /*
822 * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/bandwidth
823 */
824 static int eigrpd_instance_redistribute_metrics_bandwidth_modify(
825 struct nb_cb_modify_args *args)
826 {
827 struct eigrp_metrics metrics;
828 struct eigrp *eigrp;
829 uint32_t proto;
830
831 switch (args->event) {
832 case NB_EV_VALIDATE:
833 case NB_EV_PREPARE:
834 case NB_EV_ABORT:
835 /* NOTHING */
836 break;
837 case NB_EV_APPLY:
838 eigrp = nb_running_get_entry(args->dnode, NULL, true);
839 proto = yang_dnode_get_enum(args->dnode, "../../protocol");
840 redistribute_get_metrics(args->dnode, &metrics);
841 eigrp_redistribute_set(eigrp, proto, metrics);
842 break;
843 }
844
845 return NB_OK;
846 }
847
848 static int eigrpd_instance_redistribute_metrics_bandwidth_destroy(
849 struct nb_cb_destroy_args *args)
850 {
851 struct eigrp_metrics metrics;
852 struct eigrp *eigrp;
853 uint32_t proto;
854
855 switch (args->event) {
856 case NB_EV_VALIDATE:
857 case NB_EV_PREPARE:
858 case NB_EV_ABORT:
859 /* NOTHING */
860 break;
861 case NB_EV_APPLY:
862 eigrp = nb_running_get_entry(args->dnode, NULL, true);
863 proto = yang_dnode_get_enum(args->dnode, "../../protocol");
864 redistribute_get_metrics(args->dnode, &metrics);
865 eigrp_redistribute_set(eigrp, proto, metrics);
866 break;
867 }
868
869 return NB_OK;
870 }
871
872 /*
873 * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/delay
874 */
875 static int eigrpd_instance_redistribute_metrics_delay_modify(
876 struct nb_cb_modify_args *args)
877 {
878 return eigrpd_instance_redistribute_metrics_bandwidth_modify(args);
879 }
880
881 static int eigrpd_instance_redistribute_metrics_delay_destroy(
882 struct nb_cb_destroy_args *args)
883 {
884 return eigrpd_instance_redistribute_metrics_bandwidth_destroy(args);
885 }
886
887 /*
888 * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/reliability
889 */
890 static int eigrpd_instance_redistribute_metrics_reliability_modify(
891 struct nb_cb_modify_args *args)
892 {
893 return eigrpd_instance_redistribute_metrics_bandwidth_modify(args);
894 }
895
896 static int eigrpd_instance_redistribute_metrics_reliability_destroy(
897 struct nb_cb_destroy_args *args)
898 {
899 return eigrpd_instance_redistribute_metrics_bandwidth_destroy(args);
900 }
901
902 /*
903 * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/load
904 */
905 static int
906 eigrpd_instance_redistribute_metrics_load_modify(struct nb_cb_modify_args *args)
907 {
908 return eigrpd_instance_redistribute_metrics_bandwidth_modify(args);
909 }
910
911 static int eigrpd_instance_redistribute_metrics_load_destroy(
912 struct nb_cb_destroy_args *args)
913 {
914 return eigrpd_instance_redistribute_metrics_bandwidth_destroy(args);
915 }
916
917 /*
918 * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/mtu
919 */
920 static int
921 eigrpd_instance_redistribute_metrics_mtu_modify(struct nb_cb_modify_args *args)
922 {
923 return eigrpd_instance_redistribute_metrics_bandwidth_modify(args);
924 }
925
926 static int eigrpd_instance_redistribute_metrics_mtu_destroy(
927 struct nb_cb_destroy_args *args)
928 {
929 return eigrpd_instance_redistribute_metrics_bandwidth_destroy(args);
930 }
931
932 /*
933 * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/delay
934 */
935 static int lib_interface_eigrp_delay_modify(struct nb_cb_modify_args *args)
936 {
937 struct eigrp_interface *ei;
938 struct interface *ifp;
939
940 switch (args->event) {
941 case NB_EV_VALIDATE:
942 ifp = nb_running_get_entry(args->dnode, NULL, false);
943 if (ifp == NULL) {
944 /*
945 * XXX: we can't verify if the interface exists
946 * and is active until EIGRP is up.
947 */
948 break;
949 }
950
951 ei = ifp->info;
952 if (ei == NULL)
953 return NB_ERR_INCONSISTENCY;
954 break;
955 case NB_EV_PREPARE:
956 case NB_EV_ABORT:
957 /* NOTHING */
958 break;
959 case NB_EV_APPLY:
960 ifp = nb_running_get_entry(args->dnode, NULL, true);
961 ei = ifp->info;
962 if (ei == NULL)
963 return NB_ERR_INCONSISTENCY;
964
965 ei->params.delay = yang_dnode_get_uint32(args->dnode, NULL);
966 eigrp_if_reset(ifp);
967 break;
968 }
969
970 return NB_OK;
971 }
972
973 /*
974 * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/bandwidth
975 */
976 static int lib_interface_eigrp_bandwidth_modify(struct nb_cb_modify_args *args)
977 {
978 struct interface *ifp;
979 struct eigrp_interface *ei;
980
981 switch (args->event) {
982 case NB_EV_VALIDATE:
983 ifp = nb_running_get_entry(args->dnode, NULL, false);
984 if (ifp == NULL) {
985 /*
986 * XXX: we can't verify if the interface exists
987 * and is active until EIGRP is up.
988 */
989 break;
990 }
991
992 ei = ifp->info;
993 if (ei == NULL)
994 return NB_ERR_INCONSISTENCY;
995 break;
996 case NB_EV_PREPARE:
997 case NB_EV_ABORT:
998 /* NOTHING */
999 break;
1000 case NB_EV_APPLY:
1001 ifp = nb_running_get_entry(args->dnode, NULL, true);
1002 ei = ifp->info;
1003 if (ei == NULL)
1004 return NB_ERR_INCONSISTENCY;
1005
1006 ei->params.bandwidth = yang_dnode_get_uint32(args->dnode, NULL);
1007 eigrp_if_reset(ifp);
1008 break;
1009 }
1010
1011 return NB_OK;
1012 }
1013
1014 /*
1015 * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/hello-interval
1016 */
1017 static int
1018 lib_interface_eigrp_hello_interval_modify(struct nb_cb_modify_args *args)
1019 {
1020 struct interface *ifp;
1021 struct eigrp_interface *ei;
1022
1023 switch (args->event) {
1024 case NB_EV_VALIDATE:
1025 ifp = nb_running_get_entry(args->dnode, NULL, false);
1026 if (ifp == NULL) {
1027 /*
1028 * XXX: we can't verify if the interface exists
1029 * and is active until EIGRP is up.
1030 */
1031 break;
1032 }
1033
1034 ei = ifp->info;
1035 if (ei == NULL)
1036 return NB_ERR_INCONSISTENCY;
1037 break;
1038 case NB_EV_PREPARE:
1039 case NB_EV_ABORT:
1040 /* NOTHING */
1041 break;
1042 case NB_EV_APPLY:
1043 ifp = nb_running_get_entry(args->dnode, NULL, true);
1044 ei = ifp->info;
1045 if (ei == NULL)
1046 return NB_ERR_INCONSISTENCY;
1047
1048 ei->params.v_hello = yang_dnode_get_uint16(args->dnode, NULL);
1049 break;
1050 }
1051
1052 return NB_OK;
1053 }
1054
1055 /*
1056 * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/hold-time
1057 */
1058 static int lib_interface_eigrp_hold_time_modify(struct nb_cb_modify_args *args)
1059 {
1060 struct interface *ifp;
1061 struct eigrp_interface *ei;
1062
1063 switch (args->event) {
1064 case NB_EV_VALIDATE:
1065 ifp = nb_running_get_entry(args->dnode, NULL, false);
1066 if (ifp == NULL) {
1067 /*
1068 * XXX: we can't verify if the interface exists
1069 * and is active until EIGRP is up.
1070 */
1071 break;
1072 }
1073
1074 ei = ifp->info;
1075 if (ei == NULL)
1076 return NB_ERR_INCONSISTENCY;
1077 break;
1078 case NB_EV_PREPARE:
1079 case NB_EV_ABORT:
1080 /* NOTHING */
1081 break;
1082 case NB_EV_APPLY:
1083 ifp = nb_running_get_entry(args->dnode, NULL, true);
1084 ei = ifp->info;
1085 if (ei == NULL)
1086 return NB_ERR_INCONSISTENCY;
1087
1088 ei->params.v_wait = yang_dnode_get_uint16(args->dnode, NULL);
1089 break;
1090 }
1091
1092 return NB_OK;
1093 }
1094
1095 /*
1096 * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/split-horizon
1097 */
1098 static int
1099 lib_interface_eigrp_split_horizon_modify(struct nb_cb_modify_args *args)
1100 {
1101 switch (args->event) {
1102 case NB_EV_VALIDATE:
1103 /* TODO: Not implemented. */
1104 case NB_EV_PREPARE:
1105 case NB_EV_ABORT:
1106 return NB_OK;
1107 case NB_EV_APPLY:
1108 snprintf(args->errmsg, args->errmsg_len,
1109 "split-horizon command not implemented yet");
1110 /* NOTHING */
1111 break;
1112 }
1113
1114 return NB_OK;
1115 }
1116
1117 /*
1118 * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance
1119 */
1120 static int lib_interface_eigrp_instance_create(struct nb_cb_create_args *args)
1121 {
1122 struct eigrp_interface *eif;
1123 struct interface *ifp;
1124 struct eigrp *eigrp;
1125
1126 switch (args->event) {
1127 case NB_EV_VALIDATE:
1128 ifp = nb_running_get_entry(args->dnode, NULL, false);
1129 if (ifp == NULL) {
1130 /*
1131 * XXX: we can't verify if the interface exists
1132 * and is active until EIGRP is up.
1133 */
1134 break;
1135 }
1136
1137 eigrp = eigrp_get(yang_dnode_get_uint16(args->dnode, "./asn"),
1138 ifp->vrf->vrf_id);
1139 eif = eigrp_interface_lookup(eigrp, ifp->name);
1140 if (eif == NULL)
1141 return NB_ERR_INCONSISTENCY;
1142 break;
1143 case NB_EV_PREPARE:
1144 case NB_EV_ABORT:
1145 /* NOTHING */
1146 break;
1147 case NB_EV_APPLY:
1148 ifp = nb_running_get_entry(args->dnode, NULL, true);
1149 eigrp = eigrp_get(yang_dnode_get_uint16(args->dnode, "./asn"),
1150 ifp->vrf->vrf_id);
1151 eif = eigrp_interface_lookup(eigrp, ifp->name);
1152 if (eif == NULL)
1153 return NB_ERR_INCONSISTENCY;
1154
1155 nb_running_set_entry(args->dnode, eif);
1156 break;
1157 }
1158
1159 return NB_OK;
1160 }
1161
1162 static int lib_interface_eigrp_instance_destroy(struct nb_cb_destroy_args *args)
1163 {
1164 switch (args->event) {
1165 case NB_EV_VALIDATE:
1166 case NB_EV_PREPARE:
1167 case NB_EV_ABORT:
1168 /* NOTHING */
1169 break;
1170 case NB_EV_APPLY:
1171 nb_running_unset_entry(args->dnode);
1172 break;
1173 }
1174
1175 return NB_OK;
1176 }
1177
1178 /*
1179 * XPath:
1180 * /frr-interface:lib/interface/frr-eigrpd:eigrp/instance/summarize-addresses
1181 */
1182 static int lib_interface_eigrp_instance_summarize_addresses_create(
1183 struct nb_cb_create_args *args)
1184 {
1185 switch (args->event) {
1186 case NB_EV_VALIDATE:
1187 /* TODO: Not implemented. */
1188 case NB_EV_PREPARE:
1189 case NB_EV_ABORT:
1190 return NB_OK;
1191 case NB_EV_APPLY:
1192 snprintf(args->errmsg, args->errmsg_len,
1193 "summary command not implemented yet");
1194 break;
1195 }
1196
1197 return NB_OK;
1198 }
1199
1200 static int lib_interface_eigrp_instance_summarize_addresses_destroy(
1201 struct nb_cb_destroy_args *args)
1202 {
1203 switch (args->event) {
1204 case NB_EV_VALIDATE:
1205 /* TODO: Not implemented. */
1206 case NB_EV_PREPARE:
1207 case NB_EV_ABORT:
1208 return NB_OK;
1209 case NB_EV_APPLY:
1210 snprintf(args->errmsg, args->errmsg_len,
1211 "no summary command not implemented yet");
1212 /* NOTHING */
1213 break;
1214 }
1215
1216 return NB_OK;
1217 }
1218
1219 /*
1220 * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance/authentication
1221 */
1222 static int lib_interface_eigrp_instance_authentication_modify(
1223 struct nb_cb_modify_args *args)
1224 {
1225 struct eigrp_interface *eif;
1226
1227 switch (args->event) {
1228 case NB_EV_VALIDATE:
1229 case NB_EV_PREPARE:
1230 case NB_EV_ABORT:
1231 /* NOTHING */
1232 break;
1233 case NB_EV_APPLY:
1234 eif = nb_running_get_entry(args->dnode, NULL, true);
1235 eif->params.auth_type = yang_dnode_get_enum(args->dnode, NULL);
1236 break;
1237 }
1238
1239 return NB_OK;
1240 }
1241
1242 /*
1243 * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance/keychain
1244 */
1245 static int
1246 lib_interface_eigrp_instance_keychain_modify(struct nb_cb_modify_args *args)
1247 {
1248 struct eigrp_interface *eif;
1249 struct keychain *keychain;
1250
1251 switch (args->event) {
1252 case NB_EV_VALIDATE:
1253 keychain = keychain_lookup(
1254 yang_dnode_get_string(args->dnode, NULL));
1255 if (keychain == NULL)
1256 return NB_ERR_INCONSISTENCY;
1257 break;
1258 case NB_EV_PREPARE:
1259 args->resource->ptr =
1260 strdup(yang_dnode_get_string(args->dnode, NULL));
1261 if (args->resource->ptr == NULL)
1262 return NB_ERR_RESOURCE;
1263 break;
1264 case NB_EV_ABORT:
1265 free(args->resource->ptr);
1266 args->resource->ptr = NULL;
1267 break;
1268 case NB_EV_APPLY:
1269 eif = nb_running_get_entry(args->dnode, NULL, true);
1270 if (eif->params.auth_keychain)
1271 free(eif->params.auth_keychain);
1272
1273 eif->params.auth_keychain = args->resource->ptr;
1274 break;
1275 }
1276
1277 return NB_OK;
1278 }
1279
1280 static int
1281 lib_interface_eigrp_instance_keychain_destroy(struct nb_cb_destroy_args *args)
1282 {
1283 struct eigrp_interface *eif;
1284
1285 switch (args->event) {
1286 case NB_EV_VALIDATE:
1287 case NB_EV_PREPARE:
1288 case NB_EV_ABORT:
1289 /* NOTHING */
1290 break;
1291 case NB_EV_APPLY:
1292 eif = nb_running_get_entry(args->dnode, NULL, true);
1293 if (eif->params.auth_keychain)
1294 free(eif->params.auth_keychain);
1295
1296 eif->params.auth_keychain = NULL;
1297 break;
1298 }
1299
1300 return NB_OK;
1301 }
1302
1303 /* clang-format off */
1304 const struct frr_yang_module_info frr_eigrpd_info = {
1305 .name = "frr-eigrpd",
1306 .nodes = {
1307 {
1308 .xpath = "/frr-eigrpd:eigrpd/instance",
1309 .cbs = {
1310 .create = eigrpd_instance_create,
1311 .destroy = eigrpd_instance_destroy,
1312 .cli_show = eigrp_cli_show_header,
1313 .cli_show_end = eigrp_cli_show_end_header,
1314 }
1315 },
1316 {
1317 .xpath = "/frr-eigrpd:eigrpd/instance/router-id",
1318 .cbs = {
1319 .modify = eigrpd_instance_router_id_modify,
1320 .destroy = eigrpd_instance_router_id_destroy,
1321 .cli_show = eigrp_cli_show_router_id,
1322 }
1323 },
1324 {
1325 .xpath = "/frr-eigrpd:eigrpd/instance/passive-interface",
1326 .cbs = {
1327 .create = eigrpd_instance_passive_interface_create,
1328 .destroy = eigrpd_instance_passive_interface_destroy,
1329 .cli_show = eigrp_cli_show_passive_interface,
1330 }
1331 },
1332 {
1333 .xpath = "/frr-eigrpd:eigrpd/instance/active-time",
1334 .cbs = {
1335 .modify = eigrpd_instance_active_time_modify,
1336 .cli_show = eigrp_cli_show_active_time,
1337 }
1338 },
1339 {
1340 .xpath = "/frr-eigrpd:eigrpd/instance/variance",
1341 .cbs = {
1342 .modify = eigrpd_instance_variance_modify,
1343 .destroy = eigrpd_instance_variance_destroy,
1344 .cli_show = eigrp_cli_show_variance,
1345 }
1346 },
1347 {
1348 .xpath = "/frr-eigrpd:eigrpd/instance/maximum-paths",
1349 .cbs = {
1350 .modify = eigrpd_instance_maximum_paths_modify,
1351 .destroy = eigrpd_instance_maximum_paths_destroy,
1352 .cli_show = eigrp_cli_show_maximum_paths,
1353 }
1354 },
1355 {
1356 .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights",
1357 .cbs = {
1358 .cli_show = eigrp_cli_show_metrics,
1359 }
1360 },
1361 {
1362 .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K1",
1363 .cbs = {
1364 .modify = eigrpd_instance_metric_weights_K1_modify,
1365 .destroy = eigrpd_instance_metric_weights_K1_destroy,
1366 }
1367 },
1368 {
1369 .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K2",
1370 .cbs = {
1371 .modify = eigrpd_instance_metric_weights_K2_modify,
1372 .destroy = eigrpd_instance_metric_weights_K2_destroy,
1373 }
1374 },
1375 {
1376 .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K3",
1377 .cbs = {
1378 .modify = eigrpd_instance_metric_weights_K3_modify,
1379 .destroy = eigrpd_instance_metric_weights_K3_destroy,
1380 }
1381 },
1382 {
1383 .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K4",
1384 .cbs = {
1385 .modify = eigrpd_instance_metric_weights_K4_modify,
1386 .destroy = eigrpd_instance_metric_weights_K4_destroy,
1387 }
1388 },
1389 {
1390 .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K5",
1391 .cbs = {
1392 .modify = eigrpd_instance_metric_weights_K5_modify,
1393 .destroy = eigrpd_instance_metric_weights_K5_destroy,
1394 }
1395 },
1396 {
1397 .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K6",
1398 .cbs = {
1399 .modify = eigrpd_instance_metric_weights_K6_modify,
1400 .destroy = eigrpd_instance_metric_weights_K6_destroy,
1401 }
1402 },
1403 {
1404 .xpath = "/frr-eigrpd:eigrpd/instance/network",
1405 .cbs = {
1406 .create = eigrpd_instance_network_create,
1407 .destroy = eigrpd_instance_network_destroy,
1408 .cli_show = eigrp_cli_show_network,
1409 }
1410 },
1411 {
1412 .xpath = "/frr-eigrpd:eigrpd/instance/neighbor",
1413 .cbs = {
1414 .create = eigrpd_instance_neighbor_create,
1415 .destroy = eigrpd_instance_neighbor_destroy,
1416 .cli_show = eigrp_cli_show_neighbor,
1417 }
1418 },
1419 {
1420 .xpath = "/frr-eigrpd:eigrpd/instance/redistribute",
1421 .cbs = {
1422 .create = eigrpd_instance_redistribute_create,
1423 .destroy = eigrpd_instance_redistribute_destroy,
1424 .cli_show = eigrp_cli_show_redistribute,
1425 }
1426 },
1427 {
1428 .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/route-map",
1429 .cbs = {
1430 .modify = eigrpd_instance_redistribute_route_map_modify,
1431 .destroy = eigrpd_instance_redistribute_route_map_destroy,
1432 }
1433 },
1434 {
1435 .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/metrics/bandwidth",
1436 .cbs = {
1437 .modify = eigrpd_instance_redistribute_metrics_bandwidth_modify,
1438 .destroy = eigrpd_instance_redistribute_metrics_bandwidth_destroy,
1439 }
1440 },
1441 {
1442 .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/metrics/delay",
1443 .cbs = {
1444 .modify = eigrpd_instance_redistribute_metrics_delay_modify,
1445 .destroy = eigrpd_instance_redistribute_metrics_delay_destroy,
1446 }
1447 },
1448 {
1449 .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/metrics/reliability",
1450 .cbs = {
1451 .modify = eigrpd_instance_redistribute_metrics_reliability_modify,
1452 .destroy = eigrpd_instance_redistribute_metrics_reliability_destroy,
1453 }
1454 },
1455 {
1456 .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/metrics/load",
1457 .cbs = {
1458 .modify = eigrpd_instance_redistribute_metrics_load_modify,
1459 .destroy = eigrpd_instance_redistribute_metrics_load_destroy,
1460 }
1461 },
1462 {
1463 .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/metrics/mtu",
1464 .cbs = {
1465 .modify = eigrpd_instance_redistribute_metrics_mtu_modify,
1466 .destroy = eigrpd_instance_redistribute_metrics_mtu_destroy,
1467 }
1468 },
1469 {
1470 .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/delay",
1471 .cbs = {
1472 .modify = lib_interface_eigrp_delay_modify,
1473 .cli_show = eigrp_cli_show_delay,
1474 }
1475 },
1476 {
1477 .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/bandwidth",
1478 .cbs = {
1479 .modify = lib_interface_eigrp_bandwidth_modify,
1480 .cli_show = eigrp_cli_show_bandwidth,
1481 }
1482 },
1483 {
1484 .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/hello-interval",
1485 .cbs = {
1486 .modify = lib_interface_eigrp_hello_interval_modify,
1487 .cli_show = eigrp_cli_show_hello_interval,
1488 }
1489 },
1490 {
1491 .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/hold-time",
1492 .cbs = {
1493 .modify = lib_interface_eigrp_hold_time_modify,
1494 .cli_show = eigrp_cli_show_hold_time,
1495 }
1496 },
1497 {
1498 .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/split-horizon",
1499 .cbs = {
1500 .modify = lib_interface_eigrp_split_horizon_modify,
1501 }
1502 },
1503 {
1504 .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/instance",
1505 .cbs = {
1506 .create = lib_interface_eigrp_instance_create,
1507 .destroy = lib_interface_eigrp_instance_destroy,
1508 }
1509 },
1510 {
1511 .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/instance/summarize-addresses",
1512 .cbs = {
1513 .create = lib_interface_eigrp_instance_summarize_addresses_create,
1514 .destroy = lib_interface_eigrp_instance_summarize_addresses_destroy,
1515 .cli_show = eigrp_cli_show_summarize_address,
1516 }
1517 },
1518 {
1519 .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/instance/authentication",
1520 .cbs = {
1521 .modify = lib_interface_eigrp_instance_authentication_modify,
1522 .cli_show = eigrp_cli_show_authentication,
1523 }
1524 },
1525 {
1526 .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/instance/keychain",
1527 .cbs = {
1528 .modify = lib_interface_eigrp_instance_keychain_modify,
1529 .destroy = lib_interface_eigrp_instance_keychain_destroy,
1530 .cli_show = eigrp_cli_show_keychain,
1531 }
1532 },
1533 {
1534 .xpath = NULL,
1535 },
1536 }
1537 };