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.
31 #include "ospf6_proto.h"
32 #include "ospf6_lsa.h"
33 #include "ospf6_lsdb.h"
34 #include "ospf6_message.h"
35 #include "ospf6_top.h"
36 #include "ospf6_area.h"
37 #include "ospf6_interface.h"
38 #include "ospf6_neighbor.h"
39 #include "ospf6_intra.h"
40 #include "ospf6_flood.h"
42 #include "ospf6_bfd.h"
43 #include "ospf6_abr.h"
44 #include "ospf6_asbr.h"
45 #include "ospf6_lsa.h"
46 #include "ospf6_spf.h"
47 #include "ospf6_zebra.h"
49 DEFINE_HOOK(ospf6_neighbor_change
,
50 (struct ospf6_neighbor
* on
, int state
, int next_state
),
51 (on
, state
, next_state
))
53 unsigned char conf_debug_ospf6_neighbor
= 0;
55 const char *ospf6_neighbor_state_str
[] = {
56 "None", "Down", "Attempt", "Init", "Twoway",
57 "ExStart", "ExChange", "Loading", "Full", NULL
};
59 int ospf6_neighbor_cmp(void *va
, void *vb
)
61 struct ospf6_neighbor
*ona
= (struct ospf6_neighbor
*)va
;
62 struct ospf6_neighbor
*onb
= (struct ospf6_neighbor
*)vb
;
63 return (ntohl(ona
->router_id
) < ntohl(onb
->router_id
) ? -1 : 1);
66 struct ospf6_neighbor
*ospf6_neighbor_lookup(u_int32_t router_id
,
67 struct ospf6_interface
*oi
)
70 struct ospf6_neighbor
*on
;
72 for (ALL_LIST_ELEMENTS_RO(oi
->neighbor_list
, n
, on
))
73 if (on
->router_id
== router_id
)
76 return (struct ospf6_neighbor
*)NULL
;
79 /* create ospf6_neighbor */
80 struct ospf6_neighbor
*ospf6_neighbor_create(u_int32_t router_id
,
81 struct ospf6_interface
*oi
)
83 struct ospf6_neighbor
*on
;
86 on
= (struct ospf6_neighbor
*)XMALLOC(MTYPE_OSPF6_NEIGHBOR
,
87 sizeof(struct ospf6_neighbor
));
89 zlog_warn("neighbor: malloc failed");
93 memset(on
, 0, sizeof(struct ospf6_neighbor
));
94 inet_ntop(AF_INET
, &router_id
, buf
, sizeof(buf
));
95 snprintf(on
->name
, sizeof(on
->name
), "%s%%%s", buf
,
98 on
->state
= OSPF6_NEIGHBOR_DOWN
;
100 monotime(&on
->last_changed
);
101 on
->router_id
= router_id
;
103 on
->summary_list
= ospf6_lsdb_create(on
);
104 on
->request_list
= ospf6_lsdb_create(on
);
105 on
->retrans_list
= ospf6_lsdb_create(on
);
107 on
->dbdesc_list
= ospf6_lsdb_create(on
);
108 on
->lsupdate_list
= ospf6_lsdb_create(on
);
109 on
->lsack_list
= ospf6_lsdb_create(on
);
111 listnode_add_sort(oi
->neighbor_list
, on
);
113 ospf6_bfd_info_nbr_create(oi
, on
);
117 void ospf6_neighbor_delete(struct ospf6_neighbor
*on
)
119 struct ospf6_lsa
*lsa
;
121 ospf6_lsdb_remove_all(on
->summary_list
);
122 ospf6_lsdb_remove_all(on
->request_list
);
123 for (lsa
= ospf6_lsdb_head(on
->retrans_list
); lsa
;
124 lsa
= ospf6_lsdb_next(lsa
)) {
125 ospf6_decrement_retrans_count(lsa
);
126 ospf6_lsdb_remove(lsa
, on
->retrans_list
);
129 ospf6_lsdb_remove_all(on
->dbdesc_list
);
130 ospf6_lsdb_remove_all(on
->lsupdate_list
);
131 ospf6_lsdb_remove_all(on
->lsack_list
);
133 ospf6_lsdb_delete(on
->summary_list
);
134 ospf6_lsdb_delete(on
->request_list
);
135 ospf6_lsdb_delete(on
->retrans_list
);
137 ospf6_lsdb_delete(on
->dbdesc_list
);
138 ospf6_lsdb_delete(on
->lsupdate_list
);
139 ospf6_lsdb_delete(on
->lsack_list
);
141 THREAD_OFF(on
->inactivity_timer
);
143 THREAD_OFF(on
->thread_send_dbdesc
);
144 THREAD_OFF(on
->thread_send_lsreq
);
145 THREAD_OFF(on
->thread_send_lsupdate
);
146 THREAD_OFF(on
->thread_send_lsack
);
148 ospf6_bfd_reg_dereg_nbr(on
, ZEBRA_BFD_DEST_DEREGISTER
);
149 XFREE(MTYPE_OSPF6_NEIGHBOR
, on
);
152 static void ospf6_neighbor_state_change(u_char next_state
,
153 struct ospf6_neighbor
*on
, int event
)
157 prev_state
= on
->state
;
158 on
->state
= next_state
;
160 if (prev_state
== next_state
)
164 monotime(&on
->last_changed
);
167 if (IS_OSPF6_DEBUG_NEIGHBOR(STATE
)) {
168 zlog_debug("Neighbor state change %s: [%s]->[%s] (%s)",
169 on
->name
, ospf6_neighbor_state_str
[prev_state
],
170 ospf6_neighbor_state_str
[next_state
],
171 ospf6_neighbor_event_string(event
));
174 /* Optionally notify about adjacency changes */
175 if (CHECK_FLAG(on
->ospf6_if
->area
->ospf6
->config_flags
,
176 OSPF6_LOG_ADJACENCY_CHANGES
)
177 && (CHECK_FLAG(on
->ospf6_if
->area
->ospf6
->config_flags
,
178 OSPF6_LOG_ADJACENCY_DETAIL
)
179 || (next_state
== OSPF6_NEIGHBOR_FULL
)
180 || (next_state
< prev_state
)))
181 zlog_notice("AdjChg: Nbr %s: %s -> %s (%s)", on
->name
,
182 ospf6_neighbor_state_str
[prev_state
],
183 ospf6_neighbor_state_str
[next_state
],
184 ospf6_neighbor_event_string(event
));
186 if (prev_state
== OSPF6_NEIGHBOR_FULL
187 || next_state
== OSPF6_NEIGHBOR_FULL
) {
188 OSPF6_ROUTER_LSA_SCHEDULE(on
->ospf6_if
->area
);
189 if (on
->ospf6_if
->state
== OSPF6_INTERFACE_DR
) {
190 OSPF6_NETWORK_LSA_SCHEDULE(on
->ospf6_if
);
191 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_TRANSIT(on
->ospf6_if
);
193 OSPF6_INTRA_PREFIX_LSA_SCHEDULE_STUB(on
->ospf6_if
->area
);
196 if ((prev_state
== OSPF6_NEIGHBOR_EXCHANGE
197 || prev_state
== OSPF6_NEIGHBOR_LOADING
)
198 && (next_state
!= OSPF6_NEIGHBOR_EXCHANGE
199 && next_state
!= OSPF6_NEIGHBOR_LOADING
))
200 ospf6_maxage_remove(on
->ospf6_if
->area
->ospf6
);
202 hook_call(ospf6_neighbor_change
, on
, next_state
, prev_state
);
203 ospf6_bfd_trigger_event(on
, prev_state
, next_state
);
206 /* RFC2328 section 10.4 */
207 static int need_adjacency(struct ospf6_neighbor
*on
)
209 if (on
->ospf6_if
->state
== OSPF6_INTERFACE_POINTTOPOINT
210 || on
->ospf6_if
->state
== OSPF6_INTERFACE_DR
211 || on
->ospf6_if
->state
== OSPF6_INTERFACE_BDR
)
214 if (on
->ospf6_if
->drouter
== on
->router_id
215 || on
->ospf6_if
->bdrouter
== on
->router_id
)
221 int hello_received(struct thread
*thread
)
223 struct ospf6_neighbor
*on
;
225 on
= (struct ospf6_neighbor
*)THREAD_ARG(thread
);
228 if (IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
229 zlog_debug("Neighbor Event %s: *HelloReceived*", on
->name
);
231 /* reset Inactivity Timer */
232 THREAD_OFF(on
->inactivity_timer
);
233 on
->inactivity_timer
= thread_add_timer(master
, inactivity_timer
, on
,
234 on
->ospf6_if
->dead_interval
);
236 if (on
->state
<= OSPF6_NEIGHBOR_DOWN
)
237 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_INIT
, on
,
238 OSPF6_NEIGHBOR_EVENT_HELLO_RCVD
);
243 int twoway_received(struct thread
*thread
)
245 struct ospf6_neighbor
*on
;
247 on
= (struct ospf6_neighbor
*)THREAD_ARG(thread
);
250 if (on
->state
> OSPF6_NEIGHBOR_INIT
)
253 if (IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
254 zlog_debug("Neighbor Event %s: *2Way-Received*", on
->name
);
256 thread_add_event(master
, neighbor_change
, on
->ospf6_if
, 0);
258 if (!need_adjacency(on
)) {
259 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_TWOWAY
, on
,
260 OSPF6_NEIGHBOR_EVENT_TWOWAY_RCVD
);
264 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_EXSTART
, on
,
265 OSPF6_NEIGHBOR_EVENT_TWOWAY_RCVD
);
266 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_MSBIT
);
267 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_MBIT
);
268 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_IBIT
);
270 THREAD_OFF(on
->thread_send_dbdesc
);
271 on
->thread_send_dbdesc
=
272 thread_add_event(master
, ospf6_dbdesc_send
, on
, 0);
277 int negotiation_done(struct thread
*thread
)
279 struct ospf6_neighbor
*on
;
280 struct ospf6_lsa
*lsa
;
282 on
= (struct ospf6_neighbor
*)THREAD_ARG(thread
);
285 if (on
->state
!= OSPF6_NEIGHBOR_EXSTART
)
288 if (IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
289 zlog_debug("Neighbor Event %s: *NegotiationDone*", on
->name
);
292 ospf6_lsdb_remove_all(on
->summary_list
);
293 ospf6_lsdb_remove_all(on
->request_list
);
294 for (lsa
= ospf6_lsdb_head(on
->retrans_list
); lsa
;
295 lsa
= ospf6_lsdb_next(lsa
)) {
296 ospf6_decrement_retrans_count(lsa
);
297 ospf6_lsdb_remove(lsa
, on
->retrans_list
);
300 /* Interface scoped LSAs */
301 for (lsa
= ospf6_lsdb_head(on
->ospf6_if
->lsdb
); lsa
;
302 lsa
= ospf6_lsdb_next(lsa
)) {
303 if (OSPF6_LSA_IS_MAXAGE(lsa
)) {
304 ospf6_increment_retrans_count(lsa
);
305 ospf6_lsdb_add(ospf6_lsa_copy(lsa
), on
->retrans_list
);
307 ospf6_lsdb_add(ospf6_lsa_copy(lsa
), on
->summary_list
);
310 /* Area scoped LSAs */
311 for (lsa
= ospf6_lsdb_head(on
->ospf6_if
->area
->lsdb
); lsa
;
312 lsa
= ospf6_lsdb_next(lsa
)) {
313 if (OSPF6_LSA_IS_MAXAGE(lsa
)) {
314 ospf6_increment_retrans_count(lsa
);
315 ospf6_lsdb_add(ospf6_lsa_copy(lsa
), on
->retrans_list
);
317 ospf6_lsdb_add(ospf6_lsa_copy(lsa
), on
->summary_list
);
321 for (lsa
= ospf6_lsdb_head(on
->ospf6_if
->area
->ospf6
->lsdb
); lsa
;
322 lsa
= ospf6_lsdb_next(lsa
)) {
323 if (OSPF6_LSA_IS_MAXAGE(lsa
)) {
324 ospf6_increment_retrans_count(lsa
);
325 ospf6_lsdb_add(ospf6_lsa_copy(lsa
), on
->retrans_list
);
327 ospf6_lsdb_add(ospf6_lsa_copy(lsa
), on
->summary_list
);
330 UNSET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_IBIT
);
331 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_EXCHANGE
, on
,
332 OSPF6_NEIGHBOR_EVENT_NEGOTIATION_DONE
);
337 int exchange_done(struct thread
*thread
)
339 struct ospf6_neighbor
*on
;
341 on
= (struct ospf6_neighbor
*)THREAD_ARG(thread
);
344 if (on
->state
!= OSPF6_NEIGHBOR_EXCHANGE
)
347 if (IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
348 zlog_debug("Neighbor Event %s: *ExchangeDone*", on
->name
);
350 THREAD_OFF(on
->thread_send_dbdesc
);
351 ospf6_lsdb_remove_all(on
->dbdesc_list
);
354 thread_add_timer (master, ospf6_neighbor_last_dbdesc_release, on,
355 on->ospf6_if->dead_interval);
358 if (on
->request_list
->count
== 0)
359 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_FULL
, on
,
360 OSPF6_NEIGHBOR_EVENT_EXCHANGE_DONE
);
362 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_LOADING
, on
,
363 OSPF6_NEIGHBOR_EVENT_EXCHANGE_DONE
);
365 if (on
->thread_send_lsreq
== NULL
)
366 on
->thread_send_lsreq
= thread_add_event(
367 master
, ospf6_lsreq_send
, on
, 0);
373 /* Check loading state. */
374 void ospf6_check_nbr_loading(struct ospf6_neighbor
*on
)
377 /* RFC2328 Section 10.9: When the neighbor responds to these requests
378 with the proper Link State Update packet(s), the Link state request
379 list is truncated and a new Link State Request packet is sent.
381 if ((on
->state
== OSPF6_NEIGHBOR_LOADING
)
382 || (on
->state
== OSPF6_NEIGHBOR_EXCHANGE
)) {
383 if (on
->request_list
->count
== 0)
384 thread_add_event(master
, loading_done
, on
, 0);
385 else if (on
->last_ls_req
== NULL
) {
386 if (on
->thread_send_lsreq
!= NULL
)
387 THREAD_OFF(on
->thread_send_lsreq
);
388 on
->thread_send_lsreq
= thread_add_event(
389 master
, ospf6_lsreq_send
, on
, 0);
394 int loading_done(struct thread
*thread
)
396 struct ospf6_neighbor
*on
;
398 on
= (struct ospf6_neighbor
*)THREAD_ARG(thread
);
401 if (on
->state
!= OSPF6_NEIGHBOR_LOADING
)
404 if (IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
405 zlog_debug("Neighbor Event %s: *LoadingDone*", on
->name
);
407 assert(on
->request_list
->count
== 0);
409 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_FULL
, on
,
410 OSPF6_NEIGHBOR_EVENT_LOADING_DONE
);
415 int adj_ok(struct thread
*thread
)
417 struct ospf6_neighbor
*on
;
418 struct ospf6_lsa
*lsa
;
420 on
= (struct ospf6_neighbor
*)THREAD_ARG(thread
);
423 if (IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
424 zlog_debug("Neighbor Event %s: *AdjOK?*", on
->name
);
426 if (on
->state
== OSPF6_NEIGHBOR_TWOWAY
&& need_adjacency(on
)) {
427 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_EXSTART
, on
,
428 OSPF6_NEIGHBOR_EVENT_ADJ_OK
);
429 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_MSBIT
);
430 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_MBIT
);
431 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_IBIT
);
433 THREAD_OFF(on
->thread_send_dbdesc
);
434 on
->thread_send_dbdesc
=
435 thread_add_event(master
, ospf6_dbdesc_send
, on
, 0);
437 } else if (on
->state
>= OSPF6_NEIGHBOR_EXSTART
&& !need_adjacency(on
)) {
438 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_TWOWAY
, on
,
439 OSPF6_NEIGHBOR_EVENT_ADJ_OK
);
440 ospf6_lsdb_remove_all(on
->summary_list
);
441 ospf6_lsdb_remove_all(on
->request_list
);
442 for (lsa
= ospf6_lsdb_head(on
->retrans_list
); lsa
;
443 lsa
= ospf6_lsdb_next(lsa
)) {
444 ospf6_decrement_retrans_count(lsa
);
445 ospf6_lsdb_remove(lsa
, on
->retrans_list
);
452 int seqnumber_mismatch(struct thread
*thread
)
454 struct ospf6_neighbor
*on
;
455 struct ospf6_lsa
*lsa
;
457 on
= (struct ospf6_neighbor
*)THREAD_ARG(thread
);
460 if (on
->state
< OSPF6_NEIGHBOR_EXCHANGE
)
463 if (IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
464 zlog_debug("Neighbor Event %s: *SeqNumberMismatch*", on
->name
);
466 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_EXSTART
, on
,
467 OSPF6_NEIGHBOR_EVENT_SEQNUMBER_MISMATCH
);
468 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_MSBIT
);
469 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_MBIT
);
470 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_IBIT
);
472 ospf6_lsdb_remove_all(on
->summary_list
);
473 ospf6_lsdb_remove_all(on
->request_list
);
474 for (lsa
= ospf6_lsdb_head(on
->retrans_list
); lsa
;
475 lsa
= ospf6_lsdb_next(lsa
)) {
476 ospf6_decrement_retrans_count(lsa
);
477 ospf6_lsdb_remove(lsa
, on
->retrans_list
);
480 THREAD_OFF(on
->thread_send_dbdesc
);
481 on
->dbdesc_seqnum
++; /* Incr seqnum as per RFC2328, sec 10.3 */
483 on
->thread_send_dbdesc
=
484 thread_add_event(master
, ospf6_dbdesc_send
, on
, 0);
489 int bad_lsreq(struct thread
*thread
)
491 struct ospf6_neighbor
*on
;
492 struct ospf6_lsa
*lsa
;
494 on
= (struct ospf6_neighbor
*)THREAD_ARG(thread
);
497 if (on
->state
< OSPF6_NEIGHBOR_EXCHANGE
)
500 if (IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
501 zlog_debug("Neighbor Event %s: *BadLSReq*", on
->name
);
503 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_EXSTART
, on
,
504 OSPF6_NEIGHBOR_EVENT_BAD_LSREQ
);
505 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_MSBIT
);
506 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_MBIT
);
507 SET_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_IBIT
);
509 ospf6_lsdb_remove_all(on
->summary_list
);
510 ospf6_lsdb_remove_all(on
->request_list
);
511 for (lsa
= ospf6_lsdb_head(on
->retrans_list
); lsa
;
512 lsa
= ospf6_lsdb_next(lsa
)) {
513 ospf6_decrement_retrans_count(lsa
);
514 ospf6_lsdb_remove(lsa
, on
->retrans_list
);
517 THREAD_OFF(on
->thread_send_dbdesc
);
518 on
->dbdesc_seqnum
++; /* Incr seqnum as per RFC2328, sec 10.3 */
520 on
->thread_send_dbdesc
=
521 thread_add_event(master
, ospf6_dbdesc_send
, on
, 0);
526 int oneway_received(struct thread
*thread
)
528 struct ospf6_neighbor
*on
;
529 struct ospf6_lsa
*lsa
;
531 on
= (struct ospf6_neighbor
*)THREAD_ARG(thread
);
534 if (on
->state
< OSPF6_NEIGHBOR_TWOWAY
)
537 if (IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
538 zlog_debug("Neighbor Event %s: *1Way-Received*", on
->name
);
540 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_INIT
, on
,
541 OSPF6_NEIGHBOR_EVENT_ONEWAY_RCVD
);
542 thread_add_event(master
, neighbor_change
, on
->ospf6_if
, 0);
544 ospf6_lsdb_remove_all(on
->summary_list
);
545 ospf6_lsdb_remove_all(on
->request_list
);
546 for (lsa
= ospf6_lsdb_head(on
->retrans_list
); lsa
;
547 lsa
= ospf6_lsdb_next(lsa
)) {
548 ospf6_decrement_retrans_count(lsa
);
549 ospf6_lsdb_remove(lsa
, on
->retrans_list
);
552 THREAD_OFF(on
->thread_send_dbdesc
);
553 THREAD_OFF(on
->thread_send_lsreq
);
554 THREAD_OFF(on
->thread_send_lsupdate
);
555 THREAD_OFF(on
->thread_send_lsack
);
560 int inactivity_timer(struct thread
*thread
)
562 struct ospf6_neighbor
*on
;
564 on
= (struct ospf6_neighbor
*)THREAD_ARG(thread
);
567 if (IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
568 zlog_debug("Neighbor Event %s: *InactivityTimer*", on
->name
);
570 on
->inactivity_timer
= NULL
;
571 on
->drouter
= on
->prev_drouter
= 0;
572 on
->bdrouter
= on
->prev_bdrouter
= 0;
574 ospf6_neighbor_state_change(OSPF6_NEIGHBOR_DOWN
, on
,
575 OSPF6_NEIGHBOR_EVENT_INACTIVITY_TIMER
);
576 thread_add_event(master
, neighbor_change
, on
->ospf6_if
, 0);
578 listnode_delete(on
->ospf6_if
->neighbor_list
, on
);
579 ospf6_neighbor_delete(on
);
586 /* show neighbor structure */
587 static void ospf6_neighbor_show(struct vty
*vty
, struct ospf6_neighbor
*on
)
596 /* Router-ID (Name) */
597 inet_ntop(AF_INET
, &on
->router_id
, router_id
, sizeof(router_id
));
598 #ifdef HAVE_GETNAMEINFO
601 #endif /*HAVE_GETNAMEINFO*/
605 if (on
->inactivity_timer
) {
606 s
= monotime_until(&on
->inactivity_timer
->u
.sands
, NULL
)
613 snprintf(deadtime
, sizeof(deadtime
), "%02ld:%02ld:%02ld", h
, m
, s
);
616 if (if_is_pointopoint(on
->ospf6_if
->interface
))
617 snprintf(nstate
, sizeof(nstate
), "PointToPoint");
619 if (on
->router_id
== on
->drouter
)
620 snprintf(nstate
, sizeof(nstate
), "DR");
621 else if (on
->router_id
== on
->bdrouter
)
622 snprintf(nstate
, sizeof(nstate
), "BDR");
624 snprintf(nstate
, sizeof(nstate
), "DROther");
628 monotime_since(&on
->last_changed
, &res
);
629 timerstring(&res
, duration
, sizeof(duration
));
632 vty_out (vty, "%-15s %3d %11s %6s/%-12s %11s %s[%s]%s",
633 "Neighbor ID", "Pri", "DeadTime", "State", "", "Duration",
634 "I/F", "State", VNL);
637 vty_out(vty
, "%-15s %3d %11s %8s/%-12s %11s %s[%s]%s", router_id
,
638 on
->priority
, deadtime
, ospf6_neighbor_state_str
[on
->state
],
639 nstate
, duration
, on
->ospf6_if
->interface
->name
,
640 ospf6_interface_state_str
[on
->ospf6_if
->state
], VNL
);
643 static void ospf6_neighbor_show_drchoice(struct vty
*vty
,
644 struct ospf6_neighbor
*on
)
647 char drouter
[16], bdrouter
[16];
649 struct timeval now
, res
;
652 vty_out (vty, "%-15s %6s/%-11s %-15s %-15s %s[%s]%s",
653 "RouterID", "State", "Duration", "DR", "BDR", "I/F",
657 inet_ntop(AF_INET
, &on
->router_id
, router_id
, sizeof(router_id
));
658 inet_ntop(AF_INET
, &on
->drouter
, drouter
, sizeof(drouter
));
659 inet_ntop(AF_INET
, &on
->bdrouter
, bdrouter
, sizeof(bdrouter
));
662 timersub(&now
, &on
->last_changed
, &res
);
663 timerstring(&res
, duration
, sizeof(duration
));
665 vty_out(vty
, "%-15s %8s/%-11s %-15s %-15s %s[%s]%s", router_id
,
666 ospf6_neighbor_state_str
[on
->state
], duration
, drouter
,
667 bdrouter
, on
->ospf6_if
->interface
->name
,
668 ospf6_interface_state_str
[on
->ospf6_if
->state
], VNL
);
671 static void ospf6_neighbor_show_detail(struct vty
*vty
,
672 struct ospf6_neighbor
*on
)
674 char drouter
[16], bdrouter
[16];
675 char linklocal_addr
[64], duration
[32];
676 struct timeval now
, res
;
677 struct ospf6_lsa
*lsa
;
679 inet_ntop(AF_INET6
, &on
->linklocal_addr
, linklocal_addr
,
680 sizeof(linklocal_addr
));
681 inet_ntop(AF_INET
, &on
->drouter
, drouter
, sizeof(drouter
));
682 inet_ntop(AF_INET
, &on
->bdrouter
, bdrouter
, sizeof(bdrouter
));
685 timersub(&now
, &on
->last_changed
, &res
);
686 timerstring(&res
, duration
, sizeof(duration
));
688 vty_out(vty
, " Neighbor %s%s", on
->name
, VNL
);
689 vty_out(vty
, " Area %s via interface %s (ifindex %d)%s",
690 on
->ospf6_if
->area
->name
, on
->ospf6_if
->interface
->name
,
691 on
->ospf6_if
->interface
->ifindex
, VNL
);
692 vty_out(vty
, " His IfIndex: %d Link-local address: %s%s",
693 on
->ifindex
, linklocal_addr
, VNL
);
694 vty_out(vty
, " State %s for a duration of %s%s",
695 ospf6_neighbor_state_str
[on
->state
], duration
, VNL
);
696 vty_out(vty
, " His choice of DR/BDR %s/%s, Priority %d%s", drouter
,
697 bdrouter
, on
->priority
, VNL
);
698 vty_out(vty
, " DbDesc status: %s%s%s SeqNum: %#lx%s",
699 (CHECK_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_IBIT
) ? "Initial "
701 (CHECK_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_MBIT
) ? "More " : ""),
702 (CHECK_FLAG(on
->dbdesc_bits
, OSPF6_DBDESC_MSBIT
) ? "Master"
704 (u_long
)ntohl(on
->dbdesc_seqnum
), VNL
);
706 vty_out(vty
, " Summary-List: %d LSAs%s", on
->summary_list
->count
,
708 for (lsa
= ospf6_lsdb_head(on
->summary_list
); lsa
;
709 lsa
= ospf6_lsdb_next(lsa
))
710 vty_out(vty
, " %s%s", lsa
->name
, VNL
);
712 vty_out(vty
, " Request-List: %d LSAs%s", on
->request_list
->count
,
714 for (lsa
= ospf6_lsdb_head(on
->request_list
); lsa
;
715 lsa
= ospf6_lsdb_next(lsa
))
716 vty_out(vty
, " %s%s", lsa
->name
, VNL
);
718 vty_out(vty
, " Retrans-List: %d LSAs%s", on
->retrans_list
->count
,
720 for (lsa
= ospf6_lsdb_head(on
->retrans_list
); lsa
;
721 lsa
= ospf6_lsdb_next(lsa
))
722 vty_out(vty
, " %s%s", lsa
->name
, VNL
);
725 if (on
->thread_send_dbdesc
)
726 timersub(&on
->thread_send_dbdesc
->u
.sands
, &now
, &res
);
727 timerstring(&res
, duration
, sizeof(duration
));
728 vty_out(vty
, " %d Pending LSAs for DbDesc in Time %s [thread %s]%s",
729 on
->dbdesc_list
->count
, duration
,
730 (on
->thread_send_dbdesc
? "on" : "off"), VNL
);
731 for (lsa
= ospf6_lsdb_head(on
->dbdesc_list
); lsa
;
732 lsa
= ospf6_lsdb_next(lsa
))
733 vty_out(vty
, " %s%s", lsa
->name
, VNL
);
736 if (on
->thread_send_lsreq
)
737 timersub(&on
->thread_send_lsreq
->u
.sands
, &now
, &res
);
738 timerstring(&res
, duration
, sizeof(duration
));
739 vty_out(vty
, " %d Pending LSAs for LSReq in Time %s [thread %s]%s",
740 on
->request_list
->count
, duration
,
741 (on
->thread_send_lsreq
? "on" : "off"), VNL
);
742 for (lsa
= ospf6_lsdb_head(on
->request_list
); lsa
;
743 lsa
= ospf6_lsdb_next(lsa
))
744 vty_out(vty
, " %s%s", lsa
->name
, VNL
);
747 if (on
->thread_send_lsupdate
)
748 timersub(&on
->thread_send_lsupdate
->u
.sands
, &now
, &res
);
749 timerstring(&res
, duration
, sizeof(duration
));
751 " %d Pending LSAs for LSUpdate in Time %s [thread %s]%s",
752 on
->lsupdate_list
->count
, duration
,
753 (on
->thread_send_lsupdate
? "on" : "off"), VNL
);
754 for (lsa
= ospf6_lsdb_head(on
->lsupdate_list
); lsa
;
755 lsa
= ospf6_lsdb_next(lsa
))
756 vty_out(vty
, " %s%s", lsa
->name
, VNL
);
759 if (on
->thread_send_lsack
)
760 timersub(&on
->thread_send_lsack
->u
.sands
, &now
, &res
);
761 timerstring(&res
, duration
, sizeof(duration
));
762 vty_out(vty
, " %d Pending LSAs for LSAck in Time %s [thread %s]%s",
763 on
->lsack_list
->count
, duration
,
764 (on
->thread_send_lsack
? "on" : "off"), VNL
);
765 for (lsa
= ospf6_lsdb_head(on
->lsack_list
); lsa
;
766 lsa
= ospf6_lsdb_next(lsa
))
767 vty_out(vty
, " %s%s", lsa
->name
, VNL
);
769 ospf6_bfd_show_info(vty
, on
->bfd_info
, 0);
772 DEFUN (show_ipv6_ospf6_neighbor
,
773 show_ipv6_ospf6_neighbor_cmd
,
774 "show ipv6 ospf6 neighbor [<detail|drchoice>]",
780 "Display DR choices\n")
783 struct ospf6_neighbor
*on
;
784 struct ospf6_interface
*oi
;
785 struct ospf6_area
*oa
;
786 struct listnode
*i
, *j
, *k
;
787 void (*showfunc
)(struct vty
*, struct ospf6_neighbor
*);
789 OSPF6_CMD_CHECK_RUNNING();
790 showfunc
= ospf6_neighbor_show
;
793 if (!strncmp(argv
[idx_type
]->arg
, "de", 2))
794 showfunc
= ospf6_neighbor_show_detail
;
795 else if (!strncmp(argv
[idx_type
]->arg
, "dr", 2))
796 showfunc
= ospf6_neighbor_show_drchoice
;
799 if (showfunc
== ospf6_neighbor_show
)
800 vty_out(vty
, "%-15s %3s %11s %8s/%-12s %11s %s[%s]%s",
801 "Neighbor ID", "Pri", "DeadTime", "State", "IfState",
802 "Duration", "I/F", "State", VNL
);
803 else if (showfunc
== ospf6_neighbor_show_drchoice
)
804 vty_out(vty
, "%-15s %8s/%-11s %-15s %-15s %s[%s]%s", "RouterID",
805 "State", "Duration", "DR", "BDR", "I/F", "State", VNL
);
807 for (ALL_LIST_ELEMENTS_RO(ospf6
->area_list
, i
, oa
))
808 for (ALL_LIST_ELEMENTS_RO(oa
->if_list
, j
, oi
))
809 for (ALL_LIST_ELEMENTS_RO(oi
->neighbor_list
, k
, on
))
810 (*showfunc
)(vty
, on
);
816 DEFUN (show_ipv6_ospf6_neighbor_one
,
817 show_ipv6_ospf6_neighbor_one_cmd
,
818 "show ipv6 ospf6 neighbor A.B.C.D",
823 "Specify Router-ID as IPv4 address notation\n"
827 struct ospf6_neighbor
*on
;
828 struct ospf6_interface
*oi
;
829 struct ospf6_area
*oa
;
830 struct listnode
*i
, *j
, *k
;
831 void (*showfunc
)(struct vty
*, struct ospf6_neighbor
*);
834 OSPF6_CMD_CHECK_RUNNING();
835 showfunc
= ospf6_neighbor_show_detail
;
837 if ((inet_pton(AF_INET
, argv
[idx_ipv4
]->arg
, &router_id
)) != 1) {
838 vty_out(vty
, "Router-ID is not parsable: %s%s",
839 argv
[idx_ipv4
]->arg
, VNL
);
843 for (ALL_LIST_ELEMENTS_RO(ospf6
->area_list
, i
, oa
))
844 for (ALL_LIST_ELEMENTS_RO(oa
->if_list
, j
, oi
))
845 for (ALL_LIST_ELEMENTS_RO(oi
->neighbor_list
, k
, on
))
846 (*showfunc
)(vty
, on
);
851 void ospf6_neighbor_init(void)
853 install_element(VIEW_NODE
, &show_ipv6_ospf6_neighbor_cmd
);
854 install_element(VIEW_NODE
, &show_ipv6_ospf6_neighbor_one_cmd
);
857 DEFUN (debug_ospf6_neighbor
,
858 debug_ospf6_neighbor_cmd
,
859 "debug ospf6 neighbor [<state|event>]",
862 "Debug OSPFv3 Neighbor\n"
863 "Debug OSPFv3 Neighbor State Change\n"
864 "Debug OSPFv3 Neighbor Event\n")
867 unsigned char level
= 0;
870 if (!strncmp(argv
[idx_type
]->arg
, "s", 1))
871 level
= OSPF6_DEBUG_NEIGHBOR_STATE
;
872 else if (!strncmp(argv
[idx_type
]->arg
, "e", 1))
873 level
= OSPF6_DEBUG_NEIGHBOR_EVENT
;
875 level
= OSPF6_DEBUG_NEIGHBOR_STATE
| OSPF6_DEBUG_NEIGHBOR_EVENT
;
877 OSPF6_DEBUG_NEIGHBOR_ON(level
);
882 DEFUN (no_debug_ospf6_neighbor
,
883 no_debug_ospf6_neighbor_cmd
,
884 "no debug ospf6 neighbor [<state|event>]",
888 "Debug OSPFv3 Neighbor\n"
889 "Debug OSPFv3 Neighbor State Change\n"
890 "Debug OSPFv3 Neighbor Event\n")
893 unsigned char level
= 0;
896 if (!strncmp(argv
[idx_type
]->arg
, "s", 1))
897 level
= OSPF6_DEBUG_NEIGHBOR_STATE
;
898 if (!strncmp(argv
[idx_type
]->arg
, "e", 1))
899 level
= OSPF6_DEBUG_NEIGHBOR_EVENT
;
901 level
= OSPF6_DEBUG_NEIGHBOR_STATE
| OSPF6_DEBUG_NEIGHBOR_EVENT
;
903 OSPF6_DEBUG_NEIGHBOR_OFF(level
);
908 DEFUN (no_debug_ospf6
,
916 struct ospf6_lsa_handler
*handler
= NULL
;
918 OSPF6_DEBUG_ABR_OFF();
919 OSPF6_DEBUG_ASBR_OFF();
920 OSPF6_DEBUG_BROUTER_OFF();
921 OSPF6_DEBUG_BROUTER_SPECIFIC_ROUTER_OFF();
922 OSPF6_DEBUG_BROUTER_SPECIFIC_AREA_OFF();
923 OSPF6_DEBUG_FLOODING_OFF();
924 OSPF6_DEBUG_INTERFACE_OFF();
926 for (i
= 0; i
< vector_active(ospf6_lsa_handler_vector
); i
++) {
927 handler
= vector_slot(ospf6_lsa_handler_vector
, i
);
929 if (handler
!= NULL
) {
930 UNSET_FLAG(handler
->debug
, OSPF6_LSA_DEBUG
);
934 for (i
= 0; i
< 6; i
++)
935 OSPF6_DEBUG_MESSAGE_OFF(i
,
936 OSPF6_DEBUG_NEIGHBOR_STATE
937 | OSPF6_DEBUG_NEIGHBOR_EVENT
);
939 OSPF6_DEBUG_NEIGHBOR_OFF(OSPF6_DEBUG_NEIGHBOR_STATE
940 | OSPF6_DEBUG_NEIGHBOR_EVENT
);
941 OSPF6_DEBUG_ROUTE_OFF(OSPF6_DEBUG_ROUTE_TABLE
);
942 OSPF6_DEBUG_ROUTE_OFF(OSPF6_DEBUG_ROUTE_INTRA
);
943 OSPF6_DEBUG_ROUTE_OFF(OSPF6_DEBUG_ROUTE_INTER
);
944 OSPF6_DEBUG_ROUTE_OFF(OSPF6_DEBUG_ROUTE_MEMORY
);
945 OSPF6_DEBUG_SPF_OFF(OSPF6_DEBUG_SPF_PROCESS
);
946 OSPF6_DEBUG_SPF_OFF(OSPF6_DEBUG_SPF_TIME
);
947 OSPF6_DEBUG_SPF_OFF(OSPF6_DEBUG_SPF_DATABASE
);
948 OSPF6_DEBUG_ZEBRA_OFF(OSPF6_DEBUG_ZEBRA_SEND
| OSPF6_DEBUG_ZEBRA_RECV
);
953 int config_write_ospf6_debug_neighbor(struct vty
*vty
)
955 if (IS_OSPF6_DEBUG_NEIGHBOR(STATE
) && IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
956 vty_out(vty
, "debug ospf6 neighbor%s", VNL
);
957 else if (IS_OSPF6_DEBUG_NEIGHBOR(STATE
))
958 vty_out(vty
, "debug ospf6 neighbor state%s", VNL
);
959 else if (IS_OSPF6_DEBUG_NEIGHBOR(EVENT
))
960 vty_out(vty
, "debug ospf6 neighbor event%s", VNL
);
964 void install_element_ospf6_debug_neighbor(void)
966 install_element(ENABLE_NODE
, &debug_ospf6_neighbor_cmd
);
967 install_element(ENABLE_NODE
, &no_debug_ospf6_neighbor_cmd
);
968 install_element(ENABLE_NODE
, &no_debug_ospf6_cmd
);
969 install_element(CONFIG_NODE
, &debug_ospf6_neighbor_cmd
);
970 install_element(CONFIG_NODE
, &no_debug_ospf6_neighbor_cmd
);
971 install_element(CONFIG_NODE
, &no_debug_ospf6_cmd
);