2 * Copyright (C) 2003 Yasuhiro Ohara
4 * This file is part of GNU Zebra.
6 * GNU Zebra is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License as published by the
8 * Free Software Foundation; either version 2, or (at your option) any
11 * GNU Zebra is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with GNU Zebra; see the file COPYING. If not, write to the
18 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
19 * Boston, MA 02111-1307, USA.
33 #include "ospf6_lsa.h"
34 #include "ospf6_lsdb.h"
35 #include "ospf6_network.h"
36 #include "ospf6_message.h"
37 #include "ospf6_route.h"
38 #include "ospf6_top.h"
39 #include "ospf6_area.h"
40 #include "ospf6_interface.h"
41 #include "ospf6_neighbor.h"
42 #include "ospf6_intra.h"
43 #include "ospf6_spf.h"
44 #include "ospf6_snmp.h"
46 #include "ospf6_bfd.h"
48 DEFINE_MTYPE_STATIC(OSPF6D
, CFG_PLIST_NAME
, "configured prefix list names")
50 unsigned char conf_debug_ospf6_interface
= 0;
52 const char *ospf6_interface_state_str
[] =
65 struct ospf6_interface
*
66 ospf6_interface_lookup_by_ifindex (ifindex_t ifindex
)
68 struct ospf6_interface
*oi
;
69 struct interface
*ifp
;
71 ifp
= if_lookup_by_index (ifindex
);
73 return (struct ospf6_interface
*) NULL
;
75 oi
= (struct ospf6_interface
*) ifp
->info
;
79 /* schedule routing table recalculation */
81 ospf6_interface_lsdb_hook (struct ospf6_lsa
*lsa
, unsigned int reason
)
83 struct ospf6_interface
*oi
;
89 switch (ntohs (lsa
->header
->type
))
91 case OSPF6_LSTYPE_LINK
:
92 if (oi
->state
== OSPF6_INTERFACE_DR
)
93 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_TRANSIT (oi
);
95 ospf6_spf_schedule (oi
->area
->ospf6
, reason
);
104 ospf6_interface_lsdb_hook_add (struct ospf6_lsa
*lsa
)
106 ospf6_interface_lsdb_hook(lsa
, ospf6_lsadd_to_spf_reason(lsa
));
110 ospf6_interface_lsdb_hook_remove (struct ospf6_lsa
*lsa
)
112 ospf6_interface_lsdb_hook(lsa
, ospf6_lsremove_to_spf_reason(lsa
));
116 ospf6_default_iftype(struct interface
*ifp
)
118 if (if_is_pointopoint (ifp
))
119 return OSPF_IFTYPE_POINTOPOINT
;
120 else if (if_is_loopback (ifp
))
121 return OSPF_IFTYPE_LOOPBACK
;
123 return OSPF_IFTYPE_BROADCAST
;
127 ospf6_interface_get_cost (struct ospf6_interface
*oi
)
129 /* If all else fails, use default OSPF cost */
133 bw
= oi
->interface
->bandwidth
? oi
->interface
->bandwidth
: OSPF6_INTERFACE_BANDWIDTH
;
134 refbw
= ospf6
? ospf6
->ref_bandwidth
: OSPF6_REFERENCE_BANDWIDTH
;
136 /* A specifed ip ospf cost overrides a calculated one. */
137 if (CHECK_FLAG (oi
->flag
, OSPF6_INTERFACE_NOAUTOCOST
))
141 cost
= (u_int32_t
) ((double)refbw
/ (double)bw
+ (double)0.5);
142 if (cost
< 1) cost
= 1;
143 else if (cost
> UINT32_MAX
) cost
= UINT32_MAX
;
150 ospf6_interface_recalculate_cost (struct ospf6_interface
*oi
)
154 newcost
= ospf6_interface_get_cost (oi
);
155 if (newcost
== oi
->cost
) return;
158 /* update cost held in route_connected list in ospf6_interface */
159 ospf6_interface_connected_route_update (oi
->interface
);
161 /* execute LSA hooks */
164 OSPF6_LINK_LSA_SCHEDULE (oi
);
165 OSPF6_ROUTER_LSA_SCHEDULE (oi
->area
);
166 OSPF6_NETWORK_LSA_SCHEDULE (oi
);
167 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_TRANSIT (oi
);
168 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_STUB (oi
->area
);
172 /* Create new ospf6 interface structure */
173 struct ospf6_interface
*
174 ospf6_interface_create (struct interface
*ifp
)
176 struct ospf6_interface
*oi
;
177 unsigned int iobuflen
;
179 oi
= (struct ospf6_interface
*)
180 XCALLOC (MTYPE_OSPF6_IF
, sizeof (struct ospf6_interface
));
184 zlog_err ("Can't malloc ospf6_interface for ifindex %d", ifp
->ifindex
);
185 return (struct ospf6_interface
*) NULL
;
188 oi
->area
= (struct ospf6_area
*) NULL
;
189 oi
->neighbor_list
= list_new ();
190 oi
->neighbor_list
->cmp
= ospf6_neighbor_cmp
;
191 oi
->linklocal_addr
= (struct in6_addr
*) NULL
;
192 oi
->instance_id
= OSPF6_INTERFACE_INSTANCE_ID
;
193 oi
->transdelay
= OSPF6_INTERFACE_TRANSDELAY
;
194 oi
->priority
= OSPF6_INTERFACE_PRIORITY
;
196 oi
->hello_interval
= OSPF_HELLO_INTERVAL_DEFAULT
;
197 oi
->dead_interval
= OSPF_ROUTER_DEAD_INTERVAL_DEFAULT
;
198 oi
->rxmt_interval
= OSPF_RETRANSMIT_INTERVAL_DEFAULT
;
199 oi
->type
= ospf6_default_iftype (ifp
);
200 oi
->state
= OSPF6_INTERFACE_DOWN
;
204 /* Try to adjust I/O buffer size with IfMtu */
205 oi
->ifmtu
= ifp
->mtu6
;
206 iobuflen
= ospf6_iobuf_size (ifp
->mtu6
);
207 if (oi
->ifmtu
> iobuflen
)
209 if (IS_OSPF6_DEBUG_INTERFACE
)
210 zlog_debug ("Interface %s: IfMtu is adjusted to I/O buffer size: %d.",
211 ifp
->name
, iobuflen
);
212 oi
->ifmtu
= iobuflen
;
215 oi
->lsupdate_list
= ospf6_lsdb_create (oi
);
216 oi
->lsack_list
= ospf6_lsdb_create (oi
);
217 oi
->lsdb
= ospf6_lsdb_create (oi
);
218 oi
->lsdb
->hook_add
= ospf6_interface_lsdb_hook_add
;
219 oi
->lsdb
->hook_remove
= ospf6_interface_lsdb_hook_remove
;
220 oi
->lsdb_self
= ospf6_lsdb_create (oi
);
222 oi
->route_connected
= OSPF6_ROUTE_TABLE_CREATE (INTERFACE
, CONNECTED_ROUTES
);
223 oi
->route_connected
->scope
= oi
;
230 oi
->cost
= ospf6_interface_get_cost(oi
);
236 ospf6_interface_delete (struct ospf6_interface
*oi
)
238 struct listnode
*node
, *nnode
;
239 struct ospf6_neighbor
*on
;
241 for (ALL_LIST_ELEMENTS (oi
->neighbor_list
, node
, nnode
, on
))
242 ospf6_neighbor_delete (on
);
244 list_delete (oi
->neighbor_list
);
246 THREAD_OFF (oi
->thread_send_hello
);
247 THREAD_OFF (oi
->thread_send_lsupdate
);
248 THREAD_OFF (oi
->thread_send_lsack
);
250 ospf6_lsdb_remove_all (oi
->lsdb
);
251 ospf6_lsdb_remove_all (oi
->lsupdate_list
);
252 ospf6_lsdb_remove_all (oi
->lsack_list
);
254 ospf6_lsdb_delete (oi
->lsdb
);
255 ospf6_lsdb_delete (oi
->lsdb_self
);
257 ospf6_lsdb_delete (oi
->lsupdate_list
);
258 ospf6_lsdb_delete (oi
->lsack_list
);
260 ospf6_route_table_delete (oi
->route_connected
);
263 oi
->interface
->info
= NULL
;
267 XFREE (MTYPE_CFG_PLIST_NAME
, oi
->plist_name
);
269 ospf6_bfd_info_free(&(oi
->bfd_info
));
271 XFREE (MTYPE_OSPF6_IF
, oi
);
275 ospf6_interface_enable (struct ospf6_interface
*oi
)
277 UNSET_FLAG (oi
->flag
, OSPF6_INTERFACE_DISABLE
);
278 ospf6_interface_state_update (oi
->interface
);
282 ospf6_interface_disable (struct ospf6_interface
*oi
)
284 SET_FLAG (oi
->flag
, OSPF6_INTERFACE_DISABLE
);
286 thread_execute (master
, interface_down
, oi
, 0);
288 ospf6_lsdb_remove_all (oi
->lsdb
);
289 ospf6_lsdb_remove_all (oi
->lsdb_self
);
290 ospf6_lsdb_remove_all (oi
->lsupdate_list
);
291 ospf6_lsdb_remove_all (oi
->lsack_list
);
293 THREAD_OFF (oi
->thread_send_hello
);
294 THREAD_OFF (oi
->thread_send_lsupdate
);
295 THREAD_OFF (oi
->thread_send_lsack
);
297 THREAD_OFF (oi
->thread_network_lsa
);
298 THREAD_OFF (oi
->thread_link_lsa
);
299 THREAD_OFF (oi
->thread_intra_prefix_lsa
);
302 static struct in6_addr
*
303 ospf6_interface_get_linklocal_address (struct interface
*ifp
)
307 struct in6_addr
*l
= (struct in6_addr
*) NULL
;
309 /* for each connected address */
310 for (ALL_LIST_ELEMENTS_RO (ifp
->connected
, n
, c
))
312 /* if family not AF_INET6, ignore */
313 if (c
->address
->family
!= AF_INET6
)
316 /* linklocal scope check */
317 if (IN6_IS_ADDR_LINKLOCAL (&c
->address
->u
.prefix6
))
318 l
= &c
->address
->u
.prefix6
;
324 ospf6_interface_if_add (struct interface
*ifp
)
326 struct ospf6_interface
*oi
;
327 unsigned int iobuflen
;
329 oi
= (struct ospf6_interface
*) ifp
->info
;
333 /* Try to adjust I/O buffer size with IfMtu */
335 oi
->ifmtu
= ifp
->mtu6
;
336 iobuflen
= ospf6_iobuf_size (ifp
->mtu6
);
337 if (oi
->ifmtu
> iobuflen
)
339 if (IS_OSPF6_DEBUG_INTERFACE
)
340 zlog_debug ("Interface %s: IfMtu is adjusted to I/O buffer size: %d.",
341 ifp
->name
, iobuflen
);
342 oi
->ifmtu
= iobuflen
;
345 /* interface start */
346 ospf6_interface_state_update(oi
->interface
);
350 ospf6_interface_if_del (struct interface
*ifp
)
352 struct ospf6_interface
*oi
;
354 oi
= (struct ospf6_interface
*) ifp
->info
;
360 thread_execute (master
, interface_down
, oi
, 0);
362 listnode_delete (oi
->area
->if_list
, oi
);
363 oi
->area
= (struct ospf6_area
*) NULL
;
366 oi
->interface
= NULL
;
369 ospf6_interface_delete (oi
);
373 ospf6_interface_state_update (struct interface
*ifp
)
375 struct ospf6_interface
*oi
;
377 oi
= (struct ospf6_interface
*) ifp
->info
;
380 if (oi
->area
== NULL
)
382 if (CHECK_FLAG (oi
->flag
, OSPF6_INTERFACE_DISABLE
))
385 if (if_is_operative (ifp
)
386 && (ospf6_interface_get_linklocal_address(oi
->interface
)
387 || if_is_loopback(oi
->interface
)))
388 thread_add_event (master
, interface_up
, oi
, 0);
390 thread_add_event (master
, interface_down
, oi
, 0);
396 ospf6_interface_connected_route_update (struct interface
*ifp
)
398 struct ospf6_interface
*oi
;
399 struct ospf6_route
*route
;
401 struct listnode
*node
, *nnode
;
402 struct in6_addr nh_addr
;
404 oi
= (struct ospf6_interface
*) ifp
->info
;
408 /* reset linklocal pointer */
409 oi
->linklocal_addr
= ospf6_interface_get_linklocal_address (ifp
);
411 /* if area is null, do not make connected-route list */
412 if (oi
->area
== NULL
)
415 if (CHECK_FLAG (oi
->flag
, OSPF6_INTERFACE_DISABLE
))
418 /* update "route to advertise" interface route table */
419 ospf6_route_remove_all (oi
->route_connected
);
421 for (ALL_LIST_ELEMENTS (oi
->interface
->connected
, node
, nnode
, c
))
423 if (c
->address
->family
!= AF_INET6
)
426 CONTINUE_IF_ADDRESS_LINKLOCAL (IS_OSPF6_DEBUG_INTERFACE
, c
->address
);
427 CONTINUE_IF_ADDRESS_UNSPECIFIED (IS_OSPF6_DEBUG_INTERFACE
, c
->address
);
428 CONTINUE_IF_ADDRESS_LOOPBACK (IS_OSPF6_DEBUG_INTERFACE
, c
->address
);
429 CONTINUE_IF_ADDRESS_V4COMPAT (IS_OSPF6_DEBUG_INTERFACE
, c
->address
);
430 CONTINUE_IF_ADDRESS_V4MAPPED (IS_OSPF6_DEBUG_INTERFACE
, c
->address
);
435 struct prefix_list
*plist
;
436 enum prefix_list_type ret
;
437 char buf
[PREFIX2STR_BUFFER
];
439 prefix2str (c
->address
, buf
, sizeof (buf
));
440 plist
= prefix_list_lookup (AFI_IP6
, oi
->plist_name
);
441 ret
= prefix_list_apply (plist
, (void *) c
->address
);
442 if (ret
== PREFIX_DENY
)
444 if (IS_OSPF6_DEBUG_INTERFACE
)
445 zlog_debug ("%s on %s filtered by prefix-list %s ",
446 buf
, oi
->interface
->name
, oi
->plist_name
);
451 route
= ospf6_route_create ();
452 memcpy (&route
->prefix
, c
->address
, sizeof (struct prefix
));
453 apply_mask (&route
->prefix
);
454 route
->type
= OSPF6_DEST_TYPE_NETWORK
;
455 route
->path
.area_id
= oi
->area
->area_id
;
456 route
->path
.type
= OSPF6_PATH_TYPE_INTRA
;
457 route
->path
.cost
= oi
->cost
;
458 inet_pton (AF_INET6
, "::1", &nh_addr
);
459 ospf6_route_add_nexthop (route
, oi
->interface
->ifindex
, &nh_addr
);
460 ospf6_route_add (route
, oi
->route_connected
);
463 /* create new Link-LSA */
464 OSPF6_LINK_LSA_SCHEDULE (oi
);
465 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_TRANSIT (oi
);
466 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_STUB (oi
->area
);
470 ospf6_interface_state_change (u_char next_state
, struct ospf6_interface
*oi
)
474 prev_state
= oi
->state
;
475 oi
->state
= next_state
;
477 if (prev_state
== next_state
)
481 if (IS_OSPF6_DEBUG_INTERFACE
)
483 zlog_debug ("Interface state change %s: %s -> %s", oi
->interface
->name
,
484 ospf6_interface_state_str
[prev_state
],
485 ospf6_interface_state_str
[next_state
]);
489 if ((prev_state
== OSPF6_INTERFACE_DR
||
490 prev_state
== OSPF6_INTERFACE_BDR
) &&
491 (next_state
!= OSPF6_INTERFACE_DR
&&
492 next_state
!= OSPF6_INTERFACE_BDR
))
493 ospf6_sso (oi
->interface
->ifindex
, &alldrouters6
, IPV6_LEAVE_GROUP
);
495 if ((prev_state
!= OSPF6_INTERFACE_DR
&&
496 prev_state
!= OSPF6_INTERFACE_BDR
) &&
497 (next_state
== OSPF6_INTERFACE_DR
||
498 next_state
== OSPF6_INTERFACE_BDR
))
499 ospf6_sso (oi
->interface
->ifindex
, &alldrouters6
, IPV6_JOIN_GROUP
);
501 OSPF6_ROUTER_LSA_SCHEDULE (oi
->area
);
502 if (next_state
== OSPF6_INTERFACE_DOWN
)
504 OSPF6_NETWORK_LSA_EXECUTE (oi
);
505 OSPF6_INTRA_PREFIX_LSA_EXECUTE_TRANSIT (oi
);
506 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_STUB (oi
->area
);
508 else if (prev_state
== OSPF6_INTERFACE_DR
||
509 next_state
== OSPF6_INTERFACE_DR
)
511 OSPF6_NETWORK_LSA_SCHEDULE (oi
);
512 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_TRANSIT (oi
);
513 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_STUB (oi
->area
);
517 /* Terminal state or regression */
518 if ((next_state
== OSPF6_INTERFACE_POINTTOPOINT
) ||
519 (next_state
== OSPF6_INTERFACE_DROTHER
) ||
520 (next_state
== OSPF6_INTERFACE_BDR
) ||
521 (next_state
== OSPF6_INTERFACE_DR
) ||
522 (next_state
< prev_state
))
523 ospf6TrapIfStateChange (oi
);
529 /* DR Election, RFC2328 section 9.4 */
531 #define IS_ELIGIBLE(n) \
532 ((n)->state >= OSPF6_NEIGHBOR_TWOWAY && (n)->priority != 0)
534 static struct ospf6_neighbor
*
535 better_bdrouter (struct ospf6_neighbor
*a
, struct ospf6_neighbor
*b
)
537 if ((a
== NULL
|| ! IS_ELIGIBLE (a
) || a
->drouter
== a
->router_id
) &&
538 (b
== NULL
|| ! IS_ELIGIBLE (b
) || b
->drouter
== b
->router_id
))
540 else if (a
== NULL
|| ! IS_ELIGIBLE (a
) || a
->drouter
== a
->router_id
)
542 else if (b
== NULL
|| ! IS_ELIGIBLE (b
) || b
->drouter
== b
->router_id
)
545 if (a
->bdrouter
== a
->router_id
&& b
->bdrouter
!= b
->router_id
)
547 if (a
->bdrouter
!= a
->router_id
&& b
->bdrouter
== b
->router_id
)
550 if (a
->priority
> b
->priority
)
552 if (a
->priority
< b
->priority
)
555 if (ntohl (a
->router_id
) > ntohl (b
->router_id
))
557 if (ntohl (a
->router_id
) < ntohl (b
->router_id
))
560 zlog_warn ("Router-ID duplicate ?");
564 static struct ospf6_neighbor
*
565 better_drouter (struct ospf6_neighbor
*a
, struct ospf6_neighbor
*b
)
567 if ((a
== NULL
|| ! IS_ELIGIBLE (a
) || a
->drouter
!= a
->router_id
) &&
568 (b
== NULL
|| ! IS_ELIGIBLE (b
) || b
->drouter
!= b
->router_id
))
570 else if (a
== NULL
|| ! IS_ELIGIBLE (a
) || a
->drouter
!= a
->router_id
)
572 else if (b
== NULL
|| ! IS_ELIGIBLE (b
) || b
->drouter
!= b
->router_id
)
575 if (a
->drouter
== a
->router_id
&& b
->drouter
!= b
->router_id
)
577 if (a
->drouter
!= a
->router_id
&& b
->drouter
== b
->router_id
)
580 if (a
->priority
> b
->priority
)
582 if (a
->priority
< b
->priority
)
585 if (ntohl (a
->router_id
) > ntohl (b
->router_id
))
587 if (ntohl (a
->router_id
) < ntohl (b
->router_id
))
590 zlog_warn ("Router-ID duplicate ?");
595 dr_election (struct ospf6_interface
*oi
)
597 struct listnode
*node
, *nnode
;
598 struct ospf6_neighbor
*on
, *drouter
, *bdrouter
, myself
;
599 struct ospf6_neighbor
*best_drouter
, *best_bdrouter
;
600 u_char next_state
= 0;
602 drouter
= bdrouter
= NULL
;
603 best_drouter
= best_bdrouter
= NULL
;
605 /* pseudo neighbor myself, including noting current DR/BDR (1) */
606 memset (&myself
, 0, sizeof (myself
));
607 inet_ntop (AF_INET
, &oi
->area
->ospf6
->router_id
, myself
.name
,
608 sizeof (myself
.name
));
609 myself
.state
= OSPF6_NEIGHBOR_TWOWAY
;
610 myself
.drouter
= oi
->drouter
;
611 myself
.bdrouter
= oi
->bdrouter
;
612 myself
.priority
= oi
->priority
;
613 myself
.router_id
= oi
->area
->ospf6
->router_id
;
615 /* Electing BDR (2) */
616 for (ALL_LIST_ELEMENTS (oi
->neighbor_list
, node
, nnode
, on
))
617 bdrouter
= better_bdrouter (bdrouter
, on
);
619 best_bdrouter
= bdrouter
;
620 bdrouter
= better_bdrouter (best_bdrouter
, &myself
);
622 /* Electing DR (3) */
623 for (ALL_LIST_ELEMENTS (oi
->neighbor_list
, node
, nnode
, on
))
624 drouter
= better_drouter (drouter
, on
);
626 best_drouter
= drouter
;
627 drouter
= better_drouter (best_drouter
, &myself
);
631 /* the router itself is newly/no longer DR/BDR (4) */
632 if ((drouter
== &myself
&& myself
.drouter
!= myself
.router_id
) ||
633 (drouter
!= &myself
&& myself
.drouter
== myself
.router_id
) ||
634 (bdrouter
== &myself
&& myself
.bdrouter
!= myself
.router_id
) ||
635 (bdrouter
!= &myself
&& myself
.bdrouter
== myself
.router_id
))
637 myself
.drouter
= (drouter
? drouter
->router_id
: htonl (0));
638 myself
.bdrouter
= (bdrouter
? bdrouter
->router_id
: htonl (0));
640 /* compatible to Electing BDR (2) */
641 bdrouter
= better_bdrouter (best_bdrouter
, &myself
);
643 /* compatible to Electing DR (3) */
644 drouter
= better_drouter (best_drouter
, &myself
);
649 /* Set interface state accordingly (5) */
650 if (drouter
&& drouter
== &myself
)
651 next_state
= OSPF6_INTERFACE_DR
;
652 else if (bdrouter
&& bdrouter
== &myself
)
653 next_state
= OSPF6_INTERFACE_BDR
;
655 next_state
= OSPF6_INTERFACE_DROTHER
;
657 /* If NBMA, schedule Start for each neighbor having priority of 0 (6) */
660 /* If DR or BDR change, invoke AdjOK? for each neighbor (7) */
661 /* RFC 2328 section 12.4. Originating LSAs (3) will be handled
662 accordingly after AdjOK */
663 if (oi
->drouter
!= (drouter
? drouter
->router_id
: htonl (0)) ||
664 oi
->bdrouter
!= (bdrouter
? bdrouter
->router_id
: htonl (0)))
666 if (IS_OSPF6_DEBUG_INTERFACE
)
667 zlog_debug ("DR Election on %s: DR: %s BDR: %s", oi
->interface
->name
,
668 (drouter
? drouter
->name
: "0.0.0.0"),
669 (bdrouter
? bdrouter
->name
: "0.0.0.0"));
671 for (ALL_LIST_ELEMENTS_RO (oi
->neighbor_list
, node
, on
))
673 if (on
->state
< OSPF6_NEIGHBOR_TWOWAY
)
675 /* Schedule AdjOK. */
676 thread_add_event (master
, adj_ok
, on
, 0);
680 oi
->drouter
= (drouter
? drouter
->router_id
: htonl (0));
681 oi
->bdrouter
= (bdrouter
? bdrouter
->router_id
: htonl (0));
686 /* Interface State Machine */
688 interface_up (struct thread
*thread
)
690 struct ospf6_interface
*oi
;
692 oi
= (struct ospf6_interface
*) THREAD_ARG (thread
);
693 assert (oi
&& oi
->interface
);
695 if (IS_OSPF6_DEBUG_INTERFACE
)
696 zlog_debug ("Interface Event %s: [InterfaceUp]",
697 oi
->interface
->name
);
699 /* check physical interface is up */
700 if (! if_is_operative (oi
->interface
))
702 if (IS_OSPF6_DEBUG_INTERFACE
)
703 zlog_debug ("Interface %s is down, can't execute [InterfaceUp]",
704 oi
->interface
->name
);
708 /* check interface has a link-local address */
709 if (! (ospf6_interface_get_linklocal_address(oi
->interface
)
710 || if_is_loopback(oi
->interface
)))
712 if (IS_OSPF6_DEBUG_INTERFACE
)
713 zlog_debug ("Interface %s has no link local address, can't execute [InterfaceUp]",
714 oi
->interface
->name
);
719 ospf6_interface_recalculate_cost (oi
);
721 /* if already enabled, do nothing */
722 if (oi
->state
> OSPF6_INTERFACE_DOWN
)
724 if (IS_OSPF6_DEBUG_INTERFACE
)
725 zlog_debug ("Interface %s already enabled",
726 oi
->interface
->name
);
730 /* If no area assigned, return */
731 if (oi
->area
== NULL
)
733 zlog_debug ("%s: Not scheduleing Hello for %s as there is no area assigned yet", __func__
,
734 oi
->interface
->name
);
738 /* Join AllSPFRouters */
739 if (ospf6_sso (oi
->interface
->ifindex
, &allspfrouters6
, IPV6_JOIN_GROUP
) < 0)
741 if (oi
->sso_try_cnt
++ < OSPF6_INTERFACE_SSO_RETRY_MAX
)
743 zlog_info("Scheduling %s for sso retry, trial count: %d",
744 oi
->interface
->name
, oi
->sso_try_cnt
);
745 thread_add_timer (master
, interface_up
, oi
,
746 OSPF6_INTERFACE_SSO_RETRY_INT
);
750 oi
->sso_try_cnt
= 0; /* Reset on success */
752 /* Update interface route */
753 ospf6_interface_connected_route_update (oi
->interface
);
756 if (! CHECK_FLAG (oi
->flag
, OSPF6_INTERFACE_PASSIVE
) &&
757 !if_is_loopback (oi
->interface
))
758 oi
->thread_send_hello
= thread_add_event (master
, ospf6_hello_send
, oi
, 0);
760 /* decide next interface state */
761 if ((if_is_pointopoint (oi
->interface
)) ||
762 (oi
->type
== OSPF_IFTYPE_POINTOPOINT
)) {
763 ospf6_interface_state_change (OSPF6_INTERFACE_POINTTOPOINT
, oi
);
765 else if (oi
->priority
== 0)
766 ospf6_interface_state_change (OSPF6_INTERFACE_DROTHER
, oi
);
769 ospf6_interface_state_change (OSPF6_INTERFACE_WAITING
, oi
);
770 thread_add_timer (master
, wait_timer
, oi
, oi
->dead_interval
);
777 wait_timer (struct thread
*thread
)
779 struct ospf6_interface
*oi
;
781 oi
= (struct ospf6_interface
*) THREAD_ARG (thread
);
782 assert (oi
&& oi
->interface
);
784 if (IS_OSPF6_DEBUG_INTERFACE
)
785 zlog_debug ("Interface Event %s: [WaitTimer]",
786 oi
->interface
->name
);
788 if (oi
->state
== OSPF6_INTERFACE_WAITING
)
789 ospf6_interface_state_change (dr_election (oi
), oi
);
795 backup_seen (struct thread
*thread
)
797 struct ospf6_interface
*oi
;
799 oi
= (struct ospf6_interface
*) THREAD_ARG (thread
);
800 assert (oi
&& oi
->interface
);
802 if (IS_OSPF6_DEBUG_INTERFACE
)
803 zlog_debug ("Interface Event %s: [BackupSeen]",
804 oi
->interface
->name
);
806 if (oi
->state
== OSPF6_INTERFACE_WAITING
)
807 ospf6_interface_state_change (dr_election (oi
), oi
);
813 neighbor_change (struct thread
*thread
)
815 struct ospf6_interface
*oi
;
817 oi
= (struct ospf6_interface
*) THREAD_ARG (thread
);
818 assert (oi
&& oi
->interface
);
820 if (IS_OSPF6_DEBUG_INTERFACE
)
821 zlog_debug ("Interface Event %s: [NeighborChange]",
822 oi
->interface
->name
);
824 if (oi
->state
== OSPF6_INTERFACE_DROTHER
||
825 oi
->state
== OSPF6_INTERFACE_BDR
||
826 oi
->state
== OSPF6_INTERFACE_DR
)
827 ospf6_interface_state_change (dr_election (oi
), oi
);
833 interface_down (struct thread
*thread
)
835 struct ospf6_interface
*oi
;
836 struct listnode
*node
, *nnode
;
837 struct ospf6_neighbor
*on
;
839 oi
= (struct ospf6_interface
*) THREAD_ARG (thread
);
840 assert (oi
&& oi
->interface
);
842 if (IS_OSPF6_DEBUG_INTERFACE
)
843 zlog_debug ("Interface Event %s: [InterfaceDown]",
844 oi
->interface
->name
);
847 THREAD_OFF (oi
->thread_send_hello
);
849 /* Leave AllSPFRouters */
850 if (oi
->state
> OSPF6_INTERFACE_DOWN
)
851 ospf6_sso (oi
->interface
->ifindex
, &allspfrouters6
, IPV6_LEAVE_GROUP
);
853 ospf6_interface_state_change (OSPF6_INTERFACE_DOWN
, oi
);
855 for (ALL_LIST_ELEMENTS (oi
->neighbor_list
, node
, nnode
, on
))
856 ospf6_neighbor_delete (on
);
858 list_delete_all_node (oi
->neighbor_list
);
860 /* When interface state is reset, also reset information about
861 * DR election, as it is no longer valid. */
862 oi
->drouter
= oi
->prev_drouter
= htonl(0);
863 oi
->bdrouter
= oi
->prev_bdrouter
= htonl(0);
868 /* show specified interface structure */
870 ospf6_interface_show (struct vty
*vty
, struct interface
*ifp
)
872 struct ospf6_interface
*oi
;
876 char strbuf
[PREFIX2STR_BUFFER
], drouter
[32], bdrouter
[32];
877 const char *updown
[3] = {"down", "up", NULL
};
879 struct timeval res
, now
;
881 struct ospf6_lsa
*lsa
;
883 /* check physical interface type */
884 if (if_is_loopback (ifp
))
886 else if (if_is_broadcast (ifp
))
888 else if (if_is_pointopoint (ifp
))
889 type
= "POINTOPOINT";
893 vty_out (vty
, "%s is %s, type %s%s",
894 ifp
->name
, updown
[if_is_operative (ifp
)], type
,
896 vty_out (vty
, " Interface ID: %d%s", ifp
->ifindex
, VNL
);
898 if (ifp
->info
== NULL
)
900 vty_out (vty
, " OSPF not enabled on this interface%s", VNL
);
904 oi
= (struct ospf6_interface
*) ifp
->info
;
906 vty_out (vty
, " Internet Address:%s", VNL
);
908 for (ALL_LIST_ELEMENTS_RO (ifp
->connected
, i
, c
))
911 prefix2str (p
, strbuf
, sizeof (strbuf
));
915 vty_out (vty
, " inet : %s%s", strbuf
,
919 vty_out (vty
, " inet6: %s%s", strbuf
,
923 vty_out (vty
, " ??? : %s%s", strbuf
,
931 vty_out (vty
, " Instance ID %d, Interface MTU %d (autodetect: %d)%s",
932 oi
->instance_id
, oi
->ifmtu
, ifp
->mtu6
, VNL
);
933 vty_out (vty
, " MTU mismatch detection: %s%s", oi
->mtu_ignore
?
934 "disabled" : "enabled", VNL
);
935 inet_ntop (AF_INET
, &oi
->area
->area_id
,
936 strbuf
, sizeof (strbuf
));
937 vty_out (vty
, " Area ID %s, Cost %u%s", strbuf
, oi
->cost
,
941 vty_out (vty
, " Not Attached to Area%s", VNL
);
943 vty_out (vty
, " State %s, Transmit Delay %d sec, Priority %d%s",
944 ospf6_interface_state_str
[oi
->state
],
945 oi
->transdelay
, oi
->priority
,
947 vty_out (vty
, " Timer intervals configured:%s", VNL
);
948 vty_out (vty
, " Hello %d, Dead %d, Retransmit %d%s",
949 oi
->hello_interval
, oi
->dead_interval
, oi
->rxmt_interval
,
952 inet_ntop (AF_INET
, &oi
->drouter
, drouter
, sizeof (drouter
));
953 inet_ntop (AF_INET
, &oi
->bdrouter
, bdrouter
, sizeof (bdrouter
));
954 vty_out (vty
, " DR: %s BDR: %s%s", drouter
, bdrouter
, VNL
);
956 vty_out (vty
, " Number of I/F scoped LSAs is %u%s",
957 oi
->lsdb
->count
, VNL
);
959 quagga_gettime (QUAGGA_CLK_MONOTONIC
, &now
);
962 if (oi
->thread_send_lsupdate
)
963 timersub (&oi
->thread_send_lsupdate
->u
.sands
, &now
, &res
);
964 timerstring (&res
, duration
, sizeof (duration
));
965 vty_out (vty
, " %d Pending LSAs for LSUpdate in Time %s [thread %s]%s",
966 oi
->lsupdate_list
->count
, duration
,
967 (oi
->thread_send_lsupdate
? "on" : "off"),
969 for (lsa
= ospf6_lsdb_head (oi
->lsupdate_list
); lsa
;
970 lsa
= ospf6_lsdb_next (lsa
))
971 vty_out (vty
, " %s%s", lsa
->name
, VNL
);
974 if (oi
->thread_send_lsack
)
975 timersub (&oi
->thread_send_lsack
->u
.sands
, &now
, &res
);
976 timerstring (&res
, duration
, sizeof (duration
));
977 vty_out (vty
, " %d Pending LSAs for LSAck in Time %s [thread %s]%s",
978 oi
->lsack_list
->count
, duration
,
979 (oi
->thread_send_lsack
? "on" : "off"),
981 for (lsa
= ospf6_lsdb_head (oi
->lsack_list
); lsa
;
982 lsa
= ospf6_lsdb_next (lsa
))
983 vty_out (vty
, " %s%s", lsa
->name
, VNL
);
984 ospf6_bfd_show_info(vty
, oi
->bfd_info
, 1);
989 DEFUN (show_ipv6_ospf6_interface
,
990 show_ipv6_ospf6_interface_ifname_cmd
,
991 "show ipv6 ospf6 interface [IFNAME]",
999 struct interface
*ifp
;
1004 ifp
= if_lookup_by_name (argv
[idx_ifname
]->arg
);
1007 vty_out (vty
, "No such Interface: %s%s", argv
[idx_ifname
]->arg
,
1011 ospf6_interface_show (vty
, ifp
);
1015 for (ALL_LIST_ELEMENTS_RO (vrf_iflist (VRF_DEFAULT
), i
, ifp
))
1016 ospf6_interface_show (vty
, ifp
);
1022 DEFUN (show_ipv6_ospf6_interface_ifname_prefix
,
1023 show_ipv6_ospf6_interface_ifname_prefix_cmd
,
1024 "show ipv6 ospf6 interface IFNAME prefix [<X:X::X:X|X:X::X:X/M>] [<match|detail>]",
1030 "Display connected prefixes to advertise\n"
1031 OSPF6_ROUTE_ADDRESS_STR
1032 OSPF6_ROUTE_PREFIX_STR
1033 OSPF6_ROUTE_MATCH_STR
1034 "Display details of the prefixes\n")
1038 struct interface
*ifp
;
1039 struct ospf6_interface
*oi
;
1041 ifp
= if_lookup_by_name (argv
[idx_ifname
]->arg
);
1044 vty_out (vty
, "No such Interface: %s%s", argv
[idx_ifname
]->arg
, VNL
);
1051 vty_out (vty
, "OSPFv3 is not enabled on %s%s", argv
[idx_ifname
]->arg
, VNL
);
1055 ospf6_route_table_show (vty
, idx_prefix
, argc
, argv
, oi
->route_connected
);
1060 DEFUN (show_ipv6_ospf6_interface_prefix
,
1061 show_ipv6_ospf6_interface_prefix_cmd
,
1062 "show ipv6 ospf6 interface prefix [<X:X::X:X|X:X::X:X/M>] [<match|detail>]",
1067 "Display connected prefixes to advertise\n"
1068 OSPF6_ROUTE_ADDRESS_STR
1069 OSPF6_ROUTE_PREFIX_STR
1070 OSPF6_ROUTE_MATCH_STR
1071 "Display details of the prefixes\n")
1075 struct ospf6_interface
*oi
;
1076 struct interface
*ifp
;
1078 for (ALL_LIST_ELEMENTS_RO (vrf_iflist (VRF_DEFAULT
), i
, ifp
))
1080 oi
= (struct ospf6_interface
*) ifp
->info
;
1084 ospf6_route_table_show (vty
, idx_prefix
, argc
, argv
, oi
->route_connected
);
1090 /* interface variable set command */
1091 DEFUN (ipv6_ospf6_ifmtu
,
1092 ipv6_ospf6_ifmtu_cmd
,
1093 "ipv6 ospf6 ifmtu (1-65535)",
1097 "OSPFv3 Interface MTU\n"
1101 struct ospf6_interface
*oi
;
1102 struct interface
*ifp
;
1103 unsigned int ifmtu
, iobuflen
;
1104 struct listnode
*node
, *nnode
;
1105 struct ospf6_neighbor
*on
;
1107 ifp
= (struct interface
*) vty
->index
;
1110 oi
= (struct ospf6_interface
*) ifp
->info
;
1112 oi
= ospf6_interface_create (ifp
);
1115 ifmtu
= strtol (argv
[idx_number
]->arg
, NULL
, 10);
1117 if (oi
->ifmtu
== ifmtu
)
1120 if (ifp
->mtu6
!= 0 && ifp
->mtu6
< ifmtu
)
1122 vty_out (vty
, "%s's ospf6 ifmtu cannot go beyond physical mtu (%d)%s",
1123 ifp
->name
, ifp
->mtu6
, VNL
);
1127 if (oi
->ifmtu
< ifmtu
)
1129 iobuflen
= ospf6_iobuf_size (ifmtu
);
1130 if (iobuflen
< ifmtu
)
1132 vty_out (vty
, "%s's ifmtu is adjusted to I/O buffer size (%d).%s",
1133 ifp
->name
, iobuflen
, VNL
);
1134 oi
->ifmtu
= iobuflen
;
1142 /* re-establish adjacencies */
1143 for (ALL_LIST_ELEMENTS (oi
->neighbor_list
, node
, nnode
, on
))
1145 THREAD_OFF (on
->inactivity_timer
);
1146 thread_add_event (master
, inactivity_timer
, on
, 0);
1152 DEFUN (no_ipv6_ospf6_ifmtu
,
1153 no_ipv6_ospf6_ifmtu_cmd
,
1154 "no ipv6 ospf6 ifmtu",
1161 struct ospf6_interface
*oi
;
1162 struct interface
*ifp
;
1163 unsigned int iobuflen
;
1164 struct listnode
*node
, *nnode
;
1165 struct ospf6_neighbor
*on
;
1167 ifp
= (struct interface
*) vty
->index
;
1170 oi
= (struct ospf6_interface
*) ifp
->info
;
1172 oi
= ospf6_interface_create (ifp
);
1175 if (oi
->ifmtu
< ifp
->mtu
)
1177 iobuflen
= ospf6_iobuf_size (ifp
->mtu
);
1178 if (iobuflen
< ifp
->mtu
)
1180 vty_out (vty
, "%s's ifmtu is adjusted to I/O buffer size (%d).%s",
1181 ifp
->name
, iobuflen
, VNL
);
1182 oi
->ifmtu
= iobuflen
;
1185 oi
->ifmtu
= ifp
->mtu
;
1188 oi
->ifmtu
= ifp
->mtu
;
1190 /* re-establish adjacencies */
1191 for (ALL_LIST_ELEMENTS (oi
->neighbor_list
, node
, nnode
, on
))
1193 THREAD_OFF (on
->inactivity_timer
);
1194 thread_add_event (master
, inactivity_timer
, on
, 0);
1200 DEFUN (ipv6_ospf6_cost
,
1201 ipv6_ospf6_cost_cmd
,
1202 "ipv6 ospf6 cost (1-65535)",
1206 "Outgoing metric of this interface\n"
1210 struct ospf6_interface
*oi
;
1211 struct interface
*ifp
;
1212 unsigned long int lcost
;
1214 ifp
= (struct interface
*) vty
->index
;
1217 oi
= (struct ospf6_interface
*) ifp
->info
;
1219 oi
= ospf6_interface_create (ifp
);
1222 lcost
= strtol (argv
[idx_number
]->arg
, NULL
, 10);
1224 if (lcost
> UINT32_MAX
)
1226 vty_out (vty
, "Cost %ld is out of range%s", lcost
, VNL
);
1230 if (oi
->cost
== lcost
)
1234 SET_FLAG (oi
->flag
, OSPF6_INTERFACE_NOAUTOCOST
);
1236 ospf6_interface_recalculate_cost(oi
);
1241 DEFUN (no_ipv6_ospf6_cost
,
1242 no_ipv6_ospf6_cost_cmd
,
1243 "no ipv6 ospf6 cost",
1247 "Calculate interface cost from bandwidth\n"
1250 struct ospf6_interface
*oi
;
1251 struct interface
*ifp
;
1253 ifp
= (struct interface
*) vty
->index
;
1256 oi
= (struct ospf6_interface
*) ifp
->info
;
1258 oi
= ospf6_interface_create (ifp
);
1261 UNSET_FLAG (oi
->flag
, OSPF6_INTERFACE_NOAUTOCOST
);
1263 ospf6_interface_recalculate_cost(oi
);
1268 DEFUN (auto_cost_reference_bandwidth
,
1269 auto_cost_reference_bandwidth_cmd
,
1270 "auto-cost reference-bandwidth (1-4294967)",
1271 "Calculate OSPF interface cost according to bandwidth\n"
1272 "Use reference bandwidth method to assign OSPF cost\n"
1273 "The reference bandwidth in terms of Mbits per second\n")
1276 struct ospf6
*o
= vty
->index
;
1277 struct ospf6_area
*oa
;
1278 struct ospf6_interface
*oi
;
1279 struct listnode
*i
, *j
;
1282 refbw
= strtol (argv
[idx_number
]->arg
, NULL
, 10);
1283 if (refbw
< 1 || refbw
> 4294967)
1285 vty_out (vty
, "reference-bandwidth value is invalid%s", VTY_NEWLINE
);
1289 /* If reference bandwidth is changed. */
1290 if ((refbw
) == o
->ref_bandwidth
)
1293 o
->ref_bandwidth
= refbw
;
1294 for (ALL_LIST_ELEMENTS_RO (o
->area_list
, i
, oa
))
1295 for (ALL_LIST_ELEMENTS_RO (oa
->if_list
, j
, oi
))
1296 ospf6_interface_recalculate_cost (oi
);
1301 DEFUN (no_auto_cost_reference_bandwidth
,
1302 no_auto_cost_reference_bandwidth_cmd
,
1303 "no auto-cost reference-bandwidth [(1-4294967)]",
1305 "Calculate OSPF interface cost according to bandwidth\n"
1306 "Use reference bandwidth method to assign OSPF cost\n"
1307 "The reference bandwidth in terms of Mbits per second\n")
1309 struct ospf6
*o
= vty
->index
;
1310 struct ospf6_area
*oa
;
1311 struct ospf6_interface
*oi
;
1312 struct listnode
*i
, *j
;
1314 if (o
->ref_bandwidth
== OSPF6_REFERENCE_BANDWIDTH
)
1317 o
->ref_bandwidth
= OSPF6_REFERENCE_BANDWIDTH
;
1318 for (ALL_LIST_ELEMENTS_RO (o
->area_list
, i
, oa
))
1319 for (ALL_LIST_ELEMENTS_RO (oa
->if_list
, j
, oi
))
1320 ospf6_interface_recalculate_cost (oi
);
1326 DEFUN (ipv6_ospf6_hellointerval
,
1327 ipv6_ospf6_hellointerval_cmd
,
1328 "ipv6 ospf6 hello-interval (1-65535)",
1331 "Time between HELLO packets\n"
1336 struct ospf6_interface
*oi
;
1337 struct interface
*ifp
;
1339 ifp
= (struct interface
*) vty
->index
;
1342 oi
= (struct ospf6_interface
*) ifp
->info
;
1344 oi
= ospf6_interface_create (ifp
);
1347 oi
->hello_interval
= strtol (argv
[idx_number
]->arg
, NULL
, 10);
1351 /* interface variable set command */
1352 DEFUN (ipv6_ospf6_deadinterval
,
1353 ipv6_ospf6_deadinterval_cmd
,
1354 "ipv6 ospf6 dead-interval (1-65535)",
1357 "Interval time after which a neighbor is declared down\n"
1362 struct ospf6_interface
*oi
;
1363 struct interface
*ifp
;
1365 ifp
= (struct interface
*) vty
->index
;
1368 oi
= (struct ospf6_interface
*) ifp
->info
;
1370 oi
= ospf6_interface_create (ifp
);
1373 oi
->dead_interval
= strtol (argv
[idx_number
]->arg
, NULL
, 10);
1377 /* interface variable set command */
1378 DEFUN (ipv6_ospf6_transmitdelay
,
1379 ipv6_ospf6_transmitdelay_cmd
,
1380 "ipv6 ospf6 transmit-delay (1-3600)",
1383 "Link state transmit delay\n"
1387 struct ospf6_interface
*oi
;
1388 struct interface
*ifp
;
1390 ifp
= (struct interface
*) vty
->index
;
1393 oi
= (struct ospf6_interface
*) ifp
->info
;
1395 oi
= ospf6_interface_create (ifp
);
1398 oi
->transdelay
= strtol (argv
[idx_number
]->arg
, NULL
, 10);
1402 /* interface variable set command */
1403 DEFUN (ipv6_ospf6_retransmitinterval
,
1404 ipv6_ospf6_retransmitinterval_cmd
,
1405 "ipv6 ospf6 retransmit-interval (1-65535)",
1408 "Time between retransmitting lost link state advertisements\n"
1413 struct ospf6_interface
*oi
;
1414 struct interface
*ifp
;
1416 ifp
= (struct interface
*) vty
->index
;
1419 oi
= (struct ospf6_interface
*) ifp
->info
;
1421 oi
= ospf6_interface_create (ifp
);
1424 oi
->rxmt_interval
= strtol (argv
[idx_number
]->arg
, NULL
, 10);
1428 /* interface variable set command */
1429 DEFUN (ipv6_ospf6_priority
,
1430 ipv6_ospf6_priority_cmd
,
1431 "ipv6 ospf6 priority (0-255)",
1439 struct ospf6_interface
*oi
;
1440 struct interface
*ifp
;
1442 ifp
= (struct interface
*) vty
->index
;
1445 oi
= (struct ospf6_interface
*) ifp
->info
;
1447 oi
= ospf6_interface_create (ifp
);
1450 oi
->priority
= strtol (argv
[idx_number
]->arg
, NULL
, 10);
1453 (oi
->state
== OSPF6_INTERFACE_DROTHER
||
1454 oi
->state
== OSPF6_INTERFACE_BDR
||
1455 oi
->state
== OSPF6_INTERFACE_DR
))
1456 ospf6_interface_state_change (dr_election (oi
), oi
);
1461 DEFUN (ipv6_ospf6_instance
,
1462 ipv6_ospf6_instance_cmd
,
1463 "ipv6 ospf6 instance-id (0-255)",
1466 "Instance ID for this interface\n"
1467 "Instance ID value\n"
1471 struct ospf6_interface
*oi
;
1472 struct interface
*ifp
;
1474 ifp
= (struct interface
*)vty
->index
;
1477 oi
= (struct ospf6_interface
*)ifp
->info
;
1479 oi
= ospf6_interface_create (ifp
);
1482 oi
->instance_id
= strtol (argv
[idx_number
]->arg
, NULL
, 10);
1486 DEFUN (ipv6_ospf6_passive
,
1487 ipv6_ospf6_passive_cmd
,
1488 "ipv6 ospf6 passive",
1491 "Passive interface; no adjacency will be formed on this interface\n"
1494 struct ospf6_interface
*oi
;
1495 struct interface
*ifp
;
1496 struct listnode
*node
, *nnode
;
1497 struct ospf6_neighbor
*on
;
1499 ifp
= (struct interface
*) vty
->index
;
1502 oi
= (struct ospf6_interface
*) ifp
->info
;
1504 oi
= ospf6_interface_create (ifp
);
1507 SET_FLAG (oi
->flag
, OSPF6_INTERFACE_PASSIVE
);
1508 THREAD_OFF (oi
->thread_send_hello
);
1510 for (ALL_LIST_ELEMENTS (oi
->neighbor_list
, node
, nnode
, on
))
1512 THREAD_OFF (on
->inactivity_timer
);
1513 thread_add_event (master
, inactivity_timer
, on
, 0);
1519 DEFUN (no_ipv6_ospf6_passive
,
1520 no_ipv6_ospf6_passive_cmd
,
1521 "no ipv6 ospf6 passive",
1525 "passive interface: No Adjacency will be formed on this I/F\n"
1528 struct ospf6_interface
*oi
;
1529 struct interface
*ifp
;
1531 ifp
= (struct interface
*) vty
->index
;
1534 oi
= (struct ospf6_interface
*) ifp
->info
;
1536 oi
= ospf6_interface_create (ifp
);
1539 UNSET_FLAG (oi
->flag
, OSPF6_INTERFACE_PASSIVE
);
1540 THREAD_OFF (oi
->thread_send_hello
);
1541 oi
->thread_send_hello
=
1542 thread_add_event (master
, ospf6_hello_send
, oi
, 0);
1547 DEFUN (ipv6_ospf6_mtu_ignore
,
1548 ipv6_ospf6_mtu_ignore_cmd
,
1549 "ipv6 ospf6 mtu-ignore",
1552 "Disable MTU mismatch detection on this interface\n"
1555 struct ospf6_interface
*oi
;
1556 struct interface
*ifp
;
1558 ifp
= (struct interface
*) vty
->index
;
1561 oi
= (struct ospf6_interface
*) ifp
->info
;
1563 oi
= ospf6_interface_create (ifp
);
1571 DEFUN (no_ipv6_ospf6_mtu_ignore
,
1572 no_ipv6_ospf6_mtu_ignore_cmd
,
1573 "no ipv6 ospf6 mtu-ignore",
1577 "Disable MTU mismatch detection on this interface\n"
1580 struct ospf6_interface
*oi
;
1581 struct interface
*ifp
;
1583 ifp
= (struct interface
*) vty
->index
;
1586 oi
= (struct ospf6_interface
*) ifp
->info
;
1588 oi
= ospf6_interface_create (ifp
);
1596 DEFUN (ipv6_ospf6_advertise_prefix_list
,
1597 ipv6_ospf6_advertise_prefix_list_cmd
,
1598 "ipv6 ospf6 advertise prefix-list WORD",
1601 "Advertising options\n"
1602 "Filter prefix using prefix-list\n"
1603 "Prefix list name\n"
1607 struct ospf6_interface
*oi
;
1608 struct interface
*ifp
;
1610 ifp
= (struct interface
*) vty
->index
;
1613 oi
= (struct ospf6_interface
*) ifp
->info
;
1615 oi
= ospf6_interface_create (ifp
);
1619 XFREE (MTYPE_CFG_PLIST_NAME
, oi
->plist_name
);
1620 oi
->plist_name
= XSTRDUP (MTYPE_CFG_PLIST_NAME
, argv
[idx_word
]->arg
);
1622 ospf6_interface_connected_route_update (oi
->interface
);
1626 OSPF6_LINK_LSA_SCHEDULE (oi
);
1627 if (oi
->state
== OSPF6_INTERFACE_DR
)
1629 OSPF6_NETWORK_LSA_SCHEDULE (oi
);
1630 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_TRANSIT (oi
);
1632 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_STUB (oi
->area
);
1638 DEFUN (no_ipv6_ospf6_advertise_prefix_list
,
1639 no_ipv6_ospf6_advertise_prefix_list_cmd
,
1640 "no ipv6 ospf6 advertise prefix-list",
1644 "Advertising options\n"
1645 "Filter prefix using prefix-list\n"
1648 struct ospf6_interface
*oi
;
1649 struct interface
*ifp
;
1651 ifp
= (struct interface
*) vty
->index
;
1654 oi
= (struct ospf6_interface
*) ifp
->info
;
1656 oi
= ospf6_interface_create (ifp
);
1661 XFREE (MTYPE_CFG_PLIST_NAME
, oi
->plist_name
);
1662 oi
->plist_name
= NULL
;
1665 ospf6_interface_connected_route_update (oi
->interface
);
1669 OSPF6_LINK_LSA_SCHEDULE (oi
);
1670 if (oi
->state
== OSPF6_INTERFACE_DR
)
1672 OSPF6_NETWORK_LSA_SCHEDULE (oi
);
1673 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_TRANSIT (oi
);
1675 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_STUB (oi
->area
);
1681 DEFUN (ipv6_ospf6_network
,
1682 ipv6_ospf6_network_cmd
,
1683 "ipv6 ospf6 network <broadcast|point-to-point>",
1687 "Specify OSPF6 broadcast network\n"
1688 "Specify OSPF6 point-to-point network\n"
1691 int idx_network
= 3;
1692 struct ospf6_interface
*oi
;
1693 struct interface
*ifp
;
1695 ifp
= (struct interface
*) vty
->index
;
1698 oi
= (struct ospf6_interface
*) ifp
->info
;
1700 oi
= ospf6_interface_create (ifp
);
1704 if (strncmp (argv
[idx_network
]->arg
, "b", 1) == 0)
1706 if (oi
->type
== OSPF_IFTYPE_BROADCAST
)
1709 oi
->type
= OSPF_IFTYPE_BROADCAST
;
1711 else if (strncmp (argv
[idx_network
]->arg
, "point-to-p", 10) == 0)
1713 if (oi
->type
== OSPF_IFTYPE_POINTOPOINT
) {
1716 oi
->type
= OSPF_IFTYPE_POINTOPOINT
;
1719 /* Reset the interface */
1720 thread_add_event (master
, interface_down
, oi
, 0);
1721 thread_add_event (master
, interface_up
, oi
, 0);
1726 DEFUN (no_ipv6_ospf6_network
,
1727 no_ipv6_ospf6_network_cmd
,
1728 "no ipv6 ospf6 network",
1733 "Default to whatever interface type system specifies"
1736 struct ospf6_interface
*oi
;
1737 struct interface
*ifp
;
1740 ifp
= (struct interface
*) vty
->index
;
1743 oi
= (struct ospf6_interface
*) ifp
->info
;
1748 type
= ospf6_default_iftype (ifp
);
1749 if (oi
->type
== type
)
1755 /* Reset the interface */
1756 thread_add_event (master
, interface_down
, oi
, 0);
1757 thread_add_event (master
, interface_up
, oi
, 0);
1763 config_write_ospf6_interface (struct vty
*vty
)
1766 struct ospf6_interface
*oi
;
1767 struct interface
*ifp
;
1769 for (ALL_LIST_ELEMENTS_RO (vrf_iflist (VRF_DEFAULT
), i
, ifp
))
1771 oi
= (struct ospf6_interface
*) ifp
->info
;
1775 vty_out (vty
, "interface %s%s",
1776 oi
->interface
->name
, VNL
);
1779 vty_out (vty
, " description %s%s", ifp
->desc
, VNL
);
1780 if (ifp
->mtu6
!= oi
->ifmtu
)
1781 vty_out (vty
, " ipv6 ospf6 ifmtu %d%s", oi
->ifmtu
, VNL
);
1783 if (CHECK_FLAG (oi
->flag
, OSPF6_INTERFACE_NOAUTOCOST
))
1784 vty_out (vty
, " ipv6 ospf6 cost %d%s",
1787 if (oi
->hello_interval
!= OSPF6_INTERFACE_HELLO_INTERVAL
)
1788 vty_out (vty
, " ipv6 ospf6 hello-interval %d%s",
1789 oi
->hello_interval
, VNL
);
1791 if (oi
->dead_interval
!= OSPF6_INTERFACE_DEAD_INTERVAL
)
1792 vty_out (vty
, " ipv6 ospf6 dead-interval %d%s",
1793 oi
->dead_interval
, VNL
);
1795 if (oi
->rxmt_interval
!= OSPF6_INTERFACE_RXMT_INTERVAL
)
1796 vty_out (vty
, " ipv6 ospf6 retransmit-interval %d%s",
1797 oi
->rxmt_interval
, VNL
);
1799 if (oi
->priority
!= OSPF6_INTERFACE_PRIORITY
)
1800 vty_out (vty
, " ipv6 ospf6 priority %d%s",
1803 if (oi
->transdelay
!= OSPF6_INTERFACE_TRANSDELAY
)
1804 vty_out (vty
, " ipv6 ospf6 transmit-delay %d%s",
1805 oi
->transdelay
, VNL
);
1807 if (oi
->instance_id
!= OSPF6_INTERFACE_INSTANCE_ID
)
1808 vty_out (vty
, " ipv6 ospf6 instance-id %d%s",
1809 oi
->instance_id
, VNL
);
1812 vty_out (vty
, " ipv6 ospf6 advertise prefix-list %s%s",
1813 oi
->plist_name
, VNL
);
1815 if (CHECK_FLAG (oi
->flag
, OSPF6_INTERFACE_PASSIVE
))
1816 vty_out (vty
, " ipv6 ospf6 passive%s", VNL
);
1819 vty_out (vty
, " ipv6 ospf6 mtu-ignore%s", VNL
);
1821 if (oi
->type
!= ospf6_default_iftype(ifp
))
1823 if (oi
->type
== OSPF_IFTYPE_POINTOPOINT
)
1824 vty_out (vty
, " ipv6 ospf6 network point-to-point%s", VNL
);
1825 else if (oi
->type
== OSPF_IFTYPE_BROADCAST
)
1826 vty_out (vty
, " ipv6 ospf6 network broadcast%s", VNL
);
1829 ospf6_bfd_write_config(vty
, oi
);
1831 vty_out (vty
, "!%s", VNL
);
1836 static struct cmd_node interface_node
=
1844 ospf6_interface_init (void)
1846 /* Install interface node. */
1847 install_node (&interface_node
, config_write_ospf6_interface
);
1849 install_element (VIEW_NODE
, &show_ipv6_ospf6_interface_prefix_cmd
);
1850 install_element (VIEW_NODE
, &show_ipv6_ospf6_interface_ifname_cmd
);
1851 install_element (VIEW_NODE
, &show_ipv6_ospf6_interface_ifname_prefix_cmd
);
1853 install_element (CONFIG_NODE
, &interface_cmd
);
1854 install_default (INTERFACE_NODE
);
1855 install_element (INTERFACE_NODE
, &interface_desc_cmd
);
1856 install_element (INTERFACE_NODE
, &no_interface_desc_cmd
);
1857 install_element (INTERFACE_NODE
, &ipv6_ospf6_cost_cmd
);
1858 install_element (INTERFACE_NODE
, &no_ipv6_ospf6_cost_cmd
);
1859 install_element (INTERFACE_NODE
, &ipv6_ospf6_ifmtu_cmd
);
1860 install_element (INTERFACE_NODE
, &no_ipv6_ospf6_ifmtu_cmd
);
1861 install_element (INTERFACE_NODE
, &ipv6_ospf6_deadinterval_cmd
);
1862 install_element (INTERFACE_NODE
, &ipv6_ospf6_hellointerval_cmd
);
1863 install_element (INTERFACE_NODE
, &ipv6_ospf6_priority_cmd
);
1864 install_element (INTERFACE_NODE
, &ipv6_ospf6_retransmitinterval_cmd
);
1865 install_element (INTERFACE_NODE
, &ipv6_ospf6_transmitdelay_cmd
);
1866 install_element (INTERFACE_NODE
, &ipv6_ospf6_instance_cmd
);
1868 install_element (INTERFACE_NODE
, &ipv6_ospf6_passive_cmd
);
1869 install_element (INTERFACE_NODE
, &no_ipv6_ospf6_passive_cmd
);
1871 install_element (INTERFACE_NODE
, &ipv6_ospf6_mtu_ignore_cmd
);
1872 install_element (INTERFACE_NODE
, &no_ipv6_ospf6_mtu_ignore_cmd
);
1874 install_element (INTERFACE_NODE
, &ipv6_ospf6_advertise_prefix_list_cmd
);
1875 install_element (INTERFACE_NODE
, &no_ipv6_ospf6_advertise_prefix_list_cmd
);
1877 install_element (INTERFACE_NODE
, &ipv6_ospf6_network_cmd
);
1878 install_element (INTERFACE_NODE
, &no_ipv6_ospf6_network_cmd
);
1880 /* reference bandwidth commands */
1881 install_element (OSPF6_NODE
, &auto_cost_reference_bandwidth_cmd
);
1882 install_element (OSPF6_NODE
, &no_auto_cost_reference_bandwidth_cmd
);
1885 /* Clear the specified interface structure */
1887 ospf6_interface_clear (struct vty
*vty
, struct interface
*ifp
)
1889 struct ospf6_interface
*oi
;
1891 if (!if_is_operative (ifp
))
1894 if (ifp
->info
== NULL
)
1897 oi
= (struct ospf6_interface
*) ifp
->info
;
1899 if (IS_OSPF6_DEBUG_INTERFACE
)
1900 zlog_debug ("Interface %s: clear by reset", ifp
->name
);
1902 /* Reset the interface */
1903 thread_add_event (master
, interface_down
, oi
, 0);
1904 thread_add_event (master
, interface_up
, oi
, 0);
1907 /* Clear interface */
1908 DEFUN (clear_ipv6_ospf6_interface
,
1909 clear_ipv6_ospf6_interface_cmd
,
1910 "clear ipv6 ospf6 interface [IFNAME]",
1919 struct interface
*ifp
;
1920 struct listnode
*node
;
1922 if (argc
== 4) /* Clear all the ospfv3 interfaces. */
1924 for (ALL_LIST_ELEMENTS_RO (vrf_iflist (VRF_DEFAULT
), node
, ifp
))
1925 ospf6_interface_clear (vty
, ifp
);
1927 else /* Interface name is specified. */
1929 if ((ifp
= if_lookup_by_name (argv
[idx_ifname
]->arg
)) == NULL
)
1931 vty_out (vty
, "No such Interface: %s%s", argv
[idx_ifname
]->arg
, VNL
);
1934 ospf6_interface_clear (vty
, ifp
);
1941 install_element_ospf6_clear_interface (void)
1943 install_element (ENABLE_NODE
, &clear_ipv6_ospf6_interface_cmd
);
1946 DEFUN (debug_ospf6_interface
,
1947 debug_ospf6_interface_cmd
,
1948 "debug ospf6 interface",
1951 "Debug OSPFv3 Interface\n"
1954 OSPF6_DEBUG_INTERFACE_ON ();
1958 DEFUN (no_debug_ospf6_interface
,
1959 no_debug_ospf6_interface_cmd
,
1960 "no debug ospf6 interface",
1964 "Debug OSPFv3 Interface\n"
1967 OSPF6_DEBUG_INTERFACE_OFF ();
1972 config_write_ospf6_debug_interface (struct vty
*vty
)
1974 if (IS_OSPF6_DEBUG_INTERFACE
)
1975 vty_out (vty
, "debug ospf6 interface%s", VNL
);
1980 install_element_ospf6_debug_interface (void)
1982 install_element (ENABLE_NODE
, &debug_ospf6_interface_cmd
);
1983 install_element (ENABLE_NODE
, &no_debug_ospf6_interface_cmd
);
1984 install_element (CONFIG_NODE
, &debug_ospf6_interface_cmd
);
1985 install_element (CONFIG_NODE
, &no_debug_ospf6_interface_cmd
);